1 /* 2 3 silcstream.h 4 5 Author: Pekka Riikonen <priikone@silcnet.org> 6 7 Copyright (C) 2005 - 2007 Pekka Riikonen 8 9 The contents of this file are subject to one of the Licenses specified 10 in the COPYING file; You may not use this file except in compliance 11 with the License. 12 13 The software distributed under the License is distributed on an "AS IS" 14 basis, in the hope that it will be useful, but WITHOUT WARRANTY OF ANY 15 KIND, either expressed or implied. See the COPYING file for more 16 information. 17 18 */ 19 20 /****h* silcutil/SILC Stream Interface 21 * 22 * DESCRIPTION 23 * 24 * SILC Stream API is a generic representation of a stream. A common API 25 * is defined that can be used to read from and write to the stream. Any 26 * other stream API derived from this API can use this same interface for 27 * reading and writing. 28 * 29 * Note that stream implementations usually are not thread-safe. Always 30 * verify whether a stream implementation is thread-safe by checking their 31 * corresponding documentation. 32 * 33 ***/ 34 35 #ifndef SILCSTREAM_H 36 #define SILCSTREAM_H 37 38 /****s* silcutil/SilcStreamAPI/SilcStream 39 * 40 * NAME 41 * 42 * typedef void *SilcStream; 43 * 44 * DESCRIPTION 45 * 46 * Abstact stream context representing any stream. All streams are using 47 * this abstraction so that the stream can be accessed using the standard 48 * silc_stream_* functions. All streams are destroyed by calling the 49 * silc_stream_destroy function. 50 * 51 ***/ 52 typedef void *SilcStream; 53 54 /****d* silcutil/SilcStreamAPI/SilcStreamStatus 55 * 56 * NAME 57 * 58 * typedef enum { ... } SilcStreamStatus; 59 * 60 * DESCRIPTION 61 * 62 * Stream status. This status is returned into the SilcStreamNotifier 63 * callback function to indicate the status of the stream at a given 64 * moment. 65 * 66 * SOURCE 67 */ 68 typedef enum { 69 SILC_STREAM_CAN_READ, /* Data available for reading */ 70 SILC_STREAM_CAN_WRITE, /* Stream ready for writing */ 71 SILC_STREAM_EOS, /* End of stream */ 72 SILC_STREAM_CLOSED, /* Stream is closed */ 73 SILC_STREAM_INVALID, /* Stream is invalid */ 74 SILC_STREAM_NO_MEMORY, /* System out of memory */ 75 SILC_STREAM_ERROR, /* Unknown error */ 76 } SilcStreamStatus; 77 /***/ 78 79 /****f* silcutil/SilcStreamAPI/SilcStreamNotifier 80 * 81 * SYNOPSIS 82 * 83 * typedef void (*SilcStreamNotifier)(SilcStream stream, 84 * SilcStreamStatus status, 85 * void *context); 86 * 87 * DESCRIPTION 88 * 89 * A callback of this type is called as stream notifier to notify of a 90 * certain action taken over the stream. This is called to notify for 91 * example that data is ready for reading, or writing or that end of 92 * stream occurred. 93 * 94 ***/ 95 typedef void (*SilcStreamNotifier)(SilcStream stream, 96 SilcStreamStatus status, 97 void *context); 98 99 /****s* silcutil/SilcStreamAPI/SilcStreamOps 100 * 101 * NAME 102 * 103 * typedef struct { ... } SilcStreamOps; 104 * 105 * DESCRIPTION 106 * 107 * SILC Stream operations structure. This structure includes callback 108 * functions to the actual stream implementation. Any stream that 109 * use SILC Stream abstraction must fill this structure with the actual 110 * stream implementation. 111 * 112 * Each stream implementation MUST set this structure as the first field 113 * in their stream structure. As it is that structure that is passed 114 * to the silc_stream_* routines, the SILC Stream API expects that the 115 * SilcStream context starts with this structure. 116 * 117 * EXAMPLE 118 * 119 * typedef struct { 120 * const SilcStreamOps *ops; 121 * ... other stuff ... 122 * } *SilcFooStream; 123 * 124 * SilcFooStream foo; 125 * silc_stream_write(foo, data, data_len); 126 * 127 * SOURCE 128 */ 129 typedef struct { 130 /* This is called to read data from the stream. This is called when 131 silc_stream_read function was called. */ 132 int (*read)(SilcStream stream, unsigned char *buf, SilcUInt32 buf_len); 133 134 /* This is called when writing data to the stream. This is called when 135 silc_stream_write function was called. */ 136 int (*write)(SilcStream stream, const unsigned char *data, 137 SilcUInt32 data_len); 138 139 /* This is called to close the stream. This is called when the 140 silc_stream_close function was called. */ 141 SilcBool (*close)(SilcStream stream); 142 143 /* This is called to destroy the stream. This is called when the 144 silc_stream_destroy function was called. */ 145 void (*destroy)(SilcStream stream); 146 147 /* This is called to set a notifier callback to the stream and schedule 148 the stream. Stream should not be scheduled before calling this 149 function. If stream does not need scheduler then the scheduler can 150 be ignored. This is called when silc_stream_set_notifier was called. 151 Returns FALSE if the stream could not be scheduled. */ 152 SilcBool (*notifier)(SilcStream stream, SilcSchedule schedule, 153 SilcStreamNotifier callback, void *context); 154 155 /* This is called to return the associated scheduler, if set. This is 156 called when silc_stream_get_schedule was called. */ 157 SilcSchedule (*get_schedule)(SilcStream stream); 158 } SilcStreamOps; 159 /***/ 160 161 /****f* silcutil/SilcStreamAPI/silc_stream_read 162 * 163 * SYNOPSIS 164 * 165 * int silc_stream_read(SilcStream stream, unsigned char *buf, 166 * SilcUInt32 buf_len); 167 * 168 * DESCRIPTION 169 * 170 * Reads data from the stream indicated by `stream' into the data buffer 171 * indicated by `buf' which is size of `buf_len'. This returns the amount 172 * of data read, zero (0) if end of stream occurred, -1 if data could 173 * not be read at this moment, or -2 if error occurred. If -1 is returned 174 * the notifier callback will later be called with SILC_STREAM_CAN_READ 175 * status when stream is again ready for reading. 176 * 177 ***/ 178 int silc_stream_read(SilcStream stream, unsigned char *buf, 179 SilcUInt32 buf_len); 180 181 /****f* silcutil/SilcStreamAPI/silc_stream_write 182 * 183 * SYNOPSIS 184 * 185 * int silc_stream_write(SilcStream stream, const unsigned char *data, 186 * SilcUInt32 data_len); 187 * 188 * DESCRIPTION 189 * 190 * Writes `data_len' bytes of data to the stream indicated by `stream' from 191 * data buffer indicated by `data'. Returns the amount of data written, 192 * zero (0) if end of stream occurred, -1 if data could not be written 193 * at this moment, or -2 if error occurred. If -1 is returned the 194 * notifier callback will later be called with SILC_STREAM_CAN_WRITE 195 * status when stream is again ready for writing. 196 * 197 ***/ 198 int silc_stream_write(SilcStream stream, const unsigned char *data, 199 SilcUInt32 data_len); 200 201 /****f* silcutil/SilcStreamAPI/silc_stream_close 202 * 203 * SYNOPSIS 204 * 205 * SilcBool silc_stream_close(SilcStream stream); 206 * 207 * DESCRIPTION 208 * 209 * Closes the stream indicated by `stream'. No data can be read or written 210 * to the stream after calling this function. Return TRUE if the stream 211 * could be closed. If action is taken on closed stream the notifier 212 * callback may be called with an error status. 213 * 214 ***/ 215 SilcBool silc_stream_close(SilcStream stream); 216 217 /****f* silcutil/SilcStreamAPI/silc_stream_destroy 218 * 219 * SYNOPSIS 220 * 221 * void silc_stream_destroy(SilcStream stream); 222 * 223 * DESCRIPTION 224 * 225 * Destroy the stream indicated by `stream'. The `stream' will become 226 * invalid after this function returns. All streams are destroyed by 227 * calling this function. The silc_stream_close should be called 228 * before calling this function. However, if it is not called this 229 * function will call it. 230 * 231 ***/ 232 void silc_stream_destroy(SilcStream stream); 233 234 /****f* silcutil/SilcStreamAPI/silc_stream_set_notifier 235 * 236 * SYNOPSIS 237 * 238 * SilcBool silc_stream_set_notifier(SilcStream stream, 239 * SilcSchedule schedule, 240 * SilcStreamNotifier notifier, 241 * void *context); 242 * 243 * DESCRIPTION 244 * 245 * Schedule `stream' for stream events. Set the `notifier' callback to 246 * be called when some event takes place on the stream. The event will 247 * be delievered to the `notifier' callback with the `context'. It is 248 * called for example when data is available for reading or writing, or 249 * if an error occurs. This can be called at any time for valid stream. 250 * This call will also set the `stream' into non-blocking mode. 251 * 252 * If `notifier' is set to NULL no callback will be called for the stream, 253 * and the stream is not scheduled anymore. 254 * 255 * This function returns FALSE if the `schedule' was provided and the 256 * stream could not be scheduled. The actual API for `stream' may provide 257 * access to the actual error information. Returns TRUE on success. 258 * 259 ***/ 260 SilcBool silc_stream_set_notifier(SilcStream stream, SilcSchedule schedule, 261 SilcStreamNotifier notifier, void *context); 262 263 /****f* silcutil/SilcStreamAPI/silc_stream_get_schedule 264 * 265 * SYNOPSIS 266 * 267 * SilcSchedule silc_stream_get_schedule(SilcStream stream); 268 * 269 * DESCRIPTION 270 * 271 * Returns the scheduler that has been associated with the `stream', or 272 * NULL if one has not been set for the `stream'. 273 * 274 ***/ 275 SilcSchedule silc_stream_get_schedule(SilcStream stream); 276 277 #endif /* SILCSTREAM_H */ 278