Merge pull request #1 from LucasVbr/dev

Dev
This commit is contained in:
Laurian-Dufrechou
2023-04-07 18:05:58 +02:00
committed by GitHub
8 changed files with 741 additions and 40 deletions
+1
View File
@@ -8,6 +8,7 @@ src/parser.ml
*.mli
src/**/*.cmi
comp
*/**/*.output
# Tests out
tests/out/
+9 -4
View File
@@ -8,13 +8,18 @@
> Compilateur du langage Postscript en Ocaml
## Author
## Authors
👤 **Laurian DUFRECHOU**
* Github: [@Laurian-Dufrechou](https://github.com/Laurian-Dufrechou)
👤 **Gaël BRUGUES**
* Github: [@Gagl08](https://github.com/Gagl08)
👤 **Lucas VABRE**
* Github: [@LucasVbr](https://github.com/LucasVbr)
* LinkedIn: [@lucasvbr](https://linkedin.com/in/lucasvbr)
## Show your support
Give a ⭐️ if this project helped you!
+13 -9
View File
@@ -1,5 +1,5 @@
# Import lib + compile + clean folder
all: lib comp clean
# Compile
all: comp
# Compilation of Ocaml files
# Attention: order of object files important
@@ -30,12 +30,12 @@ comp.cmo: comp.ml gen.cmo typing.cmo parser.cmo interf.cmo
# ocaml lexer and parser
# Comment in for your own lexer
# lexer.ml: lexer.mll lang.cmo
# ocamllex $<
lexer.ml: lexer.mll lang.cmo
ocamllex $<
# Comment in for your own parser
# parser.ml parser.mli: parser.mly lang.cmo
# ocamlyacc $<
parser.ml parser.mli: parser.mly lang.cmo
ocamlyacc $<
lexer.cmo: lexer.ml parser.cmo
ocamlc -c $<
@@ -51,10 +51,14 @@ parser.cmo: parser.ml parser.cmi lang.cmo
.PHONY: clean
### Import files from /lib
lib:
cp ../lib/* ./
### Import files from /lib (temporarly)
# lib:
# cp ../lib/* ./
## Remove compiled modules and lib
clean:
rm -f lexer.ml parser.ml *.mli *.cmi *.cmo
## Run tests
tests:
./comp ./../tests/rectangles.c ./../tests/out/rectangles.ps
+94
View File
@@ -0,0 +1,94 @@
{
open Lexing
open Parser
open Lang
exception Lexerror
let pos lexbuf = (lexeme_start lexbuf, lexeme_end lexbuf)
let advance_line_pos pos =
{ pos with pos_lnum = pos.pos_lnum + 1; pos_bol = pos.pos_cnum; }
let advance_line lexbuf =
lexbuf.lex_curr_p <- advance_line_pos lexbuf.lex_curr_p
}
let includeline = '#' [^ '\n']* '\n'
let num = ['1'-'9']['0'-'9']*
let num_virgule = ['1'-'9']['0'-'9']*'.'(['1'-'9']['0'-'9']*)?
let alph = ['a'-'z''A'-'Z']
let literal = '/'alph(alph|'-')*
let str = '\"'alph(alph|'-'|'_'|num)*'\"'
let blancs = [' ''\t']+
let comment = '/' '*' (blancs|alph|num|num_virgule|'>'|'<')* '*' '/'
rule token = parse
blancs
{ token lexbuf } (* white space: recursive call of lexer *)
|'\n'
{advance_line lexbuf; token lexbuf } (* white space: recursive call of lexer *)
| includeline
{ advance_line lexbuf; token lexbuf } (* C include directives --> ignore *)
| comment
{ token lexbuf } (* comment --> ignore *)
| "int" {TP(IntT)}
| "bool" {TP(BoolT)}
| "string" {TP(StringT)}
| "float" {TP(FloatT)}
| "void" {TP(VoidT)}
| "lit" {TP(LitT)} (* faut demander *)
| '(' { LPAREN }
| ')' { RPAREN }
| '{' { LBRACE }
| '}' { RBRACE }
| "==" { BCEQ }
| '=' { EQ }
| '+' { PLUS }
| '-' { MINUS }
| '*' { TIMES }
| '/' { DIV }
| '%' { MOD }
| '/' { DIV }
| "<=" { BCLE }
| ">=" { BCGE }
| ">" { BCGT }
| "<" { BCLT }
| "!=" { BCNE }
| "and" {BLAND}
| "or" {BLOR}
| "," {COMMA}
| ";" {SEMICOLON}
| ":" {COLON}
| "?" {QMARK}
| "return" {RETURN}
| "if" {IF}
| "else" {ELSE}
| "while" {WHILE}
| "for" {FOR}
| "True" {BCONSTANT(true)}
| "False" {BCONSTANT(false)}
| eof {EOF}
| num_virgule as s {FLOATCONSTANT(float_of_string s)}
| num as s {INTCONSTANT(int_of_string s)}
| literal as l { LITCONSTANT l }
| str as s { STRINGCONSTANT s }
| alph alph* as i {IDENTIFIER i}
| _ {Printf.printf "ERROR: unrecogized symbol '%s'\n" (Lexing.lexeme lexbuf);
raise Lexerror }
and
ruleTail acc = parse
| eof { acc }
| _* as str { ruleTail (acc ^ str) lexbuf }
+200
View File
@@ -0,0 +1,200 @@
%{
open Lang
%}
%token <string> IDENTIFIER
%token <string> LITCONSTANT
%token <string> STRINGCONSTANT
%token <Lang.tp> TP
%token <bool> BCONSTANT
%token <int> INTCONSTANT
%token <float> FLOATCONSTANT
%token PLUS MINUS TIMES DIV MOD FPLUS FMINUS FTIMES FDIV
%token LPAREN RPAREN LBRACE RBRACE
%token EQ COMMA SEMICOLON COLON QMARK
%token IF ELSE WHILE FOR RETURN BCEQ BCGE BCGT BCLE BCLT BCNE BLAND BLOR
%token EOF
%left QMARK COLON
%left BLOR
%left BLAND
%left BCEQ BCNE
%left BCGE BCGT BCLE BCLT
%left PLUS MINUS FPLUS FMINUS
%left TIMES DIV FDIV FTIMES MOD
%right IF ELSE
%left RPAREN
%right LPAREN
%left SEMICOLON
%start start
%type <Lang.prog> start
%%
start: list_fundefn { Prog ([], $1) }
;
list_fundefn:
| {[]}
| fundefn list_fundefn {$1 :: $2}
;
fundefn: /* Compound-statement dans la doc --> 6.8.2 */
/* d'apres la doc, on peut lui mettre --> LBRACE RBRACE {Skip} */
|fundecl LBRACE block_item_list_opt RBRACE { Fundefn($1, $3) }
// |fundecl LBRACE statement RBRACE { Fundefn($1, $3) }
;
fundecl: TP IDENTIFIER LPAREN vardecl_comma_list_opt RPAREN
{ Fundecl($1, $2, $4) }
;
vardecl_comma_list_opt:
|TP IDENTIFIER COMMA vardecl_comma_list_opt {[Vardecl($1, $2)] @ $4} /* dans celle c'est récursif*/
|TP IDENTIFIER {[Vardecl($1, $2)]}
|/* empty */{ [] }
;
constant:
|LITCONSTANT{LitV($1) }
|STRINGCONSTANT {StringV($1) }
|BCONSTANT {BoolV($1) }
|INTCONSTANT {IntV($1) }
|FLOATCONSTANT {FloatV($1) }
;
expression: /* A.2.1 ---> 6.5.1 */
|IDENTIFIER {VarE($1)}
|constant {Const($1)}
|LPAREN expression RPAREN {$2}
|multiplicative_expression {$1}
|additive_expression {$1}
|relational_expression {$1}
|equality_expression {$1}
|logical_and_expression {$1}
|logical_or_expression {$1}
|conditional_expression {$1}
|IDENTIFIER LPAREN expr_list RPAREN {CallE($1,$3)}
;
/*les calculs*/
multiplicative_expression: /* 6.5.5 */
|expression FTIMES expression {BinOp(BArith(BAfmul), $1, $3)}
|expression TIMES expression {BinOp(BArith(BAmul), $1, $3)}
|expression FDIV expression {BinOp(BArith(BAfdiv), $1, $3)}
|expression DIV expression {BinOp(BArith(BAdiv), $1, $3)}
|expression MOD expression {BinOp(BArith(BAmod), $1, $3)}
;
additive_expression: /* 6.5.6 */
|expression FPLUS expression {BinOp(BArith(BAfadd), $1, $3)}
|expression FMINUS expression {BinOp(BArith(BAfsub), $1, $3)}
|expression PLUS expression {BinOp(BArith(BAadd), $1, $3)}
|expression MINUS expression {BinOp(BArith(BAsub), $1, $3)}
;
/*les comparaisons*/
relational_expression: /* 6.5.8 */
|expression BCLT expression {BinOp(BCompar(BClt), $1, $3)}
|expression BCGT expression {BinOp(BCompar(BCgt), $1, $3)}
|expression BCLE expression {BinOp(BCompar(BCle), $1, $3)}
|expression BCGE expression {BinOp(BCompar(BCge), $1, $3)}
;
equality_expression: /* 6.5.9 */
|expression BCEQ expression {BinOp(BCompar(BCeq), $1, $3)}
|expression BCNE expression {BinOp(BCompar(BCne), $1, $3)}
;
/*les operateurs booleens */
logical_and_expression:
|expression BLAND expression {BinOp(BBool(BBand), $1, $3)} /* 6.5.13 */
;
logical_or_expression:
|expression BLOR expression {BinOp(BBool(BBor), $1, $3)} /* 6.5.14 */
;
conditional_expression: /* 6.5.16 */
|expression QMARK expression COLON expression {CondE($1, $3, $5)}
;
/*///////////// FIN DES EXPRESSIONS ///////////////////*/
/*///////////// DEBUT DES STATEMENTS //////////////////*/
statement: /* A.2.3 ----> 6.8 */
|compound_statement {$1} /* peut etre fundefn plutot vu que c'est le vrai compound_statement*/
// |expression_statement {$1}
|select_statement {$1} /*if et else*/
|iteration_statement {$1} /*while et for*/
|jump_statement SEMICOLON {$1} /*return et break*/
|assignation SEMICOLON {$1}
|IDENTIFIER LPAREN expr_list RPAREN {CallC($1,$3)}
// Faut faire l'appel à des foncttions avec CondC( fname * (expr_list ) )
;
expr_list:
| { [] }
| expression expr_list{[$1] @ $2}
;
compound_statement: /* 6.8.2 */
|LBRACE block_item_list_opt RBRACE {$2}
;
block_item_list_opt: /* 6.8.2 */
|statement block_item_list_opt {Seq($1,$2)} /* pas sur du tout */
|{Skip}
;
select_statement: /* 6.8.4 */
|IF LPAREN expression RPAREN statement {CondC ($3, $5, Skip) }
|IF LPAREN expression RPAREN statement ELSE statement {CondC ($3, $5, $7) }
;
iteration_statement: /* 6.8.5 */
|WHILE LPAREN expression RPAREN statement {Loop (Seq (CondC ( $3, Skip, Exit), $5))}
|FOR LPAREN expression SEMICOLON expression SEMICOLON expression RPAREN statement {Loop (Seq (CondC ( $5, Skip, Exit), $9))} /*Absolument pas sur*/
;
jump_statement: /* 6.8.6 */
|RETURN expression {Return($2)}
;
assignation: /* 6.5.17 */ /* dans la doc ça fait parti des expressions mais pg */
|IDENTIFIER EQ expression {Assign($1, $3)}
;
/*
Dans ce qu'il y a marqué dans lang.ml, il manque
expr : CallE of fname * (expr list) ( call expression )
et
com : CallC of fname * (expr list) ( call statement )
*/
/*
Demander au prof :
---Comment ça marche pour appeler une fonction ou expressionn CallE et CallC ?
associativité des opérateurs ? (dans le pdf TP2 : introduction à YACC, partie 4 --> développons la grammaire ---> tirer 2)
*/
+402 -25
View File
@@ -1,38 +1,415 @@
(* Typechecking of source programs *)
open Lang
open Lang;;
(* Environments *)
type environment = {
localvars: (vname * tp) list;
funbind: fundecl list
}
};;
let find_var (var: vname) (env: environment) =
let rec aux local_vars =
match local_vars with
| [] -> failwith "Variable inconnue"
| tete::reste ->
let (name, _) = tete in
if name = var
then tete
else aux reste
in aux (env.localvars)
(* Fonction sur les listes de declarations de variables *)
let rec count_same_var_name (name: string) (var_decl_list: vardecl list) =
match var_decl_list with
| [] -> 0
| Vardecl(var_tp, var_name)::reste ->
(count_same_var_name name reste)
+ if name = var_name then 1 else 0
;;
(* val count_same_var_decl : string -> Lang.vardecl list -> int = <fun> *)
(* let rec tp_expr (expression: expr) (env: environment) =
let rec valid_vardecl_list (var_decl_list: vardecl list) =
match var_decl_list with
| [] -> true
| Vardecl(var_tp, var_name)::reste ->
if (count_same_var_name var_name reste) = 0
then valid_vardecl_list reste
else false
;;
(* val valid_vardecl_list : Lang.vardecl list -> bool = <fun> *)
(* Recherche dans l'environement *)
type 'a option = None| Some of 'a;;
let findEnv_var (name: vname) (env: environment) =
let rec aux = function
| [] -> None
| (k, v)::reste ->
if k = name then Some(v)
else aux(reste)
in aux(env.localvars)
;;
(* val findEnv_var :
Lang.vname -> environment
-> Lang.tp option = <fun>
*)
let findEnv_fun (name: fname) (env: environment) =
let rec aux = function
| [] -> None
| Fundecl(tp, fname, vars)::reste ->
let f = (tp, fname, vars) in
if fname = name then Some(f)
else aux(reste)
in aux(env.funbind)
;;
(* val findEnv_fun :
Lang.fname -> environment
-> (Lang.tp * Lang.fname * Lang.vardecl list) option = <fun>
*)
(* Ajout dans l'environnement *)
let addEnv_var (var_decl: vardecl) (env: environment) =
let Vardecl(var_decl_tp, var_decl_name) = var_decl
in {
localvars=(var_decl_name, var_decl_tp)::(env.localvars);
funbind=env.funbind
};;
(* val addEnv_var :
Lang.vardecl -> environment
-> environment = <fun>
*)
let addEnv_fun (fun_decl: fundecl) (env: environment) = {
localvars=(env.localvars);
funbind=(fun_decl::(env.funbind))
};;
(* val addEnv_fun :
Lang.fundecl -> environment
-> environment = <fun>
*)
(* Ajout dans l'environnement (récursif) *)
let rec build_env_fun (env: environment) (fun_decl_list: fundecl list) =
match fun_decl_list with
| [] -> env
| fun_decl::reste ->
let Fundecl(fun_decl_tp,_,var_decl_list) = fun_decl
in if valid_vardecl_list var_decl_list
then addEnv_fun fun_decl env
else raise (Failure "There is var declaration with the same name as arguments")
;;
(* val build_env_fun :
environment -> Lang.fundecl list
-> environment = <fun>
*)
let rec build_env_var (env: environment) (var_decl_list: vardecl list) =
match var_decl_list with
| [] -> env
| var_decl::reste -> build_env_var (addEnv_var var_decl env) reste
;;
(* val build_env_var :
environment -> Lang.vardecl list
-> environment = <fun>
*)
(* Typage d'une declaration de variable *)
let tp_vardecl (vdecl: vardecl) =
let Vardecl(vdecl_tp, _) = vdecl
in vdecl_tp
;;
(* val tp_vardecl : Lang.vardecl -> Lang.tp = <fun> *)
(* ----- Typage d'une expression ----- *)
let rec tp_expr (env: environment) (expression: expr) =
match expression with
| Const(const) ->
match const with
| BoolV(_) -> BoolT
| FloatV(_) -> FloatT
| IntV(_) -> IntT
| LitV(_) -> LitT
| StringV(_) -> StringT
| VarE(var) -> tp_expr (find_var var env) env
| BinOp(op, expr1, expr2) ->
| CondE(expr1, expr2, expr3) ->
| CallE(functionName, exprList) -> *)
| Const(const) -> (
match const with
| BoolV _ -> BoolT
| FloatV _ -> FloatT
| IntV _ -> IntT
| LitV _ -> LitT
| StringV _ -> StringT
)
| VarE(var) -> (
let var_value = (findEnv_var var env) in
match var_value with
| Some(value) -> value
| None -> raise (Failure "Unknown var")
)
| BinOp(op, expr1, expr2) ->
let tp_expr1 = tp_expr env expr1
and tp_expr2 = tp_expr env expr2 in
if tp_expr1 = tp_expr2
then (
match op with
| BArith(barith) -> (
match barith with
| BAadd -> IntT
| BAsub -> IntT
| BAmul -> IntT
| BAdiv -> IntT
| BAmod -> IntT
| BAfadd -> FloatT
| BAfsub -> FloatT
| BAfmul -> FloatT
| BAfdiv -> FloatT
)
| BBool(_) ->
if tp_expr1 = BoolT && tp_expr2 = BoolT
then BoolT
else raise (Failure "Invalid Boolean operation")
| BCompar(_) -> BoolT
)
else raise (Failure "Invalid type of Binary operation")
| CondE(expr1, expr2, expr3) ->
let tp_expr1 = tp_expr env expr1
and tp_expr2 = tp_expr env expr2
and tp_expr3 = tp_expr env expr3
in if tp_expr1 = BoolT && tp_expr2 = tp_expr3
then tp_expr2
else raise (Failure "Invalid type of Conditionnal Expression")
| CallE(name, list_expr) ->
match (findEnv_fun name env) with
| Some(func) -> (
let (func_tp, func_name, func_list_vardecl) = func in
if (List.map (tp_expr env) list_expr) = (List.map tp_vardecl func_list_vardecl)
then func_tp
else raise (Failure "Invalid arguments")
)
| None -> raise (Failure "Unknown function in the environment")
;;
(* val tp_expr :
environment -> Lang.expr
-> Lang.tp = <fun>
*)
(* - tp_expr: TESTS - *)
let test_tp_expr =
let function_to_test = tp_expr {
localvars=[
("i", IntT);
("f", FloatT);
("b", BoolT);
("l", LitT);
("s", StringT);
];
funbind=[
Fundecl(BoolT, "fun1", [Vardecl(IntT, "a"); Vardecl(FloatT, "b")])
]
}
and input_values = [
Const(BoolV(true));
Const(FloatV(10.98));
Const(IntV(10));
Const(LitV("l"));
Const(StringV("Hello"));
VarE("b");
VarE("f");
VarE("i");
VarE("l");
VarE("s");
BinOp(BArith(BAadd), Const(IntV(5)), VarE("i"));
BinOp(BArith(BAsub), Const(IntV(5)), VarE("i"));
BinOp(BArith(BAmul), Const(IntV(5)), VarE("i"));
BinOp(BArith(BAdiv), Const(IntV(5)), VarE("i"));
BinOp(BArith(BAmod), Const(IntV(5)), VarE("i"));
BinOp(BArith(BAfadd), Const(FloatV(5.)), VarE("f"));
BinOp(BArith(BAfsub), Const(FloatV(5.)), VarE("f"));
BinOp(BArith(BAfmul), Const(FloatV(5.)), VarE("f"));
BinOp(BArith(BAfdiv), Const(FloatV(5.)), VarE("f"));
BinOp(BCompar(BCeq), VarE("i"), VarE("i"));
BinOp(BCompar(BCge), VarE("i"), VarE("i"));
BinOp(BCompar(BCgt), VarE("i"), VarE("i"));
BinOp(BCompar(BCle), VarE("i"), VarE("i"));
BinOp(BCompar(BClt), VarE("i"), VarE("i"));
BinOp(BCompar(BCne), VarE("i"), VarE("i"));
BinOp(BBool(BBand), VarE("b"), VarE("b"));
BinOp(BBool(BBor), VarE("b"), VarE("b"));
(* (4 >= 5) ? 7 : 8 -> IntT *)
CondE(
BinOp(BCompar(BCge), Const(IntV(4)), Const(IntV(5))),
Const(IntV(7)),
Const(IntV(8))
);
CallE("fun1", [VarE("i"); VarE("f")]);
(* CallE("fun2", [VarE("i"); VarE("f")]); *)
(* CallE("fun1", [VarE("b"); VarE("f")]); *)
] and expected_result = [
BoolT; FloatT; IntT; LitT; StringT;
BoolT; FloatT; IntT; LitT; StringT;
IntT; IntT; IntT; IntT; IntT;
FloatT; FloatT; FloatT; FloatT;
BoolT; BoolT; BoolT; BoolT; BoolT; BoolT;
BoolT; BoolT;
IntT;
BoolT;
] in
(List.map function_to_test input_values) = expected_result
;;
let tp_prog (Prog (fundecls, fundefns)) = true
(* ----- Typage d'une commande ----- *)
let rec tp_cmd (env: environment) (cmd: com) =
match cmd with
| Skip -> VoidT
| Exit -> VoidT
| Assign(name, expr) -> VoidT
| Seq(cmd1, cmd2) ->
let tp_cmd1 = (tp_cmd env cmd1)
and tp_cmd2 = (tp_cmd env cmd2)
in if tp_cmd1 = VoidT
then tp_cmd2
else raise (Failure "Invalid type Sequence")
| CondC(expr1, cmd1, cmd2) ->
let tp_expr1 = tp_expr env expr1
and tp_cmd1 = tp_cmd env cmd1
and tp_cmd2 = tp_cmd env cmd2
in
if tp_expr1 = BoolT && tp_cmd1 = tp_cmd2
then tp_cmd1
else raise (Failure "Invalid type of Conditionnal Command")
| Loop(cmd1) ->
let _ = (tp_cmd env cmd1) in VoidT
| CallC(name, list_expr) -> tp_expr env (CallE(name, list_expr))
| Return(expr) -> (tp_expr env expr)
;;
(* val tp_cmd :
environment -> Lang.com
-> Lang.tp = <fun>
*)
(* - tp_cmd: TESTS - *)
let test_tp_cmd =
let function_to_test = tp_cmd {
localvars=[
("i", IntT);
("f", FloatT);
];
funbind=[
Fundecl(BoolT, "fun1", [Vardecl(IntT, "a"); Vardecl(FloatT, "b")])
]
}
and input_values = [
Skip;
Exit;
Assign("test", Const(IntV(5)));
Seq(Skip, Exit);
Seq(Skip, Return(Const(FloatV(5.))));
CondC(
BinOp(BCompar(BCge), Const(IntV(4)), Const(IntV(5))),
Skip, Skip
);
Loop(Exit);
CallC("fun1", [VarE("i"); VarE("f")]);
Return(Const(IntV(5)));
]
and expected_result = [
VoidT;
VoidT;
VoidT;
VoidT; FloatT;
VoidT;
VoidT;
BoolT;
IntT;
] in
(List.map function_to_test input_values) = expected_result
;;
(* ----- Typage d'une définition de fonction ----- *)
let tp_fundefn (env: environment) (fun_def: fundefn) =
let Fundefn(fun_decl, cmd) = fun_def in
let Fundecl(fun_decl_tp,_,var_decl_list) = fun_decl in
let env1 = build_env_var env var_decl_list in
let _ = tp_cmd env1 cmd
in if valid_vardecl_list var_decl_list && (tp_cmd env1 cmd) = fun_decl_tp
then fun_decl_tp
else raise (Failure "Type return is not the same as the type of the function")
;;
(* val tp_fundefn :
environment -> Lang.fundefn
-> Lang.tp = <fun>
*)
(* - tp_fundefn: TESTS - *)
let test_tp_fundefn =
let function_to_test = tp_fundefn {
localvars=[];
funbind=[
Fundecl(BoolT, "fun1", [Vardecl(IntT, "x"); Vardecl(FloatT, "y")]);
Fundecl(IntT, "fun2", [Vardecl(IntT, "x"); Vardecl(FloatT, "y")]);
]
}
and input_values = [
Fundefn(
Fundecl(BoolT, "fun1", [Vardecl(IntT, "a"); Vardecl(FloatT, "b")]),
Return(BinOp(BCompar(BCeq), Const(IntV(4)), Const(IntV(5))))
);
Fundefn(
Fundecl(IntT, "fun2", [Vardecl(IntT, "a"); Vardecl(FloatT, "b")]),
Return(VarE("a"))
);
]
and expected_result = [
BoolT;
IntT;
] in
(List.map function_to_test input_values) = expected_result
;;
(* ----- Typage d'un programme ----- *)
let tp_prog (Prog (fundecls, fundefns)) =
let env = build_env_fun {localvars=[];funbind=[]} fundecls in
try (
let _ = List.map (tp_fundefn env) fundefns
in true
) with _ -> false
;;
(* val tp_prog :
Lang.prog
-> bool = <fun>
*)
(* - tp_prog: TESTS - *)
let test_tp_prog =
let function_to_test = tp_prog
and input_values = [
Prog(
[
Fundecl(BoolT, "fun1", [Vardecl(IntT, "x"); Vardecl(FloatT, "y")]);
Fundecl(IntT, "fun2", [Vardecl(IntT, "x"); Vardecl(FloatT, "y")]);
],
[
Fundefn(
Fundecl(BoolT, "fun1", [Vardecl(IntT, "a"); Vardecl(FloatT, "b")]),
Return(BinOp(BCompar(BCeq), Const(IntV(4)), Const(IntV(5))))
);
Fundefn(
Fundecl(IntT, "fun2", [Vardecl(IntT, "a"); Vardecl(FloatT, "b")]),
Return(VarE("a"))
);
]
);
]
and expected_result = [
true;
] in
(List.map function_to_test input_values) = expected_result
;;
+2 -2
View File
@@ -13,12 +13,12 @@ open Instrs;;
(* For using the parser:
- Evaluate this file (use.ml)
- parse "Tests/rectangles.c" ;;
- parse "../Tests/progsimple.c" ;;
* For code generation:
- Evaluate this file (use.ml)
- run_test "Tests/rectangles.c" "Tests/rectangles.ps";;
- run_test "../Tests/rectangles.c" "../Tests/rectangles.ps";;
*)
+20
View File
@@ -0,0 +1,20 @@
void yes( int yes){
yes = 5;
return yes;
}
void main (string y, int x, int yooo) {
x = 15;
while (x < 20) {
x = x + 1 -16;
y = "hello";
if (x == 17) {
y = "world";
}
}
yooo = yes(5);
return x;
}