home *** CD-ROM | disk | FTP | other *** search
/ Usenet 1994 October / usenetsourcesnewsgroupsinfomagicoctober1994disk2.iso / unix / volume23 / abc / part20 < prev    next >
Text File  |  1991-01-08  |  56KB  |  2,385 lines

  1. Subject:  v23i099:  ABC interactive programming environment, Part20/25
  2. Newsgroups: comp.sources.unix
  3. Approved: rsalz@uunet.UU.NET
  4. X-Checksum-Snefru: 5ec2aeb9 9f828266 4f0d2de8 f003a395
  5.  
  6. Submitted-by: Steven Pemberton <steven@cwi.nl>
  7. Posting-number: Volume 23, Issue 99
  8. Archive-name: abc/part20
  9.  
  10. #! /bin/sh
  11. # This is a shell archive.  Remove anything before this line, then feed it
  12. # into a shell via "sh file" or similar.  To overwrite existing files,
  13. # type "sh file -c".
  14. # The tool that generated this appeared in the comp.sources.unix newsgroup;
  15. # send mail to comp-sources-unix@uunet.uu.net if you want that tool.
  16. # Contents:  abc/bed/e1erro.c abc/bed/e1eval.c abc/bed/e1line.c
  17. #   abc/bint1/i1nur.c abc/bint3/i3fil.c abc/bio/i4fil.c
  18. #   abc/boot/Makefile abc/ihdrs/i1num.h abc/keys/keyhlp.c
  19. #   abc/stc/i2tcu.c abc/unix/u1file.c
  20. # Wrapped by rsalz@litchi.bbn.com on Mon Dec 17 13:28:18 1990
  21. PATH=/bin:/usr/bin:/usr/ucb ; export PATH
  22. echo If this archive is complete, you will see the following message:
  23. echo '          "shar: End of archive 20 (of 25)."'
  24. if test -f 'abc/bed/e1erro.c' -a "${1}" != "-c" ; then 
  25.   echo shar: Will not clobber existing file \"'abc/bed/e1erro.c'\"
  26. else
  27.   echo shar: Extracting \"'abc/bed/e1erro.c'\" \(4638 characters\)
  28.   sed "s/^X//" >'abc/bed/e1erro.c' <<'END_OF_FILE'
  29. X/* Copyright (c) Stichting Mathematisch Centrum, Amsterdam, 1986. */
  30. X
  31. X/*
  32. X * B editor -- Handle error messages.
  33. X */
  34. X
  35. X#include "b.h"
  36. X#include "bedi.h"
  37. X#include "feat.h"
  38. X#include "bmem.h"
  39. X#include "bobj.h"
  40. X#include "erro.h"
  41. X#include "node.h"
  42. X
  43. Xextern bool hushbaby;
  44. X
  45. Xstring querepr();
  46. X
  47. Xextern int winheight; /* From scrn.c */
  48. Xextern int winstart; /* From scrn.c */
  49. Xextern int llength; /* From scrn.c */
  50. X
  51. X#define SOBIT 0200 /* Interface with wind.c */
  52. X
  53. X#define MAXMSG 1000
  54. X#define MAXBUF 50
  55. Xstatic char *msgbuffer;
  56. Xstatic bool ringbell;
  57. Xstatic int priority;
  58. X
  59. X#define M_RECORDING    MESS(6400, "Recording")
  60. X#define M_COPYBUF    MESS(6401, "Copy buffer")
  61. X
  62. Xstatic char *mrecbuf;
  63. Xstatic char *mcopybuf;
  64. X
  65. X/*
  66. X * Status line.  A combination of scroll bar, error message etc.
  67. X * Put the message on the screen and clear the buffers for next time.
  68. X * If there is no message, show status and copy buffer and recording mode.
  69. X */
  70. X
  71. XVisible Procedure
  72. Xstsline(totlines, topline, scrlines, copybuffer, recording)
  73. X    int totlines;
  74. X    int topline;
  75. X    int scrlines;
  76. X    value copybuffer;
  77. X    bool recording;
  78. X{
  79. X    register string bp;
  80. X
  81. X    if (ringbell && !hushbaby)
  82. X        trmbell();
  83. X    if (msgbuffer[0]) {
  84. X        msgbuffer[llength-1] = '\0'; /* Truncate */
  85. X        if (ringbell) {
  86. X            for (bp = msgbuffer; *bp; ++bp)
  87. X                *bp |= SOBIT;
  88. X        }
  89. X    }
  90. X    else {
  91. X        bp = msgbuffer;
  92. X#ifdef SCROLLBAR
  93. X        bp += addscrollbar(totlines, topline, scrlines);
  94. X#endif /* SCROLLBAR */
  95. X        if (recording) {
  96. X            if (!mrecbuf[0])
  97. X                strcpy(mrecbuf, getmess(M_RECORDING));
  98. X            sprintf(bp, "[%s] ", mrecbuf);
  99. X            while (*bp)
  100. X                ++bp;
  101. X        }
  102. X        if (copybuffer) {
  103. X            if (!mcopybuf[0])
  104. X                strcpy(mcopybuf, getmess(M_COPYBUF));
  105. X#ifdef SHOWBUF
  106. X            sprintf(bp, "[%s: %.80s]", mcopybuf, querepr(copybuffer));
  107. X            while (*bp)
  108. X                ++bp;
  109. X            if (bp >= msgbuffer+80)
  110. X                strcpy(msgbuffer+75, "...]");
  111. X#else /* !SHOWBUF */
  112. X            sprintf(bp, "[%s]", mcopybuf);
  113. X#endif /* !SHOWBUF */
  114. X        }
  115. X    }
  116. X    trmputdata(winheight, winheight, 0, msgbuffer);
  117. X    msgbuffer[0] = '\0';
  118. X    priority = 0;
  119. X    ringbell = No;
  120. X}
  121. X
  122. X#ifdef SCROLLBAR
  123. X
  124. X/*
  125. X * Paint a beautiful scroll bar so the user can see about what part of the
  126. X * unit is visible on the screen (considering logical lines).
  127. X */
  128. X
  129. XHidden int
  130. Xaddscrollbar(totlines, topline, scrlines)
  131. X    int totlines;
  132. X    int topline;
  133. X    int scrlines;
  134. X{
  135. X    int endline;
  136. X    register int i;
  137. X
  138. X    if (winstart > 0 || scrlines > totlines)
  139. X        return 0; /* Nothing outside screen */
  140. X    if (totlines <= 0)
  141. X        totlines = 1; /* Don't want to divide by 0 */
  142. X    topline = topline*winheight / totlines;
  143. X    endline = topline + (scrlines*winheight + totlines-1) / totlines;
  144. X    if (endline > winheight)
  145. X        endline = winheight;
  146. X    if (topline >= endline)
  147. X        topline = endline-1;
  148. X    for (i = 0; i < topline; ++i)
  149. X        msgbuffer[i] = '-';
  150. X    for (; i < endline; ++i)
  151. X        msgbuffer[i] = '#';
  152. X    for (; i < winheight; ++i)
  153. X        msgbuffer[i] = '-';
  154. X    msgbuffer[i++] = ' ';
  155. X    msgbuffer[i] = '\0';
  156. X    return i;
  157. X}
  158. X
  159. X#endif /* SCROLLBAR */
  160. X
  161. X/*
  162. X * Issue an error message.  These have highest priority.
  163. X * Once an error message is in the buffer, further error messages are ignored
  164. X * until it has been displayed.
  165. X */
  166. X
  167. XHidden Procedure
  168. Xederr1(s)
  169. X    string s;
  170. X{
  171. X    ringbell = Yes;
  172. X    if (s && priority < 3) {
  173. X        priority = 3;
  174. X        strcpy(msgbuffer, s);
  175. X    }
  176. X}
  177. X
  178. XVisible Procedure
  179. Xederr(m)
  180. X    int m;
  181. X{
  182. X    if (m == 0) ringbell= Yes;
  183. X    else ederr1(getmess(m));
  184. X}
  185. X
  186. XVisible Procedure
  187. XederrS(m, s)
  188. X    int m;
  189. X    string s;
  190. X{
  191. X    sprintf(messbuf, getmess(m), s);
  192. X    ederr1(messbuf);    
  193. X}
  194. X
  195. XVisible Procedure
  196. XederrC(m, c)
  197. X    int m;
  198. X    char c;
  199. X{
  200. X    sprintf(messbuf, getmess(m), c);
  201. X    ederr1(messbuf);
  202. X}
  203. X
  204. X/*
  205. X * Issue an informative message.  These have medium priority.
  206. X * Unlike error messages, the last such message is displayed.
  207. X */
  208. X
  209. XVisible Procedure
  210. Xedmessage(s)
  211. X    string s;
  212. X{
  213. X    if (s && priority <= 2) {
  214. X        priority = 2;
  215. X        strcpy(msgbuffer, s);
  216. X    }
  217. X}
  218. X
  219. X
  220. X/*
  221. X * Issue a debugging message.  These  have lowest priority and
  222. X * are not shown to ordinary users.
  223. X */
  224. X
  225. X#ifndef NDEBUG
  226. X
  227. X/* VARARGS 1 */
  228. XVisible Procedure
  229. Xdebug(fmt, a1, a2, a3, a4, a5, a6, a7, a8, a9, a10)
  230. X    string fmt;
  231. X{
  232. X    if (fmt && priority <= 1) {
  233. X        priority = 1;
  234. X        sprintf(msgbuffer,
  235. X            fmt, a1, a2, a3, a4, a5, a6, a7, a8, a9, a10);
  236. X    }
  237. X}
  238. X
  239. X#endif /* NDEBUG */
  240. X
  241. X/*
  242. X * Dump any error message still remaining to console or stderr.
  243. X */
  244. X
  245. XVisible Procedure
  246. Xenderro()
  247. X{
  248. X    if (!msgbuffer)
  249. X        return;
  250. X    if (msgbuffer[0])
  251. X        putSstr(errfile, "%s\n", msgbuffer);
  252. X    msgbuffer[0] = '\0';
  253. X    priority = 0;
  254. X    ringbell = No;
  255. X}
  256. X
  257. XVisible Procedure init_erro() {
  258. X    msgbuffer= (char*) getmem(MAXMSG);
  259. X    msgbuffer[0]= '\0';
  260. X    mrecbuf= (char*) getmem(MAXBUF);
  261. X    mrecbuf[0]= '\0';
  262. X    mcopybuf= (char*) getmem(MAXBUF);
  263. X    mcopybuf[0]= '\0';
  264. X}
  265. X
  266. XVisible Procedure end_erro() {
  267. X    freemem((ptr) msgbuffer);
  268. X    freemem((ptr) mrecbuf);
  269. X    freemem((ptr) mcopybuf);
  270. X}
  271. END_OF_FILE
  272.   if test 4638 -ne `wc -c <'abc/bed/e1erro.c'`; then
  273.     echo shar: \"'abc/bed/e1erro.c'\" unpacked with wrong size!
  274.   fi
  275.   # end of 'abc/bed/e1erro.c'
  276. fi
  277. if test -f 'abc/bed/e1eval.c' -a "${1}" != "-c" ; then 
  278.   echo shar: Will not clobber existing file \"'abc/bed/e1eval.c'\"
  279. else
  280.   echo shar: Extracting \"'abc/bed/e1eval.c'\" \(4245 characters\)
  281.   sed "s/^X//" >'abc/bed/e1eval.c' <<'END_OF_FILE'
  282. X/* Copyright (c) Stichting Mathematisch Centrum, Amsterdam, 1986. */
  283. X
  284. X/*
  285. X * B editor -- Width attribute evaluation.
  286. X */
  287. X
  288. X#include "b.h"
  289. X#include "b0lan.h"
  290. X#include "bedi.h"
  291. X#include "etex.h"
  292. X#include "node.h"
  293. X#include "gram.h"
  294. X
  295. X
  296. X/*
  297. X * The following convention is used throughout the editor to indicate
  298. X * the sizes of objects.
  299. X * - A zero or positive `width' value means the object contains no
  300. X *   linefeeds.  The width is counted in characters.
  301. X * - A negative `width' means the object (or its children) contains
  302. X *   at leasty one linefeed (return is treated as a linefeed here).
  303. X *   The number of linefeeds is -width.
  304. X *   There is no indication whether the object fits on that number of
  305. X *   physical lines, as logical lines may have arbitrary length.
  306. X *
  307. X * For coordinates the following convention is used.
  308. X * (Note that, in accordance to the convention in curses(3), the
  309. X * `y' coordinate always precedes the `x' coorxdinate.)
  310. X * - `Y' is the line number, counted from the beginning of the unit.
  311. X *   These are logical lines rather than physical lines.
  312. X *   The first line has line number 0.
  313. X * - `X' is the column number.  The first column is 0.  For x < 0,
  314. X *   see the important notice below.
  315. X * - `Level' is the indentation level, indicating where a new line
  316. X *   would start if inserted at the current position.
  317. X *   The initial `x' position of such a line is `level*INDENTSIZE'.
  318. X *
  319. X * ***** IMPORTANT NOTICE *****
  320. X * A special case is x = -1.  This means that the current x position is
  321. X * unknown.  Further output on the same line is suppressed, until a
  322. X * linefeed is encountered.  This feature is necessary because while
  323. X * calculating coordinates, when an object has width < 0, only the y
  324. X * coordinate of the end of that object is known.  In this case, the
  325. X * next non-empty object MUST START WITH A LINEFEED, or it will not
  326. X * be visible on the screen (in practice, a space is sometimes present
  327. X * in the parse tree which is not shown then).
  328. X */
  329. X
  330. X
  331. X/*
  332. X * Compute the (y, x) coordinates and indent level just before
  333. X * the beginning of the j'th child, if the current node starts
  334. X * at the initial values of (y, x) and level.
  335. X */
  336. X
  337. XVisible Procedure
  338. Xevalcoord(n, jch, py, px, plevel)
  339. X    register node n;
  340. X    register int jch;
  341. X    int *py;
  342. X    int *px;
  343. X    int *plevel;
  344. X{
  345. X    node nn;
  346. X    register int i;
  347. X    register string *rp = noderepr(n);
  348. X    register int k;
  349. X    register int y = 0;
  350. X    int x = *px;
  351. X    int level = *plevel;
  352. X    int nch;
  353. X    
  354. X    nch = Is_etext(n) ? 0 : nchildren(n);
  355. X    if (jch > nch)
  356. X        jch = nch+1;
  357. X    for (i = 0; i < jch; ++i) {
  358. X        if (i) {
  359. X            nn = child(n, i);
  360. X            k = nodewidth(nn);
  361. X            if (k < 0) {
  362. X                y += -k;
  363. X                x = k;
  364. X            }
  365. X            else if (x >= 0)
  366. X                x += k;
  367. X        }
  368. X        k = Fwidth(rp[i]);
  369. X        if (k < 0) {
  370. X            y += -k;
  371. X            /* The \r in the next line is actually a
  372. X               \n on the Mac.  I forgot what \r was meant
  373. X               for; believe it isn't used. */
  374. X            x = /*rp[i][0] == '\r' ? 0 :*/ INDENTSIZE*level;
  375. X            x += strlen(rp[i]) - 1;
  376. X        }
  377. X        else {
  378. X            if (x >= 0)
  379. X                x += k;
  380. X            if (rp[i]) {
  381. X                if (rp[i][k] == '\t')
  382. X                    ++level;
  383. X                else if (rp[i][k] == '\b')
  384. X                    --level;
  385. X            }
  386. X        }
  387. X    }
  388. X
  389. X    *py += y;
  390. X    *px = x;
  391. X    *plevel = level;
  392. X}
  393. X
  394. X
  395. X/*
  396. X * Yield the width of a piece of fixed text as found in a node's repr,
  397. X * excluding \b or \t.  If \n or \r is found, -1 is returned.
  398. X * It assumes that \n or \r only occur as first
  399. X * character, and \b or \t only as last.
  400. X */
  401. X
  402. XVisible int
  403. Xfwidth(str)
  404. X    register string str;
  405. X{
  406. X    register int c;
  407. X    register int n = 0;
  408. X
  409. X    if (!str)
  410. X        return 0;
  411. X    c = str[0];
  412. X    if (c == '\r' || c == '\n')
  413. X        return -1;
  414. X    for (; c; c = *++str)
  415. X        ++n;
  416. X    if (n > 0) {
  417. X        c = str[-1];
  418. X        if (c == '\t' || c == '\b')
  419. X            --n;
  420. X    }
  421. X    return n;
  422. X}
  423. X
  424. X
  425. X/*
  426. X * Evaluate the width of node n, assuming the widths of its children
  427. X * have correctly been calculated.
  428. X */
  429. X
  430. XVisible int
  431. Xevalwidth(n)
  432. X    register node n;
  433. X{
  434. X    register int w;
  435. X    register int i;
  436. X    register string *rp;
  437. X    register int y = 0;
  438. X    register int x = 0;
  439. X    register int nch;
  440. X    register node nn;
  441. X
  442. X    rp = noderepr(n);
  443. X    nch = Is_etext(n) ? 0 : nchildren(n);
  444. X    for (i = 0; i <= nch; ++i) {
  445. X        if (i) {
  446. X            nn = child(n, i);
  447. X            w = nodewidth(nn);
  448. X            if (w < 0) {
  449. X                y += -w;
  450. X                x = w;
  451. X            }
  452. X            else
  453. X                x += w;
  454. X        }
  455. X        w = Fwidth(rp[i]);
  456. X        if (w < 0) {
  457. X            y += -w;
  458. X            x = 0;
  459. X        }
  460. X        else
  461. X            x += w;
  462. X    }
  463. X    if (y > 0)
  464. X        return -y;
  465. X    return x;
  466. X}
  467. END_OF_FILE
  468.   if test 4245 -ne `wc -c <'abc/bed/e1eval.c'`; then
  469.     echo shar: \"'abc/bed/e1eval.c'\" unpacked with wrong size!
  470.   fi
  471.   # end of 'abc/bed/e1eval.c'
  472. fi
  473. if test -f 'abc/bed/e1line.c' -a "${1}" != "-c" ; then 
  474.   echo shar: Will not clobber existing file \"'abc/bed/e1line.c'\"
  475. else
  476.   echo shar: Extracting \"'abc/bed/e1line.c'\" \(4243 characters\)
  477.   sed "s/^X//" >'abc/bed/e1line.c' <<'END_OF_FILE'
  478. X/* Copyright (c) Stichting Mathematisch Centrum, Amsterdam, 1986. */
  479. X
  480. X/*
  481. X * B editor -- Routines for treating the parse tree as a sequence of lines.
  482. X *
  483. X * WARNING: The routines in this file (and many others!) assume that a
  484. X * `newline' can only occur in the zero'th representation string of a node
  485. X * (i.e., rp[0]).
  486. X */
  487. X
  488. X#include "b.h"
  489. X#include "bedi.h"
  490. X#include "etex.h"
  491. X#include "bobj.h"
  492. X#include "node.h"
  493. X#include "gram.h"
  494. X#include "supr.h"
  495. X
  496. X
  497. X/*
  498. X * Compute equality of subtrees, based on common descent.
  499. X * Strings are not checked for characterwise equality, but must
  500. X * be the same pointer; other nodes must have the same symbol and
  501. X * their children must be equal in this sense (equal pointers are
  502. X * always used as a shortcut).
  503. X *
  504. X * (Used by screen update algorithm only.)
  505. X */
  506. X
  507. XVisible bool
  508. Xeqlines(n1, n2)
  509. X    node n1;
  510. X    node n2;
  511. X{
  512. X    register node nn1;
  513. X    register node nn2;
  514. X    register int w1;
  515. X    register int w2;
  516. X    register int nch;
  517. X    register int i;
  518. X
  519. X    if (n1 == n2)
  520. X        return Yes;
  521. X    if (!Is_Node(n1) || !Is_Node(n2))
  522. X        return No;
  523. X    if (symbol(n1) != symbol(n2))
  524. X        return No;
  525. X    nch = nchildren(n1);
  526. X    Assert(nch == nchildren(n2));
  527. X    for (i = 1; i <= nch; ++i) {
  528. X        nn1 = child(n1, i);
  529. X        nn2 = child(n2, i);
  530. X        w1 = nodewidth(nn1);
  531. X        w2 = nodewidth(nn2);
  532. X        if (w1 >= 0 && w2 >= 0) {
  533. X            if (!eqlines(nn1, nn2))
  534. X                return No;
  535. X        }
  536. X        else {
  537. X            if (nn1 == nn2)
  538. X                return Yes;
  539. X            if (fwidth(noderepr(nn1)[0]) < 0 || fwidth(noderepr(nn2)[0]) < 0)
  540. X                return linelen(n1) == linelen(n2);
  541. X            return eqlines(nn1, nn2);
  542. X        }
  543. X    }
  544. X    return Yes;
  545. X}
  546. X
  547. X
  548. X/*
  549. X * Compute the length of the line beginning at the current node.
  550. X */
  551. X
  552. XVisible int
  553. Xlinelen(n)
  554. X    node n;
  555. X{
  556. X    register node nn;
  557. X    register string *rp = noderepr(n);
  558. X    register int w;
  559. X    register int nch = nchildren(n);
  560. X    register int i;
  561. X    register int len = fwidth(rp[0]);
  562. X
  563. X    if (len < 0)
  564. X        len = 0;
  565. X    for (i = 1; i <= nch; ++i) {
  566. X        nn = child(n, i);
  567. X        w = nodewidth(nn);
  568. X        if (w >= 0)
  569. X            len += w;
  570. X        else {
  571. X            n = nn;
  572. X            i = 0;
  573. X            nch = nchildren(n);
  574. X            rp = noderepr(n);
  575. X        }
  576. X        w = Fwidth(rp[i]);
  577. X        if (w < 0)
  578. X            break;
  579. X        len += w;
  580. X    }
  581. X    return len;
  582. X}
  583. X
  584. X
  585. X/*
  586. X * Move the focus to the next line.
  587. X * NB: This is a building block for use in the 'show' module;
  588. X * it cannot set ep->mode or call higher() properly!
  589. X */
  590. X
  591. XVisible bool
  592. Xnextline(pp)
  593. X    register path *pp;
  594. X{
  595. X    register node n;
  596. X    register node nn;
  597. X    register int w;
  598. X    register int nch;
  599. X    register int i = 0;
  600. X
  601. X    for (;;) {
  602. X        n = tree(*pp);
  603. X        if (nodewidth(n) < 0) {
  604. X            nch = nchildren(n);
  605. X            while (++i <= nch) {
  606. X                nn = child(n, i);
  607. X                w = nodewidth(nn);
  608. X                if (w < 0) {
  609. X                    if (!downi(pp, i)) Abort();
  610. X                    n = tree(*pp);
  611. X                    if (fwidth(noderepr(n)[0]) < 0)
  612. X                        return Yes;
  613. X                    nch = nchildren(n);
  614. X                    i = 0;
  615. X                }
  616. X            }
  617. X        }
  618. X        /* Must go upward in the tree */
  619. X        i = ichild(*pp);
  620. X        if (!up(pp))
  621. X            return No;
  622. X    }
  623. X}
  624. X
  625. X
  626. X/*
  627. X * Compute the current line number.  If the current node begins with
  628. X * a `newline', add one because the first character is actually
  629. X * on the next line.
  630. X */
  631. X
  632. XVisible int
  633. Xlineno(ep)
  634. X    register environ *ep;
  635. X{
  636. X    register int y;
  637. X
  638. X    y = -focoffset(ep);
  639. X    if (y < 0)
  640. X        y = 0;
  641. X    if (focchar(ep) == '\n')
  642. X        ++y;
  643. X    return y + Ycoord(ep->focus);
  644. X}
  645. X
  646. X
  647. X/*
  648. X * Similarly, compute the current column number.
  649. X * (Hope the abovementioned trick isn't necessary.)
  650. X */
  651. X
  652. XVisible int
  653. Xcolno(ep)
  654. X    environ *ep;
  655. X{
  656. X    int x= focoffset(ep);
  657. X
  658. X    if (x < 0)
  659. X        x= 0; /* In fact, give up */
  660. X    return x + Xcoord(ep->focus);
  661. X}
  662. X
  663. X
  664. X/*
  665. X * Make the focus exactly one line wide (if at all possible).
  666. X */
  667. X
  668. XVisible Procedure
  669. Xoneline(ep)
  670. X    register environ *ep;
  671. X{
  672. X    register node n;
  673. X    node nn;
  674. X    register string *rp;
  675. X    register int s1;
  676. X    register int s2;
  677. X    register int len;
  678. X    int ich;
  679. X    int nch;
  680. X
  681. X    ich = 1;
  682. X    while (nodewidth(tree(ep->focus)) >= 0) {
  683. X        ich = ichild(ep->focus);
  684. X        if (!up(&ep->focus)) {
  685. X            ep->mode = WHOLE;
  686. X            higher(ep);
  687. X            return;
  688. X        }
  689. X    }
  690. X    higher(ep);
  691. X    n = tree(ep->focus);
  692. X    nch = nchildren(n);
  693. X    rp = noderepr(n);
  694. X    for (s1 = 2*ich-1; s1 >= 1; --s1) {
  695. X        if (s1&1)
  696. X            len = fwidth(rp[s1/2]);
  697. X        else {
  698. X            nn = child(n, s1/2);
  699. X            len = nodewidth(nn);
  700. X        }
  701. X        if (len < 0)
  702. X            break;
  703. X    }
  704. X    for (s2 = 2*ich+1; s2 <= 2*nch+1; ++s2) {
  705. X        if (s2&1)
  706. X            len = fwidth(rp[s2/2]);
  707. X        else {
  708. X            nn = child(n, s2/2);
  709. X            len = nodewidth(nn);
  710. X        }
  711. X        if (len < 0)
  712. X            break;
  713. X    }
  714. X    ep->mode = SUBSET;
  715. X    ep->s1 = s1+1;
  716. X    ep->s2 = s2-1;
  717. X}
  718. END_OF_FILE
  719.   if test 4243 -ne `wc -c <'abc/bed/e1line.c'`; then
  720.     echo shar: \"'abc/bed/e1line.c'\" unpacked with wrong size!
  721.   fi
  722.   # end of 'abc/bed/e1line.c'
  723. fi
  724. if test -f 'abc/bint1/i1nur.c' -a "${1}" != "-c" ; then 
  725.   echo shar: Will not clobber existing file \"'abc/bint1/i1nur.c'\"
  726. else
  727.   echo shar: Extracting \"'abc/bint1/i1nur.c'\" \(5345 characters\)
  728.   sed "s/^X//" >'abc/bint1/i1nur.c' <<'END_OF_FILE'
  729. X/* Copyright (c) Stichting Mathematisch Centrum, Amsterdam, 1986. */
  730. X
  731. X/* Rational arithmetic */
  732. X
  733. X#include "b.h"
  734. X#include "feat.h"     /* for EXT_RANGE */
  735. X#include "bobj.h"
  736. X#include "i0err.h"
  737. X#include "i1num.h"
  738. X
  739. X/* Length calculations used for fraction sizes: */
  740. X
  741. X#define Maxlen(u, v) \
  742. X    (Roundsize(u) > Roundsize(v) ? Roundsize(u) : Roundsize(v))
  743. X#define Sumlen(u, v) (Roundsize(u)+Roundsize(v))
  744. X#define Difflen(u, v) (Roundsize(u)-Roundsize(v))
  745. X
  746. X/* To shut off lint and other warnings: */
  747. X#undef Copy
  748. X#define Copy(x) ((integer)copy((value)(x)))
  749. X
  750. X/* Globally used constants */
  751. X
  752. Xrational rat_half;
  753. X
  754. X/* Make a normalized rational from two integers */
  755. X
  756. XVisible rational mk_rat(x, y, len, simplify)
  757. X        integer x, y; int len; bool simplify; {
  758. X    rational a;
  759. X    integer u,v;
  760. X
  761. X    if (y == int_0) {
  762. X        if (interrupted)
  763. X            return rat_zero();
  764. X        syserr(MESS(1200, "mk_rat(x, y) with y=0"));
  765. X    }
  766. X
  767. X    if (x == int_0 && len <= 0) return rat_zero();
  768. X
  769. X    if (Msd(y) < 0) {    /* interchange signs */
  770. X        u = int_neg(x);
  771. X        v = int_neg(y);
  772. X    } else {
  773. X        u = Copy(x);
  774. X        v = Copy(y);
  775. X    }
  776. X
  777. X    a = (rational) grab_rat(len);
  778. X
  779. X    if (u == int_0 || v == int_1) {
  780. X        /* No simplification possible */
  781. X        Numerator(a) = Copy(u);
  782. X        Denominator(a) = int_1;
  783. X    }
  784. X    else if (!simplify) {
  785. X        Numerator(a) = Copy(u);
  786. X        Denominator(a) = Copy(v);
  787. X    }
  788. X    else {
  789. X        integer g, abs_u;
  790. X
  791. X        if (Msd(u) < 0) abs_u = int_neg(u);
  792. X        else abs_u = Copy(u);
  793. X        g = int_gcd(abs_u, v);
  794. X        Release(abs_u);
  795. X
  796. X        if (g != int_1) {
  797. X            Numerator(a) = int_quot(u, g);
  798. X            Denominator(a) = int_quot(v, g);
  799. X        } else {
  800. X            Numerator(a) = Copy(u);
  801. X            Denominator(a) = Copy(v);
  802. X        }
  803. X        Release(g);
  804. X    }
  805. X
  806. X    Release(u); Release(v);
  807. X
  808. X    return a;
  809. X}
  810. X
  811. X
  812. X/* Arithmetic on rational numbers */
  813. X
  814. X/* Shorthands: */
  815. X#define N(u) Numerator(u)
  816. X#define D(u) Denominator(u)
  817. X
  818. XVisible rational rat_sum(u, v) register rational u, v; {
  819. X    integer t1, t2, t3, t4;
  820. X    rational a;
  821. X
  822. X    t2= int_prod(N(u), D(v));
  823. X    t3= int_prod(N(v), D(u));
  824. X    t1= int_sum(t2, t3);
  825. X    t4= int_prod(D(u), D(v));
  826. X    a= mk_rat(t1, t4, Maxlen(u, v), Yes);
  827. X    Release(t1); Release(t2);
  828. X    Release(t3); Release(t4);
  829. X
  830. X    return a;
  831. X}
  832. X
  833. X
  834. XVisible rational rat_diff(u, v) register rational u, v; {
  835. X    integer t1, t2, t3, t4;
  836. X    rational a;
  837. X
  838. X    t2= int_prod(N(u), D(v));
  839. X    t3= int_prod(N(v), D(u));
  840. X    t1= int_diff(t2, t3);
  841. X    t4= int_prod(D(u), D(v));
  842. X    a= mk_rat(t1, t4, Maxlen(u, v), Yes);
  843. X    Release(t1); Release(t2);
  844. X    Release(t3); Release(t4);
  845. X
  846. X    return a;
  847. X}
  848. X
  849. X
  850. XVisible rational rat_prod(u, v) register rational u, v; {
  851. X    integer t1, t2;
  852. X    rational a;
  853. X
  854. X    t1= int_prod(N(u), N(v));
  855. X    t2= int_prod(D(u), D(v));
  856. X    a= mk_rat(t1, t2, Sumlen(u, v), Yes);
  857. X    Release(t1); Release(t2);
  858. X
  859. X    return a;
  860. X}
  861. X
  862. X
  863. XVisible rational rat_quot(u, v) register rational u, v; {
  864. X    integer t1, t2;
  865. X    rational a;
  866. X
  867. X    if (N(v) == int_0) {
  868. X        interr(ZERO_DIVIDE);
  869. X        return rat_zero();
  870. X    }
  871. X
  872. X    t1= int_prod(N(u), D(v));
  873. X    t2= int_prod(D(u), N(v));
  874. X    a= mk_rat(t1, t2, Difflen(u, v), Yes);
  875. X    Release(t1); Release(t2);
  876. X
  877. X    return a;
  878. X}
  879. X
  880. X
  881. XVisible rational rat_neg(u) register rational u; {
  882. X    register rational a;
  883. X
  884. X    /* Avoid a real subtraction from zero */
  885. X
  886. X    if (N(u) == int_0) return (rational) Copy(u);
  887. X
  888. X    a = (rational) grab_rat(0);
  889. X    N(a) = int_neg(N(u));
  890. X    D(a) = Copy(D(u));
  891. X    Length(a) = Length(u);
  892. X
  893. X    return a;
  894. X}
  895. X
  896. X/* Rational number to the integral power */
  897. X
  898. XVisible rational rat_power(a, n) rational a; integer n; {
  899. X    integer u, v, tu, tv, temp;
  900. X
  901. X    if (n == int_0) return mk_rat(int_1, int_1, 0, Yes);
  902. X
  903. X    if (Msd(n) < 0) {
  904. X        if (N(a) == int_0) {
  905. X            interr(NEG_POWER);
  906. X            return (rational) Copy(a);
  907. X        }
  908. X        if (Msd(N(a)) < 0) {
  909. X            u= int_neg(D(a));
  910. X            v = int_neg(N(a));
  911. X        }
  912. X        else {
  913. X            u = Copy(D(a));
  914. X            v = Copy(N(a));
  915. X        }
  916. X        n = int_neg(n);
  917. X    } else {
  918. X        if (N(a) == int_0) return (rational) Copy(a);
  919. X            /* To avoid necessary simplification later on */
  920. X        u = Copy(N(a));
  921. X        v = Copy(D(a));
  922. X        n = Copy(n);
  923. X    }
  924. X
  925. X    tu = int_1;
  926. X    tv = int_1;
  927. X    
  928. X    while (n != int_0 && !Interrupted()) {
  929. X        if (Odd(Lsd(n))) {
  930. X            if (u != int_1) {
  931. X                temp = tu;
  932. X                tu = int_prod(u, tu);
  933. X                Release(temp);
  934. X            }
  935. X            if (v != int_1) {
  936. X                temp = tv;
  937. X                tv = int_prod(v, tv);
  938. X                Release(temp);
  939. X            }
  940. X            if (n == int_1)
  941. X                break; /* Avoid useless last squaring */
  942. X        }
  943. X
  944. X        /* Square u, v */
  945. X
  946. X        if (u != int_1) {
  947. X            temp = u;
  948. X            u = int_prod(u, u);
  949. X            Release(temp);
  950. X        }
  951. X        if (v != int_1) {
  952. X            temp = v;
  953. X            v = int_prod(v, v);
  954. X            Release(temp);
  955. X        }
  956. X
  957. X        n = int_half(n);
  958. X    } /* while (n!=0) */
  959. X
  960. X    Release(n);
  961. X    Release(u);
  962. X    Release(v);
  963. X    a = mk_rat(tu, tv, 0, No);
  964. X    Release(tu); Release(tv);
  965. X
  966. X    return a;
  967. X}
  968. X
  969. X
  970. X/* Compare two rational numbers */
  971. X
  972. XVisible relation rat_comp(u, v) register rational u, v; {
  973. X    int sd, su, sv;
  974. X    integer nu, nv;
  975. X
  976. X    /* 1. Compare pointers */
  977. X    if (u == v || N(u) == N(v) && D(u) == D(v)) return 0;
  978. X
  979. X    /* 2. Either zero? */
  980. X    if (N(u) == int_0) return int_comp(int_0, N(v));
  981. X    if (N(v) == int_0) return int_comp(N(u), int_0);
  982. X
  983. X    /* 3. Compare signs */
  984. X    su = Msd(N(u));
  985. X    sv = Msd(N(v));
  986. X    su = (su>0) - (su<0);
  987. X    sv = (sv>0) - (sv<0);
  988. X    if (su != sv) return su > sv ? 1 : -1;
  989. X
  990. X    /* 4. Compute numerator of difference and return sign */
  991. X    nu= int_prod(N(u), D(v));
  992. X    nv= int_prod(N(v), D(u));
  993. X    sd= int_comp(nu, nv);
  994. X    Release(nu); Release(nv);
  995. X    return sd;
  996. X}
  997. X
  998. XVisible rational rat_zero() {
  999. X    rational r= (rational) grab_rat(0);
  1000. X    N(r) = int_0;
  1001. X    D(r) = int_1;
  1002. X    return r;
  1003. X}
  1004. X
  1005. XVisible Procedure rat_init() {
  1006. X    rat_half = (rational) grab_rat(0);
  1007. X    N(rat_half) = int_1;
  1008. X    D(rat_half) = int_2;
  1009. X}
  1010. X
  1011. XVisible Procedure endrat() {
  1012. X    Release(rat_half);
  1013. X}
  1014. END_OF_FILE
  1015.   if test 5345 -ne `wc -c <'abc/bint1/i1nur.c'`; then
  1016.     echo shar: \"'abc/bint1/i1nur.c'\" unpacked with wrong size!
  1017.   fi
  1018.   # end of 'abc/bint1/i1nur.c'
  1019. fi
  1020. if test -f 'abc/bint3/i3fil.c' -a "${1}" != "-c" ; then 
  1021.   echo shar: Will not clobber existing file \"'abc/bint3/i3fil.c'\"
  1022. else
  1023.   echo shar: Extracting \"'abc/bint3/i3fil.c'\" \(4560 characters\)
  1024.   sed "s/^X//" >'abc/bint3/i3fil.c' <<'END_OF_FILE'
  1025. X/* Copyright (c) Stichting Mathematisch Centrum, Amsterdam, 1986. */
  1026. X
  1027. X/* Facilities supplied by the file system */
  1028. X
  1029. X#include "b.h"
  1030. X#include "bmem.h"
  1031. X#include "bint.h"
  1032. X#include "bobj.h"
  1033. X#include "i2nod.h"
  1034. X#include "i2par.h"
  1035. X#include "i3scr.h"
  1036. X#include "i3sou.h"
  1037. X
  1038. XVisible Procedure f_rename(fname, nfname) value fname, nfname; {
  1039. X    char *f1, f2[100];
  1040. X    
  1041. X    strcpy(f2, strval(nfname));
  1042. X    unlink(f2);
  1043. X    f1= strval(fname);
  1044. X    VOID rename(f1, f2); 
  1045. X    /* what if it fails??? */
  1046. X}
  1047. X
  1048. XVisible Procedure f_delete(fname) value fname; {
  1049. X    unlink(strval(fname));
  1050. X}
  1051. X
  1052. XVisible unsigned f_size(file) FILE *file; {
  1053. X    long s, ftell();
  1054. X    fseek(file, 0l, 2);
  1055. X    s= ftell(file);
  1056. X    fseek(file, 0l, 0); /* rewind */
  1057. X    return s;
  1058. X}
  1059. X
  1060. XVisible Procedure f_close(ofile) FILE *ofile; {
  1061. X    bool ok= fflush(ofile) != EOF;
  1062. X    if (fclose(ofile) == EOF || !ok)
  1063. X        interr(MESS(3700, "write error (disk full?)"));
  1064. X}
  1065. X
  1066. XVisible bool f_interactive(file) FILE *file; {
  1067. X    return isatty(fileno(file));
  1068. X}
  1069. X
  1070. X/* f_getline() returns a line from a file with the newline character */
  1071. X
  1072. X#define LINESIZE 200
  1073. X
  1074. XVisible char *f_getline(file) FILE *file; {
  1075. X    char line[LINESIZE];
  1076. X    char *pline= NULL;
  1077. X    
  1078. X    while (fgets(line, LINESIZE, file) != NULL) {
  1079. X        if (pline == NULL)
  1080. X            pline= (char *) savestr(line);
  1081. X        else {
  1082. X            int len= strlen(pline) + strlen(line) + 1;
  1083. X            regetmem(&pline, (unsigned) len);
  1084. X            strcat(pline, line);
  1085. X        }
  1086. X        if (strchr(pline, '\n') != NULL)
  1087. X            return pline;
  1088. X    }
  1089. X    if (pline != NULL)
  1090. X        freestr(pline);
  1091. X    return NULL;
  1092. X}
  1093. X
  1094. XHidden struct class { literal type; char *suffix; };
  1095. X
  1096. XHidden struct class classes[]= {
  1097. X    {Cmd, Cmd_ext},
  1098. X    {Zfd, Zfd_ext},
  1099. X    {Mfd, Mfd_ext},
  1100. X    {Dfd, Dfd_ext},
  1101. X    {Zpd, Zpd_ext},
  1102. X    {Mpd, Mpd_ext},
  1103. X    {Dpd, Dpd_ext},
  1104. X    {Tar, Cts_ext},
  1105. X    {Wsp, Wsp_ext}
  1106. X};
  1107. X
  1108. X#define NCLASSES (sizeof classes / sizeof classes[0])
  1109. X
  1110. XHidden char *filesuffix(type) literal type; {
  1111. X    register struct class *cp;
  1112. X
  1113. X    for (cp= classes; cp < &classes[NCLASSES]; ++cp) {
  1114. X        if (type == cp->type)
  1115. X            return cp->suffix;
  1116. X    }
  1117. X    return "";
  1118. X}
  1119. X
  1120. X/*
  1121. X * the following constants were moved here from all os.h's
  1122. X * to use more portable filenames;
  1123. X * e.g. MSDOS conventions, since these are the most limited.
  1124. X */
  1125. X#define FNMLEN 8
  1126. X#define SUFFIXLEN 4
  1127. X
  1128. XVisible value new_fname(name, type) value name; literal type; {
  1129. X    char fname[FNMLEN + SUFFIXLEN + 1];
  1130. X    char *suffix= filesuffix(type);
  1131. X    string sname= strval(name);
  1132. X    char *sp= strchr(sname, ' ');
  1133. X    intlet len= sp ? sp-sname : strlen(sname);
  1134. X        /* if a command name only the first keyword */
  1135. X    
  1136. X    if (len > FNMLEN) len= FNMLEN;
  1137. X    strncpy(fname, sname, len); fname[len]= '\0';
  1138. X    strcat(fname, suffix);
  1139. X    /* convert also if not MSDOS, to make abc-ws's portable: */
  1140. X    conv_fname(fname, suffix);
  1141. X    if (type != Wsp &&
  1142. X        F_exists(fname) &&
  1143. X        !fnm_extend(fname, len, suffix) &&
  1144. X        !fnm_narrow(fname, len)
  1145. X       )
  1146. X        return Vnil;
  1147. X    return mk_text(fname);
  1148. X}
  1149. X
  1150. XHidden bool fnm_extend(fname, n, suffix) char *fname, *suffix; int n; {
  1151. X    /* e.g. "ABC.cmd" => "ABC1.cmd" */
  1152. X    int m;
  1153. X    int k= n;
  1154. X    
  1155. X    do {
  1156. X        for (m= k-1; fname[m] == '9'; --m);
  1157. X        if (isdigit(fname[m])) {
  1158. X            ++fname[m];
  1159. X            while (++m < k) fname[m]= '0';
  1160. X        }
  1161. X        else if (k >= FNMLEN) {
  1162. X            /* reset */
  1163. X            fname[n]= '\0';
  1164. X            strcat(fname, suffix);
  1165. X            return No;
  1166. X        }
  1167. X        else {
  1168. X            fname[++m]= '1';
  1169. X            while (++m <= k) fname[m]= '0';
  1170. X            fname[++k]= '\0';
  1171. X            strcat(fname, suffix);
  1172. X        }
  1173. X    }
  1174. X    while (F_exists(fname));
  1175. X    return Yes;
  1176. X}
  1177. X
  1178. XHidden bool fnm_narrow(fname, n) char *fname; int n; {
  1179. X    /* e.g. "ABC.cmd" => "AB1.cmd" */
  1180. X    int m;
  1181. X    
  1182. X    do {
  1183. X        for (m= n-1; ; --m) {
  1184. X            if (m < 1)
  1185. X                return No;
  1186. X            else if (!isdigit(fname[m])) { 
  1187. X                fname[m]= '1'; 
  1188. X                break; 
  1189. X            }
  1190. X            else if (fname[m] != '9') { 
  1191. X                ++fname[m]; 
  1192. X                break; 
  1193. X            }
  1194. X            else fname[m]= '0';
  1195. X        }
  1196. X    }
  1197. X    while (F_exists(fname));
  1198. X    return Yes;
  1199. X}
  1200. X
  1201. X/* Conversion of characters:
  1202. X *  . uppercase to lowercase
  1203. X *  . point to CONVP_SIGN
  1204. X *  . double quote to CONVDQ_SIGN
  1205. X *  . single quote can stay
  1206. X *  the latter is as portably unspecial as possible.
  1207. X */
  1208. X
  1209. XHidden Procedure conv_fname(fname, suffix) char *fname, *suffix; {
  1210. X    char *ext_point= fname + strlen(fname) - strlen(suffix);
  1211. X    
  1212. X    while (fname < ext_point) {
  1213. X        if (isupper(*fname)) 
  1214. X            *fname= tolower(*fname);
  1215. X        else if (*fname == C_QUOTE)
  1216. X            *fname= CONVDQ_SIGN;
  1217. X        else if (*fname == C_POINT)
  1218. X            *fname= CONVP_SIGN;
  1219. X        fname++;
  1220. X    }
  1221. X}
  1222. X
  1223. X/* recover location or workspace name from filename */
  1224. X
  1225. XVisible value mkabcname(name) char *name; {
  1226. X    char *p;
  1227. X    
  1228. X    for (p= name; *p != '\0'; ++p) {
  1229. X        if (Cap(*p))
  1230. X            *p= tolower(*p);
  1231. X        else if (*p == CONVP_SIGN)
  1232. X            *p= (*(p+1) == '\0' ? '\0' : C_POINT);
  1233. X        else if (*p == CONVDQ_SIGN)
  1234. X            *p= C_QUOTE;
  1235. X        else if (!Tagmark(p))
  1236. X            *p= C_QUOTE;
  1237. X    }
  1238. X    return mk_text(name);
  1239. X}
  1240. END_OF_FILE
  1241.   if test 4560 -ne `wc -c <'abc/bint3/i3fil.c'`; then
  1242.     echo shar: \"'abc/bint3/i3fil.c'\" unpacked with wrong size!
  1243.   fi
  1244.   # end of 'abc/bint3/i3fil.c'
  1245. fi
  1246. if test -f 'abc/bio/i4fil.c' -a "${1}" != "-c" ; then 
  1247.   echo shar: Will not clobber existing file \"'abc/bio/i4fil.c'\"
  1248. else
  1249.   echo shar: Extracting \"'abc/bio/i4fil.c'\" \(4420 characters\)
  1250.   sed "s/^X//" >'abc/bio/i4fil.c' <<'END_OF_FILE'
  1251. X/* Copyright (c) Stichting Mathematisch Centrum, Amsterdam, 1988. */
  1252. X
  1253. X#include "b.h"
  1254. X#include "bfil.h"
  1255. X#include "bmem.h"
  1256. X#include "bobj.h"
  1257. X#include "i3sou.h"
  1258. X
  1259. X#ifdef HAS_READDIR
  1260. X#include <sys/dir.h>
  1261. X#else
  1262. X#include "dir.h"
  1263. X#endif
  1264. X
  1265. X/**************************************************************************/
  1266. X/* get_names() is used to get at the names of all ABC files/workspaces      */
  1267. X/* in a given directory.                          */
  1268. X/*                                      */
  1269. X/* This version of the file is supposed to work for any kind of Unix      */
  1270. X/* and for MS-DOS.                              */
  1271. X/**************************************************************************/
  1272. X
  1273. X    /* Note: it uses readdir so isn't portable to non-BSD
  1274. X       Unix, unless you also port readdir and friends.
  1275. X       Luckily, public-domain versions are available,
  1276. X       and one should be distributed with ABC.
  1277. X       It works for MS-DOS because I have ported readdir
  1278. X       to MS-DOS, too.  Guido. */
  1279. X
  1280. XVisible value get_names(path, isabc) char *path; bool (*isabc)(); {
  1281. X    DIR *dp;
  1282. X    struct direct *dirp;
  1283. X    value v;
  1284. X    value name;
  1285. X    
  1286. X    dp= opendir(path);
  1287. X    if (dp == (DIR *) NULL)
  1288. X        return Vnil;
  1289. X    v= mk_elt();
  1290. X    for (;;) {
  1291. X        dirp= readdir(dp);
  1292. X        if (dirp == (struct direct *) NULL) {
  1293. X            closedir(dp);
  1294. X            break;
  1295. X        }
  1296. X        if ((*isabc)(path, dirp->d_name)) {
  1297. X            name= mk_text(dirp->d_name);
  1298. X            insert(name, &v);
  1299. X            release(name);
  1300. X        }
  1301. X    }
  1302. X    return v;
  1303. X}
  1304. X
  1305. X/**************************************************************************/
  1306. X/* Is this the name of a target, a unit or something else?          */
  1307. X/*                                      */
  1308. X/* For compatibility, we recognize files starting with =, <, ", > and ',  */
  1309. X/* and files ending with ".how", ".zer", ".mon", ".dya" and ".tar".      */
  1310. X/* Otherwise, unit names must end in ".cmd", ".zfd", ".mfd", ".dfd",      */
  1311. X/* ".zpd", ".mpd" or ".dpd",                                              */
  1312. X/* and target names must end in ".cts" (all ignoring case).          */
  1313. X/**************************************************************************/
  1314. X
  1315. X#define DumClass '\0'
  1316. X
  1317. XHidden struct class { char *suffix; literal type; };
  1318. X
  1319. XHidden struct class classes[]= {
  1320. X    {".cmd", Cmd},
  1321. X    {".zfd", Zfd},
  1322. X    {".mfd", Mfd},
  1323. X    {".dfd", Dfd},
  1324. X    {".zpd", Zpd},
  1325. X    {".mpd", Mpd},
  1326. X    {".dpd", Dpd},
  1327. X    {".cts", Tar},
  1328. X    
  1329. X    {".CMD", Cmd},
  1330. X    {".ZFD", Zfd},
  1331. X    {".MFD", Mfd},
  1332. X    {".DFD", Dfd},
  1333. X    {".ZPD", Zpd},
  1334. X    {".MPD", Mpd},
  1335. X    {".DPD", Dpd},
  1336. X    {".CTS", Tar},
  1337. X    
  1338. X    {".how", OldHow},
  1339. X    {".zer", OldHow},
  1340. X    {".mon", OldHow},
  1341. X    {".dya", OldHow},
  1342. X    {".tar", OldTar},
  1343. X
  1344. X    {".HOW", OldHow},
  1345. X    {".ZER", OldHow},
  1346. X    {".MON", OldHow},
  1347. X    {".DYA", OldHow},
  1348. X    {".TAR", OldTar}
  1349. X};
  1350. X
  1351. X#define NCLASSES (sizeof classes / sizeof classes[0])
  1352. X
  1353. XHidden literal classfile(fname) value fname; {
  1354. X    char *sfname, *end;
  1355. X    struct class *cp;
  1356. X
  1357. X    sfname= strval(fname);
  1358. X    switch (sfname[0]) {
  1359. X        case '\'': case '<': case '"': case '>':
  1360. X            return OldHow;
  1361. X        case '=':
  1362. X            return OldTar;
  1363. X        default:
  1364. X            break;
  1365. X    }
  1366. X    end= sfname + strlen(sfname);
  1367. X    for (cp= classes; cp < &classes[NCLASSES]; ++cp) {
  1368. X        if (end-strlen(cp->suffix) >= sfname
  1369. X            && strcmp(end-strlen(cp->suffix), cp->suffix) == 0)
  1370. X            return cp->type;
  1371. X    }
  1372. X    return DumClass;
  1373. X}
  1374. X
  1375. XVisible bool abcfile(path, name) char *path, *name; {
  1376. X    /* path argument needed, but not used */
  1377. X    bool isfile;
  1378. X    value f= mk_text(name);
  1379. X    
  1380. X    isfile= classfile(f) != DumClass ? Yes : No;
  1381. X    release(f);
  1382. X    return isfile;
  1383. X}
  1384. X
  1385. XVisible bool abcworkspace(path, name) char *path, *name; {
  1386. X    struct stat statbuf;
  1387. X    char *path1, *path2;
  1388. X    bool isws= No;
  1389. X    
  1390. X    path1= makepath(path, name);
  1391. X    if (stat(path1, &statbuf) == 0 &&
  1392. X        ((statbuf.st_mode & S_IFMT) == S_IFDIR) &&
  1393. X        (strcmp(name, CURDIR) != 0) &&
  1394. X        (strcmp(name, PARENTDIR) != 0)
  1395. X       ) {
  1396. X        path2= makepath(path1, permfile);
  1397. X        isws= F_exists(path2) ? Yes : No;
  1398. X        freepath(path2);
  1399. X    }
  1400. X    freepath(path1);
  1401. X    return isws;
  1402. X}
  1403. X
  1404. XVisible bool targetfile(fname) value fname; {
  1405. X    switch (classfile(fname)) {
  1406. X        case Tar: case OldTar:
  1407. X            return Yes;
  1408. X        default:
  1409. X            return No;
  1410. X    }
  1411. X}
  1412. X
  1413. XVisible bool unitfile(fname) value fname; {
  1414. X    switch (classfile(fname)) {
  1415. X        case Tar: case OldTar: case DumClass:
  1416. X            return No;
  1417. X        default: 
  1418. X            return Yes;
  1419. X    }
  1420. X}
  1421. X
  1422. XVisible char *base_fname(fname) value fname; {
  1423. X    char *sname;
  1424. X    char *base;
  1425. X    char *pext;
  1426. X    
  1427. X    sname= strval(fname);
  1428. X    switch (*sname) {
  1429. X        case '\'': case '<': case '"': case '>': case '=':
  1430. X            ++sname;
  1431. X        default:
  1432. X            break;
  1433. X    }
  1434. X    base= savestr(sname);
  1435. X    if ((pext= strrchr(base, '.')) != NULL)
  1436. X        *pext= '\0';
  1437. X    return base;
  1438. X}
  1439. X
  1440. XVisible bool typeclash(pname, fname) value pname, fname; {
  1441. X    return classfile(fname) != Permtype(pname) ? Yes : No;
  1442. X}
  1443. END_OF_FILE
  1444.   if test 4420 -ne `wc -c <'abc/bio/i4fil.c'`; then
  1445.     echo shar: \"'abc/bio/i4fil.c'\" unpacked with wrong size!
  1446.   fi
  1447.   # end of 'abc/bio/i4fil.c'
  1448. fi
  1449. if test -f 'abc/boot/Makefile' -a "${1}" != "-c" ; then 
  1450.   echo shar: Will not clobber existing file \"'abc/boot/Makefile'\"
  1451. else
  1452.   echo shar: Extracting \"'abc/boot/Makefile'\" \(4701 characters\)
  1453.   sed "s/^X//" >'abc/boot/Makefile' <<'END_OF_FILE'
  1454. X# EDIT MY ANCESTOR Makefile.bsd
  1455. X# AND SAY 'make -f Makefile.bsd Makefile'
  1456. X#
  1457. X# BSD Makefile for booting grammar tables with mktable from grammar file.
  1458. X#
  1459. X
  1460. X# --- Where to install the stuff ---
  1461. X
  1462. XCFILE=../bed/e1tabl.c
  1463. XHFILE=../ehdrs/tabl.h
  1464. X
  1465. X# --- What is the C preprocessor called ---
  1466. X#
  1467. X# ../scripts/mkdep has the right CPP if Setup succeeded and your UNIX ain't BSD
  1468. X
  1469. XCPP=    /bin/cc -E
  1470. X
  1471. X# --- Flags to the C compiler ---
  1472. X
  1473. XBINCL=    -I../bhdrs -I../ehdrs -I../uhdrs
  1474. XDEFS=    -DNDEBUG -DBSD
  1475. XCFLAGS= -O $(DEFS) $(BINCL)
  1476. XLDFLAGS=-s
  1477. XLIBS=    
  1478. XGDEFS=
  1479. X
  1480. X# --- Stuff for lint ---
  1481. X
  1482. XLINT=        lint
  1483. XLINTFLAGS=    -abh
  1484. XLBINCL=        $(BINCL)
  1485. X
  1486. X# --- Relevant files ---
  1487. X
  1488. XOBJS=    main.o alloc.o read.o fill.o comp.o dump.o code.o
  1489. X
  1490. XSRCS=    main.c alloc.c read.c fill.c comp.c dump.c ../bed/e1code.c
  1491. X
  1492. XHDRS=    ../bhdrs/b.h main.h ../ehdrs/code.h lang.h
  1493. X
  1494. X# --- Main entries of the makefile ---
  1495. X
  1496. Xall: tabl.c.out tabl.h.out
  1497. X
  1498. Xtabl.c.out tabl.h.out: grammar mktable
  1499. X    mktable -g grammar -h tabl.h -t tabl.c.out -i tabl.h.out
  1500. X
  1501. Xgrammar: grammar.abc lang.h
  1502. X    $(CPP) $(GDEFS) grammar.abc 2>/dev/null | sed -e "/^$$/d" -e "/^#/d" >grammar
  1503. X
  1504. Xmktable: $(OBJS)
  1505. X    $(CC) $(LDFLAGS) $(OBJS) $(LIBS) -o mktable
  1506. X
  1507. Xinstall: $(CFILE) $(HFILE)
  1508. X
  1509. X$(CFILE): tabl.c.out
  1510. X    cp tabl.c.out $(CFILE)
  1511. X
  1512. X$(HFILE): tabl.h.out
  1513. X    cp tabl.h.out $(HFILE)
  1514. X
  1515. Xclean:
  1516. X    rm -f *.o mktable grammar tabl.c.out tabl.h.out tabl.c tabl.h
  1517. X
  1518. Xclobber: clean
  1519. X    rm -f lint tags
  1520. X
  1521. Xcode.o: ../bed/e1code.c
  1522. X    $(CC) -c $(CFLAGS) ../bed/e1code.c -o code.o
  1523. X
  1524. X# --- Utilities for the programmer ---
  1525. X
  1526. Xmflags:
  1527. X    echo MFLAGS=\"$(MFLAGS)\", MAKEFLAGS=\"$(MAKEFLAGS)\"
  1528. X
  1529. X# If your UNIX isn't BSD4.2 or higher, use:
  1530. X# MKDEP=../scripts/mkdep
  1531. XMKDEP=$(CC) -M
  1532. X
  1533. XMakefile: ALWAYS
  1534. X    rm -f Makefile
  1535. X    (echo "# EDIT MY ANCESTOR Makefile.bsd"; \
  1536. X     echo "# AND SAY 'make -f Makefile.bsd Makefile'"; \
  1537. X     cat Makefile.bsd; \
  1538. X     $(MKDEP) $(DEFS) $(BINCL) $(SRCS); \
  1539. X    ) >Makefile
  1540. X
  1541. Xlint:    $(SRCS) $(HDRS)
  1542. X    $(LINT) $(LINTFLAGS) $(DEFS) $(LBINCL) $(SRCS) >lint
  1543. X
  1544. Xtags:    $(HDRS) $(SRCS)
  1545. X    rm -f tags
  1546. X    ctags $(HDRS) $(SRCS)
  1547. X
  1548. Xtest:    all
  1549. X    cp tabl.h.out tabl.h
  1550. X    cp tabl.c.out tabl.c
  1551. X    cc -c $(CFLAGS) tabl.c
  1552. X
  1553. XALWAYS:    #dummy
  1554. X
  1555. X###
  1556. Xmain.o: main.c
  1557. Xmain.o: ../bhdrs/b.h
  1558. Xmain.o: ../uhdrs/osconf.h
  1559. Xmain.o: /usr/include/stdio.h
  1560. Xmain.o: ../uhdrs/os.h
  1561. Xmain.o: /usr/include/math.h
  1562. Xmain.o: /usr/include/ctype.h
  1563. Xmain.o: /usr/include/strings.h
  1564. Xmain.o: /usr/include/sys/types.h
  1565. Xmain.o: /usr/include/sys/stat.h
  1566. Xmain.o: /usr/include/sys/file.h
  1567. Xmain.o: ../uhdrs/conf.h
  1568. Xmain.o: ../uhdrs/config.h
  1569. Xmain.o: ./main.h
  1570. Xalloc.o: alloc.c
  1571. Xalloc.o: ../bhdrs/b.h
  1572. Xalloc.o: ../uhdrs/osconf.h
  1573. Xalloc.o: /usr/include/stdio.h
  1574. Xalloc.o: ../uhdrs/os.h
  1575. Xalloc.o: /usr/include/math.h
  1576. Xalloc.o: /usr/include/ctype.h
  1577. Xalloc.o: /usr/include/strings.h
  1578. Xalloc.o: /usr/include/sys/types.h
  1579. Xalloc.o: /usr/include/sys/stat.h
  1580. Xalloc.o: /usr/include/sys/file.h
  1581. Xalloc.o: ../uhdrs/conf.h
  1582. Xalloc.o: ../uhdrs/config.h
  1583. Xalloc.o: ./main.h
  1584. Xread.o: read.c
  1585. Xread.o: ../bhdrs/b.h
  1586. Xread.o: ../uhdrs/osconf.h
  1587. Xread.o: /usr/include/stdio.h
  1588. Xread.o: ../uhdrs/os.h
  1589. Xread.o: /usr/include/math.h
  1590. Xread.o: /usr/include/ctype.h
  1591. Xread.o: /usr/include/strings.h
  1592. Xread.o: /usr/include/sys/types.h
  1593. Xread.o: /usr/include/sys/stat.h
  1594. Xread.o: /usr/include/sys/file.h
  1595. Xread.o: ../uhdrs/conf.h
  1596. Xread.o: ../uhdrs/config.h
  1597. Xread.o: ./main.h
  1598. Xfill.o: fill.c
  1599. Xfill.o: ../bhdrs/b.h
  1600. Xfill.o: ../uhdrs/osconf.h
  1601. Xfill.o: /usr/include/stdio.h
  1602. Xfill.o: ../uhdrs/os.h
  1603. Xfill.o: /usr/include/math.h
  1604. Xfill.o: /usr/include/ctype.h
  1605. Xfill.o: /usr/include/strings.h
  1606. Xfill.o: /usr/include/sys/types.h
  1607. Xfill.o: /usr/include/sys/stat.h
  1608. Xfill.o: /usr/include/sys/file.h
  1609. Xfill.o: ../uhdrs/conf.h
  1610. Xfill.o: ../uhdrs/config.h
  1611. Xfill.o: ./main.h
  1612. Xcomp.o: comp.c
  1613. Xcomp.o: ../bhdrs/b.h
  1614. Xcomp.o: ../uhdrs/osconf.h
  1615. Xcomp.o: /usr/include/stdio.h
  1616. Xcomp.o: ../uhdrs/os.h
  1617. Xcomp.o: /usr/include/math.h
  1618. Xcomp.o: /usr/include/ctype.h
  1619. Xcomp.o: /usr/include/strings.h
  1620. Xcomp.o: /usr/include/sys/types.h
  1621. Xcomp.o: /usr/include/sys/stat.h
  1622. Xcomp.o: /usr/include/sys/file.h
  1623. Xcomp.o: ../uhdrs/conf.h
  1624. Xcomp.o: ../uhdrs/config.h
  1625. Xcomp.o: ./main.h
  1626. Xcomp.o: ../ehdrs/code.h
  1627. Xdump.o: dump.c
  1628. Xdump.o: ../bhdrs/b.h
  1629. Xdump.o: ../uhdrs/osconf.h
  1630. Xdump.o: /usr/include/stdio.h
  1631. Xdump.o: ../uhdrs/os.h
  1632. Xdump.o: /usr/include/math.h
  1633. Xdump.o: /usr/include/ctype.h
  1634. Xdump.o: /usr/include/strings.h
  1635. Xdump.o: /usr/include/sys/types.h
  1636. Xdump.o: /usr/include/sys/stat.h
  1637. Xdump.o: /usr/include/sys/file.h
  1638. Xdump.o: ../uhdrs/conf.h
  1639. Xdump.o: ../uhdrs/config.h
  1640. Xdump.o: ./main.h
  1641. Xe1code.o: ../bed/e1code.c
  1642. Xe1code.o: ../bhdrs/b.h
  1643. Xe1code.o: ../uhdrs/osconf.h
  1644. Xe1code.o: /usr/include/stdio.h
  1645. Xe1code.o: ../uhdrs/os.h
  1646. Xe1code.o: /usr/include/math.h
  1647. Xe1code.o: /usr/include/ctype.h
  1648. Xe1code.o: /usr/include/strings.h
  1649. Xe1code.o: /usr/include/sys/types.h
  1650. Xe1code.o: /usr/include/sys/stat.h
  1651. Xe1code.o: /usr/include/sys/file.h
  1652. Xe1code.o: ../uhdrs/conf.h
  1653. Xe1code.o: ../uhdrs/config.h
  1654. Xe1code.o: ../ehdrs/code.h
  1655. END_OF_FILE
  1656.   if test 4701 -ne `wc -c <'abc/boot/Makefile'`; then
  1657.     echo shar: \"'abc/boot/Makefile'\" unpacked with wrong size!
  1658.   fi
  1659.   # end of 'abc/boot/Makefile'
  1660. fi
  1661. if test -f 'abc/ihdrs/i1num.h' -a "${1}" != "-c" ; then 
  1662.   echo shar: Will not clobber existing file \"'abc/ihdrs/i1num.h'\"
  1663. else
  1664.   echo shar: Extracting \"'abc/ihdrs/i1num.h'\" \(4302 characters\)
  1665.   sed "s/^X//" >'abc/ihdrs/i1num.h' <<'END_OF_FILE'
  1666. X/* Copyright (c) Stichting Mathematisch Centrum, Amsterdam, 1986. */
  1667. X
  1668. X/************************************************************************/
  1669. X/* Full numeric package: private definitions                            */
  1670. X/*                                                                      */
  1671. X/* A number is modelled as one of zero, unbounded integer,              */
  1672. X/*        unbounded rational or approximate.                            */
  1673. X/*     Zero has a 'length' field of zero, and nothing else.             */
  1674. X/*     A length field of +n means the number is an n digit integer,     */
  1675. X/*        (with digits to some large base).                             */
  1676. X/*     A length of -1 means there follow two floating point numbers,    */
  1677. X/*        one the fraction (zero or .5 <= frac <= 1), one the exponent  */
  1678. X/*        with respect to base 2 (should be an integral value).         */
  1679. X/*        (This is so when EXT_RANGE is defined.  Otherwise, there is   */
  1680. X/*        only one field, frac, which is not normalized.  This saves    */
  1681. X/*        code and data space on e.g. the IBM PC, where the natural     */
  1682. X/*        range of double's is sufficient (~1E307).)                    */
  1683. X/*     A length of -2 means there follow two values, pointers to two    */
  1684. X/*        unbounded integers, ie a rational number.                     */
  1685. X/*     A length of -n, n>2, means it is a rational with a print width   */
  1686. X/*        of n-2.                                                       */
  1687. X/*                                                                      */
  1688. X/************************************************************************/
  1689. X
  1690. X/*************** Definitions exported for integers *****************/
  1691. X
  1692. X/* typedef int digit; or short; calculated in mkconfig -> config.h */
  1693. X
  1694. Xtypedef struct integer {
  1695. X    HEADER;
  1696. X    digit    dig[1];
  1697. X} *integer;
  1698. X
  1699. X#define FreezeSmallInt(v, vv) \
  1700. X    (IsSmallInt(v) && (Freeze1(v, vv), Freeze2(v, vv)))
  1701. X#define Freeze1(v, vv) ((vv).type= Num, (vv).refcnt= Maxrefcnt)
  1702. X#define Freeze2(v, vv) \
  1703. X    ((vv).len= (v) != 0, (vv).dig[0]= SmallIntVal(v), (v)= &(vv))
  1704. X
  1705. Xinteger int_gadd();
  1706. Xinteger int_canon();
  1707. Xinteger int_sum();
  1708. Xinteger int_prod();
  1709. Xinteger int_diff();
  1710. Xinteger int_quot();
  1711. Xinteger int_neg();
  1712. Xinteger int_gcd();
  1713. Xinteger mk_int();
  1714. Xinteger int1mul();
  1715. Xinteger int_tento();
  1716. Xinteger int_half();
  1717. Xinteger int_mod();
  1718. Xdigit int_ldiv();
  1719. X
  1720. X#define int_0 ((integer) MkSmallInt(0))
  1721. X#define int_1 ((integer) MkSmallInt(1))
  1722. X#define int_2 ((integer) MkSmallInt(2))
  1723. X#define int_5 ((integer) MkSmallInt(5))
  1724. X#define int_10 ((integer) MkSmallInt(10))
  1725. X#define int_min1 ((integer) MkSmallInt(-1))
  1726. X
  1727. X#define Integral(v) (IsSmallInt(v) || Length(v)>=0)
  1728. X#define Modulo(a,b) (((a)%(b)+(b))%(b))
  1729. X#define Digit(v,n) ((v)->dig[n])
  1730. X#define Msd(v) (IsSmallInt(v) ? SmallIntVal(v) : Digit(v,Length(v)-1))
  1731. X#define Lsd(v) (IsSmallInt(v) ? SmallIntVal(v) : Digit(v,0))
  1732. X
  1733. X#define Odd(x) ((x)&1)
  1734. X#define Even(x) (!Odd(x))
  1735. X
  1736. X/* Provisional definitions */
  1737. X
  1738. X#define Copy(x) copy((value)(x))
  1739. X#define Release(x) release((value)(x))
  1740. X
  1741. X/***************** Definitions exported for rationals *****************/
  1742. X
  1743. Xtypedef struct {
  1744. X    HEADER;
  1745. X    integer    num, den;
  1746. X} *rational;
  1747. X
  1748. X
  1749. X#define Numerator(a) ((a)->num)
  1750. X#define Denominator(a) ((a)->den)
  1751. X#define Rational(a) (!IsSmallInt(a) && Length(a)<-1)
  1752. X#define Roundsize(a) (-2-Length(a))
  1753. X
  1754. Xrational mk_rat();
  1755. Xrational rat_sum();
  1756. Xrational rat_diff();
  1757. Xrational rat_neg();
  1758. Xrational rat_prod();
  1759. Xrational rat_quot();
  1760. Xrational rat_power();
  1761. Xrational rat_zero();
  1762. X
  1763. Xextern rational rat_half;
  1764. X
  1765. Xvalue tento();
  1766. Xvalue mk_exact();
  1767. X
  1768. X/***************** Definitions exported for approximate numbers *************/
  1769. X
  1770. Xtypedef struct real {
  1771. X    HEADER;
  1772. X    double    frac;
  1773. X#ifdef EXT_RANGE
  1774. X    double    expo;
  1775. X#endif /* EXT_RANGE */
  1776. X} *real;
  1777. X
  1778. X#define Frac(v) ((v)->frac)
  1779. X#ifdef EXT_RANGE
  1780. X#define Expo(v) ((v)->expo)
  1781. X#else
  1782. X#define Expo(v) 0.0
  1783. X#endif
  1784. X
  1785. X#define Approximate(v) (!IsSmallInt(v) && Length(v)==-1)
  1786. X#define Exact(v) (!Approximate(v))
  1787. X
  1788. Xextern real app_0;
  1789. X
  1790. Xreal mk_approx();
  1791. X
  1792. Xreal app_sum();
  1793. Xreal app_diff();
  1794. Xreal app_prod();
  1795. Xreal app_quot();
  1796. Xreal app_neg();
  1797. X
  1798. Xreal app_exp();
  1799. Xreal app_log();
  1800. Xreal app_power();
  1801. X
  1802. Xvalue app_frexp();
  1803. Xinteger app_floor();
  1804. Xvalue app_exactly();
  1805. X
  1806. Xvalue prod2n();
  1807. Xvalue prod10n();
  1808. Xrational ratsumhalf();
  1809. X
  1810. Xvalue grab_num();
  1811. Xvalue regrab_num();
  1812. Xvalue grab_rat();
  1813. X
  1814. Xdouble frexp(), ldexp();
  1815. END_OF_FILE
  1816.   if test 4302 -ne `wc -c <'abc/ihdrs/i1num.h'`; then
  1817.     echo shar: \"'abc/ihdrs/i1num.h'\" unpacked with wrong size!
  1818.   fi
  1819.   # end of 'abc/ihdrs/i1num.h'
  1820. fi
  1821. if test -f 'abc/keys/keyhlp.c' -a "${1}" != "-c" ; then 
  1822.   echo shar: Will not clobber existing file \"'abc/keys/keyhlp.c'\"
  1823. else
  1824.   echo shar: Extracting \"'abc/keys/keyhlp.c'\" \(4623 characters\)
  1825.   sed "s/^X//" >'abc/keys/keyhlp.c' <<'END_OF_FILE'
  1826. X/* Copyright (c) Stichting Mathematisch Centrum, Amsterdam, 1989. */
  1827. X
  1828. X/*
  1829. X * ABC keys -- Print the bindings.
  1830. X */
  1831. X
  1832. X#include "b.h"
  1833. X#include "feat.h"
  1834. X#include "bmem.h"
  1835. X#include "keys.h"
  1836. X#include "getc.h"
  1837. X
  1838. X/*
  1839. X   The following array determines the order of the editor operations
  1840. X   in the helpblurb.
  1841. X   The names and keyrepresentations are taken from deftab in e1getc.c
  1842. X   and ?1keys.c.
  1843. X   Printing is done in two columns.
  1844. X   Code NOTHING is used to produce an empty place in the second column.
  1845. X */
  1846. Xint helpcode[]= {
  1847. X    WIDEN,        EXTEND,
  1848. X    FIRST,        LAST,
  1849. X    PREVIOUS,    NEXT,
  1850. X    UPLINE,        DOWNLINE,
  1851. X    UPARROW,    DOWNARROW,
  1852. X    LEFTARROW,    RITEARROW,
  1853. X#ifdef GOTOCURSOR
  1854. X    GOTO,        NOTHING,
  1855. X#endif
  1856. X    ACCEPT,        NEWLINE,
  1857. X    UNDO,        REDO,
  1858. X    COPY,        DELETE,
  1859. X    RECORD,        PLAYBACK,
  1860. X    LOOK,        HELP,
  1861. X#ifdef CANSUSPEND
  1862. X    EXIT,        NOTHING,
  1863. X    CANCEL,        SUSPEND,
  1864. X#else
  1865. X    EXIT,        CANCEL,
  1866. X#endif
  1867. X    TERMINIT,    TERMDONE,
  1868. X    IGNORE,        NOTHING
  1869. X};
  1870. X
  1871. XHidden struct helpitem {
  1872. X    string data;    /* "[name] repr's string" */
  1873. X    int bindmark;    /* position in data of more bindings marker */
  1874. X    bool changed;    /* status of item */
  1875. X} helpitem[(sizeof(helpcode))/(sizeof(int))];
  1876. X
  1877. XHidden int nitems= 0;
  1878. X
  1879. XHidden int namewidth;        /* width of name field */
  1880. X#define GAP_FIELDS 1        /* nr of spaces between two fields */
  1881. X/*Hidden int bindwidth;*/    /* width of bindings field */
  1882. X
  1883. XHidden int helpwidth;        /* width of a column */
  1884. X#define GAP_COLUMNS 1        /* nr of spaces between the two columns */
  1885. X
  1886. X#define BINDMARK '*'        /* set after name if too many bindings */
  1887. XHidden int bindstart;        /* offset bindings field */
  1888. X#define BINDSEP ", "        /* separator bindings */
  1889. X
  1890. X/*
  1891. X * Print the bindings.
  1892. X */
  1893. X
  1894. XVisible Procedure putbindings(yfirst) int yfirst; {
  1895. X    int h;
  1896. X    bool h_changed;
  1897. X    
  1898. X    for (h= 0; h < nitems; h+= 2, yfirst++) {
  1899. X
  1900. X        if (h_changed= helpitem[h].changed) {
  1901. X            getbindings(h);
  1902. X            trmputdata(yfirst, yfirst, 0, helpitem[h].data);
  1903. X        }
  1904. X        if (h+1 < nitems) {
  1905. X            if (helpitem[h+1].changed)
  1906. X                getbindings(h+1);
  1907. X            else if (!h_changed)
  1908. X                continue;
  1909. X            trmputdata(yfirst, yfirst,
  1910. X                helpwidth+GAP_COLUMNS, helpitem[h+1].data);
  1911. X        }
  1912. X    }
  1913. X    trmsync(yfirst, 0);
  1914. X}
  1915. X
  1916. XVisible Procedure setup_bindings(width, nlines) int width, *nlines; {
  1917. X    int h;
  1918. X    int code;
  1919. X    int len;
  1920. X    string buffer;
  1921. X    string name;
  1922. X    string getname();
  1923. X
  1924. X    helpwidth= (width - GAP_COLUMNS)/2;
  1925. X    nitems= ((sizeof(helpcode))/(sizeof(int)));
  1926. X    namewidth= 0;
  1927. X
  1928. X    for (h= 0; h < nitems; h++) {
  1929. X        buffer= (string) getmem((unsigned) helpwidth+1);
  1930. X        code= helpcode[h];
  1931. X        name= getname(code);
  1932. X        strcpy(buffer, name);
  1933. X        len= strlen(buffer);
  1934. X        if (len > namewidth) /* find max name length */
  1935. X            namewidth= len;
  1936. X        helpitem[h].data= buffer;
  1937. X        helpitem[h].bindmark= len;
  1938. X        helpitem[h].changed= Yes;
  1939. X        confirm_operation(code, name);
  1940. X    }
  1941. X
  1942. X    namewidth++;
  1943. X        /* one extra space for a marker after the name
  1944. X         * if there are too many bindings to show
  1945. X         */
  1946. X    bindstart= namewidth + GAP_FIELDS;
  1947. X/*    bindwidth= helpwidth - bindstart; */
  1948. X
  1949. X    /* extend with spaces */
  1950. X    for (h= 0; h < nitems; h++)
  1951. X        extendwithspaces(helpitem[h].data, bindstart);
  1952. X    
  1953. X    /* set nlines */
  1954. X
  1955. X    *nlines= (nitems+1)/2;
  1956. X}
  1957. X
  1958. X#ifdef MEMTRACE
  1959. X
  1960. XVisible Procedure fini_bindings() {
  1961. X    int h;
  1962. X    
  1963. X    for (h= 0; h < nitems; h++) {
  1964. X        free(helpitem[h].data);
  1965. X    }
  1966. X}
  1967. X
  1968. X#endif /* MEMTRACE */
  1969. X
  1970. XHidden string getname(code) int code; {
  1971. X    tabent *d;
  1972. X    
  1973. X    for (d= deftab; d < deftab+ndefs; d++) {
  1974. X        if (code == d->code)
  1975. X            return d->name;
  1976. X    }
  1977. X    return "";
  1978. X}
  1979. X
  1980. XHidden Procedure extendwithspaces(buffer, bound) string buffer; int bound; {
  1981. X    int len= strlen(buffer);
  1982. X    string pbuf= buffer+len;
  1983. X
  1984. X    for (; len < bound; len++)
  1985. X        *pbuf++= ' ';
  1986. X    *pbuf= '\0';
  1987. X}
  1988. X
  1989. XVisible Procedure bind_changed(code) int code; {
  1990. X    int h;
  1991. X    
  1992. X    for (h= 0; h < nitems; h++) {
  1993. X        if (code == helpcode[h]) {
  1994. X            helpitem[h].changed= Yes;
  1995. X            break;
  1996. X        }
  1997. X    }
  1998. X}
  1999. X
  2000. XVisible Procedure bind_all_changed() { /* for redrawing the screen */
  2001. X    int h;
  2002. X    
  2003. X    for (h= 0; h < nitems; h++) {
  2004. X        helpitem[h].changed= Yes;
  2005. X    }
  2006. X}
  2007. X    
  2008. X
  2009. X#define Def(d)    ((d)->def != NULL && (d)->def[0] != '\0')
  2010. X#define Rep(d)    ((d)->rep != NULL && (d)->rep[0] != '\0')
  2011. X
  2012. XHidden Procedure getbindings(h) int h; {
  2013. X    tabent *d;
  2014. X    int code= helpcode[h];
  2015. X    string buffer= helpitem[h].data;
  2016. X    bool all_showed= Yes;
  2017. X    string repr;
  2018. X    
  2019. X    buffer[bindstart]= '\0';
  2020. X    for (d= deftab+ndefs-1; d >= deftab; d--) {
  2021. X
  2022. X        if (code != d->code || !Def(d) || !Rep(d))
  2023. X            continue;
  2024. X        if (!addbinding(d->rep, buffer))
  2025. X            all_showed= No;
  2026. X    }
  2027. X    /* set marker */
  2028. X    buffer[helpitem[h].bindmark]= !all_showed ? BINDMARK : ' ';
  2029. X
  2030. X    helpitem[h].changed= No;
  2031. X}
  2032. X
  2033. XHidden bool addbinding(repr, buffer) string repr, buffer; {
  2034. X    string sep= buffer[bindstart] == '\0' ? "" : BINDSEP;
  2035. X    
  2036. X    if (strlen(buffer) + strlen(sep) + strlen(repr) > helpwidth)
  2037. X        return No;
  2038. X    strcat(buffer, sep);
  2039. X    strcat(buffer, repr);
  2040. X    return Yes;
  2041. X}
  2042. END_OF_FILE
  2043.   if test 4623 -ne `wc -c <'abc/keys/keyhlp.c'`; then
  2044.     echo shar: \"'abc/keys/keyhlp.c'\" unpacked with wrong size!
  2045.   fi
  2046.   # end of 'abc/keys/keyhlp.c'
  2047. fi
  2048. if test -f 'abc/stc/i2tcu.c' -a "${1}" != "-c" ; then 
  2049.   echo shar: Will not clobber existing file \"'abc/stc/i2tcu.c'\"
  2050. else
  2051.   echo shar: Extracting \"'abc/stc/i2tcu.c'\" \(4424 characters\)
  2052.   sed "s/^X//" >'abc/stc/i2tcu.c' <<'END_OF_FILE'
  2053. X/* Copyright (c) Stichting Mathematisch Centrum, Amsterdam, 1986. */
  2054. X
  2055. X/* unification of polytypes */
  2056. X
  2057. X#include "b.h"
  2058. X#include "bobj.h"
  2059. X#include "i2stc.h"
  2060. X
  2061. XHidden bool bad;
  2062. X
  2063. XVisible Procedure unify(a, b, pu)
  2064. Xpolytype a, b, *pu;
  2065. X{
  2066. X    bad = No;
  2067. X    setreprtable();
  2068. X    starterrvars();
  2069. X#ifdef TYPETRACE
  2070. X    s_unify(a, b);
  2071. X#endif
  2072. X    u_unify(a, b, pu);
  2073. X#ifdef TYPETRACE
  2074. X    e_unify(a, b, *pu);
  2075. X#endif
  2076. X    if (bad) badtyperr(a, b);
  2077. X    enderrvars();
  2078. X    delreprtable();
  2079. X}
  2080. X
  2081. XHidden Procedure u_unify(a, b, pu)
  2082. Xpolytype a, b, *pu;
  2083. X{
  2084. X    typekind a_kind, b_kind;
  2085. X    polytype res;
  2086. X    
  2087. X    a_kind = kind(a);
  2088. X    b_kind = kind(b);
  2089. X    
  2090. X    if (are_same_types(a, b)) {
  2091. X        *pu = p_copy(a);
  2092. X    }
  2093. X    else if (t_is_var(a_kind) || t_is_var(b_kind)) {
  2094. X        substitute_for(a, b, pu);
  2095. X    }
  2096. X    else if (have_same_structure(a, b)) {
  2097. X        unify_subtypes(a, b, pu);
  2098. X    }
  2099. X    else if (has_number(a_kind) && has_number(b_kind)) {
  2100. X        *pu = mkt_number();
  2101. X    }
  2102. X    else if (has_text(a_kind) && has_text(b_kind)) {
  2103. X        *pu = mkt_text();
  2104. X    }
  2105. X    else if (has_text(a_kind) && t_is_tlt(b_kind)) {
  2106. X        u_unify(asctype(b), (res = mkt_text()), pu);
  2107. X        p_release(res);
  2108. X    }
  2109. X    else if (has_text(b_kind) && t_is_tlt(a_kind)) {
  2110. X        u_unify(asctype(a), (res = mkt_text()), pu);
  2111. X        p_release(res);
  2112. X    }
  2113. X    else if ((t_is_list(a_kind) && has_lt(b_kind))
  2114. X         ||
  2115. X         (t_is_list(b_kind) && has_lt(a_kind))
  2116. X    )
  2117. X    {
  2118. X        u_unify(asctype(a), asctype(b), &res);
  2119. X        *pu = mkt_list(res);
  2120. X    }
  2121. X    else if (t_is_table(a_kind) && has_lt(b_kind)) {
  2122. X        u_unify(asctype(a), asctype(b), &res);
  2123. X        *pu = mkt_table(p_copy(keytype(a)), res);
  2124. X    }
  2125. X    else if (t_is_table(b_kind) && has_lt(a_kind)) {
  2126. X        u_unify(asctype(a), asctype(b), &res);
  2127. X        *pu = mkt_table(p_copy(keytype(b)), res);
  2128. X    }
  2129. X    else if ((t_is_tlt(a_kind) && t_is_lt(b_kind))
  2130. X         || 
  2131. X         (t_is_lt(a_kind) && t_is_tlt(b_kind)))
  2132. X    {
  2133. X        u_unify(asctype(a), asctype(b), &res);
  2134. X        *pu = mkt_lt(res);
  2135. X    }
  2136. X    else if (t_is_error(a_kind) || t_is_error(b_kind)) {
  2137. X        *pu = mkt_error();
  2138. X    }
  2139. X    else {
  2140. X        *pu = mkt_error();
  2141. X        bad = Yes;
  2142. X    }
  2143. X    if (t_is_var(a_kind) && t_is_error(kind(bottomtype(*pu))))
  2144. X        adderrvar(a);
  2145. X    if (t_is_var(b_kind) && t_is_error(kind(bottomtype(*pu))))
  2146. X        adderrvar(b);
  2147. X}
  2148. X
  2149. XHidden Procedure unify_subtypes(a, b, pu)
  2150. Xpolytype a, b, *pu;
  2151. X{
  2152. X    polytype sa, sb, s;
  2153. X    intlet nsub, is;
  2154. X    bool err = No;
  2155. X    
  2156. X    nsub = nsubtypes(a);
  2157. X    *pu = mkt_polytype(kind(a), nsub);
  2158. X    for (is = 0; is < nsub; is++) {
  2159. X        sa = subtype(a, is);
  2160. X        sb = subtype(b, is);
  2161. X        u_unify(sa, sb, &s);
  2162. X        putsubtype(s, *pu, is);
  2163. X        if (t_is_error(kind(s)))
  2164. X            err = Yes;
  2165. X    }
  2166. X    if (err == Yes) {
  2167. X        p_release(*pu);
  2168. X        *pu = mkt_error();
  2169. X    }
  2170. X}
  2171. X
  2172. XForward bool contains();
  2173. XForward bool equal_vars();
  2174. X
  2175. XHidden Procedure substitute_for(a, b, pu)
  2176. Xpolytype a, b, *pu;
  2177. X{
  2178. X    typekind a_kind, b_kind;
  2179. X    polytype ta, tb, tu, tt;
  2180. X    
  2181. X    a_kind = kind(a);
  2182. X    b_kind = kind(b);
  2183. X    
  2184. X    ta = bottomtype(a);
  2185. X    tb = bottomtype(b);
  2186. X    
  2187. X    if (!t_is_var(kind(ta)) && !t_is_var(kind(tb)))
  2188. X        u_unify(ta, tb, &tu);
  2189. X    else if (!t_is_var(kind(ta)))
  2190. X        tu = p_copy(ta);
  2191. X    else
  2192. X        tu = p_copy(tb);
  2193. X    
  2194. X    if (t_is_var(a_kind)) {
  2195. X        if (contains(tu, bottomvar(a)))
  2196. X            textify(a, &tu);
  2197. X    }
  2198. X    if (t_is_var(b_kind)) {
  2199. X        if (contains(tu, bottomvar(b)))
  2200. X            textify(b, &tu);
  2201. X    }
  2202. X    
  2203. X    if (t_is_var(a_kind) && t_is_var(b_kind)
  2204. X        && !are_same_types(bottomvar(a), bottomvar(b)))
  2205. X    {
  2206. X            repl_type_of(bottomvar(a), bottomvar(b));
  2207. X    }
  2208. X    
  2209. X    tt= bottomtype(tu);
  2210. X    
  2211. X    if (t_is_var(a_kind)) {
  2212. X        if (!are_same_types(tt, bottomtype(a)))
  2213. X            repl_type_of(bottomvar(a), tt);
  2214. X        *pu= p_copy(a);
  2215. X    }
  2216. X    else { /* t_is_var(b_kind) */
  2217. X        if (!are_same_types(tt, bottomtype(b)))
  2218. X            repl_type_of(bottomvar(b), tt);
  2219. X        *pu= p_copy(b);
  2220. X    }
  2221. X    
  2222. X    p_release(tu);
  2223. X}
  2224. X
  2225. XHidden Procedure textify(a, pu)
  2226. Xpolytype a, *pu;
  2227. X{
  2228. X    polytype ttext, text_hopefully;
  2229. X    
  2230. X    ttext = mkt_text();
  2231. X    u_unify(*pu, ttext, &text_hopefully);
  2232. X    if (bad == No) {
  2233. X        p_release(text_hopefully);
  2234. X        u_unify(a, ttext, &text_hopefully);
  2235. X    }
  2236. X    p_release(*pu);
  2237. X    if (bad == No) {
  2238. X        *pu = ttext;
  2239. X    }
  2240. X    else {
  2241. X        *pu = mkt_error();
  2242. X        /* cyclic type errors now reported through normal mechanism */
  2243. X        p_release(ttext);
  2244. X    }
  2245. X    p_release(text_hopefully);
  2246. X}
  2247. X
  2248. XVisible bool contains(u, a) polytype u, a; {
  2249. X    bool result;
  2250. X    
  2251. X    result = No;
  2252. X    if (t_is_var(kind(u))) {
  2253. X        if (table_has_type_of(u)) {
  2254. X            result = contains(bottomtype(u), a);
  2255. X        }
  2256. X    }
  2257. X    else {
  2258. X        polytype s;
  2259. X        intlet is, nsub;
  2260. X        nsub = nsubtypes(u);
  2261. X        for (is = 0; is < nsub; is++) {
  2262. X            s = subtype(u, is);
  2263. X            if (equal_vars(s, a) || contains(s, a)) {
  2264. X                result = Yes;
  2265. X                break;
  2266. X            }
  2267. X        }
  2268. X    }
  2269. X    return (result);
  2270. X}
  2271. X
  2272. XVisible bool equal_vars(s, a) polytype s, a; {
  2273. X    return (are_same_types(bottomvar(s), a));
  2274. X}
  2275. END_OF_FILE
  2276.   if test 4424 -ne `wc -c <'abc/stc/i2tcu.c'`; then
  2277.     echo shar: \"'abc/stc/i2tcu.c'\" unpacked with wrong size!
  2278.   fi
  2279.   # end of 'abc/stc/i2tcu.c'
  2280. fi
  2281. if test -f 'abc/unix/u1file.c' -a "${1}" != "-c" ; then 
  2282.   echo shar: Will not clobber existing file \"'abc/unix/u1file.c'\"
  2283. else
  2284.   echo shar: Extracting \"'abc/unix/u1file.c'\" \(1744 characters\)
  2285.   sed "s/^X//" >'abc/unix/u1file.c' <<'END_OF_FILE'
  2286. X/* Copyright (c) Stichting Mathematisch Centrum, Amsterdam, 1988. */
  2287. X
  2288. X#include "b.h"
  2289. X#include "bmem.h"
  2290. X#include "dest.h"
  2291. X#include "bfil.h"
  2292. X
  2293. Xextern char *getenv();
  2294. Xextern char *getwd();
  2295. X
  2296. XVisible char *curdir() {
  2297. X    static char buffer[SIZE_PATH];
  2298. X    return getwd(buffer);
  2299. X}
  2300. X
  2301. XHidden string searchfile(base, abclib) string base; string abclib; {
  2302. X    char *file;
  2303. X    
  2304. X    /* search first in startup directory */
  2305. X    file= makepath(startdir, base);
  2306. X    if (F_readable(file))
  2307. X        return (string) file;
  2308. X    freepath(file);
  2309. X
  2310. X    /* then in bwsdefault */
  2311. X    if (bwsdefault != NULL) {
  2312. X        file= makepath(bwsdefault, base);
  2313. X        if (F_readable(file))
  2314. X            return (string) file;
  2315. X        freepath(file);
  2316. X    }
  2317. X        
  2318. X    /* next first in abclib */
  2319. X    file= makepath(abclib, base);
  2320. X    if (F_readable(file))
  2321. X        return (string) file;
  2322. X    freepath(file);
  2323. X
  2324. X    /* else fail */
  2325. X    return (string) NULL;
  2326. X}
  2327. X
  2328. XVisible Procedure initfile() {
  2329. X    char *homedir= getenv("HOME");
  2330. X    char *termname;
  2331. X    string termfile;
  2332. X    
  2333. X    startdir= savepath(curdir());
  2334. X    bwsdefault= homedir ? makepath(homedir, BWSNAME) : (char *) NULL;
  2335. X    messfile= searchfile(MESSFILE, ABCLIB);
  2336. X    helpfile= searchfile(HELPFILE, ABCLIB);
  2337. X    buffile= homedir ? makepath(homedir, BUFFILE) : savepath(BUFFILE);
  2338. X    
  2339. X    if (editor != (string) NULL)
  2340. X        return;    /* we don't need the keydefinitions file */
  2341. X
  2342. X    if ((termname= getenv("TERM")) != NULL) {
  2343. X        termfile= (string) getmem((unsigned) strlen(KEYSPREFIX)+strlen(termname));
  2344. X        strcpy(termfile, KEYSPREFIX);
  2345. X        strcat(termfile, termname);
  2346. X        keysfile= searchfile(termfile, ABCLIB);
  2347. X        freemem(termfile);
  2348. X    }
  2349. X    if (keysfile == (string)NULL) {
  2350. X        keysfile= searchfile(KEYSFILE, ABCLIB);
  2351. X    }
  2352. X}
  2353. X
  2354. XVisible Procedure endfile() {
  2355. X    freepath(startdir);
  2356. X    freepath(bwsdefault);
  2357. X    freepath(messfile);
  2358. X    freepath(keysfile);
  2359. X    freepath(helpfile);
  2360. X    freepath(buffile);
  2361. X}
  2362. END_OF_FILE
  2363.   if test 1744 -ne `wc -c <'abc/unix/u1file.c'`; then
  2364.     echo shar: \"'abc/unix/u1file.c'\" unpacked with wrong size!
  2365.   fi
  2366.   # end of 'abc/unix/u1file.c'
  2367. fi
  2368. echo shar: End of archive 20 \(of 25\).
  2369. cp /dev/null ark20isdone
  2370. MISSING=""
  2371. for I in 1 2 3 4 5 6 7 8 9 10 11 12 13 14 15 16 17 18 19 20 21 22 23 24 25 ; do
  2372.     if test ! -f ark${I}isdone ; then
  2373.     MISSING="${MISSING} ${I}"
  2374.     fi
  2375. done
  2376. if test "${MISSING}" = "" ; then
  2377.     echo You have unpacked all 25 archives.
  2378.     rm -f ark[1-9]isdone ark[1-9][0-9]isdone
  2379. else
  2380.     echo You still must unpack the following archives:
  2381.     echo "        " ${MISSING}
  2382. fi
  2383. exit 0 # Just in case...
  2384.