sysutils.pp 19 KB

123456789101112131415161718192021222324252627282930313233343536373839404142434445464748495051525354555657585960616263646566676869707172737475767778798081828384858687888990919293949596979899100101102103104105106107108109110111112113114115116117118119120121122123124125126127128129130131132133134135136137138139140141142143144145146147148149150151152153154155156157158159160161162163164165166167168169170171172173174175176177178179180181182183184185186187188189190191192193194195196197198199200201202203204205206207208209210211212213214215216217218219220221222223224225226227228229230231232233234235236237238239240241242243244245246247248249250251252253254255256257258259260261262263264265266267268269270271272273274275276277278279280281282283284285286287288289290291292293294295296297298299300301302303304305306307308309310311312313314315316317318319320321322323324325326327328329330331332333334335336337338339340341342343344345346347348349350351352353354355356357358359360361362363364365366367368369370371372373374375376377378379380381382383384385386387388389390391392393394395396397398399400401402403404405406407408409410411412413414415416417418419420421422423424425426427428429430431432433434435436437438439440441442443444445446447448449450451452453454455456457458459460461462463464465466467468469470471472473474475476477478479480481482483484485486487488489490491492493494495496497498499500501502503504505506507508509510511512513514515516517518519520521522523524525526527528529530531532533534535536537538539540541542543544545546547548549550551552553554555556557558559560561562563564565566567568569570571572573574575576577578579580581582583584585586587588589590591592593594595596597598599600601602603604605606607608609610611612613614615616617618619620621622623624625626627628629630631632633634635636637638639640641642643644645646647648649650651652653654655656657658659660661662663664665666667668669670671672673674675676677678679680681682683684685686687688689690691692693694695696697698699700701702703704705706707708709710711712713
  1. {
  2. This file is part of the Free Pascal run time library.
  3. Copyright (c) 1999-2004 by the Free Pascal development team.
  4. Sysutils unit for netware (libc)
  5. See the file COPYING.FPC, included in this distribution,
  6. for details about the copyright.
  7. This program is distributed in the hope that it will be useful,
  8. but WITHOUT ANY WARRANTY; without even the implied warranty of
  9. MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE.
  10. **********************************************************************}
  11. unit sysutils;
  12. interface
  13. {$MODE objfpc}
  14. { force ansistrings }
  15. {$H+}
  16. uses Libc,DOS;
  17. TYPE
  18. TNetwareLibcFindData =
  19. RECORD
  20. DirP : Pdirent; { used for opendir }
  21. EntryP: Pdirent; { and readdir }
  22. Magic : longint; { to avoid abends with uninitialized TSearchRec }
  23. _mask : string; { search mask i.e. *.* }
  24. _dir : string; { directory where to search }
  25. _attr : longint; { specified attribute }
  26. fname : string; { full pathname of found file }
  27. END;
  28. {$DEFINE HAS_SLEEP}
  29. {$DEFINE HAS_OSERROR}
  30. { Include platform independent interface part }
  31. {$i sysutilh.inc}
  32. { additional NetWare file flags}
  33. CONST
  34. faSHARE = M_A_SHARE shr 16; // Sharable file
  35. //faNO_SUBALLOC = $00000800; // Don't sub alloc. this file
  36. faTRANS = M_A_TRANS shr 16; // Transactional file (TTS usable)
  37. //faREADAUD = $00004000; // clib only: Read audit
  38. //faWRITAUD = $00008000; // clib only: Write audit
  39. faIMMPURG = M_A_IMMPURG shr 16; // Immediate purge
  40. faNORENAM = M_A_NORENAM shr 16; // Rename inhibit
  41. faNODELET = M_A_NODELET shr 16; // Delete inhibit
  42. faNOCOPY = M_A_NOCOPY shr 16; // Copy inhibit
  43. //faFILE_MIGRATED = $00400000; // clib only: File has been migrated
  44. //faDONT_MIGRATE = $00800000; // clib only: Don't migrate this file
  45. faIMMEDIATE_COMPRESS = M_A_IMMCOMPRESS shr 16; // Compress this file immediately
  46. faFILE_COMPRESSED = M_A_FILE_COMPRESSED shr 16; // File is compressed
  47. faDONT_COMPRESS = M_A_DONT_COMPRESS shr 16; // Don't compress this file
  48. faCANT_COMPRESS = M_A_CANT_COMPRESS shr 16; // Can't compress this file
  49. //faATTR_ARCHIVE = $40000000; // clib only: Entry has had an EA modified,
  50. // an ownerID changed, or trustee
  51. // info changed, etc.
  52. faSetNetwareAttrs = M_A_BITS_SIGNIFICANT; // if this is set, netware flags are changed also
  53. implementation
  54. uses
  55. sysconst;
  56. {$DEFINE FPC_FEXPAND_DRIVES}
  57. {$DEFINE FPC_FEXPAND_VOLUMES}
  58. {$DEFINE FPC_FEXPAND_NO_DEFAULT_PATHS}
  59. { Include platform independent implementation part }
  60. {$i sysutils.inc}
  61. {****************************************************************************
  62. File Functions
  63. ****************************************************************************}
  64. Function FileOpen (Const FileName : string; Mode : Integer) : THandle;
  65. VAR NWOpenFlags : longint;
  66. BEGIN
  67. NWOpenFlags:=0;
  68. Case (Mode and 3) of
  69. 0 : NWOpenFlags:=NWOpenFlags or O_RDONLY;
  70. 1 : NWOpenFlags:=NWOpenFlags or O_WRONLY;
  71. 2 : NWOpenFlags:=NWOpenFlags or O_RDWR;
  72. end;
  73. FileOpen := Fpopen (pchar(FileName),NWOpenFlags);
  74. //!! We need to set locking based on Mode !!
  75. end;
  76. Function FileCreate (Const FileName : String) : THandle;
  77. begin
  78. FileCreate:=Fpopen(Pchar(FileName),O_RdWr or O_Creat or O_Trunc or O_Binary);
  79. if FileCreate >= 0 then
  80. FileSetAttr (Filename, 0); // dont know why but open always sets ReadOnly flag
  81. end;
  82. Function FileCreate (Const FileName : String; mode:longint) : THandle;
  83. begin
  84. FileCreate:=FileCreate (FileName);
  85. end;
  86. Function FileRead (Handle : THandle; Var Buffer; Count : longint) : Longint;
  87. begin
  88. FileRead:=libc.fpread (Handle,@Buffer,Count);
  89. end;
  90. Function FileWrite (Handle : THandle; const Buffer; Count : Longint) : Longint;
  91. begin
  92. FileWrite:=libc.fpwrite (Handle,@Buffer,Count);
  93. end;
  94. Function FileSeek (Handle : THandle; FOffset,Origin : Longint) : Longint;
  95. begin
  96. FileSeek:=libc.fplseek (Handle,FOffset,Origin);
  97. end;
  98. Function FileSeek (Handle : THandle; FOffset: Int64; Origin: Longint) : Int64;
  99. begin
  100. FileSeek:=libc.fplseek64 (Handle,FOffset,Origin);
  101. end;
  102. Procedure FileClose (Handle : THandle);
  103. begin
  104. libc.fpclose(Handle);
  105. end;
  106. Function FileTruncate (Handle : THandle; Size: Int64) : boolean;
  107. begin
  108. if Size > high (longint) then
  109. FileTruncate := false
  110. {$WARNING Possible support for 64-bit FS to be checked!}
  111. else
  112. FileTruncate:=(libc.fpchsize(Handle,Size) = 0);
  113. end;
  114. Function FileLock (Handle : THandle; FOffset,FLen : Longint) : Longint;
  115. begin
  116. {$warning FileLock not implemented}
  117. //FileLock := _lock (Handle,FOffset,FLen);
  118. FileLock := -1;
  119. end;
  120. Function FileLock (Handle : THandle; FOffset,FLen : Int64) : Longint;
  121. begin
  122. {$warning need to add 64bit FileLock call }
  123. //FileLock := FileLock (Handle, longint(FOffset),longint(FLen));
  124. FileLock := -1;
  125. end;
  126. Function FileUnlock (Handle : THandle; FOffset,FLen : Longint) : Longint;
  127. begin
  128. //FileUnlock := _unlock (Handle,FOffset,FLen);
  129. {$warning FileUnLock not implemented}
  130. FileUnlock := -1;
  131. end;
  132. Function FileUnlock (Handle : THandle; FOffset,FLen : Int64) : Longint;
  133. begin
  134. {$warning need to add 64bit FileUnlock call }
  135. //FileUnlock := FileUnlock (Handle, longint(FOffset),longint(FLen));
  136. FileUnlock := -1;
  137. end;
  138. Function FileAge (Const FileName : String): Longint;
  139. var Info : TStat;
  140. TM : TTM;
  141. begin
  142. If Fpstat (pchar(FileName),Info) <> 0 then
  143. exit(-1)
  144. else
  145. begin
  146. localtime_r (Info.st_mtim.tv_sec,tm);
  147. with TM do
  148. result:=DateTimeToFileDate(EncodeDate(tm_year+1900,tm_mon+1,tm_mday)+EncodeTime(tm_hour,tm_min,tm_sec,0));
  149. end;
  150. end;
  151. Function FileExists (Const FileName : String) : Boolean;
  152. VAR Info : TStat;
  153. begin
  154. FileExists:=(Fpstat(pchar(filename),Info) = 0);
  155. end;
  156. Function UnixToWinAge(UnixAge : time_t): Longint;
  157. Var tm : TTm;
  158. begin
  159. libc.localtime_r (UnixAge, tm);
  160. with tm do
  161. Result:=DateTimeToFileDate(EncodeDate(tm_year+1900,tm_mon+1,tm_mday)+EncodeTime(tm_hour,tm_min,tm_sec,0));
  162. end;
  163. {returns true if attributes match}
  164. function find_setfields (var f : TsearchRec; var AttrsOk : boolean) : longint;
  165. var
  166. StatBuf : TStat;
  167. fname : string;
  168. begin
  169. result := 0;
  170. with F do
  171. begin
  172. if FindData.Magic = $AD02 then
  173. begin
  174. attr := (Pdirent(FindData.EntryP)^.d_mode shr 16) and $ffff;
  175. size := Pdirent(FindData.EntryP)^.d_size;
  176. name := strpas (Pdirent(FindData.EntryP)^.d_name);
  177. fname := FindData._dir + name;
  178. if Fpstat (pchar(fname),StatBuf) = 0 then
  179. time := UnixToWinAge (StatBuf.st_mtim.tv_sec)
  180. else
  181. time := 0;
  182. AttrsOk := false;
  183. if (f.FindData._attr and faHidden) = 0 then
  184. if attr and faHidden > 0 then exit;
  185. if (f.FindData._attr and faDirectory) = 0 then
  186. if attr and faDirectory > 0 then exit;
  187. if (f.FindData._attr and faSysFile) = 0 then
  188. if attr and faSysFile > 0 then exit;
  189. AttrsOk := true;
  190. end else
  191. begin
  192. FillChar (f,sizeof(f),0);
  193. result := 18;
  194. end;
  195. end;
  196. end;
  197. function findfirst(const path : string;attr : longint; out Rslt : TsearchRec) : longint;
  198. var
  199. path0 : string;
  200. p : longint;
  201. begin
  202. IF path = '' then
  203. begin
  204. result := 18;
  205. exit;
  206. end;
  207. Rslt.FindData._attr := attr;
  208. p := length (path);
  209. while (p > 0) and (not (path[p] in AllowDirectorySeparators)) do
  210. dec (p);
  211. if p > 0 then
  212. begin
  213. Rslt.FindData._mask := copy (path,p+1,255);
  214. Rslt.FindData._dir := copy (path,1,p);
  215. end else
  216. begin
  217. Rslt.FindData._mask := path;
  218. Rslt.FindData._dir := GetCurrentDir;
  219. if (Rslt.FindData._dir[length(Rslt.FindData._dir)] <> '/') and
  220. (Rslt.FindData._dir[length(Rslt.FindData._dir)] <> '\') then
  221. Rslt.FindData._dir := Rslt.FindData._dir + '/';
  222. end;
  223. if Rslt.FindData._mask = '*' then Rslt.FindData._mask := '';
  224. if Rslt.FindData._mask = '*.*' then Rslt.FindData._mask := '';
  225. //writeln (stderr,'mask: "',Rslt._mask,'" dir:"',path0,'"');
  226. Pdirent(Rslt.FindData.DirP) := opendir (pchar(Rslt.FindData._dir));
  227. if Rslt.FindData.DirP = nil then
  228. result := 18
  229. else begin
  230. Rslt.FindData.Magic := $AD02;
  231. result := findnext (Rslt);
  232. end;
  233. end;
  234. function findnext(var Rslt : TsearchRec) : longint;
  235. var attrsOk : boolean;
  236. begin
  237. if Rslt.FindData.Magic <> $AD02 then
  238. begin
  239. result := 18;
  240. exit;
  241. end;
  242. result:=0;
  243. repeat
  244. Pdirent(Rslt.FindData.EntryP) := readdir (Pdirent(Rslt.FindData.DirP));
  245. if Rslt.FindData.EntryP = nil then
  246. result := 18
  247. else
  248. result := find_setfields (Rslt,attrsOk);
  249. if (result = 0) and (attrsOk) then
  250. begin
  251. if Rslt.FindData._mask = #0 then exit;
  252. if fnmatch(@Rslt.FindData._mask[1],Pdirent(Rslt.FindData.EntryP)^.d_name,FNM_CASEFOLD) = 0 then
  253. exit;
  254. end;
  255. until result <> 0;
  256. end;
  257. Procedure FindClose(Var f: TSearchRec);
  258. begin
  259. if F.FindData.Magic <> $AD02 then exit;
  260. doserror:=0;
  261. closedir (Pdirent(f.FindData.DirP));
  262. FillChar (f,sizeof(f),0);
  263. end;
  264. Function FileGetDate (Handle : THandle) : Longint;
  265. Var Info : TStat;
  266. _PTM : PTM;
  267. begin
  268. If Fpfstat(Handle,Info) <> 0 then
  269. Result:=-1
  270. else
  271. begin
  272. _PTM := localtime (Info.st_mtim.tv_sec);
  273. IF _PTM = NIL THEN
  274. exit(-1)
  275. else
  276. with _PTM^ do
  277. Result:=DateTimeToFileDate(EncodeDate(tm_year+1900,tm_mon+1,tm_mday)+EncodeTime(tm_hour,tm_min,tm_sec,0));
  278. end;
  279. end;
  280. Function FileSetDate (Handle : THandle; Age : Longint) : Longint;
  281. Begin
  282. {dont know how to do that, utime needs filename}
  283. result := -1;
  284. end;
  285. Function FileGetAttr (Const FileName : String) : Longint;
  286. Var Info : TStat;
  287. begin
  288. If Fpstat (pchar(FileName),Info) <> 0 then
  289. Result:=-1
  290. Else
  291. Result := (Info.st_mode shr 16) and $ffff;
  292. end;
  293. Function FileSetAttr (Const Filename : String; Attr: longint) : Longint;
  294. var
  295. StatBuf : TStat;
  296. newMode : longint;
  297. begin
  298. if Fpstat (pchar(Filename),StatBuf) = 0 then
  299. begin
  300. {what should i do here ?
  301. only support sysutils-standard attributes or also support the extensions defined
  302. only for netware libc ?
  303. For now i allow the complete attributes if the bit faSetNetwareAttrs is set. Otherwise
  304. only the standard attributes can be modified}
  305. if attr and faSetNetwareAttrs > 0 then
  306. begin
  307. newmode := ((attr shl 16) and $ffff0000) or M_A_BITS_SIGNIFICANT;
  308. end else
  309. begin
  310. attr := (attr and $2f) shl 16;
  311. newmode := StatBuf.st_mode and ($ffff0000-M_A_RDONLY-M_A_HIDDEN- M_A_SYSTEM-M_A_SUBDIR-M_A_ARCH);
  312. newmode := newmode or (attr shl 16) or M_A_BITS_SIGNIFICANT;
  313. end;
  314. if Fpchmod (pchar(Filename),newMode) < 0 then
  315. result := ___errno^ else
  316. result := 0;
  317. end else
  318. result := ___errno^;
  319. end;
  320. Function DeleteFile (Const FileName : String) : Boolean;
  321. begin
  322. Result:= (libc.UnLink (pchar(FileName)) = 0);
  323. end;
  324. Function RenameFile (Const OldName, NewName : String) : Boolean;
  325. begin
  326. RenameFile:=(libc.rename(pchar(OldName),pchar(NewName)) = 0);
  327. end;
  328. {****************************************************************************
  329. Disk Functions
  330. ****************************************************************************}
  331. {
  332. The Diskfree and Disksize functions need a file on the specified drive, since this
  333. is required for the statfs system call.
  334. These filenames are set in drivestr[0..26], and have been preset to :
  335. 0 - '.' (default drive - hence current dir is ok.)
  336. 1 - '/fd0/.' (floppy drive 1 - should be adapted to local system )
  337. 2 - '/fd1/.' (floppy drive 2 - should be adapted to local system )
  338. 3 - '/' (C: equivalent of dos is the root partition)
  339. 4..26 (can be set by you're own applications)
  340. ! Use AddDisk() to Add new drives !
  341. They both return -1 when a failure occurs.
  342. }
  343. Const
  344. FixDriveStr : array[0..3] of pchar=(
  345. '.',
  346. 'a:.',
  347. 'b:.',
  348. 'sys:/'
  349. );
  350. var
  351. Drives : byte;
  352. DriveStr : array[4..26] of pchar;
  353. Procedure AddDisk(const path:string);
  354. begin
  355. if not (DriveStr[Drives]=nil) then
  356. FreeMem(DriveStr[Drives],StrLen(DriveStr[Drives])+1);
  357. GetMem(DriveStr[Drives],length(Path)+1);
  358. StrPCopy(DriveStr[Drives],path);
  359. inc(Drives);
  360. if Drives>26 then
  361. Drives:=4;
  362. end;
  363. Function DiskFree(Drive: Byte): int64;
  364. //var fs : Tstatfs;
  365. Begin
  366. { if ((Drive<4) and (not (fixdrivestr[Drive]=nil)) and fsstat(StrPas(fixdrivestr[drive]),fs)) or
  367. ((not (drivestr[Drive]=nil)) and fsstat(StrPas(drivestr[drive]),fs)) then
  368. Diskfree:=int64(fs.bavail)*int64(fs.bsize)
  369. else
  370. Diskfree:=-1;}
  371. DiskFree := -1;
  372. ConsolePrintf ('warning: fpc sysutils.diskfree not implemented'#13#10);
  373. {$warning DiskFree not implemented (does it make sense ?) }
  374. End;
  375. Function DiskSize(Drive: Byte): int64;
  376. //var fs : statfs;
  377. Begin
  378. { if ((Drive<4) and (not (fixdrivestr[Drive]=nil)) and fsstat(StrPas(fixdrivestr[drive]),fs)) or
  379. ((not (drivestr[Drive]=nil)) and fsstat(StrPas(drivestr[drive]),fs)) then
  380. DiskSize:=int64(fs.blocks)*int64(fs.bsize)
  381. else
  382. DiskSize:=-1;}
  383. DiskSize := -1;
  384. ConsolePrintf ('warning: fpc sysutils.disksize not implemented'#13#10);
  385. {$warning DiskSize not implemented (does it make sense ?) }
  386. End;
  387. Function GetCurrentDir : String;
  388. begin
  389. GetDir (0,Result);
  390. end;
  391. Function SetCurrentDir (Const NewDir : String) : Boolean;
  392. begin
  393. Libc.FpChDir(pchar(NewDir));
  394. result := (___errno^ = 0);
  395. end;
  396. Function CreateDir (Const NewDir : String) : Boolean;
  397. begin
  398. Libc.FpMkDir(pchar(NewDir),0);
  399. result := (___errno^ = 0);
  400. end;
  401. Function RemoveDir (Const Dir : String) : Boolean;
  402. begin
  403. libc.FpRmDir(pchar(Dir));
  404. result := (___errno^ = 0);
  405. end;
  406. function DirectoryExists (const Directory: string): boolean;
  407. var Info : TStat;
  408. begin
  409. If Fpstat (pchar(Directory),Info) <> 0 then
  410. exit(false)
  411. else
  412. Exit ((Info.st_mode and M_A_SUBDIR) <> 0);
  413. end;
  414. {****************************************************************************
  415. Misc Functions
  416. ****************************************************************************}
  417. procedure Beep;
  418. begin
  419. RingBell;
  420. end;
  421. {****************************************************************************
  422. Locale Functions
  423. ****************************************************************************}
  424. Procedure GetLocalTime(var SystemTime: TSystemTime);
  425. var t : TTime;
  426. tm: Ttm;
  427. begin
  428. libc.time(t);
  429. libc.localtime_r(t,tm);
  430. with SystemTime do
  431. begin
  432. Hour := tm.tm_hour;
  433. Minute := tm.tm_min;
  434. Second := tm.tm_sec;
  435. MilliSecond := 0;
  436. Day := tm.tm_mday;
  437. Month := tm.tm_mon+1;
  438. Year := tm.tm_year+1900;
  439. end;
  440. end;
  441. Procedure InitAnsi;
  442. Var i : longint;
  443. begin
  444. { Fill table entries 0 to 127 }
  445. for i := 0 to 96 do
  446. UpperCaseTable[i] := chr(i);
  447. for i := 97 to 122 do
  448. UpperCaseTable[i] := chr(i - 32);
  449. for i := 123 to 191 do
  450. UpperCaseTable[i] := chr(i);
  451. Move (CPISO88591UCT,UpperCaseTable[192],SizeOf(CPISO88591UCT));
  452. for i := 0 to 64 do
  453. LowerCaseTable[i] := chr(i);
  454. for i := 65 to 90 do
  455. LowerCaseTable[i] := chr(i + 32);
  456. for i := 91 to 191 do
  457. LowerCaseTable[i] := chr(i);
  458. Move (CPISO88591LCT,UpperCaseTable[192],SizeOf(CPISO88591UCT));
  459. end;
  460. Procedure InitInternational;
  461. begin
  462. InitInternationalGeneric;
  463. InitAnsi;
  464. end;
  465. function SysErrorMessage(ErrorCode: Integer): String;
  466. begin
  467. Result:=''; // only found perror that prints the message
  468. end;
  469. {****************************************************************************
  470. OS utility functions
  471. ****************************************************************************}
  472. Function GetEnvironmentVariable(Const EnvVar : String) : String;
  473. begin
  474. Result:=StrPas(libc.getenv(PChar(EnvVar)));
  475. end;
  476. Function GetEnvironmentVariableCount : Integer;
  477. begin
  478. Result:=FPCCountEnvVar(EnvP);
  479. end;
  480. Function GetEnvironmentString(Index : Integer) : String;
  481. begin
  482. Result:=FPCGetEnvStrFromP(Envp,Index);
  483. end;
  484. function ExecuteProcess(Const Path: AnsiString; Const ComLine: AnsiString):integer;
  485. var
  486. params:array of AnsiString;
  487. count,i: longint;
  488. Buf : pchar;
  489. p : pchar;
  490. CLine: AnsiString;
  491. begin
  492. cLine := ComLine;
  493. buf:=pchar(CLine);
  494. count:=0;
  495. while(buf^<>#0) do
  496. begin
  497. while (buf^ in [' ',#9,#10]) do
  498. inc(buf);
  499. inc(count);
  500. while not (buf^ in [' ',#0,#9,#10]) do
  501. inc(buf);
  502. end;
  503. i := 0;
  504. setlength(params,count);
  505. buf:=pchar(CLine);
  506. while(buf^<>#0) do
  507. begin
  508. while (buf^ in [' ',#9,#10]) do
  509. inc(buf);
  510. p := buf;
  511. while not (buf^ in [' ',#0,#9,#10]) do
  512. inc(buf);
  513. if buf^ <> #0 then
  514. begin
  515. buf^ := #0;
  516. inc(buf);
  517. end;
  518. params[i]:=p;
  519. inc(i);
  520. end;
  521. result := ExecuteProcess (Path, params);
  522. end;
  523. Function GetLastOSError : Integer;
  524. begin
  525. Result:=Integer(GetLastError);
  526. end;
  527. {******************************************************************************
  528. --- Exec ---
  529. ******************************************************************************}
  530. const maxargs=256;
  531. function ExecuteProcess (const Path: AnsiString;
  532. const ComLine: array of AnsiString): integer;
  533. var c : comstr;
  534. i : integer;
  535. args : array[0..maxargs+1] of pchar;
  536. arg0 : string;
  537. numargs,wstat : integer;
  538. Wiring : TWiring;
  539. newPath : string;
  540. e : EOSError;
  541. begin
  542. if pos ('.',path) = 0 then
  543. arg0 := fexpand(path+'.nlm')
  544. else
  545. arg0 := fexpand (path);
  546. args[0] := pchar(arg0);
  547. numargs := 0;
  548. for I := 0 to High (ComLine) do
  549. if numargs < maxargs then
  550. begin
  551. inc(numargs);
  552. args[numargs] := pchar(ComLine[i]);
  553. end;
  554. args[numargs+1] := nil;
  555. Wiring.infd := StdInputHandle; //textrec(Stdin).Handle;
  556. Wiring.outfd:= textrec(stdout).Handle;
  557. Wiring.errfd:= textrec(stderr).Handle;
  558. i := procve(args[0],
  559. PROC_CURRENT_SPACE+PROC_INHERIT_CWD,
  560. envP, // const char * env[] If passed as NULL, the child process inherits the parent.s environment at the time of the call.
  561. @Wiring, // wiring_t *wiring, Pass NULL to inherit system defaults for wiring.
  562. nil, // struct fd_set *fds, Not currently implemented. Pass in NULL.
  563. nil, // void *appdata, Not currently implemented. Pass in NULL.
  564. 0, // size_t appdata_size, Not currently implemented. Pass in 0
  565. nil, // void *reserved, Reserved. Pass NULL.
  566. @args); // const char *argv[]
  567. if i <> -1 then
  568. begin
  569. Fpwaitpid(i,@wstat,0);
  570. result := wstat;
  571. end else
  572. begin
  573. e:=EOSError.CreateFmt(SExecuteProcessFailed,[arg0,___errno^]);
  574. e.ErrorCode:=___errno^;
  575. raise e;
  576. end;
  577. end;
  578. procedure Sleep(milliseconds: Cardinal);
  579. begin
  580. libc._delay (milliseconds);
  581. end;
  582. {****************************************************************************
  583. Initialization code
  584. ****************************************************************************}
  585. Initialization
  586. InitExceptions; { Initialize exceptions. OS independent }
  587. InitInternational; { Initialize internationalization settings }
  588. Finalization
  589. DoneExceptions;
  590. end.