Sordie.co.uk

sea/Sea.Launcher.pas

Raw

{(
 )) Sea.Launcher
((    Sordie's Endless Augments - Main executable
 ))
((  admin@sordie.co.uk
 )}

program Sea.Launcher;

{$SETPEFLAGS 1}
{$IFOPT D-}
  {$WEAKLINKRTTI ON}
{$ENDIF}
{$RTTI EXPLICIT METHODS([]) PROPERTIES([]) FIELDS([])}
{$R *.res}

uses
  Winapi.Windows;

const
  //Exe: PAnsiChar = '.\endless.exe';
  Ini: PChar = '.\Sea\Sea.Config.ini';
  Dll: PChar = '.\Sea\Sea.Startup.dll';

procedure Error(Msg: String);
begin
  AllocConsole;

  Writeln(Msg);
  Readln;

  Halt(1);
end;

var
  Exe: String;

  HKernel32: THandle;

  SInfo: TStartupInfo;
  PInfo: TProcessInformation;

  Param: Pointer;

  Size: SIZE_T;

  Thread:   THandle;
  ThreadID: DWORD;

  PLoadLibrary: Pointer;
begin
  if GetFileAttributes('.\msimg32.dll') <> INVALID_FILE_ATTRIBUTES then
    Error('Disable or uninstall EO.Addons to use Sea');

  SetLength(Exe, MAX_PATH);
  SetLength(Exe, GetPrivateProfileString('Sea', 'Executable', '.\Endless.exe', @Exe[1], Length(Exe), Ini));

  HKernel32 := LoadLibrary(kernel32);
  if HKernel32 = 0 then
    Error('Failed to load kernel library');

  PLoadLibrary := GetProcAddress(HKernel32, 'LoadLibraryW');
  if PLoadLibrary = nil then
    Error('Failed to locate API');

  FillChar(SInfo, SizeOf(SInfo), 0);
  SInfo.cb := SizeOf(SInfo);

  if not CreateProcess(@Exe[1], nil, nil, nil, False, 0, nil, nil, SInfo, PInfo) then
    Error('Failed to create process');

  Param := VirtualAllocEx(PInfo.hProcess, nil, SizeOf(Char) * (Length(Dll) + 1), MEM_COMMIT, PAGE_READWRITE);
  if Param = nil then
    Error('Failed to allocate parameter memory');

  if not WriteProcessMemory(PInfo.hProcess, Param, Dll, SizeOf(Char) * Length(Dll), Size) then
    Error('Failed to write to parameter memory');

  Thread := CreateRemoteThread(PInfo.hProcess, nil, 0, PLoadLibrary, Param, 0, ThreadID);
  if Thread = 0 then
    Error('Failed to create remote thread');

  WaitForSingleObject(Thread, INFINITE);
  CloseHandle(Thread);

  VirtualFreeEx(PInfo.hProcess, Param, 0, MEM_RELEASE);
end.