@@ -145,7 +145,69 @@ function setupKillAndExit() {
145
145
process . _exiting = true ;
146
146
process . emit ( 'exit' , process . exitCode || 0 ) ;
147
147
}
148
+
149
+ // Flush stdio streams prior to exit.
150
+ // `flushSync` not present if stream redirected to file in shell.
151
+ flushSync ( process . stdout ) ;
152
+ flushSync ( process . stderr ) ;
153
+
148
154
process . reallyExit ( process . exitCode || 0 ) ;
155
+
156
+ function flushSync ( stream ) {
157
+
158
+ // Behavior of this function outside of process.exit() is undefined
159
+ // due to the following factors:
160
+ // * Stream fd may be blocking after this call.
161
+ // * In the event of an incomplete flush pending buffered write
162
+ // requests may be truncated.
163
+ // * No return code.
164
+
165
+ if ( stream . _writev )
166
+ return ;
167
+
168
+ var handle = stream . _handle ;
169
+ if ( ! handle || ! handle . flushSync )
170
+ return ;
171
+
172
+ var fd = handle . fd ;
173
+ if ( typeof fd !== 'number' || fd < 0 )
174
+ return ;
175
+
176
+ // FIXME: late module resolution avoids cross require problem
177
+ const fs = require ( 'fs' ) ;
178
+
179
+ const Buffer = require ( 'buffer' ) ;
180
+
181
+ // Queued libuv writes must be flushed first.
182
+ // Note: fd will set to blocking after handle.flushSync()
183
+ if ( handle . flushSync ( ) !== 0 ) {
184
+ // bad fd or write queue for libuv stream not entirely flushed
185
+ return ;
186
+ }
187
+
188
+ // then the queued stream chunks can be flushed
189
+ var state = stream . _writableState ;
190
+ var entry = state . bufferedRequest ;
191
+ while ( entry ) {
192
+ var chunk = entry . chunk ;
193
+ if ( ! ( chunk instanceof Buffer ) ) {
194
+ chunk = Buffer . from ( chunk , entry . encoding ) ;
195
+ }
196
+ // Note: fd is blocking at this point
197
+ var written = fs . writeSync ( fd , chunk , 0 , chunk . length ) ;
198
+ if ( written !== chunk . length ) {
199
+ // stream chunk not flushed entirely - stop writing.
200
+ // FIXME: buffered request queue should be repaired here
201
+ // rather than being truncated after loop break
202
+ break ;
203
+ }
204
+ entry = entry . next ;
205
+ }
206
+
207
+ state . bufferedRequestCount = 0 ;
208
+ state . bufferedRequest = null ;
209
+ state . lastBufferedRequest = null ;
210
+ }
149
211
} ;
150
212
151
213
process . kill = function ( pid , sig ) {
0 commit comments