[DEV] some other rework unneeded elements

This commit is contained in:
Edouard DUPIN 2014-07-15 23:21:52 +02:00
parent 3f5c4725f9
commit 177d1ba8c0
25 changed files with 306 additions and 833 deletions

View File

@ -1,3 +1,11 @@
/**
* @author Edouard DUPIN
*
* @copyright 2014, Edouard DUPIN, all right reserved
*
* @license APACHE-2 (see license file)
*/
#include "picoc.h"
#include "interpreter.h"
@ -46,565 +54,71 @@ void LibraryAdd(struct Table *GlobalTable, const char *LibraryName, struct Libra
/* print a type to a stream without using printf/sprintf */
void PrintType(struct ValueType *Typ, IOFILE *Stream) {
switch (Typ->Base) {
case TypeVoid: PrintStr("void", Stream); break;
case TypeInt: PrintStr("int", Stream); break;
case TypeShort: PrintStr("short", Stream); break;
case TypeChar: PrintStr("char", Stream); break;
case TypeLong: PrintStr("long", Stream); break;
case TypeUnsignedInt: PrintStr("unsigned int", Stream); break;
case TypeUnsignedShort: PrintStr("unsigned short", Stream); break;
case TypeUnsignedLong: PrintStr("unsigned long", Stream); break;
#ifndef NO_FP
case TypeFP: PrintStr("double", Stream); break;
#endif
case TypeFunction: PrintStr("function", Stream); break;
case TypeMacro: PrintStr("macro", Stream); break;
case TypePointer: if (Typ->FromType) PrintType(Typ->FromType, Stream); PrintCh('*', Stream); break;
case TypeArray: PrintType(Typ->FromType, Stream); PrintCh('[', Stream); if (Typ->ArraySize != 0) PrintSimpleInt(Typ->ArraySize, Stream); PrintCh(']', Stream); break;
case TypeStruct: PrintStr("struct ", Stream); PrintStr(Typ->Identifier, Stream); break;
case TypeUnion: PrintStr("union ", Stream); PrintStr(Typ->Identifier, Stream); break;
case TypeEnum: PrintStr("enum ", Stream); PrintStr(Typ->Identifier, Stream); break;
case TypeGotoLabel: PrintStr("goto label ", Stream); break;
case Type_Type: PrintStr("type ", Stream); break;
case TypeVoid:
PrintStr("void", Stream);
break;
case TypeInt:
PrintStr("int", Stream);
break;
case TypeShort:
PrintStr("short", Stream);
break;
case TypeChar:
PrintStr("char", Stream);
break;
case TypeLong:
PrintStr("long", Stream);
break;
case TypeUnsignedInt:
PrintStr("unsigned int", Stream);
break;
case TypeUnsignedShort:
PrintStr("unsigned short", Stream);
break;
case TypeUnsignedLong:
PrintStr("unsigned long", Stream);
break;
case TypeFP:
PrintStr("double", Stream);
break;
case TypeFunction:
PrintStr("function", Stream);
break;
case TypeMacro:
PrintStr("macro", Stream);
break;
case TypePointer:
if (Typ->FromType) {
PrintType(Typ->FromType, Stream);
}
}
#ifdef BUILTIN_MINI_STDLIB
/*
* This is a simplified standard library for small embedded systems. It doesn't require
* a system stdio library to operate.
*
* A more complete standard library for larger computers is in the library_XXX.c files.
*/
IOFILE *CStdOut;
IOFILE CStdOutBase;
static int TRUEValue = 1;
static int ZeroValue = 0;
void BasicIOInit() {
CStdOutBase.Putch = &PlatformPutc;
CStdOut = &CStdOutBase;
}
/* initialise the C library */
void CLibraryInit() {
/* define some constants */
VariableDefinePlatformVar(NULL, "NULL", &IntType, (union AnyValue *)&ZeroValue, FALSE);
VariableDefinePlatformVar(NULL, "TRUE", &IntType, (union AnyValue *)&TRUEValue, FALSE);
VariableDefinePlatformVar(NULL, "FALSE", &IntType, (union AnyValue *)&ZeroValue, FALSE);
}
/* stream for writing into strings */
void SPutc(unsigned char Ch, union OutputStreamInfo *Stream) {
struct StringOutputStream *Out = &Stream->Str;
*Out->WritePos++ = Ch;
}
/* print a character to a stream without using printf/sprintf */
void PrintCh(char OutCh, struct OutputStream *Stream) {
(*Stream->Putch)(OutCh, &Stream->i);
}
/* print a string to a stream without using printf/sprintf */
void PrintStr(const char *Str, struct OutputStream *Stream) {
while (*Str != 0) {
PrintCh(*Str++, Stream);
}
}
/* print a single character a given number of times */
void PrintRepeatedChar(char ShowChar, int Length, struct OutputStream *Stream) {
while (Length-- > 0) {
PrintCh(ShowChar, Stream);
}
}
/* print an unsigned integer to a stream without using printf/sprintf */
void PrintUnsigned(unsigned long Num, unsigned int Base, int FieldWidth, int ZeroPad, int LeftJustify, struct OutputStream *Stream) {
char Result[33];
int ResPos = sizeof(Result);
Result[--ResPos] = '\0';
if (Num == 0) {
Result[--ResPos] = '0';
}
while (Num > 0) {
unsigned long NextNum = Num / Base;
unsigned long Digit = Num - NextNum * Base;
if (Digit < 10) {
Result[--ResPos] = '0' + Digit;
} else {
Result[--ResPos] = 'a' + Digit - 10;
}
Num = NextNum;
}
if (FieldWidth > 0 && !LeftJustify) {
PrintRepeatedChar(ZeroPad ? '0' : ' ', FieldWidth - (sizeof(Result) - 1 - ResPos), Stream);
}
PrintStr(&Result[ResPos], Stream);
if (FieldWidth > 0 && LeftJustify) {
PrintRepeatedChar(' ', FieldWidth - (sizeof(Result) - 1 - ResPos), Stream);
}
}
/* print an integer to a stream without using printf/sprintf */
void PrintSimpleInt(long Num, struct OutputStream *Stream) {
PrintInt(Num, -1, FALSE, FALSE, Stream);
}
/* print an integer to a stream without using printf/sprintf */
void PrintInt(long Num, int FieldWidth, int ZeroPad, int LeftJustify, struct OutputStream *Stream) {
if (Num < 0) {
PrintCh('-', Stream);
Num = -Num;
if (FieldWidth != 0) {
FieldWidth--;
}
}
PrintUnsigned((unsigned long)Num, 10, FieldWidth, ZeroPad, LeftJustify, Stream);
}
#ifndef NO_FP
/* print a double to a stream without using printf/sprintf */
void PrintFP(double Num, struct OutputStream *Stream) {
int Exponent = 0;
int MaxDecimal;
if (Num < 0) {
PrintCh('-', Stream);
Num = -Num;
}
if (Num >= 1e7) {
Exponent = log10(Num);
} else if (Num <= 1e-7 && Num != 0.0) {
Exponent = log10(Num) - 0.999999999;
}
Num /= pow(10.0, Exponent);
PrintInt((long)Num, 0, FALSE, FALSE, Stream);
PrintCh('.', Stream);
Num = (Num - (long)Num) * 10;
if (abs(Num) >= 1e-7) {
for (MaxDecimal = 6; MaxDecimal > 0 && abs(Num) >= 1e-7; Num = (Num - (long)(Num + 1e-7)) * 10, MaxDecimal--) {
PrintCh('0' + (long)(Num + 1e-7), Stream);
}
} else {
PrintCh('0', Stream);
}
if (Exponent != 0) {
PrintCh('e', Stream);
PrintInt(Exponent, 0, FALSE, FALSE, Stream);
}
}
#endif
/* intrinsic functions made available to the language */
void GenericPrintf(struct ParseState *Parser, struct Value *ReturnValue, struct Value **Param, int NumArgs, struct OutputStream *Stream) {
char *FPos;
struct Value *NextArg = Param[0];
struct ValueType *FormatType;
int ArgCount = 1;
int LeftJustify = FALSE;
int ZeroPad = FALSE;
int FieldWidth = 0;
char *Format = Param[0]->Val->Pointer;
for (FPos = Format; *FPos != '\0'; FPos++) {
if (*FPos == '%') {
FPos++;
if (*FPos == '-') {
/* a leading '-' means left justify */
LeftJustify = TRUE;
FPos++;
}
if (*FPos == '0') {
/* a leading zero means zero pad a decimal number */
ZeroPad = TRUE;
FPos++;
}
/* get any field width in the format */
while (isdigit((int)*FPos)) {
FieldWidth = FieldWidth * 10 + (*FPos++ - '0');
}
/* now check the format type */
switch (*FPos) {
case 's': FormatType = CharPtrType; break;
case 'd': case 'u': case 'x': case 'b': case 'c': FormatType = &IntType; break;
#ifndef NO_FP
case 'f': FormatType = &FPType; break;
#endif
case '%': PrintCh('%', Stream); FormatType = NULL; break;
case '\0': FPos--; FormatType = NULL; break;
default: PrintCh(*FPos, Stream); FormatType = NULL; break;
}
if (FormatType != NULL) {
/* we have to format something */
if (ArgCount >= NumArgs) {
PrintStr("XXX", Stream); /* not enough parameters for format */
} else {
NextArg = (struct Value *)((char *)NextArg + MEM_ALIGN(sizeof(struct Value) + TypeStackSizeValue(NextArg)));
if (NextArg->Typ != FormatType &&
!((FormatType == &IntType || *FPos == 'f') && IS_NUMERIC_COERCIBLE(NextArg)) &&
!(FormatType == CharPtrType && (NextArg->Typ->Base == TypePointer ||
(NextArg->Typ->Base == TypeArray && NextArg->Typ->FromType->Base == TypeChar) ) ) ) {
PrintStr("XXX", Stream); /* bad type for format */
} else {
switch (*FPos) {
case 's':
{
char *Str;
if (NextArg->Typ->Base == TypePointer) {
Str = NextArg->Val->Pointer;
}else {
Str = &NextArg->Val->ArrayMem[0];
}
if (Str == NULL) {
PrintStr("NULL", Stream);
} else {
PrintStr(Str, Stream);
PrintCh('*', Stream);
break;
case TypeArray:
PrintType(Typ->FromType, Stream);
PrintCh('[', Stream);
if (Typ->ArraySize != 0) {
PrintSimpleInt(Typ->ArraySize, Stream);
}
PrintCh(']', Stream);
break;
case TypeStruct:
PrintStr("struct ", Stream);
PrintStr(Typ->Identifier, Stream);
break;
case TypeUnion:
PrintStr("union ", Stream);
PrintStr(Typ->Identifier, Stream);
break;
case TypeEnum:
PrintStr("enum ", Stream);
PrintStr(Typ->Identifier, Stream);
break;
case TypeGotoLabel:
PrintStr("goto label ", Stream);
break;
case Type_Type:
PrintStr("type ", Stream);
break;
}
case 'd': PrintInt(ExpressionCoerceInteger(NextArg), FieldWidth, ZeroPad, LeftJustify, Stream); break;
case 'u': PrintUnsigned(ExpressionCoerceUnsignedInteger(NextArg), 10, FieldWidth, ZeroPad, LeftJustify, Stream); break;
case 'x': PrintUnsigned(ExpressionCoerceUnsignedInteger(NextArg), 16, FieldWidth, ZeroPad, LeftJustify, Stream); break;
case 'b': PrintUnsigned(ExpressionCoerceUnsignedInteger(NextArg), 2, FieldWidth, ZeroPad, LeftJustify, Stream); break;
case 'c': PrintCh(ExpressionCoerceUnsignedInteger(NextArg), Stream); break;
#ifndef NO_FP
case 'f': PrintFP(ExpressionCoerceFP(NextArg), Stream); break;
#endif
}
}
}
ArgCount++;
}
} else {
PrintCh(*FPos, Stream);
}
}
}
/* printf(): print to console output */
void LibPrintf(struct ParseState *Parser, struct Value *ReturnValue, struct Value **Param, int NumArgs) {
struct OutputStream ConsoleStream;
ConsoleStream.Putch = &PlatformPutc;
GenericPrintf(Parser, ReturnValue, Param, NumArgs, &ConsoleStream);
}
/* sprintf(): print to a string */
void LibSPrintf(struct ParseState *Parser, struct Value *ReturnValue, struct Value **Param, int NumArgs) {
struct OutputStream StrStream;
StrStream.Putch = &SPutc;
StrStream.i.Str.Parser = Parser;
StrStream.i.Str.WritePos = Param[0]->Val->Pointer;
GenericPrintf(Parser, ReturnValue, Param+1, NumArgs-1, &StrStream);
PrintCh(0, &StrStream);
ReturnValue->Val->Pointer = *Param;
}
/* get a line of input. protected from buffer overrun */
void LibGets(struct ParseState *Parser, struct Value *ReturnValue, struct Value **Param, int NumArgs) {
ReturnValue->Val->Pointer = PlatformGetLine(Param[0]->Val->Pointer, GETS_BUF_MAX, NULL);
if (ReturnValue->Val->Pointer != NULL) {
char *EOLPos = strchr(Param[0]->Val->Pointer, '\n');
if (EOLPos != NULL) {
*EOLPos = '\0';
}
}
}
void LibGetc(struct ParseState *Parser, struct Value *ReturnValue, struct Value **Param, int NumArgs) {
ReturnValue->Val->Integer = PlatformGetCharacter();
}
void LibExit(struct ParseState *Parser, struct Value *ReturnValue, struct Value **Param, int NumArgs) {
PlatformExit(Param[0]->Val->Integer);
}
#ifdef PICOC_LIBRARY
void LibSin(struct ParseState *Parser, struct Value *ReturnValue, struct Value **Param, int NumArgs) {
ReturnValue->Val->FP = sin(Param[0]->Val->FP);
}
void LibCos(struct ParseState *Parser, struct Value *ReturnValue, struct Value **Param, int NumArgs) {
ReturnValue->Val->FP = cos(Param[0]->Val->FP);
}
void LibTan(struct ParseState *Parser, struct Value *ReturnValue, struct Value **Param, int NumArgs) {
ReturnValue->Val->FP = tan(Param[0]->Val->FP);
}
void LibAsin(struct ParseState *Parser, struct Value *ReturnValue, struct Value **Param, int NumArgs) {
ReturnValue->Val->FP = asin(Param[0]->Val->FP);
}
void LibAcos(struct ParseState *Parser, struct Value *ReturnValue, struct Value **Param, int NumArgs) {
ReturnValue->Val->FP = acos(Param[0]->Val->FP);
}
void LibAtan(struct ParseState *Parser, struct Value *ReturnValue, struct Value **Param, int NumArgs) {
ReturnValue->Val->FP = atan(Param[0]->Val->FP);
}
void LibSinh(struct ParseState *Parser, struct Value *ReturnValue, struct Value **Param, int NumArgs) {
ReturnValue->Val->FP = sinh(Param[0]->Val->FP);
}
void LibCosh(struct ParseState *Parser, struct Value *ReturnValue, struct Value **Param, int NumArgs) {
ReturnValue->Val->FP = cosh(Param[0]->Val->FP);
}
void LibTanh(struct ParseState *Parser, struct Value *ReturnValue, struct Value **Param, int NumArgs) {
ReturnValue->Val->FP = tanh(Param[0]->Val->FP);
}
void LibExp(struct ParseState *Parser, struct Value *ReturnValue, struct Value **Param, int NumArgs) {
ReturnValue->Val->FP = exp(Param[0]->Val->FP);
}
void LibFabs(struct ParseState *Parser, struct Value *ReturnValue, struct Value **Param, int NumArgs) {
ReturnValue->Val->FP = fabs(Param[0]->Val->FP);
}
void LibLog(struct ParseState *Parser, struct Value *ReturnValue, struct Value **Param, int NumArgs) {
ReturnValue->Val->FP = log(Param[0]->Val->FP);
}
void LibLog10(struct ParseState *Parser, struct Value *ReturnValue, struct Value **Param, int NumArgs) {
ReturnValue->Val->FP = log10(Param[0]->Val->FP);
}
void LibPow(struct ParseState *Parser, struct Value *ReturnValue, struct Value **Param, int NumArgs) {
ReturnValue->Val->FP = pow(Param[0]->Val->FP, Param[1]->Val->FP);
}
void LibSqrt(struct ParseState *Parser, struct Value *ReturnValue, struct Value **Param, int NumArgs) {
ReturnValue->Val->FP = sqrt(Param[0]->Val->FP);
}
void LibRound(struct ParseState *Parser, struct Value *ReturnValue, struct Value **Param, int NumArgs) {
ReturnValue->Val->FP = floor(Param[0]->Val->FP + 0.5); /* XXX - fix for soft float */
}
void LibCeil(struct ParseState *Parser, struct Value *ReturnValue, struct Value **Param, int NumArgs) {
ReturnValue->Val->FP = ceil(Param[0]->Val->FP);
}
void LibFloor(struct ParseState *Parser, struct Value *ReturnValue, struct Value **Param, int NumArgs) {
ReturnValue->Val->FP = floor(Param[0]->Val->FP);
}
#endif
#ifndef NO_STRING_FUNCTIONS
void LibMalloc(struct ParseState *Parser, struct Value *ReturnValue, struct Value **Param, int NumArgs) {
ReturnValue->Val->Pointer = malloc(Param[0]->Val->Integer);
}
#ifndef NO_CALLOC
void LibCalloc(struct ParseState *Parser, struct Value *ReturnValue, struct Value **Param, int NumArgs) {
ReturnValue->Val->Pointer = calloc(Param[0]->Val->Integer, Param[1]->Val->Integer);
}
#endif
#ifndef NO_REALLOC
void LibRealloc(struct ParseState *Parser, struct Value *ReturnValue, struct Value **Param, int NumArgs) {
ReturnValue->Val->Pointer = realloc(Param[0]->Val->Pointer, Param[1]->Val->Integer);
}
#endif
void LibFree(struct ParseState *Parser, struct Value *ReturnValue, struct Value **Param, int NumArgs) {
free(Param[0]->Val->Pointer);
}
void LibStrcpy(struct ParseState *Parser, struct Value *ReturnValue, struct Value **Param, int NumArgs) {
char *To = (char *)Param[0]->Val->Pointer;
char *From = (char *)Param[1]->Val->Pointer;
while (*From != '\0') {
*To++ = *From++;
}
*To = '\0';
}
void LibStrncpy(struct ParseState *Parser, struct Value *ReturnValue, struct Value **Param, int NumArgs) {
char *To = (char *)Param[0]->Val->Pointer;
char *From = (char *)Param[1]->Val->Pointer;
int Len = Param[2]->Val->Integer;
for (; *From != '\0' && Len > 0; Len--) {
*To++ = *From++;
}
if (Len > 0) {
*To = '\0';
}
}
void LibStrcmp(struct ParseState *Parser, struct Value *ReturnValue, struct Value **Param, int NumArgs) {
char *Str1 = (char *)Param[0]->Val->Pointer;
char *Str2 = (char *)Param[1]->Val->Pointer;
int StrEnded;
for (StrEnded = FALSE; !StrEnded; StrEnded = (*Str1 == '\0' || *Str2 == '\0'), Str1++, Str2++) {
if (*Str1 < *Str2) {
ReturnValue->Val->Integer = -1;
return;
} else if (*Str1 > *Str2) {
ReturnValue->Val->Integer = 1;
return;
}
}
ReturnValue->Val->Integer = 0;
}
void LibStrncmp(struct ParseState *Parser, struct Value *ReturnValue, struct Value **Param, int NumArgs) {
char *Str1 = (char *)Param[0]->Val->Pointer;
char *Str2 = (char *)Param[1]->Val->Pointer;
int Len = Param[2]->Val->Integer;
int StrEnded;
for (StrEnded = FALSE; !StrEnded && Len > 0; StrEnded = (*Str1 == '\0' || *Str2 == '\0'), Str1++, Str2++, Len--) {
if (*Str1 < *Str2) {
ReturnValue->Val->Integer = -1;
return;
} else if (*Str1 > *Str2) {
ReturnValue->Val->Integer = 1;
return;
}
}
ReturnValue->Val->Integer = 0;
}
void LibStrcat(struct ParseState *Parser, struct Value *ReturnValue, struct Value **Param, int NumArgs) {
char *To = (char *)Param[0]->Val->Pointer;
char *From = (char *)Param[1]->Val->Pointer;
while (*To != '\0') {
To++;
}
while (*From != '\0') {
*To++ = *From++;
}
*To = '\0';
}
void LibIndex(struct ParseState *Parser, struct Value *ReturnValue, struct Value **Param, int NumArgs) {
char *Pos = (char *)Param[0]->Val->Pointer;
int SearchChar = Param[1]->Val->Integer;
while (*Pos != '\0' && *Pos != SearchChar) {
Pos++;
}
if (*Pos != SearchChar) {
ReturnValue->Val->Pointer = NULL;
} else {
ReturnValue->Val->Pointer = Pos;
}
}
void LibRindex(struct ParseState *Parser, struct Value *ReturnValue, struct Value **Param, int NumArgs) {
char *Pos = (char *)Param[0]->Val->Pointer;
int SearchChar = Param[1]->Val->Integer;
ReturnValue->Val->Pointer = NULL;
for (; *Pos != '\0'; Pos++) {
if (*Pos == SearchChar) {
ReturnValue->Val->Pointer = Pos;
}
}
}
void LibStrlen(struct ParseState *Parser, struct Value *ReturnValue, struct Value **Param, int NumArgs) {
char *Pos = (char *)Param[0]->Val->Pointer;
int Len;
for (Len = 0; *Pos != '\0'; Pos++) {
Len++;
}
ReturnValue->Val->Integer = Len;
}
void LibMemset(struct ParseState *Parser, struct Value *ReturnValue, struct Value **Param, int NumArgs) {
/* we can use the system memset() */
memset(Param[0]->Val->Pointer, Param[1]->Val->Integer, Param[2]->Val->Integer);
}
void LibMemcpy(struct ParseState *Parser, struct Value *ReturnValue, struct Value **Param, int NumArgs) {
/* we can use the system memcpy() */
memcpy(Param[0]->Val->Pointer, Param[1]->Val->Pointer, Param[2]->Val->Integer);
}
void LibMemcmp(struct ParseState *Parser, struct Value *ReturnValue, struct Value **Param, int NumArgs) {
unsigned char *Mem1 = (unsigned char *)Param[0]->Val->Pointer;
unsigned char *Mem2 = (unsigned char *)Param[1]->Val->Pointer;
int Len = Param[2]->Val->Integer;
for (; Len > 0; Mem1++, Mem2++, Len--) {
if (*Mem1 < *Mem2) {
ReturnValue->Val->Integer = -1;
return;
} else if (*Mem1 > *Mem2) {
ReturnValue->Val->Integer = 1;
return;
}
}
ReturnValue->Val->Integer = 0;
}
#endif
/* list of all library functions and their prototypes */
struct LibraryFunction CLibrary[] = {
{ LibPrintf, "void printf(char *, ...);" },
{ LibSPrintf, "char *sprintf(char *, char *, ...);" },
{ LibGets, "char *gets(char *);" },
{ LibGetc, "int getchar();" },
{ LibExit, "void exit(int);" },
#ifdef PICOC_LIBRARY
{ LibSin, "float sin(float);" },
{ LibCos, "float cos(float);" },
{ LibTan, "float tan(float);" },
{ LibAsin, "float asin(float);" },
{ LibAcos, "float acos(float);" },
{ LibAtan, "float atan(float);" },
{ LibSinh, "float sinh(float);" },
{ LibCosh, "float cosh(float);" },
{ LibTanh, "float tanh(float);" },
{ LibExp, "float exp(float);" },
{ LibFabs, "float fabs(float);" },
{ LibLog, "float log(float);" },
{ LibLog10, "float log10(float);" },
{ LibPow, "float pow(float,float);" },
{ LibSqrt, "float sqrt(float);" },
{ LibRound, "float round(float);" },
{ LibCeil, "float ceil(float);" },
{ LibFloor, "float floor(float);" },
#endif
{ LibMalloc, "void *malloc(int);" },
#ifndef NO_CALLOC
{ LibCalloc, "void *calloc(int,int);" },
#endif
#ifndef NO_REALLOC
{ LibRealloc, "void *realloc(void *,int);" },
#endif
{ LibFree, "void free(void *);" },
#ifndef NO_STRING_FUNCTIONS
{ LibStrcpy, "void strcpy(char *,char *);" },
{ LibStrncpy, "void strncpy(char *,char *,int);" },
{ LibStrcmp, "int strcmp(char *,char *);" },
{ LibStrncmp, "int strncmp(char *,char *,int);" },
{ LibStrcat, "void strcat(char *,char *);" },
{ LibIndex, "char *index(char *,int);" },
{ LibRindex, "char *rindex(char *,int);" },
{ LibStrlen, "int strlen(char *);" },
{ LibMemset, "void memset(void *,int,int);" },
{ LibMemcpy, "void memcpy(void *,void *,int);" },
{ LibMemcmp, "int memcmp(void *,void *,int);" },
#endif
{ NULL, NULL }
};
#endif /* BUILTIN_MINI_STDLIB */

View File

@ -1,3 +1,11 @@
/**
* @author Edouard DUPIN
*
* @copyright 2014, Edouard DUPIN, all right reserved
*
* @license APACHE-2 (see license file)
*/
/* string.h library for large systems - small embedded systems use clibrary.c instead */
#include <ctype.h>
#include "../interpreter.h"

View File

@ -1,3 +1,11 @@
/**
* @author Edouard DUPIN
*
* @copyright 2014, Edouard DUPIN, all right reserved
*
* @license APACHE-2 (see license file)
*/
/* string.h library for large systems - small embedded systems use clibrary.c instead */
#include <errno.h>
#include "../interpreter.h"

View File

@ -1,8 +1,15 @@
/**
* @author Edouard DUPIN
*
* @copyright 2014, Edouard DUPIN, all right reserved
*
* @license APACHE-2 (see license file)
*/
/* stdio.h library for large systems - small embedded systems use clibrary.c instead */
#include "../interpreter.h"
#ifndef BUILTIN_MINI_STDLIB
#ifndef NO_FP
static double M_EValue = 2.7182818284590452354; /* e */
static double M_LOG2EValue = 1.4426950408889634074; /* log_2 e */
@ -158,5 +165,4 @@ void MathSetupFunc() {
VariableDefinePlatformVar(NULL, "M_SQRT1_2", &FPType, (union AnyValue *)&M_SQRT1_2Value, FALSE);
}
#endif /* !NO_FP */
#endif /* !BUILTIN_MINI_STDLIB */

View File

@ -1,3 +1,11 @@
/**
* @author Edouard DUPIN
*
* @copyright 2014, Edouard DUPIN, all right reserved
*
* @license APACHE-2 (see license file)
*/
/* string.h library for large systems - small embedded systems use clibrary.c instead */
#include "../interpreter.h"

View File

@ -1,3 +1,11 @@
/**
* @author Edouard DUPIN
*
* @copyright 2014, Edouard DUPIN, all right reserved
*
* @license APACHE-2 (see license file)
*/
/* stdio.h library for large systems - small embedded systems use clibrary.c instead */
#include <errno.h>
#include "../interpreter.h"
@ -174,7 +182,6 @@ int StdioBasePrintf(struct ParseState *Parser, FILE *Stream, char *StrOut, int S
ShowType = &IntType;
break;
/* integer base conversions */
#ifndef NO_FP
case 'e':
case 'E':
ShowType = &FPType;
@ -190,7 +197,6 @@ int StdioBasePrintf(struct ParseState *Parser, FILE *Stream, char *StrOut, int S
ShowType = &FPType;
break;
/* double, flexible format */
#endif
case 'a':
case 'A':
ShowType = &IntType;
@ -268,18 +274,14 @@ int StdioBasePrintf(struct ParseState *Parser, FILE *Stream, char *StrOut, int S
} else {
StdioOutPuts("XXX", &SOStream);
}
}
#ifndef NO_FP
else if (ShowType == &FPType) {
} else if (ShowType == &FPType) {
/* show a floating point number */
if (IS_NUMERIC_COERCIBLE(ThisArg)) {
StdioFprintfFP(&SOStream, OneFormatBuf, ExpressionCoerceFP(ThisArg));
} else {
StdioOutPuts("XXX", &SOStream);
}
}
#endif
else if (ShowType == CharPtrType) {
} else if (ShowType == CharPtrType) {
if (ThisArg->Typ->Base == TypePointer) {
StdioFprintfPointer(&SOStream, OneFormatBuf, ThisArg->Val->Pointer);
} else if ( ThisArg->Typ->Base == TypeArray

View File

@ -1,3 +1,11 @@
/**
* @author Edouard DUPIN
*
* @copyright 2014, Edouard DUPIN, all right reserved
*
* @license APACHE-2 (see license file)
*/
/* stdlib.h library for large systems - small embedded systems use clibrary.c instead */
#include "../interpreter.h"
@ -5,11 +13,9 @@
static int ZeroValue = 0;
#ifndef NO_FP
void StdlibAtof(struct ParseState *Parser, struct Value *ReturnValue, struct Value **Param, int NumArgs) {
ReturnValue->Val->FP = atof(Param[0]->Val->Pointer);
}
#endif
void StdlibAtoi(struct ParseState *Parser, struct Value *ReturnValue, struct Value **Param, int NumArgs) {
ReturnValue->Val->Integer = atoi(Param[0]->Val->Pointer);
@ -19,11 +25,9 @@ void StdlibAtol(struct ParseState *Parser, struct Value *ReturnValue, struct Val
ReturnValue->Val->Integer = atol(Param[0]->Val->Pointer);
}
#ifndef NO_FP
void StdlibStrtod(struct ParseState *Parser, struct Value *ReturnValue, struct Value **Param, int NumArgs) {
ReturnValue->Val->FP = strtod(Param[0]->Val->Pointer, Param[1]->Val->Pointer);
}
#endif
void StdlibStrtol(struct ParseState *Parser, struct Value *ReturnValue, struct Value **Param, int NumArgs) {
ReturnValue->Val->Integer = strtol(Param[0]->Val->Pointer, Param[1]->Val->Pointer, Param[2]->Val->Integer);
@ -84,10 +88,8 @@ void StdlibLabs(struct ParseState *Parser, struct Value *ReturnValue, struct Val
/* all stdlib.h functions */
struct LibraryFunction StdlibFunctions[] =
{
#ifndef NO_FP
{ StdlibAtof, "float atof(char *);" },
{ StdlibStrtod, "float strtod(char *,char **);" },
#endif
{ StdlibAtoi, "int atoi(char *);" },
{ StdlibAtol, "int atol(char *);" },
{ StdlibStrtol, "int strtol(char *,char **,int);" },
@ -115,4 +117,4 @@ void StdlibSetupFunc() {
}
}
#endif /* !BUILTIN_MINI_STDLIB */
#endif

View File

@ -1,3 +1,11 @@
/**
* @author Edouard DUPIN
*
* @copyright 2014, Edouard DUPIN, all right reserved
*
* @license APACHE-2 (see license file)
*/
/* string.h library for large systems - small embedded systems use clibrary.c instead */
#include "../interpreter.h"

View File

@ -1,3 +1,11 @@
/**
* @author Edouard DUPIN
*
* @copyright 2014, Edouard DUPIN, all right reserved
*
* @license APACHE-2 (see license file)
*/
/* string.h library for large systems - small embedded systems use clibrary.c instead */
#include <time.h>
#include "../interpreter.h"
@ -26,11 +34,9 @@ void StdCtime(struct ParseState *Parser, struct Value *ReturnValue, struct Value
ReturnValue->Val->Pointer = ctime(Param[0]->Val->Pointer);
}
#ifndef NO_FP
void StdDifftime(struct ParseState *Parser, struct Value *ReturnValue, struct Value **Param, int NumArgs) {
ReturnValue->Val->FP = difftime((time_t)Param[0]->Val->Integer, Param[1]->Val->Integer);
}
#endif
void StdGmtime(struct ParseState *Parser, struct Value *ReturnValue, struct Value **Param, int NumArgs) {
ReturnValue->Val->Pointer = gmtime(Param[0]->Val->Pointer);
@ -76,9 +82,7 @@ struct LibraryFunction StdTimeFunctions[] = {
{ StdAsctime, "char *asctime(struct tm *);" },
{ StdClock, "time_t clock();" },
{ StdCtime, "char *ctime(int *);" },
#ifndef NO_FP
{ StdDifftime, "double difftime(int, int);" },
#endif
{ StdGmtime, "struct tm *gmtime(int *);" },
{ StdGmtime_r, "struct tm *gmtime_r(int *, struct tm *);" },
{ StdLocaltime, "struct tm *localtime(int *);" },

View File

@ -1,3 +1,11 @@
/**
* @author Edouard DUPIN
*
* @copyright 2014, Edouard DUPIN, all right reserved
*
* @license APACHE-2 (see license file)
*/
/* stdlib.h library for large systems - small embedded systems use clibrary.c instead */
#include <stdio.h>
#include <unistd.h>

View File

@ -1,3 +1,11 @@
/**
* @author Edouard DUPIN
*
* @copyright 2014, Edouard DUPIN, all right reserved
*
* @license APACHE-2 (see license file)
*/
#include "interpreter.h"
@ -168,10 +176,8 @@ long ExpressionCoerceInteger(struct Value *Val) {
return (long)Val->Val->UnsignedLongInteger;
case TypePointer:
return (long)Val->Val->Pointer;
#ifndef NO_FP
case TypeFP:
return (long)Val->Val->FP;
#endif
default:
return 0;
}
@ -195,16 +201,13 @@ unsigned long ExpressionCoerceUnsignedInteger(struct Value *Val) {
return (unsigned long)Val->Val->UnsignedLongInteger;
case TypePointer:
return (unsigned long)Val->Val->Pointer;
#ifndef NO_FP
case TypeFP:
return (unsigned long)Val->Val->FP;
#endif
default:
return 0;
}
}
#ifndef NO_FP
double ExpressionCoerceFP(struct Value *Val) {
#ifndef BROKEN_FLOAT_CASTS
int IntVal;
@ -259,7 +262,6 @@ double ExpressionCoerceFP(struct Value *Val) {
}
#endif
}
#endif
/* assign an integer value */
long ExpressionAssignInt(struct ParseState *_parser, struct Value *DestValue, long FromInt, int After) {
@ -300,7 +302,6 @@ long ExpressionAssignInt(struct ParseState *_parser, struct Value *DestValue, lo
return Result;
}
#ifndef NO_FP
/* assign a floating point value */
double ExpressionAssignFP(struct ParseState *_parser, struct Value *DestValue, double FromFP) {
if (!DestValue->IsLValue) {
@ -309,7 +310,6 @@ double ExpressionAssignFP(struct ParseState *_parser, struct Value *DestValue, d
DestValue->Val->FP = FromFP;
return FromFP;
}
#endif
/* push a node on to the expression stack */
void ExpressionStackPushValueNode(struct ParseState *_parser, struct ExpressionStack **StackTop, struct Value *ValueLoc) {
@ -365,13 +365,11 @@ void ExpressionPushInt(struct ParseState *_parser, struct ExpressionStack **Stac
ExpressionStackPushValueNode(_parser, StackTop, ValueLoc);
}
#ifndef NO_FP
void ExpressionPushFP(struct ParseState *_parser, struct ExpressionStack **StackTop, double FPValue) {
struct Value *ValueLoc = VariableAllocValueFromType(_parser, &FPType, FALSE, NULL, FALSE);
ValueLoc->Val->FP = FPValue;
ExpressionStackPushValueNode(_parser, StackTop, ValueLoc);
}
#endif
/* assign to a pointer */
void ExpressionAssignToPointer(struct ParseState *_parser, struct Value *ToValue, struct Value *FromValue, const char *FuncName, int ParamNo, int AllowPointerCoercion) {
@ -441,14 +439,12 @@ void ExpressionAssign(struct ParseState *_parser, struct Value *DestValue, struc
case TypeUnsignedLong:
DestValue->Val->UnsignedLongInteger = ExpressionCoerceUnsignedInteger(SourceValue);
break;
#ifndef NO_FP
case TypeFP:
if (!IS_NUMERIC_COERCIBLE_PLUS_POINTERS(SourceValue, AllowPointerCoercion)) {
AssignFail(_parser, "%t from %t", DestValue->Typ, SourceValue->Typ, 0, 0, FuncName, ParamNo);
}
DestValue->Val->FP = ExpressionCoerceFP(SourceValue);
break;
#endif
case TypePointer:
ExpressionAssignToPointer(_parser, DestValue, SourceValue, FuncName, ParamNo, AllowPointerCoercion);
break;
@ -527,7 +523,6 @@ void ExpressionPrefixOperator(struct ParseState *_parser, struct ExpressionStack
break;
default:
/* an arithmetic operator */
#ifndef NO_FP
if (TopValue->Typ == &FPType) {
/* floating point prefix arithmetic */
double ResultFP = 0.0;
@ -543,9 +538,7 @@ void ExpressionPrefixOperator(struct ParseState *_parser, struct ExpressionStack
break;
}
ExpressionPushFP(_parser, StackTop, ResultFP);
} else
#endif
if (IS_NUMERIC_COERCIBLE(TopValue)) {
} else if (IS_NUMERIC_COERCIBLE(TopValue)) {
/* integer prefix arithmetic */
long ResultInt = 0;
long TopInt = ExpressionCoerceInteger(TopValue);
@ -694,9 +687,7 @@ void ExpressionInfixOperator(struct ParseState *_parser, struct ExpressionStack
ExpressionQuestionMarkOperator(_parser, StackTop, TopValue, BottomValue);
} else if (Op == TokenColon) {
ExpressionColonOperator(_parser, StackTop, TopValue, BottomValue);
}
#ifndef NO_FP
else if ( (TopValue->Typ == &FPType && BottomValue->Typ == &FPType)
} else if ( (TopValue->Typ == &FPType && BottomValue->Typ == &FPType)
|| (TopValue->Typ == &FPType && IS_NUMERIC_COERCIBLE(BottomValue))
|| (IS_NUMERIC_COERCIBLE(TopValue) && BottomValue->Typ == &FPType) ) {
/* floating point infix arithmetic */
@ -765,9 +756,7 @@ void ExpressionInfixOperator(struct ParseState *_parser, struct ExpressionStack
} else {
ExpressionPushFP(_parser, StackTop, ResultFP);
}
}
#endif
else if (IS_NUMERIC_COERCIBLE(TopValue) && IS_NUMERIC_COERCIBLE(BottomValue)) {
} else if (IS_NUMERIC_COERCIBLE(TopValue) && IS_NUMERIC_COERCIBLE(BottomValue)) {
/* integer operation */
long TopInt = ExpressionCoerceInteger(TopValue);
long BottomInt = ExpressionCoerceInteger(BottomValue);
@ -1348,11 +1337,7 @@ void ExpressionParseMacroCall(struct ParseState *_parser, struct ExpressionStack
enum LexToken Token;
if (_parser->Mode == RunModeRun) {
/* create a stack frame for this macro */
#ifndef NO_FP
ExpressionStackPushValueByType(_parser, StackTop, &FPType); /* largest return type there is */
#else
ExpressionStackPushValueByType(_parser, StackTop, &IntType); /* largest return type there is */
#endif
ReturnValue = (*StackTop)->Val;
HeapPushStackFrame();
ParamArray = HeapAllocStack(sizeof(struct Value *) * MDef->NumParams);

View File

@ -1,3 +1,11 @@
/**
* @author Edouard DUPIN
*
* @copyright 2014, Edouard DUPIN, all right reserved
*
* @license APACHE-2 (see license file)
*/
/* stack grows up from the bottom and heap grows down from the top of heap space */
#include "interpreter.h"

View File

@ -1,3 +1,11 @@
/**
* @author Edouard DUPIN
*
* @copyright 2014, Edouard DUPIN, all right reserved
*
* @license APACHE-2 (see license file)
*/
#include "picoc.h"
#include "interpreter.h"
@ -19,9 +27,7 @@ void IncludeInit() {
#ifndef BUILTIN_MINI_STDLIB
IncludeRegister("ctype.h", NULL, &StdCtypeFunctions[0], NULL);
IncludeRegister("errno.h", &StdErrnoSetupFunc, NULL, NULL);
#ifndef NO_FP
IncludeRegister("math.h", &MathSetupFunc, &MathFunctions[0], NULL);
#endif
IncludeRegister("stdbool.h", &StdboolSetupFunc, NULL, StdboolDefs);
IncludeRegister("stdio.h", &StdioSetupFunc, &StdioFunctions[0], StdioDefs);
IncludeRegister("stdlib.h", &StdlibSetupFunc, &StdlibFunctions[0], NULL);

View File

@ -1,5 +1,13 @@
#ifndef INTERPRETER_H
#define INTERPRETER_H
/**
* @author Edouard DUPIN
*
* @copyright 2014, Edouard DUPIN, all right reserved
*
* @license APACHE-2 (see license file)
*/
#ifndef __ECI_INTERPRETER_H__
#define __ECI_INTERPRETER_H__
#include "platform.h"
@ -30,13 +38,8 @@ typedef FILE IOFILE;
#endif
/* coercion of numeric types to other numeric types */
#ifndef NO_FP
#define IS_FP(v) ((v)->Typ->Base == TypeFP)
#define FP_VAL(v) ((v)->Val->FP)
#else
#define IS_FP(v) 0
#define FP_VAL(v) 0
#endif
#define IS_POINTER_COERCIBLE(v, ap) ((ap) ? ((v)->Typ->Base == TypePointer) : 0)
#define POINTER_COERCE(v) ((int)(v)->Val->Pointer)
@ -122,9 +125,7 @@ enum BaseType {
TypeUnsignedInt, //!< unsigned integer
TypeUnsignedShort, //!< unsigned short integer
TypeUnsignedLong, //!< unsigned long integer
#ifndef NO_FP
TypeFP, //!< floating point
#endif
TypeFunction, //!< a function
TypeMacro, //!< a macro
TypePointer, //!< a pointer
@ -183,9 +184,7 @@ union AnyValue {
struct ValueType *Typ;
struct FuncDef FuncDef;
struct MacroDef MacroDef;
#ifndef NO_FP
double FP;
#endif
void *Pointer; //!< unsafe native pointers
};
@ -289,9 +288,7 @@ extern struct StackFrame *TopStackFrame;
extern struct ValueType UberType;
extern struct ValueType IntType;
extern struct ValueType CharType;
#ifndef NO_FP
extern struct ValueType FPType;
#endif
extern struct ValueType VoidType;
extern struct ValueType TypeType;
extern struct ValueType FunctionType;
@ -307,111 +304,31 @@ extern struct LibraryFunction CLibrary[];
extern struct LibraryFunction PlatformLibrary[];
extern IOFILE *CStdOut;
/* table.c */
void TableInit();
char *TableStrRegister(const char *_str);
char *TableStrRegister2(const char *_str, int Len);
void TableInitTable(struct Table *_table, struct TableEntry **_hashTable, int _size, int _onHeap);
int TableSet(struct Table *Tbl, char *Key, struct Value *Val, const char *DeclFileName, int DeclLine, int DeclColumn);
int TableGet(struct Table *Tbl, const char *Key, struct Value **Val, const char **DeclFileName, int *DeclLine, int *DeclColumn);
struct Value *TableDelete(struct Table *Tbl, const char *Key);
char *TableSetIdentifier(struct Table *Tbl, const char *Ident, int IdentLen);
void TableStrFree();
#include <eci/lex.h>
#include <eci/parse.h>
#include <eci/expression.h>
/* lex.c */
void LexInit();
void LexCleanup();
void *LexAnalyse(const char *FileName, const char *Source, int SourceLen, int *TokenLen);
void LexInitParser(struct ParseState *Parser, const char *SourceText, void *TokenSource, const char *FileName, int RunIt);
enum LexToken LexGetToken(struct ParseState *Parser, struct Value **Value, int IncPos);
enum LexToken LexRawPeekToken(struct ParseState *Parser);
void LexToEndOfLine(struct ParseState *Parser);
void *LexCopyTokens(struct ParseState *StartParser, struct ParseState *EndParser);
void LexInteractiveClear(struct ParseState *Parser);
void LexInteractiveCompleted(struct ParseState *Parser);
void LexInteractiveStatementPrompt();
#include <eci/heap.h>
/* parse.c */
/* the following are defined in picoc.h:
* void PicocParse(const char *FileName, const char *Source, int SourceLen, int RunIt, int CleanupNow, int CleanupSource);
* void PicocParseInteractive(); */
enum ParseResult ParseStatement(struct ParseState *Parser, int CheckTrailingSemicolon);
struct Value *ParseFunctionDefinition(struct ParseState *Parser, struct ValueType *ReturnType, char *Identifier);
void ParseCleanup();
void ParserCopyPos(struct ParseState *To, struct ParseState *From);
void ParserCopy(struct ParseState *To, struct ParseState *From);
#include <eci/table.h>
#include <eci/type.h>
#include <eci/variable.h>
#include <eci/include.h>
#include <eci/clibrary.h>
#include <eci/platform.h>
#include <eci/cstdlib/ctype.h>
#include <eci/cstdlib/errno.h>
#include <eci/cstdlib/math.h>
#include <eci/cstdlib/stdbool.h>
#include <eci/cstdlib/stdio.h>
#include <eci/cstdlib/stdlib.h>
#include <eci/cstdlib/string.h>
#include <eci/cstdlib/time.h>
#include <eci/cstdlib/unistd.h>
/* expression.c */
int ExpressionParse(struct ParseState *Parser, struct Value **Result);
long ExpressionParseInt(struct ParseState *Parser);
void ExpressionAssign(struct ParseState *Parser, struct Value *DestValue, struct Value *SourceValue, int Force, const char *FuncName, int ParamNo, int AllowPointerCoercion);
long ExpressionCoerceInteger(struct Value *Val);
unsigned long ExpressionCoerceUnsignedInteger(struct Value *Val);
#ifndef NO_FP
double ExpressionCoerceFP(struct Value *Val);
#endif
/* type.c */
void TypeInit();
void TypeCleanup();
int TypeSize(struct ValueType *Typ, int ArraySize, int Compact);
int TypeSizeValue(struct Value *Val, int Compact);
int TypeStackSizeValue(struct Value *Val);
int TypeLastAccessibleOffset(struct Value *Val);
int TypeParseFront(struct ParseState *Parser, struct ValueType **Typ, int *IsStatic);
void TypeParseIdentPart(struct ParseState *Parser, struct ValueType *BasicTyp, struct ValueType **Typ, char **Identifier);
void TypeParse(struct ParseState *Parser, struct ValueType **Typ, char **Identifier, int *IsStatic);
struct ValueType *TypeGetMatching(struct ParseState *Parser, struct ValueType *ParentType, enum BaseType Base, int ArraySize, const char *Identifier, int AllowDuplicates);
struct ValueType *TypeCreateOpaqueStruct(struct ParseState *Parser, const char *StructName, int Size);
// TODO : Move this ... platform.h:
/* heap.c */
void HeapInit(int StackSize);
void HeapCleanup();
void *HeapAllocStack(int Size);
int HeapPopStack(void *Addr, int Size);
void HeapUnpopStack(int Size);
void HeapPushStackFrame();
int HeapPopStackFrame();
void *HeapAllocMem(int Size);
void HeapFreeMem(void *Mem);
/* variable.c */
void VariableInit();
void VariableCleanup();
void VariableFree(struct Value *Val);
void VariableTableCleanup(struct Table *HashTable);
void *VariableAlloc(struct ParseState *Parser, int Size, int OnHeap);
void VariableStackPop(struct ParseState *Parser, struct Value *Var);
struct Value *VariableAllocValueAndData(struct ParseState *Parser, int DataSize, int IsLValue, struct Value *LValueFrom, int OnHeap);
struct Value *VariableAllocValueAndCopy(struct ParseState *Parser, struct Value *FromValue, int OnHeap);
struct Value *VariableAllocValueFromType(struct ParseState *Parser, struct ValueType *Typ, int IsLValue, struct Value *LValueFrom, int OnHeap);
struct Value *VariableAllocValueFromExistingData(struct ParseState *Parser, struct ValueType *Typ, union AnyValue *FromValue, int IsLValue, struct Value *LValueFrom);
struct Value *VariableAllocValueShared(struct ParseState *Parser, struct Value *FromValue);
struct Value *VariableDefine(struct ParseState *Parser, char *Ident, struct Value *InitValue, struct ValueType *Typ, int MakeWritable);
struct Value *VariableDefineButIgnoreIdentical(struct ParseState *Parser, char *Ident, struct ValueType *Typ, int IsStatic, int *FirstVisit);
int VariableDefined(const char *Ident);
void VariableGet(struct ParseState *Parser, const char *Ident, struct Value **LVal);
void VariableDefinePlatformVar(struct ParseState *Parser, char *Ident, struct ValueType *Typ, union AnyValue *FromValue, int IsWritable);
void VariableStackFrameAdd(struct ParseState *Parser, const char *FuncName, int NumParams);
void VariableStackFramePop(struct ParseState *Parser);
struct Value *VariableStringLiteralGet(char *Ident);
void VariableStringLiteralDefine(char *Ident, struct Value *Val);
void *VariableDereferencePointer(struct ParseState *Parser, struct Value *PointerValue, struct Value **DerefVal, int *DerefOffset, struct ValueType **DerefType, int *DerefIsLValue);
/* clibrary.c */
void BasicIOInit();
void LibraryInit();
void LibraryAdd(struct Table *GlobalTable, const char *LibraryName, struct LibraryFunction *FuncList);
void CLibraryInit();
void PrintCh(char OutCh, IOFILE *Stream);
void PrintSimpleInt(long Num, IOFILE *Stream);
void PrintInt(long Num, int FieldWidth, int ZeroPad, int LeftJustify, IOFILE *Stream);
void PrintStr(const char *Str, IOFILE *Stream);
void PrintFP(double Num, IOFILE *Stream);
void PrintType(struct ValueType *Typ, IOFILE *Stream);
void LibPrintf(struct ParseState *Parser, struct Value *ReturnValue, struct Value **Param, int NumArgs);
/* platform.c */
/* the following are defined in picoc.h:
* void PicocCallMain(int argc, char **argv);
* int PicocPlatformSetExitPoint();
@ -433,49 +350,5 @@ void PlatformExit(int ExitVal);
char *PlatformMakeTempName(char *TempNameBuffer);
void PlatformLibraryInit();
/* include.c */
void IncludeInit();
void IncludeCleanup();
void IncludeRegister(const char *IncludeName, void (*SetupFunction)(void), struct LibraryFunction *FuncList, const char *SetupCSource);
void IncludeFile(char *Filename);
/* the following is defined in picoc.h:
* void PicocIncludeAllSystemHeaders(); */
/* stdio.c */
extern const char StdioDefs[];
extern struct LibraryFunction StdioFunctions[];
void StdioSetupFunc(void);
/* math.c */
extern struct LibraryFunction MathFunctions[];
void MathSetupFunc(void);
/* string.c */
extern struct LibraryFunction StringFunctions[];
void StringSetupFunc(void);
/* stdlib.c */
extern struct LibraryFunction StdlibFunctions[];
void StdlibSetupFunc(void);
/* time.c */
extern const char StdTimeDefs[];
extern struct LibraryFunction StdTimeFunctions[];
void StdTimeSetupFunc(void);
/* errno.c */
void StdErrnoSetupFunc(void);
/* ctype.c */
extern struct LibraryFunction StdCtypeFunctions[];
/* stdbool.c */
extern const char StdboolDefs[];
void StdboolSetupFunc(void);
/* unistd.c */
extern const char UnistdDefs[];
extern struct LibraryFunction UnistdFunctions[];
void UnistdSetupFunc(void);
#endif /* INTERPRETER_H */
#endif

View File

@ -1,3 +1,11 @@
/**
* @author Edouard DUPIN
*
* @copyright 2014, Edouard DUPIN, all right reserved
*
* @license APACHE-2 (see license file)
*/
#include "interpreter.h"
#ifdef NO_CTYPE
@ -50,15 +58,11 @@ static struct ReservedWord ReservedWords[] = {
{ "default", TokenDefault, NULL },
{ "delete", TokenDelete, NULL },
{ "do", TokenDo, NULL },
#ifndef NO_FP
{ "double", TokenDoubleType, NULL },
#endif
{ "else", TokenElse, NULL },
{ "enum", TokenEnumType, NULL },
{ "extern", TokenExternType, NULL },
#ifndef NO_FP
{ "float", TokenFloatType, NULL },
#endif
{ "for", TokenFor, NULL },
{ "goto", TokenGoto, NULL },
{ "if", TokenIf, NULL },
@ -122,10 +126,8 @@ enum LexToken LexGetNumber(struct LexState *Lexer, struct Value *Value) {
int Result = 0;
int Base = 10;
enum LexToken ResultToken;
#ifndef NO_FP
double FPResult;
double FPDiv;
#endif
if (*Lexer->Pos == '0') {
/* a binary, octal or hex literal */
LEXER_INC(Lexer);
@ -163,7 +165,6 @@ enum LexToken LexGetNumber(struct LexState *Lexer, struct Value *Value) {
LEXER_INC(Lexer);
return ResultToken;
}
#ifndef NO_FP
if ( Lexer->Pos == Lexer->End
|| *Lexer->Pos != '.') {
return ResultToken;
@ -190,9 +191,6 @@ enum LexToken LexGetNumber(struct LexState *Lexer, struct Value *Value) {
}
Value->Val->FP = FPResult;
return TokenFPConstant;
#else
return ResultToken;
#endif
}
/* get a reserved word or identifier - used while scanning */
@ -724,11 +722,9 @@ enum LexToken LexGetRawToken(struct ParseState *Parser, struct Value **Value, in
case TokenCharacterConstant:
LexValue.Typ = &CharType;
break;
#ifndef NO_FP
case TokenFPConstant:
LexValue.Typ = &FPType;
break;
#endif
default:
break;
}

View File

@ -1,3 +1,11 @@
/**
* @author Edouard DUPIN
*
* @copyright 2014, Edouard DUPIN, all right reserved
*
* @license APACHE-2 (see license file)
*/
#include "picoc.h"
#include "interpreter.h"
@ -742,7 +750,7 @@ void PicocParse(const char *FileName, const char *Source, int SourceLen, int Run
void PicocParseInteractive() {
struct ParseState Parser;
enum ParseResult Ok;
PlatformPrintf(INTERACTIVE_PROMPT_START);
PlatformPrintf("Starting eci " ECI_VERSION "\n");
LexInitParser(&Parser, NULL, NULL, StrEmpty, TRUE);
PicocPlatformSetExitPoint();
LexInteractiveClear(&Parser);

View File

@ -1,3 +1,11 @@
/**
* @author Edouard DUPIN
*
* @copyright 2014, Edouard DUPIN, all right reserved
*
* @license APACHE-2 (see license file)
*/
/* include only picoc.h here - should be able to use it with only the external interfaces, no internals from interpreter.h */
#include "picoc.h"

View File

@ -1,8 +1,16 @@
#ifndef PICOC_H
#define PICOC_H
/**
* @author Edouard DUPIN
*
* @copyright 2014, Edouard DUPIN, all right reserved
*
* @license APACHE-2 (see license file)
*/
/* picoc version number */
#define PICOC_VERSION "v2.1"
#ifndef __ECI_H__
#define __ECI_H__
/* eci version number */
#define ECI_VERSION "v0.1"
/* handy definitions */
#ifndef TRUE
@ -34,4 +42,4 @@ extern int PicocExitValue;
/* include.c */
void PicocIncludeAllSystemHeaders();
#endif /* PICOC_H */
#endif

View File

@ -1,3 +1,11 @@
/**
* @author Edouard DUPIN
*
* @copyright 2014, Edouard DUPIN, all right reserved
*
* @license APACHE-2 (see license file)
*/
#include "picoc.h"
#include "interpreter.h"
@ -180,11 +188,9 @@ void PlatformVPrintf(const char *Format, va_list Args) {
case 't':
PrintType(va_arg(Args, struct ValueType *), CStdOut);
break;
#ifndef NO_FP
case 'f':
PrintFP(va_arg(Args, double), CStdOut);
break;
#endif
case '%':
PrintCh('%', CStdOut);
break;

View File

@ -1,6 +1,13 @@
/* all platform-specific includes and defines go in this file */
#ifndef PLATFORM_H
#define PLATFORM_H
/**
* @author Edouard DUPIN
*
* @copyright 2014, Edouard DUPIN, all right reserved
*
* @license APACHE-2 (see license file)
*/
#ifndef __ECI_PLATFORM_H__
#define __ECI_PLATFORM_H__
#define LARGE_INT_POWER_OF_TEN 1000000000 /* the largest power of ten which fits in an int on this architecture */
#define ALIGN_TYPE void * /* the default data type to use for alignment */
@ -13,8 +20,7 @@
#define LOCAL_TABLE_SIZE 11 /* size of local variable table (can expand) */
#define STRUCT_TABLE_SIZE 11 /* size of struct/union member table (can expand) */
#define INTERACTIVE_PROMPT_START "starting picoc " PICOC_VERSION "\n"
#define INTERACTIVE_PROMPT_STATEMENT "picoc> "
#define INTERACTIVE_PROMPT_STATEMENT "eci> "
#define INTERACTIVE_PROMPT_LINE " > "
/* host platform includes */
@ -28,16 +34,9 @@
#include <unistd.h>
#include <stdarg.h>
#include <setjmp.h>
#ifndef NO_FP
# include <math.h>
# define PICOC_MATH_LIBRARY
/*# define USE_READLINE*/
# undef BIG_ENDIAN
# if defined(__powerpc__) || defined(__hppa__) || defined(__sparc__)
# define BIG_ENDIAN
# endif
#endif
#include <math.h>
extern jmp_buf ExitBuf;
#endif /* PLATFORM_H */
#endif

View File

@ -1,3 +1,11 @@
/**
* @author Edouard DUPIN
*
* @copyright 2014, Edouard DUPIN, all right reserved
*
* @license APACHE-2 (see license file)
*/
#include "../interpreter.h"
void UnixSetupFunc() {

View File

@ -1,11 +1,14 @@
/**
* @author Edouard DUPIN
*
* @copyright 2014, Edouard DUPIN, all right reserved
*
* @license APACHE-2 (see license file)
*/
#include "../picoc.h"
#include "../interpreter.h"
#ifdef USE_READLINE
#include <readline/readline.h>
#include <readline/history.h>
#endif
/* mark where to end the program for platforms which require this */
jmp_buf PicocExitBuf;
@ -15,23 +18,6 @@ void PlatformCleanup() {
/* get a line of interactive input */
char *PlatformGetLine(char *Buf, int MaxLen, const char *Prompt) {
#ifdef USE_READLINE
if (Prompt != NULL) {
/* use GNU readline to read the line */
char *InLine = readline(Prompt);
if (InLine == NULL) {
return NULL;
}
Buf[MaxLen] = '\0';
strncpy(Buf, InLine, MaxLen-1);
strncat(Buf, "\n", MaxLen-1);
if (InLine[0] != '\0') {
add_history(InLine);
}
free(InLine);
return Buf;
}
#endif
if (Prompt != NULL) {
printf("%s", Prompt);
}

View File

@ -1,3 +1,11 @@
/**
* @author Edouard DUPIN
*
* @copyright 2014, Edouard DUPIN, all right reserved
*
* @license APACHE-2 (see license file)
*/
#include "interpreter.h"
struct Table StringTable;

View File

@ -1,3 +1,11 @@
/**
* @author Edouard DUPIN
*
* @copyright 2014, Edouard DUPIN, all right reserved
*
* @license APACHE-2 (see license file)
*/
#include "interpreter.h"
/* some basic types */
@ -9,9 +17,7 @@ struct ValueType LongType;
struct ValueType UnsignedIntType;
struct ValueType UnsignedShortType;
struct ValueType UnsignedLongType;
#ifndef NO_FP
struct ValueType FPType;
#endif
struct ValueType VoidType;
struct ValueType TypeType;
struct ValueType FunctionType;
@ -148,12 +154,10 @@ void TypeInit() {
char x;
long y;
} la;
#ifndef NO_FP
struct DoubleAlign {
char x;
double y;
} da;
#endif
struct PointerAlign {
char x;
void *y;
@ -174,12 +178,8 @@ void TypeInit() {
TypeAddBaseType(&FunctionType, TypeFunction, sizeof(int), IntAlignBytes);
TypeAddBaseType(&MacroType, TypeMacro, sizeof(int), IntAlignBytes);
TypeAddBaseType(&GotoLabelType, TypeGotoLabel, 0, 1);
#ifndef NO_FP
TypeAddBaseType(&FPType, TypeFP, sizeof(double), (char *)&da.y - &da.x);
TypeAddBaseType(&TypeType, Type_Type, sizeof(double), (char *)&da.y - &da.x); /* must be large enough to cast to a double */
#else
TypeAddBaseType(&TypeType, Type_Type, sizeof(struct ValueType *), PointerAlignBytes);
#endif
CharArrayType = TypeAdd(NULL, &CharType, TypeArray, 0, StrEmpty, sizeof(char), (char *)&ca.y - &ca.x);
CharPtrType = TypeAdd(NULL, &CharType, TypePointer, 0, StrEmpty, sizeof(void *), PointerAlignBytes);
CharPtrPtrType = TypeAdd(NULL, CharPtrType, TypePointer, 0, StrEmpty, sizeof(void *), PointerAlignBytes);
@ -404,12 +404,10 @@ int TypeParseFront(struct ParseState *Parser, struct ValueType **Typ, int *IsSta
case TokenLongType:
*Typ = Unsigned ? &UnsignedLongType : &LongType;
break;
#ifndef NO_FP
case TokenFloatType:
case TokenDoubleType:
*Typ = &FPType;
break;
#endif
case TokenVoidType:
*Typ = &VoidType;
break;

View File

@ -1,3 +1,11 @@
/**
* @author Edouard DUPIN
*
* @copyright 2014, Edouard DUPIN, all right reserved
*
* @license APACHE-2 (see license file)
*/
#include "interpreter.h"
/* maximum size of a value to temporarily copy while we create a variable */