From 5794e55e59229f02928e4d71f3f241cb98098a02 Mon Sep 17 00:00:00 2001 From: JackCarterSmith Date: Thu, 11 Aug 2022 22:24:13 +0200 Subject: [PATCH 01/15] Minor settings update --- CMakeLists.txt | 75 +++++++++++++++++++++++++------------------ Jenkinsfile | 3 +- README.md | 7 ++-- conanfile.txt | 3 +- src/Model-Extractor.c | 3 ++ 5 files changed, 54 insertions(+), 37 deletions(-) diff --git a/CMakeLists.txt b/CMakeLists.txt index 7aabf86..7be0b65 100644 --- a/CMakeLists.txt +++ b/CMakeLists.txt @@ -1,57 +1,69 @@ # CMakeLists.txt -# Written by JackCarterSmith, 2021 +#################################################### +# Written by JackCarterSmith, 2022 # This code is released under the RSE license. +#################################################### -cmake_minimum_required(VERSION 3.1) -cmake_policy(VERSION 3.1) + +# CMake requirement and general configuration +cmake_minimum_required(VERSION 3.12) +cmake_policy(VERSION 3.12) set(CMAKE_MODULE_PATH ${CMAKE_BINARY_DIR}) - -# define project -add_definitions(-DCONF_NO_GL) -if(DEFINED ENV{CI}) - project(rse-model VERSION $ENV{CI_VERSION}.$ENV{CI_BUILD_NUMBER} DESCRIPTION "RogueSquadron Extractor - Model" LANGUAGES C) - set(RSE_MOD_NAME $ENV{CI_OUTPUT_NAME}-${PROJECT_VERSION}) -else() - project(rse-model VERSION 1.0.0 DESCRIPTION "RogueSquadron Extractor - Model" LANGUAGES C) - set(RSE_MOD_NAME RSE_Model-${PROJECT_VERSION}) +if(DEFINED ENV{MS_COMPATIBLE}) + set(CMAKE_GNUtoMS ON) # Enable compatibility level to exported libraries endif() -configure_file(${CMAKE_CURRENT_SOURCE_DIR}/src/config.h.in ${CMAKE_CURRENT_SOURCE_DIR}/src/config.h @ONLY) include(CheckIncludeFile) include(CheckCSourceCompiles) -# needed packages +add_definitions(-DCONF_NO_GL) # Used for obj-lib to not compile GL part -#find_package(GLEW REQUIRED) + +# Project definition +if(DEFINED ENV{CI}) # Jenkins CI integration mode + project(rse-model VERSION $ENV{CI_VERSION}.$ENV{CI_BUILD_NUMBER} DESCRIPTION "RogueSquadron Extractor - Model" LANGUAGES C) + set(RSE_MOD_NAME $ENV{CI_OUTPUT_NAME}-${PROJECT_VERSION}) +else() # Standalone project mode, should not be used for release. + project(rse-model VERSION 1.0.0 DESCRIPTION "RogueSquadron Extractor - Model" LANGUAGES C) + set(RSE_MOD_NAME RSE_Model-${PROJECT_VERSION}) +endif() +# Push compile infos to source +configure_file(${CMAKE_CURRENT_SOURCE_DIR}/src/config.h.in ${CMAKE_CURRENT_SOURCE_DIR}/src/config.h @ONLY) + + +# Import needed packages and references their include path +#find_package(GLEW REQUIRED) # Enable when GL rendering is ready #include_directories(${GLEW_INCLUDE_DIR}) -# define src/headers files -FILE(GLOB_RECURSE RSE_MOD_SRCS src/*.c) -FILE(GLOB_RECURSE RSE_MOD_HRDS src/*.h) -SOURCE_GROUP("Source Files" FILES ${RSE_MOD_SRCS}) -SOURCE_GROUP("Header Files" FILES ${RSE_MOD_HRDS}) +# Define src/headers files +FILE(GLOB_RECURSE RSE_MOD_SOURCES src/*.c) +FILE(GLOB_RECURSE RSE_MOD_HEADERS src/*.h) +SOURCE_GROUP("Source Files" FILES ${RSE_MOD_SOURCES}) +SOURCE_GROUP("Header Files" FILES ${RSE_MOD_HEADERS}) -# begin building RSE-Model -#set(CMAKE_BUILD_TYPE Debug) +# Building instructions for RSE-Model +if(DEFINED ENV{RSE-WS}) + set(CMAKE_BUILD_TYPE DEBUG) +endif() #include_directories(${CMAKE_CURRENT_SOURCE_DIR}) -add_executable(rse-model ${RSE_MOD_SRCS} ${RSE_MOD_HRDS}) -#set_property(TARGET rse-model PROPERTY C_STANDARD 99) -set_target_properties(rse-model PROPERTIES OUTPUT_NAME ${RSE_MOD_NAME}) +add_executable(rse-model ${RSE_MOD_SOURCES} ${RSE_MOD_HEADERS}) # Set the inputs for the compiler (srcs&hrds) +set_property(TARGET rse-model PROPERTY C_STANDARD 90) +set_target_properties(rse-model PROPERTIES OUTPUT_NAME ${RSE_MOD_NAME}) # Define the executable file name +# Link externals libraries to the linker if(MSVC) # msvc does not append 'lib' - do it here to have consistent name #set_target_properties(rse-model PROPERTIES PREFIX "lib") set_target_properties(rse-model PROPERTIES IMPORT_PREFIX "lib") -endif() -if(MSVC) - target_link_libraries(rse-model) + target_link_libraries(rse-model ${GLEW_LIBRARIES}) else() - target_link_libraries(rse-model m) + target_link_libraries(rse-model ${GLEW_LIBRARIES} m) endif() -# add GPG signature command + +# GPG signature custom command #add_custom_command( # OUTPUT "" # COMMAND gpg --batch --detach-sign @@ -61,7 +73,8 @@ endif() # VERBATIM #) -# install executable + +# Install project executable install(TARGETS rse-model RUNTIME DESTINATION bin ) \ No newline at end of file diff --git a/Jenkinsfile b/Jenkinsfile index c5a2d07..55c6b33 100644 --- a/Jenkinsfile +++ b/Jenkinsfile @@ -47,8 +47,7 @@ pipeline { sh 'cp ../linux/build/${CI_OUTPUT_NAME}-${CI_VERSION}.${BUILD_NUMBER}* .' } dir("zip_win") { - // sh 'cp ../windows/build/${CI_OUTPUT_NAME}-${CI_VERSION}.${BUILD_NUMBER}* ../windows/build/*.dll .' - sh 'cp ../windows/build/${CI_OUTPUT_NAME}-${CI_VERSION}.${BUILD_NUMBER}* .' + sh 'cp ../windows/build/${CI_OUTPUT_NAME}-${CI_VERSION}.${BUILD_NUMBER}* ../windows/build/*.dll .' } zip archive: false, dir: 'zip_linux', exclude: '', glob: '', zipFile: 'x64.zip' sh 'mv x64.zip ${CI_OUTPUT_NAME}-${CI_VERSION}.${BUILD_NUMBER}_x64.zip' diff --git a/README.md b/README.md index 6a1b814..275bdee 100644 --- a/README.md +++ b/README.md @@ -11,7 +11,7 @@ All modules are independants. This is the **'MODEL'** module. ## MODEL MODULE -It's extract texture datas from Rogue Squadron 3D (PC) game models files (HOB). +It's extract 3D rendering datas from Rogue Squadron 3D (PC) game models files (HOB). This module can do: - Extract objects inside HOB files to Wavefront OBJ format, @@ -21,7 +21,7 @@ This module can do: ## TODO - Add textures to models. -- Discover all unknow fields, animation, bones mesh, etc. +- Discover all unknowns fields, animations, bones mesh, etc. ### Using @@ -35,8 +35,9 @@ Due to issue with copyrights, I can't provide samples... You need to extract HOB ### Options - -h Print this message -- -v Activate verbose output +- -v,-vv Activate verbose/debug output mode respectively - -no-subdir Extract textures directly inside current folder +- -no-mtl Disable materials datas export with OBJ model ### Dependencies diff --git a/conanfile.txt b/conanfile.txt index d0e7072..6c8fd0c 100644 --- a/conanfile.txt +++ b/conanfile.txt @@ -8,4 +8,5 @@ cmake_find_package [options] glew:shared=True -[imports] \ No newline at end of file +[imports] +bin, *.dll -> . \ No newline at end of file diff --git a/src/Model-Extractor.c b/src/Model-Extractor.c index e4b8c0f..1ddf391 100644 --- a/src/Model-Extractor.c +++ b/src/Model-Extractor.c @@ -118,9 +118,12 @@ static unsigned char checkInputArgs(T_PROG_OPTIONS* opt_ptr, int p_arg_nbr, char opt_ptr->verbose_mode = 1; printf("[OPTN] Verbose enabled.\n"); } else if (strcmp(p_args[i], "-vv") == 0) { + opt_ptr->verbose_mode = 1; opt_ptr->debug_mode = 1; printf("[OPTN] Debug enabled.\n"); } else if (strcmp(p_args[i], "-vvv") == 0) { + opt_ptr->verbose_mode = 1; + opt_ptr->debug_mode = 1; opt_ptr->god_mode = 1; printf("[OPTN] God damn it!\n"); } else if (strcmp(p_args[i], "-no-subdir") == 0) { -- 2.39.5 From 8da3b4bd43c99c4e4ee48285cb246d6424679668 Mon Sep 17 00:00:00 2001 From: JackCarterSmith Date: Mon, 1 Aug 2022 22:53:31 +0200 Subject: [PATCH 02/15] New library structure prototype --- .gitmodules | 4 +- CMakeLists.txt | 49 +-- RSEModel/CMakeLists.txt | 43 ++ {src => RSEModel}/Model-Extractor.c | 373 +++++++++--------- RSEModel/config.h | 1 + {src => RSEModel}/config.h.in | 2 +- {src => RSEModel}/obj_exporter.c | 4 +- {src => RSEModel}/obj_exporter.h | 0 {src => RSEModel}/options.h | 64 +-- {src => RSEModel}/rlk | 0 RSPModelLib/CMakeLists.txt | 38 ++ RSPModelLib/config.h | 1 + RSPModelLib/config.h.in | 1 + {src => RSPModelLib}/errors_types.h | 0 {src => RSPModelLib}/hob_parser.c | 2 +- {src => RSPModelLib}/hob_parser.h | 5 +- {src => RSPModelLib}/hob_struct.h | 0 RSPModelLib/options.h | 32 ++ .../mingw_cross_toolchain.cmake | 0 19 files changed, 356 insertions(+), 263 deletions(-) create mode 100644 RSEModel/CMakeLists.txt rename {src => RSEModel}/Model-Extractor.c (93%) create mode 100644 RSEModel/config.h rename {src => RSEModel}/config.h.in (97%) rename {src => RSEModel}/obj_exporter.c (99%) rename {src => RSEModel}/obj_exporter.h (100%) rename {src => RSEModel}/options.h (96%) rename {src => RSEModel}/rlk (100%) create mode 100644 RSPModelLib/CMakeLists.txt create mode 100644 RSPModelLib/config.h create mode 100644 RSPModelLib/config.h.in rename {src => RSPModelLib}/errors_types.h (100%) rename {src => RSPModelLib}/hob_parser.c (99%) rename {src => RSPModelLib}/hob_parser.h (59%) rename {src => RSPModelLib}/hob_struct.h (100%) create mode 100644 RSPModelLib/options.h rename mingw_cross_toolchain.cmake => cmake/mingw_cross_toolchain.cmake (100%) diff --git a/.gitmodules b/.gitmodules index cc9feb4..5b2ac1a 100644 --- a/.gitmodules +++ b/.gitmodules @@ -1,3 +1,3 @@ -[submodule "src/rlk"] - path = src/rlk +[submodule "RSEModel/rlk"] + path = RSEModel/rlk url = https://github.com/rlk/obj.git diff --git a/CMakeLists.txt b/CMakeLists.txt index 7be0b65..e5b8488 100644 --- a/CMakeLists.txt +++ b/CMakeLists.txt @@ -14,53 +14,26 @@ if(DEFINED ENV{MS_COMPATIBLE}) set(CMAKE_GNUtoMS ON) # Enable compatibility level to exported libraries endif() -include(CheckIncludeFile) -include(CheckCSourceCompiles) - -add_definitions(-DCONF_NO_GL) # Used for obj-lib to not compile GL part - # Project definition if(DEFINED ENV{CI}) # Jenkins CI integration mode project(rse-model VERSION $ENV{CI_VERSION}.$ENV{CI_BUILD_NUMBER} DESCRIPTION "RogueSquadron Extractor - Model" LANGUAGES C) - set(RSE_MOD_NAME $ENV{CI_OUTPUT_NAME}-${PROJECT_VERSION}) + + set(RSE_MODEL_NAME $ENV{CI_OUTPUT_NAME}_${PROJECT_VERSION}) else() # Standalone project mode, should not be used for release. project(rse-model VERSION 1.0.0 DESCRIPTION "RogueSquadron Extractor - Model" LANGUAGES C) - set(RSE_MOD_NAME RSE_Model-${PROJECT_VERSION}) + set(RSE_MODEL_NAME RSEModel_${PROJECT_VERSION}) endif() -# Push compile infos to source -configure_file(${CMAKE_CURRENT_SOURCE_DIR}/src/config.h.in ${CMAKE_CURRENT_SOURCE_DIR}/src/config.h @ONLY) +set(RSP_MODEL_LIB_NAME RSPModel${PROJECT_VERSION_MAJOR}${PROJECT_VERSION_MINOR}) -# Import needed packages and references their include path -#find_package(GLEW REQUIRED) # Enable when GL rendering is ready -#include_directories(${GLEW_INCLUDE_DIR}) - - -# Define src/headers files -FILE(GLOB_RECURSE RSE_MOD_SOURCES src/*.c) -FILE(GLOB_RECURSE RSE_MOD_HEADERS src/*.h) -SOURCE_GROUP("Source Files" FILES ${RSE_MOD_SOURCES}) -SOURCE_GROUP("Header Files" FILES ${RSE_MOD_HEADERS}) - - -# Building instructions for RSE-Model -if(DEFINED ENV{RSE-WS}) - set(CMAKE_BUILD_TYPE DEBUG) -endif() -#include_directories(${CMAKE_CURRENT_SOURCE_DIR}) -add_executable(rse-model ${RSE_MOD_SOURCES} ${RSE_MOD_HEADERS}) # Set the inputs for the compiler (srcs&hrds) -set_property(TARGET rse-model PROPERTY C_STANDARD 90) -set_target_properties(rse-model PROPERTIES OUTPUT_NAME ${RSE_MOD_NAME}) # Define the executable file name -# Link externals libraries to the linker -if(MSVC) - # msvc does not append 'lib' - do it here to have consistent name - #set_target_properties(rse-model PROPERTIES PREFIX "lib") - set_target_properties(rse-model PROPERTIES IMPORT_PREFIX "lib") - target_link_libraries(rse-model ${GLEW_LIBRARIES}) -else() - target_link_libraries(rse-model ${GLEW_LIBRARIES} m) -endif() +# The project is divided in two parts: +# - RSPModelLib is the parser library for model type data, it's take HOB file as input and output extracted datas. +# It is intended to be used by others apps like rendering engine or others. +# - RSEModel is the standalone application of the library, take HOB file in argument and output OBJ/MTL file. +# Artists or users can directly use this program to retrieve data in common datas format. +add_subdirectory(RSPModelLib) +add_subdirectory(RSEModel) # GPG signature custom command diff --git a/RSEModel/CMakeLists.txt b/RSEModel/CMakeLists.txt new file mode 100644 index 0000000..d3e599f --- /dev/null +++ b/RSEModel/CMakeLists.txt @@ -0,0 +1,43 @@ +# CMakeLists.txt + +#################################################### +# Written by JackCarterSmith, 2022 +# This code is released under the RSE license. +#################################################### + + +# General configuration +include(CheckIncludeFile) +include(CheckCSourceCompiles) + +add_definitions(-DCONF_NO_GL) # Used for obj-lib to not compile GL part + +# Import needed packages and references their include path +#find_package(GLEW REQUIRED) # Enable when GL rendering is ready +#include_directories(${GLEW_INCLUDE_DIR}) + +# Push compile infos to source +configure_file(${CMAKE_CURRENT_SOURCE_DIR}/config.h.in ${CMAKE_CURRENT_SOURCE_DIR}/config.h @ONLY) + + +# Define src/headers files +FILE(GLOB_RECURSE RSE_MOD_SOURCES ./*.c) +SOURCE_GROUP("Source Files" FILES ${RSE_MOD_SOURCES}) + + +# Building instructions for RSE-Model +if(DEFINED ENV{RSE-WS}) + set(CMAKE_BUILD_TYPE DEBUG) +endif() +add_executable(rse-model ${RSE_MOD_SOURCES}) +set_property(TARGET rse-model PROPERTY C_STANDARD 90) +target_include_directories(rse-model PRIVATE ${CMAKE_CURRENT_SOURCE_DIR}) +set_target_properties(rse-model PROPERTIES OUTPUT_NAME ${RSE_MODEL_NAME}) +# Link externals libraries to the linker +if(MSVC) + # msvc does not append 'lib' - do it here to have consistent name + set_target_properties(rse-model PROPERTIES IMPORT_PREFIX "lib") + target_link_libraries(rse-model PRIVATE ${GLEW_LIBRARIES} rsp-model-lib) +else() + target_link_libraries(rse-model PRIVATE ${GLEW_LIBRARIES} m rsp-model-lib) +endif() diff --git a/src/Model-Extractor.c b/RSEModel/Model-Extractor.c similarity index 93% rename from src/Model-Extractor.c rename to RSEModel/Model-Extractor.c index 1ddf391..2d44f4d 100644 --- a/src/Model-Extractor.c +++ b/RSEModel/Model-Extractor.c @@ -1,186 +1,187 @@ -/** - * \file Model-Extractor.c - * \date 25/07/2022 - * \author JackCarterSmith - * \copyright GPL-v3.0 - * \brief HOB model parser and export to Waveform OBJ format. - */ - -#include -#include -#include -#if defined(_WIN32) - #include -#else - #include - #include -#endif -#include "errors_types.h" -#include "config.h" -#include "options.h" -#include "hob_struct.h" -#include "hob_parser.h" -#include "obj_exporter.h" - - -/* - * Internal functions declarations - */ - -static unsigned int mainProcess(int args_cnt, char* args_value[], T_PROG_OPTIONS* opt_ptr); -static void createSubDir(char *dirName); -static unsigned char checkInputArgs(T_PROG_OPTIONS* opt_ptr, int p_arg_nbr, char* p_args[]); -static void cleanUpMemory(T_HOB* hobStruct); -static void dispHelp(); - - -/* - * - MAIN - - */ -int main(int argc, char *argv[]) { - T_PROG_OPTIONS _opts; - unsigned char p; - - // Hello world! - printf("\n*** RogueSquadron Extractor (RSE) - MODEL module - v%s ***\n", VERSION); - - // Check for arguments - if (argc < 2) { - printf("\n[ERR] No input file/commands specified!\n"); - dispHelp(); - return ERROR_ARGS_NULL; - } - - // Create options for programs according to user's arguments. - p = checkInputArgs(&_opts, argc, argv); - if ( p == ERROR_GENERIC ) return NO_ERROR; - else if ( p != NO_ERROR ) return p; - - return mainProcess(argc, argv, &_opts); -} - - -/* - * Private functions definition - */ - -static unsigned int mainProcess(int args_cnt, char* args_value[], T_PROG_OPTIONS* p_opts) { - unsigned short file_index; - T_HOB* hobStruct = NULL; - int i; - - // Manage multiple inputs files - for ( file_index = p_opts->input_files_cnt; file_index < args_cnt; file_index++) - { - printf("\n=============================================\n[INFO] - Parsing file: %s ...\n", args_value[file_index]); - hobStruct = calloc(1, sizeof(T_HOB)); - // Parse data from HOB file and put in T_HOB structure. - if (parseHOBFile(args_value[file_index], hobStruct, p_opts) != NO_ERROR) { - printf("[ERR] Failed to parse datas from %s\n", args_value[file_index]); - free(hobStruct); - return ERROR_PROCESS; - } - - if (hobStruct->obj_count > 0) { - if (p_opts->output_dir) createSubDir(args_value[file_index]); - - for ( i = 0; i < hobStruct->obj_count; i++ ) { - if (exportOBJModel(&(hobStruct->objects[i]), args_value[file_index], p_opts) != NO_ERROR) - printf("[ERR] Failed to export %s object in OBJ format!\n", hobStruct->objects[i].name); - else - printf("[INFO] Successfully exported %s object in OBJ format.\n", hobStruct->objects[i].name); - } - } - } - - cleanUpMemory(hobStruct); - - return NO_ERROR; -} - -static unsigned char checkInputArgs(T_PROG_OPTIONS* opt_ptr, int p_arg_nbr, char* p_args[]) { - char test[256]; - int i; - - // Set default options - opt_ptr->raw = 0; - opt_ptr->output_dir = 1; - opt_ptr->export_mtl = 1; - - if (p_arg_nbr > 1) { - for ( i = 1; i < p_arg_nbr; i++) { - strcpy(test, p_args[i]); - if (p_args[i][0] != '-') break; - if (strcmp(p_args[i], "-h") == 0) { - dispHelp(); - return ERROR_GENERIC; - } else if (strcmp(p_args[i], "-v") == 0) { - opt_ptr->verbose_mode = 1; - printf("[OPTN] Verbose enabled.\n"); - } else if (strcmp(p_args[i], "-vv") == 0) { - opt_ptr->verbose_mode = 1; - opt_ptr->debug_mode = 1; - printf("[OPTN] Debug enabled.\n"); - } else if (strcmp(p_args[i], "-vvv") == 0) { - opt_ptr->verbose_mode = 1; - opt_ptr->debug_mode = 1; - opt_ptr->god_mode = 1; - printf("[OPTN] God damn it!\n"); - } else if (strcmp(p_args[i], "-no-subdir") == 0) { - opt_ptr->output_dir = 0; - printf("[OPTN] Export to current directory.\n"); - } else if (strcmp(p_args[i], "-mtl") == 0) { - opt_ptr->export_mtl = 0; - printf("[OPTN] No materials datas.\n"); - } else { - printf("[ERR] Unknown option: %s\n", p_args[i]); - } - } - - opt_ptr->input_files_cnt = i; - return NO_ERROR; - } - - return ERROR_ARGS_NULL; -} - -static void createSubDir(char *dirName) { - if (dirName == NULL) return; - char _dir[260]; //TODO: Change directory management - strcpy(_dir, dirName); - strcat(_dir, "-out"); - - #ifdef _WIN32 - CreateDirectory(_dir, NULL); - #else - mkdir(_dir, 0755); - #endif -} - -static void cleanUpMemory(T_HOB* hobStruct) { - int i,j; - - for ( i=0; iobj_count; i++ ) { - for ( j=0; jobjects[i].face_group_count; j++ ) { - - free(hobStruct->objects[i].object_parts[j].faces); - free(hobStruct->objects[i].object_parts[j].vertices); - } - - free(hobStruct->objects[i].object_parts); - } - - free(hobStruct->objects); - free(hobStruct); -} - -static void dispHelp() { - printf("\n"); - printf("Options:\n -h Print this message\n"); - printf(" -v -vv Activate verbose console output\n"); - printf(" -no-subdir Export models inside current folder\n"); - printf(" -no-mtl Disable materials datas export with model\n"); - printf("\n"); - printf("Usage: RSE-Model_%s [options] \n", VERSION); - printf("\n"); -} +/** + * \file Model-Extractor.c + * \date 25/07/2022 + * \author JackCarterSmith + * \copyright GPL-v3.0 + * \brief HOB model parser and export to Waveform OBJ format. + */ + +#include +#include +#include +#if defined(_WIN32) + #include +#else + #include + #include +#endif +#include +#include +#include +#include "config.h" +#include "options.h" +#include "obj_exporter.h" + + + +/* + * Internal functions declarations + */ + +static unsigned int mainProcess(int args_cnt, char* args_value[], T_PROG_OPTIONS* opt_ptr); +static void createSubDir(char *dirName); +static unsigned char checkInputArgs(T_PROG_OPTIONS* opt_ptr, int p_arg_nbr, char* p_args[]); +static void cleanUpMemory(T_HOB* hobStruct); +static void dispHelp(); + + +/* + * - MAIN - + */ +int main(int argc, char *argv[]) { + T_PROG_OPTIONS _opts; + unsigned char p; + + // Hello world! + printf("\n*** RogueSquadron Extractor (RSE) - MODEL module - v%s ***\n", VERSION); + + // Check for arguments + if (argc < 2) { + printf("\n[ERR] No input file/commands specified!\n"); + dispHelp(); + return ERROR_ARGS_NULL; + } + + // Create options for programs according to user's arguments. + p = checkInputArgs(&_opts, argc, argv); + if ( p == ERROR_GENERIC ) return NO_ERROR; + else if ( p != NO_ERROR ) return p; + + return mainProcess(argc, argv, &_opts); +} + + +/* + * Private functions definition + */ + +static unsigned int mainProcess(int args_cnt, char* args_value[], T_PROG_OPTIONS* p_opts) { + unsigned short file_index; + T_HOB* hobStruct = NULL; + int i; + + // Manage multiple inputs files + for ( file_index = p_opts->input_files_cnt; file_index < args_cnt; file_index++) + { + printf("\n=============================================\n[INFO] - Parsing file: %s ...\n", args_value[file_index]); + hobStruct = calloc(1, sizeof(T_HOB)); + // Parse data from HOB file and put in T_HOB structure. + if (RSP_ModelLib_ParseHOBFile(args_value[file_index], hobStruct, p_opts) != NO_ERROR) { + printf("[ERR] Failed to parse datas from %s\n", args_value[file_index]); + free(hobStruct); + return ERROR_PROCESS; + } + + if (hobStruct->obj_count > 0) { + if (p_opts->output_dir) createSubDir(args_value[file_index]); + + for ( i = 0; i < hobStruct->obj_count; i++ ) { + if (exportOBJModel(&(hobStruct->objects[i]), args_value[file_index], p_opts) != NO_ERROR) + printf("[ERR] Failed to export %s object in OBJ format!\n", hobStruct->objects[i].name); + else + printf("[INFO] Successfully exported %s object in OBJ format.\n", hobStruct->objects[i].name); + } + } + } + + cleanUpMemory(hobStruct); + + return NO_ERROR; +} + +static unsigned char checkInputArgs(T_PROG_OPTIONS* opt_ptr, int p_arg_nbr, char* p_args[]) { + char test[256]; + int i; + + // Set default options + opt_ptr->raw = 0; + opt_ptr->output_dir = 1; + opt_ptr->export_mtl = 1; + + if (p_arg_nbr > 1) { + for ( i = 1; i < p_arg_nbr; i++) { + strcpy(test, p_args[i]); + if (p_args[i][0] != '-') break; + if (strcmp(p_args[i], "-h") == 0) { + dispHelp(); + return ERROR_GENERIC; + } else if (strcmp(p_args[i], "-v") == 0) { + opt_ptr->verbose_mode = 1; + printf("[OPTN] Verbose enabled.\n"); + } else if (strcmp(p_args[i], "-vv") == 0) { + opt_ptr->verbose_mode = 1; + opt_ptr->debug_mode = 1; + printf("[OPTN] Debug enabled.\n"); + } else if (strcmp(p_args[i], "-vvv") == 0) { + opt_ptr->verbose_mode = 1; + opt_ptr->debug_mode = 1; + opt_ptr->god_mode = 1; + printf("[OPTN] God damn it!\n"); + } else if (strcmp(p_args[i], "-no-subdir") == 0) { + opt_ptr->output_dir = 0; + printf("[OPTN] Export to current directory.\n"); + } else if (strcmp(p_args[i], "-mtl") == 0) { + opt_ptr->export_mtl = 0; + printf("[OPTN] No materials datas.\n"); + } else { + printf("[ERR] Unknown option: %s\n", p_args[i]); + } + } + + opt_ptr->input_files_cnt = i; + return NO_ERROR; + } + + return ERROR_ARGS_NULL; +} + +static void createSubDir(char *dirName) { + if (dirName == NULL) return; + char _dir[260]; //TODO: Change directory management + strcpy(_dir, dirName); + strcat(_dir, "-out"); + + #ifdef _WIN32 + CreateDirectory(_dir, NULL); + #else + mkdir(_dir, 0755); + #endif +} + +static void cleanUpMemory(T_HOB* hobStruct) { + int i,j; + + for ( i=0; iobj_count; i++ ) { + for ( j=0; jobjects[i].face_group_count; j++ ) { + + free(hobStruct->objects[i].object_parts[j].faces); + free(hobStruct->objects[i].object_parts[j].vertices); + } + + free(hobStruct->objects[i].object_parts); + } + + free(hobStruct->objects); + free(hobStruct); +} + +static void dispHelp() { + printf("\n"); + printf("Options:\n -h Print this message\n"); + printf(" -v -vv Activate verbose console output\n"); + printf(" -no-subdir Export models inside current folder\n"); + printf(" -no-mtl Disable materials datas export with model\n"); + printf("\n"); + printf("Usage: RSE-Model_%s [options] \n", VERSION); + printf("\n"); +} diff --git a/RSEModel/config.h b/RSEModel/config.h new file mode 100644 index 0000000..bc0d1b1 --- /dev/null +++ b/RSEModel/config.h @@ -0,0 +1 @@ +#define VERSION "1.0.0" diff --git a/src/config.h.in b/RSEModel/config.h.in similarity index 97% rename from src/config.h.in rename to RSEModel/config.h.in index d35c5f2..32f49cf 100644 --- a/src/config.h.in +++ b/RSEModel/config.h.in @@ -1 +1 @@ -#define VERSION "@PROJECT_VERSION@" +#define VERSION "@PROJECT_VERSION@" diff --git a/src/obj_exporter.c b/RSEModel/obj_exporter.c similarity index 99% rename from src/obj_exporter.c rename to RSEModel/obj_exporter.c index bc3500d..0ac63c8 100644 --- a/src/obj_exporter.c +++ b/RSEModel/obj_exporter.c @@ -9,9 +9,9 @@ #include #include #include -#include "errors_types.h" +#include +#include #include "options.h" -#include "hob_struct.h" #include "rlk/obj.h" #include "obj_exporter.h" diff --git a/src/obj_exporter.h b/RSEModel/obj_exporter.h similarity index 100% rename from src/obj_exporter.h rename to RSEModel/obj_exporter.h diff --git a/src/options.h b/RSEModel/options.h similarity index 96% rename from src/options.h rename to RSEModel/options.h index 80bb82a..ec369ab 100644 --- a/src/options.h +++ b/RSEModel/options.h @@ -1,32 +1,32 @@ -/** - * \file options.h - * \date 29/07/2022 - * \author JackCarterSmith - * \copyright GPL-v3.0 - * \brief Shared options structure definition and declaration. - */ - -#ifndef OPTIONS_H_ -#define OPTIONS_H_ - -/// Options structure -typedef union u_prog_options { - struct { - unsigned char verbose_mode:1; //!< Output simple details about ID and other "light" things. - - unsigned char output_dir:1; //!< Export extracted datas to a sub-directory. - unsigned char export_mtl:1; //!< Export materials datas with object. - - unsigned char reserved0:5; //!< For future use. - - unsigned char debug_mode:1; //!< Output all values of faces, indices and vertices and others "heavy" things. - unsigned char god_mode:1; //!< Dev only. Output experimental values. - - unsigned char reserved1:6; //!< For future use. - - unsigned short input_files_cnt; //!< Internal files counters. - }; - unsigned int raw; //!< Raw options access for bit-masking or memory copy/compare. -} T_PROG_OPTIONS ; - -#endif /* OPTIONS_H_ */ +/** + * \file options.h + * \date 29/07/2022 + * \author JackCarterSmith + * \copyright GPL-v3.0 + * \brief Shared options structure definition and declaration. + */ + +#ifndef OPTIONS_H_ +#define OPTIONS_H_ + +/// Options structure +typedef union u_prog_options { + struct { + unsigned char verbose_mode:1; //!< Output simple details about ID and other "light" things. + + unsigned char output_dir:1; //!< Export extracted datas to a sub-directory. + unsigned char export_mtl:1; //!< Export materials datas with object. + + unsigned char reserved0:5; //!< For future use. + + unsigned char debug_mode:1; //!< Output all values of faces, indices and vertices and others "heavy" things. + unsigned char god_mode:1; //!< Dev only. Output experimental values. + + unsigned char reserved1:6; //!< For future use. + + unsigned short input_files_cnt; //!< Internal files counters. + }; + unsigned int raw; //!< Raw options access for bit-masking or memory copy/compare. +} T_PROG_OPTIONS ; + +#endif /* OPTIONS_H_ */ diff --git a/src/rlk b/RSEModel/rlk similarity index 100% rename from src/rlk rename to RSEModel/rlk diff --git a/RSPModelLib/CMakeLists.txt b/RSPModelLib/CMakeLists.txt new file mode 100644 index 0000000..59d017a --- /dev/null +++ b/RSPModelLib/CMakeLists.txt @@ -0,0 +1,38 @@ +# CMakeLists.txt + +#################################################### +# Written by JackCarterSmith, 2022 +# This code is released under the RSE license. +#################################################### + + +# General library configuration +if(DEFINED ENV{MS_COMPATIBLE}) + set(CMAKE_GNUtoMS ON) # Enable compatibility level to exported libraries +endif() + +include(CheckIncludeFile) +include(CheckCSourceCompiles) + +# Push compile infos to source +configure_file(${CMAKE_CURRENT_SOURCE_DIR}/config.h.in ${CMAKE_CURRENT_SOURCE_DIR}/config.h @ONLY) + + +# Define src/headers files +FILE(GLOB_RECURSE RSP_MOD_SOURCES ./*.c) +SOURCE_GROUP("Source Files" FILES ${RSP_MOD_SOURCES}) + + +# Building instructions for RSE-Model +if(DEFINED ENV{RSE-WS}) + set(CMAKE_BUILD_TYPE DEBUG) +endif() +add_library(rsp-model-lib ${RSP_MOD_SOURCES}) +set_property(TARGET rsp-model-lib PROPERTY C_STANDARD 90) +target_include_directories(rsp-model-lib PUBLIC ${CMAKE_CURRENT_SOURCE_DIR}) +set_target_properties(rsp-model-lib PROPERTIES OUTPUT_NAME ${RSP_MODEL_LIB_NAME}) +# Link externals libraries to the linker +if(MSVC) + # msvc does not append 'lib' - do it here to have consistent name + set_target_properties(rsp-model-lib PROPERTIES PREFIX "lib") +endif() diff --git a/RSPModelLib/config.h b/RSPModelLib/config.h new file mode 100644 index 0000000..bc0d1b1 --- /dev/null +++ b/RSPModelLib/config.h @@ -0,0 +1 @@ +#define VERSION "1.0.0" diff --git a/RSPModelLib/config.h.in b/RSPModelLib/config.h.in new file mode 100644 index 0000000..32f49cf --- /dev/null +++ b/RSPModelLib/config.h.in @@ -0,0 +1 @@ +#define VERSION "@PROJECT_VERSION@" diff --git a/src/errors_types.h b/RSPModelLib/errors_types.h similarity index 100% rename from src/errors_types.h rename to RSPModelLib/errors_types.h diff --git a/src/hob_parser.c b/RSPModelLib/hob_parser.c similarity index 99% rename from src/hob_parser.c rename to RSPModelLib/hob_parser.c index 427de3f..3ca2d46 100644 --- a/src/hob_parser.c +++ b/RSPModelLib/hob_parser.c @@ -15,7 +15,7 @@ #include "hob_parser.h" -unsigned char parseHOBFile(const char* fileName, T_HOB* hob_struct, T_PROG_OPTIONS* p_opts) { +unsigned char RSP_ModelLib_ParseHOBFile(const char* fileName, T_HOB* hob_struct, T_PROG_OPTIONS* p_opts) { unsigned char err = NO_ERROR; long fileSize; FILE* fStream = NULL; diff --git a/src/hob_parser.h b/RSPModelLib/hob_parser.h similarity index 59% rename from src/hob_parser.h rename to RSPModelLib/hob_parser.h index 7219839..6739711 100644 --- a/src/hob_parser.h +++ b/RSPModelLib/hob_parser.h @@ -6,10 +6,13 @@ * \brief Decode HOB file structure. */ +#include "options.h" +#include "hob_struct.h" + #ifndef SRC_HOB_PARSER_H_ #define SRC_HOB_PARSER_H_ -unsigned char parseHOBFile(const char* fileName, T_HOB* hob_struct, T_PROG_OPTIONS* p_opts); +unsigned char RSP_ModelLib_ParseHOBFile(const char* fileName, T_HOB* hob_struct, T_PROG_OPTIONS* p_opts); #endif /* SRC_HOB_PARSER_H_ */ diff --git a/src/hob_struct.h b/RSPModelLib/hob_struct.h similarity index 100% rename from src/hob_struct.h rename to RSPModelLib/hob_struct.h diff --git a/RSPModelLib/options.h b/RSPModelLib/options.h new file mode 100644 index 0000000..ec369ab --- /dev/null +++ b/RSPModelLib/options.h @@ -0,0 +1,32 @@ +/** + * \file options.h + * \date 29/07/2022 + * \author JackCarterSmith + * \copyright GPL-v3.0 + * \brief Shared options structure definition and declaration. + */ + +#ifndef OPTIONS_H_ +#define OPTIONS_H_ + +/// Options structure +typedef union u_prog_options { + struct { + unsigned char verbose_mode:1; //!< Output simple details about ID and other "light" things. + + unsigned char output_dir:1; //!< Export extracted datas to a sub-directory. + unsigned char export_mtl:1; //!< Export materials datas with object. + + unsigned char reserved0:5; //!< For future use. + + unsigned char debug_mode:1; //!< Output all values of faces, indices and vertices and others "heavy" things. + unsigned char god_mode:1; //!< Dev only. Output experimental values. + + unsigned char reserved1:6; //!< For future use. + + unsigned short input_files_cnt; //!< Internal files counters. + }; + unsigned int raw; //!< Raw options access for bit-masking or memory copy/compare. +} T_PROG_OPTIONS ; + +#endif /* OPTIONS_H_ */ diff --git a/mingw_cross_toolchain.cmake b/cmake/mingw_cross_toolchain.cmake similarity index 100% rename from mingw_cross_toolchain.cmake rename to cmake/mingw_cross_toolchain.cmake -- 2.39.5 From 5922c3ec6a02e7dd42a54b1faeb86f66c94e82e4 Mon Sep 17 00:00:00 2001 From: JackCarterSmith Date: Thu, 11 Aug 2022 22:29:40 +0200 Subject: [PATCH 03/15] Update lib name and implement basis of lib interface --- RSEModel/CMakeLists.txt | 4 +- RSEModel/Model-Extractor.c | 2 +- RSEModel/obj_exporter.c | 2 +- RSPModelLib/CMakeLists.txt | 10 +-- RSPModelLib/config.h | 1 - RSPModelLib/config.h.in | 1 - RSPModelLib/errors_types.h | 28 ------ RSPModelLib/include/RSPModel.h | 82 ++++++++++++++++++ RSPModelLib/include/RSPModel_datatypes.h | 104 +++++++++++++++++++++++ RSPModelLib/include/RSPModel_errordefs.h | 43 ++++++++++ RSPModelLib/src/RSPModel.c | 42 +++++++++ RSPModelLib/src/config.h | 6 ++ RSPModelLib/src/config.h.in | 6 ++ RSPModelLib/{ => src}/hob_parser.c | 15 ++-- RSPModelLib/{ => src}/hob_parser.h | 4 +- RSPModelLib/{ => src}/hob_struct.h | 100 ++-------------------- RSPModelLib/{ => src}/options.h | 10 +-- 17 files changed, 316 insertions(+), 144 deletions(-) delete mode 100644 RSPModelLib/config.h delete mode 100644 RSPModelLib/config.h.in delete mode 100644 RSPModelLib/errors_types.h create mode 100644 RSPModelLib/include/RSPModel.h create mode 100644 RSPModelLib/include/RSPModel_datatypes.h create mode 100644 RSPModelLib/include/RSPModel_errordefs.h create mode 100644 RSPModelLib/src/RSPModel.c create mode 100644 RSPModelLib/src/config.h create mode 100644 RSPModelLib/src/config.h.in rename RSPModelLib/{ => src}/hob_parser.c (98%) rename RSPModelLib/{ => src}/hob_parser.h (78%) rename RSPModelLib/{ => src}/hob_struct.h (67%) rename RSPModelLib/{ => src}/options.h (84%) diff --git a/RSEModel/CMakeLists.txt b/RSEModel/CMakeLists.txt index d3e599f..843e9b1 100644 --- a/RSEModel/CMakeLists.txt +++ b/RSEModel/CMakeLists.txt @@ -26,8 +26,8 @@ SOURCE_GROUP("Source Files" FILES ${RSE_MOD_SOURCES}) # Building instructions for RSE-Model -if(DEFINED ENV{RSE-WS}) - set(CMAKE_BUILD_TYPE DEBUG) +if(DEFINED ENV{CI}) + set(CMAKE_BUILD_TYPE RELEASE) endif() add_executable(rse-model ${RSE_MOD_SOURCES}) set_property(TARGET rse-model PROPERTY C_STANDARD 90) diff --git a/RSEModel/Model-Extractor.c b/RSEModel/Model-Extractor.c index 2d44f4d..06894f6 100644 --- a/RSEModel/Model-Extractor.c +++ b/RSEModel/Model-Extractor.c @@ -15,7 +15,7 @@ #include #include #endif -#include +#include #include #include #include "config.h" diff --git a/RSEModel/obj_exporter.c b/RSEModel/obj_exporter.c index 0ac63c8..94faac0 100644 --- a/RSEModel/obj_exporter.c +++ b/RSEModel/obj_exporter.c @@ -9,8 +9,8 @@ #include #include #include -#include #include +#include #include "options.h" #include "rlk/obj.h" #include "obj_exporter.h" diff --git a/RSPModelLib/CMakeLists.txt b/RSPModelLib/CMakeLists.txt index 59d017a..fbe24d2 100644 --- a/RSPModelLib/CMakeLists.txt +++ b/RSPModelLib/CMakeLists.txt @@ -15,21 +15,21 @@ include(CheckIncludeFile) include(CheckCSourceCompiles) # Push compile infos to source -configure_file(${CMAKE_CURRENT_SOURCE_DIR}/config.h.in ${CMAKE_CURRENT_SOURCE_DIR}/config.h @ONLY) +configure_file(${CMAKE_CURRENT_SOURCE_DIR}/src/config.h.in ${CMAKE_CURRENT_SOURCE_DIR}/src/config.h @ONLY) # Define src/headers files -FILE(GLOB_RECURSE RSP_MOD_SOURCES ./*.c) +FILE(GLOB_RECURSE RSP_MOD_SOURCES ./src/*.c) SOURCE_GROUP("Source Files" FILES ${RSP_MOD_SOURCES}) # Building instructions for RSE-Model -if(DEFINED ENV{RSE-WS}) - set(CMAKE_BUILD_TYPE DEBUG) +if(DEFINED ENV{CI}) + set(CMAKE_BUILD_TYPE RELEASE) endif() add_library(rsp-model-lib ${RSP_MOD_SOURCES}) set_property(TARGET rsp-model-lib PROPERTY C_STANDARD 90) -target_include_directories(rsp-model-lib PUBLIC ${CMAKE_CURRENT_SOURCE_DIR}) +target_include_directories(rsp-model-lib PUBLIC ${CMAKE_CURRENT_SOURCE_DIR}/include) set_target_properties(rsp-model-lib PROPERTIES OUTPUT_NAME ${RSP_MODEL_LIB_NAME}) # Link externals libraries to the linker if(MSVC) diff --git a/RSPModelLib/config.h b/RSPModelLib/config.h deleted file mode 100644 index bc0d1b1..0000000 --- a/RSPModelLib/config.h +++ /dev/null @@ -1 +0,0 @@ -#define VERSION "1.0.0" diff --git a/RSPModelLib/config.h.in b/RSPModelLib/config.h.in deleted file mode 100644 index 32f49cf..0000000 --- a/RSPModelLib/config.h.in +++ /dev/null @@ -1 +0,0 @@ -#define VERSION "@PROJECT_VERSION@" diff --git a/RSPModelLib/errors_types.h b/RSPModelLib/errors_types.h deleted file mode 100644 index 6d101ab..0000000 --- a/RSPModelLib/errors_types.h +++ /dev/null @@ -1,28 +0,0 @@ -/* - * errors_types.h - * - * Created on: 26 juil. 2022 - * Author: JackCarterSmith - */ - -//#include "error.h" //TODO: use it as base for error ID - - -#ifndef SRC_ERRORS_TYPES_H_ -#define SRC_ERRORS_TYPES_H_ - -#ifdef NO_ERROR -#undef NO_ERROR -#endif -#define NO_ERROR 0 -#define ERROR_GENERIC 1 -#define ERROR_MEMORY 2 -#define ERROR_IO 3 -#define ERROR_PROCESS 4 - -#define ERROR_ARGS_NULL 10 -#define ERROR_ARGS_RANGE 11 - -#define ERROR_REALITY_BROKED -1 - -#endif /* SRC_ERRORS_TYPES_H_ */ diff --git a/RSPModelLib/include/RSPModel.h b/RSPModelLib/include/RSPModel.h new file mode 100644 index 0000000..70f81c5 --- /dev/null +++ b/RSPModelLib/include/RSPModel.h @@ -0,0 +1,82 @@ +/** + * @file RSPModel.h + * @date 11/08/2022 + * @author JackCarterSmith + * @copyright GPL-v3.0 + * @brief Rogue Squadron Parser model library, used to decode decode datas + * from original game file and access them through public interface. + * + */ + +#include "RSPModel_datatypes.h" + +#ifndef RSPMODEL_H_ +#define RSPMODEL_H_ + +#ifdef __cplusplus +extern "C" { +#endif + +/////////////////////////////////////////////////////////////////////////////// +// Library's functions declaration +/////////////////////////////////////////////////////////////////////////////// + +/** + * @brief Get the current library version. + * @return Char array of the version, escape char included. + */ +char* RSPModel_getVersion( void ); + +/** + * @brief Run model parser for the specified file in file system. + * @details Model library can process HOB file from file system. It's a easy + * approach using this library for debugging purpose. + * + * @param[out] hob HOB structure to be filled with parsed datas. + * @param[in] filePath Path to the HOB file in system. + * + * @return Error status, return RSPLIB_SUCCESS in nominal case. + */ +unsigned short RSPModel_processHOBFileMemory( T_RSPMODEL_HOB* hob, const char* const filePath ); + +/** + * @brief Run model parser for the specified file in memory. + * @details Model library can process HOB file directly stored in RAM memory, + * you must load the file beforehand through a malloc/memcpy call. + * @warning No controls routines are implemented to verify file length! + * + * @param[out] hob HOB structure to be filled with parsed datas. + * @param[in] memFilePtr Pointer to the beginning of the file in memory. + * @param[in] memFileSize Size of the file in bytes. + * + * @return Error status, return RSPLIB_SUCCESS in nominal case. + */ +unsigned short RSPModel_processHOBFile( T_RSPMODEL_HOB* hob, const void* const memFilePtr, const long memFileSize ); + +/** + * @brief Convert HOB's object datas to GL compatible format. + * @note Only available if GL module as specified at compilation. + * + * @param[in] objStruct Object datas from previously parsed HOB file. + * @param[out] glObj GL structure. + * + * @return Error status, return RSPLIB_SUCCESS in nominal case. + */ +unsigned short RSPModel_objectToGL( const T_RSPMODEL_OBJECT* objStruct, void* glObj ); + +/** + * @brief Convert HOB's object datas to Direct3D compatible format. + * @note Only available if D3D module as specified at compilation. + * + * @param[in] objStruct Object datas from previously parsed HOB file. + * @param[out] D3DObj Direct3D structure. + * + * @return Error status, return RSPLIB_SUCCESS in nominal case. + */ +unsigned short RSPModel_objectToD3D( const T_RSPMODEL_OBJECT* objStruct, void* D3DObj ); + +#ifdef __cplusplus +} +#endif + +#endif /* RSPMODEL_H_ */ diff --git a/RSPModelLib/include/RSPModel_datatypes.h b/RSPModelLib/include/RSPModel_datatypes.h new file mode 100644 index 0000000..53a4f15 --- /dev/null +++ b/RSPModelLib/include/RSPModel_datatypes.h @@ -0,0 +1,104 @@ +/** + * @file RSPModel_datatypes.h + * @date 11/08/2022 + * @author JackCarterSmith + * @copyright GPL-v3.0 + * @brief RSP Model workflow structures definitions + * + */ + +#ifndef RSPMODEL_DATATYPES_H_ +#define RSPMODEL_DATATYPES_H_ + +#ifdef __cplusplus +extern "C" { +#endif + +/////////////////////////////////////////////////////////////////////////////// +// Lib's structure definitions +/////////////////////////////////////////////////////////////////////////////// + +typedef unsigned int T_RGBA; + +typedef struct vector3 { float x,y,z; } T_VECTOR3; + +typedef struct vertex { short x,y,z,w; } T_VERTEX; + +typedef struct tex_coord { unsigned short u,v; } T_TEXCOORD; + +typedef struct face_flags { + unsigned int fUnknown0:1; + unsigned int fUnknown1:1; + unsigned int fHasTexture:1; + unsigned int fIsQuad:1; + unsigned int fSeparateColorVertex:1; + unsigned int fHasColor:1; + unsigned int fHasExtraBytesBeforeColor:1; + unsigned int fUnknown7:1; + unsigned int fUnknown8:1; + unsigned int fUnknown9:1; + unsigned int fUnknown10:1; + + unsigned int reserved:21; +} FACE_FLAGS; + +typedef struct hob_face { + union { + unsigned int flags; + FACE_FLAGS flags_bits; + }; + unsigned char b1; + unsigned char b2; + unsigned char b3; + unsigned char bsize; + unsigned short material_index; + unsigned short indices[4]; + T_RGBA vertex_colors[4]; //TODO: convert in R:8_G:8_B:8_A:8 format? Caution with BE/LE conversion + T_TEXCOORD tex_coords[4]; +} T_HOB_FACE; + +typedef struct hob_face_group { + unsigned int meshdef1_offset; + + unsigned int face_block_end_offset; + unsigned int face_block_offset; + unsigned int vertex_block_offset; + + unsigned int id; + T_VECTOR3 transform; + + unsigned int face_count; + T_HOB_FACE* faces; + + unsigned int vertex_count; + T_VERTEX* vertices; +} T_HOB_FACE_GROUP; + +typedef struct rspmodel_object { + char name[16]; + unsigned int face_group_offset; + unsigned int object_part_header_offset; + unsigned int face_group_header_offset; + + unsigned int object_part_count; + unsigned int face_group_count; + + T_HOB_FACE_GROUP* object_parts; +} T_RSPMODEL_OBJECT; + +/** + * @brief Model-Extractor HOB structure of an HOB file content. + * @details Used with malloc to create a clean method of bufferized + * model datas before saving it. + * @todo Export format to use it directly in other program. + */ +typedef struct rspmodel_hob { + unsigned int obj_count; + T_RSPMODEL_OBJECT* objects; +} T_RSPMODEL_HOB; + +#ifdef __cplusplus +} +#endif + +#endif /* RSPMODEL_DATATYPES_H_ */ diff --git a/RSPModelLib/include/RSPModel_errordefs.h b/RSPModelLib/include/RSPModel_errordefs.h new file mode 100644 index 0000000..fa33c03 --- /dev/null +++ b/RSPModelLib/include/RSPModel_errordefs.h @@ -0,0 +1,43 @@ +/** + * \file RSPModel_errordefs.h + * \date 26/07/2022 + * \author JackCarterSmith + * \copyright GPL-v3.0 + * \brief Errors type definition file. Used mostly by methods in this project. + * + */ + + +#ifndef RSPMODELLIB_ERRORS_H_ +#define RSPMODELLIB_ERRORS_H_ + +#ifdef __cplusplus +extern "C" { +#endif + +/////////////////////////////////////////////////////////////////////////////// +// Errors types definitions +/////////////////////////////////////////////////////////////////////////////// + +#ifndef NO_ERROR +#define NO_ERROR 0 // In case of dual declaration by GCC +#endif +#define RSPLIB_SUCCESS NO_ERROR //!< All is running good! + +#define RSPLIB_ERROR_GENERIC 1 //!< Misuse of the program +#define RSPLIB_ERROR_MEMORY 2 //!< Memory de/allocation failure +#define RSPLIB_ERROR_IO 3 //!< File system access failure +#define RSPLIB_ERROR_PROCESS 4 //!< Internal processing failure + +#define RSPLIB_ERROR_ARGS_NULL 16 //!< Method not NULL input expected +#define RSPLIB_ERROR_ARGS_RANGE 17 //!< Method input out of expected range + +#define RSPLIB_ERROR_MOD_DISABLED 64 //!< A necessary module hasn't been activated during compilation time + +#define RSPLIB_ERROR_REALITY_BRK -1 //!< This error can only appear in alternate reality + +#ifdef __cplusplus +} +#endif + +#endif /* RSPMODELLIB_ERRORS_H_ */ diff --git a/RSPModelLib/src/RSPModel.c b/RSPModelLib/src/RSPModel.c new file mode 100644 index 0000000..2dc0263 --- /dev/null +++ b/RSPModelLib/src/RSPModel.c @@ -0,0 +1,42 @@ +/** + * \file RSPModel.c + * \date 11/08/2022 + * \author JackCarterSmith + * \copyright GPL-v3.0 + * \brief HOB model parser and export to Waveform OBJ format. + * + */ + +#include +#include "config.h" +#include "options.h" +#include "RSPModel_errordefs.h" +#include "RSPModel.h" + +char* RSPModel_getVersion( void ) { + return PRG_VERSION; +} + +unsigned short RSPModel_processHOBFileMemory( T_RSPMODEL_HOB* hob, const char* const filePath ) { + return RSPLIB_SUCCESS; +} + +unsigned short RSPModel_processHOBFile( T_RSPMODEL_HOB* hob, const void* const memFilePtr, const long memFileSize ) { + return RSPLIB_SUCCESS; +} + +unsigned short RSPModel_objectToGL( const T_RSPMODEL_OBJECT* objStruct, void* glObj ) { +#ifndef GL_SUPPORT + return RSPLIB_ERROR_MOD_DISABLED; +#endif + + return RSPLIB_SUCCESS; +} + +unsigned short RSPModel_objectToD3D( const T_RSPMODEL_OBJECT* objStruct, void* D3DObj ) { +#ifndef D3D_SUPPORT + return RSPLIB_ERROR_MOD_DISABLED; +#endif + + return RSPLIB_SUCCESS; +} diff --git a/RSPModelLib/src/config.h b/RSPModelLib/src/config.h new file mode 100644 index 0000000..2a1d023 --- /dev/null +++ b/RSPModelLib/src/config.h @@ -0,0 +1,6 @@ +#ifndef CONFIG_H_ +#define CONFIG_H_ + +#define PRG_VERSION "1.0.0" + +#endif /* CONFIG_H_ */ diff --git a/RSPModelLib/src/config.h.in b/RSPModelLib/src/config.h.in new file mode 100644 index 0000000..3f2e0c4 --- /dev/null +++ b/RSPModelLib/src/config.h.in @@ -0,0 +1,6 @@ +#ifndef CONFIG_H_ +#define CONFIG_H_ + +#define PRG_VERSION "@PROJECT_VERSION@" + +#endif /* CONFIG_H_ */ diff --git a/RSPModelLib/hob_parser.c b/RSPModelLib/src/hob_parser.c similarity index 98% rename from RSPModelLib/hob_parser.c rename to RSPModelLib/src/hob_parser.c index 3ca2d46..7de9d42 100644 --- a/RSPModelLib/hob_parser.c +++ b/RSPModelLib/src/hob_parser.c @@ -9,13 +9,14 @@ #include #include #include -#include "errors_types.h" +#include "RSPModel_errordefs.h" +#include "RSPModel_datatypes.h" #include "options.h" #include "hob_struct.h" #include "hob_parser.h" -unsigned char RSP_ModelLib_ParseHOBFile(const char* fileName, T_HOB* hob_struct, T_PROG_OPTIONS* p_opts) { +unsigned char RSP_ModelLib_ParseHOBFile(const char* fileName, T_RSPMODEL_HOB* hob_struct, T_PROG_OPTIONS* p_opts) { unsigned char err = NO_ERROR; long fileSize; FILE* fStream = NULL; @@ -47,7 +48,7 @@ unsigned char RSP_ModelLib_ParseHOBFile(const char* fileName, T_HOB* hob_struct, if (hob_struct->obj_count > 0) { // Populate HOB structure with object descriptor - hob_struct->objects = calloc(hob_struct->obj_count, sizeof(T_HOB_OBJECT)); + hob_struct->objects = calloc(hob_struct->obj_count, sizeof(T_RSPMODEL_OBJECT)); for ( i = 0; i < hob_struct->obj_count; i++ ) { if (p_opts->debug_mode) printf("\n-=====================-Begin of Object part-======================-\n"); @@ -401,7 +402,7 @@ unsigned char RSP_ModelLib_ParseHOBFile(const char* fileName, T_HOB* hob_struct, free(offset_index); } else { - err = ERROR_GENERIC; + err = RSPLIB_ERROR_GENERIC; printf("[INFO] Can't process empty file!\n"); } @@ -409,14 +410,14 @@ unsigned char RSP_ModelLib_ParseHOBFile(const char* fileName, T_HOB* hob_struct, } else { fclose(fStream); - err = ERROR_MEMORY; + err = RSPLIB_ERROR_MEMORY; if (p_opts->verbose_mode) printf("[ERR] Can't allocate enough memory for file processing!\n"); } } else { - err = ERROR_IO; + err = RSPLIB_ERROR_IO; if (p_opts->verbose_mode) printf("[ERR] Input file %s not found!\n", fileName); } - } else err = ERROR_ARGS_NULL; + } else err = RSPLIB_ERROR_ARGS_NULL; return err; } diff --git a/RSPModelLib/hob_parser.h b/RSPModelLib/src/hob_parser.h similarity index 78% rename from RSPModelLib/hob_parser.h rename to RSPModelLib/src/hob_parser.h index 6739711..32b350d 100644 --- a/RSPModelLib/hob_parser.h +++ b/RSPModelLib/src/hob_parser.h @@ -7,12 +7,12 @@ */ #include "options.h" -#include "hob_struct.h" +#include "RSPModel_datatypes.h" #ifndef SRC_HOB_PARSER_H_ #define SRC_HOB_PARSER_H_ -unsigned char RSP_ModelLib_ParseHOBFile(const char* fileName, T_HOB* hob_struct, T_PROG_OPTIONS* p_opts); +unsigned char RSP_ModelLib_ParseHOBFile(const char* fileName, T_RSPMODEL_HOB* hob_struct, T_PROG_OPTIONS* p_opts); #endif /* SRC_HOB_PARSER_H_ */ diff --git a/RSPModelLib/hob_struct.h b/RSPModelLib/src/hob_struct.h similarity index 67% rename from RSPModelLib/hob_struct.h rename to RSPModelLib/src/hob_struct.h index 28b96a8..b374150 100644 --- a/RSPModelLib/hob_struct.h +++ b/RSPModelLib/src/hob_struct.h @@ -1,12 +1,14 @@ -/* - * hob_struct.h +/** + * \file hob_struct.h + * \date 26/07/2022 + * \author JackCarterSmith + * \copyright GPL-v3.0 + * \brief HOB file mapping definition. * - * Created on: 26 juil. 2022 - * Author: JackCarterSmith */ -#ifndef SRC_HOB_STRUCT_H_ -#define SRC_HOB_STRUCT_H_ +#ifndef RSPMODELLIB_HOB_STRUCT_H_ +#define RSPMODELLIB_HOB_STRUCT_H_ /* @@ -22,90 +24,6 @@ #define PACK __attribute__((packed)) #endif -/////////////////////////////////////////////////////////////////////////////// -// HOB file structure -/////////////////////////////////////////////////////////////////////////////// - -typedef unsigned int T_RGBA; - -typedef struct vector3 { float x,y,z; } T_VECTOR3; - -typedef struct vertex { short x,y,z,w; } T_VERTEX; - -typedef struct tex_coord { unsigned short u,v; } T_TEXCOORD; - -typedef struct face_flags { - unsigned int fUnknown0:1; - unsigned int fUnknown1:1; - unsigned int fHasTexture:1; - unsigned int fIsQuad:1; - unsigned int fSeparateColorVertex:1; - unsigned int fHasColor:1; - unsigned int fHasExtraBytesBeforeColor:1; - unsigned int fUnknown7:1; - unsigned int fUnknown8:1; - unsigned int fUnknown9:1; - unsigned int fUnknown10:1; - - unsigned int reserved:21; -} FACE_FLAGS; - -typedef struct hob_face { - union { - unsigned int flags; - FACE_FLAGS flags_bits; - }; - unsigned char b1; - unsigned char b2; - unsigned char b3; - unsigned char bsize; - unsigned short material_index; - unsigned short indices[4]; - T_RGBA vertex_colors[4]; //TODO: convert in R:8_G:8_B:8_A:8 format? Caution with BE/LE conversion - T_TEXCOORD tex_coords[4]; -} T_HOB_FACE; - -typedef struct hob_face_group { - unsigned int meshdef1_offset; - - unsigned int face_block_end_offset; - unsigned int face_block_offset; - unsigned int vertex_block_offset; - - unsigned int id; - T_VECTOR3 transform; - - unsigned int face_count; - T_HOB_FACE* faces; - - unsigned int vertex_count; - T_VERTEX* vertices; -} T_HOB_FACE_GROUP; - -typedef struct hob_object { - char name[16]; - unsigned int face_group_offset; - unsigned int object_part_header_offset; - unsigned int face_group_header_offset; - - unsigned int object_part_count; - unsigned int face_group_count; - - T_HOB_FACE_GROUP* object_parts; -} T_HOB_OBJECT; - -/** - * \brief Model-Extractor HOB structure of an HOB file content. - * \details Used with malloc to create a clean method of bufferized - * model datas before saving it. - * \todo Export format to use it directly in other program. - */ -typedef struct hob { - unsigned int obj_count; - T_HOB_OBJECT* objects; -} T_HOB; - - /////////////////////////////////////////////////////////////////////////////// // Declaration of Memory Mapped Structure // Caution: the place of variable is important for correct mapping! @@ -289,4 +207,4 @@ typedef struct PACK hobfile_vertex { #pragma pack(pop) #endif -#endif /* SRC_HOB_STRUCT_H_ */ +#endif /* RSPMODELLIB_HOB_STRUCT_H_ */ diff --git a/RSPModelLib/options.h b/RSPModelLib/src/options.h similarity index 84% rename from RSPModelLib/options.h rename to RSPModelLib/src/options.h index ec369ab..d731673 100644 --- a/RSPModelLib/options.h +++ b/RSPModelLib/src/options.h @@ -1,9 +1,9 @@ /** - * \file options.h - * \date 29/07/2022 - * \author JackCarterSmith - * \copyright GPL-v3.0 - * \brief Shared options structure definition and declaration. + * \file options.h + * \date 29/07/2022 + * \author JackCarterSmith + * \copyright GPL-v3.0 + * \brief Shared options structure definition and declaration. */ #ifndef OPTIONS_H_ -- 2.39.5 From e10e74b8a161d00fb4370f9ef54eae44d1217b67 Mon Sep 17 00:00:00 2001 From: JackCarterSmith Date: Fri, 12 Aug 2022 17:58:49 +0200 Subject: [PATCH 04/15] Finished standard lib implement > static and dynamic linking... Need proper dynamic config > Standalone app basis... Need more rework > CMake proper install --- .gitignore | 2 +- .gitmodules | 4 +-- CMakeLists.txt | 28 +++++++++++++++---- RSEModel/CMakeLists.txt | 18 ++++++------ RSEModel/config.h | 1 - RSEModel/config.h.in | 1 - RSEModel/{ => src}/Model-Extractor.c | 39 +++++++++++++------------- RSEModel/{ => src}/obj_exporter.c | 8 +++--- RSEModel/{ => src}/obj_exporter.h | 2 +- RSEModel/{ => src}/options.h | 0 RSEModel/{ => src}/rlk | 0 RSPModelLib/CMakeLists.txt | 41 +++++++++++++++++++++++----- RSPModelLib/include/RSPModel.h | 34 +++++++++++++++++++---- RSPModelLib/src/RSPModel.c | 17 ++++++++++-- conanfile.txt | 2 +- config.h.in | 6 ++++ 16 files changed, 144 insertions(+), 59 deletions(-) delete mode 100644 RSEModel/config.h delete mode 100644 RSEModel/config.h.in rename RSEModel/{ => src}/Model-Extractor.c (84%) rename RSEModel/{ => src}/obj_exporter.c (96%) rename RSEModel/{ => src}/obj_exporter.h (76%) rename RSEModel/{ => src}/options.h (100%) rename RSEModel/{ => src}/rlk (100%) create mode 100644 config.h.in diff --git a/.gitignore b/.gitignore index 2c74351..cd6b464 100644 --- a/.gitignore +++ b/.gitignore @@ -15,7 +15,7 @@ # Precompiled Headers *.gch *.pch -src/config.h +config.h # Libraries *.lib diff --git a/.gitmodules b/.gitmodules index 5b2ac1a..b20867d 100644 --- a/.gitmodules +++ b/.gitmodules @@ -1,3 +1,3 @@ -[submodule "RSEModel/rlk"] - path = RSEModel/rlk +[submodule "RSEModel/src/rlk"] + path = RSEModel/src/rlk url = https://github.com/rlk/obj.git diff --git a/CMakeLists.txt b/CMakeLists.txt index e5b8488..3c268bb 100644 --- a/CMakeLists.txt +++ b/CMakeLists.txt @@ -18,20 +18,26 @@ endif() # Project definition if(DEFINED ENV{CI}) # Jenkins CI integration mode project(rse-model VERSION $ENV{CI_VERSION}.$ENV{CI_BUILD_NUMBER} DESCRIPTION "RogueSquadron Extractor - Model" LANGUAGES C) - - set(RSE_MODEL_NAME $ENV{CI_OUTPUT_NAME}_${PROJECT_VERSION}) + set(RSE_MODEL_NAME $ENV{CI_OUTPUT_NAME}) else() # Standalone project mode, should not be used for release. project(rse-model VERSION 1.0.0 DESCRIPTION "RogueSquadron Extractor - Model" LANGUAGES C) - set(RSE_MODEL_NAME RSEModel_${PROJECT_VERSION}) + set(RSE_MODEL_NAME RSEModel) endif() set(RSP_MODEL_LIB_NAME RSPModel${PROJECT_VERSION_MAJOR}${PROJECT_VERSION_MINOR}) +# Push compile infos to source +configure_file(${CMAKE_CURRENT_SOURCE_DIR}/config.h.in ${CMAKE_CURRENT_SOURCE_DIR}/RSPModelLib/src/config.h @ONLY) +configure_file(${CMAKE_CURRENT_SOURCE_DIR}/config.h.in ${CMAKE_CURRENT_SOURCE_DIR}/RSEModel/src/config.h @ONLY) + # The project is divided in two parts: # - RSPModelLib is the parser library for model type data, it's take HOB file as input and output extracted datas. # It is intended to be used by others apps like rendering engine or others. # - RSEModel is the standalone application of the library, take HOB file in argument and output OBJ/MTL file. # Artists or users can directly use this program to retrieve data in common datas format. +set(CMAKE_RUNTIME_OUTPUT_DIRECTORY ${PROJECT_BINARY_DIR}/bin) +set(CMAKE_LIBRARY_OUTPUT_DIRECTORY ${PROJECT_BINARY_DIR}/lib) +set(CMAKE_ARCHIVE_OUTPUT_DIRECTORY ${PROJECT_BINARY_DIR}/lib) add_subdirectory(RSPModelLib) add_subdirectory(RSEModel) @@ -48,6 +54,16 @@ add_subdirectory(RSEModel) # Install project executable -install(TARGETS rse-model - RUNTIME DESTINATION bin -) \ No newline at end of file +set(INSTALL_BIN_DIR "${CMAKE_INSTALL_PREFIX}/bin" CACHE PATH "Installation directory for executables") +set(INSTALL_LIB_DIR "${CMAKE_INSTALL_PREFIX}/lib" CACHE PATH "Installation directory for libraries") +set(INSTALL_INC_DIR "${CMAKE_INSTALL_PREFIX}/include" CACHE PATH "Installation directory for headers") +install(TARGETS rse-model rsp-model-lib rsp-model-libstatic + RUNTIME DESTINATION ${INSTALL_BIN_DIR} + LIBRARY DESTINATION ${INSTALL_LIB_DIR} + ARCHIVE DESTINATION ${INSTALL_LIB_DIR} +) +# Install library includes +install(FILES ${RSP_PUBLIC_HRDS} DESTINATION ${INSTALL_INC_DIR}) +# Install dependancies +install(FILES ${PROJECT_BINARY_DIR}/bin/glew32.dll + DESTINATION ${INSTALL_BIN_DIR}) diff --git a/RSEModel/CMakeLists.txt b/RSEModel/CMakeLists.txt index 843e9b1..d58b1f9 100644 --- a/RSEModel/CMakeLists.txt +++ b/RSEModel/CMakeLists.txt @@ -16,28 +16,30 @@ add_definitions(-DCONF_NO_GL) # Used for obj-lib to not compile GL part #find_package(GLEW REQUIRED) # Enable when GL rendering is ready #include_directories(${GLEW_INCLUDE_DIR}) -# Push compile infos to source -configure_file(${CMAKE_CURRENT_SOURCE_DIR}/config.h.in ${CMAKE_CURRENT_SOURCE_DIR}/config.h @ONLY) - # Define src/headers files -FILE(GLOB_RECURSE RSE_MOD_SOURCES ./*.c) -SOURCE_GROUP("Source Files" FILES ${RSE_MOD_SOURCES}) +file(GLOB_RECURSE RSE_MOD_SOURCES ./src/*.c) +source_group("Source Files" FILES ${RSE_MOD_SOURCES}) # Building instructions for RSE-Model if(DEFINED ENV{CI}) set(CMAKE_BUILD_TYPE RELEASE) endif() + + +# Declare standalone application add_executable(rse-model ${RSE_MOD_SOURCES}) set_property(TARGET rse-model PROPERTY C_STANDARD 90) -target_include_directories(rse-model PRIVATE ${CMAKE_CURRENT_SOURCE_DIR}) + +#target_include_directories(rse-model PRIVATE ${CMAKE_CURRENT_SOURCE_DIR}/src) set_target_properties(rse-model PROPERTIES OUTPUT_NAME ${RSE_MODEL_NAME}) + # Link externals libraries to the linker if(MSVC) # msvc does not append 'lib' - do it here to have consistent name set_target_properties(rse-model PROPERTIES IMPORT_PREFIX "lib") - target_link_libraries(rse-model PRIVATE ${GLEW_LIBRARIES} rsp-model-lib) + target_link_libraries(rse-model PRIVATE rsp-model-libstatic ${GLEW_LIBRARIES}) else() - target_link_libraries(rse-model PRIVATE ${GLEW_LIBRARIES} m rsp-model-lib) + target_link_libraries(rse-model PRIVATE rsp-model-libstatic ${GLEW_LIBRARIES} m) endif() diff --git a/RSEModel/config.h b/RSEModel/config.h deleted file mode 100644 index bc0d1b1..0000000 --- a/RSEModel/config.h +++ /dev/null @@ -1 +0,0 @@ -#define VERSION "1.0.0" diff --git a/RSEModel/config.h.in b/RSEModel/config.h.in deleted file mode 100644 index 32f49cf..0000000 --- a/RSEModel/config.h.in +++ /dev/null @@ -1 +0,0 @@ -#define VERSION "@PROJECT_VERSION@" diff --git a/RSEModel/Model-Extractor.c b/RSEModel/src/Model-Extractor.c similarity index 84% rename from RSEModel/Model-Extractor.c rename to RSEModel/src/Model-Extractor.c index 06894f6..4dcdd18 100644 --- a/RSEModel/Model-Extractor.c +++ b/RSEModel/src/Model-Extractor.c @@ -15,11 +15,10 @@ #include #include #endif -#include -#include -#include #include "config.h" #include "options.h" +#include +#include #include "obj_exporter.h" @@ -31,7 +30,7 @@ static unsigned int mainProcess(int args_cnt, char* args_value[], T_PROG_OPTIONS* opt_ptr); static void createSubDir(char *dirName); static unsigned char checkInputArgs(T_PROG_OPTIONS* opt_ptr, int p_arg_nbr, char* p_args[]); -static void cleanUpMemory(T_HOB* hobStruct); +static void cleanUpMemory(T_RSPMODEL_HOB* hobStruct); static void dispHelp(); @@ -43,19 +42,19 @@ int main(int argc, char *argv[]) { unsigned char p; // Hello world! - printf("\n*** RogueSquadron Extractor (RSE) - MODEL module - v%s ***\n", VERSION); + printf("\n*** RogueSquadron Extractor (RSE) - MODEL module - v%s ***\n", PRG_VERSION); // Check for arguments if (argc < 2) { printf("\n[ERR] No input file/commands specified!\n"); dispHelp(); - return ERROR_ARGS_NULL; + return RSPLIB_ERROR_ARGS_NULL; } // Create options for programs according to user's arguments. p = checkInputArgs(&_opts, argc, argv); - if ( p == ERROR_GENERIC ) return NO_ERROR; - else if ( p != NO_ERROR ) return p; + if ( p == RSPLIB_ERROR_GENERIC ) return RSPLIB_SUCCESS; + else if ( p != RSPLIB_SUCCESS ) return p; return mainProcess(argc, argv, &_opts); } @@ -67,26 +66,26 @@ int main(int argc, char *argv[]) { static unsigned int mainProcess(int args_cnt, char* args_value[], T_PROG_OPTIONS* p_opts) { unsigned short file_index; - T_HOB* hobStruct = NULL; + T_RSPMODEL_HOB* hobStruct = NULL; int i; // Manage multiple inputs files for ( file_index = p_opts->input_files_cnt; file_index < args_cnt; file_index++) { printf("\n=============================================\n[INFO] - Parsing file: %s ...\n", args_value[file_index]); - hobStruct = calloc(1, sizeof(T_HOB)); + hobStruct = calloc(1, sizeof(T_RSPMODEL_HOB)); // Parse data from HOB file and put in T_HOB structure. - if (RSP_ModelLib_ParseHOBFile(args_value[file_index], hobStruct, p_opts) != NO_ERROR) { + if (RSPModel_processHOBFile(hobStruct, args_value[file_index]) != RSPLIB_SUCCESS) { printf("[ERR] Failed to parse datas from %s\n", args_value[file_index]); free(hobStruct); - return ERROR_PROCESS; + return RSPLIB_ERROR_PROCESS; } if (hobStruct->obj_count > 0) { if (p_opts->output_dir) createSubDir(args_value[file_index]); for ( i = 0; i < hobStruct->obj_count; i++ ) { - if (exportOBJModel(&(hobStruct->objects[i]), args_value[file_index], p_opts) != NO_ERROR) + if (exportOBJModel(&(hobStruct->objects[i]), args_value[file_index], p_opts) != RSPLIB_SUCCESS) printf("[ERR] Failed to export %s object in OBJ format!\n", hobStruct->objects[i].name); else printf("[INFO] Successfully exported %s object in OBJ format.\n", hobStruct->objects[i].name); @@ -96,7 +95,7 @@ static unsigned int mainProcess(int args_cnt, char* args_value[], T_PROG_OPTIONS cleanUpMemory(hobStruct); - return NO_ERROR; + return RSPLIB_SUCCESS; } static unsigned char checkInputArgs(T_PROG_OPTIONS* opt_ptr, int p_arg_nbr, char* p_args[]) { @@ -114,7 +113,7 @@ static unsigned char checkInputArgs(T_PROG_OPTIONS* opt_ptr, int p_arg_nbr, char if (p_args[i][0] != '-') break; if (strcmp(p_args[i], "-h") == 0) { dispHelp(); - return ERROR_GENERIC; + return RSPLIB_ERROR_GENERIC; } else if (strcmp(p_args[i], "-v") == 0) { opt_ptr->verbose_mode = 1; printf("[OPTN] Verbose enabled.\n"); @@ -130,7 +129,7 @@ static unsigned char checkInputArgs(T_PROG_OPTIONS* opt_ptr, int p_arg_nbr, char } else if (strcmp(p_args[i], "-no-subdir") == 0) { opt_ptr->output_dir = 0; printf("[OPTN] Export to current directory.\n"); - } else if (strcmp(p_args[i], "-mtl") == 0) { + } else if (strcmp(p_args[i], "-no-mtl") == 0) { opt_ptr->export_mtl = 0; printf("[OPTN] No materials datas.\n"); } else { @@ -139,10 +138,10 @@ static unsigned char checkInputArgs(T_PROG_OPTIONS* opt_ptr, int p_arg_nbr, char } opt_ptr->input_files_cnt = i; - return NO_ERROR; + return RSPLIB_SUCCESS; } - return ERROR_ARGS_NULL; + return RSPLIB_ERROR_ARGS_NULL; } static void createSubDir(char *dirName) { @@ -158,7 +157,7 @@ static void createSubDir(char *dirName) { #endif } -static void cleanUpMemory(T_HOB* hobStruct) { +static void cleanUpMemory(T_RSPMODEL_HOB* hobStruct) { int i,j; for ( i=0; iobj_count; i++ ) { @@ -182,6 +181,6 @@ static void dispHelp() { printf(" -no-subdir Export models inside current folder\n"); printf(" -no-mtl Disable materials datas export with model\n"); printf("\n"); - printf("Usage: RSE-Model_%s [options] \n", VERSION); + printf("Usage: RSE-Model_%s [options] \n", PRG_VERSION); printf("\n"); } diff --git a/RSEModel/obj_exporter.c b/RSEModel/src/obj_exporter.c similarity index 96% rename from RSEModel/obj_exporter.c rename to RSEModel/src/obj_exporter.c index 94faac0..f2464a6 100644 --- a/RSEModel/obj_exporter.c +++ b/RSEModel/src/obj_exporter.c @@ -9,16 +9,16 @@ #include #include #include -#include -#include #include "options.h" +#include +#include #include "rlk/obj.h" #include "obj_exporter.h" static void mtlPathPatch(const char* out_file, const char* obj_name) ; -unsigned char exportOBJModel(T_HOB_OBJECT* hob_objects, const char *out_path, T_PROG_OPTIONS* p_opts) { +unsigned char exportOBJModel(T_RSPMODEL_OBJECT* hob_objects, const char *out_path, T_PROG_OPTIONS* p_opts) { char objExport_path[128]; char mtlExport_path[128]; obj* objConstruct = NULL; @@ -29,7 +29,7 @@ unsigned char exportOBJModel(T_HOB_OBJECT* hob_objects, const char *out_path, T_ int indicesBuff[3] = {0}; if (hob_objects == NULL || out_path == NULL) - return ERROR_ARGS_NULL; + return RSPLIB_ERROR_ARGS_NULL; if (p_opts->output_dir) { strcpy(objExport_path, out_path); diff --git a/RSEModel/obj_exporter.h b/RSEModel/src/obj_exporter.h similarity index 76% rename from RSEModel/obj_exporter.h rename to RSEModel/src/obj_exporter.h index d0f7b30..df1ec34 100644 --- a/RSEModel/obj_exporter.h +++ b/RSEModel/src/obj_exporter.h @@ -16,6 +16,6 @@ typedef struct t_material { unsigned int gl_tex_id; } T_MATERIAL; -unsigned char exportOBJModel(T_HOB_OBJECT* hob_objects, const char *out_path, T_PROG_OPTIONS* p_opts); +unsigned char exportOBJModel(T_RSPMODEL_OBJECT* hob_objects, const char *out_path, T_PROG_OPTIONS* p_opts); #endif /* SRC_OBJ_EXPORTER_H_ */ diff --git a/RSEModel/options.h b/RSEModel/src/options.h similarity index 100% rename from RSEModel/options.h rename to RSEModel/src/options.h diff --git a/RSEModel/rlk b/RSEModel/src/rlk similarity index 100% rename from RSEModel/rlk rename to RSEModel/src/rlk diff --git a/RSPModelLib/CMakeLists.txt b/RSPModelLib/CMakeLists.txt index fbe24d2..52fd59e 100644 --- a/RSPModelLib/CMakeLists.txt +++ b/RSPModelLib/CMakeLists.txt @@ -14,25 +14,52 @@ endif() include(CheckIncludeFile) include(CheckCSourceCompiles) -# Push compile infos to source -configure_file(${CMAKE_CURRENT_SOURCE_DIR}/src/config.h.in ${CMAKE_CURRENT_SOURCE_DIR}/src/config.h @ONLY) - # Define src/headers files -FILE(GLOB_RECURSE RSP_MOD_SOURCES ./src/*.c) -SOURCE_GROUP("Source Files" FILES ${RSP_MOD_SOURCES}) +file(GLOB_RECURSE RSP_MOD_SOURCES ./src/*.c) +source_group("Source Files" FILES ${RSP_MOD_SOURCES}) +file(GLOB RSP_PUBLIC_HRDS ./include/*.h) +set(RSP_PUBLIC_HRDS ${RSP_PUBLIC_HRDS} PARENT_SCOPE) # Building instructions for RSE-Model if(DEFINED ENV{CI}) set(CMAKE_BUILD_TYPE RELEASE) endif() -add_library(rsp-model-lib ${RSP_MOD_SOURCES}) + + +# Declare the shared library instance +add_library(rsp-model-lib SHARED ${RSP_MOD_SOURCES}) set_property(TARGET rsp-model-lib PROPERTY C_STANDARD 90) + target_include_directories(rsp-model-lib PUBLIC ${CMAKE_CURRENT_SOURCE_DIR}/include) + set_target_properties(rsp-model-lib PROPERTIES OUTPUT_NAME ${RSP_MODEL_LIB_NAME}) -# Link externals libraries to the linker +set_target_properties(rsp-model-lib PROPERTIES DEFINE_SYMBOL RSPMODEL_DLL) + if(MSVC) # msvc does not append 'lib' - do it here to have consistent name set_target_properties(rsp-model-lib PROPERTIES PREFIX "lib") + set_target_properties(rsp-model-lib PROPERTIES IMPORT_PREFIX "lib") +endif() + + +# Declare the static library instance +add_library(rsp-model-libstatic STATIC ${RSP_MOD_SOURCES}) +set_property(TARGET rsp-model-libstatic PROPERTY C_STANDARD 90) + +target_include_directories(rsp-model-libstatic PUBLIC ${CMAKE_CURRENT_SOURCE_DIR}/include) + +if(NOT MSVC) + set_target_properties(rsp-model-libstatic PROPERTIES OUTPUT_NAME "${RSP_MODEL_LIB_NAME}") + set_target_properties(rsp-model-libstatic PROPERTIES CLEAN_DIRECT_OUTPUT 1) +else() + set_target_properties(rsp-model-libstatic PROPERTIES OUTPUT_NAME "${RSP_MODEL_LIB_NAME}_static") + set_target_properties(rsp-model-libstatic PROPERTIES CLEAN_DIRECT_OUTPUT 1) +endif() + +if(MSVC) + # msvc does not append 'lib' - do it here to have consistent name + set_target_properties(rsp-model-libstatic PROPERTIES PREFIX "lib") + set_target_properties(rsp-model-libstatic PROPERTIES IMPORT_PREFIX "lib") endif() diff --git a/RSPModelLib/include/RSPModel.h b/RSPModelLib/include/RSPModel.h index 70f81c5..dd0cac9 100644 --- a/RSPModelLib/include/RSPModel.h +++ b/RSPModelLib/include/RSPModel.h @@ -13,6 +13,30 @@ #ifndef RSPMODEL_H_ #define RSPMODEL_H_ + +#if defined(RSPMODEL_SHARED) || defined(RSPMODEL_DLL) +# if defined(_MSC_VER) +# define RSPMODEL_ABI_EXPORT __declspec(dllexport) +# define RSPMODEL_ABI_IMPORT __declspec(dllimport) +# elif __GNUC__ >= 4 +# define RSPMODEL_ABI_EXPORT __attribute__ ((visibility("default"))) +# define RSPMODEL_ABI_IMPORT __attribute__ ((visibility("default"))) +# else +# define RSPMODEL_ABI_EXPORT +# define RSPMODEL_ABI_IMPORT +# endif +# if defined(WINDOWS) || defined(WIN32) +# ifdef RSPMODEL_DLL +# define RSPMODEL_EXTERN extern RSPMODEL_ABI_EXPORT +# else +# define RSPMODEL_EXTERN extern RSPMODEL_ABI_IMPORT +# endif +# endif +#else +# define RSPMODEL_EXTERN extern +#endif + + #ifdef __cplusplus extern "C" { #endif @@ -25,7 +49,7 @@ extern "C" { * @brief Get the current library version. * @return Char array of the version, escape char included. */ -char* RSPModel_getVersion( void ); +RSPMODEL_EXTERN char* RSPModel_getVersion( void ); /** * @brief Run model parser for the specified file in file system. @@ -37,7 +61,7 @@ char* RSPModel_getVersion( void ); * * @return Error status, return RSPLIB_SUCCESS in nominal case. */ -unsigned short RSPModel_processHOBFileMemory( T_RSPMODEL_HOB* hob, const char* const filePath ); +RSPMODEL_EXTERN unsigned short RSPModel_processHOBFile( T_RSPMODEL_HOB* hob, const char* const filePath ); /** * @brief Run model parser for the specified file in memory. @@ -51,7 +75,7 @@ unsigned short RSPModel_processHOBFileMemory( T_RSPMODEL_HOB* hob, const char* c * * @return Error status, return RSPLIB_SUCCESS in nominal case. */ -unsigned short RSPModel_processHOBFile( T_RSPMODEL_HOB* hob, const void* const memFilePtr, const long memFileSize ); +RSPMODEL_EXTERN unsigned short RSPModel_processHOBFileMemory( T_RSPMODEL_HOB* hob, const void* const memFilePtr, const long memFileSize ); /** * @brief Convert HOB's object datas to GL compatible format. @@ -62,7 +86,7 @@ unsigned short RSPModel_processHOBFile( T_RSPMODEL_HOB* hob, const void* const m * * @return Error status, return RSPLIB_SUCCESS in nominal case. */ -unsigned short RSPModel_objectToGL( const T_RSPMODEL_OBJECT* objStruct, void* glObj ); +RSPMODEL_EXTERN unsigned short RSPModel_objectToGL( const T_RSPMODEL_OBJECT* objStruct, void* glObj ); /** * @brief Convert HOB's object datas to Direct3D compatible format. @@ -73,7 +97,7 @@ unsigned short RSPModel_objectToGL( const T_RSPMODEL_OBJECT* objStruct, void* gl * * @return Error status, return RSPLIB_SUCCESS in nominal case. */ -unsigned short RSPModel_objectToD3D( const T_RSPMODEL_OBJECT* objStruct, void* D3DObj ); +RSPMODEL_EXTERN unsigned short RSPModel_objectToD3D( const T_RSPMODEL_OBJECT* objStruct, void* D3DObj ); #ifdef __cplusplus } diff --git a/RSPModelLib/src/RSPModel.c b/RSPModelLib/src/RSPModel.c index 2dc0263..ec9e26a 100644 --- a/RSPModelLib/src/RSPModel.c +++ b/RSPModelLib/src/RSPModel.c @@ -7,21 +7,34 @@ * */ +#include #include #include "config.h" #include "options.h" #include "RSPModel_errordefs.h" +#include "hob_parser.h" #include "RSPModel.h" + char* RSPModel_getVersion( void ) { return PRG_VERSION; } -unsigned short RSPModel_processHOBFileMemory( T_RSPMODEL_HOB* hob, const char* const filePath ) { +unsigned short RSPModel_processHOBFile( T_RSPMODEL_HOB* hob, const char* const filePath ) { + if ( hob == NULL || filePath == NULL ) return RSPLIB_ERROR_ARGS_NULL; + + T_PROG_OPTIONS canard; + canard.god_mode = 1; + RSP_ModelLib_ParseHOBFile(filePath, hob, &canard); + return RSPLIB_SUCCESS; } -unsigned short RSPModel_processHOBFile( T_RSPMODEL_HOB* hob, const void* const memFilePtr, const long memFileSize ) { +unsigned short RSPModel_processHOBFileMemory( T_RSPMODEL_HOB* hob, const void* const memFilePtr, const long memFileSize ) { + if ( hob == NULL || memFilePtr == NULL ) return RSPLIB_ERROR_ARGS_NULL; + + + return RSPLIB_SUCCESS; } diff --git a/conanfile.txt b/conanfile.txt index 6c8fd0c..9052a4d 100644 --- a/conanfile.txt +++ b/conanfile.txt @@ -9,4 +9,4 @@ cmake_find_package glew:shared=True [imports] -bin, *.dll -> . \ No newline at end of file +bin, *.dll -> ./bin \ No newline at end of file diff --git a/config.h.in b/config.h.in new file mode 100644 index 0000000..3f2e0c4 --- /dev/null +++ b/config.h.in @@ -0,0 +1,6 @@ +#ifndef CONFIG_H_ +#define CONFIG_H_ + +#define PRG_VERSION "@PROJECT_VERSION@" + +#endif /* CONFIG_H_ */ -- 2.39.5 From 78147d3d10c0276514ebd8cd5129aca223d39959 Mon Sep 17 00:00:00 2001 From: JackCarterSmith Date: Fri, 12 Aug 2022 22:44:14 +0200 Subject: [PATCH 05/15] Optimized lib type switching --- CMakeLists.txt | 10 +++++++++- RSPModelLib/CMakeLists.txt | 20 +++++++++++--------- RSPModelLib/include/RSPModel.h | 31 +++++++++++++++++-------------- RSPModelLib/src/RSPModel.c | 10 +++++----- RSPModelLib/src/options.h | 2 ++ 5 files changed, 44 insertions(+), 29 deletions(-) diff --git a/CMakeLists.txt b/CMakeLists.txt index 3c268bb..4133d60 100644 --- a/CMakeLists.txt +++ b/CMakeLists.txt @@ -25,6 +25,9 @@ else() # Standalone project mode, should not be used for release. endif() set(RSP_MODEL_LIB_NAME RSPModel${PROJECT_VERSION_MAJOR}${PROJECT_VERSION_MINOR}) +# Compilation option +option(RSPMODEL_SHARED "Build shared lib" ON) + # Push compile infos to source configure_file(${CMAKE_CURRENT_SOURCE_DIR}/config.h.in ${CMAKE_CURRENT_SOURCE_DIR}/RSPModelLib/src/config.h @ONLY) configure_file(${CMAKE_CURRENT_SOURCE_DIR}/config.h.in ${CMAKE_CURRENT_SOURCE_DIR}/RSEModel/src/config.h @ONLY) @@ -57,7 +60,12 @@ add_subdirectory(RSEModel) set(INSTALL_BIN_DIR "${CMAKE_INSTALL_PREFIX}/bin" CACHE PATH "Installation directory for executables") set(INSTALL_LIB_DIR "${CMAKE_INSTALL_PREFIX}/lib" CACHE PATH "Installation directory for libraries") set(INSTALL_INC_DIR "${CMAKE_INSTALL_PREFIX}/include" CACHE PATH "Installation directory for headers") -install(TARGETS rse-model rsp-model-lib rsp-model-libstatic +if(RSPMODEL_SHARED) + set(RSE_MODEL_TARGETS_LIST rse-model rsp-model-lib rsp-model-libstatic) +else() + set(RSE_MODEL_TARGETS_LIST rse-model rsp-model-libstatic) +endif() +install(TARGETS ${RSE_MODEL_TARGETS_LIST} RUNTIME DESTINATION ${INSTALL_BIN_DIR} LIBRARY DESTINATION ${INSTALL_LIB_DIR} ARCHIVE DESTINATION ${INSTALL_LIB_DIR} diff --git a/RSPModelLib/CMakeLists.txt b/RSPModelLib/CMakeLists.txt index 52fd59e..9f0beaf 100644 --- a/RSPModelLib/CMakeLists.txt +++ b/RSPModelLib/CMakeLists.txt @@ -29,18 +29,20 @@ endif() # Declare the shared library instance -add_library(rsp-model-lib SHARED ${RSP_MOD_SOURCES}) -set_property(TARGET rsp-model-lib PROPERTY C_STANDARD 90) +if(RSPMODEL_SHARED) + add_library(rsp-model-lib SHARED ${RSP_MOD_SOURCES}) + set_property(TARGET rsp-model-lib PROPERTY C_STANDARD 90) -target_include_directories(rsp-model-lib PUBLIC ${CMAKE_CURRENT_SOURCE_DIR}/include) + target_include_directories(rsp-model-lib PUBLIC ${CMAKE_CURRENT_SOURCE_DIR}/include) -set_target_properties(rsp-model-lib PROPERTIES OUTPUT_NAME ${RSP_MODEL_LIB_NAME}) -set_target_properties(rsp-model-lib PROPERTIES DEFINE_SYMBOL RSPMODEL_DLL) + set_target_properties(rsp-model-lib PROPERTIES OUTPUT_NAME ${RSP_MODEL_LIB_NAME}) + set_target_properties(rsp-model-lib PROPERTIES DEFINE_SYMBOL RSPMODEL_DLL) -if(MSVC) - # msvc does not append 'lib' - do it here to have consistent name - set_target_properties(rsp-model-lib PROPERTIES PREFIX "lib") - set_target_properties(rsp-model-lib PROPERTIES IMPORT_PREFIX "lib") + if(MSVC) + # msvc does not append 'lib' - do it here to have consistent name + set_target_properties(rsp-model-lib PROPERTIES PREFIX "lib") + set_target_properties(rsp-model-lib PROPERTIES IMPORT_PREFIX "lib") + endif() endif() diff --git a/RSPModelLib/include/RSPModel.h b/RSPModelLib/include/RSPModel.h index dd0cac9..001d25a 100644 --- a/RSPModelLib/include/RSPModel.h +++ b/RSPModelLib/include/RSPModel.h @@ -14,25 +14,28 @@ #define RSPMODEL_H_ -#if defined(RSPMODEL_SHARED) || defined(RSPMODEL_DLL) -# if defined(_MSC_VER) -# define RSPMODEL_ABI_EXPORT __declspec(dllexport) -# define RSPMODEL_ABI_IMPORT __declspec(dllimport) -# elif __GNUC__ >= 4 -# define RSPMODEL_ABI_EXPORT __attribute__ ((visibility("default"))) -# define RSPMODEL_ABI_IMPORT __attribute__ ((visibility("default"))) -# else -# define RSPMODEL_ABI_EXPORT -# define RSPMODEL_ABI_IMPORT -# endif -# if defined(WINDOWS) || defined(WIN32) -# ifdef RSPMODEL_DLL +#if defined(_MSC_VER) +# define RSPMODEL_ABI_EXPORT __declspec(dllexport) +# define RSPMODEL_ABI_IMPORT __declspec(dllimport) +#elif __GNUC__ >= 4 +# define RSPMODEL_ABI_EXPORT __attribute__ ((visibility("default"))) +# define RSPMODEL_ABI_IMPORT __attribute__ ((visibility("default"))) +#else +# define RSPMODEL_ABI_EXPORT +# define RSPMODEL_ABI_IMPORT +#endif + +#if defined(RSPMODEL_DLL) +# if defined(WIN32) +# if defined(RSPMODEL_DLLBUILD) # define RSPMODEL_EXTERN extern RSPMODEL_ABI_EXPORT # else # define RSPMODEL_EXTERN extern RSPMODEL_ABI_IMPORT # endif # endif -#else +#endif + +#ifndef RSPMODEL_EXTERN # define RSPMODEL_EXTERN extern #endif diff --git a/RSPModelLib/src/RSPModel.c b/RSPModelLib/src/RSPModel.c index ec9e26a..4ddadaf 100644 --- a/RSPModelLib/src/RSPModel.c +++ b/RSPModelLib/src/RSPModel.c @@ -1,9 +1,9 @@ /** - * \file RSPModel.c - * \date 11/08/2022 - * \author JackCarterSmith - * \copyright GPL-v3.0 - * \brief HOB model parser and export to Waveform OBJ format. + * @file RSPModel.c + * @date 11/08/2022 + * @author JackCarterSmith + * @copyright GPL-v3.0 + * @brief HOB model parser and export to Waveform OBJ format. * */ diff --git a/RSPModelLib/src/options.h b/RSPModelLib/src/options.h index d731673..1168992 100644 --- a/RSPModelLib/src/options.h +++ b/RSPModelLib/src/options.h @@ -9,6 +9,8 @@ #ifndef OPTIONS_H_ #define OPTIONS_H_ +#define RSPMODEL_DLLBUILD + /// Options structure typedef union u_prog_options { struct { -- 2.39.5 From a6e3e20bcea83d5758a5bfd6a6bf4988812eb086 Mon Sep 17 00:00:00 2001 From: JackCarterSmith Date: Sat, 13 Aug 2022 13:56:20 +0200 Subject: [PATCH 06/15] CI integration reviewed --- .gitignore | 3 +- CMakeLists.txt | 3 +- Jenkinsfile | 24 ++++++------ LICENSE-glew.txt | 73 +++++++++++++++++++++++++++++++++++++ RSPModelLib/src/config.h | 6 --- RSPModelLib/src/config.h.in | 6 --- 6 files changed, 89 insertions(+), 26 deletions(-) create mode 100644 LICENSE-glew.txt delete mode 100644 RSPModelLib/src/config.h delete mode 100644 RSPModelLib/src/config.h.in diff --git a/.gitignore b/.gitignore index cd6b464..f31e982 100644 --- a/.gitignore +++ b/.gitignore @@ -15,7 +15,8 @@ # Precompiled Headers *.gch *.pch -config.h +RSPModelLib/src/config.h +RSEModel/src/config.h # Libraries *.lib diff --git a/CMakeLists.txt b/CMakeLists.txt index 4133d60..7429aab 100644 --- a/CMakeLists.txt +++ b/CMakeLists.txt @@ -20,10 +20,11 @@ if(DEFINED ENV{CI}) # Jenkins CI integration mode project(rse-model VERSION $ENV{CI_VERSION}.$ENV{CI_BUILD_NUMBER} DESCRIPTION "RogueSquadron Extractor - Model" LANGUAGES C) set(RSE_MODEL_NAME $ENV{CI_OUTPUT_NAME}) else() # Standalone project mode, should not be used for release. - project(rse-model VERSION 1.0.0 DESCRIPTION "RogueSquadron Extractor - Model" LANGUAGES C) + project(rse-model VERSION 2.0.0 DESCRIPTION "RogueSquadron Extractor - Model" LANGUAGES C) set(RSE_MODEL_NAME RSEModel) endif() set(RSP_MODEL_LIB_NAME RSPModel${PROJECT_VERSION_MAJOR}${PROJECT_VERSION_MINOR}) +set(CMAKE_C_FLAGS "${CMAKE_C_FLAGS} -Wall") # Compilation option option(RSPMODEL_SHARED "Build shared lib" ON) diff --git a/Jenkinsfile b/Jenkinsfile index 55c6b33..eec6465 100644 --- a/Jenkinsfile +++ b/Jenkinsfile @@ -4,15 +4,15 @@ pipeline { skipDefaultCheckout(true) } environment { - CI_OUTPUT_NAME = "RSE_Model" - CI_VERSION = "1.0.1" + CI_OUTPUT_NAME = "RSEModel" + CI_VERSION = "2.0.0" CI_BUILD_NUMBER = "$BUILD_NUMBER" } stages { stage('Prepare') { steps { cleanWs() - rtConanClient(id: "conan", userHome: "/home/jackcartersmith") + rtConanClient(id: "conan") } } stage('Build') { @@ -23,7 +23,7 @@ pipeline { checkout([$class: 'GitSCM', branches: [[name: '**']], browser: [$class: 'GiteaBrowser', repoUrl: 'https://git.jcsmith.fr/JCS-Prod/RSE-Model'], extensions: [], userRemoteConfigs: [[credentialsId: 'jenkins-ssh', url: 'ssh://git@git.jcsmith.fr:2322/JCS-Prod/RSE-Model.git']]]) sh 'git submodule update --init --recursive' dir("build") { - rtConanRun(clientId: "conan", command: "install .. --build missing") + rtConanRun(clientId: "conan", command: "install .. --build=missing") } cmakeBuild buildDir: 'build', installation: 'latest', steps: [[args: 'all']] } @@ -33,7 +33,7 @@ pipeline { checkout([$class: 'GitSCM', branches: [[name: '**']], browser: [$class: 'GiteaBrowser', repoUrl: 'https://git.jcsmith.fr/JCS-Prod/RSE-Model'], extensions: [], userRemoteConfigs: [[credentialsId: 'jenkins-ssh', url: 'ssh://git@git.jcsmith.fr:2322/JCS-Prod/RSE-Model.git']]]) sh 'git submodule update --init --recursive' dir("build") { - rtConanRun(clientId: "conan", command: "install .. --profile windows --build missing") + rtConanRun(clientId: "conan", command: "install .. --profile=windows --build=missing") } cmakeBuild buildDir: 'build', cmakeArgs: '-DGNU_HOST=x86_64-w64-mingw32 -DCMAKE_TOOLCHAIN_FILE=../mingw_cross_toolchain.cmake', installation: 'latest', steps: [[args: 'all']] } @@ -44,15 +44,15 @@ pipeline { stage('Deploy') { steps { dir("zip_linux") { - sh 'cp ../linux/build/${CI_OUTPUT_NAME}-${CI_VERSION}.${BUILD_NUMBER}* .' + sh 'cp -R ../linux/build/bin ../linux/build/lib ../linux/include .' } dir("zip_win") { - sh 'cp ../windows/build/${CI_OUTPUT_NAME}-${CI_VERSION}.${BUILD_NUMBER}* ../windows/build/*.dll .' + sh 'cp -R ../windows/build/bin ../windows/build/lib ../windows/include .' } - zip archive: false, dir: 'zip_linux', exclude: '', glob: '', zipFile: 'x64.zip' - sh 'mv x64.zip ${CI_OUTPUT_NAME}-${CI_VERSION}.${BUILD_NUMBER}_x64.zip' + zip archive: false, dir: 'zip_linux', exclude: '', glob: '', zipFile: 'linux_x64.zip' + sh 'mv linux_x64.zip ${CI_OUTPUT_NAME}_${CI_VERSION}.${BUILD_NUMBER}_Linux_x86_64.zip' zip archive: false, dir: 'zip_win', exclude: '', glob: '', zipFile: 'mingw64.zip' - sh 'mv mingw64.zip ${CI_OUTPUT_NAME}-${CI_VERSION}.${BUILD_NUMBER}_mingw64.zip' + sh 'mv mingw64.zip ${CI_OUTPUT_NAME}_${CI_VERSION}.${BUILD_NUMBER}_mingw64.zip' archiveArtifacts(artifacts: '*.zip') fingerprint(targets: '*.zip') } @@ -60,8 +60,8 @@ pipeline { stage('Sign') { steps { sh 'ls -l' - sh 'gpg --batch --detach-sign -o ${CI_OUTPUT_NAME}-${CI_VERSION}.${BUILD_NUMBER}_x64.zip.gpg ${CI_OUTPUT_NAME}-${CI_VERSION}.${BUILD_NUMBER}_x64.zip' - sh 'gpg --batch --detach-sign -o ${CI_OUTPUT_NAME}-${CI_VERSION}.${BUILD_NUMBER}_mingw64.zip.gpg ${CI_OUTPUT_NAME}-${CI_VERSION}.${BUILD_NUMBER}_mingw64.zip' + sh 'gpg --batch --detach-sign -o ${CI_OUTPUT_NAME}_${CI_VERSION}.${BUILD_NUMBER}_Linux_x86_64.zip.gpg ${CI_OUTPUT_NAME}_${CI_VERSION}.${BUILD_NUMBER}_x64.zip' + sh 'gpg --batch --detach-sign -o ${CI_OUTPUT_NAME}_${CI_VERSION}.${BUILD_NUMBER}_mingw64.zip.gpg ${CI_OUTPUT_NAME}_${CI_VERSION}.${BUILD_NUMBER}_mingw64.zip' archiveArtifacts(artifacts: '*.gpg') fingerprint(targets: '*.gpg') } diff --git a/LICENSE-glew.txt b/LICENSE-glew.txt new file mode 100644 index 0000000..f707804 --- /dev/null +++ b/LICENSE-glew.txt @@ -0,0 +1,73 @@ +The OpenGL Extension Wrangler Library +Copyright (C) 2002-2007, Milan Ikits +Copyright (C) 2002-2007, Marcelo E. Magallon +Copyright (C) 2002, Lev Povalahev +All rights reserved. + +Redistribution and use in source and binary forms, with or without +modification, are permitted provided that the following conditions are met: + +* Redistributions of source code must retain the above copyright notice, + this list of conditions and the following disclaimer. +* Redistributions in binary form must reproduce the above copyright notice, + this list of conditions and the following disclaimer in the documentation + and/or other materials provided with the distribution. +* The name of the author may be used to endorse or promote products + derived from this software without specific prior written permission. + +THIS SOFTWARE IS PROVIDED BY THE COPYRIGHT HOLDERS AND CONTRIBUTORS "AS IS" +AND ANY EXPRESS OR IMPLIED WARRANTIES, INCLUDING, BUT NOT LIMITED TO, THE +IMPLIED WARRANTIES OF MERCHANTABILITY AND FITNESS FOR A PARTICULAR PURPOSE +ARE DISCLAIMED. IN NO EVENT SHALL THE COPYRIGHT OWNER OR CONTRIBUTORS BE +LIABLE FOR ANY DIRECT, INDIRECT, INCIDENTAL, SPECIAL, EXEMPLARY, OR +CONSEQUENTIAL DAMAGES (INCLUDING, BUT NOT LIMITED TO, PROCUREMENT OF +SUBSTITUTE GOODS OR SERVICES; LOSS OF USE, DATA, OR PROFITS; OR BUSINESS +INTERRUPTION) HOWEVER CAUSED AND ON ANY THEORY OF LIABILITY, WHETHER IN +CONTRACT, STRICT LIABILITY, OR TORT (INCLUDING NEGLIGENCE OR OTHERWISE) +ARISING IN ANY WAY OUT OF THE USE OF THIS SOFTWARE, EVEN IF ADVISED OF +THE POSSIBILITY OF SUCH DAMAGE. + + +Mesa 3-D graphics library +Version: 7.0 + +Copyright (C) 1999-2007 Brian Paul All Rights Reserved. + +Permission is hereby granted, free of charge, to any person obtaining a +copy of this software and associated documentation files (the "Software"), +to deal in the Software without restriction, including without limitation +the rights to use, copy, modify, merge, publish, distribute, sublicense, +and/or sell copies of the Software, and to permit persons to whom the +Software is furnished to do so, subject to the following conditions: + +The above copyright notice and this permission notice shall be included +in all copies or substantial portions of the Software. + +THE SOFTWARE IS PROVIDED "AS IS", WITHOUT WARRANTY OF ANY KIND, EXPRESS +OR IMPLIED, INCLUDING BUT NOT LIMITED TO THE WARRANTIES OF MERCHANTABILITY, +FITNESS FOR A PARTICULAR PURPOSE AND NONINFRINGEMENT. IN NO EVENT SHALL +BRIAN PAUL BE LIABLE FOR ANY CLAIM, DAMAGES OR OTHER LIABILITY, WHETHER IN +AN ACTION OF CONTRACT, TORT OR OTHERWISE, ARISING FROM, OUT OF OR IN +CONNECTION WITH THE SOFTWARE OR THE USE OR OTHER DEALINGS IN THE SOFTWARE. + + +Copyright (c) 2007 The Khronos Group Inc. + +Permission is hereby granted, free of charge, to any person obtaining a +copy of this software and/or associated documentation files (the +"Materials"), to deal in the Materials without restriction, including +without limitation the rights to use, copy, modify, merge, publish, +distribute, sublicense, and/or sell copies of the Materials, and to +permit persons to whom the Materials are furnished to do so, subject to +the following conditions: + +The above copyright notice and this permission notice shall be included +in all copies or substantial portions of the Materials. + +THE MATERIALS ARE PROVIDED "AS IS", WITHOUT WARRANTY OF ANY KIND, +EXPRESS OR IMPLIED, INCLUDING BUT NOT LIMITED TO THE WARRANTIES OF +MERCHANTABILITY, FITNESS FOR A PARTICULAR PURPOSE AND NONINFRINGEMENT. +IN NO EVENT SHALL THE AUTHORS OR COPYRIGHT HOLDERS BE LIABLE FOR ANY +CLAIM, DAMAGES OR OTHER LIABILITY, WHETHER IN AN ACTION OF CONTRACT, +TORT OR OTHERWISE, ARISING FROM, OUT OF OR IN CONNECTION WITH THE +MATERIALS OR THE USE OR OTHER DEALINGS IN THE MATERIALS. diff --git a/RSPModelLib/src/config.h b/RSPModelLib/src/config.h deleted file mode 100644 index 2a1d023..0000000 --- a/RSPModelLib/src/config.h +++ /dev/null @@ -1,6 +0,0 @@ -#ifndef CONFIG_H_ -#define CONFIG_H_ - -#define PRG_VERSION "1.0.0" - -#endif /* CONFIG_H_ */ diff --git a/RSPModelLib/src/config.h.in b/RSPModelLib/src/config.h.in deleted file mode 100644 index 3f2e0c4..0000000 --- a/RSPModelLib/src/config.h.in +++ /dev/null @@ -1,6 +0,0 @@ -#ifndef CONFIG_H_ -#define CONFIG_H_ - -#define PRG_VERSION "@PROJECT_VERSION@" - -#endif /* CONFIG_H_ */ -- 2.39.5 From 4a955f3bbbca226c29325e9240492709a339671b Mon Sep 17 00:00:00 2001 From: JackCarterSmith Date: Sat, 13 Aug 2022 15:18:02 +0200 Subject: [PATCH 07/15] Jenkins damn it path missing --- Jenkinsfile | 10 +++++----- 1 file changed, 5 insertions(+), 5 deletions(-) diff --git a/Jenkinsfile b/Jenkinsfile index eec6465..f2abc2d 100644 --- a/Jenkinsfile +++ b/Jenkinsfile @@ -12,7 +12,7 @@ pipeline { stage('Prepare') { steps { cleanWs() - rtConanClient(id: "conan") + rtConanClient(id: "conan", userHome: "/home/jackcartersmith") } } stage('Build') { @@ -35,7 +35,7 @@ pipeline { dir("build") { rtConanRun(clientId: "conan", command: "install .. --profile=windows --build=missing") } - cmakeBuild buildDir: 'build', cmakeArgs: '-DGNU_HOST=x86_64-w64-mingw32 -DCMAKE_TOOLCHAIN_FILE=../mingw_cross_toolchain.cmake', installation: 'latest', steps: [[args: 'all']] + cmakeBuild buildDir: 'build', cmakeArgs: '-DGNU_HOST=x86_64-w64-mingw32 -DCMAKE_TOOLCHAIN_FILE=../cmake/mingw_cross_toolchain.cmake', installation: 'latest', steps: [[args: 'all']] } } ) @@ -44,10 +44,10 @@ pipeline { stage('Deploy') { steps { dir("zip_linux") { - sh 'cp -R ../linux/build/bin ../linux/build/lib ../linux/include .' + sh 'cp -R ../linux/build/bin ../linux/build/lib ../linux/RSPModelLib/include .' } dir("zip_win") { - sh 'cp -R ../windows/build/bin ../windows/build/lib ../windows/include .' + sh 'cp -R ../windows/build/bin ../windows/build/lib ../windows/RSPModelLib/include .' } zip archive: false, dir: 'zip_linux', exclude: '', glob: '', zipFile: 'linux_x64.zip' sh 'mv linux_x64.zip ${CI_OUTPUT_NAME}_${CI_VERSION}.${BUILD_NUMBER}_Linux_x86_64.zip' @@ -60,7 +60,7 @@ pipeline { stage('Sign') { steps { sh 'ls -l' - sh 'gpg --batch --detach-sign -o ${CI_OUTPUT_NAME}_${CI_VERSION}.${BUILD_NUMBER}_Linux_x86_64.zip.gpg ${CI_OUTPUT_NAME}_${CI_VERSION}.${BUILD_NUMBER}_x64.zip' + sh 'gpg --batch --detach-sign -o ${CI_OUTPUT_NAME}_${CI_VERSION}.${BUILD_NUMBER}_Linux_x86_64.zip.gpg ${CI_OUTPUT_NAME}_${CI_VERSION}.${BUILD_NUMBER}_Linux_x86_64.zip' sh 'gpg --batch --detach-sign -o ${CI_OUTPUT_NAME}_${CI_VERSION}.${BUILD_NUMBER}_mingw64.zip.gpg ${CI_OUTPUT_NAME}_${CI_VERSION}.${BUILD_NUMBER}_mingw64.zip' archiveArtifacts(artifacts: '*.gpg') fingerprint(targets: '*.gpg') -- 2.39.5 From b72b2eba7102bf0934032feba13b4475497fd71a Mon Sep 17 00:00:00 2001 From: JackCarterSmith Date: Sat, 13 Aug 2022 15:47:46 +0200 Subject: [PATCH 08/15] Temporary remove MTL support --- RSEModel/src/Model-Extractor.c | 18 +++++++++--------- RSEModel/src/obj_exporter.c | 13 +++++++------ RSEModel/src/obj_exporter.h | 11 ++++++----- RSEModel/src/options.h | 11 ++++++----- RSPModelLib/include/RSPModel_errordefs.h | 10 +++++----- RSPModelLib/src/hob_parser.c | 11 ++++++----- RSPModelLib/src/hob_parser.h | 11 ++++++----- RSPModelLib/src/hob_struct.h | 10 +++++----- RSPModelLib/src/options.h | 11 ++++++----- 9 files changed, 56 insertions(+), 50 deletions(-) diff --git a/RSEModel/src/Model-Extractor.c b/RSEModel/src/Model-Extractor.c index 4dcdd18..24bbbf7 100644 --- a/RSEModel/src/Model-Extractor.c +++ b/RSEModel/src/Model-Extractor.c @@ -1,9 +1,10 @@ /** - * \file Model-Extractor.c - * \date 25/07/2022 - * \author JackCarterSmith - * \copyright GPL-v3.0 - * \brief HOB model parser and export to Waveform OBJ format. + * @file Model-Extractor.c + * @date 25/07/2022 + * @author JackCarterSmith + * @copyright GPL-v3.0 + * @brief HOB model parser and export to Waveform OBJ format. + * */ #include @@ -105,7 +106,6 @@ static unsigned char checkInputArgs(T_PROG_OPTIONS* opt_ptr, int p_arg_nbr, char // Set default options opt_ptr->raw = 0; opt_ptr->output_dir = 1; - opt_ptr->export_mtl = 1; if (p_arg_nbr > 1) { for ( i = 1; i < p_arg_nbr; i++) { @@ -129,9 +129,9 @@ static unsigned char checkInputArgs(T_PROG_OPTIONS* opt_ptr, int p_arg_nbr, char } else if (strcmp(p_args[i], "-no-subdir") == 0) { opt_ptr->output_dir = 0; printf("[OPTN] Export to current directory.\n"); - } else if (strcmp(p_args[i], "-no-mtl") == 0) { + } else if (strcmp(p_args[i], "-mtl") == 0) { opt_ptr->export_mtl = 0; - printf("[OPTN] No materials datas.\n"); + printf("[OPTN] Export materials datas.\n"); } else { printf("[ERR] Unknown option: %s\n", p_args[i]); } @@ -179,7 +179,7 @@ static void dispHelp() { printf("Options:\n -h Print this message\n"); printf(" -v -vv Activate verbose console output\n"); printf(" -no-subdir Export models inside current folder\n"); - printf(" -no-mtl Disable materials datas export with model\n"); + //printf(" -mtl Export materials datas with model\n"); printf("\n"); printf("Usage: RSE-Model_%s [options] \n", PRG_VERSION); printf("\n"); diff --git a/RSEModel/src/obj_exporter.c b/RSEModel/src/obj_exporter.c index f2464a6..b60256f 100644 --- a/RSEModel/src/obj_exporter.c +++ b/RSEModel/src/obj_exporter.c @@ -1,9 +1,10 @@ /** - * \file obj_exporter.c - * \date 27/07/2022 - * \author JackCarterSmith - * \copyright GPL-v3.0 - * \brief Export datas to Waveform OBJ format. + * @file obj_exporter.c + * @date 27/07/2022 + * @author JackCarterSmith + * @copyright GPL-v3.0 + * @brief Export datas to Waveform OBJ format. + * */ #include @@ -115,7 +116,7 @@ unsigned char exportOBJModel(T_RSPMODEL_OBJECT* hob_objects, const char *out_pat obj_delete(objConstruct); - return NO_ERROR; + return RSPLIB_SUCCESS; } static void mtlPathPatch(const char* out_file, const char* obj_name) { diff --git a/RSEModel/src/obj_exporter.h b/RSEModel/src/obj_exporter.h index df1ec34..035141e 100644 --- a/RSEModel/src/obj_exporter.h +++ b/RSEModel/src/obj_exporter.h @@ -1,9 +1,10 @@ /** - * \file obj_exporter.h - * \date 27/07/2022 - * \author JackCarterSmith - * \copyright GPL-v3.0 - * \brief Export datas to Waveform OBJ format. + * @file obj_exporter.h + * @date 27/07/2022 + * @author JackCarterSmith + * @copyright GPL-v3.0 + * @brief Export datas to Waveform OBJ format. + * */ #ifndef SRC_OBJ_EXPORTER_H_ diff --git a/RSEModel/src/options.h b/RSEModel/src/options.h index ec369ab..fd512b2 100644 --- a/RSEModel/src/options.h +++ b/RSEModel/src/options.h @@ -1,9 +1,10 @@ /** - * \file options.h - * \date 29/07/2022 - * \author JackCarterSmith - * \copyright GPL-v3.0 - * \brief Shared options structure definition and declaration. + * @file options.h + * @date 29/07/2022 + * @author JackCarterSmith + * @copyright GPL-v3.0 + * @brief Shared options structure definition and declaration. + * */ #ifndef OPTIONS_H_ diff --git a/RSPModelLib/include/RSPModel_errordefs.h b/RSPModelLib/include/RSPModel_errordefs.h index fa33c03..d707066 100644 --- a/RSPModelLib/include/RSPModel_errordefs.h +++ b/RSPModelLib/include/RSPModel_errordefs.h @@ -1,9 +1,9 @@ /** - * \file RSPModel_errordefs.h - * \date 26/07/2022 - * \author JackCarterSmith - * \copyright GPL-v3.0 - * \brief Errors type definition file. Used mostly by methods in this project. + * @file RSPModel_errordefs.h + * @date 26/07/2022 + * @author JackCarterSmith + * @copyright GPL-v3.0 + * @brief Errors type definition file. Used mostly by methods in this project. * */ diff --git a/RSPModelLib/src/hob_parser.c b/RSPModelLib/src/hob_parser.c index 7de9d42..c8f934e 100644 --- a/RSPModelLib/src/hob_parser.c +++ b/RSPModelLib/src/hob_parser.c @@ -1,9 +1,10 @@ /** - * \file hob_parser.c - * \date 26/07/2022 - * \author JackCarterSmith - * \copyright GPL-v3.0 - * \brief Decode HOB file structure. + * @file hob_parser.c + * @date 26/07/2022 + * @author JackCarterSmith + * @copyright GPL-v3.0 + * @brief Decode HOB file structure. + * */ #include diff --git a/RSPModelLib/src/hob_parser.h b/RSPModelLib/src/hob_parser.h index 32b350d..a2cb907 100644 --- a/RSPModelLib/src/hob_parser.h +++ b/RSPModelLib/src/hob_parser.h @@ -1,9 +1,10 @@ /** - * \file hob_parser.h - * \date 26/07/2022 - * \author JackCarterSmith - * \copyright GPL-v3.0 - * \brief Decode HOB file structure. + * @file hob_parser.h + * @date 26/07/2022 + * @author JackCarterSmith + * @copyright GPL-v3.0 + * @brief Decode HOB file structure. + * */ #include "options.h" diff --git a/RSPModelLib/src/hob_struct.h b/RSPModelLib/src/hob_struct.h index b374150..f90e5f6 100644 --- a/RSPModelLib/src/hob_struct.h +++ b/RSPModelLib/src/hob_struct.h @@ -1,9 +1,9 @@ /** - * \file hob_struct.h - * \date 26/07/2022 - * \author JackCarterSmith - * \copyright GPL-v3.0 - * \brief HOB file mapping definition. + * @file hob_struct.h + * @date 26/07/2022 + * @author JackCarterSmith + * @copyright GPL-v3.0 + * @brief HOB file mapping definition. * */ diff --git a/RSPModelLib/src/options.h b/RSPModelLib/src/options.h index 1168992..a88baae 100644 --- a/RSPModelLib/src/options.h +++ b/RSPModelLib/src/options.h @@ -1,9 +1,10 @@ /** - * \file options.h - * \date 29/07/2022 - * \author JackCarterSmith - * \copyright GPL-v3.0 - * \brief Shared options structure definition and declaration. + * @file options.h + * @date 29/07/2022 + * @author JackCarterSmith + * @copyright GPL-v3.0 + * @brief Shared options structure definition and declaration. + * */ #ifndef OPTIONS_H_ -- 2.39.5 From 6d3beabb5e4b1871ce1924ae911812d2ae1e225d Mon Sep 17 00:00:00 2001 From: JackCarterSmith Date: Sat, 13 Aug 2022 16:48:36 +0200 Subject: [PATCH 09/15] Implicit stdlib declaration --- RSPModelLib/include/RSPModel_errordefs.h | 2 ++ RSPModelLib/src/RSPModel.c | 1 + 2 files changed, 3 insertions(+) diff --git a/RSPModelLib/include/RSPModel_errordefs.h b/RSPModelLib/include/RSPModel_errordefs.h index d707066..6d71ca6 100644 --- a/RSPModelLib/include/RSPModel_errordefs.h +++ b/RSPModelLib/include/RSPModel_errordefs.h @@ -7,6 +7,8 @@ * */ +#include + #ifndef RSPMODELLIB_ERRORS_H_ #define RSPMODELLIB_ERRORS_H_ diff --git a/RSPModelLib/src/RSPModel.c b/RSPModelLib/src/RSPModel.c index 4ddadaf..b58ed14 100644 --- a/RSPModelLib/src/RSPModel.c +++ b/RSPModelLib/src/RSPModel.c @@ -7,6 +7,7 @@ * */ +#include #include #include #include "config.h" -- 2.39.5 From be31c972c43d1de9680421028e45cad60239545d Mon Sep 17 00:00:00 2001 From: JackCarterSmith Date: Thu, 18 Aug 2022 21:47:54 +0200 Subject: [PATCH 10/15] Deconstruct mega-parser in sub parts --- RSPModelLib/include/RSPModel_datatypes.h | 10 +- RSPModelLib/src/RSPModel.c | 2 + RSPModelLib/src/hob_parser.c | 376 +++++++++++++++++++++-- RSPModelLib/src/hob_parser.h | 2 + 4 files changed, 356 insertions(+), 34 deletions(-) diff --git a/RSPModelLib/include/RSPModel_datatypes.h b/RSPModelLib/include/RSPModel_datatypes.h index 53a4f15..2355fdf 100644 --- a/RSPModelLib/include/RSPModel_datatypes.h +++ b/RSPModelLib/include/RSPModel_datatypes.h @@ -55,9 +55,9 @@ typedef struct hob_face { unsigned short indices[4]; T_RGBA vertex_colors[4]; //TODO: convert in R:8_G:8_B:8_A:8 format? Caution with BE/LE conversion T_TEXCOORD tex_coords[4]; -} T_HOB_FACE; +} T_RSPMODEL_FACE; -typedef struct hob_face_group { +typedef struct rspmodel_obj_parts { unsigned int meshdef1_offset; unsigned int face_block_end_offset; @@ -68,11 +68,11 @@ typedef struct hob_face_group { T_VECTOR3 transform; unsigned int face_count; - T_HOB_FACE* faces; + T_RSPMODEL_FACE* faces; unsigned int vertex_count; T_VERTEX* vertices; -} T_HOB_FACE_GROUP; +} T_RSPMODEL_OBJ_PARTS; typedef struct rspmodel_object { char name[16]; @@ -83,7 +83,7 @@ typedef struct rspmodel_object { unsigned int object_part_count; unsigned int face_group_count; - T_HOB_FACE_GROUP* object_parts; + T_RSPMODEL_OBJ_PARTS* object_parts; } T_RSPMODEL_OBJECT; /** diff --git a/RSPModelLib/src/RSPModel.c b/RSPModelLib/src/RSPModel.c index b58ed14..407f1da 100644 --- a/RSPModelLib/src/RSPModel.c +++ b/RSPModelLib/src/RSPModel.c @@ -26,6 +26,8 @@ unsigned short RSPModel_processHOBFile( T_RSPMODEL_HOB* hob, const char* const f T_PROG_OPTIONS canard; canard.god_mode = 1; + canard.debug_mode = 1; + canard.verbose_mode = 1; RSP_ModelLib_ParseHOBFile(filePath, hob, &canard); return RSPLIB_SUCCESS; diff --git a/RSPModelLib/src/hob_parser.c b/RSPModelLib/src/hob_parser.c index c8f934e..2d091a3 100644 --- a/RSPModelLib/src/hob_parser.c +++ b/RSPModelLib/src/hob_parser.c @@ -17,14 +17,17 @@ #include "hob_parser.h" +static unsigned int ExtractObjects(T_RSPMODEL_HOB*, const MEMFILE, const unsigned char); +static unsigned int ExtractObjParts(T_RSPMODEL_OBJECT*, const MEMFILE, const unsigned char); +static unsigned int ExtractObjParts_faces(T_RSPMODEL_OBJ_PARTS*, const MEMFILE, const unsigned char); +static inline unsigned int ExtractObjpart_Face_Colors(T_RSPMODEL_FACE*, const char*); +static inline unsigned int ExtractObjpart_Face_UVMaps(T_RSPMODEL_FACE*, const char*); + unsigned char RSP_ModelLib_ParseHOBFile(const char* fileName, T_RSPMODEL_HOB* hob_struct, T_PROG_OPTIONS* p_opts) { unsigned char err = NO_ERROR; long fileSize; FILE* fStream = NULL; - char* memFile = NULL; - unsigned int i,j,k; - unsigned int facesExtraOffset; - int* offset_index = NULL; + MEMFILE memFile = NULL; if (hob_struct != NULL && fileName != NULL) { // Open file @@ -43,6 +46,11 @@ unsigned char RSP_ModelLib_ParseHOBFile(const char* fileName, T_RSPMODEL_HOB* ho fread(memFile, fileSize, 1, fStream); fclose(fStream); + // Do the magic! + ExtractObjects(hob_struct, memFile, p_opts->verbose_mode + p_opts->debug_mode + p_opts->god_mode); + + + /* // Retrieve object count from the header hob_struct->obj_count = ((T_HOBFILE_HEADER *)memFile)->obj_count; printf("[INFO] - Object(s) quantity: %d\n", hob_struct->obj_count); @@ -88,7 +96,8 @@ unsigned char RSP_ModelLib_ParseHOBFile(const char* fileName, T_RSPMODEL_HOB* ho hob_struct->objects[i].face_group_count = ((T_HOBFILE_FACEGROUP_HEADER *)(memFile + hob_struct->objects[i].object_part_header_offset))->facegroup_count; if (p_opts->verbose_mode) printf("[DBG] > Face groups count: %d\n", hob_struct->objects[i].face_group_count); - if (hob_struct->objects[i].object_part_count != hob_struct->objects[i].face_group_count && (p_opts->verbose_mode)) printf("[DBG] > Object parts / facegroup count are different!\n"); + if (hob_struct->objects[i].object_part_count != hob_struct->objects[i].face_group_count && (p_opts->verbose_mode)) + printf("[DBG] > Object parts / facegroup count are different!\n"); // Get facegroup datas offset_index = calloc(hob_struct->objects[i].object_part_count, sizeof(int)); @@ -354,30 +363,7 @@ unsigned char RSP_ModelLib_ParseHOBFile(const char* fileName, T_RSPMODEL_HOB* ho } // Get vertex datas - hob_struct->objects[i].object_parts[j].vertices = calloc(hob_struct->objects[i].object_parts[j].vertex_count, sizeof(T_VERTEX)); - for ( k = 0; k < hob_struct->objects[i].object_parts[j].vertex_count; k++ ) { - hob_struct->objects[i].object_parts[j].vertices[k].x = ((T_HOBFILE_VERTEX *)(memFile - + hob_struct->objects[i].object_parts[j].vertex_block_offset - + sizeof(T_VERTEX) * k))->x; - - hob_struct->objects[i].object_parts[j].vertices[k].y = ((T_HOBFILE_VERTEX *)(memFile - + hob_struct->objects[i].object_parts[j].vertex_block_offset - + sizeof(T_VERTEX) * k))->y; - - hob_struct->objects[i].object_parts[j].vertices[k].z = ((T_HOBFILE_VERTEX *)(memFile - + hob_struct->objects[i].object_parts[j].vertex_block_offset - + sizeof(T_VERTEX) * k))->z; - - hob_struct->objects[i].object_parts[j].vertices[k].w = ((T_HOBFILE_VERTEX *)(memFile - + hob_struct->objects[i].object_parts[j].vertex_block_offset - + sizeof(T_VERTEX) * k))->w; // Always 0??? - - if (p_opts->debug_mode) printf("[DBG] > Found vertex %d: (%d, %d, %d)\n", k, - hob_struct->objects[i].object_parts[j].vertices[k].x, - hob_struct->objects[i].object_parts[j].vertices[k].y, - hob_struct->objects[i].object_parts[j].vertices[k].z - ); - } + ExtractObjpartVertices(&hob_struct->objects[i].object_parts[j], memFile, p_opts->debug_mode); } // Get object part ID, used by animation? bones? @@ -406,6 +392,7 @@ unsigned char RSP_ModelLib_ParseHOBFile(const char* fileName, T_RSPMODEL_HOB* ho err = RSPLIB_ERROR_GENERIC; printf("[INFO] Can't process empty file!\n"); } + */ free(memFile); @@ -422,3 +409,334 @@ unsigned char RSP_ModelLib_ParseHOBFile(const char* fileName, T_RSPMODEL_HOB* ho return err; } + +/** + * Count objects and extract datas from them. + * + * @param[in|out] pHobStruct Take root hob structure to get the T_RSPMODEL_OBJECT buffer and header datas. + * @param[in] pMemfile + * @param[in] verbose + * + * @return Error code, RSPLIB_SUCCESS when no error. + */ +static unsigned int ExtractObjects(T_RSPMODEL_HOB* pHobStruct, const MEMFILE pMemfile, const unsigned char verbose) { + unsigned int i; + + if (pHobStruct == NULL || pMemfile == NULL) return RSPLIB_ERROR_ARGS_NULL; + + // Retrieve object count from the header + pHobStruct->obj_count = ((T_HOBFILE_HEADER *)pMemfile)->obj_count; + printf("[INFO] - Object(s) quantity: %d\n", pHobStruct->obj_count); + if (pHobStruct->obj_count <= 0) { + printf("[INFO] Can't process empty file!\n"); + return RSPLIB_ERROR_GENERIC; + } + + // Populate HOB structure with object descriptor + pHobStruct->objects = calloc(pHobStruct->obj_count, sizeof(T_RSPMODEL_OBJECT)); + if (pHobStruct->objects == NULL) return RSPLIB_ERROR_MEMORY; + + for ( i = 0; i < pHobStruct->obj_count; i++ ) { + if (verbose == 2) printf("\n-=====================-Begin of Object part-======================-\n"); + + // Get object name + memcpy(pHobStruct->objects[i].name, ((T_HOBFILE_OBJ_DESCRIPTOR *)(pMemfile + sizeof(T_HOBFILE_HEADER) + + sizeof(T_HOBFILE_OBJ_DESCRIPTOR) * i))->object_name, 16); + + if (verbose == 1) printf("\n"); + printf("[INFO] - Process %s object...\n", pHobStruct->objects[i].name); + + + // Get offsets + pHobStruct->objects[i].face_group_offset = ((T_HOBFILE_OBJ_DESCRIPTOR *)(pMemfile + sizeof(T_HOBFILE_HEADER) + + sizeof(T_HOBFILE_OBJ_DESCRIPTOR) * i))->facegroup_offset; + if (verbose == 1) printf("[DBG] > Face group offset: 0x%X\n", pHobStruct->objects[i].face_group_offset); + pHobStruct->objects[i].object_part_header_offset = ((T_HOBFILE_OBJ_DESCRIPTOR *)(pMemfile + sizeof(T_HOBFILE_HEADER) + + sizeof(T_HOBFILE_OBJ_DESCRIPTOR) * i))->object_parts_offset; + if (verbose == 1) printf("[DBG] > Face group header/object parts offset: 0x%X\n", pHobStruct->objects[i].object_part_header_offset); + pHobStruct->objects[i].face_group_header_offset = ((T_HOBFILE_OBJ_DESCRIPTOR *)(pMemfile + sizeof(T_HOBFILE_HEADER) + + sizeof(T_HOBFILE_OBJ_DESCRIPTOR) * i))->facegroup_header_2_offset; + if (verbose == 1) printf("[DBG] > Face group header2 offset: 0x%X\n", pHobStruct->objects[i].face_group_header_offset); + + if (verbose == 3) { + printf("[DBG] > Face group unknown1: %d\n",((T_HOBFILE_OBJ_DESCRIPTOR *)(pMemfile + sizeof(T_HOBFILE_HEADER) + sizeof(T_HOBFILE_OBJ_DESCRIPTOR) * i))->unknownOffset1); + printf("[DBG] > Face group unknown2: %d\n",((T_HOBFILE_OBJ_DESCRIPTOR *)(pMemfile + sizeof(T_HOBFILE_HEADER) + sizeof(T_HOBFILE_OBJ_DESCRIPTOR) * i))->unknownOffset2); + printf("[DBG] > Face group unknown3: %d\n",((T_HOBFILE_OBJ_DESCRIPTOR *)(pMemfile + sizeof(T_HOBFILE_HEADER) + sizeof(T_HOBFILE_OBJ_DESCRIPTOR) * i))->unknownOffset3); + printf("[DBG] > Face group unknown4: %.8f\n",((T_HOBFILE_OBJ_DESCRIPTOR *)(pMemfile + sizeof(T_HOBFILE_HEADER) + sizeof(T_HOBFILE_OBJ_DESCRIPTOR) * i))->unknown4); + } + + // Get count and offsets from the facegroup header + pHobStruct->objects[i].object_part_count = ((T_HOBFILE_FACEGROUP_HEADER *)(pMemfile + + pHobStruct->objects[i].object_part_header_offset))->object_part_count; + if (verbose == 1) printf("[DBG] > Object parts count: %d\n", pHobStruct->objects[i].object_part_count); + pHobStruct->objects[i].face_group_count = ((T_HOBFILE_FACEGROUP_HEADER *)(pMemfile + + pHobStruct->objects[i].object_part_header_offset))->facegroup_count; + if (verbose == 1) printf("[DBG] > Face groups count: %d\n", pHobStruct->objects[i].face_group_count); + if (pHobStruct->objects[i].object_part_count != pHobStruct->objects[i].face_group_count && (verbose == 1)) + printf("[DBG] > Object parts / facegroup count are different!\n"); + + // Get facegroup datas + ExtractObjParts(&pHobStruct->objects[i], pMemfile, verbose); + } + + return RSPLIB_SUCCESS; +} + +/** + * Count object's sub-part and extract datas from them. + * + * @param[in|out] pObject Take object structure to get the T_RSPMODEL_OBJ_PARTS buffer and object datas. + * @param[in] pMemfile + * @param[in] verbose + * + * @return Error code, RSPLIB_SUCCESS when no error. + */ +static unsigned int ExtractObjParts(T_RSPMODEL_OBJECT* pObject, const MEMFILE pMemfile, const unsigned char verbose) { + unsigned int i, subpart_offset = 0; + + if (pObject == NULL || pMemfile == NULL) return RSPLIB_ERROR_ARGS_NULL; + + pObject->object_parts = calloc(pObject->object_part_count, sizeof(T_RSPMODEL_OBJ_PARTS)); + if (pObject->object_parts == NULL) return RSPLIB_ERROR_MEMORY; + + for ( i = 0; i < pObject->object_part_count; i++ ) { + if (verbose == 2) printf("\n-----------------------Begin of Mesh part-------------------------\n"); + subpart_offset = ((T_HOBFILE_FACEGROUP_OFFSET *)(pMemfile + pObject->object_part_header_offset + + sizeof(T_HOBFILE_FACEGROUP_HEADER) + sizeof(T_HOBFILE_FACEGROUP_OFFSET) * i))->facegroup_offset; + if (verbose == 1) printf("\n[DBG] > Face group meshdef0 offset: 0x%X\n", subpart_offset); + + // Get meshdef0 datas + if (verbose == 3) printf("[DBG] > meshdef0 offset1: 0x%X\n",((T_HOBFILE_MESHDEF0 *)(pMemfile + subpart_offset))->offset1); + if (verbose == 3) printf("[DBG] > meshdef0 offset2: 0x%X\n",((T_HOBFILE_MESHDEF0 *)(pMemfile + subpart_offset))->offset2); + if (verbose == 1) printf("[DBG] > Prev meshdef0 offset: 0x%X\n",((T_HOBFILE_MESHDEF0 *)(pMemfile + subpart_offset))->prev_meshdef0_offset); + if (verbose == 1) printf("[DBG] > Next meshdef0 offset: 0x%X\n",((T_HOBFILE_MESHDEF0 *)(pMemfile + subpart_offset))->next_meshdef0_offset); + + if (verbose == 3) printf("[DBG] > meshdef0 unknown3: %.8f\n",((T_HOBFILE_MESHDEF0 *)(pMemfile + subpart_offset))->unknown3); + if (verbose == 3) printf("[DBG] > meshdef0 unknown4: %.8f\n",((T_HOBFILE_MESHDEF0 *)(pMemfile + subpart_offset))->unknown4); + if (verbose == 3) printf("[DBG] > meshdef0 unknown5: %.8f\n",((T_HOBFILE_MESHDEF0 *)(pMemfile + subpart_offset))->unknown5); + + // Get meshdef1 (mesh descriptor) offset + pObject->object_parts[i].meshdef1_offset = ((T_HOBFILE_MESHDEF0 *)(pMemfile + subpart_offset))->meshdef1_offset_plus_4; + if (verbose == 1) printf("\n[DBG] > Face group meshdef1 offset: 0x%X\n", pObject->object_parts[i].meshdef1_offset); + + if( ((T_HOBFILE_MESHDEF0 *)(pMemfile + subpart_offset))->reserved1 != 0 || + ((T_HOBFILE_MESHDEF0 *)(pMemfile + subpart_offset))->reserved2 != 0 ) { + if (verbose == 3) printf("[DBG] > Face group meshdef0: no 0!\n"); + } + + if (pObject->object_parts[i].meshdef1_offset > 0) { + // Read meshdef1 datas + pObject->object_parts[i].face_block_end_offset = ((T_HOBFILE_MESHDEF1 *)(pMemfile + + pObject->object_parts[i].meshdef1_offset - 4))->facedef_end_offset; + pObject->object_parts[i].vertex_count = ((T_HOBFILE_MESHDEF1 *)(pMemfile + + pObject->object_parts[i].meshdef1_offset - 4))->vertex_count; + pObject->object_parts[i].face_block_offset = ((T_HOBFILE_MESHDEF1 *)(pMemfile + + pObject->object_parts[i].meshdef1_offset - 4))->faceblock_offset; + if (verbose == 1) printf("[DBG] > Faces offset: 0x%X\n", pObject->object_parts[i].face_block_offset); + pObject->object_parts[i].vertex_block_offset = ((T_HOBFILE_MESHDEF1 *)(pMemfile + + pObject->object_parts[i].meshdef1_offset - 4))->vertexblocks_offset; + if (verbose == 1) printf("[DBG] > Vertex offset: 0x%X\n\n", pObject->object_parts[i].vertex_block_offset); + + // Get faces datas + ExtractObjParts_faces(&pObject->object_parts[i], pMemfile, verbose); + } + + // Get object part ID, used by animation? bones? + pObject->object_parts[i].id = ((T_HOBFILE_MESHDEF0 *)(pMemfile + subpart_offset))->object_id; + if (verbose == 1) printf("\n[DBG] > Facegroup/object ID: %d\n", pObject->object_parts[i].id); + + // Get the transform matrix, used by at-st and at-at (at this time) + pObject->object_parts[i].transform.x = ((T_HOBFILE_MESHDEF0 *)(pMemfile + subpart_offset))->transform_x; + pObject->object_parts[i].transform.y = ((T_HOBFILE_MESHDEF0 *)(pMemfile + subpart_offset))->transform_y; + pObject->object_parts[i].transform.z = ((T_HOBFILE_MESHDEF0 *)(pMemfile + subpart_offset))->transform_z; + if (verbose == 3) printf("\n[DBG] > Facegroup/object transform matrix: [%.8f %.8f %.8f]\n", + pObject->object_parts[i].transform.x, + pObject->object_parts[i].transform.y, + pObject->object_parts[i].transform.z + ); + + if (verbose == 2) printf("\n-----------------------End of Mesh part---------------------------\n"); + } + + if (verbose == 2) printf("\n-=====================-End of Object part-========================-\n"); + + return RSPLIB_SUCCESS; +} + +/** + * Extract datas from faces in object sub-part. + * + * @param[in|out] pObjParts + * @param[in] pMemfile + * @param[in] verbose + * + * @return Error code, RSPLIB_SUCCESS when no error. + */ +static unsigned int ExtractObjParts_faces(T_RSPMODEL_OBJ_PARTS* pObjParts, const MEMFILE pMemfile, const unsigned char verbose) { + unsigned int i, facesExtraOffset = 0; + + if (pObjParts == NULL || pMemfile == NULL) return RSPLIB_ERROR_ARGS_NULL; + + if( ((T_HOBFILE_FACEBLOCK *)(pMemfile + pObjParts->face_block_offset))->reserved1 != 0 || + ((T_HOBFILE_FACEBLOCK *)(pMemfile + pObjParts->face_block_offset))->reserved2 != 0 ) { + if (verbose == 3) printf("[DBG] > Face block: uncommon zero header!\n"); + } + if ( ((T_HOBFILE_FACEBLOCK *)(pMemfile + pObjParts->face_block_offset))->facesOffset != + pObjParts->face_block_offset + sizeof(T_HOBFILE_FACEBLOCK)) { + if (verbose == 3) printf("[DBG] > Face block: uncommon face data offset position!\n"); + } + + pObjParts->face_count = ((T_HOBFILE_FACEBLOCK *)(pMemfile + pObjParts->face_block_offset))->faceCounts; + pObjParts->faces = calloc(pObjParts->face_count, sizeof(T_RSPMODEL_FACE)); + for ( i = 0; i < pObjParts->face_count; i++ ) { + if (verbose == 2) printf("\n----------------------Begin of FaceGroup part----------------------\n"); + + // Get flags + pObjParts->faces[i].flags = ((T_HOBFILE_FACES_HEADER *)(pMemfile + pObjParts->face_block_offset + + sizeof(T_HOBFILE_FACEBLOCK) + sizeof(T_HOBFILE_FACES_HEADER) * i + facesExtraOffset))->flags; + + // Get unknown bytes + pObjParts->faces[i].b1 = ((T_HOBFILE_FACES_HEADER *)(pMemfile + pObjParts->face_block_offset + + sizeof(T_HOBFILE_FACEBLOCK) + sizeof(T_HOBFILE_FACES_HEADER) * i + facesExtraOffset))->b1; + pObjParts->faces[i].b2 = ((T_HOBFILE_FACES_HEADER *)(pMemfile + pObjParts->face_block_offset + + sizeof(T_HOBFILE_FACEBLOCK) + sizeof(T_HOBFILE_FACES_HEADER) * i + facesExtraOffset))->b2; + pObjParts->faces[i].b3 = ((T_HOBFILE_FACES_HEADER *)(pMemfile + pObjParts->face_block_offset + + sizeof(T_HOBFILE_FACEBLOCK) + sizeof(T_HOBFILE_FACES_HEADER) * i + facesExtraOffset))->b3; + + pObjParts->faces[i].bsize = ((T_HOBFILE_FACES_HEADER *)(pMemfile + pObjParts->face_block_offset + + sizeof(T_HOBFILE_FACEBLOCK) + sizeof(T_HOBFILE_FACES_HEADER) * i + facesExtraOffset))->faceBlockIntSize * 4; // Multiply by 4 to get the bytes exact number + if (((T_HOBFILE_FACES_HEADER *)(pMemfile + pObjParts->face_block_offset + sizeof(T_HOBFILE_FACEBLOCK) + + sizeof(T_HOBFILE_FACES_HEADER) * i + facesExtraOffset))->headerSeparator != 0) { + if (verbose == 3) printf("[DBG] > Face header: uncommon separator!\n"); + } + + // Get materials index + pObjParts->faces[i].material_index = ((T_HOBFILE_FACES_HEADER *)(pMemfile + pObjParts->face_block_offset + + sizeof(T_HOBFILE_FACEBLOCK) + sizeof(T_HOBFILE_FACES_HEADER) * i + facesExtraOffset))->materialIndex; + + // Get vertex indices + memcpy(pObjParts->faces[i].indices, ((T_HOBFILE_FACES_HEADER *)(pMemfile + pObjParts->face_block_offset + + sizeof(T_HOBFILE_FACEBLOCK) + sizeof(T_HOBFILE_FACES_HEADER) * i + facesExtraOffset))->vertexIndices, + sizeof(unsigned short) * 4); + + // Recalculate the dynamic extra bytes offset size - if present + if (pObjParts->faces[i].flags_bits.fHasExtraBytesBeforeColor) facesExtraOffset += 8; + + // Get vertex color - if present + if (pObjParts->faces[i].flags_bits.fHasColor) { + facesExtraOffset += ExtractObjpart_Face_Colors(&pObjParts->faces[i], pMemfile + pObjParts->face_block_offset + + sizeof(T_HOBFILE_FACEBLOCK) + sizeof(T_HOBFILE_FACES_HEADER) + sizeof(T_HOBFILE_FACES_HEADER) * i + + facesExtraOffset); + } + + // Get UV map - if present + if (pObjParts->faces[i].flags_bits.fHasTexture) { + facesExtraOffset += ExtractObjpart_Face_UVMaps(&pObjParts->faces[i], pMemfile + pObjParts->face_block_offset + + sizeof(T_HOBFILE_FACEBLOCK) + sizeof(T_HOBFILE_FACES_HEADER) + sizeof(T_HOBFILE_FACES_HEADER) * i + + facesExtraOffset); + } + + if (verbose == 2) { + printf("[DBG] > Face %d details: flags:0x%X b1:%d b2:%d b3%d bsize:%d\n", i, pObjParts->faces[i].flags, + pObjParts->faces[i].b1, pObjParts->faces[i].b2, pObjParts->faces[i].b3, pObjParts->faces[i].bsize); + printf("[DBG] - Type is Quad: %d\n", pObjParts->faces[i].flags_bits.fIsQuad); + printf("[DBG] - Material offset: 0x%X\n", pObjParts->faces[i].material_index); + printf("[DBG] - Vertex indices: %d, %d, %d, %d\n", pObjParts->faces[i].indices[0], pObjParts->faces[i].indices[1], + pObjParts->faces[i].indices[2], pObjParts->faces[i].indices[3]); + printf("[DBG] - Vertex colors: 0x%X, 0x%X, 0x%X, 0x%X\n", pObjParts->faces[i].vertex_colors[0], + pObjParts->faces[i].vertex_colors[1], pObjParts->faces[i].vertex_colors[2], pObjParts->faces[i].vertex_colors[3]); + printf("[DBG] - Vertex UV coord (divided by 4096):\n"); + printf("[DBG] > %.8f(%d), %.8f(%d)\n", + ((double) 1/4096) * pObjParts->faces[i].tex_coords[0].u, + pObjParts->faces[i].tex_coords[0].u, + ((double) 1/4096) * pObjParts->faces[i].tex_coords[0].v, + pObjParts->faces[i].tex_coords[0].v + ); + printf("[DBG] > %.8f(%d), %.8f(%d)\n", + ((double) 1/4096) * pObjParts->faces[i].tex_coords[1].u, + pObjParts->faces[i].tex_coords[1].u, + ((double) 1/4096) * pObjParts->faces[i].tex_coords[1].v, + pObjParts->faces[i].tex_coords[1].v + ); + printf("[DBG] > %.8f(%d), %.8f(%d)\n", + ((double) 1/4096) * pObjParts->faces[i].tex_coords[2].u, + pObjParts->faces[i].tex_coords[2].u, + ((double) 1/4096) * pObjParts->faces[i].tex_coords[2].v, + pObjParts->faces[i].tex_coords[2].v + ); + printf("[DBG] > %.8f(%d), %.8f(%d)\n", + ((double) 1/4096) * pObjParts->faces[i].tex_coords[3].u, + pObjParts->faces[i].tex_coords[3].u, + ((double) 1/4096) * pObjParts->faces[i].tex_coords[3].v, + pObjParts->faces[i].tex_coords[3].v + ); + printf("\n"); + } + + if (verbose == 2) printf("\n-----------------------End of FaceGroup part-----------------------\n"); + } + + // Get vertex datas + pObjParts->vertices = calloc(pObjParts->vertex_count, sizeof(T_VERTEX)); + if (pObjParts->vertices == NULL) return RSPLIB_ERROR_MEMORY; + + for ( i = 0; i < pObjParts->vertex_count; i++ ) { + pObjParts->vertices[i].x = + ((T_HOBFILE_VERTEX *)(pMemfile + pObjParts->vertex_block_offset + sizeof(T_VERTEX) * i))->x; + + pObjParts->vertices[i].y = + ((T_HOBFILE_VERTEX *)(pMemfile + pObjParts->vertex_block_offset + sizeof(T_VERTEX) * i))->y; + + pObjParts->vertices[i].z = + ((T_HOBFILE_VERTEX *)(pMemfile + pObjParts->vertex_block_offset + sizeof(T_VERTEX) * i))->z; + + pObjParts->vertices[i].w = + ((T_HOBFILE_VERTEX *)(pMemfile + pObjParts->vertex_block_offset + sizeof(T_VERTEX) * i))->w; // Always 0??? + + if (verbose == 2) printf("[DBG] > Found vertex %d: (%d, %d, %d)\n", i, + pObjParts->vertices[i].x, pObjParts->vertices[i].y, pObjParts->vertices[i].z + ); + } + + return RSPLIB_SUCCESS; +} + +static inline unsigned int ExtractObjpart_Face_Colors(T_RSPMODEL_FACE* pFace, const char* pFaceMemFileOffset) { + unsigned int dynOffset = 0; + + if (pFace->flags_bits.fSeparateColorVertex) { + pFace->vertex_colors[0] = ((T_HOBFILE_FACES_VERTEX_COLOR *)(pFaceMemFileOffset))->v1_rgba; + pFace->vertex_colors[1] = ((T_HOBFILE_FACES_VERTEX_COLOR *)(pFaceMemFileOffset))->v2_rgba; + pFace->vertex_colors[2] = ((T_HOBFILE_FACES_VERTEX_COLOR *)(pFaceMemFileOffset))->v3_rgba; + if (pFace->flags_bits.fIsQuad) { + pFace->vertex_colors[3] = ((T_HOBFILE_FACES_VERTEX_COLOR *)(pFaceMemFileOffset))->v4_rgba; + dynOffset += sizeof(T_HOBFILE_FACES_VERTEX_COLOR); + } else { + dynOffset += sizeof(T_HOBFILE_FACES_VERTEX_COLOR) - sizeof(T_RGBA); + } + } else { + pFace->vertex_colors[0] = ((T_HOBFILE_FACES_COLOR *)(pFaceMemFileOffset))->rgba; + pFace->vertex_colors[1] = ((T_HOBFILE_FACES_COLOR *)(pFaceMemFileOffset))->rgba; + pFace->vertex_colors[2] = ((T_HOBFILE_FACES_COLOR *)(pFaceMemFileOffset))->rgba; + pFace->vertex_colors[3] = ((T_HOBFILE_FACES_COLOR *)(pFaceMemFileOffset))->rgba; + dynOffset += sizeof(T_HOBFILE_FACES_COLOR); + } + + return dynOffset; +} + +static inline unsigned int ExtractObjpart_Face_UVMaps(T_RSPMODEL_FACE* pFace, const char* pFaceMemFileOffset) { + unsigned int dynOffset = 0; + + pFace->tex_coords[0] = ((T_HOBFILE_FACES_VERTEX_TEXTURE *)(pFaceMemFileOffset))->v1_texcoord; + pFace->tex_coords[1] = ((T_HOBFILE_FACES_VERTEX_TEXTURE *)(pFaceMemFileOffset))->v2_texcoord; + pFace->tex_coords[2] = ((T_HOBFILE_FACES_VERTEX_TEXTURE *)(pFaceMemFileOffset))->v3_texcoord; + if (pFace->flags_bits.fIsQuad) { + pFace->tex_coords[3] = ((T_HOBFILE_FACES_VERTEX_TEXTURE *)(pFaceMemFileOffset))->v4_texcoord; + dynOffset += sizeof(T_HOBFILE_FACES_VERTEX_TEXTURE); + } else { + dynOffset += sizeof(T_HOBFILE_FACES_VERTEX_TEXTURE) - sizeof(T_TEXCOORD); + } + + return dynOffset; +} diff --git a/RSPModelLib/src/hob_parser.h b/RSPModelLib/src/hob_parser.h index a2cb907..31094df 100644 --- a/RSPModelLib/src/hob_parser.h +++ b/RSPModelLib/src/hob_parser.h @@ -14,6 +14,8 @@ #ifndef SRC_HOB_PARSER_H_ #define SRC_HOB_PARSER_H_ +typedef char* MEMFILE; + unsigned char RSP_ModelLib_ParseHOBFile(const char* fileName, T_RSPMODEL_HOB* hob_struct, T_PROG_OPTIONS* p_opts); #endif /* SRC_HOB_PARSER_H_ */ -- 2.39.5 From 35ed66466b9a01a0f7cd62b7ca5e4bda4bc73358 Mon Sep 17 00:00:00 2001 From: JackCarterSmith Date: Fri, 19 Aug 2022 18:03:47 +0200 Subject: [PATCH 11/15] Added more documentation --- RSEModel/src/Model-Extractor.c | 2 +- RSEModel/src/obj_exporter.c | 2 +- RSPModelLib/include/RSPModel.h | 16 +- RSPModelLib/include/RSPModel_datatypes.h | 6 +- RSPModelLib/src/RSPModel.c | 6 +- RSPModelLib/src/hob_parser.c | 526 +++++------------------ RSPModelLib/src/hob_parser.h | 39 +- 7 files changed, 170 insertions(+), 427 deletions(-) diff --git a/RSEModel/src/Model-Extractor.c b/RSEModel/src/Model-Extractor.c index 24bbbf7..07e5402 100644 --- a/RSEModel/src/Model-Extractor.c +++ b/RSEModel/src/Model-Extractor.c @@ -43,7 +43,7 @@ int main(int argc, char *argv[]) { unsigned char p; // Hello world! - printf("\n*** RogueSquadron Extractor (RSE) - MODEL module - v%s ***\n", PRG_VERSION); + printf("\n*** RogueSquadron Extractor (RSE) - MODEL module - v%s ***\n", RSPModel_getVersion()); // Check for arguments if (argc < 2) { diff --git a/RSEModel/src/obj_exporter.c b/RSEModel/src/obj_exporter.c index b60256f..1067010 100644 --- a/RSEModel/src/obj_exporter.c +++ b/RSEModel/src/obj_exporter.c @@ -122,7 +122,7 @@ unsigned char exportOBJModel(T_RSPMODEL_OBJECT* hob_objects, const char *out_pat static void mtlPathPatch(const char* out_file, const char* obj_name) { FILE* obj = NULL; char* memFile = NULL; - long fileSize,i,pos = 0,lines; + long fileSize,i,pos = 0,lines = 0; char _path[128],b; obj = fopen(out_file, "r"); diff --git a/RSPModelLib/include/RSPModel.h b/RSPModelLib/include/RSPModel.h index 001d25a..e739c4b 100644 --- a/RSPModelLib/include/RSPModel.h +++ b/RSPModelLib/include/RSPModel.h @@ -64,7 +64,9 @@ RSPMODEL_EXTERN char* RSPModel_getVersion( void ); * * @return Error status, return RSPLIB_SUCCESS in nominal case. */ -RSPMODEL_EXTERN unsigned short RSPModel_processHOBFile( T_RSPMODEL_HOB* hob, const char* const filePath ); +RSPMODEL_EXTERN unsigned short RSPModel_processHOBFile( + T_RSPMODEL_HOB* hob, const char* const filePath + ); /** * @brief Run model parser for the specified file in memory. @@ -78,7 +80,9 @@ RSPMODEL_EXTERN unsigned short RSPModel_processHOBFile( T_RSPMODEL_HOB* hob, con * * @return Error status, return RSPLIB_SUCCESS in nominal case. */ -RSPMODEL_EXTERN unsigned short RSPModel_processHOBFileMemory( T_RSPMODEL_HOB* hob, const void* const memFilePtr, const long memFileSize ); +RSPMODEL_EXTERN unsigned short RSPModel_processHOBFileMemory( + T_RSPMODEL_HOB* hob, const void* const memFilePtr, const long memFileSize + ); /** * @brief Convert HOB's object datas to GL compatible format. @@ -89,7 +93,9 @@ RSPMODEL_EXTERN unsigned short RSPModel_processHOBFileMemory( T_RSPMODEL_HOB* ho * * @return Error status, return RSPLIB_SUCCESS in nominal case. */ -RSPMODEL_EXTERN unsigned short RSPModel_objectToGL( const T_RSPMODEL_OBJECT* objStruct, void* glObj ); +RSPMODEL_EXTERN unsigned short RSPModel_objectToGL( + const T_RSPMODEL_OBJECT* objStruct, void* glObj + ); /** * @brief Convert HOB's object datas to Direct3D compatible format. @@ -100,7 +106,9 @@ RSPMODEL_EXTERN unsigned short RSPModel_objectToGL( const T_RSPMODEL_OBJECT* obj * * @return Error status, return RSPLIB_SUCCESS in nominal case. */ -RSPMODEL_EXTERN unsigned short RSPModel_objectToD3D( const T_RSPMODEL_OBJECT* objStruct, void* D3DObj ); +RSPMODEL_EXTERN unsigned short RSPModel_objectToD3D( + const T_RSPMODEL_OBJECT* objStruct, void* D3DObj + ); #ifdef __cplusplus } diff --git a/RSPModelLib/include/RSPModel_datatypes.h b/RSPModelLib/include/RSPModel_datatypes.h index 2355fdf..9ff0496 100644 --- a/RSPModelLib/include/RSPModel_datatypes.h +++ b/RSPModelLib/include/RSPModel_datatypes.h @@ -14,9 +14,11 @@ extern "C" { #endif -/////////////////////////////////////////////////////////////////////////////// +//////////////////////////////////////////////////////////////////////////////// // Lib's structure definitions -/////////////////////////////////////////////////////////////////////////////// +//////////////////////////////////////////////////////////////////////////////// + +typedef char* MEMFILE; typedef unsigned int T_RGBA; diff --git a/RSPModelLib/src/RSPModel.c b/RSPModelLib/src/RSPModel.c index 407f1da..40afd48 100644 --- a/RSPModelLib/src/RSPModel.c +++ b/RSPModelLib/src/RSPModel.c @@ -36,7 +36,11 @@ unsigned short RSPModel_processHOBFile( T_RSPMODEL_HOB* hob, const char* const f unsigned short RSPModel_processHOBFileMemory( T_RSPMODEL_HOB* hob, const void* const memFilePtr, const long memFileSize ) { if ( hob == NULL || memFilePtr == NULL ) return RSPLIB_ERROR_ARGS_NULL; - + T_PROG_OPTIONS canard; + canard.god_mode = 1; + canard.debug_mode = 1; + canard.verbose_mode = 1; + RSP_ModelLib_ParseHOBMemFile((MEMFILE)memFilePtr, hob, &canard); return RSPLIB_SUCCESS; } diff --git a/RSPModelLib/src/hob_parser.c b/RSPModelLib/src/hob_parser.c index 2d091a3..891e6d6 100644 --- a/RSPModelLib/src/hob_parser.c +++ b/RSPModelLib/src/hob_parser.c @@ -1,9 +1,9 @@ /** * @file hob_parser.c - * @date 26/07/2022 + * @date 18/08/2022 * @author JackCarterSmith * @copyright GPL-v3.0 - * @brief Decode HOB file structure. + * @brief Process HOB file structure and extract its datas. * */ @@ -17,14 +17,34 @@ #include "hob_parser.h" +//////////////////////////////////////////////////////////////////////////////// +// Private functions declarations +//////////////////////////////////////////////////////////////////////////////// + static unsigned int ExtractObjects(T_RSPMODEL_HOB*, const MEMFILE, const unsigned char); static unsigned int ExtractObjParts(T_RSPMODEL_OBJECT*, const MEMFILE, const unsigned char); static unsigned int ExtractObjParts_faces(T_RSPMODEL_OBJ_PARTS*, const MEMFILE, const unsigned char); static inline unsigned int ExtractObjpart_Face_Colors(T_RSPMODEL_FACE*, const char*); static inline unsigned int ExtractObjpart_Face_UVMaps(T_RSPMODEL_FACE*, const char*); + +//////////////////////////////////////////////////////////////////////////////// +// Public functions definition +//////////////////////////////////////////////////////////////////////////////// + +unsigned char RSP_ModelLib_ParseHOBMemFile(const MEMFILE pMemFile, T_RSPMODEL_HOB* hob_struct, T_PROG_OPTIONS* p_opts) { + unsigned char err = RSPLIB_SUCCESS; + + if (hob_struct != NULL && pMemFile != NULL) { + // Do the magic! + err = ExtractObjects(hob_struct, pMemFile, p_opts->verbose_mode + p_opts->debug_mode + p_opts->god_mode); + } else err = RSPLIB_ERROR_ARGS_NULL; + + return err; +} + unsigned char RSP_ModelLib_ParseHOBFile(const char* fileName, T_RSPMODEL_HOB* hob_struct, T_PROG_OPTIONS* p_opts) { - unsigned char err = NO_ERROR; + unsigned char err = RSPLIB_SUCCESS; long fileSize; FILE* fStream = NULL; MEMFILE memFile = NULL; @@ -47,352 +67,7 @@ unsigned char RSP_ModelLib_ParseHOBFile(const char* fileName, T_RSPMODEL_HOB* ho fclose(fStream); // Do the magic! - ExtractObjects(hob_struct, memFile, p_opts->verbose_mode + p_opts->debug_mode + p_opts->god_mode); - - - /* - // Retrieve object count from the header - hob_struct->obj_count = ((T_HOBFILE_HEADER *)memFile)->obj_count; - printf("[INFO] - Object(s) quantity: %d\n", hob_struct->obj_count); - - if (hob_struct->obj_count > 0) { - // Populate HOB structure with object descriptor - hob_struct->objects = calloc(hob_struct->obj_count, sizeof(T_RSPMODEL_OBJECT)); - for ( i = 0; i < hob_struct->obj_count; i++ ) { - if (p_opts->debug_mode) printf("\n-=====================-Begin of Object part-======================-\n"); - - // Get object name - memcpy(hob_struct->objects[i].name, ((T_HOBFILE_OBJ_DESCRIPTOR *)(memFile - + sizeof(T_HOBFILE_HEADER) - + sizeof(T_HOBFILE_OBJ_DESCRIPTOR) * i))->object_name, 16); - if (p_opts->verbose_mode) printf("\n"); - printf("[INFO] - Process %s object...\n", hob_struct->objects[i].name); - - // Get offsets - hob_struct->objects[i].face_group_offset = ((T_HOBFILE_OBJ_DESCRIPTOR *)(memFile - + sizeof(T_HOBFILE_HEADER) - + sizeof(T_HOBFILE_OBJ_DESCRIPTOR) * i))->facegroup_offset; - if (p_opts->verbose_mode) printf("[DBG] > Face group offset: 0x%X\n", hob_struct->objects[i].face_group_offset); - hob_struct->objects[i].object_part_header_offset = ((T_HOBFILE_OBJ_DESCRIPTOR *)(memFile - + sizeof(T_HOBFILE_HEADER) - + sizeof(T_HOBFILE_OBJ_DESCRIPTOR) * i))->object_parts_offset; - if (p_opts->verbose_mode) printf("[DBG] > Face group header/object parts offset: 0x%X\n", hob_struct->objects[i].object_part_header_offset); - hob_struct->objects[i].face_group_header_offset = ((T_HOBFILE_OBJ_DESCRIPTOR *)(memFile - + sizeof(T_HOBFILE_HEADER) - + sizeof(T_HOBFILE_OBJ_DESCRIPTOR) * i))->facegroup_header_2_offset; - if (p_opts->verbose_mode) printf("[DBG] > Face group header2 offset: 0x%X\n", hob_struct->objects[i].face_group_header_offset); - - if (p_opts->god_mode) { - printf("[DBG] > Face group unknown1: %d\n",((T_HOBFILE_OBJ_DESCRIPTOR *)(memFile + sizeof(T_HOBFILE_HEADER) + sizeof(T_HOBFILE_OBJ_DESCRIPTOR) * i))->unknownOffset1); - printf("[DBG] > Face group unknown2: %d\n",((T_HOBFILE_OBJ_DESCRIPTOR *)(memFile + sizeof(T_HOBFILE_HEADER) + sizeof(T_HOBFILE_OBJ_DESCRIPTOR) * i))->unknownOffset2); - printf("[DBG] > Face group unknown3: %d\n",((T_HOBFILE_OBJ_DESCRIPTOR *)(memFile + sizeof(T_HOBFILE_HEADER) + sizeof(T_HOBFILE_OBJ_DESCRIPTOR) * i))->unknownOffset3); - printf("[DBG] > Face group unknown4: %.8f\n",((T_HOBFILE_OBJ_DESCRIPTOR *)(memFile + sizeof(T_HOBFILE_HEADER) + sizeof(T_HOBFILE_OBJ_DESCRIPTOR) * i))->unknown4); - } - - // Get count and offsets from the facegroup header - hob_struct->objects[i].object_part_count = ((T_HOBFILE_FACEGROUP_HEADER *)(memFile - + hob_struct->objects[i].object_part_header_offset))->object_part_count; - if (p_opts->verbose_mode) printf("[DBG] > Object parts count: %d\n", hob_struct->objects[i].object_part_count); - hob_struct->objects[i].face_group_count = ((T_HOBFILE_FACEGROUP_HEADER *)(memFile - + hob_struct->objects[i].object_part_header_offset))->facegroup_count; - if (p_opts->verbose_mode) printf("[DBG] > Face groups count: %d\n", hob_struct->objects[i].face_group_count); - if (hob_struct->objects[i].object_part_count != hob_struct->objects[i].face_group_count && (p_opts->verbose_mode)) - printf("[DBG] > Object parts / facegroup count are different!\n"); - - // Get facegroup datas - offset_index = calloc(hob_struct->objects[i].object_part_count, sizeof(int)); - hob_struct->objects[i].object_parts = calloc(hob_struct->objects[i].object_part_count, sizeof(T_HOB_FACE_GROUP)); - for ( j = 0; j < hob_struct->objects[i].object_part_count; j++ ) { - if (p_opts->debug_mode) printf("\n-----------------------Begin of Mesh part-------------------------\n"); - - offset_index[j] = ((T_HOBFILE_FACEGROUP_OFFSET *)(memFile + hob_struct->objects[i].object_part_header_offset - + sizeof(T_HOBFILE_FACEGROUP_HEADER) - + sizeof(T_HOBFILE_FACEGROUP_OFFSET) * j))->facegroup_offset; - if (p_opts->verbose_mode) printf("\n[DBG] > Face group meshdef0 offset: 0x%X\n", offset_index[j]); - - // Get meshdef0 datas - if (p_opts->god_mode) printf("[DBG] > meshdef0 offset1: 0x%X\n",((T_HOBFILE_MESHDEF0 *)(memFile + offset_index[j]))->offset1); - if (p_opts->god_mode) printf("[DBG] > meshdef0 offset2: 0x%X\n",((T_HOBFILE_MESHDEF0 *)(memFile + offset_index[j]))->offset2); - if (p_opts->verbose_mode) printf("[DBG] > Prev meshdef0 offset: 0x%X\n",((T_HOBFILE_MESHDEF0 *)(memFile + offset_index[j]))->prev_meshdef0_offset); - if (p_opts->verbose_mode) printf("[DBG] > Next meshdef0 offset: 0x%X\n",((T_HOBFILE_MESHDEF0 *)(memFile + offset_index[j]))->next_meshdef0_offset); - - if (p_opts->god_mode) printf("[DBG] > meshdef0 unknown3: %.8f\n",((T_HOBFILE_MESHDEF0 *)(memFile + offset_index[j]))->unknown3); - if (p_opts->god_mode) printf("[DBG] > meshdef0 unknown4: %.8f\n",((T_HOBFILE_MESHDEF0 *)(memFile + offset_index[j]))->unknown4); - if (p_opts->god_mode) printf("[DBG] > meshdef0 unknown5: %.8f\n",((T_HOBFILE_MESHDEF0 *)(memFile + offset_index[j]))->unknown5); - - // Get meshdef1 (mesh descriptor) offset - hob_struct->objects[i].object_parts[j].meshdef1_offset = ((T_HOBFILE_MESHDEF0 *)(memFile - + offset_index[j]))->meshdef1_offset_plus_4; - if (p_opts->verbose_mode) printf("\n[DBG] > Face group meshdef1 offset: 0x%X\n", hob_struct->objects[i].object_parts[j].meshdef1_offset); - - if( ((T_HOBFILE_MESHDEF0 *)(memFile + offset_index[j]))->reserved1 != 0 || - ((T_HOBFILE_MESHDEF0 *)(memFile + offset_index[j]))->reserved2 != 0 ) { - if (p_opts->god_mode) printf("[DBG] > Face group meshdef0: no 0!\n"); - } - - if (hob_struct->objects[i].object_parts[j].meshdef1_offset > 0) { - // Read meshdef1 datas - hob_struct->objects[i].object_parts[j].face_block_end_offset = ((T_HOBFILE_MESHDEF1 *)(memFile - + hob_struct->objects[i].object_parts[j].meshdef1_offset - 4))->facedef_end_offset; - hob_struct->objects[i].object_parts[j].vertex_count = ((T_HOBFILE_MESHDEF1 *)(memFile - + hob_struct->objects[i].object_parts[j].meshdef1_offset - 4))->vertex_count; - hob_struct->objects[i].object_parts[j].face_block_offset = ((T_HOBFILE_MESHDEF1 *)(memFile - + hob_struct->objects[i].object_parts[j].meshdef1_offset - 4))->faceblock_offset; - if (p_opts->verbose_mode) printf("[DBG] > Faces offset: 0x%X\n", hob_struct->objects[i].object_parts[j].face_block_offset); - hob_struct->objects[i].object_parts[j].vertex_block_offset = ((T_HOBFILE_MESHDEF1 *)(memFile - + hob_struct->objects[i].object_parts[j].meshdef1_offset - 4))->vertexblocks_offset; - if (p_opts->verbose_mode) printf("[DBG] > Vertex offset: 0x%X\n\n", hob_struct->objects[i].object_parts[j].vertex_block_offset); - - // Get face datas - if( ((T_HOBFILE_FACEBLOCK *)(memFile + hob_struct->objects[i].object_parts[j].face_block_offset))->reserved1 != 0 || - ((T_HOBFILE_FACEBLOCK *)(memFile + hob_struct->objects[i].object_parts[j].face_block_offset))->reserved2 != 0 ) { - if (p_opts->god_mode) printf("[DBG] > Face block: uncommon zero header!\n"); - } - if ( ((T_HOBFILE_FACEBLOCK *)(memFile + hob_struct->objects[i].object_parts[j].face_block_offset))->facesOffset != - hob_struct->objects[i].object_parts[j].face_block_offset + sizeof(T_HOBFILE_FACEBLOCK)) { - if (p_opts->god_mode) printf("[DBG] > Face block: uncommon face data offset position!\n"); - } - hob_struct->objects[i].object_parts[j].face_count = ((T_HOBFILE_FACEBLOCK *)(memFile - + hob_struct->objects[i].object_parts[j].face_block_offset))->faceCounts; - hob_struct->objects[i].object_parts[j].faces = calloc(hob_struct->objects[i].object_parts[j].face_count, sizeof(T_HOB_FACE)); - facesExtraOffset = 0; - for ( k = 0; k < hob_struct->objects[i].object_parts[j].face_count; k++ ) { - if (p_opts->debug_mode) printf("\n----------------------Begin of FaceGroup part----------------------\n"); - - // Get flags - hob_struct->objects[i].object_parts[j].faces[k].flags = ((T_HOBFILE_FACES_HEADER *)(memFile - + hob_struct->objects[i].object_parts[j].face_block_offset - + sizeof(T_HOBFILE_FACEBLOCK) - + sizeof(T_HOBFILE_FACES_HEADER) * k - + facesExtraOffset))->flags; - - // Get unknown bytes - hob_struct->objects[i].object_parts[j].faces[k].b1 = ((T_HOBFILE_FACES_HEADER *)(memFile - + hob_struct->objects[i].object_parts[j].face_block_offset - + sizeof(T_HOBFILE_FACEBLOCK) - + sizeof(T_HOBFILE_FACES_HEADER) * k - + facesExtraOffset))->b1; - hob_struct->objects[i].object_parts[j].faces[k].b2 = ((T_HOBFILE_FACES_HEADER *)(memFile - + hob_struct->objects[i].object_parts[j].face_block_offset - + sizeof(T_HOBFILE_FACEBLOCK) - + sizeof(T_HOBFILE_FACES_HEADER) * k - + facesExtraOffset))->b2; - hob_struct->objects[i].object_parts[j].faces[k].b3 = ((T_HOBFILE_FACES_HEADER *)(memFile - + hob_struct->objects[i].object_parts[j].face_block_offset - + sizeof(T_HOBFILE_FACEBLOCK) - + sizeof(T_HOBFILE_FACES_HEADER) * k - + facesExtraOffset))->b3; - - hob_struct->objects[i].object_parts[j].faces[k].bsize = ((T_HOBFILE_FACES_HEADER *)(memFile - + hob_struct->objects[i].object_parts[j].face_block_offset - + sizeof(T_HOBFILE_FACEBLOCK) - + sizeof(T_HOBFILE_FACES_HEADER) * k - + facesExtraOffset))->faceBlockIntSize * 4; // Multiply by 4 to get the bytes exact number - if (((T_HOBFILE_FACES_HEADER *)(memFile - + hob_struct->objects[i].object_parts[j].face_block_offset - + sizeof(T_HOBFILE_FACEBLOCK) - + sizeof(T_HOBFILE_FACES_HEADER) * k - + facesExtraOffset))->headerSeparator != 0) { - if (p_opts->god_mode) printf("[DBG] > Face header: uncommon separator!\n"); - } - - // Get materials index - hob_struct->objects[i].object_parts[j].faces[k].material_index = ((T_HOBFILE_FACES_HEADER *)(memFile - + hob_struct->objects[i].object_parts[j].face_block_offset - + sizeof(T_HOBFILE_FACEBLOCK) - + sizeof(T_HOBFILE_FACES_HEADER) * k - + facesExtraOffset))->materialIndex; - - // Get vertex indices - memcpy(hob_struct->objects[i].object_parts[j].faces[k].indices, - ((T_HOBFILE_FACES_HEADER *)(memFile - + hob_struct->objects[i].object_parts[j].face_block_offset - + sizeof(T_HOBFILE_FACEBLOCK) - + sizeof(T_HOBFILE_FACES_HEADER) * k - + facesExtraOffset))->vertexIndices, - sizeof(unsigned short) * 4); - - // Recalculate the dynamic extra bytes offset size - if present - if (hob_struct->objects[i].object_parts[j].faces[k].flags_bits.fHasExtraBytesBeforeColor) facesExtraOffset += 8; - - // Get vertex color - if present - if (hob_struct->objects[i].object_parts[j].faces[k].flags_bits.fHasColor) { - if (hob_struct->objects[i].object_parts[j].faces[k].flags_bits.fSeparateColorVertex) { - hob_struct->objects[i].object_parts[j].faces[k].vertex_colors[0] = ((T_HOBFILE_FACES_VERTEX_COLOR *)(memFile - + hob_struct->objects[i].object_parts[j].face_block_offset - + sizeof(T_HOBFILE_FACEBLOCK) - + sizeof(T_HOBFILE_FACES_HEADER) - + sizeof(T_HOBFILE_FACES_HEADER) * k - + facesExtraOffset))->v1_rgba; - hob_struct->objects[i].object_parts[j].faces[k].vertex_colors[1] = ((T_HOBFILE_FACES_VERTEX_COLOR *)(memFile - + hob_struct->objects[i].object_parts[j].face_block_offset - + sizeof(T_HOBFILE_FACEBLOCK) - + sizeof(T_HOBFILE_FACES_HEADER) - + sizeof(T_HOBFILE_FACES_HEADER) * k - + facesExtraOffset))->v2_rgba; - hob_struct->objects[i].object_parts[j].faces[k].vertex_colors[2] = ((T_HOBFILE_FACES_VERTEX_COLOR *)(memFile - + hob_struct->objects[i].object_parts[j].face_block_offset - + sizeof(T_HOBFILE_FACEBLOCK) - + sizeof(T_HOBFILE_FACES_HEADER) - + sizeof(T_HOBFILE_FACES_HEADER) * k - + facesExtraOffset))->v3_rgba; - if (hob_struct->objects[i].object_parts[j].faces[k].flags_bits.fIsQuad) { - hob_struct->objects[i].object_parts[j].faces[k].vertex_colors[3] = ((T_HOBFILE_FACES_VERTEX_COLOR *)(memFile - + hob_struct->objects[i].object_parts[j].face_block_offset - + sizeof(T_HOBFILE_FACEBLOCK) - + sizeof(T_HOBFILE_FACES_HEADER) - + sizeof(T_HOBFILE_FACES_HEADER) * k - + facesExtraOffset))->v4_rgba; - facesExtraOffset += sizeof(T_HOBFILE_FACES_VERTEX_COLOR); - } else { - facesExtraOffset += sizeof(T_HOBFILE_FACES_VERTEX_COLOR) - sizeof(T_RGBA); - } - } else { - hob_struct->objects[i].object_parts[j].faces[k].vertex_colors[0] = ((T_HOBFILE_FACES_COLOR *)(memFile - + hob_struct->objects[i].object_parts[j].face_block_offset - + sizeof(T_HOBFILE_FACEBLOCK) - + sizeof(T_HOBFILE_FACES_HEADER) - + sizeof(T_HOBFILE_FACES_HEADER) * k - + facesExtraOffset))->rgba; - hob_struct->objects[i].object_parts[j].faces[k].vertex_colors[1] = ((T_HOBFILE_FACES_COLOR *)(memFile - + hob_struct->objects[i].object_parts[j].face_block_offset - + sizeof(T_HOBFILE_FACEBLOCK) - + sizeof(T_HOBFILE_FACES_HEADER) - + sizeof(T_HOBFILE_FACES_HEADER) * k - + facesExtraOffset))->rgba; - hob_struct->objects[i].object_parts[j].faces[k].vertex_colors[2] = ((T_HOBFILE_FACES_COLOR *)(memFile - + hob_struct->objects[i].object_parts[j].face_block_offset - + sizeof(T_HOBFILE_FACEBLOCK) - + sizeof(T_HOBFILE_FACES_HEADER) - + sizeof(T_HOBFILE_FACES_HEADER) * k - + facesExtraOffset))->rgba; - hob_struct->objects[i].object_parts[j].faces[k].vertex_colors[3] = ((T_HOBFILE_FACES_COLOR *)(memFile - + hob_struct->objects[i].object_parts[j].face_block_offset - + sizeof(T_HOBFILE_FACEBLOCK) - + sizeof(T_HOBFILE_FACES_HEADER) - + sizeof(T_HOBFILE_FACES_HEADER) * k - + facesExtraOffset))->rgba; - facesExtraOffset += sizeof(T_HOBFILE_FACES_COLOR); - } - } - - // Get UV map - if present - if (hob_struct->objects[i].object_parts[j].faces[k].flags_bits.fHasTexture) { - hob_struct->objects[i].object_parts[j].faces[k].tex_coords[0] = ((T_HOBFILE_FACES_VERTEX_TEXTURE *)(memFile - + hob_struct->objects[i].object_parts[j].face_block_offset - + sizeof(T_HOBFILE_FACEBLOCK) - + sizeof(T_HOBFILE_FACES_HEADER) - + sizeof(T_HOBFILE_FACES_HEADER) * k - + facesExtraOffset))->v1_texcoord; - hob_struct->objects[i].object_parts[j].faces[k].tex_coords[1] = ((T_HOBFILE_FACES_VERTEX_TEXTURE *)(memFile - + hob_struct->objects[i].object_parts[j].face_block_offset - + sizeof(T_HOBFILE_FACEBLOCK) - + sizeof(T_HOBFILE_FACES_HEADER) - + sizeof(T_HOBFILE_FACES_HEADER) * k - + facesExtraOffset))->v2_texcoord; - hob_struct->objects[i].object_parts[j].faces[k].tex_coords[2] = ((T_HOBFILE_FACES_VERTEX_TEXTURE *)(memFile - + hob_struct->objects[i].object_parts[j].face_block_offset - + sizeof(T_HOBFILE_FACEBLOCK) - + sizeof(T_HOBFILE_FACES_HEADER) - + sizeof(T_HOBFILE_FACES_HEADER) * k - + facesExtraOffset))->v3_texcoord; - if (hob_struct->objects[i].object_parts[j].faces[k].flags_bits.fIsQuad) { - hob_struct->objects[i].object_parts[j].faces[k].tex_coords[3] = ((T_HOBFILE_FACES_VERTEX_TEXTURE *)(memFile - + hob_struct->objects[i].object_parts[j].face_block_offset - + sizeof(T_HOBFILE_FACEBLOCK) - + sizeof(T_HOBFILE_FACES_HEADER) - + sizeof(T_HOBFILE_FACES_HEADER) * k - + facesExtraOffset))->v4_texcoord; - facesExtraOffset += sizeof(T_HOBFILE_FACES_VERTEX_TEXTURE); - } else { - facesExtraOffset += sizeof(T_HOBFILE_FACES_VERTEX_TEXTURE) - sizeof(T_TEXCOORD); - } - } - - if (p_opts->debug_mode) { - printf("[DBG] > Face %d details: flags:0x%X b1:%d b2:%d b3%d bsize:%d\n", k, - hob_struct->objects[i].object_parts[j].faces[k].flags, - hob_struct->objects[i].object_parts[j].faces[k].b1, - hob_struct->objects[i].object_parts[j].faces[k].b2, - hob_struct->objects[i].object_parts[j].faces[k].b3, - hob_struct->objects[i].object_parts[j].faces[k].bsize - ); - printf("[DBG] - Type is Quad: %d\n", hob_struct->objects[i].object_parts[j].faces[k].flags_bits.fIsQuad); - printf("[DBG] - Material offset: 0x%X\n", hob_struct->objects[i].object_parts[j].faces[k].material_index); - printf("[DBG] - Vertex indices: %d, %d, %d, %d\n", - hob_struct->objects[i].object_parts[j].faces[k].indices[0], - hob_struct->objects[i].object_parts[j].faces[k].indices[1], - hob_struct->objects[i].object_parts[j].faces[k].indices[2], - hob_struct->objects[i].object_parts[j].faces[k].indices[3] - ); - printf("[DBG] - Vertex colors: 0x%X, 0x%X, 0x%X, 0x%X\n", - hob_struct->objects[i].object_parts[j].faces[k].vertex_colors[0], - hob_struct->objects[i].object_parts[j].faces[k].vertex_colors[1], - hob_struct->objects[i].object_parts[j].faces[k].vertex_colors[2], - hob_struct->objects[i].object_parts[j].faces[k].vertex_colors[3] - ); - printf("[DBG] - Vertex UV coord (divided by 4096):\n"); - printf("[DBG] > %.8f(%d), %.8f(%d)\n", - ((double) 1/4096) * hob_struct->objects[i].object_parts[j].faces[k].tex_coords[0].u, - hob_struct->objects[i].object_parts[j].faces[k].tex_coords[0].u, - ((double) 1/4096) * hob_struct->objects[i].object_parts[j].faces[k].tex_coords[0].v, - hob_struct->objects[i].object_parts[j].faces[k].tex_coords[0].v - ); - printf("[DBG] > %.8f(%d), %.8f(%d)\n", - ((double) 1/4096) * hob_struct->objects[i].object_parts[j].faces[k].tex_coords[1].u, - hob_struct->objects[i].object_parts[j].faces[k].tex_coords[1].u, - ((double) 1/4096) * hob_struct->objects[i].object_parts[j].faces[k].tex_coords[1].v, - hob_struct->objects[i].object_parts[j].faces[k].tex_coords[1].v - ); - printf("[DBG] > %.8f(%d), %.8f(%d)\n", - ((double) 1/4096) * hob_struct->objects[i].object_parts[j].faces[k].tex_coords[2].u, - hob_struct->objects[i].object_parts[j].faces[k].tex_coords[2].u, - ((double) 1/4096) * hob_struct->objects[i].object_parts[j].faces[k].tex_coords[2].v, - hob_struct->objects[i].object_parts[j].faces[k].tex_coords[2].v - ); - printf("[DBG] > %.8f(%d), %.8f(%d)\n", - ((double) 1/4096) * hob_struct->objects[i].object_parts[j].faces[k].tex_coords[3].u, - hob_struct->objects[i].object_parts[j].faces[k].tex_coords[3].u, - ((double) 1/4096) * hob_struct->objects[i].object_parts[j].faces[k].tex_coords[3].v, - hob_struct->objects[i].object_parts[j].faces[k].tex_coords[3].v - ); - printf("\n"); - } - - if (p_opts->debug_mode) printf("\n-----------------------End of FaceGroup part-----------------------\n"); - } - - // Get vertex datas - ExtractObjpartVertices(&hob_struct->objects[i].object_parts[j], memFile, p_opts->debug_mode); - } - - // Get object part ID, used by animation? bones? - hob_struct->objects[i].object_parts[j].id = ((T_HOBFILE_MESHDEF0 *)(memFile + offset_index[j]))->object_id; - if (p_opts->verbose_mode) printf("\n[DBG] > Facegroup/object ID: %d\n", hob_struct->objects[i].object_parts[j].id); - - // Get the transform matrix, used by at-st and at-at (at this time) - hob_struct->objects[i].object_parts[j].transform.x = ((T_HOBFILE_MESHDEF0 *)(memFile + offset_index[j]))->transform_x; - hob_struct->objects[i].object_parts[j].transform.y = ((T_HOBFILE_MESHDEF0 *)(memFile + offset_index[j]))->transform_y; - hob_struct->objects[i].object_parts[j].transform.z = ((T_HOBFILE_MESHDEF0 *)(memFile + offset_index[j]))->transform_z; - if (p_opts->god_mode) printf("\n[DBG] > Facegroup/object transform matrix: [%.8f %.8f %.8f]\n", - hob_struct->objects[i].object_parts[j].transform.x, - hob_struct->objects[i].object_parts[j].transform.y, - hob_struct->objects[i].object_parts[j].transform.z - ); - - if (p_opts->debug_mode) printf("\n-----------------------End of Mesh part---------------------------\n"); - } - - if (p_opts->debug_mode) printf("\n-=====================-End of Object part-========================-\n"); - } - - free(offset_index); - - } else { - err = RSPLIB_ERROR_GENERIC; - printf("[INFO] Can't process empty file!\n"); - } - */ + err = ExtractObjects(hob_struct, memFile, p_opts->verbose_mode + p_opts->debug_mode + p_opts->god_mode); free(memFile); @@ -410,11 +85,16 @@ unsigned char RSP_ModelLib_ParseHOBFile(const char* fileName, T_RSPMODEL_HOB* ho return err; } + +//////////////////////////////////////////////////////////////////////////////// +// Private functions definition +//////////////////////////////////////////////////////////////////////////////// + /** - * Count objects and extract datas from them. + * @brief Count objects and extract datas from them. * * @param[in|out] pHobStruct Take root hob structure to get the T_RSPMODEL_OBJECT buffer and header datas. - * @param[in] pMemfile + * @param[in] pMemfile Pointer to an in-memory file location. * @param[in] verbose * * @return Error code, RSPLIB_SUCCESS when no error. @@ -483,10 +163,10 @@ static unsigned int ExtractObjects(T_RSPMODEL_HOB* pHobStruct, const MEMFILE pMe } /** - * Count object's sub-part and extract datas from them. + * @brief Count object's sub-part and extract datas from them. * * @param[in|out] pObject Take object structure to get the T_RSPMODEL_OBJ_PARTS buffer and object datas. - * @param[in] pMemfile + * @param[in] pMemfile Pointer to an in-memory file location. * @param[in] verbose * * @return Error code, RSPLIB_SUCCESS when no error. @@ -564,111 +244,111 @@ static unsigned int ExtractObjParts(T_RSPMODEL_OBJECT* pObject, const MEMFILE pM } /** - * Extract datas from faces in object sub-part. + * @brief Extract datas from faces from object sub-part. * - * @param[in|out] pObjParts - * @param[in] pMemfile + * @param[in|out] pObjPart Take object sub-part structure to get the T_RSPMODEL_FACE buffer and object sub-part datas. + * @param[in] pMemfile Pointer to an in-memory file location. * @param[in] verbose * * @return Error code, RSPLIB_SUCCESS when no error. */ -static unsigned int ExtractObjParts_faces(T_RSPMODEL_OBJ_PARTS* pObjParts, const MEMFILE pMemfile, const unsigned char verbose) { +static unsigned int ExtractObjParts_faces(T_RSPMODEL_OBJ_PARTS* pObjPart, const MEMFILE pMemfile, const unsigned char verbose) { unsigned int i, facesExtraOffset = 0; - if (pObjParts == NULL || pMemfile == NULL) return RSPLIB_ERROR_ARGS_NULL; + if (pObjPart == NULL || pMemfile == NULL) return RSPLIB_ERROR_ARGS_NULL; - if( ((T_HOBFILE_FACEBLOCK *)(pMemfile + pObjParts->face_block_offset))->reserved1 != 0 || - ((T_HOBFILE_FACEBLOCK *)(pMemfile + pObjParts->face_block_offset))->reserved2 != 0 ) { + if( ((T_HOBFILE_FACEBLOCK *)(pMemfile + pObjPart->face_block_offset))->reserved1 != 0 || + ((T_HOBFILE_FACEBLOCK *)(pMemfile + pObjPart->face_block_offset))->reserved2 != 0 ) { if (verbose == 3) printf("[DBG] > Face block: uncommon zero header!\n"); } - if ( ((T_HOBFILE_FACEBLOCK *)(pMemfile + pObjParts->face_block_offset))->facesOffset != - pObjParts->face_block_offset + sizeof(T_HOBFILE_FACEBLOCK)) { + if ( ((T_HOBFILE_FACEBLOCK *)(pMemfile + pObjPart->face_block_offset))->facesOffset != + pObjPart->face_block_offset + sizeof(T_HOBFILE_FACEBLOCK)) { if (verbose == 3) printf("[DBG] > Face block: uncommon face data offset position!\n"); } - pObjParts->face_count = ((T_HOBFILE_FACEBLOCK *)(pMemfile + pObjParts->face_block_offset))->faceCounts; - pObjParts->faces = calloc(pObjParts->face_count, sizeof(T_RSPMODEL_FACE)); - for ( i = 0; i < pObjParts->face_count; i++ ) { + pObjPart->face_count = ((T_HOBFILE_FACEBLOCK *)(pMemfile + pObjPart->face_block_offset))->faceCounts; + pObjPart->faces = calloc(pObjPart->face_count, sizeof(T_RSPMODEL_FACE)); + for ( i = 0; i < pObjPart->face_count; i++ ) { if (verbose == 2) printf("\n----------------------Begin of FaceGroup part----------------------\n"); // Get flags - pObjParts->faces[i].flags = ((T_HOBFILE_FACES_HEADER *)(pMemfile + pObjParts->face_block_offset + pObjPart->faces[i].flags = ((T_HOBFILE_FACES_HEADER *)(pMemfile + pObjPart->face_block_offset + sizeof(T_HOBFILE_FACEBLOCK) + sizeof(T_HOBFILE_FACES_HEADER) * i + facesExtraOffset))->flags; // Get unknown bytes - pObjParts->faces[i].b1 = ((T_HOBFILE_FACES_HEADER *)(pMemfile + pObjParts->face_block_offset + pObjPart->faces[i].b1 = ((T_HOBFILE_FACES_HEADER *)(pMemfile + pObjPart->face_block_offset + sizeof(T_HOBFILE_FACEBLOCK) + sizeof(T_HOBFILE_FACES_HEADER) * i + facesExtraOffset))->b1; - pObjParts->faces[i].b2 = ((T_HOBFILE_FACES_HEADER *)(pMemfile + pObjParts->face_block_offset + pObjPart->faces[i].b2 = ((T_HOBFILE_FACES_HEADER *)(pMemfile + pObjPart->face_block_offset + sizeof(T_HOBFILE_FACEBLOCK) + sizeof(T_HOBFILE_FACES_HEADER) * i + facesExtraOffset))->b2; - pObjParts->faces[i].b3 = ((T_HOBFILE_FACES_HEADER *)(pMemfile + pObjParts->face_block_offset + pObjPart->faces[i].b3 = ((T_HOBFILE_FACES_HEADER *)(pMemfile + pObjPart->face_block_offset + sizeof(T_HOBFILE_FACEBLOCK) + sizeof(T_HOBFILE_FACES_HEADER) * i + facesExtraOffset))->b3; - pObjParts->faces[i].bsize = ((T_HOBFILE_FACES_HEADER *)(pMemfile + pObjParts->face_block_offset + pObjPart->faces[i].bsize = ((T_HOBFILE_FACES_HEADER *)(pMemfile + pObjPart->face_block_offset + sizeof(T_HOBFILE_FACEBLOCK) + sizeof(T_HOBFILE_FACES_HEADER) * i + facesExtraOffset))->faceBlockIntSize * 4; // Multiply by 4 to get the bytes exact number - if (((T_HOBFILE_FACES_HEADER *)(pMemfile + pObjParts->face_block_offset + sizeof(T_HOBFILE_FACEBLOCK) + if (((T_HOBFILE_FACES_HEADER *)(pMemfile + pObjPart->face_block_offset + sizeof(T_HOBFILE_FACEBLOCK) + sizeof(T_HOBFILE_FACES_HEADER) * i + facesExtraOffset))->headerSeparator != 0) { if (verbose == 3) printf("[DBG] > Face header: uncommon separator!\n"); } // Get materials index - pObjParts->faces[i].material_index = ((T_HOBFILE_FACES_HEADER *)(pMemfile + pObjParts->face_block_offset + pObjPart->faces[i].material_index = ((T_HOBFILE_FACES_HEADER *)(pMemfile + pObjPart->face_block_offset + sizeof(T_HOBFILE_FACEBLOCK) + sizeof(T_HOBFILE_FACES_HEADER) * i + facesExtraOffset))->materialIndex; // Get vertex indices - memcpy(pObjParts->faces[i].indices, ((T_HOBFILE_FACES_HEADER *)(pMemfile + pObjParts->face_block_offset + memcpy(pObjPart->faces[i].indices, ((T_HOBFILE_FACES_HEADER *)(pMemfile + pObjPart->face_block_offset + sizeof(T_HOBFILE_FACEBLOCK) + sizeof(T_HOBFILE_FACES_HEADER) * i + facesExtraOffset))->vertexIndices, sizeof(unsigned short) * 4); // Recalculate the dynamic extra bytes offset size - if present - if (pObjParts->faces[i].flags_bits.fHasExtraBytesBeforeColor) facesExtraOffset += 8; + if (pObjPart->faces[i].flags_bits.fHasExtraBytesBeforeColor) facesExtraOffset += 8; // Get vertex color - if present - if (pObjParts->faces[i].flags_bits.fHasColor) { - facesExtraOffset += ExtractObjpart_Face_Colors(&pObjParts->faces[i], pMemfile + pObjParts->face_block_offset + if (pObjPart->faces[i].flags_bits.fHasColor) { + facesExtraOffset += ExtractObjpart_Face_Colors(&pObjPart->faces[i], pMemfile + pObjPart->face_block_offset + sizeof(T_HOBFILE_FACEBLOCK) + sizeof(T_HOBFILE_FACES_HEADER) + sizeof(T_HOBFILE_FACES_HEADER) * i + facesExtraOffset); } // Get UV map - if present - if (pObjParts->faces[i].flags_bits.fHasTexture) { - facesExtraOffset += ExtractObjpart_Face_UVMaps(&pObjParts->faces[i], pMemfile + pObjParts->face_block_offset + if (pObjPart->faces[i].flags_bits.fHasTexture) { + facesExtraOffset += ExtractObjpart_Face_UVMaps(&pObjPart->faces[i], pMemfile + pObjPart->face_block_offset + sizeof(T_HOBFILE_FACEBLOCK) + sizeof(T_HOBFILE_FACES_HEADER) + sizeof(T_HOBFILE_FACES_HEADER) * i + facesExtraOffset); } if (verbose == 2) { - printf("[DBG] > Face %d details: flags:0x%X b1:%d b2:%d b3%d bsize:%d\n", i, pObjParts->faces[i].flags, - pObjParts->faces[i].b1, pObjParts->faces[i].b2, pObjParts->faces[i].b3, pObjParts->faces[i].bsize); - printf("[DBG] - Type is Quad: %d\n", pObjParts->faces[i].flags_bits.fIsQuad); - printf("[DBG] - Material offset: 0x%X\n", pObjParts->faces[i].material_index); - printf("[DBG] - Vertex indices: %d, %d, %d, %d\n", pObjParts->faces[i].indices[0], pObjParts->faces[i].indices[1], - pObjParts->faces[i].indices[2], pObjParts->faces[i].indices[3]); - printf("[DBG] - Vertex colors: 0x%X, 0x%X, 0x%X, 0x%X\n", pObjParts->faces[i].vertex_colors[0], - pObjParts->faces[i].vertex_colors[1], pObjParts->faces[i].vertex_colors[2], pObjParts->faces[i].vertex_colors[3]); + printf("[DBG] > Face %d details: flags:0x%X b1:%d b2:%d b3%d bsize:%d\n", i, pObjPart->faces[i].flags, + pObjPart->faces[i].b1, pObjPart->faces[i].b2, pObjPart->faces[i].b3, pObjPart->faces[i].bsize); + printf("[DBG] - Type is Quad: %d\n", pObjPart->faces[i].flags_bits.fIsQuad); + printf("[DBG] - Material offset: 0x%X\n", pObjPart->faces[i].material_index); + printf("[DBG] - Vertex indices: %d, %d, %d, %d\n", pObjPart->faces[i].indices[0], pObjPart->faces[i].indices[1], + pObjPart->faces[i].indices[2], pObjPart->faces[i].indices[3]); + printf("[DBG] - Vertex colors: 0x%X, 0x%X, 0x%X, 0x%X\n", pObjPart->faces[i].vertex_colors[0], + pObjPart->faces[i].vertex_colors[1], pObjPart->faces[i].vertex_colors[2], pObjPart->faces[i].vertex_colors[3]); printf("[DBG] - Vertex UV coord (divided by 4096):\n"); printf("[DBG] > %.8f(%d), %.8f(%d)\n", - ((double) 1/4096) * pObjParts->faces[i].tex_coords[0].u, - pObjParts->faces[i].tex_coords[0].u, - ((double) 1/4096) * pObjParts->faces[i].tex_coords[0].v, - pObjParts->faces[i].tex_coords[0].v + ((double) 1/4096) * pObjPart->faces[i].tex_coords[0].u, + pObjPart->faces[i].tex_coords[0].u, + ((double) 1/4096) * pObjPart->faces[i].tex_coords[0].v, + pObjPart->faces[i].tex_coords[0].v ); printf("[DBG] > %.8f(%d), %.8f(%d)\n", - ((double) 1/4096) * pObjParts->faces[i].tex_coords[1].u, - pObjParts->faces[i].tex_coords[1].u, - ((double) 1/4096) * pObjParts->faces[i].tex_coords[1].v, - pObjParts->faces[i].tex_coords[1].v + ((double) 1/4096) * pObjPart->faces[i].tex_coords[1].u, + pObjPart->faces[i].tex_coords[1].u, + ((double) 1/4096) * pObjPart->faces[i].tex_coords[1].v, + pObjPart->faces[i].tex_coords[1].v ); printf("[DBG] > %.8f(%d), %.8f(%d)\n", - ((double) 1/4096) * pObjParts->faces[i].tex_coords[2].u, - pObjParts->faces[i].tex_coords[2].u, - ((double) 1/4096) * pObjParts->faces[i].tex_coords[2].v, - pObjParts->faces[i].tex_coords[2].v + ((double) 1/4096) * pObjPart->faces[i].tex_coords[2].u, + pObjPart->faces[i].tex_coords[2].u, + ((double) 1/4096) * pObjPart->faces[i].tex_coords[2].v, + pObjPart->faces[i].tex_coords[2].v ); printf("[DBG] > %.8f(%d), %.8f(%d)\n", - ((double) 1/4096) * pObjParts->faces[i].tex_coords[3].u, - pObjParts->faces[i].tex_coords[3].u, - ((double) 1/4096) * pObjParts->faces[i].tex_coords[3].v, - pObjParts->faces[i].tex_coords[3].v + ((double) 1/4096) * pObjPart->faces[i].tex_coords[3].u, + pObjPart->faces[i].tex_coords[3].u, + ((double) 1/4096) * pObjPart->faces[i].tex_coords[3].v, + pObjPart->faces[i].tex_coords[3].v ); printf("\n"); } @@ -677,30 +357,39 @@ static unsigned int ExtractObjParts_faces(T_RSPMODEL_OBJ_PARTS* pObjParts, const } // Get vertex datas - pObjParts->vertices = calloc(pObjParts->vertex_count, sizeof(T_VERTEX)); - if (pObjParts->vertices == NULL) return RSPLIB_ERROR_MEMORY; + pObjPart->vertices = calloc(pObjPart->vertex_count, sizeof(T_VERTEX)); + if (pObjPart->vertices == NULL) return RSPLIB_ERROR_MEMORY; - for ( i = 0; i < pObjParts->vertex_count; i++ ) { - pObjParts->vertices[i].x = - ((T_HOBFILE_VERTEX *)(pMemfile + pObjParts->vertex_block_offset + sizeof(T_VERTEX) * i))->x; + for ( i = 0; i < pObjPart->vertex_count; i++ ) { + pObjPart->vertices[i].x = + ((T_HOBFILE_VERTEX *)(pMemfile + pObjPart->vertex_block_offset + sizeof(T_VERTEX) * i))->x; - pObjParts->vertices[i].y = - ((T_HOBFILE_VERTEX *)(pMemfile + pObjParts->vertex_block_offset + sizeof(T_VERTEX) * i))->y; + pObjPart->vertices[i].y = + ((T_HOBFILE_VERTEX *)(pMemfile + pObjPart->vertex_block_offset + sizeof(T_VERTEX) * i))->y; - pObjParts->vertices[i].z = - ((T_HOBFILE_VERTEX *)(pMemfile + pObjParts->vertex_block_offset + sizeof(T_VERTEX) * i))->z; + pObjPart->vertices[i].z = + ((T_HOBFILE_VERTEX *)(pMemfile + pObjPart->vertex_block_offset + sizeof(T_VERTEX) * i))->z; - pObjParts->vertices[i].w = - ((T_HOBFILE_VERTEX *)(pMemfile + pObjParts->vertex_block_offset + sizeof(T_VERTEX) * i))->w; // Always 0??? + pObjPart->vertices[i].w = + ((T_HOBFILE_VERTEX *)(pMemfile + pObjPart->vertex_block_offset + sizeof(T_VERTEX) * i))->w; // Always 0??? if (verbose == 2) printf("[DBG] > Found vertex %d: (%d, %d, %d)\n", i, - pObjParts->vertices[i].x, pObjParts->vertices[i].y, pObjParts->vertices[i].z + pObjPart->vertices[i].x, pObjPart->vertices[i].y, pObjPart->vertices[i].z ); } return RSPLIB_SUCCESS; } +/** + * @brief Extract colors from HOB's face to T_RSPMODEL_FACE instance. + * + * @param pFace[out] Pointer to an empty instance of T_RSPMODEL_FACE. + * @param pFaceMemFileOffset[in] Pointer to the in-memory location of face HOB datas. + * @warning Access to an unallocated memory location using this function result in an ACCESS_VIOLATION. + * + * @return The size of processed data. Used to count new offset between each face in object sub-part. + */ static inline unsigned int ExtractObjpart_Face_Colors(T_RSPMODEL_FACE* pFace, const char* pFaceMemFileOffset) { unsigned int dynOffset = 0; @@ -725,6 +414,15 @@ static inline unsigned int ExtractObjpart_Face_Colors(T_RSPMODEL_FACE* pFace, co return dynOffset; } +/** + * @brief Extract UV maps from HOB's face to T_RSPMODEL_FACE instance. + * + * @param pFace[out] Pointer to an empty instance of T_RSPMODEL_FACE. + * @param pFaceMemFileOffset[in] Pointer to the in-memory location of face HOB datas. + * @warning Access to an unallocated memory location using this function result in an ACCESS_VIOLATION. + * + * @return The size of processed data. Used to count new offset between each face in object sub-part. + */ static inline unsigned int ExtractObjpart_Face_UVMaps(T_RSPMODEL_FACE* pFace, const char* pFaceMemFileOffset) { unsigned int dynOffset = 0; diff --git a/RSPModelLib/src/hob_parser.h b/RSPModelLib/src/hob_parser.h index 31094df..1c4e8ec 100644 --- a/RSPModelLib/src/hob_parser.h +++ b/RSPModelLib/src/hob_parser.h @@ -1,9 +1,9 @@ /** * @file hob_parser.h - * @date 26/07/2022 + * @date 18/08/2022 * @author JackCarterSmith * @copyright GPL-v3.0 - * @brief Decode HOB file structure. + * @brief Process HOB file structure and extract its datas. * */ @@ -14,8 +14,39 @@ #ifndef SRC_HOB_PARSER_H_ #define SRC_HOB_PARSER_H_ -typedef char* MEMFILE; +/** + * @brief Process HOB file stored in memory. + * @details Parser will directly extract objects count and information stored in + * HOB file and store them in T_RSPMODEL_HOB structure. + * @note Unmanaged mode + * + * @param[in] pMemFile Pointer to an in-memory HOB file location. + * @param[out] hob_struct Allocated empty T_RSPMODEL_HOB structure instance to + * be filled with HOB datas. + * @param[in] p_opts Parser options. DEPRECATED. + * + * @return Processing error code, RSPLIB_SUCCESS if no error. + */ +unsigned char RSP_ModelLib_ParseHOBMemFile(const MEMFILE pMemFile, + T_RSPMODEL_HOB* hob_struct, T_PROG_OPTIONS* p_opts); -unsigned char RSP_ModelLib_ParseHOBFile(const char* fileName, T_RSPMODEL_HOB* hob_struct, T_PROG_OPTIONS* p_opts); +/** + * @brief Process HOB file in file system. + * @details HOB file is dumped in memory before parsing in order to enhance + * performance during parser operation and in optic to protect data + * stored in the original file (read-only). + * Parser will extract objects count and information stored in HOB file + * and store them in T_RSPMODEL_HOB structure. + * @note Managed mode + * + * @param[in] fileName String value of file name/path. + * @param[out] hob_struct Allocated empty T_RSPMODEL_HOB structure instance to + * be filled with HOB datas. + * @param[in] p_opts Parser options. DEPRECATED. + * + * @return Processing error code, RSPLIB_SUCCESS if no error. + */ +unsigned char RSP_ModelLib_ParseHOBFile(const char* fileName, + T_RSPMODEL_HOB* hob_struct, T_PROG_OPTIONS* p_opts); #endif /* SRC_HOB_PARSER_H_ */ -- 2.39.5 From be65b73bb668e209718d5d459aa898a9e8e02d8b Mon Sep 17 00:00:00 2001 From: JackCarterSmith Date: Fri, 19 Aug 2022 18:17:01 +0200 Subject: [PATCH 12/15] Upgraded obj lib and interface --- .gitmodules | 6 +-- README.md | 6 +-- RSEModel/src/Model-Extractor.c | 4 +- RSEModel/src/obj | 1 + RSEModel/src/obj_exporter.c | 93 ++++++++-------------------------- RSEModel/src/rlk | 1 - 6 files changed, 30 insertions(+), 81 deletions(-) create mode 160000 RSEModel/src/obj delete mode 160000 RSEModel/src/rlk diff --git a/.gitmodules b/.gitmodules index b20867d..019124d 100644 --- a/.gitmodules +++ b/.gitmodules @@ -1,3 +1,3 @@ -[submodule "RSEModel/src/rlk"] - path = RSEModel/src/rlk - url = https://github.com/rlk/obj.git +[submodule "RSEModel/src/obj"] + path = RSEModel/src/obj + url = https://git.jcsmith.fr/jackcartersmith/obj.git \ No newline at end of file diff --git a/README.md b/README.md index 275bdee..4c31120 100644 --- a/README.md +++ b/README.md @@ -25,7 +25,7 @@ This module can do: ### Using -`RSE-Model_"version" [options] ` or you can simply drag&drop HOB files on it. +`RSEModel [options] ` or you can simply drag&drop HOB files on it. A futur main program can extract all HOB files directly from DAT file. Due to issue with copyrights, I can't provide samples... You need to extract HOB files yourself. @@ -37,11 +37,11 @@ Due to issue with copyrights, I can't provide samples... You need to extract HOB - -h Print this message - -v,-vv Activate verbose/debug output mode respectively - -no-subdir Extract textures directly inside current folder -- -no-mtl Disable materials datas export with OBJ model +- -mtl Export materials datas with OBJ model ### Dependencies -- obj-lib: as obj file exporter. (https://github.com/rlk/obj) +- obj-lib: as obj file exporter. (https://git.jcsmith.fr/jackcartersmith/obj) ### Compiling diff --git a/RSEModel/src/Model-Extractor.c b/RSEModel/src/Model-Extractor.c index 07e5402..f8ae431 100644 --- a/RSEModel/src/Model-Extractor.c +++ b/RSEModel/src/Model-Extractor.c @@ -130,7 +130,7 @@ static unsigned char checkInputArgs(T_PROG_OPTIONS* opt_ptr, int p_arg_nbr, char opt_ptr->output_dir = 0; printf("[OPTN] Export to current directory.\n"); } else if (strcmp(p_args[i], "-mtl") == 0) { - opt_ptr->export_mtl = 0; + opt_ptr->export_mtl = 1; printf("[OPTN] Export materials datas.\n"); } else { printf("[ERR] Unknown option: %s\n", p_args[i]); @@ -179,7 +179,7 @@ static void dispHelp() { printf("Options:\n -h Print this message\n"); printf(" -v -vv Activate verbose console output\n"); printf(" -no-subdir Export models inside current folder\n"); - //printf(" -mtl Export materials datas with model\n"); + printf(" -mtl Export materials datas with model\n"); printf("\n"); printf("Usage: RSE-Model_%s [options] \n", PRG_VERSION); printf("\n"); diff --git a/RSEModel/src/obj b/RSEModel/src/obj new file mode 160000 index 0000000..09f8716 --- /dev/null +++ b/RSEModel/src/obj @@ -0,0 +1 @@ +Subproject commit 09f87160bb80d1ad331c697000ecd7a122f9ef60 diff --git a/RSEModel/src/obj_exporter.c b/RSEModel/src/obj_exporter.c index 1067010..42f3e14 100644 --- a/RSEModel/src/obj_exporter.c +++ b/RSEModel/src/obj_exporter.c @@ -13,15 +13,14 @@ #include "options.h" #include #include -#include "rlk/obj.h" +#include "obj/obj.h" #include "obj_exporter.h" -static void mtlPathPatch(const char* out_file, const char* obj_name) ; - unsigned char exportOBJModel(T_RSPMODEL_OBJECT* hob_objects, const char *out_path, T_PROG_OPTIONS* p_opts) { - char objExport_path[128]; - char mtlExport_path[128]; + char exportPath[1024]; + char objExport_name[128]; + char mtlExport_name[128]; obj* objConstruct = NULL; unsigned int i,j; int surfID = 0, materialID = 0, tmpVertex = 0, tmpIndex = 0; @@ -32,20 +31,13 @@ unsigned char exportOBJModel(T_RSPMODEL_OBJECT* hob_objects, const char *out_pat if (hob_objects == NULL || out_path == NULL) return RSPLIB_ERROR_ARGS_NULL; - if (p_opts->output_dir) { - strcpy(objExport_path, out_path); - #ifdef _WIN32 - strcat(objExport_path, "-out\\"); - #else - strcat(objExport_path, "-out/"); - #endif - strcat(objExport_path, hob_objects->name); - } else { - strcpy(objExport_path, hob_objects->name); - } - strcpy(mtlExport_path, objExport_path); - strcat(objExport_path, ".obj\0"); - strcat(mtlExport_path, ".mtl\0"); +#ifdef _WIN32 + sprintf_s(exportPath, 1024, "%s-out\\", out_path, hob_objects->name); +#else + sprintf_s(exportPath, 1024, "%s-out/", out_path, hob_objects->name); +#endif + sprintf_s(objExport_name, 128, "%s.obj", hob_objects->name); + sprintf_s(mtlExport_name, 128, "%s.mtl", hob_objects->name); objConstruct = obj_create(NULL); @@ -108,61 +100,18 @@ unsigned char exportOBJModel(T_RSPMODEL_OBJECT* hob_objects, const char *out_pat } if (p_opts->export_mtl) { - obj_write(objConstruct, objExport_path, mtlExport_path, 8); -#if defined(__GNUC__) //TODO: review MSVC file management or include and rewrite obj lib? - if (p_opts->output_dir) mtlPathPatch(objExport_path, hob_objects->name); -#endif - } else obj_write(objConstruct, objExport_path, NULL, 8); + if (p_opts->output_dir) + obj_write(objConstruct, objExport_name, mtlExport_name, exportPath, 8); + else + obj_write(objConstruct, objExport_name, mtlExport_name, NULL, 8); + } else { + if (p_opts->output_dir) + obj_write(objConstruct, objExport_name, NULL, exportPath, 8); + else + obj_write(objConstruct, objExport_name, NULL, NULL, 8); + } obj_delete(objConstruct); return RSPLIB_SUCCESS; } - -static void mtlPathPatch(const char* out_file, const char* obj_name) { - FILE* obj = NULL; - char* memFile = NULL; - long fileSize,i,pos = 0,lines = 0; - char _path[128],b; - - obj = fopen(out_file, "r"); - if ( obj != NULL ) { - fseek(obj, 0, SEEK_END); - fileSize = ftell(obj); - fseek(obj, 0, SEEK_SET); - - // Find the end of first line - for ( i = 0; i < fileSize + 1; i++) { - b = (char)fgetc(obj); - if (b == '\n') { - if (pos == 0) pos = i; - lines++; - } - } - - // Prepare mtl path for output - strcpy(_path, obj_name); - strcat(_path, ".mtl"); - - memFile = malloc(fileSize - (pos + lines)); - if ( memFile != NULL ) { - // Read the rest of file in memory - fseek(obj, pos, SEEK_SET); - fread(memFile, fileSize - (pos + lines), 1, obj); - fclose(obj); - - // Begin rewrite file - obj = fopen(out_file, "w"); - fprintf(obj, "mtllib %s", _path); -#if defined(_MSC_VER) - fwrite(memFile, fileSize - pos , 1, obj); -#elif defined(__GNUC__) - fwrite(memFile, fileSize - (pos + lines), 1, obj); -#endif - - free(memFile); - } - - fclose(obj); - } -} diff --git a/RSEModel/src/rlk b/RSEModel/src/rlk deleted file mode 160000 index 48a6916..0000000 --- a/RSEModel/src/rlk +++ /dev/null @@ -1 +0,0 @@ -Subproject commit 48a6916526d043691bb3f9e38676fbc99995da10 -- 2.39.5 From aa2d52768ad526310d33423ca49880729b20e75f Mon Sep 17 00:00:00 2001 From: JackCarterSmith Date: Fri, 19 Aug 2022 18:19:18 +0200 Subject: [PATCH 13/15] RSEModel tool clean up --- CMakeLists.txt | 2 +- RSEModel/src/{Model-Extractor.c => RSEModel.c} | 15 +++++++-------- 2 files changed, 8 insertions(+), 9 deletions(-) rename RSEModel/src/{Model-Extractor.c => RSEModel.c} (93%) diff --git a/CMakeLists.txt b/CMakeLists.txt index 7429aab..01f939f 100644 --- a/CMakeLists.txt +++ b/CMakeLists.txt @@ -31,7 +31,7 @@ option(RSPMODEL_SHARED "Build shared lib" ON) # Push compile infos to source configure_file(${CMAKE_CURRENT_SOURCE_DIR}/config.h.in ${CMAKE_CURRENT_SOURCE_DIR}/RSPModelLib/src/config.h @ONLY) -configure_file(${CMAKE_CURRENT_SOURCE_DIR}/config.h.in ${CMAKE_CURRENT_SOURCE_DIR}/RSEModel/src/config.h @ONLY) +#configure_file(${CMAKE_CURRENT_SOURCE_DIR}/config.h.in ${CMAKE_CURRENT_SOURCE_DIR}/RSEModel/src/config.h @ONLY) # The project is divided in two parts: diff --git a/RSEModel/src/Model-Extractor.c b/RSEModel/src/RSEModel.c similarity index 93% rename from RSEModel/src/Model-Extractor.c rename to RSEModel/src/RSEModel.c index f8ae431..d5d5eb7 100644 --- a/RSEModel/src/Model-Extractor.c +++ b/RSEModel/src/RSEModel.c @@ -1,6 +1,6 @@ /** - * @file Model-Extractor.c - * @date 25/07/2022 + * @file RSEModel.c + * @date 19/08/2022 * @author JackCarterSmith * @copyright GPL-v3.0 * @brief HOB model parser and export to Waveform OBJ format. @@ -16,7 +16,6 @@ #include #include #endif -#include "config.h" #include "options.h" #include #include @@ -43,7 +42,7 @@ int main(int argc, char *argv[]) { unsigned char p; // Hello world! - printf("\n*** RogueSquadron Extractor (RSE) - MODEL module - v%s ***\n", RSPModel_getVersion()); + printf("\n*** RogueSquadron Extractor (RSE) - MODEL module - RSPModelLib v%s ***\n", RSPModel_getVersion()); // Check for arguments if (argc < 2) { @@ -146,9 +145,9 @@ static unsigned char checkInputArgs(T_PROG_OPTIONS* opt_ptr, int p_arg_nbr, char static void createSubDir(char *dirName) { if (dirName == NULL) return; - char _dir[260]; //TODO: Change directory management - strcpy(_dir, dirName); - strcat(_dir, "-out"); + char _dir[1024]; + + sprintf_s(_dir, 1024, "%s-out", dirName); #ifdef _WIN32 CreateDirectory(_dir, NULL); @@ -181,6 +180,6 @@ static void dispHelp() { printf(" -no-subdir Export models inside current folder\n"); printf(" -mtl Export materials datas with model\n"); printf("\n"); - printf("Usage: RSE-Model_%s [options] \n", PRG_VERSION); + printf("Usage: RSEModel [options] \n"); printf("\n"); } -- 2.39.5 From c5589c01999009b3a7068033c49b5bac4d4e6f21 Mon Sep 17 00:00:00 2001 From: JackCarterSmith Date: Fri, 19 Aug 2022 18:23:53 +0200 Subject: [PATCH 14/15] Lib interface with better parameters options --- RSEModel/src/RSEModel.c | 5 +- RSEModel/src/options.h | 9 +- RSPModelLib/include/RSPModel.h | 8 +- RSPModelLib/include/RSPModel_datatypes.h | 16 ++++ RSPModelLib/src/RSPModel.c | 21 ++--- RSPModelLib/src/hob_parser.c | 101 +++++++++++------------ RSPModelLib/src/hob_parser.h | 13 ++- RSPModelLib/src/options.h | 35 -------- 8 files changed, 93 insertions(+), 115 deletions(-) delete mode 100644 RSPModelLib/src/options.h diff --git a/RSEModel/src/RSEModel.c b/RSEModel/src/RSEModel.c index d5d5eb7..9a35fae 100644 --- a/RSEModel/src/RSEModel.c +++ b/RSEModel/src/RSEModel.c @@ -66,16 +66,19 @@ int main(int argc, char *argv[]) { static unsigned int mainProcess(int args_cnt, char* args_value[], T_PROG_OPTIONS* p_opts) { unsigned short file_index; + RSPMODEL_PARAMETERS libParams; T_RSPMODEL_HOB* hobStruct = NULL; int i; + libParams.raw = p_opts->raw & 0x7; + // Manage multiple inputs files for ( file_index = p_opts->input_files_cnt; file_index < args_cnt; file_index++) { printf("\n=============================================\n[INFO] - Parsing file: %s ...\n", args_value[file_index]); hobStruct = calloc(1, sizeof(T_RSPMODEL_HOB)); // Parse data from HOB file and put in T_HOB structure. - if (RSPModel_processHOBFile(hobStruct, args_value[file_index]) != RSPLIB_SUCCESS) { + if (RSPModel_processHOBFile(hobStruct, args_value[file_index], libParams) != RSPLIB_SUCCESS) { printf("[ERR] Failed to parse datas from %s\n", args_value[file_index]); free(hobStruct); return RSPLIB_ERROR_PROCESS; diff --git a/RSEModel/src/options.h b/RSEModel/src/options.h index fd512b2..93e7938 100644 --- a/RSEModel/src/options.h +++ b/RSEModel/src/options.h @@ -14,16 +14,13 @@ typedef union u_prog_options { struct { unsigned char verbose_mode:1; //!< Output simple details about ID and other "light" things. + unsigned char debug_mode:1; //!< Output all values of faces, indices and vertices and others "heavy" things. + unsigned char god_mode:1; //!< Dev only. Output experimental values. unsigned char output_dir:1; //!< Export extracted datas to a sub-directory. unsigned char export_mtl:1; //!< Export materials datas with object. - unsigned char reserved0:5; //!< For future use. - - unsigned char debug_mode:1; //!< Output all values of faces, indices and vertices and others "heavy" things. - unsigned char god_mode:1; //!< Dev only. Output experimental values. - - unsigned char reserved1:6; //!< For future use. + unsigned short reserved0:11; //!< For future use. unsigned short input_files_cnt; //!< Internal files counters. }; diff --git a/RSPModelLib/include/RSPModel.h b/RSPModelLib/include/RSPModel.h index e739c4b..9d8e979 100644 --- a/RSPModelLib/include/RSPModel.h +++ b/RSPModelLib/include/RSPModel.h @@ -61,11 +61,13 @@ RSPMODEL_EXTERN char* RSPModel_getVersion( void ); * * @param[out] hob HOB structure to be filled with parsed datas. * @param[in] filePath Path to the HOB file in system. + * @param[in] params Parser options. See RSPMODEL_PARAMETERS. * * @return Error status, return RSPLIB_SUCCESS in nominal case. */ RSPMODEL_EXTERN unsigned short RSPModel_processHOBFile( - T_RSPMODEL_HOB* hob, const char* const filePath + T_RSPMODEL_HOB* hob, const char* const filePath, + const RSPMODEL_PARAMETERS params ); /** @@ -77,11 +79,13 @@ RSPMODEL_EXTERN unsigned short RSPModel_processHOBFile( * @param[out] hob HOB structure to be filled with parsed datas. * @param[in] memFilePtr Pointer to the beginning of the file in memory. * @param[in] memFileSize Size of the file in bytes. + * @param[in] params Parser options. See RSPMODEL_PARAMETERS. * * @return Error status, return RSPLIB_SUCCESS in nominal case. */ RSPMODEL_EXTERN unsigned short RSPModel_processHOBFileMemory( - T_RSPMODEL_HOB* hob, const void* const memFilePtr, const long memFileSize + T_RSPMODEL_HOB* hob, const void* const memFilePtr, const long memFileSize, + const RSPMODEL_PARAMETERS params ); /** diff --git a/RSPModelLib/include/RSPModel_datatypes.h b/RSPModelLib/include/RSPModel_datatypes.h index 9ff0496..284bbef 100644 --- a/RSPModelLib/include/RSPModel_datatypes.h +++ b/RSPModelLib/include/RSPModel_datatypes.h @@ -14,6 +14,22 @@ extern "C" { #endif +/////////////////////////////////////////////////////////////////////////////// +// Configuration structure +/////////////////////////////////////////////////////////////////////////////// + +typedef union u_rspmodel_parameters { + struct { + unsigned char verbose_mode:1; //!< Output simple details about ID and other "light" things. + unsigned char debug_mode:1; //!< Output all values of faces, indices and vertices and others "heavy" things. + unsigned char god_mode:1; //!< Dev only. Output experimental values. + + unsigned char reserved0:5; //!< For future use. + }; + unsigned char raw; //!< Raw options access for bit-masking or memory copy/compare. +} RSPMODEL_PARAMETERS ; + + //////////////////////////////////////////////////////////////////////////////// // Lib's structure definitions //////////////////////////////////////////////////////////////////////////////// diff --git a/RSPModelLib/src/RSPModel.c b/RSPModelLib/src/RSPModel.c index 40afd48..217235b 100644 --- a/RSPModelLib/src/RSPModel.c +++ b/RSPModelLib/src/RSPModel.c @@ -11,7 +11,6 @@ #include #include #include "config.h" -#include "options.h" #include "RSPModel_errordefs.h" #include "hob_parser.h" #include "RSPModel.h" @@ -21,26 +20,22 @@ char* RSPModel_getVersion( void ) { return PRG_VERSION; } -unsigned short RSPModel_processHOBFile( T_RSPMODEL_HOB* hob, const char* const filePath ) { +unsigned short RSPModel_processHOBFile( T_RSPMODEL_HOB* hob, const char* const filePath, + const RSPMODEL_PARAMETERS params ) { + if ( hob == NULL || filePath == NULL ) return RSPLIB_ERROR_ARGS_NULL; - T_PROG_OPTIONS canard; - canard.god_mode = 1; - canard.debug_mode = 1; - canard.verbose_mode = 1; - RSP_ModelLib_ParseHOBFile(filePath, hob, &canard); + RSP_ModelLib_ParseHOBFile(filePath, hob, ¶ms); return RSPLIB_SUCCESS; } -unsigned short RSPModel_processHOBFileMemory( T_RSPMODEL_HOB* hob, const void* const memFilePtr, const long memFileSize ) { +unsigned short RSPModel_processHOBFileMemory( T_RSPMODEL_HOB* hob, const void* const memFilePtr, + const long memFileSize, const RSPMODEL_PARAMETERS params ) { + if ( hob == NULL || memFilePtr == NULL ) return RSPLIB_ERROR_ARGS_NULL; - T_PROG_OPTIONS canard; - canard.god_mode = 1; - canard.debug_mode = 1; - canard.verbose_mode = 1; - RSP_ModelLib_ParseHOBMemFile((MEMFILE)memFilePtr, hob, &canard); + RSP_ModelLib_ParseHOBMemFile((MEMFILE)memFilePtr, hob, ¶ms); return RSPLIB_SUCCESS; } diff --git a/RSPModelLib/src/hob_parser.c b/RSPModelLib/src/hob_parser.c index 891e6d6..68ad686 100644 --- a/RSPModelLib/src/hob_parser.c +++ b/RSPModelLib/src/hob_parser.c @@ -12,7 +12,6 @@ #include #include "RSPModel_errordefs.h" #include "RSPModel_datatypes.h" -#include "options.h" #include "hob_struct.h" #include "hob_parser.h" @@ -21,9 +20,9 @@ // Private functions declarations //////////////////////////////////////////////////////////////////////////////// -static unsigned int ExtractObjects(T_RSPMODEL_HOB*, const MEMFILE, const unsigned char); -static unsigned int ExtractObjParts(T_RSPMODEL_OBJECT*, const MEMFILE, const unsigned char); -static unsigned int ExtractObjParts_faces(T_RSPMODEL_OBJ_PARTS*, const MEMFILE, const unsigned char); +static unsigned int ExtractObjects(T_RSPMODEL_HOB*, const MEMFILE, const RSPMODEL_PARAMETERS*); +static unsigned int ExtractObjParts(T_RSPMODEL_OBJECT*, const MEMFILE, const RSPMODEL_PARAMETERS*); +static unsigned int ExtractObjParts_faces(T_RSPMODEL_OBJ_PARTS*, const MEMFILE, const RSPMODEL_PARAMETERS*); static inline unsigned int ExtractObjpart_Face_Colors(T_RSPMODEL_FACE*, const char*); static inline unsigned int ExtractObjpart_Face_UVMaps(T_RSPMODEL_FACE*, const char*); @@ -32,24 +31,24 @@ static inline unsigned int ExtractObjpart_Face_UVMaps(T_RSPMODEL_FACE*, const ch // Public functions definition //////////////////////////////////////////////////////////////////////////////// -unsigned char RSP_ModelLib_ParseHOBMemFile(const MEMFILE pMemFile, T_RSPMODEL_HOB* hob_struct, T_PROG_OPTIONS* p_opts) { +unsigned char RSP_ModelLib_ParseHOBMemFile(const MEMFILE pMemFile, T_RSPMODEL_HOB* hobStruct, const RSPMODEL_PARAMETERS* pParams) { unsigned char err = RSPLIB_SUCCESS; - if (hob_struct != NULL && pMemFile != NULL) { + if (hobStruct != NULL && pMemFile != NULL) { // Do the magic! - err = ExtractObjects(hob_struct, pMemFile, p_opts->verbose_mode + p_opts->debug_mode + p_opts->god_mode); + err = ExtractObjects(hobStruct, pMemFile, pParams); } else err = RSPLIB_ERROR_ARGS_NULL; return err; } -unsigned char RSP_ModelLib_ParseHOBFile(const char* fileName, T_RSPMODEL_HOB* hob_struct, T_PROG_OPTIONS* p_opts) { +unsigned char RSP_ModelLib_ParseHOBFile(const char* fileName, T_RSPMODEL_HOB* hobStruct, const RSPMODEL_PARAMETERS* pParams) { unsigned char err = RSPLIB_SUCCESS; long fileSize; FILE* fStream = NULL; MEMFILE memFile = NULL; - if (hob_struct != NULL && fileName != NULL) { + if (hobStruct != NULL && fileName != NULL) { // Open file fStream = fopen(fileName, "rb"); @@ -58,7 +57,7 @@ unsigned char RSP_ModelLib_ParseHOBFile(const char* fileName, T_RSPMODEL_HOB* ho fseek(fStream, 0, SEEK_END); fileSize = ftell(fStream); fseek(fStream, 0, SEEK_SET); - if (p_opts->verbose_mode) printf("[DBG] > Input file size: %ld bytes\n", fileSize); + if (pParams->verbose_mode) printf("[DBG] > Input file size: %ld bytes\n", fileSize); memFile = malloc(fileSize + 1); if (memFile != NULL) { @@ -67,18 +66,18 @@ unsigned char RSP_ModelLib_ParseHOBFile(const char* fileName, T_RSPMODEL_HOB* ho fclose(fStream); // Do the magic! - err = ExtractObjects(hob_struct, memFile, p_opts->verbose_mode + p_opts->debug_mode + p_opts->god_mode); + err = ExtractObjects(hobStruct, memFile, pParams); free(memFile); } else { fclose(fStream); err = RSPLIB_ERROR_MEMORY; - if (p_opts->verbose_mode) printf("[ERR] Can't allocate enough memory for file processing!\n"); + if (pParams->verbose_mode) printf("[ERR] Can't allocate enough memory for file processing!\n"); } } else { err = RSPLIB_ERROR_IO; - if (p_opts->verbose_mode) printf("[ERR] Input file %s not found!\n", fileName); + if (pParams->verbose_mode) printf("[ERR] Input file %s not found!\n", fileName); } } else err = RSPLIB_ERROR_ARGS_NULL; @@ -99,7 +98,7 @@ unsigned char RSP_ModelLib_ParseHOBFile(const char* fileName, T_RSPMODEL_HOB* ho * * @return Error code, RSPLIB_SUCCESS when no error. */ -static unsigned int ExtractObjects(T_RSPMODEL_HOB* pHobStruct, const MEMFILE pMemfile, const unsigned char verbose) { +static unsigned int ExtractObjects(T_RSPMODEL_HOB* pHobStruct, const MEMFILE pMemfile, const RSPMODEL_PARAMETERS* pParams) { unsigned int i; if (pHobStruct == NULL || pMemfile == NULL) return RSPLIB_ERROR_ARGS_NULL; @@ -117,28 +116,28 @@ static unsigned int ExtractObjects(T_RSPMODEL_HOB* pHobStruct, const MEMFILE pMe if (pHobStruct->objects == NULL) return RSPLIB_ERROR_MEMORY; for ( i = 0; i < pHobStruct->obj_count; i++ ) { - if (verbose == 2) printf("\n-=====================-Begin of Object part-======================-\n"); + if (pParams->debug_mode) printf("\n-=====================-Begin of Object part-======================-\n"); // Get object name memcpy(pHobStruct->objects[i].name, ((T_HOBFILE_OBJ_DESCRIPTOR *)(pMemfile + sizeof(T_HOBFILE_HEADER) + sizeof(T_HOBFILE_OBJ_DESCRIPTOR) * i))->object_name, 16); - if (verbose == 1) printf("\n"); + if (pParams->verbose_mode) printf("\n"); printf("[INFO] - Process %s object...\n", pHobStruct->objects[i].name); // Get offsets pHobStruct->objects[i].face_group_offset = ((T_HOBFILE_OBJ_DESCRIPTOR *)(pMemfile + sizeof(T_HOBFILE_HEADER) + sizeof(T_HOBFILE_OBJ_DESCRIPTOR) * i))->facegroup_offset; - if (verbose == 1) printf("[DBG] > Face group offset: 0x%X\n", pHobStruct->objects[i].face_group_offset); + if (pParams->verbose_mode) printf("[DBG] > Face group offset: 0x%X\n", pHobStruct->objects[i].face_group_offset); pHobStruct->objects[i].object_part_header_offset = ((T_HOBFILE_OBJ_DESCRIPTOR *)(pMemfile + sizeof(T_HOBFILE_HEADER) + sizeof(T_HOBFILE_OBJ_DESCRIPTOR) * i))->object_parts_offset; - if (verbose == 1) printf("[DBG] > Face group header/object parts offset: 0x%X\n", pHobStruct->objects[i].object_part_header_offset); + if (pParams->verbose_mode) printf("[DBG] > Face group header/object parts offset: 0x%X\n", pHobStruct->objects[i].object_part_header_offset); pHobStruct->objects[i].face_group_header_offset = ((T_HOBFILE_OBJ_DESCRIPTOR *)(pMemfile + sizeof(T_HOBFILE_HEADER) + sizeof(T_HOBFILE_OBJ_DESCRIPTOR) * i))->facegroup_header_2_offset; - if (verbose == 1) printf("[DBG] > Face group header2 offset: 0x%X\n", pHobStruct->objects[i].face_group_header_offset); + if (pParams->verbose_mode) printf("[DBG] > Face group header2 offset: 0x%X\n", pHobStruct->objects[i].face_group_header_offset); - if (verbose == 3) { + if (pParams->god_mode) { printf("[DBG] > Face group unknown1: %d\n",((T_HOBFILE_OBJ_DESCRIPTOR *)(pMemfile + sizeof(T_HOBFILE_HEADER) + sizeof(T_HOBFILE_OBJ_DESCRIPTOR) * i))->unknownOffset1); printf("[DBG] > Face group unknown2: %d\n",((T_HOBFILE_OBJ_DESCRIPTOR *)(pMemfile + sizeof(T_HOBFILE_HEADER) + sizeof(T_HOBFILE_OBJ_DESCRIPTOR) * i))->unknownOffset2); printf("[DBG] > Face group unknown3: %d\n",((T_HOBFILE_OBJ_DESCRIPTOR *)(pMemfile + sizeof(T_HOBFILE_HEADER) + sizeof(T_HOBFILE_OBJ_DESCRIPTOR) * i))->unknownOffset3); @@ -148,15 +147,15 @@ static unsigned int ExtractObjects(T_RSPMODEL_HOB* pHobStruct, const MEMFILE pMe // Get count and offsets from the facegroup header pHobStruct->objects[i].object_part_count = ((T_HOBFILE_FACEGROUP_HEADER *)(pMemfile + pHobStruct->objects[i].object_part_header_offset))->object_part_count; - if (verbose == 1) printf("[DBG] > Object parts count: %d\n", pHobStruct->objects[i].object_part_count); + if (pParams->verbose_mode) printf("[DBG] > Object parts count: %d\n", pHobStruct->objects[i].object_part_count); pHobStruct->objects[i].face_group_count = ((T_HOBFILE_FACEGROUP_HEADER *)(pMemfile + pHobStruct->objects[i].object_part_header_offset))->facegroup_count; - if (verbose == 1) printf("[DBG] > Face groups count: %d\n", pHobStruct->objects[i].face_group_count); - if (pHobStruct->objects[i].object_part_count != pHobStruct->objects[i].face_group_count && (verbose == 1)) + if (pParams->verbose_mode) printf("[DBG] > Face groups count: %d\n", pHobStruct->objects[i].face_group_count); + if (pHobStruct->objects[i].object_part_count != pHobStruct->objects[i].face_group_count && (pParams->verbose_mode)) printf("[DBG] > Object parts / facegroup count are different!\n"); // Get facegroup datas - ExtractObjParts(&pHobStruct->objects[i], pMemfile, verbose); + ExtractObjParts(&pHobStruct->objects[i], pMemfile, pParams); } return RSPLIB_SUCCESS; @@ -171,7 +170,7 @@ static unsigned int ExtractObjects(T_RSPMODEL_HOB* pHobStruct, const MEMFILE pMe * * @return Error code, RSPLIB_SUCCESS when no error. */ -static unsigned int ExtractObjParts(T_RSPMODEL_OBJECT* pObject, const MEMFILE pMemfile, const unsigned char verbose) { +static unsigned int ExtractObjParts(T_RSPMODEL_OBJECT* pObject, const MEMFILE pMemfile, const RSPMODEL_PARAMETERS* pParams) { unsigned int i, subpart_offset = 0; if (pObject == NULL || pMemfile == NULL) return RSPLIB_ERROR_ARGS_NULL; @@ -180,28 +179,28 @@ static unsigned int ExtractObjParts(T_RSPMODEL_OBJECT* pObject, const MEMFILE pM if (pObject->object_parts == NULL) return RSPLIB_ERROR_MEMORY; for ( i = 0; i < pObject->object_part_count; i++ ) { - if (verbose == 2) printf("\n-----------------------Begin of Mesh part-------------------------\n"); + if (pParams->debug_mode) printf("\n-----------------------Begin of Mesh part-------------------------\n"); subpart_offset = ((T_HOBFILE_FACEGROUP_OFFSET *)(pMemfile + pObject->object_part_header_offset + sizeof(T_HOBFILE_FACEGROUP_HEADER) + sizeof(T_HOBFILE_FACEGROUP_OFFSET) * i))->facegroup_offset; - if (verbose == 1) printf("\n[DBG] > Face group meshdef0 offset: 0x%X\n", subpart_offset); + if (pParams->verbose_mode) printf("\n[DBG] > Face group meshdef0 offset: 0x%X\n", subpart_offset); // Get meshdef0 datas - if (verbose == 3) printf("[DBG] > meshdef0 offset1: 0x%X\n",((T_HOBFILE_MESHDEF0 *)(pMemfile + subpart_offset))->offset1); - if (verbose == 3) printf("[DBG] > meshdef0 offset2: 0x%X\n",((T_HOBFILE_MESHDEF0 *)(pMemfile + subpart_offset))->offset2); - if (verbose == 1) printf("[DBG] > Prev meshdef0 offset: 0x%X\n",((T_HOBFILE_MESHDEF0 *)(pMemfile + subpart_offset))->prev_meshdef0_offset); - if (verbose == 1) printf("[DBG] > Next meshdef0 offset: 0x%X\n",((T_HOBFILE_MESHDEF0 *)(pMemfile + subpart_offset))->next_meshdef0_offset); + if (pParams->god_mode) printf("[DBG] > meshdef0 offset1: 0x%X\n",((T_HOBFILE_MESHDEF0 *)(pMemfile + subpart_offset))->offset1); + if (pParams->god_mode) printf("[DBG] > meshdef0 offset2: 0x%X\n",((T_HOBFILE_MESHDEF0 *)(pMemfile + subpart_offset))->offset2); + if (pParams->verbose_mode) printf("[DBG] > Prev meshdef0 offset: 0x%X\n",((T_HOBFILE_MESHDEF0 *)(pMemfile + subpart_offset))->prev_meshdef0_offset); + if (pParams->verbose_mode) printf("[DBG] > Next meshdef0 offset: 0x%X\n",((T_HOBFILE_MESHDEF0 *)(pMemfile + subpart_offset))->next_meshdef0_offset); - if (verbose == 3) printf("[DBG] > meshdef0 unknown3: %.8f\n",((T_HOBFILE_MESHDEF0 *)(pMemfile + subpart_offset))->unknown3); - if (verbose == 3) printf("[DBG] > meshdef0 unknown4: %.8f\n",((T_HOBFILE_MESHDEF0 *)(pMemfile + subpart_offset))->unknown4); - if (verbose == 3) printf("[DBG] > meshdef0 unknown5: %.8f\n",((T_HOBFILE_MESHDEF0 *)(pMemfile + subpart_offset))->unknown5); + if (pParams->god_mode) printf("[DBG] > meshdef0 unknown3: %.8f\n",((T_HOBFILE_MESHDEF0 *)(pMemfile + subpart_offset))->unknown3); + if (pParams->god_mode) printf("[DBG] > meshdef0 unknown4: %.8f\n",((T_HOBFILE_MESHDEF0 *)(pMemfile + subpart_offset))->unknown4); + if (pParams->god_mode) printf("[DBG] > meshdef0 unknown5: %.8f\n",((T_HOBFILE_MESHDEF0 *)(pMemfile + subpart_offset))->unknown5); // Get meshdef1 (mesh descriptor) offset pObject->object_parts[i].meshdef1_offset = ((T_HOBFILE_MESHDEF0 *)(pMemfile + subpart_offset))->meshdef1_offset_plus_4; - if (verbose == 1) printf("\n[DBG] > Face group meshdef1 offset: 0x%X\n", pObject->object_parts[i].meshdef1_offset); + if (pParams->verbose_mode) printf("\n[DBG] > Face group meshdef1 offset: 0x%X\n", pObject->object_parts[i].meshdef1_offset); if( ((T_HOBFILE_MESHDEF0 *)(pMemfile + subpart_offset))->reserved1 != 0 || ((T_HOBFILE_MESHDEF0 *)(pMemfile + subpart_offset))->reserved2 != 0 ) { - if (verbose == 3) printf("[DBG] > Face group meshdef0: no 0!\n"); + if (pParams->god_mode) printf("[DBG] > Face group meshdef0: no 0!\n"); } if (pObject->object_parts[i].meshdef1_offset > 0) { @@ -212,33 +211,33 @@ static unsigned int ExtractObjParts(T_RSPMODEL_OBJECT* pObject, const MEMFILE pM + pObject->object_parts[i].meshdef1_offset - 4))->vertex_count; pObject->object_parts[i].face_block_offset = ((T_HOBFILE_MESHDEF1 *)(pMemfile + pObject->object_parts[i].meshdef1_offset - 4))->faceblock_offset; - if (verbose == 1) printf("[DBG] > Faces offset: 0x%X\n", pObject->object_parts[i].face_block_offset); + if (pParams->verbose_mode) printf("[DBG] > Faces offset: 0x%X\n", pObject->object_parts[i].face_block_offset); pObject->object_parts[i].vertex_block_offset = ((T_HOBFILE_MESHDEF1 *)(pMemfile + pObject->object_parts[i].meshdef1_offset - 4))->vertexblocks_offset; - if (verbose == 1) printf("[DBG] > Vertex offset: 0x%X\n\n", pObject->object_parts[i].vertex_block_offset); + if (pParams->verbose_mode) printf("[DBG] > Vertex offset: 0x%X\n\n", pObject->object_parts[i].vertex_block_offset); // Get faces datas - ExtractObjParts_faces(&pObject->object_parts[i], pMemfile, verbose); + ExtractObjParts_faces(&pObject->object_parts[i], pMemfile, pParams); } // Get object part ID, used by animation? bones? pObject->object_parts[i].id = ((T_HOBFILE_MESHDEF0 *)(pMemfile + subpart_offset))->object_id; - if (verbose == 1) printf("\n[DBG] > Facegroup/object ID: %d\n", pObject->object_parts[i].id); + if (pParams->verbose_mode) printf("\n[DBG] > Facegroup/object ID: %d\n", pObject->object_parts[i].id); // Get the transform matrix, used by at-st and at-at (at this time) pObject->object_parts[i].transform.x = ((T_HOBFILE_MESHDEF0 *)(pMemfile + subpart_offset))->transform_x; pObject->object_parts[i].transform.y = ((T_HOBFILE_MESHDEF0 *)(pMemfile + subpart_offset))->transform_y; pObject->object_parts[i].transform.z = ((T_HOBFILE_MESHDEF0 *)(pMemfile + subpart_offset))->transform_z; - if (verbose == 3) printf("\n[DBG] > Facegroup/object transform matrix: [%.8f %.8f %.8f]\n", + if (pParams->god_mode) printf("\n[DBG] > Facegroup/object transform matrix: [%.8f %.8f %.8f]\n", pObject->object_parts[i].transform.x, pObject->object_parts[i].transform.y, pObject->object_parts[i].transform.z ); - if (verbose == 2) printf("\n-----------------------End of Mesh part---------------------------\n"); + if (pParams->debug_mode) printf("\n-----------------------End of Mesh part---------------------------\n"); } - if (verbose == 2) printf("\n-=====================-End of Object part-========================-\n"); + if (pParams->debug_mode) printf("\n-=====================-End of Object part-========================-\n"); return RSPLIB_SUCCESS; } @@ -252,24 +251,24 @@ static unsigned int ExtractObjParts(T_RSPMODEL_OBJECT* pObject, const MEMFILE pM * * @return Error code, RSPLIB_SUCCESS when no error. */ -static unsigned int ExtractObjParts_faces(T_RSPMODEL_OBJ_PARTS* pObjPart, const MEMFILE pMemfile, const unsigned char verbose) { +static unsigned int ExtractObjParts_faces(T_RSPMODEL_OBJ_PARTS* pObjPart, const MEMFILE pMemfile, const RSPMODEL_PARAMETERS* pParams) { unsigned int i, facesExtraOffset = 0; if (pObjPart == NULL || pMemfile == NULL) return RSPLIB_ERROR_ARGS_NULL; if( ((T_HOBFILE_FACEBLOCK *)(pMemfile + pObjPart->face_block_offset))->reserved1 != 0 || ((T_HOBFILE_FACEBLOCK *)(pMemfile + pObjPart->face_block_offset))->reserved2 != 0 ) { - if (verbose == 3) printf("[DBG] > Face block: uncommon zero header!\n"); + if (pParams->god_mode) printf("[DBG] > Face block: uncommon zero header!\n"); } if ( ((T_HOBFILE_FACEBLOCK *)(pMemfile + pObjPart->face_block_offset))->facesOffset != pObjPart->face_block_offset + sizeof(T_HOBFILE_FACEBLOCK)) { - if (verbose == 3) printf("[DBG] > Face block: uncommon face data offset position!\n"); + if (pParams->god_mode) printf("[DBG] > Face block: uncommon face data offset position!\n"); } pObjPart->face_count = ((T_HOBFILE_FACEBLOCK *)(pMemfile + pObjPart->face_block_offset))->faceCounts; pObjPart->faces = calloc(pObjPart->face_count, sizeof(T_RSPMODEL_FACE)); for ( i = 0; i < pObjPart->face_count; i++ ) { - if (verbose == 2) printf("\n----------------------Begin of FaceGroup part----------------------\n"); + if (pParams->debug_mode) printf("\n----------------------Begin of FaceGroup part----------------------\n"); // Get flags pObjPart->faces[i].flags = ((T_HOBFILE_FACES_HEADER *)(pMemfile + pObjPart->face_block_offset @@ -287,7 +286,7 @@ static unsigned int ExtractObjParts_faces(T_RSPMODEL_OBJ_PARTS* pObjPart, const + sizeof(T_HOBFILE_FACEBLOCK) + sizeof(T_HOBFILE_FACES_HEADER) * i + facesExtraOffset))->faceBlockIntSize * 4; // Multiply by 4 to get the bytes exact number if (((T_HOBFILE_FACES_HEADER *)(pMemfile + pObjPart->face_block_offset + sizeof(T_HOBFILE_FACEBLOCK) + sizeof(T_HOBFILE_FACES_HEADER) * i + facesExtraOffset))->headerSeparator != 0) { - if (verbose == 3) printf("[DBG] > Face header: uncommon separator!\n"); + if (pParams->god_mode) printf("[DBG] > Face header: uncommon separator!\n"); } // Get materials index @@ -316,7 +315,7 @@ static unsigned int ExtractObjParts_faces(T_RSPMODEL_OBJ_PARTS* pObjPart, const + facesExtraOffset); } - if (verbose == 2) { + if (pParams->debug_mode) { printf("[DBG] > Face %d details: flags:0x%X b1:%d b2:%d b3%d bsize:%d\n", i, pObjPart->faces[i].flags, pObjPart->faces[i].b1, pObjPart->faces[i].b2, pObjPart->faces[i].b3, pObjPart->faces[i].bsize); printf("[DBG] - Type is Quad: %d\n", pObjPart->faces[i].flags_bits.fIsQuad); @@ -353,7 +352,7 @@ static unsigned int ExtractObjParts_faces(T_RSPMODEL_OBJ_PARTS* pObjPart, const printf("\n"); } - if (verbose == 2) printf("\n-----------------------End of FaceGroup part-----------------------\n"); + if (pParams->debug_mode) printf("\n-----------------------End of FaceGroup part-----------------------\n"); } // Get vertex datas @@ -373,7 +372,7 @@ static unsigned int ExtractObjParts_faces(T_RSPMODEL_OBJ_PARTS* pObjPart, const pObjPart->vertices[i].w = ((T_HOBFILE_VERTEX *)(pMemfile + pObjPart->vertex_block_offset + sizeof(T_VERTEX) * i))->w; // Always 0??? - if (verbose == 2) printf("[DBG] > Found vertex %d: (%d, %d, %d)\n", i, + if (pParams->debug_mode) printf("[DBG] > Found vertex %d: (%d, %d, %d)\n", i, pObjPart->vertices[i].x, pObjPart->vertices[i].y, pObjPart->vertices[i].z ); } diff --git a/RSPModelLib/src/hob_parser.h b/RSPModelLib/src/hob_parser.h index 1c4e8ec..fabf751 100644 --- a/RSPModelLib/src/hob_parser.h +++ b/RSPModelLib/src/hob_parser.h @@ -7,7 +7,6 @@ * */ -#include "options.h" #include "RSPModel_datatypes.h" @@ -21,14 +20,14 @@ * @note Unmanaged mode * * @param[in] pMemFile Pointer to an in-memory HOB file location. - * @param[out] hob_struct Allocated empty T_RSPMODEL_HOB structure instance to + * @param[out] hobStruct Allocated empty T_RSPMODEL_HOB structure instance to * be filled with HOB datas. - * @param[in] p_opts Parser options. DEPRECATED. + * @param[in] pParams Parser options. See RSPMODEL_PARAMETERS. * * @return Processing error code, RSPLIB_SUCCESS if no error. */ unsigned char RSP_ModelLib_ParseHOBMemFile(const MEMFILE pMemFile, - T_RSPMODEL_HOB* hob_struct, T_PROG_OPTIONS* p_opts); + T_RSPMODEL_HOB* hobStruct, const RSPMODEL_PARAMETERS* pParams); /** * @brief Process HOB file in file system. @@ -40,13 +39,13 @@ unsigned char RSP_ModelLib_ParseHOBMemFile(const MEMFILE pMemFile, * @note Managed mode * * @param[in] fileName String value of file name/path. - * @param[out] hob_struct Allocated empty T_RSPMODEL_HOB structure instance to + * @param[out] hobStruct Allocated empty T_RSPMODEL_HOB structure instance to * be filled with HOB datas. - * @param[in] p_opts Parser options. DEPRECATED. + * @param[in] pParams Parser options. See RSPMODEL_PARAMETERS. * * @return Processing error code, RSPLIB_SUCCESS if no error. */ unsigned char RSP_ModelLib_ParseHOBFile(const char* fileName, - T_RSPMODEL_HOB* hob_struct, T_PROG_OPTIONS* p_opts); + T_RSPMODEL_HOB* hobStruct, const RSPMODEL_PARAMETERS* pParams); #endif /* SRC_HOB_PARSER_H_ */ diff --git a/RSPModelLib/src/options.h b/RSPModelLib/src/options.h deleted file mode 100644 index a88baae..0000000 --- a/RSPModelLib/src/options.h +++ /dev/null @@ -1,35 +0,0 @@ -/** - * @file options.h - * @date 29/07/2022 - * @author JackCarterSmith - * @copyright GPL-v3.0 - * @brief Shared options structure definition and declaration. - * - */ - -#ifndef OPTIONS_H_ -#define OPTIONS_H_ - -#define RSPMODEL_DLLBUILD - -/// Options structure -typedef union u_prog_options { - struct { - unsigned char verbose_mode:1; //!< Output simple details about ID and other "light" things. - - unsigned char output_dir:1; //!< Export extracted datas to a sub-directory. - unsigned char export_mtl:1; //!< Export materials datas with object. - - unsigned char reserved0:5; //!< For future use. - - unsigned char debug_mode:1; //!< Output all values of faces, indices and vertices and others "heavy" things. - unsigned char god_mode:1; //!< Dev only. Output experimental values. - - unsigned char reserved1:6; //!< For future use. - - unsigned short input_files_cnt; //!< Internal files counters. - }; - unsigned int raw; //!< Raw options access for bit-masking or memory copy/compare. -} T_PROG_OPTIONS ; - -#endif /* OPTIONS_H_ */ -- 2.39.5 From f1ea3fc372e63e64dfc3d9d6754fa893e0830909 Mon Sep 17 00:00:00 2001 From: JackCarterSmith Date: Fri, 19 Aug 2022 19:03:11 +0200 Subject: [PATCH 15/15] sprintf_s gcc compatible fix --- RSEModel/src/RSEModel.c | 2 +- RSEModel/src/obj | 2 +- RSEModel/src/obj_exporter.c | 8 ++++---- 3 files changed, 6 insertions(+), 6 deletions(-) diff --git a/RSEModel/src/RSEModel.c b/RSEModel/src/RSEModel.c index 9a35fae..f69e853 100644 --- a/RSEModel/src/RSEModel.c +++ b/RSEModel/src/RSEModel.c @@ -150,7 +150,7 @@ static void createSubDir(char *dirName) { if (dirName == NULL) return; char _dir[1024]; - sprintf_s(_dir, 1024, "%s-out", dirName); + snprintf(_dir, 1024, "%s-out", dirName); #ifdef _WIN32 CreateDirectory(_dir, NULL); diff --git a/RSEModel/src/obj b/RSEModel/src/obj index 09f8716..63f5977 160000 --- a/RSEModel/src/obj +++ b/RSEModel/src/obj @@ -1 +1 @@ -Subproject commit 09f87160bb80d1ad331c697000ecd7a122f9ef60 +Subproject commit 63f5977aaed661f6176daca101680bfcd80e80ec diff --git a/RSEModel/src/obj_exporter.c b/RSEModel/src/obj_exporter.c index 42f3e14..e3e3e4c 100644 --- a/RSEModel/src/obj_exporter.c +++ b/RSEModel/src/obj_exporter.c @@ -32,12 +32,12 @@ unsigned char exportOBJModel(T_RSPMODEL_OBJECT* hob_objects, const char *out_pat return RSPLIB_ERROR_ARGS_NULL; #ifdef _WIN32 - sprintf_s(exportPath, 1024, "%s-out\\", out_path, hob_objects->name); + snprintf(exportPath, 1024, "%s-out\\", out_path); #else - sprintf_s(exportPath, 1024, "%s-out/", out_path, hob_objects->name); + snprintf(exportPath, 1024, "%s-out/", out_path); #endif - sprintf_s(objExport_name, 128, "%s.obj", hob_objects->name); - sprintf_s(mtlExport_name, 128, "%s.mtl", hob_objects->name); + snprintf(objExport_name, 128, "%s.obj", hob_objects->name); + snprintf(mtlExport_name, 128, "%s.mtl", hob_objects->name); objConstruct = obj_create(NULL); -- 2.39.5