home *** CD-ROM | disk | FTP | other *** search
/ Usenet 1994 October / usenetsourcesnewsgroupsinfomagicoctober1994disk2.iso / misc / volume42 / ecu / part10 < prev    next >
Encoding:
Internet Message Format  |  1994-05-23  |  64.8 KB

  1. From: wht@n4hgf.atl.ga.us (Warren Tucker)
  2. Newsgroups: comp.sources.misc
  3. Subject: v42i108:  ecu - ECU Asynchronous Communications v3.30, Part10/37
  4. Date: 23 May 1994 14:22:49 -0500
  5. Organization: Sterling Software
  6. Sender: kent@sparky.sterling.com
  7. Approved: kent@sparky.sterling.com
  8. Message-ID: <2rqvq9$dm0@sparky.sterling.com>
  9. X-Md4-Signature: 445a21b90804e7d87692032459fd6faf
  10.  
  11. Submitted-by: wht@n4hgf.atl.ga.us (Warren Tucker)
  12. Posting-number: Volume 42, Issue 108
  13. Archive-name: ecu/part10
  14. Environment: SCO,SCOXENIX,MOTOROLA,HP-UX,LINUX,NetBSD,SUNOS,SYSVR4,SOLARIS2
  15. Supersedes: ecu: Volume 32, Issue 36-75
  16.  
  17. #! /bin/sh
  18. # This is a shell archive.  Remove anything before this line, then feed it
  19. # into a shell via "sh file" or similar.  To overwrite existing files,
  20. # type "sh file -c".
  21. # Contents:  ecu330/doc/_features.txt ecu330/proc.c
  22. # Wrapped by kent@sparky on Mon May 23 13:40:50 1994
  23. PATH=/bin:/usr/bin:/usr/ucb:/usr/local/bin:/usr/lbin:$PATH ; export PATH
  24. echo If this archive is complete, you will see the following message:
  25. echo '          "shar: End of archive 10 (of 37)."'
  26. if test -f 'ecu330/doc/_features.txt' -a "${1}" != "-c" ; then 
  27.   echo shar: Will not clobber existing file \"'ecu330/doc/_features.txt'\"
  28. else
  29.   echo shar: Extracting \"'ecu330/doc/_features.txt'\" \(41249 characters\)
  30.   sed "s/^X//" >'ecu330/doc/_features.txt' <<'END_OF_FILE'
  31. X.*s 1 "Features"
  32. X.*s 2 "Supported Terminals"
  33. X
  34. XECU supports many terminals with geometries between 20 and 43
  35. Xlines, inclusive.  The column width must be 80.
  36. XThe termcap entry for a console (user tty rather than the line)
  37. XMUST contain a valid entry for the database entries listed below.
  38. X
  39. XECU does not attempt to support terminal emulation in the classic
  40. Xsense of the word.  It presents to the remote host an "ANSI-like"
  41. Xterminal type as described earlier in the introduction and in 
  42. Xthe section titled "ANSI Filter."
  43. XHowever, it does support, with limitations, any LOCAL terminal
  44. X(console) for which a valid termcap description exists. You MAY
  45. Xbe able to use ECU with a remote terminal (calling into UNIX/XENIX
  46. Xover a network or modem), but you may get unfavorable results with
  47. Xfunction key usage if your modem is a "packetizing" type, such as
  48. Xa Telebit or if ethernet or other networking chops up your keystroke
  49. Xsequences.  ECU allows approximately 100 milliseconds after receiving
  50. Xan ASCII ESC character for later characters of a function key sequence
  51. Xto arrive.  If at least one character of the sequence has not been
  52. Xreceived in that time, ECU treats the key as an ESCape, not a function key.
  53. XThis typical problem of detecting ESC vs. function key is unfortunate, but
  54. Xwe must live with it until paradigms change (say, in about 2010?).
  55. X
  56. XThe termcap entry for a console
  57. XMUST contain a valid entry for the following database entries:
  58. X
  59. X.DS L
  60. Xcl      clear screen
  61. Xkl      cursor left
  62. Xkr      cursor right
  63. Xdc      delete character
  64. Xdl      delete line
  65. Xcd      clear to end of display
  66. Xce      clear to end of line
  67. Xic      insert character
  68. Xal      insert line ("add" a "line")
  69. Xcm      cursor motion
  70. Xso      stand out (terminal specific attention getter)
  71. Xse      stand end
  72. X.DE
  73. X
  74. XThe above sequences MUST be present, valid and reasonably
  75. Xefficient.  ECU does not use curses during it's primary mode of
  76. Xoperation (keyboard send-receive). Unlike curses, ECU makes no
  77. Xattempt to emulate missing terminal functionality.  Failure to
  78. Xprovide valid entries will result in strange behavior with no
  79. Xwarning.
  80. X
  81. XNote that the formal termcap description of "kl" and "kr" 
  82. Xstate these are sequences generated by the terminal
  83. X.B keyboard ,
  84. Xbut ECU expects that these sequences also cause the desired
  85. Xeffects when
  86. X.B sent
  87. Xto the
  88. X.B screen .
  89. X
  90. XAdditionally, the following, optional, sequences will be used if
  91. Xthey are detected.
  92. X
  93. X.DS L
  94. Xmb      bold on ("XENIX" extension)
  95. Xme      bold off ("XENIX" extension)
  96. Xus      underscrore on
  97. Xue      underscrore off
  98. Xvb      visual bell
  99. X.DE
  100. X
  101. XOn SCO, termcap terminal contrtol is used.  Other
  102. Xversions use terminfo.
  103. XA future SCO version of ECU may use terminfo instead of termcap.
  104. XProblems with terminfo prevent its use at the present time.
  105. XIn addition, early versions of XENIX do not support terminfo.
  106. X
  107. XOn SCO multiscreens, SCO "extensions" to "ANSI" are supported
  108. Xas described below in "Multiscreen Local Terminals."
  109. X
  110. X.*s 2 "Host Video Control Sequences"
  111. X
  112. X.*s 3 "All Local Consoles (Terminals)"
  113. X
  114. XThe following sequences are 
  115. Xproperly interpreted by ECU for all local terminal types
  116. X(multiscreen, rlogin/xterm pseudotty, serial).
  117. X
  118. X.DS L
  119. XSequence  | Description
  120. X----------+-------------------------------
  121. XESC 7     | VT-100 save cursor position
  122. XESC 8     | VT-100 restore cursor position
  123. XESC [ @   | ICH
  124. XESC [ A   | CUU
  125. XESC [ B   | CUD
  126. XESC [ C   | CUF
  127. XESC [ D   | CUB
  128. XESC [ E   | CNL       See ANSI X3.64,
  129. XESC [ F   | CPL       screen(HW) and/or
  130. XESC [ H   | CUP       MS-DOS Technical
  131. XESC [ J   | ED        Reference Manual
  132. XESC [ K   | EL
  133. XESC [ L   | IL
  134. XESC [ M   | DL
  135. XESC [ P   | DCH
  136. XESC [ S   | SU
  137. XESC [ T   | SD
  138. XESC [ X   | ECH
  139. XESC [ `   | HPA
  140. XESC [ a   | HPR
  141. XESC [ d   | VPA
  142. XESC [ e   | VPR
  143. XESC [ f   | HVP
  144. XESC [ ? m | SGR
  145. XESC [ n   | DSR
  146. XESC [ s   | save cursor MS-DOSism
  147. XESC [ u   | restore cursor MS-DOSism
  148. X.DE
  149. X.DS L
  150. XSGR Sequences for ALL TERMINALS
  151. XSequence  | Description   |  Maps to termcap
  152. X----------+---------------+-------------------------------
  153. XESC [ 0 m | normal        |  "se"+"me"+"ue"
  154. XESC [ 1 m | bold          |  "so"
  155. XESC [ 4 m | underscore    |  "us"
  156. XESC [ 5 m | blink         |  "mb" (XENIX extension)
  157. XESC [ 7 m | reverse video |  "so"
  158. X.DE
  159. X
  160. X.DS L
  161. XDSR Sequences for ALL TERMINALS
  162. XSequence  | Description   |  responds with
  163. X----------+---------------+-------------------------------
  164. XESC [ 0 n | ignored       | 
  165. XESC [ n   | see ESC[5n    |  ESC [ 0 n
  166. XESC [ 5 n | sanity test   |  ESC [ 0 n
  167. XESC [ 6 n | report cusror |  ESC [ r ; c R 
  168. X          | (CPR)         |      r is row 1-n
  169. X          |               |      c is column 1-n
  170. X.DE
  171. XThe latter two DSR sequences are compatible with X11's xterm.
  172. XThe latter makes ECU compatible with the xterm companion program ``resize''.
  173. XFor example, if ECU "sees" ESC [ 6 n, and the screen cursor is at the
  174. Xhome position, ECU responds with:
  175. X
  176. XESC [ 1 ; 1 R     ( hex 1B 5B 31 3B 31 52 )
  177. X
  178. X.*s 3 "Multiscreen Local Terminals"
  179. X
  180. XIn addition to the above, if you are operating from an SCO color
  181. Xmultiscreen, additional (SCO and MS-DOS/ANSI.SYS) sequences
  182. Xare supported (see screen(HW)):
  183. X
  184. X.DS L
  185. XAdditional Multiscreen SGR Sequences
  186. XSequence    | Description  (no termcap mapping)
  187. X------------+-----------------------------------------------
  188. XESC [ 8 m   | non-display
  189. XESC [ 1 0 m | select primary font
  190. XESC [ 1 1 m | select first alternate font (0x00-0x1F)
  191. XESC [ 1 2 m | select second alternate font (0x80-0xFF)
  192. XESC [ 3 0 m | black foreground
  193. XESC [ 3 1 m | red foreground
  194. XESC [ 3 2 m | green foreground
  195. XESC [ 3 3 m | brown foreground
  196. XESC [ 3 4 m | blue foreground
  197. XESC [ 3 5 m | magenta foreground
  198. XESC [ 3 6 m | cyan foreground
  199. XESC [ 3 7 m | white foreground
  200. XESC [ 3 8 m | enables underline option
  201. XESC [ 3 9 m | disables underline option
  202. XESC [ 4 0 m | black background
  203. XESC [ 4 1 m | red background
  204. XESC [ 4 2 m | green background
  205. XESC [ 4 3 m | brown background
  206. XESC [ 4 4 m | blue background
  207. XESC [ 4 5 m | magenta background
  208. XESC [ 4 6 m | cyan background
  209. XESC [ 4 7 m | white background
  210. X.DE
  211. X
  212. X.s 3 "MS-DOS 'SGR Gaggles'"
  213. X
  214. XECU also does it's best to interpret MS-DOS "SGR gaggles" such as
  215. X.DS I
  216. XESC [ 5 ; 3 4 ; 4 7 m
  217. X.DE
  218. Xwhich means "set the terminal to white background with
  219. Xblue blinking foreground."
  220. X
  221. X.*s 3 "Character Mapping"
  222. X
  223. XMost versions of ECU running on an AT style machine attempt to
  224. Xuse the ruling characters in the video display adapter's ROM
  225. Xper:
  226. X.DS L
  227. XMapped Characters (see pc_scr.h):
  228. XHex  | Description
  229. X-----+---------------------------
  230. X0xDA | top left single rule
  231. X0xBF | top right single rule
  232. X0xC0 | bottom left single rule
  233. X0xD9 | bottom right single rule
  234. X0xC3 | left hand T
  235. X0xB4 | right hand T
  236. X0xB3 | vertical rule
  237. X0xC4 | horizontal rule
  238. X.DE
  239. XOn non-AT machines (or in such environments as X11), the PC ROM
  240. Xsingle ruling characters from the following table are mapped
  241. Xafter the fashion of:
  242. X.DS L
  243. X       .-----+--------.
  244. X       |     |        |
  245. X       |     +--------+
  246. X       |     |        |
  247. X       +-----+        |
  248. X       |     |        |
  249. X       `-----+--------'
  250. X.DE
  251. X
  252. X(Due to laziness on the part of the author, double
  253. Xruling characters will appear as random druk, unless your terminal
  254. Xhas joined the Church of the True-Blue ROM.
  255. XOne day an X version of this program may appear and you can choose
  256. Xto no longer accomplish real work, but may spend your days editing
  257. X42Kb resource files which will give you TAC, Total Anal Control,
  258. Xover all this.)
  259. X
  260. X.*s 2 "Function Key Mapping (Recognition)"
  261. X
  262. X(This section reflects the changes in keyboard management made
  263. Xin version 3.20.)
  264. X
  265. XECU recognizes 23 function keys as having special significance
  266. Xto its operation.
  267. XThey are:
  268. X.DS I
  269. XName      Description 
  270. X--------  ------------
  271. XF1        F1         
  272. XF2        F2        
  273. XF3        F3          
  274. XF4        F4          
  275. XF5        F5          
  276. XF6        F6          
  277. XF7        F7          
  278. XF8        F8          
  279. XF9        F9          
  280. XF10       F10         
  281. XF11       F11         
  282. XF12       F12         
  283. XHome      Home        
  284. XEnd       End         
  285. XPgUp      Page up     
  286. XPgDn      Page down   
  287. XCUU       Up arrow    
  288. XCUD       Down arrow  
  289. XCUL       Left arrow  
  290. XCUR       Right arrow 
  291. XCU5       "Cursor 5"  
  292. XIns       Insert      
  293. XBkTab     Back Tab    
  294. X.DE
  295. X
  296. XECU matches a function key sequence
  297. Xto an internal function key representation
  298. Xby testing all keystroke sequences against an internal table loaded
  299. Xat the beginning of execution from the file ~/.ecu/funckeymap.
  300. XA default funckeymap file placed in the ECU library directory
  301. X(normally /usr/local/lib/ecu) by the software installation process.  
  302. XIf there is no funckeys in the user's home directory, the default
  303. Xfile is used.
  304. X
  305. XNOTE that supported terminals MUST employ function keys which generate
  306. Xsequences less than 32 characters in length.
  307. X
  308. XX11 xterms and X terminals usually require special attention
  309. Xwith VT100.Translations overrides.  Sometimes an xmodmap must also be
  310. Xemployed.  Experimentation is the best teacher, but the supplied
  311. Xfunckeymap file and various READMEs offer some hints.  In particular,
  312. XREADME.KEYBRD contains information that is kept current.
  313. X
  314. XSeveral predefined entries are supplied with the program distribution
  315. Xin models/funckeymap.
  316. XIf you have a terminal or console with a keyboard not already
  317. Xin this file, you must construct one using the terminal's reference
  318. Xmanual or by direct discovery (typing the key and empricially noting
  319. Xits generated sequence).
  320. XThe program kbdtest3 (the source is provided in the distribution) can
  321. Xassist you in building funckeymap entries.
  322. Xcertain keys are pressed.  kbdtest.c is a more primitive version of
  323. Xthe same program.
  324. X
  325. XNormally, the TERM environment variable is used to determine
  326. Xthe funckeymap entry to be used.  Sometimes, the TERM variable
  327. Xis not adequate for identifying your keyboard arrangement.  For
  328. Xinstance, suppose you use an xterm on the console at times and
  329. Xan X terminal at other times.  The choice of function keys
  330. Xand the character sequences they emit are not likely to match.
  331. XRather than make herculean efforts with xmodmap and translations,
  332. Xyou can define two different funckeymap entries, say "xterm-sco"
  333. Xand "xterm-ncd".
  334. XThe environment variable ECUFUNCKEY, if found, overrides the
  335. XTERM variable for funckeymap keyboard management only.  
  336. XTERM is always used for identifying the display.
  337. XThus, you can set TERM to "xterm" and ECUFUNCKEY to "xterm-sco"
  338. XOR "xterm-ncd".
  339. XAlso, the -F command line switch may be used (which overrides $ECUFUNCKEY).
  340. X
  341. XThe format of an file entry is shown below.
  342. XLines beginning with '#' are comments.
  343. X
  344. X.DS I
  345. X#+------------------------------
  346. X# SCO
  347. X#-------------------------------
  348. Xansi
  349. Xansi43
  350. Xsco
  351. X    F1:F1:          esc [ M 
  352. X    F2:F2:          esc [ N 
  353. X    F3:F3:          esc [ O 
  354. X    F4:F4:          esc [ P 
  355. X    F5:F5:          esc [ Q 
  356. X    F6:F6:          esc [ R 
  357. X    F7:F7:          esc [ S 
  358. X    F8:F8:          esc [ T 
  359. X    F9:F9:          esc [ U 
  360. X    F10:F10:        esc [ V 
  361. X    F11:F11:        esc [ W 
  362. X    F12:F12:        esc [ X 
  363. X    Home:Home:      esc [ H 
  364. X    End:End:        esc [ F 
  365. X    PgUp:PgUp:      esc [ I 
  366. X    PgDn:PgDn:      esc [ G 
  367. X    CUU:CUU:        esc [ A 
  368. X    CUL:CUL:        esc [ D 
  369. X    CU5:CU5:        esc [ E 
  370. X    CUR:CUR:        esc [ C 
  371. X    CUD:CUD:        esc [ B 
  372. X    Ins:Ins:        esc [ L
  373. X    BkTab:BackTab:  esc [ Z
  374. X.DE
  375. X
  376. XThe first line(s) in a terminal keyboard description begin in
  377. Xcolumn 1 and contain the terminal types (a la $TERM) for which
  378. Xthe keyboard description are valid.  The example entry contains
  379. Xseveral references to terminal types containing the substring
  380. X'ansi'.  These are included only as an example of one keyboard
  381. Xdescription servicing multiple terminal types.
  382. X
  383. XFollowing the "first lines" are key definition entries, each
  384. Xpreceded by at least one tab or space.  Each entry is composed of
  385. Xthree fields delimited by commas.  The first field of an entry is
  386. Xthe internal ECU function key name and must be chosen from the
  387. Xfollowing strings (with no regard to case): "F1", "F2", "F3",
  388. X"F4", "F5", "F6", "F7", "F8", "F9", "F10", "F11", "F12", "Home",
  389. X"End", "PgUp", "PgDn", "CUU" (cursor up), "CUL" (cursor left),
  390. X"CU5" (unshifted cursor pad 5), "CUR" (cursor right) and "CUD"
  391. X(cursor down). The
  392. Xsecond field contains the name of the key as it appears on the
  393. Xkeyboard (such as "F16" for End on the Wyse 60).  The
  394. Xthird field is a description of the character sequence generated
  395. Xby the keyboard when the chosen key is pressed; it is a
  396. Xstring of one or more tokens separated by spaces or tabs.
  397. X
  398. XIn addition, function key sequences may not 
  399. Xexceed 31 characters in length.
  400. X
  401. XPLEASE NOTE: ECU does not have a reasonable way for you to terminate it
  402. Xif there are no Home and End keys defined, so it refuses to proceed
  403. Xif no definitions are found.  Even so, if you have incorrect definitions,
  404. Xyou may not be able to get out of ECU without a kill -1 <pid> from
  405. Xanother terminal or hanging up your connection with UNIX/XENIX
  406. Xif using ECU from remote.
  407. X
  408. X.*s 2 "Function Key Actions"
  409. X
  410. XThis section deals with how ECU behaves
  411. Xonce a function key has been recognized as having been entered
  412. Xat the keyboard. 
  413. X
  414. X.*s 3 "Standard Function Keys"
  415. X
  416. XAll function keys with the exception of the 
  417. X.B Home ,
  418. X.B BkTab
  419. X(shift TAB),
  420. Xand keypad unshifted 5 key can be programmed to 
  421. Xeither
  422. X.DS L
  423. X    transmit preselected character sequences or
  424. X    execute a procedure with arguments.
  425. X.DE
  426. X
  427. XThe default values for these sequences is shown below.
  428. X
  429. X.DS L
  430. XIdentifier Description    Default Sequence
  431. X--------   ------------   ----------------
  432. XF1         F1                ESC [ M
  433. XF2         F2                ESC [ N
  434. XF3         F3                ESC [ O
  435. XF4         F4                ESC [ P
  436. XF5         F5                ESC [ Q
  437. XF6         F6                ESC [ R
  438. XF7         F7                ESC [ S
  439. XF8         F8                ESC [ T
  440. XF9         F9                ESC [ U
  441. XF10        F10               ESC [ V
  442. XF11        F11               ESC [ W
  443. XF12        F12               ESC [ X
  444. XHome       Home          <-- intercepted (not an input key)
  445. XEnd        End               ESC [ F
  446. XPgUp       Page up           ESC [ I
  447. XPgDn       Page down         ESC [ G
  448. XCUU        Up arrow          ESC [ A
  449. XCUD        Down arrow        ESC [ B
  450. XCUL        Left arrow        ESC [ D
  451. XCUR        Right arrow       ESC [ C
  452. XCU5        "Cursor 5"    <-- intercepted (not an input key)
  453. XIns        Insert            ESC [ L
  454. X.DE
  455. XThis results in the following interactive "fkey" command display:
  456. X.DS L
  457. X F1   SCO F1    F2   SCO F2    Home  ecu cmd       PgUp  SCO PgUp
  458. X F3   SCO F3    F4   SCO F4    End   SCO End       PgDn  SCO PgDn
  459. X F5   SCO F5    F6   SCO F6    Ins   local shell   CUR5  screen dump
  460. X F7   SCO F7    F8   SCO F8    BkTab redisplay  
  461. X F9   SCO F9    F10  SCO F10   CUR^  SCO CUU       CUR>  SCO CUR
  462. X F11  SCO F11   F12  SCO F12   CUR<  SCO CUL       CURv  SCO CUD
  463. X.DE
  464. X
  465. XYou may override the default setting by using the interactive or
  466. Xprocedure command "fkey" to specify a new keyset definition
  467. Xfrom ~/.ecu/keys.
  468. X
  469. XFunction keyset definitions are appended one after another
  470. Xto ~/.ecu/keys.  The keyset name appears on a line by itself
  471. Xand the choices making up a set appear on subsequent lines
  472. Xof a special format.  
  473. X
  474. XA keyset is loaded explicitly using "fkey" and implicitly when
  475. Xconnecting to a remote system and a keyset name matches
  476. Xthe dialing directory entry name.
  477. X
  478. XConsider the example:
  479. X
  480. X.DS L
  481. Xstratus
  482. X    F1:F1:esc O q
  483. X    F2:F2:esc O r
  484. X    F3:F3:esc O s
  485. X    F4:F4:esc O t
  486. X    F5:F5:esc O u
  487. X    F6:F6:esc O v
  488. X    F7:F7:esc O w
  489. X    F8:procex:proc dowork /tmp
  490. X    F9:no status:nl
  491. X    F10:redisp:esc O y
  492. X    F11:redisp:syn
  493. X    PGDN:cancel:esc O Q
  494. X    END:enter:esc O M
  495. X    PGUP:dispform:esc O R
  496. X    CUU:^:dle
  497. X    CUD:v:so
  498. X    CUL:<:stx
  499. X    CUR:>:ack
  500. X.DE
  501. X
  502. XThe key definition lines are made up of three fields.  In addition,
  503. Xthere must be a blank or a space in the first column of the line.
  504. XThe first field is the ECU key identifier from the table above.
  505. XThe second field is a 12-character max string to display when
  506. Xthe display option of the fkey command is used.
  507. XThe last field is a either a character sequence to be transmitted 
  508. Xor a procedure to be invoked when the key is pressed.
  509. X
  510. XThe resulting fkey display for the stratus example looks similar to:
  511. X
  512. X.DS L
  513. X F1  F1     F2  F2         Home ecu cmd     PgUp  dispform
  514. X F3  F3     F4  F4         End  enter       PgDn  cancel
  515. X F5  F5     F6  F6         Ins  local shell CUR5  Screen dump
  516. X F7  status F8  procex     BkTab restore receiver display
  517. X F9         F10 redisp     CUR^ ^           CUR>  >
  518. X F11        F12            CUR< <           CURv  v
  519. X.DE
  520. X
  521. XPressing F1, causes the three characters ESC, 'O' and 'q' to be
  522. Xtransmitted.
  523. X
  524. XPressing F8 causes the procedure ``procex'' to be executed with the
  525. Xargument ``/tmp''.  The maximum length of the procedure name,
  526. Xarguments and whitespace must be less than 64 characters; any
  527. Xexcess is silently discarded.
  528. X
  529. X.*s 3 "SCO ALT-[a-z] Function Keys"
  530. X
  531. XIf you are on an SCO machine and you have installed the custom ECU mapkey file
  532. X(as described in the release directory
  533. Xin mapkeys/README), then ALT-a through ALT-z causes the "silent"
  534. Xexecution of procedures 'alt_a.ep' for ALT-a, 'alt_b.ep' for ALT-b, etc.
  535. XThe models subdirectory contains an example alt_h.ep which will home
  536. Xthe cursor when ALT-h is pressed.  This facility allows the execution
  537. Xof 26 procedures without ECU itself changing the video display at all.
  538. XAny changes to the display (short of procedure errors) will result
  539. Xsolely from the action of the invoked procedure.
  540. XIf the procedure matching the ALT-[a-z] key pressed cannot be found,
  541. Xa short error message is printed and the terminal bell is rung.
  542. X(Using back tab may be used to refresh the display in this event.)
  543. X
  544. XNOTE: ECU 3.10 CHANGES TO THE SINGLE KEY PROCEDURE FUNCTIONALITY
  545. XMAKE IT NECESSARY FOR YOU TO REVIEW mapkeys/README IF YOU HAVE USED
  546. XTHIS FEATURE IN PREVIOUS REVISIONS.
  547. X
  548. XThe strings used to represent "non-printable" characters are identical
  549. Xto the formal ASCII names given them (without regard to case), viz:
  550. X.DS I
  551. X      NUL may not appear in a function key definition
  552. X
  553. X0x00 nul    0x10 dle 
  554. X0x01 soh    0x11 dc1 
  555. X0x02 stx    0x12 dc2 
  556. X0x03 etx    0x13 dc3 
  557. X0x04 eot    0x14 dc4 
  558. X0x05 enq    0x15 nak 
  559. X0x06 ack    0x16 syn 
  560. X0x07 bel    0x17 etb 
  561. X0x08 bs     0x18 can 
  562. X0x09 ht     0x19 em  
  563. X0x0A nl     0x1A sub 
  564. X0x0B vt     0x1B esc 
  565. X0x0C np     0x1C fs  
  566. X0x0D cr     0x1D gs  
  567. X0x0E so     0x1E rs  
  568. X0x0F si     0x1F us  
  569. X            0x20 sp  
  570. X            0x7F del 
  571. X.DE
  572. X
  573. X.*s 2 "Line Editing"
  574. X
  575. XWhen you are entering a line of text for an ecu command or in
  576. Xa field on a screen, you may edit it in a number of ways at any
  577. Xtime prior to pressing Enter.  Cursor Left moves the cursor left
  578. Xby one character position, nondestructively.  Cursor Right moves
  579. Xto the right.  Insert toggles insert mode. 
  580. X
  581. XBackspace (your erase key as specified to stty in commands, the
  582. Xactual backspace key in screens) deletes the character to the
  583. Xleft of the cursor.
  584. X
  585. XYour line kill key (as specified to stty) in command mode or
  586. Xthe ^U character in screen mode erases the entire line.  Esc
  587. Xin command mode cancels the command.  Esc in screen mode usually
  588. Xcancels the screen or subfunction in a screen.
  589. X
  590. XThe DEL character erases the character beneath the cursor.  In
  591. Xthe common, but degenerate case of using DEL as the backspace
  592. Xkey (stty erase '^?') or the interrupt key (stty intr '^?'),
  593. Xthe function ordinarily served by the DEL key is unavailable.
  594. X
  595. X.*s 3 "Screen Mode Extras"
  596. X
  597. XWhen editing a field in screen mode which already contains data,
  598. Xthe field is first shown in "standout" mode (usually reverse
  599. Xvideo).
  600. X
  601. XIf the first key you press is an editing key (e.g., backspace,
  602. Xcursor left), the standout display is replaced by a normal one
  603. Xand editing proceeds.
  604. X
  605. XIf the first key you press is not an editing key (e.g., 'a'), the
  606. Xstandout display is replaced by a normal one, the field is
  607. Xerased, and your first character becomes the first character in
  608. Xthe field.
  609. X
  610. XPressing Esc while editing always leaved the original field
  611. Xunchanged.
  612. X
  613. X.*s 3 "Command Line Mode Extras"
  614. X
  615. XTyping ^L or ^R in
  616. Xinteractive command mode shows the current state of Insert mode and
  617. Xredisplays the edited string.
  618. X
  619. X.*s 2 "Screen Dump"
  620. XWhen the "cursor 5" key is pressed, the screen contents are
  621. Xdumped to a file.  By default, this file is named '~/.ecu/screen.dump'.
  622. XThe
  623. X.B sdname
  624. Xinteractive command either displays or changes the current screen
  625. Xdump file name, depending upon whether or not an argument
  626. Xis supplied.
  627. XThe
  628. X.B scrdump
  629. Xprocedure command can initiate a dump.
  630. X
  631. XNote that from an SCO multiscreen, screen dump produces a dump of the
  632. Xactual screen contents (it is obtained from
  633. Xthe video driver), including ecu-generated output.  When
  634. Xusing a non-multiscreen terminal, screen dump dumps only the
  635. Xshared memory virtual screen as received from the host.
  636. X
  637. XIf, at a multiscreen, you wish a screen dump free of ecu output
  638. X"pollution," use Shift-Tab (BkTab) to redraw the screen, then
  639. Xperform the screen dump.  If you are not on a multiscreen, then the
  640. Xscreen dump comes from the (sometimes inexact) screen memory
  641. Xrepresentation and this step is not necessary.
  642. X
  643. X.*s 3 "Multiscreen and Non-Multiscreen"
  644. XNote that from multiscreens, screen dump produces a dump of the
  645. Xactual screen contents, including ECU-generated output.  When
  646. Xusing a non-multiscreen terminal, screen dump dumps only the 
  647. Xshared memory virtual screen as received from the host.
  648. XIf standard input is not a serial line (xterm or /dev/null),
  649. Xscreen dumps will be of the non-multiscreen type.
  650. X
  651. XIf, at a multiscreen, you wish a screen dump free of ECU output
  652. X"pollution," use Shift-Tab (BkTab) to redraw the screen, then
  653. Xperform the screen dump.
  654. X
  655. X.*s 3 "Multiscreen Bug"
  656. XThere has been a bug in the multiscreen driver for some time
  657. Xwherein a MEDIA COPY (screen dump) sequence ("ESC [ 2 i") leaves
  658. Xthe "ESC [ 2" part "active".  When a screen dump (Cursor 5)
  659. Xcommand is given, I do the screen dump, then send a "l" to the
  660. Xscreen to work around the bug ("ESC 2 [ l" unlocks the keyboard,
  661. Xessentially a no-op).  If and when it gets fixed, you'll see an
  662. X"l" show up on your screen after a screen dump sequence.  To fix
  663. Xthis, comment out the
  664. X.DS I
  665. X#define MULTISCREEN_DUMP_BUG
  666. X.DE
  667. Xat the top of ecuscrdump.c.
  668. X
  669. X.*s 2 "Interactive Command History"
  670. X
  671. XAfter pressing the Home key, pressing it again invokes the
  672. Xinteractive command history function.  After the second
  673. XHome key is pressed, the last interactive command is
  674. Xredisplayed. Line editing may be performed on the command as described
  675. Xin the previous section.
  676. X
  677. XAdditionally, using the Cursor Up key accesses less recent commands.
  678. XThe Cursor Down key accesses more recent commands.  Pressing Enter causes
  679. Xthe command to be executed.  Pressing Esc aborts command entry.
  680. X
  681. X.*s 2 "Dialing Directory"
  682. X
  683. XECU provides an on-line editable dialing directory.  Remote
  684. Xsystems are defined as records using alphanumeric identifiers
  685. Xas keys.  Other record fields include telephone number, baud
  686. Xrate, parity and textual description.
  687. X
  688. XOther features include changing to alternate dialing directory
  689. Xand a multi-number redial cycle function. Refer below to the description
  690. Xof the interactive
  691. X.B dial
  692. Xcommand.
  693. X
  694. XWhile a long entry in a field may be truncated on the display,
  695. Xwhen the entry is edited, it's full contents will be dispalyed on the
  696. Xedit subform.
  697. X
  698. XEntering or editing a dialing directory entry is for the most part
  699. Xstraightforward.  A note on the use of the "tty" field is useful, however.
  700. XWhen prompted for a tty, you may choose
  701. X.BL
  702. X.LI
  703. X"Any" line  (deprecated, for compatibility only)
  704. X.LI
  705. Xa tty line matching a Devices type
  706. X.LI
  707. Xa specific tty line
  708. X.LE
  709. X
  710. XA specific line is chosen by using the base name of the tty
  711. X(e.g., "tty1a" or "acu0").  On SCO, since ttys are all named
  712. Xconsistently according to the "/dev/ttyxx" form, you may omit the "tty"
  713. X(e.g., "1a" or "4g").  This latter feature is for compatibility
  714. Xwith earlier revisions of ECU.  It is good practice to fully
  715. Xspecify the tty name.
  716. X
  717. X"Any" matches any tty line in the /usr/lib/Devices file supporting
  718. Xthe specified baud rate and whose Devices type begins with the
  719. Xcharacters (case independent) "ACU".  This choice is provided to
  720. Xbe compatible with earlier versions of ECU (prior to 3.10). 
  721. XUse of this argument is discouraged.  It's equivalent in current
  722. Xpractice is "/ACU", as you can see next.
  723. X
  724. XA more general choice for choosing a tty line based on Devices type
  725. Xis the "Devices type matching" choice, invoked by prefixing the tty
  726. Xfield with a slash or equals sign.
  727. X
  728. X.BL
  729. X.LI
  730. X/ prefix searches for a Devices type matching a regular expression (a
  731. Xla sed or ed)
  732. X.LI
  733. X= prefix searches for an exact match on a Devices type
  734. X.LE
  735. X
  736. X.DS L
  737. XExamples:
  738. X
  739. X   =ACU        matches "ACU", fails on "acu" and "ACUx"
  740. X   /.*tbit.*   matches "ACUtbit1", "tbit"
  741. X.DE
  742. X
  743. XA specific tty line may also be specified.  This is the only means
  744. Xof attaching a line not mentioned in the Devices file.
  745. X
  746. XNOTE:  If the bell rings and you are not allowed to leave a field,
  747. Xit is because you MUST enter acceptible data before you can leave
  748. Xa field using other than the ESCape key.
  749. X
  750. XThe "debug level" parameter allows you to specify a number between 0 and
  751. X9 for passing to a UUCP dialer program with the -x switch.
  752. X
  753. XThe "DCD watch" parameter allows you to modify the DCD watcher
  754. Xupon successful connection to a remote.  The values allowed are:
  755. X.DS L
  756. X   1    enable DCD watcher
  757. X   0    disable DCD watcher
  758. X   t    terminate ECU on loss of DCD
  759. X   n    no change of dcdwatch state
  760. X.DE
  761. XSpecifying 'n' leaves the dcdwatch state unaffected.  See the description
  762. Xof the
  763. X.B dcdwatch
  764. Xinteractive command for more information.
  765. X
  766. XThe following sample dialing directory screen shows an edit in
  767. Xprogress.
  768. X
  769. X.DS L
  770. X .--[ dialing directory ]-- /u1/wht/.ecu/phone --------- modified ------.
  771. X | entry name | telephone number | tty | baud P | description           |
  772. X | ......     | ........         |Any  | 2400 N | ...............       |
  773. X | ...--[ entry: new ]--------------------------------------------.     |
  774. X | ..|                                                            |     |
  775. X | ..| telephone number  1(800)555-1212                           |     |
  776. X | ..| device            =ACUtbit                                 |..   |
  777. X | ..| baud rate         19200                                    |..   |
  778. X | ..| parity            N                                        |     |
  779. X | ..| description       don't call this_________________________ |..   |
  780. X | ..| debug level       0  (dialer -x value 0-9)                 |     |
  781. X | ..| DCD watch         n                                        |     |
  782. X | ..|                                                            |     |
  783. X | ..| Enter description                                          |..   |
  784. X | ..| ESC: abort  End: finish  ^U: erase ^B: back  TAB: fwd      |     |
  785. X | ..`------------------------------------------------------------'     |
  786. X | .....      | ..........       |2b   | 9600 N | ...................   |
  787. X | sco19      | 1(408)426-9525p  |2b   | 9600 N | SCO Tech Services     |
  788. X | sco24      | 1(408)426-9495   |2b   | 2400 N | SCO Tech Services     |
  789. X +----------------------------------------------------------------------+
  790. X | down up PgDn PgUp edit add remove save find change dial dir          |
  791. X | redial: mark unMark Unmark all wait between dial ENTER:dial ESC,quit |
  792. X `----------------------------------------------------------------------'
  793. X.DE
  794. X
  795. XIn the directory editor main window,
  796. XYou may use the vi conventions of 'j' for down and 'k' for up.
  797. XYou may also use the up and down arrow keys if you are on an SCO
  798. Xmultiscreen or if the function keys have been properly defined
  799. Xwith funckeymap.  Also, '/' performs the same function as 'f'ind.
  800. XPgUp and PgDn scrolls the directory list several items at a time.
  801. XThe alternative keys, ^U and ^D, may be used.
  802. X
  803. X.*s 2 "Online Interactive Command Help"
  804. X
  805. XThe ECU help command presents a display of interactive commands.  The user
  806. Xis then prompted to enter a command name for further, Unix-style
  807. X"usage" information.
  808. X
  809. X.*s 2 "Multiscreen Event Alarm"
  810. X
  811. XOn an SCO machine, by using the 
  812. X.B BN
  813. X(bell notify) interactive command, an audible alert is sent to all
  814. Xmultiscreens when an ASCII BEL (bell) is received or when a file
  815. Xtransfer completes.  An additional option causes an alert when ANY
  816. Xdata is received from the line.  This makes it simple to do work on
  817. Xother multiscreen consoles and be alerted when attention to the
  818. Xcommunications session is required.
  819. X
  820. XFor instance, the Berkeley 4.x Unix utility "talk" rings the bell when
  821. Xanother user wishes an interactive chat mode.  BSD "biff" rings the bell
  822. Xwhen incoming mail is received.  Scripts or commands at remote sites can
  823. Xbe configured to ring the bell as in:
  824. X.DS I
  825. Xmake foo bar; bell; make more_stuff; bell;
  826. X.DE
  827. Xto call attention to the ECU user when work is being done
  828. Xon other multiscreen consoles.
  829. X
  830. XThis feature is only available when you are running ECU from a multiscreen.
  831. X
  832. X.*s 2 "Built-in Modem Dialer"
  833. X
  834. XThe built-in ECU dialer supports modems which use the 
  835. X.B
  836. XHayes-style AT command set or most variants
  837. X.R
  838. X.B thereof .
  839. XIt is used when HoneyDanBer UUCP is not installed or when there is no
  840. Xentry in the /usr/lib/uucp/Devices file for the selected outgoing line.
  841. X(For more information, see the later section titled "HoneyDanBer UUCP
  842. XInterface".)
  843. X
  844. XThe built-in dialer uses files in the ecu library directory which
  845. Xcontains modem initialization information.  Modem initialization
  846. Xfilenames are made from concatenating the tty name with ".mi".  For
  847. Xinstance, tty1a's initialization file is named "tty1a.mi".
  848. X
  849. XCommands for initializing the modem and for dialing may be specified in
  850. Xa very flexible manner.  Separate init and dial strings for each legal
  851. Xbaud rate, a single pair of strings for all baud rates or a combination
  852. Xmay be specified.
  853. X
  854. XThe ok_string is provided in the event your modem does not use
  855. X"OK" to indicate good command status.  If your modem
  856. Xissues a connect indication other than "CONNECT, specify it
  857. Xwith connect_string.  The specified string should be the consistent
  858. Xpart of the connect result (e.g., "CONNECT", not "CONNECT 9600").
  859. XThe dialer will examine the string remainder for a baud rate.
  860. XFor example, if your brain-misdirected vendor sends "CARRIER"
  861. Xinstead of "CONNECT" (after borrowing the remainder of Hayes
  862. Xhistory), then ECU will scan the remainder of a "CARRIER 9600"
  863. Xresult to find the line rate.  A warning is issued if the
  864. Xmodem reports a different rate than the line rate established
  865. Xby ECU.
  866. X
  867. X.DF L
  868. X.hl
  869. X.ce 1
  870. XSample Modem Initialization Files
  871. X
  872. X#+-----------------------------------------------------------
  873. X#  tty1a.mi - Microcom AX/9624c
  874. X#------------------------------------------------------------
  875. Xinit_>2400:ATS11=47X4S0=0S7=30\eQ1\eX1\eN3   # baud rates > 2400
  876. Xinit_default:ATS11=47X4S0=0S7=30\eQ0\eX0\eN0 # other baud rates
  877. Xdial_default:ATDT
  878. Xok_string:OK
  879. Xconnect_string:CONNECT
  880. X
  881. X#+-----------------------------------------------------------
  882. X#  tty2d.mi - USR Courier 2400
  883. X#------------------------------------------------------------
  884. Xinit_default:ATS11=47 X4 S0=0 S7=32
  885. Xdial_default:ATDT
  886. Xok_string:OK
  887. Xconnect_string:CONNECT
  888. X
  889. X.hl
  890. X.DE
  891. X
  892. X
  893. X.*s 2 "File Transfer"
  894. X
  895. XECU supports numerous file transfer protocols: as of this writing,
  896. XXMODEM, XMODEM/CRC, XMODEM-1K, YMODEM/CRC Batch, ZMODEM/CRC-16,
  897. XZMODEM/CRC-32, C-Kermit and SEAlink are supported.  `
  898. XAlthough a seamless interface
  899. X(there's some yuppie marketing newspeak) is provided to the user,
  900. Xtransfer is facilitated by executing external programs.
  901. X
  902. XKermit support requires you to obtain C-Kermit version 5A or later.
  903. XYou may also patch C-Kermit 4E to work with ECU (The
  904. Xpatch information is available in the ckermit subdirectory of the
  905. XECU release).  C-Kermit 5 is in beta release as of this writing
  906. Xand supports ECU without modification.
  907. X
  908. XXMODEM, YMODEM and ZMODEM transfers (thanks to modified public domain
  909. Xprograms by Chuck Forsberg) present dynamic status displays similar to
  910. Xthe following:
  911. X.DS L
  912. X .-[ ecusz 3.20 ]-- /tmp -------------------------------.
  913. X |  ZMODEM/CRC32   data rate ~= 900 ch/sec (94%)     T  |
  914. X |  File 1   of 1  : /t/ecu320cpio.Z                    |
  915. X |  File position:  617472 length: 915263  -rw-r--r--   |
  916. X |  Total transaction 915263 bytes (xfer time ~= 17:29) |
  917. X |  tx: D32 ZCRCG 1024          rx: HEX ZACK  605184    |
  918. X |  Comm I/O: rx 917       tx 650041   bytes            |
  919. X |  Baud rate: 9600 BINARY blklen: 1024 comm mode: RAW  |
  920. X |  Time: started: 13:39:34 this file: 13:39:35 window: |
  921. X |  13:51:34 elapsed: 00:12:00         00:11:59 +12288  |
  922. X |  Errors: this file: 2   total: 2  files skipped: 0   |
  923. X |                                                      |
  924. X |  This file 67%, transaction 67% complete             |
  925. X |  Remote: CRC32 y  duplex y  continuous stream y      |
  926. X `- Connected to tridom --------------------------------'
  927. X.DE
  928. X
  929. XDuring file transfer, data rates are displayed from time to time.
  930. XWhile the figures may vary significantly during the transfer, bear in mind
  931. Xthe calculations are for actual data throughput, measured as total DATA
  932. Xcharacters transferred from the time the file is opened until it is closed.
  933. XSo, if the data rate appears to be low at the start of the transfer
  934. Xand increase over time, perhaps it took a significant amount of time for
  935. Xthe receiver to open it's file or to respond to protocol startup stimuli.
  936. XIf the data rate appears to be higher at the beginning and become
  937. Xlower over time, perhaps flow control is being invoked.  A sudden
  938. Xreduction in the "last file" or "transaction" data rate over the
  939. Xin progress rate reflects the time required to close files, operate
  940. Xthe protocol or to skip files (in the case of ZMODEM).  If any files
  941. Xare skipped in a session, you may be sure the transaction
  942. Xrate will be (perhaps much) lower than the per-file rate.
  943. X
  944. XOn some systems and driver options, sundry driver statistics are
  945. Xdisplayed during X/Y/ZMODEM transfers.  For instance, in the above
  946. Xdisplay from a Sun session.  the driver's current output and input
  947. Xqueue depths and input queue space available are displayed along with
  948. Xthe current status of RTS and CTS.  While such gay banter is rightly
  949. Xrelegated to the "bell and whistle" category, it does provide a rare
  950. Xinsight into driver operation.  The ECU FAS/i driver for 386 systems
  951. X(after Uwe Doering's FAS driver) provides other information.
  952. X
  953. X.DS L
  954. X        |  Output queue depth       0  RTS T  CTS T                |
  955. X        |  Input queue depth       10  Input queue avail    490    |
  956. X.DE
  957. X
  958. X
  959. X.*s 2 "Automatic ZMODEM Receive"
  960. XECU in the interactive mode (no procedure executing) can interpret a
  961. XSUB, 'B', '0', '0' receive data sequence as a ZMODEM ZRQINIT frame and
  962. Xautomatically begin a ZMODEM receive operation.  The
  963. X.B autorz
  964. Xinteractive and procedure commands control
  965. Xthis feature.  By default, this feature is turned on.
  966. X
  967. X.*s 2 "Procedures (Scripts)"
  968. XA powerful, language-style procedure language is incorporated
  969. Xinto ECU.  The language is described in the companion "Procedure
  970. XLanguage" manual.
  971. X
  972. XProcedures are files of programmatic instructions written in
  973. Xthe ECU procedure language invoked explicitly by the
  974. X.B do 
  975. Xinteractive command or automatically by ECU functions described below.
  976. XProcedures are invoked by
  977. X.I name ,
  978. Xand result in execution of the file
  979. X.I name .ep.
  980. X
  981. XThe file is searched for in the current directory.  If not found there,
  982. XECU checks your personal .ecu subdirectory.  If not there, the ECU library "ep" subdirectory is searched (e.g.,
  983. X.I /usr/local/lib/ecu/ep ).
  984. X
  985. X.*s 3 "Initial (Startup) Procedure"
  986. XAn
  987. X.B
  988. Xinitial procedure
  989. X.R
  990. Xmay be be specified to ECU either to initialize an interactive
  991. Xsession or to execute an entirely unattended or "batch"
  992. Xcommunication session.  Refer to the section on command switches ("-p").
  993. X
  994. X.*s 3 "Dialing Procedure"
  995. XWhen a named dialing entry is selected for calling, if a procedure
  996. Xcan be located using the above mentioned search sequence whose name matches
  997. Xthe name of the directory, then all of the usual ECU built-in dialing
  998. Xprocedure is bypassed and the procedure is used.  For details, refer to
  999. Xother sections related to dialing.
  1000. X.*s 3 "Other Special Procedures"
  1001. XOther special procedures may be invoked when
  1002. X.BL
  1003. X.LI
  1004. Xecu starts up (_rc.ep)
  1005. X.LI
  1006. Xa connection is established (_connect.ep)
  1007. X.LI
  1008. Xan attempted connection fails (_connfail.ep)
  1009. X.LI
  1010. Xa connection is terminated with the hangup command (_hangup.ep)
  1011. X.LE
  1012. XSee the ECU procedure manual for details.
  1013. X
  1014. X.*s 2 "DCD (Carrier) Watcher"
  1015. XECU can be instructed to monitor DCD (carrier) status on any
  1016. Xtty line whose driver honors dynamic manipulation of the CLOCAL
  1017. Xcontrol bit.  
  1018. XECU may be instructed to ignore DCD (the default state).
  1019. XIn such a state, if carrier is lost after a connection has been
  1020. Xmade, ECU is unaware the connection has been lost.  An interactive
  1021. X.B stat
  1022. Xcommand will show the connection still active.
  1023. X
  1024. XWhen the DCD watcher is enabled, loss of carrier will cause
  1025. Xthe hangup command processing to automatically be executed
  1026. X(including execution of the special procedure
  1027. X_hangup.ep if any can be found).
  1028. X
  1029. XAn additional mode is available which, in addition to the hangup
  1030. Xprocessing,  causes ecu to terminate execution.
  1031. X
  1032. XThe
  1033. X.B dcdwatch
  1034. Xinteractive and procedure commands control this feature.
  1035. XIn addition, each dialing directory entry has a field
  1036. Xspecifying whether or not the DCD watcher status is to be
  1037. Xchanged upon connecting to the remote system and if so,
  1038. Xto what state.  Refer to the description of the
  1039. X.B dcdwatch
  1040. Xand
  1041. X.B dial
  1042. Xcommands for details.
  1043. X
  1044. X.*s 2 "Home Directory Files"
  1045. XECU control files reside in the .ecu subdirectory of
  1046. Xeach user's home directory.  For example, in home directory /usr/wht:
  1047. X.DS I
  1048. X   /usr/wht/.ecu/dir          CD interactive command history file
  1049. X*  /usr/wht/.ecu/keys         function key mapping
  1050. X*  /usr/wht/.ecu/funckeymap  function key mapping
  1051. X   /usr/wht/.ecu/log          connect, file transfer history
  1052. X   /usr/wht/.ecu/phone        default dialing directory
  1053. X*% /usr/wht/.ecu/colors       colors used by ECU
  1054. X.DE
  1055. X
  1056. X* The ecu library directory (normally /usr/local/lib/ecu) is searched for
  1057. Xthe "keys", "colors" and "funckeymap" file if a personal version
  1058. Xcannot be found.
  1059. X
  1060. X% The "colors" file does not apply to systems on which color is not yet
  1061. Xsupported.
  1062. X
  1063. XThe .ecu directory is searched for an ECU procedure file
  1064. X(having the '.ep' extension) if the procedure file cannot be found in
  1065. Xthe current working directory.
  1066. X
  1067. X.*s 2 "Lock Files"
  1068. X
  1069. XECU maintains lock files in the standard directory in accordance with the
  1070. XHoneyDanBer UUCP conventions (ASCII pids as 10-character strings
  1071. Xfollowed by a newline).  If porting to a machine with old-style
  1072. Xinteger pids, grep for HONEYDANBER in the sources for hints on
  1073. Xwhere changes are needed.
  1074. X
  1075. XStandard lock directories for versions supported as of this writing:
  1076. X.DS I
  1077. X   SCO               /usr/spool/uucp
  1078. X   ISC               /usr/spool/locks
  1079. X   SunOS, SVR4       /var/spool/locks
  1080. X.DE
  1081. X
  1082. X.ul 1
  1083. XWorld write access to this directory must be in effect. 
  1084. X
  1085. XSee the later section titled "HoneyDanBer UUCP Interface".
  1086. X
  1087. X.*s 2 "Dial-In/Dial-Out Line Support"
  1088. X
  1089. XOn SCO XENIX and UNIX 3.2 systems,
  1090. XECU works with the SCO getty to support dialing out on a line
  1091. Xenabled for login.  After use of the line is complete,
  1092. XECU signals the system to restore incoming call status to
  1093. Xthe line.
  1094. XSee the later section titled "HoneyDanBer UUCP Interface".
  1095. X
  1096. XThis facility is not supported in other environments as of this writing.
  1097. XScan the distribution README.* files for any updates.
  1098. X
  1099. X.*s 2 "Tools"
  1100. X
  1101. XCommands are provided for conversion of hexadecimal or decimal numbers
  1102. Xto and from ASCII equivalents.  For example, 26(10) == 0x1a == ^Z == SUB.
  1103. XFor details, refer to the description of the
  1104. X.B XA
  1105. Xand
  1106. X.B AX
  1107. Xinteractive commands.
  1108. X
  1109. X.*s 2 "Shared Memory 'Friend' Interface"
  1110. X
  1111. XECU maintains a copy of the received screen image (80 x 43
  1112. Xmaximum) and other
  1113. Xinformation in its shared memory segment.  Normally, this
  1114. Xinformation is used only by the transmitter and receiver
  1115. Xprocess.  However,  ECU supports the concept of a
  1116. X.B friend
  1117. Xprocess which may access the shared memory segment, perform
  1118. Xarbitrary auxiliary operations, read from and write to the
  1119. Xattached communications line and communicate resulting information
  1120. Xor status to an ECU procedure via a 1024-byte "friend"
  1121. Xdata area in the shared memory segment.
  1122. X
  1123. XThe procedure language supports the friend
  1124. Xprocess concept through commands and functions which allow
  1125. X.BL
  1126. X.LI
  1127. Xpassing the ECU shared memory segment id (%shmid) to a called
  1128. Xprogram,
  1129. X.LI
  1130. Xreading a single character or string of characters from
  1131. Xscreen memory,
  1132. X.LI
  1133. Xreading cursor position information and
  1134. X.LI
  1135. Xreading and writing of characters, short or long integers and
  1136. Xstrings in the 1024-byte "friend" shared memory data area.
  1137. X.LE
  1138. X
  1139. XThe algorithm for obtaining the shared memory segment key is
  1140. X.DS L
  1141. X0xEC000000L + transmitter process id
  1142. X.DE
  1143. XThus a "friend" process may either use a %shmid 
  1144. X.B
  1145. Xshared memory key
  1146. X.R
  1147. Xpassed as an argument or obtain the 
  1148. X.B
  1149. Xshared memory key
  1150. X.R
  1151. Xby using:
  1152. X.DS L
  1153. Xkey_t shmkey = 0xEC000000L | getppid();
  1154. X.DE
  1155. X
  1156. XThis facility allows batch and interactive applications
  1157. Xto be developed with C programs which would be
  1158. Xtedious or impractical to implement with procedure language alone.
  1159. X
  1160. XFor more information, refer to the shared memory header file
  1161. X.B ecushm.h ,
  1162. Xthe
  1163. X.B ecufriend
  1164. Xsubdirectory of the software release
  1165. Xand to the description of the
  1166. X.B %shmid ,
  1167. X.B %cury
  1168. Xand
  1169. X.B %curx
  1170. Xprocedure functions
  1171. Xand the
  1172. X.B getf
  1173. Xand
  1174. X.B putf
  1175. Xprocedure commands.
  1176. END_OF_FILE
  1177.   if test 41249 -ne `wc -c <'ecu330/doc/_features.txt'`; then
  1178.     echo shar: \"'ecu330/doc/_features.txt'\" unpacked with wrong size!
  1179.   fi
  1180.   # end of 'ecu330/doc/_features.txt'
  1181. fi
  1182. if test -f 'ecu330/proc.c' -a "${1}" != "-c" ; then 
  1183.   echo shar: Will not clobber existing file \"'ecu330/proc.c'\"
  1184. else
  1185.   echo shar: Extracting \"'ecu330/proc.c'\" \(20592 characters\)
  1186.   sed "s/^X//" >'ecu330/proc.c' <<'END_OF_FILE'
  1187. X/*+-------------------------------------------------------------------------
  1188. X    proc.c - procedure command and control
  1189. X    wht@n4hgf.atl.ga.us
  1190. X
  1191. X  Defined functions:
  1192. X    _cmd_gosub_common(param,type)
  1193. X    _get_goto_label(param)
  1194. X    do_proc(argc,argv)
  1195. X    dump_proc(pcb)
  1196. X    execute_esd(tesd)
  1197. X    execute_goto(pcb,goto_type)
  1198. X    execute_labelled_esd(tesd)
  1199. X    execute_proc(pcb,use_goto_label)
  1200. X    find_labelled_lcb(label,first,last)
  1201. X    find_proc_cmd(cmd_list,cmd)
  1202. X    find_procedure(name)
  1203. X    free_lcb_chain(lcb)
  1204. X    pcmd_do(param)
  1205. X    pcmd_gosub(param)
  1206. X    pcmd_gosubb(param)
  1207. X    pcmd_goto(param)
  1208. X    pcmd_gotob(param)
  1209. X    pcmd_return(param)
  1210. X    pcmd_upon(param)
  1211. X    proc_dcdloss_handler(pcb)
  1212. X    show_error_position(pcb)
  1213. X    trace_proc_cmd(pcb)
  1214. X
  1215. X--------------------------------------------------------------------------*/
  1216. X/*+:EDITS:*/
  1217. X/*:05-04-1994-04:39-wht@n4hgf-ECU release 3.30 */
  1218. X/*:03-10-1994-17:46-wht@n4hgf-was not closing files on proc exit */
  1219. X/*:09-10-1992-14:00-wht@n4hgf-ECU release 3.20 */
  1220. X/*:08-22-1992-15:39-wht@n4hgf-ECU release 3.20 BETA */
  1221. X/*:11-16-1991-15:39-wht@n4hgf2-add pcmd_upon stub */
  1222. X/*:11-16-1991-14:53-wht@n4hgf2-add proc_dcdloss_handler */
  1223. X/*:11-16-1991-14:01-wht@n4hgf-calloc pcb instead of malloc */
  1224. X/*:07-25-1991-12:59-wht@n4hgf-ECU release 3.10 */
  1225. X/*:07-01-1991-01:53-wht@n4hgf-fix return with value */
  1226. X/*:05-01-1991-04:18-wht@n4hgf-new find_procedure failed on home subdir match */
  1227. X/*:04-30-1991-03:19-root@n4hgf-add search for .ep in ecu lib ep subdir */
  1228. X/*:08-14-1990-20:40-wht@n4hgf-ecu3.00-flush old edit history */
  1229. X
  1230. X#include "ecu.h"
  1231. X#include "ecuerror.h"
  1232. X#include "ecukey.h"
  1233. X#include "esd.h"
  1234. X#include "var.h"
  1235. X#include "proc.h"
  1236. X
  1237. X#define NEED_P_CMD
  1238. X#include "ecucmd.h"
  1239. X
  1240. XPCB *pcb_stack[PROC_STACK_MAX];
  1241. X
  1242. Xint proc_level = 0;
  1243. Xint proc_trace = 0;
  1244. X
  1245. Xchar goto_label[64];
  1246. X
  1247. X/*+-------------------------------------------------------------------------
  1248. X    _get_goto_label(param)
  1249. X--------------------------------------------------------------------------*/
  1250. Xint
  1251. X_get_goto_label(param)
  1252. XESD *param;
  1253. X{
  1254. X    register erc;
  1255. X    register ESD *label_esd;
  1256. X
  1257. X    goto_label[0] = 0;
  1258. X    if (erc = get_alphanum_zstr(param, goto_label, sizeof(goto_label)))
  1259. X    {
  1260. X        if (!(label_esd = esdalloc(ESD_NOMSZ)))
  1261. X            return (eNoMemory);
  1262. X        if (!(erc = gstr(param, label_esd, 0)))
  1263. X            strcpy(goto_label, label_esd->pb);
  1264. X        esdfree(label_esd);
  1265. X    }
  1266. X
  1267. X    return (erc);
  1268. X
  1269. X}                             /* end of _get_goto_label */
  1270. X
  1271. X/*+-------------------------------------------------------------------------
  1272. X    pcmd_goto(param)
  1273. X--------------------------------------------------------------------------*/
  1274. Xint
  1275. Xpcmd_goto(param)
  1276. XESD *param;
  1277. X{
  1278. X
  1279. X    if (!proc_level)
  1280. X        return (eNotExecutingProc);
  1281. X    if (_get_goto_label(param))
  1282. X        return (eInvalidLabel);
  1283. X    return (eProcAttn_GOTO);
  1284. X
  1285. X}                             /* end of pcmd_goto */
  1286. X
  1287. X/*+-------------------------------------------------------------------------
  1288. X    pcmd_gotob(param)
  1289. X--------------------------------------------------------------------------*/
  1290. Xint
  1291. Xpcmd_gotob(param)
  1292. XESD *param;
  1293. X{
  1294. X
  1295. X    if (!proc_level)
  1296. X        return (eNotExecutingProc);
  1297. X    if (_get_goto_label(param))
  1298. X        return (eInvalidLabel);
  1299. X    return (eProcAttn_GOTOB);
  1300. X
  1301. X}                             /* end of pcmd_gotob */
  1302. X
  1303. X/*+-------------------------------------------------------------------------
  1304. X    _cmd_gosub_common(param,type)
  1305. X--------------------------------------------------------------------------*/
  1306. Xint
  1307. X_cmd_gosub_common(param, type)
  1308. XESD *param;
  1309. Xint type;
  1310. X{
  1311. X    int erc;
  1312. X    LCB *current_save;
  1313. X    int index_save;
  1314. X
  1315. X    if (_get_goto_label(param))
  1316. X        return (eInvalidLabel);
  1317. X    current_save = pcb_stack[proc_level - 1]->current;
  1318. X    index_save = current_save->text->index;
  1319. X    if (!(erc = execute_proc(pcb_stack[proc_level - 1], type)))
  1320. X    {
  1321. X        pcb_stack[proc_level - 1]->current = current_save;
  1322. X        current_save->text->index = index_save;
  1323. X    }
  1324. X    return (erc);
  1325. X
  1326. X}                             /* end of _cmd_gosub_common */
  1327. X
  1328. X/*+-------------------------------------------------------------------------
  1329. X    pcmd_gosub(param)
  1330. X--------------------------------------------------------------------------*/
  1331. Xint
  1332. Xpcmd_gosub(param)
  1333. XESD *param;
  1334. X{
  1335. X    if (!proc_level)
  1336. X        return (eNotExecutingProc);
  1337. X    return (_cmd_gosub_common(param, eProcAttn_GOTO));
  1338. X}                             /* end of pcmd_gosub */
  1339. X
  1340. X/*+-------------------------------------------------------------------------
  1341. X    pcmd_return(param)
  1342. X--------------------------------------------------------------------------*/
  1343. Xint
  1344. Xpcmd_upon(param)
  1345. XESD *param;
  1346. X{
  1347. X    pprintf("'upon' not implimented\n");
  1348. X    param->index = param->cb;
  1349. X    return (0);
  1350. X}                             /* end of pcmd_return */
  1351. X
  1352. X/*+-------------------------------------------------------------------------
  1353. X    pcmd_gosubb(param)
  1354. X--------------------------------------------------------------------------*/
  1355. Xint
  1356. Xpcmd_gosubb(param)
  1357. XESD *param;
  1358. X{
  1359. X    if (!proc_level)
  1360. X        return (eNotExecutingProc);
  1361. X    return (_cmd_gosub_common(param, eProcAttn_GOTO));
  1362. X}                             /* end of pcmd_gosubb */
  1363. X
  1364. X/*+-------------------------------------------------------------------------
  1365. X    pcmd_return(param)
  1366. X--------------------------------------------------------------------------*/
  1367. Xint
  1368. Xpcmd_return(param)
  1369. XESD *param;
  1370. X{
  1371. X    long value = 0;
  1372. X
  1373. X    if (!gint(param, &value))
  1374. X    {
  1375. X        if ((value < 0) || (value > 255))
  1376. X            value = 255;
  1377. X        if (proc_trace)
  1378. X            pprintf("return value %ld\n", value);
  1379. X        if (value)
  1380. X            value += e_USER;
  1381. X        return ((int)value);
  1382. X    }
  1383. X    return (eProcAttn_RETURN);
  1384. X}                             /* end of pcmd_return */
  1385. X
  1386. X/*+-------------------------------------------------------------------------
  1387. X    find_labelled_lcb(label,first,last)
  1388. Xsearch for match between label
  1389. X--------------------------------------------------------------------------*/
  1390. XLCB *
  1391. Xfind_labelled_lcb(label, first, last)
  1392. Xchar *label;
  1393. Xregister LCB *first;
  1394. XLCB *last;
  1395. X{
  1396. X    register llen = strlen(label);
  1397. X    ESD *text;
  1398. X
  1399. X    while (first)
  1400. X    {
  1401. X        text = first->text;
  1402. X        if ((text->cb >= llen) && (!strncmp(text->pb, label, llen))
  1403. X            && (!text->pb[llen] || isspace(text->pb[llen])))
  1404. X            return (first);
  1405. X
  1406. X        if (first == last)
  1407. X            return ((LCB *) 0);
  1408. X        first = first->next;
  1409. X    }
  1410. X    pputs("find_labelled_lab logic error\n");
  1411. X    return ((LCB *) 0);
  1412. X
  1413. X}                             /* end of find_labelled_lcb */
  1414. X
  1415. X/*+-------------------------------------------------------------------------
  1416. X    execute_goto(pcb,goto_type)
  1417. X--------------------------------------------------------------------------*/
  1418. Xexecute_goto(pcb, goto_type)
  1419. XPCB *pcb;
  1420. Xint goto_type;
  1421. X{
  1422. X    LCB *next = (LCB *) 0;     /* next lcb to execute */
  1423. X
  1424. X    switch (goto_type)
  1425. X    {
  1426. X        case eProcAttn_GOTO:
  1427. X            if (!(next = find_labelled_lcb(goto_label, pcb->current, pcb->last)))
  1428. X                next = find_labelled_lcb(goto_label, pcb->first, pcb->current);
  1429. X            break;
  1430. X        case eProcAttn_GOTOB:
  1431. X            if (!(next = find_labelled_lcb(goto_label, pcb->first, pcb->current)))
  1432. X                next = find_labelled_lcb(goto_label, pcb->current, pcb->last);
  1433. X            break;
  1434. X    }
  1435. X    if (next)
  1436. X    {
  1437. X        pcb->current = next;
  1438. X        return (0);
  1439. X    }
  1440. X    pprintf("goto/gosub label not found: %s\n", goto_label);
  1441. X    return (eFATAL_ALREADY);
  1442. X
  1443. X}                             /* end of execute_goto */
  1444. X
  1445. X/*+-------------------------------------------------------------------------
  1446. X    show_error_position(pcb)
  1447. Xcursor MUST be at left margin when this is called
  1448. X--------------------------------------------------------------------------*/
  1449. Xvoid
  1450. Xshow_error_position(pcb)
  1451. XPCB *pcb;
  1452. X{
  1453. X    ESD *tesd = pcb->current->text;
  1454. X    register itmp = tesd->old_index;
  1455. X    char tag[64];
  1456. X
  1457. X    sprintf(tag, "%s %u> ", pcb->argv[0], pcb->current->lineno);
  1458. X    pputs(tag);
  1459. X    pputs(tesd->pb);
  1460. X    pputs("\n");
  1461. X    itmp = strlen(tag) + tesd->old_index;
  1462. X    while (itmp--)
  1463. X        pputc(' ');
  1464. X    pputs("^\n");
  1465. X
  1466. X}                             /* end of show_error_position */
  1467. X
  1468. X/*+-------------------------------------------------------------------------
  1469. X    find_proc_cmd(cmd_list,cmd)
  1470. X--------------------------------------------------------------------------*/
  1471. XP_CMD *
  1472. Xfind_proc_cmd(cmd_list, cmd)
  1473. Xregister P_CMD *cmd_list;
  1474. Xregister char *cmd;
  1475. X{
  1476. X    while (cmd_list->token != -1)
  1477. X    {
  1478. X        if (!strcmp(cmd_list->cmd, cmd))
  1479. X            break;
  1480. X        cmd_list++;
  1481. X    }
  1482. X    return ((cmd_list->token == -1) ? (P_CMD *) 0 : cmd_list);
  1483. X
  1484. X}                             /* end of find_proc_cmd */
  1485. X
  1486. X/*+-------------------------------------------------------------------------
  1487. X    execute_esd(tesd)
  1488. X--------------------------------------------------------------------------*/
  1489. Xint
  1490. Xexecute_esd(tesd)
  1491. XESD *tesd;
  1492. X{
  1493. X    int erc;
  1494. X    P_CMD *pcmd;
  1495. X    static P_CMD *set_pcmd = (P_CMD *) 0;    /* quick access to 'set' */
  1496. X    char cmd[32];
  1497. X    extern int proc_interrupt;
  1498. X
  1499. X    /* if interrupt, exit */
  1500. X    if (sigint | proc_interrupt)
  1501. X        return (eCONINT);
  1502. X
  1503. X    /* if blank, skip it */
  1504. X    if (skip_cmd_break(tesd))
  1505. X        return (0);
  1506. X
  1507. X    /* if comment, skip it */
  1508. X    if (!skip_cmd_char(tesd, '#'))
  1509. X        return (0);
  1510. X
  1511. X    if (*(tesd->pb + tesd->index) == '{')
  1512. X    {
  1513. X        pputs("invalid '{'\n");
  1514. X        return (eFATAL_ALREADY);
  1515. X    }
  1516. X
  1517. X    while (1)
  1518. X    {
  1519. X        /* get command -- allow leading '$' to assume 'set' command */
  1520. X        if (*(tesd->pb + tesd->index) == '$')
  1521. X        {
  1522. X            /* find 'set' in the list -- save for rapid access later */
  1523. X            if (set_pcmd)
  1524. X                pcmd = set_pcmd;
  1525. X            else if ((pcmd = find_proc_cmd(icmd_cmds, "set")) == (P_CMD *) 0)
  1526. X                return (eInternalLogicError);
  1527. X            else
  1528. X                set_pcmd = pcmd;
  1529. X        }
  1530. X        else
  1531. X        {
  1532. X            if (get_alphanum_zstr(tesd, cmd, sizeof(cmd)))
  1533. X                return (eIllegalCommand);
  1534. X            /* find it in the list */
  1535. X            if ((pcmd = find_proc_cmd(icmd_cmds, cmd)) == (P_CMD *) 0)
  1536. X                return (eIllegalCommand);
  1537. X        }
  1538. X
  1539. X        /* check to see if this command available for procedure */
  1540. X        if (!pcmd->proc)
  1541. X            return (eInteractiveCmd);
  1542. X
  1543. X        /* execute the command */
  1544. X        if (erc = (*pcmd->proc) (tesd))
  1545. X            return (erc);
  1546. X
  1547. X        /* look for comment */
  1548. X        if (!skip_cmd_char(tesd, '#'))
  1549. X            break;
  1550. X
  1551. X        /* look for multiple commands on line */
  1552. X        if (skip_cmd_char(tesd, ';'))
  1553. X            break;
  1554. X
  1555. X        /* if blank after ';', skip it */
  1556. X        if (skip_cmd_break(tesd))
  1557. X            break;
  1558. X    }
  1559. X    return (0);
  1560. X
  1561. X}                             /* end of execute_esd */
  1562. X
  1563. X/*+-------------------------------------------------------------------------
  1564. X    execute_labelled_esd(tesd)
  1565. X--------------------------------------------------------------------------*/
  1566. Xexecute_labelled_esd(tesd)
  1567. XESD *tesd;
  1568. X{
  1569. X    register index = 0;
  1570. X    register cb = tesd->cb;
  1571. X    register char *pb = tesd->pb;
  1572. X
  1573. X/* reset indices */
  1574. X    tesd->index = index;
  1575. X    tesd->old_index = index;
  1576. X
  1577. X/* if comment, skip it */
  1578. X    if (!skip_cmd_char(tesd, '#'))
  1579. X        return (0);
  1580. X
  1581. X/* skip over any label */
  1582. X    while (!isspace(*(pb + index)) && (index < cb))
  1583. X        index++;
  1584. X    tesd->index = index;
  1585. X    tesd->old_index = index;
  1586. X
  1587. X    return (execute_esd(tesd));
  1588. X}                             /* end of execute_labelled_esd */
  1589. X
  1590. X/*+-------------------------------------------------------------------------
  1591. X    dump_proc(pcb)
  1592. X--------------------------------------------------------------------------*/
  1593. X#if 0
  1594. Xvoid
  1595. Xdump_proc(pcb)
  1596. XPCB *pcb;
  1597. X{
  1598. X    int itmp;
  1599. X    LCB *lcb;
  1600. X
  1601. X    pprintf("------ pcb @ 0x%08lx -----------------\n", pcb);
  1602. X    pprintf("argc=%d first=0x%08lx last=0x%08lx\n", pcb->argc,
  1603. X        pcb->first, pcb->last);
  1604. X    for (itmp = 0; itmp < pcb->argc; itmp++)
  1605. X    {
  1606. X        pprintf("argv(%d) @ 0x%lx: '%s'\n", itmp, pcb->argv[itmp],
  1607. X            pcb->argv[itmp]);
  1608. X    }
  1609. X    pputs("\n");
  1610. X    lcb = pcb->first;
  1611. X    while (lcb)
  1612. X    {
  1613. X        pprintf("lcb @ 0x%08lx   lineno=%u\n", lcb, lcb->lineno);
  1614. X        pputs("\n");
  1615. X        lcb = lcb->next;
  1616. X    }
  1617. X    pflush();
  1618. X}                             /* end of dump_proc */
  1619. X#endif
  1620. X
  1621. X/*+-------------------------------------------------------------------------
  1622. X    trace_proc_cmd(pcb) - if asked, show command
  1623. X--------------------------------------------------------------------------*/
  1624. Xvoid
  1625. Xtrace_proc_cmd(pcb)
  1626. XPCB *pcb;
  1627. X{
  1628. X    if (proc_trace)
  1629. X    {
  1630. X        pprintf("%s %u> ", pcb->argv[0], pcb->current->lineno);
  1631. X        pputs(pcb->current->text->pb);
  1632. X        pputc('\n');
  1633. X    }
  1634. X
  1635. X}                             /* end of trace_proc_cmd */
  1636. X
  1637. X/*+-------------------------------------------------------------------------
  1638. X    proc_dcdloss_handler(pcb) - a statement execution found DCD loss
  1639. X--------------------------------------------------------------------------*/
  1640. Xint
  1641. Xproc_dcdloss_handler(pcb)
  1642. XPCB *pcb;
  1643. X{
  1644. X    int erc = 0;
  1645. X    int itmp;
  1646. X    ESD esdcopy;
  1647. X    ESD *tesd;
  1648. X
  1649. X    if (pcb->upon_dcdloss.pb)
  1650. X    {
  1651. X        esdcopy = pcb->upon_dcdloss;    /* a copy to preserve pcb->index */
  1652. X        tesd = &esdcopy;
  1653. X        if (proc_trace)
  1654. X        {
  1655. X            pprintf("%s DCDLOSS> ", pcb->argv[0]);
  1656. X            pputs(tesd->pb + tesd->index);
  1657. X            pputc('\n');
  1658. X        }
  1659. X        if (erc = execute_esd(tesd))
  1660. X        {
  1661. X            if (erc != eFATAL_ALREADY)
  1662. X                proc_error(erc);
  1663. X            pprintf("error in 'upon dcdloss' statement\n");
  1664. X            pputs(tesd->pb + pcb->upon_dcdloss.index);
  1665. X            pputs("\n");
  1666. X            itmp = tesd->old_index - pcb->upon_dcdloss.index;;
  1667. X            while (itmp--)
  1668. X                pputc(' ');
  1669. X            pputs("^\ninvoked while executing:\n");
  1670. X            erc = eFATAL_ALREADY;
  1671. X        }
  1672. X    }
  1673. X    else
  1674. X        /* DCD watch enabled but no 'upon dcdloss' in effect */
  1675. X    {
  1676. X        pprintf("Connection terminated during procedure execution\n");
  1677. X        pputs("while executing:\n");
  1678. X        erc = eFATAL_ALREADY;
  1679. X    }
  1680. X    return (erc);
  1681. X}                             /* end of proc_dcdloss_handler */
  1682. X
  1683. X/*+-------------------------------------------------------------------------
  1684. X    execute_proc(pcb,use_goto_label) - execute a memory-resident procedure
  1685. X--------------------------------------------------------------------------*/
  1686. Xexecute_proc(pcb, use_goto_label)
  1687. XPCB *pcb;
  1688. Xint use_goto_label;
  1689. X{
  1690. X    int erc = 0;
  1691. X    extern int proc_interrupt;
  1692. X
  1693. X    if (proc_level == PROC_STACK_MAX)
  1694. X        return (eProcStackTooDeep);
  1695. X
  1696. X    pcb_stack[proc_level++] = pcb;
  1697. X    if (use_goto_label)
  1698. X    {
  1699. X        if (erc = execute_goto(pcb, use_goto_label))
  1700. X            return (erc);
  1701. X    }
  1702. X    else
  1703. X        pcb->current = pcb->first;
  1704. X
  1705. X    mkv_proc_starting(pcb);
  1706. X
  1707. X    while (pcb->current)
  1708. X    {
  1709. X        /* execute the command */
  1710. X        trace_proc_cmd(pcb);
  1711. X        if (erc = execute_labelled_esd(pcb->current->text))
  1712. X        {
  1713. X            /* handle other classes of errors */
  1714. X            switch (erc & 0xF000)
  1715. X            {
  1716. X                case e_WARNING:    /* warning */
  1717. X                    erc = 0;
  1718. X                    break;
  1719. X
  1720. X                case e_FATAL:    /* fatal */
  1721. X                    goto FUNC_RETURN;
  1722. X
  1723. X                case e_ProcAttn:    /* proc attention */
  1724. X                    switch (erc)
  1725. X                    {
  1726. X                        case eProcAttn_GOTO:
  1727. X                        case eProcAttn_GOTOB:
  1728. X                            if (erc = execute_goto(pcb, erc))
  1729. X                                break;    /* didn't find it */
  1730. X                            continue;    /* pcb->current is now goto target */
  1731. X
  1732. X                        case eProcAttn_RETURN:
  1733. X                            erc = 0;
  1734. X                            break;
  1735. X
  1736. X                        case eProcAttn_Interrupt:
  1737. X                        case eProcAttn_ESCAPE:
  1738. X                            pprintf(
  1739. X                                "procedure %s interrupted.\n", pcb->argv[0]);
  1740. X                            erc = eFATAL_ALREADY;
  1741. X                            break;
  1742. X
  1743. X                        case eProcAttn_DCDloss:
  1744. X                            erc = proc_dcdloss_handler(pcb);
  1745. X                            break;
  1746. X
  1747. X                        default:
  1748. X                            pprintf("procedure error 0x%x\n", erc);
  1749. X                            erc = eFATAL_ALREADY;
  1750. X                            break;
  1751. X                    }
  1752. X                    goto FUNC_RETURN;
  1753. X
  1754. X                default:     /* must be proc return error code */
  1755. X                    goto FUNC_RETURN;
  1756. X            }
  1757. X        }
  1758. X
  1759. X        if (sigint || proc_interrupt)
  1760. X        {
  1761. X            proc_interrupt = 0;
  1762. X            sigint = 0;
  1763. X            pprintf("procedure %s interrupted\n", pcb->argv[0]);
  1764. X            erc = eFATAL_ALREADY;
  1765. X        }
  1766. X
  1767. X        if (erc)
  1768. X            break;
  1769. X        pcb->current = pcb->current->next;
  1770. X    }
  1771. X
  1772. X  FUNC_RETURN:
  1773. X    mkv_proc_terminating(pcb);
  1774. X    if (erc)
  1775. X    {
  1776. X        if ((erc > 0) && (erc < e_USER))
  1777. X        {
  1778. X            pprintf(">>procedure %s returned %d\n", pcb->argv[0], erc);
  1779. X            erc |= e_USER;
  1780. X        }
  1781. X        else if ((erc > e_USER) && (erc <= 0x1FFF))
  1782. X        {
  1783. X            ;                 /* already said it */
  1784. X        }
  1785. X        else
  1786. X        {
  1787. X            if (erc != eFATAL_ALREADY)
  1788. X            {
  1789. X                proc_error(erc);
  1790. X                erc = eFATAL_ALREADY;
  1791. X            }
  1792. X            show_error_position(pcb);
  1793. X        }
  1794. X    }
  1795. X    pcb_stack[--proc_level] = (PCB *) 0;
  1796. X
  1797. X#if 0
  1798. X    if (erc && !proc_level)
  1799. X        plog_control((char *)0);
  1800. X#endif
  1801. X
  1802. X    if (!proc_level)
  1803. X        proc_file_reset();
  1804. X
  1805. X    return (erc);
  1806. X
  1807. X}                             /* end of execute_proc */
  1808. X
  1809. X/*+-------------------------------------------------------------------------
  1810. X    free_lcb_chain(lcb)
  1811. X--------------------------------------------------------------------------*/
  1812. Xvoid
  1813. Xfree_lcb_chain(lcb)
  1814. Xregister LCB *lcb;
  1815. X{
  1816. X    LCB *plcb;
  1817. X
  1818. X    while (lcb)
  1819. X    {
  1820. X        if (lcb->text)
  1821. X            esdfree(lcb->text);
  1822. X        plcb = lcb;
  1823. X        lcb = lcb->next;
  1824. X        free((char *)plcb);
  1825. X    }
  1826. X
  1827. X}                             /* end of free_lcb_chain */
  1828. X
  1829. X/*+-------------------------------------------------------------------------
  1830. X    find_procedure(name) - find procedure if it exists
  1831. X--------------------------------------------------------------------------*/
  1832. Xchar *
  1833. Xfind_procedure(name)
  1834. Xchar *name;
  1835. X{
  1836. X    static char procpath[256];
  1837. X
  1838. X/*
  1839. X * try to find proc file in current directory
  1840. X */
  1841. X    strcpy(procpath, name);
  1842. X    strcat(procpath, ".ep");
  1843. X    if (!access(procpath, 4))
  1844. X        return (procpath);
  1845. X    if (proc_trace && (errno != ENOENT))
  1846. X        pperror(procpath);
  1847. X
  1848. X/*
  1849. X * try to find proc file in home .ecu subdirectory
  1850. X */
  1851. X    get_home_dir(procpath);
  1852. X    strcat(procpath, "/.ecu/");
  1853. X    strcat(procpath, name);
  1854. X    strcat(procpath, ".ep");
  1855. X    if (!access(procpath, 4))
  1856. X        return (procpath);
  1857. X    if (proc_trace && (errno != ENOENT))
  1858. X        pperror(procpath);
  1859. X
  1860. X/*
  1861. X * try to find proc file in library ep subdirectory
  1862. X */
  1863. X    strcpy(procpath, ECULIBDIR);
  1864. X    strcat(procpath, "/ep/");
  1865. X    strcat(procpath, name);
  1866. X    strcat(procpath, ".ep");
  1867. X    if (!access(procpath, 4))
  1868. X        return (procpath);
  1869. X    if (proc_trace && (errno != ENOENT) && (errno != ENOTDIR))
  1870. X        pperror(procpath);
  1871. X
  1872. X/*
  1873. X * no luck
  1874. X */
  1875. X    return ((char *)0);
  1876. X
  1877. X}                             /* end of find_procedure */
  1878. X
  1879. X/*+-------------------------------------------------------------------------
  1880. X    do_proc(argc,argv) - read in a disk-based procedure and execute it
  1881. X--------------------------------------------------------------------------*/
  1882. Xdo_proc(argc, argv)
  1883. Xint argc;
  1884. Xchar **argv;
  1885. X{
  1886. X    int itmp;
  1887. X    int itmp2;
  1888. X    int erc;
  1889. X    int iargv;
  1890. X    char *pargv[MAX_PARGV];
  1891. X    int ipargv = 0;
  1892. X    char cmdbuf[ESD_NOMSZ];
  1893. X    char *procpath;
  1894. X    FILE *fp;
  1895. X    PCB *pcb = (PCB *) 0;
  1896. X    LCB *lcb = (LCB *) 0;
  1897. X    LCB *plcb;
  1898. X    ushort line_count = 0;
  1899. X    extern ulong colors_current;
  1900. X    ulong colors_at_entry = colors_current;
  1901. X    extern int proc_interrupt;
  1902. X
  1903. X    proc_interrupt = 0;         /* ok to reset here because no one ... */
  1904. X    sigint = 0;                 /* ... would call here if interrupted */
  1905. X
  1906. X    for (iargv = 0; iargv < argc; iargv++)
  1907. X    {
  1908. X        if (ipargv == MAX_PARGV)
  1909. X        {
  1910. X            pputs("\nMax arguments to procedure invocation exceeded\n");
  1911. X            erc = eFATAL_ALREADY;
  1912. X            goto FUNC_RETURN;
  1913. X        }
  1914. X        pargv[ipargv++] = argv[iargv];
  1915. X    }
  1916. X
  1917. X    if (!ipargv)
  1918. X    {
  1919. X        pputs("\nno procedure name given\n");
  1920. X        erc = eFATAL_ALREADY;
  1921. X        goto FUNC_RETURN;
  1922. X    }
  1923. X
  1924. X    if (!(procpath = find_procedure(pargv[0])))
  1925. X    {
  1926. X        pprintf("\nprocedure %s not found\n", pargv[0]);
  1927. X        erc = eFATAL_ALREADY;
  1928. X        goto FUNC_RETURN;
  1929. X    }
  1930. X    fp = fopen(procpath, "r");
  1931. X    if (!fp)
  1932. X    {
  1933. X        pperror(procpath);
  1934. X        erc = eFATAL_ALREADY;
  1935. X        goto FUNC_RETURN;
  1936. X    }
  1937. X    if (proc_trace)
  1938. X        pprintf("DO: %s\n", procpath);
  1939. X
  1940. X    if (!(pcb = (PCB *) calloc(1, sizeof(PCB))))
  1941. X    {
  1942. X        erc = eNoMemory;
  1943. X        goto FUNC_RETURN;
  1944. X    }
  1945. X
  1946. X    pcb->argv = pargv;
  1947. X    pcb->argc = ipargv;
  1948. X
  1949. X    plcb = 0;
  1950. X    line_count = 0;
  1951. X    while (1)
  1952. X    {
  1953. X
  1954. X        /*
  1955. X         * read procedure file
  1956. X         */
  1957. X        if (!(fgets(cmdbuf, sizeof(cmdbuf), fp)))
  1958. X            break;
  1959. X        line_count++;
  1960. X
  1961. X        /*
  1962. X         * housekeeping
  1963. X         */
  1964. X        itmp = strlen(cmdbuf) - 1;    /* skip blank lines */
  1965. X        if (!itmp)
  1966. X            continue;
  1967. X        cmdbuf[itmp] = 0;     /* kill trailing NL */
  1968. X        if (cmdbuf[0] == '#')/* skip comments */
  1969. X            continue;
  1970. X
  1971. X        /*
  1972. X         * convert tabs to spaces so we don't have to scan for each
  1973. X         */
  1974. X        for (itmp2 = 0; itmp2 < itmp; itmp2++)
  1975. X        {
  1976. X            if (cmdbuf[itmp2] == TAB)
  1977. X                cmdbuf[itmp2] = SPACE;
  1978. X        }
  1979. X
  1980. X        /*
  1981. X         * get a line control block
  1982. X         */
  1983. X        if (!(lcb = (LCB *) malloc(sizeof(LCB))))
  1984. X        {
  1985. X            fclose(fp);
  1986. X            erc = eNoMemory;
  1987. X            goto FUNC_RETURN;
  1988. X        }
  1989. X
  1990. X        /*
  1991. X         * link it into the pcb chain
  1992. X         */
  1993. X        lcb->prev = plcb;
  1994. X        lcb->next = 0;
  1995. X        lcb->lineno = line_count;
  1996. X
  1997. X        if (plcb)
  1998. X            plcb->next = lcb;
  1999. X        else
  2000. X            pcb->first = lcb;
  2001. X
  2002. X        /*
  2003. X         * now copy in the text
  2004. X         */
  2005. X        if (!(lcb->text = esdalloc(itmp)))
  2006. X        {
  2007. X            fclose(fp);
  2008. X            erc = eNoMemory;
  2009. X            goto FUNC_RETURN;
  2010. X        }
  2011. X        strcpy(lcb->text->pb, cmdbuf);
  2012. X        lcb->text->cb = itmp;
  2013. X        esd_null_terminate(lcb->text);
  2014. X        plcb = lcb;
  2015. X    }
  2016. X
  2017. X    /*
  2018. X     * error or not, all done reading the proc; if no error, execute the
  2019. X     * procedure
  2020. X     */
  2021. X    fclose(fp);
  2022. X    pcb->last = lcb;
  2023. X    if (line_count)
  2024. X        erc = execute_proc(pcb, 0);
  2025. X    else
  2026. X        erc = eProcEmpty;
  2027. X
  2028. X  FUNC_RETURN:
  2029. X    if (pcb)
  2030. X    {
  2031. X        if (pcb->first)
  2032. X            free_lcb_chain(pcb->first);
  2033. X        free((char *)pcb);
  2034. X    }
  2035. X    if ((erc > e_USER) && (erc <= 0x1FFF))
  2036. X        erc -= e_USER;
  2037. X    if (erc > e_USER)
  2038. X        setcolor(colors_at_entry);
  2039. X    return (erc);
  2040. X
  2041. X}                             /* end of do_proc */
  2042. X
  2043. X/*+-------------------------------------------------------------------------
  2044. X    pcmd_do(param)
  2045. X--------------------------------------------------------------------------*/
  2046. Xpcmd_do(param)
  2047. XESD *param;
  2048. X{
  2049. X    int erc;
  2050. X    register ipargv;
  2051. X    char *cmd_copy;
  2052. X    char *pargv[MAX_PARGV];
  2053. X    ESD *pargv_esd[MAX_PARGV];
  2054. X    int pargc = 0;
  2055. X
  2056. X    if (!(cmd_copy = (char *)malloc(param->cb)))
  2057. X        return (eNoMemory);
  2058. X    strcpy(cmd_copy, param->pb + param->old_index);
  2059. X    while (pargc != MAX_PARGV)
  2060. X    {
  2061. X        if (end_of_cmd(param))
  2062. X            break;
  2063. X        if (!(pargv_esd[pargc] = esdalloc(ESD_NOMSZ)))
  2064. X        {
  2065. X            erc = eNoMemory;
  2066. X            goto FUNC_RETURN;
  2067. X        }
  2068. X        if (erc = gstr(param, pargv_esd[pargc], 1))
  2069. X            goto FUNC_RETURN;
  2070. X        pargv[pargc] = pargv_esd[pargc]->pb;
  2071. X        pargc++;
  2072. X    }
  2073. X
  2074. X    if (pargc < MAX_PARGV)
  2075. X        erc = do_proc(pargc, pargv);
  2076. X    else
  2077. X    {
  2078. X        pprintf("too many arguments to procedure\n");
  2079. X        erc = eFATAL_ALREADY;
  2080. X    }
  2081. X
  2082. X  FUNC_RETURN:
  2083. X    free(cmd_copy);
  2084. X    for (ipargv = 0; ipargv < pargc; ipargv++)
  2085. X        esdfree(pargv_esd[ipargv]);
  2086. X    return (erc);
  2087. X
  2088. X}                             /* end of pcmd_do */
  2089. X
  2090. X/* vi: set tabstop=4 shiftwidth=4: */
  2091. X/* end of proc.c */
  2092. END_OF_FILE
  2093.   if test 20592 -ne `wc -c <'ecu330/proc.c'`; then
  2094.     echo shar: \"'ecu330/proc.c'\" unpacked with wrong size!
  2095.   fi
  2096.   # end of 'ecu330/proc.c'
  2097. fi
  2098. echo shar: End of archive 10 \(of 37\).
  2099. cp /dev/null ark10isdone
  2100. MISSING=""
  2101. for I in 1 2 3 4 5 6 7 8 9 10 11 12 13 14 15 16 17 18 19 20 21 22 23 24 25 26 27 28 29 30 31 32 33 34 35 36 37 ; do
  2102.     if test ! -f ark${I}isdone ; then
  2103.     MISSING="${MISSING} ${I}"
  2104.     fi
  2105. done
  2106. if test "${MISSING}" = "" ; then
  2107.     echo You have unpacked all 37 archives.
  2108.     rm -f ark[1-9]isdone ark[1-9][0-9]isdone
  2109. else
  2110.     echo You still must unpack the following archives:
  2111.     echo "        " ${MISSING}
  2112. fi
  2113. exit 0
  2114. exit 0 # Just in case...
  2115.