[flang-commits] [PATCH] D129680: [flang] Error detection/avoidance for TRANSFER with empty MOLD= type
Peter Klausler via Phabricator via flang-commits
flang-commits at lists.llvm.org
Wed Jul 13 16:51:09 PDT 2022
This revision was automatically updated to reflect the committed changes.
Closed by commit rGbe68a6adfba2: [flang] Error detection/avoidance for TRANSFER with empty MOLD= type (authored by klausler).
Repository:
rG LLVM Github Monorepo
CHANGES SINCE LAST ACTION
https://reviews.llvm.org/D129680/new/
https://reviews.llvm.org/D129680
Files:
flang/lib/Evaluate/shape.cpp
flang/runtime/misc-intrinsic.cpp
Index: flang/runtime/misc-intrinsic.cpp
===================================================================
--- flang/runtime/misc-intrinsic.cpp
+++ flang/runtime/misc-intrinsic.cpp
@@ -55,16 +55,23 @@
void RTNAME(Transfer)(Descriptor &result, const Descriptor &source,
const Descriptor &mold, const char *sourceFile, int line) {
+ std::optional<std::int64_t> elements;
if (mold.rank() > 0) {
- std::size_t moldElementBytes{mold.ElementBytes()};
- std::size_t elements{
- (source.Elements() * source.ElementBytes() + moldElementBytes - 1) /
- moldElementBytes};
- return TransferImpl(result, source, mold, sourceFile, line,
- static_cast<std::int64_t>(elements));
- } else {
- return TransferImpl(result, source, mold, sourceFile, line, {});
+ if (std::size_t sourceElementBytes{
+ source.Elements() * source.ElementBytes()}) {
+ if (std::size_t moldElementBytes{mold.ElementBytes()}) {
+ elements = static_cast<std::int64_t>(
+ (sourceElementBytes + moldElementBytes - 1) / moldElementBytes);
+ } else {
+ Terminator{sourceFile, line}.Crash("TRANSFER: zero-sized type of MOLD= "
+ "when SOURCE= is not zero-sized");
+ }
+ } else {
+ elements = 0;
+ }
}
+ return TransferImpl(
+ result, source, mold, sourceFile, line, std::move(elements));
}
void RTNAME(TransferSize)(Descriptor &result, const Descriptor &source,
Index: flang/lib/Evaluate/shape.cpp
===================================================================
--- flang/lib/Evaluate/shape.cpp
+++ flang/lib/Evaluate/shape.cpp
@@ -931,19 +931,34 @@
} else {
// SIZE= is absent and MOLD= is array: result is vector whose
// length is determined by sizes of types. See 16.9.193p4 case(ii).
+ // Note that if sourceBytes is not known to be empty, we
+ // can fold only when moldElementBytes is known to not be zero;
+ // the most general case risks a division by zero otherwise.
if (auto sourceTypeAndShape{
characteristics::TypeAndShape::Characterize(
call.arguments().at(0), *context_)}) {
- auto sourceBytes{
- sourceTypeAndShape->MeasureSizeInBytes(*context_)};
- auto moldElementBytes{
- moldTypeAndShape->MeasureElementSizeInBytes(*context_, true)};
- if (sourceBytes && moldElementBytes) {
- ExtentExpr extent{Fold(*context_,
- (std::move(*sourceBytes) +
- common::Clone(*moldElementBytes) - ExtentExpr{1}) /
- common::Clone(*moldElementBytes))};
- return Shape{MaybeExtentExpr{std::move(extent)}};
+ if (auto sourceBytes{
+ sourceTypeAndShape->MeasureSizeInBytes(*context_)}) {
+ *sourceBytes = Fold(*context_, std::move(*sourceBytes));
+ if (auto sourceBytesConst{ToInt64(*sourceBytes)}) {
+ if (*sourceBytesConst == 0) {
+ return Shape{ExtentExpr{0}};
+ }
+ }
+ if (auto moldElementBytes{
+ moldTypeAndShape->MeasureElementSizeInBytes(
+ *context_, true)}) {
+ *moldElementBytes =
+ Fold(*context_, std::move(*moldElementBytes));
+ auto moldElementBytesConst{ToInt64(*moldElementBytes)};
+ if (moldElementBytesConst && *moldElementBytesConst != 0) {
+ ExtentExpr extent{Fold(*context_,
+ (std::move(*sourceBytes) +
+ common::Clone(*moldElementBytes) - ExtentExpr{1}) /
+ common::Clone(*moldElementBytes))};
+ return Shape{MaybeExtentExpr{std::move(extent)}};
+ }
+ }
}
}
}
-------------- next part --------------
A non-text attachment was scrubbed...
Name: D129680.444458.patch
Type: text/x-patch
Size: 4057 bytes
Desc: not available
URL: <http://lists.llvm.org/pipermail/flang-commits/attachments/20220713/68036061/attachment.bin>
More information about the flang-commits
mailing list