From b2a404766c47eaa3bd2aeb526e45ffcb77578026 Mon Sep 17 00:00:00 2001 From: =?UTF-8?q?Lu=C3=ADs=20Ferreira?= Date: Mon, 20 Mar 2023 15:42:29 +0000 Subject: [PATCH 1/2] fix(stdio): allow usage of file writer on shared non-blocking file descriptors MIME-Version: 1.0 Content-Type: text/plain; charset=UTF-8 Content-Transfer-Encoding: 8bit Signed-off-by: Luís Ferreira --- std/stdio.d | 44 ++++++++++++++++++++++++++++---------------- 1 file changed, 28 insertions(+), 16 deletions(-) diff --git a/std/stdio.d b/std/stdio.d index 92e4906b4f4..4f89c135c4c 100644 --- a/std/stdio.d +++ b/std/stdio.d @@ -1267,12 +1267,7 @@ Throws: `ErrnoException` if the file is not opened or if the call to `fwrite` fa } } - auto result = trustedFwrite(_p.handle, buffer); - if (result == result.max) result = 0; - errnoEnforce(result == buffer.length, - text("Wrote ", result, " instead of ", buffer.length, - " objects of type ", T.stringof, " to file `", - _name, "'")); + _rawWrite(_p.handle, buffer, _name); } /// @@ -3168,10 +3163,7 @@ is empty, throws an `Exception`. In case of an I/O error throws { if (orientation_ <= 0) { - //file.write(writeme); causes infinite recursion!!! - //file.rawWrite(writeme); - auto result = trustedFwrite(file_._p.handle, writeme); - if (result != writeme.length) errnoEnforce(0); + _rawWrite(file_._p.handle, writeme, file_._name); return; } } @@ -3406,12 +3398,7 @@ is empty, throws an `Exception`. In case of an I/O error throws import std.conv : text; import std.exception : errnoEnforce; - auto result = trustedFwrite(file_._p.handle, buffer); - if (result == result.max) result = 0; - errnoEnforce(result == buffer.length, - text("Wrote ", result, " instead of ", buffer.length, - " objects of type ", T.stringof, " to file `", - name, "'")); + _rawWrite(file_._p.handle, buffer, file_._name); } version (Windows) @@ -4680,6 +4667,31 @@ if ((isSomeFiniteCharInputRange!R1 || isSomeString!R1) && return _fopenImpl(namez, modez); } +@trusted +private void _rawWrite(T)(FILE* handle, in T[] buffer, string name = null) +{ + import std.conv : text; + import std.exception : errnoEnforce; + + size_t result; + do + { + .clearerr(handle); + result += trustedFwrite(handle, buffer[result .. $]); + + import core.stdc.errno : errno, EAGAIN; + if (.ferror(handle) && errno != EAGAIN) + break; + } + while(result < buffer.length); + + if (result == result.max) result = 0; + errnoEnforce(result == buffer.length, + text("Wrote ", result, " instead of ", buffer.length, + " objects of type ", T.stringof, " to file `", + name, "'")); +} + version (Posix) { /*********************************** From f559fa301c7642390d9c9fd96134bc5226335836 Mon Sep 17 00:00:00 2001 From: Adam Wilson Date: Sun, 27 Oct 2024 00:11:22 -0700 Subject: [PATCH 2/2] Update std/stdio.d Co-authored-by: Paul Backus --- std/stdio.d | 2 +- 1 file changed, 1 insertion(+), 1 deletion(-) diff --git a/std/stdio.d b/std/stdio.d index 4f89c135c4c..deef4f34bb4 100644 --- a/std/stdio.d +++ b/std/stdio.d @@ -4683,7 +4683,7 @@ private void _rawWrite(T)(FILE* handle, in T[] buffer, string name = null) if (.ferror(handle) && errno != EAGAIN) break; } - while(result < buffer.length); + while (result < buffer.length); if (result == result.max) result = 0; errnoEnforce(result == buffer.length,