Merge branch 'main' into blockcountry-cleanup

This commit is contained in:
d1str4ught
2025-09-26 00:01:22 +02:00
committed by GitHub
30 changed files with 18 additions and 1278 deletions

View File

@@ -97,7 +97,6 @@ enum
HEADER_GD_AUTH_LOGIN = 100,
HEADER_GD_LOGIN_BY_KEY = 101,
HEADER_GD_VCARD = 105,
HEADER_GD_MALL_LOAD = 107,
HEADER_GD_MYSHOP_PRICELIST_UPDATE = 108, ///< 가격정보 갱신 요청
@@ -220,8 +219,6 @@ enum
HEADER_DG_CHANGE_CHARACTER_PRIV = 127,
HEADER_DG_VCARD = 131,
HEADER_DG_CREATE_OBJECT = 140,
HEADER_DG_DELETE_OBJECT = 141,
HEADER_DG_UPDATE_LAND = 142,
@@ -1153,15 +1150,6 @@ typedef struct SPacketGDHammerOfTor
uint32_t delay;
} TPacketGDHammerOfTor;
typedef struct SPacketGDVCard
{
uint32_t dwID;
char szSellCharacter[CHARACTER_NAME_MAX_LEN + 1];
char szSellAccount[LOGIN_MAX_LEN + 1];
char szBuyCharacter[CHARACTER_NAME_MAX_LEN + 1];
char szBuyAccount[LOGIN_MAX_LEN + 1];
} TPacketGDVCard;
typedef struct SGuildReserve
{
uint32_t dwID;

View File

@@ -1872,28 +1872,6 @@ void CClientManager::UpdateLand(DWORD * pdw)
ForwardPacket(HEADER_DG_UPDATE_LAND, p, sizeof(building::TLand));
}
void CClientManager::VCard(TPacketGDVCard * p)
{
sys_log(0, "VCARD: %u %s %s %s %s",
p->dwID, p->szSellCharacter, p->szSellAccount, p->szBuyCharacter, p->szBuyAccount);
m_queue_vcard.push(*p);
}
void CClientManager::VCardProcess()
{
if (!m_pkAuthPeer)
return;
while (!m_queue_vcard.empty())
{
m_pkAuthPeer->EncodeHeader(HEADER_DG_VCARD, 0, sizeof(TPacketGDVCard));
m_pkAuthPeer->Encode(&m_queue_vcard.front(), sizeof(TPacketGDVCard));
m_queue_vcard.pop();
}
}
// BLOCK_CHAT
void CClientManager::BlockChat(TPacketBlockChat* p)
{
@@ -2367,10 +2345,6 @@ void CClientManager::ProcessPackets(CPeer * peer)
UpdateLand((DWORD *) data);
break;
case HEADER_GD_VCARD:
VCard((TPacketGDVCard *) data);
break;
case HEADER_GD_MARRIAGE_ADD:
MarriageAdd((TPacketMarriageAdd *) data);
break;
@@ -2954,7 +2928,6 @@ int CClientManager::Process()
}
#endif
VCardProcess();
return 1;
}

View File

@@ -370,10 +370,6 @@ class CClientManager : public CNetBase, public singleton<CClientManager>
void DeleteObject(DWORD dwID);
void UpdateLand(DWORD * pdw);
// VCard
void VCard(TPacketGDVCard * p);
void VCardProcess();
// BLOCK_CHAT
void BlockChat(TPacketBlockChat * p);
// END_OF_BLOCK_CHAT
@@ -425,8 +421,6 @@ class CClientManager : public CNetBase, public singleton<CClientManager>
std::vector<building::TObjectProto> m_vec_kObjectProto;
std::map<DWORD, building::TObject *> m_map_pkObjectTable;
std::queue<TPacketGDVCard> m_queue_vcard;
bool m_bShutdowned;
TPlayerTableCacheMap m_map_playerCache; // 플레이어 id가 key

View File

