langdesc.html 68 KB

1234567891011121314151617181920212223242526272829303132333435363738394041424344454647484950515253545556575859606162636465666768697071727374757677787980818283848586878889909192939495969798991001011021031041051061071081091101111121131141151161171181191201211221231241251261271281291301311321331341351361371381391401411421431441451461471481491501511521531541551561571581591601611621631641651661671681691701711721731741751761771781791801811821831841851861871881891901911921931941951961971981992002012022032042052062072082092102112122132142152162172182192202212222232242252262272282292302312322332342352362372382392402412422432442452462472482492502512522532542552562572582592602612622632642652662672682692702712722732742752762772782792802812822832842852862872882892902912922932942952962972982993003013023033043053063073083093103113123133143153163173183193203213223233243253263273283293303313323333343353363373383393403413423433443453463473483493503513523533543553563573583593603613623633643653663673683693703713723733743753763773783793803813823833843853863873883893903913923933943953963973983994004014024034044054064074084094104114124134144154164174184194204214224234244254264274284294304314324334344354364374384394404414424434444454464474484494504514524534544554564574584594604614624634644654664674684694704714724734744754764774784794804814824834844854864874884894904914924934944954964974984995005015025035045055065075085095105115125135145155165175185195205215225235245255265275285295305315325335345355365375385395405415425435445455465475485495505515525535545555565575585595605615625635645655665675685695705715725735745755765775785795805815825835845855865875885895905915925935945955965975985996006016026036046056066076086096106116126136146156166176186196206216226236246256266276286296306316326336346356366376386396406416426436446456466476486496506516526536546556566576586596606616626636646656666676686696706716726736746756766776786796806816826836846856866876886896906916926936946956966976986997007017027037047057067077087097107117127137147157167177187197207217227237247257267277287297307317327337347357367377387397407417427437447457467477487497507517527537547557567577587597607617627637647657667677687697707717727737747757767777787797807817827837847857867877887897907917927937947957967977987998008018028038048058068078088098108118128138148158168178188198208218228238248258268278288298308318328338348358368378388398408418428438448458468478488498508518528538548558568578588598608618628638648658668678688698708718728738748758768778788798808818828838848858868878888898908918928938948958968978988999009019029039049059069079089099109119129139149159169179189199209219229239249259269279289299309319329339349359369379389399409419429439449459469479489499509519529539549559569579589599609619629639649659669679689699709719729739749759769779789799809819829839849859869879889899909919929939949959969979989991000100110021003100410051006100710081009101010111012101310141015101610171018101910201021102210231024102510261027102810291030103110321033103410351036103710381039104010411042104310441045104610471048104910501051105210531054105510561057105810591060106110621063106410651066106710681069107010711072107310741075107610771078107910801081108210831084108510861087108810891090109110921093109410951096109710981099110011011102110311041105110611071108110911101111111211131114111511161117111811191120112111221123112411251126112711281129113011311132113311341135113611371138113911401141114211431144114511461147114811491150115111521153115411551156115711581159116011611162116311641165116611671168116911701171117211731174117511761177117811791180118111821183118411851186118711881189119011911192119311941195119611971198119912001201120212031204120512061207120812091210121112121213121412151216121712181219122012211222122312241225122612271228122912301231123212331234123512361237123812391240124112421243124412451246124712481249125012511252125312541255125612571258125912601261126212631264126512661267126812691270127112721273127412751276127712781279128012811282128312841285128612871288128912901291129212931294129512961297129812991300130113021303130413051306130713081309131013111312131313141315131613171318131913201321132213231324132513261327132813291330133113321333133413351336133713381339134013411342134313441345134613471348134913501351135213531354135513561357135813591360136113621363136413651366136713681369137013711372137313741375137613771378137913801381138213831384138513861387138813891390139113921393139413951396139713981399140014011402140314041405140614071408140914101411141214131414141514161417141814191420142114221423142414251426142714281429143014311432143314341435143614371438143914401441144214431444144514461447144814491450145114521453145414551456145714581459146014611462146314641465146614671468146914701471147214731474
  1. <html>
  2. <head>
  3. <title> RIGAL PROGRAMMING SYSTEM LANGUAGE DESCRIPTION </title>
  4. </head>
  5. <body>
  6. <H1> <A HREF="http://www.ida.liu.se/labs/pelab/members/vaden/rigal.html"> RIGAL</a> PROGRAMMING SYSTEM</H1>
  7. <H1> LANGUAGE DESCRIPTION
  8. </H1>
  9. <HR>
  10. by Mikhail AUGUSTON
  11. <p>
  12. University of Latvia,
  13. Institute of Mathematics and Computer Science
  14. <p>
  15. <h2> TABLE OF CONTENTS</h2>
  16. <p>
  17. <p> <a href="#a"> ABSTRACT </A>
  18. <p> <a href="#1"> 1. Introduction </A>
  19. <p> <a href="#2">2. Implementation </A>
  20. <p> <a href="#3"> 3. Lexical Rules </A>
  21. <p> <a href="#4"> 4. Data </A>
  22. 4.1 Atoms
  23. 4.2 Variables
  24. 4.3 Lists
  25. 4.4 Trees
  26. <p> <a href="#5"> 5. Expressions </A>
  27. 5.1 Accumulative Assignment Statements
  28. 5.2 Semantics of Variables
  29. <p> <a href="#6"> 6. Rules </A>
  30. 6.1. Simple Patterns
  31. 6.2. Assignment in Patterns
  32. 6.3 Rule Branches. Onfail Operations
  33. 6.4 Special Variables
  34. <p> <a href="#7"> 7. Compound Patterns </A>
  35. 7.1 List Pattern
  36. 7.2 Iterative Pattern of Sequence
  37. 7.3 Patterns for Alternative and Option
  38. 7.4 Tree Pattern
  39. <p> 7.5 Iterative Tree Pattern
  40. 7.6 Names of Lists and Trees in Patterns
  41. 7.7 Patterns of Logical Condition Testing
  42. <p> <a href="#8"> 8. Statements </A>
  43. 8.1 Assignment Statement
  44. 8.2 Conditional Statement
  45. 8.3 FAIL Statement
  46. 8.4 Loop Statements
  47. 8.5 Rule Call
  48. <p> <a href="#9"> 9. Input and Output </A>
  49. 9.1 SAVE and LOAD Statements
  50. 9.2 Text Output
  51. <p> <a href="#10"> 10. Program Structure </A>
  52. 10.1 Local Variables
  53. 10.2 References to Variables of Other Rules
  54. 10.3 Attribute Grammars and RIGAL. Global Attributes
  55. <p> <a href="#11"> 11. Built-in Rules </A>
  56. <p> <a href="#12"> 12. Sample Compiler </A>
  57. 12.1 TOYLAN Language
  58. 12.2 Intermediate Form of Program. Abstract syntax tree
  59. 12.3 Target Language BAL
  60. 12.4 Main Module of Compiler
  61. 12.5 Parsing Phase
  62. 12.6 Code Generation Phase
  63. <p> <a href="#13"> 13. Conclusions and Future Work </A>
  64. <p> <a href="#R"> References </A>
  65. <a name="a">
  66. <h2> ABSTRACT </h2>
  67. A new programming language for compiler writing is described.
  68. The main data structures are atoms, lists and trees. The control
  69. structures are based on advanced pattern matching. All phases of
  70. compilation, including parsing, optimization and code generation,
  71. can be programmed in this language in short and readable form.
  72. Sample compiler written in RIGAL is presented.
  73. <a name="1">
  74. <h2> 1. Introduction </h2>
  75. Programming language RIGAL is intended to be a tool for
  76. parsing ( context checking, diagnosing and neutralization of
  77. errors included ), for code optimization, code generation, static
  78. analysis of programs, as well as for the programming of
  79. preprocessors and convertors.
  80. <p> Almost all the systems envisaged to solve compiler
  81. construction problems contain means to describe context-free
  82. grammar of the source language. Earlier systems, like the Floyd -
  83. Evans language, [1] present tools to work with stack, which is
  84. used for parsing. Parsing methods for limited grammar classes are
  85. implemented in the languages and systems of later generations
  86. (usually LL(1) or LR(1) ).
  87. <p> Such systems as YACC (Johnson [2]), CDL-2 ( Koster [3]), SHAG
  88. (Agamirzyan [4]) and many others make use of synchronous
  89. implementation of parsing and different computations, e.g.,
  90. formation of tables, context checking, etc. Usually these actions
  91. are performed by call of semantic subroutines, written in some
  92. universal programming language ( e.g., in Pascal or C).
  93. <p> Attribute grammars advanced by Knuth [5] have greatly
  94. influenced development of systems for compiler construction.
  95. Systems, like, SUPER (Serebryakov [6]), ELMA (Vooglaid, Lepp,
  96. Lijb [7]), MUG2 (Wilhelm [9]) are based on the use of attribute
  97. grammars not only for parsing, but for code generation as well.
  98. <p> Pattern matching is a convenient tool for programming of
  99. parsing, optimization and code generation. The REFAL programming
  100. language [10], acknowledged for translator writing, may serve as
  101. a good example.
  102. <p> Vienna method for defining semantics of programming languages
  103. [11] suggests the usage of labelled trees in order to present the
  104. abstract syntax of programs. Representation of compilation
  105. intermediate results in the tree form has become usual (see
  106. [12]).
  107. <p> Dependence of control structures in the program from data
  108. structures used for program's work is one of the basic principles
  109. in programming. The recursive descent method could be considered
  110. to be the application of dependence principle.
  111. <p> The above mentioned ideas and methods were taken into account
  112. when creating RIGAL language.
  113. <p> The language possesses few basic notions. Data structures
  114. contain atoms, lists and trees. Advanced mechanism of pattern
  115. matching lies at the basis of control structures.
  116. <p> The fact that RIGAL is a closed language makes RIGAL
  117. distinctive. That means that almost all the necessary
  118. computations and input-output could be executed by internal means
  119. and there is no need to use external semantic subroutines.
  120. Therefore the portability of RIGAL programs to other computers is
  121. increased.
  122. <p> Means for work with trees, different patterns including,
  123. enable both programming of parsing algorithms and optimization
  124. phases and code generation as well. The language supports design
  125. of multipass translators. Trees are used as intermediate data.
  126. <p> The language allows to split the program into small modules
  127. (rules) and presents various means to arrange interaction of
  128. these modules. Pattern matching is used for parameter passing.
  129. <p> RIGAL supports attribute translation scheme and easy
  130. implementation of synthesized and inherited attributes is
  131. possible. The problem of global attributes is solved by usage of
  132. special references.
  133. <p> Lexical analysis is a separate task and requires special
  134. language facilities for description as it is, for example, in
  135. LEX/YACC [2] system. In the current implementation of RIGAL two
  136. scanners are included that accept lexics of Pascal, C,
  137. Modula-2 and RIGAL.
  138. <a name="2">
  139. <h2> 2. Implementation </h2>
  140. RIGAL was designed and implemented in the Computing Center of
  141. Latvia University in years 1987-1988. The first implementation
  142. was for PDP-11 in RSX-11.
  143. <p> At the present stage RIGAL interpreter has been developed and
  144. optimizing compiler RIGAL -> Pascal has been implemented by means
  145. of RIGAL itself. The interpreter and the compiler have been
  146. ported to VAX/VMS , IBM PC XT/AT (MS-DOS and MS-Windows) and
  147. Unix/SUN environments.
  148. <a name="3">
  149. <h2> 3. Lexical Rules </h2>
  150. The text of RIGAL program is a sequence of tokens - atoms
  151. (e.g., identifiers and integers ), keywords (e.g., if, RETURN ),
  152. special symbols (e.g., +, ## ), names of variables and rules
  153. (e.g., $A, #L ). Tokens may be surrounded by any number of
  154. blanks. A comment is any string of symbols that begins with two
  155. consecutive symbols '-' (minus ). The end of the comment is the
  156. end of the line. For example,
  157. <xmp>
  158. #Sum -- rule for addition of two numbers
  159. $N1 -- the first number
  160. $N2 -- the second number
  161. / RETURN $N1 + $N2 / -- return of the result
  162. ##
  163. </xmp> <a name="4">
  164. <h2> 4. Data </h2>
  165. <h3> 4.1 Atoms</h3>
  166. <p> An atom is a string of symbols. If the atom is an identifier
  167. ( the first symbol is a letter followed by letters or digits or
  168. underscore symbols), in the text of RIGAL program it could be
  169. written directly: AABC total_number x25
  170. <p> Numerical atoms are integers, for instance, 2, 187, 0, -25
  171. <p> In other cases the atom is quoted: '+' ':=' '1st'
  172. <p> Some identifiers are reserved as keywords in RIGAL. If they
  173. are used as RIGAL atoms, they should be quoted. For example,
  174. 'IF', 'RETURN'. Besides, any atom, which is an identifier, also
  175. can be quoted - ABC and 'ABC' represent one and the same atom.
  176. <p> It should be noted that 25 and '25' are different atoms, the
  177. latter is just a string of symbols '2' and '5'.
  178. <p> Two special atoms are distinguished in the language.
  179. <p> NULL - this atom is frequently yielded as a result of
  180. different operations, if something was incorrect in the process
  181. of computations. This atom also represents an empty list, an
  182. empty tree and Boolean value "false".
  183. <p> T - usually this atom is yielded by logical operations and
  184. represents value "true".
  185. <p>
  186. <p> <h3> 4.2 Variables</h3>
  187. <p> The name of a variable must begin with the symbol $, followed
  188. by an identifier. Value can be assigned to a variable, for
  189. example, by the help of assignment statement: $E := A
  190. <p> In this case the atom A becomes value of the variable $E.
  191. <p> In RIGAL variables have no types, the same variable may have
  192. an atom, a list or a tree as a value in different time moments.
  193. <h3> 4.3 Lists</h3>
  194. <p> Ordered sequences, i.e., lists can be composed from atoms and
  195. from other lists and trees, as well. A special function - list
  196. constructor serves for list formation. For instance, (. A B C .)
  197. forms a list of three atoms A, B and C.
  198. <p> Arguments of the list constructor may be expressions. The
  199. sample $E := (. (. 8 14 7 .) (. A B .) .) could be rewritten as
  200. follows:
  201. <p> $A := (. 8 14 7 .); $B := (. A B .); $E := (. $A $B .);
  202. <p> Separate elements of the list can be selected by indexing.
  203. Hence, $B [1] is atom A, $A [2] is atom 14, $E [2] is list
  204. <p> (. A B .), but $E [10] is atom NULL
  205. <p> If the value of the index is a negative number, for instance
  206. -N, then the N-th element, beginning from the end of the list, is
  207. selected. For example, $A [-1] is atom 7.
  208. <p> The necessity to add one more element to the list is quite
  209. common. Operation !. is envisaged for this purpose.
  210. <p> Example. (. A B .) !. C yields the list (. A B C .)
  211. <p> To link two lists in a new list the operation !! is applied (
  212. list concatenation). For instance, (. A B .) !! (. C D .) yields
  213. (. A B C D .).
  214. <p>
  215. <p> <h3> 4.4 Trees</h3>
  216. <p>
  217. <p> Tree constructor is used to create a tree. For example,
  218. <p> <. A : B, C : D .>
  219. <p> One can imagine tree as a graph, the nodes and arches of
  220. which are marked by some objects.
  221. <p> Objects before ':' in the tree constructor are named
  222. selectors. In the given implementation solely atoms, which are
  223. identifiers ( except NULL ), may serve as selectors. In the
  224. graphical representation selectors correspond to arches of the
  225. graph. All selectors of one and the same level in the tree must
  226. be different.
  227. <p> Any object - atom, list or tree, except atom NULL, may
  228. correspond to terminal nodes of the graph ( "leaves" of the
  229. tree). Hence, multilayer trees can be built. For instance,
  230. <p> <. A : B, C : <. D : E, F : G .> .>
  231. <p> Pair "selector : object" in the tree is named branch of the
  232. tree. Branches are unordered in the tree.
  233. <p> Likewise for the list constructor, the tree constructor may
  234. be described by expressions ( in both selector and object
  235. places), for instance,
  236. <p> $X := D; $B := (. 2 8 .);
  237. <p> $C := <. A : <. M : K .>, $X : '+' , E : $B .>;
  238. <p> Select operation serves to extract the tree component. It is
  239. in the following form: tree . sel , where tree is the expression,
  240. whose value must be some tree, but sel is the expression, whose
  241. value must be an atom-identifier.
  242. <p> Consequently,
  243. <p> $C . A is the tree <. M : K .> ,
  244. <p> $C . D is the
  245. atom '+' ,
  246. <p> $C . E is the list (. 2 8 .) ,
  247. <p> $C . E[2] is the atom 8
  248. , $C . A . M is the atom K
  249. <p> If there is no branch with a given selector in the tree, then
  250. the result is NULL: $C . W is atom NULL.
  251. <p> Operation of the tree "addition" is performed as well: T1 ++
  252. T2 , where T1 and T2 are trees. Tree T2 branches are added to the
  253. tree T1 one by one. If in the tree T1 there already exists a
  254. branch with the same selector, the branch is substituted by a new
  255. one. Therefore, the operation "++" is not commutative.
  256. <p> It should be pointed out that the tree constructor is
  257. computed from left to right, i.e.,
  258. <p> <. s1 : a1, s2 : a2, s3 : a3.>
  259. <p> gives the same result as the expression
  260. <p> (( NULL ++ <. s1 : a1 .> ) ++ <. s2 : a2 .>) ++ <. s3 : a3 .>
  261. <a name="5">
  262. <h2> 5. Expressions </h2>
  263. <p> Operations = and <> serve for the comparison of objects. The
  264. result of the comparison is either T ("true") or NULL ("false").
  265. <p> Atoms are matched directly, for instance, a = b gives NULL,
  266. 25 = 25 gives T, 17 <> 25 gives T.
  267. <p> Lists are considered equal iff they contain equal number of
  268. components and if these components are equal respectively.
  269. <p> Trees are considered equal iff they contain equal number of
  270. branches and if one of the trees contains the branch "S : OB",
  271. then the other tree also contains the branch "S : OB1" and OB =
  272. OB1.
  273. <p> Arithmetical operations +, -, *, DIV, MOD are assigned for
  274. numerical atoms. The essence of these operations is similar to
  275. those in Pascal. The result of an arithmetical operation is a
  276. numerical atom. Atom NULL is also admitted as the argument of
  277. arithmetical operation, in this case integer 0 is supposed to be
  278. its value. Under matching these atoms are considered different,
  279. i.e., NULL = 0 gives NULL.
  280. <p> Besides the operations = and <> numerical values could be
  281. compared by the help of >, <, >= and <=.
  282. <p> Logical operations AND, OR and NOT usually are applied under
  283. conditions in conditional statements. Their arguments may be
  284. arbitrary objects. If the object differs from NULL, it is
  285. supposed to have the value "true" in a logical operation. Atom
  286. NULL represents the "false" value. The result of a logical
  287. operation always is either T or NULL.
  288. <p> In order to make complex hierarchic objects ( trees and lists
  289. of complex structure ) more visual and to improve the work of
  290. pattern matching, trees and lists may be labelled. A name is an
  291. atom opposed to the root node of the tree or the whole list.
  292. Labelling operation is written the following way:
  293. <p> A :: OB
  294. <p> where A is an atom , OB is
  295. an object (a tree or a list). For example,
  296. <p> Add_op :: <. arg1 : 5, arg2 : 4 .>
  297. <p> The execution order of operations in the expression is
  298. controlled by parentheses "(" and ")". Priority is assigned to
  299. every operation, and, if the execution order is not defined by
  300. parentheses, operations are executed according to their
  301. priorities - beginning with the higher and proceeding to the
  302. lower.
  303. <p> Operations are listed in decreasing order of priorities (some
  304. operations will be discussed later).
  305. <p> 1) Rule call, list constructor, tree constructor, last
  306. <p> 2) Selector ".", index "[]", ::
  307. <p> 3) NOT, unary -
  308. <p> 4) *, DIV, MOD
  309. <p> 5) !. , !! , ++ , +, binary -
  310. <p> 6) = , <> , > , < , >= , <=
  311. <p> 7) AND
  312. <p> 8) OR
  313. <p> Binary operations of the same priority are executed from left
  314. to right, while unary operations from right to left.
  315. <p>
  316. <p> <h3> 5.1 Accumulative Assignment Statements</h3>
  317. <p>
  318. <p> It is quite often that working with a list or a tree elements
  319. are added step by step, thus the growing object is retained in
  320. the same variable. Therefore short form of assignment statement
  321. has been introduced. For the operations !. , !! , ++ and +
  322. statements of the form $X := $X op Expr can be written as
  323. $X op := Expr .
  324. <h3> 5.2 Semantics of Variables</h3>
  325. <p> In the implementation of RIGAL every object - atom, list or
  326. tree has a descriptor. It is a special data structure that
  327. contains some information about this object: the value of atom,
  328. the number of elements and pointers to elements for lists and
  329. trees. Variables have pointers to object descriptors as values.
  330. <p> Statement $X := OB assigns to the variable $X a pointer to
  331. the descriptor of object OB. After the execution of the statement
  332. $Y := $X both variables $X and $Y contain pointers to the same
  333. object OB.
  334. Operations !.:= , !!:= , +:= and ++:= change the descriptor
  335. o<p>f their first argument, i.e., have a side effect. Sometimes it
  336. can be undesirable. For example,
  337. <p> $A := (. 3 17 .); $B := $A; $B !.:= 25;
  338. <p> The value of $B becomes list (. 3 17 25 .), but operation
  339. !.:= has added element 25 immediately to the list (. 3 17 .), and
  340. the descriptor of this list is changed. As the value of the
  341. variable $A was a pointer to this descriptor, then after the
  342. execution of the statement $B !.:= 25 the value of the variable
  343. $A is changed, too.
  344. <p> To prevent this, we must have a copy of the object, to which
  345. $A refers to before assigning it to $B. Operation COPY( OB )
  346. is used for this purpose. It makes a copy of the descriptor of
  347. the object OB.
  348. <p> Now we can write a "safe" call of the operation !.:= in such
  349. a way: $A := (. 3 17 .); $B := COPY( $A); $B !.:= 25;
  350. <p> As a result $B takes the value (. 3 17 25 .), but $A remains
  351. equal to (. 3 17 .). The same effect can be obtained after
  352. execution of statements $A := (. 3 17 .); $B := $A !. 25;
  353. <a name="6">
  354. <h2> 6. Rules </h2>
  355. <p> The concept of rule is analogous to concepts of procedure and
  356. function in conventional languages, such as Pascal or C.
  357. <p> First of all, by the help of a rule we can check, whether an
  358. object or a sequence of objects complies with some grammar. For
  359. this purpose rule has a pattern. Objects, assigned under rule
  360. call (arguments of the rule), are matched with the pattern. If
  361. there is a necessity, some operations could be executed, for
  362. instance, computations and input-output operations,
  363. simultaneously with rule arguments and pattern matching.
  364. <p> Rule that is called can compute and return back some value
  365. (object), i.e., it can be used as function.
  366. <p> Depending on the result of rule arguments and pattern
  367. matching, the rule call ends with success or failure. Thus the
  368. rule call could be used in another rule patterns.
  369. <h3> 6.1. Simple Patterns</h3>
  370. <p> Definition of the rule begins with the indication of the name
  371. of the rule in the form of #LLL , where LLL is an
  372. atom-identifier. In the most common case the pattern is indicated
  373. after the name of the rule. Rule definition ends with symbol
  374. '##'. For instance,
  375. #L1 A B ##
  376. <p> In this case the pattern consists of atoms A and B. Call of
  377. the rule #L1 takes place, for instance, the following way :
  378. <p> #L1 ( A B )
  379. <p> The sequence of objects - atoms A and B, is assigned as rule
  380. arguments.
  381. <p> After rule call the argument and pattern matching begins. The
  382. first argument - atom A is matched with the first pattern, which
  383. is also an atom. These atoms are equal, so their matching is
  384. successful. After that the next object from the sequence of
  385. arguments - atom B and the next pattern, also atom B, are
  386. matched. Their matching is also successful, therefore, the call
  387. of the rule #L1 is successful, too.
  388. <p> #L1( A C ) call fails, because the second argument - atom C
  389. was not successfully matched with the pattern - atom B.
  390. <p> #L1( A ) call fails, as there is no object for the second
  391. pattern with which it could be matched successfully.
  392. <p> But #L1( A B C) call is successful, as the third rule
  393. argument - atom C was not demanded by any pattern and matching of
  394. the first two rule arguments was successful.
  395. <p> Arbitrary atoms, both non-numerical and numerical, may be
  396. described as patterns.
  397. <p> Such operations as assignment statements, input - output and
  398. others may be indicated before the pattern, after it and between
  399. patterns. These statements are quoted in the pair of symbols '/'
  400. . If there is a necessity to write several statements within the
  401. pair '/' , these statements are separated by the symbol ';' .
  402. <p> A group of statements is executed in the rule pattern, if
  403. matching of the previous pattern with the corresponding rule
  404. arguments was successful.
  405. <p> The value returned by the rule is worked out by statement
  406. RETURN . It has the following form: RETURN expression.
  407. Simultaneously this statement completes the execution of the
  408. rule.
  409. <p> Example.
  410. <xmp> #L2 'begin' 'end' / RETURN 'The pair begin-end' / ##</xmp>
  411. Rule call is illustrated in the following example.
  412. <xmp> $A := #L2 ( 'begin' 'end' ); </xmp>
  413. <p> As a result the atom 'The pair begin-end' is assigned to the variable $A.
  414. <p> If RETURN statement is not described in the rule, then the
  415. NULL value is returned.
  416. <p> If the rule call ends in failure, then usually value NULL is
  417. returned, although in case of failure, it is possible to work out
  418. the returned value, which is not NULL; for this purpose statement
  419. RETURN must be used in onfail-operations (see sect.6.3.).
  420. <p> Variable could be used as pattern. It is matched with one
  421. object (atom, list or tree) from the sequence of rule arguments.
  422. Matching always ends in success, and as a side effect the
  423. variable obtains this object as value. For example,
  424. <p> #L3 $A $B /RETURN (. $B $A .)/ ##
  425. <p> After the call $X := #L3 ( 1 2) the variable $X obtains as
  426. value (. 2 1 .)
  427. <p> The rule pattern, in its turn, may refer to some rule
  428. (recursively, as well). Then the subsequence of the calling rule
  429. arguments become arguments of rule - pattern. If the call of the
  430. rule - pattern is successful, then matching of further patterns
  431. of the calling rule with the remaining arguments proceeds. If the
  432. call of the rule - pattern fails, then the pattern matching of
  433. the calling rule fails, too. For example,
  434. <p> #L4 A #L5 D ##
  435. <p> #L5 B C ##
  436. <p> Then the call #L4( A B C D) is successful, but the call
  437. <p> #L4( A E F D) is unsuccessful.
  438. <p> There is a number of built-in rules in the language (see
  439. section 11.). For instance, #NUMBER is successfully matched with
  440. a numerical atom and returns it as a value, other arguments fail
  441. and return NULL. #IDENT is successfully matched with atom -
  442. identifier and returns it as value.
  443. <h3> 6.2. Assignment in Patterns</h3>
  444. <p> Every pattern, when successfully matched with the
  445. corresponding rule argument, returns some value. The value of
  446. atom pattern coincides with this atom, the value of variable
  447. pattern coincides with the value obtained by this variable as a
  448. result of matching with the arguments. The value of rule pattern
  449. is defined by statement RETURN in this rule.
  450. <p> If the matching ends in failure, the pattern usually returns
  451. value NULL.
  452. <p> These values, returned by patterns, can be assigned at once
  453. to some variable. It is enough to write the name of the variable
  454. and the assignment symbol ':=' before the pattern element.
  455. <p> Example.
  456. <xmp>
  457. #L6 $A $R := #L7 / RETURN (. $A .) !! $R / ##
  458. #L7 $B $C / RETURN (. $B $C .) / ##
  459. </xmp>
  460. <p> After execution of the statement $X := #L6 ( 1 2 3) the value
  461. of $X will be (. 1 2 3 .)
  462. <p> Symbols of accumulative assignment '!.:=' , '!!:=' , '++:='
  463. and '+:=' can be used instead of ':=' in patterns .
  464. <p> Therefore, we can rewrite the previous example the following
  465. way: <xmp>
  466. #L6_1 $R !.:= $A $R !!:= #L7_1 / RETURN $R / ##
  467. #L7_1 $M !.:= $B $M !.:= $C / RETURN $M / ##</xmp>
  468. <p> It should be noted that all variables in the rule are
  469. initialized by value NULL, so the value of the expression NULL !.
  470. $A that equals to (. $A .) is assigned to the variable $R by the
  471. first application of the pattern $R !.:= $A in #L6_1.
  472. <p> Patterns of the type $N := #NUMBER or $ID := #IDENT are used
  473. very often, therefore, following defaults are introduced in the
  474. language. If the first letter of the variable name is N, then
  475. this variable, having been used as pattern element, will have a
  476. successful matching only with a numerical atom, in other cases
  477. matching ends in failure, and variable obtains value NULL. If the
  478. first letter of the name of the variable is I, this variable is
  479. matched successfully only with an atom-identifier.
  480. <h3> 6.3 Rule Branches. Onfail Operations</h3>
  481. <p> Several groups of patterns may be united in one rule.
  482. <p> The first group of patterns is applied to the rule arguments
  483. first. If matching of this group of patterns with the arguments
  484. is successful, the rule call is successful. But if matching has
  485. failed, transition to the next group of patterns takes place, and
  486. it is matched with the same arguments. It goes on until some
  487. group of rule patterns is matched with the arguments
  488. successfully. If not a single pattern group matches successfully
  489. with rule arguments, the rule call ends in a failure.
  490. <p> Such alternative pattern groups are called rule branches,
  491. and, when writing the rule, they are separated by the symbol
  492. ';;'.
  493. <p> If the branch fails, the execution of its patterns and
  494. statements is abandoned at the place, where branch pattern
  495. failed, and control is transferred to the next branch (if there
  496. is one) or the whole rule fails (if the current branch is the
  497. last one in the rule). Still there is a possibility to execute
  498. some operations before exit from the branch.
  499. <p> ONFAIL operation is a sequence of statements, written at the
  500. end of the branch and delimited from patterns and branch
  501. statements by keyword ONFAIL.
  502. <p> If ONFAIL-statements are described in the branch, then in
  503. case of branch failure, control is transferred to them and
  504. statements, given in ONFAIL-unit , are executed. So, in case of
  505. branch failure, causes of failure can be analyzed and message can
  506. be output. Statement RETURN can be executed in ONFAIL operations,
  507. as well. Then exit from the rule takes place (with failure), and
  508. some other value than NULL can be returned.
  509. <h3> 6.4 Special Variables</h3>
  510. Special variable without name $ denotes the first rule
  511. argument matched by a rule pattern.
  512. <p> The value of special variable $$ equals to the value of
  513. current rule argument, to which current rule pattern is applied.
  514. <a name="7">
  515. <h2> 7. Compound Patterns </h2>
  516. Lists, sequences of elements in lists and trees can be
  517. analyzed by patterns. Nesting of patterns practically is
  518. unlimited. It is allowed to insert statements before, after and
  519. within any pattern.
  520. <h3> 7.1 List Pattern</h3>
  521. <p> List pattern is written in the rule the following way:
  522. <p> (. S1 S2 ... SN .)
  523. <p> where S1, S2, ..., SN are patterns . For instance,
  524. <p> #L8 (. $E1 $E2 .) ##
  525. <p> Pattern of the rule #L8 is matched successfully with any
  526. list, containing precisely two elements. Such call is successful:
  527. <xmp> #L8( (. (. 1 2 .) <. A : B .> .) ) </xmp>
  528. <p> But the following calls end in failure.
  529. <p> #L8( A B ) - because
  530. pattern will be applied to the first argument, i.e., to atom A,
  531. <p> #L8( (. 13 .) ) - because the argument is one element list.
  532. <p> In case of success the list pattern yields value that can be
  533. assigned to some variable. This value coincides with the whole
  534. list, to which the pattern was applied.
  535. <h3> 7.2 Iterative Pattern of Sequence</h3>
  536. In RIGAL the following pattern is defined for sequence
  537. recognition: (* S1 S2 ... SN*) , where S1 , S2, ... SN are some
  538. patterns. This pattern describes the repetition of enclosed
  539. sequence of patterns zero or several times.
  540. <p> Rules with a variable number of arguments can be defined by
  541. iterative pattern of sequence. For example,
  542. <xmp> #Sum (* $S +:= $N *) / RETURN $S / ## </xmp>
  543. <p> This rule is used for summing up any amount of numbers.
  544. <xmp> #Sum( 2 5 11) = 18 and #Sum( 3 ) = 3</xmp>
  545. <p> Iterative pattern is very often used within list pattern. For
  546. instance, the following rule counts the number of list elements.
  547. <xmp>
  548. #Length (. / $L := 0 / (* $E / $L +:= 1 / *) .) / RETURN $L / ##</xmp>
  549. <p> Samples of rule call.
  550. <xmp>
  551. #Length( (. A B C .) ) = 3 and #Length( NULL ) = 0</xmp>
  552. <p> Iterative pattern (+ S1 S2 ... SN +) is analogous to the
  553. pattern (* ... *), but assigns the repetition of enclosed pattern
  554. sequence one or several times.
  555. <p> In the iterative pattern of sequence the element delimiter is
  556. indicated in the form of (* S1 S2 ... SN * Delimiter ) or (+ S1
  557. S2 ... SN + Delimiter +)
  558. <p> Atom or name of the rule may serve as Delimiter .
  559. <p> Example. Analysis of a simple Algol-like declaration. A
  560. fragment of variable table coded in a tree form is returned as a
  561. result.
  562. <xmp>
  563. #Declaration $Type := ( integer ! real )
  564. (+ $Id / $Rez ++:= <. $Id : $Type .> / + ',')
  565. / RETURN $Rez / ##
  566. </xmp>
  567. Call #Declaration ( real X ',' Y ) returns value <. X : real, Y : real .>
  568. <p> It should be noted that the pattern (* $E * ',' ) differs
  569. from the pattern (* $E ',' *) in the point that the presence of
  570. atom ',' is obligatory in the second pattern at the end of
  571. sequence.
  572. <h3> 7.3 Patterns for Alternative and Option</h3>
  573. The choice of several possible patterns is written the
  574. following way: ( S1 ! S2 ! ... ! SN )
  575. <p> Patterns S1 , S2 , ... , SN are applied one by one from left
  576. to right, until one of them succeeds.
  577. <p> In case of success alternative pattern yields value. It
  578. coincides with the value of the successful pattern within the
  579. alternative and may be assigned by some variable.
  580. <p> Example. Simple arithmetic expression parsing. When
  581. successful, an expression tree is returned, which can be regarded
  582. as an intermediate form for the next compilation phases.
  583. <xmp>
  584. #Expression $A1 := #Term
  585. (* $Op := ( '+' ! '-' ) $A2 := #Term
  586. / $A1 := <. op : $Op , arg1 : $A1 , arg2 : $A2 .> / *)
  587. / RETURN $A1 / ##
  588. #Term $A := ( $Id ! $Num ) / RETURN $A / ;;
  589. '(' $A := #Expression ')' / RETURN $A / ##
  590. </xmp>
  591. The call #Expression( X '-' Y '+' 7 ) returns the value
  592. <xmp>
  593. <. op: '+', arg1: <. op: '-', arg1: X, arg2: Y .>, arg2: 7 .>
  594. </xmp>
  595. In RIGAL we may write a rule that matches successfully with
  596. an empty sequence of arguments:
  597. <xmp> #empty ## </xmp>
  598. <p> Now the pattern for option can be written down: ( S ! #empty )
  599. <p> In short form this issue may be written down in RIGAL the
  600. following way: [ S ] where S is some pattern or pattern sequence.
  601. Pattern [ S ] always ends in success.
  602. <h3> 7.4 Tree Pattern</h3>
  603. <p> Tree pattern checks, whether the object is a tree with fixed
  604. structure. By means of this pattern access to the components of
  605. the tree is obtained. The tree pattern is described the following
  606. way:
  607. <xmp>
  608. <. Sel1 : Pat1, Sel2 : Pat2, ... , SelN : PatN .></xmp>
  609. <p> where
  610. Sel1, Sel2, ... SelN are atoms-identifiers, but Pat1, Pat2, ...
  611. PatN are patterns.
  612. <p> If the object, to which the tree pattern is applied, is not a
  613. tree, then the application of the pattern fails at once. If there
  614. is the selector Sel1 in the tree, then the pattern Pat1 is
  615. applied to the corresponding object. If there is no selector Sel1
  616. in the tree or the application of Pat1 has failed, the whole
  617. pattern also fails.
  618. <p> If matching the first branch was successful, branch matching
  619. of the pattern 'Sel2 : Pat2' , etc. begins.
  620. <p> Hence, pattern branches are applied to the tree in the same
  621. order as they are written in the pattern. Therefore, the order of
  622. tree traversing may be controlled. It is possible to have
  623. reiterative visit of branches ( if selectors are repeatedly
  624. described in the tree pattern) or omission of branches (if
  625. corresponding selectors are not given in the pattern).
  626. <p> In case of success the tree pattern returns the value, which
  627. coincides with the whole object - a tree, to which the pattern
  628. was applied, irrespective of presence of all tree selectors in
  629. the pattern or absence of some.
  630. <p> Example. Let us suppose expression tree to be formed like in
  631. the above example. The task is to traverse the tree and return a
  632. list that represents the Polish postfix form of this expression.
  633. <xmp>
  634. #Postfix_form <. arg1: $Rez := #Postfix_form,
  635. arg2: $Rez !!:= #Postfix_form,
  636. op: $Rez !.:= $Op .> / RETURN $Rez / ;;
  637. $Rez := ( $Id ! $Num ) / RETURN (. $Rez .) / ##
  638. </xmp>
  639. The call
  640. <xmp>
  641. #Postfix_form( <. op: '-',
  642. arg1: X,
  643. arg2: <. op:'+',
  644. arg1: Y,
  645. arg2: 5 .> .>)
  646. </xmp>
  647. returns the value
  648. <xmp>
  649. (. X Y 5 '+' '-'.)
  650. </xmp>
  651. <p> Some branches in the tree pattern may be described as
  652. optional, in this case they are enclosed in brackets '[' and ']'
  653. . If there is no selector of optional branch in the argument
  654. tree, its pattern is omitted and transition to next pattern
  655. branch takes place. If there is a selector of the type in the
  656. argument tree, the pattern branch is developed as usual.
  657. <h3> 7.5 Iterative Tree Pattern</h3>
  658. The simplest form of iterative tree pattern is the following:
  659. <xmp> <* $Var : P *></xmp>
  660. where $Var is some
  661. variable, and P is a pattern.
  662. <p> A loop over the tree is performed by the help of this
  663. pattern. All selectors of the argument tree are assigned to the
  664. variable $Var one by one. The pattern P is applied to each
  665. object, which corresponds in the argument tree to the current
  666. selector in the variable $Var. If even one application of the
  667. pattern P fails, the whole iterative tree pattern fails. For
  668. example,
  669. <xmp>
  670. #Variable_table <* $Id : $E := ( integer ! real )
  671. / $R !.:= (. $Id $E .)/ *> / RETURN $R / ##
  672. </xmp>
  673. Call example.
  674. <xmp>
  675. #Variable_table( <. X : integer, Y : real, Z : real .> ) =
  676. (. (. X integer .) (. Y real .) (. Z real .) .)
  677. </xmp>
  678. Sometimes, performing a loop over the tree, some branches
  679. should be updated in a special way. For this purpose iterative
  680. tree pattern with distinguished branches is used.
  681. <xmp>
  682. <* Sel1 : Pat1, Sel2 : Pat2, ..., SelN : PatN, $Var : P *>
  683. </xmp>
  684. <p> where Sel1, Sel2, ... SelN are atoms-identifiers;
  685. <p> Pat1, Pat2, ... PatN are patterns,
  686. i.e., like elements in simple tree pattern;
  687. $Var is a variable, but P is a pattern, as in simple case of
  688. iterative tree pattern.
  689. <p> The pattern is applied to the argument tree the following
  690. way. First of all distinguished pattern branches 'Sel : Pat' are
  691. developed. Their matching with branches of the argument tree
  692. happens exactly the same way as with simple tree pattern. Then
  693. the element '$Var : P' is applied to other branches of the
  694. argument tree the same way as in simple iterative tree pattern.
  695. <p> Some distinguished branches can be optional, for this purpose
  696. they are enclosed in brackets '[' and ']'. Semantics is the same
  697. as in the case of simple tree pattern.
  698. <p> Example. Let it be a tree of arbitrary size. In some of its
  699. subtrees there is the selector LABEL, to which numerical atom is
  700. attached. All these numbers over the whole tree must be collected
  701. in a list, and the list must be returned as result.
  702. <xmp>
  703. #Label_list
  704. <* [ LABEL : $Result !.:= $N ],
  705. $S : $Result !!:= #Label_list *> / RETURN $Result / ;;
  706. $E ##
  707. </xmp>
  708. <p> The rule has two branches. Traversing of the tree and its
  709. subtrees is described in the first branch. The resulting list is
  710. formed in the variable $Result. The traversing of subtrees is
  711. carried out by the help of recursive call of the rule
  712. #Label_list. The second branch of the rule consisting of just one
  713. pattern $E is applied at the leaves of the tree. The pattern
  714. matches successfully with any object and the whole branch returns
  715. value NULL, which is accepted as empty list at the previous level
  716. of recursion.
  717. <p>
  718. Call sample.
  719. <xmp>
  720. #Label_list ( <. A: <. LABEL: 5, B: abc .>,
  721. LABEL: 17, D: 25 .> ) = (. 17 5 .)
  722. </xmp>
  723. <h3> 7.6 Names of Lists and Trees in Patterns</h3>
  724. <p> The assignment of names was discussed in Section 5.
  725. <p> In list and tree patterns we can have matching of list and
  726. tree names with the described values or simply get these names in
  727. the described variable. For this purpose the name may be
  728. indicated before list or tree pattern: atom :: pattern
  729. <p> If the atom described in the pattern coincides with the name
  730. of the list (or tree), to which the pattern is applied, the
  731. application of the pattern to the argument begins. If it does
  732. not, other pattern elements are not applied and the pattern
  733. fails.
  734. <p> To obtain access to the name of the argument, instead of atom
  735. we must indicate the variable, in which the name is assigned as
  736. value.
  737. <h3> 7.7 Patterns of Logical Condition Testing</h3>
  738. Pattern of the type: S' ( expression ) works the following
  739. way. First of all the expression is evaluated. If its value
  740. differs from NULL, the pattern is successful. The value of the
  741. matched argument is returned as the value of the pattern, if
  742. matching was successful. If the value of the expression equals to
  743. NULL, the pattern fails and returns NULL.
  744. <p> The value of special variable $$ in the expression of
  745. S-pattern equals to the value of the argument, to which S-pattern
  746. is applied.
  747. <p> The skip of token sequence until the nearest symbol ';' is
  748. described by the pattern: (* S' ( $$ <> ';' ) *)
  749. <p> Let under parsing a case is accentuated when the assignment
  750. statement is in the form of X := X + E , where X is a variable,
  751. and E is an expression. This case could be described by pattern
  752. of the type: $Id ':=' S' ( $$ = $Id ) '+' #Expression
  753. <p> Pattern of the type: V' ( expression ) works similar to
  754. S-pattern, yet in case of success no advancing along the sequence
  755. of rule arguments takes place, so the next pattern element is
  756. applied to the same argument.
  757. <p> This pattern is useful for context condition check. Example.
  758. The pattern
  759. <xmp>
  760. S' ( #NUMBER($$) and ( $$ > 7))
  761. </xmp>
  762. may be substituted by
  763. a sequence of patterns
  764. <xmp>
  765. $Num V'($Num > 7)
  766. </xmp>
  767. <a name="8">
  768. <h2> 8. Statements </h2>
  769. <h3> 8.1 Assignment Statement</h3>
  770. In the left side of assignment statement a variable may be
  771. indicated, which is followed by an arbitrary number of list
  772. indexes and/or tree selectors. For example,
  773. <xmp>
  774. $X := (. A B C .); $Y:= <. D : E, F : G .>;
  775. </xmp>
  776. <p> After assignment $X[2] := T the value of $X is (. A T C .) .
  777. <p> After assignment $Y.D :=17 the value of $Y is <.D :17, F:G .>
  778. <p> The execution of the statement $Y.A := T yields the run time
  779. error message. The necessary result is obtained the following
  780. way:
  781. <xmp>
  782. $Y ++:= <. A : T .>;
  783. </xmp>
  784. <p> Tree branch is deleted by assigning an empty object to the
  785. corresponding selector: $Y.D := NULL;
  786. <h3> 8.2 Conditional Statement</h3>
  787. Conditional statement has the following form:
  788. <xmp>
  789. IF expression -> statements
  790. </xmp>
  791. Then branches may
  792. follow (it is not compulsory)
  793. <xmp>
  794. ELSIF expression -> statements
  795. </xmp>
  796. Conditional statement ends with keyword FI.
  797. <p> In conditional statement branches expressions are computed
  798. one by one, until a value different from NULL is obtained. Then
  799. the statements described in this branch are executed.
  800. <h3> 8.3 FAIL Statement</h3>
  801. FAIL statement finishes the execution of the rule branch with
  802. failure. Example. In order to repair errors in parsing process,
  803. the sequence of tokens should be skipped quite frequently, for
  804. instance, until semicolon symbol. It is done the following way.
  805. <xmp>
  806. #statement ... ;; -- branches for statement analysis
  807. (* #Not_semicolon *) ';' -- no statement is recognised
  808. ##
  809. #Not_semicolon $E / IF $E = ';' -> FAIL FI/ ##
  810. </xmp>
  811. <h3> 8.4 Loop Statements</h3>
  812. Statement of the types
  813. <xmp>
  814. FORALL $VAR IN expression
  815. DO statements OD
  816. FORALL SELECTORS $VAR BRANCHES $VAR1 IN expression
  817. DO statements OD
  818. FORALL BRANCHES $VAR1 IN expression
  819. DO statements OD
  820. </xmp>
  821. loops over a list or a tree.
  822. <p> The value of the expression must be either a list or a tree.
  823. Value of the current list element (if the loop is over the list)
  824. or value of the current selector (if the loop is over the tree)
  825. is assigned to the loop variable $VAR one by one. The
  826. corresponding branch value is assigned to the variable $VAR1 (if
  827. the loop is over the tree). Statements, describing body of the
  828. loop, may use the current value of the variables $VAR and $VAR1.
  829. <p>
  830. Loop statement of the type
  831. <xmp> LOOP statements END;</xmp>
  832. repeats statements of
  833. the loop body, until one of the statements - BREAK, RETURN or
  834. FAIL is not executed.
  835. <h3> 8.5 Rule Call</h3>
  836. If a rule is called just to execute statements described in
  837. it, and value returned by the rule is not necessary, the rule
  838. call is written down as statement. It is analogous to procedure
  839. call in traditional programming languages. Success/failure of the
  840. rule and value returned by it is disregarded in such a call.
  841. <a name="9">
  842. <h2> 9. Input and Output </h2>
  843. <h3> 9.1 SAVE and LOAD Statements</h3>
  844. Objects created by RIGAL program (atoms, lists, trees) can be
  845. saved in the file and loaded back to the memory.
  846. <p> Statement
  847. <xmp>
  848. SAVE $Var file-specification
  849. </xmp>
  850. unloads the object,
  851. which is the value of the variable $Var to the file with the
  852. given specification. File, formed by SAVE statement, contains
  853. precisely one object (atom, list or tree).
  854. <p> We can load the object from the file in the memory having
  855. executed statement:
  856. <xmp>
  857. LOAD $Var file-specification
  858. </xmp>
  859. <h3> 9.2 Text Output</h3>
  860. To output texts (messages, generated object codes, etc. )
  861. several text files can be opened in the RIGAL program. The text
  862. file FFF is opened by statement: OPEN FFF file-specification
  863. File-specification may be an expression. It presents the name of
  864. the file on the device.
  865. <p> Statement of the type
  866. <xmp>
  867. FFF << Expr1 Expr2 ... ExprN
  868. </xmp>
  869. outputs a sequence
  870. of atoms to the file FFF. Values of expressions Expr1, Expr2, ...
  871. are either atoms or lists consisting of objects, different from
  872. trees.
  873. <p> This statement outputs atoms as sequences of symbols to the
  874. text file, inserting a blank after every atom. Atoms in the list
  875. are output in the same order as they are in the list.
  876. <xmp>
  877. Example. FFF << A B 12 ;
  878. </xmp>
  879. <p> A string of characters is output in the text file FFF the
  880. following way: "A B 12 "
  881. Symbol @ in the sequence of expressions of output statement
  882. switches over to other output mode of blanks separating atoms. By
  883. default at the beginning of execution of text output statement
  884. the output mode with blanks is on.
  885. <p> Example. FFF << A B @ C D 25 @ E F 57 ;
  886. <p> The following string of characters is output to the text file
  887. <p> "A B CD25E F 57"
  888. <p> Statement of the type
  889. <p> FFF << ...
  890. <p> always begins output with
  891. the beginning of a new record. Output statement of the type
  892. <p> FFF <] ...
  893. <p> continues output in the current record.
  894. <p> By the help of the statement of the type
  895. <p> PRINT expression
  896. <p> the value of atom, list
  897. or tree can be output in a readable form on the display, disk or
  898. on the printer. It is useful when debugging RIGAL programs.
  899. <a name="10">
  900. <h2> 10. Program Structure </h2>
  901. <p> Program written in the RIGAL language consists of the main
  902. program and rules. The main program text must be at the beginning
  903. of the RIGAL program text, but the text of the rules is written
  904. afterwards. Main program, as well as rule, begins by the name
  905. indication in the form of #main_program_name, then statements are
  906. described, separated by symbols ';' . The end of the main program
  907. is marked by the symbol '##'.
  908. <p> Usually operations that deal with the initial object loading,
  909. rule call and unloading of created objects in the files are
  910. concentrated in the main program. Therefore, main program has no
  911. pattern elements or arguments of its own.
  912. <p> When RIGAL is used for parsing, text file with the input
  913. information first is updated by scanner, which transforms it into
  914. a list of tokens. Thus rules describing required parsing can be
  915. applied to this list. Intermediate results of the RIGAL program,
  916. for instance, abstract syntax trees obtained by parsing can be
  917. unloaded in the file by the help of SAVE statement. They are
  918. unloaded so, that other RIGAL programs (for instance, those,
  919. which implement phase of code generation in compilers) can load
  920. them as input data. Sample of main program is given in Section
  921. 12.4.
  922. <p> Rules can be written down after main program in any order.
  923. <h3> 10.1 Local Variables</h3>
  924. <p> There are no special variable declarations in RIGAL. The fact
  925. that a variable is used in some statement, pattern or expression
  926. implies that the variable is defined as local variable of the
  927. rule or the main program.
  928. <p> For recursive rule calls local rule variables are pushed in a
  929. stack, so, that every active rule instance has its own set of
  930. local variables.
  931. <p> All variables are initialized by the NULL value, when the
  932. corresponding rule or the main program is called and when the
  933. execution of rule branch starts.
  934. <h3> 10.2 References to Variables of Other Rules</h3>
  935. <p> The construction of RIGAL makes it possible to obtain access
  936. from the rule to local variables of another rule. It has the
  937. following form: LAST #L $X
  938. <p> This reference denotes the value of the variable $X in the
  939. last (in time ) and still active instance of the rule #L. Such
  940. references can be used in left and right sides of assignment
  941. statement.
  942. <p> If at the moment of evaluation of the expression LAST #L $X
  943. there is no active instance of the rule #L, the value of the
  944. expression LAST #L $X equals NULL. If such LAST #L $X is in the
  945. left side of assignment statement, the statement is disregarded
  946. (and run time error message is output).
  947. <p> By the help of LAST we may refer to both rule and main
  948. program variables.
  949. <h3> 10.3 Attribute Grammars and RIGAL. Global Attributes</h3>
  950. <p> There is a close analogy between attribute grammar and RIGAL
  951. program. Rules in RIGAL correspond to grammar nonterminals, and
  952. variables - to attributes.
  953. <p> In attribute grammars the greatest part of attributes are
  954. used as transit attributes. To avoid this global attributes are
  955. introduced in the attribute grammar implementations. The usage of
  956. LAST references solves this problem in RIGAL.
  957. <p> Implementation of both synthesized and inherited attributes
  958. is possible as it is demonstrated in the following scheme.
  959. <xmp>
  960. #LA ... ... ...
  961. assigns value to the attribute $A
  962. calls #LB ... ... ... ##
  963. #LB ... ... ...
  964. $B1 := LAST #LA $A -- uses the inherited attribute $A from #LA
  965. calls #LC
  966. -- after this call the value of the attribute $C
  967. -- from #LC is assigned to the synthesized attribute $B2
  968. ... ... ... ##
  969. #LC ... ... ...
  970. assigns value to the attribute $C
  971. LAST #LB $B2 := $C -- the value is assigned to the
  972. -- synthesized attribute $B2 of #LB
  973. ... ... ... ##
  974. </xmp>
  975. <a name="11">
  976. <h2> 11. Built-in Rules </h2>
  977. There is a number of built-in rules in the language. These
  978. rules implement functions, the implementation of which is
  979. impossible or ineffective by other language means.
  980. <p> Call of built-in rules is written down the same way as call
  981. of rules defined by the user itself. Along with the value a
  982. built-in rule yields success or failure hence, built-in rules are
  983. used as patterns.
  984. <p> There are predicates such as #ATOM(E), #NUMBER(E), #IDENT(E),
  985. #LIST(E) and #TREE(E).
  986. <p> The built-in rule #LEN(E) returns numerical atom as value. If
  987. E is an atom, then for non-numerical atoms it returns the number
  988. of atom symbols. For numerical atoms this rule returns the number
  989. of significant digits plus 1, if the atom is a negative number.
  990. #LEN( NULL) equals 0, #LEN('ABC') equals 3, #LEN(-185) equals 4.
  991. <p> If E is a list, then #LEN(E) returns the number of list
  992. elements, but, if E is a tree, then it returns the number of tree
  993. branches.
  994. <p> #EXPLODE(E). If E is an atom, then it succeeds and returns
  995. one character atom list that represents the value E 'decomposed'
  996. in separate characters. If E is a numerical atom, only
  997. significant digits are present.
  998. <p> Examples.#EXPLODE(X25) yields (. 'X' '2' '5' .).
  999. <p> #EXPLODE(-34) yields (. '-' '3' '4' .).
  1000. <p> #IMPLODE(E1 E2 ... EN). This rule yields the concatenation of
  1001. atoms or lists E1, E2, ..., EN in a new, non-numerical atom.
  1002. <p> Examples.#IMPLODE( A B 34) equals 'AB34'.
  1003. <p> #IMPLODE(25 (. A -3 .) ) equals '25A-3'.
  1004. <p> #CHR(N). The rule returns an atom, which consists of just one
  1005. ASCII character with the code N ( 0 <= N <= 127).
  1006. <p> #ORD(A). Returns an integer, which is an internal code of the
  1007. first character of the nonnumerical atom A.
  1008. <p> For instance, #ORD( A) = 65, #ORD( ABC) = 65.
  1009. <p> #PARM(T) . Returns list of parameters which was assigned when
  1010. the whole program called for execution.
  1011. <p> #DEBUG(E). If E equals the atom 'RULES', then, as soon as the
  1012. rule is called, information concerning calls of the rules (both
  1013. user defined and built-in rules) and their execution results will
  1014. be output. The call #DEBUG(NORULES) stops the debugging of the
  1015. rules.
  1016. <a name="12">
  1017. <h2> 12. Sample Compiler </h2>
  1018. Compiler for the TOYLAN language, which is a very simple
  1019. programming language, is discussed in the following units.
  1020. Compiler works in two passes. The first phase is parsing and
  1021. construction of the program's intermediate form as abstract
  1022. syntax tree. The second phase is code generation.
  1023. <p> Description of input and intermediate language grammars by
  1024. means of RIGAL is presented. Thus formalized compiler
  1025. documentation (admitting checking on a computer) is obtained.
  1026. <h3> 12.1 TOYLAN Language</h3>
  1027. The description of TOYLAN syntax can be regarded as
  1028. description of acceptable sequences of tokens. Atoms represent
  1029. lexical elements of TOYLAN program: keywords, identifiers,
  1030. constants, operation signs, delimiters. The context free grammar
  1031. of TOYLAN can be described in the form of RIGAL program.
  1032. <xmp>
  1033. #PROGRAM
  1034. 'PROGRAM' $Id
  1035. (* #DECLARATION ';' *) (+ #STATEMENT + ';' ) ##
  1036. #DECLARATION ('INTEGER'!'BOOLEAN') (+ $Id + ',') ##
  1037. #STATEMENT ( #ASSIGNMENT ! #INPUT !
  1038. #OUTPUT ! #CONDITIONAL ) ##
  1039. #ASSIGNMENT $Id ':=' #EXPRESSION ##
  1040. #INPUT 'GET' '(' (+ $Id + ',') ')' ##
  1041. #OUTPUT 'PUT' '(' (+ #EXPRESSION + ',') ')' ##
  1042. #CONDITIONAL 'IF' #EXPRESSION 'THEN' (+ #STATEMENT + ';')
  1043. ['ELSE' (+ #STATEMENT + ';' )] 'FI' ##
  1044. #EXPRESSION #SUM [ '=' #SUM ] ##
  1045. #SUM #FACTOR (* '+' #FACTOR *) ##
  1046. #FACTOR #TERM (* '*' #TERM *) ##
  1047. #TERM $N ;; -- numeric constant
  1048. ('TRUE' ! 'FALSE' ) ;; -- Boolean constants
  1049. $Id;; -- variable
  1050. '(' #EXPRESSION ')' ##
  1051. </xmp>
  1052. Context conditions are the following:
  1053. <p> 1) all variables used in statements and expressions must be
  1054. declared,
  1055. <p> 2) one and the same variable name should not be declared
  1056. twice,
  1057. <p> 3) left and right parts of assignment statement must be of
  1058. the same type,
  1059. <p> 4) operands of input-output statements must be of the type
  1060. INTEGER.
  1061. <p> All variables of the type INTEGER have initial value 0, and
  1062. all variables of the type BOOLEAN have initial value FALSE.
  1063. <h3> 12.2 Intermediate Form of Program.
  1064. Abstract syntax tree</h3>
  1065. Special languages to represent intermediate results of
  1066. compilation are used in compiler building practice. For instance,
  1067. P-code for PASCAL compilers and language DIANA [8] for ADA.
  1068. <p> The result of the first phase of the TOYLAN compiler is a
  1069. tree. Let's call it abstract syntax tree. Along program
  1070. components it contains some semantic attributes, for instance,
  1071. types of expressions. One of the most significant attributes is
  1072. table of variables, obtained as a result of parsing of the TOYLAN
  1073. program declarations.
  1074. <p> The structure of abstract syntax tree of the TOYLAN program
  1075. is described by the following rules.
  1076. <xmp>
  1077. #S_PROGRAM
  1078. 'PROGRAM'::<. NAME : $Id,
  1079. DECLARATIONS : #S_DECLARATIONS ,
  1080. STATEMENTS : (.(* #S_STATEMENT *).) .> ##
  1081. #S_DECLARATIONS -- variables table
  1082. <* $Id : ( INTEGER ! BOOLEAN ) *> ##
  1083. #S_STATEMENT
  1084. ASSIGNMENT :: <. LEFT : $Id,
  1085. RIGHT : #S_EXPRESSION .> ;;
  1086. INPUT :: (. (* $Id *) .) ;;
  1087. OUTPUT :: (. (* #S_EXPRESSION *) .) ;;
  1088. CONDITIONAL :: <. COND : #S_EXPRESSION,
  1089. THEN : (.(* #S_STATEMENT *).),
  1090. [ ELSE : (.(* #S_STATEMENT *).)] .> ##
  1091. #S_EXPRESSION
  1092. COMPARE :: <. ARG1 : #S_EXPRESSION, ARG2 : #S_EXPRESSION,
  1093. TYPE : BOOLEAN .> ;;
  1094. ADD :: <. ARG1 : #S_EXPRESSION, ARG2 : #S_EXPRESSION,
  1095. TYPE : INTEGER .> ;;
  1096. MULT :: <. ARG1 : #S_EXPRESSION, ARG2 : #S_EXPRESSION,
  1097. TYPE : INTEGER .> ;;
  1098. <. VARIABLE : $Id , TYPE : ( INTEGER ! BOOLEAN ) .> ;;
  1099. <. CONSTANT : $N , TYPE : INTEGER .> ;;
  1100. <. CONSTANT : ( 0 ! 1) , TYPE : BOOLEAN .> ##
  1101. </xmp>
  1102. <h3> 12.3 Target Language BAL</h3>
  1103. The goal of the TOYLAN compiler is to obtain program text in
  1104. a low level language BAL. This language is a simplified model of
  1105. assembler languages. The memory of BAL-machine is divided into
  1106. separate words. Every word may contain an integer, besides, there
  1107. are work registers R0, R1, R2, ... of the word size each. Let us
  1108. suppose the number of registers to be unlimited, in order to
  1109. eliminate the problem of optimal register usage during generation
  1110. phase.
  1111. <p> Command of BAL ABC: DEFWORD N reserves a word in the memory
  1112. and imbeds integer N in it. We can refer to this word in other
  1113. commands by name ABC.
  1114. <p> Commands of BAL have two operands which are described by the
  1115. name of memory word, by the name of register or by the literal of
  1116. the type =NNN, where NNN is an integer. Commands can be marked by
  1117. labels.
  1118. <p> 1) MOV A1,A2 This command moves memory word A1 to memory word A2.
  1119. <p> 2) LOAD RI,A Loading of word A into register RI.
  1120. <p> 3) SAVE RI,A Unloading of the contents of register RI into memory
  1121. word A.
  1122. <p> 4) ADD RI,A or ADD RI,RJ The sum of operands is imbedded in RI.
  1123. <p> 5) MULT RI,A or MULT RI,RJ Multiplication of operands is
  1124. imbedded in RI.
  1125. <p> 6) COMPARE RI,A or COMPARE RI,RJ If operand values are equal,
  1126. it is 1 that is imbedded in RI, if they are not
  1127. equal, 0 is imbedded.
  1128. <p> 7) BRANCH RI,M If the value of RI is equal to 0, then transfer
  1129. to the command marked by label M takes place,
  1130. otherwise, to the next command.
  1131. <p> 8) JUMP M Unconditional transfer to the command marked by label M.
  1132. <p> 9) EOJ Completes the execution of the BAL program.
  1133. <p> 10) READ A Reads the integer from standard input device and
  1134. imbeds it in word A.
  1135. <p> 11) WRITE A or WRITE RI Outputs the integer from memory word or
  1136. from register to standard output device.
  1137. <p> 12) NOP An empty statement.
  1138. <h3> 12.4 Main Module of Compiler</h3>
  1139. The main program of the TOYLAN compiler contains calls of the
  1140. first and second compilation phases and file opening statements.
  1141. <xmp>
  1142. #TOYLAN_COMPILER
  1143. OPEN REP ' '; --message file is connected with the screen
  1144. $LEXEMS:=#CALL_PAS(35 'A.TOY');
  1145. -- a list of tokens is loaded from the file A.TOY by scanner
  1146. $S_TREE := #A_PROGRAM($LEXEMS);
  1147. -- 1st phase; result of parsing - abstract syntax tree - is
  1148. -- imbedded in the variable $S_TREE; during parsing messages
  1149. -- about discovered errors in file REP can be output.
  1150. IF $S_TREE -> OPEN GEN 'A.BAL'; -- if the tree is created,
  1151. -- then file is opened to output the generated BAL text
  1152. #G_PROGRAM($S_TREE) -- 2nd phase - code generation
  1153. ELSIF T -> REP << errors are discovered FI;
  1154. REP << end of compilation ##
  1155. </xmp>
  1156. The compilation listing that contains source text and error
  1157. messages is not envisaged in the TOYLAN compiler. Formation of
  1158. the listing can be a separate phase.
  1159. <h3> 12.5 Parsing Phase</h3>
  1160. The rule #A_PROGRAM carries out parsing of tokens list,
  1161. checks context conditions, generates error messages and builds
  1162. abstract syntax tree of TOYLAN program.
  1163. <p> Patterns of the rule #A_PROGRAM and of the rules subordinate
  1164. to it, actually, coincide with patterns of the rule #PROGRAM and
  1165. with the associated rules that describe context free grammar of
  1166. the TOYLAN language. Just operations to check context conditions,
  1167. to output error messages and to construct abstract syntax tree
  1168. are added.
  1169. <p> In our parser diagnostics is based on the following
  1170. principles. First of all, "panic" reaction to an error should be
  1171. avoided and several messages concerning one and the same error
  1172. should not be output (though, we can't manage it always),
  1173. secondly, error neutralization is transition to the analysis of
  1174. the next statement, i.e., skip of tokens until the nearest symbol
  1175. ';'.
  1176. <xmp>
  1177. #A_PROGRAM -- the rule is applied to the list of tokens
  1178. (. PROGRAM $Id
  1179. (* $DECL++:= #A_DECLARATION ';' *)
  1180. --formation of variables table
  1181. (+ $STATEMENTS !.:= #A_STATEMENT + ';' )
  1182. --formation of statements list
  1183. .) / RETURN 'PROGRAM' :: <. NAME : $Id,
  1184. DECLARATIONS : $DECL ,
  1185. STATEMENTS : $STATEMENTS .>/ ##
  1186. #A_DECLARATION $TYPE := ( INTEGER ! BOOLEAN )
  1187. (+ $Id /IF LAST #A_PROGRAM $DECL.$Id OR $REZ.$Id ->
  1188. REP << VARIABLE $Id DOUBLE DEFINED FI;
  1189. $REZ++:= <.$Id : $TYPE .>/ + ',' ) / RETURN $REZ / ##
  1190. #A_STATEMENT $REZ := ( #A_ASSIGNMENT ! #A_INPUT !
  1191. #A_OUTPUT ! #A_CONDITIONAL ) / RETURN $REZ / ;;
  1192. (* $A!.:=S'($$ <> ';' ) *) -- skip until nearest ';'
  1193. / REP << UNRECOGNIZED STATEMENT $A /
  1194. ##
  1195. #A_ASSIGNMENT $Id ':='/ $LPType := LAST #A_PROGRAM $DECL .$Id;
  1196. IF NOT $LPType -> REP << VARIABLE $Id ' IS NOT DEFINED ' FI /
  1197. $E:= #A_EXPRESSION
  1198. /IF $LPType <> $E . TYPE ->
  1199. REP<< 'LEFT AND RIGHT SIDE TYPES ARE DIFFERENT '
  1200. 'IN ASSIGNMENT STATEMENT ' FI;
  1201. RETURN ASSIGNMENT::<. LEFT: $Id, RIGHT: $E .> /
  1202. ONFAIL IF $LPType -> REP<< 'WRONG EXPRESSION IN ASSIGNMENT' FI ##
  1203. #A_INPUT GET '('
  1204. (+ $E !.:= $Id /IF LAST #A_PROGRAM $DECL.$Id <> INTEGER ->
  1205. REP << $Id 'IN STATEMENT GET IS NOT OF THE TYPE INTEGER'
  1206. FI / + ',' ) ')' / RETURN INPUT :: $E / ##
  1207. #A_OUTPUT PUT '(' (+ $C := #A_EXPRESSION / $E !.:= $C;
  1208. IF $C . TYPE <> INTEGER ->
  1209. REP << OPERAND OF PUT STATEMENT IS NOT OF THE TYPE INTEGER
  1210. FI / + ',' ) ')'/ RETURN OUTPUT :: $E / ##
  1211. #A_CONDITIONAL 'IF' $BE := #A_EXPRESSION
  1212. /IF $BE . TYPE <> BOOLEAN ->
  1213. REP<< CONDITION IS NOT OF BOOLEAN TYPE FI /
  1214. 'THEN' (+ $P1 !.:= #A_STATEMENT + ';' )
  1215. [ 'ELSE' (+ $P2 !.:= #A_STATEMENT + ';' ) ] 'FI'
  1216. / RETURN CONDITIONAL :: <. COND : $BE , THEN : $P1 ,
  1217. ELSE : $P2 .> / ##
  1218. #A_EXPRESSION $A := #A_SUM [ '=' $B := #A_SUM
  1219. / $A := COMPARE::<. ARG1 : $A, ARG2 : $B, TYPE : BOOLEAN.>/ ]
  1220. / RETURN $A / ##
  1221. #A_SUM $A := #A_FACTOR (* '+' $B := #A_FACTOR
  1222. / $A := ADD::<. ARG1: $A, ARG2: $B, TYPE: INTEGER .>/ *)
  1223. / RETURN $A / ##
  1224. #A_FACTOR $A := #A_TERM (* '*' $B := #A_TERM
  1225. /$A := MULT::<. ARG1: $A, ARG2: $B, TYPE: INTEGER .>/ *)
  1226. / RETURN $A / ##
  1227. #A_TERM
  1228. $N / RETURN <. CONSTANT : $N , TYPE : INTEGER .>/;;
  1229. ( ( TRUE / $K :=1/ ) ! ( FALSE / $K :=0 / ) )
  1230. /RETURN <. CONSTANT: $K, TYPE: BOOLEAN .>/ ;;
  1231. $Id / $X:= LAST #A_PROGRAM $DECL.$Id;
  1232. IF NOT $X -> REP << VARIABLE $Id IS NOT DECLARED
  1233. ELSIF T -> RETURN <. VARIABLE: $Id, TYPE: $X .> FI / ;;
  1234. '(' $E := #A_EXPRESSION ')' / RETURN $E / ##
  1235. </xmp>
  1236. <h3> 12.6 Code Generation Phase</h3>
  1237. Code generation is performed when traversing abstract syntax
  1238. tree.
  1239. <p> To avoid possible conflicts between variable names in the
  1240. TOYLAN program and register names (of the type RNNN) and labels
  1241. (of the type LNNN) in the object program, variable names are
  1242. substituted by standard names of the type VARNNN.
  1243. <xmp>
  1244. #G_PROGRAM / $LABEL := 0 / --global variable $LABEL serves
  1245. --to generate unique labels.
  1246. PROGRAM::<.DECLARATIONS: $TAB := #TABLE_OF_NUMBERS,
  1247. --creation of the table of unique variable numbers
  1248. STATEMENTS: (.(* #G_STATEMENT *).) / GEN << 'EOJ' /,
  1249. DECLARATIONS : #G_DECLARATIONS .> ##
  1250. #TABLE_OF_NUMBERS <* $Id: $TYPE /$N :=$N+1; $T++:=<. $Id: $N.>/ *>
  1251. /RETURN $T/ ##
  1252. #G_STATEMENT ( #G_ASSIGNMENT ! #G_INPUT !
  1253. #G_OUTPUT ! #G_CONDITIONAL ) ##
  1254. #G_ASSIGNMENT ASSIGNMENT::<. LEFT: $Id := #NAME,
  1255. RIGHT :( ( <. VARIABLE: $Id1:=#NAME .>
  1256. /GEN << MOV @ $Id1 ',' $Id / ) !
  1257. ( <. CONSTANT : $N .> /GEN << MOV @ '=' $N ',' $Id /) !
  1258. ( $NREG := #G_EXPRESSION
  1259. /GEN << 'SAVE' @ 'R' $NREG ',' $Id / ) ) .> ##
  1260. #G_INPUT INPUT::(. (* $Id := #NAME /GEN << READ $Id / *) .) ##
  1261. #G_OUTPUT OUTPUT :: (. (*
  1262. ( ( <. VARIABLE : $Id := #NAME .> /GEN << WRITE $Id / ) !
  1263. ( <. CONSTANT : $N .> /GEN << WRITE @ '=' $N / ) !
  1264. ( $NREG := #G_EXPRESSION /GEN << WRITE @ 'R' $NREG /) )
  1265. *) .) ##
  1266. #G_CONDITIONAL CONDITIONAL ::
  1267. <. COND : $NREG := #G_EXPRESSION
  1268. / $LABEL1 :=#NEW_LABEL(); $LABEL2 :=#NEW_LABEL() /,
  1269. THEN : / GEN << BRANCH @ 'R' $NREG ',L' $LABEL1 /
  1270. (. (* #G_STATEMENT *) .)
  1271. / IF $.ELSE -> GEN << JUMP @ 'L' $LABEL2 FI;
  1272. GEN << @ 'L' $LABEL1 ': NOP' / ,
  1273. [ ELSE : (. (* #G_STATEMENT *) .)
  1274. / GEN << @ 'L' $LABEL2 ': NOP' / ] .> ##
  1275. #G_EXPRESSION --returns the number of the register containing
  1276. --result of the evaluation of expression
  1277. $EXPR
  1278. / $NREG := 0 / -- number of the first accessible register
  1279. /RETURN #G_EXPR($EXPR)/
  1280. ##
  1281. #G_EXPR ( <. VARIABLE: $ID :=#NAME .> !
  1282. <. CONSTANT: $N / $ID := #IMPLODE('=' $N)/ .>)
  1283. / $REG := COPY( LAST #G_EXPRESSION $NREG ) ;
  1284. GEN << 'LOAD' @ 'R' $REG ',' $ID ;
  1285. LAST #G_EXPRESSION $NREG + := 1; RETURN $REG / ;;
  1286. $OP::<. ARG1 : $R1 := #G_EXPR, ARG2 : $R2 := #G_EXPR .>
  1287. / GEN << $OP @ 'R' $R1 ',R' $R2 ; RETURN $R1 / ##
  1288. #G_DECLARATIONS
  1289. <* $ID: $TYPE /$ID1 := #NAME($ID); GEN<< $ID1 ':' DEFWORD 0 /*> ##
  1290. #NEW_LABEL --auxiliary rule
  1291. /LAST #G_PROGRAM $LABEL+:=1;
  1292. RETURN COPY (LAST #G_PROGRAM $LABEL )/ ##
  1293. #NAME $ID --returns standard name of the variable $ID in $TAB
  1294. / RETURN #IMPLODE( VAR LAST #G_PROGRAM $TAB.$ID)/ ##
  1295. </xmp>
  1296. <a name="13">
  1297. <h2> 13. Conclusions and Future Work </h2>
  1298. As it was demonstrated above, RIGAL supports syntax-oriented
  1299. style of compiler design. Programs written in RIGAL are
  1300. well-structured and it is easy to read and debug them.
  1301. <p> Our experience [13] proves that the optimizing RIGAL compiler
  1302. in VAX/VMS environment makes it possible to implement production
  1303. quality compilers for high level languages.
  1304. <p> RIGAL can be considered as yet another language prototyping
  1305. tool in the sense of [14], because it allows the designer to
  1306. develop an experimental translator in short period of time.
  1307. <p> Besides interpreter for debugging purposes and optimizing
  1308. compiler RIGAL support system includes a cross-referencer, which
  1309. helps to avoid misuse of global variables.
  1310. <p> In order to improve static and dynamic type checking,
  1311. variable type descriptions in the form of formal comments would
  1312. be added to the language.
  1313. <p> Taking in account that control structures of RIGAL program
  1314. are very close to input data structures, it seems promising to
  1315. develop automatic and semiautomatic methods for test example
  1316. generation for the given RIGAL program.
  1317. <a name="r">
  1318. <h2>References</h2>
  1319. <p> [1] A.Aho, J.Ullman. The theory of parsing, translation and
  1320. compiling// Prentice-Hall, Inc. Englewood Cliffs,N.J. 1972. -
  1321. vol.1,2.
  1322. <p> [2] S.C.Johnson. YACC - Yet Another Compiler Compiler // Bell
  1323. Laboratories, Murray Hill,N.J., 1978, A technical manual.
  1324. <p> [3] C.H.Koster. Using the CDL Compiler Compiler// Lecture Notes
  1325. in Computer Science , Vol.21, Springer-Verlag, Berlin, 1977.
  1326. <p> [4] I.R.Agamirzyan. Compiler Design Technological Support System SHAG. // Space
  1327. mechanics algorithms, Leningrad, vol. 79,1985, pp. 1-53.,(in Russian)
  1328. <p> [5] D.E.Knuth. Semantics of context-free languages// Mathematical
  1329. Systems Theory, 2, 2, 1968, pp.127-146.
  1330. <p> [6] V.A.Serebryakov. Methods of Attribute Translation.// In:
  1331. Programming Languages, Moscow, "Nauka", 1985, pp. 47-79,(in Russian).
  1332. <p> [7] A.O.Vooglaid, M.V. Lepp, D.B.Lijb. Input Languages of the
  1333. ELMA System. // Proceedings of the Tallin Polytechnical Institute,
  1334. (in Russian).
  1335. <p> [8] The intermediate language DIANA : Design and Implementation //Lecture
  1336. Notes in Computer Science, Vol.180, Springer-Verlag,
  1337. Berlin, 1984.
  1338. <p> [9] R.Vilhelm. Presentation of the compiler generation system MUG2:
  1339. Examples, global flow analysis and optimization// Le point
  1340. sur la compilation, INRIA, 1978, à.307-336.
  1341. <p> [10] Basic REFAL and its implementation on computers.// CNIPIASS,
  1342. Moscow, 1977, (in Russian).
  1343. <p> [11] P.Lucas. Formal definition of programming languages and
  1344. systems // IFIP Congress, 1971.
  1345. <p> [12] M.Ganapatti, C.N.Fisher, J.L.Hennessy. Retargetable compiler
  1346. code generation// ACM Computing Survays, 14(4), 1982.
  1347. <p> [13] J.Barzdin, A.Kalnins, M.Auguston, SDL tools for rapid
  1348. prototyping and testing.// in SDL'89 : The language at work,
  1349. ed. O.Faergemand and M.M.Marques, North-Holland, 1989,
  1350. pp.127-133.
  1351. <p> [14] R.Herndon, V.Berzins, The realizable benefits of a language
  1352. prototyping language.// IEEE Transactions on Software
  1353. Engineering , vol.14, No 6, June 1988, pp.803-809