bootgram.y 50 KB

1234567891011121314151617181920212223242526272829303132333435363738394041424344454647484950515253545556575859606162636465666768697071727374757677787980818283848586878889909192939495969798991001011021031041051061071081091101111121131141151161171181191201211221231241251261271281291301311321331341351361371381391401411421431441451461471481491501511521531541551561571581591601611621631641651661671681691701711721731741751761771781791801811821831841851861871881891901911921931941951961971981992002012022032042052062072082092102112122132142152162172182192202212222232242252262272282292302312322332342352362372382392402412422432442452462472482492502512522532542552562572582592602612622632642652662672682692702712722732742752762772782792802812822832842852862872882892902912922932942952962972982993003013023033043053063073083093103113123133143153163173183193203213223233243253263273283293303313323333343353363373383393403413423433443453463473483493503513523533543553563573583593603613623633643653663673683693703713723733743753763773783793803813823833843853863873883893903913923933943953963973983994004014024034044054064074084094104114124134144154164174184194204214224234244254264274284294304314324334344354364374384394404414424434444454464474484494504514524534544554564574584594604614624634644654664674684694704714724734744754764774784794804814824834844854864874884894904914924934944954964974984995005015025035045055065075085095105115125135145155165175185195205215225235245255265275285295305315325335345355365375385395405415425435445455465475485495505515525535545555565575585595605615625635645655665675685695705715725735745755765775785795805815825835845855865875885895905915925935945955965975985996006016026036046056066076086096106116126136146156166176186196206216226236246256266276286296306316326336346356366376386396406416426436446456466476486496506516526536546556566576586596606616626636646656666676686696706716726736746756766776786796806816826836846856866876886896906916926936946956966976986997007017027037047057067077087097107117127137147157167177187197207217227237247257267277287297307317327337347357367377387397407417427437447457467477487497507517527537547557567577587597607617627637647657667677687697707717727737747757767777787797807817827837847857867877887897907917927937947957967977987998008018028038048058068078088098108118128138148158168178188198208218228238248258268278288298308318328338348358368378388398408418428438448458468478488498508518528538548558568578588598608618628638648658668678688698708718728738748758768778788798808818828838848858868878888898908918928938948958968978988999009019029039049059069079089099109119129139149159169179189199209219229239249259269279289299309319329339349359369379389399409419429439449459469479489499509519529539549559569579589599609619629639649659669679689699709719729739749759769779789799809819829839849859869879889899909919929939949959969979989991000100110021003100410051006100710081009101010111012101310141015101610171018101910201021102210231024102510261027102810291030103110321033103410351036103710381039104010411042104310441045104610471048104910501051105210531054105510561057105810591060106110621063106410651066106710681069107010711072107310741075107610771078107910801081108210831084108510861087108810891090109110921093109410951096109710981099110011011102110311041105110611071108110911101111111211131114111511161117111811191120112111221123112411251126112711281129113011311132113311341135113611371138113911401141114211431144114511461147114811491150115111521153115411551156115711581159116011611162116311641165116611671168116911701171117211731174117511761177117811791180118111821183118411851186118711881189119011911192119311941195119611971198119912001201120212031204120512061207120812091210121112121213121412151216121712181219122012211222122312241225122612271228122912301231123212331234123512361237123812391240124112421243124412451246124712481249125012511252125312541255125612571258125912601261126212631264126512661267126812691270127112721273127412751276127712781279128012811282128312841285128612871288128912901291129212931294129512961297129812991300130113021303130413051306130713081309131013111312131313141315131613171318131913201321132213231324132513261327132813291330133113321333133413351336133713381339134013411342134313441345134613471348134913501351135213531354135513561357135813591360136113621363136413651366136713681369137013711372137313741375137613771378137913801381138213831384138513861387138813891390139113921393139413951396139713981399140014011402140314041405140614071408140914101411141214131414141514161417141814191420142114221423142414251426142714281429143014311432143314341435143614371438143914401441144214431444144514461447144814491450145114521453145414551456145714581459146014611462146314641465146614671468146914701471147214731474147514761477147814791480148114821483148414851486148714881489149014911492149314941495149614971498149915001501150215031504150515061507150815091510151115121513151415151516151715181519152015211522152315241525152615271528152915301531153215331534153515361537153815391540154115421543154415451546154715481549155015511552155315541555155615571558155915601561156215631564156515661567156815691570157115721573157415751576157715781579158015811582158315841585158615871588158915901591159215931594159515961597159815991600160116021603160416051606160716081609161016111612161316141615161616171618161916201621162216231624162516261627162816291630163116321633163416351636163716381639164016411642164316441645164616471648164916501651165216531654165516561657165816591660166116621663166416651666166716681669167016711672167316741675167616771678167916801681168216831684168516861687168816891690169116921693169416951696169716981699170017011702170317041705170617071708170917101711171217131714171517161717171817191720172117221723172417251726172717281729173017311732173317341735173617371738173917401741174217431744174517461747174817491750175117521753175417551756175717581759176017611762176317641765176617671768176917701771177217731774177517761777177817791780178117821783178417851786178717881789179017911792179317941795179617971798179918001801180218031804180518061807180818091810181118121813181418151816181718181819182018211822182318241825182618271828182918301831183218331834183518361837183818391840184118421843184418451846184718481849185018511852185318541855185618571858185918601861186218631864186518661867186818691870187118721873187418751876187718781879188018811882188318841885188618871888188918901891189218931894189518961897189818991900190119021903190419051906190719081909191019111912191319141915191619171918191919201921192219231924192519261927192819291930193119321933193419351936193719381939194019411942194319441945194619471948194919501951195219531954195519561957195819591960196119621963196419651966196719681969197019711972197319741975197619771978197919801981198219831984198519861987198819891990199119921993199419951996199719981999200020012002200320042005200620072008200920102011201220132014201520162017201820192020202120222023202420252026202720282029203020312032203320342035203620372038203920402041204220432044204520462047204820492050205120522053205420552056205720582059206020612062206320642065206620672068206920702071207220732074207520762077207820792080208120822083208420852086208720882089209020912092209320942095209620972098209921002101210221032104210521062107210821092110211121122113211421152116211721182119212021212122212321242125212621272128212921302131213221332134213521362137213821392140214121422143214421452146214721482149215021512152215321542155215621572158215921602161216221632164216521662167216821692170217121722173217421752176217721782179218021812182218321842185218621872188218921902191219221932194219521962197219821992200220122022203220422052206220722082209221022112212221322142215221622172218221922202221222222232224222522262227222822292230223122322233223422352236223722382239224022412242224322442245224622472248224922502251225222532254225522562257225822592260226122622263226422652266226722682269227022712272227322742275227622772278227922802281228222832284228522862287228822892290229122922293229422952296229722982299230023012302230323042305230623072308230923102311231223132314231523162317231823192320232123222323232423252326232723282329233023312332233323342335233623372338233923402341
  1. %{
  2. #ifndef NORCSID
  3. static char rcsid[]="$Header$";
  4. #endif
  5. /*
  6. * (c) copyright 1983 by the Vrije Universiteit, Amsterdam, The Netherlands.
  7. *
  8. * This product is part of the Amsterdam Compiler Kit.
  9. *
  10. * Permission to use, sell, duplicate or disclose this software must be
  11. * obtained in writing. Requests for such permissions may be sent to
  12. *
  13. * Dr. Andrew S. Tanenbaum
  14. * Wiskundig Seminarium
  15. * Vrije Universiteit
  16. * Postbox 7161
  17. * 1007 MC Amsterdam
  18. * The Netherlands
  19. *
  20. * Author: Hans van Staveren
  21. */
  22. #ifdef vax | vax2 | vax4
  23. #define BIG
  24. #endif
  25. #ifdef BIG
  26. #define BORS(x,y) x
  27. #else
  28. #define BORS(x,y) y
  29. #endif
  30. /* Tunable constants */
  31. #define MAXALLREG 5 /* Maximum number of allocates per rule */
  32. #define MAXREGS BORS(36,32) /* Total number of registers */
  33. #define MAXREGVARS 8 /* Maximum regvars per type */
  34. #define MAXPROPS 16 /* Total number of register properties */
  35. #define MAXTOKENS BORS(75,32) /* Different kind of tokens */
  36. #define MAXSETS BORS(100,80) /* Number of tokenexpressions definable */
  37. #define MAXEMPATLEN 25 /* Maximum length of EM-pattern/replacement */
  38. #define TOKENSIZE 5 /* Maximum number of fields in token struct */
  39. #define MAXINSTANCE BORS(250,120) /* Maximum number of different tokeninstances */
  40. #define MAXSTRINGS BORS(800,400)/* Maximum number of different codestrings */
  41. #define MAXPATTERN BORS(8000,6000) /* Maximum number of bytes in pattern[] */
  42. #define MAXNODES BORS(450,400) /* Maximum number of expression nodes */
  43. #define MAXMEMBERS 2 /* Maximum number of subregisters per reg */
  44. #define NMOVES BORS(50,30) /* Maximum number of move definitions */
  45. #define MAXC1 20 /* Maximum of coercions type 1 */
  46. #define MAXC2 20 /* Maximum of coercions type 2 */
  47. #define MAXC3 20 /* Maximum of coercions type 3 */
  48. #define MAXSPLIT 4 /* Maximum degree of split */
  49. #define MAXNSTR 40 /* Maximum consecutive strings in coderule */
  50. char *hname="tables.h";
  51. char *cname="tables.c";
  52. char *iname=0; /* stdin */
  53. /* Derived constants */
  54. #define SETSIZE ((MAXREGS+1+MAXTOKENS+15)>>4)
  55. #define PROPSETSIZE ((MAXPROPS+15)>>4)
  56. #define BMASK 0377
  57. #define BSHIFT 8
  58. #define TRUE 1
  59. #define FALSE 0
  60. #define MAXPATLEN 7 /* Maximum length of tokenpatterns */
  61. typedef char byte;
  62. typedef char * string;
  63. char *malloc(),*myalloc();
  64. #include <stdio.h>
  65. #include <assert.h>
  66. #include <ctype.h>
  67. #include <em_spec.h>
  68. #include <em_flag.h>
  69. #include <em_reg.h>
  70. #include <cg_pattern.h>
  71. typedef struct list1str {
  72. struct list1str *l1next;
  73. string l1name;
  74. } *list1;
  75. typedef struct list2str {
  76. struct list2str *l2next;
  77. list1 l2list;
  78. } *list2;
  79. typedef struct list3str {
  80. struct list3str *l3next;
  81. list2 l3list;
  82. } *list3;
  83. typedef struct reginfo {
  84. string rname;
  85. string rrepr;
  86. int rsize;
  87. int rmembers[MAXMEMBERS];
  88. int rregvar;
  89. short rprop[PROPSETSIZE];
  90. } *reginfo;
  91. typedef struct tokeninfo {
  92. string t_name;
  93. list2 t_struct;
  94. struct {
  95. int t_type;
  96. string t_sname;
  97. } t_fields[TOKENSIZE-1];
  98. int t_size;
  99. cost_t t_cost;
  100. int t_format;
  101. } token_t,*token_p;
  102. typedef struct ident {
  103. struct ident *i_next;
  104. string i_name;
  105. int i_type;
  106. # define IREG 1
  107. # define IPRP 2
  108. # define ITOK 3
  109. # define IEXP 4
  110. union {
  111. int i_regno;
  112. int i_prpno;
  113. int i_tokno;
  114. int i_expno;
  115. } i_i;
  116. } ident_t,*ident_p;
  117. #define ITABSIZE 32
  118. ident_p identtab[ITABSIZE];
  119. #define LOOKUP 0
  120. #define HALFWAY 1
  121. #define ENTER 2
  122. #define JUSTLOOKING 3
  123. typedef struct expr {
  124. int expr_typ;
  125. # define TYPINT 1
  126. # define TYPREG 2
  127. # define TYPSTR 3
  128. # define TYPBOOL 4
  129. int expr_index;
  130. } expr_t,*expr_p;
  131. unsigned cc1=1,cc2=1,cc3=1,cc4=1;
  132. node_t nodes[MAXNODES];
  133. node_p lastnode=nodes+1;
  134. string codestrings[MAXSTRINGS];
  135. int ncodestrings;
  136. int strar[MAXNSTR];
  137. int nstr;
  138. int pathash[256];
  139. reginfo machregs[MAXREGS];
  140. char stregclass[MAXREGS];
  141. int nmachregs=1;
  142. int nregclasses=1;
  143. int maxmembers;
  144. struct {
  145. ident_p propname;
  146. set_t propset;
  147. } machprops[MAXPROPS];
  148. int nprops=0;
  149. token_t machtokens[MAXTOKENS];
  150. int nmachtokens=1;
  151. set_t machsets[MAXSETS];
  152. int nmachsets=0;
  153. int patmnem[MAXEMPATLEN];
  154. int empatlen;
  155. int maxempatlen;
  156. int empatexpr;
  157. int maxrule=1;
  158. int pattokexp[MAXPATLEN];
  159. int tokpatlen;
  160. int lookident=0; /* lexical analyzer flag */
  161. list3 structpool=0;
  162. int nallreg;
  163. int allreg[MAXALLREG];
  164. int maxallreg;
  165. int lino=0;
  166. int nerrors=0;
  167. int curtokexp;
  168. expr_t arexp[TOKENSIZE];
  169. int narexp;
  170. inst_t arinstance[MAXINSTANCE];
  171. int narinstance=1;
  172. move_t machmoves[NMOVES];
  173. int nmoves=0;
  174. byte pattern[MAXPATTERN];
  175. int npatbytes=0;
  176. int prevind;
  177. int rulecount; /* Temporary index for ... construct */
  178. int ncoderules=0;
  179. int codebytes=0;
  180. FILE *cfile;
  181. FILE *hfile;
  182. int maxtokensize=0;
  183. int dealflag;
  184. int emrepllen;
  185. int replmnem[MAXEMPATLEN];
  186. int tokrepllen;
  187. int replinst[MAXPATLEN];
  188. int replexpr[MAXPATLEN];
  189. c1_t c1coercs[MAXC1];
  190. c2_t c2coercs[MAXC2];
  191. c3_t c3coercs[MAXC3];
  192. int nc1=0,nc2=0,nc3=0;
  193. int maxsplit=0;
  194. int wsize= -1;
  195. int psize= -1;
  196. int bsize= -1;
  197. char *fmt=0;
  198. int cchandled;
  199. int ccspoiled;
  200. int ccregexpr;
  201. int ccinstanceno;
  202. int cocopropno;
  203. int cocosetno;
  204. int allexpno;
  205. int rvused; /* regvars used */
  206. int nregvar[4]; /* # of register variables of all kinds */
  207. int rvnumbers[4][MAXREGVARS]; /* The register numbers */
  208. #define chktabsiz(size,maxsize,which) if(size>=maxsize) tabovf(which)
  209. #define MUST1BEINT(e) int exp1=e.expr_index;tstint(e)
  210. #define MUST2BEINT(e1,e2) int exp1=e1.expr_index,exp2=e2.expr_index;tstint(e1);tstint(e2)
  211. #define MUST1BEBOOL(e) int exp1=e.expr_index;tstbool(e)
  212. #define MUST2BEBOOL(e1,e2) int exp1=e1.expr_index,exp2=e2.expr_index;tstbool(e1);tstbool(e2)
  213. %}
  214. %union {
  215. int yy_int;
  216. int *yy_intp;
  217. string yy_string;
  218. list1 yy_list1;
  219. list2 yy_list2;
  220. expr_t yy_expr;
  221. cost_t yy_cost;
  222. set_t yy_set;
  223. ident_p yy_ident;
  224. char yy_char;
  225. inst_t yy_instance;
  226. }
  227. %type <yy_list1> list1,structlistel
  228. %type <yy_list2> structlist,structdecl
  229. %type <yy_expr> expr optexpr
  230. %type <yy_cost> optcost cost optcommacost
  231. %type <yy_int> optboolexpr optnocoerc mnem emargno tokargno optprop
  232. %type <yy_int> optcommabool optstack subreg tokenexpressionno optregvar
  233. %type <yy_int> tokeninstanceno code stackreplacement optslashnumber
  234. %type <yy_set> tokenexpression
  235. %type <yy_instance> tokeninstance
  236. %type <yy_string> optformat
  237. %token <yy_string> IDENT TYPENAME
  238. %token <yy_ident> RIDENT,PIDENT,TIDENT,EIDENT
  239. %token <yy_string> LSTRING,STRING
  240. %token <yy_int> NUMBER
  241. %token <yy_intp> CIDENT
  242. %token REGISTERHEAD TOKENHEAD EXPRESSIONHEAD CODEHEAD MOVEHEAD TESTHEAD STACKHEAD
  243. %token REGVAR INREG LOOP POINTER FLOAT
  244. %token TIMEFAC SIZEFAC FORMAT RETURN
  245. %token MOVE ERASE ALLOCATE ELLIPS COST REMOVE STACK
  246. %token SEP SAMESIGN SFIT UFIT ROM DEFINED TOSTRING LOWW HIGHW
  247. %token NOCC SETCC SAMECC TEST NOCOERC
  248. %token <yy_char> LCASELETTER
  249. %start machinespec
  250. %left OR2
  251. %left AND2
  252. %left CMPEQ,CMPNE
  253. %left CMPLT,CMPLE,CMPGT,CMPGE
  254. %left RSHIFT,LSHIFT
  255. %left '+','-'
  256. %left '*','/','%'
  257. %nonassoc NOT,COMP,UMINUS
  258. %nonassoc '$'
  259. %%
  260. machinespec
  261. : rcsid constants registersection tokensection
  262. { inbetween(); }
  263. expressionsection codesection movesection testsection stacksection
  264. ;
  265. rcsid
  266. : /* empty */
  267. | STRING
  268. { strlookup($1); }
  269. ;
  270. constants
  271. : /* empty */
  272. | constants CIDENT '=' NUMBER
  273. { *$2 = $4; }
  274. | constants SIZEFAC '=' NUMBER optslashnumber
  275. { cc1 = $4; cc2 = $5; }
  276. | constants TIMEFAC '=' NUMBER optslashnumber
  277. { cc3 = $4; cc4 = $5; }
  278. | constants FORMAT '=' STRING
  279. { fmt = $4; }
  280. ;
  281. optslashnumber
  282. : /* empty */
  283. { $$ = 1; }
  284. | '/' NUMBER
  285. { $$ = $2; }
  286. ;
  287. registersection
  288. : REGISTERHEAD registerdefs
  289. ;
  290. registerdefs
  291. : /* empty */
  292. | registerdefs registerdef
  293. ;
  294. registerdef
  295. : IDENT '=' '(' STRING ',' NUMBER list1 ')' optregvar list1 '.'
  296. { register ident_p ip;
  297. register list1 l;
  298. register reginfo r;
  299. int i;
  300. r=(reginfo) myalloc(sizeof(struct reginfo));
  301. r->rname = $1;
  302. r->rrepr = $4;
  303. r->rsize = $6;
  304. if($9>=0 && $7!=0)
  305. yyerror("No subregisters allowed in regvar");
  306. for (i=0;i<MAXMEMBERS;i++)
  307. r->rmembers[i] = 0;
  308. i=0;
  309. for (l=$7;l!=0;l=l->l1next) {
  310. ip=ilookup(l->l1name,LOOKUP);
  311. if (ip->i_type != IREG)
  312. yyerror("Bad member of set");
  313. chktabsiz(i,MAXMEMBERS,"Member of register");
  314. r->rmembers[i++] = ip->i_i.i_regno;
  315. }
  316. maxmembers=max(maxmembers,i);
  317. r->rregvar=$9;
  318. if ($9>=0) {
  319. rvused=1;
  320. chktabsiz(nregvar[$9],MAXREGVARS,"Regvar");
  321. rvnumbers[$9][nregvar[$9]++] = nmachregs;
  322. }
  323. for(i=0;i<PROPSETSIZE;i++)
  324. r->rprop[i] = 0;
  325. ip=ilookup($1,ENTER);
  326. ip->i_type=IREG;
  327. ip->i_i.i_regno=nmachregs;
  328. for (l = $10; l!= 0; l=l->l1next) {
  329. ip = ilookup(l->l1name,HALFWAY);
  330. if (ip->i_type) {
  331. if (ip->i_type != IPRP)
  332. yyerror("Multiple defined symbol");
  333. else if(machprops[ip->i_i.i_prpno].propset.set_size != r->rsize)
  334. yyerror("property has more than 1 size");
  335. } else {
  336. chktabsiz(nprops,MAXPROPS,"Property");
  337. ip->i_type = IPRP;
  338. ip->i_i.i_prpno = nprops;
  339. machprops[nprops].propname = ip;
  340. machprops[nprops++].propset.set_size = r->rsize;
  341. }
  342. r->rprop[ip->i_i.i_prpno>>4] |= (1<<(ip->i_i.i_prpno&017));
  343. }
  344. chktabsiz(nmachregs,MAXREGS,"Register table");
  345. machregs[nmachregs++] = r;
  346. }
  347. | error '.'
  348. ;
  349. optregvar
  350. : /* nothing */
  351. { $$ = -1; }
  352. | REGVAR
  353. { $$ = reg_any; }
  354. | REGVAR '(' LOOP ')'
  355. { $$ = reg_loop; }
  356. | REGVAR '(' POINTER ')'
  357. { $$ = reg_pointer; }
  358. | REGVAR '(' FLOAT ')'
  359. { $$ = reg_float; }
  360. ;
  361. tokensection
  362. : TOKENHEAD tkdefs
  363. ;
  364. tkdefs
  365. : /* empty */
  366. | tkdefs tkdef
  367. ;
  368. tkdef
  369. : IDENT '=' structdecl NUMBER optcost optformat
  370. { register token_p tp;
  371. register ident_p ip;
  372. chktabsiz(nmachtokens,MAXTOKENS,"Token table");
  373. tp = &machtokens[nmachtokens];
  374. tp->t_name = $1;
  375. tp->t_struct = $3;
  376. tp->t_size = $4;
  377. tp->t_cost = $5;
  378. ip = ilookup($1,ENTER);
  379. ip->i_type = ITOK;
  380. ip->i_i.i_tokno = nmachtokens++;
  381. maxtokensize=max(maxtokensize,structsize($3));
  382. setfields(tp,$6);
  383. }
  384. | error
  385. ;
  386. structdecl
  387. : '{' structlist '}'
  388. { $$ = lookstruct($2); }
  389. ;
  390. structlist
  391. : /* empty */
  392. { $$=0; }
  393. | structlistel structlist
  394. { $$=(list2) myalloc(sizeof(struct list2str));
  395. $$->l2next = $2;
  396. $$->l2list = $1;
  397. }
  398. ;
  399. structlistel
  400. : TYPENAME list1 ';'
  401. { $$=(list1) myalloc(sizeof(struct list1str));
  402. $$->l1next = $2;
  403. $$->l1name = $1;
  404. }
  405. ;
  406. optcost : /* empty */
  407. { $$.c_size = $$.c_time = 0; }
  408. | COST '=' '(' expr ',' expr ')'
  409. { MUST2BEINT($4,$6);
  410. $$.c_size = exp1;
  411. $$.c_time = exp2;
  412. }
  413. ;
  414. optformat
  415. : /* empty */
  416. { $$ = 0; }
  417. | STRING
  418. ;
  419. expressionsection
  420. : /* empty */
  421. | EXPRESSIONHEAD tokenexpressions
  422. ;
  423. tokenexpressions
  424. : tokenexpressionline
  425. | tokenexpressionline tokenexpressions
  426. ;
  427. tokenexpressionline
  428. : IDENT '=' tokenexpression
  429. {
  430. { register ident_p ip;
  431. chktabsiz(nmachsets,MAXSETS,"Expression table");
  432. machsets[nmachsets] = $3;
  433. ip=ilookup($1,ENTER);
  434. ip->i_type = IEXP;
  435. ip->i_i.i_expno = nmachsets++;
  436. }
  437. }
  438. | error
  439. ;
  440. tokenexpression
  441. : PIDENT
  442. { $$ = machprops[$1->i_i.i_prpno].propset; }
  443. | TIDENT
  444. { register i;
  445. for(i=0;i<SETSIZE;i++) $$.set_val[i]=0;
  446. $$.set_val[($1->i_i.i_tokno+nmachregs+1)>>4] |=
  447. 01<<(($1->i_i.i_tokno+nmachregs+1)&017);
  448. $$.set_size = machtokens[$1->i_i.i_tokno].t_size;
  449. }
  450. | EIDENT
  451. { $$=machsets[$1->i_i.i_expno]; }
  452. | tokenexpression '*' tokenexpression
  453. { register i;
  454. if (($$.set_size=$1.set_size)==0)
  455. $$.set_size = $3.set_size;
  456. for (i=0;i<SETSIZE;i++)
  457. $$.set_val[i] = $1.set_val[i] & $3.set_val[i];
  458. }
  459. | tokenexpression '+' tokenexpression
  460. { register i;
  461. if ($1.set_size == -1)
  462. $$.set_size = $3.set_size;
  463. else if ($3.set_size == -1)
  464. $$.set_size = $1.set_size;
  465. else if ($1.set_size == $3.set_size)
  466. $$.set_size = $1.set_size;
  467. else
  468. $$.set_size = 0;
  469. for (i=0;i<SETSIZE;i++)
  470. $$.set_val[i] = $1.set_val[i] | $3.set_val[i];
  471. }
  472. | tokenexpression '-' tokenexpression
  473. { register i;
  474. if ($1.set_size == -1)
  475. $$.set_size = $3.set_size;
  476. else if ($3.set_size == -1)
  477. $$.set_size = $1.set_size;
  478. else if ($1.set_size == $3.set_size)
  479. $$.set_size = $1.set_size;
  480. else
  481. $$.set_size = 0;
  482. for (i=0;i<SETSIZE;i++)
  483. $$.set_val[i] = $1.set_val[i] & ~ $3.set_val[i];
  484. }
  485. | '(' tokenexpression ')'
  486. { $$ = $2; }
  487. ;
  488. codesection
  489. : CODEHEAD coderules
  490. ;
  491. coderules
  492. : coderule
  493. | coderules coderule
  494. ;
  495. coderule
  496. : { nallreg=emrepllen=tokrepllen=0; }
  497. empattern SEP stackpattern SEP code SEP stackreplacement SEP
  498. emreplacement SEP cost
  499. { int i;
  500. if (emrepllen) {
  501. outbyte(DO_EMREPLACE+(emrepllen<<5));
  502. for (i=0;i<emrepllen;i++) {
  503. out(replmnem[i]);
  504. out(replexpr[i]);
  505. }
  506. }
  507. if ($8==0) {
  508. outbyte(DO_TOKREPLACE+(tokrepllen<<5));
  509. for(i=0;i<tokrepllen;i++)
  510. out(replinst[i]);
  511. } else {
  512. static int warncount=0;
  513. if (!warncount++)
  514. fprintf(stderr,
  515. "WARNING: convert to stacksection, will disappear soon");
  516. outbyte(DO_TOKREPLACE);
  517. }
  518. if ($12.c_size!=0 || $12.c_time!=0) {
  519. outbyte(DO_COST);
  520. out($12.c_size);
  521. out($12.c_time);
  522. }
  523. outbyte(empatlen==0? DO_RETURN : DO_NEXTEM);
  524. fprintf(cfile,"\n");
  525. ncoderules++;
  526. maxallreg=max(maxallreg,nallreg);
  527. if (empatlen==0) { /* coercion */
  528. if (tokrepllen<1 && $8==0)
  529. yyerror("No replacement in coercion");
  530. if (tokpatlen>1)
  531. yyerror("Token pattern too long");
  532. if ($8!=0) { /* stacking */
  533. c1_p cp;
  534. chktabsiz(nc1,MAXC1,"Coerc table 1");
  535. cp = &c1coercs[nc1++];
  536. cp->c1_texpno = pattokexp[1];
  537. cp->c1_prop = -1;
  538. cp->c1_codep = $6;
  539. } else if (tokrepllen>1) { /* splitting */
  540. c2_p cp;
  541. chktabsiz(nc2,MAXC2,"Coerc table 2");
  542. cp= &c2coercs[nc2++];
  543. cp->c2_texpno = pattokexp[1];
  544. cp->c2_nsplit = tokrepllen;
  545. maxsplit=max(maxsplit,tokrepllen);
  546. for (i=0;i<tokrepllen;i++)
  547. cp->c2_repl[i] = replinst[i];
  548. cp->c2_codep = $6;
  549. if (nallreg>0)
  550. yyerror("No allocates allowed here");
  551. } else { /* one to one coercion */
  552. c3_p cp;
  553. chktabsiz(nc3,MAXC3,"Coerc table 3");
  554. cp= &c3coercs[nc3++];
  555. if (tokpatlen)
  556. cp->c3_texpno = pattokexp[1];
  557. else
  558. cp->c3_texpno = 0;
  559. if (nallreg>1)
  560. yyerror("Too many allocates in coercion");
  561. cp->c3_prop = nallreg==0 ? 0 : allreg[0];
  562. cp->c3_repl = replinst[0];
  563. cp->c3_codep = $6;
  564. }
  565. }
  566. }
  567. | error
  568. ;
  569. empattern
  570. : /* empty */
  571. { empatlen=0; }
  572. | mnemlist optboolexpr
  573. { register i;
  574. empatexpr = $2;
  575. patbyte(0);
  576. patshort(prevind);
  577. prevind = npatbytes - 3;
  578. maxempatlen = max(empatlen,maxempatlen);
  579. pat(empatlen);
  580. for(i=1;i<=empatlen;i++)
  581. patbyte(patmnem[i]);
  582. pat(empatexpr);
  583. rulecount = npatbytes;
  584. patbyte(1); /* number of different rules with this pattern */
  585. pat(codebytes); /* first rule */
  586. }
  587. | ELLIPS
  588. { pattern[rulecount]++;
  589. maxrule= max(maxrule,pattern[rulecount]);
  590. pat(codebytes);
  591. }
  592. ;
  593. mnemlist
  594. : mnem
  595. { empatlen = 1; patmnem[empatlen] = $1; }
  596. | mnemlist mnem
  597. { chktabsiz(empatlen+1,MAXEMPATLEN,"EM pattern");
  598. patmnem[++empatlen] = $2;
  599. }
  600. ;
  601. mnem : IDENT
  602. { if(strlen($1)!=3 || ($$=mlookup($1))==0)
  603. yyerror("not an EM-mnemonic");
  604. }
  605. ;
  606. stackpattern
  607. : optnocoerc tokenexpressionlist optstack
  608. { register i;
  609. if (tokpatlen != 0) {
  610. outbyte(($1 ? ( $3 ? DO_XXMATCH: DO_XMATCH ) : DO_MATCH)+(tokpatlen<<5));
  611. for(i=1;i<=tokpatlen;i++) {
  612. out(pattokexp[i]);
  613. }
  614. }
  615. if ($3 && tokpatlen==0 && empatlen==0) {
  616. outbyte(DO_COERC);
  617. }
  618. if ($3 && !$1 && empatlen!=0) {
  619. outbyte(DO_REMOVE);
  620. out(allexpno);
  621. }
  622. }
  623. ;
  624. optnocoerc
  625. : /* empty */
  626. { $$ = 0; }
  627. | NOCOERC ':'
  628. { $$ = 1; }
  629. ;
  630. tokenexpressionlist
  631. : /* empty */
  632. { tokpatlen = 0; }
  633. | tokenexpressionlist tokenexpressionno
  634. { chktabsiz(tokpatlen+1,MAXPATLEN,"Token pattern");
  635. pattokexp[++tokpatlen] = $2;
  636. if (machsets[$2].set_size==0)
  637. yyerror("Various sized set in tokenpattern");
  638. }
  639. ;
  640. tokenexpressionno
  641. : tokenexpression
  642. { $$ = exprlookup($1); }
  643. ;
  644. optstack
  645. : /* empty */
  646. { $$ = 0; }
  647. | STACK
  648. { $$ = 1; }
  649. ;
  650. code :
  651. { $$ = codebytes; cchandled=ccspoiled=0; }
  652. initcode restcode
  653. { if (cchandled==0 && ccspoiled!=0) {
  654. outbyte(DO_ERASE);
  655. out(ccregexpr);
  656. }
  657. }
  658. ;
  659. initcode
  660. : /* empty */
  661. | initcode remove
  662. | initcode allocate
  663. ;
  664. remove
  665. : REMOVE '(' tokenexpressionno
  666. { curtokexp = $3; }
  667. optcommabool ')'
  668. { outbyte(DO_REMOVE+ ($5!=0 ? 32 : 0));
  669. out($3);
  670. if ($5!=0) out($5);
  671. }
  672. | REMOVE '(' expr ')'
  673. { if ($3.expr_typ != TYPREG)
  674. yyerror("Expression must be register");
  675. outbyte(DO_RREMOVE);
  676. out($3.expr_index);
  677. }
  678. ;
  679. optcommabool
  680. : /* empty */
  681. { $$ = 0; }
  682. | ',' expr
  683. { MUST1BEBOOL($2);
  684. $$ = exp1;
  685. }
  686. ;
  687. restcode: /* empty */
  688. | restcode LSTRING expr
  689. { outbyte(DO_LOUTPUT);
  690. out(stringno($2));
  691. free($2);
  692. out($3.expr_index);
  693. ccspoiled++;
  694. }
  695. | restcode stringlist
  696. { int i;
  697. for(i=0;nstr>0;i++,nstr--) {
  698. if (i%8==0) outbyte(DO_ROUTPUT+(nstr>7 ? 7 : nstr-1)*32);
  699. out(strar[i]);
  700. }
  701. ccspoiled++;
  702. }
  703. | restcode RETURN
  704. { outbyte(DO_PRETURN); }
  705. | restcode move
  706. | restcode erase
  707. | restcode NOCC
  708. { outbyte(DO_ERASE);
  709. out(ccregexpr);
  710. cchandled++;
  711. }
  712. | restcode SAMECC
  713. { cchandled++; }
  714. | restcode SETCC '(' tokeninstanceno ')'
  715. { outbyte(DO_MOVE);
  716. out(ccinstanceno);
  717. out($4);
  718. cchandled++;
  719. }
  720. | restcode TEST '(' tokeninstanceno ')'
  721. { outbyte(DO_MOVE);
  722. out($4);
  723. out(ccinstanceno);
  724. ccspoiled=0;
  725. }
  726. ;
  727. stringlist
  728. : STRING
  729. { nstr=1;
  730. strar[0]=stringno($1);
  731. free($1);
  732. }
  733. | stringlist STRING
  734. { chktabsiz(nstr,MAXNSTR,"Consecutiv strings");
  735. strar[nstr++] = stringno($2);
  736. free($2);
  737. }
  738. ;
  739. move
  740. : MOVE '(' tokeninstanceno ',' tokeninstanceno ')'
  741. { outbyte(DO_MOVE);
  742. out($3);
  743. out($5);
  744. }
  745. ;
  746. erase
  747. : ERASE '(' expr ')'
  748. { outbyte(DO_ERASE);
  749. out($3.expr_index);
  750. if($3.expr_typ != TYPREG)
  751. yyerror("Bad argument of erase");
  752. }
  753. ;
  754. allocate
  755. : ALLOCATE { dealflag=0; } '(' alloclist ')'
  756. { if (dealflag)
  757. outbyte(DO_REALLOCATE);
  758. }
  759. ;
  760. alloclist
  761. : allocel
  762. | alloclist optcomma allocel
  763. ;
  764. allocel
  765. : tokeninstanceno /* deallocate */
  766. { outbyte(DO_DEALLOCATE);
  767. out($1);
  768. dealflag++;
  769. }
  770. | PIDENT
  771. { allreg[nallreg++] = $1->i_i.i_prpno;
  772. outbyte(DO_ALLOCATE);
  773. out($1->i_i.i_prpno);
  774. }
  775. | PIDENT '=' tokeninstanceno
  776. { allreg[nallreg++] = $1->i_i.i_prpno;
  777. outbyte(DO_ALLOCATE+32);
  778. out($1->i_i.i_prpno);
  779. out($3);
  780. }
  781. ;
  782. stackreplacement
  783. : /* empty */
  784. { $$=0; }
  785. | STACK
  786. { $$=1; }
  787. | '{' STACK '}'
  788. { $$=1; }
  789. | stackrepllist
  790. { $$=0; }
  791. ;
  792. stackrepllist
  793. : tokeninstanceno
  794. { tokrepllen=1; replinst[0] = $1; }
  795. | stackrepllist tokeninstanceno
  796. { chktabsiz(tokrepllen+1,MAXPATLEN,"Stack replacement");
  797. replinst[tokrepllen++] = $2;
  798. }
  799. ;
  800. emreplacement
  801. : /* empty, normal case */
  802. | emrepllist
  803. ;
  804. emrepllist
  805. : mnem optexpr
  806. { emrepllen=1;
  807. replmnem[0]=$1;
  808. replexpr[0]=$2.expr_index;
  809. }
  810. | emrepllist mnem optexpr
  811. { chktabsiz(emrepllen+1,MAXEMPATLEN,"EM replacement");
  812. replmnem[emrepllen]=$2;
  813. replexpr[emrepllen]=$3.expr_index;
  814. emrepllen++;
  815. }
  816. ;
  817. cost : /* empty */
  818. { $$.c_size = $$.c_time = 0;
  819. }
  820. | '(' expr ',' expr ')'
  821. { MUST2BEINT($2,$4);
  822. $$.c_size = exp1;
  823. $$.c_time = exp2;
  824. }
  825. | cost '+' '%' '[' tokargno ']'
  826. { $$.c_size = lookup(1,EX_PLUS,$1.c_size,
  827. lookup(0,EX_COST,$5,0));
  828. $$.c_time = lookup(1,EX_PLUS,$1.c_time,
  829. lookup(0,EX_COST,$5,1));
  830. }
  831. ;
  832. movesection
  833. : MOVEHEAD movedefs
  834. ;
  835. movedefs
  836. : movedef
  837. | movedefs movedef
  838. ;
  839. movedef
  840. : '(' tokenexpressionno
  841. { curtokexp = $2; }
  842. optboolexpr ',' tokenexpressionno
  843. { curtokexp = $6;
  844. pattokexp[1] = $2;
  845. pattokexp[2] = $6;
  846. tokpatlen=2;
  847. }
  848. optboolexpr ',' code optcommacost ')'
  849. { register move_p mp;
  850. outbyte(DO_RETURN);
  851. fprintf(cfile,"\n");
  852. chktabsiz(nmoves,NMOVES,"Move definition table");
  853. mp = &machmoves[nmoves++];
  854. mp->m_set1 = $2;
  855. mp->m_expr1= $4;
  856. mp->m_set2 = $6;
  857. mp->m_expr2= $8;
  858. mp->m_cindex=$10;
  859. mp->m_cost = $11;
  860. }
  861. | error
  862. ;
  863. testsection
  864. : /* empty */
  865. | TESTHEAD testdefs
  866. ;
  867. testdefs: testdef
  868. | testdefs testdef
  869. ;
  870. testdef : '(' tokenexpressionno
  871. { curtokexp = $2;
  872. pattokexp[1] = $2;
  873. pattokexp[2] = cocosetno;
  874. tokpatlen=2;
  875. }
  876. optboolexpr ',' code optcommacost ')'
  877. { register move_p mp;
  878. outbyte(DO_RETURN);
  879. fprintf(cfile,"\n");
  880. chktabsiz(nmoves,NMOVES,"Move definition table(tests)");
  881. mp = &machmoves[nmoves++];
  882. mp->m_set1 = $2;
  883. mp->m_expr1 = $4;
  884. mp->m_set2 = cocosetno;
  885. mp->m_expr2 = 0;
  886. mp->m_cindex = $6;
  887. mp->m_cost = $7;
  888. }
  889. ;
  890. stacksection
  891. : STACKHEAD stackdefs
  892. | /* empty */
  893. ;
  894. stackdefs
  895. : stackdef
  896. | stackdefs stackdef
  897. ;
  898. stackdef
  899. : '(' tokenexpressionno
  900. { curtokexp = $2;
  901. pattokexp[1] = $2;
  902. tokpatlen=1;
  903. }
  904. optboolexpr ',' optprop ',' code optcommacost ')'
  905. { register c1_p cp;
  906. outbyte(DO_TOKREPLACE);
  907. outbyte(DO_RETURN);
  908. fprintf(cfile,"\n");
  909. chktabsiz(nc1,MAXC1,"Stacking table");
  910. cp = &c1coercs[nc1++];
  911. cp->c1_texpno = $2;
  912. cp->c1_expr = $4;
  913. cp->c1_prop = $6;
  914. cp->c1_codep = $8;
  915. cp->c1_cost = $9;
  916. }
  917. ;
  918. optprop
  919. : /* empty */
  920. { $$ = -1; }
  921. | PIDENT
  922. { $$ = $1->i_i.i_prpno; }
  923. ;
  924. optcommacost
  925. : /* empty */
  926. { $$.c_size = 0; $$.c_time = 0;}
  927. | ',' cost
  928. { $$ = $2; }
  929. ;
  930. list1 : /* empty */
  931. { $$ = 0; }
  932. | optcomma IDENT list1
  933. { $$=(list1) myalloc(sizeof(struct list1str));
  934. $$->l1next = $3;
  935. $$->l1name = $2;
  936. }
  937. ;
  938. optcomma: /* nothing */
  939. | ','
  940. ;
  941. emargno : NUMBER
  942. { if ($1<1 || $1>empatlen)
  943. yyerror("Number after $ out of range");
  944. $$ = $1;
  945. }
  946. ;
  947. tokargno
  948. : NUMBER
  949. { if ($1<1 || $1>tokpatlen)
  950. yyerror("Number within %[] out of range");
  951. $$ = $1;
  952. }
  953. ;
  954. expr : '$' emargno
  955. { $$.expr_index = lookup(0,EX_ARG,$2,0); $$.expr_typ = argtyp(patmnem[$2]);
  956. }
  957. | NUMBER
  958. { $$.expr_index = lookup(0,EX_CON,(int)($1&0177777),(int)($1>>16));
  959. $$.expr_typ = TYPINT;
  960. }
  961. | STRING
  962. { $$.expr_index = lookup(0,EX_STRING,strlookup($1),0);
  963. $$.expr_typ = TYPSTR;
  964. }
  965. | RIDENT
  966. { $$.expr_index = lookup(0,EX_REG,$1->i_i.i_regno,0);
  967. $$.expr_typ = TYPREG;
  968. }
  969. | '%' '[' tokargno '.' IDENT ']'
  970. { $$.expr_index = lookup(0,EX_TOKFIELD,$3,
  971. findstructel(pattokexp[$3],$5,&$$.expr_typ));
  972. }
  973. | '%' '[' tokargno subreg ']'
  974. { chkregexp(pattokexp[$3]);
  975. $$.expr_index = lookup(0,EX_SUBREG,$3,$4);
  976. $$.expr_typ = TYPREG;
  977. }
  978. | '%' '[' LCASELETTER subreg ']'
  979. { if ($3 >= 'a'+nallreg)
  980. yyerror("Bad letter in %[x] construct");
  981. $$.expr_index = lookup(0,EX_ALLREG,$3-'a'+1,$4);
  982. $$.expr_typ = TYPREG;
  983. }
  984. | '%' '[' IDENT ']'
  985. { $$.expr_index = lookup(0,EX_TOKFIELD,0,
  986. findstructel(curtokexp,$3,&$$.expr_typ));
  987. }
  988. | TOSTRING '(' expr ')'
  989. { MUST1BEINT($3);
  990. $$.expr_index = lookup(0,EX_TOSTRING,exp1,0);
  991. $$.expr_typ = TYPSTR;
  992. }
  993. | DEFINED '(' expr ')'
  994. { $$.expr_index = lookup(0,EX_DEFINED,$3.expr_index,0);
  995. $$.expr_typ = TYPBOOL;
  996. }
  997. | SAMESIGN '(' expr ',' expr ')'
  998. { MUST2BEINT($3,$5);
  999. $$.expr_index = lookup(1,EX_SAMESIGN,exp1,exp2);
  1000. $$.expr_typ = TYPBOOL;
  1001. }
  1002. | SFIT '(' expr ',' expr ')'
  1003. { MUST2BEINT($3,$5);
  1004. $$.expr_index = lookup(0,EX_SFIT,exp1,exp2);
  1005. $$.expr_typ = TYPBOOL;
  1006. }
  1007. | UFIT '(' expr ',' expr ')'
  1008. { MUST2BEINT($3,$5);
  1009. $$.expr_index = lookup(0,EX_UFIT,exp1,exp2);
  1010. $$.expr_typ = TYPBOOL;
  1011. }
  1012. | ROM '(' emargno ',' NUMBER ')'
  1013. { if ($5<1 || $5>3)
  1014. yyerror("Second argument of rom must be >=1 and <=3");
  1015. $$.expr_index = lookup(0,EX_ROM,$3-1,$5-1);
  1016. $$.expr_typ = TYPINT;
  1017. }
  1018. | LOWW '(' emargno ')'
  1019. {
  1020. $$.expr_index = lookup(0,EX_LOWW,$3-1,0);
  1021. $$.expr_typ = TYPINT;
  1022. }
  1023. | HIGHW '(' emargno ')'
  1024. {
  1025. $$.expr_index = lookup(0,EX_HIGHW,$3-1,0);
  1026. $$.expr_typ = TYPINT;
  1027. }
  1028. | '(' expr ')'
  1029. { $$ = $2; }
  1030. | expr CMPEQ expr
  1031. { switch(commontype($1,$3)) {
  1032. case TYPINT:
  1033. $$.expr_index = lookup(1,EX_NCPEQ,$1.expr_index,$3.expr_index);
  1034. break;
  1035. case TYPSTR:
  1036. $$.expr_index = lookup(1,EX_SCPEQ,$1.expr_index,$3.expr_index);
  1037. break;
  1038. case TYPREG:
  1039. $$.expr_index = lookup(1,EX_RCPEQ,$1.expr_index,$3.expr_index);
  1040. break;
  1041. }
  1042. $$.expr_typ = TYPBOOL;
  1043. }
  1044. | expr CMPNE expr
  1045. { switch(commontype($1,$3)) {
  1046. case TYPINT:
  1047. $$.expr_index = lookup(1,EX_NCPNE,$1.expr_index,$3.expr_index);
  1048. break;
  1049. case TYPSTR:
  1050. $$.expr_index = lookup(1,EX_SCPNE,$1.expr_index,$3.expr_index);
  1051. break;
  1052. case TYPREG:
  1053. $$.expr_index = lookup(1,EX_RCPNE,$1.expr_index,$3.expr_index);
  1054. break;
  1055. }
  1056. $$.expr_typ = TYPBOOL;
  1057. }
  1058. | expr CMPGT expr
  1059. { MUST2BEINT($1,$3);
  1060. $$.expr_index = lookup(0,EX_NCPGT,exp1,exp2);
  1061. $$.expr_typ = TYPBOOL;
  1062. }
  1063. | expr CMPGE expr
  1064. { MUST2BEINT($1,$3);
  1065. $$.expr_index = lookup(0,EX_NCPGE,exp1,exp2);
  1066. $$.expr_typ = TYPBOOL;
  1067. }
  1068. | expr CMPLT expr
  1069. { MUST2BEINT($1,$3);
  1070. $$.expr_index = lookup(0,EX_NCPLT,exp1,exp2);
  1071. $$.expr_typ = TYPBOOL;
  1072. }
  1073. | expr CMPLE expr
  1074. { MUST2BEINT($1,$3);
  1075. $$.expr_index = lookup(0,EX_NCPLE,exp1,exp2);
  1076. $$.expr_typ = TYPBOOL;
  1077. }
  1078. | expr OR2 expr
  1079. { MUST2BEBOOL($1,$3);
  1080. $$.expr_index = lookup(0,EX_OR2,exp1,exp2);
  1081. $$.expr_typ = TYPBOOL;
  1082. }
  1083. | expr AND2 expr
  1084. { MUST2BEBOOL($1,$3);
  1085. $$.expr_index = lookup(0,EX_AND2,exp1,exp2);
  1086. $$.expr_typ = TYPBOOL;
  1087. }
  1088. | expr '+' expr
  1089. { switch(commontype($1,$3)) {
  1090. case TYPINT:
  1091. $$.expr_index = lookup(1,EX_PLUS,$1.expr_index,$3.expr_index);
  1092. break;
  1093. case TYPSTR:
  1094. $$.expr_index = lookup(0,EX_CAT,$1.expr_index,$3.expr_index);
  1095. break;
  1096. default:
  1097. yyerror("Bad types");
  1098. }
  1099. $$.expr_typ = $1.expr_typ;
  1100. }
  1101. | expr '-' expr
  1102. { MUST2BEINT($1,$3);
  1103. $$.expr_index = lookup(0,EX_MINUS,exp1,exp2);
  1104. $$.expr_typ = TYPINT;
  1105. }
  1106. | expr '*' expr
  1107. { MUST2BEINT($1,$3);
  1108. $$.expr_index = lookup(1,EX_TIMES,exp1,exp2);
  1109. $$.expr_typ = TYPINT;
  1110. }
  1111. | expr '/' expr
  1112. { MUST2BEINT($1,$3);
  1113. $$.expr_index = lookup(0,EX_DIVIDE,exp1,exp2);
  1114. $$.expr_typ = TYPINT;
  1115. }
  1116. | expr '%' expr
  1117. { MUST2BEINT($1,$3);
  1118. $$.expr_index = lookup(0,EX_MOD,exp1,exp2);
  1119. $$.expr_typ = TYPINT;
  1120. }
  1121. | expr LSHIFT expr
  1122. { MUST2BEINT($1,$3);
  1123. $$.expr_index = lookup(0,EX_LSHIFT,exp1,exp2);
  1124. $$.expr_typ = TYPINT;
  1125. }
  1126. | expr RSHIFT expr
  1127. { MUST2BEINT($1,$3);
  1128. $$.expr_index = lookup(0,EX_RSHIFT,exp1,exp2);
  1129. $$.expr_typ = TYPINT;
  1130. }
  1131. | NOT expr
  1132. { MUST1BEBOOL($2);
  1133. $$.expr_index = lookup(0,EX_NOT,exp1,0);
  1134. $$.expr_typ = TYPBOOL;
  1135. }
  1136. | COMP expr
  1137. { MUST1BEINT($2);
  1138. $$.expr_index = lookup(0,EX_COMP,exp1,0);
  1139. $$.expr_typ = TYPINT;
  1140. }
  1141. | INREG '(' expr ')'
  1142. { MUST1BEINT($3);
  1143. $$.expr_index = lookup(0,EX_INREG,exp1,0);
  1144. $$.expr_typ = TYPINT;
  1145. }
  1146. | REGVAR '(' expr ')'
  1147. { MUST1BEINT($3);
  1148. $$.expr_index = lookup(0,EX_REGVAR,exp1,0);
  1149. $$.expr_typ = TYPREG;
  1150. }
  1151. /*
  1152. | '-' expr %prec UMINUS
  1153. { MUST1BEINT($2);
  1154. $$.expr_index = lookup(0,EX_UMINUS,exp1,0);
  1155. $$.expr_typ = TYPINT;
  1156. }
  1157. */
  1158. ;
  1159. subreg : /* empty */
  1160. { $$=0; }
  1161. | '.' NUMBER
  1162. { $$=$2; }
  1163. ;
  1164. optboolexpr
  1165. : /* empty */
  1166. { $$ = 0; }
  1167. | expr
  1168. { MUST1BEBOOL($1);
  1169. $$=exp1;
  1170. }
  1171. ;
  1172. optexpr
  1173. : /* empty */
  1174. { $$.expr_typ=0;
  1175. $$.expr_index=0;
  1176. }
  1177. | expr
  1178. ;
  1179. tokeninstanceno
  1180. : tokeninstance
  1181. { $$ = instno($1); }
  1182. ;
  1183. tokeninstance
  1184. : '%' '[' tokargno subreg ']'
  1185. { register i;
  1186. if ($4!=0)
  1187. chkregexp(pattokexp[$3]);
  1188. $$.in_which = IN_COPY;
  1189. $$.in_info[0] = $3;
  1190. $$.in_info[1] = $4;
  1191. for (i=2;i<TOKENSIZE;i++)
  1192. $$.in_info[i] = 0;
  1193. }
  1194. | '%' '[' tokargno '.' IDENT ']'
  1195. { int typ;
  1196. register i;
  1197. $$.in_which = IN_COPY;
  1198. $$.in_info[0] = $3;
  1199. $$.in_info[1] = findstructel(pattokexp[$3],$5,&typ);
  1200. if (typ != TYPREG)
  1201. yyerror("Must be register");
  1202. for (i=2;i<TOKENSIZE;i++)
  1203. $$.in_info[i] = 0;
  1204. }
  1205. | RIDENT
  1206. { register i;
  1207. $$.in_which = IN_RIDENT;
  1208. $$.in_info[0] = $1->i_i.i_regno;
  1209. for (i=1;i<TOKENSIZE;i++)
  1210. $$.in_info[i] = 0;
  1211. }
  1212. | REGVAR '(' expr ')'
  1213. { register i;
  1214. MUST1BEINT($3);
  1215. $$.in_which = IN_REGVAR;
  1216. $$.in_info[0] = exp1;
  1217. for (i=1;i<TOKENSIZE;i++)
  1218. $$.in_info[i] = 0;
  1219. }
  1220. | '%' '[' LCASELETTER subreg ']'
  1221. { register i;
  1222. if ($3 >= 'a'+nallreg)
  1223. yyerror("Bad letter in %[x] construct");
  1224. $$.in_which = IN_ALLOC;
  1225. $$.in_info[0] = $3-'a';
  1226. $$.in_info[1] = $4;
  1227. for (i=2;i<TOKENSIZE;i++)
  1228. $$.in_info[i] = 0;
  1229. }
  1230. | '{' TIDENT attlist '}'
  1231. { register i;
  1232. $$.in_which = IN_DESCR;
  1233. $$.in_info[0] = $2->i_i.i_tokno;
  1234. for(i=0;i<narexp;i++) {
  1235. if (arexp[i].expr_typ !=
  1236. machtokens[$2->i_i.i_tokno].t_fields[i].t_type)
  1237. yyerror("Attribute %d has wrong type",i+1);
  1238. $$.in_info[i+1] = arexp[i].expr_index;
  1239. }
  1240. for (i=narexp+1;i<TOKENSIZE;i++) {
  1241. if (machtokens[$2->i_i.i_tokno].t_fields[i-1].t_type!=0)
  1242. yyerror("Too few attributes");
  1243. $$.in_info[i] = 0;
  1244. }
  1245. }
  1246. ;
  1247. attlist
  1248. : /* empty */
  1249. { narexp = 0; }
  1250. | attlist ',' expr
  1251. { arexp[narexp++] = $3; }
  1252. ;
  1253. %%
  1254. char * myalloc(n) {
  1255. register char *p;
  1256. p= (char*) malloc(n);
  1257. if (p==0) {
  1258. yyerror("Out of core");
  1259. exit(1);
  1260. }
  1261. return(p);
  1262. }
  1263. tstint(e) expr_t e; {
  1264. if(e.expr_typ != TYPINT)
  1265. yyerror("Must be integer expression");
  1266. }
  1267. tstbool(e) expr_t e; {
  1268. if(e.expr_typ != TYPBOOL)
  1269. yyerror("Must be boolean expression");
  1270. }
  1271. structsize(s) register list2 s; {
  1272. register list1 l;
  1273. register sum;
  1274. sum = 0;
  1275. while ( s != 0 ) {
  1276. l = s->l2list->l1next;
  1277. while ( l != 0 ) {
  1278. sum++;
  1279. l = l->l1next;
  1280. }
  1281. s = s->l2next;
  1282. }
  1283. return(sum);
  1284. }
  1285. list2 lookstruct(ll) list2 ll; {
  1286. list3 l3;
  1287. list2 l21,l22;
  1288. list1 l11,l12;
  1289. for (l3=structpool;l3 != 0;l3=l3->l3next) {
  1290. for (l21=l3->l3list,l22=ll;l21!=0 && l22!=0;
  1291. l21=l21->l2next,l22=l22->l2next) {
  1292. for(l11=l21->l2list,l12=l22->l2list;
  1293. l11!=0 && l12!=0 && strcmp(l11->l1name,l12->l1name)==0;
  1294. l11=l11->l1next,l12=l12->l1next)
  1295. ;
  1296. if (l11!=0 || l12!=0)
  1297. goto contin;
  1298. }
  1299. if(l21==0 && l22==0)
  1300. return(l3->l3list);
  1301. contin:;
  1302. }
  1303. l3 = (list3) myalloc(sizeof(struct list3str));
  1304. l3->l3next=structpool;
  1305. l3->l3list=ll;
  1306. structpool=l3;
  1307. return(ll);
  1308. }
  1309. instno(inst) inst_t inst; {
  1310. register i,j;
  1311. for(i=1;i<narinstance;i++) {
  1312. if (arinstance[i].in_which != inst.in_which)
  1313. continue;
  1314. for(j=0;j<TOKENSIZE;j++)
  1315. if(arinstance[i].in_info[j] != inst.in_info[j])
  1316. goto cont;
  1317. return(i);
  1318. cont:;
  1319. }
  1320. chktabsiz(narinstance,MAXINSTANCE,"Instance table");
  1321. arinstance[narinstance] = inst;
  1322. return(narinstance++);
  1323. }
  1324. string scopy(s) string s; {
  1325. register string t;
  1326. t = (char *) myalloc(strlen(s)+1);
  1327. strcpy(t,s);
  1328. return(t);
  1329. }
  1330. strlookup(s) string s; {
  1331. register i;
  1332. for(i=0;i<ncodestrings;i++)
  1333. if(strcmp(s,codestrings[i])==0)
  1334. return(i);
  1335. chktabsiz(ncodestrings,MAXSTRINGS,"string table");
  1336. codestrings[ncodestrings] = scopy(s);
  1337. return(ncodestrings++);
  1338. }
  1339. stringno(s) register string s; {
  1340. char buf[256];
  1341. register char *p=buf;
  1342. while(*s != 0) switch(*s) {
  1343. default:
  1344. *p++ = *s++;
  1345. continue;
  1346. case '$':
  1347. s++;
  1348. switch(*s) {
  1349. default:
  1350. yyerror("Bad character after $ in codestring");
  1351. case '$':
  1352. *p++ = *s++;
  1353. continue;
  1354. case '1':
  1355. case '2':
  1356. case '3':
  1357. case '4':
  1358. case '5':
  1359. case '6':
  1360. case '7':
  1361. case '8':
  1362. case '9':
  1363. *p++ = argtyp(patmnem[*s-'0']) == TYPINT ?
  1364. PR_EMINT : PR_EMSTR;
  1365. *p++ = *s++ -'0';
  1366. continue;
  1367. }
  1368. case '%':
  1369. s++;
  1370. if (*s != '[') {
  1371. if(*s == '%') {
  1372. *p++ = *s++;
  1373. continue;
  1374. } else
  1375. yyerror("Bad character following %% in codestring");
  1376. } else
  1377. s++;
  1378. if(isdigit(*s)) {
  1379. int num;
  1380. num = *s++ - '0';
  1381. if (num<1 || num>tokpatlen)
  1382. yyerror("Number within %[] out of range");
  1383. if (*s == ']') {
  1384. s++;
  1385. *p++ = PR_TOK;
  1386. *p++ = num;
  1387. } else if (*s++ != '.')
  1388. yyerror("Bad character following %%[digit in codestring");
  1389. else {
  1390. char field[256];
  1391. register char *f=field;
  1392. int type,offset;
  1393. while( *s != ']' && *s != 0)
  1394. *f++ = *s++;
  1395. *f++ = 0;
  1396. if (*s != ']')
  1397. yyerror("Unterminated %[] construction in codestring");
  1398. else
  1399. s++;
  1400. if (isdigit(field[0])) {
  1401. chkregexp(pattokexp[num]);
  1402. *p++ = PR_SUBREG;
  1403. *p++ = num;
  1404. *p++ = atoi(field);
  1405. } else {
  1406. offset = findstructel(pattokexp[num],field,&type);
  1407. *p++ = PR_TOKFLD;
  1408. *p++ = num;
  1409. *p++ = offset;
  1410. }
  1411. }
  1412. } else if (*s >= 'a' && *s < 'a'+nallreg) {
  1413. int reg,subreg;
  1414. reg = *s++ -'a'+1;
  1415. if(*s == ']')
  1416. subreg = 255;
  1417. else {
  1418. if (*s != '.')
  1419. yyerror("Bad character following %%[x in codestring");
  1420. s++;
  1421. if(!isdigit(*s))
  1422. yyerror("Bad character following %%[x. in codestring");
  1423. subreg = *s - '0';
  1424. s++;
  1425. if(*s != ']')
  1426. yyerror("Bad character following %%[x.y in codestring");
  1427. }
  1428. s++;
  1429. *p++ = PR_ALLREG;
  1430. *p++ = reg;
  1431. *p++ = subreg;
  1432. } else
  1433. yyerror("Bad character following %%[ in codestring");
  1434. }
  1435. *p++ = 0;
  1436. return(strlookup(buf));
  1437. }
  1438. tabovf(tablename) string tablename; {
  1439. char buf[256];
  1440. sprintf(buf,"%s overflow",tablename);
  1441. yyerror(buf);
  1442. exit(-1);
  1443. }
  1444. main(argc,argv) char *argv[]; {
  1445. while (--argc) {
  1446. ++argv;
  1447. if (argv[0][0]=='-') {
  1448. switch (argv[0][1]) {
  1449. case 'h':
  1450. hname= &argv[0][2];
  1451. break;
  1452. case 'c':
  1453. cname= &argv[0][2];
  1454. break;
  1455. default:
  1456. fprintf(stderr,"Bad flag %s\n",argv[0]);
  1457. break;
  1458. }
  1459. } else {
  1460. iname= argv[0];
  1461. }
  1462. }
  1463. inithash();
  1464. initio();
  1465. inittables();
  1466. yyparse();
  1467. if (nerrors==0) {
  1468. compueq();
  1469. hashpatterns();
  1470. finishio();
  1471. verbose();
  1472. }
  1473. debug();
  1474. exit(nerrors);
  1475. }
  1476. lookup(comm,operator,lnode,rnode) {
  1477. register node_p p;
  1478. for (p=nodes+1;p<lastnode;p++) {
  1479. if (p->ex_operator != operator)
  1480. continue;
  1481. if (!(p->ex_lnode == lnode && p->ex_rnode == rnode ||
  1482. comm && p->ex_lnode == rnode && p->ex_rnode == lnode))
  1483. continue;
  1484. return(p-nodes);
  1485. }
  1486. if (lastnode >= &nodes[MAXNODES])
  1487. yyerror("node table overflow");
  1488. lastnode++;
  1489. p->ex_operator = operator;
  1490. p->ex_lnode = lnode;
  1491. p->ex_rnode = rnode;
  1492. return(p-nodes);
  1493. }
  1494. compueq() {
  1495. register i,j;
  1496. for (i=1;i<nmachregs;i++) {
  1497. for (j=1;j<i;j++)
  1498. if (eqregclass(i,j)) {
  1499. stregclass[i] = stregclass[j];
  1500. break;
  1501. }
  1502. if (j==i)
  1503. stregclass[i] = nregclasses++;
  1504. }
  1505. }
  1506. eqregclass(r1,r2) {
  1507. register reginfo rp1,rp2;
  1508. register i;
  1509. short regbits[(MAXREGS+15)>>4];
  1510. int member;
  1511. rp1 = machregs[r1]; rp2 = machregs[r2];
  1512. for (i=0;i<((nprops+15)>>4);i++)
  1513. if (rp1->rprop[i] != rp2->rprop[i])
  1514. return(0);
  1515. for (i=0;i<((MAXREGS+15)>>4);i++)
  1516. regbits[i] = 0;
  1517. for (i=0;i<maxmembers;i++) {
  1518. if (member = rp1->rmembers[i])
  1519. regbits[member>>4] |= (1<<(member&017));
  1520. }
  1521. for (i=0;i<maxmembers;i++) {
  1522. member = rp2->rmembers[i];
  1523. if (regbits[member>>4]&(1<<(member&017)))
  1524. return(0);
  1525. }
  1526. return(1);
  1527. }
  1528. unsigned hash(name) register string name; {
  1529. register unsigned sum;
  1530. register i;
  1531. for (sum=i=0;*name;i+=3)
  1532. sum ^= (*name++)<<(i&07);
  1533. return(sum);
  1534. }
  1535. ident_p ilookup(name,enterf) string name; int enterf; {
  1536. register ident_p p,*pp;
  1537. pp = &identtab[hash(name)%ITABSIZE];
  1538. while (*pp != 0) {
  1539. if (strcmp((*pp)->i_name,name)==0)
  1540. if (enterf != ENTER)
  1541. return(*pp);
  1542. else
  1543. yyerror("Multiply defined symbol");
  1544. pp = &(*pp)->i_next;
  1545. }
  1546. if (enterf == LOOKUP)
  1547. yyerror("Undefined symbol");
  1548. if (enterf == JUSTLOOKING)
  1549. return(0);
  1550. p = *pp = (ident_p) myalloc(sizeof(ident_t));
  1551. p->i_name = name;
  1552. p->i_next = 0;
  1553. p->i_type = 0;
  1554. return(p);
  1555. }
  1556. initio() {
  1557. if (iname!=0 && freopen(iname,"r",stdin)==NULL) {
  1558. fprintf(stderr,"Can't open %s\n",iname);
  1559. exit(-1);
  1560. }
  1561. if ((cfile=fopen(cname,"w"))==NULL) {
  1562. fprintf(stderr,"Can't create %s\n",cname);
  1563. exit(-1);
  1564. }
  1565. if ((hfile=fopen(hname,"w"))==NULL) {
  1566. fprintf(stderr,"Can't create %s\n",hname);
  1567. exit(-1);
  1568. }
  1569. fprintf(cfile,"#include \"param.h\"\n");
  1570. fprintf(cfile,"#include \"tables.h\"\n");
  1571. fprintf(cfile,"#include \"types.h\"\n");
  1572. fprintf(cfile,"#include <cg_pattern.h>\n");
  1573. fprintf(cfile,"#include \"data.h\"\n");
  1574. fprintf(cfile,"\nbyte coderules[] = {\n");
  1575. patbyte(0);
  1576. }
  1577. exprlookup(sett) set_t sett; {
  1578. register i,j,ok;
  1579. for(i=0;i<nmachsets;i++) {
  1580. ok= (sett.set_size == machsets[i].set_size);
  1581. for(j=0;j<SETSIZE;j++) {
  1582. if (sett.set_val[j] == machsets[i].set_val[j])
  1583. continue;
  1584. ok=0;
  1585. break;
  1586. }
  1587. if (ok)
  1588. return(i);
  1589. }
  1590. chktabsiz(nmachsets,MAXSETS,"Expression table");
  1591. machsets[nmachsets] = sett;
  1592. return(nmachsets++);
  1593. }
  1594. inittables() {
  1595. register reginfo r;
  1596. register i;
  1597. inst_t inst;
  1598. set_t sett;
  1599. nodes[0].ex_operator=EX_CON;
  1600. nodes[0].ex_lnode=0;
  1601. nodes[0].ex_rnode=0;
  1602. cocopropno=nprops++;
  1603. r=(reginfo)myalloc(sizeof(struct reginfo));
  1604. r->rname = "cc reg";
  1605. r->rrepr = "CC";
  1606. r->rsize = -1;
  1607. r->rregvar= -1;
  1608. for(i=0;i<MAXMEMBERS;i++)
  1609. r->rmembers[i] = 0;
  1610. for(i=0;i<PROPSETSIZE;i++)
  1611. r->rprop[i] = 0;
  1612. r->rprop[cocopropno>>4] |= (1<<(cocopropno&017));
  1613. chktabsiz(nmachregs,MAXREGS,"Register table");
  1614. machregs[nmachregs++] = r;
  1615. inst.in_which = IN_RIDENT;
  1616. inst.in_info[0] = nmachregs-1;
  1617. for(i=1;i<TOKENSIZE;i++)
  1618. inst.in_info[i]=0;
  1619. ccinstanceno=instno(inst);
  1620. ccregexpr=lookup(0,EX_REG,nmachregs-1,0);
  1621. sett.set_size=0;
  1622. for (i=0;i<SETSIZE;i++)
  1623. sett.set_val[i]=0;
  1624. sett.set_val[nmachregs>>4] |= (01<<(nmachregs&017));
  1625. cocosetno=exprlookup(sett);
  1626. }
  1627. outregs() {
  1628. register i,j,k;
  1629. static short rset[(MAXREGS+15)>>4];
  1630. int t,ready;
  1631. fprintf(cfile,"char stregclass[] = {\n");
  1632. for (i=0;i<nmachregs;i++)
  1633. fprintf(cfile,"\t%d,\n",stregclass[i]);
  1634. fprintf(cfile,"};\n\nstruct reginfo machregs[] = {\n{0},\n");
  1635. for (i=1;i<nmachregs;i++) {
  1636. fprintf(cfile,"{%d,%d",strlookup(machregs[i]->rrepr),
  1637. machregs[i]->rsize);
  1638. if (maxmembers!=0) {
  1639. fprintf(cfile,",{");
  1640. for(j=0;j<maxmembers;j++)
  1641. fprintf(cfile,"%d,",machregs[i]->rmembers[j]);
  1642. /* now compute and print set of registers
  1643. * that clashes with this register.
  1644. * A register clashes with al its children (and theirs)
  1645. * and with all their parents.
  1646. */
  1647. for (j=0;j<((MAXREGS+15)>>4);j++)
  1648. rset[j]=0;
  1649. rset[i>>4] |= (1<<(i&017));
  1650. do {
  1651. ready=1;
  1652. for (j=1;j<nmachregs;j++)
  1653. if (rset[j>>4]&(1<<(j&017)))
  1654. for (k=0;k<maxmembers;k++)
  1655. if ((t=machregs[j]->rmembers[k])!=0) {
  1656. if ((rset[t>>4]&(1<<(t&017)))==0)
  1657. ready=0;
  1658. rset[t>>4] |= (1<<(t&017));
  1659. }
  1660. } while (!ready);
  1661. do {
  1662. ready=1;
  1663. for (j=1;j<nmachregs;j++)
  1664. for (k=0;k<maxmembers;k++)
  1665. if ((t=machregs[j]->rmembers[k])!=0)
  1666. if (rset[t>>4]&(1<<(t&017))) {
  1667. if (rset[j>>4]&(1<<(j&017))==0)
  1668. ready=0;
  1669. rset[j>>4] |= (1<<(j&017));
  1670. }
  1671. } while (!ready);
  1672. fprintf(cfile,"},{");
  1673. for (j=0;j<((nmachregs+15)>>4);j++)
  1674. fprintf(cfile,"%d,",rset[j]);
  1675. fprintf(cfile,"}");
  1676. }
  1677. if (machregs[i]->rregvar>=0)
  1678. fprintf(cfile,",1");
  1679. fprintf(cfile,"},\n");
  1680. }
  1681. fprintf(cfile,"};\n\n");
  1682. }
  1683. finishio() {
  1684. register i;
  1685. register node_p np;
  1686. int j;
  1687. int setsize;
  1688. register move_p mp;
  1689. fprintf(cfile,"};\n\n");
  1690. if (wsize>0)
  1691. fprintf(hfile,"#define TEM_WSIZE %d\n",wsize);
  1692. else
  1693. yyerror("Wordsize undefined");
  1694. if (psize>0)
  1695. fprintf(hfile,"#define TEM_PSIZE %d\n",psize);
  1696. else
  1697. yyerror("Pointersize undefined");
  1698. if (bsize>=0)
  1699. fprintf(hfile,"#define TEM_BSIZE %d\n",bsize);
  1700. else
  1701. fprintf(hfile,"extern int TEM_BSIZE;\n");
  1702. if (fmt!=0)
  1703. fprintf(hfile,"#define WRD_FMT \"%s\"\n",fmt);
  1704. fprintf(hfile,"#define MAXALLREG %d\n",maxallreg);
  1705. setsize = (nmachregs+1 + nmachtokens + 15)>>4;
  1706. fprintf(hfile,"#define SETSIZE %d\n",setsize);
  1707. fprintf(hfile,"#define NPROPS %d\n",nprops);
  1708. fprintf(hfile,"#define NREGS %d\n",nmachregs);
  1709. fprintf(hfile,"#define REGSETSIZE %d\n",(nmachregs+15)>>4);
  1710. fprintf(hfile,"#define TOKENSIZE %d\n",maxtokensize);
  1711. fprintf(hfile,"#define MAXMEMBERS %d\n",maxmembers);
  1712. fprintf(hfile,"#define LONGESTPATTERN %d\n",maxempatlen);
  1713. fprintf(hfile,"#define MAXRULE %d\n",maxrule);
  1714. fprintf(hfile,"#define NMOVES %d\n",nmoves);
  1715. fprintf(hfile,"#define NC1 %d\n",nc1);
  1716. if (nc2) {
  1717. assert(maxsplit!=0);
  1718. fprintf(hfile,"#define NC2 %d\n",nc2);
  1719. fprintf(hfile,"#define MAXSPLIT %d\n",maxsplit);
  1720. }
  1721. fprintf(hfile,"#define NC3 %d\n",nc3);
  1722. outregs();
  1723. fprintf(cfile,"tkdef_t tokens[] = {\n");
  1724. for(i=0;i<nmachtokens;i++) {
  1725. fprintf(cfile,"{%d,{%d,%d},{",machtokens[i].t_size,
  1726. machtokens[i].t_cost.c_size,
  1727. machtokens[i].t_cost.c_time);
  1728. for(j=0;j<maxtokensize;j++)
  1729. fprintf(cfile,"%d,",machtokens[i].t_fields[j].t_type);
  1730. fprintf(cfile,"},%d},\n",machtokens[i].t_format);
  1731. }
  1732. fprintf(cfile,"};\n\nnode_t enodes[] = {\n");
  1733. for(np=nodes;np<lastnode;np++)
  1734. fprintf(cfile,"{%d,%d,%d},\n",np->ex_operator,np->ex_lnode,
  1735. np->ex_rnode);
  1736. fprintf(cfile,"};\n\nstring codestrings[] = {\n");
  1737. for(i=0;i<ncodestrings;i++) {
  1738. register char *p;
  1739. p=codestrings[i];
  1740. fprintf(cfile,"\t\"");
  1741. while (*p) {
  1742. fprintf(cfile, !isascii(*p) || iscntrl(*p) ? "\\%03o" : "%c", (*p)&BMASK);
  1743. p++;
  1744. }
  1745. fprintf(cfile,"\",\n");
  1746. }
  1747. fprintf(cfile,"};\n\nset_t machsets[] = {\n");
  1748. for(i=0;i<nmachsets;i++) {
  1749. fprintf(cfile,"{%d,{",machsets[i].set_size);
  1750. for(j=0;j<setsize;j++)
  1751. fprintf(cfile,"0%o,",machsets[i].set_val[j]);
  1752. fprintf(cfile,"}},\n");
  1753. }
  1754. fprintf(cfile,"};\n\ninst_t tokeninstances[] = {\n");
  1755. for(i=0;i<narinstance;i++) {
  1756. fprintf(cfile,"{ %d, {",arinstance[i].in_which);
  1757. for(j=0;j<=maxtokensize;j++)
  1758. fprintf(cfile,"%d,",arinstance[i].in_info[j]);
  1759. fprintf(cfile,"}},\n");
  1760. }
  1761. fprintf(cfile,"};\n\nmove_t moves[] = {\n");
  1762. for (i=0;i<nmoves;i++) {
  1763. mp = &machmoves[i];
  1764. fprintf(cfile,"{%d,%d,%d,%d,%d,{%d,%d}},\n",
  1765. mp->m_set1, mp->m_expr1,
  1766. mp->m_set2, mp->m_expr2,
  1767. mp->m_cindex,
  1768. mp->m_cost.c_size,mp->m_cost.c_time);
  1769. }
  1770. fprintf(cfile,"};\n\nbyte pattern[] = {\n");
  1771. for (i=0;i<npatbytes;i++) {
  1772. fprintf(cfile,"%3d,",pattern[i]&BMASK);
  1773. if ((i%10)==9)
  1774. fprintf(cfile,"\n");
  1775. }
  1776. fprintf(cfile,"\n};\n\nint pathash[256] = {\n");
  1777. for(i=0;i<256;i++) {
  1778. fprintf(cfile,"%6d,",pathash[i]);
  1779. if((i&07)==07)
  1780. fprintf(cfile,"\n");
  1781. }
  1782. fprintf(cfile,"};\n\nc1_t c1coercs[] = {\n");
  1783. for (i=0;i<nc1;i++)
  1784. fprintf(cfile,"{%d,%d,%d,%d,{%d,%d}},\n",
  1785. c1coercs[i].c1_texpno,
  1786. c1coercs[i].c1_expr,
  1787. c1coercs[i].c1_prop,
  1788. c1coercs[i].c1_codep,
  1789. c1coercs[i].c1_cost.c_size,
  1790. c1coercs[i].c1_cost.c_time);
  1791. if (nc2)
  1792. fprintf(cfile,"};\n\nc2_t c2coercs[] = {\n");
  1793. for (i=0;i<nc2;i++) {
  1794. fprintf(cfile,"{%d,%d,{",
  1795. c2coercs[i].c2_texpno,
  1796. c2coercs[i].c2_nsplit);
  1797. for (j=0;j<maxsplit;j++)
  1798. fprintf(cfile,"%d,",c2coercs[i].c2_repl[j]);
  1799. fprintf(cfile,"},%d},\n",c2coercs[i].c2_codep);
  1800. }
  1801. fprintf(cfile,"};\n\nc3_t c3coercs[] = {\n");
  1802. for (i=0;i<nc3;i++)
  1803. fprintf(cfile,"{%d,%d,%d,%d},\n",
  1804. c3coercs[i].c3_texpno,
  1805. c3coercs[i].c3_prop,
  1806. c3coercs[i].c3_repl,
  1807. c3coercs[i].c3_codep);
  1808. fprintf(cfile,"};\n\n");
  1809. for (i=0;i<nprops;i++) {
  1810. fprintf(cfile,"struct reginfo *rlist%02d[] = {\n",i);
  1811. for (j=2;j<=nmachregs;j++) {
  1812. if (machregs[j-1]->rregvar<0 &&
  1813. (machprops[i].propset.set_val[j>>4]&(1<<(j&017))))
  1814. fprintf(cfile,"\t&machregs[%d],\n",j-1);
  1815. }
  1816. fprintf(cfile,"\t0\n};\n");
  1817. }
  1818. fprintf(cfile,"struct reginfo **reglist[] = {\n");
  1819. for (i=0;i<nprops;i++) {
  1820. fprintf(cfile,"\trlist%02d,\n",i);
  1821. }
  1822. fprintf(cfile,"};\n");
  1823. fprintf(cfile,"unsigned cc1 = %u;\n",cc1);
  1824. fprintf(cfile,"unsigned cc2 = %u;\n",cc2);
  1825. fprintf(cfile,"unsigned cc3 = %u;\n",cc3);
  1826. fprintf(cfile,"unsigned cc4 = %u;\n",cc4);
  1827. if (rvused)
  1828. outregvar();
  1829. }
  1830. outregvar() {
  1831. register i,j;
  1832. fprintf(hfile,"#define REGVARS\n");
  1833. fprintf(cfile,"#include \"regvar.h\"\n");
  1834. fprintf(cfile,"int nregvar[4] = { ");
  1835. for (i=0;i<4;i++) fprintf(cfile,"%d, ",nregvar[i]);
  1836. fprintf(cfile,"};\n");
  1837. for (i=0;i<4;i++)
  1838. if (nregvar[i]>0)
  1839. fprintf(cfile,"struct regassigned ratar%d[%d];\n",
  1840. i,nregvar[i]);
  1841. for (i=0;i<4;i++) if (nregvar[i]>0) {
  1842. fprintf(cfile,"int rvtar%d[] = {",i);
  1843. for (j=0;j<nregvar[i];j++)
  1844. fprintf(cfile,"%d,",rvnumbers[i][j]);
  1845. fprintf(cfile,"};\n");
  1846. }
  1847. fprintf(cfile,"\nint *rvnumbers[] = {\n");
  1848. for (i=0;i<4;i++)
  1849. if (nregvar[i]>0)
  1850. fprintf(cfile,"\trvtar%d,\n",i);
  1851. else
  1852. fprintf(cfile,"\t0,\n");
  1853. fprintf(cfile,"};\n\nstruct regassigned *regassigned[] = {\n");
  1854. for (i=0;i<4;i++)
  1855. if (nregvar[i]>0)
  1856. fprintf(cfile,"\tratar%d,\n",i);
  1857. else
  1858. fprintf(cfile,"\t0,\n");
  1859. fprintf(cfile,"};\n");
  1860. }
  1861. verbose() {
  1862. fprintf(stderr,"Codebytes %d\n",codebytes);
  1863. fprintf(stderr,"Registers %d(%d)\n",nmachregs,MAXREGS);
  1864. fprintf(stderr,"Properties %d(%d)\n",nprops,MAXPROPS);
  1865. fprintf(stderr,"Tokens %d(%d)\n",nmachtokens,MAXTOKENS);
  1866. fprintf(stderr,"Sets %d(%d)\n",nmachsets,MAXSETS);
  1867. fprintf(stderr,"Tokeninstances %d(%d)\n",narinstance,MAXINSTANCE);
  1868. fprintf(stderr,"Strings %d(%d)\n",ncodestrings,MAXSTRINGS);
  1869. fprintf(stderr,"Enodes %d(%d)\n",lastnode-nodes,MAXNODES);
  1870. fprintf(stderr,"Patbytes %d(%d)\n",npatbytes,MAXPATTERN);
  1871. }
  1872. inbetween() {
  1873. register ident_p ip;
  1874. register i,j;
  1875. register move_p mp;
  1876. lookident=1; /* for lexical analysis */
  1877. chktabsiz(nmachsets+1,MAXSETS,"Expressiontable");
  1878. for (i=0;i<SETSIZE;i++)
  1879. machsets[nmachsets].set_val[i] = 0xFFFF;
  1880. machsets[nmachsets].set_val[0] &= ~1;
  1881. machsets[nmachsets].set_size = 0;
  1882. ip=ilookup("SCRATCH",ENTER);
  1883. ip->i_type=IEXP;
  1884. ip->i_i.i_expno = nmachsets++;
  1885. for (i=0;i<SETSIZE;i++)
  1886. machsets[nmachsets].set_val[i] = 0xFFFF;
  1887. machsets[nmachsets].set_size = 0;
  1888. ip=ilookup("ALL",ENTER);
  1889. ip->i_type=IEXP;
  1890. allexpno = ip->i_i.i_expno = nmachsets++;
  1891. mp = &machmoves[nmoves++];
  1892. mp->m_set1 = cocosetno;
  1893. mp->m_expr1 = 0;
  1894. mp->m_set2 = nmachsets-1;
  1895. mp->m_expr2 = 0;
  1896. mp->m_cindex = 0;
  1897. mp->m_cost.c_size = 0;
  1898. mp->m_cost.c_time = 0;
  1899. /*
  1900. * Create sets of registers per property
  1901. */
  1902. for (i=0;i<nprops;i++) {
  1903. short *sp = machprops[i].propset.set_val;
  1904. sp[0] |= 1;
  1905. for (j=2;j<=nmachregs;j++)
  1906. if (machregs[j-1]->rprop[i>>4]&(1<<(i&017)))
  1907. sp[j>>4] |= (1<<(j&017));
  1908. }
  1909. }
  1910. formconversion(p,tp) register char *p; register token_p tp; {
  1911. char buf[256];
  1912. register char *q=buf;
  1913. char field[256];
  1914. register char *f;
  1915. int i;
  1916. if (p==0)
  1917. return(0);
  1918. while (*p) switch(*p) {
  1919. default: *q++ = *p++; continue;
  1920. case '%':
  1921. p++;
  1922. if(*p == '%') {
  1923. *q++ = *p++;
  1924. continue;
  1925. }
  1926. if (*p == '[')
  1927. p++;
  1928. else
  1929. yyerror("Bad character after % in format");
  1930. f=field;
  1931. while (*p != 0 && *p != ']')
  1932. *f++ = *p++;
  1933. *f++ = 0;
  1934. if (*p == ']')
  1935. p++;
  1936. else
  1937. yyerror("Unterminated %[] construct in format");
  1938. for (i=0;i<TOKENSIZE-1;i++)
  1939. if (strcmp(field,tp->t_fields[i].t_sname)==0)
  1940. break;
  1941. if (i==TOKENSIZE-1)
  1942. yyerror("Unknown field in %[] construct in format");
  1943. *q++ = i+1;
  1944. }
  1945. *q++ = 0;
  1946. return(strlookup(buf));
  1947. }
  1948. setfields(tp,format) register token_p tp; string format; {
  1949. register i;
  1950. list2 ll;
  1951. register list1 l;
  1952. int type;
  1953. for(i=0;i<TOKENSIZE-1;i++)
  1954. tp->t_fields[i].t_type = 0;
  1955. i=0;
  1956. for(ll=tp->t_struct;ll!=0;ll=ll->l2next) {
  1957. l=ll->l2list;
  1958. if(strcmp(l->l1name,"REGISTER")==0)
  1959. type = TYPREG;
  1960. else if (strcmp(l->l1name,"INT")==0)
  1961. type = TYPINT;
  1962. else type = TYPSTR;
  1963. for(l=l->l1next;l!=0;l=l->l1next) {
  1964. tp->t_fields[i].t_type = type;
  1965. tp->t_fields[i].t_sname = l->l1name;
  1966. i++;
  1967. }
  1968. }
  1969. if (format != 0)
  1970. tp->t_format = formconversion(format,tp);
  1971. else
  1972. tp->t_format = -1;
  1973. }
  1974. chkregexp(number) {
  1975. register i;
  1976. for(i=nmachregs+1;i<nmachregs+1+nmachtokens;i++)
  1977. if(machsets[number].set_val[i>>4]&(01<<(i&017)))
  1978. yyerror("No tokens allowed in this set");
  1979. }
  1980. findstructel(number,name,t) string name; int *t; {
  1981. register i;
  1982. register token_p tp;
  1983. register list2 structdecl;
  1984. int offset;
  1985. for(i=1;i<=nmachregs;i++)
  1986. if (machsets[number].set_val[i>>4]&(01<<(i&017)))
  1987. yyerror("No registers allowed in this set");
  1988. structdecl = 0;
  1989. for (i=nmachregs+1;i<nmachregs+1+nmachtokens;i++) {
  1990. if (machsets[number].set_val[i>>4]&(01<<(i&017))) {
  1991. if (structdecl == 0) {
  1992. structdecl = machtokens[i-(nmachregs+1)].t_struct;
  1993. tp = &machtokens[i-(nmachregs+1)];
  1994. } else if(structdecl != machtokens[i-(nmachregs+1)].t_struct)
  1995. yyerror("Multiple structs in this set");
  1996. }
  1997. }
  1998. if (structdecl == 0) {
  1999. yyerror("No structs in this set");
  2000. return(0);
  2001. }
  2002. for(offset=0;offset<TOKENSIZE-1;offset++)
  2003. if(tp->t_fields[offset].t_type != 0 &&
  2004. strcmp(tp->t_fields[offset].t_sname,name)==0) {
  2005. *t = tp->t_fields[offset].t_type;
  2006. return(offset+1);
  2007. }
  2008. yyerror("No such field in this struct");
  2009. return(0);
  2010. }
  2011. extern char em_flag[];
  2012. argtyp(mn) {
  2013. switch(em_flag[mn-sp_fmnem]&EM_PAR) {
  2014. case PAR_W:
  2015. case PAR_S:
  2016. case PAR_Z:
  2017. case PAR_O:
  2018. case PAR_N:
  2019. case PAR_L:
  2020. case PAR_F:
  2021. case PAR_R:
  2022. case PAR_C:
  2023. return(TYPINT);
  2024. default:
  2025. return(TYPSTR);
  2026. }
  2027. }
  2028. commontype(e1,e2) expr_t e1,e2; {
  2029. if(e1.expr_typ != e2.expr_typ)
  2030. yyerror("Type incompatibility");
  2031. return(e1.expr_typ);
  2032. }
  2033. extern char em_mnem[][4];
  2034. #define HASHSIZE (2*(sp_lmnem-sp_fmnem))
  2035. struct hashmnem {
  2036. char h_name[3];
  2037. byte h_value;
  2038. } hashmnem[HASHSIZE];
  2039. inithash() {
  2040. register i;
  2041. for(i=0;i<=sp_lmnem-sp_fmnem;i++)
  2042. enter(em_mnem[i],i+sp_fmnem);
  2043. }
  2044. enter(name,value) char *name; {
  2045. register unsigned h;
  2046. h=hash(name)%HASHSIZE;
  2047. while (hashmnem[h].h_name[0] != 0)
  2048. h = (h+1)%HASHSIZE;
  2049. strncpy(hashmnem[h].h_name,name,3);
  2050. hashmnem[h].h_value = value;
  2051. }
  2052. int mlookup(name) char *name; {
  2053. register unsigned h;
  2054. h = hash(name)%HASHSIZE;
  2055. while (strncmp(hashmnem[h].h_name,name,3) != 0 &&
  2056. hashmnem[h].h_name[0] != 0)
  2057. h = (h+1)%HASHSIZE;
  2058. return(hashmnem[h].h_value&BMASK); /* 0 if not found */
  2059. }
  2060. hashpatterns() {
  2061. short index;
  2062. register byte *bp,*tp;
  2063. register short i;
  2064. unsigned short hashvalue;
  2065. int patlen;
  2066. index = prevind;
  2067. while (index != 0) {
  2068. bp = &pattern[index];
  2069. tp = &bp[PO_MATCH];
  2070. i = *tp++&BMASK;
  2071. if (i==BMASK) {
  2072. i = *tp++&BMASK;
  2073. i |= (*tp++&BMASK)<<BSHIFT;
  2074. }
  2075. patlen = i;
  2076. hashvalue = 0;
  2077. switch(patlen) {
  2078. default: /* 3 or more */
  2079. hashvalue = (hashvalue<<4)^(*tp++&BMASK);
  2080. case 2:
  2081. hashvalue = (hashvalue<<4)^(*tp++&BMASK);
  2082. case 1:
  2083. hashvalue = (hashvalue<<4)^(*tp++&BMASK);
  2084. }
  2085. assert(hashvalue!= ILLHASH);
  2086. i=index;
  2087. index = (bp[PO_NEXT]&BMASK)|(bp[PO_NEXT+1]<<BSHIFT);
  2088. bp[PO_HASH] = hashvalue>>BSHIFT;
  2089. hashvalue &= BMASK;
  2090. bp[PO_NEXT] = pathash[hashvalue]&BMASK;
  2091. bp[PO_NEXT+1] = pathash[hashvalue]>>BSHIFT;
  2092. pathash[hashvalue] = i;
  2093. }
  2094. }
  2095. debug() {
  2096. register i,j;
  2097. for(i=0;i<ITABSIZE;i++) {
  2098. register ident_p ip;
  2099. for(ip=identtab[i];ip!=0;ip=ip->i_next)
  2100. printf("%-14s %1d %3d\n",ip->i_name,
  2101. ip->i_type,ip->i_i.i_regno);
  2102. }
  2103. for(i=2;i<nmachregs;i++) {
  2104. register reginfo rp;
  2105. rp=machregs[i];
  2106. printf("%s = (\"%s\", %d",rp->rname,rp->rrepr,rp->rsize);
  2107. for(j=0;j<MAXMEMBERS;j++)
  2108. if(rp->rmembers[j] != 0)
  2109. printf(", %s",machregs[rp->rmembers[j]]->rname);
  2110. printf(")");
  2111. for(j=0;j<nprops;j++)
  2112. if(rp->rprop[j>>4]&(1<<(j&017)))
  2113. printf(", %s",machprops[j].propname->i_name);
  2114. printf(".\n");
  2115. }
  2116. }
  2117. out(n) {
  2118. assert(n>=0);
  2119. if (n<128)
  2120. outbyte(n);
  2121. else {
  2122. outbyte(n/256+128);
  2123. outbyte(n%256);
  2124. }
  2125. }
  2126. outbyte(n) {
  2127. fprintf(cfile,"%d, ",n&BMASK);
  2128. codebytes++;
  2129. }
  2130. pat(n) {
  2131. assert(n>=0);
  2132. if (n<128)
  2133. patbyte(n);
  2134. else {
  2135. patbyte(n/256+128);
  2136. patbyte(n%256);
  2137. }
  2138. }
  2139. patshort(n) {
  2140. patbyte(n&BMASK);
  2141. patbyte(n>>BSHIFT);
  2142. }
  2143. patbyte(n) {
  2144. chktabsiz(npatbytes,MAXPATTERN,"Pattern table");
  2145. pattern[npatbytes++] = n;
  2146. }
  2147. max(a,b) {
  2148. if (a>b)
  2149. return(a);
  2150. return(b);
  2151. }
  2152. #include "bootlex.c"