From fb7db9ae3e8ac271651d1884a3611d30bac04a98 Mon Sep 17 00:00:00 2001
From: =?UTF-8?q?Sebastian=20Dr=C3=B6ge?= <sebastian@centricular.com>
Date: Tue, 9 Jul 2024 12:11:37 +0300
Subject: [PATCH 1/2] Use vasprintf() if available for error messages and
 otherwise vsnprintf()

vasprintf() is a GNU/BSD extension and would allocate as much memory as required
on the heap, similar to g_strdup_printf(). It's ridiculous that such a function
is still not provided as part of standard C.

If it's not available, use vsnprintf() to at least avoid stack/heap buffer
overflows, which can lead to arbitrary code execution.

Thanks to Noriko Totsuka for reporting.

Fixes JVN#02030803 / JPCERT#92912620 / CVE-2024-40897
Fixes #69

Part-of: <https://gitlab.freedesktop.org/gstreamer/orc/-/merge_requests/191>
---
 meson.build       |  1 +
 orc/orccompiler.c |  6 +++++-
 orc/orcparse.c    | 14 +++++++++++---
 3 files changed, 17 insertions(+), 4 deletions(-)

#diff --git a/meson.build b/meson.build
#index c7ba5d7d..fe8c6016 100644
#--- a/meson.build
#+++ b/meson.build
#@@ -136,6 +136,7 @@ int main() {
# '''
# cdata.set('HAVE_MONOTONIC_CLOCK', cc.compiles(monotonic_test))
# cdata.set('HAVE_GETTIMEOFDAY', cc.has_function('gettimeofday'))
#+cdata.set('HAVE_VASPRINTF', cc.has_function('vasprintf'))
# cdata.set('HAVE_POSIX_MEMALIGN', cc.has_function('posix_memalign'))
# cdata.set('HAVE_MMAP', cc.has_function('mmap'))
# 
diff --git a/orc/orccompiler.c b/orc/orccompiler.c
index 1e24b8a3..d3394612 100644
--- a/orc/orccompiler.c
+++ b/orc/orccompiler.c
@@ -1489,8 +1489,12 @@ orc_compiler_error_valist (OrcCompiler *compiler, const char *fmt,
 
   if (compiler->error_msg) return;
 
+#ifdef HAVE_VASPRINTF
+  vasprintf (&s, fmt, args);
+#else
   s = malloc (ORC_COMPILER_ERROR_BUFFER_SIZE);
-  vsprintf (s, fmt, args);
+  vsnprintf (s, ORC_COMPILER_ERROR_BUFFER_SIZE, fmt, args);
+#endif
   compiler->error_msg = s;
   compiler->error = TRUE;
   compiler->result = ORC_COMPILE_RESULT_UNKNOWN_COMPILE;
diff --git a/orc/orcparse.c b/orc/orcparse.c
index b0d67095..ae4f1b6b 100644
--- a/orc/orcparse.c
+++ b/orc/orcparse.c
@@ -16,6 +16,7 @@
  * @short_description: Parse Orc source code
  */
 
+#define ORC_ERROR_LENGTH 256
 
 typedef struct _OrcParser OrcParser;
 struct _OrcParser {
@@ -424,33 +425,42 @@ orc_parse_get_error_where (OrcParser *parser)
 static void
 orc_parse_log_valist (OrcParser *parser, const char *format, va_list args)
 {
-  char s[100];
   int len;
   
   if (parser->error_program != parser->program) {
     sprintf(s, "In function %s:\n", parser->program->name);
     len = strlen(s);
 
     if (parser->log_size + len + 1 >= parser->log_alloc) {
       parser->log_alloc += 100;
       parser->log = realloc (parser->log, parser->log_alloc);
     }
 
     strcpy (parser->log + parser->log_size, s);
     parser->log_size += len;
     parser->error_program = parser->program;
   }
 
-  vsprintf(s, format, args);
+#ifdef HAVE_VASPRINTF
+  char *s;
+  vasprintf (&s, format, args);
+#else
+  char s[ORC_ERROR_LENGTH] = { '\0' };
+  vsnprintf (s, sizeof (s), format, args);
+#endif
   len = strlen(s);
 
   if (parser->log_size + len + 1 >= parser->log_alloc) {
     parser->log_alloc += 100;
     parser->log = realloc (parser->log, parser->log_alloc);
   }
 
   strcpy (parser->log + parser->log_size, s);
   parser->log_size += len;
+
+#ifdef HAVE_VASPRINTF
+  free (s);
+#endif
 }
 
 static void
-- 
GitLab


From abd75edff9de9a06d0531b9db50963a0da42145c Mon Sep 17 00:00:00 2001
From: "L. E. Segovia" <amy@centricular.com>
Date: Tue, 9 Jul 2024 12:03:53 -0300
Subject: [PATCH 2/2] orccompiler, orcparse: Use secure UCRT printing functions
 on Windows

See #69

Part-of: <https://gitlab.freedesktop.org/gstreamer/orc/-/merge_requests/191>
---
 orc/orccompiler.c | 5 ++++-
 orc/orcparse.c    | 5 ++++-
 2 files changed, 8 insertions(+), 2 deletions(-)

diff --git a/orc/orccompiler.c b/orc/orccompiler.c
index d3394612..617ae295 100644
--- a/orc/orccompiler.c
+++ b/orc/orccompiler.c
@@ -1485,12 +1485,15 @@ static void
 orc_compiler_error_valist (OrcCompiler *compiler, const char *fmt,
     va_list args)
 {
-  char *s;
+  char *s = NULL;
 
   if (compiler->error_msg) return;
 
 #ifdef HAVE_VASPRINTF
   vasprintf (&s, fmt, args);
+#elif defined(_UCRT)
+  s = malloc (ORC_COMPILER_ERROR_BUFFER_SIZE);
+  vsnprintf_s (s, ORC_COMPILER_ERROR_BUFFER_SIZE, _TRUNCATE, fmt, args);
 #else
   s = malloc (ORC_COMPILER_ERROR_BUFFER_SIZE);
   vsnprintf (s, ORC_COMPILER_ERROR_BUFFER_SIZE, fmt, args);
diff --git a/orc/orcparse.c b/orc/orcparse.c
index ae4f1b6b..abeb9f59 100644
--- a/orc/orcparse.c
+++ b/orc/orcparse.c
@@ -429,8 +429,11 @@ orc_parse_add_error_valist (OrcParser *parser, const char *format, va_list args)
   }
 
 #ifdef HAVE_VASPRINTF
-  char *s;
+  char *s = NULL;
   vasprintf (&s, format, args);
+#elif defined(_UCRT)
+  char s[ORC_ERROR_LENGTH] = { '\0' };
+  vsnprintf_s (s, ORC_ERROR_LENGTH, _TRUNCATE, format, args);
 #else
   char s[ORC_ERROR_LENGTH] = { '\0' };
   vsnprintf (s, sizeof (s), format, args);
-- 
GitLab

