Implements werrstr in glibc (XCC)
[akaros.git] / user / ndblib / read9pmsg.c
1 /* 
2  * This file is part of the UCB release of Plan 9. It is subject to the license
3  * terms in the LICENSE file found in the top-level directory of this
4  * distribution and at http://akaros.cs.berkeley.edu/files/Plan9License. No
5  * part of the UCB release of Plan 9, including this file, may be copied,
6  * modified, propagated, or distributed except according to the terms contained
7  * in the LICENSE file.
8  */
9 #include <stdlib.h>
10
11 #include <stdio.h>
12 #include <parlib.h>
13 #include <unistd.h>
14 #include <signal.h>
15 #include <fcntl.h>
16 #include <iplib.h>
17 #include <fcall.h>
18 #include <fcallfmt.h>
19 #include <ndb.h>
20
21 long
22 readn(int f, void *av, long n)
23 {
24         char *a;
25         long m, t;
26
27         a = av;
28         t = 0;
29         while(t < n){
30                 m = read(f, a+t, n-t);
31                 if(m <= 0){
32                         if(t == 0)
33                                 return m;
34                         break;
35                 }
36                 t += m;
37         }
38         return t;
39 }
40
41 int
42 read9pmsg(int fd, void *abuf, unsigned int n)
43 {
44         int m, len;
45         uint8_t *buf;
46
47         buf = abuf;
48
49         /* read count */
50         m = readn(fd, buf, BIT32SZ);
51         if(m != BIT32SZ){
52                 if(m < 0)
53                         return -1;
54                 return 0;
55         }
56
57         len = GBIT32(buf);
58         if(len <= BIT32SZ || len > n){
59                 werrstr("bad length in 9P2000 message header");
60                 return -1;
61         }
62         len -= BIT32SZ;
63         m = readn(fd, buf+BIT32SZ, len);
64         if(m < len)
65                 return 0;
66         return BIT32SZ+m;
67 }