LIB.T
上传用户:jnzhq888
上传日期:2007-01-18
资源大小:51694k
文件大小:969k
源码类别:

操作系统开发

开发平台:

WINDOWS

  1. 15138
  2. 15139 /*
  3. 15140 **  Key to command mapping.
  4. 15141 */
  5. 15142 typedef struct _KEYMAP {
  6. 15143     CHAR        Key;
  7. 15144     STATUS      (*Function)();
  8. 15145 } KEYMAP;
  9. 15146
  10. 15147 /*
  11. 15148 **  Command history structure.
  12. 15149 */
  13. 15150 typedef struct _HISTORY {
  14. 15151     int         Size;
  15. 15152     int         Pos;
  16. 15153     CHAR        *Lines[HIST_SIZE];
  17. 15154 } HISTORY;
  18. 15155
  19. 15156 /*
  20. 15157 **  Globals.
  21. 15158 */
  22. 15159 int             rl_eof;
  23. 15160 int             rl_erase;
  24. 15161 int             rl_intr;
  25. 15162 int             rl_kill;
  26. 15163 int             rl_quit;
  27. 15164
  28. 15165 STATIC CHAR             NIL[] = "";
  29. 15166 STATIC CONST CHAR       *Input = NIL;
  30. 15167 STATIC CHAR             *Line;
  31. 15168 STATIC CONST char       *Prompt;
  32. 15169 STATIC CHAR             *Yanked;
  33. .Ep 126 src/lib/editline/editline.c
  34. 15170 STATIC char             *Screen;
  35. 15171 STATIC char             NEWLINE[]= CRLF;
  36. 15172 STATIC HISTORY          H;
  37. 15173 STATIC int              Repeat;
  38. 15174 STATIC int              End;
  39. 15175 STATIC int              Mark;
  40. 15176 STATIC int              OldPoint;
  41. 15177 STATIC int              Point;
  42. 15178 STATIC int              PushBack;
  43. 15179 STATIC int              Pushed;
  44. 15180 STATIC int              Signal;
  45. 15181 FORWARD KEYMAP          Map[33];
  46. 15182 FORWARD KEYMAP          MetaMap[17];
  47. 15183 STATIC SIZE_T           Length;
  48. 15184 STATIC SIZE_T           ScreenCount;
  49. 15185 STATIC SIZE_T           ScreenSize;
  50. 15186 STATIC char             *backspace;
  51. 15187 STATIC int              TTYwidth;
  52. 15188 STATIC int              TTYrows;
  53. 15189
  54. 15190 /* Display print 8-bit chars as `M-x' or as the actual 8-bit char? */
  55. 15191 int             rl_meta_chars = 0;
  56. 15192
  57. 15193 /*
  58. 15194 **  Declarations.
  59. 15195 */
  60. 15196 STATIC CHAR     *editinput();
  61. 15197 extern int      read();
  62. 15198 extern int      write();
  63. 15199 #if     defined(USE_TERMCAP)
  64. 15200 extern char     *getenv();
  65. 15201 extern char     *tgetstr();
  66. 15202 extern int      tgetent();
  67. 15203 #endif  /* defined(USE_TERMCAP) */
  68. 15204
  69. 15205 /*
  70. 15206 **  TTY input/output functions.
  71. 15207 */
  72. 15208
  73. 15209 STATIC void
  74. 15210 TTYflush()
  75. 15211 {
  76. 15212     if (ScreenCount) {
  77. 15213         (void)write(1, Screen, ScreenCount);
  78. 15214         ScreenCount = 0;
  79. 15215     }
  80. 15216 }
  81. 15218 STATIC void
  82. 15219 TTYput(c)
  83. 15220     CHAR        c;
  84. 15221 {
  85. 15222     Screen[ScreenCount] = c;
  86. 15223     if (++ScreenCount >= ScreenSize - 1) {
  87. 15224         ScreenSize += SCREEN_INC;
  88. 15225         RENEW(Screen, char, ScreenSize);
  89. 15226     }
  90. 15227 }
  91. 15229 STATIC void
  92. .Op 127 src/lib/editline/editline.c
  93. 15230 TTYputs(p)
  94. 15231     CHAR        *p;
  95. 15232 {
  96. 15233     while (*p)
  97. 15234         TTYput(*p++);
  98. 15235 }
  99. 15237 STATIC void
  100. 15238 TTYshow(c)
  101. 15239     CHAR        c;
  102. 15240 {
  103. 15241     if (c == DEL) {
  104. 15242         TTYput('^');
  105. 15243         TTYput('?');
  106. 15244     }
  107. 15245     else if (ISCTL(c)) {
  108. 15246         TTYput('^');
  109. 15247         TTYput(UNCTL(c));
  110. 15248     }
  111. 15249     else if (rl_meta_chars && ISMETA(c)) {
  112. 15250         TTYput('M');
  113. 15251         TTYput('-');
  114. 15252         TTYput(UNMETA(c));
  115. 15253     }
  116. 15254     else
  117. 15255         TTYput(c);
  118. 15256 }
  119. 15258 STATIC void
  120. 15259 TTYstring(p)
  121. 15260     CHAR        *p;
  122. 15261 {
  123. 15262     while (*p)
  124. 15263         TTYshow(*p++);
  125. 15264 }
  126. 15266 STATIC unsigned int
  127. 15267 TTYget()
  128. 15268 {
  129. 15269     CHAR        c;
  130. 15270
  131. 15271     TTYflush();
  132. 15272     if (Pushed) {
  133. 15273         Pushed = 0;
  134. 15274         return PushBack;
  135. 15275     }
  136. 15276     if (*Input)
  137. 15277         return *Input++;
  138. 15278     return read(0, &c, (SIZE_T)1) == 1 ? c : EOF;
  139. 15279 }
  140. 15281 #define TTYback()       (backspace ? TTYputs((CHAR *)backspace) : TTYput('b'))
  141. 15282
  142. 15283 STATIC void
  143. 15284 TTYbackn(n)
  144. 15285     int         n;
  145. 15286 {
  146. 15287     while (--n >= 0)
  147. 15288         TTYback();
  148. 15289 }
  149. .Ep 128 src/lib/editline/editline.c
  150. 15291 STATIC void
  151. 15292 TTYinfo()
  152. 15293 {
  153. 15294     static int          init;
  154. 15295 #if     defined(USE_TERMCAP)
  155. 15296     char                *term;
  156. 15297     char                buff[2048];
  157. 15298     char                *bp;
  158. 15299 #endif  /* defined(USE_TERMCAP) */
  159. 15300 #if     defined(TIOCGWINSZ)
  160. 15301     struct winsize      W;
  161. 15302 #endif  /* defined(TIOCGWINSZ) */
  162. 15303
  163. 15304     if (init) {
  164. 15305 #if     defined(TIOCGWINSZ)
  165. 15306         /* Perhaps we got resized. */
  166. 15307         if (ioctl(0, TIOCGWINSZ, &W) >= 0
  167. 15308          && W.ws_col > 0 && W.ws_row > 0) {
  168. 15309             TTYwidth = (int)W.ws_col;
  169. 15310             TTYrows = (int)W.ws_row;
  170. 15311         }
  171. 15312 #endif  /* defined(TIOCGWINSZ) */
  172. 15313         return;
  173. 15314     }
  174. 15315     init++;
  175. 15316
  176. 15317     TTYwidth = TTYrows = 0;
  177. 15318 #if     defined(USE_TERMCAP)
  178. 15319     bp = &buff[0];
  179. 15320     if ((term = getenv("TERM")) == NULL)
  180. 15321         term = "dumb";
  181. 15322     if (tgetent(buff, term) < 0) {
  182. 15323        TTYwidth = SCREEN_WIDTH;
  183. 15324        TTYrows = SCREEN_ROWS;
  184. 15325        return;
  185. 15326     }
  186. 15327     if ((backspace = tgetstr("le", &bp)) != NULL)
  187. 15328         backspace = strdup(backspace);
  188. 15329     TTYwidth = tgetnum("co");
  189. 15330     TTYrows = tgetnum("li");
  190. 15331 #endif  /* defined(USE_TERMCAP) */
  191. 15332
  192. 15333 #if     defined(TIOCGWINSZ)
  193. 15334     if (ioctl(0, TIOCGWINSZ, &W) >= 0) {
  194. 15335         TTYwidth = (int)W.ws_col;
  195. 15336         TTYrows = (int)W.ws_row;
  196. 15337     }
  197. 15338 #endif  /* defined(TIOCGWINSZ) */
  198. 15339
  199. 15340     if (TTYwidth <= 0 || TTYrows <= 0) {
  200. 15341         TTYwidth = SCREEN_WIDTH;
  201. 15342         TTYrows = SCREEN_ROWS;
  202. 15343     }
  203. 15344 }
  204. 15345
  205. 15346
  206. 15347 /*
  207. 15348 **  Print an array of words in columns.
  208. 15349 */
  209. .Op 129 src/lib/editline/editline.c
  210. 15350 STATIC void
  211. 15351 columns(ac, av)
  212. 15352     int         ac;
  213. 15353     CHAR        **av;
  214. 15354 {
  215. 15355     CHAR        *p;
  216. 15356     int         i;
  217. 15357     int         j;
  218. 15358     int         k;
  219. 15359     int         len;
  220. 15360     int         skip;
  221. 15361     int         longest;
  222. 15362     int         cols;
  223. 15363
  224. 15364     /* Find longest name, determine column count from that. */
  225. 15365     for (longest = 0, i = 0; i < ac; i++)
  226. 15366         if ((j = strlen((char *)av[i])) > longest)
  227. 15367             longest = j;
  228. 15368     cols = TTYwidth / (longest + 3);
  229. 15369
  230. 15370     TTYputs((CHAR *)NEWLINE);
  231. 15371     for (skip = ac / cols + 1, i = 0; i < skip; i++) {
  232. 15372         for (j = i; j < ac; j += skip) {
  233. 15373             for (p = av[j], len = strlen((char *)p), k = len; --k >= 0; p++)
  234. 15374                 TTYput(*p);
  235. 15375             if (j + skip < ac)
  236. 15376                 while (++len < longest + 3)
  237. 15377                     TTYput(' ');
  238. 15378         }
  239. 15379         TTYputs((CHAR *)NEWLINE);
  240. 15380     }
  241. 15381 }
  242. 15383 STATIC void
  243. 15384 reposition()
  244. 15385 {
  245. 15386     int         i;
  246. 15387     CHAR        *p;
  247. 15388
  248. 15389     TTYput('r');
  249. 15390     TTYputs((CONST CHAR *)Prompt);
  250. 15391     for (i = Point, p = Line; --i >= 0; p++)
  251. 15392         TTYshow(*p);
  252. 15393 }
  253. 15395 STATIC void
  254. 15396 left(Change)
  255. 15397     STATUS      Change;
  256. 15398 {
  257. 15399     TTYback();
  258. 15400     if (Point) {
  259. 15401         if (ISCTL(Line[Point - 1]))
  260. 15402             TTYback();
  261. 15403         else if (rl_meta_chars && ISMETA(Line[Point - 1])) {
  262. 15404             TTYback();
  263. 15405             TTYback();
  264. 15406         }
  265. 15407     }
  266. 15408     if (Change == CSmove)
  267. 15409         Point--;
  268. .Ep 130 src/lib/editline/editline.c
  269. 15410 }
  270. 15412 STATIC void
  271. 15413 right(Change)
  272. 15414     STATUS      Change;
  273. 15415 {
  274. 15416     TTYshow(Line[Point]);
  275. 15417     if (Change == CSmove)
  276. 15418         Point++;
  277. 15419 }
  278. 15421 STATIC STATUS
  279. 15422 ring_bell()
  280. 15423 {
  281. 15424     TTYput('7');
  282. 15425     TTYflush();
  283. 15426     return CSstay;
  284. 15427 }
  285. 15429 STATIC STATUS
  286. 15430 do_macro(c)
  287. 15431     unsigned int        c;
  288. 15432 {
  289. 15433     CHAR                name[4];
  290. 15434
  291. 15435     name[0] = '_';
  292. 15436     name[1] = c;
  293. 15437     name[2] = '_';
  294. 15438     name[3] = '';
  295. 15439
  296. 15440     if ((Input = (CHAR *)getenv((char *)name)) == NULL) {
  297. 15441         Input = NIL;
  298. 15442         return ring_bell();
  299. 15443     }
  300. 15444     return CSstay;
  301. 15445 }
  302. 15447 STATIC STATUS
  303. 15448 do_forward(move)
  304. 15449     STATUS      move;
  305. 15450 {
  306. 15451     int         i;
  307. 15452     CHAR        *p;
  308. 15453
  309. 15454     i = 0;
  310. 15455     do {
  311. 15456         p = &Line[Point];
  312. 15457         for ( ; Point < End && (*p == ' ' || !isalnum(*p)); Point++, p++)
  313. 15458             if (move == CSmove)
  314. 15459                 right(CSstay);
  315. 15460
  316. 15461         for (; Point < End && isalnum(*p); Point++, p++)
  317. 15462             if (move == CSmove)
  318. 15463                 right(CSstay);
  319. 15464
  320. 15465         if (Point == End)
  321. 15466             break;
  322. 15467     } while (++i < Repeat);
  323. 15468
  324. 15469     return CSstay;
  325. .Op 131 src/lib/editline/editline.c
  326. 15470 }
  327. 15472 STATIC STATUS
  328. 15473 do_case(type)
  329. 15474     CASE        type;
  330. 15475 {
  331. 15476     int         i;
  332. 15477     int         end;
  333. 15478     int         count;
  334. 15479     CHAR        *p;
  335. 15480
  336. 15481     (void)do_forward(CSstay);
  337. 15482     if (OldPoint != Point) {
  338. 15483         if ((count = Point - OldPoint) < 0)
  339. 15484             count = -count;
  340. 15485         Point = OldPoint;
  341. 15486         if ((end = Point + count) > End)
  342. 15487             end = End;
  343. 15488         for (i = Point, p = &Line[i]; i < end; i++, p++) {
  344. 15489             if (type == TOupper) {
  345. 15490                 if (islower(*p))
  346. 15491                     *p = toupper(*p);
  347. 15492             }
  348. 15493             else if (isupper(*p))
  349. 15494                 *p = tolower(*p);
  350. 15495             right(CSmove);
  351. 15496         }
  352. 15497     }
  353. 15498     return CSstay;
  354. 15499 }
  355. 15501 STATIC STATUS
  356. 15502 case_down_word()
  357. 15503 {
  358. 15504     return do_case(TOlower);
  359. 15505 }
  360. 15507 STATIC STATUS
  361. 15508 case_up_word()
  362. 15509 {
  363. 15510     return do_case(TOupper);
  364. 15511 }
  365. 15513 STATIC void
  366. 15514 ceol()
  367. 15515 {
  368. 15516     int         extras;
  369. 15517     int         i;
  370. 15518     CHAR        *p;
  371. 15519
  372. 15520     for (extras = 0, i = Point, p = &Line[i]; i <= End; i++, p++) {
  373. 15521         TTYput(' ');
  374. 15522         if (ISCTL(*p)) {
  375. 15523             TTYput(' ');
  376. 15524             extras++;
  377. 15525         }
  378. 15526         else if (rl_meta_chars && ISMETA(*p)) {
  379. 15527             TTYput(' ');
  380. 15528             TTYput(' ');
  381. 15529             extras += 2;
  382. .Ep 132 src/lib/editline/editline.c
  383. 15530         }
  384. 15531     }
  385. 15532
  386. 15533     for (i += extras; i > Point; i--)
  387. 15534         TTYback();
  388. 15535 }
  389. 15537 STATIC void
  390. 15538 clear_line()
  391. 15539 {
  392. 15540     Point = -strlen(Prompt);
  393. 15541     TTYput('r');
  394. 15542     ceol();
  395. 15543     Point = 0;
  396. 15544     End = 0;
  397. 15545     Line[0] = '';
  398. 15546 }
  399. 15548 STATIC STATUS
  400. 15549 insert_string(p)
  401. 15550     CHAR        *p;
  402. 15551 {
  403. 15552     SIZE_T      len;
  404. 15553     int         i;
  405. 15554     CHAR        *new;
  406. 15555     CHAR        *q;
  407. 15556
  408. 15557     len = strlen((char *)p);
  409. 15558     if (End + len >= Length) {
  410. 15559         if ((new = NEW(CHAR, Length + len + MEM_INC)) == NULL)
  411. 15560             return CSstay;
  412. 15561         if (Length) {
  413. 15562             COPYFROMTO(new, Line, Length);
  414. 15563             DISPOSE(Line);
  415. 15564         }
  416. 15565         Line = new;
  417. 15566         Length += len + MEM_INC;
  418. 15567     }
  419. 15568
  420. 15569     for (q = &Line[Point], i = End - Point; --i >= 0; )
  421. 15570         q[len + i] = q[i];
  422. 15571     COPYFROMTO(&Line[Point], p, len);
  423. 15572     End += len;
  424. 15573     Line[End] = '';
  425. 15574     TTYstring(&Line[Point]);
  426. 15575     Point += len;
  427. 15576
  428. 15577     return Point == End ? CSstay : CSmove;
  429. 15578 }
  430. 15580 STATIC STATUS
  431. 15581 redisplay()
  432. 15582 {
  433. 15583     TTYputs((CONST CHAR *)NEWLINE);
  434. 15584     TTYputs((CONST CHAR *)Prompt);
  435. 15585     TTYstring(Line);
  436. 15586     return CSmove;
  437. 15587 }
  438. 15589 STATIC STATUS
  439. .Op 133 src/lib/editline/editline.c
  440. 15590 toggle_meta_mode()
  441. 15591 {
  442. 15592     rl_meta_chars = ! rl_meta_chars;
  443. 15593     return redisplay();
  444. 15594 }
  445. 15595
  446. 15596
  447. 15597 STATIC CHAR *
  448. 15598 next_hist()
  449. 15599 {
  450. 15600     return H.Pos >= H.Size - 1 ? NULL : H.Lines[++H.Pos];
  451. 15601 }
  452. 15603 STATIC CHAR *
  453. 15604 prev_hist()
  454. 15605 {
  455. 15606     return H.Pos == 0 ? NULL : H.Lines[--H.Pos];
  456. 15607 }
  457. 15609 STATIC STATUS
  458. 15610 do_insert_hist(p)
  459. 15611     CHAR        *p;
  460. 15612 {
  461. 15613     if (p == NULL)
  462. 15614         return ring_bell();
  463. 15615     Point = 0;
  464. 15616     reposition();
  465. 15617     ceol();
  466. 15618     End = 0;
  467. 15619     return insert_string(p);
  468. 15620 }
  469. 15622 STATIC STATUS
  470. 15623 do_hist(move)
  471. 15624     CHAR        *(*move)();
  472. 15625 {
  473. 15626     CHAR        *p;
  474. 15627     int         i;
  475. 15628
  476. 15629     i = 0;
  477. 15630     do {
  478. 15631         if ((p = (*move)()) == NULL)
  479. 15632             return ring_bell();
  480. 15633     } while (++i < Repeat);
  481. 15634     return do_insert_hist(p);
  482. 15635 }
  483. 15637 STATIC STATUS
  484. 15638 h_next()
  485. 15639 {
  486. 15640     return do_hist(next_hist);
  487. 15641 }
  488. 15643 STATIC STATUS
  489. 15644 h_prev()
  490. 15645 {
  491. 15646     return do_hist(prev_hist);
  492. 15647 }
  493. 15649 STATIC STATUS
  494. .Ep 134 src/lib/editline/editline.c
  495. 15650 h_first()
  496. 15651 {
  497. 15652     return do_insert_hist(H.Lines[H.Pos = 0]);
  498. 15653 }
  499. 15655 STATIC STATUS
  500. 15656 h_last()
  501. 15657 {
  502. 15658     return do_insert_hist(H.Lines[H.Pos = H.Size - 1]);
  503. 15659 }
  504. 15661 /*
  505. 15662 **  Return zero if pat appears as a substring in text.
  506. 15663 */
  507. 15664 STATIC int
  508. 15665 substrcmp(text, pat, len)
  509. 15666     char        *text;
  510. 15667     char        *pat;
  511. 15668     int         len;
  512. 15669 {
  513. 15670     char        c;
  514. 15671
  515. 15672     if ((c = *pat) == '')
  516. 15673         return *text == '';
  517. 15674     for ( ; *text; text++)
  518. 15675         if (*text == c && strncmp(text, pat, len) == 0)
  519. 15676             return 0;
  520. 15677     return 1;
  521. 15678 }
  522. 15680 STATIC CHAR *
  523. 15681 search_hist(search, move)
  524. 15682     CHAR        *search;
  525. 15683     CHAR        *(*move)();
  526. 15684 {
  527. 15685     static CHAR *old_search;
  528. 15686     int         len;
  529. 15687     int         pos;
  530. 15688     int         (*match)();
  531. 15689     char        *pat;
  532. 15690
  533. 15691     /* Save or get remembered search pattern. */
  534. 15692     if (search && *search) {
  535. 15693         if (old_search)
  536. 15694             DISPOSE(old_search);
  537. 15695         old_search = (CHAR *)strdup((char *)search);
  538. 15696     }
  539. 15697     else {
  540. 15698         if (old_search == NULL || *old_search == '')
  541. 15699             return NULL;
  542. 15700         search = old_search;
  543. 15701     }
  544. 15702
  545. 15703     /* Set up pattern-finder. */
  546. 15704     if (*search == '^') {
  547. 15705         match = strncmp;
  548. 15706         pat = (char *)(search + 1);
  549. 15707     }
  550. 15708     else {
  551. 15709         match = substrcmp;
  552. .Op 135 src/lib/editline/editline.c
  553. 15710         pat = (char *)search;
  554. 15711     }
  555. 15712     len = strlen(pat);
  556. 15713
  557. 15714     for (pos = H.Pos; (*move)() != NULL; )
  558. 15715         if ((*match)((char *)H.Lines[H.Pos], pat, len) == 0)
  559. 15716             return H.Lines[H.Pos];
  560. 15717     H.Pos = pos;
  561. 15718     return NULL;
  562. 15719 }
  563. 15721 STATIC STATUS
  564. 15722 h_search()
  565. 15723 {
  566. 15724     static int  Searching;
  567. 15725     CONST char  *old_prompt;
  568. 15726     CHAR        *(*move)();
  569. 15727     CHAR        *p;
  570. 15728
  571. 15729     if (Searching)
  572. 15730         return ring_bell();
  573. 15731     Searching = 1;
  574. 15732
  575. 15733     clear_line();
  576. 15734     old_prompt = Prompt;
  577. 15735     Prompt = "Search: ";
  578. 15736     TTYputs((CONST CHAR *)Prompt);
  579. 15737     move = Repeat == NO_ARG ? prev_hist : next_hist;
  580. 15738     p = editinput();
  581. 15739     Prompt = old_prompt;
  582. 15740     Searching = 0;
  583. 15741     TTYputs((CONST CHAR *)Prompt);
  584. 15742     if (p == NULL && Signal > 0) {
  585. 15743         Signal = 0;
  586. 15744         clear_line();
  587. 15745         return redisplay();
  588. 15746     }
  589. 15747     p = search_hist(p, move);
  590. 15748     clear_line();
  591. 15749     if (p == NULL) {
  592. 15750         (void)ring_bell();
  593. 15751         return redisplay();
  594. 15752     }
  595. 15753     return do_insert_hist(p);
  596. 15754 }
  597. 15756 STATIC STATUS
  598. 15757 fd_char()
  599. 15758 {
  600. 15759     int         i;
  601. 15760
  602. 15761     i = 0;
  603. 15762     do {
  604. 15763         if (Point >= End)
  605. 15764             break;
  606. 15765         right(CSmove);
  607. 15766     } while (++i < Repeat);
  608. 15767     return CSstay;
  609. 15768 }
  610. .Ep 136 src/lib/editline/editline.c
  611. 15770 STATIC void
  612. 15771 save_yank(begin, i)
  613. 15772     int         begin;
  614. 15773     int         i;
  615. 15774 {
  616. 15775     if (Yanked) {
  617. 15776         DISPOSE(Yanked);
  618. 15777         Yanked = NULL;
  619. 15778     }
  620. 15779
  621. 15780     if (i < 1)
  622. 15781         return;
  623. 15782
  624. 15783     if ((Yanked = NEW(CHAR, (SIZE_T)i + 1)) != NULL) {
  625. 15784         COPYFROMTO(Yanked, &Line[begin], i);
  626. 15785         Yanked[i] = '';
  627. 15786     }
  628. 15787 }
  629. 15789 STATIC STATUS
  630. 15790 delete_string(count)
  631. 15791     int         count;
  632. 15792 {
  633. 15793     int         i;
  634. 15794     CHAR        *p;
  635. 15795
  636. 15796     if (count <= 0 || End == Point)
  637. 15797         return ring_bell();
  638. 15798
  639. 15799     if (count == 1 && Point == End - 1) {
  640. 15800         /* Optimize common case of delete at end of line. */
  641. 15801         End--;
  642. 15802         p = &Line[Point];
  643. 15803         i = 1;
  644. 15804         TTYput(' ');
  645. 15805         if (ISCTL(*p)) {
  646. 15806             i = 2;
  647. 15807             TTYput(' ');
  648. 15808         }
  649. 15809         else if (rl_meta_chars && ISMETA(*p)) {
  650. 15810             i = 3;
  651. 15811             TTYput(' ');
  652. 15812             TTYput(' ');
  653. 15813         }
  654. 15814         TTYbackn(i);
  655. 15815         *p = '';
  656. 15816         return CSmove;
  657. 15817     }
  658. 15818     if (Point + count > End && (count = End - Point) <= 0)
  659. 15819         return CSstay;
  660. 15820
  661. 15821     if (count > 1)
  662. 15822         save_yank(Point, count);
  663. 15823
  664. 15824     for (p = &Line[Point], i = End - (Point + count) + 1; --i >= 0; p++)
  665. 15825         p[0] = p[count];
  666. 15826     ceol();
  667. 15827     End -= count;
  668. 15828     TTYstring(&Line[Point]);
  669. 15829     return CSmove;
  670. .Op 137 src/lib/editline/editline.c
  671. 15830 }
  672. 15832 STATIC STATUS
  673. 15833 bk_char()
  674. 15834 {
  675. 15835     int         i;
  676. 15836
  677. 15837     i = 0;
  678. 15838     do {
  679. 15839         if (Point == 0)
  680. 15840             break;
  681. 15841         left(CSmove);
  682. 15842     } while (++i < Repeat);
  683. 15843
  684. 15844     return CSstay;
  685. 15845 }
  686. 15847 STATIC STATUS
  687. 15848 bk_del_char()
  688. 15849 {
  689. 15850     int         i;
  690. 15851
  691. 15852     i = 0;
  692. 15853     do {
  693. 15854         if (Point == 0)
  694. 15855             break;
  695. 15856         left(CSmove);
  696. 15857     } while (++i < Repeat);
  697. 15858
  698. 15859     return delete_string(i);
  699. 15860 }
  700. 15862 STATIC STATUS
  701. 15863 kill_line()
  702. 15864 {
  703. 15865     int         i;
  704. 15866
  705. 15867     if (Repeat != NO_ARG) {
  706. 15868         if (Repeat < Point) {
  707. 15869             i = Point;
  708. 15870             Point = Repeat;
  709. 15871             reposition();
  710. 15872             (void)delete_string(i - Point);
  711. 15873         }
  712. 15874         else if (Repeat > Point) {
  713. 15875             right(CSmove);
  714. 15876             (void)delete_string(Repeat - Point - 1);
  715. 15877         }
  716. 15878         return CSmove;
  717. 15879     }
  718. 15880
  719. 15881     save_yank(Point, End - Point);
  720. 15882     Line[Point] = '';
  721. 15883     ceol();
  722. 15884     End = Point;
  723. 15885     return CSstay;
  724. 15886 }
  725. 15888 STATIC STATUS
  726. 15889 insert_char(c)
  727. .Ep 138 src/lib/editline/editline.c
  728. 15890     int         c;
  729. 15891 {
  730. 15892     STATUS      s;
  731. 15893     CHAR        buff[2];
  732. 15894     CHAR        *p;
  733. 15895     CHAR        *q;
  734. 15896     int         i;
  735. 15897
  736. 15898     if (Repeat == NO_ARG || Repeat < 2) {
  737. 15899         buff[0] = c;
  738. 15900         buff[1] = '';
  739. 15901         return insert_string(buff);
  740. 15902     }
  741. 15903
  742. 15904     if ((p = NEW(CHAR, Repeat + 1)) == NULL)
  743. 15905         return CSstay;
  744. 15906     for (i = Repeat, q = p; --i >= 0; )
  745. 15907         *q++ = c;
  746. 15908     *q = '';
  747. 15909     Repeat = 0;
  748. 15910     s = insert_string(p);
  749. 15911     DISPOSE(p);
  750. 15912     return s;
  751. 15913 }
  752. 15915 STATIC STATUS
  753. 15916 meta()
  754. 15917 {
  755. 15918     unsigned int        c;
  756. 15919     KEYMAP              *kp;
  757. 15920
  758. 15921     if ((c = TTYget()) == EOF)
  759. 15922         return CSeof;
  760. 15923 #if     defined(ANSI_ARROWS)
  761. 15924     /* Also include VT-100 arrows. */
  762. 15925     if (c == '[' || c == 'O')
  763. 15926         switch (c = TTYget()) {
  764. 15927         default:        return ring_bell();
  765. 15928         case EOF:       return CSeof;
  766. 15929         case 'A':       return h_prev();
  767. 15930         case 'B':       return h_next();
  768. 15931         case 'C':       return fd_char();
  769. 15932         case 'D':       return bk_char();
  770. 15933         }
  771. 15934 #endif  /* defined(ANSI_ARROWS) */
  772. 15935
  773. 15936     if (isdigit(c)) {
  774. 15937         for (Repeat = c - '0'; (c = TTYget()) != EOF && isdigit(c); )
  775. 15938             Repeat = Repeat * 10 + c - '0';
  776. 15939         Pushed = 1;
  777. 15940         PushBack = c;
  778. 15941         return CSstay;
  779. 15942     }
  780. 15943
  781. 15944     if (isupper(c))
  782. 15945         return do_macro(c);
  783. 15946     for (kp = MetaMap; kp->Function; kp++)
  784. 15947         if (kp->Key == c)
  785. 15948             return (*kp->Function)();
  786. 15949
  787. .Op 139 src/lib/editline/editline.c
  788. 15950     return ring_bell();
  789. 15951 }
  790. 15953 STATIC STATUS
  791. 15954 emacs(c)
  792. 15955     unsigned int        c;
  793. 15956 {
  794. 15957     STATUS              s;
  795. 15958     KEYMAP              *kp;
  796. 15959
  797. 15960     OldPoint = Point;
  798. 15961     if (rl_meta_chars && ISMETA(c)) {
  799. 15962         Pushed = 1;
  800. 15963         PushBack = UNMETA(c);
  801. 15964         return meta();
  802. 15965     }
  803. 15966     for (kp = Map; kp->Function; kp++)
  804. 15967         if (kp->Key == c)
  805. 15968             break;
  806. 15969     s = kp->Function ? (*kp->Function)() : insert_char((int)c);
  807. 15970     if (!Pushed)
  808. 15971         /* No pushback means no repeat count; hacky, but true. */
  809. 15972         Repeat = NO_ARG;
  810. 15973     return s;
  811. 15974 }
  812. 15976 STATIC STATUS
  813. 15977 TTYspecial(c)
  814. 15978     unsigned int        c;
  815. 15979 {
  816. 15980     if (ISMETA(c))
  817. 15981         return CSdispatch;
  818. 15982
  819. 15983     if (c == rl_erase || c == DEL)
  820. 15984         return bk_del_char();
  821. 15985     if (c == rl_kill) {
  822. 15986         if (Point != 0) {
  823. 15987             Point = 0;
  824. 15988             reposition();
  825. 15989         }
  826. 15990         Repeat = NO_ARG;
  827. 15991         return kill_line();
  828. 15992     }
  829. 15993     if (c == rl_eof && Point == 0 && End == 0)
  830. 15994         return CSeof;
  831. 15995     if (c == rl_intr) {
  832. 15996         Signal = SIGINT;
  833. 15997         return CSsignal;
  834. 15998     }
  835. 15999     if (c == rl_quit) {
  836. 16000         Signal = SIGQUIT;
  837. 16001         return CSeof;
  838. 16002     }
  839. 16003
  840. 16004     return CSdispatch;
  841. 16005 }
  842. 16007 STATIC CHAR *
  843. 16008 editinput()
  844. 16009 {
  845. .Ep 140 src/lib/editline/editline.c
  846. 16010     unsigned int        c;
  847. 16011
  848. 16012     Repeat = NO_ARG;
  849. 16013     OldPoint = Point = Mark = End = 0;
  850. 16014     Line[0] = '';
  851. 16015
  852. 16016     Signal = -1;
  853. 16017     while ((c = TTYget()) != EOF)
  854. 16018         switch (TTYspecial(c)) {
  855. 16019         case CSdone:
  856. 16020             return Line;
  857. 16021         case CSeof:
  858. 16022             return NULL;
  859. 16023         case CSsignal:
  860. 16024             return (CHAR *)"";
  861. 16025         case CSmove:
  862. 16026             reposition();
  863. 16027             break;
  864. 16028         case CSdispatch:
  865. 16029             switch (emacs(c)) {
  866. 16030             case CSdone:
  867. 16031                 return Line;
  868. 16032             case CSeof:
  869. 16033                 return NULL;
  870. 16034             case CSsignal:
  871. 16035                 return (CHAR *)"";
  872. 16036             case CSmove:
  873. 16037                 reposition();
  874. 16038                 break;
  875. 16039             case CSdispatch:
  876. 16040             case CSstay:
  877. 16041                 break;
  878. 16042             }
  879. 16043             break;
  880. 16044         case CSstay:
  881. 16045             break;
  882. 16046         }
  883. 16047     return NULL;
  884. 16048 }
  885. 16050 STATIC void
  886. 16051 hist_add(p)
  887. 16052     CHAR        *p;
  888. 16053 {
  889. 16054     int         i;
  890. 16055
  891. 16056     if ((p = (CHAR *)strdup((char *)p)) == NULL)
  892. 16057         return;
  893. 16058     if (H.Size < HIST_SIZE)
  894. 16059         H.Lines[H.Size++] = p;
  895. 16060     else {
  896. 16061         DISPOSE(H.Lines[0]);
  897. 16062         for (i = 0; i < HIST_SIZE - 1; i++)
  898. 16063             H.Lines[i] = H.Lines[i + 1];
  899. 16064         H.Lines[i] = p;
  900. 16065     }
  901. 16066     H.Pos = H.Size - 1;
  902. 16067 }
  903. 16069 /*
  904. .Op 141 src/lib/editline/editline.c
  905. 16070 **  For compatibility with FSF readline.
  906. 16071 */
  907. 16072 /* ARGSUSED0 */
  908. 16073 void
  909. 16074 rl_reset_terminal(p)
  910. 16075     char        *p;
  911. 16076 {
  912. 16077 }
  913. 16079 void
  914. 16080 rl_initialize()
  915. 16081 {
  916. 16082 }
  917. 16084 char *
  918. 16085 readline(prompt)
  919. 16086     CONST char  *prompt;
  920. 16087 {
  921. 16088     CHAR        *line;
  922. 16089     int         s;
  923. 16090
  924. 16091     if (Line == NULL) {
  925. 16092         Length = MEM_INC;
  926. 16093         if ((Line = NEW(CHAR, Length)) == NULL)
  927. 16094             return NULL;
  928. 16095     }
  929. 16096
  930. 16097     TTYinfo();
  931. 16098     rl_ttyset(0);
  932. 16099     hist_add(NIL);
  933. 16100     ScreenSize = SCREEN_INC;
  934. 16101     Screen = NEW(char, ScreenSize);
  935. 16102     Prompt = prompt ? prompt : (char *)NIL;
  936. 16103     TTYputs((CONST CHAR *)Prompt);
  937. 16104     if ((line = editinput()) != NULL) {
  938. 16105         line = (CHAR *)strdup((char *)line);
  939. 16106         TTYputs((CHAR *)NEWLINE);
  940. 16107         TTYflush();
  941. 16108     }
  942. 16109     rl_ttyset(1);
  943. 16110     DISPOSE(Screen);
  944. 16111     DISPOSE(H.Lines[--H.Size]);
  945. 16112     if (Signal > 0) {
  946. 16113         s = Signal;
  947. 16114         Signal = 0;
  948. 16115         (void)kill(getpid(), s);
  949. 16116     }
  950. 16117     return (char *)line;
  951. 16118 }
  952. 16120 void
  953. 16121 add_history(p)
  954. 16122     char        *p;
  955. 16123 {
  956. 16124     if (p == NULL || *p == '')
  957. 16125         return;
  958. 16126
  959. 16127 #if     defined(UNIQUE_HISTORY)
  960. 16128     if (H.Pos && strcmp(p, (char *) H.Lines[H.Pos - 1]) == 0)
  961. 16129         return;
  962. .Ep 142 src/lib/editline/editline.c
  963. 16130 #endif  /* defined(UNIQUE_HISTORY) */
  964. 16131     if (H.Size && strcmp(p, (char *) H.Lines[H.Size - 1]) == 0)
  965. 16132         return;
  966. 16133     hist_add((CHAR *)p);
  967. 16134 }
  968. 16135
  969. 16136
  970. 16137 STATIC STATUS
  971. 16138 beg_line()
  972. 16139 {
  973. 16140     if (Point) {
  974. 16141         Point = 0;
  975. 16142         return CSmove;
  976. 16143     }
  977. 16144     return CSstay;
  978. 16145 }
  979. 16147 STATIC STATUS
  980. 16148 del_char()
  981. 16149 {
  982. 16150     return delete_string(Repeat == NO_ARG ? 1 : Repeat);
  983. 16151 }
  984. 16153 STATIC STATUS
  985. 16154 end_line()
  986. 16155 {
  987. 16156     if (Point != End) {
  988. 16157         Point = End;
  989. 16158         return CSmove;
  990. 16159     }
  991. 16160     return CSstay;
  992. 16161 }
  993. 16163 /*
  994. 16164 **  Move back to the beginning of the current word and return an
  995. 16165 **  allocated copy of it.
  996. 16166 */
  997. 16167 STATIC CHAR *
  998. 16168 find_word()
  999. 16169 {
  1000. 16170     static char SEPS[] = "#:;&|^$=`'{}()<>nt ";
  1001. 16171     CHAR        *p;
  1002. 16172     CHAR        *new;
  1003. 16173     SIZE_T      len;
  1004. 16174
  1005. 16175     for (p = &Line[Point]; p > Line && strchr(SEPS, (char)p[-1]) == NULL; p--)
  1006. 16176         continue;
  1007. 16177     len = Point - (p - Line) + 1;
  1008. 16178     if ((new = NEW(CHAR, len)) == NULL)
  1009. 16179         return NULL;
  1010. 16180     COPYFROMTO(new, p, len);
  1011. 16181     new[len - 1] = '';
  1012. 16182     return new;
  1013. 16183 }
  1014. 16185 STATIC STATUS
  1015. 16186 c_possible()
  1016. 16187 {
  1017. 16188     CHAR        **av;
  1018. 16189     CHAR        *word;
  1019. .Op 143 src/lib/editline/editline.c
  1020. 16190     int         ac;
  1021. 16191
  1022. 16192     word = find_word();
  1023. 16193     ac = rl_list_possib((char *)word, (char ***)&av);
  1024. 16194     if (word)
  1025. 16195         DISPOSE(word);
  1026. 16196     if (ac) {
  1027. 16197         columns(ac, av);
  1028. 16198         while (--ac >= 0)
  1029. 16199             DISPOSE(av[ac]);
  1030. 16200         DISPOSE(av);
  1031. 16201         return CSmove;
  1032. 16202     }
  1033. 16203     return ring_bell();
  1034. 16204 }
  1035. 16206 STATIC STATUS
  1036. 16207 c_complete()
  1037. 16208 {
  1038. 16209     CHAR        *p;
  1039. 16210     CHAR        *word;
  1040. 16211     int         unique;
  1041. 16212     STATUS      s;
  1042. 16213
  1043. 16214     word = find_word();
  1044. 16215     p = (CHAR *)rl_complete((char *)word, &unique);
  1045. 16216     if (word)
  1046. 16217         DISPOSE(word);
  1047. 16218     if (p && *p) {
  1048. 16219         s = insert_string(p);
  1049. 16220 #if ANNOYING_NOISE
  1050. 16221         if (!unique)
  1051. 16222             (void)ring_bell();
  1052. 16223 #endif
  1053. 16224         DISPOSE(p);
  1054. 16225         return s;
  1055. 16226     }
  1056. 16227     return c_possible();
  1057. 16228 }
  1058. 16230 STATIC STATUS
  1059. 16231 accept_line()
  1060. 16232 {
  1061. 16233     Line[End] = '';
  1062. 16234     return CSdone;
  1063. 16235 }
  1064. 16237 STATIC STATUS
  1065. 16238 transpose()
  1066. 16239 {
  1067. 16240     CHAR        c;
  1068. 16241
  1069. 16242     if (Point) {
  1070. 16243         if (Point == End)
  1071. 16244             left(CSmove);
  1072. 16245         c = Line[Point - 1];
  1073. 16246         left(CSstay);
  1074. 16247         Line[Point - 1] = Line[Point];
  1075. 16248         TTYshow(Line[Point - 1]);
  1076. 16249         Line[Point++] = c;
  1077. .Ep 144 src/lib/editline/editline.c
  1078. 16250         TTYshow(c);
  1079. 16251     }
  1080. 16252     return CSstay;
  1081. 16253 }
  1082. 16255 STATIC STATUS
  1083. 16256 quote()
  1084. 16257 {
  1085. 16258     unsigned int        c;
  1086. 16259
  1087. 16260     return (c = TTYget()) == EOF ? CSeof : insert_char((int)c);
  1088. 16261 }
  1089. 16263 STATIC STATUS
  1090. 16264 wipe()
  1091. 16265 {
  1092. 16266     int         i;
  1093. 16267
  1094. 16268     if (Mark > End)
  1095. 16269         return ring_bell();
  1096. 16270
  1097. 16271     if (Point > Mark) {
  1098. 16272         i = Point;
  1099. 16273         Point = Mark;
  1100. 16274         Mark = i;
  1101. 16275         reposition();
  1102. 16276     }
  1103. 16277
  1104. 16278     return delete_string(Mark - Point);
  1105. 16279 }
  1106. 16281 STATIC STATUS
  1107. 16282 mk_set()
  1108. 16283 {
  1109. 16284     Mark = Point;
  1110. 16285     return CSstay;
  1111. 16286 }
  1112. 16288 STATIC STATUS
  1113. 16289 exchange()
  1114. 16290 {
  1115. 16291     unsigned int        c;
  1116. 16292
  1117. 16293     if ((c = TTYget()) != CTL('X'))
  1118. 16294         return c == EOF ? CSeof : ring_bell();
  1119. 16295
  1120. 16296     if ((c = Mark) <= End) {
  1121. 16297         Mark = Point;
  1122. 16298         Point = c;
  1123. 16299         return CSmove;
  1124. 16300     }
  1125. 16301     return CSstay;
  1126. 16302 }
  1127. 16304 STATIC STATUS
  1128. 16305 yank()
  1129. 16306 {
  1130. 16307     if (Yanked && *Yanked)
  1131. 16308         return insert_string(Yanked);
  1132. 16309     return CSstay;
  1133. .Op 145 src/lib/editline/editline.c
  1134. 16310 }
  1135. 16312 STATIC STATUS
  1136. 16313 copy_region()
  1137. 16314 {
  1138. 16315     if (Mark > End)
  1139. 16316         return ring_bell();
  1140. 16317
  1141. 16318     if (Point > Mark)
  1142. 16319         save_yank(Mark, Point - Mark);
  1143. 16320     else
  1144. 16321         save_yank(Point, Mark - Point);
  1145. 16322
  1146. 16323     return CSstay;
  1147. 16324 }
  1148. 16326 STATIC STATUS
  1149. 16327 move_to_char()
  1150. 16328 {
  1151. 16329     unsigned int        c;
  1152. 16330     int                 i;
  1153. 16331     CHAR                *p;
  1154. 16332
  1155. 16333     if ((c = TTYget()) == EOF)
  1156. 16334         return CSeof;
  1157. 16335     for (i = Point + 1, p = &Line[i]; i < End; i++, p++)
  1158. 16336         if (*p == c) {
  1159. 16337             Point = i;
  1160. 16338             return CSmove;
  1161. 16339         }
  1162. 16340     return CSstay;
  1163. 16341 }
  1164. 16343 STATIC STATUS
  1165. 16344 fd_word()
  1166. 16345 {
  1167. 16346     return do_forward(CSmove);
  1168. 16347 }
  1169. 16349 STATIC STATUS
  1170. 16350 fd_kill_word()
  1171. 16351 {
  1172. 16352     int         i;
  1173. 16353
  1174. 16354     (void)do_forward(CSstay);
  1175. 16355     if (OldPoint != Point) {
  1176. 16356         i = Point - OldPoint;
  1177. 16357         Point = OldPoint;
  1178. 16358         return delete_string(i);
  1179. 16359     }
  1180. 16360     return CSstay;
  1181. 16361 }
  1182. 16363 STATIC STATUS
  1183. 16364 bk_word()
  1184. 16365 {
  1185. 16366     int         i;
  1186. 16367     CHAR        *p;
  1187. 16368
  1188. 16369     i = 0;
  1189. .Ep 146 src/lib/editline/editline.c
  1190. 16370     do {
  1191. 16371         for (p = &Line[Point]; p > Line && !isalnum(p[-1]); p--)
  1192. 16372             left(CSmove);
  1193. 16373
  1194. 16374         for (; p > Line && p[-1] != ' ' && isalnum(p[-1]); p--)
  1195. 16375             left(CSmove);
  1196. 16376
  1197. 16377         if (Point == 0)
  1198. 16378             break;
  1199. 16379     } while (++i < Repeat);
  1200. 16380
  1201. 16381     return CSstay;
  1202. 16382 }
  1203. 16384 STATIC STATUS
  1204. 16385 bk_kill_word()
  1205. 16386 {
  1206. 16387     (void)bk_word();
  1207. 16388     if (OldPoint != Point)
  1208. 16389         return delete_string(OldPoint - Point);
  1209. 16390     return CSstay;
  1210. 16391 }
  1211. 16393 STATIC int
  1212. 16394 argify(line, avp)
  1213. 16395     CHAR        *line;
  1214. 16396     CHAR        ***avp;
  1215. 16397 {
  1216. 16398     CHAR        *c;
  1217. 16399     CHAR        **p;
  1218. 16400     CHAR        **new;
  1219. 16401     int         ac;
  1220. 16402     int         i;
  1221. 16403
  1222. 16404     i = MEM_INC;
  1223. 16405     if ((*avp = p = NEW(CHAR*, i))== NULL)
  1224. 16406          return 0;
  1225. 16407
  1226. 16408     for (c = line; isspace(*c); c++)
  1227. 16409         continue;
  1228. 16410     if (*c == 'n' || *c == '')
  1229. 16411         return 0;
  1230. 16412
  1231. 16413     for (ac = 0, p[ac++] = c; *c && *c != 'n'; ) {
  1232. 16414         if (isspace(*c)) {
  1233. 16415             *c++ = '';
  1234. 16416             if (*c && *c != 'n') {
  1235. 16417                 if (ac + 1 == i) {
  1236. 16418                     new = NEW(CHAR*, i + MEM_INC);
  1237. 16419                     if (new == NULL) {
  1238. 16420                         p[ac] = NULL;
  1239. 16421                         return ac;
  1240. 16422                     }
  1241. 16423                     COPYFROMTO(new, p, i * sizeof (char **));
  1242. 16424                     i += MEM_INC;
  1243. 16425                     DISPOSE(p);
  1244. 16426                     *avp = p = new;
  1245. 16427                 }
  1246. 16428                 p[ac++] = c;
  1247. 16429             }
  1248. .Op 147 src/lib/editline/editline.c
  1249. 16430         }
  1250. 16431         else
  1251. 16432             c++;
  1252. 16433     }
  1253. 16434     *c = '';
  1254. 16435     p[ac] = NULL;
  1255. 16436     return ac;
  1256. 16437 }
  1257. 16439 STATIC STATUS
  1258. 16440 last_argument()
  1259. 16441 {
  1260. 16442     CHAR        **av;
  1261. 16443     CHAR        *p;
  1262. 16444     STATUS      s;
  1263. 16445     int         ac;
  1264. 16446
  1265. 16447     if (H.Size == 1 || (p = H.Lines[H.Size - 2]) == NULL)
  1266. 16448         return ring_bell();
  1267. 16449
  1268. 16450     if ((p = (CHAR *)strdup((char *)p)) == NULL)
  1269. 16451         return CSstay;
  1270. 16452     ac = argify(p, &av);
  1271. 16453
  1272. 16454     if (Repeat != NO_ARG)
  1273. 16455         s = Repeat < ac ? insert_string(av[Repeat]) : ring_bell();
  1274. 16456     else
  1275. 16457         s = ac ? insert_string(av[ac - 1]) : CSstay;
  1276. 16458
  1277. 16459     if (ac)
  1278. 16460         DISPOSE(av);
  1279. 16461     DISPOSE(p);
  1280. 16462     return s;
  1281. 16463 }
  1282. 16465 STATIC KEYMAP   Map[33] = {
  1283. 16466     {   CTL('@'),       mk_set          },
  1284. 16467     {   CTL('A'),       beg_line        },
  1285. 16468     {   CTL('B'),       bk_char         },
  1286. 16469     {   CTL('D'),       del_char        },
  1287. 16470     {   CTL('E'),       end_line        },
  1288. 16471     {   CTL('F'),       fd_char         },
  1289. 16472     {   CTL('G'),       ring_bell       },
  1290. 16473     {   CTL('H'),       bk_del_char     },
  1291. 16474     {   CTL('I'),       c_complete      },
  1292. 16475     {   CTL('J'),       accept_line     },
  1293. 16476     {   CTL('K'),       kill_line       },
  1294. 16477     {   CTL('L'),       redisplay       },
  1295. 16478     {   CTL('M'),       accept_line     },
  1296. 16479     {   CTL('N'),       h_next          },
  1297. 16480     {   CTL('O'),       ring_bell       },
  1298. 16481     {   CTL('P'),       h_prev          },
  1299. 16482     {   CTL('Q'),       ring_bell       },
  1300. 16483     {   CTL('R'),       h_search        },
  1301. 16484     {   CTL('S'),       ring_bell       },
  1302. 16485     {   CTL('T'),       transpose       },
  1303. 16486     {   CTL('U'),       ring_bell       },
  1304. 16487     {   CTL('V'),       quote           },
  1305. 16488     {   CTL('W'),       bk_kill_word    },
  1306. 16489     {   CTL('X'),       exchange        },
  1307. .Ep 148 src/lib/editline/editline.c
  1308. 16490     {   CTL('Y'),       yank            },
  1309. 16491     {   CTL('Z'),       end_line        },
  1310. 16492     {   CTL('['),       meta            },
  1311. 16493     {   CTL(']'),       move_to_char    },
  1312. 16494     {   CTL('^'),       ring_bell       },
  1313. 16495     {   CTL('_'),       ring_bell       },
  1314. 16496     {   0,              NULL            }
  1315. 16497 };
  1316. 16498
  1317. 16499 STATIC KEYMAP   MetaMap[17]= {
  1318. 16500     {   CTL('H'),       wipe            },
  1319. 16501     {   DEL,            wipe            },
  1320. 16502     {   ' ',            mk_set          },
  1321. 16503     {   '.',            last_argument   },
  1322. 16504     {   '<',            h_first         },
  1323. 16505     {   '>',            h_last          },
  1324. 16506     {   '?',            c_possible      },
  1325. 16507     {   'b',            bk_word         },
  1326. 16508     {   'd',            fd_kill_word    },
  1327. 16509     {   'f',            fd_word         },
  1328. 16510     {   'l',            case_down_word  },
  1329. 16511     {   'm',            toggle_meta_mode },
  1330. 16512     {   'u',            case_up_word    },
  1331. 16513     {   'y',            yank            },
  1332. 16514     {   'w',            copy_region     },
  1333. 16515     {   0,              NULL            }
  1334. 16516 };
  1335. ++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++
  1336. src/lib/editline/sysos9.c    
  1337. ++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++
  1338. 16600 /*  $Revision: 1.1 $
  1339. 16601 **
  1340. 16602 **  OS-9 system-dependant routines for editline library.
  1341. 16603 */
  1342. 16604 #include "editline.h"
  1343. 16605 #include <sgstat.h>
  1344. 16606 #include <modes.h>
  1345. 16607
  1346. 16608
  1347. 16609 void
  1348. 16610 rl_ttyset(Reset)
  1349. 16611     int                 Reset;
  1350. 16612 {
  1351. 16613     static struct sgbuf old;
  1352. 16614     struct sgbuf        new;
  1353. 16615
  1354. 16616
  1355. 16617     if (Reset == 0) {
  1356. 16618         _gs_opt(0, &old);
  1357. 16619         _gs_opt(0, &new);
  1358. 16620         new.sg_backsp = 0;      new.sg_delete = 0;      new.sg_echo = 0;
  1359. 16621         new.sg_alf = 0;         new.sg_nulls = 0;       new.sg_pause = 0;
  1360. 16622         new.sg_page = 0;        new.sg_bspch = 0;       new.sg_dlnch = 0;
  1361. 16623         new.sg_eorch = 0;       new.sg_eofch = 0;       new.sg_rlnch = 0;
  1362. 16624         new.sg_dulnch = 0;      new.sg_psch = 0;        new.sg_kbich = 0;
  1363. .Op 149 src/lib/editline/sysos9.c
  1364. 16625         new.sg_kbach = 0;       new.sg_bsech = 0;       new.sg_bellch = 0;
  1365. 16626         new.sg_xon = 0;         new.sg_xoff = 0;        new.sg_tabcr = 0;
  1366. 16627         new.sg_tabsiz = 0;
  1367. 16628         _ss_opt(0, &new);
  1368. 16629         rl_erase = old.sg_bspch;
  1369. 16630         rl_kill = old.sg_dlnch;
  1370. 16631         rl_eof = old.sg_eofch;
  1371. 16632         rl_intr = old.sg_kbich;
  1372. 16633         rl_quit = -1;
  1373. 16634     }
  1374. 16635     else
  1375. 16636         _ss_opt(0, &old);
  1376. 16637 }
  1377. 16639 void
  1378. 16640 rl_add_slash(path, p)
  1379. 16641     char        *path;
  1380. 16642     char        *p;
  1381. 16643 {
  1382. 16644     (void)strcat(p, access(path, S_IREAD | S_IFDIR) ? " " : "/");
  1383. 16645 }
  1384. ++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++
  1385. src/lib/editline/sysunix.c    
  1386. ++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++
  1387. 16700 /*  $Revision: 1.2 $
  1388. 16701 **
  1389. 16702 **  Unix system-dependant routines for editline library.
  1390. 16703 */
  1391. 16704 #include "editline.h"
  1392. 16705
  1393. 16706 #if     defined(HAVE_TCGETATTR)
  1394. 16707 #include <termios.h>
  1395. 16708
  1396. 16709 void
  1397. 16710 rl_ttyset(Reset)
  1398. 16711     int                         Reset;
  1399. 16712 {
  1400. 16713     static struct termios       old;
  1401. 16714     struct termios              new;
  1402. 16715
  1403. 16716     if (Reset == 0) {
  1404. 16717         (void)tcgetattr(0, &old);
  1405. 16718         rl_erase = old.c_cc[VERASE];
  1406. 16719         rl_kill = old.c_cc[VKILL];
  1407. 16720         rl_eof = old.c_cc[VEOF];
  1408. 16721         rl_intr = old.c_cc[VINTR];
  1409. 16722         rl_quit = old.c_cc[VQUIT];
  1410. 16723
  1411. 16724         new = old;
  1412. 16725         new.c_lflag &= ~(ECHO | ICANON | ISIG | IEXTEN);
  1413. 16726         new.c_cc[VMIN] = 1;
  1414. 16727         new.c_cc[VTIME] = 0;
  1415. 16728         (void)tcsetattr(0, TCSADRAIN, &new);
  1416. 16729     }
  1417. .Ep 150 src/lib/editline/sysunix.c
  1418. 16730     else
  1419. 16731         (void)tcsetattr(0, TCSADRAIN, &old);
  1420. 16732 }
  1421. 16734 #else
  1422. 16735 #if     defined(HAVE_TERMIO)
  1423. 16736 #include <termio.h>
  1424. 16737
  1425. 16738 void
  1426. 16739 rl_ttyset(Reset)
  1427. 16740     int                         Reset;
  1428. 16741 {
  1429. 16742     static struct termio        old;
  1430. 16743     struct termio               new;
  1431. 16744
  1432. 16745     if (Reset == 0) {
  1433. 16746         (void)ioctl(0, TCGETA, &old);
  1434. 16747         rl_erase = old.c_cc[VERASE];
  1435. 16748         rl_kill = old.c_cc[VKILL];
  1436. 16749         rl_eof = old.c_cc[VEOF];
  1437. 16750         rl_intr = old.c_cc[VINTR];
  1438. 16751         rl_quit = old.c_cc[VQUIT];
  1439. 16752
  1440. 16753         new = old;
  1441. 16754         new.c_cc[VINTR] = -1;
  1442. 16755         new.c_cc[VQUIT] = -1;
  1443. 16756         new.c_lflag &= ~(ECHO | ICANON);
  1444. 16757         new.c_cc[VMIN] = 1;
  1445. 16758         new.c_cc[VTIME] = 0;
  1446. 16759         (void)ioctl(0, TCSETAW, &new);
  1447. 16760     }
  1448. 16761     else
  1449. 16762         (void)ioctl(0, TCSETAW, &old);
  1450. 16763 }
  1451. 16765 #else
  1452. 16766 #include <sgtty.h>
  1453. 16767
  1454. 16768 void
  1455. 16769 rl_ttyset(Reset)
  1456. 16770     int                         Reset;
  1457. 16771 {
  1458. 16772     static struct sgttyb        old_sgttyb;
  1459. 16773     static struct tchars        old_tchars;
  1460. 16774     struct sgttyb               new_sgttyb;
  1461. 16775     struct tchars               new_tchars;
  1462. 16776
  1463. 16777     if (Reset == 0) {
  1464. 16778         (void)ioctl(0, TIOCGETP, &old_sgttyb);
  1465. 16779         rl_erase = old_sgttyb.sg_erase;
  1466. 16780         rl_kill = old_sgttyb.sg_kill;
  1467. 16781
  1468. 16782         (void)ioctl(0, TIOCGETC, &old_tchars);
  1469. 16783         rl_eof = old_tchars.t_eofc;
  1470. 16784         rl_intr = old_tchars.t_intrc;
  1471. 16785         rl_quit = old_tchars.t_quitc;
  1472. 16786
  1473. 16787         new_sgttyb = old_sgttyb;
  1474. 16788         new_sgttyb.sg_flags &= ~ECHO;
  1475. 16789         new_sgttyb.sg_flags |= RAW;
  1476. .Op 151 src/lib/editline/sysunix.c
  1477. 16790         (void)ioctl(0, TIOCSETP, &new_sgttyb);
  1478. 16791
  1479. 16792         new_tchars = old_tchars;
  1480. 16793         new_tchars.t_intrc = -1;
  1481. 16794         new_tchars.t_quitc = -1;
  1482. 16795         (void)ioctl(0, TIOCSETC, &new_tchars);
  1483. 16796     }
  1484. 16797     else {
  1485. 16798         (void)ioctl(0, TIOCSETP, &old_sgttyb);
  1486. 16799         (void)ioctl(0, TIOCSETC, &old_tchars);
  1487. 16800     }
  1488. 16801 }
  1489. 16802 #endif  /* defined(HAVE_TERMIO) */
  1490. 16803 #endif  /* defined(HAVE_TCGETATTR) */
  1491. 16804
  1492. 16805 void
  1493. 16806 rl_add_slash(path, p)
  1494. 16807     char        *path;
  1495. 16808     char        *p;
  1496. 16809 {
  1497. 16810     struct stat Sb;
  1498. 16811
  1499. 16812     if (stat(path, &Sb) >= 0)
  1500. 16813         (void)strcat(p, S_ISDIR(Sb.st_mode) ? "/" : " ");
  1501. 16814 }
  1502. ++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++
  1503. src/lib/editline/testit.c    
  1504. ++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++
  1505. 16900 /*  $Revision: 1.3 $
  1506. 16901 **
  1507. 16902 **  A "micro-shell" to test editline library.
  1508. 16903 **  If given any arguments, commands aren't executed.
  1509. 16904 */
  1510. 16905 #include <stdio.h>
  1511. 16906 #if     defined(HAVE_STDLIB)
  1512. 16907 #include <stdlib.h>
  1513. 16908 #endif  /* defined(HAVE_STDLIB) */
  1514. 16909
  1515. 16910 extern char     *readline();
  1516. 16911 extern void     add_history();
  1517. 16912
  1518. 16913 #if     !defined(HAVE_STDLIB)
  1519. 16914 extern int      chdir();
  1520. 16915 extern int      free();
  1521. 16916 extern int      strncmp();
  1522. 16917 extern int      system();
  1523. 16918 extern void     exit();
  1524. 16919 extern char     *getenv();
  1525. 16920 #endif  /* !defined(HAVE_STDLIB) */
  1526. 16921
  1527. 16922
  1528. 16923 #if     defined(NEED_PERROR)
  1529. 16924 void
  1530. .Ep 152 src/lib/editline/testit.c
  1531. 16925 perror(s)
  1532. 16926     char        *s;
  1533. 16927 {
  1534. 16928     extern int  errno;
  1535. 16929
  1536. 16930     (voidf)printf(stderr, "%s: error %dn", s, errno);
  1537. 16931 }
  1538. 16932 #endif  /* defined(NEED_PERROR) */
  1539. 16933
  1540. 16934
  1541. 16935 /* ARGSUSED1 */
  1542. 16936 int
  1543. 16937 main(ac, av)
  1544. 16938     int         ac;
  1545. 16939     char        *av[];
  1546. 16940 {
  1547. 16941     char        *prompt;
  1548. 16942     char        *p;
  1549. 16943     int         doit;
  1550. 16944
  1551. 16945     doit = ac == 1;
  1552. 16946     if ((prompt = getenv("TESTPROMPT")) == NULL)
  1553. 16947         prompt = "testit>  ";
  1554. 16948
  1555. 16949     while ((p = readline(prompt)) != NULL) {
  1556. 16950         (void)printf("ttt|%s|n", p);
  1557. 16951         if (doit)
  1558. 16952             if (strncmp(p, "cd ", 3) == 0) {
  1559. 16953                 if (chdir(&p[3]) < 0)
  1560. 16954                     perror(&p[3]);
  1561. 16955             }
  1562. 16956             else if (system(p) != 0)
  1563. 16957                 perror(p);
  1564. 16958         add_history(p);
  1565. 16959         free(p);
  1566. 16960     }
  1567. 16961     exit(0);
  1568. 16962     /* NOTREACHED */
  1569. 16963 }
  1570. ++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++
  1571. src/lib/end/edata.s    
  1572. ++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++
  1573. 17000 #
  1574. 17001 .sect .text
  1575. 17002 .sect .rom
  1576. 17003 .sect .data
  1577. 17004 .sect .bss
  1578. 17005 .define _edata
  1579. 17006 .sect .data
  1580. 17007         .align _EM_WSIZE
  1581. 17008 _edata:
  1582. .Op 153 src/lib/end/em_end.s
  1583. ++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++
  1584. src/lib/end/em_end.s    
  1585. ++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++
  1586. 17100 #
  1587. 17101 .sect .text
  1588. 17102 .sect .rom
  1589. 17103 .sect .data
  1590. 17104 .sect .bss
  1591. 17105 .define endtext,enddata,endbss,__end
  1592. 17106 .sect .text
  1593. 17107         .align _EM_WSIZE
  1594. 17108 .sect .rom
  1595. 17109         .align _EM_WSIZE
  1596. 17110 .sect .data
  1597. 17111         .align _EM_WSIZE
  1598. 17112 .sect .bss
  1599. 17113         .align _EM_WSIZE
  1600. 17114 .sect .end ! only for declaration of _end, __end and endbss.
  1601. 17115
  1602. 17116         .sect .text
  1603. 17117 endtext:
  1604. 17118         .sect .rom
  1605. 17119 endrom:
  1606. 17120         .sect .data
  1607. 17121 enddata:
  1608. 17122         .sect .end
  1609. 17123 __end:
  1610. 17124 endbss:
  1611. ++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++
  1612. src/lib/end/end.s    
  1613. ++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++
  1614. 17200 .sect .text
  1615. 17201 .sect .rom
  1616. 17202 .sect .data
  1617. 17203 .sect .bss
  1618. 17204 .define _end
  1619. 17205 .sect .end ! only for declaration of _end, __end and endbss.
  1620. 17206 _end:
  1621. .Ep 154 src/lib/end/etext.s
  1622. ++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++
  1623. src/lib/end/etext.s    
  1624. ++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++
  1625. 17300 #
  1626. 17301 .sect .text
  1627. 17302 .sect .rom
  1628. 17303 .sect .data
  1629. 17304 .sect .bss
  1630. 17305 .define _etext
  1631. 17306 .sect .text
  1632. 17307         .align _EM_WSIZE
  1633. 17308         .sect .text
  1634. 17309 _etext:
  1635. ++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++
  1636. src/lib/float/FP_bias.h    
  1637. ++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++
  1638. 17400 /*
  1639. 17401   (c) copyright 1988 by the Vrije Universiteit, Amsterdam, The Netherlands.
  1640. 17402   See the copyright notice in the ACK home directory, in the file "Copyright".
  1641. 17403 */
  1642. 17404
  1643. 17405 /* $Header: FP_bias.h,v 1.4 89/07/25 14:16:55 ceriel Exp $ */
  1644. 17406
  1645. 17407 /*
  1646. 17408         include file for floating point package
  1647. 17409 */
  1648. 17410
  1649. 17411                 /*      FLOAT FORMAT EXPONENT BIAS      */
  1650. 17412
  1651. 17413 #define SGL_BIAS         127    /* excess  128 notation used    */
  1652. 17414 #define DBL_BIAS        1023    /* excess 1024 notation used    */
  1653. 17415 #define EXT_BIAS           0    /* 2s-complement notation used  */
  1654. 17416                                 /* this is possible because the */
  1655. 17417                                 /* sign is in a seperate word   */
  1656. 17418                 
  1657. 17419                 /*      VARIOUS MAX AND MIN VALUES      */
  1658. 17420                 /*      1) FOR THE DIFFERENT FORMATS    */
  1659. 17421
  1660. 17422 #define SGL_MAX            254  /*      standard definition     */
  1661. 17423 #define SGL_MIN              1  /*      standard definition     */
  1662. 17424 #define DBL_MAX           2046  /*      standard definition     */
  1663. 17425 #define DBL_MIN              1  /*      standard definition     */
  1664. 17426 #define EXT_MAX          16383  /*      standard minimum        */
  1665. 17427 #define EXT_MIN         -16382  /*      standard minimum        */
  1666. .Op 155 src/lib/float/FP_shift.h
  1667. ++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++
  1668. src/lib/float/FP_shift.h    
  1669. ++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++
  1670. 17500 /*
  1671. 17501   (c) copyright 1988 by the Vrije Universiteit, Amsterdam, The Netherlands.
  1672. 17502   See the copyright notice in the ACK home directory, in the file "Copyright".
  1673. 17503 */
  1674. 17504
  1675. 17505 /* $Header: FP_shift.h,v 1.3 89/07/25 14:17:04 ceriel Exp $ */
  1676. 17506
  1677. 17507 /*
  1678. 17508         include file for floating point package
  1679. 17509 */
  1680. 17510
  1681. 17511 # define        CARRYBIT        0x80000000L
  1682. 17512 # define        NORMBIT         0x80000000L
  1683. 17513 # define        EXP_STORE       16
  1684. 17514
  1685. 17515
  1686. 17516                                 /* parameters for Single Precision */
  1687. 17517 #define SGL_EXPSHIFT    7
  1688. 17518 #define SGL_M1LEFT      8
  1689. 17519 #define SGL_ZERO        0xffffff80L
  1690. 17520 #define SGL_EXACT       0xff
  1691. 17521 #define SGL_RUNPACK     SGL_M1LEFT
  1692. 17522
  1693. 17523 #define SGL_ROUNDUP     0x80
  1694. 17524 #define SGL_CARRYOUT    0x01000000L
  1695. 17525 #define SGL_MASK        0x007fffffL
  1696. 17526
  1697. 17527                                 /* parameters for Double Precision */
  1698. 17528                                 /* used in extend.c */
  1699. 17529
  1700. 17530 #define DBL_EXPSHIFT    4
  1701. 17531
  1702. 17532 #define DBL_M1LEFT      11
  1703. 17533
  1704. 17534 #define DBL_RPACK       (32-DBL_M1LEFT)
  1705. 17535 #define DBL_LPACK       DBL_M1LEFT
  1706. 17536
  1707. 17537                                 /* used in compact.c */
  1708. 17538
  1709. 17539 #define DBL_ZERO        0xfffffd00L
  1710. 17540
  1711. 17541 #define DBL_EXACT       0x7ff
  1712. 17542
  1713. 17543 #define DBL_RUNPACK     DBL_M1LEFT
  1714. 17544 #define DBL_LUNPACK     (32-DBL_RUNPACK)
  1715. 17545
  1716. 17546 #define DBL_ROUNDUP     0x400
  1717. 17547 #define DBL_CARRYOUT    0x00200000L
  1718. 17548 #define DBL_MASK        0x000fffffL
  1719. .Ep 156 src/lib/float/FP_trap.h
  1720. ++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++
  1721. src/lib/float/FP_trap.h    
  1722. ++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++
  1723. 17600 /*
  1724. 17601   (c) copyright 1988 by the Vrije Universiteit, Amsterdam, The Netherlands.
  1725. 17602   See the copyright notice in the ACK home directory, in the file "Copyright".
  1726. 17603 */
  1727. 17604
  1728. 17605 /* $Header: FP_trap.h,v 1.2 88/04/07 11:33:06 ceriel Exp $ */
  1729. 17606
  1730. 17607 /*
  1731. 17608         include file for floating point package
  1732. 17609 */
  1733. 17610
  1734. 17611                         /*      EM TRAPS        */
  1735. 17612
  1736. 17613 #define EIOVFL  3       /* Integer  Overflow            */
  1737. 17614 #define EFOVFL  4       /* Floating Overflow            */
  1738. 17615 #define EFUNFL  5       /* Floating Underflow           */
  1739. 17616 #define EIDIVZ  6       /* Integer  Divide by 0         */
  1740. 17617 #define EFDIVZ  7       /* Floating Divide by 0.0       */
  1741. 17618 #define EIUND   8       /* Integer  Undefined Number    */
  1742. 17619 #define EFUND   9       /* Floating Undefined Number    */
  1743. 17620 #define ECONV   10      /* Conversion Error             */
  1744. 17621 # define trap(x) _fptrp(x)
  1745. ++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++
  1746. src/lib/float/FP_types.h    
  1747. ++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++
  1748. 17700 /*
  1749. 17701   (c) copyright 1988 by the Vrije Universiteit, Amsterdam, The Netherlands.
  1750. 17702   See the copyright notice in the ACK home directory, in the file "Copyright".
  1751. 17703 */
  1752. 17704
  1753. 17705 /* $Header: FP_types.h,v 1.4 93/01/05 12:03:05 ceriel Exp $ */
  1754. 17706
  1755. 17707 /********************************************************/
  1756. 17708 /*
  1757. 17709         Type definitions for C Floating Point Package
  1758. 17710         include file for floating point package
  1759. 17711 */
  1760. 17712 /********************************************************/
  1761. 17713 /*
  1762. 17714         THESE STRUCTURES ARE USED TO ADDRESS THE INDIVIDUAL
  1763. 17715         PARTS OF THE FLOATING POINT NUMBER REPRESENTATIONS.
  1764. 17716
  1765. 17717         THREE STRUCTURES ARE DEFINED:
  1766. 17718                 SINGLE: single precision floating format
  1767. 17719                 DOUBLE: double precision floating format
  1768. 17720                 EXTEND: double precision extended format
  1769. 17721 */
  1770. 17722 /********************************************************/
  1771. 17723
  1772. 17724 #ifndef __FPTYPES
  1773. .Op 157 src/lib/float/FP_types.h
  1774. 17725 #define __FPTYPES
  1775. 17726
  1776. 17727 typedef struct  {
  1777. 17728         unsigned long   h_32;   /* higher 32 bits of 64 */
  1778. 17729         unsigned long   l_32;   /* lower  32 bits of 64 */
  1779. 17730 }       B64;
  1780. 17731
  1781. 17732 typedef unsigned long   SINGLE;
  1782. 17733
  1783. 17734 typedef struct  {
  1784. 17735         unsigned long   d[2];
  1785. 17736 }       DOUBLE;
  1786. 17737
  1787. 17738 typedef struct  {       /* expanded float format        */
  1788. 17739         short   sign;
  1789. 17740         short   exp;
  1790. 17741         B64     mantissa;
  1791. 17742 #define m1 mantissa.h_32
  1792. 17743 #define m2 mantissa.l_32
  1793. 17744 } EXTEND;
  1794. 17745
  1795. 17746 struct  fef4_returns {
  1796. 17747         int     e;
  1797. 17748         SINGLE  f;
  1798. 17749 };
  1799. 17750
  1800. 17751 struct  fef8_returns {
  1801. 17752         int     e;
  1802. 17753         DOUBLE  f;
  1803. 17754 };
  1804. 17755
  1805. 17756 struct fif4_returns {
  1806. 17757         SINGLE ipart;
  1807. 17758         SINGLE fpart;
  1808. 17759 };
  1809. 17760
  1810. 17761 struct fif8_returns {
  1811. 17762         DOUBLE ipart;
  1812. 17763         DOUBLE fpart;
  1813. 17764 };
  1814. 17765
  1815. 17766 #if __STDC__
  1816. 17767 #define _PROTOTYPE(function, params)    function params
  1817. 17768 #else
  1818. 17769 #define _PROTOTYPE(function, params)    function()
  1819. 17770 #endif
  1820. 17771 _PROTOTYPE( void add_ext, (EXTEND *e1, EXTEND *e2));
  1821. 17772 _PROTOTYPE( void mul_ext, (EXTEND *e1, EXTEND *e2));
  1822. 17773 _PROTOTYPE( void div_ext, (EXTEND *e1, EXTEND *e2));
  1823. 17774 _PROTOTYPE( void sub_ext, (EXTEND *e1, EXTEND *e2));
  1824. 17775 _PROTOTYPE( void sft_ext, (EXTEND *e1, EXTEND *e2));
  1825. 17776 _PROTOTYPE( void nrm_ext, (EXTEND *e1));
  1826. 17777 _PROTOTYPE( void zrf_ext, (EXTEND *e1));
  1827. 17778 _PROTOTYPE( void extend, (unsigned long *from, EXTEND *to, int size));
  1828. 17779 _PROTOTYPE( void compact, (EXTEND *from, unsigned long *to, int size));
  1829. 17780 _PROTOTYPE( void _fptrp, (int));
  1830. 17781 _PROTOTYPE( void adf4, (SINGLE s2, SINGLE s1));
  1831. 17782 _PROTOTYPE( void adf8, (DOUBLE s2, DOUBLE s1));
  1832. 17783 _PROTOTYPE( void sbf4, (SINGLE s2, SINGLE s1));
  1833. 17784 _PROTOTYPE( void sbf8, (DOUBLE s2, DOUBLE s1));
  1834. .Ep 158 src/lib/float/FP_types.h
  1835. 17785 _PROTOTYPE( void dvf4, (SINGLE s2, SINGLE s1));
  1836. 17786 _PROTOTYPE( void dvf8, (DOUBLE s2, DOUBLE s1));
  1837. 17787 _PROTOTYPE( void mlf4, (SINGLE s2, SINGLE s1));
  1838. 17788 _PROTOTYPE( void mlf8, (DOUBLE s2, DOUBLE s1));
  1839. 17789 _PROTOTYPE( void ngf4, (SINGLE f));
  1840. 17790 _PROTOTYPE( void ngf8, (DOUBLE f));
  1841. 17791 _PROTOTYPE( void zrf4, (SINGLE *l));
  1842. 17792 _PROTOTYPE( void zrf8, (DOUBLE *z));
  1843. 17793 _PROTOTYPE( void cff4, (DOUBLE src));
  1844. 17794 _PROTOTYPE( void cff8, (SINGLE src));
  1845. 17795 _PROTOTYPE( void cif4, (int ss, long src));
  1846. 17796 _PROTOTYPE( void cif8, (int ss, long src));
  1847. 17797 _PROTOTYPE( void cuf4, (int ss, long src));
  1848. 17798 _PROTOTYPE( void cuf8, (int ss, long src));
  1849. 17799 _PROTOTYPE( long cfu, (int ds, int ss, DOUBLE src));
  1850. 17800 _PROTOTYPE( long cfi, (int ds, int ss, DOUBLE src));
  1851. 17801 _PROTOTYPE( int cmf4, (SINGLE s2, SINGLE s1));
  1852. 17802 _PROTOTYPE( int cmf8, (DOUBLE d1, DOUBLE d2));
  1853. 17803 _PROTOTYPE( void fef4, (struct fef4_returns *r, SINGLE s1));
  1854. 17804 _PROTOTYPE( void fef8, (struct fef8_returns *r, DOUBLE s1));
  1855. 17805 _PROTOTYPE( void fif4, (struct fif4_returns *p, SINGLE x, SINGLE y));
  1856. 17806 _PROTOTYPE( void fif8, (struct fif8_returns *p, DOUBLE x, DOUBLE y));
  1857. 17807
  1858. 17808 _PROTOTYPE( void b64_sft, (B64 *, int));
  1859. 17809 _PROTOTYPE( void b64_lsft, (B64 *));
  1860. 17810 _PROTOTYPE( void b64_rsft, (B64 *));
  1861. 17811 _PROTOTYPE( int b64_add, (B64 *, B64 *));
  1862. 17812 #endif
  1863. ++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++
  1864. src/lib/float/adder.h    
  1865. ++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++
  1866. 17900 /*
  1867. 17901   (c) copyright 1988 by the Vrije Universiteit, Amsterdam, The Netherlands.
  1868. 17902   See the copyright notice in the ACK home directory, in the file "Copyright".
  1869. 17903 */
  1870. 17904
  1871. 17905 /* $Header: adder.h,v 1.2 92/02/20 18:20:25 philip Exp $ */
  1872. 17906
  1873. 17907 /*
  1874. 17908  *      include file for 32 & 64 bit addition
  1875. 17909  */
  1876. 17910
  1877. 17911 typedef struct  B64 {
  1878. 17912         unsigned long   h_32;   /* higher 32 bits of 64 */
  1879. 17913         unsigned long   l_32;   /* lower  32 bits of 64 */
  1880. 17914 }       B64;
  1881. .Op 159 src/lib/float/byte_order.h
  1882. ++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++
  1883. src/lib/float/byte_order.h    
  1884. ++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++
  1885. 18000 #define CHAR_UNSIGNED   0
  1886. 18001 #define MSB_AT_LOW_ADDRESS      0
  1887. 18002 #define MSW_AT_LOW_ADDRESS      0
  1888. 18003 #define FL_MSB_AT_LOW_ADDRESS   0
  1889. 18004 #define FL_MSW_AT_LOW_ADDRESS   0
  1890. 18005 #define FL_MSL_AT_LOW_ADDRESS   0
  1891. ++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++
  1892. src/lib/float/get_put.h    
  1893. ++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++
  1894. 18100 /*
  1895. 18101   (c) copyright 1988 by the Vrije Universiteit, Amsterdam, The Netherlands.
  1896. 18102   See the copyright notice in the ACK home directory, in the file "Copyright".
  1897. 18103 */
  1898. 18104
  1899. 18105 /* $Header: get_put.h,v 1.3 89/10/25 17:15:01 ceriel Exp $ */
  1900. 18106
  1901. 18107 #include <byte_order.h>
  1902. 18108
  1903. 18109 #if CHAR_UNSIGNED
  1904. 18110 #define Xchar(ch)       (ch)
  1905. 18111 #else
  1906. 18112 #define Xchar(ch)       ((ch) & 0377)
  1907. 18113 #endif
  1908. 18114
  1909. 18115 #define BYTES_REVERSED (MSB_AT_LOW_ADDRESS != FL_MSB_AT_LOW_ADDRESS)
  1910. 18116 #define WORDS_REVERSED (MSW_AT_LOW_ADDRESS != FL_MSW_AT_LOW_ADDRESS)
  1911. 18117 #define LONGS_REVERSED (FL_MSL_AT_LOW_ADDRESS)
  1912. 18118
  1913. 18119 #if BYTES_REVERSED
  1914. 18120 #define uget2(c)        (Xchar((c)[1]) | ((unsigned) Xchar((c)[0]) << 8))
  1915. 18121 #define Xput2(i, c)     (((c)[1] = (i)), ((c)[0] = (i) >> 8))
  1916. 18122 #define put2(i, c)      { register int j = (i); Xput2(j, c); }
  1917. 18123 #else
  1918. 18124 #define uget2(c)        (* ((unsigned short *) (c)))
  1919. 18125 #define Xput2(i, c)     (* ((short *) (c)) = (i))
  1920. 18126 #define put2(i, c)      Xput2(i, c)
  1921. 18127 #endif
  1922. 18128
  1923. 18129 #define get2(c)         ((short) uget2(c))
  1924. 18130
  1925. 18131 #if WORDS_REVERSED || BYTES_REVERSED
  1926. 18132 #define get4(c)         (uget2((c)+2) | ((long) uget2(c) << 16))
  1927. 18133 #define put4(l, c)      { register long x=(l); 
  1928. 18134                           Xput2((int)x,(c)+2); 
  1929. 18135                           Xput2((int)(x>>16),(c)); 
  1930. 18136                         }
  1931. 18137 #else
  1932. 18138 #define get4(c)         (* ((long *) (c)))
  1933. 18139 #define put4(l, c)      (* ((long *) (c)) = (l))
  1934. .Ep 160 src/lib/float/get_put.h
  1935. 18140 #endif
  1936. ++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++
  1937. src/lib/float/add_ext.c    
  1938. ++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++
  1939. 18200 /*
  1940. 18201   (c) copyright 1988 by the Vrije Universiteit, Amsterdam, The Netherlands.
  1941. 18202   See the copyright notice in the ACK home directory, in the file "Copyright".
  1942. 18203 */
  1943. 18204
  1944. 18205 /* $Header: add_ext.c,v 1.7 93/01/05 12:03:11 ceriel Exp $ */
  1945. 18206
  1946. 18207 /*
  1947. 18208         ADD TWO EXTENDED FORMAT NUMBERS
  1948. 18209 */
  1949. 18210
  1950. 18211 #include "FP_types.h"
  1951. 18212
  1952. 18213 void
  1953. 18214 add_ext(e1,e2)
  1954. 18215 register EXTEND *e1,*e2;
  1955. 18216 {
  1956. 18217         if ((e2->m1 | e2->m2) == 0L) {
  1957. 18218                 return;
  1958. 18219         }
  1959. 18220         if ((e1->m1 | e1->m2) == 0L) {
  1960. 18221                 *e1 = *e2;
  1961. 18222                 return;
  1962. 18223         }
  1963. 18224         sft_ext(e1, e2);        /* adjust mantissas to equal powers */
  1964. 18225         if (e1->sign != e2->sign) {
  1965. 18226                 /* e1 + e2 = e1 - (-e2) */
  1966. 18227                 if (e2->m1 > e1->m1 ||
  1967. 18228                     (e2->m1 == e1->m1 && e2->m2 > e1->m2)) {
  1968. 18229                         /*      abs(e2) > abs(e1) */
  1969. 18230                         EXTEND x;
  1970. 18231
  1971. 18232                         x = *e1;
  1972. 18233                         *e1 = *e2;
  1973. 18234                         if (x.m2 > e1->m2) {
  1974. 18235                                 e1->m1 -= 1;    /* carry in */
  1975. 18236                         }
  1976. 18237                         e1->m1 -= x.m1;
  1977. 18238                         e1->m2 -= x.m2;
  1978. 18239                 }
  1979. 18240                 else {
  1980. 18241                         if (e2->m2 > e1->m2)
  1981. 18242                                 e1->m1 -= 1;    /* carry in */
  1982. 18243                         e1->m1 -= e2->m1;
  1983. 18244                         e1->m2 -= e2->m2;
  1984. 18245                 }
  1985. 18246         }
  1986. 18247         else {
  1987. 18248                 if (b64_add(&e1->mantissa,&e2->mantissa)) {     /* addition carry */
  1988. 18249                         b64_rsft(&e1->mantissa);        /* shift mantissa one bit RIGHT */
  1989. .Op 161 src/lib/float/add_ext.c
  1990. 18250                         e1->m1 |= 0x80000000L;  /* set max bit  */
  1991. 18251                         e1->exp++;              /* increase the exponent */
  1992. 18252                 }
  1993. 18253         }
  1994. 18254         nrm_ext(e1);
  1995. 18255 }
  1996. ++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++
  1997. src/lib/float/adder.c    
  1998. ++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++
  1999. 18300 /*
  2000. 18301   (c) copyright 1988 by the Vrije Universiteit, Amsterdam, The Netherlands.
  2001. 18302   See the copyright notice in the ACK home directory, in the file "Copyright".
  2002. 18303 */
  2003. 18304
  2004. 18305 /* $Header: adder.c,v 1.6 93/01/05 12:03:17 ceriel Exp $ */
  2005. 18306
  2006. 18307 /*
  2007. 18308  *      these are the routines the routines to do 32 and  64-bit addition
  2008. 18309  */
  2009. 18310
  2010. 18311 # ifdef EXT_DEBUG
  2011. 18312 # include <stdio.h>
  2012. 18313 # endif
  2013. 18314
  2014. 18315 # include "FP_types.h"
  2015. 18316 # define        UNKNOWN -1
  2016. 18317 # define        TRUE     1
  2017. 18318 # define        FALSE    0
  2018. 18319 # define        MAXBIT  0x80000000L
  2019. 18320
  2020. 18321         /*
  2021. 18322          *      add 64 bits
  2022. 18323          */
  2023. 18324 int
  2024. 18325 b64_add(e1,e2)
  2025. 18326                 /*
  2026. 18327                  * pointers to 64 bit 'registers'
  2027. 18328                  */
  2028. 18329 register        B64     *e1,*e2;
  2029. 18330 {
  2030. 18331                 register        int     overflow;
  2031. 18332                                 int     carry;
  2032. 18333
  2033. 18334                         /* add higher pair of 32 bits */
  2034. 18335         overflow = ((unsigned long) 0xFFFFFFFF - e1->h_32 < e2->h_32);
  2035. 18336         e1->h_32 += e2->h_32;
  2036. 18337
  2037. 18338                         /* add lower pair of 32 bits */
  2038. 18339         carry = ((unsigned long) 0xFFFFFFFF - e1->l_32 < e2->l_32);
  2039. 18340         e1->l_32 += e2->l_32;
  2040. 18341 # ifdef EXT_DEBUG
  2041. 18342         printf("tttttb64_add: overflow (%d); internal carry(%d)n",
  2042. 18343                                         overflow,carry);
  2043. 18344         fflush(stdout);
  2044. .Ep 162 src/lib/float/adder.c
  2045. 18345 # endif
  2046. 18346         if ((carry) && (++e1->h_32 == 0))
  2047. 18347                 return(TRUE);           /* had a 64 bit overflow */
  2048. 18348         return(overflow);               /* return status from higher add */
  2049. 18349 }
  2050. ++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++
  2051. src/lib/float/adf4.c    
  2052. ++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++
  2053. 18400 /*
  2054. 18401   (c) copyright 1988 by the Vrije Universiteit, Amsterdam, The Netherlands.
  2055. 18402   See the copyright notice in the ACK home directory, in the file "Copyright".
  2056. 18403 */
  2057. 18404
  2058. 18405 /* $Header: adf4.c,v 1.7 93/01/05 12:03:23 ceriel Exp $ */
  2059. 18406
  2060. 18407 /*
  2061. 18408         ADD TWO FLOATS - SINGLE (ADF 4)
  2062. 18409 */
  2063. 18410
  2064. 18411 #include        "FP_types.h"
  2065. 18412
  2066. 18413 void
  2067. 18414 adf4(s2,s1)
  2068. 18415 SINGLE  s1,s2;
  2069. 18416 {
  2070. 18417         EXTEND  e1,e2;
  2071. 18418         int     swap = 0;
  2072. 18419
  2073. 18420         if (s1 == (SINGLE) 0) {
  2074. 18421                 s1 = s2;
  2075. 18422                 return;
  2076. 18423         }
  2077. 18424         if (s2 == (SINGLE) 0) {
  2078. 18425                 return;
  2079. 18426         }
  2080. 18427         extend(&s1,&e1,sizeof(SINGLE));
  2081. 18428         extend(&s2,&e2,sizeof(SINGLE));
  2082. 18429         add_ext(&e1,&e2);
  2083. 18430         compact(&e1,&s1,sizeof(SINGLE));
  2084. 18431 }
  2085. .Op 163 src/lib/float/adf8.c
  2086. ++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++
  2087. src/lib/float/adf8.c    
  2088. ++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++
  2089. 18500 /*
  2090. 18501   (c) copyright 1988 by the Vrije Universiteit, Amsterdam, The Netherlands.
  2091. 18502   See the copyright notice in the ACK home directory, in the file "Copyright".
  2092. 18503 */
  2093. 18504
  2094. 18505 /* $Header: adf8.c,v 1.7 93/01/05 12:03:29 ceriel Exp $ */
  2095. 18506
  2096. 18507 /*
  2097. 18508         ADD TWO FLOATS - DOUBLE (ADF 8)
  2098. 18509 */
  2099. 18510
  2100. 18511 #include        "FP_types.h"
  2101. 18512
  2102. 18513 void
  2103. 18514 adf8(s2,s1)
  2104. 18515 DOUBLE  s1,s2;
  2105. 18516 {
  2106. 18517         EXTEND  e1,e2;
  2107. 18518
  2108. 18519         if (s1.d[0] == 0 && s1.d[1] == 0) {
  2109. 18520                 s1 = s2;
  2110. 18521                 return;
  2111. 18522         }
  2112. 18523         if (s2.d[0] == 0 && s2.d[1] == 0) {
  2113. 18524                 return;
  2114. 18525         }
  2115. 18526
  2116. 18527         extend(&s1.d[0],&e1,sizeof(DOUBLE));
  2117. 18528         extend(&s2.d[0],&e2,sizeof(DOUBLE));
  2118. 18529         add_ext(&e1,&e2);
  2119. 18530         compact(&e1,&s1.d[0],sizeof(DOUBLE));
  2120. 18531 }
  2121. ++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++
  2122. src/lib/float/cff4.c    
  2123. ++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++
  2124. 18600 /*
  2125. 18601   (c) copyright 1988 by the Vrije Universiteit, Amsterdam, The Netherlands.
  2126. 18602   See the copyright notice in the ACK home directory, in the file "Copyright".
  2127. 18603 */
  2128. 18604
  2129. 18605 /* $Header: cff4.c,v 1.5 93/01/05 12:03:36 ceriel Exp $ */
  2130. 18606
  2131. 18607 /*
  2132. 18608                 CONVERT DOUBLE TO SINGLE (CFF 8 4)
  2133. 18609
  2134. 18610         This routine works quite simply. A floating point
  2135. 18611         of size 08 is converted to extended format.
  2136. 18612         This extended variable is converted back to
  2137. 18613         a floating point of size 04.
  2138. 18614
  2139. .Ep 164 src/lib/float/cff4.c
  2140. 18615 */
  2141. 18616
  2142. 18617 #include        "FP_types.h"
  2143. 18618
  2144. 18619 void
  2145. 18620 cff4(src)
  2146. 18621 DOUBLE  src;    /* the source itself -  THIS TIME it's DOUBLE */
  2147. 18622 {
  2148. 18623         EXTEND  buf;
  2149. 18624
  2150. 18625         extend(&src.d[0],&buf,sizeof(DOUBLE));  /* no matter what */
  2151. 18626         compact(&buf,&(src.d[1]),sizeof(SINGLE));
  2152. 18627 }
  2153. ++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++
  2154. src/lib/float/cff8.c    
  2155. ++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++
  2156. 18700 /*
  2157. 18701   (c) copyright 1988 by the Vrije Universiteit, Amsterdam, The Netherlands.
  2158. 18702   See the copyright notice in the ACK home directory, in the file "Copyright".
  2159. 18703 */
  2160. 18704
  2161. 18705 /* $Header: cff8.c,v 1.5 93/01/05 12:03:41 ceriel Exp $ */
  2162. 18706
  2163. 18707 /*
  2164. 18708                 CONVERT SINGLE TO DOUBLE (CFF 4 8)
  2165. 18709
  2166. 18710         This routine works quite simply. A floating point
  2167. 18711         of size 04 is converted to extended format.
  2168. 18712         This extended variable is converted back to
  2169. 18713         a floating point of size 08.
  2170. 18714
  2171. 18715 */
  2172. 18716
  2173. 18717 #include "FP_types.h"
  2174. 18718
  2175. 18719 void
  2176. 18720 cff8(src)
  2177. 18721 SINGLE  src;
  2178. 18722 {
  2179. 18723         EXTEND  buf;
  2180. 18724
  2181. 18725         extend(&src,&buf,sizeof(SINGLE));       /* no matter what */
  2182. 18726         compact(&buf, &src,sizeof(DOUBLE));
  2183. 18727 }
  2184. .Op 165 src/lib/float/cfi.c
  2185. ++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++
  2186. src/lib/float/cfi.c    
  2187. ++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++
  2188. 18800 /*
  2189. 18801   (c) copyright 1988 by the Vrije Universiteit, Amsterdam, The Netherlands.
  2190. 18802   See the copyright notice in the ACK home directory, in the file "Copyright".
  2191. 18803 */
  2192. 18804
  2193. 18805 /* $Header: cfi.c,v 1.5 93/01/05 12:03:48 ceriel Exp $ */
  2194. 18806
  2195. 18807 /*
  2196. 18808                 CONVERT FLOAT TO SIGNED (CFI m n)
  2197. 18809
  2198. 18810                 N.B. The caller must know what it is getting.
  2199. 18811                      A LONG is always returned. If it is an
  2200. 18812                      integer the high byte is cleared first.
  2201. 18813 */
  2202. 18814
  2203. 18815 #include "FP_trap.h"
  2204. 18816 #include "FP_types.h"
  2205. 18817 #include "FP_shift.h"
  2206. 18818
  2207. 18819 long
  2208. 18820 cfi(ds,ss,src)
  2209. 18821 int     ds;     /* destination size (2 or 4) */
  2210. 18822 int     ss;     /* source size      (4 or 8) */
  2211. 18823 DOUBLE  src;    /* assume worst case */
  2212. 18824 {
  2213. 18825         EXTEND  buf;
  2214. 18826         long    new;
  2215. 18827         short   max_exp;
  2216. 18828
  2217. 18829         extend(&src.d[0],&buf,ss);      /* get extended format */
  2218. 18830         if (buf.exp < 0) {      /* no conversion needed */
  2219. 18831                 src.d[ss == 8] = 0L;
  2220. 18832                 return(0L);
  2221. 18833         }
  2222. 18834         max_exp = (ds << 3) - 2;        /* signed numbers */
  2223. 18835                                 /* have more limited max_exp */
  2224. 18836         if (buf.exp > max_exp) {
  2225. 18837                 if (buf.exp == max_exp+1 && buf.sign && buf.m1 == NORMBIT &&
  2226. 18838                     buf.m2 == 0L) {
  2227. 18839                 }
  2228. 18840                 else {
  2229. 18841                         trap(EIOVFL);   /* integer overflow     */
  2230. 18842                         buf.exp %= max_exp; /* truncate */
  2231. 18843                 }
  2232. 18844         }
  2233. 18845         new = buf.m1 >> (31-buf.exp);
  2234. 18846         if (buf.sign)
  2235. 18847                 new = -new;
  2236. 18848 done:
  2237. 18849         src.d[ss == 8] = new;
  2238. 18850         return(new);
  2239. 18851 }
  2240. .Ep 166 src/lib/float/cfu.c
  2241. ++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++
  2242. src/lib/float/cfu.c    
  2243. ++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++
  2244. 18900 /*
  2245. 18901   (c) copyright 1988 by the Vrije Universiteit, Amsterdam, The Netherlands.
  2246. 18902   See the copyright notice in the ACK home directory, in the file "Copyright".
  2247. 18903 */
  2248. 18904
  2249. 18905 /* $Header: cfu.c,v 1.5 93/01/05 12:03:55 ceriel Exp $ */
  2250. 18906
  2251. 18907 /*
  2252. 18908                 CONVERT FLOAT TO UNSIGNED (CFU m n)
  2253. 18909
  2254. 18910                 N.B. The caller must know what it is getting.
  2255. 18911                      A LONG is always returned. If it is an
  2256. 18912                      integer the high byte is cleared first.
  2257. 18913 */
  2258. 18914
  2259. 18915 #include "FP_trap.h"
  2260. 18916 #include "FP_types.h"
  2261. 18917
  2262. 18918 long
  2263. 18919 cfu(ds,ss,src)
  2264. 18920 int     ds;     /* destination size (2 or 4) */
  2265. 18921 int     ss;     /* source size      (4 or 8) */
  2266. 18922 DOUBLE  src;    /* assume worst case */
  2267. 18923 {
  2268. 18924         EXTEND  buf;
  2269. 18925         long    new;
  2270. 18926         short   newint, max_exp;
  2271. 18927
  2272. 18928         extend(&src.d[0],&buf,ss);      /* get extended format  */
  2273. 18929         if (buf.exp < 0) {      /* no conversion needed */
  2274. 18930                 src.d[ss == 8] = 0L;
  2275. 18931                 return(0L);
  2276. 18932         }
  2277. 18933         max_exp = (ds << 3) - 1;
  2278. 18934         if (buf.exp > max_exp) {
  2279. 18935                 trap(EIOVFL);   /* integer overflow     */
  2280. 18936                 buf.exp %= max_exp;
  2281. 18937         }
  2282. 18938         new = buf.m1 >> (31-buf.exp);
  2283. 18939 done:
  2284. 18940         src.d[ss == 8] = new;
  2285. 18941         return(new);
  2286. 18942 }
  2287. .Op 167 src/lib/float/cif4.c
  2288. ++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++
  2289. src/lib/float/cif4.c    
  2290. ++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++
  2291. 19000 /*
  2292. 19001   (c) copyright 1988 by the Vrije Universiteit, Amsterdam, The Netherlands.
  2293. 19002   See the copyright notice in the ACK home directory, in the file "Copyright".
  2294. 19003 */
  2295. 19004
  2296. 19005 /* $Header: cif4.c,v 1.5 93/01/05 12:04:01 ceriel Exp $ */
  2297. 19006
  2298. 19007 /*
  2299. 19008         CONVERT INTEGER TO SINGLE (CIF n 4)
  2300. 19009
  2301. 19010         THIS ROUTINE WORKS BY FILLING AN EXTENDED
  2302. 19011         WITH THE INTEGER VALUE IN EXTENDED FORMAT
  2303. 19012         AND USES COMPACT() TO PUT IT INTO THE PROPER
  2304. 19013         FLOATING POINT PRECISION.
  2305. 19014 */
  2306. 19015
  2307. 19016 #include "FP_types.h"
  2308. 19017
  2309. 19018 void
  2310. 19019 cif4(ss,src)
  2311. 19020 int     ss;     /* source size */
  2312. 19021 long    src;    /* largest possible integer to convert */
  2313. 19022 {
  2314. 19023         EXTEND  buf;
  2315. 19024         short   *ipt;
  2316. 19025         long    i_src;
  2317. 19026         SINGLE  *result;
  2318. 19027
  2319. 19028         zrf_ext(&buf);
  2320. 19029         if (ss == sizeof(long)) {
  2321. 19030                 buf.exp = 31;
  2322. 19031                 i_src = src;
  2323. 19032                 result = (SINGLE *) &src;
  2324. 19033         }
  2325. 19034         else    {
  2326. 19035                 ipt = (short *) &src;
  2327. 19036                 i_src = (long) *ipt;
  2328. 19037                 buf.exp = 15;
  2329. 19038                 result = (SINGLE *) &ss;
  2330. 19039         }
  2331. 19040         if (i_src == 0) {
  2332. 19041                 *result = (SINGLE) 0L;
  2333. 19042                 return;
  2334. 19043         }
  2335. 19044                         /* ESTABLISHED THAT src != 0    */
  2336. 19045                         /* adjust exponent field        */
  2337. 19046         buf.sign = (i_src < 0) ? 0x8000 : 0;
  2338. 19047                         /* clear sign bit of integer    */
  2339. 19048                         /* move to mantissa field       */
  2340. 19049         buf.m1 = (i_src < 0) ? -i_src : i_src;
  2341. 19050                         /* adjust mantissa field        */
  2342. 19051         if (ss != sizeof(long))
  2343. 19052                 buf.m1 <<= 16;
  2344. 19053         nrm_ext(&buf);          /* adjust mantissa field        */
  2345. 19054         compact(&buf, result,sizeof(SINGLE));   /* put on stack */
  2346. .Ep 168 src/lib/float/cif4.c
  2347. 19055 }
  2348. ++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++
  2349. src/lib/float/cif8.c    
  2350. ++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++
  2351. 19100 /*
  2352. 19101   (c) copyright 1988 by the Vrije Universiteit, Amsterdam, The Netherlands.
  2353. 19102   See the copyright notice in the ACK home directory, in the file "Copyright".
  2354. 19103 */
  2355. 19104
  2356. 19105 /* $Header: cif8.c,v 1.5 93/01/05 12:04:07 ceriel Exp $ */
  2357. 19106
  2358. 19107 /*
  2359. 19108         CONVERT INTEGER TO FLOAT (CIF n 8)
  2360. 19109
  2361. 19110         THIS ROUTINE WORKS BY FILLING AN EXTENDED
  2362. 19111         WITH THE INTEGER VALUE IN EXTENDED FORMAT
  2363. 19112         AND USES COMPACT() TO PUT IT INTO THE PROPER
  2364. 19113         FLOATING POINT PRECISION.
  2365. 19114 */
  2366. 19115
  2367. 19116 #include "FP_types.h"
  2368. 19117
  2369. 19118 void
  2370. 19119 cif8(ss,src)
  2371. 19120 int     ss;     /* source size */
  2372. 19121 long    src;    /* largest possible integer to convert */
  2373. 19122 {
  2374. 19123         EXTEND  buf;
  2375. 19124         DOUBLE  *result;        /* for return value */
  2376. 19125         short   *ipt;
  2377. 19126         long    i_src;
  2378. 19127
  2379. 19128         result = (DOUBLE *) ((void *) &ss);     /* always */
  2380. 19129         zrf_ext(&buf);
  2381. 19130         if (ss == sizeof(long)) {
  2382. 19131                 buf.exp = 31;
  2383. 19132                 i_src = src;
  2384. 19133         }
  2385. 19134         else    {
  2386. 19135                 ipt = (short *) &src;
  2387. 19136                 i_src = (long) *ipt;
  2388. 19137                 buf.exp = 15;
  2389. 19138         }
  2390. 19139         if (i_src == 0) {
  2391. 19140                 zrf8(result);
  2392. 19141                 return;
  2393. 19142         }
  2394. 19143                         /* ESTABLISHED THAT src != 0    */
  2395. 19144                         /* adjust exponent field        */
  2396. 19145         buf.sign = (i_src < 0) ? 0x8000 : 0;
  2397. 19146                         /* clear sign bit of integer    */
  2398. 19147                         /* move to mantissa field       */
  2399. 19148         buf.m1 = (i_src < 0) ? -i_src : i_src;
  2400. 19149                         /* adjust mantissa field        */
  2401. .Op 169 src/lib/float/cif8.c
  2402. 19150         if (ss != sizeof(long))
  2403. 19151                 buf.m1 <<= 16;
  2404. 19152         nrm_ext(&buf);
  2405. 19153         compact(&buf,&result->d[0],8);
  2406. 19154 }
  2407. ++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++
  2408. src/lib/float/cmf4.c    
  2409. ++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++
  2410. 19200 /*
  2411. 19201   (c) copyright 1988 by the Vrije Universiteit, Amsterdam, The Netherlands.
  2412. 19202   See the copyright notice in the ACK home directory, in the file "Copyright".
  2413. 19203 */
  2414. 19204
  2415. 19205 /* $Header: cmf4.c,v 1.6 93/01/05 12:04:14 ceriel Exp $ */
  2416. 19206
  2417. 19207 /*
  2418. 19208         COMPARE SINGLES (CMF 4)
  2419. 19209 */
  2420. 19210
  2421. 19211 #include        "FP_types.h"
  2422. 19212 #include        "get_put.h"
  2423. 19213
  2424. 19214 int
  2425. 19215 cmf4(f1,f2)
  2426. 19216 SINGLE  f1,f2;
  2427. 19217 {
  2428. 19218                 /*
  2429. 19219                  * return ((f1 < f2) ? 1 : (f1 - f2))
  2430. 19220                  */
  2431. 19221 #define SIGN(x) (((x) < 0) ? -1 : 1)
  2432. 19222         int     sign1,sign2;
  2433. 19223         long    l1,l2;
  2434. 19224
  2435. 19225         l1 = get4((char *) &f1);
  2436. 19226         l2 = get4((char *) &f2);
  2437. 19227
  2438. 19228         if (l1 == l2) return 0;
  2439. 19229
  2440. 19230         sign1 = SIGN(l1);
  2441. 19231         sign2 = SIGN(l2);
  2442. 19232         if (sign1 != sign2) {
  2443. 19233                 if ((l1 & 0x7fffffff) == 0 &&
  2444. 19234                     (l2 & 0x7fffffff) == 0) return 0;
  2445. 19235                 return ((sign1 > 0) ? -1 : 1);
  2446. 19236         }
  2447. 19237
  2448. 19238         return (sign1 * ((l1 < l2) ? 1 : -1));
  2449. 19239 }
  2450. .Ep 170 src/lib/float/cmf8.c
  2451. ++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++
  2452. src/lib/float/cmf8.c    
  2453. ++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++
  2454. 19300 /*
  2455. 19301   (c) copyright 1988 by the Vrije Universiteit, Amsterdam, The Netherlands.
  2456. 19302   See the copyright notice in the ACK home directory, in the file "Copyright".
  2457. 19303 */
  2458. 19304
  2459. 19305 /* $Header: cmf8.c,v 1.9 93/01/05 12:04:22 ceriel Exp $ */
  2460. 19306
  2461. 19307 /*
  2462. 19308         COMPARE DOUBLES (CMF 8)
  2463. 19309 */
  2464. 19310
  2465. 19311 #include        "FP_types.h"
  2466. 19312 #include        "get_put.h"
  2467. 19313
  2468. 19314 int
  2469. 19315 cmf8(d1,d2)
  2470. 19316 DOUBLE  d1,d2;
  2471. 19317 {
  2472. 19318 #define SIGN(x) (((x) < 0) ? -1 : 1)
  2473. 19319                 /*
  2474. 19320                  * return ((d1 < d2) ? 1 : (d1 > d2) ? -1 : 0))
  2475. 19321                  */
  2476. 19322         long    l1,l2;
  2477. 19323         int     sign1,sign2;
  2478. 19324         int     rv;
  2479. 19325
  2480. 19326 #if FL_MSL_AT_LOW_ADDRESS
  2481. 19327         l1 = get4((char *)&d1);
  2482. 19328         l2 = get4((char *)&d2);
  2483. 19329 #else
  2484. 19330         l1 = get4(((char *)&d1+4));
  2485. 19331         l2 = get4(((char *)&d2+4));
  2486. 19332 #endif
  2487. 19333         sign1 = SIGN(l1);
  2488. 19334         sign2 = SIGN(l2);
  2489. 19335         if (sign1 != sign2) {
  2490. 19336                 l1 &= 0x7fffffff;
  2491. 19337                 l2 &= 0x7fffffff;
  2492. 19338                 if (l1 != 0 || l2 != 0) {
  2493. 19339                         return ((sign1 > 0) ? -1 : 1);
  2494. 19340                 }
  2495. 19341         }
  2496. 19342         if (l1 != l2)   {       /* we can decide here */
  2497. 19343                 rv = l1 < l2 ? 1 : -1;
  2498. 19344         }
  2499. 19345         else    {               /* decide in 2nd half */
  2500. 19346                 unsigned long u1, u2;
  2501. 19347 #if FL_MSL_AT_LOW_ADDRESS
  2502. 19348                 u1 = get4(((char *)&d1 + 4));
  2503. 19349                 u2 = get4(((char *)&d2 + 4));
  2504. 19350 #else
  2505. 19351                 u1 = get4((char *)&d1);
  2506. 19352                 u2 = get4((char *)&d2);
  2507. 19353 #endif
  2508. 19354                 if (u1 == u2)
  2509. .Op 171 src/lib/float/cmf8.c
  2510. 19355                         return(0);
  2511. 19356                 if (u1 < u2) rv = 1;
  2512. 19357                 else rv = -1;
  2513. 19358         }
  2514. 19359         return sign1 * rv;
  2515. 19360 }
  2516. ++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++
  2517. src/lib/float/compact.c    
  2518. ++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++
  2519. 19400 /*
  2520. 19401   (c) copyright 1988 by the Vrije Universiteit, Amsterdam, The Netherlands.
  2521. 19402   See the copyright notice in the ACK home directory, in the file "Copyright".
  2522. 19403 */
  2523. 19404
  2524. 19405 /* $Header: compact.c,v 1.13 93/01/05 12:04:28 ceriel Exp $ */
  2525. 19406
  2526. 19407 /*
  2527. 19408         COMPACT EXTEND FORMAT INTO FLOAT OF PROPER SIZE
  2528. 19409 */
  2529. 19410
  2530. 19411 # include "FP_bias.h"
  2531. 19412 # include "FP_shift.h"
  2532. 19413 # include "FP_trap.h"
  2533. 19414 # include "FP_types.h"
  2534. 19415 # include "get_put.h"
  2535. 19416
  2536. 19417 void
  2537. 19418 compact(f,to,size)
  2538. 19419 EXTEND  *f;
  2539. 19420 unsigned long   *to;
  2540. 19421 int     size;
  2541. 19422 {
  2542. 19423         int     error = 0;
  2543. 19424
  2544. 19425         if (size == sizeof(DOUBLE)) {
  2545. 19426         /*
  2546. 19427          * COMPACT EXTENDED INTO DOUBLE
  2547. 19428          */
  2548. 19429                 DOUBLE *DBL = (DOUBLE *) (void *) to;
  2549. 19430
  2550. 19431                 if ((f->m1|(f->m2 & DBL_ZERO)) == 0L)   {
  2551. 19432                         zrf8(DBL);
  2552. 19433                         return;
  2553. 19434                 }
  2554. 19435                 f->exp += DBL_BIAS;     /* restore proper bias  */
  2555. 19436                 if (f->exp > DBL_MAX)   {
  2556. 19437 dbl_over:                       trap(EFOVFL);
  2557. 19438                         f->exp = DBL_MAX+1;
  2558. 19439                         f->m1 = 0;
  2559. 19440                         f->m2 = 0;
  2560. 19441                         if (error++)
  2561. 19442                                 return;
  2562. 19443                 }
  2563. 19444                 else if (f->exp < DBL_MIN)      {
  2564. .Ep 172 src/lib/float/compact.c
  2565. 19445                         b64_rsft(&(f->mantissa));
  2566. 19446                         if (f->exp < 0) {
  2567. 19447                                 b64_sft(&(f->mantissa), -f->exp);
  2568. 19448                                 f->exp = 0;
  2569. 19449                         }
  2570. 19450                         /* underflow ??? */
  2571. 19451                 }
  2572. 19452                         
  2573. 19453                 /* local CAST conversion                */
  2574. 19454
  2575. 19455                 /* because of special format shift only 10 bits */
  2576. 19456                 /* bit shift mantissa 10 bits           */
  2577. 19457
  2578. 19458                 /* first align within words, then do store operation */
  2579. 19459
  2580. 19460                 DBL->d[0] = f->m1 >> DBL_RUNPACK;   /* plus 22 == 32 */
  2581. 19461                 DBL->d[1] = f->m2 >> DBL_RUNPACK;   /* plus 22 == 32 */
  2582. 19462                 DBL->d[1] |= (f->m1 << DBL_LUNPACK); /* plus 10 == 32 */
  2583. 19463
  2584. 19464                 /* if not exact then round to nearest   */
  2585. 19465                 /* on a tie, round to even */
  2586. 19466
  2587. 19467 #ifdef EXCEPTION_INEXACT
  2588. 19468                 if ((f->m2 & DBL_EXACT) != 0) {
  2589. 19469                     INEXACT();
  2590. 19470 #endif
  2591. 19471                     if (((f->m2 & DBL_EXACT) > DBL_ROUNDUP)
  2592. 19472                         || ((f->m2 & DBL_EXACT) == DBL_ROUNDUP
  2593. 19473                             && (f->m2 & (DBL_ROUNDUP << 1)))) {
  2594. 19474                         DBL->d[1]++;    /* rounding up  */
  2595. 19475                         if (DBL->d[1] == 0L) { /* carry out     */
  2596. 19476                             DBL->d[0]++;
  2597. 19477
  2598. 19478                             if (f->exp == 0 && (DBL->d[0] & ~DBL_MASK)) {
  2599. 19479                                         f->exp++;
  2600. 19480                                 }
  2601. 19481                             if (DBL->d[0] & DBL_CARRYOUT) { /* carry out */
  2602. 19482                                 if (DBL->d[0] & 01)
  2603. 19483                                     DBL->d[1] = CARRYBIT;
  2604. 19484                                 DBL->d[0] >>= 1;
  2605. 19485                                 f->exp++;
  2606. 19486                             }
  2607. 19487                         }
  2608. 19488                         /*      check for overflow                      */
  2609. 19489                         if (f->exp > DBL_MAX)
  2610. 19490                                 goto dbl_over;
  2611. 19491                     }
  2612. 19492 #ifdef EXCEPTION_INEXACT
  2613. 19493                 }
  2614. 19494 #endif
  2615. 19495
  2616. 19496                 /*
  2617. 19497                  * STORE EXPONENT AND SIGN:
  2618. 19498                  *
  2619. 19499                  * 1) clear leading bits (B4-B15)
  2620. 19500                  * 2) shift and store exponent
  2621. 19501                  */
  2622. 19502
  2623. 19503                 DBL->d[0] &= DBL_MASK;
  2624. 19504                 DBL->d[0] |= 
  2625. .Op 173 src/lib/float/compact.c
  2626. 19505                         ((long) (f->exp << DBL_EXPSHIFT) << EXP_STORE);
  2627. 19506                 if (f->sign)
  2628. 19507                         DBL->d[0] |= CARRYBIT;
  2629. 19508
  2630. 19509                 /*
  2631. 19510                  * STORE MANTISSA
  2632. 19511                  */
  2633. 19512
  2634. 19513 #if FL_MSL_AT_LOW_ADDRESS
  2635. 19514                 put4(DBL->d[0], (char *) &DBL->d[0]);
  2636. 19515                 put4(DBL->d[1], (char *) &DBL->d[1]);
  2637. 19516 #else
  2638. 19517                 { unsigned long l;
  2639. 19518                   put4(DBL->d[1], (char *) &l);
  2640. 19519                   put4(DBL->d[0], (char *) &DBL->d[1]);
  2641. 19520                   DBL->d[0] = l;
  2642. 19521                 }
  2643. 19522 #endif
  2644. 19523         }
  2645. 19524         else {
  2646. 19525                 /*
  2647. 19526                  * COMPACT EXTENDED INTO FLOAT
  2648. 19527                  */
  2649. 19528                 SINGLE  *SGL;
  2650. 19529
  2651. 19530                 /* local CAST conversion                */
  2652. 19531                 SGL = (SINGLE *) (void *) to;
  2653. 19532                 if ((f->m1 & SGL_ZERO) == 0L)   {
  2654. 19533                         *SGL = 0L;
  2655. 19534                         return;
  2656. 19535                 }
  2657. 19536                 f->exp += SGL_BIAS;     /* restore bias */
  2658. 19537                 if (f->exp > SGL_MAX)   {
  2659. 19538 sgl_over:                       trap(EFOVFL);
  2660. 19539                         f->exp = SGL_MAX+1;
  2661. 19540                         f->m1 = 0L;
  2662. 19541                         f->m2 = 0L;
  2663. 19542                         if (error++)
  2664. 19543                                 return;
  2665. 19544                 }
  2666. 19545                 else if (f->exp < SGL_MIN)      {
  2667. 19546                         b64_rsft(&(f->mantissa));
  2668. 19547                         if (f->exp < 0) {
  2669. 19548                                 b64_sft(&(f->mantissa), -f->exp);
  2670. 19549                                 f->exp = 0;
  2671. 19550                         }
  2672. 19551                         /* underflow ??? */
  2673. 19552                 }
  2674. 19553
  2675. 19554                 /* shift mantissa and store     */
  2676. 19555                 *SGL = (f->m1 >> SGL_RUNPACK);
  2677. 19556
  2678. 19557                 /* check for rounding to nearest        */
  2679. 19558                 /* on a tie, round to even              */
  2680. 19559 #ifdef EXCEPTION_INEXACT
  2681. 19560                 if (f->m2 != 0 ||
  2682. 19561                     (f->m1 & SGL_EXACT) != 0L) {
  2683. 19562                         INEXACT();
  2684. 19563 #endif
  2685. 19564                         if (((f->m1 & SGL_EXACT) > SGL_ROUNDUP)
  2686. .Ep 174 src/lib/float/compact.c
  2687. 19565                             || ((f->m1 & SGL_EXACT) == SGL_ROUNDUP
  2688. 19566                                 && (f->m1 & (SGL_ROUNDUP << 1)))) {
  2689. 19567                                 (*SGL)++;
  2690. 19568                                 if (f->exp == 0 && (*SGL & ~SGL_MASK)) {
  2691. 19569                                         f->exp++;
  2692. 19570                                 }
  2693. 19571                         /* check normal */
  2694. 19572                                 if (*SGL & SGL_CARRYOUT)        {
  2695. 19573                                         *SGL >>= 1;
  2696. 19574                                         f->exp++;
  2697. 19575                                 }
  2698. 19576                                 if (f->exp > SGL_MAX)
  2699. 19577                                         goto sgl_over;
  2700. 19578                         }
  2701. 19579 #ifdef EXCEPTION_INEXACT
  2702. 19580                 }
  2703. 19581 #endif
  2704. 19582
  2705. 19583                 /*
  2706. 19584                  * STORE EXPONENT AND SIGN:
  2707. 19585                  *
  2708. 19586                  * 1) clear leading bit of fraction
  2709. 19587                  * 2) shift and store exponent
  2710. 19588                  */
  2711. 19589
  2712. 19590                 *SGL &= SGL_MASK; /* B23-B31 are 0 */
  2713. 19591                 *SGL |= ((long) (f->exp << SGL_EXPSHIFT) << EXP_STORE);
  2714. 19592                 if (f->sign)
  2715. 19593                         *SGL |= CARRYBIT;
  2716. 19594
  2717. 19595                 /*
  2718. 19596                  * STORE MANTISSA
  2719. 19597                  */
  2720. 19598
  2721. 19599                 put4(*SGL, (char *) &SGL);
  2722. 19600         }
  2723. 19601 }
  2724. ++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++
  2725. src/lib/float/cuf4.c    
  2726. ++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++
  2727. 19700 /*
  2728. 19701   (c) copyright 1988 by the Vrije Universiteit, Amsterdam, The Netherlands.
  2729. 19702   See the copyright notice in the ACK home directory, in the file "Copyright".
  2730. 19703 */
  2731. 19704
  2732. 19705 /* $Header: cuf4.c,v 1.6 93/01/05 12:04:35 ceriel Exp $ */
  2733. 19706
  2734. 19707 /*
  2735. 19708         CONVERT INTEGER TO SINGLE (CUF n 4)
  2736. 19709
  2737. 19710         THIS ROUTINE WORKS BY FILLING AN EXTENDED
  2738. 19711         WITH THE INTEGER VALUE IN EXTENDED FORMAT
  2739. 19712         AND USES COMPACT() TO PUT IT INTO THE PROPER
  2740. 19713         FLOATING POINT PRECISION.
  2741. 19714 */
  2742. .Op 175 src/lib/float/cuf4.c
  2743. 19715
  2744. 19716 #include "FP_types.h"
  2745. 19717
  2746. 19718 void
  2747. 19719 cuf4(ss,src)
  2748. 19720 int     ss;     /* source size */
  2749. 19721 long    src;    /* largest possible integer to convert */
  2750. 19722 {
  2751. 19723         EXTEND  buf;
  2752. 19724         short   *ipt;
  2753. 19725         SINGLE  *result;
  2754. 19726         long    i_src;
  2755. 19727
  2756. 19728         zrf_ext(&buf);
  2757. 19729         if (ss == sizeof(long)) {
  2758. 19730                 buf.exp = 31;
  2759. 19731                 i_src = src;
  2760. 19732                 result = (SINGLE *) &src;
  2761. 19733         }
  2762. 19734         else    {
  2763. 19735                 ipt = (short *) &src;
  2764. 19736                 i_src = (long) *ipt;
  2765. 19737                 buf.exp = 15;
  2766. 19738                 result = (SINGLE *) ((void *) &ss);
  2767. 19739         }
  2768. 19740         if (i_src == 0) {
  2769. 19741                 *result = (SINGLE) 0L;
  2770. 19742                 return;
  2771. 19743         }
  2772. 19744                         /* ESTABLISHED THAT src != 0    */
  2773. 19745
  2774. 19746                         /* adjust exponent field        */
  2775. 19747         if (ss != sizeof(long))
  2776. 19748                 i_src <<= 16;
  2777. 19749
  2778. 19750                         /* move to mantissa field       */
  2779. 19751         buf.m1 = i_src;
  2780. 19752
  2781. 19753                         /* adjust mantissa field        */
  2782. 19754         nrm_ext(&buf);
  2783. 19755         compact(&buf,result,4);
  2784. 19756 }
  2785. ++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++
  2786. src/lib/float/cuf8.c    
  2787. ++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++
  2788. 19800 /*
  2789. 19801   (c) copyright 1988 by the Vrije Universiteit, Amsterdam, The Netherlands.
  2790. 19802   See the copyright notice in the ACK home directory, in the file "Copyright".
  2791. 19803 */
  2792. 19804
  2793. 19805 /* $Header: cuf8.c,v 1.6 93/01/05 12:04:41 ceriel Exp $ */
  2794. 19806
  2795. 19807 /*
  2796. 19808         CONVERT INTEGER TO FLOAT (CUF n 8)
  2797. 19809
  2798. .Ep 176 src/lib/float/cuf8.c
  2799. 19810         THIS ROUTINE WORKS BY FILLING AN EXTENDED
  2800. 19811         WITH THE INTEGER VALUE IN EXTENDED FORMAT
  2801. 19812         AND USES COMPACT() TO PUT IT INTO THE PROPER
  2802. 19813         FLOATING POINT PRECISION.
  2803. 19814 */
  2804. 19815
  2805. 19816 #include "FP_types.h"
  2806. 19817
  2807. 19818 void
  2808. 19819 cuf8(ss,src)
  2809. 19820 int     ss;     /* source size */
  2810. 19821 long    src;    /* largest possible integer to convert */
  2811. 19822 {
  2812. 19823         EXTEND  buf;
  2813. 19824         short   *ipt;
  2814. 19825         long    i_src;
  2815. 19826
  2816. 19827         zrf_ext(&buf);
  2817. 19828         if (ss == sizeof(long)) {
  2818. 19829                 buf.exp = 31;
  2819. 19830                 i_src = src;
  2820. 19831         }
  2821. 19832         else    {
  2822. 19833                 ipt = (short *) &src;
  2823. 19834                 i_src = (long) *ipt;
  2824. 19835                 buf.exp = 15;
  2825. 19836         }
  2826. 19837         if (i_src == 0) {
  2827. 19838                 zrf8((DOUBLE *)((void *)&ss));
  2828. 19839                 return;
  2829. 19840         }
  2830. 19841                         /* ESTABLISHED THAT src != 0    */
  2831. 19842
  2832. 19843                         /* adjust exponent field        */
  2833. 19844         if (ss != sizeof(long))
  2834. 19845                 i_src <<= 16;
  2835. 19846
  2836. 19847                         /* move to mantissa field       */
  2837. 19848         buf.m1 = i_src;
  2838. 19849
  2839. 19850                         /* adjust mantissa field        */
  2840. 19851         nrm_ext(&buf);
  2841. 19852         compact(&buf,(unsigned long *) (void *)&ss,8);
  2842. 19853 }
  2843. ++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++
  2844. src/lib/float/div_ext.c    
  2845. ++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++
  2846. 19900 /*
  2847. 19901   (c) copyright 1988 by the Vrije Universiteit, Amsterdam, The Netherlands.
  2848. 19902   See the copyright notice in the ACK home directory, in the file "Copyright".
  2849. 19903 */
  2850. 19904
  2851. 19905 /* $Header: div_ext.c,v 1.10 93/01/05 12:04:47 ceriel Exp $ */
  2852. 19906
  2853. 19907 /*
  2854. 19908         DIVIDE EXTENDED FORMAT
  2855. 19909 */
  2856. .Op 177 src/lib/float/div_ext.c
  2857. 19910
  2858. 19911 #include "FP_bias.h"
  2859. 19912 #include "FP_trap.h"
  2860. 19913 #include "FP_types.h"
  2861. 19914
  2862. 19915 /*
  2863. 19916         November 15, 1984
  2864. 19917
  2865. 19918         This is a routine to do the work.
  2866. 19919         There are two versions: 
  2867. 19920         One is based on the partial products method
  2868. 19921         and makes no use possible machine instructions
  2869. 19922         to divide (hardware dividers).
  2870. 19923         The other is used when USE_DIVIDE is defined. It is much faster on
  2871. 19924         machines with fast 4 byte operations.
  2872. 19925 */
  2873. 19926 /********************************************************/
  2874. 19927
  2875. 19928 void
  2876. 19929 div_ext(e1,e2)
  2877. 19930 EXTEND  *e1,*e2;
  2878. 19931 {
  2879. 19932         short   error = 0;
  2880. 19933         B64             result;
  2881. 19934         register        unsigned long   *lp;
  2882. 19935 #ifndef USE_DIVIDE
  2883. 19936         short   count;
  2884. 19937 #else
  2885. 19938         unsigned short u[9], v[5];
  2886. 19939         register int j;
  2887. 19940         register unsigned short *u_p = u;
  2888. 19941         int maxv = 4;
  2889. 19942 #endif
  2890. 19943
  2891. 19944         if ((e2->m1 | e2->m2) == 0) {
  2892. 19945                 /*
  2893. 19946                  * Exception 8.2 - Divide by zero
  2894. 19947                  */
  2895. 19948                 trap(EFDIVZ);
  2896. 19949                 e1->m1 = e1->m2 = 0L;
  2897. 19950                 e1->exp = EXT_MAX;
  2898. 19951                 return;
  2899. 19952         }
  2900. 19953         if ((e1->m1 | e1->m2) == 0) {   /* 0 / anything == 0 */
  2901. 19954                 e1->exp = 0;    /* make sure */
  2902. 19955                 return;
  2903. 19956         }
  2904. 19957 #ifndef USE_DIVIDE
  2905. 19958         /*
  2906. 19959          * numbers are right shifted one bit to make sure
  2907. 19960          * that m1 is quaranteed to be larger if its
  2908. 19961          * maximum bit is set
  2909. 19962          */
  2910. 19963         b64_rsft(&e1->mantissa);        /* 64 bit shift right */
  2911. 19964         b64_rsft(&e2->mantissa);        /* 64 bit shift right */
  2912. 19965         e1->exp++;
  2913. 19966         e2->exp++;
  2914. 19967 #endif
  2915. 19968         /*      check for underflow, divide by zero, etc        */
  2916. 19969         e1->sign ^= e2->sign;
  2917. .Ep 178 src/lib/float/div_ext.c
  2918. 19970         e1->exp -= e2->exp;
  2919. 19971
  2920. 19972 #ifndef USE_DIVIDE
  2921. 19973                 /* do division of mantissas     */
  2922. 19974                 /* uses partial product method  */
  2923. 19975                 /* init control variables       */
  2924. 19976
  2925. 19977         count = 64;
  2926. 19978         result.h_32 = 0L;
  2927. 19979         result.l_32 = 0L;
  2928. 19980
  2929. 19981                 /* partial product division loop */
  2930. 19982
  2931. 19983         while (count--) {
  2932. 19984                 /* first left shift result 1 bit        */
  2933. 19985                 /* this is ALWAYS done                  */
  2934. 19986
  2935. 19987                 b64_lsft(&result);
  2936. 19988
  2937. 19989                 /* compare dividend and divisor         */
  2938. 19990                 /* if dividend >= divisor add a bit     */
  2939. 19991                 /* and subtract divisior from dividend  */
  2940. 19992
  2941. 19993                 if ( (e1->m1 < e2->m1) ||
  2942. 19994                         ((e1->m1 == e2->m1) && (e1->m2 < e2->m2) ))
  2943. 19995                         ;       /* null statement */
  2944. 19996                                 /* i.e., don't add or subtract */
  2945. 19997                 else    {
  2946. 19998                         result.l_32++;  /* ADD  */
  2947. 19999                         if (e2->m2 > e1->m2)
  2948. 20000                                 e1->m1 -= 1;    /* carry in */
  2949. 20001                         e1->m1 -= e2->m1;       /* do SUBTRACTION */
  2950. 20002                         e1->m2 -= e2->m2;       /*    SUBTRACTION */
  2951. 20003                 }
  2952. 20004
  2953. 20005                 /*      shift dividend left one bit OR  */
  2954. 20006                 /*      IF it equals ZERO we can break out      */
  2955. 20007                 /*      of the loop, but still must shift       */
  2956. 20008                 /*      the quotient the remaining count bits   */
  2957. 20009                 /* NB   save the results of this test in error  */
  2958. 20010                 /*      if not zero, then the result is inexact. */
  2959. 20011                 /*      this would be reported in IEEE standard */
  2960. 20012
  2961. 20013                 /*      lp points to dividend                   */
  2962. 20014                 lp = &e1->m1;
  2963. 20015
  2964. 20016                 error = ((*lp | *(lp+1)) != 0L) ? 1 : 0;
  2965. 20017                 if (error)      {       /* more work */
  2966. 20018                         /*      assume max bit == 0 (see above) */
  2967. 20019                         b64_lsft(&e1->mantissa);
  2968. 20020                         continue;
  2969. 20021                 }
  2970. 20022                 else
  2971. 20023                         break;  /* leave loop   */
  2972. 20024         }       /* end of divide by subtraction loop    */
  2973. 20025
  2974. 20026         if (count > 0)  {
  2975. 20027                 lp = &result.h_32;
  2976. 20028                 if (count > 31) {       /* move to higher word */
  2977. 20029                         *lp = *(lp+1);
  2978. .Op 179 src/lib/float/div_ext.c
  2979. 20030                         count -= 32;
  2980. 20031                         *(lp+1) = 0L;   /* clear low word       */
  2981. 20032                 }
  2982. 20033                 if (*lp)
  2983. 20034                         *lp <<= count;  /* shift rest of way    */
  2984. 20035                 lp++;   /*  == &result.l_32     */
  2985. 20036                 if (*lp) {
  2986. 20037                         result.h_32 |= (*lp >> 32-count);
  2987. 20038                         *lp <<= count;
  2988. 20039                 }
  2989. 20040         }
  2990. 20041 #else /* USE_DIVIDE */
  2991. 20042
  2992. 20043         u[4] = (e1->m2 & 1) << 15;
  2993. 20044         b64_rsft(&(e1->mantissa));
  2994. 20045         u[0] = e1->m1 >> 16;
  2995. 20046         u[1] = e1->m1;
  2996. 20047         u[2] = e1->m2 >> 16;
  2997. 20048         u[3] = e1->m2;
  2998. 20049         u[5] = 0; u[6] = 0; u[7] = 0;
  2999. 20050         v[1] = e2->m1 >> 16;
  3000. 20051         v[2] = e2->m1;
  3001. 20052         v[3] = e2->m2 >> 16;
  3002. 20053         v[4] = e2->m2;
  3003. 20054         while (! v[maxv]) maxv--;
  3004. 20055         result.h_32 = 0;
  3005. 20056         result.l_32 = 0;
  3006. 20057         lp = &result.h_32;
  3007. 20058
  3008. 20059         /*
  3009. 20060          * Use an algorithm of Knuth (The art of programming, Seminumerical
  3010. 20061          * algorithms), to divide u by v. u and v are both seen as numbers
  3011. 20062          * with base 65536. 
  3012. 20063          */
  3013. 20064         for (j = 0; j <= 3; j++, u_p++) {
  3014. 20065                 unsigned long q_est, temp;
  3015. 20066
  3016. 20067                 if (j == 2) lp++;
  3017. 20068                 if (u_p[0] == 0 && u_p[1] < v[1]) continue;
  3018. 20069                 temp = ((unsigned long)u_p[0] << 16) + u_p[1];
  3019. 20070                 if (u_p[0] >= v[1]) {
  3020. 20071                         q_est = 0x0000FFFFL;
  3021. 20072                 }
  3022. 20073                 else {
  3023. 20074                         q_est = temp / v[1];
  3024. 20075                 }
  3025. 20076                 temp -= q_est * v[1];
  3026. 20077                 while (temp < 0x10000 && v[2]*q_est > ((temp<<16)+u_p[2])) {
  3027. 20078                         q_est--;
  3028. 20079                         temp += v[1];
  3029. 20080                 }
  3030. 20081                 /*      Now, according to Knuth, we have an estimate of the
  3031. 20082                         quotient, that is either correct or one too big, but
  3032. 20083                         almost always correct.
  3033. 20084                 */
  3034. 20085                 if (q_est != 0)  {
  3035. 20086                         int i;
  3036. 20087                         unsigned long k = 0;
  3037. 20088                         int borrow = 0;
  3038. 20089
  3039. .Ep 180 src/lib/float/div_ext.c
  3040. 20090                         for (i = maxv; i > 0; i--) {
  3041. 20091                                 unsigned long tmp = q_est * v[i] + k + borrow;
  3042. 20092                                 unsigned short md = tmp;
  3043. 20093
  3044. 20094                                 borrow = (md > u_p[i]);
  3045. 20095                                 u_p[i] -= md;
  3046. 20096                                 k = tmp >> 16;
  3047. 20097                         }
  3048. 20098                         k += borrow;
  3049. 20099                         borrow = u_p[0] < k;
  3050. 20100                         u_p[0] -= k;
  3051. 20101
  3052. 20102                         if (borrow) {
  3053. 20103                                 /* So, this does not happen often; the estimate
  3054. 20104                                    was one too big; correct this
  3055. 20105                                 */
  3056. 20106                                 *lp |= (j & 1) ? (q_est - 1) : ((q_est-1)<<16);
  3057. 20107                                 borrow = 0;
  3058. 20108                                 for (i = maxv; i > 0; i--) {
  3059. 20109                                         unsigned long tmp 
  3060. 20110                                             = v[i]+(unsigned long)u_p[i]+borrow;
  3061. 20111                                         
  3062. 20112                                         u_p[i] = tmp;
  3063. 20113                                         borrow = tmp >> 16;
  3064. 20114                                 }
  3065. 20115                                 u_p[0] += borrow;
  3066. 20116                         }
  3067. 20117                         else *lp |= (j & 1) ? q_est : (q_est<<16);
  3068. 20118                 }
  3069. 20119         }
  3070. 20120 #ifdef  EXCEPTION_INEXACT
  3071. 20121         u_p = &u[0];
  3072. 20122         for (j = 7; j >= 0; j--) {
  3073. 20123                 if (*u_p++) {
  3074. 20124                         error = 1;
  3075. 20125                         break;
  3076. 20126                 }
  3077. 20127         }
  3078. 20128 #endif
  3079. 20129 #endif
  3080. 20130
  3081. 20131 #ifdef  EXCEPTION_INEXACT
  3082. 20132         if (error)      {
  3083. 20133                 /*
  3084. 20134                  * report here exception 8.5 - Inexact
  3085. 20135                  * from Draft 8.0 of IEEE P754:
  3086. 20136                  * In the absence of an invalid operation exception,
  3087. 20137                  * if the rounded result of an operation is not exact or if
  3088. 20138                  * it overflows without a trap, then the inexact exception
  3089. 20139                  * shall be assigned. The rounded or overflowed result
  3090. 20140                  * shall be delivered to the destination.
  3091. 20141                  */
  3092. 20142                 INEXACT();
  3093. 20143 #endif
  3094. 20144         e1->mantissa = result;
  3095. 20145
  3096. 20146         nrm_ext(e1);
  3097. 20147         if (e1->exp < EXT_MIN)  {
  3098. 20148                 /*
  3099. 20149                  * Exception 8.4 - Underflow
  3100. .Op 181 src/lib/float/div_ext.c
  3101. 20150                  */
  3102. 20151                 trap(EFUNFL);   /* underflow */
  3103. 20152                 e1->exp = EXT_MIN;
  3104. 20153                 e1->m1 = e1->m2 = 0L;
  3105. 20154                 return;
  3106. 20155         }
  3107. 20156         if (e1->exp >= EXT_MAX) {
  3108. 20157                 /*
  3109. 20158                  * Exception 8.3 - Overflow
  3110. 20159                  */
  3111. 20160                 trap(EFOVFL);   /* overflow */
  3112. 20161                 e1->exp = EXT_MAX;
  3113. 20162                 e1->m1 = e1->m2 = 0L;
  3114. 20163                 return;
  3115. 20164         }
  3116. 20165 }
  3117. ++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++
  3118. src/lib/float/dvf4.c    
  3119. ++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++
  3120. 20200 /*
  3121. 20201   (c) copyright 1988 by the Vrije Universiteit, Amsterdam, The Netherlands.
  3122. 20202   See the copyright notice in the ACK home directory, in the file "Copyright".
  3123. 20203 */
  3124. 20204
  3125. 20205 /* $Header: dvf4.c,v 1.5 93/01/05 12:04:53 ceriel Exp $ */
  3126. 20206
  3127. 20207 /*
  3128. 20208         DIVIDE TWO SINGLES - SINGLE Precision (dvf 4)
  3129. 20209 */
  3130. 20210
  3131. 20211 #include        "FP_types.h"
  3132. 20212
  3133. 20213 void
  3134. 20214 dvf4(s2,s1)
  3135. 20215 SINGLE  s1,s2;
  3136. 20216 {
  3137. 20217         EXTEND  e1,e2;
  3138. 20218
  3139. 20219         extend(&s1,&e1,sizeof(SINGLE));
  3140. 20220         extend(&s2,&e2,sizeof(SINGLE));
  3141. 20221
  3142. 20222                 /* do a divide */
  3143. 20223         div_ext(&e1,&e2);
  3144. 20224         compact(&e1,&s1,sizeof(SINGLE));
  3145. 20225 }
  3146. .Ep 182 src/lib/float/dvf8.c
  3147. ++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++
  3148. src/lib/float/dvf8.c    
  3149. ++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++
  3150. 20300 /*
  3151. 20301   (c) copyright 1988 by the Vrije Universiteit, Amsterdam, The Netherlands.
  3152. 20302   See the copyright notice in the ACK home directory, in the file "Copyright".
  3153. 20303 */
  3154. 20304
  3155. 20305 /* $Header: dvf8.c,v 1.5 93/01/05 12:04:59 ceriel Exp $ */
  3156. 20306
  3157. 20307 /*
  3158. 20308         DIVIDE TWO FLOATS - DOUBLE Precision (DVF 8)
  3159. 20309 */
  3160. 20310
  3161. 20311 #include        "FP_types.h"
  3162. 20312
  3163. 20313 void
  3164. 20314 dvf8(s2,s1)
  3165. 20315 DOUBLE  s1,s2;
  3166. 20316 {
  3167. 20317         EXTEND  e1,e2;
  3168. 20318
  3169. 20319         extend(&s1.d[0],&e1,sizeof(DOUBLE));
  3170. 20320         extend(&s2.d[0],&e2,sizeof(DOUBLE));
  3171. 20321
  3172. 20322                 /* do a divide */
  3173. 20323         div_ext(&e1,&e2);
  3174. 20324         compact(&e1,&s1.d[0],sizeof(DOUBLE));
  3175. 20325 }
  3176. ++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++
  3177. src/lib/float/extend.c    
  3178. ++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++
  3179. 20400 /*
  3180. 20401   (c) copyright 1988 by the Vrije Universiteit, Amsterdam, The Netherlands.
  3181. 20402   See the copyright notice in the ACK home directory, in the file "Copyright".
  3182. 20403 */
  3183. 20404
  3184. 20405 /* $Header: extend.c,v 1.11 93/01/05 12:05:05 ceriel Exp $ */
  3185. 20406
  3186. 20407 /*
  3187. 20408         CONVERTS FLOATING POINT TO EXTENDED FORMAT
  3188. 20409
  3189. 20410         Two sizes of FLOATING Point are known:
  3190. 20411                 SINGLE and DOUBLE
  3191. 20412 */
  3192. 20413 /********************************************************/
  3193. 20414 /*
  3194. 20415         It is not required to normalize in extended
  3195. 20416         format, but it has been chosen to do so.
  3196. 20417         Extended Format is as follows (at exit):
  3197. 20418
  3198. 20419 ->sign  S000 0000 | 0000 0000           <SIGN>
  3199. .Op 183 src/lib/float/extend.c
  3200. 20420 ->exp   0EEE EEEE | EEEE EEEE           <EXPONENT>
  3201. 20421 ->m1    LFFF FFFF | FFFF FFFF           <L.Fraction>
  3202. 20422         FFFF FFFF | FFFF FFFF           <Fraction>
  3203. 20423 ->m2    FFFF FFFF | FFFF FFFF           <Fraction>
  3204. 20424         FFFF F000 | 0000 0000           <Fraction>
  3205. 20425 */
  3206. 20426 /********************************************************/
  3207. 20427
  3208. 20428 #include "FP_bias.h"
  3209. 20429 #include "FP_shift.h"
  3210. 20430 #include "FP_types.h"
  3211. 20431 #include "get_put.h"
  3212. 20432 /********************************************************/
  3213. 20433
  3214. 20434 void
  3215. 20435 extend(from,to,size)
  3216. 20436 unsigned long   *from;
  3217. 20437 EXTEND  *to;
  3218. 20438 int     size;
  3219. 20439 {
  3220. 20440         register char *cpt1;
  3221. 20441         unsigned long   tmp;
  3222. 20442         int     leadbit = 0;
  3223. 20443
  3224. 20444         cpt1 = (char *) from;
  3225. 20445
  3226. 20446 #if FL_MSL_AT_LOW_ADDRESS
  3227. 20447 #if FL_MSW_AT_LOW_ADDRESS
  3228. 20448         to->exp = uget2(cpt1);
  3229. 20449 #else
  3230. 20450         to->exp = uget2(cpt1+2);
  3231. 20451 #endif
  3232. 20452 #else
  3233. 20453 #if FL_MSW_AT_LOW_ADDRESS
  3234. 20454         to->exp = uget2(cpt1+(size == sizeof(DOUBLE) ? 4 : 0));
  3235. 20455 #else
  3236. 20456         to->exp = uget2(cpt1+(size == sizeof(DOUBLE) ? 6 : 2));
  3237. 20457 #endif
  3238. 20458 #endif
  3239. 20459         to->sign = (to->exp & 0x8000);  /* set sign bit */
  3240. 20460         to->exp ^= to->sign;
  3241. 20461         if (size == sizeof(DOUBLE))
  3242. 20462                 to->exp >>= DBL_EXPSHIFT;
  3243. 20463         else
  3244. 20464                 to->exp >>= SGL_EXPSHIFT;
  3245. 20465         if (to->exp > 0)
  3246. 20466                 leadbit++;      /* will set Lead bit later      */
  3247. 20467         else to->exp++;
  3248. 20468
  3249. 20469         if (size == sizeof(DOUBLE))     {
  3250. 20470 #if FL_MSL_AT_LOW_ADDRESS
  3251. 20471                 to->m1 = get4(cpt1);
  3252. 20472                 cpt1 += 4;
  3253. 20473                 tmp = get4(cpt1);
  3254. 20474 #else
  3255. 20475                 tmp = get4(cpt1);
  3256. 20476                 cpt1 += 4;
  3257. 20477                 to->m1 = get4(cpt1);
  3258. 20478 #endif
  3259. 20479                 if (to->exp == 1 && to->m1 == 0 && tmp == 0) {
  3260. .Ep 184 src/lib/float/extend.c
  3261. 20480                         to->exp = 0;
  3262. 20481                         to->sign = 0;
  3263. 20482                         to->m1 = 0;
  3264. 20483                         to->m2 = 0;
  3265. 20484                         return;
  3266. 20485                 }
  3267. 20486                 to->m1 <<= DBL_M1LEFT;          /* shift        */
  3268. 20487                 to->exp -= DBL_BIAS;            /* remove bias  */
  3269. 20488                 to->m1 |= (tmp>>DBL_RPACK);     /* plus 10 == 32        */
  3270. 20489                 to->m2 = (tmp<<DBL_LPACK);      /* plus 22 == 32        */
  3271. 20490         }
  3272. 20491         else    {       /* size == sizeof(SINGLE)               */
  3273. 20492                 to->m1 = get4(cpt1);
  3274. 20493                 to->m1  <<= SGL_M1LEFT; /* shift        */
  3275. 20494                 if (to->exp == 1 && to->m1 == 0) {
  3276. 20495                         to->exp = 0;
  3277. 20496                         to->sign = 0;
  3278. 20497                         to->m1 = 0;
  3279. 20498                         to->m2 = 0;
  3280. 20499                         return;
  3281. 20500                 }
  3282. 20501                 to->exp -= SGL_BIAS;            /* remove bias  */
  3283. 20502                 to->m2 = 0L;
  3284. 20503         }
  3285. 20504
  3286. 20505         to->m1 |= NORMBIT;                              /* set bit L    */
  3287. 20506         if (leadbit == 0) {             /* set or clear Leading Bit     */
  3288. 20507                 to->m1 &= ~NORMBIT;                     /* clear bit L  */
  3289. 20508                 nrm_ext(to);                            /* and normalize */
  3290. 20509         }
  3291. 20510 }
  3292. ++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++
  3293. src/lib/float/fef4.c    
  3294. ++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++
  3295. 20600 /*
  3296. 20601   (c) copyright 1988 by the Vrije Universiteit, Amsterdam, The Netherlands.
  3297. 20602   See the copyright notice in the ACK home directory, in the file "Copyright".
  3298. 20603 */
  3299. 20604
  3300. 20605 /* $Header: fef4.c,v 1.7 93/01/05 12:05:12 ceriel Exp $ */
  3301. 20606
  3302. 20607 /*
  3303. 20608         SEPERATE INTO EXPONENT AND FRACTION (FEF 4)
  3304. 20609 */
  3305. 20610
  3306. 20611 #include        "FP_types.h"
  3307. 20612
  3308. 20613 void
  3309. 20614 fef4(r,s1)
  3310. 20615 SINGLE  s1;
  3311. 20616 struct fef4_returns     *r;
  3312. 20617 {
  3313. 20618         EXTEND  buf;
  3314. 20619         register struct fef4_returns    *p = r; /* make copy; r might refer
  3315. .Op 185 src/lib/float/fef4.c
  3316. 20620                                                    to itself (see table)
  3317. 20621                                                 */
  3318. 20622
  3319. 20623         extend(&s1,&buf,sizeof(SINGLE));
  3320. 20624         if (buf.exp == 0 && buf.m1 == 0 && buf.m2 == 0) {
  3321. 20625                 p->e = 0;
  3322. 20626         }
  3323. 20627         else {
  3324. 20628                 p->e = buf.exp+1;
  3325. 20629                 buf.exp = -1;
  3326. 20630         }
  3327. 20631         compact(&buf,&p->f,sizeof(SINGLE));
  3328. 20632 }
  3329. ++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++
  3330. src/lib/float/fef8.c    
  3331. ++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++
  3332. 20700 /*
  3333. 20701   (c) copyright 1988 by the Vrije Universiteit, Amsterdam, The Netherlands.
  3334. 20702   See the copyright notice in the ACK home directory, in the file "Copyright".
  3335. 20703 */
  3336. 20704
  3337. 20705 /* $Header: fef8.c,v 1.7 93/01/05 12:05:18 ceriel Exp $ */
  3338. 20706
  3339. 20707 /*
  3340. 20708         SEPERATE DOUBLE INTO EXPONENT AND FRACTION (FEF 8)
  3341. 20709 */
  3342. 20710
  3343. 20711 #include        "FP_types.h"
  3344. 20712
  3345. 20713 void
  3346. 20714 fef8(r, s1)
  3347. 20715 DOUBLE  s1;
  3348. 20716 struct fef8_returns *r;
  3349. 20717 {
  3350. 20718         EXTEND  buf;
  3351. 20719         register struct fef8_returns *p = r;    /* make copy, r might refer
  3352. 20720                                                    to itself (see table)
  3353. 20721                                                 */
  3354. 20722
  3355. 20723         extend(&s1.d[0],&buf,sizeof(DOUBLE));
  3356. 20724         if (buf.exp == 0 && buf.m1 == 0 && buf.m2 == 0) {
  3357. 20725                 p->e = 0;
  3358. 20726         }
  3359. 20727         else {
  3360. 20728                 p->e = buf.exp + 1;
  3361. 20729                 buf.exp = -1;
  3362. 20730         }
  3363. 20731         compact(&buf,&p->f.d[0],sizeof(DOUBLE));
  3364. 20732 }
  3365. .Ep 186 src/lib/float/fif4.c
  3366. ++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++
  3367. src/lib/float/fif4.c    
  3368. ++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++
  3369. 20800 /*
  3370. 20801   (c) copyright 1988 by the Vrije Universiteit, Amsterdam, The Netherlands.
  3371. 20802   See the copyright notice in the ACK home directory, in the file "Copyright".
  3372. 20803 */
  3373. 20804
  3374. 20805 /* $Header: fif4.c,v 1.7 93/01/05 12:05:24 ceriel Exp $ */
  3375. 20806
  3376. 20807 /*
  3377. 20808         MULTIPLY AND DISMEMBER PARTS (FIF 4)
  3378. 20809 */
  3379. 20810
  3380. 20811 #include "FP_types.h"
  3381. 20812 #include "FP_shift.h"
  3382. 20813
  3383. 20814 void
  3384. 20815 fif4(p,x,y)
  3385. 20816 SINGLE  x,y;
  3386. 20817 struct fif4_returns *p;
  3387. 20818 {
  3388. 20819
  3389. 20820         EXTEND  e1,e2;
  3390. 20821
  3391. 20822         extend(&y,&e1,sizeof(SINGLE));
  3392. 20823         extend(&x,&e2,sizeof(SINGLE));
  3393. 20824                 /* do a multiply */
  3394. 20825         mul_ext(&e1,&e2);
  3395. 20826         e2 = e1;
  3396. 20827         compact(&e2,&y,sizeof(SINGLE));
  3397. 20828         if (e1.exp < 0) {
  3398. 20829                 p->ipart = 0;
  3399. 20830                 p->fpart = y;
  3400. 20831                 return;
  3401. 20832         }
  3402. 20833         if (e1.exp > 30 - SGL_M1LEFT) {
  3403. 20834                 p->ipart = y;
  3404. 20835                 p->fpart = 0;
  3405. 20836                 return;
  3406. 20837         }
  3407. 20838         b64_sft(&e1.mantissa, 63 - e1.exp);
  3408. 20839         b64_sft(&e1.mantissa, e1.exp - 63);     /* "loose" low order bits */
  3409. 20840         compact(&e1,&(p->ipart),sizeof(SINGLE));
  3410. 20841         extend(&(p->ipart), &e2, sizeof(SINGLE));
  3411. 20842         extend(&y, &e1, sizeof(SINGLE));
  3412. 20843         sub_ext(&e1, &e2);
  3413. 20844         compact(&e1, &(p->fpart), sizeof(SINGLE));
  3414. 20845 }
  3415. .Op 187 src/lib/float/fif8.c
  3416. ++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++
  3417. src/lib/float/fif8.c    
  3418. ++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++
  3419. 20900 /*
  3420. 20901   (c) copyright 1988 by the Vrije Universiteit, Amsterdam, The Netherlands.
  3421. 20902   See the copyright notice in the ACK home directory, in the file "Copyright".
  3422. 20903 */
  3423. 20904
  3424. 20905 /* $Header: fif8.c,v 1.7 93/01/05 12:05:30 ceriel Exp $ */
  3425. 20906
  3426. 20907 /*
  3427. 20908         MULTIPLY AND DISMEMBER PARTS (FIF 8)
  3428. 20909 */
  3429. 20910
  3430. 20911 #include "FP_types.h"
  3431. 20912 #include "FP_shift.h"
  3432. 20913
  3433. 20914 void
  3434. 20915 fif8(p,x,y)
  3435. 20916 DOUBLE  x,y;
  3436. 20917 struct fif8_returns *p;
  3437. 20918 {
  3438. 20919
  3439. 20920         EXTEND  e1,e2;
  3440. 20921
  3441. 20922         extend(&y.d[0],&e1,sizeof(DOUBLE));
  3442. 20923         extend(&x.d[0],&e2,sizeof(DOUBLE));
  3443. 20924                 /* do a multiply */
  3444. 20925         mul_ext(&e1,&e2);
  3445. 20926         e2 = e1;
  3446. 20927         compact(&e2, &y.d[0], sizeof(DOUBLE));
  3447. 20928         if (e1.exp < 0) {
  3448. 20929                 p->ipart.d[0] = 0;
  3449. 20930                 p->ipart.d[1] = 0;
  3450. 20931                 p->fpart = y;
  3451. 20932                 return;
  3452. 20933         }
  3453. 20934         if (e1.exp > 62 - DBL_M1LEFT) {
  3454. 20935                 p->ipart = y;
  3455. 20936                 p->fpart.d[0] = 0;
  3456. 20937                 p->fpart.d[1] = 0;
  3457. 20938                 return;
  3458. 20939         }
  3459. 20940         b64_sft(&e1.mantissa, 63 - e1.exp);
  3460. 20941         b64_sft(&e1.mantissa, e1.exp - 63);     /* "loose" low order bits */
  3461. 20942         compact(&e1, &(p->ipart.d[0]), sizeof(DOUBLE));
  3462. 20943         extend(&(p->ipart.d[0]), &e2, sizeof(DOUBLE));
  3463. 20944         extend(&y.d[0], &e1, sizeof(DOUBLE));
  3464. 20945         sub_ext(&e1, &e2);
  3465. 20946         compact(&e1, &(p->fpart.d[0]), sizeof(DOUBLE));
  3466. 20947 }
  3467. .Ep 188 src/lib/float/mlf4.c
  3468. ++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++
  3469. src/lib/float/mlf4.c    
  3470. ++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++
  3471. 21000 /*
  3472. 21001   (c) copyright 1988 by the Vrije Universiteit, Amsterdam, The Netherlands.
  3473. 21002   See the copyright notice in the ACK home directory, in the file "Copyright".
  3474. 21003 */
  3475. 21004
  3476. 21005 /* $Header: mlf4.c,v 1.4 93/01/05 12:05:37 ceriel Exp $ */
  3477. 21006
  3478. 21007 /*
  3479. 21008  * Multiply Single Precesion Float (MLF 4)
  3480. 21009  */
  3481. 21010
  3482. 21011 #include        "FP_types.h"
  3483. 21012
  3484. 21013 void
  3485. 21014 mlf4(s2,s1)