Commit a9b711f3 authored by Sergio Costas's avatar Sergio Costas

Added RETURN support

Now the parser copies the parameter list when typedefining a function pointer
parent 0130ba95
......@@ -63,6 +63,25 @@ class crusty(object):
setattr(retval,element,getattr(self,element))
return retval
def __str__(self):
first = True
salida = ""
for element in dir(self):
if element.startswith("_"):
continue
if not first:
salida += ", "
first = False
dato = getattr(self,element)
salida += "{:s}: ".format(element)
if dato is None:
salida += "None"
continue
if isinstance(dato,list):
salida += "pointer"
continue
salida += str(dato)
return salida
def __init__(self,headerpath,libpath):
......@@ -491,6 +510,14 @@ class crusty(object):
(assignment.type == "-") or
(assignment.type == "&") or
(assignment.type == "MUL_ASSIGN") or
(assignment.type == "DIV_ASSIGN") or
(assignment.type == "ADD_ASSIGN") or
(assignment.type == "SUB_ASSIGN") or
(assignment.type == "MOD_ASSIGN") or
(assignment.type == "AND_ASSIGN") or
(assignment.type == "XOR_ASSIGN") or
(assignment.type == "OR_ASSIGN") or
(assignment.type == "RIGHT_OP") or
(assignment.type == "LEFT_OP")):
child1 = assignment.child1
child2 = assignment.child2
......@@ -546,9 +573,10 @@ class crusty(object):
def _get_variable_properties(self,node, pointers, is_parameter, is_retval = False):
retval = {"crust": False, "borrowed": False, "recycle": False, "enum": False, "status": self.STATUS_UNINITIALIZED, "pointer": pointers, "struct": False, "array": False, "function": False}
retval = {"crust": False, "borrowed": False, "recycle": False, "enum": False, "status": self.STATUS_UNINITIALIZED, "pointer": pointers, "struct": False, "array": False, "function": False, "function_params": None}
if not isinstance(node,self.AST_node):
return retval
retval["function_params"] = node.function_params
if node.t_crusty:
if node.pointer == 0:
if is_parameter:
......@@ -766,12 +794,24 @@ class crusty(object):
retvals += self._check_return_block(block_false,self._copy_container(option[1]))
return retvals
if node.type == "MUL_ASSIGN":
if ((node.type == "MUL_ASSIGN") or
(node.type == "DIV_ASSIGN") or
(node.type == "ADD_ASSIGN") or
(node.type == "SUB_ASSIGN") or
(node.type == "MOD_ASSIGN") or
(node.type == "AND_ASSIGN") or
(node.type == "XOR_ASSIGN") or
(node.type == "OR_ASSIGN")):
options = self._eval_assignment(node,var_container,False)
retvals = []
for option in options:
retvals += self._check_return_block(tree[1:],option[1])
return retvals
if node.type == "RETURN":
if node.child1 is not None:
self._eval_assignment(node.child1[0],var_container,False)
return [(None,None)]
print("Tipo: {:s}; Nombre: {:s}; Linea: {:s}".format(str(node.type),str(node.name),str(node.line)))
return self._check_return_block(tree[1:],var_container)
......@@ -121,6 +121,9 @@ void mix_ast_leaves(struct AST *base, struct AST *new_leaf) {
base->t_null |= new_leaf->t_null;
base->t_ellipsis |= new_leaf->t_ellipsis;
base->t_label |= new_leaf->t_label;
if (base->function_params == NULL) {
base->function_params = copy_leaf(new_leaf->function_params);
}
//base->t_ |= new_leaf->t_;
}
......@@ -197,10 +200,35 @@ struct AST *find_type(char *type) {
return NULL;
}
#define COPY_ELEMENT(ELEMENT) if (leaf->ELEMENT != NULL) {tmp->ELEMENT = copy_leaf(leaf->ELEMENT);}
#define RESET_ELEMENT(ELEMENT) tmp->ELEMENT = NULL;
#define COPY_STRING(ELEMENT) if (leaf->ELEMENT != NULL) {tmp->ELEMENT = strdup(leaf->ELEMENT);}
struct AST *copy_leaf(struct AST *leaf) {
if (leaf == NULL) {
return NULL;
}
struct AST *tmp = (struct AST *)malloc(sizeof(struct AST));
memcpy(tmp,leaf,sizeof(struct AST));
COPY_STRING(data)
COPY_STRING(name)
COPY_STRING(filename)
RESET_ELEMENT(next)
RESET_ELEMENT(right)
RESET_ELEMENT(condition)
RESET_ELEMENT(child1)
RESET_ELEMENT(child2)
RESET_ELEMENT(child3)
RESET_ELEMENT(child4)
RESET_ELEMENT(bitfield)
RESET_ELEMENT(struct_data)
RESET_ELEMENT(enum_data)
RESET_ELEMENT(arrays)
RESET_ELEMENT(assignment)
RESET_ELEMENT(for_ch1)
RESET_ELEMENT(for_ch2)
RESET_ELEMENT(for_ch3)
COPY_ELEMENT(function_params)
return (tmp);
}
......
......@@ -97,6 +97,7 @@ void copy_ast_data(struct AST *base, struct AST *new_leaf);
struct AST *transform_leaf(struct AST *leaf, int newtype);
void free_tree(struct AST *tree);
void free_all();
struct AST *copy_leaf(struct AST *leaf);
void check_typedef(struct AST *type);
......
......@@ -255,5 +255,8 @@ class Test(unittest.TestCase):
def testIfWithNot2(self):
self._generic_test("unitest/test61.c",[ (crusty.crusty.MSG_ERROR,"Assignment to '{:s}' at line {:d}, which was already assigned at line {:d}","param",9,5) ])
def testReturn(self):
self._all_fine_test("unitest/test62.c")
if __name__ == '__main__':
unittest.main()
......@@ -5,7 +5,7 @@ typedef __crust_t__ unsigned char *crust_t;
void test_function(crust_t __crust_borrow__ param) {
}
void main(crust_t __crust_borrow__ param) {
void (*test2)(crust_t param);
void main(crust_t __crust_borrow__ param2) {
void (*test2)(crust_t param3);
test2 = test_function;
}
typedef __crust_t__ unsigned char *crust_t;
#define NULL ((void *)0)
void main(crust_t param) {
crust_t var2 = (crust_t) 5;
if (!(param != NULL)) {
param = var2;
} else {
main(param);
}
}
typedef __crust_t__ unsigned char *crust_t;
#define NULL ((void *)0)
void main(crust_t param) {
crust_t var2 = (crust_t) 5;
if (!(param == NULL)) {
param = var2;
}
}
typedef __crust_t__ unsigned char *crust_t;
#define NULL ((void *)0)
void main(crust_t param) {
crust_t var2;
var2 = param;
return;
main2(param); // will not fail because there is a RETURN before
}
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