[project @ 2001-06-22 12:36:33 by rrt]
[ghc-hetmet.git] / ghc / lib / std / PrelIO.hsc
1 {-# OPTIONS -fno-implicit-prelude #-}
2
3 #undef DEBUG_DUMP
4
5 -- -----------------------------------------------------------------------------
6 -- $Id: PrelIO.hsc,v 1.5 2001/06/22 12:36:33 rrt Exp $
7 --
8 -- (c) The University of Glasgow, 1992-2001
9 --
10 -- Module PrelIO
11
12 -- This module defines all basic IO operations.
13 -- These are needed for the IO operations exported by Prelude,
14 -- but as it happens they also do everything required by library
15 -- module IO.
16
17 module PrelIO where
18
19 #include "cbits/HsStd.h"
20 #include "PrelHandle_hsc.h"
21
22 import PrelBase
23
24 import PrelPosix
25 import PrelMarshalAlloc
26 import PrelMarshalUtils
27 import PrelStorable
28 import PrelCError
29 import PrelCString
30 import PrelCTypes
31 import PrelCTypesISO
32
33 import PrelIOBase
34 import PrelHandle       -- much of the real stuff is in here
35
36 import PrelMaybe
37 import PrelReal
38 import PrelNum
39 import PrelRead
40 import PrelShow
41 import PrelMaybe        ( Maybe(..) )
42 import PrelPtr
43 import PrelList
44 import PrelException    ( ioError, catch, throw )
45 import PrelConc
46
47 -- -----------------------------------------------------------------------------
48 -- Standard IO
49
50 putChar         :: Char -> IO ()
51 putChar c       =  hPutChar stdout c
52
53 putStr          :: String -> IO ()
54 putStr s        =  hPutStr stdout s
55
56 putStrLn        :: String -> IO ()
57 putStrLn s      =  do putStr s
58                       putChar '\n'
59
60 print           :: Show a => a -> IO ()
61 print x         =  putStrLn (show x)
62
63 getChar         :: IO Char
64 getChar         =  hGetChar stdin
65
66 getLine         :: IO String
67 getLine         =  hGetLine stdin
68
69 getContents     :: IO String
70 getContents     =  hGetContents stdin
71
72 interact        ::  (String -> String) -> IO ()
73 interact f      =   do s <- getContents
74                        putStr (f s)
75
76 readFile        :: FilePath -> IO String
77 readFile name   =  openFile name ReadMode >>= hGetContents
78
79 writeFile       :: FilePath -> String -> IO ()
80 writeFile name str = do
81     hdl <- openFile name WriteMode
82     hPutStr hdl str
83     hClose hdl
84
85 appendFile      :: FilePath -> String -> IO ()
86 appendFile name str = do
87     hdl <- openFile name AppendMode
88     hPutStr hdl str
89     hClose hdl
90
91 readLn          :: Read a => IO a
92 readLn          =  do l <- getLine
93                       r <- readIO l
94                       return r
95
96   -- raises an exception instead of an error
97 readIO          :: Read a => String -> IO a
98 readIO s        =  case (do { (x,t) <- reads s ;
99                               ("","") <- lex t ;
100                               return x }) of
101 #ifndef NEW_READS_REP
102                         [x]    -> return x
103                         []     -> ioError (userError "Prelude.readIO: no parse")
104                         _      -> ioError (userError "Prelude.readIO: ambiguous parse")
105 #else
106                         Just x -> return x
107                         Nothing  -> ioError (userError "Prelude.readIO: no parse")
108 #endif
109
110 -- ---------------------------------------------------------------------------
111 -- Simple input operations
112
113 -- Computation "hReady hdl" indicates whether at least
114 -- one item is available for input from handle "hdl".
115
116 -- If hWaitForInput finds anything in the Handle's buffer, it
117 -- immediately returns.  If not, it tries to read from the underlying
118 -- OS handle. Notice that for buffered Handles connected to terminals
119 -- this means waiting until a complete line is available.
120
121 hReady :: Handle -> IO Bool
122 hReady h = hWaitForInput h 0
123
124 hWaitForInput :: Handle -> Int -> IO Bool
125 hWaitForInput h msecs = do
126   wantReadableHandle "hReady" h $ \ handle_ -> do
127   let ref = haBuffer handle_
128   buf <- readIORef ref
129
130   if not (bufferEmpty buf)
131         then return True
132         else do
133
134   r <- throwErrnoIfMinus1Retry "hReady"
135           (inputReady (fromIntegral (haFD handle_)) (fromIntegral msecs))
136   return (r /= 0)
137
138 foreign import "inputReady" 
139   inputReady :: CInt -> CInt -> IO CInt
140
141 -- ---------------------------------------------------------------------------
142 -- hGetChar
143
144 -- hGetChar reads the next character from a handle,
145 -- blocking until a character is available.
146
147 hGetChar :: Handle -> IO Char
148 hGetChar handle =
149   wantReadableHandle "hGetChar" handle $ \handle_ -> do
150
151   let fd = haFD handle_
152       ref = haBuffer handle_
153
154   buf <- readIORef ref
155   if not (bufferEmpty buf)
156         then hGetcBuffered fd ref buf
157         else do
158
159   -- buffer is empty.
160   case haBufferMode handle_ of
161     LineBuffering    -> do
162         new_buf <- fillReadBuffer fd True buf
163         hGetcBuffered fd ref new_buf
164     BlockBuffering _ -> do
165         new_buf <- fillReadBuffer fd False buf
166         hGetcBuffered fd ref new_buf
167     NoBuffering -> do
168         -- make use of the minimal buffer we already have
169         let raw = bufBuf buf
170         r <- throwErrnoIfMinus1RetryMayBlock "hGetChar"
171                 (read_off (fromIntegral fd) raw 0 1)
172                 (threadWaitRead fd)
173         if r == 0
174            then ioe_EOF
175            else do (c,_) <- readCharFromBuffer raw 0
176                    return c
177
178 hGetcBuffered fd ref buf@Buffer{ bufBuf=b, bufRPtr=r, bufWPtr=w }
179  = do (c,r) <- readCharFromBuffer b r
180       let new_buf | r == w    = buf{ bufRPtr=0, bufWPtr=0 }
181                   | otherwise = buf{ bufRPtr=r }
182       writeIORef ref new_buf
183       return c
184
185 -- ---------------------------------------------------------------------------
186 -- hGetLine
187
188 -- If EOF is reached before EOL is encountered, ignore the EOF and
189 -- return the partial line. Next attempt at calling hGetLine on the
190 -- handle will yield an EOF IO exception though.
191
192 -- ToDo: the unbuffered case is wrong: it doesn't lock the handle for
193 -- the duration.
194 hGetLine :: Handle -> IO String
195 hGetLine h = do
196   m <- wantReadableHandle "hGetLine" h $ \ handle_ -> do
197         case haBufferMode handle_ of
198            NoBuffering      -> return Nothing
199            LineBuffering    -> do
200               l <- hGetLineBuffered handle_
201               return (Just l)
202            BlockBuffering _ -> do 
203               l <- hGetLineBuffered handle_
204               return (Just l)
205   case m of
206         Nothing -> hGetLineUnBuffered h
207         Just l  -> return l
208
209
210 hGetLineBuffered handle_ = do
211   let ref = haBuffer handle_
212   buf <- readIORef ref
213   hGetLineBufferedLoop handle_ ref buf []
214
215
216 hGetLineBufferedLoop handle_ ref 
217         buf@Buffer{ bufRPtr=r, bufWPtr=w, bufBuf=raw } xss =
218   let 
219         -- find the end-of-line character, if there is one
220         loop raw r
221            | r == w = return (False, w)
222            | otherwise =  do
223                 (c,r') <- readCharFromBuffer raw r
224                 if c == '\n' 
225                    then return (True, r) -- NB. not r': don't include the '\n'
226                    else loop raw r'
227   in do
228   (eol, off) <- loop raw r
229
230 #ifdef DEBUG_DUMP
231   puts ("hGetLineBufferedLoop: r=" ++ show r ++ ", w=" ++ show w ++ ", off=" ++ show off ++ "\n")
232 #endif
233
234   xs <- unpack raw r off
235   if eol
236         then do if w == off + 1
237                    then writeIORef ref buf{ bufRPtr=0, bufWPtr=0 }
238                    else writeIORef ref buf{ bufRPtr = off + 1 }
239                 return (concat (reverse (xs:xss)))
240         else do
241              maybe_buf <- maybeFillReadBuffer (haFD handle_) True 
242                                 buf{ bufWPtr=0, bufRPtr=0 }
243              case maybe_buf of
244                 -- Nothing indicates we caught an EOF, and we may have a
245                 -- partial line to return.
246                 Nothing -> let str = concat (reverse (xs:xss)) in
247                            if not (null str)
248                               then return str
249                               else ioe_EOF
250                 Just new_buf -> 
251                      hGetLineBufferedLoop handle_ ref new_buf (xs:xss)
252
253
254 unpack :: RawBuffer -> Int -> Int -> IO [Char]
255 unpack buf r 0   = return ""
256 unpack buf (I## r) (I## len) = IO $ \s -> unpack [] (len -## 1##) s
257    where
258     unpack acc i s
259      | i <## r  = (## s, acc ##)
260      | otherwise = 
261           case readCharArray## buf i s of
262             (## s, ch ##) -> unpack (C## ch : acc) (i -## 1##) s
263
264
265 hGetLineUnBuffered :: Handle -> IO String
266 hGetLineUnBuffered h = do
267   c <- hGetChar h
268   if c == '\n' then
269      return ""
270    else do
271     l <- getRest
272     return (c:l)
273  where
274   getRest = do
275     c <- 
276       catch 
277         (hGetChar h)
278         (\ err -> do
279           if isEOFError err then
280              return '\n'
281            else
282              ioError err)
283     if c == '\n' then
284        return ""
285      else do
286        s <- getRest
287        return (c:s)
288
289 -- -----------------------------------------------------------------------------
290 -- hGetContents
291
292 -- hGetContents returns the list of characters corresponding to the
293 -- unread portion of the channel or file managed by the handle, which
294 -- is made semi-closed.
295
296 -- hGetContents on a DuplexHandle only affects the read side: you can
297 -- carry on writing to it afterwards.
298
299 hGetContents :: Handle -> IO String
300 hGetContents handle@(DuplexHandle r w) 
301   = withHandle' "hGetContents" handle r (hGetContents' handle)
302 hGetContents handle@(FileHandle m) 
303   = withHandle' "hGetContents" handle m (hGetContents' handle)
304
305 hGetContents' handle handle_ = 
306     case haType handle_ of 
307       ClosedHandle         -> ioe_closedHandle
308       SemiClosedHandle     -> ioe_closedHandle
309       AppendHandle         -> ioe_notReadable
310       WriteHandle          -> ioe_notReadable
311       _ -> do xs <- lazyRead handle
312               return (handle_{ haType=SemiClosedHandle}, xs )
313
314 -- Note that someone may close the semi-closed handle (or change its
315 -- buffering), so each time these lazy read functions are pulled on,
316 -- they have to check whether the handle has indeed been closed.
317
318 lazyRead :: Handle -> IO String
319 lazyRead handle = 
320    unsafeInterleaveIO $
321         withHandle_ "lazyRead" handle $ \ handle_ -> do
322         case haType handle_ of
323           ClosedHandle     -> return ""
324           SemiClosedHandle -> lazyRead' handle handle_
325           _ -> ioException 
326                   (IOError (Just handle) IllegalOperation "lazyRead"
327                         "illegal handle type" Nothing)
328
329 lazyRead' h handle_ = do
330   let ref = haBuffer handle_
331       fd  = haFD handle_
332
333   -- even a NoBuffering handle can have a char in the buffer... 
334   -- (see hLookAhead)
335   buf <- readIORef ref
336   if not (bufferEmpty buf)
337         then lazyReadBuffered h fd ref buf
338         else do
339
340   case haBufferMode handle_ of
341      NoBuffering      -> do
342         -- make use of the minimal buffer we already have
343         let raw = bufBuf buf
344             fd  = haFD handle_
345         r <- throwErrnoIfMinus1RetryMayBlock "hGetChar"
346                 (read_off (fromIntegral fd) raw 0 1)
347                 (threadWaitRead fd)
348         if r == 0
349            then return ""
350            else do (c,_) <- readCharFromBuffer raw 0
351                    rest <- lazyRead h
352                    return (c : rest)
353
354      LineBuffering    -> lazyReadBuffered h fd ref buf
355      BlockBuffering _ -> lazyReadBuffered h fd ref buf
356
357 -- we never want to block during the read, so we call fillReadBuffer with
358 -- is_line==True, which tells it to "just read what there is".
359 lazyReadBuffered h fd ref buf = do
360    maybe_new_buf <- 
361         if bufferEmpty buf 
362            then maybeFillReadBuffer fd True buf
363            else return (Just buf)
364    case maybe_new_buf of
365         Nothing  -> return ""
366         Just buf -> do
367            more <- lazyRead h
368            writeIORef ref buf{ bufRPtr=0, bufWPtr=0 }
369            unpackAcc (bufBuf buf) (bufRPtr buf) (bufWPtr buf) more
370
371
372 maybeFillReadBuffer fd is_line buf
373   = catch 
374      (do buf <- fillReadBuffer fd is_line buf
375          return (Just buf)
376      )
377      (\e -> if isEOFError e 
378                 then return Nothing 
379                 else throw e)
380
381
382 unpackAcc :: RawBuffer -> Int -> Int -> [Char] -> IO [Char]
383 unpackAcc buf r 0 acc  = return ""
384 unpackAcc buf (I## r) (I## len) acc = IO $ \s -> unpack acc (len -## 1##) s
385    where
386     unpack acc i s
387      | i <## r  = (## s, acc ##)
388      | otherwise = 
389           case readCharArray## buf i s of
390             (## s, ch ##) -> unpack (C## ch : acc) (i -## 1##) s
391
392 -- ---------------------------------------------------------------------------
393 -- hPutChar
394
395 -- `hPutChar hdl ch' writes the character `ch' to the file or channel
396 -- managed by `hdl'.  Characters may be buffered if buffering is
397 -- enabled for `hdl'.
398
399 hPutChar :: Handle -> Char -> IO ()
400 hPutChar handle c = 
401     c `seq` do   -- must evaluate c before grabbing the handle lock
402     wantWritableHandle "hPutChar" handle $ \ handle_  -> do
403     let fd = haFD handle_
404     case haBufferMode handle_ of
405         LineBuffering    -> hPutcBuffered handle_ True  c
406         BlockBuffering _ -> hPutcBuffered handle_ False c
407         NoBuffering      ->
408                 withObject (castCharToCChar c) $ \buf ->
409                 throwErrnoIfMinus1RetryMayBlock_ "hPutChar"
410                    (c_write (fromIntegral fd) buf 1)
411                    (threadWaitWrite fd)
412
413
414 hPutcBuffered handle_ is_line c = do
415   let ref = haBuffer handle_
416   buf <- readIORef ref
417   let w = bufWPtr buf
418   w'  <- writeCharIntoBuffer (bufBuf buf) w c
419   let new_buf = buf{ bufWPtr = w' }
420   if bufferFull new_buf || is_line && c == '\n'
421      then do 
422         flushed_buf <- flushWriteBuffer (haFD handle_) new_buf
423         writeIORef ref flushed_buf
424      else do 
425         writeIORef ref new_buf
426
427
428 hPutChars :: Handle -> [Char] -> IO ()
429 hPutChars handle [] = return ()
430 hPutChars handle (c:cs) = hPutChar handle c >> hPutChars handle cs
431
432 -- ---------------------------------------------------------------------------
433 -- hPutStr
434
435 -- `hPutStr hdl s' writes the string `s' to the file or
436 -- hannel managed by `hdl', buffering the output if needs be.
437
438 -- We go to some trouble to avoid keeping the handle locked while we're
439 -- evaluating the string argument to hPutStr, in case doing so triggers another
440 -- I/O operation on the same handle which would lead to deadlock.  The classic
441 -- case is
442 --
443 --              putStr (trace "hello" "world")
444 --
445 -- so the basic scheme is this:
446 --
447 --      * copy the string into a fresh buffer,
448 --      * "commit" the buffer to the handle.
449 --
450 -- Committing may involve simply copying the contents of the new
451 -- buffer into the handle's buffer, flushing one or both buffers, or
452 -- maybe just swapping the buffers over (if the handle's buffer was
453 -- empty).  See commitBuffer below.
454
455 hPutStr :: Handle -> String -> IO ()
456 hPutStr handle str = do
457     buffer_mode <- wantWritableHandle "hPutStr" handle 
458                         (\ handle_ -> do getSpareBuffer handle_)
459     case buffer_mode of
460        (NoBuffering, _) -> do
461             hPutChars handle str        -- v. slow, but we don't care
462        (LineBuffering, buf) -> do
463             writeLines handle buf str
464        (BlockBuffering _, buf) -> do
465             writeBlocks handle buf str
466
467
468 getSpareBuffer :: Handle__ -> IO (BufferMode, Buffer)
469 getSpareBuffer Handle__{haBuffer=ref, 
470                         haBuffers=spare_ref,
471                         haBufferMode=mode}
472  = do
473    case mode of
474      NoBuffering -> return (mode, error "no buffer!")
475      _ -> do
476           bufs <- readIORef spare_ref
477           buf  <- readIORef ref
478           case bufs of
479             BufferListCons b rest -> do
480                 writeIORef spare_ref rest
481                 return ( mode, newEmptyBuffer b WriteBuffer (bufSize buf))
482             BufferListNil -> do
483                 new_buf <- allocateBuffer (bufSize buf) WriteBuffer
484                 return (mode, new_buf)
485
486
487 writeLines :: Handle -> Buffer -> String -> IO ()
488 writeLines hdl Buffer{ bufBuf=raw, bufSize=len } s =
489   let
490    shoveString :: Int -> [Char] -> IO ()
491         -- check n == len first, to ensure that shoveString is strict in n.
492    shoveString n cs | n == len = do
493         new_buf <- commitBuffer hdl raw len n True{-needs flush-} False
494         writeBlocks hdl new_buf cs
495    shoveString n [] = do
496         commitBuffer hdl raw len n False{-no flush-} True{-release-}
497         return ()
498    shoveString n (c:cs) = do
499         n' <- writeCharIntoBuffer raw n c
500         shoveString n' cs
501   in
502   shoveString 0 s
503
504 writeBlocks :: Handle -> Buffer -> String -> IO ()
505 writeBlocks hdl Buffer{ bufBuf=raw, bufSize=len } s =
506   let
507    shoveString :: Int -> [Char] -> IO ()
508         -- check n == len first, to ensure that shoveString is strict in n.
509    shoveString n cs | n == len = do
510         new_buf <- commitBuffer hdl raw len n True{-needs flush-} False
511         writeBlocks hdl new_buf cs
512    shoveString n [] = do
513         commitBuffer hdl raw len n False{-no flush-} True{-release-}
514         return ()
515    shoveString n (c:cs) = do
516         n' <- writeCharIntoBuffer raw n c
517         shoveString n' cs
518   in
519   shoveString 0 s
520
521 -- -----------------------------------------------------------------------------
522 -- commitBuffer handle buf sz count flush release
523 -- 
524 -- Write the contents of the buffer 'buf' ('sz' bytes long, containing
525 -- 'count' bytes of data) to handle (handle must be block or line buffered).
526 -- 
527 -- Implementation:
528 -- 
529 --    for block/line buffering,
530 --       1. If there isn't room in the handle buffer, flush the handle
531 --          buffer.
532 -- 
533 --       2. If the handle buffer is empty,
534 --               if flush, 
535 --                   then write buf directly to the device.
536 --                   else swap the handle buffer with buf.
537 -- 
538 --       3. If the handle buffer is non-empty, copy buf into the
539 --          handle buffer.  Then, if flush != 0, flush
540 --          the buffer.
541
542 commitBuffer
543         :: Handle                       -- handle to commit to
544         -> RawBuffer -> Int             -- address and size (in bytes) of buffer
545         -> Int                          -- number of bytes of data in buffer
546         -> Bool                         -- flush the handle afterward?
547         -> Bool                         -- release the buffer?
548         -> IO Buffer
549
550 commitBuffer hdl raw sz count flush release = do
551   wantWritableHandle "commitAndReleaseBuffer" hdl $ 
552     \ handle_@Handle__{ haFD=fd, haBuffer=ref, haBuffers=spare_buf_ref } -> do
553
554 #ifdef DEBUG_DUMP
555       puts ("commitBuffer: sz=" ++ show sz ++ ", count=" ++ show count
556             ++ ", flush=" ++ show flush ++ ", release=" ++ show release ++"\n")
557 #endif
558
559       old_buf@Buffer{ bufBuf=old_raw, bufRPtr=r, bufWPtr=w, bufSize=size }
560           <- readIORef ref
561
562       buf_ret <-
563         -- enough room in handle buffer?
564          if (not flush && (size - w > count))
565                 -- The > is to be sure that we never exactly fill
566                 -- up the buffer, which would require a flush.  So
567                 -- if copying the new data into the buffer would
568                 -- make the buffer full, we just flush the existing
569                 -- buffer and the new data immediately, rather than
570                 -- copying before flushing.
571
572                 -- not flushing, and there's enough room in the buffer:
573                 -- just copy the data in and update bufWPtr.
574             then do memcpy_off old_raw w raw (fromIntegral count)
575                     writeIORef ref old_buf{ bufWPtr = w + count }
576                     return (newEmptyBuffer raw WriteBuffer sz)
577
578                 -- else, we have to flush
579             else do flushed_buf <- flushWriteBuffer fd old_buf
580
581                     let this_buf = 
582                             Buffer{ bufBuf=raw, bufState=WriteBuffer, 
583                                     bufRPtr=0, bufWPtr=count, bufSize=sz }
584
585                         -- if:  (a) we don't have to flush, and
586                         --      (b) size(new buffer) == size(old buffer), and
587                         --      (c) new buffer is not full,
588                         -- we can just just swap them over...
589                     if (not flush && sz == size && count /= sz)
590                         then do 
591                           writeIORef ref this_buf
592                           return flushed_buf                         
593
594                         -- otherwise, we have to flush the new data too,
595                         -- and start with a fresh buffer
596                         else do 
597                           flushWriteBuffer fd this_buf
598                           writeIORef ref flushed_buf
599                             -- if the sizes were different, then allocate
600                             -- a new buffer of the correct size.
601                           if sz == size
602                              then return (newEmptyBuffer raw WriteBuffer sz)
603                              else allocateBuffer size WriteBuffer
604
605       -- release the buffer if necessary
606       if release && bufSize buf_ret == size
607          then do
608               spare_bufs <- readIORef spare_buf_ref
609               writeIORef spare_buf_ref 
610                 (BufferListCons (bufBuf buf_ret) spare_bufs)
611               return buf_ret
612          else
613               return buf_ret
614
615
616 foreign import "memcpy_wrap" unsafe 
617    memcpy_off :: RawBuffer -> Int -> RawBuffer -> CSize -> IO (Ptr ())
618 #def inline \
619 void *memcpy_wrap(char *dst, int dst_off, char *src, size_t sz) \
620 { return memcpy(dst+dst_off, src, sz); }
621
622 -- ---------------------------------------------------------------------------
623 -- hPutStrLn
624
625 -- Derived action `hPutStrLn hdl str' writes the string `str' to
626 -- the handle `hdl', adding a newline at the end.
627
628 hPutStrLn :: Handle -> String -> IO ()
629 hPutStrLn hndl str = do
630  hPutStr  hndl str
631  hPutChar hndl '\n'
632
633 -- ---------------------------------------------------------------------------
634 -- hPrint
635
636 -- Computation `hPrint hdl t' writes the string representation of `t'
637 -- given by the `shows' function to the file or channel managed by `hdl'.
638
639 hPrint :: Show a => Handle -> a -> IO ()
640 hPrint hdl = hPutStrLn hdl . show