Blob


1 /*
2 * Lib9 is miscellany from the Plan 9 C library that doesn't
3 * fit into libutf or into libfmt, but is still missing from traditional
4 * Unix C libraries.
5 */
6 #ifndef _LIB9H_
7 #define _LIB9H_ 1
9 #if defined(__cplusplus)
10 extern "C" {
11 #endif
14 #include <unistd.h>
15 #include <string.h>
16 #include <stdlib.h>
17 #include <stdarg.h>
18 #include <fcntl.h>
19 #include <assert.h>
20 #include <setjmp.h>
22 #ifndef _FMTH_
23 # include <fmt.h>
24 #endif
26 #define nil ((void*)0)
27 #define nelem(x) (sizeof(x)/sizeof((x)[0]))
29 #define _NEEDUCHAR 1
30 #define _NEEDUSHORT 1
31 #define _NEEDUINT 1
32 #define _NEEDULONG 1
34 #if defined(__linux__)
35 # include <sys/types.h>
36 # if defined(__USE_MISC)
37 # undef _NEEDUSHORT
38 # undef _NEEDUINT
39 # undef _NEEDULONG
40 # endif
41 #endif
42 #if defined(__FreeBSD__)
43 # include <sys/types.h>
44 # if !defined(_POSIX_SOURCE)
45 # undef _NEEDUSHORT
46 # undef _NEEDUINT
47 # endif
48 #endif
49 #if defined(__APPLE__)
50 # include <sys/types.h>
51 # undef _NEEDUSHORT
52 # undef _NEEDUINT
53 #endif
55 typedef signed char schar;
56 typedef unsigned int u32int;
57 #ifdef _NEEDUCHAR
58 typedef unsigned char uchar;
59 #endif
60 #ifdef _NEEDUSHORT
61 typedef unsigned short ushort;
62 #endif
63 #ifdef _NEEDUINT
64 typedef unsigned int uint;
65 #endif
66 #ifdef _NEEDULONG
67 typedef unsigned long ulong;
68 #endif
69 typedef unsigned long long uvlong;
70 typedef long long vlong;
72 /* rfork to create new process running fn(arg) */
74 #if defined(__FreeBSD__)
75 #undef RFFDG
76 #undef RFNOTEG
77 #undef RFPROC
78 #undef RFMEM
79 #undef RFNOWAIT
80 #undef RFCFDG
81 #endif
83 enum
84 {
85 /* RFNAMEG = (1<<0), */
86 /* RFENVG = (1<<1), */
87 RFFDG = (1<<2),
88 RFNOTEG = (1<<3),
89 RFPROC = (1<<4),
90 RFMEM = (1<<5),
91 RFNOWAIT = (1<<6),
92 /* RFCNAMEG = (1<<10), */
93 /* RFCENVG = (1<<11), */
94 RFCFDG = (1<<12),
95 /* RFREND = (1<<13), */
96 /* RFNOMNT = (1<<14) */
97 };
98 extern int ffork(int, void(*)(void*), void*);
100 /* wait for processes */
101 #define wait _p9wait
102 typedef struct Waitmsg Waitmsg;
103 struct Waitmsg
105 int pid; /* of loved one */
106 ulong time[3]; /* of loved one & descendants */
107 char *msg;
108 };
109 extern int await(char*, int);
110 extern Waitmsg* wait(void);
112 /* synchronization */
113 typedef struct Lock Lock;
114 struct Lock
116 int val;
117 };
119 extern int _tas(void*);
120 extern void lock(Lock*);
121 extern void unlock(Lock*);
122 extern int canlock(Lock*);
124 typedef struct QLp QLp;
125 struct QLp
127 int inuse;
128 QLp *next;
129 int state;
130 };
132 typedef struct QLock QLock;
133 struct QLock
135 Lock lock;
136 int locked;
137 QLp *head;
138 QLp *tail;
139 };
141 extern void qlock(QLock*);
142 extern void qunlock(QLock*);
143 extern int canqlock(QLock*);
144 extern void _qlockinit(ulong (*)(ulong, ulong));
146 typedef struct RWLock RWLock;
147 struct RWLock
149 Lock lock;
150 int readers;
151 int writer;
152 QLp *head;
153 QLp *tail;
154 };
156 extern void rlock(RWLock*);
157 extern void runlock(RWLock*);
158 extern int canrlock(RWLock*);
159 extern void wlock(RWLock*);
160 extern void wunlock(RWLock*);
161 extern int canwlock(RWLock*);
163 typedef struct Rendez Rendez;
164 struct Rendez
166 QLock *l;
167 QLp *head;
168 QLp *tail;
169 };
171 extern void rsleep(Rendez*);
172 extern int rwakeup(Rendez*);
173 extern int rwakeupall(Rendez*);
175 extern ulong rendezvous(ulong, ulong);
177 /* one of a kind */
178 extern void sysfatal(char*, ...);
179 extern int nrand(int);
180 extern long lrand(void);
181 extern void setmalloctag(void*, ulong);
182 extern void setrealloctag(void*, ulong);
183 extern void *mallocz(ulong, int);
184 extern long readn(int, void*, long);
185 extern void exits(char*);
186 extern void _exits(char*);
187 extern ulong getcallerpc(void*);
189 /* string routines */
190 extern char* strecpy(char*, char*, char*);
191 extern int tokenize(char*, char**, int);
192 extern int cistrncmp(char*, char*, int);
193 extern int cistrcmp(char*, char*);
194 extern char* cistrstr(char*, char*);
195 extern int getfields(char*, char**, int, int, char*);
196 extern int gettokens(char *, char **, int, char *);
198 /* formatting helpers */
199 extern int dec64(uchar*, int, char*, int);
200 extern int enc64(char*, int, uchar*, int);
201 extern int dec32(uchar*, int, char*, int);
202 extern int enc32(char*, int, uchar*, int);
203 extern int dec16(uchar*, int, char*, int);
204 extern int enc16(char*, int, uchar*, int);
205 extern int encodefmt(Fmt*);
207 /* error string */
208 enum
210 ERRMAX = 128
211 };
212 extern void rerrstr(char*, uint);
213 extern void werrstr(char*, ...);
214 extern int errstr(char*, uint);
216 /* compiler directives on plan 9 */
217 #define USED(x) if(x){}else{}
218 #define SET(x) ((x)=0)
220 /* command line */
221 extern char *argv0;
222 extern void __fixargv0(void);
223 #define ARGBEGIN for((argv0||(argv0=(__fixargv0(),*argv))),argv++,argc--;\
224 argv[0] && argv[0][0]=='-' && argv[0][1];\
225 argc--, argv++) {\
226 char *_args, *_argt;\
227 Rune _argc;\
228 _args = &argv[0][1];\
229 if(_args[0]=='-' && _args[1]==0){\
230 argc--; argv++; break;\
231 }\
232 _argc = 0;\
233 while(*_args && (_args += chartorune(&_argc, _args)))\
234 switch(_argc)
235 #define ARGEND SET(_argt);USED(_argt);USED(_argc);USED(_args);}USED(argv);USED(argc);
236 #define ARGF() (_argt=_args, _args="",\
237 (*_argt? _argt: argv[1]? (argc--, *++argv): 0))
238 #define EARGF(x) (_argt=_args, _args="",\
239 (*_argt? _argt: argv[1]? (argc--, *++argv): ((x), abort(), (char*)0)))
241 #define ARGC() _argc
243 #define OREAD O_RDONLY
244 #define OWRITE O_WRONLY
245 #define AEXIST 0
246 #define AREAD 4
247 #define AWRITE 2
248 #define AEXEC 1
249 #define ORCLOSE 8
250 #define OCEXEC 16
252 #define dup dup2
253 #define exec execv
254 #define seek lseek
255 #define getwd getcwd
257 #if defined(__cplusplus)
259 #endif
261 #endif /* _LIB9H_ */