[commit: ghc] master: Fix: hPutBuf issues unnecessary empty write syscalls for large writes (#13246) (805db96)
git at git.haskell.org
git at git.haskell.org
Sun Feb 12 01:09:19 UTC 2017
Repository : ssh://git@git.haskell.org/ghc
On branch : master
Link : http://ghc.haskell.org/trac/ghc/changeset/805db96544111bd548c9a32488a9c97996cc2b49/ghc
>---------------------------------------------------------------
commit 805db96544111bd548c9a32488a9c97996cc2b49
Author: Niklas Hambüchen <mail at nh2.me>
Date: Sat Feb 11 19:24:30 2017 -0500
Fix: hPutBuf issues unnecessary empty write syscalls for large writes (#13246)
Until now, any `hPutBuf` that wrote `>= the handle buffer size` would
trigger an unnecessary `write("")` system call before the actual write
system call.
This is fixed by making sure that we never flush an empty handle buffer:
Only flush `when (w > 0)`.
Reviewers: simonmar, austin, hvr, bgamari
Reviewed By: bgamari
Subscribers: thomie
Differential Revision: https://phabricator.haskell.org/D3119
>---------------------------------------------------------------
805db96544111bd548c9a32488a9c97996cc2b49
libraries/base/GHC/IO/Handle/Text.hs | 13 ++++++++-----
1 file changed, 8 insertions(+), 5 deletions(-)
diff --git a/libraries/base/GHC/IO/Handle/Text.hs b/libraries/base/GHC/IO/Handle/Text.hs
index 4a5e4cf..c53b429 100644
--- a/libraries/base/GHC/IO/Handle/Text.hs
+++ b/libraries/base/GHC/IO/Handle/Text.hs
@@ -745,11 +745,14 @@ bufWrite h_ at Handle__{..} ptr count can_block =
writeIORef haByteBuffer old_buf{ bufR = w + count }
return count
- -- else, we have to flush
- else do debugIO "hPutBuf: flushing first"
- old_buf' <- Buffered.flushWriteBuffer haDevice old_buf
- -- TODO: we should do a non-blocking flush here
- writeIORef haByteBuffer old_buf'
+ -- else, we have to flush any existing handle buffer data
+ -- and can then write out the data in `ptr` directly.
+ else do -- No point flushing when there's nothing in the buffer.
+ when (w > 0) $ do
+ debugIO "hPutBuf: flushing first"
+ flushed_buf <- Buffered.flushWriteBuffer haDevice old_buf
+ -- TODO: we should do a non-blocking flush here
+ writeIORef haByteBuffer flushed_buf
-- if we can fit in the buffer, then just loop
if count < size
then bufWrite h_ ptr count can_block
More information about the ghc-commits
mailing list