la fin approche

This commit is contained in:
Guillotin Damien 2022-01-11 11:47:31 +01:00
parent 94c2ce32e5
commit ae1324106a
5 changed files with 251 additions and 168 deletions

View file

@ -5,7 +5,6 @@ struct
open Tds open Tds
open Ast open Ast
open AstType open AstType
open AstPlacement
open Type open Type
open Code open Code
@ -27,19 +26,16 @@ let rec getTailleAvant aff n =
(res + (getTaille t), false) (res + (getTaille t), false)
) (0, false) l_typstr ) (0, false) l_typstr
in tai in tai
| _ -> failwith "TODO or not TODO" | _ -> failwith "Internal Error"
end end
| Attribut(aff2, info) -> (** (A.c).x | Attribut(aff2, info) ->
avec A = (1 2 (3 4) 5) = (a b c d)
avec c = (x y)
ici A ~ aff2 | c ~ info | x ~ n *)
begin begin
match info_ast_to_info info with match info_ast_to_info info with
| InfoVar(n2, _, _, _) -> | InfoVar(_, _, _, _) ->
let t2 = getType aff2 in let t2 = getType aff2 in
let aff_gen = Ident (info_to_info_ast (InfoVar("", t2, 0, ""))) in let aff_gen = Ident (info_to_info_ast (InfoVar("", t2, 0, ""))) in
getTailleAvant aff_gen n getTailleAvant aff_gen n
| _ -> failwith "adaidadj" | _ -> failwith "Internal Error"
end end
and getType aff = and getType aff =
@ -49,7 +45,7 @@ and getType aff =
begin begin
match info_ast_to_info info with match info_ast_to_info info with
| InfoVar(_, t, _, _) -> t | InfoVar(_, t, _, _) -> t
| _ -> failwith "prooblemo" | _ -> failwith "Internal Error"
end end
| Attribut(aff2, info) -> | Attribut(aff2, info) ->
begin begin
@ -66,9 +62,9 @@ and getType aff =
res res
) Undefined l_typstr ) Undefined l_typstr
in t2 in t2
| _ -> failwith "pas ok" | _ -> failwith "Internal Error"
end end
| _ -> failwith "sproblematik" | _ -> failwith "Internal Error"
end end
and getTailleAttribut aff n = and getTailleAttribut aff n =
@ -85,7 +81,7 @@ and getTailleAttribut aff n =
else else
res res
) l_typstr 0 ) l_typstr 0
| _ -> failwith "TODO' or not TODO'" | _ -> failwith "Internal Error"
end end
| Attribut(_, _) -> getTaille (getType aff) | Attribut(_, _) -> getTaille (getType aff)
@ -96,7 +92,7 @@ and getBase aff =
begin begin
match info_ast_to_info i with match info_ast_to_info i with
| InfoVar(_, _, base, _) -> base | InfoVar(_, _, base, _) -> base
| _ -> failwith "spa bon" | _ -> failwith "Internal Error"
end end
| Attribut(a,i) -> | Attribut(a,i) ->
begin begin
@ -106,7 +102,7 @@ and getBase aff =
let ita = getTailleAvant aff n in let ita = getTailleAvant aff n in
let res = ib + ita in let res = ib + ita in
res res
| _ -> failwith "v vhjbhki" | _ -> failwith "Internal Error"
end end
and getReg aff = and getReg aff =
@ -116,7 +112,7 @@ and getReg aff =
begin begin
match info_ast_to_info i with match info_ast_to_info i with
| InfoVar(_, _, _, reg) -> reg | InfoVar(_, _, _, reg) -> reg
| _ -> failwith "spa bon" | _ -> failwith "Internal Error"
end end
| Attribut(a,_) -> getReg a | Attribut(a,_) -> getReg a
@ -138,7 +134,7 @@ and analyse_code_affectable a =
match info_ast_to_info i with match info_ast_to_info i with
| InfoVar(_, t, base, reg) -> "LOAD (" ^ (string_of_int (getTaille t)) ^ ") " ^ (string_of_int base) ^ "[" ^ reg ^ "]\n" | InfoVar(_, t, base, reg) -> "LOAD (" ^ (string_of_int (getTaille t)) ^ ") " ^ (string_of_int base) ^ "[" ^ reg ^ "]\n"
| InfoConst(_,v) -> "LOADL " ^ (string_of_int v) ^ "\n" | InfoConst(_,v) -> "LOADL " ^ (string_of_int v) ^ "\n"
| _ -> failwith "w-wtf bwo y-you okay -.-" | _ -> failwith "Internal Error"
end end
| Attribut(_, _) -> | Attribut(_, _) ->
@ -154,7 +150,7 @@ and analyse_code_expression e =
| InfoFun(nom,_,_) -> | InfoFun(nom,_,_) ->
(List.fold_right (fun e res -> analyse_code_expression e ^ res) le "") ^ (List.fold_right (fun e res -> analyse_code_expression e ^ res) le "") ^
"CALL (ST) " ^ nom ^ "\n" "CALL (ST) " ^ nom ^ "\n"
| _ -> failwith "eeeeencore un pb" | _ -> failwith "Internal Error"
end end
| Booleen(b) -> | Booleen(b) ->
@ -201,7 +197,7 @@ and analyse_code_expression e =
begin begin
match info_ast_to_info i with match info_ast_to_info i with
| InfoVar(_, _, base, _) -> "LOADL " ^ (string_of_int base) ^ "\n" | InfoVar(_, _, base, _) -> "LOADL " ^ (string_of_int base) ^ "\n"
| _ -> failwith "on a un pb" | _ -> failwith "Internal Error"
end end
| Tuple(l_expr) -> | Tuple(l_expr) ->
List.fold_right (fun e res -> analyse_code_expression e ^ res) l_expr "" List.fold_right (fun e res -> analyse_code_expression e ^ res) l_expr ""
@ -217,7 +213,7 @@ and analyse_code_instruction i taille_return taille_args taille_var =
"PUSH " ^ (string_of_int (getTaille t)) ^ "\n" ^ "PUSH " ^ (string_of_int (getTaille t)) ^ "\n" ^
analyse_code_expression e ^ analyse_code_expression e ^
"STORE (" ^ (string_of_int (getTaille t)) ^ ") " ^ (string_of_int base) ^ "[" ^ reg ^ "]\n" "STORE (" ^ (string_of_int (getTaille t)) ^ ") " ^ (string_of_int base) ^ "[" ^ reg ^ "]\n"
| _ -> failwith "match non exautique" | _ -> failwith "Internal Error"
end end
| Affectation(a, e) -> | Affectation(a, e) ->
@ -229,7 +225,7 @@ and analyse_code_instruction i taille_return taille_args taille_var =
| InfoVar (_, t, base, reg) -> | InfoVar (_, t, base, reg) ->
(analyse_code_expression e) ^ (analyse_code_expression e) ^
"STORE (" ^ string_of_int (getTaille t) ^ ") " ^ (string_of_int base) ^ "[" ^ reg ^ "]\n" "STORE (" ^ string_of_int (getTaille t) ^ ") " ^ (string_of_int base) ^ "[" ^ reg ^ "]\n"
| _ -> failwith "Erreur interne : symbole non reconnnu" | _ -> failwith "Internal Error"
end end
| Dref(a, t) -> | Dref(a, t) ->
@ -246,9 +242,9 @@ and analyse_code_instruction i taille_return taille_args taille_var =
| InfoVar(n, _, _, _) -> | InfoVar(n, _, _, _) ->
(analyse_code_expression e) ^ (analyse_code_expression e) ^
"STORE (" ^ (string_of_int (getTailleAttribut a n)) ^ ") " ^ (string_of_int (getBase a)) ^ "[" ^ reg ^ "]\n" "STORE (" ^ (string_of_int (getTailleAttribut a n)) ^ ") " ^ (string_of_int (getBase a)) ^ "[" ^ reg ^ "]\n"
| _ -> failwith "toujours pas bonn" | _ -> failwith "Internal Error"
end end
| _ -> failwith "toujours pas bon" | _ -> failwith "Internal Error"
end end
end end
@ -321,20 +317,20 @@ and analyse_code_instruction i taille_return taille_args taille_var =
"LOADL ' '\n" ^ "LOADL ' '\n" ^
"SUBR COut\n" "SUBR COut\n"
,taille + (getTaille t)) ,taille + (getTaille t))
| _ -> failwith "peut pas print des non printable, ofc" | _ -> failwith "Internal Error"
) ("LOADL ' '\nSUBR COut\n", base) l_t in ) ("LOADL ' '\nSUBR COut\n", base) l_t in
res res
end end
| _ -> failwith "toujours pas bon ca" | _ -> failwith "Internal Error"
in in
let rec affichage_expression e t = let affichage_expression e t =
let l_typstr = let l_typstr =
match t with match t with
| Struct(l_typstr) -> l_typstr | Struct(l_typstr) -> l_typstr
| _ -> failwith "wowowowow" | _ -> failwith "Internal Error"
in in
let l_t, l_s = List.split l_typstr in let l_t, _ = List.split l_typstr in
match e with match e with
| Tuple(l_e) -> | Tuple(l_e) ->
List.fold_right ( List.fold_right (
@ -346,7 +342,7 @@ and analyse_code_instruction i taille_return taille_args taille_var =
| Rat -> AffichageRat(e) | Rat -> AffichageRat(e)
| Pointeur(_) -> AffichagePointeur(e) | Pointeur(_) -> AffichagePointeur(e)
| Struct(_) -> AffichageStruct(e, t) | Struct(_) -> AffichageStruct(e, t)
| _ -> failwith "peut pas print des non printable, duh" | _ -> failwith "Internal Error"
in in
"LOADL ' '\n" ^ "LOADL ' '\n" ^
"SUBR COut\n" ^ "SUBR COut\n" ^
@ -357,21 +353,21 @@ and analyse_code_instruction i taille_return taille_args taille_var =
| Affectable(a) -> | Affectable(a) ->
begin begin
match a with match a with
| Dref(a,t) -> failwith "ok1" | Dref(_, _) -> failwith "Internal Error"
| Ident(i) -> | Ident(i) ->
begin begin
match info_ast_to_info i with match info_ast_to_info i with
| InfoVar(_, t, base, reg) -> | InfoVar(_, t, base, reg) ->
affichage base reg t affichage base reg t
| _ -> failwith "spa bon" | _ -> failwith "Internal Error"
end end
| Attribut(a2,i) -> | Attribut(_, i) ->
match info_ast_to_info i with match info_ast_to_info i with
| InfoVar(n, t, _, _) -> | InfoVar(_, t, _, _) ->
let base = getBase a in let base = getBase a in
let reg = getReg a in let reg = getReg a in
affichage base reg t affichage base reg t
| _ -> failwith "zifj" | _ -> failwith "Internal Error"
end end
| AppelFonction(i, le) -> | AppelFonction(i, le) ->
begin begin
@ -393,16 +389,16 @@ and analyse_code_instruction i taille_return taille_args taille_var =
| Rat -> AffichageRat(Nothing) | Rat -> AffichageRat(Nothing)
| Pointeur(_) -> AffichagePointeur(Nothing) | Pointeur(_) -> AffichagePointeur(Nothing)
| Struct(l_ts) -> AffichageStruct(Tuple(List.map (fun _ -> Nothing) l_ts), t) | Struct(l_ts) -> AffichageStruct(Tuple(List.map (fun _ -> Nothing) l_ts), t)
| _ -> failwith "peut pas print des non printable, duuuh" | _ -> failwith "Internal Error"
in in
"LOADL ' '\n" ^ "LOADL ' '\n" ^
"SUBR COut\n" ^ "SUBR COut\n" ^
(analyse_code_instruction i "0" "0" "0") ^ (analyse_code_instruction i "0" "0" "0") ^
res res
) l_typstr "LOADL ' '\nSUBR COut\n" *) ) l_typstr "LOADL ' '\nSUBR COut\n" *)
| _ -> failwith "bizreement pas ok" | _ -> failwith "Internal Error"
end end
| _ -> failwith "spa cool ca" | _ -> failwith "Internal Error"
in in
"LOADL '{'\n" ^ "LOADL '{'\n" ^
@ -416,20 +412,19 @@ and analyse_code_instruction i taille_return taille_args taille_var =
let etiq2 = getEtiquette () in let etiq2 = getEtiquette () in
(analyse_code_expression e) ^ (analyse_code_expression e) ^
"JUMPIF (0) " ^ etiq1 ^ "\n" ^ "JUMPIF (0) " ^ etiq1 ^ "\n" ^
(analyse_code_bloc b1 taille_return taille_args taille_var) ^ (analyse_code_bloc b1 taille_return taille_args) ^
"JUMP " ^ etiq2 ^ "\n" ^ "JUMP " ^ etiq2 ^ "\n" ^
etiq1 ^ "\n" ^ etiq1 ^ "\n" ^
(analyse_code_bloc b2 taille_return taille_args taille_var) ^ (analyse_code_bloc b2 taille_return taille_args) ^
etiq2 ^ "\n" etiq2 ^ "\n"
| TantQue(e, b) -> | TantQue(e, b) ->
let taille_var = string_of_int (List.fold_right (fun e res -> taille_variables_declarees e + res) b 0) in
let etiq_while = getEtiquette () in let etiq_while = getEtiquette () in
let etiq_fin = getEtiquette () in let etiq_fin = getEtiquette () in
etiq_while ^ "\n" ^ etiq_while ^ "\n" ^
(analyse_code_expression e) ^ (analyse_code_expression e) ^
"JUMPIF (0) " ^ etiq_fin ^ "\n" ^ "JUMPIF (0) " ^ etiq_fin ^ "\n" ^
(analyse_code_bloc b taille_return taille_args taille_var) ^ (analyse_code_bloc b taille_return taille_args) ^
"JUMP " ^ etiq_while ^ "\n" ^ "JUMP " ^ etiq_while ^ "\n" ^
etiq_fin ^ "\n" etiq_fin ^ "\n"
@ -440,7 +435,7 @@ and analyse_code_instruction i taille_return taille_args taille_var =
| Empty -> "" | Empty -> ""
and analyse_code_bloc bloc taille_return taille_args taille_var = and analyse_code_bloc bloc taille_return taille_args =
let taille_var = string_of_int (List.fold_right (fun e res -> taille_variables_declarees e + res) bloc 0) in let taille_var = string_of_int (List.fold_right (fun e res -> taille_variables_declarees e + res) bloc 0) in
List.fold_right ( List.fold_right (
fun i res -> (analyse_code_instruction i taille_return taille_args taille_var) ^ res fun i res -> (analyse_code_instruction i taille_return taille_args taille_var) ^ res
@ -450,19 +445,18 @@ and analyse_code_bloc bloc taille_return taille_args taille_var =
and analyse_code_fonction (AstPlacement.Fonction(info, _, bloc)) = and analyse_code_fonction (AstPlacement.Fonction(info, _, bloc)) =
match info_ast_to_info info with match info_ast_to_info info with
| InfoFun(name, t, l_t) -> | InfoFun(name, t, l_t) ->
let taille_var = string_of_int (List.fold_right (fun e res -> taille_variables_declarees e + res) bloc 0) in
let taille_return = string_of_int (getTaille t) in let taille_return = string_of_int (getTaille t) in
let taille_args = string_of_int (List.fold_right (fun e res -> getTaille e + res) l_t 0) in let taille_args = string_of_int (List.fold_right (fun e res -> getTaille e + res) l_t 0) in
name ^ "\n" ^ name ^ "\n" ^
(analyse_code_bloc bloc taille_return taille_args taille_var) ^ (analyse_code_bloc bloc taille_return taille_args) ^
"HALT\n" "HALT\n"
| _ -> failwith "spa normal" | _ -> failwith "Internal Error"
let analyser (AstPlacement.Programme(fonctions, prog)) = let analyser (AstPlacement.Programme(fonctions, prog)) =
let code = getEntete () in let code = getEntete () in
let code = code ^ List.fold_right (fun e res -> (analyse_code_fonction e) ^ res) fonctions "" in let code = code ^ List.fold_right (fun e res -> (analyse_code_fonction e) ^ res) fonctions "" in
let code = code ^ "main\n" in let code = code ^ "main\n" in
let code = code ^ (analyse_code_bloc prog "0" "0" "0") in let code = code ^ (analyse_code_bloc prog "0" "0") in
code ^ "\nHALT" code ^ "\nHALT"
end end

View file

@ -4,7 +4,6 @@ struct
open Tds open Tds
open Ast open Ast
open AstType
open AstPlacement open AstPlacement
open Type open Type
@ -21,7 +20,7 @@ let rec analyse_placement_instruction i base reg =
let taille = getTaille t in let taille = getTaille t in
modifier_adresse_info base reg info; modifier_adresse_info base reg info;
taille taille
| _ -> failwith "wtf frère" | _ -> failwith "Internal Error"
end end
| AstType.Conditionnelle(_, b1, b2) -> | AstType.Conditionnelle(_, b1, b2) ->
@ -49,7 +48,7 @@ and analyse_placement_fonction (AstType.Fonction(info, l_typinfo, bloc)) =
| InfoVar(_,t,_,_) -> | InfoVar(_,t,_,_) ->
modifier_adresse_info (res_q - (getTaille t)) "LB" x; modifier_adresse_info (res_q - (getTaille t)) "LB" x;
res_q - (getTaille t) res_q - (getTaille t)
| _ -> failwith "pas normal" | _ -> failwith "Internal Error"
end end
) l_typinfo 0 in ) l_typinfo 0 in
let _ = analyse_placement_bloc 3 "LB" bloc in let _ = analyse_placement_bloc 3 "LB" bloc in

