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

📄 numexpr.c

📁 类PASCAL语言的编译器,LINUX环境的,我没试过是否正确.
💻 C
📖 第 1 页 / 共 5 页
字号:
/****************************************************************************** *                        FREXX PROGRAMMING LANGUAGE                          * ****************************************************************************** numexpr.c Supports *FULL* C language expression operator priority and much more...! *****************************************************************************//************************************************************************ *                                                                      * * fpl.library - A shared library interpreting script langauge.         * * Copyright (C) 1992-1994 FrexxWare                                    * * Author: Daniel Stenberg                                              * *                                                                      * * This program is free software; you may redistribute for non          * * commercial purposes only. Commercial programs must have a written    * * permission from the author to use FPL. FPL is *NOT* public domain!   * * Any provided source code is only for reference and for assurance     * * that users should be able to compile FPL on any operating system     * * he/she wants to use it in!                                           * *                                                                      * * You may not change, resource, patch files or in any way reverse      * * engineer anything in the FPL package.                                * *                                                                      * * This program is distributed in the hope that it will be useful,      * * but WITHOUT ANY WARRANTY; without even the implied warranty of       * * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE.                 * *                                                                      * * Daniel Stenberg                                                      * * Ankdammsgatan 36, 4tr                                                * * S-171 43 Solna                                                       * * Sweden                                                               * *                                                                      * * FidoNet 2:201/328    email:dast@sth.frontec.se                       * *                                                                      * ************************************************************************/#ifdef AMIGA#include <exec/types.h>#include <proto/exec.h>#elif defined(UNIX) || defined(WIN32)#include <sys/types.h>#endif#include "script.h"#include <stdio.h>#include <stddef.h>#include <limits.h>#include "debug.h"static ReturnCode INLINE GetArrayInfo(struct Data *, long *, long *, long, uchar *);static ReturnCode INLINE Convert(struct Expr *, struct Data *);static ReturnCode INLINE PrototypeInside(struct Data *,					 struct Expr *val,					 long,					 struct Identifier *);static ReturnCode INLINE inside(struct Data *, struct fplArgument *,                                struct Identifier *);#ifdef STRING_STACKstatic ReturnCode INLINE StringToStack(struct Data *,                                       struct fplStr **);static ReturnCode INLINE StringFromStack(struct Data *,                                         struct fplStr **);#endif/*********************************************************************** * * int Expression(struct Expr *, struct Data *, uchar, struct Local *) * * Returns a nonzero value if any error occured. * The result of the Expression is returned in the Expr structure which you * give the pointer to in the first argument. * *****************/ReturnCode REGARGSExpression(struct Expr *val, /* return value struct pointer */           struct Data *scr, /* everything */           long control,    /* ESPECIALLLY DEFINED */           struct Identifier *ident) /* pointer to the pointer holding                                        the local variable names linked                                        list */{  struct Expr *expr, *basexpr;  ReturnCode ret;  struct Identifier *pident; /* general purpose struct identifier pointer */  struct Unary *un; /* general purpose struct Unary pointers */  long *dims=NULL; /* dimension pointer for variable arrays! */  long pos;       /* general purpose integer */  uchar *text;     /* general purpose char pointer */  uchar hit;  uchar *array;  long num;  long *nump;     /* for general purpose long pointers */  struct fplMsg *msg;  struct fplStr *string;#if defined(AMIGA) && defined(SHARED)  if(ret=CheckStack(scr, scr->stack_limit, scr->stack_margin)) {    if(ret==1)      return(FPLERR_OUT_OF_MEMORY);    else      return(FPLERR_OUT_OF_STACK);  }#endif  GETMEM(expr, sizeof(struct Expr));  memset(expr, 0, sizeof(struct Expr));  basexpr=expr;  do {    if(ret=Eat(scr)) {       /* getaway blanks and comments */      if(control&CON_END && ret==FPLERR_UNEXPECTED_END) {        /* If there can be an unexpected ending, break out of the loop           with a nice return code! */        break;      }    } else if(expr->flags&FPL_STRING && !(control&CON_GROUNDLVL))      /* get outta string calcs if not on ground level! */      break;    if(!(expr->flags&FPL_OPERAND)) {  /* operand coming up */      if(control&CON_IDENT || isident(*scr->text)) {        /*         * It's a valid identifier character.         */        uchar *point;        num=0; /* Dimension counter when taking care of array variables */        if(control&CON_IDENT) {          if(!ident)            ret=FPLERR_IDENTIFIER_NOT_FOUND;          control&=~CON_IDENT; /* switch off that bit to get away from any                                  trouble such as double using this! */        } else {          CALL(Getword(scr));          ret=GetIdentifier(scr, scr->buf, &ident);        }        point=scr->text;        Eat(scr); /* getaway blanks */        /*         * `ret' can only be FPL_OK or FPLERR_IDENTIFIER_NOT_FOUND at this         * position.         */        if(control&CON_DECLARE && *scr->text==CHAR_OPEN_PAREN) {	  CALL(PrototypeInside(scr, val, control, ident));	  expr->flags|=FPL_OPERAND|FPL_ACTION;        } else if(control&CON_DECLARE ||                  (ident && ident->flags&FPL_VARIABLE)) {          /* The ident check above really must be there, otherwise we might             read it when it is a NULL pointer" */          /* it's a variable */          pident=ident;          if(ret &&                     /* we didn't find it... */             !(control&CON_DECLARE))    /* and we're not declaring! */            /*             * We didn't find the requested identifier and we're *NOT*             * declaring. This means error!             */            return(ret);          else if(!ret) {	    if(ident->flags&FPL_REFERENCE)	      return FPLERR_ILLEGAL_VARIABLE; /* this is a reference _only_! */            /* The symbol was found */	    if(control&CON_LEVELOK) /* level _is_ OK! */	      ;            else if(control&CON_DECLARE &&	       (ident->level>=scr->varlevel || scr->varlevel==1)) {              /*               * If the name already declared in this (or higher) level               * and declaration is wanted.               */              if((ident->flags&FPL_STATIC_VARIABLE &&                  control&CON_DECLSTATIC &&                  ident->level==scr->varlevel) ||                 /*                  * If this is a `static' variable and the variable already                  * exists on this very level in this very function as static,                  * then skip this. It's perfectly OK to jump to the ending                  * semicolon since this has been parsed before!                  */                 (ident->flags&FPL_EXPORT_SYMBOL && control&CON_DECLEXP)) {                /*                 * If this is an `export' symbol and it already exists as an                 * `export' symbol! Then just ignore this!                 */                /*                 * The current implementation unfortunately uses the statement                 * below to pass this declaration. That means comma-                 * separated exported symbols will be passed if only the first                 * is alredy declared... This will although work in all those                 * cases it is the SAME code that is executed twice!                 */                if(GetEnd(scr, CHAR_SEMICOLON, (uchar)255, FALSE))                  return FPLERR_MISSING_SEMICOLON;                scr->text--; /* get back on the semicolon! */                break;              } else {                CALL(Warn(scr, FPLERR_IDENTIFIER_USED));                /* run it over! */                DelIdentifier(scr, ident->name, NULL);              }            } else if(!(control&CON_DECLARE) &&                      (ident->level && /* not global */                       ident->level<(scr->varlevel-scr->level)))              /*               * From the wrong program level and we're not declaring.               */              return(FPLERR_IDENTIFIER_NOT_FOUND);            else if(ident->flags&FPL_STATIC_VARIABLE &&                    ((ident->func && (ident->func==scr->func)) ||                     ident->level>scr->varlevel)                    )              /*               * A static variable declared either in the wrong function or               * in a higher level!               */              return(FPLERR_IDENTIFIER_NOT_FOUND);          }          text = NULL; /* no name information yet! */	  control &= ~CON_LEVELOK; /* forget about the level OK stuff!! */          if(*scr->text==CHAR_OPEN_BRACKET) {            /*             * It's an array. Get the result of the expression within the             * square brackets.             */            if(!dims) {              GETMEM(dims, MAX_DIMS*sizeof(long));            }            if(!(control&CON_DECLARE) && pident->data.variable.size)              num=pident->data.variable.num;            if(control&CON_DECLARE || num) {              /*               * Get the name now, cause the GetArrayInfo() call may               * destroy the 'scr->buf' buffer!               */              STRDUP(text, scr->buf);              GETMEM(nump, sizeof(long));              *nump = num;              CALL(GetArrayInfo(scr, dims, nump, control, text));              num = *nump;              FREE(nump);              if(!(control&CON_DECLARE)) {                /*                 * Free the name now, cause we don't declare anything                 * and this isn't needed any more!                 */                FREE(text);                text = NULL;              }              if(!(control&CON_DECLARE)) {                if(num > pident->data.variable.num) {                  /*                   * If not declaring and overfilled quota: fail!                   *                   *                   * Copy the variable name to the buffer to make the                   * error message look good!                   */                  strcpy(scr->buf, pident->name);                  return FPLERR_ILLEGAL_ARRAY;                                  } else {                  for(pos=0; pos<num; pos++)                    if(pident->data.variable.dims[pos]<=dims[pos]) {                      /*                       * Copy the variable name to the buffer to make the                       * error message look good!                       */                      strcpy(scr->buf, pident->name);                      return FPLERR_ILLEGAL_ARRAY;                    }                }              }              point=scr->text; /* move point to current location  */              Eat(scr); /* pass all traling whitespaces */            }          }          if(control&CON_DECLARE) {            expr->flags|=FPL_ACTION;            GETMEM(pident, sizeof(struct Identifier));            pident->level=              (control&(CON_DECLEXP|CON_DECLGLOB))?0:scr->varlevel;            pident->flags=              (control&CON_DECLINT?FPL_INT_VARIABLE:FPL_STRING_VARIABLE)|                (control&CON_DECLEXP?FPL_EXPORT_SYMBOL:0)|                  (control&CON_DECLGLOB?FPL_GLOBAL_SYMBOL:                    (control&CON_DECLSTATIC?FPL_STATIC_VARIABLE:0))|                    (control&CON_DECL8?FPL_CHAR_VARIABLE:                     (control&CON_DECL16?FPL_SHORT_VARIABLE:0))|                       (control&CON_DECLCONST?FPL_READONLY:0);            pident->file=scr->prog->name; /* file */            pident->func=scr->func; /* declared in this function */            /* Get variable name */            if(text)              /*               * The name has already been allocated above!               */              pident->name = text;            else {              /*               * Get the name!               */              STRDUP(pident->name, scr->buf); /* no real strdup */            }            if(num) {              /*               * Array variable declaration! It is a bit different from               * common variable declaration so I decided to put the code               * for it right here:               */              long size=dims[0]; /* array size */              for(pos=1; pos<num; pos++)                size*=dims[pos];              /* Now `size' is the total number of members in the array we're                 about to declare */              /* Get memory for the dimension array */              GETMEM(pident->data.variable.dims, num * sizeof(long));              /* Copy the dim info to the newly allocated area */              memcpy((void *)pident->data.variable.dims, dims, num*sizeof(long));              /* Get memory for the array  */              GETMEM(pident->data.variable.var.val32, size * sizeof(long));              /* Set all string lengths to NULL and integers to zero: */              memset(pident->data.variable.var.val32, 0, size * sizeof(void *));              pident->data.variable.size=size; /* total number of array members */              pident->data.variable.num=num;   /* number of dimensions */              /* reset the dims array! */              memset((void *)dims, 0, sizeof(long) * num);              /* reset num: */              num=1;            } else {#ifdef DEBUG              CheckMem(scr, pident);#endif              GETMEM(pident->data.variable.var.val32, sizeof(long));              *pident->data.variable.var.val32=0;              pident->data.variable.num=0;              pident->data.variable.size=1;

⌨️ 快捷键说明

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