⭐ 欢迎来到虫虫下载站! | 📦 资源下载 📁 资源专辑 ℹ️ 关于我们
⭐ 虫虫下载站

📄 bwb_inp.c

📁 这是一个简易的basic语言解释器, 可供我们学习和改进.
💻 C
📖 第 1 页 / 共 4 页
字号:
/***************************************************************        bwb_inp.c       Input Routines                        for Bywater BASIC Interpreter                        Commands:       DATA                                        READ                                        RESTORE                                        INPUT                                        LINE INPUT                        Copyright (c) 1993, Ted A. Campbell                        Bywater Software                        email: tcamp@delphi.com        Copyright and Permissions Information:        All U.S. and international rights are claimed by the author,        Ted A. Campbell.	This software is released under the terms of the GNU General	Public License (GPL), which is distributed with this software	in the file "COPYING".  The GPL specifies the terms under	which users may copy and use the software in this distribution.	A separate license is available for commercial distribution,	for information on which you should contact the author.***************************************************************//*---------------------------------------------------------------*//* NOTE: Modifications marked "JBV" were made by Jon B. Volkoff, *//* 11/1995 (eidetics@cerf.net).                                  *//*---------------------------------------------------------------*/#include <stdio.h>#include <ctype.h>#include <math.h>#include "bwbasic.h"#include "bwb_mes.h"/* Declarations of functions visible to this file only */#if ANSI_Cstatic struct bwb_line *bwb_xinp( struct bwb_line *l, FILE *f );static struct bwb_line *inp_str( struct bwb_line *l, char *buffer,   char *var_list, int *position );static int inp_const( char *m_buffer, char *s_buffer, int *position );static int inp_assign( char *b, struct bwb_variable *v );static int inp_advws( FILE *f );static int inp_xgetc( FILE *f, int is_string );static int inp_eatcomma( FILE *f );static bnumber inp_numconst( char *expression ); /* JBV */#elsestatic struct bwb_line *bwb_xinp();static struct bwb_line *inp_str();static int inp_const();static int inp_assign();static int inp_advws();static int inp_xgetc();static int inp_eatcomma();static bnumber inp_numconst(); /* JBV */#endifstatic char_saved = FALSE;static cs;static int last_inp_adv_rval = FALSE; /* JBV *//***************************************************************        FUNCTION:       bwb_read()        DESCRIPTION:    This function implements the BASIC READ                        statement.        SYNTAX:         READ variable[, variable...]***************************************************************/#if ANSI_Cstruct bwb_line *bwb_read( struct bwb_line *l )#elsestruct bwb_line *bwb_read( l )   struct bwb_line *l;#endif   {   int pos;   register int n;   int main_loop, adv_loop;   struct bwb_variable *v;   int n_params;                         /* number of parameters */   int *pp;                              /* pointer to parameter values */   char tbuf[ MAXSTRINGSIZE + 1 ];#if INTENSIVE_DEBUG   sprintf( bwb_ebuf, "in bwb_read(): buffer <%s>",      &( l->buffer[ l->position ]));   bwb_debug( bwb_ebuf );#endif   /* Process each variable read from the READ statement */   main_loop = TRUE;   while ( main_loop == TRUE )      {      /* first check position in l->buffer and advance beyond whitespace */      adv_loop = TRUE;      while( adv_loop == TRUE )         {#if INTENSIVE_DEBUG         sprintf( bwb_ebuf, "in bwb_read() adv_loop char <%d> = <%c>",            l->buffer[ l->position ], l->buffer[ l->position ] );         bwb_debug( bwb_ebuf );#endif         switch ( l->buffer[ l->position ] )            {            case ',':                   /* comma delimiter */            case ' ':                   /* whitespace */            case '\t':               ++l->position;               break;            case ':':                   /* end of line segment */	    case '\n':                  /* end of line */            case '\r':            case '\0':               adv_loop = FALSE;        /* break out of advance loop */               main_loop = FALSE;       /* break out of main loop */               break;            default:                    /* anything else */               adv_loop = FALSE;        /* break out of advance loop */               break;            }         }#if INTENSIVE_DEBUG      sprintf( bwb_ebuf, "in bwb_read(): end of adv_loop <%d> main_loop <%d>",         adv_loop, main_loop );      bwb_debug( bwb_ebuf );#endif      /* be sure main_loop id still valid after checking the line */      if ( main_loop == TRUE )         {         /* Read a variable name */         bwb_getvarname( l->buffer, tbuf, &( l->position ) );         inp_adv( l->buffer, &( l->position ) );         v = var_find( tbuf );#if INTENSIVE_DEBUG	 sprintf( bwb_ebuf, "in bwb_read(): line <%d> variable <%s>",	    l->number, v->name );	 bwb_debug( bwb_ebuf );	 sprintf( bwb_ebuf, "in bwb_read(): remaining line <%s>",	    &( l->buffer[ l->position ] ) );	 bwb_debug( bwb_ebuf );#endif         /* advance beyond whitespace or comma in data buffer */         inp_adv( CURTASK data_line->buffer, &CURTASK data_pos );         /* Advance to next line if end of buffer */         switch( CURTASK data_line->buffer[ CURTASK data_pos ] )            {            case '\0':                     /* end of buffer */            case '\n':            case '\r':               CURTASK data_line = CURTASK data_line->next;               /* advance farther to line with DATA statement if necessary */               pos = 0;               line_start( CURTASK data_line->buffer, &pos,                  &( CURTASK data_line->lnpos ),                  &( CURTASK data_line->lnum ),                  &( CURTASK data_line->cmdpos ),                  &( CURTASK data_line->cmdnum ),                  &( CURTASK data_line->startpos ) );               CURTASK data_pos = CURTASK data_line->startpos;#if INTENSIVE_DEBUG               sprintf( bwb_ebuf, "in bwb_read(): current data line: <%s>",                  CURTASK data_line->buffer );               bwb_debug( bwb_ebuf );#endif               break;            }         while ( bwb_cmdtable[ CURTASK data_line->cmdnum ].vector != bwb_data )            {            if ( CURTASK data_line == &CURTASK bwb_end )               {               CURTASK data_line = CURTASK bwb_start.next;               }            else               {               CURTASK data_line = CURTASK data_line->next;               }            pos = 0;            line_start( CURTASK data_line->buffer, &pos,               &( CURTASK data_line->lnpos ),               &( CURTASK data_line->lnum ),               &( CURTASK data_line->cmdpos ),               &( CURTASK data_line->cmdnum ),               &( CURTASK data_line->startpos ) );            CURTASK data_pos = CURTASK data_line->startpos;#if INTENSIVE_DEBUG            sprintf( bwb_ebuf, "in bwb_read(): advance to data line: <%s>",               CURTASK data_line->buffer );            bwb_debug( bwb_ebuf );#endif            }         /* advance beyond whitespace in data buffer */         adv_loop = TRUE;         while ( adv_loop == TRUE )            {            switch( CURTASK data_line->buffer[ CURTASK data_pos ] )               {               case '\0':                       /* end of buffer */               case '\n':               case '\r':                  bwb_error( err_od );                  return bwb_zline( l );               case ' ':                        /* whitespace */               case '\t':                  ++CURTASK data_pos;                  break;               default:                  adv_loop = FALSE;             /* carry on */                  break;               }            }         /* now at last we have a variable in v that needs to be            assigned data from the data_buffer at position CURTASK data_pos.            What remains to be done is to get one single bit of data,            a string constant or numerical constant, into the small            buffer */         inp_const( CURTASK data_line->buffer, tbuf, &CURTASK data_pos );#if INTENSIVE_DEBUG	 sprintf( bwb_ebuf, "in bwb_read(): data constant is <%s>", tbuf );	 bwb_debug( bwb_ebuf );#endif         /* get parameters if the variable is dimensioned */	 adv_ws( l->buffer, &( l->position ) );	 if ( l->buffer[ l->position ] == '(' )	    {#if INTENSIVE_DEBUG	    sprintf( bwb_ebuf, "in bwb_read(): variable <%s> is dimensioned",	       v->name );	    bwb_debug( bwb_ebuf );#endif            dim_getparams( l->buffer, &( l->position ), &n_params, &pp );            for ( n = 0; n < v->dimensions; ++n )               {               v->array_pos[ n ] = pp[ n ];               }	    }#if INTENSIVE_DEBUG	 else	    {	    sprintf( bwb_ebuf, "in bwb_read(): variable <%s> is NOT dimensioned",	       v->name );	    bwb_debug( bwb_ebuf );	    sprintf( bwb_ebuf, "in bwb_read(): remaining line <%s>",	       &( l->buffer[ l->position ] ) );	    bwb_debug( bwb_ebuf );	    }#endif         /* finally assign the data to the variable */         inp_assign( tbuf, v );         }                              /* end of remainder of main loop */      }                                 /* end of main_loop */#if INTENSIVE_DEBUG   sprintf( bwb_ebuf, "in bwb_read(): exiting function, line <%s> ",      &( l->buffer[ l->position ] ) );   bwb_debug( bwb_ebuf );#endif   return bwb_zline( l );   }/***************************************************************        FUNCTION:       bwb_data()        DESCRIPTION:    This function implements the BASIC DATA                        statement, although at the point at which                        DATA statements are encountered, no                        processing is done.  All actual processing                        of DATA statements is accomplished by READ                        (bwb_read()).        SYNTAX:         DATA constant[, constant]...***************************************************************/#if ANSI_Cstruct bwb_line *bwb_data( struct bwb_line *l )#elsestruct bwb_line *bwb_data( l )   struct bwb_line *l;#endif   {#if MULTISEG_LINES   adv_eos( l->buffer, &( l->position ));#endif   return bwb_zline( l );   }/***************************************************************        FUNCTION:       bwb_restore()        DESCRIPTION:    This function implements the BASIC RESTORE                        statement.        SYNTAX:         RESTORE [line number]***************************************************************/#if ANSI_Cstruct bwb_line *bwb_restore( struct bwb_line *l )#elsestruct bwb_line *bwb_restore( l )   struct bwb_line *l;#endif   {   struct bwb_line *r;   struct bwb_line *r_line;   int n;   int pos;   char tbuf[ MAXSTRINGSIZE + 1 ];   /* get the first element beyond the starting position */   adv_element( l->buffer, &( l->position ), tbuf );   /* if the line is not a numerical constant, then there is no      argument; set the current line to the first in the program */   if ( is_numconst( tbuf ) != TRUE )      {      CURTASK data_line = &CURTASK bwb_start;      CURTASK data_pos = 0;#if INTENSIVE_DEBUG      sprintf( bwb_ebuf, "in bwb_restore(): RESTORE w/ no argument " );      bwb_debug( bwb_ebuf );#endif      return bwb_zline( l );      }   /* find the line */   n = atoi( tbuf );#if INTENSIVE_DEBUG   sprintf( bwb_ebuf, "in bwb_restore(): line for restore is <%d>", n );   bwb_debug( bwb_ebuf );#endif   r_line = NULL;   for ( r = CURTASK bwb_start.next; r != &CURTASK bwb_end; r = r->next )      {      if ( r->number == n )         {         r_line = r;         }      }   if ( r_line == NULL )      {#if PROG_ERRORS      sprintf( bwb_ebuf, "at line %d: Can't find line number for RESTORE.",         l->number );      bwb_error( bwb_ebuf );#else      sprintf( bwb_ebuf, err_lnnotfound, n );      bwb_error( bwb_ebuf );#endif      return bwb_zline( l );      }   /* initialize variables for the line */   pos = 0;   line_start( r_line->buffer, &pos,      &( r_line->lnpos ),      &( r_line->lnum ),      &( r_line->cmdpos ),      &( r_line->cmdnum ),      &( r_line->startpos ) );   /* verify that line is a data statement */   if ( bwb_cmdtable[ r_line->cmdnum ].vector != bwb_data )      {#if PROG_ERRORS      sprintf( bwb_ebuf, "at line %d: Line %d is not a DATA statement.",         l->number, r_line->number );      bwb_error( bwb_ebuf );#else      bwb_error( err_syntax );#endif      return bwb_zline( l );      }   /* reassign CURTASK data_line */   CURTASK data_line = r_line;   CURTASK data_pos = CURTASK data_line->startpos;   return bwb_zline( l );   }/***************************************************************        FUNCTION:       bwb_input()        DESCRIPTION:    This function implements the BASIC INPUT                        statement.        SYNTAX:         INPUT [;][prompt$;]variable[$,variable]...                        INPUT#n variable[$,variable]...***************************************************************/#if ANSI_Cstruct bwb_line *bwb_input( struct bwb_line *l )#elsestruct bwb_line *bwb_input( l )   struct bwb_line *l;#endif   {   FILE *fp;   int pos;   int req_devnumber;   struct exp_ese *v;   int is_prompt;

⌨️ 快捷键说明

复制代码 Ctrl + C
搜索代码 Ctrl + F
全屏模式 F11
切换主题 Ctrl + Shift + D
显示快捷键 ?
增大字号 Ctrl + =
减小字号 Ctrl + -