sstrings.inc 13 KB

123456789101112131415161718192021222324252627282930313233343536373839404142434445464748495051525354555657585960616263646566676869707172737475767778798081828384858687888990919293949596979899100101102103104105106107108109110111112113114115116117118119120121122123124125126127128129130131132133134135136137138139140141142143144145146147148149150151152153154155156157158159160161162163164165166167168169170171172173174175176177178179180181182183184185186187188189190191192193194195196197198199200201202203204205206207208209210211212213214215216217218219220221222223224225226227228229230231232233234235236237238239240241242243244245246247248249250251252253254255256257258259260261262263264265266267268269270271272273274275276277278279280281282283284285286287288289290291292293294295296297298299300301302303304305306307308309310311312313314315316317318319320321322323324325326327328329330331332333334335336337338339340341342343344345346347348349350351352353354355356357358359360361362363364365366367368369370371372373374375376377378379380381382383384385386387388389390391392393394395396397398399400401402403404405406407408409410411412413414415416417418419420421422423424425426427428429430431432433434435436437438439440441442443444445446447448449450451452453454455456457458459460461462463464465466467468469470471472473474475476477478479480481482483484485486487488489490491492493494495496497498499500501502503504505506507508509510511512513514515516517518519520521522523524525526527528529530531532533534535536537538539540541542543544545546547548549550551552553554555556557558559560561562563564565566567568569570571572573574575576577578579580581582583584585586587588589590591592593594595596597598599600601602603604605606607608609610611612613614615616617618619620621622623624625626627628629630631632633634635636637638639640641642643644645646647648649650651652653654655656657658659660661662663664665666667668669670671672673674675676677678679680681682683684685686687688689690691692693694695696697698699700701702703704705706707708709710711712
  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. procedure int_str_extended(d : extended;len,fr : longint;var s : string);[public, alias : 'STR_EXTENDED'];
  191. begin
  192. str_real(len,fr,d,rt_s80real,s);
  193. end;
  194. procedure int_str_comp(d : comp;len,fr : longint;var s : string);[public, alias : 'STR_COMP'];
  195. begin
  196. str_real(len,fr,d,rt_s64bit,s);
  197. end;
  198. procedure int_str_fixed(d : fixed;len,fr : longint;var s : string);[public, alias : 'STR_FIXED'];
  199. begin
  200. str_real(len,fr,d,rt_f32bit,s);
  201. end;
  202. procedure int_str_longint(v : longint;len : longint;var s : string);[public, alias : 'STR_LONGINT'];
  203. begin
  204. int_str(v,s);
  205. if length(s)<len then
  206. s:=space(len-length(s))+s;
  207. end;
  208. procedure int_str_cardinal(v : cardinal;len : longint;var s : string);[public, alias : 'STR_CARDINAL'];
  209. begin
  210. int_str(v,s);
  211. if length(s)<len then
  212. s:=space(len-length(s))+s;
  213. end;
  214. {*****************************************************************************
  215. Val() Functions
  216. *****************************************************************************}
  217. Function InitVal(const s:string;var negativ:boolean;var base:byte):Word;
  218. var
  219. Code : Longint;
  220. begin
  221. {Skip Spaces and Tab}
  222. code:=1;
  223. while (code<=length(s)) and (s[code] in [' ',#9]) do
  224. inc(code);
  225. {Sign}
  226. negativ:=false;
  227. case s[code] of
  228. '-' : begin
  229. negativ:=true;
  230. inc(code);
  231. end;
  232. '+' : inc(code);
  233. end;
  234. {Base}
  235. base:=10;
  236. if code<=length(s) then
  237. begin
  238. case s[code] of
  239. '$' : begin
  240. base:=16;
  241. repeat
  242. inc(code);
  243. until (code>=length(s)) or (s[code]<>'0');
  244. if length(s)-code>7 then
  245. inc(code,8);
  246. end;
  247. '%' : begin
  248. base:=2;
  249. inc(code);
  250. end;
  251. end;
  252. end;
  253. InitVal:=code;
  254. end;
  255. procedure val(const s : string;var l : longint;var code : word);
  256. var
  257. base,u : byte;
  258. negativ : boolean;
  259. begin
  260. l:=0;
  261. Code:=InitVal(s,negativ,base);
  262. if Code>length(s) then
  263. exit;
  264. if negativ and (s='-2147483648') then
  265. begin
  266. Code:=0;
  267. l:=$80000000;
  268. exit;
  269. end;
  270. while Code<=Length(s) do
  271. begin
  272. u:=ord(s[code]);
  273. case u of
  274. 48..57 : dec(u,48);
  275. 65..70 : dec(u,55);
  276. 97..104 : dec(u,87);
  277. else
  278. u:=16;
  279. end;
  280. l:=l*longint(base);
  281. if (u>=base) or ((base=10) and (2147483647-l<longint(u))) then
  282. begin
  283. l:=0;
  284. exit;
  285. end;
  286. inc(l,u);
  287. inc(code);
  288. end;
  289. code := 0;
  290. if negativ then
  291. l:=0-l;
  292. end;
  293. procedure val(const s : string;var l : longint;var code : integer);
  294. begin
  295. val(s,l,word(code));
  296. end;
  297. procedure val(const s : string;var l : longint);
  298. var
  299. code : word;
  300. begin
  301. val (s,l,code);
  302. end;
  303. procedure val(const s : string;var b : byte);
  304. var
  305. l : longint;
  306. begin
  307. val(s,l);
  308. b:=l;
  309. end;
  310. procedure val(const s : string;var b : byte;var code : word);
  311. var
  312. l : longint;
  313. begin
  314. val(s,l,code);
  315. b:=l;
  316. end;
  317. procedure val(const s : string;var b : byte;var code : Integer);
  318. begin
  319. val(s,b,word(code));
  320. end;
  321. procedure val(const s : string;var b : shortint);
  322. var
  323. l : longint;
  324. begin
  325. val(s,l);
  326. b:=l;
  327. end;
  328. procedure val(const s : string;var b : shortint;var code : word);
  329. var
  330. l : longint;
  331. begin
  332. val(s,l,code);
  333. b:=l;
  334. end;
  335. procedure val(const s : string;var b : shortint;var code : Integer);
  336. begin
  337. val(s,b,word(code));
  338. end;
  339. procedure val(const s : string;var b : word);
  340. var
  341. l : longint;
  342. begin
  343. val(s,l);
  344. b:=l;
  345. end;
  346. procedure val(const s : string;var b : word;var code : word);
  347. var
  348. l : longint;
  349. begin
  350. val(s,l,code);
  351. b:=l;
  352. end;
  353. procedure val(const s : string;var b : word;var code : Integer);
  354. begin
  355. val(s,b,word(code));
  356. end;
  357. procedure val(const s : string;var b : integer);
  358. var
  359. l : longint;
  360. begin
  361. val(s,l);
  362. b:=l;
  363. end;
  364. procedure val(const s : string;var b : integer;var code : word);
  365. var
  366. l : longint;
  367. begin
  368. val(s,l,code);
  369. b:=l;
  370. end;
  371. procedure val(const s : string;var b : integer;var code : Integer);
  372. begin
  373. val(s,b,word(code));
  374. end;
  375. procedure val(const s : string;var d : real;var code : word);
  376. var
  377. hd,
  378. esign,sign : real;
  379. exponent,i : longint;
  380. flags : byte;
  381. begin
  382. d:=0;
  383. code:=1;
  384. exponent:=0;
  385. esign:=1;
  386. flags:=0;
  387. sign:=1;
  388. while (code<=length(s)) and (s[code] in [' ',#9]) do
  389. inc(code);
  390. case s[code] of
  391. '+' : inc(code);
  392. '-' : begin
  393. sign:=-1.0;
  394. inc(code);
  395. end;
  396. end;
  397. while (Code<=Length(s)) and (s[code] in ['0'..'9']) do
  398. begin
  399. { Read integer part }
  400. flags:=flags or 1;
  401. d:=d*10;
  402. d:=d+(ord(s[code])-ord('0'));
  403. inc(code);
  404. end;
  405. { Decimal ? }
  406. if (s[code]='.') and (length(s)>=code) then
  407. begin
  408. hd:=0.1;
  409. inc(code);
  410. { After dot, a number is required. }
  411. if not(s[code] in ['0'..'9']) or (length(s)<code) then
  412. begin
  413. d:=0.0;
  414. exit;
  415. end;
  416. while (s[code] in ['0'..'9']) and (length(s)>=code) do
  417. begin
  418. { Read fractional part. }
  419. flags:=flags or 2;
  420. d:=d+hd*(ord(s[code])-ord('0'));
  421. hd:=hd/10.0;
  422. inc(code);
  423. end;
  424. end;
  425. { Again, read integer and fractional part}
  426. if flags=0 then
  427. begin
  428. d:=0.0;
  429. exit;
  430. end;
  431. { Exponent ? }
  432. if (upcase(s[code])='E') and (length(s)>=code) then
  433. begin
  434. inc(code);
  435. if s[code]='+' then
  436. inc(code)
  437. else
  438. if s[code]='-' then
  439. begin
  440. esign:=-1;
  441. inc(code);
  442. end;
  443. if not(s[code] in ['0'..'9']) or (length(s)<code) then
  444. begin
  445. d:=0.0;
  446. exit;
  447. end;
  448. while (s[code] in ['0'..'9']) and (length(s)>=code) do
  449. begin
  450. exponent:=exponent*10;
  451. exponent:=exponent+ord(s[code])-ord('0');
  452. inc(code);
  453. end;
  454. end;
  455. { Calculate Exponent }
  456. if esign>0 then
  457. for i:=1 to exponent do
  458. d:=d*10
  459. else
  460. for i:=1 to exponent do
  461. d:=d/10;
  462. { Not all characters are read ? }
  463. if length(s)>=code then
  464. begin
  465. d:=0.0;
  466. exit;
  467. end;
  468. { evalute sign }
  469. d:=d*sign;
  470. { success ! }
  471. code:=0;
  472. end;
  473. procedure val(const s : string;var d : real;var code : integer);
  474. begin
  475. val(s,d,word(code));
  476. end;
  477. procedure val(const s : string;var d : real);
  478. var
  479. code : word;
  480. begin
  481. val(s,d,code);
  482. end;
  483. procedure val(const s : string;var d : single;var code : word);
  484. var
  485. e : double;
  486. begin
  487. val(s,e,code);
  488. d:=e;
  489. end;
  490. procedure val(const s : string;var d : single;var code : integer);
  491. var
  492. e : double;
  493. begin
  494. val(s,e,word(code));
  495. d:=e;
  496. end;
  497. procedure val(const s : string;var d : single);
  498. var
  499. code : word;
  500. e : double;
  501. begin
  502. val(s,e,code);
  503. d:=e;
  504. end;
  505. procedure val(const s : string;var d : extended;var code : word);
  506. var
  507. e : double;
  508. begin
  509. val(s,e,code);
  510. d:=e;
  511. end;
  512. procedure val(const s : string;var d : extended;var code : integer);
  513. var
  514. e : double;
  515. begin
  516. val(s,e,word(code));
  517. d:=e;
  518. end;
  519. procedure val(const s : string;var d : extended);
  520. var
  521. code : word;
  522. e : double;
  523. begin
  524. val(s,e,code);
  525. d:=e;
  526. end;
  527. procedure val(const s : string;var d : comp;var code : word);
  528. var
  529. e : double;
  530. begin
  531. val(s,e,code);
  532. d:=e;
  533. end;
  534. procedure val(const s : string;var d : comp;var code : integer);
  535. var
  536. e : double;
  537. begin
  538. val(s,e,word(code));
  539. d:=e;
  540. end;
  541. procedure val(const s : string;var d : comp);
  542. var
  543. code : word;
  544. e : double;
  545. begin
  546. val(s,e,code);
  547. d:=e;
  548. end;
  549. procedure val(const s : string;var v : cardinal;var code : word);
  550. var
  551. negativ : boolean;
  552. base,u : byte;
  553. begin
  554. v:=0;
  555. code:=InitVal(s,negativ,base);
  556. if (Code>length(s)) or negativ then
  557. exit;
  558. while Code<=Length(s) do
  559. begin
  560. u:=ord(s[code]);
  561. case u of
  562. 48..57 : dec(u,48);
  563. 65..70 : dec(u,55);
  564. 97..104 : dec(u,87);
  565. else
  566. u:=16;
  567. end;
  568. cardinal(v):=cardinal(v)*cardinal(longint(base));
  569. if (u>base) or (cardinal($ffffffff)-cardinal(v)>cardinal(longint(u))) then
  570. begin
  571. v:=0;
  572. exit;
  573. end;
  574. inc(v,u);
  575. inc(code);
  576. end;
  577. code:=0;
  578. end;
  579. procedure val(const s : string;var v : cardinal);
  580. var
  581. code : word;
  582. begin
  583. val(s,v,code);
  584. end;
  585. procedure val(const s : string;var v : cardinal;var code : integer);
  586. begin
  587. val(s,v,word(code));
  588. end;
  589. {
  590. $Log$
  591. Revision 1.3 1998-05-12 10:42:45 peter
  592. * moved getopts to inc/, all supported OS's need argc,argv exported
  593. + strpas, strlen are now exported in the systemunit
  594. * removed logs
  595. * removed $ifdef ver_above
  596. }