home *** CD-ROM | disk | FTP | other *** search
/ Usenet 1994 January / usenetsourcesnewsgroupsinfomagicjanuary1994.iso / sources / unix / volume10 / ease / part03 < prev    next >
Encoding:
Internet Message Format  |  1987-07-09  |  50.4 KB

  1. Path: uunet!rs
  2. From: rs@uunet.UU.NET (Rich Salz)
  3. Newsgroups: comp.sources.unix
  4. Subject: v10i053:  Ease translator repost, Part03/04
  5. Message-ID: <621@uunet.UU.NET>
  6. Date: 10 Jul 87 11:25:37 GMT
  7. Organization: UUNET Communications Services, Arlington, VA
  8. Lines: 2115
  9. Approved: rs@uunet.UU.NET
  10.  
  11. Submitted-by: Wombat <rsk@j.cc.purdue.edu>
  12. Posting-number: Volume 10, Issue 53
  13. Archive-name: ease/Part03
  14.  
  15. #! /bin/sh
  16. # This is a shell archive.  Remove anything before this line, then unpack
  17. # it by saving it into a file and typing "sh file".  To overwrite existing
  18. # files, type "sh file -c".  You can also feed this as standard input via
  19. # unshar, or by typing "sh <file", e.g..  If this archive is complete, you
  20. # will see the following message at the end:
  21. #        "End of archive 3 (of 4)."
  22. PATH=/bin:/usr/bin:/usr/ucb ; export PATH
  23. if test -f 'config-files/FINIS/base.cpp' -a "${1}" != "-c" ; then 
  24.   echo shar: Will not clobber existing file \"'config-files/FINIS/base.cpp'\"
  25. else
  26. echo shar: Extracting \"'config-files/FINIS/base.cpp'\" \(7566 characters\)
  27. sed "s/^X//" >'config-files/FINIS/base.cpp' <<'END_OF_FILE'
  28. X/***********************************************************
  29. X ***********************************************************
  30. X ****
  31. X ****    General configuration information
  32. X ****
  33. X ****    This information is basically just "boiler-plate"; it must be
  34. X ****    there, but is essentially constant.
  35. X ****
  36. X ****    Information in this file should be independent of location --
  37. X ****    i.e., although there are some policy decisions made, they are
  38. X ****    not specific to Berkeley per se.
  39. X ****
  40. X ****    $Id: base.cpp,v 1.3 85/05/04 17:00:43 acu Exp Locker: acu $
  41. X ****
  42. X ***********************************************************
  43. X ***********************************************************/
  44. X
  45. X
  46. X#include "version.cpp"
  47. X
  48. X
  49. X/************************
  50. X **   Special macros   **
  51. X ************************/
  52. X
  53. Xmacro
  54. X    m_daemon = "MAILER-DAEMON";
  55. X        /* my name */
  56. X
  57. X    m_ufrom = "From ${m_sreladdr}  ${m_udate}";
  58. X        /* UNIX header format */
  59. X
  60. X    m_addrops = ".:%@!^=/[]";
  61. X        /* delimiter (operator) characters */
  62. X
  63. X    m_defaddr = concat ( 
  64. X            ifset (m_sname, "${m_sname} "),
  65. X            "<${m_sreladdr}>"
  66. X                );
  67. X        /* format of a total name */
  68. X
  69. X    m_smtp = "${m_oname} Sendmail ${m_version}/${berkhosts} ready at ${m_adate}";
  70. X        /* SMTP login message */
  71. X
  72. X
  73. X/***************
  74. X **   Class   **
  75. X ***************/
  76. X
  77. Xclass
  78. X    uucphosts = {};
  79. X
  80. X/*****************
  81. X **   Options   **
  82. X *****************/
  83. X
  84. Xoptions
  85. X    o_alias = "/usr/lib/aliases";
  86. X        /* location of alias file */
  87. X
  88. X    o_ewait    = "10";
  89. X        /* wait up to ten minutes for alias file rebuild */
  90. X
  91. X    o_bsub  = ".";
  92. X        /* substitution for space (blank) characters */
  93. X
  94. X    o_delivery = d_background;
  95. X        /* default delivery mode (deliver in background) */
  96. X
  97. X    /***
  98. X    o_qwait = "";
  99. X        /* (don't) connect to "expensive" mailers */
  100. X
  101. X    o_tmode = "0600";
  102. X        /* temporary file mode */
  103. X
  104. X    o_gid = "3";
  105. X        /* default GID (network) */
  106. X
  107. X    o_fsmtp = "/usr/lib/sendmail.hf";
  108. X        /* location of help file */
  109. X
  110. X    o_slog = "9";
  111. X        /* log level */
  112. X
  113. X    /***
  114. X    o_dnet = "ARPA";
  115. X         /* default network name */
  116. X
  117. X    o_hformat = "";
  118. X         /* default messages to old style */
  119. X
  120. X    o_qdir = "/usr/spool/mqueue";
  121. X        /* queue directory */
  122. X
  123. X    o_tread = "2h";
  124. X        /* read timeout -- violates protocols */
  125. X
  126. X    o_flog = "/usr/lib/sendmail.st";
  127. X         /* status file */
  128. X
  129. X    o_safe = "";
  130. X         /* queue everything before transmission */
  131. X
  132. X    o_qtimeout = "3d";
  133. X        /* default timeout interval */
  134. X
  135. X    o_timezone = "EST";
  136. X         /* time zone names (V6 only) */
  137. X
  138. X    o_dmuid = "5";
  139. X         /* default UID (network) */
  140. X
  141. X    o_wizpass = "XXXXXXXXXXXXX";
  142. X         /* wizard's password */
  143. X
  144. X    o_loadq = "999";
  145. X         /* load average at which we just queue messages */
  146. X
  147. X    o_loadnc = "999";
  148. X         /* load average at which we refuse connections */
  149. X
  150. X
  151. X/*****************************
  152. X **   Message precedences   **
  153. X *****************************/
  154. X
  155. Xprecedence
  156. X    first-class      = 0;
  157. X    special-delivery = 100;
  158. X    junk         = -100;
  159. X
  160. X
  161. X/***********************
  162. X **   Trusted users   **
  163. X ***********************/
  164. X
  165. Xtrusted
  166. X    {root, daemon, uucp, network};
  167. X    {aat};
  168. X
  169. X
  170. X/***************************
  171. X **   Format of headers   **
  172. X ***************************/
  173. X
  174. Xheader
  175. X    define ("Received:", concat (ifset (m_shostname, "from ${m_shostname} "),
  176. X        "by ${m_oname}; ${m_adate}"));
  177. X    define ("Subject:", "");
  178. X
  179. X    /*** 
  180. X    define ("Posted-Date:", "${m_odate}");
  181. X     ***/
  182. X
  183. X    for (f_return)
  184. X        define ("Return-Path:", "<${m_sreladdr}>");
  185. X
  186. X    for (f_date) {
  187. X        define ("Resent-Date:", "${m_odate}");
  188. X        define ("Date:",     "${m_odate}");
  189. X    };
  190. X
  191. X    for (f_from) {
  192. X        define ("Resent-From:", "${m_defaddr}");
  193. X        define ("From:",     "${m_defaddr}");
  194. X    };
  195. X
  196. X    for (f_full)
  197. X        define ("Full-Name:", "${m_sname}");
  198. X
  199. X    /***
  200. X    for (f_locm)
  201. X        define ("Received-Date:", "${m_adate}");
  202. X     ***/
  203. X
  204. X    for (f_mesg) {
  205. X        define ("Resent-Message-Id:", "<${m_ctime}.${m_qid}@${m_oname}>");
  206. X        define ("Message-Id:",           "<${m_ctime}.${m_qid}@${m_oname}>");
  207. X    };
  208. X
  209. X
  210. X/*************************
  211. X *************************
  212. X **   Rewriting rules   **
  213. X ************************* 
  214. X *************************/
  215. X
  216. X/*************************
  217. X **  Field definitions  **
  218. X *************************/
  219. X
  220. Xfield
  221. X    anypath            : match (0*);
  222. X    path, usr, hostpath,
  223. X    domain            : match (1*);
  224. X    this_host        : match (1) in m_sitename;
  225. X    hostname        : match (1);
  226. X    campushost        : match (1) in campushosts;
  227. X    localdomain        : match (1) in localname;
  228. X    topdomain_id        : match (1) in topdomain;
  229. X    uucphost        : match (1) in uucphosts;
  230. X    phonehost        : match (1) in phonehosts;
  231. X
  232. X/********************************
  233. X *  Sender Field Pre-rewriting  *
  234. X ********************************/
  235. X
  236. Xruleset SEND_PRW {
  237. X
  238. X/***
  239. X    if ( anypath < anypath > anypath )
  240. X        retry ( $1$2$3 );            /* defocus */
  241. X
  242. X}
  243. X
  244. X/***********************************
  245. X *  Recipient Field Pre-rewriting  *
  246. X ***********************************/
  247. X
  248. Xruleset RECP_PRW {
  249. X
  250. X/***
  251. X    if ( anypath < anypath > anypath )
  252. X        retry ( $1$2$3 );            /* defocus */
  253. X
  254. X}
  255. X
  256. X
  257. X/*********************************
  258. X *  Final Output Post-rewriting  *
  259. X *********************************/
  260. X
  261. Xruleset FINAL_RW {
  262. X
  263. X    if ( @ )
  264. X        return ();                /* handle <> error addr */
  265. X
  266. X    /* externalize local domain info */
  267. X
  268. X    /***
  269. X    if ( anypath < anypath "LOCAL" > anypath )
  270. X        retry ( $1 < $2 $localname > $3 );    /* change local info */
  271. X    
  272. X    /***
  273. X    if ( anypath < anypath "LOCAL.ARPA" > anypath )
  274. X        retry ( $1 < $2 $localname > $3 );    /* change local info */
  275. X
  276. X    if ( anypath < path > anypath )
  277. X        retry ( $1$2$3 );            /* defocus */
  278. X        
  279. X    if ( @path: @path: usr )
  280. X        retry ( @$1,@$2:$3);            /* <route-addr> canonical */
  281. X
  282. X    /* UUCP must always be presented in old form */
  283. X
  284. X    if ( usr @ hostname ".UUCP" )
  285. X        retry ( $2!$1);                /* u@h.UUCP => h!u */
  286. X
  287. X    /* delete duplicate local names -- mostly for arpaproto.mc */
  288. X
  289. X    if ( usr % this_host @ this_host )
  290. X        retry ( $1@$3 );            /* u%UCB@UCB => u@UCB */
  291. X
  292. X    if ( usr % this_host @ this_host ".ARPA" )
  293. X        retry ( $1@$3 ".ARPA" );        /* u%UCB@UCB => u@UCB */
  294. X
  295. X}
  296. X
  297. X
  298. X/***************************
  299. X *  Name Canonicalization  *
  300. X ***************************/
  301. X
  302. Xruleset NAME_CANON {
  303. X
  304. X    /* handle "from:<>" special case */
  305. X
  306. X    if ( <>    )
  307. X        return ( @ );                /* turn into magic token */
  308. X
  309. X    /* basic textual canonicalization -- note RFC733 heuristic here */
  310. X
  311. X    if ( anypath < anypath < anypath < path > anypath > anypath > anypath )
  312. X        retry ( $4 );                /* 3-level <> nesting */
  313. X
  314. X    if ( anypath < anypath < path > anypath > anypath )
  315. X        retry ( $3 );                /* 2-level <> nesting */
  316. X
  317. X    if ( anypath < path > anypath )
  318. X        retry ( $2 );                /* basic RFC821/822 parsing */
  319. X
  320. X    if ( usr " at " path )
  321. X        retry ( $1@$2 );            /* "at" -> "@" for RFC 822 */
  322. X
  323. X    /* make sure <@a,@b,@c:user@d> syntax is easy to parse -- undone later */
  324. X
  325. X    if ( @path, usr )
  326. X        retry ( @$1:$2 );            /* change all "," to ":" */
  327. X
  328. X    /* localize and dispose of route-based addresses */
  329. X
  330. X    if ( @path: usr )
  331. X        return ( LOCAL_RW ( <@$1>:$2 ) );    /* handle <route-addr> */
  332. X
  333. X    /* more miscellaneous cleanup */
  334. X
  335. X    if ( path )
  336. X        next ( HOSTDEP_RW ( $1 ) );        /* host dependent cleanup */
  337. X
  338. X    if ( path: anypath; @domain )
  339. X        return ( $1:$2;@$3 );            /* list syntax */
  340. X
  341. X    if ( usr @ domain )
  342. X        next ( $1<@$2> );            /* focus on domain */
  343. X
  344. X    if ( path < path @ domain > )
  345. X        retry ( $1$2<@$3> );            /* move gaze right */
  346. X
  347. X    if ( path < @domain > )
  348. X        return ( LOCAL_RW ( $1<@$2> ) );    /* already canonical */
  349. X
  350. X    /* convert old-style addresses to a domain-based address */
  351. X
  352. X    if ( usr % hostpath )
  353. X        return ( LOCAL_RW ( $1<@$2> ) );    /* user%host */
  354. X
  355. X    if ( hostname:usr )
  356. X        return ( LOCAL_RW ( $2<@$1> ) );    /* host:user */    
  357. X
  358. X    if ( hostname.usr )
  359. X        return ( LOCAL_RW ( $2<@$1> ) );    /* host.user */
  360. X
  361. X    if ( hostname^usr )
  362. X        retry ( $1!$2);                /* convert ^ to ! */
  363. X
  364. X    if ( hostname!usr )
  365. X        return ( LOCAL_RW ( $2<@$1".UUCP"> ) );       /* resolve uucp names */
  366. X
  367. X    if ( hostname=usr )
  368. X        return ( LOCAL_RW ( $2<@$1".BITNET"> ) );  /* resolve bitnet names */
  369. END_OF_FILE
  370. if test 7566 -ne `wc -c <'config-files/FINIS/base.cpp'`; then
  371.     echo shar: \"'config-files/FINIS/base.cpp'\" unpacked with wrong size!
  372. fi
  373. # end of 'config-files/FINIS/base.cpp'
  374. fi
  375. if test -f 'maketd/abrv.c' -a "${1}" != "-c" ; then 
  376.   echo shar: Will not clobber existing file \"'maketd/abrv.c'\"
  377. else
  378. echo shar: Extracting \"'maketd/abrv.c'\" \(6197 characters\)
  379. sed "s/^X//" >'maketd/abrv.c' <<'END_OF_FILE'
  380. X/* abbreviation related routines 
  381. X * Written & hacked by Stephen Uitti, PUCC staff, ach@pucc-j, 1985
  382. X * maketd is copyright (C) Purdue University, 1985
  383. X *
  384. X * Permission is hereby given for its free reproduction and
  385. X * modification for non-commercial purposes, provided that this
  386. X * notice and all embedded copyright notices be retained.
  387. X * Commercial organisations may give away copies as part of their
  388. X * systems provided that they do so without charge, and that they
  389. X * acknowledge the source of the software.
  390. X */
  391. X
  392. X#ifdef BSD2_9
  393. X#include <sys/types.h>
  394. X#endif
  395. X#include <stdio.h>
  396. X#include <ctype.h>
  397. Xextern char *malloc();
  398. X
  399. X#include "srtunq.h"
  400. X#include "abrv.h"
  401. X#include "maketd.h"
  402. X
  403. Xstruct srtent abrv;            /* include file abrevs */
  404. Xchar   *abrvtbl[MXABR];            /* translation table strings */
  405. Xint    abrvlen[MXABR];            /* string lengths (for speed) */
  406. X
  407. X/* lngsrt - string length more important than lexicographical compare.
  408. X * return > 0 if b is longer than a.
  409. X * return < 0 if b is shorter than a.
  410. X * if a & b are the same length, return strcmp(a, b), which means
  411. X * that 0 is returned if the strings are THE SAME,
  412. X * if b > a: return > 0
  413. X * if b < a: return < 0
  414. X */
  415. Xint
  416. Xlngsrt(a, b)
  417. Xchar *a, *b;
  418. X{
  419. X    register i;
  420. X
  421. X    if ((i = strlen(b) - strlen(a)) != 0)
  422. X    return i;
  423. X    else
  424. X    return strcmp(a, b);
  425. X}
  426. X
  427. X/* hincl - include header optimizer:
  428. X * Compress multiple leading /'s to just one.
  429. X * Remove leading "./".
  430. X * Doesn't change date, just returns pointer into begining of path.
  431. X */
  432. Xchar *
  433. Xhincl(p)
  434. Xregister char *p;
  435. X{
  436. X    if (*p == '/')        /* compress multiple leading /'s */
  437. X    while (p[1] == '/')    /* to just one */
  438. X        p++;
  439. X    if (strncmp("./", p, 2) == 0) {
  440. X    p += 2;            /* leading "./" can confuse make */
  441. X    while (*p == '/')    /* don't change ".//a.h" to "/a.h" */
  442. X        p++;
  443. X    }
  444. X    return p;
  445. X}
  446. X
  447. X/* srchincl - search line for make defines of A-Z
  448. X * Put entries into abrvtbl.
  449. X */
  450. Xvoid
  451. Xsrchincl(p)
  452. Xregister char *p;
  453. X{
  454. X    register char *q, *r;
  455. X    register i;
  456. X
  457. X    if (shortincl && *p != '\0') {
  458. X    while (*p == SPC || *p == '\t')
  459. X        p++;        /* ignore white space */
  460. X    q = p;            /* what letter */
  461. X    if (isupper(*p)) {    /* A-Z, for now */
  462. X        p++;
  463. X        while (*p == SPC || *p == '\t')
  464. X        p++;        /* ignore white space */
  465. X        if (*p++ == '=') {
  466. X        while (*p == SPC || *p == '\t')
  467. X            p++;
  468. X        if ((i = strlen(p)) != 0) {
  469. X            if ((r = malloc((unsigned)(i + 1))) == NULL)
  470. X            err("Out of memory in define search");
  471. X            if (abrvtbl[*q - 'A'])
  472. X            fprintf(stderr, "%s: warning - %c redefined in %s\n",
  473. X                prgnm, *q, makename);
  474. X            abrvtbl[*q - 'A'] = r;
  475. X            while (*p != '\0' && *p != '#' && *p != '\n')
  476. X            *r++ = *p++;
  477. X            *r = '\0';    /* null terminate result */
  478. X        }        /* if non-null string */
  479. X        }            /* if = */
  480. X    }            /* if A-Z */
  481. X    }                /* if shortinclude & string */
  482. X}
  483. X
  484. X/* abrvsetup - set up abrev table, spit out the abrevs.     Use
  485. X * any A-Z definitions found in Makefile, no duplicates.  Add
  486. X * /usr/include & /usr/include/sys if "all" dependencies are
  487. X * being generated (including /usr/include based files).
  488. X * Try to use I=/usr/include and S=/usr/include/sys, but don't
  489. X * make a stink about it.
  490. X */
  491. Xvoid
  492. Xabrvsetup()
  493. X{
  494. X    register i;                /* temp */
  495. X    register char *p;            /* temp */
  496. X    register slot;            /* slot search point */
  497. X    register j;                /* temp */
  498. X    static abrdone = FALSE;        /* do this only once */
  499. X    register flushi = FALSE;        /* print I=.. */
  500. X    register flushs = FALSE;        /* print S=.. */
  501. X    static char *istring = "I=/usr/include";
  502. X    static char *sstring = "S=/usr/include/sys";
  503. X
  504. X    if (abrdone)
  505. X    return;
  506. X    if (shortincl) {
  507. X    abrdone = TRUE;            /* we've done this */
  508. X    /* add /usr/include/sys, /usr/include if not already there */
  509. X    if (alldep) {
  510. X        if (abrvtbl['S'-'A'] == NULL) {
  511. X        flushs = TRUE;
  512. X        srchincl(sstring);
  513. X        } else if ((p = srtin(&abrv, &sstring[2], lngsrt)) != NULL)
  514. X        fprintf(stderr, "%s: %s - %s\n", prgnm, p, &sstring[2]);
  515. X        if (abrvtbl['I'-'A'] == NULL) {
  516. X        flushi = TRUE;
  517. X        srchincl(istring);
  518. X        } else if ((p = srtin(&abrv, &istring[2], lngsrt)) != NULL)
  519. X        fprintf(stderr, "%s: %s - %s\n", prgnm, p, &istring[2]);
  520. X    }
  521. X    if (!replace) {            /* no new defines with replace */
  522. X        srtgti(&abrv);        /* init tree traversal */
  523. X        slot = 0;            /* start at bgn */
  524. X        while ((p = srtgets(&abrv)) != NULL) {
  525. X        j = strlen(p);
  526. X        for (i = 0; i < MXABR; i++) { /* look for this definition */
  527. X            if (abrvtbl[i] == NULL)
  528. X            continue;    /* check non-null entries */
  529. X            if (*abrvtbl[i] == '\0')
  530. X            continue;    /* check non-null entries */
  531. X            if (strcmp(p, abrvtbl[i]) == 0)
  532. X            break;        /* exact match found */
  533. X            else if (strlen(abrvtbl[i]) == j + 1 &&
  534. X            strncmp(p, abrvtbl[i], j) == 0 &&
  535. X                abrvtbl[i][j] == '/')
  536. X            break;        /* match of "p/" found */
  537. X        }
  538. X        if (i == MXABR) {    /* not found */
  539. X            for (i = slot; i < MXABR; i++) /* find free slot */
  540. X            if (abrvtbl[i] == NULL)
  541. X                break;
  542. X            if (i < MXABR) {    /* free slot found */
  543. X        /*     if (!usestdout && !replace) */
  544. X                fprintf(makefd, "%c=%s\n", 'A' + i, p);
  545. X            abrvtbl[i++] = p;
  546. X            slot = i;    /* reduce free slot search time */
  547. X            }
  548. X        }            /* if not found */
  549. X        }                /* while */
  550. X    }                /* if !replace */
  551. X    if (flushi && !usestdout && !replace)
  552. X        fprintf(makefd, "%s\n", istring);
  553. X    if (flushs && !usestdout && !replace)
  554. X        fprintf(makefd, "%s\n", sstring);
  555. X    for (i = 0; i < MXABR; i++) {    /* set up string lengths */
  556. X        if (abrvtbl[i] == NULL) {
  557. X        abrvlen[i] = 0;
  558. X        } else {
  559. X        abrvlen[i] = strlen(abrvtbl[i]);
  560. X        if (verbose)
  561. X            fprintf(stderr, "%s: %c='%s'\n",
  562. X            prgnm, i + 'A', abrvtbl[i]);
  563. X        }                /* if */
  564. X    }                /* for */
  565. X    }                    /* if */
  566. X}
  567. X
  568. X/* findabr - find an abbreviation in abrvtbl for string p (if any).
  569. X * if multiple abbreations work, use longest.
  570. X * (ie: /usr/include & /usr/include/sys; use /usr/include/sys)
  571. X * if found, return index
  572. X * else: MXABR
  573. X * Do not match abbreviations of less than 3 characters.
  574. X */
  575. Xint
  576. Xfindabr(p)
  577. Xregister char *p;            /* string pointer */
  578. X{
  579. X    register i;                /* for index */
  580. X    register j;                /* found index */
  581. X
  582. X    for (i = 0, j = MXABR; i < MXABR; i++)
  583. X    if (abrvlen[i] > 2)        /* changing "." to $A is evil */
  584. X        if (strncmp(abrvtbl[i], p, abrvlen[i]) == 0)
  585. X        if (j == MXABR || (abrvlen[i] > abrvlen[j]))
  586. X            j = i;
  587. X    return j;
  588. X}
  589. END_OF_FILE
  590. if test 6197 -ne `wc -c <'maketd/abrv.c'`; then
  591.     echo shar: \"'maketd/abrv.c'\" unpacked with wrong size!
  592. fi
  593. # end of 'maketd/abrv.c'
  594. fi
  595. if test -f 'src/emitcf.c' -a "${1}" != "-c" ; then 
  596.   echo shar: Will not clobber existing file \"'src/emitcf.c'\"
  597. else
  598. echo shar: Extracting \"'src/emitcf.c'\" \(7227 characters\)
  599. sed "s/^X//" >'src/emitcf.c' <<'END_OF_FILE'
  600. X/*    $Header: /usr/src/local/etc/ease/RCS/emitcf.c,v 1.3 85/11/22 20:14:11 jss Exp $    */
  601. X
  602. X/*
  603. X *    emitcf.c  -- This file contains routines associated with the writing
  604. X *             and formatting of a translated sendmail configuration file.
  605. X *
  606. X *    author      -- James S. Schoner, Purdue University Computing Center,
  607. X *                         West Lafayette, Indiana  47907
  608. X *
  609. X *      date      -- July 9, 1985
  610. X *
  611. X *    Copyright (c) 1985 by Purdue Research Foundation
  612. X *
  613. X *    All rights reserved.
  614. X *
  615. X */
  616. X
  617. X#include <stdio.h>
  618. X#include "symtab.h"
  619. X
  620. X#define REGLINE 60    /* length of output lines which may be continued */
  621. X#define MAXLINE 256    /* liberal maximum line length             */
  622. X
  623. Xextern short Rformat;            /* read-format flag for a class  */
  624. Xextern char *MacScan ();
  625. Xextern char  MakeMac ();
  626. Xextern void  PrintError (),
  627. X         FatalError (),
  628. X         PrintWarning (),
  629. X         ErrorReport ();
  630. X
  631. Xvoid  PrintDef ();
  632. X
  633. Xstatic char ClassCH;            /* printable class macro char    */
  634. X
  635. X/*
  636. X *    EmitDef () -- Emit a definition line (Ease block definition) in cf 
  637. X *              format.
  638. X *
  639. X */
  640. Xvoid
  641. XEmitDef (blockdef, targ, defstr1, defstr2)
  642. Xregister enum bdefs blockdef;    /* type of definition        */
  643. Xregister struct he *targ;    /* target to be defined      */
  644. Xchar *defstr1, *defstr2;    /* one or two definition strings */
  645. X{
  646. X    /*
  647. X     *  This routine is about as pretty as a translated ease file...
  648. X     *  Each type of line (Ease block) is handled case by case below.
  649. X     *
  650. X     */
  651. X    switch (blockdef) {
  652. X        case def_macro:        printf ("D%c", MakeMac (targ, ID_MACRO));
  653. X                    PrintDef (def_macro, MacScan (defstr1));
  654. X                    if (ISMACRO(targ->idd))
  655. X                        PrintWarning ("Redefining macro %s.\n", targ->psb);
  656. X                    targ->idd |= ID_MACRO;  /* signal definition */
  657. X                    break;
  658. X
  659. X        case def_class:        if (Rformat)    /* read format */
  660. X                        printf ("F");
  661. X                    else
  662. X                        printf ("C");
  663. X                    printf ("%c", ClassCH = MakeMac (targ, ID_CLASS));
  664. X                    if (Rformat) {    /* read format */
  665. X                        printf ("%s\n", defstr1);
  666. X                        Rformat = FALSE;
  667. X                    } else
  668. X                        PrintDef (def_class, defstr1);
  669. X                    if (ISCLASS(targ->idd))
  670. X                        PrintWarning ("Redefining class %s.\n", targ->psb);
  671. X                    targ->idd |= ID_CLASS;  /* signal definition */
  672. X                    break;
  673. X
  674. X        case def_option:    printf ("O%c", *defstr1);
  675. X                    PrintDef (def_option, defstr2);
  676. X                    break;
  677. X
  678. X        case def_prec:        printf ("P%s=%d\n", targ->psb, targ->idval.prec);
  679. X                    break;
  680. X
  681. X        case def_trusted:    printf ("T");
  682. X                    PrintDef (def_trusted, defstr1);
  683. X                    break;
  684. X
  685. X        case def_header:    printf ("H");
  686. X                    if (defstr1 != NULL)
  687. X                        printf ("?%s?", defstr1);
  688. X                    PrintDef (def_header, defstr2);
  689. X                    break;
  690. X
  691. X        case def_mailer:    if (ISMAILER(targ->idtype)) {
  692. X                        if (ISMAILER(targ->idd))
  693. X                            PrintWarning ("Redefining mailer %s.\n", targ->psb);
  694. X                    } else if (ISTYPED(targ->idtype)) {
  695. X                        PrintError ("Redeclaration of identifier as mailer:", targ->psb);
  696. X                        return;
  697. X                    }
  698. X                    targ->idd |= ID_MAILER;  /* signal definition */
  699. X                    printf ("M%s, ", targ->psb);
  700. X                    PrintDef (def_mailer, defstr1);
  701. X                    break;
  702. X
  703. X        case def_ruleset:    printf ("R");
  704. X                    PrintDef (def_ruleset, defstr1);
  705. X                    break;
  706. X
  707. X        default:        FatalError ("Bad case in EmitDef ()", (char *) NULL);
  708. X    }
  709. X}
  710. X
  711. X
  712. X/*
  713. X *      PrintContinued () -- Print a line definition (buf) by splitting it over
  714. X *                 more than one line.  The two definition types 
  715. X *                 accepted for this method of continuation are class
  716. X *                 and trusted user lists, indicated in the argument 
  717. X *                 btype 
  718. X *
  719. X */
  720. Xvoid
  721. XPrintContinued (btype, buf)
  722. Xenum bdefs     btype;    /* block (line) type for definition */
  723. Xregister char *buf;    /* buffer containing the definition */
  724. X{
  725. X    register char *tmp;    /* breakpoint search pointer   */
  726. X    register char  tc;    /* temporary swap byte         */
  727. X    int  buflen;        /* length of definition buffer */    
  728. X
  729. X    buflen = strlen (buf);
  730. X    tmp = buf + REGLINE;
  731. X    while ((*--tmp != ' ') && (tmp != buf))     /* look for suitable break */
  732. X        /* null */ ;
  733. X    if (tmp == buf) {
  734. X        for (tmp = buf + REGLINE; (*tmp != ' ') && (tmp - buf != buflen); tmp++)
  735. X            /* null */ ;
  736. X        if ((tmp - buf) >= MAXLINE)
  737. X            PrintWarning ("Member name may be too long.\n", (char *) NULL);
  738. X    }
  739. X    tc = *tmp;        /* swap break char with null char */
  740. X    *tmp = '\0';
  741. X    printf ("%s\n", buf);
  742. X    if ((*tmp = tc) == '\0')
  743. X        return;
  744. X    else
  745. X        tmp++;
  746. X    if (btype == def_class)        /* start next line   */
  747. X        printf ("C%c", ClassCH);
  748. X    else
  749. X        printf ("T");
  750. X    if (strlen (tmp) < REGLINE)    /* continue the line */
  751. X        printf ("%s\n", tmp);
  752. X    else
  753. X        PrintContinued (btype, tmp);
  754. X}
  755. X
  756. X
  757. X/*
  758. X *    PrintDef () -- Handles special cases (like line continuation) when 
  759. X *               printing definitions.
  760. X *
  761. X */
  762. Xvoid
  763. XPrintDef (btype, dstr)
  764. Xregister enum bdefs btype;    /* block type (output line type) */
  765. Xregister char *dstr;        /* definition string         */
  766. X{
  767. X    register char *tmp;
  768. X
  769. X    for (tmp = dstr; *tmp != '\0'; tmp++)     /* search for line continuations */
  770. X        if ((*tmp == '\\') && (*++tmp == '\n'))
  771. X            if (btype != def_header) {
  772. X                ErrorReport ("Non-header string contains line continuation\n");
  773. X                return;
  774. X            } else
  775. X                break;
  776. X
  777. X    /*
  778. X     *  Perform case by case handling of definition printing.
  779. X     *
  780. X     */
  781. X    switch (btype) {
  782. X        case def_header :  if (*tmp-- == '\n') {
  783. X                    *tmp = '\0';
  784. X                    if (tmp - dstr >= MAXLINE)
  785. X                        PrintWarning ("Header may be too long.\n", 
  786. X                                  (char *) NULL);
  787. X                    printf ("%s\n\t", dstr);
  788. X                    tmp += 2;
  789. X                        PrintDef (def_header, tmp);
  790. X                   } else {
  791. X                    if (strlen (dstr) >= MAXLINE)
  792. X                        PrintWarning ("Header may be too long.\n", 
  793. X                                  (char *) NULL);
  794. X                    printf ("%s\n", dstr);
  795. X                   }
  796. X                   break;
  797. X
  798. X        case def_mailer :  if (strlen (dstr) >= MAXLINE)
  799. X                    PrintWarning ("Mailer definition may be too long.\n", 
  800. X                              (char *) NULL);
  801. X                   printf ("%s\n", dstr);
  802. X                   break;
  803. X
  804. X        case def_ruleset:  if (strlen (dstr) >= MAXLINE)
  805. X                    PrintWarning ("Rewriting rule may be too long.\n", 
  806. X                              (char *) NULL);
  807. X                   printf ("%s\n", dstr);
  808. X                   break;
  809. X
  810. X        case def_option :  if (strlen (dstr) >= MAXLINE)
  811. X                    PrintWarning ("Option assignment may be too long.\n", 
  812. X                              (char *) NULL);
  813. X                   printf ("%s\n", dstr);
  814. X                   break;
  815. X
  816. X        case def_macro  :  if (strlen (dstr) >= MAXLINE)
  817. X                    PrintWarning ("Macro assignment may be too long.\n", 
  818. X                              (char *) NULL);
  819. X                   printf ("%s\n", dstr);
  820. X                   break;
  821. X
  822. X        case def_prec   :  if (strlen (dstr) >= MAXLINE)
  823. X                    PrintWarning ("Precedence relation may be too long.\n", 
  824. X                              (char *) NULL);
  825. X                   printf ("%s\n", dstr);
  826. X                   break;
  827. X
  828. X        case def_trusted:
  829. X        case def_class  :  if (strlen (dstr) < REGLINE)
  830. X                    printf ("%s\n", dstr);
  831. X                   else        /* use line continuation feature */
  832. X                       PrintContinued (btype, dstr);
  833. X                   break;
  834. X
  835. X        default         :  FatalError ("Invalid case in PrintDef ()", (char *) NULL);
  836. X    }
  837. X}
  838. X
  839. X
  840. X/*
  841. X *    StartRuleset () -- Prints a ruleset heading for the ruleset identifier
  842. X *                   contained in the argument rsid.
  843. X *
  844. X */
  845. Xvoid
  846. XStartRuleset (rsid)
  847. Xregister struct he *rsid;    /* ruleset identifier */
  848. X{
  849. X    if (!ISRULESET(rsid->idtype))
  850. X        if (ISTYPED(rsid->idtype))
  851. X            PrintError ("Identifier not of ruleset type:", rsid->psb);
  852. X        else
  853. X            PrintError ("Ruleset identifier not bound to a number:", rsid->psb);
  854. X    else {
  855. X        if (ISRULESET(rsid->idd))
  856. X            PrintWarning ("Redefining ruleset %s.\n", rsid->psb);
  857. X        rsid->idd |= ID_RULESET;
  858. X        printf ("S%s\n", rsid->idval.rsn);
  859. X    }
  860. X}
  861. END_OF_FILE
  862. if test 7227 -ne `wc -c <'src/emitcf.c'`; then
  863.     echo shar: \"'src/emitcf.c'\" unpacked with wrong size!
  864. fi
  865. # end of 'src/emitcf.c'
  866. fi
  867. if test -f 'src/parser.y' -a "${1}" != "-c" ; then 
  868.   echo shar: Will not clobber existing file \"'src/parser.y'\"
  869. else
  870. echo shar: Extracting \"'src/parser.y'\" \(14482 characters\)
  871. sed "s/^X//" >'src/parser.y' <<'END_OF_FILE'
  872. X%{
  873. X/*    $Header: /usr/src/local/etc/ease/RCS/parser.y,v 1.3 85/12/10 18:02:11 jss Exp $    */
  874. X
  875. X/*
  876. X *    parser.y -- EASE parser.
  877. X *
  878. X *            Contains code for yacc(1) which produces a parser (y.tab.c)
  879. X *            for Ease, a specification format for sendmail configuration
  880. X *            files.
  881. X *
  882. X *    author   -- James S. Schoner, Purdue University Computing Center,
  883. X *                          West Lafayette, Indiana  47907
  884. X *
  885. X *    date     -- July 2, 1985
  886. X *
  887. X *    Copyright (c) 1985 by Purdue Research Foundation
  888. X *
  889. X *    All rights reserved.
  890. X *
  891. X */
  892. X
  893. X#include <stdio.h>
  894. X#include "symtab.h"
  895. X
  896. Xextern void       BindID ();
  897. Xextern void       EmitDef ();
  898. Xextern char      *ListAppend ();
  899. Xextern char       *MakeCond ();
  900. Xextern char      *MakeRStr ();
  901. Xextern char       *ConvOpt ();
  902. Xextern char      *ConvFlg ();
  903. Xextern char      *MacScan ();
  904. Xextern char      *ConvMat ();
  905. Xextern void       StartRuleset ();
  906. Xextern char      *MakePosTok ();
  907. Xextern char      *GetField ();
  908. Xextern char      *Bracket ();
  909. Xextern char      *MakeRSCall ();
  910. Xextern char      *CheckMailer ();
  911. Xextern char      *CheckRS ();
  912. Xextern char      *MakeField ();
  913. Xextern char       MakeMac ();
  914. Xextern void       AssignType ();
  915. Xextern void       RemoveSymbol ();
  916. Xextern void       yyerror ();
  917. X
  918. Xextern short RMatch;        /* ruleset match flag               */
  919. X
  920. Xchar *Cbuf = " ";        /* character buffer                 */
  921. Xchar *Mbuf = "$ ";        /* macro buffer                        */
  922. Xchar *Tsb;            /* pointer to temporary string buffer */
  923. Xchar *Flaglist;            /* pointer to header flag list          */
  924. X
  925. X%}
  926. X
  927. X%union {            /* value stack element type    */
  928. X    int      ival;        /* integer token            */
  929. X    char      *psb;        /* string token               */
  930. X    struct he *phe;        /* pointer to hash entry       */
  931. X    enum opts optval;    /* sendmail options           */
  932. X    enum flgs flgval;    /* mailer flags               */
  933. X    enum mats mpval;    /* mailer attribute parameters */
  934. X}
  935. X
  936. X%start config
  937. X
  938. X%token     <phe>    IDENT
  939. X%token  <psb>    SCONST
  940. X%token  <ival>    ICONST SEPCHAR
  941. X%token BIND MACRO CLASS OPTIONS PRECEDENCE TRUSTED HEADER RULESET MAILER
  942. X%token IF RETRY NEXT RETURN RESOLVE CONCAT IFSET FOR CANON READCLASS
  943. X%token MPATH MFLAGS MSENDER MRECIPIENT MARGV MEOL MMAXSIZE
  944. X%token AAOPT AOPT BBOPT COPT DOPT DOPTI DOPTB DOPTQ DDOPT EOPT EOPTP EOPTE 
  945. X%token EOPTM EOPTW EOPTZ FFOPT FOPT GOPT HHOPT IOPT LLOPT MOPT NNOPT OOPT QQOPT
  946. X%token ROPT SSOPT SOPT TTOPT TOPT UOPT VOPT WWOPT XOPT XXOPT
  947. X%token FFLAG RFLAG SSFLAG NFLAG LFLAG SFLAG MFLAG FFFLAG DDFLAG MMFLAG XFLAG
  948. X%token PPFLAG UFLAG HFLAG AAFLAG UUFLAG EFLAG XXFLAG LLFLAG PFLAG IIFLAG CCFLAG
  949. X%token ASGN COMMA LBRACE RBRACE LPAREN RPAREN SEMI DOLLAR MATCH IN HOSTNUM
  950. X%token DEFINE FIELD COLON STAR HOST USER
  951. X
  952. X%type    <psb>        mval strval ifcon conval ifres elseres nameset namelist
  953. X%type    <psb>        doptid eoptid idlist fcond dlist mflags route mdefs
  954. X%type    <psb>        matchaddr matchtok action actionstmt mailerspec mtdef
  955. X%type    <psb>        rwaddr rwtok ftype reftok rword cantok resolution
  956. X%type    <psb>        userspec hword hostid dheader
  957. X%type    <ival>        anychar
  958. X%type    <phe>        cdef
  959. X%type    <optval>    optid
  960. X%type    <flgval>    flagid
  961. X%type    <mpval>        mvar
  962. X
  963. X%left COMMA
  964. X%left LPAREN RPAREN
  965. X%nonassoc SCONST
  966. X
  967. X%%
  968. Xconfig        :    /* empty */
  969. X        |    config blockdef
  970. X        |    error blockdef
  971. X        ;
  972. X
  973. Xblockdef    :    BIND bindings
  974. X        |    MACRO macdefs
  975. X        |    CLASS classdefs
  976. X        |    OPTIONS optdefs
  977. X        |    PRECEDENCE precdefs
  978. X        |    TRUSTED tlist
  979. X        |    HEADER hdefs
  980. X        |    MAILER mlist
  981. X        |    RULESET rdef
  982. X        |    FIELD fdefs
  983. X        ;
  984. X
  985. Xbindings    :    /* empty */
  986. X        |    bindings IDENT ASGN RULESET ICONST SEMI {
  987. X                BindID ($2, $5, ID_RULESET);
  988. X            }
  989. X        |    error SEMI {
  990. X                yyerrok;
  991. X            }
  992. X        ;
  993. X
  994. Xmacdefs        :    /* empty */
  995. X        |    macdefs IDENT ASGN mval SEMI {
  996. X                EmitDef (def_macro, $2, $4, (char *) NULL);
  997. X            }
  998. X        |    error SEMI {
  999. X                yyerrok;
  1000. X            }
  1001. X        ;
  1002. X
  1003. Xmval        :    strval                %prec COMMA {
  1004. X                $$ = $1;
  1005. X            }
  1006. X        |    CONCAT LPAREN conval RPAREN {
  1007. X                $$ = $3;
  1008. X            }
  1009. X        ;
  1010. X
  1011. Xstrval        :    SCONST {
  1012. X                $$ = $1;
  1013. X            }
  1014. X        |    strval SCONST {
  1015. X                $$ = ListAppend ($1, $2, (char *) NULL);
  1016. X                free ($1);
  1017. X            }
  1018. X        ;
  1019. X
  1020. Xconval        :    strval COMMA ifcon {
  1021. X                $$ = ListAppend ($1, $3, (char *) NULL);
  1022. X                free ($1);
  1023. X                free ($3);
  1024. X            }
  1025. X        |    ifcon COMMA strval {
  1026. X                $$ = ListAppend ($1, $3, (char *) NULL);
  1027. X                free ($1);
  1028. X                free ($3);
  1029. X            }
  1030. X        |    error {
  1031. X                $$ = NULL;
  1032. X            }
  1033. X        ;
  1034. X
  1035. Xifcon        :    IFSET LPAREN IDENT COMMA ifres RPAREN {
  1036. X                $$ = MakeCond ($3, $5);
  1037. X            }
  1038. X        ;
  1039. X
  1040. Xifres        :    mval elseres {
  1041. X                if ($2 != NULL) {
  1042. X                    $$ = ListAppend ($1, $2, "$|");
  1043. X                    free ($1);
  1044. X                    free ($2);
  1045. X                } else
  1046. X                    $$ = $1;
  1047. X            }
  1048. X        |    error {
  1049. X                $$ = NULL;
  1050. X            }
  1051. X        ;
  1052. X
  1053. Xelseres        :    /* empty */ {
  1054. X                $$ = NULL;
  1055. X            }
  1056. X        |    COMMA mval {
  1057. X                $$ = $2;
  1058. X            }
  1059. X        ;
  1060. X
  1061. Xclassdefs    :    /* empty */ 
  1062. X        |    classdefs IDENT ASGN nameset {
  1063. X                EmitDef (def_class, $2, $4, (char *) NULL);
  1064. X            }
  1065. X        |    error
  1066. X        ;
  1067. X
  1068. Xnameset        :    LBRACE namelist RBRACE SEMI {
  1069. X                $$ = $2;
  1070. X            }
  1071. X        |    LBRACE RBRACE SEMI {
  1072. X                $$ = NULL;
  1073. X            }
  1074. X        |    LBRACE error RBRACE SEMI {
  1075. X                $$ = NULL;
  1076. X            }
  1077. X        |    READCLASS LPAREN strval RPAREN SEMI {
  1078. X                $$ = MakeRStr ($3, (char *) NULL);
  1079. X            }
  1080. X        |    READCLASS LPAREN strval COMMA strval RPAREN SEMI {
  1081. X                $$ = MakeRStr ($3, $5);
  1082. X            }
  1083. X        |    READCLASS LPAREN error RPAREN SEMI {
  1084. X                $$ = NULL;
  1085. X            }
  1086. X        |    error SEMI {
  1087. X                $$ = NULL;
  1088. X                yyerrok;
  1089. X            }
  1090. X        ;
  1091. X
  1092. Xnamelist    :    IDENT {
  1093. X                $$ = ListAppend ($1->psb, (char *) NULL, (char *) NULL);
  1094. X                RemoveSymbol ($1);
  1095. X            }
  1096. X        |    strval {
  1097. X                $$ = $1;
  1098. X            }
  1099. X        |    namelist COMMA IDENT {
  1100. X                $$ = ListAppend ($1, $3->psb, " ");
  1101. X                free ($1);
  1102. X                RemoveSymbol ($3);
  1103. X            }
  1104. X        |    namelist COMMA strval {
  1105. X                $$ = ListAppend ($1, $3, " ");
  1106. X                free ($1);
  1107. X                free ($3);
  1108. X            }
  1109. X        ;
  1110. X
  1111. Xoptdefs        :    /* empty */
  1112. X        |    optdefs optid ASGN strval SEMI {
  1113. X                EmitDef (def_option, (struct he *) NULL, ConvOpt ($2), $4);
  1114. X            }
  1115. X        |    optdefs DOPT ASGN doptid SEMI {
  1116. X                EmitDef (def_option, (struct he *) NULL, ConvOpt (opt_d), $4);
  1117. X            }
  1118. X        |    optdefs EOPT ASGN eoptid SEMI {
  1119. X                EmitDef (def_option, (struct he *) NULL, ConvOpt (opt_e), $4);
  1120. X            }
  1121. X        |    error SEMI {
  1122. X                yyerrok;
  1123. X            }
  1124. X        ;
  1125. X
  1126. Xoptid        :    AAOPT {
  1127. X                $$ = opt_A;
  1128. X            }
  1129. X        |    AOPT {
  1130. X                $$ = opt_a;
  1131. X            }
  1132. X        |    BBOPT {
  1133. X                $$ = opt_B;
  1134. X            }
  1135. X        |    COPT {
  1136. X                $$ = opt_c;
  1137. X            }
  1138. X        |    DDOPT {
  1139. X                $$ = opt_D;
  1140. X            }
  1141. X        |    FFOPT {
  1142. X                $$ = opt_F;
  1143. X            }
  1144. X        |    FOPT {
  1145. X                $$ = opt_f;
  1146. X            }
  1147. X        |    GOPT {
  1148. X                $$ = opt_g;
  1149. X            }
  1150. X        |    HHOPT {
  1151. X                $$ = opt_H;
  1152. X            }
  1153. X        |    IOPT {
  1154. X                $$ = opt_i;
  1155. X            }
  1156. X        |    LLOPT {
  1157. X                $$ = opt_L;
  1158. X            }
  1159. X        |    MOPT {
  1160. X                $$ = opt_m;
  1161. X            }
  1162. X        |    NNOPT {
  1163. X                $$ = opt_N;
  1164. X            }
  1165. X        |    OOPT {
  1166. X                $$ = opt_o;
  1167. X            }
  1168. X        |    QQOPT {
  1169. X                $$ = opt_Q;
  1170. X            }
  1171. X        |    ROPT {
  1172. X                $$ = opt_r;
  1173. X            }
  1174. X        |    SSOPT {
  1175. X                $$ = opt_S;
  1176. X            }
  1177. X        |    SOPT {
  1178. X                $$ = opt_s;
  1179. X            }
  1180. X        |    TTOPT {
  1181. X                $$ = opt_T;
  1182. X            }
  1183. X        |    TOPT {
  1184. X                $$ = opt_t;
  1185. X            }
  1186. X        |    UOPT {
  1187. X                $$ = opt_u;
  1188. X            }
  1189. X        |    VOPT {
  1190. X                $$ = opt_v;
  1191. X            }
  1192. X        |    WWOPT {
  1193. X                $$ = opt_W;
  1194. X            }
  1195. X        |    XOPT {
  1196. X                $$ = opt_x;
  1197. X            }
  1198. X        |    XXOPT {
  1199. X                $$ = opt_X;
  1200. X            }
  1201. X        ;
  1202. X
  1203. Xdoptid        :    DOPTI {
  1204. X                $$ = ConvOpt (d_opt_i);
  1205. X            }
  1206. X        |    DOPTB {
  1207. X                $$ = ConvOpt (d_opt_b);
  1208. X            }
  1209. X        |    DOPTQ {
  1210. X                $$ = ConvOpt (d_opt_q);
  1211. X            }
  1212. X        ;
  1213. X
  1214. Xeoptid        :    EOPTP {
  1215. X                $$ = ConvOpt (e_opt_p);
  1216. X            }
  1217. X        |    EOPTE {
  1218. X                $$ = ConvOpt (e_opt_e);
  1219. X            }
  1220. X        |    EOPTM {
  1221. X                $$ = ConvOpt (e_opt_m);
  1222. X            }
  1223. X        |    EOPTW {
  1224. X                $$ = ConvOpt (e_opt_w);
  1225. X            }
  1226. X        |    EOPTZ {
  1227. X                $$ = ConvOpt (e_opt_z);
  1228. X            }
  1229. X        ;
  1230. X
  1231. Xprecdefs    :    /* empty */
  1232. X        |    precdefs IDENT ASGN ICONST SEMI {
  1233. X                BindID ($2, $4, ID_PREC);
  1234. X                EmitDef (def_prec, $2, (char *) NULL, (char *) NULL);
  1235. X            }
  1236. X        ;
  1237. X
  1238. Xtlist        :    /* empty */
  1239. X        |    tlist LBRACE IDENT idlist RBRACE SEMI {
  1240. X                EmitDef (def_trusted, (struct he *) NULL, 
  1241. X                     ListAppend ($3->psb, $4, " "), (char *) NULL);
  1242. X                free ($4);
  1243. X                RemoveSymbol ($3);
  1244. X            }
  1245. X        |    tlist LBRACE RBRACE SEMI
  1246. X        |    error SEMI {
  1247. X                yyerrok;
  1248. X            }
  1249. X        ;
  1250. X
  1251. Xhdefs        :    /* empty */
  1252. X        |    hdefs FOR fcond dheader SEMI {
  1253. X                EmitDef (def_header, (struct he *) NULL, $3, $4);
  1254. X            }
  1255. X        |    hdefs FOR fcond LBRACE { Flaglist = $3; } 
  1256. X                dheaders RBRACE SEMI
  1257. X        |    hdefs DEFINE dlist SEMI {
  1258. X                EmitDef (def_header, (struct he *) NULL, (char *) NULL, $3);
  1259. X            }
  1260. X        |    error SEMI {
  1261. X                yyerrok;
  1262. X            }
  1263. X        ;
  1264. X
  1265. Xfcond        :    LPAREN RPAREN {
  1266. X                $$ = NULL;
  1267. X            }
  1268. X        |    LPAREN mflags RPAREN {
  1269. X                $$ = $2;
  1270. X            }
  1271. X        |    LPAREN error RPAREN {
  1272. X                $$ = NULL;
  1273. X            }
  1274. X        ;
  1275. X
  1276. Xmflags        :    flagid {
  1277. X                $$ = ListAppend (ConvFlg ($1), (char *) NULL, (char *) NULL);
  1278. X            }
  1279. X        |    mflags COMMA flagid {
  1280. X                $$ = ListAppend ($1, ConvFlg($3), (char *) NULL);
  1281. X                free ($1);
  1282. X            }
  1283. X        ;
  1284. X
  1285. Xflagid        :    FFLAG {
  1286. X                $$ = flg_f;
  1287. X            }
  1288. X        |    RFLAG {
  1289. X                $$ = flg_r;
  1290. X            }
  1291. X        |    SSFLAG {
  1292. X                $$ = flg_S;
  1293. X            }
  1294. X        |    NFLAG {
  1295. X                $$ = flg_n;
  1296. X            }
  1297. X        |    LFLAG {
  1298. X                $$ = flg_l;
  1299. X            }
  1300. X        |    SFLAG {
  1301. X                $$ = flg_s;
  1302. X            }
  1303. X        |    MFLAG {
  1304. X                $$ = flg_m;
  1305. X            }
  1306. X        |    FFFLAG {
  1307. X                $$ = flg_F;
  1308. X            }
  1309. X        |    DDFLAG {
  1310. X                $$ = flg_D;
  1311. X            }
  1312. X        |    MMFLAG {
  1313. X                $$ = flg_M;
  1314. X            }
  1315. X        |    XFLAG {
  1316. X                $$ = flg_x;
  1317. X            }
  1318. X        |    PPFLAG {
  1319. X                $$ = flg_P;
  1320. X            }
  1321. X        |    UFLAG {
  1322. X                $$ = flg_u;
  1323. X            }
  1324. X        |    HFLAG {
  1325. X                $$ = flg_h;
  1326. X            }
  1327. X        |    AAFLAG {
  1328. X                $$ = flg_A;
  1329. X            }
  1330. X        |    UUFLAG {
  1331. X                $$ = flg_U;
  1332. X            }
  1333. X        |    EFLAG {
  1334. X                $$ = flg_e;
  1335. X            }
  1336. X        |    XXFLAG {
  1337. X                $$ = flg_X;
  1338. X            }
  1339. X        |    LLFLAG {
  1340. X                $$ = flg_L;
  1341. X            }
  1342. X        |    PFLAG {
  1343. X                $$ = flg_p;
  1344. X            }
  1345. X        |    IIFLAG {
  1346. X                $$ = flg_I;
  1347. X            }
  1348. X        |    CCFLAG {
  1349. X                $$ = flg_C;
  1350. X            }
  1351. X        ;
  1352. X
  1353. Xdheader        :    /* empty */ {
  1354. X                $$ = NULL;
  1355. X            }
  1356. X        |    DEFINE dlist {
  1357. X                $$ = $2;
  1358. X            }
  1359. X        |    error {
  1360. X                $$ = NULL;
  1361. X            }
  1362. X        ;
  1363. X
  1364. Xdheaders    :    /* empty */
  1365. X        |    dheaders DEFINE dlist SEMI {
  1366. X                EmitDef (def_header, (struct he *) NULL, Flaglist, $3);
  1367. X            }
  1368. X        |    error
  1369. X        ;
  1370. X
  1371. Xdlist        :    LPAREN strval COMMA mval RPAREN {
  1372. X                $$ = ListAppend ($2, MacScan ($4), " ");
  1373. X                free ($2);
  1374. X                free ($4);
  1375. X            }
  1376. X        |    LPAREN error RPAREN {
  1377. X                $$ = NULL;
  1378. X            }
  1379. X        ;
  1380. X
  1381. Xmlist        :    /* empty */
  1382. X        |    mlist IDENT LBRACE mdefs RBRACE SEMI {
  1383. X                EmitDef (def_mailer, $2, $4, (char *) NULL);
  1384. X            }
  1385. X        |    mlist IDENT LBRACE RBRACE SEMI {
  1386. X                EmitDef (def_mailer, $2, (char *) NULL, (char *) NULL);
  1387. X            }
  1388. X        |    error SEMI {
  1389. X                yyerrok;
  1390. X            }
  1391. X        ;
  1392. X
  1393. Xmdefs        :    mtdef {
  1394. X                $$ = $1;
  1395. X            }
  1396. X        |    mdefs COMMA mtdef {
  1397. X                $$ = ListAppend ($1, $3, ", ");
  1398. X                free ($1);
  1399. X                free ($3);
  1400. X            }
  1401. X        ;    
  1402. X
  1403. Xmtdef        :    mvar ASGN mval {
  1404. X                $$ = ListAppend (ConvMat ($1), MacScan ($3), "=");
  1405. X                free ($3);
  1406. X            }
  1407. X        |    MFLAGS ASGN LBRACE mflags RBRACE {
  1408. X                $$ = ListAppend (ConvMat (mat_flags), $4, "=");
  1409. X            }
  1410. X        |    MSENDER ASGN IDENT {
  1411. X                $$ = ListAppend (ConvMat (mat_sender), CheckRS ($3), "=");
  1412. X            }
  1413. X        |    MRECIPIENT ASGN IDENT {
  1414. X                $$ = ListAppend (ConvMat (mat_recipient), CheckRS ($3), "=");
  1415. X            }
  1416. X        |    error {
  1417. X                $$ = NULL;
  1418. X            }
  1419. X        ;
  1420. X
  1421. Xmvar        :    MPATH {
  1422. X                $$ = mat_path;
  1423. X            }
  1424. X        |    MARGV {
  1425. X                $$ = mat_argv;
  1426. X            }
  1427. X        |    MEOL {
  1428. X                $$ = mat_eol;
  1429. X            }
  1430. X        |    MMAXSIZE {
  1431. X                $$ = mat_maxsize;
  1432. X            }
  1433. X        ;
  1434. X
  1435. Xrdef        :    /* empty */
  1436. X        |    rdef IDENT { StartRuleset ($2); } rulelist
  1437. X        ;
  1438. X
  1439. Xrulelist    :    LBRACE ruledefs RBRACE {
  1440. X                RMatch = FALSE;
  1441. X            }
  1442. X        |    error {
  1443. X                RMatch = FALSE;
  1444. X            }
  1445. X        ;
  1446. X
  1447. Xruledefs    :    /* empty */ {
  1448. X                RMatch = TRUE;
  1449. X            }
  1450. X        |    ruledefs IF LPAREN matchaddr RPAREN actionstmt {
  1451. X                EmitDef (def_ruleset, (struct he *) NULL, 
  1452. X                     ListAppend ($4, $6, "\t"), (char *) NULL);
  1453. X            free ($4);
  1454. X            free ($6);
  1455. X            }
  1456. X        |    error SEMI {
  1457. X                yyerrok;
  1458. X            }
  1459. X        ;
  1460. X
  1461. Xmatchaddr    :    /* empty */ {
  1462. X                $$ = NULL;
  1463. X            }
  1464. X        |    matchaddr matchtok {
  1465. X                $$ = ListAppend ($1, $2, (char *) NULL);
  1466. X                free ($1);
  1467. X            }
  1468. X        |    error {
  1469. X                $$ = NULL;
  1470. X            }
  1471. X        ;
  1472. X
  1473. Xmatchtok    :    IDENT {
  1474. X                $$ = GetField ($1);
  1475. X            }
  1476. X        |    anychar {
  1477. X                *Cbuf = $1;
  1478. X                $$ = ListAppend (Cbuf, (char *) NULL, (char *) NULL);
  1479. X            }
  1480. X        |    mval {
  1481. X                $$ = MacScan ($1);
  1482. X            }
  1483. X        |    DOLLAR IDENT {
  1484. X                Mbuf[1] = MakeMac ($2, ID_MACRO);
  1485. X                $$ = ListAppend (Mbuf, (char *) NULL, (char *) NULL);
  1486. X            }
  1487. X        ;
  1488. X
  1489. Xactionstmt    :    action LPAREN rwaddr RPAREN SEMI {
  1490. X                $$ = ListAppend ($1, $3, (char *) NULL);
  1491. X                free ($3);
  1492. X            }
  1493. X        |    RESOLVE LPAREN resolution RPAREN SEMI {
  1494. X                $$ = $3;
  1495. X            }
  1496. X        |    error SEMI {
  1497. X                $$ = NULL;
  1498. X                yyerrok;
  1499. X            }
  1500. X        ;
  1501. X
  1502. Xaction        :    RETRY {
  1503. X                $$ = NULL;
  1504. X            }
  1505. X        |    NEXT {
  1506. X                $$ = "$:";
  1507. X            }
  1508. X        |    RETURN {
  1509. X                $$ = "$@";
  1510. X            }
  1511. X        ;
  1512. X
  1513. Xrwaddr        :    /* empty */ {
  1514. X                $$ = NULL;
  1515. X            }
  1516. X        |    rwaddr rwtok {
  1517. X                $$ = ListAppend ($1, $2, (char *) NULL);
  1518. X                free ($1);
  1519. X            }
  1520. X        |    rwaddr IDENT LPAREN rwaddr RPAREN {
  1521. X                $$ = ListAppend ($1, (Tsb = MakeRSCall ($2, $4)), (char *) NULL);
  1522. X                free ($1);
  1523. X                free ($4);
  1524. X                free (Tsb);
  1525. X            }
  1526. X        |    error {
  1527. X                $$ = NULL;
  1528. X            }
  1529. X        ;
  1530. X
  1531. Xrwtok        :    anychar {
  1532. X                *Cbuf = $1;
  1533. X                $$ = ListAppend (Cbuf, (char *) NULL, (char *) NULL);
  1534. X            }
  1535. X        |    mval {
  1536. X                $$ = MacScan ($1);
  1537. X            }
  1538. X        |    cantok {
  1539. X                $$ = $1;
  1540. X            }
  1541. X        |    reftok {
  1542. X                $$ = $1;
  1543. X            }
  1544. X        ;
  1545. X
  1546. Xcantok        :    CANON LPAREN IDENT RPAREN {
  1547. X                $$ = Bracket ($3->psb, TRUE);
  1548. X                RemoveSymbol ($3);
  1549. X            }
  1550. X        |    CANON LPAREN SCONST RPAREN {
  1551. X                $$ = Bracket (MacScan ($3), TRUE);
  1552. X                free ($3);
  1553. X            }
  1554. X        |    CANON LPAREN reftok RPAREN {
  1555. X                $$ = Bracket ($3, TRUE);
  1556. X                free ($3);
  1557. X            }
  1558. X        ;
  1559. X
  1560. Xreftok        :    DOLLAR IDENT {
  1561. X                Mbuf[1] = MakeMac ($2, ID_MACRO);
  1562. X                $$ = ListAppend (Mbuf, (char *) NULL, (char *) NULL);
  1563. X            }
  1564. X        |    DOLLAR ICONST {
  1565. X                $$ = ListAppend (MakePosTok ($2), (char *) NULL, (char *) NULL);
  1566. X            }
  1567. X        ;
  1568. X
  1569. Xanychar        :    SEPCHAR {
  1570. X                $$ = $1;
  1571. X            }
  1572. X        |    COLON {
  1573. X                $$ = ':';
  1574. X            }
  1575. X        |    STAR {
  1576. X                $$ = '*';
  1577. X            }
  1578. X        |    SEMI {
  1579. X                $$ = ';';
  1580. X            }
  1581. X        |    LBRACE {
  1582. X                $$ = '{';
  1583. X            }
  1584. X        |    RBRACE {
  1585. X                $$ = '}';
  1586. X            }
  1587. X        |    COMMA {
  1588. X                $$ = ',';
  1589. X            }
  1590. X        |    ASGN {
  1591. X                $$ = '=';
  1592. X            }
  1593. X        ;
  1594. X
  1595. Xresolution    :    mailerspec COMMA route {
  1596. X                $$ = ListAppend ($1, $3, (char *) NULL);
  1597. X                free ($1);
  1598. X                free ($3);
  1599. X            }
  1600. X        |    error {
  1601. X                $$ = NULL;
  1602. X            }
  1603. X        ;
  1604. X
  1605. Xmailerspec    :    MAILER LPAREN rword RPAREN {
  1606. X                $$ = ListAppend ("$#", $3, (char *) NULL);
  1607. X            }
  1608. X        ;
  1609. X
  1610. Xroute        :    HOST LPAREN hword RPAREN COMMA userspec {
  1611. X                $$ = ListAppend (Tsb = ListAppend ("$@", $3, (char *) NULL),
  1612. X                         $6, (char *) NULL);
  1613. X                free (Tsb);
  1614. X                free ($6);
  1615. X            }
  1616. X        |    userspec {
  1617. X                $$ = $1;
  1618. X            }
  1619. X        ;
  1620. X
  1621. Xhword        :    hostid {
  1622. X                $$ = $1;
  1623. X            }
  1624. X        |    HOSTNUM LPAREN reftok RPAREN {
  1625. X                $$ = Bracket ($3, FALSE);
  1626. X                free ($3);
  1627. X            }
  1628. X        ;
  1629. X
  1630. Xhostid        :    /* empty */ {
  1631. X                $$ = NULL;
  1632. X            }
  1633. X        |    hostid IDENT {
  1634. X                $$ = ListAppend ($1, $2->psb, (char *) NULL);
  1635. X                RemoveSymbol ($2);
  1636. X                free ($1);
  1637. X            }
  1638. X        |    hostid rwtok {
  1639. X                $$ = ListAppend ($1, $2, (char *) NULL);
  1640. X                free ($1);
  1641. X            }
  1642. X        ;
  1643. X
  1644. Xuserspec    :    USER LPAREN rwaddr RPAREN {
  1645. X                $$ = ListAppend ("$:", $3, (char *) NULL);
  1646. X                free ($3);
  1647. X            }
  1648. X        ;
  1649. X
  1650. Xrword        :    IDENT {
  1651. X                $$ = CheckMailer ($1);
  1652. X            }
  1653. X        |    reftok {
  1654. X                $$ = $1;
  1655. X            }
  1656. X        ;
  1657. X
  1658. Xfdefs        :    /* empty */
  1659. X        |    fdefs IDENT idlist COLON ftype SEMI {
  1660. X                AssignType (ListAppend ($2->psb, $3, " "), $5);
  1661. X                free ($3);
  1662. X            }
  1663. X        |    error SEMI {
  1664. X                yyerrok;
  1665. X            }
  1666. X        ;
  1667. X
  1668. Xidlist        :    /* empty */ {
  1669. X                $$ = NULL;
  1670. X            }
  1671. X        |    idlist COMMA IDENT {
  1672. X                $$ = ListAppend ($1, $3->psb, " ");
  1673. X                free ($1);
  1674. X            }
  1675. X        ;
  1676. X
  1677. Xftype        :    MATCH LPAREN ICONST RPAREN cdef {
  1678. X                $$ = ListAppend (MakeField ($3, $5, FALSE), 
  1679. X                             (char *) NULL, (char *) NULL);
  1680. X            }
  1681. X        |    MATCH LPAREN ICONST STAR RPAREN {
  1682. X                $$ = ListAppend (MakeField ($3, (struct he *) NULL, TRUE), 
  1683. X                         (char *) NULL, (char *) NULL);
  1684. X            }
  1685. X        |    error {
  1686. X                $$ = NULL;
  1687. X            }
  1688. X        ;
  1689. X
  1690. Xcdef        :    /* empty */ {
  1691. X                $$ = NULL;
  1692. X            }
  1693. X        |    IN IDENT {
  1694. X                $$ = $2;
  1695. X            }
  1696. X        ;
  1697. END_OF_FILE
  1698. if test 14482 -ne `wc -c <'src/parser.y'`; then
  1699.     echo shar: \"'src/parser.y'\" unpacked with wrong size!
  1700. fi
  1701. # end of 'src/parser.y'
  1702. fi
  1703. if test -f 'src/strops.c' -a "${1}" != "-c" ; then 
  1704.   echo shar: Will not clobber existing file \"'src/strops.c'\"
  1705. else
  1706. echo shar: Extracting \"'src/strops.c'\" \(10730 characters\)
  1707. sed "s/^X//" >'src/strops.c' <<'END_OF_FILE'
  1708. X/*    $Header: /usr/src/local/etc/ease/RCS/strops.c,v 1.2 85/10/29 23:45:39 jss Exp $    */
  1709. X
  1710. X/*
  1711. X *    strops.c   -- Contains string operation routines used for constructing
  1712. X *              definitions in cf format.
  1713. X *
  1714. X *    author       -- James S. Schoner, Purdue University Computing Center,
  1715. X *                        West Lafayette, Indiana  47907
  1716. X *
  1717. X *    date       -- July 9, 1985
  1718. X *
  1719. X *    Copyright (c) 1985 by Purdue Research Foundation
  1720. X *
  1721. X *    All rights reserved.
  1722. X *
  1723. X */
  1724. X
  1725. X#include <stdio.h>
  1726. X#include <strings.h>
  1727. X#include "symtab.h"
  1728. X
  1729. X#define MAXTOKPOS   99        /* maximum number of token positions */
  1730. X#define MAXNAME        1024    /* maximum length of an identifier   */
  1731. X
  1732. Xextern struct he *LookupSymbol ();
  1733. Xextern char       MakeMac ();
  1734. Xextern void      FatalError (),
  1735. X          PrintError (),
  1736. X          ErrorReport ();
  1737. X
  1738. Xshort  Rformat = FALSE;            /* class read format flag      */
  1739. Xstatic char   *Ptok   = "$  ";        /* positional token structure     */
  1740. Xstatic char   *Cfield = "$= ";        /* class reference structure      */
  1741. Xstatic char   *Ofield = "$-";        /* one token match structure      */
  1742. Xstatic char   *Zfield = "$*";        /* zero or more tokens structure  */
  1743. Xstatic char   *Pfield = "$+";        /* one or more tokens structure      */
  1744. Xstatic char   *Mtest  = "$? ";        /* conditional macro test string  */
  1745. X
  1746. X
  1747. X/*
  1748. X *    ConvOpt () -- Convert an Ease option identifier (optid) by returning a
  1749. X *              string representation of the cf format.  
  1750. X *
  1751. X */
  1752. Xchar *
  1753. XConvOpt (optid) 
  1754. Xregister enum opts optid;
  1755. X{
  1756. X    switch (optid) {
  1757. X        case opt_A  :    return ("A");
  1758. X        case opt_a  :    return ("a");
  1759. X        case opt_B  :    return ("B");
  1760. X        case d_opt_b:    return ("b");
  1761. X        case opt_c  :    return ("c");
  1762. X        case opt_D  :    return ("D");
  1763. X        case opt_d  :    return ("d");
  1764. X        case opt_e  :
  1765. X        case e_opt_e:    return ("e");
  1766. X        case opt_F  :    return ("F");
  1767. X        case opt_f  :    return ("f");
  1768. X        case opt_g  :    return ("g");
  1769. X        case opt_H  :    return ("H");
  1770. X        case opt_i  :
  1771. X        case d_opt_i:    return ("i");
  1772. X        case opt_L  :    return ("L");
  1773. X        case opt_m  :
  1774. X        case e_opt_m:    return ("m");
  1775. X        case opt_N  :    return ("N");
  1776. X        case opt_o  :    return ("o");
  1777. X        case e_opt_p:    return ("p");
  1778. X        case opt_Q  :    return ("Q");
  1779. X        case d_opt_q:    return ("q");
  1780. X        case opt_r  :    return ("r");
  1781. X        case opt_S  :    return ("S");
  1782. X        case opt_s  :    return ("s");
  1783. X        case opt_T  :    return ("T");
  1784. X        case opt_t  :    return ("t");
  1785. X        case opt_u  :    return ("u");
  1786. X        case opt_v  :    return ("v");
  1787. X        case opt_W  :    return ("W");
  1788. X        case e_opt_w:    return ("w");
  1789. X        case opt_x  :    return ("x");
  1790. X        case opt_X  :    return ("X");
  1791. X        case e_opt_z:    return ("z");
  1792. X        default     :    FatalError ("Bad case in ConvOpt ()", (char *) NULL);
  1793. X    }
  1794. X    /*NOTREACHED*/
  1795. X}
  1796. X
  1797. X
  1798. X/*
  1799. X *    ConvFlg () -- Convert an Ease mailer flag identifier (flgid) by 
  1800. X *              string representation of the cf format.  
  1801. X *
  1802. X */
  1803. Xchar *
  1804. XConvFlg (flgid)
  1805. Xregister enum flgs flgid;    /* flag identifier */
  1806. X{
  1807. X    switch (flgid) {
  1808. X        case flg_f:    return ("f");
  1809. X        case flg_r:    return ("r");
  1810. X        case flg_S:    return ("S");
  1811. X        case flg_n:    return ("n");
  1812. X        case flg_l:    return ("l");
  1813. X        case flg_s:    return ("s");
  1814. X        case flg_m:    return ("m");
  1815. X        case flg_F:    return ("F");
  1816. X        case flg_D:    return ("D");
  1817. X        case flg_M:    return ("M");
  1818. X        case flg_x:    return ("x");
  1819. X        case flg_P:    return ("P");
  1820. X        case flg_u:    return ("u");
  1821. X        case flg_h:    return ("h");
  1822. X        case flg_A:    return ("A");
  1823. X        case flg_U:    return ("U");
  1824. X        case flg_e:    return ("e");
  1825. X        case flg_X:    return ("X");
  1826. X        case flg_L:    return ("L");
  1827. X        case flg_p:    return ("p");
  1828. X        case flg_I:    return ("I");
  1829. X        case flg_C:    return ("C");
  1830. X        default   :    FatalError ("Bad case in ConvFlg ()", (char *) NULL);
  1831. X    }
  1832. X    /*NOTREACHED*/
  1833. X}
  1834. X
  1835. X
  1836. X/*
  1837. X *    ConvMat () -- Convert an Ease mailer attribute (mat) by returning a
  1838. X *              string representation of the cf format.  
  1839. X *
  1840. X */
  1841. Xchar *
  1842. XConvMat (mat)
  1843. Xregister enum mats mat;        /* mailer attribute flag */
  1844. X{
  1845. X    switch (mat) {
  1846. X        case mat_path        : return ("P");
  1847. X        case mat_flags        : return ("F");
  1848. X        case mat_sender        : return ("S");
  1849. X        case mat_recipient    : return ("R");
  1850. X        case mat_argv        : return ("A");
  1851. X        case mat_eol        : return ("E");
  1852. X        case mat_maxsize    : return ("M");
  1853. X        default            : FatalError ("Bad case in ConvMat ()", (char *) NULL);
  1854. X    }
  1855. X    /*NOTREACHED*/
  1856. X}
  1857. X
  1858. X
  1859. X/*
  1860. X *    MacScan () -- Scan a string (pstring) for macros, replacing the Ease
  1861. X *              form with the one-character form required by cf format.
  1862. X *
  1863. X */
  1864. Xchar *
  1865. XMacScan (pstring)
  1866. Xchar *pstring;        /* macro expandable string */
  1867. X{
  1868. X    register char *searchptr;    /* string search pointer     */
  1869. X    register char *bptr, *eptr;    /* macro begin and end pointers */
  1870. X    char macname [MAXNAME];        /* macro name buffer        */
  1871. X
  1872. X    if ((searchptr = pstring) == NULL)
  1873. X        return ((char *) NULL);
  1874. X    while (*searchptr != '\0')     /* find and rewrite all macros  */
  1875. X        if (*searchptr == '\\') {
  1876. X            searchptr = searchptr + 2;
  1877. X            continue;
  1878. X        } else if (*searchptr++ == '$' && *searchptr == '{') {
  1879. X            if (sscanf (searchptr + 1, "%[^}]", macname) != 1) {
  1880. X                PrintError ("Invalid macro format:", searchptr + 1);
  1881. X                return ((char *) NULL);
  1882. X            } 
  1883. X            *searchptr++ = MakeMac (LookupSymbol (macname), ID_MACRO);
  1884. X            bptr = eptr = searchptr;
  1885. X            while (*eptr++ != '}')    /* delete old macro chars */
  1886. X                /* empty */ ;
  1887. X            do
  1888. X                *bptr++ = *eptr;
  1889. X            while (*eptr++ != '\0');
  1890. X        }
  1891. X    return (pstring);
  1892. X}
  1893. X
  1894. X
  1895. X/*
  1896. X *    MakeRStr () -- Construct and return a pointer to a class read string 
  1897. X *               using the filename fname and read format rformat.  
  1898. X *
  1899. X */
  1900. Xchar *
  1901. XMakeRStr (fname, rformat)
  1902. Xchar *fname,            /* file name for class read */
  1903. X     *rformat;            /* format for class read    */
  1904. X{
  1905. X    register char *res;    /* resultant read string    */
  1906. X
  1907. X    Rformat = TRUE;        /* set read format flag     */
  1908. X    if (rformat == NULL)
  1909. X        return (fname);
  1910. X    res = (char *) realloc (fname, strlen (fname) + strlen (rformat) + 2);
  1911. X    if (res == NULL)
  1912. X        FatalError ("System out of string space in MakeRStr ()", (char *) NULL);
  1913. X    res = strcat (res, " ");    /* construct read string */
  1914. X    res = strcat (res, rformat);
  1915. X    free (rformat);
  1916. X    return (res);
  1917. X}
  1918. X
  1919. X
  1920. X/*
  1921. X *    ListAppend () -- Append string list2 to string list1 using the 
  1922. X *             separator sep.  A pointer to the newly constructed
  1923. X *             string is returned.
  1924. X *
  1925. X */
  1926. Xchar *
  1927. XListAppend (list1, list2, sep)
  1928. Xchar *list1,            /* first string     */
  1929. X     *list2,            /* second string      */
  1930. X     *sep;            /* string separator    */
  1931. X{
  1932. X    register char *res;    /* resultant string    */
  1933. X
  1934. X    res = (char *) malloc (strlen (list1) + strlen (list2) + strlen (sep) + 1);
  1935. X    if (res == NULL)
  1936. X        FatalError ("System out of string space in ListAppend ()", (char *) NULL);
  1937. X    res = strcpy (res, list1);
  1938. X    if (list1 != NULL)    /* use separator if first string not null */
  1939. X        res = strcat (res, sep);
  1940. X    res = strcat (res, list2);
  1941. X    return (res);
  1942. X}
  1943. X
  1944. X
  1945. X/*
  1946. X *    MakeCond () -- Construct a macro conditional string in cf format.  The
  1947. X *               conditional is based on the macro testmac, with an "if
  1948. X *               set" result ifstring, which may contain an optional 
  1949. X *               "if not set" result string appended to it.
  1950. X *
  1951. X */
  1952. Xchar *
  1953. XMakeCond (testmac, ifstring)
  1954. Xstruct he *testmac;        /* macro for conditional testing          */
  1955. Xchar       *ifstring;         /* "if macro set" result string(s)           */
  1956. X{
  1957. X    register char *res;    /* resultant conditional string             */
  1958. X
  1959. X    Mtest[2] = MakeMac (testmac, ID_MACRO);       /* get one-char macro rep */
  1960. X    res = (char *) malloc (strlen (ifstring) + 6);
  1961. X    if (res == NULL)
  1962. X        FatalError ("System out of string space in MakeCond ()", (char *) NULL);
  1963. X    res = strcpy (res, Mtest);
  1964. X    res = strcat (res, ifstring);        /* build result part      */
  1965. X    res = strcat (res, "$.");        /* end of conditional     */
  1966. X    free (ifstring);
  1967. X    return (res);
  1968. X}
  1969. X
  1970. X
  1971. X/*
  1972. X *    MakePosTok () -- Construct and return a positional token string 
  1973. X *             representation from the parameter num.
  1974. X *
  1975. X */
  1976. Xchar *
  1977. XMakePosTok (num)
  1978. Xregister int num;            /* numerical value of positional token */
  1979. X{
  1980. X    if (num > MAXTOKPOS) {
  1981. X        ErrorReport ("Positional token too large.\n");
  1982. X        return ((char *) NULL);
  1983. X    } else {
  1984. X        if (num > 9) {    /* two-digit positional token */
  1985. X            Ptok[1] = '0' + (num / 10);
  1986. X            Ptok[2] = '0' + (num % 10);
  1987. X            Ptok[3] = '\0';
  1988. X        } else {
  1989. X            Ptok[1] = '0' + num;
  1990. X            Ptok[2] = '\0';
  1991. X        }
  1992. X    return (Ptok);
  1993. X    }
  1994. X}
  1995. X
  1996. X
  1997. X/*
  1998. X *    Bracket () -- Construct and return a cf string form of the 
  1999. X *              canonicalization of the string identifier passed in
  2000. X *              the string parameter psb if dflag is true, else
  2001. X *              simply bracket the identifier without dollar signs
  2002. X *              for numeric hostname specifications.
  2003. X *
  2004. X */
  2005. Xchar *
  2006. XBracket (psb, dflag)
  2007. Xchar *psb;            /* identifier to be canonicalized */
  2008. Xshort dflag;            /* dollar flag               */
  2009. X{
  2010. X    register char *res;    /* resultant cf form           */
  2011. X    register short extra;    /* extra space needed for malloc  */
  2012. X    
  2013. X    extra = dflag ? 5 : 3;
  2014. X    res = (char *) malloc (strlen (psb) + extra);
  2015. X    if (res == NULL)
  2016. X        FatalError ("System out of string space in Bracket ()", (char *) NULL);
  2017. X    if (dflag)
  2018. X        res = strcpy (res, "$[");
  2019. X    else
  2020. X        res = strcpy (res, "[");
  2021. X    res = strcat (res, psb);
  2022. X    if (dflag)
  2023. X        res = strcat (res, "$");
  2024. X    res = strcat (res, "]");
  2025. X    return (res);
  2026. X}
  2027. X
  2028. X
  2029. X/*
  2030. X *    MakeRSCall () -- Construct and return a cf string form of a call
  2031. X *             to a ruleset (cid), which would pass to it the
  2032. X *             remainder of a rewriting address (rwaddr).
  2033. X *
  2034. X */
  2035. Xchar *
  2036. XMakeRSCall (cid, rwaddr)
  2037. Xregister struct he *cid;    /* called ruleset identifier         */
  2038. Xregister char *rwaddr;        /* remainder of rewriting address    */
  2039. X{
  2040. X    register char *res;    /* resultant cf string for the call  */
  2041. X    
  2042. X    if (!ISRULESET(cid->idtype)) {    /* check validity of ruleset */
  2043. X        PrintError ("Undefined ruleset identifier:", cid->psb);
  2044. X        return ((char *) NULL);
  2045. X    }
  2046. X    res = (char *) malloc (strlen (cid->idval.rsn) + strlen (rwaddr) + 3);
  2047. X    if (res == NULL)
  2048. X        FatalError ("System out of string space in MakeRSCall ()", (char *) NULL);
  2049. X    res = strcpy (res, "$>");    /* construct the call string */
  2050. X    res = strcat (res, cid->idval.rsn);
  2051. X    res = strcat (res, rwaddr);
  2052. X    return (res);
  2053. X}
  2054. X
  2055. X
  2056. X/*
  2057. X *    MakeField () -- Construct and return the cf string format for a
  2058. X *            field variable.  The match count (count), an optional
  2059. X *            class (class), and a match repetition flag (fstar)
  2060. X *            are used to determine what type of field string to
  2061. X *            construct.
  2062. X *
  2063. X */
  2064. Xchar *
  2065. XMakeField (count, class, fstar)
  2066. Xregister int count;        /* match count (0 or 1) */
  2067. Xregister struct he *class;    /* optional class type  */
  2068. Xregister short fstar;        /* repetition flag    */
  2069. X{
  2070. X    switch (count) {
  2071. X        case 0:      if (class == NULL)    /* any token is valid */
  2072. X                if (fstar)
  2073. X                    return (Zfield);
  2074. X                else {
  2075. X                    ErrorReport ("Invalid field type.\n");
  2076. X                    return ((char *) NULL);
  2077. X                }
  2078. X              else {        /* match 0 from class */
  2079. X                Cfield[1] = '~';
  2080. X                Cfield[2] = MakeMac (class, ID_CLASS);
  2081. X                return (Cfield);
  2082. X              }
  2083. X        case 1:      if (class == NULL)    /* any token is valid */
  2084. X                if (fstar)
  2085. X                    return (Pfield);
  2086. X                else
  2087. X                    return (Ofield);
  2088. X              else {        /* match 1 from class */
  2089. X                Cfield[1] = '=';
  2090. X                Cfield[2] = MakeMac (class, ID_CLASS);
  2091. X                return (Cfield);
  2092. X              }
  2093. X        default:  ErrorReport ("Invalid field type.\n");
  2094. X    }
  2095. X    /*NOTREACHED*/
  2096. X}
  2097. END_OF_FILE
  2098. if test 10730 -ne `wc -c <'src/strops.c'`; then
  2099.     echo shar: \"'src/strops.c'\" unpacked with wrong size!
  2100. fi
  2101. # end of 'src/strops.c'
  2102. fi
  2103. echo shar: End of archive 3 \(of 4\).
  2104. cp /dev/null ark3isdone
  2105. MISSING=""
  2106. for I in 1 2 3 4 ; do
  2107.     if test ! -f ark${I}isdone ; then
  2108.     MISSING="${MISSING} ${I}"
  2109.     fi
  2110. done
  2111. if test "${MISSING}" = "" ; then
  2112.     echo You have unpacked all 4 archives.
  2113.     rm -f ark[1-9]isdone
  2114. else
  2115.     echo You still need to unpack the following archives:
  2116.     echo "        " ${MISSING}
  2117. fi
  2118. ##  End of shell archive.
  2119. exit 0
  2120.  
  2121. -- 
  2122.  
  2123. Rich $alz            "Anger is an energy"
  2124. Cronus Project, BBN Labs    rsalz@bbn.com
  2125. Moderator, comp.sources.unix    sources@uunet.uu.net
  2126.