home *** CD-ROM | disk | FTP | other *** search
/ DOS/V Power Report 1997 March / VPR9703A.ISO / VPR_DATA / DOGA / SOURCES / POLYEDIT.LZH / ML / PARSE2.C < prev    next >
C/C++ Source or Header  |  1996-02-16  |  6KB  |  305 lines

  1. /*
  2.  *        関数の管理
  3.  *
  4.  *        1994.5.22        T.Koabayashi
  5.  */
  6. #include <stdio.h>
  7. #include <stdlib.h>
  8. #include <string.h>
  9. #include <assert.h>
  10.  
  11. #include "parse.h"
  12. #include "err.h"
  13.  
  14. #include "inlib.h"
  15.  
  16. static    void    ParseArray( void );
  17.  
  18. /*    構文解析処理    */
  19. void    ParseFunction( ident )
  20. int        ident ;
  21. {
  22.     int        args ;
  23.  
  24.     GetToken();
  25.     if ( Input.token == SYM_OPEN1 )
  26.     {
  27.         GetToken();
  28.         args = 0 ;
  29.         if ( Input.token != SYM_CLOSE1 )
  30.         {
  31.             args = 1 ;
  32.             ParseExpression();
  33.             while( Input.token != SYM_CLOSE1 )
  34.             {
  35.                 if ( Input.token != SYM_COMMA )
  36.                 {
  37.                     ParseError( " , または ) が必要です。" );
  38.                     break ;
  39.                 }
  40.                 args ++ ;
  41.                 GetToken();
  42.                 ParseExpression();
  43.             }
  44.         }
  45.         GetToken();
  46.         CodeSetInt( args );
  47.         CodeSetIdent( IDENT_FUNC, ident );
  48.     }
  49.     else
  50.     {
  51.         DataStruct    data ;
  52.         data.type = TYPE_FUNC ;
  53.         data.funcd.ident = ident ;
  54.         CodeSetConst( &data );
  55.     }
  56. }
  57.  
  58. /*    関数定義の構文解析    */
  59. void    ParseDefineFunction( code )
  60. CodeSentense    *code ;
  61. {
  62.     int        args, ident ;
  63.     CodeConst    *vars ;
  64.     FuncBuffer    *func ;
  65.  
  66.     code->stype = SENT_DEF_FUNC ;
  67.  
  68.     /*    関数名の設定    */
  69.     GetToken();
  70.     if ( Input.token == SYM_PRIVATE ) {
  71.         GetToken();
  72.         ident = IdentSearch( IdentFunction, Input.str );
  73.         if (ident < 0) {
  74.             ident = IdentAppend( IdentFunction, Input.str, IDENT_PRIVATE|IDENT_FUNC );
  75.             ClassList[0].func[ident].type = FUNC_NO;
  76.         }
  77.     } else {
  78.         ident = IdentSearch( IdentFunction, Input.str );
  79.         if (ident < 0) {
  80.             ident = IdentAppend( IdentFunction, Input.str, IDENT_FUNC );
  81.             ClassList[0].func[ident].type = FUNC_NO;
  82.         }
  83.     }
  84.     func = ClassList[0].func + ident ;
  85.  
  86.     GetToken();
  87.     if ( Input.token == SYM_SEMCLN ) {
  88.         return;
  89.     }
  90.  
  91.     if (func->type != FUNC_NO) {
  92.         ParseError( "関数 %s が二重定義されています。", IdentFunction->name[ident] );
  93.     }
  94.  
  95.     func->type = FUNC_USR ;
  96.     func->name = IdentFunction->name[ident] ;
  97.     func->ptr = CodeNextPtr();
  98.  
  99.     /*    ローカル変数の初期化    */
  100.     IdentLocalVar = IdentAlloc( MAX_LOCAL_VAR, 0 );
  101.  
  102.     if ( Input.token != SYM_OPEN1 )
  103.         ParseError( " ( が必要です。" );
  104.  
  105.     GetToken();
  106.     if ( Input.token != SYM_CLOSE1 )
  107.     {
  108.         args = 1 ;
  109.         IdentAppend( IdentLocalVar, Input.str, IDENT_LOCAL );
  110.         GetToken();
  111.         while( Input.token != SYM_CLOSE1 )
  112.         {
  113.             if ( Input.token != SYM_COMMA )
  114.             {
  115.                 ParseError( " , または ) が必要です。" );
  116.                 break ;
  117.             }
  118.             args ++ ;
  119.             GetToken();
  120.             IdentAppend( IdentLocalVar, Input.str, IDENT_LOCAL );
  121.             GetToken();
  122.         }
  123.     }
  124.     else
  125.         args = 0 ;
  126.     CodeSetInt( args );
  127.     vars = CodeSetInt( 0 );
  128.  
  129.     /*    関数本体の解析    */
  130.     GetToken();
  131.     ParseSentense();
  132.  
  133.     /*    ローカル変数の解放    */
  134.     vars->data.id.i = IdentLocalVar->count ;
  135.     IdentFree( IdentLocalVar );
  136.     IdentLocalVar = NULL ;
  137. }
  138.  
  139. /*
  140.  *        return 文の構文解析
  141.  */
  142. void    ParseReturn( code )
  143. CodeSentense    *code ;
  144. {
  145.     code->stype = SENT_RETURN ;
  146.     GetToken();
  147.     if ( Input.token == SYM_SEMCLN )
  148.     {
  149.         DataStruct c ;
  150.         c.type = TYPE_NOASN ;
  151.         CodeSetConst( &c );
  152.     }
  153.     else
  154.     {
  155.         ParseExpression();
  156.     }
  157.     CodeSetOperator( OPE_EXP_END );
  158.     if ( Input.token != SYM_SEMCLN )
  159.         ParseError( " ; が必要です。" );
  160.     else
  161.         GetToken();
  162. }
  163.  
  164. /*
  165.  *        変数宣言文の解析
  166.  */
  167. void    ParseVar( code, sw )
  168. CodeSentense    *code ;
  169. int        sw ;        /*    1:global    0:local    */
  170. {
  171.     int        ident ;
  172.     char    name[IDENT_CHARS] ;
  173.     int        flag ;
  174.  
  175.     flag = ( sw ) ? IDENT_GLOBAL : IDENT_LOCAL ;
  176.  
  177.     code->stype = SENT_VAR ;
  178.     do
  179.     {
  180.         GetToken();
  181.         while ( Input.token == SYM_PRIVATE || Input.token == SYM_CONST )
  182.         {
  183.             if ( Input.token == SYM_PRIVATE )
  184.                 flag |= IDENT_PRIVATE ;
  185.             else
  186.                 flag |= IDENT_CONST ;
  187.             GetToken();
  188.         }
  189.         if ( Input.token == SYM_IDENT )
  190.         {
  191.             strcpy( name, Input.str );
  192.             GetToken();
  193.             if ( sw )
  194.             {
  195.                 ident = IdentAppend( IdentGlobalVar, name, flag );
  196.             }
  197.             else
  198.             {
  199.                 ident = IdentAppend( IdentLocalVar, name, flag );
  200.             }
  201.             if ( Input.token == SYM_OPEN3 )
  202.             {
  203.                 flag |= IDENT_ARY ;
  204.                 CodeSetIdent( flag, ident );
  205.                 ParseArray();
  206.             }
  207.             else if ( Input.token == SYM_ASSIGN )
  208.             {
  209.                 CodeSetIdent( flag, ident );
  210.                 GetToken();
  211.                 ParseExpression();
  212.                 CodeSetOperator( OPE_EXP_END );
  213.             }
  214.         }
  215.         else
  216.         {
  217.             ParseError( "識別子が必要です" );
  218.             break ;
  219.         }
  220.     }
  221.     while( Input.token == SYM_COMMA );
  222.     if ( Input.token != SYM_SEMCLN )
  223.         ParseError( ";が必要です" );
  224.     else
  225.         GetToken();
  226.  
  227.     CodeSetOperator( OPE_EXP_END );
  228. }
  229.  
  230. /*    配列変数の解析    */
  231. static    void    ParseArray()
  232. {
  233.     int        n ;
  234.  
  235.     n = 0 ;
  236.     while( Input.token == SYM_OPEN3 )
  237.     {
  238.         GetToken();
  239.         ParseExpression();
  240.         if ( Input.token != SYM_CLOSE3 )
  241.         {
  242.             ParseError( " ] が必要です" );
  243.             break ;
  244.         }
  245.         n ++ ;
  246.         GetToken();
  247.     }
  248.     CodeSetInt( n );    /*    次数    */
  249.     CodeSetOperator( OPE_EXP_END );
  250.     return ;
  251. }
  252.  
  253. void    ParseGlobalVar( ident )
  254. int        ident ;
  255. {
  256.     CodeIdent    *code ;
  257.  
  258.     code = CodeSetIdent( IDENT_GLOBAL, ident );
  259.     GetToken();
  260.     if ( Input.token == SYM_OPEN3 )
  261.     {
  262.         code->itype |= IDENT_ARY ;
  263.         ParseArray();
  264.     }
  265. }
  266.  
  267. void    ParseLocalVar( ident )
  268. int        ident ;
  269. {
  270.     CodeIdent    *code ;
  271.  
  272.     code = CodeSetIdent( IDENT_LOCAL, ident );
  273.     GetToken();
  274.     if ( Input.token == SYM_OPEN3 )
  275.     {
  276.         code->itype |= IDENT_ARY ;
  277.         ParseArray();
  278.     }
  279. }
  280.  
  281. /*
  282.  *        代入文の解析
  283.  */
  284. void    ParseAssign( code )
  285. CodeSentense    *code ;
  286. {
  287.     if ( Input.token < SYM_ASSIGN || SYM_ASN_DEC < Input.token )
  288.         ParseError( "代入演算子が必要です" );
  289.  
  290.     code->stype = Input.token - ( SYM_ASSIGN - SENT_ASSIGN ) ;
  291.     if ( Input.token < SYM_ASN_INC )
  292.     {
  293.         GetToken();
  294.         ParseExpression();
  295.     }
  296.     else
  297.         GetToken();
  298.     if ( Input.token != SYM_SEMCLN && Input.token != SYM_CLOSE1 )
  299.         ParseError( " ; が必要です" );
  300.  
  301.     GetToken();
  302.     CodeSetOperator( OPE_EXP_END );
  303. }
  304.  
  305.