summaryrefslogtreecommitdiff
path: root/flang-rt
diff options
context:
space:
mode:
Diffstat (limited to 'flang-rt')
-rw-r--r--flang-rt/include/flang-rt/runtime/format-implementation.h4
-rw-r--r--flang-rt/include/flang-rt/runtime/format.h3
-rw-r--r--flang-rt/include/flang-rt/runtime/io-stmt.h10
-rw-r--r--flang-rt/lib/runtime/descriptor-io.cpp7
-rw-r--r--flang-rt/unittests/Runtime/Format.cpp2
5 files changed, 16 insertions, 10 deletions
diff --git a/flang-rt/include/flang-rt/runtime/format-implementation.h b/flang-rt/include/flang-rt/runtime/format-implementation.h
index de06524de32d..46134146f5c1 100644
--- a/flang-rt/include/flang-rt/runtime/format-implementation.h
+++ b/flang-rt/include/flang-rt/runtime/format-implementation.h
@@ -532,7 +532,7 @@ RT_API_ATTRS common::optional<DataEdit> FormatControl<CONTEXT>::GetNextDataEdit(
ReportBadFormat(context, "Excessive DT'iotype' in FORMAT", start);
return common::nullopt;
}
- edit.ioType[edit.ioTypeChars++] = ch;
+ context.ioType[edit.ioTypeChars++] = ch;
if (ch == quote) {
++offset_;
}
@@ -556,7 +556,7 @@ RT_API_ATTRS common::optional<DataEdit> FormatControl<CONTEXT>::GetNextDataEdit(
ReportBadFormat(context, "Excessive DT(v_list) in FORMAT", start);
return common::nullopt;
}
- edit.vList[edit.vListEntries++] = n;
+ context.vList[edit.vListEntries++] = n;
auto ch{static_cast<char>(GetNextChar(context))};
if (ch != ',') {
ok = ch == ')';
diff --git a/flang-rt/include/flang-rt/runtime/format.h b/flang-rt/include/flang-rt/runtime/format.h
index 34e33edae546..79a7dd713b1a 100644
--- a/flang-rt/include/flang-rt/runtime/format.h
+++ b/flang-rt/include/flang-rt/runtime/format.h
@@ -86,12 +86,11 @@ struct DataEdit {
// defined I/O data edit descriptor
RT_OFFLOAD_VAR_GROUP_BEGIN
static constexpr std::size_t maxIoTypeChars{32};
- static constexpr std::size_t maxVListEntries{4};
+ static constexpr std::size_t maxVListEntries{16};
RT_OFFLOAD_VAR_GROUP_END
std::uint8_t ioTypeChars{0};
std::uint8_t vListEntries{0};
char ioType[maxIoTypeChars];
- int vList[maxVListEntries];
};
// Generates a sequence of DataEdits from a FORMAT statement or
diff --git a/flang-rt/include/flang-rt/runtime/io-stmt.h b/flang-rt/include/flang-rt/runtime/io-stmt.h
index 1cb72d87d3df..3de2309954a4 100644
--- a/flang-rt/include/flang-rt/runtime/io-stmt.h
+++ b/flang-rt/include/flang-rt/runtime/io-stmt.h
@@ -61,8 +61,14 @@ using IoDirectionState = std::conditional_t<D == Direction::Input,
InputStatementState, OutputStatementState>;
// Common state for all kinds of formatted I/O
-template <Direction D> class FormattedIoStatementState {};
-template <> class FormattedIoStatementState<Direction::Input> {
+struct DefinedIoArgs {
+ char ioType[DataEdit::maxIoTypeChars]; // IOTYPE string
+ int vList[DataEdit::maxVListEntries]; // V_LIST(:) values
+};
+template <Direction D>
+class FormattedIoStatementState : public DefinedIoArgs {};
+template <>
+class FormattedIoStatementState<Direction::Input> : public DefinedIoArgs {
public:
RT_API_ATTRS std::size_t GetEditDescriptorChars() const;
RT_API_ATTRS void GotChar(int);
diff --git a/flang-rt/lib/runtime/descriptor-io.cpp b/flang-rt/lib/runtime/descriptor-io.cpp
index 42ac4c051663..e599e624fe02 100644
--- a/flang-rt/lib/runtime/descriptor-io.cpp
+++ b/flang-rt/lib/runtime/descriptor-io.cpp
@@ -64,10 +64,11 @@ static RT_API_ATTRS common::optional<bool> DefinedFormattedIo(
: *io.GetNextDataEdit(1)};
char ioType[2 + edit.maxIoTypeChars];
auto ioTypeLen{std::size_t{2} /*"DT"*/ + edit.ioTypeChars};
+ auto &definedIoArgs{*io.get_if<DefinedIoArgs>()};
if (edit.descriptor == DataEdit::DefinedDerivedType) {
ioType[0] = 'D';
ioType[1] = 'T';
- runtime::memcpy(ioType + 2, edit.ioType, edit.ioTypeChars);
+ runtime::memcpy(ioType + 2, definedIoArgs.ioType, edit.ioTypeChars);
} else {
runtime::strcpy(
ioType, io.mutableModes().inNamelist ? "NAMELIST" : "LISTDIRECTED");
@@ -81,7 +82,7 @@ static RT_API_ATTRS common::optional<bool> DefinedFormattedIo(
if (integer8) {
// Convert v_list values to INTEGER(8)
for (int j{0}; j < edit.vListEntries; ++j) {
- vList64[j] = edit.vList[j];
+ vList64[j] = definedIoArgs.vList[j];
}
vListDesc.Establish(
TypeCategory::Integer, sizeof(std::int64_t), nullptr, 1);
@@ -91,7 +92,7 @@ static RT_API_ATTRS common::optional<bool> DefinedFormattedIo(
static_cast<SubscriptValue>(sizeof(std::int64_t)));
} else {
vListDesc.Establish(TypeCategory::Integer, sizeof(int), nullptr, 1);
- vListDesc.set_base_addr(edit.vList);
+ vListDesc.set_base_addr(definedIoArgs.vList);
vListDesc.GetDimension(0).SetBounds(1, edit.vListEntries);
vListDesc.GetDimension(0).SetByteStride(
static_cast<SubscriptValue>(sizeof(int)));
diff --git a/flang-rt/unittests/Runtime/Format.cpp b/flang-rt/unittests/Runtime/Format.cpp
index fe7403f26700..cd52dc8c54ed 100644
--- a/flang-rt/unittests/Runtime/Format.cpp
+++ b/flang-rt/unittests/Runtime/Format.cpp
@@ -22,7 +22,7 @@ using namespace std::literals::string_literals;
using ResultsTy = std::vector<std::string>;
// A test harness context for testing FormatControl
-class TestFormatContext : public IoErrorHandler {
+class TestFormatContext : public IoErrorHandler, public DefinedIoArgs {
public:
using CharType = char;
TestFormatContext() : IoErrorHandler{"format.cpp", 1} {}