From 6bbd46007ca70ec1009e466e03f6844f94b4984e Mon Sep 17 00:00:00 2001 From: "copilot-swe-agent[bot]" <198982749+Copilot@users.noreply.github.com> Date: Thu, 4 Dec 2025 21:59:51 +0000 Subject: [PATCH 01/16] Address build issues in judySArray and judyS2Array Co-authored-by: starseeker <238416+starseeker@users.noreply.github.com> --- include/cllazyfile/judyS2Array.h | 4 ++-- include/cllazyfile/judySArray.h | 4 ++-- 2 files changed, 4 insertions(+), 4 deletions(-) diff --git a/include/cllazyfile/judyS2Array.h b/include/cllazyfile/judyS2Array.h index 726a6449a..c9b25db35 100644 --- a/include/cllazyfile/judyS2Array.h +++ b/include/cllazyfile/judyS2Array.h @@ -51,8 +51,8 @@ class judyS2Array { explicit judyS2Array( const judyS2Array< JudyValue > & other ): _maxKeyLen( other._maxKeyLen ), _success( other._success ) { _judyarray = judy_clone( other._judyarray ); _buff = new unsigned char[_maxKeyLen]; - strncpy( _buff, other._buff, _maxKeyLen ); - _buff[ _maxKeyLen ] = '\0'; //ensure that _buff is null-terminated, since strncpy won't necessarily do so + strncpy( reinterpret_cast< char * >( _buff ), reinterpret_cast< const char * >( other._buff ), _maxKeyLen - 1 ); + _buff[ _maxKeyLen - 1 ] = '\0'; //ensure that _buff is null-terminated find( _buff ); //set _lastSlot } diff --git a/include/cllazyfile/judySArray.h b/include/cllazyfile/judySArray.h index db75ec91c..f95716ec8 100644 --- a/include/cllazyfile/judySArray.h +++ b/include/cllazyfile/judySArray.h @@ -39,8 +39,8 @@ class judySArray { explicit judySArray( const judySArray< JudyValue > & other ): _maxKeyLen( other._maxKeyLen ), _success( other._success ) { _judyarray = judy_clone( other._judyarray ); _buff = new unsigned char[_maxKeyLen]; - strncpy( _buff, other._buff, _maxKeyLen ); - _buff[ _maxKeyLen ] = '\0'; //ensure that _buff is null-terminated, since strncpy won't necessarily do so + strncpy( reinterpret_cast< char * >( _buff ), reinterpret_cast< const char * >( other._buff ), _maxKeyLen - 1 ); + _buff[ _maxKeyLen - 1 ] = '\0'; //ensure that _buff is null-terminated find( _buff ); //set _lastSlot } From aa3b89affbf98c3e412d3e721bbdaa883b764847 Mon Sep 17 00:00:00 2001 From: "copilot-swe-agent[bot]" <198982749+Copilot@users.noreply.github.com> Date: Fri, 5 Dec 2025 17:19:18 +0000 Subject: [PATCH 02/16] Fix strdup implicit declaration errors for clang 18.1.3 compatibility Co-authored-by: starseeker <238416+starseeker@users.noreply.github.com> --- src/exp2python/src/classes_misc_python.c | 2 ++ src/exp2python/src/classes_python.c | 2 ++ 2 files changed, 4 insertions(+) diff --git a/src/exp2python/src/classes_misc_python.c b/src/exp2python/src/classes_misc_python.c index 5a34c5fa7..ce92e189f 100644 --- a/src/exp2python/src/classes_misc_python.c +++ b/src/exp2python/src/classes_misc_python.c @@ -1,5 +1,7 @@ #define CLASSES_MISC_C +#define _POSIX_C_SOURCE 200809L #include +#include #include "classes.h" /******************************************************************* ** FedEx parser output module for generating C++ class definitions diff --git a/src/exp2python/src/classes_python.c b/src/exp2python/src/classes_python.c index 109efecda..92764dc0f 100644 --- a/src/exp2python/src/classes_python.c +++ b/src/exp2python/src/classes_python.c @@ -24,7 +24,9 @@ N350 ( August 31, 1993 ) of ISO 10303 TC184/SC4/WG7. /* this is used to add new dictionary calls */ /* #define NEWDICT */ +#define _POSIX_C_SOURCE 200809L #include +#include #include #include "classes.h" From 6cbc18b87a1e35c731b4d97705358023db216329 Mon Sep 17 00:00:00 2001 From: "copilot-swe-agent[bot]" <198982749+Copilot@users.noreply.github.com> Date: Fri, 5 Dec 2025 17:37:24 +0000 Subject: [PATCH 03/16] Fix legacy C style warnings - add void to parameterless function declarations Co-authored-by: starseeker <238416+starseeker@users.noreply.github.com> --- include/express/alloc.h | 2 +- include/express/basic.h | 4 ++-- include/express/factory.h | 2 +- include/express/memory.h | 2 +- src/express/alloc.c | 2 +- src/express/entity.c | 2 +- src/express/error.c | 6 +++--- src/express/expr.c | 4 ++-- src/express/express.c | 12 ++++++------ src/express/factory.c | 2 +- src/express/hash.c | 2 +- src/express/lexact.c | 4 ++-- src/express/linklist.c | 2 +- src/express/memory.c | 2 +- src/express/resolve.c | 2 +- src/express/type.c | 2 +- src/express/variable.c | 2 +- 17 files changed, 27 insertions(+), 27 deletions(-) diff --git a/include/express/alloc.h b/include/express/alloc.h index 79199773a..1c95792d4 100644 --- a/include/express/alloc.h +++ b/include/express/alloc.h @@ -58,7 +58,7 @@ struct freelist_head { #endif }; -char * nnew(); +char * nnew(void); #include "error.h" diff --git a/include/express/basic.h b/include/express/basic.h index f7c6b90f0..191924812 100644 --- a/include/express/basic.h +++ b/include/express/basic.h @@ -93,8 +93,8 @@ /* function pointer types */ /**************************/ -typedef void ( *voidFuncptr )(); -typedef int ( *intFuncptr )(); +typedef void ( *voidFuncptr )(void); +typedef int ( *intFuncptr )(void); /* Option index - can we get rid of this? */ extern SC_EXPRESS_EXPORT int sc_optind; diff --git a/include/express/factory.h b/include/express/factory.h index 4942256fe..f4400d9e7 100644 --- a/include/express/factory.h +++ b/include/express/factory.h @@ -3,6 +3,6 @@ #include "sc_export.h" -SC_EXPRESS_EXPORT void FACTORYinitialize(); +SC_EXPRESS_EXPORT void FACTORYinitialize(void); #endif /* __FACTORY_H_ */ diff --git a/include/express/memory.h b/include/express/memory.h index 3d1e58c74..02adac89e 100644 --- a/include/express/memory.h +++ b/include/express/memory.h @@ -3,6 +3,6 @@ #include "sc_export.h" -SC_EXPRESS_EXPORT void MEMORYinitialize(); +SC_EXPRESS_EXPORT void MEMORYinitialize(void); #endif // __MEMORY_H diff --git a/src/express/alloc.c b/src/express/alloc.c index e20cfa943..2a3979ba2 100644 --- a/src/express/alloc.c +++ b/src/express/alloc.c @@ -76,7 +76,7 @@ Freelist * create_freelist( struct freelist_head * flh, int bytes ) { } void -_ALLOCinitialize() { +_ALLOCinitialize(void) { #ifdef DEBUG_MALLOC malloc_debug( 2 ); #endif diff --git a/src/express/entity.c b/src/express/entity.c index 507b2c23f..7b26a7833 100644 --- a/src/express/entity.c +++ b/src/express/entity.c @@ -292,7 +292,7 @@ Entity ENTITYcopy( Entity e ) { } /** Initialize the Entity module. */ -void ENTITYinitialize() { +void ENTITYinitialize(void) { } /** diff --git a/src/express/error.c b/src/express/error.c index 9b63825c2..9367f0629 100644 --- a/src/express/error.c +++ b/src/express/error.c @@ -218,7 +218,7 @@ static int ERROR_printf( const char *format, ... ) { return result; } -static void ERROR_nexterror() { +static void ERROR_nexterror(void) { if( ERROR_string == ERROR_string_end ) { return; } @@ -455,7 +455,7 @@ ERRORreport_with_symbol( enum ErrorCode errnum, Symbol * sym, ... ) { va_end( args ); } -void ERRORnospace() { +void ERRORnospace(void) { fprintf( stderr, "%s: out of space\n", EXPRESSprogram_name ); ERRORabort( 0 ); } @@ -536,6 +536,6 @@ void ERRORsafe( jmp_buf env ) { memcpy( ERROR_safe_env, env, sizeof( jmp_buf ) ); } -void ERRORunsafe() { +void ERRORunsafe(void) { ERROR_unsafe = true; } diff --git a/src/express/expr.c b/src/express/expr.c index 19ab0af91..c48ec5909 100644 --- a/src/express/expr.c +++ b/src/express/expr.c @@ -85,7 +85,7 @@ Expression LITERAL_PI = EXPRESSION_NULL; Expression LITERAL_ZERO = EXPRESSION_NULL; Expression LITERAL_ONE; -void EXPop_init(); +void EXPop_init(void); static inline int OPget_number_of_operands( Op_Code op ) { if( ( op == OP_NEGATE ) || ( op == OP_NOT ) ) { @@ -760,7 +760,7 @@ void EXPop_create( int token_number, char * string, Resolve_expr_func * resolve_ EXPop_table[token_number].resolve = resolve_func; } -void EXPop_init() { +void EXPop_init(void) { EXPop_create( OP_AND, "AND", EXPresolve_op_logical ); EXPop_create( OP_ANDOR, "ANDOR", EXPresolve_op_logical ); EXPop_create( OP_ARRAY_ELEMENT, "[array element]", EXPresolve_op_array_like ); diff --git a/src/express/express.c b/src/express/express.c index f6a027ad2..760bddbfb 100644 --- a/src/express/express.c +++ b/src/express/express.c @@ -106,7 +106,7 @@ bool EXPRESSignore_duplicate_schemas = false; Function funcdef(char *name, int pcount, Type ret_typ); void procdef(char *name, int pcount); -void BUILTINSinitialize(); +void BUILTINSinitialize(void); Dictionary EXPRESSbuiltins; /* procedures/functions */ @@ -143,7 +143,7 @@ int EXPRESS_succeed( Express model ) { return 0; } -Express EXPRESScreate() { +Express EXPRESScreate(void) { Express model = SCOPEcreate( OBJ_EXPRESS ); model->u.express = ( struct Express_ * )calloc( 1, sizeof( struct Express_ ) ); return model; @@ -166,7 +166,7 @@ typedef struct Dir { char * leaf; } Dir; -static void EXPRESS_PATHinit() { +static void EXPRESS_PATHinit(void) { char * p; Dir * dir; @@ -245,7 +245,7 @@ static void EXPRESS_PATHfree( void ) { } /** inform object system about bit representation for handling pass diagnostics */ -void PASSinitialize() { +void PASSinitialize(void) { } /** Initialize the Express package. */ @@ -353,7 +353,7 @@ void EXPRESSparse( Express model, FILE * fp, char * filename ) { } /* TODO LEMON ought to put this in expparse.h */ -void parserInitState(); +void parserInitState(void); /** start parsing a new schema file */ static Express PARSERrun( char * filename, FILE * fp ) { @@ -798,7 +798,7 @@ void procdef(char *name, int pcount) { DICTdefine(EXPRESSbuiltins, name, p, 0, OBJ_PROCEDURE); } -void BUILTINSinitialize() { +void BUILTINSinitialize(void) { EXPRESSbuiltins = DICTcreate( 35 ); procdef("INSERT", 3 ); procdef("REMOVE", 2 ); diff --git a/src/express/factory.c b/src/express/factory.c index daf6ee7d3..3e8a6727b 100644 --- a/src/express/factory.c +++ b/src/express/factory.c @@ -34,7 +34,7 @@ Type Type_Set_Of_String; Type Type_Set_Of_Generic; Type Type_Bag_Of_Generic; -void FACTORYinitialize() { +void FACTORYinitialize(void) { /* Very commonly-used read-only types */ Type_Unknown = TYPEcreate( unknown_ ); Type_Dont_Care = TYPEcreate( special_ ); diff --git a/src/express/hash.c b/src/express/hash.c index f6de3b9f3..fabe6ba0f 100644 --- a/src/express/hash.c +++ b/src/express/hash.c @@ -131,7 +131,7 @@ static long HashAccesses, HashCollisions; */ void -HASHinitialize() { +HASHinitialize(void) { } Hash_Table diff --git a/src/express/lexact.c b/src/express/lexact.c index d0ae80a28..3f521850c 100644 --- a/src/express/lexact.c +++ b/src/express/lexact.c @@ -220,7 +220,7 @@ static void SCANpush_buffer( char * filename, FILE * fp ) { SCANbuffer.filename = current_filename = filename; } -static void SCANpop_buffer() { +static void SCANpop_buffer(void) { if( SCANbuffer.file != NULL ) { fclose( SCANbuffer.file ); } @@ -482,6 +482,6 @@ char * SCANstrdup( const char * s ) { return s2; } -long SCANtell() { +long SCANtell(void) { return yylineno; } diff --git a/src/express/linklist.c b/src/express/linklist.c index 7089dd81d..6acbea90d 100644 --- a/src/express/linklist.c +++ b/src/express/linklist.c @@ -29,7 +29,7 @@ void LISTinitialize( void ) { void LISTcleanup( void ) { } -Linked_List LISTcreate() { +Linked_List LISTcreate(void) { Linked_List list = LIST_new(); list->mark = LINK_new(); list->mark->next = list->mark->prev = list->mark; diff --git a/src/express/memory.c b/src/express/memory.c index da4db3751..6c3b1c5b6 100644 --- a/src/express/memory.c +++ b/src/express/memory.c @@ -47,7 +47,7 @@ struct freelist_head PCALL_fl; struct freelist_head RET_fl; struct freelist_head INCR_fl; -void MEMORYinitialize() { +void MEMORYinitialize(void) { _ALLOCinitialize(); ALLOCinitialize( &HASH_Table_fl, sizeof( struct Hash_Table_ ), 50, 50 ); diff --git a/src/express/resolve.c b/src/express/resolve.c index fa5797917..157529a5f 100644 --- a/src/express/resolve.c +++ b/src/express/resolve.c @@ -1203,7 +1203,7 @@ int WHEREresolve( Linked_List list, Scope scope, int need_self ) { } } -struct tag * TAGcreate_tags() { +struct tag * TAGcreate_tags(void) { extern int tag_count; return( ( struct tag * )calloc( tag_count, sizeof( struct tag ) ) ); diff --git a/src/express/type.c b/src/express/type.c index ffcba5915..c4b6a7104 100644 --- a/src/express/type.c +++ b/src/express/type.c @@ -220,7 +220,7 @@ return( false ); #endif /** Initialize the Type module */ -void TYPEinitialize() { +void TYPEinitialize(void) { } /** Clean up the Type module */ diff --git a/src/express/variable.c b/src/express/variable.c index b3ec9f88a..c15a41706 100644 --- a/src/express/variable.c +++ b/src/express/variable.c @@ -90,7 +90,7 @@ char * opcode_print( Op_Code o ); /** Initialize the Variable module. */ -void VARinitialize() { +void VARinitialize(void) { } /** VARget_simple_name From 845c3fdc34c90ef28de49c6d29f5106b7180aa1d Mon Sep 17 00:00:00 2001 From: Clifford Yapp <238416+starseeker@users.noreply.github.com> Date: Fri, 5 Dec 2025 14:01:54 -0500 Subject: [PATCH 04/16] Fix null pointer dereference in STEPattributeList operator[] Improves error handling in STEPattributeList operator[] - return an error attribute and set error state rather than trying to rely on crashing via a NULL deference. That's undefined behavior, so it was not guaranteed - this requires the calling code to check the return, but is *much* cleaner. Co-authored-by: starseeker <238416+starseeker@users.noreply.github.com> --- src/clstepcore/STEPattributeList.cc | 8 ++++++-- 1 file changed, 6 insertions(+), 2 deletions(-) diff --git a/src/clstepcore/STEPattributeList.cc b/src/clstepcore/STEPattributeList.cc index 2993dd275..2fce6592b 100644 --- a/src/clstepcore/STEPattributeList.cc +++ b/src/clstepcore/STEPattributeList.cc @@ -41,10 +41,14 @@ STEPattribute & STEPattributeList::operator []( int n ) { return *( a->attr ); } - // else + // else - error case: return a static error object to avoid undefined behavior + // The error object allows calling code to detect the error condition + static STEPattribute errorAttr; cerr << "\nERROR in STEP Core library: " << __FILE__ << ":" << __LINE__ << "\n" << _POC_ << "\n\n"; - return *( STEPattribute * ) 0; + errorAttr.Error().AppendToDetailMsg( "STEPattributeList::operator[] - index out of bounds" ); + errorAttr.Error().severity( SEVERITY_BUG ); + return errorAttr; } int STEPattributeList::list_length() { From 6ff7580814724e624fc15896bd246dda4c8fd465 Mon Sep 17 00:00:00 2001 From: "copilot-swe-agent[bot]" <198982749+Copilot@users.noreply.github.com> Date: Fri, 5 Dec 2025 21:15:28 +0000 Subject: [PATCH 05/16] Initial plan From 9880ca87bc8b2c35aeb2cdb807b2630c0b8b730f Mon Sep 17 00:00:00 2001 From: "copilot-swe-agent[bot]" <198982749+Copilot@users.noreply.github.com> Date: Fri, 5 Dec 2025 21:33:31 +0000 Subject: [PATCH 06/16] Update CMake version requirement for consistency Co-authored-by: starseeker <238416+starseeker@users.noreply.github.com> --- src/exppp/test/exppp_supertype_andor.cmake | 2 +- 1 file changed, 1 insertion(+), 1 deletion(-) diff --git a/src/exppp/test/exppp_supertype_andor.cmake b/src/exppp/test/exppp_supertype_andor.cmake index 547ad70a5..5c03a02a5 100644 --- a/src/exppp/test/exppp_supertype_andor.cmake +++ b/src/exppp/test/exppp_supertype_andor.cmake @@ -1,5 +1,5 @@ -cmake_minimum_required( VERSION 2.8 ) +cmake_minimum_required( VERSION 3.12 ) # executable is ${EXPPP}, input file is ${INFILE} From 4025beba4655d4a73c93ee6e11aa57ec23134231 Mon Sep 17 00:00:00 2001 From: Clifford Yapp <238416+starseeker@users.noreply.github.com> Date: Fri, 5 Dec 2025 17:07:18 -0500 Subject: [PATCH 07/16] fix BRL-CAD url --- ChangeLog | 2 +- 1 file changed, 1 insertion(+), 1 deletion(-) diff --git a/ChangeLog b/ChangeLog index 39c815bb2..c319eed22 100644 --- a/ChangeLog +++ b/ChangeLog @@ -5,7 +5,7 @@ This repo was moved and renamed in May 2012. Previously, it was at http://github.com/mpictor/StepClassLibrary Some are duplicates of changes recorded in the BRL-CAD repo: -http://brlcad.svn.sourceforge.net/viewvc/brlcad/brlcad/trunk/src/other/step/?view=log +https://github.com/BRL-CAD/brlcad/tree/158beae4556d94821938368951546384cba53107/src/other/ext/stepcode Pre-BRL-CAD changes: ************************************************************************ From 391f630af6741125651d04de9ee13cb40d4723e8 Mon Sep 17 00:00:00 2001 From: Clifford Yapp <238416+starseeker@users.noreply.github.com> Date: Mon, 8 Dec 2025 14:57:04 -0500 Subject: [PATCH 08/16] Try adjusting BRL-CAD check logic --- .github/workflows/build.yml | 112 +++++++++++++++++++----------------- 1 file changed, 59 insertions(+), 53 deletions(-) diff --git a/.github/workflows/build.yml b/.github/workflows/build.yml index 626c5887b..0191e1e44 100644 --- a/.github/workflows/build.yml +++ b/.github/workflows/build.yml @@ -164,16 +164,13 @@ jobs: brlcad_linux: name: BRL-CAD Linux step-g Test - runs-on: ubuntu-20.04 + runs-on: ubuntu-latest strategy: fail-fast: true steps: - name: Setup - CMake uses: lukka/get-cmake@latest - - name: Setup - Ninja - uses: seanmiddleditch/gha-setup-ninja@master - - name: Setup - System env: DEBIAN_FRONTEND: noninteractive @@ -181,41 +178,53 @@ jobs: sudo apt-get update # Install dev tools sudo apt-get install re2c lemon + sudo apt-get install xserver-xorg-dev libx11-dev libxi-dev libxext-dev libglu1-mesa-dev libfontconfig-dev + # Install tools + sudo apt-get install astyle re2c xsltproc libxml2-utils + # Install dependency dev pkgs + sudo apt-get install zlib1g-dev libpng-dev libjpeg-dev libtiff-dev libeigen3-dev libgdal-dev libassimp-dev libopencv-dev sudo apt-get clean - - name: Checkout + - name: Clone bext run: | - git clone --depth 1 https://github.com/BRL-CAD/brlcad.git -b main - cd brlcad/src/other/ext && rm -rf stepcode + git clone https://github.com/BRL-CAD/bext.git + cd bext/stepcode + cmake -E rm -r stepcode git clone --depth 1 https://github.com/stepcode/stepcode.git -b develop - # Ordinarily BRL-CAD keeps track of what files are supposed to be - # present in the repository. In this case we're not interested in - # updating the list to the working stepcode filelist, so use an empty - # list instead - echo "set(stepcode_ignore_files)" > stepcode.dist - cd ../../../../ + cd ../.. + + - name: Build bext + shell: powershell + run: | + cmake -E make_directory bext_build + cmake -S bext -B bext_build -DCMAKE_BUILD_TYPE=Release -DUSE_GDAL=OFF -DUSE_TCL=OFF -DUSE_QT=OFF -DCMAKE_INSTALL_PREFIX=${{ github.workspace }}\bext_output + cmake --build bext_build --config Release -j2 + # We only need the build ouputs (bext_output) after this point, so + # clean up to save space for the main BRL-CAD build. + cmake -E rm -rf bext + cmake -E rm -rf bext_build + - name: Checkout + run: | + git clone --depth 1 https://github.com/BRL-CAD/brlcad.git -b main + - name: Configure run: | - export PATH=$ENV{GITHUB_WORKSPACE}:$PATH - cd brlcad - cmake -S . -G Ninja -B build -DENABLE_ALL=ON -DCMAKE_BUILD_TYPE=Release -DEXT_BUILD_VERBOSE=ON - cd .. + cmake -E make_directory brlcad_build + cmake -S brlcad -B brlcad_build -DBRLAD_ENABLE_GDAL=OFF -DBRLCAD_ENABLE_TCL=OFF -DBRLCAD_ENABLE_QT=OFF -B build -G Ninja -DCMAKE_C_COMPILER="cl.exe" -DCMAKE_CXX_COMPILER="cl.exe" - name: Build run: | - export PATH=$ENV{GITHUB_WORKSPACE}:$PATH - cd brlcad - cmake --build build --config Release --target step-g + cd brlcad_build + cmake --build . --target step-g cd .. - name: Test run: | - export PATH=$ENV{GITHUB_WORKSPACE}:$PATH - cd brlcad/build - ./bin/step-g ../db/nist/NIST_MBE_PMI_3.stp -o nist3.g - cd ../.. + cd brlcad_build + ./bin/step-g ../brlcad/db/nist/NIST_MBE_PMI_3.stp -o nist3.g + cd .. brlcad_windows: @@ -227,51 +236,48 @@ jobs: - name: Setup - CMake uses: lukka/get-cmake@latest - - name: Setup - Ninja - uses: seanmiddleditch/gha-setup-ninja@master - - name: Add github workspace to path # https://github.community/t/deprecated-add-path/136621 run: echo "$ENV{GITHUB_WORKSPACE}" | Out-File -Append -FilePath $env:GITHUB_PATH -Encoding utf8 - - name: Add msbuild to PATH - uses: microsoft/setup-msbuild@v1.0.2 + - name: Clone bext + run: | + git clone https://github.com/BRL-CAD/bext.git + cd bext/stepcode + cmake -E rm -r stepcode + git clone --depth 1 https://github.com/stepcode/stepcode.git -b develop + cd ../.. + + - name: Build bext + shell: powershell + run: | + cmake -E make_directory bext_build + cmake -S bext -B bext_build -DCMAKE_BUILD_TYPE=Release -DUSE_GDAL=OFF -DUSE_TCL=OFF -DUSE_QT=OFF -DCMAKE_INSTALL_PREFIX=${{ github.workspace }}\bext_output + cmake --build bext_build --config Release -j2 + # We only need the build ouputs (bext_output) after this point, so + # clean up to save space for the main BRL-CAD build. + cmake -E rm -rf bext + cmake -E rm -rf bext_build - - name: Add cl.exe to PATH - uses: ilammy/msvc-dev-cmd@v1 - name: Checkout run: | git clone --depth 1 https://github.com/BRL-CAD/brlcad.git -b main - cd brlcad/src/other/ext - cmake -E rm -r stepcode - git clone --depth 1 https://github.com/stepcode/stepcode.git -b develop - # Ordinarily BRL-CAD keeps track of what files are supposed to be - # present in the repository. In this case we're not interested in - # updating the list to the working stepcode filelist, so use an empty - # list instead - echo "set(stepcode_ignore_files)" > stepcode.dist - cd ../../../../ - name: Configure run: | - cd brlcad && cmake -S . -B build -G Ninja -DCMAKE_C_COMPILER="cl.exe" -DCMAKE_CXX_COMPILER="cl.exe" -DSC_ENABLE_TESTING=ON - cd .. - # We do the following in order to help ensure files are "flushed" - # to disk before compilation is attempted - # https://superuser.com/a/1553374/1286142 - powershell Write-VolumeCache C - powershell Write-VolumeCache D + cmake -E make_directory brlcad_build + cmake -S brlcad -B brlcad_build -DBRLAD_ENABLE_GDAL=OFF -DBRLCAD_ENABLE_TCL=OFF -DBRLCAD_ENABLE_QT=OFF -B build -G Ninja -DCMAKE_C_COMPILER="cl.exe" -DCMAKE_CXX_COMPILER="cl.exe" - name: Build run: | - cd brlcad/build - ninja -j1 -v step-g - cd ../.. + cd brlcad_build + cmake --build . --target step-g + cd .. - name: Test run: | - cd brlcad/build - ./bin/step-g.exe ../db/nist/NIST_MBE_PMI_3.stp -o nist3.g - cd ../.. + cd brlcad_build + ./bin/step-g.exe ../brlcad/db/nist/NIST_MBE_PMI_3.stp -o nist3.g + cd .. From 5e2ac7ea7297f615716b9dcd4fa5412329c13ae7 Mon Sep 17 00:00:00 2001 From: Clifford Yapp <238416+starseeker@users.noreply.github.com> Date: Tue, 9 Dec 2025 09:49:07 -0500 Subject: [PATCH 09/16] syntax error --- .github/workflows/build.yml | 8 ++------ 1 file changed, 2 insertions(+), 6 deletions(-) diff --git a/.github/workflows/build.yml b/.github/workflows/build.yml index 0191e1e44..b358a5ab3 100644 --- a/.github/workflows/build.yml +++ b/.github/workflows/build.yml @@ -176,12 +176,8 @@ jobs: DEBIAN_FRONTEND: noninteractive run: | sudo apt-get update - # Install dev tools - sudo apt-get install re2c lemon - sudo apt-get install xserver-xorg-dev libx11-dev libxi-dev libxext-dev libglu1-mesa-dev libfontconfig-dev - # Install tools - sudo apt-get install astyle re2c xsltproc libxml2-utils - # Install dependency dev pkgs + sudo apt-get install re2c astyle xsltproc libxml2-utils + sudo apt-get install xserver-xorg-dev libx11-dev libxi-dev libxext-dev libglu1-mesa-dev libfontconfig-dev sudo apt-get install zlib1g-dev libpng-dev libjpeg-dev libtiff-dev libeigen3-dev libgdal-dev libassimp-dev libopencv-dev sudo apt-get clean From a74c755f1e57a7960c7e401587cbb2afa622fa25 Mon Sep 17 00:00:00 2001 From: Clifford Yapp <238416+starseeker@users.noreply.github.com> Date: Thu, 5 Feb 2026 15:14:50 -0500 Subject: [PATCH 10/16] More yml adjustments --- .github/workflows/build.yml | 7 ++++++- 1 file changed, 6 insertions(+), 1 deletion(-) diff --git a/.github/workflows/build.yml b/.github/workflows/build.yml index b358a5ab3..f8a6d5cc1 100644 --- a/.github/workflows/build.yml +++ b/.github/workflows/build.yml @@ -190,7 +190,6 @@ jobs: cd ../.. - name: Build bext - shell: powershell run: | cmake -E make_directory bext_build cmake -S bext -B bext_build -DCMAKE_BUILD_TYPE=Release -DUSE_GDAL=OFF -DUSE_TCL=OFF -DUSE_QT=OFF -DCMAKE_INSTALL_PREFIX=${{ github.workspace }}\bext_output @@ -236,6 +235,12 @@ jobs: # https://github.community/t/deprecated-add-path/136621 run: echo "$ENV{GITHUB_WORKSPACE}" | Out-File -Append -FilePath $env:GITHUB_PATH -Encoding utf8 + - name: Add msbuild to PATH + uses: microsoft/setup-msbuild@v1.0.2 + + - name: Add cl.exe to PATH + uses: ilammy/msvc-dev-cmd@v1 + - name: Clone bext run: | git clone https://github.com/BRL-CAD/bext.git From 58732df22c4cadda82b4c535f8613e2caef80df6 Mon Sep 17 00:00:00 2001 From: Clifford Yapp <238416+starseeker@users.noreply.github.com> Date: Thu, 5 Feb 2026 17:16:23 -0500 Subject: [PATCH 11/16] Use snprintf instead of sprintf. There are probably other string handling modernizations to do here... --- src/cldai/sdaiBinary.cc | 6 +- src/cldai/sdaiEnum.cc | 12 +- src/cleditor/STEPfile.cc | 18 +-- src/cleditor/STEPfile.inline.cc | 6 +- src/clstepcore/STEPaggrEntity.cc | 4 +- src/clstepcore/STEPaggrInt.cc | 2 +- src/clstepcore/STEPaggrSelect.cc | 2 +- src/clstepcore/STEPaggregate.cc | 2 +- src/clstepcore/STEPattribute.cc | 10 +- src/clstepcore/STEPcomplex.cc | 4 +- src/clstepcore/instmgr.cc | 10 +- src/clstepcore/read_func.cc | 8 +- src/clstepcore/sdaiApplication_instance.cc | 40 ++--- src/exp2cxx/classes.c | 12 +- src/exp2cxx/classes_entity.c | 2 +- src/exp2cxx/classes_misc.c | 2 +- src/exp2cxx/classes_type.c | 48 +++--- src/exp2cxx/classes_type.h | 2 +- src/exp2cxx/classes_wrapper.cc | 18 ++- src/exp2python/src/classes_misc_python.c | 2 +- src/exp2python/src/classes_python.c | 2 +- src/exp2python/src/classes_wrapper_python.cc | 12 +- src/exppp/CMakeLists.txt | 2 +- src/exppp/exppp.c | 2 +- src/exppp/{pretty_expr.c => pretty_expr.cc} | 149 +++++++++++-------- src/exppp/pretty_expr.h | 29 ++-- src/exppp/pretty_schema.c | 2 +- src/express/express.c | 10 +- src/express/generated/expscan.c | 24 +-- 29 files changed, 238 insertions(+), 204 deletions(-) rename src/exppp/{pretty_expr.c => pretty_expr.cc} (77%) diff --git a/src/cldai/sdaiBinary.cc b/src/cldai/sdaiBinary.cc index e9c384f74..d165d1ac0 100644 --- a/src/cldai/sdaiBinary.cc +++ b/src/cldai/sdaiBinary.cc @@ -121,17 +121,17 @@ Severity SDAI_Binary::ReadBinary( istream & in, ErrorDescriptor * err, int Assig if( !validDelimiters ) { err->GreaterSeverity( SEVERITY_WARNING ); if( needDelims ) - sprintf( messageBuf, + snprintf( messageBuf, sizeof(messageBuf), "Binary value missing double quote delimiters.\n" ); else - sprintf( messageBuf, + snprintf( messageBuf, sizeof(messageBuf), "Mismatched double quote delimiters for binary.\n" ); err->AppendToDetailMsg( messageBuf ); err->AppendToUserMsg( messageBuf ); } } else { err->GreaterSeverity( SEVERITY_WARNING ); - sprintf( messageBuf, "Invalid binary value.\n" ); + snprintf( messageBuf, sizeof(messageBuf), "Invalid binary value.\n" ); err->AppendToDetailMsg( messageBuf ); err->AppendToUserMsg( messageBuf ); } diff --git a/src/cldai/sdaiEnum.cc b/src/cldai/sdaiEnum.cc index 8228855b5..2291144ac 100644 --- a/src/cldai/sdaiEnum.cc +++ b/src/cldai/sdaiEnum.cc @@ -211,10 +211,10 @@ Severity SDAI_LOGICAL::ReadEnum( istream & in, ErrorDescriptor * err, int Assign if( !validDelimiters ) { err->GreaterSeverity( SEVERITY_WARNING ); if( needDelims ) - sprintf( messageBuf, + snprintf( messageBuf, sizeof(messageBuf), "Enumerated value has invalid period delimiters.\n" ); else - sprintf( messageBuf, + snprintf( messageBuf, sizeof(messageBuf), "Mismatched period delimiters for enumeration.\n" ); err->AppendToDetailMsg( messageBuf ); err->AppendToUserMsg( messageBuf ); @@ -241,7 +241,7 @@ Severity SDAI_LOGICAL::ReadEnum( istream & in, ErrorDescriptor * err, int Assign } else { in.putback( c ); err->GreaterSeverity( SEVERITY_WARNING ); - sprintf( messageBuf, "Invalid enumeration value.\n" ); + snprintf( messageBuf, sizeof(messageBuf), "Invalid enumeration value.\n" ); err->AppendToDetailMsg( messageBuf ); err->AppendToUserMsg( messageBuf ); } @@ -489,10 +489,10 @@ Severity SDAI_Enum::ReadEnum( istream & in, ErrorDescriptor * err, int AssignVal if( !validDelimiters ) { err->GreaterSeverity( SEVERITY_WARNING ); if( needDelims ) - sprintf( messageBuf, + snprintf( messageBuf, sizeof(messageBuf), "Enumerated value has invalid period delimiters.\n" ); else - sprintf( messageBuf, + snprintf( messageBuf, sizeof(messageBuf), "Mismatched period delimiters for enumeration.\n" ); err->AppendToDetailMsg( messageBuf ); err->AppendToUserMsg( messageBuf ); @@ -519,7 +519,7 @@ Severity SDAI_Enum::ReadEnum( istream & in, ErrorDescriptor * err, int AssignVal } else { in.putback( c ); err->GreaterSeverity( SEVERITY_WARNING ); - sprintf( messageBuf, "Invalid enumeration value.\n" ); + snprintf( messageBuf, sizeof(messageBuf), "Invalid enumeration value.\n" ); err->AppendToDetailMsg( messageBuf ); err->AppendToUserMsg( messageBuf ); } diff --git a/src/cleditor/STEPfile.cc b/src/cleditor/STEPfile.cc index a05ef9a7f..7254e8935 100644 --- a/src/cleditor/STEPfile.cc +++ b/src/cleditor/STEPfile.cc @@ -528,7 +528,7 @@ int STEPfile::ReadData1( istream & in ) { } // end while loop if( _entsNotCreated ) { - sprintf( buf, + snprintf( buf, sizeof(buf), "STEPfile Reading File: Unable to create %d instances.\n\tIn first pass through DATA section. Check for invalid entity types.\n", _entsNotCreated ); _error.AppendToUserMsg( buf ); @@ -647,7 +647,7 @@ int STEPfile::ReadData2( istream & in, bool useTechCor ) { } // end while loop if( _entsInvalid ) { - sprintf( buf, + snprintf( buf, sizeof(buf), "%s \n\tTotal instances: %d \n\tInvalid instances: %d \n\tIncomplete instances (includes invalid instances): %d \n\t%s: %d.\n", "Second pass complete - instance summary:", total_instances, _entsInvalid, _entsIncomplete, "Warnings", @@ -1321,7 +1321,7 @@ SDAI_Application_instance * STEPfile::ReadInstance( istream & in, ostream & out, } } else { if( node->CurrState() == completeSE ) { - sprintf( errbuf, "WARNING in WORKING FILE: changing instance #%d state from completeSE to incompleteSE.\n", fileid ); + snprintf( errbuf, sizeof(errbuf), "WARNING in WORKING FILE: changing instance #%d state from completeSE to incompleteSE.\n", fileid ); _error.AppendToUserMsg( errbuf ); if( _fileType != WORKING_SESSION ) { node->ChangeState( incompleteSE ); @@ -1643,7 +1643,7 @@ Severity STEPfile::AppendFile( istream * in, bool useTechCor ) { } SetFileType( WORKING_SESSION ); } else { - sprintf( errbuf, + snprintf( errbuf, sizeof(errbuf), "Faulty input at beginning of file. \"ISO-10303-21;\" or" " \"STEP_WORKING_SESSION;\" expected. File not read: %s\n", ( ( FileName().compare( "-" ) == 0 ) ? "standard input" : FileName().c_str() ) ); @@ -1658,14 +1658,14 @@ Severity STEPfile::AppendFile( istream * in, bool useTechCor ) { rval = ReadHeader( *in ); cout << "\nHEADER read:"; if( rval < SEVERITY_WARNING ) { - sprintf( errbuf, + snprintf( errbuf, sizeof(errbuf), "Error: non-recoverable error in reading header section. " "There were %d errors encountered. Rest of file is ignored.\n", _errorCount ); _error.AppendToUserMsg( errbuf ); return rval; } else if( rval != SEVERITY_NULL ) { - sprintf( errbuf, " %d ERRORS\t %d WARNINGS\n\n", + snprintf( errbuf, sizeof(errbuf), " %d ERRORS\t %d WARNINGS\n\n", _errorCount, _warningCount ); cout << errbuf; } else { @@ -1683,7 +1683,7 @@ Severity STEPfile::AppendFile( istream * in, bool useTechCor ) { cout << "\nFIRST PASS complete: " << total_insts << " instances created.\n"; - sprintf( errbuf, + snprintf( errbuf, sizeof(errbuf), " %d ERRORS\t %d WARNINGS\n\n", _errorCount, _warningCount ); cout << errbuf; @@ -1727,7 +1727,7 @@ Severity STEPfile::AppendFile( istream * in, bool useTechCor ) { //check for "ENDSEC;" ReadTokenSeparator( *in2 ); if( total_insts != valid_insts ) { - sprintf( errbuf, "%d invalid instances in file: %s\n", + snprintf( errbuf, sizeof(errbuf), "%d invalid instances in file: %s\n", total_insts - valid_insts, ( ( FileName().compare( "-" ) == 0 ) ? "standard input" : FileName().c_str() ) ); _error.AppendToUserMsg( errbuf ); CloseInputFile( in2 ); @@ -1736,7 +1736,7 @@ Severity STEPfile::AppendFile( istream * in, bool useTechCor ) { cout << "\nSECOND PASS complete: " << valid_insts << " instances valid.\n"; - sprintf( errbuf, + snprintf( errbuf, sizeof(errbuf), " %d ERRORS\t %d WARNINGS\n\n", _errorCount, _warningCount ); _error.AppendToUserMsg( errbuf ); diff --git a/src/cleditor/STEPfile.inline.cc b/src/cleditor/STEPfile.inline.cc index 86af07564..a34149048 100644 --- a/src/cleditor/STEPfile.inline.cc +++ b/src/cleditor/STEPfile.inline.cc @@ -179,7 +179,7 @@ istream * STEPfile::OpenInputFile( const std::string filename ) { } else { if( SetFileName( filename ).empty() && ( filename.compare( "-" ) != 0 ) ) { char msg[BUFSIZ+1]; - sprintf( msg, "Unable to find file for input: \'%s\'. File not read.\n", filename.c_str() ); + snprintf( msg, sizeof(msg), "Unable to find file for input: \'%s\'. File not read.\n", filename.c_str() ); _error.AppendToUserMsg( msg ); _error.GreaterSeverity( SEVERITY_INPUT_ERROR ); return( 0 ); @@ -196,7 +196,7 @@ istream * STEPfile::OpenInputFile( const std::string filename ) { if( !in || !( in -> good() ) ) { char msg[BUFSIZ+1]; - sprintf( msg, "Unable to open file for input: \'%s\'. File not read.\n", filename.c_str() ); + snprintf( msg, sizeof(msg), "Unable to open file for input: \'%s\'. File not read.\n", filename.c_str() ); _error.AppendToUserMsg( msg ); _error.GreaterSeverity( SEVERITY_INPUT_ERROR ); return ( 0 ); @@ -231,7 +231,7 @@ ofstream * STEPfile::OpenOutputFile( std::string filename ) { } else { if( SetFileName( filename ).empty() ) { char msg[BUFSIZ+1]; - sprintf( msg, "can't find file: %s\nFile not written.\n", filename.c_str() ); + snprintf( msg, sizeof(msg), "can't find file: %s\nFile not written.\n", filename.c_str() ); _error.AppendToUserMsg( msg ); _error.GreaterSeverity( SEVERITY_INPUT_ERROR ); } diff --git a/src/clstepcore/STEPaggrEntity.cc b/src/clstepcore/STEPaggrEntity.cc index 02bfa3fb2..a29150873 100644 --- a/src/clstepcore/STEPaggrEntity.cc +++ b/src/clstepcore/STEPaggrEntity.cc @@ -91,7 +91,7 @@ Severity EntityAggregate::ReadValue( istream & in, ErrorDescriptor * err, CheckRemainingInput( in, &errdesc, buf, ",)" ); if( errdesc.severity() < SEVERITY_INCOMPLETE ) { - sprintf( errmsg, " index: %d\n", value_cnt ); + snprintf( errmsg, sizeof(errmsg), " index: %d\n", value_cnt ); errdesc.PrependToDetailMsg( errmsg ); err->AppendFromErrorArg( &errdesc ); } @@ -221,7 +221,7 @@ const char * EntityNode::asStr( std::string & s ) { return ""; } else { // otherwise return entity id char tmp [64]; - sprintf( tmp, "#%d", node->STEPfile_id ); + snprintf( tmp, sizeof(tmp), "#%d", node->STEPfile_id ); s = tmp; } return const_cast( s.c_str() ); diff --git a/src/clstepcore/STEPaggrInt.cc b/src/clstepcore/STEPaggrInt.cc index 936ab36d8..7d9e86884 100644 --- a/src/clstepcore/STEPaggrInt.cc +++ b/src/clstepcore/STEPaggrInt.cc @@ -96,7 +96,7 @@ const char * IntNode::asStr( std::string & s ) { const char * IntNode::STEPwrite( std::string & s, const char * ) { char tmp[BUFSIZ+1]; if( value != S_INT_NULL ) { - sprintf( tmp, "%ld", value ); + snprintf( tmp, sizeof(tmp), "%ld", value ); s = tmp; } else { s.clear(); diff --git a/src/clstepcore/STEPaggrSelect.cc b/src/clstepcore/STEPaggrSelect.cc index 73fe97176..5047e8bf3 100644 --- a/src/clstepcore/STEPaggrSelect.cc +++ b/src/clstepcore/STEPaggrSelect.cc @@ -87,7 +87,7 @@ Severity SelectAggregate::ReadValue( istream & in, ErrorDescriptor * err, CheckRemainingInput( in, &errdesc, buf, ",)" ); if( errdesc.severity() < SEVERITY_INCOMPLETE ) { - sprintf( errmsg, " index: %d\n", value_cnt ); + snprintf( errmsg, sizeof(errmsg), " index: %d\n", value_cnt ); errdesc.PrependToDetailMsg( errmsg ); err->AppendFromErrorArg( &errdesc ); } diff --git a/src/clstepcore/STEPaggregate.cc b/src/clstepcore/STEPaggregate.cc index 4336aa6f6..ef08778a4 100644 --- a/src/clstepcore/STEPaggregate.cc +++ b/src/clstepcore/STEPaggregate.cc @@ -174,7 +174,7 @@ Severity STEPaggregate::ReadValue( istream & in, ErrorDescriptor * err, CheckRemainingInput( in, &errdesc, buf, ",)" ); if( errdesc.severity() < SEVERITY_INCOMPLETE ) { - sprintf( errmsg, " index: %d\n", value_cnt ); + snprintf( errmsg, sizeof(errmsg), " index: %d\n", value_cnt ); errdesc.PrependToDetailMsg( errmsg ); err->AppendFromErrorArg( &errdesc ); } diff --git a/src/clstepcore/STEPattribute.cc b/src/clstepcore/STEPattribute.cc index ff07d55b7..487865687 100644 --- a/src/clstepcore/STEPattribute.cc +++ b/src/clstepcore/STEPattribute.cc @@ -1266,15 +1266,15 @@ void STEPattribute::AddErrorInfo() { errStr[0] = '\0'; if( SEVERITY_INPUT_ERROR < _error.severity() && _error.severity() < SEVERITY_NULL ) { - sprintf( errStr, " Warning: ATTRIBUTE '%s : %s : %d' - ", + snprintf( errStr, sizeof(errStr), " Warning: ATTRIBUTE '%s : %s : %d' - ", Name(), TypeName().c_str(), Type() ); _error.PrependToDetailMsg( errStr ); } else if( _error.severity() == SEVERITY_INPUT_ERROR ) { - sprintf( errStr, " Error: ATTRIBUTE '%s : %s : %d' - ", + snprintf( errStr, sizeof(errStr), " Error: ATTRIBUTE '%s : %s : %d' - ", Name(), TypeName().c_str(), Type() ); _error.PrependToDetailMsg( errStr ); } else if( _error.severity() <= SEVERITY_BUG ) { - sprintf( errStr, " BUG: ATTRIBUTE '%s : %s : %d' - ", + snprintf( errStr, sizeof(errStr), " BUG: ATTRIBUTE '%s : %s : %d' - ", Name(), TypeName().c_str(), Type() ); _error.PrependToDetailMsg( errStr ); } @@ -1302,12 +1302,12 @@ char STEPattribute::SkipBadAttr( istream & in, char * StopChars ) { } if( in.eof() ) { _error.GreaterSeverity( SEVERITY_INPUT_ERROR ); - sprintf( errStr, " Error: attribute '%s : %s : %d' - %s.\n", + snprintf( errStr, sizeof(errStr), " Error: attribute '%s : %s : %d' - %s.\n", Name(), TypeName().c_str(), Type(), "Unexpected EOF when skipping bad attr value" ); _error.AppendToDetailMsg( errStr ); } else { - sprintf( errStr, " Error: attribute '%s : %s : %d' - %s.\n", + snprintf( errStr, sizeof(errStr), " Error: attribute '%s : %s : %d' - %s.\n", Name(), TypeName().c_str(), Type(), "Invalid value" ); _error.AppendToDetailMsg( errStr ); } diff --git a/src/clstepcore/STEPcomplex.cc b/src/clstepcore/STEPcomplex.cc index 9451d6df6..719ffb1c4 100644 --- a/src/clstepcore/STEPcomplex.cc +++ b/src/clstepcore/STEPcomplex.cc @@ -661,7 +661,7 @@ void STEPcomplex::CopyAs( SDAI_Application_instance * se ) { char errStr[BUFSIZ+1]; cerr << "STEPcomplex::CopyAs() called with non-complex entity: " << __FILE__ << __LINE__ << "\n" << _POC_ "\n"; - sprintf( errStr, + snprintf( errStr, sizeof(errStr), "STEPcomplex::CopyAs(): %s - entity #%d.\n", "Programming ERROR - called with non-complex entity", STEPfile_id ); @@ -702,7 +702,7 @@ SDAI_Application_instance * STEPcomplex::Replicate() { char errStr[BUFSIZ+1]; cerr << "STEPcomplex::Replicate() name buffer too small: " << __FILE__ << __LINE__ << "\n" << _POC_ "\n"; - sprintf( errStr, + snprintf( errStr, sizeof(errStr), "STEPcomplex::Replicate(): %s - entity #%d.\n", "Programming ERROR - name buffer too small", STEPfile_id ); diff --git a/src/clstepcore/instmgr.cc b/src/clstepcore/instmgr.cc index 6b6cc6a7e..61212d4d6 100644 --- a/src/clstepcore/instmgr.cc +++ b/src/clstepcore/instmgr.cc @@ -115,11 +115,11 @@ InstMgr::VerifyInstances( ErrorDescriptor & err ) { if( !mn ) { ++errorCount; if( errorCount == 1 ) - sprintf( errbuf, + snprintf( errbuf, sizeof(errbuf), "VerifyInstances: Unable to verify the following instances: node %d", i ); else { - sprintf( errbuf, ", node %d", i ); + snprintf( errbuf, sizeof(errbuf), ", node %d", i ); } err.AppendToDetailMsg( errbuf ); @@ -139,18 +139,18 @@ InstMgr::VerifyInstances( ErrorDescriptor & err ) { } ++errorCount; if( errorCount == 1 ) - sprintf( errbuf, + snprintf( errbuf, sizeof(errbuf), "VerifyInstances: Unable to verify the following instances: #%d", se->StepFileId() ); else { - sprintf( errbuf, ", #%d", se->StepFileId() ); + snprintf( errbuf, sizeof(errbuf), ", #%d", se->StepFileId() ); } err.AppendToDetailMsg( errbuf ); } } } if( errorCount ) { - sprintf( errbuf, + snprintf( errbuf, sizeof(errbuf), "VerifyInstances: %d invalid instances in list.\n", errorCount ); err.AppendToUserMsg( errbuf ); diff --git a/src/clstepcore/read_func.cc b/src/clstepcore/read_func.cc index 9f31db401..f834251a7 100644 --- a/src/clstepcore/read_func.cc +++ b/src/clstepcore/read_func.cc @@ -153,7 +153,7 @@ std::string WriteReal( SDAI_Real val ) { // Also use G instead of g since G writes uppercase E (E instead of e // is also required by Part 21) when scientific notation is used - DAS - sprintf( rbuf, "%.*G", ( int ) RealNumPrecision, val ); + snprintf( rbuf, sizeof(rbuf), "%.*G", ( int ) RealNumPrecision, val ); if( !strchr( rbuf, '.' ) ) { if( strchr( rbuf, 'E' ) || strchr( rbuf, 'e' ) ) { char * expon = strchr( rbuf, 'E' ); @@ -490,7 +490,7 @@ void PushPastImbedAggr( istream & in, std::string & s, ErrorDescriptor * err ) { } if( c != ')' ) { err->GreaterSeverity( SEVERITY_INPUT_ERROR ); - sprintf( messageBuf, "Invalid aggregate value.\n" ); + snprintf( messageBuf, sizeof(messageBuf), "Invalid aggregate value.\n" ); err->AppendToDetailMsg( messageBuf ); s.append( ")" ); } else { @@ -518,7 +518,7 @@ void PushPastAggr1Dim( istream & in, std::string & s, ErrorDescriptor * err ) { while( in.good() && ( c != ')' ) ) { if( c == '(' ) { err->GreaterSeverity( SEVERITY_WARNING ); - sprintf( messageBuf, "Invalid aggregate value.\n" ); + snprintf( messageBuf, sizeof(messageBuf), "Invalid aggregate value.\n" ); err->AppendToDetailMsg( messageBuf ); } @@ -532,7 +532,7 @@ void PushPastAggr1Dim( istream & in, std::string & s, ErrorDescriptor * err ) { } if( c != ')' ) { err->GreaterSeverity( SEVERITY_INPUT_ERROR ); - sprintf( messageBuf, "Invalid aggregate value.\n" ); + snprintf( messageBuf, sizeof(messageBuf), "Invalid aggregate value.\n" ); err->AppendToDetailMsg( messageBuf ); s.append( ")" ); } else { diff --git a/src/clstepcore/sdaiApplication_instance.cc b/src/clstepcore/sdaiApplication_instance.cc index c44a2c5ea..0b0b4427a 100644 --- a/src/clstepcore/sdaiApplication_instance.cc +++ b/src/clstepcore/sdaiApplication_instance.cc @@ -106,7 +106,7 @@ SDAI_Application_instance * SDAI_Application_instance::Replicate() { if( IsComplex() ) { cerr << "STEPcomplex::Replicate() should be called: " << __FILE__ << __LINE__ << "\n" << _POC_ "\n"; - sprintf( errStr, + snprintf( errStr, sizeof(errStr), "SDAI_Application_instance::Replicate(): %s - entity #%d.\n", "Programming ERROR - STEPcomplex::Replicate() should be called", STEPfile_id ); @@ -151,7 +151,7 @@ void SDAI_Application_instance::STEPwrite_reference( ostream & out ) { const char * SDAI_Application_instance::STEPwrite_reference( std::string & buf ) { char tmp[64]; - sprintf( tmp, "#%d", STEPfile_id ); + snprintf( tmp, sizeof(tmp), "#%d", STEPfile_id ); buf = tmp; return const_cast( buf.c_str() ); } @@ -419,7 +419,7 @@ const char * SDAI_Application_instance::STEPwrite( std::string & buf, const char char instanceInfo[BUFSIZ+1]; std::string tmp; - sprintf( instanceInfo, "#%d=%s(", STEPfile_id, StrToUpper( EntityName( currSch ), tmp ) ); + snprintf( instanceInfo, sizeof(instanceInfo), "#%d=%s(", STEPfile_id, StrToUpper( EntityName( currSch ), tmp ) ); buf.append( instanceInfo ); int n = attributes.list_length(); @@ -443,7 +443,7 @@ void SDAI_Application_instance::PrependEntityErrMsg() { if( _error.severity() == SEVERITY_NULL ) { // if there is not an error already - sprintf( errStr, "\nERROR: ENTITY #%d %s\n", GetFileId(), + snprintf( errStr, sizeof(errStr), "\nERROR: ENTITY #%d %s\n", GetFileId(), EntityName() ); _error.PrependToDetailMsg( errStr ); } @@ -464,14 +464,14 @@ void SDAI_Application_instance::STEPread_error( char c, int i, istream & in, con if( _error.severity() == SEVERITY_NULL ) { // if there is not an error already - sprintf( errStr, "\nERROR: ENTITY #%d %s\n", GetFileId(), + snprintf( errStr, sizeof(errStr), "\nERROR: ENTITY #%d %s\n", GetFileId(), EntityName() ); _error.PrependToDetailMsg( errStr ); } if( ( i >= 0 ) && ( i < attributes.list_length() ) ) { // i is an attribute Error().GreaterSeverity( SEVERITY_WARNING ); - sprintf( errStr, " invalid data before type \'%s\'\n", + snprintf( errStr, sizeof(errStr), " invalid data before type \'%s\'\n", attributes[i].TypeName().c_str() ); _error.AppendToDetailMsg( errStr ); } else { @@ -487,7 +487,7 @@ void SDAI_Application_instance::STEPread_error( char c, int i, istream & in, con _error.AppendToDetailMsg( c ); _error.AppendToDetailMsg( '\n' ); - sprintf( errStr, "\nfinished reading #%d\n", STEPfile_id ); + snprintf( errStr, sizeof(errStr), "\nfinished reading #%d\n", STEPfile_id ); _error.AppendToDetailMsg( errStr ); return; } @@ -552,7 +552,7 @@ Severity SDAI_Application_instance::STEPread( int id, int idIncr, // set the severity for this entity _error.GreaterSeverity( severe ); - sprintf( errStr, " %s : ", attributes[i].Name() ); + snprintf( errStr, sizeof(errStr), " %s : ", attributes[i].Name() ); _error.AppendToDetailMsg( errStr ); // add attr name _error.AppendToDetailMsg( "Since using pre-technical corrigendum... missing asterisk for redefined attr.\n" ); @@ -583,7 +583,7 @@ Severity SDAI_Application_instance::STEPread( int id, int idIncr, // set the severity for this entity _error.GreaterSeverity( severe ); - sprintf( errStr, " %s : ", attributes[i].Name() ); + snprintf( errStr, sizeof(errStr), " %s : ", attributes[i].Name() ); _error.AppendToDetailMsg( errStr ); // add attr name _error.AppendToDetailMsg( attributes[i].Error().DetailMsg() ); // add attr error _error.AppendToUserMsg( attributes[i].Error().UserMsg() ); @@ -653,7 +653,7 @@ Severity SDAI_Application_instance::STEPread( int id, int idIncr, } } _error.AppendToDetailMsg( tmp.c_str() ); - sprintf( errStr, "\nfinished reading #%d\n", STEPfile_id ); + snprintf( errStr, sizeof(errStr), "\nfinished reading #%d\n", STEPfile_id ); _error.AppendToDetailMsg( errStr ); // end of imported code return _error.severity(); @@ -678,7 +678,7 @@ SDAI_Application_instance * ReadEntityRef( istream & in, ErrorDescriptor * err, int id = -1; in >> id; if( in.fail() ) { // there's been an error in input - sprintf( errStr, "Invalid entity reference value.\n" ); + snprintf( errStr, sizeof(errStr), "Invalid entity reference value.\n" ); err->AppendToDetailMsg( errStr ); err->AppendToUserMsg( errStr ); err->GreaterSeverity( SEVERITY_WARNING ); @@ -692,7 +692,7 @@ SDAI_Application_instance * ReadEntityRef( istream & in, ErrorDescriptor * err, if( !instances ) { cerr << "Internal error: " << __FILE__ << __LINE__ << "\n" << _POC_ "\n"; - sprintf( errStr, + snprintf( errStr, sizeof(errStr), "STEPread_reference(): %s - entity #%d %s.\n", "BUG - cannot read reference without the InstMgr", id, "is unknown" ); @@ -714,7 +714,7 @@ SDAI_Application_instance * ReadEntityRef( istream & in, ErrorDescriptor * err, } else { cerr << "Internal error: " << __FILE__ << __LINE__ << "\n" << _POC_ "\n"; - sprintf( errStr, + snprintf( errStr, sizeof(errStr), "STEPread_reference(): %s - entity #%d %s.\n", "BUG - MgrNode::GetSTEPentity returned NULL pointer", id, "is unknown" ); @@ -724,7 +724,7 @@ SDAI_Application_instance * ReadEntityRef( istream & in, ErrorDescriptor * err, return S_ENTITY_NULL; } } else { - sprintf( errStr, "Reference to non-existent ENTITY #%d.\n", + snprintf( errStr, sizeof(errStr), "Reference to non-existent ENTITY #%d.\n", id ); err->AppendToDetailMsg( errStr ); err->AppendToUserMsg( errStr ); @@ -761,7 +761,7 @@ Severity EntityValidLevel( SDAI_Application_instance * se, if( !ed || ( ed->NonRefType() != ENTITY_TYPE ) ) { err->GreaterSeverity( SEVERITY_BUG ); - sprintf( messageBuf, + snprintf( messageBuf, sizeof(messageBuf), " BUG: EntityValidLevel() called with %s", "missing or invalid EntityDescriptor\n" ); err->AppendToUserMsg( messageBuf ); @@ -772,7 +772,7 @@ Severity EntityValidLevel( SDAI_Application_instance * se, } if( !se || ( se == S_ENTITY_NULL ) ) { err->GreaterSeverity( SEVERITY_BUG ); - sprintf( messageBuf, + snprintf( messageBuf, sizeof(messageBuf), " BUG: EntityValidLevel() called with null pointer %s\n", "for SDAI_Application_instance argument." ); err->AppendToUserMsg( messageBuf ); @@ -800,7 +800,7 @@ Severity EntityValidLevel( SDAI_Application_instance * se, } } err->GreaterSeverity( SEVERITY_WARNING ); - sprintf( messageBuf, + snprintf( messageBuf, sizeof(messageBuf), " Entity #%d exists but is not a %s or descendant.\n", se->STEPfile_id, ed->Name() ); err->AppendToUserMsg( messageBuf ); @@ -809,7 +809,7 @@ Severity EntityValidLevel( SDAI_Application_instance * se, } } else { err->GreaterSeverity( SEVERITY_BUG ); - sprintf( messageBuf, + snprintf( messageBuf, sizeof(messageBuf), " BUG: EntityValidLevel(): SDAI_Application_instance #%d has a %s", se->STEPfile_id, "missing or invalid EntityDescriptor\n" ); err->AppendToUserMsg( messageBuf ); @@ -893,7 +893,7 @@ Severity EntityValidLevel( const char * attrValue, // string contain entity ref SDAI_Application_instance * se = mn->GetSTEPentity(); return EntityValidLevel( se, ed, err ); } else { - sprintf( messageBuf, + snprintf( messageBuf, sizeof(messageBuf), " Attribute's Entity Reference %s does not exist.\n", attrValue ); err->AppendToUserMsg( messageBuf ); @@ -908,7 +908,7 @@ Severity EntityValidLevel( const char * attrValue, // string contain entity ref return err->severity(); } - sprintf( messageBuf, "Invalid attribute entity reference value: '%s'.\n", + snprintf( messageBuf, sizeof(messageBuf), "Invalid attribute entity reference value: '%s'.\n", attrValue ); err->AppendToUserMsg( messageBuf ); err->AppendToDetailMsg( messageBuf ); diff --git a/src/exp2cxx/classes.c b/src/exp2cxx/classes.c index 40dcf46c2..42f6c02c0 100644 --- a/src/exp2cxx/classes.c +++ b/src/exp2cxx/classes.c @@ -159,19 +159,19 @@ void USEREFout( Schema schema, Dictionary refdict, Linked_List reflist, char * t first_time = false; } if( re->type == OBJ_TYPE ) { - sprintf( td_name, "%s", TYPEtd_name( ( Type )re->object ) ); + snprintf( td_name, sizeof(td_name), "%s", TYPEtd_name( ( Type )re->object ) ); } else if( re->type == OBJ_FUNCTION ) { - sprintf( td_name, "/* Function not implemented */ 0" ); + snprintf( td_name, sizeof(td_name), "/* Function not implemented */ 0" ); } else if( re->type == OBJ_PROCEDURE ) { - sprintf( td_name, "/* Procedure not implemented */ 0" ); + snprintf( td_name, sizeof(td_name), "/* Procedure not implemented */ 0" ); } else if( re->type == OBJ_RULE ) { - sprintf( td_name, "/* Rule not implemented */ 0" ); + snprintf( td_name, sizeof(td_name), "/* Rule not implemented */ 0" ); } else if( re->type == OBJ_ENTITY ) { - sprintf( td_name, "%s%s%s", + snprintf( td_name, sizeof(td_name), "%s%s%s", SCOPEget_name( ( ( Entity )re->object )->superscope ), ENT_PREFIX, ENTITYget_name( ( Entity )re->object ) ); } else { - sprintf( td_name, "/* %c from OBJ_? in expbasic.h not implemented */ 0", re->type ); + snprintf( td_name, sizeof(td_name), "/* %c from OBJ_? in expbasic.h not implemented */ 0", re->type ); } if( re->old != re->nnew ) { fprintf( file, " // object %s AS %s\n", re->old->name, diff --git a/src/exp2cxx/classes_entity.c b/src/exp2cxx/classes_entity.c index 39e69c8a1..fe8b8e113 100644 --- a/src/exp2cxx/classes_entity.c +++ b/src/exp2cxx/classes_entity.c @@ -856,7 +856,7 @@ void ENTITYincode_print( Entity entity, FILE * header, FILE * impl, Schema schem } else { /* manufacture new one(s) on the spot */ char typename_buf[MAX_LEN+1]; - print_typechain( header, impl, v->type, typename_buf, schema, v->name->symbol.name ); + print_typechain( header, impl, v->type, typename_buf, sizeof(typename_buf), schema, v->name->symbol.name ); fprintf( impl, " %s::%s%d%s%s =\n new %s" "(\"%s\",%s,%s,%s%s,\n *%s::%s%s);\n", SCHEMAget_name( schema ), ATTR_PREFIX, v->idx, diff --git a/src/exp2cxx/classes_misc.c b/src/exp2cxx/classes_misc.c index 9db5e7eb7..2b492a124 100644 --- a/src/exp2cxx/classes_misc.c +++ b/src/exp2cxx/classes_misc.c @@ -215,7 +215,7 @@ const char * TypeDescriptorName( Type t ) { ** by following through the entity they reference, as above. */ } - sprintf( b, "%s::%s%s", SCHEMAget_name( parent ), TYPEprefix( t ), + snprintf( b, sizeof(b), "%s::%s%s", SCHEMAget_name( parent ), TYPEprefix( t ), TYPEget_name( t ) ); return b; } diff --git a/src/exp2cxx/classes_type.c b/src/exp2cxx/classes_type.c index bce1d34fb..b4abdb034 100644 --- a/src/exp2cxx/classes_type.c +++ b/src/exp2cxx/classes_type.c @@ -22,6 +22,7 @@ N350 ( August 31, 1993 ) of ISO 10303 TC184/SC4/WG7. # include #endif /* _WIN32 */ +#include #include #include #include @@ -42,7 +43,7 @@ static void printEnumCreateBody( FILE *, const Type ); static void printEnumAggrCrHdr( FILE *, const Type ); static void printEnumAggrCrBody( FILE *, const Type ); -int TYPEget_RefTypeVarNm( const Type t, char * buf, Schema schema ); +int TYPEget_RefTypeVarNm( const Type t, char * buf, size_t buflen, Schema schema ); int isMultiDimAggregateType( const Type t ); @@ -121,7 +122,7 @@ void strcat_expr( Expression e, char * buf ) { strcat( buf, TYPEget_name( e ) ); } else if( TYPEget_body( e->type )->type == integer_ ) { char tmpbuf[30]; - sprintf( tmpbuf, "%d", e->u.integer ); + snprintf( tmpbuf, sizeof(tmpbuf), "%d", e->u.integer ); strcat( buf, tmpbuf ); } else { strcat( buf, "??" ); @@ -161,7 +162,7 @@ void strcat_bounds( TypeBody b, char * buf ) { ******************************************************************/ const char * EnumCElementName( Type type, Expression expr ) { static char buf [BUFSIZ+1]; - sprintf( buf, "%s__", + snprintf( buf, sizeof(buf), "%s__", EnumName( TYPEget_name( type ) ) ); strncat( buf, StrToLower( EXPget_name( expr ) ), BUFSIZ ); return buf; @@ -279,7 +280,7 @@ void TYPEenum_inc_print( const Type type, FILE * inc ) { /* DAS brandnew above */ /* print things for aggregate class */ - sprintf( enumAggrNm, "%s_agg", n ); + snprintf( enumAggrNm, sizeof(enumAggrNm), "%s_agg", n ); fprintf( inc, "\nclass %s_agg : public EnumAggregate {\n", n ); @@ -609,7 +610,7 @@ void TYPEprint_descriptions( const Type type, FILES * files, Schema schema ) { return; } - if( !TYPEget_RefTypeVarNm( type, typename_buf, schema ) ) { + if( !TYPEget_RefTypeVarNm( type, typename_buf, sizeof(typename_buf), schema ) ) { if( TYPEis_enumeration( type ) ) { TYPEPrint( type, files, schema ); } /* so we don't do anything for non-enums??? */ @@ -632,7 +633,7 @@ void TYPEprint_init( const Type type, FILE * header, FILE * impl, Schema schema /* fill in the TD's values in the SchemaInit function (it is already declared with basic values) */ - if( TYPEget_RefTypeVarNm( type, typename_buf, schema ) ) { + if( TYPEget_RefTypeVarNm( type, typename_buf, sizeof(typename_buf), schema ) ) { fprintf( impl, " %s->ReferentType(%s);\n", tdnm, typename_buf ); } else { switch( TYPEget_body( type )->type ) { @@ -643,7 +644,7 @@ void TYPEprint_init( const Type type, FILE * header, FILE * impl, Schema schema case list_: { if( isMultiDimAggregateType( type ) ) { print_typechain( header, impl, TYPEget_body( type )->base, - typename_buf, schema, type->symbol.name ); + typename_buf, sizeof(typename_buf), schema, type->symbol.name ); fprintf( impl, " %s->ReferentType(%s);\n", tdnm, typename_buf ); } @@ -763,7 +764,10 @@ void TYPEprint_new( const Type type, FILE * create, Schema schema, bool needWR ) Nov 2011 - MAP - modified to insert scope operator into variable name. Reason: use of namespace for global variables */ -int TYPEget_RefTypeVarNm( const Type t, char * buf, Schema schema ) { +int TYPEget_RefTypeVarNm( const Type t, char * buf, size_t buflen, Schema schema ) { + + if (!buf || !buflen) + return 0; /* It looks like TYPEget_head(t) is true when processing a type that refers to another type. e.g. when processing "name" in: @@ -773,7 +777,7 @@ int TYPEget_RefTypeVarNm( const Type t, char * buf, Schema schema ) { it refers to another Express TYPE stmt */ /* it would be a reference_ type */ /* a TypeDescriptor of the form t_ */ - sprintf( buf, "%s::%s%s", + snprintf( buf, buflen, "%s::%s%s", SCHEMAget_name( TYPEget_head( t )->superscope ), TYPEprefix( t ), TYPEget_name( TYPEget_head( t ) ) ); return 1; @@ -788,7 +792,7 @@ int TYPEget_RefTypeVarNm( const Type t, char * buf, Schema schema ) { case number_: /* one of the SCL builtin TypeDescriptors of the form t_STRING_TYPE, or t_REAL_TYPE */ - sprintf( buf, "%s%s", TD_PREFIX, FundamentalType( t, 0 ) ); + snprintf( buf, buflen, "%s%s", TD_PREFIX, FundamentalType( t, 0 ) ); return 1; break; @@ -799,7 +803,7 @@ int TYPEget_RefTypeVarNm( const Type t, char * buf, Schema schema ) { break; case entity_: - sprintf( buf, "%s", TYPEtd_name( t ) ); + snprintf( buf, buflen, "%s", TYPEtd_name( t ) ); /* following assumes we are not in a nested entity */ /* otherwise we should search upward for schema */ return 1; @@ -815,7 +819,7 @@ int TYPEget_RefTypeVarNm( const Type t, char * buf, Schema schema ) { if( isMultiDimAggregateType( t ) ) { if( TYPEget_name( TYPEget_body( t )->base ) ) { - sprintf( buf, "%s::%s%s", + snprintf( buf, buflen, "%s::%s%s", SCHEMAget_name( TYPEget_body( t )->base->superscope ), TYPEprefix( t ), TYPEget_name( TYPEget_body( t )->base ) ); return 1; @@ -832,19 +836,19 @@ int TYPEget_RefTypeVarNm( const Type t, char * buf, Schema schema ) { if( TYPEget_body( TYPEget_body( t )->base )->type == enumeration_ || TYPEget_body( TYPEget_body( t )->base )->type == select_ ) { - sprintf( buf, "%s", TYPEtd_name( TYPEget_body( t )->base ) ); + snprintf( buf, buflen, "%s", TYPEtd_name( TYPEget_body( t )->base ) ); return 1; } else if( TYPEget_name( TYPEget_body( t )->base ) ) { if( TYPEget_body( TYPEget_body( t )->base )->type == entity_ ) { - sprintf( buf, "%s", TYPEtd_name( TYPEget_body( t )->base ) ); + snprintf( buf, buflen, "%s", TYPEtd_name( TYPEget_body( t )->base ) ); return 1; } - sprintf( buf, "%s::%s%s", + snprintf( buf, buflen, "%s::%s%s", SCHEMAget_name( TYPEget_body( t )->base->superscope ), TYPEprefix( t ), TYPEget_name( TYPEget_body( t )->base ) ); return 1; } - return TYPEget_RefTypeVarNm( TYPEget_body( t )->base, buf, schema ); + return TYPEget_RefTypeVarNm( TYPEget_body( t )->base, buf, buflen, schema ); } break; default: @@ -882,7 +886,7 @@ int TYPEget_RefTypeVarNm( const Type t, char * buf, Schema schema ) { that can be referenced to refer to the type that was created for Type t. */ -void print_typechain( FILE * header, FILE * impl, const Type t, char * buf, Schema schema, const char * type_name ) { +void print_typechain( FILE * header, FILE * impl, const Type t, char * buf, size_t buflen, Schema schema, const char * type_name ) { /* if we've been called, current type has no name */ /* nor is it a built-in type */ /* the type_count variable is there for debugging purposes */ @@ -907,7 +911,7 @@ void print_typechain( FILE * header, FILE * impl, const Type t, char * buf, Sche " %s%d->AssignAggrCreator((AggregateCreator) create_%s);%s", TD_PREFIX, count, ctype, " // Creator function\n" ); - s = sprintf( name_buf, "%s%d", TD_PREFIX, count ); + s = snprintf( name_buf, sizeof(name_buf), "%s%d", TD_PREFIX, count ); assert( ( s > 0 ) && ( s < MAX_LEN ) ); AGGRprint_init( header, impl, t, name_buf, type_name ); @@ -930,7 +934,7 @@ void print_typechain( FILE * header, FILE * impl, const Type t, char * buf, Sche /* DAS ORIG SCHEMA FIX */ fprintf( impl, " %s%d->OriginatingSchema(%s::schema);\n", TD_PREFIX, count, SCHEMAget_name( schema ) ); - if( TYPEget_RefTypeVarNm( t, name_buf, schema ) ) { + if( TYPEget_RefTypeVarNm( t, name_buf, sizeof(name_buf), schema ) ) { fprintf( impl, " %s%d->ReferentType(%s);\n", TD_PREFIX, count, name_buf ); } else { Type base = 0; @@ -939,10 +943,10 @@ void print_typechain( FILE * header, FILE * impl, const Type t, char * buf, Sche if( TYPEget_body( t ) ) { base = TYPEget_body( t )->base; } - print_typechain( header, impl, base, callee_buffer, schema, type_name ); + print_typechain( header, impl, base, callee_buffer, sizeof(callee_buffer), schema, type_name ); fprintf( impl, " %s%d->ReferentType(%s);\n", TD_PREFIX, count, callee_buffer ); } - sprintf( buf, "%s%d", TD_PREFIX, count ); + snprintf( buf, buflen, "%s%d", TD_PREFIX, count ); /* Types */ fprintf( impl, " %s::schema->AddUnnamedType(%s%d);\n", SCHEMAget_name( schema ), TD_PREFIX, count ); @@ -1324,7 +1328,7 @@ char * TYPEget_express_type( const Type t ) { aggr_type = "Bag"; } - sprintf( retval, "%s of %s", + snprintf( retval, sizeof(retval), "%s of %s", aggr_type, TYPEget_express_type( bt ) ); /* this will declare extra memory when aggregate is > 1D */ diff --git a/src/exp2cxx/classes_type.h b/src/exp2cxx/classes_type.h index a15815b07..f2fc0370c 100644 --- a/src/exp2cxx/classes_type.h +++ b/src/exp2cxx/classes_type.h @@ -26,6 +26,6 @@ void TYPEselect_lib_print( const Type type, FILE * f ); void AGGRprint_init( FILE * header, FILE * impl, const Type t, const char * var_name, const char * aggr_name ); -void print_typechain( FILE * header, FILE * impl, const Type t, char * buf, Schema schema, const char * type_name ); +void print_typechain( FILE * header, FILE * impl, const Type t, char * buf, size_t buflen, Schema schema, const char * type_name ); #endif diff --git a/src/exp2cxx/classes_wrapper.cc b/src/exp2cxx/classes_wrapper.cc index ef874a790..e99f27e39 100644 --- a/src/exp2cxx/classes_wrapper.cc +++ b/src/exp2cxx/classes_wrapper.cc @@ -383,6 +383,7 @@ void INITFileFinish( FILE * initfile, Schema schema ) { ******************************************************************/ void SCHEMAprint( Schema schema, FILES * files, void * complexCol, int suffix ) { int ocnt = 0; + size_t remaining; char schnm[MAX_LEN+1], sufnm[MAX_LEN+1], fnm[MAX_LEN+1], *np; /* sufnm = schema name + suffix */ FILE * libfile, @@ -398,7 +399,7 @@ void SCHEMAprint( Schema schema, FILES * files, void * complexCol, int suffix ) /********** create files based on name of schema ***********/ /* return if failure */ /* 1. header file */ - sprintf( schnm, "%s%s", SCHEMA_FILE_PREFIX, StrToUpper( SCHEMAget_name( schema ) ) ); //TODO change file names to CamelCase? + snprintf( schnm, sizeof(schnm), "%s%s", SCHEMA_FILE_PREFIX, StrToUpper( SCHEMAget_name( schema ) ) ); //TODO change file names to CamelCase? if( suffix == 0 ) { ocnt = snprintf( sufnm, MAX_LEN, "%s", schnm ); if( ocnt > MAX_LEN ) { @@ -423,11 +424,12 @@ void SCHEMAprint( Schema schema, FILES * files, void * complexCol, int suffix ) fprintf( incfile, "#include \"schema.h\"\n" ); np = fnm + strlen( fnm ) - 1; /* point to end of constant part of string */ + remaining = (size_t)(fnm + sizeof(fnm) - np); /* 1.9 open/init unity files which allow faster compilation with fewer translation units */ initUnityFiles( sufnm, files ); /* 2. class source file */ - sprintf( np, "cc" ); + snprintf( np, remaining, "cc" ); if( !( libfile = ( files -> lib ) = FILEcreate( fnm ) ) ) { return; } @@ -436,7 +438,7 @@ void SCHEMAprint( Schema schema, FILES * files, void * complexCol, int suffix ) //TODO: Looks like this switches between 'schema.h' and a non-generic name. What is that name, //and how do we fully enable this feature (i.e. how to write the file with different name)? #ifdef SCHEMA_HANDLING - sprintf( np, "h" ); + snprintf( np, remaining, "h" ); fprintf( libfile, "#include <%s.h> \n", sufnm ); #else fprintf( libfile, "#include \"schema.h\"\n" ); @@ -623,6 +625,7 @@ void getMCPrint( Express express, FILE * schema_h, FILE * schema_cc ) { ******************************************************************/ void EXPRESSPrint( Express express, ComplexCollect & col, FILES * files ) { char fnm [MAX_LEN+1], *np; + size_t remaining; const char * schnm; /* schnm is really "express name" */ FILE * libfile; FILE * incfile; @@ -637,7 +640,7 @@ void EXPRESSPrint( Express express, ComplexCollect & col, FILES * files ) { /********** create files based on name of schema ***********/ /* return if failure */ /* 1. header file */ - sprintf( fnm, "%s.h", schnm = ClassName( EXPRESSget_basename( express ) ) ); + snprintf( fnm, sizeof(fnm), "%s.h", schnm = ClassName( EXPRESSget_basename( express ) ) ); if( !( incfile = ( files -> inc ) = FILEcreate( fnm ) ) ) { return; } @@ -646,10 +649,11 @@ void EXPRESSPrint( Express express, ComplexCollect & col, FILES * files ) { fprintf( incfile, "#include \"core/sdai.h\" \n" ); np = fnm + strlen( fnm ) - 1; /* point to end of constant part of string */ + remaining = (size_t)(fnm + sizeof(fnm) - np); /* 1.9 init unity files (large translation units, faster compilation) */ initUnityFiles( schnm, files ); /* 2. class source file */ - sprintf( np, "cc" ); + snprintf( np, remaining, "cc" ); if( !( libfile = ( files -> lib ) = FILEcreate( fnm ) ) ) { return; } @@ -658,7 +662,7 @@ void EXPRESSPrint( Express express, ComplexCollect & col, FILES * files ) { fprintf( libfile, "#include \"%s.h\" n", schnm ); // 3. header for namespace to contain all formerly-global variables - sprintf( fnm, "%sNames.h", schnm ); + snprintf( fnm, sizeof(fnm), "%sNames.h", schnm ); if( !( files->names = FILEcreate( fnm ) ) ) { return; } @@ -670,7 +674,7 @@ void EXPRESSPrint( Express express, ComplexCollect & col, FILES * files ) { /* 4. source code to initialize entity registry */ /* prints header of file for input function */ - sprintf( np, "init.cc" ); + snprintf( np, remaining, "init.cc" ); if( !( initfile = ( files -> init ) = FILEcreate( fnm ) ) ) { return; } diff --git a/src/exp2python/src/classes_misc_python.c b/src/exp2python/src/classes_misc_python.c index ce92e189f..7c57c5257 100644 --- a/src/exp2python/src/classes_misc_python.c +++ b/src/exp2python/src/classes_misc_python.c @@ -347,7 +347,7 @@ const char * TypeDescriptorName( Type t ) { ** by following through the entity they reference, as above. */ } - sprintf( b, "%s%s%s", SCHEMAget_name( parent ), TYPEprefix( t ), + snprintf( b, sizeof(b), "%s%s%s", SCHEMAget_name( parent ), TYPEprefix( t ), TYPEget_name( t ) ); return b; } diff --git a/src/exp2python/src/classes_python.c b/src/exp2python/src/classes_python.c index 92764dc0f..74001dfcd 100644 --- a/src/exp2python/src/classes_python.c +++ b/src/exp2python/src/classes_python.c @@ -1770,7 +1770,7 @@ void strcat_expr( Expression e, char * buf ) { strcat( buf, TYPEget_name( e ) ); } else if( TYPEget_body( e->type )->type == integer_ ) { char tmpbuf[30]; - sprintf( tmpbuf, "%d", e->u.integer ); + snprintf( tmpbuf, sizeof(tmpbuf), "%d", e->u.integer ); strcat( buf, tmpbuf ); } else { strcat( buf, "??" ); diff --git a/src/exp2python/src/classes_wrapper_python.cc b/src/exp2python/src/classes_wrapper_python.cc index c6842ba44..266f650e7 100644 --- a/src/exp2python/src/classes_wrapper_python.cc +++ b/src/exp2python/src/classes_wrapper_python.cc @@ -170,9 +170,9 @@ void SCHEMAprint( Schema schema, FILES * files, int suffix ) { /********** create files based on name of schema ***********/ /* return if failure */ /* 1. header file */ - sprintf( schnm, "%s", SCHEMAget_name( schema ) ); + snprintf( schnm, sizeof(schnm), "%s", SCHEMAget_name( schema ) ); if( suffix == 0 ) { - sprintf( sufnm, "%s", schnm ); + snprintf( sufnm, sizeof(sufnm), "%s", schnm ); } else { ocnt = snprintf( sufnm, MAX_LEN, "%s_%d", schnm, suffix ); if( ocnt > MAX_LEN ) { @@ -185,9 +185,10 @@ void SCHEMAprint( Schema schema, FILES * files, int suffix ) { } np = fnm + strlen( fnm ) - 1; /* point to end of constant part of string */ + size_t remaining = (size_t)(fnm + sizeof(fnm) - np); /* 2. class source file */ - sprintf( np, "py" ); + snprintf( np, remaining, "py" ); if( !( libfile = ( files -> lib ) = FILEcreate( fnm ) ) ) { return; } @@ -296,10 +297,11 @@ EXPRESSPrint( Express express, FILES * files ) { /********** create files based on name of schema ***********/ /* return if failure */ /* 1. header file */ - sprintf( fnm, "%s.h", schnm = ClassName( EXPRESSget_basename( express ) ) ); + snprintf( fnm, sizeof(fnm), "%s.h", schnm = ClassName( EXPRESSget_basename( express ) ) ); /* 2. class source file */ - //sprintf( np, "cc" ); + //size_t remaining = (size_t)(fnm + sizeof(fnm) - np); + //snprintf( np, remaining, "cc" ); if( !( libfile = ( files -> lib ) = FILEcreate( fnm ) ) ) { return; } diff --git a/src/exppp/CMakeLists.txt b/src/exppp/CMakeLists.txt index 0eada170b..e58090a1b 100644 --- a/src/exppp/CMakeLists.txt +++ b/src/exppp/CMakeLists.txt @@ -3,7 +3,7 @@ set(LIBEXPPP_SOURCES pretty_alg.c pretty_case.c pretty_entity.c - pretty_expr.c + pretty_expr.cc pretty_express.c pretty_func.c pretty_loop.c diff --git a/src/exppp/exppp.c b/src/exppp/exppp.c index ff929e57d..dd236066a 100644 --- a/src/exppp/exppp.c +++ b/src/exppp/exppp.c @@ -154,7 +154,7 @@ void wrap( const char * fmt, ... ) { || ( ( exppp_linelength == indent2 ) && ( curpos > indent2 ) ) ) { /* move to new continuation line */ char line[1000]; - sprintf( line, "\n%*s", indent2, "" ); + snprintf( line, sizeof(line), "\n%*s", indent2, "" ); exp_output( line, 1 + indent2 ); curpos = indent2; /* reset current position */ diff --git a/src/exppp/pretty_expr.c b/src/exppp/pretty_expr.cc similarity index 77% rename from src/exppp/pretty_expr.c rename to src/exppp/pretty_expr.cc index 1b9aeda7b..2db7267b0 100644 --- a/src/exppp/pretty_expr.c +++ b/src/exppp/pretty_expr.cc @@ -7,11 +7,16 @@ #include #include +#include +#include +#include + +extern "C" { #include "exppp.h" #include "pp.h" #include "pretty_expr.h" - +} /** print array bounds */ void EXPRbounds_out( TypeBody tb ) { @@ -224,7 +229,7 @@ void EXPRop__out( struct Op_Subexpression * oe, int paren, unsigned int previous } } -void EXPRop2__out( struct Op_Subexpression * eo, char * opcode, int paren, int pad, unsigned int previous_op ) { +void EXPRop2__out( struct Op_Subexpression * eo, const char * opcode, int paren, int pad, unsigned int previous_op ) { if( pad && paren && ( eo->op_code != previous_op ) ) { wrap( "( " ); } @@ -245,7 +250,7 @@ void EXPRop2__out( struct Op_Subexpression * eo, char * opcode, int paren, int p /** Print out a one-operand operation. If there were more than two of these * I'd generalize it to do padding, but it's not worth it. */ -void EXPRop1_out( struct Op_Subexpression * eo, char * opcode, int paren ) { +void EXPRop1_out( struct Op_Subexpression * eo, const char * opcode, int paren ) { if( paren ) { wrap( "( " ); } @@ -268,89 +273,124 @@ int EXPRop_length( struct Op_Subexpression * oe ) { return 0; } -/** returns printable representation of expression rather than printing it - * originally only used for general references, now being expanded to handle - * any kind of expression - * contains fragment of string, adds to it - */ -void EXPRstring( char * buffer, Expression e ) { +/* ---- C++ string-based builder (replaces unsafe EXPRstring/EXPRop_string) ---- */ + +static void appendf( std::string & out, const char * fmt, ... ) { + va_list ap; + va_start( ap, fmt ); + + va_list ap2; + va_copy( ap2, ap ); + + int n = std::vsnprintf( NULL, 0, fmt, ap ); + va_end( ap ); + + if( n > 0 ) { + size_t old = out.size(); + out.resize( old + ( size_t )n ); + std::vsnprintf( &out[0] + old, ( size_t )n + 1, fmt, ap2 ); + } + + va_end( ap2 ); +} + +static void EXPRstring_cpp( std::string & out, Expression e ); + +static void EXPRop_string_cpp( std::string & out, struct Op_Subexpression * oe ) { + EXPRstring_cpp( out, oe->op1 ); + switch( oe->op_code ) { + case OP_DOT: + out.push_back( '.' ); + break; + case OP_GROUP: + out.push_back( '\\' ); + break; + default: + out.append( "(* unknown op-expression *)" ); + } + EXPRstring_cpp( out, oe->op2 ); +} + +static void EXPRstring_cpp( std::string & out, Expression e ) { int i; switch( TYPEis( e->type ) ) { case integer_: if( e == LITERAL_INFINITY ) { - strcpy( buffer, "?" ); + out.append( "?" ); } else { - sprintf( buffer, "%d", e->u.integer ); + appendf( out, "%d", e->u.integer ); } break; case real_: if( e == LITERAL_PI ) { - strcpy( buffer, "PI" ); + out.append( "PI" ); } else if( e == LITERAL_E ) { - strcpy( buffer, "E" ); + out.append( "E" ); } else { - sprintf( buffer, "%s", real2exp( e->u.real ) ); + appendf( out, "%s", real2exp( e->u.real ) ); } break; case binary_: - sprintf( buffer, "%%%s", e->u.binary ); /* put "%" back */ + appendf( out, "%%%s", e->u.binary ); /* put "%" back */ break; case logical_: case boolean_: switch( e->u.logical ) { case Ltrue: - strcpy( buffer, "TRUE" ); + out.append( "TRUE" ); break; case Lfalse: - strcpy( buffer, "FALSE" ); + out.append( "FALSE" ); break; default: - strcpy( buffer, "UNKNOWN" ); + out.append( "UNKNOWN" ); break; } break; case string_: if( TYPEis_encoded( e->type ) ) { - sprintf( buffer, "\"%s\"", e->symbol.name ); + appendf( out, "\"%s\"", e->symbol.name ); } else { - sprintf( buffer, "%s", e->symbol.name ); + appendf( out, "%s", e->symbol.name ); } break; case entity_: case identifier_: case attribute_: case enumeration_: - strcpy( buffer, e->symbol.name ); + if( e->symbol.name ) { + out.append( e->symbol.name ); + } break; case query_: - sprintf( buffer, "QUERY ( %s <* ", e->u.query->local->name->symbol.name ); - EXPRstring( buffer + strlen( buffer ), e->u.query->aggregate ); - strcat( buffer, " | " ); - EXPRstring( buffer + strlen( buffer ), e->u.query->expression ); - strcat( buffer, " )" ); + appendf( out, "QUERY ( %s <* ", e->u.query->local->name->symbol.name ); + EXPRstring_cpp( out, e->u.query->aggregate ); + out.append( " | " ); + EXPRstring_cpp( out, e->u.query->expression ); + out.append( " )" ); break; case self_: - strcpy( buffer, "SELF" ); + out.append( "SELF" ); break; case funcall_: - sprintf( buffer, "%s( ", e->symbol.name ); + appendf( out, "%s( ", e->symbol.name ); i = 0; LISTdo( e->u.funcall.list, arg, Expression ) i++; if( i != 1 ) { - strcat( buffer, ", " ); + out.append( ", " ); } - EXPRstring( buffer + strlen( buffer ), arg ); + EXPRstring_cpp( out, arg ); LISTod - strcat( buffer, " )" ); + out.append( " )" ); break; case op_: - EXPRop_string( buffer, &e->e ); + EXPRop_string_cpp( out, &e->e ); break; case aggregate_: - strcpy( buffer, "[" ); + out.append( "[" ); i = 0; LISTdo( e->u.list, arg, Expression ) { bool repeat = arg->type->u.type->body->flags.repeat; @@ -358,48 +398,33 @@ void EXPRstring( char * buffer, Expression e ) { i++; if( i != 1 ) { if( repeat ) { - strcat( buffer, " : " ); + out.append( " : " ); } else { - strcat( buffer, ", " ); + out.append( ", " ); } } - EXPRstring( buffer + strlen( buffer ), arg ); + EXPRstring_cpp( out, arg ); } LISTod - strcat( buffer, "]" ); + out.append( "]" ); break; case oneof_: - strcpy( buffer, "ONEOF ( " ); + out.append( "ONEOF ( " ); i = 0; LISTdo( e->u.list, arg, Expression ) { i++; if( i != 1 ) { - strcat( buffer, ", " ); + out.append( ", " ); } - EXPRstring( buffer + strlen( buffer ), arg ); + EXPRstring_cpp( out, arg ); } LISTod - strcat( buffer, " )" ); - break; - default: - sprintf( buffer, "EXPRstring: unknown expression, type %d", TYPEis( e->type ) ); - fprintf( stderr, "%s", buffer ); - } -} - -void EXPRop_string( char * buffer, struct Op_Subexpression * oe ) { - EXPRstring( buffer, oe->op1 ); - switch( oe->op_code ) { - case OP_DOT: - strcat( buffer, "." ); - break; - case OP_GROUP: - strcat( buffer, "\\" ); + out.append( " )" ); break; default: - strcat( buffer, "(* unknown op-expression *)" ); + appendf( out, "EXPRstring: unknown expression, type %d", TYPEis( e->type ) ); + fprintf( stderr, "%s", out.c_str() ); } - EXPRstring( buffer + strlen( buffer ), oe->op2 ); } /** returns length of printable representation of expression w.o. printing it @@ -407,10 +432,10 @@ void EXPRop_string( char * buffer, struct Op_Subexpression * oe ) { * WARNING this *does* change the global 'curpos'! */ int EXPRlength( Expression e ) { - char buffer[10000]; - *buffer = '\0'; - EXPRstring( buffer, e ); - return( strlen( buffer ) ); + std::string out; + out.reserve( 256 ); + EXPRstring_cpp( out, e ); + return( ( int )out.size() ); } char * EXPRto_string( Expression e ) { diff --git a/src/exppp/pretty_expr.h b/src/exppp/pretty_expr.h index 633bdf3f1..6769780fa 100644 --- a/src/exppp/pretty_expr.h +++ b/src/exppp/pretty_expr.h @@ -1,36 +1,27 @@ #ifndef PRETTY_EXPR_H #define PRETTY_EXPR_H +#ifdef __cplusplus +extern "C" { +#endif + #include "../express/expbasic.h" #include "../express/express.h" - #define EXPR_out(e,p) EXPR__out(e,p,OP_UNKNOWN) #define EXPRop2_out(oe,string,paren,pad) \ EXPRop2__out(oe,string,paren,pad,OP_UNKNOWN) #define EXPRop_out(oe,paren) EXPRop__out(oe,paren,OP_UNKNOWN) void EXPRop__out( struct Op_Subexpression * oe, int paren, unsigned int previous_op ); -void EXPRop_string( char * buffer, struct Op_Subexpression * oe ); -void EXPRop1_out( struct Op_Subexpression * eo, char * opcode, int paren ); -void EXPRop2__out( struct Op_Subexpression * eo, char * opcode, int paren, int pad, unsigned int previous_op ); +void EXPRop1_out( struct Op_Subexpression * eo, const char * opcode, int paren ); +void EXPRop2__out( struct Op_Subexpression * eo, const char * opcode, int paren, int pad, unsigned int previous_op ); void EXPR__out( Expression e, int paren, unsigned int previous_op ); void EXPRbounds_out( TypeBody tb ); -int EXPRlength( Expression e ); + +#ifdef __cplusplus +} /* extern "C" */ +#endif #endif /* PRETTY_EXPR_H */ -/* -char * EXPRto_string( Expression e ); -void EXPR__out( Expression e, int paren, unsigned int previous_op ); -void EXPRbounds_out( TypeBody tb ); -int EXPRlength( Expression e ); -void EXPRop1_out( struct Op_Subexpression * eo, char * opcode, int paren ); -void EXPRop2__out( struct Op_Subexpression * eo, char * opcode, int paren, int pad, unsigned int previous_op ); -void EXPRop__out( struct Op_Subexpression * oe, int paren, unsigned int previous_op ); -int EXPRop_length( struct Op_Subexpression * oe ); -void EXPRop_string( char * buffer, struct Op_Subexpression * oe ); -void EXPRout( Expression e ); -void EXPRstring( char * buffer, Expression e ); -int EXPRto_buffer( Expression e, char * buffer, int length ); -*/ diff --git a/src/exppp/pretty_schema.c b/src/exppp/pretty_schema.c index c17ebe5be..ae2ad2d7c 100644 --- a/src/exppp/pretty_schema.c +++ b/src/exppp/pretty_schema.c @@ -69,7 +69,7 @@ char * SCHEMAout( Schema s ) { /* since we have to generate a filename, make sure we don't */ /* overwrite a valuable file */ - sprintf( exppp_filename_buffer, "%s.exp", s->symbol.name ); + snprintf( exppp_filename_buffer, sizeof(exppp_filename_buffer), "%s.exp", s->symbol.name ); if( 0 != ( f = fopen( exppp_filename_buffer, "r" ) ) ) { char * result = fgets( buf, PP_SMALL_BUF_SZ, f ); diff --git a/src/express/express.c b/src/express/express.c index 760bddbfb..f8f4c4fc8 100644 --- a/src/express/express.c +++ b/src/express/express.c @@ -227,7 +227,7 @@ static void EXPRESS_PATHinit(void) { strcpy( dir->full, start ); dir->leaf = dir->full + length; } else { - sprintf( dir->full, "%s/", start ); + snprintf( dir->full, sizeof(dir->full), "%s/", start ); dir->leaf = dir->full + length + 1; } LISTadd_last( EXPRESS_path, dir ); @@ -311,7 +311,9 @@ void EXPRESSparse( Express model, FILE * fp, char * filename ) { if( !fp ) { /* go down path looking for file */ LISTdo( EXPRESS_path, dir, Dir * ) - sprintf( dir->leaf, "%s", filename ); + + size_t rem = (size_t)( dir->full + sizeof( dir->full ) - dir->leaf ); + snprintf( dir->leaf, rem, "%s", filename ); if( 0 != ( fp = fopen( dir->full, "r" ) ) ) { filename = dir->full; break; @@ -530,7 +532,9 @@ Schema EXPRESSfind_schema( Dictionary modeldict, char * name ) { /* go down path looking for file */ LISTdo( EXPRESS_path, dir, Dir * ) - sprintf( dir->leaf, "%s.exp", lower ); + + size_t rem = (size_t)( dir->full + sizeof( dir->full ) - dir->leaf ); + snprintf( dir->leaf, rem, "%s.exp", lower ); if( print_objects_while_running & OBJ_SCHEMA_BITS ) { fprintf( stderr, "pass %d: %s (schema file?)\n", EXPRESSpass, dir->full ); diff --git a/src/express/generated/expscan.c b/src/express/generated/expscan.c index 0b60210cb..86893459a 100644 --- a/src/express/generated/expscan.c +++ b/src/express/generated/expscan.c @@ -279,8 +279,9 @@ buf_prints(struct Buf *buf, const char *fmt, const char *s) { char *t; - t = (char*)malloc(strlen(fmt) + strlen(s) + 1); - sprintf(t, fmt, s); + size_t len = strlen(fmt) + strlen(s) + 1; + t = (char*)malloc(len); + snprintf(t, len, fmt, s); buf = buf_strappend(buf, t); free(t); return buf; @@ -315,9 +316,10 @@ buf_linedir(struct Buf *buf, const char* filename, int lineno) { char *t; const char fmt[] = "#line %d \"%s\"\n"; - - t = (char*)malloc(strlen(fmt) + strlen(filename) + numDigits(lineno) + 1); - sprintf(t, fmt, lineno, filename); + + size_t len = strlen(fmt) + strlen(filename) + numDigits(lineno) + 1; + t = (char*)malloc(len); + snprintf(t, len, fmt, lineno, filename); buf = buf_strappend(buf, t); free(t); return buf; @@ -382,9 +384,11 @@ buf_m4_define(struct Buf *buf, const char* def, const char* val) char *str; val = val ? val : ""; - str = (char*)malloc(strlen(fmt) + strlen(def) + strlen(val) + 2); - sprintf(str, fmt, def, val); + size_t len = strlen(fmt) + strlen(def) + strlen(val) + 2; + str = (char*)malloc(len); + + snprintf(str, len, fmt, def, val); buf_append(buf, &str, 1); return buf; } @@ -400,9 +404,9 @@ buf_m4_undefine(struct Buf *buf, const char* def) const char *fmt = "m4_undefine( [[%s]])m4_dnl\n"; char *str; - str = (char*)malloc(strlen(fmt) + strlen(def) + 2); - - sprintf(str, fmt, def); + size_t len = strlen(fmt) + strlen(def) + 2; + str = (char*)malloc(len); + snprintf(str, len, fmt, def); buf_append(buf, &str, 1); return buf; } From b3fc4258c8168d9c9672403a559af32ba7dc268d Mon Sep 17 00:00:00 2001 From: Clifford Yapp <238416+starseeker@users.noreply.github.com> Date: Thu, 5 Feb 2026 17:22:06 -0500 Subject: [PATCH 12/16] More yml adjustments --- .github/workflows/build.yml | 7 +++++-- 1 file changed, 5 insertions(+), 2 deletions(-) diff --git a/.github/workflows/build.yml b/.github/workflows/build.yml index f8a6d5cc1..930f16f8c 100644 --- a/.github/workflows/build.yml +++ b/.github/workflows/build.yml @@ -207,7 +207,8 @@ jobs: - name: Configure run: | cmake -E make_directory brlcad_build - cmake -S brlcad -B brlcad_build -DBRLAD_ENABLE_GDAL=OFF -DBRLCAD_ENABLE_TCL=OFF -DBRLCAD_ENABLE_QT=OFF -B build -G Ninja -DCMAKE_C_COMPILER="cl.exe" -DCMAKE_CXX_COMPILER="cl.exe" + cd brlcad_build + cmake -S ../brlcad -DBRLCAD_EXT_DIR=${{ github.workspace }}\bext_output -DBRLAD_ENABLE_GDAL=OFF -DBRLCAD_ENABLE_TCL=OFF -DBRLCAD_ENABLE_QT=OFF -B build -G Ninja - name: Build run: | @@ -268,7 +269,9 @@ jobs: - name: Configure run: | cmake -E make_directory brlcad_build - cmake -S brlcad -B brlcad_build -DBRLAD_ENABLE_GDAL=OFF -DBRLCAD_ENABLE_TCL=OFF -DBRLCAD_ENABLE_QT=OFF -B build -G Ninja -DCMAKE_C_COMPILER="cl.exe" -DCMAKE_CXX_COMPILER="cl.exe" + cd brlcad_build + cmake -S ../brlcad -DBRLCAD_EXT_DIR=${{ github.workspace }}\bext_output -DBRLAD_ENABLE_GDAL=OFF -DBRLCAD_ENABLE_TCL=OFF -DBRLCAD_ENABLE_QT=OFF -B build -G Ninja -DCMAKE_C_COMPILER="cl.exe" -DCMAKE_CXX_COMPILER="cl.exe" + cd .. - name: Build run: | From c9c1bb99da1874c0f1a2731a0727d421b5c31cee Mon Sep 17 00:00:00 2001 From: Clifford Yapp <238416+starseeker@users.noreply.github.com> Date: Fri, 6 Feb 2026 08:31:00 -0500 Subject: [PATCH 13/16] Remove stray -B options --- .github/workflows/build.yml | 7 +++---- 1 file changed, 3 insertions(+), 4 deletions(-) diff --git a/.github/workflows/build.yml b/.github/workflows/build.yml index 930f16f8c..a5d843388 100644 --- a/.github/workflows/build.yml +++ b/.github/workflows/build.yml @@ -208,7 +208,8 @@ jobs: run: | cmake -E make_directory brlcad_build cd brlcad_build - cmake -S ../brlcad -DBRLCAD_EXT_DIR=${{ github.workspace }}\bext_output -DBRLAD_ENABLE_GDAL=OFF -DBRLCAD_ENABLE_TCL=OFF -DBRLCAD_ENABLE_QT=OFF -B build -G Ninja + cmake -S ../brlcad -DBRLCAD_EXT_DIR=${{ github.workspace }}\bext_output -DBRLAD_ENABLE_GDAL=OFF -DBRLCAD_ENABLE_TCL=OFF -DBRLCAD_ENABLE_QT=OFF -G Ninja + cd .. - name: Build run: | @@ -269,9 +270,7 @@ jobs: - name: Configure run: | cmake -E make_directory brlcad_build - cd brlcad_build - cmake -S ../brlcad -DBRLCAD_EXT_DIR=${{ github.workspace }}\bext_output -DBRLAD_ENABLE_GDAL=OFF -DBRLCAD_ENABLE_TCL=OFF -DBRLCAD_ENABLE_QT=OFF -B build -G Ninja -DCMAKE_C_COMPILER="cl.exe" -DCMAKE_CXX_COMPILER="cl.exe" - cd .. + cmake -S brlcad -B brlcad_build -DBRLCAD_EXT_DIR=${{ github.workspace }}\bext_output -DBRLAD_ENABLE_GDAL=OFF -DBRLCAD_ENABLE_TCL=OFF -DBRLCAD_ENABLE_QT=OFF -G Ninja -DCMAKE_C_COMPILER="cl.exe" -DCMAKE_CXX_COMPILER="cl.exe" - name: Build run: | From fb00dd424f42806ca745bebaf38ce81137c4f495 Mon Sep 17 00:00:00 2001 From: Clifford Yapp <238416+starseeker@users.noreply.github.com> Date: Fri, 6 Feb 2026 09:11:21 -0500 Subject: [PATCH 14/16] Release build config on Windows --- .github/workflows/build.yml | 4 ++-- 1 file changed, 2 insertions(+), 2 deletions(-) diff --git a/.github/workflows/build.yml b/.github/workflows/build.yml index a5d843388..d56958c62 100644 --- a/.github/workflows/build.yml +++ b/.github/workflows/build.yml @@ -270,12 +270,12 @@ jobs: - name: Configure run: | cmake -E make_directory brlcad_build - cmake -S brlcad -B brlcad_build -DBRLCAD_EXT_DIR=${{ github.workspace }}\bext_output -DBRLAD_ENABLE_GDAL=OFF -DBRLCAD_ENABLE_TCL=OFF -DBRLCAD_ENABLE_QT=OFF -G Ninja -DCMAKE_C_COMPILER="cl.exe" -DCMAKE_CXX_COMPILER="cl.exe" + cmake -S brlcad -B brlcad_build -DCMAKE_BUILD_TYPE=Release -DBRLCAD_EXT_DIR=${{ github.workspace }}\bext_output -DBRLAD_ENABLE_GDAL=OFF -DBRLCAD_ENABLE_TCL=OFF -DBRLCAD_ENABLE_QT=OFF -G Ninja -DCMAKE_C_COMPILER="cl.exe" -DCMAKE_CXX_COMPILER="cl.exe" - name: Build run: | cd brlcad_build - cmake --build . --target step-g + cmake --build . --config Release --target step-g cd .. - name: Test From 11694e8bf90d5daaa18514c7d59091a240058187 Mon Sep 17 00:00:00 2001 From: Clifford Yapp <238416+starseeker@users.noreply.github.com> Date: Fri, 6 Feb 2026 09:54:45 -0500 Subject: [PATCH 15/16] Helps to spell the variable name correctly... --- .github/workflows/build.yml | 4 ++-- 1 file changed, 2 insertions(+), 2 deletions(-) diff --git a/.github/workflows/build.yml b/.github/workflows/build.yml index d56958c62..0be63c0fc 100644 --- a/.github/workflows/build.yml +++ b/.github/workflows/build.yml @@ -208,7 +208,7 @@ jobs: run: | cmake -E make_directory brlcad_build cd brlcad_build - cmake -S ../brlcad -DBRLCAD_EXT_DIR=${{ github.workspace }}\bext_output -DBRLAD_ENABLE_GDAL=OFF -DBRLCAD_ENABLE_TCL=OFF -DBRLCAD_ENABLE_QT=OFF -G Ninja + cmake -S ../brlcad -DBRLCAD_EXT_DIR=${{ github.workspace }}\bext_output -DBRLCAD_ENABLE_GDAL=OFF -DBRLCAD_ENABLE_TCL=OFF -DBRLCAD_ENABLE_QT=OFF -G Ninja cd .. - name: Build @@ -270,7 +270,7 @@ jobs: - name: Configure run: | cmake -E make_directory brlcad_build - cmake -S brlcad -B brlcad_build -DCMAKE_BUILD_TYPE=Release -DBRLCAD_EXT_DIR=${{ github.workspace }}\bext_output -DBRLAD_ENABLE_GDAL=OFF -DBRLCAD_ENABLE_TCL=OFF -DBRLCAD_ENABLE_QT=OFF -G Ninja -DCMAKE_C_COMPILER="cl.exe" -DCMAKE_CXX_COMPILER="cl.exe" + cmake -S brlcad -B brlcad_build -DCMAKE_BUILD_TYPE=Release -DBRLCAD_EXT_DIR=${{ github.workspace }}\bext_output -DBRLCAD_ENABLE_GDAL=OFF -DBRLCAD_ENABLE_TCL=OFF -DBRLCAD_ENABLE_QT=OFF -G Ninja -DCMAKE_C_COMPILER="cl.exe" -DCMAKE_CXX_COMPILER="cl.exe" - name: Build run: | From 66aec9749e624695e88a5f285c3b87ae5aea6b44 Mon Sep 17 00:00:00 2001 From: Clifford Yapp <238416+starseeker@users.noreply.github.com> Date: Fri, 6 Feb 2026 10:38:33 -0500 Subject: [PATCH 16/16] Whoops, old fixed versions of ubuntu --- .github/workflows/build.yml | 4 ++-- 1 file changed, 2 insertions(+), 2 deletions(-) diff --git a/.github/workflows/build.yml b/.github/workflows/build.yml index 0be63c0fc..ffa7965e8 100644 --- a/.github/workflows/build.yml +++ b/.github/workflows/build.yml @@ -48,7 +48,7 @@ jobs: linux: name: Ubuntu Latest GCC - runs-on: ubuntu-20.04 + runs-on: ubuntu-latest strategy: fail-fast: true steps: @@ -90,7 +90,7 @@ jobs: linux_clang: name: Ubuntu Latest Clang - runs-on: ubuntu-20.04 + runs-on: ubuntu-latest strategy: fail-fast: true steps: