mirror of
https://git.code.sf.net/p/newrpl/sources
synced 2024-11-16 19:51:25 +01:00
220 lines
5.6 KiB
C
220 lines
5.6 KiB
C
#include "newrpl.h"
|
|
#include "libraries.h"
|
|
#include "hal.h"
|
|
// LIB 64 PROVIDES COMMANDS THAT DEAL WITH ROUNDING AND PRECISION
|
|
|
|
// MAIN LIBRARY NUMBER, CHANGE THIS FOR EACH LIBRARY
|
|
#define LIBRARY_NUMBER 64
|
|
#define LIB_ENUM lib64_enum
|
|
#define LIB_NAMES lib64_names
|
|
#define LIB_HANDLER lib64_handler
|
|
#define LIB_NUMBEROFCMDS LIB64_NUMBEROFCMDS
|
|
|
|
// LIST OF COMMANDS EXPORTED, CHANGE FOR EACH LIBRARY
|
|
#define CMD_LIST \
|
|
CMD(SETPREC), \
|
|
CMD(FLOOR), \
|
|
CMD(CEIL), \
|
|
CMD(IP), \
|
|
CMD(FP)
|
|
|
|
// ADD MORE OPCODES HERE
|
|
|
|
|
|
// EXTRA LIST FOR COMMANDS WITH SYMBOLS THAT ARE DISALLOWED IN AN ENUM
|
|
// THE NAMES AND ENUM SYMBOLS ARE GIVEN SEPARATELY
|
|
/*#define CMD_EXTRANAME \
|
|
"VOID",
|
|
|
|
#define CMD_EXTRAENUM \
|
|
VOID
|
|
*/
|
|
|
|
// INTERNAL DECLARATIONS
|
|
|
|
|
|
// CREATE AN ENUM WITH THE OPCODE NAMES FOR THE DISPATCHER
|
|
#define CMD(a) a
|
|
enum LIB_ENUM { CMD_LIST /*, CMD_EXTRAENUM */, LIB_NUMBEROFCMDS };
|
|
#undef CMD
|
|
|
|
// AND A LIST OF STRINGS WITH THE NAMES FOR THE COMPILER
|
|
#define CMD(a) #a
|
|
char *LIB_NAMES[]= { CMD_LIST /*, CMD_EXTRANAME*/ };
|
|
#undef CMD
|
|
|
|
|
|
void LIB_HANDLER()
|
|
{
|
|
if(ISPROLOG(CurOpcode)) {
|
|
// THIS LIBRARY DOES NOT DEFINE ANY OBJECTS
|
|
Exceptions=EX_BADOPCODE;
|
|
ExceptionPointer=IPtr;
|
|
return;
|
|
}
|
|
|
|
switch(OPCODE(CurOpcode))
|
|
{
|
|
case SETPREC:
|
|
{
|
|
// TAKE AN INTEGER NUMBER FROM THE STACK
|
|
if(rplDepthData()<1) {
|
|
Exceptions|=EX_BADARGCOUNT;
|
|
ExceptionPointer=IPtr;
|
|
return;
|
|
}
|
|
BINT64 number=rplReadNumberAsBINT(rplPeekData(1));
|
|
if(Exceptions) return;
|
|
if(number<9) number=9;
|
|
if(number>REAL_PRECISION_MAX) number=REAL_PRECISION_MAX;
|
|
mpd_qsetprec(&Context,number);
|
|
rplDropData(1);
|
|
return;
|
|
}
|
|
|
|
case FLOOR:
|
|
{
|
|
if(rplDepthData()<1) {
|
|
Exceptions|=EX_BADARGCOUNT;
|
|
ExceptionPointer=IPtr;
|
|
return;
|
|
}
|
|
WORDPTR arg=rplPeekData(1);
|
|
mpd_t rnum;
|
|
if(ISBINT(*arg)) return;
|
|
rplReadNumberAsReal(rplPeekData(1),&rnum);
|
|
if(Exceptions) return;
|
|
mpd_floor(&RReg[1],&rnum,&Context);
|
|
if(Exceptions) return;
|
|
rplDropData(1);
|
|
rplRRegToRealPush(1);
|
|
return;
|
|
}
|
|
|
|
case CEIL:
|
|
{
|
|
if(rplDepthData()<1) {
|
|
Exceptions|=EX_BADARGCOUNT;
|
|
ExceptionPointer=IPtr;
|
|
return;
|
|
}
|
|
WORDPTR arg=rplPeekData(1);
|
|
if(ISBINT(*arg)) return;
|
|
mpd_t rnum;
|
|
rplReadNumberAsReal(rplPeekData(1),&rnum);
|
|
if(Exceptions) return;
|
|
mpd_ceil(&RReg[1],&rnum,&Context);
|
|
if(Exceptions) return;
|
|
rplDropData(1);
|
|
rplRRegToRealPush(1);
|
|
return;
|
|
}
|
|
|
|
case IP:
|
|
{
|
|
if(rplDepthData()<1) {
|
|
Exceptions|=EX_BADARGCOUNT;
|
|
ExceptionPointer=IPtr;
|
|
return;
|
|
}
|
|
WORDPTR arg=rplPeekData(1);
|
|
if(ISBINT(*arg)) return;
|
|
mpd_t rnum;
|
|
rplReadNumberAsReal(arg,&rnum);
|
|
if(Exceptions) return;
|
|
mpd_trunc(&RReg[1],&rnum,&Context);
|
|
if(Exceptions) return;
|
|
rplDropData(1);
|
|
rplRRegToRealPush(1);
|
|
return;
|
|
}
|
|
|
|
case FP:
|
|
{
|
|
if(rplDepthData()<1) {
|
|
Exceptions|=EX_BADARGCOUNT;
|
|
ExceptionPointer=IPtr;
|
|
return;
|
|
}
|
|
WORDPTR arg=rplPeekData(1);
|
|
if(ISBINT(*arg)) {
|
|
rplDropData(1);
|
|
rplNewSINTPush(0,DECBINT);
|
|
return;
|
|
}
|
|
mpd_t rnum;
|
|
rplReadNumberAsReal(arg,&rnum);
|
|
if(Exceptions) return;
|
|
mpd_trunc(&RReg[1],&rnum,&Context);
|
|
if(Exceptions) return;
|
|
mpd_sub(&RReg[2],&rnum,&RReg[1],&Context);
|
|
if(Exceptions) return;
|
|
rplDropData(1);
|
|
rplRRegToRealPush(2);
|
|
return;
|
|
}
|
|
|
|
|
|
// ADD MORE OPCODES HERE
|
|
|
|
// STANDARIZED OPCODES:
|
|
// --------------------
|
|
// LIBRARIES ARE FORCED TO ALWAYS HANDLE THE STANDARD OPCODES
|
|
|
|
|
|
case OPCODE_COMPILE:
|
|
// COMPILE RECEIVES:
|
|
// TokenStart = token string
|
|
// TokenLen = token length
|
|
// BlankStart = token blanks afterwards
|
|
// BlanksLen = blanks length
|
|
// CurrentConstruct = Opcode of current construct/WORD of current composite
|
|
|
|
// COMPILE RETURNS:
|
|
// RetNum = enum CompileErrors
|
|
|
|
|
|
// THIS STANDARD FUNCTION WILL TAKE CARE OF COMPILATION OF STANDARD COMMANDS GIVEN IN THE LIST
|
|
// NO NEED TO CHANGE THIS UNLESS CUSTOM OPCODES
|
|
libCompileCmds(LIBRARY_NUMBER,LIB_NAMES,NULL,LIB_NUMBEROFCMDS);
|
|
|
|
return;
|
|
|
|
case OPCODE_DECOMPILE:
|
|
// DECOMPILE RECEIVES:
|
|
// DecompileObject = Ptr to WORD of object to decompile
|
|
// DecompStringEnd = Ptr to the end of decompile string
|
|
|
|
//DECOMPILE RETURNS
|
|
// RetNum = enum DecompileErrors
|
|
|
|
// THIS STANDARD FUNCTION WILL TAKE CARE OF DECOMPILING STANDARD COMMANDS GIVEN IN THE LIST
|
|
// NO NEED TO CHANGE THIS UNLESS THERE ARE CUSTOM OPCODES
|
|
libDecompileCmds(LIB_NAMES,NULL,LIB_NUMBEROFCMDS);
|
|
return;
|
|
case OPCODE_VALIDATE:
|
|
// VALIDATE RECEIVES OPCODES COMPILED BY OTHER LIBRARIES, TO BE INCLUDED WITHIN A COMPOSITE OWNED BY
|
|
// THIS LIBRARY. EVERY COMPOSITE HAS TO EVALUATE IF THE OBJECT BEING COMPILED IS ALLOWED INSIDE THIS
|
|
// COMPOSITE OR NOT. FOR EXAMPLE, A REAL MATRIX SHOULD ONLY ALLOW REAL NUMBERS INSIDE, ANY OTHER
|
|
// OPCODES SHOULD BE REJECTED AND AN ERROR THROWN.
|
|
// TokenStart = token string
|
|
// TokenLen = token length
|
|
// ArgNum2 = Opcode/WORD of object
|
|
|
|
// VALIDATE RETURNS:
|
|
// RetNum = enum CompileErrors
|
|
|
|
|
|
|
|
return;
|
|
}
|
|
// BY DEFAULT, ISSUE A BAD OPCODE ERROR
|
|
Exceptions|=EX_BADOPCODE;
|
|
ExceptionPointer=IPtr;
|
|
return;
|
|
|
|
}
|
|
|
|
|
|
|
|
|