sysutils.pp 24 KB

123456789101112131415161718192021222324252627282930313233343536373839404142434445464748495051525354555657585960616263646566676869707172737475767778798081828384858687888990919293949596979899100101102103104105106107108109110111112113114115116117118119120121122123124125126127128129130131132133134135136137138139140141142143144145146147148149150151152153154155156157158159160161162163164165166167168169170171172173174175176177178179180181182183184185186187188189190191192193194195196197198199200201202203204205206207208209210211212213214215216217218219220221222223224225226227228229230231232233234235236237238239240241242243244245246247248249250251252253254255256257258259260261262263264265266267268269270271272273274275276277278279280281282283284285286287288289290291292293294295296297298299300301302303304305306307308309310311312313314315316317318319320321322323324325326327328329330331332333334335336337338339340341342343344345346347348349350351352353354355356357358359360361362363364365366367368369370371372373374375376377378379380381382383384385386387388389390391392393394395396397398399400401402403404405406407408409410411412413414415416417418419420421422423424425426427428429430431432433434435436437438439440441442443444445446447448449450451452453454455456457458459460461462463464465466467468469470471472473474475476477478479480481482483484485486487488489490491492493494495496497498499500501502503504505506507508509510511512513514515516517518519520521522523524525526527528529530531532533534535536537538539540541542543544545546547548549550551552553554555556557558559560561562563564565566567568569570571572573574575576577578579580581582583584585586587588589590591592593594595596597598599600601602603604605606607608609610611612613614615616617618619620621622623624625626627628629630631632633634635636637638639640641642643644645646647648649650651652653654655656657658659660661662663664665666667668669670671672673674675676677678679680681682683684685686687688689690691692693694695696697698699700701702703704705706707708709710711712713714715716717718719720721722723724725726727728729730731732733734735736737738739740741742743744745746747748749750751752753754755756757758759760761762763764765766767768769770771772773774775776777778779780781782783784785786787788789790791792793794795796797798799800801802803804805806807808809810811812813814815816817818819820821822823824825826827828829830831832833834835836837838839840841842843844845846847848849850851852853854855856857858859860861862863864865866867868869870871872873874875876877878879880881882883884885886887888889890891892893894895896897898899900901902903904905906907908909910911912913914915916917918919920921922923924925926927928929930931932933934935936937938939940941942943944945946947948949950951952953954955956957958959960961962963964965966967968969970971972973974975
  1. {
  2. This file is part of the Free Pascal run time library.
  3. Copyright (c) 1999-2005 by Florian Klaempfl and Yury Sidorov
  4. members of the Free Pascal development team
  5. Sysutils unit for wince
  6. See the file COPYING.FPC, included in this distribution,
  7. for details about the copyright.
  8. This program is distributed in the hope that it will be useful,
  9. but WITHOUT ANY WARRANTY; without even the implied warranty of
  10. MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE.
  11. **********************************************************************}
  12. unit sysutils;
  13. interface
  14. {$MODE objfpc}
  15. { force ansistrings }
  16. {$H+}
  17. uses
  18. dos,
  19. windows;
  20. {$DEFINE HAS_SLEEP}
  21. {$DEFINE HAS_OSERROR}
  22. {$DEFINE HAS_OSCONFIG}
  23. { Include platform independent interface part }
  24. {$i sysutilh.inc}
  25. type
  26. TSystemTime = Windows.TSystemTime;
  27. EWinCEError = class(Exception)
  28. public
  29. ErrorCode : DWORD;
  30. end;
  31. Var
  32. WinCEPlatform : Longint;
  33. WinCEMajorVersion,
  34. WinCEMinorVersion,
  35. WinCEBuildNumber : dword;
  36. WinCECSDVersion : ShortString; // CSD record is 128 bytes only?
  37. implementation
  38. uses
  39. sysconst;
  40. {$DEFINE FPC_NOGENERICANSIROUTINES}
  41. {$define HASEXPANDUNCFILENAME}
  42. { Include platform independent implementation part }
  43. {$i sysutils.inc}
  44. procedure PWideCharToString(const str: PWideChar; out Result: string; strlen: longint = -1);
  45. var
  46. len: longint;
  47. begin
  48. if str^ = #0 then
  49. Result:=''
  50. else
  51. begin
  52. while True do begin
  53. if strlen <> -1 then
  54. len:=(strlen + 1) div SizeOf(WideChar)
  55. else
  56. len:=WideToAnsiBuf(str, -1, nil, 0);
  57. if len > 0 then
  58. begin
  59. SetLength(Result, len - 1);
  60. if (WideToAnsiBuf(str, -1, @Result[1], len) = 0) and (strlen <> -1) then
  61. begin
  62. strlen:=-1;
  63. continue;
  64. end;
  65. end
  66. else
  67. Result:='';
  68. break;
  69. end;
  70. end;
  71. end;
  72. function ExpandUNCFileName (const filename:string) : string;
  73. { returns empty string on errors }
  74. var
  75. s : widestring;
  76. size : dword;
  77. rc : dword;
  78. buf : pwidechar;
  79. begin
  80. s := ExpandFileName (filename);
  81. size := max_path*SizeOf(WideChar);
  82. getmem(buf,size);
  83. try
  84. rc := WNetGetUniversalName (pwidechar(s), UNIVERSAL_NAME_INFO_LEVEL, buf, @size);
  85. if rc=ERROR_MORE_DATA then
  86. begin
  87. buf:=reallocmem(buf,size);
  88. rc := WNetGetUniversalName (pwidechar(s), UNIVERSAL_NAME_INFO_LEVEL, buf, @size);
  89. end;
  90. if rc = NO_ERROR then
  91. Result := PRemoteNameInfo(buf)^.lpUniversalName
  92. else if rc = ERROR_NOT_CONNECTED then
  93. Result := filename
  94. else
  95. Result := '';
  96. finally
  97. freemem(buf);
  98. end;
  99. end;
  100. {****************************************************************************
  101. File Functions
  102. ****************************************************************************}
  103. Function FileOpen (Const FileName : string; Mode : Integer) : THandle;
  104. const
  105. AccessMode: array[0..2] of Cardinal = (
  106. GENERIC_READ,
  107. GENERIC_WRITE,
  108. GENERIC_READ or GENERIC_WRITE);
  109. ShareMode: array[0..4] of Integer = (
  110. 0,
  111. 0,
  112. FILE_SHARE_READ,
  113. FILE_SHARE_WRITE,
  114. FILE_SHARE_READ or FILE_SHARE_WRITE);
  115. var
  116. fn: PWideChar;
  117. begin
  118. fn:=StringToPWideChar(FileName);
  119. result := CreateFile(fn, dword(AccessMode[Mode and 3]),
  120. dword(ShareMode[(Mode and $F0) shr 4]), nil, OPEN_EXISTING,
  121. FILE_ATTRIBUTE_NORMAL, 0);
  122. FreeMem(fn);
  123. end;
  124. Function FileCreate (Const FileName : String) : THandle;
  125. var
  126. fn: PWideChar;
  127. begin
  128. fn:=StringToPWideChar(FileName);
  129. Result := CreateFile(fn, GENERIC_READ or GENERIC_WRITE,
  130. 0, nil, CREATE_ALWAYS, FILE_ATTRIBUTE_NORMAL, 0);
  131. FreeMem(fn);
  132. end;
  133. Function FileCreate (Const FileName : String; Mode:longint) : THandle;
  134. begin
  135. FileCreate:=FileCreate(FileName);
  136. end;
  137. Function FileRead (Handle : THandle; Var Buffer; Count : longint) : Longint;
  138. Var
  139. res : dword;
  140. begin
  141. if ReadFile(Handle, Buffer, Count, res, nil) then
  142. FileRead:=Res
  143. else
  144. FileRead:=-1;
  145. end;
  146. Function FileWrite (Handle : THandle; const Buffer; Count : Longint) : Longint;
  147. Var
  148. Res : dword;
  149. begin
  150. if WriteFile(Handle, Buffer, Count, Res, nil) then
  151. FileWrite:=Res
  152. else
  153. FileWrite:=-1;
  154. end;
  155. Function FileSeek (Handle : THandle;FOffset,Origin : Longint) : Longint;
  156. begin
  157. Result := longint(SetFilePointer(Handle, FOffset, nil, Origin));
  158. end;
  159. Function FileSeek (Handle : THandle; FOffset,Origin : Int64) : Int64;
  160. begin
  161. {$warning need to add 64bit call }
  162. Result := longint(SetFilePointer(Handle, longint(FOffset), nil, longint(Origin)));
  163. end;
  164. Procedure FileClose (Handle : THandle);
  165. begin
  166. if Handle<=4 then
  167. exit;
  168. CloseHandle(Handle);
  169. end;
  170. Function FileTruncate (Handle : THandle;Size: Longint) : boolean;
  171. begin
  172. Result:=longint(SetFilePointer(handle,Size,nil,FILE_BEGIN))<>-1;
  173. If Result then
  174. Result:=SetEndOfFile(handle);
  175. end;
  176. Function DosToWinTime (DTime:longint; out Wtime : TFileTime):longbool;
  177. begin
  178. DosToWinTime:=dos.DosToWinTime(DTime, Wtime);
  179. end;
  180. Function WinToDosTime (Const Wtime : TFileTime; out DTime:longint):longbool;
  181. begin
  182. WinToDosTime:=dos.WinToDosTime(Wtime, DTime);
  183. end;
  184. Function FileAge (Const FileName : String): Longint;
  185. var
  186. Handle: THandle;
  187. FindData: TWin32FindData;
  188. fn: PWideChar;
  189. begin
  190. fn:=StringToPWideChar(FileName);
  191. Handle := FindFirstFile(fn, FindData);
  192. FreeMem(fn);
  193. if Handle <> INVALID_HANDLE_VALUE then
  194. begin
  195. Windows.FindClose(Handle);
  196. if (FindData.dwFileAttributes and FILE_ATTRIBUTE_DIRECTORY) = 0 then
  197. If WinToDosTime(FindData.ftLastWriteTime,Result) then
  198. exit;
  199. end;
  200. Result := -1;
  201. end;
  202. Function FileExists (Const FileName : String) : Boolean;
  203. var
  204. Attr:Dword;
  205. begin
  206. Attr:=FileGetAttr(FileName);
  207. if Attr <> $ffffffff then
  208. Result:= (Attr and FILE_ATTRIBUTE_DIRECTORY) = 0
  209. else
  210. Result:=False;
  211. end;
  212. Function DirectoryExists (Const Directory : String) : Boolean;
  213. var
  214. Attr:Dword;
  215. begin
  216. Attr:=FileGetAttr(Directory);
  217. if Attr <> $ffffffff then
  218. Result:= (Attr and FILE_ATTRIBUTE_DIRECTORY) <> 0
  219. else
  220. Result:=False;
  221. end;
  222. Function FindMatch(var f: TSearchRec) : Longint;
  223. begin
  224. { Find file with correct attribute }
  225. While (F.FindData.dwFileAttributes and cardinal(F.ExcludeAttr))<>0 do
  226. begin
  227. if not FindNextFile (F.FindHandle,F.FindData) then
  228. begin
  229. Result:=GetLastError;
  230. exit;
  231. end;
  232. end;
  233. { Convert some attributes back }
  234. WinToDosTime(F.FindData.ftLastWriteTime,F.Time);
  235. f.size:=F.FindData.NFileSizeLow;
  236. f.attr:=F.FindData.dwFileAttributes;
  237. PWideCharToString(@F.FindData.cFileName, f.Name);
  238. Result:=0;
  239. end;
  240. Function FindFirst (Const Path : String; Attr : Longint; out Rslt : TSearchRec) : Longint;
  241. var
  242. fn: PWideChar;
  243. begin
  244. fn:=StringToPWideChar(Path);
  245. Rslt.Name:=Path;
  246. Rslt.Attr:=attr;
  247. Rslt.ExcludeAttr:=(not Attr) and ($1e);
  248. { $1e = faHidden or faSysFile or faVolumeID or faDirectory }
  249. { FindFirstFile is a WinCE Call }
  250. Rslt.FindHandle:=FindFirstFile (fn, Rslt.FindData);
  251. FreeMem(fn);
  252. If Rslt.FindHandle=Invalid_Handle_value then
  253. begin
  254. Result:=GetLastError;
  255. exit;
  256. end;
  257. { Find file with correct attribute }
  258. Result:=FindMatch(Rslt);
  259. end;
  260. Function FindNext (Var Rslt : TSearchRec) : Longint;
  261. begin
  262. if FindNextFile(Rslt.FindHandle, Rslt.FindData) then
  263. Result := FindMatch(Rslt)
  264. else
  265. Result := GetLastError;
  266. end;
  267. Procedure FindClose (Var F : TSearchrec);
  268. begin
  269. if F.FindHandle <> INVALID_HANDLE_VALUE then
  270. Windows.FindClose(F.FindHandle);
  271. end;
  272. Function FileGetDate (Handle : THandle) : Longint;
  273. Var
  274. FT : TFileTime;
  275. begin
  276. If GetFileTime(Handle,nil,nil,@ft) and
  277. WinToDosTime(FT, Result) then
  278. exit;
  279. Result:=-1;
  280. end;
  281. Function FileSetDate (Handle : THandle;Age : Longint) : Longint;
  282. Var
  283. FT: TFileTime;
  284. begin
  285. Result := 0;
  286. if DosToWinTime(Age, FT) and SetFileTime(Handle, FT, FT, FT) then
  287. Exit;
  288. Result := GetLastError;
  289. end;
  290. Function FileGetAttr (Const FileName : String) : Longint;
  291. var
  292. fn: PWideChar;
  293. begin
  294. fn:=StringToPWideChar(FileName);
  295. Result:=GetFileAttributes(fn);
  296. FreeMem(fn);
  297. end;
  298. Function FileSetAttr (Const Filename : String; Attr: longint) : Longint;
  299. var
  300. fn: PWideChar;
  301. begin
  302. fn:=StringToPWideChar(FileName);
  303. if not SetFileAttributes(fn, Attr) then
  304. Result := GetLastError
  305. else
  306. Result:=0;
  307. FreeMem(fn);
  308. end;
  309. Function DeleteFile (Const FileName : String) : Boolean;
  310. var
  311. fn: PWideChar;
  312. begin
  313. fn:=StringToPWideChar(FileName);
  314. DeleteFile:=Windows.DeleteFile(fn);
  315. FreeMem(fn);
  316. end;
  317. Function RenameFile (Const OldName, NewName : String) : Boolean;
  318. var
  319. fold, fnew: PWideChar;
  320. begin
  321. fold:=StringToPWideChar(OldName);
  322. fnew:=StringToPWideChar(NewName);
  323. Result := MoveFile(fold, fnew);
  324. FreeMem(fnew);
  325. FreeMem(fold);
  326. end;
  327. {****************************************************************************
  328. Disk Functions
  329. ****************************************************************************}
  330. function diskfree(drive : byte) : int64;
  331. begin
  332. Result := Dos.diskfree(drive);
  333. end;
  334. function disksize(drive : byte) : int64;
  335. begin
  336. Result := Dos.disksize(drive);
  337. end;
  338. Function GetCurrentDir : String;
  339. begin
  340. GetDir(0, result);
  341. end;
  342. Function SetCurrentDir (Const NewDir : String) : Boolean;
  343. begin
  344. {$I-}
  345. ChDir(NewDir);
  346. {$I+}
  347. result := (IOResult = 0);
  348. end;
  349. Function CreateDir (Const NewDir : String) : Boolean;
  350. begin
  351. {$I-}
  352. MkDir(NewDir);
  353. {$I+}
  354. result := (IOResult = 0);
  355. end;
  356. Function RemoveDir (Const Dir : String) : Boolean;
  357. begin
  358. {$I-}
  359. RmDir(Dir);
  360. {$I+}
  361. result := (IOResult = 0);
  362. end;
  363. {****************************************************************************
  364. Time Functions
  365. ****************************************************************************}
  366. Procedure GetLocalTime(var SystemTime: TSystemTime);
  367. Var
  368. Syst : Windows.TSystemtime;
  369. begin
  370. windows.Getlocaltime(@syst);
  371. SystemTime.year:=syst.wYear;
  372. SystemTime.month:=syst.wMonth;
  373. SystemTime.day:=syst.wDay;
  374. SystemTime.hour:=syst.wHour;
  375. SystemTime.minute:=syst.wMinute;
  376. SystemTime.second:=syst.wSecond;
  377. SystemTime.millisecond:=syst.wMilliSeconds;
  378. end;
  379. {****************************************************************************
  380. Misc Functions
  381. ****************************************************************************}
  382. procedure Beep;
  383. begin
  384. MessageBeep(0);
  385. end;
  386. {****************************************************************************
  387. Locale Functions
  388. ****************************************************************************}
  389. Procedure InitAnsi;
  390. Var
  391. i : longint;
  392. begin
  393. { Fill table entries 0 to 127 }
  394. for i := 0 to 96 do
  395. UpperCaseTable[i] := chr(i);
  396. for i := 97 to 122 do
  397. UpperCaseTable[i] := chr(i - 32);
  398. for i := 123 to 191 do
  399. UpperCaseTable[i] := chr(i);
  400. Move (CPISO88591UCT,UpperCaseTable[192],SizeOf(CPISO88591UCT));
  401. for i := 0 to 64 do
  402. LowerCaseTable[i] := chr(i);
  403. for i := 65 to 90 do
  404. LowerCaseTable[i] := chr(i + 32);
  405. for i := 91 to 191 do
  406. LowerCaseTable[i] := chr(i);
  407. Move (CPISO88591LCT,UpperCaseTable[192],SizeOf(CPISO88591UCT));
  408. end;
  409. function GetLocaleStr(LID, LT: Longint; const Def: string): ShortString;
  410. var
  411. L: Integer;
  412. Buf: array[0..255] of WideChar;
  413. s: widestring;
  414. begin
  415. L := GetLocaleInfo(LID, LT, Buf, SizeOf(Buf) div SizeOf(WideChar));
  416. if L > 0 then
  417. begin
  418. SetString(s, Buf, L - 1);
  419. Result:=s;
  420. end
  421. else
  422. Result := Def;
  423. end;
  424. function GetLocaleChar(LID, LT: Longint; Def: Char): Char;
  425. var
  426. Buf: array[0..1] of WideChar;
  427. Buf2: array[0..1] of Char;
  428. begin
  429. if GetLocaleInfo(LID, LT, Buf, 2) > 0 then
  430. begin
  431. WideToAnsiBuf(Buf, -1, Buf2, SizeOf(Buf2));
  432. Result := Buf2[0];
  433. end
  434. else
  435. Result := Def;
  436. end;
  437. Function GetLocaleInt(LID,TP,Def: LongInt): LongInt;
  438. Var
  439. S: String;
  440. C: Integer;
  441. Begin
  442. S:=GetLocaleStr(LID,TP,'0');
  443. Val(S,Result,C);
  444. If C<>0 Then
  445. Result:=Def;
  446. End;
  447. procedure GetFormatSettings;
  448. var
  449. HF : Shortstring;
  450. LID : LCID;
  451. I,Day,DateOrder : longint;
  452. begin
  453. LID := GetUserDefaultLCID;
  454. { Date stuff }
  455. for I := 1 to 12 do
  456. begin
  457. ShortMonthNames[I]:=GetLocaleStr(LID,LOCALE_SABBREVMONTHNAME1+I-1,ShortMonthNames[i]);
  458. LongMonthNames[I]:=GetLocaleStr(LID,LOCALE_SMONTHNAME1+I-1,LongMonthNames[i]);
  459. end;
  460. for I := 1 to 7 do
  461. begin
  462. Day := (I + 5) mod 7;
  463. ShortDayNames[I]:=GetLocaleStr(LID,LOCALE_SABBREVDAYNAME1+Day,ShortDayNames[i]);
  464. LongDayNames[I]:=GetLocaleStr(LID,LOCALE_SDAYNAME1+Day,LongDayNames[i]);
  465. end;
  466. DateSeparator := GetLocaleChar(LID, LOCALE_SDATE, '/');
  467. DateOrder := GetLocaleInt(LID, LOCALE_IDate, 0);
  468. Case DateOrder Of
  469. 1: Begin
  470. ShortDateFormat := 'dd/mm/yyyy';
  471. LongDateFormat := 'dddd, d. mmmm yyyy';
  472. End;
  473. 2: Begin
  474. ShortDateFormat := 'yyyy/mm/dd';
  475. LongDateFormat := 'dddd, yyyy mmmm d.';
  476. End;
  477. else
  478. // Default american settings...
  479. ShortDateFormat := 'mm/dd/yyyy';
  480. LongDateFormat := 'dddd, mmmm d. yyyy';
  481. End;
  482. { Time stuff }
  483. TimeSeparator := GetLocaleChar(LID, LOCALE_STIME, ':');
  484. TimeAMString := GetLocaleStr(LID, LOCALE_S1159, 'AM');
  485. TimePMString := GetLocaleStr(LID, LOCALE_S2359, 'PM');
  486. if StrToIntDef(GetLocaleStr(LID, LOCALE_ITLZERO, '0'), 0) = 0 then
  487. HF:='h'
  488. else
  489. HF:='hh';
  490. // No support for 12 hour stuff at the moment...
  491. ShortTimeFormat := HF+':nn';
  492. LongTimeFormat := HF + ':nn:ss';
  493. { Currency stuff }
  494. CurrencyString:=GetLocaleStr(LID, LOCALE_SCURRENCY, '');
  495. CurrencyFormat:=StrToIntDef(GetLocaleStr(LID, LOCALE_ICURRENCY, '0'), 0);
  496. NegCurrFormat:=StrToIntDef(GetLocaleStr(LID, LOCALE_INEGCURR, '0'), 0);
  497. { Number stuff }
  498. ThousandSeparator:=GetLocaleChar(LID, LOCALE_STHOUSAND, ',');
  499. DecimalSeparator:=GetLocaleChar(LID, LOCALE_SDECIMAL, '.');
  500. CurrencyDecimals:=StrToIntDef(GetLocaleStr(LID, LOCALE_ICURRDIGITS, '0'), 0);
  501. end;
  502. Procedure InitInternational;
  503. begin
  504. InitInternationalGeneric;
  505. SysLocale.MBCS:=GetSystemMetrics(SM_DBCSENABLED)<>0;
  506. SysLocale.RightToLeft:=GetSystemMetrics(SM_MIDEASTENABLED)<>0;
  507. InitAnsi;
  508. GetFormatSettings;
  509. end;
  510. {****************************************************************************
  511. Target Dependent
  512. ****************************************************************************}
  513. function SysErrorMessage(ErrorCode: Integer): String;
  514. var
  515. MsgBuffer: PWideChar;
  516. len: longint;
  517. begin
  518. len:=FormatMessage(
  519. FORMAT_MESSAGE_ALLOCATE_BUFFER or FORMAT_MESSAGE_FROM_SYSTEM or FORMAT_MESSAGE_IGNORE_INSERTS,
  520. nil,
  521. ErrorCode,
  522. 0,
  523. @MsgBuffer, { This function allocs the memory }
  524. 0,
  525. nil);
  526. while (len > 0) and (MsgBuffer[len - 1] <= #32) do
  527. Dec(len);
  528. MsgBuffer[len]:=#0;
  529. PWideCharToString(PWideChar(MsgBuffer), Result);
  530. LocalFree(HLOCAL(MsgBuffer));
  531. end;
  532. {****************************************************************************
  533. Initialization code
  534. ****************************************************************************}
  535. // WinCE does not have environment. It can be emulated via registry or file. (YS)
  536. Function GetEnvironmentVariable(Const EnvVar : String) : String;
  537. begin
  538. Result := '';
  539. end;
  540. Function GetEnvironmentVariableCount : Integer;
  541. begin
  542. Result := 0;
  543. end;
  544. Function GetEnvironmentString(Index : Integer) : String;
  545. begin
  546. Result := '';
  547. end;
  548. function ExecuteProcess(Const Path: AnsiString; Const ComLine: AnsiString):integer;
  549. var
  550. PI: TProcessInformation;
  551. Proc : THandle;
  552. l : DWord;
  553. e : EOSError;
  554. begin
  555. DosError := 0;
  556. if not CreateProcess(PWideChar(widestring(Path)), PWideChar(widestring(ComLine)),
  557. nil, nil, FALSE, 0, nil, nil, nil, PI) then
  558. begin
  559. e:=EOSError.CreateFmt(SExecuteProcessFailed,[Path,GetLastError]);
  560. e.ErrorCode:=GetLastError;
  561. raise e;
  562. end;
  563. Proc:=PI.hProcess;
  564. CloseHandle(PI.hThread);
  565. if WaitForSingleObject(Proc, dword($ffffffff)) <> $ffffffff then
  566. begin
  567. GetExitCodeProcess(Proc,l);
  568. CloseHandle(Proc);
  569. result:=l;
  570. end
  571. else
  572. begin
  573. e:=EOSError.CreateFmt(SExecuteProcessFailed,[Path,GetLastError]);
  574. e.ErrorCode:=GetLastError;
  575. CloseHandle(Proc);
  576. raise e;
  577. end;
  578. end;
  579. function ExecuteProcess(Const Path: AnsiString; Const ComLine: Array of AnsiString):integer;
  580. Var
  581. CommandLine : AnsiString;
  582. i : Integer;
  583. Begin
  584. Commandline:='';
  585. For i:=0 to high(ComLine) Do
  586. Commandline:=CommandLine+' '+Comline[i];
  587. ExecuteProcess:=ExecuteProcess(Path,CommandLine);
  588. End;
  589. Procedure Sleep(Milliseconds : Cardinal);
  590. begin
  591. Windows.Sleep(MilliSeconds)
  592. end;
  593. Function GetLastOSError : Integer;
  594. begin
  595. Result:=GetLastError;
  596. end;
  597. {****************************************************************************
  598. Initialization code
  599. ****************************************************************************}
  600. Procedure LoadVersionInfo;
  601. Var
  602. versioninfo : TOSVERSIONINFO;
  603. i : Integer;
  604. begin
  605. versioninfo.dwOSVersionInfoSize:=sizeof(versioninfo);
  606. GetVersionEx(versioninfo);
  607. WinCEPlatform:=versionInfo.dwPlatformId;
  608. WinCEMajorVersion:=versionInfo.dwMajorVersion;
  609. WinCEMinorVersion:=versionInfo.dwMinorVersion;
  610. WinCEBuildNumber:=versionInfo.dwBuildNumber;
  611. i:=WideToAnsiBuf(@versioninfo.szCSDVersion, -1, @WinCECSDVersion[1], SizeOf(WinCECSDVersion) - 1);
  612. if i <> 0 then
  613. WinCECSDVersion[0]:=chr(i - 1);
  614. end;
  615. Function GetSpecialDir(ID: Integer) : String;
  616. Var
  617. APath : array[0..MAX_PATH] of WideChar;
  618. begin
  619. if SHGetSpecialFolderPath(0, APath, ID, True) then
  620. begin
  621. PWideCharToString(APath, Result);
  622. Result:=IncludeTrailingPathDelimiter(Result);
  623. end
  624. else
  625. Result:='';
  626. end;
  627. Function GetAppConfigDir(Global : Boolean) : String;
  628. begin
  629. If Global then
  630. Result:=DGetAppConfigDir(Global) // or use windows dir ??
  631. else
  632. begin
  633. Result:=GetSpecialDir(CSIDL_APPDATA)+ApplicationName;
  634. If (Result='') then
  635. Result:=DGetAppConfigDir(Global);
  636. end;
  637. end;
  638. Function GetAppConfigFile(Global : Boolean; SubDir : Boolean) : String;
  639. begin
  640. if Global then
  641. begin
  642. Result:=IncludeTrailingPathDelimiter(DGetAppConfigDir(Global));
  643. if SubDir then
  644. Result:=IncludeTrailingPathDelimiter(Result+'Config');
  645. Result:=Result+ApplicationName+ConfigExtension;
  646. end
  647. else
  648. begin
  649. Result:=IncludeTrailingPathDelimiter(GetAppConfigDir(False));
  650. if SubDir then
  651. Result:=Result+'Config\';
  652. Result:=Result+ApplicationName+ConfigExtension;
  653. end;
  654. end;
  655. {****************************************************************************
  656. Target Dependent WideString stuff
  657. ****************************************************************************}
  658. function WinCECompareWideString(const s1, s2 : WideString) : PtrInt;
  659. begin
  660. SetLastError(0);
  661. Result:=CompareString(LOCALE_USER_DEFAULT,0,pwidechar(s1),
  662. length(s1),pwidechar(s2),length(s2))-2;
  663. if GetLastError<>0 then
  664. RaiseLastOSError;
  665. end;
  666. function WinCECompareTextWideString(const s1, s2 : WideString) : PtrInt;
  667. begin
  668. SetLastError(0);
  669. Result:=CompareString(LOCALE_USER_DEFAULT,NORM_IGNORECASE,pwidechar(s1),
  670. length(s1),pwidechar(s2),length(s2))-2;
  671. if GetLastError<>0 then
  672. RaiseLastOSError;
  673. end;
  674. function WinCEAnsiUpperCase(const s: string): string;
  675. var
  676. buf: PWideChar;
  677. len: longint;
  678. begin
  679. if s <> '' then
  680. begin
  681. buf:=StringToPWideChar(s, @len);
  682. CharUpperBuff(buf, len);
  683. PWideCharToString(buf, Result, len);
  684. FreeMem(buf);
  685. end
  686. else
  687. Result:='';
  688. end;
  689. function WinCEAnsiLowerCase(const s: string): string;
  690. var
  691. buf: PWideChar;
  692. len: longint;
  693. begin
  694. if s <> '' then
  695. begin
  696. buf:=StringToPWideChar(s, @len);
  697. CharLowerBuff(buf, len);
  698. PWideCharToString(buf, Result, len);
  699. FreeMem(buf);
  700. end
  701. else
  702. Result:='';
  703. end;
  704. function WinCEAnsiCompareStr(const S1, S2: string): PtrInt;
  705. var
  706. ws1, ws2: PWideChar;
  707. begin
  708. ws1:=StringToPWideChar(S1);
  709. ws2:=StringToPWideChar(S2);
  710. Result:=CompareString(LOCALE_USER_DEFAULT, 0, ws1, -1, ws2, -1) - 2;
  711. FreeMem(ws2);
  712. FreeMem(ws1);
  713. end;
  714. function WinCEAnsiCompareText(const S1, S2: string): PtrInt;
  715. var
  716. ws1, ws2: PWideChar;
  717. begin
  718. ws1:=StringToPWideChar(S1);
  719. ws2:=StringToPWideChar(S2);
  720. Result:=CompareString(LOCALE_USER_DEFAULT, NORM_IGNORECASE, ws1, -1, ws2, -1) - 2;
  721. FreeMem(ws2);
  722. FreeMem(ws1);
  723. end;
  724. function WinCEAnsiStrComp(S1, S2: PChar): PtrInt;
  725. var
  726. ws1, ws2: PWideChar;
  727. begin
  728. ws1:=PCharToPWideChar(S1);
  729. ws2:=PCharToPWideChar(S2);
  730. Result:=CompareString(LOCALE_USER_DEFAULT, 0, ws1, -1, ws2, -1) - 2;
  731. FreeMem(ws2);
  732. FreeMem(ws1);
  733. end;
  734. function WinCEAnsiStrIComp(S1, S2: PChar): PtrInt;
  735. var
  736. ws1, ws2: PWideChar;
  737. begin
  738. ws1:=PCharToPWideChar(S1);
  739. ws2:=PCharToPWideChar(S2);
  740. Result:=CompareString(LOCALE_USER_DEFAULT, NORM_IGNORECASE, ws1, -1, ws2, -1) - 2;
  741. FreeMem(ws2);
  742. FreeMem(ws1);
  743. end;
  744. function WinCEAnsiStrLComp(S1, S2: PChar; MaxLen: PtrUInt): PtrInt;
  745. var
  746. ws1, ws2: PWideChar;
  747. len1, len2: longint;
  748. begin
  749. ws1:=PCharToPWideChar(S1, MaxLen, @len1);
  750. ws2:=PCharToPWideChar(S2, MaxLen, @len2);
  751. Result:=CompareString(LOCALE_USER_DEFAULT, 0, ws1, len1, ws2, len2) - 2;
  752. FreeMem(ws2);
  753. FreeMem(ws1);
  754. end;
  755. function WinCEAnsiStrLIComp(S1, S2: PChar; MaxLen: PtrUInt): PtrInt;
  756. var
  757. ws1, ws2: PWideChar;
  758. len1, len2: longint;
  759. begin
  760. ws1:=PCharToPWideChar(S1, MaxLen, @len1);
  761. ws2:=PCharToPWideChar(S2, MaxLen, @len2);
  762. Result:=CompareString(LOCALE_USER_DEFAULT, NORM_IGNORECASE, ws1, len1, ws2, len2) - 2;
  763. FreeMem(ws2);
  764. FreeMem(ws1);
  765. end;
  766. function WinCEAnsiStrLower(Str: PChar): PChar;
  767. var
  768. buf: PWideChar;
  769. len: longint;
  770. begin
  771. buf:=PCharToPWideChar(Str, -1, @len);
  772. CharLowerBuff(buf, len);
  773. WideToAnsiBuf(buf, -1, Result, len + 1);
  774. FreeMem(buf);
  775. end;
  776. function WinCEAnsiStrUpper(Str: PChar): PChar;
  777. var
  778. buf: PWideChar;
  779. len: longint;
  780. begin
  781. buf:=PCharToPWideChar(Str, -1, @len);
  782. CharUpperBuff(buf, len);
  783. WideToAnsiBuf(buf, -1, Result, len + 1);
  784. FreeMem(buf);
  785. end;
  786. { there is a similiar procedure in the system unit which inits the fields which
  787. are relevant already for the system unit }
  788. procedure InitWinCEWidestrings;
  789. begin
  790. widestringmanager.CompareWideStringProc:=@WinCECompareWideString;
  791. widestringmanager.CompareTextWideStringProc:=@WinCECompareTextWideString;
  792. widestringmanager.UpperAnsiStringProc:=@WinCEAnsiUpperCase;
  793. widestringmanager.LowerAnsiStringProc:=@WinCEAnsiLowerCase;
  794. widestringmanager.CompareStrAnsiStringProc:=@WinCEAnsiCompareStr;
  795. widestringmanager.CompareTextAnsiStringProc:=@WinCEAnsiCompareText;
  796. widestringmanager.StrCompAnsiStringProc:=@WinCEAnsiStrComp;
  797. widestringmanager.StrICompAnsiStringProc:=@WinCEAnsiStrIComp;
  798. widestringmanager.StrLCompAnsiStringProc:=@WinCEAnsiStrLComp;
  799. widestringmanager.StrLICompAnsiStringProc:=@WinCEAnsiStrLIComp;
  800. widestringmanager.StrLowerAnsiStringProc:=@WinCEAnsiStrLower;
  801. widestringmanager.StrUpperAnsiStringProc:=@WinCEAnsiStrUpper;
  802. end;
  803. Initialization
  804. InitWinCEWidestrings;
  805. InitExceptions; { Initialize exceptions. OS independent }
  806. InitInternational; { Initialize internationalization settings }
  807. LoadVersionInfo;
  808. SysConfigDir:='\Windows';
  809. Finalization
  810. DoneExceptions;
  811. end.