on master help sign in
be certain to use the same output device as before any stdout redirection
9bad126coreyoconnor
cbits/output_buffer.c+3−3
@@ -3,16 +3,16 @@
3
3
4#include "output_buffer.h"
4#include "output_buffer.h"
5
5
6−void stdout_output_buffer ( uint8_t* buffer, size_t buffer_size )
6+void stdout_output_buffer ( int out_fd, uint8_t* buffer, size_t buffer_size )
7{
7{
8 while ( buffer_size )
8 while ( buffer_size )
9 {
9 {
10− const ssize_t r = write( STDOUT_FILENO, (void*) buffer, buffer_size );
10+ const ssize_t r = write( out_fd, (void*) buffer, buffer_size );
11
11
12 buffer_size -= (size_t) r;
12 buffer_size -= (size_t) r;
13 buffer += (size_t) r;
13 buffer += (size_t) r;
14 }
14 }
15
15
16− fdatasync( STDOUT_FILENO );
16+ fdatasync( out_fd );
17}
17}
18
18
cbits/output_buffer.h+1−1
@@ -2,4 +2,4 @@
2#include <unistd.h>
2#include <unistd.h>
3#include <stdint.h>
3#include <stdint.h>
4
4
5−void stdout_output_buffer ( uint8_t* buffer, size_t buffer_size );
5+void stdout_output_buffer ( int out_fd, uint8_t* buffer, size_t buffer_size );
src/Graphics/Vty/Terminal/TerminfoBased.hs+10−4
@@ -24,10 +24,12 @@ import Data.Maybe ( isJust, isNothing, fromJust )
24import Data.Word
24import Data.Word
25
25
26import Foreign.Ptr
26import Foreign.Ptr
27−import Foreign.C.Types ( CLong, CSize )
27+import Foreign.C.Types ( CLong, CSize, CInt )
28
28
29import qualified System.Console.Terminfo as Terminfo
29import qualified System.Console.Terminfo as Terminfo
30import System.IO
30import System.IO
31+import System.Posix.IO
32+import System.Posix.Types ( Fd(..) )
31
33
32data Term = Term
34data Term = Term
33 { term_info_ID :: String
35 { term_info_ID :: String
@@ -42,6 +44,7 @@ data Term = Term
42 , set_default_attr :: CapExpression
44 , set_default_attr :: CapExpression
43 , clear_screen :: CapExpression
45 , clear_screen :: CapExpression
44 , display_attr_caps :: DisplayAttrCaps
46 , display_attr_caps :: DisplayAttrCaps
47+ , term_fd :: Fd
45 }
48 }
46
49
47data DisplayAttrCaps = DisplayAttrCaps
50data DisplayAttrCaps = DisplayAttrCaps
@@ -90,6 +93,7 @@ terminal_instance in_ID = do
90 case parse_result of
93 case parse_result of
91 Left e -> fail $ show e
94 Left e -> fail $ show e
92 Right cap -> return $ Just cap
95 Right cap -> return $ Just cap
96+ term_fd <- liftIO $ dup stdOutput
93 pure Term
97 pure Term
94 <*> pure in_ID
98 <*> pure in_ID
95 <*> pure ti
99 <*> pure ti
@@ -103,6 +107,7 @@ terminal_instance in_ID = do
103 <*> require_cap "sgr0"
107 <*> require_cap "sgr0"
104 <*> require_cap "clear"
108 <*> require_cap "clear"
105 <*> current_display_attr_caps ti
109 <*> current_display_attr_caps ti
110+ <*> pure term_fd
106
111
107current_display_attr_caps :: ( Applicative m, MonadIO m )
112current_display_attr_caps :: ( Applicative m, MonadIO m )
108 => Terminfo.Terminal
113 => Terminfo.Terminal
@@ -165,16 +170,17 @@ instance Terminal Term where
165 | otherwise -> return $ DisplayRegion (toEnum w) (toEnum h)
170 | otherwise -> return $ DisplayRegion (toEnum w) (toEnum h)
166
171
167 -- Output the byte buffer of the specified size to the terminal device.
172 -- Output the byte buffer of the specified size to the terminal device.
168− output_byte_buffer _t out_ptr out_byte_count = do
173+ output_byte_buffer t out_ptr out_byte_count = do
169 -- flush is required *before* the c_output_byte_buffer call
174 -- flush is required *before* the c_output_byte_buffer call
170 -- otherwise there may still be data in GHC's internal stdout buffer.
175 -- otherwise there may still be data in GHC's internal stdout buffer.
171 hFlush stdout
176 hFlush stdout
177+ let Fd c_fd = term_fd t
172 if out_byte_count /= 0
178 if out_byte_count /= 0
173− then c_output_byte_buffer out_ptr ( toEnum $! fromEnum out_byte_count )
179+ then c_output_byte_buffer c_fd out_ptr ( toEnum $! fromEnum out_byte_count )
174 else return ()
180 else return ()
175
181
176foreign import ccall unsafe "output_buffer.h stdout_output_buffer" c_output_byte_buffer
182foreign import ccall unsafe "output_buffer.h stdout_output_buffer" c_output_byte_buffer
177− :: Ptr Word8 -> CSize -> IO ()
183+ :: CInt -> Ptr Word8 -> CSize -> IO ()
178foreign import ccall "gwinsz.h c_get_window_size" c_get_window_size
184foreign import ccall "gwinsz.h c_get_window_size" c_get_window_size
179 :: IO CLong
185 :: IO CLong
180
186