mirror of
https://github.com/TrinityCore/TrinityCore.git
synced 2026-01-16 07:30:42 +01:00
Merge branch 'battle.net' into 4.3.4
This commit is contained in:
6
contrib/Connection Patcher/App.config
Normal file
6
contrib/Connection Patcher/App.config
Normal file
@@ -0,0 +1,6 @@
|
||||
<?xml version="1.0" encoding="utf-8"?>
|
||||
<configuration>
|
||||
<startup>
|
||||
<supportedRuntime version="v4.0" sku=".NETFramework,Version=v4.0,Profile=Client"/>
|
||||
</startup>
|
||||
</configuration>
|
||||
69
contrib/Connection Patcher/Connection Patcher.csproj
Normal file
69
contrib/Connection Patcher/Connection Patcher.csproj
Normal file
@@ -0,0 +1,69 @@
|
||||
<?xml version="1.0" encoding="utf-8"?>
|
||||
<Project ToolsVersion="12.0" DefaultTargets="Build" xmlns="http://schemas.microsoft.com/developer/msbuild/2003">
|
||||
<Import Project="$(MSBuildExtensionsPath)\$(MSBuildToolsVersion)\Microsoft.Common.props" Condition="Exists('$(MSBuildExtensionsPath)\$(MSBuildToolsVersion)\Microsoft.Common.props')" />
|
||||
<PropertyGroup>
|
||||
<Configuration Condition=" '$(Configuration)' == '' ">Debug</Configuration>
|
||||
<Platform Condition=" '$(Platform)' == '' ">AnyCPU</Platform>
|
||||
<ProjectGuid>{137B1355-6A81-4A3A-A01E-93ABAA4FFFDB}</ProjectGuid>
|
||||
<OutputType>Exe</OutputType>
|
||||
<AppDesignerFolder>Properties</AppDesignerFolder>
|
||||
<RootNamespace>Connection_Patcher</RootNamespace>
|
||||
<AssemblyName>Connection Patcher</AssemblyName>
|
||||
<TargetFrameworkVersion>v4.0</TargetFrameworkVersion>
|
||||
<FileAlignment>512</FileAlignment>
|
||||
<TargetFrameworkProfile>Client</TargetFrameworkProfile>
|
||||
</PropertyGroup>
|
||||
<PropertyGroup Condition=" '$(Configuration)|$(Platform)' == 'Debug|AnyCPU' ">
|
||||
<PlatformTarget>AnyCPU</PlatformTarget>
|
||||
<DebugSymbols>true</DebugSymbols>
|
||||
<DebugType>full</DebugType>
|
||||
<Optimize>false</Optimize>
|
||||
<OutputPath>bin\Debug\</OutputPath>
|
||||
<DefineConstants>TRACE;DEBUG</DefineConstants>
|
||||
<ErrorReport>prompt</ErrorReport>
|
||||
<WarningLevel>4</WarningLevel>
|
||||
<GenerateSerializationAssemblies>Off</GenerateSerializationAssemblies>
|
||||
<RunCodeAnalysis>false</RunCodeAnalysis>
|
||||
</PropertyGroup>
|
||||
<PropertyGroup Condition=" '$(Configuration)|$(Platform)' == 'Release|AnyCPU' ">
|
||||
<PlatformTarget>AnyCPU</PlatformTarget>
|
||||
<DebugType>none</DebugType>
|
||||
<Optimize>true</Optimize>
|
||||
<OutputPath>bin\Release\</OutputPath>
|
||||
<DefineConstants>
|
||||
</DefineConstants>
|
||||
<ErrorReport>prompt</ErrorReport>
|
||||
<WarningLevel>4</WarningLevel>
|
||||
<GenerateSerializationAssemblies>Off</GenerateSerializationAssemblies>
|
||||
<UseVSHostingProcess>false</UseVSHostingProcess>
|
||||
</PropertyGroup>
|
||||
<PropertyGroup>
|
||||
<NoWin32Manifest>true</NoWin32Manifest>
|
||||
</PropertyGroup>
|
||||
<ItemGroup>
|
||||
<Reference Include="System" />
|
||||
</ItemGroup>
|
||||
<ItemGroup>
|
||||
<Compile Include="Constants\BinaryTypes.cs" />
|
||||
<Compile Include="Helper.cs" />
|
||||
<Compile Include="Offsets\Windows.cs" />
|
||||
<Compile Include="Patcher.cs" />
|
||||
<Compile Include="Patches\Mac.cs" />
|
||||
<Compile Include="Patches\Windows.cs" />
|
||||
<Compile Include="Patterns\Mac.cs" />
|
||||
<Compile Include="Patterns\Windows.cs" />
|
||||
<Compile Include="Program.cs" />
|
||||
<Compile Include="Properties\AssemblyInfo.cs" />
|
||||
</ItemGroup>
|
||||
<ItemGroup>
|
||||
<None Include="App.config" />
|
||||
</ItemGroup>
|
||||
<Import Project="$(MSBuildToolsPath)\Microsoft.CSharp.targets" />
|
||||
<!-- To modify your build process, add your task inside one of the targets below and uncomment it.
|
||||
Other similar extension points exist, see Microsoft.Common.targets.
|
||||
<Target Name="BeforeBuild">
|
||||
</Target>
|
||||
<Target Name="AfterBuild">
|
||||
</Target>
|
||||
-->
|
||||
</Project>
|
||||
22
contrib/Connection Patcher/Connection Patcher.sln
Normal file
22
contrib/Connection Patcher/Connection Patcher.sln
Normal file
@@ -0,0 +1,22 @@
|
||||
|
||||
Microsoft Visual Studio Solution File, Format Version 12.00
|
||||
# Visual Studio 2013
|
||||
VisualStudioVersion = 12.0.30110.0
|
||||
MinimumVisualStudioVersion = 10.0.40219.1
|
||||
Project("{FAE04EC0-301F-11D3-BF4B-00C04F79EFBC}") = "Connection Patcher", "Connection Patcher.csproj", "{137B1355-6A81-4A3A-A01E-93ABAA4FFFDB}"
|
||||
EndProject
|
||||
Global
|
||||
GlobalSection(SolutionConfigurationPlatforms) = preSolution
|
||||
Debug|Any CPU = Debug|Any CPU
|
||||
Release|Any CPU = Release|Any CPU
|
||||
EndGlobalSection
|
||||
GlobalSection(ProjectConfigurationPlatforms) = postSolution
|
||||
{137B1355-6A81-4A3A-A01E-93ABAA4FFFDB}.Debug|Any CPU.ActiveCfg = Debug|Any CPU
|
||||
{137B1355-6A81-4A3A-A01E-93ABAA4FFFDB}.Debug|Any CPU.Build.0 = Debug|Any CPU
|
||||
{137B1355-6A81-4A3A-A01E-93ABAA4FFFDB}.Release|Any CPU.ActiveCfg = Release|Any CPU
|
||||
{137B1355-6A81-4A3A-A01E-93ABAA4FFFDB}.Release|Any CPU.Build.0 = Release|Any CPU
|
||||
EndGlobalSection
|
||||
GlobalSection(SolutionProperties) = preSolution
|
||||
HideSolutionNode = FALSE
|
||||
EndGlobalSection
|
||||
EndGlobal
|
||||
29
contrib/Connection Patcher/Constants/BinaryTypes.cs
Normal file
29
contrib/Connection Patcher/Constants/BinaryTypes.cs
Normal file
@@ -0,0 +1,29 @@
|
||||
/*
|
||||
* Copyright (C) 2012-2014 Arctium Emulation <http://arctium.org>
|
||||
* Copyright (C) 2008-2014 TrinityCore <http://www.trinitycore.org/>
|
||||
*
|
||||
* 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 3 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/>.
|
||||
*/
|
||||
|
||||
namespace Connection_Patcher.Constants
|
||||
{
|
||||
enum BinaryTypes : uint
|
||||
{
|
||||
None = 0000000000,
|
||||
Pe32 = 0x0000014C,
|
||||
Pe64 = 0x00008664,
|
||||
Mach32 = 0xFEEDFACE,
|
||||
Mach64 = 0xFEEDFACF
|
||||
}
|
||||
}
|
||||
76
contrib/Connection Patcher/Helper.cs
Normal file
76
contrib/Connection Patcher/Helper.cs
Normal file
@@ -0,0 +1,76 @@
|
||||
/*
|
||||
* Copyright (C) 2012-2014 Arctium Emulation <http://arctium.org>
|
||||
* Copyright (C) 2008-2014 TrinityCore <http://www.trinitycore.org/>
|
||||
*
|
||||
* 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 3 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/>.
|
||||
*/
|
||||
|
||||
using Connection_Patcher.Constants;
|
||||
using System;
|
||||
using System.IO;
|
||||
using System.Security.Cryptography;
|
||||
|
||||
namespace Connection_Patcher
|
||||
{
|
||||
class Helper
|
||||
{
|
||||
public static BinaryTypes GetBinaryType(byte[] data)
|
||||
{
|
||||
BinaryTypes type = 0u;
|
||||
|
||||
using (var reader = new BinaryReader(new MemoryStream(data)))
|
||||
{
|
||||
var magic = (uint)reader.ReadUInt16();
|
||||
|
||||
// Check MS-DOS magic
|
||||
if (magic == 0x5A4D)
|
||||
{
|
||||
reader.BaseStream.Seek(0x3C, SeekOrigin.Begin);
|
||||
|
||||
// Read PE start offset
|
||||
var peOffset = reader.ReadUInt32();
|
||||
|
||||
reader.BaseStream.Seek(peOffset, SeekOrigin.Begin);
|
||||
|
||||
var peMagic = reader.ReadUInt32();
|
||||
|
||||
// Check PE magic
|
||||
if (peMagic != 0x4550)
|
||||
throw new NotSupportedException("Not a PE file!");
|
||||
|
||||
type = (BinaryTypes)reader.ReadUInt16();
|
||||
}
|
||||
else
|
||||
{
|
||||
reader.BaseStream.Seek(0, SeekOrigin.Begin);
|
||||
|
||||
type = (BinaryTypes)reader.ReadUInt32();
|
||||
}
|
||||
}
|
||||
|
||||
return type;
|
||||
}
|
||||
|
||||
public static string GetFileChecksum(byte[] data)
|
||||
{
|
||||
using (var stream = new BufferedStream(new MemoryStream(data), 1200000))
|
||||
{
|
||||
var sha256 = new SHA256Managed();
|
||||
var checksum = sha256.ComputeHash(stream);
|
||||
|
||||
return BitConverter.ToString(checksum).Replace("-", "").ToLower();
|
||||
}
|
||||
}
|
||||
}
|
||||
}
|
||||
40
contrib/Connection Patcher/Offsets/Windows.cs
Normal file
40
contrib/Connection Patcher/Offsets/Windows.cs
Normal file
@@ -0,0 +1,40 @@
|
||||
/*
|
||||
* Copyright (C) 2008-2014 TrinityCore <http://www.trinitycore.org/>
|
||||
*
|
||||
* 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 3 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/>.
|
||||
*/
|
||||
|
||||
namespace Connection_Patcher.Offsets
|
||||
{
|
||||
static class Windows
|
||||
{
|
||||
public static class x86
|
||||
{
|
||||
public static readonly long BNet = 0xD3259;
|
||||
public static readonly long Send = 0x889CA;
|
||||
public static readonly long Recv = 0x86EEE;
|
||||
public static readonly long Signature = 0x20B79;
|
||||
public static readonly long RealmList = 0x228D6C;
|
||||
}
|
||||
|
||||
public static class x64
|
||||
{
|
||||
public static readonly long BNet = 0;
|
||||
public static readonly long Send = 0xAAB6B;
|
||||
public static readonly long Recv = 0xA9FA3;
|
||||
public static readonly long Signature = 0;
|
||||
public static readonly long RealmList = 0x2BB33C;
|
||||
}
|
||||
}
|
||||
}
|
||||
130
contrib/Connection Patcher/Patcher.cs
Normal file
130
contrib/Connection Patcher/Patcher.cs
Normal file
@@ -0,0 +1,130 @@
|
||||
/*
|
||||
* Copyright (C) 2012-2014 Arctium Emulation <http://arctium.org>
|
||||
* Copyright (C) 2008-2014 TrinityCore <http://www.trinitycore.org/>
|
||||
*
|
||||
* 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 3 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/>.
|
||||
*/
|
||||
|
||||
using Connection_Patcher.Constants;
|
||||
using System;
|
||||
using System.IO;
|
||||
|
||||
namespace Connection_Patcher
|
||||
{
|
||||
class Patcher : IDisposable
|
||||
{
|
||||
public string Binary { get; set; }
|
||||
public bool Initialized { get; private set; }
|
||||
public BinaryTypes Type { get; private set; }
|
||||
|
||||
public byte[] binary;
|
||||
bool success;
|
||||
|
||||
public Patcher(string file)
|
||||
{
|
||||
Initialized = false;
|
||||
success = false;
|
||||
|
||||
using (var stream = new MemoryStream(File.ReadAllBytes(file)))
|
||||
{
|
||||
Binary = file;
|
||||
binary = stream.ToArray();
|
||||
|
||||
if (binary != null)
|
||||
{
|
||||
Type = Helper.GetBinaryType(binary);
|
||||
|
||||
Initialized = true;
|
||||
}
|
||||
}
|
||||
}
|
||||
|
||||
public void Patch(byte[] bytes, byte[] pattern, long address = 0)
|
||||
{
|
||||
if (Initialized && (address != 0 || binary.Length >= pattern.Length))
|
||||
{
|
||||
var offset = pattern == null ? address : SearchOffset(pattern);
|
||||
Console.WriteLine("Found offset {0}", offset);
|
||||
|
||||
if (offset != 0 && binary.Length >= bytes.Length)
|
||||
{
|
||||
try
|
||||
{
|
||||
for (int i = 0; i < bytes.Length; i++)
|
||||
binary[offset + i] = bytes[i];
|
||||
}
|
||||
catch (Exception ex)
|
||||
{
|
||||
throw new NotSupportedException(ex.Message);
|
||||
}
|
||||
}
|
||||
}
|
||||
}
|
||||
|
||||
long SearchOffset(byte[] pattern)
|
||||
{
|
||||
var matches = 0;
|
||||
|
||||
for (long i = 0; i < binary.Length; i++)
|
||||
{
|
||||
matches = 0;
|
||||
|
||||
for (int j = 0; j < pattern.Length; j++)
|
||||
{
|
||||
if (pattern.Length > (binary.Length - i))
|
||||
return 0;
|
||||
|
||||
if (pattern[j] == 0)
|
||||
{
|
||||
matches++;
|
||||
continue;
|
||||
}
|
||||
|
||||
if (binary[i + j] != pattern[j])
|
||||
break;
|
||||
|
||||
matches++;
|
||||
}
|
||||
|
||||
if (matches == pattern.Length)
|
||||
return i;
|
||||
}
|
||||
|
||||
return 0;
|
||||
}
|
||||
|
||||
public void Finish()
|
||||
{
|
||||
success = true;
|
||||
}
|
||||
|
||||
public void Dispose()
|
||||
{
|
||||
try
|
||||
{
|
||||
if (File.Exists(Binary))
|
||||
File.Delete(Binary);
|
||||
|
||||
if (success)
|
||||
File.WriteAllBytes(Binary, binary);
|
||||
}
|
||||
catch (UnauthorizedAccessException)
|
||||
{
|
||||
|
||||
}
|
||||
|
||||
binary = null;
|
||||
}
|
||||
}
|
||||
}
|
||||
44
contrib/Connection Patcher/Patches/Mac.cs
Normal file
44
contrib/Connection Patcher/Patches/Mac.cs
Normal file
@@ -0,0 +1,44 @@
|
||||
/*
|
||||
* Copyright (C) 2012-2014 Arctium Emulation <http://arctium.org>
|
||||
* Copyright (C) 2008-2014 TrinityCore <http://www.trinitycore.org/>
|
||||
*
|
||||
* 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 3 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/>.
|
||||
*/
|
||||
|
||||
namespace Connection_Patcher.Patches
|
||||
{
|
||||
class Mac
|
||||
{
|
||||
public static class x86
|
||||
{
|
||||
public static byte[] BNet = { };
|
||||
public static byte[] Send = { };
|
||||
public static byte[] Recv = { };
|
||||
public static byte[] Password = { 0x0F, 0x85 };
|
||||
public static byte[] Signature = { };
|
||||
}
|
||||
|
||||
public static class x64
|
||||
{
|
||||
//public static byte[] BNet = { 0xB8, 0xD5, 0xF8, 0x7F, 0x82, 0x89, 0x47, 0x0C, 0x5D, 0xC3, 0x90, 0x90, 0x90 };
|
||||
public static byte[] BNet = { };
|
||||
//public static byte[] Send = { 0x90, 0x31, 0xDB };
|
||||
public static byte[] Send = { };
|
||||
public static byte[] Recv = { };
|
||||
public static byte[] Password = { 0x0F, 0x85 };
|
||||
//public static byte[] Signature = { 0x45, 0x31, 0xED, 0x4D, 0x89, 0xFC, 0x90, 0x90, 0x90, 0x90, 0x90, 0x90, 0x90, 0xEB };
|
||||
public static byte[] Signature = { };
|
||||
}
|
||||
}
|
||||
}
|
||||
46
contrib/Connection Patcher/Patches/Windows.cs
Normal file
46
contrib/Connection Patcher/Patches/Windows.cs
Normal file
@@ -0,0 +1,46 @@
|
||||
/*
|
||||
* Copyright (C) 2012-2014 Arctium Emulation <http://arctium.org>
|
||||
* Copyright (C) 2008-2014 TrinityCore <http://www.trinitycore.org/>
|
||||
*
|
||||
* 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 3 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/>.
|
||||
*/
|
||||
|
||||
namespace Connection_Patcher.Patches
|
||||
{
|
||||
class Windows
|
||||
{
|
||||
public static class x86
|
||||
{
|
||||
public static byte[] BNet = { 0x89, 0x48, 0x08, 0xC7, 0x40, 0x0C, 0xD5, 0xF8, 0x7F, 0x82, 0x90 };
|
||||
public static byte[] Send = { 0xBA, 0x00, 0x00, 0x00, 0x00, 0x90, 0xEB };
|
||||
public static byte[] Recv = { 0xB8, 0x00, 0x00, 0x00, 0x00 };
|
||||
public static byte[] Password = { 0x75 };
|
||||
public static byte[] Signature = { 0x90, 0x90, 0x90, 0x90, 0x90, 0x90, 0x90, 0x90, 0xE9 };
|
||||
public static byte[] RealmList = { 0x08 };
|
||||
public static byte[] RealmListBn = { 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00 };
|
||||
}
|
||||
|
||||
public static class x64
|
||||
{
|
||||
//public static byte[] BNet = { 0xB8, 0xD5, 0xF8, 0x7F, 0x82, 0x89, 0x41, 0x0C, 0x48, 0x8B, 0xC1, 0xC3 };
|
||||
public static byte[] BNet = { };
|
||||
public static byte[] Send = { 0x45, 0x33, 0xED, 0x90, 0x90, 0x90 };
|
||||
public static byte[] Recv = { 0xB8, 0x00, 0x00, 0x00, 0x00, 0x90 };
|
||||
public static byte[] Password = { 0x75 };
|
||||
public static byte[] RealmList = { 0x4C, 0x8B, 0xEA };
|
||||
//public static byte[] Signature = { 0x90, 0x90, 0x90, 0x90, 0x90, 0x90, 0x90, 0x90, 0xE9 };
|
||||
public static byte[] Signature = { };
|
||||
}
|
||||
}
|
||||
}
|
||||
33
contrib/Connection Patcher/Patterns/Mac.cs
Normal file
33
contrib/Connection Patcher/Patterns/Mac.cs
Normal file
@@ -0,0 +1,33 @@
|
||||
/*
|
||||
* Copyright (C) 2012-2014 Arctium Emulation <http://arctium.org>
|
||||
* Copyright (C) 2008-2014 TrinityCore <http://www.trinitycore.org/>
|
||||
*
|
||||
* 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 3 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/>.
|
||||
*/
|
||||
|
||||
namespace Connection_Patcher.Patterns
|
||||
{
|
||||
class Mac
|
||||
{
|
||||
public static class x86
|
||||
{
|
||||
public static byte[] Password = { 0x0F, 0x84, 0xE3, 0x00, 0x00, 0x00, 0x8B, 0x03, 0x8B, 0x40, 0x04 };
|
||||
}
|
||||
|
||||
public static class x64
|
||||
{
|
||||
public static byte[] Password = { 0x0F, 0x84, 0x00, 0xFF, 0xFF, 0xFF, 0x49, 0x8B, 0x45, 0x00, 0xB9, 0x40 };
|
||||
}
|
||||
}
|
||||
}
|
||||
34
contrib/Connection Patcher/Patterns/Windows.cs
Normal file
34
contrib/Connection Patcher/Patterns/Windows.cs
Normal file
@@ -0,0 +1,34 @@
|
||||
/*
|
||||
* Copyright (C) 2012-2014 Arctium Emulation <http://arctium.org>
|
||||
* Copyright (C) 2008-2014 TrinityCore <http://www.trinitycore.org/>
|
||||
*
|
||||
* 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 3 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/>.
|
||||
*/
|
||||
|
||||
namespace Connection_Patcher.Patterns
|
||||
{
|
||||
class Windows
|
||||
{
|
||||
public static class x86
|
||||
{
|
||||
public static byte[] Password = { 0x74, 0x89, 0x8B, 0x16, 0x8B, 0x42, 0x04 };
|
||||
public static byte[] RealmListBn = { 0x2E, 0x6C, 0x6F, 0x67, 0x6F, 0x6E, 0x2E, 0x62, 0x61, 0x74, 0x74, 0x6C, 0x65, 0x2E, 0x6E, 0x65, 0x74 };
|
||||
}
|
||||
|
||||
public static class x64
|
||||
{
|
||||
public static byte[] Password = { 0x74, 0x84, 0x48, 0x8B, 0x03 };
|
||||
}
|
||||
}
|
||||
}
|
||||
196
contrib/Connection Patcher/Program.cs
Normal file
196
contrib/Connection Patcher/Program.cs
Normal file
@@ -0,0 +1,196 @@
|
||||
/*
|
||||
* Copyright (C) 2012-2014 Arctium Emulation <http://arctium.org>
|
||||
* Copyright (C) 2008-2014 TrinityCore <http://www.trinitycore.org/>
|
||||
*
|
||||
* 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 3 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/>.
|
||||
*/
|
||||
|
||||
using Connection_Patcher.Constants;
|
||||
using System;
|
||||
using System.IO;
|
||||
using System.Net;
|
||||
using System.Text;
|
||||
using System.Threading;
|
||||
|
||||
namespace Connection_Patcher
|
||||
{
|
||||
class Program
|
||||
{
|
||||
static void Main(string[] args)
|
||||
{
|
||||
if (args.Length >= 1)
|
||||
{
|
||||
Console.ForegroundColor = ConsoleColor.Cyan;
|
||||
|
||||
Console.WriteLine("Client Connection Patcher");
|
||||
Console.WriteLine("Press Enter to patch...");
|
||||
|
||||
Console.ReadKey(true);
|
||||
|
||||
var commonAppData = Environment.GetFolderPath(Environment.SpecialFolder.CommonApplicationData);
|
||||
var modulePath = "";
|
||||
var moduleFile = "";
|
||||
|
||||
// Let's use Win32 as default module
|
||||
var patchSend = Patches.Windows.x86.Send;
|
||||
var offsetSend = Offsets.Windows.x86.Send;
|
||||
var patchRecv = Patches.Windows.x86.Recv;
|
||||
var offsetRecv = Offsets.Windows.x86.Recv;
|
||||
var patchBNet = Patches.Windows.x86.BNet;
|
||||
var offsetBNet = Offsets.Windows.x86.BNet;
|
||||
var patchSignature = Patches.Windows.x86.Signature;
|
||||
var offsetSignature = Offsets.Windows.x86.Signature;
|
||||
var fileName = args[0].Replace(".exe", "_Patched.exe");
|
||||
var battleNetFileName = args[0].Replace("Wow.exe", "Battle.net.dll");
|
||||
var modulePatch = Patches.Windows.x86.Password;
|
||||
var modulePattern = Patterns.Windows.x86.Password;
|
||||
var realmListPatch = Patches.Windows.x86.RealmList;
|
||||
var realmListoffset = Offsets.Windows.x86.RealmList;
|
||||
var realmListBnPatch = Patches.Windows.x86.RealmListBn;
|
||||
var realmListBnPattern = Patterns.Windows.x86.RealmListBn;
|
||||
|
||||
Console.ForegroundColor = ConsoleColor.White;
|
||||
Console.Write("Creating patched binaries for ");
|
||||
|
||||
using (var patcher = new Patcher(args[0]))
|
||||
{
|
||||
switch (patcher.Type)
|
||||
{
|
||||
case BinaryTypes.Pe32:
|
||||
Console.WriteLine("Win32 client...");
|
||||
modulePath = commonAppData + "/Blizzard Entertainment/Battle.net/Cache/";
|
||||
moduleFile = "8f52906a2c85b416a595702251570f96d3522f39237603115f2f1ab24962043c.auth";
|
||||
break;
|
||||
//case BinaryTypes.Pe64:
|
||||
// Console.WriteLine("Win64 client...");
|
||||
// fileName = patcher.Binary.Replace(".exe", "") + "_Patched.exe";
|
||||
|
||||
// modulePath = commonAppData + "/Blizzard Entertainment/Battle.net/Cache/";
|
||||
// moduleFile = "0a3afee2cade3a0e8b458c4b4660104cac7fc50e2ca9bef0d708942e77f15c1d.auth";
|
||||
// break;
|
||||
//case BinaryTypes.Mach32:
|
||||
// break;
|
||||
//case BinaryTypes.Mach64:
|
||||
// Console.WriteLine("Mc64 client...");
|
||||
// patchBNet = Patches.Mac.x64.BNet;
|
||||
// patternBNet = Patterns.Mac.x64.BNet;
|
||||
// patchSend = Patches.Mac.x64.Send;
|
||||
// patternSend = Patterns.Mac.x64.Send;
|
||||
// patchSignature = Patches.Mac.x64.Signature;
|
||||
// patternSignature = Patterns.Mac.x64.Signature;
|
||||
// fileName = patcher.Binary + " Patched";
|
||||
|
||||
// modulePath = "/Users/Shared/Blizzard/Battle.net/Cache/";
|
||||
// moduleFile = "97eeb2e28e9e56ed6a22d09f44e2ff43c93315e006bbad43bafc0defaa6f50ae.auth";
|
||||
// modulePatch = Patches.Mac.x64.Password;
|
||||
// modulePattern = Patterns.Mac.x64.Password;
|
||||
// break;
|
||||
default:
|
||||
throw new NotSupportedException("Type: " + patcher.Type + " not supported!");
|
||||
}
|
||||
|
||||
if (!File.Exists(battleNetFileName + "_backup"))
|
||||
{
|
||||
File.Copy(battleNetFileName, battleNetFileName + "_backup");
|
||||
File.SetAttributes(battleNetFileName + "_backup", File.GetAttributes(battleNetFileName + "_backup") | FileAttributes.ReadOnly);
|
||||
}
|
||||
|
||||
using (var bnpatcher = new Patcher(battleNetFileName))
|
||||
{
|
||||
bnpatcher.Patch(patchBNet, null, offsetBNet);
|
||||
bnpatcher.Patch(patchSignature, null, offsetSignature);
|
||||
bnpatcher.Patch(realmListBnPatch, realmListBnPattern);
|
||||
bnpatcher.Finish();
|
||||
}
|
||||
|
||||
patcher.Patch(patchSend, null, offsetSend);
|
||||
patcher.Patch(patchRecv, null, offsetRecv);
|
||||
patcher.Patch(realmListPatch, null, realmListoffset);
|
||||
|
||||
patcher.Binary = fileName;
|
||||
|
||||
patcher.Finish();
|
||||
|
||||
Console.ForegroundColor = ConsoleColor.Green;
|
||||
Console.WriteLine("Patching done.");
|
||||
|
||||
CreateModule(moduleFile, modulePath, modulePatch, modulePattern);
|
||||
|
||||
Console.ForegroundColor = ConsoleColor.Green;
|
||||
Console.WriteLine("Successfully created your patched binaries.");
|
||||
}
|
||||
}
|
||||
else
|
||||
{
|
||||
Console.ForegroundColor = ConsoleColor.Red;
|
||||
Console.WriteLine("Wrong number of arguments: Missing client file.");
|
||||
}
|
||||
|
||||
Console.ForegroundColor = ConsoleColor.Gray;
|
||||
Thread.Sleep(5000);
|
||||
Environment.Exit(0);
|
||||
}
|
||||
|
||||
static void CreateModule(string moduleName, string path, byte[] patches, byte[] patterns)
|
||||
{
|
||||
var modulePath = path + moduleName[0] + moduleName[1] + "/" + moduleName[2] + moduleName[3];
|
||||
var module = modulePath + "/" + moduleName;
|
||||
|
||||
if (!File.Exists(module))
|
||||
{
|
||||
Console.ForegroundColor = ConsoleColor.White;
|
||||
Console.WriteLine("Base module doesn't exist, downloading it...");
|
||||
|
||||
if (!Directory.Exists(modulePath))
|
||||
Directory.CreateDirectory(modulePath);
|
||||
|
||||
var webClient = new WebClient();
|
||||
|
||||
webClient.DownloadFileCompleted += (o, e) => PatchModule(module, path, patches, patterns);
|
||||
webClient.DownloadFileAsync(new Uri("http://xx.depot.battle.net:1119/" + moduleName), module);
|
||||
|
||||
Console.ForegroundColor = ConsoleColor.Green;
|
||||
Console.WriteLine("Done.");
|
||||
}
|
||||
else
|
||||
PatchModule(module, path, patches, patterns);
|
||||
}
|
||||
|
||||
static void PatchModule(string file, string path, byte[] patches, byte[] pattern)
|
||||
{
|
||||
Console.ForegroundColor = ConsoleColor.White;
|
||||
Console.WriteLine("Patching module...");
|
||||
|
||||
using (var patcher2 = new Patcher(file))
|
||||
{
|
||||
patcher2.Patch(patches, pattern);
|
||||
|
||||
var moduleName = Helper.GetFileChecksum(patcher2.binary) + ".auth";
|
||||
var modulePath = path + moduleName[0] + moduleName[1] + "/" + moduleName[2] + moduleName[3];
|
||||
|
||||
if (!Directory.Exists(modulePath))
|
||||
Directory.CreateDirectory(modulePath);
|
||||
|
||||
patcher2.Binary = modulePath + "/" + moduleName;
|
||||
|
||||
patcher2.Finish();
|
||||
}
|
||||
|
||||
Console.ForegroundColor = ConsoleColor.Green;
|
||||
Console.WriteLine("Patching module finished.");
|
||||
|
||||
Console.ForegroundColor = ConsoleColor.Gray;
|
||||
}
|
||||
}
|
||||
}
|
||||
36
contrib/Connection Patcher/Properties/AssemblyInfo.cs
Normal file
36
contrib/Connection Patcher/Properties/AssemblyInfo.cs
Normal file
@@ -0,0 +1,36 @@
|
||||
using System.Reflection;
|
||||
using System.Runtime.CompilerServices;
|
||||
using System.Runtime.InteropServices;
|
||||
|
||||
// General Information about an assembly is controlled through the following
|
||||
// set of attributes. Change these attribute values to modify the information
|
||||
// associated with an assembly.
|
||||
[assembly: AssemblyTitle("Connection Patcher")]
|
||||
[assembly: AssemblyDescription("")]
|
||||
[assembly: AssemblyConfiguration("")]
|
||||
[assembly: AssemblyCompany("")]
|
||||
[assembly: AssemblyProduct("Connection Patcher")]
|
||||
[assembly: AssemblyCopyright("Copyright © 2014")]
|
||||
[assembly: AssemblyTrademark("")]
|
||||
[assembly: AssemblyCulture("")]
|
||||
|
||||
// Setting ComVisible to false makes the types in this assembly not visible
|
||||
// to COM components. If you need to access a type in this assembly from
|
||||
// COM, set the ComVisible attribute to true on that type.
|
||||
[assembly: ComVisible(false)]
|
||||
|
||||
// The following GUID is for the ID of the typelib if this project is exposed to COM
|
||||
[assembly: Guid("07c6905b-5b42-4804-81fe-73d0f74ebfb1")]
|
||||
|
||||
// Version information for an assembly consists of the following four values:
|
||||
//
|
||||
// Major Version
|
||||
// Minor Version
|
||||
// Build Number
|
||||
// Revision
|
||||
//
|
||||
// You can specify all the values or you can default the Build and Revision Numbers
|
||||
// by using the '*' as shown below:
|
||||
// [assembly: AssemblyVersion("1.0.*")]
|
||||
[assembly: AssemblyVersion("1.0.0.0")]
|
||||
[assembly: AssemblyFileVersion("1.0.0.0")]
|
||||
@@ -46,8 +46,12 @@ CREATE TABLE `account` (
|
||||
`locale` tinyint(3) unsigned NOT NULL DEFAULT '0',
|
||||
`os` varchar(3) NOT NULL DEFAULT '',
|
||||
`recruiter` int(10) unsigned NOT NULL DEFAULT '0',
|
||||
`battlenet_account` int(10) unsigned DEFAULT NULL,
|
||||
`battlenet_index` tinyint(3) unsigned DEFAULT NULL,
|
||||
PRIMARY KEY (`id`),
|
||||
UNIQUE KEY `idx_username` (`username`)
|
||||
UNIQUE KEY `idx_username` (`username`),
|
||||
UNIQUE KEY `uk_bnet_acc` (`battlenet_account`, `battlenet_index`),
|
||||
CONSTRAINT `fk_bnet_acc` FOREIGN KEY (`battlenet_account`) REFERENCES `battlenet_accounts` (`id`) ON DELETE RESTRICT ON UPDATE RESTRICT
|
||||
) ENGINE=InnoDB DEFAULT CHARSET=utf8 COMMENT='Account System';
|
||||
/*!40101 SET character_set_client = @saved_cs_client */;
|
||||
|
||||
@@ -136,6 +140,145 @@ LOCK TABLES `autobroadcast` WRITE;
|
||||
/*!40000 ALTER TABLE `autobroadcast` ENABLE KEYS */;
|
||||
UNLOCK TABLES;
|
||||
|
||||
--
|
||||
-- Table structure for table `battlenet_account_bans`
|
||||
--
|
||||
|
||||
DROP TABLE IF EXISTS `battlenet_account_bans`;
|
||||
/*!40101 SET @saved_cs_client = @@character_set_client */;
|
||||
/*!40101 SET character_set_client = utf8 */;
|
||||
CREATE TABLE `battlenet_account_bans` (
|
||||
`id` int(10) unsigned NOT NULL DEFAULT '0' COMMENT 'Account id',
|
||||
`bandate` int(10) unsigned NOT NULL DEFAULT '0',
|
||||
`unbandate` int(10) unsigned NOT NULL DEFAULT '0',
|
||||
`bannedby` varchar(50) NOT NULL,
|
||||
`banreason` varchar(255) NOT NULL,
|
||||
`active` tinyint(3) unsigned NOT NULL DEFAULT '1',
|
||||
PRIMARY KEY (`id`,`bandate`)
|
||||
) ENGINE=InnoDB DEFAULT CHARSET=utf8 COMMENT='Ban List';
|
||||
/*!40101 SET character_set_client = @saved_cs_client */;
|
||||
|
||||
--
|
||||
-- Dumping data for table `battlenet_account_bans`
|
||||
--
|
||||
|
||||
LOCK TABLES `battlenet_account_bans` WRITE;
|
||||
/*!40000 ALTER TABLE `battlenet_account_bans` DISABLE KEYS */;
|
||||
/*!40000 ALTER TABLE `battlenet_account_bans` ENABLE KEYS */;
|
||||
UNLOCK TABLES;
|
||||
|
||||
--
|
||||
-- Table structure for table `battlenet_accounts`
|
||||
--
|
||||
|
||||
DROP TABLE IF EXISTS `battlenet_accounts`;
|
||||
/*!40101 SET @saved_cs_client = @@character_set_client */;
|
||||
/*!40101 SET character_set_client = utf8 */;
|
||||
CREATE TABLE `battlenet_accounts` (
|
||||
`id` int(10) unsigned NOT NULL AUTO_INCREMENT COMMENT 'Identifier',
|
||||
`email` varchar(320) NOT NULL,
|
||||
`sha_pass_hash` varchar(64) NOT NULL DEFAULT '',
|
||||
`v` varchar(256) NOT NULL DEFAULT '',
|
||||
`s` varchar(64) NOT NULL DEFAULT '',
|
||||
`sessionKey` varchar(128) NOT NULL DEFAULT '',
|
||||
`joindate` timestamp NOT NULL DEFAULT CURRENT_TIMESTAMP,
|
||||
`last_ip` varchar(15) NOT NULL DEFAULT '127.0.0.1',
|
||||
`failed_logins` int(10) unsigned NOT NULL DEFAULT '0',
|
||||
`locked` tinyint(3) unsigned NOT NULL DEFAULT '0',
|
||||
`lock_country` varchar(2) NOT NULL DEFAULT '00',
|
||||
`last_login` timestamp NOT NULL DEFAULT '0000-00-00 00:00:00',
|
||||
`online` tinyint(3) unsigned NOT NULL DEFAULT '0',
|
||||
`locale` tinyint(3) unsigned NOT NULL DEFAULT '0',
|
||||
`os` varchar(3) NOT NULL DEFAULT '',
|
||||
PRIMARY KEY (`id`)
|
||||
) ENGINE=InnoDB AUTO_INCREMENT=7 DEFAULT CHARSET=utf8 COMMENT='Account System';
|
||||
/*!40101 SET character_set_client = @saved_cs_client */;
|
||||
|
||||
-- Table structure for table `battlenet_components`
|
||||
--
|
||||
|
||||
DROP TABLE IF EXISTS `battlenet_components`;
|
||||
/*!40101 SET @saved_cs_client = @@character_set_client */;
|
||||
/*!40101 SET character_set_client = utf8 */;
|
||||
CREATE TABLE `battlenet_components` (
|
||||
`Program` varchar(4) NOT NULL,
|
||||
`Platform` varchar(4) NOT NULL,
|
||||
`Build` int(11) unsigned NOT NULL,
|
||||
PRIMARY KEY (`Program`,`Platform`,`Build`)
|
||||
) ENGINE=InnoDB DEFAULT CHARSET=utf8;
|
||||
/*!40101 SET character_set_client = @saved_cs_client */;
|
||||
|
||||
--
|
||||
-- Dumping data for table `battlenet_components`
|
||||
--
|
||||
|
||||
LOCK TABLES `battlenet_components` WRITE;
|
||||
/*!40000 ALTER TABLE `battlenet_components` DISABLE KEYS */;
|
||||
INSERT INTO `battlenet_components` VALUES
|
||||
('Bnet','Cmp1',3),
|
||||
('Bnet','Win',26487),
|
||||
('Bnet','Wn64',26487),
|
||||
('Tool','Win',2736),
|
||||
('WoW','base',15595),
|
||||
('WoW','enGB',15595),
|
||||
('WoW','enUS',15595),
|
||||
('WoW','Win',15595),
|
||||
('WoW','Wn64',15595);
|
||||
/*!40000 ALTER TABLE `battlenet_components` ENABLE KEYS */;
|
||||
UNLOCK TABLES;
|
||||
|
||||
--
|
||||
-- Table structure for table `battlenet_modules`
|
||||
--
|
||||
|
||||
DROP TABLE IF EXISTS `battlenet_modules`;
|
||||
/*!40101 SET @saved_cs_client = @@character_set_client */;
|
||||
/*!40101 SET character_set_client = utf8 */;
|
||||
CREATE TABLE `battlenet_modules` (
|
||||
`Hash` varchar(64) NOT NULL,
|
||||
`Name` varchar(64) NOT NULL DEFAULT '',
|
||||
`Type` varchar(8) NOT NULL,
|
||||
`System` varchar(8) NOT NULL,
|
||||
`Data` text,
|
||||
PRIMARY KEY (`Hash`),
|
||||
UNIQUE KEY `uk_name_type_system` (`Name`,`Type`,`System`)
|
||||
) ENGINE=InnoDB DEFAULT CHARSET=utf8;
|
||||
/*!40101 SET character_set_client = @saved_cs_client */;
|
||||
|
||||
--
|
||||
-- Dumping data for table `battlenet_modules`
|
||||
--
|
||||
|
||||
LOCK TABLES `battlenet_modules` WRITE;
|
||||
/*!40000 ALTER TABLE `battlenet_modules` DISABLE KEYS */;
|
||||
INSERT INTO `battlenet_modules` VALUES
|
||||
('19c91b68752b7826df498bf73aca1103c86962a9a55a0a7033e5ad895f4d927c','Password','auth','Mc64',NULL),
|
||||
('1af5418a448f8ad05451e3f7dbb2d9af9cb13458eea2368ebfc539476b954f1c','RiskFingerprint','auth','Mc64',NULL),
|
||||
('207640724f4531d3b2a21532224d1486e8c4d2d805170381cbc3093264157960','SelectGameAccount','auth','Mac',NULL),
|
||||
('2e6d53adab37a41542b38e01f62cd365eab8805ed0de73c307cc6d9d1dfe478c','Password','auth','Win',NULL),
|
||||
('36b27cd911b33c61730a8b82c8b2495fd16e8024fc3b2dde08861c77a852941c','Thumbprint','auth','Win','E716F4F0A01EB9C032A6C1393356A4F766F067949D71023C0CFC0613718966EF814E65CC6EE70C432A7F8AFD8A062B52603A2697E851D231D72C0277614181D713369B1E8E4BEEAB72045A9AAD45F319DB918ECDDB83C8EF8B7510600D391D45E7FEC0BEEAE904A5F9FA620F1CCDAD699D84A4739CE669B5A551831E396214E13B4C88F573F5CDC784CD01530C086B674C03BEB66403A0F87ED17ABBB403DE54CF31BE828A20C566C22E4D4263AA77220B0644D99245345BCAC276EA06925EB984D664725C3CB757140AFE12E27CB996F17159B1057E9B58B78BBB5A139C9FF6215A0D250B75FC9DD435655DDEADCD6CFD84800792C146B3633188ECEB53D2038C185E0BD51A9E6C70FD38ADF530F8DF50FB62053C5E894897AB7DD65C7AC80665F18E7989BE6E30F15E939751123D6D8A44F033175301D15AAAD2AEA06FAC60BA4065846AE938F32B1CB15F16DC0E76792A7332346896048065D17C059899E1D2300E402BD0EA74265DA6A42B1C854E2470D7B21AE4A2DAE90E602A759B2CA0EE610B50D5389DB89335D5451FE76DD85B09FD5297D6F9EFB6C34CE885007F7DF20D6A524E0C3E772FA04B3DD2E014D3A337A790943DAD523CBB5453F4FDF8E74DFE361BD5F25AB31952B478148B570DF5762643F32B994FEC99A747E4A265A66EE84A53509EC285C84679606049314FC526C61B537AC8061C788F8B86F52208'),
|
||||
('393ca8d75aff6f04f79532cf95a88b91e5743bc59121520ac31fc4508019fe60','Token','auth','Mac',NULL),
|
||||
('3c2f63e5949aa6fd6cf330b109ca5b9adcd215beac846b7462ed3aa01d5ad6bb','Password','auth','Mac',NULL),
|
||||
('52e2978db6468dfade7c61da89513f443c9225692b5085fbe956749870993703','SelectGameAccount','auth','Mc64',NULL),
|
||||
('548b5ef9e0dd5c2f89f59c3e0979249b27505c51f0c77d2b27133726eaee0ad0','Thumbprint','auth','Mac','E716F4F0A01EB9C032A6C1393356A4F766F067949D71023C0CFC0613718966EF814E65CC6EE70C432A7F8AFD8A062B52603A2697E851D231D72C0277614181D713369B1E8E4BEEAB72045A9AAD45F319DB918ECDDB83C8EF8B7510600D391D45E7FEC0BEEAE904A5F9FA620F1CCDAD699D84A4739CE669B5A551831E396214E13B4C88F573F5CDC784CD01530C086B674C03BEB66403A0F87ED17ABBB403DE54CF31BE828A20C566C22E4D4263AA77220B0644D99245345BCAC276EA06925EB984D664725C3CB757140AFE12E27CB996F17159B1057E9B58B78BBB5A139C9FF6215A0D250B75FC9DD435655DDEADCD6CFD84800792C146B3633188ECEB53D2038C185E0BD51A9E6C70FD38ADF530F8DF50FB62053C5E894897AB7DD65C7AC80665F18E7989BE6E30F15E939751123D6D8A44F033175301D15AAAD2AEA06FAC60BA4065846AE938F32B1CB15F16DC0E76792A7332346896048065D17C059899E1D2300E402BD0EA74265DA6A42B1C854E2470D7B21AE4A2DAE90E602A759B2CA0EE610B50D5389DB89335D5451FE76DD85B09FD5297D6F9EFB6C34CE885007F7DF20D6A524E0C3E772FA04B3DD2E014D3A337A790943DAD523CBB5453F4FDF8E74DFE361BD5F25AB31952B478148B570DF5762643F32B994FEC99A747E4A265A66EE84A53509EC285C84679606049314FC526C61B537AC8061C788F8B86F52208'),
|
||||
('5e298e530698af905e1247e51ef0b109b352ac310ce7802a1f63613db980ed17','RiskFingerprint','auth','Win',NULL),
|
||||
('851c1d2ef926e9b9a345a460874e65517195129b9e3bdec7cc77710fa0b1fad6','Password','auth','Wn64',NULL),
|
||||
('894d25d3219d97d085ea5a8b98e66df5bd9f460ec6f104455246a12b8921409d','SelectGameAccount','auth','Wn64',NULL),
|
||||
('8c43bda10be33a32abbc09fb2279126c7f5953336391276cff588565332fcd40','RiskFingerprint','auth','Wn64',NULL),
|
||||
('a1edab845d9e13e9c84531369be2f61b930a37c8e7a9c66d11ef8963380e178a','Token','auth','Mc64',NULL),
|
||||
('a330f388b6687f8a42fe8fbb592a3df724b20b65fb0989342bb8261f2f452318','Token','auth','Wn64',NULL),
|
||||
('abc6bb719a73ec1055296001910e26afa561f701ad9995b1ecd7f55f9d3ca37c','SelectGameAccount','auth','Win',NULL),
|
||||
('b37136b39add83cfdbafa81857de3dd8f15b34e0135ec6cd9c3131d3a578d8c2','Thumbprint','auth','Mc64','E716F4F0A01EB9C032A6C1393356A4F766F067949D71023C0CFC0613718966EF814E65CC6EE70C432A7F8AFD8A062B52603A2697E851D231D72C0277614181D713369B1E8E4BEEAB72045A9AAD45F319DB918ECDDB83C8EF8B7510600D391D45E7FEC0BEEAE904A5F9FA620F1CCDAD699D84A4739CE669B5A551831E396214E13B4C88F573F5CDC784CD01530C086B674C03BEB66403A0F87ED17ABBB403DE54CF31BE828A20C566C22E4D4263AA77220B0644D99245345BCAC276EA06925EB984D664725C3CB757140AFE12E27CB996F17159B1057E9B58B78BBB5A139C9FF6215A0D250B75FC9DD435655DDEADCD6CFD84800792C146B3633188ECEB53D2038C185E0BD51A9E6C70FD38ADF530F8DF50FB62053C5E894897AB7DD65C7AC80665F18E7989BE6E30F15E939751123D6D8A44F033175301D15AAAD2AEA06FAC60BA4065846AE938F32B1CB15F16DC0E76792A7332346896048065D17C059899E1D2300E402BD0EA74265DA6A42B1C854E2470D7B21AE4A2DAE90E602A759B2CA0EE610B50D5389DB89335D5451FE76DD85B09FD5297D6F9EFB6C34CE885007F7DF20D6A524E0C3E772FA04B3DD2E014D3A337A790943DAD523CBB5453F4FDF8E74DFE361BD5F25AB31952B478148B570DF5762643F32B994FEC99A747E4A265A66EE84A53509EC285C84679606049314FC526C61B537AC8061C788F8B86F52208'),
|
||||
('c0f38d05aa1b83065e839c9bd96c831e9f7e42477085138752657a6a9bb9c520','RiskFingerprint','auth','Mac',NULL),
|
||||
('c3a1ac0694979e709c3b5486927e558af1e2be02ca96e5615c5a65aacc829226','Thumbprint','auth','Wn64','E716F4F0A01EB9C032A6C1393356A4F766F067949D71023C0CFC0613718966EF814E65CC6EE70C432A7F8AFD8A062B52603A2697E851D231D72C0277614181D713369B1E8E4BEEAB72045A9AAD45F319DB918ECDDB83C8EF8B7510600D391D45E7FEC0BEEAE904A5F9FA620F1CCDAD699D84A4739CE669B5A551831E396214E13B4C88F573F5CDC784CD01530C086B674C03BEB66403A0F87ED17ABBB403DE54CF31BE828A20C566C22E4D4263AA77220B0644D99245345BCAC276EA06925EB984D664725C3CB757140AFE12E27CB996F17159B1057E9B58B78BBB5A139C9FF6215A0D250B75FC9DD435655DDEADCD6CFD84800792C146B3633188ECEB53D2038C185E0BD51A9E6C70FD38ADF530F8DF50FB62053C5E894897AB7DD65C7AC80665F18E7989BE6E30F15E939751123D6D8A44F033175301D15AAAD2AEA06FAC60BA4065846AE938F32B1CB15F16DC0E76792A7332346896048065D17C059899E1D2300E402BD0EA74265DA6A42B1C854E2470D7B21AE4A2DAE90E602A759B2CA0EE610B50D5389DB89335D5451FE76DD85B09FD5297D6F9EFB6C34CE885007F7DF20D6A524E0C3E772FA04B3DD2E014D3A337A790943DAD523CBB5453F4FDF8E74DFE361BD5F25AB31952B478148B570DF5762643F32B994FEC99A747E4A265A66EE84A53509EC285C84679606049314FC526C61B537AC8061C788F8B86F52208'),
|
||||
('fbe675a99fb5f4b7fb3eb5e5a22add91a4cabf83e3c5930c6659ad13c457ba18','Token','auth','Win',NULL),
|
||||
('bfe4ceb47700aa872e815e007e27df955d4cd4bc1fe731039ee6498ce209f368','Resume','auth','Win',NULL),
|
||||
('00ffd88a437afbb88d7d4b74be2e3b43601605ee229151aa9f4bebb29ef66280','Resume','auth','Mac',NULL),
|
||||
('898166926805f897804bdbbf40662c9d768590a51a0b26c40dbcdf332ba11974','Resume','auth','Wn64',NULL),
|
||||
('304627d437c38500c0b5ca0c6220eeade91390e52a2b005ff3f7754afa1f93cd','Resume','auth','Mc64',NULL);
|
||||
/*!40000 ALTER TABLE `battlenet_modules` ENABLE KEYS */;
|
||||
UNLOCK TABLES;
|
||||
|
||||
--
|
||||
-- Table structure for table `ip2nation`
|
||||
--
|
||||
@@ -390,6 +533,8 @@ CREATE TABLE `realmlist` (
|
||||
`allowedSecurityLevel` tinyint(3) unsigned NOT NULL DEFAULT '0',
|
||||
`population` float unsigned NOT NULL DEFAULT '0',
|
||||
`gamebuild` int(10) unsigned NOT NULL DEFAULT '15595',
|
||||
`Region` tinyint(3) unsigned NOT NULL DEFAULT '2',
|
||||
`Battlegroup` tinyint(3) unsigned NOT NULL DEFAULT '1',
|
||||
PRIMARY KEY (`id`),
|
||||
UNIQUE KEY `idx_name` (`name`)
|
||||
) ENGINE=InnoDB AUTO_INCREMENT=2 DEFAULT CHARSET=utf8 COMMENT='Realm System';
|
||||
@@ -401,7 +546,7 @@ CREATE TABLE `realmlist` (
|
||||
|
||||
LOCK TABLES `realmlist` WRITE;
|
||||
/*!40000 ALTER TABLE `realmlist` DISABLE KEYS */;
|
||||
INSERT INTO `realmlist` VALUES (1,'Trinity','127.0.0.1','127.0.0.1','255.255.255.0',8085,1,0,1,0,0,15595);
|
||||
INSERT INTO `realmlist` VALUES (1,'Trinity','127.0.0.1','127.0.0.1','255.255.255.0',8085,1,0,1,0,0,15595,2,1);
|
||||
/*!40000 ALTER TABLE `realmlist` ENABLE KEYS */;
|
||||
UNLOCK TABLES;
|
||||
|
||||
|
||||
148
sql/updates/auth/2014_05_06_00_auth_battlenet_434.sql
Normal file
148
sql/updates/auth/2014_05_06_00_auth_battlenet_434.sql
Normal file
@@ -0,0 +1,148 @@
|
||||
ALTER TABLE `account`
|
||||
ADD `battlenet_account` int(10) unsigned DEFAULT NULL AFTER `recruiter`,
|
||||
ADD CONSTRAINT `fk_bnet_acc` FOREIGN KEY (`battlenet_account`) REFERENCES `battlenet_accounts` (`id`) ON DELETE RESTRICT ON UPDATE RESTRICT;
|
||||
|
||||
ALTER TABLE `realmlist`
|
||||
ADD `Region` tinyint(3) UNSIGNED NOT NULL DEFAULT 2 AFTER `gamebuild`,
|
||||
ADD `Battlegroup` tinyint(3) UNSIGNED NOT NULL DEFAULT 0 AFTER `Region`;
|
||||
|
||||
--
|
||||
-- Table structure for table `battlenet_account_bans`
|
||||
--
|
||||
|
||||
DROP TABLE IF EXISTS `battlenet_account_bans`;
|
||||
/*!40101 SET @saved_cs_client = @@character_set_client */;
|
||||
/*!40101 SET character_set_client = utf8 */;
|
||||
CREATE TABLE `battlenet_account_bans` (
|
||||
`id` int(10) unsigned NOT NULL DEFAULT '0' COMMENT 'Account id',
|
||||
`bandate` int(10) unsigned NOT NULL DEFAULT '0',
|
||||
`unbandate` int(10) unsigned NOT NULL DEFAULT '0',
|
||||
`bannedby` varchar(50) NOT NULL,
|
||||
`banreason` varchar(255) NOT NULL,
|
||||
`active` tinyint(3) unsigned NOT NULL DEFAULT '1',
|
||||
PRIMARY KEY (`id`,`bandate`)
|
||||
) ENGINE=InnoDB DEFAULT CHARSET=utf8 COMMENT='Ban List';
|
||||
/*!40101 SET character_set_client = @saved_cs_client */;
|
||||
|
||||
--
|
||||
-- Dumping data for table `battlenet_account_bans`
|
||||
--
|
||||
|
||||
LOCK TABLES `battlenet_account_bans` WRITE;
|
||||
/*!40000 ALTER TABLE `battlenet_account_bans` DISABLE KEYS */;
|
||||
/*!40000 ALTER TABLE `battlenet_account_bans` ENABLE KEYS */;
|
||||
UNLOCK TABLES;
|
||||
|
||||
--
|
||||
-- Table structure for table `battlenet_accounts`
|
||||
--
|
||||
|
||||
DROP TABLE IF EXISTS `battlenet_accounts`;
|
||||
/*!40101 SET @saved_cs_client = @@character_set_client */;
|
||||
/*!40101 SET character_set_client = utf8 */;
|
||||
CREATE TABLE `battlenet_accounts` (
|
||||
`id` int(10) unsigned NOT NULL AUTO_INCREMENT COMMENT 'Identifier',
|
||||
`email` varchar(320) NOT NULL,
|
||||
`sha_pass_hash` varchar(64) NOT NULL DEFAULT '',
|
||||
`v` varchar(256) NOT NULL DEFAULT '',
|
||||
`s` varchar(64) NOT NULL DEFAULT '',
|
||||
`joindate` timestamp NOT NULL DEFAULT CURRENT_TIMESTAMP,
|
||||
`last_ip` varchar(15) NOT NULL DEFAULT '127.0.0.1',
|
||||
`failed_logins` int(10) unsigned NOT NULL DEFAULT '0',
|
||||
`locked` tinyint(3) unsigned NOT NULL DEFAULT '0',
|
||||
`lock_country` varchar(2) NOT NULL DEFAULT '00',
|
||||
`last_login` timestamp NOT NULL DEFAULT '0000-00-00 00:00:00',
|
||||
`online` tinyint(3) unsigned NOT NULL DEFAULT '0',
|
||||
`locale` tinyint(3) unsigned NOT NULL DEFAULT '0',
|
||||
`os` varchar(3) NOT NULL DEFAULT '',
|
||||
PRIMARY KEY (`id`)
|
||||
) ENGINE=InnoDB AUTO_INCREMENT=7 DEFAULT CHARSET=utf8 COMMENT='Account System';
|
||||
/*!40101 SET character_set_client = @saved_cs_client */;
|
||||
|
||||
-- Table structure for table `battlenet_components`
|
||||
--
|
||||
|
||||
DROP TABLE IF EXISTS `battlenet_components`;
|
||||
/*!40101 SET @saved_cs_client = @@character_set_client */;
|
||||
/*!40101 SET character_set_client = utf8 */;
|
||||
CREATE TABLE `battlenet_components` (
|
||||
`Program` varchar(4) NOT NULL,
|
||||
`Platform` varchar(4) NOT NULL,
|
||||
`Build` int(11) unsigned NOT NULL,
|
||||
PRIMARY KEY (`Program`,`Platform`,`Build`)
|
||||
) ENGINE=InnoDB DEFAULT CHARSET=utf8;
|
||||
/*!40101 SET character_set_client = @saved_cs_client */;
|
||||
|
||||
--
|
||||
-- Dumping data for table `battlenet_components`
|
||||
--
|
||||
|
||||
LOCK TABLES `battlenet_components` WRITE;
|
||||
/*!40000 ALTER TABLE `battlenet_components` DISABLE KEYS */;
|
||||
INSERT INTO `battlenet_components` VALUES
|
||||
('Bnet','Cmp1',3),
|
||||
('Bnet','Win',21719),
|
||||
('Bnet','Win',26487),
|
||||
('Bnet','Wn64',26487),
|
||||
('Tool','Win',1569),
|
||||
('Tool','Win',2736),
|
||||
('WoW','base',12340),
|
||||
('WoW','base',15595),
|
||||
('WoW','enGB',12340),
|
||||
('WoW','enGB',15595),
|
||||
('WoW','enUS',12340),
|
||||
('WoW','enUS',15595),
|
||||
('WoW','Win',12340),
|
||||
('WoW','Win',15595),
|
||||
('WoW','Wn64',15595);
|
||||
/*!40000 ALTER TABLE `battlenet_components` ENABLE KEYS */;
|
||||
UNLOCK TABLES;
|
||||
|
||||
--
|
||||
-- Table structure for table `battlenet_modules`
|
||||
--
|
||||
|
||||
DROP TABLE IF EXISTS `battlenet_modules`;
|
||||
/*!40101 SET @saved_cs_client = @@character_set_client */;
|
||||
/*!40101 SET character_set_client = utf8 */;
|
||||
CREATE TABLE `battlenet_modules` (
|
||||
`Hash` varchar(64) NOT NULL,
|
||||
`Name` varchar(64) NOT NULL DEFAULT '',
|
||||
`Type` varchar(8) NOT NULL,
|
||||
`System` varchar(8) NOT NULL,
|
||||
`Data` text,
|
||||
PRIMARY KEY (`Hash`),
|
||||
UNIQUE KEY `uk_name_type_system` (`Name`,`Type`,`System`)
|
||||
) ENGINE=InnoDB DEFAULT CHARSET=utf8;
|
||||
/*!40101 SET character_set_client = @saved_cs_client */;
|
||||
|
||||
--
|
||||
-- Dumping data for table `battlenet_modules`
|
||||
--
|
||||
|
||||
LOCK TABLES `battlenet_modules` WRITE;
|
||||
/*!40000 ALTER TABLE `battlenet_modules` DISABLE KEYS */;
|
||||
INSERT INTO `battlenet_modules` VALUES
|
||||
('19c91b68752b7826df498bf73aca1103c86962a9a55a0a7033e5ad895f4d927c','Password','auth','Mc64',NULL),
|
||||
('1af5418a448f8ad05451e3f7dbb2d9af9cb13458eea2368ebfc539476b954f1c','RiskFingerprint','auth','Mc64',NULL),
|
||||
('207640724f4531d3b2a21532224d1486e8c4d2d805170381cbc3093264157960','SelectGameAccount','auth','Mac',NULL),
|
||||
('2e6d53adab37a41542b38e01f62cd365eab8805ed0de73c307cc6d9d1dfe478c','Password','auth','Win',NULL),
|
||||
('36b27cd911b33c61730a8b82c8b2495fd16e8024fc3b2dde08861c77a852941c','Thumbprint','auth','Win','E716F4F0A01EB9C032A6C1393356A4F766F067949D71023C0CFC0613718966EF814E65CC6EE70C432A7F8AFD8A062B52603A2697E851D231D72C0277614181D713369B1E8E4BEEAB72045A9AAD45F319DB918ECDDB83C8EF8B7510600D391D45E7FEC0BEEAE904A5F9FA620F1CCDAD699D84A4739CE669B5A551831E396214E13B4C88F573F5CDC784CD01530C086B674C03BEB66403A0F87ED17ABBB403DE54CF31BE828A20C566C22E4D4263AA77220B0644D99245345BCAC276EA06925EB984D664725C3CB757140AFE12E27CB996F17159B1057E9B58B78BBB5A139C9FF6215A0D250B75FC9DD435655DDEADCD6CFD84800792C146B3633188ECEB53D2038C185E0BD51A9E6C70FD38ADF530F8DF50FB62053C5E894897AB7DD65C7AC80665F18E7989BE6E30F15E939751123D6D8A44F033175301D15AAAD2AEA06FAC60BA4065846AE938F32B1CB15F16DC0E76792A7332346896048065D17C059899E1D2300E402BD0EA74265DA6A42B1C854E2470D7B21AE4A2DAE90E602A759B2CA0EE610B50D5389DB89335D5451FE76DD85B09FD5297D6F9EFB6C34CE885007F7DF20D6A524E0C3E772FA04B3DD2E014D3A337A790943DAD523CBB5453F4FDF8E74DFE361BD5F25AB31952B478148B570DF5762643F32B994FEC99A747E4A265A66EE84A53509EC285C84679606049314FC526C61B537AC8061C788F8B86F52208'),
|
||||
('393ca8d75aff6f04f79532cf95a88b91e5743bc59121520ac31fc4508019fe60','Token','auth','Mac',NULL),
|
||||
('3c2f63e5949aa6fd6cf330b109ca5b9adcd215beac846b7462ed3aa01d5ad6bb','Password','auth','Mac',NULL),
|
||||
('52e2978db6468dfade7c61da89513f443c9225692b5085fbe956749870993703','SelectGameAccount','auth','Mc64',NULL),
|
||||
('548b5ef9e0dd5c2f89f59c3e0979249b27505c51f0c77d2b27133726eaee0ad0','Thumbprint','auth','Mac','E716F4F0A01EB9C032A6C1393356A4F766F067949D71023C0CFC0613718966EF814E65CC6EE70C432A7F8AFD8A062B52603A2697E851D231D72C0277614181D713369B1E8E4BEEAB72045A9AAD45F319DB918ECDDB83C8EF8B7510600D391D45E7FEC0BEEAE904A5F9FA620F1CCDAD699D84A4739CE669B5A551831E396214E13B4C88F573F5CDC784CD01530C086B674C03BEB66403A0F87ED17ABBB403DE54CF31BE828A20C566C22E4D4263AA77220B0644D99245345BCAC276EA06925EB984D664725C3CB757140AFE12E27CB996F17159B1057E9B58B78BBB5A139C9FF6215A0D250B75FC9DD435655DDEADCD6CFD84800792C146B3633188ECEB53D2038C185E0BD51A9E6C70FD38ADF530F8DF50FB62053C5E894897AB7DD65C7AC80665F18E7989BE6E30F15E939751123D6D8A44F033175301D15AAAD2AEA06FAC60BA4065846AE938F32B1CB15F16DC0E76792A7332346896048065D17C059899E1D2300E402BD0EA74265DA6A42B1C854E2470D7B21AE4A2DAE90E602A759B2CA0EE610B50D5389DB89335D5451FE76DD85B09FD5297D6F9EFB6C34CE885007F7DF20D6A524E0C3E772FA04B3DD2E014D3A337A790943DAD523CBB5453F4FDF8E74DFE361BD5F25AB31952B478148B570DF5762643F32B994FEC99A747E4A265A66EE84A53509EC285C84679606049314FC526C61B537AC8061C788F8B86F52208'),
|
||||
('5e298e530698af905e1247e51ef0b109b352ac310ce7802a1f63613db980ed17','RiskFingerprint','auth','Win',NULL),
|
||||
('851c1d2ef926e9b9a345a460874e65517195129b9e3bdec7cc77710fa0b1fad6','Password','auth','Wn64',NULL),
|
||||
('894d25d3219d97d085ea5a8b98e66df5bd9f460ec6f104455246a12b8921409d','SelectGameAccount','auth','Wn64',NULL),
|
||||
('8c43bda10be33a32abbc09fb2279126c7f5953336391276cff588565332fcd40','RiskFingerprint','auth','Wn64',NULL),
|
||||
('a1edab845d9e13e9c84531369be2f61b930a37c8e7a9c66d11ef8963380e178a','Token','auth','Mc64',NULL),
|
||||
('a330f388b6687f8a42fe8fbb592a3df724b20b65fb0989342bb8261f2f452318','Token','auth','Wn64',NULL),
|
||||
('abc6bb719a73ec1055296001910e26afa561f701ad9995b1ecd7f55f9d3ca37c','SelectGameAccount','auth','Win',NULL),
|
||||
('b37136b39add83cfdbafa81857de3dd8f15b34e0135ec6cd9c3131d3a578d8c2','Thumbprint','auth','Mc64','E716F4F0A01EB9C032A6C1393356A4F766F067949D71023C0CFC0613718966EF814E65CC6EE70C432A7F8AFD8A062B52603A2697E851D231D72C0277614181D713369B1E8E4BEEAB72045A9AAD45F319DB918ECDDB83C8EF8B7510600D391D45E7FEC0BEEAE904A5F9FA620F1CCDAD699D84A4739CE669B5A551831E396214E13B4C88F573F5CDC784CD01530C086B674C03BEB66403A0F87ED17ABBB403DE54CF31BE828A20C566C22E4D4263AA77220B0644D99245345BCAC276EA06925EB984D664725C3CB757140AFE12E27CB996F17159B1057E9B58B78BBB5A139C9FF6215A0D250B75FC9DD435655DDEADCD6CFD84800792C146B3633188ECEB53D2038C185E0BD51A9E6C70FD38ADF530F8DF50FB62053C5E894897AB7DD65C7AC80665F18E7989BE6E30F15E939751123D6D8A44F033175301D15AAAD2AEA06FAC60BA4065846AE938F32B1CB15F16DC0E76792A7332346896048065D17C059899E1D2300E402BD0EA74265DA6A42B1C854E2470D7B21AE4A2DAE90E602A759B2CA0EE610B50D5389DB89335D5451FE76DD85B09FD5297D6F9EFB6C34CE885007F7DF20D6A524E0C3E772FA04B3DD2E014D3A337A790943DAD523CBB5453F4FDF8E74DFE361BD5F25AB31952B478148B570DF5762643F32B994FEC99A747E4A265A66EE84A53509EC285C84679606049314FC526C61B537AC8061C788F8B86F52208'),
|
||||
('c0f38d05aa1b83065e839c9bd96c831e9f7e42477085138752657a6a9bb9c520','RiskFingerprint','auth','Mac',NULL),
|
||||
('c3a1ac0694979e709c3b5486927e558af1e2be02ca96e5615c5a65aacc829226','Thumbprint','auth','Wn64','E716F4F0A01EB9C032A6C1393356A4F766F067949D71023C0CFC0613718966EF814E65CC6EE70C432A7F8AFD8A062B52603A2697E851D231D72C0277614181D713369B1E8E4BEEAB72045A9AAD45F319DB918ECDDB83C8EF8B7510600D391D45E7FEC0BEEAE904A5F9FA620F1CCDAD699D84A4739CE669B5A551831E396214E13B4C88F573F5CDC784CD01530C086B674C03BEB66403A0F87ED17ABBB403DE54CF31BE828A20C566C22E4D4263AA77220B0644D99245345BCAC276EA06925EB984D664725C3CB757140AFE12E27CB996F17159B1057E9B58B78BBB5A139C9FF6215A0D250B75FC9DD435655DDEADCD6CFD84800792C146B3633188ECEB53D2038C185E0BD51A9E6C70FD38ADF530F8DF50FB62053C5E894897AB7DD65C7AC80665F18E7989BE6E30F15E939751123D6D8A44F033175301D15AAAD2AEA06FAC60BA4065846AE938F32B1CB15F16DC0E76792A7332346896048065D17C059899E1D2300E402BD0EA74265DA6A42B1C854E2470D7B21AE4A2DAE90E602A759B2CA0EE610B50D5389DB89335D5451FE76DD85B09FD5297D6F9EFB6C34CE885007F7DF20D6A524E0C3E772FA04B3DD2E014D3A337A790943DAD523CBB5453F4FDF8E74DFE361BD5F25AB31952B478148B570DF5762643F32B994FEC99A747E4A265A66EE84A53509EC285C84679606049314FC526C61B537AC8061C788F8B86F52208'),
|
||||
('fbe675a99fb5f4b7fb3eb5e5a22add91a4cabf83e3c5930c6659ad13c457ba18','Token','auth','Win',NULL);
|
||||
/*!40000 ALTER TABLE `battlenet_modules` ENABLE KEYS */;
|
||||
UNLOCK TABLES;
|
||||
|
||||
8
sql/updates/auth/2014_06_01_00_auth_battlenet_434.sql
Normal file
8
sql/updates/auth/2014_06_01_00_auth_battlenet_434.sql
Normal file
@@ -0,0 +1,8 @@
|
||||
ALTER TABLE `battlenet_accounts` ADD `sessionKey` VARCHAR(128) NOT NULL DEFAULT '' AFTER `s`;
|
||||
|
||||
DELETE FROM `battlenet_modules` WHERE `Name`='Resume';
|
||||
INSERT INTO `battlenet_modules` VALUES
|
||||
('bfe4ceb47700aa872e815e007e27df955d4cd4bc1fe731039ee6498ce209f368','Resume','auth','Win',NULL),
|
||||
('00ffd88a437afbb88d7d4b74be2e3b43601605ee229151aa9f4bebb29ef66280','Resume','auth','Mac',NULL),
|
||||
('898166926805f897804bdbbf40662c9d768590a51a0b26c40dbcdf332ba11974','Resume','auth','Wn64',NULL),
|
||||
('304627d437c38500c0b5ca0c6220eeade91390e52a2b005ff3f7754afa1f93cd','Resume','auth','Mc64',NULL);
|
||||
3
sql/updates/auth/2014_06_08_00_auth_account_434.sql
Normal file
3
sql/updates/auth/2014_06_08_00_auth_account_434.sql
Normal file
@@ -0,0 +1,3 @@
|
||||
ALTER TABLE `account`
|
||||
ADD `battlenet_index` tinyint(3) unsigned DEFAULT NULL AFTER `battlenet_account`,
|
||||
ADD UNIQUE KEY `uk_bnet_acc` (`battlenet_account`, `battlenet_index`);
|
||||
3
sql/updates/auth/2014_06_08_01_auth_account_434.sql
Normal file
3
sql/updates/auth/2014_06_08_01_auth_account_434.sql
Normal file
@@ -0,0 +1,3 @@
|
||||
DELETE FROM `battlenet_components` WHERE `Program`='WoW' AND `Build`=12340;
|
||||
DELETE FROM `battlenet_components` WHERE `Program`='Tool' AND `Build`=1569;
|
||||
DELETE FROM `battlenet_components` WHERE `Program`='Bnet' AND `Build`=21719;
|
||||
@@ -79,4 +79,9 @@ namespace AuthHelper
|
||||
|
||||
return NULL;
|
||||
}
|
||||
|
||||
bool IsBuildSupportingBattlenet(int build)
|
||||
{
|
||||
return build >= 15595;
|
||||
}
|
||||
}
|
||||
|
||||
@@ -70,6 +70,96 @@ enum LoginResult
|
||||
LOGIN_LOCKED_ENFORCED = 0x10
|
||||
};
|
||||
|
||||
enum GameAccountFlags
|
||||
{
|
||||
GAMEACCOUNT_FLAG_GM = 0x00000001,
|
||||
GAMEACCOUNT_FLAG_NOKICK = 0x00000002,
|
||||
GAMEACCOUNT_FLAG_COLLECTOR = 0x00000004,
|
||||
GAMEACCOUNT_FLAG_WOW_TRIAL = 0x00000008,
|
||||
GAMEACCOUNT_FLAG_CANCELLED = 0x00000010,
|
||||
GAMEACCOUNT_FLAG_IGR = 0x00000020,
|
||||
GAMEACCOUNT_FLAG_WHOLESALER = 0x00000040,
|
||||
GAMEACCOUNT_FLAG_PRIVILEGED = 0x00000080,
|
||||
GAMEACCOUNT_FLAG_EU_FORBID_ELV = 0x00000100,
|
||||
GAMEACCOUNT_FLAG_EU_FORBID_BILLING = 0x00000200,
|
||||
GAMEACCOUNT_FLAG_WOW_RESTRICTED = 0x00000400,
|
||||
GAMEACCOUNT_FLAG_REFERRAL = 0x00000800,
|
||||
GAMEACCOUNT_FLAG_BLIZZARD = 0x00001000,
|
||||
GAMEACCOUNT_FLAG_RECURRING_BILLING = 0x00002000,
|
||||
GAMEACCOUNT_FLAG_NOELECTUP = 0x00004000,
|
||||
GAMEACCOUNT_FLAG_KR_CERTIFICATE = 0x00008000,
|
||||
GAMEACCOUNT_FLAG_EXPANSION_COLLECTOR = 0x00010000,
|
||||
GAMEACCOUNT_FLAG_DISABLE_VOICE = 0x00020000,
|
||||
GAMEACCOUNT_FLAG_DISABLE_VOICE_SPEAK = 0x00040000,
|
||||
GAMEACCOUNT_FLAG_REFERRAL_RESURRECT = 0x00080000,
|
||||
GAMEACCOUNT_FLAG_EU_FORBID_CC = 0x00100000,
|
||||
GAMEACCOUNT_FLAG_OPENBETA_DELL = 0x00200000,
|
||||
GAMEACCOUNT_FLAG_PROPASS = 0x00400000,
|
||||
GAMEACCOUNT_FLAG_PROPASS_LOCK = 0x00800000,
|
||||
GAMEACCOUNT_FLAG_PENDING_UPGRADE = 0x01000000,
|
||||
GAMEACCOUNT_FLAG_RETAIL_FROM_TRIAL = 0x02000000,
|
||||
GAMEACCOUNT_FLAG_EXPANSION2_COLLECTOR = 0x04000000,
|
||||
GAMEACCOUNT_FLAG_OVERMIND_LINKED = 0x08000000,
|
||||
GAMEACCOUNT_FLAG_DEMOS = 0x10000000,
|
||||
GAMEACCOUNT_FLAG_DEATH_KNIGHT_OK = 0x20000000,
|
||||
};
|
||||
|
||||
namespace Battlenet
|
||||
{
|
||||
enum AuthResult
|
||||
{
|
||||
AUTH_OK = 0,
|
||||
AUTH_INTERNAL_ERROR = 100,
|
||||
AUTH_CORRUPTED_MODULE = 102,
|
||||
AUTH_BAD_SERVER_PROOF = 103,
|
||||
AUTH_UNKNOWN_ACCOUNT = 104,
|
||||
AUTH_CLOSED = 105,
|
||||
AUTH_LOGIN_TIMEOUT = 106,
|
||||
AUTH_NO_GAME_ACCOUNTS = 107,
|
||||
AUTH_INVALID_TOKEN = 108,
|
||||
AUTH_INVALID_PROGRAM = 109,
|
||||
AUTH_INVALID_OS = 110,
|
||||
AUTH_UNSUPPORTED_LANGUAGE = 111,
|
||||
AUTH_REGION_BAD_VERSION = 112,
|
||||
AUTH_TEMP_OUTAGE = 113,
|
||||
AUTH_CANT_DOWNLOAD_MODULE = 114,
|
||||
AUTH_DUPLICATE_LOGON = 115,
|
||||
AUTH_BAD_CREDENTIALS_2 = 116,
|
||||
AUTH_VERSION_CHECK_SUCCEEDED = 117,
|
||||
AUTH_BAD_VERSION_HASH = 118,
|
||||
AUTH_CANT_RETRIEVE_PORTAL_LIST = 119,
|
||||
AUTH_DARK_PORTAL_DOES_NOT_EXIST = 120,
|
||||
AUTH_DARK_PORTAL_FILE_CORRUPTED = 121,
|
||||
AUTH_BATTLENET_MAINTENANCE = 122,
|
||||
AUTH_LOGON_TOO_FAST = 123,
|
||||
AUTH_USE_GRUNT_LOGON = 124,
|
||||
AUTH_NO_GAME_ACCOUNTS_IN_REGION = 140,
|
||||
AUTH_ACCOUNT_LOCKED = 141,
|
||||
|
||||
LOGIN_SERVER_BUSY = 200,
|
||||
LOGIN_NO_GAME_ACCOUNT = 201,
|
||||
LOGIN_BANNED = 202,
|
||||
LOGIN_SUSPENDED = 203,
|
||||
LOGIN_GAME_ACCOUNT_LOCKED = 204,
|
||||
LOGIN_ALREADY_ONLINE = 205,
|
||||
LOGIN_NOTIME = 206,
|
||||
LOGIN_EXPIRED = 207,
|
||||
LOGIN_EXPIRED_2 = 208,
|
||||
LOGIN_PARENTALCONTROL = 209,
|
||||
LOGIN_TRIAL_EXPIRED = 210,
|
||||
LOGIN_ANTI_INDULGENCE = 211,
|
||||
LOGIN_INCORRECT_REGION = 212,
|
||||
LOGIN_LOCKED_ENFORCED = 213,
|
||||
LOGIN_CHARGEBACK = 214,
|
||||
LOGIN_IGR_WITHOUT_BNET = 215,
|
||||
LOGIN_UNLOCKABLE_LOCK = 216,
|
||||
LOGIN_IGR_REQUIRED = 217,
|
||||
LOGIN_PAYMENT_CHANGED = 218,
|
||||
LOGIN_INVALID_PAYMENT = 219,
|
||||
LOGIN_INVALID_ACCOUNT_STATE = 220
|
||||
};
|
||||
}
|
||||
|
||||
enum ExpansionFlags
|
||||
{
|
||||
POST_BC_EXP_FLAG = 0x2,
|
||||
@@ -92,6 +182,7 @@ namespace AuthHelper
|
||||
bool IsAcceptedClientBuild(int build);
|
||||
bool IsPostBCAcceptedClientBuild(int build);
|
||||
bool IsPreBCAcceptedClientBuild(int build);
|
||||
bool IsBuildSupportingBattlenet(int build);
|
||||
}
|
||||
|
||||
#endif
|
||||
|
||||
@@ -151,7 +151,8 @@ extern int main(int argc, char** argv)
|
||||
}
|
||||
|
||||
// Launch the listening network socket
|
||||
RealmAcceptor acceptor;
|
||||
RealmAcceptor<AuthSocket> acceptor;
|
||||
RealmAcceptor<Battlenet::Socket> bnetacceptor;
|
||||
|
||||
int32 rmport = sConfigMgr->GetIntDefault("RealmServerPort", 3724);
|
||||
if (rmport < 0 || rmport > 0xFFFF)
|
||||
@@ -170,6 +171,13 @@ extern int main(int argc, char** argv)
|
||||
return 1;
|
||||
}
|
||||
|
||||
bind_addr.set_port_number(1119);
|
||||
if (bnetacceptor.open(bind_addr, ACE_Reactor::instance(), ACE_NONBLOCK) == -1)
|
||||
{
|
||||
TC_LOG_ERROR("server.authserver", "Auth server can not bind to %s:%d", bind_ip.c_str(), 1119);
|
||||
return 1;
|
||||
}
|
||||
|
||||
// Initialize the signal handlers
|
||||
AuthServerSignalHandler SignalINT, SignalTERM;
|
||||
|
||||
@@ -246,6 +254,8 @@ extern int main(int argc, char** argv)
|
||||
#endif
|
||||
#endif
|
||||
|
||||
sBattlenetMgr->Load();
|
||||
|
||||
// maximum counter for next ping
|
||||
uint32 numLoops = (sConfigMgr->GetIntDefault("MaxPingTime", 30) * (MINUTE * 1000000 / 100000));
|
||||
uint32 loopCounter = 0;
|
||||
|
||||
@@ -18,9 +18,29 @@
|
||||
|
||||
#include "Common.h"
|
||||
#include "RealmList.h"
|
||||
#include "BattlenetManager.h"
|
||||
#include "Database/DatabaseEnv.h"
|
||||
#include "Util.h"
|
||||
|
||||
RealmList::RealmList() : m_UpdateInterval(0), m_NextUpdateTime(time(NULL)) { }
|
||||
ACE_INET_Addr const& Realm::GetAddressForClient(ACE_INET_Addr const& clientAddr) const
|
||||
{
|
||||
// Attempt to send best address for client
|
||||
if (clientAddr.is_loopback())
|
||||
// Assume that user connecting from the machine that authserver is located on
|
||||
// has all realms available in his local network
|
||||
return LocalAddress;
|
||||
|
||||
// Check if connecting client is in the same network
|
||||
if (IsIPAddrInNetwork(LocalAddress, clientAddr, LocalSubnetMask))
|
||||
return LocalAddress;
|
||||
|
||||
// Return external IP
|
||||
return ExternalAddress;
|
||||
}
|
||||
|
||||
RealmList::RealmList() : m_UpdateInterval(0), m_NextUpdateTime(time(NULL))
|
||||
{
|
||||
}
|
||||
|
||||
// Load the realm list from the database
|
||||
void RealmList::Initialize(uint32 updateInterval)
|
||||
@@ -31,7 +51,7 @@ void RealmList::Initialize(uint32 updateInterval)
|
||||
UpdateRealms(true);
|
||||
}
|
||||
|
||||
void RealmList::UpdateRealm(uint32 id, const std::string& name, ACE_INET_Addr const& address, ACE_INET_Addr const& localAddr, ACE_INET_Addr const& localSubmask, uint8 icon, RealmFlags flag, uint8 timezone, AccountTypes allowedSecurityLevel, float popu, uint32 build)
|
||||
void RealmList::UpdateRealm(uint32 id, const std::string& name, ACE_INET_Addr const& address, ACE_INET_Addr const& localAddr, ACE_INET_Addr const& localSubmask, uint8 icon, RealmFlags flag, uint8 timezone, AccountTypes allowedSecurityLevel, float popu, uint32 build, uint8 region, uint8 battlegroup)
|
||||
{
|
||||
// Create new if not exist or update existed
|
||||
Realm& realm = m_realms[name];
|
||||
@@ -49,6 +69,8 @@ void RealmList::UpdateRealm(uint32 id, const std::string& name, ACE_INET_Addr co
|
||||
realm.LocalAddress = localAddr;
|
||||
realm.LocalSubnetMask = localSubmask;
|
||||
realm.gamebuild = build;
|
||||
realm.Region = region;
|
||||
realm.Battlegroup = battlegroup;
|
||||
}
|
||||
|
||||
void RealmList::UpdateIfNeed()
|
||||
@@ -91,12 +113,14 @@ void RealmList::UpdateRealms(bool init)
|
||||
uint8 allowedSecurityLevel = fields[9].GetUInt8();
|
||||
float pop = fields[10].GetFloat();
|
||||
uint32 build = fields[11].GetUInt32();
|
||||
uint8 region = fields[12].GetUInt8();
|
||||
uint8 battlegroup = fields[13].GetUInt8();
|
||||
|
||||
ACE_INET_Addr externalAddr(port, externalAddress.c_str(), AF_INET);
|
||||
ACE_INET_Addr localAddr(port, localAddress.c_str(), AF_INET);
|
||||
ACE_INET_Addr submask(0, localSubmask.c_str(), AF_INET);
|
||||
|
||||
UpdateRealm(realmId, name, externalAddr, localAddr, submask, icon, flag, timezone, (allowedSecurityLevel <= SEC_ADMINISTRATOR ? AccountTypes(allowedSecurityLevel) : SEC_ADMINISTRATOR), pop, build);
|
||||
UpdateRealm(realmId, name, externalAddr, localAddr, submask, icon, flag, timezone, (allowedSecurityLevel <= SEC_ADMINISTRATOR ? AccountTypes(allowedSecurityLevel) : SEC_ADMINISTRATOR), pop, build, region, battlegroup);
|
||||
|
||||
if (init)
|
||||
TC_LOG_INFO("server.authserver", "Added realm \"%s\" at %s:%u.", name.c_str(), m_realms[name].ExternalAddress.get_host_addr(), port);
|
||||
@@ -104,3 +128,16 @@ void RealmList::UpdateRealms(bool init)
|
||||
while (result->NextRow());
|
||||
}
|
||||
}
|
||||
|
||||
Realm const* RealmList::GetRealm(Battlenet::RealmId const& id) const
|
||||
{
|
||||
auto itr = std::find_if(m_realms.begin(), m_realms.end(), [id](RealmMap::value_type const& pair)
|
||||
{
|
||||
return pair.second.Region == id.Region && pair.second.Battlegroup == id.Battlegroup && pair.second.m_ID == id.Index;
|
||||
});
|
||||
|
||||
if (itr != m_realms.end())
|
||||
return &itr->second;
|
||||
|
||||
return NULL;
|
||||
}
|
||||
|
||||
@@ -51,8 +51,17 @@ struct Realm
|
||||
AccountTypes allowedSecurityLevel;
|
||||
float populationLevel;
|
||||
uint32 gamebuild;
|
||||
uint8 Region;
|
||||
uint8 Battlegroup;
|
||||
|
||||
ACE_INET_Addr const& GetAddressForClient(ACE_INET_Addr const& clientAddr) const;
|
||||
};
|
||||
|
||||
namespace Battlenet
|
||||
{
|
||||
struct RealmId;
|
||||
}
|
||||
|
||||
/// Storage object for the list of realms on the server
|
||||
class RealmList
|
||||
{
|
||||
@@ -71,10 +80,11 @@ public:
|
||||
RealmMap::const_iterator begin() const { return m_realms.begin(); }
|
||||
RealmMap::const_iterator end() const { return m_realms.end(); }
|
||||
uint32 size() const { return m_realms.size(); }
|
||||
Realm const* GetRealm(Battlenet::RealmId const& id) const;
|
||||
|
||||
private:
|
||||
void UpdateRealms(bool init=false);
|
||||
void UpdateRealm(uint32 id, const std::string& name, ACE_INET_Addr const& address, ACE_INET_Addr const& localAddr, ACE_INET_Addr const& localSubmask, uint8 icon, RealmFlags flag, uint8 timezone, AccountTypes allowedSecurityLevel, float popu, uint32 build);
|
||||
void UpdateRealm(uint32 id, const std::string& name, ACE_INET_Addr const& address, ACE_INET_Addr const& localAddr, ACE_INET_Addr const& localSubmask, uint8 icon, RealmFlags flag, uint8 timezone, AccountTypes allowedSecurityLevel, float popu, uint32 build, uint8 region, uint8 battlegroup);
|
||||
|
||||
RealmMap m_realms;
|
||||
uint32 m_UpdateInterval;
|
||||
|
||||
@@ -293,19 +293,11 @@ void AuthSocket::_SetVSFields(const std::string& rI)
|
||||
x.SetBinary(sha.GetDigest(), sha.GetLength());
|
||||
v = g.ModExp(x, N);
|
||||
|
||||
// No SQL injection (username escaped)
|
||||
char *v_hex, *s_hex;
|
||||
v_hex = v.AsHexStr();
|
||||
s_hex = s.AsHexStr();
|
||||
|
||||
PreparedStatement* stmt = LoginDatabase.GetPreparedStatement(LOGIN_UPD_VS);
|
||||
stmt->setString(0, v_hex);
|
||||
stmt->setString(1, s_hex);
|
||||
stmt->setString(0, v.AsHexStr());
|
||||
stmt->setString(1, s.AsHexStr());
|
||||
stmt->setString(2, _login);
|
||||
LoginDatabase.Execute(stmt);
|
||||
|
||||
OPENSSL_free(v_hex);
|
||||
OPENSSL_free(s_hex);
|
||||
}
|
||||
|
||||
// Logon Challenge command handler
|
||||
@@ -488,7 +480,9 @@ bool AuthSocket::_HandleLogonChallenge()
|
||||
unk3.SetRand(16 * 8);
|
||||
|
||||
// Fill the response packet with the result
|
||||
if (AuthHelper::IsAcceptedClientBuild(_build))
|
||||
if (fields[9].GetUInt32() && AuthHelper::IsBuildSupportingBattlenet(_build))
|
||||
pkt << uint8(WOW_FAIL_USE_BATTLENET);
|
||||
else if (AuthHelper::IsAcceptedClientBuild(_build))
|
||||
pkt << uint8(WOW_SUCCESS);
|
||||
else
|
||||
pkt << uint8(WOW_FAIL_VERSION_INVALID);
|
||||
@@ -650,19 +644,14 @@ bool AuthSocket::_HandleLogonProof()
|
||||
TC_LOG_DEBUG("server.authserver", "'%s:%d' User '%s' successfully authenticated", socket().getRemoteAddress().c_str(), socket().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
|
||||
// No SQL injection (escaped user name) and IP address as received by socket
|
||||
const char *K_hex = K.AsHexStr();
|
||||
|
||||
PreparedStatement *stmt = LoginDatabase.GetPreparedStatement(LOGIN_UPD_LOGONPROOF);
|
||||
stmt->setString(0, K_hex);
|
||||
stmt->setString(0, K.AsHexStr());
|
||||
stmt->setString(1, socket().getRemoteAddress().c_str());
|
||||
stmt->setUInt32(2, GetLocaleByName(_localizationName));
|
||||
stmt->setString(3, _os);
|
||||
stmt->setString(4, _login);
|
||||
LoginDatabase.DirectExecute(stmt);
|
||||
|
||||
OPENSSL_free((void*)K_hex);
|
||||
|
||||
// Finish SRP6 and send the final result to the client
|
||||
sha.Initialize();
|
||||
sha.UpdateBigNumbers(&A, &M, &K, NULL);
|
||||
@@ -693,7 +682,7 @@ bool AuthSocket::_HandleLogonProof()
|
||||
memcpy(proof.M2, sha.GetDigest(), 20);
|
||||
proof.cmd = AUTH_LOGON_PROOF;
|
||||
proof.error = 0;
|
||||
proof.unk1 = 0x00800000; // Accountflags. 0x01 = GM, 0x08 = Trial, 0x00800000 = Pro pass (arena tournament)
|
||||
proof.unk1 = GAMEACCOUNT_FLAG_PROPASS_LOCK;
|
||||
proof.unk2 = 0x00; // SurveyId
|
||||
proof.unk3 = 0x00;
|
||||
socket().send((char *)&proof, sizeof(proof));
|
||||
@@ -879,28 +868,6 @@ bool AuthSocket::_HandleReconnectProof()
|
||||
}
|
||||
}
|
||||
|
||||
ACE_INET_Addr const& AuthSocket::GetAddressForClient(Realm const& realm, ACE_INET_Addr const& clientAddr)
|
||||
{
|
||||
// Attempt to send best address for client
|
||||
if (clientAddr.is_loopback())
|
||||
{
|
||||
// Try guessing if realm is also connected locally
|
||||
if (realm.LocalAddress.is_loopback() || realm.ExternalAddress.is_loopback())
|
||||
return clientAddr;
|
||||
|
||||
// Assume that user connecting from the machine that authserver is located on
|
||||
// has all realms available in his local network
|
||||
return realm.LocalAddress;
|
||||
}
|
||||
|
||||
// Check if connecting client is in the same network
|
||||
if (IsIPAddrInNetwork(realm.LocalAddress, clientAddr, realm.LocalSubnetMask))
|
||||
return realm.LocalAddress;
|
||||
|
||||
// Return external IP
|
||||
return realm.ExternalAddress;
|
||||
}
|
||||
|
||||
// Realm List command handler
|
||||
bool AuthSocket::_HandleRealmList()
|
||||
{
|
||||
@@ -981,12 +948,12 @@ bool AuthSocket::_HandleRealmList()
|
||||
pkt << lock; // if 1, then realm locked
|
||||
pkt << uint8(flag); // RealmFlags
|
||||
pkt << name;
|
||||
pkt << GetAddressString(GetAddressForClient(realm, clientAddr));
|
||||
pkt << GetAddressString(realm.GetAddressForClient(clientAddr));
|
||||
pkt << realm.populationLevel;
|
||||
pkt << AmountOfCharacters;
|
||||
pkt << realm.timezone; // realm category
|
||||
if (_expversion & POST_BC_EXP_FLAG) // 2.x and 3.x clients
|
||||
pkt << uint8(0x2C); // unk, may be realm number/id?
|
||||
pkt << uint8(realm.m_ID);
|
||||
else
|
||||
pkt << uint8(0x0); // 1.12.1 and 1.12.2 clients
|
||||
|
||||
|
||||
@@ -39,8 +39,6 @@ public:
|
||||
virtual void OnAccept(void);
|
||||
virtual void OnClose(void);
|
||||
|
||||
static ACE_INET_Addr const& GetAddressForClient(Realm const& realm, ACE_INET_Addr const& clientAddr);
|
||||
|
||||
bool _HandleLogonChallenge();
|
||||
bool _HandleLogonProof();
|
||||
bool _HandleReconnectChallenge();
|
||||
|
||||
220
src/server/authserver/Server/BattlenetBitStream.h
Normal file
220
src/server/authserver/Server/BattlenetBitStream.h
Normal file
@@ -0,0 +1,220 @@
|
||||
/*
|
||||
* Copyright (C) 2008-2014 TrinityCore <http://www.trinitycore.org/>
|
||||
*
|
||||
* 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 __BATTLENETBITSTREAM_H__
|
||||
#define __BATTLENETBITSTREAM_H__
|
||||
|
||||
#include "ByteConverter.h"
|
||||
#include <exception>
|
||||
#include <string>
|
||||
#include <vector>
|
||||
#include <type_traits>
|
||||
#include <ace/Auto_Ptr.h>
|
||||
#include <ace/Stack_Trace.h>
|
||||
|
||||
namespace Battlenet
|
||||
{
|
||||
class BitStreamPositionException : public std::exception
|
||||
{
|
||||
public:
|
||||
BitStreamPositionException() : st(1) { }
|
||||
|
||||
char const* what() const
|
||||
{
|
||||
return st.c_str();
|
||||
}
|
||||
|
||||
ACE_Stack_Trace st;
|
||||
};
|
||||
|
||||
class BitStream
|
||||
{
|
||||
public:
|
||||
static uint32 const MaxSize = 0x1000;
|
||||
|
||||
// length : The maximum number of bytes to read
|
||||
BitStream(uint32 length) : _numBits(length * 8), _readPos(0), _writePos(0)
|
||||
{
|
||||
_buffer.resize(length, 0);
|
||||
}
|
||||
|
||||
BitStream() : _numBits(0), _readPos(0), _writePos(0)
|
||||
{
|
||||
_buffer.reserve(0x1000);
|
||||
}
|
||||
|
||||
void AlignToNextByte()
|
||||
{
|
||||
_readPos = (_readPos + 7) & ~7;
|
||||
_writePos = (_writePos + 7) & ~7;
|
||||
}
|
||||
|
||||
std::string ReadString(uint32 bitCount, int32 baseLength = 0)
|
||||
{
|
||||
uint32 len = Read<uint32>(bitCount) + baseLength;
|
||||
AlignToNextByte();
|
||||
std::string str(reinterpret_cast<char*>(&_buffer[_readPos >> 3]), len);
|
||||
_readPos += len * 8;
|
||||
return str;
|
||||
}
|
||||
|
||||
ACE_Auto_Array_Ptr<uint8> ReadBytes(uint32 count)
|
||||
{
|
||||
AlignToNextByte();
|
||||
if (_readPos + count * 8 > _numBits)
|
||||
throw BitStreamPositionException();
|
||||
|
||||
ACE_Auto_Array_Ptr<uint8> buf(new uint8[count]);
|
||||
memcpy(buf.get(), &_buffer[_readPos >> 3], count);
|
||||
_readPos += count * 8;
|
||||
return buf;
|
||||
}
|
||||
|
||||
float ReadFloat()
|
||||
{
|
||||
uint32 val = Read<uint32>(32);
|
||||
return *reinterpret_cast<float*>(&val);
|
||||
}
|
||||
|
||||
std::string ReadFourCC()
|
||||
{
|
||||
uint32 fcc = Read<uint32>(32);
|
||||
EndianConvertReverse(fcc);
|
||||
size_t len = 4;
|
||||
while (!(fcc & 0xFF))
|
||||
{
|
||||
fcc >>= 8;
|
||||
--len;
|
||||
}
|
||||
|
||||
return std::string(reinterpret_cast<char*>(&fcc), len);
|
||||
}
|
||||
|
||||
template<typename T>
|
||||
T Read(uint32 bitCount)
|
||||
{
|
||||
static_assert(std::is_integral<T>::value || std::is_enum<T>::value, "T must be an integer type");
|
||||
|
||||
uint64 ret = 0;
|
||||
while (bitCount != 0)
|
||||
{
|
||||
uint32 bitPos = (_readPos & 7);
|
||||
uint32 bitsLeftInByte = 8 - bitPos;
|
||||
if (bitsLeftInByte >= bitCount)
|
||||
bitsLeftInByte = bitCount;
|
||||
|
||||
bitCount -= bitsLeftInByte;
|
||||
ret |= (uint64)(_buffer[_readPos >> 3] >> bitPos & (uint32)((uint8)(1 << bitsLeftInByte) - 1)) << bitCount;
|
||||
_readPos += bitsLeftInByte;
|
||||
}
|
||||
|
||||
return static_cast<T>(ret);
|
||||
}
|
||||
|
||||
void WriteString(std::string const& str, uint32 bitCount, int32 baseLength = 0)
|
||||
{
|
||||
Write(str.length() + baseLength, bitCount);
|
||||
WriteBytes(str.c_str(), str.length());
|
||||
}
|
||||
|
||||
template<typename T>
|
||||
void WriteBytes(T* data, uint32 count)
|
||||
{
|
||||
AlignToNextByte();
|
||||
if (!count || !data)
|
||||
return;
|
||||
|
||||
if ((_writePos >> 3) + count > MaxSize)
|
||||
throw BitStreamPositionException();
|
||||
|
||||
_buffer.resize(_buffer.size() + count);
|
||||
memcpy(&_buffer[_writePos >> 3], data, count);
|
||||
_writePos += count * 8;
|
||||
}
|
||||
|
||||
void WriteFloat(float value)
|
||||
{
|
||||
uint32 intVal = *reinterpret_cast<uint32*>(&value);
|
||||
Write(intVal, 32);
|
||||
}
|
||||
|
||||
void WriteFourCC(std::string const& fcc)
|
||||
{
|
||||
uint32 intVal = *(uint32*)fcc.c_str();
|
||||
size_t len = fcc.length();
|
||||
EndianConvertReverse(intVal);
|
||||
// Add padding
|
||||
while (len++ < 4)
|
||||
intVal >>= 8;
|
||||
|
||||
Write(intVal, 32);
|
||||
}
|
||||
|
||||
template<typename T>
|
||||
void Write(T value, uint32 bitCount)
|
||||
{
|
||||
static_assert(std::is_integral<T>::value || std::is_enum<T>::value, "T must be an integer type");
|
||||
|
||||
if (_writePos + bitCount >= 8 * MaxSize)
|
||||
throw BitStreamPositionException();
|
||||
|
||||
while (bitCount != 0)
|
||||
{
|
||||
uint32 bitPos = (_writePos & 7);
|
||||
uint32 bitsLeftInByte = 8 - bitPos;
|
||||
if (bitsLeftInByte >= bitCount)
|
||||
bitsLeftInByte = bitCount;
|
||||
|
||||
bitCount -= bitsLeftInByte;
|
||||
|
||||
uint8 firstHalf = (uint8)(~(((uint8)(1 << bitsLeftInByte) - 1) << bitPos));
|
||||
uint8 secondHalf = (uint8)((((uint8)(1 << bitsLeftInByte) - 1) & (uint8)(value >> bitCount)) << bitPos);
|
||||
|
||||
if (_buffer.size() > (_writePos >> 3))
|
||||
_buffer[_writePos >> 3] = (uint8)(_buffer[_writePos >> 3] & firstHalf | secondHalf);
|
||||
else
|
||||
_buffer.push_back(secondHalf);
|
||||
|
||||
_writePos += bitsLeftInByte;
|
||||
}
|
||||
}
|
||||
|
||||
void SetReadPos(uint32 bits)
|
||||
{
|
||||
if (bits >= _numBits)
|
||||
throw BitStreamPositionException();
|
||||
|
||||
_readPos = bits;
|
||||
}
|
||||
|
||||
bool IsRead() const { return _readPos >= _numBits; }
|
||||
|
||||
uint8* GetBuffer() { return _buffer.data(); }
|
||||
|
||||
size_t GetSize() const { return _buffer.size(); }
|
||||
|
||||
void FinishReading() { _readPos = _numBits; }
|
||||
|
||||
private:
|
||||
std::vector<uint8> _buffer;
|
||||
uint32 _numBits;
|
||||
uint32 _readPos;
|
||||
uint32 _writePos;
|
||||
};
|
||||
}
|
||||
|
||||
#endif // __BATTLENETBITSTREAM_H__
|
||||
96
src/server/authserver/Server/BattlenetManager.cpp
Normal file
96
src/server/authserver/Server/BattlenetManager.cpp
Normal file
@@ -0,0 +1,96 @@
|
||||
/*
|
||||
* Copyright (C) 2008-2014 TrinityCore <http://www.trinitycore.org/>
|
||||
*
|
||||
* 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/>.
|
||||
*/
|
||||
|
||||
#include "BattlenetManager.h"
|
||||
#include "DatabaseEnv.h"
|
||||
|
||||
BattlenetMgr::~BattlenetMgr()
|
||||
{
|
||||
for (Battlenet::Component* component : _components)
|
||||
delete component;
|
||||
|
||||
for (auto const& m : _modules)
|
||||
delete m.second;
|
||||
}
|
||||
|
||||
void BattlenetMgr::Load()
|
||||
{
|
||||
LoadComponents();
|
||||
LoadModules();
|
||||
}
|
||||
|
||||
void BattlenetMgr::LoadComponents()
|
||||
{
|
||||
QueryResult result = LoginDatabase.Query("SELECT Program, Platform, Build FROM battlenet_components");
|
||||
if (result)
|
||||
{
|
||||
do
|
||||
{
|
||||
Field* fields = result->Fetch();
|
||||
Battlenet::Component* component = new Battlenet::Component();
|
||||
component->Program = fields[0].GetString();
|
||||
component->Platform = fields[1].GetString();
|
||||
component->Build = fields[2].GetUInt32();
|
||||
|
||||
_components.insert(component);
|
||||
_programs.insert(component->Program);
|
||||
_platforms.insert(component->Platform);
|
||||
|
||||
} while (result->NextRow());
|
||||
}
|
||||
}
|
||||
|
||||
void BattlenetMgr::LoadModules()
|
||||
{
|
||||
QueryResult result = LoginDatabase.Query("SELECT `Hash`, `Name`, `Type`, `System`, `Data` FROM battlenet_modules");
|
||||
if (result)
|
||||
{
|
||||
do
|
||||
{
|
||||
Field* fields = result->Fetch();
|
||||
Battlenet::ModuleInfo* module = new Battlenet::ModuleInfo();
|
||||
module->Type = fields[2].GetString();
|
||||
HexStrToByteArray(fields[0].GetString(), module->ModuleId);
|
||||
std::string data = fields[4].GetString();
|
||||
module->DataSize = data.length() / 2;
|
||||
if (module->DataSize)
|
||||
{
|
||||
module->Data = new uint8[data.length() / 2];
|
||||
HexStrToByteArray(data, module->Data);
|
||||
}
|
||||
|
||||
_modules[{ fields[3].GetString(), fields[1].GetString() }] = module;
|
||||
} while (result->NextRow());
|
||||
}
|
||||
}
|
||||
|
||||
bool BattlenetMgr::HasComponent(Battlenet::Component const* component) const
|
||||
{
|
||||
for (Battlenet::Component const* c : _components)
|
||||
if (component->Program == c->Program && component->Platform == c->Platform && component->Build == c->Build)
|
||||
return true;
|
||||
|
||||
return false;
|
||||
}
|
||||
|
||||
Battlenet::ModuleInfo* BattlenetMgr::CreateModule(std::string const& os, std::string const& name) const
|
||||
{
|
||||
Battlenet::ModuleKey key { os, name };
|
||||
ASSERT(_modules.count(key));
|
||||
|
||||
return new Battlenet::ModuleInfo(*_modules.at(key));
|
||||
}
|
||||
111
src/server/authserver/Server/BattlenetManager.h
Normal file
111
src/server/authserver/Server/BattlenetManager.h
Normal file
@@ -0,0 +1,111 @@
|
||||
/*
|
||||
* Copyright (C) 2008-2014 TrinityCore <http://www.trinitycore.org/>
|
||||
*
|
||||
* 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 __BATTLENETMANAGER_H__
|
||||
#define __BATTLENETMANAGER_H__
|
||||
|
||||
#include "Define.h"
|
||||
#include <ace/Singleton.h>
|
||||
#include <string>
|
||||
#include <set>
|
||||
#include <map>
|
||||
|
||||
namespace Battlenet
|
||||
{
|
||||
struct Component
|
||||
{
|
||||
std::string Program;
|
||||
std::string Platform;
|
||||
uint32 Build;
|
||||
};
|
||||
|
||||
struct ModuleKey
|
||||
{
|
||||
std::string Platform;
|
||||
std::string Name;
|
||||
|
||||
bool operator<(ModuleKey const& right) const
|
||||
{
|
||||
int32 res = Platform.compare(right.Platform);
|
||||
if (res < 0)
|
||||
return true;
|
||||
else if (res > 0)
|
||||
return false;
|
||||
|
||||
return Name < right.Name;
|
||||
}
|
||||
};
|
||||
|
||||
struct ModuleInfo
|
||||
{
|
||||
ModuleInfo() : Region("EU"), DataSize(0), Data(nullptr) { }
|
||||
ModuleInfo(ModuleInfo const& right) : Type(right.Type), Region(right.Region), DataSize(right.DataSize), Data(nullptr)
|
||||
{
|
||||
memcpy(ModuleId, right.ModuleId, 32);
|
||||
if (DataSize)
|
||||
{
|
||||
Data = new uint8[DataSize];
|
||||
memcpy(Data, right.Data, DataSize);
|
||||
}
|
||||
}
|
||||
~ModuleInfo()
|
||||
{
|
||||
delete Data;
|
||||
}
|
||||
|
||||
std::string Type;
|
||||
std::string Region;
|
||||
uint8 ModuleId[32];
|
||||
uint32 DataSize;
|
||||
uint8* Data;
|
||||
};
|
||||
|
||||
struct RealmId
|
||||
{
|
||||
uint8 Region;
|
||||
uint8 Battlegroup;
|
||||
uint32 Index;
|
||||
uint32 Build;
|
||||
};
|
||||
}
|
||||
|
||||
class BattlenetMgr
|
||||
{
|
||||
friend class ACE_Singleton<BattlenetMgr, ACE_Null_Mutex>;
|
||||
BattlenetMgr() { }
|
||||
~BattlenetMgr();
|
||||
|
||||
public:
|
||||
void Load();
|
||||
bool HasComponent(Battlenet::Component const* component) const;
|
||||
bool HasProgram(std::string const& program) const { return _programs.count(program); }
|
||||
bool HasPlatform(std::string const& platform) const { return _platforms.count(platform); }
|
||||
Battlenet::ModuleInfo* CreateModule(std::string const& os, std::string const& name) const;
|
||||
|
||||
private:
|
||||
void LoadComponents();
|
||||
void LoadModules();
|
||||
|
||||
std::set<Battlenet::Component*> _components;
|
||||
std::set<std::string> _programs;
|
||||
std::set<std::string> _platforms;
|
||||
std::map<Battlenet::ModuleKey, Battlenet::ModuleInfo*> _modules;
|
||||
};
|
||||
|
||||
#define sBattlenetMgr ACE_Singleton<BattlenetMgr, ACE_Null_Mutex>::instance()
|
||||
|
||||
#endif // __BATTLENETMANAGER_H__
|
||||
42
src/server/authserver/Server/BattlenetPacketCrypt.cpp
Normal file
42
src/server/authserver/Server/BattlenetPacketCrypt.cpp
Normal file
@@ -0,0 +1,42 @@
|
||||
/*
|
||||
* Copyright (C) 2008-2014 TrinityCore <http://www.trinitycore.org/>
|
||||
*
|
||||
* 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/>.
|
||||
*/
|
||||
|
||||
#include "BattlenetPacketCrypt.h"
|
||||
#include "Cryptography/HmacHash.h"
|
||||
#include "Cryptography/BigNumber.h"
|
||||
|
||||
Battlenet::PacketCrypt::PacketCrypt() : ::PacketCrypt(SHA256_DIGEST_LENGTH)
|
||||
{
|
||||
}
|
||||
|
||||
void Battlenet::PacketCrypt::Init(BigNumber* K)
|
||||
{
|
||||
uint8 ServerEncryptionKey[SEED_KEY_SIZE] = { 0x68, 0xE0, 0xC7, 0x2E, 0xDD, 0xD6, 0xD2, 0xF3, 0x1E, 0x5A, 0xB1, 0x55, 0xB1, 0x8B, 0x63, 0x1E };
|
||||
uint8 ClientDecryptionKey[SEED_KEY_SIZE] = { 0xDE, 0xA9, 0x65, 0xAE, 0x54, 0x3A, 0x1E, 0x93, 0x9E, 0x69, 0x0C, 0xAA, 0x68, 0xDE, 0x78, 0x39 };
|
||||
|
||||
HmacSha256 serverEncryptHmac(K->GetNumBytes(), K->AsByteArray().get());
|
||||
serverEncryptHmac.UpdateData(ServerEncryptionKey, SEED_KEY_SIZE);
|
||||
serverEncryptHmac.Finalize();
|
||||
|
||||
HmacSha256 clientDecryptHmac(K->GetNumBytes(), K->AsByteArray().get());
|
||||
clientDecryptHmac.UpdateData(ClientDecryptionKey, SEED_KEY_SIZE);
|
||||
clientDecryptHmac.Finalize();
|
||||
|
||||
_clientDecrypt.Init(clientDecryptHmac.GetDigest());
|
||||
_serverEncrypt.Init(serverEncryptHmac.GetDigest());
|
||||
_initialized = true;
|
||||
}
|
||||
36
src/server/authserver/Server/BattlenetPacketCrypt.h
Normal file
36
src/server/authserver/Server/BattlenetPacketCrypt.h
Normal file
@@ -0,0 +1,36 @@
|
||||
/*
|
||||
* Copyright (C) 2008-2014 TrinityCore <http://www.trinitycore.org/>
|
||||
*
|
||||
* 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 __BATTLENETPACKETCRYPT_H__
|
||||
#define __BATTLENETPACKETCRYPT_H__
|
||||
|
||||
#include "PacketCrypt.h"
|
||||
|
||||
class BigNumber;
|
||||
|
||||
namespace Battlenet
|
||||
{
|
||||
class PacketCrypt : public ::PacketCrypt
|
||||
{
|
||||
public:
|
||||
PacketCrypt();
|
||||
|
||||
void Init(BigNumber* K) override;
|
||||
};
|
||||
}
|
||||
|
||||
#endif // __BATTLENETPACKETCRYPT_H__
|
||||
449
src/server/authserver/Server/BattlenetPackets.cpp
Normal file
449
src/server/authserver/Server/BattlenetPackets.cpp
Normal file
@@ -0,0 +1,449 @@
|
||||
/*
|
||||
* Copyright (C) 2008-2014 TrinityCore <http://www.trinitycore.org/>
|
||||
*
|
||||
* 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/>.
|
||||
*/
|
||||
|
||||
#include "BattlenetPackets.h"
|
||||
#include "Common.h"
|
||||
#include "Util.h"
|
||||
#include <limits>
|
||||
#include <sstream>
|
||||
|
||||
std::string Battlenet::PacketHeader::ToString() const
|
||||
{
|
||||
std::ostringstream stream;
|
||||
stream << "Battlenet::PacketHeader opcode: " << Opcode << ", channel: " << Channel;
|
||||
return stream.str();
|
||||
}
|
||||
|
||||
Battlenet::ServerPacket::ServerPacket(PacketHeader const& header) : Packet(header, *new BitStream())
|
||||
{
|
||||
_stream.Write(header.Opcode, 6);
|
||||
_stream.Write(1, 1);
|
||||
_stream.Write(header.Channel, 4);
|
||||
}
|
||||
|
||||
Battlenet::ServerPacket::~ServerPacket()
|
||||
{
|
||||
delete &_stream;
|
||||
}
|
||||
|
||||
void Battlenet::AuthChallenge::Read()
|
||||
{
|
||||
Program = _stream.ReadFourCC();
|
||||
Platform = _stream.ReadFourCC();
|
||||
Locale = _stream.ReadFourCC();
|
||||
|
||||
Components.resize(_stream.Read<uint32>(6));
|
||||
for (size_t i = 0; i < Components.size(); ++i)
|
||||
{
|
||||
Component& component = Components[i];
|
||||
component.Program = _stream.ReadFourCC();
|
||||
component.Platform = _stream.ReadFourCC();
|
||||
component.Build = _stream.Read<uint32>(32);
|
||||
}
|
||||
|
||||
if (_stream.Read<uint32>(1))
|
||||
Login = _stream.ReadString(9, 3);
|
||||
}
|
||||
|
||||
std::string Battlenet::AuthChallenge::ToString() const
|
||||
{
|
||||
std::ostringstream stream;
|
||||
stream << "Battlenet::AuthChallenge Program: " << Program << ", Platform: " << Platform << ", Locale: " << Locale;
|
||||
for (Component const& component : Components)
|
||||
stream << std::endl << "Battlenet::Component Program: " << component.Program << ", Platform: " << component.Platform << ", Build: " << component.Build;
|
||||
|
||||
if (!Login.empty())
|
||||
stream << std::endl << "Battlenet::AuthChallenge Login: " << Login;
|
||||
|
||||
return stream.str();
|
||||
}
|
||||
|
||||
void Battlenet::AuthResumeInfo::Read()
|
||||
{
|
||||
Program = _stream.ReadFourCC();
|
||||
Platform = _stream.ReadFourCC();
|
||||
Locale = _stream.ReadFourCC();
|
||||
|
||||
Components.resize(_stream.Read<uint32>(6));
|
||||
for (size_t i = 0; i < Components.size(); ++i)
|
||||
{
|
||||
Component& component = Components[i];
|
||||
component.Program = _stream.ReadFourCC();
|
||||
component.Platform = _stream.ReadFourCC();
|
||||
component.Build = _stream.Read<uint32>(32);
|
||||
}
|
||||
|
||||
Login = _stream.ReadString(9, 3);
|
||||
Region = _stream.Read<uint8>(8);
|
||||
GameAccountName = _stream.ReadString(5, 1);
|
||||
}
|
||||
|
||||
std::string Battlenet::AuthResumeInfo::ToString() const
|
||||
{
|
||||
std::ostringstream stream;
|
||||
stream << "Battlenet::AuthReconnect Program: " << Program << ", Platform: " << Platform << ", Locale: " << Locale;
|
||||
for (Component const& component : Components)
|
||||
stream << std::endl << "Battlenet::Component Program: " << component.Program << ", Platform: " << component.Platform << ", Build: " << component.Build;
|
||||
|
||||
stream << std::endl << "Battlenet::AuthReconnect Login: " << Login;
|
||||
stream << std::endl << "Battlenet::AuthReconnect Region: " << uint32(Region);
|
||||
stream << std::endl << "Battlenet::AuthReconnect GameAccountName: " << GameAccountName;
|
||||
|
||||
return stream.str();
|
||||
}
|
||||
|
||||
Battlenet::ProofRequest::~ProofRequest()
|
||||
{
|
||||
for (size_t i = 0; i < Modules.size(); ++i)
|
||||
delete Modules[i];
|
||||
}
|
||||
|
||||
void Battlenet::ProofRequest::Write()
|
||||
{
|
||||
_stream.Write(Modules.size(), 3);
|
||||
for (ModuleInfo const* info : Modules)
|
||||
{
|
||||
_stream.WriteBytes(info->Type.c_str(), 4);
|
||||
_stream.WriteFourCC(info->Region);
|
||||
_stream.WriteBytes(info->ModuleId, 32);
|
||||
_stream.Write(info->DataSize, 10);
|
||||
_stream.WriteBytes(info->Data, info->DataSize);
|
||||
}
|
||||
}
|
||||
|
||||
std::string Battlenet::ProofRequest::ToString() const
|
||||
{
|
||||
std::ostringstream stream;
|
||||
stream << "Battlenet::ProofRequest modules " << Modules.size();
|
||||
for (ModuleInfo const* module : Modules)
|
||||
stream << std::endl << "Battlenet::ModuleInfo Locale " << module->Region.c_str() << ", ModuleId " << ByteArrayToHexStr(module->ModuleId, 32) << ", DataSize " << module->DataSize << ", Data " << ByteArrayToHexStr(module->Data, module->DataSize);
|
||||
|
||||
return stream.str();
|
||||
}
|
||||
|
||||
Battlenet::ProofResponse::~ProofResponse()
|
||||
{
|
||||
for (size_t i = 0; i < Modules.size(); ++i)
|
||||
delete Modules[i];
|
||||
}
|
||||
|
||||
void Battlenet::ProofResponse::Read()
|
||||
{
|
||||
Modules.resize(_stream.Read<uint32>(3));
|
||||
for (size_t i = 0; i < Modules.size(); ++i)
|
||||
{
|
||||
BitStream*& dataStream = Modules[i];
|
||||
dataStream = new BitStream(_stream.Read<uint32>(10));
|
||||
memcpy(dataStream->GetBuffer(), _stream.ReadBytes(dataStream->GetSize()).get(), dataStream->GetSize());
|
||||
}
|
||||
}
|
||||
|
||||
std::string Battlenet::ProofResponse::ToString() const
|
||||
{
|
||||
std::ostringstream stream;
|
||||
stream << "Battlenet::ProofResponse Modules " << Modules.size();
|
||||
for (BitStream* module : Modules)
|
||||
{
|
||||
std::string hexStr = ByteArrayToHexStr(module->GetBuffer(), module->GetSize());
|
||||
stream << std::endl << "Battlenet::ProofResponse::ModuleData Size: " << module->GetSize() << ", Data: " << hexStr;
|
||||
}
|
||||
|
||||
return stream.str();
|
||||
}
|
||||
|
||||
Battlenet::AuthComplete::~AuthComplete()
|
||||
{
|
||||
for (ModuleInfo* m : Modules)
|
||||
delete m;
|
||||
}
|
||||
|
||||
void Battlenet::AuthComplete::Write()
|
||||
{
|
||||
_stream.Write(Result != 0, 1);
|
||||
if (Result == 0)
|
||||
{
|
||||
_stream.Write(Modules.size(), 3);
|
||||
for (size_t i = 0; i < Modules.size(); ++i)
|
||||
{
|
||||
ModuleInfo* info = Modules[i];
|
||||
_stream.WriteBytes(info->Type.c_str(), 4);
|
||||
_stream.WriteFourCC(info->Region);
|
||||
_stream.WriteBytes(info->ModuleId, 32);
|
||||
_stream.Write(info->DataSize, 10);
|
||||
_stream.WriteBytes(info->Data, info->DataSize);
|
||||
}
|
||||
|
||||
_stream.Write(PingTimeout + std::numeric_limits<int32>::min(), 32);
|
||||
_stream.Write(1, 1);
|
||||
// if written == 1
|
||||
{
|
||||
_stream.Write(1, 1);
|
||||
// if written == 1
|
||||
{
|
||||
_stream.Write(Threshold, 32);
|
||||
_stream.Write(Rate, 32);
|
||||
}
|
||||
}
|
||||
|
||||
_stream.WriteString(FirstName, 8); // First name
|
||||
_stream.WriteString(LastName, 8); // Last name - not set for WoW
|
||||
|
||||
_stream.Write(AccountId, 32);
|
||||
_stream.Write(Region, 8);
|
||||
_stream.Write(0, 64);
|
||||
|
||||
_stream.Write(GameAccountRegion, 8);
|
||||
_stream.WriteString(GameAccountName, 5, -1);
|
||||
_stream.Write(GameAccountFlags, 64);
|
||||
|
||||
_stream.Write(0, 32);
|
||||
}
|
||||
else
|
||||
{
|
||||
_stream.Write(!Modules.empty(), 1);
|
||||
if (!Modules.empty())
|
||||
{
|
||||
ModuleInfo* info = Modules[0];
|
||||
_stream.WriteBytes(info->Type.c_str(), 4);
|
||||
_stream.WriteFourCC(info->Region);
|
||||
_stream.WriteBytes(info->ModuleId, 32);
|
||||
}
|
||||
|
||||
_stream.Write(ErrorType, 2);
|
||||
if (ErrorType == 1)
|
||||
{
|
||||
_stream.Write(Result, 16);
|
||||
_stream.Write(0x80000000, 32);
|
||||
}
|
||||
}
|
||||
}
|
||||
|
||||
std::string Battlenet::AuthComplete::ToString() const
|
||||
{
|
||||
std::ostringstream stream;
|
||||
stream << "Battlenet::AuthComplete AuthResult " << Result << " PingTimeout " << PingTimeout << " Threshold " << Threshold << " Rate " << Rate
|
||||
<< " FirstName " << FirstName << " LastName " << LastName << " AccountId " << AccountId << " Region " << uint32(Region) << " GameAccountName " << GameAccountName
|
||||
<< " GameAccountFlags " << GameAccountFlags << " Modules " << Modules.size();
|
||||
|
||||
for (ModuleInfo const* module : Modules)
|
||||
stream << std::endl << "Battlenet::ModuleInfo Locale " << module->Region.c_str() << ", ModuleId " << ByteArrayToHexStr(module->ModuleId, 32) << ", DataSize " << module->DataSize << ", Data " << ByteArrayToHexStr(module->Data, module->DataSize);
|
||||
|
||||
return stream.str();
|
||||
}
|
||||
|
||||
void Battlenet::AuthComplete::SetAuthResult(AuthResult result)
|
||||
{
|
||||
ErrorType = result != AUTH_OK ? 1 : 0;
|
||||
Result = result;
|
||||
}
|
||||
|
||||
Battlenet::AuthResume::~AuthResume()
|
||||
{
|
||||
for (ModuleInfo* m : Modules)
|
||||
delete m;
|
||||
}
|
||||
|
||||
void Battlenet::AuthResume::Write()
|
||||
{
|
||||
_stream.Write(Result != 0, 1);
|
||||
if (Result == 0)
|
||||
{
|
||||
_stream.Write(Modules.size(), 3);
|
||||
for (size_t i = 0; i < Modules.size(); ++i)
|
||||
{
|
||||
ModuleInfo* info = Modules[i];
|
||||
_stream.WriteBytes(info->Type.c_str(), 4);
|
||||
_stream.WriteFourCC(info->Region);
|
||||
_stream.WriteBytes(info->ModuleId, 32);
|
||||
_stream.Write(info->DataSize, 10);
|
||||
_stream.WriteBytes(info->Data, info->DataSize);
|
||||
}
|
||||
|
||||
_stream.Write(PingTimeout + std::numeric_limits<int32>::min(), 32);
|
||||
_stream.Write(1, 1);
|
||||
// if written == 1
|
||||
{
|
||||
_stream.Write(1, 1);
|
||||
// if written == 1
|
||||
{
|
||||
_stream.Write(Threshold, 32);
|
||||
_stream.Write(Rate, 32);
|
||||
}
|
||||
}
|
||||
}
|
||||
else
|
||||
{
|
||||
_stream.Write(!Modules.empty(), 1);
|
||||
if (!Modules.empty())
|
||||
{
|
||||
ModuleInfo* info = Modules[0];
|
||||
_stream.WriteBytes(info->Type.c_str(), 4);
|
||||
_stream.WriteFourCC(info->Region);
|
||||
_stream.WriteBytes(info->ModuleId, 32);
|
||||
}
|
||||
|
||||
_stream.Write(ErrorType, 2);
|
||||
if (ErrorType == 1)
|
||||
{
|
||||
_stream.Write(Result, 16);
|
||||
_stream.Write(0x80000000, 32);
|
||||
}
|
||||
}
|
||||
}
|
||||
|
||||
std::string Battlenet::AuthResume::ToString() const
|
||||
{
|
||||
std::ostringstream stream;
|
||||
stream << "Battlenet::AuthResume AuthResult " << Result << " PingTimeout " << PingTimeout << " Threshold " << Threshold << " Rate " << Rate << " Modules " << Modules.size();
|
||||
for (ModuleInfo const* module : Modules)
|
||||
stream << std::endl << "Battlenet::ModuleInfo Locale " << module->Region.c_str() << ", ModuleId " << ByteArrayToHexStr(module->ModuleId, 32) << ", DataSize " << module->DataSize << ", Data " << ByteArrayToHexStr(module->Data, module->DataSize);
|
||||
|
||||
return stream.str();
|
||||
}
|
||||
|
||||
void Battlenet::AuthResume::SetAuthResult(AuthResult result)
|
||||
{
|
||||
ErrorType = result != AUTH_OK ? 1 : 0;
|
||||
Result = result;
|
||||
}
|
||||
|
||||
Battlenet::RealmCharacterCounts::~RealmCharacterCounts()
|
||||
{
|
||||
for (ServerPacket* realmData : RealmData)
|
||||
delete realmData;
|
||||
}
|
||||
|
||||
void Battlenet::RealmCharacterCounts::Write()
|
||||
{
|
||||
_stream.Write(false, 1); // failure
|
||||
_stream.Write(CharacterCounts.size(), 7);
|
||||
for (CharacterCountEntry const& entry : CharacterCounts)
|
||||
{
|
||||
_stream.Write(entry.Realm.Battlegroup, 8);
|
||||
_stream.Write(entry.Realm.Index, 32);
|
||||
_stream.Write(entry.Realm.Region, 8);
|
||||
_stream.Write(entry.CharacterCount, 16);
|
||||
}
|
||||
|
||||
for (ServerPacket* realmData : RealmData)
|
||||
{
|
||||
realmData->Write();
|
||||
_stream.WriteBytes(realmData->GetData(), realmData->GetSize());
|
||||
}
|
||||
}
|
||||
|
||||
std::string Battlenet::RealmCharacterCounts::ToString() const
|
||||
{
|
||||
std::ostringstream stream;
|
||||
stream << "Battlenet::RealmCharacterCounts Realms " << CharacterCounts.size();
|
||||
|
||||
for (CharacterCountEntry const& entry : CharacterCounts)
|
||||
stream << std::endl << "Region " << uint32(entry.Realm.Region) << " Battlegroup " << uint32(entry.Realm.Region) << " Index " << entry.Realm.Index << " Characters " << entry.CharacterCount;
|
||||
|
||||
for (ServerPacket* realmData : RealmData)
|
||||
stream << std::endl << realmData->ToString();
|
||||
|
||||
return stream.str().c_str();
|
||||
}
|
||||
|
||||
void Battlenet::RealmUpdate::Write()
|
||||
{
|
||||
_stream.Write(true, 1); // Success
|
||||
_stream.Write(Type + -std::numeric_limits<int32>::min(), 32);
|
||||
_stream.WriteFloat(Population);
|
||||
_stream.Write(Flags, 8);
|
||||
_stream.Write(Lock, 8);
|
||||
_stream.Write(Timezone, 32);
|
||||
_stream.Write(!Version.empty(), 1);
|
||||
if (!Version.empty())
|
||||
{
|
||||
_stream.WriteString(Version, 5);
|
||||
_stream.Write(Build, 32);
|
||||
|
||||
uint32 ip = Address.get_ip_address();
|
||||
uint16 port = Address.get_port_number();
|
||||
|
||||
EndianConvertReverse(ip);
|
||||
EndianConvertReverse(port);
|
||||
|
||||
_stream.WriteBytes(&ip, 4);
|
||||
_stream.WriteBytes(&port, 2);
|
||||
}
|
||||
|
||||
_stream.WriteString(Name, 10);
|
||||
|
||||
_stream.Write(Battlegroup, 8);
|
||||
_stream.Write(Index, 32);
|
||||
_stream.Write(Region, 8);
|
||||
}
|
||||
|
||||
std::string Battlenet::RealmUpdate::ToString() const
|
||||
{
|
||||
std::ostringstream stream;
|
||||
stream << "Battlenet::RealmUpdate Timezone " << Timezone << " Population " << Population << " Lock " << uint32(Lock) << " Type " << Type << " Name " << Name
|
||||
<< " Flags " << uint32(Flags) << " Region " << uint32(Region) << " Battlegroup " << uint32(Battlegroup) << " Index " << Index;
|
||||
|
||||
if (!Version.empty())
|
||||
stream << " Version " << Version;
|
||||
|
||||
return stream.str().c_str();
|
||||
}
|
||||
|
||||
void Battlenet::RealmJoinRequest::Read()
|
||||
{
|
||||
Realm.Battlegroup = _stream.Read<uint8>(8);
|
||||
Realm.Index = _stream.Read<uint32>(32);
|
||||
Realm.Region = _stream.Read<uint8>(8);
|
||||
ClientSeed = _stream.Read<uint32>(32);
|
||||
}
|
||||
|
||||
std::string Battlenet::RealmJoinRequest::ToString() const
|
||||
{
|
||||
std::ostringstream stream;
|
||||
stream << "Battlenet::RealmJoinRequest ClientSeed " << ClientSeed << " Region " << uint32(Realm.Region) << " Battlegroup " << uint32(Realm.Battlegroup) << " Index " << Realm.Index;
|
||||
return stream.str().c_str();
|
||||
}
|
||||
|
||||
void Battlenet::RealmJoinResult::Write()
|
||||
{
|
||||
_stream.Write(0, 27);
|
||||
_stream.Write(0, 1); // Fail
|
||||
_stream.Write(ServerSeed, 32);
|
||||
_stream.Write(0, 5); // IPv6 addresses
|
||||
_stream.Write(IPv4.size(), 5);
|
||||
for (ACE_INET_Addr const& addr : IPv4)
|
||||
{
|
||||
uint32 ip = addr.get_ip_address();
|
||||
uint16 port = addr.get_port_number();
|
||||
|
||||
EndianConvertReverse(ip);
|
||||
EndianConvertReverse(port);
|
||||
|
||||
_stream.WriteBytes(&ip, 4);
|
||||
_stream.WriteBytes(&port, 2);
|
||||
}
|
||||
}
|
||||
|
||||
std::string Battlenet::RealmJoinResult::ToString() const
|
||||
{
|
||||
std::ostringstream stream;
|
||||
stream << "Battlenet::RealmJoinResult ServerSeed " << ServerSeed << " IPv4 Addresses " << IPv4.size();
|
||||
for (ACE_INET_Addr const& addr : IPv4)
|
||||
stream << std::endl << "Battlenet::RealmJoinResult::Address " << GetAddressString(addr);
|
||||
|
||||
return stream.str().c_str();
|
||||
}
|
||||
360
src/server/authserver/Server/BattlenetPackets.h
Normal file
360
src/server/authserver/Server/BattlenetPackets.h
Normal file
@@ -0,0 +1,360 @@
|
||||
/*
|
||||
* Copyright (C) 2008-2014 TrinityCore <http://www.trinitycore.org/>
|
||||
*
|
||||
* 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 __BATTLENETPACKETS_H__
|
||||
#define __BATTLENETPACKETS_H__
|
||||
|
||||
#include "AuthCodes.h"
|
||||
#include "BattlenetBitStream.h"
|
||||
#include "BattlenetManager.h"
|
||||
#include "Define.h"
|
||||
#include "Errors.h"
|
||||
#include <string>
|
||||
|
||||
namespace Battlenet
|
||||
{
|
||||
class BitStream;
|
||||
|
||||
enum Channel
|
||||
{
|
||||
AUTHENTICATION = 0,
|
||||
CREEP = 1,
|
||||
WOW = 2
|
||||
};
|
||||
|
||||
enum AuthOpcode
|
||||
{
|
||||
CMSG_AUTH_CHALLENGE = 0x0,
|
||||
CMSG_AUTH_RECONNECT = 0x1,
|
||||
CMSG_AUTH_PROOF_RESPONSE = 0x2,
|
||||
|
||||
SMSG_AUTH_COMPLETE = 0x0,
|
||||
SMSG_AUTH_RESUME = 0x1,
|
||||
SMSG_AUTH_PROOF_REQUEST = 0x2
|
||||
};
|
||||
|
||||
enum CreepOpcodes
|
||||
{
|
||||
CMSG_PING = 0x0,
|
||||
CMSG_ENABLE_ENCRYPTION = 0x5,
|
||||
CMSG_DISCONNECT = 0x6,
|
||||
CMSG_INVALID_PACKET = 0x9,
|
||||
|
||||
SMSG_PONG = 0x0
|
||||
};
|
||||
|
||||
enum WoWOpcodes
|
||||
{
|
||||
CMSG_REALM_UPDATE_SUBSCRIBE = 0x0,
|
||||
CMSG_REALM_UPDATE_UNSUBSCRIBE = 0x1,
|
||||
CMSG_JOIN_REQUEST = 0x8,
|
||||
|
||||
SMSG_CHARACTER_COUNTS = 0x0,
|
||||
SMSG_REALM_UPDATE = 0x2,
|
||||
SMSG_REALM_UPDATE_END = 0x3,
|
||||
SMSG_JOIN_RESULT = 0x8
|
||||
};
|
||||
|
||||
struct PacketHeader
|
||||
{
|
||||
PacketHeader(uint32 opcode, uint32 channel) : Opcode(opcode), Channel(channel) { }
|
||||
PacketHeader() : Opcode(0), Channel(AUTHENTICATION) { }
|
||||
|
||||
uint32 Opcode;
|
||||
int32 Channel;
|
||||
|
||||
bool operator<(PacketHeader const& right) const
|
||||
{
|
||||
if (Opcode < right.Opcode)
|
||||
return true;
|
||||
if (Opcode > right.Opcode)
|
||||
return false;
|
||||
|
||||
return Channel < right.Channel;
|
||||
}
|
||||
|
||||
bool operator==(PacketHeader const& right) const
|
||||
{
|
||||
return Opcode == right.Opcode && Channel == right.Channel;
|
||||
}
|
||||
|
||||
std::string ToString() const;
|
||||
};
|
||||
|
||||
class Packet
|
||||
{
|
||||
public:
|
||||
Packet(PacketHeader const& header, BitStream& stream) : _header(header), _stream(stream) { }
|
||||
virtual ~Packet() { }
|
||||
|
||||
PacketHeader const& GetHeader() const { return _header; }
|
||||
|
||||
virtual void Write() = 0;
|
||||
virtual void Read() = 0;
|
||||
|
||||
virtual std::string ToString() const = 0;
|
||||
|
||||
protected:
|
||||
PacketHeader _header;
|
||||
BitStream& _stream;
|
||||
|
||||
private:
|
||||
Packet(Packet const& right);
|
||||
Packet& operator=(Packet const& right);
|
||||
};
|
||||
|
||||
class ClientPacket : public Packet
|
||||
{
|
||||
public:
|
||||
ClientPacket(PacketHeader const& header, BitStream& stream) : Packet(header, stream) { }
|
||||
|
||||
void Write() override final { ASSERT(!"Write not implemented for this packet."); }
|
||||
};
|
||||
|
||||
class ServerPacket : public Packet
|
||||
{
|
||||
public:
|
||||
ServerPacket(PacketHeader const& header);
|
||||
~ServerPacket();
|
||||
|
||||
void Read() override final { ASSERT(!"Read not implemented for server packets."); }
|
||||
|
||||
uint8 const* GetData() const { return _stream.GetBuffer(); }
|
||||
size_t GetSize() const { return _stream.GetSize(); }
|
||||
};
|
||||
|
||||
class AuthChallenge final : public ClientPacket
|
||||
{
|
||||
public:
|
||||
AuthChallenge(PacketHeader const& header, BitStream& stream) : ClientPacket(header, stream)
|
||||
{
|
||||
ASSERT(header == PacketHeader(CMSG_AUTH_CHALLENGE, AUTHENTICATION) && "Invalid packet header for AuthChallenge");
|
||||
}
|
||||
|
||||
void Read() override;
|
||||
std::string ToString() const override;
|
||||
|
||||
std::string Program;
|
||||
std::string Platform;
|
||||
std::string Locale;
|
||||
std::vector<Component> Components;
|
||||
std::string Login;
|
||||
};
|
||||
|
||||
class AuthResumeInfo final : public ClientPacket
|
||||
{
|
||||
public:
|
||||
AuthResumeInfo(PacketHeader const& header, BitStream& stream) : ClientPacket(header, stream)
|
||||
{
|
||||
ASSERT(header == PacketHeader(CMSG_AUTH_RECONNECT, AUTHENTICATION) && "Invalid packet header for AuthResumeInfo");
|
||||
}
|
||||
|
||||
void Read() override;
|
||||
std::string ToString() const override;
|
||||
|
||||
std::string Program;
|
||||
std::string Platform;
|
||||
std::string Locale;
|
||||
std::vector<Component> Components;
|
||||
std::string Login;
|
||||
uint8 Region;
|
||||
std::string GameAccountName;
|
||||
};
|
||||
|
||||
class ProofRequest final : public ServerPacket
|
||||
{
|
||||
public:
|
||||
ProofRequest() : ServerPacket(PacketHeader(SMSG_AUTH_PROOF_REQUEST, AUTHENTICATION)) { }
|
||||
~ProofRequest();
|
||||
|
||||
void Write() override;
|
||||
std::string ToString() const override;
|
||||
|
||||
std::vector<ModuleInfo*> Modules;
|
||||
};
|
||||
|
||||
class ProofResponse final : public ClientPacket
|
||||
{
|
||||
public:
|
||||
ProofResponse(PacketHeader const& header, BitStream& stream) : ClientPacket(header, stream)
|
||||
{
|
||||
ASSERT(header == PacketHeader(CMSG_AUTH_PROOF_RESPONSE, AUTHENTICATION) && "Invalid packet header for ProofResponse");
|
||||
}
|
||||
|
||||
~ProofResponse();
|
||||
|
||||
void Read() override;
|
||||
std::string ToString() const override;
|
||||
|
||||
std::vector<BitStream*> Modules;
|
||||
};
|
||||
|
||||
class AuthComplete final : public ServerPacket
|
||||
{
|
||||
public:
|
||||
AuthComplete() : ServerPacket(PacketHeader(SMSG_AUTH_COMPLETE, AUTHENTICATION)),
|
||||
Result(AUTH_OK), ErrorType(0), PingTimeout(120000), Threshold(25000000), Rate(1000),
|
||||
FirstName(""), LastName(""), AccountId(0), Region(2), GameAccountRegion(2), GameAccountName("")
|
||||
{
|
||||
}
|
||||
|
||||
~AuthComplete();
|
||||
|
||||
void Write() override;
|
||||
std::string ToString() const override;
|
||||
|
||||
std::vector<ModuleInfo*> Modules;
|
||||
void SetAuthResult(AuthResult result);
|
||||
AuthResult Result;
|
||||
uint32 ErrorType;
|
||||
|
||||
int32 PingTimeout;
|
||||
uint32 Threshold;
|
||||
uint32 Rate;
|
||||
std::string FirstName;
|
||||
std::string LastName;
|
||||
uint32 AccountId;
|
||||
uint8 Region;
|
||||
uint8 GameAccountRegion;
|
||||
std::string GameAccountName;
|
||||
uint64 GameAccountFlags;
|
||||
};
|
||||
|
||||
class AuthResume final : public ServerPacket
|
||||
{
|
||||
public:
|
||||
AuthResume() : ServerPacket(PacketHeader(SMSG_AUTH_RESUME, AUTHENTICATION)),
|
||||
Result(AUTH_OK), ErrorType(0), PingTimeout(120000), Threshold(25000000), Rate(1000)
|
||||
{
|
||||
}
|
||||
|
||||
~AuthResume();
|
||||
|
||||
void Write() override;
|
||||
std::string ToString() const override;
|
||||
|
||||
std::vector<ModuleInfo*> Modules;
|
||||
void SetAuthResult(AuthResult result);
|
||||
AuthResult Result;
|
||||
uint32 ErrorType;
|
||||
|
||||
int32 PingTimeout;
|
||||
uint32 Threshold;
|
||||
uint32 Rate;
|
||||
};
|
||||
|
||||
class Pong final : public ServerPacket
|
||||
{
|
||||
public:
|
||||
Pong() : ServerPacket(PacketHeader(SMSG_PONG, CREEP))
|
||||
{
|
||||
}
|
||||
|
||||
void Write() override { }
|
||||
std::string ToString() const override { return "Battlenet::Pong"; }
|
||||
};
|
||||
|
||||
class RealmCharacterCounts final : public ServerPacket
|
||||
{
|
||||
public:
|
||||
RealmCharacterCounts() : ServerPacket(PacketHeader(SMSG_CHARACTER_COUNTS, WOW))
|
||||
{
|
||||
}
|
||||
~RealmCharacterCounts();
|
||||
|
||||
struct CharacterCountEntry
|
||||
{
|
||||
RealmId Realm;
|
||||
uint32 CharacterCount;
|
||||
};
|
||||
|
||||
void Write() override;
|
||||
std::string ToString() const override;
|
||||
|
||||
std::vector<CharacterCountEntry> CharacterCounts;
|
||||
std::vector<ServerPacket*> RealmData;
|
||||
};
|
||||
|
||||
class RealmUpdate final : public ServerPacket
|
||||
{
|
||||
public:
|
||||
RealmUpdate() : ServerPacket(PacketHeader(SMSG_REALM_UPDATE, WOW)),
|
||||
Timezone(0), Population(0.0f), Lock(0), Type(0), Name(""), Version(""),
|
||||
Address(), Flags(0), Region(0), Battlegroup(0), Index(0), Build(0)
|
||||
{
|
||||
}
|
||||
|
||||
void Write() override;
|
||||
std::string ToString() const override;
|
||||
|
||||
uint32 Timezone;
|
||||
float Population;
|
||||
uint8 Lock;
|
||||
uint32 Type;
|
||||
std::string Name;
|
||||
std::string Version;
|
||||
ACE_INET_Addr Address;
|
||||
uint8 Flags;
|
||||
uint8 Region;
|
||||
uint8 Battlegroup;
|
||||
uint32 Index;
|
||||
uint32 Build;
|
||||
};
|
||||
|
||||
class RealmUpdateComplete final : public ServerPacket
|
||||
{
|
||||
public:
|
||||
RealmUpdateComplete() : ServerPacket(PacketHeader(SMSG_REALM_UPDATE_END, WOW))
|
||||
{
|
||||
}
|
||||
|
||||
void Write() override { }
|
||||
std::string ToString() const override { return "Battlenet::RealmUpdateComplete"; }
|
||||
};
|
||||
|
||||
class RealmJoinRequest final : public ClientPacket
|
||||
{
|
||||
public:
|
||||
RealmJoinRequest(PacketHeader const& header, BitStream& stream) : ClientPacket(header, stream)
|
||||
{
|
||||
ASSERT(header == PacketHeader(CMSG_JOIN_REQUEST, WOW) && "Invalid packet header for RealmJoinRequest");
|
||||
}
|
||||
|
||||
void Read() override;
|
||||
std::string ToString() const override;
|
||||
|
||||
uint32 ClientSeed;
|
||||
uint32 Unknown;
|
||||
RealmId Realm;
|
||||
};
|
||||
|
||||
class RealmJoinResult final : public ServerPacket
|
||||
{
|
||||
public:
|
||||
RealmJoinResult() : ServerPacket(PacketHeader(SMSG_JOIN_RESULT, WOW)), ServerSeed(0)
|
||||
{
|
||||
}
|
||||
|
||||
void Write() override;
|
||||
std::string ToString() const override;
|
||||
|
||||
uint32 ServerSeed;
|
||||
std::vector<ACE_INET_Addr> IPv4;
|
||||
};
|
||||
}
|
||||
|
||||
#endif // __BATTLENETPACKETS_H__
|
||||
1011
src/server/authserver/Server/BattlenetSocket.cpp
Normal file
1011
src/server/authserver/Server/BattlenetSocket.cpp
Normal file
File diff suppressed because it is too large
Load Diff
120
src/server/authserver/Server/BattlenetSocket.h
Normal file
120
src/server/authserver/Server/BattlenetSocket.h
Normal file
@@ -0,0 +1,120 @@
|
||||
/*
|
||||
* Copyright (C) 2008-2014 TrinityCore <http://www.trinitycore.org/>
|
||||
*
|
||||
* 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 _BATTLENETSOCKET_H
|
||||
#define _BATTLENETSOCKET_H
|
||||
|
||||
#include "RealmSocket.h"
|
||||
#include "BattlenetPackets.h"
|
||||
#include "BattlenetPacketCrypt.h"
|
||||
#include "BigNumber.h"
|
||||
|
||||
class ACE_INET_Addr;
|
||||
|
||||
namespace Battlenet
|
||||
{
|
||||
struct PacketHeader;
|
||||
class BitStream;
|
||||
|
||||
enum ModuleType
|
||||
{
|
||||
MODULE_PASSWORD,
|
||||
MODULE_TOKEN,
|
||||
MODULE_THUMBPRINT,
|
||||
MODULE_SELECT_GAME_ACCOUNT,
|
||||
MODULE_RISK_FINGERPRINT,
|
||||
MODULE_RESUME,
|
||||
|
||||
MODULE_COUNT
|
||||
};
|
||||
|
||||
class Socket : public RealmSocket::Session
|
||||
{
|
||||
public:
|
||||
static uint32 const SRP6_V_Size;
|
||||
static uint32 const SRP6_S_Size;
|
||||
|
||||
explicit Socket(RealmSocket& socket);
|
||||
|
||||
typedef bool(Socket::*PacketHandler)(PacketHeader& socket, BitStream& packet);
|
||||
|
||||
// Auth
|
||||
bool HandleAuthChallenge(PacketHeader& header, BitStream& packet);
|
||||
bool HandleAuthReconnect(PacketHeader& header, BitStream& packet);
|
||||
bool HandleAuthProofResponse(PacketHeader& header, BitStream& packet);
|
||||
|
||||
// Creep
|
||||
bool HandlePing(PacketHeader& header, BitStream& packet);
|
||||
bool HandleEnableEncryption(PacketHeader& header, BitStream& packet);
|
||||
bool HandleDisconnect(PacketHeader& header, BitStream& packet);
|
||||
|
||||
// WoW
|
||||
bool HandleRealmUpdateSubscribe(PacketHeader& header, BitStream& packet);
|
||||
bool HandleRealmJoinRequest(PacketHeader& header, BitStream& packet);
|
||||
|
||||
void OnRead() override;
|
||||
void OnAccept() override;
|
||||
void OnClose() override;
|
||||
|
||||
void Send(ServerPacket& packet);
|
||||
|
||||
private:
|
||||
void _SetVSFields(std::string const& rI);
|
||||
|
||||
typedef bool(Socket::*ModuleHandler)(BitStream* dataStream, ServerPacket** response);
|
||||
static ModuleHandler const ModuleHandlers[MODULE_COUNT];
|
||||
|
||||
bool HandlePasswordModule(BitStream* dataStream, ServerPacket** response);
|
||||
bool HandleSelectGameAccountModule(BitStream* dataStream, ServerPacket** response);
|
||||
bool HandleRiskFingerprintModule(BitStream* dataStream, ServerPacket** response);
|
||||
bool HandleResumeModule(BitStream* dataStream, ServerPacket** response);
|
||||
bool UnhandledModule(BitStream* dataStream, ServerPacket** response);
|
||||
|
||||
RealmSocket& _socket;
|
||||
|
||||
uint32 _accountId;
|
||||
std::string _accountName;
|
||||
std::string _locale;
|
||||
std::string _os;
|
||||
uint32 _build;
|
||||
uint32 _gameAccountId;
|
||||
uint8 _gameAccountIndex;
|
||||
AccountTypes _accountSecurityLevel;
|
||||
|
||||
BigNumber N;
|
||||
BigNumber g;
|
||||
BigNumber k;
|
||||
|
||||
BigNumber I;
|
||||
BigNumber s;
|
||||
BigNumber v;
|
||||
|
||||
BigNumber b;
|
||||
BigNumber B;
|
||||
BigNumber K; // session key
|
||||
|
||||
BigNumber _reconnectProof;
|
||||
|
||||
std::queue<ModuleType> _modulesWaitingForData;
|
||||
|
||||
PacketCrypt _crypt;
|
||||
bool _authed;
|
||||
};
|
||||
|
||||
}
|
||||
|
||||
#endif // _BATTLENETSOCKET_H
|
||||
@@ -24,7 +24,9 @@
|
||||
|
||||
#include "RealmSocket.h"
|
||||
#include "AuthSocket.h"
|
||||
#include "BattlenetSocket.h"
|
||||
|
||||
template<class LoginType>
|
||||
class RealmAcceptor : public ACE_Acceptor<RealmSocket, ACE_SOCK_Acceptor>
|
||||
{
|
||||
public:
|
||||
@@ -42,7 +44,7 @@ protected:
|
||||
ACE_NEW_RETURN(sh, RealmSocket, -1);
|
||||
|
||||
sh->reactor(reactor());
|
||||
sh->set_session(new AuthSocket(*sh));
|
||||
sh->set_session(new LoginType(*sh));
|
||||
return 0;
|
||||
}
|
||||
|
||||
|
||||
@@ -32,17 +32,17 @@ AccountMgr::~AccountMgr()
|
||||
ClearRBAC();
|
||||
}
|
||||
|
||||
AccountOpResult AccountMgr::CreateAccount(std::string username, std::string password, std::string email = "")
|
||||
AccountOpResult AccountMgr::CreateAccount(std::string username, std::string password, std::string email /*= ""*/)
|
||||
{
|
||||
if (utf8length(username) > MAX_ACCOUNT_STR)
|
||||
return AOR_NAME_TOO_LONG; // username's too long
|
||||
return AccountOpResult::AOR_NAME_TOO_LONG; // username's too long
|
||||
|
||||
normalizeString(username);
|
||||
normalizeString(password);
|
||||
normalizeString(email);
|
||||
Utf8ToUpperOnlyLatin(username);
|
||||
Utf8ToUpperOnlyLatin(password);
|
||||
Utf8ToUpperOnlyLatin(email);
|
||||
|
||||
if (GetId(username))
|
||||
return AOR_NAME_ALREADY_EXIST; // username does already exist
|
||||
return AccountOpResult::AOR_NAME_ALREADY_EXIST; // username does already exist
|
||||
|
||||
PreparedStatement* stmt = LoginDatabase.GetPreparedStatement(LOGIN_INS_ACCOUNT);
|
||||
|
||||
@@ -56,7 +56,7 @@ AccountOpResult AccountMgr::CreateAccount(std::string username, std::string pass
|
||||
stmt = LoginDatabase.GetPreparedStatement(LOGIN_INS_REALM_CHARACTERS_INIT);
|
||||
LoginDatabase.Execute(stmt);
|
||||
|
||||
return AOR_OK; // everything's fine
|
||||
return AccountOpResult::AOR_OK; // everything's fine
|
||||
}
|
||||
|
||||
AccountOpResult AccountMgr::DeleteAccount(uint32 accountId)
|
||||
@@ -67,7 +67,7 @@ AccountOpResult AccountMgr::DeleteAccount(uint32 accountId)
|
||||
PreparedQueryResult result = LoginDatabase.Query(stmt);
|
||||
|
||||
if (!result)
|
||||
return AOR_NAME_NOT_EXIST;
|
||||
return AccountOpResult::AOR_NAME_NOT_EXIST;
|
||||
|
||||
// Obtain accounts characters
|
||||
stmt = CharacterDatabase.GetPreparedStatement(CHAR_SEL_CHARS_BY_ACCOUNT_ID);
|
||||
@@ -128,7 +128,7 @@ AccountOpResult AccountMgr::DeleteAccount(uint32 accountId)
|
||||
|
||||
LoginDatabase.CommitTransaction(trans);
|
||||
|
||||
return AOR_OK;
|
||||
return AccountOpResult::AOR_OK;
|
||||
}
|
||||
|
||||
AccountOpResult AccountMgr::ChangeUsername(uint32 accountId, std::string newUsername, std::string newPassword)
|
||||
@@ -139,16 +139,16 @@ AccountOpResult AccountMgr::ChangeUsername(uint32 accountId, std::string newUser
|
||||
PreparedQueryResult result = LoginDatabase.Query(stmt);
|
||||
|
||||
if (!result)
|
||||
return AOR_NAME_NOT_EXIST;
|
||||
return AccountOpResult::AOR_NAME_NOT_EXIST;
|
||||
|
||||
if (utf8length(newUsername) > MAX_ACCOUNT_STR)
|
||||
return AOR_NAME_TOO_LONG;
|
||||
return AccountOpResult::AOR_NAME_TOO_LONG;
|
||||
|
||||
if (utf8length(newPassword) > MAX_ACCOUNT_STR)
|
||||
return AOR_PASS_TOO_LONG;
|
||||
return AccountOpResult::AOR_PASS_TOO_LONG;
|
||||
|
||||
normalizeString(newUsername);
|
||||
normalizeString(newPassword);
|
||||
Utf8ToUpperOnlyLatin(newUsername);
|
||||
Utf8ToUpperOnlyLatin(newPassword);
|
||||
|
||||
stmt = LoginDatabase.GetPreparedStatement(LOGIN_UPD_USERNAME);
|
||||
|
||||
@@ -158,7 +158,7 @@ AccountOpResult AccountMgr::ChangeUsername(uint32 accountId, std::string newUser
|
||||
|
||||
LoginDatabase.Execute(stmt);
|
||||
|
||||
return AOR_OK;
|
||||
return AccountOpResult::AOR_OK;
|
||||
}
|
||||
|
||||
AccountOpResult AccountMgr::ChangePassword(uint32 accountId, std::string newPassword)
|
||||
@@ -166,13 +166,13 @@ AccountOpResult AccountMgr::ChangePassword(uint32 accountId, std::string newPass
|
||||
std::string username;
|
||||
|
||||
if (!GetName(accountId, username))
|
||||
return AOR_NAME_NOT_EXIST; // account doesn't exist
|
||||
return AccountOpResult::AOR_NAME_NOT_EXIST; // account doesn't exist
|
||||
|
||||
if (utf8length(newPassword) > MAX_ACCOUNT_STR)
|
||||
return AOR_PASS_TOO_LONG;
|
||||
return AccountOpResult::AOR_PASS_TOO_LONG;
|
||||
|
||||
normalizeString(username);
|
||||
normalizeString(newPassword);
|
||||
Utf8ToUpperOnlyLatin(username);
|
||||
Utf8ToUpperOnlyLatin(newPassword);
|
||||
|
||||
PreparedStatement* stmt = LoginDatabase.GetPreparedStatement(LOGIN_UPD_PASSWORD);
|
||||
|
||||
@@ -189,7 +189,7 @@ AccountOpResult AccountMgr::ChangePassword(uint32 accountId, std::string newPass
|
||||
|
||||
LoginDatabase.Execute(stmt);
|
||||
|
||||
return AOR_OK;
|
||||
return AccountOpResult::AOR_OK;
|
||||
}
|
||||
|
||||
AccountOpResult AccountMgr::ChangeEmail(uint32 accountId, std::string newEmail)
|
||||
@@ -197,13 +197,13 @@ AccountOpResult AccountMgr::ChangeEmail(uint32 accountId, std::string newEmail)
|
||||
std::string username;
|
||||
|
||||
if (!GetName(accountId, username))
|
||||
return AOR_NAME_NOT_EXIST; // account doesn't exist
|
||||
return AccountOpResult::AOR_NAME_NOT_EXIST; // account doesn't exist
|
||||
|
||||
if (utf8length(newEmail) > MAX_EMAIL_STR)
|
||||
return AOR_EMAIL_TOO_LONG;
|
||||
return AccountOpResult::AOR_EMAIL_TOO_LONG;
|
||||
|
||||
normalizeString(username);
|
||||
normalizeString(newEmail);
|
||||
Utf8ToUpperOnlyLatin(username);
|
||||
Utf8ToUpperOnlyLatin(newEmail);
|
||||
|
||||
PreparedStatement* stmt = LoginDatabase.GetPreparedStatement(LOGIN_UPD_EMAIL);
|
||||
|
||||
@@ -212,7 +212,7 @@ AccountOpResult AccountMgr::ChangeEmail(uint32 accountId, std::string newEmail)
|
||||
|
||||
LoginDatabase.Execute(stmt);
|
||||
|
||||
return AOR_OK;
|
||||
return AccountOpResult::AOR_OK;
|
||||
}
|
||||
|
||||
AccountOpResult AccountMgr::ChangeRegEmail(uint32 accountId, std::string newEmail)
|
||||
@@ -220,13 +220,13 @@ AccountOpResult AccountMgr::ChangeRegEmail(uint32 accountId, std::string newEmai
|
||||
std::string username;
|
||||
|
||||
if (!GetName(accountId, username))
|
||||
return AOR_NAME_NOT_EXIST; // account doesn't exist
|
||||
return AccountOpResult::AOR_NAME_NOT_EXIST; // account doesn't exist
|
||||
|
||||
if (utf8length(newEmail) > MAX_EMAIL_STR)
|
||||
return AOR_EMAIL_TOO_LONG;
|
||||
return AccountOpResult::AOR_EMAIL_TOO_LONG;
|
||||
|
||||
normalizeString(username);
|
||||
normalizeString(newEmail);
|
||||
Utf8ToUpperOnlyLatin(username);
|
||||
Utf8ToUpperOnlyLatin(newEmail);
|
||||
|
||||
PreparedStatement* stmt = LoginDatabase.GetPreparedStatement(LOGIN_UPD_REG_EMAIL);
|
||||
|
||||
@@ -235,7 +235,7 @@ AccountOpResult AccountMgr::ChangeRegEmail(uint32 accountId, std::string newEmai
|
||||
|
||||
LoginDatabase.Execute(stmt);
|
||||
|
||||
return AOR_OK;
|
||||
return AccountOpResult::AOR_OK;
|
||||
}
|
||||
|
||||
uint32 AccountMgr::GetId(std::string const& username)
|
||||
@@ -303,8 +303,8 @@ bool AccountMgr::CheckPassword(uint32 accountId, std::string password)
|
||||
if (!GetName(accountId, username))
|
||||
return false;
|
||||
|
||||
normalizeString(username);
|
||||
normalizeString(password);
|
||||
Utf8ToUpperOnlyLatin(username);
|
||||
Utf8ToUpperOnlyLatin(password);
|
||||
|
||||
PreparedStatement* stmt = LoginDatabase.GetPreparedStatement(LOGIN_SEL_CHECK_PASSWORD);
|
||||
stmt->setUInt32(0, accountId);
|
||||
@@ -322,8 +322,8 @@ bool AccountMgr::CheckEmail(uint32 accountId, std::string newEmail)
|
||||
if (!GetEmail(accountId, oldEmail))
|
||||
return false;
|
||||
|
||||
normalizeString(oldEmail);
|
||||
normalizeString(newEmail);
|
||||
Utf8ToUpperOnlyLatin(oldEmail);
|
||||
Utf8ToUpperOnlyLatin(newEmail);
|
||||
|
||||
if (strcmp(oldEmail.c_str(), newEmail.c_str()) == 0)
|
||||
return true;
|
||||
@@ -341,19 +341,6 @@ uint32 AccountMgr::GetCharactersCount(uint32 accountId)
|
||||
return (result) ? (*result)[0].GetUInt64() : 0;
|
||||
}
|
||||
|
||||
bool AccountMgr::normalizeString(std::string& utf8String)
|
||||
{
|
||||
wchar_t buffer[MAX_ACCOUNT_STR+1];
|
||||
|
||||
size_t maxLength = MAX_ACCOUNT_STR;
|
||||
if (!Utf8toWStr(utf8String, buffer, maxLength))
|
||||
return false;
|
||||
|
||||
std::transform(&buffer[0], buffer+maxLength, &buffer[0], wcharToUpperOnlyLatin);
|
||||
|
||||
return WStrToUtf8(buffer, maxLength, utf8String);
|
||||
}
|
||||
|
||||
std::string AccountMgr::CalculateShaPassHash(std::string const& name, std::string const& password)
|
||||
{
|
||||
SHA1Hash sha;
|
||||
|
||||
@@ -22,7 +22,7 @@
|
||||
#include "RBAC.h"
|
||||
#include <ace/Singleton.h>
|
||||
|
||||
enum AccountOpResult
|
||||
enum class AccountOpResult : uint8
|
||||
{
|
||||
AOR_OK,
|
||||
AOR_NAME_TOO_LONG,
|
||||
@@ -40,6 +40,7 @@ enum PasswordChangeSecurity
|
||||
PW_RBAC
|
||||
};
|
||||
|
||||
#define MAX_PASS_STR 16
|
||||
#define MAX_ACCOUNT_STR 16
|
||||
#define MAX_EMAIL_STR 64
|
||||
|
||||
@@ -58,7 +59,7 @@ class AccountMgr
|
||||
~AccountMgr();
|
||||
|
||||
public:
|
||||
AccountOpResult CreateAccount(std::string username, std::string password, std::string email);
|
||||
AccountOpResult CreateAccount(std::string username, std::string password, std::string email = "");
|
||||
static AccountOpResult DeleteAccount(uint32 accountId);
|
||||
static AccountOpResult ChangeUsername(uint32 accountId, std::string newUsername, std::string newPassword);
|
||||
static AccountOpResult ChangePassword(uint32 accountId, std::string newPassword);
|
||||
@@ -75,7 +76,6 @@ class AccountMgr
|
||||
static uint32 GetCharactersCount(uint32 accountId);
|
||||
|
||||
static std::string CalculateShaPassHash(std::string const& name, std::string const& password);
|
||||
static bool normalizeString(std::string& utf8String);
|
||||
static bool IsPlayerAccount(uint32 gmlevel);
|
||||
static bool IsAdminAccount(uint32 gmlevel);
|
||||
static bool IsConsoleAccount(uint32 gmlevel);
|
||||
|
||||
144
src/server/game/Accounts/BattlenetAccountMgr.cpp
Normal file
144
src/server/game/Accounts/BattlenetAccountMgr.cpp
Normal file
@@ -0,0 +1,144 @@
|
||||
/*
|
||||
* Copyright (C) 2008-2014 TrinityCore <http://www.trinitycore.org/>
|
||||
*
|
||||
* 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/>.
|
||||
*/
|
||||
|
||||
#include "AccountMgr.h"
|
||||
#include "BattlenetAccountMgr.h"
|
||||
#include "DatabaseEnv.h"
|
||||
#include "Util.h"
|
||||
#include "SHA256.h"
|
||||
|
||||
AccountOpResult Battlenet::AccountMgr::CreateBattlenetAccount(std::string email, std::string password)
|
||||
{
|
||||
if (utf8length(email) > 64)
|
||||
return AccountOpResult::AOR_NAME_TOO_LONG;
|
||||
|
||||
Utf8ToUpperOnlyLatin(email);
|
||||
Utf8ToUpperOnlyLatin(password);
|
||||
|
||||
if (GetId(email))
|
||||
return AccountOpResult::AOR_NAME_ALREADY_EXIST;
|
||||
|
||||
PreparedStatement* stmt = LoginDatabase.GetPreparedStatement(LOGIN_INS_BNET_ACCOUNT);
|
||||
stmt->setString(0, email);
|
||||
stmt->setString(1, CalculateShaPassHash(email, password));
|
||||
LoginDatabase.Execute(stmt);
|
||||
|
||||
return AccountOpResult::AOR_OK;
|
||||
}
|
||||
|
||||
AccountOpResult Battlenet::AccountMgr::ChangeUsername(uint32 accountId, std::string newUsername, std::string newPassword)
|
||||
{
|
||||
// Check if accounts exists
|
||||
PreparedStatement* stmt = LoginDatabase.GetPreparedStatement(LOGIN_SEL_BNET_ACCOUNT_EMAIL_BY_ID);
|
||||
stmt->setUInt32(0, accountId);
|
||||
PreparedQueryResult result = LoginDatabase.Query(stmt);
|
||||
|
||||
if (!result)
|
||||
return AccountOpResult::AOR_NAME_NOT_EXIST;
|
||||
|
||||
Utf8ToUpperOnlyLatin(newUsername);
|
||||
if (utf8length(newUsername) > MAX_ACCOUNT_STR)
|
||||
return AccountOpResult::AOR_NAME_TOO_LONG;
|
||||
|
||||
Utf8ToUpperOnlyLatin(newPassword);
|
||||
if (utf8length(newPassword) > MAX_PASS_STR)
|
||||
return AccountOpResult::AOR_PASS_TOO_LONG;
|
||||
|
||||
stmt = LoginDatabase.GetPreparedStatement(LOGIN_UPD_BNET_PASSWORD);
|
||||
stmt->setString(0, newUsername);
|
||||
stmt->setString(1, CalculateShaPassHash(newUsername, newPassword));
|
||||
stmt->setUInt32(2, accountId);
|
||||
LoginDatabase.Execute(stmt);
|
||||
|
||||
return AccountOpResult::AOR_OK;
|
||||
}
|
||||
|
||||
AccountOpResult Battlenet::AccountMgr::ChangePassword(uint32 accountId, std::string newPassword)
|
||||
{
|
||||
std::string username;
|
||||
if (!GetName(accountId, username))
|
||||
return AccountOpResult::AOR_NAME_NOT_EXIST; // account doesn't exist
|
||||
|
||||
Utf8ToUpperOnlyLatin(username);
|
||||
Utf8ToUpperOnlyLatin(newPassword);
|
||||
if (utf8length(newPassword) > MAX_PASS_STR)
|
||||
return AccountOpResult::AOR_PASS_TOO_LONG;
|
||||
|
||||
PreparedStatement* stmt = LoginDatabase.GetPreparedStatement(LOGIN_UPD_BNET_PASSWORD);
|
||||
stmt->setString(0, username);
|
||||
stmt->setString(1, CalculateShaPassHash(username, newPassword));
|
||||
stmt->setUInt32(2, accountId);
|
||||
LoginDatabase.Execute(stmt);
|
||||
|
||||
return AccountOpResult::AOR_OK;
|
||||
}
|
||||
|
||||
uint32 Battlenet::AccountMgr::GetId(std::string const& username)
|
||||
{
|
||||
PreparedStatement* stmt = LoginDatabase.GetPreparedStatement(LOGIN_SEL_BNET_ACCOUNT_ID_BY_EMAIL);
|
||||
stmt->setString(0, username);
|
||||
if (PreparedQueryResult result = LoginDatabase.Query(stmt))
|
||||
return (*result)[0].GetUInt32();
|
||||
|
||||
return 0;
|
||||
}
|
||||
|
||||
bool Battlenet::AccountMgr::GetName(uint32 accountId, std::string& name)
|
||||
{
|
||||
PreparedStatement* stmt = LoginDatabase.GetPreparedStatement(LOGIN_SEL_BNET_ACCOUNT_EMAIL_BY_ID);
|
||||
stmt->setUInt32(0, accountId);
|
||||
if (PreparedQueryResult result = LoginDatabase.Query(stmt))
|
||||
{
|
||||
name = (*result)[0].GetString();
|
||||
return true;
|
||||
}
|
||||
|
||||
return false;
|
||||
}
|
||||
|
||||
bool Battlenet::AccountMgr::CheckPassword(uint32 accountId, std::string password)
|
||||
{
|
||||
std::string username;
|
||||
|
||||
if (!GetName(accountId, username))
|
||||
return false;
|
||||
|
||||
Utf8ToUpperOnlyLatin(username);
|
||||
Utf8ToUpperOnlyLatin(password);
|
||||
|
||||
PreparedStatement* stmt = LoginDatabase.GetPreparedStatement(LOGIN_SEL_BNET_CHECK_PASSWORD);
|
||||
stmt->setUInt32(0, accountId);
|
||||
stmt->setString(1, CalculateShaPassHash(username, password));
|
||||
PreparedQueryResult result = LoginDatabase.Query(stmt);
|
||||
|
||||
return !result.null();
|
||||
}
|
||||
|
||||
std::string Battlenet::AccountMgr::CalculateShaPassHash(std::string const& name, std::string const& password)
|
||||
{
|
||||
SHA256Hash email;
|
||||
email.UpdateData(name);
|
||||
email.Finalize();
|
||||
|
||||
SHA256Hash sha;
|
||||
sha.UpdateData(ByteArrayToHexStr(email.GetDigest(), email.GetLength()));
|
||||
sha.UpdateData(":");
|
||||
sha.UpdateData(password);
|
||||
sha.Finalize();
|
||||
|
||||
return ByteArrayToHexStr(sha.GetDigest(), sha.GetLength(), true);
|
||||
}
|
||||
45
src/server/game/Accounts/BattlenetAccountMgr.h
Normal file
45
src/server/game/Accounts/BattlenetAccountMgr.h
Normal file
@@ -0,0 +1,45 @@
|
||||
/*
|
||||
* Copyright (C) 2008-2014 TrinityCore <http://www.trinitycore.org/>
|
||||
*
|
||||
* 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 BattlenetAccountMgr_h__
|
||||
#define BattlenetAccountMgr_h__
|
||||
|
||||
#include "Define.h"
|
||||
#include <string>
|
||||
#include <ace/Singleton.h>
|
||||
|
||||
enum class AccountOpResult : uint8;
|
||||
|
||||
#define MAX_BNET_EMAIL_STR 320
|
||||
|
||||
namespace Battlenet
|
||||
{
|
||||
namespace AccountMgr
|
||||
{
|
||||
AccountOpResult CreateBattlenetAccount(std::string email, std::string password);
|
||||
AccountOpResult ChangeUsername(uint32 accountId, std::string newUsername, std::string newPassword);
|
||||
AccountOpResult ChangePassword(uint32 accountId, std::string newPassword);
|
||||
bool CheckPassword(uint32 accountId, std::string password);
|
||||
|
||||
uint32 GetId(std::string const& username);
|
||||
bool GetName(uint32 accountId, std::string& name);
|
||||
|
||||
std::string CalculateShaPassHash(std::string const& name, std::string const& password);
|
||||
}
|
||||
}
|
||||
|
||||
#endif // BattlenetAccountMgr_h__
|
||||
@@ -856,9 +856,20 @@ int WorldSocket::HandleAuthSession(WorldPacket& recvPacket)
|
||||
// Get the account information from the realmd database
|
||||
// 0 1 2 3 4 5 6 7 8
|
||||
// SELECT id, sessionkey, last_ip, locked, expansion, mutetime, locale, recruiter, os FROM account WHERE username = ?
|
||||
PreparedStatement* stmt = LoginDatabase.GetPreparedStatement(LOGIN_SEL_ACCOUNT_INFO_BY_NAME);
|
||||
|
||||
stmt->setString(0, account);
|
||||
size_t hashPos = account.find_last_of('#');
|
||||
PreparedStatement* stmt;
|
||||
if (hashPos != std::string::npos)
|
||||
{
|
||||
Tokenizer tokens(account, '#', 2);
|
||||
stmt = LoginDatabase.GetPreparedStatement(LOGIN_SEL_ACCOUNT_INFO_BY_BNET);
|
||||
stmt->setUInt32(0, atol(tokens[0]));
|
||||
stmt->setUInt8(1, atol(tokens[1]));
|
||||
}
|
||||
else
|
||||
{
|
||||
stmt = LoginDatabase.GetPreparedStatement(LOGIN_SEL_ACCOUNT_INFO_BY_NAME);
|
||||
stmt->setString(0, account);
|
||||
}
|
||||
|
||||
PreparedQueryResult result = LoginDatabase.Query(stmt);
|
||||
|
||||
|
||||
@@ -39,7 +39,7 @@
|
||||
#endif /* ACE_LACKS_PRAGMA_ONCE */
|
||||
|
||||
#include "Common.h"
|
||||
#include "AuthCrypt.h"
|
||||
#include "WorldPacketCrypt.h"
|
||||
|
||||
class ACE_Message_Block;
|
||||
class WorldPacket;
|
||||
@@ -176,7 +176,7 @@ class WorldSocket : public WorldHandler
|
||||
std::string m_Address;
|
||||
|
||||
/// Class used for managing encryption of the headers
|
||||
AuthCrypt m_Crypt;
|
||||
WorldPacketCrypt m_Crypt;
|
||||
|
||||
/// Mutex lock to protect m_Session
|
||||
LockType m_SessionLock;
|
||||
|
||||
@@ -16,7 +16,7 @@
|
||||
* with this program. If not, see <http://www.gnu.org/licenses/>.
|
||||
*/
|
||||
|
||||
#include "Cryptography/HMACSHA1.h"
|
||||
#include "Cryptography/HmacHash.h"
|
||||
#include "Cryptography/WardenKeyGeneration.h"
|
||||
#include "Common.h"
|
||||
#include "WorldPacket.h"
|
||||
@@ -283,7 +283,7 @@ void WardenWin::RequestData()
|
||||
{
|
||||
uint32 seed = static_cast<uint32>(rand32());
|
||||
buff << uint32(seed);
|
||||
HmacHash hmac(4, (uint8*)&seed);
|
||||
HmacSha1 hmac(4, (uint8*)&seed);
|
||||
hmac.UpdateData(wd->Str);
|
||||
hmac.Finalize();
|
||||
buff.append(hmac.GetDigest(), hmac.GetLength());
|
||||
|
||||
@@ -23,6 +23,7 @@ Category: commandscripts
|
||||
EndScriptData */
|
||||
|
||||
#include "AccountMgr.h"
|
||||
#include "BattlenetAccountMgr.h"
|
||||
#include "Chat.h"
|
||||
#include "Language.h"
|
||||
#include "Player.h"
|
||||
@@ -126,10 +127,15 @@ public:
|
||||
if (!accountName || !password)
|
||||
return false;
|
||||
|
||||
AccountOpResult result = sAccountMgr->CreateAccount(std::string(accountName), std::string(password), email);
|
||||
AccountOpResult result;
|
||||
if (strchr(accountName, '@'))
|
||||
result = Battlenet::AccountMgr::CreateBattlenetAccount(std::string(accountName), std::string(password));
|
||||
else
|
||||
result = sAccountMgr->CreateAccount(std::string(accountName), std::string(password), email);
|
||||
|
||||
switch (result)
|
||||
{
|
||||
case AOR_OK:
|
||||
case AccountOpResult::AOR_OK:
|
||||
handler->PSendSysMessage(LANG_ACCOUNT_CREATED, accountName);
|
||||
if (handler->GetSession())
|
||||
{
|
||||
@@ -139,15 +145,15 @@ public:
|
||||
accountName, email.c_str());
|
||||
}
|
||||
break;
|
||||
case AOR_NAME_TOO_LONG:
|
||||
case AccountOpResult::AOR_NAME_TOO_LONG:
|
||||
handler->SendSysMessage(LANG_ACCOUNT_TOO_LONG);
|
||||
handler->SetSentErrorMessage(true);
|
||||
return false;
|
||||
case AOR_NAME_ALREADY_EXIST:
|
||||
case AccountOpResult::AOR_NAME_ALREADY_EXIST:
|
||||
handler->SendSysMessage(LANG_ACCOUNT_ALREADY_EXIST);
|
||||
handler->SetSentErrorMessage(true);
|
||||
return false;
|
||||
case AOR_DB_INTERNAL_ERROR:
|
||||
case AccountOpResult::AOR_DB_INTERNAL_ERROR:
|
||||
handler->PSendSysMessage(LANG_ACCOUNT_NOT_CREATED_SQL_ERROR, accountName);
|
||||
handler->SetSentErrorMessage(true);
|
||||
return false;
|
||||
@@ -173,7 +179,7 @@ public:
|
||||
return false;
|
||||
|
||||
std::string accountName = account;
|
||||
if (!AccountMgr::normalizeString(accountName))
|
||||
if (!Utf8ToUpperOnlyLatin(accountName))
|
||||
{
|
||||
handler->PSendSysMessage(LANG_ACCOUNT_NOT_EXIST, accountName.c_str());
|
||||
handler->SetSentErrorMessage(true);
|
||||
@@ -197,14 +203,14 @@ public:
|
||||
AccountOpResult result = AccountMgr::DeleteAccount(accountId);
|
||||
switch (result)
|
||||
{
|
||||
case AOR_OK:
|
||||
case AccountOpResult::AOR_OK:
|
||||
handler->PSendSysMessage(LANG_ACCOUNT_DELETED, accountName.c_str());
|
||||
break;
|
||||
case AOR_NAME_NOT_EXIST:
|
||||
case AccountOpResult::AOR_NAME_NOT_EXIST:
|
||||
handler->PSendSysMessage(LANG_ACCOUNT_NOT_EXIST, accountName.c_str());
|
||||
handler->SetSentErrorMessage(true);
|
||||
return false;
|
||||
case AOR_DB_INTERNAL_ERROR:
|
||||
case AccountOpResult::AOR_DB_INTERNAL_ERROR:
|
||||
handler->PSendSysMessage(LANG_ACCOUNT_NOT_DELETED_SQL_ERROR, accountName.c_str());
|
||||
handler->SetSentErrorMessage(true);
|
||||
return false;
|
||||
@@ -416,14 +422,14 @@ public:
|
||||
AccountOpResult result = AccountMgr::ChangeEmail(handler->GetSession()->GetAccountId(), std::string(email));
|
||||
switch (result)
|
||||
{
|
||||
case AOR_OK:
|
||||
case AccountOpResult::AOR_OK:
|
||||
handler->SendSysMessage(LANG_COMMAND_EMAIL);
|
||||
TC_LOG_INFO("entities.player.character", "Account: %u (IP: %s) Character:[%s] (GUID: %u) Changed Email from [%s] to [%s].",
|
||||
handler->GetSession()->GetAccountId(), handler->GetSession()->GetRemoteAddress().c_str(),
|
||||
handler->GetSession()->GetPlayer()->GetName().c_str(), handler->GetSession()->GetPlayer()->GetGUIDLow(),
|
||||
oldEmail, email);
|
||||
break;
|
||||
case AOR_EMAIL_TOO_LONG:
|
||||
case AccountOpResult::AOR_EMAIL_TOO_LONG:
|
||||
handler->SendSysMessage(LANG_EMAIL_TOO_LONG);
|
||||
handler->SetSentErrorMessage(true);
|
||||
return false;
|
||||
@@ -501,13 +507,13 @@ public:
|
||||
AccountOpResult result = AccountMgr::ChangePassword(handler->GetSession()->GetAccountId(), std::string(newPassword));
|
||||
switch (result)
|
||||
{
|
||||
case AOR_OK:
|
||||
case AccountOpResult::AOR_OK:
|
||||
handler->SendSysMessage(LANG_COMMAND_PASSWORD);
|
||||
TC_LOG_INFO("entities.player.character", "Account: %u (IP: %s) Character:[%s] (GUID: %u) Changed Password.",
|
||||
handler->GetSession()->GetAccountId(), handler->GetSession()->GetRemoteAddress().c_str(),
|
||||
handler->GetSession()->GetPlayer()->GetName().c_str(), handler->GetSession()->GetPlayer()->GetGUIDLow());
|
||||
break;
|
||||
case AOR_PASS_TOO_LONG:
|
||||
case AccountOpResult::AOR_PASS_TOO_LONG:
|
||||
handler->SendSysMessage(LANG_PASSWORD_TOO_LONG);
|
||||
handler->SetSentErrorMessage(true);
|
||||
return false;
|
||||
@@ -586,7 +592,7 @@ public:
|
||||
{
|
||||
///- Convert Account name to Upper Format
|
||||
accountName = account;
|
||||
if (!AccountMgr::normalizeString(accountName))
|
||||
if (!Utf8ToUpperOnlyLatin(accountName))
|
||||
{
|
||||
handler->PSendSysMessage(LANG_ACCOUNT_NOT_EXIST, accountName.c_str());
|
||||
handler->SetSentErrorMessage(true);
|
||||
@@ -656,7 +662,7 @@ public:
|
||||
if (isAccountNameGiven)
|
||||
{
|
||||
targetAccountName = arg1;
|
||||
if (!AccountMgr::normalizeString(targetAccountName))
|
||||
if (!Utf8ToUpperOnlyLatin(targetAccountName))
|
||||
{
|
||||
handler->PSendSysMessage(LANG_ACCOUNT_NOT_EXIST, targetAccountName.c_str());
|
||||
handler->SetSentErrorMessage(true);
|
||||
@@ -744,7 +750,7 @@ public:
|
||||
return false;
|
||||
|
||||
std::string accountName = account;
|
||||
if (!AccountMgr::normalizeString(accountName))
|
||||
if (!Utf8ToUpperOnlyLatin(accountName))
|
||||
{
|
||||
handler->PSendSysMessage(LANG_ACCOUNT_NOT_EXIST, accountName.c_str());
|
||||
handler->SetSentErrorMessage(true);
|
||||
@@ -775,14 +781,14 @@ public:
|
||||
|
||||
switch (result)
|
||||
{
|
||||
case AOR_OK:
|
||||
case AccountOpResult::AOR_OK:
|
||||
handler->SendSysMessage(LANG_COMMAND_PASSWORD);
|
||||
break;
|
||||
case AOR_NAME_NOT_EXIST:
|
||||
case AccountOpResult::AOR_NAME_NOT_EXIST:
|
||||
handler->PSendSysMessage(LANG_ACCOUNT_NOT_EXIST, accountName.c_str());
|
||||
handler->SetSentErrorMessage(true);
|
||||
return false;
|
||||
case AOR_PASS_TOO_LONG:
|
||||
case AccountOpResult::AOR_PASS_TOO_LONG:
|
||||
handler->SendSysMessage(LANG_PASSWORD_TOO_LONG);
|
||||
handler->SetSentErrorMessage(true);
|
||||
return false;
|
||||
@@ -813,7 +819,7 @@ public:
|
||||
}
|
||||
|
||||
std::string accountName = account;
|
||||
if (!AccountMgr::normalizeString(accountName))
|
||||
if (!Utf8ToUpperOnlyLatin(accountName))
|
||||
{
|
||||
handler->PSendSysMessage(LANG_ACCOUNT_NOT_EXIST, accountName.c_str());
|
||||
handler->SetSentErrorMessage(true);
|
||||
@@ -843,16 +849,16 @@ public:
|
||||
AccountOpResult result = AccountMgr::ChangeEmail(targetAccountId, email);
|
||||
switch (result)
|
||||
{
|
||||
case AOR_OK:
|
||||
case AccountOpResult::AOR_OK:
|
||||
handler->SendSysMessage(LANG_COMMAND_EMAIL);
|
||||
TC_LOG_INFO("entities.player.character", "ChangeEmail: Account %s [Id: %u] had it's email changed to %s.",
|
||||
accountName.c_str(), targetAccountId, email);
|
||||
break;
|
||||
case AOR_NAME_NOT_EXIST:
|
||||
case AccountOpResult::AOR_NAME_NOT_EXIST:
|
||||
handler->PSendSysMessage(LANG_ACCOUNT_NOT_EXIST, accountName.c_str());
|
||||
handler->SetSentErrorMessage(true);
|
||||
return false;
|
||||
case AOR_EMAIL_TOO_LONG:
|
||||
case AccountOpResult::AOR_EMAIL_TOO_LONG:
|
||||
handler->SendSysMessage(LANG_EMAIL_TOO_LONG);
|
||||
handler->SetSentErrorMessage(true);
|
||||
return false;
|
||||
@@ -889,7 +895,7 @@ public:
|
||||
}
|
||||
|
||||
std::string accountName = account;
|
||||
if (!AccountMgr::normalizeString(accountName))
|
||||
if (!Utf8ToUpperOnlyLatin(accountName))
|
||||
{
|
||||
handler->PSendSysMessage(LANG_ACCOUNT_NOT_EXIST, accountName.c_str());
|
||||
handler->SetSentErrorMessage(true);
|
||||
@@ -919,16 +925,16 @@ public:
|
||||
AccountOpResult result = AccountMgr::ChangeRegEmail(targetAccountId, email);
|
||||
switch (result)
|
||||
{
|
||||
case AOR_OK:
|
||||
case AccountOpResult::AOR_OK:
|
||||
handler->SendSysMessage(LANG_COMMAND_EMAIL);
|
||||
TC_LOG_INFO("entities.player.character", "ChangeRegEmail: Account %s [Id: %u] had it's Registration Email changed to %s.",
|
||||
accountName.c_str(), targetAccountId, email);
|
||||
break;
|
||||
case AOR_NAME_NOT_EXIST:
|
||||
case AccountOpResult::AOR_NAME_NOT_EXIST:
|
||||
handler->PSendSysMessage(LANG_ACCOUNT_NOT_EXIST, accountName.c_str());
|
||||
handler->SetSentErrorMessage(true);
|
||||
return false;
|
||||
case AOR_EMAIL_TOO_LONG:
|
||||
case AccountOpResult::AOR_EMAIL_TOO_LONG:
|
||||
handler->SendSysMessage(LANG_EMAIL_TOO_LONG);
|
||||
handler->SetSentErrorMessage(true);
|
||||
return false;
|
||||
|
||||
@@ -174,7 +174,7 @@ public:
|
||||
switch (mode)
|
||||
{
|
||||
case BAN_ACCOUNT:
|
||||
if (!AccountMgr::normalizeString(nameOrIP))
|
||||
if (!Utf8ToUpperOnlyLatin(nameOrIP))
|
||||
{
|
||||
handler->PSendSysMessage(LANG_ACCOUNT_NOT_EXIST, nameOrIP.c_str());
|
||||
handler->SetSentErrorMessage(true);
|
||||
@@ -245,7 +245,7 @@ public:
|
||||
return false;
|
||||
|
||||
std::string accountName = nameStr;
|
||||
if (!AccountMgr::normalizeString(accountName))
|
||||
if (!Utf8ToUpperOnlyLatin(accountName))
|
||||
{
|
||||
handler->PSendSysMessage(LANG_ACCOUNT_NOT_EXIST, accountName.c_str());
|
||||
handler->SetSentErrorMessage(true);
|
||||
@@ -710,7 +710,7 @@ public:
|
||||
switch (mode)
|
||||
{
|
||||
case BAN_ACCOUNT:
|
||||
if (!AccountMgr::normalizeString(nameOrIP))
|
||||
if (!Utf8ToUpperOnlyLatin(nameOrIP))
|
||||
{
|
||||
handler->PSendSysMessage(LANG_ACCOUNT_NOT_EXIST, nameOrIP.c_str());
|
||||
handler->SetSentErrorMessage(true);
|
||||
|
||||
@@ -858,7 +858,7 @@ public:
|
||||
return false;
|
||||
|
||||
std::string accountName = accountStr;
|
||||
if (!AccountMgr::normalizeString(accountName))
|
||||
if (!Utf8ToUpperOnlyLatin(accountName))
|
||||
{
|
||||
handler->PSendSysMessage(LANG_ACCOUNT_NOT_EXIST, accountName.c_str());
|
||||
handler->SetSentErrorMessage(true);
|
||||
|
||||
@@ -1218,8 +1218,7 @@ public:
|
||||
char* limitStr = strtok(NULL, " ");
|
||||
int32 limit = limitStr ? atoi(limitStr) : -1;
|
||||
|
||||
if (!AccountMgr::normalizeString
|
||||
(account))
|
||||
if (!Utf8ToUpperOnlyLatin(account))
|
||||
return false;
|
||||
|
||||
PreparedStatement* stmt = LoginDatabase.GetPreparedStatement(LOGIN_SEL_ACCOUNT_LIST_BY_NAME);
|
||||
|
||||
@@ -142,7 +142,7 @@ public:
|
||||
{
|
||||
accountName = param1;
|
||||
|
||||
if (AccountMgr::normalizeString(accountName))
|
||||
if (Utf8ToUpperOnlyLatin(accountName))
|
||||
accountId = AccountMgr::GetId(accountName);
|
||||
|
||||
if (!accountId)
|
||||
|
||||
@@ -0,0 +1,39 @@
|
||||
/*
|
||||
* Copyright (C) 2008-2014 TrinityCore <http://www.trinitycore.org/>
|
||||
*
|
||||
* 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/>.
|
||||
*/
|
||||
|
||||
#include "PacketCrypt.h"
|
||||
|
||||
PacketCrypt::PacketCrypt(uint32 rc4InitSize)
|
||||
: _clientDecrypt(rc4InitSize), _serverEncrypt(rc4InitSize), _initialized(false)
|
||||
{
|
||||
}
|
||||
|
||||
void PacketCrypt::DecryptRecv(uint8* data, size_t len)
|
||||
{
|
||||
if (!_initialized)
|
||||
return;
|
||||
|
||||
_clientDecrypt.UpdateData(len, data);
|
||||
}
|
||||
|
||||
void PacketCrypt::EncryptSend(uint8* data, size_t len)
|
||||
{
|
||||
if (!_initialized)
|
||||
return;
|
||||
|
||||
_serverEncrypt.UpdateData(len, data);
|
||||
}
|
||||
@@ -1,6 +1,5 @@
|
||||
/*
|
||||
* 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
|
||||
@@ -16,27 +15,29 @@
|
||||
* with this program. If not, see <http://www.gnu.org/licenses/>.
|
||||
*/
|
||||
|
||||
#ifndef _AUTHCRYPT_H
|
||||
#define _AUTHCRYPT_H
|
||||
#ifndef _PACKETCRYPT_H
|
||||
#define _PACKETCRYPT_H
|
||||
|
||||
#include "Cryptography/ARC4.h"
|
||||
|
||||
class BigNumber;
|
||||
|
||||
class AuthCrypt
|
||||
class PacketCrypt
|
||||
{
|
||||
public:
|
||||
AuthCrypt();
|
||||
PacketCrypt(uint32 rc4InitSize);
|
||||
virtual ~PacketCrypt() { }
|
||||
|
||||
void Init(BigNumber* K);
|
||||
void DecryptRecv(uint8 *, size_t);
|
||||
void EncryptSend(uint8 *, size_t);
|
||||
virtual void Init(BigNumber* K) = 0;
|
||||
void DecryptRecv(uint8* data, size_t length);
|
||||
void EncryptSend(uint8* data, size_t length);
|
||||
|
||||
bool IsInitialized() const { return _initialized; }
|
||||
|
||||
private:
|
||||
protected:
|
||||
ARC4 _clientDecrypt;
|
||||
ARC4 _serverEncrypt;
|
||||
bool _initialized;
|
||||
};
|
||||
#endif
|
||||
|
||||
#endif // _PACKETCRYPT_H
|
||||
@@ -16,58 +16,36 @@
|
||||
* with this program. If not, see <http://www.gnu.org/licenses/>.
|
||||
*/
|
||||
|
||||
#include "AuthCrypt.h"
|
||||
#include "Cryptography/HMACSHA1.h"
|
||||
#include "WorldPacketCrypt.h"
|
||||
#include "Cryptography/HmacHash.h"
|
||||
#include "Cryptography/BigNumber.h"
|
||||
|
||||
AuthCrypt::AuthCrypt() :
|
||||
_clientDecrypt(SHA_DIGEST_LENGTH), _serverEncrypt(SHA_DIGEST_LENGTH),
|
||||
_initialized(false)
|
||||
{ }
|
||||
WorldPacketCrypt::WorldPacketCrypt() : PacketCrypt(SHA_DIGEST_LENGTH)
|
||||
{
|
||||
}
|
||||
|
||||
void AuthCrypt::Init(BigNumber* K)
|
||||
void WorldPacketCrypt::Init(BigNumber* K)
|
||||
{
|
||||
uint8 ServerEncryptionKey[SEED_KEY_SIZE] = { 0xCC, 0x98, 0xAE, 0x04, 0xE8, 0x97, 0xEA, 0xCA, 0x12, 0xDD, 0xC0, 0x93, 0x42, 0x91, 0x53, 0x57 };
|
||||
HmacHash serverEncryptHmac(SEED_KEY_SIZE, (uint8*)ServerEncryptionKey);
|
||||
HmacSha1 serverEncryptHmac(SEED_KEY_SIZE, (uint8*)ServerEncryptionKey);
|
||||
uint8 *encryptHash = serverEncryptHmac.ComputeHash(K);
|
||||
|
||||
uint8 ServerDecryptionKey[SEED_KEY_SIZE] = { 0xC2, 0xB3, 0x72, 0x3C, 0xC6, 0xAE, 0xD9, 0xB5, 0x34, 0x3C, 0x53, 0xEE, 0x2F, 0x43, 0x67, 0xCE };
|
||||
HmacHash clientDecryptHmac(SEED_KEY_SIZE, (uint8*)ServerDecryptionKey);
|
||||
HmacSha1 clientDecryptHmac(SEED_KEY_SIZE, (uint8*)ServerDecryptionKey);
|
||||
uint8 *decryptHash = clientDecryptHmac.ComputeHash(K);
|
||||
|
||||
//ARC4 _serverDecrypt(encryptHash);
|
||||
_clientDecrypt.Init(decryptHash);
|
||||
_serverEncrypt.Init(encryptHash);
|
||||
//ARC4 _clientEncrypt(decryptHash);
|
||||
|
||||
// Drop first 1024 bytes, as WoW uses ARC4-drop1024.
|
||||
uint8 syncBuf[1024];
|
||||
memset(syncBuf, 0, 1024);
|
||||
|
||||
_serverEncrypt.UpdateData(1024, syncBuf);
|
||||
//_clientEncrypt.UpdateData(1024, syncBuf);
|
||||
|
||||
memset(syncBuf, 0, 1024);
|
||||
|
||||
//_serverDecrypt.UpdateData(1024, syncBuf);
|
||||
_clientDecrypt.UpdateData(1024, syncBuf);
|
||||
|
||||
_initialized = true;
|
||||
}
|
||||
|
||||
void AuthCrypt::DecryptRecv(uint8 *data, size_t len)
|
||||
{
|
||||
if (!_initialized)
|
||||
return;
|
||||
|
||||
_clientDecrypt.UpdateData(len, data);
|
||||
}
|
||||
|
||||
void AuthCrypt::EncryptSend(uint8 *data, size_t len)
|
||||
{
|
||||
if (!_initialized)
|
||||
return;
|
||||
|
||||
_serverEncrypt.UpdateData(len, data);
|
||||
}
|
||||
|
||||
@@ -0,0 +1,34 @@
|
||||
/*
|
||||
* 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 _WORLDPACKETCRYPT_H
|
||||
#define _WORLDPACKETCRYPT_H
|
||||
|
||||
#include "PacketCrypt.h"
|
||||
|
||||
class BigNumber;
|
||||
|
||||
class WorldPacketCrypt : public PacketCrypt
|
||||
{
|
||||
public:
|
||||
WorldPacketCrypt();
|
||||
|
||||
void Init(BigNumber* K) override;
|
||||
};
|
||||
|
||||
#endif // _WORLDPACKETCRYPT_H
|
||||
@@ -190,13 +190,19 @@ ACE_Auto_Array_Ptr<uint8> BigNumber::AsByteArray(int32 minSize, bool littleEndia
|
||||
return ret;
|
||||
}
|
||||
|
||||
char * BigNumber::AsHexStr() const
|
||||
std::string BigNumber::AsHexStr() const
|
||||
{
|
||||
return BN_bn2hex(_bn);
|
||||
char* ch = BN_bn2hex(_bn);
|
||||
std::string ret = ch;
|
||||
OPENSSL_free(ch);
|
||||
return ret;
|
||||
}
|
||||
|
||||
char * BigNumber::AsDecStr() const
|
||||
std::string BigNumber::AsDecStr() const
|
||||
{
|
||||
return BN_bn2dec(_bn);
|
||||
char* ch = BN_bn2dec(_bn);
|
||||
std::string ret = ch;
|
||||
OPENSSL_free(ch);
|
||||
return ret;
|
||||
}
|
||||
|
||||
|
||||
@@ -21,6 +21,7 @@
|
||||
|
||||
#include "Define.h"
|
||||
#include <ace/Auto_Ptr.h>
|
||||
#include <string>
|
||||
|
||||
struct bignum_st;
|
||||
|
||||
@@ -89,8 +90,8 @@ class BigNumber
|
||||
|
||||
ACE_Auto_Array_Ptr<uint8> AsByteArray(int32 minSize = 0, bool littleEndian = true);
|
||||
|
||||
char * AsHexStr() const;
|
||||
char * AsDecStr() const;
|
||||
std::string AsHexStr() const;
|
||||
std::string AsDecStr() const;
|
||||
|
||||
private:
|
||||
struct bignum_st *_bn;
|
||||
|
||||
@@ -1,57 +0,0 @@
|
||||
/*
|
||||
* 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/>.
|
||||
*/
|
||||
|
||||
#include "HMACSHA1.h"
|
||||
#include "BigNumber.h"
|
||||
#include "Common.h"
|
||||
|
||||
HmacHash::HmacHash(uint32 len, uint8 *seed)
|
||||
{
|
||||
HMAC_CTX_init(&m_ctx);
|
||||
HMAC_Init_ex(&m_ctx, seed, len, EVP_sha1(), NULL);
|
||||
memset(m_digest, 0, sizeof(m_digest));
|
||||
}
|
||||
|
||||
HmacHash::~HmacHash()
|
||||
{
|
||||
HMAC_CTX_cleanup(&m_ctx);
|
||||
}
|
||||
|
||||
void HmacHash::UpdateData(const std::string &str)
|
||||
{
|
||||
HMAC_Update(&m_ctx, (uint8 const*)str.c_str(), str.length());
|
||||
}
|
||||
|
||||
void HmacHash::UpdateData(const uint8* data, size_t len)
|
||||
{
|
||||
HMAC_Update(&m_ctx, data, len);
|
||||
}
|
||||
|
||||
void HmacHash::Finalize()
|
||||
{
|
||||
uint32 length = 0;
|
||||
HMAC_Final(&m_ctx, (uint8*)m_digest, &length);
|
||||
ASSERT(length == SHA_DIGEST_LENGTH);
|
||||
}
|
||||
|
||||
uint8 *HmacHash::ComputeHash(BigNumber* bn)
|
||||
{
|
||||
HMAC_Update(&m_ctx, bn->AsByteArray().get(), bn->GetNumBytes());
|
||||
Finalize();
|
||||
return (uint8*)m_digest;
|
||||
}
|
||||
66
src/server/shared/Cryptography/HmacHash.cpp
Normal file
66
src/server/shared/Cryptography/HmacHash.cpp
Normal file
@@ -0,0 +1,66 @@
|
||||
/*
|
||||
* 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/>.
|
||||
*/
|
||||
|
||||
#include "HmacHash.h"
|
||||
#include "BigNumber.h"
|
||||
#include "Common.h"
|
||||
|
||||
template<HashCreateFn HashCreator, uint32 DigestLength>
|
||||
HmacHash<HashCreator, DigestLength>::HmacHash(uint32 len, uint8 *seed)
|
||||
{
|
||||
HMAC_CTX_init(&_ctx);
|
||||
HMAC_Init_ex(&_ctx, seed, len, HashCreator(), NULL);
|
||||
memset(_digest, 0, DigestLength);
|
||||
}
|
||||
|
||||
template<HashCreateFn HashCreator, uint32 DigestLength>
|
||||
HmacHash<HashCreator, DigestLength>::~HmacHash()
|
||||
{
|
||||
HMAC_CTX_cleanup(&_ctx);
|
||||
}
|
||||
|
||||
template<HashCreateFn HashCreator, uint32 DigestLength>
|
||||
void HmacHash<HashCreator, DigestLength>::UpdateData(const std::string &str)
|
||||
{
|
||||
HMAC_Update(&_ctx, (uint8 const*)str.c_str(), str.length());
|
||||
}
|
||||
|
||||
template<HashCreateFn HashCreator, uint32 DigestLength>
|
||||
void HmacHash<HashCreator, DigestLength>::UpdateData(const uint8* data, size_t len)
|
||||
{
|
||||
HMAC_Update(&_ctx, data, len);
|
||||
}
|
||||
|
||||
template<HashCreateFn HashCreator, uint32 DigestLength>
|
||||
void HmacHash<HashCreator, DigestLength>::Finalize()
|
||||
{
|
||||
uint32 length = 0;
|
||||
HMAC_Final(&_ctx, _digest, &length);
|
||||
ASSERT(length == DigestLength);
|
||||
}
|
||||
|
||||
template<HashCreateFn HashCreator, uint32 DigestLength>
|
||||
uint8* HmacHash<HashCreator, DigestLength>::ComputeHash(BigNumber* bn)
|
||||
{
|
||||
HMAC_Update(&_ctx, bn->AsByteArray().get(), bn->GetNumBytes());
|
||||
Finalize();
|
||||
return _digest;
|
||||
}
|
||||
|
||||
template class HmacHash<EVP_sha1, SHA_DIGEST_LENGTH>;
|
||||
template class HmacHash<EVP_sha256, SHA256_DIGEST_LENGTH>;
|
||||
@@ -28,20 +28,26 @@ class BigNumber;
|
||||
|
||||
#define SEED_KEY_SIZE 16
|
||||
|
||||
typedef EVP_MD const* (*HashCreateFn)();
|
||||
|
||||
template<HashCreateFn HashCreator, uint32 DigestLength>
|
||||
class HmacHash
|
||||
{
|
||||
public:
|
||||
HmacHash(uint32 len, uint8 *seed);
|
||||
~HmacHash();
|
||||
void UpdateData(const std::string &str);
|
||||
void UpdateData(const uint8* data, size_t len);
|
||||
void UpdateData(std::string const& str);
|
||||
void UpdateData(uint8 const* data, size_t len);
|
||||
void Finalize();
|
||||
uint8 *ComputeHash(BigNumber* bn);
|
||||
uint8 *GetDigest() { return (uint8*)m_digest; }
|
||||
int GetLength() const { return SHA_DIGEST_LENGTH; }
|
||||
uint8* ComputeHash(BigNumber* bn);
|
||||
uint8* GetDigest() { return _digest; }
|
||||
uint32 GetLength() const { return DigestLength; }
|
||||
private:
|
||||
HMAC_CTX m_ctx;
|
||||
uint8 m_digest[SHA_DIGEST_LENGTH];
|
||||
HMAC_CTX _ctx;
|
||||
uint8 _digest[DigestLength];
|
||||
};
|
||||
#endif
|
||||
|
||||
typedef HmacHash<EVP_sha1, SHA_DIGEST_LENGTH> HmacSha1;
|
||||
typedef HmacHash<EVP_sha256, SHA256_DIGEST_LENGTH> HmacSha256;
|
||||
|
||||
#endif
|
||||
66
src/server/shared/Cryptography/SHA256.cpp
Normal file
66
src/server/shared/Cryptography/SHA256.cpp
Normal file
@@ -0,0 +1,66 @@
|
||||
/*
|
||||
* Copyright (C) 2008-2014 TrinityCore <http://www.trinitycore.org/>
|
||||
*
|
||||
* 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/>.
|
||||
*/
|
||||
|
||||
#include "SHA256.h"
|
||||
#include "BigNumber.h"
|
||||
#include <stdarg.h>
|
||||
|
||||
SHA256Hash::SHA256Hash()
|
||||
{
|
||||
SHA256_Init(&mC);
|
||||
memset(mDigest, 0, SHA256_DIGEST_LENGTH * sizeof(uint8));
|
||||
}
|
||||
|
||||
SHA256Hash::~SHA256Hash()
|
||||
{
|
||||
SHA256_Init(&mC);
|
||||
}
|
||||
|
||||
void SHA256Hash::UpdateData(const uint8 *dta, int len)
|
||||
{
|
||||
SHA256_Update(&mC, dta, len);
|
||||
}
|
||||
|
||||
void SHA256Hash::UpdateData(const std::string &str)
|
||||
{
|
||||
UpdateData((uint8 const*)str.c_str(), str.length());
|
||||
}
|
||||
|
||||
void SHA256Hash::UpdateBigNumbers(BigNumber* bn0, ...)
|
||||
{
|
||||
va_list v;
|
||||
BigNumber* bn;
|
||||
|
||||
va_start(v, bn0);
|
||||
bn = bn0;
|
||||
while (bn)
|
||||
{
|
||||
UpdateData(bn->AsByteArray().get(), bn->GetNumBytes());
|
||||
bn = va_arg(v, BigNumber*);
|
||||
}
|
||||
va_end(v);
|
||||
}
|
||||
|
||||
void SHA256Hash::Initialize()
|
||||
{
|
||||
SHA256_Init(&mC);
|
||||
}
|
||||
|
||||
void SHA256Hash::Finalize(void)
|
||||
{
|
||||
SHA256_Final(mDigest, &mC);
|
||||
}
|
||||
49
src/server/shared/Cryptography/SHA256.h
Normal file
49
src/server/shared/Cryptography/SHA256.h
Normal file
@@ -0,0 +1,49 @@
|
||||
/*
|
||||
* Copyright (C) 2008-2014 TrinityCore <http://www.trinitycore.org/>
|
||||
*
|
||||
* 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 SHA256_h__
|
||||
#define SHA256_h__
|
||||
|
||||
#include "Define.h"
|
||||
#include <string>
|
||||
#include <openssl/sha.h>
|
||||
|
||||
class BigNumber;
|
||||
|
||||
class SHA256Hash
|
||||
{
|
||||
public:
|
||||
SHA256Hash();
|
||||
~SHA256Hash();
|
||||
|
||||
void UpdateBigNumbers(BigNumber* bn0, ...);
|
||||
|
||||
void UpdateData(const uint8 *dta, int len);
|
||||
void UpdateData(const std::string &str);
|
||||
|
||||
void Initialize();
|
||||
void Finalize();
|
||||
|
||||
uint8 *GetDigest(void) { return mDigest; };
|
||||
int GetLength(void) const { return SHA256_DIGEST_LENGTH; };
|
||||
|
||||
private:
|
||||
SHA256_CTX mC;
|
||||
uint8 mDigest[SHA256_DIGEST_LENGTH];
|
||||
};
|
||||
|
||||
#endif // SHA256_h__
|
||||
@@ -22,7 +22,7 @@ void LoginDatabaseConnection::DoPrepareStatements()
|
||||
if (!m_reconnecting)
|
||||
m_stmts.resize(MAX_LOGINDATABASE_STATEMENTS);
|
||||
|
||||
PrepareStatement(LOGIN_SEL_REALMLIST, "SELECT id, name, address, localAddress, localSubnetMask, port, icon, flag, timezone, allowedSecurityLevel, population, gamebuild FROM realmlist WHERE flag <> 3 ORDER BY name", CONNECTION_SYNCH);
|
||||
PrepareStatement(LOGIN_SEL_REALMLIST, "SELECT id, name, address, localAddress, localSubnetMask, port, icon, flag, timezone, allowedSecurityLevel, population, gamebuild, Region, Battlegroup FROM realmlist WHERE flag <> 3 ORDER BY name", CONNECTION_SYNCH);
|
||||
PrepareStatement(LOGIN_DEL_EXPIRED_IP_BANS, "DELETE FROM ip_banned WHERE unbandate<>bandate AND unbandate<=UNIX_TIMESTAMP()", CONNECTION_ASYNC);
|
||||
PrepareStatement(LOGIN_UPD_EXPIRED_ACCOUNT_BANS, "UPDATE account_banned SET active = 0 WHERE active = 1 AND unbandate<>bandate AND unbandate<=UNIX_TIMESTAMP()", CONNECTION_SYNCH);
|
||||
PrepareStatement(LOGIN_SEL_IP_BANNED, "SELECT * FROM ip_banned WHERE ip = ?", CONNECTION_SYNCH);
|
||||
@@ -37,13 +37,14 @@ void LoginDatabaseConnection::DoPrepareStatements()
|
||||
PrepareStatement(LOGIN_SEL_SESSIONKEY, "SELECT a.sessionkey, a.id, aa.gmlevel FROM account a LEFT JOIN account_access aa ON (a.id = aa.id) WHERE username = ?", CONNECTION_SYNCH);
|
||||
PrepareStatement(LOGIN_UPD_VS, "UPDATE account SET v = ?, s = ? WHERE username = ?", CONNECTION_ASYNC);
|
||||
PrepareStatement(LOGIN_UPD_LOGONPROOF, "UPDATE account SET sessionkey = ?, last_ip = ?, last_login = NOW(), locale = ?, failed_logins = 0, os = ? WHERE username = ?", CONNECTION_SYNCH);
|
||||
PrepareStatement(LOGIN_SEL_LOGONCHALLENGE, "SELECT a.sha_pass_hash, a.id, a.locked, a.lock_country, a.last_ip, aa.gmlevel, a.v, a.s, a.token_key FROM account a LEFT JOIN account_access aa ON (a.id = aa.id) WHERE a.username = ?", CONNECTION_SYNCH);
|
||||
PrepareStatement(LOGIN_SEL_LOGONCHALLENGE, "SELECT a.sha_pass_hash, a.id, a.locked, a.lock_country, a.last_ip, aa.gmlevel, a.v, a.s, a.token_key, a.battlenet_account FROM account a LEFT JOIN account_access aa ON (a.id = aa.id) WHERE a.username = ?", CONNECTION_SYNCH);
|
||||
PrepareStatement(LOGIN_SEL_LOGON_COUNTRY, "SELECT country FROM ip2nation WHERE ip < ? ORDER BY ip DESC LIMIT 0,1", CONNECTION_SYNCH);
|
||||
PrepareStatement(LOGIN_UPD_FAILEDLOGINS, "UPDATE account SET failed_logins = failed_logins + 1 WHERE username = ?", CONNECTION_ASYNC);
|
||||
PrepareStatement(LOGIN_SEL_FAILEDLOGINS, "SELECT id, failed_logins FROM account WHERE username = ?", CONNECTION_SYNCH);
|
||||
PrepareStatement(LOGIN_SEL_ACCOUNT_ID_BY_NAME, "SELECT id FROM account WHERE username = ?", CONNECTION_SYNCH);
|
||||
PrepareStatement(LOGIN_SEL_ACCOUNT_LIST_BY_NAME, "SELECT id, username FROM account WHERE username = ?", CONNECTION_SYNCH);
|
||||
PrepareStatement(LOGIN_SEL_ACCOUNT_INFO_BY_NAME, "SELECT id, sessionkey, last_ip, locked, expansion, mutetime, locale, recruiter, os FROM account WHERE username = ?", CONNECTION_SYNCH);
|
||||
PrepareStatement(LOGIN_SEL_ACCOUNT_INFO_BY_BNET, "SELECT id, sessionkey, last_ip, locked, expansion, mutetime, locale, recruiter, os FROM account WHERE battlenet_account = ? AND battlenet_index = ?", CONNECTION_SYNCH);
|
||||
PrepareStatement(LOGIN_SEL_ACCOUNT_LIST_BY_EMAIL, "SELECT id, username FROM account WHERE email = ?", CONNECTION_SYNCH);
|
||||
PrepareStatement(LOGIN_SEL_NUM_CHARS_ON_REALM, "SELECT numchars FROM realmcharacters WHERE realmid = ? AND acctid= ?", CONNECTION_SYNCH);
|
||||
PrepareStatement(LOGIN_SEL_ACCOUNT_BY_IP, "SELECT id, username FROM account WHERE last_ip = ?", CONNECTION_SYNCH);
|
||||
@@ -101,4 +102,20 @@ void LoginDatabaseConnection::DoPrepareStatements()
|
||||
PrepareStatement(LOGIN_SEL_RBAC_ACCOUNT_PERMISSIONS, "SELECT permissionId, granted FROM rbac_account_permissions WHERE accountId = ? AND (realmId = ? OR realmId = -1) ORDER BY permissionId, realmId", CONNECTION_SYNCH);
|
||||
PrepareStatement(LOGIN_INS_RBAC_ACCOUNT_PERMISSION, "INSERT INTO rbac_account_permissions (accountId, permissionId, granted, realmId) VALUES (?, ?, ?, ?) ON DUPLICATE KEY UPDATE granted = VALUES(granted)", CONNECTION_ASYNC);
|
||||
PrepareStatement(LOGIN_DEL_RBAC_ACCOUNT_PERMISSION, "DELETE FROM rbac_account_permissions WHERE accountId = ? AND permissionId = ? AND (realmId = ? OR realmId = -1)", CONNECTION_ASYNC);
|
||||
|
||||
PrepareStatement(LOGIN_SEL_BNET_ACCOUNT_INFO, "SELECT sha_pass_hash, id, locked, lock_country, last_ip, v, s FROM battlenet_accounts WHERE email = ?", CONNECTION_SYNCH);
|
||||
PrepareStatement(LOGIN_DEL_BNET_EXPIRED_BANS, "UPDATE battlenet_account_bans SET active = 0 WHERE active = 1 AND unbandate <> bandate AND unbandate <= UNIX_TIMESTAMP()", CONNECTION_SYNCH);
|
||||
PrepareStatement(LOGIN_SEL_BNET_ACTIVE_ACCOUNT_BAN, "SELECT bandate, unbandate FROM battlenet_account_bans WHERE id = ? AND active = 1", CONNECTION_SYNCH);
|
||||
PrepareStatement(LOGIN_UPD_BNET_VS_FIELDS, "UPDATE battlenet_accounts SET v = ?, s = ? WHERE email = ?", CONNECTION_ASYNC);
|
||||
PrepareStatement(LOGIN_UPD_BNET_SESSION_KEY, "UPDATE battlenet_accounts SET sessionKey = ? WHERE id = ?", CONNECTION_ASYNC);
|
||||
PrepareStatement(LOGIN_SEL_BNET_RECONNECT_INFO, "SELECT ba.id, ba.sessionKey, a.id FROM battlenet_accounts ba LEFT JOIN account a ON ba.id = a.battlenet_account WHERE ba.email = ? AND a.battlenet_index = ?", CONNECTION_SYNCH);
|
||||
PrepareStatement(LOGIN_SEL_BNET_GAME_ACCOUNTS, "SELECT a.battlenet_index, a.id, ab.bandate, ab.unbandate, ab.active FROM account a LEFT JOIN account_banned ab ON a.id = ab.id WHERE battlenet_account = ?", CONNECTION_SYNCH);
|
||||
PrepareStatement(LOGIN_SEL_BNET_GAME_ACCOUNT, "SELECT a.id, ab.bandate, ab.unbandate, ab.active FROM account a LEFT JOIN account_banned ab ON a.id = ab.id WHERE battlenet_index = ? AND battlenet_account = ?", CONNECTION_SYNCH);
|
||||
PrepareStatement(LOGIN_UPD_BNET_LAST_LOGIN_INFO, "UPDATE battlenet_accounts SET last_ip = ?, last_login = NOW(), locale = ?, failed_logins = 0, os = ? WHERE id = ?", CONNECTION_ASYNC);
|
||||
PrepareStatement(LOGIN_SEL_BNET_CHARACTER_COUNTS, "SELECT rc.numchars, r.id, r.Region, r.Battlegroup, r.gamebuild FROM realmcharacters rc INNER JOIN realmlist r ON rc.realmid = r.id WHERE rc.acctid = ?", CONNECTION_SYNCH);
|
||||
PrepareStatement(LOGIN_INS_BNET_ACCOUNT, "INSERT INTO battlenet_accounts (`email`,`sha_pass_hash`) VALUES (?, ?)", CONNECTION_ASYNC);
|
||||
PrepareStatement(LOGIN_SEL_BNET_ACCOUNT_EMAIL_BY_ID, "SELECT email FROM battlenet_accounts WHERE id = ?", CONNECTION_SYNCH);
|
||||
PrepareStatement(LOGIN_SEL_BNET_ACCOUNT_ID_BY_EMAIL, "SELECT id FROM battlenet_accounts WHERE email = ?", CONNECTION_SYNCH);
|
||||
PrepareStatement(LOGIN_UPD_BNET_PASSWORD, "UPDATE account SET v = '', s = '', username = ?, sha_pass_hash = ? WHERE id = ?", CONNECTION_ASYNC);
|
||||
PrepareStatement(LOGIN_SEL_BNET_CHECK_PASSWORD, "SELECT 1 FROM battlenet_accounts WHERE id = ? AND sha_pass_hash = ?", CONNECTION_ASYNC);
|
||||
}
|
||||
|
||||
@@ -62,6 +62,7 @@ enum LoginDatabaseStatements
|
||||
LOGIN_SEL_ACCOUNT_ID_BY_NAME,
|
||||
LOGIN_SEL_ACCOUNT_LIST_BY_NAME,
|
||||
LOGIN_SEL_ACCOUNT_INFO_BY_NAME,
|
||||
LOGIN_SEL_ACCOUNT_INFO_BY_BNET,
|
||||
LOGIN_SEL_ACCOUNT_LIST_BY_EMAIL,
|
||||
LOGIN_SEL_NUM_CHARS_ON_REALM,
|
||||
LOGIN_SEL_ACCOUNT_BY_IP,
|
||||
@@ -120,6 +121,23 @@ enum LoginDatabaseStatements
|
||||
LOGIN_SEL_RBAC_ACCOUNT_PERMISSIONS,
|
||||
LOGIN_INS_RBAC_ACCOUNT_PERMISSION,
|
||||
LOGIN_DEL_RBAC_ACCOUNT_PERMISSION,
|
||||
|
||||
LOGIN_SEL_BNET_ACCOUNT_INFO,
|
||||
LOGIN_DEL_BNET_EXPIRED_BANS,
|
||||
LOGIN_SEL_BNET_ACTIVE_ACCOUNT_BAN,
|
||||
LOGIN_UPD_BNET_VS_FIELDS,
|
||||
LOGIN_UPD_BNET_SESSION_KEY,
|
||||
LOGIN_SEL_BNET_RECONNECT_INFO,
|
||||
LOGIN_SEL_BNET_GAME_ACCOUNTS,
|
||||
LOGIN_SEL_BNET_GAME_ACCOUNT,
|
||||
LOGIN_UPD_BNET_LAST_LOGIN_INFO,
|
||||
LOGIN_SEL_BNET_CHARACTER_COUNTS,
|
||||
LOGIN_INS_BNET_ACCOUNT,
|
||||
LOGIN_SEL_BNET_ACCOUNT_EMAIL_BY_ID,
|
||||
LOGIN_SEL_BNET_ACCOUNT_ID_BY_EMAIL,
|
||||
LOGIN_UPD_BNET_PASSWORD,
|
||||
LOGIN_SEL_BNET_CHECK_PASSWORD,
|
||||
|
||||
MAX_LOGINDATABASE_STATEMENTS
|
||||
};
|
||||
|
||||
|
||||
@@ -524,6 +524,17 @@ void vutf8printf(FILE* out, const char *str, va_list* ap)
|
||||
#endif
|
||||
}
|
||||
|
||||
bool Utf8ToUpperOnlyLatin(std::string& utf8String)
|
||||
{
|
||||
std::wstring wstr;
|
||||
if (!Utf8toWStr(utf8String, wstr))
|
||||
return false;
|
||||
|
||||
std::transform(wstr.begin(), wstr.end(), wstr.begin(), wcharToUpperOnlyLatin);
|
||||
|
||||
return WStrToUtf8(wstr, utf8String);
|
||||
}
|
||||
|
||||
std::string ByteArrayToHexStr(uint8 const* bytes, uint32 arrayLen, bool reverse /* = false */)
|
||||
{
|
||||
int32 init = 0;
|
||||
@@ -547,3 +558,28 @@ std::string ByteArrayToHexStr(uint8 const* bytes, uint32 arrayLen, bool reverse
|
||||
|
||||
return ss.str();
|
||||
}
|
||||
|
||||
void HexStrToByteArray(std::string const& str, uint8* out, bool reverse /*= false*/)
|
||||
{
|
||||
// string must have even number of characters
|
||||
if (str.length() & 1)
|
||||
return;
|
||||
|
||||
int32 init = 0;
|
||||
int32 end = str.length();
|
||||
int8 op = 1;
|
||||
|
||||
if (reverse)
|
||||
{
|
||||
init = str.length() - 2;
|
||||
end = -2;
|
||||
op = -1;
|
||||
}
|
||||
|
||||
uint32 j = 0;
|
||||
for (int32 i = init; i != end; i += 2 * op)
|
||||
{
|
||||
char buffer[3] = { str[i], str[i + 1], '\0' };
|
||||
out[j++] = strtoul(buffer, NULL, 16);
|
||||
}
|
||||
}
|
||||
|
||||
@@ -344,6 +344,7 @@ bool consoleToUtf8(const std::string& conStr, std::string& utf8str);
|
||||
bool Utf8FitTo(const std::string& str, std::wstring search);
|
||||
void utf8printf(FILE* out, const char *str, ...);
|
||||
void vutf8printf(FILE* out, const char *str, va_list* ap);
|
||||
bool Utf8ToUpperOnlyLatin(std::string& utf8String);
|
||||
|
||||
bool IsIPAddress(char const* ipaddress);
|
||||
|
||||
@@ -356,6 +357,7 @@ std::string GetAddressString(ACE_INET_Addr const& addr);
|
||||
uint32 CreatePIDFile(const std::string& filename);
|
||||
|
||||
std::string ByteArrayToHexStr(uint8 const* bytes, uint32 length, bool reverse = false);
|
||||
void HexStrToByteArray(std::string const& str, uint8* out, bool reverse = false);
|
||||
#endif
|
||||
|
||||
//handler for operations on large flags
|
||||
|
||||
@@ -184,7 +184,7 @@ int RASocket::check_access_level(const std::string& user)
|
||||
{
|
||||
std::string safeUser = user;
|
||||
|
||||
AccountMgr::normalizeString(safeUser);
|
||||
Utf8ToUpperOnlyLatin(safeUser);
|
||||
|
||||
PreparedStatement* stmt = LoginDatabase.GetPreparedStatement(LOGIN_SEL_ACCOUNT_ACCESS);
|
||||
stmt->setString(0, safeUser);
|
||||
@@ -215,10 +215,10 @@ int RASocket::check_access_level(const std::string& user)
|
||||
int RASocket::check_password(const std::string& user, const std::string& pass)
|
||||
{
|
||||
std::string safe_user = user;
|
||||
AccountMgr::normalizeString(safe_user);
|
||||
Utf8ToUpperOnlyLatin(safe_user);
|
||||
|
||||
std::string safe_pass = pass;
|
||||
AccountMgr::normalizeString(safe_pass);
|
||||
Utf8ToUpperOnlyLatin(safe_pass);
|
||||
|
||||
std::string hash = AccountMgr::CalculateShaPassHash(safe_user, safe_pass);
|
||||
|
||||
|
||||
Reference in New Issue
Block a user