View file

@ -11,7 +11,23 @@ struct
type t1 = Ast.AstSyntax.programme type t1 = Ast.AstSyntax.programme
type t2 = Ast.AstTds.programme type t2 = Ast.AstTds.programme
(*
recherche_type:
tds -> typ -> typ
Description:
Permet d'obtenir le type d'un typedef
Parameters:
- tds : la table des symboles que l'on souhaite cherche
- t : le type que l'on cherche
Returns:
Le type d'un typedef
Pre-conditions:
- True
Post-conditions:
- True
Exceptions:
- IdentifiantNonDeclare
*)
let rec recherche_type tds t = let rec recherche_type tds t =
match t with match t with
| TIdent(t_nom) -> | TIdent(t_nom) ->
@ -22,19 +38,33 @@ let rec recherche_type tds t =
begin begin
match info_ast_to_info i with match info_ast_to_info i with
| InfoType(_, t2) -> recherche_type tds t2 | InfoType(_, t2) -> recherche_type tds t2
| _ -> failwith "un truc louche ca" | _ -> failwith "Internal Error"
end end
end end
| _ -> | Struct (l_typstr) ->
begin
match t with
| Struct (l_typstr) ->
let n_l_typstr = (List.map (fun (t, n) -> (recherche_type tds t, n)) l_typstr) in let n_l_typstr = (List.map (fun (t, n) -> (recherche_type tds t, n)) l_typstr) in
Struct n_l_typstr Struct n_l_typstr
| _ -> t | _ -> t
end
(*
analyse_tds_affectable:
tds -> AstSyntax.affectable -> bool -> AstTds.affectable
Description:
Transforme les affectable de l'AstSyntax en AstTds
Parameters:
- tds : la table des symboles courante
- a : l'affectable à analyser
- modif : permet de savoir s'il sagit d'un affectable dans une expression ou dans une affectation
Returns:
Un nouvel AstTds.affectable
Pre-conditions:
- True
Post-conditions:
- True
Exceptions:
- IdentifiantNonDeclare
- MauvaiseUtilisationIdentifiant
*)
let rec analyse_tds_affectable tds a modif = let rec analyse_tds_affectable tds a modif =
match a with match a with
| AstSyntax.Dref new_aff -> | AstSyntax.Dref new_aff ->
@ -52,21 +82,38 @@ let rec analyse_tds_affectable tds a modif =
| InfoConst _ -> | InfoConst _ ->
begin begin
if modif then if modif then
failwith "bah non en fait" failwith "Internal Error"
else else
AstTds.Ident(info) AstTds.Ident(info)
end end
| InfoFun _ -> raise (MauvaiseUtilisationIdentifiant(n)) | InfoFun _ -> (* On ne peut pas utiliser une fonction comme affectable *)
raise (MauvaiseUtilisationIdentifiant(n))
| _ -> failwith "Internal Error"
end end
end end
| AstSyntax.Attribut(aff, str) -> | AstSyntax.Attribut(aff, str) ->
(*
extraction_info:
affectable -> info_ast
Description:
Extrait l'info d'un affectable
Parameters:
- aff : Affectable dont on veut extraire l'info
Returns:
L'info de l'affectable
Pre-conditions:
- True
Post-conditions:
- True
*)
let rec extraction_info aff = let rec extraction_info aff =
match aff with match aff with
| Dref(aff2) -> extraction_info aff2 | Dref(aff2) -> extraction_info aff2
| Ident(info) -> info | Ident(info) -> info
| Attribut(aff2, info) -> info | Attribut(_, info) -> info
in in
let n_aff = analyse_tds_affectable tds aff modif in let n_aff = analyse_tds_affectable tds aff modif in
let info = extraction_info n_aff in let info = extraction_info n_aff in
match info_ast_to_info info with match info_ast_to_info info with
@ -77,60 +124,69 @@ let rec analyse_tds_affectable tds a modif =
let t = List.fold_right (fun (t, n) res -> if str = n then t else res) l_att Undefined in let t = List.fold_right (fun (t, n) res -> if str = n then t else res) l_att Undefined in
if t != Undefined then if t != Undefined then
AstTds.Attribut(n_aff, info_to_info_ast (InfoVar(str, t, 0, ""))) AstTds.Attribut(n_aff, info_to_info_ast (InfoVar(str, t, 0, "")))
else else (** L'attribut ne correspond à aucun attribut du struct *)
raise (MauvaiseUtilisationIdentifiant str) raise (MauvaiseUtilisationIdentifiant str)
| _ -> | _ -> (** Il faut que l'objet sur le quel on appelle l'attribut soit un struct *)
let _ = print_endline (string_of_type t) in raise (MauvaiseUtilisationIdentifiant str)
raise (MauvaiseUtilisationIdentifiant str) end (** Ce ne peut etre qu'un InfoVar *)
end
| _ -> raise (MauvaiseUtilisationIdentifiant str) | _ -> raise (MauvaiseUtilisationIdentifiant str)
(* analyse_tds_expression : AstSyntax.expression -> AstTds.expression *) (*
(* Paramètre tds : la table des symboles courante *) analyse_tds_affectable:
(* Paramètre e : l'expression à analyser *) tds -> AstSyntax.expression -> AstTds.expression
(* Vérifie la bonne utilisation des identifiants et tranforme l'expression Description:
en une expression de type AstTds.expression *) Vérifie la bonne utilisation des identifiants et transforme les expressions de l'AstSyntax en AstTds
(* Erreur si mauvaise utilisation des identifiants *) Parameters:
- tds : la table des symboles courante
- e : l'expression à analyser
Returns:
Une nouvelle AstTds.expression
Pre-conditions:
- True
Post-conditions:
- True
Exceptions:
- IdentifiantNonDeclare
- MauvaiseUtilisationIdentifiant
*)
let rec analyse_tds_expression tds e = let rec analyse_tds_expression tds e =
match e with match e with
| AstSyntax.AppelFonction(str, l_expr) -> | AstSyntax.AppelFonction(str, l_expr) ->
begin begin
match chercherGlobalement tds str with match chercherGlobalement tds str with
(* L'identifiant est déja déclaré *)
| None -> raise (IdentifiantNonDeclare str) | None -> (* L'identifiant est déja déclaré *)
raise (IdentifiantNonDeclare str)
| Some info -> | Some info ->
match (info_ast_to_info info) with match (info_ast_to_info info) with
| InfoFun(_, _, _) -> | InfoFun(_, _, _) ->
let nl_expr = List.map (fun e -> analyse_tds_expression tds e) l_expr in let nl_expr = List.map (fun e -> analyse_tds_expression tds e) l_expr in
AstTds.AppelFonction(info, nl_expr) AstTds.AppelFonction(info, nl_expr)
(* L'identifiant ne fait pas référence à une fonction, on lève ue exception *) | _ -> (* L'identifiant ne fait pas référence à une fonction, on lève une exception *)
| _ -> raise (MauvaiseUtilisationIdentifiant str) raise (MauvaiseUtilisationIdentifiant str)
end end
| AstSyntax.Booleen(b) -> | AstSyntax.Booleen(b) -> AstTds.Booleen(b)
begin
AstTds.Booleen(b) | AstSyntax.Entier(i) -> AstTds.Entier(i)
end
| AstSyntax.Entier(i) ->
begin
AstTds.Entier(i)
end
| AstSyntax.Unaire(u, expr) -> | AstSyntax.Unaire(u, expr) ->
begin let new_expr = analyse_tds_expression tds expr in
let new_expr = analyse_tds_expression tds expr in AstTds.Unaire (u, new_expr)
AstTds.Unaire (u, new_expr)
end
| AstSyntax.Binaire(b, expr_1, expr_2) -> | AstSyntax.Binaire(b, expr_1, expr_2) ->
begin let new_expr_1 = analyse_tds_expression tds expr_1 in
let new_expr_1 = analyse_tds_expression tds expr_1 in let new_expr_2 = analyse_tds_expression tds expr_2 in
let new_expr_2 = analyse_tds_expression tds expr_2 in AstTds.Binaire(b, new_expr_1, new_expr_2)
AstTds.Binaire(b, new_expr_1, new_expr_2)
end
| AstSyntax.Affectable(a) -> AstTds.Affectable(analyse_tds_affectable tds a false) | AstSyntax.Affectable(a) -> AstTds.Affectable(analyse_tds_affectable tds a false)
| AstSyntax.Null -> AstTds.Null | AstSyntax.Null -> AstTds.Null
| AstSyntax.NewType(t) -> AstTds.NewType(t) | AstSyntax.NewType(t) -> AstTds.NewType(t)
| AstSyntax.Adresse(n) -> | AstSyntax.Adresse(n) ->
let info = chercherGlobalement tds n in let info = chercherGlobalement tds n in
begin begin
@ -144,22 +200,37 @@ let rec analyse_tds_expression tds e =
| _ -> raise (MauvaiseUtilisationIdentifiant(n)) | _ -> raise (MauvaiseUtilisationIdentifiant(n))
end end
end end
| AstSyntax.Tuple(le) -> | AstSyntax.Tuple(le) ->
let n_le = List.map (fun e -> analyse_tds_expression tds e) le in let n_le = List.map (fun e -> analyse_tds_expression tds e) le in
AstTds.Tuple(n_le) AstTds.Tuple(n_le)
let rec analyse_tds_typedef tds (AstSyntax.TypeDef(n, t)) =
(*
analyse_tds_typedef:
tds -> AstSyntax.typedef -> AstTds.instruction
Description:
Transforme les typedef de l'AstSyntax en AstTds.instructions
Parameters:
- tds : la table des symboles courante
- td : le typedef à analyser
Returns:
Une nouvelle AstTds.affectable
Pre-conditions:
- True
Post-conditions:
- True
Exceptions:
- DoubleDeclaration
*)
let analyse_tds_typedef tds (AstSyntax.TypeDef(n, t)) =
begin begin
match chercherLocalement tds n with match chercherLocalement tds n with
| None -> | None -> (* L'identifiant n'est pas trouvé dans la tds locale du bloc, on ajoute donc dans la tds la constante *)
(* L'identifiant n'est pas trouvé dans la tds locale,
il n'a donc pas été déclaré dans le bloc courant *)
(* Ajout dans la tds de la constante *)
ajouter tds n (info_to_info_ast (InfoType (n, t))); ajouter tds n (info_to_info_ast (InfoType (n, t)));
Empty Empty
| Some _ ->
(* L'identifiant est trouvé dans la tds locale, | Some _ -> (* L'identifiant est trouvé dans la tds locale, il a donc double déclaration *)
il a donc déjà été déclaré dans le bloc courant *)
raise (DoubleDeclaration n) raise (DoubleDeclaration n)
end end
@ -169,109 +240,130 @@ let rec analyse_tds_typedef tds (AstSyntax.TypeDef(n, t)) =
(* Vérifie la bonne utilisation des identifiants et tranforme l'instruction (* Vérifie la bonne utilisation des identifiants et tranforme l'instruction
en une instruction de type AstTds.instruction *) en une instruction de type AstTds.instruction *)
(* Erreur si mauvaise utilisation des identifiants *) (* Erreur si mauvaise utilisation des identifiants *)
(*
analyse_tds_typedef:
tds -> AstSyntax.typedef -> AstTds.instruction
Description:
Transforme les typedef de l'AstSyntax en AstTds.instructions
Parameters:
- tds : la table des symboles courante
- td : le typedef à analyser
Returns:
Une nouvelle AstTds.affectable
Pre-conditions:
- True
Post-conditions:
- True
Exceptions:
- DoubleDeclaration
*)
let rec analyse_tds_instruction tds i = let rec analyse_tds_instruction tds i =
match i with match i with
| AstSyntax.Declaration (t, n, e) -> | AstSyntax.Declaration (t, n, e) ->
begin begin
match chercherLocalement tds n with match chercherLocalement tds n with
| None -> | None -> (* L'identifiant n'est pas trouvé dans la tds locale, il n'a donc pas été déclaré dans le bloc courant *)
let nt = recherche_type tds t in let nt = recherche_type tds t in
(* L'identifiant n'est pas trouvé dans la tds locale,
il n'a donc pas été déclaré dans le bloc courant *) (* Vérification de la bonne utilisation des identifiants dans l'expression et obtention de l'expression transformée *)
(* Vérification de la bonne utilisation des identifiants dans l'expression *)
(* et obtention de l'expression transformée *)
let ne = analyse_tds_expression tds e in let ne = analyse_tds_expression tds e in
(* Création de l'information associée à l'identfiant *) (* Création de l'information associée à l'identfiant *)
let info = InfoVar (n, nt, 0, "") in let info = InfoVar (n, nt, 0, "") in
(* Création du pointeur sur l'information *) (* Création du pointeur sur l'information *)
let ia = info_to_info_ast info in let ia = info_to_info_ast info in
(* Ajout de l'information (pointeur) dans la tds *) (* Ajout de l'information (pointeur) dans la tds *)
ajouter tds n ia; ajouter tds n ia;
(* Renvoie de la nouvelle déclaration où le nom a été remplacé par l'information
et l'expression remplacée par l'expression issue de l'analyse *) (* Renvoie de la nouvelle déclaration où le nom a été remplacé par l'information et l'expression remplacée par l'expression issue de l'analyse *)
AstTds.Declaration (nt, ia, ne) AstTds.Declaration (nt, ia, ne)
| Some _ ->
(* L'identifiant est trouvé dans la tds locale, | Some _ -> (* L'identifiant est trouvé dans la tds locale, il a donc déjà été déclaré dans le bloc courant *)
il a donc déjà été déclaré dans le bloc courant *)
raise (DoubleDeclaration n) raise (DoubleDeclaration n)
end end
| AstSyntax.Affectation (aff, e) -> | AstSyntax.Affectation (aff, e) ->
begin begin
let ne = analyse_tds_expression tds e in let ne = analyse_tds_expression tds e in
let n_a = analyse_tds_affectable tds aff false in let n_a = analyse_tds_affectable tds aff false in
match aff with match aff with
| Dref a -> | Dref _ ->
Affectation (n_a, ne) Affectation (n_a, ne)
| Ident(n) -> | Ident(n) ->
begin begin
match chercherGlobalement tds n with match chercherGlobalement tds n with
| None -> | None -> (* L'identifiant n'est pas trouvé dans la tds globale. *)
(* L'identifiant n'est pas trouvé dans la tds globale. *) raise (IdentifiantNonDeclare n)
raise (IdentifiantNonDeclare n)
| Some info -> | Some info -> (* L'identifiant est trouvé dans la tds globale, il a donc déjà été déclaré. L'information associée est récupérée. *)
(* L'identifiant est trouvé dans la tds globale, begin
il a donc déjà été déclaré. L'information associée est récupérée. *) match info_ast_to_info info with
begin | InfoVar _ -> (* Renvoie de la nouvelle affectation où le nom a été remplacé par l'information et l'expression remplacée par l'expression issue de l'analyse *)
match info_ast_to_info info with Affectation (n_a, ne)
| InfoVar _ ->
(* Renvoie de la nouvelle affectation où le nom a été remplacé par l'information | _ -> (* Modification d'une constante ou d'une fonction *)
et l'expression remplacée par l'expression issue de l'analyse *) raise (MauvaiseUtilisationIdentifiant n)
Affectation (n_a, ne) end
| _ -> end
(* Modification d'une constante ou d'une fonction *) | Attribut(_, _) -> (* RAF *)
raise (MauvaiseUtilisationIdentifiant n) Affectation(n_a, ne)
end
end
| Attribut(aff2, n) ->
begin
(** RAF *)
Affectation(n_a, ne)
end
end end
| AstSyntax.Constante (n,v) -> | AstSyntax.Constante (n,v) ->
begin begin
match chercherLocalement tds n with match chercherLocalement tds n with
| None -> | None -> (* L'identifiant n'est pas trouvé dans la tds locale, il n'a donc pas été déclaré dans le bloc courant *)
(* L'identifiant n'est pas trouvé dans la tds locale,
il n'a donc pas été déclaré dans le bloc courant *) (* Ajout dans la tds de la constante *)
(* Ajout dans la tds de la constante *) ajouter tds n (info_to_info_ast (InfoConst (n,v)));
ajouter tds n (info_to_info_ast (InfoConst (n,v)));
(* Suppression du noeud de déclaration des constantes devenu inutile *) (* Suppression du noeud de déclaration des constantes devenu inutile *)
Empty Empty
| Some _ ->
(* L'identifiant est trouvé dans la tds locale, | Some _ -> (* L'identifiant est trouvé dans la tds locale, il a donc déjà été déclaré dans le bloc courant *)
il a donc déjà été déclaré dans le bloc courant *)
raise (DoubleDeclaration n) raise (DoubleDeclaration n)
end end
| AstSyntax.Affichage e -> | AstSyntax.Affichage e ->
(* Vérification de la bonne utilisation des identifiants dans l'expression *) (* Vérification de la bonne utilisation des identifiants dans l'expression et obtention de l'expression transformée *)
(* et obtention de l'expression transformée *)
let ne = analyse_tds_expression tds e in let ne = analyse_tds_expression tds e in
(* Renvoie du nouvel affichage où l'expression remplacée par l'expression issue de l'analyse *) (* Renvoie du nouvel affichage où l'expression remplacée par l'expression issue de l'analyse *)
Affichage (ne) Affichage (ne)
| AstSyntax.Conditionnelle (c,t,e) -> | AstSyntax.Conditionnelle (c,t,e) ->
(* Analyse de la condition *) (* Analyse de la condition *)
let nc = analyse_tds_expression tds c in let nc = analyse_tds_expression tds c in
(* Analyse du bloc then *) (* Analyse du bloc then *)
let tast = analyse_tds_bloc tds t in let tast = analyse_tds_bloc tds t in
(* Analyse du bloc else *) (* Analyse du bloc else *)
let east = analyse_tds_bloc tds e in let east = analyse_tds_bloc tds e in
(* Renvoie la nouvelle structure de la conditionnelle *) (* Renvoie la nouvelle structure de la conditionnelle *)
Conditionnelle (nc, tast, east) Conditionnelle (nc, tast, east)
| AstSyntax.TantQue (c,b) -> | AstSyntax.TantQue (c,b) ->
(* Analyse de la condition *) (* Analyse de la condition *)
let nc = analyse_tds_expression tds c in let nc = analyse_tds_expression tds c in
(* Analyse du bloc *) (* Analyse du bloc *)
let bast = analyse_tds_bloc tds b in let bast = analyse_tds_bloc tds b in
(* Renvoie la nouvelle structure de la boucle *) (* Renvoie la nouvelle structure de la boucle *)
TantQue (nc, bast) TantQue (nc, bast)
| AstSyntax.Retour (e) -> | AstSyntax.Retour (e) ->
(* Analyse de l'expression *) (* Analyse de l'expression *)
let ne = analyse_tds_expression tds e in let ne = analyse_tds_expression tds e in
Retour (ne) Retour (ne)
| AstSyntax.LocalTypeDef(td) -> | AstSyntax.LocalTypeDef(td) ->
(* Analyse du typedef *)
analyse_tds_typedef tds td analyse_tds_typedef tds td
@ -309,9 +401,6 @@ let analyse_tds_fonction maintds (AstSyntax.Fonction(t, str, l_typstr, bloc)) =
| Some _ -> raise (DoubleDeclaration str) | Some _ -> raise (DoubleDeclaration str)
| None -> | None ->
begin begin
(* Info de l'identifiant de la fonction *)
let info = Tds.InfoVar(str, Undefined, 0, "") in
(* Copie de la tds globale dans la tds locale au bloc *) (* Copie de la tds globale dans la tds locale au bloc *)
let tds_bloc = creerTDSFille maintds in let tds_bloc = creerTDSFille maintds in

View file

@ -18,15 +18,14 @@ let rec analyse_type_affectable a =
begin begin
match (analyse_type_affectable a) with match (analyse_type_affectable a) with
| (na, Pointeur t) -> (AstType.Dref(na, t), t) | (na, Pointeur t) -> (AstType.Dref(na, t), t)
| _ -> failwith "jsp koi mettre ici" | _ -> failwith "Internal Error"
end end
| AstTds.Ident(info) -> | AstTds.Ident(info) ->
begin begin
match info_ast_to_info info with match info_ast_to_info info with
| InfoVar(_, t, _, _) -> (AstType.Ident(info), t) | InfoVar(_, t, _, _) -> (AstType.Ident(info), t)
| InfoConst _ -> (AstType.Ident(info), Int) | InfoConst _ -> (AstType.Ident(info), Int)
| InfoFun _ -> failwith "c chelou frr" | _ -> failwith "Internal Error"
| InfoType _ -> failwith "c koi le pb encore"
end end
| AstTds.Attribut(aff, info) -> | AstTds.Attribut(aff, info) ->
begin begin
@ -34,7 +33,7 @@ let rec analyse_type_affectable a =
match info_ast_to_info info with match info_ast_to_info info with
| InfoVar(_, t, _, _) -> | InfoVar(_, t, _, _) ->
(AstType.Attribut(n_aff, info), t) (AstType.Attribut(n_aff, info), t)
| _ -> failwith "heuuuu wtf, c cringe" | _ -> failwith "Internal Error"
end end
@ -55,7 +54,7 @@ let rec analyse_type_expression e =
(AstType.AppelFonction(info, n_l_expr), t) (AstType.AppelFonction(info, n_l_expr), t)
else else
raise (TypesParametresInattendus(l_type_fun, l_type)) raise (TypesParametresInattendus(l_type_fun, l_type))
| _ -> failwith "pas normal" | _ -> failwith "Internal Error"
end end
| AstTds.Unaire(u, expr) -> | AstTds.Unaire(u, expr) ->
@ -105,7 +104,7 @@ let rec analyse_type_expression e =
| InfoVar(_, t, _, _) -> | InfoVar(_, t, _, _) ->
let _ = modifier_type_info (Pointeur(t)) info in let _ = modifier_type_info (Pointeur(t)) info in
(AstType.Adresse(info), Pointeur(t)) (AstType.Adresse(info), Pointeur(t))
| _ -> failwith "FAIII with" | _ -> failwith "Internal Error"
end end
| AstTds.Tuple(l_expr) -> | AstTds.Tuple(l_expr) ->
@ -135,8 +134,8 @@ let rec analyse_type_instruction opt i =
| Dref a -> | Dref a ->
begin begin
match (analyse_type_affectable a) with match (analyse_type_affectable a) with
| (na, Pointeur t) -> AstType.Affectation(na, ne) | (na, Pointeur _) -> AstType.Affectation(na, ne)
| _ -> failwith "jsp koi mettre ici" | _ -> failwith "Internal Error"
end end
| AstTds.Ident info -> | AstTds.Ident info ->
begin begin
@ -146,7 +145,7 @@ let rec analyse_type_instruction opt i =
AstType.Affectation(AstType.Ident(info), ne) AstType.Affectation(AstType.Ident(info), ne)
else else
raise (TypeInattendu(nt, t)) raise (TypeInattendu(nt, t))
| _ -> failwith "wut" | _ -> failwith "Internal Error"
end end
| AstTds.Attribut(aff2, info) -> | AstTds.Attribut(aff2, info) ->
begin begin
@ -157,7 +156,7 @@ let rec analyse_type_instruction opt i =
AstType.Affectation(Attribut(na, info), ne) AstType.Affectation(Attribut(na, info), ne)
else else
raise (TypeInattendu(nt, t)) raise (TypeInattendu(nt, t))
| _ -> failwith "pas bon du tout" | _ -> failwith "Internal Error"
end end
end end
@ -170,7 +169,7 @@ let rec analyse_type_instruction opt i =
| Bool -> AstType.AffichageBool(ne) | Bool -> AstType.AffichageBool(ne)
| Pointeur _ -> AstType.AffichagePointeur(ne) | Pointeur _ -> AstType.AffichagePointeur(ne)
| Struct _ -> AstType.AffichageStruct(ne, nt) | Struct _ -> AstType.AffichageStruct(ne, nt)
| _ -> failwith "un truc chelou" | _ -> failwith "Internal Error"
end end
| AstTds.Conditionnelle (e, b1, b2) -> | AstTds.Conditionnelle (e, b1, b2) ->
@ -203,7 +202,7 @@ let rec analyse_type_instruction opt i =
AstType.Retour(ne) AstType.Retour(ne)
else else
raise (TypeInattendu(nt, t)) raise (TypeInattendu(nt, t))
| None -> failwith "Pas de return dans le main" | None -> failwith "Internal Error"
end end
| AstTds.Empty -> AstType.Empty | AstTds.Empty -> AstType.Empty
@ -244,7 +243,7 @@ let analyse_type_fonction opt (AstTds.Fonction(t, info, l_typinfo, bloc)) =
end end
else else
raise (TypeInattendu(t, t_ret)) raise (TypeInattendu(t, t_ret))
| None -> failwith "Il faut un return dans une fonction" | None -> failwith "Internal Error"
(* analyser : AstTds.ast -> AstType.ast *) (* analyser : AstTds.ast -> AstType.ast *)

View file

@ -55,6 +55,7 @@ struct
match a with match a with
| AstSyntax.Dref(n) -> (string_of_affectable n) | AstSyntax.Dref(n) -> (string_of_affectable n)
| AstSyntax.Ident(n) -> n ^ " " | AstSyntax.Ident(n) -> n ^ " "
| _ -> ""
(* Conversion des expressions *) (* Conversion des expressions *)
let rec string_of_expression e = let rec string_of_expression e =
@ -69,6 +70,7 @@ struct
| Fraction -> "["^(string_of_expression e1)^"/"^(string_of_expression e2)^"] " | Fraction -> "["^(string_of_expression e1)^"/"^(string_of_expression e2)^"] "
| _ -> (string_of_expression e1)^(string_of_binaire b)^(string_of_expression e2)^" " | _ -> (string_of_expression e1)^(string_of_binaire b)^(string_of_expression e2)^" "
end end
|_ -> ""
let string_of_typedef (TypeDef(n, t)) = n ^ "->" ^ (string_of_type t) ^ "\n" let string_of_typedef (TypeDef(n, t)) = n ^ "->" ^ (string_of_type t) ^ "\n"