barely working bindings
This commit is contained in:
parent
5751d3fd42
commit
2014412d5b
|
@ -28,6 +28,7 @@ SET(HDRS
|
|||
tokenizer.h
|
||||
unicode.h
|
||||
error.h
|
||||
binding.h
|
||||
)
|
||||
|
||||
SET(SRCS
|
||||
|
@ -38,6 +39,7 @@ SET(SRCS
|
|||
tokenizer.c
|
||||
unicode.c
|
||||
error.c
|
||||
binding.c
|
||||
)
|
||||
|
||||
add_executable(lci ${SRCS} ${HDRS})
|
||||
|
|
|
@ -0,0 +1,43 @@
|
|||
#include "binding.h"
|
||||
|
||||
struct returnobject;
|
||||
struct scopeobject;
|
||||
struct returnobject *fopenWrapper(struct scopeobject *scope)
|
||||
{
|
||||
fprintf(stderr, "HERE\n");
|
||||
}
|
||||
|
||||
void loadBinding(ScopeObject *scope)
|
||||
{
|
||||
/* TODO: add error checking and handling */
|
||||
|
||||
/* stdio */
|
||||
|
||||
Binding *fopen = malloc(sizeof(Binding));
|
||||
|
||||
fopen->library = createIdentifierNode(IT_DIRECT, (void *)copyString("STDIO"), NULL, NULL, 0);
|
||||
|
||||
IdentifierNode* name = createIdentifierNode(IT_DIRECT, (void *)copyString("FOPENIN"), NULL, NULL, 0);
|
||||
IdentifierNodeList *args = createIdentifierNodeList();
|
||||
IdentifierNode *filename = createIdentifierNode(IT_DIRECT, (void *)copyString("filename"), NULL, NULL, 0);
|
||||
IdentifierNode *mode = createIdentifierNode(IT_DIRECT, (void *)copyString("mode"), NULL, NULL, 0);
|
||||
addIdentifierNode(args, filename);
|
||||
addIdentifierNode(args, mode);
|
||||
StmtNodeList *stmts = createStmtNodeList();
|
||||
BindingStmtNode *binding = createBindingStmtNode(&fopenWrapper);
|
||||
StmtNode *wrapper = createStmtNode(ST_BINDING, binding);
|
||||
addStmtNode(stmts, wrapper);
|
||||
BlockNode *body = createBlockNode(stmts);
|
||||
/* TODO: should this first parameter be NULL? */
|
||||
fopen->interface = createFuncDefStmtNode(NULL, name, args, body);
|
||||
ValueObject *val = createFunctionValueObject(fopen->interface);
|
||||
|
||||
createScopeValue(scope, scope, name);
|
||||
updateScopeValue(scope, scope, name, val);
|
||||
|
||||
return;
|
||||
|
||||
loadBindingAbort: /* Exception handling */
|
||||
|
||||
return;
|
||||
}
|
|
@ -0,0 +1,49 @@
|
|||
/**
|
||||
* Structures and functions for binding to external libraries.
|
||||
*
|
||||
* \file binding.h
|
||||
*
|
||||
* \author Justin J. Meza
|
||||
*
|
||||
* \date 2013
|
||||
*/
|
||||
|
||||
#ifndef __BINDING_H__
|
||||
#define __BINDING_H__
|
||||
|
||||
#include <stdio.h>
|
||||
|
||||
#include "interpreter.h"
|
||||
|
||||
/**
|
||||
* Stores a binding to an external library call to export.
|
||||
*/
|
||||
typedef struct {
|
||||
IdentifierNode *library; /**< The library this binding belongs to. */
|
||||
FuncDefStmtNode *interface; /**< The interface that exports the binding. */
|
||||
} Binding;
|
||||
|
||||
void loadBinding(ScopeObject *); /* TODO: make this take an IdentifierNode library to load */
|
||||
|
||||
/**
|
||||
* TODO:
|
||||
* - At startup, check which bindings are imported (using "CAN HAS" syntax)
|
||||
* - Package those bindings as VT_FUNCs in BUKKITs
|
||||
* - Add those bindings to the top-level scope (maybe create a new,
|
||||
* higher-than-global scope for this)
|
||||
* - To implement a new binding, specify the interface, which will contain a
|
||||
* BlockNode that contains a StmtListNode with one statement: a
|
||||
* BindingStmtNode that implements a native function that modifies directly
|
||||
* the scope.
|
||||
* - Binding creation/deletion helper functions.
|
||||
|
||||
IdentifierNode *scope = ??? what goes here again?;
|
||||
IdentifierNode *name = createIdentifierNode("FileOpen");
|
||||
IdentifierNodeList *args = ... add these ...
|
||||
BlockNode *block = ... block with appropriate BindingStmtNode ...
|
||||
FuncDefStmtNode *def = createFuncDefStmtNode();
|
||||
Binding *binding = createBinding("STDIO", def);
|
||||
|
||||
*/
|
||||
|
||||
#endif /* __BINDING_H__ */
|
|
@ -3589,7 +3589,7 @@ ReturnObject *interpretExprStmtNode(StmtNode *node,
|
|||
*
|
||||
* \param [in] scope The scope to evaluate \a node under.
|
||||
*
|
||||
* \pre \a node contains a statement created by createAltArrayDefNode().
|
||||
* \pre \a node contains a statement created by createAltArrayDefStmtNode().
|
||||
*
|
||||
* \return A pointer to a default return value.
|
||||
*
|
||||
|
@ -3639,11 +3639,31 @@ ReturnObject *interpretAltArrayDefStmtNode(StmtNode *node,
|
|||
return createReturnObject(RT_DEFAULT, NULL);
|
||||
}
|
||||
|
||||
/**
|
||||
* Interprets a binding statement.
|
||||
*
|
||||
* \param [in] node The statement to interpret.
|
||||
*
|
||||
* \param [in] scope The scope to evaluate \a node under.
|
||||
*
|
||||
* \pre \a node contains a statement created by createBindingStmtNode().
|
||||
*
|
||||
* \return A pointer to a default return value.
|
||||
*
|
||||
* \retval NULL An error occurred during interpretation.
|
||||
*/
|
||||
ReturnObject *interpretBindingStmtNode(StmtNode *node,
|
||||
ScopeObject *scope)
|
||||
{
|
||||
BindingStmtNode *stmt = (BindingStmtNode *)node->stmt;
|
||||
return (stmt->binding)(scope);
|
||||
}
|
||||
|
||||
/*
|
||||
* A jump table for statements. The index of a function in the table is given
|
||||
* by its its index in the enumerated StmtType type.
|
||||
*/
|
||||
static ReturnObject *(*StmtJumpTable[14])(StmtNode *, ScopeObject *) = {
|
||||
static ReturnObject *(*StmtJumpTable[15])(StmtNode *, ScopeObject *) = {
|
||||
interpretCastStmtNode,
|
||||
interpretPrintStmtNode,
|
||||
interpretInputStmtNode,
|
||||
|
@ -3657,7 +3677,8 @@ static ReturnObject *(*StmtJumpTable[14])(StmtNode *, ScopeObject *) = {
|
|||
interpretDeallocationStmtNode,
|
||||
interpretFuncDefStmtNode,
|
||||
interpretExprStmtNode,
|
||||
interpretAltArrayDefStmtNode };
|
||||
interpretAltArrayDefStmtNode,
|
||||
interpretBindingStmtNode };
|
||||
|
||||
/**
|
||||
* Interprets a statement.
|
||||
|
@ -3753,7 +3774,10 @@ int interpretMainNode(MainNode *main)
|
|||
{
|
||||
ReturnObject *ret = NULL;
|
||||
if (!main) return 1;
|
||||
ret = interpretBlockNode(main->block, NULL);
|
||||
ScopeObject *libs = createScopeObject(NULL);
|
||||
if (!libs) return 1;
|
||||
loadBinding(libs);
|
||||
ret = interpretBlockNode(main->block, libs);
|
||||
if (!ret) return 1;
|
||||
deleteReturnObject(ret);
|
||||
return 0;
|
||||
|
|
|
@ -101,7 +101,7 @@ typedef enum {
|
|||
/**
|
||||
* Stores return state.
|
||||
*/
|
||||
typedef struct {
|
||||
typedef struct returnobject {
|
||||
ReturnType type; /**< The type of return encountered. */
|
||||
ValueObject *value; /**< The optional return value. */
|
||||
} ReturnObject;
|
||||
|
|
33
parser.c
33
parser.c
|
@ -1105,6 +1105,39 @@ void deleteAltArrayDefStmtNode(AltArrayDefStmtNode *node)
|
|||
free(node);
|
||||
}
|
||||
|
||||
/**
|
||||
* Creates a binding statement.
|
||||
*
|
||||
* \param [in] binding A pointer to the function that defines the binding.
|
||||
*
|
||||
* \return A pointer to a binding statement with the desired properties.
|
||||
*
|
||||
* \retval NULL Memory allocation failed.
|
||||
*/
|
||||
BindingStmtNode *createBindingStmtNode(struct returnobject *(*binding)(struct scopeobject *))
|
||||
{
|
||||
BindingStmtNode *p = malloc(sizeof(BindingStmtNode));
|
||||
if (!p) {
|
||||
perror("malloc");
|
||||
return NULL;
|
||||
}
|
||||
p->binding = binding;
|
||||
return p;
|
||||
}
|
||||
|
||||
/**
|
||||
* Deletes a binding statement.
|
||||
*
|
||||
* \param [in,out] node The binding statement to delete.
|
||||
*
|
||||
* \post The memory at \a node and all of its members will be freed.
|
||||
*/
|
||||
void deleteBindingStmtNode(BindingStmtNode *node)
|
||||
{
|
||||
if (!node) return;
|
||||
free(node);
|
||||
}
|
||||
|
||||
/**
|
||||
* Creates an expression.
|
||||
*
|
||||
|
|
22
parser.h
22
parser.h
|
@ -228,6 +228,7 @@ typedef enum {
|
|||
ST_FUNCDEF, /**< Function definition statement. */
|
||||
ST_EXPR, /**< Expression statement. */
|
||||
ST_ALTARRAYDEF, /**< Function definition statement. */
|
||||
ST_BINDING, /**< Binding to external library. */
|
||||
} StmtType;
|
||||
|
||||
/**
|
||||
|
@ -364,6 +365,15 @@ typedef struct {
|
|||
IdentifierNode *parent; /**< An optional inherited array. */
|
||||
} AltArrayDefStmtNode;
|
||||
|
||||
/**
|
||||
* Stores a binding to a native function.
|
||||
*/
|
||||
struct ReturnObject;
|
||||
struct ScopeObject;
|
||||
typedef struct {
|
||||
struct ReturnObject *(*binding)(struct ScopeObject *); /**< The function that implements the binding. */
|
||||
} BindingStmtNode;
|
||||
|
||||
/**
|
||||
* Stores the main code block of a program.
|
||||
*
|
||||
|
@ -716,6 +726,18 @@ AltArrayDefStmtNode *createAltArrayDefStmtNode(IdentifierNode *, BlockNode *, Id
|
|||
void deleteAltArrayDefStmtNode(AltArrayDefStmtNode *);
|
||||
/**@}*/
|
||||
|
||||
/**
|
||||
* \name BindingStmtNode modifiers
|
||||
*
|
||||
* Functions for creating and deleting BindingStmtNodes.
|
||||
*/
|
||||
/**@{*/
|
||||
struct returnobject;
|
||||
struct scopeobject;
|
||||
BindingStmtNode *createBindingStmtNode(struct returnobject *(*binding)(struct scopeobject *));
|
||||
void deleteBindingStmtNode(BindingStmtNode *);
|
||||
/**@}*/
|
||||
|
||||
/**
|
||||
* \name ExprNode modifiers
|
||||
*
|
||||
|
|
Loading…
Reference in New Issue