1
2
3
4
5
6
7
8
9
10
11
12
13
14
15
16
17
18
19
20
21
22
23
24
25
26
27
28
29
30
31
32
33
34
35
36
37
38
39
40
41
42
43
44
45
46
47
48
49
50
51
52
53
54
55
56
57
58
59
60
61
62
63
64
65
66
67
68
69
70
71
72
73
74
75
76
77
78
79
80
81
82
83
84
85
86
87
88
89
90
91
92
93
94
95
96
97
98
99
100
101
102
103
104
105
106
107
108
109
110
111
112
113
114
115
116
117
118
119
120
121
122
123
124
125
126
127
128
129
130
131
132
133
134
135
136
137
138
139
140
141
142
143
144
145
146
147
148
149
150
151
152
153
154
155
156
157
158
159
160
161
162
163
164
165
166
167
168
169
170
171
172
173
174
175
176
177
178
179
180
181
182
183
184
185
186
187
188
189
190
191
192
193
194
195
196
197
198
199
200
201
202
203
204
205
206
207
208
209
210
211
212
213
214
215
216
217
218
219
220
221
222
223
224
225
226
227
228
229
230
231
232
233
234
235
236
237
238
239
240
241
242
243
244
245
246
247
248
249
250
251
252
253
254
255
256
257
258
259
260
261
262
263
264
265
266
267
268
269
270
271
272
273
274
275
276
277
278
279
280
281
282
283
284
285
286
287
288
289
290
291
292
293
294
295
296
297
298
299
300
301
302
303
304
305
306
307
308
309
310
311
312
313
314
315
316
317
318
319
320
321
322
323
324
325
326
327
328
329
330
331
332
333
334
335
336
337
338
339
340
341
342
343
344
345
346
347
348
349
350
351
352
353
354
355
356
357
358
359
360
361
362
363
364
365
366
367
368
369
370
371
372
373
374
375
376
377
378
379
380
381
382
383
384
385
386
387
388
389
390
391
392
393
394
395
396
397
398
399
400
401
402
403
404
405
406
407
408
409
410
411
412
413
414
415
416
417
418
419
420
421
422
423
424
425
426
427
428
429
430
431
432
433
434
435
436
437
438
439
440
441
442
443
444
445
446
447
448
449
450
451
452
453
454
455
456
457
458
459
460
461
462
463
464
465
466
467
468
469
470
471
472
473
474
475
476
477
478
479
480
481
482
483
484
485
486
487
488
489
490
491
492
493
494
495
496
497
498
499
500
501
502
503
504
505
506
507
508
509
510
511
512
513
514
515
516
517
518
519
520
521
522
523
524
525
526
527
528
529
530
531
532
533
534
535
536
537
|
.HTML "APE — The ANSI/POSIX Environment
.de XX
.IP \ \ \ \-
..
.TL
APE \(em The ANSI/POSIX Environment
.AU
Howard Trickey
howard@plan9.bell-labs.com
.SH
Introduction
.PP
When a large or frequently-updated program must be ported
to or from Plan 9, the ANSI/POSIX environment known as APE can be useful.
APE combines the set of headers and object code libraries specified by
the ANSI C standard (ANSI X3.159-1989) with the POSIX operating system
interface standard (IEEE 1003.1-1990, ISO 9945-1), the part of POSIX
defining the basic operating system functions.
Using APE will cause slower compilation and marginally slower execution speeds,
so if the importing or exporting happens only infrequently, due consideration
should be given to using the usual Plan 9 compilation environment instead.
Another factor to consider is that the Plan 9 header organization is
much simpler to remember and use.
.PP
There are some aspects of required POSIX behavior that are impossible or
very hard to simulate in Plan 9. They are described below.
Experience has shown, however, that the simulation is adequate for the
vast majority of programs. A much more common problem is that
many programs use functions or headers not defined by POSIX.
APE has some extensions to POSIX to help in this regard.
Extensions must be explicitly enabled with an appropriate
.CW #define ,
in order that the APE environment be a good aid for testing
ANSI/POSIX compliance of programs.
.SH
Pcc
.PP
The
.CW pcc
command acts as a front end to the Plan 9 C compilers and loaders.
It runs an ANSI C preprocessor over source files, using the APE
headers to satisfy
.CW "#include <\fIfile\fP>"
directives; then it runs a Plan 9 C compiler; finally, it may load
with APE libraries to produce an executable program.
The document
.I "How to Use the Plan 9 C Compiler"
explains how environment variables are used by convention to
handle compilation for differing architectures.
The environment variable
.CW $objtype
controls which Plan 9 compiler and loader are used by
.CW pcc ,
as well as the location of header and library files.
For example, if
.CW $objtype
is
.CW mips ,
then
.CW pcc
has
.CW cpp
look for headers in
.CW /mips/include/ape
followed by
.CW /sys/include/ape ;
then
.CW pcc
uses
.CW vc
to create
.CW .v
object files;
finally,
.CW vl
is used to create an executable using libraries in
.CW /mips/lib/ape .
.SH
Psh and Cc
.PP
The
.CW pcc
command is intended for uses where the source code is
ANSI/POSIX, but the programs are built in the usual Plan 9
manner \(em with
.CW mk
and producing object files with names ending in
.CW .v ,
etc.
Sometimes it is best to use the standard POSIX
.CW make
and
.CW cc
(which produces object files with names ending in
.CW .o ,
and automatically calls the loader unless
.CW -c
is specified).
Under these circumstances, execute the command:
.DS
.CW "ape/psh"
.DE
This starts a POSIX shell, with an environment that
includes the POSIX commands
.CW ar89 ,
.CW c89 ,
.CW cc ,
.CW basename ,
.CW dirname ,
.CW expr ,
.CW false ,
.CW grep ,
.CW kill ,
.CW make ,
.CW rmdir ,
.CW sed ,
.CW sh ,
.CW stty ,
.CW true ,
.CW uname ,
and
.CW yacc .
There are also a few placeholders for commands that cannot be
implemented in Plan 9:
.CW chown ,
.CW ln ,
and
.CW umask .
.PP
The
.CW cc
command accepts the options mandated for
the POSIX command
.CW c89 ,
as specified in the C-Language Development Utilities Option
annex of the POSIX Shell and Utilities standard.
It also accepts the following nonstandard options:
.CW -v
for echoing the commands for each pass to stdout;
.CW -A
to turn on ANSI prototype warnings;
.CW -S
to leave assembly language in
.I file .s;
.CW -Wp,\fIargs\fP
to pass
.I args
to the
.CW cpp ;
.CW -W0,\fIargs\fP
to pass
.I args
to 2c, etc.;
and
.CW -Wl,\fIargs\fP
to pass
.I args
to 2l, etc.
.PP
The
.CW sh
command is pdksh, a mostly POSIX-compliant public domain Korn Shell.
The Plan 9 implementation does not include
the emacs and vi editing modes.
.PP
The
.CW stty
command only has effect if the
.CW ape/ptyfs
command has been started to interpose a pseudo-tty interface
between
.CW /dev/cons
and the running command.
None of the distributed commands do this automatically.
.SH
Symbols
.PP
The C and POSIX standards require that certain symbols be
defined in headers.
They also require that certain other classes of symbols not
be defined in the headers, and specify certain other
symbols that may be defined in headers at the discretion
of the implementation.
POSIX defines
.I "feature test macros" ,
which are preprocessor symbols beginning with an underscore
and then a capital letter; if the program
.CW #defines
a feature test macro before the inclusion of any headers,
then it is requesting that certain symbols be visible in the headers.
The most important feature test macro is
.CW _POSIX_SOURCE :
when it is defined, exactly the symbols required by POSIX are
visible in the appropriate headers.
Consider
.CW <signal.h>
for example:
ANSI defines some names that must be defined in
.CW <signal.h> ,
but POSIX defines others, such as
.CW sigset_t ,
which are not allowed according to ANSI.
The solution is to make the additional symbols visible only when
.CW _POSIX_SOURCE
is defined.
.PP
To export a program, it helps to know whether it fits
in one of the following categories:
.IP 1.
Strictly conforming ANSI C program. It only uses features of the language,
libraries, and headers explicitly required by the C standard. It does not
depend on unspecified, undefined, or implementation-dependent behavior,
and does not exceed any minimum implementation limit.
.IP 2.
Strictly conforming POSIX program. Similar, but for the POSIX standard as well.
.IP 3.
Some superset of POSIX, with extensions. Each extension
is selected by a feature test macro, so it is clear which extensions
are being used.
.PP
With APE, if headers are always included to declare any library functions
used, then the set of feature test macros defined by a program will
show which of the above categories the program is in.
To accomplish this, no symbol is defined in a header if it is not required
by the C or POSIX standard, and those required by the POSIX standard
are protected by
.CW "#ifdef _POSIX_SOURCE" .
For example,
.CW <errno.h>
defines
.CW EDOM ,
.CW ERANGE ,
and
.CW errno ,
as required by the C standard.
The C standard allows more names beginning with
.CW E ,
but our header defines only those unless
.CW _POSIX_SOURCE
is defined, in which case the symbols required by POSIX are also defined.
This means that a program that uses
.CW ENAMETOOLONG
cannot masquerade as a strictly conforming ANSI C program.
.PP
.CW Pcc
and
.CW cc
do not predefine any preprocessor symbols except those required by
the ANSI C standard:
.CW __STDC__ ,
.CW __LINE__ ,
.CW __FILE__ ,
.CW __DATE__ ,
and
.CW __TIME__ .
Any others must be defined in the program itself or by using
.CW -D
on the command line.
.SH
Extensions
.PP
The discipline enforced by putting only required
names in the headers is useful for exporting programs,
but it gets in the way when importing programs.
The compromise is to allow additional symbols in headers,
additional headers, and additional library functions,
but only under control of extension feature test macros.
The following extensions are provided; unless otherwise
specified, the additional library functions are in the
default APE library.
.XX
.CW _LIBG_EXTENSION .
This allows the use of the Plan 9 graphics library.
The functions are as described in the Plan 9 manual (see
.I graphics (2))
except that
.CW div
had to be renamed
.CW ptdiv .
Include the
.CW <libg.h>
header to declare the needed types and functions.
.XX
.CW _LIMITS_EXTENSION .
POSIX does not require that names such as
.CW PATH_MAX
and
.CW OPEN_MAX
be defined in
.CW <limits.h> ,
but many programs assume they are defined there.
If
.CW _LIMITS_EXTENSION
is defined, those names will all be defined when
.CW <limits.h>
is included.
.XX
.CW _BSD_EXTENSION .
This extension includes not only Berkeley Unix routines,
but also a grab bag of other miscellaneous routines often
found in Unix implementations.
The extension allows the inclusion of any of:
.CW <bsd.h>
for
.CW bcopy() ,
.CW bcmp() ,
and similar Berkeley functions;
.CW <netdb.h>
for
.CW gethostbyname() ,
etc.,
and associated structures;
.CW <select.h>
for the Berkeley
.CW select
function and associated types and macros
for dealing with multiple input sources;
.CW <sys/ioctl.h>
for the
.CW ioctl
function (minimally implemented);
.CW <sys/param.h>
for
.CW NOFILES_MAX ;
.CW <sys/pty.h>
for pseudo-tty support via the
.CW ptsname(int)
and
.CW ptmname(int)
functions;
.CW <sys/resource.h> ;
.CW <sys/socket.h>
for socket structures, constants, and functions;
.CW <sys/time.h>
for definitions of the
.CW timeval
and
.CW timezone
structures;
and
.CW <sys/uio.h>
for the
.CW iovec
structure and the
.CW writev
and
.CW readv
functions used for scatter/gather I/O.
Defining
.CW _BSD_EXTENSION
also enables various extra definitions in
.CW <ctype.h> ,
.CW <signal.h> ,
.CW <stdio.h> ,
.CW <unistd.h> ,
.CW <sys/stat.h> ,
and
.CW <sys/times.h> .
.XX
.CW _NET_EXTENSION .
This extension allows inclusion of
.CW <libnet.h> ,
which defines the networking functions described in the Plan 9 manual page
.I dial (2).
.XX
.CW _PLAN9_EXTENSION .
This extension allows inclusion of
.CW <u.h> ,
.CW <lock.h> ,
.CW <qlock.h> ,
.CW <utf.h> ,
.CW <fmt.h> ,
and
.CW <draw.h> .
These are pieces of Plan 9 source code ported into APE,
mostly from
.CW <libc.h> .
.XX
.CW _REGEXP_EXTENSION .
This extension allows inclusion of
.CW <regexp.h> ,
which defines the regular expression matching functions described
in the Plan 9 manual page
.I regexp (2).
.XX
.CW _RESEARCH_SOURCE .
This extension enables a small library of functions from the Tenth Edition Unix
Research System (V10).
These functions and the types needed to use them are all defined in the
.CW <libv.h>
header.
The provided functions are:
.CW srand ,
.CW rand ,
.CW nrand ,
.CW lrand ,
and
.CW frand
(better random number generators);
.CW getpass ,
.CW tty_echoon ,
.CW tty_echooff
(for dealing with the common needs for mucking with terminal
characteristics);
.CW min
and
.CW max ;
.CW nap ;
and
.CW setfields ,
.CW getfields ,
and
.CW getmfields
(for parsing a line into fields).
See the Research Unix System Programmer's Manual, Tenth Edition, for a description
of these functions.
.XX
.CW _C99_SNPRINTF_EXTENSION .
This extension permits the use of the return values of
.I snprintf
and
.I vsnprintf .
Before C99, the 1999 C standard,
these functions usually returned the number of bytes,
excluding terminating NUL,
actually stored in the target string.
(GNU, as usual, had to be different and returned -1 if the target
string was too small.)
C99 requires them to instead return the number of bytes,
excluding terminating NUL,
that would have been written into the target string if it were infinitely large
or a negative value if an `encoding error' occurs,
so old programs compiled under C99 rules will be prone to overrunning
their buffers.
This extension is a way for the programmer to declare that he or she understands
the situation and has adjusted the code being compiled to compensate.
.SH
Common Problems
.PP
Some large systems, including X11, have been ported successfully
to Plan 9 using APE
(the X11 port is not included in the distribution, however,
because supporting it properly is too big a job).
The problems encountered fall into three categories:
(1) non-ANSI C/POSIX features used; (2) inadequate simulation of POSIX functions;
and (3) compiler/loader bugs.
By far the majority of problems are in the first category.
.PP
POSIX is just starting to be a target for programmers.
Most existing code is written to work with one or both of a BSD or a System V Unix.
System V is fairly close to POSIX, but there are some differences.
Also, many System V systems have imported some BSD features that are
not part of POSIX.
A good strategy for porting external programs is to first try using
.CW CFLAGS=-D_POSIX_SOURCE ;
if that doesn't work, try adding
.CW _D_BSD_EXTENSION
and perhaps include
.CW <bsd.h>
in source files.
Here are some solutions to problems that might remain:
.XX
Third (environment) argument to
.CW main .
Use the
.CW environ
global instead.
.XX
.CW OPEN_MAX ,
.CW PATH_MAX ,
etc., assumed in
.CW <limits.h> .
Rewrite to call
.CW sysconf
or define
.CW _LIMITS_EXTENSION .
.XX
.CW <varargs.h> .
Rewrite to use
.CW <stdarg.h> .
.PP
The second class of problems has to do with inadequacies in the Plan 9
simulation of POSIX functions.
These shortcomings have rarely gotten in the way
(except, perhaps, for the
.CW link
problem).
.XX
Functions for setting the userid, groupid, effective userid and effective groupid
do not do anything useful. The concept is impossible to simulate in Plan 9.
.CW Chown
also does nothing.
.XX
.CW execlp
and the related functions do not look at the
.CW PATH
environment variable. They just try the current directory and
.CW /bin
if the pathname is not absolute.
.XX
Advisory locking via
.CW fcntl
is not implemented.
.XX
.CW isatty
is hard to do correctly.
The approximation used is only sometimes correct.
.XX
.CW link
always fails.
.XX
With
.CW open ,
the
.CW O_NOCTTY
option has no effect.
The concept of a controlling tty is foreign to Plan 9.
.XX
.CW setsid
forks the name space and note group,
which is only approximately the right behavior.
.XX
The functions dealing with stacking signals,
.CW sigpending ,
.CW sigprocmask
and
.CW sigsuspend ,
do not work.
.XX
.CW umask
has no effect, as there is no such concept in Plan 9.
.XX
code that does
.CW getenv("HOME")
should be changed to
.CW getenv("home")
on Plan 9.
|