@@ -239,6 +239,223 @@ namespace bin2cpp
239239 return true ;
240240 }
241241
242+ bool ManagerGenerator::createCHeaderFile (const char * file_path)
243+ {
244+ FILE* fout = fopen (file_path, " w" );
245+ if ( !fout )
246+ return false ;
247+
248+ // define macro guard a macro matching the filename
249+ std::string macroGuard;
250+ macroGuard += getCppIncludeGuardMacroName (mContext .codeNamespace .c_str ()); // prefix the custom namespace for the file manager
251+ if ( !macroGuard.empty () )
252+ macroGuard += " _" ;
253+ macroGuard += getCppIncludeGuardMacroName (file_path);
254+
255+ std::string classMacroGuardPrefix = getClassMacroGuardPrefix ();
256+ std::string fileHeader = getHeaderTemplate (false );
257+
258+ fprintf (fout, " %s" , fileHeader.c_str ());
259+ fprintf (fout, " #ifndef %s\n " , macroGuard.c_str ());
260+ fprintf (fout, " #define %s\n " , macroGuard.c_str ());
261+ fprintf (fout, " \n " );
262+ fprintf (fout, " #include <stddef.h>\n " );
263+ fprintf (fout, " #include <stdbool.h>\n " );
264+ fprintf (fout, " \n " );
265+ fprintf (fout, " #ifndef %s_EMBEDDEDFILE_STRUCT\n " , classMacroGuardPrefix.c_str ());
266+ fprintf (fout, " #define %s_EMBEDDEDFILE_STRUCT\n " , classMacroGuardPrefix.c_str ());
267+ fprintf (fout, " typedef struct %s %s;\n " , mContext .baseClass .c_str (), mContext .baseClass .c_str ());
268+ fprintf (fout, " typedef bool(*bin2c_load_func)();\n " );
269+ fprintf (fout, " typedef void(*bin2c_free_func)();\n " );
270+ fprintf (fout, " typedef bool(*bin2c_save_func)(const char*);\n " );
271+ fprintf (fout, " typedef struct %s\n " , mContext .baseClass .c_str ());
272+ fprintf (fout, " {\n " );
273+ fprintf (fout, " size_t size;\n " );
274+ fprintf (fout, " const char* file_name;\n " );
275+ fprintf (fout, " const char* file_path;\n " );
276+ fprintf (fout, " const unsigned char* buffer;\n " );
277+ fprintf (fout, " bin2c_load_func load;\n " );
278+ fprintf (fout, " bin2c_free_func unload;\n " );
279+ fprintf (fout, " bin2c_save_func save;\n " );
280+ fprintf (fout, " } %s;\n " , mContext .baseClass .c_str ());
281+ fprintf (fout, " typedef %s* %sPtr;\n " , mContext .baseClass .c_str (), mContext .baseClass .c_str ());
282+ fprintf (fout, " #endif //%s_EMBEDDEDFILE_STRUCT\n " , classMacroGuardPrefix.c_str ());
283+ fprintf (fout, " \n " );
284+ fprintf (fout, " size_t bin2c_filemanager_get_file_count();\n " );
285+ fprintf (fout, " bool bin2c_filemanager_register_file(%s* file);\n " , mContext .baseClass .c_str ());
286+ fprintf (fout, " const %s* bin2c_filemanager_get_file(size_t index);\n " , mContext .baseClass .c_str ());
287+ fprintf (fout, " bool bin2c_filemanager_save_files(const char* directory);\n " );
288+ fprintf (fout, " \n " );
289+ fprintf (fout, " #endif //%s\n " , macroGuard.c_str ());
290+
291+ fclose (fout);
292+
293+ return true ;
294+ }
295+
296+ bool ManagerGenerator::createCSourceFile (const char * file_path)
297+ {
298+ FILE* fout = fopen (file_path, " w" );
299+ if ( !fout )
300+ return false ;
301+
302+ // Build header and cpp file path
303+ std::string headerPath = getHeaderFilePath (file_path);
304+ std::string sourcePath = file_path;
305+
306+ std::string fileHeader = getHeaderTemplate (false );
307+
308+ fprintf (fout, " %s" , fileHeader.c_str ());
309+ fprintf (fout, " #if defined(_WIN32) && !defined(_CRT_SECURE_NO_WARNINGS)\n " );
310+ fprintf (fout, " #define _CRT_SECURE_NO_WARNINGS\n " );
311+ fprintf (fout, " #endif\n " );
312+ fprintf (fout, " \n " );
313+ fprintf (fout, " #include \" %s\"\n " , mContext .managerHeaderFilename .c_str ());
314+ fprintf (fout, " #include <stdlib.h> // for malloc\n " );
315+ fprintf (fout, " #include <stdio.h> // for snprintf()\n " );
316+ fprintf (fout, " #include <string.h> // strlen\n " );
317+ fprintf (fout, " #include <sys/stat.h> // stat\n " );
318+ fprintf (fout, " #include <errno.h> // errno, EEXIST\n " );
319+ fprintf (fout, " #if defined(_WIN32)\n " );
320+ fprintf (fout, " #include <direct.h> // _mkdir\n " );
321+ fprintf (fout, " #endif\n " );
322+ fprintf (fout, " #if defined(_WIN32)\n " );
323+ fprintf (fout, " #define portable_stat _stat\n " );
324+ fprintf (fout, " #define portable_mkdir(path) _mkdir(path)\n " );
325+ fprintf (fout, " #define PATH_SEPARATOR_CHAR '\\\\ '\n " );
326+ fprintf (fout, " #define PATH_SEPARATOR_STR \"\\\\\"\n " );
327+ fprintf (fout, " #else\n " );
328+ fprintf (fout, " #define portable_stat stat\n " );
329+ fprintf (fout, " #define portable_mkdir(path) mkdir(path, 0755)\n " );
330+ fprintf (fout, " #define PATH_SEPARATOR_CHAR '/'\n " );
331+ fprintf (fout, " #define PATH_SEPARATOR_STR \" /\"\n " );
332+ fprintf (fout, " #endif\n " );
333+ fprintf (fout, " \n " );
334+ fprintf (fout, " #define BIN2C_MAX_PATH 32767\n " );
335+ fprintf (fout, " \n " );
336+ fprintf (fout, " static %s** registered_files = NULL;\n " , mContext .baseClass .c_str ());
337+ fprintf (fout, " static size_t registered_files_count = 0;\n " );
338+ fprintf (fout, " \n " );
339+ fprintf (fout, " size_t bin2c_filemanager_get_file_count()\n " );
340+ fprintf (fout, " {\n " );
341+ fprintf (fout, " return registered_files_count;\n " );
342+ fprintf (fout, " }\n " );
343+ fprintf (fout, " \n " );
344+ fprintf (fout, " bool bin2c_filemanager_register_file(%s* file)\n " , mContext .baseClass .c_str ());
345+ fprintf (fout, " {\n " );
346+ fprintf (fout, " // allocate ram\n " );
347+ fprintf (fout, " size_t new_ram_size = sizeof(%s**) * (registered_files_count + 1);\n " , mContext .baseClass .c_str ());
348+ fprintf (fout, " %s** tmp = NULL;\n " , mContext .baseClass .c_str ());
349+ fprintf (fout, " if ( registered_files == NULL )\n " );
350+ fprintf (fout, " tmp = (%s**)malloc(new_ram_size);\n " , mContext .baseClass .c_str ());
351+ fprintf (fout, " else\n " );
352+ fprintf (fout, " tmp = (%s**)realloc(registered_files, new_ram_size);\n " , mContext .baseClass .c_str ());
353+ fprintf (fout, " if ( tmp == NULL )\n " );
354+ fprintf (fout, " return false;\n " );
355+ fprintf (fout, " \n " );
356+ fprintf (fout, " registered_files = tmp;\n " );
357+ fprintf (fout, " registered_files_count++;\n " );
358+ fprintf (fout, " \n " );
359+ fprintf (fout, " // insert\n " );
360+ fprintf (fout, " registered_files[registered_files_count - 1] = file;\n " );
361+ fprintf (fout, " \n " );
362+ fprintf (fout, " return true;\n " );
363+ fprintf (fout, " }\n " );
364+ fprintf (fout, " \n " );
365+ fprintf (fout, " const %s* bin2c_filemanager_get_file(size_t index)\n " , mContext .baseClass .c_str ());
366+ fprintf (fout, " {\n " );
367+ fprintf (fout, " if ( index >= registered_files_count )\n " );
368+ fprintf (fout, " return NULL;\n " );
369+ fprintf (fout, " return registered_files[index];\n " );
370+ fprintf (fout, " }\n " );
371+ fprintf (fout, " \n " );
372+ fprintf (fout, " static inline bool bin2c_filemanager_is_root_directory(const char* path)\n " );
373+ fprintf (fout, " {\n " );
374+ fprintf (fout, " if ( path == NULL && path[0] == '\0 ' )\n " );
375+ fprintf (fout, " return false;\n " );
376+ fprintf (fout, " #if defined(_WIN32)\n " );
377+ fprintf (fout, " bool is_drive_letter = ((path[0] >= 'a' && path[0] <= 'z') || (path[0] >= 'A' && path[0] <= 'Z'));\n " );
378+ fprintf (fout, " if ( (is_drive_letter && path[1] == ':' && path[2] == '\0 ') || // test for C:\n " );
379+ fprintf (fout, " (is_drive_letter && path[1] == ':' && path[2] == PATH_SEPARATOR_CHAR && path[3] == '\0 ') ) // test for C:\\ \n " );
380+ fprintf (fout, " return true;\n " );
381+ fprintf (fout, " #else\n " );
382+ fprintf (fout, " if ( path[0] == PATH_SEPARATOR_CHAR )\n " );
383+ fprintf (fout, " return true;\n " );
384+ fprintf (fout, " #endif\n " );
385+ fprintf (fout, " return false;\n " );
386+ fprintf (fout, " }\n " );
387+ fprintf (fout, " \n " );
388+ fprintf (fout, " bool bin2c_filemanager_create_parent_directories(const char* file_path)\n " );
389+ fprintf (fout, " {\n " );
390+ fprintf (fout, " if ( file_path == NULL )\n " );
391+ fprintf (fout, " return false;\n " );
392+ fprintf (fout, " char* accumulator = (char*)malloc(BIN2C_MAX_PATH);\n " );
393+ fprintf (fout, " if ( accumulator == NULL )\n " );
394+ fprintf (fout, " return false;\n " );
395+ fprintf (fout, " accumulator[0] = '\0 ';\n " );
396+ fprintf (fout, " size_t length = strlen(file_path);\n " );
397+ fprintf (fout, " for ( size_t i = 0; i < length; i++ )\n " );
398+ fprintf (fout, " {\n " );
399+ fprintf (fout, " if ( file_path[i] == PATH_SEPARATOR_CHAR && !(accumulator[0] == '\0 ') && !bin2c_filemanager_is_root_directory(accumulator) )\n " );
400+ fprintf (fout, " {\n " );
401+ fprintf (fout, " int ret = portable_mkdir(accumulator);\n " );
402+ fprintf (fout, " if ( ret != 0 && errno != EEXIST )\n " );
403+ fprintf (fout, " {\n " );
404+ fprintf (fout, " free(accumulator);\n " );
405+ fprintf (fout, " return false;\n " );
406+ fprintf (fout, " }\n " );
407+ fprintf (fout, " }\n " );
408+ fprintf (fout, " \n " );
409+ fprintf (fout, " // append\n " );
410+ fprintf (fout, " char tmp[] = { file_path[i], '\0 ' };\n " );
411+ fprintf (fout, " strcat(accumulator, tmp);\n " );
412+ fprintf (fout, " }\n " );
413+ fprintf (fout, " free(accumulator);\n " );
414+ fprintf (fout, " return true;\n " );
415+ fprintf (fout, " }\n " );
416+ fprintf (fout, " \n " );
417+ fprintf (fout, " bool bin2c_filemanager_save_files(const char * directory)\n " );
418+ fprintf (fout, " {\n " );
419+ fprintf (fout, " if (directory == NULL)\n " );
420+ fprintf (fout, " return false;\n " );
421+ fprintf (fout, " char* path = (char*)malloc(BIN2C_MAX_PATH);\n " );
422+ fprintf (fout, " if ( path == NULL )\n " );
423+ fprintf (fout, " return false;\n " );
424+ fprintf (fout, " path[0] = '\0 ';\n " );
425+ fprintf (fout, " for(size_t i=0; i< registered_files_count; i++)\n " );
426+ fprintf (fout, " {\n " );
427+ fprintf (fout, " const Bin2cFile* f = bin2c_filemanager_get_file(i);\n " );
428+ fprintf (fout, " if ( !f )\n " );
429+ fprintf (fout, " {\n " );
430+ fprintf (fout, " free(path);\n " );
431+ fprintf (fout, " return false;\n " );
432+ fprintf (fout, " }\n " );
433+ fprintf (fout, " \n " );
434+ fprintf (fout, " char path[32767] = { 0 };\n " );
435+ fprintf (fout, " snprintf(path, sizeof(path), \" %%s%%c%%s\" , directory, PATH_SEPARATOR_CHAR, f->file_path);\n " );
436+ fprintf (fout, " \n " );
437+ fprintf (fout, " if (!bin2c_filemanager_create_parent_directories(path))\n " );
438+ fprintf (fout, " {\n " );
439+ fprintf (fout, " free(path);\n " );
440+ fprintf (fout, " return false;\n " );
441+ fprintf (fout, " }\n " );
442+ fprintf (fout, " bool saved = f->save(path);\n " );
443+ fprintf (fout, " if (!saved)\n " );
444+ fprintf (fout, " {\n " );
445+ fprintf (fout, " free(path);\n " );
446+ fprintf (fout, " return false;\n " );
447+ fprintf (fout, " }\n " );
448+ fprintf (fout, " }\n " );
449+ fprintf (fout, " free(path);\n " );
450+ fprintf (fout, " return true;\n " );
451+ fprintf (fout, " }\n " );
452+ fprintf (fout, " \n " );
453+
454+ fclose (fout);
455+
456+ return true ;
457+ }
458+
242459 bool ManagerGenerator::printFileContent ()
243460 {
244461 return false ;
0 commit comments