aboutsummaryrefslogtreecommitdiff
diff options
context:
space:
mode:
-rw-r--r--sql/updates/world/2014_07_25_03_world_waypoint_data.sql1
-rw-r--r--sql/updates/world/2014_07_26_00_world_waypoints.sql145
-rw-r--r--sql/updates/world/2014_07_26_01_world_creature_formations.sql9
-rw-r--r--sql/updates/world/2014_07_27_00_world_misc.sql114
-rw-r--r--sql/updates/world/2014_07_27_01_world_misc.sql3
-rw-r--r--sql/updates/world/2014_07_27_02_world_waypoints.sql97
-rw-r--r--src/server/authserver/Server/AuthSession.cpp248
-rw-r--r--src/server/authserver/Server/AuthSession.h59
-rw-r--r--src/server/game/CMakeLists.txt1
-rw-r--r--src/server/game/Globals/ObjectAccessor.h4
-rwxr-xr-xsrc/server/game/Movement/MovementGenerators/WaypointMovementGenerator.cpp19
-rw-r--r--src/server/game/Movement/Waypoints/WaypointManager.cpp20
-rw-r--r--src/server/game/Movement/Waypoints/WaypointManager.h12
-rw-r--r--src/server/game/Server/WorldSession.cpp2
-rw-r--r--src/server/game/Server/WorldSocket.cpp233
-rw-r--r--src/server/game/Server/WorldSocket.h29
-rw-r--r--src/server/game/World/World.cpp3
-rw-r--r--src/server/scripts/Commands/cs_wp.cpp2
-rw-r--r--src/server/shared/Database/DatabaseWorkerPool.h12
-rw-r--r--src/server/shared/Database/Implementation/WorldDatabase.cpp4
-rw-r--r--src/server/shared/Networking/Socket.h109
21 files changed, 803 insertions, 323 deletions
diff --git a/sql/updates/world/2014_07_25_03_world_waypoint_data.sql b/sql/updates/world/2014_07_25_03_world_waypoint_data.sql
new file mode 100644
index 00000000000..008248d8395
--- /dev/null
+++ b/sql/updates/world/2014_07_25_03_world_waypoint_data.sql
@@ -0,0 +1 @@
+ALTER TABLE `waypoint_data` CHANGE `move_flag` `move_type` INT(11) NOT NULL DEFAULT 0;
diff --git a/sql/updates/world/2014_07_26_00_world_waypoints.sql b/sql/updates/world/2014_07_26_00_world_waypoints.sql
new file mode 100644
index 00000000000..c012728efc0
--- /dev/null
+++ b/sql/updates/world/2014_07_26_00_world_waypoints.sql
@@ -0,0 +1,145 @@
+-- Pathing for Garadar Wolf Rider Entry: 19068
+SET @NPC := 68369;
+SET @PATH := @NPC * 10;
+UPDATE `creature` SET `spawndist`=0,`MovementType`=2,`position_x`=-1306.285,`position_y`=6952.27,`position_z`=31.80549 WHERE `guid`=@NPC;
+DELETE FROM `creature_addon` WHERE `guid`=@NPC;
+INSERT INTO `creature_addon` (`guid`,`path_id`,`bytes2`,`mount`,`auras`) VALUES (@NPC,@PATH,4097,18509, '');
+UPDATE `creature` SET `position_x`=-1312.285,`position_y`=6940.27,`position_z`=31.40549,`orientation`=1.049322 WHERE `guid`=68368;
+DELETE FROM `creature_formations` WHERE `leaderGUID`=68369;
+INSERT INTO `creature_formations` (`leaderGUID`,`memberGUID`,`dist`,`angle`,`groupAI`)VALUES
+(68369,68369,0,0,2),(68369,68368,10,180,2);
+DELETE FROM `waypoint_data` WHERE `id`=@PATH;
+INSERT INTO `waypoint_data` (`id`,`point`,`position_x`,`position_y`,`position_z`,`orientation`,`delay`,`move_type`,`action`,`action_chance`,`wpguid`) VALUES
+(@PATH,1,-1306.285,6952.27,31.80549,0,0,1,0,100,0),
+(@PATH,2,-1297.114,6970.51,32.55774,0,0,1,0,100,0),
+(@PATH,3,-1286.846,6984.002,32.94885,0,0,1,0,100,0),
+(@PATH,4,-1294.647,6996.062,32.38757,0,0,1,0,100,0),
+(@PATH,5,-1325.328,7024.249,33.6833,0,0,1,0,100,0),
+(@PATH,6,-1348.238,7032.215,33.68893,0,0,1,0,100,0),
+(@PATH,7,-1368.992,7045.52,34.10938,0,0,1,0,100,0),
+(@PATH,8,-1386.631,7061.436,34.45948,0,0,1,0,100,0),
+(@PATH,9,-1394.578,7075.491,33.83854,0,0,1,0,100,0),
+(@PATH,10,-1398.298,7096.861,33.335,0,0,1,0,100,0),
+(@PATH,11,-1403.897,7125.299,33.58035,0,0,1,0,100,0),
+(@PATH,12,-1389.057,7138.8,33.99598,0,0,1,0,100,0),
+(@PATH,13,-1370.205,7156.964,33.61451,0,0,1,0,100,0),
+(@PATH,14,-1370.205,7156.964,33.61451,0,0,1,0,100,0),
+(@PATH,15,-1359.099,7166.051,33.47036,0,0,1,0,100,0),
+(@PATH,16,-1347.834,7156.16,33.48244,0,0,1,0,100,0),
+(@PATH,17,-1340.037,7146.628,33.13161,0,0,1,0,100,0),
+(@PATH,18,-1327.699,7131.039,33.02342,0,0,1,0,100,0),
+(@PATH,19,-1314.86,7100.454,35.69725,0,0,1,0,100,0),
+(@PATH,20,-1327.699,7131.039,33.02342,0,0,1,0,100,0),
+(@PATH,21,-1340.037,7146.628,33.13161,0,0,1,0,100,0),
+(@PATH,22,-1347.834,7156.16,33.48244,0,0,1,0,100,0),
+(@PATH,23,-1359.099,7166.051,33.47036,0,0,1,0,100,0),
+(@PATH,24,-1369.572,7157.438,33.394,0,0,1,0,100,0),
+(@PATH,25,-1386.934,7139.82,34.2103,0,0,1,0,100,0),
+(@PATH,26,-1403.897,7125.299,33.58035,0,0,1,0,100,0),
+(@PATH,27,-1398.298,7096.861,33.335,0,0,1,0,100,0),
+(@PATH,28,-1394.578,7075.491,33.83854,0,0,1,0,100,0),
+(@PATH,29,-1386.631,7061.436,34.45948,0,0,1,0,100,0),
+(@PATH,30,-1368.992,7045.52,34.10938,0,0,1,0,100,0),
+(@PATH,31,-1348.238,7032.215,33.68893,0,0,1,0,100,0),
+(@PATH,32,-1325.328,7024.249,33.6833,0,0,1,0,100,0),
+(@PATH,33,-1294.647,6996.062,32.38757,0,0,1,0,100,0),
+(@PATH,34,-1286.846,6984.002,32.94885,0,0,1,0,100,0),
+(@PATH,35,-1297.114,6970.51,32.55774,0,0,1,0,100,0),
+(@PATH,36,-1306.285,6952.27,31.80549,0,0,1,0,100,0),
+(@PATH,37,-1318.743,6930.187,31.66993,0,0,1,0,100,0),
+(@PATH,38,-1334.226,6909.456,31.35373,0,0,1,0,100,0),
+(@PATH,39,-1349.58,6892.065,30.41895,0,0,1,0,100,0),
+(@PATH,40,-1368.256,6872.903,30.07822,0,0,1,0,100,0),
+(@PATH,41,-1389.396,6856.315,28.70381,0,0,1,0,100,0),
+(@PATH,42,-1404.557,6849.696,27.38716,0,0,1,0,100,0),
+(@PATH,43,-1413.721,6831.764,26.72453,0,0,1,0,100,0),
+(@PATH,44,-1420.326,6810.526,27.59953,0,0,1,0,100,0),
+(@PATH,45,-1439.301,6791.51,28.34141,0,0,1,0,100,0),
+(@PATH,46,-1453.281,6768.101,27.12888,0,0,1,0,100,0),
+(@PATH,47,-1470.179,6739.332,25.1649,0,0,1,0,100,0),
+(@PATH,48,-1483.529,6716.287,24.14556,0,0,1,0,100,0),
+(@PATH,49,-1493.718,6694.826,24.19415,0,0,1,0,100,0),
+(@PATH,50,-1504.721,6664.285,24.20934,0,0,1,0,100,0),
+(@PATH,51,-1510.836,6642.756,22.9326,0,0,1,0,100,0),
+(@PATH,52,-1515.425,6620.579,21.01927,0,0,1,0,100,0),
+(@PATH,53,-1519.032,6604.414,20.89977,0,0,1,0,100,0),
+(@PATH,54,-1510.836,6642.756,22.9326,0,0,1,0,100,0),
+(@PATH,55,-1504.721,6664.285,24.20934,0,0,1,0,100,0),
+(@PATH,56,-1493.718,6694.826,24.19415,0,0,1,0,100,0),
+(@PATH,57,-1483.529,6716.287,24.14556,0,0,1,0,100,0),
+(@PATH,58,-1470.179,6739.332,25.1649,0,0,1,0,100,0),
+(@PATH,59,-1453.281,6768.101,27.12888,0,0,1,0,100,0),
+(@PATH,60,-1439.301,6791.51,28.34141,0,0,1,0,100,0),
+(@PATH,61,-1420.326,6810.526,27.59953,0,0,1,0,100,0),
+(@PATH,62,-1413.721,6831.764,26.72453,0,0,1,0,100,0),
+(@PATH,63,-1404.557,6849.696,27.38716,0,0,1,0,100,0),
+(@PATH,64,-1389.396,6856.315,28.70381,0,0,1,0,100,0),
+(@PATH,65,-1368.256,6872.903,30.07822,0,0,1,0,100,0),
+(@PATH,66,-1349.58,6892.065,30.41895,0,0,1,0,100,0),
+(@PATH,67,-1334.226,6909.456,31.35373,0,0,1,0,100,0),
+(@PATH,68,-1318.743,6930.187,31.66993,0,0,1,0,100,0);
+
+-- Pathing for Garadar Wolf Rider Entry: 19068
+SET @NPC := 68371;
+SET @PATH := @NPC * 10;
+UPDATE `creature` SET `spawndist`=0,`MovementType`=2,`position_x`=-1211.921,`position_y`=7410.358,`position_z`=27.81794 WHERE `guid`=@NPC;
+DELETE FROM `creature_addon` WHERE `guid`=@NPC;
+INSERT INTO `creature_addon` (`guid`,`path_id`,`bytes2`,`mount`,`auras`) VALUES (@NPC,@PATH,4097,18509, '');
+UPDATE `creature` SET `position_x`=-1212.921,`position_y`=7400.358,`position_z`=28.68889,`orientation`=2.005122 WHERE `guid`=68370;
+DELETE FROM `creature_formations` WHERE `leaderGUID`=68371;
+INSERT INTO `creature_formations` (`leaderGUID`,`memberGUID`,`dist`,`angle`,`groupAI`)VALUES
+(68371,68371,0,0,2),(68371,68370,10,180,2);
+DELETE FROM `waypoint_data` WHERE `id`=@PATH;
+INSERT INTO `waypoint_data` (`id`,`point`,`position_x`,`position_y`,`position_z`,`orientation`,`delay`,`move_type`,`action`,`action_chance`,`wpguid`) VALUES
+(@PATH,1,-1211.921,7410.358,27.81794,0,0,1,0,100,0),
+(@PATH,2,-1214.586,7425.123,25.99836,0,0,1,0,100,0),
+(@PATH,3,-1222.165,7481.616,21.67305,0,0,1,0,100,0),
+(@PATH,4,-1220.974,7497.774,20.48409,0,0,1,0,100,0),
+(@PATH,5,-1214.87,7518.328,19.43397,0,0,1,0,100,0),
+(@PATH,6,-1212.915,7540.512,18.40359,0,0,1,0,100,0),
+(@PATH,7,-1211.614,7556.853,17.56509,0,0,1,0,100,0),
+(@PATH,8,-1216.004,7573.963,16.24247,0,0,1,0,100,0),
+(@PATH,9,-1217.563,7593.355,14.74553,0,0,1,0,100,0),
+(@PATH,10,-1219.645,7606.309,13.68142,0,0,1,0,100,0),
+(@PATH,11,-1225.298,7625.371,12.251,0,0,1,0,100,0),
+(@PATH,12,-1229.663,7641.069,11.23986,0,0,1,0,100,0),
+(@PATH,13,-1237.146,7655.85,10.48808,0,0,1,0,100,0),
+(@PATH,14,-1242.923,7670.299,9.753622,0,0,1,0,100,0),
+(@PATH,15,-1240.828,7683.721,9.396078,0,0,1,0,100,0),
+(@PATH,16,-1250.555,7678.873,8.685507,0,0,1,0,100,0),
+(@PATH,17,-1237.549,7656.549,10.52263,0,0,1,0,100,0),
+(@PATH,18,-1229.939,7641.217,11.3557,0,0,1,0,100,0),
+(@PATH,19,-1225.466,7625.775,12.251,0,0,1,0,100,0),
+(@PATH,20,-1219.507,7606.408,13.66946,0,0,1,0,100,0),
+(@PATH,21,-1217.322,7593.599,14.80558,0,0,1,0,100,0),
+(@PATH,22,-1216.509,7573.793,16.26286,0,0,1,0,100,0),
+(@PATH,23,-1211.828,7556.847,17.56509,0,0,1,0,100,0),
+(@PATH,24,-1212.723,7540.783,18.39443,0,0,1,0,100,0),
+(@PATH,25,-1215.317,7518.904,19.44593,0,0,1,0,100,0),
+(@PATH,26,-1221.131,7497.735,20.48873,0,0,1,0,100,0),
+(@PATH,27,-1222.776,7482.632,21.6545,0,0,1,0,100,0),
+(@PATH,28,-1220.757,7459.46,23.17959,0,0,1,0,100,0),
+(@PATH,29,-1217.947,7442.052,24.55239,0,0,1,0,100,0),
+(@PATH,30,-1215.386,7427.643,25.71003,0,0,1,0,100,0),
+(@PATH,31,-1212.104,7411.986,27.62336,0,0,1,0,100,0),
+(@PATH,32,-1213.585,7392.814,29.7174,0,0,1,0,100,0),
+(@PATH,33,-1220.035,7371.12,33.57092,0,0,1,0,100,0),
+(@PATH,34,-1222.352,7358.362,34.27285,0,0,1,0,100,0),
+(@PATH,35,-1222.356,7341.586,34.02285,0,0,1,0,100,0),
+(@PATH,36,-1202.531,7331.909,34.10541,0,0,1,0,100,0),
+(@PATH,37,-1186.747,7320.795,34.03506,0,0,1,0,100,0),
+(@PATH,38,-1181.867,7303.457,34.13747,0,0,1,0,100,0),
+(@PATH,39,-1181.804,7297.336,34.78957,0,0,1,0,100,0),
+(@PATH,40,-1192.18,7249.516,35.21297,0,0,1,0,100,0),
+(@PATH,41,-1195.673,7231.294,42.2477,0,0,1,0,100,0),
+(@PATH,42,-1196.073,7218.396,48.50587,0,0,1,0,100,0),
+(@PATH,43,-1195.584,7229.94,43.06007,0,0,1,0,100,0),
+(@PATH,44,-1194.09,7244.866,35.06643,0,0,1,0,100,0),
+(@PATH,45,-1192.24,7248.374,35.16298,0,0,1,0,100,0),
+(@PATH,46,-1180.625,7296.229,34.84074,0,0,1,0,100,0),
+(@PATH,47,-1182.318,7302.35,34.07021,0,0,1,0,100,0),
+(@PATH,48,-1184.25,7317.054,34.17605,0,0,1,0,100,0),
+(@PATH,49,-1198.885,7329.619,34.02688,0,0,1,0,100,0),
+(@PATH,50,-1218.819,7338.442,34.02285,0,0,1,0,100,0),
+(@PATH,51,-1222.647,7357.911,34.27285,0,0,1,0,100,0),
+(@PATH,52,-1213.344,7392.449,29.94091,0,0,1,0,100,0);
diff --git a/sql/updates/world/2014_07_26_01_world_creature_formations.sql b/sql/updates/world/2014_07_26_01_world_creature_formations.sql
new file mode 100644
index 00000000000..dc424437dfc
--- /dev/null
+++ b/sql/updates/world/2014_07_26_01_world_creature_formations.sql
@@ -0,0 +1,9 @@
+-- Fix Garadar Wolf Rider Formations
+UPDATE `creature` SET `position_x`=-1312.285,`position_y`=6940.27,`position_z`=31.40549,`orientation`=1.049322 WHERE `guid`=68368;
+DELETE FROM `creature_formations` WHERE `leaderGUID`=68369;
+INSERT INTO `creature_formations` (`leaderGUID`,`memberGUID`,`dist`,`angle`,`groupAI`)VALUES
+(68369,68369,0,0,2),(68369,68368,8,0,2);
+UPDATE `creature` SET `position_x`=-1212.921,`position_y`=7400.358,`position_z`=28.68889,`orientation`=2.005122 WHERE `guid`=68370;
+DELETE FROM `creature_formations` WHERE `leaderGUID`=68371;
+INSERT INTO `creature_formations` (`leaderGUID`,`memberGUID`,`dist`,`angle`,`groupAI`)VALUES
+(68371,68371,0,0,2),(68371,68370,8,0,2);
diff --git a/sql/updates/world/2014_07_27_00_world_misc.sql b/sql/updates/world/2014_07_27_00_world_misc.sql
new file mode 100644
index 00000000000..42f4a82b158
--- /dev/null
+++ b/sql/updates/world/2014_07_27_00_world_misc.sql
@@ -0,0 +1,114 @@
+DELETE FROM `creature_text` WHERE `entry` IN(17246,17240, 17242, 17241,17214,17215,17117);
+DELETE FROM `creature_text` WHERE `entry` =17375 and `id` IN(3,4);
+
+INSERT INTO `creature_text` (`entry`, `groupid`, `id`, `text`, `type`, `language`, `probability`, `emote`, `duration`, `sound`, `comment`, `BroadcastTextID`) VALUES
+(17246, 0, 0, 'Yarr, Admiral. Let me think about it... Arrr... It be comin'' into focus.', 12, 7, 100, 1, 0, 0, '"Cookie" McWeaksauce', 13699),
+(17246, 1, 0, 'It looks like it be succulent pork ribs basted with its own delectable juices and a side o'' Captain Sander''s Secret Sauce - fer dippin''.', 12, 7, 100, 1, 0, 0, '"Cookie" McWeaksauce', 13700),
+(17246, 2, 0, 'And fer dessert we be havin'' cheesecake, flown in fresh from Stormwind on the wings o'' angels...', 12, 7, 100, 1, 0, 0, '"Cookie" McWeaksauce', 13701),
+(17246, 3, 0, 'No. Not really...', 12, 7, 100, 274, 0, 0, '"Cookie" McWeaksauce', 13702),
+(17246, 4, 0, 'It be chicken...', 12, 7, 100, 1, 0, 0, '"Cookie" McWeaksauce', 13704),
+(17240, 0, 0, 'Hey, Cookie! What''s for dinner tonight? And don''t say chicken!', 12, 7, 100, 22, 0, 0, 'Admiral Odesyus', 13698),
+(17240, 1, 0, 'Wow! Really?', 12, 7, 100, 5, 0, 0, 'Admiral Odesyus', 13702),
+(17240, 2, 0, 'I hate you so much, Cookie.', 12, 7, 100, 1, 0, 0, 'Admiral Odesyus', 13705),
+(17242, 0, 0, 'Of course! Anything for you, darling!', 12, 7, 100, 5, 0, 0, 'Archaeologist Adamant Ironheart', 13712),
+(17242, 1, 0, 'Alright, let me take a look at that tablet.', 12, 7, 100, 1, 0, 0, 'Archaeologist Adamant Ironheart', 13713),
+(17242, 2, 0, '%s slowly reads the tablet, mouthing the words in their native tongue.', 16, 7, 100, 0, 0, 0, 'Archaeologist Adamant Ironheart', 13714),
+(17242, 3, 0, 'Naga warlord! Oh dear...', 12, 7, 100, 5, 0, 0, 'Archaeologist Adamant Ironheart', 13715),
+(17242, 4, 0, 'Well, you aren''t going to like what I have to tell you, young missy. This tablet is a naga communication. Their leader, Warlord Sriss''tiz, has ordered his naga to take the rest of the island by force.', 12, 7, 100, 1, 0, 0, 'Archaeologist Adamant Ironheart', 13716),
+(17242, 5, 0, 'And it looks like he''s got reinforcements comin'' from Nazjatar!', 12, 7, 100, 5, 0, 0, 'Archaeologist Adamant Ironheart', 13717),
+(17242, 6, 0, 'We''ve got to do something about this!', 12, 0, 100, 5, 0, 0, 'Archaeologist Adamant Ironheart', 13718),
+(17241, 0, 0, 'Adamant, could you please take a look at this tablet and try to decipher the runes?', 12, 7, 100, 1, 0, 0, 'Priestess Kyleen Il''dinare', 13711),
+(17241, 1, 0, 'Thank you, Adamant. I think I know just the person for the job.', 12, 7, 100, 2, 0, 0, 'Priestess Kyleen Il''dinare', 13719),
+(17214, 0, 0, 'Now to apply the ointment to her wounds.', 12, 7, 100, 1, 0, 0, 'Anchorite Fateema', 13596),
+(17214, 1, 0, 'It appears that the ointment is ineffective. Such a pity...', 12, 7, 100, 1, 0, 0, 'Anchorite Fateema', 13597),
+(17214, 2, 0, 'Man''ari... But how... We are not eredar! She must know! If there are others like her, we must find them and explain...', 12, 7, 100, 1, 0, 0, 'Anchorite Fateema', 13608),
+(17215, 0, 0, 'There may still be a solution. Come here, $n. I will explain what I need.', 12, 7, 100, 1, 0, 0, 'Daedal0', 13598),
+(17215, 1, 0, 'This should do it...', 12, 7, 100, 0, 0, 0, 'Daedal', 13599),
+(17215, 2, 0, 'Wake up little creature. Wake up from your slumber... You are safe now.', 12, 7, 100, 0, 0, 0, 'Daedal', 13600),
+(17117, 0, 0, '%s groans.', 16, 7, 100, 0, 0, 0, 'Injured Night Elf Priestess', 13601),
+(17117, 1, 0, '%s sits up.', 16, 7, 100, 0, 0, 0, 'Injured Night Elf Priestess', 13602),
+(17117, 2, 0, 'Whe... Where am I? What... What is this place?', 12, 7, 100, 6, 0, 0, 'Injured Night Elf Priestess', 13603),
+(17117, 3, 0, 'BY THE LIGHT OF ELUNE! Eredar! Cursed demons, what have you done to me? I have not come alone, we will fight you as we have in the past! I...', 12, 7, 100, 5, 0, 0, 'Injured Night Elf Priestess', 13604),
+(17117, 4, 0, '%s falls back into a coma.', 16, 0, 100, 0, 0, 0, 'Injured Night Elf Priestess', 13605),
+(17375, 0, 3, '[Furbolg] The prophecy is true!', 12, 0, 100, 0, 0, 0, 'Stillpine Captive', 13980),
+(17375, 0, 4, '%s growls at its captors.', 16, 0, 100, 0, 0, 0, 'Stillpine Captive', 13977);
+
+-- Change cookie mcweaksauces spawn position to sniffed one, wp lead to where was previously spawned
+UPDATE `creature` SET `position_x`=-4708.59, `position_y`=-12400.26, `position_z`=11.94285, `orientation`=0.9948376 WHERE `guid`=61976;
+
+
+UPDATE `creature_template` SET `ainame`='SmartAI', `scriptname`='' WHERE `entry` IN(17246,17240, 17242, 17241, 17240,17214,17215,17117);
+
+DELETE FROM `smart_scripts` WHERE `entryorguid`IN(17246,17240, 17242, 17241, 17240,17214,17215,17117) AND `source_type`=0;
+DELETE FROM `smart_scripts` WHERE `entryorguid`IN(1724100,1724600,1724100, 1721500, 1721400) AND `source_type`=9;
+
+INSERT INTO `smart_scripts` (`entryorguid`, `source_type`, `id`, `link`, `event_type`, `event_phase_mask`, `event_chance`, `event_flags`, `event_param1`, `event_param2`, `event_param3`, `event_param4`, `action_type`, `action_param1`, `action_param2`, `action_param3`, `action_param4`, `action_param5`, `action_param6`, `target_type`, `target_param1`, `target_param2`, `target_param3`, `target_x`, `target_y`, `target_z`, `target_o`, `comment`) VALUES
+(17241,0,0,0,20,0,100,0,9514,0,0,0,80,1724100,2,0,0,0,0,1,0,0,0,0,0,0,0,'Priestess Kyleen Il''dinare - On Quest reward rune covered tablet - run script'),
+(17242,0,0,0,38,0,100,0,1,1,0,0,53,0,1724200,0,0,0,0,1,0,0,0,0,0,0,0,'Archaeologist Adamant Ironheart - On Data Set 1 1- Start WP (Path 1)'),
+(17242,0,1,0,38,0,100,0,2,2,0,0,53,0,1724201,0,0,0,0,1,0,0,0,0,0,0,0,'Archaeologist Adamant Ironheart - On Data Set 2 2- Start WP (Path 2)'),
+(17242,0,2,0,40,0,100,0,1,1724201,0,0,66,0,0,0,0,0,0,8,0,0,0,0,0,0,6.26573,'Archaeologist Adamant Ironheart - On Reached WP1 (Path 2) - Set Orientation'),
+(17246,0,0,0,1,0,100,0,0,30000,300000,450000,80,1724600,0,0,0,0,0,1,0,0,0,0,0,0,0,'"Cookie" McWeaksauce - OOC - Run Script'),
+(17246,0,1,0,40,0,100,0,3,17246,0,0,54,60000,0,0,0,0,0,1,0,0,0,0,0,0,0,'"Cookie" McWeaksauce - On Reached WP3 - Pause WP'),
+(17240,0,0,0,38,0,100,0,1,1,0,0,66,0,0,0,0,0,0,19 ,17246,0,0,0,0,0,0,'Admiral Odesyus - On Data Set 1 1- Face "Cookie" McWeaksauce'),
+(17240,0,1,0,38,0,100,0,2,2,0,0,66,0,0,0,0,0,0,8,0,0,0,0,0,0,4.38078,'Admiral Odesyus - On Data Set 2 2- Set Orientation'),
+(17215,0,0,0,38,0,100,0,1,1,0,0,81,0,0,0,0,0,0,1,0,0,0,0,0,0,0,'Daedal - On Data Set 1 1- Set NPC Flags'),
+(17215,0,1,0,38,0,100,0,2,2,0,0,81,83,0,0,0,0,0,1,0,0,0,0,0,0,0,'Daedal - On Data Set 2 2- Set NPC Flags'),
+(17215,0,2,0,20,0,100,0,9473,2,0,0,80,1721500,2,0,0,0,0,1,0,0,0,0,0,0,0,'Daedal - On Quest Reward - An Alternative Alternative - Run Script'),
+(17117,0,0,0,38,0,100,0,1,1,0,0,91,2,0,0,0,0,0,1,0,0,0,0,0,0,0,'Injured Night Elf Priestess - On Data Set 1 1- Set Bytes 1'),
+(17117,0,1,0,38,0,100,0,2,2,0,0,90,2,0,0,0,0,0,1,0,0,0,0,0,0,0,'Injured Night Elf Priestess - On Data Set 2 2- Set Bytes 1'),
+(17214,0,0,0,20,0,100,0,9463,2,0,0,80,1721400,2,0,0,0,0,1,0,0,0,0,0,0,0,'Anchorite Fateema - On Quest Reward - Medicinal Purposes - Run Script'),
+(1721400,9,0,0,0,0,100,0,0,0,0,0,45,1,1,0,0,0,0,19,17215,0,0,0,0,0,0,'Anchorite Fateema - Script - Set Data 1 1 Daedal'),
+(1721400,9,1,0,0,0,100,0,1000,1000,0,0,1,0,0,0,0,0,0,1,0,0,0,0,0,0,0,'Anchorite Fateema - Script - Say Line 1'),
+(1721400,9,2,0,0,0,100,0,9000,9000,0,0,1,1,0,0,0,0,0,1,0,0,0,0,0,0,0,'Anchorite Fateema - Script - Say Line 2'),
+(1721400,9,3,0,0,0,100,0,9000,9000,0,0,1,0,0,0,0,0,0,19,17215,0,0,0,0,0,0,'Anchorite Fateema - Script - Say Line 1 (Daedal)'),
+(1721400,9,4,0,0,0,100,0,0,0,0,0,45,2,2,0,0,0,0,19,17215,0,0,0,0,0,0,'Anchorite Fateema - Script - Set Data 2 2 Daedal'),
+(1721500,9,0,0,0,0,100,0,0,0,0,0,1,1,0,0,0,0,0,1,0,0,0,0,0,0,0,'Daedal - Script - Say Line 2'),
+(1721500,9,1,0,0,0,100,0,7000,7000,0,0,1,2,0,0,0,0,0,1,0,0,0,0,0,0,0,'Daedal - Script - Say Line 3'),
+(1721500,9,2,0,0,0,100,0,3000,3000,0,0,1,0,0,0,0,0,0,19,17117,0,0,0,0,0,0,'Daedal - Script - Say Line 1 (Injured Night Elf Priestess)'),
+(1721500,9,3,0,0,0,100,0,5000,5000,0,0,1,1,0,0,0,0,0,19,17117,0,0,0,0,0,0,'Daedal - Script - Say Line 2 (Injured Night Elf Priestess)'),
+(1721500,9,4,0,0,0,100,0,0,0,0,0,45,1,1,0,0,0,0,19,17117,0,0,0,0,0,0,'Daedal - Script - Set Data 1 1 (Injured Night Elf Priestess)'),
+(1721500,9,5,0,0,0,100,0,5000,5000,0,0,1,2,0,0,0,0,0,19,17117,0,0,0,0,0,0,'Daedal - Script - Say Line 3 (Injured Night Elf Priestess)'),
+(1721500,9,6,0,0,0,100,0,7000,7000,0,0,1,3,0,0,0,0,0,19,17117,0,0,0,0,0,0,'Daedal - Script - Say Line 4 (Injured Night Elf Priestess)'),
+(1721500,9,7,0,0,0,100,0,5000,5000,0,0,1,4,0,0,0,0,0,19,17117,0,0,0,0,0,0,'Daedal - Script - Say Line 5 (Injured Night Elf Priestess)'),
+(1721500,9,8,0,0,0,100,0,0,0,0,0,45,2,2,0,0,0,0,19,17117,0,0,0,0,0,0,'Daedal - Script - Set Data 2 2 (Injured Night Elf Priestess)'),
+(1721500,9,9,0,0,0,100,0,7000,7000,0,0,1,2,0,0,0,0,0,19,17214,0,0,0,0,0,0,'Daedal - Script - Say Line 3 (Anchorite Fateema)'),
+(1724600,9,0,0,0,0,100,0,0,0,0,0,53,0,17246,0,0,0,0,1,0,0,0,0,0,0,0,'Cookie" McWeaksauce - Script - Start WP'),
+(1724600,9,1,0,0,0,100,0,5000,5000,0,0,45,1,1,0,0,0,0,19,17240,0,0,0,0,0,0,'Cookie" McWeaksauce - Script - Set Data 1 1 on Admiral Odesyus'),
+(1724600,9,2,0,0,0,100,0,1000,1000,0,0,1,0,0,0,0,0,0,19,17240,0,0,0,0,0,0,'Cookie" McWeaksauce - Script - Say Line 1 on Admiral Odesyus'),
+(1724600,9,3,0,0,0,100,0,9000,9000,0,0,1,0,0,0,0,0,0,1,0,0,0,0,0,0,0,'Cookie" McWeaksauce - Script - Say Line 1'),
+(1724600,9,4,0,0,0,100,0,9000,9000,0,0,1,1,0,0,0,0,0,1,0,0,0,0,0,0,0,'Cookie" McWeaksauce - Script - Say Line 2'),
+(1724600,9,5,0,0,0,100,0,9000,9000,0,0,1,2,0,0,0,0,0,1,0,0,0,0,0,0,0,'Cookie" McWeaksauce - Script - Say Line 3'),
+(1724600,9,6,0,0,0,100,0,5000,5000,0,0,1,1,0,0,0,0,0,19,17240,0,0,0,0,0,0,'Cookie" McWeaksauce - Script - Say Line 2 on Admiral Odesyus'),
+(1724600,9,7,0,0,0,100,0,9000,9000,0,0,1,3,0,0,0,0,0,1,0,0,0,0,0,0,0,'Cookie" McWeaksauce - Script - Say Line 4'),
+(1724600,9,8,0,0,0,100,0,4000,4000,0,0,1,4,0,0,0,0,0,1,0,0,0,0,0,0,0,'Cookie" McWeaksauce - Script - Say Line 6'),
+(1724600,9,9,0,0,0,100,0,1000,1000,0,0,11,30221,0,0,0,0,0,19,620,0,0,0,0,0,0,'Cookie" McWeaksauce - Script - Cast Shoot (Target Closest chicken)'),
+(1724600,9,10,0,0,0,100,0,5000,5000,0,0,1,2,0,0,0,0,0,19,17240,0,0,0,0,0,0,'Cookie" McWeaksauce - Script - Say Line 3 on Admiral Odesyus'),
+(1724600,9,11,0,0,0,100,0,5000,5000,0,0,45,2,2,0,0,0,0,19,17240,0,0,0,0,0,0,'Cookie" McWeaksauce - Script - Set Data 2 2 on Admiral Odesyus'),
+(1724100,9,0,0,0,0,100,0,0,0,0,0,81,0,0,0,0,0,0,1,0,0,0,0,0,0,0,'Priestess Kyleen Il''dinare - Script - Set NPC Flags'),
+(1724100,9,1,0,0,0,100,0,0,0,0,0,66,0,0,0,0,0,0,19,17242,0,0,0,0,0,0,'Priestess Kyleen Il''dinare - Script - Face Archaeologist Adamant Ironheart'),
+(1724100,9,2,0,0,0,100,0,1000,1000,0,0,1,0,0,0,0,0,0,1,0,0,0,0,0,0,0,'Priestess Kyleen Il''dinare - Script - Say Line 1'),
+(1724100,9,3,0,0,0,100,0,2000,2000,0,0,45,1,1,0,0,0,0,19,17242,0,0,0,0,0,0,'Priestess Kyleen Il''dinare - Script - Set Data 1 1 on Archaeologist Adamant Ironheart'),
+(1724100,9,4,0,0,0,100,0,1000,1000,0,0,1,0,0,0,0,0,0,19,17242,0,0,0,0,0,0,'Priestess Kyleen Il''dinare - Script - Say Line 1 (Archaeologist Adamant Ironheart)'),
+(1724100,9,5,0,0,0,100,0,7000,7000,0,0,1,1,0,0,0,0,0,19,17242,0,0,0,0,0,0,'Priestess Kyleen Il''dinare - Script - Say Line 2 (Archaeologist Adamant Ironheart)'),
+(1724100,9,6,0,0,0,100,0,2000,2000,0,0,1,2,0,0,0,0,0,19,17242,0,0,0,0,0,0,'Priestess Kyleen Il''dinare - Script - Say Line 3 (Archaeologist Adamant Ironheart)'),
+(1724100,9,7,0,0,0,100,0,5000,5000,0,0,1,3,0,0,0,0,0,19,17242,0,0,0,0,0,0,'Priestess Kyleen Il''dinare - Script - Say Line 4 (Archaeologist Adamant Ironheart)'),
+(1724100,9,8,0,0,0,100,0,7000,7000,0,0,1,4,0,0,0,0,0,19,17242,0,0,0,0,0,0,'Priestess Kyleen Il''dinare - Script - Say Line 5 (Archaeologist Adamant Ironheart)'),
+(1724100,9,9,0,0,0,100,0,7000,7000,0,0,1,5,0,0,0,0,0,19,17242,0,0,0,0,0,0,'Priestess Kyleen Il''dinare - Script - Say Line 6 (Archaeologist Adamant Ironheart)'),
+(1724100,9,10,0,0,0,100,0,5000,5000,0,0,1,1,0,0,0,0,0,1,0,0,0,0,0,0,0,'Priestess Kyleen Il''dinare - Script - Say Line 2'),
+(1724100,9,11,0,0,0,100,0,2000,2000,0,0,45,2,2,0,0,0,0,19,17242,0,0,0,0,0,0,'Priestess Kyleen Il''dinare - Script - Set Data 2 2 on Archaeologist Adamant Ironheart'),
+(1724100,9,12,0,0,0,100,0,3000,3000,0,0,66,0,0,0,0,0,0,8,0,0,0,0,0,0,0.994838,'Priestess Kyleen Il''dinare - Script - Set Orientation'),
+(1724100,9,13,0,0,0,100,0,0,0,0,0,81,2,0,0,0,0,0,1,0,0,0,0,0,0,0,'Priestess Kyleen Il''dinare - Script - Set NPC Flags');
+
+DELETE FROM `waypoints` WHERE `entry` IN (1724200,1724201, 17246);
+INSERT INTO `waypoints` (`entry`, `pointid`, `position_x`, `position_y`, `position_z`, `point_comment`) VALUES
+(1724200, 1, -4699.27, -12419.77, 11.7000, 'Archaeologist Adamant Ironheart'),
+(1724201, 1, -4693.81, -12423.1, 11.8935, 'Archaeologist Adamant Ironheart'),
+(17246, 1, -4712.833, -12394.57, 12.2762, '"Cookie" McWeaksauce'),
+(17246, 2, -4715.833, -12400.07, 12.5262, '"Cookie" McWeaksauce'),
+(17246, 3, -4712.333, -12404.32, 12.2762, '"Cookie" McWeaksauce'),
+(17246, 4, -4715.833, -12400.07, 12.5262, '"Cookie" McWeaksauce'),
+(17246, 5, -4708.59, -12400.26, 11.94285, '"Cookie" McWeaksauce');
+
+DELETE FROM `conditions` WHERE `SourceTypeOrReferenceId`=13 AND `SourceEntry`=30221;
+INSERT INTO `conditions` (`SourceTypeOrReferenceId`, `SourceGroup`, `SourceEntry`, `SourceId`, `ElseGroup`, `ConditionTypeOrReference`, `ConditionTarget`, `ConditionValue1`, `ConditionValue2`, `ConditionValue3`, `NegativeCondition`, `ErrorType`, `ErrorTextId`, `ScriptName`, `Comment`) VALUES
+(13, 1, 30221, 0, 0, 31, 0, 3, 620, 0, 0, 0, 0, '', 'Shoot Targets Chicken');
diff --git a/sql/updates/world/2014_07_27_01_world_misc.sql b/sql/updates/world/2014_07_27_01_world_misc.sql
new file mode 100644
index 00000000000..359f543ce68
--- /dev/null
+++ b/sql/updates/world/2014_07_27_01_world_misc.sql
@@ -0,0 +1,3 @@
+-- Fix Startup Errors
+DELETE FROM `creature_addon` WHERE `guid` IN (103589,104200);
+DELETE FROM `waypoint_scripts` WHERE `id` IN (460,461);
diff --git a/sql/updates/world/2014_07_27_02_world_waypoints.sql b/sql/updates/world/2014_07_27_02_world_waypoints.sql
new file mode 100644
index 00000000000..badb3af6078
--- /dev/null
+++ b/sql/updates/world/2014_07_27_02_world_waypoints.sql
@@ -0,0 +1,97 @@
+-- Pathing for Murkblood Invader Entry: 18238
+SET @NPC := 65508;
+SET @PATH := @NPC * 10;
+UPDATE `creature` SET `spawndist`=0,`MovementType`=2,`position_x`=-1928.632,`position_y`=8725.079,`position_z`=24.25752,`orientation`=3.095328 WHERE `guid`=@NPC;
+DELETE FROM `creature_addon` WHERE `guid`=@NPC;
+INSERT INTO `creature_addon` (`guid`,`path_id`,`bytes2`,`mount`,`auras`) VALUES (@NPC,@PATH,1,17891, '');
+UPDATE `creature` SET `position_x`=-1918.632,`position_y`=8724.079,`position_z`=24.25752,`orientation`=3.095328 WHERE `guid`=65506;
+UPDATE `creature` SET `position_x`=-1908.632,`position_y`=8724.079,`position_z`=24.64092,`orientation`=3.095328 WHERE `guid`=65507;
+DELETE FROM `creature_formations` WHERE `leaderGUID`=65508;
+INSERT INTO `creature_formations` (`leaderGUID`,`memberGUID`,`dist`,`angle`,`groupAI`)VALUES
+(65508,65508,0,0,2),(65508,65506,10,0,2),(65508,65507,20,0,2);
+DELETE FROM `waypoint_data` WHERE `id`=@PATH;
+INSERT INTO `waypoint_data` (`id`,`point`,`position_x`,`position_y`,`position_z`,`orientation`,`delay`,`move_type`,`action`,`action_chance`,`wpguid`) VALUES
+(@PATH,1,-1928.632,8725.079,24.25752,0,0,0,0,100,0),
+(@PATH,2,-1966.446,8717.539,21.99185,0,0,0,0,100,0),
+(@PATH,3,-2005.826,8716.254,19.80993,0,0,0,0,100,0),
+(@PATH,4,-2016.783,8714.921,19.39349,0,0,0,0,100,0),
+(@PATH,5,-2042.417,8701.892,18.07981,0,0,0,0,100,0),
+(@PATH,6,-2068.804,8680.673,18.93495,0,0,0,0,100,0),
+(@PATH,7,-2087.212,8652.72,17.59001,0,0,0,0,100,0),
+(@PATH,8,-2102.178,8631.095,17.35943,0,0,0,0,100,0),
+(@PATH,9,-2124.29,8607.336,17.17577,0,0,0,0,100,0),
+(@PATH,10,-2125.007,8588.16,17.36669,0,0,0,0,100,0),
+(@PATH,11,-2116.553,8560.366,19.12604,0,0,0,0,100,0),
+(@PATH,12,-2114.252,8531.596,21.75403,0,0,0,0,100,0),
+(@PATH,13,-2108.561,8507.092,23.44275,0,0,0,0,100,0),
+(@PATH,14,-2106.812,8478.482,22.60953,0,0,0,0,100,0),
+(@PATH,15,-2106.71,8463.584,22.14218,0,0,0,0,100,0),
+(@PATH,16,-2088.777,8437.308,21.56343,0,0,0,0,100,0),
+(@PATH,17,-2074.934,8402.895,18.74801,0,0,0,0,100,0),
+(@PATH,18,-2054.847,8372.031,17.88245,0,0,0,0,100,0),
+(@PATH,19,-2044.42,8353.194,16.45808,0,0,0,0,100,0),
+(@PATH,20,-2040.957,8337.205,14.9322,0,0,0,0,100,0),
+(@PATH,21,-2021.216,8310.251,11.5401,0,0,0,0,100,0),
+(@PATH,22,-2004.646,8291.519,10.82406,0,0,0,0,100,0),
+(@PATH,23,-1989.724,8273.373,8.883897,0,0,0,0,100,0),
+(@PATH,24,-1983.553,8259.863,6.539972,0,0,0,0,100,0),
+(@PATH,25,-1982.861,8233.603,2.136774,0,0,0,0,100,0),
+(@PATH,26,-1986.143,8199.416,0.9015293,0,0,0,0,100,0),
+(@PATH,27,-2011.609,8175.506,0.3361206,0,0,0,0,100,0),
+(@PATH,28,-2030.666,8151.698,1.648474,0,0,0,0,100,0),
+(@PATH,29,-2048.426,8130.438,2.55332,0,0,0,0,100,0),
+(@PATH,30,-2064.924,8112.038,2.538671,0,0,0,0,100,0),
+(@PATH,31,-2079.267,8093.191,2.946595,0,0,0,0,100,0),
+(@PATH,32,-2091.217,8071.594,2.854432,0,0,0,0,100,0),
+(@PATH,33,-2106.352,8049.733,1.976455,0,0,0,0,100,0),
+(@PATH,34,-2121.393,8026.129,1.529545,0,0,0,0,100,0),
+(@PATH,35,-2126.731,8001.408,0.009037018,0,0,0,0,100,0),
+(@PATH,36,-2133.614,7980.045,-1.761643,0,0,0,0,100,0),
+(@PATH,37,-2141.162,7953.366,-4.754976,0,0,0,0,100,0),
+(@PATH,38,-2141.755,7928.814,-6.847231,0,0,0,0,100,0),
+(@PATH,39,-2143.836,7906.825,-8.610537,0,0,0,0,100,0),
+(@PATH,40,-2146.907,7880.856,-10.76713,0,0,0,0,100,0),
+(@PATH,41,-2149.451,7859.555,-11.69755,0,0,0,0,100,0),
+(@PATH,42,-2149.775,7839.294,-12.42301,0,0,0,0,100,0),
+(@PATH,43,-2152.03,7824.522,-12.74447,0,0,0,0,100,0),
+(@PATH,44,-2149.775,7839.294,-12.42301,0,0,0,0,100,0),
+(@PATH,45,-2149.451,7859.555,-11.69755,0,0,0,0,100,0),
+(@PATH,46,-2146.907,7880.856,-10.76713,0,0,0,0,100,0),
+(@PATH,47,-2143.836,7906.825,-8.610537,0,0,0,0,100,0),
+(@PATH,48,-2141.755,7928.814,-6.847231,0,0,0,0,100,0),
+(@PATH,49,-2141.162,7953.366,-4.754976,0,0,0,0,100,0),
+(@PATH,50,-2133.614,7980.045,-1.761643,0,0,0,0,100,0),
+(@PATH,51,-2126.731,8001.408,0.009037018,0,0,0,0,100,0),
+(@PATH,52,-2121.393,8026.129,1.529545,0,0,0,0,100,0),
+(@PATH,53,-2106.352,8049.733,1.976455,0,0,0,0,100,0),
+(@PATH,54,-2091.217,8071.594,2.854432,0,0,0,0,100,0),
+(@PATH,55,-2079.267,8093.191,2.946595,0,0,0,0,100,0),
+(@PATH,56,-2064.924,8112.038,2.538671,0,0,0,0,100,0),
+(@PATH,57,-2048.426,8130.438,2.55332,0,0,0,0,100,0),
+(@PATH,58,-2030.666,8151.698,1.648474,0,0,0,0,100,0),
+(@PATH,59,-2011.609,8175.506,0.3361206,0,0,0,0,100,0),
+(@PATH,60,-1986.143,8199.416,0.9015293,0,0,0,0,100,0),
+(@PATH,61,-1982.861,8233.603,2.136774,0,0,0,0,100,0),
+(@PATH,62,-1983.553,8259.863,6.539972,0,0,0,0,100,0),
+(@PATH,63,-1989.724,8273.373,8.883897,0,0,0,0,100,0),
+(@PATH,64,-2004.646,8291.519,10.82406,0,0,0,0,100,0),
+(@PATH,65,-2021.216,8310.251,11.5401,0,0,0,0,100,0),
+(@PATH,66,-2040.957,8337.205,14.9322,0,0,0,0,100,0),
+(@PATH,67,-2044.42,8353.194,16.45808,0,0,0,0,100,0),
+(@PATH,68,-2054.847,8372.031,17.88245,0,0,0,0,100,0),
+(@PATH,69,-2074.934,8402.895,18.74801,0,0,0,0,100,0),
+(@PATH,70,-2088.777,8437.308,21.56343,0,0,0,0,100,0),
+(@PATH,71,-2106.71,8463.584,22.14218,0,0,0,0,100,0),
+(@PATH,72,-2106.812,8478.482,22.60953,0,0,0,0,100,0),
+(@PATH,73,-2108.561,8507.092,23.44275,0,0,0,0,100,0),
+(@PATH,74,-2114.252,8531.596,21.75403,0,0,0,0,100,0),
+(@PATH,75,-2116.553,8560.366,19.12604,0,0,0,0,100,0),
+(@PATH,76,-2125.007,8588.16,17.36669,0,0,0,0,100,0),
+(@PATH,77,-2124.29,8607.336,17.17577,0,0,0,0,100,0),
+(@PATH,78,-2102.178,8631.095,17.35943,0,0,0,0,100,0),
+(@PATH,79,-2087.212,8652.72,17.59001,0,0,0,0,100,0),
+(@PATH,80,-2068.804,8680.673,18.93495,0,0,0,0,100,0),
+(@PATH,81,-2042.417,8701.892,18.07981,0,0,0,0,100,0),
+(@PATH,82,-2016.783,8714.921,19.39349,0,0,0,0,100,0),
+(@PATH,83,-2005.826,8716.254,19.80993,0,0,0,0,100,0),
+(@PATH,84,-1966.446,8717.539,21.99185,0,0,0,0,100,0);
diff --git a/src/server/authserver/Server/AuthSession.cpp b/src/server/authserver/Server/AuthSession.cpp
index 446b0a43158..b2fb516804f 100644
--- a/src/server/authserver/Server/AuthSession.cpp
+++ b/src/server/authserver/Server/AuthSession.cpp
@@ -16,11 +16,8 @@
* with this program. If not, see <http://www.gnu.org/licenses/>.
*/
-#include <memory>
-#include <boost/lexical_cast.hpp>
-#include <boost/asio/write.hpp>
-#include <AuthSession.h>
-#include <Log.h>
+#include "AuthSession.h"
+#include "Log.h"
#include "ByteBuffer.h"
#include "AuthCodes.h"
#include "Database/DatabaseEnv.h"
@@ -28,6 +25,7 @@
#include "openssl/crypto.h"
#include "Configuration/Config.h"
#include "RealmList.h"
+#include <boost/lexical_cast.hpp>
using boost::asio::ip::tcp;
@@ -111,98 +109,88 @@ typedef struct AUTH_RECONNECT_PROOF_C
#pragma pack(pop)
-
-typedef struct AuthHandler
-{
- eAuthCmd cmd;
- uint32 status;
- size_t packetSize;
- bool (AuthSession::*handler)();
-} AuthHandler;
-
#define BYTE_SIZE 32
#define REALMLIST_SKIP_PACKETS 5
+#define XFER_ACCEPT_SIZE 1
+#define XFER_RESUME_SIZE 9
+#define XFER_CANCEL_SIZE 1
-const AuthHandler table[] =
+std::unordered_map<uint8, AuthHandler> AuthSession::InitHandlers()
{
- { AUTH_LOGON_CHALLENGE, STATUS_CONNECTED, sizeof(AUTH_LOGON_CHALLENGE_C), &AuthSession::_HandleLogonChallenge },
- { AUTH_LOGON_PROOF, STATUS_CONNECTED, sizeof(AUTH_LOGON_PROOF_C), &AuthSession::_HandleLogonProof },
- { AUTH_RECONNECT_CHALLENGE, STATUS_CONNECTED, sizeof(AUTH_LOGON_CHALLENGE_C), &AuthSession::_HandleReconnectChallenge },
- { AUTH_RECONNECT_PROOF, STATUS_CONNECTED, sizeof(AUTH_RECONNECT_PROOF_C), &AuthSession::_HandleReconnectProof },
- { REALM_LIST, STATUS_AUTHED, REALMLIST_SKIP_PACKETS, &AuthSession::_HandleRealmList }
-};
+ std::unordered_map<uint8, AuthHandler> handlers;
+
+ handlers[AUTH_LOGON_CHALLENGE] = { STATUS_CONNECTED, sizeof(AUTH_LOGON_CHALLENGE_C), &AuthSession::HandleLogonChallenge };
+ handlers[AUTH_LOGON_PROOF] = { STATUS_CONNECTED, sizeof(AUTH_LOGON_PROOF_C), &AuthSession::HandleLogonProof };
+ handlers[AUTH_RECONNECT_CHALLENGE] = { STATUS_CONNECTED, sizeof(AUTH_LOGON_CHALLENGE_C), &AuthSession::HandleReconnectChallenge };
+ handlers[AUTH_RECONNECT_PROOF] = { STATUS_CONNECTED, sizeof(AUTH_RECONNECT_PROOF_C), &AuthSession::HandleReconnectProof };
+ handlers[REALM_LIST] = { STATUS_AUTHED, REALMLIST_SKIP_PACKETS, &AuthSession::HandleRealmList };
+ handlers[XFER_ACCEPT] = { STATUS_AUTHED, XFER_ACCEPT_SIZE, &AuthSession::HandleXferAccept };
+ handlers[XFER_RESUME] = { STATUS_AUTHED, XFER_RESUME_SIZE, &AuthSession::HandleXferResume };
+ handlers[XFER_CANCEL] = { STATUS_AUTHED, XFER_CANCEL_SIZE, &AuthSession::HandleXferCancel };
+
+ return handlers;
+}
-void AuthSession::AsyncReadHeader()
-{
- auto self(shared_from_this());
+std::unordered_map<uint8, AuthHandler> const Handlers = AuthSession::InitHandlers();
- _socket.async_read_some(boost::asio::buffer(_readBuffer, 1), [this, self](boost::system::error_code error, size_t transferedBytes)
+void AuthSession::ReadHeaderHandler(boost::system::error_code error, size_t transferedBytes)
+{
+ if (!error && transferedBytes == 1)
{
- if (!error && transferedBytes == 1)
+ uint8 cmd = GetReadBuffer()[0];
+ auto itr = Handlers.find(cmd);
+ if (itr != Handlers.end())
{
- for (const AuthHandler& entry : table)
+ // Handle dynamic size packet
+ if (cmd == AUTH_LOGON_CHALLENGE || cmd == AUTH_RECONNECT_CHALLENGE)
{
- if ((uint8)entry.cmd == _readBuffer[0] && (entry.status == STATUS_CONNECTED || (_isAuthenticated && entry.status == STATUS_AUTHED)))
- {
- // Handle dynamic size packet
- if (_readBuffer[0] == AUTH_LOGON_CHALLENGE || _readBuffer[0] == AUTH_RECONNECT_CHALLENGE)
- {
- _socket.read_some(boost::asio::buffer(&_readBuffer[1], sizeof(uint8) + sizeof(uint16))); //error + size
+ ReadData(sizeof(uint8) + sizeof(uint16), sizeof(cmd)); //error + size
+ sAuthLogonChallenge_C* challenge = reinterpret_cast<sAuthLogonChallenge_C*>(GetReadBuffer());
- AsyncReadData(entry.handler, *reinterpret_cast<uint16*>(&_readBuffer[2]), sizeof(uint8) + sizeof(uint8) + sizeof(uint16)); // cmd + error + size
- }
- else
- {
- AsyncReadData(entry.handler, entry.packetSize, sizeof(uint8));
- }
- break;
- }
+ AsyncReadData(challenge->size, sizeof(uint8) + sizeof(uint8) + sizeof(uint16)); // cmd + error + size
}
+ else
+ AsyncReadData(itr->second.packetSize, sizeof(uint8));
}
- else
- {
- CloseSocket();
- }
- });
+ }
+ else
+ CloseSocket();
}
-void AuthSession::AsyncReadData(bool (AuthSession::*handler)(), size_t dataSize, size_t bufferOffSet)
+void AuthSession::ReadDataHandler(boost::system::error_code error, size_t transferedBytes)
{
- auto self(shared_from_this());
-
- _socket.async_read_some(boost::asio::buffer(&_readBuffer[bufferOffSet], dataSize), [handler, this, self](boost::system::error_code error, size_t transferedBytes)
+ if (!error && transferedBytes > 0)
{
- if (!error && transferedBytes > 0)
- {
- if (!(*this.*handler)())
- {
- CloseSocket();
- return;
- }
-
- AsyncReadHeader();
- }
- else
+ if (!(*this.*Handlers.at(GetReadBuffer()[0]).handler)())
{
CloseSocket();
+ return;
}
- });
+
+ AsyncReadHeader();
+ }
+ else
+ CloseSocket();
}
-void AuthSession::AsyncWrite(std::size_t length)
+void AuthSession::AsyncWrite(ByteBuffer const& packet)
{
- boost::asio::async_write(_socket, boost::asio::buffer(_writeBuffer, length), [this](boost::system::error_code error, std::size_t /*length*/)
- {
- if (error)
- {
- CloseSocket();
- }
- });
+ std::vector<uint8> data(packet.size());
+ std::memcpy(data.data(), packet.contents(), packet.size());
+
+ std::lock_guard<std::mutex> guard(_writeLock);
+
+ bool needsWriteStart = _writeQueue.empty();
+
+ _writeQueue.push(std::move(data));
+
+ if (needsWriteStart)
+ AsyncWrite(_writeQueue.front());
}
-bool AuthSession::_HandleLogonChallenge()
+bool AuthSession::HandleLogonChallenge()
{
- sAuthLogonChallenge_C *challenge = (sAuthLogonChallenge_C*)&_readBuffer;
+ sAuthLogonChallenge_C* challenge = reinterpret_cast<sAuthLogonChallenge_C*>(GetReadBuffer());
//TC_LOG_DEBUG("server.authserver", "[AuthChallenge] got full packet, %#04x bytes", challenge->size);
TC_LOG_DEBUG("server.authserver", "[AuthChallenge] name(%d): '%s'", challenge->I_len, challenge->I);
@@ -226,8 +214,8 @@ bool AuthSession::_HandleLogonChallenge()
// Verify that this IP is not in the ip_banned table
LoginDatabase.Execute(LoginDatabase.GetPreparedStatement(LOGIN_DEL_EXPIRED_IP_BANS));
- std::string const& ipAddress = _socket.remote_endpoint().address().to_string();
- unsigned short port = _socket.remote_endpoint().port();
+ std::string ipAddress = GetRemoteIpAddress().to_string();
+ uint16 port = GetRemotePort();
PreparedStatement* stmt = LoginDatabase.GetPreparedStatement(LOGIN_SEL_IP_BANNED);
stmt->setString(0, ipAddress);
@@ -413,20 +401,17 @@ bool AuthSession::_HandleLogonChallenge()
pkt << uint8(WOW_FAIL_UNKNOWN_ACCOUNT);
}
- std::memcpy(_writeBuffer, (char const*)pkt.contents(), pkt.size());
-
- AsyncWrite(pkt.size());
-
+ AsyncWrite(pkt);
return true;
}
// Logon Proof command handler
-bool AuthSession::_HandleLogonProof()
+bool AuthSession::HandleLogonProof()
{
TC_LOG_DEBUG("server.authserver", "Entering _HandleLogonProof");
// Read the packet
- sAuthLogonProof_C *logonProof = (sAuthLogonProof_C*)&_readBuffer;
+ sAuthLogonProof_C *logonProof = reinterpret_cast<sAuthLogonProof_C*>(GetReadBuffer());
// If the client has no valid version
if (_expversion == NO_VALID_EXP_FLAG)
@@ -514,12 +499,12 @@ bool AuthSession::_HandleLogonProof()
// Check if SRP6 results match (password is correct), else send an error
if (!memcmp(M.AsByteArray().get(), logonProof->M1, 20))
{
- TC_LOG_DEBUG("server.authserver", "'%s:%d' User '%s' successfully authenticated", GetRemoteIpAddress().c_str(), GetRemotePort(), _login.c_str());
+ TC_LOG_DEBUG("server.authserver", "'%s:%d' User '%s' successfully authenticated", GetRemoteIpAddress().to_string().c_str(), GetRemotePort(), _login.c_str());
// Update the sessionkey, last_ip, last login time and reset number of failed logins in the account table for this account
PreparedStatement *stmt = LoginDatabase.GetPreparedStatement(LOGIN_UPD_LOGONPROOF);
stmt->setString(0, K.AsHexStr());
- stmt->setString(1, GetRemoteIpAddress().c_str());
+ stmt->setString(1, GetRemoteIpAddress().to_string().c_str());
stmt->setUInt32(2, GetLocaleByName(_localizationName));
stmt->setString(3, _os);
stmt->setString(4, _login);
@@ -546,12 +531,17 @@ bool AuthSession::_HandleLogonProof()
delete[] token;
if (validToken != incomingToken)
{
- char data[] = { AUTH_LOGON_PROOF, WOW_FAIL_UNKNOWN_ACCOUNT, 3, 0 };
- socket().send(data, sizeof(data));
- return false;
+ ByteBuffer packet;
+ packet << uint8(AUTH_LOGON_PROOF);
+ packet << uint8(WOW_FAIL_UNKNOWN_ACCOUNT);
+ packet << uint8(3);
+ packet << uint8(0);
+ AsyncWrite(packet);
+ return false;
}*/
}
+ ByteBuffer packet;
if (_expversion & POST_BC_EXP_FLAG) // 2.x and 3.x clients
{
sAuthLogonProof_S proof;
@@ -562,8 +552,8 @@ bool AuthSession::_HandleLogonProof()
proof.unk2 = 0x00; // SurveyId
proof.unk3 = 0x00;
- std::memcpy(_writeBuffer, (char *)&proof, sizeof(proof));
- AsyncWrite(sizeof(proof));
+ packet.resize(sizeof(proof));
+ std::memcpy(packet.contents(), &proof, sizeof(proof));
}
else
{
@@ -573,21 +563,24 @@ bool AuthSession::_HandleLogonProof()
proof.error = 0;
proof.unk2 = 0x00;
- std::memcpy(_writeBuffer, (char *)&proof, sizeof(proof));
- AsyncWrite(sizeof(proof));
+ packet.resize(sizeof(proof));
+ std::memcpy(packet.contents(), &proof, sizeof(proof));
}
+ AsyncWrite(packet);
_isAuthenticated = true;
}
else
{
- char data[4] = { AUTH_LOGON_PROOF, WOW_FAIL_UNKNOWN_ACCOUNT, 3, 0 };
-
- std::memcpy(_writeBuffer, data, sizeof(data));
- AsyncWrite(sizeof(data));
+ ByteBuffer packet;
+ packet << uint8(AUTH_LOGON_PROOF);
+ packet << uint8(WOW_FAIL_UNKNOWN_ACCOUNT);
+ packet << uint8(3);
+ packet << uint8(0);
+ AsyncWrite(packet);
TC_LOG_DEBUG("server.authserver", "'%s:%d' [AuthChallenge] account %s tried to login with invalid password!",
- GetRemoteIpAddress().c_str(), GetRemotePort(), _login.c_str());
+ GetRemoteIpAddress().to_string().c_str(), GetRemotePort(), _login.c_str());
uint32 MaxWrongPassCount = sConfigMgr->GetIntDefault("WrongPass.MaxCount", 0);
@@ -596,7 +589,7 @@ bool AuthSession::_HandleLogonProof()
{
PreparedStatement* logstmt = LoginDatabase.GetPreparedStatement(LOGIN_INS_FALP_IP_LOGGING);
logstmt->setString(0, _login);
- logstmt->setString(1, GetRemoteIpAddress());
+ logstmt->setString(1, GetRemoteIpAddress().to_string());
logstmt->setString(2, "Logged on failed AccountLogin due wrong password");
LoginDatabase.Execute(logstmt);
@@ -630,17 +623,17 @@ bool AuthSession::_HandleLogonProof()
LoginDatabase.Execute(stmt);
TC_LOG_DEBUG("server.authserver", "'%s:%d' [AuthChallenge] account %s got banned for '%u' seconds because it failed to authenticate '%u' times",
- GetRemoteIpAddress().c_str(), GetRemotePort(), _login.c_str(), WrongPassBanTime, failed_logins);
+ GetRemoteIpAddress().to_string().c_str(), GetRemotePort(), _login.c_str(), WrongPassBanTime, failed_logins);
}
else
{
stmt = LoginDatabase.GetPreparedStatement(LOGIN_INS_IP_AUTO_BANNED);
- stmt->setString(0, GetRemoteIpAddress());
+ stmt->setString(0, GetRemoteIpAddress().to_string());
stmt->setUInt32(1, WrongPassBanTime);
LoginDatabase.Execute(stmt);
TC_LOG_DEBUG("server.authserver", "'%s:%d' [AuthChallenge] IP got banned for '%u' seconds because account %s failed to authenticate '%u' times",
- GetRemoteIpAddress().c_str(), GetRemotePort(), WrongPassBanTime, _login.c_str(), failed_logins);
+ GetRemoteIpAddress().to_string().c_str(), GetRemotePort(), WrongPassBanTime, _login.c_str(), failed_logins);
}
}
}
@@ -650,10 +643,10 @@ bool AuthSession::_HandleLogonProof()
return true;
}
-bool AuthSession::_HandleReconnectChallenge()
+bool AuthSession::HandleReconnectChallenge()
{
TC_LOG_DEBUG("server.authserver", "Entering _HandleReconnectChallenge");
- sAuthLogonChallenge_C *challenge = (sAuthLogonChallenge_C*)&_readBuffer;
+ sAuthLogonChallenge_C* challenge = reinterpret_cast<sAuthLogonChallenge_C*>(GetReadBuffer());
//TC_LOG_DEBUG("server.authserver", "[AuthChallenge] got full packet, %#04x bytes", challenge->size);
TC_LOG_DEBUG("server.authserver", "[AuthChallenge] name(%d): '%s'", challenge->I_len, challenge->I);
@@ -668,7 +661,7 @@ bool AuthSession::_HandleReconnectChallenge()
if (!result)
{
TC_LOG_ERROR("server.authserver", "'%s:%d' [ERROR] user %s tried to login and we cannot find his session key in the database.",
- GetRemoteIpAddress().c_str(), GetRemotePort(), _login.c_str());
+ GetRemoteIpAddress().to_string().c_str(), GetRemotePort(), _login.c_str());
return false;
}
@@ -697,15 +690,14 @@ bool AuthSession::_HandleReconnectChallenge()
pkt.append(_reconnectProof.AsByteArray(16).get(), 16); // 16 bytes random
pkt << uint64(0x00) << uint64(0x00); // 16 bytes zeros
- std::memcpy(_writeBuffer, (char const*)pkt.contents(), pkt.size());
- AsyncWrite(pkt.size());
+ AsyncWrite(pkt);
return true;
}
-bool AuthSession::_HandleReconnectProof()
+bool AuthSession::HandleReconnectProof()
{
TC_LOG_DEBUG("server.authserver", "Entering _HandleReconnectProof");
- sAuthReconnectProof_C *reconnectProof = (sAuthReconnectProof_C*)&_readBuffer;
+ sAuthReconnectProof_C *reconnectProof = reinterpret_cast<sAuthReconnectProof_C*>(GetReadBuffer());
if (_login.empty() || !_reconnectProof.GetNumBytes() || !K.GetNumBytes())
return false;
@@ -726,20 +718,19 @@ bool AuthSession::_HandleReconnectProof()
pkt << uint8(AUTH_RECONNECT_PROOF);
pkt << uint8(0x00);
pkt << uint16(0x00); // 2 bytes zeros
- std::memcpy(_writeBuffer, (char const*)pkt.contents(), pkt.size());
- AsyncWrite(pkt.size());
+ AsyncWrite(pkt);
_isAuthenticated = true;
return true;
}
else
{
- TC_LOG_ERROR("server.authserver", "'%s:%d' [ERROR] user %s tried to login, but session is invalid.", GetRemoteIpAddress().c_str(),
+ TC_LOG_ERROR("server.authserver", "'%s:%d' [ERROR] user %s tried to login, but session is invalid.", GetRemoteIpAddress().to_string().c_str(),
GetRemotePort(), _login.c_str());
return false;
}
}
-bool AuthSession::_HandleRealmList()
+bool AuthSession::HandleRealmList()
{
TC_LOG_DEBUG("server.authserver", "Entering _HandleRealmList");
@@ -750,7 +741,7 @@ bool AuthSession::_HandleRealmList()
PreparedQueryResult result = LoginDatabase.Query(stmt);
if (!result)
{
- TC_LOG_ERROR("server.authserver", "'%s:%d' [ERROR] user %s tried to login but we cannot find him in the database.", GetRemoteIpAddress().c_str(),
+ TC_LOG_ERROR("server.authserver", "'%s:%d' [ERROR] user %s tried to login but we cannot find him in the database.", GetRemoteIpAddress().to_string().c_str(),
GetRemotePort(), _login.c_str());
return false;
}
@@ -808,7 +799,7 @@ bool AuthSession::_HandleRealmList()
pkt << lock; // if 1, then realm locked
pkt << uint8(flag); // RealmFlags
pkt << name;
- pkt << boost::lexical_cast<std::string>(realm.GetAddressForClient(_socket.remote_endpoint().address()));
+ pkt << boost::lexical_cast<std::string>(realm.GetAddressForClient(GetRemoteIpAddress()));
pkt << realm.populationLevel;
pkt << AmountOfCharacters;
pkt << realm.timezone; // realm category
@@ -852,10 +843,32 @@ bool AuthSession::_HandleRealmList()
hdr << uint16(pkt.size() + RealmListSizeBuffer.size());
hdr.append(RealmListSizeBuffer); // append RealmList's size buffer
hdr.append(pkt); // append realms in the realmlist
+ AsyncWrite(hdr);
+ return true;
+}
+
+// Resume patch transfer
+bool AuthSession::HandleXferResume()
+{
+ TC_LOG_DEBUG("server.authserver", "Entering _HandleXferResume");
+ //uint8
+ //uint64
+ return true;
+}
- std::memcpy(_writeBuffer, (char const*)hdr.contents(), hdr.size());
- AsyncWrite(hdr.size());
+// Cancel patch transfer
+bool AuthSession::HandleXferCancel()
+{
+ TC_LOG_DEBUG("server.authserver", "Entering _HandleXferCancel");
+ //uint8
+ return false;
+}
+// Accept patch transfer
+bool AuthSession::HandleXferAccept()
+{
+ TC_LOG_DEBUG("server.authserver", "Entering _HandleXferAccept");
+ //uint8
return true;
}
@@ -889,12 +902,3 @@ void AuthSession::SetVSFields(const std::string& rI)
stmt->setString(2, _login);
LoginDatabase.Execute(stmt);
}
-
-void AuthSession::CloseSocket()
-{
- boost::system::error_code socketError;
- _socket.close(socketError);
- if (socketError)
- TC_LOG_DEBUG("server.authserver", "Account '%s' errored when closing socket: %i (%s)",
- _login.c_str(), socketError.value(), socketError.message().c_str());
-}
diff --git a/src/server/authserver/Server/AuthSession.h b/src/server/authserver/Server/AuthSession.h
index 6dc9c404857..eedffb86ff8 100644
--- a/src/server/authserver/Server/AuthSession.h
+++ b/src/server/authserver/Server/AuthSession.h
@@ -19,46 +19,52 @@
#ifndef __AUTHSESSION_H__
#define __AUTHSESSION_H__
-#include <memory>
-#include <boost/asio/ip/tcp.hpp>
#include "Common.h"
+#include "Socket.h"
#include "BigNumber.h"
+#include <memory>
+#include <boost/asio/ip/tcp.hpp>
using boost::asio::ip::tcp;
-const size_t bufferSize = 4096;
+struct AuthHandler;
+class ByteBuffer;
-#define BUFFER_SIZE 4096
-
-class AuthSession : public std::enable_shared_from_this < AuthSession >
+class AuthSession : public Socket<AuthSession>
{
+
public:
- AuthSession(tcp::socket&& socket) : _socket(std::move(socket))
+ static std::unordered_map<uint8, AuthHandler> InitHandlers();
+
+ AuthSession(tcp::socket&& socket) : Socket(std::move(socket), 1)
{
N.SetHexStr("894B645E89E1535BBDAD5B8B290650530801B18EBFBF5E8FAB3C82872A3E9BB7");
g.SetDword(7);
}
- void Start()
+ void Start() override
{
AsyncReadHeader();
}
- bool _HandleLogonChallenge();
- bool _HandleLogonProof();
- bool _HandleReconnectChallenge();
- bool _HandleReconnectProof();
- bool _HandleRealmList();
+ using Socket<AuthSession>::AsyncWrite;
+ void AsyncWrite(ByteBuffer const& packet);
- const std::string GetRemoteIpAddress() const { return _socket.remote_endpoint().address().to_string(); };
- unsigned short GetRemotePort() const { return _socket.remote_endpoint().port(); }
+protected:
+ void ReadHeaderHandler(boost::system::error_code error, size_t transferedBytes) override;
+ void ReadDataHandler(boost::system::error_code error, size_t transferedBytes) override;
private:
- void AsyncReadHeader();
- void AsyncReadData(bool (AuthSession::*handler)(), size_t dataSize, size_t bufferOffset);
- void AsyncWrite(size_t length);
+ bool HandleLogonChallenge();
+ bool HandleLogonProof();
+ bool HandleReconnectChallenge();
+ bool HandleReconnectProof();
+ bool HandleRealmList();
- void CloseSocket();
+ //data transfer handle for patch
+ bool HandleXferResume();
+ bool HandleXferCancel();
+ bool HandleXferAccept();
void SetVSFields(const std::string& rI);
@@ -67,10 +73,6 @@ private:
BigNumber K;
BigNumber _reconnectProof;
- tcp::socket _socket;
- char _readBuffer[BUFFER_SIZE];
- char _writeBuffer[BUFFER_SIZE];
-
bool _isAuthenticated;
std::string _tokenKey;
std::string _login;
@@ -82,4 +84,15 @@ private:
AccountTypes _accountSecurityLevel;
};
+#pragma pack(push, 1)
+
+struct AuthHandler
+{
+ uint32 status;
+ size_t packetSize;
+ bool (AuthSession::*handler)();
+};
+
+#pragma pack(pop)
+
#endif
diff --git a/src/server/game/CMakeLists.txt b/src/server/game/CMakeLists.txt
index 8e4ae9b5498..abb415e0f64 100644
--- a/src/server/game/CMakeLists.txt
+++ b/src/server/game/CMakeLists.txt
@@ -123,6 +123,7 @@ include_directories(
${CMAKE_SOURCE_DIR}/src/server/shared/Dynamic/LinkedReference
${CMAKE_SOURCE_DIR}/src/server/shared/Dynamic
${CMAKE_SOURCE_DIR}/src/server/shared/Logging
+ ${CMAKE_SOURCE_DIR}/src/server/shared/Networking
${CMAKE_SOURCE_DIR}/src/server/shared/Packets
${CMAKE_SOURCE_DIR}/src/server/shared/Threading
${CMAKE_SOURCE_DIR}/src/server/shared/Utilities
diff --git a/src/server/game/Globals/ObjectAccessor.h b/src/server/game/Globals/ObjectAccessor.h
index d2331f14690..f466d8bd328 100644
--- a/src/server/game/Globals/ObjectAccessor.h
+++ b/src/server/game/Globals/ObjectAccessor.h
@@ -51,7 +51,7 @@ class HashMapHolder
static void Insert(T* o)
{
- boost::shared_lock<boost::shared_mutex> lock(_lock);
+ boost::unique_lock<boost::shared_mutex> lock(_lock);
_objectMap[o->GetGUID()] = o;
}
@@ -59,12 +59,14 @@ class HashMapHolder
static void Remove(T* o)
{
boost::unique_lock<boost::shared_mutex> lock(_lock);
+
_objectMap.erase(o->GetGUID());
}
static T* Find(uint64 guid)
{
boost::shared_lock<boost::shared_mutex> lock(_lock);
+
typename MapType::iterator itr = _objectMap.find(guid);
return (itr != _objectMap.end()) ? itr->second : NULL;
}
diff --git a/src/server/game/Movement/MovementGenerators/WaypointMovementGenerator.cpp b/src/server/game/Movement/MovementGenerators/WaypointMovementGenerator.cpp
index aee8c497247..8cde9876ca1 100755
--- a/src/server/game/Movement/MovementGenerators/WaypointMovementGenerator.cpp
+++ b/src/server/game/Movement/MovementGenerators/WaypointMovementGenerator.cpp
@@ -161,13 +161,28 @@ bool WaypointMovementGenerator<Creature>::StartMove(Creature* creature)
if (node->orientation && node->delay)
init.SetFacing(node->orientation);
- init.SetWalk(!node->run);
+ switch (node->move_type)
+ {
+ case WAYPOINT_MOVE_TYPE_LAND:
+ init.SetAnimation(Movement::ToGround);
+ break;
+ case WAYPOINT_MOVE_TYPE_TAKEOFF:
+ init.SetAnimation(Movement::ToFly);
+ break;
+ case WAYPOINT_MOVE_TYPE_RUN:
+ init.SetWalk(false);
+ break;
+ case WAYPOINT_MOVE_TYPE_WALK:
+ init.SetWalk(true);
+ break;
+ }
+
init.Launch();
//Call for creature group update
if (creature->GetFormation() && creature->GetFormation()->getLeader() == creature)
{
- creature->SetWalk(!node->run);
+ creature->SetWalk(node->move_type != WAYPOINT_MOVE_TYPE_RUN);
creature->GetFormation()->LeaderMoveTo(formationDest.x, formationDest.y, formationDest.z);
}
diff --git a/src/server/game/Movement/Waypoints/WaypointManager.cpp b/src/server/game/Movement/Waypoints/WaypointManager.cpp
index f7cb147a148..2820c5dee17 100644
--- a/src/server/game/Movement/Waypoints/WaypointManager.cpp
+++ b/src/server/game/Movement/Waypoints/WaypointManager.cpp
@@ -42,7 +42,7 @@ void WaypointMgr::Load()
uint32 oldMSTime = getMSTime();
// 0 1 2 3 4 5 6 7 8 9
- QueryResult result = WorldDatabase.Query("SELECT id, point, position_x, position_y, position_z, orientation, move_flag, delay, action, action_chance FROM waypoint_data ORDER BY id, point");
+ QueryResult result = WorldDatabase.Query("SELECT id, point, position_x, position_y, position_z, orientation, move_type, delay, action, action_chance FROM waypoint_data ORDER BY id, point");
if (!result)
{
@@ -73,7 +73,14 @@ void WaypointMgr::Load()
wp->y = y;
wp->z = z;
wp->orientation = o;
- wp->run = fields[6].GetBool();
+ wp->move_type = fields[6].GetUInt32();
+
+ if (wp->move_type >= WAYPOINT_MOVE_TYPE_MAX)
+ {
+ TC_LOG_ERROR("sql.sql", "Waypoint %u in waypoint_data has invalid move_type, ignoring", wp->id);
+ continue;
+ }
+
wp->delay = fields[7].GetUInt32();
wp->event_id = fields[8].GetUInt32();
wp->event_chance = fields[9].GetInt16();
@@ -126,7 +133,14 @@ void WaypointMgr::ReloadPath(uint32 id)
wp->y = y;
wp->z = z;
wp->orientation = o;
- wp->run = fields[5].GetBool();
+ wp->move_type = fields[5].GetUInt32();
+
+ if (wp->move_type >= WAYPOINT_MOVE_TYPE_MAX)
+ {
+ TC_LOG_ERROR("sql.sql", "Waypoint %u in waypoint_data has invalid move_type, ignoring", wp->id);
+ continue;
+ }
+
wp->delay = fields[6].GetUInt32();
wp->event_id = fields[7].GetUInt32();
wp->event_chance = fields[8].GetUInt8();
diff --git a/src/server/game/Movement/Waypoints/WaypointManager.h b/src/server/game/Movement/Waypoints/WaypointManager.h
index 385f4809729..8e5dd1f64c7 100644
--- a/src/server/game/Movement/Waypoints/WaypointManager.h
+++ b/src/server/game/Movement/Waypoints/WaypointManager.h
@@ -21,13 +21,23 @@
#include <vector>
+enum WaypointMoveType
+{
+ WAYPOINT_MOVE_TYPE_WALK,
+ WAYPOINT_MOVE_TYPE_RUN,
+ WAYPOINT_MOVE_TYPE_LAND,
+ WAYPOINT_MOVE_TYPE_TAKEOFF,
+
+ WAYPOINT_MOVE_TYPE_MAX
+};
+
struct WaypointData
{
uint32 id;
float x, y, z, orientation;
uint32 delay;
uint32 event_id;
- bool run;
+ uint32 move_type;
uint8 event_chance;
};
diff --git a/src/server/game/Server/WorldSession.cpp b/src/server/game/Server/WorldSession.cpp
index cabb0ef0494..46411b35522 100644
--- a/src/server/game/Server/WorldSession.cpp
+++ b/src/server/game/Server/WorldSession.cpp
@@ -134,7 +134,7 @@ WorldSession::WorldSession(uint32 id, uint32 battlenetAccountId, std::shared_ptr
if (sock)
{
- m_Address = sock->GetRemoteIpAddress();
+ m_Address = sock->GetRemoteIpAddress().to_string();
ResetTimeOutTime();
LoginDatabase.PExecute("UPDATE account SET online = 1 WHERE id = %u;", GetAccountId()); // One-time query
}
diff --git a/src/server/game/Server/WorldSocket.cpp b/src/server/game/Server/WorldSocket.cpp
index 7dad289d1e9..48c12f84870 100644
--- a/src/server/game/Server/WorldSocket.cpp
+++ b/src/server/game/Server/WorldSocket.cpp
@@ -16,8 +16,6 @@
* with this program. If not, see <http://www.gnu.org/licenses/>.
*/
-#include <boost/asio/write.hpp>
-#include <boost/asio/read_until.hpp>
#include <memory>
#include "WorldSocket.h"
#include "ServerPktHeader.h"
@@ -29,10 +27,9 @@
#include "BattlenetAccountMgr.h"
using boost::asio::ip::tcp;
-using boost::asio::streambuf;
WorldSocket::WorldSocket(tcp::socket&& socket)
- : _socket(std::move(socket)), _authSeed(rand32()), _OverSpeedPings(0), _worldSession(nullptr)
+ : Socket(std::move(socket), sizeof(ClientPktHeader)), _authSeed(rand32()), _OverSpeedPings(0), _worldSession(nullptr)
{
}
@@ -63,135 +60,119 @@ void WorldSocket::HandleSendAuthSession()
AsyncWrite(packet);
}
-void WorldSocket::AsyncReadHeader()
+void WorldSocket::ReadHeaderHandler(boost::system::error_code error, size_t transferedBytes)
{
- auto self(shared_from_this());
- _socket.async_read_some(boost::asio::buffer(_readBuffer, sizeof(ClientPktHeader)), [this, self](boost::system::error_code error, size_t transferedBytes)
+ if (!error && transferedBytes == sizeof(ClientPktHeader))
{
- if (!error && transferedBytes == sizeof(ClientPktHeader))
- {
- ClientPktHeader* header = (ClientPktHeader*)&_readBuffer;
-
- if (_worldSession)
- _authCrypt.DecryptRecv((uint8*)header, sizeof(ClientPktHeader));
+ _authCrypt.DecryptRecv(GetReadBuffer(), sizeof(ClientPktHeader));
- EndianConvertReverse(header->size);
- EndianConvert(header->cmd);
+ ClientPktHeader* header = reinterpret_cast<ClientPktHeader*>(GetReadBuffer());
+ EndianConvertReverse(header->size);
+ EndianConvert(header->cmd);
- AsyncReadData(header->size - sizeof(header->cmd));
- }
- else
- {
- // _socket.is_open() till returns true even after calling close()
- CloseSocket();
- }
- });
+ AsyncReadData(header->size - sizeof(header->cmd), sizeof(ClientPktHeader));
+ }
+ else
+ CloseSocket();
}
-void WorldSocket::AsyncReadData(size_t dataSize)
+void WorldSocket::ReadDataHandler(boost::system::error_code error, size_t transferedBytes)
{
- auto self(shared_from_this());
- _socket.async_read_some(boost::asio::buffer(&_readBuffer[sizeof(ClientPktHeader)], dataSize), [this, dataSize, self](boost::system::error_code error, size_t transferedBytes)
- {
- if (!error && transferedBytes == dataSize)
- {
- ClientPktHeader* header = (ClientPktHeader*)&_readBuffer;
+ ClientPktHeader* header = reinterpret_cast<ClientPktHeader*>(GetReadBuffer());
- header->size -= sizeof(header->cmd);
+ if (!error && transferedBytes == (header->size - sizeof(header->cmd)))
+ {
+ header->size -= sizeof(header->cmd);
- Opcodes opcode = PacketFilter::DropHighBytes(Opcodes(header->cmd));
+ Opcodes opcode = PacketFilter::DropHighBytes(Opcodes(header->cmd));
- std::string opcodeName = GetOpcodeNameForLogging(opcode);
+ std::string opcodeName = GetOpcodeNameForLogging(opcode);
- WorldPacket packet(opcode, header->size);
+ WorldPacket packet(opcode, header->size);
- if (header->size > 0)
- {
- packet.resize(header->size);
+ if (header->size > 0)
+ {
+ packet.resize(header->size);
- std::memcpy(packet.contents(), &_readBuffer[sizeof(ClientPktHeader)], header->size);
- }
+ std::memcpy(packet.contents(), &(GetReadBuffer()[sizeof(ClientPktHeader)]), header->size);
+ }
- if (sPacketLog->CanLogPacket())
- sPacketLog->LogPacket(packet, CLIENT_TO_SERVER);
+ if (sPacketLog->CanLogPacket())
+ sPacketLog->LogPacket(packet, CLIENT_TO_SERVER);
- TC_LOG_TRACE("network.opcode", "C->S: %s %s", (_worldSession ? _worldSession->GetPlayerInfo() : GetRemoteIpAddress()).c_str(), GetOpcodeNameForLogging(opcode).c_str());
+ TC_LOG_TRACE("network.opcode", "C->S: %s %s", (_worldSession ? _worldSession->GetPlayerInfo() : GetRemoteIpAddress().to_string()).c_str(), GetOpcodeNameForLogging(opcode).c_str());
- switch (opcode)
- {
- case CMSG_PING:
- HandlePing(packet);
- break;
- case CMSG_AUTH_SESSION:
- if (_worldSession)
- {
- TC_LOG_ERROR("network", "WorldSocket::ProcessIncoming: received duplicate CMSG_AUTH_SESSION from %s", _worldSession->GetPlayerInfo().c_str());
- break;
- }
-
- sScriptMgr->OnPacketReceive(shared_from_this(), packet);
- HandleAuthSession(packet);
- break;
- case CMSG_KEEP_ALIVE:
- TC_LOG_DEBUG("network", "%s", opcodeName.c_str());
- sScriptMgr->OnPacketReceive(shared_from_this(), packet);
- break;
- case CMSG_LOG_DISCONNECT:
- packet.rfinish(); // contains uint32 disconnectReason;
- TC_LOG_DEBUG("network", "%s", opcodeName.c_str());
- sScriptMgr->OnPacketReceive(shared_from_this(), packet);
- return;
- // not an opcode, client sends string "WORLD OF WARCRAFT CONNECTION - CLIENT TO SERVER" without opcode
- // first 4 bytes become the opcode (2 dropped)
- case MSG_VERIFY_CONNECTIVITY:
+ switch (opcode)
+ {
+ case CMSG_PING:
+ HandlePing(packet);
+ break;
+ case CMSG_AUTH_SESSION:
+ if (_worldSession)
{
- TC_LOG_DEBUG("network", "%s", opcodeName.c_str());
- sScriptMgr->OnPacketReceive(shared_from_this(), packet);
- std::string str;
- packet >> str;
- if (str != "D OF WARCRAFT CONNECTION - CLIENT TO SERVER")
- {
- _socket.close();
- break;
- }
-
- HandleSendAuthSession();
+ TC_LOG_ERROR("network", "WorldSocket::ProcessIncoming: received duplicate CMSG_AUTH_SESSION from %s", _worldSession->GetPlayerInfo().c_str());
break;
}
- case CMSG_ENABLE_NAGLE:
+
+ sScriptMgr->OnPacketReceive(shared_from_this(), packet);
+ HandleAuthSession(packet);
+ break;
+ case CMSG_KEEP_ALIVE:
+ TC_LOG_DEBUG("network", "%s", opcodeName.c_str());
+ sScriptMgr->OnPacketReceive(shared_from_this(), packet);
+ break;
+ case CMSG_LOG_DISCONNECT:
+ packet.rfinish(); // contains uint32 disconnectReason;
+ TC_LOG_DEBUG("network", "%s", opcodeName.c_str());
+ sScriptMgr->OnPacketReceive(shared_from_this(), packet);
+ return;
+ // not an opcode, client sends string "WORLD OF WARCRAFT CONNECTION - CLIENT TO SERVER" without opcode
+ // first 4 bytes become the opcode (2 dropped)
+ case MSG_VERIFY_CONNECTIVITY:
+ {
+ TC_LOG_DEBUG("network", "%s", opcodeName.c_str());
+ sScriptMgr->OnPacketReceive(shared_from_this(), packet);
+ std::string str;
+ packet >> str;
+ if (str != "D OF WARCRAFT CONNECTION - CLIENT TO SERVER")
{
- TC_LOG_DEBUG("network", "%s", opcodeName.c_str());
- sScriptMgr->OnPacketReceive(shared_from_this(), packet);
- if (_worldSession)
- _worldSession->HandleEnableNagleAlgorithm();
+ CloseSocket();
break;
}
- default:
+
+ HandleSendAuthSession();
+ break;
+ }
+ case CMSG_ENABLE_NAGLE:
+ {
+ TC_LOG_DEBUG("network", "%s", opcodeName.c_str());
+ sScriptMgr->OnPacketReceive(shared_from_this(), packet);
+ if (_worldSession)
+ _worldSession->HandleEnableNagleAlgorithm();
+ break;
+ }
+ default:
+ {
+ if (!_worldSession)
{
- if (!_worldSession)
- {
- TC_LOG_ERROR("network.opcode", "ProcessIncoming: Client not authed opcode = %u", uint32(opcode));
- break;
- }
-
- // Our Idle timer will reset on any non PING opcodes.
- // Catches people idling on the login screen and any lingering ingame connections.
- _worldSession->ResetTimeOutTime();
-
- // Copy the packet to the heap before enqueuing
- _worldSession->QueuePacket(new WorldPacket(packet));
+ TC_LOG_ERROR("network.opcode", "ProcessIncoming: Client not authed opcode = %u", uint32(opcode));
break;
}
- }
- AsyncReadHeader();
- }
- else
- {
- // _socket.is_open() till returns true even after calling close()
- CloseSocket();
+ // Our Idle timer will reset on any non PING opcodes.
+ // Catches people idling on the login screen and any lingering ingame connections.
+ _worldSession->ResetTimeOutTime();
+
+ // Copy the packet to the heap before enqueuing
+ _worldSession->QueuePacket(new WorldPacket(packet));
+ break;
+ }
}
- });
+
+ AsyncReadHeader();
+ }
+ else
+ CloseSocket();
}
void WorldSocket::AsyncWrite(WorldPacket const& packet)
@@ -207,7 +188,7 @@ void WorldSocket::AsyncWrite(WorldPacket const& packet)
pkt = &buff;
}
- TC_LOG_TRACE("network.opcode", "S->C: %s %s", (_worldSession ? _worldSession->GetPlayerInfo() : GetRemoteIpAddress()).c_str(), GetOpcodeNameForLogging(pkt->GetOpcode()).c_str());
+ TC_LOG_TRACE("network.opcode", "S->C: %s %s", (_worldSession ? _worldSession->GetPlayerInfo() : GetRemoteIpAddress().to_string()).c_str(), GetOpcodeNameForLogging(pkt->GetOpcode()).c_str());
ServerPktHeader header(pkt->size() + 2, pkt->GetOpcode());
@@ -228,25 +209,6 @@ void WorldSocket::AsyncWrite(WorldPacket const& packet)
AsyncWrite(_writeQueue.front());
}
-void WorldSocket::AsyncWrite(std::vector<uint8> const& data)
-{
- auto self(shared_from_this());
- boost::asio::async_write(_socket, boost::asio::buffer(data), [this, self](boost::system::error_code error, std::size_t /*length*/)
- {
- if (!error)
- {
- std::lock_guard<std::mutex> deleteGuard(_writeLock);
-
- _writeQueue.pop();
-
- if (!_writeQueue.empty())
- AsyncWrite(_writeQueue.front());
- }
- else
- CloseSocket();
- });
-}
-
void WorldSocket::HandleAuthSession(WorldPacket& recvPacket)
{
uint8 digest[20];
@@ -306,7 +268,7 @@ void WorldSocket::HandleAuthSession(WorldPacket& recvPacket)
if (sWorld->IsClosed())
{
SendAuthResponseError(AUTH_REJECT);
- TC_LOG_ERROR("network", "WorldSocket::HandleAuthSession: World closed, denying client (%s).", GetRemoteIpAddress().c_str());
+ TC_LOG_ERROR("network", "WorldSocket::HandleAuthSession: World closed, denying client (%s).", GetRemoteIpAddress().to_string().c_str());
return;
}
@@ -347,7 +309,7 @@ void WorldSocket::HandleAuthSession(WorldPacket& recvPacket)
expansion = world_expansion;
// For hook purposes, we get Remoteaddress at this point.
- std::string address = GetRemoteIpAddress();
+ std::string address = GetRemoteIpAddress().to_string();
// As we don't know if attempted login process by ip works, we update last_attempt_ip right away
stmt = LoginDatabase.GetPreparedStatement(LOGIN_UPD_LAST_ATTEMPT_IP);
@@ -550,7 +512,7 @@ void WorldSocket::HandlePing(WorldPacket& recvPacket)
if (_worldSession && !_worldSession->HasPermission(rbac::RBAC_PERM_SKIP_CHECK_OVERSPEED_PING))
{
TC_LOG_ERROR("network", "WorldSocket::HandlePing: %s kicked for over-speed pings (address: %s)",
- _worldSession->GetPlayerInfo().c_str(), GetRemoteIpAddress().c_str());
+ _worldSession->GetPlayerInfo().c_str(), GetRemoteIpAddress().to_string().c_str());
CloseSocket();
return;
@@ -568,8 +530,7 @@ void WorldSocket::HandlePing(WorldPacket& recvPacket)
}
else
{
- TC_LOG_ERROR("network", "WorldSocket::HandlePing: peer sent CMSG_PING, but is not authenticated or got recently kicked, address = %s",
- GetRemoteIpAddress().c_str());
+ TC_LOG_ERROR("network", "WorldSocket::HandlePing: peer sent CMSG_PING, but is not authenticated or got recently kicked, address = %s", GetRemoteIpAddress().to_string().c_str());
CloseSocket();
return;
@@ -579,13 +540,3 @@ void WorldSocket::HandlePing(WorldPacket& recvPacket)
packet << ping;
return AsyncWrite(packet);
}
-
-void WorldSocket::CloseSocket()
-{
- boost::system::error_code socketError;
- _socket.close(socketError);
- if (socketError)
- TC_LOG_DEBUG("network", "WorldSocket::CloseSocket: Player '%s' (%s) errored when closing socket: %i (%s)",
- _worldSession ? _worldSession->GetPlayerInfo().c_str() : "unknown", GetRemoteIpAddress().c_str(),
- socketError.value(), socketError.message().c_str());
-}
diff --git a/src/server/game/Server/WorldSocket.h b/src/server/game/Server/WorldSocket.h
index 085ee98b00d..ca50b46efb0 100644
--- a/src/server/game/Server/WorldSocket.h
+++ b/src/server/game/Server/WorldSocket.h
@@ -21,14 +21,12 @@
#include "Common.h"
#include "WorldPacketCrypt.h"
+#include "Socket.h"
#include "Util.h"
#include "WorldPacket.h"
#include "WorldSession.h"
-#include <memory>
#include <chrono>
-#include <mutex>
#include <boost/asio/ip/tcp.hpp>
-#include <boost/asio/streambuf.hpp>
using boost::asio::ip::tcp;
@@ -42,7 +40,7 @@ struct ClientPktHeader
#pragma pack(pop)
-class WorldSocket : public std::enable_shared_from_this<WorldSocket>
+class WorldSocket : public Socket<WorldSocket>
{
public:
WorldSocket(tcp::socket&& socket);
@@ -50,15 +48,14 @@ public:
WorldSocket(WorldSocket const& right) = delete;
WorldSocket& operator=(WorldSocket const& right) = delete;
- void Start();
-
- std::string GetRemoteIpAddress() const { return _socket.remote_endpoint().address().to_string(); };
- uint16 GetRemotePort() const { return _socket.remote_endpoint().port(); }
-
- void CloseSocket();
- bool IsOpen() const { return _socket.is_open(); }
+ void Start() override;
void AsyncWrite(WorldPacket const& packet);
+ using Socket<WorldSocket>::AsyncWrite;
+
+protected:
+ void ReadHeaderHandler(boost::system::error_code error, size_t transferedBytes) override;
+ void ReadDataHandler(boost::system::error_code error, size_t transferedBytes) override;
private:
void HandleSendAuthSession();
@@ -67,16 +64,6 @@ private:
void HandlePing(WorldPacket& recvPacket);
- void AsyncReadHeader();
- void AsyncReadData(size_t dataSize);
- void AsyncWrite(std::vector<uint8> const& data);
-
- tcp::socket _socket;
-
- char _readBuffer[4096];
- std::mutex _writeLock;
- std::queue<std::vector<uint8> > _writeQueue;
-
uint32 _authSeed;
WorldPacketCrypt _authCrypt;
diff --git a/src/server/game/World/World.cpp b/src/server/game/World/World.cpp
index e5dc9ba1a4c..14591db9eb6 100644
--- a/src/server/game/World/World.cpp
+++ b/src/server/game/World/World.cpp
@@ -2778,8 +2778,7 @@ void World::UpdateRealmCharCount(uint32 accountId)
{
PreparedStatement* stmt = CharacterDatabase.GetPreparedStatement(CHAR_SEL_CHARACTER_COUNT);
stmt->setUInt32(0, accountId);
- PreparedQueryResultFuture result = CharacterDatabase.AsyncQuery(stmt);
- m_realmCharCallbacks.push_back(std::move(result));
+ m_realmCharCallbacks.push_back(CharacterDatabase.AsyncQuery(stmt));
}
void World::_UpdateRealmCharCount(PreparedQueryResult resultCharCount)
diff --git a/src/server/scripts/Commands/cs_wp.cpp b/src/server/scripts/Commands/cs_wp.cpp
index b1a90cf6f2e..9b8f6aff992 100644
--- a/src/server/scripts/Commands/cs_wp.cpp
+++ b/src/server/scripts/Commands/cs_wp.cpp
@@ -546,7 +546,7 @@ public:
// Check
// Remember: "show" must also be the name of a column!
if ((show != "delay") && (show != "action") && (show != "action_chance")
- && (show != "move_flag") && (show != "del") && (show != "move")
+ && (show != "move_type") && (show != "del") && (show != "move")
)
{
return false;
diff --git a/src/server/shared/Database/DatabaseWorkerPool.h b/src/server/shared/Database/DatabaseWorkerPool.h
index a1ee6407fea..18797b6b12a 100644
--- a/src/server/shared/Database/DatabaseWorkerPool.h
+++ b/src/server/shared/Database/DatabaseWorkerPool.h
@@ -297,8 +297,10 @@ class DatabaseWorkerPool
QueryResultFuture AsyncQuery(const char* sql)
{
BasicStatementTask* task = new BasicStatementTask(sql, true);
+ // Store future result before enqueueing - task might get already processed and deleted before returning from this method
+ QueryResultFuture result = task->GetFuture();
Enqueue(task);
- return task->GetFuture(); //! Actual return value has no use yet
+ return result;
}
//! Enqueues a query in string format -with variable args- that will set the value of the QueryResultFuture return object as soon as the query is executed.
@@ -320,8 +322,10 @@ class DatabaseWorkerPool
PreparedQueryResultFuture AsyncQuery(PreparedStatement* stmt)
{
PreparedStatementTask* task = new PreparedStatementTask(stmt, true);
+ // Store future result before enqueueing - task might get already processed and deleted before returning from this method
+ PreparedQueryResultFuture result = task->GetFuture();
Enqueue(task);
- return task->GetFuture();
+ return result;
}
//! Enqueues a vector of SQL operations (can be both adhoc and prepared) that will set the value of the QueryResultHolderFuture
@@ -331,8 +335,10 @@ class DatabaseWorkerPool
QueryResultHolderFuture DelayQueryHolder(SQLQueryHolder* holder)
{
SQLQueryHolderTask* task = new SQLQueryHolderTask(holder);
+ // Store future result before enqueueing - task might get already processed and deleted before returning from this method
+ QueryResultHolderFuture result = task->GetFuture();
Enqueue(task);
- return task->GetFuture();
+ return result;
}
/**
diff --git a/src/server/shared/Database/Implementation/WorldDatabase.cpp b/src/server/shared/Database/Implementation/WorldDatabase.cpp
index 800f9eafb60..53f3b5519cd 100644
--- a/src/server/shared/Database/Implementation/WorldDatabase.cpp
+++ b/src/server/shared/Database/Implementation/WorldDatabase.cpp
@@ -51,12 +51,12 @@ void WorldDatabaseConnection::DoPrepareStatements()
PrepareStatement(WORLD_UPD_WAYPOINT_DATA_WPGUID, "UPDATE waypoint_data SET wpguid = ? WHERE id = ? and point = ?", CONNECTION_ASYNC);
PrepareStatement(WORLD_SEL_WAYPOINT_DATA_MAX_ID, "SELECT MAX(id) FROM waypoint_data", CONNECTION_SYNCH);
PrepareStatement(WORLD_SEL_WAYPOINT_DATA_MAX_POINT, "SELECT MAX(point) FROM waypoint_data WHERE id = ?", CONNECTION_SYNCH);
- PrepareStatement(WORLD_SEL_WAYPOINT_DATA_BY_ID, "SELECT point, position_x, position_y, position_z, orientation, move_flag, delay, action, action_chance FROM waypoint_data WHERE id = ? ORDER BY point", CONNECTION_SYNCH);
+ PrepareStatement(WORLD_SEL_WAYPOINT_DATA_BY_ID, "SELECT point, position_x, position_y, position_z, orientation, move_type, delay, action, action_chance FROM waypoint_data WHERE id = ? ORDER BY point", CONNECTION_SYNCH);
PrepareStatement(WORLD_SEL_WAYPOINT_DATA_POS_BY_ID, "SELECT point, position_x, position_y, position_z FROM waypoint_data WHERE id = ?", CONNECTION_SYNCH);
PrepareStatement(WORLD_SEL_WAYPOINT_DATA_POS_FIRST_BY_ID, "SELECT position_x, position_y, position_z FROM waypoint_data WHERE point = 1 AND id = ?", CONNECTION_SYNCH);
PrepareStatement(WORLD_SEL_WAYPOINT_DATA_POS_LAST_BY_ID, "SELECT position_x, position_y, position_z, orientation FROM waypoint_data WHERE id = ? ORDER BY point DESC LIMIT 1", CONNECTION_SYNCH);
PrepareStatement(WORLD_SEL_WAYPOINT_DATA_BY_WPGUID, "SELECT id, point FROM waypoint_data WHERE wpguid = ?", CONNECTION_SYNCH);
- PrepareStatement(WORLD_SEL_WAYPOINT_DATA_ALL_BY_WPGUID, "SELECT id, point, delay, move_flag, action, action_chance FROM waypoint_data WHERE wpguid = ?", CONNECTION_SYNCH);
+ PrepareStatement(WORLD_SEL_WAYPOINT_DATA_ALL_BY_WPGUID, "SELECT id, point, delay, move_type, action, action_chance FROM waypoint_data WHERE wpguid = ?", CONNECTION_SYNCH);
PrepareStatement(WORLD_UPD_WAYPOINT_DATA_ALL_WPGUID, "UPDATE waypoint_data SET wpguid = 0", CONNECTION_ASYNC);
PrepareStatement(WORLD_SEL_WAYPOINT_DATA_BY_POS, "SELECT id, point FROM waypoint_data WHERE (abs(position_x - ?) <= ?) and (abs(position_y - ?) <= ?) and (abs(position_z - ?) <= ?)", CONNECTION_SYNCH);
PrepareStatement(WORLD_SEL_WAYPOINT_DATA_WPGUID_BY_ID, "SELECT wpguid FROM waypoint_data WHERE id = ? and wpguid <> 0", CONNECTION_SYNCH);
diff --git a/src/server/shared/Networking/Socket.h b/src/server/shared/Networking/Socket.h
new file mode 100644
index 00000000000..676418c27a7
--- /dev/null
+++ b/src/server/shared/Networking/Socket.h
@@ -0,0 +1,109 @@
+/*
+ * Copyright (C) 2008-2014 TrinityCore <http://www.trinitycore.org/>
+ * Copyright (C) 2005-2009 MaNGOS <http://getmangos.com/>
+ *
+ * This program is free software; you can redistribute it and/or modify it
+ * under the terms of the GNU General Public License as published by the
+ * Free Software Foundation; either version 2 of the License, or (at your
+ * option) any later version.
+ *
+ * This program is distributed in the hope that it will be useful, but WITHOUT
+ * ANY WARRANTY; without even the implied warranty of MERCHANTABILITY or
+ * FITNESS FOR A PARTICULAR PURPOSE. See the GNU General Public License for
+ * more details.
+ *
+ * You should have received a copy of the GNU General Public License along
+ * with this program. If not, see <http://www.gnu.org/licenses/>.
+ */
+
+#ifndef __SOCKET_H__
+#define __SOCKET_H__
+
+#include "Define.h"
+#include "Log.h"
+#include <vector>
+#include <mutex>
+#include <queue>
+#include <memory>
+#include <functional>
+#include <boost/asio/ip/tcp.hpp>
+#include <boost/asio/write.hpp>
+
+using boost::asio::ip::tcp;
+
+template<class T>
+class Socket : public std::enable_shared_from_this<T>
+{
+public:
+ Socket(tcp::socket&& socket, std::size_t headerSize) : _socket(std::move(socket)), _headerSize(headerSize) { }
+
+ virtual void Start() = 0;
+
+ boost::asio::ip::address GetRemoteIpAddress() const { return _socket.remote_endpoint().address(); };
+ uint16 GetRemotePort() const { return _socket.remote_endpoint().port(); }
+
+ void AsyncReadHeader()
+ {
+ _socket.async_read_some(boost::asio::buffer(_readBuffer, _headerSize), std::bind(&Socket<T>::ReadHeaderHandlerInternal, this->shared_from_this(), std::placeholders::_1, std::placeholders::_2));
+ }
+
+ void AsyncReadData(std::size_t size, std::size_t bufferOffset)
+ {
+ _socket.async_read_some(boost::asio::buffer(&_readBuffer[bufferOffset], size), std::bind(&Socket<T>::ReadDataHandlerInternal, this->shared_from_this(), std::placeholders::_1, std::placeholders::_2));
+ }
+
+ void ReadData(std::size_t size, std::size_t bufferOffset)
+ {
+ _socket.read_some(boost::asio::buffer(&_readBuffer[bufferOffset], size));
+ }
+
+ void AsyncWrite(std::vector<uint8> const& data)
+ {
+ boost::asio::async_write(_socket, boost::asio::buffer(data), std::bind(&Socket<T>::WriteHandler, this->shared_from_this(), std::placeholders::_1, std::placeholders::_2));
+ }
+
+ bool IsOpen() const { return _socket.is_open(); }
+ void CloseSocket()
+ {
+ boost::system::error_code socketError;
+ _socket.close(socketError);
+ if (socketError)
+ TC_LOG_DEBUG("network", "Socket::CloseSocket: %s errored when closing socket: %i (%s)", GetRemoteIpAddress().to_string().c_str(), socketError.value(), socketError.message().c_str());
+ }
+
+ uint8* GetReadBuffer() { return _readBuffer; }
+
+protected:
+ virtual void ReadHeaderHandler(boost::system::error_code error, size_t transferedBytes) = 0;
+ virtual void ReadDataHandler(boost::system::error_code error, size_t transferedBytes) = 0;
+
+ std::mutex _writeLock;
+ std::queue<std::vector<uint8> > _writeQueue;
+
+private:
+ void ReadHeaderHandlerInternal(boost::system::error_code error, size_t transferedBytes) { ReadHeaderHandler(error, transferedBytes); }
+ void ReadDataHandlerInternal(boost::system::error_code error, size_t transferedBytes) { ReadDataHandler(error, transferedBytes); }
+
+ void WriteHandler(boost::system::error_code error, size_t /*transferedBytes*/)
+ {
+ if (!error)
+ {
+ std::lock_guard<std::mutex> deleteGuard(_writeLock);
+
+ _writeQueue.pop();
+
+ if (!_writeQueue.empty())
+ AsyncWrite(_writeQueue.front());
+ }
+ else
+ CloseSocket();
+ }
+
+ tcp::socket _socket;
+
+ uint8 _readBuffer[4096];
+
+ std::size_t _headerSize;
+};
+
+#endif // __SOCKET_H__