[flang-commits] [flang] b232a88 - [flang] runtime: fix WRITE after BACKSPACE on variable-length file

peter klausler via flang-commits flang-commits at lists.llvm.org
Tue Aug 24 09:38:59 PDT 2021


Author: peter klausler
Date: 2021-08-24T09:34:52-07:00
New Revision: b232a88c6fac07a2c4304d156a33664dbbe77a1b

URL: https://github.com/llvm/llvm-project/commit/b232a88c6fac07a2c4304d156a33664dbbe77a1b
DIFF: https://github.com/llvm/llvm-project/commit/b232a88c6fac07a2c4304d156a33664dbbe77a1b.diff

LOG: [flang] runtime: fix WRITE after BACKSPACE on variable-length file

BACKSPACE leaves "recordLength" set, which is fine for a later READ,
but it causes a later WRITE to fail due to a misinterpretation of the
knowledge of the record length as indication of a fixed-length record
file (RECL=).  Fix.

Differential Revision: https://reviews.llvm.org/D108594

Added: 
    

Modified: 
    flang/runtime/unit.cpp

Removed: 
    


################################################################################
diff  --git a/flang/runtime/unit.cpp b/flang/runtime/unit.cpp
index 55304a8f34e08..c08b8b7b5330e 100644
--- a/flang/runtime/unit.cpp
+++ b/flang/runtime/unit.cpp
@@ -258,13 +258,20 @@ bool ExternalFileUnit::Emit(const char *data, std::size_t bytes,
     std::size_t elementBytes, IoErrorHandler &handler) {
   auto furthestAfter{std::max(furthestPositionInRecord,
       positionInRecord + static_cast<std::int64_t>(bytes))};
-  if (furthestAfter > recordLength.value_or(furthestAfter)) {
-    handler.SignalError(IostatRecordWriteOverrun,
-        "Attempt to write %zd bytes to position %jd in a fixed-size record of "
-        "%jd bytes",
-        bytes, static_cast<std::intmax_t>(positionInRecord),
-        static_cast<std::intmax_t>(*recordLength));
-    return false;
+  if (recordLength) {
+    // It is possible for recordLength to have a value now for a
+    // variable-length output record if the previous operation
+    // was a BACKSPACE.
+    if (!isFixedRecordLength) {
+      recordLength.reset();
+    } else if (furthestAfter > *recordLength) {
+      handler.SignalError(IostatRecordWriteOverrun,
+          "Attempt to write %zd bytes to position %jd in a fixed-size record "
+          "of %jd bytes",
+          bytes, static_cast<std::intmax_t>(positionInRecord),
+          static_cast<std::intmax_t>(*recordLength));
+      return false;
+    }
   }
   WriteFrame(frameOffsetInFile_, recordOffsetInFrame_ + furthestAfter, handler);
   if (positionInRecord > furthestPositionInRecord) {


        


More information about the flang-commits mailing list