Advertisement
Guest User

Untitled

a guest
Jun 21st, 2017
87
0
Never
Not a member of Pastebin yet? Sign Up, it unlocks many cool features!
text 91.61 KB | None | 0 0
  1.  
  2. program MEOW;
  3.  
  4. {$APPTYPE CONSOLE}
  5.  
  6. {$DEFINE THREAD_SAFE}
  7. {$DEFINE LOG_CONFIG}
  8. {$DEFINE LOG_SQL}
  9. {$DEFINE LOG_UNHANDLED_PACKET_FAMILY}
  10. {$DEFINE LOG_UNHANDLED_PACKET_ACTION}
  11.  
  12. uses
  13. Windows, WinSock;
  14.  
  15. type
  16. procedureref = reference to procedure;
  17.  
  18. CriticalSectionHelper = record helper for TRTLCriticalSection
  19. procedure Create; inline;
  20. procedure Free; inline;
  21.  
  22. procedure Enter; inline;
  23. procedure Leave; inline;
  24.  
  25. procedure Section(Code: procedureref); inline;
  26. end;{CriticalSectionHelper}
  27.  
  28. const
  29. sqlite3 = 'sqlite3.dll';
  30.  
  31. type
  32. TSQLiteDB = Pointer;
  33. TSQLiteQuery = Pointer;
  34.  
  35. function sqlite3_open(DBName: PAnsiChar; var DB: TSQLiteDB): Integer; cdecl; external sqlite3;
  36. function sqlite3_close(DB: TSQLiteDB): Integer; cdecl; external sqlite3;
  37. function sqlite3_prepare(DB: TSQLiteDB; QueryStr: PAnsiChar; QuerySize: Integer; var Query: TSQLiteQuery; var NextQuery: PAnsiChar): Integer; cdecl; external sqlite3;
  38. function sqlite3_step(Query: TSQLiteQuery): Integer; cdecl; external sqlite3;
  39. function sqlite3_finalize(Query: TSQLiteQuery): Integer; cdecl; external sqlite3;
  40. function sqlite3_column_count(Query: TSQLiteQuery): Integer; cdecl; external sqlite3;
  41. function sqlite3_column_name(Query: TSQLiteQuery; i: Integer): PAnsiChar; cdecl; external sqlite3;
  42. function sqlite3_column_type(Query: TSQLiteQuery; i: Integer): Integer; cdecl; external sqlite3;
  43. function sqlite3_column_int(Query: TSQLiteQuery; i: Integer): Integer; cdecl; external sqlite3;
  44. function sqlite3_column_text(Query: TSQLiteQuery; i: Integer): PAnsiChar; cdecl; external sqlite3;
  45.  
  46. const
  47. SQLITE_OK = 0;
  48. SQLITE_ROW = 100;
  49. SQLITE_DONE = 101;
  50.  
  51. SQLITE_INTEGER = 1;
  52. SQLITE_TEXT = 3;
  53. SQLITE_NULL = 5;
  54.  
  55. type
  56. TDatabase = class
  57. var CriticalSection: TRTLCriticalSection;
  58.  
  59. var FileName: AnsiString;
  60. var DB: TSQLiteDB;
  61.  
  62. var Transaction: Boolean;
  63.  
  64. type TTable = class
  65. var Database: TDatabase;
  66.  
  67. type TCell = record
  68. DataType: Integer;
  69.  
  70. DataStr: AnsiString;
  71. DataInt: Integer;
  72. end;{TCell}
  73.  
  74. var ColumnNames: array of AnsiString;
  75. var Table: array of array of TCell;
  76.  
  77. constructor Create(ADatabase: TDatabase; SQL: AnsiString);
  78. destructor Destroy; override;
  79.  
  80. function Empty: Boolean; inline;
  81.  
  82. function Column(Name: AnsiString): Integer;
  83.  
  84. function Value(Name: AnsiString; Row: Integer = 0; Default: AnsiString = ''): AnsiString; overload;
  85. function Value(Name: AnsiString; Row: Integer = 0; Default: Integer = 0): Integer; overload;
  86. end;{TTable}
  87.  
  88. constructor Create(AFileName: AnsiString);
  89. destructor Destroy; override;
  90.  
  91. function Prepare(SQL: AnsiString): TSQLiteQuery;
  92. procedure Finalize(var Query: TSQLiteQuery);
  93.  
  94. function Query (SQL: AnsiString): Boolean;
  95. function QueryTable(SQL: AnsiString): TTable; inline;
  96.  
  97. function TableExists(Name: AnsiString): Boolean;
  98.  
  99. function BeginTransaction: Boolean;
  100. function EndTransaction(Rollback: Boolean = False): Boolean;
  101. end;{TDatabase}
  102.  
  103. TINIFile = class
  104. var CriticalSection: TRTLCriticalSection;
  105.  
  106. var FileName: AnsiString;
  107.  
  108. constructor Create(AFileName: AnsiString);
  109. destructor Destroy; override;
  110.  
  111. function Read(Section, Key: AnsiString; Default: AnsiString = ''): AnsiString; overload;
  112. function Read(Section, Key: AnsiString; Default: Integer = 0): Integer; overload;
  113. function Read(Section, Key: AnsiString; Default: Boolean = False): Boolean; overload;
  114. end;{TINIFile}
  115.  
  116. TArray<T: class> = class
  117. var Items: array of T;
  118.  
  119. constructor Create;
  120. destructor Destroy; override;
  121.  
  122. function Find (Item: T): Integer;
  123. function Add (Item: T): Integer;
  124. function Remove(Item: T): Integer;
  125.  
  126. procedure Clear;
  127. end;{TArray<T>}
  128.  
  129. TSHA256Hash = packed record
  130. A, B, C, D, E, F, G, H: Cardinal;
  131. end;{TSHA256Hash}
  132.  
  133. TSHA256 = record
  134. Hash: TSHA256Hash;
  135. MLen: Int64;
  136. Buffer: array[0..63] of Byte;
  137. Index: Integer;
  138.  
  139. procedure Init;
  140. procedure Compress;
  141. procedure Update(Data: Pointer; Len: Integer);
  142. function Done: AnsiString;
  143.  
  144. class function HashStr(S: AnsiString): AnsiString; static;
  145. end;{TSHA256}
  146.  
  147. Server = class abstract
  148. const RequiredVersion: array[0..2] of Byte = (0, 0, 28);
  149.  
  150. const ReceiveKey = 8;
  151. const SendKey = 10;
  152.  
  153. const PacketFamilyRaw = 255;
  154. const PacketFamilyConnection = 1;
  155. const PacketFamilyAccount = 2;
  156. const PacketFamilyLogin = 4;
  157. const PacketFamilyGameState = 5;
  158. const PacketFamilyWalk = 6;
  159. const PacketFamilyFace = 7;
  160. const PacketFamilyTalk = 18;
  161. const PacketFamilyPlayers = 22;
  162. const PacketFamilyRequest = 27;
  163.  
  164. const PacketActionRaw = 255;
  165. const PacketActionRequest = 1;
  166. const PacketActionAccept = 2;
  167. const PacketActionReply = 3;
  168. const PacketActionRemove = 4;
  169. const PacketActionAgree = 5;
  170. const PacketActionCreate = 6;
  171. const PacketActionPlayer = 8;
  172. const PacketActionMessage = 15;
  173. const PacketActionSpecial = 16;
  174. const PacketActionAdmin = 17;
  175. const PacketActionReport = 21;
  176.  
  177. type TPacket = record
  178. Family: Byte;
  179. Action: Byte;
  180.  
  181. Data: AnsiString;
  182.  
  183. Time: Cardinal;
  184.  
  185. procedure SetID(AFamily, AAction: Byte);
  186.  
  187. procedure Reset; inline;
  188.  
  189. procedure Discard(Count: Integer = 1); inline;
  190.  
  191. procedure AddByte(b: Byte); inline;
  192. procedure AddInt1(i: Byte); inline;
  193. procedure AddInt2(i: Word); inline;
  194. procedure AddInt3(i: Cardinal); inline;
  195. procedure AddInt4(i: Cardinal); inline;
  196. procedure AddBreakString(s: AnsiString); inline;
  197. procedure AddString (s: AnsiString); inline;
  198.  
  199. function GetByte: Byte;
  200. function GetInt1: Byte;
  201. function GetInt2: Word;
  202. function GetInt3: Cardinal;
  203. function GetInt4: Cardinal;
  204. function GetBreakString: AnsiString;
  205. function GetString(Len: Integer = -1): AnsiString;
  206. end;{TPacket}
  207.  
  208. TGameData = class abstract
  209. var Data: AnsiString;
  210. var CRC: array[0..3] of Byte;
  211. var Len: array[0..1] of Byte;
  212.  
  213. var FileName: AnsiString;
  214.  
  215. class function DataID: Byte; virtual; abstract;
  216.  
  217. constructor Create(AFileName: AnsiString);
  218.  
  219. function Load: Boolean; virtual;
  220. end;{TGameData}
  221.  
  222. TItemData = class(TGameData)
  223. class function DataID: Byte; override;
  224. end;{TItemData}
  225.  
  226. TNPCData = class(TGameData)
  227. class function DataID: Byte; override;
  228. end;{TNPCData}
  229.  
  230. TSpellData = class(TGameData)
  231. class function DataID: Byte; override;
  232. end;{TSpellData}
  233.  
  234. TClassData = class(TGameData)
  235. class function DataID: Byte; override;
  236. end;{TClassData}
  237.  
  238. TMapData = class(TGameData)
  239. class function DataID: Byte; override;
  240. end;{TMapData}
  241.  
  242. class var ItemData: TItemData;
  243. class var NPCData: TNPCData;
  244. class var SpellData: TSpellData;
  245. class var ClassData: TClassData;
  246. class var MapData: TMapData;
  247.  
  248. type TSession = class
  249. var Socket: TSocket;
  250. var IPStr: AnsiString;
  251. var IPInt: Integer;
  252.  
  253. var Thread: THandle;
  254.  
  255. var ID: Cardinal;
  256. var Initialized: Boolean;
  257. var LoggedIn: Boolean;
  258.  
  259. var Packet: record
  260. Buffer: AnsiString;
  261.  
  262. Queue: record
  263. Items: array of TPacket;
  264. Time: Cardinal;
  265. Active: Boolean;
  266. end;{Queue}
  267.  
  268. Receive: TPacket;
  269. Send: TPacket;
  270.  
  271. Time: Cardinal;
  272. end;{Packet}
  273.  
  274. var Name: AnsiString;
  275. var Password: AnsiString;
  276. var HDDSerial: AnsiString;
  277.  
  278. var X: Integer;
  279. var Y: Integer;
  280. var D: Integer;
  281. var S: Integer;
  282.  
  283. var Admin: Integer;
  284.  
  285. var Tag: AnsiString;
  286. var Sex: Integer;
  287. var HairStyle: Integer;
  288. var HairColour: Integer;
  289. var Race: Integer;
  290.  
  291. var ClassID: Integer;
  292. var Title: AnsiString;
  293. var Home: AnsiString;
  294. var Partner: AnsiString;
  295. var Guild: AnsiString;
  296. var Rank: AnsiString;
  297.  
  298. var Boots: Integer;
  299. var Armour: Integer;
  300. var Hat: Integer;
  301. var Shield: Integer;
  302. var Weapon: Integer;
  303.  
  304. constructor Create(ASocket: TSocket);
  305. destructor Destroy; override;
  306.  
  307. function Sync(Discard: Boolean = False): Boolean;
  308. procedure Unload;
  309.  
  310. procedure Log(Params: array of const);
  311.  
  312. procedure Send(var Packet: TPacket; Raw: Boolean = False); overload;
  313. procedure Send( Raw: Boolean = False); overload; inline;
  314.  
  315. procedure SendData(Data: TGameData);
  316.  
  317. procedure Login;
  318. procedure Logout;
  319.  
  320. procedure BuildCharacterPacket(var Packet: TPacket);
  321.  
  322. const DirectionDown = 0;
  323. const DirectionLeft = 1;
  324. const DirectionUp = 2;
  325. const DirectionRight = 3;
  326.  
  327. procedure Refresh;
  328. function Walk(Direction: Integer; Admin: Boolean = False; Ghost: Boolean = False): Boolean;
  329. function Face(Direction: Integer): Boolean;
  330. function Say(Text: AnsiString): Boolean;
  331.  
  332. function Execute: Boolean;
  333.  
  334. procedure DefaultHandler(var Param); override;
  335. procedure UnhandledAction(Name: AnsiString = '');
  336.  
  337. procedure HandleRaw (var Param); message Server.PacketFamilyRaw;
  338. procedure HandleConnection(var Param); message Server.PacketFamilyConnection;
  339. procedure HandleAccount (var Param); message Server.PacketFamilyAccount;
  340. procedure HandleLogin (var Param); message Server.PacketFamilyLogin;
  341. procedure HandleGameState (var Param); message Server.PacketFamilyGameState;
  342. procedure HandleWalk (var Param); message Server.PacketFamilyWalk;
  343. procedure HandleFace (var Param); message Server.PacketFamilyFace;
  344. procedure HandleRequest (var Param); message Server.PacketFamilyRequest;
  345. procedure HandleTalk (var Param); message Server.PacketFamilyTalk;
  346. end;{Session}
  347.  
  348. class var CriticalSection: TRTLCriticalSection;
  349.  
  350. class var Sessions: TArray<TSession>;
  351. class var Socket: TSocket;
  352.  
  353. class var Database: TDatabase;
  354. class var Configuration: TINIFile;
  355.  
  356. class var Connection: record
  357. Bind: AnsiString;
  358. Port: Word;
  359. Timeout: Cardinal;
  360.  
  361. BytesIn: Int64;
  362. BytesOut: Int64;
  363. end;{Connection}
  364.  
  365. class var PacketQueue: record
  366. Enabled: Boolean;
  367. Size: Integer;
  368. end;{Packet}
  369.  
  370. class var Defaults: record
  371. X, Y, D: Integer;
  372. end;{Defaults}
  373.  
  374. const ViewRange = 12;
  375. const TextLength = 100;
  376.  
  377. class constructor Create;
  378. class destructor Destroy;
  379.  
  380. class procedure Main;
  381.  
  382. class var Caption: AnsiString;
  383. class procedure UpdateCaption;
  384.  
  385. class procedure Log(Params: array of const; Prefix: AnsiString = '');
  386.  
  387. class procedure Send(var Packet: TPacket; Sender: TSession = nil; Ranged: Boolean = True);
  388.  
  389. class function GetSessionByID (ID: Cardinal): TSession;
  390. class function GetSessionByName(Name: AnsiString): TSession;
  391.  
  392. const NameMax = 12;
  393. const NameChars = 'abcdefghijklmnopqrstuvwxyz0123456789';
  394.  
  395. class function ValidName(Name: AnsiString): Boolean;
  396.  
  397. class function GetAccount(Name: AnsiString; Items: AnsiString = '*'): TDatabase.TTable;
  398. class function AccountExists(Name: AnsiString): Boolean;
  399. end;{Server}
  400.  
  401. const
  402. EOInt1Max = 253;
  403. EOInt2Max = 64009;
  404. EOInt3Max = 16194277;
  405.  
  406. function PackEOInt(b1: Byte = 0; b2: Byte = 0; b3: Byte = 0; b4: Byte = 0): Cardinal;
  407. begin
  408. if b1 = 254 then b1 := 0 else if b1 > 0 then dec(b1);
  409. if b2 = 254 then b2 := 0 else if b2 > 0 then dec(b2);
  410. if b3 = 254 then b3 := 0 else if b3 > 0 then dec(b3);
  411. if b4 = 254 then b4 := 0 else if b4 > 0 then dec(b4);
  412.  
  413. Result := (b4 * EOInt3Max) + (b3 * EOInt2Max) + (b2 * EOInt1Max) + b1;
  414. end;{PackEOInt}
  415.  
  416. function UnpackEOInt(Num: Cardinal): AnsiString;
  417. var
  418. i: Cardinal;
  419. begin
  420. Result := #254#254#254#254;
  421.  
  422. i := Num;
  423.  
  424. if i >= EOInt3Max then
  425. begin
  426. Result[4] := AnsiChar(Num div EOInt3Max + 1);
  427. Num := Num mod EOInt3Max;
  428. end;{if i >= EOInt3Max}
  429.  
  430. if i >= EOInt2Max then
  431. begin
  432. Result[3] := AnsiChar(Num div EOInt2Max + 1);
  433. Num := Num mod EOInt2Max;
  434. end;{if i >= EOInt2Max}
  435.  
  436. if i >= EOInt1Max then
  437. begin
  438. Result[2] := AnsiChar(Num div EOInt1Max + 1);
  439. Num := Num mod EOInt1Max;
  440. end;{if i >= EOInt3Max}
  441.  
  442. Result[1] := AnsiChar(Num + 1);
  443. end;{UnpackEOInt}
  444.  
  445. function FoldData(Str: AnsiString; Key: Byte): AnsiString;
  446. var
  447. i: Integer;
  448. c: AnsiChar;
  449. Buffer: AnsiString;
  450. begin
  451. if Key = 0 then exit(Str);
  452.  
  453. Result := '';
  454. Buffer := '';
  455.  
  456. for c in Str do
  457. begin
  458. if (ord(c) mod Key) = 0 then
  459. Buffer := Buffer + c
  460. else
  461. begin
  462. if length(Buffer) > 0 then
  463. begin
  464. for i := length(Buffer) downto 1 do
  465. Result := Result + Buffer[i];
  466.  
  467. Buffer := '';
  468. end;{if length(Buffer)}
  469.  
  470. Result := Result + c;
  471. end;{else}
  472. end;{for c}
  473.  
  474. if length(Buffer) > 0 then
  475. for i := length(Buffer) downto 1 do
  476. Result := Result + Buffer[i];
  477. end;{FoldData}
  478.  
  479. function bswap(A: integer): Integer;
  480. asm
  481. bswap eax
  482. end;{bswap}
  483.  
  484. procedure bswap256(s, d: PInteger);
  485. asm
  486. push ebx
  487. mov ecx, eax
  488. mov eax,[ecx]; mov ebx,[ecx+4]; bswap eax; bswap ebx; mov [edx], eax; mov [edx+4], ebx
  489. mov eax,[ecx+8]; mov ebx,[ecx+12]; bswap eax; bswap ebx; mov [edx+8], eax; mov [edx+12], ebx
  490. mov eax,[ecx+16]; mov ebx,[ecx+20]; bswap eax; bswap ebx; mov [edx+16], eax; mov [edx+20], ebx
  491. mov eax,[ecx+24]; mov ebx,[ecx+28]; bswap eax; bswap ebx; mov [edx+24], eax; mov [edx+28], ebx
  492. pop ebx
  493. end;{bswap256}
  494.  
  495. function InterlockedExchangeAdd64(var Addend: Int64; Value: Int64): Int64; register;
  496. asm
  497. push edi
  498. push esi
  499. push ebp
  500. push ebx
  501.  
  502. mov esi, dword ptr [Value]
  503. mov edi, dword ptr [Value + 4]
  504. mov ebp, eax
  505.  
  506. mov eax, [ebp]
  507. mov edx, [ebp + 4]
  508. @@lockmore:
  509. mov ecx, edx
  510. mov ebx, eax
  511.  
  512. add ebx, esi
  513. adc ecx, edi
  514.  
  515. lock cmpxchg8b [ebp]
  516. jnz @@lockmore
  517.  
  518. pop ebx
  519. pop ebp
  520. pop esi
  521. pop edi
  522. end;{InterlockedExchangeAdd64}
  523.  
  524. function Lower(S: AnsiString): AnsiString;
  525. begin
  526. Result := S;
  527. if length(Result) = 0 then exit;
  528.  
  529. CharLowerBuffA(Pointer(Result), length(Result));
  530. end;{Lower}
  531.  
  532. function Int(S: AnsiString; Default: Integer = 0): Integer;
  533. var
  534. Code: Integer;
  535. begin
  536. Val(String(S), Result, Code);
  537. if Code <> 0 then Result := Default;
  538. end;{Int}
  539.  
  540. function Str(I: Integer): AnsiString; overload;
  541. var
  542. S: ShortString;
  543. begin
  544. System.Str(I, S);
  545. Result := AnsiString(S);
  546. end;{Str(Integer}
  547.  
  548. function Str(F: Extended): AnsiString; overload;
  549. var
  550. S: ShortString;
  551. begin
  552. System.Str(F:2:2, S);
  553. Result := AnsiString(S);
  554. end;{Str(Extended}
  555.  
  556. function Tidy(s: AnsiString): AnsiString;
  557. var
  558. i: Integer;
  559. c: AnsiChar;
  560. begin
  561. Result := '';
  562.  
  563. for c in s do
  564. if pos(String(c), '0123456789.') > 0 then Result := Result + c;
  565.  
  566. if length(Result) = 0 then exit('0');
  567.  
  568. if pos('.', String(Result)) > 0 then
  569. begin
  570. while Result[length(Result)] = '0' do
  571. Result := copy(Result, 1, length(Result) - 1);
  572.  
  573. if Result[length(Result)] = '.' then
  574. Result := copy(Result, 1, length(Result) - 1);
  575. end;{if pos('.'...}
  576.  
  577. while (length(Result) > 0) and (Result[1] = '0') do
  578. Result := copy(Result, 2, length(Result));
  579.  
  580. i := pos('.', String(Result)) - 1; if i < 1 then i := length(Result);
  581.  
  582. repeat
  583. dec(i, 3); if i < 1 then break;
  584.  
  585. Result := copy(Result, 1, i) + ',' + copy(Result, i + 1, length(Result));
  586. until False;
  587.  
  588. if (length(Result) = 0) or (Result[1] = '.') then Result := '0' + Result;
  589. end;{Tidy}
  590.  
  591. function Scale(i: Int64): AnsiString;
  592. const
  593. MinAdjustValue = 900;
  594. ScaleStr: array[0..3] of AnsiString = ('B', 'KB', 'MB', 'GB');
  595. var
  596. j: Integer;
  597. k: Extended;
  598. begin
  599. j := 0;
  600. k := i;
  601.  
  602. while k > MinAdjustValue do
  603. begin
  604. k := k / 1024;
  605. inc(j); if j = high(ScaleStr) then break;
  606. end;{while i}
  607.  
  608. Result := Tidy(Str(k)) + ScaleStr[j];
  609. end;{Scale}
  610.  
  611. function Str(B: Boolean): AnsiString; overload;
  612. begin
  613. if B then
  614. Result := 'true'
  615. else
  616. Result := 'false';
  617. end;{Str(Boolean}
  618.  
  619. function Bool(S: AnsiString; Default: Boolean = False): Boolean;
  620. begin
  621. if length(S) = 0 then exit(Default);
  622. S := Lower(copy(S, 1, 2));
  623.  
  624. if (S[1] = 't') or (S = 'ok') or (S = 'on') then
  625. Result := True
  626. else
  627. Result := Int(S, Integer(Default)) <> 0;
  628. end;{Bool}
  629.  
  630. procedure Error(Params: array of const);
  631. begin
  632. Server.Log(Params, '/!\ ERROR');
  633. halt(1);
  634. end;{Error}
  635.  
  636. procedure CriticalSectionHelper.Create;
  637. begin
  638. {$IFDEF THREAD_SAFE}
  639. InitializeCriticalSection(Self);
  640. {$ENDIF THREAD_SAFE}
  641. end;{CriticalSectionHelper.Create}
  642.  
  643. procedure CriticalSectionHelper.Free;
  644. begin
  645. {$IFDEF THREAD_SAFE}
  646. DeleteCriticalSection(Self);
  647. {$ENDIF THREAD_SAFE}
  648. end;{CriticalSectionHelper.Free}
  649.  
  650. procedure CriticalSectionHelper.Enter;
  651. begin
  652. {$IFDEF THREAD_SAFE}
  653. EnterCriticalSection(Self);
  654. {$ENDIF THREAD_SAFE}
  655. end;{CriticalSectionHelper.Enter}
  656.  
  657. procedure CriticalSectionHelper.Leave;
  658. begin
  659. {$IFDEF THREAD_SAFE}
  660. LeaveCriticalSection(Self);
  661. {$ENDIF THREAD_SAFE}
  662. end;{CriticalSectionHelper.Leave}
  663.  
  664. procedure CriticalSectionHelper.Section(Code: procedureref);
  665. begin
  666. Enter;
  667. try
  668. Code;
  669. finally
  670. Leave;
  671. end;{try...finally}
  672. end;{CriticalSectionHelper.Secion}
  673.  
  674. constructor TDatabase.TTable.Create(ADatabase: TDatabase; SQL: AnsiString);
  675. var
  676. i: Integer;
  677. Query: TSQLiteQuery;
  678. begin
  679. inherited Create;
  680.  
  681. Database := ADatabase;
  682.  
  683. Database.CriticalSection.Enter;
  684.  
  685. try
  686. Query := Database.Prepare(SQL);
  687. if Query = nil then exit;
  688.  
  689. while sqlite3_step(Query) = SQLITE_ROW do
  690. begin
  691. if length(Table) = 0 then
  692. begin
  693. SetLength(ColumnNames, sqlite3_column_count(Query));
  694.  
  695. for i := 0 to length(ColumnNames) - 1 do
  696. ColumnNames[i] := lower(sqlite3_column_name(Query, i));
  697. end;{if length(Table) = 0}
  698.  
  699. SetLength(Table, length(Table) + 1);
  700. SetLength(Table[high(Table)], length(ColumnNames));
  701.  
  702. for i := 0 to length(ColumnNames) - 1 do
  703. with Table[high(Table)][i] do
  704. begin
  705. DataType := sqlite3_column_type(Query, i);
  706.  
  707. case DataType of
  708. SQLITE_INTEGER:
  709. begin
  710. DataInt := sqlite3_column_int(Query, i);
  711. DataStr := Str(DataInt);
  712. end;{SQLITE_INTEGER:}
  713.  
  714. SQLITE_TEXT:
  715. begin
  716. DataStr := sqlite3_column_text(Query, i);
  717. DataInt := Int(DataStr);
  718. end;{SQLITE_TEXT:}
  719. else
  720. DataStr := '';
  721. DataInt := 0;
  722. end;{case DataType}
  723. end;{with Table}
  724. end;{while sqlite3_step}
  725. finally
  726. Database.Finalize(Query);
  727. end;{try...finally}
  728. end;{TDatabase.TTable.Create}
  729.  
  730. destructor TDatabase.TTable.Destroy;
  731. begin
  732. Database.CriticalSection.Leave;
  733.  
  734. inherited;
  735. end;{TDatabase.TTable.Destroy}
  736.  
  737. function TDatabase.TTable.Empty: Boolean;
  738. begin
  739. Result := length(Table) = 0;
  740. end;{TDatabase.Empty}
  741.  
  742. function TDatabase.TTable.Column(Name: AnsiString): Integer;
  743. var
  744. i: Integer;
  745. begin
  746. Name := lower(Name);
  747.  
  748. for i := 0 to length(ColumnNames) - 1 do
  749. if Name = ColumnNames[i] then exit(i);
  750.  
  751. Result := -1;
  752. end;{TDatabase.TTable.Column}
  753.  
  754. function TDatabase.TTable.Value(Name: AnsiString; Row: Integer = 0; Default: AnsiString = ''): AnsiString;
  755. var
  756. i: Integer;
  757. begin
  758. i := Column(Name);
  759. if i = -1 then exit(Default);
  760.  
  761. Result := Table[Row][i].DataStr;
  762. end;{TDatabase.TTable.Value(AnsiString}
  763.  
  764. function TDatabase.TTable.Value(Name: AnsiString; Row: Integer = 0; Default: Integer = 0): Integer;
  765. var
  766. i: Integer;
  767. begin
  768. i := Column(Name);
  769. if i = -1 then exit(Default);
  770.  
  771. Result := Table[Row][i].DataInt;
  772. end;{TDatabase.TTable.Value(Integer}
  773.  
  774. constructor TDatabase.Create(AFileName: AnsiString);
  775. begin
  776. inherited Create;
  777.  
  778. CriticalSection.Create;
  779.  
  780. FileName := AFileName;
  781.  
  782. Transaction := False;
  783.  
  784. if sqlite3_open(PAnsiChar(FileName), DB) <> SQLITE_OK then
  785. Error(['Failed to open database "', FileName, '"']);
  786. end;{TDatabase.Create}
  787.  
  788. destructor TDatabase.Destroy;
  789. begin
  790. if DB <> nil then
  791. begin
  792. if Transaction then
  793. EndTransaction(True);
  794.  
  795. sqlite3_close(DB);
  796. DB := nil;
  797. end;{if DB <> nil}
  798.  
  799. CriticalSection.Free;
  800.  
  801. inherited;
  802. end;{TDatabase.Destroy}
  803.  
  804. function TDatabase.Prepare(SQL: AnsiString): TSQLiteQuery;
  805. var
  806. NextQuery: PAnsiChar;
  807. begin
  808. if DB = nil then exit(nil);
  809.  
  810. {$IFDEF LOG_SQL}
  811. Server.Log(['Database (', FileName, ') ', SQL]);
  812. {$ENDIF LOG_SQL}
  813.  
  814. if sqlite3_prepare(DB, PAnsiChar(SQL), -1, Result, NextQuery) <> SQLITE_OK then
  815. if Result <> nil then
  816. Finalize(Result);
  817. end;{TDatabase.Prepare}
  818.  
  819. procedure TDatabase.Finalize(var Query: TSQLiteQuery);
  820. begin
  821. if Query = nil then exit;
  822.  
  823. sqlite3_finalize(Query);
  824. Query := nil;
  825. end;{TDatabase.Finalize}
  826.  
  827. function TDatabase.Query(SQL: AnsiString): Boolean;
  828. var
  829. Query: TSQLiteQuery;
  830. begin
  831. CriticalSection.Enter;
  832. try
  833. Query := Prepare(SQL);
  834. if Query = nil then exit(False);
  835.  
  836. Result := sqlite3_step(Query) = SQLITE_DONE;
  837. finally
  838. Finalize(Query);
  839.  
  840. CriticalSection.Leave;
  841. end;{try...finally}
  842. end;{TDatabase.Query}
  843.  
  844. function TDatabase.QueryTable(SQL: AnsiString): TTable;
  845. begin
  846. Result := TTable.Create(Self, SQL);
  847. end;{TDatabase.QueryTable}
  848.  
  849. function TDatabase.TableExists(Name: AnsiString): Boolean;
  850. begin
  851. with QueryTable('SELECT `sql` FROM `sqlite_master` WHERE `type` = "table" AND `name` = "' + Name + '";') do try
  852. Result := not Empty;
  853. finally
  854. Free;
  855. end;{with QueryTable..}
  856. end;{TDatabase.TableExists}
  857.  
  858. function TDatabase.BeginTransaction: Boolean;
  859. begin
  860. CriticalSection.Enter;
  861. try
  862. if Transaction then exit(False);
  863.  
  864. Result := Query('BEGIN TRANSACTION;');
  865. if Result then Transaction := True;
  866. finally
  867. CriticalSection.Leave;
  868. end;{try...finallly}
  869. end;{TDatabase.BeginTransaction}
  870.  
  871. function TDatabase.EndTransaction(Rollback: Boolean = False): Boolean;
  872. begin
  873. CriticalSection.Enter;
  874. try
  875. //if not Transaction then exit(False);
  876.  
  877. if Rollback then
  878. Result := Query('ROLLBACK;')
  879. else
  880. Result := Query('COMMIT;');
  881.  
  882. if Result then Transaction := False;
  883. finally
  884. CriticalSection.Leave;
  885. end;{try...finally}
  886. end;{TDatabase.EndTransaction}
  887.  
  888. constructor TINIFile.Create(AFileName: AnsiString);
  889. begin
  890. inherited Create;
  891.  
  892. FileName := AFileName;
  893.  
  894. CriticalSection.Create;
  895. end;{TINIFile.Create}
  896.  
  897. destructor TINIFile.Destroy;
  898. begin
  899. CriticalSection.Free;
  900.  
  901. inherited;
  902. end;{TINIFile.Destroy}
  903.  
  904. function TINIFile.Read(Section, Key: AnsiString; Default: AnsiString = ''): AnsiString;
  905. begin
  906. CriticalSection.Enter;
  907.  
  908. try
  909. SetLength(Result, 256);
  910. SetLength(Result, GetPrivateProfileStringA(PAnsiChar(Section), PAnsiChar(Key), PAnsiChar(Default), PAnsiChar(Result), length(Result), PAnsiChar(FileName)));
  911. finally
  912. CriticalSection.Leave;
  913. end;{try...finally}
  914.  
  915. {$IFDEF LOG_CONFIG}
  916. Server.Log(['Configuration (', FileName, ') [', Section, '] ', Key ,'=', Result]);
  917. {$ENDIF LOG_CONFIG}
  918. end;{TINIFile.Read(String}
  919.  
  920. function TINIFile.Read(Section, Key: AnsiString; Default: Integer = 0): Integer;
  921. begin
  922. Result := Int(Read(Section, Key, Str(Default)));
  923. end;{TINIFile.Read(Integer}
  924.  
  925. function TINIFile.Read(Section, Key: AnsiString; Default: Boolean = False): Boolean;
  926. begin
  927. Result := Bool(Read(Section, Key, Str(Default)));
  928. end;{TINIFile.Read(Boolean}
  929.  
  930. constructor TArray<T>.Create;
  931. begin
  932. inherited Create;
  933.  
  934. Clear;
  935. end;{TArray<T>.Create}
  936.  
  937. destructor TArray<T>.Destroy;
  938. begin
  939. Clear;
  940.  
  941. inherited;
  942. end;{TArray<T>.Destroy}
  943.  
  944. function TArray<T>.Find(Item: T): Integer;
  945. var
  946. i: Integer;
  947. begin
  948. for i := 0 to high(Items) do
  949. if Items[i] = Item then exit(i);
  950.  
  951. Result := -1;
  952. end;{TArray<T>.Add}
  953.  
  954. function TArray<T>.Add(Item: T): Integer;
  955. begin
  956. Result := Find(Item);
  957.  
  958. if Result = -1 then
  959. begin
  960. SetLength(Items, length(Items) + 1);
  961. Result := high(Items);
  962. Items[Result] := Item;
  963. end;{if Result = -1}
  964. end;{TArray<T>.Add}
  965.  
  966. function TArray<T>.Remove(Item: T): Integer;
  967. begin
  968. Result := Find(Item);
  969. if Result = -1 then exit;
  970.  
  971. if Result < high(Items) then
  972. move(Items[Result + 1], Items[Result], sizeof(T) * (length(Items) - 1));
  973.  
  974. SetLength(Items, length(Items) - 1);
  975. end;{TArray<T>.Remove}
  976.  
  977. procedure TArray<T>.Clear;
  978. begin
  979. SetLength(Items, 0);
  980. end;{TArray<T>.Clear}
  981.  
  982. procedure TSHA256.Init;
  983. begin
  984. Hash.A := $6a09e667;
  985. Hash.B := $bb67ae85;
  986. Hash.C := $3c6ef372;
  987. Hash.D := $a54ff53a;
  988. Hash.E := $510e527f;
  989. Hash.F := $9b05688c;
  990. Hash.G := $1f83d9ab;
  991. Hash.H := $5be0cd19;
  992.  
  993. FillChar(Buffer, sizeof(Buffer), 0);
  994.  
  995. Index := 0;
  996. MLen := 0;
  997. end;{TSHA256.Init}
  998.  
  999. procedure TSHA256.Compress;
  1000. var
  1001. a, b, c, d, e, f, g, h: Cardinal;
  1002. t1, t2: Cardinal;
  1003. W: array[0..63] of Cardinal;
  1004. i: longword;
  1005. begin
  1006. Index:= 0;
  1007.  
  1008. Move(Buffer,W,Sizeof(Buffer));
  1009.  
  1010. a := Hash.A;
  1011. b := Hash.B;
  1012. c := Hash.C;
  1013. d := Hash.D;
  1014. e := Hash.E;
  1015. f := Hash.F;
  1016. g := Hash.G;
  1017. h := Hash.H;
  1018.  
  1019. for i:= 0 to 15 do
  1020. W[i] := bswap(W[i]);
  1021.  
  1022. for i:= 16 to 63 do
  1023. W[i] := (((W[i - 2] shr 17) or (W[i - 2] shl 15)) xor ((W[i - 2] shr 19) or
  1024. (W[i - 2] shl 13)) xor (W[i - 2] shr 10)) + W[i - 7] + (((W[i - 15]
  1025. shr 7) or (W[i - 15] shl 25)) xor ((W[i - 15] shr 18) or (W[i - 15]
  1026. shl 14)) xor (W[i - 15] shr 3)) + W[i - 16];
  1027.  
  1028. t1 := h + (((e shr 6) or (e shl 26)) xor ((e shr 11) or (e shl 21)) xor ((e shr 25) or (e shl 7))) + ((e and f) xor (not e and g)) + $428a2f98 + W[0]; t2:= (((a shr 2) or (a shl 30)) xor ((a shr 13) or (a shl 19)) xor ((a shr 22) xor (a shl 10))) + ((a and b) xor (a and c) xor (b and c)); h := t1 + t2; d := d + t1;
  1029. t1 := g + (((d shr 6) or (d shl 26)) xor ((d shr 11) or (d shl 21)) xor ((d shr 25) or (d shl 7))) + ((d and e) xor (not d and f)) + $71374491 + W[1]; t2:= (((h shr 2) or (h shl 30)) xor ((h shr 13) or (h shl 19)) xor ((h shr 22) xor (h shl 10))) + ((h and a) xor (h and b) xor (a and b)); g := t1 + t2; c := c + t1;
  1030. t1 := f + (((c shr 6) or (c shl 26)) xor ((c shr 11) or (c shl 21)) xor ((c shr 25) or (c shl 7))) + ((c and d) xor (not c and e)) + $b5c0fbcf + W[2]; t2:= (((g shr 2) or (g shl 30)) xor ((g shr 13) or (g shl 19)) xor ((g shr 22) xor (g shl 10))) + ((g and h) xor (g and a) xor (h and a)); f := t1 + t2; b := b + t1;
  1031. t1 := e + (((b shr 6) or (b shl 26)) xor ((b shr 11) or (b shl 21)) xor ((b shr 25) or (b shl 7))) + ((b and c) xor (not b and d)) + $e9b5dba5 + W[3]; t2:= (((f shr 2) or (f shl 30)) xor ((f shr 13) or (f shl 19)) xor ((f shr 22) xor (f shl 10))) + ((f and g) xor (f and h) xor (g and h)); e := t1 + t2; a := a + t1;
  1032. t1 := d + (((a shr 6) or (a shl 26)) xor ((a shr 11) or (a shl 21)) xor ((a shr 25) or (a shl 7))) + ((a and b) xor (not a and c)) + $3956c25b + W[4]; t2:= (((e shr 2) or (e shl 30)) xor ((e shr 13) or (e shl 19)) xor ((e shr 22) xor (e shl 10))) + ((e and f) xor (e and g) xor (f and g)); d := t1 + t2; h := h + t1;
  1033. t1 := c + (((h shr 6) or (h shl 26)) xor ((h shr 11) or (h shl 21)) xor ((h shr 25) or (h shl 7))) + ((h and a) xor (not h and b)) + $59f111f1 + W[5]; t2:= (((d shr 2) or (d shl 30)) xor ((d shr 13) or (d shl 19)) xor ((d shr 22) xor (d shl 10))) + ((d and e) xor (d and f) xor (e and f)); c := t1 + t2; g := g + t1;
  1034. t1 := b + (((g shr 6) or (g shl 26)) xor ((g shr 11) or (g shl 21)) xor ((g shr 25) or (g shl 7))) + ((g and h) xor (not g and a)) + $923f82a4 + W[6]; t2:= (((c shr 2) or (c shl 30)) xor ((c shr 13) or (c shl 19)) xor ((c shr 22) xor (c shl 10))) + ((c and d) xor (c and e) xor (d and e)); b := t1 + t2; f := f + t1;
  1035. t1 := a + (((f shr 6) or (f shl 26)) xor ((f shr 11) or (f shl 21)) xor ((f shr 25) or (f shl 7))) + ((f and g) xor (not f and h)) + $ab1c5ed5 + W[7]; t2:= (((b shr 2) or (b shl 30)) xor ((b shr 13) or (b shl 19)) xor ((b shr 22) xor (b shl 10))) + ((b and c) xor (b and d) xor (c and d)); a := t1 + t2; e := e + t1;
  1036. t1 := h + (((e shr 6) or (e shl 26)) xor ((e shr 11) or (e shl 21)) xor ((e shr 25) or (e shl 7))) + ((e and f) xor (not e and g)) + $d807aa98 + W[8]; t2:= (((a shr 2) or (a shl 30)) xor ((a shr 13) or (a shl 19)) xor ((a shr 22) xor (a shl 10))) + ((a and b) xor (a and c) xor (b and c)); h := t1 + t2; d := d + t1;
  1037. t1 := g + (((d shr 6) or (d shl 26)) xor ((d shr 11) or (d shl 21)) xor ((d shr 25) or (d shl 7))) + ((d and e) xor (not d and f)) + $12835b01 + W[9]; t2:= (((h shr 2) or (h shl 30)) xor ((h shr 13) or (h shl 19)) xor ((h shr 22) xor (h shl 10))) + ((h and a) xor (h and b) xor (a and b)); g := t1 + t2; c := c + t1;
  1038. t1 := f + (((c shr 6) or (c shl 26)) xor ((c shr 11) or (c shl 21)) xor ((c shr 25) or (c shl 7))) + ((c and d) xor (not c and e)) + $243185be + W[10]; t2:= (((g shr 2) or (g shl 30)) xor ((g shr 13) or (g shl 19)) xor ((g shr 22) xor (g shl 10))) + ((g and h) xor (g and a) xor (h and a)); f := t1 + t2; b := b + t1;
  1039. t1 := e + (((b shr 6) or (b shl 26)) xor ((b shr 11) or (b shl 21)) xor ((b shr 25) or (b shl 7))) + ((b and c) xor (not b and d)) + $550c7dc3 + W[11]; t2:= (((f shr 2) or (f shl 30)) xor ((f shr 13) or (f shl 19)) xor ((f shr 22) xor (f shl 10))) + ((f and g) xor (f and h) xor (g and h)); e := t1 + t2; a := a + t1;
  1040. t1 := d + (((a shr 6) or (a shl 26)) xor ((a shr 11) or (a shl 21)) xor ((a shr 25) or (a shl 7))) + ((a and b) xor (not a and c)) + $72be5d74 + W[12]; t2:= (((e shr 2) or (e shl 30)) xor ((e shr 13) or (e shl 19)) xor ((e shr 22) xor (e shl 10))) + ((e and f) xor (e and g) xor (f and g)); d := t1 + t2; h := h + t1;
  1041. t1 := c + (((h shr 6) or (h shl 26)) xor ((h shr 11) or (h shl 21)) xor ((h shr 25) or (h shl 7))) + ((h and a) xor (not h and b)) + $80deb1fe + W[13]; t2:= (((d shr 2) or (d shl 30)) xor ((d shr 13) or (d shl 19)) xor ((d shr 22) xor (d shl 10))) + ((d and e) xor (d and f) xor (e and f)); c := t1 + t2; g := g + t1;
  1042. t1 := b + (((g shr 6) or (g shl 26)) xor ((g shr 11) or (g shl 21)) xor ((g shr 25) or (g shl 7))) + ((g and h) xor (not g and a)) + $9bdc06a7 + W[14]; t2:= (((c shr 2) or (c shl 30)) xor ((c shr 13) or (c shl 19)) xor ((c shr 22) xor (c shl 10))) + ((c and d) xor (c and e) xor (d and e)); b := t1 + t2; f := f + t1;
  1043. t1 := a + (((f shr 6) or (f shl 26)) xor ((f shr 11) or (f shl 21)) xor ((f shr 25) or (f shl 7))) + ((f and g) xor (not f and h)) + $c19bf174 + W[15]; t2:= (((b shr 2) or (b shl 30)) xor ((b shr 13) or (b shl 19)) xor ((b shr 22) xor (b shl 10))) + ((b and c) xor (b and d) xor (c and d)); a := t1 + t2; e := e + t1;
  1044. t1 := h + (((e shr 6) or (e shl 26)) xor ((e shr 11) or (e shl 21)) xor ((e shr 25) or (e shl 7))) + ((e and f) xor (not e and g)) + $e49b69c1 + W[16]; t2:= (((a shr 2) or (a shl 30)) xor ((a shr 13) or (a shl 19)) xor ((a shr 22) xor (a shl 10))) + ((a and b) xor (a and c) xor (b and c)); h := t1 + t2; d := d + t1;
  1045. t1 := g + (((d shr 6) or (d shl 26)) xor ((d shr 11) or (d shl 21)) xor ((d shr 25) or (d shl 7))) + ((d and e) xor (not d and f)) + $efbe4786 + W[17]; t2:= (((h shr 2) or (h shl 30)) xor ((h shr 13) or (h shl 19)) xor ((h shr 22) xor (h shl 10))) + ((h and a) xor (h and b) xor (a and b)); g := t1 + t2; c := c + t1;
  1046. t1 := f + (((c shr 6) or (c shl 26)) xor ((c shr 11) or (c shl 21)) xor ((c shr 25) or (c shl 7))) + ((c and d) xor (not c and e)) + $0fc19dc6 + W[18]; t2:= (((g shr 2) or (g shl 30)) xor ((g shr 13) or (g shl 19)) xor ((g shr 22) xor (g shl 10))) + ((g and h) xor (g and a) xor (h and a)); f := t1 + t2; b := b + t1;
  1047. t1 := e + (((b shr 6) or (b shl 26)) xor ((b shr 11) or (b shl 21)) xor ((b shr 25) or (b shl 7))) + ((b and c) xor (not b and d)) + $240ca1cc + W[19]; t2:= (((f shr 2) or (f shl 30)) xor ((f shr 13) or (f shl 19)) xor ((f shr 22) xor (f shl 10))) + ((f and g) xor (f and h) xor (g and h)); e := t1 + t2; a := a + t1;
  1048. t1 := d + (((a shr 6) or (a shl 26)) xor ((a shr 11) or (a shl 21)) xor ((a shr 25) or (a shl 7))) + ((a and b) xor (not a and c)) + $2de92c6f + W[20]; t2:= (((e shr 2) or (e shl 30)) xor ((e shr 13) or (e shl 19)) xor ((e shr 22) xor (e shl 10))) + ((e and f) xor (e and g) xor (f and g)); d := t1 + t2; h := h + t1;
  1049. t1 := c + (((h shr 6) or (h shl 26)) xor ((h shr 11) or (h shl 21)) xor ((h shr 25) or (h shl 7))) + ((h and a) xor (not h and b)) + $4a7484aa + W[21]; t2:= (((d shr 2) or (d shl 30)) xor ((d shr 13) or (d shl 19)) xor ((d shr 22) xor (d shl 10))) + ((d and e) xor (d and f) xor (e and f)); c := t1 + t2; g := g + t1;
  1050. t1 := b + (((g shr 6) or (g shl 26)) xor ((g shr 11) or (g shl 21)) xor ((g shr 25) or (g shl 7))) + ((g and h) xor (not g and a)) + $5cb0a9dc + W[22]; t2:= (((c shr 2) or (c shl 30)) xor ((c shr 13) or (c shl 19)) xor ((c shr 22) xor (c shl 10))) + ((c and d) xor (c and e) xor (d and e)); b := t1 + t2; f := f + t1;
  1051. t1 := a + (((f shr 6) or (f shl 26)) xor ((f shr 11) or (f shl 21)) xor ((f shr 25) or (f shl 7))) + ((f and g) xor (not f and h)) + $76f988da + W[23]; t2:= (((b shr 2) or (b shl 30)) xor ((b shr 13) or (b shl 19)) xor ((b shr 22) xor (b shl 10))) + ((b and c) xor (b and d) xor (c and d)); a := t1 + t2; e := e + t1;
  1052. t1 := h + (((e shr 6) or (e shl 26)) xor ((e shr 11) or (e shl 21)) xor ((e shr 25) or (e shl 7))) + ((e and f) xor (not e and g)) + $983e5152 + W[24]; t2:= (((a shr 2) or (a shl 30)) xor ((a shr 13) or (a shl 19)) xor ((a shr 22) xor (a shl 10))) + ((a and b) xor (a and c) xor (b and c)); h := t1 + t2; d := d + t1;
  1053. t1 := g + (((d shr 6) or (d shl 26)) xor ((d shr 11) or (d shl 21)) xor ((d shr 25) or (d shl 7))) + ((d and e) xor (not d and f)) + $a831c66d + W[25]; t2:= (((h shr 2) or (h shl 30)) xor ((h shr 13) or (h shl 19)) xor ((h shr 22) xor (h shl 10))) + ((h and a) xor (h and b) xor (a and b)); g := t1 + t2; c := c + t1;
  1054. t1 := f + (((c shr 6) or (c shl 26)) xor ((c shr 11) or (c shl 21)) xor ((c shr 25) or (c shl 7))) + ((c and d) xor (not c and e)) + $b00327c8 + W[26]; t2:= (((g shr 2) or (g shl 30)) xor ((g shr 13) or (g shl 19)) xor ((g shr 22) xor (g shl 10))) + ((g and h) xor (g and a) xor (h and a)); f := t1 + t2; b := b + t1;
  1055. t1 := e + (((b shr 6) or (b shl 26)) xor ((b shr 11) or (b shl 21)) xor ((b shr 25) or (b shl 7))) + ((b and c) xor (not b and d)) + $bf597fc7 + W[27]; t2:= (((f shr 2) or (f shl 30)) xor ((f shr 13) or (f shl 19)) xor ((f shr 22) xor (f shl 10))) + ((f and g) xor (f and h) xor (g and h)); e := t1 + t2; a := a + t1;
  1056. t1 := d + (((a shr 6) or (a shl 26)) xor ((a shr 11) or (a shl 21)) xor ((a shr 25) or (a shl 7))) + ((a and b) xor (not a and c)) + $c6e00bf3 + W[28]; t2:= (((e shr 2) or (e shl 30)) xor ((e shr 13) or (e shl 19)) xor ((e shr 22) xor (e shl 10))) + ((e and f) xor (e and g) xor (f and g)); d := t1 + t2; h := h + t1;
  1057. t1 := c + (((h shr 6) or (h shl 26)) xor ((h shr 11) or (h shl 21)) xor ((h shr 25) or (h shl 7))) + ((h and a) xor (not h and b)) + $d5a79147 + W[29]; t2:= (((d shr 2) or (d shl 30)) xor ((d shr 13) or (d shl 19)) xor ((d shr 22) xor (d shl 10))) + ((d and e) xor (d and f) xor (e and f)); c := t1 + t2; g := g + t1;
  1058. t1 := b + (((g shr 6) or (g shl 26)) xor ((g shr 11) or (g shl 21)) xor ((g shr 25) or (g shl 7))) + ((g and h) xor (not g and a)) + $06ca6351 + W[30]; t2:= (((c shr 2) or (c shl 30)) xor ((c shr 13) or (c shl 19)) xor ((c shr 22) xor (c shl 10))) + ((c and d) xor (c and e) xor (d and e)); b := t1 + t2; f := f + t1;
  1059. t1 := a + (((f shr 6) or (f shl 26)) xor ((f shr 11) or (f shl 21)) xor ((f shr 25) or (f shl 7))) + ((f and g) xor (not f and h)) + $14292967 + W[31]; t2:= (((b shr 2) or (b shl 30)) xor ((b shr 13) or (b shl 19)) xor ((b shr 22) xor (b shl 10))) + ((b and c) xor (b and d) xor (c and d)); a := t1 + t2; e := e + t1;
  1060. t1 := h + (((e shr 6) or (e shl 26)) xor ((e shr 11) or (e shl 21)) xor ((e shr 25) or (e shl 7))) + ((e and f) xor (not e and g)) + $27b70a85 + W[32]; t2:= (((a shr 2) or (a shl 30)) xor ((a shr 13) or (a shl 19)) xor ((a shr 22) xor (a shl 10))) + ((a and b) xor (a and c) xor (b and c)); h := t1 + t2; d := d + t1;
  1061. t1 := g + (((d shr 6) or (d shl 26)) xor ((d shr 11) or (d shl 21)) xor ((d shr 25) or (d shl 7))) + ((d and e) xor (not d and f)) + $2e1b2138 + W[33]; t2:= (((h shr 2) or (h shl 30)) xor ((h shr 13) or (h shl 19)) xor ((h shr 22) xor (h shl 10))) + ((h and a) xor (h and b) xor (a and b)); g := t1 + t2; c := c + t1;
  1062. t1 := f + (((c shr 6) or (c shl 26)) xor ((c shr 11) or (c shl 21)) xor ((c shr 25) or (c shl 7))) + ((c and d) xor (not c and e)) + $4d2c6dfc + W[34]; t2:= (((g shr 2) or (g shl 30)) xor ((g shr 13) or (g shl 19)) xor ((g shr 22) xor (g shl 10))) + ((g and h) xor (g and a) xor (h and a)); f := t1 + t2; b := b + t1;
  1063. t1 := e + (((b shr 6) or (b shl 26)) xor ((b shr 11) or (b shl 21)) xor ((b shr 25) or (b shl 7))) + ((b and c) xor (not b and d)) + $53380d13 + W[35]; t2:= (((f shr 2) or (f shl 30)) xor ((f shr 13) or (f shl 19)) xor ((f shr 22) xor (f shl 10))) + ((f and g) xor (f and h) xor (g and h)); e := t1 + t2; a := a + t1;
  1064. t1 := d + (((a shr 6) or (a shl 26)) xor ((a shr 11) or (a shl 21)) xor ((a shr 25) or (a shl 7))) + ((a and b) xor (not a and c)) + $650a7354 + W[36]; t2:= (((e shr 2) or (e shl 30)) xor ((e shr 13) or (e shl 19)) xor ((e shr 22) xor (e shl 10))) + ((e and f) xor (e and g) xor (f and g)); d := t1 + t2; h := h + t1;
  1065. t1 := c + (((h shr 6) or (h shl 26)) xor ((h shr 11) or (h shl 21)) xor ((h shr 25) or (h shl 7))) + ((h and a) xor (not h and b)) + $766a0abb + W[37]; t2:= (((d shr 2) or (d shl 30)) xor ((d shr 13) or (d shl 19)) xor ((d shr 22) xor (d shl 10))) + ((d and e) xor (d and f) xor (e and f)); c := t1 + t2; g := g + t1;
  1066. t1 := b + (((g shr 6) or (g shl 26)) xor ((g shr 11) or (g shl 21)) xor ((g shr 25) or (g shl 7))) + ((g and h) xor (not g and a)) + $81c2c92e + W[38]; t2:= (((c shr 2) or (c shl 30)) xor ((c shr 13) or (c shl 19)) xor ((c shr 22) xor (c shl 10))) + ((c and d) xor (c and e) xor (d and e)); b := t1 + t2; f := f + t1;
  1067. t1 := a + (((f shr 6) or (f shl 26)) xor ((f shr 11) or (f shl 21)) xor ((f shr 25) or (f shl 7))) + ((f and g) xor (not f and h)) + $92722c85 + W[39]; t2:= (((b shr 2) or (b shl 30)) xor ((b shr 13) or (b shl 19)) xor ((b shr 22) xor (b shl 10))) + ((b and c) xor (b and d) xor (c and d)); a := t1 + t2; e := e + t1;
  1068. t1 := h + (((e shr 6) or (e shl 26)) xor ((e shr 11) or (e shl 21)) xor ((e shr 25) or (e shl 7))) + ((e and f) xor (not e and g)) + $a2bfe8a1 + W[40]; t2:= (((a shr 2) or (a shl 30)) xor ((a shr 13) or (a shl 19)) xor ((a shr 22) xor (a shl 10))) + ((a and b) xor (a and c) xor (b and c)); h := t1 + t2; d := d + t1;
  1069. t1 := g + (((d shr 6) or (d shl 26)) xor ((d shr 11) or (d shl 21)) xor ((d shr 25) or (d shl 7))) + ((d and e) xor (not d and f)) + $a81a664b + W[41]; t2:= (((h shr 2) or (h shl 30)) xor ((h shr 13) or (h shl 19)) xor ((h shr 22) xor (h shl 10))) + ((h and a) xor (h and b) xor (a and b)); g := t1 + t2; c := c + t1;
  1070. t1 := f + (((c shr 6) or (c shl 26)) xor ((c shr 11) or (c shl 21)) xor ((c shr 25) or (c shl 7))) + ((c and d) xor (not c and e)) + $c24b8b70 + W[42]; t2:= (((g shr 2) or (g shl 30)) xor ((g shr 13) or (g shl 19)) xor ((g shr 22) xor (g shl 10))) + ((g and h) xor (g and a) xor (h and a)); f := t1 + t2; b := b + t1;
  1071. t1 := e + (((b shr 6) or (b shl 26)) xor ((b shr 11) or (b shl 21)) xor ((b shr 25) or (b shl 7))) + ((b and c) xor (not b and d)) + $c76c51a3 + W[43]; t2:= (((f shr 2) or (f shl 30)) xor ((f shr 13) or (f shl 19)) xor ((f shr 22) xor (f shl 10))) + ((f and g) xor (f and h) xor (g and h)); e := t1 + t2; a := a + t1;
  1072. t1 := d + (((a shr 6) or (a shl 26)) xor ((a shr 11) or (a shl 21)) xor ((a shr 25) or (a shl 7))) + ((a and b) xor (not a and c)) + $d192e819 + W[44]; t2:= (((e shr 2) or (e shl 30)) xor ((e shr 13) or (e shl 19)) xor ((e shr 22) xor (e shl 10))) + ((e and f) xor (e and g) xor (f and g)); d := t1 + t2; h := h + t1;
  1073. t1 := c + (((h shr 6) or (h shl 26)) xor ((h shr 11) or (h shl 21)) xor ((h shr 25) or (h shl 7))) + ((h and a) xor (not h and b)) + $d6990624 + W[45]; t2:= (((d shr 2) or (d shl 30)) xor ((d shr 13) or (d shl 19)) xor ((d shr 22) xor (d shl 10))) + ((d and e) xor (d and f) xor (e and f)); c := t1 + t2; g := g + t1;
  1074. t1 := b + (((g shr 6) or (g shl 26)) xor ((g shr 11) or (g shl 21)) xor ((g shr 25) or (g shl 7))) + ((g and h) xor (not g and a)) + $f40e3585 + W[46]; t2:= (((c shr 2) or (c shl 30)) xor ((c shr 13) or (c shl 19)) xor ((c shr 22) xor (c shl 10))) + ((c and d) xor (c and e) xor (d and e)); b := t1 + t2; f := f + t1;
  1075. t1 := a + (((f shr 6) or (f shl 26)) xor ((f shr 11) or (f shl 21)) xor ((f shr 25) or (f shl 7))) + ((f and g) xor (not f and h)) + $106aa070 + W[47]; t2:= (((b shr 2) or (b shl 30)) xor ((b shr 13) or (b shl 19)) xor ((b shr 22) xor (b shl 10))) + ((b and c) xor (b and d) xor (c and d)); a := t1 + t2; e := e + t1;
  1076. t1 := h + (((e shr 6) or (e shl 26)) xor ((e shr 11) or (e shl 21)) xor ((e shr 25) or (e shl 7))) + ((e and f) xor (not e and g)) + $19a4c116 + W[48]; t2:= (((a shr 2) or (a shl 30)) xor ((a shr 13) or (a shl 19)) xor ((a shr 22) xor (a shl 10))) + ((a and b) xor (a and c) xor (b and c)); h := t1 + t2; d := d + t1;
  1077. t1 := g + (((d shr 6) or (d shl 26)) xor ((d shr 11) or (d shl 21)) xor ((d shr 25) or (d shl 7))) + ((d and e) xor (not d and f)) + $1e376c08 + W[49]; t2:= (((h shr 2) or (h shl 30)) xor ((h shr 13) or (h shl 19)) xor ((h shr 22) xor (h shl 10))) + ((h and a) xor (h and b) xor (a and b)); g := t1 + t2; c := c + t1;
  1078. t1 := f + (((c shr 6) or (c shl 26)) xor ((c shr 11) or (c shl 21)) xor ((c shr 25) or (c shl 7))) + ((c and d) xor (not c and e)) + $2748774c + W[50]; t2:= (((g shr 2) or (g shl 30)) xor ((g shr 13) or (g shl 19)) xor ((g shr 22) xor (g shl 10))) + ((g and h) xor (g and a) xor (h and a)); f := t1 + t2; b := b + t1;
  1079. t1 := e + (((b shr 6) or (b shl 26)) xor ((b shr 11) or (b shl 21)) xor ((b shr 25) or (b shl 7))) + ((b and c) xor (not b and d)) + $34b0bcb5 + W[51]; t2:= (((f shr 2) or (f shl 30)) xor ((f shr 13) or (f shl 19)) xor ((f shr 22) xor (f shl 10))) + ((f and g) xor (f and h) xor (g and h)); e := t1 + t2; a := a + t1;
  1080. t1 := d + (((a shr 6) or (a shl 26)) xor ((a shr 11) or (a shl 21)) xor ((a shr 25) or (a shl 7))) + ((a and b) xor (not a and c)) + $391c0cb3 + W[52]; t2:= (((e shr 2) or (e shl 30)) xor ((e shr 13) or (e shl 19)) xor ((e shr 22) xor (e shl 10))) + ((e and f) xor (e and g) xor (f and g)); d := t1 + t2; h := h + t1;
  1081. t1 := c + (((h shr 6) or (h shl 26)) xor ((h shr 11) or (h shl 21)) xor ((h shr 25) or (h shl 7))) + ((h and a) xor (not h and b)) + $4ed8aa4a + W[53]; t2:= (((d shr 2) or (d shl 30)) xor ((d shr 13) or (d shl 19)) xor ((d shr 22) xor (d shl 10))) + ((d and e) xor (d and f) xor (e and f)); c := t1 + t2; g := g + t1;
  1082. t1 := b + (((g shr 6) or (g shl 26)) xor ((g shr 11) or (g shl 21)) xor ((g shr 25) or (g shl 7))) + ((g and h) xor (not g and a)) + $5b9cca4f + W[54]; t2:= (((c shr 2) or (c shl 30)) xor ((c shr 13) or (c shl 19)) xor ((c shr 22) xor (c shl 10))) + ((c and d) xor (c and e) xor (d and e)); b := t1 + t2; f := f + t1;
  1083. t1 := a + (((f shr 6) or (f shl 26)) xor ((f shr 11) or (f shl 21)) xor ((f shr 25) or (f shl 7))) + ((f and g) xor (not f and h)) + $682e6ff3 + W[55]; t2:= (((b shr 2) or (b shl 30)) xor ((b shr 13) or (b shl 19)) xor ((b shr 22) xor (b shl 10))) + ((b and c) xor (b and d) xor (c and d)); a := t1 + t2; e := e + t1;
  1084. t1 := h + (((e shr 6) or (e shl 26)) xor ((e shr 11) or (e shl 21)) xor ((e shr 25) or (e shl 7))) + ((e and f) xor (not e and g)) + $748f82ee + W[56]; t2:= (((a shr 2) or (a shl 30)) xor ((a shr 13) or (a shl 19)) xor ((a shr 22) xor (a shl 10))) + ((a and b) xor (a and c) xor (b and c)); h := t1 + t2; d := d + t1;
  1085. t1 := g + (((d shr 6) or (d shl 26)) xor ((d shr 11) or (d shl 21)) xor ((d shr 25) or (d shl 7))) + ((d and e) xor (not d and f)) + $78a5636f + W[57]; t2:= (((h shr 2) or (h shl 30)) xor ((h shr 13) or (h shl 19)) xor ((h shr 22) xor (h shl 10))) + ((h and a) xor (h and b) xor (a and b)); g := t1 + t2; c := c + t1;
  1086. t1 := f + (((c shr 6) or (c shl 26)) xor ((c shr 11) or (c shl 21)) xor ((c shr 25) or (c shl 7))) + ((c and d) xor (not c and e)) + $84c87814 + W[58]; t2:= (((g shr 2) or (g shl 30)) xor ((g shr 13) or (g shl 19)) xor ((g shr 22) xor (g shl 10))) + ((g and h) xor (g and a) xor (h and a)); f := t1 + t2; b := b + t1;
  1087. t1 := e + (((b shr 6) or (b shl 26)) xor ((b shr 11) or (b shl 21)) xor ((b shr 25) or (b shl 7))) + ((b and c) xor (not b and d)) + $8cc70208 + W[59]; t2:= (((f shr 2) or (f shl 30)) xor ((f shr 13) or (f shl 19)) xor ((f shr 22) xor (f shl 10))) + ((f and g) xor (f and h) xor (g and h)); e := t1 + t2; a := a + t1;
  1088. t1 := d + (((a shr 6) or (a shl 26)) xor ((a shr 11) or (a shl 21)) xor ((a shr 25) or (a shl 7))) + ((a and b) xor (not a and c)) + $90befffa + W[60]; t2:= (((e shr 2) or (e shl 30)) xor ((e shr 13) or (e shl 19)) xor ((e shr 22) xor (e shl 10))) + ((e and f) xor (e and g) xor (f and g)); d := t1 + t2; h := h + t1;
  1089. t1 := c + (((h shr 6) or (h shl 26)) xor ((h shr 11) or (h shl 21)) xor ((h shr 25) or (h shl 7))) + ((h and a) xor (not h and b)) + $a4506ceb + W[61]; t2:= (((d shr 2) or (d shl 30)) xor ((d shr 13) or (d shl 19)) xor ((d shr 22) xor (d shl 10))) + ((d and e) xor (d and f) xor (e and f)); c := t1 + t2; g := g + t1;
  1090. t1 := b + (((g shr 6) or (g shl 26)) xor ((g shr 11) or (g shl 21)) xor ((g shr 25) or (g shl 7))) + ((g and h) xor (not g and a)) + $bef9a3f7 + W[62]; t2:= (((c shr 2) or (c shl 30)) xor ((c shr 13) or (c shl 19)) xor ((c shr 22) xor (c shl 10))) + ((c and d) xor (c and e) xor (d and e)); b := t1 + t2; f := f + t1;
  1091. t1 := a + (((f shr 6) or (f shl 26)) xor ((f shr 11) or (f shl 21)) xor ((f shr 25) or (f shl 7))) + ((f and g) xor (not f and h)) + $c67178f2 + W[63]; t2:= (((b shr 2) or (b shl 30)) xor ((b shr 13) or (b shl 19)) xor ((b shr 22) xor (b shl 10))) + ((b and c) xor (b and d) xor (c and d)); a := t1 + t2; e := e + t1;
  1092.  
  1093. inc(Hash.A, a);
  1094. inc(Hash.B, b);
  1095. inc(Hash.C, c);
  1096. inc(Hash.D, d);
  1097. inc(Hash.E, e);
  1098. inc(Hash.F, f);
  1099. inc(Hash.G, g);
  1100. inc(Hash.H, h);
  1101.  
  1102. FillChar(W,Sizeof(W),0);
  1103. FillChar(Buffer,Sizeof(Buffer),0);
  1104. end;{TSHA256.Compress}
  1105.  
  1106. procedure TSHA256.Update(Data: Pointer; Len: Integer);
  1107. var
  1108. i: Integer;
  1109. begin
  1110. inc(MLen, Int64(Cardinal(Len) shl 3));
  1111.  
  1112. while Len > 0 do
  1113. begin
  1114. i := 64 - Index;
  1115.  
  1116. if i <= Len then
  1117. begin
  1118. move(Data^, Buffer[Index], i);
  1119. dec(Len, i);
  1120. inc(Integer(Data), i);
  1121. Compress;
  1122. Index := 0;
  1123. end{if i <= Len}
  1124. else
  1125. begin
  1126. move(Data^, Buffer[Index], Len);
  1127. inc(Index, Len);
  1128. break;
  1129. end;{else}
  1130. end;{while Len > 0}
  1131. end;{TSHA256.Update}
  1132.  
  1133. function TSHA256.Done: AnsiString;
  1134. const
  1135. HexChar: array[0..15] of AnsiChar = '0123456789ABCDEF';
  1136. type
  1137. TInt64 = packed record
  1138. Lo, Hi: Cardinal;
  1139. end;{TInt64}
  1140. var
  1141. i: Integer;
  1142. PResult: PAnsiChar;
  1143. Digest: array[0..31] of Byte;
  1144. begin
  1145. Buffer[Index] := $80;
  1146.  
  1147. fillchar(Buffer[Index + 1], 63 - Index, 0);
  1148.  
  1149. if Index >= 56 then
  1150. begin
  1151. Compress;
  1152. fillchar(Buffer, 56, 0);
  1153. end;{if Index >= 56}
  1154.  
  1155. PInteger(@Buffer[56])^ := bswap(TInt64(MLen).Hi);
  1156. PInteger(@Buffer[60])^ := bswap(TInt64(MLen).Lo);
  1157.  
  1158. Compress;
  1159.  
  1160. bswap256(@Hash, @Digest);
  1161.  
  1162. Setlength(Result, sizeof(Digest) * 2);
  1163. PResult := PAnsiChar(Result);
  1164.  
  1165. for i := 0 to sizeof(Digest) - 1 do
  1166. begin
  1167. PResult[0] := HexChar[Digest[I] shr 4];
  1168. PResult[1] := HexChar[Digest[I] and 15];
  1169. inc(PResult,2);
  1170. end;{for i}
  1171. end;{TSHA256.Done}
  1172.  
  1173. class function TSHA256.HashStr(S: AnsiString): AnsiString;
  1174. var
  1175. SHA256: TSHA256;
  1176. begin
  1177. SHA256.Init;
  1178. SHA256.Update(PAnsiChar(S), length(S));
  1179. Result := SHA256.Done;
  1180. end;{class)TSHA256.HashStr}
  1181.  
  1182. class constructor Server.Create;
  1183. const
  1184. Banner = ' . . __ __ ___ __ _ _'#13#10' \`-"''"-''/ '+
  1185. '( \/ )( _) / \( \/\/ )'#13#10' } o o { - ) ( ) _)( () )\ '+
  1186. '/'#13#10' =. Y ,= (_/\/\_)(___) \__/ \/\/'#13#10' /-O-\ .'#13#10+
  1187. ' / \ ) Mini EO? WOW!'#13#10' ( )-( )/ Created by Sordie o'+
  1188. 'ut of boredom'#13#10' "" ""';
  1189. var
  1190. WSAData: TWSAData;
  1191. AddrIn: TSockAddrIn;
  1192. begin
  1193. Writeln(Banner);
  1194.  
  1195. CriticalSection.Create;
  1196.  
  1197. Sessions := TArray<TSession>.Create;
  1198.  
  1199. WSAStartup(MakeLong(2, 2), WSAData);
  1200.  
  1201. Configuration := TINIFile.Create('.\MEOW.ini');
  1202.  
  1203. Database := TDatabase.Create(Configuration.Read('database', 'name', '.\MEOW.db'));
  1204. //Database.Query('DROP TABLE `accounts`;');
  1205.  
  1206. if not Database.TableExists('accounts') then
  1207. begin
  1208. Log(['Creating accounts database']);
  1209.  
  1210. if not Database.Query('CREATE TABLE `accounts` (' +
  1211. '`id` INTEGER PRIMARY KEY, ' +
  1212. '`name` VARCHAR (' + Str(NameMax) + '), ' +
  1213. '`password` VARCHAR (64), ' +
  1214. '`x` INTEGER, ' +
  1215. '`y` INTEGER, ' +
  1216. '`d` INTEGER, ' +
  1217. '`s` INTEGER, ' +
  1218. '`admin` INTEGER, ' +
  1219. '`tag` VARCHAR (3), ' +
  1220. '`sex` INTEGER, ' +
  1221. '`hairstyle` INTEGER, ' +
  1222. '`haircolour` INTEGER, ' +
  1223. '`race` INTEGER, ' +
  1224. '`class` INTEGER, ' +
  1225. '`title` VARCHAR (64), ' +
  1226. '`home` VARCHAR (64), ' +
  1227. '`partner` VARCHAR (' + Str(NameMax) + '), ' +
  1228. '`guild` VARCHAR (64), ' +
  1229. '`rank` VARCHAR (64), ' +
  1230. '`boots` INTEGER, ' +
  1231. '`armour` INTEGER, ' +
  1232. '`hat` INTEGER, ' +
  1233. '`shield` INTEGER, ' +
  1234. '`weapon` INTEGER' +
  1235. ');') then
  1236. Error(['Failed to create table']);
  1237. end;{if not Database.TableExists}
  1238.  
  1239. PacketQueue.Enabled := Configuration.Read('packetqueue', 'enabled', True);
  1240. if PacketQueue.Enabled then
  1241. PacketQueue.Size := Configuration.Read('packetqueue', 'size', 10);
  1242.  
  1243. Socket := WinSock.socket(PF_INET, SOCK_STREAM, IPPROTO_TCP);
  1244. if Socket = 0 then
  1245. Error(['Failed to create socket']);
  1246.  
  1247. Connection.Bind := Configuration.Read('connection', 'bind', '0.0.0.0');
  1248. Connection.Port := Configuration.Read('connection', 'port', 8078);
  1249. Connection.Timeout := Configuration.Read('connection', 'timeout', 180000);
  1250.  
  1251. FillChar(AddrIn, sizeof(AddrIn), 0);
  1252. with AddrIn do
  1253. begin
  1254. sin_family := AF_INET;
  1255. sin_addr.S_addr := inet_addr(PAnsiChar(Connection.Bind));
  1256. sin_port := htons(Connection.Port);
  1257. end;{with AddrIn}
  1258. if bind(Socket, AddrIn, sizeof(AddrIn)) <> 0 then
  1259. Error(['Failed to bind socket']);
  1260.  
  1261. if listen(Socket, 0) <> 0 then
  1262. Error(['Cannot listen on socket']);
  1263.  
  1264. ItemData := TItemData. Create(Configuration.Read('data', 'item', '.\dat001.eif'));
  1265. NPCData := TNPCData. Create(Configuration.Read('data', 'npc', '.\dtn001.enf'));
  1266. SpellData := TSpellData.Create(Configuration.Read('data', 'spell', '.\dsl001.esf'));
  1267. ClassData := TClassData.Create(Configuration.Read('data', 'class', '.\dat001.ecf'));
  1268. MapData := TMapData. Create(Configuration.Read('data', 'map', '.\00001.emf'));
  1269.  
  1270. Defaults.X := Configuration.Read('defaults', 'x', 10);
  1271. Defaults.Y := Configuration.Read('defaults', 'y', 10);
  1272. Defaults.D := Configuration.Read('defaults', 'd', 0);
  1273.  
  1274. Connection.BytesIn := 0;
  1275. Connection.BytesOut := 0;
  1276.  
  1277. UpdateCaption;
  1278.  
  1279. try
  1280. Main;
  1281. except
  1282. Log(['Server Exception']);
  1283. end;{try...except}
  1284. end;{class)Server.Create}
  1285.  
  1286. class destructor Server.Destroy;
  1287. begin
  1288. if Socket <> 0 then
  1289. begin
  1290. closesocket(Socket);
  1291. Socket := 0;
  1292. end;{if Socket <> 0}
  1293.  
  1294. Sessions.Free;
  1295.  
  1296. ItemData.Free;
  1297. NPCData.Free;
  1298. SpellData.Free;
  1299. ClassData.Free;
  1300. MapData.Free;
  1301.  
  1302. Configuration.Free;
  1303. Database.Free;
  1304.  
  1305. CriticalSection.Free;
  1306. Readln;
  1307. end;{class)Server.Destroy}
  1308.  
  1309. class procedure Server.Main;
  1310. var
  1311. FDSet: TFDSet;
  1312. SockSize: Integer;
  1313. SockAddr: TSockAddr;
  1314. begin
  1315. repeat
  1316. Sleep(1);
  1317.  
  1318. FDSet.fd_count := 1;
  1319. FDSet.fd_array[0] := Socket;
  1320.  
  1321. if select(0, @FDSet, nil, nil, nil) = 1 then
  1322. begin
  1323. SockSize := sizeof(SockAddr);
  1324. TSession.Create(accept(Socket, @SockAddr, @SockSize));
  1325. end;{if select}
  1326. until Socket = 0;
  1327. end;{class)Server.Main}
  1328.  
  1329. class procedure Server.Log(Params: array of const; Prefix: AnsiString = '');
  1330. var
  1331. i: Integer;
  1332. begin
  1333. CriticalSection.Enter;
  1334. try
  1335. if length(Prefix) > 0 then
  1336. Write(Prefix + ' ');
  1337.  
  1338. for i := 0 to high(Params) do
  1339. with TVarRec(Params[i]) do
  1340. case VType of
  1341. vtInteger: Write(VInteger);
  1342. vtBoolean: Write(VBoolean);
  1343. vtChar: Write(VChar);
  1344. vtWideChar: Write(VWideChar);
  1345. vtExtended: Write(VExtended^);
  1346. vtString: Write(AnsiString(VString));
  1347. vtPointer: Write(Cardinal(VPointer));
  1348. vtPChar: Write(AnsiString(VPChar));
  1349. vtObject: Write(VObject.ClassName);
  1350. vtClass: Write(VClass.ClassName);
  1351. vtPWideChar: Write(WideString(VPWideChar));
  1352. vtWideString: Write(WideString(VWideString));
  1353. vtInt64: Write(VInt64^);
  1354. vtUnicodeString: Write(String(VUnicodeString));
  1355. vtAnsiString: Write(AnsiString(VAnsiString));
  1356. else
  1357. Write('?(', VType, ')');
  1358. end;{case VType}
  1359. finally
  1360. Writeln;
  1361. CriticalSection.Leave;
  1362. end;{try...finally}
  1363. end;{class)Server.Log}
  1364.  
  1365. class procedure Server.Send(var Packet: TPacket; Sender: TSession = nil; Ranged: Boolean = True);
  1366. var
  1367. Session: TSession;
  1368. begin
  1369. CriticalSection.Enter;
  1370. try
  1371. for Session in Sessions.Items do
  1372. if (Session <> Sender) and Session.LoggedIn then
  1373. begin
  1374. if Ranged and (Sender <> nil) and
  1375. ((Session.X < (Sender.X - ViewRange)) or (Session.X > (Sender.X + ViewRange)) or
  1376. (Session.Y < (Sender.Y - ViewRange)) or (Session.Y > (Sender.Y + ViewRange))) then
  1377. continue;
  1378.  
  1379. Session.Send(Packet);
  1380. end;{if (Session <> Sender)}
  1381. finally
  1382. CriticalSection.Leave;
  1383. end;{try...finally}
  1384. end;{Server.Send}
  1385.  
  1386. class procedure Server.UpdateCaption;
  1387. begin
  1388. CriticalSection.Section(procedure
  1389. var
  1390. NewCaption: AnsiString;
  1391. begin
  1392. NewCaption := 'MEOW - ' +
  1393. Str(length(Sessions.Items)) + ' Connection(s) - ' +
  1394. Scale(Connection.BytesIn) + ' in / ' +
  1395. Scale(Connection.BytesOut) + ' out';
  1396.  
  1397. if NewCaption <> Caption then
  1398. begin
  1399. Caption := NewCaption;
  1400. SetConsoleTitleA(PAnsiChar(Caption));
  1401. end;{if NewCaption <> Caption}
  1402. end);{CriticalSection.Section}
  1403. end;{class)Server.Update}
  1404.  
  1405. class function Server.GetSessionByID(ID: Cardinal): TSession;
  1406. var
  1407. Session: TSession;
  1408. begin
  1409. CriticalSection.Enter;
  1410. try
  1411. for Session in Sessions.Items do
  1412. if Session.ID = ID then exit(Session);
  1413.  
  1414. Result := nil;
  1415. finally
  1416. CriticalSection.Leave;
  1417. end;{try...finally}
  1418. end;{class)Server.GetSessionByID}
  1419.  
  1420. class function Server.GetSessionByName(Name: AnsiString): TSession;
  1421. var
  1422. Session: TSession;
  1423. begin
  1424. Name := Lower(Name);
  1425.  
  1426. CriticalSection.Enter;
  1427. try
  1428. for Session in Sessions.Items do
  1429. if Session.Name = Name then exit(Session);
  1430.  
  1431. Result := nil;
  1432. finally
  1433. CriticalSection.Leave;
  1434. end;{try...finally}
  1435. end;{Server.GetSessionByName}
  1436.  
  1437. class function Server.ValidName(Name: AnsiString): Boolean;
  1438. var
  1439. c: AnsiChar;
  1440. begin
  1441. if (length(Name) < 3) or (length(Name) > NameMax) then exit(False);
  1442.  
  1443. for c in Name do
  1444. if pos(String(c), NameChars) = 0 then
  1445. exit(False);
  1446.  
  1447. Result := True;
  1448. end;{class)Server.ValidName}
  1449.  
  1450. class function Server.GetAccount(Name: AnsiString; Items: AnsiString = '*'): TDatabase.TTable;
  1451. begin
  1452. Result := Database.QueryTable('SELECT ' + Items + ' FROM `accounts` WHERE `name` = "' + Name + '";');
  1453. end;{class)Server.GetAccount}
  1454.  
  1455. class function Server.AccountExists(Name: AnsiString): Boolean;
  1456. begin
  1457. with GetAccount(Name, '`id`') do try
  1458. Result := length(Table) > 0
  1459. finally
  1460. Free;
  1461. end;{with GetAccount}
  1462. end;{class)Server.AccountExists}
  1463.  
  1464. procedure Server.TPacket.SetID(AFamily, AAction: Byte);
  1465. begin
  1466. Family := AFamily;
  1467. Action := AAction;
  1468. end;{Server.TPacket.SetID}
  1469.  
  1470. procedure Server.TPacket.Reset;
  1471. begin
  1472. Data := '';
  1473. end;{Server.TPacket.Reset}
  1474.  
  1475. procedure Server.TPacket.Discard(Count: Integer = 1);
  1476. begin
  1477. Data := copy(Data, Count + 1, length(Data));
  1478. end;{Server.TPacket.Discard}
  1479.  
  1480. procedure Server.TPacket.AddByte(b: Byte);
  1481. begin
  1482. Data := Data + AnsiChar(b);
  1483. end;{Server.TPacket.AddByte}
  1484.  
  1485. procedure Server.TPacket.AddInt1(i: Byte);
  1486. begin
  1487. Data := Data + UnpackEOInt(i)[1];
  1488. end;{Server.TPacket.AddInt1}
  1489.  
  1490. procedure Server.TPacket.AddInt2(i: Word);
  1491. begin
  1492. Data := Data + copy(UnpackEOInt(i), 1, 2);
  1493. end;{Server.TPacket.AddInt2}
  1494.  
  1495. procedure Server.TPacket.AddInt3(i: Cardinal);
  1496. begin
  1497. Data := Data + copy(UnpackEOInt(i), 1, 3);
  1498. end;{Server.TPacket.AddInt3}
  1499.  
  1500. procedure Server.TPacket.AddInt4(i: Cardinal);
  1501. begin
  1502. Data := Data + UnpackEOInt(i);
  1503. end;{Server.TPacket.AddInt4}
  1504.  
  1505. procedure Server.TPacket.AddBreakString(s: AnsiString);
  1506. begin
  1507. Data := Data + s + #$FF;
  1508. end;{Server.TPacket.AddBreakString}
  1509.  
  1510. procedure Server.TPacket.AddString(s: AnsiString);
  1511. begin
  1512. Data := Data + s;
  1513. end;{Server.TPacket.AddString}
  1514.  
  1515. function Server.TPacket.GetByte: Byte;
  1516. begin
  1517. if length(Data) = 0 then exit(0);
  1518.  
  1519. Result := ord(Data[1]);
  1520. Data := copy(Data, 2, length(Data));
  1521. end;{Server.TPacket.GetByte}
  1522.  
  1523. function Server.TPacket.GetInt1: Byte;
  1524. begin
  1525. if length(Data) = 0 then exit(0);
  1526.  
  1527. Result := PackEOInt(ord(Data[1]));
  1528. Data := copy(Data, 2, length(Data));
  1529. end;{Server.TPacket.GetInt1}
  1530.  
  1531. function Server.TPacket.GetInt2: Word;
  1532. begin
  1533. if length(Data) = 0 then exit(0);
  1534. if length(Data) < 2 then exit(GetInt1);
  1535.  
  1536. Result := PackEOInt(ord(Data[1]), ord(Data[2]));
  1537. Data := copy(Data, 3, length(Data));
  1538. end;{Server.TPacket.GetInt2}
  1539.  
  1540. function Server.TPacket.GetInt3: Cardinal;
  1541. begin
  1542. if length(Data) = 0 then exit(0);
  1543. if length(Data) < 2 then exit(GetInt1);
  1544. if length(Data) < 3 then exit(GetInt2);
  1545.  
  1546. Result := PackEOInt(ord(Data[1]), ord(Data[2]), ord(Data[3]));
  1547. Data := copy(Data, 4, length(Data));
  1548. end;{Server.TPacket.GetInt3}
  1549.  
  1550. function Server.TPacket.GetInt4: Cardinal;
  1551. begin
  1552. if length(Data) = 0 then exit(0);
  1553. if length(Data) < 2 then exit(GetInt1);
  1554. if length(Data) < 3 then exit(GetInt2);
  1555. if length(Data) < 4 then exit(GetInt3);
  1556.  
  1557. Result := PackEOInt(ord(Data[1]), ord(Data[2]), ord(Data[3]), ord(Data[4]));
  1558. Data := copy(Data, 5, length(Data));
  1559. end;{Server.TPacketGetInt4}
  1560.  
  1561. function Server.TPacket.GetBreakString: AnsiString;
  1562. var
  1563. i: Integer;
  1564. begin
  1565. for i := 1 to length(Data) do
  1566. if Data[i] = #$FF then break;
  1567.  
  1568. Result := copy(Data, 1, i - 1);
  1569. Data := copy(Data, i + 1, length(Data));
  1570. end;{Server.TPacket.GetBreakString}
  1571.  
  1572. function Server.TPacket.GetString(Len: Integer = -1): AnsiString;
  1573. begin
  1574. if Len = -1 then
  1575. begin
  1576. Result := Data;
  1577. Data := '';
  1578. end{if Len = -1}
  1579. else
  1580. begin
  1581. Result := copy(Data, 1, Len);
  1582. Data := copy(Data, Len + 1, length(Data));
  1583. end;{else}
  1584. end;{Server.TPacket.GetString}
  1585.  
  1586. constructor Server.TGameData.Create(AFileName: AnsiString);
  1587. begin
  1588. inherited Create;
  1589.  
  1590. FileName := AFileName;
  1591. Load;
  1592. end;{Server.TGameData.Create}
  1593.  
  1594. function Server.TGameData.Load: Boolean;
  1595. var
  1596. l: Cardinal;
  1597. f: THandle;
  1598. begin
  1599. f := CreateFileA(PAnsiChar(FileName), GENERIC_READ, 0, nil, OPEN_EXISTING, FILE_ATTRIBUTE_NORMAL, 0);
  1600. if f = 0 then exit(False);
  1601.  
  1602. try
  1603. l := SetFilePointer(f, 0, nil, FIlE_END);
  1604. if (l = Cardinal(-1)) or (l < 10) then exit(False);
  1605.  
  1606. SetLength(Data, l);
  1607.  
  1608. SetFilePointer(f, 0, nil, FILE_BEGIN);
  1609. ReadFile(f, Data[1], l, l, nil);
  1610.  
  1611. CRC[0] := ord(Data[4]);
  1612. CRC[1] := ord(Data[5]);
  1613. CRC[2] := ord(Data[6]);
  1614. CRC[3] := ord(Data[7]);
  1615.  
  1616. Len[0] := ord(Data[8]);
  1617. Len[1] := ord(Data[9]);
  1618.  
  1619. Result := True;
  1620. finally
  1621. CloseHandle(f);
  1622. end;{try...finally}
  1623. end;{Server.TGameData.Load}
  1624.  
  1625. class function Server.TItemData.DataID: Byte;
  1626. begin
  1627. Result := 5;
  1628. end;{class)Server.TItemData.DataID}
  1629.  
  1630. class function Server.TNPCData.DataID: Byte;
  1631. begin
  1632. Result := 6;
  1633. end;{class)Server.TNPCData.DataID}
  1634.  
  1635. class function Server.TSpellData.DataID: Byte;
  1636. begin
  1637. Result := 7;
  1638. end;{class)Server.TSpellData.DataID}
  1639.  
  1640. class function Server.TClassData.DataID: Byte;
  1641. begin
  1642. Result := 11;
  1643. end;{class)Server.TClassData.DataID}
  1644.  
  1645. class function Server.TMapData.DataID: Byte;
  1646. begin
  1647. Result := 4;
  1648. end;{class)Server.TMapData.DataID}
  1649.  
  1650. function SessionThread(Session: Server.TSession): Integer;
  1651. begin
  1652. Result := 0;
  1653.  
  1654. try
  1655. try
  1656. while Session.Execute do
  1657. Sleep(1);
  1658. except
  1659. Server.Log(['Session exception']);
  1660. end;{try...except}
  1661. finally
  1662. Server.CriticalSection.Enter;
  1663. try Session.Free; except end;
  1664. Server.CriticalSection.Leave;
  1665.  
  1666. EndThread(Result);
  1667. end;{try...finally}
  1668. end;{SessionThread}
  1669.  
  1670. constructor Server.TSession.Create(ASocket: TSocket);
  1671. var
  1672. i: Integer;
  1673. Addr: TSockAddr;
  1674. begin
  1675. inherited Create;
  1676.  
  1677. Initialized := False;
  1678. LoggedIn := False;
  1679.  
  1680. Unload;
  1681.  
  1682. Socket := ASocket;
  1683.  
  1684. if Socket <> 0 then
  1685. begin
  1686. FillChar(Addr, sizeof(Addr), 0);
  1687. i := sizeof(Addr);
  1688. getpeername(Socket, Addr, i);
  1689. IPStr := AnsiString(inet_ntoa(Addr.sin_addr));
  1690. IPInt := Addr.sin_addr.S_addr;
  1691.  
  1692. i := 1;
  1693. ioctlsocket(Socket, FIONBIO, i);
  1694. end;{if Socket}
  1695.  
  1696. Server.CriticalSection.Section(procedure
  1697. begin
  1698. ID := 100;
  1699. while Server.GetSessionByID(ID) <> nil do inc(ID);
  1700.  
  1701. Server.Sessions.Add(Self);
  1702. end);{Server.CriticalSection.Section}
  1703.  
  1704. Packet.Time := GetTickCount + Server.Connection.Timeout;
  1705.  
  1706. BeginThread(nil, 0, @SessionThread, Pointer(Self), 0, Thread);
  1707.  
  1708. Log(['Created']);
  1709.  
  1710. Server.UpdateCaption;
  1711. end;{Server.TSession.Create}
  1712.  
  1713. destructor Server.TSession.Destroy;
  1714. begin
  1715. Logout;
  1716.  
  1717. if Socket <> 0 then
  1718. begin
  1719. closesocket(Socket);
  1720. Socket := 0;
  1721. end;{if Socket <> 0}
  1722.  
  1723. Server.CriticalSection.Section(procedure
  1724. begin
  1725. Server.Sessions.Remove(Self);
  1726. end);{Server.CriticalSection.Section}
  1727.  
  1728. Log(['Destroyed']);
  1729.  
  1730. inherited;
  1731.  
  1732. Server.UpdateCaption;
  1733. end;{Server.TSession.Destroy}
  1734.  
  1735. function Server.TSession.Sync(Discard: Boolean = False): Boolean;
  1736. var
  1737. SQL: AnsiString;
  1738. begin
  1739. if length(Name) = 0 then exit(False);
  1740.  
  1741. if Discard then
  1742. with Server.GetAccount(Name) do try
  1743. if length(Table) = 0 then exit(False);
  1744.  
  1745. Password := Value('password', 0, '');
  1746. if length(Password) = 0 then exit(False);
  1747.  
  1748. X := Value('x', 0, Server.Defaults.X);
  1749. Y := Value('y', 0, Server.Defaults.Y);
  1750. D := Value('d', 0, Server.Defaults.D);
  1751. S := Value('s', 0, 0);
  1752. Admin := Value('admin', 0, 0);
  1753. Tag := copy(Value('tag', 0, ''), 1, 3);
  1754. Sex := Value('sex', 0, 0);
  1755. HairStyle := Value('hairstyle', 0, 0);
  1756. HairColour := Value('haircolour', 0, 0);
  1757. Race := Value('race', 0, 0);
  1758. ClassID := Value('class', 0, 0);
  1759. Title := Value('title', 0, '');
  1760. Home := Value('home', 0, '');
  1761. Partner := Value('partner', 0, '');
  1762. Guild := Value('guild', 0, '');
  1763. Rank := Value('rank', 0, '');
  1764. Boots := Value('boots', 0, 0);
  1765. Armour := Value('armour', 0, 0);
  1766. Hat := Value('hat', 0, 0);
  1767. Shield := Value('shield', 0, 0);
  1768. Weapon := Value('weapon', 0, 0);
  1769.  
  1770. Result := True;
  1771. finally
  1772. Free;
  1773. end{with Server.GetAccount}
  1774. else
  1775. begin
  1776. if not Server.AccountExists(Name) then
  1777. begin
  1778. SQL := 'INSERT INTO `accounts` (`name`) VALUES ("' + Name + '");';
  1779. Result := Server.Database.Query(SQL);
  1780. if not Result then
  1781. begin
  1782. Log(['Failed to insert into database']);
  1783. exit;
  1784. end;{if not Result}
  1785. end;{if not Server.AccountExists}
  1786.  
  1787. SQL := 'UPDATE `accounts` SET ' +
  1788. '`password` = "' + Password + '", ' +
  1789. '`x` = ' + Str(X) + ', ' +
  1790. '`y` = ' + Str(Y) + ', ' +
  1791. '`d` = ' + Str(D) + ', ' +
  1792. '`s` = ' + Str(S) + ', ' +
  1793. '`admin` = ' + Str(Admin) + ', ' +
  1794. '`tag` = "' + Tag + '", ' +
  1795. '`sex` = ' + Str(Sex) + ', ' +
  1796. '`hairstyle` = ' + Str(HairStyle) + ', ' +
  1797. '`haircolour` = ' + Str(HairColour) + ', ' +
  1798. '`race` = ' + Str(Race) + ', ' +
  1799. '`class` = ' + Str(ClassID) + ', ' +
  1800. '`title` = "' + Title + '", ' +
  1801. '`home` = "' + Home + '", ' +
  1802. '`partner` = "' + Partner + '", ' +
  1803. '`guild` = "' + Guild + '", ' +
  1804. '`rank` = "' + Rank + '", '+
  1805. '`boots` = ' + Str(Boots) + ', ' +
  1806. '`armour` = ' + Str(Armour) + ', ' +
  1807. '`hat` = ' + Str(Hat) + ', ' +
  1808. '`shield` = ' + Str(Shield) + ', ' +
  1809. '`weapon` = ' + Str(Weapon) +
  1810. ' WHERE `name` = "' + Name + '";';
  1811.  
  1812. Result := Server.Database.Query(SQL);
  1813.  
  1814. if not Result then Log(['Database sync failed']);
  1815. end{else}
  1816. end;{Server.TSession.Sync}
  1817.  
  1818. procedure Server.TSession.Unload;
  1819. begin
  1820. Name := '';
  1821. Password := '';
  1822. LoggedIn := False;
  1823. end;{Server.TSession.Unload}
  1824.  
  1825. procedure Server.TSession.Log(Params: array of const);
  1826. begin
  1827. Server.Log(Params, 'Session (' + IPStr + ')');
  1828. end;{Server.TSession.Log}
  1829.  
  1830. procedure Server.TSession.Send(var Packet: TPacket; Raw: Boolean = False);
  1831. var
  1832. i, j, Size: Integer;
  1833. Encoded: AnsiString;
  1834. EncodeBuf: AnsiString;
  1835. begin
  1836. Encoded := copy(UnpackEOInt(length(Packet.Data) + 2), 1, 2) +
  1837. AnsiChar(Packet.Action) +
  1838. AnsiChar(Packet.Family) +
  1839. Packet.Data;
  1840.  
  1841. Size := length(Encoded);
  1842.  
  1843. if not Raw then
  1844. begin
  1845. Encoded := FoldData(Encoded, Server.SendKey);
  1846.  
  1847. SetLength(EncodeBuf, Size);
  1848.  
  1849. EncodeBuf[1] := Encoded[1];
  1850. EncodeBuf[2] := Encoded[2];
  1851.  
  1852. i := 2; j := 2;
  1853.  
  1854. while i < Size do
  1855. begin
  1856. EncodeBuf[i + 1] := AnsiChar(ord(Encoded[j + 1]) xor $80);
  1857. inc(j);
  1858. inc(i, 2);
  1859. end;{while i < Size}
  1860.  
  1861. i := Size - 1;
  1862. if Boolean(Size mod 2) then dec(i);
  1863.  
  1864. while i >= 2 do
  1865. begin
  1866. EncodeBuf[i + 1] := AnsiChar(ord(Encoded[j + 1]) xor $80);
  1867. inc(j);
  1868. dec(i, 2);
  1869. end;{while i >= 2}
  1870.  
  1871. for i := 3 to Size do
  1872. if EncodeBuf[i] = #128 then EncodeBuf[i] := #0
  1873. else if EncodeBuf[i] = #0 then EncodeBuf[i] := #128;
  1874.  
  1875. Encoded := EncodeBuf;
  1876. end;{if not Raw}
  1877.  
  1878. WinSock.send(Socket, Encoded[1], Size, 0);
  1879. InterlockedExchangeAdd64(Server.Connection.BytesOut, Size);
  1880. Server.UpdateCaption;
  1881. end;{Server.TSession.Send}
  1882.  
  1883. procedure Server.TSession.Send(Raw: Boolean = False);
  1884. begin
  1885. Send(Packet.Send, Raw);
  1886. end;{Server.TSession.Send}
  1887.  
  1888. procedure Server.TSession.SendData(Data: TGameData);
  1889. var
  1890. Packet: Server.TPacket;
  1891. begin
  1892. Packet.SetID(Server.PacketFamilyRaw, Server.PacketActionRaw);
  1893.  
  1894. Packet.AddInt1(Data.DataID);
  1895.  
  1896. if Data.DataID <> 4 then
  1897. Packet.AddInt1(1);
  1898.  
  1899. Packet.AddString(Data.Data);
  1900.  
  1901. Send(Packet, True);
  1902. end;{Server.TSession.SendData}
  1903.  
  1904. procedure Server.TSession.Login;
  1905. var
  1906. Packet: TPacket;
  1907. begin
  1908. Packet.SetID(Server.PacketFamilyGameState, Server.PacketActionReply);
  1909.  
  1910. Packet.AddInt2(1);
  1911. Packet.AddInt2(ID);
  1912. Packet.AddInt4(ID);
  1913. Packet.AddInt2(1); // Map ID
  1914.  
  1915. Packet.AddByte(Server.MapData.CRC[0]);
  1916. Packet.AddByte(Server.MapData.CRC[1]);
  1917. Packet.AddByte(Server.MapData.CRC[2]);
  1918. Packet.AddByte(Server.MapData.CRC[3]);
  1919. Packet.AddInt3(length(Server.MapData.Data));
  1920.  
  1921. Packet.AddByte(Server.ItemData.CRC[0]);
  1922. Packet.AddByte(Server.ItemData.CRC[1]);
  1923. Packet.AddByte(Server.ItemData.CRC[2]);
  1924. Packet.AddByte(Server.ItemData.CRC[3]);
  1925. Packet.AddByte(Server.ItemData.Len[0]);
  1926. Packet.AddByte(Server.ItemData.Len[1]);
  1927.  
  1928. Packet.AddByte(Server.NPCData.CRC[0]);
  1929. Packet.AddByte(Server.NPCData.CRC[1]);
  1930. Packet.AddByte(Server.NPCData.CRC[2]);
  1931. Packet.AddByte(Server.NPCData.CRC[3]);
  1932. Packet.AddByte(Server.NPCData.Len[0]);
  1933. Packet.AddByte(Server.NPCData.Len[1]);
  1934.  
  1935. Packet.AddByte(Server.SpellData.CRC[0]);
  1936. Packet.AddByte(Server.SpellData.CRC[1]);
  1937. Packet.AddByte(Server.SpellData.CRC[2]);
  1938. Packet.AddByte(Server.SpellData.CRC[3]);
  1939. Packet.AddByte(Server.SpellData.Len[0]);
  1940. Packet.AddByte(Server.SpellData.Len[1]);
  1941.  
  1942. Packet.AddByte(Server.ClassData.CRC[0]);
  1943. Packet.AddByte(Server.ClassData.CRC[1]);
  1944. Packet.AddByte(Server.ClassData.CRC[2]);
  1945. Packet.AddByte(Server.ClassData.CRC[3]);
  1946. Packet.AddByte(Server.ClassData.Len[0]);
  1947. Packet.AddByte(Server.ClassData.Len[1]);
  1948.  
  1949. Packet.AddBreakString(Name);
  1950. Packet.AddBreakString(Title);
  1951. Packet.AddBreakString(Guild);
  1952. Packet.AddBreakString(Rank);
  1953.  
  1954. Packet.AddInt1(ClassID);
  1955.  
  1956. Packet.AddString(copy(Tag + ' ', 1, 3)); // Tag
  1957.  
  1958. Packet.AddInt1(Admin); // Admin
  1959. Packet.AddInt1(0); // Level
  1960. Packet.AddInt4(0); // Exp
  1961. Packet.AddInt4(0); // Usage
  1962. Packet.AddInt2(10); // HP
  1963. Packet.AddInt2(10); // MaxHP
  1964. Packet.AddInt2(10); // TP
  1965. Packet.AddInt2(10); // MaxTP
  1966. Packet.AddInt2(10); // MaxSP
  1967. Packet.AddInt2(0); // Stat points
  1968. Packet.AddInt2(0); // Skill points
  1969. Packet.AddInt2(0); // Karma
  1970. Packet.AddInt2(0); // Min damage
  1971. Packet.AddInt2(0); // Max damage
  1972. Packet.AddInt2(0); // Accuracy
  1973. Packet.AddInt2(0); // Evade
  1974. Packet.AddInt2(0); // Armour
  1975.  
  1976. Packet.AddInt2(0); // Str
  1977. Packet.AddInt2(0); // Int
  1978. Packet.AddInt2(0); // Wis
  1979. Packet.AddInt2(0); // Agi
  1980. Packet.AddInt2(0); // Con
  1981. Packet.AddInt2(0); // Cha
  1982.  
  1983. Packet.AddInt2(0); // Elements
  1984. Packet.AddInt2(0);
  1985. Packet.AddInt2(0);
  1986. Packet.AddInt2(0);
  1987. Packet.AddInt2(0);
  1988. Packet.AddInt2(0);
  1989. Packet.AddInt2(0);
  1990.  
  1991. Packet.AddInt1(0); // Guild Rank
  1992. Packet.AddInt2(1); // Jail map
  1993. Packet.AddInt2(4);
  1994. Packet.AddInt1($24);
  1995. Packet.AddInt1($24);
  1996. Packet.AddInt2($10);
  1997. Packet.AddInt2($10);
  1998. Packet.AddInt2(1);
  1999. Packet.AddInt2(1);
  2000. Packet.AddInt1(0);
  2001.  
  2002. Packet.AddByte(255);
  2003.  
  2004. Send(Packet);
  2005. end;{Server.TSession.Login}
  2006.  
  2007. procedure Server.TSession.Logout;
  2008. var
  2009. Packet: TPacket;
  2010. begin
  2011. if not LoggedIn then exit;
  2012.  
  2013. Packet.SetID(Server.PacketFamilyPlayers, Server.PacketActionRemove);
  2014. Packet.AddInt2(ID);
  2015.  
  2016. Server.Send(Packet, Self);
  2017.  
  2018. Sync;
  2019. Unload;
  2020. end;{Server.TSession.Logout}
  2021.  
  2022. procedure Server.TSession.BuildCharacterPacket(var Packet: TPacket);
  2023. begin
  2024. Packet.AddBreakString(Name);
  2025.  
  2026. Packet.AddInt2(ID);
  2027.  
  2028. if LoggedIn then
  2029. begin
  2030. Packet.AddInt2(1);
  2031. Packet.AddInt2(X);
  2032. Packet.AddInt2(Y);
  2033. end{if LoggedIn}
  2034. else
  2035. begin
  2036. Packet.AddInt2(0);
  2037. Packet.AddInt2(0);
  2038. Packet.AddInt2(0);
  2039. end;{else}
  2040.  
  2041. Packet.AddInt1(D);
  2042. Packet.AddInt1(ClassID);
  2043. Packet.AddString(copy(Tag + ' ', 1, 3));
  2044. Packet.AddInt1(0); // Level
  2045. Packet.AddInt1(Sex);
  2046. Packet.AddInt1(HairStyle);
  2047. Packet.AddInt1(HairColour);
  2048. Packet.AddInt1(Race);
  2049. Packet.AddInt2(10); // MaxHP
  2050. Packet.AddInt2(10); // HP
  2051. Packet.AddInt2(10); // MaxTP
  2052. Packet.AddInt2(10); // TP
  2053.  
  2054. Packet.AddInt2(Boots);
  2055. Packet.AddInt2(0);
  2056. Packet.AddInt2(0);
  2057. Packet.AddInt2(0);
  2058. Packet.AddInt2(Armour);
  2059. Packet.AddInt2(0);
  2060. Packet.AddInt2(Hat);
  2061. Packet.AddInt2(Shield);
  2062. Packet.AddInt2(Weapon);
  2063.  
  2064. Packet.AddInt1(S);
  2065.  
  2066. if LoggedIn then
  2067. Packet.AddInt1(0) // Hidden
  2068. else
  2069. Packet.AddInt1(1);
  2070. end;{Server.TSession.BuildCharacterPacket}
  2071.  
  2072. procedure Server.TSession.Refresh;
  2073. var
  2074. Packet: TPacket;
  2075. begin
  2076. Packet.SetID(Server.PacketFamilyPlayers, Server.PacketActionRemove);
  2077. Packet.AddInt2(ID);
  2078.  
  2079. Server.Send(Packet);
  2080.  
  2081. Packet.Reset;
  2082. Packet.SetID(Server.PacketFamilyPlayers, Server.PacketActionAgree);
  2083. Packet.AddByte(255);
  2084. BuildCharacterPacket(Packet);
  2085. Packet.AddInt1(1);
  2086. Packet.AddByte(255);
  2087. Packet.AddInt1(1);
  2088.  
  2089. Server.Send(Packet);
  2090. end;{Server.TSession.Refresh}
  2091.  
  2092. function Server.TSession.Walk(Direction: Integer; Admin: Boolean = False; Ghost: Boolean = False): Boolean;
  2093. var
  2094. i: Integer;
  2095. State: Integer;
  2096. NewX, NewY: Integer;
  2097. PacketShow: TPacket;
  2098. PacketHide: TPacket;
  2099. PacketWalk: TPacket;
  2100. PacketChar: TPacket;
  2101. Session: TSession;
  2102. NewCoords: array[-Server.ViewRange..Server.ViewRange] of TPoint;
  2103. OldCoords: array[-Server.ViewRange..Server.ViewRange] of TPoint;
  2104. begin
  2105. NewX := X;
  2106. NewY := Y;
  2107.  
  2108. case Direction of
  2109. DirectionDown: inc(NewY);
  2110. DirectionLeft: dec(NewX);
  2111. DirectionUp: dec(NewY);
  2112. DirectionRight: inc(NewX);
  2113. else
  2114. Log(['Invalid walk direction ', Direction]);
  2115. exit(False);
  2116. end;{case Direction}
  2117.  
  2118. D := Direction;
  2119. X := NewX;
  2120. Y := NewY;
  2121.  
  2122. PacketShow.SetID(Server.PacketFamilyPlayers, Server.PacketActionAgree);
  2123. PacketShow.AddByte(255);
  2124. BuildCharacterPacket(PacketShow);
  2125. PacketShow.AddByte(255);
  2126. PacketShow.AddInt1(1);
  2127.  
  2128. PacketHide.SetID(Server.PacketFamilyPlayers, Server.PacketActionRemove);
  2129. PacketHide.AddInt2(ID);
  2130.  
  2131. PacketWalk.SetID(Server.PacketFamilyWalk, Server.PacketActionPlayer);
  2132. PacketWalk.AddInt2(ID);
  2133. PacketWalk.AddInt1(D);
  2134. PacketWalk.AddInt1(X);
  2135. PacketWalk.AddInt1(Y);
  2136.  
  2137. for i := -Server.ViewRange to Server.ViewRange do
  2138. case Direction of
  2139. DirectionDown:
  2140. begin
  2141. NewCoords[i].X := X + i;
  2142. NewCoords[i].Y := Y + Server.ViewRange - abs(i);
  2143. OldCoords[i].X := X + i;
  2144. OldCoords[i].Y := Y - Server.ViewRange - 1 + abs(i);
  2145. end;{DirectionDown:}
  2146.  
  2147. DirectionLeft:
  2148. begin
  2149. NewCoords[i].X := X - Server.ViewRange + abs(i);
  2150. NewCoords[i].Y := Y + i;
  2151. OldCoords[i].X := X + Server.ViewRange + 1 - abs(i);
  2152. OldCoords[i].Y := Y + i;
  2153. end;{DirectionLeft:}
  2154.  
  2155. DirectionUp:
  2156. begin
  2157. NewCoords[i].X := X + i;
  2158. NewCoords[i].Y := Y - Server.ViewRange + abs(i);
  2159. OldCoords[i].X := X + i;
  2160. OldCoords[i].Y := Y + Server.ViewRange + 1 - abs(i);
  2161. end;{DirectionUp:}
  2162.  
  2163. DirectionRight:
  2164. begin
  2165. NewCoords[i].X := X + Server.ViewRange - abs(i);
  2166. NewCoords[i].Y := Y + i;
  2167. OldCoords[i].X := X - Server.ViewRange - 1 + abs(i);
  2168. OldCoords[i].Y := Y + i;
  2169. end;{DirectionRight:}
  2170. end;{case Direction}
  2171.  
  2172. Server.CriticalSection.Enter;
  2173. try
  2174. for Session in Server.Sessions.Items do
  2175. if (Session <> Self) and Session.LoggedIn and
  2176. (Session.X >= (X - Server.ViewRange)) and (Session.X <= (X + Server.ViewRange)) and
  2177. (Session.Y >= (Y - Server.ViewRange)) and (Session.Y <= (Y + Server.ViewRange)) and
  2178. (length(Session.Name) > 0) then
  2179. begin
  2180. State := 0;
  2181.  
  2182. for i := -Server.ViewRange to Server.ViewRange do
  2183. if (Session.X = NewCoords[i].X) and (Session.Y = NewCoords[i].Y) then
  2184. begin
  2185. State := 1;
  2186. break;
  2187. end{if (Session.X...}
  2188. else if (Session.X = OldCoords[i].X) and (Session.Y = OldCoords[i].Y) then
  2189. begin
  2190. State := -1;
  2191. break;
  2192. end;{else if (Session.X...}
  2193.  
  2194. case State of
  2195. 1:
  2196. begin
  2197. PacketChar.Reset;
  2198. PacketChar.SetID(PacketFamilyPlayers, PacketActionAgree);
  2199. PacketChar.AddByte(255);
  2200. Session.BuildCharacterPacket(PacketChar);
  2201. PacketChar.AddByte(255);
  2202. PacketChar.AddInt1(1);
  2203.  
  2204. Session.Send(PacketShow);
  2205. Send(PacketChar);
  2206. end;{1:}
  2207.  
  2208. -1:
  2209. begin
  2210. PacketChar.Reset;
  2211. PacketChar.SetID(PacketFamilyPlayers, PacketActionRemove);
  2212. PacketChar.AddInt2(Session.ID);
  2213.  
  2214. Session.Send(PacketHide);
  2215. Send(PacketChar);
  2216. end;{-1:}
  2217. else
  2218. Session.Send(PacketWalk);
  2219. end;{case State}
  2220. end;{if Session <> Self}
  2221. finally
  2222. Server.CriticalSection.Leave;
  2223. end;{try...finally}
  2224.  
  2225. Result := True;
  2226. end;{Server.TSession.Walk}
  2227.  
  2228. function Server.TSession.Face(Direction: Integer): Boolean;
  2229. var
  2230. Packet: TPacket;
  2231. begin
  2232. if (Direction < 0) or (Direction > 3) then
  2233. begin
  2234. Log(['Invalid face direction ', Direction]);
  2235. exit(False);
  2236. end;{if Direction..}
  2237.  
  2238. D := Direction;
  2239.  
  2240. Packet.SetID(Server.PacketFamilyFace, Server.PacketActionPlayer);
  2241. Packet.AddInt2(ID);
  2242. Packet.AddInt1(D);
  2243.  
  2244. Server.Send(Packet, Self);
  2245.  
  2246. Result := True;
  2247. end;{Server.TSession.Face}
  2248.  
  2249. function Server.TSession.Say(Text: AnsiString): Boolean;
  2250. function StartsWith(wth: AnsiString): Boolean;
  2251. begin
  2252. Result := lower(copy(Text, 1, length(wth))) = wth;
  2253. if Result then Text := copy(Text, length(wth) + 1, length(Text));
  2254. end;{StartsWith}
  2255. var
  2256. Packet: TPacket;
  2257. begin
  2258. if length(Text) = 0 then exit(False);
  2259.  
  2260. Result := True;
  2261.  
  2262. if StartsWith('=hairstyle') then HairStyle := Int(Text)
  2263. else if StartsWith('=haircolour') then HairColour := Int(Text)
  2264. else if StartsWith('=sex') then Sex := Int(Text)
  2265. else if StartsWith('=race') then Race := Int(Text)
  2266.  
  2267. else if StartsWith('=admin') then Admin := Int(Text)
  2268.  
  2269. else if StartsWith('=tag') then Tag := copy(Text, 1, 3)
  2270.  
  2271. else if StartsWith('=armour') then Armour := Int(Text)
  2272. else if StartsWith('=boots') then Boots := Int(Text)
  2273. else if StartsWith('=hat') then Hat := Int(Text)
  2274. else if StartsWith('=shield') then Shield := Int(Text)
  2275. else if StartsWith('=weapon') then Weapon := Int(Text)
  2276.  
  2277. else
  2278. begin
  2279. Text := copy(Text, 1, Server.TextLength);
  2280.  
  2281. Packet.SetID(PacketFamilyTalk, PacketActionPlayer);
  2282.  
  2283. Packet.AddInt2(ID);
  2284. Packet.AddString(Text);
  2285.  
  2286. Server.Send(Packet, Self);
  2287. exit;
  2288. end;{else}
  2289.  
  2290. Refresh;
  2291. end;{Server.TSession.Say}
  2292.  
  2293. function Server.TSession.Execute: Boolean;
  2294. procedure QueuePacket(Time: Cardinal);
  2295. begin
  2296. if length(Packet.Queue.Items) = Server.PacketQueue.Size then
  2297. begin
  2298. Log(['Packet queue full']);
  2299. Initialized := False;
  2300. exit;
  2301. end;{if length(Packet.Queue.Items}
  2302.  
  2303. SetLength(Packet.Queue.Items, length(Packet.Queue.Items) + 1);
  2304. Packet.Queue.Items[high(Packet.Queue.Items)] := Packet.Receive;
  2305. Packet.Queue.Items[high(Packet.Queue.Items)].Time := Time;
  2306. end;{QueuePacket}
  2307.  
  2308. function UnqueuePacket: Boolean;
  2309. begin
  2310. if (length(Packet.Queue.Items) = 0) or (GetTickCount < Packet.Queue.Time) then exit(False);
  2311.  
  2312. Result := True;
  2313.  
  2314. Packet.Receive := Packet.Queue.Items[high(Packet.Queue.Items)];
  2315. SetLength(Packet.Queue.Items, length(Packet.Queue.Items) - 1);
  2316.  
  2317. Packet.Queue.Time := GetTickCount + Packet.Receive.Time;
  2318. Packet.Receive.Time := GetTickCount;
  2319. end;{UnqueuePacket}
  2320. const
  2321. BufSize = 1024;
  2322. var
  2323. i: Integer;
  2324. Size: Integer;
  2325. ReadLen: Integer;
  2326. ReadBuf: AnsiString;
  2327. begin
  2328. if (Socket = 0) or (recv(Socket, nil^, 0, MSG_OOB) = 0) then
  2329. begin
  2330. Log(['Connection dropped']);
  2331. exit(False);
  2332. end;{if (Socket = 0)..}
  2333.  
  2334. if GetTickCount > Packet.Time then
  2335. begin
  2336. Log(['Connection timeout']);
  2337. exit(False);
  2338. end;{if GetTickCount}
  2339.  
  2340. Packet.Queue.Active := UnqueuePacket;
  2341.  
  2342. if not Packet.Queue.Active then
  2343. begin
  2344. if ioctlsocket(Socket, FIONREAD, i) = 0 then
  2345. begin
  2346. SetLength(ReadBuf, BufSize);
  2347.  
  2348. repeat
  2349. ReadLen := recv(Socket, ReadBuf[1], BufSize, 0);
  2350. if ReadLen < 1 then break;
  2351.  
  2352. InterlockedExchangeAdd64(Server.Connection.BytesIn, ReadLen);
  2353.  
  2354. Packet.Buffer := Packet.Buffer + copy(ReadBuf, 1, ReadLen);
  2355. until False;
  2356.  
  2357. Server.UpdateCaption;
  2358. Packet.Time := GetTickCount + Server.Connection.Timeout;
  2359. end;{if ioctlsocket}
  2360.  
  2361. if length(Packet.Buffer) < 2 then exit(True);
  2362.  
  2363. Size := PackEOInt(ord(Packet.Buffer[1]), ord(Packet.Buffer[2]));
  2364. if length(Packet.Buffer) < (Size + 2) then exit(True);
  2365.  
  2366. Packet.Receive.Data := copy(Packet.Buffer, 3, Size);
  2367. Packet.Buffer := copy(Packet.Buffer, Size + 3, length(Packet.Buffer));
  2368.  
  2369. if Size < 3 then exit(true);
  2370.  
  2371. if Initialized then
  2372. begin
  2373. ReadBuf := '';
  2374. i := 1;
  2375.  
  2376. while i <= length(Packet.Receive.Data) do
  2377. begin
  2378. ReadBuf := ReadBuf + AnsiChar(ord(Packet.Receive.Data[i]) xor $80);
  2379. inc(i, 2);
  2380. end;{while i <= length(Packet.Receive.Data)}
  2381.  
  2382. dec(i);
  2383. if Boolean(length(Packet.Receive.Data) mod 2) then dec(i, 2);
  2384.  
  2385. repeat
  2386. ReadBuf := ReadBuf + AnsiChar(ord(Packet.Receive.Data[i]) xor $80);
  2387. dec(i, 2);
  2388. until i <= 0;
  2389.  
  2390. for i := 3 to length(Packet.Receive.Data) do
  2391. if ReadBuf[i] = #128 then ReadBuf[i] := #0
  2392. else if ReadBuf[i] = #0 then ReadBuf[i] := #128;
  2393.  
  2394. Packet.Receive.Data := FoldData(ReadBuf, ReceiveKey);
  2395. end;{if Initialized}
  2396.  
  2397. Packet.Receive.Family := ord(Packet.Receive.Data[2]);
  2398. Packet.Receive.Action := ord(Packet.Receive.Data[1]);
  2399. Packet.Receive.Data := copy(Packet.Receive.Data, 3, length(Packet.Receive.Data));
  2400. Packet.Receive.Time := GetTickCount;
  2401.  
  2402. if Packet.Receive.Family <> Server.PacketFamilyRaw then
  2403. begin
  2404. // Sequence
  2405. Packet.Receive.GetByte;
  2406. end;{if Packet.Receive.Family}
  2407. end;{if not Packet.Queue.Active}
  2408.  
  2409. Packet.Send.Reset;
  2410. Packet.Send.SetID(Packet.Receive.Family, Server.PacketActionReply);
  2411.  
  2412. i := Packet.Receive.Family;
  2413.  
  2414. if (not Server.PacketQueue.Enabled) or Packet.Queue.Active then
  2415. Dispatch(i)
  2416. else
  2417. case Packet.Receive.Family of
  2418. 0: ;
  2419. else
  2420. Dispatch(i)
  2421. end;{case Packet.Receive.Family}
  2422.  
  2423. Result := Initialized;
  2424. end;{Server.TSession.Execute}
  2425.  
  2426. procedure Server.TSession.DefaultHandler(var Param);
  2427. begin
  2428. {$IFDEF LOG_UNHANDLED_PACKET_FAMILY}
  2429. Log(['Unhandled packet family ', Packet.Receive.Family]);
  2430. {$ENDIF LOG_UNHANDLED_PACKET_FAMILY}
  2431. end;{Server.TSession.DefaultHandler}
  2432.  
  2433. procedure Server.TSession.UnhandledAction(Name: AnsiString = '');
  2434. begin
  2435. {$IFDEF LOG_UNHANDLED_PACKET_ACTION}
  2436. if length(Name) = 0 then Name := 'family (' + Str(Packet.Receive.Family) + ')';
  2437. Log(['Unhandled ' + Name + ' action ', Packet.Receive.Action]);
  2438. {$ENDIF LOG_UNHANDLED_PACKET_ACTION}
  2439. end;{Server.TSession.UnhandledAction}
  2440.  
  2441. procedure Server.TSession.HandleRaw(var Param);
  2442. function AuthClient(Auth: Integer): Integer;
  2443. begin
  2444. inc(Auth);
  2445.  
  2446. Result := (Auth mod 11 + 1) * 119;
  2447. if Result = 0 then exit;
  2448.  
  2449. Result := 110905 + (Auth mod 9 + 1) * ((11092004 - Auth) mod Result) * 119 + Auth mod 2004;
  2450. end;{AuthClient}
  2451. var
  2452. Auth: Integer;
  2453. s1, s2: Byte;
  2454. Ver: array[0..2] of Byte;
  2455. Seq: Byte;
  2456. begin
  2457. Packet.Send.SetID(Server.PacketFamilyRaw, Server.PacketActionRaw);
  2458.  
  2459. Auth := Packet.Receive.GetInt3;
  2460.  
  2461. Ver[0] := Packet.Receive.GetInt1;
  2462. Ver[1] := Packet.Receive.GetInt1;
  2463. Ver[2] := Packet.Receive.GetInt1;
  2464.  
  2465. if (Ver[0] <> Server.RequiredVersion[0])
  2466. or (Ver[1] <> Server.RequiredVersion[1])
  2467. or (Ver[2] <> Server.RequiredVersion[2]) then
  2468. begin
  2469. Packet.Send.AddByte(1);
  2470. Packet.Send.AddByte(Server.RequiredVersion[0] + 1);
  2471. Packet.Send.AddByte(Server.RequiredVersion[1] + 1);
  2472. Packet.Send.AddByte(Server.RequiredVersion[2] + 1);
  2473.  
  2474. Log(['Invalid client version ', Ver[0], '.', Ver[1], '.', Ver[2]]);
  2475.  
  2476. Send(True);
  2477. exit;
  2478. end;{if (Ver...}
  2479.  
  2480. Packet.Receive.Discard(2);
  2481. HDDSerial := Packet.Receive.GetString;
  2482.  
  2483. //2 = ok
  2484. //3 = ip permabanned
  2485. //10 = some weird sound?
  2486. Packet.Send.AddByte(2);
  2487.  
  2488. Seq := 1 + Random(220);
  2489.  
  2490. s1 := (Seq + 12) div 7;
  2491. s2 := (Seq + 5) mod 7;
  2492.  
  2493. Packet.Send.AddByte(s1);
  2494. Packet.Send.AddByte(s2);
  2495.  
  2496. Log(['Initialized']);// s1:' + Str(s1) + ' s2:' + Str(s2)]);
  2497.  
  2498. Packet.Send.AddByte(Server.SendKey);
  2499. Packet.Send.AddByte(Server.ReceiveKey);
  2500.  
  2501. Packet.Send.AddInt2(ID);
  2502.  
  2503. Packet.Send.AddInt3(AuthClient(Auth));
  2504.  
  2505. Send(True);
  2506.  
  2507. Initialized := True;
  2508. end;{Server.TSession.HandleRaw}
  2509.  
  2510. procedure Server.TSession.HandleConnection;
  2511. procedure HandleConnectionAccept;
  2512. begin
  2513. SendData(Server.ItemData);
  2514. SendData(Server.NPCData);
  2515. SendData(Server.SpellData);
  2516. SendData(Server.ClassData);
  2517. end;{HandleConnectionAccept}
  2518. begin
  2519. case Packet.Receive.Action of
  2520. Server.PacketActionAccept: HandleConnectionAccept;
  2521. else
  2522. UnhandledAction('connection');
  2523. end;{case Packet.Receive.Action}
  2524. end;{Server.TSession.HandleConnection}
  2525.  
  2526. procedure Server.TSession.HandleAccount;
  2527. const
  2528. AccountReplyAlreadyExists = 1;
  2529. AccountReplyNotApproved = 2;
  2530. AccountReplyCreated = 3;
  2531. AccountReplyChangeFailed = 5;
  2532. AccountReplyChanged = 6;
  2533. AccountReplyContinue = 1000;
  2534.  
  2535. function CheckAccount(AccountName: AnsiString): Boolean;
  2536. begin
  2537. Result := True;
  2538.  
  2539. if False{AccountsDisabled} then
  2540.  
  2541. else if not Server.ValidName(AccountName) then
  2542. begin
  2543. Packet.Send.AddInt2(AccountReplyNotApproved);
  2544. Packet.Send.AddString('NO');
  2545. Send;
  2546. end{else if not Server.ValidName}
  2547.  
  2548. else if Server.AccountExists(AccountName) then
  2549. begin
  2550. Packet.Send.AddInt2(AccountReplyAlreadyExists);
  2551. Packet.Send.AddString('NO');
  2552. Send;
  2553. end{else if}
  2554.  
  2555. else Result := False;
  2556. end;{CheckAccount}
  2557.  
  2558. procedure HandleAccountRequest;
  2559. var
  2560. AccountName: AnsiString;
  2561. begin
  2562. AccountName := Lower(Packet.Receive.GetString);
  2563.  
  2564. if CheckAccount(AccountName) then exit;
  2565.  
  2566. Packet.Send.AddInt2(AccountReplyContinue);
  2567. Packet.Send.AddString('OK');
  2568. Send;
  2569. end;{HandleAccountRequest}
  2570.  
  2571. procedure HandleAccountCreate;
  2572. var
  2573. AccountName: AnsiString;
  2574. begin
  2575. Packet.Receive.Discard(3);
  2576. AccountName := Lower(Packet.Receive.GetBreakString);
  2577.  
  2578. if CheckAccount(AccountName) then exit;
  2579.  
  2580. Name := AccountName;
  2581. Password := TSHA256.HashStr(Packet.Receive.GetBreakString);
  2582.  
  2583. {FullName := }Packet.Receive.GetBreakString;
  2584. {Location := }Packet.Receive.GetBreakString;
  2585. {EmailAddress := }Packet.Receive.GetBreakString;
  2586. {ComputerName := }Packet.Receive.GetBreakString;
  2587.  
  2588. if Packet.Receive.GetBreakString <> HDDSerial then
  2589. begin
  2590. Packet.Send.AddInt2(AccountReplyNotApproved);
  2591. Packet.Send.AddString('NO');
  2592. Send;
  2593. exit;
  2594. end;{if Packet.Receive.GetBreakString <> HDDSerial}
  2595.  
  2596. Log(['Creating account']);
  2597.  
  2598. X := Server.Defaults.X;
  2599. Y := Server.Defaults.Y;
  2600. D := Server.Defaults.D;
  2601.  
  2602. Sync;
  2603.  
  2604. Packet.Send.AddInt2(AccountReplyCreated);
  2605. Packet.Send.AddString('OK');
  2606. Send;
  2607. end;{HandleAccountCreate}
  2608. begin
  2609. case Packet.Receive.Action of
  2610. Server.PacketActionRequest: HandleAccountRequest;
  2611. Server.PacketActionCreate: HandleAccountCreate;
  2612. else
  2613. UnhandledAction('account');
  2614. end;{case Packet.Receive.Action}
  2615. end;{Server.TSession.HandleAccount}
  2616.  
  2617. procedure Server.TSession.HandleLogin(var Param);
  2618. const
  2619. LoginReplyUnknownUser = 1;
  2620. LoginReplyWrongPassword = 2;
  2621. LoginReplyOK = 3;
  2622. // 4 = clear input
  2623. LoginReplyAlreadyLoggedIn = 5;
  2624.  
  2625. procedure HandleLoginRequest;
  2626. begin
  2627. Server.CriticalSection.Section(procedure
  2628. var
  2629. User: AnsiString;
  2630. Pass: AnsiString;
  2631. begin
  2632. User := Lower(Packet.Receive.GetBreakString);
  2633. Pass := TSHA256.HashStr(Packet.Receive.GetBreakString);
  2634.  
  2635. if GetSessionByName(User) <> nil then
  2636. begin
  2637. Unload;
  2638.  
  2639. Packet.Send.AddInt2(LoginReplyAlreadyLoggedIn);
  2640. Send;
  2641.  
  2642. exit;
  2643. end;{if GetSessionByName}
  2644.  
  2645. Name := User;
  2646.  
  2647. if not Sync(True) then
  2648. begin
  2649. Unload;
  2650.  
  2651. Packet.Send.AddInt2(LoginReplyUnknownUser);
  2652. Send;
  2653. end{if not Sync(True)}
  2654. else if Pass <> Password then
  2655. begin
  2656. Unload;
  2657.  
  2658. Packet.Send.AddInt2(LoginReplyWrongPassword);
  2659. Send;
  2660. end{else if Pass <> Password}
  2661.  
  2662. else Login;
  2663. end);{Server.CriticalSection.Section}
  2664. end;{HandleLoginRequest}
  2665. begin
  2666. case Packet.Receive.Action of
  2667. Server.PacketActionRequest: HandleLoginRequest;
  2668. else
  2669. UnhandledAction('login');
  2670. end;{case Packet.Receive.Action}
  2671. end;{Server.TSession.HandleLogin}
  2672.  
  2673. procedure Server.TSession.HandleGameState(var Param);
  2674. procedure HandleGameStateAgree;
  2675. var
  2676. FileID: Byte;
  2677. begin
  2678. FileID := Packet.Receive.GetInt1;
  2679.  
  2680. case FileID of
  2681. 1: SendData(Server.MapData);
  2682. 2: SendData(Server.ItemData);
  2683. 3: SendData(Server.NPCData);
  2684. 4: SendData(Server.SpellData);
  2685. 5: SendData(Server.ClassData);
  2686. else
  2687. Log(['Unknown file ID ', FileID]);
  2688. end;{case FileID}
  2689. end;{HandleGameStateAgree}
  2690.  
  2691. procedure HandleGameStateMessage;
  2692. var
  2693. i: Integer;
  2694. begin
  2695. Packet.Send.AddInt2(2);
  2696. Packet.Send.AddByte(255);
  2697.  
  2698. Packet.Send.AddBreakString('MEOW');
  2699.  
  2700. for i := 0 to 6 do
  2701. Packet.Send.AddBreakString('');
  2702.  
  2703. Packet.Send.AddByte(255);
  2704.  
  2705. Packet.Send.AddInt1(0); // Weight
  2706. Packet.Send.AddInt1(50); // Max weight
  2707.  
  2708. Packet.Send.AddByte(255); // Inventory
  2709. Packet.Send.AddByte(255); // Spells
  2710.  
  2711. LoggedIn := True;
  2712.  
  2713. Server.CriticalSection.Section(procedure
  2714. var
  2715. p, Count: Integer;
  2716. Session: Server.TSession;
  2717. begin
  2718. p := length(Packet.Send.Data) + 1;
  2719. Packet.Send.AddInt1(0);
  2720. Packet.Send.AddByte(255);
  2721.  
  2722. Count := 0;
  2723.  
  2724. for Session in Server.Sessions.Items do
  2725. if Session.LoggedIn then
  2726. begin
  2727. Session.BuildCharacterPacket(Packet.Send);
  2728. Packet.Send.AddByte(255);
  2729. inc(Count);
  2730. end;{if Session.LoggedIn}
  2731.  
  2732. Packet.Send.Data[p] := UnpackEOInt(Count)[1];
  2733. end);{Server.CriticalSection.Section}
  2734.  
  2735. Packet.Send.AddByte(255); // NPCs
  2736. //Packet.Send.AddByte(255); // Items
  2737.  
  2738. Send;
  2739.  
  2740. Packet.Send.Reset;
  2741. Packet.Send.SetID(Server.PacketFamilyPlayers, Server.PacketActionAgree);
  2742. Packet.Send.AddByte(255);
  2743. BuildCharacterPacket(Packet.Send);
  2744. Packet.Send.AddInt1(1);
  2745. Packet.Send.AddByte(255);
  2746. Packet.Send.AddInt1(1);
  2747.  
  2748. Server.Send(Packet.Send, Self);
  2749. end;{HandleGameStateMessage}
  2750. begin
  2751. case Packet.Receive.Action of
  2752. Server.PacketActionRequest: Login;
  2753. Server.PacketActionAgree: HandleGameStateAgree;
  2754. Server.PacketActionMessage: HandleGameStateMessage;
  2755. else
  2756. UnhandledAction('game state');
  2757. end;{case Packet.Receive.Action}
  2758. end;{Server.TSession.HandleGameState}
  2759.  
  2760. procedure Server.TSession.HandleWalk(var Param);
  2761. begin
  2762. case Packet.Receive.Action of
  2763. Server.PacketActionPlayer: Walk(Packet.Receive.GetInt1);
  2764. Server.PacketActionSpecial: Walk(Packet.Receive.GetInt1, False, True);
  2765. Server.PacketActionAdmin: Walk(Packet.Receive.GetInt1, True);
  2766. else
  2767. UnhandledAction('walk');
  2768. end;{case Packet.Receive.Action}
  2769. end;{Server.TSession.HandleWalk}
  2770.  
  2771. procedure Server.TSession.HandleFace(var Param);
  2772. begin
  2773. case Packet.Receive.Action of
  2774. Server.PacketActionPlayer: Face(Packet.Receive.GetInt1);
  2775. else
  2776. UnhandledAction('face');
  2777. end;{case Packet.Receive.Action}
  2778. end;{Server.TSession.HandleFace}
  2779.  
  2780. procedure Server.TSession.HandleRequest(var Param);
  2781. procedure HandleRequestRequest;
  2782. var
  2783. RequestID: Integer;
  2784. Session: TSession;
  2785. begin
  2786. RequestID := Packet.Receive.GetInt2;
  2787.  
  2788. Packet.Send.SetID(Server.PacketFamilyPlayers, Server.PacketActionRemove);
  2789. Packet.Send.AddInt2(RequestID);
  2790. Send;
  2791.  
  2792. Packet.Send.Reset;
  2793. Packet.Send.SetID(Server.PacketFamilyPlayers, Server.PacketActionAgree);
  2794. Packet.Send.AddByte(255);
  2795.  
  2796. Server.CriticalSection.Enter;
  2797. try
  2798. Session := Server.GetSessionByID(RequestID);
  2799. if Session = nil then exit;
  2800.  
  2801. Session.BuildCharacterPacket(Packet.Send);
  2802. finally
  2803. Server.CriticalSection.Leave;
  2804. end;{try..finally}
  2805.  
  2806. Packet.Send.AddInt1(1);
  2807. Packet.Send.AddByte(255);
  2808. Packet.Send.AddInt1(1);
  2809.  
  2810. Send;
  2811. end;{HandleRequestRequest}
  2812. begin
  2813. case Packet.Receive.Action of
  2814. Server.PacketActionRequest: HandleRequestRequest;
  2815. else
  2816. UnhandledAction('request');
  2817. end;{case Packet.Receive.Action}
  2818. end;{Server.TSession.HandleRequest}
  2819.  
  2820. procedure Server.TSession.HandleTalk(var Param);
  2821. begin
  2822. case Packet.Receive.Action of
  2823. Server.PacketActionReport: Say(Packet.Receive.GetBreakString);
  2824. else
  2825. UnhandledAction('talk');
  2826. end;{case Packet.Receive.Action}
  2827. end;{Server.TSession.HandleTalk}
  2828.  
  2829. begin
  2830. Server.Create;
  2831. end.
Advertisement
Add Comment
Please, Sign In to add comment
Advertisement