Ver código fonte

Code reformat and organization.

Iñigo Valentin 4 anos atrás
pai
commit
9125b378b6
50 arquivos alterados com 6009 adições e 9419 exclusões
  1. 0 0
      RuneOptimizerGUI/RuneOptimizer.py
  2. 0 0
      RuneOptimizerGUI/classes/DialogConfirm.py
  3. 0 0
      RuneOptimizerGUI/classes/DialogNewTeam.py
  4. 0 0
      RuneOptimizerGUI/classes/DialogUpdateJson.py
  5. 0 0
      RuneOptimizerGUI/classes/PanelInfo.py
  6. 0 0
      RuneOptimizerGUI/classes/PanelOptimizer.py
  7. 0 0
      RuneOptimizerGUI/classes/PanelResults.py
  8. 0 0
      RuneOptimizerGUI/classes/PanelTeams.py
  9. 0 0
      RuneOptimizerGUI/classes/PanelUnits.py
  10. 0 0
      RuneOptimizerGUI/classes/RuneOptimizerFrame.py
  11. 0 0
      RuneOptimizerGUI/classes/TabList.py
  12. 0 0
      RuneOptimizerGUI/res/icon/info.png
  13. 0 0
      RuneOptimizerGUI/res/icon/optimize.png
  14. 0 0
      RuneOptimizerGUI/res/icon/progress.gif
  15. 0 0
      RuneOptimizerGUI/res/icon/results.png
  16. 0 0
      RuneOptimizerGUI/res/icon/teams.png
  17. 0 0
      RuneOptimizerGUI/res/icon/units.png
  18. 39 7
      src/Makefile
  19. 19 34
      src/RuneOptimizer/RuneOptimizer.c
  20. 209 7
      src/RuneOptimizer/RuneOptimizer.h
  21. 46 71
      src/RuneOptimizer/db/db.c
  22. 28 22
      src/RuneOptimizer/db/db.h
  23. 345 65
      src/RuneOptimizer/error/error.h
  24. 3 4
      src/RuneOptimizer/help/help.c
  25. 1 1
      src/RuneOptimizer/help/help.h
  26. 51 1358
      src/RuneOptimizer/optimize/optimize.c
  27. 121 122
      src/RuneOptimizer/optimize/optimize.h
  28. 132 0
      src/RuneOptimizer/optimize/optimize_count_runes_for_sets.c
  29. 65 0
      src/RuneOptimizer/optimize/optimize_fetch_unit.c
  30. 56 0
      src/RuneOptimizer/optimize/optimize_get_runes.c
  31. 396 0
      src/RuneOptimizer/optimize/optimize_parse_arguments.c
  32. 433 0
      src/RuneOptimizer/optimize/optimize_print.c
  33. 213 0
      src/RuneOptimizer/optimize/optimize_query.c
  34. 15 423
      src/RuneOptimizer/team/team.c
  35. 114 30
      src/RuneOptimizer/team/team.h
  36. 98 0
      src/RuneOptimizer/team/team_add_unit.c
  37. 96 0
      src/RuneOptimizer/team/team_create.c
  38. 74 0
      src/RuneOptimizer/team/team_delete.c
  39. 98 0
      src/RuneOptimizer/team/team_list.c
  40. 85 0
      src/RuneOptimizer/team/team_remove_unit.c
  41. 16 7238
      src/RuneOptimizer/update/update.c
  42. 109 37
      src/RuneOptimizer/update/update.h
  43. 184 0
      src/RuneOptimizer/update/update_current_stats.c
  44. 208 0
      src/RuneOptimizer/update/update_db_tables.c
  45. 1905 0
      src/RuneOptimizer/update/update_get_monster_name.c
  46. 46 0
      src/RuneOptimizer/update/update_info.c
  47. 92 0
      src/RuneOptimizer/update/update_json.c
  48. 235 0
      src/RuneOptimizer/update/update_json_rune.c
  49. 139 0
      src/RuneOptimizer/update/update_json_unit.c
  50. 338 0
      src/RuneOptimizer/update/update_rune_totals.c

+ 0 - 0
src/RuneOptimizerGUI/RuneOptimizer.py → RuneOptimizerGUI/RuneOptimizer.py


+ 0 - 0
src/RuneOptimizerGUI/classes/DialogConfirm.py → RuneOptimizerGUI/classes/DialogConfirm.py


+ 0 - 0
src/RuneOptimizerGUI/classes/DialogNewTeam.py → RuneOptimizerGUI/classes/DialogNewTeam.py


+ 0 - 0
src/RuneOptimizerGUI/classes/DialogUpdateJson.py → RuneOptimizerGUI/classes/DialogUpdateJson.py


+ 0 - 0
src/RuneOptimizerGUI/classes/PanelInfo.py → RuneOptimizerGUI/classes/PanelInfo.py


+ 0 - 0
src/RuneOptimizerGUI/classes/PanelOptimizer.py → RuneOptimizerGUI/classes/PanelOptimizer.py


+ 0 - 0
src/RuneOptimizerGUI/classes/PanelResults.py → RuneOptimizerGUI/classes/PanelResults.py


+ 0 - 0
src/RuneOptimizerGUI/classes/PanelTeams.py → RuneOptimizerGUI/classes/PanelTeams.py


+ 0 - 0
src/RuneOptimizerGUI/classes/PanelUnits.py → RuneOptimizerGUI/classes/PanelUnits.py


+ 0 - 0
src/RuneOptimizerGUI/classes/RuneOptimizerFrame.py → RuneOptimizerGUI/classes/RuneOptimizerFrame.py


+ 0 - 0
src/RuneOptimizerGUI/classes/TabList.py → RuneOptimizerGUI/classes/TabList.py


+ 0 - 0
src/RuneOptimizerGUI/res/icon/info.png → RuneOptimizerGUI/res/icon/info.png


+ 0 - 0
src/RuneOptimizerGUI/res/icon/optimize.png → RuneOptimizerGUI/res/icon/optimize.png


+ 0 - 0
src/RuneOptimizerGUI/res/icon/progress.gif → RuneOptimizerGUI/res/icon/progress.gif


+ 0 - 0
src/RuneOptimizerGUI/res/icon/results.png → RuneOptimizerGUI/res/icon/results.png


+ 0 - 0
src/RuneOptimizerGUI/res/icon/teams.png → RuneOptimizerGUI/res/icon/teams.png


+ 0 - 0
src/RuneOptimizerGUI/res/icon/units.png → RuneOptimizerGUI/res/icon/units.png


+ 39 - 7
src/Makefile

@@ -1,13 +1,45 @@
+# Try to detect operating system
+ifeq ($(OS),Windows_NT)
+	ifeq ($(shell uname -s),) # not in a bash-like shell
+		RM = del /F /Q
+		MKDIR = mkdir
+	else # in a bash-like shell, like msys
+		RM = rm -f
+		MKDIR = mkdir -p
+	endif
+	EXTENSION=.exe
+	INC=-I C:\MinGW\lib
+else
+	RM = rm -f
+	MKDIR = mkdir -p
+	EXTENSION=
+	INC=
+endif
+
+SRC=RuneOptimizer/RuneOptimizer.c
 CC=gcc
 CFLAGS=
-OPTS_DEBUG=-Wall -g -fsanitize=address
+OPTS_DEBUG=-Wall -g
 OPTS=-O3
 LIBS=-lsqlite3 -lm -ljson-c
 OUT=../RuneOptimizer
-compile :
-	$(CC) RuneOptimizer/RuneOptimizer.c $(LIBS) $(OPTS) -o $(OUT)
+OUT_DEBUG=../RuneOptimizer_DEBUG
+TEST_SRC=test/TestRuneOptimizer.c
+TEST_OUT=test/RuneOptimizerTest
+TEST_FUNCTION=-Wl,-etest_main
+
+default :
+	@$(CC) -o $(OUT)$(EXTENSION) $(SRC) $(INC) $(LIBS) $(OPTS)
 	@echo Compiled executable $(OUT)
-#RuneOptimizer: RuneOptimizer.c
-#	$(CC) -o makeRO RuneOptimizer.c
-#install :
-#	gcc RuneOptimizer.c -lsqlite3 -o makeRO
+
+debug :
+	$(CC) -o $(OUT_DEBUG)$(EXTENSION) $(SRC) $(INC) $(LIBS)
+	@echo Compiled debug executable $(OUT_DEBUG)
+
+test : default
+	@$(CC) -o $(TEST_OUT)$(EXTENSION) $(TEST_SRC) $(INC) $(LIBS) $(TEST_FUNCTION)
+clean :
+# TODO: Delete database?
+	@$(RM) $(OUT)$(EXTENSION)
+	@$(RM) $(OUT_DEBUG)$(EXTENSION)
+	@echo All clean

+ 19 - 34
src/RuneOptimizer/RuneOptimizer.c

@@ -26,90 +26,75 @@
 #include <json-c/json.h>
 #include "RuneOptimizer.h"
 #include "error/error.h"
-#include "db/db.h"
 #include "db/db.c"
-#include "help/help.h"
 #include "help/help.c"
-#include "optimize/optimize.h"
 #include "optimize/optimize.c"
-#include "team/team.h"
 #include "team/team.c"
-#include "update/update.h"
 #include "update/update.c"
 
-/**
- * Starts the program.
- *
- * Reads parameters and runs the appropiate functions.
- *
- * @param argc Argument count.
- * @param argv Argument list.
- * @return SUCCESS on success, other on error.
- */
 int main(int argc, char *argv[]){
     // Parse the arguments to find the command (index 1)
 
     // If no arguments, end here
     if (argc < 2){
         fprintf(stderr, "No command specified\n");
-        return ERROR_INPUT_NO_COMMAND;
+        return(ERROR_INPUT_NO_COMMAND);
     }
 
     // Set the global database location
     int last_path_separator = -1;
     for(int i = 0; i < strlen(argv[0]); i++){
-        if(argv[0][i] == '/'){
+        if(argv[0][i] == '/' || argv[0][i] == '\\'){
             last_path_separator = i + 1;
         }
     }
     if (last_path_separator != -1){
         strncpy(db_location, argv[0], last_path_separator);
         strncpy(executable_location, argv[0], last_path_separator);
+        
     }
     else{
         strcpy(db_location, "");
         strcpy(executable_location, "");
     }
-    strcat(db_location, DB_NAME);
+    strcat(db_location, DEFAULT_DB_PATH);
+    
+    int result = SUCCESS;
 
     // Version command
     if (strcmp(argv[1], "version") == 0){
         printf("%s\n", VERSION);
-        return SUCCESS;
+        return(SUCCESS);
     }
 
     // Update command
     else if (strcmp(argv[1], "update") == 0){
-        return update(argc - 2, argv + 2);
+        return(cmd_update(argc - 2, argv + 2));
     }
 
-    // Optimize command, call the function with all the arguments to be
-    // processed there.
+    // Optimize command.
     else if (strcmp(argv[1], "optimize") == 0){
-        int result = optimize(argc, argv);
-        return result;
+        // Pass the rest of the arguments to the team command.
+        return(cmd_optimize(argc - 2, argv + 2));
     }
 
     // Help command. Call and return
     else if (strcmp(argv[1], "help") == 0){
-        show_help();
-        return SUCCESS;
+        cmd_help();
+        return(SUCCESS);
     }
 
-    // Help command.
+    // Team command.
     else if (strcmp(argv[1], "team") == 0){
-        // Pass the rest of the arguments to the team function, handle it there.
-        return team(argc - 2, argv + 2);
-    }
-
-    // Update command
-    else if (strcmp(argv[1], "update") == 0){
-        update(argc - 2, argv + 2);
+        // Pass the rest of the arguments to the team command.
+        return(cmd_team(argc - 2, argv + 2));
     }
 
     // Any other command is an error
     else{
         fprintf(stderr, "Invalid command specified: %s\n", argv[1]);
-        return ERROR_INPUT_INVALID_COMMAND;
+        return(ERROR_INPUT_INVALID_COMMAND);
     }
+    
+    return result;
 }

+ 209 - 7
src/RuneOptimizer/RuneOptimizer.h

@@ -15,19 +15,220 @@
  * RuneOptimizer. If not, see <https://www.gnu.org/licenses/>.
  */
 
+/**
+ * Application version
+ */
 #define VERSION "0.1-RC1"
+
+/**
+ * Application author.
+ */
 #define AUTHOR "Iñigo Valentin"
+
+/**
+ * Application author email.
+ */
 #define MAIL "i@inigovalentin.com"
 
-#define DB_NAME "data.sqlite"
+/**
+ * Default path to the database.
+ * 
+ * It's the same directory as the executable.
+ */
+#define DEFAULT_DB_PATH "data.sqlite"
 
+/**
+ * Mock boolean value TRUE
+ */
 #define TRUE 1
+
+/**
+ * Mock boolean value of FALSE.
+ */
 #define FALSE 0
 
+/**
+ * Set ID of Energy runes.
+ */
+#define ENERGY 1
+
+/**
+ * Set ID of Guard runes.
+ */
+#define GUARD 2
+
+/**
+ * Set ID of Swift runes.
+ */
+#define SWIFT 3
+
+/**
+ * Set ID of Blade runes.
+ */
+#define BLADE 4
+
+/**
+ * Set ID of Rage runes.
+ */
+#define RAGE 5
+
+/**
+ * Set ID of Focus runes.
+ */
+#define FOCUS 6
+
+/**
+ * Set ID of Endure runes.
+ */
+#define ENDURE 7
+
+/**
+ * Set ID of Fatal runes.
+ */
+#define FATAL 8
+
+/**
+ * Set ID of Despair runes.
+ */
+#define DESPAIR 10
+
+/**
+ * Set ID of Vampire runes.
+ */
+#define VAMPIRE 11
+
+/**
+ * Set ID of Violent runes.
+ */
+#define VIOLENT 13
+
+/**
+ * Set ID of Nemesis runes.
+ */
+#define NEMESIS 14
+
+/**
+ * Set ID of Will runes.
+ */
+#define WILL 15
+
+/**
+ * Set ID of Shield runes.
+ */
+#define SHIELD 16
+
+/**
+ * Set ID of Revenge runes.
+ */
+#define REVENGE 17
+
+/**
+ * Set ID of Destroy runes.
+ */
+#define DESTROY 18
+
+/**
+ * Set ID of Fight runes.
+ */
+#define FIGHT 19
+
+/**
+ * Set ID of Determination runes.
+ */
+#define DETERMINATION 20
+
+/**
+ * Set ID of Enhance runes.
+ */
+#define ENHANCE 21
+
+/**
+ * Set ID of Accuracy runes.
+ */
+#define ACCURACY 22
+
+/**
+ * Set ID of Tolerance runes.
+ */
+#define TOLERANCE 23
+
+
+/**
+ * Stat ID for HP stat in runes..
+ */
+#define HP_FLAT 1
+
+/**
+ * Stat ID for HP% stat in runes..
+ */
+#define HP_PERCENT 2
+
+/**
+ * Stat ID for ATK stat in runes..
+ */
+#define ATK_FLAT 3
+
+/**
+ * Stat ID for ATK% stat in runes..
+ */
+#define ATK_PERCENT 4
+
+/**
+ * Stat ID for DEF stat in runes..
+ */
+#define DEF_FLAT 5
+
+/**
+ * Stat ID for DEF% stat in runes..
+ */
+#define DEF_PERCENT 6
+
+/**
+ * Stat ID for SPD stat in runes.
+ */
+#define SPD 8
+
+/**
+ * Stat ID for CRR stat in runes.
+ */
+#define CRR 9
+
+/**
+ * Stat ID for CRD stat in runes.
+ */
+#define CRD 10
+
+/**
+ * Stat ID for RES stat in runes.
+ */
+#define RES 11
+
+/**
+ * Stat ID for ACC stat in runes.
+ */
+#define ACC 12
+
+
+
+/**
+ * Global database connection.
+ */
+sqlite3 *db = NULL;
+
+/**
+ * Path to the database.
+ */
 char db_location[256];
+
+/**
+ * Path to the execcutable.
+ */
 char executable_location[512];
 
-struct Rune_Set_Count {
+/**
+ * Number of runes for a given list of runes.
+ */
+typedef struct Rune_Set_Count {
     unsigned short energy;
     unsigned short guard;
     unsigned short swift;
@@ -49,15 +250,16 @@ struct Rune_Set_Count {
     unsigned short enhance;
     unsigned short accuracy;
     unsigned short tolerance;
-};
+} Rune_Set_Count;
 
 /**
  * Starts the program.
  *
- * Reads parameters and runs the appropiate functions.
+ * Reads command line parameters and runs the appropiate command.
  *
- * @param argc Argument count.
- * @param argv Argument list.
- * @return SUCCESS on success, other on error.
+ * @param argc Number of arguments passed to the program.
+ * @param argv Arguments passed to the program.
+ * @return SUCCESS on success, other on error. Most errors are listed in
+ * <a href="file:../error/error.h">../error/error.h</a>
  */
 int main(int argc, char *argv[]);

+ 46 - 71
src/RuneOptimizer/db/db.c

@@ -15,124 +15,99 @@
  * RuneOptimizer. If not, see <https://www.gnu.org/licenses/>.
  */
 
-/**
- * Opens the database connection.
- *
- * @param[out] db Database object.
- * @param[in] path Database path, relative to the execution path. Optional.
- * @return SUCCESS or an error code.
- */
-int db_open(sqlite3 **db, char *path){
+#include "db.h"
+
+int db_close(){
+    if (db != NULL){
+        int result = sqlite3_close_v2(db);
+        if (result != SQLITE_OK){
+            fprintf(
+              stderr,
+              "Error closing database connection: %s", sqlite3_errmsg(db)
+            );
+            return(result);
+        }
+    }
+    return(SUCCESS);
+}
+
+int db_open(char *path){
 
     // Get the path, relative to the program
     char db_location[512];
     strcpy(db_location, executable_location);
 
     // If db specified as argument, use it, else use the default location.
-    if (path == NULL){
-        strcat(db_location, DEFAULT_DB_PATH);
-    }
-    else{
-        strcat(db_location, path);
-    }
+    if (path == NULL) strcat(db_location, DEFAULT_DB_PATH);
+    else strcat(db_location, path);
     if (
-        SUCCESS != sqlite3_open_v2(db_location, db, SQLITE_OPEN_READWRITE, NULL)
+        SUCCESS != sqlite3_open_v2(db_location, &db, SQLITE_OPEN_READWRITE, NULL)
     ){
-        fprintf(stderr, "Cannot open database: %s\n", sqlite3_errmsg(*db));
-        sqlite3_close(*db);
-        return ERROR_DB_CANT_OPEN;
+        fprintf(stderr, "Cannot open database: %s\n", sqlite3_errmsg(db));
+        db_close();
+        return(ERROR_DB_CANT_OPEN);
     }
-    return SUCCESS;
-}
-
-/**
- * Finalizes a database connection.
- *
- * @param[in|out] db Connection to close.
- * @return SUCCESS or an error code.
- */
-int db_close(sqlite3 **db){
-    sqlite3_close_v2(*db);
+    return(SUCCESS);
 }
 
-/**
- * Executes a database query for a result.
- *
- * @param[in|out] db Connection to the database.
- * @param[out] stmt Statement to load
- * @param[in] query Query to execute.
- * @param[in] parameters List of string parameters to bind to the query.
- * @return SUCCESS or an error code.
- */
-int db_query(
-  sqlite3 **db, sqlite3_stmt **stmt, char query[], char *parameters[]
-){
+int db_query(sqlite3_stmt **stmt, char query[], char *parameters[]){
 
     // If the connection has not been initialized, do it now
-    if (NULL == *db){
-        db_open(db, NULL);
-    }
+    if (NULL == db) db_open(NULL);
 
-    if (SQLITE_OK != sqlite3_prepare_v2(*db, query, -1, stmt, 0)) {
+    if (SQLITE_OK != sqlite3_prepare_v2(db, query, -1, stmt, 0)) {
         fprintf(
-          stderr, "ERROR executing query '%s': %s\n", query, sqlite3_errmsg(*db)
+          stderr, "ERROR executing query '%s': %s\n", query, sqlite3_errmsg(db)
         );
         sqlite3_finalize(*stmt);
-        sqlite3_close(*db);
-        return ERROR_DB_DELETE_UNITS_TEAMS;
+        return(ERROR_DB_QUERY);
     }
 
     // Loop and bind parameters
     char total_parameters = sqlite3_bind_parameter_count(*stmt);
     for (int i = 0; i < total_parameters; i ++){
-        sqlite3_bind_text(*stmt, i + 1, parameters[i], strlen(parameters[i]), NULL);
+        sqlite3_bind_text(
+          *stmt, i + 1, parameters[i], strlen(parameters[i]), NULL
+        );
     }
 
     //printf("PREP QUERY: %s\n", sqlite3_expanded_sql(*stmt));
 
-    return SUCCESS;
+    return(SUCCESS);
 }
 
-/**
- * Executes a database statement.
- *
- * @param[in|out] db Connection to the database.
- * @param[in] query Query to execute.
- * @param[in] parameters List of string parameters to bind to the query.
- * @return SUCCESS or an error code.
- */
-int db_execute(sqlite3 **db, char query[], char *parameters[]){
+int db_execute(char query[], char *parameters[]){
 
     // If the connection has not been initialized, do it now
-    if (NULL == *db){
-        db_open(db, NULL);
-    }
+    if (NULL == db) db_open(NULL);
 
     sqlite3_stmt *stmt;
-    if (SQLITE_OK != sqlite3_prepare_v2(*db, query, -1, &stmt, 0)) {
+    if (SQLITE_OK != sqlite3_prepare_v2(db, query, -1, &stmt, 0)) {
         fprintf(
-          stderr, "ERROR executing statement '%s': %s\n", query, sqlite3_errmsg(*db)
+          stderr, "ERROR executing statement '%s': %s\n",
+          query, sqlite3_errmsg(db)
         );
         sqlite3_finalize(stmt);
-        return ERROR_DB_QUERY;
+        return(ERROR_DB_EXECUTE);
     }
 
     // Loop and bind parameters
     char total_parameters = sqlite3_bind_parameter_count(stmt);
     for (int i = 0; i < total_parameters; i ++){
-        sqlite3_bind_text(stmt, i + 1, parameters[i], strlen(parameters[i]), NULL);
+        sqlite3_bind_text(
+          stmt, i + 1, parameters[i], strlen(parameters[i]), NULL
+        );
     }
     //printf("PREP QUERY: %s\n", sqlite3_expanded_sql(stmt));
     if (SQLITE_DONE != sqlite3_step(stmt)){
         fprintf(
-          stderr,
-          "ERROR Executing statement '%s': %s\n",
-          query, sqlite3_errmsg(*db)
+          stderr, "ERROR Executing statement '%s': %s\n",
+          query, sqlite3_errmsg(db)
         );
         sqlite3_finalize(stmt);
-        return ERROR_DB_EXECUTE;
+        return(ERROR_DB_EXECUTE);
     }
 
     sqlite3_finalize(stmt);
-    return SUCCESS;
+    return(SUCCESS);
 }

+ 28 - 22
src/RuneOptimizer/db/db.h

@@ -15,44 +15,50 @@
  * RuneOptimizer. If not, see <https://www.gnu.org/licenses/>.
  */
 
-#define DEFAULT_DB_PATH "./data.sqlite"
-
 /**
- * Opens the database connection.
+ * Finalizes a database connection.
  *
- * @param[out] db Database object.
- * @param[in] path Database path, relative to the execution path. Optional.
- * @return SUCCESS or an error code.
+ * @return SUCCESS or an SQLITE error code.
  */
-int db_open(sqlite3 **db, char *path);
+int db_close();
 
 /**
- * Finalizes a database connection.
+ * Opens the database connection.
+ * 
+ * Sets up the global db connection. On error, it prints a description to
+ * stderr.
  *
- * @param[in|out] db Connection to close.
- * @return SUCCESS or an error code.
+ * @param[in] path Database path, relative to the execution path. Optional.
+ * @return SUCCESS if the connection gets opened, or ERROR_DB_CANT_OPEN on
+ * error.
  */
-int db_close(sqlite3 **db);
+int db_open(char *path);
+
 
 /**
  * Executes a database query for a result.
+ * 
+ * Uses the global database connection. If the connection is not initializad, it
+ * calls @{see db_open}. On error, it prints a description to stderr.
  *
- * @param[in|out] db Connection to the database.
- * @param[out] stmt Statement to load
+ * @param[out] stmt Statement to store the query results.
  * @param[in] query Query to execute.
- * @param[in] parameters List of string parameters to bind to the query.
- * @return SUCCESS or an error code.
+ * @param[in] parameters List of string parameters to bind to the query. They
+ * all will be considered strings.
+ * @return SUCCESS if the query is executed and the statment ready to be read,
+ * or ERROR_DB_QUERY on error.
  */
-int db_query(
-  sqlite3 **db, sqlite3_stmt **stmt, char query[], char *parameters[]
-);
+int db_query(sqlite3_stmt **stmt, char query[], char *parameters[]);
 
 /**
  * Executes a database statement.
+ * 
+ * Uses the global database connection. If the connection is not initializad, it
+ * calls @{see db_open}On error, it prints a description to stderr.
  *
- * @param[in|out] db Connection to the database.
  * @param[in] query Query to execute.
- * @param[in] parameters List of string parameters to bind to the query.
- * @return SUCCESS or an error code.
+ * @param[in] parameters List of string parameters to bind to the query. They
+ * all will be considered strings.
+ * @return SUCCESS if the query is executed or ERROR_DB_EXECUTE on error.
  */
-int db_execute(sqlite3 **db, char query[], char *parameters[]);
+int db_execute(char query[], char *parameters[]);

+ 345 - 65
src/RuneOptimizer/error/error.h

@@ -15,68 +15,348 @@
  * RuneOptimizer. If not, see <https://www.gnu.org/licenses/>.
  */
 
-#define SUCCESS 0
-#define UNIMPLEMENTED 1
-#define ERROR_INPUT_NO_COMMAND 100
-#define ERROR_INPUT_INVALID_COMMAND 101
-#define ERROR_INPUT_NO_UNIT 102
-#define ERROR_INPUT_INVALID_LEVEL 103
-#define ERROR_INPUT_NO_LEVEL 104
-#define ERROR_INPUT_INVALID_SET 105
-#define ERROR_INPUT_NO_SET 106
-#define ERROR_INPUT_INVALID_STAT 107
-#define ERROR_INPUT_NO_STAT 108
-#define ERROR_INPUT_NO_HP 109
-#define ERROR_INPUT_NO_ATK 110
-#define ERROR_INPUT_NO_DEF 111
-#define ERROR_INPUT_NO_SPD 112
-#define ERROR_INPUT_NO_CRR 113
-#define ERROR_INPUT_NO_CRD 114
-#define ERROR_INPUT_NO_RES 115
-#define ERROR_INPUT_NO_ACC 116
-#define ERROR_INPUT_NO_EHP 117
-#define ERROR_INPUT_NO_DMG 118
-#define ERROR_INPUT_INCOMPLETE_SETS 119
-#define ERROR_INPUT_TEAM_NO_ACTION 120
-#define ERROR_INPUT_TEAM_INVALID_ACTION 121
-#define ERROR_INPUT_TEAM_CREATE_ARGUMENT_COUNT 122
-#define ERROR_INPUT_TEAM_CREATE_PRIORITY 123
-#define ERROR_INPUT_UPDATE_NO_ARGUMENTS 124
-#define ERROR_INPUT_UPDATE_UNKNOWN_SOURCE 125
-#define ERROR_INPUT_VERIFY_TEAM_UNIT_TEAM 126
-#define ERROR_INPUT_VERIFY_TEAM_UNIT_UNIT 127
-#define ERROR_INPUT_VERIFY_TEAM_UNIT_INCLUDED 128
-#define ERROR_INPUT_TEAM_DELETE_ARGUMENT_COUNT 129
-#define ERROR_DB_CANT_OPEN 200
-#define ERROR_DB_UNIT 201
-#define ERROR_DB_UNIT_NOF_FOUND 202
-#define ERROR_DB_RUNES_SLOT 203
-#define ERROR_DB_RUNES_RESULT 204
-#define ERROR_DB_STATS_RESULT 205
-#define ERROR_DB_TEAM_ID 206
-#define ERROR_DB_NEW_TEAM_ID 207
-#define ERROR_DB_DROP_RUNE_STATS 208
-#define ERROR_DB_DROP_RUNES 209
-#define ERROR_DB_DROP_UNITS 210
-#define ERROR_DB_DROP_TEAMS 211
-#define ERROR_DB_DROP_UNITS_TEAMS 211
-#define ERROR_DB_CREATE_RUNE_STATS 212
-#define ERROR_DB_CREATE_RUNES 213
-#define ERROR_DB_CREATE_UNITS 214
-#define ERROR_DB_CREATE_TEAMS 215
-#define ERROR_DB_CREATE_UNITS_TEAMS 216
-#define ERROR_DB_INSERT_RUNE_STATS 217
-#define ERROR_DB_INSERT_RUNES 218
-#define ERROR_DB_INSERT_UNITS 219
-#define ERROR_DB_INSERT_TEAMS 220
-#define ERROR_DB_INSERT_UNITS_TEAMS 221
-#define ERROR_DB_UPDATE_UNITS 222
-#define ERROR_DB_RUNES 223
-#define ERROR_DB_DROP_INFO 213
-#define ERROR_DB_CREATE_INFO 214
-#define ERROR_DB_INSERT_INFO 215
-#define ERROR_DB_VERIFY_TEAM_UNIT 216
-#define ERROR_DB_DELETE_UNITS_TEAMS 217
-#define ERROR_DB_DELETE_TEAMS 217
-#define ERROR_DB_QUERY 218
-#define ERROR_DB_EXECUTE 218
+/**
+ * Success indicator
+ */
+#define SUCCESS -0
+
+/**
+ * Indicator for an unimplemented functionality.
+ */
+#define UNIMPLEMENTED -800
+
+/**
+ * Error indicating 
+ */
+#define ERROR_INPUT_NO_COMMAND -100
+
+/**
+ * Error indicating 
+ */
+#define ERROR_INPUT_INVALID_COMMAND -101
+
+/**
+ * Error indicating 
+ */
+#define ERROR_INPUT_NO_UNIT -102
+
+/**
+ * Error indicating 
+ */
+#define ERROR_INPUT_INVALID_LEVEL -103
+
+/**
+ * Error indicating 
+ */
+#define ERROR_INPUT_NO_LEVEL -104
+
+/**
+ * Error indicating 
+ */
+#define ERROR_INPUT_INVALID_SET -105
+
+/**
+ * Error indicating 
+ */
+#define ERROR_INPUT_NO_SET -106
+
+/**
+ * Error indicating 
+ */
+#define ERROR_INPUT_INVALID_STAT -107
+
+/**
+ * Error indicating 
+ */
+#define ERROR_INPUT_NO_STAT -108
+
+/**
+ * Error indicating 
+ */
+#define ERROR_INPUT_NO_HP -109
+
+/**
+ * Error indicating 
+ */
+#define ERROR_INPUT_NO_ATK -110
+
+/**
+ * Error indicating 
+ */
+#define ERROR_INPUT_NO_DEF -111
+
+/**
+ * Error indicating 
+ */
+#define ERROR_INPUT_NO_SPD -112
+
+/**
+ * Error indicating 
+ */
+#define ERROR_INPUT_NO_CRR -113
+
+/**
+ * Error indicating 
+ */
+#define ERROR_INPUT_NO_CRD -114
+
+/**
+ * Error indicating 
+ */
+#define ERROR_INPUT_NO_RES -115
+
+/**
+ * Error indicating 
+ */
+#define ERROR_INPUT_NO_ACC -116
+
+/**
+ * Error indicating 
+ */
+#define ERROR_INPUT_NO_EHP -117
+
+/**
+ * Error indicating 
+ */
+#define ERROR_INPUT_NO_DMG -118
+
+/**
+ * Error indicating 
+ */
+#define ERROR_INPUT_NO_TEAMS -119
+
+/**
+ * Error indicating 
+ */
+#define ERROR_INPUT_INCOMPLETE_SETS -120
+
+/**
+ * Error indicating 
+ */
+#define ERROR_INPUT_TEAM_NO_ACTION -121
+
+/**
+ * Error indicating 
+ */
+#define ERROR_INPUT_TEAM_INVALID_ACTION -122
+
+/**
+ * Error indicating 
+ */
+#define ERROR_INPUT_TEAM_CREATE_ARGUMENT_COUNT -123
+
+/**
+ * Error indicating 
+ */
+#define ERROR_INPUT_TEAM_CREATE_PRIORITY -124
+
+/**
+ * Error indicating 
+ */
+#define ERROR_INPUT_UPDATE_NO_ARGUMENTS -125
+
+/**
+ * Error indicating 
+ */
+#define ERROR_INPUT_UPDATE_UNKNOWN_SOURCE -126
+
+/**
+ * Error indicating 
+ */
+#define ERROR_INPUT_VERIFY_TEAM -127
+
+/**
+ * Error indicating 
+ */
+#define ERROR_INPUT_VERIFY_TEAM_UNIT_TEAM -128
+
+/**
+ * Error indicating 
+ */
+#define ERROR_INPUT_VERIFY_TEAM_UNIT_UNIT -129
+
+/**
+ * Error indicating 
+ */
+#define ERROR_INPUT_VERIFY_TEAM_UNIT_INCLUDED -130
+
+/**
+ * Error indicating 
+ */
+#define ERROR_INPUT_TEAM_DELETE_ARGUMENT_COUNT -131
+
+/**
+ * Error indicating 
+ */
+#define ERROR_DB_CANT_OPEN -200
+
+/**
+ * Error indicating 
+ */
+#define ERROR_DB_UNIT -201
+
+/**
+ * Error indicating 
+ */
+#define ERROR_DB_UNIT_NOT_FOUND -202
+
+/**
+ * Error indicating 
+ */
+#define ERROR_DB_RUNES_SLOT -203
+
+/**
+ * Error indicating 
+ */
+#define ERROR_DB_RUNES_RESULT -204
+
+/**
+ * Error indicating 
+ */
+#define ERROR_DB_STATS_RESULT -205
+
+/**
+ * Error indicating 
+ */
+#define ERROR_DB_TEAM_ID -206
+
+/**
+ * Error indicating 
+ */
+#define ERROR_DB_NEW_TEAM_ID -207
+
+/**
+ * Error indicating 
+ */
+#define ERROR_DB_DROP_RUNE_STATS -208
+
+/**
+ * Error indicating 
+ */
+#define ERROR_DB_DROP_RUNES -209
+
+/**
+ * Error indicating 
+ */
+#define ERROR_DB_DROP_UNITS -210
+
+/**
+ * Error indicating 
+ */
+#define ERROR_DB_DROP_TEAMS -211
+
+/**
+ * Error indicating 
+ */
+#define ERROR_DB_DROP_UNITS_TEAMS -212
+
+/**
+ * Error indicating 
+ */
+#define ERROR_DB_CREATE_RUNE_STATS -213
+
+/**
+ * Error indicating 
+ */
+#define ERROR_DB_CREATE_RUNES -214
+
+/**
+ * Error indicating 
+ */
+#define ERROR_DB_CREATE_UNITS -215
+
+/**
+ * Error indicating 
+ */
+#define ERROR_DB_CREATE_TEAMS -216
+
+/**
+ * Error indicating 
+ */
+#define ERROR_DB_CREATE_UNITS_TEAMS -217
+
+/**
+ * Error indicating 
+ */
+#define ERROR_DB_INSERT_RUNE_STATS -218
+
+/**
+ * Error indicating 
+ */
+#define ERROR_DB_INSERT_RUNES -219
+
+/**
+ * Error indicating 
+ */
+#define ERROR_DB_INSERT_UNITS -220
+
+/**
+ * Error indicating 
+ */
+#define ERROR_DB_INSERT_TEAMS -221
+
+/**
+ * Error indicating 
+ */
+#define ERROR_DB_INSERT_UNITS_TEAMS -222
+
+/**
+ * Error indicating 
+ */
+#define ERROR_DB_UPDATE_UNITS -223
+
+/**
+ * Error indicating 
+ */
+#define ERROR_DB_RUNES -224
+
+/**
+ * Error indicating 
+ */
+#define ERROR_DB_DROP_INFO -225
+
+/**
+ * Error indicating 
+ */
+#define ERROR_DB_CREATE_INFO -226
+
+/**
+ * Error indicating 
+ */
+#define ERROR_DB_INSERT_INFO -227
+
+/**
+ * Error indicating 
+ */
+#define ERROR_DB_VERIFY_TEAM_UNIT -228
+
+/**
+ * Error indicating 
+ */
+#define ERROR_DB_DELETE_UNITS_TEAMS -229
+
+/**
+ * Error indicating 
+ */
+#define ERROR_DB_VERIFY_TEAM -230
+
+/**
+ * Error indicating 
+ */
+#define ERROR_DB_DELETE_TEAMS -231
+
+/**
+ * Error indicating 
+ */
+#define ERROR_DB_QUERY -232
+
+/**
+ * Error indicating 
+ */
+#define ERROR_DB_EXECUTE -233
+
+/**
+ * Error indicating 
+ */
+#define ERROR_DB_DROP -234
+

+ 3 - 4
src/RuneOptimizer/help/help.c

@@ -15,10 +15,9 @@
  * RuneOptimizer. If not, see <https://www.gnu.org/licenses/>.
  */
 
-/**
- * Displays the help text.
- */
-void show_help(){
+#include "help.h"
+
+void cmd_help(){
     printf("\nRune Optimizer %s\n", VERSION);
     printf("%s <%s>\n", AUTHOR, MAIL);
     printf("\n  Usage:\n");

+ 1 - 1
src/RuneOptimizer/help/help.h

@@ -18,4 +18,4 @@
 /**
  * Displays the help text.
  */
-void show_help();
+void cmd_help();

Diferenças do arquivo suprimidas por serem muito extensas
+ 51 - 1358
src/RuneOptimizer/optimize/optimize.c


+ 121 - 122
src/RuneOptimizer/optimize/optimize.h

@@ -15,43 +15,15 @@
  * RuneOptimizer. If not, see <https://www.gnu.org/licenses/>.
  */
 
-// Rune set definitions
-#define ENERGY 1
-#define GUARD 2
-#define SWIFT 3
-#define BLADE 4
-#define RAGE 5
-#define FOCUS 6
-#define ENDURE 7
-#define FATAL 8
-#define DESPAIR 10
-#define VAMPIRE 11
-#define VIOLENT 13
-#define NEMESIS 14
-#define WILL 15
-#define SHIELD 16
-#define REVENGE 17
-#define DESTROY 18
-#define FIGHT 19
-#define DETERMINATION 20
-#define ENHANCE 21
-#define ACCURACY 22
-#define TOLERANCE 23
-
-// Rune stat definitions
-#define HP_FLAT 1
-#define HP_PERCENT 2
-#define ATK_FLAT 3
-#define ATK_PERCENT 4
-#define DEF_FLAT 5
-#define DEF_PERCENT 6
-#define SPD 8
-#define CRR 9
-#define CRD 10
-#define RES 11
-#define ACC 12
+/**
+ * Hard limit on the number of results
+ */
+#define MAX_RESULTS 5000
 
-struct Unit {
+/**
+ * Structure representing a unit. Represents an entity from the table 'unit'.
+ */
+typedef struct Unit {
     unsigned char id[12];
     unsigned char name[50];
     unsigned int base_hp;
@@ -74,9 +46,12 @@ struct Unit {
     unsigned short current_res;
     unsigned int current_ehp;
     unsigned short current_dmg;
-};
+} Unit;
 
-struct Rune {
+/**
+ * Structure representing a rune.
+ */
+typedef struct Rune {
     unsigned char id[12];
     unsigned char slot;
     unsigned char set;
@@ -92,9 +67,12 @@ struct Rune {
     unsigned char crd;
     unsigned char acc;
     unsigned char res;
-};
+} Rune;
 
-struct Stats {
+/**
+ * A set of stats.
+ */
+typedef struct Stats {
     unsigned int hp;
     unsigned short atk;
     unsigned short def;
@@ -105,20 +83,35 @@ struct Stats {
     unsigned short res;
     unsigned int ehp;
     unsigned short dmg;
-};
+} Stats;
 
 
+/**
+ * A result, composed of 6 runes.
+ */
 typedef struct Result {
     unsigned char rune_ids[6][12];
     signed int rating;
     struct Stats stats;
 } Result;
 
-char stat_names[][13] = {
+/**
+ * Names for run stats.
+ * 
+ * Indexed by Com2Us ID.
+ */
+const char stat_names[][13] = {
   "NULL", "HP_FLAT", "HP",  "ATK_FLAT", "ATK", "DEF_FLAT",
   "DEF",  "NULL",    "SPD", "CRR",      "CRD", "RES",      "ACC"
 };
-char set_names[][25] = {
+
+
+/**
+ * Names for rune sets.
+ * 
+ * Indexed by Com2Us ID.
+ */
+const char set_names[][25] = {
   "NULL",    "ENERGY",  "GUARD",         "SWIFT",   "BLADE",    "RAGE",
   "FOCUS",   "ENDURE",  "FATAL",         "NULL",    "DESPAIR",  "VAMPIRE",
   "NULL",    "VIOLENT", "NEMESIS",       "WILL",    "SHIELD",   "REVENGE",
@@ -126,83 +119,27 @@ char set_names[][25] = {
 };
 
 /**
- * Parses the arguments for the optimize command.
+ * Calculates how many runes of each type it takes to satisfy a lst of up to
+ * three sets.
  *
- * @param[in] argc Argument count.
- * @param[in] argv Argument list.
- * @param[out] id Unit id or name.
- * @param[out] level Level to treat the runes as.
- * @param[out] sets List of requested sets.
- * @param[out] stats List of requested stats.
- * @param[out] min_stats Minimum stats for the optimization.
- * @param[out] storage 1 to use only runes from storage.
- * @param[in] excluded_teams List of teams whose unit's runes to exclude.
- * @param[in] excluded_units List of units whose runes to exclude.
- * @param[out] gui 1 to format the output for the GUI
- * @return SUCCESS or an error code.
+ * @param[in] sets List of up to three sets.
+ * @param[out] requested_set_count Structure to populate. It will have the
+ * number of runes of each type needed to form the sets.
+ * @return Number of requested runes. In ost cases, it should be 6.
  */
-int parse_optimization_arguments(
-  int argc,  char argv[][128], char id[64],             char *level,
-  int *sets, int *stats,   struct Stats *min_stats, char *gui,
-  char *storage, char excluded_teams[64][64], char excluded_units[64][64]
+char optimize_count_runes_for_sets(
+  int sets[3], Rune_Set_Count *requested_set_count
 );
 
 /**
  * Populates a Unit structure with data from the database.
  *
- * @param[in] id Argument count.
+ * @param[in] id Unit ID.
  * @param[out] unit Structure to populate.
- * @return SUCCESS or an error code.
- */
-int retrieveUnit(char id[64], struct Unit *unit);
-
-/**
- * Populates a Rune_Set_Count structure with the number of each rune requested
- * for the optimization.
- *
- * @param[in] sets Sets requested as arguments.
- * @param[out] requested_set_count Structure to populate.
- * @return Number of requested runes.
+ * @return SUCCESS if the unit is loaded, or ERROR_DB_UNIT_NOT_FOUND if the
+ * unit doesn't exist in the database.
  */
-char calculateRequiredSetCount(
-  int sets[3],
-  struct Rune_Set_Count *requested_set_count
-);
-
-/**
- * Generates the query to get the runes from the databas for even slots.
- *
- * @param[in] level Level to consider runes at.
- * @param[in] sets Requested sets.
- * @param[in] stats Requested sets for even slots.
- * @param[in] excluded_teams List of teams whose unit's runes to exclude.
- * @param[in] excluded_units List of units whose runes to exclude.
- * @param[in] storage 1 to select only unassigned runes.
- * @param[in] unit_id ID of the unit being optimized
- * @param[out] query String with the query.
- */
-void createQueryForEvenSlots(
-  char level, int* sets, int* stats,
-  char excluded_teams[64][64], char excluded_units[64][64],
-  char storage, char unit_id[64], char query[2500]
-);
-
-/**
- * Generates the query to get the runes from the databas for odd slots.
- *
- * @param[in] level Level to consider runes at.
- * @param[in] sets Requested sets.
- * @param[in] excluded_teams List of teams whose unit's runes to exclude.
- * @param[in] excluded_units List of units whose runes to exclude.
- * @param[in] storage 1 to select only unassigned runes.
- * @param[in] unit_id ID of the unit being optimized
- * @param[out] query String with the query.
- */
-void createQueryForOddSlots(
-  char level, int* sets,
-  char excluded_teams[64][64], char excluded_units[64][64],
-  char storage, char unit_id[64], char query[2500]
-);
+int optimize_fetch_unit(char id[64], struct Unit *unit);
 
 /**
  * Gets the list of runes to test during the optimization from the database.
@@ -218,11 +155,35 @@ void createQueryForOddSlots(
  * @param[out] rune_count Number of runes retrieved for each slot.
  * @return SUCCESS or an error code.
  */
-int get_runes(
-  char query_even[1500],     char query_odd[1500],
+int optimize_get_runes(
+  char query_even[1500], char query_odd[1500],
   struct Rune runes[7][600], int rune_count[7]
 );
 
+/**
+ * Parses the arguments for the optimize command.
+ *
+ * @param[in] argc Number of argument passed to the optimizer command.
+ * @param[in] argv Arguments passed to the optimizer.
+ * @param[out] id Unit id or name.
+ * @param[out] level Level to treat the runes as.
+ * @param[out] sets List of requested sets.
+ * @param[out] stats List of requested stats.
+ * @param[out] min_stats Minimum stats for the optimization.
+ * @param[out] storage 1 to use only runes from storage.
+ * @param[in] excluded_teams List of teams whose unit's runes to exclude.
+ * @param[in] excluded_units List of units whose runes to exclude.
+ * @param[out] gui 1 to format the output for the GUI
+ * @return SUCCESS or an error code. See
+ * <a href="file:../error/error.h">../error/error.h</a> for a list of error
+ * codes.
+ */
+int optimize_parse_arguments(
+  int argc, char argv[][128], char id[64], char *level,
+  int *sets, int *stats, struct Stats *min_stats, char *gui,
+  char *storage, char excluded_teams[64][64], char excluded_units[64][64]
+);
+
 /**
  * Print a nice summary with all the data fethced from the command line and db.
  *
@@ -236,7 +197,7 @@ int get_runes(
  * @param[in] rune_count Number of runes for each slot.
  * @param[in] max_combinations Total combinations to test during optimization.
  */
-void print_summary(
+void optimize_print_summary(
   struct Unit *unit, int* sets, int* stats, struct Stats *min_stats,
   char level, int rune_count[7], unsigned long max_combinations
 );
@@ -250,27 +211,53 @@ void print_summary(
  * @param[in] result Result to display.
  * @return SUCCESS or an error code.
  */
-int present_option(struct Unit *unit, Result *result);
+int optimize_print_result(struct Unit *unit, Result *result);
 
 /**
  * Prepares and prints the output for the GUI.
  *
- * Basically, it's JSON.
+ * Basically, it formats the output to JSON.
  *
  * @param[in] results All results.
  * @param[in] result_count Number of results.
  * @return SUCCESS or an error code.
  */
-int gui_output(Result results[5000], int result_count);
+int optimize_print_gui(Result results[5000], int result_count);
 
 /**
- * Starts the optimization process.
+ * Generates the query to get the runes from the databas for even slots.
  *
- * @param[in] argc Argument count.
- * @param[in] argv Argument list.
- * @return SUCCESS or an error code.
+ * @param[in] level Level to consider runes at.
+ * @param[in] sets Requested sets.
+ * @param[in] stats Requested sets for even slots.
+ * @param[in] excluded_teams List of teams whose unit's runes to exclude.
+ * @param[in] excluded_units List of units whose runes to exclude.
+ * @param[in] storage 1 to select only unassigned runes.
+ * @param[in] unit_id ID of the unit being optimized
+ * @param[out] query String with the query.
+ */
+void optimize_query_for_even_slots(
+  char level, int* sets, int* stats,
+  char excluded_teams[64][64], char excluded_units[64][64],
+  char storage, char unit_id[64], char query[2500]
+);
+
+/**
+ * Generates the query to get the runes from the databas for odd slots.
+ *
+ * @param[in] level Level to consider runes at.
+ * @param[in] sets Requested sets.
+ * @param[in] excluded_teams List of teams whose unit's runes to exclude.
+ * @param[in] excluded_units List of units whose runes to exclude.
+ * @param[in] storage 1 to select only unassigned runes.
+ * @param[in] unit_id ID of the unit being optimized
+ * @param[out] query String with the query.
  */
-int optimize(int argc, char *argv[]);
+void optimize_query_for_odd_slots(
+  char level, int* sets,
+  char excluded_teams[64][64], char excluded_units[64][64],
+  char storage, char unit_id[64], char query[2500]
+);
 
 /**
  * Sorts the result array.
@@ -302,3 +289,15 @@ unsigned int calculate_ehp(unsigned int hp, unsigned short def);
 unsigned short calculate_dmg(
   unsigned short atk, unsigned short crr, unsigned short crd
 );
+
+/**
+ * Starts the optimization process.
+ *
+ * @param[in] @param[in] argc Number of arguments passed to the optimize
+ * command.
+ * @param[in] argv Arguments passed to the optimize command.
+ * @return SUCCESS or an error code. See
+ * <a href="file:../error/error.h">../error/error.h</a> for a list of error
+ * codes.
+ */
+int cmd_optimize(int argc, char *argv[]);

+ 132 - 0
src/RuneOptimizer/optimize/optimize_count_runes_for_sets.c

@@ -0,0 +1,132 @@
+/*
+ * This file is part of RuneOptimizer.
+ *
+ * RuneOptimizer is free software: you can redistribute it and/or modify it
+ * under the terms of the GNU General Public License as published by the Free
+ * Software Foundation, either version 3 of the License, or (at your option)
+ * any later version.
+ *
+ * RuneOptimizer is distributed in the hope that it will be useful, but WITHOUT
+ * ANY WARRANTY; without even the implied warranty of MERCHANTABILITY or
+ * FITNESS FOR A PARTICULAR PURPOSE. See the GNU General Public License for
+ * more details.
+ *
+ * You should have received a copy of the GNU General Public License along with
+ * RuneOptimizer. If not, see <https://www.gnu.org/licenses/>.
+ */
+
+char optimize_count_runes_for_sets(
+  int sets[3], Rune_Set_Count *requested_set_count
+){
+    requested_set_count->energy = 0;
+    requested_set_count->guard = 0;
+    requested_set_count->swift = 0;
+    requested_set_count->blade = 0;
+    requested_set_count->rage = 0;
+    requested_set_count->focus = 0;
+    requested_set_count->endure = 0;
+    requested_set_count->fatal = 0;
+    requested_set_count->despair = 0;
+    requested_set_count->vampire = 0;
+    requested_set_count->violent = 0;
+    requested_set_count->nemesis = 0;
+    requested_set_count->will = 0;
+    requested_set_count->shield = 0;
+    requested_set_count->revenge = 0;
+    requested_set_count->destroy = 0;
+    requested_set_count->fight = 0;
+    requested_set_count->determination = 0;
+    requested_set_count->enhance = 0;
+    requested_set_count->accuracy = 0;
+    requested_set_count->tolerance = 0;
+    char total_requested_runes = 0;
+    for (int i = 0; i < 3; i ++){
+        switch (sets[i]){
+            case ENERGY:
+                requested_set_count->energy += 2;
+                total_requested_runes += 2;
+                break;
+            case GUARD:
+                requested_set_count->guard += 2;
+                total_requested_runes += 2;
+                break;
+            case SWIFT:
+                requested_set_count->swift += 4;
+                total_requested_runes += 4;
+                break;
+            case BLADE:
+                requested_set_count->blade += 2;
+                total_requested_runes += 2;
+                break;
+            case RAGE:
+                requested_set_count->rage += 4;
+                total_requested_runes += 4;
+                break;
+            case FOCUS:
+                requested_set_count->focus += 2;
+                total_requested_runes += 2;
+                break;
+            case ENDURE:
+                requested_set_count->endure += 2;
+                total_requested_runes += 2;
+                break;
+            case FATAL:
+                requested_set_count->fatal += 4;
+                total_requested_runes += 4;
+                break;
+            case DESPAIR:
+                requested_set_count->despair += 2;
+                total_requested_runes += 2;
+                break;
+            case VAMPIRE:
+                requested_set_count->vampire += 4;
+                total_requested_runes += 4;
+                break;
+            case VIOLENT:
+                requested_set_count->violent += 4;
+                total_requested_runes += 4;
+                break;
+            case NEMESIS:
+                requested_set_count->nemesis += 2;
+                total_requested_runes += 2;
+                break;
+            case WILL:
+                requested_set_count->will += 2;
+                total_requested_runes += 2;
+                break;
+            case SHIELD:
+                requested_set_count->shield += 2;
+                total_requested_runes += 2;
+                break;
+            case REVENGE:
+                requested_set_count->revenge += 2;
+                total_requested_runes += 2;
+                break;
+            case DESTROY:
+                requested_set_count->destroy += 2;
+                total_requested_runes += 2;
+                break;
+            case FIGHT:
+                requested_set_count->fight += 2;
+                total_requested_runes += 2;
+                break;
+            case DETERMINATION:
+                requested_set_count->determination += 2;
+                total_requested_runes += 2;
+                break;
+            case ENHANCE:
+                requested_set_count->enhance += 2;
+                total_requested_runes += 2;
+                break;
+            case ACCURACY:
+                requested_set_count->accuracy += 2;
+                total_requested_runes += 2;
+                break;
+            case TOLERANCE:
+                requested_set_count->tolerance += 2;
+                total_requested_runes += 2;
+                break;
+        }
+    }
+    return total_requested_runes;
+}

+ 65 - 0
src/RuneOptimizer/optimize/optimize_fetch_unit.c

@@ -0,0 +1,65 @@
+/*
+ * This file is part of RuneOptimizer.
+ *
+ * RuneOptimizer is free software: you can redistribute it and/or modify it
+ * under the terms of the GNU General Public License as published by the Free
+ * Software Foundation, either version 3 of the License, or (at your option)
+ * any later version.
+ *
+ * RuneOptimizer is distributed in the hope that it will be useful, but WITHOUT
+ * ANY WARRANTY; without even the implied warranty of MERCHANTABILITY or
+ * FITNESS FOR A PARTICULAR PURPOSE. See the GNU General Public License for
+ * more details.
+ *
+ * You should have received a copy of the GNU General Public License along with
+ * RuneOptimizer. If not, see <https://www.gnu.org/licenses/>.
+ */
+
+int optimize_fetch_unit(char id[64], struct Unit *unit){
+    sqlite3_stmt *stmt_unit;
+    char *parameters[2] = {id, id};
+    db_query(
+      &stmt_unit,
+      "SELECT "
+      "id, name, base_hp, base_atk, base_def, base_spd, base_crr, base_crd, "
+      "base_res, base_acc, current_hp, current_atk, current_def, current_spd, "
+      "current_crr, current_crd, current_res, current_acc "
+      "FROM units WHERE id = ? OR name = ?",
+      parameters
+    );
+
+    // Fetch just one line
+    int step = sqlite3_step(stmt_unit);
+
+    // Populate the unit structure with the red data.
+    if (step != SQLITE_ROW) {
+        fprintf(stderr, "Unit not found: %s\n", sqlite3_errmsg(db));
+        sqlite3_finalize(stmt_unit);
+        return(ERROR_DB_UNIT_NOT_FOUND);
+    }
+    strcpy(unit->id, sqlite3_column_text(stmt_unit, 0));
+    strcpy(unit->name, sqlite3_column_text(stmt_unit, 1));
+    unit->base_hp = sqlite3_column_int(stmt_unit, 2);
+    unit->base_atk = sqlite3_column_int(stmt_unit, 3);
+    unit->base_def = sqlite3_column_int(stmt_unit, 4);
+    unit->base_spd = sqlite3_column_int(stmt_unit, 5);
+    unit->base_crr = sqlite3_column_int(stmt_unit, 6);
+    unit->base_crd = sqlite3_column_int(stmt_unit, 7);
+    unit->base_res = sqlite3_column_int(stmt_unit, 8);
+    unit->base_acc = sqlite3_column_int(stmt_unit, 9);
+    unit->base_ehp = calculate_ehp(unit->base_hp, unit->base_def);
+    unit->base_dmg =
+      calculate_dmg(unit->base_atk, unit->base_crr, unit->base_crd);
+    unit->current_hp = sqlite3_column_int(stmt_unit, 10);
+    unit->current_atk = sqlite3_column_int(stmt_unit, 11);
+    unit->current_def = sqlite3_column_int(stmt_unit, 12);
+    unit->current_spd = sqlite3_column_int(stmt_unit, 13);
+    unit->current_crr = sqlite3_column_int(stmt_unit, 14);
+    unit->current_crd = sqlite3_column_int(stmt_unit, 15);
+    unit->current_res = sqlite3_column_int(stmt_unit, 16);
+    unit->current_acc = sqlite3_column_int(stmt_unit, 17);
+    unit->current_ehp = calculate_ehp(unit->current_hp, unit->current_def);
+    unit->current_dmg =
+      calculate_dmg(unit->current_atk, unit->current_crr, unit->current_crd);
+    return(SUCCESS);
+}

+ 56 - 0
src/RuneOptimizer/optimize/optimize_get_runes.c

@@ -0,0 +1,56 @@
+/*
+ * This file is part of RuneOptimizer.
+ *
+ * RuneOptimizer is free software: you can redistribute it and/or modify it
+ * under the terms of the GNU General Public License as published by the Free
+ * Software Foundation, either version 3 of the License, or (at your option)
+ * any later version.
+ *
+ * RuneOptimizer is distributed in the hope that it will be useful, but WITHOUT
+ * ANY WARRANTY; without even the implied warranty of MERCHANTABILITY or
+ * FITNESS FOR A PARTICULAR PURPOSE. See the GNU General Public License for
+ * more details.
+ *
+ * You should have received a copy of the GNU General Public License along with
+ * RuneOptimizer. If not, see <https://www.gnu.org/licenses/>.
+ */
+
+int optimize_get_runes(
+  char query_even[1500], char query_odd[1500],
+  struct Rune runes[7][600], int rune_count[7]
+){
+    char **query;
+    sqlite3 *db = NULL;
+    sqlite3_stmt *stmt_runes[7];
+    char *parameters[1];
+    parameters[0] = malloc(sizeof(int));
+    for (char i = 1; i < 7; i ++){
+        if (i % 2 == 0) query = &query_even;
+        else  query = &query_odd;
+        sprintf(parameters[0], "%d", i);
+        db_query(&stmt_runes[i], *query, parameters);
+        int j = 0;
+        while (SQLITE_ROW == sqlite3_step(stmt_runes[i])){
+            strcpy(runes[i][j].id, sqlite3_column_text(stmt_runes[i], 0));
+            strcpy(runes[i][j].unit, sqlite3_column_text(stmt_runes[i], 1));
+            runes[i][j].slot = sqlite3_column_int(stmt_runes[i], 2);
+            runes[i][j].set = sqlite3_column_int(stmt_runes[i], 3);
+            runes[i][j].hp_flat = sqlite3_column_int(stmt_runes[i], 4);
+            runes[i][j].atk_flat = sqlite3_column_int(stmt_runes[i], 5);
+            runes[i][j].def_flat = sqlite3_column_int(stmt_runes[i], 6);
+            runes[i][j].hp_percent = sqlite3_column_int(stmt_runes[i], 7);
+            runes[i][j].atk_percent = sqlite3_column_int(stmt_runes[i], 8);
+            runes[i][j].def_percent = sqlite3_column_int(stmt_runes[i], 9);
+            runes[i][j].spd = sqlite3_column_int(stmt_runes[i], 10);
+            runes[i][j].crr = sqlite3_column_int(stmt_runes[i], 11);
+            runes[i][j].crd = sqlite3_column_int(stmt_runes[i], 12);
+            runes[i][j].res = sqlite3_column_int(stmt_runes[i], 13);
+            runes[i][j].acc = sqlite3_column_int(stmt_runes[i], 14);
+            j ++;
+        }
+        rune_count[i] = j;
+    }
+    for (int r = 1; r < 7; r ++) sqlite3_finalize(stmt_runes[r]);
+    free(parameters[0]);
+    return SUCCESS;
+}

+ 396 - 0
src/RuneOptimizer/optimize/optimize_parse_arguments.c

@@ -0,0 +1,396 @@
+/*
+ * This file is part of RuneOptimizer.
+ *
+ * RuneOptimizer is free software: you can redistribute it and/or modify it
+ * under the terms of the GNU General Public License as published by the Free
+ * Software Foundation, either version 3 of the License, or (at your option)
+ * any later version.
+ *
+ * RuneOptimizer is distributed in the hope that it will be useful, but WITHOUT
+ * ANY WARRANTY; without even the implied warranty of MERCHANTABILITY or
+ * FITNESS FOR A PARTICULAR PURPOSE. See the GNU General Public License for
+ * more details.
+ *
+ * You should have received a copy of the GNU General Public License along with
+ * RuneOptimizer. If not, see <https://www.gnu.org/licenses/>.
+ */
+
+int optimize_parse_arguments(
+  int argc, char argv[][128], char id[64], char *level,
+  int *sets, int *stats, struct Stats *min_stats, char *gui,
+  char *storage, char excluded_teams[64][64], char excluded_units[64][64]
+){
+    // Get unit identifier
+    if (argc < 1){
+        fprintf(stderr, "No unit specified for optimization\n");
+        return ERROR_INPUT_NO_UNIT;
+    }
+    strncpy(id, argv[0], 64);
+
+    // Assign default values for non-value arguments
+    *storage = 0;
+    *gui = 0;
+
+    // Loop command line arguments
+    for (int i = 1; i < argc; i ++){
+
+        // Rune level arguments
+        if (strcmp("--level", argv[i]) == 0 || strcmp("-l", argv[i]) == 0){
+            if (i < argc - 1){
+                if (strcmp("current", argv[i + 1]) == 0) *level = 0;
+                else if (strcmp("12", argv[i + 1]) == 0) *level = 12;
+                else if (strcmp("15", argv[i + 1]) == 0) *level = 15;
+                else{
+                    fprintf(
+                      stderr,
+                      "Invalid option for argument %s: %s\n"
+                      "Valid options are 'current', '12' or '15'\n",
+                      argv[i], argv[i + 1]
+                    );
+                    return ERROR_INPUT_INVALID_LEVEL;
+                }
+                i ++; // Advance one position in argument reading
+            }
+            else{
+                fprintf(
+                  stderr,
+                  "Argument %s requires a value.\n"
+                  "Valid options are 'current', '12' or '15'\n", argv[i]
+                );
+                return ERROR_INPUT_NO_LEVEL;
+            }
+        }
+
+        // Excluded teams
+        else if (
+          strcmp("--no-teams", argv[i]) == 0 || strcmp("-x", argv[i]) == 0
+        ){
+            if (i < argc - 1){
+                // Separate string by commas
+                int j = 0;
+                // Returns first token
+                char opt_list[64];
+                strcpy(opt_list, argv[i + 1]);
+                char *token = strtok(opt_list, ",");
+
+                // Keep printing tokens while one of the
+                // delimiters present in the list, or until its complete
+                while (token != NULL){
+                    strcpy(excluded_teams[j], token);
+                    token = strtok(NULL, ",");
+                    j ++;
+                }
+                i ++; // Advance one position in argument reading
+            }
+            else{
+                fprintf(
+                  stderr,
+                  "Argument %s requires a comma-separated list of values.\n",
+                  argv[i]
+                );
+                return ERROR_INPUT_NO_TEAMS;
+            }
+        }
+
+        // Excluded units
+        else if (
+          strcmp("--no-units", argv[i]) == 0 || strcmp("-u", argv[i]) == 0
+        ){
+            if (i < argc - 1){
+                // Separate string by commas
+                int j = 0;
+                // Returns first token
+                char *token = strtok(argv[i + 1], ",");
+
+                // Keep printing tokens while one of the
+                // delimiters present in the list, or until its complete
+                while (token != NULL && j < 3){
+                    strcpy(excluded_units[j], token);
+                    token = strtok(NULL, ",");
+                    j ++;
+                }
+                i ++; // Advance one position in argument reading
+            }
+            else{
+                fprintf(
+                  stderr,
+                  "Argument %s requires a comma-separated list of values.\n",
+                  argv[i]
+                );
+                return ERROR_INPUT_NO_SET;
+            }
+        }
+
+        // Rune sets argument
+        else if (strcmp("--sets", argv[i]) == 0 || strcmp("-e", argv[i]) == 0){
+            if (i < argc - 1){
+                // Separate string by commas
+                int j = 0;
+                // Returns first token
+                char *token = strtok(argv[i + 1], ",");
+
+                // Keep printing tokens while one of the
+                // delimiters present in the list, or until its complete
+                while (token != NULL && j < 3){
+                    if (strcmp(token, "energy") == 0) sets[j] = ENERGY;
+                    else if (strcmp(token, "guard") == 0) sets[j] = GUARD;
+                    else if (strcmp(token, "swift") == 0) sets[j] = SWIFT;
+                    else if (strcmp(token, "blade") == 0) sets[j] = BLADE;
+                    else if (strcmp(token, "rage") == 0) sets[j] = RAGE;
+                    else if (strcmp(token, "focus") == 0) sets[j] = FOCUS;
+                    else if (strcmp(token, "endure") == 0) sets[j] = ENDURE;
+                    else if (strcmp(token, "fatal") == 0) sets[j] = FATAL;
+                    else if (strcmp(token, "despair") == 0) sets[j] = DESPAIR;
+                    else if (strcmp(token, "vampire") == 0) sets[j] = VAMPIRE;
+                    else if (strcmp(token, "violent") == 0) sets[j] = VIOLENT;
+                    else if (strcmp(token, "nemesis") == 0) sets[j] = NEMESIS;
+                    else if (strcmp(token, "will") == 0) sets[j] = WILL;
+                    else if (strcmp(token, "shield") == 0) sets[j] = SHIELD;
+                    else if (strcmp(token, "revenge") == 0) sets[j] = REVENGE;
+                    else if (strcmp(token, "destroy") == 0) sets[j] = DESTROY;
+                    else if (strcmp(token, "fight") == 0) sets[j] = FIGHT;
+                    else if (strcmp(token, "determination") == 0)
+                        sets[j] = DETERMINATION;
+                    else if (strcmp(token, "enhance") == 0) sets[j] = ENHANCE;
+                    else if (strcmp(token, "accuracy") == 0) sets[j] = ACCURACY;
+                    else if (strcmp(token, "tolerance") == 0)
+                        sets[j] = TOLERANCE;
+                    else{
+                        fprintf(stderr, "Unknown rune set %s.\n", token);
+                        return ERROR_INPUT_INVALID_SET;
+                    }
+                    token = strtok(NULL, ",");
+                    j ++;
+                }
+                i ++; // Advance one position in argument reading
+            }
+            else{
+                fprintf(
+                  stderr,
+                  "Argument %s requires a comma-separated list of values.\n",
+                  argv[i]
+                );
+                return ERROR_INPUT_NO_SET;
+            }
+        }
+
+        // Accepted stats arguments
+        else if (strcmp("--stats", argv[i]) == 0 || strcmp("-t", argv[i]) == 0){
+            if (i < argc - 1){
+                // Separate string by commas
+                int j = 0;
+                // Returns first token
+                char *token = strtok(argv[i + 1], ",");
+
+                // Keep printing tokens while one of the
+                // delimiters present in the list, or until its complete
+                while (token != NULL && j < 3){
+                    if (strcmp(token, "hp") == 0) stats[j] = HP_PERCENT;
+                    else if (strcmp(token, "atk") == 0) stats[j] = ATK_PERCENT;
+                    else if (strcmp(token, "def") == 0) stats[j] = DEF_PERCENT;
+                    else if (strcmp(token, "hpflat") == 0) stats[j] = HP_FLAT;
+                    else if (strcmp(token, "atkflat") == 0) stats[j] = ATK_FLAT;
+                    else if (strcmp(token, "defflat") == 0) stats[j] = DEF_FLAT;
+                    else if (strcmp(token, "spd") == 0) stats[j] = SPD;
+                    else if (strcmp(token, "crr") == 0) stats[j] = CRR;
+                    else if (strcmp(token, "crd") == 0) stats[j] = CRD;
+                    else if (strcmp(token, "res") == 0) stats[j] = RES;
+                    else if (strcmp(token, "acc") == 0) stats[j] = ACC;
+                    else{
+                        fprintf(stderr, "Unknown rune stat %s.\n", token);
+                        return ERROR_INPUT_INVALID_STAT;
+                    }
+                    token = strtok(NULL, ",");
+                    j ++;
+                }
+                i ++; // Advance one position in argument reading
+            }
+            else{
+                fprintf(
+                  stderr,
+                  "Argument %s requires a comma-separated list of values.\n",
+                  argv[i]
+                );
+                return ERROR_INPUT_NO_STAT;
+            }
+        }
+
+        // Minimum stats arguments.
+        else if (
+          strcmp("--min-hp", argv[i]) == 0 || strcmp("-h", argv[i]) == 0
+        ){
+            if (i < argc - 1){
+                unsigned short stat_tmp = atoi(argv[i + 1]);
+                if (stat_tmp == 1) stat_tmp = 0;
+                min_stats->hp = stat_tmp;
+                i ++; // Advance one position in argument reading
+            }
+            else{
+                fprintf(
+                  stderr, "Argument %s requires a numeric value.\n", argv[i]
+                );
+                return ERROR_INPUT_NO_HP;
+            }
+        }
+        else if (
+          strcmp("--min-atk", argv[i]) == 0 || strcmp("-a", argv[i]) == 0
+        ){
+            if (i < argc - 1){
+                unsigned short stat_tmp = atoi(argv[i + 1]);
+                if (stat_tmp == 1) stat_tmp = 0;
+                min_stats->atk = stat_tmp;
+                i ++; // Advance one position in argument reading
+            }
+            else{
+                fprintf(
+                  stderr, "Argument %s requires a numeric value.\n", argv[i]
+                );
+                return ERROR_INPUT_NO_ATK;
+            }
+        }
+        else if (
+          strcmp("--min-def", argv[i]) == 0 || strcmp("-d", argv[i]) == 0
+        ){
+            if (i < argc - 1){
+                unsigned short stat_tmp = atoi(argv[i + 1]);
+                if (stat_tmp == 1) stat_tmp = 0;
+                min_stats->def = stat_tmp;
+                i ++; // Advance one position in argument reading
+            }
+            else{
+                fprintf(
+                  stderr, "Argument %s requires a numeric value.\n", argv[i]
+                );
+                return ERROR_INPUT_NO_DEF;
+            }
+        }
+        else if (
+          strcmp("--min-spd", argv[i]) == 0 || strcmp("-s", argv[i]) == 0
+        ){
+            if (i < argc - 1){
+                unsigned short stat_tmp = atoi(argv[i + 1]);
+                if (stat_tmp == 1) stat_tmp = 0;
+                min_stats->spd = stat_tmp;
+                i ++; // Advance one position in argument reading
+            }
+            else{
+                fprintf(
+                  stderr, "Argument %s requires a numeric value.\n", argv[i]
+                );
+                return ERROR_INPUT_NO_SPD;
+            }
+        }
+        else if (
+          strcmp("--min-crr", argv[i]) == 0 || strcmp("-c", argv[i]) == 0
+        ){
+            if (i < argc - 1){
+                unsigned short stat_tmp = atoi(argv[i + 1]);
+                if (stat_tmp == 1) stat_tmp = 0;
+                else if (stat_tmp > 100) stat_tmp = 100;
+                min_stats->crr = stat_tmp;
+                // Advance one position in argument reading
+                i ++;
+            }
+            else{
+                fprintf(
+                  stderr, "Argument %s requires a numeric value.\n", argv[i]
+                );
+                return ERROR_INPUT_NO_CRR;
+            }
+        }
+        else if (
+          strcmp("--min-crd", argv[i]) == 0 || strcmp("-d", argv[i]) == 0
+        ){
+            if (i < argc - 1){
+                unsigned short stat_tmp = atoi(argv[i + 1]);
+                if (stat_tmp == 1) stat_tmp = 0;
+                min_stats->crd = stat_tmp;
+                i ++; // Advance one position in argument reading
+            }
+            else{
+                fprintf(
+                  stderr, "Argument %s requires a numeric value.\n", argv[i]
+                );
+                return ERROR_INPUT_NO_CRD;
+            }
+        }
+        else if (
+          strcmp("--min-res", argv[i]) == 0 || strcmp("-r", argv[i]) == 0
+        ){
+            if (i < argc - 1){
+                unsigned short stat_tmp = atoi(argv[i + 1]);
+                if (stat_tmp == 1) stat_tmp = 0;
+                else if (stat_tmp > 100) stat_tmp = 100;
+                min_stats->res = stat_tmp;
+                i ++; // Advance one position in argument reading
+            }
+            else{
+                fprintf(
+                  stderr, "Argument %s requires a numeric value.\n", argv[i]
+                );
+                return ERROR_INPUT_NO_RES;
+            }
+        }
+        else if (
+          strcmp("--min-acc", argv[i]) == 0 || strcmp("-f", argv[i]) == 0
+        ){
+            if (i < argc - 1){
+                unsigned short stat_tmp = atoi(argv[i + 1]);
+                if (stat_tmp == 1) stat_tmp = 0;
+                else if (stat_tmp > 85) stat_tmp = 85;
+                min_stats->acc = stat_tmp;
+                i ++; // Advance one position in argument reading
+            }
+            else{
+                fprintf(
+                  stderr, "Argument %s requires a numeric value.\n", argv[i]
+                );
+                return ERROR_INPUT_NO_ACC;
+            }
+        }
+        else if (
+          strcmp("--min-ehp", argv[i]) == 0 || strcmp("-p", argv[i]) == 0
+        ){
+            if (i < argc - 1){
+                unsigned int stat_tmp = atoi(argv[i + 1]);
+                if (stat_tmp == 1) stat_tmp = 0;
+                min_stats->ehp = stat_tmp;
+                i ++; // Advance one position in argument reading
+            }
+            else{
+                fprintf(
+                  stderr, "Argument %s requires a numeric value.\n", argv[i]
+                );
+                return ERROR_INPUT_NO_EHP;
+            }
+        }
+        else if (
+          strcmp("--min-dmg", argv[i]) == 0 || strcmp("-m", argv[i]) == 0
+        ){
+            if (i < argc - 1){
+                unsigned short stat_tmp = atoi(argv[i + 1]);
+                if (stat_tmp == 1) stat_tmp = 0;
+                min_stats->dmg = stat_tmp;
+                i ++; // Advance one position in argument reading
+            }
+            else{
+                fprintf(
+                  stderr, "Argument %s requires a numeric value.\n", argv[i]
+                );
+                return ERROR_INPUT_NO_DMG;
+            }
+        }
+        // Storage option?
+        else if (
+          strcmp("--storage", argv[i]) == 0 || strcmp("-o", argv[i]) == 0
+        ){
+            *storage = 1;
+        }
+        // GUI invoked?
+        else if (strcmp("--gui", argv[i]) == 0 || strcmp("-g", argv[i]) == 0){
+            *gui = 1;
+        }
+
+    }
+    return SUCCESS;
+}

+ 433 - 0
src/RuneOptimizer/optimize/optimize_print.c

@@ -0,0 +1,433 @@
+/*
+ * This file is part of RuneOptimizer.
+ *
+ * RuneOptimizer is free software: you can redistribute it and/or modify it
+ * under the terms of the GNU General Public License as published by the Free
+ * Software Foundation, either version 3 of the License, or (at your option)
+ * any later version.
+ *
+ * RuneOptimizer is distributed in the hope that it will be useful, but WITHOUT
+ * ANY WARRANTY; without even the implied warranty of MERCHANTABILITY or
+ * FITNESS FOR A PARTICULAR PURPOSE. See the GNU General Public License for
+ * more details.
+ *
+ * You should have received a copy of the GNU General Public License along with
+ * RuneOptimizer. If not, see <https://www.gnu.org/licenses/>.
+ */
+
+void optimize_print_summary(
+  struct Unit *unit, int* sets, int* stats, struct Stats *min_stats,
+  char level, int rune_count[7], unsigned long max_combinations
+){
+    // This is an output example:
+    ////////////////////////////////
+    //
+    // -----------------------------------    Requested rune sets:
+    // | Lushen                          |       RAGE  BLADE
+    // | ID: 7223811472                  |
+    // -----------------------------------    Accepted stats:
+    // | STAT | BASE   | CURR.  | MIN.   |       ATK  CRR  CRD
+    // -----------------------------------
+    // | HP:  |  9225  | 12262  | 10000  |    Considering runes at level 15
+    // | ATK: |   900  |  2482  |  2482  |
+    // | DEF: |   461  |   703  |   703  |    Runes considered by slot:
+    // | SPD: |   103  |   159  |   159  |      1: 27    2: 39    3: 25
+    // | CRR: |    15% |    79% |    79% |      4: 35    5: 24    6: 32
+    // | CRD: |    50% |   188% |   188% |
+    // | RES: |    15% |    35% |    35% |    Total combinations: 707616000
+    // | ACC: |     0% |    11% |    10% |
+    // -----------------------------------
+    //
+    printf(
+      " -----------------------------------------    Requested rune sets:\n"
+    );
+    printf(" | %*s |      ", -37, unit->name);
+    for (int i = 0; i < 3; i ++){
+        if (sets[i] != 0) printf(" %s ", set_names[sets[i]]);
+        else break;
+    }
+    printf("\n");
+    printf(" | ID: %*s |\n", -33, unit->id);
+    printf(" -----------------------------------------    Accepted stats:\n");
+    printf(" | STAT | BASE     | CURR.    | MIN.     |      ");
+    for (int i = 0; i < 12; i ++){
+        if (stats[i] != 0) printf(" %s ", stat_names[stats[i]]);
+        else break;
+    }
+    printf("\n");
+    printf(" -----------------------------------------\n");
+    printf(
+      " | HP:  | %*d  | %*d  | %*d  |    ", 7,
+      unit->base_hp, 7, unit->current_hp, 7, min_stats->hp
+    );
+    if (level == 0) printf("Using runes at their current level\n");
+    else printf("Considering runes at level %d\n", level);
+    printf(
+      " | ATK: | %*d  | %*d  | %*d  |\n", 7,
+      unit->base_atk, 7, unit->current_atk, 7, min_stats->atk
+    );
+    printf(
+      " | DEF: | %*d  | %*d  | %*d  |    Runes considered by slot:\n",
+      7, unit->base_def, 7, unit->current_def, 7, min_stats->def
+    );
+    printf(
+      " | SPD: | %*d  | %*d  | %*d  |      1:%*d    2:%*d    3:%*d\n",
+      7, unit->base_spd, 7, unit->current_spd, 7, min_stats->spd,
+      3, rune_count[1], 3, rune_count[2], 3, rune_count[3]
+    );
+    printf(
+      " | CRR: | %*d\% | %*d\% | %*d\% |      4:%*d    5:%*d    6:%*d\n",
+      7, unit->base_crr, 7, unit->current_crr, 7, min_stats->crr,
+      3, rune_count[4], 3, rune_count[5], 3, rune_count[6]
+    );
+    printf(
+      " | CRD: | %*d\% | %*d\% | %*d\% |\n",
+      7, unit->base_crd, 7, unit->current_crd, 7, min_stats->crd
+    );
+    printf(
+      " | RES: | %*d\% | %*d\% | %*d\% |    Total combinations: %d\n",
+      7, unit->base_res, 7, unit->current_res, 7, min_stats->res,
+      max_combinations
+    );
+    printf(
+      " | ACC: | %*d\% | %*d\% | %*d\% |\n",
+      7, unit->base_acc, 7, unit->current_acc, 7, min_stats->acc
+    );
+    printf(
+      " | EHP: | %*d  | %*d  | %*d  |\n",
+      7, unit->base_ehp, 7, unit->current_ehp, 7, min_stats->ehp
+    );
+    printf(
+      " | DMG: | %*d  | %*d  | %*d  |\n",
+      7, unit->base_dmg, 7, unit->current_dmg, 7, min_stats->dmg
+    );
+    printf(" -----------------------------------------\n");
+    return;
+}
+
+int optimize_print_result(struct Unit *unit, Result *result){
+    printf(" ------------------------------\n");
+    printf(" | %*s |\n", -26, unit->name);
+    printf(" | ID: %*s |\n", -22, unit->id);
+    printf(" ------------------------------\n");
+    printf(" | STAT | CURR.    | NEW      |\n");
+    printf(" ------------------------------\n");
+    printf(" | HP:  | %*d  | %*d  |\n", 7, unit->current_hp, 7, result->stats.hp);
+    printf(" | ATK: | %*d  | %*d  |\n", 7, unit->current_atk, 7, result->stats.atk);
+    printf(" | DEF: | %*d  | %*d  |\n", 7, unit->current_def, 7, result->stats.def);
+    printf(" | SPD: | %*d  | %*d  |\n", 7, unit->current_spd, 7, result->stats.spd);
+    printf(" | CRR: | %*d\% | %*d\% |\n", 7, unit->current_crr, 7, result->stats.crr);
+    printf(" | CRD: | %*d\% | %*d\% |\n", 7, unit->current_crd, 7, result->stats.crd);
+    printf(" | RES: | %*d\% | %*d\% |\n", 7, unit->current_res, 7, result->stats.res);
+    printf(" | ACC: | %*d\% | %*d\% |\n", 7, unit->current_acc, 7, result->stats.acc);
+    printf(" | EHP: | %*d  | %*d  |\n", 7, unit->current_ehp, 7, result->stats.ehp);
+    printf(" | DMG: | %*d  | %*d  |\n", 7, unit->current_dmg, 7, result->stats.dmg);
+    printf(" ------------------------------\n");
+
+    // This bit may be hard to follow.
+    // I'm populating  8 lines of text with data, to display the runes in
+    // a nice table format.
+    //
+    // This is an output exaple:
+    //
+    // ------------------------------  ------------------------------  ------------------------------
+    // |6|RAGE         | 23285581330|  |1|BLADE        | 22677809846|  |2|BLADE        | 21432847749|
+    // ------------------------------  ------------------------------  ------------------------------
+    // | Storage       |        +12 |  | Storage       |        +12 |  | Perna         |        +15 |
+    // ------------------------------  ------------------------------  ------------------------------
+    // | ACC           48           |  | ATK_FLAT     118           |  | SPD           42           |
+    // | RES            6           |  |                            |  |                            |
+    // | ATK_FLAT      19           |  | RES           14           |  | CRD           16           |
+    // | CRR           12           |  | ACC            8           |  | CRR           10           |
+    // | HP            14           |  | HP_FLAT      580           |  | ATK            7 + 3       |
+    // | CRD           14           |  | CRR           10           |  | DEF            7 + 3       |
+    // ------------------------------  ------------------------------  ------------------------------
+    //
+    // ------------------------------  ------------------------------  ------------------------------
+    // |5|RAGE         | 26260912967|  |4|RAGE         | 27947761086|  |3|RAGE         | 27654723287|
+    // ------------------------------  ------------------------------  ------------------------------
+    // | Lushen        |        +15 |  | Lushen        |        +15 |  | Covenant      |        +12 |
+    // ------------------------------  ------------------------------  ------------------------------
+    // | HP_FLAT     2448           |  | CRD           80           |  | DEF_FLAT     118           |
+    // |                            |  |                            |  | HP_FLAT      167           |
+    // | CRR           16           |  | CRR            6           |  | RES            8           |
+    // | SPD            6 + 2       |  | RES           11           |  | DEF           11           |
+    // | CRD           11           |  | SPD           18           |  | CRD           18           |
+    // | ATK            6 + 5       |  | ATK            8           |  | CRR           12           |
+    // ------------------------------  ------------------------------  ------------------------------
+    //
+    // I know, I'm breaking the 80-characters-line rule.
+
+    char present[8][130];
+    strcpy(present[0], "");
+    strcpy(present[1], "");
+    strcpy(present[2], "");
+    strcpy(present[3], "");
+    strcpy(present[4], "");
+    strcpy(present[5], "");
+    strcpy(present[6], "");
+    strcpy(present[7], "");
+
+    // Retrieve the runes from the database
+    printf("\n");
+    char *parameters[1];
+    for (int i = 6; i != 0;){
+        parameters[0] = result->rune_ids[i - 1];
+        sqlite3_stmt *rune_res;
+
+        db_query(
+          &rune_res,
+          "SELECT "
+          "runes.id, runes.slot, runes.type, units.id, units.name, runes.level "
+          "FROM runes LEFT JOIN units ON runes.unit = units.id "
+          "WHERE runes.id = ?",
+          parameters
+        );
+        if (SQLITE_ROW == sqlite3_step(rune_res)) {
+            char tmp[130];
+            strcpy(tmp, "");
+            strcat(present[0], "|");
+            sprintf(tmp, "%*d", 1, sqlite3_column_int(rune_res, 1));
+            strcat(present[0], tmp);
+            strcat(present[0], "|");
+            sprintf(
+              tmp, "%*s|", -13, set_names[sqlite3_column_int(rune_res, 2)]
+            );
+            strcat(present[0], tmp);
+            sprintf(tmp, "%*s|  ", 12, sqlite3_column_text(rune_res, 0));
+            strcat(present[0], tmp);
+            strcat(present[1], "|");
+            if (sqlite3_column_type(rune_res, 3) == SQLITE_NULL){
+                sprintf(tmp, " %*s", -14, "Storage");
+                strcat(present[1], tmp);
+                strcat(present[1], "|");
+            }
+            else{
+                sprintf(tmp, " %*s", -14, sqlite3_column_text(rune_res, 4));
+                strcat(present[1], tmp);
+                strcat(present[1], "|");
+            }
+            // Rune level
+            sprintf(
+              tmp, "        +%*s |  ", 2, sqlite3_column_text(rune_res, 5)
+            );
+            strcat(present[1], tmp);
+
+            // Get stats
+            sqlite3_stmt *stats_res;
+            db_query(
+              &stats_res,
+              "SELECT rune, slot, stat, value, enchant, grind "
+              "FROM rune_stats "
+              "WHERE rune = ?",
+              parameters
+            );
+            int curr_slot = -1;
+            while (1 == 1){
+                int status = sqlite3_step(stats_res);
+                if (status == SQLITE_ROW){
+                    // Print empty lines for no-stats
+                    while (sqlite3_column_int(stats_res, 1) != curr_slot){
+                        sprintf(tmp, "|                            |  ");
+                        strcat(present[curr_slot + 3], tmp);
+                        curr_slot ++;
+                    }
+                    if (sqlite3_column_int(stats_res, 1) == curr_slot){
+                        strcat(present[curr_slot + 3], "| ");
+                        sprintf(
+                          tmp,
+                          "%*s",
+                          -9, stat_names[sqlite3_column_int(stats_res, 2)]
+                        );
+                        strcat(present[curr_slot + 3], tmp);
+                        sprintf(
+                          tmp, " %*d", 6, sqlite3_column_int(stats_res, 3)
+                        );
+                        strcat(present[curr_slot + 3], tmp);
+
+                        // Display grinds
+                        if (sqlite3_column_int(stats_res, 5) > 0){
+                            sprintf(
+                              tmp,
+                              " + %*d", -8, sqlite3_column_int(stats_res, 5)
+                            );
+                        }
+                        else{
+                            sprintf(tmp, "           ");
+                        }
+                        strcat(present[curr_slot + 3], tmp);
+                        strcat(present[curr_slot + 3], "|  ");
+                    }
+
+                    curr_slot ++;
+                    }
+                else{
+                    break;
+                }
+            }
+            // Populate all empty stat lines
+            while (curr_slot <= 4){
+                sprintf(tmp, "|                            |  ");
+                strcat(present[curr_slot + 3], tmp);
+                curr_slot ++;
+            }
+            sqlite3_finalize(stats_res);
+        }
+        else{
+            fprintf(stderr, "Errors in row: %s\n", sqlite3_errmsg(db));
+        }
+        sqlite3_finalize(rune_res);
+
+        // Loop control
+        // It's weird, but I wanna present the runes in the same format the
+        // game does:
+        //
+        // 6 1 2
+        // 5 4 3
+        // After slots 2 and 3, the generated strings are written.
+        if (i == 6) i = 1;
+        else if (i == 1) i = 2;
+        else if (i == 2){
+            // Print and reinitialize the strings
+            printf(
+              "------------------------------  "
+              "------------------------------  "
+              "------------------------------\n"
+            );
+            printf(present[0]);
+            printf(
+              "\n------------------------------  "
+              "------------------------------  "
+              "------------------------------\n"
+            );
+            printf(present[1]);
+            printf(
+              "\n------------------------------  "
+              "------------------------------  "
+              "------------------------------\n"
+            );
+            printf(present[2]);
+            printf("\n");
+            printf(present[3]);
+            printf("\n");
+            printf(present[4]);
+            printf("\n");
+            printf(present[5]);
+            printf("\n");
+            printf(present[6]);
+            printf("\n");
+            printf(present[7]);
+            printf(
+              "\n------------------------------  "
+              "------------------------------  "
+              "------------------------------\n"
+            );
+            strcpy(present[0], "");
+            strcpy(present[1], "");
+            strcpy(present[2], "");
+            strcpy(present[3], "");
+            strcpy(present[4], "");
+            strcpy(present[5], "");
+            strcpy(present[6], "");
+            strcpy(present[7], "");
+            i = 5;
+        }
+        else if (i == 5) i = 4;
+        else if (i == 4) i = 3;
+        else if (i == 3){
+            // Print and exit loop
+            printf(
+              "\n------------------------------  "
+              "------------------------------  "
+              "------------------------------\n"
+            );
+            printf(present[0]);
+            printf(
+              "\n------------------------------  "
+              "------------------------------  "
+              "------------------------------\n"
+            );
+            printf(present[1]);
+            printf(
+              "\n------------------------------  "
+              "------------------------------  "
+              "------------------------------\n"
+            );
+            printf(present[2]);
+            printf("\n");
+            printf(present[3]);
+            printf("\n");
+            printf(present[4]);
+            printf("\n");
+            printf(present[5]);
+            printf("\n");
+            printf(present[6]);
+            printf("\n");
+            printf(present[7]);
+            printf(
+              "\n------------------------------  "
+              "------------------------------  "
+              "------------------------------\n"
+            );
+            i = 0;
+        }
+    }
+    return SUCCESS;
+}
+
+int optimize_print_gui(Result results[5000], int result_count){
+    //Print for GUI
+    char tmp[300];
+    strcpy(tmp, "");
+    char json[300];
+    printf("{\"result_count\":%d,\"results\":[", result_count);
+    int result_limit = 100;
+    for (int i = 0; i < result_count && i < result_limit; i++){
+        //printf("RES LOOP %d", i);
+        sprintf(tmp, "{\"id\":%d,\"rating\":%d,", i, results[i].rating);
+        strcpy(json, tmp);
+        sprintf(tmp, "\"hp\":%d,", results[i].stats.hp);
+        strcat(json, tmp);
+        sprintf(tmp, "\"atk\":%d,", results[i].stats.atk);
+        strcat(json, tmp);
+        sprintf(tmp, "\"dfc\":%d,", results[i].stats.def);
+        strcat(json, tmp);
+        sprintf(tmp, "\"spd\":%d,", results[i].stats.spd);
+        strcat(json, tmp);
+        sprintf(tmp, "\"crr\":%d,", results[i].stats.crr);
+        strcat(json, tmp);
+
+        sprintf(tmp, "\"crd\":%d,", results[i].stats.crd);
+        strcat(json, tmp);
+        sprintf(tmp, "\"res\":%d,", results[i].stats.res);
+        strcat(json, tmp);
+        sprintf(tmp, "\"acc\":%d,", results[i].stats.acc);
+        strcat(json, tmp);
+        sprintf(tmp, "\"ehp\":%d,", results[i].stats.ehp);
+        strcat(json, tmp);
+        sprintf(tmp, "\"dmg\":%d,", results[i].stats.dmg);
+        strcat(json, tmp);
+        strcat(json, "\"runes\":[");
+        //printf("    A %s", json);
+        for (int j = 0; j < 5; j++){
+            //printf("    RUNE LOOP %d", j);
+            sprintf(tmp, "\"%s\",", results[i].rune_ids[j]);
+            strcat(json, tmp);
+        }
+        //printf("    B %s", json);
+        sprintf(tmp, "\"%s\"", results[i].rune_ids[5]);
+        strcat(json, tmp);
+        strcat(json, "]},");
+
+        // If last result, remove last comma
+        if (i == result_count - 1 || i == result_limit - 1){
+            json[strlen(json) - 1] = 0;
+        }
+
+        printf(json);
+    }
+
+    // End and print
+    printf("]}\n");
+    return SUCCESS;
+}

+ 213 - 0
src/RuneOptimizer/optimize/optimize_query.c

@@ -0,0 +1,213 @@
+/*
+ * This file is part of RuneOptimizer.
+ *
+ * RuneOptimizer is free software: you can redistribute it and/or modify it
+ * under the terms of the GNU General Public License as published by the Free
+ * Software Foundation, either version 3 of the License, or (at your option)
+ * any later version.
+ *
+ * RuneOptimizer is distributed in the hope that it will be useful, but WITHOUT
+ * ANY WARRANTY; without even the implied warranty of MERCHANTABILITY or
+ * FITNESS FOR A PARTICULAR PURPOSE. See the GNU General Public License for
+ * more details.
+ *
+ * You should have received a copy of the GNU General Public License along with
+ * RuneOptimizer. If not, see <https://www.gnu.org/licenses/>.
+ */
+
+/**
+ * Generates the query to get the runes from the databas for even slots.
+ *
+ * @param[in] level Level to consider runes at.
+ * @param[in] sets Requested sets.
+ * @param[in] stats Requested sets for even slots.
+ * @param[in] excluded_teams List of teams whose unit's runes to exclude.
+ * @param[in] excluded_units List of units whose runes to exclude.
+ * @param[in] storage 1 to select only unassigned runes.
+ * @param[out] query String with the query.
+ */
+void optimize_query_for_even_slots(
+  char level, int* sets, int* stats,
+  char excluded_teams[64][64], char excluded_units[64][64],
+  char storage, char unit_id[64], char query[2500]
+){
+    char column[10];
+    if (level == 12) strcpy(column, "lv12_");
+    else if (level == 15) strcpy(column, "lv15_");
+    else strcpy(column, "current_");
+    strcpy(query, "SELECT id, unit, slot, type, ");
+    strcat(query, column);
+    strcat(query, "hp_flat, ");
+    strcat(query, column);
+    strcat(query, "atk_flat, ");
+    strcat(query, column);
+    strcat(query, "def_flat, ");
+    strcat(query, column);
+    strcat(query, "hp_percent, ");
+    strcat(query, column);
+    strcat(query, "atk_percent, ");
+    strcat(query, column);
+    strcat(query, "def_percent, ");
+    strcat(query, column);
+    strcat(query, "spd, ");
+    strcat(query, column);
+    strcat(query, "crr, ");
+    strcat(query, column);
+    strcat(query, "crd, ");
+    strcat(query, column);
+    strcat(query, "res, ");
+    strcat(query, column);
+    strcat(query, "acc FROM runes WHERE slot = ? AND type IN (");
+    char cur_set[2];
+    char stat_set[2];
+    if (sets[0] != 0){
+        sprintf(cur_set, "%d", sets[0]);
+        strcat(query, cur_set);
+        strcat(query, ", ");
+    }
+    if (sets[1] != 0){
+        sprintf(cur_set, "%d", sets[1]);
+        strcat(query, cur_set);
+        strcat(query, ", ");
+    }
+    if (sets[2] != 0){
+        sprintf(cur_set, "%d", sets[2]);
+        strcat(query, cur_set);
+        strcat(query, ", ");
+    }
+    strcat(query, "-1) AND main_stat IN (");
+    for (int i = 0; i < 12; i ++){
+        if (stats[i] != 0){
+            sprintf(stat_set, "%d", stats[i]);
+            strcat(query, stat_set);
+            strcat(query, ", ");
+        }
+        else{
+            break;
+        }
+    }
+    strcat(query, "-1) ");
+    if (storage == 1){
+        // They are not null, are empty!
+        strcat(query, " AND (unit = '' OR unit = '");
+        strcat(query, unit_id);
+        strcat(query, "') ");
+    }
+    // Excluded teams
+    strcat(query, " AND (unit = '' OR unit = '");
+    strcat(query, unit_id);
+    strcat(
+      query, "' OR unit NOT IN (SELECT unit FROM units_teams WHERE team IN("
+    );
+    for (int i = 0; i < 64 && excluded_teams[i][0] != '\0'; i ++){
+        strcat(query, "'");
+        strcat(query, excluded_teams[i]);
+        strcat(query, "',");
+    }
+    strcat(query, "'-1'))) ");
+    // Excluded units
+    strcat(query, " AND (unit = '' OR unit = '");
+    strcat(query, unit_id);
+    strcat(query, "' OR unit NOT IN (");
+    for (int i = 0; i < 64 && excluded_units[i][0] != '\0'; i ++){
+        strcat(query, "'");
+        strcat(query, excluded_units[i]);
+        strcat(query, "',");
+    }
+    strcat(query, "'-1')) ");
+    //printf("QUERY: %s\n", query);
+    return;
+}
+
+/**
+ * Generates the query to get the runes from the databas for odd slots.
+ *
+ * @param[in] level Level to consider runes at.
+ * @param[in] sets Requested sets.
+ * @param[in] excluded_teams List of teams whose unit's runes to exclude.
+ * @param[in] excluded_units List of units whose runes to exclude.
+ * @param[in] storage 1 to select only unassigned runes.
+ * @param[in] unit_id ID of the unit being optimized.
+ * @param[out] query String with the query.
+ */
+void optimize_query_for_odd_slots(
+  char level, int* sets,
+  char excluded_teams[64][64], char excluded_units[64][64],
+  char storage, char unit_id[64], char query[2500]
+){
+    char column[10];
+    if (level == 12) strcpy(column, "lv12_");
+    else if (level == 15) strcpy(column, "lv15_");
+    else strcpy(column, "current_");
+    strcpy(query, "SELECT id, unit, slot, type, ");
+    strcat(query, column);
+    strcat(query, "hp_flat, ");
+    strcat(query, column);
+    strcat(query, "atk_flat, ");
+    strcat(query, column);
+    strcat(query, "def_flat, ");
+    strcat(query, column);
+    strcat(query, "hp_percent, ");
+    strcat(query, column);
+    strcat(query, "atk_percent, ");
+    strcat(query, column);
+    strcat(query, "def_percent, ");
+    strcat(query, column);
+    strcat(query, "spd, ");
+    strcat(query, column);
+    strcat(query, "crr, ");
+    strcat(query, column);
+    strcat(query, "crd, ");
+    strcat(query, column);
+    strcat(query, "res, ");
+    strcat(query, column);
+    strcat(query, "acc FROM runes WHERE slot = ? AND type IN (");
+    char cur_set[2];
+    char stat_set[2];
+    if (sets[0] != 0){
+        sprintf(cur_set, "%d", sets[0]);
+        strcat(query, cur_set);
+        strcat(query, ", ");
+    }
+    if (sets[1] != 0){
+        sprintf(cur_set, "%d", sets[1]);
+        strcat(query, cur_set);
+        strcat(query, ", ");
+    }
+    if (sets[2] != 0){
+        sprintf(cur_set, "%d", sets[2]);
+        strcat(query, cur_set);
+        strcat(query, ", ");
+    }
+    strcat(query, "-1) ");
+    if (storage == 1){
+        // They are not null, are empty!
+        strcat(query, " AND (unit = '' OR unit = '");
+        strcat(query, unit_id);
+        strcat(query, "') ");
+    }
+    // Excluded teams
+    strcat(query, " AND (unit = '' OR unit = '");
+    strcat(query, unit_id);
+    strcat(
+      query, "' OR unit NOT IN (SELECT unit FROM units_teams WHERE team IN("
+    );
+    for (int i = 0; i < 64 && excluded_teams[i][0] != '\0'; i ++){
+        strcat(query, "'");
+        strcat(query, excluded_teams[i]);
+        strcat(query, "',");
+    }
+    strcat(query, "'-1'))) ");
+    // Excluded units
+    strcat(query, " AND (unit = '' OR unit = '");
+    strcat(query, unit_id);
+    strcat(query, "' OR unit NOT IN (");
+    for (int i = 0; i < 64 && excluded_units[i][0] != '\0'; i ++){
+        strcat(query, "'");
+        strcat(query, excluded_units[i]);
+        strcat(query, "',");
+    }
+    strcat(query, "'-1')) ");
+    //printf("QUERY: %s\n", query);
+    return;
+}

+ 15 - 423
src/RuneOptimizer/team/team.c

@@ -15,443 +15,35 @@
  * RuneOptimizer. If not, see <https://www.gnu.org/licenses/>.
  */
 
-/**
- * Parses the arguments passes to the team function and calls the appripiate
- * function.
- *
- * @param argc[in] Argument count.
- * @param argv[in] Argument list.
- * @return SUCCESS or an error code.
- */
-int team(int argc, char *argv[]){
+#include "team.h"
+#include "team_list.c"
+#include "team_create.c"
+#include "team_delete.c"
+#include "team_add_unit.c"
+#include "team_remove_unit.c"
+
+int cmd_team(int argc, char *argv[]){
     if (argc < 1){
         fprintf(stderr, "Command team needs an action\n");
-        return ERROR_INPUT_TEAM_NO_ACTION;
+        return(ERROR_INPUT_TEAM_NO_ACTION);
     }
     if (strcmp(argv[0], "list") == 0){
-        return list_team(argc - 1, argv + 1);
+        return(team_list(argc - 1, argv + 1));
     }
     else if (strcmp(argv[0], "create") == 0){
-        return create_team(argc - 1, argv + 1);
+        return(team_create(argc - 1, argv + 1));
     }
     else if (strcmp(argv[0], "delete") == 0){
-        return delete_team(argc - 1, argv + 1);
+        return(team_delete(argc - 1, argv + 1));
     }
     else if (strcmp(argv[0], "add_unit") == 0){
-        return add_team_unit(argc - 1, argv + 1);
+        return(team_add_unit(argc - 1, argv + 1));
     }
     else if (strcmp(argv[0], "remove_unit") == 0){
-        return remove_team_unit(argc - 1, argv + 1);
+        return(team_remove_unit(argc - 1, argv + 1));
     }
     else{
         fprintf(stderr, "Invalid action for team command: %s\n", argv[0]);
-        return ERROR_INPUT_TEAM_INVALID_ACTION;
-    }
-}
-
-/**
- * Removes a unit from a team.
- *
- * @param argc[in] Argument count.
- * @param argv[in] Argument list.
- * @return SUCCESS or an error code.
- */
-int remove_team_unit(int argc, char *argv[]){
-    if (argc != 2){
-        fprintf(
-          stderr, "remove_unit needs exactly two argument, %d supplied\n",
-          argc
-        );
-        return ERROR_INPUT_TEAM_NO_ACTION;
-    }
-    sqlite3 *db = NULL;
-    sqlite3_stmt *stmt_verify;
-    char *parameters[2] = {argv[0], argv[1]};
-    db_query(
-      &db, &stmt_verify,
-      "SELECT count(unit) AS inc FROM units_teams WHERE team = ? AND unit = ?",
-      parameters
-    );
-    if (SQLITE_ROW != sqlite3_step(stmt_verify)){
-        fprintf(
-          stderr, "Unable to verify unit and team: %s\n", sqlite3_errmsg(db)
-        );
-        sqlite3_finalize(stmt_verify);
-        sqlite3_close(db);
-        return ERROR_DB_VERIFY_TEAM_UNIT;
-    }
-    if (sqlite3_column_int(stmt_verify, 0) == 0){
-        fprintf(
-          stderr,
-          "There is no unit with ID '%s' in team with ID '%s'\n",
-          argv[1],
-          argv[0]
-        );
-        sqlite3_finalize(stmt_verify);
-        sqlite3_close(db);
-        return ERROR_INPUT_VERIFY_TEAM_UNIT_TEAM;
-    }
-    sqlite3_finalize(stmt_verify);
-
-    // Delete from units_teams.
-    if (
-      SUCCESS !=
-      db_execute(
-        &db, "DELETE FROM units_teams WHERE team = ? AND unit = ?", parameters
-      )
-    ){
-        fprintf(
-          stderr,
-          "Unable to remove unit from team: %s\n", sqlite3_errmsg(db)
-        );
-        sqlite3_close(db);
-        return ERROR_DB_DELETE_UNITS_TEAMS;
-    }
-
-    // Inform about the new team ocmposition
-    printf(
-      "Unit with ID '%s' succesfully removed from team with id '%s'\n",
-      argv[1], argv[0]
-    );
-    sqlite3_close(db);
-
-    // Show the team composition and end.
-    char *args_to_list[2] = {argv[0], "--units"};
-    list_team(2, args_to_list);
-    return SUCCESS;
-}
-
-/**
- * Adds a unit to a team.
- *
- * @param argc[in] Argument count.
- * @param argv[in] Argument list.
- * @return SUCCESS or an error code.
- */
-int add_team_unit(int argc, char *argv[]){
-    if (argc != 2){
-        fprintf(
-          stderr, "add_unit needs exactly two arguments, %d supplied\n",
-          argc
-        );
-        return ERROR_INPUT_TEAM_NO_ACTION;
-    }
-    sqlite3 *db = NULL;
-    sqlite3_stmt *stmt_verify;
-    char *parameters[4] = {argv[0], argv[1], argv[0], argv[1]};
-    db_query(
-      &db, &stmt_verify,
-      "SELECT "
-      "(SELECT count(id) FROM teams WHERE id = ?) AS team, "
-      "(SELECT count(id) FROM units WHERE id = ?) AS unit, "
-      "(SELECT count(*) FROM units_teams WHERE team = ? AND unit = ?) AS inc",
-      parameters
-    );
-    if (SQLITE_ROW != sqlite3_step(stmt_verify)){
-        fprintf(
-          stderr, "Unable to verify unit and team: %s\n", sqlite3_errmsg(db)
-        );
-        sqlite3_finalize(stmt_verify);
-        sqlite3_close(db);
-        return ERROR_DB_VERIFY_TEAM_UNIT;
-    }
-    if (sqlite3_column_int(stmt_verify, 0) == 0){
-        fprintf(stderr, "Team with ID '%s' does not exists\n", argv[0]);
-        sqlite3_finalize(stmt_verify);
-        sqlite3_close(db);
-        return ERROR_INPUT_VERIFY_TEAM_UNIT_TEAM;
-    }
-    if (sqlite3_column_int(stmt_verify, 1) == 0){
-        fprintf(stderr, "Unit with ID '%s' does not exists\n", argv[1]);
-        sqlite3_finalize(stmt_verify);
-        sqlite3_close(db);
-        return ERROR_INPUT_VERIFY_TEAM_UNIT_UNIT;
-    }
-    if (sqlite3_column_int(stmt_verify, 2) != 0){
-        fprintf(
-          stderr,
-          "Unit with ID '%s' is already in team with ID %s\n", argv[1], argv[0]
-        );
-        sqlite3_finalize(stmt_verify);
-        sqlite3_close(db);
-        return ERROR_INPUT_VERIFY_TEAM_UNIT_INCLUDED;
-    }
-    sqlite3_finalize(stmt_verify);
-
-    // Insert into units_teams
-    if (
-      SUCCESS !=
-      db_execute(
-        &db, "INSERT INTO units_teams (team, unit) VALUES (?, ?)", parameters
-      )
-    ){
-        fprintf(
-          stderr,
-          "Unable to add unit to team: %s\n", sqlite3_errmsg(db)
-        );
-        sqlite3_close(db);
-        return ERROR_DB_INSERT_UNITS_TEAMS;
-    }
-
-    // Inform about the newly created team
-    printf(
-      "Unit with ID '%s' succesfully added to team with id '%s'\n",
-      argv[1], argv[0]
-    );
-    sqlite3_close(db);
-
-    // Show the team composition and end.
-    char *args_to_list[2] = {argv[0], "--units"};
-    list_team(2, args_to_list);
-    return SUCCESS;
-}
-
-/**
- * Displays teams.
- *
- * @param argc[in] Argument count.
- * @param argv[in] Argument list.
- * @return SUCCESS or an error code.
- */
-int list_team(int argc, char *argv[]){
-    // Get parameters
-    char show_units = FALSE;
-    int number_of_options = 0;
-    for (int i = 0; i < argc; i ++){
-        if (strcmp("--units", argv[i]) == 0 || strcmp("-u", argv[i]) == 0){
-            number_of_options ++;
-            show_units = TRUE;
-        }
-    }
-
-    char query[300] = "SELECT id, name, priority FROM teams ";
-    char *parameters[] = {"", ""};
-    if (argc > number_of_options){
-        strcat(query, "WHERE id = ? OR name = ?");
-        parameters[0] = argv[0];
-        parameters[1] = argv[0];
-    }
-    strcat(query, " ORDER BY priority DESC");
-    sqlite3 *db = NULL;
-    sqlite3_stmt *stmt_teams;
-    db_query(&db, &stmt_teams, query, parameters);
-
-    printf(" --------------------------------------------------\n");
-    printf(" | ID   | Name                             | Prio |\n");
-    printf(" --------------------------------------------------\n");
-    while (1 == 1){
-        int status = sqlite3_step(stmt_teams);
-        if (status == SQLITE_ROW){
-            printf(
-              " | %*s | %*s | %*d |\n",
-              4, sqlite3_column_text(stmt_teams, 0),
-              -32, sqlite3_column_text(stmt_teams, 1),
-              4, sqlite3_column_int(stmt_teams, 2)
-            );
-
-            // If units are to be shown, query them here
-            if (show_units == TRUE){
-                strcpy(
-                  query,
-                  "SELECT id, name, level FROM units WHERE id IN "
-                  "  (SELECT DISTINCT unit FROM units_teams WHERE team = ?);"
-                );
-                sqlite3_stmt *stmt_units;
-                if (SQLITE_OK != sqlite3_prepare_v2(db, query, -1, &stmt_units, 0)) {
-                    fprintf(
-                    stderr,
-                    "Failed to execute statement to select new team ID: %s\n",
-                    sqlite3_errmsg(db)
-                    );
-                    sqlite3_finalize(stmt_units);
-                    sqlite3_close(db);
-                    return ERROR_DB_TEAM_ID;
-                }
-                sqlite3_bind_text(
-                  stmt_units, 1, sqlite3_column_text(stmt_teams, 0),
-                  strlen(sqlite3_column_text(stmt_teams, 0)), NULL
-                );
-                printf(" |      |----------------------------------|      |\n");
-                char tmp[64];
-                while (SQLITE_ROW == sqlite3_step(stmt_units)){
-                    strcpy(tmp, sqlite3_column_text(stmt_units, 1));
-                    if (strlen(tmp) > 9){
-                        tmp[10] = '\0';
-                    }
-                    sprintf(
-                      tmp,
-                      "%s (Lv.%d) (#%s) ",
-                      tmp,
-                      sqlite3_column_int(stmt_units, 2),
-                      sqlite3_column_text(stmt_units, 0)
-                    );
-                    printf(
-                      " |      | %*s |      |\n",
-                      32, tmp
-                    );
-                }
-                printf(" --------------------------------------------------\n");
-            }
-        }
-        else{
-            break;
-        }
-    }
-    if (show_units == FALSE){
-        // If units are shown, the last team has already closed the table.
-        printf(" --------------------------------------------------\n");
-    }
-    sqlite3_finalize(stmt_teams);
-    sqlite3_close(db);
-    return SUCCESS;
-}
-
-
-/**
- * Creates a team.
- *
- * @param argc[in] Argument count.
- * @param argv[in] Argument list.
- * @return SUCCESS or an error code.
- */
-int create_team(int argc, char *argv[]){
-    if (argc < 1 || argc > 2){
-        fprintf(
-          stderr,
-          "Team creation takes 1 or 2 arguments, %d supplied\n", argc
-        );
-        return ERROR_INPUT_TEAM_CREATE_ARGUMENT_COUNT;
-    }
-    int priority = 0;
-
-    // If priority has been supplied as argument, validate it
-    if (argc == 2){
-        priority = atoi(argv[1]);
-        if(
-          strspn(argv[1], "0123456789") != strlen(argv[1]) ||
-          priority < 0 ||
-          priority > 50
-        ){
-            fprintf(stderr, "Priority must be an integer between 0 and 50\n");
-            return ERROR_INPUT_TEAM_CREATE_PRIORITY;
-        }
-    }
-    // Read name
-    char name[128];
-    strcpy(name, argv[0]);
-    int new_id = -1;
-    sqlite3 *db = NULL;
-    sqlite3_stmt *stmt_id;
-
-    // Get the new id for the team
-    db_query(
-      &db, &stmt_id,
-      "SELECT max(CAST(id AS INTEGER)) + 1 AS id FROM teams;",
-      NULL
-    );
-    if (SQLITE_ROW != sqlite3_step(stmt_id)){
-        fprintf(stderr, "Unable to read teams: %s\n", sqlite3_errmsg(db));
-        sqlite3_finalize(stmt_id);
-        sqlite3_close(db);
-        return ERROR_DB_NEW_TEAM_ID;
-    }
-
-    // Get all parameters and convert to char.
-    new_id = sqlite3_column_int(stmt_id, 0);
-    sqlite3_finalize(stmt_id);
-    char priority_c[2];
-    char id_c[4];
-    sprintf(id_c, "%d", new_id);
-    sprintf(priority_c, "%d", priority);
-    char *parameters[3] = {id_c, argv[0], priority_c};
-
-    // Insert into teams
-    if (
-      SUCCESS !=
-      db_execute(
-        &db,
-        "INSERT INTO teams (id, name, priority) VALUES (?, ?, ?)", parameters
-      )
-    ){
-        fprintf(
-          stderr,
-          "Unable to create team: %s\n", sqlite3_errmsg(db)
-        );
-        sqlite3_close(db);
-        return ERROR_DB_INSERT_TEAMS;
-    }
-
-    // Inform about the newly created team
-    sqlite3_close(db);
-    printf("Team ID %d '%s' created with priority %d\n", new_id, name, priority);
-    return SUCCESS;
-}
-
-/**
- * Deletes a team.
- *
- * @param argc[in] Argument count.
- * @param argv[in] Argument list.
- * @return SUCCESS or an error code.
- */
-int delete_team(int argc, char *argv[]){
-    if (argc != 1){
-        fprintf(
-          stderr,
-          "Team deletion takes exactly one argument, %d supplied\n", argc
-        );
-        return ERROR_INPUT_TEAM_DELETE_ARGUMENT_COUNT;
-    }
-    sqlite3 *db = NULL;
-
-    // Verify that the team exists.
-    sqlite3_stmt *stmt_verify;
-    char *parameters[1] = {argv[0]};
-    db_query(
-      &db, &stmt_verify,
-      "SELECT count(id) AS c FROM teams WHERE id = ?", parameters
-    );
-    if (SQLITE_ROW != sqlite3_step(stmt_verify)){
-        fprintf(
-          stderr, "Unable to verify team: %s\n", sqlite3_errmsg(db)
-        );
-        sqlite3_finalize(stmt_verify);
-        sqlite3_close(db);
-        return ERROR_DB_VERIFY_TEAM_UNIT;
-    }
-    if (sqlite3_column_int(stmt_verify, 0) == 0){
-        fprintf(stderr, "Team with ID '%s' does not exists\n", argv[0]);
-        sqlite3_finalize(stmt_verify);
-        sqlite3_close(db);
-        return ERROR_INPUT_VERIFY_TEAM_UNIT_TEAM;
-    }
-    sqlite3_finalize(stmt_verify);
-
-    // Delete from table teams.
-    if (
-      SUCCESS !=
-      db_execute(&db, "DELETE FROM teams WHERE id = ?", parameters)
-    ){
-        fprintf(
-          stderr,
-          "Unable to delete team: %s\n", sqlite3_errmsg(db)
-        );
-        sqlite3_close(db);
-        return ERROR_DB_DELETE_TEAMS;
-    }
-
-    // Delete from table units_teams.
-    if (
-      SUCCESS !=
-      db_execute(&db, "DELETE FROM units_teams WHERE id = ?", parameters)
-    ){
-        fprintf(
-          stderr,
-          "Unable to delete units in team: %s\n", sqlite3_errmsg(db)
-        );
-        sqlite3_close(db);
-        return ERROR_DB_DELETE_UNITS_TEAMS;
+        return(ERROR_INPUT_TEAM_INVALID_ACTION);
     }
-    sqlite3_close(db);
-    return SUCCESS;
 }

+ 114 - 30
src/RuneOptimizer/team/team.h

@@ -16,56 +16,140 @@
  */
 
 /**
- * Parses the arguments passes to the team function and calls the appripiate
- * function.
- *
- * @param argc[in] Argument count.
- * @param argv[in] Argument list.
- * @return SUCCESS or an error code.
+ * Validates the options for adding a unit to a team.
+ * 
+ * It checks if the unit and team IDs exist, and if the unit is already a member
+ * of the team.
+ * 
+ * @param[in] team ID of the team to add the unit to.
+ * @param[in] unit ID of the unit to add.
+ * @return SUCCESS if everything is OK, ERROR_INPUT_VERIFY_TEAM_UNIT_TEAM if the
+ * team doesn't exist, ERROR_INPUT_VERIFY_TEAM_UNIT_UNIT if the unit doesn't
+ * exist or ERROR_DB_VERIFY_TEAM_UNIT for other errors.
  */
-int team(int argc, char *argv[]);
+int team_add_unit_validate(char *team, char *unit);
 
 /**
- * Removes a unit from a team.
+ * Adds a unit to a team.
+ * 
+ * Inserts a row in the table 'units_teams'. In case of error, it will print a
+ * description to stderr.
  *
- * @param argc[in] Argument count.
- * @param argv[in] Argument list.
- * @return SUCCESS or an error code.
+ * @param argc[in] Number of arguments passed to the option.
+ * @param argv[in] Aguments passed to the option.
+ * @return SUCCESS or an error code. See
+ * <a href="file:../error/error.h">../error/error.h</a> for a list of error
+ * codes.
  */
-int remove_team_unit(int argc, char *argv[]);
+int team_add_unit(int argc, char *argv[]);
 
 /**
- * Adds a unit to a team.
+ * Creates a team.
+ * 
+ * Saves it to the database table 'teams 'with the provided name and
+ * (optionally) priority. It will have no units in 'units_teams'. In case of
+ * error, it will print a description to stderr.
  *
- * @param argc[in] Argument count.
- * @param argv[in] Argument list.
- * @return SUCCESS or an error code.
+ * @param argc[in] Number of arguments passed to the option.
+ * @param argv[in] Arguments passed to the option. It needs to have a size of 1
+ * or two. The frst one must be the new team name, the seecond one is optional
+ * and is the priority of the new team. If not specified, the priority will be
+ * 0.
+ * @return SUCCESS or an error code. See
+ * <a href="file:../error/error.h">../error/error.h</a> for a list of error
+ * codes.
+ */
+int team_create(int argc, char *argv[]);
+
+/**
+ * Validates a string as a priority for a team.
+ * 
+ * To be valid, the string must contain a number between 0 and 50.
+ * 
+ * @param[in] priority String to evaluate as priority.
+ * @return 0-50 if the priority is valid, -1 otherwise.
  */
-int add_team_unit(int argc, char *argv[]);
+int team_create_validate_priority(char *priority);
 
 /**
- * Displays teams.
+ * Gets the next available id for the table teams.
+ * 
+ * It will get the nexxt ID to the highest one currently in the table 'teams',
+ * but it will not get any unused one lower than that.
+ * 
+ * @return -1 on error, positive integer with the ID on success.
+ */
+int team_create_get_next_id();
+
+/**
+ * Validates data for team deletion.
+ * 
+ * Checks if the team exists.
+ * 
+ * @return SUCCESS if everything is OK, ERROR_INPUT_VERIFY_TEAM if the team
+ * doesn't exist, or ERROR_DB_VERIFY_TEAM for any database errors.
+ */
+int team_delete_validate(char *team);
+
+/**
+ * Deletes a team.
+ * 
+ * It deletes the row from the table 'teams', and any related row in the table
+ * 'units_teams'. In case of error, it will print a
+ * description to stderr.
  *
  * @param argc[in] Argument count.
  * @param argv[in] Argument list.
- * @return SUCCESS or an error code.
+ * @return SUCCESS or an error code. See
+ * <a href="file:../error/error.h">../error/error.h</a> for a list of error
+ * codes.
  */
-int list_team(int argc, char *argv[]);
+int team_delete(int argc, char *argv[]);
 
 /**
- * Creates a team.
+ * Displays a list of teams ar a single team info.
+ *  *
+ * @param argc[in] Number of arguments passed to the option.
+ * @param argv[in] Arguments passed to the option. If one of them is the -u or
+ * --units option, it will also print the units for each of the printed teams.
+ * @return Allways SUCCESS.
+ */
+int team_list(int argc, char *argv[]);
+
+/**
+ * Performs a validation for the unit removal function.
+ * 
+ * It chechs that a unit exists in units_teams for a team.
+ * 
+ * @param[in] team ID of the team to check.
+ * @param[in] unit ID of the unit to check.
+ * @return SUCCESS if the unit was removed from the team,
+ * ERROR_INPUT_VERIFY_TEAM_UNIT_TEAM if the unit is not part of the team, or
+ * ERROR_DB_VERIFY_TEAM_UNIT on error.
+ */
+int team_remove_unit_validate(char *team, char *unit);
+
+/**
+ * Removes a unit from a team.
  *
- * @param argc[in] Argument count.
- * @param argv[in] Argument list.
- * @return SUCCESS or an error code.
+ * It deletes the entry in the table 'units_teams'.
+ *
+ * @param argc[in] Number or arguments passed to the option.
+ * @param argv[in] Argument passed to the option.
+ * @return SUCCESS or an error code. See
+ * <a href="file:../error/error.h">../error/error.h</a> for a list of error
+ * codes.
  */
-int create_team(int argc, char *argv[]);
+int team_remove_unit(int argc, char *argv[]);
 
 /**
- * Deletes a team.
+ * Parses the arguments passes to the team function and calls the appripiate
+ * function.
  *
- * @param argc[in] Argument count.
- * @param argv[in] Argument list.
- * @return SUCCESS or an error code.
+ * @param[in] argc Number of arguments passed to the team command.
+ * @param[in] argv Arguments passed to the team command.
+ * @return SUCCESS or an error code. See
+ * <a href="file:../error/error.h">../error/error.h</a> for a list of error
+ * codes.
  */
-int delete_team(int argc, char *argv[]);
+int cmd_team(int argc, char *argv[]);

+ 98 - 0
src/RuneOptimizer/team/team_add_unit.c

@@ -0,0 +1,98 @@
+/*
+ * This file is part of RuneOptimizer.
+ *
+ * RuneOptimizer is free software: you can redistribute it and/or modify it
+ * under the terms of the GNU General Public License as published by the Free
+ * Software Foundation, either version 3 of the License, or (at your option)
+ * any later version.
+ *
+ * RuneOptimizer is distributed in the hope that it will be useful, but WITHOUT
+ * ANY WARRANTY; without even the implied warranty of MERCHANTABILITY or
+ * FITNESS FOR A PARTICULAR PURPOSE. See the GNU General Public License for
+ * more details.
+ *
+ * You should have received a copy of the GNU General Public License along with
+ * RuneOptimizer. If not, see <https://www.gnu.org/licenses/>.
+ */
+
+int team_add_unit_validate(char *team, char *unit){
+    int status = SUCCESS;
+    sqlite3_stmt *stmt_verify;
+    char *parameters[4] = {team, unit, team, unit};
+    db_query(
+      &stmt_verify,
+      "SELECT "
+      "(SELECT count(id) FROM teams WHERE id = ?) AS team, "
+      "(SELECT count(id) FROM units WHERE id = ?) AS unit, "
+      "(SELECT count(*) FROM units_teams WHERE team = ? AND unit = ?) AS inc",
+      parameters
+    );
+    if (SQLITE_ROW != sqlite3_step(stmt_verify)){
+        status = ERROR_DB_VERIFY_TEAM_UNIT;
+    }
+    else if (sqlite3_column_int(stmt_verify, 0) == 0){
+        status = ERROR_INPUT_VERIFY_TEAM_UNIT_TEAM;
+    }
+    else if (sqlite3_column_int(stmt_verify, 1) == 0){
+        status = ERROR_INPUT_VERIFY_TEAM_UNIT_UNIT;
+    }
+    else if (sqlite3_column_int(stmt_verify, 2) != 0){
+        status = ERROR_INPUT_VERIFY_TEAM_UNIT_INCLUDED;
+    }
+    sqlite3_finalize(stmt_verify);
+    return(status);
+}
+
+int team_add_unit(int argc, char *argv[]){
+    if (argc != 2){
+        fprintf(
+          stderr, "add_unit needs exactly two arguments, %d supplied\n",
+          argc
+        );
+        return(ERROR_INPUT_TEAM_NO_ACTION);
+    }
+    int validation = team_add_unit_validate(argv[0], argv[1]);
+    if (SUCCESS != validation){
+        char errmsg[86] = "Unable to verify unit and team.\n";
+        switch (validation){
+            case ERROR_INPUT_VERIFY_TEAM_UNIT_TEAM:
+                sprintf(errmsg, "Team with ID '%s' does not exists\n", argv[0]);
+                break;
+            case ERROR_INPUT_VERIFY_TEAM_UNIT_UNIT:
+                sprintf(errmsg, "Unit with ID '%s' does not exists\n", argv[1]);
+                break;
+            case ERROR_INPUT_VERIFY_TEAM_UNIT_INCLUDED:
+                sprintf(
+                  errmsg,
+                  "Unit with ID '%s' is already in team with ID %s\n",
+                  argv[1], argv[0]
+                );
+                break;
+        }
+        fprintf(stderr, errmsg);
+        return(validation);
+    }
+
+    // Insert into units_teams
+    char *parameters[2] = {argv[0], argv[1]};
+    if (
+      SUCCESS !=
+      db_execute(
+        "INSERT INTO units_teams (team, unit) VALUES (?, ?)", parameters
+      )
+    ){
+        fprintf(stderr, "Unable to add unit to team: %s\n", sqlite3_errmsg(db));
+        return(ERROR_DB_INSERT_UNITS_TEAMS);
+    }
+
+    // Inform about the newly created team
+    printf(
+      "Unit with ID '%s' succesfully added to team with id '%s'\n",
+      argv[1], argv[0]
+    );
+
+    // Show the team composition and end.
+    char *args_to_list[2] = {argv[0], "--units"};
+    team_list(2, args_to_list);
+    return(SUCCESS);
+}

+ 96 - 0
src/RuneOptimizer/team/team_create.c

@@ -0,0 +1,96 @@
+/*
+ * This file is part of RuneOptimizer.
+ *
+ * RuneOptimizer is free software: you can redistribute it and/or modify it
+ * under the terms of the GNU General Public License as published by the Free
+ * Software Foundation, either version 3 of the License, or (at your option)
+ * any later version.
+ *
+ * RuneOptimizer is distributed in the hope that it will be useful, but WITHOUT
+ * ANY WARRANTY; without even the implied warranty of MERCHANTABILITY or
+ * FITNESS FOR A PARTICULAR PURPOSE. See the GNU General Public License for
+ * more details.
+ *
+ * You should have received a copy of the GNU General Public License along with
+ * RuneOptimizer. If not, see <https://www.gnu.org/licenses/>.
+ */
+
+int team_create_validate_priority(char *priority){
+    int prio = atoi(priority);
+    // Has an actual 0 been passed?
+    // Or is the 0 returned by atoi bc priority is no number?
+    if (prio == 0 && strspn(priority, "0") != strlen(priority)){
+        return(-1);
+    }
+    if (prio < 0 || prio > 50){
+      return(-1);
+    }
+    return(prio);
+}
+
+int team_create_get_next_id(){
+    int new_id = -1;
+    sqlite3_stmt *stmt_id;
+
+    // Get the new id for the team
+    db_query(
+      &stmt_id, "SELECT max(CAST(id AS INTEGER)) + 1 AS id FROM teams;", NULL
+    );
+    if (SQLITE_ROW != sqlite3_step(stmt_id)){
+        fprintf(stderr, "Unable to read teams: %s\n", sqlite3_errmsg(db));
+        sqlite3_finalize(stmt_id);
+        return(-1);
+    }
+
+    // Get all parameters and convert to char.
+    new_id = sqlite3_column_int(stmt_id, 0);
+    sqlite3_finalize(stmt_id);
+}
+
+int team_create(int argc, char *argv[]){
+    if (argc < 1 || argc > 2){
+        fprintf(
+          stderr, "Team creation takes 1 or 2 arguments, %d supplied\n", argc
+        );
+        return(ERROR_INPUT_TEAM_CREATE_ARGUMENT_COUNT);
+    }
+    int priority = 0;
+
+    // If priority has been supplied as argument, validate it
+    if (argc == 2){
+        priority = team_create_validate_priority(argv[1]);
+        if (priority == -1){
+            fprintf(stderr, "Priority must be an integer between 0 and 50\n");
+            return(ERROR_INPUT_TEAM_CREATE_PRIORITY);
+        }
+    }
+    // Read name
+    char name[128];
+    strcpy(name, argv[0]);
+    int new_id = team_create_get_next_id();
+    if (-1 == new_id){
+        fprintf(stderr, "Unable to get id for the team\n");
+        return(ERROR_DB_NEW_TEAM_ID);
+    }
+    
+    char priority_c[2];
+    char id_c[4];
+    sprintf(id_c, "%d", new_id);
+    sprintf(priority_c, "%d", priority);
+    char *parameters[3] = {id_c, argv[0], priority_c};
+
+    // Insert into teams
+    if (
+      SUCCESS !=
+      db_execute(
+        "INSERT INTO teams (id, name, priority) VALUES (?, ?, ?)", parameters
+      )
+    ){
+        fprintf(stderr, "Unable to create team: %s\n", sqlite3_errmsg(db));
+        return(ERROR_DB_INSERT_TEAMS);
+    }
+
+    // Inform about the newly created team
+    printf("Team ID %d '%s' created with priority %d\n", new_id, name, priority);
+    return(SUCCESS);
+}

+ 74 - 0
src/RuneOptimizer/team/team_delete.c

@@ -0,0 +1,74 @@
+/*
+ * This file is part of RuneOptimizer.
+ *
+ * RuneOptimizer is free software: you can redistribute it and/or modify it
+ * under the terms of the GNU General Public License as published by the Free
+ * Software Foundation, either version 3 of the License, or (at your option)
+ * any later version.
+ *
+ * RuneOptimizer is distributed in the hope that it will be useful, but WITHOUT
+ * ANY WARRANTY; without even the implied warranty of MERCHANTABILITY or
+ * FITNESS FOR A PARTICULAR PURPOSE. See the GNU General Public License for
+ * more details.
+ *
+ * You should have received a copy of the GNU General Public License along with
+ * RuneOptimizer. If not, see <https://www.gnu.org/licenses/>.
+ */
+
+int team_delete_validate(char *team){
+    // Verify that the team exists.
+    sqlite3_stmt *stmt_verify;
+    char *parameters[1] = {team};
+    db_query(
+      &stmt_verify,
+      "SELECT count(id) AS c FROM teams WHERE id = ?", parameters
+    );
+    if (SQLITE_ROW != sqlite3_step(stmt_verify)){
+        sqlite3_finalize(stmt_verify);
+        return(ERROR_DB_VERIFY_TEAM);
+    }
+    if (sqlite3_column_int(stmt_verify, 0) == 0){
+        sqlite3_finalize(stmt_verify);
+        return(ERROR_INPUT_VERIFY_TEAM);
+    }
+    sqlite3_finalize(stmt_verify);
+    return(SUCCESS);
+}
+
+int team_delete(int argc, char *argv[]){
+    if (argc != 1){
+        fprintf(
+          stderr,
+          "Team deletion takes exactly one argument, %d supplied\n", argc
+        );
+        return(ERROR_INPUT_TEAM_DELETE_ARGUMENT_COUNT);
+    }
+    
+    
+    // Verify that the team exists
+    int validation = team_delete_validate(argv[0]);
+    if (SUCCESS != validation){
+        fprintf(stderr, "Team with ID '%s' does not exists\n", argv[0]);
+        return validation;
+    }
+
+    // Delete from table teams.
+    char *parameters[1] = {argv[0]};
+    if (
+      SUCCESS != db_execute("DELETE FROM teams WHERE id = ?", parameters)
+    ){
+        fprintf(stderr, "Unable to delete team: %s\n", sqlite3_errmsg(db));
+        return(ERROR_DB_DELETE_TEAMS);
+    }
+
+    // Delete from table units_teams.
+    if (
+      SUCCESS != db_execute("DELETE FROM units_teams WHERE id = ?", parameters)
+    ){
+        fprintf(
+          stderr, "Unable to delete units in team: %s\n", sqlite3_errmsg(db)
+        );
+        return(ERROR_DB_DELETE_UNITS_TEAMS);
+    }
+    return(SUCCESS);
+}

+ 98 - 0
src/RuneOptimizer/team/team_list.c

@@ -0,0 +1,98 @@
+/*
+ * This file is part of RuneOptimizer.
+ *
+ * RuneOptimizer is free software: you can redistribute it and/or modify it
+ * under the terms of the GNU General Public License as published by the Free
+ * Software Foundation, either version 3 of the License, or (at your option)
+ * any later version.
+ *
+ * RuneOptimizer is distributed in the hope that it will be useful, but WITHOUT
+ * ANY WARRANTY; without even the implied warranty of MERCHANTABILITY or
+ * FITNESS FOR A PARTICULAR PURPOSE. See the GNU General Public License for
+ * more details.
+ *
+ * You should have received a copy of the GNU General Public License along with
+ * RuneOptimizer. If not, see <https://www.gnu.org/licenses/>.
+ */
+
+int team_list(int argc, char *argv[]){
+    // Get parameters
+    char show_units = FALSE;
+    int number_of_options = 0;
+    for (int i = 0; i < argc; i ++){
+        if (strcmp("--units", argv[i]) == 0 || strcmp("-u", argv[i]) == 0){
+            number_of_options ++;
+            show_units = TRUE;
+        }
+    }
+
+    char query[300] = "SELECT id, name, priority FROM teams ";
+    char *parameters[] = {"", ""};
+    if (argc > number_of_options){
+        strcat(query, "WHERE id = ? OR name = ?");
+        parameters[0] = argv[0];
+        parameters[1] = argv[0];
+    }
+    strcat(query, " ORDER BY priority DESC");
+    sqlite3_stmt *stmt_teams;
+    db_query(&stmt_teams, query, parameters);
+
+    printf(" --------------------------------------------------\n");
+    printf(" | ID   | Name                             | Prio |\n");
+    printf(" --------------------------------------------------\n");
+    while (1 == 1){
+        int status = sqlite3_step(stmt_teams);
+        if (status == SQLITE_ROW){
+            printf(
+              " | %*s | %*s | %*d |\n",
+              4, sqlite3_column_text(stmt_teams, 0),
+              -32, sqlite3_column_text(stmt_teams, 1),
+              4, sqlite3_column_int(stmt_teams, 2)
+            );
+
+            // If units are to be shown, query them here
+            if (show_units == TRUE){
+                strcpy(
+                  query,
+                  "SELECT id, name, level FROM units WHERE id IN "
+                  "  (SELECT DISTINCT unit FROM units_teams WHERE team = ?);"
+                );
+                sqlite3_stmt *stmt_units;
+                char *unit_parameters[1];
+                unit_parameters[0] = malloc(5);
+                strcpy(unit_parameters[0], sqlite3_column_text(stmt_teams, 0));
+                db_query(&stmt_units, query, unit_parameters);
+                printf(" |      |----------------------------------|      |\n");
+                char tmp[64];
+                while (SQLITE_ROW == sqlite3_step(stmt_units)){
+                    strcpy(tmp, sqlite3_column_text(stmt_units, 1));
+                    if (strlen(tmp) > 9){
+                        tmp[10] = '\0';
+                    }
+                    sprintf(
+                      tmp,
+                      "%s (Lv.%d) (#%s) ",
+                      tmp,
+                      sqlite3_column_int(stmt_units, 2),
+                      sqlite3_column_text(stmt_units, 0)
+                    );
+                    printf(
+                      " |      | %*s |      |\n",
+                      32, tmp
+                    );
+                }
+                free(unit_parameters[0]);
+                printf(" --------------------------------------------------\n");
+            }
+        }
+        else{
+            break;
+        }
+    }
+    if (show_units == FALSE){
+        // If units are shown, the last team has already closed the table.
+        printf(" --------------------------------------------------\n");
+    }
+    sqlite3_finalize(stmt_teams);
+    return(SUCCESS);
+}

+ 85 - 0
src/RuneOptimizer/team/team_remove_unit.c

@@ -0,0 +1,85 @@
+/*
+ * This file is part of RuneOptimizer.
+ *
+ * RuneOptimizer is free software: you can redistribute it and/or modify it
+ * under the terms of the GNU General Public License as published by the Free
+ * Software Foundation, either version 3 of the License, or (at your option)
+ * any later version.
+ *
+ * RuneOptimizer is distributed in the hope that it will be useful, but WITHOUT
+ * ANY WARRANTY; without even the implied warranty of MERCHANTABILITY or
+ * FITNESS FOR A PARTICULAR PURPOSE. See the GNU General Public License for
+ * more details.
+ *
+ * You should have received a copy of the GNU General Public License along with
+ * RuneOptimizer. If not, see <https://www.gnu.org/licenses/>.
+ */
+
+int team_remove_unit_validate(char *team, char *unit){
+    sqlite3_stmt *stmt_validate;
+    char *parameters[2] = {team, unit};
+    db_query(
+      &stmt_validate,
+      "SELECT count(unit) AS inc FROM units_teams WHERE team = ? AND unit = ?",
+      parameters
+    );
+    if (SQLITE_ROW != sqlite3_step(stmt_validate)){
+        fprintf(
+          stderr, "Unable to verify unit and team: %s\n", sqlite3_errmsg(db)
+        );
+        sqlite3_finalize(stmt_validate);
+        return(ERROR_DB_VERIFY_TEAM_UNIT);
+    }
+    if (sqlite3_column_int(stmt_validate, 0) == 0){
+        fprintf(
+          stderr,
+          "There is no unit with ID '%s' in team with ID '%s'\n",
+          unit,
+          team
+        );
+        sqlite3_finalize(stmt_validate);
+        return(ERROR_INPUT_VERIFY_TEAM_UNIT_TEAM);
+    }
+    sqlite3_finalize(stmt_validate);
+    return SUCCESS;
+}
+
+int team_remove_unit(int argc, char *argv[]){
+    if (argc != 2){
+        fprintf(
+          stderr, "remove_unit needs exactly two argument, %d supplied\n",
+          argc
+        );
+        return(ERROR_INPUT_TEAM_NO_ACTION);
+    }
+    int validation = team_remove_unit_validate(argv[0], argv[1]);
+    if (SUCCESS != validation){
+        return validation;
+    }
+
+    // Delete from units_teams.
+    char *parameters[2] = {argv[0], argv[1]};
+    if (
+      SUCCESS !=
+      db_execute(
+        "DELETE FROM units_teams WHERE team = ? AND unit = ?", parameters
+      )
+    ){
+        fprintf(
+          stderr,
+          "Unable to remove unit from team: %s\n", sqlite3_errmsg(db)
+        );
+        return(ERROR_DB_DELETE_UNITS_TEAMS);
+    }
+
+    // Inform about the new team ocmposition
+    printf(
+      "Unit with ID '%s' succesfully removed from team with id '%s'\n",
+      argv[1], argv[0]
+    );
+
+    // Show the team composition and end.
+    char *args_to_list[2] = {argv[0], "--units"};
+    team_list(2, args_to_list);
+    return(SUCCESS);
+}

+ 16 - 7238
src/RuneOptimizer/update/update.c

@@ -15,14 +15,24 @@
  * RuneOptimizer. If not, see <https://www.gnu.org/licenses/>.
  */
 
+#include "update.h"
+#include "update_current_stats.c"
+#include "update_get_monster_name.c"
+#include "update_db_tables.c"
+#include "update_rune_totals.c"
+#include "update_json_rune.c"
+#include "update_json_unit.c"
+#include "update_info.c"
+#include "update_json.c"
+
 /**
  * Parses the command parameters and calls one of the update functions.
  *
- * @param[in] argc Argument count.
- * @param[in] argv Argument list.
+ * @param[in] argc Number of arguments passed to the update command.
+ * @param[in] argv Arguments passed to the update command.
  * @return SUCCESS or an error code.
  */
-int update(int argc, char *argv[]){
+int cmd_update(int argc, char *argv[]){
 
     // Options
     char six_stars = FALSE;
@@ -34,7 +44,7 @@ int update(int argc, char *argv[]){
     if (argc == 0){
         fprintf(
           stderr,
-          "Team creation takes 1 or more arguments, %d supplied\n", argc - 3
+          "update command takes 1 or more arguments, %d supplied\n", argc - 3
         );
         return ERROR_INPUT_UPDATE_NO_ARGUMENTS;
     }
@@ -65,6 +75,7 @@ int update(int argc, char *argv[]){
     if (strlen(argv[0]) > 5){
         char extension[6];
         strncpy(extension, argv[0] + strlen(argv[0]) - 5, 5);
+        extension[5] = '\0';
         if (strcmp(extension, ".json") == 0){
             return update_json(
               argv[0], six_stars, with_runes, clear_teams, gui
@@ -72,7239 +83,6 @@ int update(int argc, char *argv[]){
         }
     }
     // TODO: More ifs as more options are implemented...
-    fprintf(stderr, "Unknwon source supplied: %d\n", argv[0]);
+    fprintf(stderr, "Unknwon source supplied: %s\n", argv[0]);
     return ERROR_INPUT_UPDATE_UNKNOWN_SOURCE;
 }
-
-/**
- * Updates the database from a json file.
- *
- * @param[in] file Path to the file.
- * @param[in] six_stars Indicator to import only 6* units. Units with runes will
- * be saved anyway.
- * @param[in] with_runes Indicator to import only units with runes.
- * @param[in] clear_teams Indicator to recreate tables teams and units_teams.
- * @param[in] gui Indicator to format output for thr GUI.
- * @return SUCCESS or an error code.
- */
-int update_json(
-  char file[], unsigned char six_stars,
-  unsigned char with_runes, unsigned char clear_teams, unsigned char gui
-){
-    if (gui == FALSE) printf("Updating from json file: %s\n", file);
-
-    // Read the JSON content
-    json_object *root = json_object_from_file(file);
-    if (!root){
-        fprintf(stderr, "Cant access file: %s\n", file);
-        return ERROR_INPUT_UPDATE_UNKNOWN_SOURCE;
-    }
-
-    json_object *wizard_id = json_object_object_get(root, "wizard_id");
-
-    json_object *wizard_info = json_object_object_get(root, "wizard_info");
-    json_object *wizard_name =
-      json_object_object_get(wizard_info, "wizard_name");
-    json_object *wizard_level =
-      json_object_object_get(wizard_info, "wizard_level");
-    if (gui == TRUE){
-        printf("Player ID: %s\n", json_object_get_string(wizard_id));
-        printf("Player name: %s\n", json_object_get_string(wizard_name));
-        printf("Player level: %s\n", json_object_get_string(wizard_level));
-        fflush(stdout);
-    }
-    else{
-        printf("\tPlayer ID: %s\n", json_object_get_string(wizard_id));
-        printf("\tPlayer name: %s\n", json_object_get_string(wizard_name));
-        printf("\tPlayer level: %s\n", json_object_get_string(wizard_level));
-    }
-
-    // Recreate the database tables
-    int status = recreate_tables(clear_teams);
-    if (SUCCESS != status){
-        return status;
-    }
-    sqlite3 *db = NULL;
-
-    // Parse runes
-    unsigned int total_runes = 0;
-    unsigned int total_stats = 0;
-    json_object *runes = json_object_object_get(root, "runes");
-    int rune_count = json_object_array_length(runes);
-    json_object *idx;
-    char *query_parameters[43];
-    for (int i = 1; i < 43; i ++){
-        query_parameters[i] = malloc(5);
-    }
-    for (int i = 0; i < rune_count; i++){
-        total_runes ++;
-        struct DB_Rune rune;
-        strcpy(rune.unit, ""); // Here all runes are unassigned.
-        idx = json_object_array_get_idx(runes, i);
-        json_object *rune_id = json_object_object_get(idx, "rune_id");
-        strcpy(rune.id, json_object_get_string(rune_id));
-        json_object *slot_no = json_object_object_get(idx, "slot_no");
-        rune.slot = json_object_get_int(slot_no);
-        // rank -> Quality
-        json_object *rank = json_object_object_get(idx, "rank");
-        rune.quality = json_object_get_int(rank);
-        // class -> Stars
-        json_object *class = json_object_object_get(idx, "class");
-        rune.stars = json_object_get_int(class);
-        json_object *set_id = json_object_object_get(idx, "set_id");
-        rune.set = json_object_get_int(set_id);
-        // upgrade_curre -> Power up level
-        json_object *upgrade_curr = json_object_object_get(idx, "upgrade_curr");
-        rune.level = json_object_get_int(upgrade_curr);
-        json_object *base_value = json_object_object_get(idx, "base_value");
-        rune.buy_value = json_object_get_int(base_value);
-        json_object *sell_value = json_object_object_get(idx, "sell_value");
-        rune.sell_value = json_object_get_int(sell_value);
-
-        // Main stat
-        json_object *pri_eff = json_object_object_get(idx, "pri_eff");
-        json_object *pri_stat = json_object_array_get_idx(pri_eff, 0);
-        rune.main.stat = json_object_get_int(pri_stat);
-        json_object *pri_value = json_object_array_get_idx(pri_eff, 1);
-        rune.main.value = json_object_get_int(pri_value);
-
-        json_object *prefix_eff = json_object_object_get(idx, "prefix_eff");
-
-        // Innate stat
-        json_object *prefix_stat = json_object_array_get_idx(prefix_eff, 0);
-        rune.innate.stat = json_object_get_int(prefix_stat);
-        json_object *prefix_value = json_object_array_get_idx(prefix_eff, 1);
-        rune.innate.value = json_object_get_int(prefix_value);
-
-        json_object *sec_eff = json_object_object_get(idx, "sec_eff");
-        int stat_count = json_object_array_length(sec_eff);
-        json_object *stat_idx;
-        rune.stat_count = 0;
-        for (int i = 0; i < stat_count && i < 4; i++){
-            rune.stat_count ++;
-            stat_idx = json_object_array_get_idx(sec_eff, i);
-            json_object *stat = json_object_array_get_idx(stat_idx, 0);
-            rune.stats[i].stat = json_object_get_int(stat);
-            json_object *value = json_object_array_get_idx(stat_idx, 1);
-            rune.stats[i].value = json_object_get_int(value);
-            json_object *enchant = json_object_array_get_idx(stat_idx, 2);
-            rune.stats[i].enchant = json_object_get_int(enchant);
-            json_object *grind = json_object_array_get_idx(stat_idx, 3);
-            rune.stats[i].grind = json_object_get_int(grind);
-        }
-
-        // All the rune info has been loaded. Now, calculate the rest of stats
-        calculate_rune_totals(&rune);
-
-        // Insert the rune into the database
-        query_parameters[0] = rune.id;
-        query_parameters[1] = ""; //unit
-        sprintf(query_parameters[2], "%d", rune.set);
-        sprintf(query_parameters[3], "%d", rune.slot);
-        sprintf(query_parameters[4], "%d", rune.stars);
-        sprintf(query_parameters[5], "%d", rune.level);
-        sprintf(query_parameters[6], "%d", rune.quality);
-        sprintf(query_parameters[7], "%d", rune.efficiency);
-        sprintf(query_parameters[8], "%d", rune.max_efficiency);
-        sprintf(query_parameters[9], "%d", rune.main.stat);
-        sprintf(query_parameters[10], "%d", rune.current_hp_percent);
-        sprintf(query_parameters[11], "%d", rune.current_atk_percent);
-        sprintf(query_parameters[12], "%d", rune.current_def_percent);
-        sprintf(query_parameters[13], "%d", rune.current_hp_flat);
-        sprintf(query_parameters[14], "%d", rune.current_atk_flat);
-        sprintf(query_parameters[15], "%d", rune.current_def_flat);
-        sprintf(query_parameters[16], "%d", rune.current_spd);
-        sprintf(query_parameters[17], "%d", rune.current_crr);
-        sprintf(query_parameters[18], "%d", rune.current_crd);
-        sprintf(query_parameters[19], "%d", rune.current_acc);
-        sprintf(query_parameters[20], "%d", rune.current_res);
-        sprintf(query_parameters[21], "%d", rune.lv12_hp_percent);
-        sprintf(query_parameters[22], "%d", rune.lv12_atk_percent);
-        sprintf(query_parameters[23], "%d", rune.lv12_def_percent);
-        sprintf(query_parameters[24], "%d", rune.lv12_hp_flat);
-        sprintf(query_parameters[25], "%d", rune.lv12_atk_flat);
-        sprintf(query_parameters[26], "%d", rune.lv12_def_flat);
-        sprintf(query_parameters[27], "%d", rune.lv12_spd);
-        sprintf(query_parameters[28], "%d", rune.lv12_crr);
-        sprintf(query_parameters[29], "%d", rune.lv12_crd);
-        sprintf(query_parameters[30], "%d", rune.lv12_acc);
-        sprintf(query_parameters[31], "%d", rune.lv12_res);
-        sprintf(query_parameters[32], "%d", rune.lv15_hp_percent);
-        sprintf(query_parameters[33], "%d", rune.lv15_atk_percent);
-        sprintf(query_parameters[34], "%d", rune.lv15_def_percent);
-        sprintf(query_parameters[35], "%d", rune.lv15_hp_flat);
-        sprintf(query_parameters[36], "%d", rune.lv15_atk_flat);
-        sprintf(query_parameters[37], "%d", rune.lv15_def_flat);
-        sprintf(query_parameters[38], "%d", rune.lv15_spd);
-        sprintf(query_parameters[39], "%d", rune.lv15_crr);
-        sprintf(query_parameters[40], "%d", rune.lv15_crd);
-        sprintf(query_parameters[41], "%d", rune.lv15_acc);
-        sprintf(query_parameters[42], "%d", rune.lv15_res);
-        if (
-          SUCCESS !=
-          db_execute(
-            &db,
-            "INSERT INTO runes ("
-            "  id,"
-            "  unit,"
-            "  type,"
-            "  slot,"
-            "  stars,"
-            "  level,"
-            "  quality,"
-            "  efficiency,"
-            "  max_efficiency,"
-            "  main_stat,"
-            "  current_hp_percent,"
-            "  current_atk_percent,"
-            "  current_def_percent,"
-            "  current_hp_flat,"
-            "  current_atk_flat,"
-            "  current_def_flat,"
-            "  current_spd,"
-            "  current_crr,"
-            "  current_crd,"
-            "  current_acc,"
-            "  current_res,"
-            "  lv12_hp_percent,"
-            "  lv12_atk_percent,"
-            "  lv12_def_percent,"
-            "  lv12_hp_flat,"
-            "  lv12_atk_flat,"
-            "  lv12_def_flat,"
-            "  lv12_spd,"
-            "  lv12_crr,"
-            "  lv12_crd,"
-            "  lv12_acc,"
-            "  lv12_res,"
-            "  lv15_hp_percent,"
-            "  lv15_atk_percent,"
-            "  lv15_def_percent,"
-            "  lv15_hp_flat,"
-            "  lv15_atk_flat,"
-            "  lv15_def_flat,"
-            "  lv15_spd,"
-            "  lv15_crr,"
-            "  lv15_crd,"
-            "  lv15_acc,"
-            "  lv15_res"
-            ") VALUES ("
-            "  ?, ?, ?, ?, ?, ?, ?, ?, ?, ?, ?, ?, ?, ?, ?, ?, ?, ?, ?, ?, ?,"
-            "  ?, ?, ?, ?, ?, ?, ?, ?, ?, ?, ?, ?, ?, ?, ?, ?, ?, ?, ?, ?, ?, ?"
-            ")",
-            query_parameters
-          )
-        ){
-            fprintf(
-              stderr,
-              "Unable to insert rune: %s\n", sqlite3_errmsg(db)
-            );
-            sqlite3_close(db);
-            return ERROR_DB_INSERT_RUNES;
-        }
-
-        // Insert main stat
-        total_stats ++;
-        //query_parameters[0] = rune.id; // No need, already has id
-        query_parameters[1] = "-1"; // Main stat
-        sprintf(query_parameters[2], "%d", rune.main.stat);
-        sprintf(query_parameters[3], "%d", rune.main.value);
-        query_parameters[4] = "0"; // Mains can't be grinded.
-        query_parameters[5] = "0"; // Mains can't be enchanted.
-        if (
-          SUCCESS !=
-          db_execute(
-            &db,
-            "INSERT INTO rune_stats(rune, slot, stat, value, grind, enchant) "
-            "VALUES (?, ?, ?, ?, ?, ?)",
-            query_parameters
-          )
-        ){
-            fprintf(
-              stderr,
-              "Unable to insert rune main stat: %s\n", sqlite3_errmsg(db)
-            );
-            sqlite3_close(db);
-            return ERROR_DB_INSERT_RUNE_STATS;
-        }
-
-        // Insert innate stat
-        if (rune.innate.stat != 0){
-            total_stats ++;
-            //query_parameters[0] = rune.id; // No need, already has id
-            query_parameters[1] = "0"; // Main stat
-            sprintf(query_parameters[2], "%d", rune.innate.stat);
-            sprintf(query_parameters[3], "%d", rune.innate.value);
-            query_parameters[4] = "0"; // Innates can't be grinded.
-            query_parameters[5] = "0"; // Innates can't be enchanted.
-            if (
-              SUCCESS !=
-              db_execute(
-                &db,
-                "INSERT INTO rune_stats "
-                "(rune, slot, stat, value, grind, enchant) "
-                "VALUES (?, ?, ?, ?, ?, ?)",
-                query_parameters
-              )
-            ){
-                fprintf(
-                  stderr,
-                  "Unable to insert rune innate stat: %s\n", sqlite3_errmsg(db)
-                );
-                sqlite3_close(db);
-                return ERROR_DB_INSERT_RUNE_STATS;
-            }
-        }
-
-        // Insert normal stats
-        for (int s = 0; s < rune.stat_count; s ++){
-            total_stats ++;
-            //query_parameters[0] = rune.id; // No need, already has id
-            query_parameters[1] = malloc(5);
-            sprintf(query_parameters[1], "%d", s + 1); // 1-4
-            query_parameters[2] = malloc(5);
-            sprintf(query_parameters[2], "%d", rune.stats[s].stat);
-            sprintf(query_parameters[3], "%d", rune.stats[s].value);
-            query_parameters[4] = malloc(5);
-            sprintf(query_parameters[4], "%d", rune.stats[s].grind);
-            query_parameters[5] = malloc(5);
-            sprintf(query_parameters[5], "%d", rune.stats[s].enchant);
-            if (
-              SUCCESS !=
-              db_execute(
-                &db,
-                "INSERT INTO rune_stats"
-                "(rune, slot, stat, value, grind, enchant) "
-                "VALUES (?, ?, ?, ?, ?, ?)",
-                query_parameters
-              )
-            ){
-                fprintf(
-                  stderr,
-                  "Unable to insert rune stat: %s\n", sqlite3_errmsg(db)
-                );
-                sqlite3_close(db);
-                return ERROR_DB_INSERT_RUNE_STATS;
-            }
-
-        }
-    }
-
-    // Parse units
-    unsigned int total_units = 0;
-    unsigned char unit_has_runes = FALSE;
-    json_object *unit_list = json_object_object_get(root, "unit_list");
-    int unit_count = json_object_array_length(unit_list);
-    for (int i = 0; i < unit_count; i++){
-        unit_has_runes = FALSE;
-        struct DB_Unit unit;
-        idx = json_object_array_get_idx(unit_list, i);
-        json_object *unit_id = json_object_object_get(idx, "unit_id");
-        strcpy(unit.id, json_object_get_string(unit_id));
-        json_object *unit_master_id =
-          json_object_object_get(idx, "unit_master_id");
-        unit.monster= json_object_get_int(unit_master_id);
-        get_monster_name(unit.monster, unit.name);
-        json_object *unit_level = json_object_object_get(idx, "unit_level");
-        unit.level = json_object_get_int(unit_level);
-        // class -> Stars
-        json_object *class = json_object_object_get(idx, "class");
-        unit.stars = json_object_get_int(class);
-        // con * 15 -> HP
-        json_object *con = json_object_object_get(idx, "con");
-        unit.base_hp = json_object_get_int(con) * 15;
-        json_object *atk = json_object_object_get(idx, "atk");
-        unit.base_atk = json_object_get_int(atk);
-        json_object *def = json_object_object_get(idx, "def");
-        unit.base_def = json_object_get_int(def);
-        json_object *spd = json_object_object_get(idx, "spd");
-        unit.base_spd = json_object_get_int(spd);
-        json_object *resist = json_object_object_get(idx, "resist");
-        unit.base_res = json_object_get_int(resist);
-        json_object *accuracy = json_object_object_get(idx, "accuracy");
-        unit.base_acc = json_object_get_int(accuracy);
-        json_object *critical_rate =
-          json_object_object_get(idx, "critical_rate");
-        unit.base_crr = json_object_get_int(critical_rate);
-        json_object *critical_damage =
-          json_object_object_get(idx, "critical_damage");
-        unit.base_crd = json_object_get_int(critical_damage);
-        json_object *homunculus_name =
-          json_object_object_get(idx, "homunculus_name");
-        if (strlen(json_object_get_string(homunculus_name)) > 0){
-            strcpy(unit.name, json_object_get_string(homunculus_name));
-        }
-
-        // Parse unit runes
-        json_object *unit_runes = json_object_object_get(idx, "runes");
-        rune_count = json_object_array_length(unit_runes);
-
-        for (int i = 0; i < rune_count; i++){
-            unit_has_runes = TRUE;
-            total_runes ++;
-            struct DB_Rune rune;
-            strcpy(rune.unit, unit.id);
-            idx = json_object_array_get_idx(runes, i);
-            json_object *rune_id = json_object_object_get(idx, "rune_id");
-            strcpy(rune.id, json_object_get_string(rune_id));
-            json_object *slot_no = json_object_object_get(idx, "slot_no");
-            rune.slot = json_object_get_int(slot_no);
-            // rank -> Quality
-            json_object *rank = json_object_object_get(idx, "rank");
-            rune.quality = json_object_get_int(rank);
-            // class -> Stars
-            json_object *class = json_object_object_get(idx, "class");
-            rune.stars = json_object_get_int(class);
-            json_object *set_id = json_object_object_get(idx, "set_id");
-            rune.set = json_object_get_int(set_id);
-            // upgrade_curre -> Power up level
-            json_object *upgrade_curr =
-              json_object_object_get(idx, "upgrade_curr");
-            rune.level = json_object_get_int(upgrade_curr);
-            json_object *base_value = json_object_object_get(idx, "base_value");
-            rune.buy_value = json_object_get_int(base_value);
-            json_object *sell_value = json_object_object_get(idx, "sell_value");
-            rune.sell_value = json_object_get_int(sell_value);
-
-            // Main stat
-            json_object *pri_eff = json_object_object_get(idx, "pri_eff");
-            json_object *pri_stat = json_object_array_get_idx(pri_eff, 0);
-            rune.main.stat = json_object_get_int(pri_stat);
-            json_object *pri_value = json_object_array_get_idx(pri_eff, 1);
-            rune.main.value = json_object_get_int(pri_value);
-
-            json_object *prefix_eff = json_object_object_get(idx, "prefix_eff");
-
-            // Innate stat
-            json_object *prefix_stat = json_object_array_get_idx(prefix_eff, 0);
-            rune.innate.stat = json_object_get_int(prefix_stat);
-            json_object *prefix_value =
-              json_object_array_get_idx(prefix_eff, 1);
-            rune.innate.value = json_object_get_int(prefix_value);
-
-            json_object *sec_eff = json_object_object_get(idx, "sec_eff");
-            int stat_count = json_object_array_length(sec_eff);
-            json_object *stat_idx;
-            rune.stat_count = 0;
-            for (int i = 0; i < stat_count && i < 4; i++){
-                rune.stat_count ++;
-                stat_idx = json_object_array_get_idx(sec_eff, i);
-                json_object *stat = json_object_array_get_idx(stat_idx, 0);
-                rune.stats[i].stat = json_object_get_int(stat);
-                json_object *value = json_object_array_get_idx(stat_idx, 1);
-                rune.stats[i].value = json_object_get_int(value);
-                json_object *enchant = json_object_array_get_idx(stat_idx, 2);
-                rune.stats[i].enchant = json_object_get_int(enchant);
-                json_object *grind = json_object_array_get_idx(stat_idx, 3);
-                rune.stats[i].grind = json_object_get_int(grind);
-            }
-
-            // All the rune info has been loaded.
-            // Now, calculate the rest of stats
-            calculate_rune_totals(&rune);
-
-            // Insert the rune into the database
-
-            for (int i = 1; i < 43; i ++){
-                query_parameters[i] = malloc(5);
-            }
-            char tmp[5];
-            query_parameters[0] = rune.id;
-            query_parameters[1] = rune.unit;
-            sprintf(query_parameters[2], "%d", rune.set);
-            sprintf(query_parameters[3], "%d", rune.slot);
-            sprintf(query_parameters[4], "%d", rune.stars);
-            sprintf(query_parameters[5], "%d", rune.level);
-            sprintf(query_parameters[6], "%d", rune.quality);
-            sprintf(query_parameters[7], "%d", rune.efficiency);
-            sprintf(query_parameters[8], "%d", rune.max_efficiency);
-            sprintf(query_parameters[9], "%d", rune.main.stat);
-            sprintf(query_parameters[10], "%d", rune.current_hp_percent);
-            sprintf(query_parameters[11], "%d", rune.current_atk_percent);
-            sprintf(query_parameters[12], "%d", rune.current_def_percent);
-            sprintf(query_parameters[13], "%d", rune.current_hp_flat);
-            sprintf(query_parameters[14], "%d", rune.current_atk_flat);
-            sprintf(query_parameters[15], "%d", rune.current_def_flat);
-            sprintf(query_parameters[16], "%d", rune.current_spd);
-            sprintf(query_parameters[17], "%d", rune.current_crr);
-            sprintf(query_parameters[18], "%d", rune.current_crd);
-            sprintf(query_parameters[19], "%d", rune.current_acc);
-            sprintf(query_parameters[20], "%d", rune.current_res);
-            sprintf(query_parameters[21], "%d", rune.lv12_hp_percent);
-            sprintf(query_parameters[22], "%d", rune.lv12_atk_percent);
-            sprintf(query_parameters[23], "%d", rune.lv12_def_percent);
-            sprintf(query_parameters[24], "%d", rune.lv12_hp_flat);
-            sprintf(query_parameters[25], "%d", rune.lv12_atk_flat);
-            sprintf(query_parameters[26], "%d", rune.lv12_def_flat);
-            sprintf(query_parameters[27], "%d", rune.lv12_spd);
-            sprintf(query_parameters[28], "%d", rune.lv12_crr);
-            sprintf(query_parameters[29], "%d", rune.lv12_crd);
-            sprintf(query_parameters[30], "%d", rune.lv12_acc);
-            sprintf(query_parameters[31], "%d", rune.lv12_res);
-            sprintf(query_parameters[32], "%d", rune.lv15_hp_percent);
-            sprintf(query_parameters[33], "%d", rune.lv15_atk_percent);
-            sprintf(query_parameters[34], "%d", rune.lv15_def_percent);
-            sprintf(query_parameters[35], "%d", rune.lv15_hp_flat);
-            sprintf(query_parameters[36], "%d", rune.lv15_atk_flat);
-            sprintf(query_parameters[37], "%d", rune.lv15_def_flat);
-            sprintf(query_parameters[38], "%d", rune.lv15_spd);
-            sprintf(query_parameters[39], "%d", rune.lv15_crr);
-            sprintf(query_parameters[40], "%d", rune.lv15_crd);
-            sprintf(query_parameters[41], "%d", rune.lv15_acc);
-            sprintf(query_parameters[42], "%d", rune.lv15_res);
-            if (
-              SUCCESS !=
-              db_execute(
-                &db,
-                "INSERT INTO runes ("
-                "  id,"
-                "  unit,"
-                "  type,"
-                "  slot,"
-                "  stars,"
-                "  level,"
-                "  quality,"
-                "  efficiency,"
-                "  max_efficiency,"
-                "  main_stat,"
-                "  current_hp_percent,"
-                "  current_atk_percent,"
-                "  current_def_percent,"
-                "  current_hp_flat,"
-                "  current_atk_flat,"
-                "  current_def_flat,"
-                "  current_spd,"
-                "  current_crr,"
-                "  current_crd,"
-                "  current_acc,"
-                "  current_res,"
-                "  lv12_hp_percent,"
-                "  lv12_atk_percent,"
-                "  lv12_def_percent,"
-                "  lv12_hp_flat,"
-                "  lv12_atk_flat,"
-                "  lv12_def_flat,"
-                "  lv12_spd,"
-                "  lv12_crr,"
-                "  lv12_crd,"
-                "  lv12_acc,"
-                "  lv12_res,"
-                "  lv15_hp_percent,"
-                "  lv15_atk_percent,"
-                "  lv15_def_percent,"
-                "  lv15_hp_flat,"
-                "  lv15_atk_flat,"
-                "  lv15_def_flat,"
-                "  lv15_spd,"
-                "  lv15_crr,"
-                "  lv15_crd,"
-                "  lv15_acc,"
-                "  lv15_res"
-                ") VALUES ("
-                "  ?, ?, ?, ?, ?, ?, ?, ?, ?, ?, ?, ?, ?, ?, ?,"
-                "  ?, ?, ?, ?, ?, ?, ?, ?, ?, ?, ?, ?, ?, ?,"
-                "  ?, ?, ?, ?, ?, ?, ?, ?, ?, ?, ?, ?, ?, ?"
-                ")",
-                query_parameters
-              )
-            ){
-                fprintf(
-                  stderr,
-                  "Unable to insert rune: %s\n", sqlite3_errmsg(db)
-                );
-                sqlite3_close(db);
-                return ERROR_DB_INSERT_RUNES;
-            }
-
-            // Insert main stat
-            total_stats ++;
-            //query_parameters[0] = rune.id; // No need, already has id
-            query_parameters[1] = "-1"; // Main stat
-            sprintf(query_parameters[2], "%d", rune.main.stat);
-            sprintf(query_parameters[3], "%d", rune.main.value);
-            query_parameters[4] = "0"; // Mains can't be grinded.
-            query_parameters[5] = "0"; // Mains can't be enchanted.
-            if (
-              SUCCESS !=
-              db_execute(
-                &db,
-                "INSERT INTO "
-                "rune_stats(rune, slot, stat, value, grind, enchant) "
-                "VALUES (?, ?, ?, ?, ?, ?)",
-                query_parameters
-              )
-            ){
-                fprintf(
-                  stderr,
-                  "Unable to insert rune main stat: %s\n", sqlite3_errmsg(db)
-                );
-                sqlite3_close(db);
-                return ERROR_DB_INSERT_RUNE_STATS;
-            }
-
-            // Insert innate stat
-            if (rune.innate.stat != 0){
-                total_stats ++;
-                //query_parameters[0] = rune.id; // No need, already has id
-                query_parameters[1] = "0"; // Main stat
-                sprintf(query_parameters[2], "%d", rune.innate.stat);
-                sprintf(query_parameters[3], "%d", rune.innate.value);
-                query_parameters[4] = "0"; // Innates can't be grinded.
-                query_parameters[5] = "0"; // Innates can't be enchanted.
-                if (
-                  SUCCESS !=
-                  db_execute(
-                    &db,
-                    "INSERT INTO "
-                    "rune_stats(rune, slot, stat, value, grind, enchant) "
-                    "VALUES (?, ?, ?, ?, ?, ?)",
-                    query_parameters
-                  )
-                ){
-                    fprintf(
-                      stderr,
-                      "Unable to insert rune innate stat: %s\n",
-                      sqlite3_errmsg(db)
-                    );
-                    sqlite3_close(db);
-                    return ERROR_DB_INSERT_RUNE_STATS;
-                }
-            }
-
-            // Insert normal stats
-            for (int s = 0; s < rune.stat_count; s ++){
-                total_stats ++;
-                //query_parameters[0] = rune.id; // No need, already has id
-                query_parameters[1] = malloc(5);
-                sprintf(query_parameters[1], "%d", s + 1); // 1-4
-                query_parameters[2] = malloc(5);
-                sprintf(query_parameters[2], "%d", rune.stats[s].stat);
-                sprintf(query_parameters[3], "%d", rune.stats[s].value);
-                query_parameters[4] = malloc(5);
-                sprintf(query_parameters[4], "%d", rune.stats[s].grind);
-                query_parameters[5] = malloc(5);
-                sprintf(query_parameters[5], "%d", rune.stats[s].enchant);
-                if (
-                  SUCCESS !=
-                  db_execute(
-                    &db,
-                    "INSERT INTO "
-                    "rune_stats(rune, slot, stat, value, grind, enchant) "
-                    "VALUES (?, ?, ?, ?, ?, ?)",
-                    query_parameters
-                  )
-                ){
-                    fprintf(
-                      stderr,
-                      "Unable to insert rune stat: %s\n", sqlite3_errmsg(db)
-                    );
-                    sqlite3_close(db);
-                    return ERROR_DB_INSERT_RUNE_STATS;
-                }
-
-            }
-        }
-
-
-        // Insert unit, depending on flags and status
-        if (
-            unit_has_runes == TRUE ||
-            (six_stars == FALSE && with_runes == FALSE) ||
-            (six_stars == TRUE && unit.stars == TRUE)
-        ){
-            total_units ++;
-            query_parameters[0] = unit.id;
-            sprintf(query_parameters[1], "%d", unit.monster);
-            query_parameters[2] = unit.name;
-            sprintf(query_parameters[3], "%d", unit.stars);
-            sprintf(query_parameters[4], "%d", unit.level);
-            sprintf(query_parameters[5], "%d", unit.base_hp);
-            sprintf(query_parameters[6], "%d", unit.base_atk);
-            sprintf(query_parameters[7], "%d", unit.base_def);
-            sprintf(query_parameters[8], "%d", unit.base_spd);
-            sprintf(query_parameters[9], "%d", unit.base_crr);
-            sprintf(query_parameters[10], "%d", unit.base_crd);
-            sprintf(query_parameters[10], "%d", unit.base_res);
-            sprintf(query_parameters[11], "%d", unit.base_acc);
-            // Insert current stats as base stats.
-            // They will be updated later.
-            sprintf(query_parameters[12], "%d", unit.base_hp);
-            sprintf(query_parameters[13], "%d", unit.base_atk);
-            sprintf(query_parameters[14], "%d", unit.base_def);
-            sprintf(query_parameters[15], "%d", unit.base_spd);
-            sprintf(query_parameters[16], "%d", unit.base_crr);
-            sprintf(query_parameters[17], "%d", unit.base_crd);
-            sprintf(query_parameters[18], "%d", unit.base_res);
-            sprintf(query_parameters[19], "%d", unit.base_acc);
-            // TODO: Storage
-            sprintf(query_parameters[20], "%d", 0);
-            if (
-              SUCCESS !=
-              db_execute(
-                &db,
-                "INSERT INTO units ("
-                "  id,"
-                "  monster,"
-                "  name,"
-                "  stars,"
-                "  level,"
-                "  base_hp,"
-                "  base_atk,"
-                "  base_def,"
-                "  base_spd,"
-                "  base_crr,"
-                "  base_crd,"
-                "  base_res,"
-                "  base_acc,"
-                "  current_hp,"
-                "  current_atk,"
-                "  current_def,"
-                "  current_spd,"
-                "  current_crr,"
-                "  current_crd,"
-                "  current_res,"
-                "  current_acc,"
-                "  storage"
-                ") VALUES ("
-                "  ?, ?, ?, ?, ?, ?, ?, ?, ?, ?, ?,"
-                "  ?, ?, ?, ?, ?, ?, ?, ?, ?, ?, ?"
-                ")",
-                query_parameters
-              )
-            ){
-                fprintf(
-                  stderr,
-                  "Unable to insert unit: %s\n", sqlite3_errmsg(db)
-                );
-                sqlite3_close(db);
-                return ERROR_DB_INSERT_UNITS;
-            }
-        }
-    }
-
-    int calculate_result = calculate_current_stats();
-    if (SUCCESS != calculate_result){
-        return calculate_result;
-    }
-
-    // Insert into table info
-    time_t t = time(NULL);
-    struct tm tm = *localtime(&t);
-    char ts[130];
-    sprintf(
-      ts,
-      "%d-%02d-%02d %02d:%02d:%02d",
-      tm.tm_year + 1900,
-      tm.tm_mon + 1,
-      tm.tm_mday,
-      tm.tm_hour,
-      tm.tm_min,
-      tm.tm_sec
-    );
-    sprintf(query_parameters[0], "%s", json_object_get_string(wizard_id));
-    sprintf(query_parameters[1], "%s", json_object_get_string(wizard_name));
-    sprintf(query_parameters[2], "%s", json_object_get_string(wizard_level));
-    query_parameters[3] = ts;
-    query_parameters[4] = "0"; // Modified
-    if (
-      SUCCESS !=
-      db_execute(
-        &db,
-        "INSERT INTO info ( player_id, player_name, player_level, ts, modified)"
-        "VALUES (?, ?, ?, ?, ?)",
-        query_parameters
-      )
-    ){
-        fprintf(
-            stderr,
-            "Unable to save meta info: %s\n", sqlite3_errmsg(db)
-        );
-        sqlite3_close(db);
-        return ERROR_DB_INSERT_INFO;
-    }
-
-    // All parsed
-    printf("%d units saved.\n", total_units);
-    printf("%d runes saved.\n", total_runes);
-    printf("%d rune stats saved.\n", total_stats);
-    printf("Player info updated\n");
-
-    sqlite3_close(db);
-    return SUCCESS;
-}
-
-/**
- * Calculates the current stats for units with runes in the database.
- *
- * @return SUCCESS or an error code.
- */
-int calculate_current_stats(){
-
-    sqlite3 *db = NULL;
-    sqlite3_stmt *stmt_unit;
-
-    db_query(
-      &db, &stmt_unit,
-      "SELECT"
-      "  id,"
-      "  base_hp,"
-      "  base_atk,"
-      "  base_def,"
-      "  base_spd,"
-      "  base_crr,"
-      "  base_crd,"
-      "  base_res,"
-      "  base_acc,"
-      "  current_hp,"
-      "  current_atk,"
-      "  current_def,"
-      "  current_spd,"
-      "  current_crr,"
-      "  current_crd,"
-      "  current_res,"
-      "  current_acc"
-      " FROM units WHERE id IN (SELECT DISTINCT unit FROM runes)",
-      NULL
-    );
-
-    unsigned char id[12];
-    unsigned int base_hp = 0;
-    unsigned int base_atk = 0;
-    unsigned int base_def = 0;
-    unsigned int base_spd = 0;
-    unsigned int base_crr = 0;
-    unsigned int base_crd = 0;
-    unsigned int base_res = 0;
-    unsigned int base_acc = 0;
-    unsigned int current_hp = 0;
-    unsigned int current_atk = 0;
-    unsigned int current_def = 0;
-    unsigned int current_spd = 0;
-    unsigned int current_crr = 0;
-    unsigned int current_crd = 0;
-    unsigned int current_res = 0;
-    unsigned int current_acc = 0;
-    while (SQLITE_ROW == sqlite3_step(stmt_unit)){
-        strcpy(id, sqlite3_column_text(stmt_unit, 0));
-        base_hp = sqlite3_column_int(stmt_unit, 1);
-        base_atk = sqlite3_column_int(stmt_unit, 2);
-        base_def = sqlite3_column_int(stmt_unit, 3);
-        base_spd = sqlite3_column_int(stmt_unit, 4);
-        base_crr = sqlite3_column_int(stmt_unit, 5);
-        base_crd = sqlite3_column_int(stmt_unit, 6);
-        base_res = sqlite3_column_int(stmt_unit, 7);
-        base_acc = sqlite3_column_int(stmt_unit, 8);
-        current_hp = base_hp;
-        current_atk = base_atk;
-        current_def = base_def;
-        current_spd = base_spd;
-        current_crr = base_crr;
-        current_crd = base_crd;
-        current_res = base_res;
-        current_acc = base_acc;
-
-        // Loop runes and add flat and percent stats
-        // Also, count rune sets for bonus
-        struct Rune_Set_Count set_count;
-        set_count.energy = 0;
-        set_count.guard = 0;
-        set_count.swift = 0;
-        set_count.blade = 0;
-        set_count.rage = 0;
-        set_count.focus = 0;
-        set_count.endure = 0;
-        set_count.fatal = 0;
-        set_count.despair = 0;
-        set_count.vampire = 0;
-        set_count.violent = 0;
-        set_count.nemesis = 0;
-        set_count.will = 0;
-        set_count.shield = 0;
-        set_count.revenge = 0;
-        set_count.destroy = 0;
-        set_count.fight = 0;
-        set_count.determination = 0;
-        set_count.enhance = 0;
-        set_count.accuracy = 0;
-        set_count.tolerance = 0;
-        sqlite3_stmt *stmt_runes;
-        char *parameters[1];
-        parameters[0] = id;
-        db_query(
-          &db, &stmt_runes,
-          "SELECT"
-          "  type,"
-          "  current_hp_flat,"
-          "  current_atk_flat,"
-          "  current_def_flat,"
-          "  current_hp_percent,"
-          "  current_atk_percent,"
-          "  current_def_percent,"
-          "  current_spd,"
-          "  current_crr,"
-          "  current_crd,"
-          "  current_res,"
-          "  current_acc,"
-          "  slot"
-          " FROM runes WHERE unit = ?",
-          parameters
-        );
-        while (SQLITE_ROW == sqlite3_step(stmt_runes)){
-            // Switch the rune set
-            switch (sqlite3_column_int(stmt_runes, 0)){
-                case ENERGY:
-                    set_count.energy ++;
-                    break;
-                case GUARD:
-                    set_count.guard ++;
-                    break;
-                case SWIFT:
-                    set_count.swift ++;
-                    break;
-                case BLADE:
-                    set_count.blade ++;
-                    break;
-                case RAGE:
-                    set_count.rage ++;
-                    break;
-                case FOCUS:
-                    set_count.focus ++;
-                    break;
-                case ENDURE:
-                    set_count.endure ++;
-                    break;
-                case FATAL:
-                    set_count.fatal ++;
-                    break;
-                case DESPAIR:
-                    set_count.despair ++;
-                    break;
-                case VAMPIRE:
-                    set_count.vampire ++;
-                    break;
-                case VIOLENT:
-                    set_count.violent ++;
-                    break;
-                case NEMESIS:
-                    set_count.nemesis ++;
-                    break;
-                case WILL:
-                    set_count.will ++;
-                    break;
-                case SHIELD:
-                    set_count.shield ++;
-                    break;
-                case REVENGE:
-                    set_count.revenge ++;
-                    break;
-                case DESTROY:
-                    set_count.destroy ++;
-                    break;
-                case FIGHT:
-                    set_count.fight ++;
-                    break;
-                case DETERMINATION:
-                    set_count.determination ++;
-                    break;
-                case ENHANCE:
-                    set_count.enhance ++;
-                    break;
-                case ACCURACY:
-                    set_count.accuracy ++;
-                    break;
-                case TOLERANCE:
-                    set_count.tolerance ++;
-                    break;
-            }
-
-            //Add rune values
-            current_hp += sqlite3_column_int(stmt_runes, 1);
-            current_atk += sqlite3_column_int(stmt_runes, 2);
-            current_def += sqlite3_column_int(stmt_runes, 3);
-            current_hp += base_hp * sqlite3_column_int(stmt_runes, 4) / 100;
-            current_atk += base_atk * sqlite3_column_int(stmt_runes, 5) / 100;
-            current_def += base_def * sqlite3_column_int(stmt_runes, 6) / 100;
-            current_spd += sqlite3_column_int(stmt_runes, 7);
-            current_crr += sqlite3_column_int(stmt_runes, 8);
-            current_crd += sqlite3_column_int(stmt_runes, 9);
-            current_res += sqlite3_column_int(stmt_runes, 10);
-            current_acc += sqlite3_column_int(stmt_runes, 11);
-        }
-        sqlite3_finalize(stmt_runes);
-
-        // Rune set bonuses
-        if (set_count.energy >= 2) // +15% Base HP per set of 2
-            current_hp += base_hp * 0.15 * (set_count.energy % 2);
-        if (set_count.guard >= 2) // +15% base DEF per set of 2
-            current_def += base_def * 0.15 * (set_count.guard % 2);
-        if (set_count.swift >= 4) // +25% base SPD per set of 4
-            current_spd += base_spd * 0.25;
-        if (set_count.blade >= 2) // +12% CRR per set of 2
-            current_crr += 12;
-        if (set_count.rage >= 4) // +40% CRD per set of 4
-            current_crd += 40;
-        if (set_count.focus >= 2) // +20% ACC per set of 2
-            current_acc += 20;
-        if (set_count.endure >= 2) // +20% RES per set of 2
-            current_res += 20;
-        if (set_count.fatal >= 4) // +35% base ATK per set of 4
-            current_atk += base_atk * 0.35;
-        if (set_count.fight >= 2) // +8% base ATK per set of 2
-            current_atk += base_atk * 0.08 * (set_count.fight % 2);
-        if (set_count.determination >= 2) // +8% base DEF per set of 2
-            current_def += base_def * 0.08 * (set_count.determination % 2);
-        if (set_count.enhance >= 2) // +8% base HP per set of 2
-            current_hp += base_hp * 0.08 * (set_count.enhance % 2);
-        if (set_count.accuracy >= 2) // +10% ACC per set of 2
-            current_acc += 20;
-        if (set_count.tolerance >= 2) // +10% RES per set of 2
-            current_res += 20;
-
-        // Cap limited stats
-        if (current_crr > 100) current_crr = 100;
-        if (current_res > 100) current_res = 100;
-        if (current_acc > 85) current_acc = 85;
-
-        // Update in database
-        char *parameters_update[9];
-        for (int i = 1; i < 9; i ++){
-            parameters_update[i] = malloc(5);
-        }
-        sprintf(parameters_update[0], "%d", current_hp);
-        sprintf(parameters_update[1], "%d", current_atk);
-        sprintf(parameters_update[2], "%d", current_def);
-        sprintf(parameters_update[3], "%d", current_spd);
-        sprintf(parameters_update[4], "%d", current_crr);
-        sprintf(parameters_update[5], "%d", current_crd);
-        sprintf(parameters_update[6], "%d", current_res);
-        sprintf(parameters_update[7], "%d", current_acc);
-        parameters_update[8] = id;
-
-        if (
-          SUCCESS !=
-          db_execute(
-            &db,
-            "UPDATE units SET"
-            "  current_hp = ?,"
-            "  current_atk = ?,"
-            "  current_def = ?,"
-            "  current_spd = ?,"
-            "  current_crr = ?,"
-            "  current_crd = ?,"
-            "  current_res = ?,"
-            "  current_acc = ? "
-            "WHERE id = ?",
-            parameters_update
-          )
-        ){
-            fprintf(
-              stderr,
-              "Unable to undate unit info: %s\n", sqlite3_errmsg(db)
-            );
-            sqlite3_close(db);
-            return ERROR_DB_UPDATE_UNITS;
-        }
-    }
-    sqlite3_finalize(stmt_unit);
-    sqlite3_close(db);
-    return SUCCESS;
-}
-
-/**
- * Recreates the tables in the database.
- *
- * @param[in] clear_teams Indicator to recreate tables teams and units_teams.
- * @return SUCCESS or an error code.
- */
-int recreate_tables(unsigned char clear_teams){
-    sqlite3 *db = NULL;
-    // Table rune_stats
-    if (
-      SUCCESS !=
-      db_execute(
-        &db, "DROP TABLE IF EXISTS rune_stats;", NULL
-      )
-    ){
-        fprintf(
-          stderr, "Unable to drop table rune_stats: %s\n", sqlite3_errmsg(db)
-        );
-        sqlite3_close(db);
-        return ERROR_DB_DROP_RUNE_STATS;
-    }
-    if (
-      SUCCESS !=
-      db_execute(
-        &db,
-        "CREATE TABLE rune_stats("
-        "  rune CHAR(12),"
-        "  slot INT,"
-        "  stat INT,"
-        "  value INT,"
-        "  grind INT,"
-        "  enchant INT"
-        ");",
-        NULL
-      )
-    ){
-        fprintf(
-          stderr,
-          "Unable to create table rune_stats: %s\n", sqlite3_errmsg(db)
-        );
-        sqlite3_close(db);
-        return ERROR_DB_CREATE_RUNE_STATS;
-    }
-
-    // Table runes
-    if (
-      SUCCESS !=
-      db_execute(&db, "DROP TABLE IF EXISTS runes;", NULL)
-    ){
-        fprintf(
-          stderr, "Unable to drop table runes: %s\n", sqlite3_errmsg(db)
-        );
-        sqlite3_close(db);
-        return ERROR_DB_DROP_RUNES;
-    }
-    if (
-      SUCCESS !=
-      db_execute(
-        &db,
-        "CREATE TABLE runes("
-        "  id CHAR(12),"
-        "  unit CHAR(12),"
-        "  type INT,"
-        "  slot INT,"
-        "  stars INT,"
-        "  level INT,"
-        "  quality INT,"
-        "  efficiency FLOAT,"
-        "  max_efficiency FLOAT,"
-        "  main_stat INT,"
-        "  current_hp_percent INT,"
-        "  current_atk_percent INT,"
-        "  current_def_percent INT,"
-        "  current_hp_flat INT,"
-        "  current_atk_flat INT,"
-        "  current_def_flat INT,"
-        "  current_spd INT,"
-        "  current_crr INT,"
-        "  current_crd INT,"
-        "  current_acc INT,"
-        "  current_res INT,"
-        "  lv12_hp_percent INT,"
-        "  lv12_atk_percent INT,"
-        "  lv12_def_percent INT,"
-        "  lv12_hp_flat INT,"
-        "  lv12_atk_flat INT,"
-        "  lv12_def_flat INT,"
-        "  lv12_spd INT,"
-        "  lv12_crr INT,"
-        "  lv12_crd INT,"
-        "  lv12_acc INT,"
-        "  lv12_res INT,"
-        "  lv15_hp_percent INT,"
-        "  lv15_atk_percent INT,"
-        "  lv15_def_percent INT,"
-        "  lv15_hp_flat INT,"
-        "  lv15_atk_flat INT,"
-        "  lv15_def_flat INT,"
-        "  lv15_spd INT,"
-        "  lv15_crr INT,"
-        "  lv15_crd INT,"
-        "  lv15_acc INT,"
-        "  lv15_res INT"
-        ");",
-        NULL
-      )
-    ){
-        fprintf(
-          stderr, "Unable to create table runes: %s\n", sqlite3_errmsg(db)
-        );
-        sqlite3_close(db);
-        return ERROR_DB_CREATE_RUNES;
-    }
-
-    // Table units
-    if (
-      SUCCESS !=
-      db_execute(
-        &db, "DROP TABLE IF EXISTS units;", NULL
-      )
-    ){
-        fprintf(
-          stderr, "Unable to drop table units: %s\n", sqlite3_errmsg(db)
-        );
-        sqlite3_close(db);
-        return ERROR_DB_DROP_UNITS;
-    }
-    if (
-      SUCCESS !=
-      db_execute(
-        &db,
-        "CREATE TABLE units("
-        "  id CHAR(12),"
-        "  monster INT,"
-        "  name CHAR(128),"
-        "  stars INT,"
-        "  level INT,"
-        "  storage INT,"
-        "  base_hp INT,"
-        "  base_atk INT,"
-        "  base_def INT,"
-        "  base_spd INT,"
-        "  base_crr INT,"
-        "  base_crd INT,"
-        "  base_res INT,"
-        "  base_acc INT,"
-        "  current_hp INT,"
-        "  current_atk INT,"
-        "  current_def INT,"
-        "  current_spd INT,"
-        "  current_crr INT,"
-        "  current_crd INT,"
-        "  current_res INT,"
-        "  current_acc INT"
-        ");",
-        NULL
-      )
-    ){
-        fprintf(
-          stderr,
-          "Unable to create table units: %s\n", sqlite3_errmsg(db)
-        );
-        sqlite3_close(db);
-        return ERROR_DB_CREATE_UNITS;
-    }
-
-    // Table info
-    if (
-      SUCCESS !=
-      db_execute(
-        &db, "DROP TABLE IF EXISTS info;", NULL
-      )
-    ){
-        fprintf(
-          stderr, "Unable to drop table info: %s\n", sqlite3_errmsg(db)
-        );
-        sqlite3_close(db);
-        return ERROR_DB_DROP_INFO;
-    }
-    if (
-      SUCCESS !=
-      db_execute(
-        &db,
-        "CREATE TABLE info("
-        "  player_id CHAR(12),"
-        "  player_name CHAR(64),"
-        "  player_level INT,"
-        "  ts DATETIME,"
-        "  modified INT"
-        ");",
-        NULL
-      )
-    ){
-        fprintf(
-          stderr,
-          "Unable to create table info: %s\n", sqlite3_errmsg(db)
-        );
-        sqlite3_close(db);
-        return ERROR_DB_CREATE_INFO;
-    }
-
-    // Tables teams and units_teams (optional)
-    if (clear_teams == TRUE){
-        if (
-          SUCCESS !=
-          db_execute(
-            &db, "DROP TABLE IF EXISTS units_teams;", NULL
-          )
-        ){
-            fprintf(
-              stderr,
-              "Unable to drop table units_teams: %s\n", sqlite3_errmsg(db)
-            );
-            sqlite3_close(db);
-            return ERROR_DB_DROP_UNITS_TEAMS;
-        }
-        if (
-          SUCCESS !=
-          db_execute(
-            &db,
-            "CREATE TABLE units_teams(unit CHAR(12), team CHAR(12));",
-            NULL
-          )
-        ){
-            fprintf(
-              stderr,
-              "Unable to create table units_teams: %s\n", sqlite3_errmsg(db)
-            );
-            sqlite3_close(db);
-            return ERROR_DB_CREATE_UNITS_TEAMS;
-        }
-        if (
-          SUCCESS !=
-          db_execute(
-            &db, "DROP TABLE IF EXISTS teams;", NULL
-          )
-        ){
-            fprintf(
-              stderr, "Unable to drop table teams: %s\n", sqlite3_errmsg(db)
-            );
-            sqlite3_close(db);
-            return ERROR_DB_DROP_TEAMS;
-        }
-        if (
-          SUCCESS !=
-          db_execute(
-            &db,
-            "CREATE TABLE teams(unit CHAR(12), name CHAR(50), priority INT);",
-            NULL
-          )
-        ){
-            fprintf(
-              stderr,
-              "Unable to create table teams: %s\n", sqlite3_errmsg(db)
-            );
-            sqlite3_close(db);
-            return ERROR_DB_CREATE_TEAMS;
-        }
-    }
-
-    sqlite3_close(db);
-    return SUCCESS;
-}
-
-/**
- * Calculates the total stat values for a rune.
- *
- * @param[in|out] rune Rune to do the calculation on.
- */
-void calculate_rune_totals(struct DB_Rune *rune){
-    rune->efficiency = 0.0f;
-    rune->max_efficiency = 0.0f;
-    rune->current_hp_flat = 0;
-    rune->current_hp_percent = 0;
-    rune->lv12_hp_flat = 0;
-    rune->lv12_hp_percent = 0;
-    rune->lv15_hp_flat = 0;
-    rune->lv15_hp_percent = 0;
-    rune->current_atk_flat = 0;
-    rune->current_atk_percent = 0;
-    rune->lv12_atk_flat = 0;
-    rune->lv12_atk_percent = 0;
-    rune->lv15_atk_flat = 0;
-    rune->lv15_atk_percent = 0;
-    rune->current_def_flat = 0;
-    rune->current_def_percent = 0;
-    rune->lv12_def_flat = 0;
-    rune->lv12_def_percent = 0;
-    rune->lv15_def_flat = 0;
-    rune->lv15_def_percent = 0;
-    rune->current_spd = 0;
-    rune->lv12_spd = 0;
-    rune->lv15_spd = 0;
-    rune->current_crr = 0;
-    rune->lv12_crr = 0;
-    rune->lv15_crr = 0;
-    rune->current_crd = 0;
-    rune->lv12_crd = 0;
-    rune->lv15_crd = 0;
-    rune->current_res = 0;
-    rune->lv12_res = 0;
-    rune->lv15_res = 0;
-    rune->current_acc = 0;
-    rune->lv12_acc = 0;
-    rune->lv15_acc = 0;
-    // TODO: Calculate efficiencies
-    switch (rune->main.stat){
-        case HP_FLAT:
-            rune->current_hp_flat += rune->main.value;
-            if (rune->level > 12){
-                rune->lv12_hp_flat += rune->main.value;
-            }
-            else{
-                rune->lv12_hp_flat +=
-                  main_stats_values[rune->main.stat][rune->stars][0];
-            }
-            rune->lv15_hp_flat +=
-              main_stats_values[rune->main.stat][rune->stars][1];
-            break;
-        case HP_PERCENT:
-            rune->current_hp_percent += rune->main.value;
-            if (rune->level > 12){
-                rune->lv12_hp_percent += rune->main.value;
-            }
-            else{
-                rune->lv12_hp_percent +=
-                  main_stats_values[rune->main.stat][rune->stars][0];
-            }
-            rune->lv15_hp_percent +=
-              main_stats_values[rune->main.stat][rune->stars][1];
-            break;
-        case ATK_FLAT:
-            rune->current_atk_flat += rune->main.value;
-            if (rune->level > 12){
-                rune->lv12_atk_flat += rune->main.value;
-            }
-            else{
-                rune->lv12_atk_flat +=
-                  main_stats_values[rune->main.stat][rune->stars][0];
-            }
-            rune->lv15_atk_flat +=
-              main_stats_values[rune->main.stat][rune->stars][1];
-            break;
-        case ATK_PERCENT:
-            rune->current_atk_percent += rune->main.value;
-            if (rune->level > 12){
-                rune->lv12_atk_percent += rune->main.value;
-            }
-            else{
-                rune->lv12_atk_percent +=
-                  main_stats_values[rune->main.stat][rune->stars][0];
-            }
-            rune->lv15_atk_percent +=
-              main_stats_values[rune->main.stat][rune->stars][1];
-            break;
-        case DEF_FLAT:
-            rune->current_def_flat += rune->main.value;
-            if (rune->level > 12){
-                rune->lv12_def_flat += rune->main.value;
-            }
-            else{
-                rune->lv12_def_flat +=
-                  main_stats_values[rune->main.stat][rune->stars][0];
-            }
-            rune->lv15_def_flat +=
-              main_stats_values[rune->main.stat][rune->stars][1];
-            break;
-        case DEF_PERCENT:
-            rune->current_def_percent += rune->main.value;
-            if (rune->level > 12){
-                rune->lv12_def_percent += rune->main.value;
-            }
-            else{
-                rune->lv12_def_percent +=
-                  main_stats_values[rune->main.stat][rune->stars][0];
-            }
-            rune->lv15_def_percent +=
-              main_stats_values[rune->main.stat][rune->stars][1];
-            break;
-        case SPD:
-            rune->current_spd += rune->main.value;
-            if (rune->level > 12){
-                rune->lv12_spd += rune->main.value;
-            }
-            else{
-                rune->lv12_spd +=
-                  main_stats_values[rune->main.stat][rune->stars][0];
-            }
-            rune->lv15_spd +=
-              main_stats_values[rune->main.stat][rune->stars][1];
-            break;
-        case CRR:
-            rune->current_crr += rune->main.value;
-            if (rune->level > 12){
-                rune->lv12_crr += rune->main.value;
-            }
-            else{
-                rune->lv12_crr +=
-                  main_stats_values[rune->main.stat][rune->stars][0];
-            }
-            rune->lv15_crr +=
-              main_stats_values[rune->main.stat][rune->stars][1];
-            break;
-        case CRD:
-            rune->current_crd += rune->main.value;
-            if (rune->level > 12){
-                rune->lv12_crd += rune->main.value;
-            }
-            else{
-                rune->lv12_crd +=
-                  main_stats_values[rune->main.stat][rune->stars][0];
-            }
-            rune->lv15_crd +=
-              main_stats_values[rune->main.stat][rune->stars][1];
-            break;
-        case RES:
-            rune->current_res += rune->main.value;
-            if (rune->level > 12){
-                rune->lv12_res += rune->main.value;
-            }
-            else{
-                rune->lv12_res +=
-                  main_stats_values[rune->main.stat][rune->stars][0];
-            }
-            rune->lv15_res +=
-              main_stats_values[rune->main.stat][rune->stars][1];
-            break;
-        case ACC:
-            rune->current_acc += rune->main.value;
-            if (rune->level > 12){
-                rune->lv12_acc += rune->main.value;
-            }
-            else{
-                rune->lv12_acc +=
-                  main_stats_values[rune->main.stat][rune->stars][0];
-            }
-            rune->lv15_acc +=
-              main_stats_values[rune->main.stat][rune->stars][1];
-            break;
-    }
-    switch (rune->innate.stat){
-        case HP_FLAT:
-            rune->current_hp_flat += rune->innate.value;
-            rune->lv12_hp_flat += rune->innate.value;
-            rune->lv15_hp_flat += rune->innate.value;
-            break;
-        case HP_PERCENT:
-            rune->current_hp_percent += rune->innate.value;
-            rune->lv12_hp_percent += rune->innate.value;
-            rune->lv15_hp_percent += rune->innate.value;
-            break;
-        case ATK_FLAT:
-            rune->current_atk_flat += rune->innate.value;
-            rune->lv12_atk_flat += rune->innate.value;
-            rune->lv15_atk_flat += rune->innate.value;
-            break;
-        case ATK_PERCENT:
-            rune->current_atk_percent += rune->innate.value;
-            rune->lv12_atk_percent += rune->innate.value;
-            rune->lv15_atk_percent += rune->innate.value;
-            break;
-        case DEF_FLAT:
-            rune->current_def_flat += rune->innate.value;
-            rune->lv12_def_flat += rune->innate.value;
-            rune->lv15_def_flat += rune->innate.value;
-            break;
-        case DEF_PERCENT:
-            rune->current_def_percent += rune->innate.value;
-            rune->lv12_def_percent += rune->innate.value;
-            rune->lv15_def_percent += rune->innate.value;
-            break;
-        case SPD:
-            rune->current_spd += rune->innate.value;
-            rune->lv12_spd += rune->innate.value;
-            rune->lv15_spd += rune->innate.value;
-            break;
-        case CRR:
-            rune->current_crr += rune->innate.value;
-            rune->lv12_crr += rune->innate.value;
-            rune->lv15_crr += rune->innate.value;
-            break;
-        case CRD:
-            rune->current_crd += rune->innate.value;
-            rune->lv12_crd += rune->innate.value;
-            rune->lv15_crd += rune->innate.value;
-            break;
-        case RES:
-            rune->current_res += rune->innate.value;
-            rune->lv12_res += rune->innate.value;
-            rune->lv15_res += rune->innate.value;
-            break;
-        case ACC:
-            rune->current_acc += rune->innate.value;
-            rune->lv12_acc += rune->innate.value;
-            rune->lv15_acc += rune->innate.value;
-            break;
-    }
-    for (int i = 0; i < rune->stat_count; i++){
-        switch (rune->stats[i].stat){
-            case HP_FLAT:
-                rune->current_hp_flat +=
-                  (rune->stats[i].value + rune->stats[i].grind);
-                rune->lv12_hp_flat +=
-                  (rune->stats[i].value + rune->stats[i].grind);
-                rune->lv15_hp_flat +=
-                  (rune->stats[i].value + rune->stats[i].grind);
-                break;
-            case HP_PERCENT:
-                rune->current_hp_percent +=
-                  (rune->stats[i].value + rune->stats[i].grind);
-                rune->lv12_hp_percent +=
-                  (rune->stats[i].value + rune->stats[i].grind);
-                rune->lv15_hp_percent +=
-                  (rune->stats[i].value + rune->stats[i].grind);
-                break;
-            case ATK_FLAT:
-                rune->current_atk_flat +=
-                  (rune->stats[i].value + rune->stats[i].grind);
-                rune->lv12_atk_flat +=
-                  (rune->stats[i].value + rune->stats[i].grind);
-                rune->lv15_atk_flat +=
-                  (rune->stats[i].value + rune->stats[i].grind);
-                break;
-            case ATK_PERCENT:
-                rune->current_atk_percent +=
-                  (rune->stats[i].value + rune->stats[i].grind);
-                rune->lv12_atk_percent +=
-                  (rune->stats[i].value + rune->stats[i].grind);
-                rune->lv15_atk_percent +=
-                  (rune->stats[i].value + rune->stats[i].grind);
-                break;
-            case DEF_FLAT:
-                rune->current_def_flat +=
-                  (rune->stats[i].value + rune->stats[i].grind);
-                rune->lv12_def_flat +=
-                  (rune->stats[i].value + rune->stats[i].grind);
-                rune->lv15_def_flat +=
-                  (rune->stats[i].value + rune->stats[i].grind);
-                break;
-            case DEF_PERCENT:
-                rune->current_def_percent +=
-                  (rune->stats[i].value + rune->stats[i].grind);
-                rune->lv12_def_percent +=
-                  (rune->stats[i].value + rune->stats[i].grind);
-                rune->lv15_def_percent +=
-                  (rune->stats[i].value + rune->stats[i].grind);
-                break;
-            case SPD:
-                rune->current_spd +=
-                  (rune->stats[i].value + rune->stats[i].grind);
-                rune->lv12_spd +=
-                  (rune->stats[i].value + rune->stats[i].grind);
-                rune->lv15_spd +=
-                  (rune->stats[i].value + rune->stats[i].grind);
-                break;
-            case CRR:
-                rune->current_crr +=
-                  (rune->stats[i].value + rune->stats[i].grind);
-                rune->lv12_crr +=
-                  (rune->stats[i].value + rune->stats[i].grind);
-                rune->lv15_crr +=
-                  (rune->stats[i].value + rune->stats[i].grind);
-                break;
-            case CRD:
-                rune->current_crd +=
-                  (rune->stats[i].value + rune->stats[i].grind);
-                rune->lv12_crd +=
-                  (rune->stats[i].value + rune->stats[i].grind);
-                rune->lv15_crd +=
-                  (rune->stats[i].value + rune->stats[i].grind);
-                break;
-            case RES:
-                rune->current_res +=
-                  (rune->stats[i].value + rune->stats[i].grind);
-                rune->lv12_res +=
-                  (rune->stats[i].value + rune->stats[i].grind);
-                rune->lv15_res +=
-                  (rune->stats[i].value + rune->stats[i].grind);
-                break;
-            case ACC:
-                rune->current_acc +=
-                  (rune->stats[i].value + rune->stats[i].grind);
-                rune->lv12_acc +=
-                  (rune->stats[i].value + rune->stats[i].grind);
-                rune->lv15_acc +=
-                  (rune->stats[i].value + rune->stats[i].grind);
-                break;
-        }
-    }
-}
-
-/**
- * Gets a monster name from it's ID.
- *
- * @param[in] id Monster ID.
- * @param[out] name Monster name.
- */
-void get_monster_name(int id, char name[64]){
-    switch(id){
-        case 10102:
-            strcpy(name, "Fairy");
-            break;
-        case 10103:
-            strcpy(name, "Fairy");
-            break;
-        case 10104:
-            strcpy(name, "Fairy");
-            break;
-        case 10105:
-            strcpy(name, "Fairy");
-            break;
-        case 10111:
-            strcpy(name, "Elucia");
-            break;
-        case 10112:
-            strcpy(name, "Iselia");
-            break;
-        case 10113:
-            strcpy(name, "Aeilene");
-            break;
-        case 10114:
-            strcpy(name, "Neal");
-            break;
-        case 10115:
-            strcpy(name, "Sorin");
-            break;
-        case 10131:
-            strcpy(name, "Elucia");
-            break;
-        case 10132:
-            strcpy(name, "Iselia");
-            break;
-        case 10133:
-            strcpy(name, "Aeilene");
-            break;
-        case 10134:
-            strcpy(name, "Neal");
-            break;
-        case 10135:
-            strcpy(name, "Sorin");
-            break;
-        case 10201:
-            strcpy(name, "Imp");
-            break;
-        case 10202:
-            strcpy(name, "Imp");
-            break;
-        case 10203:
-            strcpy(name, "Imp");
-            break;
-        case 10204:
-            strcpy(name, "Imp");
-            break;
-        case 10205:
-            strcpy(name, "Imp");
-            break;
-        case 10211:
-            strcpy(name, "Fynn");
-            break;
-        case 10212:
-            strcpy(name, "Cogma");
-            break;
-        case 10213:
-            strcpy(name, "Ralph");
-            break;
-        case 10214:
-            strcpy(name, "Taru");
-            break;
-        case 10215:
-            strcpy(name, "Garok");
-            break;
-        case 10301:
-            strcpy(name, "Pixie");
-            break;
-        case 10302:
-            strcpy(name, "Pixie");
-            break;
-        case 10303:
-            strcpy(name, "Pixie");
-            break;
-        case 10304:
-            strcpy(name, "Pixie");
-            break;
-        case 10305:
-            strcpy(name, "Pixie");
-            break;
-        case 10311:
-            strcpy(name, "Kacey");
-            break;
-        case 10312:
-            strcpy(name, "Tatu");
-            break;
-        case 10313:
-            strcpy(name, "Shannon");
-            break;
-        case 10314:
-            strcpy(name, "Cheryl");
-            break;
-        case 10315:
-            strcpy(name, "Camaryn");
-            break;
-        case 10331:
-            strcpy(name, "Kacey");
-            break;
-        case 10332:
-            strcpy(name, "Tatu");
-            break;
-        case 10333:
-            strcpy(name, "Shannon");
-            break;
-        case 10334:
-            strcpy(name, "Cheryl");
-            break;
-        case 10335:
-            strcpy(name, "Camaryn");
-            break;
-        case 10401:
-            strcpy(name, "Yeti");
-            break;
-        case 10402:
-            strcpy(name, "Yeti");
-            break;
-        case 10403:
-            strcpy(name, "Yeti");
-            break;
-        case 10404:
-            strcpy(name, "Yeti");
-            break;
-        case 10405:
-            strcpy(name, "Yeti");
-            break;
-        case 10411:
-            strcpy(name, "Kunda");
-            break;
-        case 10412:
-            strcpy(name, "Tantra");
-            break;
-        case 10413:
-            strcpy(name, "Rakaja");
-            break;
-        case 10414:
-            strcpy(name, "Arkajan");
-            break;
-        case 10415:
-            strcpy(name, "Kumae");
-            break;
-        case 10501:
-            strcpy(name, "Harpy");
-            break;
-        case 10502:
-            strcpy(name, "Harpy");
-            break;
-        case 10503:
-            strcpy(name, "Harpy");
-            break;
-        case 10504:
-            strcpy(name, "Harpy");
-            break;
-        case 10505:
-            strcpy(name, "Harpy");
-            break;
-        case 10511:
-            strcpy(name, "Ramira");
-            break;
-        case 10512:
-            strcpy(name, "Lucasha");
-            break;
-        case 10513:
-            strcpy(name, "Prilea");
-            break;
-        case 10514:
-            strcpy(name, "Kabilla");
-            break;
-        case 10515:
-            strcpy(name, "Hellea");
-            break;
-        case 10601:
-            strcpy(name, "Hellhound");
-            break;
-        case 10602:
-            strcpy(name, "Hellhound");
-            break;
-        case 10603:
-            strcpy(name, "Hellhound");
-            break;
-        case 10604:
-            strcpy(name, "Hellhound");
-            break;
-        case 10605:
-            strcpy(name, "Hellhound");
-            break;
-        case 10611:
-            strcpy(name, "Tarq");
-            break;
-        case 10612:
-            strcpy(name, "Sieq");
-            break;
-        case 10613:
-            strcpy(name, "Gamir");
-            break;
-        case 10614:
-            strcpy(name, "Shamar");
-            break;
-        case 10615:
-            strcpy(name, "Shumar");
-            break;
-        case 10701:
-            strcpy(name, "Warbear");
-            break;
-        case 10702:
-            strcpy(name, "Warbear");
-            break;
-        case 10703:
-            strcpy(name, "Warbear");
-            break;
-        case 10704:
-            strcpy(name, "Warbear");
-            break;
-        case 10705:
-            strcpy(name, "Warbear");
-            break;
-        case 10711:
-            strcpy(name, "Dagora");
-            break;
-        case 10712:
-            strcpy(name, "Ursha");
-            break;
-        case 10713:
-            strcpy(name, "Ramagos");
-            break;
-        case 10714:
-            strcpy(name, "Lusha");
-            break;
-        case 10715:
-            strcpy(name, "Gorgo");
-            break;
-        case 10731:
-            strcpy(name, "Dagora");
-            break;
-        case 10732:
-            strcpy(name, "Ursha");
-            break;
-        case 10733:
-            strcpy(name, "Ramagos");
-            break;
-        case 10734:
-            strcpy(name, "Lusha");
-            break;
-        case 10735:
-            strcpy(name, "Gorgo");
-            break;
-        case 10801:
-            strcpy(name, "Elemental");
-            break;
-        case 10802:
-            strcpy(name, "Elemental");
-            break;
-        case 10803:
-            strcpy(name, "Elemental");
-            break;
-        case 10804:
-            strcpy(name, "Elemental");
-            break;
-        case 10805:
-            strcpy(name, "Elemental");
-            break;
-        case 10811:
-            strcpy(name, "Daharenos");
-            break;
-        case 10812:
-            strcpy(name, "Bremis");
-            break;
-        case 10813:
-            strcpy(name, "Taharus");
-            break;
-        case 10814:
-            strcpy(name, "Priz");
-            break;
-        case 10815:
-            strcpy(name, "Camules");
-            break;
-        case 10901:
-            strcpy(name, "Garuda");
-            break;
-        case 10902:
-            strcpy(name, "Garuda");
-            break;
-        case 10903:
-            strcpy(name, "Garuda");
-            break;
-        case 10904:
-            strcpy(name, "Garuda");
-            break;
-        case 10905:
-            strcpy(name, "Garuda");
-            break;
-        case 10911:
-            strcpy(name, "Konamiya");
-            break;
-        case 10912:
-            strcpy(name, "Cahule");
-            break;
-        case 10913:
-            strcpy(name, "Lindermen");
-            break;
-        case 10914:
-            strcpy(name, "Teon");
-            break;
-        case 10915:
-            strcpy(name, "Rizak");
-            break;
-        case 11001:
-            strcpy(name, "Inugami");
-            break;
-        case 11002:
-            strcpy(name, "Inugami");
-            break;
-        case 11003:
-            strcpy(name, "Inugami");
-            break;
-        case 11004:
-            strcpy(name, "Inugami");
-            break;
-        case 11005:
-            strcpy(name, "Inugami");
-            break;
-        case 11011:
-            strcpy(name, "Icaru");
-            break;
-        case 11012:
-            strcpy(name, "Raoq");
-            break;
-        case 11013:
-            strcpy(name, "Ramahan");
-            break;
-        case 11014:
-            strcpy(name, "Belladeon");
-            break;
-        case 11015:
-            strcpy(name, "Kro");
-            break;
-        case 11031:
-            strcpy(name, "Icaru");
-            break;
-        case 11032:
-            strcpy(name, "Raoq");
-            break;
-        case 11033:
-            strcpy(name, "Ramahan");
-            break;
-        case 11034:
-            strcpy(name, "Belladeon");
-            break;
-        case 11035:
-            strcpy(name, "Kro");
-            break;
-        case 11101:
-            strcpy(name, "Salamander");
-            break;
-        case 11102:
-            strcpy(name, "Salamander");
-            break;
-        case 11103:
-            strcpy(name, "Salamander");
-            break;
-        case 11104:
-            strcpy(name, "Salamander");
-            break;
-        case 11105:
-            strcpy(name, "Salamander");
-            break;
-        case 11111:
-            strcpy(name, "Kaimann");
-            break;
-        case 11112:
-            strcpy(name, "Krakdon");
-            break;
-        case 11113:
-            strcpy(name, "Lukan");
-            break;
-        case 11114:
-            strcpy(name, "Sharman");
-            break;
-        case 11115:
-            strcpy(name, "Decamaron");
-            break;
-        case 11201:
-            strcpy(name, "Nine-tailed Fox");
-            break;
-        case 11202:
-            strcpy(name, "Nine-tailed Fox");
-            break;
-        case 11203:
-            strcpy(name, "Nine-tailed Fox");
-            break;
-        case 11204:
-            strcpy(name, "Nine-tailed Fox");
-            break;
-        case 11205:
-            strcpy(name, "Nine-tailed Fox");
-            break;
-        case 11211:
-            strcpy(name, "Soha");
-            break;
-        case 11212:
-            strcpy(name, "Shihwa");
-            break;
-        case 11213:
-            strcpy(name, "Arang");
-            break;
-        case 11214:
-            strcpy(name, "Chamie");
-            break;
-        case 11215:
-            strcpy(name, "Kamiya");
-            break;
-        case 11223:
-            strcpy(name, "Imperfect Nine-tailed Fox");
-            break;
-        case 11301:
-            strcpy(name, "Serpent");
-            break;
-        case 11302:
-            strcpy(name, "Serpent");
-            break;
-        case 11303:
-            strcpy(name, "Serpent");
-            break;
-        case 11304:
-            strcpy(name, "Serpent");
-            break;
-        case 11305:
-            strcpy(name, "Serpent");
-            break;
-        case 11311:
-            strcpy(name, "Shailoq");
-            break;
-        case 11312:
-            strcpy(name, "Fao");
-            break;
-        case 11313:
-            strcpy(name, "Ermeda");
-            break;
-        case 11314:
-            strcpy(name, "Elpuria");
-            break;
-        case 11315:
-            strcpy(name, "Mantura");
-            break;
-        case 11401:
-            strcpy(name, "Golem");
-            break;
-        case 11402:
-            strcpy(name, "Golem");
-            break;
-        case 11403:
-            strcpy(name, "Golem");
-            break;
-        case 11404:
-            strcpy(name, "Golem");
-            break;
-        case 11405:
-            strcpy(name, "Golem");
-            break;
-        case 11411:
-            strcpy(name, "Kuhn");
-            break;
-        case 11412:
-            strcpy(name, "Kugo");
-            break;
-        case 11413:
-            strcpy(name, "Ragion");
-            break;
-        case 11414:
-            strcpy(name, "Groggo");
-            break;
-        case 11415:
-            strcpy(name, "Maggi");
-            break;
-        case 11501:
-            strcpy(name, "Griffon");
-            break;
-        case 11502:
-            strcpy(name, "Griffon");
-            break;
-        case 11503:
-            strcpy(name, "Griffon");
-            break;
-        case 11504:
-            strcpy(name, "Griffon");
-            break;
-        case 11505:
-            strcpy(name, "Griffon");
-            break;
-        case 11511:
-            strcpy(name, "Kahn");
-            break;
-        case 11512:
-            strcpy(name, "Spectra");
-            break;
-        case 11513:
-            strcpy(name, "Bernard");
-            break;
-        case 11514:
-            strcpy(name, "Shamann");
-            break;
-        case 11515:
-            strcpy(name, "Varus");
-            break;
-        case 11531:
-            strcpy(name, "Kahn");
-            break;
-        case 11532:
-            strcpy(name, "Spectra");
-            break;
-        case 11533:
-            strcpy(name, "Bernard");
-            break;
-        case 11534:
-            strcpy(name, "Shamann");
-            break;
-        case 11535:
-            strcpy(name, "Varus");
-            break;
-        case 11601:
-            strcpy(name, "Undine");
-            break;
-        case 11602:
-            strcpy(name, "Undine");
-            break;
-        case 11603:
-            strcpy(name, "Undine");
-            break;
-        case 11604:
-            strcpy(name, "Undine");
-            break;
-        case 11605:
-            strcpy(name, "Undine");
-            break;
-        case 11611:
-            strcpy(name, "Mikene");
-            break;
-        case 11612:
-            strcpy(name, "Atenai");
-            break;
-        case 11613:
-            strcpy(name, "Delphoi");
-            break;
-        case 11614:
-            strcpy(name, "Icasha");
-            break;
-        case 11615:
-            strcpy(name, "Tilasha");
-            break;
-        case 11621:
-            strcpy(name, "Imperfect Undine");
-            break;
-        case 11701:
-            strcpy(name, "Inferno");
-            break;
-        case 11702:
-            strcpy(name, "Inferno");
-            break;
-        case 11703:
-            strcpy(name, "Inferno");
-            break;
-        case 11704:
-            strcpy(name, "Inferno");
-            break;
-        case 11705:
-            strcpy(name, "Inferno");
-            break;
-        case 11711:
-            strcpy(name, "Purian");
-            break;
-        case 11712:
-            strcpy(name, "Tagaros");
-            break;
-        case 11713:
-            strcpy(name, "Anduril");
-            break;
-        case 11714:
-            strcpy(name, "Eludain");
-            break;
-        case 11715:
-            strcpy(name, "Drogan");
-            break;
-        case 11801:
-            strcpy(name, "Sylph");
-            break;
-        case 11802:
-            strcpy(name, "Sylph");
-            break;
-        case 11803:
-            strcpy(name, "Sylph");
-            break;
-        case 11804:
-            strcpy(name, "Sylph");
-            break;
-        case 11805:
-            strcpy(name, "Sylph");
-            break;
-        case 11811:
-            strcpy(name, "Tyron");
-            break;
-        case 11812:
-            strcpy(name, "Baretta");
-            break;
-        case 11813:
-            strcpy(name, "Shimitae");
-            break;
-        case 11814:
-            strcpy(name, "Eredas");
-            break;
-        case 11815:
-            strcpy(name, "Aschubel");
-            break;
-        case 11822:
-            strcpy(name, "Imperfect Sylph");
-            break;
-        case 11901:
-            strcpy(name, "Sylphid");
-            break;
-        case 11902:
-            strcpy(name, "Sylphid");
-            break;
-        case 11903:
-            strcpy(name, "Sylphid");
-            break;
-        case 11904:
-            strcpy(name, "Sylphid");
-            break;
-        case 11905:
-            strcpy(name, "Sylphid");
-            break;
-        case 11911:
-            strcpy(name, "Lumirecia");
-            break;
-        case 11912:
-            strcpy(name, "Fria");
-            break;
-        case 11913:
-            strcpy(name, "Acasis");
-            break;
-        case 11914:
-            strcpy(name, "Mihael");
-            break;
-        case 11915:
-            strcpy(name, "Icares");
-            break;
-        case 12001:
-            strcpy(name, "High Elemental");
-            break;
-        case 12002:
-            strcpy(name, "High Elemental");
-            break;
-        case 12003:
-            strcpy(name, "High Elemental");
-            break;
-        case 12004:
-            strcpy(name, "High Elemental");
-            break;
-        case 12005:
-            strcpy(name, "High Elemental");
-            break;
-        case 12011:
-            strcpy(name, "Ellena");
-            break;
-        case 12012:
-            strcpy(name, "Kahli");
-            break;
-        case 12013:
-            strcpy(name, "Moria");
-            break;
-        case 12014:
-            strcpy(name, "Shren");
-            break;
-        case 12015:
-            strcpy(name, "Jumaline");
-            break;
-        case 12101:
-            strcpy(name, "Harpu");
-            break;
-        case 12102:
-            strcpy(name, "Harpu");
-            break;
-        case 12103:
-            strcpy(name, "Harpu");
-            break;
-        case 12104:
-            strcpy(name, "Harpu");
-            break;
-        case 12105:
-            strcpy(name, "Harpu");
-            break;
-        case 12111:
-            strcpy(name, "Sisroo");
-            break;
-        case 12112:
-            strcpy(name, "Colleen");
-            break;
-        case 12113:
-            strcpy(name, "Seal");
-            break;
-        case 12114:
-            strcpy(name, "Sia");
-            break;
-        case 12115:
-            strcpy(name, "Seren");
-            break;
-        case 12201:
-            strcpy(name, "Slime");
-            break;
-        case 12202:
-            strcpy(name, "Slime");
-            break;
-        case 12203:
-            strcpy(name, "Slime");
-            break;
-        case 12301:
-            strcpy(name, "Forest Keeper");
-            break;
-        case 12302:
-            strcpy(name, "Forest Keeper");
-            break;
-        case 12303:
-            strcpy(name, "Forest Keeper");
-            break;
-        case 12401:
-            strcpy(name, "Mushroom");
-            break;
-        case 12402:
-            strcpy(name, "Mushroom");
-            break;
-        case 12403:
-            strcpy(name, "Mushroom");
-            break;
-        case 12501:
-            strcpy(name, "Maned Boar");
-            break;
-        case 12502:
-            strcpy(name, "Maned Boar");
-            break;
-        case 12503:
-            strcpy(name, "Maned Boar");
-            break;
-        case 12601:
-            strcpy(name, "Monster Flower");
-            break;
-        case 12602:
-            strcpy(name, "Monster Flower");
-            break;
-        case 12603:
-            strcpy(name, "Monster Flower");
-            break;
-        case 12605:
-            strcpy(name, "Monster Flower");
-            break;
-        case 12701:
-            strcpy(name, "Ghost");
-            break;
-        case 12702:
-            strcpy(name, "Ghost");
-            break;
-        case 12703:
-            strcpy(name, "Ghost");
-            break;
-        case 12705:
-            strcpy(name, "Ghost");
-            break;
-        case 12801:
-            strcpy(name, "Low Elemental");
-            break;
-        case 12802:
-            strcpy(name, "Low Elemental");
-            break;
-        case 12803:
-            strcpy(name, "Low Elemental");
-            break;
-        case 12804:
-            strcpy(name, "Low Elemental");
-            break;
-        case 12805:
-            strcpy(name, "Low Elemental");
-            break;
-        case 12811:
-            strcpy(name, "Tigresse");
-            break;
-        case 12812:
-            strcpy(name, "Lamor");
-            break;
-        case 12813:
-            strcpy(name, "Samour");
-            break;
-        case 12814:
-            strcpy(name, "Varis");
-            break;
-        case 12815:
-            strcpy(name, "Havana");
-            break;
-        case 12901:
-            strcpy(name, "Mimick");
-            break;
-        case 12902:
-            strcpy(name, "Mimick");
-            break;
-        case 12903:
-            strcpy(name, "Mimick");
-            break;
-        case 12905:
-            strcpy(name, "Mimick");
-            break;
-        case 13001:
-            strcpy(name, "Horned Frog");
-            break;
-        case 13002:
-            strcpy(name, "Horned Frog");
-            break;
-        case 13003:
-            strcpy(name, "Horned Frog");
-            break;
-        case 13005:
-            strcpy(name, "Horned Frog");
-            break;
-        case 13101:
-            strcpy(name, "Sandman");
-            break;
-        case 13102:
-            strcpy(name, "Sandman");
-            break;
-        case 13103:
-            strcpy(name, "Sandman");
-            break;
-        case 13105:
-            strcpy(name, "Sandman");
-            break;
-        case 13201:
-            strcpy(name, "Howl");
-            break;
-        case 13202:
-            strcpy(name, "Howl");
-            break;
-        case 13203:
-            strcpy(name, "Howl");
-            break;
-        case 13204:
-            strcpy(name, "Howl");
-            break;
-        case 13205:
-            strcpy(name, "Howl");
-            break;
-        case 13211:
-            strcpy(name, "Lulu");
-            break;
-        case 13212:
-            strcpy(name, "Lala");
-            break;
-        case 13213:
-            strcpy(name, "Chichi");
-            break;
-        case 13214:
-            strcpy(name, "Shushu");
-            break;
-        case 13215:
-            strcpy(name, "Chacha");
-            break;
-        case 13301:
-            strcpy(name, "Succubus");
-            break;
-        case 13302:
-            strcpy(name, "Succubus");
-            break;
-        case 13303:
-            strcpy(name, "Succubus");
-            break;
-        case 13304:
-            strcpy(name, "Succubus");
-            break;
-        case 13305:
-            strcpy(name, "Succubus");
-            break;
-        case 13311:
-            strcpy(name, "Izaria");
-            break;
-        case 13312:
-            strcpy(name, "Akia");
-            break;
-        case 13313:
-            strcpy(name, "Selena");
-            break;
-        case 13314:
-            strcpy(name, "Aria");
-            break;
-        case 13315:
-            strcpy(name, "Isael");
-            break;
-        case 13322:
-            strcpy(name, "Imperfect Succubus");
-            break;
-        case 13401:
-            strcpy(name, "Joker");
-            break;
-        case 13402:
-            strcpy(name, "Joker");
-            break;
-        case 13403:
-            strcpy(name, "Joker");
-            break;
-        case 13404:
-            strcpy(name, "Joker");
-            break;
-        case 13405:
-            strcpy(name, "Joker");
-            break;
-        case 13411:
-            strcpy(name, "Sian");
-            break;
-        case 13412:
-            strcpy(name, "Jojo");
-            break;
-        case 13413:
-            strcpy(name, "Lushen");
-            break;
-        case 13414:
-            strcpy(name, "Figaro");
-            break;
-        case 13415:
-            strcpy(name, "Liebli");
-            break;
-        case 13422:
-            strcpy(name, "Imperfect Joker");
-            break;
-        case 13501:
-            strcpy(name, "Ninja");
-            break;
-        case 13502:
-            strcpy(name, "Ninja");
-            break;
-        case 13503:
-            strcpy(name, "Ninja");
-            break;
-        case 13504:
-            strcpy(name, "Ninja");
-            break;
-        case 13505:
-            strcpy(name, "Ninja");
-            break;
-        case 13511:
-            strcpy(name, "Susano");
-            break;
-        case 13512:
-            strcpy(name, "Garo");
-            break;
-        case 13513:
-            strcpy(name, "Orochi");
-            break;
-        case 13514:
-            strcpy(name, "Gin");
-            break;
-        case 13515:
-            strcpy(name, "Han");
-            break;
-        case 13521:
-            strcpy(name, "Imperfect Ninja");
-            break;
-        case 13601:
-            strcpy(name, "Surprise Box");
-            break;
-        case 13602:
-            strcpy(name, "Surprise Box");
-            break;
-        case 13603:
-            strcpy(name, "Surprise Box");
-            break;
-        case 13604:
-            strcpy(name, "Surprise Box");
-            break;
-        case 13605:
-            strcpy(name, "Surprise Box");
-            break;
-        case 13701:
-            strcpy(name, "Bearman");
-            break;
-        case 13702:
-            strcpy(name, "Bearman");
-            break;
-        case 13703:
-            strcpy(name, "Bearman");
-            break;
-        case 13704:
-            strcpy(name, "Bearman");
-            break;
-        case 13705:
-            strcpy(name, "Bearman");
-            break;
-        case 13711:
-            strcpy(name, "Gruda");
-            break;
-        case 13712:
-            strcpy(name, "Kungen");
-            break;
-        case 13713:
-            strcpy(name, "Dagorr");
-            break;
-        case 13714:
-            strcpy(name, "Ahman");
-            break;
-        case 13715:
-            strcpy(name, "Haken");
-            break;
-        case 13801:
-            strcpy(name, "Valkyrja");
-            break;
-        case 13802:
-            strcpy(name, "Valkyrja");
-            break;
-        case 13803:
-            strcpy(name, "Valkyrja");
-            break;
-        case 13804:
-            strcpy(name, "Valkyrja");
-            break;
-        case 13805:
-            strcpy(name, "Valkyrja");
-            break;
-        case 13811:
-            strcpy(name, "Camilla");
-            break;
-        case 13812:
-            strcpy(name, "Vanessa");
-            break;
-        case 13813:
-            strcpy(name, "Katarina");
-            break;
-        case 13814:
-            strcpy(name, "Akroma");
-            break;
-        case 13815:
-            strcpy(name, "Trinity");
-            break;
-        case 13901:
-            strcpy(name, "Pierret");
-            break;
-        case 13902:
-            strcpy(name, "Pierret");
-            break;
-        case 13903:
-            strcpy(name, "Pierret");
-            break;
-        case 13904:
-            strcpy(name, "Pierret");
-            break;
-        case 13905:
-            strcpy(name, "Pierret");
-            break;
-        case 13911:
-            strcpy(name, "Julie");
-            break;
-        case 13912:
-            strcpy(name, "Clara");
-            break;
-        case 13913:
-            strcpy(name, "Sophia");
-            break;
-        case 13914:
-            strcpy(name, "Eva");
-            break;
-        case 13915:
-            strcpy(name, "Luna");
-            break;
-        case 14001:
-            strcpy(name, "Werewolf");
-            break;
-        case 14002:
-            strcpy(name, "Werewolf");
-            break;
-        case 14003:
-            strcpy(name, "Werewolf");
-            break;
-        case 14004:
-            strcpy(name, "Werewolf");
-            break;
-        case 14005:
-            strcpy(name, "Werewolf");
-            break;
-        case 14011:
-            strcpy(name, "Vigor");
-            break;
-        case 14012:
-            strcpy(name, "Garoche");
-            break;
-        case 14013:
-            strcpy(name, "Shakan");
-            break;
-        case 14014:
-            strcpy(name, "Eshir");
-            break;
-        case 14015:
-            strcpy(name, "Jultan");
-            break;
-        case 14031:
-            strcpy(name, "Vigor");
-            break;
-        case 14032:
-            strcpy(name, "Garoche");
-            break;
-        case 14033:
-            strcpy(name, "Shakan");
-            break;
-        case 14034:
-            strcpy(name, "Eshir");
-            break;
-        case 14035:
-            strcpy(name, "Jultan");
-            break;
-        case 14101:
-            strcpy(name, "Phantom Thief");
-            break;
-        case 14102:
-            strcpy(name, "Phantom Thief");
-            break;
-        case 14103:
-            strcpy(name, "Phantom Thief");
-            break;
-        case 14104:
-            strcpy(name, "Phantom Thief");
-            break;
-        case 14105:
-            strcpy(name, "Phantom Thief");
-            break;
-        case 14111:
-            strcpy(name, "Luer");
-            break;
-        case 14112:
-            strcpy(name, "Jean");
-            break;
-        case 14113:
-            strcpy(name, "Julien");
-            break;
-        case 14114:
-            strcpy(name, "Louis");
-            break;
-        case 14115:
-            strcpy(name, "Guillaume");
-            break;
-        case 14201:
-            strcpy(name, "Angelmon");
-            break;
-        case 14202:
-            strcpy(name, "Angelmon");
-            break;
-        case 14203:
-            strcpy(name, "Angelmon");
-            break;
-        case 14204:
-            strcpy(name, "Angelmon");
-            break;
-        case 14205:
-            strcpy(name, "Angelmon");
-            break;
-        case 14211:
-            strcpy(name, "Blue Angelmon");
-            break;
-        case 14212:
-            strcpy(name, "Red Angelmon");
-            break;
-        case 14213:
-            strcpy(name, "Gold Angelmon");
-            break;
-        case 14214:
-            strcpy(name, "White Angelmon");
-            break;
-        case 14215:
-            strcpy(name, "Dark Angelmon");
-            break;
-        case 14314:
-            strcpy(name, "Rainbowmon");
-            break;
-        case 14401:
-            strcpy(name, "Dragon");
-            break;
-        case 14402:
-            strcpy(name, "Dragon");
-            break;
-        case 14403:
-            strcpy(name, "Dragon");
-            break;
-        case 14404:
-            strcpy(name, "Dragon");
-            break;
-        case 14405:
-            strcpy(name, "Dragon");
-            break;
-        case 14411:
-            strcpy(name, "Verad");
-            break;
-        case 14412:
-            strcpy(name, "Zaiross");
-            break;
-        case 14413:
-            strcpy(name, "Jamire");
-            break;
-        case 14414:
-            strcpy(name, "Zerath");
-            break;
-        case 14415:
-            strcpy(name, "Grogen");
-            break;
-        case 14501:
-            strcpy(name, "Phoenix");
-            break;
-        case 14502:
-            strcpy(name, "Phoenix");
-            break;
-        case 14503:
-            strcpy(name, "Phoenix");
-            break;
-        case 14504:
-            strcpy(name, "Phoenix");
-            break;
-        case 14505:
-            strcpy(name, "Phoenix");
-            break;
-        case 14511:
-            strcpy(name, "Sigmarus");
-            break;
-        case 14512:
-            strcpy(name, "Perna");
-            break;
-        case 14513:
-            strcpy(name, "Teshar");
-            break;
-        case 14514:
-            strcpy(name, "Eludia");
-            break;
-        case 14515:
-            strcpy(name, "Jaara");
-            break;
-        case 14601:
-            strcpy(name, "Chimera");
-            break;
-        case 14602:
-            strcpy(name, "Chimera");
-            break;
-        case 14603:
-            strcpy(name, "Chimera");
-            break;
-        case 14604:
-            strcpy(name, "Chimera");
-            break;
-        case 14605:
-            strcpy(name, "Chimera");
-            break;
-        case 14611:
-            strcpy(name, "Taor");
-            break;
-        case 14612:
-            strcpy(name, "Rakan");
-            break;
-        case 14613:
-            strcpy(name, "Lagmaron");
-            break;
-        case 14614:
-            strcpy(name, "Shan");
-            break;
-        case 14615:
-            strcpy(name, "Zeratu");
-            break;
-        case 14701:
-            strcpy(name, "Vampire");
-            break;
-        case 14702:
-            strcpy(name, "Vampire");
-            break;
-        case 14703:
-            strcpy(name, "Vampire");
-            break;
-        case 14704:
-            strcpy(name, "Vampire");
-            break;
-        case 14705:
-            strcpy(name, "Vampire");
-            break;
-        case 14711:
-            strcpy(name, "Liesel");
-            break;
-        case 14712:
-            strcpy(name, "Verdehile");
-            break;
-        case 14713:
-            strcpy(name, "Argen");
-            break;
-        case 14714:
-            strcpy(name, "Julianne");
-            break;
-        case 14715:
-            strcpy(name, "Cadiz");
-            break;
-        case 14722:
-            strcpy(name, "Imperfect Vampire");
-            break;
-        case 14723:
-            strcpy(name, "Imperfect Vampire");
-            break;
-        case 14801:
-            strcpy(name, "Viking");
-            break;
-        case 14802:
-            strcpy(name, "Viking");
-            break;
-        case 14803:
-            strcpy(name, "Viking");
-            break;
-        case 14804:
-            strcpy(name, "Viking");
-            break;
-        case 14805:
-            strcpy(name, "Viking");
-            break;
-        case 14811:
-            strcpy(name, "Huga");
-            break;
-        case 14812:
-            strcpy(name, "Geoffrey");
-            break;
-        case 14813:
-            strcpy(name, "Walter");
-            break;
-        case 14814:
-            strcpy(name, "Jansson");
-            break;
-        case 14815:
-            strcpy(name, "Janssen");
-            break;
-        case 14901:
-            strcpy(name, "Amazon");
-            break;
-        case 14902:
-            strcpy(name, "Amazon");
-            break;
-        case 14903:
-            strcpy(name, "Amazon");
-            break;
-        case 14904:
-            strcpy(name, "Amazon");
-            break;
-        case 14905:
-            strcpy(name, "Amazon");
-            break;
-        case 14911:
-            strcpy(name, "Ellin");
-            break;
-        case 14912:
-            strcpy(name, "Ceres");
-            break;
-        case 14913:
-            strcpy(name, "Hina");
-            break;
-        case 14914:
-            strcpy(name, "Lyn");
-            break;
-        case 14915:
-            strcpy(name, "Mara");
-            break;
-        case 15001:
-            strcpy(name, "Martial Cat");
-            break;
-        case 15002:
-            strcpy(name, "Martial Cat");
-            break;
-        case 15003:
-            strcpy(name, "Martial Cat");
-            break;
-        case 15004:
-            strcpy(name, "Martial Cat");
-            break;
-        case 15005:
-            strcpy(name, "Martial Cat");
-            break;
-        case 15011:
-            strcpy(name, "Mina");
-            break;
-        case 15012:
-            strcpy(name, "Mei");
-            break;
-        case 15013:
-            strcpy(name, "Naomi");
-            break;
-        case 15014:
-            strcpy(name, "Xiao Ling");
-            break;
-        case 15015:
-            strcpy(name, "Miho");
-            break;
-        case 15031:
-            strcpy(name, "Mina");
-            break;
-        case 15032:
-            strcpy(name, "Mei");
-            break;
-        case 15033:
-            strcpy(name, "Naomi");
-            break;
-        case 15034:
-            strcpy(name, "Xiao Ling");
-            break;
-        case 15035:
-            strcpy(name, "Miho");
-            break;
-        case 15105:
-            strcpy(name, "Devilmon");
-            break;
-        case 15201:
-            strcpy(name, "Vagabond");
-            break;
-        case 15202:
-            strcpy(name, "Vagabond");
-            break;
-        case 15203:
-            strcpy(name, "Vagabond");
-            break;
-        case 15204:
-            strcpy(name, "Vagabond");
-            break;
-        case 15205:
-            strcpy(name, "Vagabond");
-            break;
-        case 15211:
-            strcpy(name, "Allen");
-            break;
-        case 15212:
-            strcpy(name, "Kai'en");
-            break;
-        case 15213:
-            strcpy(name, "Roid");
-            break;
-        case 15214:
-            strcpy(name, "Darion");
-            break;
-        case 15215:
-            strcpy(name, "Jubelle");
-            break;
-        case 15301:
-            strcpy(name, "Epikion Priest");
-            break;
-        case 15302:
-            strcpy(name, "Epikion Priest");
-            break;
-        case 15303:
-            strcpy(name, "Epikion Priest");
-            break;
-        case 15304:
-            strcpy(name, "Epikion Priest");
-            break;
-        case 15305:
-            strcpy(name, "Epikion Priest");
-            break;
-        case 15311:
-            strcpy(name, "Rina");
-            break;
-        case 15312:
-            strcpy(name, "Chloe");
-            break;
-        case 15313:
-            strcpy(name, "Michelle");
-            break;
-        case 15314:
-            strcpy(name, "Iona");
-            break;
-        case 15315:
-            strcpy(name, "Rasheed");
-            break;
-        case 15401:
-            strcpy(name, "Magical Archer");
-            break;
-        case 15402:
-            strcpy(name, "Magical Archer");
-            break;
-        case 15403:
-            strcpy(name, "Magical Archer");
-            break;
-        case 15404:
-            strcpy(name, "Magical Archer");
-            break;
-        case 15405:
-            strcpy(name, "Magical Archer");
-            break;
-        case 15411:
-            strcpy(name, "Sharron");
-            break;
-        case 15412:
-            strcpy(name, "Cassandra");
-            break;
-        case 15413:
-            strcpy(name, "Ardella");
-            break;
-        case 15414:
-            strcpy(name, "Chris");
-            break;
-        case 15415:
-            strcpy(name, "Bethony");
-            break;
-        case 15501:
-            strcpy(name, "Rakshasa");
-            break;
-        case 15502:
-            strcpy(name, "Rakshasa");
-            break;
-        case 15503:
-            strcpy(name, "Rakshasa");
-            break;
-        case 15504:
-            strcpy(name, "Rakshasa");
-            break;
-        case 15505:
-            strcpy(name, "Rakshasa");
-            break;
-        case 15511:
-            strcpy(name, "Su");
-            break;
-        case 15512:
-            strcpy(name, "Hwa");
-            break;
-        case 15513:
-            strcpy(name, "Yen");
-            break;
-        case 15514:
-            strcpy(name, "Pang");
-            break;
-        case 15515:
-            strcpy(name, "Ran");
-            break;
-        case 15601:
-            strcpy(name, "Bounty Hunter");
-            break;
-        case 15602:
-            strcpy(name, "Bounty Hunter");
-            break;
-        case 15603:
-            strcpy(name, "Bounty Hunter");
-            break;
-        case 15604:
-            strcpy(name, "Bounty Hunter");
-            break;
-        case 15605:
-            strcpy(name, "Bounty Hunter");
-            break;
-        case 15611:
-            strcpy(name, "Wayne");
-            break;
-        case 15612:
-            strcpy(name, "Randy");
-            break;
-        case 15613:
-            strcpy(name, "Roger");
-            break;
-        case 15614:
-            strcpy(name, "Walkers");
-            break;
-        case 15615:
-            strcpy(name, "Jamie");
-            break;
-        case 15701:
-            strcpy(name, "Oracle");
-            break;
-        case 15702:
-            strcpy(name, "Oracle");
-            break;
-        case 15703:
-            strcpy(name, "Oracle");
-            break;
-        case 15704:
-            strcpy(name, "Oracle");
-            break;
-        case 15705:
-            strcpy(name, "Oracle");
-            break;
-        case 15711:
-            strcpy(name, "Praha");
-            break;
-        case 15712:
-            strcpy(name, "Juno");
-            break;
-        case 15713:
-            strcpy(name, "Seara");
-            break;
-        case 15714:
-            strcpy(name, "Laima");
-            break;
-        case 15715:
-            strcpy(name, "Giana");
-            break;
-        case 15801:
-            strcpy(name, "Imp Champion");
-            break;
-        case 15802:
-            strcpy(name, "Imp Champion");
-            break;
-        case 15803:
-            strcpy(name, "Imp Champion");
-            break;
-        case 15804:
-            strcpy(name, "Imp Champion");
-            break;
-        case 15805:
-            strcpy(name, "Imp Champion");
-            break;
-        case 15811:
-            strcpy(name, "Yaku");
-            break;
-        case 15812:
-            strcpy(name, "Fairo");
-            break;
-        case 15813:
-            strcpy(name, "Pigma");
-            break;
-        case 15814:
-            strcpy(name, "Shaffron");
-            break;
-        case 15815:
-            strcpy(name, "Loque");
-            break;
-        case 15901:
-            strcpy(name, "Mystic Witch");
-            break;
-        case 15902:
-            strcpy(name, "Mystic Witch");
-            break;
-        case 15903:
-            strcpy(name, "Mystic Witch");
-            break;
-        case 15904:
-            strcpy(name, "Mystic Witch");
-            break;
-        case 15905:
-            strcpy(name, "Mystic Witch");
-            break;
-        case 15911:
-            strcpy(name, "Megan");
-            break;
-        case 15912:
-            strcpy(name, "Rebecca");
-            break;
-        case 15913:
-            strcpy(name, "Silia");
-            break;
-        case 15914:
-            strcpy(name, "Linda");
-            break;
-        case 15915:
-            strcpy(name, "Gina");
-            break;
-        case 16001:
-            strcpy(name, "Grim Reaper");
-            break;
-        case 16002:
-            strcpy(name, "Grim Reaper");
-            break;
-        case 16003:
-            strcpy(name, "Grim Reaper");
-            break;
-        case 16004:
-            strcpy(name, "Grim Reaper");
-            break;
-        case 16005:
-            strcpy(name, "Grim Reaper");
-            break;
-        case 16011:
-            strcpy(name, "Hemos");
-            break;
-        case 16012:
-            strcpy(name, "Sath");
-            break;
-        case 16013:
-            strcpy(name, "Hiva");
-            break;
-        case 16014:
-            strcpy(name, "Prom");
-            break;
-        case 16015:
-            strcpy(name, "Thrain");
-            break;
-        case 16101:
-            strcpy(name, "Occult Girl");
-            break;
-        case 16102:
-            strcpy(name, "Occult Girl");
-            break;
-        case 16103:
-            strcpy(name, "Occult Girl");
-            break;
-        case 16104:
-            strcpy(name, "Occult Girl");
-            break;
-        case 16105:
-            strcpy(name, "Occult Girl");
-            break;
-        case 16111:
-            strcpy(name, "Anavel");
-            break;
-        case 16112:
-            strcpy(name, "Rica");
-            break;
-        case 16113:
-            strcpy(name, "Charlotte");
-            break;
-        case 16114:
-            strcpy(name, "Lora");
-            break;
-        case 16115:
-            strcpy(name, "Nicki");
-            break;
-        case 16201:
-            strcpy(name, "Death Knight");
-            break;
-        case 16202:
-            strcpy(name, "Death Knight");
-            break;
-        case 16203:
-            strcpy(name, "Death Knight");
-            break;
-        case 16204:
-            strcpy(name, "Death Knight");
-            break;
-        case 16205:
-            strcpy(name, "Death Knight");
-            break;
-        case 16211:
-            strcpy(name, "Fedora");
-            break;
-        case 16212:
-            strcpy(name, "Arnold");
-            break;
-        case 16213:
-            strcpy(name, "Briand");
-            break;
-        case 16214:
-            strcpy(name, "Conrad");
-            break;
-        case 16215:
-            strcpy(name, "Dias");
-            break;
-        case 16301:
-            strcpy(name, "Lich");
-            break;
-        case 16302:
-            strcpy(name, "Lich");
-            break;
-        case 16303:
-            strcpy(name, "Lich");
-            break;
-        case 16304:
-            strcpy(name, "Lich");
-            break;
-        case 16305:
-            strcpy(name, "Lich");
-            break;
-        case 16311:
-            strcpy(name, "Rigel");
-            break;
-        case 16312:
-            strcpy(name, "Antares");
-            break;
-        case 16313:
-            strcpy(name, "Fuco");
-            break;
-        case 16314:
-            strcpy(name, "Halphas");
-            break;
-        case 16315:
-            strcpy(name, "Grego");
-            break;
-        case 16401:
-            strcpy(name, "Skull Soldier");
-            break;
-        case 16402:
-            strcpy(name, "Skull Soldier");
-            break;
-        case 16403:
-            strcpy(name, "Skull Soldier");
-            break;
-        case 16501:
-            strcpy(name, "Living Armor");
-            break;
-        case 16502:
-            strcpy(name, "Living Armor");
-            break;
-        case 16503:
-            strcpy(name, "Living Armor");
-            break;
-        case 16504:
-            strcpy(name, "Living Armor");
-            break;
-        case 16505:
-            strcpy(name, "Living Armor");
-            break;
-        case 16511:
-            strcpy(name, "Nickel");
-            break;
-        case 16512:
-            strcpy(name, "Iron");
-            break;
-        case 16513:
-            strcpy(name, "Copper");
-            break;
-        case 16514:
-            strcpy(name, "Silver");
-            break;
-        case 16515:
-            strcpy(name, "Zinc");
-            break;
-        case 16601:
-            strcpy(name, "Dragon Knight");
-            break;
-        case 16602:
-            strcpy(name, "Dragon Knight");
-            break;
-        case 16603:
-            strcpy(name, "Dragon Knight");
-            break;
-        case 16604:
-            strcpy(name, "Dragon Knight");
-            break;
-        case 16605:
-            strcpy(name, "Dragon Knight");
-            break;
-        case 16611:
-            strcpy(name, "Chow");
-            break;
-        case 16612:
-            strcpy(name, "Laika");
-            break;
-        case 16613:
-            strcpy(name, "Leo");
-            break;
-        case 16614:
-            strcpy(name, "Jager");
-            break;
-        case 16615:
-            strcpy(name, "Ragdoll");
-            break;
-        case 16704:
-            strcpy(name, "Magical Archer");
-            break;
-        case 16714:
-            strcpy(name, "Fami");
-            break;
-        case 16801:
-            strcpy(name, "Monkey King");
-            break;
-        case 16802:
-            strcpy(name, "Monkey King");
-            break;
-        case 16803:
-            strcpy(name, "Monkey King");
-            break;
-        case 16804:
-            strcpy(name, "Monkey King");
-            break;
-        case 16805:
-            strcpy(name, "Monkey King");
-            break;
-        case 16811:
-            strcpy(name, "Shi Hou");
-            break;
-        case 16812:
-            strcpy(name, "Mei Hou Wang");
-            break;
-        case 16813:
-            strcpy(name, "Xing Zhe");
-            break;
-        case 16814:
-            strcpy(name, "Qitian Dasheng");
-            break;
-        case 16815:
-            strcpy(name, "Son Zhang Lao");
-            break;
-        case 16901:
-            strcpy(name, "Samurai");
-            break;
-        case 16902:
-            strcpy(name, "Samurai");
-            break;
-        case 16903:
-            strcpy(name, "Samurai");
-            break;
-        case 16904:
-            strcpy(name, "Samurai");
-            break;
-        case 16905:
-            strcpy(name, "Samurai");
-            break;
-        case 16911:
-            strcpy(name, "Kaz");
-            break;
-        case 16912:
-            strcpy(name, "Jun");
-            break;
-        case 16913:
-            strcpy(name, "Kaito");
-            break;
-        case 16914:
-            strcpy(name, "Tosi");
-            break;
-        case 16915:
-            strcpy(name, "Sige");
-            break;
-        case 16921:
-            strcpy(name, "Imperfect Samurai");
-            break;
-        case 17001:
-            strcpy(name, "Archangel");
-            break;
-        case 17002:
-            strcpy(name, "Archangel");
-            break;
-        case 17003:
-            strcpy(name, "Archangel");
-            break;
-        case 17004:
-            strcpy(name, "Archangel");
-            break;
-        case 17005:
-            strcpy(name, "Archangel");
-            break;
-        case 17011:
-            strcpy(name, "Ariel");
-            break;
-        case 17012:
-            strcpy(name, "Velajuel");
-            break;
-        case 17013:
-            strcpy(name, "Eladriel");
-            break;
-        case 17014:
-            strcpy(name, "Artamiel");
-            break;
-        case 17015:
-            strcpy(name, "Fermion");
-            break;
-        case 17101:
-            strcpy(name, "Ifrit");
-            break;
-        case 17102:
-            strcpy(name, "Ifrit");
-            break;
-        case 17103:
-            strcpy(name, "Ifrit");
-            break;
-        case 17104:
-            strcpy(name, "Ifrit");
-            break;
-        case 17105:
-            strcpy(name, "Ifrit");
-            break;
-        case 17111:
-            strcpy(name, "Theomars");
-            break;
-        case 17112:
-            strcpy(name, "Tesarion");
-            break;
-        case 17113:
-            strcpy(name, "Akhamamir");
-            break;
-        case 17114:
-            strcpy(name, "Elsharion");
-            break;
-        case 17115:
-            strcpy(name, "Veromos");
-            break;
-        case 17201:
-            strcpy(name, "Drunken Master");
-            break;
-        case 17202:
-            strcpy(name, "Drunken Master");
-            break;
-        case 17203:
-            strcpy(name, "Drunken Master");
-            break;
-        case 17204:
-            strcpy(name, "Drunken Master");
-            break;
-        case 17205:
-            strcpy(name, "Drunken Master");
-            break;
-        case 17211:
-            strcpy(name, "Mao");
-            break;
-        case 17212:
-            strcpy(name, "Xiao Chun");
-            break;
-        case 17213:
-            strcpy(name, "Huan");
-            break;
-        case 17214:
-            strcpy(name, "Tien Qin");
-            break;
-        case 17215:
-            strcpy(name, "Wei Shin");
-            break;
-        case 17301:
-            strcpy(name, "Kung Fu Girl");
-            break;
-        case 17302:
-            strcpy(name, "Kung Fu Girl");
-            break;
-        case 17303:
-            strcpy(name, "Kung Fu Girl");
-            break;
-        case 17304:
-            strcpy(name, "Kung Fu Girl");
-            break;
-        case 17305:
-            strcpy(name, "Kung Fu Girl");
-            break;
-        case 17311:
-            strcpy(name, "Xiao Lin");
-            break;
-        case 17312:
-            strcpy(name, "Hong Hua");
-            break;
-        case 17313:
-            strcpy(name, "Ling Ling");
-            break;
-        case 17314:
-            strcpy(name, "Liu Mei");
-            break;
-        case 17315:
-            strcpy(name, "Fei");
-            break;
-        case 17323:
-            strcpy(name, "Imperfect Kung Fu Girl");
-            break;
-        case 17401:
-            strcpy(name, "Beast Monk");
-            break;
-        case 17402:
-            strcpy(name, "Beast Monk");
-            break;
-        case 17403:
-            strcpy(name, "Beast Monk");
-            break;
-        case 17404:
-            strcpy(name, "Beast Monk");
-            break;
-        case 17405:
-            strcpy(name, "Beast Monk");
-            break;
-        case 17411:
-            strcpy(name, "Chandra");
-            break;
-        case 17412:
-            strcpy(name, "Kumar");
-            break;
-        case 17413:
-            strcpy(name, "Ritesh");
-            break;
-        case 17414:
-            strcpy(name, "Shazam");
-            break;
-        case 17415:
-            strcpy(name, "Rahul");
-            break;
-        case 17501:
-            strcpy(name, "Mischievous Bat");
-            break;
-        case 17502:
-            strcpy(name, "Mischievous Bat");
-            break;
-        case 17503:
-            strcpy(name, "Mischievous Bat");
-            break;
-        case 17601:
-            strcpy(name, "Battle Scorpion");
-            break;
-        case 17602:
-            strcpy(name, "Battle Scorpion");
-            break;
-        case 17603:
-            strcpy(name, "Battle Scorpion");
-            break;
-        case 17701:
-            strcpy(name, "Minotauros");
-            break;
-        case 17702:
-            strcpy(name, "Minotauros");
-            break;
-        case 17703:
-            strcpy(name, "Minotauros");
-            break;
-        case 17704:
-            strcpy(name, "Minotauros");
-            break;
-        case 17705:
-            strcpy(name, "Minotauros");
-            break;
-        case 17711:
-            strcpy(name, "Urtau");
-            break;
-        case 17712:
-            strcpy(name, "Burentau");
-            break;
-        case 17713:
-            strcpy(name, "Eintau");
-            break;
-        case 17714:
-            strcpy(name, "Grotau");
-            break;
-        case 17715:
-            strcpy(name, "Kamatau");
-            break;
-        case 17801:
-            strcpy(name, "Lizardman");
-            break;
-        case 17802:
-            strcpy(name, "Lizardman");
-            break;
-        case 17803:
-            strcpy(name, "Lizardman");
-            break;
-        case 17804:
-            strcpy(name, "Lizardman");
-            break;
-        case 17805:
-            strcpy(name, "Lizardman");
-            break;
-        case 17811:
-            strcpy(name, "Kernodon");
-            break;
-        case 17812:
-            strcpy(name, "Igmanodon");
-            break;
-        case 17813:
-            strcpy(name, "Velfinodon");
-            break;
-        case 17814:
-            strcpy(name, "Glinodon");
-            break;
-        case 17815:
-            strcpy(name, "Devinodon");
-            break;
-        case 17901:
-            strcpy(name, "Hell Lady");
-            break;
-        case 17902:
-            strcpy(name, "Hell Lady");
-            break;
-        case 17903:
-            strcpy(name, "Hell Lady");
-            break;
-        case 17904:
-            strcpy(name, "Hell Lady");
-            break;
-        case 17905:
-            strcpy(name, "Hell Lady");
-            break;
-        case 17911:
-            strcpy(name, "Beth");
-            break;
-        case 17912:
-            strcpy(name, "Raki");
-            break;
-        case 17913:
-            strcpy(name, "Ethna");
-            break;
-        case 17914:
-            strcpy(name, "Asima");
-            break;
-        case 17915:
-            strcpy(name, "Craka");
-            break;
-        case 18001:
-            strcpy(name, "Brownie Magician");
-            break;
-        case 18002:
-            strcpy(name, "Brownie Magician");
-            break;
-        case 18003:
-            strcpy(name, "Brownie Magician");
-            break;
-        case 18004:
-            strcpy(name, "Brownie Magician");
-            break;
-        case 18005:
-            strcpy(name, "Brownie Magician");
-            break;
-        case 18011:
-            strcpy(name, "Orion");
-            break;
-        case 18012:
-            strcpy(name, "Draco");
-            break;
-        case 18013:
-            strcpy(name, "Aquila");
-            break;
-        case 18014:
-            strcpy(name, "Gemini");
-            break;
-        case 18015:
-            strcpy(name, "Korona");
-            break;
-        case 18101:
-            strcpy(name, "Kobold Bomber");
-            break;
-        case 18102:
-            strcpy(name, "Kobold Bomber");
-            break;
-        case 18103:
-            strcpy(name, "Kobold Bomber");
-            break;
-        case 18104:
-            strcpy(name, "Kobold Bomber");
-            break;
-        case 18105:
-            strcpy(name, "Kobold Bomber");
-            break;
-        case 18111:
-            strcpy(name, "Malaka");
-            break;
-        case 18112:
-            strcpy(name, "Zibrolta");
-            break;
-        case 18113:
-            strcpy(name, "Taurus");
-            break;
-        case 18114:
-            strcpy(name, "Dover");
-            break;
-        case 18115:
-            strcpy(name, "Bering");
-            break;
-        case 18201:
-            strcpy(name, "King Angelmon");
-            break;
-        case 18202:
-            strcpy(name, "King Angelmon");
-            break;
-        case 18203:
-            strcpy(name, "King Angelmon");
-            break;
-        case 18204:
-            strcpy(name, "King Angelmon");
-            break;
-        case 18205:
-            strcpy(name, "King Angelmon");
-            break;
-        case 18211:
-            strcpy(name, "Blue King Angelmon");
-            break;
-        case 18212:
-            strcpy(name, "Red King Angelmon");
-            break;
-        case 18213:
-            strcpy(name, "Gold King Angelmon");
-            break;
-        case 18214:
-            strcpy(name, "White King Angelmon");
-            break;
-        case 18215:
-            strcpy(name, "Dark King Angelmon");
-            break;
-        case 18301:
-            strcpy(name, "Sky Dancer");
-            break;
-        case 18302:
-            strcpy(name, "Sky Dancer");
-            break;
-        case 18303:
-            strcpy(name, "Sky Dancer");
-            break;
-        case 18304:
-            strcpy(name, "Sky Dancer");
-            break;
-        case 18305:
-            strcpy(name, "Sky Dancer");
-            break;
-        case 18311:
-            strcpy(name, "Mihyang");
-            break;
-        case 18312:
-            strcpy(name, "Hwahee");
-            break;
-        case 18313:
-            strcpy(name, "Chasun");
-            break;
-        case 18314:
-            strcpy(name, "Yeonhong");
-            break;
-        case 18315:
-            strcpy(name, "Wolyung");
-            break;
-        case 18401:
-            strcpy(name, "Taoist");
-            break;
-        case 18402:
-            strcpy(name, "Taoist");
-            break;
-        case 18403:
-            strcpy(name, "Taoist");
-            break;
-        case 18404:
-            strcpy(name, "Taoist");
-            break;
-        case 18405:
-            strcpy(name, "Taoist");
-            break;
-        case 18411:
-            strcpy(name, "Gildong");
-            break;
-        case 18412:
-            strcpy(name, "Gunpyeong");
-            break;
-        case 18413:
-            strcpy(name, "Woochi");
-            break;
-        case 18414:
-            strcpy(name, "Hwadam");
-            break;
-        case 18415:
-            strcpy(name, "Woonhak");
-            break;
-        case 18501:
-            strcpy(name, "Beast Hunter");
-            break;
-        case 18502:
-            strcpy(name, "Beast Hunter");
-            break;
-        case 18503:
-            strcpy(name, "Beast Hunter");
-            break;
-        case 18504:
-            strcpy(name, "Beast Hunter");
-            break;
-        case 18505:
-            strcpy(name, "Beast Hunter");
-            break;
-        case 18511:
-            strcpy(name, "Gangchun");
-            break;
-        case 18512:
-            strcpy(name, "Nangrim");
-            break;
-        case 18513:
-            strcpy(name, "Suri");
-            break;
-        case 18514:
-            strcpy(name, "Baekdu");
-            break;
-        case 18515:
-            strcpy(name, "Hanra");
-            break;
-        case 18601:
-            strcpy(name, "Pioneer");
-            break;
-        case 18602:
-            strcpy(name, "Pioneer");
-            break;
-        case 18603:
-            strcpy(name, "Pioneer");
-            break;
-        case 18604:
-            strcpy(name, "Pioneer");
-            break;
-        case 18605:
-            strcpy(name, "Pioneer");
-            break;
-        case 18611:
-            strcpy(name, "Woosa");
-            break;
-        case 18612:
-            strcpy(name, "Chiwu");
-            break;
-        case 18613:
-            strcpy(name, "Pungbaek");
-            break;
-        case 18614:
-            strcpy(name, "Nigong");
-            break;
-        case 18615:
-            strcpy(name, "Woonsa");
-            break;
-        case 18701:
-            strcpy(name, "Penguin Knight");
-            break;
-        case 18702:
-            strcpy(name, "Penguin Knight");
-            break;
-        case 18703:
-            strcpy(name, "Penguin Knight");
-            break;
-        case 18704:
-            strcpy(name, "Penguin Knight");
-            break;
-        case 18705:
-            strcpy(name, "Penguin Knight");
-            break;
-        case 18711:
-            strcpy(name, "Toma");
-            break;
-        case 18712:
-            strcpy(name, "Naki");
-            break;
-        case 18713:
-            strcpy(name, "Mav");
-            break;
-        case 18714:
-            strcpy(name, "Dona");
-            break;
-        case 18715:
-            strcpy(name, "Kuna");
-            break;
-        case 18801:
-            strcpy(name, "Barbaric King");
-            break;
-        case 18802:
-            strcpy(name, "Barbaric King");
-            break;
-        case 18803:
-            strcpy(name, "Barbaric King");
-            break;
-        case 18804:
-            strcpy(name, "Barbaric King");
-            break;
-        case 18805:
-            strcpy(name, "Barbaric King");
-            break;
-        case 18811:
-            strcpy(name, "Aegir");
-            break;
-        case 18812:
-            strcpy(name, "Surtr");
-            break;
-        case 18813:
-            strcpy(name, "Hraesvelg");
-            break;
-        case 18814:
-            strcpy(name, "Mimirr");
-            break;
-        case 18815:
-            strcpy(name, "Hrungnir");
-            break;
-        case 18901:
-            strcpy(name, "Polar Queen");
-            break;
-        case 18902:
-            strcpy(name, "Polar Queen");
-            break;
-        case 18903:
-            strcpy(name, "Polar Queen");
-            break;
-        case 18904:
-            strcpy(name, "Polar Queen");
-            break;
-        case 18905:
-            strcpy(name, "Polar Queen");
-            break;
-        case 18911:
-            strcpy(name, "Alicia");
-            break;
-        case 18912:
-            strcpy(name, "Brandia");
-            break;
-        case 18913:
-            strcpy(name, "Tiana");
-            break;
-        case 18914:
-            strcpy(name, "Elenoa");
-            break;
-        case 18915:
-            strcpy(name, "Lydia");
-            break;
-        case 19001:
-            strcpy(name, "Battle Mammoth");
-            break;
-        case 19002:
-            strcpy(name, "Battle Mammoth");
-            break;
-        case 19003:
-            strcpy(name, "Battle Mammoth");
-            break;
-        case 19004:
-            strcpy(name, "Battle Mammoth");
-            break;
-        case 19005:
-            strcpy(name, "Battle Mammoth");
-            break;
-        case 19011:
-            strcpy(name, "Talc");
-            break;
-        case 19012:
-            strcpy(name, "Granite");
-            break;
-        case 19013:
-            strcpy(name, "Olivine");
-            break;
-        case 19014:
-            strcpy(name, "Marble");
-            break;
-        case 19015:
-            strcpy(name, "Basalt");
-            break;
-        case 19104:
-            strcpy(name, "Fairy Queen");
-            break;
-        case 19114:
-            strcpy(name, "Fran");
-            break;
-        case 19201:
-            strcpy(name, "Ifrit");
-            break;
-        case 19202:
-            strcpy(name, "Ifrit");
-            break;
-        case 19203:
-            strcpy(name, "Ifrit");
-            break;
-        case 19204:
-            strcpy(name, "Ifrit");
-            break;
-        case 19205:
-            strcpy(name, "Ifrit");
-            break;
-        case 19211:
-            strcpy(name, "Theomars");
-            break;
-        case 19212:
-            strcpy(name, "Tesarion");
-            break;
-        case 19213:
-            strcpy(name, "Akhamamir");
-            break;
-        case 19214:
-            strcpy(name, "Elsharion");
-            break;
-        case 19215:
-            strcpy(name, "Veromos");
-            break;
-        case 19301:
-            strcpy(name, "Cow Girl");
-            break;
-        case 19302:
-            strcpy(name, "Cow Girl");
-            break;
-        case 19303:
-            strcpy(name, "Cow Girl");
-            break;
-        case 19304:
-            strcpy(name, "Cow Girl");
-            break;
-        case 19305:
-            strcpy(name, "Cow Girl");
-            break;
-        case 19311:
-            strcpy(name, "Sera");
-            break;
-        case 19312:
-            strcpy(name, "Anne");
-            break;
-        case 19313:
-            strcpy(name, "Hannah");
-            break;
-        case 19314:
-            strcpy(name, "Loren");
-            break;
-        case 19315:
-            strcpy(name, "Cassie");
-            break;
-        case 19401:
-            strcpy(name, "Pirate Captain");
-            break;
-        case 19402:
-            strcpy(name, "Pirate Captain");
-            break;
-        case 19403:
-            strcpy(name, "Pirate Captain");
-            break;
-        case 19404:
-            strcpy(name, "Pirate Captain");
-            break;
-        case 19405:
-            strcpy(name, "Pirate Captain");
-            break;
-        case 19411:
-            strcpy(name, "Galleon");
-            break;
-        case 19412:
-            strcpy(name, "Carrack");
-            break;
-        case 19413:
-            strcpy(name, "Barque");
-            break;
-        case 19414:
-            strcpy(name, "Brig");
-            break;
-        case 19415:
-            strcpy(name, "Frigate");
-            break;
-        case 19501:
-            strcpy(name, "Charger Shark");
-            break;
-        case 19502:
-            strcpy(name, "Charger Shark");
-            break;
-        case 19503:
-            strcpy(name, "Charger Shark");
-            break;
-        case 19504:
-            strcpy(name, "Charger Shark");
-            break;
-        case 19505:
-            strcpy(name, "Charger Shark");
-            break;
-        case 19511:
-            strcpy(name, "Aqcus");
-            break;
-        case 19512:
-            strcpy(name, "Ignicus");
-            break;
-        case 19513:
-            strcpy(name, "Zephicus");
-            break;
-        case 19514:
-            strcpy(name, "Rumicus");
-            break;
-        case 19515:
-            strcpy(name, "Calicus");
-            break;
-        case 19601:
-            strcpy(name, "Mermaid");
-            break;
-        case 19602:
-            strcpy(name, "Mermaid");
-            break;
-        case 19603:
-            strcpy(name, "Mermaid");
-            break;
-        case 19604:
-            strcpy(name, "Mermaid");
-            break;
-        case 19605:
-            strcpy(name, "Mermaid");
-            break;
-        case 19611:
-            strcpy(name, "Tetra");
-            break;
-        case 19612:
-            strcpy(name, "Platy");
-            break;
-        case 19613:
-            strcpy(name, "Cichlid");
-            break;
-        case 19614:
-            strcpy(name, "Molly");
-            break;
-        case 19615:
-            strcpy(name, "Betta");
-            break;
-        case 19701:
-            strcpy(name, "Sea Emperor");
-            break;
-        case 19702:
-            strcpy(name, "Sea Emperor");
-            break;
-        case 19703:
-            strcpy(name, "Sea Emperor");
-            break;
-        case 19704:
-            strcpy(name, "Sea Emperor");
-            break;
-        case 19705:
-            strcpy(name, "Sea Emperor");
-            break;
-        case 19711:
-            strcpy(name, "Poseidon");
-            break;
-        case 19712:
-            strcpy(name, "Okeanos");
-            break;
-        case 19713:
-            strcpy(name, "Triton");
-            break;
-        case 19714:
-            strcpy(name, "Pontos");
-            break;
-        case 19715:
-            strcpy(name, "Manannan");
-            break;
-        case 19801:
-            strcpy(name, "Magic Knight");
-            break;
-        case 19802:
-            strcpy(name, "Magic Knight");
-            break;
-        case 19803:
-            strcpy(name, "Magic Knight");
-            break;
-        case 19804:
-            strcpy(name, "Magic Knight");
-            break;
-        case 19805:
-            strcpy(name, "Magic Knight");
-            break;
-        case 19811:
-            strcpy(name, "Lapis");
-            break;
-        case 19812:
-            strcpy(name, "Astar");
-            break;
-        case 19813:
-            strcpy(name, "Lupinus");
-            break;
-        case 19814:
-            strcpy(name, "Iris");
-            break;
-        case 19815:
-            strcpy(name, "Lanett");
-            break;
-        case 19823:
-            strcpy(name, "Imperfect Magic Knight");
-            break;
-        case 19901:
-            strcpy(name, "Assassin");
-            break;
-        case 19902:
-            strcpy(name, "Assassin");
-            break;
-        case 19903:
-            strcpy(name, "Assassin");
-            break;
-        case 19904:
-            strcpy(name, "Assassin");
-            break;
-        case 19905:
-            strcpy(name, "Assassin");
-            break;
-        case 19911:
-            strcpy(name, "Stella");
-            break;
-        case 19912:
-            strcpy(name, "Lexy");
-            break;
-        case 19913:
-            strcpy(name, "Tanya");
-            break;
-        case 19914:
-            strcpy(name, "Natalie");
-            break;
-        case 19915:
-            strcpy(name, "Isabelle");
-            break;
-        case 20001:
-            strcpy(name, "Neostone Fighter");
-            break;
-        case 20002:
-            strcpy(name, "Neostone Fighter");
-            break;
-        case 20003:
-            strcpy(name, "Neostone Fighter");
-            break;
-        case 20004:
-            strcpy(name, "Neostone Fighter");
-            break;
-        case 20005:
-            strcpy(name, "Neostone Fighter");
-            break;
-        case 20011:
-            strcpy(name, "Ryan");
-            break;
-        case 20012:
-            strcpy(name, "Trevor");
-            break;
-        case 20013:
-            strcpy(name, "Logan");
-            break;
-        case 20014:
-            strcpy(name, "Lucas");
-            break;
-        case 20015:
-            strcpy(name, "Karl");
-            break;
-        case 20101:
-            strcpy(name, "Neostone Agent");
-            break;
-        case 20102:
-            strcpy(name, "Neostone Agent");
-            break;
-        case 20103:
-            strcpy(name, "Neostone Agent");
-            break;
-        case 20104:
-            strcpy(name, "Neostone Agent");
-            break;
-        case 20105:
-            strcpy(name, "Neostone Agent");
-            break;
-        case 20111:
-            strcpy(name, "Emma");
-            break;
-        case 20112:
-            strcpy(name, "Lisa");
-            break;
-        case 20113:
-            strcpy(name, "Olivia");
-            break;
-        case 20114:
-            strcpy(name, "Illianna");
-            break;
-        case 20115:
-            strcpy(name, "Sylvia");
-            break;
-        case 20201:
-            strcpy(name, "Martial Artist");
-            break;
-        case 20202:
-            strcpy(name, "Martial Artist");
-            break;
-        case 20203:
-            strcpy(name, "Martial Artist");
-            break;
-        case 20204:
-            strcpy(name, "Martial Artist");
-            break;
-        case 20205:
-            strcpy(name, "Martial Artist");
-            break;
-        case 20211:
-            strcpy(name, "Luan");
-            break;
-        case 20212:
-            strcpy(name, "Sin");
-            break;
-        case 20213:
-            strcpy(name, "Lo");
-            break;
-        case 20214:
-            strcpy(name, "Hiro");
-            break;
-        case 20215:
-            strcpy(name, "Jackie");
-            break;
-        case 20301:
-            strcpy(name, "Mummy");
-            break;
-        case 20302:
-            strcpy(name, "Mummy");
-            break;
-        case 20303:
-            strcpy(name, "Mummy");
-            break;
-        case 20304:
-            strcpy(name, "Mummy");
-            break;
-        case 20305:
-            strcpy(name, "Mummy");
-            break;
-        case 20311:
-            strcpy(name, "Nubia");
-            break;
-        case 20312:
-            strcpy(name, "Sonora");
-            break;
-        case 20313:
-            strcpy(name, "Namib");
-            break;
-        case 20314:
-            strcpy(name, "Sahara");
-            break;
-        case 20315:
-            strcpy(name, "Karakum");
-            break;
-        case 20401:
-            strcpy(name, "Anubis");
-            break;
-        case 20402:
-            strcpy(name, "Anubis");
-            break;
-        case 20403:
-            strcpy(name, "Anubis");
-            break;
-        case 20404:
-            strcpy(name, "Anubis");
-            break;
-        case 20405:
-            strcpy(name, "Anubis");
-            break;
-        case 20411:
-            strcpy(name, "Avaris");
-            break;
-        case 20412:
-            strcpy(name, "Khmun");
-            break;
-        case 20413:
-            strcpy(name, "Iunu");
-            break;
-        case 20414:
-            strcpy(name, "Amarna");
-            break;
-        case 20415:
-            strcpy(name, "Thebae");
-            break;
-        case 20501:
-            strcpy(name, "Desert Queen");
-            break;
-        case 20502:
-            strcpy(name, "Desert Queen");
-            break;
-        case 20503:
-            strcpy(name, "Desert Queen");
-            break;
-        case 20504:
-            strcpy(name, "Desert Queen");
-            break;
-        case 20505:
-            strcpy(name, "Desert Queen");
-            break;
-        case 20511:
-            strcpy(name, "Bastet");
-            break;
-        case 20512:
-            strcpy(name, "Sekhmet");
-            break;
-        case 20513:
-            strcpy(name, "Hathor");
-            break;
-        case 20514:
-            strcpy(name, "Isis");
-            break;
-        case 20515:
-            strcpy(name, "Nephthys");
-            break;
-        case 20601:
-            strcpy(name, "Horus");
-            break;
-        case 20602:
-            strcpy(name, "Horus");
-            break;
-        case 20603:
-            strcpy(name, "Horus");
-            break;
-        case 20604:
-            strcpy(name, "Horus");
-            break;
-        case 20605:
-            strcpy(name, "Horus");
-            break;
-        case 20611:
-            strcpy(name, "Qebehsenuef");
-            break;
-        case 20612:
-            strcpy(name, "Duamutef");
-            break;
-        case 20613:
-            strcpy(name, "Imesety");
-            break;
-        case 20614:
-            strcpy(name, "Wedjat");
-            break;
-        case 20615:
-            strcpy(name, "Amduat");
-            break;
-        case 20621:
-            strcpy(name, "Imperfect Horus");
-            break;
-        case 20701:
-            strcpy(name, "Jack-o'-lantern");
-            break;
-        case 20702:
-            strcpy(name, "Jack-o'-lantern");
-            break;
-        case 20703:
-            strcpy(name, "Jack-o'-lantern");
-            break;
-        case 20704:
-            strcpy(name, "Jack-o'-lantern");
-            break;
-        case 20705:
-            strcpy(name, "Jack-o'-lantern");
-            break;
-        case 20711:
-            strcpy(name, "Chilling");
-            break;
-        case 20712:
-            strcpy(name, "Smokey");
-            break;
-        case 20713:
-            strcpy(name, "Windy");
-            break;
-        case 20714:
-            strcpy(name, "Misty");
-            break;
-        case 20715:
-            strcpy(name, "Dusky");
-            break;
-        case 20801:
-            strcpy(name, "Frankenstein");
-            break;
-        case 20802:
-            strcpy(name, "Frankenstein");
-            break;
-        case 20803:
-            strcpy(name, "Frankenstein");
-            break;
-        case 20804:
-            strcpy(name, "Frankenstein");
-            break;
-        case 20805:
-            strcpy(name, "Frankenstein");
-            break;
-        case 20811:
-            strcpy(name, "Tractor");
-            break;
-        case 20812:
-            strcpy(name, "Bulldozer");
-            break;
-        case 20813:
-            strcpy(name, "Crane");
-            break;
-        case 20814:
-            strcpy(name, "Driller");
-            break;
-        case 20815:
-            strcpy(name, "Crawler");
-            break;
-        case 20901:
-            strcpy(name, "Elven Ranger");
-            break;
-        case 20902:
-            strcpy(name, "Elven Ranger");
-            break;
-        case 20903:
-            strcpy(name, "Elven Ranger");
-            break;
-        case 20904:
-            strcpy(name, "Elven Ranger");
-            break;
-        case 20905:
-            strcpy(name, "Elven Ranger");
-            break;
-        case 20911:
-            strcpy(name, "Eluin");
-            break;
-        case 20912:
-            strcpy(name, "Adrian");
-            break;
-        case 20913:
-            strcpy(name, "Erwin");
-            break;
-        case 20914:
-            strcpy(name, "Lucien");
-            break;
-        case 20915:
-            strcpy(name, "Isillen");
-            break;
-        case 21001:
-            strcpy(name, "Harg");
-            break;
-        case 21002:
-            strcpy(name, "Harg");
-            break;
-        case 21003:
-            strcpy(name, "Harg");
-            break;
-        case 21004:
-            strcpy(name, "Harg");
-            break;
-        case 21005:
-            strcpy(name, "Harg");
-            break;
-        case 21011:
-            strcpy(name, "Remy");
-            break;
-        case 21012:
-            strcpy(name, "Racuni");
-            break;
-        case 21013:
-            strcpy(name, "Raviti");
-            break;
-        case 21014:
-            strcpy(name, "Dova");
-            break;
-        case 21015:
-            strcpy(name, "Kroa");
-            break;
-        case 21101:
-            strcpy(name, "Fairy King");
-            break;
-        case 21102:
-            strcpy(name, "Fairy King");
-            break;
-        case 21103:
-            strcpy(name, "Fairy King");
-            break;
-        case 21104:
-            strcpy(name, "Fairy King");
-            break;
-        case 21105:
-            strcpy(name, "Fairy King");
-            break;
-        case 21111:
-            strcpy(name, "Psamathe");
-            break;
-        case 21112:
-            strcpy(name, "Daphnis");
-            break;
-        case 21113:
-            strcpy(name, "Ganymede");
-            break;
-        case 21114:
-            strcpy(name, "Oberon");
-            break;
-        case 21115:
-            strcpy(name, "Nyx");
-            break;
-        case 21201:
-            strcpy(name, "Panda Warrior");
-            break;
-        case 21202:
-            strcpy(name, "Panda Warrior");
-            break;
-        case 21203:
-            strcpy(name, "Panda Warrior");
-            break;
-        case 21204:
-            strcpy(name, "Panda Warrior");
-            break;
-        case 21205:
-            strcpy(name, "Panda Warrior");
-            break;
-        case 21211:
-            strcpy(name, "Mo Long");
-            break;
-        case 21212:
-            strcpy(name, "Xiong Fei");
-            break;
-        case 21213:
-            strcpy(name, "Feng Yan");
-            break;
-        case 21214:
-            strcpy(name, "Tian Lang");
-            break;
-        case 21215:
-            strcpy(name, "Mi Ying");
-            break;
-        case 21301:
-            strcpy(name, "Dice Magician");
-            break;
-        case 21302:
-            strcpy(name, "Dice Magician");
-            break;
-        case 21303:
-            strcpy(name, "Dice Magician");
-            break;
-        case 21304:
-            strcpy(name, "Dice Magician");
-            break;
-        case 21305:
-            strcpy(name, "Dice Magician");
-            break;
-        case 21311:
-            strcpy(name, "Reno");
-            break;
-        case 21312:
-            strcpy(name, "Ludo");
-            break;
-        case 21313:
-            strcpy(name, "Morris");
-            break;
-        case 21314:
-            strcpy(name, "Tablo");
-            break;
-        case 21315:
-            strcpy(name, "Monte");
-            break;
-        case 21401:
-            strcpy(name, "Harp Magician");
-            break;
-        case 21402:
-            strcpy(name, "Harp Magician");
-            break;
-        case 21403:
-            strcpy(name, "Harp Magician");
-            break;
-        case 21404:
-            strcpy(name, "Harp Magician");
-            break;
-        case 21405:
-            strcpy(name, "Harp Magician");
-            break;
-        case 21411:
-            strcpy(name, "Sonnet");
-            break;
-        case 21412:
-            strcpy(name, "Harmonia");
-            break;
-        case 21413:
-            strcpy(name, "Triana");
-            break;
-        case 21414:
-            strcpy(name, "Celia");
-            break;
-        case 21415:
-            strcpy(name, "Vivachel");
-            break;
-        case 21422:
-            strcpy(name, "Imperfect Harp Magician");
-            break;
-        case 21501:
-            strcpy(name, "Unicorn");
-            break;
-        case 21502:
-            strcpy(name, "Unicorn");
-            break;
-        case 21503:
-            strcpy(name, "Unicorn");
-            break;
-        case 21504:
-            strcpy(name, "Unicorn");
-            break;
-        case 21505:
-            strcpy(name, "Unicorn");
-            break;
-        case 21511:
-            strcpy(name, "Amelia");
-            break;
-        case 21512:
-            strcpy(name, "Helena");
-            break;
-        case 21513:
-            strcpy(name, "Diana");
-            break;
-        case 21514:
-            strcpy(name, "Eleanor");
-            break;
-        case 21515:
-            strcpy(name, "Alexandra");
-            break;
-        case 21611:
-            strcpy(name, "Amelia");
-            break;
-        case 21612:
-            strcpy(name, "Helena");
-            break;
-        case 21613:
-            strcpy(name, "Diana");
-            break;
-        case 21614:
-            strcpy(name, "Eleanor");
-            break;
-        case 21615:
-            strcpy(name, "Alexandra");
-            break;
-        case 21714:
-            strcpy(name, "Super Angelmon");
-            break;
-        case 21801:
-            strcpy(name, "Paladin");
-            break;
-        case 21802:
-            strcpy(name, "Paladin");
-            break;
-        case 21803:
-            strcpy(name, "Paladin");
-            break;
-        case 21804:
-            strcpy(name, "Paladin");
-            break;
-        case 21805:
-            strcpy(name, "Paladin");
-            break;
-        case 21811:
-            strcpy(name, "Josephine");
-            break;
-        case 21812:
-            strcpy(name, "Ophilia");
-            break;
-        case 21813:
-            strcpy(name, "Louise");
-            break;
-        case 21814:
-            strcpy(name, "Jeanne");
-            break;
-        case 21815:
-            strcpy(name, "Leona");
-            break;
-        case 21901:
-            strcpy(name, "Chakram Dancer");
-            break;
-        case 21902:
-            strcpy(name, "Chakram Dancer");
-            break;
-        case 21903:
-            strcpy(name, "Chakram Dancer");
-            break;
-        case 21904:
-            strcpy(name, "Chakram Dancer");
-            break;
-        case 21905:
-            strcpy(name, "Chakram Dancer");
-            break;
-        case 21911:
-            strcpy(name, "Talia");
-            break;
-        case 21912:
-            strcpy(name, "Shaina");
-            break;
-        case 21913:
-            strcpy(name, "Melissa");
-            break;
-        case 21914:
-            strcpy(name, "Deva");
-            break;
-        case 21915:
-            strcpy(name, "Belita");
-            break;
-        case 22001:
-            strcpy(name, "Boomerang Warrior");
-            break;
-        case 22002:
-            strcpy(name, "Boomerang Warrior");
-            break;
-        case 22003:
-            strcpy(name, "Boomerang Warrior");
-            break;
-        case 22004:
-            strcpy(name, "Boomerang Warrior");
-            break;
-        case 22005:
-            strcpy(name, "Boomerang Warrior");
-            break;
-        case 22011:
-            strcpy(name, "Sabrina");
-            break;
-        case 22012:
-            strcpy(name, "Maruna");
-            break;
-        case 22013:
-            strcpy(name, "Zenobia");
-            break;
-        case 22014:
-            strcpy(name, "Bailey");
-            break;
-        case 22015:
-            strcpy(name, "Martina");
-            break;
-        case 22101:
-            strcpy(name, "Dryad");
-            break;
-        case 22102:
-            strcpy(name, "Dryad");
-            break;
-        case 22103:
-            strcpy(name, "Dryad");
-            break;
-        case 22104:
-            strcpy(name, "Dryad");
-            break;
-        case 22105:
-            strcpy(name, "Dryad");
-            break;
-        case 22111:
-            strcpy(name, "Herne");
-            break;
-        case 22112:
-            strcpy(name, "Nisha");
-            break;
-        case 22113:
-            strcpy(name, "Mellia");
-            break;
-        case 22114:
-            strcpy(name, "Felleria");
-            break;
-        case 22115:
-            strcpy(name, "Hyanes");
-            break;
-        case 22201:
-            strcpy(name, "Druid");
-            break;
-        case 22202:
-            strcpy(name, "Druid");
-            break;
-        case 22203:
-            strcpy(name, "Druid");
-            break;
-        case 22204:
-            strcpy(name, "Druid");
-            break;
-        case 22205:
-            strcpy(name, "Druid");
-            break;
-        case 22211:
-            strcpy(name, "Abellio");
-            break;
-        case 22212:
-            strcpy(name, "Bellenus");
-            break;
-        case 22213:
-            strcpy(name, "Taranys");
-            break;
-        case 22214:
-            strcpy(name, "Valantis");
-            break;
-        case 22215:
-            strcpy(name, "Pater");
-            break;
-        case 22311:
-            strcpy(name, "Abellio");
-            break;
-        case 22312:
-            strcpy(name, "Bellenus");
-            break;
-        case 22313:
-            strcpy(name, "Taranys");
-            break;
-        case 22314:
-            strcpy(name, "Valantis");
-            break;
-        case 22315:
-            strcpy(name, "Pater");
-            break;
-        case 22401:
-            strcpy(name, "Giant Warrior");
-            break;
-        case 22402:
-            strcpy(name, "Giant Warrior");
-            break;
-        case 22403:
-            strcpy(name, "Giant Warrior");
-            break;
-        case 22404:
-            strcpy(name, "Giant Warrior");
-            break;
-        case 22405:
-            strcpy(name, "Giant Warrior");
-            break;
-        case 22411:
-            strcpy(name, "Bagir");
-            break;
-        case 22412:
-            strcpy(name, "Vidurr");
-            break;
-        case 22413:
-            strcpy(name, "Skogul");
-            break;
-        case 22414:
-            strcpy(name, "Einheri");
-            break;
-        case 22415:
-            strcpy(name, "Trasar");
-            break;
-        case 22503:
-            strcpy(name, "Giant Warrior");
-            break;
-        case 22505:
-            strcpy(name, "Giant Warrior");
-            break;
-        case 22513:
-            strcpy(name, "Skogul");
-            break;
-        case 22515:
-            strcpy(name, "Trasar");
-            break;
-        case 22601:
-            strcpy(name, "Lightning Emperor");
-            break;
-        case 22602:
-            strcpy(name, "Lightning Emperor");
-            break;
-        case 22603:
-            strcpy(name, "Lightning Emperor");
-            break;
-        case 22604:
-            strcpy(name, "Lightning Emperor");
-            break;
-        case 22605:
-            strcpy(name, "Lightning Emperor");
-            break;
-        case 22611:
-            strcpy(name, "Bolverk");
-            break;
-        case 22612:
-            strcpy(name, "Baleygr");
-            break;
-        case 22613:
-            strcpy(name, "Odin");
-            break;
-        case 22614:
-            strcpy(name, "Geldnir");
-            break;
-        case 22615:
-            strcpy(name, "Herteit");
-            break;
-        case 22701:
-            strcpy(name, "Sniper Mk.I");
-            break;
-        case 22702:
-            strcpy(name, "Sniper Mk.I");
-            break;
-        case 22703:
-            strcpy(name, "Sniper Mk.I");
-            break;
-        case 22704:
-            strcpy(name, "Sniper Mk.I");
-            break;
-        case 22705:
-            strcpy(name, "Sniper Mk.I");
-            break;
-        case 22711:
-            strcpy(name, "Covenant");
-            break;
-        case 22712:
-            strcpy(name, "Carcano");
-            break;
-        case 22713:
-            strcpy(name, "Carbine");
-            break;
-        case 22714:
-            strcpy(name, "Magnum");
-            break;
-        case 22715:
-            strcpy(name, "Dragunov");
-            break;
-        case 22802:
-            strcpy(name, "Sniper Mk.I");
-            break;
-        case 22803:
-            strcpy(name, "Sniper Mk.I");
-            break;
-        case 22805:
-            strcpy(name, "Sniper Mk.I");
-            break;
-        case 22812:
-            strcpy(name, "Carcano");
-            break;
-        case 22813:
-            strcpy(name, "Carbine");
-            break;
-        case 22815:
-            strcpy(name, "Dragunov");
-            break;
-        case 22901:
-            strcpy(name, "Cannon Girl");
-            break;
-        case 22902:
-            strcpy(name, "Cannon Girl");
-            break;
-        case 22903:
-            strcpy(name, "Cannon Girl");
-            break;
-        case 22904:
-            strcpy(name, "Cannon Girl");
-            break;
-        case 22905:
-            strcpy(name, "Cannon Girl");
-            break;
-        case 22911:
-            strcpy(name, "Abigail");
-            break;
-        case 22912:
-            strcpy(name, "Scarlett");
-            break;
-        case 22913:
-            strcpy(name, "Christina");
-            break;
-        case 22914:
-            strcpy(name, "Emily");
-            break;
-        case 22915:
-            strcpy(name, "Bella");
-            break;
-        case 23005:
-            strcpy(name, "Vampire Lord");
-            break;
-        case 23015:
-            strcpy(name, "Eirgar");
-            break;
-        case 23101:
-            strcpy(name, "Demon");
-            break;
-        case 23102:
-            strcpy(name, "Demon");
-            break;
-        case 23103:
-            strcpy(name, "Demon");
-            break;
-        case 23104:
-            strcpy(name, "Demon");
-            break;
-        case 23105:
-            strcpy(name, "Demon");
-            break;
-        case 23111:
-            strcpy(name, "Belial");
-            break;
-        case 23112:
-            strcpy(name, "Bael");
-            break;
-        case 23113:
-            strcpy(name, "Mephisto");
-            break;
-        case 23114:
-            strcpy(name, "Lucifer");
-            break;
-        case 23115:
-            strcpy(name, "Beelzebub");
-            break;
-        case 23201:
-            strcpy(name, "데몬(물)");
-            break;
-        case 23205:
-            strcpy(name, "데몬(어둠)");
-            break;
-        case 23211:
-            strcpy(name, "데몬(물)");
-            break;
-        case 23215:
-            strcpy(name, "데몬(어둠)");
-            break;
-        case 23301:
-            strcpy(name, "Gargoyle");
-            break;
-        case 23302:
-            strcpy(name, "Gargoyle");
-            break;
-        case 23303:
-            strcpy(name, "Gargoyle");
-            break;
-        case 23304:
-            strcpy(name, "Gargoyle");
-            break;
-        case 23305:
-            strcpy(name, "Gargoyle");
-            break;
-        case 23311:
-            strcpy(name, "Tanzaite");
-            break;
-        case 23312:
-            strcpy(name, "Kunite");
-            break;
-        case 23313:
-            strcpy(name, "Malite");
-            break;
-        case 23314:
-            strcpy(name, "Phenaka");
-            break;
-        case 23315:
-            strcpy(name, "Onyx");
-            break;
-        case 23401:
-            strcpy(name, "가고일(물)");
-            break;
-        case 23402:
-            strcpy(name, "가고일(불)");
-            break;
-        case 23403:
-            strcpy(name, "가고일(바람)");
-            break;
-        case 23404:
-            strcpy(name, "가고일(빛)");
-            break;
-        case 23405:
-            strcpy(name, "가고일(어둠)");
-            break;
-        case 23411:
-            strcpy(name, "가고일(물)");
-            break;
-        case 23412:
-            strcpy(name, "가고일(불)");
-            break;
-        case 23413:
-            strcpy(name, "가고일(바람)");
-            break;
-        case 23414:
-            strcpy(name, "가고일(빛)");
-            break;
-        case 23415:
-            strcpy(name, "가고일(어둠)");
-            break;
-        case 23501:
-            strcpy(name, "Beast Rider");
-            break;
-        case 23502:
-            strcpy(name, "Beast Rider");
-            break;
-        case 23503:
-            strcpy(name, "Beast Rider");
-            break;
-        case 23504:
-            strcpy(name, "Beast Rider");
-            break;
-        case 23505:
-            strcpy(name, "Beast Rider");
-            break;
-        case 23511:
-            strcpy(name, "Barbara");
-            break;
-        case 23512:
-            strcpy(name, "Masha");
-            break;
-        case 23513:
-            strcpy(name, "Savannah");
-            break;
-        case 23514:
-            strcpy(name, "Narsha");
-            break;
-        case 23515:
-            strcpy(name, "Xiana");
-            break;
-        case 23601:
-            strcpy(name, "Beast Rider");
-            break;
-        case 23602:
-            strcpy(name, "Beast Rider");
-            break;
-        case 23603:
-            strcpy(name, "Beast Rider");
-            break;
-        case 23604:
-            strcpy(name, "Beast Rider");
-            break;
-        case 23605:
-            strcpy(name, "Beast Rider");
-            break;
-        case 23611:
-            strcpy(name, "Barbara");
-            break;
-        case 23612:
-            strcpy(name, "Masha");
-            break;
-        case 23613:
-            strcpy(name, "Savannah");
-            break;
-        case 23614:
-            strcpy(name, "Narsha");
-            break;
-        case 23615:
-            strcpy(name, "Xiana");
-            break;
-        case 23701:
-            strcpy(name, "Art Master");
-            break;
-        case 23702:
-            strcpy(name, "Art Master");
-            break;
-        case 23703:
-            strcpy(name, "Art Master");
-            break;
-        case 23704:
-            strcpy(name, "Art Master");
-            break;
-        case 23705:
-            strcpy(name, "Art Master");
-            break;
-        case 23711:
-            strcpy(name, "Haegang");
-            break;
-        case 23712:
-            strcpy(name, "Jeogun");
-            break;
-        case 23713:
-            strcpy(name, "Cheongpung");
-            break;
-        case 23714:
-            strcpy(name, "Hanwul");
-            break;
-        case 23715:
-            strcpy(name, "Mookwol");
-            break;
-        case 23801:
-            strcpy(name, "족자(물)");
-            break;
-        case 23802:
-            strcpy(name, "족자(불)");
-            break;
-        case 23803:
-            strcpy(name, "족자(바람)");
-            break;
-        case 23804:
-            strcpy(name, "족자(빛)");
-            break;
-        case 23805:
-            strcpy(name, "족자(어둠)");
-            break;
-        case 23806:
-            strcpy(name, "족자(무)");
-            break;
-        case 23901:
-            strcpy(name, "String Master");
-            break;
-        case 23902:
-            strcpy(name, "String Master");
-            break;
-        case 23903:
-            strcpy(name, "String Master");
-            break;
-        case 23904:
-            strcpy(name, "String Master");
-            break;
-        case 23905:
-            strcpy(name, "String Master");
-            break;
-        case 23911:
-            strcpy(name, "Songseol");
-            break;
-        case 23912:
-            strcpy(name, "Hongyeon");
-            break;
-        case 23913:
-            strcpy(name, "Yeonhwa");
-            break;
-        case 23914:
-            strcpy(name, "Dongbaek");
-            break;
-        case 23915:
-            strcpy(name, "Mirinae");
-            break;
-        case 24001:
-            strcpy(name, "류(물)");
-            break;
-        case 24002:
-            strcpy(name, "류(불)");
-            break;
-        case 24003:
-            strcpy(name, "류(바람)");
-            break;
-        case 24004:
-            strcpy(name, "류(빛)");
-            break;
-        case 24005:
-            strcpy(name, "류(어둠)");
-            break;
-        case 24011:
-            strcpy(name, "RYU");
-            break;
-        case 24012:
-            strcpy(name, "RYU");
-            break;
-        case 24013:
-            strcpy(name, "RYU");
-            break;
-        case 24014:
-            strcpy(name, "RYU");
-            break;
-        case 24015:
-            strcpy(name, "RYU");
-            break;
-        case 24102:
-            strcpy(name, "켄(불)");
-            break;
-        case 24112:
-            strcpy(name, "KEN");
-            break;
-        case 24201:
-            strcpy(name, "바이슨(물)");
-            break;
-        case 24202:
-            strcpy(name, "바이슨(불)");
-            break;
-        case 24203:
-            strcpy(name, "바이슨(바람)");
-            break;
-        case 24204:
-            strcpy(name, "바이슨(빛)");
-            break;
-        case 24205:
-            strcpy(name, "바이슨(어둠)");
-            break;
-        case 24211:
-            strcpy(name, "M. BISON");
-            break;
-        case 24212:
-            strcpy(name, "M. BISON");
-            break;
-        case 24213:
-            strcpy(name, "M. BISON");
-            break;
-        case 24214:
-            strcpy(name, "M. BISON");
-            break;
-        case 24215:
-            strcpy(name, "M. BISON");
-            break;
-        case 24301:
-            strcpy(name, "달심(물)");
-            break;
-        case 24302:
-            strcpy(name, "달심(불)");
-            break;
-        case 24303:
-            strcpy(name, "달심(바람)");
-            break;
-        case 24304:
-            strcpy(name, "달심(빛)");
-            break;
-        case 24305:
-            strcpy(name, "달심(어둠)");
-            break;
-        case 24311:
-            strcpy(name, "DHALSIM");
-            break;
-        case 24312:
-            strcpy(name, "DHALSIM");
-            break;
-        case 24313:
-            strcpy(name, "DHALSIM");
-            break;
-        case 24314:
-            strcpy(name, "DHALSIM");
-            break;
-        case 24315:
-            strcpy(name, "DHALSIM");
-            break;
-        case 24401:
-            strcpy(name, "춘리(물)");
-            break;
-        case 24402:
-            strcpy(name, "춘리(불)");
-            break;
-        case 24403:
-            strcpy(name, "춘리(바람)");
-            break;
-        case 24404:
-            strcpy(name, "춘리(빛)");
-            break;
-        case 24405:
-            strcpy(name, "춘리(어둠)");
-            break;
-        case 24411:
-            strcpy(name, "CHUN-LI");
-            break;
-        case 24412:
-            strcpy(name, "CHUN-LI");
-            break;
-        case 24413:
-            strcpy(name, "CHUN-LI");
-            break;
-        case 24414:
-            strcpy(name, "CHUN-LI");
-            break;
-        case 24415:
-            strcpy(name, "CHUN-LI");
-            break;
-        case 24501:
-            strcpy(name, "Striker");
-            break;
-        case 24502:
-            strcpy(name, "Striker");
-            break;
-        case 24503:
-            strcpy(name, "Striker");
-            break;
-        case 24504:
-            strcpy(name, "Striker");
-            break;
-        case 24505:
-            strcpy(name, "Striker");
-            break;
-        case 24511:
-            strcpy(name, "Moore");
-            break;
-        case 24512:
-            strcpy(name, "Douglas");
-            break;
-        case 24513:
-            strcpy(name, "Kashmir");
-            break;
-        case 24514:
-            strcpy(name, "Talisman");
-            break;
-        case 24515:
-            strcpy(name, "Vancliffe");
-            break;
-        case 24602:
-            strcpy(name, "Shadow Claw");
-            break;
-        case 24612:
-            strcpy(name, "Bernadotte");
-            break;
-        case 24701:
-            strcpy(name, "Slayer");
-            break;
-        case 24702:
-            strcpy(name, "Slayer");
-            break;
-        case 24703:
-            strcpy(name, "Slayer");
-            break;
-        case 24704:
-            strcpy(name, "Slayer");
-            break;
-        case 24705:
-            strcpy(name, "Slayer");
-            break;
-        case 24711:
-            strcpy(name, "Borgnine");
-            break;
-        case 24712:
-            strcpy(name, "Karnal");
-            break;
-        case 24713:
-            strcpy(name, "Sagar");
-            break;
-        case 24714:
-            strcpy(name, "Craig");
-            break;
-        case 24715:
-            strcpy(name, "Gurkha");
-            break;
-        case 24801:
-            strcpy(name, "Poison Master");
-            break;
-        case 24802:
-            strcpy(name, "Poison Master");
-            break;
-        case 24803:
-            strcpy(name, "Poison Master");
-            break;
-        case 24804:
-            strcpy(name, "Poison Master");
-            break;
-        case 24805:
-            strcpy(name, "Poison Master");
-            break;
-        case 24811:
-            strcpy(name, "Kyle");
-            break;
-        case 24812:
-            strcpy(name, "Todd");
-            break;
-        case 24813:
-            strcpy(name, "Jarrett");
-            break;
-        case 24814:
-            strcpy(name, "Hekerson");
-            break;
-        case 24815:
-            strcpy(name, "Cayde");
-            break;
-        case 24901:
-            strcpy(name, "Blade Dancer");
-            break;
-        case 24902:
-            strcpy(name, "Blade Dancer");
-            break;
-        case 24903:
-            strcpy(name, "Blade Dancer");
-            break;
-        case 24904:
-            strcpy(name, "Blade Dancer");
-            break;
-        case 24905:
-            strcpy(name, "Blade Dancer");
-            break;
-        case 24911:
-            strcpy(name, "Lariel");
-            break;
-        case 24912:
-            strcpy(name, "Berenice");
-            break;
-        case 24913:
-            strcpy(name, "Cordelia");
-            break;
-        case 24914:
-            strcpy(name, "Leah");
-            break;
-        case 24915:
-            strcpy(name, "Vereesa");
-            break;
-        case 40101:
-            strcpy(name, "Inugami");
-            break;
-        case 40201:
-            strcpy(name, "Phoenix");
-            break;
-        case 40302:
-            strcpy(name, "Golem");
-            break;
-        case 40403:
-            strcpy(name, "Sylphid");
-            break;
-        case 40501:
-            strcpy(name, "Undine");
-            break;
-        case 40602:
-            strcpy(name, "Inferno");
-            break;
-        case 40703:
-            strcpy(name, "Chimera");
-            break;
-        case 40803:
-            strcpy(name, "Salamander");
-            break;
-        case 40903:
-            strcpy(name, "Sylph");
-            break;
-        case 41006:
-            strcpy(name, "Otherworldly Dragon");
-            break;
-        case 41101:
-            strcpy(name, "Death Knight");
-            break;
-        case 41202:
-            strcpy(name, "Lich");
-            break;
-        case 41303:
-            strcpy(name, "Keeper of Remains");
-            break;
-        case 41401:
-            strcpy(name, "Contaminated Dragon");
-            break;
-        case 42006:
-            strcpy(name, "Ath'taros");
-            break;
-        case 42106:
-            strcpy(name, "Lyrith");
-            break;
-        case 42206:
-            strcpy(name, "Lyrith");
-            break;
-        case 43001:
-            strcpy(name, "Ice Beast");
-            break;
-        case 43002:
-            strcpy(name, "Fire Beast");
-            break;
-        case 43003:
-            strcpy(name, "Wind Beast");
-            break;
-        case 43004:
-            strcpy(name, "Light Beast");
-            break;
-        case 43005:
-            strcpy(name, "Dark Beast");
-            break;
-        case 44007:
-            strcpy(name, "Chaos Beast Khi'zar Kha'jul");
-            break;
-        case 44008:
-            strcpy(name, "Chaos Beast Khi'zar Kha'jul");
-            break;
-        case 44009:
-            strcpy(name, "Chaos Beast Khi'zar Kha'jul");
-            break;
-        case 45001:
-            strcpy(name, "형상아이템용 더미(물)");
-            break;
-        case 45002:
-            strcpy(name, "형상아이템용 더미(불)");
-            break;
-        case 45003:
-            strcpy(name, "형상아이템용 더미(바람)");
-            break;
-        case 45004:
-            strcpy(name, "형상아이템용 더미(빛)");
-            break;
-        case 45005:
-            strcpy(name, "형상아이템용 더미(어둠)");
-            break;
-        case 46001:
-            strcpy(name, "Tartarus");
-            break;
-        case 46002:
-            strcpy(name, "미궁 보스 머리");
-            break;
-        case 46003:
-            strcpy(name, "미궁 보스 왼쪽팔");
-            break;
-        case 46004:
-            strcpy(name, "미궁 보스 오른쪽팔");
-            break;
-        case 46101:
-            strcpy(name, "Leos");
-            break;
-        case 46102:
-            strcpy(name, "Kotos");
-            break;
-        case 46103:
-            strcpy(name, "Guilles");
-            break;
-        case 46201:
-            strcpy(name, "미궁 룬문양 (물)");
-            break;
-        case 46202:
-            strcpy(name, "미궁 룬문양 (불)");
-            break;
-        case 46203:
-            strcpy(name, "미궁 룬문양 (바람)");
-            break;
-        case 46301:
-            strcpy(name, "Leos");
-            break;
-        case 46302:
-            strcpy(name, "Kotos");
-            break;
-        case 46303:
-            strcpy(name, "Guilles");
-            break;
-        case 46304:
-            strcpy(name, "Leos");
-            break;
-        case 46305:
-            strcpy(name, "Kotos");
-            break;
-        case 46306:
-            strcpy(name, "Guilles");
-            break;
-        case 46307:
-            strcpy(name, "Leos");
-            break;
-        case 46308:
-            strcpy(name, "Kotos");
-            break;
-        case 46309:
-            strcpy(name, "Guilles");
-            break;
-        case 47001:
-            strcpy(name, "Ancient Guardian");
-            break;
-        case 47002:
-            strcpy(name, "Ancient Guardian");
-            break;
-        case 47003:
-            strcpy(name, "Ancient Guardian");
-            break;
-        case 47101:
-            strcpy(name, "Fairy 2A");
-            break;
-        case 47102:
-            strcpy(name, "Fairy 2A");
-            break;
-        case 47103:
-            strcpy(name, "Fairy 2A");
-            break;
-        case 47104:
-            strcpy(name, "Fairy 2A");
-            break;
-        case 47105:
-            strcpy(name, "Fairy 2A");
-            break;
-        case 47201:
-            strcpy(name, "Pixie 2A");
-            break;
-        case 47202:
-            strcpy(name, "Pixie 2A");
-            break;
-        case 47203:
-            strcpy(name, "Pixie 2A");
-            break;
-        case 47204:
-            strcpy(name, "Pixie 2A");
-            break;
-        case 47205:
-            strcpy(name, "Pixie 2A");
-            break;
-        case 47301:
-            strcpy(name, "Warbear 2A");
-            break;
-        case 47302:
-            strcpy(name, "Warbear 2A");
-            break;
-        case 47303:
-            strcpy(name, "Warbear 2A");
-            break;
-        case 47304:
-            strcpy(name, "Warbear 2A");
-            break;
-        case 47305:
-            strcpy(name, "Warbear 2A");
-            break;
-        case 47401:
-            strcpy(name, "Inugami 2A");
-            break;
-        case 47402:
-            strcpy(name, "Inugami 2A");
-            break;
-        case 47403:
-            strcpy(name, "Inugami 2A");
-            break;
-        case 47404:
-            strcpy(name, "Inugami 2A");
-            break;
-        case 47405:
-            strcpy(name, "Inugami 2A");
-            break;
-        case 47501:
-            strcpy(name, "Werewolf 2A");
-            break;
-        case 47502:
-            strcpy(name, "Werewolf 2A");
-            break;
-        case 47503:
-            strcpy(name, "Werewolf 2A");
-            break;
-        case 47504:
-            strcpy(name, "Werewolf 2A");
-            break;
-        case 47505:
-            strcpy(name, "Werewolf 2A");
-            break;
-        case 47601:
-            strcpy(name, "Martial Cat 2A");
-            break;
-        case 47602:
-            strcpy(name, "Martial Cat 2A");
-            break;
-        case 47603:
-            strcpy(name, "Martial Cat 2A");
-            break;
-        case 47604:
-            strcpy(name, "Martial Cat 2A");
-            break;
-        case 47605:
-            strcpy(name, "Martial Cat 2A");
-            break;
-        case 47701:
-            strcpy(name, "Griffon 2A");
-            break;
-        case 47702:
-            strcpy(name, "Griffon 2A");
-            break;
-        case 47703:
-            strcpy(name, "Griffon 2A");
-            break;
-        case 47704:
-            strcpy(name, "Griffon 2A");
-            break;
-        case 47705:
-            strcpy(name, "Griffon 2A");
-            break;
-        case 60101:
-            strcpy(name, "Keeper of Water");
-            break;
-        case 60102:
-            strcpy(name, "Keeper of Fire");
-            break;
-        case 60103:
-            strcpy(name, "Keeper of Wind");
-            break;
-        case 60104:
-            strcpy(name, "Keeper of Light");
-            break;
-        case 60105:
-            strcpy(name, "Keeper of Darkness");
-            break;
-        case 60201:
-            strcpy(name, "Ancient Giant");
-            break;
-        case 60202:
-            strcpy(name, "Ancient Giant");
-            break;
-        case 60203:
-            strcpy(name, "Ancient Giant");
-            break;
-        case 60204:
-            strcpy(name, "Ancient Giant");
-            break;
-        case 60205:
-            strcpy(name, "Ancient Giant");
-            break;
-        case 60301:
-            strcpy(name, "Legendary Dragon");
-            break;
-        case 60302:
-            strcpy(name, "Legendary Dragon");
-            break;
-        case 60303:
-            strcpy(name, "Legendary Dragon");
-            break;
-        case 60304:
-            strcpy(name, "Legendary Dragon");
-            break;
-        case 60305:
-            strcpy(name, "Legendary Dragon");
-            break;
-        case 60401:
-            strcpy(name, "Angelmon");
-            break;
-        case 60402:
-            strcpy(name, "Angelmon");
-            break;
-        case 60403:
-            strcpy(name, "Angelmon");
-            break;
-        case 60404:
-            strcpy(name, "Angelmon");
-            break;
-        case 60405:
-            strcpy(name, "Angelmon");
-            break;
-        case 60501:
-            strcpy(name, "Angelmon");
-            break;
-        case 60502:
-            strcpy(name, "Angelmon");
-            break;
-        case 60503:
-            strcpy(name, "Angelmon");
-            break;
-        case 60504:
-            strcpy(name, "Angelmon");
-            break;
-        case 60505:
-            strcpy(name, "Angelmon");
-            break;
-        case 60601:
-            strcpy(name, "Angelmon");
-            break;
-        case 60602:
-            strcpy(name, "Angelmon");
-            break;
-        case 60603:
-            strcpy(name, "Angelmon");
-            break;
-        case 60604:
-            strcpy(name, "Angelmon");
-            break;
-        case 60605:
-            strcpy(name, "Angelmon");
-            break;
-        case 60701:
-            strcpy(name, "Angelmon");
-            break;
-        case 60702:
-            strcpy(name, "Angelmon");
-            break;
-        case 60703:
-            strcpy(name, "Angelmon");
-            break;
-        case 60704:
-            strcpy(name, "Angelmon");
-            break;
-        case 60705:
-            strcpy(name, "Angelmon");
-            break;
-        case 60804:
-            strcpy(name, "Rainbowmon");
-            break;
-        case 60805:
-            strcpy(name, "Devilmon");
-            break;
-        case 60904:
-            strcpy(name, "Rainbowmon");
-            break;
-        case 60905:
-            strcpy(name, "Devilmon");
-            break;
-        case 61004:
-            strcpy(name, "Rainbowmon");
-            break;
-        case 61005:
-            strcpy(name, "Devilmon");
-            break;
-        case 61104:
-            strcpy(name, "Rainbowmon");
-            break;
-        case 61105:
-            strcpy(name, "Devilmon");
-            break;
-        case 62004:
-            strcpy(name, "Keeper of Magic");
-            break;
-        case 62101:
-            strcpy(name, "Ancient Lich King");
-            break;
-        case 62102:
-            strcpy(name, "Ancient Lich King");
-            break;
-        case 62103:
-            strcpy(name, "Ancient Lich King");
-            break;
-        case 62104:
-            strcpy(name, "Ancient Lich King");
-            break;
-        case 62105:
-            strcpy(name, "Ancient Lich King");
-            break;
-        case 62200:
-            strcpy(name, "월드보스-고대골렘");
-            break;
-        case 62303:
-            strcpy(name, "Ancient Intercessor");
-            break;
-        case 62403:
-            strcpy(name, "Ancient Tormentor");
-            break;
-        case 62504:
-            strcpy(name, "Ancient Intercessor");
-            break;
-        case 62604:
-            strcpy(name, "Ancient Punisher");
-            break;
-        case 63102:
-            strcpy(name, "만랩튜토리얼보스(불)");
-            break;
-        case 63202:
-            strcpy(name, "만랩튜토리얼_드래곤(불)");
-            break;
-        case 63301:
-            strcpy(name, "만랩튜토리얼_가고일(물)");
-            break;
-        case 63302:
-            strcpy(name, "만랩튜토리얼_가고일(불)");
-            break;
-        case 63303:
-            strcpy(name, "만랩튜토리얼_가고일(바람)");
-            break;
-        case 70001:
-            strcpy(name, "Dimension Predator");
-            break;
-        case 70002:
-            strcpy(name, "Dimension Predator");
-            break;
-        case 70003:
-            strcpy(name, "Dimension Predator");
-            break;
-        case 70004:
-            strcpy(name, "Dimension Predator");
-            break;
-        case 70005:
-            strcpy(name, "Dimension Predator");
-            break;
-        case 70101:
-            strcpy(name, "Dimension Predator");
-            break;
-        case 70102:
-            strcpy(name, "Dimension Predator");
-            break;
-        case 70103:
-            strcpy(name, "Dimension Predator");
-            break;
-        case 70104:
-            strcpy(name, "Dimension Predator");
-            break;
-        case 70105:
-            strcpy(name, "Dimension Predator");
-            break;
-        case 70201:
-            strcpy(name, "Dimension Predator");
-            break;
-        case 70202:
-            strcpy(name, "Dimension Predator");
-            break;
-        case 70203:
-            strcpy(name, "Dimension Predator");
-            break;
-        case 70204:
-            strcpy(name, "Dimension Predator");
-            break;
-        case 70205:
-            strcpy(name, "Dimension Predator");
-            break;
-        case 71004:
-            strcpy(name, "Hollow");
-            break;
-        case 71005:
-            strcpy(name, "Hollow");
-            break;
-        case 71101:
-            strcpy(name, "Void");
-            break;
-        case 71102:
-            strcpy(name, "Void");
-            break;
-        case 71103:
-            strcpy(name, "Void");
-            break;
-        case 100116:
-            strcpy(name, "Tower");
-            break;
-        case 100126:
-            strcpy(name, "Tower");
-            break;
-        case 100136:
-            strcpy(name, "Tower");
-            break;
-        case 100146:
-            strcpy(name, "Tower");
-            break;
-        case 100156:
-            strcpy(name, "Tower");
-            break;
-        case 100216:
-            strcpy(name, "Tower");
-            break;
-        case 100226:
-            strcpy(name, "Tower");
-            break;
-        case 100236:
-            strcpy(name, "Tower");
-            break;
-        case 100246:
-            strcpy(name, "Tower");
-            break;
-        case 100256:
-            strcpy(name, "Tower");
-            break;
-        case 100316:
-            strcpy(name, "Tower");
-            break;
-        case 100326:
-            strcpy(name, "Tower");
-            break;
-        case 100336:
-            strcpy(name, "Tower");
-            break;
-        case 100346:
-            strcpy(name, "Tower");
-            break;
-        case 100356:
-            strcpy(name, "Tower");
-            break;
-        case 100416:
-            strcpy(name, "Tower");
-            break;
-        case 100426:
-            strcpy(name, "Tower");
-            break;
-        case 100436:
-            strcpy(name, "Tower");
-            break;
-        case 100446:
-            strcpy(name, "Tower");
-            break;
-        case 100456:
-            strcpy(name, "Tower");
-            break;
-        case 100516:
-            strcpy(name, "Tower");
-            break;
-        case 100526:
-            strcpy(name, "Tower");
-            break;
-        case 100536:
-            strcpy(name, "Tower");
-            break;
-        case 100546:
-            strcpy(name, "Tower");
-            break;
-        case 100556:
-            strcpy(name, "Tower");
-            break;
-        case 100616:
-            strcpy(name, "Tower");
-            break;
-        case 100626:
-            strcpy(name, "Tower");
-            break;
-        case 100636:
-            strcpy(name, "Tower");
-            break;
-        case 100646:
-            strcpy(name, "Tower");
-            break;
-        case 100656:
-            strcpy(name, "Tower");
-            break;
-        case 100716:
-            strcpy(name, "Tower");
-            break;
-        case 100726:
-            strcpy(name, "Tower");
-            break;
-        case 100736:
-            strcpy(name, "Tower");
-            break;
-        case 100746:
-            strcpy(name, "Tower");
-            break;
-        case 100756:
-            strcpy(name, "Tower");
-            break;
-        case 100816:
-            strcpy(name, "Tower");
-            break;
-        case 100826:
-            strcpy(name, "Tower");
-            break;
-        case 100836:
-            strcpy(name, "Tower");
-            break;
-        case 100846:
-            strcpy(name, "Tower");
-            break;
-        case 100856:
-            strcpy(name, "Tower");
-            break;
-        case 100916:
-            strcpy(name, "Tower");
-            break;
-        case 100926:
-            strcpy(name, "Tower");
-            break;
-        case 100936:
-            strcpy(name, "Tower");
-            break;
-        case 100946:
-            strcpy(name, "Tower");
-            break;
-        case 100956:
-            strcpy(name, "Tower");
-            break;
-        case 101016:
-            strcpy(name, "Tower");
-            break;
-        case 101026:
-            strcpy(name, "Tower");
-            break;
-        case 101036:
-            strcpy(name, "Tower");
-            break;
-        case 101046:
-            strcpy(name, "Tower");
-            break;
-        case 101056:
-            strcpy(name, "Tower");
-            break;
-        case 101116:
-            strcpy(name, "Tower");
-            break;
-        case 101126:
-            strcpy(name, "Tower");
-            break;
-        case 101136:
-            strcpy(name, "Tower");
-            break;
-        case 101146:
-            strcpy(name, "Tower");
-            break;
-        case 101156:
-            strcpy(name, "Tower");
-            break;
-        case 101216:
-            strcpy(name, "Tower");
-            break;
-        case 101226:
-            strcpy(name, "Tower");
-            break;
-        case 101236:
-            strcpy(name, "Tower");
-            break;
-        case 101246:
-            strcpy(name, "Tower");
-            break;
-        case 101256:
-            strcpy(name, "Tower");
-            break;
-        case 101316:
-            strcpy(name, "Tower");
-            break;
-        case 101326:
-            strcpy(name, "Tower");
-            break;
-        case 101336:
-            strcpy(name, "Tower");
-            break;
-        case 101346:
-            strcpy(name, "Tower");
-            break;
-        case 101356:
-            strcpy(name, "Tower");
-            break;
-        case 101416:
-            strcpy(name, "Tower");
-            break;
-        case 101426:
-            strcpy(name, "Tower");
-            break;
-        case 101436:
-            strcpy(name, "Tower");
-            break;
-        case 101446:
-            strcpy(name, "Tower");
-            break;
-        case 101456:
-            strcpy(name, "Tower");
-            break;
-        case 101516:
-            strcpy(name, "Tower");
-            break;
-        case 101526:
-            strcpy(name, "Tower");
-            break;
-        case 101536:
-            strcpy(name, "Tower");
-            break;
-        case 101546:
-            strcpy(name, "Tower");
-            break;
-        case 101556:
-            strcpy(name, "Tower");
-            break;
-        case 101616:
-            strcpy(name, "타워(물) - 전체 충격 수정");
-            break;
-        case 101626:
-            strcpy(name, "타워(불) - 전체 충격 수정");
-            break;
-        case 101636:
-            strcpy(name, "타워(바람) - 전체 충격 수정");
-            break;
-        case 101646:
-            strcpy(name, "타워(빛) - 전체 충격 수정");
-            break;
-        case 101656:
-            strcpy(name, "타워(어둠) - 전체 충격 수정");
-            break;
-        case 101716:
-            strcpy(name, "타워(물) - 공속 게이지");
-            break;
-        case 101726:
-            strcpy(name, "타워(불) - 공속 게이지");
-            break;
-        case 101736:
-            strcpy(name, "타워(바람) - 공속 게이지");
-            break;
-        case 101746:
-            strcpy(name, "타워(빛) - 공속 게이지");
-            break;
-        case 101756:
-            strcpy(name, "타워(어둠) - 공속 게이지");
-            break;
-        case 110106:
-            strcpy(name, "시험의탑 타워(왼쪽)");
-            break;
-        case 110206:
-            strcpy(name, "시험의탑 타워(오른쪽)");
-            break;
-        case 110306:
-            strcpy(name, "Incarnation of Greed");
-            break;
-        case 110406:
-            strcpy(name, "Incarnation of Vendetta");
-            break;
-        case 110506:
-            strcpy(name, "Incarnation of Protection");
-            break;
-        case 110606:
-            strcpy(name, "Incarnation of Greed");
-            break;
-        case 110706:
-            strcpy(name, "Incarnation of Vendetta");
-            break;
-        case 110806:
-            strcpy(name, "Incarnation of Protection");
-            break;
-        case 110902:
-            strcpy(name, "Fire Minion");
-            break;
-        case 111006:
-            strcpy(name, "만랩튜토타워_방어 약화");
-            break;
-        case 111016:
-            strcpy(name, "만랩튜토타워_공격 강화");
-            break;
-        case 112023:
-            strcpy(name, "Tower");
-            break;
-        case 112033:
-            strcpy(name, "Tower");
-            break;
-        case 112124:
-            strcpy(name, "Tower");
-            break;
-        case 112134:
-            strcpy(name, "Tower");
-            break;
-        case 120101:
-            strcpy(name, "Tower");
-            break;
-        case 120102:
-            strcpy(name, "Tower");
-            break;
-        case 120103:
-            strcpy(name, "Tower");
-            break;
-        case 120104:
-            strcpy(name, "Tower");
-            break;
-        case 120105:
-            strcpy(name, "Tower");
-            break;
-        case 120111:
-            strcpy(name, "Tower");
-            break;
-        case 120112:
-            strcpy(name, "Tower");
-            break;
-        case 120113:
-            strcpy(name, "Tower");
-            break;
-        case 120114:
-            strcpy(name, "Tower");
-            break;
-        case 120115:
-            strcpy(name, "Tower");
-            break;
-        case 120201:
-            strcpy(name, "Tower");
-            break;
-        case 120202:
-            strcpy(name, "Tower");
-            break;
-        case 120203:
-            strcpy(name, "Tower");
-            break;
-        case 120204:
-            strcpy(name, "Tower");
-            break;
-        case 120205:
-            strcpy(name, "Tower");
-            break;
-        case 120211:
-            strcpy(name, "Tower");
-            break;
-        case 120212:
-            strcpy(name, "Tower");
-            break;
-        case 120213:
-            strcpy(name, "Tower");
-            break;
-        case 120214:
-            strcpy(name, "Tower");
-            break;
-        case 120215:
-            strcpy(name, "Tower");
-            break;
-        case 120301:
-            strcpy(name, "Tower");
-            break;
-        case 120302:
-            strcpy(name, "Tower");
-            break;
-        case 120303:
-            strcpy(name, "Tower");
-            break;
-        case 120304:
-            strcpy(name, "Tower");
-            break;
-        case 120305:
-            strcpy(name, "Tower");
-            break;
-        case 120311:
-            strcpy(name, "Tower");
-            break;
-        case 120312:
-            strcpy(name, "Tower");
-            break;
-        case 120313:
-            strcpy(name, "Tower");
-            break;
-        case 120314:
-            strcpy(name, "Tower");
-            break;
-        case 120315:
-            strcpy(name, "Tower");
-            break;
-        case 120401:
-            strcpy(name, "Tower");
-            break;
-        case 120402:
-            strcpy(name, "Tower");
-            break;
-        case 120403:
-            strcpy(name, "Tower");
-            break;
-        case 120404:
-            strcpy(name, "Tower");
-            break;
-        case 120405:
-            strcpy(name, "Tower");
-            break;
-        case 120411:
-            strcpy(name, "Tower");
-            break;
-        case 120412:
-            strcpy(name, "Tower");
-            break;
-        case 120413:
-            strcpy(name, "Tower");
-            break;
-        case 120414:
-            strcpy(name, "Tower");
-            break;
-        case 120415:
-            strcpy(name, "Tower");
-            break;
-        case 120501:
-            strcpy(name, "Tower");
-            break;
-        case 120502:
-            strcpy(name, "Tower");
-            break;
-        case 120503:
-            strcpy(name, "Tower");
-            break;
-        case 120504:
-            strcpy(name, "Tower");
-            break;
-        case 120505:
-            strcpy(name, "Tower");
-            break;
-        case 120511:
-            strcpy(name, "Tower");
-            break;
-        case 120512:
-            strcpy(name, "Tower");
-            break;
-        case 120513:
-            strcpy(name, "Tower");
-            break;
-        case 120514:
-            strcpy(name, "Tower");
-            break;
-        case 120515:
-            strcpy(name, "Tower");
-            break;
-        case 120601:
-            strcpy(name, "Tower");
-            break;
-        case 120602:
-            strcpy(name, "Tower");
-            break;
-        case 120603:
-            strcpy(name, "Tower");
-            break;
-        case 120604:
-            strcpy(name, "Tower");
-            break;
-        case 120605:
-            strcpy(name, "Tower");
-            break;
-        case 120611:
-            strcpy(name, "Tower");
-            break;
-        case 120612:
-            strcpy(name, "Tower");
-            break;
-        case 120613:
-            strcpy(name, "Tower");
-            break;
-        case 120614:
-            strcpy(name, "Tower");
-            break;
-        case 120615:
-            strcpy(name, "Tower");
-            break;
-        case 120701:
-            strcpy(name, "Tower");
-            break;
-        case 120702:
-            strcpy(name, "Tower");
-            break;
-        case 120703:
-            strcpy(name, "Tower");
-            break;
-        case 120704:
-            strcpy(name, "Tower");
-            break;
-        case 120705:
-            strcpy(name, "Tower");
-            break;
-        case 120711:
-            strcpy(name, "Tower");
-            break;
-        case 120712:
-            strcpy(name, "Tower");
-            break;
-        case 120713:
-            strcpy(name, "Tower");
-            break;
-        case 120714:
-            strcpy(name, "Tower");
-            break;
-        case 120715:
-            strcpy(name, "Tower");
-            break;
-        case 200103:
-            strcpy(name, "Small Crystal");
-            break;
-        case 200113:
-            strcpy(name, "Medium Crystal");
-            break;
-        case 200204:
-            strcpy(name, "Small Crystal");
-            break;
-        case 200214:
-            strcpy(name, "Medium Crystal");
-            break;
-        case 210106:
-            strcpy(name, "Small Crystal");
-            break;
-        case 210206:
-            strcpy(name, "Small Crystal");
-            break;
-        case 210306:
-            strcpy(name, "Small Crystal");
-            break;
-        case 210406:
-            strcpy(name, "Small Crystal");
-            break;
-        case 210506:
-            strcpy(name, "Small Crystal");
-            break;
-        case 210606:
-            strcpy(name, "Medium Crystal");
-            break;
-        case 210706:
-            strcpy(name, "Medium Crystal");
-            break;
-        case 210806:
-            strcpy(name, "Medium Crystal");
-            break;
-        case 210906:
-            strcpy(name, "Medium Crystal");
-            break;
-        case 211006:
-            strcpy(name, "Medium Crystal");
-            break;
-        case 220001:
-            strcpy(name, "Small Crystal");
-            break;
-        case 220002:
-            strcpy(name, "Small Crystal");
-            break;
-        case 220003:
-            strcpy(name, "Small Crystal");
-            break;
-        case 220004:
-            strcpy(name, "Small Crystal");
-            break;
-        case 220005:
-            strcpy(name, "Small Crystal");
-            break;
-        case 220011:
-            strcpy(name, "Medium Crystal");
-            break;
-        case 220012:
-            strcpy(name, "Medium Crystal");
-            break;
-        case 220013:
-            strcpy(name, "Medium Crystal");
-            break;
-        case 220014:
-            strcpy(name, "Medium Crystal");
-            break;
-        case 220015:
-            strcpy(name, "Medium Crystal");
-            break;
-        case 310106:
-            strcpy(name, "Taotie");
-            break;
-        case 310206:
-            strcpy(name, "Turtle");
-            break;
-        case 310306:
-            strcpy(name, "Ice Beast");
-            break;
-        case 400001:
-            strcpy(name, "Predator's Wreckage");
-            break;
-        case 400002:
-            strcpy(name, "Predator's Wreckage");
-            break;
-        case 400003:
-            strcpy(name, "Predator's Wreckage");
-            break;
-        case 400004:
-            strcpy(name, "Predator's Wreckage");
-            break;
-        case 400005:
-            strcpy(name, "Predator's Wreckage");
-            break;
-        case 400006:
-            strcpy(name, "Predator's Wreckage");
-            break;
-        case 400007:
-            strcpy(name, "Predator's Wreckage");
-            break;
-        case 400008:
-            strcpy(name, "Predator's Wreckage");
-            break;
-        case 400009:
-            strcpy(name, "Predator's Wreckage");
-            break;
-        case 400010:
-            strcpy(name, "Predator's Wreckage");
-            break;
-        case 1000101:
-            strcpy(name, "Homunculus(Attack)");
-            break;
-        case 1000102:
-            strcpy(name, "Homunculus(Attack)");
-            break;
-        case 1000103:
-            strcpy(name, "Homunculus(Attack)");
-            break;
-        case 1000111:
-            strcpy(name, "Homunculus(Attack)");
-            break;
-        case 1000112:
-            strcpy(name, "Homunculus(Attack)");
-            break;
-        case 1000113:
-            strcpy(name, "Homunculus(Attack)");
-            break;
-        case 1000204:
-            strcpy(name, "Homunculus(Support)");
-            break;
-        case 1000205:
-            strcpy(name, "Homunculus(Support)");
-            break;
-        case 1000214:
-            strcpy(name, "Homunculus(Support)");
-            break;
-        case 1000215:
-            strcpy(name, "Homunculus(Support)");
-            break;
-        case 10101:
-            strcpy(name, "Fairy");
-            break;
-        case 13231:
-            strcpy(name, "Lulu and Friends");
-            break;
-        case 13232:
-            strcpy(name, "Lala and Friends");
-            break;
-        case 13233:
-            strcpy(name, "Chichi and Friends");
-            break;
-        case 13234:
-            strcpy(name, "Shushu and Friends");
-            break;
-        case 13235:
-            strcpy(name, "Chacha and Friends");
-            break;
-        case 16031:
-            strcpy(name, "Hemos");
-            break;
-        case 16032:
-            strcpy(name, "Sath");
-            break;
-        case 16033:
-            strcpy(name, "Hiva");
-            break;
-        case 16034:
-            strcpy(name, "Prom");
-            break;
-        case 16035:
-            strcpy(name, "Thrain");
-            break;
-        case 47004:
-            strcpy(name, "Ancient Guardian");
-            break;
-        case 47801:
-            strcpy(name, "Lulu and Friends");
-            break;
-        case 47802:
-            strcpy(name, "Lala and Friends");
-            break;
-        case 47803:
-            strcpy(name, "Chichi and Friends");
-            break;
-        case 47804:
-            strcpy(name, "Shushu and Friends");
-            break;
-        case 47805:
-            strcpy(name, "Chacha and Friends");
-            break;
-        case 47901:
-            strcpy(name, "Hemos");
-            break;
-        case 47902:
-            strcpy(name, "Sath");
-            break;
-        case 47903:
-            strcpy(name, "Hiva");
-            break;
-        case 47904:
-            strcpy(name, "Prom");
-            break;
-        case 47905:
-            strcpy(name, "Thrain");
-            break;
-        case 120801:
-            strcpy(name, "Tower");
-            break;
-        case 120802:
-            strcpy(name, "Tower");
-            break;
-        case 120803:
-            strcpy(name, "Tower");
-            break;
-        case 120804:
-            strcpy(name, "Tower");
-            break;
-        case 120805:
-            strcpy(name, "Tower");
-            break;
-        case 120811:
-            strcpy(name, "Tower");
-            break;
-        case 120812:
-            strcpy(name, "Tower");
-            break;
-        case 120813:
-            strcpy(name, "Tower");
-            break;
-        case 120814:
-            strcpy(name, "Tower");
-            break;
-        case 120815:
-            strcpy(name, "Tower");
-            break;
-        case 120901:
-            strcpy(name, "Tower");
-            break;
-        case 120902:
-            strcpy(name, "Tower");
-            break;
-        case 120903:
-            strcpy(name, "Tower");
-            break;
-        case 120904:
-            strcpy(name, "Tower");
-            break;
-        case 120905:
-            strcpy(name, "Tower");
-            break;
-        case 120911:
-            strcpy(name, "Tower");
-            break;
-        case 120912:
-            strcpy(name, "Tower");
-            break;
-        case 120913:
-            strcpy(name, "Tower");
-            break;
-        case 120914:
-            strcpy(name, "Tower");
-            break;
-        case 120915:
-            strcpy(name, "Tower");
-            break;
-        case 25001:
-            strcpy(name, "Onmyouji");
-            break;
-        case 25002:
-            strcpy(name, "Onmyouji");
-            break;
-        case 25003:
-            strcpy(name, "Onmyouji");
-            break;
-        case 25004:
-            strcpy(name, "Onmyouji");
-            break;
-        case 25005:
-            strcpy(name, "Onmyouji");
-            break;
-        case 25011:
-            strcpy(name, "Shizuka");
-            break;
-        case 25012:
-            strcpy(name, "Tomoe");
-            break;
-        case 25013:
-            strcpy(name, "Giou");
-            break;
-        case 25014:
-            strcpy(name, "Seimei");
-            break;
-        case 25015:
-            strcpy(name, "Douman");
-            break;
-        case 25101:
-            strcpy(name, "Onimusha");
-            break;
-        case 25102:
-            strcpy(name, "Onimusha");
-            break;
-        case 25103:
-            strcpy(name, "Onimusha");
-            break;
-        case 25104:
-            strcpy(name, "Onimusha");
-            break;
-        case 25105:
-            strcpy(name, "Onimusha");
-            break;
-        case 25111:
-            strcpy(name, "Suiki");
-            break;
-        case 25112:
-            strcpy(name, "Kaki");
-            break;
-        case 25113:
-            strcpy(name, "Fuuki");
-            break;
-        case 25114:
-            strcpy(name, "Kinki");
-            break;
-        case 25115:
-            strcpy(name, "Ongyouki");
-            break;
-        case 12031:
-            strcpy(name, "Ellena");
-            break;
-        case 12032:
-            strcpy(name, "Kahli");
-            break;
-        case 12033:
-            strcpy(name, "Moria");
-            break;
-        case 12034:
-            strcpy(name, "Shren");
-            break;
-        case 12035:
-            strcpy(name, "Jumaline");
-            break;
-        case 48001:
-            strcpy(name, "하이엘리멘탈 2차 각성 보스(물)");
-            break;
-        case 48002:
-            strcpy(name, "하이엘리멘탈 2차 각성 보스(불)");
-            break;
-        case 48003:
-            strcpy(name, "하이엘리멘탈 2차 각성 보스(바람)");
-            break;
-        case 48004:
-            strcpy(name, "하이엘리멘탈 2차 각성 보스(빛)");
-            break;
-        case 48005:
-            strcpy(name, "하이엘리멘탈 2차 각성 보스(어둠)");
-            break;
-        case 121001:
-            strcpy(name, "2차각성 하이엘리멘탈 수정_왼쪽(물)");
-            break;
-        case 121002:
-            strcpy(name, "2차각성 하이엘리멘탈 수정_왼쪽(불)");
-            break;
-        case 121003:
-            strcpy(name, "2차각성 하이엘리멘탈 수정_왼쪽(바람)");
-            break;
-        case 121004:
-            strcpy(name, "2차각성 하이엘리멘탈 수정_왼쪽(빛)");
-            break;
-        case 121005:
-            strcpy(name, "2차각성 하이엘리멘탈 수정_왼쪽(어둠)");
-            break;
-        case 121011:
-            strcpy(name, "2차각성 하이엘리멘탈 수정_오른쪽(물)");
-            break;
-        case 121012:
-            strcpy(name, "2차각성 하이엘리멘탈 수정_오른쪽(불)");
-            break;
-        case 121013:
-            strcpy(name, "2차각성 하이엘리멘탈 수정_오른쪽(바람)");
-            break;
-        case 121014:
-            strcpy(name, "2차각성 하이엘리멘탈 수정_오른쪽(빛)");
-            break;
-        case 121015:
-            strcpy(name, "2차각성 하이엘리멘탈 수정_오른쪽(어둠)");
-            break;
-        case 25201:
-            strcpy(name, "Mage");
-            break;
-        case 25202:
-            strcpy(name, "Mage");
-            break;
-        case 25203:
-            strcpy(name, "Mage");
-            break;
-        case 25204:
-            strcpy(name, "Mage");
-            break;
-        case 25205:
-            strcpy(name, "Mage");
-            break;
-        case 25211:
-            strcpy(name, "Nana");
-            break;
-        case 25212:
-            strcpy(name, "Coco");
-            break;
-        case 25213:
-            strcpy(name, "Momo");
-            break;
-        case 25214:
-            strcpy(name, "Dorothy");
-            break;
-        case 25215:
-            strcpy(name, "Kiki");
-            break;
-        case 25301:
-            strcpy(name, "Sky Surfer");
-            break;
-        case 25302:
-            strcpy(name, "Sky Surfer");
-            break;
-        case 25303:
-            strcpy(name, "Sky Surfer");
-            break;
-        case 25304:
-            strcpy(name, "Sky Surfer");
-            break;
-        case 25305:
-            strcpy(name, "Sky Surfer");
-            break;
-        case 25311:
-            strcpy(name, "Miles");
-            break;
-        case 25312:
-            strcpy(name, "John");
-            break;
-        case 25313:
-            strcpy(name, "Oliver");
-            break;
-        case 25314:
-            strcpy(name, "Daniel");
-            break;
-        case 25315:
-            strcpy(name, "Jackson");
-            break;
-        case 25401:
-            strcpy(name, "ROBO");
-            break;
-        case 25402:
-            strcpy(name, "ROBO");
-            break;
-        case 25403:
-            strcpy(name, "ROBO");
-            break;
-        case 25404:
-            strcpy(name, "ROBO");
-            break;
-        case 25405:
-            strcpy(name, "ROBO");
-            break;
-        case 25411:
-            strcpy(name, "ROBO-R40");
-            break;
-        case 25412:
-            strcpy(name, "ROBO-P27");
-            break;
-        case 25413:
-            strcpy(name, "ROBO-G92");
-            break;
-        case 25414:
-            strcpy(name, "ROBO-E65");
-            break;
-        case 25415:
-            strcpy(name, "ROBO-F29");
-            break;
-        case 25501:
-            strcpy(name, "ROBO(물)_잔해");
-            break;
-        case 25511:
-            strcpy(name, "ROBO(물)_잔해");
-            break;
-        case 20121:
-            strcpy(name, "Imperfect Neostone Agent");
-            break;
-        case 22123:
-            strcpy(name, "Imperfect Dryad");
-            break;
-        case 25601:
-            strcpy(name, "Totemist");
-            break;
-        case 25602:
-            strcpy(name, "Totemist");
-            break;
-        case 25603:
-            strcpy(name, "Totemist");
-            break;
-        case 25604:
-            strcpy(name, "Totemist");
-            break;
-        case 25605:
-            strcpy(name, "Totemist");
-            break;
-        case 25611:
-            strcpy(name, "Aaliyah");
-            break;
-        case 25612:
-            strcpy(name, "Nora");
-            break;
-        case 25613:
-            strcpy(name, "Riley");
-            break;
-        case 25614:
-            strcpy(name, "Ella");
-            break;
-        case 25615:
-            strcpy(name, "Maya");
-            break;
-        default:
-            strcpy(name, "UNKNOWN MONSTER");
-    }
-}

+ 109 - 37
src/RuneOptimizer/update/update.h

@@ -15,14 +15,22 @@
  * RuneOptimizer. If not, see <https://www.gnu.org/licenses/>.
  */
 
+/**
+ * Structure representing a rune stat, with the same fields as the table
+ * 'rune_stats' in the database.
+ */
 struct Rune_Stat {
     unsigned char stat;
     unsigned int value;
     unsigned int grind;
     unsigned char enchant;
-};
+} Rune_Stat;
 
-struct DB_Unit {
+/**
+ * Structure representing a unit, with the same fields as the table 'unit' in
+ * the database.
+ */
+typedef struct DB_Unit {
     unsigned char id[12];
     unsigned int monster;
     unsigned char name[128];
@@ -48,9 +56,13 @@ struct DB_Unit {
     unsigned short current_res;
     unsigned int current_ehp;
     unsigned short current_dmg;
-};
+} BD_Unit;
 
-struct DB_Rune {
+/**
+ * Structure representing a rune, with the same fields as the table 'runes' in
+ * the database.
+ */
+typedef struct DB_Rune {
     unsigned char id[12];
     unsigned char slot;
     unsigned char quality;
@@ -99,23 +111,15 @@ struct DB_Rune {
     struct Rune_Stat innate;
     unsigned char stat_count;
     struct Rune_Stat stats[4];
-};
+} DB_Rune;
 
-#define HP_FLAT 1
-#define HP_PERCENT 2
-#define ATK_FLAT 3
-#define ATK_PERCENT 4
-#define DEF_FLAT 5
-#define DEF_PERCENT 6
-#define SPD 8
-#define CRR 9
-#define CRD 10
-#define RES 11
-#define ACC 12
 
-// Values for main stats.
-// Nested by stat, stars, level(0->12, 1->15)
-int main_stats_values[13][7][2] = {
+/**
+ * Values for main stats.
+ *
+ * Nested by stat, stars, level(0->12, 1->15)
+ */
+const int main_stats_values[13][7][2] = {
   { //NULL (unused)
       {0, 0},
       {0, 0},
@@ -234,28 +238,55 @@ int main_stats_values[13][7][2] = {
 };
 
 /**
- * Parses the command parameters and calls one of the update functions.
+ * Calculates the current stats for units with runes in the database.
+ * 
+ * It counts the bonus stats provided by runes and sets, and updates the
+ * current_* columns in the database for every unit with at least one rune
+ * assigned.
  *
- * @param[in] argc Argument count.
- * @param[in] argv Argument list.
- * @return SUCCESS or an error code.
+ * @return SUCCESS or an error code. See
+ * <a href="file:../error/error.h">../error/error.h</a> for a list of error
+ * codes.
  */
-int update(int argc, char *argv[]);
+int update_current_stats();
 
 /**
- * Calculates the current stats for units with runes in the database.
+ * Recreates the tables in the database.
+ * 
+ * It does not just delete the data, but it actualy drops and recreats the
+ * tables. By default, itdoes this to all tables except 'teams' and
+ * 'units_teams'.
  *
- * @return SUCCESS or an error code.
+ * @param[in] clear_teams Indicator to recreate tables teams and units_teams.
+ * @return SUCCESS or an error code. See
+ * <a href="file:../error/error.h">../error/error.h</a> for a list of error
+ * codes.
  */
-int calculate_current_stats();
+int update_db_tables(unsigned char clear_teams);
 
 /**
- * Recreates the tables in the database.
+ * Gets a monster name from it's ID.
+ * 
+ * If the monster is unawakened, the name will be in the format
+ * 'name (element)'. If the monster is second awakened, the name will be
+ * 'name (2A)'. For the rest of cases, it will be just 'name'. In any case, the
+ * monster name will be truncated so that the total length of the string is less
+ * than 64 characters.
  *
- * @param[in] clear_teams Indicator to recreate tables teams and units_teams.
- * @return SUCCESS or an error code.
+ * @param[in] id Monster ID.
+ * @param[out] name Monster name.
+ */
+void update_get_monster_name(int id, char name[64]);
+
+/**
+ * Updaes the data in the table 'info'.
+ * 
+ * @param[in] id Player ID.
+ * @param[in] name Player name.
+ * @param[in] level Player level.
+ * @return SUCCESS if the info is saved or ERROR_DB_INSERT_INFO on error.
  */
-int recreate_tables(unsigned char clear_teams);
+int update_info(const char *id, const char *name, const char *level);
 
 /**
  * Updates the database from a json file.
@@ -266,24 +297,65 @@ int recreate_tables(unsigned char clear_teams);
  * @param[in] with_runes Indicator to import only units with runes.
  * @param[in] clear_teams Indicator to recreate tables teams and units_teams.
  * @param[in] gui Indicator to format output for thr GUI.
- * @return SUCCESS or an error code.
+ * @return SUCCESS or an error code. See
+ * <a href="file:../error/error.h">../error/error.h</a> for a list of error
+ * codes.
  */
 int update_json(
   char file[], unsigned char six_stars,
   unsigned char with_runes, unsigned char clear_teams, unsigned char gui
 );
 
+/**
+ * Saves a single rune to the database obtaining data from its json object.
+ * 
+ * Saves data to the tables 'runes' and 'rune_stats'. In case of error, a
+ * description will be printed to stderr.
+ * 
+ * @param[in] rune_json Rune json fragment.
+ * @param[in] unit_id ID of the unit the rune is assigned to. To leave it
+ * unassigned, pass an empty string, not NULL.
+ * @return The number of stats saved to the database, including the main stat,
+ * innate stat (if any), and all the normal stats. -1 incase of error.
+ */
+int update_json_rune(json_object *rune_json, char *unit_id);
+
+/**
+ * Saves a single unit to the database obtaining data from its json object.
+ * 
+ * Saves data to the tables 'units'. If the unit has any rune assigned, it will
+ * also be saved to 'runes'. In case of error, a description will be printed to
+ * stderr.
+ * 
+ * @param[in] unit_json Unit json fragment.
+ * @param[in] six_stars Indicator to import only 6* units. Units with runes will
+ * be saved anyway.
+ * @param[in] with_runes Indicator to import only units with runes.
+ * @param[out] total_runes Cunter for runes. Will be increased for each saved
+ * rune.
+ * @param[out] total_stats Cunter for rune stats. Will be increased for each
+ * stat on each saved rune.
+ * @return 1 if the unit was saved to the database. 0 If everything was OK but
+ * the unit was not saved because it did not match the criteria. -1 on error.
+ */
+int update_json_unit(
+  json_object *unit_json, unsigned char six_stars,
+  unsigned char with_runes, unsigned int *total_runes, unsigned int *total_stats
+);
+
 /**
  * Calculates the total stat values for a rune.
  *
  * @param[in|out] rune Rune to do the calculation on.
  */
-void calculate_rune_totals(struct DB_Rune *rune);
+void update_rune_totals(struct DB_Rune *rune);
 
 /**
- * Gets a monster name from it's ID.
+ * Parses the command parameters and calls one of the update functions.
  *
- * @param[in] id Monster ID.
- * @param[out] name Monster name.
+ * @param[in] argc Number of arguments passed to the update command.
+ * @param[in] argv Arguments passed to the update command.
+ * @return SUCCESS or an error code.
  */
-void get_monster_name(int id, char name[64]);
+int cmd_update(int argc, char *argv[]);
+

+ 184 - 0
src/RuneOptimizer/update/update_current_stats.c

@@ -0,0 +1,184 @@
+/*
+ * This file is part of RuneOptimizer.
+ *
+ * RuneOptimizer is free software: you can redistribute it and/or modify it
+ * under the terms of the GNU General Public License as published by the Free
+ * Software Foundation, either version 3 of the License, or (at your option)
+ * any later version.
+ *
+ * RuneOptimizer is distributed in the hope that it will be useful, but WITHOUT
+ * ANY WARRANTY; without even the implied warranty of MERCHANTABILITY or
+ * FITNESS FOR A PARTICULAR PURPOSE. See the GNU General Public License for
+ * more details.
+ *
+ * You should have received a copy of the GNU General Public License along with
+ * RuneOptimizer. If not, see <https://www.gnu.org/licenses/>.
+ */
+
+int update_current_stats(){
+    printf("START\n");
+    sqlite3_stmt *stmt_unit;
+    db_query(
+      &stmt_unit,
+      "SELECT id, base_hp, base_atk, base_def, base_spd,"
+      "  base_crr, base_crd, base_res, base_acc,"
+      "  current_hp, current_atk, current_def, current_spd,"
+      "  current_crr, current_crd, current_res, current_acc"
+      " FROM units WHERE id IN (SELECT DISTINCT unit FROM runes)",
+      NULL
+    );
+    Unit unit;
+    while (SQLITE_ROW == sqlite3_step(stmt_unit)){
+        strcpy(unit.id, sqlite3_column_text(stmt_unit, 0));
+        unit.base_hp = sqlite3_column_int(stmt_unit, 1);
+        unit.base_atk = sqlite3_column_int(stmt_unit, 2);
+        unit.base_def = sqlite3_column_int(stmt_unit, 3);
+        unit.base_spd = sqlite3_column_int(stmt_unit, 4);
+        unit.base_crr = sqlite3_column_int(stmt_unit, 5);
+        unit.base_crd = sqlite3_column_int(stmt_unit, 6);
+        unit.base_res = sqlite3_column_int(stmt_unit, 7);
+        unit.base_acc = sqlite3_column_int(stmt_unit, 8);
+        unit.current_hp = unit.base_hp;
+        unit.current_atk = unit.base_atk;
+        unit.current_def = unit.base_def;
+        unit.current_spd = unit.base_spd;
+        unit.current_crr = unit.base_crr;
+        unit.current_crd = unit.base_crd;
+        unit.current_res = unit.base_res;
+        unit.current_acc = unit.base_acc;
+
+        // Loop runes and add flat and percent stats
+        // Also, count rune sets for bonus
+        Rune_Set_Count set_count = {
+          .energy = 0, .guard = 0, .swift = 0, .blade = 0, .rage = 0,
+          .focus = 0, .endure = 0, .fatal = 0, .despair = 0, .vampire = 0,
+          .violent = 0, .nemesis = 0, .will = 0, .shield = 0, .revenge = 0,
+          .destroy = 0, .fight = 0, .determination = 0, .enhance = 0,
+          .accuracy = 0, .tolerance = 0,
+        };
+        sqlite3_stmt *stmt_runes;
+        char *parameters[1];
+        parameters[0] = unit.id;
+        db_query(
+          &stmt_runes,
+          "SELECT type,"
+          "  current_hp_flat, current_atk_flat, current_def_flat,"
+          "  current_hp_percent, current_atk_percent, current_def_percent,"
+          "  current_spd, current_crr, current_crd, current_res, current_acc, "
+          "  slot"
+          " FROM runes WHERE unit = ?",
+          parameters
+        );
+        while (SQLITE_ROW == sqlite3_step(stmt_runes)){
+            // Switch the rune set
+            switch (sqlite3_column_int(stmt_runes, 0)){
+                case ENERGY: set_count.energy ++; break;
+                case GUARD: set_count.guard ++; break;
+                case SWIFT: set_count.swift ++; break;
+                case BLADE: set_count.blade ++; break;
+                case RAGE: set_count.rage ++; break;
+                case FOCUS: set_count.focus ++; break;
+                case ENDURE: set_count.endure ++; break;
+                case FATAL: set_count.fatal ++; break;
+                case DESPAIR: set_count.despair ++; break;
+                case VAMPIRE: set_count.vampire ++; break;
+                case VIOLENT: set_count.violent ++; break;
+                case NEMESIS: set_count.nemesis ++; break;
+                case WILL: set_count.will ++; break;
+                case SHIELD: set_count.shield ++; break;
+                case REVENGE: set_count.revenge ++; break;
+                case DESTROY: set_count.destroy ++; break;
+                case FIGHT: set_count.fight ++; break;
+                case DETERMINATION: set_count.determination ++; break;
+                case ENHANCE: set_count.enhance ++; break;
+                case ACCURACY: set_count.accuracy ++; break;
+                case TOLERANCE: set_count.tolerance ++; break;
+            }
+
+            //Add rune values
+            unit.current_hp += sqlite3_column_int(stmt_runes, 1);
+            unit.current_atk += sqlite3_column_int(stmt_runes, 2);
+            unit.current_def += sqlite3_column_int(stmt_runes, 3);
+            unit.current_hp +=
+              unit.base_hp * sqlite3_column_int(stmt_runes, 4) / 100;
+            unit.current_atk +=
+              unit.base_atk * sqlite3_column_int(stmt_runes, 5) / 100;
+            unit.current_def +=
+              unit.base_def * sqlite3_column_int(stmt_runes, 6) / 100;
+            unit.current_spd += sqlite3_column_int(stmt_runes, 7);
+            unit.current_crr += sqlite3_column_int(stmt_runes, 8);
+            unit.current_crd += sqlite3_column_int(stmt_runes, 9);
+            unit.current_res += sqlite3_column_int(stmt_runes, 10);
+            unit.current_acc += sqlite3_column_int(stmt_runes, 11);
+        }
+        sqlite3_finalize(stmt_runes);
+
+        // Rune set bonuses
+        if (set_count.energy >= 2) // +15% Base HP per set of 2
+            unit.current_hp += unit.base_hp * 0.15 * (set_count.energy % 2);
+        if (set_count.guard >= 2) // +15% base DEF per set of 2
+            unit.current_def += unit.base_def * 0.15 * (set_count.guard % 2);
+        if (set_count.swift >= 4) // +25% base SPD per set of 4
+            unit.current_spd += unit.base_spd * 0.25;
+        if (set_count.blade >= 2) // +12% CRR per set of 2
+            unit.current_crr += 12;
+        if (set_count.rage >= 4) // +40% CRD per set of 4
+            unit.current_crd += 40;
+        if (set_count.focus >= 2) // +20% ACC per set of 2
+            unit.current_acc += 20;
+        if (set_count.endure >= 2) // +20% RES per set of 2
+            unit.current_res += 20;
+        if (set_count.fatal >= 4) // +35% base ATK per set of 4
+            unit.current_atk += unit.base_atk * 0.35;
+        if (set_count.fight >= 2) // +8% base ATK per set of 2
+            unit.current_atk += unit.base_atk * 0.08 * (set_count.fight % 2);
+        if (set_count.determination >= 2) // +8% base DEF per set of 2
+            unit.current_def +=
+              unit.base_def * 0.08 * (set_count.determination % 2);
+        if (set_count.enhance >= 2) // +8% base HP per set of 2
+            unit.current_hp += unit.base_hp * 0.08 * (set_count.enhance % 2);
+        if (set_count.accuracy >= 2) // +10% ACC per set of 2
+            unit.current_acc += 20;
+        if (set_count.tolerance >= 2) // +10% RES per set of 2
+            unit.current_res += 20;
+
+        // Cap limited stats
+        if (unit.current_crr > 100) unit.current_crr = 100;
+        if (unit.current_res > 100) unit.current_res = 100;
+        if (unit.current_acc > 85) unit.current_acc = 85;
+
+        // Update in database
+        char *parameters_update[9];
+        for (int i = 0; i < 9; i ++){
+            parameters_update[i] = malloc(5);
+        }
+        sprintf(parameters_update[0], "%d", unit.current_hp);
+        sprintf(parameters_update[1], "%d", unit.current_atk);
+        sprintf(parameters_update[2], "%d", unit.current_def);
+        sprintf(parameters_update[3], "%d", unit.current_spd);
+        sprintf(parameters_update[4], "%d", unit.current_crr);
+        sprintf(parameters_update[5], "%d", unit.current_crd);
+        sprintf(parameters_update[6], "%d", unit.current_res);
+        sprintf(parameters_update[7], "%d", unit.current_acc);
+        parameters_update[8] = unit.id;
+        if (
+          SUCCESS !=
+          db_execute(
+            "UPDATE units SET"
+            "  current_hp = ?, current_atk = ?, current_def = ?, "
+            "  current_spd = ?, current_crr = ?, current_crd = ?,"
+            "  current_res = ?, current_acc = ? "
+            "WHERE id = ?",
+            parameters_update
+          )
+        ){
+            fprintf(
+              stderr, "Unable to undate unit info: %s\n", sqlite3_errmsg(db)
+            );
+            return ERROR_DB_UPDATE_UNITS;
+        }
+    }
+    sqlite3_finalize(stmt_unit);
+    printf("END\n");
+    return SUCCESS;
+}

+ 208 - 0
src/RuneOptimizer/update/update_db_tables.c

@@ -0,0 +1,208 @@
+/*
+ * This file is part of RuneOptimizer.
+ *
+ * RuneOptimizer is free software: you can redistribute it and/or modify it
+ * under the terms of the GNU General Public License as published by the Free
+ * Software Foundation, either version 3 of the License, or (at your option)
+ * any later version.
+ *
+ * RuneOptimizer is distributed in the hope that it will be useful, but WITHOUT
+ * ANY WARRANTY; without even the implied warranty of MERCHANTABILITY or
+ * FITNESS FOR A PARTICULAR PURPOSE. See the GNU General Public License for
+ * more details.
+ *
+ * You should have received a copy of the GNU General Public License along with
+ * RuneOptimizer. If not, see <https://www.gnu.org/licenses/>.
+ */
+
+int update_db_tables(unsigned char clear_teams){
+
+    // Drop all tables
+    char table_names[6][11] = {
+      "rune_stats", "runes", "units", "info", "teams", "units_teams"
+    };
+    char query_drop[64];
+    int tables_to_drop = 4;
+    // By default, only drop the first 6 tables. If clear teams flag, all 6.
+    if (clear_teams == TRUE){
+        tables_to_drop = 6;
+    }
+    for (int i = 0; i < tables_to_drop; i ++){
+        sprintf(query_drop, "DROP TABLE IF EXISTS %s;", table_names[i]);
+        if (SUCCESS != db_execute(query_drop, NULL)){
+            fprintf(
+              stderr, "Unable to drop table %s: %s\n",
+              table_names[i], sqlite3_errmsg(db)
+            );
+            return ERROR_DB_DROP;
+        }
+    }
+
+    // Table rune_stats
+    if (
+      SUCCESS !=
+      db_execute(
+        "CREATE TABLE IF NOT EXISTS rune_stats("
+        "  rune CHAR(12), slot INT, stat INT, value INT, grind INT, enchant INT"
+        ");",
+        NULL
+      )
+    ){
+        fprintf(
+          stderr,
+          "Unable to create table rune_stats: %s\n", sqlite3_errmsg(db)
+        );
+        return ERROR_DB_CREATE_RUNE_STATS;
+    }
+
+    // Table runes
+    if (
+      SUCCESS !=
+      db_execute(
+        "CREATE TABLE IF NOT EXISTS runes("
+        "  id CHAR(12),"
+        "  unit CHAR(12),"
+        "  type INT,"
+        "  slot INT,"
+        "  stars INT,"
+        "  level INT,"
+        "  quality INT,"
+        "  efficiency FLOAT,"
+        "  max_efficiency FLOAT,"
+        "  main_stat INT,"
+        "  current_hp_percent INT,"
+        "  current_atk_percent INT,"
+        "  current_def_percent INT,"
+        "  current_hp_flat INT,"
+        "  current_atk_flat INT,"
+        "  current_def_flat INT,"
+        "  current_spd INT,"
+        "  current_crr INT,"
+        "  current_crd INT,"
+        "  current_acc INT,"
+        "  current_res INT,"
+        "  lv12_hp_percent INT,"
+        "  lv12_atk_percent INT,"
+        "  lv12_def_percent INT,"
+        "  lv12_hp_flat INT,"
+        "  lv12_atk_flat INT,"
+        "  lv12_def_flat INT,"
+        "  lv12_spd INT,"
+        "  lv12_crr INT,"
+        "  lv12_crd INT,"
+        "  lv12_acc INT,"
+        "  lv12_res INT,"
+        "  lv15_hp_percent INT,"
+        "  lv15_atk_percent INT,"
+        "  lv15_def_percent INT,"
+        "  lv15_hp_flat INT,"
+        "  lv15_atk_flat INT,"
+        "  lv15_def_flat INT,"
+        "  lv15_spd INT,"
+        "  lv15_crr INT,"
+        "  lv15_crd INT,"
+        "  lv15_acc INT,"
+        "  lv15_res INT"
+        ");",
+        NULL
+      )
+    ){
+        fprintf(
+          stderr, "Unable to create table runes: %s\n", sqlite3_errmsg(db)
+        );
+        return ERROR_DB_CREATE_RUNES;
+    }
+
+    // Table units
+    if (
+      SUCCESS !=
+      db_execute(
+        "CREATE TABLE IF NOT EXISTS units("
+        "  id CHAR(12),"
+        "  monster INT,"
+        "  name CHAR(128),"
+        "  stars INT,"
+        "  level INT,"
+        "  storage INT,"
+        "  base_hp INT,"
+        "  base_atk INT,"
+        "  base_def INT,"
+        "  base_spd INT,"
+        "  base_crr INT,"
+        "  base_crd INT,"
+        "  base_res INT,"
+        "  base_acc INT,"
+        "  current_hp INT,"
+        "  current_atk INT,"
+        "  current_def INT,"
+        "  current_spd INT,"
+        "  current_crr INT,"
+        "  current_crd INT,"
+        "  current_res INT,"
+        "  current_acc INT"
+        ");",
+        NULL
+      )
+    ){
+        fprintf(
+          stderr,
+          "Unable to create table units: %s\n", sqlite3_errmsg(db)
+        );
+        return ERROR_DB_CREATE_UNITS;
+    }
+
+    // Table info
+    if (
+      SUCCESS !=
+      db_execute(
+        "CREATE TABLE IF NOT EXISTS info("
+        "  player_id CHAR(12),"
+        "  player_name CHAR(64),"
+        "  player_level INT,"
+        "  ts DATETIME,"
+        "  modified INT"
+        ");",
+        NULL
+      )
+    ){
+        fprintf(
+          stderr,
+          "Unable to create table info: %s\n", sqlite3_errmsg(db)
+        );
+        return ERROR_DB_CREATE_INFO;
+    }
+
+    // Tables teams and units_teams (optional)
+    if (clear_teams == TRUE){
+        if (
+          SUCCESS !=
+          db_execute(
+            "CREATE TABLE IF NOT EXISTS "
+            "units_teams(unit CHAR(12), team CHAR(12));",
+            NULL
+          )
+        ){
+            fprintf(
+              stderr,
+              "Unable to create table units_teams: %s\n", sqlite3_errmsg(db)
+            );
+            return ERROR_DB_CREATE_UNITS_TEAMS;
+        }
+        if (
+          SUCCESS !=
+          db_execute(
+            "CREATE TABLE IF NOT EXISTS "
+            "teams(unit CHAR(12), name CHAR(50), priority INT);",
+            NULL
+          )
+        ){
+            fprintf(
+              stderr,
+              "Unable to create table teams: %s\n", sqlite3_errmsg(db)
+            );
+            return ERROR_DB_CREATE_TEAMS;
+        }
+    }
+
+    return SUCCESS;
+}

+ 1905 - 0
src/RuneOptimizer/update/update_get_monster_name.c

@@ -0,0 +1,1905 @@
+/*
+ * This file is part of RuneOptimizer.
+ *
+ * RuneOptimizer is free software: you can redistribute it and/or modify it
+ * under the terms of the GNU General Public License as published by the Free
+ * Software Foundation, either version 3 of the License, or (at your option)
+ * any later version.
+ *
+ * RuneOptimizer is distributed in the hope that it will be useful, but WITHOUT
+ * ANY WARRANTY; without even the implied warranty of MERCHANTABILITY or
+ * FITNESS FOR A PARTICULAR PURPOSE. See the GNU General Public License for
+ * more details.
+ *
+ * You should have received a copy of the GNU General Public License along with
+ * RuneOptimizer. If not, see <https://www.gnu.org/licenses/>.
+ */
+
+void update_get_monster_name(int id, char name[64]){
+    
+    /*
+     * This list is generated from a SWDB database, with the query:
+     * SELECT (
+     *   'case ' || id || ': strcpy(name, "' ||
+     *   CASE
+     *     WHEN awakens_from IS NULL THEN
+     *       substr(name, 0, 55) ||
+     *       " (" ||
+     *       (SELECT name FROM element WHERE id = monster.element) ||
+     *       ")"
+     *     WHEN awakens_from IS NOT NULL AND base_stars - natural_stars > 1 THEN
+     *       substr(name, 0, 58) || " (2A)"
+     *     ELSE substr(name, 0, 63) END
+     *   || '"); break;'
+     * ) AS t FROM monster;
+     */
+
+    switch(id){
+        case 10102: strcpy(name, "Fairy (Fire)"); break;
+        case 10103: strcpy(name, "Fairy (Wind)"); break;
+        case 10104: strcpy(name, "Fairy (Light)"); break;
+        case 10105: strcpy(name, "Fairy (Dark)"); break;
+        case 10111: strcpy(name, "Elucia"); break;
+        case 10112: strcpy(name, "Iselia"); break;
+        case 10113: strcpy(name, "Aeilene"); break;
+        case 10114: strcpy(name, "Neal"); break;
+        case 10115: strcpy(name, "Sorin"); break;
+        case 10131: strcpy(name, "Elucia (2A)"); break;
+        case 10132: strcpy(name, "Iselia (2A)"); break;
+        case 10133: strcpy(name, "Aeilene (2A)"); break;
+        case 10134: strcpy(name, "Neal (2A)"); break;
+        case 10135: strcpy(name, "Sorin (2A)"); break;
+        case 10201: strcpy(name, "Imp (Water)"); break;
+        case 10202: strcpy(name, "Imp (Fire)"); break;
+        case 10203: strcpy(name, "Imp (Wind)"); break;
+        case 10204: strcpy(name, "Imp (Light)"); break;
+        case 10205: strcpy(name, "Imp (Dark)"); break;
+        case 10211: strcpy(name, "Fynn"); break;
+        case 10212: strcpy(name, "Cogma"); break;
+        case 10213: strcpy(name, "Ralph"); break;
+        case 10214: strcpy(name, "Taru"); break;
+        case 10215: strcpy(name, "Garok"); break;
+        case 10301: strcpy(name, "Pixie (Water)"); break;
+        case 10302: strcpy(name, "Pixie (Fire)"); break;
+        case 10303: strcpy(name, "Pixie (Wind)"); break;
+        case 10304: strcpy(name, "Pixie (Light)"); break;
+        case 10305: strcpy(name, "Pixie (Dark)"); break;
+        case 10311: strcpy(name, "Kacey"); break;
+        case 10312: strcpy(name, "Tatu"); break;
+        case 10313: strcpy(name, "Shannon"); break;
+        case 10314: strcpy(name, "Cheryl"); break;
+        case 10315: strcpy(name, "Camaryn"); break;
+        case 10331: strcpy(name, "Kacey (2A)"); break;
+        case 10332: strcpy(name, "Tatu (2A)"); break;
+        case 10333: strcpy(name, "Shannon (2A)"); break;
+        case 10334: strcpy(name, "Cheryl (2A)"); break;
+        case 10335: strcpy(name, "Camaryn (2A)"); break;
+        case 10401: strcpy(name, "Yeti (Water)"); break;
+        case 10402: strcpy(name, "Yeti (Fire)"); break;
+        case 10403: strcpy(name, "Yeti (Wind)"); break;
+        case 10404: strcpy(name, "Yeti (Light)"); break;
+        case 10405: strcpy(name, "Yeti (Dark)"); break;
+        case 10411: strcpy(name, "Kunda"); break;
+        case 10412: strcpy(name, "Tantra"); break;
+        case 10413: strcpy(name, "Rakaja"); break;
+        case 10414: strcpy(name, "Arkajan"); break;
+        case 10415: strcpy(name, "Kumae"); break;
+        case 10501: strcpy(name, "Harpy (Water)"); break;
+        case 10502: strcpy(name, "Harpy (Fire)"); break;
+        case 10503: strcpy(name, "Harpy (Wind)"); break;
+        case 10504: strcpy(name, "Harpy (Light)"); break;
+        case 10505: strcpy(name, "Harpy (Dark)"); break;
+        case 10511: strcpy(name, "Ramira"); break;
+        case 10512: strcpy(name, "Lucasha"); break;
+        case 10513: strcpy(name, "Prilea"); break;
+        case 10514: strcpy(name, "Kabilla"); break;
+        case 10515: strcpy(name, "Hellea"); break;
+        case 10601: strcpy(name, "Hellhound (Water)"); break;
+        case 10602: strcpy(name, "Hellhound (Fire)"); break;
+        case 10603: strcpy(name, "Hellhound (Wind)"); break;
+        case 10604: strcpy(name, "Hellhound (Light)"); break;
+        case 10605: strcpy(name, "Hellhound (Dark)"); break;
+        case 10611: strcpy(name, "Tarq"); break;
+        case 10612: strcpy(name, "Sieq"); break;
+        case 10613: strcpy(name, "Gamir"); break;
+        case 10614: strcpy(name, "Shamar"); break;
+        case 10615: strcpy(name, "Shumar"); break;
+        case 10701: strcpy(name, "Warbear (Water)"); break;
+        case 10702: strcpy(name, "Warbear (Fire)"); break;
+        case 10703: strcpy(name, "Warbear (Wind)"); break;
+        case 10704: strcpy(name, "Warbear (Light)"); break;
+        case 10705: strcpy(name, "Warbear (Dark)"); break;
+        case 10711: strcpy(name, "Dagora"); break;
+        case 10712: strcpy(name, "Ursha"); break;
+        case 10713: strcpy(name, "Ramagos"); break;
+        case 10714: strcpy(name, "Lusha"); break;
+        case 10715: strcpy(name, "Gorgo"); break;
+        case 10731: strcpy(name, "Dagora (2A)"); break;
+        case 10732: strcpy(name, "Ursha (2A)"); break;
+        case 10733: strcpy(name, "Ramagos (2A)"); break;
+        case 10734: strcpy(name, "Lusha (2A)"); break;
+        case 10735: strcpy(name, "Gorgo (2A)"); break;
+        case 10801: strcpy(name, "Elemental (Water)"); break;
+        case 10802: strcpy(name, "Elemental (Fire)"); break;
+        case 10803: strcpy(name, "Elemental (Wind)"); break;
+        case 10804: strcpy(name, "Elemental (Light)"); break;
+        case 10805: strcpy(name, "Elemental (Dark)"); break;
+        case 10811: strcpy(name, "Daharenos"); break;
+        case 10812: strcpy(name, "Bremis"); break;
+        case 10813: strcpy(name, "Taharus"); break;
+        case 10814: strcpy(name, "Priz"); break;
+        case 10815: strcpy(name, "Camules"); break;
+        case 10901: strcpy(name, "Garuda (Water)"); break;
+        case 10902: strcpy(name, "Garuda (Fire)"); break;
+        case 10903: strcpy(name, "Garuda (Wind)"); break;
+        case 10904: strcpy(name, "Garuda (Light)"); break;
+        case 10905: strcpy(name, "Garuda (Dark)"); break;
+        case 10911: strcpy(name, "Konamiya"); break;
+        case 10912: strcpy(name, "Cahule"); break;
+        case 10913: strcpy(name, "Lindermen"); break;
+        case 10914: strcpy(name, "Teon"); break;
+        case 10915: strcpy(name, "Rizak"); break;
+        case 11001: strcpy(name, "Inugami (Water)"); break;
+        case 11002: strcpy(name, "Inugami (Fire)"); break;
+        case 11003: strcpy(name, "Inugami (Wind)"); break;
+        case 11004: strcpy(name, "Inugami (Light)"); break;
+        case 11005: strcpy(name, "Inugami (Dark)"); break;
+        case 11011: strcpy(name, "Icaru"); break;
+        case 11012: strcpy(name, "Raoq"); break;
+        case 11013: strcpy(name, "Ramahan"); break;
+        case 11014: strcpy(name, "Belladeon"); break;
+        case 11015: strcpy(name, "Kro"); break;
+        case 11031: strcpy(name, "Icaru (2A)"); break;
+        case 11032: strcpy(name, "Raoq (2A)"); break;
+        case 11033: strcpy(name, "Ramahan (2A)"); break;
+        case 11034: strcpy(name, "Belladeon (2A)"); break;
+        case 11035: strcpy(name, "Kro (2A)"); break;
+        case 11101: strcpy(name, "Salamander (Water)"); break;
+        case 11102: strcpy(name, "Salamander (Fire)"); break;
+        case 11103: strcpy(name, "Salamander (Wind)"); break;
+        case 11104: strcpy(name, "Salamander (Light)"); break;
+        case 11105: strcpy(name, "Salamander (Dark)"); break;
+        case 11111: strcpy(name, "Kaimann"); break;
+        case 11112: strcpy(name, "Krakdon"); break;
+        case 11113: strcpy(name, "Lukan"); break;
+        case 11114: strcpy(name, "Sharman"); break;
+        case 11115: strcpy(name, "Decamaron"); break;
+        case 11201: strcpy(name, "Nine-tailed Fox (Water)"); break;
+        case 11202: strcpy(name, "Nine-tailed Fox (Fire)"); break;
+        case 11203: strcpy(name, "Nine-tailed Fox"); break;
+        case 11204: strcpy(name, "Nine-tailed Fox (Light)"); break;
+        case 11205: strcpy(name, "Nine-tailed Fox (Dark)"); break;
+        case 11211: strcpy(name, "Soha"); break;
+        case 11212: strcpy(name, "Shihwa"); break;
+        case 11213: strcpy(name, "Arang"); break;
+        case 11214: strcpy(name, "Chamie"); break;
+        case 11215: strcpy(name, "Kamiya"); break;
+        case 11223: strcpy(name, "Imperfect Nine-tailed Fox (Wind)"); break;
+        case 11301: strcpy(name, "Serpent (Water)"); break;
+        case 11302: strcpy(name, "Serpent (Fire)"); break;
+        case 11303: strcpy(name, "Serpent (Wind)"); break;
+        case 11304: strcpy(name, "Serpent (Light)"); break;
+        case 11305: strcpy(name, "Serpent (Dark)"); break;
+        case 11311: strcpy(name, "Shailoq"); break;
+        case 11312: strcpy(name, "Fao"); break;
+        case 11313: strcpy(name, "Ermeda"); break;
+        case 11314: strcpy(name, "Elpuria"); break;
+        case 11315: strcpy(name, "Mantura"); break;
+        case 11401: strcpy(name, "Golem (Water)"); break;
+        case 11402: strcpy(name, "Golem (Fire)"); break;
+        case 11403: strcpy(name, "Golem (Wind)"); break;
+        case 11404: strcpy(name, "Golem (Light)"); break;
+        case 11405: strcpy(name, "Golem (Dark)"); break;
+        case 11411: strcpy(name, "Kuhn"); break;
+        case 11412: strcpy(name, "Kugo"); break;
+        case 11413: strcpy(name, "Ragion"); break;
+        case 11414: strcpy(name, "Groggo"); break;
+        case 11415: strcpy(name, "Maggi"); break;
+        case 11501: strcpy(name, "Griffon (Water)"); break;
+        case 11502: strcpy(name, "Griffon (Fire)"); break;
+        case 11503: strcpy(name, "Griffon (Wind)"); break;
+        case 11504: strcpy(name, "Griffon (Light)"); break;
+        case 11505: strcpy(name, "Griffon (Dark)"); break;
+        case 11511: strcpy(name, "Kahn"); break;
+        case 11512: strcpy(name, "Spectra"); break;
+        case 11513: strcpy(name, "Bernard"); break;
+        case 11514: strcpy(name, "Shamann"); break;
+        case 11515: strcpy(name, "Varus"); break;
+        case 11531: strcpy(name, "Kahn (2A)"); break;
+        case 11532: strcpy(name, "Spectra (2A)"); break;
+        case 11533: strcpy(name, "Bernard (2A)"); break;
+        case 11534: strcpy(name, "Shamann (2A)"); break;
+        case 11535: strcpy(name, "Varus (2A)"); break;
+        case 11601: strcpy(name, "Undine"); break;
+        case 11602: strcpy(name, "Undine (Fire)"); break;
+        case 11603: strcpy(name, "Undine (Wind)"); break;
+        case 11604: strcpy(name, "Undine (Light)"); break;
+        case 11605: strcpy(name, "Undine (Dark)"); break;
+        case 11611: strcpy(name, "Mikene"); break;
+        case 11612: strcpy(name, "Atenai"); break;
+        case 11613: strcpy(name, "Delphoi"); break;
+        case 11614: strcpy(name, "Icasha"); break;
+        case 11615: strcpy(name, "Tilasha"); break;
+        case 11621: strcpy(name, "Imperfect Undine (Water)"); break;
+        case 11701: strcpy(name, "Inferno (Water)"); break;
+        case 11702: strcpy(name, "Inferno (Fire)"); break;
+        case 11703: strcpy(name, "Inferno (Wind)"); break;
+        case 11704: strcpy(name, "Inferno (Light)"); break;
+        case 11705: strcpy(name, "Inferno (Dark)"); break;
+        case 11711: strcpy(name, "Purian"); break;
+        case 11712: strcpy(name, "Tagaros"); break;
+        case 11713: strcpy(name, "Anduril"); break;
+        case 11714: strcpy(name, "Eludain"); break;
+        case 11715: strcpy(name, "Drogan"); break;
+        case 11801: strcpy(name, "Sylph (Water)"); break;
+        case 11802: strcpy(name, "Sylph"); break;
+        case 11803: strcpy(name, "Sylph (Wind)"); break;
+        case 11804: strcpy(name, "Sylph (Light)"); break;
+        case 11805: strcpy(name, "Sylph (Dark)"); break;
+        case 11811: strcpy(name, "Tyron"); break;
+        case 11812: strcpy(name, "Baretta"); break;
+        case 11813: strcpy(name, "Shimitae"); break;
+        case 11814: strcpy(name, "Eredas"); break;
+        case 11815: strcpy(name, "Aschubel"); break;
+        case 11822: strcpy(name, "Imperfect Sylph (Fire)"); break;
+        case 11901: strcpy(name, "Sylphid (Water)"); break;
+        case 11902: strcpy(name, "Sylphid (Fire)"); break;
+        case 11903: strcpy(name, "Sylphid (Wind)"); break;
+        case 11904: strcpy(name, "Sylphid (Light)"); break;
+        case 11905: strcpy(name, "Sylphid (Dark)"); break;
+        case 11911: strcpy(name, "Lumirecia"); break;
+        case 11912: strcpy(name, "Fria"); break;
+        case 11913: strcpy(name, "Acasis"); break;
+        case 11914: strcpy(name, "Mihael"); break;
+        case 11915: strcpy(name, "Icares"); break;
+        case 12001: strcpy(name, "High Elemental (Water)"); break;
+        case 12002: strcpy(name, "High Elemental (Fire)"); break;
+        case 12003: strcpy(name, "High Elemental (Wind)"); break;
+        case 12004: strcpy(name, "High Elemental (Light)"); break;
+        case 12005: strcpy(name, "High Elemental (Dark)"); break;
+        case 12011: strcpy(name, "Ellena"); break;
+        case 12012: strcpy(name, "Kahli"); break;
+        case 12013: strcpy(name, "Moria"); break;
+        case 12014: strcpy(name, "Shren"); break;
+        case 12015: strcpy(name, "Jumaline"); break;
+        case 12101: strcpy(name, "Harpu (Water)"); break;
+        case 12102: strcpy(name, "Harpu (Fire)"); break;
+        case 12103: strcpy(name, "Harpu (Wind)"); break;
+        case 12104: strcpy(name, "Harpu (Light)"); break;
+        case 12105: strcpy(name, "Harpu (Dark)"); break;
+        case 12111: strcpy(name, "Sisroo"); break;
+        case 12112: strcpy(name, "Colleen"); break;
+        case 12113: strcpy(name, "Seal"); break;
+        case 12114: strcpy(name, "Sia"); break;
+        case 12115: strcpy(name, "Seren"); break;
+        case 12201: strcpy(name, "Slime (Water)"); break;
+        case 12202: strcpy(name, "Slime (Fire)"); break;
+        case 12203: strcpy(name, "Slime (Wind)"); break;
+        case 12301: strcpy(name, "Forest Keeper (Water)"); break;
+        case 12302: strcpy(name, "Forest Keeper (Fire)"); break;
+        case 12303: strcpy(name, "Forest Keeper (Wind)"); break;
+        case 12401: strcpy(name, "Mushroom (Water)"); break;
+        case 12402: strcpy(name, "Mushroom (Fire)"); break;
+        case 12403: strcpy(name, "Mushroom (Wind)"); break;
+        case 12501: strcpy(name, "Maned Boar (Water)"); break;
+        case 12502: strcpy(name, "Maned Boar (Fire)"); break;
+        case 12503: strcpy(name, "Maned Boar (Wind)"); break;
+        case 12601: strcpy(name, "Monster Flower (Water)"); break;
+        case 12602: strcpy(name, "Monster Flower (Fire)"); break;
+        case 12603: strcpy(name, "Monster Flower (Wind)"); break;
+        case 12605: strcpy(name, "Monster Flower (Dark)"); break;
+        case 12701: strcpy(name, "Ghost (Water)"); break;
+        case 12702: strcpy(name, "Ghost (Fire)"); break;
+        case 12703: strcpy(name, "Ghost (Wind)"); break;
+        case 12705: strcpy(name, "Ghost (Dark)"); break;
+        case 12801: strcpy(name, "Low Elemental (Water)"); break;
+        case 12802: strcpy(name, "Low Elemental (Fire)"); break;
+        case 12803: strcpy(name, "Low Elemental (Wind)"); break;
+        case 12804: strcpy(name, "Low Elemental (Light)"); break;
+        case 12805: strcpy(name, "Low Elemental (Dark)"); break;
+        case 12811: strcpy(name, "Tigresse"); break;
+        case 12812: strcpy(name, "Lamor"); break;
+        case 12813: strcpy(name, "Samour"); break;
+        case 12814: strcpy(name, "Varis"); break;
+        case 12815: strcpy(name, "Havana"); break;
+        case 12901: strcpy(name, "Mimick (Water)"); break;
+        case 12902: strcpy(name, "Mimick (Fire)"); break;
+        case 12903: strcpy(name, "Mimick (Wind)"); break;
+        case 12905: strcpy(name, "Mimick (Dark)"); break;
+        case 13001: strcpy(name, "Horned Frog (Water)"); break;
+        case 13002: strcpy(name, "Horned Frog (Fire)"); break;
+        case 13003: strcpy(name, "Horned Frog (Wind)"); break;
+        case 13005: strcpy(name, "Horned Frog (Dark)"); break;
+        case 13101: strcpy(name, "Sandman (Water)"); break;
+        case 13102: strcpy(name, "Sandman (Fire)"); break;
+        case 13103: strcpy(name, "Sandman (Wind)"); break;
+        case 13105: strcpy(name, "Sandman (Dark)"); break;
+        case 13201: strcpy(name, "Howl (Water)"); break;
+        case 13202: strcpy(name, "Howl (Fire)"); break;
+        case 13203: strcpy(name, "Howl (Wind)"); break;
+        case 13204: strcpy(name, "Howl (Light)"); break;
+        case 13205: strcpy(name, "Howl (Dark)"); break;
+        case 13211: strcpy(name, "Lulu"); break;
+        case 13212: strcpy(name, "Lala"); break;
+        case 13213: strcpy(name, "Chichi"); break;
+        case 13214: strcpy(name, "Shushu"); break;
+        case 13215: strcpy(name, "Chacha"); break;
+        case 13301: strcpy(name, "Succubus (Water)"); break;
+        case 13302: strcpy(name, "Succubus"); break;
+        case 13303: strcpy(name, "Succubus (Wind)"); break;
+        case 13304: strcpy(name, "Succubus (Light)"); break;
+        case 13305: strcpy(name, "Succubus (Dark)"); break;
+        case 13311: strcpy(name, "Izaria"); break;
+        case 13312: strcpy(name, "Akia"); break;
+        case 13313: strcpy(name, "Selena"); break;
+        case 13314: strcpy(name, "Aria"); break;
+        case 13315: strcpy(name, "Isael"); break;
+        case 13322: strcpy(name, "Imperfect Succubus (Fire)"); break;
+        case 13401: strcpy(name, "Joker (Water)"); break;
+        case 13402: strcpy(name, "Joker"); break;
+        case 13403: strcpy(name, "Joker (Wind)"); break;
+        case 13404: strcpy(name, "Joker (Light)"); break;
+        case 13405: strcpy(name, "Joker (Dark)"); break;
+        case 13411: strcpy(name, "Sian"); break;
+        case 13412: strcpy(name, "Jojo"); break;
+        case 13413: strcpy(name, "Lushen"); break;
+        case 13414: strcpy(name, "Figaro"); break;
+        case 13415: strcpy(name, "Liebli"); break;
+        case 13422: strcpy(name, "Imperfect Joker (Fire)"); break;
+        case 13501: strcpy(name, "Ninja"); break;
+        case 13502: strcpy(name, "Ninja (Fire)"); break;
+        case 13503: strcpy(name, "Ninja (Wind)"); break;
+        case 13504: strcpy(name, "Ninja (Light)"); break;
+        case 13505: strcpy(name, "Ninja (Dark)"); break;
+        case 13511: strcpy(name, "Susano"); break;
+        case 13512: strcpy(name, "Garo"); break;
+        case 13513: strcpy(name, "Orochi"); break;
+        case 13514: strcpy(name, "Gin"); break;
+        case 13515: strcpy(name, "Han"); break;
+        case 13521: strcpy(name, "Imperfect Ninja (Water)"); break;
+        case 13601: strcpy(name, "Surprise Box (Water)"); break;
+        case 13602: strcpy(name, "Surprise Box (Fire)"); break;
+        case 13603: strcpy(name, "Surprise Box (Wind)"); break;
+        case 13604: strcpy(name, "Surprise Box (Light)"); break;
+        case 13605: strcpy(name, "Surprise Box (Dark)"); break;
+        case 13701: strcpy(name, "Bearman (Water)"); break;
+        case 13702: strcpy(name, "Bearman (Fire)"); break;
+        case 13703: strcpy(name, "Bearman (Wind)"); break;
+        case 13704: strcpy(name, "Bearman (Light)"); break;
+        case 13705: strcpy(name, "Bearman (Dark)"); break;
+        case 13711: strcpy(name, "Gruda"); break;
+        case 13712: strcpy(name, "Kungen"); break;
+        case 13713: strcpy(name, "Dagorr"); break;
+        case 13714: strcpy(name, "Ahman"); break;
+        case 13715: strcpy(name, "Haken"); break;
+        case 13801: strcpy(name, "Valkyrja (Water)"); break;
+        case 13802: strcpy(name, "Valkyrja (Fire)"); break;
+        case 13803: strcpy(name, "Valkyrja (Wind)"); break;
+        case 13804: strcpy(name, "Valkyrja (Light)"); break;
+        case 13805: strcpy(name, "Valkyrja (Dark)"); break;
+        case 13811: strcpy(name, "Camilla"); break;
+        case 13812: strcpy(name, "Vanessa"); break;
+        case 13813: strcpy(name, "Katarina"); break;
+        case 13814: strcpy(name, "Akroma"); break;
+        case 13815: strcpy(name, "Trinity"); break;
+        case 13901: strcpy(name, "Pierret (Water)"); break;
+        case 13902: strcpy(name, "Pierret (Fire)"); break;
+        case 13903: strcpy(name, "Pierret (Wind)"); break;
+        case 13904: strcpy(name, "Pierret (Light)"); break;
+        case 13905: strcpy(name, "Pierret (Dark)"); break;
+        case 13911: strcpy(name, "Julie"); break;
+        case 13912: strcpy(name, "Clara"); break;
+        case 13913: strcpy(name, "Sophia"); break;
+        case 13914: strcpy(name, "Eva"); break;
+        case 13915: strcpy(name, "Luna"); break;
+        case 14001: strcpy(name, "Werewolf (Water)"); break;
+        case 14002: strcpy(name, "Werewolf (Fire)"); break;
+        case 14003: strcpy(name, "Werewolf (Wind)"); break;
+        case 14004: strcpy(name, "Werewolf (Light)"); break;
+        case 14005: strcpy(name, "Werewolf (Dark)"); break;
+        case 14011: strcpy(name, "Vigor"); break;
+        case 14012: strcpy(name, "Garoche"); break;
+        case 14013: strcpy(name, "Shakan"); break;
+        case 14014: strcpy(name, "Eshir"); break;
+        case 14015: strcpy(name, "Jultan"); break;
+        case 14031: strcpy(name, "Vigor (2A)"); break;
+        case 14032: strcpy(name, "Garoche (2A)"); break;
+        case 14033: strcpy(name, "Shakan (2A)"); break;
+        case 14034: strcpy(name, "Eshir (2A)"); break;
+        case 14035: strcpy(name, "Jultan (2A)"); break;
+        case 14101: strcpy(name, "Phantom Thief (Water)"); break;
+        case 14102: strcpy(name, "Phantom Thief (Fire)"); break;
+        case 14103: strcpy(name, "Phantom Thief (Wind)"); break;
+        case 14104: strcpy(name, "Phantom Thief (Light)"); break;
+        case 14105: strcpy(name, "Phantom Thief (Dark)"); break;
+        case 14111: strcpy(name, "Luer"); break;
+        case 14112: strcpy(name, "Jean"); break;
+        case 14113: strcpy(name, "Julien"); break;
+        case 14114: strcpy(name, "Louis"); break;
+        case 14115: strcpy(name, "Guillaume"); break;
+        case 14201: strcpy(name, "Angelmon (Water)"); break;
+        case 14202: strcpy(name, "Angelmon (Fire)"); break;
+        case 14203: strcpy(name, "Angelmon (Wind)"); break;
+        case 14204: strcpy(name, "Angelmon (Light)"); break;
+        case 14205: strcpy(name, "Angelmon (Dark)"); break;
+        case 14211: strcpy(name, "Blue Angelmon"); break;
+        case 14212: strcpy(name, "Red Angelmon"); break;
+        case 14213: strcpy(name, "Gold Angelmon"); break;
+        case 14214: strcpy(name, "White Angelmon"); break;
+        case 14215: strcpy(name, "Dark Angelmon"); break;
+        case 14314: strcpy(name, "Rainbowmon (Light)"); break;
+        case 14401: strcpy(name, "Dragon (Water)"); break;
+        case 14402: strcpy(name, "Dragon (Fire)"); break;
+        case 14403: strcpy(name, "Dragon (Wind)"); break;
+        case 14404: strcpy(name, "Dragon (Light)"); break;
+        case 14405: strcpy(name, "Dragon (Dark)"); break;
+        case 14411: strcpy(name, "Verad"); break;
+        case 14412: strcpy(name, "Zaiross"); break;
+        case 14413: strcpy(name, "Jamire"); break;
+        case 14414: strcpy(name, "Zerath"); break;
+        case 14415: strcpy(name, "Grogen"); break;
+        case 14501: strcpy(name, "Phoenix (Water)"); break;
+        case 14502: strcpy(name, "Phoenix (Fire)"); break;
+        case 14503: strcpy(name, "Phoenix (Wind)"); break;
+        case 14504: strcpy(name, "Phoenix (Light)"); break;
+        case 14505: strcpy(name, "Phoenix (Dark)"); break;
+        case 14511: strcpy(name, "Sigmarus"); break;
+        case 14512: strcpy(name, "Perna"); break;
+        case 14513: strcpy(name, "Teshar"); break;
+        case 14514: strcpy(name, "Eludia"); break;
+        case 14515: strcpy(name, "Jaara"); break;
+        case 14601: strcpy(name, "Chimera (Water)"); break;
+        case 14602: strcpy(name, "Chimera (Fire)"); break;
+        case 14603: strcpy(name, "Chimera (Wind)"); break;
+        case 14604: strcpy(name, "Chimera (Light)"); break;
+        case 14605: strcpy(name, "Chimera (Dark)"); break;
+        case 14611: strcpy(name, "Taor"); break;
+        case 14612: strcpy(name, "Rakan"); break;
+        case 14613: strcpy(name, "Lagmaron"); break;
+        case 14614: strcpy(name, "Shan"); break;
+        case 14615: strcpy(name, "Zeratu"); break;
+        case 14701: strcpy(name, "Vampire (Water)"); break;
+        case 14702: strcpy(name, "Vampire"); break;
+        case 14703: strcpy(name, "Vampire"); break;
+        case 14704: strcpy(name, "Vampire (Light)"); break;
+        case 14705: strcpy(name, "Vampire (Dark)"); break;
+        case 14711: strcpy(name, "Liesel"); break;
+        case 14712: strcpy(name, "Verdehile"); break;
+        case 14713: strcpy(name, "Argen"); break;
+        case 14714: strcpy(name, "Julianne"); break;
+        case 14715: strcpy(name, "Cadiz"); break;
+        case 14722: strcpy(name, "Imperfect Vampire (Fire)"); break;
+        case 14723: strcpy(name, "Imperfect Vampire (Wind)"); break;
+        case 14801: strcpy(name, "Viking (Water)"); break;
+        case 14802: strcpy(name, "Viking (Fire)"); break;
+        case 14803: strcpy(name, "Viking (Wind)"); break;
+        case 14804: strcpy(name, "Viking (Light)"); break;
+        case 14805: strcpy(name, "Viking (Dark)"); break;
+        case 14811: strcpy(name, "Huga"); break;
+        case 14812: strcpy(name, "Geoffrey"); break;
+        case 14813: strcpy(name, "Walter"); break;
+        case 14814: strcpy(name, "Jansson"); break;
+        case 14815: strcpy(name, "Janssen"); break;
+        case 14901: strcpy(name, "Amazon (Water)"); break;
+        case 14902: strcpy(name, "Amazon (Fire)"); break;
+        case 14903: strcpy(name, "Amazon (Wind)"); break;
+        case 14904: strcpy(name, "Amazon (Light)"); break;
+        case 14905: strcpy(name, "Amazon (Dark)"); break;
+        case 14911: strcpy(name, "Ellin"); break;
+        case 14912: strcpy(name, "Ceres"); break;
+        case 14913: strcpy(name, "Hina"); break;
+        case 14914: strcpy(name, "Lyn"); break;
+        case 14915: strcpy(name, "Mara"); break;
+        case 15001: strcpy(name, "Martial Cat (Water)"); break;
+        case 15002: strcpy(name, "Martial Cat (Fire)"); break;
+        case 15003: strcpy(name, "Martial Cat (Wind)"); break;
+        case 15004: strcpy(name, "Martial Cat (Light)"); break;
+        case 15005: strcpy(name, "Martial Cat (Dark)"); break;
+        case 15011: strcpy(name, "Mina"); break;
+        case 15012: strcpy(name, "Mei"); break;
+        case 15013: strcpy(name, "Naomi"); break;
+        case 15014: strcpy(name, "Xiao Ling"); break;
+        case 15015: strcpy(name, "Miho"); break;
+        case 15031: strcpy(name, "Mina (2A)"); break;
+        case 15032: strcpy(name, "Mei (2A)"); break;
+        case 15033: strcpy(name, "Naomi (2A)"); break;
+        case 15034: strcpy(name, "Xiao Ling (2A)"); break;
+        case 15035: strcpy(name, "Miho (2A)"); break;
+        case 15105: strcpy(name, "Devilmon (Dark)"); break;
+        case 15201: strcpy(name, "Vagabond (Water)"); break;
+        case 15202: strcpy(name, "Vagabond (Fire)"); break;
+        case 15203: strcpy(name, "Vagabond (Wind)"); break;
+        case 15204: strcpy(name, "Vagabond (Light)"); break;
+        case 15205: strcpy(name, "Vagabond (Dark)"); break;
+        case 15211: strcpy(name, "Allen"); break;
+        case 15212: strcpy(name, "Kai'en"); break;
+        case 15213: strcpy(name, "Roid"); break;
+        case 15214: strcpy(name, "Darion"); break;
+        case 15215: strcpy(name, "Jubelle"); break;
+        case 15301: strcpy(name, "Epikion Priest (Water)"); break;
+        case 15302: strcpy(name, "Epikion Priest (Fire)"); break;
+        case 15303: strcpy(name, "Epikion Priest (Wind)"); break;
+        case 15304: strcpy(name, "Epikion Priest (Light)"); break;
+        case 15305: strcpy(name, "Epikion Priest (Dark)"); break;
+        case 15311: strcpy(name, "Rina"); break;
+        case 15312: strcpy(name, "Chloe"); break;
+        case 15313: strcpy(name, "Michelle"); break;
+        case 15314: strcpy(name, "Iona"); break;
+        case 15315: strcpy(name, "Rasheed"); break;
+        case 15401: strcpy(name, "Magical Archer (Water)"); break;
+        case 15402: strcpy(name, "Magical Archer (Fire)"); break;
+        case 15403: strcpy(name, "Magical Archer (Wind)"); break;
+        case 15404: strcpy(name, "Magical Archer (Light)"); break;
+        case 15405: strcpy(name, "Magical Archer (Dark)"); break;
+        case 15411: strcpy(name, "Sharron"); break;
+        case 15412: strcpy(name, "Cassandra"); break;
+        case 15413: strcpy(name, "Ardella"); break;
+        case 15414: strcpy(name, "Chris"); break;
+        case 15415: strcpy(name, "Bethony"); break;
+        case 15501: strcpy(name, "Rakshasa (Water)"); break;
+        case 15502: strcpy(name, "Rakshasa (Fire)"); break;
+        case 15503: strcpy(name, "Rakshasa (Wind)"); break;
+        case 15504: strcpy(name, "Rakshasa (Light)"); break;
+        case 15505: strcpy(name, "Rakshasa (Dark)"); break;
+        case 15511: strcpy(name, "Su"); break;
+        case 15512: strcpy(name, "Hwa"); break;
+        case 15513: strcpy(name, "Yen"); break;
+        case 15514: strcpy(name, "Pang"); break;
+        case 15515: strcpy(name, "Ran"); break;
+        case 15601: strcpy(name, "Bounty Hunter (Water)"); break;
+        case 15602: strcpy(name, "Bounty Hunter (Fire)"); break;
+        case 15603: strcpy(name, "Bounty Hunter (Wind)"); break;
+        case 15604: strcpy(name, "Bounty Hunter (Light)"); break;
+        case 15605: strcpy(name, "Bounty Hunter (Dark)"); break;
+        case 15611: strcpy(name, "Wayne"); break;
+        case 15612: strcpy(name, "Randy"); break;
+        case 15613: strcpy(name, "Roger"); break;
+        case 15614: strcpy(name, "Walkers"); break;
+        case 15615: strcpy(name, "Jamie"); break;
+        case 15701: strcpy(name, "Oracle (Water)"); break;
+        case 15702: strcpy(name, "Oracle (Fire)"); break;
+        case 15703: strcpy(name, "Oracle (Wind)"); break;
+        case 15704: strcpy(name, "Oracle (Light)"); break;
+        case 15705: strcpy(name, "Oracle (Dark)"); break;
+        case 15711: strcpy(name, "Praha"); break;
+        case 15712: strcpy(name, "Juno"); break;
+        case 15713: strcpy(name, "Seara"); break;
+        case 15714: strcpy(name, "Laima"); break;
+        case 15715: strcpy(name, "Giana"); break;
+        case 15801: strcpy(name, "Imp Champion (Water)"); break;
+        case 15802: strcpy(name, "Imp Champion (Fire)"); break;
+        case 15803: strcpy(name, "Imp Champion (Wind)"); break;
+        case 15804: strcpy(name, "Imp Champion (Light)"); break;
+        case 15805: strcpy(name, "Imp Champion (Dark)"); break;
+        case 15811: strcpy(name, "Yaku"); break;
+        case 15812: strcpy(name, "Fairo"); break;
+        case 15813: strcpy(name, "Pigma"); break;
+        case 15814: strcpy(name, "Shaffron"); break;
+        case 15815: strcpy(name, "Loque"); break;
+        case 15901: strcpy(name, "Mystic Witch (Water)"); break;
+        case 15902: strcpy(name, "Mystic Witch (Fire)"); break;
+        case 15903: strcpy(name, "Mystic Witch (Wind)"); break;
+        case 15904: strcpy(name, "Mystic Witch (Light)"); break;
+        case 15905: strcpy(name, "Mystic Witch (Dark)"); break;
+        case 15911: strcpy(name, "Megan"); break;
+        case 15912: strcpy(name, "Rebecca"); break;
+        case 15913: strcpy(name, "Silia"); break;
+        case 15914: strcpy(name, "Linda"); break;
+        case 15915: strcpy(name, "Gina"); break;
+        case 16001: strcpy(name, "Grim Reaper (Water)"); break;
+        case 16002: strcpy(name, "Grim Reaper (Fire)"); break;
+        case 16003: strcpy(name, "Grim Reaper (Wind)"); break;
+        case 16004: strcpy(name, "Grim Reaper (Light)"); break;
+        case 16005: strcpy(name, "Grim Reaper (Dark)"); break;
+        case 16011: strcpy(name, "Hemos"); break;
+        case 16012: strcpy(name, "Sath"); break;
+        case 16013: strcpy(name, "Hiva"); break;
+        case 16014: strcpy(name, "Prom"); break;
+        case 16015: strcpy(name, "Thrain"); break;
+        case 16101: strcpy(name, "Occult Girl (Water)"); break;
+        case 16102: strcpy(name, "Occult Girl (Fire)"); break;
+        case 16103: strcpy(name, "Occult Girl (Wind)"); break;
+        case 16104: strcpy(name, "Occult Girl (Light)"); break;
+        case 16105: strcpy(name, "Occult Girl (Dark)"); break;
+        case 16111: strcpy(name, "Anavel"); break;
+        case 16112: strcpy(name, "Rica"); break;
+        case 16113: strcpy(name, "Charlotte"); break;
+        case 16114: strcpy(name, "Lora"); break;
+        case 16115: strcpy(name, "Nicki"); break;
+        case 16201: strcpy(name, "Death Knight (Water)"); break;
+        case 16202: strcpy(name, "Death Knight (Fire)"); break;
+        case 16203: strcpy(name, "Death Knight (Wind)"); break;
+        case 16204: strcpy(name, "Death Knight (Light)"); break;
+        case 16205: strcpy(name, "Death Knight (Dark)"); break;
+        case 16211: strcpy(name, "Fedora"); break;
+        case 16212: strcpy(name, "Arnold"); break;
+        case 16213: strcpy(name, "Briand"); break;
+        case 16214: strcpy(name, "Conrad"); break;
+        case 16215: strcpy(name, "Dias"); break;
+        case 16301: strcpy(name, "Lich (Water)"); break;
+        case 16302: strcpy(name, "Lich (Fire)"); break;
+        case 16303: strcpy(name, "Lich (Wind)"); break;
+        case 16304: strcpy(name, "Lich (Light)"); break;
+        case 16305: strcpy(name, "Lich (Dark)"); break;
+        case 16311: strcpy(name, "Rigel"); break;
+        case 16312: strcpy(name, "Antares"); break;
+        case 16313: strcpy(name, "Fuco"); break;
+        case 16314: strcpy(name, "Halphas"); break;
+        case 16315: strcpy(name, "Grego"); break;
+        case 16401: strcpy(name, "Skull Soldier (Water)"); break;
+        case 16402: strcpy(name, "Skull Soldier (Fire)"); break;
+        case 16403: strcpy(name, "Skull Soldier (Wind)"); break;
+        case 16501: strcpy(name, "Living Armor (Water)"); break;
+        case 16502: strcpy(name, "Living Armor (Fire)"); break;
+        case 16503: strcpy(name, "Living Armor (Wind)"); break;
+        case 16504: strcpy(name, "Living Armor (Light)"); break;
+        case 16505: strcpy(name, "Living Armor (Dark)"); break;
+        case 16511: strcpy(name, "Nickel"); break;
+        case 16512: strcpy(name, "Iron"); break;
+        case 16513: strcpy(name, "Copper"); break;
+        case 16514: strcpy(name, "Silver"); break;
+        case 16515: strcpy(name, "Zinc"); break;
+        case 16601: strcpy(name, "Dragon Knight (Water)"); break;
+        case 16602: strcpy(name, "Dragon Knight (Fire)"); break;
+        case 16603: strcpy(name, "Dragon Knight (Wind)"); break;
+        case 16604: strcpy(name, "Dragon Knight (Light)"); break;
+        case 16605: strcpy(name, "Dragon Knight (Dark)"); break;
+        case 16611: strcpy(name, "Chow"); break;
+        case 16612: strcpy(name, "Laika"); break;
+        case 16613: strcpy(name, "Leo"); break;
+        case 16614: strcpy(name, "Jager"); break;
+        case 16615: strcpy(name, "Ragdoll"); break;
+        case 16704: strcpy(name, "Magical Archer (Light)"); break;
+        case 16714: strcpy(name, "Fami"); break;
+        case 16801: strcpy(name, "Monkey King (Water)"); break;
+        case 16802: strcpy(name, "Monkey King (Fire)"); break;
+        case 16803: strcpy(name, "Monkey King (Wind)"); break;
+        case 16804: strcpy(name, "Monkey King (Light)"); break;
+        case 16805: strcpy(name, "Monkey King (Dark)"); break;
+        case 16811: strcpy(name, "Shi Hou"); break;
+        case 16812: strcpy(name, "Mei Hou Wang"); break;
+        case 16813: strcpy(name, "Xing Zhe"); break;
+        case 16814: strcpy(name, "Qitian Dasheng"); break;
+        case 16815: strcpy(name, "Son Zhang Lao"); break;
+        case 16901: strcpy(name, "Samurai"); break;
+        case 16902: strcpy(name, "Samurai (Fire)"); break;
+        case 16903: strcpy(name, "Samurai (Wind)"); break;
+        case 16904: strcpy(name, "Samurai (Light)"); break;
+        case 16905: strcpy(name, "Samurai (Dark)"); break;
+        case 16911: strcpy(name, "Kaz"); break;
+        case 16912: strcpy(name, "Jun"); break;
+        case 16913: strcpy(name, "Kaito"); break;
+        case 16914: strcpy(name, "Tosi"); break;
+        case 16915: strcpy(name, "Sige"); break;
+        case 16921: strcpy(name, "Imperfect Samurai (Water)"); break;
+        case 17001: strcpy(name, "Archangel (Water)"); break;
+        case 17002: strcpy(name, "Archangel (Fire)"); break;
+        case 17003: strcpy(name, "Archangel (Wind)"); break;
+        case 17004: strcpy(name, "Archangel (Light)"); break;
+        case 17005: strcpy(name, "Archangel (Dark)"); break;
+        case 17011: strcpy(name, "Ariel"); break;
+        case 17012: strcpy(name, "Velajuel"); break;
+        case 17013: strcpy(name, "Eladriel"); break;
+        case 17014: strcpy(name, "Artamiel"); break;
+        case 17015: strcpy(name, "Fermion"); break;
+        case 17101: strcpy(name, "Ifrit (Water)"); break;
+        case 17102: strcpy(name, "Ifrit (Fire)"); break;
+        case 17103: strcpy(name, "Ifrit (Wind)"); break;
+        case 17104: strcpy(name, "Ifrit (Light)"); break;
+        case 17105: strcpy(name, "Ifrit (Dark)"); break;
+        case 17111: strcpy(name, "Theomars"); break;
+        case 17112: strcpy(name, "Tesarion"); break;
+        case 17113: strcpy(name, "Akhamamir"); break;
+        case 17114: strcpy(name, "Elsharion"); break;
+        case 17115: strcpy(name, "Veromos"); break;
+        case 17201: strcpy(name, "Drunken Master (Water)"); break;
+        case 17202: strcpy(name, "Drunken Master (Fire)"); break;
+        case 17203: strcpy(name, "Drunken Master (Wind)"); break;
+        case 17204: strcpy(name, "Drunken Master (Light)"); break;
+        case 17205: strcpy(name, "Drunken Master (Dark)"); break;
+        case 17211: strcpy(name, "Mao"); break;
+        case 17212: strcpy(name, "Xiao Chun"); break;
+        case 17213: strcpy(name, "Huan"); break;
+        case 17214: strcpy(name, "Tien Qin"); break;
+        case 17215: strcpy(name, "Wei Shin"); break;
+        case 17301: strcpy(name, "Kung Fu Girl (Water)"); break;
+        case 17302: strcpy(name, "Kung Fu Girl (Fire)"); break;
+        case 17303: strcpy(name, "Kung Fu Girl"); break;
+        case 17304: strcpy(name, "Kung Fu Girl (Light)"); break;
+        case 17305: strcpy(name, "Kung Fu Girl (Dark)"); break;
+        case 17311: strcpy(name, "Xiao Lin"); break;
+        case 17312: strcpy(name, "Hong Hua"); break;
+        case 17313: strcpy(name, "Ling Ling"); break;
+        case 17314: strcpy(name, "Liu Mei"); break;
+        case 17315: strcpy(name, "Fei"); break;
+        case 17323: strcpy(name, "Imperfect Kung Fu Girl (Wind)"); break;
+        case 17401: strcpy(name, "Beast Monk (Water)"); break;
+        case 17402: strcpy(name, "Beast Monk (Fire)"); break;
+        case 17403: strcpy(name, "Beast Monk (Wind)"); break;
+        case 17404: strcpy(name, "Beast Monk (Light)"); break;
+        case 17405: strcpy(name, "Beast Monk (Dark)"); break;
+        case 17411: strcpy(name, "Chandra"); break;
+        case 17412: strcpy(name, "Kumar"); break;
+        case 17413: strcpy(name, "Ritesh"); break;
+        case 17414: strcpy(name, "Shazam"); break;
+        case 17415: strcpy(name, "Rahul"); break;
+        case 17501: strcpy(name, "Mischievous Bat (Water)"); break;
+        case 17502: strcpy(name, "Mischievous Bat (Fire)"); break;
+        case 17503: strcpy(name, "Mischievous Bat (Wind)"); break;
+        case 17601: strcpy(name, "Battle Scorpion (Water)"); break;
+        case 17602: strcpy(name, "Battle Scorpion (Fire)"); break;
+        case 17603: strcpy(name, "Battle Scorpion (Wind)"); break;
+        case 17701: strcpy(name, "Minotauros (Water)"); break;
+        case 17702: strcpy(name, "Minotauros (Fire)"); break;
+        case 17703: strcpy(name, "Minotauros (Wind)"); break;
+        case 17704: strcpy(name, "Minotauros (Light)"); break;
+        case 17705: strcpy(name, "Minotauros (Dark)"); break;
+        case 17711: strcpy(name, "Urtau"); break;
+        case 17712: strcpy(name, "Burentau"); break;
+        case 17713: strcpy(name, "Eintau"); break;
+        case 17714: strcpy(name, "Grotau"); break;
+        case 17715: strcpy(name, "Kamatau"); break;
+        case 17801: strcpy(name, "Lizardman (Water)"); break;
+        case 17802: strcpy(name, "Lizardman (Fire)"); break;
+        case 17803: strcpy(name, "Lizardman (Wind)"); break;
+        case 17804: strcpy(name, "Lizardman (Light)"); break;
+        case 17805: strcpy(name, "Lizardman (Dark)"); break;
+        case 17811: strcpy(name, "Kernodon"); break;
+        case 17812: strcpy(name, "Igmanodon"); break;
+        case 17813: strcpy(name, "Velfinodon"); break;
+        case 17814: strcpy(name, "Glinodon"); break;
+        case 17815: strcpy(name, "Devinodon"); break;
+        case 17901: strcpy(name, "Hell Lady (Water)"); break;
+        case 17902: strcpy(name, "Hell Lady (Fire)"); break;
+        case 17903: strcpy(name, "Hell Lady (Wind)"); break;
+        case 17904: strcpy(name, "Hell Lady (Light)"); break;
+        case 17905: strcpy(name, "Hell Lady (Dark)"); break;
+        case 17911: strcpy(name, "Beth"); break;
+        case 17912: strcpy(name, "Raki"); break;
+        case 17913: strcpy(name, "Ethna"); break;
+        case 17914: strcpy(name, "Asima"); break;
+        case 17915: strcpy(name, "Craka"); break;
+        case 18001: strcpy(name, "Brownie Magician (Water)"); break;
+        case 18002: strcpy(name, "Brownie Magician (Fire)"); break;
+        case 18003: strcpy(name, "Brownie Magician (Wind)"); break;
+        case 18004: strcpy(name, "Brownie Magician (Light)"); break;
+        case 18005: strcpy(name, "Brownie Magician (Dark)"); break;
+        case 18011: strcpy(name, "Orion"); break;
+        case 18012: strcpy(name, "Draco"); break;
+        case 18013: strcpy(name, "Aquila"); break;
+        case 18014: strcpy(name, "Gemini"); break;
+        case 18015: strcpy(name, "Korona"); break;
+        case 18101: strcpy(name, "Kobold Bomber (Water)"); break;
+        case 18102: strcpy(name, "Kobold Bomber (Fire)"); break;
+        case 18103: strcpy(name, "Kobold Bomber (Wind)"); break;
+        case 18104: strcpy(name, "Kobold Bomber (Light)"); break;
+        case 18105: strcpy(name, "Kobold Bomber (Dark)"); break;
+        case 18111: strcpy(name, "Malaka"); break;
+        case 18112: strcpy(name, "Zibrolta"); break;
+        case 18113: strcpy(name, "Taurus"); break;
+        case 18114: strcpy(name, "Dover"); break;
+        case 18115: strcpy(name, "Bering"); break;
+        case 18201: strcpy(name, "King Angelmon (Water)"); break;
+        case 18202: strcpy(name, "King Angelmon (Fire)"); break;
+        case 18203: strcpy(name, "King Angelmon (Wind)"); break;
+        case 18204: strcpy(name, "King Angelmon (Light)"); break;
+        case 18205: strcpy(name, "King Angelmon (Dark)"); break;
+        case 18211: strcpy(name, "Blue King Angelmon"); break;
+        case 18212: strcpy(name, "Red King Angelmon"); break;
+        case 18213: strcpy(name, "Gold King Angelmon"); break;
+        case 18214: strcpy(name, "White King Angelmon"); break;
+        case 18215: strcpy(name, "Dark King Angelmon"); break;
+        case 18301: strcpy(name, "Sky Dancer (Water)"); break;
+        case 18302: strcpy(name, "Sky Dancer (Fire)"); break;
+        case 18303: strcpy(name, "Sky Dancer (Wind)"); break;
+        case 18304: strcpy(name, "Sky Dancer (Light)"); break;
+        case 18305: strcpy(name, "Sky Dancer (Dark)"); break;
+        case 18311: strcpy(name, "Mihyang"); break;
+        case 18312: strcpy(name, "Hwahee"); break;
+        case 18313: strcpy(name, "Chasun"); break;
+        case 18314: strcpy(name, "Yeonhong"); break;
+        case 18315: strcpy(name, "Wolyung"); break;
+        case 18401: strcpy(name, "Taoist (Water)"); break;
+        case 18402: strcpy(name, "Taoist (Fire)"); break;
+        case 18403: strcpy(name, "Taoist (Wind)"); break;
+        case 18404: strcpy(name, "Taoist (Light)"); break;
+        case 18405: strcpy(name, "Taoist (Dark)"); break;
+        case 18411: strcpy(name, "Gildong"); break;
+        case 18412: strcpy(name, "Gunpyeong"); break;
+        case 18413: strcpy(name, "Woochi"); break;
+        case 18414: strcpy(name, "Hwadam"); break;
+        case 18415: strcpy(name, "Woonhak"); break;
+        case 18501: strcpy(name, "Beast Hunter (Water)"); break;
+        case 18502: strcpy(name, "Beast Hunter (Fire)"); break;
+        case 18503: strcpy(name, "Beast Hunter (Wind)"); break;
+        case 18504: strcpy(name, "Beast Hunter (Light)"); break;
+        case 18505: strcpy(name, "Beast Hunter (Dark)"); break;
+        case 18511: strcpy(name, "Gangchun"); break;
+        case 18512: strcpy(name, "Nangrim"); break;
+        case 18513: strcpy(name, "Suri"); break;
+        case 18514: strcpy(name, "Baekdu"); break;
+        case 18515: strcpy(name, "Hanra"); break;
+        case 18601: strcpy(name, "Pioneer (Water)"); break;
+        case 18602: strcpy(name, "Pioneer (Fire)"); break;
+        case 18603: strcpy(name, "Pioneer (Wind)"); break;
+        case 18604: strcpy(name, "Pioneer (Light)"); break;
+        case 18605: strcpy(name, "Pioneer (Dark)"); break;
+        case 18611: strcpy(name, "Woosa"); break;
+        case 18612: strcpy(name, "Chiwu"); break;
+        case 18613: strcpy(name, "Pungbaek"); break;
+        case 18614: strcpy(name, "Nigong"); break;
+        case 18615: strcpy(name, "Woonsa"); break;
+        case 18701: strcpy(name, "Penguin Knight (Water)"); break;
+        case 18702: strcpy(name, "Penguin Knight (Fire)"); break;
+        case 18703: strcpy(name, "Penguin Knight (Wind)"); break;
+        case 18704: strcpy(name, "Penguin Knight (Light)"); break;
+        case 18705: strcpy(name, "Penguin Knight (Dark)"); break;
+        case 18711: strcpy(name, "Toma"); break;
+        case 18712: strcpy(name, "Naki"); break;
+        case 18713: strcpy(name, "Mav"); break;
+        case 18714: strcpy(name, "Dona"); break;
+        case 18715: strcpy(name, "Kuna"); break;
+        case 18801: strcpy(name, "Barbaric King (Water)"); break;
+        case 18802: strcpy(name, "Barbaric King (Fire)"); break;
+        case 18803: strcpy(name, "Barbaric King (Wind)"); break;
+        case 18804: strcpy(name, "Barbaric King (Light)"); break;
+        case 18805: strcpy(name, "Barbaric King (Dark)"); break;
+        case 18811: strcpy(name, "Aegir"); break;
+        case 18812: strcpy(name, "Surtr"); break;
+        case 18813: strcpy(name, "Hraesvelg"); break;
+        case 18814: strcpy(name, "Mimirr"); break;
+        case 18815: strcpy(name, "Hrungnir"); break;
+        case 18901: strcpy(name, "Polar Queen (Water)"); break;
+        case 18902: strcpy(name, "Polar Queen (Fire)"); break;
+        case 18903: strcpy(name, "Polar Queen (Wind)"); break;
+        case 18904: strcpy(name, "Polar Queen (Light)"); break;
+        case 18905: strcpy(name, "Polar Queen (Dark)"); break;
+        case 18911: strcpy(name, "Alicia"); break;
+        case 18912: strcpy(name, "Brandia"); break;
+        case 18913: strcpy(name, "Tiana"); break;
+        case 18914: strcpy(name, "Elenoa"); break;
+        case 18915: strcpy(name, "Lydia"); break;
+        case 19001: strcpy(name, "Battle Mammoth (Water)"); break;
+        case 19002: strcpy(name, "Battle Mammoth (Fire)"); break;
+        case 19003: strcpy(name, "Battle Mammoth (Wind)"); break;
+        case 19004: strcpy(name, "Battle Mammoth (Light)"); break;
+        case 19005: strcpy(name, "Battle Mammoth (Dark)"); break;
+        case 19011: strcpy(name, "Talc"); break;
+        case 19012: strcpy(name, "Granite"); break;
+        case 19013: strcpy(name, "Olivine"); break;
+        case 19014: strcpy(name, "Marble"); break;
+        case 19015: strcpy(name, "Basalt"); break;
+        case 19104: strcpy(name, "Fairy Queen (Light)"); break;
+        case 19114: strcpy(name, "Fran"); break;
+        case 19201: strcpy(name, "Ifrit (Water)"); break;
+        case 19202: strcpy(name, "Ifrit (Fire)"); break;
+        case 19203: strcpy(name, "Ifrit (Wind)"); break;
+        case 19204: strcpy(name, "Ifrit (Light)"); break;
+        case 19205: strcpy(name, "Ifrit (Dark)"); break;
+        case 19211: strcpy(name, "Theomars"); break;
+        case 19212: strcpy(name, "Tesarion"); break;
+        case 19213: strcpy(name, "Akhamamir"); break;
+        case 19214: strcpy(name, "Elsharion"); break;
+        case 19215: strcpy(name, "Veromos"); break;
+        case 19301: strcpy(name, "Cow Girl (Water)"); break;
+        case 19302: strcpy(name, "Cow Girl (Fire)"); break;
+        case 19303: strcpy(name, "Cow Girl (Wind)"); break;
+        case 19304: strcpy(name, "Cow Girl (Light)"); break;
+        case 19305: strcpy(name, "Cow Girl (Dark)"); break;
+        case 19311: strcpy(name, "Sera"); break;
+        case 19312: strcpy(name, "Anne"); break;
+        case 19313: strcpy(name, "Hannah"); break;
+        case 19314: strcpy(name, "Loren"); break;
+        case 19315: strcpy(name, "Cassie"); break;
+        case 19401: strcpy(name, "Pirate Captain (Water)"); break;
+        case 19402: strcpy(name, "Pirate Captain (Fire)"); break;
+        case 19403: strcpy(name, "Pirate Captain (Wind)"); break;
+        case 19404: strcpy(name, "Pirate Captain (Light)"); break;
+        case 19405: strcpy(name, "Pirate Captain (Dark)"); break;
+        case 19411: strcpy(name, "Galleon"); break;
+        case 19412: strcpy(name, "Carrack"); break;
+        case 19413: strcpy(name, "Barque"); break;
+        case 19414: strcpy(name, "Brig"); break;
+        case 19415: strcpy(name, "Frigate"); break;
+        case 19501: strcpy(name, "Charger Shark (Water)"); break;
+        case 19502: strcpy(name, "Charger Shark (Fire)"); break;
+        case 19503: strcpy(name, "Charger Shark (Wind)"); break;
+        case 19504: strcpy(name, "Charger Shark (Light)"); break;
+        case 19505: strcpy(name, "Charger Shark (Dark)"); break;
+        case 19511: strcpy(name, "Aqcus"); break;
+        case 19512: strcpy(name, "Ignicus"); break;
+        case 19513: strcpy(name, "Zephicus"); break;
+        case 19514: strcpy(name, "Rumicus"); break;
+        case 19515: strcpy(name, "Calicus"); break;
+        case 19601: strcpy(name, "Mermaid (Water)"); break;
+        case 19602: strcpy(name, "Mermaid (Fire)"); break;
+        case 19603: strcpy(name, "Mermaid (Wind)"); break;
+        case 19604: strcpy(name, "Mermaid (Light)"); break;
+        case 19605: strcpy(name, "Mermaid (Dark)"); break;
+        case 19611: strcpy(name, "Tetra"); break;
+        case 19612: strcpy(name, "Platy"); break;
+        case 19613: strcpy(name, "Cichlid"); break;
+        case 19614: strcpy(name, "Molly"); break;
+        case 19615: strcpy(name, "Betta"); break;
+        case 19701: strcpy(name, "Sea Emperor (Water)"); break;
+        case 19702: strcpy(name, "Sea Emperor (Fire)"); break;
+        case 19703: strcpy(name, "Sea Emperor (Wind)"); break;
+        case 19704: strcpy(name, "Sea Emperor (Light)"); break;
+        case 19705: strcpy(name, "Sea Emperor (Dark)"); break;
+        case 19711: strcpy(name, "Poseidon"); break;
+        case 19712: strcpy(name, "Okeanos"); break;
+        case 19713: strcpy(name, "Triton"); break;
+        case 19714: strcpy(name, "Pontos"); break;
+        case 19715: strcpy(name, "Manannan"); break;
+        case 19801: strcpy(name, "Magic Knight (Water)"); break;
+        case 19802: strcpy(name, "Magic Knight (Fire)"); break;
+        case 19803: strcpy(name, "Magic Knight"); break;
+        case 19804: strcpy(name, "Magic Knight (Light)"); break;
+        case 19805: strcpy(name, "Magic Knight (Dark)"); break;
+        case 19811: strcpy(name, "Lapis"); break;
+        case 19812: strcpy(name, "Astar"); break;
+        case 19813: strcpy(name, "Lupinus"); break;
+        case 19814: strcpy(name, "Iris"); break;
+        case 19815: strcpy(name, "Lanett"); break;
+        case 19823: strcpy(name, "Imperfect Magic Knight (Wind)"); break;
+        case 19901: strcpy(name, "Assassin (Water)"); break;
+        case 19902: strcpy(name, "Assassin (Fire)"); break;
+        case 19903: strcpy(name, "Assassin (Wind)"); break;
+        case 19904: strcpy(name, "Assassin (Light)"); break;
+        case 19905: strcpy(name, "Assassin (Dark)"); break;
+        case 19911: strcpy(name, "Stella"); break;
+        case 19912: strcpy(name, "Lexy"); break;
+        case 19913: strcpy(name, "Tanya"); break;
+        case 19914: strcpy(name, "Natalie"); break;
+        case 19915: strcpy(name, "Isabelle"); break;
+        case 20001: strcpy(name, "Neostone Fighter (Water)"); break;
+        case 20002: strcpy(name, "Neostone Fighter (Fire)"); break;
+        case 20003: strcpy(name, "Neostone Fighter (Wind)"); break;
+        case 20004: strcpy(name, "Neostone Fighter (Light)"); break;
+        case 20005: strcpy(name, "Neostone Fighter (Dark)"); break;
+        case 20011: strcpy(name, "Ryan"); break;
+        case 20012: strcpy(name, "Trevor"); break;
+        case 20013: strcpy(name, "Logan"); break;
+        case 20014: strcpy(name, "Lucas"); break;
+        case 20015: strcpy(name, "Karl"); break;
+        case 20101: strcpy(name, "Neostone Agent (Water)"); break;
+        case 20102: strcpy(name, "Neostone Agent (Fire)"); break;
+        case 20103: strcpy(name, "Neostone Agent (Wind)"); break;
+        case 20104: strcpy(name, "Neostone Agent (Light)"); break;
+        case 20105: strcpy(name, "Neostone Agent (Dark)"); break;
+        case 20111: strcpy(name, "Emma"); break;
+        case 20112: strcpy(name, "Lisa"); break;
+        case 20113: strcpy(name, "Olivia"); break;
+        case 20114: strcpy(name, "Illianna"); break;
+        case 20115: strcpy(name, "Sylvia"); break;
+        case 20201: strcpy(name, "Martial Artist (Water)"); break;
+        case 20202: strcpy(name, "Martial Artist (Fire)"); break;
+        case 20203: strcpy(name, "Martial Artist (Wind)"); break;
+        case 20204: strcpy(name, "Martial Artist (Light)"); break;
+        case 20205: strcpy(name, "Martial Artist (Dark)"); break;
+        case 20211: strcpy(name, "Luan"); break;
+        case 20212: strcpy(name, "Sin"); break;
+        case 20213: strcpy(name, "Lo"); break;
+        case 20214: strcpy(name, "Hiro"); break;
+        case 20215: strcpy(name, "Jackie"); break;
+        case 20301: strcpy(name, "Mummy (Water)"); break;
+        case 20302: strcpy(name, "Mummy (Fire)"); break;
+        case 20303: strcpy(name, "Mummy (Wind)"); break;
+        case 20304: strcpy(name, "Mummy (Light)"); break;
+        case 20305: strcpy(name, "Mummy (Dark)"); break;
+        case 20311: strcpy(name, "Nubia"); break;
+        case 20312: strcpy(name, "Sonora"); break;
+        case 20313: strcpy(name, "Namib"); break;
+        case 20314: strcpy(name, "Sahara"); break;
+        case 20315: strcpy(name, "Karakum"); break;
+        case 20401: strcpy(name, "Anubis (Water)"); break;
+        case 20402: strcpy(name, "Anubis (Fire)"); break;
+        case 20403: strcpy(name, "Anubis (Wind)"); break;
+        case 20404: strcpy(name, "Anubis (Light)"); break;
+        case 20405: strcpy(name, "Anubis (Dark)"); break;
+        case 20411: strcpy(name, "Avaris"); break;
+        case 20412: strcpy(name, "Khmun"); break;
+        case 20413: strcpy(name, "Iunu"); break;
+        case 20414: strcpy(name, "Amarna"); break;
+        case 20415: strcpy(name, "Thebae"); break;
+        case 20501: strcpy(name, "Desert Queen (Water)"); break;
+        case 20502: strcpy(name, "Desert Queen (Fire)"); break;
+        case 20503: strcpy(name, "Desert Queen (Wind)"); break;
+        case 20504: strcpy(name, "Desert Queen (Light)"); break;
+        case 20505: strcpy(name, "Desert Queen (Dark)"); break;
+        case 20511: strcpy(name, "Bastet"); break;
+        case 20512: strcpy(name, "Sekhmet"); break;
+        case 20513: strcpy(name, "Hathor"); break;
+        case 20514: strcpy(name, "Isis"); break;
+        case 20515: strcpy(name, "Nephthys"); break;
+        case 20601: strcpy(name, "Horus"); break;
+        case 20602: strcpy(name, "Horus (Fire)"); break;
+        case 20603: strcpy(name, "Horus (Wind)"); break;
+        case 20604: strcpy(name, "Horus (Light)"); break;
+        case 20605: strcpy(name, "Horus (Dark)"); break;
+        case 20611: strcpy(name, "Qebehsenuef"); break;
+        case 20612: strcpy(name, "Duamutef"); break;
+        case 20613: strcpy(name, "Imesety"); break;
+        case 20614: strcpy(name, "Wedjat"); break;
+        case 20615: strcpy(name, "Amduat"); break;
+        case 20621: strcpy(name, "Imperfect Horus (Water)"); break;
+        case 20701: strcpy(name, "Jack-o'-lantern (Water)"); break;
+        case 20702: strcpy(name, "Jack-o'-lantern (Fire)"); break;
+        case 20703: strcpy(name, "Jack-o'-lantern (Wind)"); break;
+        case 20704: strcpy(name, "Jack-o'-lantern (Light)"); break;
+        case 20705: strcpy(name, "Jack-o'-lantern (Dark)"); break;
+        case 20711: strcpy(name, "Chilling"); break;
+        case 20712: strcpy(name, "Smokey"); break;
+        case 20713: strcpy(name, "Windy"); break;
+        case 20714: strcpy(name, "Misty"); break;
+        case 20715: strcpy(name, "Dusky"); break;
+        case 20801: strcpy(name, "Frankenstein (Water)"); break;
+        case 20802: strcpy(name, "Frankenstein (Fire)"); break;
+        case 20803: strcpy(name, "Frankenstein (Wind)"); break;
+        case 20804: strcpy(name, "Frankenstein (Light)"); break;
+        case 20805: strcpy(name, "Frankenstein (Dark)"); break;
+        case 20811: strcpy(name, "Tractor"); break;
+        case 20812: strcpy(name, "Bulldozer"); break;
+        case 20813: strcpy(name, "Crane"); break;
+        case 20814: strcpy(name, "Driller"); break;
+        case 20815: strcpy(name, "Crawler"); break;
+        case 20901: strcpy(name, "Elven Ranger (Water)"); break;
+        case 20902: strcpy(name, "Elven Ranger (Fire)"); break;
+        case 20903: strcpy(name, "Elven Ranger (Wind)"); break;
+        case 20904: strcpy(name, "Elven Ranger (Light)"); break;
+        case 20905: strcpy(name, "Elven Ranger (Dark)"); break;
+        case 20911: strcpy(name, "Eluin"); break;
+        case 20912: strcpy(name, "Adrian"); break;
+        case 20913: strcpy(name, "Erwin"); break;
+        case 20914: strcpy(name, "Lucien"); break;
+        case 20915: strcpy(name, "Isillen"); break;
+        case 21001: strcpy(name, "Harg (Water)"); break;
+        case 21002: strcpy(name, "Harg (Fire)"); break;
+        case 21003: strcpy(name, "Harg (Wind)"); break;
+        case 21004: strcpy(name, "Harg (Light)"); break;
+        case 21005: strcpy(name, "Harg (Dark)"); break;
+        case 21011: strcpy(name, "Remy"); break;
+        case 21012: strcpy(name, "Racuni"); break;
+        case 21013: strcpy(name, "Raviti"); break;
+        case 21014: strcpy(name, "Dova"); break;
+        case 21015: strcpy(name, "Kroa"); break;
+        case 21101: strcpy(name, "Fairy King (Water)"); break;
+        case 21102: strcpy(name, "Fairy King (Fire)"); break;
+        case 21103: strcpy(name, "Fairy King (Wind)"); break;
+        case 21104: strcpy(name, "Fairy King (Light)"); break;
+        case 21105: strcpy(name, "Fairy King (Dark)"); break;
+        case 21111: strcpy(name, "Psamathe"); break;
+        case 21112: strcpy(name, "Daphnis"); break;
+        case 21113: strcpy(name, "Ganymede"); break;
+        case 21114: strcpy(name, "Oberon"); break;
+        case 21115: strcpy(name, "Nyx"); break;
+        case 21201: strcpy(name, "Panda Warrior (Water)"); break;
+        case 21202: strcpy(name, "Panda Warrior (Fire)"); break;
+        case 21203: strcpy(name, "Panda Warrior (Wind)"); break;
+        case 21204: strcpy(name, "Panda Warrior (Light)"); break;
+        case 21205: strcpy(name, "Panda Warrior (Dark)"); break;
+        case 21211: strcpy(name, "Mo Long"); break;
+        case 21212: strcpy(name, "Xiong Fei"); break;
+        case 21213: strcpy(name, "Feng Yan"); break;
+        case 21214: strcpy(name, "Tian Lang"); break;
+        case 21215: strcpy(name, "Mi Ying"); break;
+        case 21301: strcpy(name, "Dice Magician (Water)"); break;
+        case 21302: strcpy(name, "Dice Magician (Fire)"); break;
+        case 21303: strcpy(name, "Dice Magician (Wind)"); break;
+        case 21304: strcpy(name, "Dice Magician (Light)"); break;
+        case 21305: strcpy(name, "Dice Magician (Dark)"); break;
+        case 21311: strcpy(name, "Reno"); break;
+        case 21312: strcpy(name, "Ludo"); break;
+        case 21313: strcpy(name, "Morris"); break;
+        case 21314: strcpy(name, "Tablo"); break;
+        case 21315: strcpy(name, "Monte"); break;
+        case 21401: strcpy(name, "Harp Magician (Water)"); break;
+        case 21402: strcpy(name, "Harp Magician"); break;
+        case 21403: strcpy(name, "Harp Magician (Wind)"); break;
+        case 21404: strcpy(name, "Harp Magician (Light)"); break;
+        case 21405: strcpy(name, "Harp Magician (Dark)"); break;
+        case 21411: strcpy(name, "Sonnet"); break;
+        case 21412: strcpy(name, "Harmonia"); break;
+        case 21413: strcpy(name, "Triana"); break;
+        case 21414: strcpy(name, "Celia"); break;
+        case 21415: strcpy(name, "Vivachel"); break;
+        case 21422: strcpy(name, "Imperfect Harp Magician (Fire)"); break;
+        case 21501: strcpy(name, "Unicorn (Water)"); break;
+        case 21502: strcpy(name, "Unicorn (Fire)"); break;
+        case 21503: strcpy(name, "Unicorn (Wind)"); break;
+        case 21504: strcpy(name, "Unicorn (Light)"); break;
+        case 21505: strcpy(name, "Unicorn (Dark)"); break;
+        case 21511: strcpy(name, "Amelia"); break;
+        case 21512: strcpy(name, "Helena"); break;
+        case 21513: strcpy(name, "Diana"); break;
+        case 21514: strcpy(name, "Eleanor"); break;
+        case 21515: strcpy(name, "Alexandra"); break;
+        case 21611: strcpy(name, "Amelia (Water)"); break;
+        case 21612: strcpy(name, "Helena (Fire)"); break;
+        case 21613: strcpy(name, "Diana (Wind)"); break;
+        case 21614: strcpy(name, "Eleanor (Light)"); break;
+        case 21615: strcpy(name, "Alexandra (Dark)"); break;
+        case 21714: strcpy(name, "Super Angelmon (Light)"); break;
+        case 21801: strcpy(name, "Paladin (Water)"); break;
+        case 21802: strcpy(name, "Paladin (Fire)"); break;
+        case 21803: strcpy(name, "Paladin (Wind)"); break;
+        case 21804: strcpy(name, "Paladin (Light)"); break;
+        case 21805: strcpy(name, "Paladin (Dark)"); break;
+        case 21811: strcpy(name, "Josephine"); break;
+        case 21812: strcpy(name, "Ophilia"); break;
+        case 21813: strcpy(name, "Louise"); break;
+        case 21814: strcpy(name, "Jeanne"); break;
+        case 21815: strcpy(name, "Leona"); break;
+        case 21901: strcpy(name, "Chakram Dancer (Water)"); break;
+        case 21902: strcpy(name, "Chakram Dancer (Fire)"); break;
+        case 21903: strcpy(name, "Chakram Dancer (Wind)"); break;
+        case 21904: strcpy(name, "Chakram Dancer (Light)"); break;
+        case 21905: strcpy(name, "Chakram Dancer (Dark)"); break;
+        case 21911: strcpy(name, "Talia"); break;
+        case 21912: strcpy(name, "Shaina"); break;
+        case 21913: strcpy(name, "Melissa"); break;
+        case 21914: strcpy(name, "Deva"); break;
+        case 21915: strcpy(name, "Belita"); break;
+        case 22001: strcpy(name, "Boomerang Warrior (Water)"); break;
+        case 22002: strcpy(name, "Boomerang Warrior (Fire)"); break;
+        case 22003: strcpy(name, "Boomerang Warrior (Wind)"); break;
+        case 22004: strcpy(name, "Boomerang Warrior (Light)"); break;
+        case 22005: strcpy(name, "Boomerang Warrior (Dark)"); break;
+        case 22011: strcpy(name, "Sabrina"); break;
+        case 22012: strcpy(name, "Maruna"); break;
+        case 22013: strcpy(name, "Zenobia"); break;
+        case 22014: strcpy(name, "Bailey"); break;
+        case 22015: strcpy(name, "Martina"); break;
+        case 22101: strcpy(name, "Dryad (Water)"); break;
+        case 22102: strcpy(name, "Dryad (Fire)"); break;
+        case 22103: strcpy(name, "Dryad (Wind)"); break;
+        case 22104: strcpy(name, "Dryad (Light)"); break;
+        case 22105: strcpy(name, "Dryad (Dark)"); break;
+        case 22111: strcpy(name, "Herne"); break;
+        case 22112: strcpy(name, "Nisha"); break;
+        case 22113: strcpy(name, "Mellia"); break;
+        case 22114: strcpy(name, "Felleria"); break;
+        case 22115: strcpy(name, "Hyanes"); break;
+        case 22201: strcpy(name, "Druid (Water)"); break;
+        case 22202: strcpy(name, "Druid (Fire)"); break;
+        case 22203: strcpy(name, "Druid (Wind)"); break;
+        case 22204: strcpy(name, "Druid (Light)"); break;
+        case 22205: strcpy(name, "Druid (Dark)"); break;
+        case 22211: strcpy(name, "Abellio"); break;
+        case 22212: strcpy(name, "Bellenus"); break;
+        case 22213: strcpy(name, "Taranys"); break;
+        case 22214: strcpy(name, "Valantis"); break;
+        case 22215: strcpy(name, "Pater"); break;
+        case 22311: strcpy(name, "Abellio (Water)"); break;
+        case 22312: strcpy(name, "Bellenus (Fire)"); break;
+        case 22313: strcpy(name, "Taranys (Wind)"); break;
+        case 22314: strcpy(name, "Valantis (Light)"); break;
+        case 22315: strcpy(name, "Pater (Dark)"); break;
+        case 22401: strcpy(name, "Giant Warrior (Water)"); break;
+        case 22402: strcpy(name, "Giant Warrior (Fire)"); break;
+        case 22403: strcpy(name, "Giant Warrior (Wind)"); break;
+        case 22404: strcpy(name, "Giant Warrior (Light)"); break;
+        case 22405: strcpy(name, "Giant Warrior (Dark)"); break;
+        case 22411: strcpy(name, "Bagir"); break;
+        case 22412: strcpy(name, "Vidurr"); break;
+        case 22413: strcpy(name, "Skogul"); break;
+        case 22414: strcpy(name, "Einheri"); break;
+        case 22415: strcpy(name, "Trasar"); break;
+        case 22503: strcpy(name, "Giant Warrior (Wind)"); break;
+        case 22505: strcpy(name, "Giant Warrior (Dark)"); break;
+        case 22513: strcpy(name, "Skogul (Wind)"); break;
+        case 22515: strcpy(name, "Trasar (Dark)"); break;
+        case 22601: strcpy(name, "Lightning Emperor (Water)"); break;
+        case 22602: strcpy(name, "Lightning Emperor (Fire)"); break;
+        case 22603: strcpy(name, "Lightning Emperor (Wind)"); break;
+        case 22604: strcpy(name, "Lightning Emperor (Light)"); break;
+        case 22605: strcpy(name, "Lightning Emperor (Dark)"); break;
+        case 22611: strcpy(name, "Bolverk"); break;
+        case 22612: strcpy(name, "Baleygr"); break;
+        case 22613: strcpy(name, "Odin"); break;
+        case 22614: strcpy(name, "Geldnir"); break;
+        case 22615: strcpy(name, "Herteit"); break;
+        case 22701: strcpy(name, "Sniper Mk.I (Water)"); break;
+        case 22702: strcpy(name, "Sniper Mk.I (Fire)"); break;
+        case 22703: strcpy(name, "Sniper Mk.I (Wind)"); break;
+        case 22704: strcpy(name, "Sniper Mk.I (Light)"); break;
+        case 22705: strcpy(name, "Sniper Mk.I (Dark)"); break;
+        case 22711: strcpy(name, "Covenant"); break;
+        case 22712: strcpy(name, "Carcano"); break;
+        case 22713: strcpy(name, "Carbine"); break;
+        case 22714: strcpy(name, "Magnum"); break;
+        case 22715: strcpy(name, "Dragunov"); break;
+        case 22802: strcpy(name, "Sniper Mk.I (Fire)"); break;
+        case 22803: strcpy(name, "Sniper Mk.I (Wind)"); break;
+        case 22805: strcpy(name, "Sniper Mk.I (Dark)"); break;
+        case 22812: strcpy(name, "Carcano (Fire)"); break;
+        case 22813: strcpy(name, "Carbine (Wind)"); break;
+        case 22815: strcpy(name, "Dragunov (Dark)"); break;
+        case 22901: strcpy(name, "Cannon Girl (Water)"); break;
+        case 22902: strcpy(name, "Cannon Girl (Fire)"); break;
+        case 22903: strcpy(name, "Cannon Girl (Wind)"); break;
+        case 22904: strcpy(name, "Cannon Girl (Light)"); break;
+        case 22905: strcpy(name, "Cannon Girl (Dark)"); break;
+        case 22911: strcpy(name, "Abigail"); break;
+        case 22912: strcpy(name, "Scarlett"); break;
+        case 22913: strcpy(name, "Christina"); break;
+        case 22914: strcpy(name, "Emily"); break;
+        case 22915: strcpy(name, "Bella"); break;
+        case 23005: strcpy(name, "Vampire Lord (Dark)"); break;
+        case 23015: strcpy(name, "Eirgar"); break;
+        case 23101: strcpy(name, "Demon (Water)"); break;
+        case 23102: strcpy(name, "Demon (Fire)"); break;
+        case 23103: strcpy(name, "Demon (Wind)"); break;
+        case 23104: strcpy(name, "Demon (Light)"); break;
+        case 23105: strcpy(name, "Demon (Dark)"); break;
+        case 23111: strcpy(name, "Belial"); break;
+        case 23112: strcpy(name, "Bael"); break;
+        case 23113: strcpy(name, "Mephisto"); break;
+        case 23114: strcpy(name, "Lucifer"); break;
+        case 23115: strcpy(name, "Beelzebub"); break;
+        case 23201: strcpy(name, "데몬(물) (Water)"); break;
+        case 23205: strcpy(name, "데몬(어둠) (Dark)"); break;
+        case 23211: strcpy(name, "데몬(물) (Water)"); break;
+        case 23215: strcpy(name, "데몬(어둠) (Dark)"); break;
+        case 23301: strcpy(name, "Gargoyle (Water)"); break;
+        case 23302: strcpy(name, "Gargoyle (Fire)"); break;
+        case 23303: strcpy(name, "Gargoyle (Wind)"); break;
+        case 23304: strcpy(name, "Gargoyle (Light)"); break;
+        case 23305: strcpy(name, "Gargoyle (Dark)"); break;
+        case 23311: strcpy(name, "Tanzaite"); break;
+        case 23312: strcpy(name, "Kunite"); break;
+        case 23313: strcpy(name, "Malite"); break;
+        case 23314: strcpy(name, "Phenaka"); break;
+        case 23315: strcpy(name, "Onyx"); break;
+        case 23401: strcpy(name, "가고일(물) (Water)"); break;
+        case 23402: strcpy(name, "가고일(불) (Fire)"); break;
+        case 23403: strcpy(name, "가고일(바람) (Wind)"); break;
+        case 23404: strcpy(name, "가고일(빛) (Light)"); break;
+        case 23405: strcpy(name, "가고일(어둠) (Dark)"); break;
+        case 23411: strcpy(name, "가고일(물) (Water)"); break;
+        case 23412: strcpy(name, "가고일(불) (Fire)"); break;
+        case 23413: strcpy(name, "가고일(바람) (Wind)"); break;
+        case 23414: strcpy(name, "가고일(빛) (Light)"); break;
+        case 23415: strcpy(name, "가고일(어둠) (Dark)"); break;
+        case 23501: strcpy(name, "Beast Rider (Water)"); break;
+        case 23502: strcpy(name, "Beast Rider (Fire)"); break;
+        case 23503: strcpy(name, "Beast Rider (Wind)"); break;
+        case 23504: strcpy(name, "Beast Rider (Light)"); break;
+        case 23505: strcpy(name, "Beast Rider (Dark)"); break;
+        case 23511: strcpy(name, "Barbara"); break;
+        case 23512: strcpy(name, "Masha"); break;
+        case 23513: strcpy(name, "Savannah"); break;
+        case 23514: strcpy(name, "Narsha"); break;
+        case 23515: strcpy(name, "Xiana"); break;
+        case 23601: strcpy(name, "Beast Rider (Water)"); break;
+        case 23602: strcpy(name, "Beast Rider (Fire)"); break;
+        case 23603: strcpy(name, "Beast Rider (Wind)"); break;
+        case 23604: strcpy(name, "Beast Rider (Light)"); break;
+        case 23605: strcpy(name, "Beast Rider (Dark)"); break;
+        case 23611: strcpy(name, "Barbara"); break;
+        case 23612: strcpy(name, "Masha"); break;
+        case 23613: strcpy(name, "Savannah"); break;
+        case 23614: strcpy(name, "Narsha"); break;
+        case 23615: strcpy(name, "Xiana"); break;
+        case 23701: strcpy(name, "Art Master (Water)"); break;
+        case 23702: strcpy(name, "Art Master (Fire)"); break;
+        case 23703: strcpy(name, "Art Master (Wind)"); break;
+        case 23704: strcpy(name, "Art Master (Light)"); break;
+        case 23705: strcpy(name, "Art Master (Dark)"); break;
+        case 23711: strcpy(name, "Haegang"); break;
+        case 23712: strcpy(name, "Jeogun"); break;
+        case 23713: strcpy(name, "Cheongpung"); break;
+        case 23714: strcpy(name, "Hanwul"); break;
+        case 23715: strcpy(name, "Mookwol"); break;
+        case 23801: strcpy(name, "족자(물) (Water)"); break;
+        case 23802: strcpy(name, "족자(불) (Fire)"); break;
+        case 23803: strcpy(name, "족자(바람) (Wind)"); break;
+        case 23804: strcpy(name, "족자(빛) (Light)"); break;
+        case 23805: strcpy(name, "족자(어둠) (Dark)"); break;
+        case 23806: strcpy(name, "족자(무) (Pure)"); break;
+        case 23901: strcpy(name, "String Master (Water)"); break;
+        case 23902: strcpy(name, "String Master (Fire)"); break;
+        case 23903: strcpy(name, "String Master (Wind)"); break;
+        case 23904: strcpy(name, "String Master (Light)"); break;
+        case 23905: strcpy(name, "String Master (Dark)"); break;
+        case 23911: strcpy(name, "Songseol"); break;
+        case 23912: strcpy(name, "Hongyeon"); break;
+        case 23913: strcpy(name, "Yeonhwa"); break;
+        case 23914: strcpy(name, "Dongbaek"); break;
+        case 23915: strcpy(name, "Mirinae"); break;
+        case 24001: strcpy(name, "류(물) (Water)"); break;
+        case 24002: strcpy(name, "류(불) (Fire)"); break;
+        case 24003: strcpy(name, "류(바람) (Wind)"); break;
+        case 24004: strcpy(name, "류(빛) (Light)"); break;
+        case 24005: strcpy(name, "류(어둠) (Dark)"); break;
+        case 24011: strcpy(name, "RYU (Water)"); break;
+        case 24012: strcpy(name, "RYU (Fire)"); break;
+        case 24013: strcpy(name, "RYU (Wind)"); break;
+        case 24014: strcpy(name, "RYU (Light)"); break;
+        case 24015: strcpy(name, "RYU (Dark)"); break;
+        case 24102: strcpy(name, "켄(불) (Fire)"); break;
+        case 24112: strcpy(name, "KEN (Fire)"); break;
+        case 24201: strcpy(name, "바이슨(물) (Water)"); break;
+        case 24202: strcpy(name, "바이슨(불) (Fire)"); break;
+        case 24203: strcpy(name, "바이슨(바람) (Wind)"); break;
+        case 24204: strcpy(name, "바이슨(빛) (Light)"); break;
+        case 24205: strcpy(name, "바이슨(어둠) (Dark)"); break;
+        case 24211: strcpy(name, "M. BISON (Water)"); break;
+        case 24212: strcpy(name, "M. BISON (Fire)"); break;
+        case 24213: strcpy(name, "M. BISON (Wind)"); break;
+        case 24214: strcpy(name, "M. BISON (Light)"); break;
+        case 24215: strcpy(name, "M. BISON (Dark)"); break;
+        case 24301: strcpy(name, "달심(물) (Water)"); break;
+        case 24302: strcpy(name, "달심(불) (Fire)"); break;
+        case 24303: strcpy(name, "달심(바람) (Wind)"); break;
+        case 24304: strcpy(name, "달심(빛) (Light)"); break;
+        case 24305: strcpy(name, "달심(어둠) (Dark)"); break;
+        case 24311: strcpy(name, "DHALSIM (Water)"); break;
+        case 24312: strcpy(name, "DHALSIM (Fire)"); break;
+        case 24313: strcpy(name, "DHALSIM (Wind)"); break;
+        case 24314: strcpy(name, "DHALSIM (Light)"); break;
+        case 24315: strcpy(name, "DHALSIM (Dark)"); break;
+        case 24401: strcpy(name, "춘리(물) (Water)"); break;
+        case 24402: strcpy(name, "춘리(불) (Fire)"); break;
+        case 24403: strcpy(name, "춘리(바람) (Wind)"); break;
+        case 24404: strcpy(name, "춘리(빛) (Light)"); break;
+        case 24405: strcpy(name, "춘리(어둠) (Dark)"); break;
+        case 24411: strcpy(name, "CHUN-LI (Water)"); break;
+        case 24412: strcpy(name, "CHUN-LI (Fire)"); break;
+        case 24413: strcpy(name, "CHUN-LI (Wind)"); break;
+        case 24414: strcpy(name, "CHUN-LI (Light)"); break;
+        case 24415: strcpy(name, "CHUN-LI (Dark)"); break;
+        case 24501: strcpy(name, "Striker (Water)"); break;
+        case 24502: strcpy(name, "Striker (Fire)"); break;
+        case 24503: strcpy(name, "Striker (Wind)"); break;
+        case 24504: strcpy(name, "Striker (Light)"); break;
+        case 24505: strcpy(name, "Striker (Dark)"); break;
+        case 24511: strcpy(name, "Moore"); break;
+        case 24512: strcpy(name, "Douglas"); break;
+        case 24513: strcpy(name, "Kashmir"); break;
+        case 24514: strcpy(name, "Talisman"); break;
+        case 24515: strcpy(name, "Vancliffe"); break;
+        case 24602: strcpy(name, "Shadow Claw (Fire)"); break;
+        case 24612: strcpy(name, "Bernadotte"); break;
+        case 24701: strcpy(name, "Slayer (Water)"); break;
+        case 24702: strcpy(name, "Slayer (Fire)"); break;
+        case 24703: strcpy(name, "Slayer (Wind)"); break;
+        case 24704: strcpy(name, "Slayer (Light)"); break;
+        case 24705: strcpy(name, "Slayer (Dark)"); break;
+        case 24711: strcpy(name, "Borgnine"); break;
+        case 24712: strcpy(name, "Karnal"); break;
+        case 24713: strcpy(name, "Sagar"); break;
+        case 24714: strcpy(name, "Craig"); break;
+        case 24715: strcpy(name, "Gurkha"); break;
+        case 24801: strcpy(name, "Poison Master (Water)"); break;
+        case 24802: strcpy(name, "Poison Master (Fire)"); break;
+        case 24803: strcpy(name, "Poison Master (Wind)"); break;
+        case 24804: strcpy(name, "Poison Master (Light)"); break;
+        case 24805: strcpy(name, "Poison Master (Dark)"); break;
+        case 24811: strcpy(name, "Kyle"); break;
+        case 24812: strcpy(name, "Todd"); break;
+        case 24813: strcpy(name, "Jarrett"); break;
+        case 24814: strcpy(name, "Hekerson"); break;
+        case 24815: strcpy(name, "Cayde"); break;
+        case 24901: strcpy(name, "Blade Dancer (Water)"); break;
+        case 24902: strcpy(name, "Blade Dancer (Fire)"); break;
+        case 24903: strcpy(name, "Blade Dancer (Wind)"); break;
+        case 24904: strcpy(name, "Blade Dancer (Light)"); break;
+        case 24905: strcpy(name, "Blade Dancer (Dark)"); break;
+        case 24911: strcpy(name, "Lariel"); break;
+        case 24912: strcpy(name, "Berenice"); break;
+        case 24913: strcpy(name, "Cordelia"); break;
+        case 24914: strcpy(name, "Leah"); break;
+        case 24915: strcpy(name, "Vereesa"); break;
+        case 40101: strcpy(name, "Inugami (Water)"); break;
+        case 40201: strcpy(name, "Phoenix (Water)"); break;
+        case 40302: strcpy(name, "Golem (Fire)"); break;
+        case 40403: strcpy(name, "Sylphid (Wind)"); break;
+        case 40501: strcpy(name, "Undine (Water)"); break;
+        case 40602: strcpy(name, "Inferno (Fire)"); break;
+        case 40703: strcpy(name, "Chimera (Wind)"); break;
+        case 40803: strcpy(name, "Salamander (Wind)"); break;
+        case 40903: strcpy(name, "Sylph (Wind)"); break;
+        case 41006: strcpy(name, "Otherworldly Dragon (Pure)"); break;
+        case 41101: strcpy(name, "Death Knight (Water)"); break;
+        case 41202: strcpy(name, "Lich (Fire)"); break;
+        case 41303: strcpy(name, "Keeper of Remains (Wind)"); break;
+        case 41401: strcpy(name, "Contaminated Dragon (Water)"); break;
+        case 42006: strcpy(name, "Ath'taros (Pure)"); break;
+        case 42106: strcpy(name, "Lyrith (Pure)"); break;
+        case 42206: strcpy(name, "Lyrith (Pure)"); break;
+        case 43001: strcpy(name, "Ice Beast (Water)"); break;
+        case 43002: strcpy(name, "Fire Beast (Fire)"); break;
+        case 43003: strcpy(name, "Wind Beast (Wind)"); break;
+        case 43004: strcpy(name, "Light Beast (Light)"); break;
+        case 43005: strcpy(name, "Dark Beast (Dark)"); break;
+        case 44007: strcpy(name, "Chaos Beast Khi'zar Kha'jul (Pure)"); break;
+        case 44008: strcpy(name, "Chaos Beast Khi'zar Kha'jul (Pure)"); break;
+        case 44009: strcpy(name, "Chaos Beast Khi'zar Kha'jul (Pure)"); break;
+        case 45001: strcpy(name, "형상아이템용 더미(물) (Water)"); break;
+        case 45002: strcpy(name, "형상아이템용 더미(불) (Fire)"); break;
+        case 45003: strcpy(name, "형상아이템용 더미(바람) (Wind)"); break;
+        case 45004: strcpy(name, "형상아이템용 더미(빛) (Light)"); break;
+        case 45005: strcpy(name, "형상아이템용 더미(어둠) (Dark)"); break;
+        case 46001: strcpy(name, "Tartarus (Pure)"); break;
+        case 46002: strcpy(name, "미궁 보스 머리 (Pure)"); break;
+        case 46003: strcpy(name, "미궁 보스 왼쪽팔 (Pure)"); break;
+        case 46004: strcpy(name, "미궁 보스 오른쪽팔 (Pure)"); break;
+        case 46101: strcpy(name, "Leos (Water)"); break;
+        case 46102: strcpy(name, "Kotos (Fire)"); break;
+        case 46103: strcpy(name, "Guilles (Wind)"); break;
+        case 46201: strcpy(name, "미궁 룬문양 (물) (Water)"); break;
+        case 46202: strcpy(name, "미궁 룬문양 (불) (Fire)"); break;
+        case 46203: strcpy(name, "미궁 룬문양 (바람) (Wind)"); break;
+        case 46301: strcpy(name, "Leos (Water)"); break;
+        case 46302: strcpy(name, "Kotos (Fire)"); break;
+        case 46303: strcpy(name, "Guilles (Wind)"); break;
+        case 46304: strcpy(name, "Leos (Water)"); break;
+        case 46305: strcpy(name, "Kotos (Fire)"); break;
+        case 46306: strcpy(name, "Guilles (Wind)"); break;
+        case 46307: strcpy(name, "Leos (Water)"); break;
+        case 46308: strcpy(name, "Kotos (Fire)"); break;
+        case 46309: strcpy(name, "Guilles (Wind)"); break;
+        case 47001: strcpy(name, "Ancient Guardian (Water)"); break;
+        case 47002: strcpy(name, "Ancient Guardian (Wind)"); break;
+        case 47003: strcpy(name, "Ancient Guardian (Fire)"); break;
+        case 47101: strcpy(name, "Fairy 2A (Water)"); break;
+        case 47102: strcpy(name, "Fairy 2A (Fire)"); break;
+        case 47103: strcpy(name, "Fairy 2A (Wind)"); break;
+        case 47104: strcpy(name, "Fairy 2A (Light)"); break;
+        case 47105: strcpy(name, "Fairy 2A (Dark)"); break;
+        case 47201: strcpy(name, "Pixie 2A (Water)"); break;
+        case 47202: strcpy(name, "Pixie 2A (Fire)"); break;
+        case 47203: strcpy(name, "Pixie 2A (Wind)"); break;
+        case 47204: strcpy(name, "Pixie 2A (Light)"); break;
+        case 47205: strcpy(name, "Pixie 2A (Dark)"); break;
+        case 47301: strcpy(name, "Warbear 2A (Water)"); break;
+        case 47302: strcpy(name, "Warbear 2A (Fire)"); break;
+        case 47303: strcpy(name, "Warbear 2A (Wind)"); break;
+        case 47304: strcpy(name, "Warbear 2A (Light)"); break;
+        case 47305: strcpy(name, "Warbear 2A (Dark)"); break;
+        case 47401: strcpy(name, "Inugami 2A (Water)"); break;
+        case 47402: strcpy(name, "Inugami 2A (Fire)"); break;
+        case 47403: strcpy(name, "Inugami 2A (Wind)"); break;
+        case 47404: strcpy(name, "Inugami 2A (Light)"); break;
+        case 47405: strcpy(name, "Inugami 2A (Dark)"); break;
+        case 47501: strcpy(name, "Werewolf 2A (Water)"); break;
+        case 47502: strcpy(name, "Werewolf 2A (Fire)"); break;
+        case 47503: strcpy(name, "Werewolf 2A (Wind)"); break;
+        case 47504: strcpy(name, "Werewolf 2A (Light)"); break;
+        case 47505: strcpy(name, "Werewolf 2A (Dark)"); break;
+        case 47601: strcpy(name, "Martial Cat 2A (Water)"); break;
+        case 47602: strcpy(name, "Martial Cat 2A (Fire)"); break;
+        case 47603: strcpy(name, "Martial Cat 2A (Wind)"); break;
+        case 47604: strcpy(name, "Martial Cat 2A (Light)"); break;
+        case 47605: strcpy(name, "Martial Cat 2A (Dark)"); break;
+        case 47701: strcpy(name, "Griffon 2A (Water)"); break;
+        case 47702: strcpy(name, "Griffon 2A (Fire)"); break;
+        case 47703: strcpy(name, "Griffon 2A (Wind)"); break;
+        case 47704: strcpy(name, "Griffon 2A (Light)"); break;
+        case 47705: strcpy(name, "Griffon 2A (Dark)"); break;
+        case 60101: strcpy(name, "Keeper of Water (Water)"); break;
+        case 60102: strcpy(name, "Keeper of Fire (Fire)"); break;
+        case 60103: strcpy(name, "Keeper of Wind (Wind)"); break;
+        case 60104: strcpy(name, "Keeper of Light (Light)"); break;
+        case 60105: strcpy(name, "Keeper of Darkness (Dark)"); break;
+        case 60201: strcpy(name, "Ancient Giant (Water)"); break;
+        case 60202: strcpy(name, "Ancient Giant (Fire)"); break;
+        case 60203: strcpy(name, "Ancient Giant (Wind)"); break;
+        case 60204: strcpy(name, "Ancient Giant (Light)"); break;
+        case 60205: strcpy(name, "Ancient Giant (Dark)"); break;
+        case 60301: strcpy(name, "Legendary Dragon (Water)"); break;
+        case 60302: strcpy(name, "Legendary Dragon (Fire)"); break;
+        case 60303: strcpy(name, "Legendary Dragon (Wind)"); break;
+        case 60304: strcpy(name, "Legendary Dragon (Light)"); break;
+        case 60305: strcpy(name, "Legendary Dragon (Dark)"); break;
+        case 60401: strcpy(name, "Angelmon (Water)"); break;
+        case 60402: strcpy(name, "Angelmon (Fire)"); break;
+        case 60403: strcpy(name, "Angelmon (Wind)"); break;
+        case 60404: strcpy(name, "Angelmon (Light)"); break;
+        case 60405: strcpy(name, "Angelmon (Dark)"); break;
+        case 60501: strcpy(name, "Angelmon (Water)"); break;
+        case 60502: strcpy(name, "Angelmon (Fire)"); break;
+        case 60503: strcpy(name, "Angelmon (Wind)"); break;
+        case 60504: strcpy(name, "Angelmon (Light)"); break;
+        case 60505: strcpy(name, "Angelmon (Dark)"); break;
+        case 60601: strcpy(name, "Angelmon (Water)"); break;
+        case 60602: strcpy(name, "Angelmon (Fire)"); break;
+        case 60603: strcpy(name, "Angelmon (Wind)"); break;
+        case 60604: strcpy(name, "Angelmon (Light)"); break;
+        case 60605: strcpy(name, "Angelmon (Dark)"); break;
+        case 60701: strcpy(name, "Angelmon (Water)"); break;
+        case 60702: strcpy(name, "Angelmon (Fire)"); break;
+        case 60703: strcpy(name, "Angelmon (Wind)"); break;
+        case 60704: strcpy(name, "Angelmon (Light)"); break;
+        case 60705: strcpy(name, "Angelmon (Dark)"); break;
+        case 60804: strcpy(name, "Rainbowmon (Light)"); break;
+        case 60805: strcpy(name, "Devilmon (Dark)"); break;
+        case 60904: strcpy(name, "Rainbowmon (Light)"); break;
+        case 60905: strcpy(name, "Devilmon (Dark)"); break;
+        case 61004: strcpy(name, "Rainbowmon (Light)"); break;
+        case 61005: strcpy(name, "Devilmon (Dark)"); break;
+        case 61104: strcpy(name, "Rainbowmon (Light)"); break;
+        case 61105: strcpy(name, "Devilmon (Dark)"); break;
+        case 62004: strcpy(name, "Keeper of Magic (Light)"); break;
+        case 62101: strcpy(name, "Ancient Lich King (Water)"); break;
+        case 62102: strcpy(name, "Ancient Lich King (Fire)"); break;
+        case 62103: strcpy(name, "Ancient Lich King (Wind)"); break;
+        case 62104: strcpy(name, "Ancient Lich King (Light)"); break;
+        case 62105: strcpy(name, "Ancient Lich King (Dark)"); break;
+        case 62200: strcpy(name, "월드보스-고대골렘 (Water)"); break;
+        case 62303: strcpy(name, "Ancient Intercessor (Wind)"); break;
+        case 62403: strcpy(name, "Ancient Tormentor (Wind)"); break;
+        case 62504: strcpy(name, "Ancient Intercessor (Light)"); break;
+        case 62604: strcpy(name, "Ancient Punisher (Light)"); break;
+        case 63102: strcpy(name, "만랩튜토리얼보스(불) (Fire)"); break;
+        case 63202: strcpy(name, "만랩튜토리얼_드래곤(불) (Fire)"); break;
+        case 63301: strcpy(name, "만랩튜토리얼_가고일(물) (Water)"); break;
+        case 63302: strcpy(name, "만랩튜토리얼_가고일(불) (Fire)"); break;
+        case 63303: strcpy(name, "만랩튜토리얼_가고일(바람) (Wind)"); break;
+        case 70001: strcpy(name, "Dimension Predator (Water)"); break;
+        case 70002: strcpy(name, "Dimension Predator (Fire)"); break;
+        case 70003: strcpy(name, "Dimension Predator (Wind)"); break;
+        case 70004: strcpy(name, "Dimension Predator (Light)"); break;
+        case 70005: strcpy(name, "Dimension Predator (Dark)"); break;
+        case 70101: strcpy(name, "Dimension Predator (Water)"); break;
+        case 70102: strcpy(name, "Dimension Predator (Fire)"); break;
+        case 70103: strcpy(name, "Dimension Predator (Wind)"); break;
+        case 70104: strcpy(name, "Dimension Predator (Light)"); break;
+        case 70105: strcpy(name, "Dimension Predator (Dark)"); break;
+        case 70201: strcpy(name, "Dimension Predator (Water)"); break;
+        case 70202: strcpy(name, "Dimension Predator (Fire)"); break;
+        case 70203: strcpy(name, "Dimension Predator (Wind)"); break;
+        case 70204: strcpy(name, "Dimension Predator (Light)"); break;
+        case 70205: strcpy(name, "Dimension Predator (Dark)"); break;
+        case 71004: strcpy(name, "Hollow (Light)"); break;
+        case 71005: strcpy(name, "Hollow (Dark)"); break;
+        case 71101: strcpy(name, "Void (Water)"); break;
+        case 71102: strcpy(name, "Void (Fire)"); break;
+        case 71103: strcpy(name, "Void (Wind)"); break;
+        case 100116: strcpy(name, "Tower (Pure)"); break;
+        case 100126: strcpy(name, "Tower (Pure)"); break;
+        case 100136: strcpy(name, "Tower (Pure)"); break;
+        case 100146: strcpy(name, "Tower (Pure)"); break;
+        case 100156: strcpy(name, "Tower (Pure)"); break;
+        case 100216: strcpy(name, "Tower (Pure)"); break;
+        case 100226: strcpy(name, "Tower (Pure)"); break;
+        case 100236: strcpy(name, "Tower (Pure)"); break;
+        case 100246: strcpy(name, "Tower (Pure)"); break;
+        case 100256: strcpy(name, "Tower (Pure)"); break;
+        case 100316: strcpy(name, "Tower (Pure)"); break;
+        case 100326: strcpy(name, "Tower (Pure)"); break;
+        case 100336: strcpy(name, "Tower (Pure)"); break;
+        case 100346: strcpy(name, "Tower (Pure)"); break;
+        case 100356: strcpy(name, "Tower (Pure)"); break;
+        case 100416: strcpy(name, "Tower (Pure)"); break;
+        case 100426: strcpy(name, "Tower (Pure)"); break;
+        case 100436: strcpy(name, "Tower (Pure)"); break;
+        case 100446: strcpy(name, "Tower (Pure)"); break;
+        case 100456: strcpy(name, "Tower (Pure)"); break;
+        case 100516: strcpy(name, "Tower (Pure)"); break;
+        case 100526: strcpy(name, "Tower (Pure)"); break;
+        case 100536: strcpy(name, "Tower (Pure)"); break;
+        case 100546: strcpy(name, "Tower (Pure)"); break;
+        case 100556: strcpy(name, "Tower (Pure)"); break;
+        case 100616: strcpy(name, "Tower (Pure)"); break;
+        case 100626: strcpy(name, "Tower (Pure)"); break;
+        case 100636: strcpy(name, "Tower (Pure)"); break;
+        case 100646: strcpy(name, "Tower (Pure)"); break;
+        case 100656: strcpy(name, "Tower (Pure)"); break;
+        case 100716: strcpy(name, "Tower (Pure)"); break;
+        case 100726: strcpy(name, "Tower (Pure)"); break;
+        case 100736: strcpy(name, "Tower (Pure)"); break;
+        case 100746: strcpy(name, "Tower (Pure)"); break;
+        case 100756: strcpy(name, "Tower (Pure)"); break;
+        case 100816: strcpy(name, "Tower (Pure)"); break;
+        case 100826: strcpy(name, "Tower (Pure)"); break;
+        case 100836: strcpy(name, "Tower (Pure)"); break;
+        case 100846: strcpy(name, "Tower (Pure)"); break;
+        case 100856: strcpy(name, "Tower (Pure)"); break;
+        case 100916: strcpy(name, "Tower (Pure)"); break;
+        case 100926: strcpy(name, "Tower (Pure)"); break;
+        case 100936: strcpy(name, "Tower (Pure)"); break;
+        case 100946: strcpy(name, "Tower (Pure)"); break;
+        case 100956: strcpy(name, "Tower (Pure)"); break;
+        case 101016: strcpy(name, "Tower (Pure)"); break;
+        case 101026: strcpy(name, "Tower (Pure)"); break;
+        case 101036: strcpy(name, "Tower (Pure)"); break;
+        case 101046: strcpy(name, "Tower (Pure)"); break;
+        case 101056: strcpy(name, "Tower (Pure)"); break;
+        case 101116: strcpy(name, "Tower (Pure)"); break;
+        case 101126: strcpy(name, "Tower (Pure)"); break;
+        case 101136: strcpy(name, "Tower (Pure)"); break;
+        case 101146: strcpy(name, "Tower (Pure)"); break;
+        case 101156: strcpy(name, "Tower (Pure)"); break;
+        case 101216: strcpy(name, "Tower (Pure)"); break;
+        case 101226: strcpy(name, "Tower (Pure)"); break;
+        case 101236: strcpy(name, "Tower (Pure)"); break;
+        case 101246: strcpy(name, "Tower (Pure)"); break;
+        case 101256: strcpy(name, "Tower (Pure)"); break;
+        case 101316: strcpy(name, "Tower (Pure)"); break;
+        case 101326: strcpy(name, "Tower (Pure)"); break;
+        case 101336: strcpy(name, "Tower (Pure)"); break;
+        case 101346: strcpy(name, "Tower (Pure)"); break;
+        case 101356: strcpy(name, "Tower (Pure)"); break;
+        case 101416: strcpy(name, "Tower (Pure)"); break;
+        case 101426: strcpy(name, "Tower (Pure)"); break;
+        case 101436: strcpy(name, "Tower (Pure)"); break;
+        case 101446: strcpy(name, "Tower (Pure)"); break;
+        case 101456: strcpy(name, "Tower (Pure)"); break;
+        case 101516: strcpy(name, "Tower (Pure)"); break;
+        case 101526: strcpy(name, "Tower (Pure)"); break;
+        case 101536: strcpy(name, "Tower (Pure)"); break;
+        case 101546: strcpy(name, "Tower (Pure)"); break;
+        case 101556: strcpy(name, "Tower (Pure)"); break;
+        case 101616: strcpy(name, "타워(물) - 전체 충격 수정 (Pure)"); break;
+        case 101626: strcpy(name, "타워(불) - 전체 충격 수정 (Pure)"); break;
+        case 101636: strcpy(name, "타워(바람) - 전체 충격 수정 (Pure)"); break;
+        case 101646: strcpy(name, "타워(빛) - 전체 충격 수정 (Pure)"); break;
+        case 101656: strcpy(name, "타워(어둠) - 전체 충격 수정 (Pure)"); break;
+        case 101716: strcpy(name, "타워(물) - 공속 게이지 (Pure)"); break;
+        case 101726: strcpy(name, "타워(불) - 공속 게이지 (Pure)"); break;
+        case 101736: strcpy(name, "타워(바람) - 공속 게이지 (Pure)"); break;
+        case 101746: strcpy(name, "타워(빛) - 공속 게이지 (Pure)"); break;
+        case 101756: strcpy(name, "타워(어둠) - 공속 게이지 (Pure)"); break;
+        case 110106: strcpy(name, "시험의탑 타워(왼쪽) (Pure)"); break;
+        case 110206: strcpy(name, "시험의탑 타워(오른쪽) (Pure)"); break;
+        case 110306: strcpy(name, "Incarnation of Greed (Pure)"); break;
+        case 110406: strcpy(name, "Incarnation of Vendetta (Pure)"); break;
+        case 110506: strcpy(name, "Incarnation of Protection (Pure)"); break;
+        case 110606: strcpy(name, "Incarnation of Greed (Pure)"); break;
+        case 110706: strcpy(name, "Incarnation of Vendetta (Pure)"); break;
+        case 110806: strcpy(name, "Incarnation of Protection (Pure)"); break;
+        case 110902: strcpy(name, "Fire Minion (Fire)"); break;
+        case 111006: strcpy(name, "만랩튜토타워_방어 약화 (Pure)"); break;
+        case 111016: strcpy(name, "만랩튜토타워_공격 강화 (Pure)"); break;
+        case 112023: strcpy(name, "Tower (Wind)"); break;
+        case 112033: strcpy(name, "Tower (Wind)"); break;
+        case 112124: strcpy(name, "Tower (Light)"); break;
+        case 112134: strcpy(name, "Tower (Light)"); break;
+        case 120101: strcpy(name, "Tower (Water)"); break;
+        case 120102: strcpy(name, "Tower (Fire)"); break;
+        case 120103: strcpy(name, "Tower (Wind)"); break;
+        case 120104: strcpy(name, "Tower (Light)"); break;
+        case 120105: strcpy(name, "Tower (Dark)"); break;
+        case 120111: strcpy(name, "Tower (Water)"); break;
+        case 120112: strcpy(name, "Tower (Fire)"); break;
+        case 120113: strcpy(name, "Tower (Wind)"); break;
+        case 120114: strcpy(name, "Tower (Light)"); break;
+        case 120115: strcpy(name, "Tower (Dark)"); break;
+        case 120201: strcpy(name, "Tower (Water)"); break;
+        case 120202: strcpy(name, "Tower (Fire)"); break;
+        case 120203: strcpy(name, "Tower (Wind)"); break;
+        case 120204: strcpy(name, "Tower (Light)"); break;
+        case 120205: strcpy(name, "Tower (Dark)"); break;
+        case 120211: strcpy(name, "Tower (Water)"); break;
+        case 120212: strcpy(name, "Tower (Fire)"); break;
+        case 120213: strcpy(name, "Tower (Wind)"); break;
+        case 120214: strcpy(name, "Tower (Light)"); break;
+        case 120215: strcpy(name, "Tower (Dark)"); break;
+        case 120301: strcpy(name, "Tower (Water)"); break;
+        case 120302: strcpy(name, "Tower (Fire)"); break;
+        case 120303: strcpy(name, "Tower (Wind)"); break;
+        case 120304: strcpy(name, "Tower (Light)"); break;
+        case 120305: strcpy(name, "Tower (Dark)"); break;
+        case 120311: strcpy(name, "Tower (Water)"); break;
+        case 120312: strcpy(name, "Tower (Fire)"); break;
+        case 120313: strcpy(name, "Tower (Wind)"); break;
+        case 120314: strcpy(name, "Tower (Light)"); break;
+        case 120315: strcpy(name, "Tower (Dark)"); break;
+        case 120401: strcpy(name, "Tower (Water)"); break;
+        case 120402: strcpy(name, "Tower (Fire)"); break;
+        case 120403: strcpy(name, "Tower (Wind)"); break;
+        case 120404: strcpy(name, "Tower (Light)"); break;
+        case 120405: strcpy(name, "Tower (Dark)"); break;
+        case 120411: strcpy(name, "Tower (Water)"); break;
+        case 120412: strcpy(name, "Tower (Fire)"); break;
+        case 120413: strcpy(name, "Tower (Wind)"); break;
+        case 120414: strcpy(name, "Tower (Light)"); break;
+        case 120415: strcpy(name, "Tower (Dark)"); break;
+        case 120501: strcpy(name, "Tower (Water)"); break;
+        case 120502: strcpy(name, "Tower (Fire)"); break;
+        case 120503: strcpy(name, "Tower (Wind)"); break;
+        case 120504: strcpy(name, "Tower (Light)"); break;
+        case 120505: strcpy(name, "Tower (Dark)"); break;
+        case 120511: strcpy(name, "Tower (Water)"); break;
+        case 120512: strcpy(name, "Tower (Fire)"); break;
+        case 120513: strcpy(name, "Tower (Wind)"); break;
+        case 120514: strcpy(name, "Tower (Light)"); break;
+        case 120515: strcpy(name, "Tower (Dark)"); break;
+        case 120601: strcpy(name, "Tower (Water)"); break;
+        case 120602: strcpy(name, "Tower (Fire)"); break;
+        case 120603: strcpy(name, "Tower (Wind)"); break;
+        case 120604: strcpy(name, "Tower (Light)"); break;
+        case 120605: strcpy(name, "Tower (Dark)"); break;
+        case 120611: strcpy(name, "Tower (Water)"); break;
+        case 120612: strcpy(name, "Tower (Fire)"); break;
+        case 120613: strcpy(name, "Tower (Wind)"); break;
+        case 120614: strcpy(name, "Tower (Light)"); break;
+        case 120615: strcpy(name, "Tower (Dark)"); break;
+        case 120701: strcpy(name, "Tower (Water)"); break;
+        case 120702: strcpy(name, "Tower (Fire)"); break;
+        case 120703: strcpy(name, "Tower (Wind)"); break;
+        case 120704: strcpy(name, "Tower (Light)"); break;
+        case 120705: strcpy(name, "Tower (Dark)"); break;
+        case 120711: strcpy(name, "Tower (Water)"); break;
+        case 120712: strcpy(name, "Tower (Fire)"); break;
+        case 120713: strcpy(name, "Tower (Wind)"); break;
+        case 120714: strcpy(name, "Tower (Light)"); break;
+        case 120715: strcpy(name, "Tower (Dark)"); break;
+        case 200103: strcpy(name, "Small Crystal (Wind)"); break;
+        case 200113: strcpy(name, "Medium Crystal (Wind)"); break;
+        case 200204: strcpy(name, "Small Crystal (Light)"); break;
+        case 200214: strcpy(name, "Medium Crystal (Light)"); break;
+        case 210106: strcpy(name, "Small Crystal (Pure)"); break;
+        case 210206: strcpy(name, "Small Crystal (Pure)"); break;
+        case 210306: strcpy(name, "Small Crystal (Pure)"); break;
+        case 210406: strcpy(name, "Small Crystal (Pure)"); break;
+        case 210506: strcpy(name, "Small Crystal (Pure)"); break;
+        case 210606: strcpy(name, "Medium Crystal (Pure)"); break;
+        case 210706: strcpy(name, "Medium Crystal (Pure)"); break;
+        case 210806: strcpy(name, "Medium Crystal (Pure)"); break;
+        case 210906: strcpy(name, "Medium Crystal (Pure)"); break;
+        case 211006: strcpy(name, "Medium Crystal (Pure)"); break;
+        case 220001: strcpy(name, "Small Crystal (Water)"); break;
+        case 220002: strcpy(name, "Small Crystal (Fire)"); break;
+        case 220003: strcpy(name, "Small Crystal (Wind)"); break;
+        case 220004: strcpy(name, "Small Crystal (Light)"); break;
+        case 220005: strcpy(name, "Small Crystal (Dark)"); break;
+        case 220011: strcpy(name, "Medium Crystal (Water)"); break;
+        case 220012: strcpy(name, "Medium Crystal (Fire)"); break;
+        case 220013: strcpy(name, "Medium Crystal (Wind)"); break;
+        case 220014: strcpy(name, "Medium Crystal (Light)"); break;
+        case 220015: strcpy(name, "Medium Crystal (Dark)"); break;
+        case 310106: strcpy(name, "Taotie (Pure)"); break;
+        case 310206: strcpy(name, "Turtle (Pure)"); break;
+        case 310306: strcpy(name, "Ice Beast (Pure)"); break;
+        case 400001: strcpy(name, "Predator's Wreckage (Water)"); break;
+        case 400002: strcpy(name, "Predator's Wreckage (Fire)"); break;
+        case 400003: strcpy(name, "Predator's Wreckage (Wind)"); break;
+        case 400004: strcpy(name, "Predator's Wreckage (Light)"); break;
+        case 400005: strcpy(name, "Predator's Wreckage (Dark)"); break;
+        case 400006: strcpy(name, "Predator's Wreckage (Water)"); break;
+        case 400007: strcpy(name, "Predator's Wreckage (Fire)"); break;
+        case 400008: strcpy(name, "Predator's Wreckage (Wind)"); break;
+        case 400009: strcpy(name, "Predator's Wreckage (Light)"); break;
+        case 400010: strcpy(name, "Predator's Wreckage (Dark)"); break;
+        case 1000101: strcpy(name, "Homunculus(Attack) (Water)"); break;
+        case 1000102: strcpy(name, "Homunculus(Attack) (Fire)"); break;
+        case 1000103: strcpy(name, "Homunculus(Attack) (Wind)"); break;
+        case 1000111: strcpy(name, "Homunculus(Attack)"); break;
+        case 1000112: strcpy(name, "Homunculus(Attack)"); break;
+        case 1000113: strcpy(name, "Homunculus(Attack)"); break;
+        case 1000204: strcpy(name, "Homunculus(Support) (Light)"); break;
+        case 1000205: strcpy(name, "Homunculus(Support) (Dark)"); break;
+        case 1000214: strcpy(name, "Homunculus(Support)"); break;
+        case 1000215: strcpy(name, "Homunculus(Support)"); break;
+        case 10101: strcpy(name, "Fairy (Water)"); break;
+        case 13231: strcpy(name, "Lulu and Friends (2A)"); break;
+        case 13232: strcpy(name, "Lala and Friends (2A)"); break;
+        case 13233: strcpy(name, "Chichi and Friends (2A)"); break;
+        case 13234: strcpy(name, "Shushu and Friends (2A)"); break;
+        case 13235: strcpy(name, "Chacha and Friends (2A)"); break;
+        case 16031: strcpy(name, "Hemos (2A)"); break;
+        case 16032: strcpy(name, "Sath (2A)"); break;
+        case 16033: strcpy(name, "Hiva (2A)"); break;
+        case 16034: strcpy(name, "Prom (2A)"); break;
+        case 16035: strcpy(name, "Thrain (2A)"); break;
+        case 47004: strcpy(name, "Ancient Guardian (Dark)"); break;
+        case 47801: strcpy(name, "Lulu and Friends (Water)"); break;
+        case 47802: strcpy(name, "Lala and Friends (Fire)"); break;
+        case 47803: strcpy(name, "Chichi and Friends (Wind)"); break;
+        case 47804: strcpy(name, "Shushu and Friends (Light)"); break;
+        case 47805: strcpy(name, "Chacha and Friends (Dark)"); break;
+        case 47901: strcpy(name, "Hemos (Water)"); break;
+        case 47902: strcpy(name, "Sath (Fire)"); break;
+        case 47903: strcpy(name, "Hiva (Wind)"); break;
+        case 47904: strcpy(name, "Prom (Light)"); break;
+        case 47905: strcpy(name, "Thrain (Dark)"); break;
+        case 120801: strcpy(name, "Tower (Water)"); break;
+        case 120802: strcpy(name, "Tower (Fire)"); break;
+        case 120803: strcpy(name, "Tower (Wind)"); break;
+        case 120804: strcpy(name, "Tower (Light)"); break;
+        case 120805: strcpy(name, "Tower (Dark)"); break;
+        case 120811: strcpy(name, "Tower (Water)"); break;
+        case 120812: strcpy(name, "Tower (Fire)"); break;
+        case 120813: strcpy(name, "Tower (Wind)"); break;
+        case 120814: strcpy(name, "Tower (Light)"); break;
+        case 120815: strcpy(name, "Tower (Dark)"); break;
+        case 120901: strcpy(name, "Tower (Water)"); break;
+        case 120902: strcpy(name, "Tower (Fire)"); break;
+        case 120903: strcpy(name, "Tower (Wind)"); break;
+        case 120904: strcpy(name, "Tower (Light)"); break;
+        case 120905: strcpy(name, "Tower (Dark)"); break;
+        case 120911: strcpy(name, "Tower (Water)"); break;
+        case 120912: strcpy(name, "Tower (Fire)"); break;
+        case 120913: strcpy(name, "Tower (Wind)"); break;
+        case 120914: strcpy(name, "Tower (Light)"); break;
+        case 120915: strcpy(name, "Tower (Dark)"); break;
+        case 25001: strcpy(name, "Onmyouji (Water)"); break;
+        case 25002: strcpy(name, "Onmyouji (Fire)"); break;
+        case 25003: strcpy(name, "Onmyouji (Wind)"); break;
+        case 25004: strcpy(name, "Onmyouji (Light)"); break;
+        case 25005: strcpy(name, "Onmyouji (Dark)"); break;
+        case 25011: strcpy(name, "Shizuka"); break;
+        case 25012: strcpy(name, "Tomoe"); break;
+        case 25013: strcpy(name, "Giou"); break;
+        case 25014: strcpy(name, "Seimei"); break;
+        case 25015: strcpy(name, "Douman"); break;
+        case 25101: strcpy(name, "Onimusha (Water)"); break;
+        case 25102: strcpy(name, "Onimusha (Fire)"); break;
+        case 25103: strcpy(name, "Onimusha (Wind)"); break;
+        case 25104: strcpy(name, "Onimusha (Light)"); break;
+        case 25105: strcpy(name, "Onimusha (Dark)"); break;
+        case 25111: strcpy(name, "Suiki"); break;
+        case 25112: strcpy(name, "Kaki"); break;
+        case 25113: strcpy(name, "Fuuki"); break;
+        case 25114: strcpy(name, "Kinki"); break;
+        case 25115: strcpy(name, "Ongyouki"); break;
+        case 12031: strcpy(name, "Ellena (2A)"); break;
+        case 12032: strcpy(name, "Kahli (2A)"); break;
+        case 12033: strcpy(name, "Moria (2A)"); break;
+        case 12034: strcpy(name, "Shren (2A)"); break;
+        case 12035: strcpy(name, "Jumaline (2A)"); break;
+        case 48001: strcpy(name, "하이엘리멘탈 2차 각성 보스(물) (Water)"); break;
+        case 48002: strcpy(name, "하이엘리멘탈 2차 각성 보스(불) (Fire)"); break;
+        case 48003: strcpy(name, "하이엘리멘탈 2차 각성 보스(바람) (Wind)"); break;
+        case 48004: strcpy(name, "하이엘리멘탈 2차 각성 보스(빛) (Light)"); break;
+        case 48005: strcpy(name, "하이엘리멘탈 2차 각성 보스(어둠) (Dark)"); break;
+        case 121001: strcpy(name, "2차각성 하이엘리멘탈 수정_왼쪽(물) (Water)"); break;
+        case 121002: strcpy(name, "2차각성 하이엘리멘탈 수정_왼쪽(불) (Fire)"); break;
+        case 121003: strcpy(name, "2차각성 하이엘리멘탈 수정_왼쪽(바람) (Wind)"); break;
+        case 121004: strcpy(name, "2차각성 하이엘리멘탈 수정_왼쪽(빛) (Light)"); break;
+        case 121005: strcpy(name, "2차각성 하이엘리멘탈 수정_왼쪽(어둠) (Dark)"); break;
+        case 121011: strcpy(name, "2차각성 하이엘리멘탈 수정_오른쪽(물) (Water)"); break;
+        case 121012: strcpy(name, "2차각성 하이엘리멘탈 수정_오른쪽(불) (Fire)"); break;
+        case 121013: strcpy(name, "2차각성 하이엘리멘탈 수정_오른쪽(바람) (Wind)"); break;
+        case 121014: strcpy(name, "2차각성 하이엘리멘탈 수정_오른쪽(빛) (Light)"); break;
+        case 121015: strcpy(name, "2차각성 하이엘리멘탈 수정_오른쪽(어둠) (Dark)"); break;
+        case 25201: strcpy(name, "Mage (Water)"); break;
+        case 25202: strcpy(name, "Mage (Fire)"); break;
+        case 25203: strcpy(name, "Mage (Wind)"); break;
+        case 25204: strcpy(name, "Mage (Light)"); break;
+        case 25205: strcpy(name, "Mage (Dark)"); break;
+        case 25211: strcpy(name, "Nana"); break;
+        case 25212: strcpy(name, "Coco"); break;
+        case 25213: strcpy(name, "Momo"); break;
+        case 25214: strcpy(name, "Dorothy"); break;
+        case 25215: strcpy(name, "Kiki"); break;
+        case 25301: strcpy(name, "Sky Surfer (Water)"); break;
+        case 25302: strcpy(name, "Sky Surfer (Fire)"); break;
+        case 25303: strcpy(name, "Sky Surfer (Wind)"); break;
+        case 25304: strcpy(name, "Sky Surfer (Light)"); break;
+        case 25305: strcpy(name, "Sky Surfer (Dark)"); break;
+        case 25311: strcpy(name, "Miles"); break;
+        case 25312: strcpy(name, "John"); break;
+        case 25313: strcpy(name, "Oliver"); break;
+        case 25314: strcpy(name, "Daniel"); break;
+        case 25315: strcpy(name, "Jackson"); break;
+        case 25401: strcpy(name, "ROBO (Water)"); break;
+        case 25402: strcpy(name, "ROBO (Fire)"); break;
+        case 25403: strcpy(name, "ROBO (Wind)"); break;
+        case 25404: strcpy(name, "ROBO (Light)"); break;
+        case 25405: strcpy(name, "ROBO (Dark)"); break;
+        case 25411: strcpy(name, "ROBO-R40"); break;
+        case 25412: strcpy(name, "ROBO-P27"); break;
+        case 25413: strcpy(name, "ROBO-G92"); break;
+        case 25414: strcpy(name, "ROBO-E65"); break;
+        case 25415: strcpy(name, "ROBO-F29"); break;
+        case 25501: strcpy(name, "ROBO(물)_잔해 (Water)"); break;
+        case 25511: strcpy(name, "ROBO(물)_잔해 (Water)"); break;
+        case 20121: strcpy(name, "Imperfect Neostone Agent (Water)"); break;
+        case 22123: strcpy(name, "Imperfect Dryad (Wind)"); break;
+        case 25601: strcpy(name, "Totemist (Water)"); break;
+        case 25602: strcpy(name, "Totemist (Fire)"); break;
+        case 25603: strcpy(name, "Totemist (Wind)"); break;
+        case 25604: strcpy(name, "Totemist (Light)"); break;
+        case 25605: strcpy(name, "Totemist (Dark)"); break;
+        case 25611: strcpy(name, "Aaliyah"); break;
+        case 25612: strcpy(name, "Nora"); break;
+        case 25613: strcpy(name, "Riley"); break;
+        case 25614: strcpy(name, "Ella"); break;
+        case 25615: strcpy(name, "Maya"); break;
+        default: strcpy(name, "UNKNOWN MONSTER");
+    }
+}

+ 46 - 0
src/RuneOptimizer/update/update_info.c

@@ -0,0 +1,46 @@
+/*
+ * This file is part of RuneOptimizer.
+ *
+ * RuneOptimizer is free software: you can redistribute it and/or modify it
+ * under the terms of the GNU General Public License as published by the Free
+ * Software Foundation, either version 3 of the License, or (at your option)
+ * any later version.
+ *
+ * RuneOptimizer is distributed in the hope that it will be useful, but WITHOUT
+ * ANY WARRANTY; without even the implied warranty of MERCHANTABILITY or
+ * FITNESS FOR A PARTICULAR PURPOSE. See the GNU General Public License for
+ * more details.
+ *
+ * You should have received a copy of the GNU General Public License along with
+ * RuneOptimizer. If not, see <https://www.gnu.org/licenses/>.
+ */
+
+int update_info(const char *id, const char *name, const char *level){
+    time_t t = time(NULL);
+    struct tm tm = *localtime(&t);
+    char ts[130];
+    sprintf(
+      ts,
+      "%d-%02d-%02d %02d:%02d:%02d",
+      tm.tm_year + 1900, tm.tm_mon + 1, tm.tm_mday,
+      tm.tm_hour, tm.tm_min, tm.tm_sec
+    );
+    char *query_parameters[5];
+    for (int i = 1; i < 5; i ++) query_parameters[i] = malloc(5);
+    sprintf(query_parameters[0], "%s", id);
+    sprintf(query_parameters[1], "%s", name);
+    sprintf(query_parameters[2], "%s", level);
+    query_parameters[3] = ts;
+    query_parameters[4] = "0"; // Modified, always 0.
+    if (
+      SUCCESS !=
+      db_execute(
+        "INSERT INTO info ( player_id, player_name, player_level, ts, modified)"
+        "VALUES (?, ?, ?, ?, ?)",
+        query_parameters
+      )
+    ){
+        fprintf(stderr, "Unable to save meta info: %s\n", sqlite3_errmsg(db));
+        return ERROR_DB_INSERT_INFO;
+    }
+}

+ 92 - 0
src/RuneOptimizer/update/update_json.c

@@ -0,0 +1,92 @@
+/*
+ * This file is part of RuneOptimizer.
+ *
+ * RuneOptimizer is free software: you can redistribute it and/or modify it
+ * under the terms of the GNU General Public License as published by the Free
+ * Software Foundation, either version 3 of the License, or (at your option)
+ * any later version.
+ *
+ * RuneOptimizer is distributed in the hope that it will be useful, but WITHOUT
+ * ANY WARRANTY; without even the implied warranty of MERCHANTABILITY or
+ * FITNESS FOR A PARTICULAR PURPOSE. See the GNU General Public License for
+ * more details.
+ *
+ * You should have received a copy of the GNU General Public License along with
+ * RuneOptimizer. If not, see <https://www.gnu.org/licenses/>.
+ */
+
+int update_json(
+  char file[], unsigned char six_stars,
+  unsigned char with_runes, unsigned char clear_teams, unsigned char gui
+){
+    // Counters for objcts saved
+    unsigned int total_units = 0;
+    unsigned int total_runes = 0;
+    unsigned int total_stats = 0;
+
+    if (gui == FALSE) printf("Updating from json file: %s\n", file);
+
+    // Read the JSON content
+    json_object *root = json_object_from_file(file);
+    if (!root){
+        fprintf(stderr, "Cant access file: %s\n", file);
+        return(ERROR_INPUT_UPDATE_UNKNOWN_SOURCE);
+    }
+
+    json_object *wizard_id = json_object_object_get(root, "wizard_id");
+    json_object *wizard_info = json_object_object_get(root, "wizard_info");
+    json_object *wizard_name =
+      json_object_object_get(wizard_info, "wizard_name");
+    json_object *wizard_level =
+      json_object_object_get(wizard_info, "wizard_level");
+    printf("Player ID: %s\n", json_object_get_string(wizard_id));
+    printf("Player name: %s\n", json_object_get_string(wizard_name));
+    printf("Player level: %s\n", json_object_get_string(wizard_level));
+    fflush(stdout); // To refresh GUI output.
+
+    // Recreate the database tables
+    int status = update_db_tables(clear_teams);
+    if (SUCCESS != status) return(status);
+
+    // Parse runes
+    json_object *runes = json_object_object_get(root, "runes");
+    int rune_count = json_object_array_length(runes);
+    json_object *idx;
+    for (int i = 0; i < rune_count; i++){
+        total_runes ++;
+        idx = json_object_array_get_idx(runes, i);
+        status = update_json_rune(idx, "");
+        if (status != -1) total_stats += status;
+    }
+
+    // Parse units
+    json_object *unit_list = json_object_object_get(root, "unit_list");
+    int unit_count = json_object_array_length(unit_list);
+    for (int i = 0; i < unit_count; i++){
+        idx = json_object_array_get_idx(unit_list, i);
+        
+        status = update_json_unit(
+          idx, six_stars, with_runes, &total_runes, &total_stats
+        );
+        if (status == 1) total_units ++;
+    }
+
+    status = update_current_stats();
+    if (SUCCESS != status) return(status);
+
+    // Insert into table info
+    status = update_info(
+      json_object_get_string(wizard_id),
+      json_object_get_string(wizard_name),
+      json_object_get_string(wizard_level)
+    );
+    if (SUCCESS != status) return(status);
+    
+    // All parsed
+    printf("%d units saved.\n", total_units);
+    printf("%d runes saved.\n", total_runes);
+    printf("%d rune stats saved.\n", total_stats);
+    printf("Player info updated\n");
+
+    return(SUCCESS);
+}

+ 235 - 0
src/RuneOptimizer/update/update_json_rune.c

@@ -0,0 +1,235 @@
+/*
+ * This file is part of RuneOptimizer.
+ *
+ * RuneOptimizer is free software: you can redistribute it and/or modify it
+ * under the terms of the GNU General Public License as published by the Free
+ * Software Foundation, either version 3 of the License, or (at your option)
+ * any later version.
+ *
+ * RuneOptimizer is distributed in the hope that it will be useful, but WITHOUT
+ * ANY WARRANTY; without even the implied warranty of MERCHANTABILITY or
+ * FITNESS FOR A PARTICULAR PURPOSE. See the GNU General Public License for
+ * more details.
+ *
+ * You should have received a copy of the GNU General Public License along with
+ * RuneOptimizer. If not, see <https://www.gnu.org/licenses/>.
+ */
+
+int update_json_rune(json_object *rune_json, char *unit_id){
+    int total_stats = 0;
+    DB_Rune rune;
+    char *query_parameters[43];
+    for (int i = 1; i < 43; i ++) query_parameters[i] = malloc(5);
+    // Rune ID
+    json_object *rune_id = json_object_object_get(rune_json, "rune_id");
+    strcpy(rune.id, json_object_get_string(rune_id));
+    // Rune unit
+    strcpy(rune.unit, unit_id);
+    // Rune slot
+    json_object *slot_no = json_object_object_get(rune_json, "slot_no");
+    rune.slot = json_object_get_int(slot_no);
+    // Rune quality (rank)
+    json_object *rank = json_object_object_get(rune_json, "rank");
+    rune.quality = json_object_get_int(rank);
+    // Rune stars (class)
+    json_object *class = json_object_object_get(rune_json, "class");
+    rune.stars = json_object_get_int(class);
+    // Rune set
+    json_object *set_id = json_object_object_get(rune_json, "set_id");
+    rune.set = json_object_get_int(set_id);
+    // Rune level (upgrade_curr)
+    json_object *upgrade_curr =
+      json_object_object_get(rune_json, "upgrade_curr");
+    rune.level = json_object_get_int(upgrade_curr);
+    // Rune value
+    json_object *base_value = json_object_object_get(rune_json, "base_value");
+    rune.buy_value = json_object_get_int(base_value);
+    // Rune sell value
+    json_object *sell_value = json_object_object_get(rune_json, "sell_value");
+    rune.sell_value = json_object_get_int(sell_value);
+    // Main stat
+    json_object *pri_eff = json_object_object_get(rune_json, "pri_eff");
+    json_object *pri_stat = json_object_array_get_idx(pri_eff, 0);
+    rune.main.stat = json_object_get_int(pri_stat);
+    json_object *pri_value = json_object_array_get_idx(pri_eff, 1);
+    rune.main.value = json_object_get_int(pri_value);
+    // Innate stat
+    json_object *prefix_eff = json_object_object_get(rune_json, "prefix_eff");
+    json_object *prefix_stat = json_object_array_get_idx(prefix_eff, 0);
+    rune.innate.stat = json_object_get_int(prefix_stat);
+    json_object *prefix_value = json_object_array_get_idx(prefix_eff, 1);
+    rune.innate.value = json_object_get_int(prefix_value);
+    json_object *sec_eff = json_object_object_get(rune_json, "sec_eff");
+    // Loop stats
+    int stat_count = json_object_array_length(sec_eff);
+    json_object *stat_json;
+    rune.stat_count = 0;
+    for (int i = 0; i < stat_count && i < 4; i++){
+        rune.stat_count ++;
+        stat_json = json_object_array_get_idx(sec_eff, i);
+        json_object *stat = json_object_array_get_idx(stat_json, 0);
+        rune.stats[i].stat = json_object_get_int(stat);
+        json_object *value = json_object_array_get_idx(stat_json, 1);
+        rune.stats[i].value = json_object_get_int(value);
+        json_object *enchant = json_object_array_get_idx(stat_json, 2);
+        rune.stats[i].enchant = json_object_get_int(enchant);
+        json_object *grind = json_object_array_get_idx(stat_json, 3);
+        rune.stats[i].grind = json_object_get_int(grind);
+    }
+
+    // All the rune info has been loaded. Now, calculate the rest of stats
+    update_rune_totals(&rune);
+
+    // Insert the rune into the database
+    query_parameters[0] = rune.id;
+    query_parameters[1] = unit_id;
+    sprintf(query_parameters[2], "%d", rune.set);
+    sprintf(query_parameters[3], "%d", rune.slot);
+    sprintf(query_parameters[4], "%d", rune.stars);
+    sprintf(query_parameters[5], "%d", rune.level);
+    sprintf(query_parameters[6], "%d", rune.quality);
+    sprintf(query_parameters[7], "%d", rune.efficiency);
+    sprintf(query_parameters[8], "%d", rune.max_efficiency);
+    sprintf(query_parameters[9], "%d", rune.main.stat);
+    sprintf(query_parameters[10], "%d", rune.current_hp_percent);
+    sprintf(query_parameters[11], "%d", rune.current_atk_percent);
+    sprintf(query_parameters[12], "%d", rune.current_def_percent);
+    sprintf(query_parameters[13], "%d", rune.current_hp_flat);
+    sprintf(query_parameters[14], "%d", rune.current_atk_flat);
+    sprintf(query_parameters[15], "%d", rune.current_def_flat);
+    sprintf(query_parameters[16], "%d", rune.current_spd);
+    sprintf(query_parameters[17], "%d", rune.current_crr);
+    sprintf(query_parameters[18], "%d", rune.current_crd);
+    sprintf(query_parameters[19], "%d", rune.current_acc);
+    sprintf(query_parameters[20], "%d", rune.current_res);
+    sprintf(query_parameters[21], "%d", rune.lv12_hp_percent);
+    sprintf(query_parameters[22], "%d", rune.lv12_atk_percent);
+    sprintf(query_parameters[23], "%d", rune.lv12_def_percent);
+    sprintf(query_parameters[24], "%d", rune.lv12_hp_flat);
+    sprintf(query_parameters[25], "%d", rune.lv12_atk_flat);
+    sprintf(query_parameters[26], "%d", rune.lv12_def_flat);
+    sprintf(query_parameters[27], "%d", rune.lv12_spd);
+    sprintf(query_parameters[28], "%d", rune.lv12_crr);
+    sprintf(query_parameters[29], "%d", rune.lv12_crd);
+    sprintf(query_parameters[30], "%d", rune.lv12_acc);
+    sprintf(query_parameters[31], "%d", rune.lv12_res);
+    sprintf(query_parameters[32], "%d", rune.lv15_hp_percent);
+    sprintf(query_parameters[33], "%d", rune.lv15_atk_percent);
+    sprintf(query_parameters[34], "%d", rune.lv15_def_percent);
+    sprintf(query_parameters[35], "%d", rune.lv15_hp_flat);
+    sprintf(query_parameters[36], "%d", rune.lv15_atk_flat);
+    sprintf(query_parameters[37], "%d", rune.lv15_def_flat);
+    sprintf(query_parameters[38], "%d", rune.lv15_spd);
+    sprintf(query_parameters[39], "%d", rune.lv15_crr);
+    sprintf(query_parameters[40], "%d", rune.lv15_crd);
+    sprintf(query_parameters[41], "%d", rune.lv15_acc);
+    sprintf(query_parameters[42], "%d", rune.lv15_res);
+    if (
+      SUCCESS !=
+      db_execute(
+        "INSERT INTO runes ("
+        "  id,                  unit,               type,"
+        "  slot,                stars,              level,"
+        "  quality,             efficiency,         max_efficiency,"
+        "  main_stat,           current_hp_percent, current_atk_percent,"
+        "  current_def_percent, current_hp_flat,    current_atk_flat,"
+        "  current_def_flat,    current_spd,        current_crr,"
+        "  current_crd,         current_acc,        current_res,"
+        "  lv12_hp_percent,     lv12_atk_percent,   lv12_def_percent,"
+        "  lv12_hp_flat,        lv12_atk_flat,      lv12_def_flat,"
+        "  lv12_spd,            lv12_crr,           lv12_crd,"
+        "  lv12_acc,            lv12_res,           lv15_hp_percent,"
+        "  lv15_atk_percent,    lv15_def_percent,   lv15_hp_flat,"
+        "  lv15_atk_flat,       lv15_def_flat,      lv15_spd,"
+        "  lv15_crr,            lv15_crd,           lv15_acc,"
+        "  lv15_res"
+        ") VALUES ("
+        "  ?, ?, ?, ?, ?, ?, ?, ?, ?, ?, ?, ?, ?, ?, ?, ?, ?, ?, ?, ?, ?,"
+        "  ?, ?, ?, ?, ?, ?, ?, ?, ?, ?, ?, ?, ?, ?, ?, ?, ?, ?, ?, ?, ?, ?"
+        ")",
+        query_parameters
+      )
+    ){
+        fprintf(stderr, "Unable to insert rune: %s\n", sqlite3_errmsg(db));
+        return(-1);
+    }
+
+    // Insert main stat
+    total_stats ++;
+    //query_parameters[0] = rune.id; // No need, already has id
+    query_parameters[1] = "-1"; // Main stat
+    sprintf(query_parameters[2], "%d", rune.main.stat);
+    sprintf(query_parameters[3], "%d", rune.main.value);
+    query_parameters[4] = "0"; // Mains can't be grinded.
+    query_parameters[5] = "0"; // Mains can't be enchanted.
+    if (
+      SUCCESS !=
+      db_execute(
+        "INSERT INTO rune_stats(rune, slot, stat, value, grind, enchant) "
+        "VALUES (?, ?, ?, ?, ?, ?)",
+      query_parameters
+      )
+    ){
+        fprintf(
+          stderr, "Unable to insert rune main stat: %s\n", sqlite3_errmsg(db)
+        );
+        return(-1);
+    }
+
+    // Insert innate stat
+    if (rune.innate.stat != 0){
+        total_stats ++;
+        //query_parameters[0] = rune.id; // No need, already has id
+        query_parameters[1] = "0"; // Main stat
+        sprintf(query_parameters[2], "%d", rune.innate.stat);
+        sprintf(query_parameters[3], "%d", rune.innate.value);
+        query_parameters[4] = "0"; // Innates can't be grinded.
+        query_parameters[5] = "0"; // Innates can't be enchanted.
+        if (
+          SUCCESS !=
+          db_execute(
+            "INSERT INTO rune_stats "
+            "(rune, slot, stat, value, grind, enchant) "
+            "VALUES (?, ?, ?, ?, ?, ?)",
+          query_parameters
+          )
+        ){
+            fprintf(
+              stderr,
+              "Unable to insert rune innate stat: %s\n", sqlite3_errmsg(db)
+            );
+            return(-1);
+        }
+    }
+
+    // Insert normal stats
+    for (int s = 0; s < rune.stat_count; s ++){
+        total_stats ++;
+        //query_parameters[0] = rune.id; // No need, already has id
+        query_parameters[1] = malloc(5);
+        sprintf(query_parameters[1], "%d", s + 1); // 1-4
+        query_parameters[2] = malloc(5);
+        sprintf(query_parameters[2], "%d", rune.stats[s].stat);
+        sprintf(query_parameters[3], "%d", rune.stats[s].value);
+        query_parameters[4] = malloc(5);
+        sprintf(query_parameters[4], "%d", rune.stats[s].grind);
+        query_parameters[5] = malloc(5);
+        sprintf(query_parameters[5], "%d", rune.stats[s].enchant);
+        if (
+          SUCCESS !=
+          db_execute(
+            "INSERT INTO rune_stats"
+            "(rune, slot, stat, value, grind, enchant) "
+            "VALUES (?, ?, ?, ?, ?, ?)",
+          query_parameters
+          )
+        ){
+            fprintf(
+              stderr, "Unable to insert rune stat: %s\n", sqlite3_errmsg(db)
+            );
+            return(-1);
+        }
+
+    }
+    return(total_stats);
+}

+ 139 - 0
src/RuneOptimizer/update/update_json_unit.c

@@ -0,0 +1,139 @@
+/*
+ * This file is part of RuneOptimizer.
+ *
+ * RuneOptimizer is free software: you can redistribute it and/or modify it
+ * under the terms of the GNU General Public License as published by the Free
+ * Software Foundation, either version 3 of the License, or (at your option)
+ * any later version.
+ *
+ * RuneOptimizer is distributed in the hope that it will be useful, but WITHOUT
+ * ANY WARRANTY; without even the implied warranty of MERCHANTABILITY or
+ * FITNESS FOR A PARTICULAR PURPOSE. See the GNU General Public License for
+ * more details.
+ *
+ * You should have received a copy of the GNU General Public License along with
+ * RuneOptimizer. If not, see <https://www.gnu.org/licenses/>.
+ */
+
+int update_json_unit(
+  json_object *unit_json, unsigned char six_stars,
+  unsigned char with_runes, unsigned int *total_runes, unsigned int *total_stats
+){
+    int ret_val = 0;
+    unsigned char unit_has_runes = FALSE;
+    struct DB_Unit unit;
+    char *query_parameters[23];
+    for (int i = 1; i < 23; i ++) query_parameters[i] = malloc(5);
+    // Unit ID
+    json_object *unit_id = json_object_object_get(unit_json, "unit_id");
+    strcpy(unit.id, json_object_get_string(unit_id));
+    // Unit monster ID
+    json_object *unit_master_id =
+      json_object_object_get(unit_json, "unit_master_id");
+    unit.monster= json_object_get_int(unit_master_id);
+    // Unit name
+    update_get_monster_name(unit.monster, unit.name);
+    json_object *unit_level = json_object_object_get(unit_json, "unit_level");
+    unit.level = json_object_get_int(unit_level);
+    // Unit stars (class)
+    json_object *class = json_object_object_get(unit_json, "class");
+    unit.stars = json_object_get_int(class);
+    // Unit base HP (con * 15)
+    json_object *con = json_object_object_get(unit_json, "con");
+    unit.base_hp = json_object_get_int(con) * 15;
+    // Unit base ATK
+    json_object *atk = json_object_object_get(unit_json, "atk");
+    unit.base_atk = json_object_get_int(atk);
+    // Unit base DEF
+    json_object *def = json_object_object_get(unit_json, "def");
+    unit.base_def = json_object_get_int(def);
+    // Unit base SPD
+    json_object *spd = json_object_object_get(unit_json, "spd");
+    unit.base_spd = json_object_get_int(spd);
+    // Unit base RES
+    json_object *resist = json_object_object_get(unit_json, "resist");
+    unit.base_res = json_object_get_int(resist);
+    // Unit base ACC
+    json_object *accuracy = json_object_object_get(unit_json, "accuracy");
+    unit.base_acc = json_object_get_int(accuracy);
+    // Unit base CRR
+    json_object *critical_rate =
+      json_object_object_get(unit_json, "critical_rate");
+    unit.base_crr = json_object_get_int(critical_rate);
+    // Unit base CRD
+    json_object *critical_damage =
+      json_object_object_get(unit_json, "critical_damage");
+    unit.base_crd = json_object_get_int(critical_damage);
+    // Homunculus name (if is Homunculus)
+    json_object *homunculus_name =
+      json_object_object_get(unit_json, "homunculus_name");
+    if (strlen(json_object_get_string(homunculus_name)) > 0){
+        strcpy(unit.name, json_object_get_string(homunculus_name));
+    }
+
+    // Parse unit runes
+    json_object *unit_runes = json_object_object_get(unit_json, "runes");
+    int rune_count = json_object_array_length(unit_runes);
+    json_object *idx;
+    for (int i = 0; i < rune_count; i++){
+        unit_has_runes = TRUE;
+        *total_runes ++;
+        idx = json_object_array_get_idx(unit_runes, i);
+        int status = update_json_rune(idx, unit.id);
+        if (status != -1) *total_stats += status;
+    }
+
+    // Insert unit, depending on flags and status
+    if (
+        unit_has_runes == TRUE ||
+        (six_stars == FALSE && with_runes == FALSE) ||
+        (six_stars == TRUE && unit.stars == TRUE)
+    ){
+        ret_val = 1;
+        query_parameters[0] = unit.id;
+        query_parameters[1] = unit.name;
+        sprintf(query_parameters[2], "%d", unit.stars);
+        sprintf(query_parameters[3], "%d", unit.level);
+        sprintf(query_parameters[4], "%d", unit.base_hp);
+        sprintf(query_parameters[5], "%d", unit.base_atk);
+        sprintf(query_parameters[6], "%d", unit.base_def);
+        sprintf(query_parameters[7], "%d", unit.base_spd);
+        sprintf(query_parameters[8], "%d", unit.base_crr);
+        sprintf(query_parameters[9], "%d", unit.base_crd);
+        sprintf(query_parameters[10], "%d", unit.base_res);
+        sprintf(query_parameters[11], "%d", unit.base_acc);
+        // Insert current stats as base stats.
+        // They will be updated later.
+        sprintf(query_parameters[12], "%d", unit.base_hp);
+        sprintf(query_parameters[13], "%d", unit.base_atk);
+        sprintf(query_parameters[14], "%d", unit.base_def);
+        sprintf(query_parameters[15], "%d", unit.base_spd);
+        sprintf(query_parameters[16], "%d", unit.base_crr);
+        sprintf(query_parameters[17], "%d", unit.base_crd);
+        sprintf(query_parameters[18], "%d", unit.base_res);
+        sprintf(query_parameters[19], "%d", unit.base_acc);
+        // TODO: Get storage status. But how??
+        sprintf(query_parameters[20], "%d", 0);
+        sprintf(query_parameters[21], "%d", unit.monster);
+        if (
+          SUCCESS !=
+          db_execute(
+            "INSERT INTO units ("
+            "  id,          name,        stars,       level,"
+            "  base_hp,     base_atk,    base_def,    base_spd,"
+            "  base_crr,    base_crd,    base_res,    base_acc,"
+            "  current_hp,  current_atk, current_def, current_spd,"
+            "  current_crr, current_crd, current_res, current_acc,"
+            "  storage, monster"
+            ") VALUES ("
+            "  ?, ?, ?, ?, ?, ?, ?, ?, ?, ?, ?, ?, ?, ?, ?, ?, ?, ?, ?, ?, ?, ?"
+            ")",
+          query_parameters
+          )
+        ){
+            fprintf(stderr, "Unable to insert unit: %s\n", sqlite3_errmsg(db));
+            return(-1);
+        }
+    }
+    return(ret_val);
+}

+ 338 - 0
src/RuneOptimizer/update/update_rune_totals.c

@@ -0,0 +1,338 @@
+/*
+ * This file is part of RuneOptimizer.
+ *
+ * RuneOptimizer is free software: you can redistribute it and/or modify it
+ * under the terms of the GNU General Public License as published by the Free
+ * Software Foundation, either version 3 of the License, or (at your option)
+ * any later version.
+ *
+ * RuneOptimizer is distributed in the hope that it will be useful, but WITHOUT
+ * ANY WARRANTY; without even the implied warranty of MERCHANTABILITY or
+ * FITNESS FOR A PARTICULAR PURPOSE. See the GNU General Public License for
+ * more details.
+ *
+ * You should have received a copy of the GNU General Public License along with
+ * RuneOptimizer. If not, see <https://www.gnu.org/licenses/>.
+ */
+
+void update_rune_totals(struct DB_Rune *rune){
+    rune->efficiency = 0.0f;
+    rune->max_efficiency = 0.0f;
+    rune->current_hp_flat = 0;
+    rune->current_hp_percent = 0;
+    rune->lv12_hp_flat = 0;
+    rune->lv12_hp_percent = 0;
+    rune->lv15_hp_flat = 0;
+    rune->lv15_hp_percent = 0;
+    rune->current_atk_flat = 0;
+    rune->current_atk_percent = 0;
+    rune->lv12_atk_flat = 0;
+    rune->lv12_atk_percent = 0;
+    rune->lv15_atk_flat = 0;
+    rune->lv15_atk_percent = 0;
+    rune->current_def_flat = 0;
+    rune->current_def_percent = 0;
+    rune->lv12_def_flat = 0;
+    rune->lv12_def_percent = 0;
+    rune->lv15_def_flat = 0;
+    rune->lv15_def_percent = 0;
+    rune->current_spd = 0;
+    rune->lv12_spd = 0;
+    rune->lv15_spd = 0;
+    rune->current_crr = 0;
+    rune->lv12_crr = 0;
+    rune->lv15_crr = 0;
+    rune->current_crd = 0;
+    rune->lv12_crd = 0;
+    rune->lv15_crd = 0;
+    rune->current_res = 0;
+    rune->lv12_res = 0;
+    rune->lv15_res = 0;
+    rune->current_acc = 0;
+    rune->lv12_acc = 0;
+    rune->lv15_acc = 0;
+    // TODO: Calculate efficiencies
+    switch (rune->main.stat){
+        case HP_FLAT:
+            rune->current_hp_flat += rune->main.value;
+            if (rune->level > 12){
+                rune->lv12_hp_flat += rune->main.value;
+            }
+            else{
+                rune->lv12_hp_flat +=
+                  main_stats_values[rune->main.stat][rune->stars][0];
+            }
+            rune->lv15_hp_flat +=
+              main_stats_values[rune->main.stat][rune->stars][1];
+            break;
+        case HP_PERCENT:
+            rune->current_hp_percent += rune->main.value;
+            if (rune->level > 12){
+                rune->lv12_hp_percent += rune->main.value;
+            }
+            else{
+                rune->lv12_hp_percent +=
+                  main_stats_values[rune->main.stat][rune->stars][0];
+            }
+            rune->lv15_hp_percent +=
+              main_stats_values[rune->main.stat][rune->stars][1];
+            break;
+        case ATK_FLAT:
+            rune->current_atk_flat += rune->main.value;
+            if (rune->level > 12){
+                rune->lv12_atk_flat += rune->main.value;
+            }
+            else{
+                rune->lv12_atk_flat +=
+                  main_stats_values[rune->main.stat][rune->stars][0];
+            }
+            rune->lv15_atk_flat +=
+              main_stats_values[rune->main.stat][rune->stars][1];
+            break;
+        case ATK_PERCENT:
+            rune->current_atk_percent += rune->main.value;
+            if (rune->level > 12){
+                rune->lv12_atk_percent += rune->main.value;
+            }
+            else{
+                rune->lv12_atk_percent +=
+                  main_stats_values[rune->main.stat][rune->stars][0];
+            }
+            rune->lv15_atk_percent +=
+              main_stats_values[rune->main.stat][rune->stars][1];
+            break;
+        case DEF_FLAT:
+            rune->current_def_flat += rune->main.value;
+            if (rune->level > 12){
+                rune->lv12_def_flat += rune->main.value;
+            }
+            else{
+                rune->lv12_def_flat +=
+                  main_stats_values[rune->main.stat][rune->stars][0];
+            }
+            rune->lv15_def_flat +=
+              main_stats_values[rune->main.stat][rune->stars][1];
+            break;
+        case DEF_PERCENT:
+            rune->current_def_percent += rune->main.value;
+            if (rune->level > 12){
+                rune->lv12_def_percent += rune->main.value;
+            }
+            else{
+                rune->lv12_def_percent +=
+                  main_stats_values[rune->main.stat][rune->stars][0];
+            }
+            rune->lv15_def_percent +=
+              main_stats_values[rune->main.stat][rune->stars][1];
+            break;
+        case SPD:
+            rune->current_spd += rune->main.value;
+            if (rune->level > 12){
+                rune->lv12_spd += rune->main.value;
+            }
+            else{
+                rune->lv12_spd +=
+                  main_stats_values[rune->main.stat][rune->stars][0];
+            }
+            rune->lv15_spd +=
+              main_stats_values[rune->main.stat][rune->stars][1];
+            break;
+        case CRR:
+            rune->current_crr += rune->main.value;
+            if (rune->level > 12){
+                rune->lv12_crr += rune->main.value;
+            }
+            else{
+                rune->lv12_crr +=
+                  main_stats_values[rune->main.stat][rune->stars][0];
+            }
+            rune->lv15_crr +=
+              main_stats_values[rune->main.stat][rune->stars][1];
+            break;
+        case CRD:
+            rune->current_crd += rune->main.value;
+            if (rune->level > 12){
+                rune->lv12_crd += rune->main.value;
+            }
+            else{
+                rune->lv12_crd +=
+                  main_stats_values[rune->main.stat][rune->stars][0];
+            }
+            rune->lv15_crd +=
+              main_stats_values[rune->main.stat][rune->stars][1];
+            break;
+        case RES:
+            rune->current_res += rune->main.value;
+            if (rune->level > 12){
+                rune->lv12_res += rune->main.value;
+            }
+            else{
+                rune->lv12_res +=
+                  main_stats_values[rune->main.stat][rune->stars][0];
+            }
+            rune->lv15_res +=
+              main_stats_values[rune->main.stat][rune->stars][1];
+            break;
+        case ACC:
+            rune->current_acc += rune->main.value;
+            if (rune->level > 12){
+                rune->lv12_acc += rune->main.value;
+            }
+            else{
+                rune->lv12_acc +=
+                  main_stats_values[rune->main.stat][rune->stars][0];
+            }
+            rune->lv15_acc +=
+              main_stats_values[rune->main.stat][rune->stars][1];
+            break;
+    }
+    switch (rune->innate.stat){
+        case HP_FLAT:
+            rune->current_hp_flat += rune->innate.value;
+            rune->lv12_hp_flat += rune->innate.value;
+            rune->lv15_hp_flat += rune->innate.value;
+            break;
+        case HP_PERCENT:
+            rune->current_hp_percent += rune->innate.value;
+            rune->lv12_hp_percent += rune->innate.value;
+            rune->lv15_hp_percent += rune->innate.value;
+            break;
+        case ATK_FLAT:
+            rune->current_atk_flat += rune->innate.value;
+            rune->lv12_atk_flat += rune->innate.value;
+            rune->lv15_atk_flat += rune->innate.value;
+            break;
+        case ATK_PERCENT:
+            rune->current_atk_percent += rune->innate.value;
+            rune->lv12_atk_percent += rune->innate.value;
+            rune->lv15_atk_percent += rune->innate.value;
+            break;
+        case DEF_FLAT:
+            rune->current_def_flat += rune->innate.value;
+            rune->lv12_def_flat += rune->innate.value;
+            rune->lv15_def_flat += rune->innate.value;
+            break;
+        case DEF_PERCENT:
+            rune->current_def_percent += rune->innate.value;
+            rune->lv12_def_percent += rune->innate.value;
+            rune->lv15_def_percent += rune->innate.value;
+            break;
+        case SPD:
+            rune->current_spd += rune->innate.value;
+            rune->lv12_spd += rune->innate.value;
+            rune->lv15_spd += rune->innate.value;
+            break;
+        case CRR:
+            rune->current_crr += rune->innate.value;
+            rune->lv12_crr += rune->innate.value;
+            rune->lv15_crr += rune->innate.value;
+            break;
+        case CRD:
+            rune->current_crd += rune->innate.value;
+            rune->lv12_crd += rune->innate.value;
+            rune->lv15_crd += rune->innate.value;
+            break;
+        case RES:
+            rune->current_res += rune->innate.value;
+            rune->lv12_res += rune->innate.value;
+            rune->lv15_res += rune->innate.value;
+            break;
+        case ACC:
+            rune->current_acc += rune->innate.value;
+            rune->lv12_acc += rune->innate.value;
+            rune->lv15_acc += rune->innate.value;
+            break;
+    }
+    for (int i = 0; i < rune->stat_count; i++){
+        switch (rune->stats[i].stat){
+            case HP_FLAT:
+                rune->current_hp_flat +=
+                  (rune->stats[i].value + rune->stats[i].grind);
+                rune->lv12_hp_flat +=
+                  (rune->stats[i].value + rune->stats[i].grind);
+                rune->lv15_hp_flat +=
+                  (rune->stats[i].value + rune->stats[i].grind);
+                break;
+            case HP_PERCENT:
+                rune->current_hp_percent +=
+                  (rune->stats[i].value + rune->stats[i].grind);
+                rune->lv12_hp_percent +=
+                  (rune->stats[i].value + rune->stats[i].grind);
+                rune->lv15_hp_percent +=
+                  (rune->stats[i].value + rune->stats[i].grind);
+                break;
+            case ATK_FLAT:
+                rune->current_atk_flat +=
+                  (rune->stats[i].value + rune->stats[i].grind);
+                rune->lv12_atk_flat +=
+                  (rune->stats[i].value + rune->stats[i].grind);
+                rune->lv15_atk_flat +=
+                  (rune->stats[i].value + rune->stats[i].grind);
+                break;
+            case ATK_PERCENT:
+                rune->current_atk_percent +=
+                  (rune->stats[i].value + rune->stats[i].grind);
+                rune->lv12_atk_percent +=
+                  (rune->stats[i].value + rune->stats[i].grind);
+                rune->lv15_atk_percent +=
+                  (rune->stats[i].value + rune->stats[i].grind);
+                break;
+            case DEF_FLAT:
+                rune->current_def_flat +=
+                  (rune->stats[i].value + rune->stats[i].grind);
+                rune->lv12_def_flat +=
+                  (rune->stats[i].value + rune->stats[i].grind);
+                rune->lv15_def_flat +=
+                  (rune->stats[i].value + rune->stats[i].grind);
+                break;
+            case DEF_PERCENT:
+                rune->current_def_percent +=
+                  (rune->stats[i].value + rune->stats[i].grind);
+                rune->lv12_def_percent +=
+                  (rune->stats[i].value + rune->stats[i].grind);
+                rune->lv15_def_percent +=
+                  (rune->stats[i].value + rune->stats[i].grind);
+                break;
+            case SPD:
+                rune->current_spd +=
+                  (rune->stats[i].value + rune->stats[i].grind);
+                rune->lv12_spd +=
+                  (rune->stats[i].value + rune->stats[i].grind);
+                rune->lv15_spd +=
+                  (rune->stats[i].value + rune->stats[i].grind);
+                break;
+            case CRR:
+                rune->current_crr +=
+                  (rune->stats[i].value + rune->stats[i].grind);
+                rune->lv12_crr +=
+                  (rune->stats[i].value + rune->stats[i].grind);
+                rune->lv15_crr +=
+                  (rune->stats[i].value + rune->stats[i].grind);
+                break;
+            case CRD:
+                rune->current_crd +=
+                  (rune->stats[i].value + rune->stats[i].grind);
+                rune->lv12_crd +=
+                  (rune->stats[i].value + rune->stats[i].grind);
+                rune->lv15_crd +=
+                  (rune->stats[i].value + rune->stats[i].grind);
+                break;
+            case RES:
+                rune->current_res +=
+                  (rune->stats[i].value + rune->stats[i].grind);
+                rune->lv12_res +=
+                  (rune->stats[i].value + rune->stats[i].grind);
+                rune->lv15_res +=
+                  (rune->stats[i].value + rune->stats[i].grind);
+                break;
+            case ACC:
+                rune->current_acc +=
+                  (rune->stats[i].value + rune->stats[i].grind);
+                rune->lv12_acc +=
+                  (rune->stats[i].value + rune->stats[i].grind);
+                rune->lv15_acc +=
+                  (rune->stats[i].value + rune->stats[i].grind);
+                break;
+        }
+    }
+}

Alguns arquivos não foram mostrados porque muitos arquivos mudaram nesse diff