home *** CD-ROM | disk | FTP | other *** search
/ NetNews Usenet Archive 1992 #20 / NN_1992_20.iso / spool / comp / sources / misc / 3944 < prev    next >
Encoding:
Text File  |  1992-09-13  |  57.1 KB  |  2,438 lines

  1. Newsgroups: comp.sources.misc
  2. Path: sparky!kent
  3. From: wht@n4hgf.Mt-Park.GA.US (Warren Tucker)
  4. Subject:  v32i052:  ecu - ECU Asynchronous Communications v3.20, Part17/40
  5. Message-ID: <1992Sep13.153653.5650@sparky.imd.sterling.com>
  6. Followup-To: comp.sources.d
  7. X-Md4-Signature: 1e1581eedfca7743f82adff0a5d02ca7
  8. Sender: kent@sparky.imd.sterling.com (Kent Landfield)
  9. Organization: Sterling Software
  10. References: <csm-v32i036=ecu.141245@sparky.IMD.Sterling.COM>
  11. Date: Sun, 13 Sep 1992 15:36:53 GMT
  12. Approved: kent@sparky.imd.sterling.com
  13. Lines: 2423
  14.  
  15. Submitted-by: wht@n4hgf.Mt-Park.GA.US (Warren Tucker)
  16. Posting-number: Volume 32, Issue 52
  17. Archive-name: ecu/part17
  18. Environment: SCO,XENIX,ISC,SUNOS,SYSVR4,HDB,Curses
  19. Supersedes: ecu: Volume 21, Issue 53-89
  20.  
  21. ---- Cut Here and feed the following to sh ----
  22. #!/bin/sh
  23. # this is ecu320.17 (part 17 of ecu320)
  24. # do not concatenate these parts, unpack them in order with /bin/sh
  25. # file gint.c continued
  26. #
  27. if test ! -r _shar_seq_.tmp; then
  28.     echo 'Please unpack part 1 first!'
  29.     exit 1
  30. fi
  31. (read Scheck
  32.  if test "$Scheck" != 17; then
  33.     echo Please unpack part "$Scheck" next!
  34.     exit 1
  35.  else
  36.     exit 0
  37.  fi
  38. ) < _shar_seq_.tmp || exit 1
  39. if test ! -f _shar_wnt_.tmp; then
  40.     echo 'x - still skipping gint.c'
  41. else
  42. echo 'x - continuing file gint.c'
  43. sed 's/^X//' << 'SHAR_EOF' >> 'gint.c' &&
  44. X
  45. X        default:
  46. X            break;
  47. X    }   /* end of switch statement */
  48. X
  49. X/* we did not catch any special cases with the switch statement must
  50. Xbe numeric integer */
  51. X
  52. X    return(gint_constant(param,value));
  53. X
  54. X}   /* end of gint_base() */
  55. X
  56. X/*+-------------------------------------------------------------------------
  57. X    gintop(param,intop) - evaluate integer operator
  58. X--------------------------------------------------------------------------*/
  59. Xint
  60. Xgintop(param,intop)
  61. XESD *param;
  62. Xint *intop;
  63. X{
  64. X    register erc;
  65. X
  66. X    if(erc = skip_cmd_break(param))
  67. X        return(erc);
  68. X    switch(param->pb[param->index])
  69. X    {
  70. X        case '+':
  71. X            param->index++;
  72. X            *intop = OP_ADD;
  73. X            break;
  74. X
  75. X        case '-':
  76. X            param->index++;
  77. X            *intop = OP_SUB;
  78. X            break;
  79. X
  80. X        case '*':
  81. X            param->index++;
  82. X            *intop = OP_MUL;
  83. X            break;
  84. X
  85. X        case '/':
  86. X            param->index++;
  87. X            *intop = OP_DIV;
  88. X            break;
  89. X
  90. X        case '|':
  91. X            if(*(param->pb + param->index + 1) == '|')
  92. X                return(eInvalidIntOp);
  93. X            param->index++;
  94. X            *intop = OP_OR;
  95. X            break;
  96. X
  97. X        case '@':
  98. X            param->index++;
  99. X            *intop = OP_MOD;
  100. X            break;
  101. X
  102. X        case '^':
  103. X            param->index++;
  104. X            *intop = OP_XOR;
  105. X            break;
  106. X
  107. X        case '&':
  108. X            if(*(param->pb + param->index + 1) == '&')
  109. X                return(eInvalidIntOp);
  110. X            param->index++;
  111. X            *intop = OP_AND;
  112. X            break;
  113. X
  114. X        default:
  115. X            return(eInvalidIntOp);
  116. X    }   /* end of switch statement */
  117. X
  118. X    return(0);
  119. X
  120. X}   /* end of gintop() */
  121. X
  122. X/*+-------------------------------------------------------------------------
  123. X    gint(param,int_returned) - evaluate integer expression
  124. X--------------------------------------------------------------------------*/
  125. Xint
  126. Xgint(param,int_returned)
  127. XESD *param;
  128. Xlong *int_returned;
  129. X{
  130. Xregister erc;
  131. Xlong int1;
  132. Xlong int_accum = 0;
  133. Xint intop;
  134. Xint unary_minus = 0;
  135. X
  136. X    if(erc = skip_cmd_break(param))
  137. X        return(erc);
  138. X    if(param->pb[param->index] == '-')
  139. X        unary_minus++,param->index++;
  140. X
  141. X    if(erc = gint_base(param,&int1))
  142. X        return(erc);
  143. X    int_accum = (unary_minus) ? -int1 : int1;
  144. X
  145. X    while((erc = gintop(param,&intop)) == 0)
  146. X    {
  147. X        if(erc = gint_base(param,&int1))
  148. X            return(erc);
  149. X        switch(intop)
  150. X        {
  151. X            case OP_ADD:
  152. X                int_accum += int1;
  153. X                break;
  154. X            case OP_SUB:
  155. X                int_accum -= int1;
  156. X                break;
  157. X            case OP_MUL:
  158. X                int_accum *= int1;
  159. X                break;
  160. X            case OP_DIV:
  161. X                int_accum /= int1;
  162. X                break;
  163. X            case OP_MOD:
  164. X                int_accum %= int1;
  165. X                break;
  166. X            case OP_XOR:
  167. X                int_accum ^= (unsigned)int1;
  168. X                break;
  169. X            case OP_AND:
  170. X                int_accum &= (unsigned)int1;
  171. X                break;
  172. X            case OP_OR:
  173. X                int_accum |= (unsigned)int1;
  174. X                break;
  175. X            default:
  176. X                return(eInvalidIntOp);
  177. X        }
  178. X    }
  179. X    param->index = param->old_index;
  180. X
  181. X    *int_returned = int_accum;
  182. X    return(0);
  183. X}   /* end of gint() */
  184. X
  185. X/*+-------------------------------------------------------------------------
  186. X    col_range(param,col1,col2) - get a column range
  187. X:$i0[-$i1]
  188. Xargument may be integer constant, function or variable, but not expression
  189. X--------------------------------------------------------------------------*/
  190. Xint
  191. Xgcol_range(param,col1,col2)
  192. XESD *param;
  193. Xulong *col1;
  194. Xulong *col2;
  195. X{
  196. X    register erc;
  197. X
  198. X    if(skip_cmd_char(param,':') == 0)
  199. X    {
  200. X        if(erc = gint_base(param,col1))
  201. X            return(erc);
  202. X
  203. X        if(skip_cmd_char(param,'-') == 0)     /* if hyphen found, range */
  204. X        {
  205. X            if(erc = gint_base(param,col2))
  206. X                return(erc);
  207. X        }
  208. X        else
  209. X            *col2 = *col1;        /* otherwise, first and last columns same */
  210. X
  211. X        if(*col1 > *col2)
  212. X        {
  213. X            pputs("Invalid column range: column 1 greater than column 2\n");
  214. X            return(eFATAL_ALREADY);
  215. X        }
  216. X    }
  217. X    else
  218. X        erc = eBadParameter;
  219. X
  220. X    return(erc);
  221. X}   /* end of gcol_range() */
  222. X
  223. X/* vi: set tabstop=4 shiftwidth=4: */
  224. X/* end of gint.c */
  225. SHAR_EOF
  226. echo 'File gint.c is complete' &&
  227. chmod 0644 gint.c ||
  228. echo 'restore of gint.c failed'
  229. Wc_c="`wc -c < 'gint.c'`"
  230. test 7030 -eq "$Wc_c" ||
  231.     echo 'gint.c: original size 7030, current size' "$Wc_c"
  232. rm -f _shar_wnt_.tmp
  233. fi
  234. # ============= gstr.c ==============
  235. if test -f 'gstr.c' -a X"$1" != X"-c"; then
  236.     echo 'x - skipping gstr.c (File already exists)'
  237.     rm -f _shar_wnt_.tmp
  238. else
  239. > _shar_wnt_.tmp
  240. echo 'x - extracting gstr.c (Text)'
  241. sed 's/^X//' << 'SHAR_EOF' > 'gstr.c' &&
  242. X/*+-------------------------------------------------------------------------
  243. X    gstr.c - ecu get string parameter functions
  244. X    wht@n4hgf.Mt-Park.GA.US
  245. X
  246. X  Defined functions:
  247. X    gstr(param,result,realloc_ok)
  248. X
  249. X--------------------------------------------------------------------------*/
  250. X/*+:EDITS:*/
  251. X/*:09-10-1992-13:59-wht@n4hgf-ECU release 3.20 */
  252. X/*:08-22-1992-15:39-wht@n4hgf-ECU release 3.20 BETA */
  253. X/*:07-25-1991-12:58-wht@n4hgf-ECU release 3.10 */
  254. X/*:05-02-1991-03:54-wht@n4hgf-new realloc algorithm */
  255. X/*:08-14-1990-20:40-wht@n4hgf-ecu3.00-flush old edit history */
  256. X
  257. X#include "ecu.h"
  258. X#include "ecuerror.h"
  259. X#include "esd.h"
  260. X#include "var.h"
  261. X
  262. Xextern int proctrace;
  263. X
  264. X/*+-------------------------------------------------------------------------
  265. X    gstr(param,result,realloc_ok) - get a string 
  266. X
  267. XExamples:
  268. X
  269. X set $s0='test ... '+%date+' '+%time+%chr(0x0D)+%chr(0x0A)
  270. X hexdump $s0
  271. X0000  74 65 73 74 20 2E 2E 2E 20 30 36 2D 30 39 2D 31 | test ... 06-09-1 |
  272. X0010  39 38 39 20 31 37 3A 31 35 0D 0A                | 989 17:15..      |
  273. X
  274. X set $s0='12345678':1-6+'abc'
  275. X set s0
  276. X$S00 = '234567abc'
  277. X
  278. Xif realloc_ok and string too small, realloc result string as necessary
  279. X
  280. X--------------------------------------------------------------------------*/
  281. Xint
  282. Xgstr(param,result,realloc_ok)
  283. XESD *param;
  284. XESD *result;
  285. Xint realloc_ok;
  286. X{
  287. Xregister char param_char;
  288. Xregister char *pb;
  289. XESD *tesd;
  290. XESD *svptr;
  291. Xint cb = 0;
  292. Xint segment_index;
  293. Xint next_is_literal = 0;    /* last char was not a backslash */
  294. Xulong itmp1;
  295. Xulong itmp2;
  296. Xulong itmp3;
  297. Xulong itmp4;
  298. Xint erc;
  299. Xint param_index_save;
  300. Xint result_remaining;
  301. Xint in_quoted_string = 0;   /* not currently in quoted string */
  302. Xint end_of_parameter = 0;
  303. X
  304. X    if(erc = skip_cmd_break(param))
  305. X        return(erc);
  306. X
  307. X    segment_index = 0;            
  308. X    result_remaining = result->maxcb;    /* number we can put into result */
  309. X    param_index_save = param->index;
  310. X
  311. X    if((tesd = esdalloc(ESD_MAXSIZE)) == (ESD *)0)
  312. X        return(eNoMemory);
  313. X    pb = tesd->pb;
  314. X
  315. XCONCATENATE:
  316. X    while((param->index < param->cb) && !end_of_parameter)
  317. X    {
  318. X        param_char = param->pb[param->index];
  319. X        if(in_quoted_string)
  320. X        {
  321. X            ++param->index;
  322. X            if(next_is_literal)
  323. X            {
  324. X                next_is_literal = 0;
  325. X                switch(param_char)
  326. X                {
  327. X                    case 'b' : param_char = 0x08; break;
  328. X                    case 'n' : param_char = 0x0A; break;
  329. X                    case 'r' : param_char = 0x0D; break;
  330. X                    case 't' : param_char = 0x09; break;
  331. X                    case '\'': param_char = '\''; break;
  332. X                }
  333. X                if((result_remaining-- == 0) &&
  334. X                    (!realloc_ok && (cb == ESD_MAXSIZE)))
  335. X                {
  336. X                    erc = eBufferTooSmall;
  337. X                    goto RETURN;
  338. X                }
  339. X                *(pb + cb++) = param_char;
  340. X            }
  341. X            else if(param_char == '\\')
  342. X                next_is_literal = 1;
  343. X            else if(param_char == '\'')
  344. X                in_quoted_string = 0;
  345. X            else
  346. X            {
  347. X                if((result_remaining-- == 0) &&
  348. X                    (!realloc_ok && (cb == ESD_MAXSIZE)))
  349. X                {
  350. X                    erc = eBufferTooSmall;
  351. X                    goto RETURN;
  352. X                }
  353. X                *(pb + cb++) = param_char;
  354. X            }
  355. X        }
  356. X        else /* not in quoted string */
  357. X        {
  358. X            param->old_index = param->index;
  359. X            switch(param_char)
  360. X            {
  361. X            case '\'':      /* apostrophe denotes literal text */
  362. X                ++param->index;
  363. X                in_quoted_string = 1;
  364. X                break;
  365. X
  366. X            case '%':
  367. X                ++param->index;
  368. X                tesd->cb = cb;
  369. X                if(erc = feval_str(param,tesd))
  370. X                    goto RETURN;
  371. X                cb = tesd->cb;
  372. X                result_remaining = (result->maxcb - cb);
  373. X                break;
  374. X
  375. X            case '$':           /* '$Snn' variable reference? */
  376. X                /* must be at least two more character */
  377. X                if(param->index >= param->cb-2)
  378. X                {
  379. X                    erc = eSyntaxError;
  380. X                    goto RETURN;
  381. X                }
  382. X                param->old_index = ++param->index;
  383. X                if(to_lower(param->pb[param->index++]) != 's' )
  384. X                {
  385. X                    erc = eIllegalVarType;
  386. X                    goto RETURN;
  387. X                }
  388. X                if(erc = get_svptr(param,&svptr,0))
  389. X                    goto RETURN;
  390. X                if((!realloc_ok && (svptr->cb > (result->maxcb - cb))) ||
  391. X                    (svptr->cb > (ESD_MAXSIZE - cb)))
  392. X                {
  393. X                    erc = eBufferTooSmall;
  394. X                    goto RETURN;
  395. X                }
  396. X                else if(svptr->cb)
  397. X                {
  398. X                    memcpy(&pb[cb],svptr->pb,svptr->cb);
  399. X                    cb += svptr->cb;
  400. X                    result_remaining -= svptr->cb;
  401. X                }
  402. X                break;
  403. X
  404. X            case ':':
  405. X/*
  406. X * itmp1 holds col 1 (0-n) of substring operation
  407. X * itmp2 holds col 2 (0-n) of operation adjusted to reflect
  408. X *       end of string segment
  409. X * itmp3 holds length of string segment
  410. X * itmp4 holds length of substring segment output by substring operation
  411. X*/
  412. X                if(erc = gcol_range(param,&itmp1,&itmp2))
  413. X                    goto RETURN;
  414. X                if((itmp3 = cb - segment_index)
  415. X                    &&
  416. X                    (itmp4 = ((itmp2<itmp3)?itmp2:itmp3) - itmp1 + 1))
  417. X                {
  418. X                    if(itmp1)
  419. X                        memcpy(&pb[segment_index],
  420. X                            &pb[segment_index+(int)itmp1],(int)itmp4);
  421. X                    cb -= ((int)itmp3 - (int)itmp4);
  422. X                }
  423. X                break;
  424. X
  425. X            case '+':
  426. X                segment_index = cb;
  427. X                ++param->index;
  428. X                goto CONCATENATE;
  429. X
  430. X            case ';':
  431. X            case '#':
  432. X                end_of_parameter = 1;
  433. X                break;
  434. X
  435. X            default:
  436. X                erc = 0;
  437. X                if((param->index < param->cb) &&
  438. X                    isalnum(*(param->pb + param->index)))
  439. X                    erc = eSyntaxError;
  440. X                else if(param_index_save == param->index)
  441. X                    erc = eBadParameter;
  442. X                end_of_parameter = 1;
  443. X                break;
  444. X            }   /* end of switch (param_char) */
  445. X        }       /* end of else not in quoted string */
  446. X    }           /* end of while(index<cb) */
  447. X
  448. X
  449. XRETURN:
  450. X    if(result_remaining < 0)
  451. X    {
  452. X        if(!realloc_ok)
  453. X            erc = eBufferTooSmall;
  454. X        else
  455. X        {
  456. X            int new_size = (cb + 128) & (~127);    /* speed + anti-fragment */
  457. X            if(new_size > ESD_MAXSIZE)
  458. X                new_size = ESD_MAXSIZE;
  459. X            if(new_size < cb)
  460. X                erc = eBufferTooSmall;
  461. X            else
  462. X                erc = esdrealloc(result,new_size);
  463. X        }
  464. X        if(erc)
  465. X            return(erc);
  466. X    }
  467. X    if(cb)
  468. X        memcpy(result->pb,pb,cb);
  469. X    result->cb = cb;
  470. X    esd_null_terminate(result);
  471. X    esdfree(tesd);
  472. X    return(erc);
  473. X}   /* end of gqstr */
  474. X
  475. X/* vi: set tabstop=4 shiftwidth=4: */
  476. X/* end of qstr.c */
  477. SHAR_EOF
  478. chmod 0644 gstr.c ||
  479. echo 'restore of gstr.c failed'
  480. Wc_c="`wc -c < 'gstr.c'`"
  481. test 5625 -eq "$Wc_c" ||
  482.     echo 'gstr.c: original size 5625, current size' "$Wc_c"
  483. rm -f _shar_wnt_.tmp
  484. fi
  485. # ============= hdbintf.c ==============
  486. if test -f 'hdbintf.c' -a X"$1" != X"-c"; then
  487.     echo 'x - skipping hdbintf.c (File already exists)'
  488.     rm -f _shar_wnt_.tmp
  489. else
  490. > _shar_wnt_.tmp
  491. echo 'x - extracting hdbintf.c (Text)'
  492. sed 's/^X//' << 'SHAR_EOF' > 'hdbintf.c' &&
  493. X#if defined(SHARE_DEBUG)
  494. X#define LOG_UNGETTY
  495. X#define LOG_HDBDIAL
  496. X#endif
  497. X
  498. X/* #define CHOOSE_DEBUG */
  499. X
  500. X/*+-------------------------------------------------------------------------
  501. X    hdbintf.c - HDB UUCP database and /etc/utmp interface routines
  502. X    wht@n4hgf.Mt-Park.GA.US
  503. X
  504. X  Defined functions:
  505. X    _ungetty_return_line(line)
  506. X    add_to_ungetty_list(line)
  507. X    dialcodes_translate(phone)
  508. X    dialstr_translate(translate_list,to_translate)
  509. X    display_ungetty_list()
  510. X    dvtype_match(typespec,dvtype)
  511. X    enddlent()
  512. X    enddvent()
  513. X    getdlent()
  514. X    getdlentname(name)
  515. X    getdvbaud(baud)
  516. X    getdvent()
  517. X    getdvline(line)
  518. X    getdvtype(type)
  519. X    hdb_choose_Any(baud)
  520. X    hdb_choose_Device(type,baud)
  521. X    hdb_dial(presult)
  522. X    hdb_dial_error_text(errcode)
  523. X    hdb_init()
  524. X    in_ungetty_list(line)
  525. X    malformed_Devices_entry(text,ntokens,tokens)
  526. X    remove_from_ungetty_list(line)
  527. X    reserve_line(line)
  528. X    strip_phone_num(sptr)
  529. X    ugstat_text(ugstat)
  530. X    ungetty_get_line(line)
  531. X    ungetty_return_all_but(line)
  532. X    ungetty_return_line(line)
  533. X
  534. XDate: Fri, 23 Aug 91 18:30:06 +0300 (MSD)
  535. XFrom: emory!hq.demos.su!ache (Andrew A. Chernov, canton Uri's citizen)
  536. X1) HDB dialers may return connect speed as return code (!= 0)
  537. X2) Using HDB Dialcodes file for phone numbers translation now
  538. X   (\D,\T escape sequence)
  539. X
  540. X--------------------------------------------------------------------------*/
  541. X/*+:EDITS:*/
  542. X/*:09-10-1992-13:59-wht@n4hgf-ECU release 3.20 */
  543. X/*:09-10-1992-03:35-wht@n4hgf-change the way we flunk a line=="-" */
  544. X/*:09-04-1992-19:08-wht@n4hgf-harden Devices parsing */
  545. X/*:08-29-1992-15:37-wht@n4hgf-absolutely prohibit /dev/tty fed to ecuungetty */
  546. X/*:08-22-1992-15:39-wht@n4hgf-ECU release 3.20 BETA */
  547. X/*:07-21-1992-17:20-wht@n4hgf-hdb_dial of "/=" type bug fixed */
  548. X/*:07-19-1992-22:12-wht@n4hgf-move old check_utmp here+call it reserve_line */
  549. X/*:07-19-1992-10:07-wht@n4hgf-add ungetty_return_all_but */
  550. X/*:07-19-1992-09:11-wht@n4hgf-validate tty line name before ungetty get */
  551. X/*:06-07-1992-17:05-wht@n4hgf-lock tty before ungetty get */
  552. X/*:05-13-1992-13:27-wht@n4hgf-active_pde use */
  553. X/*:05-13-1992-10:30-cma@ifsbd-Add baud rate checking to hdb_dial function */
  554. X/*:05-04-1992-04:45-wht@n4hgf-wrong sense of strcmp in ,M test for SVR4 */
  555. X/*:04-28-1992-03:29-wht@n4hgf-more fixes for abend due to line problems */
  556. X/*:04-27-1992-20:02-wht@n4hgf-add ecuungetty error reporting */
  557. X/*:04-25-1992-13:02-wht@n4hgf-some exits from hdb_choose_Any omitted enddvent */
  558. X/*:04-24-1992-21:59-wht@n4hgf-more SCO tty name normalizing */
  559. X/*:04-19-1992-03:21-jhpb@sarto.budd-lake.nj.us-3.18.37 has ESIX SVR4 */
  560. X/*:01-18-1992-13:29-root@n4hgf-use proctrace value for expresp_verbosity */
  561. X/*:11-15-1991-04:02-wht@n4hgf-SCO tty naming now observed in getdvline */
  562. X/*:09-01-1991-16:20-wht@n4hgf2-generalize HDB configuration files location */
  563. X/*:09-01-1991-02:27-wht@n4hgf2-dialer gets file name instead of "ECUdial" */
  564. X/*:08-25-1991-13:07-wht@n4hgf-apply ache@hq.demos.su patches */
  565. X/*:08-10-1991-17:39-wht@n4hgf-US_WEGOTIT handling */
  566. X/*:07-25-1991-12:58-wht@n4hgf-ECU release 3.10 */
  567. X/*:06-02-1991-17:42-wht@n4hgf-add getdvtype */
  568. X/*:06-02-1991-17:27-wht@n4hgf-hdb_choose_Device + move hdb_choose_Any here */
  569. X/*:10-16-1990-20:43-wht@n4hgf-add SHARE_DEBUG */
  570. X/*:09-19-1990-19:36-wht@n4hgf-ecu_log_event now gets pid for log from caller */
  571. X/*:08-14-1990-20:40-wht@n4hgf-ecu3.00-flush old edit history */
  572. X
  573. X#include "ecu.h"
  574. X#include "ecupde.h"
  575. X#include "esd.h"
  576. X#include "var.h"
  577. X#include "termecu.h"
  578. X#include "utmpstatus.h"
  579. X#include "ecuungetty.h"
  580. X#include "dvent.h"
  581. X#include "dlent.h"
  582. X#include "dialprog.h"
  583. X#include <errno.h>
  584. X#include <utmp.h>
  585. X
  586. Xchar *arg_token();
  587. Xchar *skip_ld_break();
  588. Xchar *dialcodes_translate();
  589. Xchar *strip_phone_num();
  590. X
  591. Xextern char kbdintr;        /* current input INTR */
  592. Xextern ulong colors_current;
  593. Xextern int proctrace;
  594. Xextern int expresp_verbosity;
  595. X
  596. Xint there_is_hdb_on_this_machine = 0;
  597. Xstatic FILE *fpdv = (FILE *)0;
  598. Xstatic FILE *fpdl = (FILE *)0;
  599. Xchar *Devices_file = "/usr/lib/uucp/Devices";
  600. Xchar *Dialers_file = "/usr/lib/uucp/Dialers";
  601. Xchar *Dialcodes_file = "/usr/lib/uucp/Dialcodes";
  602. Xuchar last_ugstat = 0;
  603. X
  604. X#define UNGETTY_LIST_MAX    3
  605. Xchar *ungetty_list[UNGETTY_LIST_MAX];
  606. X
  607. X/*+-------------------------------------------------------------------------
  608. X    display_ungetty_list() - display ungetty list with pputs()
  609. X--------------------------------------------------------------------------*/
  610. X#if defined(USE_ECUUNGETTY)
  611. Xvoid
  612. Xdisplay_ungetty_list()
  613. X{
  614. X    int itmp;
  615. X    int found_one = 0;
  616. X
  617. X    for(itmp = 0; itmp < UNGETTY_LIST_MAX; itmp++)
  618. X    {
  619. X        if(*ungetty_list[itmp])
  620. X        {
  621. X            found_one = 1;
  622. X            break;
  623. X        }
  624. X    }
  625. X
  626. X    if(!found_one)
  627. X    {
  628. X        pputs("No lines acquired by ecuungetty\n");
  629. X        return;
  630. X    }
  631. X
  632. X    pputs("Acquired by ecuungetty: ");
  633. X    for(itmp = 0; itmp < UNGETTY_LIST_MAX; itmp++)
  634. X    {
  635. X        if(*ungetty_list[itmp])
  636. X        {
  637. X            pputs(ungetty_list[itmp]);
  638. X            pputs(" ");
  639. X        }
  640. X    }
  641. X    pputs("\n");
  642. X
  643. X}    /* end of display_ungetty_list */
  644. X#endif /* defined(USE_ECUUNGETTY) */
  645. X
  646. X/*+-------------------------------------------------------------------------
  647. X    in_ungetty_list(line) - check for line present in ungetty list
  648. X--------------------------------------------------------------------------*/
  649. X#if defined(USE_ECUUNGETTY)
  650. Xint
  651. Xin_ungetty_list(line)
  652. Xchar *line;
  653. X{
  654. X    int itmp;
  655. X
  656. X    for(itmp = 0; itmp < UNGETTY_LIST_MAX; itmp++)
  657. X    {
  658. X        if(!strcmp(line,ungetty_list[itmp]))
  659. X            return(1);
  660. X    }
  661. X    return(0);
  662. X
  663. X}    /* end of in_ungetty_list */
  664. X#endif /* defined(USE_ECUUNGETTY) */
  665. X
  666. X/*+-------------------------------------------------------------------------
  667. X    add_to_ungetty_list(line) - add line to ungetty list
  668. X--------------------------------------------------------------------------*/
  669. X#if defined(USE_ECUUNGETTY)
  670. Xvoid
  671. Xadd_to_ungetty_list(line)
  672. Xchar *line;
  673. X{
  674. X    int itmp;
  675. X    char *lptr;
  676. X
  677. X    if(in_ungetty_list(line))
  678. X        return;
  679. X
  680. X    for(itmp = 0; itmp < UNGETTY_LIST_MAX; itmp++)
  681. X    {
  682. X        if(!*(lptr = ungetty_list[itmp]))
  683. X        {
  684. X            strcpy(lptr,line);
  685. X            return;
  686. X        }
  687. X    }
  688. X    ecu_log_event(getpid(),"ungetty_list overflow");
  689. X    termecu(TERMECU_LOGIC_ERROR);
  690. X    /*NOTREACHED*/
  691. X
  692. X}    /* end of add_to_ungetty_list */
  693. X#endif /* defined(USE_ECUUNGETTY) */
  694. X
  695. X/*+-------------------------------------------------------------------------
  696. X    remove_from_ungetty_list(line) - remove line from ungetty list
  697. X--------------------------------------------------------------------------*/
  698. X#if defined(USE_ECUUNGETTY)
  699. Xvoid
  700. Xremove_from_ungetty_list(line)
  701. Xchar *line;
  702. X{
  703. X    int itmp;
  704. X    char *lptr;
  705. X
  706. X    for(itmp = 0; itmp < UNGETTY_LIST_MAX; itmp++)
  707. X    {
  708. X        if(!strcmp((lptr = ungetty_list[itmp]),line))
  709. X        {
  710. X            *lptr = 0;
  711. X            return;
  712. X        }
  713. X    }
  714. X
  715. X#ifdef CHOOSE_DEBUG
  716. X    {
  717. X        char s128[128];
  718. X        sprintf(s128,"remove_from_ungetty_list failed for %s",line);
  719. X        ecu_log_event(getpid(),s128);
  720. X    }
  721. X#endif
  722. X
  723. X}    /* end of remove_from_ungetty_list */
  724. X#endif /* defined(USE_ECUUNGETTY) */
  725. X
  726. X/*+-------------------------------------------------------------------------
  727. X    ugstat_text(ugstat) - text for ecuungetty code
  728. X--------------------------------------------------------------------------*/
  729. Xchar *
  730. Xugstat_text(ugstat)
  731. Xint ugstat;
  732. X{
  733. X    static char errant[32];
  734. X
  735. X    switch(ugstat)
  736. X    {
  737. X        case UG_NOTENAB:
  738. X            return("line not enabled");
  739. X            break;
  740. X        case UG_RESTART:
  741. X            return("restart needed");
  742. X            break;
  743. X        case UG_FAIL:
  744. X            return("line in use");
  745. X            break;
  746. X        case UGE_T_LOGIN:
  747. X            return("-t found US_LOGIN");
  748. X            break;
  749. X        case UGE_T_LOGGEDIN:
  750. X            return("-t found US_LOGGGEDIN");
  751. X            break;
  752. X        case UGE_T_NOTFOUND:
  753. X            return("not found");
  754. X            break;
  755. X        case UGE_BADSWITCH:
  756. X            return("usage: bad switch");
  757. X            break;
  758. X        case UGE_BADARGC:
  759. X            return("usage: bad arg count");
  760. X            break;
  761. X        case UGE_BADARGV:
  762. X            return("this a valid tty??");
  763. X            break;
  764. X        case UGE_NOTROOT:
  765. X            return("not setuid root");
  766. X            break;
  767. X        case UGE_CALLER:
  768. X            return("invalid caller");
  769. X            break;
  770. X        case UGE_NOUUCP:
  771. X            return("cannot find uucp passwd entry");
  772. X            break;
  773. X        case UGE_LOGIC:
  774. X            return("logic error");
  775. X            break;
  776. X        case UGE_BOMB:
  777. X            return("core dumped or killed");
  778. X            break;
  779. X        case UGE_DNE:
  780. X            return("did not execute");
  781. X            break;
  782. X    }
  783. X    sprintf(errant,"error %u",ugstat);
  784. X    return(errant);
  785. X}    /* end of ugstat_text */
  786. X
  787. X/*+-------------------------------------------------------------------------
  788. X    ungetty_get_line(line) - acquire a line through ecuungetty protocol
  789. X--------------------------------------------------------------------------*/
  790. Xint
  791. Xungetty_get_line(line)
  792. Xchar *line;
  793. X{
  794. X#if !defined(USE_ECUUNGETTY)
  795. X    return(0);
  796. X#else
  797. X    int itmp;
  798. X    int rtn = 0;
  799. X    int we_locked = 0;
  800. X    int ungetty_pid;
  801. X    SIGTYPE (*original_sighdlr)();
  802. X    int wait_status;
  803. X    char ungetty[128];
  804. X    char ungetty_log[80];
  805. X    char bamboozlement[20];
  806. X    struct stat st;
  807. X    char *bamboozle();
  808. X
  809. X    /*
  810. X     * quick check - ecuungetty does a much better job
  811. X     */
  812. X    if(!strcmp(line,"/dev/tty")) /* some keep getting /dev/tty chown'd! */
  813. X        return(LINST_INVALID);
  814. X    if(stat(line,&st))
  815. X    {
  816. X        if(errno == ENOENT)
  817. X            return(LINST_NODEV);
  818. X        return(LINST_OPNFAIL);
  819. X    }
  820. X    if((st.st_mode & S_IFMT) != S_IFCHR)
  821. X        return(LINST_NOTCHR);
  822. X    if(!there_is_hdb_on_this_machine)
  823. X        return(0);
  824. X    if(in_ungetty_list(line))
  825. X        return(0);
  826. X
  827. X    /*
  828. X     * lock line before ecuungetty call
  829. X     */
  830. X    if((itmp = lock_tty(line)) && (itmp != LINST_WEGOTIT))
  831. X        return(itmp);
  832. X    we_locked = (!itmp);
  833. X
  834. X    sprintf(ungetty,"%s/ecuungetty",ECULIBDIR);
  835. X    strcpy(bamboozlement,bamboozle(getpid()));
  836. X    if(access(ungetty,1))
  837. X    {
  838. X        pperror(ungetty);
  839. X        rtn = LINST_ENABLED;
  840. X        goto RETURN;
  841. X    }
  842. X    original_sighdlr = signal(SIGCLD,SIG_DFL);
  843. X    if((ungetty_pid = smart_fork()) == 0)
  844. X    {
  845. X        execl(ungetty,"ungetty",line,bamboozlement,(char *)0);
  846. X        _exit(UGE_DNE);    /* did not execute */
  847. X    }
  848. X    while(((itmp = wait(&wait_status)) != ungetty_pid) && (itmp != -1))
  849. X        ;
  850. X    signal(SIGCLD,original_sighdlr);
  851. X
  852. X    if(wait_status & 0xFF)
  853. X        last_ugstat = UGE_BOMB;
  854. X    else
  855. X        last_ugstat = (uchar)(wait_status >> 8);
  856. X    switch(last_ugstat)
  857. X    {
  858. X        case UG_NOTENAB:    /* line acquired: not enabled */
  859. X            break;
  860. X
  861. X        case UG_RESTART:    /* line acquired: need ungetty -r when done */
  862. X#if defined(LOG_UNGETTY)
  863. X            sprintf(ungetty_log,"UNGETTY acquired %s",shm->Lline);
  864. X            ecu_log_event(getpid(),ungetty_log);
  865. X#endif
  866. X            add_to_ungetty_list(line);
  867. X            break;
  868. X
  869. X        case UG_FAIL:        /* line in use */
  870. X            rtn = LINST_ENABLED_IN_USE;
  871. X            break;
  872. X
  873. X        default:
  874. X            sprintf(ungetty_log,"UNGETTY status 0x%04x: %s",
  875. X                wait_status,ugstat_text(last_ugstat));
  876. X            ecu_log_event(getpid(),ungetty_log);
  877. X            rtn = (last_ugstat == UGE_BOMB)
  878. X                ? LINST_ECUUNGETTY2 : LINST_ECUUNGETTY;
  879. X            break;
  880. X    }
  881. X
  882. XRETURN: ;
  883. X    if(rtn && we_locked)
  884. X        unlock_tty(line);
  885. X    return(rtn);
  886. X
  887. X#endif /* !defined(USE_ECUUNGETTY) */
  888. X}    /* end of ungetty_get_line */
  889. X
  890. X/*+-------------------------------------------------------------------------
  891. X    reserve_line(line)
  892. Xreturn 0 if line reserved, else LINST code
  893. X--------------------------------------------------------------------------*/
  894. Xint
  895. Xreserve_line(line)
  896. Xchar *line;
  897. X{
  898. Xregister utstatus;
  899. Xregister status = 0;
  900. X
  901. X    switch(utstatus = utmp_status(line))
  902. X    {
  903. X        case US_DIALOUT:    /* enabled for login, currently dialout */
  904. X            status = LINST_DIALOUT_IN_USE;
  905. X            break;
  906. X        case US_LOGGEDIN:   /* enabled for login, in use */
  907. X            status = LINST_ENABLED_IN_USE;
  908. X            break;
  909. X        case US_NOTFOUND:   /* not in utmp, or getty dead */
  910. X            break;
  911. X        case US_WEGOTIT:    /* we own the line */
  912. X            status = LINST_WEGOTIT;   /* not really an error */
  913. X            break;
  914. X        case US_LOGIN:      /* enabled for login, idle */
  915. X            status = ungetty_get_line(line);
  916. X            break;
  917. X    }
  918. X
  919. X#if defined(LOG_LOCKS)
  920. X    {
  921. X        char s64[64];
  922. X        sprintf(s64,"UTMPCHK %s st=%d ut=%d",line,status,utstatus);
  923. X        ecu_log_event(getpid(),s64);
  924. X    }
  925. X#endif
  926. X
  927. X    return(status);
  928. X
  929. X}   /* end of reserve_line */
  930. X
  931. X/*+-------------------------------------------------------------------------
  932. X    _ungetty_return_line(line) - return line to "getty" status
  933. X--------------------------------------------------------------------------*/
  934. Xvoid
  935. X_ungetty_return_line(line)
  936. Xchar *line;
  937. X{
  938. X#if !defined(USE_ECUUNGETTY)
  939. X    return;
  940. X#else
  941. X    int ungetty_pid;
  942. X    int itmp;
  943. X    SIGTYPE (*original_sighdlr)();
  944. X    int wait_status = 0xDEAD;
  945. X    char ungetty[128];
  946. X#if defined(LOG_UNGETTY)
  947. X    char ungetty_log[80];
  948. X#endif
  949. X    char bamboozlement[20];
  950. X    char *bamboozle();
  951. X
  952. X    if(!there_is_hdb_on_this_machine)
  953. X        return;
  954. X    if(!in_ungetty_list(line))
  955. X        return;
  956. X
  957. X    sprintf(ungetty,"%s/ecuungetty",ECULIBDIR);
  958. X    strcpy(bamboozlement,bamboozle(getpid()));
  959. X
  960. X    /* call ungetty to see if we need to switch to dialin */
  961. X#if 0 /* if in_ungetty_list, trust we need to -r */
  962. X    if(access(ungetty,1))
  963. X    {
  964. X        pperror(ungetty);
  965. X        return;
  966. X    }
  967. X    original_sighdlr = signal(SIGCLD,SIG_DFL);
  968. X    if((ungetty_pid = smart_fork()) == 0)
  969. X    {
  970. X        execl(ungetty,"ungetty","-t",line,bamboozlement,(char *)0);
  971. X        ecu_log_event(getpid(),"could not exec ecuungetty -t");
  972. X        _exit(UGE_DNE);    /* did not execute */
  973. X    }
  974. X    while(((itmp = wait(&wait_status)) != ungetty_pid) &&
  975. X            (itmp != -1) )
  976. X        ;
  977. X    signal(SIGCLD,original_sighdlr);
  978. X
  979. X#if defined(LOG_UNGETTY)
  980. X    sprintf(ungetty_log,"UNGETTY -t %s status %04x",line,wait_status);
  981. X    ecu_log_event(getpid(),ungetty_log);
  982. X#endif
  983. X    switch((uchar)(wait_status >> 8))
  984. X    {
  985. X        case UG_RESTART:
  986. X            break;
  987. X
  988. X        default:
  989. X            remove_from_ungetty_list(line);
  990. X            return;
  991. X    }
  992. X#endif
  993. X
  994. X    original_sighdlr = signal(SIGCLD,SIG_DFL);
  995. X    if((ungetty_pid = smart_fork()) == 0)
  996. X    {
  997. X        execl(ungetty,"ungetty","-r",line,bamboozlement,(char *)0);
  998. X        ecu_log_event(getpid(),"could not exec ecuungetty -r");
  999. X        _exit(UGE_DNE);    /* did not execute */
  1000. X    }
  1001. X
  1002. X    while(((itmp = wait(&wait_status)) != ungetty_pid) &&
  1003. X            (itmp != -1))
  1004. X        ;
  1005. X
  1006. X#if defined(LOG_UNGETTY)
  1007. X    if(wait_status)
  1008. X    {
  1009. X        sprintf(ungetty_log,"UNGETTY -r %s status 0x%04x",
  1010. X            line,wait_status);
  1011. X    }
  1012. X    else
  1013. X        sprintf(ungetty_log,"UNGETTY returned %s",line);
  1014. X    ecu_log_event(getpid(),ungetty_log);
  1015. X#endif
  1016. X
  1017. X    remove_from_ungetty_list(line);
  1018. X
  1019. X#endif /* !defined(USE_ECUUNGETTY) */
  1020. X}    /* end of _ungetty_return_line */
  1021. X
  1022. X/*+-------------------------------------------------------------------------
  1023. X    ungetty_return_line(line) - return one or all lines to "getty" status
  1024. X--------------------------------------------------------------------------*/
  1025. Xvoid
  1026. Xungetty_return_line(line)
  1027. Xchar *line;
  1028. X{
  1029. X#if !defined(USE_ECUUNGETTY)
  1030. X    return;
  1031. X#else
  1032. X    int itmp;
  1033. X
  1034. X    if(line)
  1035. X        _ungetty_return_line(line);
  1036. X    else
  1037. X    {
  1038. X        for(itmp = 0; itmp < UNGETTY_LIST_MAX; itmp++)
  1039. X        {
  1040. X            if(*(line = ungetty_list[itmp]))
  1041. X                _ungetty_return_line(line);
  1042. X        }
  1043. X    }
  1044. X
  1045. X#endif /* !defined(USE_ECUUNGETTY) */
  1046. X}    /* end of ungetty_return_line */
  1047. X
  1048. X/*+-------------------------------------------------------------------------
  1049. X    ungetty_return_all_but(line) - return all lines but 'line'
  1050. X--------------------------------------------------------------------------*/
  1051. Xvoid
  1052. Xungetty_return_all_but(line)
  1053. Xchar *line;
  1054. X{
  1055. X#if !defined(USE_ECUUNGETTY)
  1056. X    return;
  1057. X#else
  1058. X    int itmp;
  1059. X
  1060. X    for(itmp = 0; itmp < UNGETTY_LIST_MAX; itmp++)
  1061. X    {
  1062. X        if(ungetty_list[itmp][0] && strcmp(line,ungetty_list[itmp]))
  1063. X            _ungetty_return_line(line);
  1064. X    }
  1065. X
  1066. X#endif /* !defined(USE_ECUUNGETTY) */
  1067. X}    /* end of ungetty_return_all_but */
  1068. X
  1069. X/*+-------------------------------------------------------------------------
  1070. X    malformed_Devices_entry(text,ntokens,tokens)
  1071. X--------------------------------------------------------------------------*/
  1072. Xvoid
  1073. Xmalformed_Devices_entry(text,ntokens,tokens)
  1074. Xchar *text;
  1075. Xint ntokens;
  1076. Xchar **tokens;
  1077. X{
  1078. X    char s512[512];
  1079. X    char *cptr;
  1080. X    char *nlptr;
  1081. X    static already = 0;
  1082. X    extern int tty_not_char_special;
  1083. X
  1084. X    sprintf(s512,"malformed Devices entry (%s):\n",text);
  1085. X    cptr = s512 + strlen(s512);
  1086. X    nlptr = cptr - 1;
  1087. X
  1088. X    while(ntokens--)
  1089. X    {
  1090. X        if(((cptr - s512) + strlen(*tokens) + 2) > sizeof(s512))
  1091. X            break;
  1092. X        sprintf(cptr,"%s ",*tokens++);
  1093. X        cptr += strlen(cptr);
  1094. X    }
  1095. X
  1096. X    if(!already && !tty_not_char_special)
  1097. X    {
  1098. X        pputs("\7\n");
  1099. X        pputs(s512);
  1100. X        pputs("\nFurther Devices errors will not be displayed,\n");
  1101. X        pputs("but are logged in ~/.ecu/log.  Press any key to continue.\7");
  1102. X        ttyflush(0);
  1103. X        ttygetc(1);
  1104. X        pputs("\n");
  1105. X    }
  1106. X    already = 1;
  1107. X
  1108. X    memcpy(s512,"MALFORMED",9);        /* mod for log file */
  1109. X    *nlptr = ' ';
  1110. X    ecu_log_event(xmtr_pid,s512);
  1111. X
  1112. X}    /* end of malformed_Devices_entry */
  1113. X
  1114. X/*+-------------------------------------------------------------------------
  1115. X    getdvent() - get first or next Devices entry (a la getpwent)
  1116. X--------------------------------------------------------------------------*/
  1117. XDVE *
  1118. Xgetdvent()
  1119. X{
  1120. X#define MAX_DV_TOKENS 9
  1121. X    char *tokens[MAX_DV_TOKENS];
  1122. X    int ntokens;
  1123. X#if 0
  1124. X    int itokens;
  1125. X#endif
  1126. X    char *cptr;
  1127. X    static DVE dve;
  1128. X    static char dvstr[256];
  1129. X    char *strchr();
  1130. X    char *skip_ld_break();
  1131. X
  1132. X    if(!there_is_hdb_on_this_machine)
  1133. X        goto RETURN_NULL;
  1134. X
  1135. X    if(!fpdv)
  1136. X    {
  1137. X        if(!(fpdv = fopen(Devices_file,"r")))
  1138. X        {
  1139. X            pperror(Devices_file);
  1140. X            goto RETURN_NULL;
  1141. X        }
  1142. X    }
  1143. X
  1144. X    while(1)
  1145. X    {
  1146. X        /*
  1147. X         * read a Devices line
  1148. X         */
  1149. X        if(!fgets(dvstr,sizeof(dvstr),fpdv))
  1150. X        {
  1151. XRETURN_NULL:
  1152. X#ifdef CHOOSE_DEBUG
  1153. X            ecu_log_event(xmtr_pid,"getdvent returning NULL");
  1154. X#endif
  1155. X            return((DVE *)0);
  1156. X        }
  1157. X
  1158. X        /*
  1159. X         * weed out comments and blank lines
  1160. X         */
  1161. X        if(strlen(dvstr) <= 1)                    /* blank line */
  1162. X            continue;
  1163. X        cptr = skip_ld_break(dvstr);            /* first non-blank */
  1164. X        if(!*cptr || strchr("#\n",*cptr))        /* comment or all white space */
  1165. X            continue;
  1166. X
  1167. X        /*
  1168. X         * tokenize
  1169. X         */
  1170. X        build_arg_array(dvstr,tokens,MAX_DV_TOKENS,&ntokens);
  1171. X
  1172. X        /*
  1173. X         * honor '#' whever it occurs
  1174. X         */
  1175. X#if 0
  1176. X        for(itokens = 0; itokens < ntokens; itokens++)
  1177. X        {
  1178. X            if(!tokens[itokens])
  1179. X                tokens[itokens] = "";
  1180. X            if(cptr = strchr(tokens[itokens],'#'))
  1181. X            {
  1182. X                *cptr = 0;
  1183. X                ntokens = itokens + 1;
  1184. X                break;
  1185. X            }
  1186. X        }
  1187. X#endif
  1188. X
  1189. X        /*
  1190. X         * a bit of validation
  1191. X         */
  1192. X        if(ntokens < 4)
  1193. X        {
  1194. X            malformed_Devices_entry("too few fields",ntokens,tokens);
  1195. X            continue;
  1196. X        }
  1197. X
  1198. X        /*
  1199. X         * TCP,et - - Any TCP - 
  1200. X         * found in Sun Devices (UUCP over TCP)
  1201. X         */
  1202. X#if 0    /* leave this generic; handle in getdvbaud and getdvtype */
  1203. X        if(!strcmp(tokens[1],"-"))
  1204. X        {
  1205. X            malformed_Devices_entry("bad tty specified",ntokens,tokens);
  1206. X            continue;
  1207. X        }
  1208. X#endif
  1209. X
  1210. X        break;
  1211. X    }
  1212. X
  1213. X    /*
  1214. X     * we have a good entry
  1215. X     */
  1216. X    dve.type = tokens[0];
  1217. X    dve.line = tokens[1];
  1218. X
  1219. X#if defined(SVR4)
  1220. X    { /* get rid of possible SVR4 ",M" modem control suffix */
  1221. X        int itmp;
  1222. X        itmp = strlen(dve.line);
  1223. X        if((itmp > 2) && !strcmp(dve.line + itmp - 2,",M"))
  1224. X          dve.line[itmp - 2] = 0;
  1225. X    }
  1226. X#endif /* SVR4 */
  1227. X
  1228. X    dve.dialer = tokens[2];
  1229. X    if(!strcmpi(tokens[3],"Any"))
  1230. X    {
  1231. X        dve.low_baud = 1;
  1232. X        dve.high_baud = 65535;
  1233. X    }
  1234. X    else
  1235. X    {
  1236. X        dve.low_baud = atoi(tokens[3]);
  1237. X        if(!(cptr = strchr(tokens[3],'-')))
  1238. X            dve.high_baud = dve.low_baud;
  1239. X        else
  1240. X            dve.high_baud = atoi(cptr + 1);
  1241. X    }
  1242. X    dve.dialprog = tokens[4];
  1243. X    dve.token = tokens[5];
  1244. X#ifdef CHOOSE_DEBUG
  1245. X    {
  1246. X        char s256[256];
  1247. X        sprintf(s256,"getdvent returning '%s' type='%s'",dve.line,dve.type);
  1248. X        ecu_log_event(xmtr_pid,s256);
  1249. X    }
  1250. X#endif
  1251. X    return(&dve);
  1252. X
  1253. X}    /* end of getdvent */
  1254. X
  1255. X/*+-------------------------------------------------------------------------
  1256. X    enddvent() - close Devices file
  1257. X--------------------------------------------------------------------------*/
  1258. Xvoid
  1259. Xenddvent()
  1260. X{
  1261. X    if(fpdv)
  1262. X    {
  1263. X        fclose(fpdv);
  1264. X        fpdv = (FILE *)0;
  1265. X    }
  1266. X}    /* end of enddvent */
  1267. X
  1268. X/*+-------------------------------------------------------------------------
  1269. X    getdvbaud(baud) - get Devices entry matching baud rate
  1270. X--------------------------------------------------------------------------*/
  1271. XDVE *
  1272. Xgetdvbaud(baud)
  1273. Xuint baud;
  1274. X{
  1275. X    DVE *tdve;
  1276. X
  1277. X#ifdef CHOOSE_DEBUG
  1278. X    char s128[128];
  1279. X
  1280. X    sprintf(s128,"getdvbaud looking for %u baud",baud);
  1281. X    ecu_log_event(getpid(),s128);
  1282. X#endif
  1283. X
  1284. X    while(1)
  1285. X    {
  1286. X        if((tdve = getdvent()) == (DVE *)0)
  1287. X            return(tdve);
  1288. X#ifdef CHOOSE_DEBUG
  1289. X        sprintf(s128,"getdvbaud found %s type '%s' baud lo=%d hi=%d",
  1290. X            tdve->line,tdve->type,tdve->low_baud,tdve->high_baud);
  1291. X        
  1292. X        ecu_log_event(getpid(),s128);
  1293. X#endif
  1294. X        if(!strcmp(tdve->line,"-"))    /* neo-entries like TCP have "-" line */
  1295. X            continue;
  1296. X        if((tdve->low_baud <= baud) && (baud <= tdve->high_baud))
  1297. X        {
  1298. X#ifdef CHOOSE_DEBUG
  1299. X            sprintf(s128,"getdvbaud returning %s",tdve->line);
  1300. X            ecu_log_event(getpid(),s128);
  1301. X#endif
  1302. X            return(tdve);
  1303. X        }
  1304. X    }
  1305. X    /*NOTREACHED*/
  1306. X
  1307. X}    /* end of getdvbaud */
  1308. X
  1309. X/*+-------------------------------------------------------------------------
  1310. X    getdvline(line) - get Devices entry matching line
  1311. Xcalling argument 'line's is string AFTER "/dev/"
  1312. X--------------------------------------------------------------------------*/
  1313. XDVE *
  1314. Xgetdvline(line)
  1315. Xchar *line;
  1316. X{
  1317. X    DVE *tdve;
  1318. X
  1319. X#ifdef CHOOSE_DEBUG
  1320. X    char s128[128];
  1321. X
  1322. X    sprintf(s128,"getdvline looking for %s",line);
  1323. X    ecu_log_event(getpid(),s128);
  1324. X#endif
  1325. X
  1326. X    while(1)
  1327. X    {
  1328. X        if((tdve = getdvent()) == (DVE *)0)
  1329. X            return(tdve);
  1330. X#ifdef CHOOSE_DEBUG
  1331. X        sprintf(s128,"getdvline %s found baud lo=%d hi=%d",tdve->line,
  1332. X            tdve->low_baud, tdve->high_baud);
  1333. X        ecu_log_event(getpid(),s128);
  1334. X#endif
  1335. X        if(!TTYNAME_STRCMP(tdve->line,line))
  1336. X            return(tdve);
  1337. X    }
  1338. X    /*NOTREACHED*/
  1339. X
  1340. X}    /* end of getdvline */
  1341. X
  1342. X/*+-------------------------------------------------------------------------
  1343. X    dvtype_match(typespec,dvtype) - match between pde typespec and dvtype
  1344. X
  1345. Xreturns 1 if pde type specification 'typespec' matches Devices device 'type'
  1346. X--------------------------------------------------------------------------*/
  1347. Xint
  1348. Xdvtype_match(typespec,dvtype)
  1349. Xchar *typespec;
  1350. Xchar *dvtype;
  1351. X{
  1352. X    char *emsg;
  1353. X    char *match;
  1354. X    int matchlen;
  1355. X    int re_match = 1;
  1356. X    char cmpbuf[128];
  1357. X
  1358. X    if(*typespec == '=')
  1359. X        typespec++;
  1360. X    else if(*typespec == '/')
  1361. X    {
  1362. X        re_match = 0;
  1363. X        typespec++;
  1364. X    }
  1365. X
  1366. X    if(re_match)
  1367. X    {
  1368. X        if(!strcmp(dvtype,typespec))
  1369. X            return(1);
  1370. X    }
  1371. X    else
  1372. X    {
  1373. X        if(regexp_compile(typespec,cmpbuf,sizeof(cmpbuf),&emsg))
  1374. X            return(0);
  1375. X        if(regexp_scan(cmpbuf,dvtype,&match,&matchlen))
  1376. X            return(1);
  1377. X    }
  1378. X    return(0);
  1379. X
  1380. X}    /* end of dvtype_match */
  1381. X
  1382. X/*+-------------------------------------------------------------------------
  1383. X    getdvtype(type) - get Devices entry matching type
  1384. X
  1385. Xtype is either 'Device_type'   search for exact match on Device_type
  1386. X               '=Device_type'  search for exact match on Device_type
  1387. X               '/regexp'       search for match with regular expression
  1388. X
  1389. Xyou must make sure any supplied regexp is a valid one, for regexp
  1390. Xcompilation errors are indistinguishable from other seach failures
  1391. X
  1392. Xuses optimized implementation of dvtype_match functionality
  1393. X--------------------------------------------------------------------------*/
  1394. XDVE *
  1395. Xgetdvtype(type)
  1396. Xchar *type;
  1397. X{
  1398. X    DVE *tdve;
  1399. X    char *emsg;
  1400. X    char *match;
  1401. X    int matchlen;
  1402. X    int re_match = 0;    /* regular expression match */
  1403. X    char cmpbuf[128];
  1404. X
  1405. X    if(*type == '=')
  1406. X        type++;
  1407. X    else if(*type == '/')
  1408. X    {
  1409. X        re_match = 1;
  1410. X        type++;
  1411. X        if(regexp_compile(type,cmpbuf,sizeof(cmpbuf),&emsg))
  1412. X            return((DVE *)0);
  1413. X    }
  1414. X
  1415. X    while(tdve = getdvent())
  1416. X    {
  1417. X        if(!strcmp(tdve->line,"-"))    /* neo-entries like TCP have "-" line */
  1418. X            continue;
  1419. X        if(re_match)
  1420. X        {
  1421. X            if(regexp_scan(cmpbuf,tdve->type,&match,&matchlen))
  1422. X                break;
  1423. X        }
  1424. X        else
  1425. X        {
  1426. X            if(!strcmp(tdve->type,type))
  1427. X                break;
  1428. X        }
  1429. X    }
  1430. X    return(tdve);
  1431. X
  1432. X}    /* end of getdvtype */
  1433. X
  1434. X/*+-------------------------------------------------------------------------
  1435. X    dialstr_translate(translate_list,to_translate) - translate dial strings
  1436. X--------------------------------------------------------------------------*/
  1437. X#if 0
  1438. Xvoid
  1439. Xdialstr_translate(translate_list,to_translate)
  1440. Xregister char *translate_list;
  1441. Xchar *to_translate;
  1442. X{
  1443. X    register char *cptr;
  1444. X
  1445. X    while(*translate_list && *(translate_list + 1))
  1446. X    {
  1447. X        for(cptr=to_translate; *cptr; cptr++)
  1448. X        {
  1449. X            if(*translate_list == *cptr)
  1450. X                *cptr = *(translate_list + 1);
  1451. X        }
  1452. X        translate_list += 2;
  1453. X    }
  1454. X}    /* end of dialstr_translate */
  1455. X#endif
  1456. X
  1457. X/*+-------------------------------------------------------------------------
  1458. X    getdlent() - get first or next Dialers entry (a la getpwent)
  1459. X--------------------------------------------------------------------------*/
  1460. Xstruct dlent *
  1461. Xgetdlent()
  1462. X{
  1463. X    int itmp;
  1464. X#define MAX_DL_TOKENS 3
  1465. X    char *tokens[MAX_DL_TOKENS];
  1466. X    static struct dlent dle;
  1467. X    static char dlstr[128];
  1468. X    char *strchr();
  1469. X
  1470. X    if(!there_is_hdb_on_this_machine)
  1471. X        return((struct dlent *)0);
  1472. X
  1473. X    if(!fpdl)
  1474. X    {
  1475. X        if(!(fpdl = fopen(Dialers_file,"r")))
  1476. X        {
  1477. X            pperror(Dialers_file);
  1478. X            return((struct dlent *)0);
  1479. X        }
  1480. X    }
  1481. X
  1482. X    while(1)
  1483. X    {
  1484. X        if(!fgets(dlstr,sizeof(dlstr),fpdl))
  1485. X            return((struct dlent *)0);
  1486. X        if(((itmp = strlen(dlstr)) <= 1) || (dlstr[0] == '#') ||
  1487. X            (dlstr[0] == ' '))
  1488. X        {
  1489. X            continue;
  1490. X        }
  1491. X        dlstr[--itmp] = 0;
  1492. X        for(itmp = 0; itmp < MAX_DL_TOKENS; itmp++)
  1493. X            tokens[itmp] = "";
  1494. X        if(tokens[0] = arg_token(dlstr," \t\r\n"))
  1495. X        {
  1496. X            if(tokens[1] = arg_token((char *)0," \t\r\n"))
  1497. X            {
  1498. X            extern char *str_token_static;
  1499. X                tokens[2] = skip_ld_break(str_token_static);
  1500. X            }
  1501. X        }
  1502. X        break;
  1503. X    }
  1504. X
  1505. X    dle.name = tokens[0];
  1506. X    dle.tlate = tokens[1];
  1507. X    dle.script = tokens[2];
  1508. X    return(&dle);
  1509. X
  1510. X}    /* end of getdlent */
  1511. X
  1512. X/*+-------------------------------------------------------------------------
  1513. X    enddlent() - close Dialers file
  1514. X--------------------------------------------------------------------------*/
  1515. Xvoid
  1516. Xenddlent()
  1517. X{
  1518. X    if(fpdl)
  1519. X    {
  1520. X        fclose(fpdl);
  1521. X        fpdl = (FILE *)0;
  1522. X    }
  1523. X}    /* end of enddlent */
  1524. X
  1525. X/*+-------------------------------------------------------------------------
  1526. X    getdlentname(name) - get Dialers entry by name
  1527. X--------------------------------------------------------------------------*/
  1528. Xstruct dlent *
  1529. Xgetdlentname(name)
  1530. Xchar *name;
  1531. X{
  1532. X    register DLE *tdle;
  1533. X
  1534. X    while(tdle = getdlent())
  1535. X    {
  1536. X        if(!strcmp(name,tdle->name))
  1537. X            break;
  1538. X    }
  1539. X    return(tdle);
  1540. X
  1541. X}    /* end of getdlentname */
  1542. X
  1543. X/*+-------------------------------------------------------------------------
  1544. X    hdb_choose_Any(baud) - user will take 'Any' line
  1545. X
  1546. Xgive preference to current line
  1547. X--------------------------------------------------------------------------*/
  1548. XDVE *
  1549. Xhdb_choose_Any(baud)
  1550. Xuint baud;
  1551. X{
  1552. X    DVE *tdve = (DVE *)0;
  1553. X    char newtty[sizeof(shm->Lline)];
  1554. X    int lerr = 0;
  1555. X    int utmpst = 0;
  1556. X#if defined(LOG_HDBDIAL) || defined(CHOOSE_DEBUG)
  1557. X    char s128[128];
  1558. X#endif
  1559. X
  1560. X#ifdef CHOOSE_DEBUG
  1561. X    sprintf(s128,"hdb_choose_Any baud=%u current line='%s'",baud,shm->Lline);
  1562. X    ecu_log_event(getpid(),s128);
  1563. X#endif
  1564. X
  1565. X    enddvent();    /* krock but safe */
  1566. X
  1567. X/*
  1568. X * see if shm->Lline in use by someone else; if not and baud rate ok, no further
  1569. X */
  1570. X
  1571. X    if(shm->Lline[0])
  1572. X    {
  1573. X        while(tdve = getdvline(shm->Lline + 5))
  1574. X        {
  1575. X            if((tdve->low_baud <= baud) && (baud <= tdve->high_baud))
  1576. X                break;
  1577. X        }
  1578. X
  1579. X        if(tdve)
  1580. X        {
  1581. X            switch(utmpst = utmp_status(shm->Lline))
  1582. X            {
  1583. X            case US_WEGOTIT:
  1584. X                goto RETURN;
  1585. X            case US_NOTFOUND:    /* not in utmp, or getty dead */
  1586. X#if 0
  1587. X                if(access(shm->Lline,6))
  1588. X                    break;
  1589. X#endif
  1590. X                if((lerr = line_lock_status(shm->Lline)) &&
  1591. X                    (lerr != LINST_WEGOTIT))
  1592. X                {
  1593. X                    break;
  1594. X                }
  1595. X                goto RETURN;
  1596. X            case US_LOGIN:        /* enabled for login, idle */
  1597. X                goto RETURN;
  1598. X            }
  1599. X        }
  1600. X
  1601. X        enddvent();
  1602. X    }
  1603. X
  1604. X    /*
  1605. X     * we've got to pick a new line
  1606. X     */
  1607. X
  1608. X#ifdef CHOOSE_DEBUG
  1609. X    sprintf(s128,"must pick new line utmpst=%u lerr=%u",utmpst,lerr);
  1610. X    ecu_log_event(getpid(),s128);
  1611. X#endif
  1612. X
  1613. X    lerr = 0;
  1614. X    while(1)
  1615. X    {
  1616. X        if(!(tdve = getdvbaud(baud)))
  1617. X            break;
  1618. X
  1619. X        /* by now, we know shm->Lline wont work */
  1620. X        if(!TTYNAME_STRCMP(tdve->line,shm->Lline + 5))
  1621. X            continue;
  1622. X
  1623. X        /* if not acu, dont use it */
  1624. X        if(ulindex(tdve->type,"ACU") < 0)
  1625. X            continue;
  1626. X
  1627. X        sprintf(newtty,"/dev/%s",tdve->line);
  1628. X        switch(utmpst = utmp_status(newtty))
  1629. X        {
  1630. X            case US_NOTFOUND:    /* not in utmp, or getty dead */
  1631. X#if 0
  1632. X                if(access(newtty,6)) /* ecuungetty won't be able to help us */
  1633. X                    break;
  1634. X#endif
  1635. X                if((lerr = line_lock_status(newtty)) &&
  1636. X                    (lerr != LINST_WEGOTIT))
  1637. X                {
  1638. X                    break;
  1639. X                }
  1640. X                goto RETURN;
  1641. X
  1642. X            case US_LOGIN:        /* enabled for login, idle */
  1643. X                goto RETURN;
  1644. X
  1645. X            case US_WEGOTIT:
  1646. X                goto RETURN;
  1647. X        }
  1648. X    }
  1649. X
  1650. XRETURN:
  1651. X    enddvent();
  1652. X#ifdef LOG_HDBDIAL
  1653. X    sprintf(s128,"CHOOSEANY lerr=%d chose %s",
  1654. X        lerr,(tdve) ? tdve->line : "<none>");
  1655. X    ecu_log_event(getpid(),s128);
  1656. X#endif
  1657. X    return(tdve);
  1658. X
  1659. X}    /* end of hdb_choose_Any */
  1660. X
  1661. X/*+-------------------------------------------------------------------------
  1662. X    hdb_choose_Device(type,baud) - need line with 'type' and 'baud'
  1663. X
  1664. Xreturn DVE pointer if line chosen, 0 if failed to find a line
  1665. XPriority is given to retaining the current line
  1666. X--------------------------------------------------------------------------*/
  1667. XDVE *
  1668. Xhdb_choose_Device(type,baud)
  1669. Xchar *type;
  1670. Xuint baud;
  1671. X{
  1672. X    DVE *tdve = (DVE *)0;
  1673. X    char s32[32];
  1674. X    int itmp = 0;
  1675. X    int lerr = 0;
  1676. X    int utmpst = 0;
  1677. X    int done;
  1678. X
  1679. X#ifdef CHOOSE_DEBUG
  1680. X    char s128[128];
  1681. X    sprintf(s128,"hdb_choose_Device type='%s' baud=%u curr line='%s'",
  1682. X        type,baud,shm->Lline);
  1683. X    ecu_log_event(getpid(),s128);
  1684. X#endif
  1685. X
  1686. X    /*
  1687. X     * check current line
  1688. X     */
  1689. X    if(shm->Lline[0])
  1690. X    {
  1691. X        while(tdve = getdvline(shm->Lline + 5))
  1692. X        {
  1693. X            if(dvtype_match(type,tdve->type) &&
  1694. X                (tdve->low_baud <= baud) && (baud <= tdve->high_baud))
  1695. X            {
  1696. X                break;
  1697. X            }
  1698. X        }
  1699. X        enddvent();
  1700. X
  1701. X        if(tdve)
  1702. X        {
  1703. X            switch(utmpst = utmp_status(shm->Lline))
  1704. X            {
  1705. X                case US_WEGOTIT:
  1706. X                    goto RETURN;
  1707. X
  1708. X                case US_NOTFOUND:    /* not in utmp, or getty dead */
  1709. X#if 0
  1710. X                    if(access(shm->Lline,6))
  1711. X                        break;
  1712. X#endif
  1713. X                    if((lerr = line_lock_status(shm->Lline)) &&
  1714. X                        (lerr != LINST_WEGOTIT))
  1715. X                    {
  1716. X                        break;
  1717. X                    }
  1718. X                    goto RETURN;
  1719. X
  1720. X                case US_LOGIN:        /* enabled for login, idle */
  1721. X                    goto RETURN;
  1722. X            }
  1723. X        }
  1724. X    }
  1725. X
  1726. X    /*
  1727. X     * we've got to pick a new line
  1728. X     */
  1729. X
  1730. X#ifdef CHOOSE_DEBUG
  1731. X    sprintf(s128,"must pick new line utmpst=%u lerr=%u",utmpst,lerr);
  1732. X    ecu_log_event(getpid(),s128);
  1733. X#endif
  1734. X
  1735. X    done = 0;
  1736. X    lerr = 0;
  1737. X    while(!done)
  1738. X    {
  1739. X        /*
  1740. X         * get Devices entry matching type
  1741. X         */
  1742. X        if(!(tdve = getdvtype(type)))
  1743. X        {
  1744. X#ifdef CHOOSE_DEBUG
  1745. X            sprintf(s128,"no line matches type '%s'",type);
  1746. X            ecu_log_event(getpid(),s128);
  1747. X#endif
  1748. X            break;
  1749. X        }
  1750. X
  1751. X        /*
  1752. X         * does baud rate match?
  1753. X         */
  1754. X        if((tdve->low_baud > baud) || (baud > tdve->high_baud))
  1755. X            continue;
  1756. X
  1757. X        sprintf(s32,"/dev/%s",tdve->line);
  1758. X        itmp = utmp_status(s32);
  1759. X#ifdef CHOOSE_DEBUG
  1760. X        sprintf(s128,"%s: utmp_status = %d  lock status=%d",s32,itmp,
  1761. X                line_lock_status(s32));
  1762. X        ecu_log_event(getpid(),s128);
  1763. X#endif
  1764. X        switch(itmp)
  1765. X        {
  1766. X            case US_NOTFOUND:    /* not in utmp, or getty dead */
  1767. X#if 0
  1768. X                if(access(s32,6))    /* ecuungetty won't be able to help us */
  1769. X                    break;
  1770. X#endif
  1771. X                if(!(itmp = line_lock_status(s32)) || (itmp == LINST_WEGOTIT))
  1772. X                    done = 1;
  1773. X                break;
  1774. X
  1775. X            case US_WEGOTIT:    /* we own the line */
  1776. X                /* this would be a curious case to succeed */
  1777. X                done = 1;
  1778. X                break;
  1779. X
  1780. X            case US_LOGIN:        /* enabled for login, idle */
  1781. X                done = 1;
  1782. X                break;
  1783. X
  1784. X            default:
  1785. X                break;
  1786. X        }
  1787. X    }
  1788. X
  1789. XRETURN:
  1790. X    enddvent();
  1791. X    return(tdve);
  1792. X
  1793. X}    /* end of hdb_choose_Device */
  1794. X
  1795. X/*+-------------------------------------------------------------------------
  1796. X    hdb_dial_error(errcode) - dialer program error code to text
  1797. X
  1798. Xalso sets iv[0] to dial command status
  1799. X--------------------------------------------------------------------------*/
  1800. Xchar *
  1801. Xhdb_dial_error_text(errcode)
  1802. Xint errcode;
  1803. X{
  1804. X    static char errant[64];
  1805. X
  1806. X    iv[0] = 1;
  1807. X    switch(errcode &= 0x7F)
  1808. X    {
  1809. X        case RCE_INUSE:
  1810. X            return("!Line in use");
  1811. X        case RCE_SIG:
  1812. X            iv[0] = 2;
  1813. X            return("!Interrupted");
  1814. X        case RCE_ARGS:
  1815. X            return("!Invalid arguments");
  1816. X        case RCE_PHNO:
  1817. X            return("!Invalid phone number");
  1818. X        case RCE_SPEED:
  1819. X            return("!Bad baud rate");
  1820. X        case RCE_OPEN:
  1821. X            return("!Line open error");
  1822. X        case RCE_IOCTL:
  1823. X            return("!Ioctl error");
  1824. X        case RCE_TIMOUT:
  1825. X            iv[0] = 3;
  1826. X            return("!Modem Error");
  1827. X        case RCE_NOTONE:
  1828. X            return("NO DIAL TONE");
  1829. X        case RCE_BUSY:
  1830. X            return("BUSY");
  1831. X        case RCE_NOCARR:
  1832. X            return("NO CARRIER");
  1833. X        case RCE_ANSWER:
  1834. X            return("NO ANSWER");
  1835. X        default:
  1836. X        case RCE_NULL:
  1837. X            sprintf(errant,"unknown dialer error code %d",errcode);
  1838. X            return(errant);
  1839. X    }
  1840. X    /*NOTREACHED*/
  1841. X}    /* end of hdb_dial_error */
  1842. X
  1843. X/*+-------------------------------------------------------------------------
  1844. X    hdb_dial(presult) - dial with uucp dialer if we can
  1845. X
  1846. Xreturn 0 if connected
  1847. X       1 if dial failed
  1848. X       2 if interrupted
  1849. X       3 if modem error
  1850. X       4 if use ecu DCE dialer
  1851. X--------------------------------------------------------------------------*/
  1852. Xint
  1853. Xhdb_dial(presult)
  1854. Xchar **presult;
  1855. X{
  1856. X    int itmp;
  1857. X    PID_T dial_pid;
  1858. X    int wait_status;
  1859. X    int old_ttymode = get_ttymode();
  1860. X    SIGTYPE (*original_sighdlr)();
  1861. X    DVE *tdve;
  1862. X    struct dlent *tdle = (struct dlent *)0;
  1863. X    char baudstr[16];
  1864. X    char dbgstr[16];
  1865. X    char dial_log[100];
  1866. X    char *stripped_num;
  1867. X    char *sptr;
  1868. X    char *dptr;
  1869. X    static char stat_s64[64];
  1870. X    ulong colors_at_entry = colors_current;
  1871. X    extern char *make_char_graphic();
  1872. X    char token[128];        /* translated dialer token */
  1873. X    FILE *fp;
  1874. X    char credit_file[128];
  1875. X    char *error_name = "";
  1876. X    int error_baud = 0;
  1877. X
  1878. X    if(sigint)    /* don't even start if console interrupt posted */
  1879. X    {
  1880. X        sigint = 0;
  1881. X        return(2);
  1882. X    }
  1883. X
  1884. X    if(!there_is_hdb_on_this_machine)
  1885. X        return(4);
  1886. X
  1887. X#if defined(CHOOSE_DEBUG)
  1888. X    sprintf(dial_log,"HDB_DIAL Lline=%s Lbaud=%d",
  1889. X        shm->Lline,shm->Lbaud);
  1890. X    ecu_log_event(getpid(),dial_log);
  1891. X#endif
  1892. X
  1893. X    /*
  1894. X     * get a Devices entry appropriate for dialing on the line;
  1895. X     */
  1896. X    enddvent();
  1897. X    while(tdve = getdvline(shm->Lline + 5))
  1898. X    {
  1899. X        if((tdve->low_baud <= shm->Lbaud) &&
  1900. X            (shm->Lbaud <= tdve->high_baud)) 
  1901. X        {
  1902. X            break;
  1903. X        }
  1904. X    }
  1905. X    error_name = shm->Lline + 5;
  1906. X    error_baud = shm->Lbaud;
  1907. X    enddvent();
  1908. X
  1909. X    if(!tdve)
  1910. X    {
  1911. X        pprintf("no Devices entry for %s at %u baud ... trying ecu dialer\n",
  1912. X            error_name,error_baud);
  1913. X        return(4);
  1914. X    }
  1915. X
  1916. X    dial_log[0] = 0;
  1917. X    if(*tdve->dialprog != '/')
  1918. X    {
  1919. X        tdle = getdlentname(tdve->dialprog);
  1920. X        enddlent();
  1921. X        if(!tdle)
  1922. X        {
  1923. X            sprintf(dial_log,
  1924. X                "UUCPDIAL Devices entry %s: '%s' not found in Dialers",
  1925. X                shm->Lline + 5,tdve->dialprog);
  1926. X        }
  1927. X    }
  1928. X    else if(access(tdve->dialprog,1))
  1929. X    {
  1930. X        sprintf(dial_log,"UUCPDIAL Devices entry %s: (%s) %s",
  1931. X            shm->Lline + 5,tdve->dialprog,errno_text(errno));
  1932. X    }
  1933. X
  1934. X    if(dial_log[0])
  1935. X    {
  1936. X#if defined(LOG_HDBDIAL)
  1937. X        ecu_log_event(getpid(),dial_log);
  1938. X#endif
  1939. X        pputs(dial_log + 9);
  1940. X        pputs("\n");
  1941. X        return(4);
  1942. X    }
  1943. X
  1944. X    stripped_num = strip_phone_num(shm->Ltelno);
  1945. X
  1946. X    /*
  1947. X     * if trailing '$', read and append ~/.ecu/.credit
  1948. X     */
  1949. X    dptr = stripped_num;
  1950. X    if(*(dptr - 1) == '$')
  1951. X    {
  1952. X        *--dptr = 0;
  1953. X        get_home_dir(credit_file);
  1954. X        strcat(credit_file,"/.ecu/.credit");
  1955. X        chmod(credit_file,0400);    /* let's keep this one quiet */
  1956. X        if(fp = fopen(credit_file,"r"))
  1957. X        {
  1958. X            fgets(dptr,30,fp);
  1959. X            fclose(fp);
  1960. X        }
  1961. X        if(!fp || !(*dptr))
  1962. X        {
  1963. X            strcpy(sv[0]->pb,"!CREDIT CARD ERROR");
  1964. X            sv[0]->cb = strlen(sv[0]->pb);
  1965. X            pputs("\ncredit card error\n");
  1966. X            iv[0] = 1;
  1967. X            return(1);
  1968. X        }
  1969. X        if(*(dptr + strlen(dptr) - 1) == 0x0A)
  1970. X            *(dptr + strlen(dptr) - 1) = 0; /* kill NL */
  1971. X    }
  1972. X
  1973. X  /* Translate Token now (thanks to ache@hq.demos.su) */
  1974. X
  1975. X    if (tdve->token == (char *)0 || !tdve->token[0])
  1976. X        strcpy(token, stripped_num);
  1977. X    else {
  1978. X        dptr = token;
  1979. X        for (sptr = tdve->token; *sptr; sptr++)
  1980. X            if (*sptr != '\\')
  1981. X                *dptr++ = *sptr;
  1982. X            else {
  1983. X                char *s, *t;
  1984. X
  1985. X                switch (*(sptr + 1)) {
  1986. X
  1987. X                /* Direct */
  1988. X                case 'D':
  1989. X                    sptr++;
  1990. X                    s = stripped_num;
  1991. X                    while (*s)
  1992. X                        *dptr++ = *s++;
  1993. X                    break;
  1994. X
  1995. X                /* Dialcodes Translate */
  1996. X                case 'T':
  1997. X                    sptr++;
  1998. X                    s = stripped_num;
  1999. X                    t = dialcodes_translate(&s);
  2000. X                    while(*t)
  2001. X                        *dptr++ = *t++;
  2002. X                    while (*s)
  2003. X                        *dptr++ = *s++;
  2004. X                    break;
  2005. X
  2006. X                default:
  2007. X                    *dptr++ = '\\';
  2008. X                    break;
  2009. X                }
  2010. X            }
  2011. X        *dptr = 0;
  2012. X    }
  2013. X
  2014. X    pprintf("Type %s to abort ... ",
  2015. X        (kbdintr == 0x7F) ? "DEL" : make_char_graphic(kbdintr,0));
  2016. X    setcolor(colors_normal);
  2017. X
  2018. X    if(Ldial_debug_level)
  2019. X    {
  2020. X        ttymode(0);
  2021. X        pputs("\n");
  2022. X    }
  2023. X    else
  2024. X        ttymode(2);
  2025. X
  2026. X    if(!tdle)
  2027. X    {
  2028. X        if(access(tdve->dialprog,1))
  2029. X        {
  2030. X            pperror(tdve->dialprog);
  2031. X            pputs("trying ecu dialer\n");
  2032. X            return(4);
  2033. X        }
  2034. X        sprintf(baudstr,"%u",shm->Lbaud);
  2035. X        sprintf(dbgstr,"-x%d",Ldial_debug_level);
  2036. X        original_sighdlr = signal(SIGCLD,SIG_DFL);
  2037. X        if((dial_pid = smart_fork()) == 0)
  2038. X        {
  2039. X            signal(SIGINT,SIG_DFL);
  2040. X            execl(tdve->dialprog,
  2041. X#if defined(WHT) || defined(ECUdial)
  2042. X                "ECUdial",        /* tell dialer ECU is calling */
  2043. X#else
  2044. X                tdve->dialprog,
  2045. X#endif
  2046. X                dbgstr, shm->Lline,token,baudstr,(char *)0);
  2047. X            _exit(0xFF);    /* did not execute */
  2048. X        }
  2049. X
  2050. X        wait_status = (RC_FAIL | RCE_SIG) << 8;
  2051. X        while(((itmp = wait(&wait_status)) != dial_pid) && (itmp != -1))
  2052. X            ;
  2053. X        signal(SIGCLD,original_sighdlr);
  2054. X        ttymode(old_ttymode);
  2055. X        ttyflush(0);
  2056. X
  2057. X        if(sigint)    /* keyboard interrupt? */
  2058. X        {
  2059. X            kill(dial_pid,9);    /* kill dialer */
  2060. X            lflash_dtr();        /* drop line */
  2061. X            sigint = 0;            /* reset SIGINT indication */
  2062. X        }
  2063. X        lreset_ksr(); /* uucp dialers are nice guys, but lets use our termio */
  2064. X
  2065. X#if defined(LOG_HDBDIAL)
  2066. X        if(wait_status)
  2067. X        {
  2068. X            sprintf(dial_log,"UUCPDIAL %s %s exit status0x%04x",
  2069. X                tdve->dialprog,token,wait_status & 0xFFFF);
  2070. X            ecu_log_event(getpid(),dial_log);
  2071. X        }
  2072. X#endif
  2073. X
  2074. X        /*
  2075. X         * if system reports interrupt, fake dial-reported status
  2076. X         */
  2077. X        if(wait_status & 0xFF)
  2078. X            wait_status = (RC_FAIL | RCE_SIG) << 8;
  2079. X
  2080. X        if((wait_status & 0xFF00) == 0xFF00)
  2081. X        {
  2082. X            pprintf("%s failed  ... trying ecu dialer\n",tdve->dialprog);
  2083. X            return(4);
  2084. X        }
  2085. X
  2086. X        wait_status = (wait_status >> 8) & 0xFF;
  2087. X
  2088. X        if(!(wait_status & ~RC_BAUD))
  2089. X        {
  2090. X            char *cptr;
  2091. X
  2092. X            wait_status &= RC_BAUD;
  2093. X            switch (wait_status) 
  2094. X            {
  2095. X            case 0:         cptr = baudstr; break;  /* SAME */
  2096. X            case B50:       cptr = "50"; break;
  2097. X            case B75:       cptr = "75"; break;
  2098. X            case B110:      cptr = "110"; break;
  2099. X            case B134:      cptr = "134.5"; break;
  2100. X            case B150:      cptr = "150"; break;
  2101. X            case B200:      cptr = "200"; break;
  2102. X            case B300:      cptr = "300"; break;
  2103. X            case B600:      cptr = "600"; break;
  2104. X            case B1200:     cptr = "1200"; break;
  2105. X            case B1800:     cptr = "1800"; break;
  2106. X            case B2400:     cptr = "2400"; break;
  2107. X            case B4800:     cptr = "4800"; break;
  2108. X            case B9600:     cptr = "9600"; break;
  2109. X#if defined(B19200)
  2110. X            case B19200:    cptr = "19200"; break;
  2111. X#endif
  2112. X#if defined(B38400)
  2113. X            case B38400:    cptr = "38400"; break;
  2114. X#endif
  2115. X            default:
  2116. X                switch (wait_status) {
  2117. X                case EXTA:      cptr = "EXTA"; break;
  2118. X                case EXTB:      cptr = "EXTB"; break;
  2119. X                default:        cptr = "????"; break;
  2120. X                }
  2121. X            }
  2122. X
  2123. X            sprintf(stat_s64,"CONNECT %s",cptr);
  2124. X            *presult = stat_s64;    /* DCE_dial will report result code */
  2125. X            return(0);
  2126. X        }
  2127. X
  2128. X        *presult = hdb_dial_error_text(wait_status);
  2129. X        setcolor(colors_error);
  2130. X        pputs(*presult);
  2131. X        setcolor(colors_at_entry);
  2132. X        pputc('\n');
  2133. X        lflash_dtr();
  2134. X    }
  2135. X    else
  2136. X    {
  2137. X        pprintf("using Dialers entry '%s'\n",tdle->name);
  2138. X        expresp_verbosity = (proc_level & proctrace) ? proctrace : 0;
  2139. X        if(execute_expresp(tdle->script))
  2140. X        {
  2141. X            *presult = "DIALER SCRIPT FAILED";
  2142. X            setcolor(colors_error);
  2143. X            pputs(*presult);
  2144. X            setcolor(colors_at_entry);
  2145. X            pputc('\n');
  2146. X            iv[0] = 1;
  2147. X        }
  2148. X        else
  2149. X        {
  2150. X            extern char last_Speed_result[];
  2151. X            if(last_Speed_result[0])
  2152. X                *presult = last_Speed_result;
  2153. X            else
  2154. X            {
  2155. X                sprintf(stat_s64,"CONNECT %u",shm->Lbaud);
  2156. X                *presult = stat_s64;    /* DCE_dial will report result code */
  2157. X            }
  2158. X            setcolor(colors_at_entry);
  2159. X            iv[0] = 0;
  2160. X        }
  2161. X    }
  2162. X
  2163. X    return((int)iv[0]);
  2164. X
  2165. X}    /* end of hdb_dial */
  2166. X
  2167. X/*+-------------------------------------------------------------------------
  2168. X    hdb_init() - initialize HoneyDanBerInterface
  2169. X--------------------------------------------------------------------------*/
  2170. Xvoid
  2171. Xhdb_init()
  2172. X{
  2173. X    char *hdblibdir = HDBLIBDIR;        /* system independent location */
  2174. X    int itmp;
  2175. X    int buflen = strlen(hdblibdir) + 64;
  2176. X    char *emsg = "hdb_init memory allocation failed!\n";
  2177. X
  2178. X    if(!(Devices_file = malloc(buflen)))
  2179. X    {
  2180. X        pputs(emsg);
  2181. X        termecu(TERMECU_MALLOC);
  2182. X    }
  2183. X    strcpy(Devices_file,hdblibdir);
  2184. X    strcat(Devices_file,"/Devices");
  2185. X
  2186. X    if(!(Dialers_file = malloc(buflen)))
  2187. X    {
  2188. X        pputs(emsg);
  2189. X        termecu(TERMECU_MALLOC);
  2190. X    }
  2191. X    for(itmp = 0; itmp < UNGETTY_LIST_MAX; itmp++)
  2192. X    {
  2193. X        if(!(ungetty_list[itmp] = malloc(64)))
  2194. X        {
  2195. X            pputs(emsg);
  2196. X            termecu(TERMECU_MALLOC);
  2197. X        }
  2198. X    }
  2199. X    strcpy(Dialers_file,hdblibdir);
  2200. X    strcat(Dialers_file,"/Dialers");
  2201. X
  2202. X    if(!(Dialcodes_file = malloc(buflen)))
  2203. X    {
  2204. X        pputs(emsg);
  2205. X        termecu(TERMECU_MALLOC);
  2206. X    }
  2207. X    strcpy(Dialcodes_file,hdblibdir);
  2208. X    strcat(Dialcodes_file,"/Dialcodes");
  2209. X
  2210. X    there_is_hdb_on_this_machine = !access(Devices_file,4);
  2211. X
  2212. X}    /* end of hdb_init */
  2213. X
  2214. X/*+-------------------------------------------------------------------------
  2215. Xdialcodes_translate(phone)  -  translate first part of phone using Dialcodes
  2216. X--------------------------------------------------------------------------*/
  2217. Xchar *
  2218. Xdialcodes_translate(phone)
  2219. Xchar **phone;
  2220. X{
  2221. X    FILE *f;
  2222. X    int itmp;
  2223. X#define MAX_DLC_TOKENS 2
  2224. X    char *tokens[MAX_DLC_TOKENS];
  2225. X    static char dlstr[128];
  2226. X
  2227. X    if(!(f = fopen(Dialcodes_file, "r")))
  2228. X        return("");
  2229. X
  2230. X    while(fgets(dlstr,sizeof(dlstr),f))
  2231. X    {
  2232. X        if(((itmp = strlen(dlstr)) > 0) && (dlstr[itmp - 1] == '\n'))
  2233. X            dlstr[--itmp] = 0;
  2234. X        if((dlstr[0] == '#') || (dlstr[0] == ' ') || (!itmp))
  2235. X            continue;
  2236. X        if(tokens[0] = arg_token(dlstr," \t\r\n"))
  2237. X        {
  2238. X            if (!(tokens[1] = arg_token((char *)0," \t\r\n")))
  2239. X                tokens[1] = "";
  2240. X            itmp = strlen(tokens[0]);
  2241. X            if (strncmp(*phone, tokens[0], itmp))
  2242. X                continue;
  2243. X            fclose(f);
  2244. X            *phone += itmp;
  2245. X            fclose(f);
  2246. X            return(tokens[1]);
  2247. X        }
  2248. X        break;
  2249. X    }
  2250. X
  2251. X    fclose(f);
  2252. X    return("");
  2253. X}
  2254. X
  2255. X/*+-------------------------------------------------------------------------
  2256. X      strip_phone_num(sptr) - remove junk characters from phone
  2257. X--------------------------------------------------------------------------*/
  2258. Xchar *
  2259. Xstrip_phone_num(sptr)
  2260. Xchar *sptr;
  2261. X{
  2262. X    static char stripped_num[64];
  2263. X    char *dptr;
  2264. X
  2265. X    dptr = stripped_num;
  2266. X    while(*sptr)
  2267. X    {
  2268. X        if((*sptr == '(') || (*sptr == ')')
  2269. X#if defined(WHT) || defined(STRIP_TELNO_HYPHENS)
  2270. X            || (*sptr == '-')    /* some want '-' for pauses; I use ',' */
  2271. X#endif
  2272. X            )
  2273. X        {
  2274. X            sptr++;
  2275. X            continue;
  2276. X        }
  2277. X        *dptr++ = *sptr++;
  2278. X    }
  2279. X    *dptr = 0;
  2280. X
  2281. X    return(stripped_num);
  2282. X}
  2283. X
  2284. X/* vi: set tabstop=4 shiftwidth=4: */
  2285. X/* end of hdbintf.c */
  2286. SHAR_EOF
  2287. chmod 0644 hdbintf.c ||
  2288. echo 'restore of hdbintf.c failed'
  2289. Wc_c="`wc -c < 'hdbintf.c'`"
  2290. test 40881 -eq "$Wc_c" ||
  2291.     echo 'hdbintf.c: original size 40881, current size' "$Wc_c"
  2292. rm -f _shar_wnt_.tmp
  2293. fi
  2294. # ============= kbdtest.c ==============
  2295. if test -f 'kbdtest.c' -a X"$1" != X"-c"; then
  2296.     echo 'x - skipping kbdtest.c (File already exists)'
  2297.     rm -f _shar_wnt_.tmp
  2298. else
  2299. > _shar_wnt_.tmp
  2300. echo 'x - extracting kbdtest.c (Text)'
  2301. sed 's/^X//' << 'SHAR_EOF' > 'kbdtest.c' &&
  2302. X/*+-----------------------------------------------------------------------
  2303. X    kbdtest.c -- hack to test keyboard function key sequences
  2304. X    wht@n4hgf.Mt-Park.GA.US
  2305. X
  2306. X  compile with     cc -o kbdtest kbdtest.c
  2307. X  or just          cc kbdtest.c;a.out
  2308. X------------------------------------------------------------------------*/
  2309. X/*+:EDITS:*/
  2310. X/*:09-10-1992-13:59-wht@n4hgf-ECU release 3.20 */
  2311. X/*:08-22-1992-15:39-wht@n4hgf-ECU release 3.20 BETA */
  2312. X/*:07-25-1991-12:58-wht@n4hgf-ECU release 3.10 */
  2313. X/*:12-21-1990-23:47-wht@n4hgf-liven up for release with ECU 3 */
  2314. X/*:04-07-1990-01:36-wht@tridom-bring out of the daaaaark ages a bit */
  2315. X/*:04-18-1988-13:44-wht-first edits -- oollldd program */
  2316. X
  2317. X#include <stdio.h>
  2318. X#include <signal.h>
  2319. X#include <ctype.h>
  2320. X#include <fcntl.h>
  2321. X#include <termio.h>
  2322. X#include "ecu_types.h"
  2323. X#include <sys/errno.h>
  2324. X#include "ecu_stat.h"
  2325. X#include <string.h>
  2326. X
  2327. X#define TTYIN   0
  2328. X#define TTYOUT  1
  2329. X#define TTYERR  2
  2330. X
  2331. Xstruct termio tv0;        /* for saving, changing TTY atributes */
  2332. Xstruct termio tv;        /* for saving, changing TTY atributes */
  2333. X
  2334. X/*+-----------------------------------------------------------------------
  2335. X    ttymode(arg) -- control user console (kbd/screen)
  2336. X
  2337. X  Where arg ==
  2338. X    0 restore attributes saved at start of execution
  2339. X    1 raw mode 
  2340. X
  2341. X------------------------------------------------------------------------*/
  2342. Xvoid ttymode(arg)
  2343. X{
  2344. X    char *mode_type;
  2345. X
  2346. X    switch(arg)
  2347. X    {
  2348. X        case 0:    
  2349. X            mode_type = "console to cooked mode\r\n";
  2350. X            break;
  2351. X        default: 
  2352. X            mode_type = "console to raw mode\r\n";
  2353. X            break;
  2354. X    }
  2355. X    (void)fprintf(stderr,mode_type);
  2356. X
  2357. X    if(arg)
  2358. X    {
  2359. X        (void)ioctl(TTYIN,TCGETA,&tv);
  2360. X        Ltermio.c_cflag &= ~(CS8 | PARENB | PARODD);
  2361. X        Ltermio.c_cflag |= CS8;
  2362. X        tv.c_iflag &= ~(INLCR | ICRNL | IGNCR | IXOFF | IUCLC | ISTRIP);
  2363. X        tv.c_oflag |= OPOST;
  2364. X        tv.c_oflag &= ~(OLCUC | ONLCR | OCRNL | ONOCR | ONLRET);
  2365. X        tv.c_lflag &= ~(ICANON | ISIG | ECHO);
  2366. X        tv.c_cc[VEOF] = '\01';
  2367. X        tv.c_cc[VEOL] = '\0';
  2368. X        tv.c_cc[VMIN] = 1;
  2369. X        tv.c_cc[VTIME] = 1;
  2370. X        (void)ioctl(TTYIN,TCSETAW,&tv);
  2371. X    }
  2372. X    else
  2373. X        (void)ioctl(TTYIN,TCSETAW,&tv0);
  2374. X}
  2375. X
  2376. X
  2377. X/*+-----------------------------------------------------------------------
  2378. X    main()
  2379. X------------------------------------------------------------------------*/
  2380. Xmain(argc,argv)
  2381. Xint argc;
  2382. Xchar **argv;
  2383. X{
  2384. Xunsigned char inchar;
  2385. X
  2386. X    setbuf(stdout,NULL);
  2387. X    setbuf(stderr,NULL);
  2388. X
  2389. X    ioctl(TTYIN,TCGETA,&tv0);        /* get original status */
  2390. X    ttymode(2);
  2391. X
  2392. X    fprintf(stderr,"press ^D (0x04) to terminate program\r\n");
  2393. X
  2394. X    while(read(TTYIN,&inchar,1) == 1)
  2395. X    {
  2396. X        printf("%02x %c\r\n",inchar,
  2397. X            ((inchar >= 0x20) && (inchar < 0x7F)) ? inchar : '.');
  2398. X        if((inchar & 0x7F) == 4)
  2399. X        {
  2400. X            ttymode(0);
  2401. X            exit(0);
  2402. X        }
  2403. X    }
  2404. X    ttymode(0);
  2405. X    exit(1);
  2406. X
  2407. X}
  2408. X
  2409. X/* vi: set tabstop=4 shiftwidth=4: */
  2410. X/* end of kbdtest.c */
  2411. SHAR_EOF
  2412. chmod 0644 kbdtest.c ||
  2413. echo 'restore of kbdtest.c failed'
  2414. Wc_c="`wc -c < 'kbdtest.c'`"
  2415. test 2711 -eq "$Wc_c" ||
  2416.     echo 'kbdtest.c: original size 2711, current size' "$Wc_c"
  2417. rm -f _shar_wnt_.tmp
  2418. fi
  2419. # ============= kbdtest3.c ==============
  2420. if test -f 'kbdtest3.c' -a X"$1" != X"-c"; then
  2421.     echo 'x - skipping kbdtest3.c (File already exists)'
  2422.     rm -f _shar_wnt_.tmp
  2423. else
  2424. > _shar_wnt_.tmp
  2425. echo 'x - extracting kbdtest3.c (Text)'
  2426. sed 's/^X//' << 'SHAR_EOF' > 'kbdtest3.c' &&
  2427. X/* CHK=0x2F4F */
  2428. Xchar *revision = "3.21";
  2429. SHAR_EOF
  2430. true || echo 'restore of kbdtest3.c failed'
  2431. fi
  2432. echo 'End of ecu320 part 17'
  2433. echo 'File kbdtest3.c is continued in part 18'
  2434. echo 18 > _shar_seq_.tmp
  2435. exit 0
  2436.  
  2437. exit 0 # Just in case...
  2438.