// ===================================================================================================================================== // allen_cpu_base_arithmetic.c - Wed 13 jun 2007 00:09 CEST - Allen version 2.0 // ===================================================================================================================================== // Copyright (c) 2007, Archville, BSD License. // A copy can be found here: http://www.opensource.org/licenses/bsd-license.php // Initally based on Salvatore Sanfilippo within Picol 0.1.0 // // All rights reserved. // // Redistribution and use in source and binary forms, with or without modification, // are permitted provided that the following conditions are met: // // * Redistributions of source code must retain the above copyright notice, // this list of conditions and the following disclaimer. // * Redistributions in binary form must reproduce the above copyright notice, // this list of conditions and the following disclaimer in the documentation // and/or other materials provided with the distribution. // * Neither the name of the Garabatos de licor nor the names of its contributors may // be used to endorse or promote products derived from this software // without specific prior written permission. // // This software is provided by the copyright holders and contributors // "as is" and any express or implied warranties, including, but not // limited to, the implied warranties of merchantability and fitness for // a particular purpose are disclaimed. in no event shall the copyright owner or // contributors be liable for any direct, indirect, incidental, special, // exemplary, or consequential damages (including, but not limited to, // procurement of substitute goods or services; loss of use, data, or // profits; or business interruption) however caused and on any theory of // liability, whether in contract, strict liability, or tort (including // negligence or otherwise) arising in any way out of the use of this // software, even if advised of the possibility of such damage. // ===================================================================================================================================== // Include libraries. // ===================================================================================================================================== #include // Standard input/output. #include // Standard C libraries. #include // String libraries. #include // Math libraries. #include // Types and conversion libraries. #include "allen_interpreter.h" // Main interpreter library. #include "allen_parser.h" // Main parser library. // ===================================================================================================================================== // Parameters. // ===================================================================================================================================== #define TBASE_ARITH_BSIZE 1024 // Buffer size. // ===================================================================================================================================== // Possible errors. // ===================================================================================================================================== #define TBASE_ARITH_EDIV "division: parameter is zero" // Error: Divide by zero returns inderminate result. #define TBASE_ARITH_EMOD "modulus: parameter is zero" // Error: Modulus by zero returns indeterminate result. // ===================================================================================================================================== // Tokens. // ===================================================================================================================================== #define TBASE_ARITH_PLS "+" // Addition. #define TBASE_ARITH_DPLS "++" // Increment. #define TBASE_ARITH_MIN "-" // Substraction. #define TBASE_ARITH_DMIN "--" // Decrement. #define TBASE_ARITH_MUL "*" // Multiplication. #define TBASE_ARITH_DMUL "**" // Square. #define TBASE_ARITH_DIV "/" // Division. #define TBASE_ARITH_DDIV "//" // Division without floating point. #define TBASE_ARITH_MOD "%" // Modulus. #define TBASE_ARITH_POW "^" // Pow. // ===================================================================================================================================== // Basic arithmetic operators. // ===================================================================================================================================== // Allows to perform regular arithmetic operations on value lists // and return results based on their expresions. // Index: Example: Result: // AllenVM_CPU_BASE_ARITH_PLS(); :: + 2 3 - 4 1.000000 // AllenVM_CPU_BASE_ARITH_DPLS(); :: ++ 2 3.000000 // AllenVM_CPU_BASE_ARITH_MIN(); :: - 2 3 4 -5.000000 // AllenVM_CPU_BASE_ARITH_DMIN(); :: -- 2 1.000000 // AllenVM_CPU_BASE_ARITH_MUL(); :: * 2 3 4 24.000000 // AllenVM_CPU_BASE_ARITH_DMUL(); :: ** 2 4.000000 // AllenVM_CPU_BASE_ARITH_DIV(); :: / 2 3 4 0.166667 // AllenVM_CPU_BASE_ARITH_DDIV(); :: // 2 3 0 // AllenVM_CPU_BASE_ARITH_MOD(); :: % 10 3 1.000000 // AllenVM_CPU_BASE_ARITH_POW(); :: ^ 2 4 + 1 17.000000 // Total: 10. // ------------------------------------------------------------------------------------------------------------------------------------- // Function: AllenVM_CPU_BASE_ARITH_PLS(); // Purpose: Addition. // Returns: Expression result. // ------------------------------------------------------------------------------------------------------------------------------------- static int AllenVM_CPU_BASE_ARITH_PLS(struct AllenInterp *i, int argc, char **argv, void *pd) { char buf[TBASE_ARITH_BSIZE]; register int p,op; register float c=0; // Buffer and parameters. if(argc>=2) c=atof(argv[1]); // Conversion. for(op=1,p=2; p=2) c=atof(argv[1])+1; // Increment. snprintf(buf,TBASE_ARITH_BSIZE,"%f",c); // Copy result to buffer as float. AllenVM_InterpSetResult(i,buf); // Set interpreter result. return Allen_VM_OK; // Everything ok. } // ------------------------------------------------------------------------------------------------------------------------------------- // Function: AllenVM_CPU_BASE_ARITH_MIN(); // Purpose: Substraction. // Returns: Expression result. // ------------------------------------------------------------------------------------------------------------------------------------- static int AllenVM_CPU_BASE_ARITH_MIN(struct AllenInterp *i, int argc, char **argv, void *pd) { char buf[TBASE_ARITH_BSIZE]; register int p,op; register float c=0; // Buffer and parameters. if(argc>=2) c=atof(argv[1]); // Conversion. for(op=2,p=2; p=2) c=atof(argv[1])-1; // Decrement. snprintf(buf,TBASE_ARITH_BSIZE,"%f",c); // Copy result to buffer as float. AllenVM_InterpSetResult(i,buf); // Set interpreter result. return Allen_VM_OK; // Everything ok. } // ------------------------------------------------------------------------------------------------------------------------------------- // Function: AllenVM_CPU_BASE_ARITH_MUL(); // Purpose: Multiplication. // Returns: Expression result. // ------------------------------------------------------------------------------------------------------------------------------------- static int AllenVM_CPU_BASE_ARITH_MUL(struct AllenInterp *i, int argc, char **argv, void *pd) { char buf[TBASE_ARITH_BSIZE]; register int p,op; register float c=0; // Buffer and parameters. if(argc>=2) c=atof(argv[1]); // Conversion. for(op=3,p=2; p=2) c=atof(argv[1])*atof(argv[1]); // Square. snprintf(buf,TBASE_ARITH_BSIZE,"%f",c); // Copy result to buffer as float. AllenVM_InterpSetResult(i,buf); // Set interpreter result. return Allen_VM_OK; // Everything ok. } // ------------------------------------------------------------------------------------------------------------------------------------- // Function: AllenVM_CPU_BASE_ARITH_DIV(); // Purpose: Division. // Returns: Expression result. // ------------------------------------------------------------------------------------------------------------------------------------- static int AllenVM_CPU_BASE_ARITH_DIV(struct AllenInterp *i, int argc, char **argv, void *pd) { char buf[TBASE_ARITH_BSIZE]; register int p,op; register float c=0; // Buffer and parameters. if(argc>=2) c=atof(argv[1]); // Conversion. for(op=4,p=2; p=2) c=atof(argv[1]); // Conversion. for(p=2; p=2) c=atof(argv[1]); // Conversion. for(op=5,p=2; p=2) c=atof(argv[1]); // Conversion. for(op=6,p=2; p