diff options
author | Tristan Gingold <tgingold@free.fr> | 2020-07-02 18:23:01 +0200 |
---|---|---|
committer | Tristan Gingold <tgingold@free.fr> | 2020-07-02 18:23:05 +0200 |
commit | 0948af90416fe146923b8d1e89c7a86bb17efe66 (patch) | |
tree | fe7bbc302ceda63f79b6b663687cf550fb9fff26 /src/vhdl/vhdl-sem_expr.adb | |
parent | c75cc353c3dd24097f29aaaacb96ae4a9598b642 (diff) | |
download | ghdl-0948af90416fe146923b8d1e89c7a86bb17efe66.tar.gz ghdl-0948af90416fe146923b8d1e89c7a86bb17efe66.tar.bz2 ghdl-0948af90416fe146923b8d1e89c7a86bb17efe66.zip |
vhdl-sem_expr: fix overload handling for conditional operation
Diffstat (limited to 'src/vhdl/vhdl-sem_expr.adb')
-rw-r--r-- | src/vhdl/vhdl-sem_expr.adb | 56 |
1 files changed, 44 insertions, 12 deletions
diff --git a/src/vhdl/vhdl-sem_expr.adb b/src/vhdl/vhdl-sem_expr.adb index d38be0c7b..753a64429 100644 --- a/src/vhdl/vhdl-sem_expr.adb +++ b/src/vhdl/vhdl-sem_expr.adb @@ -2005,33 +2005,66 @@ package body Vhdl.Sem_Expr is function Sem_Operator_Pass2_Interpretation (Expr : Iir; Res_Type : Iir) return Iir is + Is_Dyadic : constant Boolean := + Get_Kind (Expr) in Iir_Kinds_Dyadic_Operator; Decl : Iir; Overload : Iir; Overload_List : Iir_List; Full_Compat : Iir; + Conv_Compat : Iir; It : List_Iterator; + Level : Compatibility_Level; begin -- Second pass -- Find the uniq implementation for this call. Overload := Get_Implementation (Expr); Overload_List := Get_Overload_List (Overload); + Full_Compat := Null_Iir; + Conv_Compat := Null_Iir; + It := List_Iterate (Overload_List); while Is_Valid (It) loop Decl := Get_Element (It); - -- FIXME: wrong: compatibilty with return type and args. - if Are_Types_Compatible (Get_Return_Type (Decl), Res_Type) - /= Not_Compatible - then - if Full_Compat /= Null_Iir then - Error_Operator_Overload (Expr, Overload_List); - return Null_Iir; - else - Full_Compat := Decl; - end if; - end if; + Level := Sem_Operator_Compatibility (Decl, Expr, Is_Dyadic, Res_Type); + case Level is + when Not_Compatible => + -- Ignored + null; + when Fully_Compatible => + if Full_Compat = Null_Iir then + Full_Compat := Decl; + else + -- There are several fully compatible functions. + -- TODO: remove non-fully compatible functions from the list + -- before displaying the list. + Error_Operator_Overload (Expr, Overload_List); + return Null_Iir; + end if; + when Via_Conversion => + if Conv_Compat = Null_Iir then + Conv_Compat := Decl; + else + -- Not yet an error, as there can be one fully compatible + -- function. + Conv_Compat := Overload; + end if; + end case; Next (It); end loop; + + if Full_Compat = Null_Iir then + if Conv_Compat = Overload then + -- Several results through implicit conversion. + -- TODO: remove incompatible declarations from the list before + -- displaying it. + Error_Operator_Overload (Expr, Overload_List); + return Null_Iir; + else + Full_Compat := Conv_Compat; + end if; + end if; + Free_Iir (Overload); Overload := Get_Type (Expr); Free_Overload_List (Overload); @@ -2041,7 +2074,6 @@ package body Vhdl.Sem_Expr is "no matching function declarations for %n", +Expr); return Null_Iir; else - Destroy_Iir_List (Overload_List); return Full_Compat; end if; end Sem_Operator_Pass2_Interpretation; |