Commit e54b8ec7 authored by Sarah Spall's avatar Sarah Spall Committed by Vikram Narayanan
Browse files

took container allocating code put in own function and modified to allocate containers for fields

parent 8af0a335
......@@ -81,24 +81,45 @@ CCSTStatement* helper(Variable *p)
}
}
}
CCSTCompoundStatement* function_pointer_caller_body(Rpc *f)
{
std::vector<CCSTDeclaration*> declarations;
std::vector<CCSTStatement*> statements;
std::vector<Parameter*> params = f->parameters();
// allocate container structs if necessary
for(std::vector<Parameter*>::iterator it = params.begin(); it != params.end(); it ++) {
Parameter *p = *it;
if(p->type()->num() == 4 && p->alloc_caller()) {
ProjectionType *pt = dynamic_cast<ProjectionType*>(p->type());
Assert(pt != 0x0, "Error: dynamic cast to Projection type failed!\n");
statements.push_back(alloc_init_containers_driver(pt, f->current_scope(), "caller"));
}
}
// allocate trampolines
// marshal parameters
}
CCSTCompoundStatement* caller_body(Rpc *r)
{
std::vector<CCSTDeclaration*> declarations;
std::vector<CCSTStatement*> statements;
// allocate necessary container shit
// allocate necessary container things
/* code that loops through parameters and allocates/initializes whatever necessary before marshalling*/
// loop through params, declare a tmp and pull out marshal value
std::vector<Parameter*> params = r->parameters();
std::vector<CCSTInitDeclarator*> err_decs;
err_decs.push_back(new CCSTDeclarator(0x0, new CCSTDirectDecId("err")));
CCSTDeclaration *err_variable = new CCSTDeclaration(int_type(), err_decs);
declarations.push_back(err_variable);
// for each parameter that is ia projection -- & is alloc
for(std::vector<Parameter*>::iterator it = params.begin(); it != params.end(); it ++)
{
......@@ -106,87 +127,42 @@ CCSTCompoundStatement* caller_body(Rpc *r)
if(p->type()->num() == 4 && p->alloc_caller()) {
ProjectionType *pt = dynamic_cast<ProjectionType*>(p->type());
Assert(pt != 0x0, "Error: dynamic cast to Projection type failed!\n");
// lookup container struct
int err;
const char* container_name_ = container_name(pt->name());
Type *container_tmp = r->current_scope()->lookup(container_name_, &err);
printf("looked up container %s for function %s. pointer for regular projection %p\n", container_name_, r->name(), r->current_scope()->lookup(pt->name(), &err));
Assert(container_tmp != 0x0, "Error: could not find container in environment\n");
ProjectionType *container = dynamic_cast<ProjectionType*>(container_tmp);
Assert(container != 0x0, "Error: dynamic cast to Projection type failed!\n");
// declare instance of container
std::vector<CCSTInitDeclarator*> decs;
decs.push_back(new CCSTDeclarator(new CCSTPointer(), new CCSTDirectDecId(container_name_)));
CCSTDeclaration *container_declaration = new CCSTDeclaration(type2(container), decs);
// finish declaring instance of container
declarations.push_back(container_declaration);
// file_container = kzalloc(sizeof(*file_container), GFP_KERNEL);
std::vector<CCSTAssignExpr*> kzalloc_args;
kzalloc_args.push_back(new CCSTUnaryExprSizeOf(new CCSTUnaryExprCastExpr(new CCSTUnaryOp(unary_mult_t), new CCSTPrimaryExprId(container_name_))));
kzalloc_args.push_back(new CCSTEnumConst("GFP_KERNEL"));
statements.push_back(new CCSTAssignExpr(new CCSTPrimaryExprId(container_name_), equals(), function_call("kzalloc", kzalloc_args)));
// if null
// LIBLCD_ERR("kzalloc");
// lcd_exit(-1); /* abort */
statements.push_back(if_cond_fail(new CCSTUnaryExprCastExpr(Not(), new CCSTPrimaryExprId(container_name_))
, "kzalloc"));
// insert into dstore
// do error checking
// err = lcd_dstore_insert...
std::vector<CCSTAssignExpr*> dstore_insert_args;
dstore_insert_args.push_back(new CCSTPrimaryExprId("dstore")); // lookup this name in the future.
dstore_insert_args.push_back(new CCSTPrimaryExprId(container_name_)); // what we are inserting
dstore_insert_args.push_back(new CCSTEnumConst("STRUCT_FILE_TAG")); // this part is not clear
ProjectionField *my_ref_field = container->get_field("my_ref");
Assert(my_ref_field != 0x0, "Error: could not find field in projection\n");
dstore_insert_args.push_back(access(my_ref_field));
// insert into dstore
statements.push_back(new CCSTAssignExpr(new CCSTPrimaryExprId("err"), equals(), function_call("lcd_dstore_insert", dstore_insert_args)));
// do error checking
statements.push_back(if_cond_fail(new CCSTPrimaryExprId("err"), "dstore"));
statements.push_back(alloc_init_containers_driver(pt, r->current_scope(), "caller"));
}
}
// marshal parameters.
/* end of this code, could go in own function maybe?*/
// if function pointer pass reference to container
// which will be a parameter.... so don't need to check... thank god
/*
std::vector<CCSTStatement*> statements_tmp = marshal_in_parameters(r->parameters());
statements.insert(statements.end(), statements_tmp.begin(), statements_tmp.end());
// implicit returns
// replace with parameter loop
//std::vector<CCSTStatement*> uirs = unmarshal_implicit_return(r->implicit_ret_marshal_info());
//statements.insert(statements.end(), uirs.begin(), uirs.end());
ReturnVariable *rv = r->return_variable();
if(rv->type()->num() != 5) { // not void
// Marshal_type *ret_info = r->explicit_ret_marshal_info();
}
else {
statements.push_back(new CCSTReturn());
std::vector<Variable*> marshal_params = r->marshal_parameters;
for(std::vector<Variable*>::iterator it = marshal_params.begin(); it != marshal_params.end(); it ++) {
Variable *mp = *it;
if (mp->type()->num() == 4) { // is a projection and we need to pass a reference.
ProjectionType *pt = dynamic_cast<ProjectionType*>(mp->type());
Assert(pt != 0x0, "Error: dynamic cast to projection failed!\n");
std::vector<ProjectionField*> pt_fields = pt->fields();
for(std::vector<ProjectionField*>::iterator it2 = pt_fields.begin(); it2 != pt_fields.end(); it2 ++) {
ProjectionField *pf = *it2;
if (pf->in()) { // marshal this field
std::vector<CCSTAssignExpr*> register_args;
register_args.push_back(access(pf)); // pass field marked in.
statements.push_back(function_call(access_register_mapping(pf->marshal_info()->get_register())
, register_args));
}
}
} else {
std::vector<CCSTAssignExpr*> register_args;
register_args.push_back(access(mp));
statements.push_back(function_call(access_register_mapping(mp->marshal_info()->get_register())
, register_args));
}
}
*/
return new CCSTCompoundStatement(declarations, statements);
}
......
......@@ -63,6 +63,11 @@ CCSTUnaryOp* Not()
return new CCSTUnaryOp(unary_bang_t);
}
CCSTUnaryOp* reference()
{
return new CCSTUnaryOp(unary_bit_and_t);
}
/*
* confirm this works
* returns a new string with _p on end.
......@@ -638,3 +643,119 @@ CCSTIfStatement* if_cond_fail(CCSTExpression *cond, const char *err_msg)
return new CCSTIfStatement(cond, if_body);
}
CCSTCompoundStatement* alloc_init_containers_driver(ProjectionType *pt, LexicalScope *ls, const char *side)
{
std::vector<CCSTDeclaration*> declarations;
std::vector<CCSTStatement*> statements;
std::vector<CCSTInitDeclarator*> err_decs;
err_decs.push_back(new CCSTDeclarator(0x0, new CCSTDirectDecId("err")));
CCSTDeclaration *err_variable = new CCSTDeclaration(int_type(), err_decs);
declarations.push_back(err_variable);
statements.push_back(alloc_init_containers(pt, ls, side));
return new CCSTCompoundStatement(declarations, statements);
}
// need to pass scope!
CCSTCompoundStatement* alloc_init_containers(ProjectionType *pt, LexicalScope *ls, const char *side)
{
std::vector<CCSTDeclaration*> declarations;
std::vector<CCSTStatement*> statements;
// declare container
int err;
const char* container_name_ = container_name(pt->name());
Type *container_tmp = ls->lookup(container_name_, &err); // fix
Assert(container_tmp != 0x0, "Error: could not find container in environment\n");
ProjectionType *container = dynamic_cast<ProjectionType*>(container_tmp);
Assert(container != 0x0, "Error: dynamic cast to Projection type failed!\n");
std::vector<CCSTInitDeclarator*> decs;
decs.push_back(new CCSTDeclarator(new CCSTPointer(), new CCSTDirectDecId(container_name_)));
CCSTDeclaration *container_declaration = new CCSTDeclaration(type2(container), decs);
declarations.push_back(container_declaration);
// alloc
std::vector<CCSTAssignExpr*> kzalloc_args;
kzalloc_args.push_back(new CCSTUnaryExprSizeOf(new CCSTUnaryExprCastExpr(new CCSTUnaryOp(unary_mult_t), new CCSTPrimaryExprId(container_name_))));
kzalloc_args.push_back(new CCSTEnumConst("GFP_KERNEL"));
statements.push_back(new CCSTAssignExpr(new CCSTPrimaryExprId(container_name_), equals(), function_call("kzalloc", kzalloc_args)));
// error check
// if null
// LIBLCD_ERR("kzalloc");
// lcd_exit(-1); /* abort */
statements.push_back(if_cond_fail(new CCSTUnaryExprCastExpr(Not(), new CCSTPrimaryExprId(container_name_))
, "kzalloc"));
// insert into dstore
// do error checking
// err = lcd_dstore_insert...
std::vector<CCSTAssignExpr*> dstore_insert_args;
dstore_insert_args.push_back(new CCSTPrimaryExprId("dstore")); // lookup this name in the future.
dstore_insert_args.push_back(new CCSTPrimaryExprId(container_name_)); // what we are inserting
dstore_insert_args.push_back(new CCSTEnumConst("STRUCT_FILE_TAG")); // this part is not clear
ProjectionField *my_ref_field = container->get_field("my_ref");
Assert(my_ref_field != 0x0, "Error: could not find field in projection\n");
dstore_insert_args.push_back(access(my_ref_field));
// insert into dstore
statements.push_back(new CCSTAssignExpr(new CCSTPrimaryExprId("err"), equals(), function_call("lcd_dstore_insert", dstore_insert_args)));
// do error checking
statements.push_back(if_cond_fail(new CCSTPrimaryExprId("err"), "dstore"));
Parameter *tmp = new Parameter(container, container_name_, 1);
std::vector<ProjectionField*> fields = pt->fields();
for(std::vector<ProjectionField*>::iterator it = fields.begin(); it != fields.end(); it ++) {
ProjectionField *pf = *it;
if(pf->type()->num() == 4 && alloc_caller(pf, side)) {
ProjectionType *pt2 = dynamic_cast<ProjectionType*>(pf->type());
Assert(pt2 != 0x0, "Error: dynamic cast to Projection type failed!\n");
statements.push_back(alloc_init_containers(pt2, ls, side));
// need to link/init
// need to access this field, but from the container....
Assert(pf->accessor() != 0x0, "Error: field does not have a surrounding variable");
Variable *sv = pf->accessor()->accessor();
pf->accessor()->set_accessor(tmp);
// 1. get container for this field
const char* container_name2 = container_name(pt2->name());
Type *container_tmp2 = ls->lookup(container_name2, &err); // fix
Assert(container_tmp2 != 0x0, "Error: could not find container in environment\n");
ProjectionType *container2 = dynamic_cast<ProjectionType*>(container_tmp2);
Assert(container2 != 0x0, "Error: dynamic cast to Projection type failed!\n");
// 2. in container look up field
ProjectionField *tmp_pf = container2->get_field(pt2->name()); // make sure name returns the name i think it does
// 3. create a tmp variable
Parameter *tmp2 = new Parameter(container2, container_name2, 1);
// 4. set accessor in field.
tmp_pf->set_accessor(tmp2);
statements.push_back(new CCSTAssignExpr(access(pf), equals(), new CCSTUnaryExprCastExpr(reference() ,access(tmp_pf)))); // doing "&" may be wrong... put in function that checks
}
}
return new CCSTCompoundStatement(declarations, statements);
}
bool alloc_caller(Variable *v, const char *side)
{
if(strcmp(side, "caller") == 0) {
return v->alloc_caller();
}
return v->alloc_callee();
}
#ifndef ASSERT_H
#define ASSERT_H
#include <errno.h>
#include <cstdlib>
#include <string.h>
#include <stdio.h>
#include <stdlib.h>
#include <stdarg.h>
#include <string>
/* taken from Scott Bauer
*/
static inline void AssertionFailure(std::string exp, std::string file, int line, const char* format, ...)
//static void AssertionFailure(char *exp, char *file, int line, const char* format, ... )
{
printf("Assertion '%s' failed at line %d of file %s\n", exp.c_str(), line, file.c_str());
printf("Error is %s\n", strerror(errno));
va_list args;
va_start(args, format);
vfprintf(stdout, format, args);
va_end(args);
exit(EXIT_FAILURE);
}
/* taken from Scott Bauer
* Will be moved to more appropriate place
*/
#define Assert(exp, format, ...) if (exp) ; else AssertionFailure( #exp, __FILE__, __LINE__, format, ##__VA_ARGS__ )
#endif
#ifndef CODE_GEN_H
#define CODE_GEN_H
#include "lcd_ast.h"
#include "ccst.h"
#define CONTAINER_OF "container_of"
// server.cpp
CCSTFile* generate_server_source(Module *m); // todo complete
CCSTFile* generate_server_header(Module *m); // todo complete?
CCSTCompoundStatement* callee_body(Rpc *r); // todo complete 2 functions in the file.....
CCSTDeclaration* callee_declaration(Rpc *r); // todo complete
CCSTCompoundStatement* dispatch_loop_body(std::vector<Rpc*> rpcs); //todo complete... revamp
CCSTDeclaration* dispatch_function_declaration(); // todo complete
// client.cpp
CCSTFile* generate_client_header(Module *m); // todo empty, maybe unnecessary?
CCSTFile* generate_client_source(Module *m); // todo complete
CCSTCompoundStatement* caller_body(Rpc *r); // todo complete
std::vector<CCSTStatement*> marshal_in_parameters(std::vector<Parameter*> params); // complete
std::vector<CCSTStatement*> marshal_parameters(std::vector<Parameter*> params); // todo i think this belongs in a different file
std::vector<CCSTStatement*> unmarshal_implicit_return(std::vector<Parameter*> implicit_returns); // todo does this belong in a different file?
CCSTStatement* unmarshal_explicit_return(Marshal_type *return_info); // todo does this belong in a different file?
const char* struct_name(ProjectionType *pt); // complete
// client seems to be missing important functions.
// helper.cpp
CCSTCompoundStatement* alloc_init_containers_driver(ProjectionType *pt, LexicalScope *ls, const char* side); // complete
CCSTCompoundStatement* alloc_init_containers(ProjectionType *pf, LexicalScope *ls, const char* side); // complete
bool alloc_caller(Variable *v, const char* side); // complete
CCSTStructUnionSpecifier* struct_declaration(ProjectionType *pt); // complete
CCSTDeclaration* declare_and_initialize_container_struct(Variable *v); // complete
std::vector<CCSTAssignExpr*> container_of_args(CCSTPostFixExpr *struct_pointer, const char *type_name, const char *field_name); // complete
CCSTDeclaration* typedef_declaration(Typedef *t); // todo. totally not done
CCSTAssignOp* equals(); // complete
CCSTDeclaration* declare_static_variable(Variable *v); // complete
CCSTExDeclaration* construct_enum(Module *m); // todo?
CCSTEnumeratorList* construct_enumlist(std::vector<Rpc*> rpcs); // ???????
CCSTUnaryOp* indirection(); // complete
CCSTUnaryExprCastExpr* dereference(CCSTCastExpr *to_deref); //complete
CCSTPostFixExpr* access(Variable *v); // complete to test.
CCSTPrimaryExprId* function_name(const char *func_name); // complete
CCSTPostFixExprAssnExpr* function_call(const char* func_name, std::vector<CCSTAssignExpr*> args); // complete
CCSTUnaryOp* Not();
CCSTIfStatement* if_cond_fail(CCSTExpression *cond, const char *err_msg); // complete
std::vector<CCSTDecSpecifier*> int_type(); // complete
// name creators
const char* parameter_name(const char *name); // complete
const char* container_name(const char *name); // complete
const char* enum_name(const char *name); // todo totally incomplete
const char* string_to_upper(const char *str); //???????? const or not? this function seems retarded.
CCSTPointer* pointer(int p_count); // complete
std::vector<CCSTDecSpecifier*> struct_type(const char *type_name); // complete
std::vector<CCSTDecSpecifier*> type2(Type *t); // complete?
std::vector<CCSTSpecifierQual*> type(Type *t); // complete?
CCSTTypeName* type_cast(Type *t); //??????
std::vector<CCSTSpecifierQual*> integer_type_cast(IntegerType *it); /// ????????
// is this in the correct file?
CCSTCompoundStatement* interface_init_function_body(std::vector<GlobalVariable*> globals); // complete
CCSTFuncDef* function_definition(CCSTDeclaration *function_declaration, CCSTCompoundStatement *body); // complete
CCSTDeclaration* function_declaration(Rpc *r); // complete
CCSTParamTypeList* parameter_list(std::vector<Parameter*> params); // complete
// needed functions.
// creates a function declaration from a return type, a name and parameters
// add marshal and unmarshal cpp files to this
// unmarshal.cpp
CCSTStatement* unmarshal_variable(Variable *v); // almost complete
// marshal.cpp
CCSTStatement* marshal_variable(Variable *v); // empty
#endif
Markdown is supported
0% or .
You are about to add 0 people to the discussion. Proceed with caution.
Finish editing this message first!
Please register or to comment