1- /* nob - v3.7 .0 - Public Domain - https://github.com/tsoding/nob.h
1+ /* nob - v3.8 .0 - Public Domain - https://github.com/tsoding/nob.h
22
33 This library is the next generation of the [NoBuild](https://github.com/tsoding/nobuild) idea.
44
@@ -303,7 +303,7 @@ typedef struct {
303303
304304NOBDEF bool nob_walk_dir_opt (const char * root , Nob_Walk_Func func , Nob_Walk_Dir_Opt );
305305
306- #define nob_walk_dir (root , func , ...) nob_walk_dir_opt((root), (func), (Nob_Walk_Dir_Opt){__VA_ARGS__})
306+ #define nob_walk_dir (root , func , ...) nob_walk_dir_opt((root), (func), NOB_CLIT (Nob_Walk_Dir_Opt){__VA_ARGS__})
307307
308308typedef struct {
309309 char * name ;
@@ -585,14 +585,14 @@ typedef struct {
585585typedef struct {
586586 const char * stdin_path ;
587587} Nob_Chain_Begin_Opt ;
588- #define nob_chain_begin (chain , ...) nob_chain_begin_opt((chain), (Nob_Chain_Begin_Opt) { __VA_ARGS__ })
588+ #define nob_chain_begin (chain , ...) nob_chain_begin_opt((chain), NOB_CLIT (Nob_Chain_Begin_Opt) { __VA_ARGS__ })
589589NOBDEF bool nob_chain_begin_opt (Nob_Chain * chain , Nob_Chain_Begin_Opt opt );
590590
591591typedef struct {
592592 bool err2out ;
593593 bool dont_reset ;
594594} Nob_Chain_Cmd_Opt ;
595- #define nob_chain_cmd (chain , cmd , ...) nob_chain_cmd_opt((chain), (cmd), (Nob_Chain_Cmd_Opt) { __VA_ARGS__ })
595+ #define nob_chain_cmd (chain , cmd , ...) nob_chain_cmd_opt((chain), (cmd), NOB_CLIT (Nob_Chain_Cmd_Opt) { __VA_ARGS__ })
596596NOBDEF bool nob_chain_cmd_opt (Nob_Chain * chain , Nob_Cmd * cmd , Nob_Chain_Cmd_Opt opt );
597597
598598typedef struct {
@@ -601,7 +601,7 @@ typedef struct {
601601 const char * stdout_path ;
602602 const char * stderr_path ;
603603} Nob_Chain_End_Opt ;
604- #define nob_chain_end (chain , ...) nob_chain_end_opt((chain), (Nob_Chain_End_Opt) { __VA_ARGS__ })
604+ #define nob_chain_end (chain , ...) nob_chain_end_opt((chain), NOB_CLIT (Nob_Chain_End_Opt) { __VA_ARGS__ })
605605NOBDEF bool nob_chain_end_opt (Nob_Chain * chain , Nob_Chain_End_Opt opt );
606606
607607// Get amount of processors on the machine.
@@ -614,7 +614,7 @@ NOBDEF uint64_t nob_nanos_since_unspecified_epoch(void);
614614
615615// Same as nob_cmd_run_opt but using cool variadic macro to set the default options.
616616// See https://x.com/vkrajacic/status/1749816169736073295 for more info on how to use such macros.
617- #define nob_cmd_run (cmd , ...) nob_cmd_run_opt((cmd), (Nob_Cmd_Opt){__VA_ARGS__})
617+ #define nob_cmd_run (cmd , ...) nob_cmd_run_opt((cmd), NOB_CLIT (Nob_Cmd_Opt){__VA_ARGS__})
618618
619619// DEPRECATED:
620620//
@@ -651,9 +651,16 @@ typedef struct {
651651// use it as a C string.
652652NOBDEF void nob_cmd_render (Nob_Cmd cmd , Nob_String_Builder * render );
653653
654- NOBDEF void nob__cmd_append (Nob_Cmd * cmd , size_t n , ...);
654+ // Compound Literal
655+ #if defined(__cplusplus )
656+ #define NOB_CLIT (type ) type
657+ #else
658+ #define NOB_CLIT (type ) (type)
659+ #endif
660+
661+ NOBDEF void nob__cmd_append (Nob_Cmd * cmd , ...);
655662#define nob_cmd_append (cmd , ...) \
656- nob__cmd_append(cmd, (sizeof((const char*[]){ __VA_ARGS__})/sizeof (const char*)), __VA_ARGS__ )
663+ nob__cmd_append(cmd, __VA_ARGS__, (const char*)-1 )
657664
658665// TODO: nob_cmd_extend() evaluates other_cmd twice
659666// It can be fixed by turning nob_cmd_extend() call into a statement.
@@ -950,12 +957,13 @@ static Nob_Proc nob__cmd_start_process(Nob_Cmd cmd, Nob_Fd *fdin, Nob_Fd *fdout,
950957// Any messages with the level below nob_minimal_log_level are going to be suppressed.
951958Nob_Log_Level nob_minimal_log_level = NOB_INFO ;
952959
953- NOBDEF void nob__cmd_append (Nob_Cmd * cmd , size_t n , ...)
960+ NOBDEF void nob__cmd_append (Nob_Cmd * cmd , ...)
954961{
955962 va_list args ;
956- va_start (args , n );
957- for (size_t i = 0 ; i < n ; ++ i ) {
963+ va_start (args , cmd );
964+ for (;; ) {
958965 const char * arg = va_arg (args , const char * );
966+ if (arg == (const char * )-1 ) break ;
959967 nob_da_append (cmd , arg );
960968 }
961969 va_end (args );
@@ -2020,7 +2028,7 @@ bool nob__walk_dir_opt_impl(Nob_String_Builder *file_path, Nob_Walk_Func func, s
20202028
20212029 // Pre-order walking
20222030 if (!opt .post_order ) {
2023- if (!func ((Nob_Walk_Entry ) {
2031+ if (!func (NOB_CLIT (Nob_Walk_Entry ) {
20242032 .path = file_path -> items ,
20252033 .type = file_type ,
20262034 .level = level ,
@@ -2067,7 +2075,7 @@ bool nob__walk_dir_opt_impl(Nob_String_Builder *file_path, Nob_Walk_Func func, s
20672075
20682076 // Post-order walking
20692077 if (opt .post_order ) {
2070- if (!func ((Nob_Walk_Entry ) {
2078+ if (!func (NOB_CLIT (Nob_Walk_Entry ) {
20712079 .path = file_path -> items ,
20722080 .type = file_type ,
20732081 .level = level ,
@@ -2159,7 +2167,7 @@ NOBDEF Nob_File_Type nob_get_file_type(const char *path)
21592167 DWORD attr = GetFileAttributesA (path );
21602168 if (attr == INVALID_FILE_ATTRIBUTES ) {
21612169 nob_log (NOB_ERROR , "Could not get file attributes of %s: %s" , path , nob_win32_error_message (GetLastError ()));
2162- return -1 ;
2170+ return ( Nob_File_Type ) - 1 ;
21632171 }
21642172
21652173 if (attr & FILE_ATTRIBUTE_DIRECTORY ) return NOB_FILE_DIRECTORY ;
@@ -2754,8 +2762,8 @@ NOBDEF char *nob_temp_dir_name(const char *path)
27542762 return nob_temp_strndup (path , i + 1 );
27552763#else
27562764 if (!path ) path = "" ; // Treating NULL as empty.
2757- char * drive = nob_temp_alloc (_MAX_DRIVE );
2758- char * dir = nob_temp_alloc (_MAX_DIR );
2765+ char * drive = ( char * ) nob_temp_alloc (_MAX_DRIVE );
2766+ char * dir = ( char * ) nob_temp_alloc (_MAX_DIR );
27592767 // https://learn.microsoft.com/en-us/previous-versions/visualstudio/visual-studio-2010/8e46eyt7(v=vs.100)
27602768 errno_t ret = _splitpath_s (path , drive , _MAX_DRIVE , dir , _MAX_DIR , NULL , 0 , NULL , 0 );
27612769 NOB_ASSERT (ret == 0 );
@@ -2777,8 +2785,8 @@ NOBDEF char *nob_temp_file_name(const char *path)
27772785 return s + i ;
27782786#else
27792787 if (!path ) path = "" ; // Treating NULL as empty.
2780- char * fname = nob_temp_alloc (_MAX_FNAME );
2781- char * ext = nob_temp_alloc (_MAX_EXT );
2788+ char * fname = ( char * ) nob_temp_alloc (_MAX_FNAME );
2789+ char * ext = ( char * ) nob_temp_alloc (_MAX_EXT );
27822790 // https://learn.microsoft.com/en-us/previous-versions/visualstudio/visual-studio-2010/8e46eyt7(v=vs.100)
27832791 errno_t ret = _splitpath_s (path , NULL , 0 , NULL , 0 , fname , _MAX_FNAME , ext , _MAX_EXT );
27842792 NOB_ASSERT (ret == 0 );
@@ -2792,7 +2800,7 @@ NOBDEF char *nob_temp_file_ext(const char *path)
27922800 return strrchr (nob_temp_file_name (path ), '.' );
27932801#else
27942802 if (!path ) path = "" ; // Treating NULL as empty.
2795- char * ext = nob_temp_alloc (_MAX_EXT );
2803+ char * ext = ( char * ) nob_temp_alloc (_MAX_EXT );
27962804 // https://learn.microsoft.com/en-us/previous-versions/visualstudio/visual-studio-2010/8e46eyt7(v=vs.100)
27972805 errno_t ret = _splitpath_s (path , NULL , 0 , NULL , 0 , NULL , 0 , ext , _MAX_EXT );
27982806 NOB_ASSERT (ret == 0 );
@@ -2946,6 +2954,7 @@ NOBDEF char *nob_temp_running_executable_path(void)
29462954 #define procs_wait_and_reset nob_procs_wait_and_reset
29472955 #define procs_append_with_flush nob_procs_append_with_flush
29482956 #define procs_flush nob_procs_flush
2957+ #define CLIT NOB_CLIT
29492958 #define Cmd Nob_Cmd
29502959 #define Cmd_Redirect Nob_Cmd_Redirect
29512960 #define Cmd_Opt Nob_Cmd_Opt
@@ -3012,6 +3021,8 @@ NOBDEF char *nob_temp_running_executable_path(void)
30123021/*
30133022 Revision history:
30143023
3024+ 3.8.0 (2026-03-24) Add NOB_CLIT()
3025+ Fix compliation on MSVC with /TP
30153026 3.7.0 (2026-03-20) Add nob_sb_append_sv()
30163027 3.6.0 (2026-03-16) Add nob_sv_chop_suffix()
30173028 Deprecate nob_sv_end_with()
0 commit comments