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
|
Notes on the OS/2 Perl port
Raymond Chen
(rjc@math.princeton.edu)
Kai Uwe Rommel
(rommel@lan.informatik.tu-muenchen.dbp.de)
-1. Background.
This port was based on the MS-DOS port by Diomidis Spinellis.
0. Set-up.
First copy the files in the os2 directory into the parent
directory. Also install the file msdos/dir.h in your include
directory.
1. Compiling.
Perl has been compiled under MS-DOS using the Microsoft C compiler
version 6.0. Before compiling install dir.h as <sys/dir.h>. You will
need a Unix-like make program and something like yacc (e.g. bison). I
just ran yacc on my UNIX box and downloaded the resulting y.tab.[ch]
files. Compilation takes 45 minutes on a 16MHz 386 machine running
no jobs other than the compiler, so you will probably need something to
do in the meantime. Like, say, lunch. (Compilation time does not
include formatting the manual.) If you compile with optimization
turned off, it takes about half as long.
The executable is 270k (perlsym.exe is 473k; if you compile
without optimization, the sizes are 329K/531K), and the top level
directory needs 800K for sources, 550K for object code, and 800K for the
executables, assuming you want to build both perl.exe and perlsym.exe
with full optimization.
The makefile will compile glob for you which you will need to place
somewhere in your path so that perl globbing will work correctly. All
the tests were run, although some modifications were necessary because
OS/2 isn't UNIX. The tests that failed failed because of limitations of
the operating system and aren't the fault of the compiler. a2p and s2p
were not tested.
In the eg directory you will find the syscalls.pl header file,
and a sample program that demonstrates some of the improvements
of the OS/2 version over the MS-DOS version and some of the
system calls.
2. Using OS/2 Perl
The OS/2 version of perl has much of the functionality of the Unix
version. Here are some things that don't work: sockets, password
functions, [gs]et[eug]id, dbm functions, fork.
One thing that doesn't work is "split" with no arguments. Somehow,
yylval.arg is empty ... [[ Wait, sorry, I fixed that. --rjc ]]
Care has been taken to implement the rest, although the implementation
might not be the best possible. Here are short notes on the tricky
bits:
2.1. In-place editing.
Files currently can be edited in-place provided you are creating a
backup. Considerable effort is made to ensure that a reasonable
name for the backup is selected, while still remaining within
the 8.3 contraints of the FAT filesystem. (HPFS users have nothing
to worry about, since HPFS doesn't have the stupid 8.3 rule.)
The rules for how OS/2 perl combines your filename with the suffix
(the thing passed to "-i") are rather complicated, but the basic
idea is that the "obvious" name is chosen.
Here are the rules:
Style 0: Append the suffix exactly as UNIX perl would do it.
If the filesystem likes it, use it. (HPFS will always
swallow it. FAT will rarely accept it.)
Style 1: If the suffix begins with a '.', change the file extension
to whatever you supplied. If the name matches the original
name, use the fallback method.
Style 2: If the suffix is a single character, not a '.', try to add the
suffix to the following places, using the first one that works.
[1] Append to extension.
[2] Append to filename,
[3] Replace end of extension,
[4] Replace end of filename.
If the name matches the original name, use the fallback method.
Style 3: Any other case: Ignore the suffix completely and use the
fallback method.
Fallback method: Change the extension to ".$$$". If that matches the
original name, then change the extension to ".~~~".
If filename is more than 1000 characters long, we die a horrible
death. Sorry.
Examples, assuming style 0 failed.
suffix = ".bak" (style 1)
foo.bar => foo.bak
foo.bak => foo.$$$ (fallback)
foo.$$$ => foo.~~~ (fallback)
makefile => makefile.bak
suffix = "~" (style 2)
foo.c => foo.c~
foo.c~ => foo.c~~
foo.c~~ => foo~.c~~
foo~.c~~ => foo~~.c~~
foo~~~~~.c~~ => foo~~~~~.$$$ (fallback)
foo.pas => foo~.pas
makefile => makefile.~
longname.fil => longname.fi~
longname.fi~ => longnam~.fi~
longnam~.fi~ => longnam~.$$$
2.2. Directory access.
Are implemented, but in order to support telldir() and seekdir(),
they operate by reading in the entire directory at opendir(),
then handing out pieces of it each time you do a readdir().
2.3. Pipes and redirection.
Pipes and redirection are supported. Although OS/2 does not
terminate programs which try to write to closed pipes, perl will
kill them for you if you do it like this:
open(I, "long-running-program|");
... process a few lines ...
close(I); # discard the rest ...
The killing works like this: We wait until the child program either
closes its stdout or tries to write to it. If it writes to its stdout,
we kill it. Otherwise, we cwait for it. This is pretty much what UNIX
does by default.
All pipe commands are given to cmd.exe (or your COMSPEC) for execution as
CMD /c your-command-line
so you can go ahead and load it up with any goofy things you want,
like 2>1 redirection, more pipes, && || etc.
The pipe() function is also supported, so you can go ahead and
make your own funky file descriptor connections before piping off
a process. However, you have to mark the descriptor you are
retaining as NOINHERIT before spawning, else you are in deadlock city.
Unfortunately, there's no way to mark the handle as NOINHERIT yet.
It's on my wish list.
2.4. Syscall and Ioctl
IOCtl is not supported because the API is very different from the
UNIX API. Instead, IOCtl is supported as a syscall. Here are
the syscalls I've written so far:
$OS2_GetVersion = 0;
$OS2_Shutdown = 1;
$OS2_Beep = 2;
$OS2_PhysicalDisk = 3;
$OS2_Config = 4;
$OS2_IOCtl = 5;
$OS2_QCurDisk = 6;
$OS2_SelectDisk = 7;
$OS2_SetMaxFH = 8;
$OS2_Sleep = 9;
$OS2_StartSession = 10;
$OS2_StopSession = 11;
$OS2_SelectSession = 12;
The arguments you pass are handed off to OS/2 without interpretation,
and the return value is returned straight to you. However, you don't
have to supply arguments for the ones whose descriptions are "must be
zero"; perl will supply the mandatory zeros for you.
2.5. Binary file access
Files are opened in text mode by default. This means that CR LF pairs
are translated to LF. If binary access is needed the `binarymode'
function should be used. There is currently no way to reverse the
effect of the binary function. If that is needed close and reopen the
file.
2.6. Priority
The getpriority and setpriority functions are implemented, but since
OS/2 priorities are different from UNIX priorities, the arguments aren't
the same. Basically, the arguments you pass are handed directly to
OS/2. The only exception is the last argument to setpriority. To make
it easier to make delta priorities, if the priority class is 0xff, it
is changed to 0. That way, you can write
setpriority(0,0,-2)
instead of
setpriority(0,0,0xfe)
to decrease the delta by 2.
2.7. Interpreter startup.
The effect of the Unix #!/bin/perl interpreter startup can be obtained
under OS/2 by giving the script a .cmd extension and beginning the script
with the line
extproc C:\binp\perl.exe -S
You should provide the appropriate path to your executable, and
the -S option is necessary so that perl can find your script.
2.8. The kill function.
UNIX and OS/2 have different ideas about the kill function. I've
done a pretty feeble job of taking perl's UNIXish approach and
trying to jam it into the OS/2 way. No doubt you'll find that
your kill()s aren't working. My apologies in advance.
3. Bug reports.
I don't normally have access to an OS/2 machine, so if you find
a bug, you can go ahead and tell me about it, but the odds that
I'd be able to fix it are slim.
4. Wish list.
4.1. OS/2.
Make ENOPIPE a fatal error.
Permit linking of files. (Allegedly, they're working on this.)
Get a fork.
Make CMD.EXE pass through the return code of its child.
4.2 perl.
Provide a nice way to add new functions to perl without having
to understand the innards of perl. Not being fluent in perl
innards hacking, I added my extra functions via syscall.
4.3. My port.
4.3.1. In-place editing.
Make more idiot-proof.
Allow in-place editing without backup. (How?)
4.3.2. Spawning and piping.
Make popen() cleverer. Currently, it blindly hands everything
off to CMD.EXE. This wastes an exec if the command line didn't
have any shell metacharacters and if the program being run
is not a batch file.
Clever spawning is carried out by do_spawn. We should try
to make popen() do much of the same sort of preprocessing
as do_spawn does (which means, of course, that we probably
should yank out code to be dished off into a subroutine).
In do_spawn(), use DosExecPgm instead of spawnl in order to get more
precise reasons why the child terminated (RESULTCODES).
July 1990
Raymond Chen <rjc@math.princeton.edu>
1817 Oxford St. Apt 6
Berkeley, CA 94709-1828 USA
-----------------------
I picked up the OS/2 port with patches 19-28. When compiling, I found
out that os2.c and director.c were missing. I had to rewrite them because
even the original author of the port (Raymond Chen) did no longer have them.
I had directory routines laying around, this was no big deal.
I rewrote os2.c, but did not implement the syscall() as described above.
I had not the time and did not really need it. Feel free ...
Changes to above described port:
- the small program GLOB is now named PERLGLOB for better ordering in
my /bin directory
- added help page (well, a graphical user interface would be overkill
but a simple help page should be in every program :-)
- several cosmetic changes in standard distribution files because of
naming conventions etc., #ifdef'd OS2
- syscall() not supported as noted above
- chdir now recognizes also drive letters and changes also the drive
- new mypopen(), mypclose() functions and simulation routines for DOS mode,
they are selected automatically in real mode
- the new pclose() does not kill the child, my experience is that this is
not needed.
- setpriority is now: setpriority(class, pid, val)
see description of DosSetPrty() for class and val meanings
- getpriority is now: getpriority(dummy, pid)
see description of DosGetPrty()
- kill is now: kill(pid, sig)
where sig can be 0 (kill process)
1-3 (send process flags A-C, see DosFlagProcess())
if pid is less than zero, the signal is sent to the whole
process tree originating at -pid.
The following files are now new with patch >=29:
readme.os2 this file
dir.h sys/dir.h
director.c directory routines
os2.c kernel of OS/2 port (see below)
popen.c new popen.c
mktemp.c enhanced mktemp(), uses TMP env. variable, used by popen.c
perl.cs Compiler Shell script for perl itself
perl.def linker definition file for perl
perl.bad names of protect-only API calls for BIND
perlglob.cs Compiler Shell script for perl globbing program
perlglob.def linker definition file for perlglob
a2p.cs Compiler Shell script for a2p (see below)
a2p.def linker definition file for a2p
makefile Makefile, not tested
perlsh.cmd the converted perlsh
perldb.dif changes required for perldb.pl (change for your needs)
selfrun.cmd sample selfrunning perl script for OS/2
selfrun.bat sample selfrunning perl script for DOS mode
Note: I don't use make but my own utility, the Compiler Shell CS.
It was posted in comp.binaries.os2 or you can ask me for the newest
version. The .CS files are the "makefiles" for it.
Note: MS C 6.00 is required. C 5.1 is not capable of compiling perl,
especially not with -DDEBUGGING
August 1990
Kai Uwe Rommel
rommel@lan.informatik.tu-muenchen.dbp.de
Breslauer Str. 25
D-8756 Kahl/Main
+ I have verified with patchlevel 37, that the OS/2 port compiles,
after doing two minor changes. HPFS filenames support was also added.
Some bugs were fixed.
+ To compile,
- you need the bison parser generator
- copy config.h from os2 into the main perl directory (important !)
- copy perl.cs and perlglob.cs from the os2 subdir to the main dir
- copy a2p.cs from os2 to x2p
- say "bison -d perl.y"
"ren perl_tab.c perl.c" and
"ren perl_tab.h perly.h" in the main directory
- say "cs perl" and
"cs perlglob" in the main directory
- say "cs a2p" in the x2p subdir
+ If you don't have CS or don't want to use it, you have to
construct a makefile ...
+ If you have GNU gdbm, you can define NDBM in config.h and link with a
large model library of gdbm.
+ I am not shure if I can verify the OS/2 port with each release
from Larry Wall. Therefore, in future releases there may be
changes required to compile perl for OS/2.
October 1990
Kai Uwe Rommel
rommel@lan.informatik.tu-muenchen.dbp.de
|