RT-AC56 3.0.0.4.374.37 core
[tomato.git] / release / src-rt-6.x.4708 / cfe / cfe / hosttools / makereg.c
blobc49b485441ad37b944b3d8aa51063b82d5f9f9f6
1 /* *********************************************************************
2 * Broadcom Common Firmware Environment (CFE)
4 * Register Table Generator File: makereg.c
5 *
6 * Author: Mitch Lichtenberg (mpl@broadcom.com)
7 *
8 * Warning: don't eat your lunch before reading this program.
9 * It's nasty!
11 * This program generates tables of SOC registers and values
12 * that are easy for us to display.
14 *********************************************************************
16 * Copyright 2000,2001,2002,2003
17 * Broadcom Corporation. All rights reserved.
19 * This software is furnished under license and may be used and
20 * copied only in accordance with the following terms and
21 * conditions. Subject to these conditions, you may download,
22 * copy, install, use, modify and distribute modified or unmodified
23 * copies of this software in source and/or binary form. No title
24 * or ownership is transferred hereby.
26 * 1) Any source code used, modified or distributed must reproduce
27 * and retain this copyright notice and list of conditions
28 * as they appear in the source file.
30 * 2) No right is granted to use any trade name, trademark, or
31 * logo of Broadcom Corporation. The "Broadcom Corporation"
32 * name may not be used to endorse or promote products derived
33 * from this software without the prior written permission of
34 * Broadcom Corporation.
36 * 3) THIS SOFTWARE IS PROVIDED "AS-IS" AND ANY EXPRESS OR
37 * IMPLIED WARRANTIES, INCLUDING BUT NOT LIMITED TO, ANY IMPLIED
38 * WARRANTIES OF MERCHANTABILITY, FITNESS FOR A PARTICULAR
39 * PURPOSE, OR NON-INFRINGEMENT ARE DISCLAIMED. IN NO EVENT
40 * SHALL BROADCOM BE LIABLE FOR ANY DAMAGES WHATSOEVER, AND IN
41 * PARTICULAR, BROADCOM SHALL NOT BE LIABLE FOR DIRECT, INDIRECT,
42 * INCIDENTAL, SPECIAL, EXEMPLARY, OR CONSEQUENTIAL DAMAGES
43 * (INCLUDING, BUT NOT LIMITED TO, PROCUREMENT OF SUBSTITUTE
44 * GOODS OR SERVICES; LOSS OF USE, DATA, OR PROFITS; OR
45 * BUSINESS INTERRUPTION) HOWEVER CAUSED AND ON ANY THEORY
46 * OF LIABILITY, WHETHER IN CONTRACT, STRICT LIABILITY, OR
47 * TORT (INCLUDING NEGLIGENCE OR OTHERWISE), EVEN IF ADVISED OF
48 * THE POSSIBILITY OF SUCH DAMAGE.
49 ********************************************************************* */
51 #include <stdio.h>
52 #include <string.h>
53 #include <malloc.h>
54 #include <stdlib.h>
56 #if defined(_MSC_VER) || defined(__CYGWIN__)
57 #define TEXTMODE "t"
58 #else
59 #define TEXTMODE ""
60 #endif
62 typedef struct Cons {
63 char *str;
64 int num;
65 } CONS;
67 typedef struct RegInfo {
68 unsigned long reg_mask;
69 char *reg_agent;
70 int reg_agentidx;
71 char *reg_addr;
72 char *reg_inst;
73 char *reg_subinst;
74 char *reg_printfunc;
75 char *reg_description;
76 } REGINFO;
78 typedef struct ConstInfo {
79 char *name;
80 unsigned int value;
81 } CONSTINFO;
83 #define MAXCONST 64
84 CONSTINFO constants[MAXCONST];
85 int constcnt = 0;
87 #define MAXREGS 2000
88 REGINFO allregs[MAXREGS];
89 int regcnt = 0;
91 int maskcnt = 0;
93 #define MAXAGENTS 32
94 char *agentnames[MAXAGENTS];
95 int agentcnt;
97 #define CMD_AGENT 1
98 #define CMD_ENDAGENT 2
100 CONS commands[] = {
101 {"!agent",CMD_AGENT},
102 {"!endagent",CMD_ENDAGENT},
103 {NULL,0}};
106 int assoc(CONS *list,char *str)
108 while (list->str) {
109 if (strcmp(list->str,str) == 0) return list->num;
110 list++;
113 return -1;
116 char *gettoken(char **ptr)
118 char *p = *ptr;
119 char *ret;
121 /* skip white space */
123 while (*p && isspace(*p)) p++;
124 ret = p;
126 /* check for end of string */
128 if (!*p) {
129 *ptr = p;
130 return NULL;
133 /* skip non-whitespace */
135 while (*p) {
136 if (isspace(*p)) break;
138 /* do quoted strings */
140 if (*p == '"') {
141 p++;
142 ret = p;
143 while (*p && (*p != '"')) p++;
144 if (*p == '"') *p = '\0';
147 p++;
151 if (*p) {
152 *p++ = '\0';
154 *ptr = p;
156 return ret;
159 static int readline(FILE *str,char *dest,int destlen)
161 char *x;
163 for (;;) {
164 if (!fgets(dest,destlen,str)) return -1;
165 if (x = strchr(dest,'\n')) *x = '\0';
166 if (dest[0] == '\0') continue;
167 if (dest[0] == ';') continue;
168 break;
171 return 0;
175 static void fatal(char *str,char *val)
177 fprintf(stderr,"fatal error: %s %s\n",str,val ? val : "");
178 exit(1);
181 static unsigned int newmask(void)
183 int res;
185 res = maskcnt;
187 if (maskcnt == 32) {
188 fatal("Out of mask bits",NULL);
191 maskcnt++;
193 return 1<<res;
196 static void addconst(char *name,unsigned int val)
198 if (constcnt == MAXCONST) {
199 fatal("Out of constant space",NULL);
202 constants[constcnt].name = strdup(name);
203 constants[constcnt].value = val;
205 constcnt++;
208 static void addreg(
209 char *agentname,
210 int agentidx,
211 unsigned long mask,
212 char *addr,
213 char *inst,
214 char *subinst,
215 char *printfunc,
216 char *description)
218 allregs[regcnt].reg_mask = mask;
219 allregs[regcnt].reg_addr = strdup(addr);
220 allregs[regcnt].reg_agent = strdup(agentname);
221 allregs[regcnt].reg_agentidx = agentidx;
222 allregs[regcnt].reg_inst = strdup(inst);
223 allregs[regcnt].reg_subinst = strdup(subinst);
224 allregs[regcnt].reg_printfunc = strdup(printfunc);
225 allregs[regcnt].reg_description = strdup(description);
226 regcnt++;
230 static void macroexpand(char *instr,char *exp,char *outstr)
232 while (*instr) {
233 if (*instr == '$') {
234 strcpy(outstr,exp);
235 outstr += strlen(outstr);
236 instr++;
238 else {
239 *outstr++ = *instr++;
243 *outstr = '\0';
247 static void doagentcmd(FILE *str,char *line)
249 char *agentname;
250 char *instances;
251 char *inst;
252 char *ptr;
253 char regline[500];
254 char cumlname[100];
255 REGINFO regs[100];
256 char temp[20];
257 int rmax = 0;
258 int idx;
259 unsigned int cumlmask;
260 int agentidx;
262 agentname = gettoken(&line);
263 instances = gettoken(&line);
264 if (!instances) {
265 strcpy(temp,"*");
266 instances = temp;
269 fprintf(stderr,"Agent %s Instances %s\n",agentname,instances);
271 if (agentcnt == MAXAGENTS) {
272 fatal("Out of agent slots\n",NULL);
275 agentnames[agentcnt] = strdup(agentname);
276 agentidx = agentcnt;
277 agentcnt++;
279 regline[0] = '\0';
281 while ((readline(str,regline,sizeof(regline)) >= 0) && (rmax < 100)) {
282 char *atext,*subinst,*pfunc,*descr;
284 if (regline[0] == '!') break;
286 ptr = regline;
287 atext = gettoken(&ptr);
288 subinst = gettoken(&ptr);
289 pfunc = gettoken(&ptr);
290 descr = gettoken(&ptr);
292 if (!descr) {
293 fatal("Missing fields for ",atext);
296 regs[rmax].reg_addr = strdup(atext);
297 regs[rmax].reg_subinst = strdup(subinst);
298 regs[rmax].reg_printfunc = strdup(pfunc);
299 regs[rmax].reg_description = strdup(descr);
300 regs[rmax].reg_mask = 0;
301 rmax++;
304 if (rmax == 100) fatal("Too many registers in section ",agentname);
306 inst = strtok(instances,",");
308 cumlmask = 0;
309 while (inst) {
310 char defname[100];
311 unsigned int curmask;
313 sprintf(defname,"SOC_AGENT_%s%s",
314 agentname,inst[0] == '*' ? "" : inst);
316 curmask = newmask();
317 cumlmask |= curmask;
319 addconst(defname,curmask);
321 for (idx = 0; idx < rmax; idx++) {
322 char descr[100];
323 char atext[200];
325 macroexpand(regs[idx].reg_addr,inst,atext);
326 strcpy(descr,regs[idx].reg_description);
328 addreg(agentname,
329 agentidx,
330 curmask,
331 atext,
332 inst,
333 regs[idx].reg_subinst,
334 regs[idx].reg_printfunc,
335 descr);
337 inst = strtok(NULL,",");
340 if (instances[0] != '*') {
341 sprintf(cumlname,"SOC_AGENT_%s",agentname);
342 addconst(cumlname,cumlmask);
346 static void docommand(FILE *str,char *line)
348 char *cmd;
350 cmd = gettoken(&line);
351 if (!cmd) return;
353 switch (assoc(commands,cmd)) {
354 case CMD_AGENT:
355 doagentcmd(str,line);
356 break;
357 default:
358 fatal("Invalid command",cmd);
359 break;
364 static int ingestfile(FILE *str)
366 char line[500];
368 while (readline(str,line,sizeof(line)) >= 0) {
369 if (line[0] == '!') {
370 docommand(str,line);
372 else {
373 fatal("Command string required before register data",NULL);
379 void saveincfile(char *fname)
381 FILE *str;
382 int idx;
384 str = fopen(fname,"w" TEXTMODE);
385 if (!str) {
386 perror(fname);
387 exit(1);
390 fprintf(str,"\n\n");
392 fprintf(str,"#ifndef %s\n",constants[0].name);
393 for (idx = 0; idx < constcnt; idx++) {
394 fprintf(str,"#define %s 0x%08X\n",constants[idx].name,
395 constants[idx].value);
397 fprintf(str,"#endif\n");
399 fprintf(str,"\n\n");
401 fprintf(str,"#ifdef _CFE_\n");
402 fprintf(str,"#ifdef __ASSEMBLER__\n");
403 fprintf(str,"\t.globl socstatetable\n");
404 fprintf(str,"socstatetable:\n");
405 for (idx = 0; idx < regcnt; idx++) {
406 fprintf(str,"\t\t.word 0x%08X,%s\n",
407 allregs[idx].reg_mask,allregs[idx].reg_addr);
409 fprintf(str,"\t\t.word 0,0\n");
410 fprintf(str,"#endif\n");
412 fprintf(str,"\n\n");
413 fprintf(str,"#ifndef __ASSEMBLER__\n");
415 /* Addr Agent Inst Subinst Mask Printfunc Descr */
417 fprintf(str,"char *socagents[] = {\n");
418 for (idx = 0; idx < agentcnt; idx++) {
419 fprintf(str,"\t\"%s\",\n",agentnames[idx]);
421 fprintf(str,"\tNULL};\n\n");
423 fprintf(str,"const socreg_t socregs[] = {\n");
424 for (idx = 0; idx < regcnt; idx++) {
425 fprintf(str," {%s,%d,\"%s\",\"%s\",\n 0x%08X,%s,\"%s\"},\n",
426 allregs[idx].reg_addr,
427 allregs[idx].reg_agentidx,
428 allregs[idx].reg_inst,
429 allregs[idx].reg_subinst,
430 allregs[idx].reg_mask,
431 allregs[idx].reg_printfunc,
432 allregs[idx].reg_description);
434 fprintf(str," {0,0,NULL,NULL,0,NULL,NULL}};\n\n");
436 fprintf(str,"#endif\n");
437 fprintf(str,"#endif\n");
438 fclose(str);
441 int main(int argc,char *argv[])
443 FILE *str;
444 int idx;
446 if (argc != 3) {
447 fprintf(stderr,"usage: makereg inputfile outputfile\n");
448 exit(1);
451 str = fopen(argv[1],"r" TEXTMODE);
453 if (!str) {
454 perror(argv[1]);
455 exit(1);
458 ingestfile(str);
460 fclose(str);
462 fprintf(stderr,"Total registers: %d\n",regcnt);
464 saveincfile(argv[2]);
466 exit(0);
467 return 0;