void CInputAuth::PasspodAnswer(LPDESC d, const char * c_pData) { if (!g_bAuthServer) { sys_err ("CInputAuth class is not for game server. IP %s might be a hacker.", inet_ntoa(d->GetAddr().sin_addr)); d->DelayedDisconnect(5); return; } TPacketCGPasspod * packet = (TPacketCGPasspod*)c_pData; RequestConfirmPasspod Confirm; memcpy(Confirm.passpod, packet->szAnswer, MAX_PASSPOD + 1); memcpy(Confirm.login, d->GetAccountTable().login, LOGIN_MAX_LEN + 1); if (!d->GetAccountTable().id) { sys_err("HEADER_CG_PASSPOD_ANSWER received to desc with no account table binded"); return; } int ret_code = 1; sys_log(0, "Passpod start %s %s", d->GetAccountTable().login, packet->szAnswer); ret_code = CPasspod::instance().ConfirmPasspod(d->GetAccountTable().login, packet->szAnswer); if (ret_code != 0) { sys_log(0, "PASSPOD: wrong answer: %s ret_code %d", d->GetAccountTable().login, ret_code); LoginFailure(d, ERR_MESSAGE[ret_code]); if (!d->CheckMatrixTryCount()) { LoginFailure(d, "QUIT"); d->SetPhase(PHASE_CLOSE); } } else { sys_log(0, "PASSPOD: success: %s", d->GetAccountTable().login); DBManager::instance().SendAuthLogin(d); } // g_PasspodDesc->DBPacket(HEADER_GP_CONFIRM_PASSPOD, 0, &Confirm, sizeof(Confirm)); // sys_log(0, "PASSPOD %s %d", Confirm.login, Confirm.passpod); }
int CInputAuth::Analyze(LPDESC d, BYTE bHeader, const char * c_pData) { if (!g_bAuthServer) { sys_err ("CInputAuth class is not for game server. IP %s might be a hacker.", inet_ntoa(d->GetAddr().sin_addr)); d->DelayedDisconnect(5); return 0; } int iExtraLen = 0; if (test_server) sys_log(0, " InputAuth Analyze Header[%d] ", bHeader); switch (bHeader) { case HEADER_CG_PONG: Pong(d); break; case HEADER_CG_LOGIN3: Login(d, c_pData); break; //2012.07.19 OpenID : 김용욱 case HEADER_CG_LOGIN5_OPENID: if (openid_server) LoginOpenID(d, c_pData); else sys_err("HEADER_CG_LOGIN5_OPENID : wrong client access"); break; case HEADER_CG_PASSPOD_ANSWER: PasspodAnswer(d, c_pData); break; case HEADER_CG_HANDSHAKE: break; default: sys_err("This phase does not handle this header %d (0x%x)(phase: AUTH)", bHeader, bHeader); break; } return iExtraLen; }
int CInputHandshake::Analyze(LPDESC d, BYTE bHeader, const char * c_pData) { if (bHeader == 10) // 엔터는 무시 return 0; if (bHeader == HEADER_CG_TEXT) { ++c_pData; const char * c_pSep; if (!(c_pSep = strchr(c_pData, '\n'))) // \n을 찾는다. return -1; if (*(c_pSep - 1) == '\r') --c_pSep; std::string stResult; std::string stBuf; stBuf.assign(c_pData, 0, c_pSep - c_pData); sys_log(0, "SOCKET_CMD: FROM(%s) CMD(%s)", d->GetHostName(), stBuf.c_str()); if (!stBuf.compare("IS_SERVER_UP")) { if (g_bNoMoreClient) stResult = "NO"; else stResult = "YES"; } else if (!stBuf.compare("IS_PASSPOD_UP")) { if (g_bNoPasspod) stResult = "NO"; else stResult = "YES"; } //else if (!stBuf.compare("SHOWMETHEMONEY")) else if (stBuf == g_stAdminPagePassword) { if (!IsEmptyAdminPage()) { if (!IsAdminPage(inet_ntoa(d->GetAddr().sin_addr))) { char szTmp[64]; snprintf(szTmp, sizeof(szTmp), "WEBADMIN : Wrong Connector : %s", inet_ntoa(d->GetAddr().sin_addr)); stResult += szTmp; } else { d->SetAdminMode(); stResult = "UNKNOWN"; } } else { d->SetAdminMode(); stResult = "UNKNOWN"; } } else if (!stBuf.compare("USER_COUNT")) { char szTmp[64]; if (!IsEmptyAdminPage()) { if (!IsAdminPage(inet_ntoa(d->GetAddr().sin_addr))) { snprintf(szTmp, sizeof(szTmp), "WEBADMIN : Wrong Connector : %s", inet_ntoa(d->GetAddr().sin_addr)); } else { int iTotal; int * paiEmpireUserCount; int iLocal; DESC_MANAGER::instance().GetUserCount(iTotal, &paiEmpireUserCount, iLocal); snprintf(szTmp, sizeof(szTmp), "%d %d %d %d %d", iTotal, paiEmpireUserCount[1], paiEmpireUserCount[2], paiEmpireUserCount[3], iLocal); } } else { int iTotal; int * paiEmpireUserCount; int iLocal; DESC_MANAGER::instance().GetUserCount(iTotal, &paiEmpireUserCount, iLocal); snprintf(szTmp, sizeof(szTmp), "%d %d %d %d %d", iTotal, paiEmpireUserCount[1], paiEmpireUserCount[2], paiEmpireUserCount[3], iLocal); } stResult += szTmp; } else if (!stBuf.compare("CHECK_P2P_CONNECTIONS")) { std::ostringstream oss(std::ostringstream::out); oss << "P2P CONNECTION NUMBER : " << P2P_MANAGER::instance().GetDescCount() << "\n"; std::string hostNames; P2P_MANAGER::Instance().GetP2PHostNames(hostNames); oss << hostNames; stResult = oss.str(); TPacketGGCheckAwakeness packet; packet.bHeader = HEADER_GG_CHECK_AWAKENESS; P2P_MANAGER::instance().Send(&packet, sizeof(packet)); } else if (!stBuf.compare("PACKET_INFO")) { m_pMainPacketInfo->Log("packet_info.txt"); stResult = "OK"; } else if (!stBuf.compare("PROFILE")) { CProfiler::instance().Log("profile.txt"); stResult = "OK"; } //gift notify delete command else if (!stBuf.compare(0,15,"DELETE_AWARDID ")) { char szTmp[64]; std::string msg = stBuf.substr(15,26); // item_award의 id범위? TPacketDeleteAwardID p; p.dwID = (DWORD)(atoi(msg.c_str())); snprintf(szTmp,sizeof(szTmp),"Sent to DB cache to delete ItemAward, id: %d",p.dwID); //sys_log(0,"%d",p.dwID); // strlcpy(p.login, msg.c_str(), sizeof(p.login)); db_clientdesc->DBPacket(HEADER_GD_DELETE_AWARDID, 0, &p, sizeof(p)); stResult += szTmp; } else { stResult = "UNKNOWN"; if (d->IsAdminMode()) { // 어드민 명령들 if (!stBuf.compare(0, 7, "NOTICE ")) { std::string msg = stBuf.substr(7, 50); LogManager::instance().CharLog(0, 0, 0, 1, "NOTICE", msg.c_str(), d->GetHostName()); BroadcastNotice(msg.c_str()); } else if (!stBuf.compare("CLOSE_PASSPOD")) { g_bNoPasspod = true; stResult += "CLOSE_PASSPOD"; } else if (!stBuf.compare("OPEN_PASSPOD")) { g_bNoPasspod = false; stResult += "OPEN_PASSPOD"; } else if (!stBuf.compare("SHUTDOWN")) { LogManager::instance().CharLog(0, 0, 0, 2, "SHUTDOWN", "", d->GetHostName()); TPacketGGShutdown p; p.bHeader = HEADER_GG_SHUTDOWN; P2P_MANAGER::instance().Send(&p, sizeof(TPacketGGShutdown)); sys_err("Accept shutdown command from %s.", d->GetHostName()); Shutdown(10); } else if (!stBuf.compare("SHUTDOWN_ONLY")) { LogManager::instance().CharLog(0, 0, 0, 2, "SHUTDOWN", "", d->GetHostName()); sys_err("Accept shutdown only command from %s.", d->GetHostName()); Shutdown(10); } else if (!stBuf.compare(0, 3, "DC ")) { std::string msg = stBuf.substr(3, LOGIN_MAX_LEN); dev_log(LOG_DEB0, "DC : '%s'", msg.c_str()); TPacketGGDisconnect pgg; pgg.bHeader = HEADER_GG_DISCONNECT; strlcpy(pgg.szLogin, msg.c_str(), sizeof(pgg.szLogin)); P2P_MANAGER::instance().Send(&pgg, sizeof(TPacketGGDisconnect)); // delete login key { TPacketDC p; strlcpy(p.login, msg.c_str(), sizeof(p.login)); db_clientdesc->DBPacket(HEADER_GD_DC, 0, &p, sizeof(p)); } } else if (!stBuf.compare(0, 10, "RELOAD_CRC")) { LoadValidCRCList(); BYTE bHeader = HEADER_GG_RELOAD_CRC_LIST; P2P_MANAGER::instance().Send(&bHeader, sizeof(BYTE)); stResult = "OK"; } else if (!stBuf.compare(0, 20, "CHECK_CLIENT_VERSION")) { CheckClientVersion(); BYTE bHeader = HEADER_GG_CHECK_CLIENT_VERSION; P2P_MANAGER::instance().Send(&bHeader, sizeof(BYTE)); stResult = "OK"; } else if (!stBuf.compare(0, 6, "RELOAD")) { if (stBuf.size() == 6) { LoadStateUserCount(); db_clientdesc->DBPacket(HEADER_GD_RELOAD_PROTO, 0, NULL, 0); DBManager::instance().LoadDBString(); } else { char c = stBuf[7]; switch (LOWER(c)) { case 'u': LoadStateUserCount(); break; case 'p': db_clientdesc->DBPacket(HEADER_GD_RELOAD_PROTO, 0, NULL, 0); break; case 's': DBManager::instance().LoadDBString(); break; case 'q': quest::CQuestManager::instance().Reload(); break; case 'f': fishing::Initialize(); break; case 'a': db_clientdesc->DBPacket(HEADER_GD_RELOAD_ADMIN, 0, NULL, 0); sys_log(0, "Reloading admin infomation."); break; } } } else if (!stBuf.compare(0, 6, "EVENT ")) { std::istringstream is(stBuf); std::string strEvent, strFlagName; long lValue; is >> strEvent >> strFlagName >> lValue; if (!is.fail()) { sys_log(0, "EXTERNAL EVENT FLAG name %s value %d", strFlagName.c_str(), lValue); quest::CQuestManager::instance().RequestSetEventFlag(strFlagName, lValue); stResult = "EVENT FLAG CHANGE "; stResult += strFlagName; } else { stResult = "EVENT FLAG FAIL"; } } // BLOCK_CHAT else if (!stBuf.compare(0, 11, "BLOCK_CHAT ")) { std::istringstream is(stBuf); std::string strBlockChat, strCharName; long lDuration; is >> strBlockChat >> strCharName >> lDuration; if (!is.fail()) { sys_log(0, "EXTERNAL BLOCK_CHAT name %s duration %d", strCharName.c_str(), lDuration); do_block_chat(NULL, const_cast<char*>(stBuf.c_str() + 11), 0, 0); stResult = "BLOCK_CHAT "; stResult += strCharName; } else { stResult = "BLOCK_CHAT FAIL"; } }
void CInputAuth::LoginOpenID(LPDESC d, const char * c_pData) { #ifdef ENABLE_LIMIT_TIME #endif //OpenID test code. TPacketCGLogin5 *tempInfo1 = (TPacketCGLogin5 *)c_pData; //일본 웹 서버에 인증키 확인 요청을 보낸다. char* authKey = tempInfo1->authKey; char returnID[LOGIN_MAX_LEN + 1] = {0}; int test_url_get_protocol = auth_OpenID(authKey, inet_ntoa(d->GetAddr().sin_addr), returnID); //인증 실패. 에러 처리 if (0!=test_url_get_protocol) { LoginFailure(d, "OpenID Fail"); return; } TPacketCGLogin3 tempInfo2; strncpy(tempInfo2.login, returnID, LOGIN_MAX_LEN); strncpy(tempInfo2.passwd, "0000", PASSWD_MAX_LEN); for(int i=0; i<4; i++) tempInfo2.adwClientKey[i] = tempInfo1->adwClientKey[i]; TPacketCGLogin3 * pinfo = &tempInfo2; if (!g_bAuthServer) { sys_err ("CInputAuth class is not for game server. IP %s might be a hacker.", inet_ntoa(d->GetAddr().sin_addr)); d->DelayedDisconnect(5); return; } // string 무결성을 위해 복사 char login[LOGIN_MAX_LEN + 1]; trim_and_lower(pinfo->login, login, sizeof(login)); char passwd[PASSWD_MAX_LEN + 1]; strlcpy(passwd, pinfo->passwd, sizeof(passwd)); sys_log(0, "InputAuth::Login : %s(%d) desc %p", login, strlen(login), get_pointer(d)); // check login string if (false == FN_IS_VALID_LOGIN_STRING(login)) { sys_log(0, "InputAuth::Login : IS_NOT_VALID_LOGIN_STRING(%s) desc %p", login, get_pointer(d)); LoginFailure(d, "NOID"); return; } if (g_bNoMoreClient) { TPacketGCLoginFailure failurePacket; failurePacket.header = HEADER_GC_LOGIN_FAILURE; strlcpy(failurePacket.szStatus, "SHUTDOWN", sizeof(failurePacket.szStatus)); d->Packet(&failurePacket, sizeof(failurePacket)); return; } if (DESC_MANAGER::instance().FindByLoginName(login)) { LoginFailure(d, "ALREADY"); return; } DWORD dwKey = DESC_MANAGER::instance().CreateLoginKey(d); DWORD dwPanamaKey = dwKey ^ pinfo->adwClientKey[0] ^ pinfo->adwClientKey[1] ^ pinfo->adwClientKey[2] ^ pinfo->adwClientKey[3]; d->SetPanamaKey(dwPanamaKey); 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)); char szPasswd[PASSWD_MAX_LEN * 2 + 1]; DBManager::instance().EscapeString(szPasswd, sizeof(szPasswd), passwd, strlen(passwd)); char szLogin[LOGIN_MAX_LEN * 2 + 1]; DBManager::instance().EscapeString(szLogin, sizeof(szLogin), login, strlen(login)); // CHANNEL_SERVICE_LOGIN if (Login_IsInChannelService(szLogin)) { sys_log(0, "ChannelServiceLogin [%s]", szLogin); DBManager::instance().ReturnQuery(QID_AUTH_LOGIN_OPENID, dwKey, p, "SELECT '%s',password,securitycode,social_id,id,status,availDt - NOW() > 0," "UNIX_TIMESTAMP(silver_expire)," "UNIX_TIMESTAMP(gold_expire)," "UNIX_TIMESTAMP(safebox_expire)," "UNIX_TIMESTAMP(autoloot_expire)," "UNIX_TIMESTAMP(fish_mind_expire)," "UNIX_TIMESTAMP(marriage_fast_expire)," "UNIX_TIMESTAMP(money_drop_rate_expire)," "UNIX_TIMESTAMP(create_time)" " FROM account WHERE login='******'", szPasswd, szLogin); } // END_OF_CHANNEL_SERVICE_LOGIN else { DBManager::instance().ReturnQuery(QID_AUTH_LOGIN_OPENID, dwKey, p, "SELECT PASSWORD('%s'),password,securitycode,social_id,id,status,availDt - NOW() > 0," "UNIX_TIMESTAMP(silver_expire)," "UNIX_TIMESTAMP(gold_expire)," "UNIX_TIMESTAMP(safebox_expire)," "UNIX_TIMESTAMP(autoloot_expire)," "UNIX_TIMESTAMP(fish_mind_expire)," "UNIX_TIMESTAMP(marriage_fast_expire)," "UNIX_TIMESTAMP(money_drop_rate_expire)," "UNIX_TIMESTAMP(create_time)" " FROM account WHERE login='******'", szPasswd, szLogin); } }