@@ -80,24 +80,6 @@ bool CClientManager::FindLogonAccount(const char * c_pszLogin)
void CClientManager::QUERY_LOGIN_BY_KEY(CPeer * pkPeer, DWORD dwHandle, TPacketGDLoginByKey * p)
{
#ifdef ENABLE_LIMIT_TIME
static int s_updateCount = 0;
static int s_curTime = time(0);
if (s_updateCount > 100)
{
s_curTime = time(0);
s_updateCount = 0;
}
++s_updateCount;
if (s_curTime >= GLOBAL_LIMIT_TIME)
{
sys_err("Server life time expired.");
exit(0);
return;
}
#endif
CLoginData * pkLoginData = GetLoginData(p->dwLoginKey);
char szLogin[LOGIN_MAX_LEN + 1];
trim_and_lower(p->szLogin, szLogin, sizeof(szLogin));

View File

@@ -1,138 +0,0 @@
#include "stdafx.h"
#ifdef OS_FREEBSD
#include "FileMonitor_FreeBSD.h"
#include "libthecore/log.h"
#define INVALID_KERNEL_EVENT -1
FileMonitorFreeBSD::FileMonitorFreeBSD()
{
m_KernelEventQueue = INVALID_KERNEL_EVENT;
}
FileMonitorFreeBSD::~FileMonitorFreeBSD()
{
if( m_KernelEventQueue != INVALID_KERNEL_EVENT )
{
close ( m_KernelEventQueue );
m_KernelEventQueue = INVALID_KERNEL_EVENT;
}
TMonitorFileHashMap::iterator it;
for( it = m_FileLists.begin(); it != m_FileLists.end(); ++it )
{
close(it->second.fhMonitor);
}
m_FileLists.clear();
m_MonitoredEventLists.clear();
m_TriggeredEventLists.clear();
}
void FileMonitorFreeBSD::Update(DWORD dwPulses)
{
if( m_KernelEventQueue == INVALID_KERNEL_EVENT || m_FileLists.size() == 0 )
return;
int nEvent = kevent(m_KernelEventQueue, &m_TriggeredEventLists[0], (int)m_TriggeredEventLists.size(), &m_MonitoredEventLists[0], (int)m_MonitoredEventLists.size(), NULL );
if( nEvent == INVALID_KERNEL_EVENT )
{
return;
}
else if( nEvent > 0 )
{
for( int i = 0; i < nEvent; ++i )
{
int nEventFlags = m_MonitoredEventLists[i].flags;
eFileUpdatedOptions eUpdateOption = e_FileUpdate_None;
if (nEventFlags & EV_ERROR)
eUpdateOption = e_FileUpdate_Error;
else if (nEventFlags & NOTE_DELETE)
eUpdateOption = e_FileUpdate_Deleted;
else if (nEventFlags & NOTE_EXTEND || nEventFlags & NOTE_WRITE)
eUpdateOption = e_FileUpdate_Modified;
else if (nEventFlags & NOTE_ATTRIB)
eUpdateOption = e_FileUpdate_AttrModified;
else if (nEventFlags & NOTE_LINK)
eUpdateOption = e_FileUpdate_Linked;
else if (nEventFlags & NOTE_RENAME)
eUpdateOption = e_FileUpdate_Renamed;
else if (nEventFlags & NOTE_REVOKE)
eUpdateOption = e_FileUpdate_Revoked;
if( eUpdateOption != e_FileUpdate_None )
{
TMonitorFileHashMap::iterator it;
for( it = m_FileLists.begin(); it != m_FileLists.end(); ++it )
{
FileIOContext_FreeBSD& context = it->second;
if( context.idxToEventList == i )
{
std::string strModifedFileName = it->first;
context.pListenFunc( strModifedFileName, eUpdateOption );
break;
}
}
}
}
}
}
void FileMonitorFreeBSD::AddWatch(const std::string& strFileName, PFN_FileChangeListener pListenerFunc)
{
int iFileHandle = -1;
if( (iFileHandle = open(strFileName.c_str(), O_RDONLY)) == -1)
{
sys_err("FileMonitorFreeBSD:AddWatch : can`t open file(%s).\n", strFileName.c_str());
return;
}
//create kqueue if not exists
if( m_KernelEventQueue == INVALID_KERNEL_EVENT )
m_KernelEventQueue = kqueue();
if( m_KernelEventQueue == INVALID_KERNEL_EVENT )
{
sys_err("FileMonitorFreeBSD:AddWatch : failed to create kqueue.\n");
return;
}
TMonitorFileHashMap::iterator it = m_FileLists.find( strFileName );
if( it != m_FileLists.end() )
{
sys_log(0, "FileMonitorFreeBSD:AddWatch : trying to add duplicated watch on file(%s).\n", strFileName.c_str() );
return;
}
//set file context
FileIOContext_FreeBSD context;
{
context.fhMonitor = iFileHandle;
context.idxToEventList = (int)m_MonitoredEventLists.size();
context.pListenFunc = pListenerFunc;
}
m_FileLists[strFileName] = context;
//set events
struct kevent kTriggerEvent, kMonitorEvent;
EV_SET(&kTriggerEvent, iFileHandle, EVFILT_VNODE,
EV_ADD | EV_ENABLE | EV_ONESHOT,
NOTE_DELETE | NOTE_WRITE | NOTE_EXTEND | NOTE_ATTRIB | NOTE_LINK | NOTE_RENAME | NOTE_REVOKE,
0, 0);
m_TriggeredEventLists.push_back( kTriggerEvent );
m_MonitoredEventLists.push_back( kMonitorEvent );
}
#endif

View File

@@ -1,44 +0,0 @@
#pragma once
#ifdef OS_FREEBSD
#include "IFileMonitor.h"
#include <unistd.h>
#include <sys/event.h>
#include <sys/types.h>
#include <sys/signal.h>
#include <sys/time.h>
struct FileIOContext_FreeBSD
{
int fhMonitor;
int idxToEventList; // evtTrigger & evtMonitor index should be same
PFN_FileChangeListener pListenFunc;
};
class FileMonitorFreeBSD : public IFileMonitor
{
private:
FileMonitorFreeBSD(); //hidden
public:
virtual ~FileMonitorFreeBSD();
void AddWatch (const std::string& strFileName, PFN_FileChangeListener pListenerFunc);
void Update (DWORD dwPulses);
static FileMonitorFreeBSD& Instance()
{
static FileMonitorFreeBSD theMonitor;
return theMonitor;
}
private:
typedef std::unordered_map<std::string, FileIOContext_FreeBSD> TMonitorFileHashMap;
typedef std::vector<struct kevent> TEventList;
TMonitorFileHashMap m_FileLists;
TEventList m_MonitoredEventLists;
TEventList m_TriggeredEventLists;
int m_KernelEventQueue;
};
#endif

View File

@@ -1,30 +0,0 @@
#ifndef IFILEMONITOR_INCLUDED
#define IFILEMONITOR_INCLUDED
//#include <boost/function.hpp>
#include <unordered_map>
enum eFileUpdatedOptions
{
e_FileUpdate_None = -1,
e_FileUpdate_Error,
e_FileUpdate_Deleted,
e_FileUpdate_Modified,
e_FileUpdate_AttrModified,
e_FileUpdate_Linked,
e_FileUpdate_Renamed,
e_FileUpdate_Revoked,
};
// TODO : in FreeBSD boost function doesn`t work with boost bind
// so currently we only support for static function ptr only
//typedef boost::function< void ( const std::string&, eFileUpdatedOptions ) > PFN_FileChangeListener;
typedef void (* PFN_FileChangeListener )(const std::string&, eFileUpdatedOptions);
struct IFileMonitor
{
virtual void Update (DWORD dwPulses) = 0;
virtual void AddWatch (const std::string& strFileName, PFN_FileChangeListener pListenerFunc) = 0;
};
#endif // IFILEMONITOR_INCLUDED

View File

@@ -1,178 +0,0 @@
/* vi: set sw=4 ts=8 cino=g0,\:0 : */
/*********************************************************************
* date : 2010.4.7
* file : auth_brazil.c
* author : mhh
* description :
*/
#include "stdafx.h"
#ifndef OS_WINDOWS
#include <unistd.h>
#include <stdint.h>
#endif
#include <stdio.h>
#include <string.h>
#include "libthecore/xmd5.h"
#include "auth_brazil.h"
static const char* FN_md5(const char *src)
{
static char s_buffer[512];
memset(s_buffer, 0x00, sizeof(s_buffer));
unsigned char digest[16] = {0};
MD5_CTX md5;
MD5Init(&md5);
MD5Update(&md5, (const unsigned char*) src, strlen(src));
MD5Final(digest, &md5);
int offset = 0;
for (int i=0; i<16; ++i) {
offset += sprintf(s_buffer + offset, "%02x", digest[i]);
}
return s_buffer;
}
static int FN_make_request(const char *login, const char *password, /*out*/ char *dst, int dst_size)
{
int len = snprintf(dst, dst_size,
// "GET /metin2/game_auth.php?ID=%s&PW=%s HTTP/1.1\r\n"
"GET /metin2/?ID=%s&PW=%s HTTP/1.1\r\n"
"Host: auth.ongame.com.br\r\n"
"Connection: Close\r\n\r\n",
login, FN_md5(password));
return len;
}
static int FN_parse_reply(char *reply)
{
char buffer[2048];
strlcpy(buffer, reply, sizeof(buffer));
const char *delim = "\r\n";
char *last = 0;
char *v = strtok_r(buffer, delim, &last);
char *result = 0;
while (v)
{
result = v;
v = strtok_r(NULL, delim, &last);
}
if (result)
{
if (0 == strcasecmp("true", result))
return AUTH_BRAZIL_SUCC;
else if (0 == strcasecmp("false", result))
return AUTH_BRAZIL_WRONGPWD;
else if (0 == strcasecmp("unknown", result))
return AUTH_BRAZIL_NOID;
else if (0 == strcasecmp("flash", result))
return AUTH_BRAZIL_FLASHUSER;
}
return AUTH_BRAZIL_SERVER_ERR;
}
extern void socket_timeout(socket_t s, long sec, long usec);
int auth_brazil(const char *login, const char *pwd)
{
const char *host = "auth.ongame.com.br";
int port = 80;
socket_t fd = socket_connect(host, port);
if (fd < 0)
{
sys_err("[AUTH_BRAZIL] : could not connect to gsp server(%s)", host);
return AUTH_BRAZIL_SERVER_ERR;
}
socket_block(fd);
socket_timeout(fd, 3, 0);
// send request
{
char request[512];
int len = FN_make_request(login, pwd, request, sizeof(request));
#ifndef OS_WINDOWS
if (write(fd, request, len) < 0)
#else
if (_write(fd, request, len) < 0)
#endif
{
sys_err("[AUTH_BRAZIL] : could not send auth-request (%s)", login);
close(fd);
return AUTH_BRAZIL_SERVER_ERR;
}
}
// read reply
{
char reply[1024] = {0};
int len = read(fd, reply, sizeof(reply));
close(fd);
if (len <= 0)
{
sys_err("[AUTH_BRAZIL] : could not recv auth-reply (%s)", login);
return AUTH_BRAZIL_SERVER_ERR;
}
// 응답받은 경우에만 query count를 늘린다.
auth_brazil_inc_query_count();
return FN_parse_reply(reply);
}
}
static int s_query_count = 0;
int auth_brazil_inc_query_count()
{
return ++s_query_count;
}
void auth_brazil_log()
{
FILE *fp = 0;
// open and try backup
{
fp = fopen("AUTH_COUNT.log", "a");
if (0 == fp)
return;
struct stat sb;
fstat(fileno(fp), &sb);
if (sb.st_size > 1024 * 1024)
{
fclose(fp);
rename("AUTH_COUNT.log", "AUTH_COUNT.log.old");
fp = fopen("AUTH_COUNT.log", "a");
}
}
// write log
{
fprintf(fp, "%d\n", s_query_count);
fclose(fp);
}
// reset query count
s_query_count = 0;
}

View File

@@ -1,23 +0,0 @@
/* vi: set sw=4 ts=8 cino=g0,\:0 : */
/*********************************************************************
* date : 2010.4.7
* file : auth_brazil.h
* author : mhh
* description :
*/
#ifndef __auth_brazil_h_1270647899__
#define __auth_brazil_h_1270647899__
#define AUTH_BRAZIL_SERVER_ERR 0
#define AUTH_BRAZIL_SUCC 1
#define AUTH_BRAZIL_NOID 2
#define AUTH_BRAZIL_WRONGPWD 3
#define AUTH_BRAZIL_FLASHUSER 4
int auth_brazil(const char *login, const char *pwd);
int auth_brazil_inc_query_count();
void auth_brazil_log();
#endif // __auth_brazil_h_1270647899__

View File

@@ -3744,11 +3744,6 @@ bool CHARACTER::UseItemEx(LPITEM item, TItemPos DestCell)
item->SetCount(item->GetCount()-1);
break;
case 90008: // VCARD
case 90009: // VCARD
VCardUse(this, this, item);
break;
case ITEM_ELK_VNUM: // 돈꾸러미
{
int iGold = item->GetSocket(0);

View File

@@ -692,15 +692,6 @@ void CHARACTER_MANAGER::Update(int iPulse)
for (itertype(m_map_dwMobKillCount) it = m_map_dwMobKillCount.begin(); it != m_map_dwMobKillCount.end(); ++it)
DBManager::instance().SendMoneyLog(MONEY_LOG_MONSTER_KILL, it->first, it->second);
#ifdef _USE_SERVER_KEY_
extern bool Metin2Server_IsInvalid();
extern bool g_bShutdown;
if (Metin2Server_IsInvalid())
{
g_bShutdown = true;
}
#endif
m_map_dwMobKillCount.clear();
}

View File

@@ -12,7 +12,6 @@
#include "item_manager.h"
#include "p2p.h"
#include "char.h"
#include "ip_ban.h"
#include "war_map.h"
#include "locale_service.h"
#include "config.h"
@@ -827,8 +826,6 @@ void config_init(const string& st_localeServiceName)
g_bAuthServer = true;
LoadBanIP("BANIP");
if (!strcasecmp(szIP, "master"))
fprintf(stdout, "AUTH_SERVER: I am the master\n");
else

View File

@@ -17,7 +17,6 @@
#include "login_data.h"
#include "locale_service.h"
#include "spam.h"
#include "auth_brazil.h"
extern std::string g_stBlockDate;
@@ -634,29 +633,6 @@ void DBManager::SendMoneyLog(BYTE type, DWORD vnum, int gold)
db_clientdesc->DBPacket(HEADER_GD_MONEY_LOG, 0, &p, sizeof(p));
}
void VCardUse(LPCHARACTER CardOwner, LPCHARACTER CardTaker, LPITEM item)
{
TPacketGDVCard p;
p.dwID = item->GetSocket(0);
strlcpy(p.szSellCharacter, CardOwner->GetName(), sizeof(p.szSellCharacter));
strlcpy(p.szSellAccount, CardOwner->GetDesc()->GetAccountTable().login, sizeof(p.szSellAccount));
strlcpy(p.szBuyCharacter, CardTaker->GetName(), sizeof(p.szBuyCharacter));
strlcpy(p.szBuyAccount, CardTaker->GetDesc()->GetAccountTable().login, sizeof(p.szBuyAccount));
db_clientdesc->DBPacket(HEADER_GD_VCARD, 0, &p, sizeof(TPacketGDVCard));
CardTaker->ChatPacket(CHAT_TYPE_INFO, LC_TEXT("%d분의 결제시간이 추가 되었습니다. (결제번호 %d)"), item->GetSocket(1) / 60, item->GetSocket(0));
LogManager::instance().VCardLog(p.dwID, CardTaker->GetX(), CardTaker->GetY(), g_stHostname.c_str(),
CardOwner->GetName(), CardOwner->GetDesc()->GetHostName(),
CardTaker->GetName(), CardTaker->GetDesc()->GetHostName());
ITEM_MANAGER::instance().RemoveItem(item);
sys_log(0, "VCARD_TAKE: %u %s -> %s", p.dwID, CardOwner->GetName(), CardTaker->GetName());
}
size_t DBManager::EscapeString(char* dst, size_t dstSize, const char *src, size_t srcSize)
{
return m_sql_direct.EscapeString(dst, dstSize, src, srcSize);

View File

@@ -158,9 +158,6 @@ typedef struct SHighscoreRegisterQueryInfo
bool bOrder;
} THighscoreRegisterQueryInfo;
extern void VCardUse(LPCHARACTER CardOwner, LPCHARACTER CardTaker, LPITEM item);
// ACCOUNT_DB
class AccountDB : public singleton<AccountDB>
{

View File

@@ -192,16 +192,6 @@ EVENTFUNC(ping_event)
desc->SetPong(false);
}
#ifdef ENABLE_LIMIT_TIME
if ((unsigned)get_global_time() >= GLOBAL_LIMIT_TIME)
{
extern void ClearAdminPages();
ClearAdminPages();
extern g_bShutdown;
g_bShutdown = true;
}
#endif
desc->SendHandshake(get_dword_time(), 0);
return (ping_event_second_cycle);

