Split off mapreg code from script.c
* new mapserver files, mapreg.h, mapreg_txt.c, mapreg_sql.c * removed MAPREGSQL from project files / makefiles * mapreg storage engine is now fully dependent on the server type * added config settings mapreg_txt and mapreg_db to inter config * added get_str() function to complement add_str() * fixed txt mapreg code allowing too long variable names git-svn-id: https://svn.code.sf.net/p/rathena/svn/trunk@13081 54d463be-8e91-2dee-dedb-b68131a5f0ec
This commit is contained in:
parent
efef65a62f
commit
dcc2cdb5da
@ -4,6 +4,13 @@ AS OF SVN REV. 5091, WE ARE NOW USING TRUNK. ALL UNTESTED BUGFIXES/FEATURES GO
|
||||
IF YOU HAVE A WORKING AND TESTED BUGFIX PUT IT INTO STABLE AS WELL AS TRUNK.
|
||||
|
||||
2008/08/15
|
||||
* Split off mapreg code from script.c [ultramage]
|
||||
- new mapserver files, mapreg.h, mapreg_txt.c, mapreg_sql.c
|
||||
- removed MAPREGSQL from project files / makefiles
|
||||
- mapreg storage engine is now fully dependent on the server type
|
||||
- added config settings mapreg_txt and mapreg_db to inter config
|
||||
- added get_str() function to complement add_str()
|
||||
- fixed txt mapreg code allowing too long variable names
|
||||
* Removed gm_cant_party_max_lv. It now uses gm_cant_party_min_lv as the threshold. (bugreport:2051) [SketchyPhoenix]
|
||||
2008/08/11
|
||||
* Fixed right-click npc unload not unloading duplicates (bugreport:2014)
|
||||
|
@ -1,5 +1,7 @@
|
||||
Date Added
|
||||
|
||||
2008/08/13
|
||||
* Added config settings mapreg_txt and mapreg_db to inter config [ultramage]
|
||||
2008/08/10
|
||||
* Removed duplicate gef_cas mapflags [Yommy]
|
||||
2008/08/01
|
||||
|
@ -38,6 +38,9 @@ castle_txt: save/castle.txt
|
||||
// Status change flatfile database, for status changes that are saved between sessions.
|
||||
scdata_txt: save/scdata.txt
|
||||
|
||||
// Mapserver permanent script variables ($-type)
|
||||
mapreg_txt: save/mapreg.txt
|
||||
|
||||
|
||||
// SQL version options only
|
||||
|
||||
@ -114,6 +117,7 @@ item_db_db: item_db
|
||||
item_db2_db: item_db2
|
||||
mob_db_db: mob_db
|
||||
mob_db2_db: mob_db2
|
||||
mapreg_db: mapreg
|
||||
|
||||
//Use SQL item_db and mob_db for the map server
|
||||
use_sql_db: no
|
||||
|
@ -121,8 +121,6 @@ help_txt: conf/help.txt
|
||||
help2_txt: conf/help2.txt
|
||||
charhelp_txt: conf/charhelp.txt
|
||||
|
||||
mapreg_txt: save/mapreg.txt
|
||||
|
||||
// Scripts
|
||||
import: npc/scripts_main.conf
|
||||
|
||||
|
35
configure
vendored
35
configure
vendored
@ -1,5 +1,5 @@
|
||||
#! /bin/sh
|
||||
# From configure.in Revision: 13024 .
|
||||
# From configure.in Revision: 13073 .
|
||||
# Guess values for system-dependent variables and create Makefiles.
|
||||
# Generated by GNU Autoconf 2.61.
|
||||
#
|
||||
@ -1256,9 +1256,6 @@ Optional Features:
|
||||
gcollect, bcheck (defaults to builtin)
|
||||
--enable-packetver=ARG Sets the PACKETVER define of the map-server. (see
|
||||
src/map/clif.h)
|
||||
--enable-mapregsql Makes map-wide script variables be saved to SQL
|
||||
instead of TXT files in the sql map-server.
|
||||
(disabled by default)
|
||||
--enable-debug Compiles extra debug code. (disabled by default)
|
||||
(available options: yes, no, gdb)
|
||||
|
||||
@ -1764,28 +1761,6 @@ fi
|
||||
|
||||
|
||||
|
||||
#
|
||||
# mapregsql
|
||||
#
|
||||
# Check whether --enable-mapregsql was given.
|
||||
if test "${enable_mapregsql+set}" = set; then
|
||||
enableval=$enable_mapregsql;
|
||||
enable_mapregsql="$enableval"
|
||||
case $enableval in
|
||||
no);;
|
||||
yes);;
|
||||
*) { { echo "$as_me:$LINENO: error: invalid argument --enable-mapregsql=$enableval... stopping" >&5
|
||||
echo "$as_me: error: invalid argument --enable-mapregsql=$enableval... stopping" >&2;}
|
||||
{ (exit 1); exit 1; }; };;
|
||||
esac
|
||||
|
||||
else
|
||||
enable_mapregsql="no"
|
||||
|
||||
fi
|
||||
|
||||
|
||||
|
||||
#
|
||||
# debug
|
||||
#
|
||||
@ -4516,14 +4491,6 @@ if test -n "$enable_packetver" ; then
|
||||
fi
|
||||
|
||||
|
||||
#
|
||||
# Mapregsql
|
||||
#
|
||||
if test "$enable_mapregsql" = "yes" ; then
|
||||
CFLAGS="$CFLAGS -DMAPREGSQL"
|
||||
fi
|
||||
|
||||
|
||||
#
|
||||
# Debug
|
||||
#
|
||||
|
29
configure.in
29
configure.in
@ -50,27 +50,6 @@ AC_ARG_ENABLE(
|
||||
)
|
||||
|
||||
|
||||
#
|
||||
# mapregsql
|
||||
#
|
||||
AC_ARG_ENABLE(
|
||||
[mapregsql],
|
||||
AC_HELP_STRING(
|
||||
[--enable-mapregsql],
|
||||
[Makes map-wide script variables be saved to SQL instead of TXT files in the sql map-server. (disabled by default)]
|
||||
),
|
||||
[
|
||||
enable_mapregsql="$enableval"
|
||||
case $enableval in
|
||||
no);;
|
||||
yes);;
|
||||
*) AC_MSG_ERROR([[invalid argument --enable-mapregsql=$enableval... stopping]]);;
|
||||
esac
|
||||
],
|
||||
[enable_mapregsql="no"]
|
||||
)
|
||||
|
||||
|
||||
#
|
||||
# debug
|
||||
#
|
||||
@ -338,14 +317,6 @@ if test -n "$enable_packetver" ; then
|
||||
fi
|
||||
|
||||
|
||||
#
|
||||
# Mapregsql
|
||||
#
|
||||
if test "$enable_mapregsql" = "yes" ; then
|
||||
CFLAGS="$CFLAGS -DMAPREGSQL"
|
||||
fi
|
||||
|
||||
|
||||
#
|
||||
# Debug
|
||||
#
|
||||
|
@ -533,7 +533,7 @@ nothing - A permanent variable attached to the character, the default
|
||||
names starting with 'l' if you want full backward compatibility.
|
||||
"$" - A global permanent variable.
|
||||
They are stored in "save\mapreg.txt" or database table `mapreg`,
|
||||
depending on server type and the MAPREGSQL compilation flag.
|
||||
depending on server type.
|
||||
"$@" - A global temporary variable.
|
||||
This is important for scripts which are called with no RID
|
||||
attached, that is, not triggered by a specific character object.
|
||||
|
@ -18,13 +18,15 @@ MAP_OBJ = map.o chrif.o clif.o pc.o status.o npc.o \
|
||||
storage.o skill.o atcommand.o charcommand.o battle.o \
|
||||
intif.o trade.o party.o vending.o guild.o pet.o \
|
||||
log.o mail.o date.o unit.o mercenary.o quest.o
|
||||
MAP_TXT_OBJ = $(MAP_OBJ:%=obj_txt/%)
|
||||
MAP_SQL_OBJ = $(MAP_OBJ:%=obj_sql/%)
|
||||
MAP_TXT_OBJ = $(MAP_OBJ:%=obj_txt/%) \
|
||||
obj_txt/mapreg_txt.o
|
||||
MAP_SQL_OBJ = $(MAP_OBJ:%=obj_sql/%) \
|
||||
obj_sql/mapreg_sql.o
|
||||
MAP_H = map.h chrif.h clif.h pc.h status.h npc.h \
|
||||
chat.h itemdb.h mob.h script.h path.h \
|
||||
storage.h skill.h atcommand.h charcommand.h battle.h \
|
||||
intif.h trade.h party.h vending.h guild.h pet.h \
|
||||
log.h mail.h date.h unit.h mercenary.h quest.h
|
||||
log.h mail.h date.h unit.h mercenary.h quest.h mapreg.h
|
||||
|
||||
HAVE_MYSQL=@HAVE_MYSQL@
|
||||
ifeq ($(HAVE_MYSQL),yes)
|
||||
|
@ -32,6 +32,7 @@
|
||||
#include "unit.h"
|
||||
#include "battle.h"
|
||||
#include "script.h"
|
||||
#include "mapreg.h"
|
||||
#include "guild.h"
|
||||
#include "pet.h"
|
||||
#include "mercenary.h"
|
||||
@ -2932,9 +2933,6 @@ int map_config_read(char *cfgName)
|
||||
if (strcmpi(w1, "charhelp_txt") == 0)
|
||||
strcpy(charhelp_txt, w2);
|
||||
else
|
||||
if (strcmpi(w1, "mapreg_txt") == 0)
|
||||
strcpy(mapreg_txt, w2);
|
||||
else
|
||||
if(strcmpi(w1,"map_cache_file") == 0)
|
||||
strncpy(map_cache_file,w2,255);
|
||||
else
|
||||
@ -3034,6 +3032,9 @@ int inter_config_read(char *cfgName)
|
||||
if(strcmpi(w1,"log_db_db")==0)
|
||||
strcpy(log_db_db, w2);
|
||||
#endif
|
||||
else
|
||||
if( mapreg_config_read(w1,w2) )
|
||||
continue;
|
||||
//support the import command, just like any other config
|
||||
else
|
||||
if(strcmpi(w1,"import")==0)
|
||||
|
17
src/map/mapreg.h
Normal file
17
src/map/mapreg.h
Normal file
@ -0,0 +1,17 @@
|
||||
// Copyright (c) Athena Dev Teams - Licensed under GNU GPL
|
||||
// For more information, see LICENCE in the main folder
|
||||
|
||||
#ifndef _MAPREG_H_
|
||||
#define _MAPREG_H_
|
||||
|
||||
void mapreg_reload(void);
|
||||
void mapreg_final(void);
|
||||
void mapreg_init(void);
|
||||
bool mapreg_config_read(const char* w1, const char* w2);
|
||||
|
||||
int mapreg_readreg(int uid);
|
||||
char* mapreg_readregstr(int uid);
|
||||
bool mapreg_setreg(int uid, int val);
|
||||
bool mapreg_setregstr(int uid, const char* str);
|
||||
|
||||
#endif /* _MAPREG_H_ */
|
242
src/map/mapreg_sql.c
Normal file
242
src/map/mapreg_sql.c
Normal file
@ -0,0 +1,242 @@
|
||||
// Copyright (c) Athena Dev Teams - Licensed under GNU GPL
|
||||
// For more information, see LICENCE in the main folder
|
||||
|
||||
#include "../common/cbasetypes.h"
|
||||
#include "../common/db.h"
|
||||
#include "../common/malloc.h"
|
||||
#include "../common/showmsg.h"
|
||||
#include "../common/sql.h"
|
||||
#include "../common/strlib.h"
|
||||
#include "../common/timer.h"
|
||||
#include "map.h" // mmysql_handle
|
||||
#include "script.h"
|
||||
#include <stdlib.h>
|
||||
#include <string.h>
|
||||
|
||||
static DBMap* mapreg_db = NULL; // int var_id -> int value
|
||||
static DBMap* mapregstr_db = NULL; // int var_id -> char* value
|
||||
|
||||
static char mapreg_table[32] = "mapreg";
|
||||
static bool mapreg_dirty = false;
|
||||
#define MAPREG_AUTOSAVE_INTERVAL (300*1000)
|
||||
|
||||
|
||||
/// Looks up the value of an integer variable using its uid.
|
||||
int mapreg_readreg(int uid)
|
||||
{
|
||||
return (int)idb_get(mapreg_db, uid);
|
||||
}
|
||||
|
||||
/// Looks up the value of a string variable using its uid.
|
||||
char* mapreg_readregstr(int uid)
|
||||
{
|
||||
return (char*)idb_get(mapregstr_db, uid);
|
||||
}
|
||||
|
||||
/// Modifies the value of an integer variable.
|
||||
bool mapreg_setreg(int uid, int val)
|
||||
{
|
||||
int num = uid & 0x00ffffff;
|
||||
int i = uid & 0xff000000 >> 24;
|
||||
const char* name = get_str(num);
|
||||
|
||||
if( val != 0 )
|
||||
{
|
||||
if( idb_put(mapreg_db,uid,(void*)val) )
|
||||
; // already exists, delay write
|
||||
else
|
||||
if( name[1] == '@' )
|
||||
; // nothing more to do
|
||||
else
|
||||
{// write new wariable to database
|
||||
char tmp_str[32*2+1];
|
||||
Sql_EscapeStringLen(mmysql_handle, tmp_str, name, strnlen(name, 32));
|
||||
if( SQL_ERROR == Sql_Query(mmysql_handle, "INSERT INTO `%s`(`varname`,`index`,`value`) VALUES ('%s','%d','%d')", mapreg_table, tmp_str, i, val) )
|
||||
Sql_ShowDebug(mmysql_handle);
|
||||
}
|
||||
}
|
||||
else // val == 0
|
||||
{
|
||||
idb_remove(mapreg_db,uid);
|
||||
|
||||
if( name[1] == '@' )
|
||||
; // nothing more to do
|
||||
else
|
||||
{// Remove from database because it is unused.
|
||||
if( SQL_ERROR == Sql_Query(mmysql_handle, "DELETE FROM `%s` WHERE `varname`='%s' AND `index`='%d'", mapreg_table, name, i) )
|
||||
Sql_ShowDebug(mmysql_handle);
|
||||
}
|
||||
}
|
||||
|
||||
mapreg_dirty = true;
|
||||
return true;
|
||||
}
|
||||
|
||||
/// Modifies the value of a string variable.
|
||||
bool mapreg_setregstr(int uid, const char* str)
|
||||
{
|
||||
int num = uid & 0x00ffffff;
|
||||
int i = uid & 0xff000000 >> 24;
|
||||
const char* name = get_str(num);
|
||||
|
||||
if( str == NULL || *str == 0 )
|
||||
{
|
||||
if(name[1] != '@') {
|
||||
if( SQL_ERROR == Sql_Query(mmysql_handle, "DELETE FROM `%s` WHERE `varname`='%s' AND `index`='%d'", mapreg_table, name, i) )
|
||||
Sql_ShowDebug(mmysql_handle);
|
||||
}
|
||||
idb_remove(mapregstr_db,uid);
|
||||
}
|
||||
else
|
||||
{
|
||||
if (idb_put(mapregstr_db,uid, aStrdup(str)))
|
||||
;
|
||||
else if(name[1] != '@') { //put returned null, so we must insert.
|
||||
// Someone is causing a database size infinite increase here without name[1] != '@' [Lance]
|
||||
char tmp_str[32*2+1];
|
||||
char tmp_str2[255*2+1];
|
||||
Sql_EscapeStringLen(mmysql_handle, tmp_str, name, strnlen(name, 32));
|
||||
Sql_EscapeStringLen(mmysql_handle, tmp_str2, str, strnlen(str, 255));
|
||||
if( SQL_ERROR == Sql_Query(mmysql_handle, "INSERT INTO `%s`(`varname`,`index`,`value`) VALUES ('%s','%d','%s')", mapreg_table, tmp_str, i, tmp_str2) )
|
||||
Sql_ShowDebug(mmysql_handle);
|
||||
}
|
||||
}
|
||||
|
||||
mapreg_dirty = true;
|
||||
return true;
|
||||
}
|
||||
|
||||
/// Loads permanent variables from database
|
||||
static void script_load_mapreg(void)
|
||||
{
|
||||
/*
|
||||
0 1 2
|
||||
+-------------------------+
|
||||
| varname | index | value |
|
||||
+-------------------------+
|
||||
*/
|
||||
SqlStmt* stmt = SqlStmt_Malloc(mmysql_handle);
|
||||
char varname[32+1];
|
||||
int index;
|
||||
char value[255+1];
|
||||
uint32 length;
|
||||
|
||||
if ( SQL_ERROR == SqlStmt_Prepare(stmt, "SELECT `varname`, `index`, `value` FROM `%s`", mapreg_table)
|
||||
|| SQL_ERROR == SqlStmt_Execute(stmt)
|
||||
) {
|
||||
SqlStmt_ShowDebug(stmt);
|
||||
SqlStmt_Free(stmt);
|
||||
return;
|
||||
}
|
||||
|
||||
SqlStmt_BindColumn(stmt, 0, SQLDT_STRING, &varname[0], 32, &length, NULL);
|
||||
SqlStmt_BindColumn(stmt, 1, SQLDT_INT, &index, 0, NULL, NULL);
|
||||
SqlStmt_BindColumn(stmt, 2, SQLDT_STRING, &value[0], 255, NULL, NULL);
|
||||
|
||||
while ( SQL_SUCCESS == SqlStmt_NextRow(stmt) )
|
||||
{
|
||||
int s = add_str(varname);
|
||||
int i = index;
|
||||
|
||||
if( varname[length-1] == '$' )
|
||||
idb_put(mapregstr_db, (i<<24)|s, aStrdup(value));
|
||||
else
|
||||
idb_put(mapreg_db, (i<<24)|s, (void *)atoi(value));
|
||||
}
|
||||
|
||||
SqlStmt_Free(stmt);
|
||||
|
||||
mapreg_dirty = false;
|
||||
}
|
||||
|
||||
/// Saves permanent variables to database
|
||||
static void script_save_mapreg(void)
|
||||
{
|
||||
DBIterator* iter;
|
||||
void* data;
|
||||
DBKey key;
|
||||
|
||||
iter = mapreg_db->iterator(mapreg_db);
|
||||
for( data = iter->first(iter,&key); iter->exists(iter); data = iter->next(iter,&key) )
|
||||
{
|
||||
int num = key.i & 0x00ffffff;
|
||||
int i = key.i & 0xff000000 >> 24;
|
||||
const char* name = get_str(num);
|
||||
|
||||
if( name[1] == '@' )
|
||||
continue;
|
||||
|
||||
if( SQL_ERROR == Sql_Query(mmysql_handle, "UPDATE `%s` SET `value`='%d' WHERE `varname`='%s' AND `index`='%d'", mapreg_table, (int)data, name, i) )
|
||||
Sql_ShowDebug(mmysql_handle);
|
||||
}
|
||||
iter->destroy(iter);
|
||||
|
||||
iter = mapregstr_db->iterator(mapregstr_db);
|
||||
for( data = iter->first(iter,&key); iter->exists(iter); data = iter->next(iter,&key) )
|
||||
{
|
||||
int num = key.i & 0x00ffffff;
|
||||
int i = key.i & 0xff000000 >> 24;
|
||||
const char* name = get_str(num);
|
||||
char tmp_str2[2*255+1];
|
||||
|
||||
if( name[1] == '@' )
|
||||
continue;
|
||||
|
||||
Sql_EscapeStringLen(mmysql_handle, tmp_str2, (char*)data, safestrnlen((char*)data, 255));
|
||||
if( SQL_ERROR == Sql_Query(mmysql_handle, "UPDATE `%s` SET `value`='%s' WHERE `varname`='%s' AND `index`='%d'", mapreg_table, tmp_str2, name, i) )
|
||||
Sql_ShowDebug(mmysql_handle);
|
||||
}
|
||||
iter->destroy(iter);
|
||||
|
||||
mapreg_dirty = false;
|
||||
}
|
||||
|
||||
static int script_autosave_mapreg(int tid, unsigned int tick, int id, intptr data)
|
||||
{
|
||||
if( mapreg_dirty )
|
||||
script_save_mapreg();
|
||||
|
||||
return 0;
|
||||
}
|
||||
|
||||
|
||||
void mapreg_reload(void)
|
||||
{
|
||||
if( mapreg_dirty )
|
||||
script_save_mapreg();
|
||||
|
||||
mapreg_db->clear(mapreg_db, NULL);
|
||||
mapregstr_db->clear(mapregstr_db, NULL);
|
||||
|
||||
script_load_mapreg();
|
||||
}
|
||||
|
||||
void mapreg_final(void)
|
||||
{
|
||||
if( mapreg_dirty )
|
||||
script_save_mapreg();
|
||||
|
||||
mapreg_db->destroy(mapreg_db,NULL);
|
||||
mapregstr_db->destroy(mapregstr_db,NULL);
|
||||
}
|
||||
|
||||
void mapreg_init(void)
|
||||
{
|
||||
mapreg_db = idb_alloc(DB_OPT_BASE);
|
||||
mapregstr_db = idb_alloc(DB_OPT_RELEASE_DATA);
|
||||
|
||||
script_load_mapreg();
|
||||
|
||||
add_timer_func_list(script_autosave_mapreg, "script_autosave_mapreg");
|
||||
add_timer_interval(gettick() + MAPREG_AUTOSAVE_INTERVAL, script_autosave_mapreg, 0, 0, MAPREG_AUTOSAVE_INTERVAL);
|
||||
}
|
||||
|
||||
bool mapreg_config_read(const char* w1, const char* w2)
|
||||
{
|
||||
if(!strcmpi(w1, "mapreg_db"))
|
||||
safestrncpy(mapreg_table, w2, sizeof(mapreg_table));
|
||||
else
|
||||
return false;
|
||||
|
||||
return true;
|
||||
}
|
202
src/map/mapreg_txt.c
Normal file
202
src/map/mapreg_txt.c
Normal file
@ -0,0 +1,202 @@
|
||||
// Copyright (c) Athena Dev Teams - Licensed under GNU GPL
|
||||
// For more information, see LICENCE in the main folder
|
||||
|
||||
#include "../common/cbasetypes.h"
|
||||
#include "../common/db.h"
|
||||
#include "../common/lock.h"
|
||||
#include "../common/malloc.h"
|
||||
#include "../common/showmsg.h"
|
||||
#include "../common/strlib.h"
|
||||
#include "../common/timer.h"
|
||||
#include "script.h"
|
||||
#include <stdio.h>
|
||||
#include <stdlib.h>
|
||||
#include <string.h>
|
||||
|
||||
static DBMap* mapreg_db = NULL; // int var_id -> int value
|
||||
static DBMap* mapregstr_db = NULL; // int var_id -> char* value
|
||||
|
||||
static char mapreg_txt[256] = "save/mapreg.txt";
|
||||
static bool mapreg_dirty = false;
|
||||
#define MAPREG_AUTOSAVE_INTERVAL (300*1000)
|
||||
|
||||
|
||||
/// Looks up the value of an integer variable using its uid.
|
||||
int mapreg_readreg(int uid)
|
||||
{
|
||||
return (int)idb_get(mapreg_db, uid);
|
||||
}
|
||||
|
||||
/// Looks up the value of a string variable using its uid.
|
||||
char* mapreg_readregstr(int uid)
|
||||
{
|
||||
return (char*)idb_get(mapregstr_db, uid);
|
||||
}
|
||||
|
||||
/// Modifies the value of an integer variable.
|
||||
bool mapreg_setreg(int uid, int val)
|
||||
{
|
||||
if( val != 0 )
|
||||
idb_put(mapreg_db,uid,(void*)val);
|
||||
else
|
||||
idb_remove(mapreg_db,uid);
|
||||
|
||||
mapreg_dirty = true;
|
||||
return true;
|
||||
}
|
||||
|
||||
/// Modifies the value of a string variable.
|
||||
bool mapreg_setregstr(int uid, const char* str)
|
||||
{
|
||||
if( str == NULL || *str == 0 )
|
||||
idb_remove(mapregstr_db,uid);
|
||||
else
|
||||
idb_put(mapregstr_db,uid,aStrdup(str));
|
||||
|
||||
mapreg_dirty = true;
|
||||
return true;
|
||||
}
|
||||
|
||||
/// Loads permanent variables from savefile
|
||||
static void script_load_mapreg(void)
|
||||
{
|
||||
FILE* fp;
|
||||
char line[1024];
|
||||
|
||||
fp = fopen(mapreg_txt,"rt");
|
||||
if( fp == NULL )
|
||||
return;
|
||||
|
||||
while( fgets(line,sizeof(line),fp) )
|
||||
{
|
||||
char varname[32+1];
|
||||
char value[255+1];
|
||||
int n,s,i;
|
||||
|
||||
// read name and index
|
||||
if( sscanf(line, "%255[^,],%d\t%n", varname,&i,&n) != 2 &&
|
||||
(i = 0, sscanf(line,"%[^\t]\t%n", varname,&n) != 1) )
|
||||
continue;
|
||||
|
||||
// read value
|
||||
if( sscanf(line + n, "%[^\n\r]", value) != 1 )
|
||||
{
|
||||
ShowError("%s: %s broken data !\n", mapreg_txt, varname);
|
||||
continue;
|
||||
}
|
||||
|
||||
s = add_str(varname);
|
||||
if( varname[strlen(varname)-1] == '$' )
|
||||
idb_put(mapregstr_db, (i<<24)|s, aStrdup(value));
|
||||
else
|
||||
idb_put(mapreg_db, (i<<24)|s, (void*)atoi(value));
|
||||
}
|
||||
fclose(fp);
|
||||
|
||||
mapreg_dirty = false;
|
||||
}
|
||||
|
||||
/// Saves permanent variables to savefile
|
||||
static void script_save_mapreg(void)
|
||||
{
|
||||
FILE *fp;
|
||||
int lock;
|
||||
DBIterator* iter;
|
||||
void* data;
|
||||
DBKey key;
|
||||
|
||||
fp = lock_fopen(mapreg_txt,&lock);
|
||||
if( fp == NULL )
|
||||
{
|
||||
ShowError("script_save_mapreg: Unable to lock-open file [%s]!\n", mapreg_txt);
|
||||
return;
|
||||
}
|
||||
|
||||
iter = mapreg_db->iterator(mapreg_db);
|
||||
for( data = iter->first(iter,&key); iter->exists(iter); data = iter->next(iter,&key) )
|
||||
{
|
||||
int num = key.i & 0x00ffffff;
|
||||
int i = key.i & 0xff000000 >> 24;
|
||||
const char* name = get_str(num);
|
||||
|
||||
if( name[1] == '@' )
|
||||
continue;
|
||||
|
||||
if( i == 0 )
|
||||
fprintf(fp, "%s\t%d\n", name, (int)data);
|
||||
else
|
||||
fprintf(fp, "%s,%d\t%d\n", name, i, (int)data);
|
||||
}
|
||||
iter->destroy(iter);
|
||||
|
||||
iter = mapregstr_db->iterator(mapregstr_db);
|
||||
for( data = iter->first(iter,&key); iter->exists(iter); data = iter->next(iter,&key) )
|
||||
{
|
||||
int num = key.i & 0x00ffffff;
|
||||
int i = key.i & 0xff000000 >> 24;
|
||||
const char* name = get_str(num);
|
||||
|
||||
if( name[1] == '@' )
|
||||
continue;
|
||||
|
||||
if( i == 0 )
|
||||
fprintf(fp, "%s\t%s\n", name, (char *)data);
|
||||
else
|
||||
fprintf(fp, "%s,%d\t%s\n", name, i, (char *)data);
|
||||
}
|
||||
iter->destroy(iter);
|
||||
|
||||
lock_fclose(fp,mapreg_txt,&lock);
|
||||
|
||||
mapreg_dirty = false;
|
||||
}
|
||||
|
||||
static int script_autosave_mapreg(int tid, unsigned int tick, int id, intptr data)
|
||||
{
|
||||
if( mapreg_dirty )
|
||||
script_save_mapreg();
|
||||
|
||||
return 0;
|
||||
}
|
||||
|
||||
|
||||
void mapreg_reload(void)
|
||||
{
|
||||
if( mapreg_dirty )
|
||||
script_save_mapreg();
|
||||
|
||||
mapreg_db->clear(mapreg_db, NULL);
|
||||
mapregstr_db->clear(mapregstr_db, NULL);
|
||||
|
||||
script_load_mapreg();
|
||||
}
|
||||
|
||||
void mapreg_final(void)
|
||||
{
|
||||
if( mapreg_dirty )
|
||||
script_save_mapreg();
|
||||
|
||||
mapreg_db->destroy(mapreg_db,NULL);
|
||||
mapregstr_db->destroy(mapregstr_db,NULL);
|
||||
}
|
||||
|
||||
void mapreg_init(void)
|
||||
{
|
||||
mapreg_db = idb_alloc(DB_OPT_BASE);
|
||||
mapregstr_db = idb_alloc(DB_OPT_RELEASE_DATA);
|
||||
|
||||
script_load_mapreg();
|
||||
|
||||
add_timer_func_list(script_autosave_mapreg, "script_autosave_mapreg");
|
||||
add_timer_interval(gettick() + MAPREG_AUTOSAVE_INTERVAL, script_autosave_mapreg, 0, 0, MAPREG_AUTOSAVE_INTERVAL);
|
||||
}
|
||||
|
||||
bool mapreg_config_read(const char* w1, const char* w2)
|
||||
{
|
||||
if(!strcmpi(w1, "mapreg_txt"))
|
||||
safestrncpy(mapreg_txt, w2, sizeof(mapreg_txt));
|
||||
else
|
||||
return false;
|
||||
|
||||
return true;
|
||||
}
|
389
src/map/script.c
389
src/map/script.c
@ -26,6 +26,7 @@
|
||||
#include "mob.h"
|
||||
#include "npc.h"
|
||||
#include "pet.h"
|
||||
#include "mapreg.h"
|
||||
#include "mercenary.h" //[orn]
|
||||
#include "intif.h"
|
||||
#include "skill.h"
|
||||
@ -157,9 +158,10 @@ static int script_pos,script_size;
|
||||
#define GETVALUE(buf,i) ((int)MakeDWord(MakeWord((buf)[i],(buf)[i+1]),MakeWord((buf)[i+2],0)))
|
||||
#define SETVALUE(buf,i,n) ((buf)[i]=GetByte(n,0),(buf)[i+1]=GetByte(n,1),(buf)[i+2]=GetByte(n,2))
|
||||
|
||||
#define GETSTRING(off) (str_buf+(off))
|
||||
static char *str_buf;
|
||||
static int str_pos,str_size;
|
||||
static int str_data_size = 0;
|
||||
int str_num=LABEL_START;
|
||||
static struct str_data_struct {
|
||||
enum c_op type;
|
||||
int str;
|
||||
@ -169,7 +171,6 @@ static struct str_data_struct {
|
||||
int val;
|
||||
int next;
|
||||
} *str_data = NULL;
|
||||
int str_num=LABEL_START,str_data_size;
|
||||
|
||||
// Using a prime number for SCRIPT_HASH_SIZE should give better distributions
|
||||
#define SCRIPT_HASH_SIZE 1021
|
||||
@ -179,11 +180,6 @@ int str_hash[SCRIPT_HASH_SIZE];
|
||||
//#define SCRIPT_HASH_SDBM
|
||||
#define SCRIPT_HASH_ELF
|
||||
|
||||
static DBMap* mapreg_db=NULL; // int var_id -> int value
|
||||
static DBMap* mapregstr_db=NULL; // int var_id -> char* value
|
||||
static int mapreg_dirty=-1;
|
||||
char mapreg_txt[256]="save/mapreg.txt";
|
||||
#define MAPREG_AUTOSAVE_INTERVAL (300*1000)
|
||||
|
||||
static DBMap* scriptlabel_db=NULL; // const char* label_name -> int script_pos
|
||||
static DBMap* userfunc_db=NULL; // const char* func_name -> struct script_code*
|
||||
@ -248,12 +244,6 @@ int potion_flag=0; //For use on Alchemist improved potions/Potion Pitcher. [Skot
|
||||
int potion_hp=0, potion_per_hp=0, potion_sp=0, potion_per_sp=0;
|
||||
int potion_target=0;
|
||||
|
||||
#if !defined(TXT_ONLY) && defined(MAPREGSQL)
|
||||
char mapregsql_db[32] = "mapreg";
|
||||
char mapregsql_db_varname[32] = "varname";
|
||||
char mapregsql_db_index[32] = "index";
|
||||
char mapregsql_db_value[32] = "value";
|
||||
#endif
|
||||
|
||||
c_op get_com(unsigned char *script,int *pos);
|
||||
int get_num(unsigned char *script,int *pos);
|
||||
@ -278,9 +268,6 @@ const char* parse_subexpr(const char* p,int limit);
|
||||
void push_val(struct script_stack *stack,int type,int val);
|
||||
int run_func(struct script_state *st);
|
||||
|
||||
int mapreg_setreg(int num,int val);
|
||||
int mapreg_setregstr(int num,const char *str);
|
||||
|
||||
enum {
|
||||
MF_NOMEMO, //0
|
||||
MF_NOTELEPORT,
|
||||
@ -515,66 +502,84 @@ static unsigned int calc_hash(const char* p)
|
||||
return h % SCRIPT_HASH_SIZE;
|
||||
}
|
||||
|
||||
|
||||
/*==========================================
|
||||
* str_dataの中に名前があるか検索する
|
||||
* str_data manipulation functions
|
||||
*------------------------------------------*/
|
||||
// 既存のであれば番号、無ければ-1
|
||||
static int search_str(const char *p)
|
||||
|
||||
/// Looks up string using the provided id.
|
||||
const char* get_str(int id)
|
||||
{
|
||||
Assert( id >= LABEL_START && id < str_size );
|
||||
return str_buf+str_data[id].str;
|
||||
}
|
||||
|
||||
/// Returns the uid of the string, or -1.
|
||||
static int search_str(const char* p)
|
||||
{
|
||||
int i;
|
||||
i=str_hash[calc_hash(p)];
|
||||
while(i){
|
||||
if(strcasecmp(str_buf+str_data[i].str,p)==0){
|
||||
|
||||
for( i = str_hash[calc_hash(p)]; i != 0; i = str_data[i].next )
|
||||
if( strcasecmp(get_str(i),p) == 0 )
|
||||
return i;
|
||||
}
|
||||
i=str_data[i].next;
|
||||
}
|
||||
|
||||
return -1;
|
||||
}
|
||||
|
||||
/*==========================================
|
||||
* str_dataに名前を登録
|
||||
*------------------------------------------*/
|
||||
// 既存のであれば番号、無ければ登録して新規番号
|
||||
/// Stores a copy of the string and returns its id.
|
||||
/// If an identical string is already present, returns its id instead.
|
||||
int add_str(const char* p)
|
||||
{
|
||||
int i;
|
||||
int i, h;
|
||||
int len;
|
||||
|
||||
i=calc_hash(p);
|
||||
if(str_hash[i]==0){
|
||||
str_hash[i]=str_num;
|
||||
} else {
|
||||
i=str_hash[i];
|
||||
for(;;){
|
||||
if(strcasecmp(str_buf+str_data[i].str,p)==0){
|
||||
return i;
|
||||
}
|
||||
if(str_data[i].next==0)
|
||||
break;
|
||||
i=str_data[i].next;
|
||||
}
|
||||
str_data[i].next=str_num;
|
||||
h = calc_hash(p);
|
||||
|
||||
if( str_hash[h] == 0 )
|
||||
{// empty bucket, add new node here
|
||||
str_hash[h] = str_num;
|
||||
}
|
||||
if(str_num>=str_data_size){
|
||||
str_data_size+=128;
|
||||
else
|
||||
{// scan for end of list, or occurence of identical string
|
||||
for( i = str_hash[h]; ; i = str_data[i].next )
|
||||
{
|
||||
if( strcasecmp(get_str(i),p) == 0 )
|
||||
return i; // string already in list
|
||||
if( str_data[i].next == 0 )
|
||||
break; // reached the end
|
||||
}
|
||||
|
||||
// append node to end of list
|
||||
str_data[i].next = str_num;
|
||||
}
|
||||
|
||||
// grow list if neccessary
|
||||
if( str_num >= str_data_size )
|
||||
{
|
||||
str_data_size += 128;
|
||||
RECREATE(str_data,struct str_data_struct,str_data_size);
|
||||
memset(str_data + (str_data_size - 128), '\0', 128);
|
||||
}
|
||||
|
||||
len=(int)strlen(p);
|
||||
while(str_pos+len+1>=str_size){
|
||||
str_size+=256;
|
||||
|
||||
// grow string buffer if neccessary
|
||||
while( str_pos+len+1 >= str_size )
|
||||
{
|
||||
str_size += 256;
|
||||
RECREATE(str_buf,char,str_size);
|
||||
memset(str_buf + (str_size - 256), '\0', 256);
|
||||
}
|
||||
memcpy(str_buf+str_pos,p,len+1);
|
||||
str_data[str_num].type=C_NOP;
|
||||
str_data[str_num].str=str_pos;
|
||||
str_data[str_num].next=0;
|
||||
str_data[str_num].func=NULL;
|
||||
str_data[str_num].backpatch=-1;
|
||||
str_data[str_num].label=-1;
|
||||
str_pos+=len+1;
|
||||
|
||||
safestrncpy(str_buf+str_pos, p, len+1);
|
||||
str_data[str_num].type = C_NOP;
|
||||
str_data[str_num].str = str_pos;
|
||||
str_data[str_num].next = 0;
|
||||
str_data[str_num].func = NULL;
|
||||
str_data[str_num].backpatch = -1;
|
||||
str_data[str_num].label = -1;
|
||||
str_pos += len+1;
|
||||
|
||||
return str_num++;
|
||||
}
|
||||
|
||||
@ -1462,7 +1467,7 @@ const char* parse_syntax(const char* p)
|
||||
str_data[l].type = C_USERFUNC;
|
||||
set_label(l, script_pos, p);
|
||||
if( parse_options&SCRIPT_USE_LABEL_DB )
|
||||
strdb_put(scriptlabel_db, GETSTRING(str_data[l].str), (void*)script_pos);
|
||||
strdb_put(scriptlabel_db, get_str(l), (void*)script_pos);
|
||||
return skip_space(p);
|
||||
}
|
||||
else
|
||||
@ -1959,7 +1964,7 @@ struct script_code* parse_script(const char *src,const char *file,int line,int o
|
||||
i=add_word(p);
|
||||
set_label(i,script_pos,p);
|
||||
if( parse_options&SCRIPT_USE_LABEL_DB )
|
||||
strdb_put(scriptlabel_db, GETSTRING(str_data[i].str), (void*)script_pos);
|
||||
strdb_put(scriptlabel_db, get_str(i), (void*)script_pos);
|
||||
p=tmpp+1;
|
||||
p=skip_space(p);
|
||||
continue;
|
||||
@ -2129,7 +2134,7 @@ void get_val(struct script_state* st, struct script_data* data)
|
||||
data->u.str = pc_readregstr(sd, data->u.num);
|
||||
break;
|
||||
case '$':
|
||||
data->u.str = (char *)idb_get(mapregstr_db, data->u.num);
|
||||
data->u.str = mapreg_readregstr(data->u.num);
|
||||
break;
|
||||
case '#':
|
||||
if( name[1] == '#' )
|
||||
@ -2183,7 +2188,7 @@ void get_val(struct script_state* st, struct script_data* data)
|
||||
data->u.num = pc_readreg(sd, data->u.num);
|
||||
break;
|
||||
case '$':
|
||||
data->u.num = (int)idb_get(mapreg_db, data->u.num);
|
||||
data->u.num = mapreg_readreg(data->u.num);
|
||||
break;
|
||||
case '#':
|
||||
if( name[1] == '#' )
|
||||
@ -3190,249 +3195,6 @@ void run_script_main(struct script_state *st)
|
||||
|
||||
}
|
||||
|
||||
/*==========================================
|
||||
* マップ変数の変更
|
||||
*------------------------------------------*/
|
||||
int mapreg_setreg(int num, int val)
|
||||
{
|
||||
#if !defined(TXT_ONLY) && defined(MAPREGSQL)
|
||||
int i = num >> 24;
|
||||
char* name = str_buf + str_data[num&0x00ffffff].str;
|
||||
|
||||
if( val != 0 ) {
|
||||
if(idb_put(mapreg_db,num,(void*)val))
|
||||
;
|
||||
else if(name[1] != '@') {
|
||||
char tmp_str[32*2+1];
|
||||
Sql_EscapeStringLen(mmysql_handle, tmp_str, name, strnlen(name, 32));
|
||||
if( SQL_ERROR == Sql_Query(mmysql_handle, "INSERT INTO `%s`(`%s`,`%s`,`%s`) VALUES ('%s','%d','%d')", mapregsql_db, mapregsql_db_varname, mapregsql_db_index, mapregsql_db_value, tmp_str, i, val) )
|
||||
Sql_ShowDebug(mmysql_handle);
|
||||
}
|
||||
} else { // val == 0
|
||||
if(name[1] != '@') { // Remove from database because it is unused.
|
||||
if( SQL_ERROR == Sql_Query(mmysql_handle, "DELETE FROM `%s` WHERE `%s`='%s' AND `%s`='%d'", mapregsql_db, mapregsql_db_varname, name, mapregsql_db_index, i) )
|
||||
Sql_ShowDebug(mmysql_handle);
|
||||
}
|
||||
idb_remove(mapreg_db,num);
|
||||
}
|
||||
#else
|
||||
if(val != 0)
|
||||
idb_put(mapreg_db,num,(void*)val);
|
||||
else
|
||||
idb_remove(mapreg_db,num);
|
||||
#endif
|
||||
|
||||
mapreg_dirty = 1;
|
||||
return 1;
|
||||
}
|
||||
/*==========================================
|
||||
* 文字列型マップ変数の変更
|
||||
*------------------------------------------*/
|
||||
int mapreg_setregstr(int num, const char* str)
|
||||
{
|
||||
#if !defined(TXT_ONLY) && defined(MAPREGSQL)
|
||||
int i = num >> 24;
|
||||
char* name = str_buf + str_data[num&0x00ffffff].str;
|
||||
|
||||
if( str==NULL || *str==0 ) {
|
||||
if(name[1] != '@') {
|
||||
if( SQL_ERROR == Sql_Query(mmysql_handle, "DELETE FROM `%s` WHERE `%s`='%s' AND `%s`='%d'", mapregsql_db, mapregsql_db_varname, name, mapregsql_db_index, i) )
|
||||
Sql_ShowDebug(mmysql_handle);
|
||||
}
|
||||
idb_remove(mapregstr_db,num);
|
||||
mapreg_dirty = 1;
|
||||
return 1;
|
||||
}
|
||||
|
||||
if (idb_put(mapregstr_db,num, aStrdup(str)))
|
||||
;
|
||||
else if(name[1] != '@') { //put returned null, so we must insert.
|
||||
// Someone is causing a database size infinite increase here without name[1] != '@' [Lance]
|
||||
char tmp_str[32*2+1];
|
||||
char tmp_str2[255*2+1];
|
||||
Sql_EscapeStringLen(mmysql_handle, tmp_str, name, strnlen(name, 32));
|
||||
Sql_EscapeStringLen(mmysql_handle, tmp_str2, str, strnlen(str, 255));
|
||||
if( SQL_ERROR == Sql_Query(mmysql_handle, "INSERT INTO `%s`(`%s`,`%s`,`%s`) VALUES ('%s','%d','%s')", mapregsql_db, mapregsql_db_varname, mapregsql_db_index, mapregsql_db_value, tmp_str, i, tmp_str2) )
|
||||
Sql_ShowDebug(mmysql_handle);
|
||||
}
|
||||
#else
|
||||
if( str==NULL || *str==0 )
|
||||
idb_remove(mapregstr_db,num);
|
||||
else
|
||||
idb_put(mapregstr_db,num,aStrdup(str));
|
||||
#endif
|
||||
|
||||
mapreg_dirty = 1;
|
||||
return 1;
|
||||
}
|
||||
|
||||
/*==========================================
|
||||
* 永続的マップ変数の読み込み
|
||||
*------------------------------------------*/
|
||||
static int script_load_mapreg(void)
|
||||
{
|
||||
#if defined(TXT_ONLY) || !defined(MAPREGSQL)
|
||||
FILE* fp;
|
||||
char line[1024];
|
||||
|
||||
if( (fp=fopen(mapreg_txt,"rt")) == NULL )
|
||||
return -1;
|
||||
|
||||
while(fgets(line,sizeof(line),fp))
|
||||
{
|
||||
char buf1[256],buf2[1024];
|
||||
char* p;
|
||||
int n,v,s,i;
|
||||
if( sscanf(line,"%255[^,],%d\t%n",buf1,&i,&n)!=2 &&
|
||||
(i=0,sscanf(line,"%[^\t]\t%n",buf1,&n)!=1) )
|
||||
continue;
|
||||
if( buf1[strlen(buf1)-1] == '$' ) {
|
||||
if( sscanf(line + n, "%[^\n\r]", buf2) != 1 ) {
|
||||
ShowError("%s: %s broken data !\n", mapreg_txt, buf1);
|
||||
continue;
|
||||
}
|
||||
p = aStrdup(buf2);
|
||||
s = add_str(buf1);
|
||||
idb_put(mapregstr_db, (i<<24)|s, p);
|
||||
} else {
|
||||
if( sscanf(line + n, "%d", &v) != 1 ) {
|
||||
ShowError("%s: %s broken data !\n", mapreg_txt, buf1);
|
||||
continue;
|
||||
}
|
||||
s = add_str(buf1);
|
||||
idb_put(mapreg_db, (i<<24)|s, (void*)v);
|
||||
}
|
||||
}
|
||||
fclose(fp);
|
||||
|
||||
mapreg_dirty = 0;
|
||||
return 0;
|
||||
#else
|
||||
/*
|
||||
0 1 2
|
||||
+-------------------------+
|
||||
| varname | index | value |
|
||||
+-------------------------+
|
||||
*/
|
||||
|
||||
SqlStmt* stmt = SqlStmt_Malloc(mmysql_handle);
|
||||
char varname[32+1];
|
||||
int index;
|
||||
char value[255+1];
|
||||
uint32 length;
|
||||
|
||||
if ( SQL_ERROR == SqlStmt_Prepare(stmt, "SELECT `%s`, `%s`, `%s` FROM `%s`", mapregsql_db_varname, mapregsql_db_index, mapregsql_db_value, mapregsql_db)
|
||||
|| SQL_ERROR == SqlStmt_Execute(stmt)
|
||||
) {
|
||||
SqlStmt_ShowDebug(stmt);
|
||||
SqlStmt_Free(stmt);
|
||||
return -1;
|
||||
}
|
||||
|
||||
SqlStmt_BindColumn(stmt, 0, SQLDT_STRING, &varname[0], 32, &length, NULL);
|
||||
SqlStmt_BindColumn(stmt, 1, SQLDT_INT, &index, 0, NULL, NULL);
|
||||
SqlStmt_BindColumn(stmt, 2, SQLDT_STRING, &value[0], 255, NULL, NULL);
|
||||
|
||||
while ( SQL_SUCCESS == SqlStmt_NextRow(stmt) )
|
||||
{
|
||||
if( varname[length-1] == '$' ) {
|
||||
int s = add_str(varname);
|
||||
int i = index;
|
||||
char* p = aStrdup(value);
|
||||
idb_put(mapregstr_db, (i<<24)|s, p);
|
||||
} else {
|
||||
int s = add_str(varname);
|
||||
int i = index;
|
||||
int v = atoi(value);
|
||||
idb_put(mapreg_db, (i<<24)|s, (void *)v);
|
||||
}
|
||||
}
|
||||
|
||||
SqlStmt_Free(stmt);
|
||||
|
||||
mapreg_dirty = 0;
|
||||
return 0;
|
||||
|
||||
#endif /* TXT_ONLY */
|
||||
}
|
||||
/*==========================================
|
||||
* 永続的マップ変数の書き込み
|
||||
*------------------------------------------*/
|
||||
static int script_save_mapreg_intsub(DBKey key,void *data,va_list ap)
|
||||
{
|
||||
int num=key.i&0x00ffffff, i=key.i>>24;
|
||||
char *name=str_buf+str_data[num].str;
|
||||
|
||||
#if defined(TXT_ONLY) || !defined(MAPREGSQL)
|
||||
FILE *fp=va_arg(ap,FILE*);
|
||||
if( name[1]!='@' ) {
|
||||
if(i==0)
|
||||
fprintf(fp,"%s\t%d\n", name, (int)data);
|
||||
else
|
||||
fprintf(fp,"%s,%d\t%d\n", name, i, (int)data);
|
||||
}
|
||||
#else
|
||||
if ( name[1] != '@') {
|
||||
if( SQL_ERROR == Sql_Query(mmysql_handle, "UPDATE `%s` SET `%s`='%d' WHERE `%s`='%s' AND `%s`='%d'", mapregsql_db, mapregsql_db_value, (int)data, mapregsql_db_varname, name, mapregsql_db_index, i) )
|
||||
Sql_ShowDebug(mmysql_handle);
|
||||
}
|
||||
#endif
|
||||
|
||||
return 0;
|
||||
}
|
||||
|
||||
static int script_save_mapreg_strsub(DBKey key,void *data,va_list ap)
|
||||
{
|
||||
int num=key.i&0x00ffffff, i=key.i>>24;
|
||||
char *name=str_buf+str_data[num].str;
|
||||
|
||||
#if defined(TXT_ONLY) || !defined(MAPREGSQL)
|
||||
FILE *fp=va_arg(ap,FILE*);
|
||||
if( name[1]!='@' ) {
|
||||
if(i==0)
|
||||
fprintf(fp,"%s\t%s\n", name, (char *)data);
|
||||
else
|
||||
fprintf(fp,"%s,%d\t%s\n", name, i, (char *)data);
|
||||
}
|
||||
#else
|
||||
if ( name[1] != '@') {
|
||||
char tmp_str2[2*255+1];
|
||||
Sql_EscapeStringLen(mmysql_handle, tmp_str2, (char*)data, safestrnlen((char*)data, 255));
|
||||
if( SQL_ERROR == Sql_Query(mmysql_handle, "UPDATE `%s` SET `%s`='%s' WHERE `%s`='%s' AND `%s`='%d'", mapregsql_db, mapregsql_db_value, tmp_str2, mapregsql_db_varname, name, mapregsql_db_index, i) )
|
||||
Sql_ShowDebug(mmysql_handle);
|
||||
}
|
||||
#endif
|
||||
|
||||
return 0;
|
||||
}
|
||||
static int script_save_mapreg(void)
|
||||
{
|
||||
#if defined(TXT_ONLY) || !defined(MAPREGSQL)
|
||||
FILE *fp;
|
||||
int lock;
|
||||
|
||||
if( (fp=lock_fopen(mapreg_txt,&lock))==NULL ) {
|
||||
ShowError("script_save_mapreg: Unable to lock-open file [%s]\n",mapreg_txt);
|
||||
return -1;
|
||||
}
|
||||
mapreg_db->foreach(mapreg_db,script_save_mapreg_intsub,fp);
|
||||
mapregstr_db->foreach(mapregstr_db,script_save_mapreg_strsub,fp);
|
||||
lock_fclose(fp,mapreg_txt,&lock);
|
||||
#else
|
||||
mapreg_db->foreach(mapreg_db,script_save_mapreg_intsub);
|
||||
mapregstr_db->foreach(mapregstr_db,script_save_mapreg_strsub);
|
||||
#endif
|
||||
mapreg_dirty=0;
|
||||
return 0;
|
||||
}
|
||||
static int script_autosave_mapreg(int tid, unsigned int tick, int id, intptr data)
|
||||
{
|
||||
if(mapreg_dirty)
|
||||
if (script_save_mapreg() == -1)
|
||||
ShowError("Failed to save the mapreg data!\n");
|
||||
return 0;
|
||||
}
|
||||
|
||||
int script_config_read(char *cfgName)
|
||||
{
|
||||
int i;
|
||||
@ -3548,11 +3310,8 @@ int do_final_script()
|
||||
}
|
||||
#endif
|
||||
|
||||
if(mapreg_dirty>=0)
|
||||
script_save_mapreg();
|
||||
mapreg_final();
|
||||
|
||||
mapreg_db->destroy(mapreg_db,NULL);
|
||||
mapregstr_db->destroy(mapregstr_db,NULL);
|
||||
scriptlabel_db->destroy(scriptlabel_db,NULL);
|
||||
userfunc_db->destroy(userfunc_db,do_final_userfunc_sub);
|
||||
if(sleep_db) {
|
||||
@ -3578,26 +3337,16 @@ int do_final_script()
|
||||
*------------------------------------------*/
|
||||
int do_init_script()
|
||||
{
|
||||
mapreg_db= idb_alloc(DB_OPT_BASE);
|
||||
mapregstr_db=idb_alloc(DB_OPT_RELEASE_DATA);
|
||||
userfunc_db=strdb_alloc(DB_OPT_DUP_KEY,0);
|
||||
scriptlabel_db=strdb_alloc((DBOptions)(DB_OPT_DUP_KEY|DB_OPT_ALLOW_NULL_DATA),50);
|
||||
|
||||
mapreg_init();
|
||||
|
||||
script_load_mapreg();
|
||||
|
||||
add_timer_func_list(script_autosave_mapreg, "script_autosave_mapreg");
|
||||
add_timer_interval(gettick() + MAPREG_AUTOSAVE_INTERVAL, script_autosave_mapreg, 0, 0, MAPREG_AUTOSAVE_INTERVAL);
|
||||
|
||||
return 0;
|
||||
}
|
||||
|
||||
int script_reload()
|
||||
{
|
||||
if(mapreg_dirty>=0)
|
||||
script_save_mapreg();
|
||||
|
||||
mapreg_db->clear(mapreg_db, NULL);
|
||||
mapregstr_db->clear(mapregstr_db, NULL);
|
||||
userfunc_db->clear(userfunc_db,do_final_userfunc_sub);
|
||||
scriptlabel_db->clear(scriptlabel_db, NULL);
|
||||
|
||||
@ -3614,7 +3363,7 @@ int script_reload()
|
||||
linkdb_final(&sleep_db);
|
||||
}
|
||||
|
||||
script_load_mapreg();
|
||||
mapreg_reload();
|
||||
return 0;
|
||||
}
|
||||
|
||||
|
@ -4,6 +4,8 @@
|
||||
#ifndef _SCRIPT_H_
|
||||
#define _SCRIPT_H_
|
||||
|
||||
struct map_session_data;
|
||||
|
||||
extern int potion_flag; //For use on Alchemist improved potions/Potion Pitcher. [Skotlex]
|
||||
extern int potion_hp, potion_per_hp, potion_sp, potion_per_sp;
|
||||
extern int potion_target;
|
||||
@ -150,7 +152,8 @@ struct DBMap* script_get_userfunc_db(void);
|
||||
int script_config_read(char *cfgName);
|
||||
int do_init_script(void);
|
||||
int do_final_script(void);
|
||||
int add_str(const char *p);
|
||||
int add_str(const char* p);
|
||||
const char* get_str(int id);
|
||||
int script_reload(void);
|
||||
|
||||
extern char mapreg_txt[];
|
||||
|
@ -283,8 +283,6 @@ int convert_init(void)
|
||||
fclose(fp);
|
||||
}
|
||||
|
||||
//FIXME: CONVERT MAPREG HERE! (after enforcing MAPREGSQL for sql)
|
||||
|
||||
return 0;
|
||||
}
|
||||
|
||||
|
@ -303,6 +303,14 @@ SOURCE=..\src\map\map.h
|
||||
# End Source File
|
||||
# Begin Source File
|
||||
|
||||
SOURCE=..\src\map\mapreg.h
|
||||
# End Source File
|
||||
# Begin Source File
|
||||
|
||||
SOURCE=..\src\map\mapreg_sql.c
|
||||
# End Source File
|
||||
# Begin Source File
|
||||
|
||||
SOURCE=..\src\map\mercenary.c
|
||||
# End Source File
|
||||
# Begin Source File
|
||||
|
@ -359,6 +359,14 @@ SOURCE=..\src\map\map.h
|
||||
# End Source File
|
||||
# Begin Source File
|
||||
|
||||
SOURCE=..\src\map\mapreg.h
|
||||
# End Source File
|
||||
# Begin Source File
|
||||
|
||||
SOURCE=..\src\map\mapreg_txt.c
|
||||
# End Source File
|
||||
# Begin Source File
|
||||
|
||||
SOURCE=..\src\map\mercenary.h
|
||||
# End Source File
|
||||
# Begin Source File
|
||||
|
@ -22,7 +22,7 @@
|
||||
/wd4100"
|
||||
Optimization="0"
|
||||
AdditionalIncludeDirectories="..\3rdparty\mysql\include;..\3rdparty\zlib\include;..\3rdparty\pcre\include"
|
||||
PreprocessorDefinitions="WIN32;_WIN32;__WIN32;_DEBUG;PCRE_SUPPORT;MAPREGSQL;FD_SETSIZE=4096;DB_MANUAL_CAST_TO_UNION"
|
||||
PreprocessorDefinitions="WIN32;_WIN32;__WIN32;_DEBUG;PCRE_SUPPORT;FD_SETSIZE=4096;DB_MANUAL_CAST_TO_UNION"
|
||||
GeneratePreprocessedFile="0"
|
||||
MinimalRebuild="TRUE"
|
||||
ExceptionHandling="FALSE"
|
||||
@ -94,7 +94,7 @@
|
||||
OptimizeForProcessor="2"
|
||||
OptimizeForWindowsApplication="TRUE"
|
||||
AdditionalIncludeDirectories="..\3rdparty\mysql\include;..\3rdparty\zlib\include;..\3rdparty\pcre\include"
|
||||
PreprocessorDefinitions="WIN32;_WIN32;__WIN32;NDEBUG;PCRE_SUPPORT;MAPREGSQL;FD_SETSIZE=4096;DB_MANUAL_CAST_TO_UNION"
|
||||
PreprocessorDefinitions="WIN32;_WIN32;__WIN32;NDEBUG;PCRE_SUPPORT;FD_SETSIZE=4096;DB_MANUAL_CAST_TO_UNION"
|
||||
StringPooling="TRUE"
|
||||
RuntimeLibrary="3"
|
||||
DefaultCharIsUnsigned="FALSE"
|
||||
@ -226,6 +226,12 @@
|
||||
<File
|
||||
RelativePath="..\src\map\map.h">
|
||||
</File>
|
||||
<File
|
||||
RelativePath="..\src\map\mapreg.h">
|
||||
</File>
|
||||
<File
|
||||
RelativePath="..\src\map\mapreg_sql.c">
|
||||
</File>
|
||||
<File
|
||||
RelativePath="..\src\map\mercenary.c">
|
||||
</File>
|
||||
|
@ -226,6 +226,12 @@
|
||||
<File
|
||||
RelativePath="..\src\map\map.h">
|
||||
</File>
|
||||
<File
|
||||
RelativePath="..\src\map\mapreg.h">
|
||||
</File>
|
||||
<File
|
||||
RelativePath="..\src\map\mapreg_txt.c">
|
||||
</File>
|
||||
<File
|
||||
RelativePath="..\src\map\mercenary.c">
|
||||
</File>
|
||||
|
@ -41,7 +41,7 @@
|
||||
Name="VCCLCompilerTool"
|
||||
Optimization="0"
|
||||
AdditionalIncludeDirectories="..\3rdparty\mysql\include;..\3rdparty\zlib\include;..\3rdparty\pcre\include"
|
||||
PreprocessorDefinitions="WIN32;_WIN32;__WIN32;_DEBUG;PCRE_SUPPORT;MAPREGSQL;_CRT_SECURE_NO_DEPRECATE;_CRT_NONSTDC_NO_DEPRECATE;FD_SETSIZE=4096;DB_MANUAL_CAST_TO_UNION"
|
||||
PreprocessorDefinitions="WIN32;_WIN32;__WIN32;_DEBUG;PCRE_SUPPORT;_CRT_SECURE_NO_DEPRECATE;_CRT_NONSTDC_NO_DEPRECATE;FD_SETSIZE=4096;DB_MANUAL_CAST_TO_UNION"
|
||||
GeneratePreprocessedFile="0"
|
||||
MinimalRebuild="true"
|
||||
ExceptionHandling="0"
|
||||
@ -133,7 +133,7 @@
|
||||
EnableFiberSafeOptimizations="true"
|
||||
WholeProgramOptimization="true"
|
||||
AdditionalIncludeDirectories="..\3rdparty\mysql\include;..\3rdparty\zlib\include;..\3rdparty\pcre\include"
|
||||
PreprocessorDefinitions="WIN32;_WIN32;__WIN32;NDEBUG;PCRE_SUPPORT;MAPREGSQL;_CRT_SECURE_NO_DEPRECATE;_CRT_NONSTDC_NO_DEPRECATE;FD_SETSIZE=4096;DB_MANUAL_CAST_TO_UNION"
|
||||
PreprocessorDefinitions="WIN32;_WIN32;__WIN32;NDEBUG;PCRE_SUPPORT;_CRT_SECURE_NO_DEPRECATE;_CRT_NONSTDC_NO_DEPRECATE;FD_SETSIZE=4096;DB_MANUAL_CAST_TO_UNION"
|
||||
StringPooling="true"
|
||||
RuntimeLibrary="0"
|
||||
DefaultCharIsUnsigned="false"
|
||||
@ -441,6 +441,14 @@
|
||||
RelativePath="..\src\map\map.h"
|
||||
>
|
||||
</File>
|
||||
<File
|
||||
RelativePath="..\src\map\mapreg.h"
|
||||
>
|
||||
</File>
|
||||
<File
|
||||
RelativePath="..\src\map\mapreg_sql.c"
|
||||
>
|
||||
</File>
|
||||
<File
|
||||
RelativePath="..\src\map\mercenary.c"
|
||||
>
|
||||
|
@ -300,6 +300,14 @@
|
||||
RelativePath="..\src\map\map.h"
|
||||
>
|
||||
</File>
|
||||
<File
|
||||
RelativePath="..\src\map\mapreg.h"
|
||||
>
|
||||
</File>
|
||||
<File
|
||||
RelativePath="..\src\map\mapreg_txt.c"
|
||||
>
|
||||
</File>
|
||||
<File
|
||||
RelativePath="..\src\map\mercenary.c"
|
||||
>
|
||||
|
@ -42,7 +42,7 @@
|
||||
Name="VCCLCompilerTool"
|
||||
Optimization="0"
|
||||
AdditionalIncludeDirectories="..\3rdparty\mysql\include;..\3rdparty\zlib\include;..\3rdparty\pcre\include"
|
||||
PreprocessorDefinitions="WIN32;_WIN32;__WIN32;_DEBUG;PCRE_SUPPORT;MAPREGSQL;_CRT_SECURE_NO_DEPRECATE;_CRT_NONSTDC_NO_DEPRECATE;FD_SETSIZE=4096;DB_MANUAL_CAST_TO_UNION"
|
||||
PreprocessorDefinitions="WIN32;_WIN32;__WIN32;_DEBUG;PCRE_SUPPORT;_CRT_SECURE_NO_DEPRECATE;_CRT_NONSTDC_NO_DEPRECATE;FD_SETSIZE=4096;DB_MANUAL_CAST_TO_UNION"
|
||||
GeneratePreprocessedFile="0"
|
||||
MinimalRebuild="true"
|
||||
ExceptionHandling="0"
|
||||
@ -136,7 +136,7 @@
|
||||
EnableFiberSafeOptimizations="true"
|
||||
WholeProgramOptimization="true"
|
||||
AdditionalIncludeDirectories="..\3rdparty\mysql\include;..\3rdparty\zlib\include;..\3rdparty\pcre\include"
|
||||
PreprocessorDefinitions="WIN32;_WIN32;__WIN32;NDEBUG;PCRE_SUPPORT;MAPREGSQL;_CRT_SECURE_NO_DEPRECATE;_CRT_NONSTDC_NO_DEPRECATE;FD_SETSIZE=4096;DB_MANUAL_CAST_TO_UNION"
|
||||
PreprocessorDefinitions="WIN32;_WIN32;__WIN32;NDEBUG;PCRE_SUPPORT;_CRT_SECURE_NO_DEPRECATE;_CRT_NONSTDC_NO_DEPRECATE;FD_SETSIZE=4096;DB_MANUAL_CAST_TO_UNION"
|
||||
StringPooling="true"
|
||||
RuntimeLibrary="0"
|
||||
DefaultCharIsUnsigned="false"
|
||||
@ -446,6 +446,14 @@
|
||||
RelativePath="..\src\map\map.h"
|
||||
>
|
||||
</File>
|
||||
<File
|
||||
RelativePath="..\src\map\mapreg.h"
|
||||
>
|
||||
</File>
|
||||
<File
|
||||
RelativePath="..\src\map\mapreg_sql.c"
|
||||
>
|
||||
</File>
|
||||
<File
|
||||
RelativePath="..\src\map\mercenary.c"
|
||||
>
|
||||
|
@ -305,6 +305,14 @@
|
||||
RelativePath="..\src\map\map.h"
|
||||
>
|
||||
</File>
|
||||
<File
|
||||
RelativePath="..\src\map\mapreg.h"
|
||||
>
|
||||
</File>
|
||||
<File
|
||||
RelativePath="..\src\map\mapreg_txt.c"
|
||||
>
|
||||
</File>
|
||||
<File
|
||||
RelativePath="..\src\map\mercenary.c"
|
||||
>
|
||||
|
Loading…
x
Reference in New Issue
Block a user