0 | module System.UV.Raw.Stream
  1 |
  2 | import System.UV.Raw.Callback
  3 | import System.UV.Raw.Handle
  4 | import System.UV.Raw.Loop
  5 | import System.UV.Raw.Pointer
  6 | import System.UV.Raw.Req
  7 | import System.UV.Raw.Util
  8 |
  9 | %default total
 10 |
 11 | --------------------------------------------------------------------------------
 12 | -- FFI
 13 | --------------------------------------------------------------------------------
 14 |
 15 | %foreign (idris_uv "uv_shutdown")
 16 | prim__uv_shutdown : Ptr Shutdown -> Ptr Stream -> AnyPtr -> PrimIO Int32
 17 |
 18 | %foreign (idris_uv "uv_listen")
 19 | prim__uv_listen : Ptr Stream -> (backlog : Int32) -> AnyPtr -> PrimIO Int32
 20 |
 21 | %foreign (idris_uv "uv_accept")
 22 | prim__uv_accept : (server, client : Ptr Stream) -> PrimIO Int32
 23 |
 24 | %foreign (idris_uv "uv_read_start")
 25 | prim__uv_read_start : Ptr Stream -> AnyPtr -> AnyPtr -> PrimIO Int32
 26 |
 27 | %foreign (idris_uv "uv_read_stop")
 28 | prim__uv_read_stop : Ptr Stream -> PrimIO Int32
 29 |
 30 | %foreign (idris_uv "idris_uv_write")
 31 | prim__uv_write :
 32 |      Ptr Write
 33 |   -> Ptr Stream
 34 |   -> Ptr Bits8
 35 |   -> Bits32
 36 |   -> AnyPtr
 37 |   -> PrimIO Int32
 38 |
 39 | %foreign (idris_uv "uv_is_readable")
 40 | prim__uv_is_readable : Ptr Stream -> PrimIO Int32
 41 |
 42 | %foreign (idris_uv "uv_is_writable")
 43 | prim__uv_is_writable : Ptr Stream -> PrimIO Int32
 44 |
 45 | %foreign (idris_uv "uv_stream_set_blocking")
 46 | prim__uv_stream_set_blocking: Ptr Stream -> Int32 -> PrimIO Int32
 47 |
 48 | %foreign (idris_uv "uv_stream_get_write_queue_size")
 49 | prim__uv_get_write_queue_size: Ptr Stream -> PrimIO Bits32
 50 |
 51 | --------------------------------------------------------------------------------
 52 | -- API
 53 | --------------------------------------------------------------------------------
 54 |
 55 | export
 56 | record AllocCB where
 57 |   [noHints]
 58 |   constructor AC
 59 |   ptr : AnyPtr
 60 |
 61 | parameters {auto has : HasIO io}
 62 |
 63 |   export %inline
 64 |   allocCB : (Ptr Handle -> Bits32 -> Ptr Buf -> IO ()) -> io AllocCB
 65 |   allocCB = map AC . ptrUintPtrCB
 66 |
 67 |   export
 68 |   sizedAlloc : Bits32 -> io AllocCB
 69 |   sizedAlloc s =
 70 |     allocCB $ \_,_,buf => do
 71 |       cs <- mallocPtrs Bits8 s
 72 |       initBuf buf cs s
 73 |
 74 |   export
 75 |   defaultAlloc : io AllocCB
 76 |   defaultAlloc =
 77 |     allocCB $ \_,size,buf => do
 78 |       cs <- mallocPtrs Bits8 size
 79 |       initBuf buf cs size
 80 |
 81 |   export %inline
 82 |   freeAllocCB : AllocCB -> io ()
 83 |   freeAllocCB = unlockAnyPtr . ptr
 84 |
 85 |   ||| Shutdown the outgoing (write) side of a duplex stream.
 86 |   ||| It waits for pending write requests to complete. The handle should
 87 |   ||| refer to a initialized stream.
 88 |   ||| The cb is called after shutdown is complete.
 89 |   export %inline
 90 |   uv_shutdown :
 91 |        (str : Ptr t)
 92 |     -> {auto 0 cst : PCast t Stream}
 93 |     -> (Ptr Shutdown -> Int32 -> IO ())
 94 |     ->  io Int32
 95 |   uv_shutdown str act = do
 96 |     p  <- mallocPtr Shutdown
 97 |     cb <- ptrIntCB (\p,y => act p y >> freeReq p)
 98 |     uv_req_set_data p cb
 99 |     primIO $ prim__uv_shutdown p (castPtr str) cb
