worked on function call return type check and started checking return type
This commit is contained in:
101
src/grammar.y
101
src/grammar.y
@ -32,12 +32,17 @@
|
||||
|
||||
%locations
|
||||
|
||||
|
||||
%type <integ> idlist
|
||||
%type <tn> assignable
|
||||
%type <tn> expression
|
||||
%type <tn> constant
|
||||
%type <tn> id_or_types
|
||||
%type <tn> types
|
||||
%type <tn> sblock
|
||||
%type <tn> compound_statement
|
||||
%type <tn> simple_statement
|
||||
%type <tn> statement_list
|
||||
%type <integ> argument_list
|
||||
%type <integ> ablock
|
||||
%token <words> ID 101
|
||||
@ -100,6 +105,7 @@
|
||||
%precedence DOT
|
||||
%precedence RESERVE RELEASE
|
||||
|
||||
|
||||
%%
|
||||
|
||||
program:
|
||||
@ -247,7 +253,16 @@ definition:
|
||||
}
|
||||
//counter = 0;
|
||||
printdebug("Created a new scope after seeing a function definition");
|
||||
} idlist R_PAREN ASSIGN sblock //check sblock type
|
||||
} idlist R_PAREN ASSIGN sblock {
|
||||
TableNode *expected = getReturn(getTypeEntry(look_up(cur, $1)));
|
||||
if ($8 == undefined) {
|
||||
printdebug("sblock return type is undefined");
|
||||
} else if ($8 != expected) {
|
||||
printdebug("expected %s as return type but got %s", getName(expected), getName($8));
|
||||
} else {
|
||||
printdebug("CORRECT RETURN TYPE!!!");
|
||||
}
|
||||
}
|
||||
|
||||
;
|
||||
|
||||
@ -350,6 +365,7 @@ sblock:
|
||||
}
|
||||
statement_list
|
||||
{
|
||||
$<tn>$ = $3;
|
||||
printdebug("Moving up a scope after seeing sblock");
|
||||
cur = getParent(cur);
|
||||
}
|
||||
@ -374,6 +390,7 @@ sblock:
|
||||
{
|
||||
printdebug("Moving up a scope after seeing sblock with dblock");
|
||||
cur = getParent(cur);
|
||||
$<tn>$ = $5;
|
||||
}
|
||||
R_BRACE
|
||||
;
|
||||
@ -458,18 +475,59 @@ id_or_types:
|
||||
|
||||
|
||||
statement_list:
|
||||
compound_statement statement_list
|
||||
| compound_statement
|
||||
| simple_statement SEMI_COLON statement_list
|
||||
| simple_statement SEMI_COLON
|
||||
compound_statement statement_list {
|
||||
if ($1 == undefined && $2 != undefined) {
|
||||
$$ = $2;
|
||||
} else if ($1 != undefined && $2 == undefined) {
|
||||
$$ = $1;
|
||||
} else if ($1 == $2) {
|
||||
$$ = $1;
|
||||
} else {
|
||||
printdebug("differing return types within same function at line %d, column %d", @1.first_line, @1.first_column);
|
||||
$$ = undefined;
|
||||
}
|
||||
}
|
||||
| compound_statement {
|
||||
$$ = $1;
|
||||
}
|
||||
| simple_statement SEMI_COLON statement_list{
|
||||
if ($1 == undefined && $3 != undefined) {
|
||||
$$ = $3;
|
||||
} else if ($1 != undefined && $3 == undefined) {
|
||||
$$ = $1;
|
||||
} else if ($1 == $3) {
|
||||
$$ = $1;
|
||||
} else {
|
||||
printdebug("differing return types within same function at line %d, column %d", @1.first_line, @1.first_column);
|
||||
$$ = undefined;
|
||||
}
|
||||
}
|
||||
| simple_statement SEMI_COLON {
|
||||
$$ = $1;
|
||||
}
|
||||
;
|
||||
|
||||
|
||||
|
||||
compound_statement:
|
||||
WHILE L_PAREN expression R_PAREN sblock
|
||||
| IF L_PAREN expression R_PAREN THEN sblock ELSE sblock
|
||||
| sblock
|
||||
WHILE L_PAREN expression R_PAREN sblock {
|
||||
$$ = $5;
|
||||
}
|
||||
| IF L_PAREN expression R_PAREN THEN sblock ELSE sblock {
|
||||
if ($6 == undefined && $8 != undefined) {
|
||||
$$ = $8;
|
||||
} else if ($6 != undefined && $8 == undefined) {
|
||||
$$ = $6;
|
||||
} else if ($6 == $8) {
|
||||
$$ = $6;
|
||||
} else {
|
||||
printdebug("differing return types within same function at line %d, column %d", @1.first_line, @1.first_column);
|
||||
$$ = undefined;
|
||||
}
|
||||
}
|
||||
| sblock {
|
||||
$$ = $1;
|
||||
}
|
||||
;
|
||||
|
||||
|
||||
@ -517,9 +575,11 @@ simple_statement:
|
||||
printdebug(" - Invalid types %s$1: %s and $3: %s%s", COLOR_YELLOW, getType(left), getType(right), COLOR_WHITE);
|
||||
printdebug(" - %sgetType for address: %s", COLOR_YELLOW, getType(left));
|
||||
}
|
||||
|
||||
$$ = undefined;
|
||||
}
|
||||
|
||||
| RETURN expression
|
||||
| RETURN expression {$$ = $2;}
|
||||
;
|
||||
|
||||
|
||||
@ -697,6 +757,7 @@ expression:
|
||||
else if(getAdInfoType((TableNode*)$1) == TYPE_ARRAY_TYPE||
|
||||
getAdInfoType((TableNode*)$1) == TYPE_RECORD_TYPE||
|
||||
getAdInfoType((TableNode*)$1) == TYPE_FUNCTION_TYPE||
|
||||
getAdInfoType((TableNode*)$1) == TYPE_PRIMITIVE_TYPE ||
|
||||
getAdInfoType((TableNode*)$1) == TYPE_FUNCTION_DECLARATION){
|
||||
printdebug("assignable passing up to expression is array type, record type, function type, or function declaration");
|
||||
$$= ((TableNode*)$1);
|
||||
@ -751,20 +812,20 @@ assignable:
|
||||
printdebug("%stype is %d", COLOR_PURPLE, type);
|
||||
printdebug("%s", getName((TableNode*)$1));
|
||||
|
||||
if (type == TYPE_FUNCTION_DECLARATION) {
|
||||
if (type == TYPE_FUNCTION_TYPE) {
|
||||
printdebug("%sEntering function call", COLOR_LIGHTGREEN);
|
||||
if (look_up(getParent(cur), getName((TableNode*)$1))->additionalinfo->FunDecAdInfo->regularoras) {
|
||||
printdebug("as function");
|
||||
//char *funtype = getType(look_up(cur, $1));
|
||||
printdebug("%s", getType(look_up(cur, getName((TableNode*)$1))));
|
||||
// printdebug("%s", getType(look_up(cur, getName((TableNode*)$1))));
|
||||
|
||||
|
||||
|
||||
TableNode * typeNode = table_lookup(getAncestor(cur), getType((TableNode*)$1));
|
||||
TableNode * typeNode = $1;
|
||||
TableNode *param = getParameter(typeNode);
|
||||
printTableNode(param);
|
||||
|
||||
if (getAdInfoType(param) == TYPE_RECORD) {
|
||||
if (getAdInfoType(param) == TYPE_RECORD_TYPE) {
|
||||
SymbolTable *recList = getRecList(param);
|
||||
TableNode *lastCheckedRef = getFirstEntry(recList);
|
||||
TableNode *lastCheckedAct = getFirstEntry(cur);
|
||||
@ -772,12 +833,14 @@ assignable:
|
||||
lastCheckedRef = getNextEntry(lastCheckedRef);
|
||||
}
|
||||
|
||||
|
||||
if ($3 != getRecLength(param)) {
|
||||
printdebug("expected %d arguments but got %d", getRecLength(param), $3);
|
||||
}
|
||||
//this isn't very efficient, but will hopefully work
|
||||
while (lastCheckedAct != NULL && lastCheckedRef != NULL) {
|
||||
if (strcmp(getName(lastCheckedAct), getName(lastCheckedRef)) != 0) {
|
||||
if (getTypeEntry(lastCheckedRef) != getTypeEntry(lastCheckedAct)) {
|
||||
printdebug("expected %s. expression in function call got %s. at line %d and column %d",getType(lastCheckedRef), getName(lastCheckedAct), @3.first_line, @3.first_column);
|
||||
printdebug("%d", strcmp(getName(lastCheckedAct), getName(lastCheckedRef)));
|
||||
|
||||
}
|
||||
lastCheckedAct = getNextEntry(lastCheckedAct);
|
||||
TableNode *tn = getFirstEntry(recList);
|
||||
@ -804,8 +867,12 @@ assignable:
|
||||
if (strcmp(expected, actual) != 0) {
|
||||
printdebug("expected %s expression in function call but got %s at line %d and column %d",expected, actual, @3.first_line, @3.first_column);
|
||||
}
|
||||
if ($3 != 1) {
|
||||
printdebug("expected 1 argument but got %d", $3);
|
||||
}
|
||||
}
|
||||
$$ = getReturn((table_lookup(getAncestor(cur), getType((TableNode*)$1))));
|
||||
printTableNode(getReturn($1));
|
||||
$$ = getReturn($1);
|
||||
printdebug("[ASSIGNABLE - RULE 2] assignable = type: %s | name_func = %s", getName((TableNode*)$$), getName((TableNode*)$1));
|
||||
|
||||
} else if (type == TYPE_ARRAY_TYPE) {
|
||||
|
16
tests/sprint2/test/sp2_sp2_arrayargs.alpha
Normal file
16
tests/sprint2/test/sp2_sp2_arrayargs.alpha
Normal file
@ -0,0 +1,16 @@
|
||||
type string: 1 -> character
|
||||
type a_of_s: 1 -> string
|
||||
|
||||
(* maybe some other type definitions *)
|
||||
|
||||
entry(arg) := {
|
||||
[ string: one_name; string: another_name; a_of_s: many_names ]
|
||||
another_name := reserve another_name(4); (* reserve space for an an array of character, with 4 members *)
|
||||
many_names := reserve a_of_s(many_names);
|
||||
many_names(0) := one_name;
|
||||
many_names(1) := another_name;
|
||||
many_names(2) := reserve a_of_s(2)(6); (* reserve space for an item of the same type as a_of_s(2), an array of character, with 6 members *)
|
||||
many_names(2)(0) := "P";
|
||||
|
||||
return 0;
|
||||
}
|
16
tests/sprint2/test/sp2_sp2_arrayargs.alpha~
Normal file
16
tests/sprint2/test/sp2_sp2_arrayargs.alpha~
Normal file
@ -0,0 +1,16 @@
|
||||
type string: 1 -> character
|
||||
type a_of_s: 1 -> string
|
||||
|
||||
(* maybe some other type definitions *)
|
||||
|
||||
entry(arg) := {
|
||||
[ string: one_name; string: another_name; a_of_s: many_names ]
|
||||
another_name := reserve another_name(4); (* reserve space for an an array of character, with 4 members *)
|
||||
many_names := reserve a_of_s(3);
|
||||
many_names(0) := one_name;
|
||||
many_names(1) := another_name;
|
||||
many_names(2) := reserve a_of_s(2)(6); (* reserve space for an item of the same type as a_of_s(2), an array of character, with 6 members *)
|
||||
many_names(2)(0) := "P";
|
||||
|
||||
return 0;
|
||||
}
|
17
tests/sprint3/test/sp3_multiple_args.alpha
Normal file
17
tests/sprint3/test/sp3_multiple_args.alpha
Normal file
@ -0,0 +1,17 @@
|
||||
type rec: [character: x; integer: y]
|
||||
|
||||
type T2: rec -> integer
|
||||
|
||||
type main: string -> integer
|
||||
function entry: main
|
||||
function bar: T2
|
||||
|
||||
bar2 (r,s) := {
|
||||
return r;
|
||||
}
|
||||
|
||||
entry (arg) := {
|
||||
[ integer: result ; rec: w]
|
||||
result := bar('c', 7);
|
||||
return 0;
|
||||
}
|
17
tests/sprint3/test/sp3_multiple_args.alpha~
Normal file
17
tests/sprint3/test/sp3_multiple_args.alpha~
Normal file
@ -0,0 +1,17 @@
|
||||
type rec: [character: x; integer: y]
|
||||
|
||||
type T2: rec -> integer
|
||||
|
||||
type main: string -> integer
|
||||
function entry: main
|
||||
function bar: T2
|
||||
|
||||
bar2 (r,s) := {
|
||||
return s;
|
||||
}
|
||||
|
||||
entry (arg) := {
|
||||
[ integer: result ; rec: w]
|
||||
result := bar('c', 7);
|
||||
return 0;
|
||||
}
|
Reference in New Issue
Block a user