Parcourir la source

Add printOn function and fix readEvalPrint with imports

pull/14/head
mtardy il y a 4 ans
Parent
révision
7ca8267244
4 fichiers modifiés avec 211 ajouts et 83 suppressions
  1. +128
    -0
      buffer.h
  2. +71
    -80
      object.c
  3. +9
    -3
      parse.leg
  4. +3
    -0
      test3.txt

+ 128
- 0
buffer.h Voir le fichier

@ -0,0 +1,128 @@
#ifndef __buffer_h
#define __buffer_h
#include <stdio.h>
#include <stdlib.h>
#include <string.h>
#include <sys/types.h>
#define BUFFER_INITIALISER { 0, 0, 0 }
#define DECLARE_BUFFER(TYPE, NAME) \
\
typedef struct \
{ \
TYPE *contents; \
size_t position; \
size_t capacity; \
} NAME; \
\
extern inline NAME *new##NAME(NAME *b) \
{ \
return calloc(1, sizeof(NAME)); \
} \
\
extern inline NAME *NAME##_release(NAME *b) \
{ \
if (b->contents) free(b->contents); \
memset(b, 0, sizeof(NAME)); \
return b; \
} \
\
extern inline void NAME##_delete(NAME *b) \
{ \
NAME##_release(b); \
free(b); \
} \
\
extern inline void NAME##_clear(NAME *b) \
{ \
b->position= 0; \
} \
\
extern inline size_t NAME##_position(NAME *b) \
{ \
return b->position; \
} \
\
extern inline void NAME##_errorBounds(NAME *b, ssize_t index) \
{ \
fprintf(stderr, "index %zi out of bounds for "#NAME" of size %zi\n", index, b->capacity); \
abort(); \
} \
\
extern inline void NAME##_errorMemory(NAME *b) \
{ \
fprintf(stderr, "out of memory typing to grow "#NAME" of size %zi\n", b->capacity); \
abort(); \
} \
\
extern inline TYPE NAME##_get(NAME *b, ssize_t index) \
{ \
if (index >= 0) { \
if (index < b->position) return b->contents[index]; \
} \
else { \
if (b->position + index >= 0) return b->contents[b->position + index]; \
} \
NAME##_errorBounds(b, index); \
abort(); \
/* NOTREACHED */ \
} \
\
extern inline NAME *NAME##_grow(NAME *b, size_t size) \
{ \
if (0 == size) size= 2; \
if (b->capacity < size) { \
b->contents= b->contents \
? realloc(b->contents, sizeof(TYPE) * size) \
: malloc ( sizeof(TYPE) * size); \
if (!b->contents) NAME##_errorMemory(b); \
memset(b->contents + b->capacity, 0, sizeof(TYPE) * (size - b->capacity)); \
b->capacity= size; \
} \
return b; \
} \
\
extern inline TYPE NAME##_append(NAME *b, TYPE value) \
{ \
if (b->position == b->capacity) NAME##_grow(b, b->capacity * 2); \
return b->contents[b->position++]= value; \
} \
\
extern inline void NAME##_appendAll(NAME *b, const TYPE *s, size_t len) \
{ \
while (len--) NAME##_append(b, *s++); \
} \
\
extern inline TYPE *NAME##_buffer(NAME *b) \
{ \
return b->contents; \
}
#define DECLARE_STRING_BUFFER(TYPE, NAME) \
\
DECLARE_BUFFER(TYPE, NAME); \
\
extern inline TYPE *NAME##_appendString(NAME *b, TYPE *string) \
{ \
for (TYPE *ptr= string; *ptr; ++ptr) NAME##_append(b, *string++); \
return string; \
} \
\
extern inline TYPE *NAME##_contents(NAME *b) \
{ \
NAME##_append(b, 0); \
b->position--; \
return b->contents; \
}
#define buffer_do(T, V, B) \
for ( size_t index_of_##V= 0; \
index_of_##V < (B)->position; \
index_of_##V = (B)->position ) \
for ( T V; \
index_of_##V < (B)->position && (V= (B)->contents[index_of_##V], 1); \
++index_of_##V )
#endif // __buffer_h

+ 71
- 80
object.c Voir le fichier

@ -87,7 +87,6 @@ struct Symbol {
typedef oop (*primitive_t)(oop params);
struct Function {
type_t type;
primitive_t primitive;
@ -173,9 +172,12 @@ void *memcheck(void *ptr)
return ptr;
}
#include "buffer.h"
DECLARE_STRING_BUFFER(char, StringBuffer);
void print(oop ast);
void println(oop ast);
void printOn(StringBuffer *buf, oop obj);
int getInteger(oop obj)
{
@ -456,106 +458,95 @@ oop map_values(oop map)
return values;
}
void map_print(oop map, int ident)
void map_printOn(StringBuffer *buf, oop map, int ident)
{
assert(is(Map, map));
if (ident == 0) {
printf("{";);
map_print(map, ident + 1);
printf("}";);
StringBuffer_append(buf, '{';);
map_printOn(buf, map, ident + 1);
StringBuffer_append(buf, '}';);
return;
}
for (size_t i = 0; i < map_size(map); i++) {
printf("\n";);
StringBuffer_append(buf, '\n';);
for (size_t i = 0; i < ident; i++) {
printf("|");
printf(" ");
if (isatty(fileno(stdout))) {
StringBuffer_appendString(buf, "\033[90m|\033[0m");
} else {
StringBuffer_appendString(buf, "|");
}
StringBuffer_appendString(buf, " ");
}
// todo: a key could be a map itself
print(get(map, Map, elements)[i].key);
printf(": ");
printOn(buf, get(map, Map, elements)[i].key);
StringBuffer_appendString(buf, ": ");
oop rhs = get(map, Map, elements)[i].value;
if (getType(rhs) == Map) {
map_print(rhs, ident + 1);
map_printOn(buf, rhs, ident + 1);
} else {
print(rhs);
printOn(buf, rhs);
}
if (i < map_size(map) - 1) printf(",";);
if (ident == 1 && i == map_size(map) - 1) printf("\n";);
if (i < map_size(map) - 1) StringBuffer_append(buf, ',';);
if (ident == 1 && i == map_size(map) - 1) StringBuffer_append(buf, '\n';);
}
return;
}
char *toString(oop ast)
{
int length;
assert(ast);
switch (getType(ast)) {
case Undefined:
return "null";
case Integer:
//TODO
length = snprintf(NULL, 0, "%d", getInteger(ast));
printf("length is %i\n", length);
printf("%i", getInteger(ast));
return "null";
case String:
return get(ast, String, value);
case Symbol:
return get(ast, Symbol, name);
case Function:
// TODO
if (get(ast, Function, primitive) == NULL) {
printf("Function:");
} else {
printf("Primitive:");
}
print(get(ast, Function, name));
printf("(");
print(get(ast, Function, param));
printf(")");
case Map:
// TODO
map_print(ast, 0);
}
assert(0);
}
void print(oop ast)
void printOn(StringBuffer *buf, oop obj)
{
assert(ast);
switch (getType(ast)) {
case Undefined:
printf("null");
return;
case Integer:
printf("%i", getInteger(ast));
return;
case String:
printf("%s", get(ast, String, value));
return;
case Symbol:
printf("%s", get(ast, Symbol, name));
return;
case Function:
if (get(ast, Function, primitive) == NULL) {
printf("Function:");
} else {
printf("Primitive:");
assert(obj);
switch (getType(obj)) {
case Undefined: {
StringBuffer_appendString(buf, "null");
return;
}
case Integer: {
char tmp[32];
int length = snprintf(tmp, sizeof(tmp), "%i", getInteger(obj));
StringBuffer_appendAll(buf, tmp, length);
return;
}
case String: {
StringBuffer_appendAll(buf, get(obj, String, value), string_size(obj));
return;
}
case Symbol: {
char *name= get(obj, Symbol, name);
StringBuffer_appendString(buf, name);
return;
}
case Function: {
if (get(obj, Function, primitive) == NULL) {
StringBuffer_appendString(buf, "Function:");
} else {
StringBuffer_appendString(buf, "Primitive:");
}
printOn(buf, get(obj, Function, name));
StringBuffer_append(buf, '(');
printOn(buf, get(obj, Function, param));
StringBuffer_append(buf, ')');
return;
}
case Map: {
map_printOn(buf, obj, 0);
return;
}
print(get(ast, Function, name));
printf("(");
print(get(ast, Function, param));
printf(")");
return;
case Map:
map_print(ast, 0);
return;
}
assert(0);
}
char *printString(oop obj)
{
static StringBuffer buf= BUFFER_INITIALISER;
StringBuffer_clear(&buf);
printOn(&buf, obj);
return StringBuffer_contents(&buf);
}
void print(oop obj)
{
fputs(printString(obj), stdout);
}
void println(oop ast)
{
print(ast);

+ 9
- 3
parse.leg Voir le fichier

@ -86,7 +86,7 @@ DO_PROTOS()
#undef _DO
int opt_v= 0;
oop mrAST= null;
oop mrAST= &_null;
typedef struct input_t
{
@ -1852,18 +1852,22 @@ oop evalArgs(oop scope, oop args)
oop AST= NULL;
void readEvalPrint(char *fileName) {
void readEvalPrint(char *fileName)
{
inputStackPush(fileName);
input_t *top= inputStack;
jbRecPush();
jb_record *jtop= jbs;
int jbt= sigsetjmp(jbs->jb, 0);
if (0 == jbt) {
while (inputStack && yyparse()) {
while (yyparse()) {
if (opt_v > 1) printf("%s:%i: ", get(inputStack->name, String, value), inputStack->lineNumber);
if (!yylval) {
fclose(inputStack->file);
if (top == inputStack) break;
inputStackPop();
assert(inputStack);
continue;
} // EOF
if (opt_v > 1) println(yylval);
@ -1871,6 +1875,8 @@ void readEvalPrint(char *fileName) {
if (opt_v > 0) println(res);
assert(jbs == jtop);
}
assert(inputStack);
inputStackPop();
jbRecPop();
return;
}

+ 3
- 0
test3.txt Voir le fichier

@ -0,0 +1,3 @@
println(666)
import "test-proto.txt"
println(12)

Chargement…
Annuler
Enregistrer