100 |
101 |   ||| Start listening for incoming connections.
102 |   ||| backlog indicates the number of connections the kernel might queue,
103 |   ||| same as listen(2). When a new incoming connection is received
104 |   ||| the uv_connection_cb callback is called.
105 |   export %inline
106 |   uv_listen :
107 |        (str : Ptr t)
108 |     -> {auto 0 cst : PCast t Stream}
109 |     -> (backlog : Int32)
110 |     -> (Ptr Stream -> Int32 -> IO ())
111 |     ->  io Int32
112 |   uv_listen str bl act = do
113 |     cb <- ptrIntCB act
114 |     primIO $ prim__uv_listen (castPtr str) bl cb
115 |
116 |   export %inline
117 |   uv_accept :
118 |        (server : Ptr s)
119 |     -> (client : Ptr t)
120 |     -> {auto 0 csts : PCast s Stream}
121 |     -> {auto 0 cstt : PCast t Stream}
122 |     ->  io Int32
123 |   uv_accept ser cli = primIO $ prim__uv_accept (castPtr ser) (castPtr cli)
124 |
125 |   ||| Read data from an incoming stream.
126 |   ||| The `readCB` callback will be made several times until there is
127 |   ||| no more data to read or `readstop` is called.
128 |   export %inline
129 |   uv_read_start :
130 |        Ptr t
131 |     -> {auto 0 cstt : PCast t Stream}
132 |     -> AllocCB
133 |     -> (readCb  : Ptr Stream -> Int32 -> Ptr Buf -> IO ())
134 |     ->  io Int32
135 |   uv_read_start str (AC p) readCB = do
136 |     cb <- ptrIntPtrCB readCB
137 |     uv_handle_set_data (castPtr {t = Stream} str) cb
138 |     primIO $ prim__uv_read_start (castPtr str) p cb
139 |
140 |   ||| Stop reading data from the stream. The uv_read_cb callback will no longer
141 |   ||| be called.
142 |   |||
143 |   ||| This function is idempotent and may be safely called on a stopped stream.
144 |   |||
145 |   ||| This function will always succeed; hence, checking its return value
146 |   ||| is unnecessary. A non-zero return indicates that finishing releasing
147 |   ||| resources may be pending on the next input event on that TTY on Windows,
148 |   ||| and  does not indicate failure.
149 |   export %inline
150 |   uv_read_stop : Ptr t -> {auto 0 cstt : PCast t Stream} -> io ()
151 |   uv_read_stop str = ignore $ primIO $ prim__uv_read_stop (castPtr str)
152 |
153 |   ||| Write data to stream. Buffers are written in order. Example:
154 |   export %inline
155 |   uv_write :
156 |        Ptr t
157 |     -> {auto 0 cstt : PCast t Stream}
158 |     -> Ptr Bits8
159 |     -> Bits32
160 |     -> (Ptr Write -> Int32 -> IO ())
161 |     ->  io Int32
162 |   uv_write str buf size act = do
163 |     wr <- mallocPtr Write
164 |     cb <- ptrIntCB (\x,y => act x y >> freeReq x)
165 |     uv_req_set_data wr cb
166 |     primIO $ prim__uv_write wr (castPtr str) buf size cb
167 |
168 |   export %inline
169 |   uv_is_readable : Ptr t -> (0 _ : PCast t Stream) => io Bool
170 |   uv_is_readable p = int32ToBool <$> primIO (prim__uv_is_readable $ castPtr p)
171 |
172 |   export %inline
173 |   uv_is_writable : Ptr t -> (0 _ : PCast t Stream) => io Bool
174 |   uv_is_writable p = int32ToBool <$> primIO (prim__uv_is_writable $ castPtr p)
175 |
176 |   export %inline
177 |   uv_stream_set_blocking : Ptr t -> (0 _ : PCast t Stream) => Bool ->  io Int32
178 |   uv_stream_set_blocking p b =
179 |     primIO $ prim__uv_stream_set_blocking (castPtr p) (boolToInt32 b)
180 |
181 |   export %inline
182 |   uv_get_write_queue_size: Ptr t -> (0 _ : PCast t Stream) => io Bits32
183 |   uv_get_write_queue_size p = primIO $ prim__uv_get_write_queue_size (castPtr p)
184 |