home *** CD-ROM | disk | FTP | other *** search
/ Programming Languages Suite / ProgramD2.iso / Database / CLIPR502.DOS / SOURCE / SAMPLE / DOT.PRG < prev    next >
Encoding:
Text File  |  1993-02-15  |  108.9 KB  |  5,280 lines

  1. /***
  2. *
  3. * Dot.prg
  4. *
  5. * Dot-prompt interpreter written in Clipper.
  6. *
  7. * Copyright (c) 1986-1993, Computer Associates International, Inc.
  8. * All rights reserved.
  9. * NOTE
  10. * ----
  11. * DOT is offered as an example of Clipper capabilities.  It does
  12. * not constitute a working dBASE interpreter.
  13. *
  14. *
  15. * PROGRAM OVERVIEW
  16. * ----------------
  17. * DOT is an interpreter for some of the commands in the Clipper command
  18. * set.  DOT consists of a stack, a parser to fill it, procedure driven
  19. * stack analyzers, list and expression building functions, command line
  20. * execution procedures, etc.
  21. *
  22. * After a command has been entered the verb analyzer checks the stack
  23. * for an equal sign after the first identifier.  If an assignment is
  24. * found, the analyzer procedure macro is set to "ASSIGN".  If not, the
  25. * analyzer searches the verb list for the existence of the first stack
  26. * item.  If a match is found, it is checked for correct abbreviation.
  27. * If it is correct, the analysis procedure macro is initialized to the
  28. * procedure name found in the analyzer procedure list.  If the item
  29. * was not found or failed the abbreviation test, the analyzer macro is
  30. * set to "UNKNOWN".  The analyzer procedure is used to set the Class
  31. * Execution procedure macro, execution flags and Command Line
  32. * Substitution macros.  If an assignment or a variable is to be
  33. * created or deleted, it is done next, in the top most level of DOT.
  34. * One of six Class Execution procedures is called next, based on what
  35. * was found on the stack.  The called procedure contains Clipper
  36. * command strings with substitution macros used in the variable
  37. * portion of the line.  The command is selected with the execution
  38. * flag set in the analyzer.  After the command has been executed, it
  39. * is placed into the History array.  The control variables and command
  40. * line macros are reset, and the loop returns to the top, ready for
  41. * another command.
  42. * What ever you want to do, DOT can be tailored to your needs by
  43. * adding PROCEDUREs and FUNCTIONs to form new commands.  A command can
  44. * be appended to DOT by adding the verb and the matching analysis
  45. * procedure name to the verb and analyzer lists. Next, decide on the
  46. * Class Execution procedure you want to execute your command in, and
  47. * add another DO CASE switch variable to the PUBLIC switch list at the
  48. * beginning of the DOT procedure.  The analysis procedure can be added
  49. * after you have selected the PROCEDURE and switch names.  These
  50. * procedures and/or functions that you define can be made up of any
  51. * combination of Clipper, "C", or ASSEMBLY routines. They, in turn,
  52. * are interfaced to DOT by using Clipper's EXTEND system and EXTERNAL
  53. * references. The EXTERNALs can either by added directly to DOT, your
  54. * .PRG file, or compiled as a seperate file and included in the link
  55. * line as an object module.
  56. *
  57. */
  58.  
  59. clear
  60.  
  61. ** set CALLS class flags public **
  62. public CALLS1, CALLS2, CALLS3, CALLS4, CALLS5, CALLS6, CALLS7
  63.  
  64. ** set DBF_NTX class flags public **
  65. public DBF_NTX1, DBF_NTX2, DBF_NTX3, DBF_NTX4, DBF_NTX5, DBF_NTX6
  66. public DBF_NTX7, DBF_NTX8, DBF_NTX9, DBF_NTX10, DBF_NTX11, DBF_NTX12
  67. public DBF_NTX13, DBF_NTX14, DBF_NTX15, DBF_NTX16, DBF_NTX17, DBF_NTX18
  68. public DBF_NTX19, DBF_NTX20, DBF_NTX21, DBF_NTX22, DBF_NTX23, DBF_NTX24
  69. public DBF_NTX25, DBF_NTX26, DBF_NTX27, DBF_NTX28, DBF_NTX29, DBF_NTX30
  70. public DBF_NTX31, DBF_NTX32, DBF_NTX33, DBF_NTX34, DBF_NTX35, DBF_NTX36
  71.  
  72. ** set ERRS class flags public **
  73. public ERRS1, ERRS2, ERRS3, ERRS4, ERRS5, ERRS6, ERRS7, ERRS8, ERRS9
  74. public ERRS10, ERRS11, ERRS12, ERRS13, ERRS14, ERRS15
  75.  
  76. ** set SCRN class flags public **
  77. public SCRN1, SCRN2, SCRN3, SCRN4, SCRN5, SCRN6, SCRN7, SCRN8, SCRN9
  78. public SCRN10, SCRN11, SCRN12, SCRN13, SCRN14, SCRN15, SCRN16, SCRN17
  79. public SCRN18, SCRN19, SCRN20, SCRN21, SCRN22, SCRN23, SCRN24, SCRN25
  80. public SCRN26, SCRN27, SCRN28
  81.  
  82. ** set SETS class flags public **
  83. public SETS1, SETS2, SETS3, SETS4, SETS5, SETS6, SETS7, SETS8, SETS9
  84. public SETS10, SETS11, SETS12, SETS13, SETS14, SETS15, SETS16, SETS17
  85. public SETS18, SETS19, SETS20, SETS21, SETS22
  86.  
  87. ** set VARS class flags public **
  88. public VARS1, VARS2, VARS3, VARS4, VARS5, VARS6, VARS7, VARS8, VARS9
  89. public VARS10, VARS11, VARS12
  90.  
  91. ** set data and index file status flags public **
  92. public DBF_OPEN, NTX_OPEN
  93.  
  94. ** set command line execution macro variables public **
  95. public box_exp, coord1, coord2, coord3, coord4, dbf_file, dest, exp1
  96. public exp2, exp3, get_exp, get_pict, list0, list1, list2, list3, list4
  97. public list5, list6, list7, list8, list9, ntx_file, rng_exp1, rng_exp2
  98. public say_exp, say_pict, source, var1
  99.  
  100. ** set non-releasable macro variables **
  101. public alias, filter, range1, range2, relation, valid_exp
  102.  
  103. ** initialize non-releasable macro variables **
  104. store "" to alias, filter, range1, range2, relation, valid_exp
  105.  
  106. ** set conditional and scoping system variables public **
  107. public condition, rewind_dbf, scope
  108.  
  109. ** set internal status flags public **
  110. public color_stat, confr_stat, delim_stat, exact_stat, inten_stat
  111.  
  112. ** initialize internal status flags **
  113. color_stat = "7/0"
  114. confr_stat = "OFF"
  115. delim_stat = "OFF"
  116. exact_stat = "OFF"
  117. inten_stat = "ON"
  118.  
  119. ** set internal control variables public **
  120. public bottom_on, cmd_line, error_on, executor, hist_max, lex_proc
  121. public lex_list, max_hist, save_col, save_row, set_list, set_proc
  122. public stack_size, verb_list, dot_vers
  123.  
  124. ** initialize internal search list variables **
  125. do fill_lists
  126.  
  127. ** initialize internal control variables **
  128. bottom_on = .T.
  129. cmd_line = replicate("°", 80)
  130. error_on = .T.
  131. save_col = 0
  132. save_row = 0
  133. stack_size = 30
  134.  
  135. ** initialize the history variables **
  136. hist_max = 0
  137. max_hist = 20
  138. declare history[max_hist]
  139. dot_vers = "10/27/86"
  140.  
  141.  
  142. ** 5.0 error handler (see end of source file) **
  143. public SysErrorBlock := ErrorBlock( {|e| DotError(e)} )
  144.  
  145.  
  146. quit_now = .F.
  147.  
  148. do while !quit_now
  149.  
  150.     ** reset command line execution macro variables **
  151.     store "" to box_exp, coord1, coord2, coord3, coord4
  152.     store "" to dbf_file, dest, exp1, exp2, exp3
  153.     store "" to get_exp, get_pict, ntx_file, rng_exp1, rng_exp2
  154.     store "" to say_exp, say_pict, source, var1
  155.     store "" to list0, list1, list2, list3, list4
  156.     store "" to list5, list6, list7, list8, list9
  157.  
  158.  
  159.     begin sequence
  160.  
  161.         declare stack[stack_size]        && initialize STACK.
  162.         stack_ptr = 0                    && initialize stack element pointer.
  163.         max_ptr = 0                      && initialize stack element counter.
  164.  
  165.         lex_proc = ""                    && initialize analyzer macro.
  166.         executor = ""                    && initialize "class" executor macro.
  167.  
  168.         ** set PROMPT environment quantity **
  169.         set color to
  170.         set delimiters OFF
  171.         set confirm OFF
  172.         set exact OFF
  173.  
  174.         if bottom_on
  175.             do input_ln with "B"         && prompt at bottom of screen.
  176.         endif
  177.  
  178.         ** set HELP and HISTORY call keys **
  179.         set key 28 to help
  180.         set key 5 to history
  181.  
  182.         accept ". " to command           && get input from keyboard.
  183.  
  184.         do hist_put                      && place command into HISTORY array.
  185.  
  186.         command = "&command"             && expand all macros in string
  187.  
  188.         set key 5 to                     && turn OFF HISTORY mode.
  189.  
  190.         if bottom_on
  191.             do input_ln with "A"         && cursor to last display position.
  192.         endif
  193.  
  194.         do parse                         && call "stack" population routine.
  195.         max_ptr = stack_ptr              && assign maximum stack elements.
  196.  
  197.         if max_ptr > 0                   && stack elements exist.
  198.             if !err()                    && NO errors occurred in parser.
  199.                 do set_lex               && do analyzer macro set procedure.
  200.                 do &lex_proc             && do the analyze procedure macro.
  201.  
  202.                 if CALLS7
  203.                     quit_now = .t.
  204.                     break
  205.                 endif
  206.  
  207.                 if executor = "VARS"
  208.                     ** check for variable creation or release activity. **
  209.                     do case
  210.                         case VARS9
  211.                             ** if a variable is to be created **
  212.                             &var1 = &exp2
  213.                             VARS9 = .F.
  214.  
  215.                         case VARS10
  216.                             ** if an array is to be created **
  217.                             declare &var1[&exp1]
  218.                             VARS10 = .F.
  219.  
  220.                         case VARS11
  221.                             ** if a variable is to be released **
  222.                             release &var1
  223.                             VARS11 = .F.
  224.  
  225.                         case VARS12
  226.                             ** if an array is assigned a value **
  227.                             &var1[&exp1] = &exp2
  228.                             VARS12 = .F.
  229.                     endcase
  230.                 endif
  231.             endif
  232.  
  233.             if err()
  234.                 executor = "ERRS"        && set error executor procedure.
  235.             endif
  236.  
  237.  
  238.             ** set EXECUTION environment **
  239.             set color to &color_stat
  240.             set delimiters &delim_stat
  241.             set confirm &confr_stat
  242.             set exact &exact_stat
  243.  
  244.             do &executor                 && do execution procedure.
  245.  
  246.  
  247.         endif
  248.  
  249.     recover
  250.         ** this is just here to reset the parser **
  251.         command := '? ""'
  252.         do parse
  253.  
  254.     end
  255.  
  256. enddo
  257.  
  258. *
  259. ** eoproc dot.prg
  260.  
  261.  
  262. *******************
  263. * Dot procedures. *
  264. *******************
  265.  
  266.  
  267. ***
  268. * Procedure ACCEPT
  269. * Evaluates stack for ACCEPT verb.
  270. * Sets execution class macro, class execution flag(s) and command line
  271. * substitution macros.
  272. *
  273.  
  274. procedure accept
  275.  
  276. private stack_ptr, stack_item, item_ok, string, to, dest, active, error
  277.  
  278. stack_ptr = 2
  279. store .F. to string, to, dest, item_ok
  280. active = 1        && 0 = done, 1 = string, 2 = TO token, 3 = expression.
  281. error = 0
  282.  
  283. do while stack_ptr <= max_ptr .and. error = 0
  284.  
  285.     stack_item = ""
  286.     item_ok = get_stack("stack_item")
  287.  
  288.     do case 
  289.         case active = 0 .or. !item_ok
  290.             error = 2
  291.  
  292.         case active = 1
  293.             if !(upper(stack_item) == "TO")
  294.                 exp1 = stack_item
  295.                 string = .T.
  296.                 active = 2
  297.             else
  298.                 to = .T.    
  299.                 active = 3
  300.             endif
  301.  
  302.         case active = 2
  303.             if upper(stack_item) == "TO"
  304.                 to = .T.
  305.                 active = 3
  306.             else
  307.                 error = 15
  308.             endif
  309.  
  310.         case active = 3    
  311.             var1 = stack_item
  312.             dest = .T.
  313.             active = 0
  314.     endcase
  315. enddo
  316.  
  317. do case
  318.     case error = 2 .or. active <> 0
  319.         ERRS2 = .T.
  320.  
  321.     case error = 15
  322.         ERRS15 = .T.
  323.  
  324.     case to .and. dest .and. !string
  325.         executor = "VARS"
  326.         VARS1 = .T.
  327.         VARS9 = .T.
  328.  
  329.     case to .and. dest .and. string
  330.         executor = "VARS"
  331.         VARS2 = .T.
  332.         VARS9 = .T.
  333. endcase
  334.  
  335. return
  336.  
  337. *
  338. ** eoproc accept
  339.  
  340.  
  341. ***
  342. * Procedure APPEND
  343. * Evaluates stack for APPEND verb.
  344. * Sets execution class macro, class execution flag(s) and command line
  345. * substitution macros.
  346. *
  347.  
  348. procedure append
  349.  
  350. private stack_ptr, stack_item, item_ok, blank, file, from, active, error
  351.  
  352. stack_ptr = 2
  353. store .F. to blank, file, from, item_ok
  354. active = 0        && 0 = done, 1 = BLANK or FROM toke, 2 = source.
  355. error = 0
  356.  
  357. if error_on .and. !dbf_open
  358.     error = 5
  359. else
  360.     active = 1
  361. endif
  362.  
  363. do while stack_ptr <= max_ptr .and. error = 0
  364.  
  365.     stack_item = ""
  366.     item_ok = get_stack("stack_item")
  367.  
  368.     do case
  369.         case active = 0
  370.             error = 2
  371.  
  372.         case active = 1
  373.             do case
  374.                 case cmd_abbr(upper(stack_item), "BLANK")
  375.                     blank = .T.
  376.                     active = 0
  377.  
  378.                 case upper(stack_item) == "FROM"
  379.                     from = .T.
  380.                     active = 2
  381.  
  382.                 otherwise
  383.                     error = 2    
  384.             endcase
  385.  
  386.         case active = 2
  387.             exp1 = stack_item
  388.             if error_on
  389.                 if if("."$exp1, file(exp1), file("&exp1..dbf"))
  390.                     file = .T.
  391.                 else
  392.                     error = 13
  393.                 endif
  394.             else
  395.                 file = .T.
  396.             endif
  397.             active = 0
  398.     endcase
  399. enddo
  400.  
  401. do case
  402.     case error = 2 .or. active <> 0
  403.         ERRS2 = .T.
  404.  
  405.     case error = 5
  406.         ERRS5 = .T.
  407.  
  408.     case error = 13
  409.         ERRS13 = .T.
  410.  
  411.     case blank
  412.         executor = "DBF_NTX"
  413.         DBF_NTX18 = .T.
  414.  
  415.     case from .and. file
  416.         executor = "DBF_NTX"
  417.         DBF_NTX31 = .T.
  418. endcase
  419.  
  420. return
  421.  
  422. *
  423. ** eoproc append
  424.  
  425.  
  426. **
  427. * Procedure ASSIGN
  428. * Evaluates stack for assignment operator "=".
  429. * Sets execution class macro, class execution flag(s) and command line
  430. * substitution macros.
  431. *
  432.  
  433. procedure assign
  434.  
  435. private stack_ptr, equal, exp, array
  436.  
  437. stack_ptr = 1
  438. store .F. to equal, exp, array
  439.  
  440. do while stack_ptr <= max_ptr
  441.     do case
  442.         case stack_ptr = 1
  443.             var1 = stack[stack_ptr]
  444.             stack_ptr = stack_ptr + 1
  445.             if stack_ptr <= max_ptr
  446.                 if "["$stack[stack_ptr]
  447.                     var1 = var1 + stack[stack_ptr]
  448.                     stack_ptr = stack_ptr + 1
  449.                 endif
  450.             endif
  451.             if "["$var1
  452.                 string = var1
  453.                 var1 = ""
  454.                 open_ptr = at("[",string)
  455.                 close_ptr = at("]",string)
  456.                 var1 = substr(string, 1, (open_ptr - 1))
  457.                 exp1 = substr(string,(open_ptr+1),(close_ptr-open_ptr-1))
  458.                 array = .T.
  459.             endif
  460.  
  461.         case stack[stack_ptr] = "="
  462.             equal = .T.
  463.             exp = get_expr1("exp2")
  464.     endcase
  465. enddo
  466.  
  467. if equal
  468.     if exp
  469.         executor = "VARS"
  470.         if array
  471.             VARS12 = .T.
  472.         else
  473.             VARS9 = .T.
  474.         endif
  475.     else
  476.        ERRS2 = .F.
  477.     endif
  478. else
  479.     ERRS1 = .T.
  480. endif
  481.  
  482. return
  483.  
  484. *
  485. ** eoproc assign
  486.  
  487.  
  488. ***
  489. * Procedure AT
  490. * Evaluates stack for @ token.
  491. * Sets execution class macro, class execution flag(s) and command line
  492. * substitution macros.
  493. *
  494.  
  495. procedure at
  496.  
  497. set exact on
  498.  
  499. private at, clear, box, say, say_part, get, get_part, pic1, pic2, range,;
  500.     valid, xy, tlbr, co_num, stack_ptr, stack_item, active, null
  501.  
  502. store .F. to at, clear, box, say, say_part, get, get_part, pic1, pic2,;
  503.     range, valid, xy, tlbr
  504.  
  505. co_num = "1"
  506. stack_ptr = 1
  507. active = 1        && 0 = done, 1 = processing say, 2 = processing get.
  508.  
  509. do while stack_ptr <= max_ptr .and. !err()
  510.  
  511.     stack_item = upper(stack[stack_ptr])
  512.  
  513.     do case
  514.         case stack_item = "@"
  515.             null = get_expr1("coord&co_num")
  516.             co_num = str(val(co_num)+1,1)
  517.  
  518.         case stack_item = ","
  519.             null = get_expr1("coord&co_num")
  520.             co_num = str(val(co_num)+1,1)
  521.  
  522.         case stack_item = "BOX"
  523.             box = .T.
  524.             null = get_expr1("box_exp")
  525.  
  526.         case stack_item = "SAY"
  527.             active = 1
  528.             say = .T.
  529.             say_part = get_expr1("say_exp")
  530.  
  531.         case stack_item = "GET"
  532.             active = 2
  533.             get = .T.
  534.             get_part = get_expr1("get_exp")
  535.  
  536.         case cmd_abbr(stack_item, "PICTURE")
  537.             do case
  538.                 case say .and. !get
  539.                     pic1 = .T.
  540.                     null = get_expr1("say_pict")
  541.  
  542.                 case get .and. !say
  543.                     pic2 = .T.
  544.                     null = get_expr1("get_pict")
  545.  
  546.                 case say .and. get
  547.                     if active = 1        && if processing a say.
  548.                         pic1 = get_expr1("say_pict")
  549.                     else                 && if processing a get.
  550.                         pic2 = get_expr1("get_pict")
  551.                     endif
  552.  
  553.                 otherwise
  554.                     ERRS2 = .T.
  555.             endcase
  556.  
  557.         case cmd_abbr(stack_item, "CLEAR")
  558.             clear = .T.
  559.             stack_ptr = stack_ptr + 1
  560.  
  561.         case cmd_abbr(stack_item, "RANGE")
  562.             range = .T.
  563.             null = get_expr1("rng_exp1")
  564.             null = get_expr1("rng_exp2")
  565.  
  566.         case cmd_abbr(stack_item, "VALID")
  567.             valid = .T.
  568.             null = get_expr1("valid_exp")
  569.  
  570.         otherwise
  571.             ERRS2 = .T.
  572.     endcase
  573. enddo
  574.  
  575. set exact &exact_stat
  576.  
  577. if !err()
  578.  
  579.     if !empty(coord1) .and. !empty(coord2)
  580.         if !empty(coord3) .and. !empty(coord4)
  581.             tlbr = .T.
  582.         else
  583.             xy = .T.
  584.         endif
  585.     else
  586.         ERRS2 = .T.
  587.     endif
  588.  
  589.     do case
  590.         case xy .and. !say .and. !get .and. !clear .and. !box
  591.             executor = "SCRN"
  592.             SCRN1 = .T.
  593.     
  594.         case xy .and. clear .and. !say .and. !get .and. !box
  595.             executor = "SCRN"
  596.             SCRN2 = .T.
  597.  
  598.         case xy .and. say .and. !get
  599.             do case
  600.                 case !say_part
  601.                     ERRS2 = .T.
  602.  
  603.                 case !pic1 .and. !clear .and. !range .and. !valid
  604.                     executor = "SCRN"
  605.                     SCRN3 = .T.
  606.  
  607.                 case pic1 .and. !clear .and. !range .and. !valid
  608.                     executor = "SCRN"
  609.                     SCRN4 = .T.
  610.  
  611.                 otherwise
  612.                     ERRS1 = .T.
  613.             endcase
  614.  
  615.         case xy .and. get .and. !say
  616.             do case
  617.                 case !get_part
  618.                     ERRS2 = .T.
  619.  
  620.                 case !pic2 .and. !range .and. !valid
  621.                     executor = "SCRN"
  622.                     SCRN5 = .T.
  623.  
  624.                 case pic2 .and. !range .and. !valid
  625.                     executor = "SCRN"
  626.                     SCRN6 = .T.
  627.  
  628.                 case !pic2 .and. range .and. !valid
  629.                     executor = "SCRN"
  630.                     SCRN7 = .T.
  631.  
  632.                 case !pic2 .and. !range .and. valid
  633.                     executor = "SCRN"
  634.                     SCRN8 = .T.
  635.  
  636.                 case pic2 .and. !range .and. valid
  637.                     executor = "SCRN"
  638.                     SCRN10 = .T.
  639.  
  640.                 case pic2 .and. range .and. !valid
  641.                     executor = "SCRN"
  642.                     SCRN11 = .T.
  643.  
  644.                 otherwise
  645.                     ERRS2 = .T.
  646.             endcase
  647.  
  648.         case xy .and. say .and. get
  649.             do case
  650.                 case !say_part .or. !get_part
  651.                     ERRS2 = .T.
  652.  
  653.                 case !pic1 .and. !pic2 .and. !range .and. !valid
  654.                     executor = "SCRN"
  655.                     SCRN13 = .T.
  656.  
  657.                 case pic1 .and. !pic2 .and. !range .and. !valid
  658.                     executor = "SCRN"
  659.                     SCRN14 = .T.
  660.  
  661.                 case pic1 .and. pic2 .and. !range .and. !valid
  662.                     executor = "SCRN"
  663.                     SCRN15 = .T.
  664.  
  665.                 case pic1 .and. pic2 .and. range .and. !valid
  666.                     executor = "SCRN"
  667.                     SCRN16 = .T.
  668.  
  669.                 case pic1 .and. pic2 .and. !range .and. valid
  670.                     executor = "SCRN"
  671.                     SCRN17 = .T.
  672.  
  673.                 case !pic1 .and. pic2 .and. !range .and. !valid
  674.                     executor = "SCRN"
  675.                     SCRN19 = .T.
  676.  
  677.                 case !pic1 .and. pic2 .and. range .and. !valid
  678.                     executor = "SCRN"
  679.                     SCRN20 = .T.
  680.  
  681.                 case !pic1 .and. pic2 .and. !range .and. valid
  682.                     executor = "SCRN"
  683.                     SCRN21 = .T.
  684.  
  685.                 otherwise
  686.                     ERRS2 = .T.
  687.             endcase
  688.  
  689.         case tlbr .and. box
  690.             executor = "SCRN"
  691.             SCRN22 = .T.
  692.  
  693.         otherwise
  694.             ERRS1 = .T.
  695.     endcase
  696. endif
  697.  
  698. return
  699.  
  700. *
  701. ** eoproc at
  702.  
  703.  
  704. ***
  705. * Procedure CALL
  706. * Evaluates stack for CALL verb.
  707. * Sets execution class macro, class execution flag(s) and command line
  708. * substitution macros.
  709. *
  710.  
  711. procedure call
  712.  
  713. private stack_ptr, stack_item, xproc, with, params, active, error,;
  714.   item_ok
  715.  
  716. stack_ptr = 2
  717. store .F. to xproc, with, params, item_ok
  718. active = 1       && 0 = done, 1 = procedure, 2 = WITH toke and params.
  719. error = 0
  720.  
  721. do while stack_ptr <= max_ptr .and. error = 0
  722.  
  723.     stack_item = ""
  724.     stack_item = stack[stack_ptr]
  725.  
  726.     do case
  727.         case active = 0
  728.             error = 2
  729.  
  730.         case active = 1
  731.             exp1 = stack_item
  732.             xproc = .T.
  733.             stack_ptr = stack_ptr + 1
  734.             if stack_ptr > max_ptr
  735.                 active = 0
  736.             else
  737.                 active = 2
  738.             endif
  739.  
  740.         case active = 2
  741.             if upper(stack_item) = "WITH"
  742.                 with = .T.
  743.                 params = get_list("E")
  744.                 if params
  745.                     active = 0
  746.                 else
  747.                     error = 2
  748.                 endif
  749.             else
  750.                 error = 2
  751.             endif
  752.     endcase
  753. enddo
  754.  
  755. do case
  756.     case error = 2 .or. active <> 0
  757.         ERRS2 = .T.
  758.  
  759.     case xproc .and. !with .and. !params
  760.         executor = "CALLS"
  761.         CALLS4 = .T.
  762.  
  763.     case xproc .and. with .and. params
  764.         executor = "CALLS"
  765.         CALLS5 = .T.
  766. endcase
  767.  
  768. return
  769.  
  770. *
  771. ** eoproc call
  772.  
  773.  
  774. ***    
  775. * Procedure CLEAR
  776. * Evaluates stack for CLEAR verb.
  777. * Sets execution class macro, class execution flag(s) and command line
  778. * substitution macros.
  779. *
  780.  
  781. procedure clear
  782.  
  783. if stack_ptr = 1
  784.     executor = "SCRN"
  785.     SCRN23 = .T.
  786. else
  787.     ERRS2 = .T.
  788. endif
  789.  
  790. return
  791.  
  792. *
  793. ** eoproc clear
  794.  
  795.  
  796. ***
  797. * Procedure COLOR
  798. * Evaluates stack for SET COLOR command, called from SET procedure.
  799. * Sets execution class macro, class execution flag(s) and command line
  800. * substitution macros.
  801. *
  802.  
  803. procedure color
  804.  
  805. private stack_ptr, to
  806.  
  807. stack_ptr = 3
  808. to = .F.
  809.  
  810. if stack_ptr <= max_ptr
  811.     if upper(stack[stack_ptr]) = "TO"
  812.         to = .T.
  813.         stack_ptr = stack_ptr + 1
  814.         do while stack_ptr <= max_ptr         && build up color string.
  815.             exp1 = exp1 + stack[stack_ptr]
  816.             stack_ptr = stack_ptr + 1
  817.         enddo
  818.     endif
  819. endif
  820.  
  821. if to
  822.     executor = "SETS"
  823.     SETS1 = .T.
  824. else
  825.     ERRS2 = .T.
  826. endif
  827.  
  828. return
  829.  
  830. *
  831. ** eoproc color
  832.  
  833.  
  834. ***
  835. * Procedure COPY
  836. * Evaluates stack for COPY verb.
  837. * Simple non-conditional and non-scoped syntax.
  838. * Sets execution class macro, class execution flag(s) and command line
  839. * substitution macros.
  840. *
  841.  
  842. procedure copy
  843.  
  844. private stack_ptr, stack_item, item_ok, struc, to, target, active, error
  845.  
  846. stack_ptr = 2
  847. store .F. to struc, to, target, item_ok
  848. active = 0            && 0 = done, 1 = STRU or TO toke, 2 = target.
  849. error = 0
  850.  
  851. if error_on .and. !DBF_OPEN
  852.     error = 5
  853. else
  854.     active = 1
  855. endif
  856.  
  857. do while stack_ptr <= max_ptr .and. error = 0
  858.  
  859.     stack_item = ""
  860.     item_ok = get_stack("stack_item")
  861.  
  862.     do case
  863.         case active = 0
  864.             error = 2
  865.  
  866.         case active = 1
  867.             do case 
  868.                 case cmd_abbr(upper(stack_item), "STRUCTURE") .and. !struc
  869.                     struc = .T.
  870.                     active = 1
  871.  
  872.                 case upper(stack_item) == "TO"
  873.                     to = .T.
  874.                     active = 2
  875.  
  876.                 otherwise
  877.                     error = 2
  878.             endcase
  879.  
  880.         case active = 2
  881.             exp1 = stack_item
  882.             target = .T.
  883.             active = 0
  884.     endcase
  885. enddo
  886.  
  887. do case
  888.     case error = 2 .or. active <> 0
  889.         ERRS2 = .T.
  890.  
  891.     case error = 5
  892.         ERRS5 = .T.
  893.  
  894.     case !struc .and. to .and. target
  895.         executor = "DBF_NTX"
  896.         DBF_NTX28 = .T.
  897.  
  898.     case struc .and. to .and. target
  899.         executor = "DBF_NTX"
  900.         DBF_NTX29 = .T.
  901.  
  902.     otherwise
  903.         ERRS2 = .T.
  904. endcase
  905.  
  906. return
  907.  
  908. *
  909. ** eoproc copy
  910.  
  911.  
  912. ***
  913. * Procedure CONFIRM
  914. * Evaluates stack for SET CONFIRM command.  Called procedure SET.
  915. * Sets execution class macro, class execution flag(s) and command line
  916. * substitution macros.
  917. *
  918.  
  919. procedure confirm
  920.  
  921. private stack_ptr, stack_item, item_ok, toggle
  922.  
  923. stack_ptr = 3
  924. stack_item = ""
  925. store .F. to item_ok, toggle
  926.  
  927. item_ok = get_stack("stack_item")
  928.  
  929. if item_ok .and. upper(stack_item)$"ON^OFF"
  930.     toggle = .T.
  931. else
  932.     error = 2
  933. endif
  934.  
  935. if toggle
  936.     executor = "SETS"
  937.     SETS2 = .T.
  938. else
  939.     ERRS2 = .T.
  940. endif
  941.  
  942. return
  943.  
  944. *
  945. ** eoproc confirm
  946.  
  947.  
  948. ***
  949. * Procedure calls
  950. * Executor for CALLS class of commands.
  951. *
  952.  
  953. procedure calls
  954.  
  955. private i, qqq
  956.  
  957. do case
  958.     case CALLS1
  959.         do &exp1
  960.         CALLS1 = .F.
  961.  
  962.     case CALLS2
  963.         for i = 0 to 9
  964.             qqq = "list"+str(i,1)
  965.             if (empty(&qqq))
  966.                 &qqq = "[]"
  967.             end
  968.         next
  969.  
  970.         do &exp1 with &list0, &list1, &list2, &list3, &list4, &list5, &list6,;
  971.             &list7, &list8, &list9
  972.         CALLS2 = .F.
  973.  
  974.     case CALLS3
  975.         run &exp1
  976.         ?
  977.         CALLS3 = .F.
  978.  
  979.     case CALLS4
  980.         call &exp1
  981.         CALLS4 = .F.
  982.  
  983.     case CALLS5
  984.         for i = 0 to 9
  985.             qqq = "list"+str(i,1)
  986.             if (empty(&qqq))
  987.                 &qqq = "[]"
  988.             end
  989.         next
  990.  
  991.         call &exp1 with &list0, &list1, &list2, &list3, &list4, &list5, &list6
  992.         CALLS5 = .F.
  993.  
  994.     case CALLS6
  995.         quit
  996.         CALLS6 = .F.
  997.  
  998.     case CALLS7
  999.         ** RETURN is not executed at this level **
  1000.  
  1001. endcase
  1002.  
  1003. return
  1004.  
  1005. *
  1006. ** eoproc calls
  1007.  
  1008.  
  1009. ***
  1010. * Procedure dbf_ntx
  1011. * Executor for DBF_NTX class of commands.
  1012. *
  1013.  
  1014. procedure dbf_ntx
  1015.  
  1016. private more, disp_row, i, qqq
  1017.  
  1018. do case
  1019.     case DBF_NTX1 
  1020.         use
  1021.         DBF_NTX1 = .F.
  1022.         DBF_OPEN = .F.
  1023.         NTX_OPEN = .F.
  1024.  
  1025.     case DBF_NTX2
  1026.         use &dbf_file
  1027.         DBF_NTX2 = .F.
  1028.         DBF_OPEN = .T.
  1029.         NTX_OPEN = .F.
  1030.  
  1031.     case DBF_NTX3
  1032.         use &dbf_file index &list0, &list1, &list2, &list3, &list4, &list5,;
  1033.             &list6, &list7, &list8, &list9
  1034.         DBF_NTX3 = .F.
  1035.         DBF_OPEN = .T.
  1036.         NTX_OPEN = .T.
  1037.  
  1038.     case DBF_NTX4
  1039.         use &dbf_file alias &exp2
  1040.         DBF_NTX4 = .F.
  1041.         DBF_OPEN = .T.
  1042.         NTX_OPEN = .F.
  1043.  
  1044.     case DBF_NTX5
  1045.         use &dbf_file index &list0, &list1, &list2, &list3, &list4, &list5,;
  1046.             &list6, &list7, &list8, &list9 alias &exp2
  1047.         DBF_NTX5 = .F.
  1048.         DBF_OPEN = .T.
  1049.         NTX_OPEN = .T.
  1050.  
  1051.     case DBF_NTX32
  1052.         use &dbf_file exclusive
  1053.         DBF_NTX32 = .F.
  1054.         DBF_OPEN = .T.
  1055.         NTX_OPEN = .F.
  1056.  
  1057.     case DBF_NTX33
  1058.         use &dbf_file index &list0, &list1, &list2, &list3, &list4, &list5,;
  1059.             &list6, &list7, &list8, &list9 exclusive
  1060.         DBF_NTX33 = .F.
  1061.         DBF_OPEN = .T.
  1062.         NTX_OPEN = .T.
  1063.  
  1064.     case DBF_NTX34
  1065.         use &dbf_file alias &exp2 exclusive
  1066.         DBF_NTX34 = .F.
  1067.         DBF_OPEN = .T.
  1068.         NTX_OPEN = .F.
  1069.  
  1070.     case DBF_NTX35
  1071.         use &dbf_file index &list0, &list1, &list2, &list3, &list4, &list5,;
  1072.             &list6, &list7, &list8, &list9 alias &exp2 exclusive
  1073.         DBF_NTX35 = .F.
  1074.         DBF_OPEN = .T.
  1075.         NTX_OPEN = .T.
  1076.  
  1077.     case DBF_NTX6
  1078.         ? "Indexing file on " + upper(exp1) + " to " + upper(ntx_file)
  1079.         index on &exp1 to &ntx_file
  1080.         ? "Index file creation complete"
  1081.         NTX_OPEN = .T.
  1082.         DBF_NTX6 = .F.
  1083.  
  1084.     case DBF_NTX7
  1085.         goto &exp1
  1086.         DBF_NTX7 = .F.
  1087.  
  1088.     case DBF_NTX8
  1089.         goto top
  1090.         DBF_NTX8 = .F.
  1091.  
  1092.     case DBF_NTX9
  1093.         goto bottom
  1094.         DBF_NTX9 = .F.
  1095.  
  1096.     case DBF_NTX10
  1097.         skip
  1098.         if EOF()
  1099.             ? "End of file encountered"
  1100.         endif
  1101.         if BOF()
  1102.             ? "Beginning of file encountered"
  1103.         endif
  1104.         DBF_NTX10 = .F.
  1105.  
  1106.     case DBF_NTX11
  1107.         skip &exp1
  1108.         if EOF()
  1109.             ? "End of file encountered"
  1110.         endif
  1111.         if BOF()
  1112.             ? "Beginning of file encountered"
  1113.         endif
  1114.         DBF_NTX11 = .F.
  1115.  
  1116.     case DBF_NTX12
  1117.         go top
  1118.         do list_do with .T., .F.
  1119.         DBF_NTX12 = .F.
  1120.  
  1121.     case DBF_NTX13
  1122.         go top
  1123.         for i = 0 to 9
  1124.             qqq = "list"+str(i,1)
  1125.             if (empty(&qqq))
  1126.                 &qqq = "[]"
  1127.             end
  1128.         next
  1129.  
  1130.         list &list0, &list1, &list2, &list3, &list4, &list5, &list6, &list7,;
  1131.             &list8, &list9 while inkey() <> 27
  1132.         DBF_NTX13 = .F.
  1133.  
  1134.     case DBF_NTX14
  1135.         do list_do with .T., .T.
  1136.         DBF_NTX14 = .F.
  1137.  
  1138.     case DBF_NTX15
  1139.         for i = 0 to 9
  1140.             qqq = "list"+str(i,1)
  1141.             if (empty(&qqq))
  1142.                 &qqq = "[]"
  1143.             end
  1144.         next
  1145.  
  1146.         display &list0, &list1, &list2, &list3, &list4, &list5, &list6,;
  1147.             &list7, &list8, &list9
  1148.         DBF_NTX15 = .F.
  1149.  
  1150.     case DBF_NTX16
  1151.         select &exp1
  1152.         DBF_NTX16 = .F.
  1153.  
  1154.     case DBF_NTX17
  1155.         seek &exp1
  1156.         if eof()
  1157.             ? "NOT Found"
  1158.         else
  1159.             ? "Found"
  1160.         endif
  1161.         DBF_NTX17 = .F.
  1162.  
  1163.     case DBF_NTX18
  1164.         append blank
  1165.         DBF_NTX18 = .F.
  1166.  
  1167.     case DBF_NTX19
  1168.         do do_cnd_scp with "delete_it"  && calls condition/scope logic.
  1169.         DBF_NTX19 = .F.
  1170.  
  1171.     case DBF_NTX22
  1172.         dir &exp1
  1173.         DBF_NTX22 = .F.
  1174.  
  1175.     case DBF_NTX20
  1176.         do do_cnd_scp with "recall_it"  && calls condition/scope logic.
  1177.         DBF_NTX20 = .F.
  1178.  
  1179.     case DBF_NTX21
  1180.         pack
  1181.         DBF_NTX21 = .F.
  1182.  
  1183.     case DBF_NTX23
  1184.         type &exp1
  1185.         DBF_NTX23 = .F.
  1186.  
  1187.     case DBF_NTX24
  1188.         unlock
  1189.         DBF_NTX24 = .F.
  1190.  
  1191.     case DBF_NTX25
  1192.         unlock all
  1193.         DBF_NTX25 = .F.
  1194.  
  1195.     case DBF_NTX26
  1196.         replace &var1 with &exp1
  1197.         DBF_NTX26 = .F.
  1198.  
  1199.     case DBF_NTX27
  1200.         replace all &var1 with &exp1
  1201.         DBF_NTX27 = .F.
  1202.  
  1203.     case DBF_NTX28
  1204.         copy to &exp1
  1205.         DBF_NTX28 = .F.
  1206.  
  1207.     case DBF_NTX29
  1208.         copy structure to &exp1
  1209.         DBF_NTX29 = .F.
  1210.  
  1211.     case DBF_NTX30
  1212.         erase &exp1
  1213.         DBF_NTX30 = .F.
  1214.  
  1215.     case DBF_NTX31
  1216.         append from &exp1
  1217.         DBF_NTX31 = .F.
  1218.  
  1219.   case DBF_NTX36
  1220.      ? "Are you sure? (Y/N)" 
  1221.      more = .T.
  1222.      disp_row = row()
  1223.  
  1224.      do while more
  1225.         more = !(ltrim(str(inkey(0),3))$"13^27^78^89^110^121")
  1226.         if lastkey() > 31 .and. lastkey() < 127
  1227.            @ disp_row, 21 say chr(lastkey()) 
  1228.         endif
  1229.      enddo
  1230.  
  1231.      if upper(chr(lastkey())) = "Y"
  1232.         zap
  1233.      endif
  1234.  
  1235.      DBF_NTX36 = .F.
  1236.  
  1237. endcase
  1238.  
  1239. return
  1240.  
  1241. *
  1242. ** eoproc dbf_ntx
  1243.  
  1244.  
  1245. ***
  1246. * Procedure DECIMAL
  1247. * Evaluates the stack for the SET DECIMALS command.  Called SET procedure.
  1248. * Sets execution class macro, class execution flag(s) and command line
  1249. * substitution macros.
  1250. *
  1251.  
  1252. procedure decimal
  1253.  
  1254. private stack_ptr, to, null
  1255.  
  1256. stack_ptr = 3
  1257. to = .F.
  1258.  
  1259. if stack_ptr <= max_ptr
  1260.     if upper(stack[stack_ptr]) = "TO"
  1261.         to = .T.
  1262.         null = get_expr1("exp1")
  1263.     endif
  1264. endif
  1265.  
  1266. if to
  1267.     executor = "SETS"
  1268.     SETS3 = .T.
  1269. else
  1270.     ERRS2 = .T.
  1271. endif
  1272.  
  1273. return
  1274.  
  1275. *
  1276. ** eoproc decimal
  1277.  
  1278.  
  1279. ***
  1280. * Procedure DECLARE
  1281. * Evaluates the stack for the DECLARE verb.
  1282. * Sets execution class macro, class execution flag(s) and command line
  1283. * substitution macros.
  1284. *
  1285.  
  1286. procedure declare
  1287.  
  1288. private stack_ptr, string
  1289.  
  1290. stack_ptr = 2
  1291. string = ""
  1292.  
  1293. if get_stack("string")
  1294.     open_ptr = at("[",string)
  1295.     close_ptr = at("]",string)
  1296.     var1 = substr(string, 1, (open_ptr - 1))
  1297.     exp1 = substr(string,(open_ptr+1),(close_ptr-open_ptr-1))
  1298.     executor = "VARS"
  1299.     VARS10 = .T.
  1300. else
  1301.     ERRS2 = .T.
  1302. endif
  1303.  
  1304. return
  1305.  
  1306. *
  1307. ** eoproc declare
  1308.  
  1309.  
  1310. ***
  1311. * Procedure DEFAULT
  1312. * Evaluates the stack for the SET DEFAULT command.  Called by SET procedure.
  1313. * Sets execution class macro, class execution flag(s) and command line
  1314. * substitution macros.
  1315. *
  1316.  
  1317. procedure default
  1318.  
  1319. private stack_ptr, to
  1320.  
  1321. stack_ptr = 3
  1322. store .F. to to, drive
  1323.  
  1324. if stack_ptr <= max_ptr
  1325.     if upper(stack[stack_ptr]) = "TO"
  1326.         to = .T.
  1327.         drive = get_expr1("exp1")
  1328.     endif
  1329. endif
  1330.  
  1331. if to .and. drive
  1332.     executor = "SETS"
  1333.     SETS4 = .T.
  1334. else
  1335.     ERRS2 = .T.
  1336. endif
  1337.  
  1338. return
  1339.  
  1340. *
  1341. ** eoproc default
  1342.  
  1343.  
  1344. ***
  1345. * Procedure DELETE
  1346. * Analyze the stack for the DELETE verb.
  1347. * Sets execution class macro, class execution flag(s) and command line
  1348. * substitution macros.
  1349. * UDF CND_SCP() used to set condition and scope control variables.
  1350. *
  1351.  
  1352. procedure delete
  1353.  
  1354. private stack_ptr, for, while, next, record, all, stack_item
  1355.  
  1356. stack_ptr = 2
  1357. store .F. to for, while, next, record, all, condition
  1358. scope = 0
  1359.  
  1360. if cnd_scp()       && no errors during condition and scope analysis.
  1361.  
  1362.     do case
  1363.         case for .or. while .or. all .or. next .or. record
  1364.             ** w/ w/o scope and/or condition. **
  1365.             if DBF_OPEN .or. !error_on
  1366.                 executor = "DBF_NTX"
  1367.                 DBF_NTX19 = .T.
  1368.             else    
  1369.                 ERRS5 = .T.
  1370.             endif
  1371.  
  1372.         case !for .and. !while .and. !all .and. !next .and. !record;
  1373.             .and. max_ptr = 1
  1374.             ** w/o scope or conditional **
  1375.             if DBF_OPEN .or. !error_on
  1376.                 executor = "DBF_NTX"
  1377.                 DBF_NTX19 = .T.
  1378.                 scope = 1     && use RECORD (scope = 1) for single delete.
  1379.                 exp3 = str(recno())
  1380.  
  1381.                 if &exp3 > lastrec()
  1382.                     ERRS6 = .T.
  1383.                     DBF_NTX19 = .F.
  1384.                 else
  1385.                     exp3 = "recno() = &exp3"
  1386.                 endif
  1387.             else
  1388.                 ERRS5 = .T.
  1389.             endif
  1390.  
  1391.         otherwise        
  1392.             ERRS2 = .T.
  1393.     endcase        
  1394.  
  1395. endif
  1396.  
  1397. return
  1398.  
  1399. *
  1400. ** eoproc delete
  1401.  
  1402.  
  1403. ***
  1404. * Procedure delete_it
  1405. * Executes a record delete.  Called by procedure DO_CND_SCP.
  1406. *
  1407.  
  1408. procedure delete_it
  1409.  
  1410. delete
  1411.  
  1412. return
  1413.  
  1414. *
  1415. ** eoproc delete_it
  1416.  
  1417.  
  1418. ***
  1419. * Procedure DELIM
  1420. * Evaluates stack for SET DELIMITERS command.  Called by procedure
  1421. * SET.
  1422. * Sets execution class macro, class execution flag(s) and command line
  1423. * substitution macros.
  1424. *
  1425.  
  1426. procedure delim
  1427.  
  1428. private stack_ptr, stack_item, to, switch, string, error, active, null
  1429.  
  1430. stack_ptr = 3
  1431. store .F. to to, switch, string, null
  1432. active = 1   && 0 = done, 1 = TO token or toggle, 2 = string/DEFAULT token.
  1433. error = 0
  1434.  
  1435. do while stack_ptr <= max_ptr .and. error = 0
  1436.  
  1437.     stack_item = ""
  1438.     null = get_stack("stack_item")
  1439.  
  1440.     do case
  1441.         case active = 0
  1442.             error = 2
  1443.  
  1444.         case active = 1
  1445.             do case 
  1446.                 case upper(stack_item) == "TO"
  1447.                     to = .T.
  1448.                     active = 2
  1449.  
  1450.                 case upper(stack_item)$"ON^OFF"
  1451.                     exp1 = stack_item
  1452.                     switch = .T.
  1453.                     active = 0
  1454.  
  1455.                 otherwise
  1456.                     error = 2
  1457.             endcase
  1458.  
  1459.         case active = 2
  1460.             exp1 = stack_item
  1461.             string = .T.
  1462.             active = 0
  1463.     endcase
  1464. enddo
  1465.  
  1466. do case
  1467.     case error = 2 .or. active <> 0
  1468.         ERRS2 = .T.
  1469.  
  1470.     case to .and. string
  1471.         executor = "SETS"
  1472.         SETS6 = .T.
  1473.  
  1474.     case switch
  1475.         executor = "SETS"
  1476.         SETS5 = .T.
  1477. endcase
  1478.  
  1479. return
  1480.  
  1481. *
  1482. ** eoproc delim
  1483.  
  1484.  
  1485. ***
  1486. * Procedure DIR
  1487. * Sets execution class macro, class execution flag(s) and command line
  1488. * substitution macros from the command line not the stack.
  1489. *
  1490.  
  1491. procedure dir
  1492.  
  1493. exp1 = substr(command, len(stack[1]) + 1)
  1494.  
  1495. executor = "DBF_NTX"
  1496. DBF_NTX22 = .T.
  1497.  
  1498. *
  1499. ** eoproc dir
  1500.  
  1501.  
  1502. ***
  1503. * Procedure DISPLAY
  1504. * Evaluates the stack for the DISPLAY verb.
  1505. * Sets execution class macro, class execution flag(s) and command line
  1506. * substitution macros.
  1507. *
  1508.  
  1509. procedure display
  1510.  
  1511. private stack_ptr
  1512.  
  1513. stack_ptr = 1
  1514.  
  1515. if DBF_OPEN .or. !error_on
  1516.     if max_ptr = 1
  1517.         executor = "DBF_NTX"
  1518.         DBF_NTX14 = .T.
  1519.     else
  1520.         if get_list("E")
  1521.             executor = "DBF_NTX"
  1522.             DBF_NTX15 = .T.
  1523.         else
  1524.             ERRS2 = .T.
  1525.         endif
  1526.     endif
  1527. else
  1528.     ERRS5 = .T.
  1529. endif
  1530.  
  1531. return
  1532.  
  1533. *
  1534. ** eoproc display
  1535.  
  1536.  
  1537. ***
  1538. * Procedure DO
  1539. * Evaluates the stack for the DO verb.
  1540. * Sets execution class macro, class execution flag(s) and command line
  1541. * substitution macros.
  1542. *
  1543.  
  1544. procedure do
  1545.  
  1546. private stack_ptr, stack_item, item_ok, xproc, with, params, active, error
  1547.  
  1548. stack_ptr = 2
  1549. store .F. to xproc, with, params, item_ok
  1550. active = 1            && 0 = done, 1 = procedure, 2 = WITH toke and params.
  1551. error = 0
  1552.  
  1553. do while stack_ptr <= max_ptr .and. error = 0
  1554.  
  1555.     stack_item = ""
  1556.     stack_item = stack[stack_ptr]
  1557.  
  1558.     do case
  1559.         case active = 0
  1560.             error = 2
  1561.  
  1562.         case active = 1
  1563.             exp1 = stack_item
  1564.             xproc = .T.
  1565.             stack_ptr = stack_ptr + 1
  1566.             if stack_ptr > max_ptr
  1567.                 active = 0
  1568.             else
  1569.                 active = 2
  1570.             endif
  1571.  
  1572.         case active = 2
  1573.             if upper(stack_item) = "WITH"
  1574.                 with = .T.
  1575.                 params = get_list("E")
  1576.                 if params
  1577.                     active = 0
  1578.                 else
  1579.                     error = 2
  1580.                 endif
  1581.             else
  1582.                 error = 2
  1583.             endif
  1584.     endcase
  1585. enddo
  1586.  
  1587. do case
  1588.     case error = 2 .or. active <> 0
  1589.         ERRS2 = .T.
  1590.  
  1591.     case xproc .and. !with .and. !params
  1592.         executor = "CALLS"
  1593.         CALLS1 = .T.
  1594.  
  1595.     case xproc .and. with .and. params
  1596.         executor = "CALLS"
  1597.         CALLS2 = .T.
  1598. endcase
  1599.  
  1600. return
  1601.  
  1602. *
  1603. ** eoproc do
  1604.  
  1605.  
  1606. ***
  1607. * Procedure do_cnd_scp
  1608. * Executes logic for conditional and scoped commands.  Called by executor
  1609. * procedures.  Calls to procedures containing single iterations of command
  1610. * being executed.
  1611. *
  1612.  
  1613. procedure do_cnd_scp
  1614.  
  1615. parameters action_proc
  1616.  
  1617. private more, count, do_it
  1618. more = .T.
  1619. count = 0
  1620.  
  1621. if rewind_dbf
  1622.     go top
  1623. endif
  1624.  
  1625. do while more .and. !EOF()
  1626.     do_it = .F.
  1627.      
  1628.     if scope > 0                    && handles scoping stuff.
  1629.         do case
  1630.             case scope = 1          && record.
  1631.                 if &exp3
  1632.                     do_it = .T.
  1633.                     more = .F.
  1634.                 endif
  1635.  
  1636.             case scope = 2          && all.
  1637.                 do_it = .T.
  1638.  
  1639.             case scope = 3          && next.
  1640.                 count = count + 1
  1641.                 if count <= &exp3
  1642.                     do_it = .T.
  1643.                 else
  1644.                     do_it = .F.
  1645.                     more = .F.
  1646.                 endif
  1647.  
  1648.         endcase
  1649.     endif
  1650.  
  1651.     if condition                    && handles conditional stuff.
  1652.  
  1653.         if "" <> exp1
  1654.             if &exp1                && FOR condition.
  1655.                 do_it = .T.
  1656.             else
  1657.                 do_it = .F.
  1658.             endif
  1659.         endif
  1660.  
  1661.         if "" <> exp2
  1662.             if &exp2                && WHILE condition.
  1663.                 do_it = .T.
  1664.             else
  1665.                 do_it = .F.
  1666.                 more = .F.
  1667.             endif
  1668.         endif
  1669.     endif
  1670.  
  1671.     if do_it
  1672.         do &action_proc             && call single iteration of command.
  1673.     endif
  1674.  
  1675.     if more
  1676.         skip
  1677.     endif
  1678.  
  1679. enddo
  1680.  
  1681. return
  1682.  
  1683. *
  1684. ** eoproc do_cnd_scp
  1685.  
  1686.  
  1687. ***
  1688. * Procedure ERASE
  1689. * Sets execution class macro, class execution flag(s) and command line
  1690. * substitution macros from the command line.
  1691. *
  1692.  
  1693. procedure erase
  1694.  
  1695. private error
  1696.  
  1697. error = 0
  1698.  
  1699. exp1 = substr(command, len(stack[1]) + 1)
  1700.  
  1701. if !empty(exp1)
  1702.     if file(stack_item) .or. !error_on
  1703.         exp1 = stack_item
  1704.     else
  1705.         error = 13
  1706.     endif
  1707. endif
  1708.  
  1709. if error = 13
  1710.     ERRS13 = .T.
  1711. else
  1712.     executor = "DBF_NTX"
  1713.     DBF_NTX30 = .T.
  1714. endif
  1715.  
  1716. return
  1717.  
  1718. *
  1719. ** eoproc erase
  1720.  
  1721.  
  1722. ***
  1723. * Procedure errs
  1724. * Executor for the ERRS class of commands, the DOT error message system.
  1725. *
  1726.  
  1727. procedure errs
  1728.  
  1729. do case
  1730.     case ERRS1
  1731.         ? "Unrecognized command, F1 for Help."
  1732.         ERRS1 = .F.
  1733.  
  1734.     case ERRS2
  1735.         ? "Syntax error, F1 for Help."
  1736.         ERRS2 = .F.
  1737.  
  1738.     case ERRS3
  1739.         ? "Undefined expression."
  1740.         ERRS3 = .F.
  1741.  
  1742.     case ERRS4
  1743.         ? "Undefined variable : "+"&exp1"
  1744.         ERRS4 = .F.
  1745.  
  1746.     case ERRS5
  1747.         ? "Database NOT in use."
  1748.         ERRS5 = .F.
  1749.  
  1750.     case ERRS6
  1751.         ? "Record out of range."
  1752.         ERRS6 = .F.
  1753.  
  1754.     case ERRS7
  1755.         ? "Data file NOT found."
  1756.         ERRS7 = .F.
  1757.  
  1758.     case ERRS8
  1759.         ? "Unbalanced delimiters."
  1760.         ERRS8 = .F.
  1761.  
  1762.     case ERRS9
  1763.         ? "Index file NOT in use"
  1764.         ERRS9 = .F.
  1765.  
  1766.     case ERRS10
  1767.         ? "Not implemented"
  1768.         ERRS10 = .F.
  1769.  
  1770.     case ERRS11
  1771.         ? "Index file NOT found"
  1772.         ERRS11 = .F.
  1773.  
  1774.     case ERRS12
  1775.         ? "Illegal goto value"
  1776.         ERRS12 = .F.
  1777.  
  1778.     case ERRS13
  1779.         ? "File NOT found"
  1780.         ERRS13 = .F.
  1781.  
  1782.     case ERRS14
  1783.         ? "Invalid function key number, 2 - 40"
  1784.         ERRS14 = .F.
  1785.  
  1786.     case ERRS15
  1787.         ? "Missing key word"
  1788.         ERRS15 = .F.
  1789. endcase
  1790.  
  1791. return
  1792.  
  1793. *
  1794. ** eoproc errs
  1795.  
  1796.  
  1797. ***
  1798. * Procedure ESCAPE
  1799. * Evaluates stack for the SET ESCAPE command. Called by SET procedure.
  1800. * Sets execution class macro, class execution flag(s) and command line
  1801. * substitution macros.
  1802. *
  1803.  
  1804. procedure escape
  1805.  
  1806. stack_ptr = 3
  1807.  
  1808. if stack_ptr <= max_ptr
  1809.     exp1 = upper(stack[stack_ptr])
  1810.     if "&exp1"$"ON^OFF"
  1811.         executor = "SETS"
  1812.         SETS7 = .T.
  1813.     else
  1814.         ERRS2 = .T.
  1815.     endif
  1816. else
  1817.     ERRS2 = .T.
  1818. endif
  1819.  
  1820. return
  1821.  
  1822. *
  1823. ** eoproc escape
  1824.  
  1825.  
  1826. ***
  1827. * Procedure EXACT
  1828. * Evaluates the stack for SET EXACT command.  Called by SET procedure.
  1829. * Sets execution class macro, class execution flag(s) and command line
  1830. * substitution macros.
  1831. *
  1832.  
  1833. procedure exact
  1834.  
  1835. stack_ptr = 3
  1836.  
  1837. if stack_ptr <= max_ptr
  1838.     exp1 = upper(stack[stack_ptr])
  1839.     if "&exp1"$"ON^OFF"
  1840.         executor = "SETS"
  1841.         SETS20 = .T.
  1842.     else 
  1843.         ERRS2 = .T.
  1844.     endif
  1845. else
  1846.     ERRS2 = .T.
  1847. endif
  1848.  
  1849. return
  1850.  
  1851. *
  1852. ** eoproc exact
  1853.  
  1854.  
  1855. ***
  1856. * Procedure EXCLUSIVE
  1857. * Evaluates the stack for the SET EXCLUSIVE command.  Called from
  1858. * procedure SET.
  1859. * Sets execution class macro, class execution flag(s) and command
  1860. * line substitution macros.
  1861. *
  1862.  
  1863. procedure exclusive
  1864.  
  1865. stack_ptr = 3
  1866.  
  1867. if stack_ptr <= max_ptr
  1868.     exp1 = upper(stack[stack_ptr])
  1869.     if "&exp1"$"ON^OFF"
  1870.         executor = "SETS"
  1871.         SETS19 = .T.
  1872.     else
  1873.         ERRS2 = .T.
  1874.     endif
  1875. else
  1876.     ERRS2 = .T.
  1877. endif
  1878.  
  1879. return
  1880.  
  1881. *
  1882. ** eoproc exclusive
  1883.  
  1884.  
  1885. ***
  1886. * Procedure fill_lists
  1887. * Called from procedure DOT.  Fills the verb_list, lex_list, set_list and
  1888. * set_proc search strings.
  1889. *
  1890.  
  1891. procedure fill_lists
  1892.  
  1893. verb_list =    "         .!        .?        .??       .@        .ACCEPT   "+;
  1894.     ".APPEND   .CLEAR    .CLS      .DECLARE  .DELETE   .DIRECTORY.DISPLAY  "+;
  1895.     ".DO       .EXIT     .GO       .GOTO     .INDEX    .INPUT    .LIST     "+;
  1896.     ".PACK     .QUIT     .READ     .RECALL   .RELEASE  .RETURN   .RUN      "+;
  1897.     ".SEEK     .SELECT   .SET      .SKIP     .TYPE     .USE      .WAIT     "+;
  1898.     ".CALL     .UNLOCK   .REPLACE  .COPY     .ERASE    .ZAP      "
  1899.  
  1900. lex_list =     "         RUN       QUES1     QUES2     AT        ACCEPT    "+;
  1901.     "APPEND    CLEAR     CLEAR     DECLARE   DELETE    DIR       DISPLAY   "+;
  1902.     "DO        QUIT      GOTO      GOTO      INDEX     INPUT     LIST      "+;
  1903.     "PACK      QUIT      RREAD     RECALL    RELEASE   QUIT      RUN       "+;
  1904.     "SEEK      SELECT    SSET      SKIP      TYPE      USE       WWAIT     "+;
  1905.     "CALL      UNLOCK    REPLACE   COPY      ERASE     ZAP       "
  1906.  
  1907. set_list =      "          .COLOR     .CONFIRM   .DECIMALS  .DEFAULT   "+;
  1908.     ".DELIMITERS.EXACT     .ESCAPE    .EXCLUSIVE .FILTER    .FIXED     "+;
  1909.     ".FUNCTION  .INDEX     .INTENSITY .KEY       .ORDER     .PATH      "+;
  1910.     ".RELATION  .UNIQUE    "
  1911.  
  1912. set_proc =      "          COLOR      CONFIRM    DECIMAL    DEFAULT    "+;
  1913.     "DELIM      EXACT      ESCAPE     EXCLUSIVE  FILTER     FIXED      "+;
  1914.     "FUNC_SET   INDEX_SET  INTENSITY  KEY        ORDER      PATH       "+;
  1915.     "RELATE     UNIQUE     "    
  1916.  
  1917. return
  1918.  
  1919. *
  1920. ** eoproc fill_lists
  1921.  
  1922.  
  1923. ***
  1924. * Procedure FILTER
  1925. * Evaluates the stack for the SET FILTER command.  Called by procedure SET.
  1926. * Sets execution class macro, class execution flag(s) and command line
  1927. * substitution macros.
  1928. *
  1929.  
  1930. procedure filter
  1931.  
  1932. private stack_ptr, stack_item, to, filter, error
  1933.  
  1934. stack_ptr = 3
  1935. stack_item = ""
  1936. error = 0
  1937. store .F. to to, filter
  1938.  
  1939. if DBF_OPEN .or. if(error_on, DBF_OPEN, .T.)
  1940.     if get_stack("stack_item")
  1941.         to = (upper(stack_item) = "TO")
  1942.         filter = get_stack("exp1")
  1943.     else
  1944.         error = 2
  1945.     endif
  1946. else
  1947.     error = 5
  1948. endif
  1949.  
  1950. do case
  1951.     case error = 5
  1952.         ERRS5 = .T.
  1953.  
  1954.     case error = 2 .or. !to .and. !filter
  1955.         ERRS2 = .T.
  1956.  
  1957.     case to .and. filter
  1958.         executor = "SETS"
  1959.         SETS17 = .T.
  1960.  
  1961.     case to .and. !filter
  1962.         executor = "SETS"
  1963.         SETS18 = .T.
  1964. endcase
  1965.  
  1966. return
  1967.  
  1968. *
  1969. ** eoproc filter
  1970.  
  1971.  
  1972. ***
  1973. * Procedure FIXED
  1974. * Evaluates the stack for the SET FIXED command, called by procedure SET.
  1975. * Sets execution class macro, class execution flag(s) and command line
  1976. * substitution macros.
  1977. *
  1978.  
  1979. procedure fixed
  1980.  
  1981. stack_ptr = 3
  1982.  
  1983. if stack_ptr <= max_ptr
  1984.     exp1 = upper(stack[stack_ptr])
  1985.     if "&exp1"$"ON^OFF"
  1986.         executor = "SETS"
  1987.         SETS8 = .T.
  1988.     else
  1989.         ERRS2 = .T.
  1990.     endif
  1991. else
  1992.     ERRS2 = .T.
  1993. endif
  1994.  
  1995. return
  1996.  
  1997. *
  1998. ** eoproc fixed
  1999.  
  2000.  
  2001. ***
  2002. * Procedure FUNC
  2003. * Evaluates the stack for the SET FUNCTION command, called by procedure SET.
  2004. * Sets execution class macro, class execution flag(s) and command line
  2005. * substitution macros.
  2006. *
  2007.  
  2008. procedure func_set
  2009.  
  2010. private stack_ptr, stack_item, string, to, key, error, active, null
  2011.  
  2012. stack_ptr = 3
  2013. store .F. to key, to, string, null
  2014. error = 0
  2015. active = 1  && 0 = error, 1 = function number, 2 = TO token, 3 = string.
  2016.  
  2017. do while stack_ptr <= max_ptr
  2018.  
  2019.     stack_item = ""
  2020.     null = get_stack("stack_item")
  2021.  
  2022.     if upper(stack_item) = "TO"
  2023.         if active = 2    && expected TO token.
  2024.             to = .T.
  2025.             active = 3
  2026.         else
  2027.             error = 2
  2028.         endif
  2029.     else
  2030.         do case
  2031.             case active = 0                && unexpected something.
  2032.                 error = 2
  2033.  
  2034.             case active = 1                && expecting key number.
  2035.                 exp1 = stack_item
  2036.                 if val(exp1) > 1 .and. val(exp1) < 41
  2037.                     key = .T.
  2038.                 else
  2039.                     error = 14
  2040.                 endif
  2041.                 active = 2
  2042.  
  2043.             case active = 3                && expecting string.
  2044.                 exp2 = stack_item
  2045.                 string = .T.
  2046.                 active = 0
  2047.         endcase
  2048.     endif
  2049. enddo
  2050.  
  2051. do case
  2052.     case error = 2
  2053.         ERRS2 = .T.
  2054.  
  2055.     case error = 14
  2056.         ERRS14 = .T.
  2057.  
  2058.     case key .and. to .and. string
  2059.         executor = "SETS"
  2060.         SETS9 = .T.
  2061.  
  2062.     otherwise
  2063.         ERRS2 = .T.
  2064. endcase
  2065.  
  2066. return
  2067.  
  2068. *
  2069. ** eoproc func
  2070.  
  2071.  
  2072. ***
  2073. * Procedure GOTO
  2074. * Evaluates the stack for the GO or GOTO verb.
  2075. * Sets execution class macro, class execution flag(s) and command line
  2076. * substitution macros.
  2077. *
  2078.  
  2079. procedure goto
  2080.  
  2081. private stack_ptr, stack_item, bottom, top, error
  2082.  
  2083. stack_ptr = 2
  2084. stack_item = ""
  2085. store .F. to bottom, top
  2086. error = 0
  2087.  
  2088. if DBF_OPEN .or. if(error_on, DBF_OPEN, .T.)  && check for open data file.
  2089.     if get_stack("stack_item")                && stack item exists.
  2090.  
  2091.         top = (upper(stack_item) == "TOP")
  2092.         bottom = cmd_abbr(upper(stack_item), "BOTTOM")
  2093.  
  2094.         if !top .and. !bottom
  2095.  
  2096.             exp1 = stack_item
  2097.  
  2098.             if error_on                       && check legal goto value.
  2099.                 do case
  2100.                     case &exp1 > lastrec()    && too big.
  2101.                         error = 6
  2102.                         
  2103.                     case &exp1 < 0            && too small.
  2104.                         error = 12
  2105.                 endcase
  2106.             endif
  2107.         endif
  2108.     else
  2109.         error = 2
  2110.     endif
  2111. else
  2112.     error = 5
  2113. endif
  2114.  
  2115. do case
  2116.     case error = 2
  2117.         ERRS2 = .T.
  2118.  
  2119.     case error = 5
  2120.         ERRS5 = .T.
  2121.  
  2122.     case error = 6
  2123.         ERRS6 = .T.
  2124.  
  2125.     case error = 12
  2126.         ERRS12 = .T.
  2127.  
  2128.     case !top .and. !bottom
  2129.         executor = "DBF_NTX"
  2130.         DBF_NTX7 = .T.
  2131.  
  2132.     case top
  2133.         executor = "DBF_NTX"
  2134.         DBF_NTX8 = .T.
  2135.  
  2136.     case bottom
  2137.         executor = "DBF_NTX"
  2138.         DBF_NTX9 = .T.
  2139. endcase
  2140.  
  2141. return
  2142.  
  2143. *
  2144. ** eoproc goto
  2145.  
  2146.  
  2147. ***
  2148. * Procedure help
  2149. * Help for DOT.
  2150. *
  2151.  
  2152. procedure help
  2153.  
  2154. parameters call_proc, line_num, call_var
  2155.  
  2156. set key 5 to
  2157.  
  2158. if call_proc = "HELP"
  2159.     return
  2160. endif
  2161.  
  2162. row = row()
  2163. col = col()
  2164.  
  2165. save screen
  2166. clear
  2167.  
  2168. text
  2169.                           Commands supported by DOT
  2170.  
  2171.   <F1> - Help
  2172.   <>  - History mode.  Up to [max_hist] commands are saved.  After
  2173.          [max_hist] commands have been saved, each new command is added
  2174.          to the end of the history array and the top command is thrown
  2175.          away.
  2176.  
  2177.          <>     - move backward through commands.
  2178.          <>     - move forward through commands.
  2179.          <ESC>   - returns without selecting a command.
  2180.          <─┘>   - executes the selection.
  2181.  
  2182.   @ <row>,<col> 
  2183.      [say <exp> [picture <clause>]]
  2184.      [get <exp> [picture <clause>] 
  2185.      [range <exp, exp>] [valid <exp>]]
  2186.      [clear]
  2187.   @ t, l, b, r BOX <string>
  2188.   ! or RUN <DOS command or file>
  2189.   ?  [<exp>]
  2190.   ?? [<exp>]
  2191.   <var> = <exp>              
  2192.  
  2193. endtext
  2194.  
  2195. wait "Strike any key for more help, <ESC> to return"
  2196.  
  2197. if lastkey() = 27
  2198.     set key 5 to history
  2199.     clear
  2200.     restore screen
  2201.     return
  2202. endif
  2203.  
  2204. clear
  2205.  
  2206. text
  2207.                           More commands supported by DOT
  2208.  
  2209.   accept [<string>] to <memvar>
  2210.   append blank
  2211.   call <procedure> [with <param1>[,<parameter list>]]
  2212.   clear
  2213.   cls
  2214.   copy [structure] to <filename>
  2215.   dir [<drive>][<path>][<skeleton>]
  2216.   display [<exp>[,<expression list>]]
  2217.   delete [<scope>][FOR/WHILE <expression>].
  2218.   do <procedure> [with <param1>[,<parameter list>]]
  2219.   erase <file name>.<extension>
  2220.   exit
  2221.   go[to] <exp>/TOP/BOTTOM
  2222.   index on <key expression> to <ntxfile>
  2223.   input [<string>] to <var> 
  2224.   list [<exp>[,<expression list>]]
  2225.   pack
  2226.   quit
  2227.   read
  2228.   recall [<scope>] [FOR/WHILE <expression>].
  2229.   release <var>
  2230.  
  2231. endtext
  2232.  
  2233. wait "Strike any key for more help, <ESC> to return"
  2234.  
  2235. if lastkey() = 27
  2236.     set key 5 to history
  2237.     clear
  2238.     restore screen
  2239.     return
  2240. endif
  2241.  
  2242. clear
  2243.  
  2244. text
  2245.                           More commands supported by DOT
  2246.  
  2247.   replace <fieldname> with <expression>
  2248.   return            ** Returns to previous level **
  2249.   seek <exp>
  2250.   select <exp>/<alias>  ** variables not usable **
  2251.   set color to <expression>
  2252.   set decimals to <expression>
  2253.   set default to <drive:>
  2254.   set delimiters <ON/OFF>
  2255.   set delimiters to [<string>]/[DEFAULT]
  2256.   set filter to [<filter expression>]
  2257.   set escape <ON/OFF>
  2258.   set exact <ON/OFF>
  2259.   set exclusive <ON/OFF>
  2260.   set fixed <ON/OFF>
  2261.   set function <function key number> to <string>
  2262.   set intensity <ON/OFF>
  2263.   set index to [<ntxfile>[,<ntxlist>]]]
  2264.   set key <ascii key number> to <string>
  2265.   set path to [<path expression>]
  2266.   set order to [<expN>]
  2267.   set relation to [<key expression> into <alias>]
  2268.  
  2269. endtext
  2270.  
  2271. wait "Strike any key for more help, <ESC> to return"
  2272.  
  2273. if lastkey() = 27
  2274.     set key 5 to history
  2275.     clear
  2276.     restore screen
  2277.     return
  2278. endif
  2279.  
  2280. clear
  2281.  
  2282. text
  2283.                           More commands supported by DOT
  2284.  
  2285.   skip [<exp>]
  2286.   type <file name>.<extension>
  2287.   unlock [ALL]
  2288.   use [<filename> [index <ntxfile>[,<ntxlist>]]][alias <alias name>]
  2289.       exclusive
  2290.   wait [[<string>][to <var>]]
  2291.   zap
  2292.  
  2293.                                    Comments
  2294.  
  2295.   1. Command MUST be entered as shown in HELP or error may be generated.
  2296.   2. Lists can contain up to 10 items. CALL or DO use up to 7 items.
  2297.   3. The SET FUNCTION command does not allow [F1] to be reset.
  2298.      Range [2] to [40]
  2299.   4. The SET KEY command does not allow [28] and [24] keys to be reset.
  2300.      Range [-39] to [387].
  2301.   5. The SET KEY command overrides the SET FUNCTION key.
  2302.   6. SET KEY should ONLY be used with VALID procedure names.
  2303.   7. If a GET is pending, DO NOT use History [] to execute a READ or
  2304.      the GET will be cleared.
  2305.  
  2306. endtext
  2307.  
  2308. wait "Strike any key for more help, <ESC> to return"
  2309.  
  2310. if lastkey() = 27
  2311.     set key 5 to history
  2312.     clear
  2313.     restore screen
  2314.     return
  2315. endif
  2316.  
  2317. clear
  2318.  
  2319. text
  2320.                                    Comments
  2321.  
  2322.   8. FOR and WHILE are NON-exclusive phrases.  WHILE takes precedence.
  2323.   9. When more than one scoping key word is present, control will be
  2324.      given to the last key word in the command line.
  2325.  10. Input and Display sections can use different I/O environments when
  2326.      SETs are issued.  See main DOT procedure.
  2327.  11. SAFETY is NOT on, BE FOREWARNED.
  2328.  12. Macros are expanded before being placed on stack so DOT may behave
  2329.      differently than a Clipper program with macros.
  2330.  
  2331.  
  2332.                               Flow Chart
  2333.  
  2334.   The next page contains a simple flow chart of the internal structure of
  2335.   the DOT test utility.  Upper case words represent the names of
  2336.   PROCEDURES called by the main DOT procedure.  Several macros are used
  2337.   to call procedures that will vary based on the contents of the stack.
  2338.   These cases are noted as such and do not use the upper case convention.
  2339.  
  2340. endtext
  2341.  
  2342. wait "Strike any key for more help, <ESC> to return"
  2343.  
  2344. if lastkey() = 27
  2345.     set key 5 to history
  2346.     clear
  2347.     restore screen
  2348.     return
  2349. endif
  2350.  
  2351. clear
  2352. text
  2353. DOT────>────── (initialize flags, execution and control variables)
  2354.                    
  2355.                FILL_LIST    ** initialize search string variables.
  2356.                    
  2357.   ┌─────>───── (initialize stack array) 
  2358.   │                
  2359.   │             INPUT_LN    ** put cursor at bottom of screen.
  2360.   │                
  2361.   │             (input)     ** accept the command line from the console.
  2362.   │                
  2363.   │             INPUT_LN    ** return to display portion of screen.
  2364.   │                
  2365.                 PARSE      ** place components of command line on stack.
  2366.   │                
  2367.   │             SET_LEX     ** set analysis procedure macro "lex_proc".
  2368.   │                
  2369.   │            (analyze)    ** do analyze procedure macro "lex_proc".
  2370.   │                
  2371.   │             HIST_PUT    ** put command into history array.
  2372.   │                
  2373.   │            (execute)    ** do execution procedure macro "executor".
  2374.   │                
  2375.   └─────<───── (reset command line substitution macro variables)
  2376. endtext
  2377.  
  2378. wait "Strike any key for more help, <ESC> to return"
  2379.  
  2380. if lastkey() = 27
  2381.     set key 5 to history
  2382.     clear
  2383.     restore screen
  2384.     return
  2385. endif
  2386.  
  2387. clear
  2388. text
  2389.                              DOT assistance programs
  2390.  
  2391.   what_key   : Returns the numeric value of a key. <ALT-Q> aborts.
  2392.   hist_purge : Empties the history array.
  2393.   set_sets   : Reset all the SET commands listed to their DEFAULT
  2394.                setting.
  2395.  
  2396.                            Internal Control Variables
  2397.  
  2398.   bottom_on = .T.  -  Places the input window at the bottom of the screen.
  2399.   error_on  = .T.  -  Checks for DBF, NTX ON/OFF or existence.
  2400.   max_hist  = 20   -  Maximum number of history item stored before
  2401.                       overwrites of earlier 'saved' commands starts.
  2402.  
  2403. endtext
  2404.  
  2405. wait "Strike any key to continue."
  2406.  
  2407. clear
  2408.  
  2409. set key 5 to history
  2410. restore screen
  2411. return
  2412.  
  2413. *
  2414. ** eoproc help
  2415.  
  2416.  
  2417. ***
  2418. * Procedure hist_purge
  2419. * Purges the history array.
  2420. *
  2421.  
  2422. procedure hist_purge
  2423.  
  2424. do while hist_max > 0
  2425.     history[hist_max] = ""
  2426.     hist_max = hist_max - 1
  2427. enddo
  2428. hist_ptr = 0
  2429.  
  2430. return
  2431.  
  2432. *
  2433. ** eoproc hist_purge
  2434.  
  2435.  
  2436. ***
  2437. * Procedure hist_put
  2438. * Stores command into the history array
  2439. *
  2440.  
  2441. procedure hist_put
  2442.  
  2443. if hist_max < max_hist
  2444.     hist_max = hist_max + 1
  2445. else 
  2446.     for i = 2 to max_hist 
  2447.         history[i-1] = history[i]
  2448.     next
  2449. endif
  2450.  
  2451. history[hist_max] = command
  2452.  
  2453. return
  2454.  
  2455. *
  2456. ** eoproc hist_put
  2457.  
  2458.  
  2459. ***
  2460. * Procedure history
  2461. * Allows user to select from the list of history'd commands.
  2462. *
  2463.  
  2464. procedure history
  2465.  
  2466. parameters call_proc, call_line, call_var
  2467.  
  2468. private key, hist_ptr, curr_row, curr_col, cmd_line
  2469.  
  2470. if hist_max > 0 .and. call_proc <> "HISTORY"
  2471.  
  2472.     set intensity on
  2473.     clear gets
  2474.  
  2475.     key = 0
  2476.     hist_ptr = hist_max
  2477.     curr_row = row()
  2478.     curr_col = col()
  2479.  
  2480.     set key 5 to stuff_up
  2481.     set key 24 to stuff_dn
  2482.  
  2483.     do while .T.
  2484.         cmd_line = history[hist_ptr] + space(77 - len(history[hist_ptr]))
  2485.         @ curr_row, curr_col get cmd_line
  2486.         read
  2487.  
  2488.         key = lastkey()
  2489.  
  2490.         do case
  2491.             case key = 5
  2492.                 ** up-arrow, backwards **
  2493.                 hist_ptr = hist_ptr - 1
  2494.                 if hist_ptr <= 0
  2495.                     hist_ptr = hist_max
  2496.                 endif
  2497.     
  2498.             case key = 24
  2499.                 ** down-arrow, forward **
  2500.                 hist_ptr = hist_ptr + 1
  2501.                 if hist_ptr > hist_max
  2502.                     hist_ptr = 1
  2503.                 endif
  2504.  
  2505.             case key = 13 .or. key = 27
  2506.                 if key = 13
  2507.                     keyboard trim(cmd_line) + chr(13)
  2508.                 endif
  2509.                 @ curr_row, curr_col
  2510.                 set intensity &inten_stat
  2511.                 set key 5 to history
  2512.                 set key 24 to
  2513.                 return
  2514.         endcase
  2515.     enddo
  2516. endif
  2517.  
  2518. *
  2519. ** eoproc history
  2520.  
  2521.  
  2522. ***
  2523. * Procedure INDEX
  2524. * Evaluates the stack for the INDEX verb.
  2525. * Sets execution class macro, class execution flag(s) and command line
  2526. * substitution macros.
  2527. *
  2528.  
  2529. procedure index
  2530.  
  2531. private stack_ptr, stack_item, item_ok, on, to, key, file, active, error
  2532.  
  2533. stack_ptr = 2
  2534. store .F. to on, to, key, file
  2535. active = 1    && 0 = error, 1 = key, 2 = file.
  2536. error = 0
  2537.  
  2538. if error_on .and. !DBF_OPEN  && if file checking is on and file is not open.
  2539.     error = 5
  2540. endif
  2541.  
  2542. do while stack_ptr <= max_ptr .and. error = 0
  2543.     stack_item = ""
  2544.     item_ok = get_stack("stack_item")
  2545.  
  2546.     do case
  2547.         case upper(stack_item) = "ON" .and. !on
  2548.             on = .T.
  2549.             active = 1
  2550.  
  2551.         case upper(stack_item) = "TO" .and. !to
  2552.             to = .T.
  2553.             active = 2
  2554.  
  2555.         otherwise
  2556.             do case
  2557.                 case active = 1
  2558.                     key = .T.
  2559.                     exp1 = stack_item
  2560.                     if !file
  2561.                         active = 2
  2562.                     else
  2563.                         active = 0
  2564.                     endif
  2565.  
  2566.                 case active = 2
  2567.                     file = .T.
  2568.                     ntx_file = stack_item
  2569.                     if !key
  2570.                         active = 1
  2571.                     else
  2572.                         active = 0
  2573.                     endif
  2574.  
  2575.                 otherwise
  2576.                     error = 2
  2577.             endcase
  2578.     endcase
  2579. enddo
  2580.  
  2581. do case
  2582.     case error = 2
  2583.         ERRS2 = .T.
  2584.  
  2585.     case error = 5
  2586.         ERRS5 = .T.
  2587.     
  2588.     case on .and. to .and. key .and. file
  2589.         executor = "DBF_NTX"
  2590.         DBF_NTX6 = .T.
  2591.  
  2592.     otherwise
  2593.         ERRS2 = .T.
  2594. endcase
  2595.  
  2596. return
  2597.  
  2598. *
  2599. ** eoproc index
  2600.  
  2601.  
  2602. ***
  2603. * Procedure INDEX_set
  2604. * Evaluates stack for SET INDEX TO command.  Called by procedure SET.
  2605. * Sets execution class macro, class execution flag(s) and command line
  2606. * substitution macros.
  2607. *
  2608.  
  2609. procedure index_set
  2610.  
  2611. private stack_ptr, stack_item, item_ok, to, file, error
  2612.  
  2613. stack_ptr = 3
  2614. stack_item = ""
  2615. store .F. to item_ok, to, file
  2616. error = 0
  2617.  
  2618. if error_on .and. !DBF_OPEN        && check for open data file.
  2619.     error = 5
  2620. else
  2621.     stack_item = stack[stack_ptr]
  2622.  
  2623.     if (upper(stack_item) == "TO")
  2624.         to = .T.
  2625.         file = get_list("NF")
  2626.  
  2627.         if !file                   && error occurred in building list.
  2628.             if empty(list0)        && list is empty, turn indexes off.
  2629.                 file = .T.
  2630.             else                   && index file not found.
  2631.                 error = 11
  2632.             endif
  2633.         endif
  2634.     else
  2635.         error = 2
  2636.     endif
  2637. endif
  2638.  
  2639. do case
  2640.     case error = 2
  2641.         ERRS2 = .T.
  2642.  
  2643.     case error = 5
  2644.         ERRS5 = .T.
  2645.  
  2646.     case error = 11
  2647.         ERRS11 = .T.
  2648.  
  2649.     case to .and. file
  2650.         executor = "SETS"
  2651.         SETS10 = .T.
  2652. endcase
  2653.  
  2654. return
  2655.  
  2656. *
  2657. ** eoproc index_set
  2658.  
  2659.  
  2660. ***
  2661. * Procedure INPUT
  2662. * Evaluates stack for INPUT verb.
  2663. * Sets execution class macro, class execution flag(s) and command line
  2664. * substitution macros.
  2665. *
  2666.  
  2667. procedure input
  2668.  
  2669. private stack_ptr, string, to, dest, stack_item
  2670.  
  2671. stack_ptr = 1
  2672. store .F. to string, to, dest
  2673.  
  2674. do while stack_ptr <= max_ptr
  2675.     stack_item = upper(stack[stack_ptr])
  2676.     do case
  2677.         case stack_item = "INPU"
  2678.             string = get_expr1("exp1")
  2679.             if upper(exp1) = "TO"
  2680.                 string = .F.
  2681.                 exp1 = ""
  2682.                 stack_ptr = stack_ptr - 1
  2683.             endif
  2684.  
  2685.         case stack_item = "TO"
  2686.             to = .T.
  2687.             dest = get_expr1("var1")
  2688.         otherwise
  2689.             stack_ptr = stack_ptr + 1
  2690.     endcase
  2691. enddo
  2692.  
  2693. if !err()
  2694.     do case
  2695.         case to .and. dest .and. !string
  2696.             executor = "VARS"
  2697.             VARS3 = .T.
  2698.             VARS9 = .T.
  2699.  
  2700.         case to .and. dest .and. string
  2701.             executor = "VARS"
  2702.             VARS4 = .T.
  2703.             VARS9 = .T.
  2704.  
  2705.         otherwise
  2706.             ERRS2 = .T.
  2707.     endcase
  2708. endif
  2709.  
  2710. return
  2711.  
  2712. *
  2713. ** eoproc input
  2714.  
  2715.  
  2716. ***
  2717. * Procedure input_ln
  2718. * Places the input line on the bottom of screen and manages the
  2719. * placement of the end of output diamond.
  2720. *
  2721.  
  2722. procedure input_ln
  2723.  
  2724. parameters when
  2725.  
  2726. if when = "B"
  2727.     save_row = row()
  2728.     save_col = col()
  2729.  
  2730.     ?? chr(4)                && display cursor position marker.
  2731.  
  2732.     @ MaxRow(), 0 say ""
  2733.  
  2734.     do while (save_row > MaxRow()-2)
  2735.         ?
  2736.         save_row = save_row - 1
  2737.     enddo
  2738.  
  2739.     @ MaxRow()-1, 0 clear
  2740.     @ MaxRow()-1, 0 say cmd_line
  2741.     @ MaxRow()-1, 0 say ""
  2742. else
  2743.     @ MaxRow()-1, 0 clear
  2744.     @ save_row, save_col say " "
  2745.     @ save_row, save_col say ""
  2746. endif
  2747.  
  2748. return
  2749.  
  2750. *
  2751. ** eoproc input_ln
  2752.  
  2753.  
  2754. ***
  2755. * Procedure INTENSITY
  2756. * Evaluates the stack for the SET INTENSITY command.  Called by the 
  2757. * SET procedure.
  2758. * Sets execution class macro, class execution flag(s) and command line
  2759. * substitution macros.
  2760. *
  2761.  
  2762. procedure intensity
  2763.  
  2764. stack_ptr = 2
  2765.  
  2766. if get_expr1("exp1")
  2767.     if exp1$"ON^OFF"
  2768.         executor = "SETS"
  2769.         SETS11 = .T.
  2770.     else
  2771.         ERRS2 = .T.
  2772.     endif
  2773. else
  2774.     ERRS2 = .T.
  2775. endif
  2776.  
  2777. return
  2778.  
  2779. *
  2780. ** eoproc intensity
  2781.  
  2782.  
  2783. ***
  2784. * Procedure KEY
  2785. * Evaluates the stack for the SET KEY command.  Called from procedure
  2786. * SET.
  2787. * Sets execution class macro, class execution flag(s) and command line
  2788. * substitution macros.
  2789. * Does not allow [F1] or [] to be reset.
  2790. *
  2791.  
  2792. procedure key
  2793.  
  2794. private stack_ptr, string, to, key, null, stack_item
  2795.  
  2796. stack_ptr = 2
  2797. store .F. to key, to, null
  2798.  
  2799. do while stack_ptr <= max_ptr
  2800.     stack_item = upper(stack[stack_ptr])
  2801.     do case
  2802.         case stack_item = "KEY"
  2803.             key = get_expr1("exp1")
  2804.             if key .and. val(exp1) > -40 .and. val(exp1) < 388;
  2805.                 .and. val(exp1) <> 28 .and. val(exp1) <> 24
  2806.                 key = .T.
  2807.             endif
  2808.  
  2809.         case stack_item = "TO"
  2810.             to = .T.
  2811.             null = get_expr1("exp2")
  2812.  
  2813.         otherwise
  2814.             stack_ptr = stack_ptr + 1
  2815.     endcase
  2816. enddo
  2817.  
  2818. if !err()
  2819.     if key .and. to
  2820.         executor = "SETS"
  2821.         SETS14 = .T.
  2822.     else
  2823.         ERRS2 = .T.
  2824.     endif
  2825. endif
  2826.  
  2827. return
  2828.  
  2829. *
  2830. ** eoproc key
  2831.  
  2832.  
  2833. ***
  2834. * Procedure LIST
  2835. * Evaluates stack for the LIST verb.
  2836. * Sets execution class macro, class execution flag(s) and command line
  2837. * substitution macros.
  2838. *
  2839.  
  2840. procedure list
  2841.  
  2842. private stack_ptr
  2843.  
  2844. stack_ptr = 1
  2845.  
  2846. if DBF_OPEN .or. !error_on
  2847.     if max_ptr = 1
  2848.         executor = "DBF_NTX"
  2849.         DBF_NTX12 = .T.
  2850.     else
  2851.         if get_list("E")
  2852.             executor = "DBF_NTX"
  2853.             DBF_NTX13 = .T.
  2854.         else
  2855.             ERRS2 = .T.
  2856.         endif
  2857.     endif
  2858. else
  2859.     ERRS5 = .T.
  2860. endif
  2861.  
  2862. return
  2863.  
  2864. *
  2865. ** eoproc list
  2866.  
  2867.  
  2868. ***
  2869. * Procedure list_do
  2870. * Emulates the LIST/DISPLAY command, called LIST executor.
  2871. *
  2872. * Usage : list_do <logical 1>, <logical 2>
  2873. * Where :    <logical 1> = record number display flag.
  2874. *         :    <logical 2> = LIST/DISPLAY flag. .T. = DISPLAY mode
  2875. *
  2876.  
  2877. procedure list_do
  2878.  
  2879. parameters recno_on, is_display
  2880.  
  2881. private disp_count, count, header, l_part1, l_part2, l_part3, use_part2,;
  2882.     use_part3
  2883.  
  2884. if recno_on
  2885.     header = "[Record#  "
  2886.     l_part1 = "str(recno(),7)+space(2)"
  2887. else
  2888.     header = "["
  2889.     l_part1 = "space(0)"
  2890. endif
  2891.  
  2892. l_part2 = "space(0)"
  2893. l_part3 = "space(0)"
  2894.  
  2895. use_part2 = .F.
  2896. use_part3 = .F.
  2897.  
  2898. count = 1
  2899.  
  2900. do while "" <> fieldname(count)
  2901.     header = header + spacer_h(fieldname(count))
  2902.     if len(l_part1) < 150
  2903.         l_part1 = l_part1 + "+" + fld_form(fieldname(count)) + "+space(" +;
  2904.             spacer_l(fieldname(count)) + ")"
  2905.     else
  2906.         if len(l_part2) < 150
  2907.             l_part2 = l_part2 + "+" + fld_form(fieldname(count)) + "+space(" +;
  2908.                 spacer_l(fieldname(count)) + ")"
  2909.         else
  2910.             l_part3 = l_part3 + "+" + fld_form(fieldname(count)) + "+space(" +;
  2911.                 spacer_l(fieldname(count)) + ")"
  2912.         endif
  2913.     endif
  2914.     count = count + 1
  2915. enddo
  2916.  
  2917. header = header + "]"
  2918.  
  2919. use_part2 = !empty(&l_part2)
  2920. use_part3 = !empty(&l_part3)
  2921.  
  2922. ? &header
  2923.  
  2924. if !eof()
  2925.     for i = 1 to if(!is_display, lastrec(), 1)
  2926.         ? &l_part1
  2927.  
  2928.         if use_part2
  2929.             ?? &l_part2
  2930.             if use_part3
  2931.                 ?? &l_part3
  2932.             endif
  2933.         endif
  2934.  
  2935.         if !is_display
  2936.             skip
  2937.         endif
  2938.  
  2939.         if inkey() = 27
  2940.             return        
  2941.         endif
  2942.     next
  2943. endif
  2944.  
  2945. return
  2946.  
  2947. *
  2948. ** eoproc list_do
  2949.  
  2950.  
  2951. ***
  2952. * Procedure ORDER
  2953. * Evaluates stack for the SET ORDER command. Called from SET procedure.
  2954. * Sets execution class macro, class execution flag(s) and command line
  2955. * substitution macros.
  2956. *
  2957.  
  2958. procedure order
  2959.  
  2960. private stack_ptr, stack_item, to, exp, null
  2961.  
  2962. stack_ptr = 3
  2963.  
  2964. store .F. to to, exp, null
  2965.  
  2966. do while stack_ptr <= max_ptr
  2967.     stack_item = ""
  2968.     null = get_stack("stack_item")
  2969.  
  2970.     if upper(stack_item) = "TO" .and. !to
  2971.         to = .T.
  2972.     else
  2973.         exp1 = stack_item
  2974.         exp = .T.
  2975.     endif
  2976. enddo
  2977.  
  2978. do case
  2979.     case !(DBF_OPEN) .and. error_on
  2980.         ERRS5 = .T.
  2981.  
  2982.     case !(NTX_OPEN) .and. error_on
  2983.         ERRS9 = .T.
  2984.  
  2985.     case to .and. exp
  2986.         executor = "SETS"
  2987.         SETS21 = .T.
  2988.  
  2989.     case to .and. !exp
  2990.         executor = "SETS"
  2991.         SETS22 = .T.
  2992.     
  2993.     otherwise
  2994.         ERRS2 = .T.
  2995.  
  2996. endcase
  2997.  
  2998. return
  2999.  
  3000. *
  3001. ** eoproc order
  3002.  
  3003.  
  3004. ***
  3005. * Procedure PACK
  3006. * Evaluates the stack for PACK verb.
  3007. * Sets execution class macro, class execution flag(s) and command line
  3008. * substitution macros.
  3009. *
  3010.  
  3011. procedure pack
  3012.  
  3013. if max_ptr = 1
  3014.     if DBF_OPEN .or. !error_on
  3015.         executor = "DBF_NTX"
  3016.         DBF_NTX21 = .T.
  3017.     else
  3018.         ERRS5 = .T.
  3019.     endif
  3020. else
  3021.     ERRS2 = .T.
  3022. endif
  3023.  
  3024. return
  3025.  
  3026. *
  3027. ** eoproc pack
  3028.  
  3029.  
  3030. ***
  3031. * Procedure parse
  3032. * breaks command line into tokens and populates stack.
  3033. *
  3034.  
  3035. procedure parse
  3036.  
  3037. parameters stack_max
  3038.  
  3039. private line_len, scan_ptr, parse_more, tokens, collect_it, scan_char,;
  3040.     next_char, inc_before, inc_after, start_char, stop_char, item_count,;
  3041.     more_char
  3042.  
  3043. command = trim(ltrim(command))
  3044.  
  3045. if !empty(command)
  3046.     line_len = len(command)
  3047.     scan_ptr = 1
  3048.     parse_more = .T.
  3049.     tokens = " +-*/%<>#,!@.$^?=[()]'" + ["]
  3050.     stack_ptr = 1
  3051.     stack[1] = ""
  3052.     collect_it = .F.
  3053.     inc_before = .F.
  3054.     inc_after = .F.
  3055. else
  3056.     parse_more = .F.
  3057. endif
  3058.  
  3059. do while parse_more
  3060.  
  3061.     scan_char = substr(command, scan_ptr, 1)
  3062.  
  3063.     do case
  3064.         case !scan_char$tokens .and. "" <> scan_char
  3065.             ** if the scan character is NOT one of the parsed characters **
  3066.             collect_it = .T.
  3067.  
  3068.         case "" = scan_char
  3069.             ** if scan character is NULL, stop the parser. **
  3070.             parse_more = .F.
  3071.  
  3072.         case scan_char = " "
  3073.             ** if the scan character is a blank, check if stack element is **
  3074.             ** empty. If not, set the pre-collection stack increment flag **
  3075.             ** to true.                                                     ** 
  3076.  
  3077.             if "" <> stack[stack_ptr]
  3078.                 inc_before = .T.
  3079.             endif
  3080.  
  3081.         case scan_char$"+-*/%<>#,!@.$^?="
  3082.             ** If the scan character is one of the parsed elements set the **
  3083.             ** collector flag true, initialize the next character variable, **
  3084.             ** and check if either the pre or post collection flags need to **
  3085.             ** be set.                                                        **
  3086.  
  3087.             collect_it = .T.
  3088.  
  3089.             if stack[stack_ptr] <> scan_char
  3090.                 if "" <> stack[stack_ptr]
  3091.                     inc_before = .T.
  3092.                 endif
  3093.             endif
  3094.  
  3095.             next_char = if((scan_ptr+1) <= line_len,;
  3096.                 substr(command, scan_ptr+1, 1), "")
  3097.             if !next_char$tokens .and. "" <> next_char
  3098.                 inc_after = .T.
  3099.             endif
  3100.  
  3101.         case scan_char$"[('" .or. scan_char = ["]
  3102.             ** if the scan character is a string delimiter or a **
  3103.             ** grouping operator, check for any empty stack element **
  3104.             ** then check for balanced delimiters or groupers. **
  3105.  
  3106.             if "" <> stack[stack_ptr]
  3107.                 stack_ptr = stack_ptr + 1
  3108.                 stack[stack_ptr] = ""
  3109.             endif
  3110.  
  3111.             start_char = scan_char
  3112.  
  3113.             if scan_char = "("
  3114.                 stop_char = ")"
  3115.             else
  3116.                 if scan_char = "["
  3117.                     stop_char = "]"
  3118.                 else
  3119.                     stop_char = scan_char
  3120.                 endif
  3121.             endif
  3122.  
  3123.             item_count = 0
  3124.             more_char = .T.
  3125.  
  3126.             do while more_char            
  3127.                 stack[stack_ptr] = stack[stack_ptr] + scan_char
  3128.  
  3129.                 if start_char <> stop_char
  3130.                     if scan_char = start_char
  3131.                         item_count = item_count + 1
  3132.                     else
  3133.                         if scan_char = stop_char
  3134.                             item_count = item_count - 1
  3135.                         endif
  3136.                     endif
  3137.                 else
  3138.                     if item_count > 0
  3139.                         if scan_char = stop_char
  3140.                             item_count = item_count - 1
  3141.                         endif
  3142.                     else
  3143.                         item_count = 1
  3144.                     endif
  3145.                 endif
  3146.  
  3147.                 if item_count = 0 .or. "" = scan_char
  3148.                     more_char = .F.
  3149.                 else
  3150.                     scan_ptr = scan_ptr + 1
  3151.                     scan_char = substr(command, scan_ptr, 1)
  3152.                 endif
  3153.             enddo
  3154.             
  3155.             if scan_ptr > line_len
  3156.                 ERRS8 = .T.
  3157.             else
  3158.                 next_char = substr(command, scan_ptr + 1,1)
  3159.                 if !next_char$tokens .and. "" <> next_char
  3160.                     inc_after = .T.
  3161.                 endif
  3162.             endif
  3163.  
  3164.     endcase
  3165.      
  3166.     if inc_before
  3167.         stack_ptr = stack_ptr + 1
  3168.         stack[stack_ptr] = ""
  3169.         inc_before = .F.
  3170.     endif
  3171.  
  3172.     if collect_it                    && add current char to stack.
  3173.         stack[stack_ptr] = stack[stack_ptr] + scan_char
  3174.         collect_it = .F.
  3175.     endif
  3176.  
  3177.     if inc_after                     && increment after adding char.
  3178.         stack_ptr = stack_ptr + 1
  3179.         stack[stack_ptr] = ""
  3180.         inc_after = .F.
  3181.     endif
  3182.  
  3183.     scan_ptr = scan_ptr + 1
  3184.  
  3185. enddo
  3186.  
  3187. return
  3188.  
  3189. *
  3190. ** eoproc parse
  3191.  
  3192.  
  3193. ***
  3194. * Procedure PATH
  3195. * Evaluates stack for SET PATH command.  Called from SET procedure.
  3196. * Sets execution class macro, class execution flag(s) and command line
  3197. * substitution macros.
  3198. *
  3199.  
  3200. procedure path
  3201.  
  3202. private stack_ptr, to, null
  3203.  
  3204. stack_ptr = 3
  3205. store .F. to to, null
  3206.  
  3207. if upper(stack[stack_ptr]) = "TO"
  3208.     to = .T.
  3209.     null = get_expr1("exp1")
  3210. endif
  3211.  
  3212. if to
  3213.     executor = "SETS"
  3214.     SETS12 = .T.
  3215. else
  3216.     ERRS2 = .T.
  3217. endif
  3218.  
  3219. return
  3220.  
  3221. *
  3222. ** eoproc path
  3223.  
  3224.  
  3225. ***
  3226. * Procedure ques1
  3227. * Evaluates stack for single question mark (?).
  3228. * Sets execution class macro, class execution flag(s) and command line
  3229. * substitution macros.
  3230. *
  3231.  
  3232. procedure ques1
  3233.  
  3234. private stack_ptr
  3235.  
  3236. stack_ptr = 2
  3237.  
  3238. if get_stack("exp1")
  3239.     executor = "SCRN"
  3240.     SCRN25 = .T.
  3241. else
  3242.     executor = "SCRN"
  3243.     SCRN24 = .T.
  3244. endif
  3245.  
  3246. return 
  3247.  
  3248. *
  3249. ** eoproc ques1
  3250.     
  3251.  
  3252. ***
  3253. * Procedure ques2
  3254. * Evaluates stack for double question marks (??).
  3255. * Sets execution class macro, class execution flag(s) and command line
  3256. * substitution macros.
  3257. *
  3258.  
  3259. procedure ques2
  3260.  
  3261. private stack_ptr
  3262.  
  3263. stack_ptr = 1
  3264.  
  3265. if get_expr1("exp1")
  3266.     executor = "SCRN"
  3267.     SCRN27 = .T.
  3268. else
  3269.     executor = "SCRN"
  3270.     SCRN26 = .T.
  3271. endif
  3272.  
  3273. return 
  3274.  
  3275. *
  3276. ** eoproc ques2
  3277.  
  3278.  
  3279. ***
  3280. * Procedure QUIT
  3281. * called from analyze, analyzes the stack for the QUIT, EXIT or
  3282. * RETURN verb.
  3283. *
  3284.  
  3285. procedure quit
  3286.  
  3287. if max_ptr = 1
  3288.     executor = "CALLS"
  3289.     if stack[1]$"QUIT EXIT"
  3290.         CALLS6 = .T.
  3291.     else
  3292.         CALLS7 = .T.
  3293.     endif
  3294. else
  3295.     ERRS2 = .T.
  3296. endif
  3297.  
  3298. return
  3299.  
  3300. *
  3301. ** eoproc quit
  3302.  
  3303.  
  3304. ***
  3305. * Procedure rREAD
  3306. * Evaluates stack for READ verb. 
  3307. * Sets execution class macro, class execution flag(s) and command line
  3308. * substitution macros.
  3309. *
  3310.  
  3311. procedure rread
  3312.  
  3313. executor = "SCRN"
  3314. SCRN28 = .T.
  3315.  
  3316. return
  3317.  
  3318. *
  3319. ** eoproc rread
  3320.  
  3321.  
  3322. ***
  3323. * Procedure RECALL
  3324. * Evaluates the stack for RECALL verb.  Calls the condition and
  3325. * scope analyzer CND_SCP to set condition and scope flags and
  3326. * expressions.
  3327. * Sets execution class macro, class execution flag(s) and command line
  3328. * substitution macros.
  3329. *
  3330.  
  3331. procedure recall
  3332.  
  3333. private stack_ptr, for, while, next, record, all, stack_item
  3334.  
  3335. stack_ptr = 2
  3336. store .F. to for, while, next, record, all, condition
  3337. scope = 0
  3338.  
  3339. if cnd_scp()    && no errors during generic condition and scope analysis.
  3340.     do case 
  3341.         case for .or. while .or. all .or. next .or. record
  3342.             ** w/ w/o scope and/or condition. **
  3343.             if DBF_OPEN .or. !error_on
  3344.                 executor = "DBF_NTX"
  3345.                 DBF_NTX20 = .T.
  3346.             else    
  3347.                 ERRS5 = .T.
  3348.             endif
  3349.  
  3350.         case !for .and. !while .and. !all .and. !next .and. !record;
  3351.             .and. max_ptr = 1
  3352.             ** w/o scope or conditional **
  3353.             if DBF_OPEN .or. !error_on
  3354.                 executor = "DBF_NTX"
  3355.                 DBF_NTX20 = .T.
  3356.                 scope = 1       && use RECORD (scope = 1) for single recall.
  3357.                 exp3 = str(recno())
  3358.  
  3359.                 if &exp3 > lastrec() .and. error_on
  3360.                     ERRS6 = .T.
  3361.                     DBF_NTX20 = .F.
  3362.                 else
  3363.                     exp3 = "recno() = &exp3"
  3364.                 endif
  3365.             else
  3366.                 ERRS5 = .T.
  3367.             endif
  3368.  
  3369.         otherwise        
  3370.             ERRS2 = .T.
  3371.     endcase        
  3372. endif
  3373.  
  3374. return
  3375.  
  3376. *
  3377. ** eoproc recall
  3378.  
  3379.  
  3380. ***
  3381. * Procedure recall_it
  3382. * Called by do_cnd_scp called from DBF_NTX execution procedure.
  3383. *
  3384.  
  3385. procedure recall_it
  3386.  
  3387. recall
  3388.  
  3389. return
  3390.  
  3391. *
  3392. ** eoproc recall_it
  3393.  
  3394.  
  3395. ***
  3396. * Procedure RELATE
  3397. * Evaluates stack for SET RELATION command.  Called from SET procedure.
  3398. * Sets execution class macro, class execution flag(s) and command line
  3399. * substitution macros.
  3400. *
  3401.  
  3402. procedure relate
  3403.  
  3404. private stack_ptr, to, exp, alias, stack_item
  3405.  
  3406. stack_ptr = 3
  3407. store .F. to to, exp, alias
  3408.  
  3409. do while stack_ptr <= max_ptr
  3410.     stack_item = upper(stack[stack_ptr])
  3411.     do case
  3412.         case stack_item = "TO"
  3413.             to = .T.
  3414.             exp = get_expr1("exp1")
  3415.  
  3416.         case stack_item = "INTO"
  3417.             alias = get_expr1("exp2")
  3418.  
  3419.         otherwise
  3420.             stack_ptr = stack_ptr + 1
  3421.     endcase
  3422. enddo
  3423.  
  3424. if !err()
  3425.     do case
  3426.         case to .and. exp .and. alias .and. if(error_on, DBF_OPEN, .T.)
  3427.             executor = "SETS"
  3428.             SETS16 = .T.
  3429.  
  3430.         case to .and. !exp .and. !alias .and. if(error_on, DBF_OPEN, .T.)
  3431.             executor = "SETS"
  3432.             SETS15 = .T.
  3433.  
  3434.         case if(error_on, !DBF_OPEN, .F.)
  3435.             ERRS5 = .T.
  3436.  
  3437.         otherwise
  3438.             ERRS2 = .T.
  3439.     endcase
  3440. endif
  3441.  
  3442. return
  3443.  
  3444. *
  3445. ** eoproc relate
  3446.  
  3447.  
  3448. ***
  3449. * Procedure RELEASE
  3450. * Evaluates stack for the RELEASE verb.
  3451. * Sets execution class macro, class execution flag(s) and command line
  3452. * substitution macros.
  3453. *
  3454.  
  3455. procedure release
  3456.  
  3457. private stack_ptr
  3458.  
  3459. stack_ptr = 2
  3460.  
  3461. if max_ptr = 2
  3462.     var1 = stack[stack_ptr]
  3463.     if type("&var1") <> "U"
  3464.         executor = "VARS"
  3465.         VARS11 = .T.
  3466.     else
  3467.         ERRS3 = .T.
  3468.     endif
  3469. else
  3470.     ERRS2 = .T.
  3471. endif
  3472.  
  3473. return
  3474.  
  3475. *
  3476. ** eoproc release
  3477.  
  3478.  
  3479. ***
  3480. * Procedure REPLACE
  3481. * Evaluates stack for the REPLACE command.
  3482. * Sets execution class macro, class execution flag(s) and command line
  3483. * substitution macros.
  3484. *
  3485.  
  3486. procedure replace
  3487.  
  3488. private stack_ptr, stack_item, dest, with, source, all, null
  3489.  
  3490. stack_ptr = 2
  3491. store .F. to dest, with, source, all
  3492.  
  3493. do while stack_ptr <= max_ptr
  3494.  
  3495.     stack_item = ""
  3496.     null = get_stack("stack_item")
  3497.  
  3498.     do case
  3499.         case upper(stack_item) = "ALL"
  3500.             all = .T.
  3501.  
  3502.         case upper(stack_item) = "WITH"
  3503.             with = .T.
  3504.  
  3505.         otherwise
  3506.             if "" == var1
  3507.                 var1 = stack_item
  3508.                 dest = .T.
  3509.             else
  3510.                 exp1 = stack_item
  3511.                 source = .T.
  3512.             endif
  3513.     endcase
  3514. enddo
  3515.  
  3516. do case
  3517.     case !DBF_OPEN .and. error_on
  3518.         ERRS5 = .T.
  3519.  
  3520.     case dest .and. with .and. source .and. !all
  3521.         executor = "DBF_NTX"
  3522.         DBF_NTX26 = .T.
  3523.  
  3524.     case dest .and. with .and. source .and. all
  3525.         executor = "DBF_NTX"
  3526.         DBF_NTX27 = .T.
  3527.  
  3528.     otherwise
  3529.         ERRS2 = .T.
  3530. endcase
  3531.  
  3532. return
  3533.  
  3534. *
  3535. ** eoproc replace
  3536.  
  3537.  
  3538. ***
  3539. * Procedure RUN
  3540. * Evaluates stack for the RUN or ! verb.
  3541. * Sets execution class macro, class execution flag(s) and command line
  3542. * substitution macros.
  3543. *
  3544.  
  3545. procedure run
  3546.  
  3547. exp1 = substr(command, len(stack[1]) + 1)
  3548.  
  3549. if !empty(exp1)
  3550.     executor = "CALLS"
  3551.     CALLS3 = .T.
  3552. else
  3553.     ERRS2 = .T.
  3554. endif
  3555.  
  3556. return
  3557.  
  3558. *
  3559. ** eoproc run
  3560.  
  3561.  
  3562. ***
  3563. * Procedure SEEK
  3564. * Evaluates stack for the SEEK verb.
  3565. * Sets execution class macro, class execution flag(s) and command line
  3566. * substitution macros.
  3567. *
  3568.  
  3569. procedure seek
  3570.  
  3571. private stack_ptr
  3572.  
  3573. stack_ptr = 1
  3574.  
  3575. if DBF_OPEN .or. !error_on
  3576.     if NTX_OPEN .or. !error_on
  3577.         if get_expr1("exp1")
  3578.             executor = "DBF_NTX"
  3579.             DBF_NTX17 = .T.
  3580.         else
  3581.             ERRS2 = .T.
  3582.         endif
  3583.     else
  3584.         ERRS9 = .T.
  3585.     endif
  3586. else
  3587.     ERRS5 = .T.
  3588. endif
  3589.  
  3590. return
  3591.  
  3592. *
  3593. ** eoproc seek
  3594.  
  3595.  
  3596. ***
  3597. * Procedure SELECT
  3598. * Evaluates stack for the SELECT verb.
  3599. * Sets execution class macro, class execution flag(s) and command line
  3600. * substitution macros.
  3601. *
  3602.  
  3603. procedure select
  3604.  
  3605. private stack_ptr, select, expr_type
  3606.  
  3607. stack_ptr = 1
  3608. select = .F.
  3609. expr_type = ""
  3610.  
  3611. if get_expr1("exp1")
  3612.     if select(exp1) > 0
  3613.         select = .T.
  3614.     else
  3615.         expr_type = type(exp1)
  3616.  
  3617.         if expr_type = "N"
  3618.             if val(exp1) <= 250 .and. val(exp1) >= 0
  3619.                 select = .T.
  3620.             endif
  3621.         endif
  3622.     endif
  3623. endif
  3624.  
  3625. if select
  3626.     executor = "DBF_NTX"
  3627.     DBF_NTX16 = .T.
  3628. else
  3629.     ERRS2 = .T.
  3630. endif
  3631.  
  3632. return
  3633.  
  3634. *
  3635. ** eoproc select
  3636.  
  3637.  
  3638. ***
  3639. * Procedure SSET
  3640. * Evaluates the next key word in SET command.  Checks abbreviation of
  3641. * key word.  Key ok, [do_sets] procedure macro is set.  Key fail or not
  3642. * found, set unknown command error flag ERRS1.
  3643. *
  3644.  
  3645. procedure sset
  3646.  
  3647. private stack_ptr, seek_strng, position, do_sets, error
  3648.  
  3649. stack_ptr = 2
  3650. do_sets = ""
  3651. error = 0
  3652.  
  3653. seek_strng = upper(stack[stack_ptr])
  3654. position = at("." + seek_strng, set_list)
  3655.  
  3656. if position > 0
  3657.     if cmd_abbr(seek_strng, trim(substr(set_list, (position + 1), 10)))
  3658.         do_sets = substr(set_proc, position, 10)
  3659.     else
  3660.         error = 1
  3661.     endif
  3662. else
  3663.     error = 1
  3664. endif
  3665.  
  3666. if error = 1
  3667.     ERRS1 = .T.
  3668. else
  3669.     do &do_sets
  3670. endif
  3671.  
  3672. return
  3673.  
  3674. *
  3675. ** eoproc set
  3676.  
  3677.  
  3678. ***
  3679. * Procedure sets
  3680. * executes the SETS class of commands
  3681. *
  3682.  
  3683. procedure sets
  3684.  
  3685. do case
  3686.     case SETS1
  3687.         set color to &exp1
  3688.         color_stat = exp1
  3689.         SETS1 = .F.
  3690.  
  3691.     case SETS2
  3692.         set confirm &exp1
  3693.         confr_stat = exp1
  3694.         SETS2 = .F.
  3695.  
  3696.     case SETS3
  3697.         set decimal to &exp1
  3698.         SETS3 = .F.
  3699.  
  3700.     case SETS4
  3701.         set default to &exp1
  3702.         SETS4 = .F.
  3703.  
  3704.     case SETS5
  3705.         set delimiters &exp1
  3706.         delim_stat = exp1
  3707.         SETS5 = .F.
  3708.  
  3709.     case SETS6
  3710.         set delimiters to &exp1
  3711.         SETS6 = .F.
  3712.  
  3713.     case SETS7
  3714.         set escape &exp1
  3715.         SETS7 = .F.
  3716.  
  3717.     case SETS8
  3718.         set fixed &exp1
  3719.         SETS8 = .F.
  3720.  
  3721.     case SETS9
  3722.         set function &exp1 to &exp2
  3723.         SETS9 = .F.
  3724.  
  3725.     case SETS10
  3726.         set index to &list0, &list1, &list2, &list3, &list4, &list5,;
  3727.             &list6, &list7, &list8, &list9
  3728.         SETS10 = .F.
  3729.  
  3730.         if empty(list0)
  3731.             NTX_OPEN = .F.
  3732.         else
  3733.             NTX_OPEN = .T.
  3734.         endif
  3735.  
  3736.     case SETS11
  3737.         set intensity &exp1
  3738.         inten_stat = exp1
  3739.         SETS11 = .F.
  3740.  
  3741.     case SETS12
  3742.         set path to &exp1
  3743.         SETS12 = .F.
  3744.  
  3745.     case SETS13
  3746.         set unique &exp1
  3747.         SETS13 = .F.
  3748.  
  3749.     case SETS14
  3750. * CAUTION:  5.0 A31
  3751. *        set key &exp1 to &exp2
  3752.         SETS14 = .F.
  3753.  
  3754.     case SETS15
  3755.         set relation to
  3756.         SETS15 = .F.
  3757.  
  3758.     case SETS16
  3759.         relation = exp1
  3760.         alias = exp2
  3761.         set relation to &relation into &alias
  3762.         SETS16 = .F.
  3763.  
  3764.     case SETS17
  3765.         filter = exp1
  3766.         set filter to &filter
  3767.         SETS17 = .F.
  3768.  
  3769.     case SETS18
  3770.         filter = ""
  3771.         set filter to
  3772.         SETS18 = .F.
  3773.  
  3774.     case SETS19
  3775.         set exclusive &exp1
  3776.         SETS19 = .F.
  3777.  
  3778.     case SETS20
  3779.         set exact &exp1
  3780.         exact_stat = exp1
  3781.         SETS20 = .F.
  3782.  
  3783.     case SETS21
  3784.         set order to &exp1
  3785.         SETS21 = .F.
  3786.  
  3787.     case SETS22
  3788.         set order to
  3789.         SETS22 = .F.
  3790. endcase
  3791.  
  3792. return
  3793.  
  3794. *
  3795. ** eoproc sets
  3796.  
  3797.  
  3798. ***
  3799. * Procedure set_lex
  3800. * Locates the verb in verb_list string and initializes "lex_proc" macro with 
  3801. * the corresponding procedure name found in the lex_list string.
  3802. * Calls CMD_ABBR().
  3803. *
  3804.  
  3805. procedure set_lex
  3806.  
  3807. private seek_strng, verb_string, position
  3808.  
  3809. if assign_chk()
  3810.     lex_proc = "ASSIGN"
  3811. else
  3812.     seek_strng = upper(stack[1])
  3813.     position = at("." + seek_strng, verb_list)
  3814.     if position > 0
  3815.         verb_string = trim(substr(verb_list, position + 1, 9))
  3816.         if cmd_abbr(seek_strng, verb_string)
  3817.             lex_proc = substr(lex_list, position, 10)
  3818.         else
  3819.             lex_proc = "UNKNOWN"
  3820.         endif
  3821.     else
  3822.         lex_proc = "UNKNOWN"
  3823.     endif
  3824. endif
  3825.  
  3826. return
  3827.  
  3828. *
  3829. ** eoproc set_lex
  3830.  
  3831.  
  3832. ***
  3833. * Procedure set_sets
  3834. * Called from interactive prompt.  Resets the SET commands to their
  3835. * DEFAULT settings.
  3836. *
  3837.  
  3838. procedure set_sets
  3839.  
  3840. set alternate OFF
  3841. set alternate to
  3842. set bell OFF
  3843. set color to
  3844. set confirm OFF
  3845. set console ON
  3846. set decimal to 2
  3847. set default to
  3848. set deleted OFF
  3849. set delimiters OFF
  3850. set delimiters to
  3851. set device to SCREEN
  3852. set escape ON
  3853. set exact OFF
  3854. set exclusive ON
  3855. set filter to
  3856. set fixed OFF
  3857. set format to
  3858.  
  3859. for i = 2 to 40
  3860.     set function i to ""
  3861. next
  3862.  
  3863. set index to
  3864. set intensity ON
  3865.  
  3866. for i = -39 to 387
  3867. *    set key i to ""
  3868. * CAUTION:  5.0 A31  (this was illegal anyway)
  3869.     set key i to
  3870. next
  3871.  
  3872. set order to 1
  3873. set print OFF
  3874. set path to
  3875. set relation to
  3876. set scoreboard ON
  3877. set unique OFF
  3878.  
  3879. inten_stat = "ON"
  3880. color_stat = "7/0"
  3881. delim_stat = "OFF"
  3882. confr_stat = "OFF"
  3883. exact_stat = "OFF"
  3884.  
  3885. return
  3886.  
  3887. *
  3888. ** eoproc set_sets
  3889.  
  3890.  
  3891. ***
  3892. * Procedure SKIP
  3893. * Evaluates stack for SKIP verb.
  3894. * Sets execution class macro, class execution flag(s) and command line
  3895. * substitution macros.
  3896. *
  3897.  
  3898. procedure skip
  3899.  
  3900. private stack_ptr
  3901.  
  3902. stack_ptr = 1
  3903.         
  3904. if DBF_OPEN .or. !error_on
  3905.     if get_expr1("exp1")
  3906.         if is_n_expr(&exp1)
  3907.             if if(error_on, &exp1 <= lastrec(), .T.)
  3908.                 executor = "DBF_NTX"
  3909.                 DBF_NTX11 = .T.
  3910.             else
  3911.                 ERRS6 = .T.
  3912.             endif
  3913.         else
  3914.             ERRS3 = .T.
  3915.         endif
  3916.     else
  3917.         executor = "DBF_NTX"
  3918.         DBF_NTX10 = .T.
  3919.     endif
  3920. else
  3921.     ERRS5 = .T.
  3922. endif
  3923.  
  3924. return
  3925.  
  3926. *
  3927. ** eoproc skip
  3928.  
  3929.  
  3930. ***
  3931. * Procedure stuff_up
  3932. * Clears the get list when an up-arrow is depressed.
  3933. * Called from HISTORY procedure. 
  3934. *
  3935.  
  3936. procedure stuff_up
  3937.  
  3938. parameters call_proc, call_line, call_var
  3939.  
  3940. if call_proc <> "STUFF_UP"
  3941.     clear gets
  3942. endif
  3943.  
  3944. return
  3945.  
  3946. *
  3947. ** eoproc stuff_up
  3948.  
  3949.  
  3950. ***
  3951. * Procedure stuff_dn
  3952. * Clears the get list when a down-arrow is depressed.
  3953. * Called from HISTORY procedure.
  3954.  
  3955. procedure stuff_dn
  3956.  
  3957. parameters call_proc, call_line, call_var
  3958.  
  3959. if call_proc <> "STUFF_DN"
  3960.     clear gets
  3961. endif
  3962.  
  3963. return
  3964.  
  3965. *
  3966. ** eoproc stuff_dn
  3967.  
  3968.  
  3969. ***
  3970. * Procedure scrn
  3971. * executes the SCRN class commands
  3972. *
  3973.  
  3974. procedure scrn
  3975.  
  3976. do case
  3977.     case SCRN1
  3978.         @ &coord1, &coord2    
  3979.         SCRN1 = .F.
  3980.  
  3981.     case SCRN2
  3982.         @ &coord1, &coord2 clear
  3983.         SCRN2 = .F.
  3984.  
  3985.     case SCRN3
  3986.         @ &coord1, &coord2 say &say_exp
  3987.         SCRN3 = .F.
  3988.  
  3989.     case SCRN4
  3990.         @ &coord1, &coord2 say &say_exp picture &say_pict
  3991.         SCRN4 = .F.
  3992.  
  3993.     case SCRN5
  3994.         @ &coord1, &coord2 get &get_exp
  3995.         SCRN5 = .F.
  3996.  
  3997.     case SCRN6
  3998.         @ &coord1, &coord2 get &get_exp picture &get_pict
  3999.         SCRN6 = .F.
  4000.  
  4001.     case SCRN7
  4002.         range1 = rng_exp1
  4003.         range2 = rng_exp2
  4004.         @ &coord1, &coord2 get &get_exp range &range1, &range2
  4005.         SCRN7 = .F.
  4006.  
  4007.     case SCRN8
  4008.         @ &coord1, &coord2 get &get_exp valid &valid_exp
  4009.         SCRN8 = .F.
  4010.  
  4011.     case SCRN10
  4012.         @ &coord1, &coord2 get &get_exp picture &get_pict valid &valid_exp
  4013.         SCRN10 = .F.
  4014.  
  4015.     case SCRN11
  4016.         range1 = rng_exp1
  4017.         range2 = rng_exp2
  4018.         @ &coord1, &coord2 get &get_exp picture &get_pict range &range1,;
  4019.             &range2
  4020.         SCRN11 = .F.
  4021.  
  4022.     case SCRN13
  4023.         @ &coord1, &coord2 say &say_exp get &get_exp
  4024.         SCRN13 = .F.
  4025.  
  4026.     case SCRN14
  4027.         @ &coord1, &coord2 say &say_exp picture &say_pict get &get_exp
  4028.         SCRN14 = .F.
  4029.  
  4030.     case SCRN15
  4031.         @ &coord1, &coord2 say &say_exp picture &say_pict get &get_exp;
  4032.             picture &get_pict
  4033.         SCRN15 = .F.
  4034.  
  4035.     case SCRN16
  4036.         range1 = rng_exp1
  4037.         range2 = rng_exp2
  4038.         @ &coord1, &coord2 say &say_exp picture &say_pict get &get_exp;
  4039.             picture &get_pict range &range1, &range2
  4040.         SCRN16 = .F.
  4041.  
  4042.     case SCRN17
  4043.         @ &coord1, &coord2 say &say_exp picture &say_pict get &get_exp;
  4044.             picture &get_pict valid &valid_exp
  4045.         SCRN17 = .F.
  4046.  
  4047.     case SCRN19
  4048.         @ &coord1, &coord2 say &say_exp get &get_exp picture &get_pict
  4049.         SCRN19 = .F.
  4050.  
  4051.     case SCRN20
  4052.         range1 = rng_exp1
  4053.         range2 = rng_exp2
  4054.         @ &coord1, &coord2 say &say_exp get &get_exp picture &get_pict;
  4055.             range &range1, &range2
  4056.         SCRN20 = .F.
  4057.  
  4058.     case SCRN21
  4059.         @ &coord1, &coord2 say &say_exp get &get_exp picture &get_pict;
  4060.             valid &valid_exp
  4061.         SCRN21 = .F.
  4062.  
  4063.     case SCRN22
  4064.         @ &coord1, &coord2, &coord3, &coord4 box &box_exp
  4065.         SCRN22 = .F.
  4066.  
  4067.     case SCRN23
  4068.         clear
  4069.         SCRN23 = .F.
  4070.  
  4071.     case SCRN24
  4072.         ?
  4073.         SCRN24 = .F.
  4074.  
  4075.     case SCRN25
  4076.         ? &exp1
  4077.         SCRN25 = .F.
  4078.  
  4079.     case SCRN26
  4080.         ??
  4081.         SCRN26 = .F.
  4082.  
  4083.     case SCRN27
  4084.         ?? &exp1
  4085.         SCRN27 = .F.
  4086.  
  4087.     case SCRN28
  4088.         cur_row = row()
  4089.         read
  4090.         @ cur_row+1, 1
  4091.         SCRN28 = .F.
  4092. endcase
  4093.  
  4094. return
  4095.  
  4096. *
  4097. ** eoproc scrn
  4098.  
  4099.  
  4100. ***
  4101. * Procedure TYPE
  4102. * Evaluates stack for TYPE verb.
  4103. * Sets execution class macro, class execution flag(s) and command line
  4104. * substitution macros.
  4105. *
  4106.  
  4107. procedure type
  4108.  
  4109. private stack_ptr
  4110.  
  4111. stack_ptr = 1
  4112.  
  4113. if get_expr1("exp1")
  4114.     executor = "DBF_NTX"
  4115.     DBF_NTX23 = .T.
  4116. else
  4117.     ERRS2 = .T.
  4118. endif
  4119.  
  4120. return
  4121.  
  4122. *
  4123. ** eoproc type
  4124.  
  4125.  
  4126. ***
  4127. * Procedure unknown
  4128. * If command cannot be found this routine is called to set unknown
  4129. * error flag.
  4130. *
  4131.  
  4132. procedure unknown
  4133.  
  4134. ERRS1 = .T.
  4135.  
  4136. return
  4137.  
  4138. *
  4139. ** eoproc unknown
  4140.  
  4141.  
  4142. ***
  4143. * Procedure UNLOCK
  4144. * Evaluates stack for UNLOCK verb.
  4145. * Sets execution class macro, class execution flag(s) and command line
  4146. * substitution macros.
  4147. *
  4148.  
  4149. procedure unlock
  4150.  
  4151. private stack_ptr
  4152.  
  4153. stack_ptr = 1
  4154.  
  4155. if max_ptr = 1
  4156.     executor = "DBF_NTX"
  4157.     DBF_NTX24 = .T.
  4158. else
  4159.     if max_ptr = 2 .and. upper(stack[2]) = "ALL"
  4160.         executor = "DBF_NTX"
  4161.         DBF_NTX25 = .T.
  4162.     else
  4163.         ERRS1 = .T.
  4164.     endif
  4165. endif
  4166.  
  4167. return
  4168.  
  4169. *
  4170. ** eoproc unlock
  4171.                       
  4172.  
  4173. ***
  4174. * Procedure USE
  4175. * Evaluates stack for USE verb.
  4176. * Sets execution class macro, class execution flag(s) and command line
  4177. * substitution macros.
  4178. *
  4179.  
  4180. procedure use 
  4181.  
  4182. private stack_ptr, file, dbf, index, ntx, alias, name, excl,;
  4183.   stack_item
  4184.  
  4185. stack_ptr = 1
  4186. store .F. to file, dbf, index, ntx, alias, name, excl
  4187.  
  4188. do while stack_ptr <= max_ptr .and. !err()
  4189.  
  4190.     stack_item = upper(stack[stack_ptr])
  4191.  
  4192.     do case 
  4193.         case "USE" = stack_item
  4194.             if get_expr1("dbf_file")
  4195.                 file = .T.
  4196.                 dbf = if(error_on, file("&dbf_file..DBF"), .T.)
  4197.             endif
  4198.  
  4199.         case cmd_abbr(stack_item, "INDEX")
  4200.             index = .T.
  4201.             ntx = get_list("NF")
  4202.  
  4203.         case cmd_abbr(stack_item, "ALIAS")
  4204.             alias = .T.
  4205.             name = get_expr1("exp2")
  4206.  
  4207.         case cmd_abbr(stack_item, "EXCLUSIVE")
  4208.             excl = .T.
  4209.             stack_ptr = stack_ptr + 1
  4210.  
  4211.         otherwise
  4212.             ERRS2 = .T.
  4213.     endcase
  4214. enddo
  4215.  
  4216. if !err()
  4217.     do case
  4218.         case !file .and. !dbf .and. !index .and. !ntx .and. !alias;
  4219.             .and. !excl
  4220.             *** Close the current selected data file. ***
  4221.             executor = "DBF_NTX"
  4222.             DBF_NTX1 = .T.
  4223.  
  4224.         case file .and. dbf .and. !index .and. !ntx .and. !alias;
  4225.             .and. !excl
  4226.             executor = "DBF_NTX"
  4227.             DBF_NTX2 = .T.
  4228.  
  4229.         case file .and. dbf .and. index .and. ntx .and. !alias;
  4230.             .and. !excl
  4231.             executor = "DBF_NTX"
  4232.             DBF_NTX3 = .T.
  4233.  
  4234.         case file .and. dbf .and. alias .and. name .and. !index;
  4235.             .and. !ntx .and. !excl
  4236.             executor = "DBF_NTX"
  4237.             DBF_NTX4 = .T.
  4238.  
  4239.         case file .and. dbf .and. index .and. ntx .and. alias;
  4240.             .and. name .and. !excl
  4241.             executor = "DBF_NTX"
  4242.             DBF_NTX5 = .T.
  4243.  
  4244.         case file .and. dbf .and. !index .and. !ntx .and. !alias;
  4245.             .and. excl
  4246.             executor = "DBF_NTX"
  4247.             DBF_NTX32 = .T.
  4248.  
  4249.         case file .and. dbf .and. index .and. ntx .and. !alias;
  4250.             .and. excl
  4251.             executor = "DBF_NTX"
  4252.             DBF_NTX33 = .T.
  4253.  
  4254.         case file .and. dbf .and. alias .and. name .and. !index;
  4255.             .and. !ntx .and. excl
  4256.             executor = "DBF_NTX"
  4257.             DBF_NTX34 = .T.
  4258.  
  4259.         case file .and. dbf .and. index .and. ntx .and. alias;
  4260.             .and. name .and. excl
  4261.             executor = "DBF_NTX"
  4262.             DBF_NTX35 = .T.
  4263.  
  4264.         case file .and. !dbf .and. !index .and. !ntx .and. error_on
  4265.             ERRS7 = .T.
  4266.  
  4267.         case file .and. dbf .and. index .and. !ntx .and. error_on
  4268.             ERRS11 = .T.
  4269.  
  4270.         otherwise
  4271.             ERRS2 = .T.
  4272.     endcase
  4273. endif
  4274. return
  4275.  
  4276. *
  4277. ** eoproc use 
  4278.  
  4279.  
  4280. ***
  4281. * Procedure vars
  4282. * executes the VARS class of commands
  4283. *
  4284.  
  4285. procedure vars
  4286.  
  4287. do case
  4288.     case VARS1
  4289.         accept to &var1
  4290.         VARS1 = .F.
  4291.  
  4292.     case VARS2
  4293.         accept &exp1 to &var1
  4294.         VARS2 = .F.
  4295.  
  4296.     case VARS3
  4297.         input to &var1
  4298.         VARS3 = .F.
  4299.  
  4300.     case VARS4
  4301.         input &exp1 to &var1
  4302.         VARS4 = .F.
  4303.  
  4304.     case VARS5
  4305.         wait
  4306.         VARS5 = .F.
  4307.  
  4308.     case VARS6
  4309.         wait to &var1
  4310.         VARS6 = .F.
  4311.  
  4312.     case VARS7
  4313.         wait &exp1 to &var1
  4314.         VARS7 = .F.
  4315.  
  4316.     case VARS8
  4317.         wait &exp1
  4318.         VARS8 = .F.
  4319. endcase
  4320.  
  4321. return
  4322.  
  4323. *
  4324. ** eoproc var
  4325.  
  4326.  
  4327. ***
  4328. * Procedure what_key
  4329. * displays ascii decimal value of a key
  4330. *
  4331.  
  4332. procedure what_key
  4333.  
  4334. private key, trash
  4335.  
  4336. save screen
  4337.  
  4338. clear
  4339. key = 0
  4340.  
  4341. do while key <> 272
  4342.     trash = inkey()
  4343.     key = lastkey()
  4344.     @ 10,10 say str(key,4) + " <ALT-Q> returns (272)."
  4345.     for col = 40 to 60 step 1
  4346.         @ 10, col say ""
  4347.     next
  4348.     for col = 40 to 60 step 2
  4349.         @ 10, col say ""
  4350.     next
  4351. enddo
  4352.  
  4353. restore screen
  4354.  
  4355. return
  4356.  
  4357. *
  4358. ** eoproc what_key
  4359.  
  4360.  
  4361. ***
  4362. * Procedure wWAIT
  4363. * Evaluates stack for WAIT verb.
  4364. * Sets execution class macro, class execution flag(s) and command line
  4365. * substitution macros.
  4366. *
  4367.  
  4368. procedure wwait
  4369.  
  4370. private stack_ptr, string, to, dest, stack_item
  4371.  
  4372. stack_ptr = 1
  4373. store .F. to string, to, dest
  4374.  
  4375. do while stack_ptr <= max_ptr
  4376.     stack_item = upper(stack[stack_ptr])
  4377.     do case
  4378.         case stack_item = "WAIT"
  4379.             string = get_expr1("exp1")
  4380.             if upper(exp1) = "TO"
  4381.                 string = .F.
  4382.                 exp1 = ""
  4383.                 stack_ptr = stack_ptr - 1
  4384.             endif
  4385.  
  4386.         case stack_item = "TO"
  4387.             to = .T.
  4388.             dest = get_expr1("var1")
  4389.  
  4390.         otherwise
  4391.             stack_ptr = stack_ptr + 1
  4392.     endcase
  4393. enddo
  4394.  
  4395. if !err()
  4396.     do case
  4397.         case !to .and. !dest .and. !string
  4398.             executor = "VARS"
  4399.             VARS5 = .T.
  4400.  
  4401.         case to .and. dest .and. !string
  4402.             executor = "VARS"
  4403.             VARS6 = .T.
  4404.             VARS9 = .T.
  4405.  
  4406.         case to .and. dest .and. string
  4407.             executor = "VARS"
  4408.             VARS7 = .T.
  4409.             VARS9 = .T.
  4410.  
  4411.         case !to .and. !dest .and. string
  4412.             executor = "VARS"
  4413.             VARS8 = .T.
  4414.  
  4415.         otherwise
  4416.             ERRS2 = .T.
  4417.     endcase
  4418. endif
  4419.  
  4420. return
  4421.  
  4422. *
  4423. ** eoproc wwait
  4424.  
  4425.  
  4426. ***
  4427. * Procedure ZAP
  4428. * Evaluates stack for ZAP verb. 
  4429. * Sets execution class macro, class execution flag.
  4430. *
  4431.  
  4432. procedure zap
  4433.  
  4434. if error_on .and. !DBF_OPEN
  4435.   ERRS5 = .T.
  4436. else
  4437.   if stack_ptr = 1
  4438.      executor = "DBF_NTX"
  4439.      DBF_NTX36 = .T.
  4440.   else
  4441.      ERRS2 = .T.
  4442.   endif
  4443. endif
  4444.  
  4445. return
  4446.  
  4447. *
  4448. ** eoproc ZAP
  4449.  
  4450.  
  4451. *********************************
  4452. * End of procedures for dot.prg *
  4453. *********************************
  4454.  
  4455. *********************
  4456. * Functions for Dot *
  4457. *********************
  4458.  
  4459.  
  4460. ***
  4461. * Function assign_chk
  4462. * Check command for assignment operator.
  4463. *
  4464. *    Usage :    assign_chk()
  4465. *
  4466. *     Returns:
  4467. *        .T. - assignment operator found after first identifier.
  4468. *        .F. - no operator found.
  4469. *
  4470. * Called from SET_LEX procedure.
  4471. *
  4472.  
  4473. function assign_chk
  4474.  
  4475. private stack_item, status
  4476.  
  4477. stack_item = ""
  4478. status = .F.
  4479.  
  4480. if max_ptr >= 2
  4481.   stack_item = stack[2]
  4482. endif
  4483.  
  4484. if substr(stack[1],1,1)$"_ABCDEFGHIJKLMNOPQRSTUVWXYZabcdefghijklmnopqrstuvwxyz"
  4485.   if stack_item == "="
  4486.         status = .T.
  4487.   else
  4488.      if substr(stack_item,1,1) == "["   && if no close brace error in parser.
  4489.         if max_ptr >= 3
  4490.            if stack[3] == "="
  4491.               status = .T.
  4492.            endif
  4493.         endif 
  4494.      endif
  4495.   endif
  4496. endif
  4497.  
  4498. return (status)
  4499.  
  4500. *
  4501. ** eofunc assign_chk
  4502.  
  4503.  
  4504. ***
  4505. * Function cmd_abbr
  4506. * Checks verb for correct abbreviation.
  4507. *
  4508. *    Usage   : cmd_abbr(<string1>, <string2>)
  4509. *
  4510. *        <string1> - upper of verb to check.
  4511. *        <string2> - upper full spelling of verb.
  4512. *
  4513. *     Returns :
  4514. *        .T. - s1 ok.
  4515. *        .F. - s1 NOT ok.
  4516. *
  4517. *    Notes      :
  4518. *        1. DIR is an exception to the four char abbreviation definition.        
  4519. *
  4520.  
  4521. function cmd_abbr
  4522.  
  4523. parameters s1, s2
  4524.  
  4525. private status, s1_len, abbr_len
  4526.  
  4527. status = .F.
  4528. s1_len = len(s1)
  4529. abbr_len = len(s2)
  4530.  
  4531. if abbr_len > 4
  4532.     abbr_len = 4
  4533. endif
  4534.  
  4535. s1 = "." + s1
  4536. s2 = "." + s2
  4537.  
  4538. if s1$s2 .and. s1_len >= abbr_len .or. s1 == ".DIR"
  4539.     status = .T.
  4540. endif
  4541.  
  4542. return (status)
  4543.  
  4544. *
  4545. ** eofunc cmd_abbr
  4546.  
  4547.  
  4548. ***
  4549. * Function cnd_scp
  4550. * Evaluates the stack for condition and scope.  Called from procedures that
  4551. * need to analyze conditions and/or scope key words.
  4552. *
  4553. *    Usage :    cnd_scp()
  4554. *
  4555. *     Returns:
  4556. *        .T. - if no error occurred in analysis.
  4557. *        .F. - error occurred.
  4558. *
  4559. *    Control variables effected:
  4560. *        Strings   -   condition
  4561. *                      scope
  4562. *
  4563. *        Logicals  -   for
  4564. *                      while
  4565. *                      record
  4566. *                      all
  4567. *                      next
  4568. *                      rewind_dbf
  4569. *                      to
  4570. *                      source
  4571. *
  4572. *        Numerics  -   scope
  4573. *
  4574.  
  4575. function cnd_scp
  4576.  
  4577. rewind_dbf = .F.
  4578.  
  4579. do while stack_ptr <= max_ptr .and. !err()
  4580.  
  4581.     stack_item = upper(stack[stack_ptr])
  4582.  
  4583.     do case
  4584.         case stack_item = "FOR"
  4585.             condition = get_expr1("exp1")
  4586.             if condition
  4587.                 for = .T.
  4588.                 rewind_dbf = .T.
  4589.             else
  4590.                 ERRS2 = .T.
  4591.             endif
  4592.  
  4593.         case cmd_abbr(stack_item, "WHILE")
  4594.             condition = get_expr1("exp2")
  4595.             if condition
  4596.                 while = .T.
  4597.                 rewind_dbf = .F.
  4598.             else
  4599.                 ERRS2 = .T.
  4600.             endif
  4601.  
  4602.         case cmd_abbr(stack_item, "RECORD")
  4603.             if get_expr1("exp3") .and. is_num(&exp3)
  4604.                 if &exp3 <= lastrec()
  4605.                     record = .T.
  4606.                     scope = 1
  4607.                     rewind_dbf = .F.
  4608.                     exp3 = "recno() = &exp3"
  4609.                 else
  4610.                     ERRS6 = .T.
  4611.                 endif
  4612.             else
  4613.                 ERRS2 = .T.
  4614.             endif
  4615.  
  4616.         case stack_item = "ALL"
  4617.             all = .T.
  4618.             scope = 2
  4619.             rewind_dbf = .T.
  4620.             stack_ptr = stack_ptr + 1
  4621.  
  4622.         case stack_item = "NEXT"
  4623.             if get_expr1("exp3") .and. is_num(&exp3)
  4624.                 next = .T.
  4625.                 scope = 3
  4626.                 rewind_dbf = .F.
  4627.             else    
  4628.                 ERRS2 = .T.
  4629.             endif
  4630.  
  4631.         case stack_item = "TO"
  4632.             if get_expr1("dest")
  4633.                 to = .T.
  4634.             else
  4635.                 ERRS2 = .T.
  4636.             endif
  4637.  
  4638.         case stack_item = "FROM"
  4639.             if get_expr1("source")
  4640.                 source = .T.
  4641.             else
  4642.                 ERRS2 = .T.
  4643.             endif
  4644.  
  4645.         otherwise
  4646.             stack_ptr = stack_ptr + 1
  4647.     endcase
  4648. enddo
  4649.  
  4650. return (!err())
  4651.  
  4652. *
  4653. ** eoproc cnd_scp
  4654.  
  4655.  
  4656. ***
  4657. * Function err
  4658. * Check for error status flags set.
  4659. *
  4660. *    Usage : err()
  4661. *
  4662. *    Returns:
  4663. *        .T. - if any of the error flags are set.
  4664. *
  4665.  
  4666. function err
  4667.  
  4668. private status
  4669.  
  4670. status = .F.
  4671.  
  4672. if error_on
  4673.     if ERRS1 .or. ERRS2 .or. ERRS3 .or. ERRS4 .or. ERRS5 .or. ERRS6 .or. ERRS7;
  4674.         .or. ERRS8 .or. ERRS9 .or. ERRS10 .or. ERRS11 .or. ERRS12 .or. ERRS13;
  4675.         .or. ERRS14 .or. ERRS15
  4676.         status = .T.
  4677.     endif
  4678. endif
  4679.  
  4680. return (status)
  4681.  
  4682. *
  4683. ** eofunc err
  4684.  
  4685.  
  4686. ***
  4687. * Function fld_form
  4688. * Provides the correct column formatting for any given field type.
  4689. * Called by the list_do procedure.
  4690. *
  4691. *    Usage     : fld_form(<character expression>)
  4692. *
  4693. *        <character expression> - name of field to provide formatting
  4694. *                                 for.
  4695. *
  4696. *     Returns :
  4697. *        Output format string for fieldname.
  4698. *
  4699.  
  4700. function fld_form
  4701.  
  4702. parameters fld_name
  4703.  
  4704. private type, fld_form
  4705.  
  4706. type = type("&fld_name")
  4707.  
  4708. do case
  4709.     case type = "C"
  4710.         fld_form = fld_name
  4711.  
  4712.     case type = "D"
  4713.         fld_form = "dtoc(&fld_name)"
  4714.  
  4715.     case type = "L"
  4716.         fld_form = [if((&fld_name), ".T.", ".F.")]
  4717.  
  4718.     case type = "M"
  4719.         fld_form = ["Memo      "]
  4720.  
  4721.     case type = "N"
  4722.         fld_form = "str(&fld_name)"
  4723. endcase
  4724.  
  4725. return (fld_form)
  4726.  
  4727. *
  4728. ** eofunc fld_form
  4729.  
  4730.  
  4731. ***
  4732. * Function get_expr1()
  4733. * Fills the passed variable.
  4734. *
  4735. *    Usage   : get_expr1(<var_name>)
  4736. *
  4737. *        <var_name> -  contains name of target variable.
  4738. *
  4739. *    Returns :
  4740. *        .T. - variable is NOT empty.
  4741. *        .F. - variable is empty.
  4742. *
  4743. *    Notes   :
  4744. *
  4745. *            1. Increments stack pointer before getting stack item.
  4746. *            2. Leaves the stack pointer at the next item on stack.  
  4747. *            
  4748.  
  4749. function get_expr1
  4750.  
  4751. parameters var_name
  4752.  
  4753. private current, next, get_more
  4754.  
  4755. current = ""
  4756. next = ""
  4757. get_more = .F.
  4758. stack_ptr = stack_ptr + 1
  4759.  
  4760. if stack_ptr <= max_ptr
  4761.     &var_name = &var_name + stack[stack_ptr]
  4762.     stack_ptr = stack_ptr + 1
  4763.  
  4764.     if current <> ","
  4765.         if stack_ptr <= max_ptr
  4766.             next = stack[stack_ptr]
  4767.  
  4768.             if &var_name$"+-!.\" .or. substr(next,1,1)$"|+-/%*<>=#.!$^(["
  4769.                 get_more = .T.
  4770.             endif
  4771.  
  4772.         endif
  4773.     endif
  4774. endif
  4775.  
  4776. do while get_more
  4777.  
  4778.     get_more = .F.
  4779.     current = stack[stack_ptr]
  4780.     &var_name = &var_name + current
  4781.     stack_ptr = stack_ptr + 1
  4782.  
  4783.     if stack_ptr <= max_ptr
  4784.         next = stack[stack_ptr]
  4785.         if current$"|+-/%*<>=#.!$^==" .and. next <> "," .or.;
  4786.             substr(next,1,1)$"|+-/%*<>=#.!$^([" .and. current <> ","
  4787.              get_more = .T.
  4788.         endif
  4789.     endif
  4790.  
  4791. enddo
  4792.  
  4793. return ("" <> &var_name)
  4794.  
  4795. *
  4796. ** eofunc get_expr1
  4797.  
  4798.  
  4799. ***
  4800. * Function get_list
  4801. * Gets a list of expression from the stack.  List variables start at 1.
  4802. *
  4803. *    Usage  :  get_list(<control string>)
  4804. *
  4805. *        <control string> - indicates that the list contains....
  4806. *
  4807. *                    "E"     - expressions.
  4808. *                    "NF" - index files.
  4809. *
  4810. *    Returns :
  4811. *        .T. - list filled successfully, or if "NF" and empty.
  4812. *        .F. - list is empty or error occurred.
  4813. *
  4814. *    Notes   :
  4815. *
  4816. *        1. If string = "NF" and error_on = .F. no index file
  4817. *           checking is done.
  4818. *        2. Increments stack pointer before getting something from the
  4819. *           stack.
  4820. *        3. Leaves stack pointer at next item on stack.
  4821. *
  4822.  
  4823. function get_list
  4824.  
  4825. parameters list_type
  4826.  
  4827. private get_more, count, list_ok, stack_item, null
  4828.  
  4829. if stack_ptr <= max_ptr
  4830.     list_ok = .T.
  4831.     get_more = .T.
  4832.     count = "0"
  4833.     stack_item = ""
  4834. else
  4835.     get_more = .F.
  4836.     if list_type = "NF"
  4837.         list_ok = .T.
  4838.     else
  4839.         list_ok = .F.
  4840.     endif
  4841. endif
  4842.  
  4843. do while get_more
  4844.     get_more = .F.
  4845.     stack_item = ""
  4846.  
  4847.     null = get_expr1("stack_item")
  4848.  
  4849.     if stack_item <> ","
  4850.         if list_type = "NF"
  4851.             list_ok = if(error_on, file("&stack_item..NTX"), .T.)
  4852.         endif
  4853.         if list_ok
  4854.             store stack_item to list&count
  4855.             count = str(val(count)+1,1)
  4856.         endif
  4857.     endif
  4858.  
  4859.     if stack_ptr <= max_ptr .and. val(count) < 10 .and. list_ok
  4860.         if stack[stack_ptr] = ","
  4861.             get_more = .T.
  4862.         endif
  4863.     endif
  4864. enddo
  4865.  
  4866. return (list_ok)
  4867.  
  4868. *
  4869. ** eofunc get_list
  4870.  
  4871.  
  4872. ***
  4873. * Function get_stack
  4874. * Fills the variable passed in var_name.
  4875. *
  4876. *     Usage    : get_stack(<var_name>)
  4877. *
  4878. *        <var_name> - literal name of variable to store expression to.
  4879. *
  4880. *    Returns:
  4881. *        .T. - if NOT null
  4882. *        .F. - if null.
  4883. *
  4884. *    Notes:
  4885. *
  4886. *        1. Does NOT increment the stack pointer before getting 
  4887. *           something from the stack.
  4888. *         2. Leaves the stack pointer at the next item on the stack.  
  4889. *
  4890.  
  4891. function get_stack
  4892.  
  4893. parameters var_name
  4894.  
  4895. private current, next, get_more
  4896.  
  4897. current = ""
  4898. next = ""
  4899. get_more = .F.
  4900.  
  4901. if stack_ptr <= max_ptr
  4902.  
  4903.     &var_name = stack[stack_ptr]
  4904.     current = &var_name
  4905.     stack_ptr = stack_ptr + 1
  4906.  
  4907.     if stack_ptr <= max_ptr
  4908.         next = upper(stack[stack_ptr])
  4909.     endif
  4910.  
  4911.     if current <> ","
  4912.         if current$"+-!\*.?" .or. substr(next,1,1)$"|+-/%*<>=#!$^([?*."
  4913.             get_more = .T.
  4914.         endif
  4915.     endif
  4916. endif
  4917.  
  4918. do while get_more
  4919.  
  4920.     get_more = .F.
  4921.     current = stack[stack_ptr]
  4922.     &var_name = &var_name + current
  4923.     stack_ptr = stack_ptr + 1
  4924.  
  4925.     if stack_ptr <= max_ptr
  4926.         next = stack[stack_ptr]
  4927.         if substr(current,1,1)$"|+-/%*<>=#.!$^=?" .and. next <> "," .or.;
  4928.             substr(next,1,1)$"|+-/%*<>=#.!$^([?" .and. current <> ","
  4929.              get_more = .T.
  4930.         endif
  4931.     endif
  4932.  
  4933. enddo
  4934.  
  4935. return (!(&var_name == ""))
  4936.  
  4937. *
  4938. ** eofunc get_stack
  4939.  
  4940.  
  4941. ***
  4942. * Function is_n_expr
  4943. * Checks the contents of eval_item for numeric type.
  4944. *
  4945. *     Usage     : is_n_expr(<eval_item>)
  4946. *
  4947. *         <eval_item> - macro expanded string.
  4948. *
  4949. *    Returns : 
  4950. *        .T. - item is numeric.
  4951. *        .F. - item is NOT numeric.
  4952. *
  4953.  
  4954. function is_n_expr
  4955.  
  4956. parameters eval_item
  4957.  
  4958. return (type("eval_item")$"N")
  4959.  
  4960. *
  4961. ** eofunc is_n_expr
  4962.  
  4963.  
  4964. ***
  4965. * Function is_num
  4966. * checks if a string contains only numbers.
  4967. *
  4968. *     Usage     : is_num(<eval_item>)
  4969. *
  4970. *         <eval_item> - macro expanded string.
  4971. *
  4972. *    Returns : 
  4973. *        .T. - item is string of numbers.
  4974. *        .F. - item is NOT a string of numbers.
  4975. *
  4976. *
  4977.  
  4978. function is_num
  4979.  
  4980. parameters string
  4981.  
  4982. private status, len, counter
  4983.  
  4984. if type("string")$"NC"
  4985.     if type("string") = "N"
  4986.         string = str(string)
  4987.     endif
  4988.  
  4989.     string = ltrim(string)
  4990.     status = .T.
  4991.     len = len(string)
  4992.     counter = 1
  4993.  
  4994.     do while counter <= len .and. status
  4995.         if !substr(string,counter,1)$"0123456789"
  4996.             status = .F.
  4997.         endif
  4998.         counter = counter + 1
  4999.     enddo
  5000. else
  5001.     status = .F.
  5002. endif
  5003.  
  5004. return (status)
  5005.  
  5006. *
  5007. ** eofunc is_num
  5008.  
  5009.  
  5010. ***
  5011. * Function spacer_h
  5012. * Build a string for a list/display header.
  5013. * Called by the list_do procedure.
  5014. *
  5015. *     Usage     : spacer_h(<field name>)
  5016. *
  5017. *        <field name> - name of the field to format.
  5018. *
  5019. *    Returns :
  5020. *        Character string containing field name plus the number of
  5021. *        blanks to pad the column out.
  5022. *
  5023. *    Notes   :
  5024. *
  5025. *        1. Called from procedure list_do.
  5026. *
  5027.  
  5028. function spacer_h
  5029.  
  5030. parameter fld_name
  5031.  
  5032. private type, string
  5033.  
  5034. type = type("&fld_name")
  5035. string = ""
  5036.  
  5037. do case
  5038.     case type = "C"
  5039.         string = fld_name + space(if(len(fld_name) >= len(&fld_name), 1,;
  5040.             (len(&fld_name) - len(fld_name)) + 1))
  5041.  
  5042.     case type = "D"
  5043.         string = fld_name + space(if((len(fld_name) >= 8), 1,;
  5044.             (8 - len(fld_name)) + 1))
  5045.  
  5046.     case type = "L"
  5047.         string = fld_name + space(if((len(fld_name) >= 3), 1,;
  5048.             (3 - len(fld_name)) + 1))
  5049.  
  5050.     case type = "M"
  5051.         string = fld_name + space(if((len(fld_name) = 10), 1,;
  5052.             (10 - len(fld_name)) + 1))
  5053.  
  5054.     case type = "N"
  5055.         string = space(if((len(fld_name) >= len(str(&fld_name))), 0,;
  5056.             (len(str(&fld_name)) - len(fld_name)))) + fld_name + space(1)
  5057. endcase
  5058.  
  5059. return (string)
  5060.  
  5061. *
  5062. ** eofunc spacer_h
  5063.  
  5064.  
  5065. ***
  5066. * Function spacer_l
  5067. * Calculate the number of characters to pad a list/display line.
  5068. * Called by the list_do procedure.
  5069. *
  5070. *     Usage     : spacer_h(<field name>)
  5071. *
  5072. *        <field name> - name of the field pad.
  5073. *
  5074. *    Returns :
  5075. *        Number of spaces needed to pad out a column in a screen
  5076. *        output line.
  5077. *
  5078. *    Notes   :
  5079. *
  5080. *        1. Called from procedure list_do.
  5081. *
  5082.  
  5083. function spacer_l
  5084.  
  5085. parameters fld_name
  5086.  
  5087. private type, blanks
  5088.  
  5089. type = type("&fld_name")
  5090. blanks = 0
  5091.  
  5092. do case
  5093.     case type = "C"
  5094.         blanks = if(len(&fld_name) >= len(fld_name), 1,;
  5095.             (len(fld_name) - len(&fld_name)) + 1)
  5096.  
  5097.     case type = "D"
  5098.         blanks = if(8 >= len(fld_name), 1, (len(fld_name) - 8) + 1)
  5099.  
  5100.     case type = "L"
  5101.         blanks = if(3 >= len(fld_name), 1, (len(fld_name) - 3) + 1)
  5102.  
  5103.     case type = "M"
  5104.         blanks = if(10 >= len(fld_name), 1, (len(fld_name) - 10) + 1)
  5105.  
  5106.     case type = "N"
  5107.         blanks = if((len(str(&fld_name)) >= len(fld_name)), 1,;
  5108.             (len(fld_name) - len(str(&fld_name)) + 1))
  5109. endcase
  5110.  
  5111. return (ltrim(str(blanks,2)))
  5112.  
  5113. *
  5114. ** eofunc spacer_l
  5115.  
  5116.  
  5117.  
  5118. ***
  5119. *    5.0 error handler for Dot...
  5120. *
  5121.  
  5122. #include "error.ch"
  5123.  
  5124. #define NTRIM(n)        ( LTrim(Str(n)) )
  5125.  
  5126.  
  5127.  
  5128. ***
  5129. *    DotError()
  5130. *
  5131. static func DotError(e)
  5132.  
  5133.     local i, cMessage, aOptions, nChoice
  5134.     local bSaveErrorBlock
  5135.  
  5136.  
  5137.     // switch to system error handler (in case of error in here)
  5138.     bSaveErrorBlock := ErrorBlock(SysErrorBlock)
  5139.  
  5140.  
  5141.     // for network open error, set NETERR() and alert user
  5142.     if ( e:genCode == EG_OPEN .and. e:osCode == 32 )
  5143.         NetErr(.t.)
  5144.     end
  5145.  
  5146.     // for lock error during APPEND BLANK, set NETERR() and alert user
  5147.     if ( e:genCode == EG_APPENDLOCK .and. e:canDefault )
  5148.         NetErr(.t.)
  5149.     end
  5150.  
  5151.  
  5152.     // build error message
  5153.     cMessage := ErrorMessage(e)
  5154.  
  5155.  
  5156.     // build options array
  5157.     aOptions := {"Break", "Quit"}
  5158.  
  5159.     if (e:canRetry)
  5160.         AAdd(aOptions, "Retry")
  5161.     end
  5162.  
  5163.     if (e:canDefault)
  5164.         AAdd(aOptions, "Default")
  5165.     end
  5166.  
  5167.  
  5168.     // put up alert box
  5169.     nChoice := 0
  5170.     while ( nChoice == 0 )
  5171.  
  5172.         if ( Empty(e:osCode) )
  5173.             nChoice := Alert( cMessage, aOptions )
  5174.  
  5175.         else
  5176.             nChoice := Alert( cMessage + ;
  5177.                             ";(DOS Error " + NTRIM(e:osCode) + ")", ;
  5178.                             aOptions )
  5179.         end
  5180.  
  5181.     end
  5182.  
  5183.  
  5184.     // switch back to our error handler before leaving
  5185.     ErrorBlock(bSaveErrorBlock)
  5186.  
  5187.  
  5188.     // do as instructed
  5189.     if ( !Empty(nChoice) )
  5190.  
  5191.         if ( aOptions[nChoice] == "Break" )
  5192.             Break(e)
  5193.  
  5194.         elseif ( aOptions[nChoice] == "Retry" )
  5195.             return (.t.)
  5196.  
  5197.         elseif ( aOptions[nChoice] == "Default" )
  5198.  
  5199.             // default for division by zero is zero
  5200.             if ( e:genCode == EG_ZERODIV )
  5201.                 return (0)
  5202.  
  5203.             end
  5204.  
  5205.             return (.f.)
  5206.  
  5207.         end
  5208.  
  5209.     end
  5210.  
  5211.  
  5212.     // display message and quit
  5213.     if ( !Empty(e:osCode) )
  5214.         cMessage += " (DOS Error " + NTRIM(e:osCode) + ") "
  5215.     end
  5216.  
  5217.  
  5218.     ? cMessage
  5219.     ErrorLevel(1)
  5220.     QUIT
  5221.  
  5222. return (.f.)
  5223.  
  5224.  
  5225.  
  5226. /***
  5227. *    ErrorMessage()
  5228. */
  5229. static func ErrorMessage(e)
  5230.  
  5231.     local cMessage
  5232.  
  5233.  
  5234.     // start error message
  5235.     cMessage := if( e:severity > ES_WARNING, "Error ", "Warning " )
  5236.  
  5237.  
  5238.     // add subsystem name if available
  5239.     if ( ValType(e:subsystem) == "C" )
  5240.         cMessage += e:subsystem()
  5241.     else
  5242.         cMessage += "???"
  5243.     end
  5244.  
  5245.  
  5246.     // add subsystem's error code if available
  5247.     if ( ValType(e:subCode) == "N" )
  5248.         cMessage += ("/" + NTRIM(e:subCode))
  5249.     else
  5250.         cMessage += "/???"
  5251.     end
  5252.  
  5253.  
  5254.     // add error description if available
  5255.     if ( ValType(e:description) == "C" )
  5256.         cMessage += ("  " + e:description)
  5257.     end
  5258.  
  5259.  
  5260.     // add either filename or operation
  5261.     if ( !Empty(e:filename) )
  5262.         cMessage += (": " + e:filename)
  5263.  
  5264.     elseif ( !Empty(e:operation) )
  5265.         cMessage += (": " + e:operation)
  5266.  
  5267.     end
  5268.  
  5269.  
  5270.     return (cMessage)
  5271.  
  5272. *
  5273. *
  5274. ** eof dot.prg
  5275.  
  5276.