home *** CD-ROM | disk | FTP | other *** search
/ System Booster / System Booster.iso / Texteditors / Origami / bindings / ref2ocl < prev    next >
Encoding:
Text File  |  1996-09-27  |  49.9 KB  |  1,739 lines

  1. #!/bin/sh
  2.  
  3. TMP_DIR="/tmp"
  4.  
  5. trap "/bin/rm -r -f $TMP_DIR/ref.tmp.* $TMP_DIR/ref.tmp.?.awk" 0 1 2 3 15
  6.  
  7. #{{{}}}
  8. #{{{  maybe show help
  9. if test x$1 = x-h
  10. then
  11.    cat <<\HERE
  12.  
  13. USAGE:
  14. ref2ocl AWK sourcefile roff outfile
  15.  for generating documents:  AWK is the awk-command to use
  16.                             sourcefile is :-)
  17.  
  18. ref2ocl AWK sourcefile [extension]
  19.  for generating ocl source: AWK is your the awk-command to use
  20.                             sourcefile is :-)
  21.                             extension may be  an  postfix  for  sourcefile,  if
  22.                               given, sourcefileextension will be added in front
  23.                               and after including libary references.
  24.  
  25. The reference source may use:
  26.  
  27.  command            | effect
  28.                     |  help browser           | reference-file
  29.  ----------------------------------------------------------------------------
  30.  text               | will be printed         | will be printed
  31.  ----------------------------------------------------------------------------
  32.  fold               | a subnode in help tree  | chapter
  33.   comments:         |   first word starting with @ will not be used as
  34.     start="@"       |   for the printed header. But it will be used for
  35.      end =""        |   distinguishing the chapters/nodes!
  36.                     | if same header used,    |   if same header used,
  37.                     |   use previous fold!    |   leave a hint
  38.  ----------------------------------------------------------------------------
  39.  @ref-doc-only      | write only the man page to standard-out
  40.  ----------------------------------------------------------------------------
  41.  @ref-class-id      | use class-d's n,n+1,..  | none
  42.  ----------------------------------------------------------------------------
  43.  @ref-menu          | specify menu string and | none
  44.                     | subnode names:          -------------------------------
  45.                     | @ref-menu n op1 str1 .. args
  46.                     | n is the default action, highlighted at startup
  47.                     | op1,op2,.. can be quit - exit browser
  48.                     |                   ret  - return to upper node
  49.                     |                   next - page )down
  50.                     |                   prev - page-up
  51.                     |                   kill - copy node to kill-buffer
  52.                     |               or  a user defined function, which has to
  53.                     |                   return a value:
  54.                     |                     0 - continue current page afterwards
  55.                     |                     1 - quit afterwards like quit
  56.                     |
  57.                     | str1,str2,..  can be any string, not containing " "
  58.                     | args can be any list of characters, not containing " "
  59.  ----------------------------------------------------------------------------
  60.  @ref-see-also      | none                    | specify text for see-also
  61.                     |                         | hint. Leading C will be cut
  62.                     |                         | and used to start as chapter
  63.  ----------------------------------------------------------------------------
  64.  @ref-fun           | make menu entry, call   | none
  65.                     | first word as function  |
  66.                     | use following as title  |
  67.                     | function must be deffun!|
  68.                     | returning a value:      |
  69.                     |  0 continue current page|
  70.                     |    afterwards           |
  71.                     |  1 quit from infobrowser|
  72.                     |    afterwards           |
  73.  ----------------------------------------------------------------------------
  74.  @ref-top-start-box | specify the box char-   | title, if not underline/bold
  75.  @ref-top-end-box   | acters:                 | none
  76.  @ref-sub-start-box |   top-left top top-right| none
  77.  @ref-sub-end-box   |   left right            | none
  78.                     |   bot-left bot bot-right|
  79.  ----------------------------------------------------------------------------
  80.  @ref-start-picture | Start and end the unmodified output of the given text.
  81.  @ref-end-picture   | No formatting will be done.
  82.  ----------------------------------------------------------------------------
  83.  @ref-start-item .. | Start and end a indented block, not handled as
  84.  @ref-end-item      | chapter/reference-node
  85.  ----------------------------------------------------------------------------
  86.  @ref-start-tbl ..  | Start and end the display of a table. the argument to
  87.  @ref-end-tbl       | start are name,length pairs for the fields
  88.                     | Items are separetded by @@
  89.                     | A @@ between the arguments to @ref-start-tbl generate
  90.                     | additional space between the columns
  91.  ----------------------------------------------------------------------------
  92.  @ref-comment-start | text between will be ignored
  93.       :             |   nested commentsare allowed
  94.  @ref-comment-end   |
  95.  ----------------------------------------------------------------------------
  96.  @ref-indent l r i s| This command is only allowed outside of text nodes!
  97.                     | i specifies the indent  |
  98.                     | of items in the text    |
  99.                     | l/r specify first/last  |
  100.                     |    used for text        |
  101.                     | s additional spaces,    | s=0 -> .ad l
  102.                     |    allowed for blockfill| s>0 -> .ad b
  103.  ----------------------------------------------------------------------------
  104.  fold, with 1st     | text inside will be ignored
  105.   fold-comment-word |   nested commentsare allowed
  106.  =@ref-comment-start|
  107.  ----------------------------------------------------------------------------
  108.  @ref-lib filename tags ..
  109.                     | none                    | none
  110.                     | Make uses thee entries to collet all needed info files.
  111.  ----------------------------------------------------------------------------
  112.  {{{  @ref-header name  | A fold like this will change the display of the
  113.  @ref-title foobar      | node/chapter 'name' in the following way:
  114.  @ref-author foo        |   use 'foobar' as chapter/node header
  115.       :                 |   add all authors
  116.  @ref-author bar        |      roff:    below the header
  117.  abstract for foobar    |      browser: as list behind 'name'
  118.  }}}                    |   add he abstract as small left and right indented
  119.                         | No other folds are allowed inside this description!
  120.                         | The definition has to be made outside the definition
  121.                         | of 'name'!
  122.  ----------------------------------------------------------------------------
  123.  @...               | none                    | none
  124.                     |   put unchanged in the output, @if..,.. can be used.
  125.  
  126.  Each toplevel fold may be accessed by `fold-comment` as help-browser, if
  127.  @use ( REF-TREE )
  128.  is active.
  129.  
  130.  toplevel folds are put into the reference-file, if
  131.     @use ( `fold-comment`-REF )
  132.  is active.
  133.  
  134.  demand-load is used.
  135. HERE
  136.    exit
  137. fi
  138. #}}}
  139.  
  140. #{{{  generate awk scripts
  141. #{{{  common stuff
  142. cat >$TMP_DIR/ref.tmp.o.awk <<\HERE
  143. BEGIN {
  144. #   {{{  constants
  145.    long_line="                                                                                                                        "
  146.    BACKSPACE=sprintf("%c",8)
  147.    DQ=sprintf("%c",34)
  148. #   {{{  some strings, used for generating the ocl-source
  149.    start_ref = "@if-using(%s-REF)\n@reference-begin\n"
  150.    end_ref = "@reference-end\n@fi"
  151.    start_tree="@if-using(REF-TREE)"
  152.    end_tree="@fi"
  153.    start_ref_class = start_tree"\n@use(U-C-%s)\n@reference-begin-class %s\n"
  154.    end_ref_class = "@reference-end\n"end_tree
  155. #   }}}
  156.    case_entry_lg=128
  157.    ref_indent=8
  158.    ref_first=4
  159.    info_indent=substr(long_line,1,ref_first-1)
  160.    ref_last=77
  161. #   }}}
  162. #   {{{  default values for menu,args,see also,boxes
  163. #   {{{  menu and arguments
  164.    MENU_DEF[0]=1
  165.    MENU_OPS[0]=4
  166.    MENU[0]=" Quit Return #(next-page) Back"
  167.    MENU_OP["0#0"]="quit"
  168.    MENU_OP["0#1"]="ret"
  169.    MENU_OP["0#2"]="next"
  170.    MENU_OP["0#3"]="prev"
  171.    MENU_OP["0#4"]="kill"
  172.    ARGS[0]="0123456789<>[]@$"
  173.    VIEWER[0]="ref-viewer-0"
  174.    VIEWER_ID["1 quit Quit ret Return next #(next-page) prev Back  kill Kill  0123456789<>[]@$"]=0
  175.    known_menu=1
  176.    cur_menu=0
  177. #   }}}
  178.    ADD="ABCDEFGHIJKLMNOPQRSTUVWXYZ0123456789@$()<>{}[]'`;:/\\_^#+-=,.&|"
  179.    COMPLAIN=sprintf("%sinvalid %s  %sinput! ",DQ,DQ,DQ)
  180.    box["@ref-top-start-box"]="********"
  181.    box["@ref-top-end-box"]="********"
  182.    box["@ref-sub-start-box"]="+-+||+-+"
  183.    box["@ref-sub-end-box"]="+-+||+-+"
  184.    SEE_ALSO="See also: %s"
  185. #   }}}
  186. #   {{{  ocl init
  187.    commenting=0
  188.    item_txt="\n"
  189.    known_classes = 0
  190.    known_functions = 0
  191.    top_funs=""
  192. #   }}}
  193. #   {{{  roff init
  194.    bold="\\fB"
  195.    norm="\\fP"
  196.    tbl_limiter=sprintf("%c",27)
  197.    commenting=0
  198.    doc_out=0
  199.    ritem_txt="\n"
  200.    new_para=".LP"
  201. #   }}}
  202. #   {{{  prepare info tree parsing
  203.    fold_level=0
  204.    level = 0
  205.    ref_buffer = ""
  206.    info_buffer_use = 0
  207.    ref_error = ""
  208.    lines = 0
  209.    use_id = 1
  210.    picture = 0
  211.    item_level = 0
  212.    tbl_size=0
  213. #   }}}
  214. }
  215. #{{{  error
  216. (ref_error!="") {
  217.    if (ref_error!="-") {
  218.       printf("@error %s line %s: %s\n",FILENAME,lines,ref_error)
  219.       ref_error="-"
  220.    }
  221.    next
  222. }
  223. #}}}
  224. #{{{  count lines
  225. { if (infile==FILENAME)
  226.      lines++
  227.   else {
  228.      infile=FILENAME
  229.      lines=1
  230.   }
  231.   if ($1=="@{{{") {
  232.      if ($2=="@ref-comment-start")
  233.         fold_typ[fold_level]=1
  234.      else
  235.         fold_typ[fold_level]=0
  236.      if (fold_typ[fold_level++]) {
  237.         commenting++
  238.         next
  239.      }
  240.   } else if ($1=="@}}}") {
  241.      if (fold_typ[--fold_level]) {
  242.         commenting--
  243.         if (commenting<0)
  244.            ref_error="no matching fold-comment left!"
  245.         next
  246.      }
  247.   }
  248. }
  249. #}}}
  250. #{{{  @ref-comment-start
  251. /^@ref-comment-start/ {
  252.   commenting++
  253.   next
  254. }
  255. #}}}
  256. #{{{  @ref-comment-end
  257. /^@ref-comment-end/ {
  258.    if (!commenting)
  259.        ref_error="no comment started!"
  260.    commenting--
  261.    next
  262. }
  263. #}}}
  264. #{{{  @ref-indent
  265. /^@ref-indent [0123456789]+ +[0123456789]+ +[0123456789]+( +[0123456789]+)? *$/ && level==0 {
  266.    ref_first=$2
  267.    ref_last=$3
  268.    ref_indent=$4
  269.    ref_spaces=$5
  270.    info_indent=substr(long_line,1,ref_first-1)
  271.    next
  272. }
  273. #}}}
  274. commenting!=0 || (level==0 && /^$/) { next }
  275. HERE
  276. cp $TMP_DIR/ref.tmp.o.awk $TMP_DIR/ref.tmp.r.awk
  277. #}}}
  278. #{{{  ocl-stuff
  279. cat >>$TMP_DIR/ref.tmp.o.awk <<\HERE
  280. #{{{  header
  281. /^@\{\{\{  @ref-header +[^ ]* *$/ {
  282.    header_name=$3
  283.    next
  284. }
  285. header_name!="" {
  286.    if ($1=="@ref-title")
  287.       title[header_name]=substr($0,12)
  288.    else if ($1=="@ref-author") {
  289.       if (author[header_name]=="")
  290.          author[header_name]=" ("
  291.       else
  292.          author[header_name]=author[header_name]","
  293.       author[header_name]=author[header_name] substr($0,13)
  294.    } else if ($1=="@}}}")
  295.       header_name=""
  296.    else
  297.       abstract[header_name]=abstract[header_name] $0 " "
  298.    next
  299. }
  300. #}}}
  301. #{{{  flushing text to out
  302. #{{{  link used -> print it first
  303. link_txt!="" {
  304.    printf(start_ref_class,link_class,link_class)
  305.    print(link_txt)
  306.    print(end_ref_class)
  307.    link_txt=""
  308. }
  309. #}}}
  310. #{{{  class-box used
  311. box_txt!="" {
  312.    if (box_head==1 || box_type!="        ") {
  313.       if (box_center==1)
  314.          box_indent=substr(long_line,1,ref_first-1+(ref_last-ref_first-3-length(box_txt))/2)
  315.       else
  316.          box_indent=info_indent
  317.       printf(start_ref_class,box_class,box_class)
  318.       if (box_head==0)
  319.          print("")
  320.       if (substr(box_type,1,3)!="   ") {
  321.          txt=box_indent substr(box_type,1,1)
  322.          for (i=length(box_txt)+2;i;i--)
  323.             txt=txt substr(box_type,2,1)
  324.          txt=txt substr(box_type,3,1)
  325.          print(txt)
  326.       }
  327.       print(box_indent substr(box_type,4,1)" "box_txt" "substr(box_type,5,1))
  328.       if (substr(box_type,6,3)!="   ") {
  329.          txt=box_indent substr(box_type,6,1)
  330.          for (i=length(box_txt)+2;i;i--)
  331.             txt=txt substr(box_type,7,1)
  332.          txt=txt substr(box_type,8,1)
  333.          print(txt)
  334.       }
  335.       if (box_head==1) {
  336.          print("")
  337. #         {{{  maybe add abstract
  338.          if (level==1 && abstract[header[level]]!="") {
  339.             s=abstract[header[level]]
  340.             of1=1
  341.             for (;of1<=length(s);)
  342.                if (substr(s,of1,1)==" ")
  343.                   of1++
  344.                else {
  345.                   for (of=1;of1+of<=length(s) && substr(s,of1+of,1)!=" ";of++);
  346.                   info_buffer[info_buffer_use++]=substr(s,of1,of)
  347.                   of1+=of
  348.                }
  349.             info_buffer[info_buffer_use++]="\n"
  350.             do_abstract=1
  351.          }
  352. #         }}}
  353.       }
  354.       print(end_ref_class)
  355.    }
  356.    box_txt=""
  357. }
  358. #}}}
  359. #{{{  special line and buffer used -> flush it
  360. /^@/ || do_abstract==1 {
  361. #   {{{  change indentation for abstract
  362.    if (do_abstract) {
  363.       ref_first+=ref_indent
  364.       ref_last-=ref_indent
  365.       info_indent=substr(long_line,1,ref_first-1)
  366.    }
  367. #   }}}
  368. #   {{{  generate dummy text for item flush
  369.    if (info_buffer_use==0 && item_txt!="\n" && level>0)
  370.       info_buffer[info_buffer_use++]=" "
  371. #   }}}
  372. #   {{{  if info-buffer used, flush it boxed
  373.    if (info_buffer_use!=0) {
  374.       printf(start_ref_class,class_id[level],class_id[level])
  375.       of=0
  376.       if (info_buffer[0]=="\n")
  377.          txt="\n"
  378.       else
  379.          txt=""
  380.       while (of<info_buffer_use)
  381.          if (info_buffer[of]!="\n")
  382.           {
  383. #             {{{  set of1,of2 to begin, after end of words of current line
  384.              of1=of
  385.              of2=of+1
  386.              if (picture==1)
  387.                 space=0
  388.              else {
  389.                 space=ref_last-ref_first+1-length(info_buffer[of1])
  390.                 while (of2<info_buffer_use && (length(info_buffer[of2])<space && info_buffer[of2]!="\n"))
  391.                    space-=length(info_buffer[of2++])+1
  392.              }
  393. #             }}}
  394.              if (txt!="") txt=txt"\n"
  395.              txt=txt info_indent
  396. #             {{{  last line no fill
  397.              if (of2==info_buffer_use || info_buffer[of2]=="\n")
  398.                 space=0
  399. #             }}}
  400. #             {{{  append words, maybe fill spaces
  401.              for (of=of1;of<of2;of++) {
  402.                 txt=txt info_buffer[of]
  403. #                {{{  get number of needed limiter spaces
  404.                 xx=space-(of2-of)+2
  405.                 if (xx>ref_spaces)
  406.                    xx=ref_spaces
  407.                 else if (xx<0)
  408.                    xx=0
  409.                 space=space-xx
  410. #                }}}
  411.                 txt=txt substr(long_line,1,xx+1)
  412.              }
  413. #             }}}
  414. #             {{{  empty line, force line break
  415.              if (of2<info_buffer_use && info_buffer[of2]=="\n")
  416.                 txt=txt"\n"
  417. #             }}}
  418.              info_indent=substr(long_line,1,ref_first-1)
  419.              item_txt="\n"
  420.           }
  421.          else
  422.             of++
  423.       print(txt)
  424.       print(end_ref_class)
  425.       info_buffer_use=0
  426.    }
  427. #   }}}
  428. #   {{{  maybe restore indentation (abstract)
  429.    if (do_abstract==1) {
  430.       ref_first-=ref_indent
  431.       ref_last+=ref_indent
  432.       info_indent=substr(long_line,1,ref_first-1)
  433.       do_abstract=0
  434.    }
  435. #   }}}
  436. }
  437. #}}}
  438. #}}}
  439. #{{{  ref/opp statements
  440. #{{{  tbl-handling
  441. #{{{  start-tbl
  442. /^@ref-start-tbl/ {
  443.    if (tbl_size || picture)
  444.       ref_error="tbl not allowed here"
  445.    else {
  446. #      {{{  get head/tail string for info
  447.       tbl_head="|"
  448.       tbl_line="+"
  449.       x=""
  450.       for (of=2;of<NF;)
  451.          if ($of=="@@")
  452.             if (of>2 && of<NF) {
  453.                x="+"
  454.                y="|"
  455.                of++
  456.             } else {
  457.                ref_error="invalid limiter place"
  458.                next
  459.          } else {
  460.             if ($(of+1)<=0) {
  461.                ref_error="invalid tbl-pattern-size "$(of+1)
  462.                next
  463.             }
  464.             tbl_lim[tbl_size]=y"|"
  465.             tbl_len[tbl_size++]=$(of+1)
  466.             tbl_line=tbl_line x "-"
  467.             tbl_head=tbl_head y " "
  468.             x=substr($of,1,$(of+1))
  469.             for (of1=length(x);of1>0;of1--)
  470.                tbl_line=tbl_line"-"
  471.             tbl_head=tbl_head x
  472.             for (of1=$(of+1)-length(x)+1;of1>0;of1--) {
  473.                tbl_line=tbl_line"-"
  474.                tbl_head=tbl_head" "
  475.             }
  476.             tbl_head=tbl_head"|"
  477.             tbl_line=tbl_line"+"
  478.             x=""
  479.             y=""
  480.             of+=2
  481.          }
  482.       tbl_lim[tbl_size]="|"
  483. #      }}}
  484.       xx=length(tbl_line)
  485.       if (tbl_size==0)
  486.          ref_error="no tbl parameter given"
  487.       else if (xx>ref_last-ref_first+1)
  488.          ref_error="tbl to long"
  489.       else {
  490. #         {{{  get leading indentation for tab
  491.          tbl_indent=""
  492.          of=(ref_last-ref_first-xx)/3+ref_first
  493.          tbl_indent=substr(long_line,1,of-1)
  494. #         }}}
  495. #         {{{  print info-tree
  496.          printf(start_ref_class,class_id[level],class_id[level])
  497.          print("")
  498.          print(tbl_indent tbl_line)
  499.          print(tbl_indent tbl_head)
  500.          print(tbl_indent tbl_line)
  501.          print(end_ref_class)
  502. #         }}}
  503.       }
  504.    }
  505.    next
  506. }
  507. #}}}
  508. #{{{  end-tbl
  509. /^@ref-end-tbl/ {
  510.    if (tbl_size==0)
  511.       ref_error="no tbl active"
  512.    else {
  513.       tbl_size=0
  514. #      {{{  print info-tree
  515.       printf(start_ref_class,class_id[level],class_id[level])
  516.       print(tbl_indent tbl_line)
  517.       print(end_ref_class)
  518. #      }}}
  519.    }
  520.    next
  521. }
  522. #}}}
  523. #{{{  inside tbl, no commands, other the @use,@if-using,@fi are allowed
  524. /^@[^@ ]/ && tbl_size>0 {
  525.    if ((substr($0,1,9)!="@if-using")&&(substr($0,1,3)!="@fi")&&(substr($0,1,4)!="@use")) {
  526.       ref_error="tbl crashed"
  527.       next
  528.    }
  529. }
  530. #}}}
  531. #{{{  text -> format it
  532. /^([^@]|@@|$)/ && tbl_size>0 {
  533. #   {{{  decode and format table data
  534.    of1=0
  535.    for (of=1;of<=NF;of++)
  536.       if ($of=="@@")
  537.          of1++
  538.       else {
  539.          if (tbl_txt[of1]!="")
  540.             tbl_txt[of1]=tbl_txt[of1]" "
  541.          tbl_txt[of1]=tbl_txt[of1]$of
  542.       }
  543.    txt=tbl_indent tbl_lim[0]
  544.    for (of=0;of<tbl_size;of++) {
  545.       tbl_txt[of]=tbl_txt[of] long_line
  546.       txt=txt" "substr(tbl_txt[of],1,tbl_len[of])" "tbl_lim[of+1]
  547.       tbl_txt[of]=""
  548.    }
  549. #   }}}
  550. #   {{{  print info-tree
  551.    printf(start_ref_class,class_id[level],class_id[level])
  552.    print(txt)
  553.    print(end_ref_class)
  554. #   }}}
  555.    next
  556. }
  557. #}}}
  558. #}}}
  559. #{{{  @ref-doc-only
  560. /^@ref-doc-only/ { next }
  561. #}}}
  562. #{{{  @ref-lib
  563. /^@ref-lib/ { next }
  564. #}}}
  565. #{{{  @ref-menu
  566. /^@ref-menu [0123456789]+( +((quit)|(ret)|(next)|(prev)|(kill)|([^ ()@]+)) +([^ ]+))+ +([^ ]*)$/ {
  567.    if (level!=0)
  568.       ref_error="@ref-menu only allowed on toplevel"
  569.    else {
  570.       id=substr($0,11)
  571.       if (VIEWER_ID[id]=="") {
  572.          MENU_DEF[known_menu]=$2
  573.          MENU_OPS[known_menu]=0
  574.          MENU[known_menu]=""
  575.          for (i=3;i<NF;i+=2) {
  576.             MENU_OP[known_menu"#"(MENU_OPS[known_menu]++)]=$i
  577.             MENU[known_menu]=MENU[known_menu]" "$(i+1)
  578.          }
  579.          ARGS[known_menu]=$NF
  580.          VIEWER[known_menu]="ref-viewer-"known_menu
  581.          VIEWER_ID[id]=known_menu++
  582.       }
  583.       if (cur_menu!=VIEWER_ID[id])
  584.          cur_menu=VIEWER_ID[id]
  585.    }
  586.    next
  587. }
  588. #}}}
  589. #{{{  @ref-see-also
  590. /^@ref-see-also((%%)|(%s)|[^%])*$/ {
  591.    next
  592. }
  593. #}}}
  594. #{{{  @ref-class-id
  595. /^@ref-class-id/ {
  596.    if (use_id<0+$2)
  597.       use_id=0+$2
  598.    next
  599. }
  600. #}}}
  601. #{{{  @ref-*-*-box
  602. /^@ref-(top|sub)-(start|end)-box/ {
  603.    box[$1]=substr($0 long_line,length($1)+2,8)
  604.    next
  605. }
  606. #}}}
  607. #{{{  @ref-start-picture
  608. /^@ref-start-picture *$/ {
  609.    picture=1
  610.    next
  611. }
  612. #}}}
  613. #{{{  @ref-end-picture
  614. /^@ref-end-picture *$/ {
  615.    picture=0
  616.    next
  617. }
  618. #}}}
  619. #{{{  @ref-start-item
  620. /^@ref-start-item/ {
  621.    if (picture!=0)
  622.       ref_error="item<->picture conflict"
  623.    else {
  624.       item_level++
  625.       item_txt=substr($0,17)" "
  626.       ref_first+=ref_indent
  627.       if (length(item_txt)<=ref_indent)
  628.           info_indent=substr(info_indent item_txt long_line,1,ref_first-1)
  629.       else
  630.           info_indent=info_indent item_txt"\n"substr(long_line,1,ref_first-1)
  631.    }
  632.    next
  633. }
  634. #}}}
  635. #{{{  @ref-end-item
  636. /^@ref-end-item/ {
  637.    if (item_level!=0) {
  638.       item_level--
  639.       ref_first-=ref_indent
  640.       info_indent=substr(long_line,1,ref_first-1)
  641.    } else
  642.       ref_error="no item to leave"
  643.    next
  644. }
  645. #}}}
  646. #{{{  @ref-fun
  647. /^@ref-fun/ {
  648.    if (level>0) {
  649.       if (def[level]==0) {
  650.          ref_error="new class not allowed in reused class!"
  651.          next
  652.       }
  653.       fun_header=substr($0,length($2)+11)
  654.       if (fun_header=="")
  655.          fun_header=$2
  656.       if (fun_header=="") {
  657.          ref_error="no function given"
  658.          next
  659.       }
  660. #      {{{  store link print data for flush
  661.       link_txt=info_indent"< "substr(ARGS[cur_menu],calls[level]+1,1)" > "fun_header
  662.       link_class=class_id[level]
  663. #      }}}
  664. #      {{{  look for existing function
  665.       for (i=1;i<=known_functions;i++)
  666.          if (known_f_name[i]==$2)
  667.             break
  668. #      }}}
  669.       if (i>known_functions)
  670.          known_f_name[++known_functions]=$2
  671.       calls[level]++
  672.       known_class_sets[known_id[level]]=known_class_sets[known_id[level]] " set c-" calls[level] " " 0-i
  673.    }
  674.    next
  675. }
  676. #}}}
  677. /^@[^{}@]/ {
  678.     print($0)
  679.     next
  680. }
  681. #}}}
  682. #{{{  start toplevel definition
  683. level==0 && /^@\{\{\{  [^ ]+/ {
  684.    if ($3!="") {
  685. #      {{{  error
  686.       ref_error="toplevel definition may only use one word as label!"
  687.       next
  688. #      }}}
  689.    }
  690.    level++
  691. #   {{{  init the level
  692.    calls[level]=0
  693.    call_sets=""
  694.    def[level]=1
  695.    class_name=$2
  696.    class_id[level]=use_id++
  697.    header[level]=$2
  698. #   }}}
  699. #   {{{  add to list of known
  700.    known_header[$0]=known_classes
  701.    known_prt_header[known_classes]=header[level]
  702.    known_top_class[known_classes]=class_name
  703.    known_class_chapter[known_classes]=""
  704.    known_class_id[known_classes]=class_id[level]
  705.    known_id[level]=known_classes
  706.    known_class_call[known_classes]="set ref-call "class_id[level]
  707.    known_class_browser[known_classes]=VIEWER[cur_menu]
  708.    known_class_sets[known_classes]=""
  709.    known_classes++
  710. #   }}}
  711. #   {{{  print tree header
  712.    box_type=box["@ref-top-start-box"]
  713.    box_txt=header[level]
  714.    if (title[box_txt]!="")
  715.       box_txt=title[box_txt]
  716.    if (author[header[level]]!="")
  717.       box_txt=box_txt author[header[level]] ")"
  718.    box_head=1
  719.    box_center=1
  720.    box_class=class_id[level]
  721. #   }}}
  722.    next
  723. }
  724. #}}}
  725. #{{{  end toplevel definition
  726. level==1 && /^@\}\}\}[ ]*$/ {
  727.    known_class_args[known_id[level]]=calls[level]
  728. #   {{{  print tree end header
  729.    box_type=box["@ref-top-end-box"]
  730.    box_txt=header[level]
  731.    box_head=0
  732.    box_center=1
  733.    box_class=class_id[level]
  734. #   }}}
  735. #   {{{  define toplevel access functions
  736.    top_funs=top_funs"@if-using("class_name"-TREE)(deffun "class_name"(set ref-call "class_id[level]" ref-case-fun ref-abort-unload redraw-display))@fi\n"
  737. #   }}}
  738.    print("@use("known_class_browser[known_id[level]]"-"calls[level]"-USED)")
  739.    level--
  740.    next
  741. }
  742. #}}}
  743. #{{{  start sub-class
  744. /^@\{\{\{  [^ ]+/  {
  745. #   {{{  not allowed, if not defining
  746.    if (def[level]==0) {
  747.        ref_error="new class not allowed in reused class!"
  748.        next
  749.    }
  750. #   }}}
  751. #   {{{  get name for this entry
  752.    sub_header=substr($0,7)
  753.    if (substr(sub_header,1,1)=="@")
  754.       prt_header=substr(sub_header,length($2)+2)
  755.    else
  756.       prt_header=sub_header
  757. #   }}}
  758.    if (doc_out==0){
  759. #      {{{  extend arguments
  760.       while (calls[level]>=length(ARGS[cur_menu]) ) {
  761.          for (lm=length(ARGS[cur_menu]);ADD!="*";) {
  762.             if (lm==0) {
  763.                break
  764.             } else if (substr(ADD,1,1)==substr(ARGS[cur_menu],lm,1)) {
  765.                lm=length(ARGS[cur_menu])
  766.                ADD=substr(ADD,2)"*"
  767.             } else
  768.                lm--
  769.          }
  770.          ARGS[cur_menu]=ARGS[cur_menu]substr(ADD,1,1)
  771.          ADD=substr(ADD,2)"*"
  772.       }
  773. #      }}}
  774. #      {{{  store link in ref-tree
  775.       link_txt=info_indent"< "substr(ARGS[cur_menu],calls[level]+1,1)" > "prt_header
  776.       link_class=class_id[level]
  777. #      }}}
  778.    }
  779.    calls[level]++
  780.    level++
  781. #   {{{  x=chapter id
  782.    x="" ref_chapter[1]
  783.    for (i=2;i<level;i++)
  784.       x=x "." ref_chapter[i]
  785. #   }}}
  786.    if ((i=known_header[$0])=="") {
  787.       i=known_classes
  788.       def[level]=1
  789.       class_id[level]=use_id++
  790.       class_name_used=class_name
  791. #      {{{  add to list of known
  792.       known_header[$0]=known_classes
  793.       known_prt_header[known_classes]=prt_header
  794.       known_top_class[known_classes]=class_name
  795.       known_class_chapter[known_classes]=x
  796.       known_class_id[known_classes]=class_id[level]
  797.       known_id[level]=known_classes
  798.       known_class_call[known_classes]="set ref-call "class_id[level]
  799.       known_class_browser[known_classes]=VIEWER[cur_menu]
  800.       known_class_sets[known_classes]=""
  801.       known_classes++
  802. #      }}}
  803.       header[level]=prt_header
  804. #      {{{  print tree header
  805.       box_type=box["@ref-sub-start-box"]
  806.       box_txt=header[level]
  807.       box_head=1
  808.       box_center=0
  809.       box_class=class_id[level]
  810. #      }}}
  811.    } else {
  812.       def[level]=0
  813.       class_id[level]=known_class_id[i]
  814.       class_name_used=known_top_class[i]
  815.    }
  816.    calls[level]=0
  817.    known_class_sets[known_id[level-1]]=known_class_sets[known_id[level-1]] " set c-" calls[level-1] " " class_id[level]
  818.    ind_pop[level]=item_level
  819.    ref_first-=item_level*ref_indent
  820.    info_indent=substr(long_line,1,ref_first-1)
  821.    item_level=0
  822.    next
  823. }
  824. #}}}
  825. #{{{  end sub-class
  826. /^@\}\}\}[ ]*/  {
  827.     if (def[level]) {
  828.        known_class_args[known_id[level]]=calls[level]
  829. #       {{{  print tree header
  830.        box_type=box["@ref-sub-end-box"]
  831.        box_txt=header[level]
  832.        box_head=0
  833.        box_center=0
  834.        box_class=class_id[level]
  835. #       }}}
  836.        print("@use("known_class_browser[known_id[level]]"-"calls[level]"-USED)")
  837.     }
  838.     item_level=ind_pop[level]
  839.     ref_first+=item_level*ref_indent
  840.     info_indent=substr(long_line,1,ref_first-1)
  841.     level--
  842.     ref_chapter[level]++
  843.     next
  844. }
  845. #}}}
  846. #{{{  store simple line data
  847. {
  848. #   {{{  not allowed, if not defining
  849.    if (def[level]==0) {
  850.        if ($0!="@{{{}}}")
  851.           ref_error="new text not allowed in reused class!"
  852.        next
  853.    }
  854. #   }}}
  855.    if (picture==0)
  856. #    {{{  blocking, single word storing
  857.       if (NF==0)
  858.          info_buffer[info_buffer_use++]="\n"
  859.       else
  860.          for (of=1;of<=NF;of++)
  861.             info_buffer[info_buffer_use++]=$of
  862. #    }}}
  863.    else
  864.       info_buffer[info_buffer_use++]=$0
  865. }
  866. #}}}
  867. END {
  868.    if (ref_error=="") {
  869.       if (item_level>0)
  870.          ref_error="missing end item"
  871.       else if (picture==1)
  872.          ref_error="missing end picture"
  873.       else if (tbl_size)
  874.          ref_error="missing end tbl"
  875.       else
  876. #         {{{  print functions..
  877.          if (commenting)
  878.             ref_error="open comment"
  879.          else if (known_classes==0)
  880.             ref_error="no data found"
  881.          else if (doc_out==0){
  882.             print(start_tree)
  883.             print("(demand-load(")
  884. #            {{{  forward some functions
  885.             print("(forward ref-abort-unload)(forward ref-case-fun)")
  886.             print("(defvar(ref-class ref-call ref-n ref-call-i-next ref-call-i-quit ref-call-i-back ref-call-i-kill ))")
  887.             undeclares="ref-case-fun ref-class ref-n"
  888.             unload_funs = "ref-case-fun"
  889. #            }}}
  890. #            {{{  print toplevel access functions
  891.             print(top_funs)
  892. #            }}}
  893. #            {{{  print all needed browsers
  894.             defined_vars=0
  895.             for (id in VIEWER_ID) {
  896.                cur_menu=VIEWER_ID[id]
  897. #               {{{  define missing argument variables
  898.                if (defined_vars<length(ARGS[cur_menu])) {
  899.                   printf("(defvar( ")
  900.                   while(defined_vars<length(ARGS[cur_menu])) {
  901.                      defined_vars++
  902.                      printf("c-%d ",defined_vars)
  903.                      undeclares=undeclares " c-" defined_vars
  904.                   }
  905.                   print("))")
  906.                }
  907. #               }}}
  908. #               {{{  @if-using classes, needing current browser
  909.                printf("@if-using( ")
  910.                for (j=length(ARGS[cur_menu]);j>=0;j--)
  911.                   printf(VIEWER[cur_menu]"-"j"-USED ")
  912.                print(")")
  913. #               }}}
  914. #               {{{  get ocl-source for menu string
  915.                menu=""
  916.                for (i=length(MENU[cur_menu]);i>0;i--)
  917.                   menu=" "DQ substr(MENU[cur_menu],i,1) " " menu
  918. #               }}}
  919. #               {{{  define and undeclare a macro, to generate menu strings
  920.                printf("%s","(demand-load not((defmac "VIEWER[cur_menu]"("menu" next-line "COMPLAIN" next-line ")
  921.                for (i=1;i<=5;i++) printf("%s  %s%s ",DQ,DQ,substr(ARGS[cur_menu],i,1))
  922.                printf(" next-line ")
  923.                for (i=6;i<(3*length(ARGS[cur_menu]))/4;i++) printf("%s  %s%s ",DQ,DQ,substr(ARGS[cur_menu],i,1))
  924.                print("))(undeclare("VIEWER[cur_menu]"))))")
  925. #               }}}
  926.                print("(deffun "VIEWER[cur_menu]"(")
  927.                 print(" if not(ref-call-i-quit)(")
  928.                 print("  history-edit misc ()")
  929.                 print("   insert-ascii I_QUIT")
  930.                 print("   beginning-of-line")
  931.                 print("   set-counter ref-call-i-quit store-character")
  932.                 print("   insert-ascii I_NEXT_PAGE")
  933.                 print("   beginning-of-line")
  934.                 print("   set-counter ref-call-i-next store-character")
  935.                 print("   insert-ascii I_BACK")
  936.                 print("   forward-character")
  937.                 print("   set-counter ref-call-i-back store-character")
  938.                 print("   insert-ascii I_KILL")
  939.                 print("   forward-character")
  940.                 print("   set-counter ref-call-i-kill store-character")
  941.                 print("   newline-and-indent")
  942.                 print(" )fi")
  943.                 print(" do(")
  944. #                 {{{  call help
  945.                  print("  local(modify-behaviour )( set modify-behaviour ref-class help)")
  946. #                 }}}
  947.                  print("  if not(in-prompt)(")
  948. #                  {{{  complain and return
  949.                   print("   message("COMPLAIN")")
  950.                   print("   show-cursor 15")
  951.                   print("   set ref-call 0")
  952.                   print("   return-from-macro")
  953. #                  }}}
  954.                  print("  )else(")
  955. #                  {{{  menu loop
  956.                   print("   do(")
  957. #                   {{{  menu
  958.                    print("    begin-prompt-macro")
  959.                    print("    set ref-call "MENU_DEF[cur_menu])
  960.                    print("    local(ref-n)(")
  961.                     print("     case")
  962.                     pre_add="                         "
  963.                     for (i=0;i<=length(ARGS[cur_menu]);i++) {
  964.                        if (i!=0) menu=menu " " DQ "  " DQ substr(ARGS[cur_menu],i,1)
  965.                        print("      ("pre_add"=(ref-n 0)(menu-counter ref-call(" menu ")))")
  966.                        if (i==0) pre_add="pre(set ref-n -(ref-n 1))"
  967.                     }
  968.                     print("     esac")
  969.                    print("    )")
  970.                    print("    end-prompt-macro")
  971. #                   }}}
  972. #                   {{{  decode command
  973.                    pre="                               "
  974.                    print("    case")
  975.                     for (i=0;i<MENU_OPS[cur_menu];i++) {
  976.                      printf("     ("pre"=(ref-call 0)(")
  977.                      pre="pre(set ref-call -(ref-call 1))"
  978.                      if (MENU_OP[cur_menu"#"i]=="quit")
  979.                       print("screen-off insert-ascii ref-call-i-quit screen-on set ref-call 1 return-from-macro))")
  980.                      else if (MENU_OP[cur_menu"#"i]=="ret")
  981.                       print("screen-off insert-ascii ref-call-i-quit screen-on return-from-macro))")
  982.                      else if (MENU_OP[cur_menu"#"i]=="next")
  983.                       print(" insert-ascii ref-call-i-next ))")
  984.                      else if (MENU_OP[cur_menu"#"i]=="prev")
  985.                       print(" insert-ascii ref-call-i-back ))")
  986.                      else if (MENU_OP[cur_menu"#"i]=="kill")
  987.                       print(" insert-ascii ref-call-i-kill ))")
  988.                      else
  989.                       print(" insert-ascii ref-call-i-quit set ref-call eval("MENU_OP[cur_menu"#"i]")))")
  990.                     }
  991.                    print("    default(")
  992.                      print("     screen-off insert-ascii ref-call-i-quit screen-on")
  993.                      print("     case")
  994.                      print("      (or(>(ref-call ref-n) =(ref-n 0) <=(ref-call 0))(message("DQ"invalid "DQ"  "DQ"input! )show-cursor 15 return-from-macro))")
  995.                       for (i=1;i<=length(ARGS[cur_menu]);i++) {
  996.                          printf("      (pre(set ref-call -(ref-call 1))=(ref-call 0)")
  997.                          printf("(")
  998.                          printf("@if-using( ")
  999.                          for (u=i;u<=length(ARGS[cur_menu]);u++)
  1000.                             printf(VIEWER[cur_menu]"-"u"-USED ")
  1001.                          printf(")set ref-call c-" i" @fi)")
  1002.                          print(")")
  1003.                       }
  1004.                      print("     default")
  1005.                       print("      (message("DQ"invalid "DQ"  "DQ"input! )show-cursor 15 return-from-macro)")
  1006.                      print("     esac")
  1007.                      print("     ref-case-fun)")
  1008.                     print("    esac")
  1009. #                   }}}
  1010.                   print("   )while in-prompt")
  1011. #                  }}}
  1012.                  print("  )fi")
  1013.                 print(" )while =(ref-call 0)")
  1014.                print("))")
  1015.                print("@fi")
  1016.             }
  1017. #            }}}
  1018. #            {{{  print case function
  1019. #            {{{  init loop
  1020.             part=0
  1021.             added=0
  1022.             end_string=""
  1023.             case_no=0
  1024.             handled=0
  1025. #            }}}
  1026. #            {{{  forward complain/extension fun
  1027.             print("(forward ref-case-fun-"part")")
  1028.             undeclares=undeclares" ref-case-fun-"part
  1029.             unload_funs=unload_funs" ref-case-fun-"part
  1030. #            }}}
  1031.             print("(deffun ref-case-fun(")
  1032.             print(" local(ref-class ref-n)(")
  1033.             end_string=")))"
  1034. #            {{{  print used functions
  1035.             if (known_functions>0) {
  1036.                print("  case")
  1037.                for (i=1;i<=known_functions;i++) {
  1038.                   print("   (pre(set ref-call -(ref-call "0-i-added"))=(ref-call 0)(set ref-call eval ("known_f_name[i]")))")
  1039.                   added=0-i
  1040.                   case_no++
  1041.                }
  1042.                print("  esac")
  1043.             }
  1044. #            }}}
  1045.             a=0
  1046.             handled=0
  1047.             i=0
  1048.             ifs=" "
  1049.             for (x=0;x<known_menu;x++)
  1050.                ifs=ifs VIEWER[x]"-"0"-USED "
  1051.             print("  @if-using("ifs")set ref-n 0 @fi")
  1052.             print("  case")
  1053.             end_string="esac "end_string
  1054.             while (handled<known_classes) {
  1055.                if (i==known_classes) {
  1056. #                  {{{  start next loop for next number of sub-trees
  1057.                   i=0
  1058.                   a++
  1059.                   print("  default(local(c-"a")(")
  1060.                   for (x=0;x<known_menu;x++)
  1061.                      ifs=ifs VIEWER[x]"-"a"-USED "
  1062.                   print("   @if-using("ifs")set ref-n "a" @fi")
  1063.                   print("  case")
  1064.                   end_string="esac))"end_string
  1065. #                  }}}
  1066.                } else {
  1067.                   if (known_class_args[i]==a) {
  1068. #                     {{{  print case entry
  1069.                      print("   (pre(set ref-call -(ref-call "0+known_class_id[i]-added"))or(0 @if-using(U-C-"known_class_id[i]")=(ref-call 0)@fi)")
  1070.                      print("     (@if-using(U-C-"known_class_id[i]")"known_class_sets[i]" set ref-class "known_class_id[i]" "known_class_browser[i] " return-from-macro @use not(U-C-"known_class_id[i]")@fi))")
  1071.                      added=known_class_id[i]
  1072.                      handled++
  1073.                      case_no+=1.1+0.3*a
  1074. #                     }}}
  1075. #                     {{{  maybe gen new function, to prevent big macros
  1076.                      if (case_no>case_entry_lg) {
  1077.                         print("  default(ref-case-fun-"part")"end_string)
  1078.                         print("(forward ref-case-fun-"part+1")")
  1079.                         undeclares=undeclares" ref-case-fun-"part+1
  1080.                         unload_funs=unload_funs" ref-case-fun-"part+1
  1081.                         print("(deffun ref-case-fun-"part"(")
  1082.                         print("  case")
  1083.                         end_string="esac))"
  1084.                         part++
  1085.                         case_no=0
  1086.                      }
  1087. #                     }}}
  1088.                   }
  1089.                   i++
  1090.                }
  1091.             }
  1092.             print("  default(ref-case-fun-"part")"end_string)
  1093.             print("(deffun ref-case-fun-"part"(message ("COMPLAIN ")set ref-call 0))")
  1094. #            }}}
  1095. #            {{{  ref-abort-unload
  1096.             print("(deffun ref-abort-unload(load-function not("unload_funs)
  1097. #            {{{  all needed browsers
  1098.             for (cur_menu=0;cur_menu<known_menu;cur_menu++) {
  1099.                printf("@if-using( ")
  1100. #               {{{  @if-using classes, needing current browser
  1101.                for (j=length(ARGS[cur_menu]);j>=0;j--)
  1102.                   printf(VIEWER[cur_menu]"-"j"-USED ")
  1103. #               }}}
  1104.                print(")"VIEWER[cur_menu]" @fi")
  1105.             }
  1106. #            }}}
  1107.             print(")))")
  1108. #            }}}
  1109. #            {{{  abort-hook-add
  1110.             print("@if-using not(ABORT-HOOK-ADD)@use (ABORT-HOOK-ADD)( defmac abort-hook-add ( ) )@fi")
  1111.             print("(defmac abort-hook-add-saved(abort-hook-add))(undeclare(abort-hook-add))")
  1112.             print("(defmac abort-hook-add(set modify-behaviour 0))(undeclare(abort-hook-add-saved))")
  1113. #            }}}
  1114. #            {{{  undeclares
  1115.             print("(undeclare("undeclares" ref-abort-unload")
  1116. #            {{{  all needed browsers
  1117.             for (cur_menu=0;cur_menu<known_menu;cur_menu++) {
  1118.                printf("@if-using( ")
  1119. #               {{{  @if-using classes, needing current browser
  1120.                for (j=length(ARGS[cur_menu]);j>=0;j--)
  1121.                   printf(VIEWER[cur_menu]"-"j"-USED ")
  1122. #               }}}
  1123.                print(")"VIEWER[cur_menu]" @fi")
  1124.             }
  1125. #            }}}
  1126.             print("))")
  1127. #            }}}
  1128.             print("))")
  1129.             print(end_tree)
  1130. #            {{{  use not all viewer uses
  1131.             print("@use not( ")
  1132.             for (x=0;x<known_menu;x++) {
  1133.                for (i=length(ARGS[x]);i>=0;i--)
  1134.                   printf(" "VIEWER[x]"-"i"-USED")
  1135.                print("")
  1136.             }
  1137.             print(")")
  1138. #            }}}
  1139.          }
  1140. #         }}}
  1141.    }
  1142.    if (ref_error!="" && ref_error!="-") {
  1143.       print("@error EOF:" ref_error)
  1144.    }
  1145. }
  1146. HERE
  1147. #}}}
  1148. #{{{  nroff stuff
  1149. cat >>$TMP_DIR/ref.tmp.r.awk <<\HERE
  1150. #{{{  copy $i to fi[i] and quote roff critical chars
  1151. { for (i=0;i<=NF;i++) {
  1152.       field[i]=""
  1153.       for (l=1;l<=length($i);l++) {
  1154.          c=substr($i,l,1)
  1155.          if (c==".")
  1156.             field[i]=field[i]"\\&"c
  1157.          else if (c=="\\")
  1158.             field[i]=field[i]"\\e"
  1159.          else
  1160.             field[i]=field[i]c
  1161.       }
  1162.    }
  1163.    if (substr(field[0],1,1)=="'")
  1164.       field[0]="\&"field[0]
  1165. }
  1166. #}}}
  1167. #{{{  header
  1168. /^@\{\{\{  @ref-header +[^ ]* *$/ {
  1169.    header_name=$3
  1170.    next
  1171. }
  1172. header_name!="" {
  1173.    if ($1=="@ref-title")
  1174.       title[header_name]=substr(field[0],length($1)+2)
  1175.    else if ($1=="@ref-author")
  1176.       author[header_name]=author[header_name]".AU\n"substr(field[0],length($1)+2)"\n"
  1177.    else if ($1=="@}}}")
  1178.       header_name=""
  1179.    else
  1180.       abstract[header_name]=abstract[header_name] field[0] "\n"
  1181.    next
  1182. }
  1183. #}}}
  1184. #{{{  flushing text to out
  1185. #{{{  start-reference-chapter
  1186. ref_chapt_start!="" {
  1187.    txt=ref_chapt_start
  1188.    txt=".sp\n" new_para "\n" bold ref_chapt_start norm
  1189.    if (doc_out==0)
  1190.       printf(start_ref,class_name)
  1191.    print(txt)
  1192.    if (doc_out==0)
  1193.       print(end_ref)
  1194.    ref_chapt_start=""
  1195. }
  1196. #}}}
  1197. #{{{  end-reference-chapter
  1198. ref_chapt_end==1 {
  1199.    if (doc_out==0)
  1200.       printf(start_ref,class_name)
  1201.    print(".br")
  1202.    if (doc_out==0)
  1203.       print(end_ref)
  1204.    ref_chapt_end=0
  1205. }
  1206. #}}}
  1207. #{{{  special line and buffer used -> flush it
  1208. /^(@|$)/ && (ref_buffer!="" || (ritem_txt!="\n" && level>0)) {
  1209.    if (doc_out==0)
  1210.       printf(start_ref,class_name)
  1211.    if (picture!=1) {
  1212.       print(new_para)
  1213.       if (item_level>0)
  1214.          new_para=".IP "DQ DQ
  1215.       else
  1216.          new_para=".LP"
  1217.       ritem_txt="\n"
  1218.    }
  1219.    print(ref_buffer)
  1220.    if (doc_out==0)
  1221.       print(end_ref)
  1222.    ref_buffer=""
  1223. }
  1224. #}}}
  1225. #}}}
  1226. #{{{  ref/opp statements
  1227. #{{{  tbl-handling
  1228. #{{{  start-tbl
  1229. /^@ref-start-tbl/ {
  1230.    if (tbl_size || picture)
  1231.       ref_error="tbl not allowed here"
  1232.    else {
  1233. #      {{{  get head/tail string for info
  1234.       rtbl_head=""
  1235.       rtbl_form=""
  1236.       x=""
  1237.       y=""
  1238.       for (of=2;of<NF;)
  1239.          if ($of=="@@")
  1240.             if (of>2 && of<NF) {
  1241.                x=" | l | "
  1242.                y=tbl_limiter" "
  1243.                of++
  1244.             } else {
  1245.                ref_error="invalid limiter place"
  1246.                next
  1247.             }
  1248.         else {
  1249.            rtbl_lim[tbl_size]=y tbl_limiter
  1250.            if (tbl_size>0) {
  1251.               rtbl_form=rtbl_form x
  1252.               rtbl_head=rtbl_head y tbl_limiter
  1253.            }
  1254.            rtbl_head=rtbl_head field[of]
  1255.            rtbl_form=rtbl_form"l"
  1256.            tbl_size++
  1257.            x=" | "
  1258.            y=""
  1259.            of+=2
  1260.         }
  1261. #      }}}
  1262.       if (tbl_size==0)
  1263.          ref_error="no tbl parameter given"
  1264.       else {
  1265. #         {{{  print reference
  1266.          if (doc_out==0)
  1267.             printf(start_ref,class_name)
  1268.          print(".TS")
  1269.          print("center box tab("tbl_limiter");")
  1270.          print(rtbl_form".")
  1271.          print(rtbl_head)
  1272.          print("_")
  1273.          if (doc_out==0)
  1274.             print(end_ref)
  1275. #         }}}
  1276.       }
  1277.    }
  1278.    next
  1279. }
  1280. #}}}
  1281. #{{{  end-tbl
  1282. /^@ref-end-tbl/ {
  1283.    if (tbl_size==0)
  1284.       ref_error="no tbl active"
  1285.    else {
  1286.       tbl_size=0
  1287. #      {{{  print reference
  1288.       if (doc_out==0)
  1289.          printf(start_ref,class_name)
  1290.       print(".TE")
  1291.       if (doc_out==0)
  1292.          print(end_ref)
  1293. #      }}}
  1294.    }
  1295.    next
  1296. }
  1297. #}}}
  1298. #{{{  inside tbl, no commands, other the @use,@if-using,@fi are allowed
  1299. /^@[^@ ]/ && tbl_size>0 {
  1300.    if ((substr(field[0],1,9)!="@if-using")&&(substr(field[0],1,3)!="@fi")&&(substr(field[0],1,4)!="@use")) {
  1301.       ref_error="tbl crashed with "field[0]
  1302.       next
  1303.    }
  1304. }
  1305. #}}}
  1306. #{{{  text -> format it
  1307. /^([^@]|@@|$)/ && tbl_size>0 {
  1308. #   {{{  decode and format table data
  1309.    rtxt=""
  1310.    x=0
  1311.    y=""
  1312.    for (of=1;of<=NF;of++)
  1313.       if (field[of]=="@@") {
  1314.          x++
  1315.          y=""
  1316.          rtxt=rtxt rtbl_lim[x]
  1317.       } else {
  1318.          rtxt=rtxt y field[of]
  1319.          y=" "
  1320.       }
  1321. #   }}}
  1322. #   {{{  print reference
  1323.    if (doc_out==0)
  1324.       printf(start_ref,class_name)
  1325.    print(rtxt)
  1326.    if (doc_out==0)
  1327.       print(end_ref)
  1328. #   }}}
  1329.    next
  1330. }
  1331. #}}}
  1332. #}}}
  1333. #{{{  @ref-doc-only
  1334. /^@ref-doc-only/ {
  1335.    doc_out=1
  1336.    next
  1337. }
  1338. #}}}
  1339. #{{{  @ref-lib
  1340. /^@ref-lib/ { next }
  1341. #}}}
  1342. #{{{  @ref-menu
  1343. /^@ref-menu [0123456789]+( +((quit)|(ret)|(next)|(prev)|(kill)|([^ ()@]+)) +([^ ]+))+ +([^ ]*)$/ {
  1344.    next
  1345. }
  1346. #}}}
  1347. #{{{  @ref-see-also
  1348. /^@ref-see-also((%%)|(%s)|[^%])*$/ {
  1349.    SEE_ALSO=substr(field[0],length("@ref-see-also")+2)
  1350.    next
  1351. }
  1352. #}}}
  1353. #{{{  @ref-class-id
  1354. /^@ref-class-id/ {
  1355.    next
  1356. }
  1357. #}}}
  1358. #{{{  @ref-*-*-box
  1359. /^@ref-(top|sub)-(start|end)-box/ {
  1360.    next
  1361. }
  1362. #}}}
  1363. #{{{  @ref-start-picture
  1364. /^@ref-start-picture *$/ {
  1365.    picture=1
  1366.    if (doc_out==0)
  1367.       printf(start_ref,class_name)
  1368.    print(new_para"\n.DS")
  1369.    if (doc_out==0)
  1370.       print(end_ref)
  1371.    new_para=""
  1372.    next
  1373. }
  1374. #}}}
  1375. #{{{  @ref-end-picture
  1376. /^@ref-end-picture *$/ {
  1377.    picture=0
  1378.    if (doc_out==0)
  1379.       printf(start_ref,class_name)
  1380.    print(".DE")
  1381.    if (doc_out==0)
  1382.       print(end_ref)
  1383.    next
  1384. }
  1385. #}}}
  1386. #{{{  @ref-start-item
  1387. /^@ref-start-item/ {
  1388.    if (picture!=0)
  1389.       ref_error="item<->picture conflict"
  1390.    else {
  1391.       item_level++
  1392.       ritem_txt=substr(field[0],17)" "
  1393.       for (of=length(ritem_txt);of>0;of--)
  1394.          if (substr(ritem_txt,of,1)==DQ)
  1395.             ritem_txt=substr(ritem_txt,1,of-1)DQ substr(ritem_txt,of)
  1396.       new_para=".IP "DQ ritem_txt DQ " "
  1397.       if (item_level>1)
  1398.          new_para=".RS\n"new_para
  1399.    }
  1400.    next
  1401. }
  1402. #}}}
  1403. #{{{  @ref-end-item
  1404. /^@ref-end-item/ {
  1405.    if (item_level!=0) {
  1406.       if (doc_out==0)
  1407.          printf(start_ref,class_name)
  1408.       if (ritem_txt!="\n")
  1409.          print(new_para)
  1410.       if (item_level>1)
  1411.          print(".RE")
  1412.       if (doc_out==0)
  1413.          print(end_ref)
  1414.       item_level--
  1415.       if (item_level>0)
  1416.          new_para=".IP "DQ DQ " "
  1417.       else
  1418.          new_para=".LP"
  1419.    } else
  1420.       ref_error="no item to leave"
  1421.    next
  1422. }
  1423. #}}}
  1424. #{{{  @ref-fun
  1425. /^@ref-fun/ {
  1426.    next
  1427. }
  1428. #}}}
  1429. /^@[^{}@]/ {
  1430.     if (doc_out==0) print(field[0])
  1431.     next
  1432. }
  1433. #}}}
  1434. #{{{  start toplevel definition
  1435. level==0 && /^@\{\{\{  [^ ]+/ {
  1436.    if (NF>=3) {
  1437. #      {{{  error
  1438.       ref_error="toplevel definition may only use one word as label!"
  1439.       next
  1440. #      }}}
  1441.    }
  1442.    level++
  1443. #   {{{  init the level
  1444.    def[level]=1
  1445.    class_name=field[2]
  1446.    ref_chapter[1]="1"
  1447.    header[level]=substr(field[0],7)
  1448.    if (title[$2]=="")
  1449.       title[$2]=field[2]
  1450. #   }}}
  1451. #   {{{  add to list of known
  1452.    known_header[field[0]]=known_classes
  1453.    known_prt_header[known_classes]=header[level]
  1454.    known_top_class[known_classes]=class_name
  1455.    known_class_chapter[known_classes]=""
  1456.    known_id[level]=known_classes
  1457.    known_classes++
  1458. #   }}}
  1459. #   {{{  print ref header
  1460.    if (doc_out==0)
  1461.       printf(start_ref,class_name)
  1462.    if (ref_spaces>0)
  1463.       print(".ad b")
  1464.    else
  1465.       print(".ad l")
  1466.    print(".TL")
  1467.    print(title[$2])
  1468.    printf("%s",author[$2])
  1469.    if (abstract[$2]!="")
  1470.       printf(".AB no\n%s.AE\n",abstract[$2])
  1471.    if (doc_out==0)
  1472.       print(end_ref)
  1473. #   }}}
  1474.    next
  1475. }
  1476. #}}}
  1477. #{{{  end toplevel definition
  1478. level==1 && /^@\}\}\}[ ]*$/ {
  1479.    ref_chapt_end=1
  1480.    level--
  1481.    next
  1482. }
  1483. #}}}
  1484. #{{{  start sub-class
  1485. /^@\{\{\{  [^ ]+/  {
  1486. #   {{{  not allowed, if not defining
  1487.    if (def[level]==0) {
  1488.        ref_error="new class not allowed in reused class!"
  1489.        next
  1490.    }
  1491. #   }}}
  1492. #   {{{  get name for this entry
  1493.    sub_header=substr(field[0],7)
  1494.    if (substr(sub_header,1,1)=="@")
  1495.       prt_header=substr(sub_header,length(field[2])+2)
  1496.    else
  1497.       prt_header=sub_header
  1498. #   }}}
  1499.    level++
  1500. #   {{{  x=chapter id
  1501.    x="" ref_chapter[1]
  1502.    for (i=2;i<level;i++)
  1503.       x=x "." ref_chapter[i]
  1504. #   }}}
  1505.    if ((i=known_header[field[0]])=="") {
  1506.       i=known_classes
  1507.       def[level]=1
  1508.       class_name_used=class_name
  1509. #      {{{  add to list of known
  1510.       known_header[field[0]]=known_classes
  1511.       known_prt_header[known_classes]=prt_header
  1512.       known_top_class[known_classes]=class_name
  1513.       known_class_chapter[known_classes]=x
  1514.       known_id[level]=known_classes
  1515.       known_classes++
  1516. #      }}}
  1517.       header[level]=prt_header
  1518. #      {{{  print ref header
  1519.       ref_chapter[level]=1
  1520.       ref_chapt_start=x " " prt_header
  1521. #      }}}
  1522.    } else {
  1523.       def[level]=0
  1524.       class_name_used=known_top_class[i]
  1525. #      {{{  print ref header
  1526. #      {{{  get text
  1527.       if (SEE_ALSO=="")
  1528.          y=""
  1529.       else {
  1530.         if (class_name==class_name_used)
  1531.            yy=known_class_chapter[i] " " known_prt_header[i]
  1532.          else if (known_class_chapter[i]!="")
  1533.            yy=known_top_class[i] " - " known_class_chapter[i] " " known_prt_header[i]
  1534.          else
  1535.             yy=known_top_class[i]
  1536.          y=sprintf(SEE_ALSO,yy)
  1537.       }
  1538. #      }}}
  1539. #      {{{  get see-also string
  1540.       if (substr(y,1,1)=="C")
  1541.          ref_chapt_start=x " " substr(y,2)
  1542.       else {
  1543.          if (doc_out==0)
  1544.             printf(start_ref,class_name)
  1545.          print(new_para"\n"y)
  1546.          if (doc_out==0)
  1547.             print(end_ref)
  1548.       }
  1549. #      }}}
  1550. #      }}}
  1551.    }
  1552.    next
  1553. }
  1554. #}}}
  1555. #{{{  end sub-class
  1556. /^@\}\}\}[ ]*/  {
  1557.     if (def[level])
  1558.        ref_chapt_end=1
  1559.     level--
  1560.     ref_chapter[level]++
  1561.     next
  1562. }
  1563. #}}}
  1564. #{{{  store simple line data
  1565. {
  1566. #   {{{  not allowed, if not defining
  1567.    if (def[level]==0) {
  1568.        if (field[0]!="@{{{}}}")
  1569.           ref_error="new text not allowed in reused class!"
  1570.        next
  1571.    }
  1572. #   }}}
  1573. #   {{{  reference data as text
  1574.    if (ref_buffer!="") ref_buffer = ref_buffer "\n"
  1575.    ref_buffer=ref_buffer field[0]
  1576. #   }}}
  1577. }
  1578. #}}}
  1579. END {
  1580.    if (ref_error!="" && ref_error!="-")
  1581.       print("@error EOF:" ref_error)
  1582. }
  1583. HERE
  1584. #}}}
  1585. #{{{  shrink stuff
  1586. cat >>$TMP_DIR/ref.tmp.s.awk <<\HERE
  1587. BEGIN {
  1588.    iflevel=0
  1589.    ficount=0
  1590.    uses="";useid=1
  1591.    refclass="";refend=0
  1592. }
  1593. #{{{  store @use's
  1594. /^@use *(not *)?\([^)]+\) *$/ {
  1595.    if (useused[$0]!=useid) {
  1596.       uses=uses $0 "\n"
  1597.       useused[$0]=useid
  1598.    }
  1599.  
  1600.   next
  1601. }
  1602. #}}}
  1603. #{{{  start reference text
  1604. /^@reference-begin(-class +[^ ]+)? *$/ {
  1605.    if (refend==1 && refclass==$0)
  1606.       refend=0
  1607.    else {
  1608.       if (refend==1) {
  1609.          print("@reference-end")
  1610.          refend=0
  1611.       }
  1612.       print($0)
  1613.       refclass=$0
  1614.    }
  1615.    next
  1616. }
  1617. #}}}
  1618. #{{{  count reference-end
  1619. /^@reference-end *$/ {
  1620.    refend=1
  1621.    next
  1622. }
  1623. #}}}
  1624. #{{{  switch to other @if
  1625. /^@if-using *(not *)?\([^)]+\) *(;.*)?$/ {
  1626.    if (ficount>0) {
  1627.       if (ifuse[iflevel-ficount]!=$0) {
  1628.          if (refend==1) {
  1629.             print("@reference-end")
  1630.             refclass=""
  1631.             refend=0
  1632.          }
  1633.          if (uses!="") {
  1634.             printf("%s",uses)
  1635.             uses=""
  1636.             useid++
  1637.          }
  1638. #         awk cannot handle do-while loops in general
  1639.          if (ficount>0)
  1640.             while (ficount>0) {
  1641.                print("@fi")
  1642.                iflevel--
  1643.                ficount--
  1644.             }
  1645.          print($0)
  1646.          ifuse[iflevel++]=$0
  1647.       } else
  1648.          ficount--
  1649.    } else {
  1650.       if (refend==1) {
  1651.          print("@reference-end")
  1652.          refclass=""
  1653.          refend=0
  1654.       }
  1655.       if (uses!="") {
  1656.          printf("%s",uses)
  1657.          uses=""
  1658.          useid++
  1659.       }
  1660.       print($0)
  1661.       ifuse[iflevel++]=$0
  1662.    }
  1663.    next
  1664. }
  1665. #}}}
  1666. #{{{  @fi count
  1667. /^@fi *$/ {
  1668.    ficount++
  1669.    next
  1670. }
  1671. #}}}
  1672. #{{{  flush reference-end
  1673. refend!=0 {
  1674.    print("@reference-end")
  1675.    refclass=""
  1676.    refend=0
  1677. }
  1678. #}}}
  1679. #{{{  flush fi
  1680. ficount>0 {
  1681.    if (refend==1) {
  1682.       print("@reference-end")
  1683.       refend=0
  1684.    }
  1685.    if (ficount>0)
  1686.       while (ficount>0) {
  1687.          if (uses!="") {
  1688.             printf("%s",uses)
  1689.             uses=""
  1690.             useid++
  1691.          }
  1692.          print("@fi")
  1693.          iflevel--
  1694.          ficount--
  1695.       }
  1696. }
  1697. #}}}
  1698. #{{{  print text
  1699. { print }
  1700. #}}}
  1701. END {
  1702.    if (refend==1) {
  1703.       print("@reference-end")
  1704.       refend=0
  1705.    }
  1706.    while (ficount-->0)
  1707.       print("@fi")
  1708. }
  1709. HERE
  1710. #}}}
  1711. #}}}
  1712.  
  1713. if test $3x = roffx
  1714. then
  1715. #   {{{  do roff output
  1716.    echo "@ref-doc-only" >$TMP_DIR/ref.tmp.0
  1717.    $1 -f $TMP_DIR/ref.tmp.r.awk $TMP_DIR/ref.tmp.0 $2
  1718. #   }}}
  1719. else
  1720. #   {{{  generate ocl-source for reference-file/reference-browser
  1721.    if test $3x != x
  1722.    then
  1723.       settings="$2$3"
  1724.    else
  1725.       settings="/dev/null"
  1726.    fi
  1727.  
  1728.    using=`$1 '/^@ref-lib/{printf(" "substr($0,11+length($2)))}' $settings $2`
  1729.    files=`$1 'BEGIN{lib[1]=1}/^@ref-lib/{lib[$2]=1}END{for(a in lib)if(a!=1)print(a)}' $settings $2`
  1730.  
  1731.    echo "@use($using)" >$TMP_DIR/ref.tmp.0
  1732.    echo "@use not($using)" >$TMP_DIR/ref.tmp.1
  1733.  
  1734.    ( $1 -f $TMP_DIR/ref.tmp.o.awk $settings $TMP_DIR/ref.tmp.0 $files $settings $2 $TMP_DIR/ref.tmp.1;
  1735.      $1 -f $TMP_DIR/ref.tmp.r.awk $settings $TMP_DIR/ref.tmp.0 $files $settings $2 $TMP_DIR/ref.tmp.1
  1736.    ) | $1 -f $TMP_DIR/ref.tmp.s.awk
  1737. #   }}}
  1738. fi
  1739.