dos.pp 16 KB

123456789101112131415161718192021222324252627282930313233343536373839404142434445464748495051525354555657585960616263646566676869707172737475767778798081828384858687888990919293949596979899100101102103104105106107108109110111112113114115116117118119120121122123124125126127128129130131132133134135136137138139140141142143144145146147148149150151152153154155156157158159160161162163164165166167168169170171172173174175176177178179180181182183184185186187188189190191192193194195196197198199200201202203204205206207208209210211212213214215216217218219220221222223224225226227228229230231232233234235236237238239240241242243244245246247248249250251252253254255256257258259260261262263264265266267268269270271272273274275276277278279280281282283284285286287288289290291292293294295296297298299300301302303304305306307308309310311312313314315316317318319320321322323324325326327328329330331332333334335336337338339340341342343344345346347348349350351352353354355356357358359360361362363364365366367368369370371372373374375376377378379380381382383384385386387388389390391392393394395396397398399400401402403404405406407408409410411412413414415416417418419420421422423424425426427428429430431432433434435436437438439440441442443444445446447448449450451452453454455456457458459460461462463464465466467468469470471472473474475476477478479480481482483484485486487488489490491492493494495496497498499500501502503504505506507508509510511512513514515516517518519520521522523524525526527528529530531532533534535536537538539540541542543544545546547548549550551552553554555556557558559560561562563564565566567568569570571572573574575576577578579580581582583584585586587588589590591592593594595596597598599600601602603604605606607608609610611612613614615616617618619620621622623624625626627628629630631632633634635636637638639640641642643644645646647648649650651652653654655
  1. {
  2. $Id$
  3. This unit mimics the DOS unit for Win32
  4. This file is part of the Free Pascal run time library.
  5. Copyright (c) 1998 by the Free Pascal development team.
  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. {$I os.inc}
  13. unit dos;
  14. interface
  15. uses
  16. strings;
  17. const
  18. { bit masks for file attributes }
  19. readonly = $01;
  20. hidden = $02;
  21. sysfile = $04;
  22. volumeid = $08;
  23. directory = $10;
  24. archive = $20;
  25. anyfile = $3F;
  26. fmclosed = $D7B0;
  27. fminput = $D7B1;
  28. fmoutput = $D7B2;
  29. fminout = $D7B3;
  30. type
  31. { some string types }
  32. comstr = string; { command line string }
  33. pathstr = string; { string for a file path }
  34. dirstr = string; { string for a directory }
  35. namestr = string; { string for a file name }
  36. extstr = string; { string for an extension }
  37. { search record which is used by findfirst and findnext }
  38. { it is compatible with the DOS version }
  39. { if the fields are access using there names }
  40. { the fields have another order }
  41. {$PACKRECORDS 1}
  42. searchrec = record
  43. time : longint;
  44. size : longint;
  45. attr : longint;
  46. name : string;
  47. end;
  48. {$PACKRECORDS 2}
  49. { file record for untyped files comes from filerec.inc}
  50. {$i filerec.inc}
  51. { file record for text files comes from textrec.inc}
  52. {$i textrec.inc}
  53. {$PACKRECORDS 1}
  54. { record for date and time }
  55. datetime = record
  56. year,month,day,hour,min,sec : word;
  57. end;
  58. var
  59. { error variable }
  60. doserror : longint;
  61. procedure getdate(var year,month,day,dayofweek : word);
  62. procedure gettime(var hour,minute,second,sec100 : word);
  63. function dosversion : word;
  64. procedure setdate(year,month,day : word);
  65. procedure settime(hour,minute,second,sec100 : word);
  66. // procedure getcbreak(var breakvalue : boolean);
  67. // procedure setcbreak(breakvalue : boolean);
  68. // procedure getverify(var verify : boolean);
  69. // procedure setverify(verify : boolean);
  70. // function diskfree(drive : byte) : longint;
  71. // function disksize(drive : byte) : longint;
  72. procedure findfirst(const path : pathstr;attr : word;var f : searchRec);
  73. procedure findnext(var f : searchRec);
  74. { is a dummy in win32 }
  75. procedure swapvectors;
  76. { not supported:
  77. procedure getintvec(intno : byte;var vector : pointer);
  78. procedure setintvec(intno : byte;vector : pointer);
  79. procedure keep(exitcode : word);
  80. procedure msdos(var regs : registers);
  81. procedure intr(intno : byte;var regs : registers);
  82. }
  83. procedure getfattr(var f;var attr : word);
  84. procedure setfattr(var f;attr : word);
  85. function fsearch(const path : pathstr;dirlist : string) : pathstr;
  86. procedure getftime(var f;var time : longint);
  87. // procedure setftime(var f;time : longint);
  88. procedure packtime (var d: datetime; var time: longint);
  89. procedure unpacktime (time: longint; var d: datetime);
  90. function fexpand(const path : pathstr) : pathstr;
  91. procedure fsplit(path : pathstr;var dir : dirstr;var name : namestr;
  92. var ext : extstr);
  93. // procedure exec(const path : pathstr;const comline : comstr);
  94. function dosexitcode : word;
  95. function envcount : longint;
  96. function envstr(index : longint) : string;
  97. function getenv(const envvar : string): string;
  98. implementation
  99. {$I win32.inc}
  100. { taken from the DOS version }
  101. function fsearch(const path : pathstr;dirlist : string) : pathstr;
  102. var
  103. newdir : pathstr;
  104. i,p1 : byte;
  105. s : searchrec;
  106. begin
  107. if (pos('?',path)<>0) or (pos('*',path)<>0) then
  108. { No wildcards allowed in these things }
  109. fsearch:=''
  110. else
  111. begin
  112. { allow slash as backslash }
  113. for i:=1 to length(dirlist) do
  114. if dirlist[i]='/' then dirlist[i]:='\';
  115. repeat
  116. { get first path }
  117. p1:=pos(';',dirlist);
  118. if p1>0 then
  119. begin
  120. newdir:=copy(dirlist,1,p1-1);
  121. delete(dirlist,1,p1)
  122. end
  123. else
  124. begin
  125. newdir:=dirlist;
  126. dirlist:=''
  127. end;
  128. if (newdir[length(newdir)]<>'\') and
  129. (newdir[length(newdir)]<>':') then
  130. newdir:=newdir+'\';
  131. findfirst(newdir+path,anyfile,s);
  132. if doserror=0 then
  133. begin
  134. { this should be newdir:=newdir+path
  135. because path can contain a path part !! }
  136. {newdir:=newdir+s.name;}
  137. newdir:=newdir+path;
  138. { this was for LINUX:
  139. if pos('.\',newdir)=1 then
  140. delete(newdir, 1, 2)
  141. DOS strips off an initial .\
  142. }
  143. end
  144. else newdir:='';
  145. until(dirlist='') or (length(newdir)>0);
  146. fsearch:=newdir;
  147. end;
  148. end;
  149. procedure getftime(var f;var time : longint);
  150. type
  151. lr = record
  152. lo,hi : word;
  153. end;
  154. var
  155. dostime : longint;
  156. ft,lft : FILETIME;
  157. begin
  158. if GetFileTime(filerec(f).handle,nil,nil,@ft) and
  159. FileTimeToLocalFileTime(ft,lft) and
  160. FileTimeToDosDateTime(lft,lr(time).hi,lr(time).lo) then
  161. exit
  162. else
  163. time:=0;
  164. end;
  165. procedure setftime(var f;time : longint);
  166. begin
  167. {!!!!}
  168. end;
  169. var
  170. lastdosexitcode : word;
  171. procedure exec(const path : pathstr;const comline : comstr);
  172. procedure do_system(p : pchar);
  173. begin
  174. {!!!!!}
  175. end;
  176. var
  177. i : longint;
  178. execute : string;
  179. b : array[0..255] of char;
  180. begin
  181. doserror:=0;
  182. execute:=path+' '+comline;
  183. { allow slash as backslash for the program name only }
  184. for i:=1 to length(path) do
  185. if execute[i]='/' then execute[i]:='\';
  186. move(execute[1],b,length(execute));
  187. b[length(execute)]:=#0;
  188. do_system(b);
  189. end;
  190. function dosexitcode : word;
  191. begin
  192. dosexitcode:=lastdosexitcode;
  193. end;
  194. function dosversion : word;
  195. begin
  196. dosversion:=lo(GetVersion);
  197. end;
  198. procedure getdate(var year,month,day,dayofweek : word);
  199. var
  200. t : SYSTEMTIME;
  201. begin
  202. GetLocalTime(t);
  203. year:=t.wYear;
  204. month:=t.wMonth;
  205. day:=t.wDay;
  206. dayofweek:=t.wDayOfWeek;
  207. end;
  208. procedure setdate(year,month,day : word);
  209. var
  210. t : SYSTEMTIME;
  211. begin
  212. { we need the time set privilege }
  213. { so this function crash currently }
  214. {!!!!!}
  215. GetLocalTime(t);
  216. t.wYear:=year;
  217. t.wMonth:=month;
  218. t.wDay:=day;
  219. { only a quite good solution, we can loose some ms }
  220. SetLocalTime(t);
  221. end;
  222. procedure gettime(var hour,minute,second,sec100 : word);
  223. var
  224. t : SYSTEMTIME;
  225. begin
  226. GetLocalTime(t);
  227. hour:=t.wHour;
  228. minute:=t.wMinute;
  229. second:=t.wSecond;
  230. sec100:=t.wMilliSeconds div 10;
  231. end;
  232. procedure settime(hour,minute,second,sec100 : word);
  233. var
  234. t : SYSTEMTIME;
  235. begin
  236. { we need the time set privilege }
  237. { so this function crash currently }
  238. {!!!!!}
  239. GetLocalTime(t);
  240. t.wHour:=hour;
  241. t.wMinute:=minute;
  242. t.wSecond:=second;
  243. t.wMilliSeconds:=sec100*10;
  244. SetLocalTime(t);
  245. end;
  246. procedure getcbreak(var breakvalue : boolean);
  247. begin
  248. {!!!!}
  249. end;
  250. procedure setcbreak(breakvalue : boolean);
  251. begin
  252. {!!!!}
  253. end;
  254. procedure getverify(var verify : boolean);
  255. begin
  256. {!!!!}
  257. end;
  258. procedure setverify(verify : boolean);
  259. begin
  260. {!!!!}
  261. end;
  262. function diskfree(drive : byte) : longint;
  263. begin
  264. {!!!!}
  265. end;
  266. function disksize(drive : byte) : longint;
  267. begin
  268. {!!!!}
  269. end;
  270. procedure searchrec2dossearchrec(var f : searchrec);
  271. var
  272. l,i : longint;
  273. begin
  274. l:=length(f.name);
  275. for i:=1 to 12 do
  276. f.name[i-1]:=f.name[i];
  277. f.name[l]:=#0;
  278. end;
  279. procedure dossearchrec2searchrec(var f : searchrec);
  280. var
  281. l,i : longint;
  282. begin
  283. l:=12;
  284. for i:=0 to 12 do
  285. if f.name[i]=#0 then
  286. begin
  287. l:=i;
  288. break;
  289. end;
  290. for i:=11 downto 0 do
  291. f.name[i+1]:=f.name[i];
  292. f.name[0]:=chr(l);
  293. end;
  294. procedure findfirst(const path : pathstr;attr : word;var f : searchRec);
  295. procedure _findfirst(path : pchar;attr : word;var f : searchrec);
  296. var
  297. i : longint;
  298. begin
  299. { allow slash as backslash }
  300. for i:=0 to strlen(path) do
  301. if path[i]='/' then path[i]:='\';
  302. {!!!!!!!}
  303. end;
  304. var
  305. path0 : array[0..80] of char;
  306. begin
  307. { no error }
  308. doserror:=0;
  309. strpcopy(path0,path);
  310. _findfirst(path0,attr,f);
  311. dossearchrec2searchrec(f);
  312. end;
  313. procedure findnext(var f : searchRec);
  314. procedure _findnext(var f : searchrec);
  315. begin
  316. {!!!!}
  317. end;
  318. begin
  319. { no error }
  320. doserror:=0;
  321. searchrec2dossearchrec(f);
  322. _findnext(f);
  323. dossearchrec2searchrec(f);
  324. end;
  325. procedure swapvectors;
  326. begin
  327. { only a dummy }
  328. end;
  329. { the environment is a block of zero terminated strings }
  330. { terminated by a #0 }
  331. function envcount : longint;
  332. var
  333. hp,p : pchar;
  334. begin
  335. p:=GetEnvironmentStrings;
  336. hp:=p;
  337. envcount:=0;
  338. while hp^<>#0 do
  339. begin
  340. { next string entry}
  341. hp:=hp+strlen(hp)+1;
  342. inc(envcount);
  343. end;
  344. FreeEnvironmentStrings(p);
  345. end;
  346. function envstr(index : longint) : string;
  347. var
  348. hp,p : pchar;
  349. count,i : longint;
  350. begin
  351. { envcount takes some time in win32 }
  352. count:=envcount;
  353. { range checking }
  354. if (index<=0) or (index>count) then
  355. begin
  356. envstr:='';
  357. exit;
  358. end;
  359. p:=GetEnvironmentStrings;
  360. hp:=p;
  361. { retrive the string with the given index }
  362. for i:=2 to index do
  363. hp:=hp+strlen(hp)+1;
  364. envstr:=strpas(hp);
  365. FreeEnvironmentStrings(p);
  366. end;
  367. function getenv(const envvar : string) : string;
  368. var
  369. s : string;
  370. i : longint;
  371. hp,p : pchar;
  372. begin
  373. getenv:='';
  374. p:=GetEnvironmentStrings;
  375. hp:=p;
  376. while hp^<>#0 do
  377. begin
  378. s:=strpas(hp);
  379. i:=pos('=',s);
  380. if copy(s,1,i-1)=envvar then
  381. begin
  382. getenv:=copy(s,i+1,length(s)-i);
  383. break;
  384. end;
  385. { next string entry}
  386. hp:=hp+strlen(hp)+1;
  387. end;
  388. FreeEnvironmentStrings(p);
  389. end;
  390. procedure fsplit(path : pathstr;var dir : dirstr;var name : namestr;
  391. var ext : extstr);
  392. var
  393. p1 : byte;
  394. i : longint;
  395. begin
  396. { allow slash as backslash }
  397. for i:=1 to length(path) do
  398. if path[i]='/' then path[i]:='\';
  399. { get drive name }
  400. p1:=pos(':',path);
  401. if p1>0 then
  402. begin
  403. dir:=path[1]+':';
  404. delete(path,1,p1);
  405. end
  406. else
  407. dir:='';
  408. { split the path and the name, there are no more path informtions }
  409. { if path contains no backslashes }
  410. while true do
  411. begin
  412. p1:=pos('\',path);
  413. if p1=0 then
  414. break;
  415. dir:=dir+copy(path,1,p1);
  416. delete(path,1,p1);
  417. end;
  418. { try to find out a extension }
  419. p1:=pos('.',path);
  420. if p1>0 then
  421. begin
  422. ext:=copy(path,p1,4);
  423. delete(path,p1,length(path)-p1+1);
  424. end
  425. else
  426. ext:='';
  427. name:=path;
  428. end;
  429. function fexpand(const path : pathstr) : pathstr;
  430. var
  431. s,pa : string[79];
  432. i,j : byte;
  433. begin
  434. { There are differences between Free Pascal and Turbo Pascal
  435. e.g. for the string 'D:\DEMO\..\HELLO' which isn't handled }
  436. getdir(0,s);
  437. pa:=upcase(path);
  438. { allow slash as backslash }
  439. for i:=1 to length(pa) do
  440. if pa[i]='/' then pa[i]:='\';
  441. if (ord(pa[0])>1) and (((pa[1]>='A') and (pa[1]<='Z')) and (pa[2]=':')) then
  442. begin
  443. { we must get the right directory }
  444. getdir(ord(pa[1])-ord('A')+1,s);
  445. if (ord(pa[0])>2) and (pa[3]<>'\') then
  446. if pa[1]=s[1] then
  447. pa:=s+'\'+copy (pa,3,length(pa))
  448. else
  449. pa:=pa[1]+':\'+copy (pa,3,length(pa))
  450. end
  451. else
  452. if pa[1]='\' then
  453. pa:=s[1]+':'+pa
  454. else if s[0]=#3 then
  455. pa:=s+pa
  456. else
  457. pa:=s+'\'+pa;
  458. {First remove all references to '\.\'}
  459. while pos ('\.\',pa)<>0 do
  460. delete (pa,pos('\.\',pa),2);
  461. {Now remove also all references to '\..\' + of course previous dirs..}
  462. repeat
  463. i:=pos('\..\',pa);
  464. j:=i-1;
  465. while (j>1) and (pa[j]<>'\') do
  466. dec (j);
  467. delete (pa,j,i-j+3);
  468. until i=0;
  469. {Remove End . and \}
  470. if (length(pa)>0) and (pa[length(pa)]='.') then
  471. dec(byte(pa[0]));
  472. if (length(pa)>0) and (pa[length(pa)]='\') then
  473. dec(byte(pa[0]));
  474. fexpand:=pa;
  475. end;
  476. procedure packtime(var d : datetime;var time : longint);
  477. var
  478. zs : longint;
  479. begin
  480. time:=-1980;
  481. time:=time+d.year and 127;
  482. time:=time shl 4;
  483. time:=time+d.month;
  484. time:=time shl 5;
  485. time:=time+d.day;
  486. time:=time shl 16;
  487. zs:=d.hour;
  488. zs:=zs shl 6;
  489. zs:=zs+d.min;
  490. zs:=zs shl 5;
  491. zs:=zs+d.sec div 2;
  492. time:=time+(zs and $ffff);
  493. end;
  494. procedure unpacktime (time: longint;var d : datetime);
  495. begin
  496. d.sec:=(time and 31) * 2;
  497. time:=time shr 5;
  498. d.min:=time and 63;
  499. time:=time shr 6;
  500. d.hour:=time and 31;
  501. time:=time shr 5;
  502. d.day:=time and 31;
  503. time:=time shr 5;
  504. d.month:=time and 15;
  505. time:=time shr 4;
  506. d.year:=time + 1980;
  507. end;
  508. procedure getfattr(var f;var attr : word);
  509. var
  510. l : longint;
  511. begin
  512. l:=GetFileAttributes(filerec(f).name);
  513. if l=$ffffffff then
  514. doserror:=getlasterror;
  515. attr:=l;
  516. end;
  517. procedure setfattr(var f;attr : word);
  518. begin
  519. doserror:=0;
  520. if not(SetFileAttributes(filerec(f).name,attr)) then
  521. doserror:=getlasterror;
  522. end;
  523. end.
  524. {
  525. $Log$
  526. Revision 1.5 1998-05-06 12:36:50 michael
  527. + Removed log from before restored version.
  528. Revision 1.4 1998/04/27 14:01:38 florian
  529. * was uncompilable
  530. Revision 1.3 1998/04/26 22:37:02 florian
  531. + getftime, unpacktime, packtime
  532. Revision 1.2 1998/04/26 21:49:09 florian
  533. + first compiling and working version
  534. Revision 1.1.1.1 1998/03/25 11:18:47 root
  535. * Restored version
  536. }