node.c
上传用户:dgyhgb
上传日期:2007-01-07
资源大小:676k
文件大小:10k
源码类别:

SQL Server

开发平台:

Unix_Linux

  1. /*
  2.  * node.c  - this module contains functions those generate C-code for
  3.  *           tree generating.
  4.  *
  5.  *  This file is a part of GNU SQL Server
  6.  *
  7.  *  Copyright (c) 1996, 1997, Free Software Foundation, Inc
  8.  *  Developed at the Institute of System Software
  9.  *  This file is written by Andrew Yahin.
  10.  *  Modified by Michael Kimelman.
  11.  *
  12.  *  This program is free software; you can redistribute it and/or modify
  13.  *  it under the terms of the GNU General Public License as published by
  14.  *  the Free Software Foundation; either version 2 of the License, or
  15.  *  (at your option) any later version.
  16.  *
  17.  *  This program is distributed in the hope that it will be useful,
  18.  *  but WITHOUT ANY WARRANTY; without even the implied warranty of
  19.  *  MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE.  See the
  20.  *  GNU General Public License for more details.
  21.  *
  22.  *  You should have received a copy of the GNU General Public License
  23.  *  along with this program; if not, write to the Free Software
  24.  *  Foundation, Inc., 59 Temple Place - Suite 330, Boston, MA 02111-1307, USA.
  25.  *
  26.  *  Contacts: gss@ispras.ru
  27.  *
  28.  */
  29. /* $Id: node.c,v 1.246 1997/03/31 11:03:38 kml Exp $ */
  30. #include <stdarg.h>
  31. #include <string.h>
  32. #include "kitty.h"
  33. extern FILE *yout;
  34. static void  emit_mknode_parms  __P(( TXTREF t,i4_t look_to_the_right));
  35. static i4_t   indent = 2;
  36. static char *spaces = "                                               "; 
  37. #define TYPE_INDENT fprintf(yout,"nt%s",spaces+strlen(spaces)-indent)
  38. #define is_tree(s) 
  39.         ((CODE_TRN(s)<RULE)||(CODE_TRN(s)>SKIP_CODES)||(TstF_TRN(s,PATTERN_F)))
  40. #define is_production(s) 
  41.         ((CODE_TRN(s)!=TRLcmd_REMOVE)&&(CODE_TRN(s)!=TRLcmd_CCODE)
  42.  &&(CODE_TRN(s)!=TRLcmd_SWITCH))
  43. static void
  44. strupr(char *s)
  45. {
  46.   for(;*s;s++)
  47.     if( (*s>='a') && (*s<='z'))
  48.       *s-='a'-'A';
  49.   return;
  50. }
  51. static void 
  52. type_header(TXTREF s)
  53. {
  54.   enum token tmp_code;
  55.   MASKTYPE   msk ;
  56.   char       cn[100];
  57.   
  58.   tmp_code=CODE_TRN(s);
  59.   msk = MASK_TRN(s);
  60.   if (tmp_code == UNKNOWN)
  61.     yyfatal("Unknown trn read");
  62.   if (tmp_code == NIL_CODE)
  63.     return ;
  64.   if(!TstF(msk,PATTERN_F))
  65.     {
  66.       i4_t n=OPs_IND(s);
  67.       if(n>=0)
  68. {
  69.   fprintf(yout,"Op[%d]=",n);
  70.   msk CLRVL (n+1);
  71. }
  72.     }    
  73.   MASK_TRN(s) = msk;
  74.   ClrF(msk,ACTION_F);
  75.   fputs("mk_node(",yout);
  76.   switch(tmp_code)
  77.     {
  78.     case OPERAND:
  79.       strcpy(cn,"OPERAND");
  80.       break;
  81.     default:
  82.       strcpy(cn,NAME(tmp_code));
  83.       strupr(cn);
  84.     }
  85.   fprintf(yout,"%s,%d,",cn,(u4_t)msk);
  86. void
  87. emit_trn_constructor(TXTREF s,i4_t look_to_the_right)
  88. {
  89.   static i4_t lrop=0;
  90.   i4_t i;
  91.   char *rl_cor_str;
  92.   if(s==0)
  93.     {
  94.       fputs("TNULL",yout);
  95.       return;
  96.     }
  97.   if(is_tree(s))
  98.     {
  99.       TYPE_INDENT;  indent+=4;
  100.       type_header(s);
  101.       emit_mknode_parms(s,look_to_the_right);
  102.       return;
  103.     }
  104.   if(TstF_TRN(s,LIST_F))
  105.     rl_cor_str="rl_corrector(1,";
  106.   else
  107.     rl_cor_str="rl_corrector(0,";
  108.   i=OPs_IND(s);
  109.   if(CODE_TRN(s)==OPERAND)
  110.     {
  111.       if(i>=0)
  112. {
  113.   register i4_t ind=0;
  114.   if(look_to_the_right)
  115.     {
  116.       TYPE_INDENT;  indent+=4;
  117.       ind++;
  118.       fputs(rl_cor_str,yout);
  119.     }
  120.   if(DOWN_TRN(s))
  121.     {
  122.       if(ind==0)
  123. { TYPE_INDENT;  indent+=4; }
  124.       ind++;
  125.       if(TstF_TRN(s,LIST_F))
  126. fputs("dl_corrector(1,",yout);
  127.       else
  128. fputs("dl_corrector(0,",yout);
  129.     }
  130.   fprintf(yout,"Op[%d]",i);
  131.   if(DOWN_TRN(s))
  132.     {
  133.       fputs(",",yout);
  134.       emit_trn_constructor(DOWN_TRN(s),1);
  135.       fputs(")",yout);
  136.     }
  137.   if(ind)
  138.     indent-=4;
  139.   if(look_to_the_right)
  140.     {
  141.       fputs(",",yout);
  142.       emit_trn_constructor(RIGHT_TRN(s),1);
  143.       fputs(")",yout);
  144.     }
  145. }
  146.       else
  147. trl_err("Unexpected operand expression",__FILE__,__LINE__,
  148. Ptree(s));
  149.       return;
  150.     }
  151.   TYPE_INDENT;  indent+=4;
  152.   if(lrop)
  153.     {
  154.       lrop=0;
  155.       fputs("Rop=",yout);
  156.     }
  157.       
  158.   if(i>=0)
  159.     fprintf(yout,"Op[%d]=",i);
  160.   if(look_to_the_right)
  161.     fputs(rl_cor_str,yout);
  162.   switch(CODE_TRN(s))
  163.     {
  164.     case TRLcmd_CCODE :
  165.       fputs(STRING(XLTR_TRN(s,0)),yout);
  166.       indent-=4;
  167.       if(look_to_the_right)
  168. {
  169.   fputs(",",yout);
  170.   emit_trn_constructor(RIGHT_TRN(s),look_to_the_right);
  171.   fputs(")",yout);
  172. }
  173.       return; 
  174.     case TRLcmd_DELETE :
  175.       fprintf(yout,"del_op(");
  176.       break;
  177.     case TRLcmd_DOWN   :
  178.       fprintf(yout,"DOWN_TRN(");
  179.       break;
  180.     case TRLcmd_SET    :
  181.       fprintf(yout,"(");
  182.       break;
  183.     case TRLcmd_RIGHT  :
  184.       fprintf(yout,"RIGHT_TRN(");
  185.       break;
  186.     case TRLcmd_COPY   :
  187.       fprintf(yout,"copy_tree(");
  188.       break;
  189.     case TRLcmd_IMAGE  :
  190.       fprintf(yout,"image(");
  191.       break;
  192.     case TRLcmd_INSERT :
  193.       fprintf(yout,"insert_node(%d,",(TstF_TRN(s,BEFORE_F))?1:0);
  194.       break;
  195.     case TRLcmd_REPLACE:
  196.       fprintf(yout,"replace_node(");
  197.       break;
  198.     case TRLcmd_REMOVE :
  199.       if(TstF_TRN(s,TREE_F))
  200. fputs("free_tree(",yout);
  201.       else
  202. fputs("free_node(",yout);
  203.       break;
  204.     case TRLcmd_SWITCH :
  205.       {
  206. TXTREF ss=DOWN_TRN(s);
  207. fputs("( ( { i4_t kitty_lcc=0;",yout);
  208. if(XTXT_TRN(s,0))
  209.   {
  210.     TYPE_INDENT;
  211.     fputs("Rop=",yout);
  212.     indent+=4;
  213.     emit_trn_constructor(XTXT_TRN(s,0),0);
  214.     fputs(";",yout);
  215.     indent-=4;
  216.   }
  217. TYPE_INDENT;
  218. fputs("while(1)",yout);
  219. indent+=2;
  220. TYPE_INDENT;
  221. fputs("{",yout);
  222. indent+=2;
  223. TYPE_INDENT;
  224. fputs("kitty_lcc=0;",yout);
  225. while (ss)
  226.   { 
  227.     if(is_production(ss))
  228.       lrop=1;
  229.     if(CODE_TRN(ss)==TRLcmd_CASE)
  230.       {
  231. TYPE_INDENT;
  232. fprintf(yout,"Rop=rule_%s(&kitty_lcc,Rop)",
  233. STRING(XLTR_TRN(ss,0)));
  234.       }
  235.     else
  236.       emit_trn_constructor(ss,0);
  237.     fprintf(yout,";");
  238.     TYPE_INDENT;
  239.     /* if(CODE_TRN(ss)==RUN_RULE) */
  240.             if(TstF_TRN(s,CYCLE_F))
  241.               fputs("if(kitty_lcc) continue;",yout);
  242.             else
  243.               fputs("if(kitty_lcc) break;",yout);
  244.     ss=RIGHT_TRN(ss);
  245.   }
  246.         if( ! TstF_TRN(s,CYCLE_F) )
  247.   fputs(
  248.              /* "yyfatal("Unrecognizable SWITCH selector");" */
  249.      /* "yyerror("Unrecognizable SWITCH selector");" */
  250.         "puts("Unrecognizable SWITCH selector")   ;"
  251.       ,yout);
  252.         fputs("break;",yout);
  253. indent-=2;
  254. TYPE_INDENT;
  255. fputs("}",yout);
  256. indent-=4;
  257. TYPE_INDENT;
  258. fputs("} ), Rop)",yout);
  259. if(look_to_the_right)
  260.   {
  261.     fputs(",",yout);
  262.     emit_trn_constructor(RIGHT_TRN(s),look_to_the_right);
  263.     fputs(")",yout);
  264.   }
  265. return;
  266.       }
  267.     case RUN_RULE:
  268.       fprintf(yout,"rule_%s(&kitty_lcc,",STRING(XLTR_TRN(s,0)));
  269.       emit_trn_constructor(XTXT_TRN(s,2),0);
  270.       fputs(")",yout);
  271.       indent-=4;
  272.       if(look_to_the_right)
  273. {
  274.   fputs(",",yout);
  275.   emit_trn_constructor(RIGHT_TRN(s),look_to_the_right);
  276.   fputs(")",yout);
  277. }
  278.       return;
  279.     default:
  280.       trl_wrn("Unexpected node here",__FILE__,__LINE__,Ptree(s));
  281.       type_header(s);
  282.     }
  283.   emit_mknode_parms(s,look_to_the_right);
  284. }
  285. #define CHECK_COMMA {if (need_comma) fputs(",",yout); else need_comma=1;}
  286. #define IS_SET(n)  TST_BIT(XLNG_TRN(t,PTRN_OP(tmp_code,(n))),PTRN_BIT((n)))
  287. static void 
  288. emit_mknode_parms( TXTREF t,i4_t look_to_the_right )
  289. {
  290.   enum token tmp_code;
  291.   char      *format_ptr;
  292.   i4_t        right_ptr=0;
  293.   i4_t        down_ptr=0;
  294.   i4_t        need_comma=0;
  295.   i4_t        i,act,shift;
  296.   
  297.   tmp_code   = CODE_TRN(t);
  298.   format_ptr = FORMAT (tmp_code);
  299.   act = TstF_TRN(t,ACTION_F);
  300.   shift = (TstF_TRN(t,PATTERN_F) ? LENGTH(tmp_code) : 0);
  301.   
  302.   for (i = 0; i < LENGTH (tmp_code); i++)
  303.     {
  304.       i4_t subst = 0;
  305.       char *transform = "SIMPLE2L";
  306.       switch(format_ptr[i]) /* step for substitution C expr for atributes */
  307. {
  308. case '0': case 'r': case 'a': case 'd': case 'V': 
  309.   break;
  310. case 'y':
  311.   transform = "type2long";
  312. default:
  313.   if (act && IS_SET (i + shift) )
  314.     {
  315.       CHECK_COMMA;
  316.       fprintf(yout,"%s(%s)",transform,STRING(XLTR_TRN(t, i)));
  317.       subst = 1;
  318.     }
  319. }
  320.       if (subst)
  321. continue;
  322.       switch (format_ptr[i])
  323. {
  324. case '0':break;
  325. case 'r':
  326.   right_ptr=1;
  327.   break;
  328. case 'a':
  329.   break;
  330. case 'd':
  331.   down_ptr=1;
  332.   break;
  333. case 'V': /* special vocabulary reference (backward link) */
  334.   break;
  335. case 't':
  336.   CHECK_COMMA;
  337.   emit_trn_constructor(XTXT_TRN(t,i),0);
  338.   break;
  339. case 'N':
  340.   CHECK_COMMA;
  341.   emit_trn_constructor(XTXT_TRN(t,i),1);
  342.   break;
  343. case 'v':
  344.   /*   emit_trn_constructor(XTXT_TRN(t, i),0);*/
  345.   CHECK_COMMA;
  346.   fputs("0",yout);
  347.   break;
  348. case 'S':
  349.   /* 'S' is an optional string: if a closeparen follows,
  350.      just store NULL for this element.  */
  351. case 's':
  352.   {
  353.     CHECK_COMMA;
  354.     if((tmp_code==OPERAND) && (TstF_TRN(t,PATTERN_F)))
  355.       fprintf(yout,"%d",XLNG_TRN(t,i));
  356.     else  if(is_tree(t))
  357.       {
  358. char *ptr=STRING(XLTR_TRN(t, i));
  359. if(ptr && *ptr)
  360.   fprintf(yout,"ltr_rec("%s")",ptr);
  361. else
  362.   fputs("TNULL",yout);
  363.       }
  364.   }
  365.   break;
  366. case 'p':
  367. case 'y':
  368. case 'i':
  369. case 'x':
  370. case 'l':
  371. case 'R':
  372.   CHECK_COMMA;
  373.   fprintf(yout,"%d",XLNG_TRN(t,i));
  374.   break;
  375. case 'f':
  376.   CHECK_COMMA;
  377.   fprintf(yout,"%g",XFLT_TRN(t, i));
  378.   break;
  379. case 'T':
  380. case 'L':
  381.   CHECK_COMMA;
  382.   if(XTXT_TRN(t,i))
  383.     {
  384.       TXTREF v = XVEC_TRN(t,i);
  385.       i4_t    l = VLEN(v),n;
  386.     
  387.       fprintf(yout,"mk_vect(%d,%d",(format_ptr[i]=='T'?1:0),l);
  388.       for(n=0;n<l;n++)
  389. {
  390.   fputs(",",yout); 
  391.   if(format_ptr[i]=='T')
  392.     emit_trn_constructor(VOP(v,n).txtp,0);
  393.   else
  394.     fprintf(yout,"%d",VOP(v,n).l);
  395. }
  396.       fputs(")",yout);
  397.     }
  398.   else
  399.     fputs("TNULL",yout);
  400.   break;
  401. default:
  402.   fprintf (stderr,
  403.    "switch format wrong in emit_mknode_parm(). format was: '%c'.n",
  404.    format_ptr[i]);
  405.   yyfatal("Abort");
  406. }
  407.     }  
  408.   /* print null attribute information */
  409.   if (shift)
  410.     for(i = LENGTH(CODE_TRN(t));
  411. i < LENGTH(CODE_TRN(t)) + PTRN_ELEM(CODE_TRN(t));
  412. i++)
  413.       {
  414. CHECK_COMMA;
  415. fprintf(yout,"%d",XLNG_TRN(t,i));
  416.       }
  417.   
  418.   indent-=2;
  419.   if(down_ptr)
  420.     {
  421.       CHECK_COMMA;
  422.       emit_trn_constructor(DOWN_TRN(t),1);
  423.     }
  424.   indent-=2;
  425.   if(right_ptr)
  426.     if(look_to_the_right)
  427.       {
  428. if(!is_tree(t))
  429.   fputs(")",yout);
  430. CHECK_COMMA;
  431. emit_trn_constructor(RIGHT_TRN(t),1);
  432.       }
  433.     else if(is_tree(t))
  434.       fputs(",TNULL",yout);
  435.   fprintf(yout,")");
  436.   return;
  437. }