sstrings.inc 13 KB

123456789101112131415161718192021222324252627282930313233343536373839404142434445464748495051525354555657585960616263646566676869707172737475767778798081828384858687888990919293949596979899100101102103104105106107108109110111112113114115116117118119120121122123124125126127128129130131132133134135136137138139140141142143144145146147148149150151152153154155156157158159160161162163164165166167168169170171172173174175176177178179180181182183184185186187188189190191192193194195196197198199200201202203204205206207208209210211212213214215216217218219220221222223224225226227228229230231232233234235236237238239240241242243244245246247248249250251252253254255256257258259260261262263264265266267268269270271272273274275276277278279280281282283284285286287288289290291292293294295296297298299300301302303304305306307308309310311312313314315316317318319320321322323324325326327328329330331332333334335336337338339340341342343344345346347348349350351352353354355356357358359360361362363364365366367368369370371372373374375376377378379380381382383384385386387388389390391392393394395396397398399400401402403404405406407408409410411412413414415416417418419420421422423424425426427428429430431432433434435436437438439440441442443444445446447448449450451452453454455456457458459460461462463464465466467468469470471472473474475476477478479480481482483484485486487488489490491492493494495496497498499500501502503504505506507508509510511512513514515516517518519520521522523524525526527528529530531532533534535536537538539540541542543544545546547548549550551552553554555556557558559560561562563564565566567568569570571572573574575576577578579580581582583584585586587588589590591592593594595596597598599600601602603604605606607608609610611612613614615616617618619620621622623624625626627628629630631632633634635636637638639640641642643644645646647648649650651652653654655656657658659660661662663664665666667668669670671672673674675676677678679680681682683684685686687688689690691692693694695696697698699700701702703704705706707708709710711712713714715716717718719720721722723724725
  1. {
  2. $Id$
  3. This file is part of the Free Pascal run time library.
  4. Copyright (c) 1993,97 by the Free Pascal development team
  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. {****************************************************************************
  12. subroutines for string handling
  13. ****************************************************************************}
  14. {$I real2str.inc}
  15. function copy(const s : string;index : integer;count : integer): string;
  16. begin
  17. if count<0 then
  18. count:=0;
  19. if index>1 then
  20. dec(index)
  21. else
  22. index:=0;
  23. if index>length(s) then
  24. count:=0
  25. else
  26. if index+count>length(s) then
  27. count:=length(s)-index;
  28. Copy[0]:=chr(Count);
  29. Move(s[Index+1],Copy[1],Count);
  30. end;
  31. procedure delete(var s : string;index : integer;count : integer);
  32. begin
  33. if index<=0 then
  34. begin
  35. count:=count+index-1;
  36. index:=1;
  37. end;
  38. if (Index<=Length(s)) and (Count>0) then
  39. begin
  40. if Count+Index>length(s) then
  41. Count:=length(s)-Index+1;
  42. s[0]:=Chr(length(s)-Count);
  43. if Index<=Length(s) then
  44. Move(s[Index+Count],s[Index],Length(s)-Index+1);
  45. end;
  46. end;
  47. procedure insert(const source : string;var s : string;index : integer);
  48. begin
  49. if index>1 then
  50. dec(index)
  51. else
  52. index:=0;
  53. s:=Copy(s,1,Index)+source+Copy(s,Index+1,length(s));
  54. end;
  55. function pos(const substr : string;const s : string): byte;
  56. var i,j : longint;
  57. e : boolean;
  58. begin
  59. i := 0;
  60. j := 0;
  61. e:=(length(SubStr)>0);
  62. while e and (i<=Length(s)-Length(SubStr)) do
  63. begin
  64. inc(i);
  65. if (SubStr[1]=s[i]) and (Substr=Copy(s,i,Length(SubStr))) then
  66. begin
  67. j:=i;
  68. e:=false;
  69. end;
  70. end;
  71. Pos:=j;
  72. end;
  73. {Faster when looking for a single char...}
  74. function pos(c:char;const s:string):byte;
  75. var i:longint;
  76. begin
  77. for i:=1 to length(s) do
  78. if s[i]=c then
  79. begin
  80. pos:=i;
  81. exit;
  82. end;
  83. pos:=0;
  84. end;
  85. {$ifdef IBM_CHAR_SET}
  86. const
  87. UpCaseTbl : string[7]=#154#142#153#144#128#143#165;
  88. LoCaseTbl : string[7]=#129#132#148#130#135#134#164;
  89. {$endif}
  90. function upcase(c : char) : char;
  91. {$IFDEF IBM_CHAR_SET}
  92. var
  93. i : longint;
  94. {$ENDIF}
  95. begin
  96. if (c in ['a'..'z']) then
  97. upcase:=char(byte(c)-32)
  98. else
  99. {$IFDEF IBM_CHAR_SET}
  100. begin
  101. i:=Pos(c,LoCaseTbl);
  102. if i>0 then
  103. upcase:=UpCaseTbl[i]
  104. else
  105. upcase:=c;
  106. end;
  107. {$ELSE}
  108. upcase:=c;
  109. {$ENDIF}
  110. end;
  111. function upcase(const s : string) : string;
  112. var i : longint;
  113. begin
  114. upcase[0]:=s[0];
  115. for i := 1 to length (s) do
  116. upcase[i] := upcase (s[i]);
  117. end;
  118. function lowercase(c : char) : char;
  119. {$IFDEF IBM_CHAR_SET}
  120. var
  121. i : longint;
  122. {$ENDIF}
  123. begin
  124. if (c in ['A'..'Z']) then
  125. lowercase:=char(byte(c)+32)
  126. else
  127. {$IFDEF IBM_CHAR_SET}
  128. begin
  129. i:=Pos(c,UpCaseTbl);
  130. if i>0 then
  131. lowercase:=LoCaseTbl[i]
  132. else
  133. lowercase:=c;
  134. end;
  135. {$ELSE}
  136. lowercase:=c;
  137. {$ENDIF}
  138. end;
  139. function lowercase(const s : string) : string;
  140. var i : longint;
  141. begin
  142. lowercase [0] := s[0];
  143. for i := 1 to length (s) do
  144. lowercase[i] := lowercase (s[i]);
  145. end;
  146. function space (b : byte): string;
  147. begin
  148. space[0] := chr(b);
  149. FillChar (Space[1],b,' ');
  150. end;
  151. function hexstr(val : longint;cnt : byte) : string;
  152. const
  153. HexTbl : array[0..15] of char='0123456789ABCDEF';
  154. var
  155. i : longint;
  156. begin
  157. hexstr[0]:=char(cnt);
  158. for i:=cnt downto 1 do
  159. begin
  160. hexstr[i]:=hextbl[val and $f];
  161. val:=val shr 4;
  162. end;
  163. end;
  164. function binstr(val : longint;cnt : byte) : string;
  165. var
  166. i : longint;
  167. begin
  168. binstr[0]:=char(cnt);
  169. for i:=cnt downto 1 do
  170. begin
  171. binstr[i]:=char(48+val and 1);
  172. val:=val shr 1;
  173. end;
  174. end;
  175. {*****************************************************************************
  176. Str() Helpers
  177. *****************************************************************************}
  178. procedure int_str_real(d : real;len,fr : longint;var s : string);[public, alias : 'STR_REAL'];
  179. begin
  180. {$ifdef i386}
  181. str_real(len,fr,d,rt_s64real,s);
  182. {$else}
  183. str_real(len,fr,d,rt_s32real,s);
  184. {$endif}
  185. end;
  186. procedure int_str_single(d : single;len,fr : longint;var s : string);[public, alias : 'STR_SINGLE'];
  187. begin
  188. str_real(len,fr,d,rt_s32real,s);
  189. end;
  190. {$ifdef SUPPORT_EXTENDED}
  191. procedure int_str_extended(d : extended;len,fr : longint;var s : string);[public, alias : 'STR_EXTENDED'];
  192. begin
  193. str_real(len,fr,d,rt_s80real,s);
  194. end;
  195. {$endif SUPPORT_EXTENDED}
  196. {$ifdef SUPPORT_COMP}
  197. procedure int_str_comp(d : comp;len,fr : longint;var s : string);[public, alias : 'STR_COMP'];
  198. begin
  199. str_real(len,fr,d,rt_s64bit,s);
  200. end;
  201. {$endif SUPPORT_COMP}
  202. procedure int_str_fixed(d : fixed;len,fr : longint;var s : string);[public, alias : 'STR_FIXED'];
  203. begin
  204. str_real(len,fr,d,rt_f32bit,s);
  205. end;
  206. procedure int_str_longint(v : longint;len : longint;var s : string);[public, alias : 'STR_LONGINT'];
  207. begin
  208. int_str(v,s);
  209. if length(s)<len then
  210. s:=space(len-length(s))+s;
  211. end;
  212. procedure int_str_cardinal(v : cardinal;len : longint;var s : string);[public, alias : 'STR_CARDINAL'];
  213. begin
  214. int_str(v,s);
  215. if length(s)<len then
  216. s:=space(len-length(s))+s;
  217. end;
  218. {*****************************************************************************
  219. Val() Functions
  220. *****************************************************************************}
  221. Function InitVal(const s:string;var negativ:boolean;var base:byte):Word;
  222. var
  223. Code : Longint;
  224. begin
  225. {Skip Spaces and Tab}
  226. code:=1;
  227. while (code<=length(s)) and (s[code] in [' ',#9]) do
  228. inc(code);
  229. {Sign}
  230. negativ:=false;
  231. case s[code] of
  232. '-' : begin
  233. negativ:=true;
  234. inc(code);
  235. end;
  236. '+' : inc(code);
  237. end;
  238. {Base}
  239. base:=10;
  240. if code<=length(s) then
  241. begin
  242. case s[code] of
  243. '$' : begin
  244. base:=16;
  245. repeat
  246. inc(code);
  247. until (code>=length(s)) or (s[code]<>'0');
  248. if length(s)-code>7 then
  249. inc(code,8);
  250. end;
  251. '%' : begin
  252. base:=2;
  253. inc(code);
  254. end;
  255. end;
  256. end;
  257. InitVal:=code;
  258. end;
  259. procedure val(const s : string;var l : longint;var code : word);
  260. var
  261. base,u : byte;
  262. negativ : boolean;
  263. begin
  264. l:=0;
  265. Code:=InitVal(s,negativ,base);
  266. if Code>length(s) then
  267. exit;
  268. if negativ and (s='-2147483648') then
  269. begin
  270. Code:=0;
  271. l:=$80000000;
  272. exit;
  273. end;
  274. while Code<=Length(s) do
  275. begin
  276. u:=ord(s[code]);
  277. case u of
  278. 48..57 : dec(u,48);
  279. 65..70 : dec(u,55);
  280. 97..104 : dec(u,87);
  281. else
  282. u:=16;
  283. end;
  284. l:=l*longint(base);
  285. if (u>=base) or ((base=10) and (2147483647-l<longint(u))) then
  286. begin
  287. l:=0;
  288. exit;
  289. end;
  290. inc(l,u);
  291. inc(code);
  292. end;
  293. code := 0;
  294. if negativ then
  295. l:=0-l;
  296. end;
  297. procedure val(const s : string;var l : longint;var code : integer);
  298. begin
  299. val(s,l,word(code));
  300. end;
  301. procedure val(const s : string;var l : longint);
  302. var
  303. code : word;
  304. begin
  305. val (s,l,code);
  306. end;
  307. procedure val(const s : string;var b : byte);
  308. var
  309. l : longint;
  310. begin
  311. val(s,l);
  312. b:=l;
  313. end;
  314. procedure val(const s : string;var b : byte;var code : word);
  315. var
  316. l : longint;
  317. begin
  318. val(s,l,code);
  319. b:=l;
  320. end;
  321. procedure val(const s : string;var b : byte;var code : Integer);
  322. begin
  323. val(s,b,word(code));
  324. end;
  325. procedure val(const s : string;var b : shortint);
  326. var
  327. l : longint;
  328. begin
  329. val(s,l);
  330. b:=l;
  331. end;
  332. procedure val(const s : string;var b : shortint;var code : word);
  333. var
  334. l : longint;
  335. begin
  336. val(s,l,code);
  337. b:=l;
  338. end;
  339. procedure val(const s : string;var b : shortint;var code : Integer);
  340. begin
  341. val(s,b,word(code));
  342. end;
  343. procedure val(const s : string;var b : word);
  344. var
  345. l : longint;
  346. begin
  347. val(s,l);
  348. b:=l;
  349. end;
  350. procedure val(const s : string;var b : word;var code : word);
  351. var
  352. l : longint;
  353. begin
  354. val(s,l,code);
  355. b:=l;
  356. end;
  357. procedure val(const s : string;var b : word;var code : Integer);
  358. begin
  359. val(s,b,word(code));
  360. end;
  361. procedure val(const s : string;var b : integer);
  362. var
  363. l : longint;
  364. begin
  365. val(s,l);
  366. b:=l;
  367. end;
  368. procedure val(const s : string;var b : integer;var code : word);
  369. var
  370. l : longint;
  371. begin
  372. val(s,l,code);
  373. b:=l;
  374. end;
  375. procedure val(const s : string;var b : integer;var code : Integer);
  376. begin
  377. val(s,b,word(code));
  378. end;
  379. procedure val(const s : string;var d : real;var code : word);
  380. var
  381. hd,
  382. esign,sign : real;
  383. exponent,i : longint;
  384. flags : byte;
  385. begin
  386. d:=0;
  387. code:=1;
  388. exponent:=0;
  389. esign:=1;
  390. flags:=0;
  391. sign:=1;
  392. while (code<=length(s)) and (s[code] in [' ',#9]) do
  393. inc(code);
  394. case s[code] of
  395. '+' : inc(code);
  396. '-' : begin
  397. sign:=-1.0;
  398. inc(code);
  399. end;
  400. end;
  401. while (Code<=Length(s)) and (s[code] in ['0'..'9']) do
  402. begin
  403. { Read integer part }
  404. flags:=flags or 1;
  405. d:=d*10;
  406. d:=d+(ord(s[code])-ord('0'));
  407. inc(code);
  408. end;
  409. { Decimal ? }
  410. if (s[code]='.') and (length(s)>=code) then
  411. begin
  412. hd:=0.1;
  413. inc(code);
  414. { After dot, a number is required. }
  415. if not(s[code] in ['0'..'9']) or (length(s)<code) then
  416. begin
  417. d:=0.0;
  418. exit;
  419. end;
  420. while (s[code] in ['0'..'9']) and (length(s)>=code) do
  421. begin
  422. { Read fractional part. }
  423. flags:=flags or 2;
  424. d:=d+hd*(ord(s[code])-ord('0'));
  425. hd:=hd/10.0;
  426. inc(code);
  427. end;
  428. end;
  429. { Again, read integer and fractional part}
  430. if flags=0 then
  431. begin
  432. d:=0.0;
  433. exit;
  434. end;
  435. { Exponent ? }
  436. if (upcase(s[code])='E') and (length(s)>=code) then
  437. begin
  438. inc(code);
  439. if s[code]='+' then
  440. inc(code)
  441. else
  442. if s[code]='-' then
  443. begin
  444. esign:=-1;
  445. inc(code);
  446. end;
  447. if not(s[code] in ['0'..'9']) or (length(s)<code) then
  448. begin
  449. d:=0.0;
  450. exit;
  451. end;
  452. while (s[code] in ['0'..'9']) and (length(s)>=code) do
  453. begin
  454. exponent:=exponent*10;
  455. exponent:=exponent+ord(s[code])-ord('0');
  456. inc(code);
  457. end;
  458. end;
  459. { Calculate Exponent }
  460. if esign>0 then
  461. for i:=1 to exponent do
  462. d:=d*10
  463. else
  464. for i:=1 to exponent do
  465. d:=d/10;
  466. { Not all characters are read ? }
  467. if length(s)>=code then
  468. begin
  469. d:=0.0;
  470. exit;
  471. end;
  472. { evalute sign }
  473. d:=d*sign;
  474. { success ! }
  475. code:=0;
  476. end;
  477. procedure val(const s : string;var d : real;var code : integer);
  478. begin
  479. val(s,d,word(code));
  480. end;
  481. procedure val(const s : string;var d : real);
  482. var
  483. code : word;
  484. begin
  485. val(s,d,code);
  486. end;
  487. procedure val(const s : string;var d : single;var code : word);
  488. var
  489. e : double;
  490. begin
  491. val(s,e,code);
  492. d:=e;
  493. end;
  494. procedure val(const s : string;var d : single;var code : integer);
  495. var
  496. e : double;
  497. begin
  498. val(s,e,word(code));
  499. d:=e;
  500. end;
  501. procedure val(const s : string;var d : single);
  502. var
  503. code : word;
  504. e : double;
  505. begin
  506. val(s,e,code);
  507. d:=e;
  508. end;
  509. {$ifdef SUPPORT_EXTENDED}
  510. procedure val(const s : string;var d : extended;var code : word);
  511. var
  512. e : double;
  513. begin
  514. val(s,e,code);
  515. d:=e;
  516. end;
  517. procedure val(const s : string;var d : extended;var code : integer);
  518. var
  519. e : double;
  520. begin
  521. val(s,e,word(code));
  522. d:=e;
  523. end;
  524. procedure val(const s : string;var d : extended);
  525. var
  526. code : word;
  527. e : double;
  528. begin
  529. val(s,e,code);
  530. d:=e;
  531. end;
  532. {$endif SUPPORT_EXTENDED}
  533. {$ifdef SUPPORT_COMP}
  534. procedure val(const s : string;var d : comp;var code : word);
  535. var
  536. e : double;
  537. begin
  538. val(s,e,code);
  539. d:=comp(e);
  540. end;
  541. procedure val(const s : string;var d : comp;var code : integer);
  542. var
  543. e : double;
  544. begin
  545. val(s,e,word(code));
  546. d:=comp(e);
  547. end;
  548. procedure val(const s : string;var d : comp);
  549. var
  550. code : word;
  551. e : double;
  552. begin
  553. val(s,e,code);
  554. d:=comp(e);
  555. end;
  556. {$endif SUPPORT_COMP}
  557. procedure val(const s : string;var v : cardinal;var code : word);
  558. var
  559. negativ : boolean;
  560. base,u : byte;
  561. begin
  562. v:=0;
  563. code:=InitVal(s,negativ,base);
  564. if (Code>length(s)) or negativ then
  565. exit;
  566. while Code<=Length(s) do
  567. begin
  568. u:=ord(s[code]);
  569. case u of
  570. 48..57 : dec(u,48);
  571. 65..70 : dec(u,55);
  572. 97..104 : dec(u,87);
  573. else
  574. u:=16;
  575. end;
  576. cardinal(v):=cardinal(v)*cardinal(longint(base));
  577. if (u>base) or (cardinal($ffffffff)-cardinal(v)>cardinal(longint(u))) then
  578. begin
  579. v:=0;
  580. exit;
  581. end;
  582. inc(v,u);
  583. inc(code);
  584. end;
  585. code:=0;
  586. end;
  587. procedure val(const s : string;var v : cardinal);
  588. var
  589. code : word;
  590. begin
  591. val(s,v,code);
  592. end;
  593. procedure val(const s : string;var v : cardinal;var code : integer);
  594. begin
  595. val(s,v,word(code));
  596. end;
  597. {
  598. $Log$
  599. Revision 1.5 1998-06-04 23:45:59 peter
  600. * comp,extended are only i386 added support_comp,support_extended
  601. Revision 1.4 1998/05/31 14:14:52 peter
  602. * removed warnings using comp()
  603. Revision 1.3 1998/05/12 10:42:45 peter
  604. * moved getopts to inc/, all supported OS's need argc,argv exported
  605. + strpas, strlen are now exported in the systemunit
  606. * removed logs
  607. * removed $ifdef ver_above
  608. }