@@ -3326,29 +3326,116 @@ class CommonVisitor : public AST::BaseVisitor<Struct> {
33263326 x.base .base .loc );
33273327 }
33283328 }
3329- LCOMPILERS_ASSERT (
3330- ASRUtils::check_equal_type (ASRUtils::expr_type (lhs), ASRUtils::expr_type (rhs)));
3329+ ASR::ttype_t *left_operand_type = ASRUtils::expr_type (lhs);
3330+ ASR::ttype_t *right_operand_type = ASRUtils::expr_type (rhs);
3331+
33313332 ASR::expr_t *value = nullptr ;
3332- ASR::ttype_t *dest_type = ASRUtils::expr_type (lhs) ;
3333+ ASR::ttype_t *dest_type = left_operand_type ;
33333334
3335+ if (!ASRUtils::check_equal_type (left_operand_type, right_operand_type)) {
3336+ throw SemanticError (" Type mismatch: '" + ASRUtils::type_to_str_python (left_operand_type)
3337+ + " ' and '" + ASRUtils::type_to_str_python (right_operand_type)
3338+ + " '. Both operands must be of the same type." , x.base .base .loc );
3339+ }
3340+ // Reference: https://docs.python.org/3/reference/expressions.html#boolean-operations
33343341 if (ASRUtils::expr_value (lhs) != nullptr && ASRUtils::expr_value (rhs) != nullptr ) {
3335-
3336- LCOMPILERS_ASSERT (ASR::is_a<ASR::Logical_t>(*dest_type));
3337- bool left_value = ASR::down_cast<ASR::LogicalConstant_t>(
3338- ASRUtils::expr_value (lhs))->m_value ;
3339- bool right_value = ASR::down_cast<ASR::LogicalConstant_t>(
3340- ASRUtils::expr_value (rhs))->m_value ;
3341- bool result;
3342- switch (op) {
3343- case (ASR::logicalbinopType::And): { result = left_value && right_value; break ; }
3344- case (ASR::logicalbinopType::Or): { result = left_value || right_value; break ; }
3345- default : {
3346- throw SemanticError (" Boolean operator type not supported" ,
3347- x.base .base .loc );
3342+ switch (dest_type->type ) {
3343+ case ASR::ttypeType::Logical: {
3344+ bool left_value = ASR::down_cast<ASR::LogicalConstant_t>(
3345+ ASRUtils::expr_value (lhs))->m_value ;
3346+ bool right_value = ASR::down_cast<ASR::LogicalConstant_t>(
3347+ ASRUtils::expr_value (rhs))->m_value ;
3348+ bool result;
3349+ switch (op) {
3350+ case (ASR::logicalbinopType::And): { result = left_value && right_value; break ; }
3351+ case (ASR::logicalbinopType::Or): { result = left_value || right_value; break ; }
3352+ default : {
3353+ throw SemanticError (" Boolean operator type not supported" ,
3354+ x.base .base .loc );
3355+ }
3356+ }
3357+ value = ASRUtils::EXPR (ASR::make_LogicalConstant_t (
3358+ al, x.base .base .loc , result, dest_type));
3359+ break ;
3360+ }
3361+ case ASR::ttypeType::Integer: {
3362+ int64_t left_value = ASR::down_cast<ASR::IntegerConstant_t>(
3363+ ASRUtils::expr_value (lhs))->m_n ;
3364+ int64_t right_value = ASR::down_cast<ASR::IntegerConstant_t>(
3365+ ASRUtils::expr_value (rhs))->m_n ;
3366+ int64_t result;
3367+ switch (op) {
3368+ case (ASR::logicalbinopType::And): {
3369+ result = left_value == 0 ? left_value : right_value;
3370+ break ;
3371+ }
3372+ case (ASR::logicalbinopType::Or): {
3373+ result = left_value != 0 ? left_value : right_value;
3374+ break ;
3375+ }
3376+ default : {
3377+ throw SemanticError (" Boolean operator type not supported" ,
3378+ x.base .base .loc );
3379+ }
3380+ }
3381+ value = ASRUtils::EXPR (ASR::make_IntegerConstant_t (
3382+ al, x.base .base .loc , result, dest_type));
3383+ break ;
3384+ }
3385+ case ASR::ttypeType::Real: {
3386+ double left_value = ASR::down_cast<ASR::RealConstant_t>(
3387+ ASRUtils::expr_value (lhs))->m_r ;
3388+ double right_value = ASR::down_cast<ASR::RealConstant_t>(
3389+ ASRUtils::expr_value (rhs))->m_r ;
3390+ double result;
3391+ switch (op) {
3392+ case (ASR::logicalbinopType::And): {
3393+ result = left_value == 0 ? left_value : right_value;
3394+ break ;
3395+ }
3396+ case (ASR::logicalbinopType::Or): {
3397+ result = left_value != 0 ? left_value : right_value;
3398+ break ;
3399+ }
3400+ default : {
3401+ throw SemanticError (" Boolean operator type not supported" ,
3402+ x.base .base .loc );
3403+ }
3404+ }
3405+ value = ASRUtils::EXPR (ASR::make_RealConstant_t (
3406+ al, x.base .base .loc , result, dest_type));
3407+ break ;
33483408 }
3409+ case ASR::ttypeType::Character: {
3410+ char * left_value = ASR::down_cast<ASR::StringConstant_t>(
3411+ ASRUtils::expr_value (lhs))->m_s ;
3412+ char * right_value = ASR::down_cast<ASR::StringConstant_t>(
3413+ ASRUtils::expr_value (rhs))->m_s ;
3414+ char * result;
3415+ switch (op) {
3416+ case (ASR::logicalbinopType::And): {
3417+ result = std::strcmp (left_value, " " ) == 0 ? left_value : right_value;
3418+ break ;
3419+ }
3420+ case (ASR::logicalbinopType::Or): {
3421+ result = std::strcmp (left_value, " " ) != 0 ? left_value : right_value;
3422+ break ;
3423+ }
3424+ default : {
3425+ throw SemanticError (" Boolean operator type not supported" ,
3426+ x.base .base .loc );
3427+ }
3428+ }
3429+ value = ASRUtils::EXPR (ASR::make_StringConstant_t (
3430+ al, x.base .base .loc , result, dest_type));
3431+ break ;
3432+ }
3433+
3434+ default :
3435+ throw SemanticError (" Boolean operation not supported on objects of type '"
3436+ + ASRUtils::type_to_str_python (dest_type) + " '" ,
3437+ x.base .base .loc );
33493438 }
3350- value = ASR::down_cast<ASR::expr_t >(ASR::make_LogicalConstant_t (
3351- al, x.base .base .loc , result, dest_type));
33523439 }
33533440 tmp = ASR::make_LogicalBinOp_t (al, x.base .base .loc , lhs, op, rhs, dest_type, value);
33543441 }
@@ -7586,7 +7673,6 @@ we will have to use something else.
75867673 }
75877674 Vec<ASR::expr_t *> args_; args_.reserve (al, x.n_args );
75887675 visit_expr_list (x.m_args , x.n_args , args_);
7589-
75907676 if (x.n_args > 0 && ASRUtils::is_array (ASRUtils::expr_type (args_[0 ])) &&
75917677 imported_functions[call_name] == " math" ) {
75927678 throw SemanticError (" Function '" + call_name + " ' does not accept vector values" ,
0 commit comments