tprint.c - plan9port - [fork] Plan 9 from user space
git clone git://src.adamsgaard.dk/plan9port
Log
Files
Refs
README
LICENSE
---
tprint.c (7127B)
---
     1 #include 
     2 #include 
     3 #include 
     4 #include 
     5 #include 
     6 #define Extern extern
     7 #include "acid.h"
     8 
     9 static char *binop[NUMO];
    10 
    11 static void
    12 initbinop(void)
    13 {
    14         binop[OMUL]=        "*";
    15         binop[ODIV]=        "/";
    16         binop[OMOD]=        "%";
    17         binop[OADD]=        "+";
    18         binop[OSUB]=        "-";
    19         binop[ORSH]=        ">>";
    20         binop[OLSH]=        "<<";
    21         binop[OLT]=        "<";
    22         binop[OGT]=        ">";
    23         binop[OLEQ]=        "<=";
    24         binop[OGEQ]=        ">=";
    25         binop[OEQ]=        "==";
    26         binop[ONEQ]=        "!=";
    27         binop[OLAND]=        "&";
    28         binop[OXOR]=        "^";
    29         binop[OLOR]=        "|";
    30         binop[OCAND]=        "&&";
    31         binop[OCOR]=        "||";
    32         binop[OASGN]=        " = ";
    33 }
    34 
    35 static char *tabs = "\t\t\t\t\t\t\t\t\t\t\t\t\t\t\t\t";
    36 char *typenames[] = {
    37         "integer",
    38         "float",
    39         "string",
    40         "list",
    41         "code"
    42 };
    43 
    44 void
    45 initprint(void)
    46 {
    47         initbinop();
    48 }
    49 
    50 int
    51 cmp(const void *va, const void *vb)
    52 {
    53         char **a = (char**)va;
    54         char **b = (char**)vb;
    55 
    56         return strcmp(*a, *b);
    57 }
    58 
    59 void
    60 fundefs(void)
    61 {
    62         Lsym *l;
    63         char **vec;
    64         int i, j, n, max, col, f, g, s;
    65 
    66         max = 0;
    67         f = 0;
    68         g = 100;
    69         vec = malloc(sizeof(char*)*g);
    70         if(vec == 0)
    71                 fatal("out of memory");
    72 
    73         for(i = 0; i < Hashsize; i++) {
    74                 for(l = hash[i]; l; l = l->hash) {
    75                         if(l->proc == 0 && l->builtin == 0)
    76                                 continue;
    77                         n = strlen(l->name);
    78                         if(n > max)
    79                                 max = n;
    80                         if(f >= g) {
    81                                 g *= 2;
    82                                 vec = realloc(vec, sizeof(char*)*g);
    83                                 if(vec == 0)
    84                                         fatal("out of memory");
    85                         }
    86                         vec[f++] = l->name;
    87                 }
    88         }
    89         qsort(vec, f, sizeof(char*), cmp);
    90         max++;
    91         col = 60/max;
    92         s = (f+col-1)/col;
    93 
    94         for(i = 0; i < s; i++) {
    95                 for(j = i; j < f; j += s)
    96                         Bprint(bout, "%-*s", max, vec[j]);
    97                 Bprint(bout, "\n");
    98         }
    99 }
   100 
   101 void
   102 whatis(Lsym *l)
   103 {
   104         int t;
   105         int def;
   106         Type *ti;
   107 
   108         if(l == 0) {
   109                 fundefs();
   110                 return;
   111         }
   112 
   113         def = 0;
   114         if(l->v->set) {
   115                 t = l->v->type;
   116                 Bprint(bout, "%s variable", typenames[t]);
   117                 if(t == TINT || t == TFLOAT)
   118                         Bprint(bout, " format %c", l->v->store.fmt);
   119                 if(l->v->store.comt)
   120                         Bprint(bout, " complex %s",
   121                                                 l->v->store.comt->base->name);
   122                 Bputc(bout, '\n');
   123                 def = 1;
   124         }
   125         if(l->lt) {
   126                 Bprint(bout, "complex %s {\n", l->name);
   127                 for(ti = l->lt; ti; ti = ti->next) {
   128                         if(ti->type) {
   129                                 if(ti->fmt == 'a') {
   130                                         Bprint(bout, "\t%s %d %s;\n",
   131                                         ti->type->name, ti->offset,
   132                                         ti->tag->name);
   133                                 }
   134                                 else {
   135                                         Bprint(bout, "\t'%c' %s %d %s;\n",
   136                                         ti->fmt, ti->type->name, ti->offset,
   137                                         ti->tag->name);
   138                                 }
   139                         }
   140                         else
   141                                 Bprint(bout, "\t'%c' %d %s;\n",
   142                                 ti->fmt, ti->offset, ti->tag->name);
   143                 }
   144                 Bprint(bout, "};\n");
   145                 def = 1;
   146         }
   147         if(l->proc) {
   148                 Bprint(bout, "defn %s(", l->name);
   149                 pexpr(l->proc->left);
   150                 Bprint(bout, ") {\n");
   151                 pcode(l->proc->right, 1);
   152                 Bprint(bout, "}\n");
   153                 def = 1;
   154         }
   155         if(l->builtin) {
   156                 Bprint(bout, "builtin function\n");
   157                 def = 1;
   158         }
   159         if(def == 0)
   160                 Bprint(bout, "%s is undefined\n", l->name);
   161 }
   162 
   163 void
   164 slist(Node *n, int d)
   165 {
   166         if(n == 0)
   167                 return;
   168         if(n->op == OLIST)
   169                 Bprint(bout, "%.*s{\n", d-1, tabs);
   170         pcode(n, d);
   171         if(n->op == OLIST)
   172                 Bprint(bout, "%.*s}\n", d-1, tabs);
   173 }
   174 
   175 void
   176 pcode(Node *n, int d)
   177 {
   178         Node *r, *l;
   179 
   180         if(n == 0)
   181                 return;
   182 
   183         r = n->right;
   184         l = n->left;
   185 
   186         switch(n->op) {
   187         default:
   188                 Bprint(bout, "%.*s", d, tabs);
   189                 pexpr(n);
   190                 Bprint(bout, ";\n");
   191                 break;
   192         case OLIST:
   193                 pcode(n->left, d);
   194                 pcode(n->right, d);
   195                 break;
   196         case OLOCAL:
   197                 Bprint(bout, "%.*slocal", d, tabs);
   198                 while(l) {
   199                         Bprint(bout, " %s", l->sym->name);
   200                         l = l->left;
   201                         if(l == 0)
   202                                 Bprint(bout, ";\n");
   203                         else
   204                                 Bprint(bout, ",");
   205                 }
   206                 break;
   207         case OCOMPLEX:
   208                 Bprint(bout, "%.*scomplex %s %s;\n", d, tabs, n->sym->name, l->sym->name);
   209                 break;
   210         case OIF:
   211                 Bprint(bout, "%.*sif ", d, tabs);
   212                 pexpr(l);
   213                 d++;
   214                 Bprint(bout, " then\n");
   215                 if(r && r->op == OELSE) {
   216                         slist(r->left, d);
   217                         Bprint(bout, "%.*selse\n", d-1, tabs);
   218                         slist(r->right, d);
   219                 }
   220                 else
   221                         slist(r, d);
   222                 break;
   223         case OWHILE:
   224                 Bprint(bout, "%.*swhile ", d, tabs);
   225                 pexpr(l);
   226                 d++;
   227                 Bprint(bout, " do\n");
   228                 slist(r, d);
   229                 break;
   230         case ORET:
   231                 Bprint(bout, "%.*sreturn ", d, tabs);
   232                 pexpr(l);
   233                 Bprint(bout, ";\n");
   234                 break;
   235         case ODO:
   236                 Bprint(bout, "%.*sloop ", d, tabs);
   237                 pexpr(l->left);
   238                 Bprint(bout, ", ");
   239                 pexpr(l->right);
   240                 Bprint(bout, " do\n");
   241                 slist(r, d+1);
   242         }
   243 }
   244 
   245 void
   246 pexpr(Node *n)
   247 {
   248         Node *r, *l;
   249 
   250         if(n == 0)
   251                 return;
   252 
   253         r = n->right;
   254         l = n->left;
   255 
   256         switch(n->op) {
   257         case ONAME:
   258                 Bprint(bout, "%s", n->sym->name);
   259                 break;
   260         case OCONST:
   261                 switch(n->type) {
   262                 case TINT:
   263                         Bprint(bout, "%d", (int)n->store.u.ival);
   264                         break;
   265                 case TFLOAT:
   266                         Bprint(bout, "%g", n->store.u.fval);
   267                         break;
   268                 case TSTRING:
   269                         pstr(n->store.u.string);
   270                         break;
   271                 case TLIST:
   272                         break;
   273                 }
   274                 break;
   275         case OMUL:
   276         case ODIV:
   277         case OMOD:
   278         case OADD:
   279         case OSUB:
   280         case ORSH:
   281         case OLSH:
   282         case OLT:
   283         case OGT:
   284         case OLEQ:
   285         case OGEQ:
   286         case OEQ:
   287         case ONEQ:
   288         case OLAND:
   289         case OXOR:
   290         case OLOR:
   291         case OCAND:
   292         case OCOR:
   293                 Bputc(bout, '(');
   294                 pexpr(l);
   295                 Bprint(bout, binop[(uchar)n->op]);
   296                 pexpr(r);
   297                 Bputc(bout, ')');
   298                 break;
   299         case OASGN:
   300                 pexpr(l);
   301                 Bprint(bout, binop[(uchar)n->op]);
   302                 pexpr(r);
   303                 break;
   304         case OINDM:
   305                 Bprint(bout, "*");
   306                 pexpr(l);
   307                 break;
   308         case OEDEC:
   309                 Bprint(bout, "--");
   310                 pexpr(l);
   311                 break;
   312         case OEINC:
   313                 Bprint(bout, "++");
   314                 pexpr(l);
   315                 break;
   316         case OPINC:
   317                 pexpr(l);
   318                 Bprint(bout, "++");
   319                 break;
   320         case OPDEC:
   321                 pexpr(l);
   322                 Bprint(bout, "--");
   323                 break;
   324         case ONOT:
   325                 Bprint(bout, "!");
   326                 pexpr(l);
   327                 break;
   328         case OLIST:
   329                 pexpr(l);
   330                 if(r) {
   331                         Bprint(bout, ",");
   332                         pexpr(r);
   333                 }
   334                 break;
   335         case OCALL:
   336                 pexpr(l);
   337                 Bprint(bout, "(");
   338                 pexpr(r);
   339                 Bprint(bout, ")");
   340                 break;
   341         case OCTRUCT:
   342                 Bprint(bout, "{");
   343                 pexpr(l);
   344                 Bprint(bout, "}");
   345                 break;
   346         case OHEAD:
   347                 Bprint(bout, "head ");
   348                 pexpr(l);
   349                 break;
   350         case OTAIL:
   351                 Bprint(bout, "tail ");
   352                 pexpr(l);
   353                 break;
   354         case OAPPEND:
   355                 Bprint(bout, "append ");
   356                 pexpr(l);
   357                 Bprint(bout, ",");
   358                 pexpr(r);
   359                 break;
   360         case ODELETE:
   361                 Bprint(bout, "delete ");
   362                 pexpr(l);
   363                 Bprint(bout, ",");
   364                 pexpr(r);
   365                 break;
   366         case ORET:
   367                 Bprint(bout, "return ");
   368                 pexpr(l);
   369                 break;
   370         case OINDEX:
   371                 pexpr(l);
   372                 Bprint(bout, "[");
   373                 pexpr(r);
   374                 Bprint(bout, "]");
   375                 break;
   376         case OINDC:
   377                 Bprint(bout, "@");
   378                 pexpr(l);
   379                 break;
   380         case ODOT:
   381                 pexpr(l);
   382                 Bprint(bout, ".%s", n->sym->name);
   383                 break;
   384         case OFRAME:
   385                 Bprint(bout, "%s:%s", n->sym->name, l->sym->name);
   386                 break;
   387         case OCAST:
   388                 Bprint(bout, "(%s)", n->sym->name);
   389                 pexpr(l);
   390                 break;
   391         case OFMT:
   392                 pexpr(l);
   393                 Bprint(bout, "\\%c", (int)r->store.u.ival);
   394                 break;
   395         case OEVAL:
   396                 Bprint(bout, "eval ");
   397                 pexpr(l);
   398                 break;
   399         case OWHAT:
   400                 Bprint(bout, "whatis");
   401                 if(n->sym)
   402                         Bprint(bout, " %s", n->sym->name);
   403                 break;
   404         case OUPLUS:
   405                 Bprint(bout, "+");
   406                 pexpr(l);
   407                 break;
   408         }
   409 }
   410 
   411 void
   412 pstr(String *s)
   413 {
   414         int i, c;
   415 
   416         Bputc(bout, '"');
   417         for(i = 0; i < s->len; i++) {
   418                 c = s->string[i];
   419                 switch(c) {
   420                 case '\0':
   421                         c = '0';
   422                         break;
   423                 case '\n':
   424                         c = 'n';
   425                         break;
   426                 case '\r':
   427                         c = 'r';
   428                         break;
   429                 case '\t':
   430                         c = 't';
   431                         break;
   432                 case '\b':
   433                         c = 'b';
   434                         break;
   435                 case '\f':
   436                         c = 'f';
   437                         break;
   438                 case '\a':
   439                         c = 'a';
   440                         break;
   441                 case '\v':
   442                         c = 'v';
   443                         break;
   444                 case '\\':
   445                         c = '\\';
   446                         break;
   447                 case '"':
   448                         c = '"';
   449                         break;
   450                 default:
   451                         Bputc(bout, c);
   452                         continue;
   453                 }
   454                 Bputc(bout, '\\');
   455                 Bputc(bout, c);
   456         }
   457         Bputc(bout, '"');
   458 }