LSV.Mod.txt 10.0 KB

123456789101112131415161718192021222324252627282930313233343536373839404142434445464748495051525354555657585960616263646566676869707172737475767778798081828384858687888990919293949596979899100101102103104105106107108109110111112113114115116117118119120121122123124125126127128129130131132133134135136137138139140141142143144145146147148149150151152153154155156157158159160161162163164165166167168169170171172173174175176177178179180181182183184185186187188189190191192193194195196197198199200201202203204205206207208209210211212213214215216217218219220221222223224225226227228229230231232233234235236237238
  1. MODULE LSV; (*Lola System: display Verilog; generate txt-File; NW 31.8.2015*)
  2. IMPORT Files, Texts, Oberon, LSB;
  3. VAR W: Texts.Writer;
  4. nofgen: INTEGER;;
  5. Constructor: PROCEDURE (VAR x: LSB.Item); (*to avoid forward reference*)
  6. F: Files.File; R: Files.Rider;
  7. C: ARRAY 64, 6 OF CHAR;
  8. PROCEDURE Write(ch: CHAR);
  9. BEGIN Files.Write(R, ch)
  10. END Write;
  11. PROCEDURE WriteLn;
  12. BEGIN Files.Write(R, 0DX); Files.Write(R, 0AX)
  13. END WriteLn;
  14. PROCEDURE WriteInt(x: LONGINT); (* x >= 0 *)
  15. VAR i: INTEGER; d: ARRAY 14 OF LONGINT;
  16. BEGIN i := 0;
  17. IF x < 0 THEN Files.Write(R, "-"); x := -x END ;
  18. REPEAT d[i] := x MOD 10; x := x DIV 10; INC(i) UNTIL x = 0;
  19. REPEAT DEC(i); Files.Write(R, CHR(d[i] + 30H)) UNTIL i = 0
  20. END WriteInt;
  21. PROCEDURE WriteHex(x: LONGINT); (*x >= 0*)
  22. VAR i: INTEGER; d: ARRAY 8 OF LONGINT;
  23. BEGIN i := 0;
  24. REPEAT d[i] := x MOD 10H; x := x DIV 10H; INC(i) UNTIL (x = 0) OR (i = 8);
  25. REPEAT DEC(i);
  26. IF d[i] >= 10 THEN Files.Write(R, CHR(d[i] + 37H)) ELSE Files.Write(R, CHR(d[i] + 30H)) END
  27. UNTIL i = 0
  28. END WriteHex;
  29. PROCEDURE WriteString(s: ARRAY OF CHAR);
  30. VAR i: INTEGER;
  31. BEGIN i := 0;
  32. WHILE s[i] # 0X DO Files.Write(R, s[i]); INC(i) END
  33. END WriteString;
  34. (* ------------------------------- *)
  35. PROCEDURE Type(typ: LSB.Type);
  36. VAR obj: LSB.Object;
  37. BEGIN
  38. IF typ IS LSB.ArrayType THEN
  39. IF typ(LSB.ArrayType).eltyp # LSB.bitType THEN
  40. Write("["); WriteInt(typ.len - 1); WriteString(":0]"); Type(typ(LSB.ArrayType).eltyp)
  41. END
  42. ELSIF typ IS LSB.UnitType THEN (* obj := typ(LSB.UnitType).firstobj; *)
  43. END
  44. END Type;
  45. PROCEDURE BitArrLen(typ: LSB.Type);
  46. VAR eltyp: LSB.Type;
  47. BEGIN
  48. IF typ IS LSB.ArrayType THEN
  49. eltyp := typ(LSB.ArrayType).eltyp;
  50. WHILE eltyp IS LSB.ArrayType DO typ := eltyp; eltyp := typ(LSB.ArrayType).eltyp END ;
  51. IF eltyp = LSB.bitType THEN
  52. Write("["); WriteInt(typ.len - 1);WriteString(":0] ")
  53. END
  54. END
  55. END BitArrLen;
  56. PROCEDURE Expression(x: LSB.Item);
  57. VAR z: LSB.Item;
  58. BEGIN
  59. IF x # NIL THEN
  60. IF x IS LSB.Object THEN WriteString(x(LSB.Object).name)
  61. ELSIF x.tag = LSB.cons THEN
  62. Write("{"); Constructor(x); Write("}")
  63. ELSE
  64. IF x.tag = LSB.repl THEN
  65. Write("{"); WriteInt(x.b.val); Write("{"); Expression(x.a);
  66. Write("}"); Write("}")
  67. ELSE
  68. IF (x.tag >= LSB.and) & (x.tag <= LSB.gtr) THEN Write("(") END ;
  69. Expression(x.a);
  70. IF x.tag = LSB.sel THEN Write("["); Expression(x.b); Write("]")
  71. ELSIF x.tag = LSB.lit THEN
  72. IF x.size # 0 THEN WriteInt(x.size); Write("'"); Write("h"); WriteHex(x.val)
  73. ELSE WriteInt(x.val)
  74. END
  75. ELSE WriteString(C[x.tag]); Expression(x.b)
  76. END ;
  77. IF (x.tag >= LSB.and) & (x.tag <= LSB.gtr) THEN Write(")") END
  78. END
  79. END
  80. END
  81. END Expression;
  82. PROCEDURE Elem(VAR x: LSB.Item);
  83. BEGIN
  84. IF x.tag = LSB.repl THEN
  85. Write("{"); WriteInt(x.b.val); Write("{"); Expression(x.a); WriteString("}}")
  86. ELSE Expression(x)
  87. END
  88. END Elem;
  89. PROCEDURE Constructor0(VAR x: LSB.Item);
  90. BEGIN
  91. IF x.tag = LSB.cons THEN Constructor(x.a); WriteString(", "); Elem(x.b) ELSE Elem(x) END
  92. END Constructor0;
  93. PROCEDURE Declaration(obj: LSB.Object);
  94. VAR apar: LSB.Item; typ: LSB.Type;
  95. BEGIN typ := obj.type;
  96. IF obj.type IS LSB.UnitType THEN WriteString("unit ") ELSE Type(obj.type) END ;
  97. IF obj.tag = LSB.var THEN
  98. IF obj.type IS LSB.UnitType THEN
  99. apar := obj.a; WriteLn; Write("[");
  100. WHILE apar # NIL DO Expression(apar.b); apar := apar.a END ;
  101. Write("]")
  102. END
  103. ELSIF obj.tag = LSB.const THEN WriteString(" = "); WriteInt(obj.val)
  104. END
  105. END Declaration;
  106. PROCEDURE ObjList0(obj: LSB.Object); (*declarations*)
  107. VAR obj1: LSB.Object; param: BOOLEAN;
  108. BEGIN param := TRUE;
  109. WHILE obj # LSB.root DO
  110. IF (obj.tag = LSB.var) & ~(obj.type IS LSB.UnitType) THEN
  111. IF obj.val <= 1 THEN WriteString("reg ")
  112. ELSIF obj.val = 2 THEN WriteString("wire ")
  113. ELSIF obj.val = 3 THEN WriteString("output ")
  114. ELSIF obj.val = 4 THEN WriteString("output reg ")
  115. ELSIF obj.val = 5 THEN WriteString("inout ")
  116. ELSIF obj.val = 6 THEN WriteString("input ")
  117. ELSE WriteString("??? ")
  118. END ;
  119. BitArrLen(obj.type); WriteString(obj.name);
  120. obj1 := obj.next;
  121. WHILE (obj1 # LSB.top) & (obj1.type = obj.type) & (obj1.val = obj.val) DO
  122. WriteString(", "); obj := obj1; WriteString(obj.name); obj1 := obj.next
  123. END ;
  124. IF param & (obj.val >= 3) & (obj1.val < 3) THEN (*end param list*) param := FALSE; Write(")")
  125. END ;
  126. IF (obj.type # LSB.bitType) & (obj.type(LSB.ArrayType).eltyp # LSB.bitType) THEN Type(obj.type) END ;
  127. IF param THEN Write(",") ELSE Write(";") END ;
  128. WriteLn
  129. ELSIF obj.tag = LSB.const THEN
  130. END ;
  131. obj := obj.next
  132. END
  133. END ObjList0;
  134. PROCEDURE ActParam(VAR x: LSB.Item; fpar: LSB.Object);
  135. BEGIN Write("."); WriteString(fpar.name); Write("("); Expression(x); Write(")")
  136. END ActParam;
  137. PROCEDURE ObjList1(obj: LSB.Object); (*assignments to variables*)
  138. VAR apar, x: LSB.Item; fpar: LSB.Object; size: LONGINT;
  139. BEGIN
  140. WHILE obj # LSB.root DO
  141. IF (obj.tag = LSB.var) OR (obj.tag = LSB.const) THEN
  142. IF obj.type IS LSB.UnitType THEN
  143. WriteString(obj.type.typobj.name); Write(" "); WriteString(obj.name);
  144. apar := obj.b; fpar := obj.type(LSB.UnitType).firstobj;
  145. Write("("); ActParam(apar.b, fpar); apar := apar.a; fpar := fpar.next; (*actual param list*)
  146. WHILE apar # NIL DO WriteString(", "); ActParam(apar.b, fpar); apar := apar.a; fpar := fpar.next END ;
  147. Write(")"); Write(";"); WriteLn
  148. ELSIF (obj.b # NIL) & (obj.val = 5) THEN (*tri-state*)
  149. size := obj.type.size; x := obj.b;
  150. IF x.tag = LSB.ts THEN
  151. IF obj.type = LSB.bitType THEN
  152. WriteString("IOBUF block"); INC(nofgen); WriteInt(nofgen); WriteString(" (.IO("); WriteString(obj.name);
  153. WriteString("), .O("); WriteString(x.a(LSB.Object).name); WriteString("), .I("); x := x.b;
  154. IF x.a.type = LSB.bitType THEN Expression(x.a) ELSE WriteString(x.a(LSB.Object).name) END ;
  155. WriteString("), .T(");
  156. IF x.b.type = LSB.bitType THEN Expression(x.b) ELSE WriteString(x.b(LSB.Object).name) END ;
  157. WriteString("));")
  158. ELSE (*array type*)
  159. IF nofgen = 0 THEN WriteString("genvar i;"); WriteLn END ;
  160. INC(nofgen); WriteString("generate"); WriteLn;
  161. WriteString("for (i = 0; i < "); WriteInt(size); WriteString("; i = i+1) begin : bufblock"); WriteInt(nofgen); WriteLn;
  162. WriteString("IOBUF block (.IO("); WriteString(obj.name);
  163. WriteString("[i]), .O("); WriteString(x.a(LSB.Object).name); WriteString("[i]), .I("); x := x.b;
  164. WriteString(x.a(LSB.Object).name); WriteString("[i]), .T(");
  165. IF x.b.type = LSB.bitType THEN Expression(x.b) ELSE WriteString(x.b(LSB.Object).name); WriteString("[i]") END ;
  166. WriteString("));"); WriteLn; WriteString("end"); WriteLn; WriteString("endgenerate")
  167. END ;
  168. WriteLn
  169. END
  170. ELSIF (obj.b # NIL) & (obj.val >= 2) THEN
  171. WriteString("assign "); WriteString(obj.name);
  172. IF (obj.a # NIL) THEN Write("["); Expression(obj.a); Write("]") END ;
  173. WriteString(" = "); Expression(obj.b); Write(";"); WriteLn
  174. END
  175. ELSIF obj.tag = LSB.typ THEN (*instantiation; actual parameters*)
  176. END ;
  177. obj := obj.next
  178. END
  179. END ObjList1;
  180. PROCEDURE ObjList2(obj: LSB.Object); (*assignments to registers*)
  181. VAR apar: LSB.Item; kind: LONGINT; clk: LSB.Item;
  182. BEGIN
  183. WHILE obj # LSB.root DO
  184. IF (obj.tag = LSB.var) & ~(obj.type IS LSB.UnitType) & (obj.val < 2) THEN
  185. WriteString("always @ (posedge "); kind := obj.val;
  186. IF kind = 0 THEN Expression(obj.a)
  187. ELSE (*kind = 1*) WriteString("clk")
  188. END ;
  189. WriteString(") begin ");
  190. REPEAT WriteString(obj.name);
  191. IF (kind = 1) & (obj.a # NIL) THEN Write("["); Expression(obj.a); Write("]") END ;
  192. WriteString(" <= "); Expression(obj.b); Write(";"); WriteLn; obj := obj.next
  193. UNTIL (obj = LSB.top) OR (obj.val # kind);
  194. WriteString("end"); WriteLn
  195. ELSE obj := obj.next
  196. END
  197. END
  198. END ObjList2;
  199. PROCEDURE List*;
  200. VAR S: Texts.Scanner;
  201. BEGIN Texts.OpenScanner(S, Oberon.Par.text, Oberon.Par.pos); Texts.Scan(S);
  202. IF (S.class = Texts.Name) OR (S.class = Texts.String) THEN
  203. Texts.WriteString(W, LSB.modname); Texts.WriteString(W, " translating to "); Texts.WriteString(W, S.s);
  204. F := Files.New(S.s); Files.Set(R, F, 0);
  205. WriteString("`timescale 1ns / 1 ps"); WriteLn; nofgen := 0;
  206. WriteString("module "); WriteString(LSB.modname); WriteString("( // translated from Lola"); WriteLn;
  207. ObjList0(LSB.top); ObjList1(LSB.top); ObjList2(LSB.top);
  208. WriteString("endmodule"); WriteLn;
  209. Files.Register(F); Texts.WriteString(W, " done"); Texts.WriteLn(W); Texts.Append(Oberon.Log, W.buf)
  210. END
  211. END List;
  212. BEGIN Texts.OpenWriter(W); Constructor := Constructor0;
  213. C[LSB.const] := "CONST"; C[LSB.typ] := "TYPE"; C[LSB.var] := "VAR";
  214. C[LSB.lit] := "LIT"; C[LSB.sel] := "SEL"; C[LSB.range] := ":"; C[LSB.cons] := ",";
  215. C[LSB.or] := " | "; C[LSB.xor] := " ^ "; C[LSB.and] := " & "; C[LSB.not] := "~";
  216. C[LSB.add] := " + "; C[LSB.sub] := " - "; C[LSB.mul] := " * "; C[LSB.div] := " / ";
  217. C[LSB.eql] := " == "; C[LSB.neq] := " != "; C[LSB.lss] := " < "; C[LSB.geq] := " >= "; C[LSB.leq] := " <= "; C[LSB.gtr] := " > ";
  218. C[LSB.then] := " ? "; C[LSB.else] := " : "; C[LSB.ts] := "TS"; C[LSB.next] := "--"
  219. END LSV.