diff --git a/.gitignore b/.gitignore index 9a2ab7c..d1d940a 100644 --- a/.gitignore +++ b/.gitignore @@ -2,6 +2,11 @@ build/ build-*/ .env +# MariaDB data directory -- now a bind mount (was a Docker named volume) so +# it's visible/backup-able from the host, but that also means it lives +# inside the repo checkout and must never be committed. +/docker/data/ + # Windows game client + data assets, kept locally for end-to-end login/game # testing but not part of the server source tree. Binary/3DData is the # separate, already-pruned subset of this data the server itself actually diff --git a/CMakeLists.txt b/CMakeLists.txt index 0959fb0..7e641b9 100644 --- a/CMakeLists.txt +++ b/CMakeLists.txt @@ -34,17 +34,28 @@ add_compile_options( # in Release builds only). -fwrapv makes overflow well-defined instead # of auditing every arithmetic expression in the tree. -fwrapv + # x86-64-v2 (SSE4.2/POPCNT baseline, ~2009+ CPUs) is safe for any real + # deployment target and gets a bit more codegen than the generic x86-64 + # baseline GCC defaults to. + -march=x86-64-v2 -include "${CMAKE_SOURCE_DIR}/Src/Common/compat.h" ) add_compile_definitions(_CRT_SECURE_NO_WARNINGS) +# Link-time optimization: lets GCC inline/optimize across the many small +# .cpp translation units instead of only within each one. +include(CheckIPOSupported) +check_ipo_supported(RESULT IPO_SUPPORTED OUTPUT IPO_ERROR) +if(IPO_SUPPORTED AND CMAKE_BUILD_TYPE STREQUAL "Release") + set(CMAKE_INTERPROCEDURAL_OPTIMIZATION ON) +endif() + set(COMMON_SOURCES "Src/Common/config.cpp" "Src/Common/database/database.cpp" "Src/Common/globals.cpp" "Src/Common/log.cpp" "Src/Common/rosecrypt.cpp" - "Src/Common/seh.cpp" "Src/Common/SocketBase.cpp" "Src/Common/SocketClient.cpp" "Src/Common/SocketServer.cpp" diff --git a/README.md b/README.md index 085f202..20749bd 100644 --- a/README.md +++ b/README.md @@ -9,11 +9,20 @@ shimmed out so it builds and runs correctly under Linux/glibc/POSIX threads. ## Quick start +Needs Docker + the Compose plugin (`docker compose version` should work) on the host. Nothing else — the C++ servers, +their build toolchain, and the database all live inside the containers. + ```sh +git clone ross && cd ross cp .env.example .env # edit PUBLIC_HOST at minimum if clients connect from another machine docker compose up -d --build ``` +`docker compose up -d --build` builds the `rose-server` image (compiles all three C++ servers inside a throwaway +builder stage, see `Dockerfile`), then starts every service in `docker-compose.yml` in the background. First start +takes a minute or two (compiling + MariaDB initializing and loading `database sql files/`); `docker compose logs -f` +to watch it happen. + That brings up: | Service | Container | Port | What it is | @@ -28,6 +37,36 @@ That brings up: Point a KTRose pre-evo client at `PUBLIC_HOST:29000` and log in — `LOGIN_CREATE_ACCOUNT=1` (the default) auto-creates an account on first login with that username/password. +A default GM account is seeded into a fresh database by `database sql files/gm_account.sql`: + +- username `gmadmin`, password `changeme`, `accesslevel 900` — logs into both the game (as a GM) and the web admin + panel below. **Change this password** (via the web admin panel, or `docker compose exec db mariadb ...`) on anything + other than a throwaway local instance — it's a public default sitting in git. + +### `docker-compose.yml`, briefly + +- `x-app` at the top is a YAML anchor: a template block (image, restart policy, the full list of `environment:` + variables read from `.env`) that `loginserver`, `charserver`, and `worldserver` each pull in with `<<: *app` so the + three definitions don't repeat themselves. They differ only in `command:` (which server to run) and which port they + publish. +- `db` is stock MariaDB; anything in `database sql files/` gets executed once, alphabetically, the first time the + container starts with an empty data volume (mounted read-only at `/docker-entrypoint-initdb.d`, MariaDB's standard + init-script hook). If you change schema files after the first start, they won't re-run automatically — either + `docker compose down -v` to wipe the `db-data` volume and reinitialize, or apply the change by hand. +- `webtools` (nginx) is what clients' browsers hit; it serves the static GM toolbox directly and reverse-proxies + `/admin/*` to the `webadmin` container, which isn't published to the host itself. +- `.env` (copied from `.env.example`) is where every port, server name, and shared inter-server password gets set — + `docker-compose.yml` itself should not need editing for a normal deploy. + +Useful commands once it's up: + +```sh +docker compose logs -f worldserver # tail one server's logs +docker compose restart worldserver # restart just one service (or use the webadmin Server tab) +docker compose down # stop everything, keep the DB volume +docker compose down -v # stop everything AND wipe the database +``` + ## Web tools — `http:///` A static, no-build-step GM toolbox, generated from the same STB/DB data the server itself reads: diff --git a/Src/Char Server/main.cpp b/Src/Char Server/main.cpp index 18169fe..6abc006 100644 --- a/Src/Char Server/main.cpp +++ b/Src/Char Server/main.cpp @@ -49,9 +49,6 @@ int main(int argc, char *argv[]) else { delete server; - #ifdef _WIN32 - system("pause"); - #endif return -1; } server->LoadEncryption (); diff --git a/Src/Char Server/signal.cpp b/Src/Char Server/signal.cpp index 8baf74b..66c71f9 100644 --- a/Src/Char Server/signal.cpp +++ b/Src/Char Server/signal.cpp @@ -38,9 +38,6 @@ void StartSignal( ) signal( SIGFPE, HandleSignal ); signal( SIGSEGV, HandleSignal ); signal( SIGTERM, HandleSignal ); - #ifdef _WIN32 - signal( SIGBREAK, HandleSignal ); - #endif signal( SIGABRT, HandleSignal ); } @@ -51,9 +48,6 @@ void StopSignal( ) signal( SIGFPE, 0 ); signal( SIGSEGV, 0 ); signal( SIGTERM, 0 ); - #ifdef _WIN32 - signal( SIGBREAK, 0 ); - #endif signal( SIGABRT, 0 ); } @@ -63,21 +57,13 @@ void HandleSignal( int num ) { case SIGINT:/* Interactive attention */ Log( MSG_ERROR, "Signal received: SIGINT" ); - #ifdef _WIN32 - Sleep(1000); - #else usleep(1000); - #endif raise(num); break; case SIGILL:/* Illegal instruction */ Log( MSG_ERROR, "Signal received: SIGILL, Server will be closed, Trying to save..." ); GServer->isActive = false; - #ifdef _WIN32 - Sleep(1000); - #else usleep(1000); - #endif raise(num); break; case SIGFPE:/* Floating point error */ @@ -88,24 +74,14 @@ void HandleSignal( int num ) case SIGSEGV:/* Segmentation violation */ Log( MSG_ERROR, "Signal received: SIGSEGV, Server will be closed, Trying to save..." ); GServer->isActive = false; - #ifdef _WIN32 - Sleep(1000); - #else usleep(1000); - #endif - raise(num); - break; - + raise(num); + break; + case SIGTERM:/* Termination request */ Log( MSG_INFO, "Signal received: SIGTERM, Server will be closed" ); GServer->isActive = false; break; - #ifdef _WIN32 - case SIGBREAK:/* Control-break */ - Log( MSG_INFO, "Signal received: SIGBREAK, Server will be closed" ); - GServer->isActive = false; - break; - #endif default: cout << "Unknown Signal Number: " << num << endl; raise(num); diff --git a/Src/Common/SocketBase.cpp b/Src/Common/SocketBase.cpp index c06f1f9..07f57bb 100644 --- a/Src/Common/SocketBase.cpp +++ b/Src/Common/SocketBase.cpp @@ -45,23 +45,14 @@ void CBaseSocket::CloseSocket( void ) isActive = false; } -// Init winsocket, if we are using Windows +// No-op on Linux; kept so call sites don't need to special-case platforms. bool InitWinSocket ( void ) { -#ifdef _WIN32 - WSADATA wsa; - return (WSAStartup(MAKEWORD(2,0),&wsa)==0); -#else return true; -#endif } -// Close winsocket, if we are using Windows void CloseWinSocket( void ) { -#ifdef _WIN32 - WSACleanup( ); -#endif } diff --git a/Src/Common/SocketClient.cpp b/Src/Common/SocketClient.cpp index b3644b4..5beea78 100644 --- a/Src/Common/SocketClient.cpp +++ b/Src/Common/SocketClient.cpp @@ -19,7 +19,6 @@ developed with Main erose/hrose source server + some change from the original eich source */ #include "sockets.h" -#include "seh.hpp" #include "config.h" // Constructor @@ -183,16 +182,6 @@ void CClientSocket::SendPacket( CPacket *P ) Log(MSG_WARNING,"tried to send a packet to a socket that doesn't exist any more"); return; } - //__seh_try - //{ - // EncryptBuffer( CryptTable, Buffer ); - //} - //__seh_except(info, context) - //{ - // Log(MSG_WARNING,"Caught a bad packet %s. Send cancelled", Buffer); - // return; - //} - //__seh_end EncryptBuffer( CryptTable, Buffer2 ); #endif send( sock, (char*)Buffer2, Size, 0 ); diff --git a/Src/Common/SocketServer.cpp b/Src/Common/SocketServer.cpp index 0c76d01..29fe633 100644 --- a/Src/Common/SocketServer.cpp +++ b/Src/Common/SocketServer.cpp @@ -289,21 +289,13 @@ void CServerSocket::ServerLoop( ) if ( activity == 0 )continue; if ( activity < 0 && errno != EINTR ) { - #ifdef _WIN32 - Log( MSG_ERROR, "Select command failed. Error #%i", WSAGetLastError() ); - #else Log( MSG_ERROR, "Select command failed. Error #%i", errno ); - #endif isActive = false; } if ( LOG_THISSERVER != LOG_LOGIN_SERVER && FD_ISSET( sckISC, &fds ) ) { int clientinfolen = sizeof( sockaddr_in ); - #ifdef _WIN32 - NewSocket = accept( sckISC, (sockaddr*)&ClientInfo, (int*)&clientinfolen ); - #else NewSocket = accept( sckISC, (sockaddr*)&ClientInfo, (socklen_t*)&clientinfolen ); - #endif // TODO: check if server is full if (NewSocket != INVALID_SOCKET) { @@ -312,42 +304,26 @@ void CServerSocket::ServerLoop( ) } else { - #ifdef _WIN32 - Log( MSG_ERROR, "Error accepting socket: %i", WSAGetLastError() ); - #else Log( MSG_ERROR, "Error accepting socket: %i", errno ); - #endif } } } if ( activity < 0 && errno != EINTR ) { - #ifdef _WIN32 - Log( MSG_ERROR, "Select command failed. Error #%i", WSAGetLastError() ); - #else Log( MSG_ERROR, "Select command failed. Error #%i", errno ); - #endif isActive = false; } if ( FD_ISSET( sock, &fds ) ) { int clientinfolen = sizeof( sockaddr_in ); - #ifdef _WIN32 - NewSocket = accept( sock, (sockaddr*)&ClientInfo, (int*)&clientinfolen ); - #else NewSocket = accept( sock, (sockaddr*)&ClientInfo, (socklen_t*)&clientinfolen ); - #endif // TODO: check if server is full if (NewSocket != INVALID_SOCKET) AddUser( NewSocket, &ClientInfo, false ); else { - #ifdef _WIN32 - Log( MSG_ERROR, "Error accepting socket: %i", WSAGetLastError() ); - #else Log( MSG_ERROR, "Error accepting socket: %i", errno ); - #endif } } if(!Config.usethreads) diff --git a/Src/Common/config.cpp b/Src/Common/config.cpp index 9b17f15..cfcb25e 100644 --- a/Src/Common/config.cpp +++ b/Src/Common/config.cpp @@ -45,18 +45,6 @@ bool ConfigGetEntry( const char *pcFile, const char *pcNameMust, char* &pcResult while ( *pcPar==' ' || *pcPar=='\t' || *pcPar=='=' ) ++pcPar; *pcPoint=0; - #ifdef _WIN32 - if ( !_strcmpi( pcName, pcNameMust ) ) - { - pcResult = _strdup( pcPar ); - pcPoint = pcResult + strlen( pcPar ); - if ( *pcPoint==0 ) return true; - --pcPoint; - while( *pcPoint==' ' || *pcPoint=='\t' ) *pcPoint--=0; - return true; - } - - #else if ( strcasecmp( pcName, pcNameMust )==0 ) { pcResult = _strdup( pcPar ); @@ -66,7 +54,6 @@ bool ConfigGetEntry( const char *pcFile, const char *pcNameMust, char* &pcResult while( *pcPoint==' ' || *pcPoint=='\t' ) *pcPoint--=0; return true; } - #endif } while ( !feof( fh ) ); diff --git a/Src/Common/log.cpp b/Src/Common/log.cpp index 84dae62..62b1408 100644 --- a/Src/Common/log.cpp +++ b/Src/Common/log.cpp @@ -1,8 +1,3 @@ -#ifdef _WIN32 - #include - #include - #include -#endif #include #include #include @@ -38,12 +33,6 @@ static int __FOREGROUND = LIGHTGRAY; // Change console text color void textcolor(int color) { - #ifdef _WIN32 - __FOREGROUND = color; - SetConsoleTextAttribute(GetStdHandle(STD_OUTPUT_HANDLE), color + (__BACKGROUND << 4)); - #else - - #endif } // This function logs based on flags diff --git a/Src/Common/log.h b/Src/Common/log.h index 8d47887..a8ffb43 100644 --- a/Src/Common/log.h +++ b/Src/Common/log.h @@ -6,13 +6,7 @@ #define __ROSE_LOGGING_FUNCTIONS__ // Log path -#ifdef _WIN32 -# define LOG_DIRECTORY "log/" -#endif - -#ifdef __unix__ -# define LOG_DIRECTORY "/var/log/roseserver/" -#endif +#define LOG_DIRECTORY "/var/log/roseserver/" #define LOG_LOGIN_SERVER 0x01 #define LOG_CHARACTER_SERVER 0x02 diff --git a/Src/Common/mysql/mysql.h b/Src/Common/mysql/mysql.h deleted file mode 100644 index ab61fe6..0000000 --- a/Src/Common/mysql/mysql.h +++ /dev/null @@ -1,739 +0,0 @@ -/* Copyright (C) 2000-2003 MySQL AB - - This program 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 2 of the License, or - (at your option) any later version. - - This program 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 this program; if not, write to the Free Software - Foundation, Inc., 59 Temple Place, Suite 330, Boston, MA 02111-1307 USA */ - -#ifndef _mysql_h -#define _mysql_h - -#ifdef __CYGWIN__ /* CYGWIN implements a UNIX API */ -#undef WIN -#undef _WIN -#undef _WIN32 -#undef _WIN64 -#undef __WIN__ -#endif - -#ifdef __cplusplus -extern "C" { -#endif - -#ifndef _global_h /* If not standard header */ -#include -#ifdef __LCC__ -#include /* For windows */ -#endif -typedef char my_bool; -#if (defined(_WIN32) || defined(_WIN64)) && !defined(__WIN__) -#define __WIN__ -#endif -#if !defined(__WIN__) -#define STDCALL -#else -#define STDCALL __stdcall -#endif -typedef char * gptr; - -#ifndef my_socket_defined -#ifdef __WIN__ -#define my_socket SOCKET -#else -typedef int my_socket; -#endif /* __WIN__ */ -#endif /* my_socket_defined */ -#endif /* _global_h */ - -#include "mysql_com.h" -#include "mysql_time.h" -#include "mysql_version.h" -#include "typelib.h" - -#include "my_list.h" /* for LISTs used in 'MYSQL' and 'MYSQL_STMT' */ - -extern unsigned int mysql_port; -extern char *mysql_unix_port; - -#define CLIENT_NET_READ_TIMEOUT 365*24*3600 /* Timeout on read */ -#define CLIENT_NET_WRITE_TIMEOUT 365*24*3600 /* Timeout on write */ - -#ifdef __NETWARE__ -#pragma pack(push, 8) /* 8 byte alignment */ -#endif - -#define IS_PRI_KEY(n) ((n) & PRI_KEY_FLAG) -#define IS_NOT_NULL(n) ((n) & NOT_NULL_FLAG) -#define IS_BLOB(n) ((n) & BLOB_FLAG) -#define IS_NUM(t) ((t) <= FIELD_TYPE_INT24 || (t) == FIELD_TYPE_YEAR) -#define IS_NUM_FIELD(f) ((f)->flags & NUM_FLAG) -#define INTERNAL_NUM_FIELD(f) (((f)->type <= FIELD_TYPE_INT24 && ((f)->type != FIELD_TYPE_TIMESTAMP || (f)->length == 14 || (f)->length == 8)) || (f)->type == FIELD_TYPE_YEAR) - - -typedef struct st_mysql_field { - char *name; /* Name of column */ - char *org_name; /* Original column name, if an alias */ - char *table; /* Table of column if column was a field */ - char *org_table; /* Org table name, if table was an alias */ - char *db; /* Database for table */ - char *catalog; /* Catalog for table */ - char *def; /* Default value (set by mysql_list_fields) */ - unsigned long length; /* Width of column (create length) */ - unsigned long max_length; /* Max width for selected set */ - unsigned int name_length; - unsigned int org_name_length; - unsigned int table_length; - unsigned int org_table_length; - unsigned int db_length; - unsigned int catalog_length; - unsigned int def_length; - unsigned int flags; /* Div flags */ - unsigned int decimals; /* Number of decimals in field */ - unsigned int charsetnr; /* Character set */ - enum enum_field_types type; /* Type of field. See mysql_com.h for types */ -} MYSQL_FIELD; - -typedef char **MYSQL_ROW; /* return data as array of strings */ -typedef unsigned int MYSQL_FIELD_OFFSET; /* offset to current field */ - -#ifndef _global_h -#if defined(NO_CLIENT_LONG_LONG) -typedef unsigned long my_ulonglong; -#elif defined (__WIN__) -typedef unsigned __int64 my_ulonglong; -#else -typedef unsigned long long my_ulonglong; -#endif -#endif - -#define MYSQL_COUNT_ERROR (~(my_ulonglong) 0) - -typedef struct st_mysql_rows { - struct st_mysql_rows *next; /* list of rows */ - MYSQL_ROW data; - unsigned long length; -} MYSQL_ROWS; - -typedef MYSQL_ROWS *MYSQL_ROW_OFFSET; /* offset to current row */ - -#include "my_alloc.h" - -typedef struct st_mysql_data { - my_ulonglong rows; - unsigned int fields; - MYSQL_ROWS *data; - MEM_ROOT alloc; -#if !defined(CHECK_EMBEDDED_DIFFERENCES) || defined(EMBEDDED_LIBRARY) - MYSQL_ROWS **prev_ptr; -#endif -} MYSQL_DATA; - -enum mysql_option -{ - MYSQL_OPT_CONNECT_TIMEOUT, MYSQL_OPT_COMPRESS, MYSQL_OPT_NAMED_PIPE, - MYSQL_INIT_COMMAND, MYSQL_READ_DEFAULT_FILE, MYSQL_READ_DEFAULT_GROUP, - MYSQL_SET_CHARSET_DIR, MYSQL_SET_CHARSET_NAME, MYSQL_OPT_LOCAL_INFILE, - MYSQL_OPT_PROTOCOL, MYSQL_SHARED_MEMORY_BASE_NAME, MYSQL_OPT_READ_TIMEOUT, - MYSQL_OPT_WRITE_TIMEOUT, MYSQL_OPT_USE_RESULT, - MYSQL_OPT_USE_REMOTE_CONNECTION, MYSQL_OPT_USE_EMBEDDED_CONNECTION, - MYSQL_OPT_GUESS_CONNECTION, MYSQL_SET_CLIENT_IP, MYSQL_SECURE_AUTH -}; - -struct st_mysql_options { - unsigned int connect_timeout, read_timeout, write_timeout; - unsigned int port, protocol; - unsigned long client_flag; - char *host,*user,*password,*unix_socket,*db; - struct st_dynamic_array *init_commands; - char *my_cnf_file,*my_cnf_group, *charset_dir, *charset_name; - char *ssl_key; /* PEM key file */ - char *ssl_cert; /* PEM cert file */ - char *ssl_ca; /* PEM CA file */ - char *ssl_capath; /* PEM directory of CA-s? */ - char *ssl_cipher; /* cipher to use */ - char *shared_memory_base_name; - unsigned long max_allowed_packet; - my_bool use_ssl; /* if to use SSL or not */ - my_bool compress,named_pipe; - /* - On connect, find out the replication role of the server, and - establish connections to all the peers - */ - my_bool rpl_probe; - /* - Each call to mysql_real_query() will parse it to tell if it is a read - or a write, and direct it to the slave or the master - */ - my_bool rpl_parse; - /* - If set, never read from a master, only from slave, when doing - a read that is replication-aware - */ - my_bool no_master_reads; -#if !defined(CHECK_EMBEDDED_DIFFERENCES) || defined(EMBEDDED_LIBRARY) - my_bool separate_thread; -#endif - enum mysql_option methods_to_use; - char *client_ip; - /* Refuse client connecting to server if it uses old (pre-4.1.1) protocol */ - my_bool secure_auth; - - /* function pointers for local infile support */ - int (*local_infile_init)(void **, const char *, void *); - int (*local_infile_read)(void *, char *, unsigned int); - void (*local_infile_end)(void *); - int (*local_infile_error)(void *, char *, unsigned int); - void *local_infile_userdata; -}; - -enum mysql_status -{ - MYSQL_STATUS_READY,MYSQL_STATUS_GET_RESULT,MYSQL_STATUS_USE_RESULT -}; - -enum mysql_protocol_type -{ - MYSQL_PROTOCOL_DEFAULT, MYSQL_PROTOCOL_TCP, MYSQL_PROTOCOL_SOCKET, - MYSQL_PROTOCOL_PIPE, MYSQL_PROTOCOL_MEMORY -}; -/* - There are three types of queries - the ones that have to go to - the master, the ones that go to a slave, and the adminstrative - type which must happen on the pivot connectioin -*/ -enum mysql_rpl_type -{ - MYSQL_RPL_MASTER, MYSQL_RPL_SLAVE, MYSQL_RPL_ADMIN -}; - -struct st_mysql_methods; - -typedef struct st_mysql -{ - NET net; /* Communication parameters */ - gptr connector_fd; /* ConnectorFd for SSL */ - char *host,*user,*passwd,*unix_socket,*server_version,*host_info,*info; - char *db; - struct charset_info_st *charset; - MYSQL_FIELD *fields; - MEM_ROOT field_alloc; - my_ulonglong affected_rows; - my_ulonglong insert_id; /* id if insert on table with NEXTNR */ - my_ulonglong extra_info; /* Used by mysqlshow */ - unsigned long thread_id; /* Id for connection in server */ - unsigned long packet_length; - unsigned int port; - unsigned long client_flag,server_capabilities; - unsigned int protocol_version; - unsigned int field_count; - unsigned int server_status; - unsigned int server_language; - unsigned int warning_count; - struct st_mysql_options options; - enum mysql_status status; - my_bool free_me; /* If free in mysql_close */ - my_bool reconnect; /* set to 1 if automatic reconnect */ - - /* session-wide random string */ - char scramble[SCRAMBLE_LENGTH+1]; - - /* - Set if this is the original connection, not a master or a slave we have - added though mysql_rpl_probe() or mysql_set_master()/ mysql_add_slave() - */ - my_bool rpl_pivot; - /* - Pointers to the master, and the next slave connections, points to - itself if lone connection. - */ - struct st_mysql* master, *next_slave; - - struct st_mysql* last_used_slave; /* needed for round-robin slave pick */ - /* needed for send/read/store/use result to work correctly with replication */ - struct st_mysql* last_used_con; - - LIST *stmts; /* list of all statements */ - const struct st_mysql_methods *methods; - void *thd; - /* - Points to boolean flag in MYSQL_RES or MYSQL_STMT. We set this flag - from mysql_stmt_close if close had to cancel result set of this object. - */ - my_bool *unbuffered_fetch_owner; -} MYSQL; - -typedef struct st_mysql_res { - my_ulonglong row_count; - MYSQL_FIELD *fields; - MYSQL_DATA *data; - MYSQL_ROWS *data_cursor; - unsigned long *lengths; /* column lengths of current row */ - MYSQL *handle; /* for unbuffered reads */ - MEM_ROOT field_alloc; - unsigned int field_count, current_field; - MYSQL_ROW row; /* If unbuffered read */ - MYSQL_ROW current_row; /* buffer to current row */ - my_bool eof; /* Used by mysql_fetch_row */ - /* mysql_stmt_close() had to cancel this result */ - my_bool unbuffered_fetch_cancelled; - const struct st_mysql_methods *methods; -} MYSQL_RES; - -#define MAX_MYSQL_MANAGER_ERR 256 -#define MAX_MYSQL_MANAGER_MSG 256 - -#define MANAGER_OK 200 -#define MANAGER_INFO 250 -#define MANAGER_ACCESS 401 -#define MANAGER_CLIENT_ERR 450 -#define MANAGER_INTERNAL_ERR 500 - -#if !defined(MYSQL_SERVER) && !defined(MYSQL_CLIENT) -#define MYSQL_CLIENT -#endif - - -typedef struct st_mysql_manager -{ - NET net; - char *host,*user,*passwd; - unsigned int port; - my_bool free_me; - my_bool eof; - int cmd_status; - int last_errno; - char* net_buf,*net_buf_pos,*net_data_end; - int net_buf_size; - char last_error[MAX_MYSQL_MANAGER_ERR]; -} MYSQL_MANAGER; - -typedef struct st_mysql_parameters -{ - unsigned long *p_max_allowed_packet; - unsigned long *p_net_buffer_length; -} MYSQL_PARAMETERS; - -#if !defined(MYSQL_SERVER) && !defined(EMBEDDED_LIBRARY) -#define max_allowed_packet (*mysql_get_parameters()->p_max_allowed_packet) -#define net_buffer_length (*mysql_get_parameters()->p_net_buffer_length) -#endif - -/* - Set up and bring down the server; to ensure that applications will - work when linked against either the standard client library or the - embedded server library, these functions should be called. -*/ -int STDCALL mysql_server_init(int argc, char **argv, char **groups); -void STDCALL mysql_server_end(void); -/* - mysql_server_init/end need to be called when using libmysqld or - libmysqlclient (exactly, mysql_server_init() is called by mysql_init() so - you don't need to call it explicitely; but you need to call - mysql_server_end() to free memory). The names are a bit misleading - (mysql_SERVER* to be used when using libmysqlCLIENT). So we add more general - names which suit well whether you're using libmysqld or libmysqlclient. We - intend to promote these aliases over the mysql_server* ones. -*/ -#define mysql_library_init mysql_server_init -#define mysql_library_end mysql_server_end - -MYSQL_PARAMETERS *STDCALL mysql_get_parameters(void); - -/* - Set up and bring down a thread; these function should be called - for each thread in an application which opens at least one MySQL - connection. All uses of the connection(s) should be between these - function calls. -*/ -my_bool STDCALL mysql_thread_init(void); -void STDCALL mysql_thread_end(void); - -/* - Functions to get information from the MYSQL and MYSQL_RES structures - Should definitely be used if one uses shared libraries. -*/ - -my_ulonglong STDCALL mysql_num_rows(MYSQL_RES *res); -unsigned int STDCALL mysql_num_fields(MYSQL_RES *res); -my_bool STDCALL mysql_eof(MYSQL_RES *res); -MYSQL_FIELD *STDCALL mysql_fetch_field_direct(MYSQL_RES *res, - unsigned int fieldnr); -MYSQL_FIELD * STDCALL mysql_fetch_fields(MYSQL_RES *res); -MYSQL_ROW_OFFSET STDCALL mysql_row_tell(MYSQL_RES *res); -MYSQL_FIELD_OFFSET STDCALL mysql_field_tell(MYSQL_RES *res); - -unsigned int STDCALL mysql_field_count(MYSQL *mysql); -my_ulonglong STDCALL mysql_affected_rows(MYSQL *mysql); -my_ulonglong STDCALL mysql_insert_id(MYSQL *mysql); -unsigned int STDCALL mysql_errno(MYSQL *mysql); -const char * STDCALL mysql_error(MYSQL *mysql); -const char *STDCALL mysql_sqlstate(MYSQL *mysql); -unsigned int STDCALL mysql_warning_count(MYSQL *mysql); -const char * STDCALL mysql_info(MYSQL *mysql); -unsigned long STDCALL mysql_thread_id(MYSQL *mysql); -const char * STDCALL mysql_character_set_name(MYSQL *mysql); -int STDCALL mysql_set_character_set(MYSQL *mysql, char *csname); - -MYSQL * STDCALL mysql_init(MYSQL *mysql); -my_bool STDCALL mysql_ssl_set(MYSQL *mysql, const char *key, - const char *cert, const char *ca, - const char *capath, const char *cipher); -my_bool STDCALL mysql_change_user(MYSQL *mysql, const char *user, - const char *passwd, const char *db); -MYSQL * STDCALL mysql_real_connect(MYSQL *mysql, const char *host, - const char *user, - const char *passwd, - const char *db, - unsigned int port, - const char *unix_socket, - unsigned long clientflag); -int STDCALL mysql_select_db(MYSQL *mysql, const char *db); -int STDCALL mysql_query(MYSQL *mysql, const char *q); -int STDCALL mysql_send_query(MYSQL *mysql, const char *q, - unsigned long length); -int STDCALL mysql_real_query(MYSQL *mysql, const char *q, - unsigned long length); -MYSQL_RES * STDCALL mysql_store_result(MYSQL *mysql); -MYSQL_RES * STDCALL mysql_use_result(MYSQL *mysql); - -/* perform query on master */ -my_bool STDCALL mysql_master_query(MYSQL *mysql, const char *q, - unsigned long length); -my_bool STDCALL mysql_master_send_query(MYSQL *mysql, const char *q, - unsigned long length); -/* perform query on slave */ -my_bool STDCALL mysql_slave_query(MYSQL *mysql, const char *q, - unsigned long length); -my_bool STDCALL mysql_slave_send_query(MYSQL *mysql, const char *q, - unsigned long length); - -/* local infile support */ - -#define LOCAL_INFILE_ERROR_LEN 512 - -void -mysql_set_local_infile_handler(MYSQL *mysql, - int (*local_infile_init)(void **, const char *, - void *), - int (*local_infile_read)(void *, char *, - unsigned int), - void (*local_infile_end)(void *), - int (*local_infile_error)(void *, char*, - unsigned int), - void *); - -void -mysql_set_local_infile_default(MYSQL *mysql); - - -/* - enable/disable parsing of all queries to decide if they go on master or - slave -*/ -void STDCALL mysql_enable_rpl_parse(MYSQL* mysql); -void STDCALL mysql_disable_rpl_parse(MYSQL* mysql); -/* get the value of the parse flag */ -int STDCALL mysql_rpl_parse_enabled(MYSQL* mysql); - -/* enable/disable reads from master */ -void STDCALL mysql_enable_reads_from_master(MYSQL* mysql); -void STDCALL mysql_disable_reads_from_master(MYSQL* mysql); -/* get the value of the master read flag */ -my_bool STDCALL mysql_reads_from_master_enabled(MYSQL* mysql); - -enum mysql_rpl_type STDCALL mysql_rpl_query_type(const char* q, int len); - -/* discover the master and its slaves */ -my_bool STDCALL mysql_rpl_probe(MYSQL* mysql); - -/* set the master, close/free the old one, if it is not a pivot */ -int STDCALL mysql_set_master(MYSQL* mysql, const char* host, - unsigned int port, - const char* user, - const char* passwd); -int STDCALL mysql_add_slave(MYSQL* mysql, const char* host, - unsigned int port, - const char* user, - const char* passwd); - -int STDCALL mysql_shutdown(MYSQL *mysql, - enum mysql_enum_shutdown_level - shutdown_level); -int STDCALL mysql_dump_debug_info(MYSQL *mysql); -int STDCALL mysql_refresh(MYSQL *mysql, - unsigned int refresh_options); -int STDCALL mysql_kill(MYSQL *mysql,unsigned long pid); -int STDCALL mysql_set_server_option(MYSQL *mysql, - enum enum_mysql_set_option - option); -int STDCALL mysql_ping(MYSQL *mysql); -const char * STDCALL mysql_stat(MYSQL *mysql); -const char * STDCALL mysql_get_server_info(MYSQL *mysql); -const char * STDCALL mysql_get_client_info(void); -unsigned long STDCALL mysql_get_client_version(void); -const char * STDCALL mysql_get_host_info(MYSQL *mysql); -unsigned long STDCALL mysql_get_server_version(MYSQL *mysql); -unsigned int STDCALL mysql_get_proto_info(MYSQL *mysql); -MYSQL_RES * STDCALL mysql_list_dbs(MYSQL *mysql,const char *wild); -MYSQL_RES * STDCALL mysql_list_tables(MYSQL *mysql,const char *wild); -MYSQL_RES * STDCALL mysql_list_processes(MYSQL *mysql); -int STDCALL mysql_options(MYSQL *mysql,enum mysql_option option, - const char *arg); -void STDCALL mysql_free_result(MYSQL_RES *result); -void STDCALL mysql_data_seek(MYSQL_RES *result, - my_ulonglong offset); -MYSQL_ROW_OFFSET STDCALL mysql_row_seek(MYSQL_RES *result, - MYSQL_ROW_OFFSET offset); -MYSQL_FIELD_OFFSET STDCALL mysql_field_seek(MYSQL_RES *result, - MYSQL_FIELD_OFFSET offset); -MYSQL_ROW STDCALL mysql_fetch_row(MYSQL_RES *result); -unsigned long * STDCALL mysql_fetch_lengths(MYSQL_RES *result); -MYSQL_FIELD * STDCALL mysql_fetch_field(MYSQL_RES *result); -MYSQL_RES * STDCALL mysql_list_fields(MYSQL *mysql, const char *table, - const char *wild); -unsigned long STDCALL mysql_escape_string(char *to,const char *from, - unsigned long from_length); -unsigned long STDCALL mysql_hex_string(char *to,const char *from, - unsigned long from_length); -unsigned long STDCALL mysql_real_escape_string(MYSQL *mysql, - char *to,const char *from, - unsigned long length); -void STDCALL mysql_debug(const char *debug); -char * STDCALL mysql_odbc_escape_string(MYSQL *mysql, - char *to, - unsigned long to_length, - const char *from, - unsigned long from_length, - void *param, - char * - (*extend_buffer) - (void *, char *to, - unsigned long *length)); -void STDCALL myodbc_remove_escape(MYSQL *mysql,char *name); -unsigned int STDCALL mysql_thread_safe(void); -my_bool STDCALL mysql_embedded(void); -MYSQL_MANAGER* STDCALL mysql_manager_init(MYSQL_MANAGER* con); -MYSQL_MANAGER* STDCALL mysql_manager_connect(MYSQL_MANAGER* con, - const char* host, - const char* user, - const char* passwd, - unsigned int port); -void STDCALL mysql_manager_close(MYSQL_MANAGER* con); -int STDCALL mysql_manager_command(MYSQL_MANAGER* con, - const char* cmd, int cmd_len); -int STDCALL mysql_manager_fetch_line(MYSQL_MANAGER* con, - char* res_buf, - int res_buf_size); -my_bool STDCALL mysql_read_query_result(MYSQL *mysql); - - -/* - The following definitions are added for the enhanced - client-server protocol -*/ - -/* statement state */ -enum enum_mysql_stmt_state -{ - MYSQL_STMT_INIT_DONE= 1, MYSQL_STMT_PREPARE_DONE, MYSQL_STMT_EXECUTE_DONE, - MYSQL_STMT_FETCH_DONE -}; - - -/* bind structure */ -typedef struct st_mysql_bind -{ - unsigned long *length; /* output length pointer */ - my_bool *is_null; /* Pointer to null indicator */ - void *buffer; /* buffer to get/put data */ - enum enum_field_types buffer_type; /* buffer type */ - unsigned long buffer_length; /* buffer length, must be set for str/binary */ - - /* Following are for internal use. Set by mysql_stmt_bind_param */ - unsigned char *inter_buffer; /* for the current data position */ - unsigned long offset; /* offset position for char/binary fetch */ - unsigned long internal_length; /* Used if length is 0 */ - unsigned int param_number; /* For null count and error messages */ - unsigned int pack_length; /* Internal length for packed data */ - my_bool is_unsigned; /* set if integer type is unsigned */ - my_bool long_data_used; /* If used with mysql_send_long_data */ - my_bool internal_is_null; /* Used if is_null is 0 */ - void (*store_param_func)(NET *net, struct st_mysql_bind *param); - void (*fetch_result)(struct st_mysql_bind *, unsigned char **row); - void (*skip_result)(struct st_mysql_bind *, MYSQL_FIELD *, - unsigned char **row); -} MYSQL_BIND; - - -/* statement handler */ -typedef struct st_mysql_stmt -{ - MEM_ROOT mem_root; /* root allocations */ - LIST list; /* list to keep track of all stmts */ - MYSQL *mysql; /* connection handle */ - MYSQL_BIND *params; /* input parameters */ - MYSQL_BIND *bind; /* output parameters */ - MYSQL_FIELD *fields; /* result set metadata */ - MYSQL_DATA result; /* cached result set */ - MYSQL_ROWS *data_cursor; /* current row in cached result */ - /* copy of mysql->affected_rows after statement execution */ - my_ulonglong affected_rows; - my_ulonglong insert_id; /* copy of mysql->insert_id */ - /* - mysql_stmt_fetch() calls this function to fetch one row (it's different - for buffered, unbuffered and cursor fetch). - */ - int (*read_row_func)(struct st_mysql_stmt *stmt, - unsigned char **row); - unsigned long stmt_id; /* Id for prepared statement */ - unsigned int last_errno; /* error code */ - unsigned int param_count; /* input parameter count */ - unsigned int field_count; /* number of columns in result set */ - enum enum_mysql_stmt_state state; /* statement state */ - char last_error[MYSQL_ERRMSG_SIZE]; /* error message */ - char sqlstate[SQLSTATE_LENGTH+1]; - /* Types of input parameters should be sent to server */ - my_bool send_types_to_server; - my_bool bind_param_done; /* input buffers were supplied */ - my_bool bind_result_done; /* output buffers were supplied */ - /* mysql_stmt_close() had to cancel this result */ - my_bool unbuffered_fetch_cancelled; - /* - Is set to true if we need to calculate field->max_length for - metadata fields when doing mysql_stmt_store_result. - */ - my_bool update_max_length; -} MYSQL_STMT; - -enum enum_stmt_attr_type -{ - /* - When doing mysql_stmt_store_result calculate max_length attribute - of statement metadata. This is to be consistent with the old API, - where this was done automatically. - In the new API we do that only by request because it slows down - mysql_stmt_store_result sufficiently. - */ - STMT_ATTR_UPDATE_MAX_LENGTH -}; - - -typedef struct st_mysql_methods -{ - my_bool (*read_query_result)(MYSQL *mysql); - my_bool (*advanced_command)(MYSQL *mysql, - enum enum_server_command command, - const char *header, - unsigned long header_length, - const char *arg, - unsigned long arg_length, - my_bool skip_check); - MYSQL_DATA *(*read_rows)(MYSQL *mysql,MYSQL_FIELD *mysql_fields, - unsigned int fields); - MYSQL_RES * (*use_result)(MYSQL *mysql); - void (*fetch_lengths)(unsigned long *to, - MYSQL_ROW column, unsigned int field_count); - void (*flush_use_result)(MYSQL *mysql); -#if !defined(MYSQL_SERVER) || defined(EMBEDDED_LIBRARY) - MYSQL_FIELD * (*list_fields)(MYSQL *mysql); - my_bool (*read_prepare_result)(MYSQL *mysql, MYSQL_STMT *stmt); - int (*stmt_execute)(MYSQL_STMT *stmt); - int (*read_binary_rows)(MYSQL_STMT *stmt); - int (*unbuffered_fetch)(MYSQL *mysql, char **row); - void (*free_embedded_thd)(MYSQL *mysql); - const char *(*read_statistics)(MYSQL *mysql); - my_bool (*next_result)(MYSQL *mysql); - int (*read_change_user_result)(MYSQL *mysql, char *buff, const char *passwd); -#endif -} MYSQL_METHODS; - - -MYSQL_STMT * STDCALL mysql_stmt_init(MYSQL *mysql); -int STDCALL mysql_stmt_prepare(MYSQL_STMT *stmt, const char *query, - unsigned long length); -int STDCALL mysql_stmt_execute(MYSQL_STMT *stmt); -int STDCALL mysql_stmt_fetch(MYSQL_STMT *stmt); -int STDCALL mysql_stmt_fetch_column(MYSQL_STMT *stmt, MYSQL_BIND *bind, - unsigned int column, - unsigned long offset); -int STDCALL mysql_stmt_store_result(MYSQL_STMT *stmt); -unsigned long STDCALL mysql_stmt_param_count(MYSQL_STMT * stmt); -my_bool STDCALL mysql_stmt_attr_set(MYSQL_STMT *stmt, - enum enum_stmt_attr_type attr_type, - const void *attr); -my_bool STDCALL mysql_stmt_attr_get(MYSQL_STMT *stmt, - enum enum_stmt_attr_type attr_type, - void *attr); -my_bool STDCALL mysql_stmt_bind_param(MYSQL_STMT * stmt, MYSQL_BIND * bnd); -my_bool STDCALL mysql_stmt_bind_result(MYSQL_STMT * stmt, MYSQL_BIND * bnd); -my_bool STDCALL mysql_stmt_close(MYSQL_STMT * stmt); -my_bool STDCALL mysql_stmt_reset(MYSQL_STMT * stmt); -my_bool STDCALL mysql_stmt_free_result(MYSQL_STMT *stmt); -my_bool STDCALL mysql_stmt_send_long_data(MYSQL_STMT *stmt, - unsigned int param_number, - const char *data, - unsigned long length); -MYSQL_RES *STDCALL mysql_stmt_result_metadata(MYSQL_STMT *stmt); -MYSQL_RES *STDCALL mysql_stmt_param_metadata(MYSQL_STMT *stmt); -unsigned int STDCALL mysql_stmt_errno(MYSQL_STMT * stmt); -const char *STDCALL mysql_stmt_error(MYSQL_STMT * stmt); -const char *STDCALL mysql_stmt_sqlstate(MYSQL_STMT * stmt); -MYSQL_ROW_OFFSET STDCALL mysql_stmt_row_seek(MYSQL_STMT *stmt, - MYSQL_ROW_OFFSET offset); -MYSQL_ROW_OFFSET STDCALL mysql_stmt_row_tell(MYSQL_STMT *stmt); -void STDCALL mysql_stmt_data_seek(MYSQL_STMT *stmt, my_ulonglong offset); -my_ulonglong STDCALL mysql_stmt_num_rows(MYSQL_STMT *stmt); -my_ulonglong STDCALL mysql_stmt_affected_rows(MYSQL_STMT *stmt); -my_ulonglong STDCALL mysql_stmt_insert_id(MYSQL_STMT *stmt); -unsigned int STDCALL mysql_stmt_field_count(MYSQL_STMT *stmt); - -my_bool STDCALL mysql_commit(MYSQL * mysql); -my_bool STDCALL mysql_rollback(MYSQL * mysql); -my_bool STDCALL mysql_autocommit(MYSQL * mysql, my_bool auto_mode); -my_bool STDCALL mysql_more_results(MYSQL *mysql); -int STDCALL mysql_next_result(MYSQL *mysql); -void STDCALL mysql_close(MYSQL *sock); - - -/* status return codes */ -#define MYSQL_NO_DATA 100 - -#define mysql_reload(mysql) mysql_refresh((mysql),REFRESH_GRANT) - -#ifdef USE_OLD_FUNCTIONS -MYSQL * STDCALL mysql_connect(MYSQL *mysql, const char *host, - const char *user, const char *passwd); -int STDCALL mysql_create_db(MYSQL *mysql, const char *DB); -int STDCALL mysql_drop_db(MYSQL *mysql, const char *DB); -#define mysql_reload(mysql) mysql_refresh((mysql),REFRESH_GRANT) -#endif -#define HAVE_MYSQL_REAL_CONNECT - -/* - The following functions are mainly exported because of mysqlbinlog; - They are not for general usage -*/ - -#define simple_command(mysql, command, arg, length, skip_check) \ - (*(mysql)->methods->advanced_command)(mysql, command, \ - NullS, 0, arg, length, skip_check) -unsigned long net_safe_read(MYSQL* mysql); - -#ifdef __NETWARE__ -#pragma pack(pop) /* restore alignment */ -#endif - -#ifdef __cplusplus -} -#endif - -#endif /* _mysql_h */ diff --git a/Src/Common/seh.cpp b/Src/Common/seh.cpp deleted file mode 100644 index 9c570e6..0000000 --- a/Src/Common/seh.cpp +++ /dev/null @@ -1,29 +0,0 @@ - -//#include -#include "seh.hpp" - -#ifdef __WIN32__ - -EXCEPTION_DISPOSITION __SEH_HANDLER::ExceptionRouter(PEXCEPTION_RECORD pRecord, - __SEH_EXCEPTION_REGISTRATION* pReg, - PCONTEXT pContext, - PEXCEPTION_RECORD pRecord2) -{ - return pReg->exthandler->ExceptionHandler(pRecord, pReg, pContext, pRecord2); -} - -EXCEPTION_DISPOSITION __SEH_HANDLER::ExceptionHandler(PEXCEPTION_RECORD pRecord, - __SEH_EXCEPTION_REGISTRATION* pReg, - PCONTEXT pContext, - PEXCEPTION_RECORD pRecord2) -{ - /*std::memcpy(&excContext, pContext, sizeof(_CONTEXT)); - std::memcpy(&excRecord, pRecord, sizeof(_EXCEPTION_RECORD));*/ - memcpy(&excContext, pContext, sizeof(_CONTEXT)); - memcpy(&excRecord, pRecord, sizeof(_EXCEPTION_RECORD)); - longjmp(context, 1); -} - -#endif - - diff --git a/Src/Common/seh.hpp b/Src/Common/seh.hpp deleted file mode 100644 index 2f9362a..0000000 --- a/Src/Common/seh.hpp +++ /dev/null @@ -1,96 +0,0 @@ - -#ifndef __FV_SEH_H__ -#define __FV_SEH_H__ - -#ifdef __WIN32__ -#include -#include -#endif - -#include -//#include - -//NAMESPACE_BEGIN(PU) -//NAMESPACE_BEGIN(SEH) - -#ifdef __WIN32__ - -class __SEH_HANDLER; - -typedef struct tag__SEH_EXCEPTION_REGISTRATION -{ - tag__SEH_EXCEPTION_REGISTRATION* prev; - PEXCEPTION_HANDLER handler; - __SEH_HANDLER* exthandler; -} __SEH_EXCEPTION_REGISTRATION; - - -class __SEH_HANDLER -{ -public: - __SEH_HANDLER() { } - static EXCEPTION_DISPOSITION ExceptionRouter(PEXCEPTION_RECORD pRecord, - __SEH_EXCEPTION_REGISTRATION* pReg, - PCONTEXT pContext, - PEXCEPTION_RECORD pRecord2); - - virtual EXCEPTION_DISPOSITION ExceptionHandler(PEXCEPTION_RECORD pRecord, - __SEH_EXCEPTION_REGISTRATION* pReg, - PCONTEXT pContext, - PEXCEPTION_RECORD pRecord2); - - jmp_buf context; - EXCEPTION_RECORD excRecord; - CONTEXT excContext; -}; - -#define __seh_try \ -{ \ - __SEH_EXCEPTION_REGISTRATION _lseh_er; \ - __SEH_HANDLER _lseh_handler; \ - \ - _lseh_er.handler = \ - reinterpret_cast(__SEH_HANDLER::ExceptionRouter); \ - _lseh_er.exthandler = &_lseh_handler; \ - asm volatile ("movl %%fs:0, %0" : "=r" (_lseh_er.prev)); \ - asm volatile ("movl %0, %%fs:0" : : "r" (&_lseh_er)); \ - int _lseh_setjmp_res = setjmp(_lseh_handler.context); \ - while(true) { \ - if(_lseh_setjmp_res != 0) { \ - break; \ - } \ - -#define __seh_finally \ - break; \ - } \ - while(true) { - - -#define __seh_except(rec, ctx) \ - break; \ - } \ - PEXCEPTION_RECORD rec = &_lseh_handler.excRecord; \ - PCONTEXT ctx = &_lseh_handler.excContext; \ - \ - asm volatile ("movl %0, %%fs:0" : : "r" (_lseh_er.prev)); \ - if(_lseh_setjmp_res != 0) - -#define __seh_end } - -#else - -#define __seh_try - -#define __seh_except(rec, ctx) if(false) { - -#define __seh_end } - -#define __seh_finally - -#endif - -//NAMESPACE_END(SEH) -//NAMESPACE_END(PU) - -#endif - diff --git a/Src/Common/sockets.h b/Src/Common/sockets.h index 9d975ab..8b74e03 100644 --- a/Src/Common/sockets.h +++ b/Src/Common/sockets.h @@ -22,33 +22,23 @@ #ifndef __ROSE_SOCKETS__ #define __ROSE_SOCKETS__ #define USEIFO -#ifdef _WIN32 - - #include - #define close closesocket - #ifdef FD_SETSIZE - #undef FD_SETSIZE - #endif - #define FD_SETSIZE 1024 -#else - #include - #include - #include - #include - #include - #include - #include - #include - #include - #define WSAGetLastError() errno - #define SOCKET int - #define INVALID_SOCKET -1 - #define SOCKET_ERROR -1 - #define PVOID void * - #define ioctlsocket ioctl - #define SOCKADDR struct sockaddr - #define closesocket close -#endif +#include +#include +#include +#include +#include +#include +#include +#include +#include +#define WSAGetLastError() errno +#define SOCKET int +#define INVALID_SOCKET -1 +#define SOCKET_ERROR -1 +#define PVOID void * +#define ioctlsocket ioctl +#define SOCKADDR struct sockaddr +#define closesocket close #include "mysql.h" #include @@ -63,7 +53,6 @@ #include #include -#ifndef _WIN32 // The entire codebase was written against Windows' clock(), which returns a // monotonic MILLISECOND counter (CLOCKS_PER_SEC == 1000) that closely tracks // wall-clock time for a normal single-threaded process. POSIX clock() is @@ -84,7 +73,6 @@ static inline long __rose_portable_clock() #undef CLOCKS_PER_SEC #define CLOCKS_PER_SEC 1000 #define clock() __rose_portable_clock() -#endif #include #include "pthread.h" #include @@ -93,9 +81,6 @@ static inline long __rose_portable_clock() #include "rosecrypt.hpp" #include "config.h" #include "database/database.h" -#ifdef _WIN32 -#pragma comment(lib, "Ws2_32.lib") -#endif // Just some defs for easier use typedef char SBYTE; typedef unsigned char BYTE; @@ -105,18 +90,11 @@ typedef int SDWORD; typedef unsigned int DWORD; typedef long long SQWORD; typedef unsigned long long QWORD; -#ifdef _WIN32 -typedef unsigned __int8 byte; -typedef unsigned __int16 word; -typedef unsigned __int32 dword; -typedef unsigned __int64 qword; -#else typedef unsigned char byte; typedef unsigned short word; typedef unsigned int dword; typedef unsigned long long qword; typedef unsigned int UINT; -#endif typedef char* strings; using std::cout; using std::endl; diff --git a/Src/Login Server/loginpackets.cpp b/Src/Login Server/loginpackets.cpp index 4bafc62..c0d648b 100644 --- a/Src/Login Server/loginpackets.cpp +++ b/Src/Login Server/loginpackets.cpp @@ -58,12 +58,7 @@ bool CLoginServer::pakUserLogin( CLoginClient* thisclient, CPacket* P ) if( mysql_num_rows( result ) == 1 ) { row = mysql_fetch_row(result); - int res = 0; - #ifdef _WIN32 - res = _stricmp( row[1], thisclient->password.c_str() ); - #else - res = strcasecmp( row[1], thisclient->password.c_str() ); - #endif + int res = strcasecmp( row[1], thisclient->password.c_str() ); if ( res == 0 ) { if(atoi(row[3])==1) diff --git a/Src/Login Server/main.cpp b/Src/Login Server/main.cpp index d44ec13..8b2d791 100644 --- a/Src/Login Server/main.cpp +++ b/Src/Login Server/main.cpp @@ -50,9 +50,6 @@ int main(int argc, char *argv[]) else { delete server; - #ifdef _WIN32 - system("pause"); - #endif return -1; } server->LoadEncryption (); diff --git a/Src/Login Server/signal.cpp b/Src/Login Server/signal.cpp index d106d9e..ef2be4c 100644 --- a/Src/Login Server/signal.cpp +++ b/Src/Login Server/signal.cpp @@ -38,9 +38,6 @@ void StartSignal( ) signal( SIGFPE, HandleSignal ); signal( SIGSEGV, HandleSignal ); signal( SIGTERM, HandleSignal ); - #ifdef _WIN32 - signal( SIGBREAK, HandleSignal ); - #endif signal( SIGABRT, HandleSignal ); } @@ -51,9 +48,6 @@ void StopSignal( ) signal( SIGFPE, 0 ); signal( SIGSEGV, 0 ); signal( SIGTERM, 0 ); - #ifdef _WIN32 - signal( SIGBREAK, 0 ); - #endif signal( SIGABRT, 0 ); } @@ -63,21 +57,13 @@ void HandleSignal( int num ) { case SIGINT:/* Interactive attention */ Log( MSG_ERROR, "Signal received: SIGINT" ); - #ifdef _WIN32 - Sleep(1000); - #else usleep(1000); - #endif raise(num); break; case SIGILL:/* Illegal instruction */ Log( MSG_ERROR, "Signal received: SIGILL, Server will be closed, Trying to save..." ); GServer->isActive = false; - #ifdef _WIN32 - Sleep(1000); - #else usleep(1000); - #endif raise(num); break; case SIGFPE:/* Floating point error */ @@ -88,24 +74,14 @@ void HandleSignal( int num ) case SIGSEGV:/* Segmentation violation */ Log( MSG_ERROR, "Signal received: SIGSEGV, Server will be closed, Trying to save..." ); GServer->isActive = false; - #ifdef _WIN32 - Sleep(1000); - #else usleep(1000); - #endif - raise(num); - break; - + raise(num); + break; + case SIGTERM:/* Termination request */ Log( MSG_INFO, "Signal received: SIGTERM, Server will be closed" ); GServer->isActive = false; break; - #ifdef _WIN32 - case SIGBREAK:/* Control-break */ - Log( MSG_INFO, "Signal received: SIGBREAK, Server will be closed" ); - GServer->isActive = false; - break; - #endif default: cout << "Unknown Signal Number: " << num << endl; raise(num); diff --git a/Src/World Server/MainProcess.cpp b/Src/World Server/MainProcess.cpp index d8cb19b..5ec888d 100644 --- a/Src/World Server/MainProcess.cpp +++ b/Src/World Server/MainProcess.cpp @@ -356,11 +356,7 @@ PVOID MapProcess( PVOID TS ) } pthread_mutex_unlock( &GServer->MapMutex ); pthread_mutex_unlock( &GServer->PlayerMutex ); - #ifdef _WIN32 - Sleep(GServer->Config.MapDelay); - #else usleep(GServer->Config.MapDelay * 1000); // MapDelay is in milliseconds; usleep wants microseconds - #endif } pthread_exit( NULL ); return 0; @@ -390,11 +386,7 @@ PVOID VisibilityProcess(PVOID TS) } pthread_mutex_unlock( &GServer->MapMutex ); pthread_mutex_unlock( &GServer->PlayerMutex ); - #ifdef _WIN32 - Sleep(GServer->Config.VisualDelay); - #else usleep(GServer->Config.VisualDelay * 1000); // VisualDelay is in milliseconds; usleep wants microseconds - #endif } pthread_exit(NULL); return 0; @@ -429,11 +421,7 @@ PVOID WorldProcess( PVOID TS ) } pthread_mutex_unlock( &GServer->MapMutex ); GServer->RefreshFairy( ); - #ifdef _WIN32 - Sleep(GServer->Config.WorldDelay); - #else usleep(GServer->Config.WorldDelay * 1000); // WorldDelay is in milliseconds; usleep wants microseconds - #endif } pthread_exit(NULL); return 0; @@ -443,11 +431,7 @@ PVOID WorldProcess( PVOID TS ) void ShutdownServer(PVOID TS) { int minutes = (int)(intptr_t)TS; - #ifdef _WIN32 - Sleep(minutes*60000); - #else sleep(minutes*60); // minutes*60000 was milliseconds; sleep() wants seconds - #endif Log( MSG_INFO, "Saving User Information... " ); GServer->DisconnectAll(); Log( MSG_INFO, "Waiting Process to ShutDown... " ); diff --git a/Src/World Server/Signal.cpp b/Src/World Server/Signal.cpp index 5313055..521c8f8 100644 --- a/Src/World Server/Signal.cpp +++ b/Src/World Server/Signal.cpp @@ -38,9 +38,6 @@ void StartSignal( ) signal( SIGFPE, HandleSignal ); signal( SIGSEGV, HandleSignal ); signal( SIGTERM, HandleSignal ); - #ifdef _WIN32 - signal( SIGBREAK, HandleSignal ); - #endif signal( SIGABRT, HandleSignal ); } @@ -51,9 +48,6 @@ void StopSignal( ) signal( SIGFPE, 0 ); signal( SIGSEGV, 0 ); signal( SIGTERM, 0 ); - #ifdef _WIN32 - signal( SIGBREAK, 0 ); - #endif signal( SIGABRT, 0 ); } @@ -63,22 +57,14 @@ void HandleSignal( int num ) { case SIGINT:/* Interactive attention */ Log( MSG_ERROR, "Signal received: SIGINT" ); - #ifdef _WIN32 - Sleep(1000); - #else usleep(1000); - #endif delete GServer; raise(num); break; case SIGILL:/* Illegal instruction */ Log( MSG_ERROR, "Signal received: SIGILL, Server will be closed, Trying to save..." ); GServer->DisconnectAll(); - #ifdef _WIN32 - Sleep(1000); - #else usleep(1000); - #endif delete GServer; raise(num); break; @@ -91,25 +77,15 @@ void HandleSignal( int num ) case SIGSEGV:/* Segmentation violation */ Log( MSG_ERROR, "Signal received: SIGSEGV, Server will be closed, Trying to save..." ); GServer->DisconnectAll(); - #ifdef _WIN32 - Sleep(1000); - #else usleep(1000); - #endif delete GServer; - raise(num); - break; - + raise(num); + break; + case SIGTERM:/* Termination request */ Log( MSG_INFO, "Signal received: SIGTERM, Server will be closed" ); pthread_create( &GServer->WorldThread[SHUTDOWN_THREAD], NULL, (void *(__cdecl *)(void *))ShutdownServer, (PVOID)0); break; - #ifdef _WIN32 - case SIGBREAK:/* Control-break */ - Log( MSG_INFO, "Signal received: SIGBREAK, Server will be closed" ); - pthread_create( &GServer->WorldThread[SHUTDOWN_THREAD], NULL, (void *(__cdecl *)(void *))ShutdownServer, (PVOID)0); - break; - #endif default: cout << "Unknown Signal Number: " << num << endl; raise(num); diff --git a/Src/World Server/main.cpp b/Src/World Server/main.cpp index 5562319..a7c8949 100644 --- a/Src/World Server/main.cpp +++ b/Src/World Server/main.cpp @@ -60,9 +60,6 @@ int main(int argc, char *argv[]) else { delete server; - #ifdef _WIN32 - system("pause"); - #endif return -1; } diff --git a/Src/World Server/quest/CIntStb.hpp b/Src/World Server/quest/CIntStb.hpp index d69f751..09b4056 100644 --- a/Src/World Server/quest/CIntStb.hpp +++ b/Src/World Server/quest/CIntStb.hpp @@ -13,11 +13,7 @@ public: unsigned dataoffset = 0; unsigned short fieldlen = 0; -#ifdef _WIN32 - if ( (fh = fopen( filename, "rb" )) == 0 ) { -#else if ( (fh = rose_fopen( filename, "rb" )) == 0 ) { -#endif Log( MSG_ERROR, "Could not load STB '%s'", filename ); return 1; }else{ diff --git a/Src/World Server/quest/CRoseFile.hpp b/Src/World Server/quest/CRoseFile.hpp index c8ecc6a..0bdc2c2 100644 --- a/Src/World Server/quest/CRoseFile.hpp +++ b/Src/World Server/quest/CRoseFile.hpp @@ -215,17 +215,8 @@ class CRoseFile { ftype = FT_BINARY; } - #ifndef CFILE_NODEPRECATE - if( fopen_s( &fh, fname, fasciimode ) == 0 ) + if( ( fh = rose_fopen( fname, fasciimode ) ) != NULL ) { - #else - #ifdef _WIN32 - if( ( fh = fopen( fname, fasciimode ) ) != NULL ) - #else - if( ( fh = rose_fopen( fname, fasciimode ) ) != NULL ) - #endif - { - #endif delete[] fasciimode; //Check if unicode or ascii if( ftype != FT_BINARY ) @@ -244,13 +235,7 @@ class CRoseFile DoError( FE_INTERNALERROR ); return false; } - #ifndef CFILE_NODEPRECATE - fopen_s( &fh, fname, fasciimode ); - #elif defined(_WIN32) - fh = fopen( fname, fasciimode ); - #else - fh = rose_fopen( fname, fasciimode ); - #endif + fh = rose_fopen( fname, fasciimode ); SetAbsPos( 2 ); ftype = FT_UNICODE; #else @@ -561,12 +546,7 @@ class CRoseFile CFILE_CHAR buf; wchar_t buffer; buffer = fgetwc( fh ); - #ifndef CFILE_NODEPRECATE - size_t tmp; - wcstombs_s( &tmp, &buf, (size_t)(sizeof(buf)), &buffer, 1 ); - #else - wcstombs( &buf, &buffer, 1 ); - #endif + wcstombs( &buf, &buffer, 1 ); return (CFILE_CHAR)buf; #else DoError( FE_UNICODENOTALLOWED ); @@ -610,12 +590,7 @@ class CRoseFile #ifndef CFILE_NOUNICODE wchar_t* buffer = new wchar_t[max_count]; fgetws( buffer, max_count, fh ); - #ifndef CFILE_NODEPRECATE - size_t tmp; - wcstombs_s( &tmp, buf->arr, (size_t)(buf->absSize()), buffer, max_count ); - #else - wcstombs( buf->arr, buffer, max_count ); - #endif + wcstombs( buf->arr, buffer, max_count ); return NULL; #else DoError( FE_UNICODENOTALLOWED ); @@ -861,12 +836,7 @@ class CRoseFile { #ifndef CFILE_NOUNICODE wchar_t buffer; - #ifndef CFILE_NODEPRECATE - size_t tmp; - mbstowcs_s( &tmp, &buffer, 1, (CFILE_CHAR*)(&chr), 1 ); - #else - mbstowcs( &buffer, (CFILE_CHAR*)(&chr), 1 ); - #endif + mbstowcs( &buffer, (CFILE_CHAR*)(&chr), 1 ); return (CFILE_SCHAR)(fputwc( buffer, fh )); #else DoError( FE_UNICODENOTALLOWED ); @@ -904,12 +874,7 @@ class CRoseFile { #ifndef CFILE_NOUNICODE wchar_t* buffer = new wchar_t[ (size_t)(str->size()) ]; - #ifndef CFILE_NODEPRECATE - size_t tmp; - mbstowcs_s( &tmp, buffer, (size_t)(str->size()), str->arr, (size_t)(str->size()) ); - #else - mbstowcs( buffer, str->arr, str->size() ); - #endif + mbstowcs( buffer, str->arr, str->size() ); return (fputws( buffer, fh )!=EOF)?(true):(false); #else DoError( FE_UNICODENOTALLOWED ); diff --git a/Src/World Server/worldpackets.cpp b/Src/World Server/worldpackets.cpp index db0cdd6..c7494a3 100644 --- a/Src/World Server/worldpackets.cpp +++ b/Src/World Server/worldpackets.cpp @@ -2052,13 +2052,6 @@ bool CWorldServer::pakNPCBuy ( CPlayer* thisclient, CPacket* P ) thisclient->client->SendPacket( &pak ); thisclient->saveinventory(); return true; - //} - //__seh_except(info, context) - //{ - // Log( MSG_ERROR, "Error in pakNPCBuy"); - // return false; - //} - //__seh_end } diff --git a/Src/World Server/worldserver.cpp b/Src/World Server/worldserver.cpp index 224ac8d..c30d02e 100644 --- a/Src/World Server/worldserver.cpp +++ b/Src/World Server/worldserver.cpp @@ -360,80 +360,48 @@ void CWorldServer::ServerLoop( ) if ( activity == 0 ) { pthread_mutex_unlock( &PlayerMutex ); - #ifdef _WIN32 - Sleep(1); - #else usleep(1); - #endif continue; } if ( activity < 0 && errno != EINTR ) { - #ifdef _WIN32 - Log( MSG_ERROR, "Select command failed. Error #%i", WSAGetLastError() ); - #else Log( MSG_ERROR, "Select command failed. Error #%i", errno ); - #endif isActive = false; } if ( FD_ISSET( sckISCII, &fds ) ) { int clientinfolen = sizeof( sockaddr_in ); - #ifdef _WIN32 - NewSocket = accept( sckISCII, (sockaddr*)&ClientInfo, (int*)&clientinfolen ); - #else NewSocket = accept( sckISCII, (sockaddr*)&ClientInfo, (socklen_t*)&clientinfolen ); - #endif // TODO: check if server is full if (NewSocket != INVALID_SOCKET) AddUser( NewSocket, &ClientInfo, true); else { - #ifdef _WIN32 - Log( MSG_ERROR, "Error accepting socket: %i", WSAGetLastError() ); - #else Log( MSG_ERROR, "Error accepting socket: %i", errno ); - #endif } } } if ( activity < 0 && errno != EINTR ) { - #ifdef _WIN32 - Log( MSG_ERROR, "Select command failed. Error #%i", WSAGetLastError() ); - #else Log( MSG_ERROR, "Select command failed. Error #%i", errno ); - #endif isActive = false; } if ( FD_ISSET( sock, &fds ) ) { int clientinfolen = sizeof( sockaddr_in ); - #ifdef _WIN32 - NewSocket = accept( sock, (sockaddr*)&ClientInfo, (int*)&clientinfolen ); - #else NewSocket = accept( sock, (sockaddr*)&ClientInfo, (socklen_t*)&clientinfolen ); - #endif // TODO: check if server is full if (NewSocket != INVALID_SOCKET) AddUser( NewSocket, &ClientInfo, false); else { - #ifdef _WIN32 - Log( MSG_ERROR, "Error accepting socket: %i", WSAGetLastError() ); - #else Log( MSG_ERROR, "Error accepting socket: %i", errno ); - #endif } } if(!Config.usethreads) HandleClients( &fds ); pthread_mutex_unlock( &PlayerMutex ); - #ifdef _WIN32 - Sleep(1); - #else usleep(1); - #endif } while( isActive ); } diff --git a/database sql files/gm_account.sql b/database sql files/gm_account.sql new file mode 100644 index 0000000..c45ea3d --- /dev/null +++ b/database sql files/gm_account.sql @@ -0,0 +1,9 @@ +-- Default GM account so a fresh deploy has something to log into the +-- web admin panel and the game with. Change the password immediately on +-- any server that isn't purely local/dev -- see README.md. +-- +-- username: gmadmin +-- password: changeme (stored as md5, matching Src/Login Server/loginpackets.cpp +-- and webadmin/app.py's hash_password()) +INSERT INTO `accounts` (`username`, `password`, `accesslevel`, `lastlogin`, `logtime`) +VALUES ('gmadmin', MD5('changeme'), 900, '', 0); diff --git a/docker-compose.yml b/docker-compose.yml index 7562978..0a765db 100644 --- a/docker-compose.yml +++ b/docker-compose.yml @@ -42,7 +42,7 @@ services: MYSQL_USER: ${DB_USER:-rose} MYSQL_PASSWORD: ${DB_PASSWORD:-change_me} volumes: - - db-data:/var/lib/mysql + - "./docker/data/mysql:/var/lib/mysql" - "./database sql files:/docker-entrypoint-initdb.d:ro" healthcheck: test: ["CMD", "healthcheck.sh", "--connect", "--innodb_initialized"] @@ -118,6 +118,5 @@ services: condition: service_healthy volumes: - db-data: logs: clanmark: