[flang] Better error handling for PDT constant expression (#130637)
We currently don't consider an integer division to be a constant expression unless its divisor is known and nonzero. This produces a weird result in the linked test; do better. Fixes https://github.com/llvm/llvm-project/issues/130534.
This commit is contained in:
parent
af62a6f59a
commit
016557fab2
4 changed files with 25 additions and 6 deletions
|
|
@ -69,13 +69,14 @@ public:
|
|||
bool operator()(const Component &component) const {
|
||||
return (*this)(component.base());
|
||||
}
|
||||
// Forbid integer division by zero in constants.
|
||||
// Prevent integer division by known zeroes in constant expressions.
|
||||
template <int KIND>
|
||||
bool operator()(
|
||||
const Divide<Type<TypeCategory::Integer, KIND>> &division) const {
|
||||
using T = Type<TypeCategory::Integer, KIND>;
|
||||
if (const auto divisor{GetScalarConstantValue<T>(division.right())}) {
|
||||
return !divisor->IsZero() && (*this)(division.left());
|
||||
if ((*this)(division.left()) && (*this)(division.right())) {
|
||||
const auto divisor{GetScalarConstantValue<T>(division.right())};
|
||||
return !divisor || !divisor->IsZero();
|
||||
} else {
|
||||
return false;
|
||||
}
|
||||
|
|
|
|||
|
|
@ -567,11 +567,18 @@ const DeclTypeSpec &InstantiateHelper::InstantiateIntrinsicType(
|
|||
kind = *value;
|
||||
} else {
|
||||
foldingContext().messages().Say(symbolName,
|
||||
"KIND parameter value (%jd) of intrinsic type %s "
|
||||
"did not resolve to a supported value"_err_en_US,
|
||||
"KIND parameter value (%jd) of intrinsic type %s did not resolve to a supported value"_err_en_US,
|
||||
*value,
|
||||
parser::ToUpperCaseLetters(EnumToString(intrinsic.category())));
|
||||
}
|
||||
} else {
|
||||
std::string exprString;
|
||||
llvm::raw_string_ostream sstream(exprString);
|
||||
copy.AsFortran(sstream);
|
||||
foldingContext().messages().Say(symbolName,
|
||||
"KIND parameter expression (%s) of intrinsic type %s did not resolve to a constant value"_err_en_US,
|
||||
exprString,
|
||||
parser::ToUpperCaseLetters(EnumToString(intrinsic.category())));
|
||||
}
|
||||
switch (spec.category()) {
|
||||
case DeclTypeSpec::Numeric:
|
||||
|
|
|
|||
11
flang/test/Semantics/pdt04.f90
Normal file
11
flang/test/Semantics/pdt04.f90
Normal file
|
|
@ -0,0 +1,11 @@
|
|||
!RUN: not %flang_fc1 %s 2>&1 | FileCheck %s
|
||||
!CHECK: error: KIND parameter expression (int(1_4/0_4,kind=8)) of intrinsic type CHARACTER did not resolve to a constant value
|
||||
!CHECK: in the context: instantiation of parameterized derived type 'ty(j=1_4,k=0_4)'
|
||||
!CHECK: warning: INTEGER(4) division by zero
|
||||
program main
|
||||
type ty(j,k)
|
||||
integer, kind :: j, k
|
||||
character(kind=j/k) a
|
||||
end type
|
||||
type(ty(1,0)) x
|
||||
end
|
||||
|
|
@ -1,9 +1,9 @@
|
|||
! RUN: %python %S/test_errors.py %s %flang_fc1
|
||||
! Test instantiation of components that are procedure pointers.
|
||||
!
|
||||
program test
|
||||
type dtype(kindParam)
|
||||
integer, kind :: kindParam = 4
|
||||
!ERROR: KIND parameter expression (kindparam) of intrinsic type REAL did not resolve to a constant value
|
||||
!ERROR: KIND parameter value (66) of intrinsic type REAL did not resolve to a supported value
|
||||
!ERROR: KIND parameter value (55) of intrinsic type REAL did not resolve to a supported value
|
||||
procedure (real(kindParam)), pointer, nopass :: field => null()
|
||||
|
|
|
|||
Loading…
Reference in a new issue