diff --git a/flang/lib/Evaluate/fold-complex.cpp b/flang/lib/Evaluate/fold-complex.cpp --- a/flang/lib/Evaluate/fold-complex.cpp +++ b/flang/lib/Evaluate/fold-complex.cpp @@ -34,25 +34,23 @@ return FoldElementalIntrinsic( context, std::move(funcRef), &Scalar::CONJG); } else if (name == "cmplx") { - using Part = typename T::Part; - if (args.size() == 2) { // CMPLX(X, [KIND]) + if (args.size() > 0 && args[0].has_value()) { if (auto *x{UnwrapExpr>(args[0])}) { + // CMPLX(X [, KIND]) with complex X return Fold(context, ConvertToType(std::move(*x))); + } else { + // CMPLX(X [, Y [, KIND]]) with non-complex X + using Part = typename T::Part; + Expr re{std::move(*args[0].value().UnwrapExpr())}; + Expr im{args.size() >= 2 && args[1].has_value() + ? std::move(*args[1]->UnwrapExpr()) + : AsGenericExpr(Constant{Scalar{}})}; + return Fold(context, + Expr{ + ComplexConstructor{ToReal(context, std::move(re)), + ToReal(context, std::move(im))}}); } - Expr re{std::move(*args[0].value().UnwrapExpr())}; - Expr im{AsGenericExpr(Constant{Scalar{}})}; - return Fold(context, - Expr{ComplexConstructor{ToReal(context, std::move(re)), - ToReal(context, std::move(im))}}); } - // CMPLX(X, [Y, KIND]) - CHECK(args.size() == 3); - Expr re{std::move(*args[0].value().UnwrapExpr())}; - Expr im{args[1] ? std::move(*args[1].value().UnwrapExpr()) - : AsGenericExpr(Constant{Scalar{}})}; - return Fold(context, - Expr{ComplexConstructor{ToReal(context, std::move(re)), - ToReal(context, std::move(im))}}); } else if (name == "merge") { return FoldMerge(context, std::move(funcRef)); }