16
16
17
17
#define _GNU_SOURCE
18
18
19
+ #include <assert.h>
19
20
#include <errno.h>
20
21
#include <fcntl.h>
21
22
#include <inttypes.h>
@@ -68,6 +69,7 @@ oc_write(struct np_other_client *oc_sess, const char *msg, uint64_t msglen)
68
69
69
70
msglen = msglen ? msglen : strlen (msg );
70
71
do {
72
+ interrupted = 0 ;
71
73
cnt = write (oc_sess -> unixsock , msg + written , msglen - written );
72
74
written += cnt ;
73
75
if ((cnt < 0 ) && (errno == EAGAIN )) {
@@ -123,22 +125,28 @@ oc_realloc(struct np_other_client *oc_sess)
123
125
*
124
126
* @param[in] oc_sess Client session.
125
127
* @param[in] flags Option for function (@ref ocreadflags).
126
- * @return positive number representing number of characters written into @p oc_sess buffer.
128
+ * @param[out] read_total Optional number of characters written into @p oc_sess buffer.
129
+ * @return 0 on success.
127
130
* @return negative number on error.
128
131
*/
129
- static int64_t
130
- oc_read (struct np_other_client * oc_sess , uint32_t flags )
132
+ static int
133
+ oc_read (struct np_other_client * oc_sess , uint32_t flags , uint64_t * read_total )
131
134
{
132
- int64_t rd , rdall = 0 ;
135
+ int64_t rd ;
136
+ uint64_t rdall = 0 ;
133
137
time_t tm ;
134
138
int interrupted ;
135
139
const char * endtag ;
136
140
137
141
tm = time (NULL );
138
142
oc_sess -> buf [0 ] = 0 ;
143
+ if (read_total ) {
144
+ * read_total = 0 ;
145
+ }
139
146
140
147
do {
141
148
interrupted = 0 ;
149
+ assert (oc_sess -> bufsize >= rdall );
142
150
rd = read (oc_sess -> unixsock , oc_sess -> buf + rdall , oc_sess -> bufsize - rdall );
143
151
if (rd < 0 ) {
144
152
if (errno == EAGAIN ) {
@@ -147,7 +155,6 @@ oc_read(struct np_other_client *oc_sess, uint32_t flags)
147
155
} else if (errno == EINTR ) {
148
156
rd = 0 ;
149
157
interrupted = 1 ;
150
- break ;
151
158
} else {
152
159
fprintf (stderr , "Reading from file descriptor (%d) failed (%s).\n" , oc_sess -> unixsock , strerror (errno ));
153
160
return -1 ;
@@ -194,7 +201,11 @@ oc_read(struct np_other_client *oc_sess, uint32_t flags)
194
201
}
195
202
} while (1 );
196
203
197
- return rdall ;
204
+ if (read_total ) {
205
+ * read_total = rdall ;
206
+ }
207
+
208
+ return 0 ;
198
209
}
199
210
200
211
/**
@@ -218,7 +229,7 @@ oc_hello_handshake(struct np_other_client *oc_sess)
218
229
return rc ;
219
230
}
220
231
221
- return ( oc_read (oc_sess , OC_READ_HELLO_MSG ) >= 0 ) ? 0 : -1 ;
232
+ return oc_read (oc_sess , OC_READ_HELLO_MSG , NULL ) ;
222
233
}
223
234
224
235
struct np_other_client *
@@ -231,13 +242,13 @@ oc_connect_unix(const char *address)
231
242
oc_sess = calloc (1 , sizeof * oc_sess );
232
243
if (!oc_sess ) {
233
244
OC_FAIL_LOG ;
234
- return NULL ;
245
+ goto error ;
235
246
}
236
247
237
248
oc_sess -> unixsock = socket (AF_UNIX , SOCK_STREAM , 0 );
238
249
if (oc_sess -> unixsock < 0 ) {
239
250
OC_FAIL_LOG ;
240
- return NULL ;
251
+ goto error ;
241
252
}
242
253
243
254
memset (& sun , 0 , sizeof (sun ));
@@ -246,28 +257,33 @@ oc_connect_unix(const char *address)
246
257
247
258
if (connect (oc_sess -> unixsock , (struct sockaddr * )& sun , sizeof (sun )) < 0 ) {
248
259
OC_FAIL_LOG ;
249
- return NULL ;
260
+ goto error ;
250
261
}
251
262
252
263
if (fcntl (oc_sess -> unixsock , F_SETFL , O_NONBLOCK ) < 0 ) {
253
264
OC_FAIL_LOG ;
254
- return NULL ;
265
+ goto error ;
255
266
}
256
267
257
268
oc_sess -> buf = malloc (2048 );
258
269
if (!oc_sess -> buf ) {
259
- return NULL ;
270
+ goto error ;
260
271
}
261
272
oc_sess -> bufsize = 2048 ;
262
273
263
274
rc = oc_hello_handshake (oc_sess );
264
275
if (rc ) {
265
- return NULL ;
276
+ goto error ;
266
277
}
267
278
268
279
oc_sess -> msgid = 1 ;
269
280
270
281
return oc_sess ;
282
+
283
+ error :
284
+ oc_session_free (oc_sess );
285
+
286
+ return NULL ;
271
287
}
272
288
273
289
int
@@ -277,6 +293,8 @@ oc_send_msg(struct np_other_client *oc_sess, const char *msg)
277
293
char * starttag = NULL ;
278
294
uint64_t msglen ;
279
295
296
+ assert (oc_sess && msg );
297
+
280
298
/* increment message-id but do not increment after initial handshake */
281
299
oc_sess -> msgid = (oc_sess -> msgid != 1 ) ? oc_sess -> msgid + 1 : oc_sess -> msgid ;
282
300
@@ -285,7 +303,6 @@ oc_send_msg(struct np_other_client *oc_sess, const char *msg)
285
303
if (!starttag ) {
286
304
OC_FAIL_LOG ;
287
305
return -1 ;
288
- goto cleanup ;
289
306
}
290
307
291
308
rc = oc_write (oc_sess , starttag , 0 );
@@ -312,18 +329,16 @@ oc_send_msg(struct np_other_client *oc_sess, const char *msg)
312
329
int
313
330
oc_recv_msg (struct np_other_client * oc_sess , char * * msg )
314
331
{
315
- int64_t len ;
332
+ int rc ;
333
+ uint64_t len ;
316
334
char * endtag ;
317
335
318
- len = oc_read (oc_sess , 0 );
336
+ assert (oc_sess && msg );
319
337
320
- if (len < 0 ) {
338
+ * msg = "" ;
339
+ rc = oc_read (oc_sess , 0 , & len );
340
+ if (rc ) {
321
341
return -1 ;
322
- } else if (len == (int64_t )oc_sess -> bufsize ) {
323
- /* unlikely, though no space for zero character */
324
- if (oc_realloc (oc_sess )) {
325
- return -1 ;
326
- }
327
342
}
328
343
329
344
/* Delete end tag: \n##\n */
0 commit comments