diff --git a/wmud/db.c b/wmud/db.c index 0314ca8..618cbaa 100644 --- a/wmud/db.c +++ b/wmud/db.c @@ -20,6 +20,7 @@ #include #include +#include "world.h" #include "main.h" #include "db.h" #include "players.h" @@ -182,7 +183,52 @@ wmud_db_save_player(wmudPlayer *player, GError **err) gboolean wmud_db_load_planes(GSList **planes, GError **err) { - return FALSE; + sqlite3_stmt *sth = NULL; + int sqlite_code; + + if (dbh == NULL) + { + if (err) + g_set_error(err, WMUD_DB_ERROR, WMUD_DB_ERROR_NOINIT, "Database backend not initialized"); + + return FALSE; + } + + if ((sqlite_code = sqlite3_prepare_v2(dbh, "SELECT id, name FROM planes", -1, &sth, NULL)) != SQLITE_OK) + { + g_set_error(err, WMUD_DB_ERROR, WMUD_DB_ERROR_BADQUERY, "Bad query in wmud_db_load_planes(): %s", sqlite3_errmsg(dbh)); + + return FALSE; + } + + while (1) + { + sqlite_code = sqlite3_step(sth); + if (sqlite_code == SQLITE_ROW) + { + wmudPlane *plane = g_new0(wmudPlane, 1); + plane->id = sqlite3_column_int(sth, 0); + plane->name = g_strdup((gchar *)sqlite3_column_text(sth, 1)); + + g_log(G_LOG_DOMAIN, G_LOG_LEVEL_DEBUG, "Loaded plane _%s_", plane->name); + + *planes = g_slist_prepend(*planes, plane); + } + else if (sqlite_code == SQLITE_DONE) + { + break; + } + else + { + g_set_error(err, WMUD_DB_ERROR, WMUD_DB_ERROR_BADQUERY, "Query error in wmud_db_load_planes(): %s", sqlite3_errmsg(dbh)); + sqlite3_finalize(sth); + return FALSE; + } + } + + sqlite3_finalize(sth); + + return TRUE; } gboolean @@ -194,7 +240,52 @@ wmud_db_load_planets(GSList **planets, GError **err) gboolean wmud_db_load_directions(GSList **directions, GError **err) { - return FALSE; + sqlite3_stmt *sth = NULL; + int sqlite_code; + + if (dbh == NULL) + { + if (err) + g_set_error(err, WMUD_DB_ERROR, WMUD_DB_ERROR_NOINIT, "Database backend not initialized"); + + return FALSE; + } + + if ((sqlite_code = sqlite3_prepare_v2(dbh, "SELECT id, short_name, name FROM directions", -1, &sth, NULL)) != SQLITE_OK) + { + g_set_error(err, WMUD_DB_ERROR, WMUD_DB_ERROR_BADQUERY, "Bad query in wmud_db_load_directions(): %s", sqlite3_errmsg(dbh)); + + return FALSE; + } + + while (1) + { + sqlite_code = sqlite3_step(sth); + if (sqlite_code == SQLITE_ROW) + { + wmudDirection *dir = g_new0(wmudDirection, 1); + dir->id = sqlite3_column_int(sth, 0); + dir->short_name = g_strdup((gchar *)sqlite3_column_text(sth, 1)); + dir->name = g_strdup((gchar *)sqlite3_column_text(sth, 2)); + + g_log(G_LOG_DOMAIN, G_LOG_LEVEL_DEBUG, "Loaded direction _%s_", dir->name); + + *directions = g_slist_prepend(*directions, dir); + } + else if (sqlite_code == SQLITE_DONE) + { + break; + } + else + { + g_set_error(err, WMUD_DB_ERROR, WMUD_DB_ERROR_BADQUERY, "Query error in wmud_db_load_players(): %s", sqlite3_errmsg(dbh)); + return FALSE; + } + } + + sqlite3_finalize(sth); + + return TRUE; } gboolean diff --git a/wmud/interpreter.c b/wmud/interpreter.c index 77caef8..bcf1f90 100644 --- a/wmud/interpreter.c +++ b/wmud/interpreter.c @@ -23,6 +23,7 @@ #include "interpreter.h" #include "game-networking.h" #include "main.h" +#include "world.h" /** * SECTION:interpreter @@ -35,7 +36,7 @@ WMUD_COMMAND(quit); static wmudCommand command_list[] = { { "quit", gcmd_quit }, - { NULL, NULL }, + { NULL, NULL }, }; /** @@ -50,6 +51,52 @@ destroy_string(GString *string) g_string_free(string, TRUE); } +static void +check_direction_command(wmudDirection *dir, gboolean *found) +{ + wmudCommand *cmd; + + for (cmd = command_list; cmd->command; cmd++) + { + if (g_ascii_strcasecmp(dir->short_name, cmd->command) == 0) + { + *found = TRUE; + return; + } + + if (g_ascii_strcasecmp(dir->name, cmd->command) == 0) + { + *found = TRUE; + return; + } + } +} + +/** + * wmud_interpreter_check_directions: + * @directions: a #GSList of directions + * @err: A #GError to store possible errors on failure + * + * Checks if the given directions are already registered commands. + * + * Return value: If the directions are acceptable at the time of the check, the function returns %TRUE. Otherwise %FALSE is returned, and + */ +gboolean +wmud_interpreter_check_directions(GSList *directions, GError **err) +{ + gboolean command_found = FALSE; + + g_slist_foreach(directions, (GFunc)check_direction_command, &command_found); + + if (command_found) + { + g_set_error(err, WMUD_INTERPRETER_ERROR, WMUD_INTERPRETER_ERROR_DUPCMD, "Direction commands are not unique. Please check the database!"); + g_debug("Directions command are not unique. Please check the database!"); + } + + return command_found; +} + /** * wmud_interpret_game_command: * @client: the wmudClient whose command should be processed diff --git a/wmud/interpreter.h b/wmud/interpreter.h index 2f07ed0..dc2593b 100644 --- a/wmud/interpreter.h +++ b/wmud/interpreter.h @@ -51,6 +51,13 @@ typedef struct _wmudCommand { wmudCommandFunc commandFunc; } wmudCommand; +GQuark WMUD_INTERPRETER_ERROR; + +typedef enum { + WMUD_INTERPRETER_ERROR_DUPCMD +} wmudInterpreterError; + +gboolean wmud_interpreter_check_directions(GSList *directions, GError **err); void wmud_interpret_game_command(wmudClient *client); #endif /* __WMUD_INTERPRETER_H__ */ diff --git a/wmud/main.c b/wmud/main.c index 9634bf2..d45bfdc 100644 --- a/wmud/main.c +++ b/wmud/main.c @@ -121,6 +121,7 @@ wmud_type_init(void) { WMUD_CONFIG_ERROR = g_quark_from_string("wmud_config_error"); WMUD_DB_ERROR = g_quark_from_string("wmud_db_error"); + WMUD_INTERPRETER_ERROR = g_quark_from_string("wmud_interpreter_error"); } /** @@ -176,6 +177,7 @@ main(int argc, char **argv) g_clear_error(&err); wmud_db_load_players(&err); + wmud_world_load(&err); /* Initialization ends here */ diff --git a/wmud/world.c b/wmud/world.c index 5e71402..fb03def 100644 --- a/wmud/world.c +++ b/wmud/world.c @@ -21,6 +21,7 @@ #include "world.h" #include "db.h" +#include "interpreter.h" /** * SECTION:world @@ -77,7 +78,6 @@ wmud_world_assoc_exits_rooms(GSList *exits, GSList *rooms, GError **err) return FALSE; } - /** * wmud_world_load: * @err: a #GError to put error messages into @@ -98,7 +98,12 @@ wmud_world_load(GError **err) /* Load directions from the database */ wmud_db_load_directions(&directions, &in_err); + /* Check if the loaded directions conform to the rules */ + g_clear_error(&in_err); + wmud_interpreter_check_directions(directions, &in_err); + /* Load planes from the database */ + g_clear_error(&in_err); wmud_db_load_planes(&planes, &in_err); /* Check if the loaded planes conform to the rules */ diff --git a/wmud/world.h b/wmud/world.h index 4063902..5d22627 100644 --- a/wmud/world.h +++ b/wmud/world.h @@ -19,6 +19,19 @@ #ifndef __WMUD_WORLD_H__ #define __WMUD_WORLD_H__ +#include + +typedef struct _wmudPlane { + guint id; + gchar *name; +} wmudPlane; + +typedef struct _wmudDirection { + guint id; + gchar *short_name; + gchar *name; +} wmudDirection; + gboolean wmud_world_check_planes(GSList *planes, GError **err); gboolean wmud_world_check_planets(GSList *planets, GError **err); gboolean wmud_world_check_areas(GSList *areas, GError **err);