]> git.ipfire.org Git - thirdparty/gcc.git/commitdiff
cobol: Eliminate various errors. [PR120244]
authorRobert Dubner <rdubner@symas.com>
Wed, 30 Jul 2025 13:54:13 +0000 (09:54 -0400)
committerRobert Dubner <rdubner@symas.com>
Thu, 31 Jul 2025 13:13:16 +0000 (09:13 -0400)
The following coding errors were located by running extended tests
through valgrind.  These changes repair the errors.

gcc/cobol/ChangeLog:

PR cobol/120244
* genapi.cc (get_level_88_domain): Increase array size for final byte.
(psa_FldLiteralA): Use correct length in build_string_literal call.
* scan.l: Use a loop instead of std:transform to avoid EOF overrun.
* scan_ante.h (binary_integer_usage): Use a variable-length buffer.

gcc/cobol/genapi.cc
gcc/cobol/scan.l
gcc/cobol/scan_ante.h

index 666802ea137e6b8d46d598f73baf1b7e53d18ab8..20341643182e618c51490dc9934db5008a64e5a6 100644 (file)
@@ -531,6 +531,14 @@ get_level_88_domain(size_t parent_capacity, cbl_field_t *var, size_t &returned_s
     free(stream);
     domain += 1;
     }
+
+  if( returned_size >= retval_capacity)
+    {
+    retval_capacity *= 2;
+    retval = static_cast<char *>(xrealloc(retval, retval_capacity));
+    }
+
+  gcc_assert(returned_size < retval_capacity);
   retval[returned_size++] = '\0';
   return retval;
   }
@@ -16765,9 +16773,9 @@ psa_FldLiteralA(struct cbl_field_t *field )
                                                 vs_file_static);
     actually_create_the_static_field(
                 field,
-                build_string_literal(field->data.capacity+1,
+                build_string_literal(field->data.capacity,
                                      buffer),
-                field->data.capacity+1,
+                field->data.capacity,
                 field->data.initial,
                 NULL_TREE,
                 field->var_decl_node);
index 2da38d82a2e7b1776e2b62d7ca637103a92d9e29..ba4c044e15e30272c12cadc0861dc38d6d695dcb 100644 (file)
@@ -1673,16 +1673,17 @@ B-SHIFT-RC
                    p += 2;
                    while( ISSPACE(*p) ) p++;
                    cbl_name_t name2;
-                   std::transform( p, p + sizeof(name2), name2,
-                                   []( char ch ) {
-                                     switch(ch) {
-                                     case '-':
-                                     case '_': return ch;
-                                     default:
-                                       if( ISALNUM(ch) ) return ch;
-                                     }
-                                     return '\0';
-                                   } );
+                    const char *pend = p + sizeof(name2);
+                    char *pout = name2;
+                    while( p < pend ) {
+                      char ch = *p++;
+                      if( ISALNUM(ch) || ch == '-' || ch == '_' )  {
+                        *pout++ = ch;
+                      } else {
+                        *pout++  = '\0';
+                        break;
+                      }
+                    }
                    symbol_elem_t *e = symbol_file(PROGRAM, name2);
                    /*
                     * For NAME IN FILENAME, we want the parser to handle it.
index 19ceb2b4a08bde60bd91421b863f88b26831b04c..c00826d652fd539b4b1cbd43d56a3fe832021c1e 100644 (file)
@@ -609,7 +609,9 @@ static const std::map <std::string, bint_t > binary_integers {
 
 static int
 binary_integer_usage( const char name[]) {
-  cbl_name_t uname = {};
+  // uname can't be cbl_name_t, because at this point name[] might have more
+  // than sizeof(cbl_name_t) characters.  The length check comes later.
+  char *uname = xstrdup(name);
   std::transform(name, name + strlen(name), uname, ftoupper);
 
   dbgmsg("%s:%d: checking %s in %zu keyword_aliases",
@@ -628,6 +630,7 @@ binary_integer_usage( const char name[]) {
   yylval.computational.signable = p->second.signable;
   dbgmsg("%s:%d: %s has type %d", __func__, __LINE__,
         uname, p->second.type );
+  free(uname);
   return p->second.token;
 }