trus7

input_main.cpp

Nov 20th, 2020
79
0
Never
Not a member of Pastebin yet? Sign Up, it unlocks many cool features!
text 117.44 KB | None | 0 0
  1. #include "stdafx.h"
  2. #include "constants.h"
  3. #include "config.h"
  4. #include "utils.h"
  5. #include "desc_client.h"
  6. #include "desc_manager.h"
  7. #include "buffer_manager.h"
  8. #include "packet.h"
  9. #include "protocol.h"
  10. #include "char.h"
  11. #include "char_manager.h"
  12. #include "item.h"
  13. #include "item_manager.h"
  14. #include "cmd.h"
  15. #include "shop.h"
  16. #include "shop_manager.h"
  17. #include "safebox.h"
  18. #include "regen.h"
  19. #include "battle.h"
  20. #include "exchange.h"
  21. #include "questmanager.h"
  22. #include "profiler.h"
  23. #include "messenger_manager.h"
  24. #include "party.h"
  25. #include "p2p.h"
  26. #include "affect.h"
  27. #include "guild.h"
  28. #include "guild_manager.h"
  29. #include "log.h"
  30. #include "banword.h"
  31. #include "empire_text_convert.h"
  32. #include "unique_item.h"
  33. #include "building.h"
  34. #include "locale_service.h"
  35. #include "gm.h"
  36. #include "spam.h"
  37. #include "ani.h"
  38. #include "motion.h"
  39. #include "OXEvent.h"
  40. #include "locale_service.h"
  41. #include "HackShield.h"
  42. #include "XTrapManager.h"
  43. #include "DragonSoul.h"
  44. #ifdef __ATTENDANCE_EVENT__
  45. #include "minigame.h"
  46. #endif
  47. #ifdef __ENABLE_BATTLE_FIELD__
  48. #include "battle_zone.h"
  49. #endif
  50. #include "belt_inventory_helper.h" // @fixme119
  51. #include "../../common/CommonDefines.h"
  52. #ifdef NEW_PET_SYSTEM
  53. #include "New_PetSystem.h"
  54. #endif
  55. #ifdef __REFINE_SYSTEM__
  56. #include "refine.h"
  57. #endif
  58. #ifdef __WHISPER_ADMIN__
  59. #include "whisper_admin.h"
  60. #endif
  61. #if defined(WHEEL_OF_DESTINY)
  62. #include "wheel_of_destiny.h"
  63. #endif
  64. #include "input.h"
  65.  
  66. //#define ENABLE_CHAT_LOGGING
  67. #define ENABLE_CHAT_SPAMLIMIT
  68. #define ENABLE_WHISPER_CHAT_SPAMLIMIT
  69. #define ENABLE_CHECK_GHOSTMODE
  70.  
  71. #ifdef ENABLE_CHAT_LOGGING
  72. static char __escape_string[1024];
  73. static char __escape_string2[1024];
  74. #endif
  75.  
  76. static int __deposit_limit()
  77. {
  78. return (1000*10000); // 1õ¸¸
  79. }
  80.  
  81. #ifdef __SEND_TARGET_INFO__
  82. void CInputMain::TargetInfoLoad(LPCHARACTER ch, const char* c_pData)
  83. {
  84. TPacketCGTargetInfoLoad* p = (TPacketCGTargetInfoLoad*)c_pData;
  85. TPacketGCTargetInfo pInfo;
  86. pInfo.header = HEADER_GC_TARGET_INFO;
  87. static std::vector<LPITEM> s_vec_item;
  88. s_vec_item.clear();
  89. LPITEM pkInfoItem;
  90. LPCHARACTER m_pkChrTarget = CHARACTER_MANAGER::instance().Find(p->dwVID);
  91. if (!ch || !m_pkChrTarget)
  92. return;
  93.  
  94. // if (m_pkChrTarget && (m_pkChrTarget->IsMonster() || m_pkChrTarget->IsStone()))
  95. // {
  96. // if (thecore_heart->pulse - (int) ch->GetLastTargetInfoPulse() < passes_per_sec * 3)
  97. // return;
  98.  
  99. // ch->SetLastTargetInfoPulse(thecore_heart->pulse);
  100.  
  101. if (ITEM_MANAGER::instance().CreateDropItemVector(m_pkChrTarget, ch, s_vec_item) && (m_pkChrTarget->IsMonster() || m_pkChrTarget->IsStone()))
  102. {
  103. if (s_vec_item.size() == 0);
  104. else if (s_vec_item.size() == 1)
  105. {
  106. pkInfoItem = s_vec_item[0];
  107. pInfo.dwVID = m_pkChrTarget->GetVID();
  108. pInfo.race = m_pkChrTarget->GetRaceNum();
  109. pInfo.dwVnum = pkInfoItem->GetVnum();
  110. pInfo.count = pkInfoItem->GetCount();
  111. ch->GetDesc()->Packet(&pInfo, sizeof(TPacketGCTargetInfo));
  112. }
  113. else
  114. {
  115. int iItemIdx = s_vec_item.size() - 1;
  116. while (iItemIdx >= 0)
  117. {
  118. pkInfoItem = s_vec_item[iItemIdx--];
  119.  
  120. if (!pkInfoItem)
  121. {
  122. sys_err("pkInfoItem null in vector idx %d", iItemIdx + 1);
  123. continue;
  124. }
  125.  
  126. pInfo.dwVID = m_pkChrTarget->GetVID();
  127. pInfo.race = m_pkChrTarget->GetRaceNum();
  128. pInfo.dwVnum = pkInfoItem->GetVnum();
  129. pInfo.count = pkInfoItem->GetCount();
  130. ch->GetDesc()->Packet(&pInfo, sizeof(TPacketGCTargetInfo));
  131. }
  132. }
  133. }
  134. // }
  135. }
  136. #endif
  137.  
  138. void SendBlockChatInfo(LPCHARACTER ch, int sec)
  139. {
  140. if (sec <= 0)
  141. {
  142. ch->ChatPacket(CHAT_TYPE_INFO, LC_TEXT("äÆÃ ±ÝÁö »óÅÂÀÔ´Ï´Ù."));
  143. return;
  144. }
  145.  
  146. long hour = sec / 3600;
  147. sec -= hour * 3600;
  148.  
  149. long min = (sec / 60);
  150. sec -= min * 60;
  151.  
  152. char buf[128+1];
  153.  
  154. if (hour > 0 && min > 0)
  155. snprintf(buf, sizeof(buf), LC_TEXT("%d ½Ã°£ %d ºÐ %d ÃÊ µ¿¾È äÆÃ±ÝÁö »óÅÂÀÔ´Ï´Ù"), hour, min, sec);
  156. else if (hour > 0 && min == 0)
  157. snprintf(buf, sizeof(buf), LC_TEXT("%d ½Ã°£ %d ÃÊ µ¿¾È äÆÃ±ÝÁö »óÅÂÀÔ´Ï´Ù"), hour, sec);
  158. else if (hour == 0 && min > 0)
  159. snprintf(buf, sizeof(buf), LC_TEXT("%d ºÐ %d ÃÊ µ¿¾È äÆÃ±ÝÁö »óÅÂÀÔ´Ï´Ù"), min, sec);
  160. else
  161. snprintf(buf, sizeof(buf), LC_TEXT("%d ÃÊ µ¿¾È äÆÃ±ÝÁö »óÅÂÀÔ´Ï´Ù"), sec);
  162.  
  163. ch->ChatPacket(CHAT_TYPE_INFO, buf);
  164. }
  165.  
  166. EVENTINFO(spam_event_info)
  167. {
  168. char host[MAX_HOST_LENGTH+1];
  169.  
  170. spam_event_info()
  171. {
  172. ::memset( host, 0, MAX_HOST_LENGTH+1 );
  173. }
  174. };
  175.  
  176. typedef boost::unordered_map<std::string, std::pair<unsigned int, LPEVENT> > spam_score_of_ip_t;
  177. spam_score_of_ip_t spam_score_of_ip;
  178.  
  179. EVENTFUNC(block_chat_by_ip_event)
  180. {
  181. spam_event_info* info = dynamic_cast<spam_event_info*>( event->info );
  182.  
  183. if ( info == NULL )
  184. {
  185. sys_err( "block_chat_by_ip_event> <Factor> Null pointer" );
  186. return 0;
  187. }
  188.  
  189. const char * host = info->host;
  190.  
  191. spam_score_of_ip_t::iterator it = spam_score_of_ip.find(host);
  192.  
  193. if (it != spam_score_of_ip.end())
  194. {
  195. it->second.first = 0;
  196. it->second.second = NULL;
  197. }
  198.  
  199. return 0;
  200. }
  201.  
  202. bool SpamBlockCheck(LPCHARACTER ch, const char* const buf, const size_t buflen)
  203. {
  204. if (ch->GetLevel() < g_iSpamBlockMaxLevel)
  205. {
  206. spam_score_of_ip_t::iterator it = spam_score_of_ip.find(ch->GetDesc()->GetHostName());
  207.  
  208. if (it == spam_score_of_ip.end())
  209. {
  210. spam_score_of_ip.insert(std::make_pair(ch->GetDesc()->GetHostName(), std::make_pair(0, (LPEVENT) NULL)));
  211. it = spam_score_of_ip.find(ch->GetDesc()->GetHostName());
  212. }
  213.  
  214. if (it->second.second)
  215. {
  216. SendBlockChatInfo(ch, event_time(it->second.second) / passes_per_sec);
  217. return true;
  218. }
  219.  
  220. unsigned int score;
  221. const char * word = SpamManager::instance().GetSpamScore(buf, buflen, score);
  222.  
  223. it->second.first += score;
  224.  
  225. if (word)
  226. sys_log(0, "SPAM_SCORE: %s text: %s score: %u total: %u word: %s", ch->GetName(), buf, score, it->second.first, word);
  227.  
  228. if (it->second.first >= g_uiSpamBlockScore)
  229. {
  230. spam_event_info* info = AllocEventInfo<spam_event_info>();
  231. strlcpy(info->host, ch->GetDesc()->GetHostName(), sizeof(info->host));
  232.  
  233. it->second.second = event_create(block_chat_by_ip_event, info, PASSES_PER_SEC(g_uiSpamBlockDuration));
  234. sys_log(0, "SPAM_IP: %s for %u seconds", info->host, g_uiSpamBlockDuration);
  235.  
  236. LogManager::instance().CharLog(ch, 0, "SPAM", word);
  237.  
  238. SendBlockChatInfo(ch, event_time(it->second.second) / passes_per_sec);
  239.  
  240. return true;
  241. }
  242. }
  243.  
  244. return false;
  245. }
  246.  
  247. enum
  248. {
  249. TEXT_TAG_PLAIN,
  250. TEXT_TAG_TAG, // ||
  251. TEXT_TAG_COLOR, // |cffffffff
  252. TEXT_TAG_HYPERLINK_START, // |H
  253. TEXT_TAG_HYPERLINK_END, // |h ex) |Hitem:1234:1:1:1|h
  254. TEXT_TAG_RESTORE_COLOR,
  255. };
  256.  
  257. int GetTextTag(const char * src, int maxLen, int & tagLen, std::string & extraInfo)
  258. {
  259. tagLen = 1;
  260.  
  261. if (maxLen < 2 || *src != '|')
  262. return TEXT_TAG_PLAIN;
  263.  
  264. const char * cur = ++src;
  265.  
  266. if (*cur == '|') // ||´Â |·Î Ç¥½ÃÇÑ´Ù.
  267. {
  268. tagLen = 2;
  269. return TEXT_TAG_TAG;
  270. }
  271. else if (*cur == 'c') // color |cffffffffblahblah|r
  272. {
  273. tagLen = 2;
  274. return TEXT_TAG_COLOR;
  275. }
  276. else if (*cur == 'H') // hyperlink |Hitem:10000:0:0:0:0|h[À̸§]|h
  277. {
  278. tagLen = 2;
  279. return TEXT_TAG_HYPERLINK_START;
  280. }
  281. else if (*cur == 'h') // end of hyperlink
  282. {
  283. tagLen = 2;
  284. return TEXT_TAG_HYPERLINK_END;
  285. }
  286.  
  287. return TEXT_TAG_PLAIN;
  288. }
  289.  
  290. void GetTextTagInfo(const char * src, int src_len, int & hyperlinks, bool & colored)
  291. {
  292. colored = false;
  293. hyperlinks = 0;
  294.  
  295. int len;
  296. std::string extraInfo;
  297.  
  298. for (int i = 0; i < src_len;)
  299. {
  300. int tag = GetTextTag(&src[i], src_len - i, len, extraInfo);
  301.  
  302. if (tag == TEXT_TAG_HYPERLINK_START)
  303. ++hyperlinks;
  304.  
  305. if (tag == TEXT_TAG_COLOR)
  306. colored = true;
  307.  
  308. i += len;
  309. }
  310. }
  311.  
  312. int ProcessTextTag(LPCHARACTER ch, const char * c_pszText, size_t len)
  313. {
  314. return 0;//2012.05.17 ¡¾e¢¯e¢¯i
  315. //0 : A¢´¡íoAuA¢¬¡¤I ¡íc¢¯e
  316. //1 : ¡¾Y¡Æ¡©¡Æ©¡ ¨¬IA¡¤
  317. //2 : ¡¾Y¡Æ¡©¡Æ©¡AI AOA¢¬©ø¨£, ¡Æ©øAI¡íoA¢®¢¯¢®¨ù¡© ¡íc¢¯eA©¬
  318. //3 : ¡¾©øE?A©¬
  319. //4 : ¢¯¢®¡¤?
  320. int hyperlinks;
  321. bool colored;
  322.  
  323. GetTextTagInfo(c_pszText, len, hyperlinks, colored);
  324.  
  325. if (colored == true && hyperlinks == 0)
  326. return 4;
  327.  
  328. #ifdef ENABLE_NEWSTUFF
  329. if (g_bDisablePrismNeed)
  330. return 0;
  331. #endif
  332. int nPrismCount = ch->CountSpecifyItem(ITEM_PRISM);
  333.  
  334. if (nPrismCount < hyperlinks)
  335. return 1;
  336.  
  337.  
  338. if (!ch->GetMyShop())
  339. {
  340. ch->RemoveSpecifyItem(ITEM_PRISM, hyperlinks);
  341. return 0;
  342. } else
  343. {
  344. int sellingNumber = ch->GetMyShop()->GetNumberByVnum(ITEM_PRISM);
  345. if(nPrismCount - sellingNumber < hyperlinks)
  346. {
  347. return 2;
  348. } else
  349. {
  350. ch->RemoveSpecifyItem(ITEM_PRISM, hyperlinks);
  351. return 0;
  352. }
  353. }
  354.  
  355. return 4;
  356. }
  357.  
  358. int CInputMain::Whisper(LPCHARACTER ch, const char * data, size_t uiBytes)
  359. {
  360. const TPacketCGWhisper* pinfo = reinterpret_cast<const TPacketCGWhisper*>(data);
  361.  
  362. if (uiBytes < pinfo->wSize)
  363. return -1;
  364.  
  365. int iExtraLen = pinfo->wSize - sizeof(TPacketCGWhisper);
  366.  
  367. if (iExtraLen < 0)
  368. {
  369. sys_err("invalid packet length (len %d size %u buffer %u)", iExtraLen, pinfo->wSize, uiBytes);
  370. ch->GetDesc()->SetPhase(PHASE_CLOSE);
  371. return -1;
  372. }
  373.  
  374. #ifdef ENABLE_WHISPER_CHAT_SPAMLIMIT
  375. if (ch->IncreaseChatCounter() >= 10)
  376. {
  377. ch->GetDesc()->DelayedDisconnect(0);
  378. return (iExtraLen);
  379. }
  380. #endif
  381.  
  382. if (ch->FindAffect(AFFECT_BLOCK_CHAT))
  383. {
  384. ch->ChatPacket(CHAT_TYPE_INFO, LC_TEXT("äÆÃ ±ÝÁö »óÅÂÀÔ´Ï´Ù."));
  385. return (iExtraLen);
  386. }
  387.  
  388. #ifdef __ENABLE_BATTLE_FIELD__
  389. if (CBattleZone::instance().IsBattleZoneMapIndex(ch->GetMapIndex()))
  390. {
  391. ch->ChatPacket(CHAT_TYPE_INFO, LC_TEXT("BATTLE_ZONE_CANT_WHISPER"));
  392. return (iExtraLen);
  393. }
  394. #endif
  395.  
  396. LPCHARACTER pkChr = CHARACTER_MANAGER::instance().FindPC(pinfo->szNameTo);
  397.  
  398. if (pkChr == ch)
  399. return (iExtraLen);
  400.  
  401. LPDESC pkDesc = NULL;
  402.  
  403. BYTE bOpponentEmpire = 0;
  404.  
  405. if (test_server)
  406. {
  407. if (!pkChr)
  408. sys_log(0, "Whisper to %s(%s) from %s", "Null", pinfo->szNameTo, ch->GetName());
  409. else
  410. sys_log(0, "Whisper to %s(%s) from %s", pkChr->GetName(), pinfo->szNameTo, ch->GetName());
  411. }
  412.  
  413. if (ch->IsBlockMode(BLOCK_WHISPER))
  414. {
  415. if (ch->GetDesc())
  416. {
  417. TPacketGCWhisper pack;
  418. pack.bHeader = HEADER_GC_WHISPER;
  419. pack.bType = WHISPER_TYPE_SENDER_BLOCKED;
  420. pack.wSize = sizeof(TPacketGCWhisper);
  421. strlcpy(pack.szNameFrom, pinfo->szNameTo, sizeof(pack.szNameFrom));
  422. ch->GetDesc()->Packet(&pack, sizeof(pack));
  423. }
  424. return iExtraLen;
  425. }
  426.  
  427. if (!pkChr)
  428. {
  429. CCI * pkCCI = P2P_MANAGER::instance().Find(pinfo->szNameTo);
  430.  
  431. if (pkCCI)
  432. {
  433. pkDesc = pkCCI->pkDesc;
  434. pkDesc->SetRelay(pinfo->szNameTo);
  435. bOpponentEmpire = pkCCI->bEmpire;
  436.  
  437. if (test_server)
  438. sys_log(0, "Whisper to %s from %s (Channel %d Mapindex %d)", "Null", ch->GetName(), pkCCI->bChannel, pkCCI->lMapIndex);
  439. }
  440. }
  441. else
  442. {
  443. pkDesc = pkChr->GetDesc();
  444. bOpponentEmpire = pkChr->GetEmpire();
  445. }
  446.  
  447. if (!pkDesc)
  448. {
  449. if (ch->GetDesc())
  450. {
  451. TPacketGCWhisper pack;
  452.  
  453. pack.bHeader = HEADER_GC_WHISPER;
  454. pack.bType = WHISPER_TYPE_NOT_EXIST;
  455. pack.wSize = sizeof(TPacketGCWhisper);
  456. strlcpy(pack.szNameFrom, pinfo->szNameTo, sizeof(pack.szNameFrom));
  457. ch->GetDesc()->Packet(&pack, sizeof(TPacketGCWhisper));
  458. sys_log(0, "WHISPER: no player");
  459. }
  460. }
  461. else
  462. {
  463. if (ch->IsBlockMode(BLOCK_WHISPER))
  464. {
  465. if (ch->GetDesc())
  466. {
  467. TPacketGCWhisper pack;
  468. pack.bHeader = HEADER_GC_WHISPER;
  469. pack.bType = WHISPER_TYPE_SENDER_BLOCKED;
  470. pack.wSize = sizeof(TPacketGCWhisper);
  471. strlcpy(pack.szNameFrom, pinfo->szNameTo, sizeof(pack.szNameFrom));
  472. ch->GetDesc()->Packet(&pack, sizeof(pack));
  473. }
  474. }
  475. else if (pkChr && pkChr->IsBlockMode(BLOCK_WHISPER))
  476. {
  477. if (ch->GetDesc())
  478. {
  479. TPacketGCWhisper pack;
  480. pack.bHeader = HEADER_GC_WHISPER;
  481. pack.bType = WHISPER_TYPE_TARGET_BLOCKED;
  482. pack.wSize = sizeof(TPacketGCWhisper);
  483. strlcpy(pack.szNameFrom, pinfo->szNameTo, sizeof(pack.szNameFrom));
  484. ch->GetDesc()->Packet(&pack, sizeof(pack));
  485. }
  486. }
  487. else
  488. {
  489. BYTE bType = WHISPER_TYPE_NORMAL;
  490.  
  491. char buf[CHAT_MAX_LEN + 1];
  492. strlcpy(buf, data + sizeof(TPacketCGWhisper), MIN(iExtraLen + 1, sizeof(buf)));
  493. const size_t buflen = strlen(buf);
  494.  
  495. if (true == SpamBlockCheck(ch, buf, buflen))
  496. {
  497. if (!pkChr)
  498. {
  499. CCI * pkCCI = P2P_MANAGER::instance().Find(pinfo->szNameTo);
  500.  
  501. if (pkCCI)
  502. {
  503. pkDesc->SetRelay("");
  504. }
  505. }
  506. return iExtraLen;
  507. }
  508.  
  509. CBanwordManager::instance().ConvertString(buf, buflen);
  510.  
  511. if (g_bEmpireWhisper)
  512. if (!ch->IsEquipUniqueGroup(UNIQUE_GROUP_RING_OF_LANGUAGE))
  513. if (!(pkChr && pkChr->IsEquipUniqueGroup(UNIQUE_GROUP_RING_OF_LANGUAGE)))
  514. if (bOpponentEmpire != ch->GetEmpire() && ch->GetEmpire() && bOpponentEmpire // ¼­·Î Á¦±¹ÀÌ ´Ù¸£¸é¼­
  515. && ch->GetGMLevel() == GM_PLAYER && gm_get_level(pinfo->szNameTo) == GM_PLAYER) // µÑ´Ù ÀÏ¹Ý Ç÷¹À̾îÀ̸é
  516. // À̸§ ¹Û¿¡ ¸ð¸£´Ï gm_get_level ÇÔ¼ö¸¦ »ç¿ë
  517. {
  518. if (!pkChr)
  519. {
  520. // ´Ù¸¥ ¼­¹ö¿¡ ÀÖÀ¸´Ï Á¦±¹ Ç¥½Ã¸¸ ÇÑ´Ù. bTypeÀÇ »óÀ§ 4ºñÆ®¸¦ Empire¹øÈ£·Î »ç¿ëÇÑ´Ù.
  521. bType = ch->GetEmpire() << 4;
  522. }
  523. else
  524. {
  525. ConvertEmpireText(ch->GetEmpire(), buf, buflen, 10 + 2 * pkChr->GetSkillPower(SKILL_LANGUAGE1 + ch->GetEmpire() - 1)/*º¯È¯È®·ü*/);
  526. }
  527. }
  528.  
  529. int processReturn = ProcessTextTag(ch, buf, buflen);
  530. if (0!=processReturn)
  531. {
  532. if (ch->GetDesc())
  533. {
  534. TItemTable * pTable = ITEM_MANAGER::instance().GetTable(ITEM_PRISM);
  535.  
  536. if (pTable)
  537. {
  538. char buf[128];
  539. int len;
  540. if (3==processReturn) //±³È¯Áß
  541. len = snprintf(buf, sizeof(buf), LC_TEXT("»ç¿ëÇÒ¼ö ¾ø½À´Ï´Ù."), pTable->szLocaleName);
  542. else
  543. len = snprintf(buf, sizeof(buf), LC_TEXT("%sÀÌ ÇÊ¿äÇÕ´Ï´Ù."), pTable->szLocaleName);
  544.  
  545. if (len < 0 || len >= (int) sizeof(buf))
  546. len = sizeof(buf) - 1;
  547.  
  548. ++len; // \0 ¹®ÀÚ Æ÷ÇÔ
  549.  
  550. TPacketGCWhisper pack;
  551.  
  552. pack.bHeader = HEADER_GC_WHISPER;
  553. pack.bType = WHISPER_TYPE_ERROR;
  554. pack.wSize = sizeof(TPacketGCWhisper) + len;
  555. strlcpy(pack.szNameFrom, pinfo->szNameTo, sizeof(pack.szNameFrom));
  556.  
  557. ch->GetDesc()->BufferedPacket(&pack, sizeof(pack));
  558. ch->GetDesc()->Packet(buf, len);
  559.  
  560. sys_log(0, "WHISPER: not enough %s: char: %s", pTable->szLocaleName, ch->GetName());
  561. }
  562. }
  563.  
  564. // ¸±·¡ÀÌ »óÅÂÀÏ ¼ö ÀÖÀ¸¹Ç·Î ¸±·¡À̸¦ Ç®¾îÁØ´Ù.
  565. pkDesc->SetRelay("");
  566. return (iExtraLen);
  567. }
  568.  
  569. if (ch->IsGM())
  570. bType = (bType & 0xF0) | WHISPER_TYPE_GM;
  571.  
  572. if (buflen > 0)
  573. {
  574. TPacketGCWhisper pack;
  575.  
  576. pack.bHeader = HEADER_GC_WHISPER;
  577. pack.wSize = sizeof(TPacketGCWhisper) + buflen;
  578. pack.bType = bType;
  579. strlcpy(pack.szNameFrom, ch->GetName(), sizeof(pack.szNameFrom));
  580.  
  581. // desc->BufferedPacketÀ» ÇÏÁö ¾Ê°í ¹öÆÛ¿¡ ½á¾ßÇÏ´Â ÀÌÀ¯´Â
  582. // P2P relayµÇ¾î ÆÐŶÀÌ Ä¸½¶È­ µÉ ¼ö Àֱ⠶§¹®ÀÌ´Ù.
  583. TEMP_BUFFER tmpbuf;
  584.  
  585. tmpbuf.write(&pack, sizeof(pack));
  586. tmpbuf.write(buf, buflen);
  587.  
  588. pkDesc->Packet(tmpbuf.read_peek(), tmpbuf.size());
  589.  
  590. // @warme006
  591. // sys_log(0, "WHISPER: %s -> %s : %s", ch->GetName(), pinfo->szNameTo, buf);
  592. #ifdef ENABLE_CHAT_LOGGING
  593. if (ch->IsGM())
  594. {
  595. LogManager::instance().EscapeString(__escape_string, sizeof(__escape_string), buf, buflen);
  596. LogManager::instance().EscapeString(__escape_string2, sizeof(__escape_string2), pinfo->szNameTo, sizeof(pack.szNameFrom));
  597. LogManager::instance().ChatLog(ch->GetMapIndex(), ch->GetPlayerID(), ch->GetName(), 0, __escape_string2, "WHISPER", __escape_string, ch->GetDesc() ? ch->GetDesc()->GetHostName() : "");
  598. }
  599. #endif
  600. }
  601. }
  602. }
  603. if(pkDesc)
  604. pkDesc->SetRelay("");
  605.  
  606. return (iExtraLen);
  607. }
  608.  
  609. struct RawPacketToCharacterFunc
  610. {
  611. const void * m_buf;
  612. int m_buf_len;
  613.  
  614. RawPacketToCharacterFunc(const void * buf, int buf_len) : m_buf(buf), m_buf_len(buf_len)
  615. {
  616. }
  617.  
  618. void operator () (LPCHARACTER c)
  619. {
  620. if (!c->GetDesc())
  621. return;
  622.  
  623. c->GetDesc()->Packet(m_buf, m_buf_len);
  624. }
  625. };
  626.  
  627. struct FEmpireChatPacket
  628. {
  629. packet_chat& p;
  630. const char* orig_msg;
  631. int orig_len;
  632. char converted_msg[CHAT_MAX_LEN+1];
  633.  
  634. BYTE bEmpire;
  635. int iMapIndex;
  636. int namelen;
  637.  
  638. FEmpireChatPacket(packet_chat& p, const char* chat_msg, int len, BYTE bEmpire, int iMapIndex, int iNameLen)
  639. : p(p), orig_msg(chat_msg), orig_len(len), bEmpire(bEmpire), iMapIndex(iMapIndex), namelen(iNameLen)
  640. {
  641. memset( converted_msg, 0, sizeof(converted_msg) );
  642. }
  643.  
  644. void operator () (LPDESC d)
  645. {
  646. if (!d->GetCharacter())
  647. return;
  648.  
  649. if (d->GetCharacter()->GetMapIndex() != iMapIndex)
  650. return;
  651.  
  652. d->BufferedPacket(&p, sizeof(packet_chat));
  653.  
  654. if (d->GetEmpire() == bEmpire ||
  655. bEmpire == 0 ||
  656. d->GetCharacter()->GetGMLevel() > GM_PLAYER ||
  657. d->GetCharacter()->IsEquipUniqueGroup(UNIQUE_GROUP_RING_OF_LANGUAGE))
  658. {
  659. d->Packet(orig_msg, orig_len);
  660. }
  661. else
  662. {
  663. // »ç¶÷¸¶´Ù ½ºÅ³·¹º§ÀÌ ´Ù¸£´Ï ¸Å¹ø ÇØ¾ßÇÕ´Ï´Ù
  664. size_t len = strlcpy(converted_msg, orig_msg, sizeof(converted_msg));
  665.  
  666. if (len >= sizeof(converted_msg))
  667. len = sizeof(converted_msg) - 1;
  668.  
  669. ConvertEmpireText(bEmpire, converted_msg + namelen, len - namelen, 10 + 2 * d->GetCharacter()->GetSkillPower(SKILL_LANGUAGE1 + bEmpire - 1));
  670. d->Packet(converted_msg, orig_len);
  671. }
  672. }
  673. };
  674.  
  675. struct FYmirChatPacket
  676. {
  677. packet_chat& packet;
  678. const char* m_szChat;
  679. size_t m_lenChat;
  680. const char* m_szName;
  681.  
  682. int m_iMapIndex;
  683. BYTE m_bEmpire;
  684. bool m_ring;
  685.  
  686. char m_orig_msg[CHAT_MAX_LEN+1];
  687. int m_len_orig_msg;
  688. char m_conv_msg[CHAT_MAX_LEN+1];
  689. int m_len_conv_msg;
  690.  
  691. FYmirChatPacket(packet_chat& p, const char* chat, size_t len_chat, const char* name, size_t len_name, int iMapIndex, BYTE empire, bool ring)
  692. : packet(p),
  693. m_szChat(chat), m_lenChat(len_chat),
  694. m_szName(name),
  695. m_iMapIndex(iMapIndex), m_bEmpire(empire),
  696. m_ring(ring)
  697. {
  698. m_len_orig_msg = snprintf(m_orig_msg, sizeof(m_orig_msg), "%s : %s", m_szName, m_szChat) + 1; // ³Î ¹®ÀÚ Æ÷ÇÔ
  699.  
  700. if (m_len_orig_msg < 0 || m_len_orig_msg >= (int) sizeof(m_orig_msg))
  701. m_len_orig_msg = sizeof(m_orig_msg) - 1;
  702.  
  703. m_len_conv_msg = snprintf(m_conv_msg, sizeof(m_conv_msg), "??? : %s", m_szChat) + 1; // ³Î ¹®ÀÚ ¹ÌÆ÷ÇÔ
  704.  
  705. if (m_len_conv_msg < 0 || m_len_conv_msg >= (int) sizeof(m_conv_msg))
  706. m_len_conv_msg = sizeof(m_conv_msg) - 1;
  707.  
  708. ConvertEmpireText(m_bEmpire, m_conv_msg + 6, m_len_conv_msg - 6, 10); // 6Àº "??? : "ÀÇ ±æÀÌ
  709. }
  710.  
  711. void operator() (LPDESC d)
  712. {
  713. if (!d->GetCharacter())
  714. return;
  715.  
  716. if (d->GetCharacter()->GetMapIndex() != m_iMapIndex)
  717. return;
  718.  
  719. if (m_ring ||
  720. d->GetEmpire() == m_bEmpire ||
  721. d->GetCharacter()->GetGMLevel() > GM_PLAYER ||
  722. d->GetCharacter()->IsEquipUniqueGroup(UNIQUE_GROUP_RING_OF_LANGUAGE))
  723. {
  724. packet.size = m_len_orig_msg + sizeof(TPacketGCChat);
  725.  
  726. d->BufferedPacket(&packet, sizeof(packet_chat));
  727. d->Packet(m_orig_msg, m_len_orig_msg);
  728. }
  729. else
  730. {
  731. packet.size = m_len_conv_msg + sizeof(TPacketGCChat);
  732.  
  733. d->BufferedPacket(&packet, sizeof(packet_chat));
  734. d->Packet(m_conv_msg, m_len_conv_msg);
  735. }
  736. }
  737. };
  738.  
  739. #ifdef NEW_PET_SYSTEM
  740. #include "db.h"
  741. void CInputMain::BraveRequestPetName(LPCHARACTER ch, const char* c_pData)
  742. {
  743. if (!ch->GetDesc()) { return; }
  744. int vid = ch->GetEggVid();
  745. if (vid == 0) { return; }
  746.  
  747. TPacketCGRequestPetName* p = (TPacketCGRequestPetName*)c_pData;
  748.  
  749. if (ch->GetGold() < 100000) {
  750. ch->ChatPacket(CHAT_TYPE_INFO, "[PetSystem] Ai nevoie de 100.000 yang");
  751. }
  752.  
  753. if (ch->CountSpecifyItem(vid) > 0 && check_name(p->petname) != 0) {
  754. DBManager::instance().SendMoneyLog(MONEY_LOG_QUEST, ch->GetPlayerID(), -100000);
  755. ch->PointChange(POINT_GOLD, -100000, true);
  756. ch->RemoveSpecifyItem(vid, 1);
  757. LPITEM item = ch->AutoGiveItem(vid + 300, 1);
  758. int tmpslot = number(3, 3);
  759. int tmpskill[3] = { 0, 0, 0 };
  760. for (int i = 0; i < 3; ++i)
  761. {
  762. if (i > tmpslot - 1)
  763. tmpskill[i] = -1;
  764. }
  765. int tmpdur = number(14, 14) * 24 * 60;
  766. char szQuery1[1024];
  767. snprintf(szQuery1, sizeof(szQuery1), "INSERT INTO new_petsystem VALUES(%lu,'%s', 1, 0, 0, 0, %d, %d, %d, %d, %d, %d, %d, %d, %d, %d, %d)", item->GetID(), p->petname, number(23, 23), number(23, 23), number(23, 23), tmpskill[0], 0, tmpskill[1], 0, tmpskill[2], 0, tmpdur, tmpdur);
  768. std::unique_ptr<SQLMsg> pmsg2(DBManager::instance().DirectQuery(szQuery1));
  769. }
  770. else {
  771. ch->ChatPacket(CHAT_TYPE_INFO, "[PetSystem]Eroare in setarea numelui");
  772. }
  773. }
  774. #endif
  775.  
  776. int CInputMain::Chat(LPCHARACTER ch, const char * data, size_t uiBytes)
  777. {
  778. const TPacketCGChat* pinfo = reinterpret_cast<const TPacketCGChat*>(data);
  779.  
  780. if (uiBytes < pinfo->size)
  781. return -1;
  782.  
  783. const int iExtraLen = pinfo->size - sizeof(TPacketCGChat);
  784.  
  785. if (iExtraLen < 0)
  786. {
  787. sys_err("invalid packet length (len %d size %u buffer %u)", iExtraLen, pinfo->size, uiBytes);
  788. ch->GetDesc()->SetPhase(PHASE_CLOSE);
  789. return -1;
  790. }
  791.  
  792. char buf[CHAT_MAX_LEN - (CHARACTER_NAME_MAX_LEN + 3) + 1];
  793. strlcpy(buf, data + sizeof(TPacketCGChat), MIN(iExtraLen + 1, sizeof(buf)));
  794. const size_t buflen = strlen(buf);
  795.  
  796. if (buflen > 1 && *buf == '/')
  797. {
  798. interpret_command(ch, buf + 1, buflen - 1);
  799. return iExtraLen;
  800. }
  801. #ifdef ENABLE_CHAT_SPAMLIMIT
  802. if (ch->IncreaseChatCounter() >= 4)
  803. {
  804. if (ch->GetChatCounter() == 10)
  805. ch->GetDesc()->DelayedDisconnect(0);
  806. return iExtraLen;
  807. }
  808. #else
  809. if (ch->IncreaseChatCounter() >= 10)
  810. {
  811. if (ch->GetChatCounter() == 10)
  812. {
  813. sys_log(0, "CHAT_HACK: %s", ch->GetName());
  814. ch->GetDesc()->DelayedDisconnect(5);
  815. }
  816.  
  817. return iExtraLen;
  818. }
  819. #endif
  820.  
  821. #ifdef __ENABLE_BATTLE_FIELD__
  822. if (CBattleZone::instance().IsBattleZoneMapIndex(ch->GetMapIndex()))
  823. {
  824. ch->ChatPacket(CHAT_TYPE_INFO, LC_TEXT("BATTLE_ZONE_CANT_CHAT"));
  825. return iExtraLen;
  826. }
  827. #endif
  828.  
  829. // äÆÃ ±ÝÁö Affect ó¸®
  830. const CAffect* pAffect = ch->FindAffect(AFFECT_BLOCK_CHAT);
  831.  
  832. if (pAffect != NULL)
  833. {
  834. SendBlockChatInfo(ch, pAffect->lDuration);
  835. return iExtraLen;
  836. }
  837.  
  838. if (true == SpamBlockCheck(ch, buf, buflen))
  839. {
  840. return iExtraLen;
  841. }
  842.  
  843. // @fixme133 begin
  844. CBanwordManager::instance().ConvertString(buf, buflen);
  845.  
  846. int processReturn = ProcessTextTag(ch, buf, buflen);
  847. if (0!=processReturn)
  848. {
  849. const TItemTable* pTable = ITEM_MANAGER::instance().GetTable(ITEM_PRISM);
  850.  
  851. if (NULL != pTable)
  852. {
  853. if (3==processReturn) //±³È¯Áß
  854. ch->ChatPacket(CHAT_TYPE_INFO, LC_TEXT("»ç¿ëÇÒ¼ö ¾ø½À´Ï´Ù."), pTable->szLocaleName);
  855. else
  856. ch->ChatPacket(CHAT_TYPE_INFO, LC_TEXT("%sÀÌ ÇÊ¿äÇÕ´Ï´Ù."), pTable->szLocaleName);
  857.  
  858. }
  859.  
  860. return iExtraLen;
  861. }
  862. // @fixme133 end
  863.  
  864. char chatbuf[CHAT_MAX_LEN + 1];
  865. int len;
  866. if (pinfo->type == CHAT_TYPE_SHOUT)
  867. {
  868. len = snprintf(chatbuf, sizeof(chatbuf), "|Hmsg:%s|h%s|h|r : %s", ch->GetName(), ch->GetName(), buf);
  869. }
  870. else
  871. {
  872. len = snprintf(chatbuf, sizeof(chatbuf), "%s : %s", ch->GetName(), buf);
  873. }
  874.  
  875. if (CHAT_TYPE_SHOUT == pinfo->type)
  876. {
  877. LogManager::instance().ShoutLog(g_bChannel, ch->GetEmpire(), chatbuf);
  878. }
  879.  
  880. if (len < 0 || len >= (int) sizeof(chatbuf))
  881. len = sizeof(chatbuf) - 1;
  882.  
  883. if (pinfo->type == CHAT_TYPE_SHOUT)
  884. {
  885. // const int SHOUT_LIMIT_LEVEL = 15;
  886.  
  887. if (ch->GetLevel() < g_iShoutLimitLevel)
  888. {
  889. ch->ChatPacket(CHAT_TYPE_INFO, LC_TEXT("???? ?? %d ??? ?? ?? ???."), g_iShoutLimitLevel);
  890. return (iExtraLen);
  891. }
  892.  
  893. // if (thecore_heart->pulse - (int) ch->GetLastShoutPulse() < passes_per_sec * g_iShoutLimitTime)
  894. if (thecore_heart->pulse - (int) ch->GetLastShoutPulse() < passes_per_sec * 15)
  895. return (iExtraLen);
  896.  
  897. ch->SetLastShoutPulse(thecore_heart->pulse);
  898.  
  899. char chatbuf_global[CHAT_MAX_LEN + 1];
  900.  
  901. #if defined(ENABLE_GLOBAL_CHAT) // FLAG IMAGES SYSTEM
  902.  
  903. const char* kingdoms[3] = {"[1] ","[2] ","[3] "};
  904.  
  905. if(ch->GetEmpire() > 0 && ch->GetEmpire() == 1 or ch->GetEmpire() == 2 or ch->GetEmpire() == 3 ) {
  906. int len_global = snprintf(chatbuf_global, sizeof(chatbuf_global), "%s%s",kingdoms[ch->GetEmpire()-1], chatbuf);
  907. }
  908.  
  909. else {
  910. int len_global = snprintf(chatbuf_global, sizeof(chatbuf_global), "%s", chatbuf);
  911. }
  912.  
  913. #endif
  914.  
  915. TPacketGGShout p;
  916.  
  917. p.bHeader = HEADER_GG_SHOUT;
  918. p.bEmpire = ch->GetEmpire();
  919. strlcpy(p.szText, chatbuf_global, sizeof(p.szText));
  920.  
  921. P2P_MANAGER::instance().Send(&p, sizeof(TPacketGGShout));
  922.  
  923. SendShout(chatbuf_global, ch->GetEmpire());
  924.  
  925. return (iExtraLen);
  926. }
  927.  
  928. TPacketGCChat pack_chat;
  929.  
  930. pack_chat.header = HEADER_GC_CHAT;
  931. pack_chat.size = sizeof(TPacketGCChat) + len;
  932. pack_chat.type = pinfo->type;
  933. pack_chat.id = ch->GetVID();
  934.  
  935. switch (pinfo->type)
  936. {
  937. case CHAT_TYPE_TALKING:
  938. {
  939. const DESC_MANAGER::DESC_SET & c_ref_set = DESC_MANAGER::instance().GetClientSet();
  940.  
  941. if (false)
  942. {
  943. std::for_each(c_ref_set.begin(), c_ref_set.end(),
  944. FYmirChatPacket(pack_chat,
  945. buf,
  946. strlen(buf),
  947. ch->GetName(),
  948. strlen(ch->GetName()),
  949. ch->GetMapIndex(),
  950. ch->GetEmpire(),
  951. ch->IsEquipUniqueGroup(UNIQUE_GROUP_RING_OF_LANGUAGE)));
  952. }
  953. else
  954. {
  955. std::for_each(c_ref_set.begin(), c_ref_set.end(),
  956. FEmpireChatPacket(pack_chat,
  957. chatbuf,
  958. len,
  959. (ch->GetGMLevel() > GM_PLAYER ||
  960. ch->IsEquipUniqueGroup(UNIQUE_GROUP_RING_OF_LANGUAGE)) ? 0 : ch->GetEmpire(),
  961. ch->GetMapIndex(), strlen(ch->GetName())));
  962. #ifdef ENABLE_CHAT_LOGGING
  963. if (ch->IsGM())
  964. {
  965. LogManager::instance().EscapeString(__escape_string, sizeof(__escape_string), chatbuf, len);
  966. LogManager::instance().ChatLog(ch->GetMapIndex(), ch->GetPlayerID(), ch->GetName(), 0, "", "NORMAL", __escape_string, ch->GetDesc() ? ch->GetDesc()->GetHostName() : "");
  967. }
  968. #endif
  969. }
  970. }
  971. break;
  972.  
  973. case CHAT_TYPE_PARTY:
  974. {
  975. if (!ch->GetParty())
  976. ch->ChatPacket(CHAT_TYPE_INFO, LC_TEXT("ÆÄƼ ÁßÀÌ ¾Æ´Õ´Ï´Ù."));
  977. else
  978. {
  979. TEMP_BUFFER tbuf;
  980.  
  981. tbuf.write(&pack_chat, sizeof(pack_chat));
  982. tbuf.write(chatbuf, len);
  983.  
  984. RawPacketToCharacterFunc f(tbuf.read_peek(), tbuf.size());
  985. ch->GetParty()->ForEachOnlineMember(f);
  986. #ifdef ENABLE_CHAT_LOGGING
  987. if (ch->IsGM())
  988. {
  989. LogManager::instance().EscapeString(__escape_string, sizeof(__escape_string), chatbuf, len);
  990. LogManager::instance().ChatLog(ch->GetMapIndex(), ch->GetPlayerID(), ch->GetName(), ch->GetParty()->GetLeaderPID(), "", "PARTY", __escape_string, ch->GetDesc() ? ch->GetDesc()->GetHostName() : "");
  991. }
  992. #endif
  993. }
  994. }
  995. break;
  996.  
  997. case CHAT_TYPE_GUILD:
  998. {
  999. if (!ch->GetGuild())
  1000. ch->ChatPacket(CHAT_TYPE_INFO, LC_TEXT("±æµå¿¡ °¡ÀÔÇÏÁö ¾Ê¾Ò½À´Ï´Ù."));
  1001. else
  1002. {
  1003. ch->GetGuild()->Chat(chatbuf);
  1004. #ifdef ENABLE_CHAT_LOGGING
  1005. if (ch->IsGM())
  1006. {
  1007. LogManager::instance().EscapeString(__escape_string, sizeof(__escape_string), chatbuf, len);
  1008. LogManager::instance().ChatLog(ch->GetMapIndex(), ch->GetPlayerID(), ch->GetName(), ch->GetGuild()->GetID(), ch->GetGuild()->GetName(), "GUILD", __escape_string, ch->GetDesc() ? ch->GetDesc()->GetHostName() : "");
  1009. }
  1010. #endif
  1011. }
  1012. }
  1013. break;
  1014.  
  1015. default:
  1016. sys_err("Unknown chat type %d", pinfo->type);
  1017. break;
  1018. }
  1019.  
  1020. return (iExtraLen);
  1021. }
  1022.  
  1023. void CInputMain::ItemUse(LPCHARACTER ch, const char * data)
  1024. {
  1025. ch->UseItem(((struct command_item_use *) data)->Cell);
  1026. }
  1027.  
  1028. void CInputMain::ItemToItem(LPCHARACTER ch, const char * pcData)
  1029. {
  1030. TPacketCGItemUseToItem * p = (TPacketCGItemUseToItem *) pcData;
  1031. if (ch)
  1032. ch->UseItem(p->Cell, p->TargetCell);
  1033. }
  1034.  
  1035. void CInputMain::ItemDrop(LPCHARACTER ch, const char * data)
  1036. {
  1037. struct command_item_drop * pinfo = (struct command_item_drop *) data;
  1038.  
  1039. //MONARCH_LIMIT
  1040. //if (ch->IsMonarch())
  1041. // return;
  1042. //END_MONARCH_LIMIT
  1043. if (!ch)
  1044. return;
  1045.  
  1046. // ¿¤Å©°¡ 0º¸´Ù Å©¸é ¿¤Å©¸¦ ¹ö¸®´Â °Í ÀÌ´Ù.
  1047. if (pinfo->gold > 0)
  1048. ch->DropGold(pinfo->gold);
  1049. else
  1050. ch->DropItem(pinfo->Cell);
  1051. }
  1052.  
  1053. void CInputMain::ItemDrop2(LPCHARACTER ch, const char * data)
  1054. {
  1055. //MONARCH_LIMIT
  1056. //if (ch->IsMonarch())
  1057. // return;
  1058. //END_MONARCH_LIMIT
  1059.  
  1060. TPacketCGItemDrop2 * pinfo = (TPacketCGItemDrop2 *) data;
  1061.  
  1062. // ¿¤Å©°¡ 0º¸´Ù Å©¸é ¿¤Å©¸¦ ¹ö¸®´Â °Í ÀÌ´Ù.
  1063.  
  1064. if (!ch)
  1065. return;
  1066. if (pinfo->gold > 0)
  1067. ch->DropGold(pinfo->gold);
  1068. else
  1069. ch->DropItem(pinfo->Cell, pinfo->count);
  1070. }
  1071.  
  1072. void CInputMain::ItemDestroy(LPCHARACTER ch, const char * data)
  1073. {
  1074. struct command_item_destroy * pinfo = (struct command_item_destroy *) data;
  1075. if (ch)
  1076. ch->DestroyItem(pinfo->Cell);
  1077. }
  1078.  
  1079. void CInputMain::ItemMove(LPCHARACTER ch, const char * data)
  1080. {
  1081. struct command_item_move * pinfo = (struct command_item_move *) data;
  1082.  
  1083. if (ch)
  1084. ch->MoveItem(pinfo->Cell, pinfo->CellTo, pinfo->count);
  1085. }
  1086.  
  1087. void CInputMain::ItemPickup(LPCHARACTER ch, const char * data)
  1088. {
  1089. struct command_item_pickup * pinfo = (struct command_item_pickup*) data;
  1090. if (ch)
  1091. ch->PickupItem(pinfo->vid);
  1092. }
  1093. #if defined(WHEEL_OF_DESTINY)
  1094. void CInputMain::WheelDestiny(LPCHARACTER ch, const char* data)
  1095. {
  1096. if (!ch)
  1097. return;
  1098.  
  1099. const auto pinfo = reinterpret_cast<const TPacketCGWheelDestiny*>(data);
  1100. enum { OPEN, CLOSE, TURN, GIVE };
  1101.  
  1102. switch (pinfo->option) {
  1103. case OPEN:
  1104. if (!ch->GetWheelDestiny())
  1105. ch->SetWheelDestiny(std::make_shared<CWheelDestiny>(ch));
  1106. break;
  1107. case CLOSE:
  1108. if (ch->GetWheelDestiny()) {
  1109. if (ch->GetWheelDestiny()->GetGiftVnum())
  1110. ch->ChatPacket(CHAT_TYPE_INFO, "Wait motherfucker!");
  1111. else
  1112. {
  1113. ch->SetWheelDestiny(nullptr);
  1114. ch->ChatPacket(CHAT_TYPE_COMMAND, "BINARY_WHEEL_CLOSE");
  1115. }
  1116. }
  1117. break;
  1118. case TURN:
  1119. if (ch->GetWheelDestiny())
  1120. ch->GetWheelDestiny()->TurnWheel();
  1121. break;
  1122. case GIVE:
  1123. if (ch->GetWheelDestiny())
  1124. ch->GetWheelDestiny()->GiveMyFuckingGift();
  1125. break;
  1126. default:
  1127. sys_err("CInputMain::WheelDestiny : Unknown option %d : %s", pinfo->option, ch->GetName());
  1128. break;
  1129. }
  1130. }
  1131. #endif
  1132.  
  1133. void CInputMain::QuickslotAdd(LPCHARACTER ch, const char * data)
  1134. {
  1135. struct command_quickslot_add * pinfo = (struct command_quickslot_add *) data;
  1136. ch->SetQuickslot(pinfo->pos, pinfo->slot);
  1137. }
  1138.  
  1139. void CInputMain::QuickslotDelete(LPCHARACTER ch, const char * data)
  1140. {
  1141. struct command_quickslot_del * pinfo = (struct command_quickslot_del *) data;
  1142. ch->DelQuickslot(pinfo->pos);
  1143. }
  1144.  
  1145. void CInputMain::QuickslotSwap(LPCHARACTER ch, const char * data)
  1146. {
  1147. struct command_quickslot_swap * pinfo = (struct command_quickslot_swap *) data;
  1148. ch->SwapQuickslot(pinfo->pos, pinfo->change_pos);
  1149. }
  1150.  
  1151. int CInputMain::Messenger(LPCHARACTER ch, const char* c_pData, size_t uiBytes)
  1152. {
  1153. TPacketCGMessenger* p = (TPacketCGMessenger*) c_pData;
  1154.  
  1155. if (uiBytes < sizeof(TPacketCGMessenger))
  1156. return -1;
  1157.  
  1158. c_pData += sizeof(TPacketCGMessenger);
  1159. uiBytes -= sizeof(TPacketCGMessenger);
  1160.  
  1161. switch (p->subheader)
  1162. {
  1163. case MESSENGER_SUBHEADER_CG_ADD_BY_VID:
  1164. {
  1165. if (uiBytes < sizeof(TPacketCGMessengerAddByVID))
  1166. return -1;
  1167.  
  1168. TPacketCGMessengerAddByVID * p2 = (TPacketCGMessengerAddByVID *) c_pData;
  1169. LPCHARACTER ch_companion = CHARACTER_MANAGER::instance().Find(p2->vid);
  1170.  
  1171. if (!ch_companion)
  1172. return sizeof(TPacketCGMessengerAddByVID);
  1173.  
  1174. if (ch->IsObserverMode())
  1175. return sizeof(TPacketCGMessengerAddByVID);
  1176.  
  1177. if (ch_companion->IsBlockMode(BLOCK_MESSENGER_INVITE))
  1178. {
  1179. ch->ChatPacket(CHAT_TYPE_INFO, LC_TEXT("»ó´ë¹æÀÌ ¸Þ½ÅÁ® Ãß°¡ °ÅºÎ »óÅÂÀÔ´Ï´Ù."));
  1180. return sizeof(TPacketCGMessengerAddByVID);
  1181. }
  1182.  
  1183. LPDESC d = ch_companion->GetDesc();
  1184.  
  1185. if (!d)
  1186. return sizeof(TPacketCGMessengerAddByVID);
  1187.  
  1188. if (ch->GetGMLevel() == GM_PLAYER && ch_companion->GetGMLevel() != GM_PLAYER)
  1189. {
  1190. ch->ChatPacket(CHAT_TYPE_INFO, LC_TEXT("<¸Þ½ÅÁ®> ¿î¿µÀÚ´Â ¸Þ½ÅÁ®¿¡ Ãß°¡ÇÒ ¼ö ¾ø½À´Ï´Ù."));
  1191. return sizeof(TPacketCGMessengerAddByVID);
  1192. }
  1193.  
  1194. #ifdef __ENABLE_BATTLE_FIELD__
  1195. if (CBattleZone::instance().IsBattleZoneMapIndex(ch->GetMapIndex()))
  1196. {
  1197. ch->ChatPacket(CHAT_TYPE_INFO, LC_TEXT("BATTLE_ZONE_CANT_ADD_FRIEND"));
  1198. return sizeof(TPacketCGMessengerAddByVID);
  1199. }
  1200. #endif
  1201.  
  1202. if (ch->GetDesc() == d) // ÀÚ½ÅÀº Ãß°¡ÇÒ ¼ö ¾ø´Ù.
  1203. return sizeof(TPacketCGMessengerAddByVID);
  1204.  
  1205. MessengerManager::instance().RequestToAdd(ch, ch_companion);
  1206. //MessengerManager::instance().AddToList(ch->GetName(), ch_companion->GetName());
  1207. }
  1208. return sizeof(TPacketCGMessengerAddByVID);
  1209.  
  1210. case MESSENGER_SUBHEADER_CG_ADD_BY_NAME:
  1211. {
  1212. if (uiBytes < CHARACTER_NAME_MAX_LEN)
  1213. return -1;
  1214.  
  1215. char name[CHARACTER_NAME_MAX_LEN + 1];
  1216. strlcpy(name, c_pData, sizeof(name));
  1217.  
  1218. if (ch->GetGMLevel() == GM_PLAYER && gm_get_level(name) != GM_PLAYER)
  1219. {
  1220. ch->ChatPacket(CHAT_TYPE_INFO, LC_TEXT("<¸Þ½ÅÁ®> ¿î¿µÀÚ´Â ¸Þ½ÅÁ®¿¡ Ãß°¡ÇÒ ¼ö ¾ø½À´Ï´Ù."));
  1221. return CHARACTER_NAME_MAX_LEN;
  1222. }
  1223.  
  1224. #ifdef __ENABLE_BATTLE_FIELD__
  1225. if (CBattleZone::instance().IsBattleZoneMapIndex(ch->GetMapIndex()))
  1226. {
  1227. ch->ChatPacket(CHAT_TYPE_INFO, LC_TEXT("BATTLE_ZONE_CANT_ADD_FRIEND"));
  1228. return CHARACTER_NAME_MAX_LEN;
  1229. }
  1230. #endif
  1231.  
  1232. LPCHARACTER tch = CHARACTER_MANAGER::instance().FindPC(name);
  1233.  
  1234. if (!tch)
  1235. ch->ChatPacket(CHAT_TYPE_INFO, LC_TEXT("%s ´ÔÀº Á¢¼ÓµÇ ÀÖÁö ¾Ê½À´Ï´Ù."), name);
  1236. else
  1237. {
  1238. if (tch == ch) // ÀÚ½ÅÀº Ãß°¡ÇÒ ¼ö ¾ø´Ù.
  1239. return CHARACTER_NAME_MAX_LEN;
  1240.  
  1241. if (tch->IsBlockMode(BLOCK_MESSENGER_INVITE) == true)
  1242. {
  1243. ch->ChatPacket(CHAT_TYPE_INFO, LC_TEXT("»ó´ë¹æÀÌ ¸Þ½ÅÁ® Ãß°¡ °ÅºÎ »óÅÂÀÔ´Ï´Ù."));
  1244. }
  1245. else
  1246. {
  1247. // ¸Þ½ÅÀú°¡ ij¸¯ÅÍ´ÜÀ§°¡ µÇ¸é¼­ º¯°æ
  1248. MessengerManager::instance().RequestToAdd(ch, tch);
  1249. //MessengerManager::instance().AddToList(ch->GetName(), tch->GetName());
  1250. }
  1251. }
  1252. }
  1253. return CHARACTER_NAME_MAX_LEN;
  1254.  
  1255. case MESSENGER_SUBHEADER_CG_REMOVE:
  1256. {
  1257. if (uiBytes < CHARACTER_NAME_MAX_LEN)
  1258. return -1;
  1259.  
  1260. char char_name[CHARACTER_NAME_MAX_LEN + 1];
  1261. strlcpy(char_name, c_pData, sizeof(char_name));
  1262. MessengerManager::instance().RemoveFromList(ch->GetName(), char_name);
  1263. }
  1264. return CHARACTER_NAME_MAX_LEN;
  1265.  
  1266. default:
  1267. sys_err("CInputMain::Messenger : Unknown subheader %d : %s", p->subheader, ch->GetName());
  1268. break;
  1269. }
  1270.  
  1271. return 0;
  1272. }
  1273.  
  1274. int CInputMain::Shop(LPCHARACTER ch, const char * data, size_t uiBytes)
  1275. {
  1276. TPacketCGShop * p = (TPacketCGShop *) data;
  1277.  
  1278. if (uiBytes < sizeof(TPacketCGShop))
  1279. return -1;
  1280.  
  1281. if (test_server)
  1282. sys_log(0, "CInputMain::Shop() ==> SubHeader %d", p->subheader);
  1283.  
  1284. const char * c_pData = data + sizeof(TPacketCGShop);
  1285. uiBytes -= sizeof(TPacketCGShop);
  1286.  
  1287. switch (p->subheader)
  1288. {
  1289. case SHOP_SUBHEADER_CG_END:
  1290. sys_log(1, "INPUT: %s SHOP: END", ch->GetName());
  1291. CShopManager::instance().StopShopping(ch);
  1292. return 0;
  1293.  
  1294. case SHOP_SUBHEADER_CG_BUY:
  1295. {
  1296. if (uiBytes < sizeof(BYTE) + sizeof(BYTE))
  1297. return -1;
  1298.  
  1299. BYTE bPos = *(c_pData + 1);
  1300. sys_log(1, "INPUT: %s SHOP: BUY %d", ch->GetName(), bPos);
  1301. CShopManager::instance().Buy(ch, bPos);
  1302. return (sizeof(BYTE) + sizeof(BYTE));
  1303. }
  1304.  
  1305. case SHOP_SUBHEADER_CG_SELL:
  1306. {
  1307. if (uiBytes < sizeof(BYTE))
  1308. return -1;
  1309.  
  1310. BYTE pos = *c_pData;
  1311.  
  1312. sys_log(0, "INPUT: %s SHOP: SELL", ch->GetName());
  1313. CShopManager::instance().Sell(ch, pos);
  1314. return sizeof(BYTE);
  1315. }
  1316.  
  1317. #ifdef __SPECIAL_STORAGE__
  1318. case SHOP_SUBHEADER_CG_SELL2:
  1319. {
  1320. if (uiBytes < sizeof(BYTE) + sizeof(BYTE) + sizeof(BYTE))
  1321. return -1;
  1322.  
  1323. const BYTE wPos = *reinterpret_cast<const BYTE*>(c_pData);
  1324. const BYTE bCount = *(c_pData + sizeof(BYTE));
  1325. const BYTE bType = *(c_pData + sizeof(BYTE) + sizeof(BYTE));
  1326.  
  1327. sys_log(0, "INPUT: %s SHOP: SELL2", ch->GetName());
  1328.  
  1329. CShopManager::instance().Sell(ch, wPos, bCount, bType);
  1330. return sizeof(BYTE) + sizeof(BYTE) + sizeof(BYTE);
  1331. }
  1332. #else
  1333. case SHOP_SUBHEADER_CG_SELL2:
  1334. {
  1335. if (uiBytes < sizeof(BYTE) + sizeof(BYTE))
  1336. return -1;
  1337.  
  1338. BYTE pos = *(c_pData++);
  1339. BYTE count = *(c_pData);
  1340.  
  1341. sys_log(0, "INPUT: %s SHOP: SELL2", ch->GetName());
  1342. CShopManager::instance().Sell(ch, pos, count);
  1343. return sizeof(BYTE) + sizeof(BYTE);
  1344. }
  1345. #endif
  1346.  
  1347. default:
  1348. sys_err("CInputMain::Shop : Unknown subheader %d : %s", p->subheader, ch->GetName());
  1349. break;
  1350. }
  1351.  
  1352. return 0;
  1353. }
  1354.  
  1355. void CInputMain::OnClick(LPCHARACTER ch, const char * data)
  1356. {
  1357. struct command_on_click * pinfo = (struct command_on_click *) data;
  1358. LPCHARACTER victim;
  1359.  
  1360. if ((victim = CHARACTER_MANAGER::instance().Find(pinfo->vid)))
  1361. victim->OnClick(ch);
  1362. else if (test_server)
  1363. {
  1364. sys_err("CInputMain::OnClick %s.Click.NOT_EXIST_VID[%d]", ch->GetName(), pinfo->vid);
  1365. }
  1366. }
  1367. #ifdef ENABLE_FISH_EVENT
  1368. int CInputMain::FishEvent(LPCHARACTER ch, const char * data, size_t uiBytes)
  1369. {
  1370. TPacketCGFishEvent * p = (TPacketCGFishEvent *) data;
  1371.  
  1372. if (uiBytes < sizeof(TPacketCGFishEvent))
  1373. return -1;
  1374.  
  1375. const char * c_pData = data + sizeof(TPacketCGFishEvent);
  1376. uiBytes -= sizeof(TPacketCGFishEvent);
  1377.  
  1378. switch (p->bSubheader)
  1379. {
  1380. case FISH_EVENT_SUBHEADER_BOX_USE:
  1381. {
  1382. if (uiBytes < sizeof(BYTE) + sizeof(WORD))
  1383. return -1;
  1384.  
  1385. BYTE bWindow = *(c_pData++);
  1386. WORD wCell = *(c_pData);
  1387.  
  1388. sys_log(0, "INPUT: %s FISH_EVENT: USE_BOX", ch->GetName());
  1389.  
  1390. ch->FishEventUseBox(TItemPos(bWindow, wCell));
  1391. return (sizeof(BYTE) + sizeof(WORD));
  1392. }
  1393.  
  1394. case FISH_EVENT_SUBHEADER_SHAPE_ADD:
  1395. {
  1396. if (uiBytes < sizeof(BYTE))
  1397. return -1;
  1398.  
  1399. BYTE shapePos = *c_pData;
  1400.  
  1401. sys_log(0, "INPUT: %s FISH_EVENT: ADD_SHAPE", ch->GetName());
  1402.  
  1403. ch->FishEventAddShape(shapePos);
  1404. return sizeof(BYTE);
  1405. }
  1406.  
  1407. default:
  1408. sys_err("CInputMain::FishEvent : Unknown subheader %d : %s", p->bSubheader, ch->GetName());
  1409. break;
  1410. }
  1411.  
  1412. return 0;
  1413. }
  1414. #endif
  1415. #ifdef ENABLE_GEM_SYSTEM
  1416. int CInputMain::GemShop(LPCHARACTER ch, const char * data, size_t uiBytes)
  1417. {
  1418. TPacketCGGemShop * p = (TPacketCGGemShop *) data;
  1419.  
  1420. if (uiBytes < sizeof(TPacketCGGemShop))
  1421. return -1;
  1422.  
  1423. const char * c_pData = data + sizeof(TPacketCGGemShop);
  1424. uiBytes -= sizeof(TPacketCGGemShop);
  1425.  
  1426. switch (p->subheader)
  1427. {
  1428. case GEM_SHOP_SUBHEADER_CG_BUY:
  1429. {
  1430. if (uiBytes < sizeof(BYTE))
  1431. return -1;
  1432.  
  1433. BYTE bPos = *c_pData;
  1434.  
  1435. sys_log(1, "INPUT: %s GEM_SHOP: BUY %d", ch->GetName(), bPos);
  1436. ch->GemShopBuy(bPos);
  1437. return sizeof(BYTE);
  1438. }
  1439.  
  1440. case GEM_SHOP_SUBHEADER_CG_ADD:
  1441. {
  1442. if (uiBytes < sizeof(BYTE))
  1443. return -1;
  1444.  
  1445. BYTE bPos = *c_pData;
  1446.  
  1447. sys_log(1, "INPUT: %s GEM_SHOP: ADD %d", ch->GetName(), bPos);
  1448. ch->GemShopAdd(bPos);
  1449. return sizeof(BYTE);
  1450. }
  1451.  
  1452. case GEM_SHOP_SUBHEADER_CG_REFRESH:
  1453. sys_log(1, "INPUT: %s GEM_SHOP: REFRESH", ch->GetName());
  1454. ch->RefreshGemShopWithItem();
  1455. return 0;
  1456.  
  1457. default:
  1458. sys_err("CInputMain::GemShop() : Unknown subheader %d : %s", p->subheader, ch->GetName());
  1459. break;
  1460. }
  1461.  
  1462. return 0;
  1463. }
  1464. #endif
  1465.  
  1466. void CInputMain::Exchange(LPCHARACTER ch, const char * data)
  1467. {
  1468. struct command_exchange * pinfo = (struct command_exchange *) data;
  1469. LPCHARACTER to_ch = NULL;
  1470.  
  1471. if (!ch->CanHandleItem())
  1472. return;
  1473.  
  1474. int iPulse = thecore_pulse();
  1475.  
  1476. if ((to_ch = CHARACTER_MANAGER::instance().Find(pinfo->arg1)))
  1477. {
  1478. if (iPulse - to_ch->GetSafeboxLoadTime() < PASSES_PER_SEC(g_nPortalLimitTime))
  1479. {
  1480. to_ch->ChatPacket(CHAT_TYPE_INFO, LC_TEXT("°Å·¡ ÈÄ %dÃÊ À̳»¿¡ â°í¸¦ ¿­¼ö ¾ø½À´Ï´Ù."), g_nPortalLimitTime);
  1481. return;
  1482. }
  1483.  
  1484. if( true == to_ch->IsDead() )
  1485. {
  1486. return;
  1487. }
  1488. }
  1489.  
  1490. sys_log(0, "CInputMain()::Exchange() SubHeader %d ", pinfo->sub_header);
  1491.  
  1492. if (iPulse - ch->GetSafeboxLoadTime() < PASSES_PER_SEC(g_nPortalLimitTime))
  1493. {
  1494. ch->ChatPacket(CHAT_TYPE_INFO, LC_TEXT("°Å·¡ ÈÄ %dÃÊ À̳»¿¡ â°í¸¦ ¿­¼ö ¾ø½À´Ï´Ù."), g_nPortalLimitTime);
  1495. return;
  1496. }
  1497.  
  1498.  
  1499. switch (pinfo->sub_header)
  1500. {
  1501. case EXCHANGE_SUBHEADER_CG_START: // arg1 == vid of target character
  1502. if (!ch->GetExchange())
  1503. {
  1504. if ((to_ch = CHARACTER_MANAGER::instance().Find(pinfo->arg1)))
  1505. {
  1506. //MONARCH_LIMIT
  1507. /*
  1508. if (to_ch->IsMonarch() || ch->IsMonarch())
  1509. {
  1510. ch->ChatPacket(CHAT_TYPE_INFO, LC_TEXT("±ºÁÖ¿Í´Â °Å·¡¸¦ ÇÒ¼ö°¡ ¾ø½À´Ï´Ù"), g_nPortalLimitTime);
  1511. return;
  1512. }
  1513. //END_MONARCH_LIMIT
  1514. */
  1515. if (iPulse - ch->GetSafeboxLoadTime() < PASSES_PER_SEC(g_nPortalLimitTime))
  1516. {
  1517. ch->ChatPacket(CHAT_TYPE_INFO, LC_TEXT("â°í¸¦ ¿¬ÈÄ %dÃÊ À̳»¿¡´Â °Å·¡¸¦ ÇÒ¼ö ¾ø½À´Ï´Ù."), g_nPortalLimitTime);
  1518.  
  1519. if (test_server)
  1520. ch->ChatPacket(CHAT_TYPE_INFO, "[TestOnly][Safebox]Pulse %d LoadTime %d PASS %d", iPulse, ch->GetSafeboxLoadTime(), PASSES_PER_SEC(g_nPortalLimitTime));
  1521. return;
  1522. }
  1523.  
  1524. if (iPulse - to_ch->GetSafeboxLoadTime() < PASSES_PER_SEC(g_nPortalLimitTime))
  1525. {
  1526. to_ch->ChatPacket(CHAT_TYPE_INFO, LC_TEXT("â°í¸¦ ¿¬ÈÄ %dÃÊ À̳»¿¡´Â °Å·¡¸¦ ÇÒ¼ö ¾ø½À´Ï´Ù."), g_nPortalLimitTime);
  1527.  
  1528.  
  1529. if (test_server)
  1530. to_ch->ChatPacket(CHAT_TYPE_INFO, "[TestOnly][Safebox]Pulse %d LoadTime %d PASS %d", iPulse, to_ch->GetSafeboxLoadTime(), PASSES_PER_SEC(g_nPortalLimitTime));
  1531. return;
  1532. }
  1533.  
  1534. if (ch->GetGold() >= GOLD_MAX)
  1535. {
  1536. ch->ChatPacket(CHAT_TYPE_INFO, LC_TEXT("¾×¼ö°¡ 20¾ï ³ÉÀ» ÃʰúÇÏ¿© °Å·¡¸¦ ÇÒ¼ö°¡ ¾ø½À´Ï´Ù.."));
  1537.  
  1538. sys_err("[OVERFLOG_GOLD] START (%lld) id %u name %s ", ch->GetGold(), ch->GetPlayerID(), ch->GetName());
  1539. return;
  1540. }
  1541.  
  1542. if (to_ch->IsPC())
  1543. {
  1544. if (quest::CQuestManager::instance().GiveItemToPC(ch->GetPlayerID(), to_ch))
  1545. {
  1546. sys_log(0, "Exchange canceled by quest %s %s", ch->GetName(), to_ch->GetName());
  1547. return;
  1548. }
  1549. }
  1550.  
  1551.  
  1552. if (ch->GetMyShop() || ch->IsOpenSafebox() || ch->GetShopOwner() || ch->IsCubeOpen())
  1553. {
  1554. ch->ChatPacket(CHAT_TYPE_INFO, LC_TEXT("´Ù¸¥ °Å·¡ÁßÀϰæ¿ì °³ÀλóÁ¡À» ¿­¼ö°¡ ¾ø½À´Ï´Ù."));
  1555. return;
  1556. }
  1557.  
  1558. #ifdef __ENABLE_BATTLE_FIELD__
  1559. if (CBattleZone::instance().IsBattleZoneMapIndex(ch->GetMapIndex()))
  1560. {
  1561. ch->ChatPacket(CHAT_TYPE_INFO, LC_TEXT("BATTLE_ZONE_CANT_EXCHANGE"));
  1562. return;
  1563. }
  1564. #endif
  1565.  
  1566. ch->ExchangeStart(to_ch);
  1567. }
  1568. }
  1569. break;
  1570.  
  1571. case EXCHANGE_SUBHEADER_CG_ITEM_ADD: // arg1 == position of item, arg2 == position in exchange window
  1572. if (ch->GetExchange())
  1573. {
  1574. if (ch->GetExchange()->GetCompany()->GetAcceptStatus() != true)
  1575. ch->GetExchange()->AddItem(pinfo->Pos, pinfo->arg2);
  1576. }
  1577. break;
  1578.  
  1579. case EXCHANGE_SUBHEADER_CG_ITEM_DEL: // arg1 == position of item
  1580. if (ch->GetExchange())
  1581. {
  1582. if (ch->GetExchange()->GetCompany()->GetAcceptStatus() != true)
  1583. ch->GetExchange()->RemoveItem(pinfo->arg1);
  1584. }
  1585. break;
  1586.  
  1587. case EXCHANGE_SUBHEADER_CG_ELK_ADD: // arg1 == amount of gold
  1588. if (ch->GetExchange())
  1589. {
  1590. const long long nTotalGold = static_cast<long long>(ch->GetExchange()->GetCompany()->GetOwner()->GetGold()) + static_cast<long long>(pinfo->arg1);
  1591.  
  1592. if (GOLD_MAX <= nTotalGold)
  1593. {
  1594. ch->ChatPacket(CHAT_TYPE_INFO,("Limita de yang a fost atinsa!"));
  1595.  
  1596. sys_err("[OVERFLOW_GOLD] ELK_ADD (%lld) id %u name %s ",
  1597. ch->GetExchange()->GetCompany()->GetOwner()->GetGold(),
  1598. ch->GetExchange()->GetCompany()->GetOwner()->GetPlayerID(),
  1599. ch->GetExchange()->GetCompany()->GetOwner()->GetName());
  1600.  
  1601. return;
  1602. }
  1603.  
  1604. if (ch->GetExchange()->GetCompany()->GetAcceptStatus() != true)
  1605. ch->GetExchange()->AddGold(pinfo->arg1);
  1606. }
  1607. break;
  1608.  
  1609. case EXCHANGE_SUBHEADER_CG_ACCEPT: // arg1 == not used
  1610. if (ch->GetExchange())
  1611. {
  1612. sys_log(0, "CInputMain()::Exchange() ==> ACCEPT ");
  1613. ch->GetExchange()->Accept(true);
  1614. }
  1615.  
  1616. break;
  1617.  
  1618. case EXCHANGE_SUBHEADER_CG_CANCEL: // arg1 == not used
  1619. if (ch->GetExchange())
  1620. ch->GetExchange()->Cancel();
  1621. break;
  1622. }
  1623. }
  1624.  
  1625. void CInputMain::Position(LPCHARACTER ch, const char * data)
  1626. {
  1627. struct command_position * pinfo = (struct command_position *) data;
  1628.  
  1629. switch (pinfo->position)
  1630. {
  1631. case POSITION_GENERAL:
  1632. ch->Standup();
  1633. break;
  1634.  
  1635. case POSITION_SITTING_CHAIR:
  1636. ch->Sitdown(0);
  1637. break;
  1638.  
  1639. case POSITION_SITTING_GROUND:
  1640. ch->Sitdown(1);
  1641. break;
  1642. }
  1643. }
  1644.  
  1645. static const int ComboSequenceBySkillLevel[3][8] =
  1646. {
  1647. // 0 1 2 3 4 5 6 7
  1648. { 14, 15, 16, 17, 0, 0, 0, 0 },
  1649. { 14, 15, 16, 18, 20, 0, 0, 0 },
  1650. { 14, 15, 16, 18, 19, 17, 0, 0 },
  1651. };
  1652.  
  1653. #define COMBO_HACK_ALLOWABLE_MS 100
  1654.  
  1655. bool CheckComboHack(LPCHARACTER ch, BYTE bArg, DWORD dwTime, bool CheckSpeedHack)
  1656. {
  1657. if(!gHackCheckEnable) return false;
  1658.  
  1659. // Áװųª ±âÀý »óÅ¿¡¼­´Â °ø°ÝÇÒ ¼ö ¾øÀ¸¹Ç·Î, skipÇÑ´Ù.
  1660. // ÀÌ·¸°Ô ÇÏÁö ¸»°í, CHRACTER::CanMove()¿¡
  1661. // if (IsStun() || IsDead()) return false;
  1662. // ¸¦ Ãß°¡ÇÏ´Â°Ô ¸Â´Ù°í »ý°¢Çϳª,
  1663. // ÀÌ¹Ì ´Ù¸¥ ºÎºÐ¿¡¼­ CanMove()´Â IsStun(), IsDead()°ú
  1664. // µ¶¸³ÀûÀ¸·Î üũÇϰí Àֱ⠶§¹®¿¡ ¼öÁ¤¿¡ ÀÇÇÑ ¿µÇâÀ»
  1665. // ÃÖ¼ÒÈ­Çϱâ À§ÇØ ÀÌ·¸°Ô ¶«»§ Äڵ带 ½á³õ´Â´Ù.
  1666. if (ch->IsStun() || ch->IsDead())
  1667. return false;
  1668. int ComboInterval = dwTime - ch->GetLastComboTime();
  1669. int HackScalar = 0; // ±âº» ½ºÄ®¶ó ´ÜÀ§ 1
  1670. #if 0
  1671. sys_log(0, "COMBO: %s arg:%u seq:%u delta:%d checkspeedhack:%d",
  1672. ch->GetName(), bArg, ch->GetComboSequence(), ComboInterval - ch->GetValidComboInterval(), CheckSpeedHack);
  1673. #endif
  1674. // bArg 14 ~ 21¹ø ±îÁö ÃÑ 8ÄÞº¸ °¡´É
  1675. // 1. ù ÄÞº¸(14)´Â ÀÏÁ¤ ½Ã°£ ÀÌÈÄ¿¡ ¹Ýº¹ °¡´É
  1676. // 2. 15 ~ 21¹øÀº ¹Ýº¹ ºÒ°¡´É
  1677. // 3. Â÷·Ê´ë·Î Áõ°¡ÇÑ´Ù.
  1678. if (bArg == 14)
  1679. {
  1680. if (CheckSpeedHack && ComboInterval > 0 && ComboInterval < ch->GetValidComboInterval() - COMBO_HACK_ALLOWABLE_MS)
  1681. {
  1682. // FIXME ù¹øÂ° ÄÞº¸´Â ÀÌ»óÇÏ°Ô »¡¸® ¿Ã ¼ö°¡ À־ 300À¸·Î ³ª´® -_-;
  1683.  
  1684. // ´Ù¼öÀÇ ¸ó½ºÅÍ¿¡ ÀÇÇØ ´Ù¿îµÇ´Â »óȲ¿¡¼­ °ø°ÝÀ» Çϸé
  1685. // ù¹øÂ° ÄÞº¸°¡ ¸Å¿ì ÀûÀº ÀÎÅ͹ú·Î µé¾î¿À´Â »óȲ ¹ß»ý.
  1686. // ÀÌ·Î ÀÎÇØ ÄÞº¸ÇÙÀ¸·Î ƨ±â´Â °æ¿ì°¡ ÀÖ¾î ´ÙÀ½ ÄÚµå ºñ Ȱ¼ºÈ­.
  1687. //HackScalar = 1 + (ch->GetValidComboInterval() - ComboInterval) / 300;
  1688.  
  1689. //sys_log(0, "COMBO_HACK: 2 %s arg:%u interval:%d valid:%u atkspd:%u riding:%s",
  1690. // ch->GetName(),
  1691. // bArg,
  1692. // ComboInterval,
  1693. // ch->GetValidComboInterval(),
  1694. // ch->GetPoint(POINT_ATT_SPEED),
  1695. // ch->IsRiding() ? "yes" : "no");
  1696. }
  1697.  
  1698. ch->SetComboSequence(1);
  1699. ch->SetValidComboInterval((int) (ani_combo_speed(ch, 1) / (ch->GetPoint(POINT_ATT_SPEED) / 100.f)));
  1700. ch->SetLastComboTime(dwTime);
  1701. }
  1702. else if (bArg > 14 && bArg < 22)
  1703. {
  1704. int idx = MIN(2, ch->GetComboIndex());
  1705.  
  1706. if (ch->GetComboSequence() > 5) // ÇöÀç 6ÄÞº¸ ÀÌ»óÀº ¾ø´Ù.
  1707. {
  1708. HackScalar = 1;
  1709. ch->SetValidComboInterval(300);
  1710. sys_log(0, "COMBO_HACK: 5 %s combo_seq:%d", ch->GetName(), ch->GetComboSequence());
  1711. }
  1712. // ÀÚ°´ ½Ö¼ö ÄÞº¸ ¿¹¿Üó¸®
  1713. else if (bArg == 21 &&
  1714. idx == 2 &&
  1715. ch->GetComboSequence() == 5 &&
  1716. ch->GetJob() == JOB_ASSASSIN &&
  1717. ch->GetWear(WEAR_WEAPON) &&
  1718. ch->GetWear(WEAR_WEAPON)->GetSubType() == WEAPON_DAGGER)
  1719. ch->SetValidComboInterval(300);
  1720. #ifdef ENABLE_WOLFMAN_CHARACTER
  1721. else if (bArg == 21 && idx == 2 && ch->GetComboSequence() == 5 && ch->GetJob() == JOB_WOLFMAN && ch->GetWear(WEAR_WEAPON) && ch->GetWear(WEAR_WEAPON)->GetSubType() == WEAPON_CLAW)
  1722. ch->SetValidComboInterval(300);
  1723. #endif
  1724. else if (ComboSequenceBySkillLevel[idx][ch->GetComboSequence()] != bArg)
  1725. {
  1726. HackScalar = 1;
  1727. ch->SetValidComboInterval(300);
  1728.  
  1729. sys_log(0, "COMBO_HACK: 3 %s arg:%u valid:%u combo_idx:%d combo_seq:%d",
  1730. ch->GetName(),
  1731. bArg,
  1732. ComboSequenceBySkillLevel[idx][ch->GetComboSequence()],
  1733. idx,
  1734. ch->GetComboSequence());
  1735. }
  1736. else
  1737. {
  1738. if (CheckSpeedHack && ComboInterval < ch->GetValidComboInterval() - COMBO_HACK_ALLOWABLE_MS)
  1739. {
  1740. HackScalar = 1 + (ch->GetValidComboInterval() - ComboInterval) / 100;
  1741.  
  1742. sys_log(0, "COMBO_HACK: 2 %s arg:%u interval:%d valid:%u atkspd:%u riding:%s",
  1743. ch->GetName(),
  1744. bArg,
  1745. ComboInterval,
  1746. ch->GetValidComboInterval(),
  1747. ch->GetPoint(POINT_ATT_SPEED),
  1748. ch->IsRiding() ? "yes" : "no");
  1749. }
  1750.  
  1751. // ¸»À» ÅÀÀ» ¶§´Â 15¹ø ~ 16¹øÀ» ¹Ýº¹ÇÑ´Ù
  1752. //if (ch->IsHorseRiding())
  1753. if (ch->IsRiding())
  1754. ch->SetComboSequence(ch->GetComboSequence() == 1 ? 2 : 1);
  1755. else
  1756. ch->SetComboSequence(ch->GetComboSequence() + 1);
  1757.  
  1758. ch->SetValidComboInterval((int) (ani_combo_speed(ch, bArg - 13) / (ch->GetPoint(POINT_ATT_SPEED) / 100.f)));
  1759. ch->SetLastComboTime(dwTime);
  1760. }
  1761. }
  1762. else if (bArg == 13) // ±âº» °ø°Ý (µÐ°©(Polymorph)ÇßÀ» ¶§ ¿Â´Ù)
  1763. {
  1764. if (CheckSpeedHack && ComboInterval > 0 && ComboInterval < ch->GetValidComboInterval() - COMBO_HACK_ALLOWABLE_MS)
  1765. {
  1766. // ´Ù¼öÀÇ ¸ó½ºÅÍ¿¡ ÀÇÇØ ´Ù¿îµÇ´Â »óȲ¿¡¼­ °ø°ÝÀ» Çϸé
  1767. // ù¹øÂ° ÄÞº¸°¡ ¸Å¿ì ÀûÀº ÀÎÅ͹ú·Î µé¾î¿À´Â »óȲ ¹ß»ý.
  1768. // ÀÌ·Î ÀÎÇØ ÄÞº¸ÇÙÀ¸·Î ƨ±â´Â °æ¿ì°¡ ÀÖ¾î ´ÙÀ½ ÄÚµå ºñ Ȱ¼ºÈ­.
  1769. //HackScalar = 1 + (ch->GetValidComboInterval() - ComboInterval) / 100;
  1770.  
  1771. //sys_log(0, "COMBO_HACK: 6 %s arg:%u interval:%d valid:%u atkspd:%u",
  1772. // ch->GetName(),
  1773. // bArg,
  1774. // ComboInterval,
  1775. // ch->GetValidComboInterval(),
  1776. // ch->GetPoint(POINT_ATT_SPEED));
  1777. }
  1778.  
  1779. if (ch->GetRaceNum() >= MAIN_RACE_MAX_NUM)
  1780. {
  1781. // POLYMORPH_BUG_FIX
  1782.  
  1783. // DELETEME
  1784. /*
  1785. const CMotion * pkMotion = CMotionManager::instance().GetMotion(ch->GetRaceNum(), MAKE_MOTION_KEY(MOTION_MODE_GENERAL, MOTION_NORMAL_ATTACK));
  1786.  
  1787. if (!pkMotion)
  1788. sys_err("cannot find motion by race %u", ch->GetRaceNum());
  1789. else
  1790. {
  1791. // Á¤»óÀû °è»êÀ̶ó¸é 1000.f¸¦ °öÇØ¾ß ÇÏÁö¸¸ Ŭ¶óÀÌ¾ðÆ®°¡ ¾Ö´Ï¸ÞÀÌ¼Ç ¼ÓµµÀÇ 90%¿¡¼­
  1792. // ´ÙÀ½ ¾Ö´Ï¸ÞÀÌ¼Ç ºí·»µùÀ» Çã¿ëÇϹǷΠ900.f¸¦ °öÇÑ´Ù.
  1793. int k = (int) (pkMotion->GetDuration() / ((float) ch->GetPoint(POINT_ATT_SPEED) / 100.f) * 900.f);
  1794. ch->SetValidComboInterval(k);
  1795. ch->SetLastComboTime(dwTime);
  1796. }
  1797. */
  1798. float normalAttackDuration = CMotionManager::instance().GetNormalAttackDuration(ch->GetRaceNum());
  1799. int k = (int) (normalAttackDuration / ((float) ch->GetPoint(POINT_ATT_SPEED) / 100.f) * 900.f);
  1800. ch->SetValidComboInterval(k);
  1801. ch->SetLastComboTime(dwTime);
  1802. // END_OF_POLYMORPH_BUG_FIX
  1803. }
  1804. else
  1805. {
  1806. // ¸»ÀÌ ¾ÈµÇ´Â ÄÞº¸°¡ ¿Ô´Ù ÇØÄ¿ÀÏ °¡´É¼º?
  1807. //if (ch->GetDesc()->DelayedDisconnect(number(2, 9)))
  1808. //{
  1809. // LogManager::instance().HackLog("Hacker", ch);
  1810. // sys_log(0, "HACKER: %s arg %u", ch->GetName(), bArg);
  1811. //}
  1812.  
  1813. // À§ ÄÚµå·Î ÀÎÇØ, Æú¸®¸ðÇÁ¸¦ Ǫ´Â Áß¿¡ °ø°Ý Çϸé,
  1814. // °¡²û ÇÙÀ¸·Î ÀνÄÇÏ´Â °æ¿ì°¡ ÀÖ´Ù.
  1815.  
  1816. // ÀÚ¼¼È÷ ¸»Çô¸é,
  1817. // ¼­¹ö¿¡¼­ poly 0¸¦ ó¸®ÇßÁö¸¸,
  1818. // Ŭ¶ó¿¡¼­ ±× ÆÐŶÀ» ¹Þ±â Àü¿¡, ¸÷À» °ø°Ý. <- Áï, ¸÷ÀÎ »óÅ¿¡¼­ °ø°Ý.
  1819. //
  1820. // ±×·¯¸é Ŭ¶ó¿¡¼­´Â ¼­¹ö¿¡ ¸÷ »óÅ·Π°ø°ÝÇß´Ù´Â Ä¿¸Çµå¸¦ º¸³»°í (arg == 13)
  1821. //
  1822. // ¼­¹ö¿¡¼­´Â race´Â Àΰ£Àε¥ °ø°ÝÇüÅ´ ¸÷ÀÎ ³ðÀÌ´Ù! ¶ó°í ÇÏ¿© ÇÙüũ¸¦ Çß´Ù.
  1823.  
  1824. // »ç½Ç °ø°Ý ÆÐÅÏ¿¡ ´ëÇÑ °ÍÀº Ŭ¶óÀÌ¾ðÆ®¿¡¼­ ÆÇ´ÜÇØ¼­ º¸³¾ °ÍÀÌ ¾Æ´Ï¶ó,
  1825. // ¼­¹ö¿¡¼­ ÆÇ´ÜÇØ¾ß ÇÒ °ÍÀε¥... ¿Ö ÀÌ·¸°Ô ÇØ³ùÀ»±î...
  1826. // by rtsummit
  1827. }
  1828. }
  1829. else
  1830. {
  1831. // ¸»ÀÌ ¾ÈµÇ´Â ÄÞº¸°¡ ¿Ô´Ù ÇØÄ¿ÀÏ °¡´É¼º?
  1832. if (ch->GetDesc()->DelayedDisconnect(number(2, 9)))
  1833. {
  1834. LogManager::instance().HackLog("Hacker", ch);
  1835. sys_log(0, "HACKER: %s arg %u", ch->GetName(), bArg);
  1836. }
  1837.  
  1838. HackScalar = 10;
  1839. ch->SetValidComboInterval(300);
  1840. }
  1841.  
  1842. if (HackScalar)
  1843. {
  1844. // ¸»¿¡ Ÿ°Å³ª ³»·ÈÀ» ¶§ 1.5Ãʰ£ °ø°ÝÀº ÇÙÀ¸·Î °£ÁÖÇÏÁö ¾ÊµÇ °ø°Ý·ÂÀº ¾ø°Ô Çϴ ó¸®
  1845. if (get_dword_time() - ch->GetLastMountTime() > 1500)
  1846. ch->IncreaseComboHackCount(1 + HackScalar);
  1847.  
  1848. ch->SkipComboAttackByTime(ch->GetValidComboInterval());
  1849. }
  1850.  
  1851. return HackScalar;
  1852.  
  1853.  
  1854. }
  1855.  
  1856. void CInputMain::Move(LPCHARACTER ch, const char * data)
  1857. {
  1858. if (!ch->CanMove())
  1859. return;
  1860.  
  1861. struct command_move * pinfo = (struct command_move *) data;
  1862.  
  1863. if (pinfo->bFunc >= FUNC_MAX_NUM && !(pinfo->bFunc & 0x80))
  1864. {
  1865. sys_err("invalid move type: %s", ch->GetName());
  1866. return;
  1867. }
  1868.  
  1869. //enum EMoveFuncType
  1870. //{
  1871. // FUNC_WAIT,
  1872. // FUNC_MOVE,
  1873. // FUNC_ATTACK,
  1874. // FUNC_COMBO,
  1875. // FUNC_MOB_SKILL,
  1876. // _FUNC_SKILL,
  1877. // FUNC_MAX_NUM,
  1878. // FUNC_SKILL = 0x80,
  1879. //};
  1880.  
  1881. // ÅÚ·¹Æ÷Æ® Ç٠üũ
  1882.  
  1883. // if (!test_server)
  1884. {
  1885. const float fDist = DISTANCE_SQRT((ch->GetX() - pinfo->lX) / 100, (ch->GetY() - pinfo->lY) / 100);
  1886. // @fixme106 (changed 40 to 60)
  1887. if (((false == ch->IsRiding() && fDist > 750) || fDist > 1000) && OXEVENT_MAP_INDEX != ch->GetMapIndex())
  1888. {
  1889. #ifdef ENABLE_HACK_TELEPORT_LOG // @warme006
  1890. {
  1891. const PIXEL_POSITION & warpPos = ch->GetWarpPosition();
  1892.  
  1893. if (warpPos.x == 0 && warpPos.y == 0)
  1894. LogManager::instance().HackLog("Teleport", ch); // ºÎÁ¤È®ÇÒ ¼ö ÀÖÀ½
  1895. }
  1896. #endif
  1897. sys_log(0, "MOVE: %s trying to move too far (dist: %.1fm) Riding(%d)", ch->GetName(), fDist, ch->IsRiding());
  1898.  
  1899. ch->Show(ch->GetMapIndex(), ch->GetX(), ch->GetY(), ch->GetZ());
  1900. ch->Stop();
  1901. return;
  1902. }
  1903. #ifdef ENABLE_CHECK_GHOSTMODE
  1904. if (ch->IsPC() && ch->IsDead())
  1905. {
  1906. sys_log(0, "MOVE: %s trying to move as dead", ch->GetName());
  1907.  
  1908. ch->Show(ch->GetMapIndex(), ch->GetX(), ch->GetY(), ch->GetZ());
  1909. ch->Stop();
  1910. return;
  1911. }
  1912. #endif
  1913. //
  1914. // ½ºÇǵåÇÙ(SPEEDHACK) Check
  1915. //
  1916. DWORD dwCurTime = get_dword_time();
  1917. // ½Ã°£À» SyncÇϰí 7ÃÊ ÈÄ ºÎÅÍ °Ë»çÇÑ´Ù. (20090702 ÀÌÀü¿£ 5ÃÊ¿´À½)
  1918. bool CheckSpeedHack = (false == ch->GetDesc()->IsHandshaking() && dwCurTime - ch->GetDesc()->GetClientTime() > 7000);
  1919.  
  1920. if (CheckSpeedHack)
  1921. {
  1922. int iDelta = (int) (pinfo->dwTime - ch->GetDesc()->GetClientTime());
  1923. int iServerDelta = (int) (dwCurTime - ch->GetDesc()->GetClientTime());
  1924.  
  1925. iDelta = (int) (dwCurTime - pinfo->dwTime);
  1926.  
  1927. // ½Ã°£ÀÌ ´Ê°Ô°£´Ù. ÀÏ´Ü ·Î±×¸¸ ÇØµÐ´Ù. ÁøÂ¥ ÀÌ·± »ç¶÷µéÀÌ ¸¹ÀºÁö Ã¼Å©ÇØ¾ßÇÔ. TODO
  1928. if (iDelta >= 30000)
  1929. {
  1930. sys_log(0, "SPEEDHACK: slow timer name %s delta %d", ch->GetName(), iDelta);
  1931. ch->GetDesc()->DelayedDisconnect(3);
  1932. }
  1933. // 1ÃÊ¿¡ 20msec »¡¸® °¡´Â°Å ±îÁö´Â ÀÌÇØÇÑ´Ù.
  1934. else if (iDelta < -(iServerDelta / 50))
  1935. {
  1936. sys_log(0, "SPEEDHACK: DETECTED! %s (delta %d %d)", ch->GetName(), iDelta, iServerDelta);
  1937. ch->GetDesc()->DelayedDisconnect(3);
  1938. }
  1939. }
  1940.  
  1941. //
  1942. // ÄÞº¸ÇÙ ¹× ½ºÇǵåÇ٠üũ
  1943. //
  1944. if (pinfo->bFunc == FUNC_COMBO && g_bCheckMultiHack)
  1945. {
  1946. CheckComboHack(ch, pinfo->bArg, pinfo->dwTime, CheckSpeedHack); // ÄÞº¸ üũ
  1947. }
  1948. }
  1949.  
  1950. if (pinfo->bFunc == FUNC_MOVE)
  1951. {
  1952. if (ch->GetLimitPoint(POINT_MOV_SPEED) == 0)
  1953. return;
  1954.  
  1955. ch->SetRotation(pinfo->bRot * 5); // Áߺ¹ ÄÚµå
  1956. ch->ResetStopTime(); // ""
  1957.  
  1958. ch->Goto(pinfo->lX, pinfo->lY);
  1959. }
  1960. else
  1961. {
  1962. if (pinfo->bFunc == FUNC_ATTACK || pinfo->bFunc == FUNC_COMBO)
  1963. ch->OnMove(true);
  1964. else if (pinfo->bFunc & FUNC_SKILL)
  1965. {
  1966. const int MASK_SKILL_MOTION = 0x7F;
  1967. unsigned int motion = pinfo->bFunc & MASK_SKILL_MOTION;
  1968.  
  1969. if (!ch->IsUsableSkillMotion(motion))
  1970. {
  1971. const char* name = ch->GetName();
  1972. unsigned int job = ch->GetJob();
  1973. unsigned int group = ch->GetSkillGroup();
  1974.  
  1975. char szBuf[256];
  1976. snprintf(szBuf, sizeof(szBuf), "SKILL_HACK: name=%s, job=%d, group=%d, motion=%d", name, job, group, motion);
  1977. LogManager::instance().HackLog(szBuf, ch->GetDesc()->GetAccountTable().login, ch->GetName(), ch->GetDesc()->GetHostName());
  1978. sys_log(0, "%s", szBuf);
  1979.  
  1980. if (test_server)
  1981. {
  1982. ch->GetDesc()->DelayedDisconnect(number(2, 8));
  1983. ch->ChatPacket(CHAT_TYPE_INFO, szBuf);
  1984. }
  1985. else
  1986. {
  1987. ch->GetDesc()->DelayedDisconnect(number(150, 500));
  1988. }
  1989. }
  1990.  
  1991. ch->OnMove();
  1992. }
  1993.  
  1994. ch->SetRotation(pinfo->bRot * 5); // Áߺ¹ ÄÚµå
  1995. ch->ResetStopTime(); // ""
  1996.  
  1997. ch->Move(pinfo->lX, pinfo->lY);
  1998. ch->Stop();
  1999. ch->StopStaminaConsume();
  2000. }
  2001.  
  2002. TPacketGCMove pack;
  2003.  
  2004. pack.bHeader = HEADER_GC_MOVE;
  2005. pack.bFunc = pinfo->bFunc;
  2006. pack.bArg = pinfo->bArg;
  2007. pack.bRot = pinfo->bRot;
  2008. pack.dwVID = ch->GetVID();
  2009. pack.lX = pinfo->lX;
  2010. pack.lY = pinfo->lY;
  2011. pack.dwTime = pinfo->dwTime;
  2012. pack.dwDuration = (pinfo->bFunc == FUNC_MOVE) ? ch->GetCurrentMoveDuration() : 0;
  2013.  
  2014. ch->PacketAround(&pack, sizeof(TPacketGCMove), ch);
  2015. /*
  2016. if (pinfo->dwTime == 10653691) // µð¹ö°Å ¹ß°ß
  2017. {
  2018. if (ch->GetDesc()->DelayedDisconnect(number(15, 30)))
  2019. LogManager::instance().HackLog("Debugger", ch);
  2020.  
  2021. }
  2022. else if (pinfo->dwTime == 10653971) // Softice ¹ß°ß
  2023. {
  2024. if (ch->GetDesc()->DelayedDisconnect(number(15, 30)))
  2025. LogManager::instance().HackLog("Softice", ch);
  2026. }
  2027. */
  2028. /*
  2029. sys_log(0,
  2030. "MOVE: %s Func:%u Arg:%u Pos:%dx%d Time:%u Dist:%.1f",
  2031. ch->GetName(),
  2032. pinfo->bFunc,
  2033. pinfo->bArg,
  2034. pinfo->lX / 100,
  2035. pinfo->lY / 100,
  2036. pinfo->dwTime,
  2037. fDist);
  2038. */
  2039. }
  2040.  
  2041. void CInputMain::Attack(LPCHARACTER ch, const BYTE header, const char* data)
  2042. {
  2043. if (NULL == ch)
  2044. return;
  2045.  
  2046. struct type_identifier
  2047. {
  2048. BYTE header;
  2049. BYTE type;
  2050. };
  2051.  
  2052. const struct type_identifier* const type = reinterpret_cast<const struct type_identifier*>(data);
  2053.  
  2054. if (type->type > 0)
  2055. {
  2056. if (false == ch->CanUseSkill(type->type))
  2057. {
  2058. return;
  2059. }
  2060.  
  2061. switch (type->type)
  2062. {
  2063. case SKILL_GEOMPUNG:
  2064. case SKILL_SANGONG:
  2065. case SKILL_YEONSA:
  2066. case SKILL_KWANKYEOK:
  2067. case SKILL_HWAJO:
  2068. case SKILL_GIGUNG:
  2069. case SKILL_PABEOB:
  2070. case SKILL_MARYUNG:
  2071. case SKILL_TUSOK:
  2072. case SKILL_MAHWAN:
  2073. case SKILL_BIPABU:
  2074. case SKILL_NOEJEON:
  2075. case SKILL_CHAIN:
  2076. case SKILL_HORSE_WILDATTACK_RANGE:
  2077. if (HEADER_CG_SHOOT != type->header)
  2078. {
  2079. if (test_server)
  2080. ch->ChatPacket(CHAT_TYPE_INFO, LC_TEXT("Attack :name[%s] Vnum[%d] can't use skill by attack(warning)"), type->type);
  2081. return;
  2082. }
  2083. break;
  2084. }
  2085. }
  2086.  
  2087. switch (header)
  2088. {
  2089. case HEADER_CG_ATTACK:
  2090. {
  2091. if (NULL == ch->GetDesc())
  2092. return;
  2093.  
  2094. const TPacketCGAttack* const packMelee = reinterpret_cast<const TPacketCGAttack*>(data);
  2095.  
  2096. ch->GetDesc()->AssembleCRCMagicCube(packMelee->bCRCMagicCubeProcPiece, packMelee->bCRCMagicCubeFilePiece);
  2097.  
  2098. LPCHARACTER victim = CHARACTER_MANAGER::instance().Find(packMelee->dwVID);
  2099.  
  2100. if (NULL == victim || ch == victim)
  2101. return;
  2102.  
  2103. switch (victim->GetCharType())
  2104. {
  2105. case CHAR_TYPE_NPC:
  2106. case CHAR_TYPE_WARP:
  2107. case CHAR_TYPE_GOTO:
  2108. return;
  2109. }
  2110.  
  2111. if (packMelee->bType > 0)
  2112. {
  2113. if (false == ch->CheckSkillHitCount(packMelee->bType, victim->GetVID()))
  2114. {
  2115. return;
  2116. }
  2117. }
  2118.  
  2119. ch->Attack(victim, packMelee->bType);
  2120. }
  2121. break;
  2122.  
  2123. case HEADER_CG_SHOOT:
  2124. {
  2125. const TPacketCGShoot* const packShoot = reinterpret_cast<const TPacketCGShoot*>(data);
  2126.  
  2127. ch->Shoot(packShoot->bType);
  2128. }
  2129. break;
  2130. }
  2131. }
  2132.  
  2133. int CInputMain::SyncPosition(LPCHARACTER ch, const char * c_pcData, size_t uiBytes)
  2134. {
  2135. const TPacketCGSyncPosition* pinfo = reinterpret_cast<const TPacketCGSyncPosition*>( c_pcData );
  2136.  
  2137. if (uiBytes < pinfo->wSize)
  2138. return -1;
  2139.  
  2140. int iExtraLen = pinfo->wSize - sizeof(TPacketCGSyncPosition);
  2141.  
  2142. if (iExtraLen < 0)
  2143. {
  2144. sys_err("invalid packet length (len %d size %u buffer %u)", iExtraLen, pinfo->wSize, uiBytes);
  2145. ch->GetDesc()->SetPhase(PHASE_CLOSE);
  2146. return -1;
  2147. }
  2148.  
  2149. if (0 != (iExtraLen % sizeof(TPacketCGSyncPositionElement)))
  2150. {
  2151. sys_err("invalid packet length %d (name: %s)", pinfo->wSize, ch->GetName());
  2152. return iExtraLen;
  2153. }
  2154.  
  2155. int iCount = iExtraLen / sizeof(TPacketCGSyncPositionElement);
  2156.  
  2157. if (iCount <= 0)
  2158. return iExtraLen;
  2159.  
  2160. static const int nCountLimit = 16;
  2161.  
  2162. if( iCount > nCountLimit )
  2163. {
  2164. //LogManager::instance().HackLog( "SYNC_POSITION_HACK", ch );
  2165. sys_err( "Too many SyncPosition Count(%d) from Name(%s)", iCount, ch->GetName() );
  2166. //ch->GetDesc()->SetPhase(PHASE_CLOSE);
  2167. //return -1;
  2168. iCount = nCountLimit;
  2169. }
  2170.  
  2171. TEMP_BUFFER tbuf;
  2172. LPBUFFER lpBuf = tbuf.getptr();
  2173.  
  2174. TPacketGCSyncPosition * pHeader = (TPacketGCSyncPosition *) buffer_write_peek(lpBuf);
  2175. buffer_write_proceed(lpBuf, sizeof(TPacketGCSyncPosition));
  2176.  
  2177. const TPacketCGSyncPositionElement* e =
  2178. reinterpret_cast<const TPacketCGSyncPositionElement*>(c_pcData + sizeof(TPacketCGSyncPosition));
  2179.  
  2180. timeval tvCurTime;
  2181. gettimeofday(&tvCurTime, NULL);
  2182.  
  2183. for (int i = 0; i < iCount; ++i, ++e)
  2184. {
  2185. LPCHARACTER victim = CHARACTER_MANAGER::instance().Find(e->dwVID);
  2186.  
  2187. if (!victim)
  2188. continue;
  2189.  
  2190. switch (victim->GetCharType())
  2191. {
  2192. case CHAR_TYPE_NPC:
  2193. case CHAR_TYPE_WARP:
  2194. case CHAR_TYPE_GOTO:
  2195. continue;
  2196. }
  2197.  
  2198. // ¼ÒÀ¯±Ç °Ë»ç
  2199. if (!victim->SetSyncOwner(ch))
  2200. continue;
  2201.  
  2202. const float fDistWithSyncOwner = DISTANCE_SQRT( (victim->GetX() - ch->GetX()) / 100, (victim->GetY() - ch->GetY()) / 100 );
  2203. static const float fLimitDistWithSyncOwner = 2500.f + 1000.f;
  2204. // victim°úÀÇ °Å¸®°¡ 2500 + a ÀÌ»óÀ̸é ÇÙÀ¸·Î °£ÁÖ.
  2205. // °Å¸® ÂüÁ¶ : Ŭ¶óÀ̾ðÆ®ÀÇ __GetSkillTargetRange, __GetBowRange ÇÔ¼ö
  2206. // 2500 : ½ºÅ³ proto¿¡¼­ °¡Àå »ç°Å¸®°¡ ±ä ½ºÅ³ÀÇ »ç°Å¸®, ¶Ç´Â ȰÀÇ »ç°Å¸®
  2207. // a = POINT_BOW_DISTANCE °ª... Àε¥ ½ÇÁ¦·Î »ç¿ëÇÏ´Â °ªÀÎÁö´Â Àß ¸ð¸£°ÚÀ½. ¾ÆÀÌÅÛÀ̳ª Æ÷¼Ç, ½ºÅ³, Äù½ºÆ®¿¡´Â ¾ø´Âµ¥...
  2208. // ±×·¡µµ Ȥ½Ã³ª ÇÏ´Â ¸¶À½¿¡ ¹öÆÛ·Î »ç¿ëÇÒ °âÇØ¼­ 1000.f ·Î µÒ...
  2209. if (fDistWithSyncOwner > fLimitDistWithSyncOwner)
  2210. {
  2211. // g_iSyncHackLimitCount¹ø ±îÁö´Â ºÁÁÜ.
  2212. if (ch->GetSyncHackCount() < g_iSyncHackLimitCount)
  2213. {
  2214. ch->SetSyncHackCount(ch->GetSyncHackCount() + 1);
  2215. continue;
  2216. }
  2217. else
  2218. {
  2219. LogManager::instance().HackLog( "SYNC_POSITION_HACK", ch );
  2220.  
  2221. sys_err( "Too far SyncPosition DistanceWithSyncOwner(%f)(%s) from Name(%s) CH(%d,%d) VICTIM(%d,%d) SYNC(%d,%d)",
  2222. fDistWithSyncOwner, victim->GetName(), ch->GetName(), ch->GetX(), ch->GetY(), victim->GetX(), victim->GetY(),
  2223. e->lX, e->lY );
  2224.  
  2225. ch->GetDesc()->SetPhase(PHASE_CLOSE);
  2226.  
  2227. return -1;
  2228. }
  2229. }
  2230.  
  2231. const float fDist = DISTANCE_SQRT( (victim->GetX() - e->lX) / 100, (victim->GetY() - e->lY) / 100 );
  2232. static const long g_lValidSyncInterval = 100 * 1000; // 100ms
  2233. const timeval &tvLastSyncTime = victim->GetLastSyncTime();
  2234. timeval *tvDiff = timediff(&tvCurTime, &tvLastSyncTime);
  2235.  
  2236. // SyncPositionÀ» ¾Ç¿ëÇÏ¿© ŸÀ¯Àú¸¦ ÀÌ»óÇÑ °÷À¸·Î º¸³»´Â ÇÙ ¹æ¾îÇϱâ À§ÇÏ¿©,
  2237. // °°Àº À¯Àú¸¦ g_lValidSyncInterval ms À̳»¿¡ ´Ù½Ã SyncPositionÇÏ·Á°í Çϸé ÇÙÀ¸·Î °£ÁÖ.
  2238. if (tvDiff->tv_sec == 0 && tvDiff->tv_usec < g_lValidSyncInterval)
  2239. {
  2240. // g_iSyncHackLimitCount¹ø ±îÁö´Â ºÁÁÜ.
  2241. if (ch->GetSyncHackCount() < g_iSyncHackLimitCount)
  2242. {
  2243. ch->SetSyncHackCount(ch->GetSyncHackCount() + 1);
  2244. continue;
  2245. }
  2246. else
  2247. {
  2248. LogManager::instance().HackLog( "SYNC_POSITION_HACK", ch );
  2249.  
  2250. sys_err( "Too often SyncPosition Interval(%ldms)(%s) from Name(%s) VICTIM(%d,%d) SYNC(%d,%d)",
  2251. tvDiff->tv_sec * 1000 + tvDiff->tv_usec / 1000, victim->GetName(), ch->GetName(), victim->GetX(), victim->GetY(),
  2252. e->lX, e->lY );
  2253.  
  2254. ch->GetDesc()->SetPhase(PHASE_CLOSE);
  2255.  
  2256. return -1;
  2257. }
  2258. }
  2259. else if( fDist > 25.0f )
  2260. {
  2261. LogManager::instance().HackLog( "SYNC_POSITION_HACK", ch );
  2262.  
  2263. sys_err( "Too far SyncPosition Distance(%f)(%s) from Name(%s) CH(%d,%d) VICTIM(%d,%d) SYNC(%d,%d)",
  2264. fDist, victim->GetName(), ch->GetName(), ch->GetX(), ch->GetY(), victim->GetX(), victim->GetY(),
  2265. e->lX, e->lY );
  2266.  
  2267. ch->GetDesc()->SetPhase(PHASE_CLOSE);
  2268.  
  2269. return -1;
  2270. }
  2271. else
  2272. {
  2273. victim->SetLastSyncTime(tvCurTime);
  2274. victim->Sync(e->lX, e->lY);
  2275. buffer_write(lpBuf, e, sizeof(TPacketCGSyncPositionElement));
  2276. }
  2277. }
  2278.  
  2279. if (buffer_size(lpBuf) != sizeof(TPacketGCSyncPosition))
  2280. {
  2281. pHeader->bHeader = HEADER_GC_SYNC_POSITION;
  2282. pHeader->wSize = buffer_size(lpBuf);
  2283.  
  2284. ch->PacketAround(buffer_read_peek(lpBuf), buffer_size(lpBuf), ch);
  2285. }
  2286.  
  2287. return iExtraLen;
  2288. }
  2289.  
  2290. void CInputMain::FlyTarget(LPCHARACTER ch, const char * pcData, BYTE bHeader)
  2291. {
  2292. TPacketCGFlyTargeting * p = (TPacketCGFlyTargeting *) pcData;
  2293. ch->FlyTarget(p->dwTargetVID, p->x, p->y, bHeader);
  2294. }
  2295.  
  2296. void CInputMain::UseSkill(LPCHARACTER ch, const char * pcData)
  2297. {
  2298. TPacketCGUseSkill * p = (TPacketCGUseSkill *) pcData;
  2299. ch->UseSkill(p->dwVnum, CHARACTER_MANAGER::instance().Find(p->dwVID));
  2300. }
  2301.  
  2302. void CInputMain::ScriptButton(LPCHARACTER ch, const void* c_pData)
  2303. {
  2304. TPacketCGScriptButton * p = (TPacketCGScriptButton *) c_pData;
  2305. sys_log(0, "QUEST ScriptButton pid %d idx %u", ch->GetPlayerID(), p->idx);
  2306.  
  2307. quest::PC* pc = quest::CQuestManager::instance().GetPCForce(ch->GetPlayerID());
  2308. if (pc && pc->IsConfirmWait())
  2309. {
  2310. quest::CQuestManager::instance().Confirm(ch->GetPlayerID(), quest::CONFIRM_TIMEOUT);
  2311. }
  2312. else if (p->idx & 0x80000000)
  2313. {
  2314. //Äù½ºÆ® â¿¡¼­ Ŭ¸¯½Ã(__SelectQuest) ¿©±â·Î
  2315. quest::CQuestManager::Instance().QuestInfo(ch->GetPlayerID(), p->idx & 0x7fffffff);
  2316. }
  2317. else
  2318. {
  2319. quest::CQuestManager::Instance().QuestButton(ch->GetPlayerID(), p->idx);
  2320. }
  2321. }
  2322.  
  2323. void CInputMain::ScriptAnswer(LPCHARACTER ch, const void* c_pData)
  2324. {
  2325. TPacketCGScriptAnswer * p = (TPacketCGScriptAnswer *) c_pData;
  2326. sys_log(0, "QUEST ScriptAnswer pid %d answer %d", ch->GetPlayerID(), p->answer);
  2327.  
  2328. if (p->answer > 250) // ´ÙÀ½ ¹öư¿¡ ´ëÇÑ ÀÀ´äÀ¸·Î ¿Â ÆÐŶÀÎ °æ¿ì
  2329. {
  2330. quest::CQuestManager::Instance().Resume(ch->GetPlayerID());
  2331. }
  2332. else // ¼±Åà ¹öưÀ» °ñ¶ó¼­ ¿Â ÆÐŶÀÎ °æ¿ì
  2333. {
  2334. quest::CQuestManager::Instance().Select(ch->GetPlayerID(), p->answer);
  2335. }
  2336. }
  2337.  
  2338.  
  2339. // SCRIPT_SELECT_ITEM
  2340. void CInputMain::ScriptSelectItem(LPCHARACTER ch, const void* c_pData)
  2341. {
  2342. TPacketCGScriptSelectItem* p = (TPacketCGScriptSelectItem*) c_pData;
  2343. sys_log(0, "QUEST ScriptSelectItem pid %d answer %d", ch->GetPlayerID(), p->selection);
  2344. quest::CQuestManager::Instance().SelectItem(ch->GetPlayerID(), p->selection);
  2345. }
  2346. // END_OF_SCRIPT_SELECT_ITEM
  2347.  
  2348. void CInputMain::QuestInputString(LPCHARACTER ch, const void* c_pData)
  2349. {
  2350. TPacketCGQuestInputString * p = (TPacketCGQuestInputString*) c_pData;
  2351.  
  2352. char msg[65];
  2353. strlcpy(msg, p->msg, sizeof(msg));
  2354. sys_log(0, "QUEST InputString pid %u msg %s", ch->GetPlayerID(), msg);
  2355.  
  2356. quest::CQuestManager::Instance().Input(ch->GetPlayerID(), msg);
  2357. }
  2358.  
  2359. void CInputMain::QuestConfirm(LPCHARACTER ch, const void* c_pData)
  2360. {
  2361. TPacketCGQuestConfirm* p = (TPacketCGQuestConfirm*) c_pData;
  2362. LPCHARACTER ch_wait = CHARACTER_MANAGER::instance().FindByPID(p->requestPID);
  2363. if (p->answer)
  2364. p->answer = quest::CONFIRM_YES;
  2365. sys_log(0, "QuestConfirm from %s pid %u name %s answer %d", ch->GetName(), p->requestPID, (ch_wait)?ch_wait->GetName():"", p->answer);
  2366. if (ch_wait)
  2367. {
  2368. quest::CQuestManager::Instance().Confirm(ch_wait->GetPlayerID(), (quest::EQuestConfirmType) p->answer, ch->GetPlayerID());
  2369. }
  2370. }
  2371.  
  2372. void CInputMain::Target(LPCHARACTER ch, const char * pcData)
  2373. {
  2374. TPacketCGTarget * p = (TPacketCGTarget *) pcData;
  2375.  
  2376. building::LPOBJECT pkObj = building::CManager::instance().FindObjectByVID(p->dwVID);
  2377.  
  2378. if (pkObj)
  2379. {
  2380. TPacketGCTarget pckTarget;
  2381. pckTarget.header = HEADER_GC_TARGET;
  2382. pckTarget.dwVID = p->dwVID;
  2383. ch->GetDesc()->Packet(&pckTarget, sizeof(TPacketGCTarget));
  2384. }
  2385. else
  2386. ch->SetTarget(CHARACTER_MANAGER::instance().Find(p->dwVID));
  2387. }
  2388.  
  2389. void CInputMain::Warp(LPCHARACTER ch, const char * pcData)
  2390. {
  2391. ch->WarpEnd();
  2392. }
  2393.  
  2394. #ifdef __ADMIN_MANAGER__
  2395. enum ETypeActionBan
  2396. {
  2397. ACTION_BAN_PERMANENTLY = 0,
  2398. ACTION_BAN_IP = 1 ,
  2399. ACTION_BAN_TIME = 2,
  2400. };
  2401.  
  2402. bool CheckIsStaffAdmin(LPCHARACTER ch)
  2403. {
  2404. const char* arListMembers[] = /* Here add people member from staff what you want to have acces on administration area ban, unlimited slots !*/
  2405. {
  2406. "T69",
  2407. "[SA]Ayana",
  2408. "[GF]Twigo",
  2409. "[GM]NaNo"
  2410. };
  2411. for(unsigned int key = 0; key < _countof(arListMembers); key++)
  2412. {
  2413. if ((!strcmp(arListMembers[key], ch->GetName())) && ch->GetGMLevel() > GM_PLAYER)
  2414. return true;
  2415. }
  2416.  
  2417. return false;
  2418. }
  2419.  
  2420. bool CheckIsBlocked(LPCHARACTER ch, const char* c_szName)
  2421. {
  2422. std::unique_ptr<SQLMsg> pMsg(DBManager::instance().DirectQuery("SELECT account_id FROM player.player WHERE name = '%s'", c_szName));
  2423. MYSQL_ROW row_id = mysql_fetch_row(pMsg->Get()->pSQLResult);
  2424.  
  2425. if (pMsg->uiSQLErrno != 0 || !pMsg->Get()->uiNumRows)
  2426. {
  2427. ch->ChatPacket(CHAT_TYPE_INFO, ("%s nu poate fi gasit"), c_szName);
  2428. return false;
  2429. }
  2430.  
  2431. int account_id = 0;
  2432. str_to_number(account_id, row_id[0]);
  2433.  
  2434. std::unique_ptr<SQLMsg> pMsg2(DBManager::instance().DirectQuery("SELECT status FROM account.account WHERE id = '%d'", account_id));
  2435. MYSQL_ROW row_inf = mysql_fetch_row(pMsg2->Get()->pSQLResult);
  2436.  
  2437. const char* c_szStatus = row_inf[0];
  2438.  
  2439. if (!strcmp(c_szStatus, "BLOCK"))
  2440. {
  2441. ch->ChatPacket(CHAT_TYPE_INFO, ("%s este deja banat"), c_szName);
  2442. return true;
  2443. }
  2444.  
  2445. return false;
  2446. }
  2447.  
  2448. void InsertLogsBan(const char* c_pszWho, const char* c_pszAction, const char* c_pszVictim, const char* c_pszReason)
  2449. {
  2450. DBManager::Instance().DirectQuery("INSERT INTO log.tool_ban (who, action, victim, reason, date) VALUES('%s', '%s', '%s', '%s', NOW())", c_pszWho, c_pszAction, c_pszVictim, c_pszReason);
  2451. }
  2452.  
  2453. void CInputMain::SendAdminBanManager(LPCHARACTER ch, const char* c_pData)
  2454. {
  2455. const TPacketCGAdminBanManger* p = reinterpret_cast<const TPacketCGAdminBanManger*>(c_pData);
  2456.  
  2457. if (!ch)
  2458. return;
  2459.  
  2460. if (!CheckIsStaffAdmin(ch))
  2461. {
  2462. ch->ChatPacket(CHAT_TYPE_INFO, "<Server> Error 0x01.");
  2463. return;
  2464. }
  2465.  
  2466. char szEscapedUserName[CHAT_MAX_LEN * 2 + 1];
  2467. DBManager::instance().EscapeString(szEscapedUserName, sizeof(szEscapedUserName), p->user_name, strlen(p->user_name));
  2468.  
  2469. char szEscapedReason[CHAT_MAX_LEN * 2 + 1];
  2470. DBManager::instance().EscapeString(szEscapedReason, sizeof(szEscapedReason), p->reason, strlen(p->reason));
  2471.  
  2472. if (!strcmp(szEscapedUserName, ch->GetName()))
  2473. {
  2474. ch->ChatPacket(CHAT_TYPE_INFO, ("Nu te poti bana singur"));
  2475. return;
  2476. }
  2477.  
  2478. if (CheckIsBlocked(ch, szEscapedUserName))
  2479. return;
  2480.  
  2481. switch (p->action)
  2482. {
  2483. case ACTION_BAN_PERMANENTLY:
  2484. case ACTION_BAN_TIME:
  2485. {
  2486. std::unique_ptr<SQLMsg> pMsg(DBManager::instance().DirectQuery("SELECT name, account_id FROM player.player WHERE name = '%s'", szEscapedUserName));
  2487. MYSQL_ROW row = mysql_fetch_row(pMsg->Get()->pSQLResult);
  2488.  
  2489. if (pMsg->uiSQLErrno != 0 || !pMsg->Get()->uiNumRows)
  2490. return;
  2491.  
  2492. int account_id = 0;
  2493. str_to_number(account_id, row[1]);
  2494.  
  2495. if (p->action == ACTION_BAN_PERMANENTLY)
  2496. {
  2497. DBManager::Instance().DirectQuery("UPDATE account.account SET status = 'BLOCK', ban_reason = '%s' WHERE id = '%d'", p->reason, account_id);
  2498. InsertLogsBan(ch->GetName(), "ACTION_BAN_PERMANENTLY", szEscapedUserName, p->reason);
  2499. ch->ChatPacket(CHAT_TYPE_INFO, ("%s a fost banat permanent cu succes"), szEscapedUserName);
  2500. }
  2501. else
  2502. {
  2503. if (p->duration < 300)
  2504. {
  2505. ch->ChatPacket(CHAT_TYPE_INFO, ("Timpul este invalid"));
  2506. return;
  2507. }
  2508.  
  2509. DBManager::Instance().DirectQuery("UPDATE account.account SET availDt = FROM_UNIXTIME(UNIX_TIMESTAMP(CURRENT_TIMESTAMP()) + %i), ban_reason = '%s' WHERE id = %d", p->duration, p->reason, account_id);
  2510. InsertLogsBan(ch->GetName(), "ACTION_BAN_TIME", szEscapedUserName, p->reason);
  2511. ch->ChatPacket(CHAT_TYPE_INFO, ("%s a fost banat cu succes"), szEscapedUserName);
  2512. }
  2513. }
  2514. break;
  2515.  
  2516. case ACTION_BAN_IP:
  2517. {
  2518. std::unique_ptr<SQLMsg> pMsg(DBManager::instance().DirectQuery("SELECT name, ip FROM player.player WHERE name = '%s'", szEscapedUserName));
  2519. MYSQL_ROW row = mysql_fetch_row(pMsg->Get()->pSQLResult);
  2520.  
  2521. if (pMsg->uiSQLErrno != 0 || !pMsg->Get()->uiNumRows)
  2522. return;
  2523.  
  2524. std::unique_ptr<SQLMsg> pMsg2(DBManager::Instance().DirectQuery("UPDATE account.account INNER JOIN player.player ON player.account_id = account.id SET status = 'BLOCK', ban_reason = '%s' WHERE player.ip = '%s'", p->reason, row[1]));
  2525. InsertLogsBan(ch->GetName(), "ACTION_BAN_IP", szEscapedUserName, p->reason);
  2526. ch->ChatPacket(CHAT_TYPE_INFO, ("Toate conturile cu ip-ul respectiv au fost banate permanent cu succes!"));
  2527. }
  2528. break;
  2529. default:
  2530. return;
  2531. }
  2532. }
  2533. #endif
  2534.  
  2535. void CInputMain::SafeboxCheckin(LPCHARACTER ch, const char * c_pData)
  2536. {
  2537. if (quest::CQuestManager::instance().GetPCForce(ch->GetPlayerID())->IsRunning() == true)
  2538. return;
  2539.  
  2540. TPacketCGSafeboxCheckin * p = (TPacketCGSafeboxCheckin *) c_pData;
  2541.  
  2542. if (!ch->CanHandleItem())
  2543. return;
  2544.  
  2545. CSafebox * pkSafebox = ch->GetSafebox();
  2546. LPITEM pkItem = ch->GetItem(p->ItemPos);
  2547.  
  2548. if (!pkSafebox || !pkItem)
  2549. return;
  2550.  
  2551. if (pkItem->GetCell() >= INVENTORY_MAX_NUM && IS_SET(pkItem->GetFlag(), ITEM_FLAG_IRREMOVABLE))
  2552. {
  2553. ch->ChatPacket(CHAT_TYPE_INFO, LC_TEXT("<â°í> â°í·Î ¿Å±æ ¼ö ¾ø´Â ¾ÆÀÌÅÛ ÀÔ´Ï´Ù."));
  2554. return;
  2555. }
  2556.  
  2557. if (!pkSafebox->IsEmpty(p->bSafePos, pkItem->GetSize()))
  2558. {
  2559. ch->ChatPacket(CHAT_TYPE_INFO, LC_TEXT("<â°í> ¿Å±æ ¼ö ¾ø´Â À§Ä¡ÀÔ´Ï´Ù."));
  2560. return;
  2561. }
  2562.  
  2563. if (pkItem->GetVnum() == UNIQUE_ITEM_SAFEBOX_EXPAND)
  2564. {
  2565. ch->ChatPacket(CHAT_TYPE_INFO, LC_TEXT("<â°í> ÀÌ ¾ÆÀÌÅÛÀº ³ÖÀ» ¼ö ¾ø½À´Ï´Ù."));
  2566. return;
  2567. }
  2568.  
  2569. if( IS_SET(pkItem->GetAntiFlag(), ITEM_ANTIFLAG_SAFEBOX) )
  2570. {
  2571. ch->ChatPacket(CHAT_TYPE_INFO, LC_TEXT("<â°í> ÀÌ ¾ÆÀÌÅÛÀº ³ÖÀ» ¼ö ¾ø½À´Ï´Ù."));
  2572. return;
  2573. }
  2574.  
  2575. if (true == pkItem->isLocked())
  2576. {
  2577. ch->ChatPacket(CHAT_TYPE_INFO, LC_TEXT("<â°í> ÀÌ ¾ÆÀÌÅÛÀº ³ÖÀ» ¼ö ¾ø½À´Ï´Ù."));
  2578. return;
  2579. }
  2580.  
  2581. // @fixme140 BEGIN
  2582. if (ITEM_BELT == pkItem->GetType() && CBeltInventoryHelper::IsExistItemInBeltInventory(ch))
  2583. {
  2584. ch->ChatPacket(CHAT_TYPE_INFO, LC_TEXT("º§Æ® Àκ¥Å丮¿¡ ¾ÆÀÌÅÛÀÌ Á¸ÀçÇϸé ÇØÁ¦ÇÒ ¼ö ¾ø½À´Ï´Ù."));
  2585. return;
  2586. }
  2587. // @fixme140 END
  2588.  
  2589. pkItem->RemoveFromCharacter();
  2590.  
  2591. #ifdef __SPECIAL_STORAGE__
  2592. if (!pkItem->IsDragonSoul() && !pkItem->IsUpgradeItem() && !pkItem->IsBook() && !pkItem->IsStone())
  2593. #else
  2594. if (!pkItem->IsDragonSoul())
  2595. #endif
  2596. ch->SyncQuickslot(QUICKSLOT_TYPE_ITEM, p->ItemPos.cell, 255);
  2597. pkSafebox->Add(p->bSafePos, pkItem);
  2598.  
  2599. char szHint[128];
  2600. snprintf(szHint, sizeof(szHint), "%s %u", pkItem->GetName(), pkItem->GetCount());
  2601. LogManager::instance().ItemLog(ch, pkItem, "SAFEBOX PUT", szHint);
  2602. }
  2603.  
  2604. void CInputMain::SafeboxCheckout(LPCHARACTER ch, const char * c_pData, bool bMall)
  2605. {
  2606. TPacketCGSafeboxCheckout * p = (TPacketCGSafeboxCheckout *) c_pData;
  2607.  
  2608. if (!ch->CanHandleItem())
  2609. return;
  2610.  
  2611. CSafebox * pkSafebox;
  2612.  
  2613. if (bMall)
  2614. pkSafebox = ch->GetMall();
  2615. else
  2616. pkSafebox = ch->GetSafebox();
  2617.  
  2618. if (!pkSafebox)
  2619. return;
  2620.  
  2621. LPITEM pkItem = pkSafebox->Get(p->bSafePos);
  2622.  
  2623. if (!pkItem)
  2624. return;
  2625.  
  2626. if (!ch->IsEmptyItemGrid(p->ItemPos, pkItem->GetSize()))
  2627. return;
  2628.  
  2629. // ¾ÆÀÌÅÛ ¸ô¿¡¼­ Àκ¥À¸·Î ¿Å±â´Â ºÎºÐ¿¡¼­ ¿ëÈ¥¼® Ư¼ö ó¸®
  2630. // (¸ô¿¡¼­ ¸¸µå´Â ¾ÆÀÌÅÛÀº item_proto¿¡ Á¤Àǵȴë·Î ¼Ó¼ºÀÌ ºÙ±â ¶§¹®¿¡,
  2631. // ¿ëÈ¥¼®ÀÇ °æ¿ì, ÀÌ Ã³¸®¸¦ ÇÏÁö ¾ÊÀ¸¸é ¼Ó¼ºÀÌ Çϳªµµ ºÙÁö ¾Ê°Ô µÈ´Ù.)
  2632. if (pkItem->IsDragonSoul())
  2633. {
  2634. if (bMall)
  2635. {
  2636. DSManager::instance().DragonSoulItemInitialize(pkItem);
  2637. }
  2638.  
  2639. if (DRAGON_SOUL_INVENTORY != p->ItemPos.window_type)
  2640. {
  2641. ch->ChatPacket(CHAT_TYPE_INFO, LC_TEXT("<â°í> ¿Å±æ ¼ö ¾ø´Â À§Ä¡ÀÔ´Ï´Ù."));
  2642. return;
  2643. }
  2644.  
  2645. TItemPos DestPos = p->ItemPos;
  2646. if (!DSManager::instance().IsValidCellForThisItem(pkItem, DestPos))
  2647. {
  2648. int iCell = ch->GetEmptyDragonSoulInventory(pkItem);
  2649. if (iCell < 0)
  2650. {
  2651. ch->ChatPacket(CHAT_TYPE_INFO, LC_TEXT("<â°í> ¿Å±æ ¼ö ¾ø´Â À§Ä¡ÀÔ´Ï´Ù."));
  2652. return ;
  2653. }
  2654. DestPos = TItemPos (DRAGON_SOUL_INVENTORY, iCell);
  2655. }
  2656.  
  2657. pkSafebox->Remove(p->bSafePos);
  2658. pkItem->AddToCharacter(ch, DestPos);
  2659. ITEM_MANAGER::instance().FlushDelayedSave(pkItem);
  2660. }
  2661. #ifdef __SPECIAL_STORAGE__
  2662. else if (pkItem->IsUpgradeItem())
  2663. {
  2664. if (UPGRADE_INVENTORY != p->ItemPos.window_type)
  2665. {
  2666. ch->ChatPacket(CHAT_TYPE_INFO, LC_TEXT("<â°í> ¿Å±æ ¼ö ¾ø´Â À§Ä¡ÀÔ´Ï´Ù."));
  2667. return;
  2668. }
  2669.  
  2670. TItemPos DestPos = p->ItemPos;
  2671.  
  2672. int iCell = ch->GetEmptyUpgradeInventory(pkItem);
  2673. if (iCell < 0)
  2674. {
  2675. ch->ChatPacket(CHAT_TYPE_INFO, LC_TEXT("<â°í> ¿Å±æ ¼ö ¾ø´Â À§Ä¡ÀÔ´Ï´Ù."));
  2676. return ;
  2677. }
  2678. DestPos = TItemPos (UPGRADE_INVENTORY, iCell);
  2679.  
  2680. pkSafebox->Remove(p->bSafePos);
  2681. pkItem->AddToCharacter(ch, DestPos);
  2682. ITEM_MANAGER::instance().FlushDelayedSave(pkItem);
  2683. }
  2684. else if (pkItem->IsBook())
  2685. {
  2686. if (BOOK_INVENTORY != p->ItemPos.window_type)
  2687. {
  2688. ch->ChatPacket(CHAT_TYPE_INFO, LC_TEXT("<â°í> ¿Å±æ ¼ö ¾ø´Â À§Ä¡ÀÔ´Ï´Ù."));
  2689. return;
  2690. }
  2691.  
  2692. TItemPos DestPos = p->ItemPos;
  2693.  
  2694. int iCell = ch->GetEmptyBookInventory(pkItem);
  2695. if (iCell < 0)
  2696. {
  2697. ch->ChatPacket(CHAT_TYPE_INFO, LC_TEXT("<â°í> ¿Å±æ ¼ö ¾ø´Â À§Ä¡ÀÔ´Ï´Ù."));
  2698. return ;
  2699. }
  2700. DestPos = TItemPos (BOOK_INVENTORY, iCell);
  2701.  
  2702. pkSafebox->Remove(p->bSafePos);
  2703. pkItem->AddToCharacter(ch, DestPos);
  2704. ITEM_MANAGER::instance().FlushDelayedSave(pkItem);
  2705. }
  2706. else if (pkItem->IsStone())
  2707. {
  2708. if (STONE_INVENTORY != p->ItemPos.window_type)
  2709. {
  2710. ch->ChatPacket(CHAT_TYPE_INFO, LC_TEXT("<â°í> ¿Å±æ ¼ö ¾ø´Â À§Ä¡ÀÔ´Ï´Ù."));
  2711. return;
  2712. }
  2713.  
  2714. TItemPos DestPos = p->ItemPos;
  2715.  
  2716. int iCell = ch->GetEmptyStoneInventory(pkItem);
  2717. if (iCell < 0)
  2718. {
  2719. ch->ChatPacket(CHAT_TYPE_INFO, LC_TEXT("<â°í> ¿Å±æ ¼ö ¾ø´Â À§Ä¡ÀÔ´Ï´Ù."));
  2720. return ;
  2721. }
  2722. DestPos = TItemPos (STONE_INVENTORY, iCell);
  2723.  
  2724. pkSafebox->Remove(p->bSafePos);
  2725. pkItem->AddToCharacter(ch, DestPos);
  2726. ITEM_MANAGER::instance().FlushDelayedSave(pkItem);
  2727. }
  2728. #endif
  2729. else
  2730. {
  2731.  
  2732. #ifdef __SPECIAL_STORAGE__
  2733. if (DRAGON_SOUL_INVENTORY == p->ItemPos.window_type ||
  2734. UPGRADE_INVENTORY == p->ItemPos.window_type ||
  2735. BOOK_INVENTORY == p->ItemPos.window_type ||
  2736. STONE_INVENTORY == p->ItemPos.window_type)
  2737. #else
  2738. if (DRAGON_SOUL_INVENTORY == p->ItemPos.window_type)
  2739. #endif
  2740. {
  2741. ch->ChatPacket(CHAT_TYPE_INFO, LC_TEXT("<â°í> ¿Å±æ ¼ö ¾ø´Â À§Ä¡ÀÔ´Ï´Ù."));
  2742. return;
  2743. }
  2744. // @fixme119
  2745. if (p->ItemPos.IsBeltInventoryPosition() && false == CBeltInventoryHelper::CanMoveIntoBeltInventory(pkItem))
  2746. {
  2747. ch->ChatPacket(CHAT_TYPE_INFO, LC_TEXT("ÀÌ ¾ÆÀÌÅÛÀº º§Æ® Àκ¥Å丮·Î ¿Å±æ ¼ö ¾ø½À´Ï´Ù."));
  2748. return;
  2749. }
  2750.  
  2751. pkSafebox->Remove(p->bSafePos);
  2752. pkItem->AddToCharacter(ch, p->ItemPos);
  2753. ITEM_MANAGER::instance().FlushDelayedSave(pkItem);
  2754. }
  2755.  
  2756. DWORD dwID = pkItem->GetID();
  2757. db_clientdesc->DBPacketHeader(HEADER_GD_ITEM_FLUSH, 0, sizeof(DWORD));
  2758. db_clientdesc->Packet(&dwID, sizeof(DWORD));
  2759.  
  2760. char szHint[128];
  2761. snprintf(szHint, sizeof(szHint), "%s %u", pkItem->GetName(), pkItem->GetCount());
  2762. if (bMall)
  2763. LogManager::instance().ItemLog(ch, pkItem, "MALL GET", szHint);
  2764. else
  2765. LogManager::instance().ItemLog(ch, pkItem, "SAFEBOX GET", szHint);
  2766. }
  2767.  
  2768. void CInputMain::SafeboxItemMove(LPCHARACTER ch, const char * data)
  2769. {
  2770. struct command_item_move * pinfo = (struct command_item_move *) data;
  2771.  
  2772. if (!ch->CanHandleItem())
  2773. return;
  2774.  
  2775. if (!ch->GetSafebox())
  2776. return;
  2777.  
  2778. ch->GetSafebox()->MoveItem(pinfo->Cell.cell, pinfo->CellTo.cell, pinfo->count);
  2779. }
  2780.  
  2781. // PARTY_JOIN_BUG_FIX
  2782. void CInputMain::PartyInvite(LPCHARACTER ch, const char * c_pData)
  2783. {
  2784. if (ch->GetArena())
  2785. {
  2786. ch->ChatPacket(CHAT_TYPE_INFO, LC_TEXT("´ë·ÃÀå¿¡¼­ »ç¿ëÇÏ½Ç ¼ö ¾ø½À´Ï´Ù."));
  2787. return;
  2788. }
  2789.  
  2790. TPacketCGPartyInvite * p = (TPacketCGPartyInvite*) c_pData;
  2791.  
  2792. LPCHARACTER pInvitee = CHARACTER_MANAGER::instance().Find(p->vid);
  2793.  
  2794. if (!pInvitee || !ch->GetDesc() || !pInvitee->GetDesc())
  2795. {
  2796. sys_err("PARTY Cannot find invited character");
  2797. return;
  2798. }
  2799. #ifdef __ENABLE_BATTLE_FIELD__
  2800. if (CBattleZone::instance().IsBattleZoneMapIndex(ch->GetMapIndex()))
  2801. {
  2802. ch->ChatPacket(CHAT_TYPE_INFO, LC_TEXT("BATTLE_ZONE_CANT_INVITE_PARTY"));
  2803. return;
  2804. }
  2805. #endif
  2806. ch->PartyInvite(pInvitee);
  2807. }
  2808.  
  2809. void CInputMain::PartyInviteAnswer(LPCHARACTER ch, const char * c_pData)
  2810. {
  2811. if (ch->GetArena())
  2812. {
  2813. ch->ChatPacket(CHAT_TYPE_INFO, LC_TEXT("´ë·ÃÀå¿¡¼­ »ç¿ëÇÏ½Ç ¼ö ¾ø½À´Ï´Ù."));
  2814. return;
  2815. }
  2816.  
  2817. TPacketCGPartyInviteAnswer * p = (TPacketCGPartyInviteAnswer*) c_pData;
  2818.  
  2819. LPCHARACTER pInviter = CHARACTER_MANAGER::instance().Find(p->leader_vid);
  2820.  
  2821. // pInviter °¡ ch ¿¡°Ô ÆÄƼ ¿äûÀ» Çß¾ú´Ù.
  2822.  
  2823. if (!pInviter)
  2824. ch->ChatPacket(CHAT_TYPE_INFO, LC_TEXT("<ÆÄƼ> ÆÄƼ¿äûÀ» ÇÑ Ä³¸¯Å͸¦ ãÀ»¼ö ¾ø½À´Ï´Ù."));
  2825. else if (!p->accept)
  2826. pInviter->PartyInviteDeny(ch->GetPlayerID());
  2827. else
  2828. pInviter->PartyInviteAccept(ch);
  2829. }
  2830. // END_OF_PARTY_JOIN_BUG_FIX
  2831.  
  2832. void CInputMain::PartySetState(LPCHARACTER ch, const char* c_pData)
  2833. {
  2834. if (!CPartyManager::instance().IsEnablePCParty())
  2835. {
  2836. ch->ChatPacket(CHAT_TYPE_INFO, LC_TEXT("<ÆÄƼ> ¼­¹ö ¹®Á¦·Î ÆÄƼ °ü·Ã 󸮸¦ ÇÒ ¼ö ¾ø½À´Ï´Ù."));
  2837. return;
  2838. }
  2839.  
  2840. TPacketCGPartySetState* p = (TPacketCGPartySetState*) c_pData;
  2841.  
  2842. if (!ch->GetParty())
  2843. return;
  2844.  
  2845. if (ch->GetParty()->GetLeaderPID() != ch->GetPlayerID())
  2846. {
  2847. ch->ChatPacket(CHAT_TYPE_INFO, LC_TEXT("<ÆÄƼ> ¸®´õ¸¸ º¯°æÇÒ ¼ö ÀÖ½À´Ï´Ù."));
  2848. return;
  2849. }
  2850.  
  2851. if (!ch->GetParty()->IsMember(p->pid))
  2852. {
  2853. ch->ChatPacket(CHAT_TYPE_INFO, LC_TEXT("<ÆÄƼ> »óŸ¦ º¯°æÇÏ·Á´Â »ç¶÷ÀÌ ÆÄƼ¿øÀÌ ¾Æ´Õ´Ï´Ù."));
  2854. return;
  2855. }
  2856.  
  2857. DWORD pid = p->pid;
  2858. sys_log(0, "PARTY SetRole pid %d to role %d state %s", pid, p->byRole, p->flag ? "on" : "off");
  2859.  
  2860. switch (p->byRole)
  2861. {
  2862. case PARTY_ROLE_NORMAL:
  2863. break;
  2864.  
  2865. case PARTY_ROLE_ATTACKER:
  2866. case PARTY_ROLE_TANKER:
  2867. case PARTY_ROLE_BUFFER:
  2868. case PARTY_ROLE_SKILL_MASTER:
  2869. case PARTY_ROLE_HASTE:
  2870. case PARTY_ROLE_DEFENDER:
  2871. if (ch->GetParty()->SetRole(pid, p->byRole, p->flag))
  2872. {
  2873. TPacketPartyStateChange pack;
  2874. pack.dwLeaderPID = ch->GetPlayerID();
  2875. pack.dwPID = p->pid;
  2876. pack.bRole = p->byRole;
  2877. pack.bFlag = p->flag;
  2878. db_clientdesc->DBPacket(HEADER_GD_PARTY_STATE_CHANGE, 0, &pack, sizeof(pack));
  2879. }
  2880. /* else
  2881. ch->ChatPacket(CHAT_TYPE_INFO, LC_TEXT("<ÆÄƼ> ¾îÅÂÄ¿ ¼³Á¤¿¡ ½ÇÆÐÇÏ¿´½À´Ï´Ù.")); */
  2882. break;
  2883.  
  2884. default:
  2885. sys_err("wrong byRole in PartySetState Packet name %s state %d", ch->GetName(), p->byRole);
  2886. break;
  2887. }
  2888. }
  2889.  
  2890. void CInputMain::PartyRemove(LPCHARACTER ch, const char* c_pData)
  2891. {
  2892. if (ch->GetArena())
  2893. {
  2894. ch->ChatPacket(CHAT_TYPE_INFO, LC_TEXT("´ë·ÃÀå¿¡¼­ »ç¿ëÇÏ½Ç ¼ö ¾ø½À´Ï´Ù."));
  2895. return;
  2896. }
  2897.  
  2898. if (!CPartyManager::instance().IsEnablePCParty())
  2899. {
  2900. ch->ChatPacket(CHAT_TYPE_INFO, LC_TEXT("<ÆÄƼ> ¼­¹ö ¹®Á¦·Î ÆÄƼ °ü·Ã 󸮸¦ ÇÒ ¼ö ¾ø½À´Ï´Ù."));
  2901. return;
  2902. }
  2903.  
  2904. if (ch->GetDungeon())
  2905. {
  2906. ch->ChatPacket(CHAT_TYPE_INFO, LC_TEXT("<ÆÄƼ> ´øÀü ¾È¿¡¼­´Â ÆÄƼ¿¡¼­ Ãß¹æÇÒ ¼ö ¾ø½À´Ï´Ù."));
  2907. return;
  2908. }
  2909.  
  2910. TPacketCGPartyRemove* p = (TPacketCGPartyRemove*) c_pData;
  2911.  
  2912. if (!ch->GetParty())
  2913. return;
  2914.  
  2915. LPPARTY pParty = ch->GetParty();
  2916. if (pParty->GetLeaderPID() == ch->GetPlayerID())
  2917. {
  2918. if (ch->GetDungeon())
  2919. {
  2920. ch->ChatPacket(CHAT_TYPE_INFO, LC_TEXT("<ÆÄƼ> ´øÁ¯³»¿¡¼­´Â ÆÄƼ¿øÀ» Ãß¹æÇÒ ¼ö ¾ø½À´Ï´Ù."));
  2921. }
  2922. else
  2923. {
  2924. // Àû·æ¼º¿¡¼­ ÆÄƼÀåÀÌ ´øÁ¯ ¹Û¿¡¼­ ÆÄƼ ÇØ»ê ¸øÇÏ°Ô ¸·ÀÚ
  2925. if(pParty->IsPartyInDungeon(351))
  2926. {
  2927. ch->ChatPacket(CHAT_TYPE_INFO, LC_TEXT("<ÆÄƼ>´øÀü ¾È¿¡ ÆÄƼ¿øÀÌ ÀÖ¾î ÆÄÆ¼¸¦ ÇØ»ê ÇÒ ¼ö ¾ø½À´Ï´Ù."));
  2928. return;
  2929. }
  2930.  
  2931. // leader can remove any member
  2932. if (p->pid == ch->GetPlayerID() || pParty->GetMemberCount() == 2)
  2933. {
  2934. // party disband
  2935. CPartyManager::instance().DeleteParty(pParty);
  2936. }
  2937. else
  2938. {
  2939. LPCHARACTER B = CHARACTER_MANAGER::instance().FindByPID(p->pid);
  2940. if (B)
  2941. {
  2942. //pParty->SendPartyRemoveOneToAll(B);
  2943. B->ChatPacket(CHAT_TYPE_INFO, LC_TEXT("<ÆÄƼ> ÆÄƼ¿¡¼­ Ãß¹æ´çÇϼ̽À´Ï´Ù."));
  2944. //pParty->Unlink(B);
  2945. //CPartyManager::instance().SetPartyMember(B->GetPlayerID(), NULL);
  2946. }
  2947. pParty->Quit(p->pid);
  2948. }
  2949. }
  2950. }
  2951. else
  2952. {
  2953. // otherwise, only remove itself
  2954. if (p->pid == ch->GetPlayerID())
  2955. {
  2956. if (ch->GetDungeon())
  2957. {
  2958. ch->ChatPacket(CHAT_TYPE_INFO, LC_TEXT("<ÆÄƼ> ´øÁ¯³»¿¡¼­´Â ÆÄƼ¸¦ ³ª°¥ ¼ö ¾ø½À´Ï´Ù."));
  2959. }
  2960. else
  2961. {
  2962. if (pParty->GetMemberCount() == 2)
  2963. {
  2964. // party disband
  2965. CPartyManager::instance().DeleteParty(pParty);
  2966. }
  2967. else
  2968. {
  2969. ch->ChatPacket(CHAT_TYPE_INFO, LC_TEXT("<ÆÄƼ> ÆÄƼ¿¡¼­ ³ª°¡¼Ì½À´Ï´Ù."));
  2970. //pParty->SendPartyRemoveOneToAll(ch);
  2971. pParty->Quit(ch->GetPlayerID());
  2972. //pParty->SendPartyRemoveAllToOne(ch);
  2973. //CPartyManager::instance().SetPartyMember(ch->GetPlayerID(), NULL);
  2974. }
  2975. }
  2976. }
  2977. else
  2978. {
  2979. ch->ChatPacket(CHAT_TYPE_INFO, LC_TEXT("<ÆÄƼ> ´Ù¸¥ ÆÄƼ¿øÀ» Å»Åð½Ãų ¼ö ¾ø½À´Ï´Ù."));
  2980. }
  2981. }
  2982. }
  2983.  
  2984. void CInputMain::AnswerMakeGuild(LPCHARACTER ch, const char* c_pData)
  2985. {
  2986. TPacketCGAnswerMakeGuild* p = (TPacketCGAnswerMakeGuild*) c_pData;
  2987.  
  2988. if (ch->GetGold() < 200000)
  2989. return;
  2990.  
  2991. if (get_global_time() - ch->GetQuestFlag("guild_manage.new_disband_time") <
  2992. CGuildManager::instance().GetDisbandDelay())
  2993. {
  2994. ch->ChatPacket(CHAT_TYPE_INFO, LC_TEXT("<±æµå> ÇØ»êÇÑ ÈÄ %dÀÏ À̳»¿¡´Â ±æµå¸¦ ¸¸µé ¼ö ¾ø½À´Ï´Ù."),
  2995. quest::CQuestManager::instance().GetEventFlag("guild_disband_delay"));
  2996. return;
  2997. }
  2998.  
  2999. if (get_global_time() - ch->GetQuestFlag("guild_manage.new_withdraw_time") <
  3000. CGuildManager::instance().GetWithdrawDelay())
  3001. {
  3002. ch->ChatPacket(CHAT_TYPE_INFO, LC_TEXT("<±æµå> Å»ÅðÇÑ ÈÄ %dÀÏ À̳»¿¡´Â ±æµå¸¦ ¸¸µé ¼ö ¾ø½À´Ï´Ù."),
  3003. quest::CQuestManager::instance().GetEventFlag("guild_withdraw_delay"));
  3004. return;
  3005. }
  3006.  
  3007. if (ch->GetGuild())
  3008. return;
  3009.  
  3010. CGuildManager& gm = CGuildManager::instance();
  3011.  
  3012. TGuildCreateParameter cp;
  3013. memset(&cp, 0, sizeof(cp));
  3014.  
  3015. cp.master = ch;
  3016. strlcpy(cp.name, p->guild_name, sizeof(cp.name));
  3017.  
  3018. if (cp.name[0] == 0 || !check_name(cp.name))
  3019. {
  3020. ch->ChatPacket(CHAT_TYPE_INFO, LC_TEXT("ÀûÇÕÇÏÁö ¾ÊÀº ±æµå À̸§ ÀÔ´Ï´Ù."));
  3021. return;
  3022. }
  3023.  
  3024. DWORD dwGuildID = gm.CreateGuild(cp);
  3025.  
  3026. if (dwGuildID)
  3027. {
  3028. ch->ChatPacket(CHAT_TYPE_INFO, LC_TEXT("<±æµå> [%s] ±æµå°¡ »ý¼ºµÇ¾ú½À´Ï´Ù."), cp.name);
  3029.  
  3030. int GuildCreateFee = 200000;
  3031.  
  3032. ch->PointChange(POINT_GOLD, -GuildCreateFee);
  3033. DBManager::instance().SendMoneyLog(MONEY_LOG_GUILD, ch->GetPlayerID(), -GuildCreateFee);
  3034.  
  3035. char Log[128];
  3036. snprintf(Log, sizeof(Log), "GUILD_NAME %s MASTER %s", cp.name, ch->GetName());
  3037. LogManager::instance().CharLog(ch, 0, "MAKE_GUILD", Log);
  3038.  
  3039. ch->RemoveSpecifyItem(GUILD_CREATE_ITEM_VNUM, 1);
  3040. //ch->SendGuildName(dwGuildID);
  3041. }
  3042. else
  3043. ch->ChatPacket(CHAT_TYPE_INFO, LC_TEXT("<±æµå> ±æµå »ý¼º¿¡ ½ÇÆÐÇÏ¿´½À´Ï´Ù."));
  3044. }
  3045.  
  3046. void CInputMain::PartyUseSkill(LPCHARACTER ch, const char* c_pData)
  3047. {
  3048. TPacketCGPartyUseSkill* p = (TPacketCGPartyUseSkill*) c_pData;
  3049. if (!ch->GetParty())
  3050. return;
  3051.  
  3052. if (ch->GetPlayerID() != ch->GetParty()->GetLeaderPID())
  3053. {
  3054. ch->ChatPacket(CHAT_TYPE_INFO, LC_TEXT("<ÆÄƼ> ÆÄƼ ±â¼úÀº ÆÄƼÀ常 »ç¿ëÇÒ ¼ö ÀÖ½À´Ï´Ù."));
  3055. return;
  3056. }
  3057.  
  3058. switch (p->bySkillIndex)
  3059. {
  3060. case PARTY_SKILL_HEAL:
  3061. ch->GetParty()->HealParty();
  3062. break;
  3063. case PARTY_SKILL_WARP:
  3064. {
  3065. LPCHARACTER pch = CHARACTER_MANAGER::instance().Find(p->vid);
  3066. if (pch)
  3067. ch->GetParty()->SummonToLeader(pch->GetPlayerID());
  3068. else
  3069. ch->ChatPacket(CHAT_TYPE_INFO, LC_TEXT("<ÆÄƼ> ¼ÒȯÇÏ·Á´Â ´ë»óÀ» ãÀ» ¼ö ¾ø½À´Ï´Ù."));
  3070. }
  3071. break;
  3072. }
  3073. }
  3074.  
  3075. void CInputMain::PartyParameter(LPCHARACTER ch, const char * c_pData)
  3076. {
  3077. TPacketCGPartyParameter * p = (TPacketCGPartyParameter *) c_pData;
  3078.  
  3079. if (ch->GetParty())
  3080. ch->GetParty()->SetParameter(p->bDistributeMode);
  3081. }
  3082.  
  3083. size_t GetSubPacketSize(const GUILD_SUBHEADER_CG& header)
  3084. {
  3085. switch (header)
  3086. {
  3087. case GUILD_SUBHEADER_CG_DEPOSIT_MONEY: return sizeof(int);
  3088. case GUILD_SUBHEADER_CG_WITHDRAW_MONEY: return sizeof(int);
  3089. case GUILD_SUBHEADER_CG_ADD_MEMBER: return sizeof(DWORD);
  3090. case GUILD_SUBHEADER_CG_REMOVE_MEMBER: return sizeof(DWORD);
  3091. case GUILD_SUBHEADER_CG_CHANGE_GRADE_NAME: return 10;
  3092. case GUILD_SUBHEADER_CG_CHANGE_GRADE_AUTHORITY: return sizeof(BYTE) + sizeof(BYTE);
  3093. case GUILD_SUBHEADER_CG_OFFER: return sizeof(DWORD);
  3094. case GUILD_SUBHEADER_CG_CHARGE_GSP: return sizeof(int);
  3095. case GUILD_SUBHEADER_CG_POST_COMMENT: return 1;
  3096. case GUILD_SUBHEADER_CG_DELETE_COMMENT: return sizeof(DWORD);
  3097. case GUILD_SUBHEADER_CG_REFRESH_COMMENT: return 0;
  3098. case GUILD_SUBHEADER_CG_CHANGE_MEMBER_GRADE: return sizeof(DWORD) + sizeof(BYTE);
  3099. case GUILD_SUBHEADER_CG_USE_SKILL: return sizeof(TPacketCGGuildUseSkill);
  3100. case GUILD_SUBHEADER_CG_CHANGE_MEMBER_GENERAL: return sizeof(DWORD) + sizeof(BYTE);
  3101. case GUILD_SUBHEADER_CG_GUILD_INVITE_ANSWER: return sizeof(DWORD) + sizeof(BYTE);
  3102. }
  3103.  
  3104. return 0;
  3105. }
  3106.  
  3107. int CInputMain::Guild(LPCHARACTER ch, const char * data, size_t uiBytes)
  3108. {
  3109. if (uiBytes < sizeof(TPacketCGGuild))
  3110. return -1;
  3111.  
  3112. const TPacketCGGuild* p = reinterpret_cast<const TPacketCGGuild*>(data);
  3113. const char* c_pData = data + sizeof(TPacketCGGuild);
  3114.  
  3115. uiBytes -= sizeof(TPacketCGGuild);
  3116.  
  3117. const GUILD_SUBHEADER_CG SubHeader = static_cast<GUILD_SUBHEADER_CG>(p->subheader);
  3118. const size_t SubPacketLen = GetSubPacketSize(SubHeader);
  3119.  
  3120. if (uiBytes < SubPacketLen)
  3121. {
  3122. return -1;
  3123. }
  3124.  
  3125. CGuild* pGuild = ch->GetGuild();
  3126.  
  3127. if (NULL == pGuild)
  3128. {
  3129. if (SubHeader != GUILD_SUBHEADER_CG_GUILD_INVITE_ANSWER)
  3130. {
  3131. ch->ChatPacket(CHAT_TYPE_INFO, LC_TEXT("<±æµå> ±æµå¿¡ ¼ÓÇØÀÖÁö ¾Ê½À´Ï´Ù."));
  3132. return SubPacketLen;
  3133. }
  3134. }
  3135.  
  3136. switch (SubHeader)
  3137. {
  3138. case GUILD_SUBHEADER_CG_DEPOSIT_MONEY:
  3139. {
  3140. // by mhh : ±æµåÀÚ±ÝÀº ´çºÐ°£ ³ÖÀ» ¼ö ¾ø´Ù.
  3141. return SubPacketLen;
  3142.  
  3143. const int gold = MIN(*reinterpret_cast<const int*>(c_pData), __deposit_limit());
  3144.  
  3145. if (gold < 0)
  3146. {
  3147. ch->ChatPacket(CHAT_TYPE_INFO, LC_TEXT("<±æµå> À߸øµÈ ±Ý¾×ÀÔ´Ï´Ù."));
  3148. return SubPacketLen;
  3149. }
  3150.  
  3151. if (ch->GetGold() < gold)
  3152. {
  3153. ch->ChatPacket(CHAT_TYPE_INFO, LC_TEXT("<±æµå> °¡Áö°í ÀÖ´Â µ·ÀÌ ºÎÁ·ÇÕ´Ï´Ù."));
  3154. return SubPacketLen;
  3155. }
  3156.  
  3157. pGuild->RequestDepositMoney(ch, gold);
  3158. }
  3159. return SubPacketLen;
  3160.  
  3161. case GUILD_SUBHEADER_CG_WITHDRAW_MONEY:
  3162. {
  3163. // by mhh : ±æµåÀÚ±ÝÀº ´çºÐ°£ »¬ ¼ö ¾ø´Ù.
  3164. return SubPacketLen;
  3165.  
  3166. const int gold = MIN(*reinterpret_cast<const int*>(c_pData), 500000);
  3167.  
  3168. if (gold < 0)
  3169. {
  3170. ch->ChatPacket(CHAT_TYPE_INFO, LC_TEXT("<±æµå> À߸øµÈ ±Ý¾×ÀÔ´Ï´Ù."));
  3171. return SubPacketLen;
  3172. }
  3173.  
  3174. pGuild->RequestWithdrawMoney(ch, gold);
  3175. }
  3176. return SubPacketLen;
  3177.  
  3178. case GUILD_SUBHEADER_CG_ADD_MEMBER:
  3179. {
  3180. const DWORD vid = *reinterpret_cast<const DWORD*>(c_pData);
  3181. LPCHARACTER newmember = CHARACTER_MANAGER::instance().Find(vid);
  3182.  
  3183. if (!newmember)
  3184. {
  3185. ch->ChatPacket(CHAT_TYPE_INFO, LC_TEXT("<±æµå> ±×·¯ÇÑ »ç¶÷À» ãÀ» ¼ö ¾ø½À´Ï´Ù."));
  3186. return SubPacketLen;
  3187. }
  3188.  
  3189. if (!newmember->IsPC())
  3190. {
  3191. ch->ChatPacket(CHAT_TYPE_INFO, LC_TEXT("THE ACTION HAS BEEN STOPED - EXPLOIT DETECTED"));
  3192. return SubPacketLen;
  3193. }
  3194.  
  3195. if (!ch->IsPC())
  3196. return SubPacketLen;
  3197.  
  3198. #ifdef __ENABLE_BATTLE_FIELD__
  3199. if (CBattleZone::instance().IsBattleZoneMapIndex(ch->GetMapIndex()))
  3200. {
  3201. ch->ChatPacket(CHAT_TYPE_INFO, LC_TEXT("BATTLE_ZONE_CANT_INVITE_GUILD"));
  3202. return SubPacketLen;
  3203. }
  3204. #endif
  3205.  
  3206. if (!newmember->IsPC())
  3207. return SubPacketLen;
  3208.  
  3209. if (LC_IsCanada() == true)
  3210. {
  3211. if (newmember->GetQuestFlag("change_guild_master.be_other_member") > get_global_time())
  3212. {
  3213. ch->ChatPacket(CHAT_TYPE_INFO, LC_TEXT("<±æµå> ¾ÆÁ÷ °¡ÀÔÇÒ ¼ö ¾ø´Â ij¸¯ÅÍÀÔ´Ï´Ù"));
  3214. return SubPacketLen;
  3215. }
  3216. }
  3217.  
  3218. pGuild->Invite(ch, newmember);
  3219. }
  3220. return SubPacketLen;
  3221.  
  3222. case GUILD_SUBHEADER_CG_REMOVE_MEMBER:
  3223. {
  3224. if (pGuild->UnderAnyWar() != 0)
  3225. {
  3226. ch->ChatPacket(CHAT_TYPE_INFO, LC_TEXT("<±æµå> ±æµåÀü Áß¿¡´Â ±æµå¿øÀ» Å»Åð½Ãų ¼ö ¾ø½À´Ï´Ù."));
  3227. return SubPacketLen;
  3228. }
  3229.  
  3230. const DWORD pid = *reinterpret_cast<const DWORD*>(c_pData);
  3231. const TGuildMember* m = pGuild->GetMember(ch->GetPlayerID());
  3232.  
  3233. if (NULL == m)
  3234. return -1;
  3235.  
  3236. LPCHARACTER member = CHARACTER_MANAGER::instance().FindByPID(pid);
  3237.  
  3238. if (member)
  3239. {
  3240. if (member->GetGuild() != pGuild)
  3241. {
  3242. ch->ChatPacket(CHAT_TYPE_INFO, LC_TEXT("<±æµå> »ó´ë¹æÀÌ °°Àº ±æµå°¡ ¾Æ´Õ´Ï´Ù."));
  3243. return SubPacketLen;
  3244. }
  3245.  
  3246. if (!pGuild->HasGradeAuth(m->grade, GUILD_AUTH_REMOVE_MEMBER))
  3247. {
  3248. ch->ChatPacket(CHAT_TYPE_INFO, LC_TEXT("<±æµå> ±æµå¿øÀ» °­Á¦ Å»Åð ½Ãų ±ÇÇÑÀÌ ¾ø½À´Ï´Ù."));
  3249. return SubPacketLen;
  3250. }
  3251.  
  3252. member->SetQuestFlag("guild_manage.new_withdraw_time", get_global_time());
  3253. pGuild->RequestRemoveMember(member->GetPlayerID());
  3254.  
  3255. if (g_bGuildInviteLimit)
  3256. {
  3257. DBManager::instance().Query("REPLACE INTO guild_invite_limit VALUES(%d, %d)", pGuild->GetID(), get_global_time());
  3258. }
  3259. }
  3260. else
  3261. {
  3262. if (!pGuild->HasGradeAuth(m->grade, GUILD_AUTH_REMOVE_MEMBER))
  3263. {
  3264. ch->ChatPacket(CHAT_TYPE_INFO, LC_TEXT("<±æµå> ±æµå¿øÀ» °­Á¦ Å»Åð ½Ãų ±ÇÇÑÀÌ ¾ø½À´Ï´Ù."));
  3265. return SubPacketLen;
  3266. }
  3267.  
  3268. if (pGuild->RequestRemoveMember(pid))
  3269. ch->ChatPacket(CHAT_TYPE_INFO, LC_TEXT("<±æµå> ±æµå¿øÀ» °­Á¦ Å»Åð ½ÃÄ×½À´Ï´Ù."));
  3270. else
  3271. ch->ChatPacket(CHAT_TYPE_INFO, LC_TEXT("<±æµå> ±×·¯ÇÑ »ç¶÷À» ãÀ» ¼ö ¾ø½À´Ï´Ù."));
  3272. }
  3273. }
  3274. return SubPacketLen;
  3275.  
  3276. case GUILD_SUBHEADER_CG_CHANGE_GRADE_NAME:
  3277. {
  3278. char gradename[GUILD_GRADE_NAME_MAX_LEN + 1];
  3279. strlcpy(gradename, c_pData + 1, sizeof(gradename));
  3280.  
  3281. const TGuildMember * m = pGuild->GetMember(ch->GetPlayerID());
  3282.  
  3283. if (NULL == m)
  3284. return -1;
  3285.  
  3286. if (m->grade != GUILD_LEADER_GRADE)
  3287. {
  3288. ch->ChatPacket(CHAT_TYPE_INFO, LC_TEXT("<±æµå> Á÷À§ À̸§À» º¯°æÇÒ ±ÇÇÑÀÌ ¾ø½À´Ï´Ù."));
  3289. }
  3290. else if (*c_pData == GUILD_LEADER_GRADE)
  3291. {
  3292. ch->ChatPacket(CHAT_TYPE_INFO, LC_TEXT("<±æµå> ±æµåÀåÀÇ Á÷À§ À̸§Àº º¯°æÇÒ ¼ö ¾ø½À´Ï´Ù."));
  3293. }
  3294. else if (!check_name(gradename))
  3295. {
  3296. ch->ChatPacket(CHAT_TYPE_INFO, LC_TEXT("<±æµå> ÀûÇÕÇÏÁö ¾ÊÀº Á÷À§ À̸§ ÀÔ´Ï´Ù."));
  3297. }
  3298. else
  3299. {
  3300. pGuild->ChangeGradeName(*c_pData, gradename);
  3301. }
  3302. }
  3303. return SubPacketLen;
  3304.  
  3305. case GUILD_SUBHEADER_CG_CHANGE_GRADE_AUTHORITY:
  3306. {
  3307. const TGuildMember* m = pGuild->GetMember(ch->GetPlayerID());
  3308.  
  3309. if (NULL == m)
  3310. return -1;
  3311.  
  3312. if (m->grade != GUILD_LEADER_GRADE)
  3313. {
  3314. ch->ChatPacket(CHAT_TYPE_INFO, LC_TEXT("<±æµå> Á÷À§ ±ÇÇÑÀ» º¯°æÇÒ ±ÇÇÑÀÌ ¾ø½À´Ï´Ù."));
  3315. }
  3316. else if (*c_pData == GUILD_LEADER_GRADE)
  3317. {
  3318. ch->ChatPacket(CHAT_TYPE_INFO, LC_TEXT("<±æµå> ±æµåÀåÀÇ ±ÇÇÑÀº º¯°æÇÒ ¼ö ¾ø½À´Ï´Ù."));
  3319. }
  3320. else
  3321. {
  3322. pGuild->ChangeGradeAuth(*c_pData, *(c_pData + 1));
  3323. }
  3324. }
  3325. return SubPacketLen;
  3326.  
  3327. case GUILD_SUBHEADER_CG_OFFER:
  3328. {
  3329. DWORD offer = *reinterpret_cast<const DWORD*>(c_pData);
  3330.  
  3331. if (pGuild->GetLevel() >= GUILD_MAX_LEVEL)
  3332. {
  3333. ch->ChatPacket(CHAT_TYPE_INFO, LC_TEXT("<±æµå> ±æµå°¡ ÀÌ¹Ì ÃÖ°í ·¹º§ÀÔ´Ï´Ù."));
  3334. }
  3335. else
  3336. {
  3337. offer /= 100;
  3338. offer *= 100;
  3339.  
  3340. if (pGuild->OfferExp(ch, offer))
  3341. {
  3342. ch->ChatPacket(CHAT_TYPE_INFO, LC_TEXT("<±æµå> %uÀÇ °æÇèÄ¡¸¦ ÅõÀÚÇÏ¿´½À´Ï´Ù."), offer);
  3343. }
  3344. else
  3345. {
  3346. ch->ChatPacket(CHAT_TYPE_INFO, LC_TEXT("<±æµå> °æÇèÄ¡ ÅõÀÚ¿¡ ½ÇÆÐÇÏ¿´½À´Ï´Ù."));
  3347. }
  3348. }
  3349. }
  3350. return SubPacketLen;
  3351.  
  3352. case GUILD_SUBHEADER_CG_CHARGE_GSP:
  3353. {
  3354. const int offer = *reinterpret_cast<const int*>(c_pData);
  3355. const int gold = offer * 100;
  3356.  
  3357. if (offer < 0 || gold < offer || gold < 0 || ch->GetGold() < gold)
  3358. {
  3359. ch->ChatPacket(CHAT_TYPE_INFO, LC_TEXT("<±æµå> µ·ÀÌ ºÎÁ·ÇÕ´Ï´Ù."));
  3360. return SubPacketLen;
  3361. }
  3362.  
  3363. if (!pGuild->ChargeSP(ch, offer))
  3364. {
  3365. ch->ChatPacket(CHAT_TYPE_INFO, LC_TEXT("<±æµå> ¿ë½Å·Â ȸº¹¿¡ ½ÇÆÐÇÏ¿´½À´Ï´Ù."));
  3366. }
  3367. }
  3368. return SubPacketLen;
  3369.  
  3370. case GUILD_SUBHEADER_CG_POST_COMMENT:
  3371. {
  3372. const size_t length = *c_pData;
  3373.  
  3374. if (length > GUILD_COMMENT_MAX_LEN)
  3375. {
  3376. // À߸øµÈ ±æÀÌ.. ²÷¾îÁÖÀÚ.
  3377. sys_err("POST_COMMENT: %s comment too long (length: %u)", ch->GetName(), length);
  3378. ch->GetDesc()->SetPhase(PHASE_CLOSE);
  3379. return -1;
  3380. }
  3381.  
  3382. if (uiBytes < 1 + length)
  3383. return -1;
  3384.  
  3385. const TGuildMember* m = pGuild->GetMember(ch->GetPlayerID());
  3386.  
  3387. if (NULL == m)
  3388. return -1;
  3389.  
  3390. if (length && !pGuild->HasGradeAuth(m->grade, GUILD_AUTH_NOTICE) && *(c_pData + 1) == '!')
  3391. {
  3392. ch->ChatPacket(CHAT_TYPE_INFO, LC_TEXT("<±æµå> °øÁö±ÛÀ» ÀÛ¼ºÇÒ ±ÇÇÑÀÌ ¾ø½À´Ï´Ù."));
  3393. }
  3394. else
  3395. {
  3396. std::string str(c_pData + 1, length);
  3397. pGuild->AddComment(ch, str);
  3398. }
  3399.  
  3400. return (1 + length);
  3401. }
  3402.  
  3403. case GUILD_SUBHEADER_CG_DELETE_COMMENT:
  3404. {
  3405. const DWORD comment_id = *reinterpret_cast<const DWORD*>(c_pData);
  3406.  
  3407. pGuild->DeleteComment(ch, comment_id);
  3408. }
  3409. return SubPacketLen;
  3410.  
  3411. case GUILD_SUBHEADER_CG_REFRESH_COMMENT:
  3412. pGuild->RefreshComment(ch);
  3413. return SubPacketLen;
  3414.  
  3415. case GUILD_SUBHEADER_CG_CHANGE_MEMBER_GRADE:
  3416. {
  3417. const DWORD pid = *reinterpret_cast<const DWORD*>(c_pData);
  3418. const BYTE grade = *(c_pData + sizeof(DWORD));
  3419. const TGuildMember* m = pGuild->GetMember(ch->GetPlayerID());
  3420.  
  3421. if (NULL == m)
  3422. return -1;
  3423.  
  3424. if (m->grade != GUILD_LEADER_GRADE)
  3425. ch->ChatPacket(CHAT_TYPE_INFO, LC_TEXT("<±æµå> Á÷À§¸¦ º¯°æÇÒ ±ÇÇÑÀÌ ¾ø½À´Ï´Ù."));
  3426. else if (ch->GetPlayerID() == pid)
  3427. ch->ChatPacket(CHAT_TYPE_INFO, LC_TEXT("<±æµå> ±æµåÀåÀÇ Á÷À§´Â º¯°æÇÒ ¼ö ¾ø½À´Ï´Ù."));
  3428. else if (grade == 1)
  3429. ch->ChatPacket(CHAT_TYPE_INFO, LC_TEXT("<±æµå> ±æµåÀåÀ¸·Î Á÷À§¸¦ º¯°æÇÒ ¼ö ¾ø½À´Ï´Ù."));
  3430. else
  3431. pGuild->ChangeMemberGrade(pid, grade);
  3432. }
  3433. return SubPacketLen;
  3434.  
  3435. case GUILD_SUBHEADER_CG_USE_SKILL:
  3436. {
  3437. const TPacketCGGuildUseSkill* p = reinterpret_cast<const TPacketCGGuildUseSkill*>(c_pData);
  3438.  
  3439. pGuild->UseSkill(p->dwVnum, ch, p->dwPID);
  3440. }
  3441. return SubPacketLen;
  3442.  
  3443. case GUILD_SUBHEADER_CG_CHANGE_MEMBER_GENERAL:
  3444. {
  3445. const DWORD pid = *reinterpret_cast<const DWORD*>(c_pData);
  3446. const BYTE is_general = *(c_pData + sizeof(DWORD));
  3447. const TGuildMember* m = pGuild->GetMember(ch->GetPlayerID());
  3448.  
  3449. if (NULL == m)
  3450. return -1;
  3451.  
  3452. if (m->grade != GUILD_LEADER_GRADE)
  3453. {
  3454. ch->ChatPacket(CHAT_TYPE_INFO, LC_TEXT("<±æµå> À屺À» ÁöÁ¤ÇÒ ±ÇÇÑÀÌ ¾ø½À´Ï´Ù."));
  3455. }
  3456. else
  3457. {
  3458. if (!pGuild->ChangeMemberGeneral(pid, is_general))
  3459. {
  3460. ch->ChatPacket(CHAT_TYPE_INFO, LC_TEXT("<±æµå> ´õÀÌ»ó Àå¼ö¸¦ ÁöÁ¤ÇÒ ¼ö ¾ø½À´Ï´Ù."));
  3461. }
  3462. }
  3463. }
  3464. return SubPacketLen;
  3465.  
  3466. case GUILD_SUBHEADER_CG_GUILD_INVITE_ANSWER:
  3467. {
  3468. const DWORD guild_id = *reinterpret_cast<const DWORD*>(c_pData);
  3469. const BYTE accept = *(c_pData + sizeof(DWORD));
  3470.  
  3471. CGuild * g = CGuildManager::instance().FindGuild(guild_id);
  3472.  
  3473. if (g)
  3474. {
  3475. if (accept)
  3476. g->InviteAccept(ch);
  3477. else
  3478. g->InviteDeny(ch->GetPlayerID());
  3479. }
  3480. }
  3481. return SubPacketLen;
  3482.  
  3483. }
  3484.  
  3485. return 0;
  3486. }
  3487.  
  3488. void CInputMain::Fishing(LPCHARACTER ch, const char* c_pData)
  3489. {
  3490. TPacketCGFishing* p = (TPacketCGFishing*)c_pData;
  3491. ch->SetRotation(p->dir * 5);
  3492. ch->fishing();
  3493. return;
  3494. }
  3495.  
  3496. void CInputMain::ItemGive(LPCHARACTER ch, const char* c_pData)
  3497. {
  3498. TPacketCGGiveItem* p = (TPacketCGGiveItem*) c_pData;
  3499. LPCHARACTER to_ch = CHARACTER_MANAGER::instance().Find(p->dwTargetVID);
  3500.  
  3501. if (to_ch)
  3502. ch->GiveItem(to_ch, p->ItemPos);
  3503. else
  3504. ch->ChatPacket(CHAT_TYPE_INFO, LC_TEXT("¾ÆÀÌÅÛÀ» °Ç³×ÁÙ ¼ö ¾ø½À´Ï´Ù."));
  3505. }
  3506.  
  3507. void CInputMain::Hack(LPCHARACTER ch, const char * c_pData)
  3508. {
  3509. TPacketCGHack * p = (TPacketCGHack *) c_pData;
  3510.  
  3511. char buf[sizeof(p->szBuf)];
  3512. strlcpy(buf, p->szBuf, sizeof(buf));
  3513.  
  3514. sys_err("HACK_DETECT: %s %s", ch->GetName(), buf);
  3515.  
  3516. // ÇöÀç Ŭ¶óÀÌ¾ðÆ®¿¡¼­ ÀÌ ÆÐŶÀ» º¸³»´Â °æ¿ì°¡ ¾øÀ¸¹Ç·Î ¹«Á¶°Ç ²÷µµ·Ï ÇÑ´Ù
  3517. ch->GetDesc()->SetPhase(PHASE_CLOSE);
  3518. }
  3519.  
  3520. int CInputMain::MyShop(LPCHARACTER ch, const char * c_pData, size_t uiBytes)
  3521. {
  3522. TPacketCGMyShop * p = (TPacketCGMyShop *) c_pData;
  3523. int iExtraLen = p->bCount * sizeof(TShopItemTable);
  3524. #ifdef SHOP_BLOCK_GAME99
  3525. if (g_bChannel >= 99 & ch->GetGMLevel() <= 0) {
  3526. ch->ChatPacket(CHAT_TYPE_INFO, LC_TEXT( "SHOP_OX_ERROR"));
  3527. return (iExtraLen);
  3528. }
  3529. #endif
  3530. #ifdef OFFLINE_SHOP
  3531. if (quest::CQuestManager::instance().GetEventFlag("shop_off")==1)
  3532. if (ch)
  3533. {
  3534. ch->ChatPacket(CHAT_TYPE_INFO, LC_TEXT( "SHOP_TEMP_OFF"));
  3535. return (iExtraLen);
  3536. }
  3537. #endif
  3538. #ifdef SHOP_GM_PRIVILEGES
  3539. if (GM_PLAYER < ch->GetGMLevel() && SHOP_GM_PRIVILEGES >ch->GetGMLevel()) {
  3540. ch->ChatPacket(CHAT_TYPE_INFO, LC_TEXT("SHOP_PRIV_ERROR"));
  3541. return (iExtraLen);
  3542. }
  3543. #endif
  3544. if (uiBytes < sizeof(TPacketCGMyShop) + iExtraLen)
  3545. return -1;
  3546. #ifndef FULL_YANG
  3547. if (ch->GetGold() >= GOLD_MAX)
  3548. {
  3549. ch->ChatPacket(CHAT_TYPE_INFO, LC_TEXT("¼ÒÀ¯ µ·ÀÌ 20¾ï³ÉÀ» ³Ñ¾î °Å·¡¸¦ ÇÛ¼ö°¡ ¾ø½À´Ï´Ù."));
  3550. sys_log(0, "MyShop ==> OverFlow Gold id %u name %s ", ch->GetPlayerID(), ch->GetName());
  3551. return (iExtraLen);
  3552. }
  3553. #endif
  3554. if (ch->IsStun() || ch->IsDead())
  3555. return (iExtraLen);
  3556.  
  3557. if (ch->GetExchange() || ch->IsOpenSafebox() || ch->GetShopOwner() || ch->IsCubeOpen())
  3558. {
  3559. ch->ChatPacket(CHAT_TYPE_INFO, LC_TEXT("´Ù¸¥ °Å·¡ÁßÀϰæ¿ì °³ÀλóÁ¡À» ¿­¼ö°¡ ¾ø½À´Ï´Ù."));
  3560. return (iExtraLen);
  3561. }
  3562.  
  3563. sys_log(0, "MyShop count %d", p->bCount);
  3564. #ifdef OFFLINE_SHOP
  3565. ch->OpenMyShop(p->szSign, (TShopItemTable *)(c_pData + sizeof(TPacketCGMyShop)), p->bCount, p->days);
  3566. #else
  3567. ch->OpenMyShop(p->szSign, (TShopItemTable *)(c_pData + sizeof(TPacketCGMyShop)), p->bCount);
  3568. #endif
  3569. return (iExtraLen);
  3570. }
  3571.  
  3572. #ifdef __SHOW_CHEST_DROP__
  3573. void CInputMain::ChestDropInfo(LPCHARACTER ch, const char* c_pData)
  3574. {
  3575. TPacketCGChestDropInfo* p = (TPacketCGChestDropInfo*) c_pData;
  3576.  
  3577. if(p->wInventoryCell >= INVENTORY_MAX_NUM)
  3578. return;
  3579.  
  3580. LPITEM pkItem = ch->GetInventoryItem(p->wInventoryCell);
  3581.  
  3582. if (!pkItem)
  3583. return;
  3584.  
  3585. std::vector<TChestDropInfoTable> vec_ItemList;
  3586. ITEM_MANAGER::instance().GetChestItemList(pkItem->GetVnum(), vec_ItemList);
  3587.  
  3588. TPacketGCChestDropInfo packet;
  3589. packet.bHeader = HEADER_GC_CHEST_DROP_INFO;
  3590. packet.wSize = sizeof(packet) + sizeof(TChestDropInfoTable) * vec_ItemList.size();
  3591. packet.dwChestVnum = pkItem->GetVnum();
  3592.  
  3593. ch->GetDesc()->BufferedPacket(&packet, sizeof(packet));
  3594. ch->GetDesc()->Packet(&vec_ItemList[0], sizeof(TChestDropInfoTable) * vec_ItemList.size());
  3595. }
  3596. #endif
  3597.  
  3598. void CInputMain::Refine(LPCHARACTER ch, const char* c_pData)
  3599. {
  3600. const TPacketCGRefine* p = reinterpret_cast<const TPacketCGRefine*>(c_pData);
  3601.  
  3602. if (ch->GetExchange() || ch->IsOpenSafebox() || ch->GetShopOwner() || ch->GetMyShop() || ch->IsCubeOpen())
  3603. {
  3604. ch->ChatPacket(CHAT_TYPE_INFO, LC_TEXT("â°í,°Å·¡Ã¢µîÀÌ ¿­¸° »óÅ¿¡¼­´Â °³·®À» ÇÒ¼ö°¡ ¾ø½À´Ï´Ù"));
  3605. ch->ClearRefineMode();
  3606. return;
  3607. }
  3608.  
  3609. if (p->type == 255)
  3610. {
  3611. // DoRefine Cancel
  3612. ch->ClearRefineMode();
  3613. return;
  3614. }
  3615.  
  3616. if (p->pos >= INVENTORY_MAX_NUM)
  3617. {
  3618. ch->ClearRefineMode();
  3619. return;
  3620. }
  3621.  
  3622. LPITEM item = ch->GetInventoryItem(p->pos);
  3623.  
  3624. if (!item)
  3625. {
  3626. ch->ClearRefineMode();
  3627. return;
  3628. }
  3629.  
  3630. #ifdef __REFINE_SYSTEM__
  3631. if (!CRefineManager::instance().GetPercentage(ch, p->lLow, p->lMedium, p->lExtra, p->lTotal, item))
  3632. {
  3633. ch->ClearRefineMode();
  3634. return;
  3635. }
  3636.  
  3637. CRefineManager::instance().Increase(ch, p->lLow, p->lMedium, p->lExtra);
  3638. #endif
  3639.  
  3640. ch->SetRefineTime();
  3641.  
  3642. if (p->type == REFINE_TYPE_NORMAL)
  3643. {
  3644. sys_log (0, "refine_type_noraml");
  3645. ch->DoRefine(item);
  3646. }
  3647. else if (p->type == REFINE_TYPE_SCROLL || p->type == REFINE_TYPE_HYUNIRON || p->type == REFINE_TYPE_MUSIN || p->type == REFINE_TYPE_BDRAGON)
  3648. {
  3649. sys_log (0, "refine_type_scroll, ...");
  3650. ch->DoRefineWithScroll(item);
  3651. }
  3652. else if (p->type == REFINE_TYPE_MONEY_ONLY)
  3653. {
  3654. const LPITEM item = ch->GetInventoryItem(p->pos);
  3655.  
  3656. if (NULL != item)
  3657. {
  3658. if (500 <= item->GetRefineSet())
  3659. {
  3660. LogManager::instance().HackLog("DEVIL_TOWER_REFINE_HACK", ch);
  3661. }
  3662. else
  3663. {
  3664. if (ch->GetQuestFlag("deviltower_zone.can_refine"))
  3665. {
  3666. ch->DoRefine(item, true);
  3667. ch->SetQuestFlag("deviltower_zone.can_refine", 0);
  3668. }
  3669. else
  3670. {
  3671. ch->ChatPacket(CHAT_TYPE_INFO, "»ç±Í Ÿ¿ö ¿Ï·á º¸»óÀº Çѹø±îÁö »ç¿ë°¡´ÉÇÕ´Ï´Ù.");
  3672. }
  3673. }
  3674. }
  3675. }
  3676.  
  3677. ch->ClearRefineMode();
  3678. }
  3679.  
  3680. #ifdef __SASH_SYSTEM__
  3681. void CInputMain::Sash(LPCHARACTER pkChar, const char* c_pData)
  3682. {
  3683. quest::PC * pPC = quest::CQuestManager::instance().GetPCForce(pkChar->GetPlayerID());
  3684. if (pPC->IsRunning())
  3685. return;
  3686.  
  3687. TPacketSash * sPacket = (TPacketSash*) c_pData;
  3688. switch (sPacket->subheader)
  3689. {
  3690. case SASH_SUBHEADER_CG_CLOSE:
  3691. {
  3692. pkChar->CloseSash();
  3693. }
  3694. break;
  3695. case SASH_SUBHEADER_CG_ADD:
  3696. {
  3697. pkChar->AddSashMaterial(sPacket->tPos, sPacket->bPos);
  3698. }
  3699. break;
  3700. case SASH_SUBHEADER_CG_REMOVE:
  3701. {
  3702. pkChar->RemoveSashMaterial(sPacket->bPos);
  3703. }
  3704. break;
  3705. case SASH_SUBHEADER_CG_REFINE:
  3706. {
  3707. pkChar->RefineSashMaterials();
  3708. }
  3709. break;
  3710. default:
  3711. break;
  3712. }
  3713. }
  3714. #endif
  3715.  
  3716. #ifdef __CHANGELOOK_SYSTEM__
  3717. void CInputMain::ChangeLook(LPCHARACTER pkChar, const char* c_pData)
  3718. {
  3719. quest::PC * pPC = quest::CQuestManager::instance().GetPCForce(pkChar->GetPlayerID());
  3720. if (pPC->IsRunning())
  3721. return;
  3722.  
  3723. TPacketChangeLook * sPacket = (TPacketChangeLook*) c_pData;
  3724. switch (sPacket->subheader)
  3725. {
  3726. case CL_SUBHEADER_CLOSE:
  3727. {
  3728. pkChar->ChangeLookWindow(false);
  3729. }
  3730. break;
  3731. case CL_SUBHEADER_ADD:
  3732. {
  3733. pkChar->AddClMaterial(sPacket->tPos, sPacket->bPos);
  3734. }
  3735. break;
  3736. case CL_SUBHEADER_REMOVE:
  3737. {
  3738. pkChar->RemoveClMaterial(sPacket->bPos);
  3739. }
  3740. break;
  3741. case CL_SUBHEADER_REFINE:
  3742. {
  3743. pkChar->RefineClMaterials();
  3744. }
  3745. break;
  3746. default:
  3747. break;
  3748. }
  3749. }
  3750. #endif
  3751.  
  3752. int CInputMain::Analyze(LPDESC d, BYTE bHeader, const char * c_pData)
  3753. {
  3754. LPCHARACTER ch;
  3755.  
  3756. if (!(ch = d->GetCharacter()))
  3757. {
  3758. sys_err("no character on desc");
  3759. d->SetPhase(PHASE_CLOSE);
  3760. return (0);
  3761. }
  3762.  
  3763. int iExtraLen = 0;
  3764.  
  3765. if (test_server && bHeader != HEADER_CG_MOVE)
  3766. sys_log(0, "CInputMain::Analyze() ==> Header [%d] ", bHeader);
  3767.  
  3768. switch (bHeader)
  3769. {
  3770. case HEADER_CG_PONG:
  3771. Pong(d);
  3772. break;
  3773.  
  3774. case HEADER_CG_TIME_SYNC:
  3775. Handshake(d, c_pData);
  3776. break;
  3777.  
  3778. case HEADER_CG_CHAT:
  3779. if (test_server)
  3780. {
  3781. char* pBuf = (char*)c_pData;
  3782. sys_log(0, "%s", pBuf + sizeof(TPacketCGChat));
  3783. }
  3784.  
  3785. if ((iExtraLen = Chat(ch, c_pData, m_iBufferLeft)) < 0)
  3786. return -1;
  3787. break;
  3788.  
  3789. case HEADER_CG_WHISPER:
  3790. if ((iExtraLen = Whisper(ch, c_pData, m_iBufferLeft)) < 0)
  3791. return -1;
  3792. break;
  3793.  
  3794. case HEADER_CG_MOVE:
  3795. Move(ch, c_pData);
  3796. // @fixme103 (removed CheckClientVersion since useless in here)
  3797. break;
  3798.  
  3799. case HEADER_CG_CHARACTER_POSITION:
  3800. Position(ch, c_pData);
  3801. break;
  3802.  
  3803. case HEADER_CG_ITEM_USE:
  3804. if (!ch->IsObserverMode())
  3805. ItemUse(ch, c_pData);
  3806. break;
  3807.  
  3808. case HEADER_CG_ITEM_DROP:
  3809. if (!ch->IsObserverMode())
  3810. {
  3811. ItemDrop(ch, c_pData);
  3812. }
  3813. break;
  3814.  
  3815. case HEADER_CG_ITEM_DROP2:
  3816. if (!ch->IsObserverMode())
  3817. ItemDrop2(ch, c_pData);
  3818. break;
  3819.  
  3820. case HEADER_CG_ITEM_DESTROY:
  3821. if (!ch->IsObserverMode())
  3822. ItemDestroy(ch, c_pData);
  3823. break;
  3824.  
  3825. case HEADER_CG_ITEM_MOVE:
  3826. if (!ch->IsObserverMode())
  3827. ItemMove(ch, c_pData);
  3828. break;
  3829.  
  3830. case HEADER_CG_ITEM_PICKUP:
  3831. if (!ch->IsObserverMode())
  3832. ItemPickup(ch, c_pData);
  3833. break;
  3834.  
  3835. #if defined(WHEEL_OF_DESTINY)
  3836. case HEADER_CG_WHEEL_DESTINY:
  3837. if (!ch->IsObserverMode())
  3838. WheelDestiny(ch, c_pData);
  3839. break;
  3840. #endif
  3841.  
  3842. case HEADER_CG_ITEM_USE_TO_ITEM:
  3843. if (!ch->IsObserverMode())
  3844. ItemToItem(ch, c_pData);
  3845. break;
  3846.  
  3847. case HEADER_CG_ITEM_GIVE:
  3848. if (!ch->IsObserverMode())
  3849. ItemGive(ch, c_pData);
  3850. break;
  3851.  
  3852. case HEADER_CG_EXCHANGE:
  3853. if (!ch->IsObserverMode())
  3854. Exchange(ch, c_pData);
  3855. break;
  3856.  
  3857. case HEADER_CG_ATTACK:
  3858. case HEADER_CG_SHOOT:
  3859. if (!ch->IsObserverMode())
  3860. {
  3861. Attack(ch, bHeader, c_pData);
  3862. }
  3863. break;
  3864.  
  3865. case HEADER_CG_USE_SKILL:
  3866. if (!ch->IsObserverMode())
  3867. UseSkill(ch, c_pData);
  3868. break;
  3869.  
  3870. case HEADER_CG_QUICKSLOT_ADD:
  3871. QuickslotAdd(ch, c_pData);
  3872. break;
  3873.  
  3874. case HEADER_CG_QUICKSLOT_DEL:
  3875. QuickslotDelete(ch, c_pData);
  3876. break;
  3877.  
  3878. case HEADER_CG_QUICKSLOT_SWAP:
  3879. QuickslotSwap(ch, c_pData);
  3880. break;
  3881.  
  3882. case HEADER_CG_SHOP:
  3883. if ((iExtraLen = Shop(ch, c_pData, m_iBufferLeft)) < 0)
  3884. return -1;
  3885. break;
  3886. #ifdef ENABLE_FISH_EVENT
  3887. case HEADER_CG_FISH_EVENT_SEND:
  3888. if ((iExtraLen = FishEvent(ch, c_pData, m_iBufferLeft)) < 0)
  3889. return -1;
  3890. break;
  3891. #endif
  3892. #ifdef ENABLE_GEM_SYSTEM
  3893. case HEADER_CG_GEM_SHOP:
  3894. if ((iExtraLen = GemShop(ch, c_pData, m_iBufferLeft)) < 0)
  3895. return -1;
  3896. break;
  3897. #endif
  3898.  
  3899. case HEADER_CG_MESSENGER:
  3900. if ((iExtraLen = Messenger(ch, c_pData, m_iBufferLeft))<0)
  3901. return -1;
  3902. break;
  3903.  
  3904. case HEADER_CG_ON_CLICK:
  3905. OnClick(ch, c_pData);
  3906. break;
  3907.  
  3908. case HEADER_CG_SYNC_POSITION:
  3909. if ((iExtraLen = SyncPosition(ch, c_pData, m_iBufferLeft)) < 0)
  3910. return -1;
  3911. break;
  3912.  
  3913. case HEADER_CG_ADD_FLY_TARGETING:
  3914. case HEADER_CG_FLY_TARGETING:
  3915. FlyTarget(ch, c_pData, bHeader);
  3916. break;
  3917.  
  3918. case HEADER_CG_SCRIPT_BUTTON:
  3919. ScriptButton(ch, c_pData);
  3920. break;
  3921.  
  3922. // SCRIPT_SELECT_ITEM
  3923. case HEADER_CG_SCRIPT_SELECT_ITEM:
  3924. ScriptSelectItem(ch, c_pData);
  3925. break;
  3926. // END_OF_SCRIPT_SELECT_ITEM
  3927.  
  3928. case HEADER_CG_SCRIPT_ANSWER:
  3929. ScriptAnswer(ch, c_pData);
  3930. break;
  3931.  
  3932. case HEADER_CG_QUEST_INPUT_STRING:
  3933. QuestInputString(ch, c_pData);
  3934. break;
  3935.  
  3936. case HEADER_CG_QUEST_CONFIRM:
  3937. QuestConfirm(ch, c_pData);
  3938. break;
  3939.  
  3940. case HEADER_CG_TARGET:
  3941. Target(ch, c_pData);
  3942. break;
  3943.  
  3944. case HEADER_CG_WARP:
  3945. Warp(ch, c_pData);
  3946. break;
  3947.  
  3948. case HEADER_CG_SAFEBOX_CHECKIN:
  3949. SafeboxCheckin(ch, c_pData);
  3950. break;
  3951.  
  3952. case HEADER_CG_SAFEBOX_CHECKOUT:
  3953. SafeboxCheckout(ch, c_pData, false);
  3954. break;
  3955.  
  3956. case HEADER_CG_SAFEBOX_ITEM_MOVE:
  3957. SafeboxItemMove(ch, c_pData);
  3958. break;
  3959.  
  3960. case HEADER_CG_MALL_CHECKOUT:
  3961. SafeboxCheckout(ch, c_pData, true);
  3962. break;
  3963.  
  3964. case HEADER_CG_PARTY_INVITE:
  3965. PartyInvite(ch, c_pData);
  3966. break;
  3967.  
  3968. case HEADER_CG_PARTY_REMOVE:
  3969. PartyRemove(ch, c_pData);
  3970. break;
  3971.  
  3972. case HEADER_CG_PARTY_INVITE_ANSWER:
  3973. PartyInviteAnswer(ch, c_pData);
  3974. break;
  3975.  
  3976. case HEADER_CG_PARTY_SET_STATE:
  3977. PartySetState(ch, c_pData);
  3978. break;
  3979.  
  3980. case HEADER_CG_PARTY_USE_SKILL:
  3981. PartyUseSkill(ch, c_pData);
  3982. break;
  3983.  
  3984. case HEADER_CG_PARTY_PARAMETER:
  3985. PartyParameter(ch, c_pData);
  3986. break;
  3987.  
  3988. case HEADER_CG_ANSWER_MAKE_GUILD:
  3989. #ifdef ENABLE_NEWGUILDMAKE
  3990. ch->ChatPacket(CHAT_TYPE_INFO, "<%s> AnswerMakeGuild disabled", __FUNCTION__);
  3991. #else
  3992. AnswerMakeGuild(ch, c_pData);
  3993. #endif
  3994. break;
  3995.  
  3996. case HEADER_CG_GUILD:
  3997. if ((iExtraLen = Guild(ch, c_pData, m_iBufferLeft)) < 0)
  3998. return -1;
  3999. break;
  4000.  
  4001. case HEADER_CG_FISHING:
  4002. Fishing(ch, c_pData);
  4003. break;
  4004.  
  4005. case HEADER_CG_HACK:
  4006. Hack(ch, c_pData);
  4007. break;
  4008.  
  4009. #ifdef NEW_PET_SYSTEM
  4010. case HEADER_CG_PetSetName:
  4011. BraveRequestPetName(ch, c_pData);
  4012. break;
  4013. #endif
  4014.  
  4015. case HEADER_CG_MYSHOP:
  4016. if ((iExtraLen = MyShop(ch, c_pData, m_iBufferLeft)) < 0)
  4017. return -1;
  4018. break;
  4019.  
  4020. case HEADER_CG_REFINE:
  4021. Refine(ch, c_pData);
  4022. break;
  4023.  
  4024. #ifdef __SHOW_CHEST_DROP__
  4025. case HEADER_CG_CHEST_DROP_INFO:
  4026. ChestDropInfo(ch, c_pData);
  4027. break;
  4028. #endif
  4029.  
  4030. #ifdef ENABLE_FEATURES_OXEVENT
  4031. case HEADER_CG_OXEVENT_MANAGER:
  4032. COXEventManager::instance().Manager(ch, c_pData);
  4033. break;
  4034. #endif
  4035.  
  4036. #ifdef __ADMIN_MANAGER__
  4037. case HEADER_CG_ADMIN_BAN_MANAGER:
  4038. SendAdminBanManager(ch, c_pData);
  4039. break;
  4040. #endif
  4041.  
  4042. #ifdef __WHISPER_ADMIN__
  4043. case HEADER_CG_WHISPER_ADMIN:
  4044. CWhisperAdmin::instance().Manager(ch, c_pData);
  4045. break;
  4046. #endif
  4047.  
  4048. #ifdef __CHANGELOOK_SYSTEM__
  4049. case HEADER_CG_CL:
  4050. {
  4051. ChangeLook(ch, c_pData);
  4052. }
  4053. break;
  4054. #endif
  4055.  
  4056. #ifdef __SASH_SYSTEM__
  4057. case HEADER_CG_SASH:
  4058. {
  4059. Sash(ch, c_pData);
  4060. }
  4061. break;
  4062. #endif
  4063.  
  4064. case HEADER_CG_CLIENT_VERSION:
  4065. Version(ch, c_pData);
  4066. break;
  4067.  
  4068. case HEADER_CG_HS_ACK:
  4069. if (isHackShieldEnable)
  4070. {
  4071. CHackShieldManager::instance().VerifyAck(d->GetCharacter(), c_pData);
  4072. }
  4073. break;
  4074.  
  4075. case HEADER_CG_XTRAP_ACK:
  4076. {
  4077. TPacketXTrapCSVerify* p = reinterpret_cast<TPacketXTrapCSVerify*>((void*)c_pData);
  4078. CXTrapManager::instance().Verify_CSStep3(d->GetCharacter(), p->bPacketData);
  4079. }
  4080. break;
  4081. #ifdef __ATTENDANCE_EVENT__
  4082. case HEADER_CG_ATTENDANCE_REWARD:
  4083. CMiniGame::instance().AttendanceEventRequestReward(ch);
  4084. break;
  4085. #endif
  4086. #ifdef __ENABLE_BATTLE_FIELD__
  4087. case HEADER_CG_REQUEST_ENTER_BATTLE:
  4088. CBattleZone::instance().RequestEnter(ch);
  4089. break;
  4090.  
  4091. case HEADER_CG_REQUEST_EXIT_BATTLE:
  4092. CBattleZone::instance().RequestExit(ch);
  4093. break;
  4094. #endif
  4095. #ifdef __SEND_TARGET_INFO__
  4096. case HEADER_CG_TARGET_INFO_LOAD:
  4097. {
  4098. TargetInfoLoad(ch, c_pData);
  4099. }
  4100. break;
  4101. #endif
  4102. case HEADER_CG_DRAGON_SOUL_REFINE:
  4103. {
  4104. TPacketCGDragonSoulRefine* p = reinterpret_cast <TPacketCGDragonSoulRefine*>((void*)c_pData);
  4105. switch(p->bSubType)
  4106. {
  4107. case DS_SUB_HEADER_CLOSE:
  4108. ch->DragonSoul_RefineWindow_Close();
  4109. break;
  4110. case DS_SUB_HEADER_DO_REFINE_GRADE:
  4111. {
  4112. DSManager::instance().DoRefineGrade(ch, p->ItemGrid);
  4113. }
  4114. break;
  4115. case DS_SUB_HEADER_DO_REFINE_STEP:
  4116. {
  4117. DSManager::instance().DoRefineStep(ch, p->ItemGrid);
  4118. }
  4119. break;
  4120. case DS_SUB_HEADER_DO_REFINE_STRENGTH:
  4121. {
  4122. DSManager::instance().DoRefineStrength(ch, p->ItemGrid);
  4123. }
  4124. break;
  4125. }
  4126. }
  4127.  
  4128. break;
  4129. #ifdef __TITLE_SYSTEM__
  4130. case HEADER_CG_TITLE_CHOOSE:
  4131. {
  4132. TPacketGGTitleInfo* p = reinterpret_cast <TPacketGGTitleInfo*>((void*)c_pData);
  4133. if (ch)
  4134. ch->pChooseTitle(p->iTitle);
  4135. }
  4136. break;
  4137. #endif
  4138. }
  4139. return (iExtraLen);
  4140. }
  4141.  
  4142. int CInputDead::Analyze(LPDESC d, BYTE bHeader, const char * c_pData)
  4143. {
  4144. LPCHARACTER ch;
  4145.  
  4146. if (!(ch = d->GetCharacter()))
  4147. {
  4148. sys_err("no character on desc");
  4149. return 0;
  4150. }
  4151.  
  4152. int iExtraLen = 0;
  4153.  
  4154. switch (bHeader)
  4155. {
  4156. case HEADER_CG_PONG:
  4157. Pong(d);
  4158. break;
  4159.  
  4160. case HEADER_CG_TIME_SYNC:
  4161. Handshake(d, c_pData);
  4162. break;
  4163.  
  4164. case HEADER_CG_CHAT:
  4165. if ((iExtraLen = Chat(ch, c_pData, m_iBufferLeft)) < 0)
  4166. return -1;
  4167.  
  4168. break;
  4169.  
  4170. case HEADER_CG_WHISPER:
  4171. if ((iExtraLen = Whisper(ch, c_pData, m_iBufferLeft)) < 0)
  4172. return -1;
  4173.  
  4174. break;
  4175.  
  4176. case HEADER_CG_HACK:
  4177. Hack(ch, c_pData);
  4178. break;
  4179.  
  4180. default:
  4181. return (0);
  4182. }
  4183.  
  4184. return (iExtraLen);
  4185. }
  4186.  
  4187.  
Add Comment
Please, Sign In to add comment