View File

@@ -10,7 +10,6 @@
#include <pcg_random.hpp>
#define SEQUENCE_SEED 0
#define MAX_ALLOW_USER 4096
//#define MAX_INPUT_LEN 2048
#define MAX_INPUT_LEN 65536

View File

@@ -10,48 +10,9 @@
#include "protocol.h"
#include "messenger_manager.h"
#include "p2p.h"
#include "ip_ban.h"
#include "dev_log.h"
#include "ClientPackageCryptInfo.h"
struct valid_ip
{
const char * ip;
BYTE network;
BYTE mask;
};
static struct valid_ip admin_ip[] =
{
{ "210.123.10", 128, 128 },
{ "\n", 0, 0 }
};
int IsValidIP(struct valid_ip* ip_table, const char *host)
{
int i, j;
char ip_addr[256];
for (i = 0; *(ip_table + i)->ip != '\n'; ++i)
{
j = 255 - (ip_table + i)->mask;
do
{
snprintf(ip_addr, sizeof(ip_addr), "%s.%d", (ip_table + i)->ip, (ip_table + i)->network + j);
if (!strcmp(ip_addr, host))
return TRUE;
if (!j)
break;
}
while (j--);
}
return FALSE;
}
DESC_MANAGER::DESC_MANAGER() : m_bDestroyed(false)
{
Initialize();
@@ -158,26 +119,6 @@ LPDESC DESC_MANAGER::AcceptDesc(LPFDWATCH fdw, socket_t s)
strlcpy(host, inet_ntoa(peer.sin_addr), sizeof(host));
if (g_bAuthServer)
{
if (IsBanIP(peer.sin_addr))
{
sys_log(0, "connection from %s was banned.", host);
socket_close(desc);
return NULL;
}
}
if (!IsValidIP(admin_ip, host)) // admin_ip 에 등록된 IP 는 최대 사용자 수에 구애받지 않는다.
{
if (m_iSocketsConnected >= MAX_ALLOW_USER)
{
sys_err("max connection reached. MAX_ALLOW_USER = %d", MAX_ALLOW_USER);
socket_close(desc);
return NULL;
}
}
newd = M2_NEW DESC;
crc_t handshake = CreateHandshake();

View File

@@ -5,7 +5,6 @@
#include "common/stl.h"
#include "common/length.h"
#include "IFileMonitor.h"
class CLoginKey;
class CClientPackageCryptInfo;

View File

@@ -439,12 +439,6 @@ bool CExchange::Done()
assert(empty_pos >= 0);
if (item->GetVnum() == 90008 || item->GetVnum() == 90009) // VCARD
{
VCardUse(m_pOwner, victim, item);
continue;
}
m_pOwner->SyncQuickslot(QUICKSLOT_TYPE_ITEM, item->GetCell(), 255);
item->RemoveFromCharacter();

View File

@@ -18,10 +18,6 @@
#include "castle.h"
#include "dev_log.h"
#ifndef OS_WINDOWS
#include "limit_time.h"
#endif
extern time_t get_global_time();
bool IsEmptyAdminPage()
@@ -39,14 +35,6 @@ bool IsAdminPage(const char * ip)
return 0;
}
void ClearAdminPages()
{
for (size_t n = 0; n < g_stAdminPageIP.size(); ++n)
g_stAdminPageIP[n].clear();
g_stAdminPageIP.clear();
}
CInputProcessor::CInputProcessor() : m_pPacketInfo(NULL), m_iBufferLeft(0)
{
if (!m_pPacketInfo)
@@ -174,17 +162,6 @@ bool CInputProcessor::Process(LPDESC lpDesc, const void * c_pvOrig, int iBytes,
void CInputProcessor::Pong(LPDESC d)
{
d->SetPong(true);
extern bool Metin2Server_IsInvalid();
#ifdef ENABLE_LIMIT_TIME
if (Metin2Server_IsInvalid())
{
extern bool g_bShutdown;
g_bShutdown = true;
ClearAdminPages();
}
#endif
}
void CInputProcessor::Handshake(LPDESC d, const char * c_pData)

View File

@@ -243,8 +243,6 @@ protected:
void SetEventFlag(const char* c_pData);
void VCard(const char * c_pData);
void CreateObject(const char * c_pData);
void DeleteObject(const char * c_pData);
void UpdateLand(const char * c_pData);

View File

@@ -7,13 +7,8 @@
#include "protocol.h"
#include "matrix_card.h"
#include "locale_service.h"
#include "auth_brazil.h"
#include "db.h"
#ifndef OS_WINDOWS
#include "limit_time.h"
#endif
extern time_t get_global_time();
bool FN_IS_VALID_LOGIN_STRING(const char *str)
@@ -107,17 +102,6 @@ CInputAuth::CInputAuth()
void CInputAuth::Login(LPDESC d, const char * c_pData)
{
extern bool Metin2Server_IsInvalid();
#ifdef ENABLE_LIMIT_TIME
if (Metin2Server_IsInvalid())
{
extern void ClearAdminPages();
ClearAdminPages();
exit(1);
return;
}
#endif
TPacketCGLogin3 * pinfo = (TPacketCGLogin3 *) c_pData;
if (!g_bAuthServer)
@@ -170,26 +154,6 @@ void CInputAuth::Login(LPDESC d, const char * c_pData)
sys_log(0, "InputAuth::Login : key %u:0x%x login %s", dwKey, dwPanamaKey, login);
// BRAZIL_AUTH
if (LC_IsBrazil() && !test_server)
{
int result = auth_brazil(login, passwd);
switch (result)
{
case AUTH_BRAZIL_SERVER_ERR:
case AUTH_BRAZIL_NOID:
LoginFailure(d, "NOID");
return;
case AUTH_BRAZIL_WRONGPWD:
LoginFailure(d, "WRONGPWD");
return;
case AUTH_BRAZIL_FLASHUSER:
LoginFailure(d, "FLASH");
return;
}
}
TPacketCGLogin3 * p = M2_NEW TPacketCGLogin3;
thecore_memcpy(p, pinfo, sizeof(TPacketCGLogin3));

View File

@@ -427,8 +427,7 @@ void CInputDB::PlayerLoad(LPDESC d, const char * data)
if (LC_IsYMIR() || LC_IsKorea() || LC_IsBrazil() || LC_IsJapan())
{
LogManager::instance().LoginLog(true,
ch->GetDesc()->GetAccountTable().id, ch->GetPlayerID(), ch->GetLevel(), ch->GetJob(), ch->GetRealPoint(POINT_PLAYTIME));
LogManager::instance().LoginLog(true, ch->GetDesc()->GetAccountTable().id, ch->GetPlayerID(), ch->GetLevel(), ch->GetJob(), ch->GetRealPoint(POINT_PLAYTIME));
}
}
@@ -1843,61 +1842,6 @@ void CInputDB::Notice(const char * c_pData)
SendNotice(szBuf);
}
void CInputDB::VCard(const char * c_pData)
{
TPacketGDVCard * p = (TPacketGDVCard *) c_pData;
sys_log(0, "VCARD: %u %s %s %s %s", p->dwID, p->szSellCharacter, p->szSellAccount, p->szBuyCharacter, p->szBuyAccount);
std::unique_ptr<SQLMsg> pmsg(DBManager::instance().DirectQuery("SELECT sell_account, buy_account, time FROM vcard WHERE id=%u", p->dwID));
if (pmsg->Get()->uiNumRows != 1)
{
sys_log(0, "VCARD_FAIL: no data");
return;
}
MYSQL_ROW row = mysql_fetch_row(pmsg->Get()->pSQLResult);
if (strcmp(row[0], p->szSellAccount))
{
sys_log(0, "VCARD_FAIL: sell account differ %s", row[0]);
return;
}
if (!row[1] || *row[1])
{
sys_log(0, "VCARD_FAIL: buy account already exist");
return;
}
int time = 0;
str_to_number(time, row[2]);
if (!row[2] || time < 0)
{
sys_log(0, "VCARD_FAIL: time null");
return;
}
std::unique_ptr<SQLMsg> pmsg1(DBManager::instance().DirectQuery("UPDATE GameTime SET LimitTime=LimitTime+%d WHERE UserID='%s'", time, p->szBuyAccount));
if (pmsg1->Get()->uiAffectedRows == 0 || pmsg1->Get()->uiAffectedRows == (uint32_t)-1)
{
sys_log(0, "VCARD_FAIL: cannot modify GameTime table");
return;
}
std::unique_ptr<SQLMsg> pmsg2(DBManager::instance().DirectQuery("UPDATE vcard,GameTime SET sell_pid='%s', buy_pid='%s', buy_account='%s', sell_time=NOW(), new_time=GameTime.LimitTime WHERE vcard.id=%u AND GameTime.UserID='%s'", p->szSellCharacter, p->szBuyCharacter, p->szBuyAccount, p->dwID, p->szBuyAccount));
if (pmsg2->Get()->uiAffectedRows == 0 || pmsg2->Get()->uiAffectedRows == (uint32_t)-1)
{
sys_log(0, "VCARD_FAIL: cannot modify vcard table");
return;
}
sys_log(0, "VCARD_SUCCESS: %s %s", p->szBuyAccount, p->szBuyCharacter);
}
void CInputDB::GuildWarReserveAdd(TGuildWarReserve * p)
{
CGuildManager::instance().ReserveWarAdd(p);
@@ -2228,10 +2172,6 @@ int CInputDB::Analyze(LPDESC d, BYTE bHeader, const char * c_pData)
SetEventFlag(c_pData);
break;
case HEADER_DG_VCARD:
VCard(c_pData);
break;
case HEADER_DG_CREATE_OBJECT:
CreateObject(c_pData);
break;

View File

@@ -1,372 +0,0 @@
//#define __MAIN__
#ifdef __MAIN__
#include <stdio.h>
#include <stdlib.h>
#include <string.h>
#include <sys/types.h>
#include <sys/socket.h>
#include <netinet/in.h>
#include <arpa/inet.h>
#include <vector>
#include <algorithm>
typedef unsigned char BYTE;
typedef unsigned long DWORD;
#else
#include "stdafx.h"
#include "ip_ban.h"
#endif
class IP
{
public:
IP()
: dwStart(0), dwEnd(0), dwMask(0)
{}
IP(const IP & r)
{
dwStart = r.dwStart;
dwEnd = r.dwEnd;
dwMask = r.dwMask;
}
IP(const char * c_pszStart, const char * c_pszEnd = NULL)
{
BYTE start[4];
BYTE end[4];
BYTE mask[4];
Read(c_pszStart, start);
if (c_pszEnd && *c_pszEnd)
Read(c_pszEnd, end);
else
memcpy(end, start, sizeof(BYTE) * 4);
mask[0] = 255 - (start[0] ^ end[0]);
mask[1] = 255 - (start[1] ^ end[1]);
mask[2] = 255 - (start[2] ^ end[2]);
mask[3] = 255 - (start[3] ^ end[3]);
dwStart = (start[3] << 24) | (start[2] << 16) | (start[1] << 8) | start[0];
dwEnd = (end[3] << 24) | (end[2] << 16) | (end[1] << 8) | end[0];
dwMask = (mask[3] << 24) | (mask[2] << 16) | (mask[1] << 8) | mask[0];
Print();
}
IP(struct in_addr in)
{
dwStart = in.s_addr;
dwEnd = dwStart;
dwMask = 4294967295UL;
}
bool IsEqual(const IP & r) const
{
return (dwStart == r.dwStart && dwEnd == r.dwEnd && dwMask == r.dwMask);
}
bool IsChildOf(IP & r)
{
if ((r.dwStart & r.dwMask) != (dwStart & r.dwMask))
return false;
DWORD m = r.dwMask | dwMask;
return (dwStart & ~m) == (dwStart & ~dwMask) && (dwEnd & ~m) == (dwEnd & ~dwMask);
}
int hash()
{
return (dwStart & 0x000000FF);
}
void Print()
{
struct in_addr in_ip, in_mask, in_end;
in_ip.s_addr = dwStart;
in_mask.s_addr = dwMask;
in_end.s_addr = dwEnd;
fprintf(stderr, "\t%s", inet_ntoa(in_ip));
fprintf(stderr, "\t%s", inet_ntoa(in_end));
fprintf(stderr, "\t%s\tfirst %d\n", inet_ntoa(in_mask), hash());
}
protected:
bool Read(const char * s, BYTE * dest)
{
BYTE bClass = 0;
const char * p = s;
while (bClass < 3)
{
char szNum[4];
char * pDot = const_cast<char*>(strchr(p, '.'));
if (!pDot)
break;
strlcpy(szNum, p, sizeof(szNum));
str_to_number(dest[bClass++], szNum);
p = pDot + 1;
}
if (bClass != 3)
{
fprintf(stderr, "error reading start %s\n", s);
return false;
}
str_to_number(dest[bClass], p);
return true;
}
DWORD dwStart;
DWORD dwEnd;
DWORD dwMask;
};
std::map<int, std::vector<IP> > mapBanIP;
bool LoadBanIP(const char * filename)
{
FILE * fp = fopen(filename, "r");
if (!fp)
return false;
char buf[256];
char start[256];
char end[256];
fprintf(stderr, "LOADING BANNED IP LIST\n");
while (fgets(buf, 256, fp))
{
*strchr(buf, '\n') = '\0';
char * p = strchr(buf, '\t');
if (!p)
{
strlcpy(start, buf, sizeof(start));
*end = '\0';
}
else
{
char * p2 = strchr(p + 1, '\t');
if (p2)
*p2 = '\0';
strlcpy(end, p + 1, sizeof(end));
*p = '\0';
strlcpy(start, buf, sizeof(start));
}
IP ip(start, end);
itertype(mapBanIP) it = mapBanIP.find(ip.hash());
if (it == mapBanIP.end())
{
std::vector<IP> v;
v.push_back(ip);
mapBanIP.insert(std::map<DWORD, std::vector<IP> >::value_type(ip.hash(), v));
}
else
it->second.push_back(ip);
}
fclose(fp);
return true;
}
bool IsBanIP(struct in_addr in)
{
IP ip(in);
itertype(mapBanIP) it = mapBanIP.find(ip.hash());
if (it == mapBanIP.end())
return false;
itertype(it->second) it2 = it->second.begin();
while (it2 != it->second.end())
if (ip.IsChildOf(*(it2++)))
return true;
return false;
}
#ifdef __MAIN__
void UniqueIP(std::vector<IP> & v)
{
using namespace std;
bool found;
vector<IP>::iterator it1;
do
{
vector<IP> o;
it1 = v.begin();
while (it1 != v.end())
{
IP & ip1 = *(it1++);
found = false;
if (it1 != v.end())
{
vector<IP>::iterator it2 = it1;
while (it2 != v.end())
{
IP & ip2 = *(it2++);
if (ip1.IsEqual(ip2))
{
found = true;
break;
}
}
}
if (!found)
o.push_back(ip1);
}
if (o.size() == v.size())
break;
v.clear();
it1 = o.begin();
while (it1 != o.end())
v.push_back(*(it1++));
}
while (1);
}
void FilterIP(std::vector<IP> & v)
{
using namespace std;
bool found;
vector<IP>::iterator it1;
do
{
vector<IP> o;
it1 = v.begin();
while (it1 != v.end())
{
IP & ip1 = *(it1++);
found = false;
vector<IP>::iterator it2 = v.begin();
while (it2 != v.end())
{
IP & ip2 = *(it2++);
if (ip1.IsEqual(ip2))
continue;
if (ip1.IsChildOf(ip2))
{
found = true;
break;
}
}
if (!found)
o.push_back(ip1);
}
if (o.size() == v.size())
break;
v.clear();
it1 = o.begin();
while (it1 != o.end())
v.push_back(*(it1++));
}
while (1);
}
int main(int argc, char **argv)
{
using namespace std;
if (argc != 2)
{
printf("Syntax: %s <filename>\n", *argv);
return 1;
}
argc--, argv++;
FILE * fp = fopen(*argv, "r");
if (!fp)
return 0;
vector<IP> v;
char buf[256];
char start[32];
char end[32];
while (fgets(buf, 256, fp))
{
*strchr(buf, '\n') = '\0';
char * p = strchr(buf, '\t');
if (!p)
{
strlcpy(start, buf, sizeof(start));
*end = '\0';
}
else
{
strlcpy(end, p + 1, sizeof(end));
*p = '\0';
strlcpy(start, buf, sizeof(start));
}
v.push_back(IP(start, end));
}
fclose(fp);
printf("size %d\n", v.size());
UniqueIP(v);
printf("result1 %d\n", v.size());
FilterIP(v);
printf("result2 %d\n", v.size());
vector<IP>::iterator it = v.begin();
while (it != v.end())
(*(it++)).Print();
return 1;
}
#endif

View File

@@ -1,7 +0,0 @@
#ifndef __INC_METIN_II_GAME_BAN_IP_H__
#define __INC_METIN_II_GAME_BAN_IP_H__
extern bool LoadBanIP(const char * filename);
extern bool IsBanIP(struct in_addr in);
#endif

View File

@@ -1,8 +0,0 @@
#ifndef __LIMIT_TIME__
#define __LIMIT_TIME__
// #define ENABLE_LIMIT_TIME
#define GLOBAL_LIMIT_TIME 1684265966UL // Tue May 16 21:39:26 2023
#define TIME_OVER_PONG_DOWN_RATE 50000
#define TIME_OVER_LOGIN_DOWN_RATE 10000
#endif

View File

@@ -245,12 +245,6 @@ void LogManager::BootLog(const char * c_pszHostName, BYTE bChannel)
c_pszHostName, bChannel);
}
void LogManager::VCardLog(DWORD vcard_id, DWORD x, DWORD y, const char * hostname, const char * giver_name, const char * giver_ip, const char * taker_name, const char * taker_ip)
{
Query("INSERT DELAYED INTO vcard_log (vcard_id, x, y, hostname, giver_name, giver_ip, taker_name, taker_ip) VALUES(%u, %u, %u, '%s', '%s', '%s', '%s', '%s')",
vcard_id, x, y, hostname, giver_name, giver_ip, taker_name, taker_ip);
}
void LogManager::FishLog(DWORD dwPID, int prob_idx, int fish_id, int fish_level, DWORD dwMiliseconds, DWORD dwVnum, DWORD dwValue)
{
Query("INSERT INTO fish_log%s VALUES(NOW(), %u, %d, %u, %d, %u, %u, %u)",

View File

@@ -46,7 +46,6 @@ class LogManager : public singleton<LogManager>
void ShoutLog(BYTE bChannel, BYTE bEmpire, const char * pszText);
void LevelLog(LPCHARACTER pChar, unsigned int level, unsigned int playhour);
void BootLog(const char * c_pszHostName, BYTE bChannel);
void VCardLog(DWORD vcard_id, DWORD x, DWORD y, const char * hostname, const char * giver_name, const char * giver_ip, const char * taker_name, const char * taker_ip);
void FishLog(DWORD dwPID, int prob_idx, int fish_id, int fish_level, DWORD dwMiliseconds, DWORD dwVnum = false, DWORD dwValue = 0);
void QuestRewardLog(const char * c_pszQuestName, DWORD dwPID, DWORD dwLevel, int iValue1, int iValue2);
void DetailLoginLog(bool isLogin, LPCHARACTER ch);

View File

@@ -54,20 +54,10 @@
#include "spam.h"
#include "panama.h"
#include "threeway_war.h"
#include "auth_brazil.h"
#include "DragonLair.h"
#include "skill_power.h"
#include "SpeedServer.h"
#include "DragonSoul.h"
#ifndef OS_WINDOWS
#include "limit_time.h"
#endif
//#define __FILEMONITOR__
#if defined (OS_FREEBSD) && defined(__FILEMONITOR__)
#include "FileMonitor_FreeBSD.h"
#endif
// #ifndef OS_WINDOWS
// #include <gtest/gtest.h>
@@ -77,11 +67,6 @@
#include <execinfo.h>
#endif
// 윈도우에서 테스트할 때는 항상 서버키 체크
#ifdef _WIN32
//#define _USE_SERVER_KEY_
#endif
extern void WriteVersion();
//extern const char * _malloc_options;
#if defined(OS_FREEBSD) && defined(DEBUG_ALLOC)
@@ -237,16 +222,6 @@ void heartbeat(LPHEART ht, int pulse)
// 1초마다
if (!(pulse % ht->passes_per_sec))
{
#ifdef ENABLE_LIMIT_TIME
if ((unsigned)get_global_time() >= GLOBAL_LIMIT_TIME)
{
g_bShutdown = true;
}
#endif
if (g_bAuthServer && LC_IsBrazil() && !test_server)
auth_brazil_log();
if (!g_bAuthServer)
{
TPlayerCountPacket pack;
@@ -298,14 +273,6 @@ void heartbeat(LPHEART ht, int pulse)
if (!(pulse % (passes_per_sec + 4)))
CHARACTER_MANAGER::instance().ProcessDelayedSave();
//4초 마다
#if defined (OS_FREEBSD) && defined(__FILEMONITOR__)
if (!(pulse % (passes_per_sec * 5)))
{
FileMonitorFreeBSD::Instance().Update(pulse);
}
#endif
// 약 5.08초마다
if (!(pulse % (passes_per_sec * 5 + 2)))
{
@@ -339,87 +306,6 @@ void heartbeat(LPHEART ht, int pulse)
}
}
static bool g_isInvalidServer = false;
bool Metin2Server_IsInvalid()
{
return g_isInvalidServer;
}
void Metin2Server_Check()
{
#ifdef _SERVER_CHECK_
#ifdef _USE_SERVER_KEY_
if (false == CheckServer::CheckIp(g_szPublicIP))
{
#ifdef _WIN32
fprintf(stderr, "check ip failed\n");
#endif
g_isInvalidServer = true;
}
return;
#endif
if (LC_IsEurope() || test_server)
return;
// 브라질 ip
if (strncmp (g_szPublicIP, "189.112.1", 9) == 0)
{
return;
}
// 캐나다 ip
if (strncmp (g_szPublicIP, "74.200.6", 8) == 0)
{
return;
}
return;
static const size_t CheckServerListSize = 1;
static const char* CheckServerList[] = { "202.31.178.251"};
static const int CheckServerPort = 7120;
socket_t sockConnector = INVALID_SOCKET;
for (size_t i = 0 ; i < CheckServerListSize ; i++)
{
sockConnector = socket_connect( CheckServerList[i], CheckServerPort );
if (0 < sockConnector)
break;
}
if (0 > sockConnector)
{
if (true != LC_IsEurope()) // 유럽은 접속을 하지 못하면 인증된 것으로 간주
g_isInvalidServer = true;
return;
}
char buf[256] = { 0, };
socket_read(sockConnector, buf, sizeof(buf) - 1);
sys_log(0, "recv[%s]", buf);
if (strncmp(buf, "OK", 2) == 0)
g_isInvalidServer = false;
else if (strncmp(buf, "CK", 2) == 0)
g_isInvalidServer = true;
socket_close(sockConnector);
#else
g_isInvalidServer = false;
return;
#endif
}
static void CleanUpForEarlyExit() {
CancelReloadSpamEvent();
}
@@ -518,15 +404,6 @@ int main(int argc, char **argv)
ani_init();
PanamaLoad();
Metin2Server_Check();
#if defined(_WIN32) && defined(_USE_SERVER_KEY_)
if (CheckServer::IsFail())
{
return 1;
}
#endif
if ( g_bTrafficProfileOn )
TrafficProfiler::instance().Initialize( TRAFFIC_PROFILE_FLUSH_CYCLE, "ProfileLog" );
@@ -537,11 +414,6 @@ int main(int argc, char **argv)
sys_err("Failed to Load ClientPackageCryptInfo File(%s)", strPackageCryptInfoDir.c_str());
}
#if defined (OS_FREEBSD) && defined(__FILEMONITOR__)
PFN_FileChangeListener pPackageNotifyFunc = &(DESC_MANAGER::NotifyClientPackageFileChanged);
//FileMonitorFreeBSD::Instance().AddWatch( strPackageCryptInfoName, pPackageNotifyFunc );
#endif
while (idle());
sys_log(0, "<shutdown> Starting...");
@@ -634,12 +506,6 @@ int start(int argc, char **argv)
#if defined(OS_FREEBSD) && defined(DEBUG_ALLOC)
_malloc_message = WriteMallocMessage;
#endif
#ifdef ENABLE_LIMIT_TIME
if ((unsigned)get_global_time() >= GLOBAL_LIMIT_TIME)
{
return 0;
}
#endif
char optstring[] = "npverltI";
while ((ch = getopt(argc, argv, optstring)) != -1)
@@ -874,12 +740,6 @@ int idle()
memset(&thecore_profiler[0], 0, sizeof(thecore_profiler));
memset(&s_dwProfiler[0], 0, sizeof(s_dwProfiler));
}
#ifdef _USE_SERVER_KEY_
if (Metin2Server_IsInvalid() && 0 == (thecore_random() % 7146))
{
return 0; // shutdown
}
#endif
#ifdef OS_WINDOWS
if (_kbhit()) {

View File

@@ -345,36 +345,28 @@ int CShop::Buy(LPCHARACTER ch, BYTE pos)
{
m_pkPC->SyncQuickslot(QUICKSLOT_TYPE_ITEM, item->GetCell(), 255);
if (item->GetVnum() == 90008 || item->GetVnum() == 90009) // VCARD
char buf[512];
if (item->GetVnum() >= 80003 && item->GetVnum() <= 80007)
{
VCardUse(m_pkPC, ch, item);
item = NULL;
snprintf(buf, sizeof(buf), "%s FROM: %u TO: %u PRICE: %u", item->GetName(), ch->GetPlayerID(), m_pkPC->GetPlayerID(), dwPrice);
LogManager::instance().GoldBarLog(ch->GetPlayerID(), item->GetID(), SHOP_BUY, buf);
LogManager::instance().GoldBarLog(m_pkPC->GetPlayerID(), item->GetID(), SHOP_SELL, buf);
}
item->RemoveFromCharacter();
if (item->IsDragonSoul())
item->AddToCharacter(ch, TItemPos(DRAGON_SOUL_INVENTORY, iEmptyPos));
else
{
char buf[512];
item->AddToCharacter(ch, TItemPos(INVENTORY, iEmptyPos));
ITEM_MANAGER::instance().FlushDelayedSave(item);
if (item->GetVnum() >= 80003 && item->GetVnum() <= 80007)
{
snprintf(buf, sizeof(buf), "%s FROM: %u TO: %u PRICE: %u", item->GetName(), ch->GetPlayerID(), m_pkPC->GetPlayerID(), dwPrice);
LogManager::instance().GoldBarLog(ch->GetPlayerID(), item->GetID(), SHOP_BUY, buf);
LogManager::instance().GoldBarLog(m_pkPC->GetPlayerID(), item->GetID(), SHOP_SELL, buf);
}
item->RemoveFromCharacter();
if (item->IsDragonSoul())
item->AddToCharacter(ch, TItemPos(DRAGON_SOUL_INVENTORY, iEmptyPos));
else
item->AddToCharacter(ch, TItemPos(INVENTORY, iEmptyPos));
ITEM_MANAGER::instance().FlushDelayedSave(item);
snprintf(buf, sizeof(buf), "%s %u(%s) %u %u", item->GetName(), m_pkPC->GetPlayerID(), m_pkPC->GetName(), dwPrice, item->GetCount());
LogManager::instance().ItemLog(ch, item, "SHOP_BUY", buf);
snprintf(buf, sizeof(buf), "%s %u(%s) %u %u", item->GetName(), m_pkPC->GetPlayerID(), m_pkPC->GetName(), dwPrice, item->GetCount());
LogManager::instance().ItemLog(ch, item, "SHOP_BUY", buf);
snprintf(buf, sizeof(buf), "%s %u(%s) %u %u", item->GetName(), ch->GetPlayerID(), ch->GetName(), dwPrice, item->GetCount());
LogManager::instance().ItemLog(m_pkPC, item, "SHOP_SELL", buf);
}
snprintf(buf, sizeof(buf), "%s %u(%s) %u %u", item->GetName(), ch->GetPlayerID(), ch->GetName(), dwPrice, item->GetCount());
LogManager::instance().ItemLog(m_pkPC, item, "SHOP_SELL", buf);
r_item.pkItem = NULL;
BroadcastUpdateItem(pos);