Release 0.4.0
[wine] / ALPHA-pl13.diff
1 diff -u --recursive --new-file pl12/linux/README linux/README
2 --- pl12/linux/README   Sun Aug 15 14:26:24 1993
3 +++ linux/README        Mon Aug 16 22:18:24 1993
4 @@ -1,7 +1,13 @@
5  
6 -       Linux kernel release 0.99 patchlevel 12
7 +       Linux kernel release 0.99 patchlevel 13
8  
9 -These are the release notes for linux version 0.99.12.  Read them
10 +[ Just to show everybody that I have no personal integrity at all, this
11 +release is dedicated to Martin Mueller and Sebastian Hetze just because
12 +they wrote the German Linux Anwenderhandbuch.  The fact that they sent
13 +me some of the money they made on selling it has nothing at all to do
14 +with the dedication.  Oh, no.  That would be crass.  ]
15 +
16 +These are the release notes for linux version 0.99.13.  Read them
17  carefully, as they tell you what's new, explain how to install the
18  kernel, and what to do if something goes wrong. 
19  
20 diff -u --recursive --new-file pl12/linux/config.in linux/config.in
21 --- pl12/linux/config.in        Sun Aug 15 11:24:56 1993
22 +++ linux/config.in     Sat Sep  4 15:17:42 1993
23 @@ -13,6 +13,10 @@
24  bool 'System V IPC' CONFIG_SYSVIPC y
25  bool 'Use -m486 flag for 486-specific optimizations' CONFIG_M486 y
26  *
27 +* Program binary formats
28 +*
29 +bool 'Elf executables' CONFIG_BINFMT_ELF y
30 +*
31  * SCSI support
32  *
33  bool 'SCSI support?' CONFIG_SCSI n
34 @@ -49,14 +53,14 @@
35  bool 'SLIP (serial line) support' CONFIG_SLIP n
36  bool 'PLIP (parallel port) support' CONFIG_PLIP n
37  bool 'NE2000/NE1000 support' CONFIG_NE2000 y
38 -bool 'WD80*3 support' CONFIG_WD80x3 y
39 +bool 'WD80*3 support' CONFIG_WD80x3 n
40  #bool '3c501 support' CONFIG_EL1 n
41  bool '3c503 support' CONFIG_EL2 y
42  #bool '3c509 support' CONFIG_EL3 n
43 -bool 'HP PCLAN support' CONFIG_HPLAN y
44 -bool 'AT1500 and NE2100 support' CONFIG_AT1500 y
45 +bool 'HP PCLAN support' CONFIG_HPLAN n
46 +bool 'AT1500 and NE2100 support' CONFIG_AT1500 n
47  #bool 'DEPCA support' CONFIG_DEPCA n
48 -bool 'D-Link DE600 pocket adaptor support' CONFIG_DE600 y
49 +bool 'D-Link DE600 pocket adaptor support' CONFIG_DE600 n
50  #bool 'AT-LAN-TEC pocket adaptor support' CONFIG_ATP n
51  #bool 'EtherExpress support' CONFIG_EEXPRESS n
52  fi
53 @@ -79,7 +83,7 @@
54  *
55  bool 'Keyboard meta-key sends ESC-prefix' CONFIG_KBD_META y
56  bool 'Keyboard Num Lock on by default' CONFIG_KBD_NUML y
57 -bool 'Logitech busmouse support' CONFIG_BUSMOUSE n
58 +bool 'Logitech busmouse support' CONFIG_BUSMOUSE y
59  bool 'PS/2 mouse (aka "auxiliary device") support' CONFIG_PSMOUSE n
60  bool 'Microsoft busmouse support' CONFIG_MS_BUSMOUSE n
61  bool 'ATIXL busmouse support' CONFIG_ATIXL_BUSMOUSE n
62 @@ -95,5 +99,5 @@
63  bool 'Debug kmalloc/kfree' CONFIG_DEBUG_MALLOC n
64  bool 'Kernel profiling support' CONFIG_PROFILE n
65  if [ "$CONFIG_SCSI" = "y" ]
66 -bool 'Verbose scsi error reporting (kernel size +=12K)' CONFIG_SCSI_CONSTANTS n
67 +bool 'Verbose scsi error reporting (kernel size +=12K)' CONFIG_SCSI_CONSTANTS y
68  fi
69 diff -u --recursive --new-file pl12/linux/fs/Makefile linux/fs/Makefile
70 --- pl12/linux/fs/Makefile      Sun Mar  7 16:21:10 1993
71 +++ linux/fs/Makefile   Fri Aug 20 08:59:30 1993
72 @@ -34,6 +34,9 @@
73  FS_SUBDIRS := $(FS_SUBDIRS) xiafs
74  endif
75  
76 +ifdef CONFIG_BINFMT_ELF
77 +BINFMTS := $(BINFMTS) binfmt_elf.o
78 +endif
79  
80  .c.s:
81         $(CC) $(CFLAGS) -S $<
82 @@ -44,7 +47,7 @@
83  
84  OBJS=  open.o read_write.o inode.o devices.o file_table.o buffer.o super.o \
85         block_dev.o stat.o exec.o pipe.o namei.o fcntl.o ioctl.o \
86 -       select.o fifo.o locks.o filesystems.o
87 +       select.o fifo.o locks.o filesystems.o $(BINFMTS)
88  
89  all: fs.o filesystems.a
90  
91 diff -u --recursive --new-file pl12/linux/fs/binfmt_elf.c linux/fs/binfmt_elf.c
92 --- pl12/linux/fs/binfmt_elf.c
93 +++ linux/fs/binfmt_elf.c       Sat Sep  4 03:36:30 1993
94 @@ -0,0 +1,368 @@
95 +#include <linux/fs.h>
96 +#include <linux/sched.h>
97 +#include <linux/mm.h>
98 +#include <linux/mman.h>
99 +#include <linux/a.out.h>
100 +#include <linux/errno.h>
101 +#include <linux/signal.h>
102 +#include <linux/binfmts.h>
103 +#include <asm/segment.h>
104 +#include <linux/string.h>
105 +#include <linux/fcntl.h>
106 +#include <linux/ptrace.h>
107 +
108 +asmlinkage int sys_exit(int exit_code);
109 +asmlinkage int sys_close(unsigned fd);
110 +asmlinkage int sys_open(const char *, int, int);
111 +
112 +/*
113 + * These are the functions used to load ELF style executables and shared
114 + * libraries.  There is no binary dependent code anywhere else.
115 + */
116 +
117 +#include <linux/elf.h>
118 +
119 +int load_elf_binary(struct linux_binprm * bprm, struct pt_regs * regs)
120 +{
121 +       struct elfhdr elf_ex;
122 +       struct file * file;
123 +       struct exec ex;
124 +       struct inode *interpreter_inode;
125 +       int i;
126 +       int old_fs;
127 +       int error;
128 +       struct elf_phdr * elf_ppnt, *elf_phdata;
129 +       int elf_exec_fileno;
130 +       unsigned int elf_bss, k, elf_brk;
131 +       int retval;
132 +       char * elf_interpreter;
133 +       unsigned int elf_entry;
134 +       int status;
135 +       unsigned int start_code, end_code, end_data;
136 +       unsigned int elf_stack;
137 +       char passed_fileno[6];
138 +       
139 +       status = 0;
140 +       elf_ex = *((struct elfhdr *) bprm->buf);          /* exec-header */
141 +       
142 +       if (elf_ex.e_ident[0] != 0x7f ||
143 +           strncmp(&elf_ex.e_ident[1], "ELF",3) != 0)
144 +               return  -ENOEXEC;
145 +       
146 +       
147 +       /* First of all, some simple consistency checks */
148 +       if(elf_ex.e_type != ET_EXEC || 
149 +          (elf_ex.e_machine != EM_386 && elf_ex.e_machine != EM_486) ||
150 +          (!bprm->inode->i_op || !bprm->inode->i_op->default_file_ops ||
151 +           !bprm->inode->i_op->default_file_ops->mmap)){
152 +               return -ENOEXEC;
153 +       };
154 +       
155 +       /* Now read in all of the header information */
156 +       
157 +       elf_phdata = (struct elf_phdr *) kmalloc(elf_ex.e_phentsize * 
158 +                                                elf_ex.e_phnum, GFP_KERNEL);
159 +       
160 +       old_fs = get_fs();
161 +       set_fs(get_ds());
162 +       retval = read_exec(bprm->inode, elf_ex.e_phoff, (char *) elf_phdata,
163 +                          elf_ex.e_phentsize * elf_ex.e_phnum);
164 +       set_fs(old_fs);
165 +       if (retval < 0) {
166 +               kfree (elf_phdata);
167 +               return retval;
168 +       }
169 +       
170 +       elf_ppnt = elf_phdata;
171 +       
172 +       elf_bss = 0;
173 +       elf_brk = 0;
174 +       
175 +       elf_exec_fileno = open_inode(bprm->inode, O_RDONLY);
176 +
177 +       if (elf_exec_fileno < 0) {
178 +               kfree (elf_phdata);
179 +               return elf_exec_fileno;
180 +       }
181 +       
182 +       file = current->filp[elf_exec_fileno];
183 +       
184 +       elf_stack = 0xffffffff;
185 +       elf_interpreter = NULL;
186 +       start_code = 0;
187 +       end_code = 0;
188 +       end_data = 0;
189 +       
190 +       old_fs = get_fs();
191 +       set_fs(get_ds());
192 +       
193 +       for(i=0;i < elf_ex.e_phnum; i++){
194 +               if(elf_ppnt->p_type == PT_INTERP) {
195 +                       /* This is the program interpreter used for shared libraries - 
196 +                          for now assume that this is an a.out format binary */
197 +                       
198 +                       elf_interpreter = (char *) kmalloc(elf_ppnt->p_filesz, 
199 +                                                          GFP_KERNEL);
200 +                       
201 +                       retval = read_exec(bprm->inode,elf_ppnt->p_offset,elf_interpreter,
202 +                                          elf_ppnt->p_filesz);
203 +                       printk("Using ELF interpreter %s\n", elf_interpreter);
204 +                       if(retval >= 0)
205 +                               retval = namei(elf_interpreter, &interpreter_inode);
206 +                       if(retval >= 0)
207 +                               retval = read_exec(interpreter_inode,0,bprm->buf,128);
208 +                       
209 +                       if(retval >= 0){
210 +                               ex = *((struct exec *) bprm->buf);              /* exec-header */
211 +                               
212 +#if 0
213 +                               printk("Interpreter: %x %x %x\n",N_MAGIC(ex), ex.a_text,ex.a_data);
214 +#endif
215 +                       };
216 +               };
217 +               elf_ppnt++;
218 +       };
219 +       
220 +       set_fs(old_fs);
221 +       
222 +       /* Some simple consistency checks for the interpreter */
223 +       if(elf_interpreter){
224 +               if(retval < 0) {
225 +                       kfree(elf_interpreter);
226 +                       kfree(elf_phdata);
227 +                       return -ELIBACC;
228 +               };
229 +               if((N_MAGIC(ex) != OMAGIC) && (N_MAGIC(ex) != ZMAGIC)) {
230 +                       kfree(elf_interpreter);
231 +                       kfree(elf_phdata);
232 +                       return -ELIBBAD;
233 +               };
234 +       }
235 +       
236 +       /* OK, we are done with that, now set up the arg stuff,
237 +          and then start this sucker up */
238 +       
239 +       if (!bprm->sh_bang) {
240 +               char * passed_p;
241 +               
242 +               sprintf(passed_fileno, "%d", elf_exec_fileno);
243 +               passed_p = passed_fileno;
244 +               
245 +               if(elf_interpreter) {
246 +                       bprm->p = copy_strings(1,&passed_p,bprm->page,bprm->p,2);
247 +                       bprm->argc++;
248 +               };
249 +               if (!bprm->p) {
250 +                       if(elf_interpreter) {
251 +                             kfree(elf_interpreter);
252 +                       }
253 +                       kfree (elf_phdata);
254 +                       return -E2BIG;
255 +               }
256 +       }
257 +       
258 +       /* OK, This is the point of no return */
259 +       flush_old_exec(bprm);
260 +
261 +       current->end_data = 0;
262 +       current->end_code = 0;
263 +       current->start_mmap = ELF_START_MMAP;
264 +       current->mmap = NULL;
265 +       elf_entry = (unsigned int) elf_ex.e_entry;
266 +       
267 +       /* Do this so that we can load the interpreter, if need be.  We will
268 +          change some of these later */
269 +       current->rss = 0;
270 +       bprm->p += change_ldt(0, bprm->page);
271 +       current->start_stack = bprm->p;
272 +       
273 +       /* Now we do a little grungy work by mmaping the ELF image into
274 +          the correct location in memory.  At this point, we assume that
275 +          the image should be loaded at fixed address, not at a variable
276 +          address. */
277 +       
278 +       old_fs = get_fs();
279 +       set_fs(get_ds());
280 +       
281 +       elf_ppnt = elf_phdata;
282 +       for(i=0;i < elf_ex.e_phnum; i++){
283 +               
284 +               if(elf_ppnt->p_type == PT_INTERP) {
285 +                       /* Set these up so that we are able to load the interpreter */
286 +                       current->brk = ex.a_bss +
287 +                               (current->end_data = ex.a_data +
288 +                                (current->end_code = ex.a_text));
289 +                       elf_entry = ex.a_entry;
290 +                       
291 +                       /* Now load the interpreter into user address space */
292 +                       set_fs(old_fs);
293 +                       
294 +                       if (N_MAGIC(ex) == OMAGIC) {
295 +                               retval = read_exec(interpreter_inode, 32, (char *) 0, 
296 +                                                  ex.a_text+ex.a_data);
297 +                               iput(interpreter_inode);
298 +                       } else if (N_MAGIC(ex) == ZMAGIC) {
299 +                               retval = read_exec(interpreter_inode, 1024, (char *) 0, 
300 +                                                  ex.a_text+ex.a_data);
301 +                               iput(interpreter_inode);
302 +                       } else
303 +                               retval = -1;
304 +                       
305 +                       old_fs = get_fs();
306 +                       set_fs(get_ds());
307 +                       
308 +                       if(retval >= 0)
309 +                               zeromap_page_range((ex.a_text + ex.a_data + 0xfff) & 
310 +                                                  0xfffff000, ex.a_bss, PAGE_COPY);
311 +                       kfree(elf_interpreter);
312 +                       
313 +                       if(retval < 0) { 
314 +                               kfree(elf_phdata);
315 +                               send_sig(SIGSEGV, current, 0);
316 +                               return 0;
317 +                       };
318 +               };
319 +               
320 +               
321 +               if(elf_ppnt->p_type == PT_LOAD) {
322 +                       error = do_mmap(file,
323 +                                       elf_ppnt->p_vaddr & 0xfffff000,
324 +                                       elf_ppnt->p_filesz + (elf_ppnt->p_vaddr & 0xfff),
325 +                                       PROT_READ | PROT_WRITE | PROT_EXEC,
326 +                                       MAP_FIXED | MAP_PRIVATE,
327 +                                       elf_ppnt->p_offset & 0xfffff000);
328 +                       
329 +#ifdef LOW_ELF_STACK
330 +                       if(elf_ppnt->p_vaddr & 0xfffff000 < elf_stack) 
331 +                               elf_stack = elf_ppnt->p_vaddr & 0xfffff000;
332 +#endif
333 +                       
334 +                       k = elf_ppnt->p_vaddr;
335 +                       if(k > start_code) start_code = k;
336 +                       k = elf_ppnt->p_vaddr + elf_ppnt->p_filesz;
337 +                       if(k > elf_bss) elf_bss = k;
338 +                       if((elf_ppnt->p_flags | PROT_WRITE) && end_code <  k)
339 +                               end_code = k; 
340 +                       if(end_data < k) end_data = k; 
341 +                       k = elf_ppnt->p_vaddr + elf_ppnt->p_memsz;
342 +                       if(k > elf_brk) elf_brk = k;                 
343 +                       
344 +                       if(status == 0xffffffff) {
345 +                               set_fs(old_fs);
346 +                               kfree(elf_phdata);
347 +                               send_sig(SIGSEGV, current, 0);
348 +                               return 0;
349 +                       };
350 +               };
351 +               elf_ppnt++;
352 +       };
353 +       set_fs(old_fs);
354 +       
355 +       kfree(elf_phdata);
356 +       
357 +       if(!elf_interpreter) sys_close(elf_exec_fileno);
358 +       current->elf_executable = 1;
359 +       current->executable = bprm->inode;
360 +       bprm->inode->i_count++;
361 +#ifdef LOW_ELF_STACK
362 +       current->start_stack = p = elf_stack - 4;
363 +#endif
364 +       bprm->p -= MAX_ARG_PAGES*PAGE_SIZE;
365 +       bprm->p = (unsigned long) create_tables((char *)bprm->p,bprm->argc,bprm->envc);
366 +       if(elf_interpreter) current->arg_start += strlen(passed_fileno) + 1;
367 +       current->start_brk = current->brk = elf_brk;
368 +       current->end_code = end_code;
369 +       current->start_code = start_code;
370 +       current->start_stack = bprm->p;
371 +       current->suid = current->euid = bprm->e_uid;
372 +       current->sgid = current->egid = bprm->e_gid;
373 +       zeromap_page_range((elf_bss + 0xfff) & 0xfffff000, elf_brk - elf_bss,
374 +                          PAGE_COPY);
375 +       regs->eip = elf_entry;          /* eip, magic happens :-) */
376 +       regs->esp = bprm->p;                    /* stack pointer */
377 +       if (current->flags & PF_PTRACED)
378 +               send_sig(SIGTRAP, current, 0);
379 +       
380 +       return 0;
381 +}
382 +
383 +
384 +int load_elf_library(int fd){
385 +        struct file * file;
386 +       struct elfhdr elf_ex;
387 +       struct elf_phdr *elf_phdata  =  NULL;
388 +       struct  inode * inode;
389 +       unsigned int len;
390 +       int old_fs, retval;
391 +       unsigned int bss;
392 +       int error;
393 +       int i,j;
394 +       
395 +       len = 0;
396 +       file = current->filp[fd];
397 +       inode = file->f_inode;
398 +       
399 +       set_fs(KERNEL_DS);
400 +       if (file->f_op->read(inode, file, (char *) &elf_ex, sizeof(elf_ex)) != sizeof(elf_ex)) {
401 +               sys_close(fd);
402 +               return -EACCES;
403 +       }
404 +       set_fs(USER_DS);
405 +       
406 +       if (elf_ex.e_ident[0] != 0x7f ||
407 +           strncmp(&elf_ex.e_ident[1], "ELF",3) != 0)
408 +               return -ENOEXEC;
409 +       
410 +       /* First of all, some simple consistency checks */
411 +       if(elf_ex.e_type != ET_EXEC || elf_ex.e_phnum > 2 ||
412 +          (elf_ex.e_machine != EM_386 && elf_ex.e_machine != EM_486) ||
413 +          (!inode->i_op || !inode->i_op->bmap || 
414 +           !inode->i_op->default_file_ops->mmap)){
415 +               return -ENOEXEC;
416 +       };
417 +       
418 +       /* Now read in all of the header information */
419 +       
420 +       if(sizeof(struct elf_phdr) * elf_ex.e_phnum > PAGE_SIZE) 
421 +               return -ENOEXEC;
422 +       
423 +       elf_phdata =  (struct elf_phdr *) 
424 +               kmalloc(sizeof(struct elf_phdr) * elf_ex.e_phnum, GFP_KERNEL);
425 +       
426 +       old_fs = get_fs();
427 +       set_fs(get_ds());
428 +       retval = read_exec(inode, elf_ex.e_phoff, (char *) elf_phdata,
429 +                          sizeof(struct elf_phdr) * elf_ex.e_phnum);
430 +       set_fs(old_fs);
431 +       
432 +       j = 0;
433 +       for(i=0; i<elf_ex.e_phnum; i++)
434 +               if((elf_phdata + i)->p_type == PT_LOAD) j++;
435 +       
436 +       if(j != 1)  {
437 +               kfree(elf_phdata);
438 +               return -ENOEXEC;
439 +       };
440 +       
441 +       while(elf_phdata->p_type != PT_LOAD) elf_phdata++;
442 +       
443 +       /* Now use mmap to map the library into memory. */
444 +       error = do_mmap(file,
445 +                       elf_phdata->p_vaddr & 0xfffff000,
446 +                       elf_phdata->p_filesz + (elf_phdata->p_vaddr & 0xfff),
447 +                       PROT_READ | PROT_WRITE | PROT_EXEC,
448 +                       MAP_FIXED | MAP_PRIVATE,
449 +                       elf_phdata->p_offset & 0xfffff000);
450 +       
451 +       sys_close(fd);
452 +       if (error != elf_phdata->p_vaddr & 0xfffff000) {
453 +               kfree(elf_phdata);
454 +               return error;
455 +       }
456 +       len = (elf_phdata->p_filesz + elf_phdata->p_vaddr+ 0xfff) & 0xfffff000;
457 +       bss = elf_phdata->p_memsz + elf_phdata->p_vaddr;
458 +       if (bss > len)
459 +               zeromap_page_range(len, bss-len, PAGE_COPY);
460 +       kfree(elf_phdata);
461 +       return 0;
462 +}
463 diff -u --recursive --new-file pl12/linux/fs/buffer.c linux/fs/buffer.c
464 --- pl12/linux/fs/buffer.c      Sat Aug 14 23:47:21 1993
465 +++ linux/fs/buffer.c   Sat Sep  4 03:36:30 1993
466 @@ -160,7 +160,7 @@
467         return sync_buffers(dev, 1);
468  }
469  
470 -extern "C" int sys_sync(void)
471 +asmlinkage int sys_sync(void)
472  {
473         sync_dev(0);
474         return 0;
475 @@ -171,7 +171,7 @@
476         return fsync_dev(inode->i_dev);
477  }
478  
479 -extern "C" int sys_fsync(unsigned int fd)
480 +asmlinkage int sys_fsync(unsigned int fd)
481  {
482         struct file * file;
483         struct inode * inode;
484 diff -u --recursive --new-file pl12/linux/fs/exec.c linux/fs/exec.c
485 --- pl12/linux/fs/exec.c        Sun Aug 15 11:33:07 1993
486 +++ linux/fs/exec.c     Sat Sep  4 03:36:30 1993
487 @@ -44,13 +44,13 @@
488  #include <asm/segment.h>
489  #include <asm/system.h>
490  
491 -extern "C" int sys_exit(int exit_code);
492 -extern "C" int sys_close(unsigned fd);
493 -extern "C" int sys_open(const char *, int, int);
494 +asmlinkage int sys_exit(int exit_code);
495 +asmlinkage int sys_close(unsigned fd);
496 +asmlinkage int sys_open(const char *, int, int);
497  
498  extern void shm_exit (void);
499  
500 -static int open_inode(struct inode * inode, int mode)
501 +int open_inode(struct inode * inode, int mode)
502  {
503         int error, fd;
504         struct file *f, **fpp;
505 @@ -225,7 +225,7 @@
506   *
507   * Also note that we take the address to load from from the file itself.
508   */
509 -extern "C" int sys_uselib(const char * library)
510 +asmlinkage int sys_uselib(const char * library)
511  {
512         int fd, retval;
513         struct file * file;
514 @@ -316,7 +316,7 @@
515   * it is expensive to load a segment register, we try to avoid calling
516   * set_fs() unless we absolutely have to.
517   */
518 -static unsigned long copy_strings(int argc,char ** argv,unsigned long *page,
519 +unsigned long copy_strings(int argc,char ** argv,unsigned long *page,
520                 unsigned long p, int from_kmem)
521  {
522         char *tmp, *pag = NULL;
523 @@ -459,7 +459,7 @@
524         current->mmap = NULL;
525         while (mpnt) {
526                 mpnt1 = mpnt->vm_next;
527 -               if (mpnt->vm_ops->close)
528 +               if (mpnt->vm_ops && mpnt->vm_ops->close)
529                         mpnt->vm_ops->close(mpnt);
530                 kfree(mpnt);
531                 mpnt = mpnt1;
532 @@ -649,6 +649,7 @@
533                 }
534         }
535  
536 +       bprm.sh_bang = sh_bang;
537         fmt = formats;
538         do {
539                 int (*fn)(struct linux_binprm *, struct pt_regs *) = fmt->load_binary;
540 @@ -672,7 +673,7 @@
541  /*
542   * sys_execve() executes a new program.
543   */
544 -extern "C" int sys_execve(struct pt_regs regs)
545 +asmlinkage int sys_execve(struct pt_regs regs)
546  {
547         int error;
548         char * filename;
549 @@ -694,9 +695,16 @@
550                             struct pt_regs * regs);
551  extern int load_aout_library(int fd);
552  
553 +extern int load_elf_binary(struct linux_binprm *,
554 +                           struct pt_regs * regs);
555 +extern int load_elf_library(int fd);
556 +
557  /* Here are the actual binaries that will be accepted  */
558  struct linux_binfmt formats[] = {
559         {load_aout_binary, load_aout_library},
560 +#ifdef CONFIG_BINFMT_ELF
561 +       {load_elf_binary, load_elf_library},
562 +#endif
563         {NULL, NULL}
564  };
565  
566 @@ -713,17 +721,20 @@
567         unsigned long p = bprm->p;
568  
569         ex = *((struct exec *) bprm->buf);              /* exec-header */
570 -       if ((N_MAGIC(ex) != ZMAGIC && N_MAGIC(ex) != OMAGIC) ||
571 +       if ((N_MAGIC(ex) != ZMAGIC && N_MAGIC(ex) != OMAGIC && 
572 +            N_MAGIC(ex) != QMAGIC) ||
573             ex.a_trsize || ex.a_drsize ||
574             bprm->inode->i_size < ex.a_text+ex.a_data+ex.a_syms+N_TXTOFF(ex)) {
575                 return -ENOEXEC;
576         }
577 -       if (N_MAGIC(ex) == ZMAGIC && N_TXTOFF(ex) &&
578 +
579 +       if (N_MAGIC(ex) == ZMAGIC &&
580             (N_TXTOFF(ex) < bprm->inode->i_sb->s_blocksize)) {
581                 printk("N_TXTOFF < BLOCK_SIZE. Please convert binary.");
582                 return -ENOEXEC;
583         }
584 -       if (N_TXTOFF(ex) != BLOCK_SIZE && N_MAGIC(ex) != OMAGIC) {
585 +
586 +       if (N_TXTOFF(ex) != BLOCK_SIZE && N_MAGIC(ex) == ZMAGIC) {
587                 printk("N_TXTOFF != BLOCK_SIZE. See a.out.h.");
588                 return -ENOEXEC;
589         }
590 @@ -732,7 +743,10 @@
591         flush_old_exec(bprm);
592         current->start_brk = current->brk = ex.a_bss +
593                 (current->end_data = ex.a_data +
594 -                (current->end_code = ex.a_text));
595 +                (current->end_code = N_TXTADDR(ex) + ex.a_text));
596 +
597 +       current->start_code += N_TXTADDR(ex);
598 +
599         current->rss = 0;
600         current->suid = current->euid = bprm->e_uid;
601         current->mmap = NULL;
602 @@ -751,23 +765,25 @@
603                 file = current->filp[fd];
604                 if (!file->f_op || !file->f_op->mmap) {
605                         sys_close(fd);
606 -                       read_exec(bprm->inode, 1024, (char *) 0, ex.a_text+ex.a_data);
607 +                       read_exec(bprm->inode, N_TXTOFF(ex), 
608 +                                 (char *) N_TXTADDR(ex), ex.a_text+ex.a_data);
609                         goto beyond_if;
610                 }
611 -               error = do_mmap(file, 0, ex.a_text,
612 +               error = do_mmap(file, N_TXTADDR(ex), ex.a_text,
613                                 PROT_READ | PROT_EXEC,
614                                 MAP_FIXED | MAP_SHARED, N_TXTOFF(ex));
615 -               if (error != 0) {
616 +
617 +               if (error != N_TXTADDR(ex)) {
618                         sys_close(fd);
619                         send_sig(SIGSEGV, current, 0);
620                         return 0;
621                 };
622                 
623 -               error = do_mmap(file, ex.a_text, ex.a_data,
624 +               error = do_mmap(file, N_TXTADDR(ex) + ex.a_text, ex.a_data,
625                                 PROT_READ | PROT_WRITE | PROT_EXEC,
626                                 MAP_FIXED | MAP_PRIVATE, N_TXTOFF(ex) + ex.a_text);
627                 sys_close(fd);
628 -               if (error != ex.a_text) {
629 +               if (error != N_TXTADDR(ex) + ex.a_text) {
630                         send_sig(SIGSEGV, current, 0);
631                         return 0;
632                 };
633 @@ -775,7 +791,7 @@
634                 bprm->inode->i_count++;
635         }
636  beyond_if:
637 -       zeromap_page_range((ex.a_text + ex.a_data + 0xfff) & 0xfffff000,ex.a_bss, PAGE_COPY);
638 +       zeromap_page_range((N_TXTADDR(ex) + ex.a_text + ex.a_data + 0xfff) & 0xfffff000,ex.a_bss, PAGE_COPY);
639         p += change_ldt(ex.a_text,bprm->page);
640         p -= MAX_ARG_PAGES*PAGE_SIZE;
641         p = (unsigned long) create_tables((char *)p,bprm->argc,bprm->envc);
642 @@ -795,6 +811,7 @@
643         struct  inode * inode;
644         unsigned int len;
645         unsigned int bss;
646 +       unsigned int start_addr;
647         int error;
648         
649         file = current->filp[fd];
650 @@ -807,8 +824,8 @@
651         set_fs(USER_DS);
652         
653         /* We come in here for the regular a.out style of shared libraries */
654 -       if (N_MAGIC(ex) != ZMAGIC || ex.a_trsize ||
655 -           ex.a_drsize || ex.a_entry & 0xfff ||
656 +       if ((N_MAGIC(ex) != ZMAGIC && N_MAGIC(ex) != QMAGIC) || ex.a_trsize ||
657 +           ex.a_drsize || ((ex.a_entry & 0xfff) && N_MAGIC(ex) == ZMAGIC) ||
658             inode->i_size < ex.a_text+ex.a_data+ex.a_syms+N_TXTOFF(ex)) {
659                 return -ENOEXEC;
660         }
661 @@ -818,15 +835,22 @@
662                 return -ENOEXEC;
663         }
664         
665 +       if (N_FLAGS(ex)) return -ENOEXEC;
666 +
667 +       /* For  QMAGIC, the starting address is 0x20 into the page.  We mask
668 +          this off to get the starting address for the page */
669 +
670 +       start_addr =  ex.a_entry & 0xfffff000;
671 +
672         /* Now use mmap to map the library into memory. */
673 -       error = do_mmap(file, ex.a_entry, ex.a_text + ex.a_data,
674 +       error = do_mmap(file, start_addr, ex.a_text + ex.a_data,
675                         PROT_READ | PROT_WRITE | PROT_EXEC, MAP_FIXED | MAP_PRIVATE,
676                         N_TXTOFF(ex));
677 -       if (error != ex.a_entry)
678 +       if (error != start_addr)
679                 return error;
680         len = (ex.a_text + ex.a_data + 0xfff) & 0xfffff000;
681         bss = ex.a_text + ex.a_data + ex.a_bss;
682         if (bss > len)
683 -               zeromap_page_range(ex.a_entry + len, bss-len, PAGE_COPY);
684 +               zeromap_page_range(start_addr + len, bss-len, PAGE_COPY);
685         return 0;
686  }
687 diff -u --recursive --new-file pl12/linux/fs/ext2/namei.c linux/fs/ext2/namei.c
688 --- pl12/linux/fs/ext2/namei.c  Thu Aug 12 20:54:00 1993
689 +++ linux/fs/ext2/namei.c       Sat Aug 21 19:21:56 1993
690 @@ -937,6 +937,8 @@
691                 new_inode->i_nlink--;
692                 new_inode->i_dirt = 1;
693         }
694 +       old_dir->i_ctime = old_dir->i_mtime = CURRENT_TIME;
695 +       old_dir->i_dirt = 1;
696         old_bh->b_dirt = 1;
697         new_bh->b_dirt = 1;
698         if (dir_bh) {
699 diff -u --recursive --new-file pl12/linux/fs/fcntl.c linux/fs/fcntl.c
700 --- pl12/linux/fs/fcntl.c       Wed Jul  7 10:39:21 1993
701 +++ linux/fs/fcntl.c    Sat Sep  4 03:36:30 1993
702 @@ -35,7 +35,7 @@
703         return arg;
704  }
705  
706 -extern "C" int sys_dup2(unsigned int oldfd, unsigned int newfd)
707 +asmlinkage int sys_dup2(unsigned int oldfd, unsigned int newfd)
708  {
709         if (oldfd >= NR_OPEN || !current->filp[oldfd])
710                 return -EBADF;
711 @@ -58,12 +58,12 @@
712         return dupfd(oldfd,newfd);
713  }
714  
715 -extern "C" int sys_dup(unsigned int fildes)
716 +asmlinkage int sys_dup(unsigned int fildes)
717  {
718         return dupfd(fildes,0);
719  }
720  
721 -extern "C" int sys_fcntl(unsigned int fd, unsigned int cmd, unsigned long arg)
722 +asmlinkage int sys_fcntl(unsigned int fd, unsigned int cmd, unsigned long arg)
723  {      
724         struct file * filp;
725  
726 diff -u --recursive --new-file pl12/linux/fs/file_table.c linux/fs/file_table.c
727 --- pl12/linux/fs/file_table.c  Mon Aug  9 17:41:22 1993
728 +++ linux/fs/file_table.c       Tue Aug 17 18:32:13 1993
729 @@ -45,7 +45,7 @@
730         struct file * file;
731         int i;
732  
733 -       file = (struct file*) __get_free_page(GFP_BUFFER);
734 +       file = (struct file *) get_free_page(GFP_KERNEL);
735  
736         if (!file)
737                 return;
738 diff -u --recursive --new-file pl12/linux/fs/inode.c linux/fs/inode.c
739 --- pl12/linux/fs/inode.c       Mon Aug  9 17:41:22 1993
740 +++ linux/fs/inode.c    Tue Aug 17 18:41:05 1993
741 @@ -87,7 +87,7 @@
742         struct inode * inode;
743         int i;
744  
745 -       if(!(inode = (struct inode*) get_free_page(GFP_KERNEL)))
746 +       if (!(inode = (struct inode*) get_free_page(GFP_KERNEL)))
747                 return;
748  
749         i=PAGE_SIZE / sizeof(struct inode);
750 diff -u --recursive --new-file pl12/linux/fs/ioctl.c linux/fs/ioctl.c
751 --- pl12/linux/fs/ioctl.c       Sat Jul  3 01:07:31 1993
752 +++ linux/fs/ioctl.c    Sat Sep  4 03:36:30 1993
753 @@ -54,7 +54,7 @@
754  }
755  
756  
757 -extern "C" int sys_ioctl(unsigned int fd, unsigned int cmd, unsigned long arg)
758 +asmlinkage int sys_ioctl(unsigned int fd, unsigned int cmd, unsigned long arg)
759  {      
760         struct file * filp;
761         int on;
762 diff -u --recursive --new-file pl12/linux/fs/namei.c linux/fs/namei.c
763 --- pl12/linux/fs/namei.c       Mon Aug  9 18:02:29 1993
764 +++ linux/fs/namei.c    Sat Sep  4 03:36:30 1993
765 @@ -266,7 +266,7 @@
766   *
767   * namei for open - this is in fact almost the whole open-routine.
768   *
769 - * Note that the low bits of "flag" aren't the same asin the open
770 + * Note that the low bits of "flag" aren't the same as in the open
771   * system call - they are 00 - no permissions needed
772   *                       01 - read permission needed
773   *                       10 - write permission needed
774 @@ -369,6 +369,8 @@
775                                 return -ETXTBSY;
776                         }
777                         for(mpnt = (*p)->mmap; mpnt; mpnt = mpnt->vm_next) {
778 +                               if (mpnt->vm_page_prot & PAGE_RW)
779 +                                       continue;
780                                 if (inode == mpnt->vm_inode) {
781                                         iput(inode);
782                                         return -ETXTBSY;
783 @@ -376,6 +378,16 @@
784                         }
785                 }
786         }
787 +       if (flag & O_TRUNC) {
788 +             inode->i_size = 0;
789 +             if (inode->i_op && inode->i_op->truncate)
790 +                  inode->i_op->truncate(inode);
791 +             if ((error = notify_change(NOTIFY_SIZE, inode))) {
792 +                  iput(inode);
793 +                  return error;
794 +             }
795 +             inode->i_dirt = 1;
796 +       }
797         *res_inode = inode;
798         return 0;
799  }
800 @@ -409,7 +421,7 @@
801         return dir->i_op->mknod(dir,basename,namelen,mode,dev);
802  }
803  
804 -extern "C" int sys_mknod(const char * filename, int mode, dev_t dev)
805 +asmlinkage int sys_mknod(const char * filename, int mode, dev_t dev)
806  {
807         int error;
808         char * tmp;
809 @@ -452,7 +464,7 @@
810         return dir->i_op->mkdir(dir,basename,namelen,mode);
811  }
812  
813 -extern "C" int sys_mkdir(const char * pathname, int mode)
814 +asmlinkage int sys_mkdir(const char * pathname, int mode)
815  {
816         int error;
817         char * tmp;
818 @@ -493,7 +505,7 @@
819         return dir->i_op->rmdir(dir,basename,namelen);
820  }
821  
822 -extern "C" int sys_rmdir(const char * pathname)
823 +asmlinkage int sys_rmdir(const char * pathname)
824  {
825         int error;
826         char * tmp;
827 @@ -534,7 +546,7 @@
828         return dir->i_op->unlink(dir,basename,namelen);
829  }
830  
831 -extern "C" int sys_unlink(const char * pathname)
832 +asmlinkage int sys_unlink(const char * pathname)
833  {
834         int error;
835         char * tmp;
836 @@ -575,7 +587,7 @@
837         return dir->i_op->symlink(dir,basename,namelen,oldname);
838  }
839  
840 -extern "C" int sys_symlink(const char * oldname, const char * newname)
841 +asmlinkage int sys_symlink(const char * oldname, const char * newname)
842  {
843         int error;
844         char * from, * to;
845 @@ -631,7 +643,7 @@
846         return dir->i_op->link(oldinode, dir, basename, namelen);
847  }
848  
849 -extern "C" int sys_link(const char * oldname, const char * newname)
850 +asmlinkage int sys_link(const char * oldname, const char * newname)
851  {
852         int error;
853         char * to;
854 @@ -703,7 +715,7 @@
855                 new_dir, new_base, new_len);
856  }
857  
858 -extern "C" int sys_rename(const char * oldname, const char * newname)
859 +asmlinkage int sys_rename(const char * oldname, const char * newname)
860  {
861         int error;
862         char * from, * to;
863 diff -u --recursive --new-file pl12/linux/fs/nfs/mmap.c linux/fs/nfs/mmap.c
864 --- pl12/linux/fs/nfs/mmap.c    Sun Aug 15 11:46:03 1993
865 +++ linux/fs/nfs/mmap.c Sat Aug 21 10:31:31 1993
866 @@ -50,11 +50,9 @@
867  {
868         struct vm_area_struct * mpnt;
869  
870 -       if (off & (inode->i_sb->s_blocksize - 1))
871 +       if (prot & PAGE_RW)     /* only PAGE_COW or read-only supported now */
872                 return -EINVAL;
873 -       if (len > high_memory || off > high_memory - len) /* avoid overflow */
874 -               return -ENXIO;
875 -       if (get_limit(USER_DS) != TASK_SIZE)
876 +       if (off & (inode->i_sb->s_blocksize - 1))
877                 return -EINVAL;
878         if (!inode->i_sb || !S_ISREG(inode->i_mode))
879                 return -EACCES;
880 @@ -79,10 +77,6 @@
881         mpnt->vm_ops = &nfs_file_mmap;
882         mpnt->vm_next = current->mmap;
883         current->mmap = mpnt;
884 -#if 0
885 -       printk("VFS: Loaded mmap at %08x - %08x\n",
886 -               mpnt->vm_start, mpnt->vm_end);
887 -#endif
888         return 0;
889  }
890  
891 diff -u --recursive --new-file pl12/linux/fs/open.c linux/fs/open.c
892 --- pl12/linux/fs/open.c        Mon Aug  9 18:02:29 1993
893 +++ linux/fs/open.c     Sat Sep  4 03:35:17 1993
894 @@ -21,12 +21,12 @@
895  
896  extern void fcntl_remove_locks(struct task_struct *, struct file *);
897  
898 -extern "C" int sys_ustat(int dev, struct ustat * ubuf)
899 +asmlinkage int sys_ustat(int dev, struct ustat * ubuf)
900  {
901         return -ENOSYS;
902  }
903  
904 -extern "C" int sys_statfs(const char * path, struct statfs * buf)
905 +asmlinkage int sys_statfs(const char * path, struct statfs * buf)
906  {
907         struct inode * inode;
908         int error;
909 @@ -46,7 +46,7 @@
910         return 0;
911  }
912  
913 -extern "C" int sys_fstatfs(unsigned int fd, struct statfs * buf)
914 +asmlinkage int sys_fstatfs(unsigned int fd, struct statfs * buf)
915  {
916         struct inode * inode;
917         struct file * file;
918 @@ -65,7 +65,7 @@
919         return 0;
920  }
921  
922 -extern "C" int sys_truncate(const char * path, unsigned int length)
923 +asmlinkage int sys_truncate(const char * path, unsigned int length)
924  {
925         struct inode * inode;
926         int error;
927 @@ -91,7 +91,7 @@
928         return error;
929  }
930  
931 -extern "C" int sys_ftruncate(unsigned int fd, unsigned int length)
932 +asmlinkage int sys_ftruncate(unsigned int fd, unsigned int length)
933  {
934         struct inode * inode;
935         struct file * file;
936 @@ -114,7 +114,7 @@
937   * must be owner or have write permission.
938   * Else, update from *times, must be owner or super user.
939   */
940 -extern "C" int sys_utime(char * filename, struct utimbuf * times)
941 +asmlinkage int sys_utime(char * filename, struct utimbuf * times)
942  {
943         struct inode * inode;
944         long actime,modtime;
945 @@ -155,7 +155,7 @@
946   * XXX we should use the real ids for checking _all_ components of the
947   * path.  Now we only use them for the final component of the path.
948   */
949 -extern "C" int sys_access(const char * filename,int mode)
950 +asmlinkage int sys_access(const char * filename,int mode)
951  {
952         struct inode * inode;
953         int res, i_mode;
954 @@ -189,7 +189,7 @@
955         return -EACCES;
956  }
957  
958 -extern "C" int sys_chdir(const char * filename)
959 +asmlinkage int sys_chdir(const char * filename)
960  {
961         struct inode * inode;
962         int error;
963 @@ -210,7 +210,7 @@
964         return (0);
965  }
966  
967 -extern "C" int sys_chroot(const char * filename)
968 +asmlinkage int sys_chroot(const char * filename)
969  {
970         struct inode * inode;
971         int error;
972 @@ -231,7 +231,7 @@
973         return (0);
974  }
975  
976 -extern "C" int sys_fchmod(unsigned int fd, mode_t mode)
977 +asmlinkage int sys_fchmod(unsigned int fd, mode_t mode)
978  {
979         struct inode * inode;
980         struct file * file;
981 @@ -252,7 +252,7 @@
982         return notify_change(NOTIFY_MODE, inode);
983  }
984  
985 -extern "C" int sys_chmod(const char * filename, mode_t mode)
986 +asmlinkage int sys_chmod(const char * filename, mode_t mode)
987  {
988         struct inode * inode;
989         int error;
990 @@ -278,7 +278,7 @@
991         return error;
992  }
993  
994 -extern "C" int sys_fchown(unsigned int fd, uid_t user, gid_t group)
995 +asmlinkage int sys_fchown(unsigned int fd, uid_t user, gid_t group)
996  {
997         struct inode * inode;
998         struct file * file;
999 @@ -305,7 +305,7 @@
1000         return -EPERM;
1001  }
1002  
1003 -extern "C" int sys_chown(const char * filename, uid_t user, gid_t group)
1004 +asmlinkage int sys_chown(const char * filename, uid_t user, gid_t group)
1005  {
1006         struct inode * inode;
1007         int error;
1008 @@ -378,18 +378,7 @@
1009                 f->f_count--;
1010                 return error;
1011         }
1012 -       if (flag & O_TRUNC) {
1013 -               inode->i_size = 0;
1014 -               if (inode->i_op && inode->i_op->truncate)
1015 -                       inode->i_op->truncate(inode);
1016 -               if ((error = notify_change(NOTIFY_SIZE, inode))) {
1017 -                       iput(inode);
1018 -                       current->filp[fd] = NULL;
1019 -                       f->f_count--;
1020 -                       return error;
1021 -               }
1022 -               inode->i_dirt = 1;
1023 -       }
1024 +
1025         f->f_inode = inode;
1026         f->f_pos = 0;
1027         f->f_reada = 0;
1028 @@ -409,7 +398,7 @@
1029         return (fd);
1030  }
1031  
1032 -extern "C" int sys_open(const char * filename,int flags,int mode)
1033 +asmlinkage int sys_open(const char * filename,int flags,int mode)
1034  {
1035         char * tmp;
1036         int error;
1037 @@ -422,7 +411,7 @@
1038         return error;
1039  }
1040  
1041 -extern "C" int sys_creat(const char * pathname, int mode)
1042 +asmlinkage int sys_creat(const char * pathname, int mode)
1043  {
1044         return sys_open(pathname, O_CREAT | O_WRONLY | O_TRUNC, mode);
1045  }
1046 @@ -450,7 +439,7 @@
1047         return 0;
1048  }
1049  
1050 -extern "C" int sys_close(unsigned int fd)
1051 +asmlinkage int sys_close(unsigned int fd)
1052  {      
1053         struct file * filp;
1054  
1055 @@ -467,7 +456,7 @@
1056   * This routine simulates a hangup on the tty, to arrange that users
1057   * are given clean terminals at login time.
1058   */
1059 -extern "C" int sys_vhangup(void)
1060 +asmlinkage int sys_vhangup(void)
1061  {
1062         struct tty_struct *tty;
1063  
1064 diff -u --recursive --new-file pl12/linux/fs/pipe.c linux/fs/pipe.c
1065 --- pl12/linux/fs/pipe.c        Sun Jul 18 18:19:42 1993
1066 +++ linux/fs/pipe.c     Sat Sep  4 03:36:30 1993
1067 @@ -288,7 +288,7 @@
1068         NULL                    /* permission */
1069  };
1070  
1071 -extern "C" int sys_pipe(unsigned long * fildes)
1072 +asmlinkage int sys_pipe(unsigned long * fildes)
1073  {
1074         struct inode * inode;
1075         struct file * f[2];
1076 diff -u --recursive --new-file pl12/linux/fs/proc/array.c linux/fs/proc/array.c
1077 --- pl12/linux/fs/proc/array.c  Mon Aug  9 18:02:29 1993
1078 +++ linux/fs/proc/array.c       Fri Aug 20 09:40:57 1993
1079 @@ -194,7 +194,7 @@
1080         if (vsize) {
1081                 eip = KSTK_EIP(vsize);
1082                 esp = KSTK_ESP(vsize);
1083 -               vsize = (*p)->brk + PAGE_SIZE-1;
1084 +               vsize = (*p)->brk - (*p)->start_code + PAGE_SIZE-1;
1085                 if (esp)
1086                         vsize += TASK_SIZE - esp;
1087         }
1088 @@ -264,7 +264,7 @@
1089                 return 0;
1090         tpag = (*p)->end_code / PAGE_SIZE;
1091         if ((*p)->state != TASK_ZOMBIE) {
1092 -         pagedir = PAGE_DIR_OFFSET((*p)->tss.cr3,(*p)->start_code);
1093 +         pagedir = (unsigned long *) (*p)->tss.cr3;
1094           for (i = 0; i < 0x300; ++i) {
1095             if ((ptbl = pagedir[i]) == 0) {
1096               tpag -= PTRS_PER_PAGE;
1097 diff -u --recursive --new-file pl12/linux/fs/proc/kmsg.c linux/fs/proc/kmsg.c
1098 --- pl12/linux/fs/proc/kmsg.c   Sat Jul  3 01:31:56 1993
1099 +++ linux/fs/proc/kmsg.c        Sat Sep  4 03:39:22 1993
1100 @@ -17,7 +17,7 @@
1101  extern unsigned long log_size;
1102  extern struct wait_queue * log_wait;
1103  
1104 -extern "C" int sys_syslog(int type, char * bug, int count);
1105 +asmlinkage int sys_syslog(int type, char * bug, int count);
1106  
1107  static int kmsg_open(struct inode * inode, struct file * file)
1108  {
1109 diff -u --recursive --new-file pl12/linux/fs/read_write.c linux/fs/read_write.c
1110 --- pl12/linux/fs/read_write.c  Sat Jul  3 01:05:39 1993
1111 +++ linux/fs/read_write.c       Sat Sep  4 03:36:30 1993
1112 @@ -16,7 +16,7 @@
1113   * Count is not yet used: but we'll probably support reading several entries
1114   * at once in the future. Use count=1 in the library for future expansions.
1115   */
1116 -extern "C" int sys_readdir(unsigned int fd, struct dirent * dirent, unsigned int count)
1117 +asmlinkage int sys_readdir(unsigned int fd, struct dirent * dirent, unsigned int count)
1118  {
1119         int error;
1120         struct file * file;
1121 @@ -34,7 +34,7 @@
1122         return error;
1123  }
1124  
1125 -extern "C" int sys_lseek(unsigned int fd, off_t offset, unsigned int origin)
1126 +asmlinkage int sys_lseek(unsigned int fd, off_t offset, unsigned int origin)
1127  {
1128         struct file * file;
1129         int tmp = -1;
1130 @@ -67,7 +67,7 @@
1131         return file->f_pos;
1132  }
1133  
1134 -extern "C" int sys_read(unsigned int fd,char * buf,unsigned int count)
1135 +asmlinkage int sys_read(unsigned int fd,char * buf,unsigned int count)
1136  {
1137         int error;
1138         struct file * file;
1139 @@ -87,7 +87,7 @@
1140         return file->f_op->read(inode,file,buf,count);
1141  }
1142  
1143 -extern "C" int sys_write(unsigned int fd,char * buf,unsigned int count)
1144 +asmlinkage int sys_write(unsigned int fd,char * buf,unsigned int count)
1145  {
1146         int error;
1147         struct file * file;
1148 diff -u --recursive --new-file pl12/linux/fs/select.c linux/fs/select.c
1149 --- pl12/linux/fs/select.c      Mon Aug  9 18:02:30 1993
1150 +++ linux/fs/select.c   Sat Sep  4 03:36:30 1993
1151 @@ -192,7 +192,7 @@
1152   * Update: ERESTARTSYS breaks at least the xview clock binary, so
1153   * I'm trying ERESTARTNOHAND which restart only when you want to.
1154   */
1155 -extern "C" int sys_select( unsigned long *buffer )
1156 +asmlinkage int sys_select( unsigned long *buffer )
1157  {
1158  /* Perform the select(nd, in, out, ex, tv) system call. */
1159         int i;
1160 diff -u --recursive --new-file pl12/linux/fs/stat.c linux/fs/stat.c
1161 --- pl12/linux/fs/stat.c        Sat Jul  3 01:04:26 1993
1162 +++ linux/fs/stat.c     Sat Sep  4 03:36:30 1993
1163 @@ -86,7 +86,7 @@
1164         memcpy_tofs(statbuf,&tmp,sizeof(tmp));
1165  }
1166  
1167 -extern "C" int sys_stat(char * filename, struct old_stat * statbuf)
1168 +asmlinkage int sys_stat(char * filename, struct old_stat * statbuf)
1169  {
1170         struct inode * inode;
1171         int error;
1172 @@ -102,7 +102,7 @@
1173         return 0;
1174  }
1175  
1176 -extern "C" int sys_newstat(char * filename, struct new_stat * statbuf)
1177 +asmlinkage int sys_newstat(char * filename, struct new_stat * statbuf)
1178  {
1179         struct inode * inode;
1180         int error;
1181 @@ -118,7 +118,7 @@
1182         return 0;
1183  }
1184  
1185 -extern "C" int sys_lstat(char * filename, struct old_stat * statbuf)
1186 +asmlinkage int sys_lstat(char * filename, struct old_stat * statbuf)
1187  {
1188         struct inode * inode;
1189         int error;
1190 @@ -134,7 +134,7 @@
1191         return 0;
1192  }
1193  
1194 -extern "C" int sys_newlstat(char * filename, struct new_stat * statbuf)
1195 +asmlinkage int sys_newlstat(char * filename, struct new_stat * statbuf)
1196  {
1197         struct inode * inode;
1198         int error;
1199 @@ -150,7 +150,7 @@
1200         return 0;
1201  }
1202  
1203 -extern "C" int sys_fstat(unsigned int fd, struct old_stat * statbuf)
1204 +asmlinkage int sys_fstat(unsigned int fd, struct old_stat * statbuf)
1205  {
1206         struct file * f;
1207         struct inode * inode;
1208 @@ -165,7 +165,7 @@
1209         return 0;
1210  }
1211  
1212 -extern "C" int sys_newfstat(unsigned int fd, struct new_stat * statbuf)
1213 +asmlinkage int sys_newfstat(unsigned int fd, struct new_stat * statbuf)
1214  {
1215         struct file * f;
1216         struct inode * inode;
1217 @@ -180,7 +180,7 @@
1218         return 0;
1219  }
1220  
1221 -extern "C" int sys_readlink(const char * path, char * buf, int bufsiz)
1222 +asmlinkage int sys_readlink(const char * path, char * buf, int bufsiz)
1223  {
1224         struct inode * inode;
1225         int error;
1226 diff -u --recursive --new-file pl12/linux/fs/super.c linux/fs/super.c
1227 --- pl12/linux/fs/super.c       Wed Aug 11 20:56:05 1993
1228 +++ linux/fs/super.c    Sat Sep  4 03:36:30 1993
1229 @@ -243,7 +243,7 @@
1230   * functions, they should be faked here.  -- jrs
1231   */
1232  
1233 -extern "C" int sys_umount(char * name)
1234 +asmlinkage int sys_umount(char * name)
1235  {
1236         struct inode * inode;
1237         dev_t dev;
1238 @@ -390,7 +390,7 @@
1239   * isn't present, the flags and data info isn't used, as the syscall assumes we
1240   * are talking to an older version that didn't understand them.
1241   */
1242 -extern "C" int sys_mount(char * dev_name, char * dir_name, char * type,
1243 +asmlinkage int sys_mount(char * dev_name, char * dir_name, char * type,
1244         unsigned long new_flags, void * data)
1245  {
1246         struct file_system_type * fstype;
1247 diff -u --recursive --new-file pl12/linux/ibcs/emulate.c linux/ibcs/emulate.c
1248 --- pl12/linux/ibcs/emulate.c   Sat Jul  3 00:36:31 1993
1249 +++ linux/ibcs/emulate.c        Sat Sep  4 14:29:34 1993
1250 @@ -20,7 +20,7 @@
1251  #include <asm/segment.h>
1252  #include <asm/system.h>
1253  
1254 -extern "C" void iABI_emulate(struct pt_regs * regs)
1255 +asmlinkage void iABI_emulate(struct pt_regs * regs)
1256  {
1257         printk("lcall 7,xxx: eax = %08x\n",regs->eax);
1258  }
1259 diff -u --recursive --new-file pl12/linux/include/asm/irq.h linux/include/asm/irq.h
1260 --- pl12/linux/include/asm/irq.h        Sun Jul 18 17:19:24 1993
1261 +++ linux/include/asm/irq.h     Sat Sep  4 03:00:24 1993
1262 @@ -8,6 +8,8 @@
1263   */
1264  
1265  #include <linux/segment.h>
1266 +#include <linux/linkage.h>
1267 +
1268  #define __STR(x) #x
1269  #define STR(x) __STR(x)
1270   
1271 @@ -117,9 +119,9 @@
1272  #define BAD_IRQ_NAME(nr) IRQ_NAME2(bad_IRQ##nr)
1273         
1274  #define BUILD_IRQ(chip,nr,mask) \
1275 -extern "C" void IRQ_NAME(nr); \
1276 -extern "C" void FAST_IRQ_NAME(nr); \
1277 -extern "C" void BAD_IRQ_NAME(nr); \
1278 +asmlinkage void IRQ_NAME(nr); \
1279 +asmlinkage void FAST_IRQ_NAME(nr); \
1280 +asmlinkage void BAD_IRQ_NAME(nr); \
1281  __asm__( \
1282  "\n.align 4\n" \
1283  "_IRQ" #nr "_interrupt:\n\t" \
1284 diff -u --recursive --new-file pl12/linux/include/asm/segment.h linux/include/asm/segment.h
1285 --- pl12/linux/include/asm/segment.h    Mon Aug  2 14:31:28 1993
1286 +++ linux/include/asm/segment.h Sat Sep  4 03:02:56 1993
1287 @@ -1,7 +1,7 @@
1288  #ifndef _ASM_SEGMENT_H
1289  #define _ASM_SEGMENT_H
1290  
1291 -static inline unsigned char get_fs_byte(const char * addr)
1292 +static inline unsigned char get_user_byte(const char * addr)
1293  {
1294         register unsigned char _v;
1295  
1296 @@ -9,23 +9,9 @@
1297         return _v;
1298  }
1299  
1300 -static inline unsigned char get_fs_byte(const unsigned char * addr)
1301 -{
1302 -       register unsigned char _v;
1303 -
1304 -       __asm__ ("movb %%fs:%1,%0":"=q" (_v):"m" (*addr));
1305 -       return _v;
1306 -}
1307 -
1308 -static inline unsigned short get_fs_word(const short *addr)
1309 -{
1310 -       unsigned short _v;
1311 -
1312 -       __asm__ ("movw %%fs:%1,%0":"=r" (_v):"m" (*addr));
1313 -       return _v;
1314 -}
1315 +#define get_fs_byte(addr) get_user_byte((char *)(addr))
1316  
1317 -static inline unsigned short get_fs_word(const unsigned short *addr)
1318 +static inline unsigned short get_user_word(const short *addr)
1319  {
1320         unsigned short _v;
1321  
1322 @@ -33,31 +19,9 @@
1323         return _v;
1324  }
1325  
1326 -static inline unsigned long get_fs_long(const int *addr)
1327 -{
1328 -       unsigned long _v;
1329 -
1330 -       __asm__ ("movl %%fs:%1,%0":"=r" (_v):"m" (*addr)); \
1331 -       return _v;
1332 -}
1333 -
1334 -static inline unsigned long get_fs_long(const unsigned int *addr)
1335 -{
1336 -       unsigned long _v;
1337 -
1338 -       __asm__ ("movl %%fs:%1,%0":"=r" (_v):"m" (*addr)); \
1339 -       return _v;
1340 -}
1341 -
1342 -static inline unsigned long get_fs_long(const long *addr)
1343 -{
1344 -       unsigned long _v;
1345 -
1346 -       __asm__ ("movl %%fs:%1,%0":"=r" (_v):"m" (*addr)); \
1347 -       return _v;
1348 -}
1349 +#define get_fs_word(addr) get_user_word((short *)(addr))
1350  
1351 -static inline unsigned long get_fs_long(const unsigned long *addr)
1352 +static inline unsigned long get_user_long(const int *addr)
1353  {
1354         unsigned long _v;
1355  
1356 @@ -65,45 +29,28 @@
1357         return _v;
1358  }
1359  
1360 -static inline void put_fs_byte(char val,char *addr)
1361 -{
1362 -__asm__ ("movb %0,%%fs:%1": /* no outputs */ :"iq" (val),"m" (*addr));
1363 -}
1364 +#define get_fs_long(addr) get_user_long((int *)(addr))
1365  
1366 -static inline void put_fs_byte(char val,unsigned char *addr)
1367 +static inline void put_user_byte(char val,char *addr)
1368  {
1369  __asm__ ("movb %0,%%fs:%1": /* no outputs */ :"iq" (val),"m" (*addr));
1370  }
1371  
1372 -static inline void put_fs_word(short val,short * addr)
1373 -{
1374 -__asm__ ("movw %0,%%fs:%1": /* no outputs */ :"ir" (val),"m" (*addr));
1375 -}
1376 +#define put_fs_byte(x,addr) put_user_byte((x),(char *)(addr))
1377  
1378 -static inline void put_fs_word(short val,unsigned short * addr)
1379 +static inline void put_user_word(short val,short * addr)
1380  {
1381  __asm__ ("movw %0,%%fs:%1": /* no outputs */ :"ir" (val),"m" (*addr));
1382  }
1383  
1384 -static inline void put_fs_long(unsigned long val,int * addr)
1385 -{
1386 -__asm__ ("movl %0,%%fs:%1": /* no outputs */ :"ir" (val),"m" (*addr));
1387 -}
1388 -
1389 -static inline void put_fs_long(unsigned long val,unsigned int * addr)
1390 -{
1391 -__asm__ ("movl %0,%%fs:%1": /* no outputs */ :"ir" (val),"m" (*addr));
1392 -}
1393 +#define put_fs_word(x,addr) put_user_word((x),(short *)(addr))
1394  
1395 -static inline void put_fs_long(unsigned long val,long * addr)
1396 +static inline void put_user_long(unsigned long val,int * addr)
1397  {
1398  __asm__ ("movl %0,%%fs:%1": /* no outputs */ :"ir" (val),"m" (*addr));
1399  }
1400  
1401 -static inline void put_fs_long(unsigned long val,unsigned long * addr)
1402 -{
1403 -__asm__ ("movl %0,%%fs:%1": /* no outputs */ :"ir" (val),"m" (*addr));
1404 -}
1405 +#define put_fs_long(x,addr) put_user_long((x),(int *)(addr))
1406  
1407  static inline void memcpy_tofs(void * to, const void * from, unsigned long n)
1408  {
1409 diff -u --recursive --new-file pl12/linux/include/linux/a.out.h linux/include/linux/a.out.h
1410 --- pl12/linux/include/linux/a.out.h    Mon Aug  9 17:41:23 1993
1411 +++ linux/include/linux/a.out.h Fri Aug 20 08:59:31 1993
1412 @@ -71,24 +71,26 @@
1413  #define NMAGIC 0410
1414  /* Code indicating demand-paged executable.  */
1415  #define ZMAGIC 0413
1416 +/* This indicates a demand-paged executable with the header in the text. 
1417 +   The first page is unmapped to help trap NULL pointer references */
1418 +#define QMAGIC 0314
1419  
1420  /* Code indicating core file.  */
1421  #define CMAGIC 0421
1422 +
1423  #if !defined (N_BADMAG)
1424 -#define N_BADMAG(x)                                    \
1425 - (N_MAGIC(x) != OMAGIC && N_MAGIC(x) != NMAGIC         \
1426 -  && N_MAGIC(x) != ZMAGIC)
1427 +#define N_BADMAG(x)      (N_MAGIC(x) != OMAGIC         \
1428 +                       && N_MAGIC(x) != NMAGIC         \
1429 +                       && N_MAGIC(x) != ZMAGIC \
1430 +                       && N_MAGIC(x) != QMAGIC)
1431  #endif
1432  
1433 -#define _N_BADMAG(x)                                   \
1434 - (N_MAGIC(x) != OMAGIC && N_MAGIC(x) != NMAGIC         \
1435 -  && N_MAGIC(x) != ZMAGIC)
1436 -
1437  #define _N_HDROFF(x) (1024 - sizeof (struct exec))
1438  
1439  #if !defined (N_TXTOFF)
1440  #define N_TXTOFF(x) \
1441 - (N_MAGIC(x) == ZMAGIC ? _N_HDROFF((x)) + sizeof (struct exec) : sizeof (struct exec))
1442 + (N_MAGIC(x) == ZMAGIC ? _N_HDROFF((x)) + sizeof (struct exec) : \
1443 +  (N_MAGIC(x) == QMAGIC ? 0 : sizeof (struct exec)))
1444  #endif
1445  
1446  #if !defined (N_DATOFF)
1447 @@ -113,7 +115,7 @@
1448  
1449  /* Address of text segment in memory after it is loaded.  */
1450  #if !defined (N_TXTADDR)
1451 -#define N_TXTADDR(x) 0
1452 +#define N_TXTADDR(x) (N_MAGIC(x) == QMAGIC ? PAGE_SIZE : 0)
1453  #endif
1454  
1455  /* Address of data segment in memory after it is loaded.
1456 diff -u --recursive --new-file pl12/linux/include/linux/binfmts.h linux/include/linux/binfmts.h
1457 --- pl12/linux/include/linux/binfmts.h  Fri Aug  6 13:32:00 1993
1458 +++ linux/include/linux/binfmts.h       Sat Sep  4 03:39:51 1993
1459 @@ -1,6 +1,8 @@
1460  #ifndef _LINUX_BINFMTS_H
1461  #define _LINUX_BINFMTS_H
1462  
1463 +#include <linux/ptrace.h>
1464 +
1465  /*
1466   * MAX_ARG_PAGES defines the number of pages allocated for arguments
1467   * and envelope for the new program. 32 should suffice, this gives
1468 @@ -15,6 +17,7 @@
1469    char buf[128];
1470    unsigned long page[MAX_ARG_PAGES];
1471    unsigned long p;
1472 +  int sh_bang;
1473    struct inode * inode;
1474    int e_uid, e_gid;
1475    int argc, envc;
1476 @@ -31,6 +34,15 @@
1477  
1478  extern struct linux_binfmt formats[];
1479  
1480 +extern int read_exec(struct inode *inode, unsigned long offset,
1481 +       char * addr, unsigned long count);
1482 +
1483 +extern int open_inode(struct inode * inode, int mode);
1484  
1485 +extern void flush_old_exec(struct linux_binprm * bprm);
1486 +extern unsigned long change_ldt(unsigned long text_size,unsigned long * page);
1487 +extern unsigned long * create_tables(char * p,int argc,int envc);
1488 +extern unsigned long copy_strings(int argc,char ** argv,unsigned long *page,
1489 +               unsigned long p, int from_kmem);
1490  
1491  #endif
1492 diff -u --recursive --new-file pl12/linux/include/linux/elf.h linux/include/linux/elf.h
1493 --- pl12/linux/include/linux/elf.h
1494 +++ linux/include/linux/elf.h   Sat Sep  4 01:48:20 1993
1495 @@ -0,0 +1,153 @@
1496 +#ifndef _ELF_H
1497 +#define _ELF_H
1498 +
1499 +/* THese constants are for the segment types stored in the image headers */
1500 +#define PT_NULL    0
1501 +#define PT_LOAD    1
1502 +#define PT_DYNAMIC 2
1503 +#define PT_INTERP  3
1504 +#define PT_NOTE    4
1505 +#define PT_SHLIB   5
1506 +#define PT_PHDR    6
1507 +#define PT_LOPROC  0x70000000
1508 +#define PT_HIPROC  0x7fffffff
1509 +
1510 +/* These constants define the different elf file types */
1511 +#define ET_NONE   0
1512 +#define ET_REL    1
1513 +#define ET_EXEC   2
1514 +#define ET_DYN    3
1515 +#define ET_CORE   4
1516 +#define ET_LOPROC 5
1517 +#define ET_HIPROC 6
1518 +
1519 +/* These constants define the various ELF target machines */
1520 +#define EM_NONE  0
1521 +#define EM_M32   1
1522 +#define EM_SPARC 2
1523 +#define EM_386   3
1524 +#define EM_68K   4
1525 +#define EM_88K   5
1526 +#define EM_486   6   /* Perhaps disused */
1527 +#define EM_860   7
1528 +
1529 +/* This is the info that is needed to parse the dynamic section of the file */
1530 +#define DT_NULL                0
1531 +#define DT_NEEDED      1
1532 +#define DT_PLTRELSZ    2
1533 +#define DT_PLTGOT      3
1534 +#define DT_HASH                4
1535 +#define DT_STRTAB      5
1536 +#define DT_SYMTAB      6
1537 +#define DT_RELA                7
1538 +#define DT_RELASZ      8
1539 +#define DT_RELAENT     9
1540 +#define DT_STRSZ       10
1541 +#define DT_SYMENT      11
1542 +#define DT_INIT                12
1543 +#define DT_FINI                13
1544 +#define DT_SONAME      14
1545 +#define DT_RPATH       15
1546 +#define DT_SYMBOLIC    16
1547 +#define DT_REL         17
1548 +#define DT_RELSZ       18
1549 +#define DT_RELENT      19
1550 +#define DT_PLTREL      20
1551 +#define DT_DEBUG       21
1552 +#define DT_TEXTREL     22
1553 +#define DT_JMPREL      23
1554 +#define DT_LOPROC      0x70000000
1555 +#define DT_HIPROC      0x7fffffff
1556 +
1557 +/* This info is needed when parsing the symbol table */
1558 +#define STB_LOCAL  0
1559 +#define STB_GLOBAL 1
1560 +#define STB_WEAK   2
1561 +
1562 +#define STT_NOTYPE  0
1563 +#define STT_OBJECT  1
1564 +#define STT_FUNC    2
1565 +#define STT_SECTION 3
1566 +#define STT_FILE    4
1567 +
1568 +#define ELF32_ST_BIND(x) ((x) >> 4)
1569 +#define ELF32_ST_TYPE(x) (((unsigned int) x) & 0xf)
1570 +
1571 +
1572 +
1573 +struct dynamic{
1574 +  int d_tag;
1575 +  union{
1576 +    int d_val;
1577 +    char * d_ptr;
1578 +  } d_un;
1579 +};
1580 +
1581 +/* THe following are used with relocations */
1582 +#define ELF32_R_SYM(x) ((x) >> 8)
1583 +#define ELF32_R_TYPE(x) ((x) & 0xff)
1584 +
1585 +#define R_386_NONE     0
1586 +#define R_386_32       1
1587 +#define R_386_PC32     2
1588 +#define R_386_GOT32    3
1589 +#define R_386_PLT32    4
1590 +#define R_386_COPY     5
1591 +#define R_386_GLOB_DAT 6
1592 +#define R_386_JMP_SLOT 7
1593 +#define R_386_RELATIVE 8
1594 +#define R_386_GOTOFF   9
1595 +#define R_386_GOTPC    10
1596 +#define R_386_NUM      11
1597 +
1598 +struct Elf32_Rel{
1599 +  unsigned int * offset;
1600 +  int info;
1601 +};
1602 +
1603 +struct Elf32_Rela{
1604 +  unsigned int * offset;
1605 +  int info;
1606 +  int addend;
1607 +};
1608 +
1609 +struct Elf32_Sym{
1610 +  int st_name;
1611 +  unsigned int st_value;
1612 +  int st_size;
1613 +  unsigned char st_info;
1614 +  unsigned char st_other;
1615 +  short int st_shndx;
1616 +};
1617 +
1618 +struct elfhdr{
1619 +  char e_ident[16];
1620 +  short int e_type;
1621 +  short int e_machine;
1622 +  int   e_version;
1623 +  char *e_entry;  /* Entry point */
1624 +  int   e_phoff;
1625 +  int   e_shoff;
1626 +  int   e_flags;
1627 +  short int e_ehsize;
1628 +  short int e_phentsize;
1629 +  short int e_phnum;
1630 +  short int e_shentsize;
1631 +  short int e_shnum;
1632 +  short int e_shstrndx;
1633 +};
1634 +
1635 +struct elf_phdr{
1636 +  int p_type;
1637 +  int p_offset;
1638 +  int p_vaddr;
1639 +  int p_paddr;
1640 +  int p_filesz;
1641 +  int p_memsz;
1642 +  int p_flags;
1643 +  int p_align;
1644 +};
1645 +
1646 +#define ELF_START_MMAP 0x80000000
1647 +
1648 +#endif
1649 diff -u --recursive --new-file pl12/linux/include/linux/fs.h linux/include/linux/fs.h
1650 --- pl12/linux/include/linux/fs.h       Wed Aug 11 22:52:45 1993
1651 +++ linux/include/linux/fs.h    Sat Sep  4 02:55:18 1993
1652 @@ -6,6 +6,7 @@
1653   * structures etc.
1654   */
1655  
1656 +#include <linux/linkage.h>
1657  #include <linux/limits.h>
1658  #include <linux/wait.h>
1659  #include <linux/types.h>
1660 @@ -319,8 +320,8 @@
1661  
1662  #ifdef __KERNEL__
1663  
1664 -extern "C" int sys_open(const char *, int, int);
1665 -extern "C" int sys_close(unsigned int);                /* yes, it's really unsigned */
1666 +asmlinkage int sys_open(const char *, int, int);
1667 +asmlinkage int sys_close(unsigned int);                /* yes, it's really unsigned */
1668  
1669  extern int getname(const char * filename, char **result);
1670  extern void putname(char * name);
1671 diff -u --recursive --new-file pl12/linux/include/linux/ioport.h linux/include/linux/ioport.h
1672 --- pl12/linux/include/linux/ioport.h
1673 +++ linux/include/linux/ioport.h        Wed Sep  1 17:39:36 1993
1674 @@ -0,0 +1,28 @@
1675 +/*
1676 + * portio.h    Definitions of routines for detecting, reserving and
1677 + *             allocating system resources.
1678 + *
1679 + * Version:    0.01    8/30/93
1680 + *
1681 + * Author:     Donald Becker (becker@super.org)
1682 + */
1683 +
1684 +#ifndef _LINUX_PORTIO_H
1685 +#define _LINUX_PORTIO_H
1686 +
1687 +#define HAVE_PORTRESERVE
1688 +/*
1689 + * Call check_region() before probing for your hardware.
1690 + * Once you have found you hardware, register it with snarf_region().
1691 + */
1692 +extern void reserve_setup(char *str, int *ints);
1693 +extern int check_region(unsigned int from, unsigned int extent);
1694 +extern void snarf_region(unsigned int from, unsigned int extent);
1695 +
1696 +
1697 +#define HAVE_AUTOIRQ
1698 +extern void *irq2dev_map[16];          /* Use only if you own the IRQ. */
1699 +extern void autoirq_setup(int waittime);
1700 +extern int autoirq_report(int waittime);
1701 +
1702 +#endif /* _LINUX_PORTIO_H */
1703 diff -u --recursive --new-file pl12/linux/include/linux/kernel.h linux/include/linux/kernel.h
1704 --- pl12/linux/include/linux/kernel.h   Mon Aug  9 18:02:30 1993
1705 +++ linux/include/linux/kernel.h        Sat Sep  4 02:56:46 1993
1706 @@ -8,6 +8,7 @@
1707  #ifdef __KERNEL__
1708  
1709  #include <linux/config.h>
1710 +#include <linux/linkage.h>
1711  
1712  #define INT_MAX                ((int)(~0U>>1))
1713  #define UINT_MAX       (~0U)
1714 @@ -25,7 +26,7 @@
1715  unsigned long simple_strtoul(const char *,char **,unsigned int);
1716  int sprintf(char * buf, const char * fmt, ...);
1717  
1718 -extern "C" int printk(const char * fmt, ...);
1719 +asmlinkage int printk(const char * fmt, ...);
1720  
1721  #ifdef CONFIG_DEBUG_MALLOC
1722  #define kmalloc(a,b) deb_kmalloc(__FILE__,__LINE__, a,b)
1723 diff -u --recursive --new-file pl12/linux/include/linux/linkage.h linux/include/linux/linkage.h
1724 --- pl12/linux/include/linux/linkage.h
1725 +++ linux/include/linux/linkage.h       Sat Sep  4 02:56:10 1993
1726 @@ -0,0 +1,10 @@
1727 +#ifndef _LINUX_LINKAGE_H
1728 +#define _LINUX_LINKAGE_H
1729 +
1730 +#ifdef __cplusplus
1731 +#define asmlinkage extern "C"
1732 +#else
1733 +#define asmlinkage
1734 +#endif
1735 +
1736 +#endif
1737 diff -u --recursive --new-file pl12/linux/include/linux/page.h linux/include/linux/page.h
1738 --- pl12/linux/include/linux/page.h     Mon Aug  9 18:02:30 1993
1739 +++ linux/include/linux/page.h  Sat Sep  4 03:09:00 1993
1740 @@ -25,7 +25,7 @@
1741    ((unsigned long)(address)>>(PAGE_SHIFT-SIZEOF_PTR_LOG2)*2&PTR_MASK&~PAGE_MASK)))
1742                         /* to find an entry in a page-table */
1743  #define PAGE_PTR(address)              \
1744 -  ((unsigned long)(address)>>PAGE_SHIFT-SIZEOF_PTR_LOG2&PTR_MASK&~PAGE_MASK)
1745 +  ((unsigned long)(address)>>(PAGE_SHIFT-SIZEOF_PTR_LOG2)&PTR_MASK&~PAGE_MASK)
1746                         /* the no. of pointers that fit on a page */
1747  #define PTRS_PER_PAGE                  (PAGE_SIZE/sizeof(void*))
1748  
1749 diff -u --recursive --new-file pl12/linux/include/linux/sched.h linux/include/linux/sched.h
1750 --- pl12/linux/include/linux/sched.h    Sat Aug 14 16:01:26 1993
1751 +++ linux/include/linux/sched.h Sat Sep  4 02:42:39 1993
1752 @@ -85,7 +85,7 @@
1753  extern void trap_init(void);
1754  extern void panic(const char * str);
1755  
1756 -extern "C" void schedule(void);
1757 +asmlinkage void schedule(void);
1758  
1759  #endif /* __KERNEL__ */
1760  
1761 diff -u --recursive --new-file pl12/linux/include/linux/shm.h linux/include/linux/shm.h
1762 --- pl12/linux/include/linux/shm.h      Mon Aug  9 18:02:30 1993
1763 +++ linux/include/linux/shm.h   Sun Aug 29 23:26:57 1993
1764 @@ -63,11 +63,11 @@
1765  #define SHM_IDX_MASK   ((1<<_SHM_IDX_BITS)-1)
1766  #define SHM_READ_ONLY  (1<<BITS_PER_PTR-1)
1767  
1768 -#define SHMMAX (1<<PAGE_SHIFT+_SHM_IDX_BITS)   /* max shared seg size (bytes) */
1769 -#define SHMMIN 1        /* really PAGE_SIZE */ /* min shared seg size (bytes)*/
1770 +#define SHMMAX 0x400000                                /* max shared seg size (bytes) */
1771 +#define SHMMIN 1        /* really PAGE_SIZE */ /* min shared seg size (bytes) */
1772  #define SHMMNI (1<<_SHM_ID_BITS)               /* max num of segs system wide */
1773  #define SHMALL (1<<_SHM_IDX_BITS+_SHM_ID_BITS) /* max shm system wide (pages) */
1774 -#define        SHMLBA PAGE_SIZE                        /* attach addr a multiple of this */
1775 +#define        SHMLBA 0x1000                           /* attach addr a multiple of this */
1776  #define SHMSEG SHMMNI                          /* max shared segs per process */
1777  
1778  #ifdef __KERNEL__
1779 diff -u --recursive --new-file pl12/linux/include/linux/signal.h linux/include/linux/signal.h
1780 --- pl12/linux/include/linux/signal.h   Thu May 20 10:34:30 1993
1781 +++ linux/include/linux/signal.h        Mon Aug 16 18:55:12 1993
1782 @@ -53,6 +53,9 @@
1783  */
1784  #define SIGPWR         30
1785  
1786 +/* Arggh. Bad user source code wants this.. */
1787 +#define SIGBUS         SIGUNUSED
1788 +
1789  /*
1790   * sa_flags values: SA_STACK is not currently supported, but will allow the
1791   * usage of signal stacks by using the (now obsolete) sa_restorer field in
1792 diff -u --recursive --new-file pl12/linux/include/linux/sys.h linux/include/linux/sys.h
1793 --- pl12/linux/include/linux/sys.h      Tue Jul 20 01:35:31 1993
1794 +++ linux/include/linux/sys.h   Sat Sep  4 02:43:53 1993
1795 @@ -4,7 +4,9 @@
1796  
1797  #define sys_clone sys_fork
1798  
1799 +#ifdef __cplusplus
1800  extern "C" {
1801 +#endif
1802  
1803  extern int sys_setup();
1804  extern int sys_exit();
1805 @@ -170,7 +172,9 @@
1806  sys_wait4, sys_swapoff, sys_sysinfo, sys_ipc, sys_fsync, sys_sigreturn,
1807  sys_clone, sys_setdomainname, sys_newuname, sys_modify_ldt};
1808  
1809 +#ifdef __cplusplus
1810  }
1811 +#endif
1812  
1813  /* So we don't have to do any more manual updating.... */
1814  int NR_syscalls = sizeof(sys_call_table)/sizeof(fn_ptr);
1815 diff -u --recursive --new-file pl12/linux/include/linux/tasks.h linux/include/linux/tasks.h
1816 --- pl12/linux/include/linux/tasks.h    Mon Jan 18 22:06:34 1993
1817 +++ linux/include/linux/tasks.h Wed Aug 18 23:05:21 1993
1818 @@ -4,6 +4,6 @@
1819  /*
1820   * This is the maximum nr of tasks - change it if you need to
1821   */
1822 -#define NR_TASKS       64
1823 +#define NR_TASKS       128
1824  
1825  #endif
1826 diff -u --recursive --new-file pl12/linux/include/linux/timer.h linux/include/linux/timer.h
1827 --- pl12/linux/include/linux/timer.h    Sat Aug 14 23:47:22 1993
1828 +++ linux/include/linux/timer.h Tue Aug 17 18:39:34 1993
1829 @@ -17,6 +17,8 @@
1830   * 
1831   * HD_TIMER            harddisk timer
1832   *
1833 + * HD_TIMER2           (atdisk2 patches)
1834 + *
1835   * FLOPPY_TIMER                floppy disk timer (not used right now)
1836   * 
1837   * SCSI_TIMER          scsi.c timeout timer
1838 @@ -43,6 +45,8 @@
1839  
1840  #define TAPE_QIC02_TIMER       22      /* hhb */
1841  #define MCD_TIMER      23
1842 +
1843 +#define HD_TIMER2      24
1844  
1845  struct timer_struct {
1846         unsigned long expires;
1847 diff -u --recursive --new-file pl12/linux/init/main.c linux/init/main.c
1848 --- pl12/linux/init/main.c      Mon Aug  9 18:02:31 1993
1849 +++ linux/init/main.c   Sat Sep  4 02:58:36 1993
1850 @@ -23,12 +23,13 @@
1851  #include <linux/ctype.h>
1852  #include <linux/delay.h>
1853  #include <linux/utsname.h>
1854 +#include <linux/ioport.h>
1855  
1856  extern unsigned long * prof_buffer;
1857  extern unsigned long prof_len;
1858  extern char edata, end;
1859  extern char *linux_banner;
1860 -extern "C" void lcall7(void);
1861 +asmlinkage void lcall7(void);
1862  struct desc_struct default_ldt;
1863  
1864  /*
1865 @@ -43,6 +44,7 @@
1866   * won't be any messing with the stack from main(), but we define
1867   * some others too.
1868   */
1869 +#define __NR__exit __NR_exit
1870  static inline _syscall0(int,idle)
1871  static inline _syscall0(int,fork)
1872  static inline _syscall0(int,pause)
1873 @@ -54,7 +56,7 @@
1874  static inline _syscall3(int,execve,const char *,file,char **,argv,char **,envp)
1875  static inline _syscall3(int,open,const char *,file,int,flag,int,mode)
1876  static inline _syscall1(int,close,int,fd)
1877 -static inline _syscall1(int,exit,int,exitcode)
1878 +static inline _syscall1(int,_exit,int,exitcode)
1879  static inline _syscall3(pid_t,waitpid,pid_t,pid,int *,wait_stat,int,options)
1880  
1881  static inline pid_t wait(int * wait_stat)
1882 @@ -189,6 +191,7 @@
1883         char *str;
1884         void (*setup_func)(char *, int *);
1885  } bootsetups[] = {
1886 +       { "reserve=", reserve_setup },
1887  #ifdef CONFIG_INET
1888         { "ether=", eth_setup },
1889  #endif
1890 @@ -329,7 +332,7 @@
1891         outb_p(0,0xf0);
1892  }
1893  
1894 -extern "C" void start_kernel(void)
1895 +asmlinkage void start_kernel(void)
1896  {
1897  /*
1898   * Interrupts are still disabled. Do necessary setups, then
1899 @@ -466,9 +469,9 @@
1900         if (!(pid=fork())) {
1901                 close(0);
1902                 if (open("/etc/rc",O_RDONLY,0))
1903 -                       exit(1);
1904 +                       _exit(1);
1905                 execve("/bin/sh",argv_rc,envp_rc);
1906 -               exit(2);
1907 +               _exit(2);
1908         }
1909         if (pid>0)
1910                 while (pid != wait(&i))
1911 @@ -484,7 +487,7 @@
1912                         (void) open("/dev/tty1",O_RDWR,0);
1913                         (void) dup(0);
1914                         (void) dup(0);
1915 -                       exit(execve("/bin/sh",argv,envp));
1916 +                       _exit(execve("/bin/sh",argv,envp));
1917                 }
1918                 while (1)
1919                         if (pid == wait(&i))
1920 @@ -492,5 +495,5 @@
1921                 printf("\n\rchild %d died with code %04x\n\r",pid,i);
1922                 sync();
1923         }
1924 -       exit(0);
1925 +       _exit(0);
1926  }
1927 diff -u --recursive --new-file pl12/linux/ipc/util.c linux/ipc/util.c
1928 --- pl12/linux/ipc/util.c       Mon Aug  9 18:02:31 1993
1929 +++ linux/ipc/util.c    Sat Sep  4 14:29:20 1993
1930 @@ -13,7 +13,7 @@
1931  #include <linux/stat.h>
1932  
1933  void ipc_init (void);
1934 -extern "C" int sys_ipc (uint call, int first, int second, int third, void *ptr); 
1935 +asmlinkage int sys_ipc (uint call, int first, int second, int third, void *ptr); 
1936  
1937  #ifdef CONFIG_SYSVIPC
1938  
1939 @@ -67,7 +67,7 @@
1940         return 0;
1941  }
1942  
1943 -extern "C" int sys_ipc (uint call, int first, int second, int third, void *ptr) 
1944 +asmlinkage int sys_ipc (uint call, int first, int second, int third, void *ptr) 
1945  {
1946         
1947         if (call <= SEMCTL)
1948 @@ -123,7 +123,7 @@
1949  
1950  #else /* not CONFIG_SYSVIPC */
1951  
1952 -extern "C" int sys_ipc (uint call, int first, int second, int third, void *ptr) 
1953 +asmlinkage int sys_ipc (uint call, int first, int second, int third, void *ptr) 
1954  {
1955      return -ENOSYS;
1956  }
1957 diff -u --recursive --new-file pl12/linux/kernel/FPU-emu/errors.c linux/kernel/FPU-emu/errors.c
1958 --- pl12/linux/kernel/FPU-emu/errors.c  Thu Jul 22 01:11:49 1993
1959 +++ linux/kernel/FPU-emu/errors.c       Sat Sep  4 03:25:27 1993
1960 @@ -312,7 +312,7 @@
1961  
1962  /* Real operation attempted on two operands, one a NaN. */
1963  /* Returns nz if the exception is unmasked */
1964 -extern "C" int real_2op_NaN(FPU_REG *a, FPU_REG *b, FPU_REG *dest)
1965 +asmlinkage int real_2op_NaN(FPU_REG *a, FPU_REG *b, FPU_REG *dest)
1966  {
1967    FPU_REG *x;
1968    int signalling;
1969 @@ -326,7 +326,7 @@
1970         {
1971           signalling = !(a->sigh & b->sigh & 0x40000000);
1972           /* find the "larger" */
1973 -         if ( *(long long *)&(a->sigl) < *(long long *)&(b->sigl) )
1974 +         if ( significand(a) < significand(b) )
1975             x = b;
1976         }
1977        else
1978 @@ -378,7 +378,7 @@
1979  
1980  /* Invalid arith operation on Valid registers */
1981  /* Returns nz if the exception is unmasked */
1982 -extern "C" int arith_invalid(FPU_REG *dest)
1983 +asmlinkage int arith_invalid(FPU_REG *dest)
1984  {
1985  
1986    EXCEPTION(EX_Invalid);
1987 @@ -395,7 +395,7 @@
1988  
1989  
1990  /* Divide a finite number by zero */
1991 -extern "C" int divide_by_zero(int sign, FPU_REG *dest)
1992 +asmlinkage int divide_by_zero(int sign, FPU_REG *dest)
1993  {
1994  
1995    if ( control_word & CW_ZeroDiv )
1996 @@ -430,7 +430,7 @@
1997  
1998  
1999  /* This may be called often, so keep it lean */
2000 -extern "C" void set_precision_flag_up(void)
2001 +asmlinkage void set_precision_flag_up(void)
2002  {
2003    if ( control_word & CW_Precision )
2004      partial_status |= (SW_Precision | SW_C1);   /* The masked response */
2005 @@ -441,7 +441,7 @@
2006  
2007  
2008  /* This may be called often, so keep it lean */
2009 -extern "C" void set_precision_flag_down(void)
2010 +asmlinkage void set_precision_flag_down(void)
2011  {
2012    if ( control_word & CW_Precision )
2013      {   /* The masked response */
2014 @@ -453,7 +453,7 @@
2015  }
2016  
2017  
2018 -extern "C" int denormal_operand(void)
2019 +asmlinkage int denormal_operand(void)
2020  {
2021    if ( control_word & CW_Denormal )
2022      {   /* The masked response */
2023 @@ -468,7 +468,7 @@
2024  }
2025  
2026  
2027 -extern "C" int arith_overflow(FPU_REG *dest)
2028 +asmlinkage int arith_overflow(FPU_REG *dest)
2029  {
2030  
2031    if ( control_word & CW_Overflow )
2032 @@ -502,7 +502,7 @@
2033  }
2034  
2035  
2036 -extern "C" int arith_underflow(FPU_REG *dest)
2037 +asmlinkage int arith_underflow(FPU_REG *dest)
2038  {
2039  
2040    if ( control_word & CW_Underflow )
2041 diff -u --recursive --new-file pl12/linux/kernel/FPU-emu/fpu_arith.c linux/kernel/FPU-emu/fpu_arith.c
2042 --- pl12/linux/kernel/FPU-emu/fpu_arith.c       Thu Jul 22 01:11:50 1993
2043 +++ linux/kernel/FPU-emu/fpu_arith.c    Wed Sep  1 18:30:04 1993
2044 @@ -19,10 +19,7 @@
2045  void fadd__()
2046  {
2047    /* fadd st,st(i) */
2048 -#ifdef PECULIAR_486
2049 -  /* Default, this conveys no information, but an 80486 does it. */
2050    clear_C1();
2051 -#endif PECULIAR_486
2052    reg_add(FPU_st0_ptr, &st(FPU_rm), FPU_st0_ptr, control_word);
2053  }
2054  
2055 @@ -30,10 +27,7 @@
2056  void fmul__()
2057  {
2058    /* fmul st,st(i) */
2059 -#ifdef PECULIAR_486
2060 -  /* Default, this conveys no information, but an 80486 does it. */
2061    clear_C1();
2062 -#endif PECULIAR_486
2063    reg_mul(FPU_st0_ptr, &st(FPU_rm), FPU_st0_ptr, control_word);
2064  }
2065  
2066 @@ -42,10 +36,7 @@
2067  void fsub__()
2068  {
2069    /* fsub st,st(i) */
2070 -#ifdef PECULIAR_486
2071 -  /* Default, this conveys no information, but an 80486 does it. */
2072    clear_C1();
2073 -#endif PECULIAR_486
2074    reg_sub(FPU_st0_ptr, &st(FPU_rm), FPU_st0_ptr, control_word);
2075  }
2076  
2077 @@ -53,10 +44,7 @@
2078  void fsubr_()
2079  {
2080    /* fsubr st,st(i) */
2081 -#ifdef PECULIAR_486
2082 -  /* Default, this conveys no information, but an 80486 does it. */
2083    clear_C1();
2084 -#endif PECULIAR_486
2085    reg_sub(&st(FPU_rm), FPU_st0_ptr, FPU_st0_ptr, control_word);
2086  }
2087  
2088 @@ -64,10 +52,7 @@
2089  void fdiv__()
2090  {
2091    /* fdiv st,st(i) */
2092 -#ifdef PECULIAR_486
2093 -  /* Default, this conveys no information, but an 80486 does it. */
2094    clear_C1();
2095 -#endif PECULIAR_486
2096    reg_div(FPU_st0_ptr, &st(FPU_rm), FPU_st0_ptr, control_word);
2097  }
2098  
2099 @@ -75,10 +60,7 @@
2100  void fdivr_()
2101  {
2102    /* fdivr st,st(i) */
2103 -#ifdef PECULIAR_486
2104 -  /* Default, this conveys no information, but an 80486 does it. */
2105    clear_C1();
2106 -#endif PECULIAR_486
2107    reg_div(&st(FPU_rm), FPU_st0_ptr, FPU_st0_ptr, control_word);
2108  }
2109  
2110 @@ -87,10 +69,7 @@
2111  void fadd_i()
2112  {
2113    /* fadd st(i),st */
2114 -#ifdef PECULIAR_486
2115 -  /* Default, this conveys no information, but an 80486 does it. */
2116    clear_C1();
2117 -#endif PECULIAR_486
2118    reg_add(FPU_st0_ptr, &st(FPU_rm), &st(FPU_rm), control_word);
2119  }
2120  
2121 @@ -98,10 +77,7 @@
2122  void fmul_i()
2123  {
2124    /* fmul st(i),st */
2125 -#ifdef PECULIAR_486
2126 -  /* Default, this conveys no information, but an 80486 does it. */
2127    clear_C1();
2128 -#endif PECULIAR_486
2129    reg_mul(FPU_st0_ptr, &st(FPU_rm), &st(FPU_rm), control_word);
2130  }
2131  
2132 @@ -111,10 +87,7 @@
2133    /* fsubr st(i),st */
2134    /* This is the sense of the 80486 manual
2135       reg_sub(&st(FPU_rm), FPU_st0_ptr, &st(FPU_rm), control_word); */
2136 -#ifdef PECULIAR_486
2137 -  /* Default, this conveys no information, but an 80486 does it. */
2138    clear_C1();
2139 -#endif PECULIAR_486
2140    reg_sub(FPU_st0_ptr, &st(FPU_rm), &st(FPU_rm), control_word);
2141  }
2142  
2143 @@ -124,10 +97,7 @@
2144    /* fsub st(i),st */
2145    /* This is the sense of the 80486 manual
2146       reg_sub(FPU_st0_ptr, &st(FPU_rm), &st(FPU_rm), control_word); */
2147 -#ifdef PECULIAR_486
2148 -  /* Default, this conveys no information, but an 80486 does it. */
2149    clear_C1();
2150 -#endif PECULIAR_486
2151    reg_sub(&st(FPU_rm), FPU_st0_ptr, &st(FPU_rm), control_word);
2152  }
2153  
2154 @@ -135,10 +105,7 @@
2155  void fdivri()
2156  {
2157    /* fdivr st(i),st */
2158 -#ifdef PECULIAR_486
2159 -  /* Default, this conveys no information, but an 80486 does it. */
2160    clear_C1();
2161 -#endif PECULIAR_486
2162    reg_div(FPU_st0_ptr, &st(FPU_rm), &st(FPU_rm), control_word);
2163  }
2164  
2165 @@ -146,10 +113,7 @@
2166  void fdiv_i()
2167  {
2168    /* fdiv st(i),st */
2169 -#ifdef PECULIAR_486
2170 -  /* Default, this conveys no information, but an 80486 does it. */
2171    clear_C1();
2172 -#endif PECULIAR_486
2173    reg_div(&st(FPU_rm), FPU_st0_ptr, &st(FPU_rm), control_word);
2174  }
2175  
2176 @@ -158,10 +122,7 @@
2177  void faddp_()
2178  {
2179    /* faddp st(i),st */
2180 -#ifdef PECULIAR_486
2181 -  /* Default, this conveys no information, but an 80486 does it. */
2182    clear_C1();
2183 -#endif PECULIAR_486
2184    if ( !reg_add(FPU_st0_ptr, &st(FPU_rm), &st(FPU_rm), control_word) )
2185      pop();
2186  }
2187 @@ -170,10 +131,7 @@
2188  void fmulp_()
2189  {
2190    /* fmulp st(i),st */
2191 -#ifdef PECULIAR_486
2192 -  /* Default, this conveys no information, but an 80486 does it. */
2193    clear_C1();
2194 -#endif PECULIAR_486
2195    if ( !reg_mul(FPU_st0_ptr, &st(FPU_rm), &st(FPU_rm), control_word) )
2196      pop();
2197  }
2198 @@ -185,10 +143,7 @@
2199    /* fsubrp st(i),st */
2200    /* This is the sense of the 80486 manual
2201       reg_sub(&st(FPU_rm), FPU_st0_ptr, &st(FPU_rm), control_word); */
2202 -#ifdef PECULIAR_486
2203 -  /* Default, this conveys no information, but an 80486 does it. */
2204    clear_C1();
2205 -#endif PECULIAR_486
2206    if ( !reg_sub(FPU_st0_ptr, &st(FPU_rm), &st(FPU_rm), control_word) )
2207      pop();
2208  }
2209 @@ -199,10 +154,7 @@
2210    /* fsubp st(i),st */
2211    /* This is the sense of the 80486 manual
2212       reg_sub(FPU_st0_ptr, &st(FPU_rm), &st(FPU_rm), control_word); */
2213 -#ifdef PECULIAR_486
2214 -  /* Default, this conveys no information, but an 80486 does it. */
2215    clear_C1();
2216 -#endif PECULIAR_486
2217    if ( !reg_sub(&st(FPU_rm), FPU_st0_ptr, &st(FPU_rm), control_word) )
2218      pop();
2219  }
2220 @@ -211,10 +163,7 @@
2221  void fdivrp()
2222  {
2223    /* fdivrp st(i),st */
2224 -#ifdef PECULIAR_486
2225 -  /* Default, this conveys no information, but an 80486 does it. */
2226    clear_C1();
2227 -#endif PECULIAR_486
2228    if ( !reg_div(FPU_st0_ptr, &st(FPU_rm), &st(FPU_rm), control_word) )
2229      pop();
2230  }
2231 @@ -223,10 +172,7 @@
2232  void fdivp_()
2233  {
2234    /* fdivp st(i),st */
2235 -#ifdef PECULIAR_486
2236 -  /* Default, this conveys no information, but an 80486 does it. */
2237    clear_C1();
2238 -#endif PECULIAR_486
2239    if ( !reg_div(&st(FPU_rm), FPU_st0_ptr, &st(FPU_rm), control_word) )
2240      pop();
2241  }
2242 diff -u --recursive --new-file pl12/linux/kernel/FPU-emu/fpu_aux.c linux/kernel/FPU-emu/fpu_aux.c
2243 --- pl12/linux/kernel/FPU-emu/fpu_aux.c Thu Jul 22 01:11:50 1993
2244 +++ linux/kernel/FPU-emu/fpu_aux.c      Wed Sep  1 18:30:04 1993
2245 @@ -139,10 +139,7 @@
2246        stack_underflow();
2247        return;
2248      }
2249 -#ifdef PECULIAR_486
2250 -  /* Default, this conveys no information, but an 80486 does it. */
2251    clear_C1();
2252 -#endif PECULIAR_486
2253    reg_move(FPU_st0_ptr, &t);
2254    reg_move(sti_ptr, FPU_st0_ptr);
2255    reg_move(&t, sti_ptr);
2256 diff -u --recursive --new-file pl12/linux/kernel/FPU-emu/fpu_emu.h linux/kernel/FPU-emu/fpu_emu.h
2257 --- pl12/linux/kernel/FPU-emu/fpu_emu.h Thu Jul 22 01:11:50 1993
2258 +++ linux/kernel/FPU-emu/fpu_emu.h      Sat Sep  4 03:28:02 1993
2259 @@ -58,6 +58,7 @@
2260  #ifndef __ASSEMBLER__
2261  
2262  #include <linux/math_emu.h>
2263 +#include <linux/linkage.h>
2264  
2265  #ifdef PARANOID
2266  extern char emulating;
2267 @@ -110,33 +111,36 @@
2268                  *(long *)&((y)->exp) = *(long *)&((x)->exp); \
2269                  *(long long *)&((y)->sigl) = *(long long *)&((x)->sigl); }
2270  
2271 +#define significand(x) ( ((unsigned long long *)&((x)->sigl))[0] )
2272  
2273 +
2274  /*----- Prototypes for functions written in assembler -----*/
2275  /* extern void reg_move(FPU_REG *a, FPU_REG *b); */
2276  
2277 -extern "C" void mul64(long long *a, long long *b, long long *result);
2278 -extern "C" void poly_div2(long long *x);
2279 -extern "C" void poly_div4(long long *x);
2280 -extern "C" void poly_div16(long long *x);
2281 -extern "C" void polynomial(unsigned accum[], unsigned x[],
2282 +asmlinkage void mul64(unsigned long long *a, unsigned long long *b,
2283 +                     unsigned long long *result);
2284 +asmlinkage void poly_div2(unsigned long long *x);
2285 +asmlinkage void poly_div4(unsigned long long *x);
2286 +asmlinkage void poly_div16(unsigned long long *x);
2287 +asmlinkage void polynomial(unsigned accum[], unsigned x[],
2288                        unsigned short terms[][4], int n);
2289 -extern "C" void normalize(FPU_REG *x);
2290 -extern "C" void normalize_nuo(FPU_REG *x);
2291 -extern "C" int reg_div(FPU_REG *arg1, FPU_REG *arg2, FPU_REG *answ,
2292 +asmlinkage void normalize(FPU_REG *x);
2293 +asmlinkage void normalize_nuo(FPU_REG *x);
2294 +asmlinkage int reg_div(FPU_REG *arg1, FPU_REG *arg2, FPU_REG *answ,
2295                     unsigned int control_w);
2296 -extern "C" int reg_u_sub(FPU_REG *arg1, FPU_REG *arg2, FPU_REG *answ,
2297 +asmlinkage int reg_u_sub(FPU_REG *arg1, FPU_REG *arg2, FPU_REG *answ,
2298                       unsigned int control_w);
2299 -extern "C" int reg_u_mul(FPU_REG *arg1, FPU_REG *arg2, FPU_REG *answ,
2300 +asmlinkage int reg_u_mul(FPU_REG *arg1, FPU_REG *arg2, FPU_REG *answ,
2301                       unsigned int control_w);
2302 -extern "C" int reg_u_div(FPU_REG *arg1, FPU_REG *arg2, FPU_REG *answ,
2303 +asmlinkage int reg_u_div(FPU_REG *arg1, FPU_REG *arg2, FPU_REG *answ,
2304                       unsigned int control_w);
2305 -extern "C" int reg_u_add(FPU_REG *arg1, FPU_REG *arg2, FPU_REG *answ,
2306 +asmlinkage int reg_u_add(FPU_REG *arg1, FPU_REG *arg2, FPU_REG *answ,
2307                       unsigned int control_w);
2308 -extern "C" int wm_sqrt(FPU_REG *n, unsigned int control_w);
2309 -extern "C" unsigned    shrx(void *l, unsigned x);
2310 -extern "C" unsigned    shrxs(void *v, unsigned x);
2311 -extern "C" unsigned long div_small(unsigned long long *x, unsigned long y);
2312 -extern "C" void round_reg(FPU_REG *arg, unsigned int extent,
2313 +asmlinkage int wm_sqrt(FPU_REG *n, unsigned int control_w);
2314 +asmlinkage unsigned    shrx(void *l, unsigned x);
2315 +asmlinkage unsigned    shrxs(void *v, unsigned x);
2316 +asmlinkage unsigned long div_small(unsigned long long *x, unsigned long y);
2317 +asmlinkage void round_reg(FPU_REG *arg, unsigned int extent,
2318                       unsigned int control_w);
2319  
2320  #ifndef MAKING_PROTO
2321 diff -u --recursive --new-file pl12/linux/kernel/FPU-emu/fpu_entry.c linux/kernel/FPU-emu/fpu_entry.c
2322 --- pl12/linux/kernel/FPU-emu/fpu_entry.c       Thu Jul 22 01:11:50 1993
2323 +++ linux/kernel/FPU-emu/fpu_entry.c    Sat Sep  4 03:25:27 1993
2324 @@ -155,7 +155,7 @@
2325  static int valid_prefix(unsigned char byte);
2326  
2327  
2328 -extern "C" void math_emulate(long arg)
2329 +asmlinkage void math_emulate(long arg)
2330  {
2331    unsigned char  FPU_modrm;
2332    unsigned short code;
2333 @@ -183,7 +183,7 @@
2334        current->used_math = 1;
2335      }
2336  
2337 -  FPU_info = (struct info *) &arg;
2338 +  SETUP_DATA_AREA(arg);
2339  
2340    /* We cannot handle emulation in v86-mode */
2341    if (FPU_EFLAGS & 0x00020000)
2342 @@ -401,20 +401,12 @@
2343               switch ( (FPU_modrm >> 3) & 7 )
2344                 {
2345                 case 0:         /* fadd */
2346 -#ifdef PECULIAR_486
2347 -                 /* Default, this conveys no information,
2348 -                    but an 80486 does it. */
2349                   clear_C1();
2350 -#endif PECULIAR_486
2351                   reg_add(FPU_st0_ptr, &FPU_loaded_data, FPU_st0_ptr,
2352                           control_word);
2353                   break;
2354                 case 1:         /* fmul */
2355 -#ifdef PECULIAR_486
2356 -                 /* Default, this conveys no information,
2357 -                    but an 80486 does it. */
2358                   clear_C1();
2359 -#endif PECULIAR_486
2360                   reg_mul(FPU_st0_ptr, &FPU_loaded_data, FPU_st0_ptr,
2361                           control_word);
2362                   break;
2363 @@ -426,38 +418,22 @@
2364                     pop();
2365                   break;
2366                 case 4:         /* fsub */
2367 -#ifdef PECULIAR_486
2368 -                 /* Default, this conveys no information,
2369 -                    but an 80486 does it. */
2370                   clear_C1();
2371 -#endif PECULIAR_486
2372                   reg_sub(FPU_st0_ptr, &FPU_loaded_data, FPU_st0_ptr,
2373                           control_word);
2374                   break;
2375                 case 5:         /* fsubr */
2376 -#ifdef PECULIAR_486
2377 -                 /* Default, this conveys no information,
2378 -                    but an 80486 does it. */
2379                   clear_C1();
2380 -#endif PECULIAR_486
2381                   reg_sub(&FPU_loaded_data, FPU_st0_ptr, FPU_st0_ptr,
2382                           control_word);
2383                   break;
2384                 case 6:         /* fdiv */
2385 -#ifdef PECULIAR_486
2386 -                 /* Default, this conveys no information,
2387 -                    but an 80486 does it. */
2388                   clear_C1();
2389 -#endif PECULIAR_486
2390                   reg_div(FPU_st0_ptr, &FPU_loaded_data, FPU_st0_ptr,
2391                           control_word);
2392                   break;
2393                 case 7:         /* fdivr */
2394 -#ifdef PECULIAR_486
2395 -                 /* Default, this conveys no information,
2396 -                    but an 80486 does it. */
2397                   clear_C1();
2398 -#endif PECULIAR_486
2399                   if ( FPU_st0_tag == TW_Zero )
2400                     partial_status = status1;  /* Undo any denorm tag,
2401                                                zero-divide has priority. */
2402 @@ -637,7 +613,7 @@
2403  #include <linux/signal.h>
2404  #include <linux/sched.h>
2405  
2406 -extern "C" void math_emulate(long arg)
2407 +asmlinkage void math_emulate(long arg)
2408  {
2409    printk("math-emulation not enabled and no coprocessor found.\n");
2410    printk("killing %s.\n",current->comm);
2411 diff -u --recursive --new-file pl12/linux/kernel/FPU-emu/fpu_etc.c linux/kernel/FPU-emu/fpu_etc.c
2412 --- pl12/linux/kernel/FPU-emu/fpu_etc.c Thu Jul 22 01:11:50 1993
2413 +++ linux/kernel/FPU-emu/fpu_etc.c      Wed Sep  1 18:30:04 1993
2414 @@ -22,10 +22,7 @@
2415    if ( NOT_EMPTY_0 )
2416      {
2417        FPU_st0_ptr->sign ^= SIGN_POS^SIGN_NEG;
2418 -#ifdef PECULIAR_486
2419 -      /* Default, this conveys no information, but an 80486 does it. */
2420        clear_C1();
2421 -#endif PECULIAR_486
2422      }
2423    else
2424      stack_underflow();
2425 @@ -36,10 +33,7 @@
2426    if ( FPU_st0_tag ^ TW_Empty )
2427      {
2428        FPU_st0_ptr->sign = SIGN_POS;
2429 -#ifdef PECULIAR_486
2430 -      /* Default, this conveys no information, but an 80486 does it. */
2431        clear_C1();
2432 -#endif PECULIAR_486
2433      }
2434    else
2435      stack_underflow();
2436 diff -u --recursive --new-file pl12/linux/kernel/FPU-emu/fpu_proto.h linux/kernel/FPU-emu/fpu_proto.h
2437 --- pl12/linux/kernel/FPU-emu/fpu_proto.h       Thu Jul 22 01:11:50 1993
2438 +++ linux/kernel/FPU-emu/fpu_proto.h    Sat Sep  4 03:25:27 1993
2439 @@ -6,15 +6,15 @@
2440  extern void stack_underflow_i(int i);
2441  extern void stack_underflow_pop(int i);
2442  extern int set_precision_flag(int flags);
2443 -extern "C" void exception(int n);
2444 -extern "C" int real_2op_NaN(FPU_REG *a, FPU_REG *b, FPU_REG *dest);
2445 -extern "C" int arith_invalid(FPU_REG *dest);
2446 -extern "C" int divide_by_zero(int sign, FPU_REG *dest);
2447 -extern "C" void set_precision_flag_up(void);
2448 -extern "C" void set_precision_flag_down(void);
2449 -extern "C" int denormal_operand(void);
2450 -extern "C" int arith_overflow(FPU_REG *dest);
2451 -extern "C" int arith_underflow(FPU_REG *dest);
2452 +asmlinkage void exception(int n);
2453 +asmlinkage int real_2op_NaN(FPU_REG *a, FPU_REG *b, FPU_REG *dest);
2454 +asmlinkage int arith_invalid(FPU_REG *dest);
2455 +asmlinkage int divide_by_zero(int sign, FPU_REG *dest);
2456 +asmlinkage void set_precision_flag_up(void);
2457 +asmlinkage void set_precision_flag_down(void);
2458 +asmlinkage int denormal_operand(void);
2459 +asmlinkage int arith_overflow(FPU_REG *dest);
2460 +asmlinkage int arith_underflow(FPU_REG *dest);
2461  
2462  /* fpu_arith.c */
2463  extern void fadd__(void);
2464 @@ -50,7 +50,7 @@
2465  extern void fstp_i(void);
2466  
2467  /* fpu_entry.c */
2468 -extern "C" void math_emulate(long arg);
2469 +asmlinkage void math_emulate(long arg);
2470  extern void __math_abort(struct info *info, unsigned int signal);
2471  
2472  /* fpu_etc.c */
2473 diff -u --recursive --new-file pl12/linux/kernel/FPU-emu/fpu_system.h linux/kernel/FPU-emu/fpu_system.h
2474 --- pl12/linux/kernel/FPU-emu/fpu_system.h      Thu Jul 22 01:11:50 1993
2475 +++ linux/kernel/FPU-emu/fpu_system.h   Wed Sep  1 18:30:04 1993
2476 @@ -14,6 +14,10 @@
2477  #include <linux/sched.h>
2478  #include <linux/kernel.h>
2479  
2480 +/* This sets the pointer FPU_info to point to the argument part
2481 +   of the stack frame of math_emulate() */
2482 +#define SETUP_DATA_AREA(arg)    FPU_info = (struct info *) &arg
2483 +
2484  #define I387                   (current->tss.i387)
2485  #define FPU_info               (I387.soft.info)
2486  
2487 diff -u --recursive --new-file pl12/linux/kernel/FPU-emu/fpu_trig.c linux/kernel/FPU-emu/fpu_trig.c
2488 --- pl12/linux/kernel/FPU-emu/fpu_trig.c        Thu Jul 22 01:11:51 1993
2489 +++ linux/kernel/FPU-emu/fpu_trig.c     Wed Sep  1 18:30:05 1993
2490 @@ -20,7 +20,7 @@
2491  
2492  static void rem_kernel(unsigned long long st0, unsigned long long *y,
2493                        unsigned long long st1,
2494 -                      long long q, int n);
2495 +                      unsigned long long q, int n);
2496  
2497  #define BETTER_THAN_486
2498  
2499 @@ -27,6 +27,7 @@
2500  #define FCOS  4
2501  #define FPTAN 1
2502  
2503 +
2504  /* Used only by fptan, fsin, fcos, and fsincos. */
2505  /* This routine produces very accurate results, similar to
2506     using a value of pi with more than 128 bits precision. */
2507 @@ -36,7 +37,7 @@
2508  static int trig_arg(FPU_REG *X, int even)
2509  {
2510    FPU_REG tmp;
2511 -  long long q;
2512 +  unsigned long long q;
2513    int old_cw = control_word, saved_status = partial_status;
2514  
2515    if ( X->exp >= EXP_BIAS + 63 )
2516 @@ -51,12 +52,12 @@
2517    reg_div(X, &CONST_PI2, &tmp, PR_64_BITS | RC_CHOP | 0x3f);
2518    round_to_int(&tmp);  /* Fortunately, this can't overflow
2519                           to 2^64 */
2520 -  q = ((long long *)&(tmp.sigl))[0];
2521 +  q = significand(&tmp);
2522    if ( q )
2523      {
2524 -      rem_kernel(((unsigned long long *)&(X->sigl))[0],
2525 -                (unsigned long long *)&(tmp.sigl),
2526 -                ((unsigned long long *)&(CONST_PI2.sigl))[0],
2527 +      rem_kernel(significand(X),
2528 +                &significand(&tmp),
2529 +                significand(&CONST_PI2),
2530                  q, X->exp - CONST_PI2.exp);
2531        tmp.exp = CONST_PI2.exp;
2532        normalize(&tmp);
2533 @@ -85,7 +86,7 @@
2534         {
2535           /* This code gives the effect of having p/2 to better than
2536              128 bits precision. */
2537 -         ((long long *)&(tmp.sigl))[0] = q + 1;
2538 +         significand(&tmp) = q + 1;
2539           tmp.exp = EXP_BIAS + 63;
2540           normalize(&tmp);
2541           reg_mul(&CONST_PI2extra, &tmp, &tmp, FULL_PRECISION);
2542 @@ -104,7 +105,7 @@
2543         {
2544           /* This code gives the effect of having p/2 to better than
2545              128 bits precision. */
2546 -         ((long long *)&(tmp.sigl))[0] = q;
2547 +         significand(&tmp) = q;
2548           tmp.exp = EXP_BIAS + 63;
2549           normalize(&tmp);
2550           reg_mul(&CONST_PI2extra, &tmp, &tmp, FULL_PRECISION);
2551 @@ -204,10 +205,7 @@
2552  
2553  static void f2xm1(void)
2554  {
2555 -#ifdef PECULIAR_486
2556 -  /* Default, this conveys no information, but an 80486 does it. */
2557    clear_C1();
2558 -#endif PECULIAR_486
2559    switch ( FPU_st0_tag )
2560      {
2561      case TW_Valid:
2562 @@ -363,11 +361,7 @@
2563  
2564    if ( STACK_OVERFLOW )
2565      {  stack_overflow(); return; }
2566 -
2567 -#ifdef PECULIAR_486
2568 -  /* Default, this conveys no information, but an 80486 does it. */
2569    clear_C1();
2570 -#endif PECULIAR_486
2571    if ( !(FPU_st0_tag ^ TW_Valid) )
2572      {
2573        long e;
2574 @@ -432,19 +426,13 @@
2575  
2576  static void fdecstp(void)
2577  {
2578 -#ifdef PECULIAR_486
2579 -  /* Default, this conveys no information, but an 80486 does it. */
2580    clear_C1();
2581 -#endif PECULIAR_486
2582    top--;  /* FPU_st0_ptr will be fixed in math_emulate() before the next instr */
2583  }
2584  
2585  static void fincstp(void)
2586  {
2587 -#ifdef PECULIAR_486
2588 -  /* Default, this conveys no information, but an 80486 does it. */
2589    clear_C1();
2590 -#endif PECULIAR_486
2591    top++;  /* FPU_st0_ptr will be fixed in math_emulate() before the next instr */
2592  }
2593  
2594 @@ -451,10 +439,7 @@
2595  
2596  static void fsqrt_(void)
2597  {
2598 -#ifdef PECULIAR_486
2599 -  /* Default, this conveys no information, but an 80486 does it. */
2600    clear_C1();
2601 -#endif PECULIAR_486
2602    if ( !(FPU_st0_tag ^ TW_Valid) )
2603      {
2604        int expon;
2605 @@ -729,7 +714,7 @@
2606   */
2607  static void rem_kernel(unsigned long long st0, unsigned long long *y,
2608                        unsigned long long st1,
2609 -                      long long q, int n)
2610 +                      unsigned long long q, int n)
2611  {
2612    unsigned long long x;
2613  
2614 @@ -790,11 +775,11 @@
2615                 {
2616                   round_to_int(&tmp);  /* Fortunately, this can't overflow
2617                                           to 2^64 */
2618 -                 q = ((long long *)&(tmp.sigl))[0];
2619 +                 q = significand(&tmp);
2620  
2621 -                 rem_kernel(((unsigned long long *)&(FPU_st0_ptr->sigl))[0],
2622 -                            (unsigned long long *)&(tmp.sigl),
2623 -                            ((unsigned long long *)&(st1_ptr->sigl))[0],
2624 +                 rem_kernel(significand(FPU_st0_ptr),
2625 +                            &significand(&tmp),
2626 +                            significand(st1_ptr),
2627                              q, expdif);
2628  
2629                   tmp.exp = st1_ptr->exp;
2630 @@ -808,14 +793,24 @@
2631  
2632               if ( (round == RC_RND) && (tmp.sigh & 0xc0000000) )
2633                 {
2634 -                 /* We may need to subtract st(1) once more. */
2635 +                 /* We may need to subtract st(1) once more,
2636 +                    to get a result <= 1/2 of st(1). */
2637                   unsigned long long x;
2638 -                 x = ((unsigned long long *)&(st1_ptr->sigl))[0] -
2639 -                   ((unsigned long long *)&(tmp.sigl))[0];
2640 -                 if ( x < ((unsigned long long *)&(tmp.sigl))[0] )
2641 +                 expdif = st1_ptr->exp - tmp.exp;
2642 +                 if ( expdif <= 1 )
2643                     {
2644 -                     tmp.sign ^= (SIGN_POS^SIGN_NEG);
2645 -                     ((unsigned long long *)&(tmp.sigl))[0] = x;
2646 +                     if ( expdif == 0 )
2647 +                       x = significand(st1_ptr) - significand(&tmp);
2648 +                     else /* expdif is 1 */
2649 +                       x = (significand(st1_ptr) << 1) - significand(&tmp);
2650 +                     if ( (x < significand(&tmp)) ||
2651 +                         /* or equi-distant (from 0 & st(1)) and q is odd */
2652 +                         ((x == significand(&tmp)) && (q & 1) ) )
2653 +                       {
2654 +                         tmp.sign ^= (SIGN_POS^SIGN_NEG);
2655 +                         significand(&tmp) = x;
2656 +                         q++;
2657 +                       }
2658                     }
2659                 }
2660  
2661 @@ -849,10 +844,10 @@
2662  
2663           round_to_int(&tmp);  /* Fortunately, this can't overflow to 2^64 */
2664  
2665 -         rem_kernel(((unsigned long long *)&(FPU_st0_ptr->sigl))[0],
2666 -                    ((unsigned long long *)&(tmp.sigl)),
2667 -                    ((unsigned long long *)&(st1_ptr->sigl))[0],
2668 -                    ((long long *)&(tmp.sigl))[0],
2669 +         rem_kernel(significand(FPU_st0_ptr),
2670 +                    &significand(&tmp),
2671 +                    significand(st1_ptr),
2672 +                    significand(&tmp),
2673                      tmp.exp - EXP_BIAS
2674                      ); 
2675           tmp.exp = exp_1 + expdif;
2676 @@ -882,13 +877,15 @@
2677  
2678        control_word = old_cw;
2679        partial_status = saved_status;
2680 -      normalize(&tmp);
2681 +      normalize_nuo(&tmp);
2682        reg_move(&tmp, FPU_st0_ptr);
2683        setcc(cc);
2684  
2685 -      if ( FPU_st0_ptr->tag != TW_Zero )
2686 -       /* Use round_reg() to properly detect under/overflow etc */
2687 -       round_reg(FPU_st0_ptr, 0, control_word);
2688 +      /* The only condition to be looked for is underflow,
2689 +        and it can occur here only if underflow is unmasked. */
2690 +      if ( (FPU_st0_ptr->exp <= EXP_UNDER) && (FPU_st0_ptr->tag != TW_Zero)
2691 +         && !(control_word & CW_Underflow) )
2692 +       arith_underflow(FPU_st0_ptr);
2693  
2694        return;
2695      }
2696 @@ -961,10 +958,7 @@
2697    FPU_REG *st1_ptr = &st(1);
2698    char st1_tag = st1_ptr->tag;
2699  
2700 -#ifdef PECULIAR_486
2701 -  /* Default, this conveys no information, but an 80486 does it. */
2702    clear_C1();
2703 -#endif PECULIAR_486
2704    if ( !((FPU_st0_tag ^ TW_Valid) | (st1_tag ^ TW_Valid)) )
2705      {
2706        if ( FPU_st0_ptr->sign == SIGN_POS )
2707 @@ -1155,10 +1149,7 @@
2708    char st1_tag = st1_ptr->tag;
2709    char st1_sign = st1_ptr->sign, st0_sign = FPU_st0_ptr->sign;
2710  
2711 -#ifdef PECULIAR_486
2712 -  /* Default, this conveys no information, but an 80486 does it. */
2713    clear_C1();
2714 -#endif PECULIAR_486
2715    if ( !((FPU_st0_tag ^ TW_Valid) | (st1_tag ^ TW_Valid)) )
2716      {
2717        int saved_control, saved_status;
2718 @@ -1336,10 +1327,7 @@
2719    FPU_REG *st1_ptr = &st(1);
2720    char st1_tag = st1_ptr->tag;
2721  
2722 -#ifdef PECULIAR_486
2723 -  /* Default, this conveys no information, but an 80486 does it. */
2724    clear_C1();
2725 -#endif PECULIAR_486
2726    if ( !((FPU_st0_tag ^ TW_Valid) | (st1_tag ^ TW_Valid)) )
2727      {
2728        int saved_control, saved_status;
2729 @@ -1560,10 +1548,7 @@
2730    int old_cw = control_word;
2731    char sign = FPU_st0_ptr->sign;
2732  
2733 -#ifdef PECULIAR_486
2734 -  /* Default, this conveys no information, but an 80486 does it. */
2735    clear_C1();
2736 -#endif PECULIAR_486
2737    if ( !((FPU_st0_tag ^ TW_Valid) | (st1_tag ^ TW_Valid)) )
2738      {
2739        long scale;
2740 diff -u --recursive --new-file pl12/linux/kernel/FPU-emu/load_store.c linux/kernel/FPU-emu/load_store.c
2741 --- pl12/linux/kernel/FPU-emu/load_store.c      Thu Jul 22 01:11:51 1993
2742 +++ linux/kernel/FPU-emu/load_store.c   Wed Sep  1 18:30:05 1993
2743 @@ -84,10 +84,7 @@
2744  switch ( type )
2745    {
2746    case 000:       /* fld m32real */
2747 -#ifdef PECULIAR_486
2748 -    /* Default, this conveys no information, but an 80486 does it. */
2749      clear_C1();
2750 -#endif PECULIAR_486
2751      reg_load_single();
2752      if ( (FPU_loaded_data.tag == TW_NaN) &&
2753         real_2op_NaN(&FPU_loaded_data, &FPU_loaded_data, &FPU_loaded_data) )
2754 @@ -98,18 +95,12 @@
2755      reg_move(&FPU_loaded_data, pop_ptr);
2756      break;
2757    case 001:      /* fild m32int */
2758 -#ifdef PECULIAR_486
2759 -    /* Default, this conveys no information, but an 80486 does it. */
2760      clear_C1();
2761 -#endif PECULIAR_486
2762      reg_load_int32();
2763      reg_move(&FPU_loaded_data, pop_ptr);
2764      break;
2765    case 002:      /* fld m64real */
2766 -#ifdef PECULIAR_486
2767 -    /* Default, this conveys no information, but an 80486 does it. */
2768      clear_C1();
2769 -#endif PECULIAR_486
2770      reg_load_double();
2771      if ( (FPU_loaded_data.tag == TW_NaN) &&
2772         real_2op_NaN(&FPU_loaded_data, &FPU_loaded_data, &FPU_loaded_data) )
2773 @@ -120,73 +111,46 @@
2774      reg_move(&FPU_loaded_data, pop_ptr);
2775      break;
2776    case 003:      /* fild m16int */
2777 -#ifdef PECULIAR_486
2778 -    /* Default, this conveys no information, but an 80486 does it. */
2779      clear_C1();
2780 -#endif PECULIAR_486
2781      reg_load_int16();
2782      reg_move(&FPU_loaded_data, pop_ptr);
2783      break;
2784    case 010:      /* fst m32real */
2785 -#ifdef PECULIAR_486
2786 -    /* Default, this conveys no information, but an 80486 does it. */
2787      clear_C1();
2788 -#endif PECULIAR_486
2789      reg_store_single();
2790      break;
2791    case 011:      /* fist m32int */
2792 -#ifdef PECULIAR_486
2793 -    /* Default, this conveys no information, but an 80486 does it. */
2794      clear_C1();
2795 -#endif PECULIAR_486
2796      reg_store_int32();
2797      break;
2798    case 012:     /* fst m64real */
2799 -#ifdef PECULIAR_486
2800 -    /* Default, this conveys no information, but an 80486 does it. */
2801      clear_C1();
2802 -#endif PECULIAR_486
2803      reg_store_double();
2804      break;
2805    case 013:     /* fist m16int */
2806 -#ifdef PECULIAR_486
2807 -    /* Default, this conveys no information, but an 80486 does it. */
2808      clear_C1();
2809 -#endif PECULIAR_486
2810      reg_store_int16();
2811      break;
2812    case 014:     /* fstp m32real */
2813 -#ifdef PECULIAR_486
2814 -    /* Default, this conveys no information, but an 80486 does it. */
2815      clear_C1();
2816 -#endif PECULIAR_486
2817      if ( reg_store_single() )
2818        pop_0();  /* pop only if the number was actually stored
2819                  (see the 80486 manual p16-28) */
2820      break;
2821    case 015:     /* fistp m32int */
2822 -#ifdef PECULIAR_486
2823 -    /* Default, this conveys no information, but an 80486 does it. */
2824      clear_C1();
2825 -#endif PECULIAR_486
2826      if ( reg_store_int32() )
2827        pop_0();  /* pop only if the number was actually stored
2828                  (see the 80486 manual p16-28) */
2829      break;
2830    case 016:     /* fstp m64real */
2831 -#ifdef PECULIAR_486
2832 -    /* Default, this conveys no information, but an 80486 does it. */
2833      clear_C1();
2834 -#endif PECULIAR_486
2835      if ( reg_store_double() )
2836        pop_0();  /* pop only if the number was actually stored
2837                  (see the 80486 manual p16-28) */
2838      break;
2839    case 017:     /* fistp m16int */
2840 -#ifdef PECULIAR_486
2841 -    /* Default, this conveys no information, but an 80486 does it. */
2842      clear_C1();
2843 -#endif PECULIAR_486
2844      if ( reg_store_int16() )
2845        pop_0();  /* pop only if the number was actually stored
2846                  (see the 80486 manual p16-28) */
2847 @@ -198,10 +162,7 @@
2848      frstor();
2849      break;
2850    case 023:     /* fbld m80dec */
2851 -#ifdef PECULIAR_486
2852 -    /* Default, this conveys no information, but an 80486 does it. */
2853      clear_C1();
2854 -#endif PECULIAR_486
2855      reg_load_bcd();
2856      reg_move(&FPU_loaded_data, pop_ptr);
2857      break;
2858 @@ -220,18 +181,12 @@
2859      NO_NET_INSTR_EFFECT;
2860      break;
2861    case 025:      /* fld m80real */
2862 -#ifdef PECULIAR_486
2863 -    /* Default, this conveys no information, but an 80486 does it. */
2864      clear_C1();
2865 -#endif PECULIAR_486
2866      reg_load_extended();
2867      reg_move(&FPU_loaded_data, pop_ptr);
2868      break;
2869    case 027:      /* fild m64int */
2870 -#ifdef PECULIAR_486
2871 -    /* Default, this conveys no information, but an 80486 does it. */
2872      clear_C1();
2873 -#endif PECULIAR_486
2874      reg_load_int64();
2875      reg_move(&FPU_loaded_data, pop_ptr);
2876      break;
2877 @@ -244,10 +199,7 @@
2878      NO_NET_DATA_EFFECT;
2879      break;
2880    case 033:      /* fbstp m80dec */
2881 -#ifdef PECULIAR_486
2882 -    /* Default, this conveys no information, but an 80486 does it. */
2883      clear_C1();
2884 -#endif PECULIAR_486
2885      if ( reg_store_bcd() )
2886        pop_0();  /* pop only if the number was actually stored
2887                  (see the 80486 manual p16-28) */
2888 @@ -261,10 +213,7 @@
2889      NO_NET_INSTR_EFFECT;
2890      break;
2891    case 035:      /* fstp m80real */
2892 -#ifdef PECULIAR_486
2893 -    /* Default, this conveys no information, but an 80486 does it. */
2894      clear_C1();
2895 -#endif PECULIAR_486
2896      if ( reg_store_extended() )
2897        pop_0();  /* pop only if the number was actually stored
2898                  (see the 80486 manual p16-28) */
2899 @@ -278,10 +227,7 @@
2900      NO_NET_INSTR_EFFECT;
2901      break;
2902    case 037:      /* fistp m64int */
2903 -#ifdef PECULIAR_486
2904 -    /* Default, this conveys no information, but an 80486 does it. */
2905      clear_C1();
2906 -#endif PECULIAR_486
2907      if ( reg_store_int64() )
2908        pop_0();  /* pop only if the number was actually stored
2909                  (see the 80486 manual p16-28) */
2910 diff -u --recursive --new-file pl12/linux/kernel/FPU-emu/poly_atan.c linux/kernel/FPU-emu/poly_atan.c
2911 --- pl12/linux/kernel/FPU-emu/poly_atan.c       Thu Jul 22 01:11:51 1993
2912 +++ linux/kernel/FPU-emu/poly_atan.c    Wed Sep  1 18:30:05 1993
2913 @@ -38,12 +38,9 @@
2914    { 0xf1dd2dbf, 0x000a530a }
2915  };
2916  
2917 +static unsigned long long denomterm = 0xea2e6612fc4bd208LL;
2918  
2919 -static unsigned denomterm[2] =
2920 -{ 0xfc4bd208, 0xea2e6612 };
2921  
2922 -
2923 -
2924  /*--- poly_atan() -----------------------------------------------------------+
2925   |                                                                           |
2926   +---------------------------------------------------------------------------*/
2927 @@ -53,7 +50,7 @@
2928    short                exponent;
2929    FPU_REG       odd_poly, even_poly, pos_poly, neg_poly, ratio;
2930    FPU_REG       argSq;
2931 -  long long     arg_signif, argSqSq;
2932 +  unsigned long long     arg_signif, argSqSq;
2933    
2934  
2935  #ifdef PARANOID
2936 @@ -97,20 +94,20 @@
2937  
2938           recursions++;
2939  
2940 -         arg_signif = *(long long *)&(arg->sigl);
2941 +         arg_signif = significand(arg);
2942           if ( exponent < -1 )
2943             {
2944               if ( shrx(&arg_signif, -1-exponent) >= 0x80000000U )
2945                 arg_signif++;   /* round up */
2946             }
2947 -         *(long long *)&(numerator.sigl) = -arg_signif;
2948 +         significand(&numerator) = -arg_signif;
2949           numerator.exp = EXP_BIAS - 1;
2950           normalize(&numerator);                       /* 1 - arg */
2951  
2952 -         arg_signif = *(long long *)&(arg->sigl);
2953 +         arg_signif = significand(arg);
2954           if ( shrx(&arg_signif, -exponent) >= 0x80000000U )
2955             arg_signif++;       /* round up */
2956 -         *(long long *)&(denom.sigl) = arg_signif;
2957 +         significand(&denom) = arg_signif;
2958           denom.sigh |= 0x80000000;                    /* 1 + arg */
2959  
2960           arg->exp = numerator.exp;
2961 @@ -120,7 +117,7 @@
2962         }
2963      }
2964  
2965 -  *(long long *)&arg_signif = *(long long *)&(arg->sigl);
2966 +  arg_signif = significand(arg);
2967  
2968  #ifdef PARANOID
2969    /* This must always be true */
2970 @@ -136,8 +133,8 @@
2971    
2972    /* Now have arg_signif with binary point at the left
2973       .1xxxxxxxx */
2974 -  mul64(&arg_signif, &arg_signif, (long long *)(&argSq.sigl));
2975 -  mul64((long long *)(&argSq.sigl), (long long *)(&argSq.sigl), &argSqSq);
2976 +  mul64(&arg_signif, &arg_signif, &significand(&argSq));
2977 +  mul64(&significand(&argSq), &significand(&argSq), &argSqSq);
2978  
2979    /* will be a valid positive nr with expon = 0 */
2980    *(short *)&(pos_poly.sign) = 0;
2981 @@ -146,8 +143,8 @@
2982    /* Do the basic fixed point polynomial evaluation */
2983    polynomial(&pos_poly.sigl, (unsigned *)&argSqSq,
2984              (unsigned short (*)[4])oddplterms, HIPOWERop-1);
2985 -  mul64((long long *)(&argSq.sigl), (long long *)(&pos_poly.sigl),
2986 -       (long long *)(&pos_poly.sigl));
2987 +  mul64(&significand(&argSq), &significand(&pos_poly),
2988 +       &significand(&pos_poly));
2989  
2990    /* will be a valid positive nr with expon = 0 */
2991    *(short *)&(neg_poly.sign) = 0;
2992 @@ -158,7 +155,7 @@
2993              (unsigned short (*)[4])oddnegterms, HIPOWERon-1);
2994  
2995    /* Subtract the mantissas */
2996 -  *((long long *)(&pos_poly.sigl)) -= *((long long *)(&neg_poly.sigl));
2997 +  significand(&pos_poly) -= significand(&neg_poly);
2998  
2999    reg_move(&pos_poly, &odd_poly);
3000    poly_add_1(&odd_poly);
3001 @@ -166,8 +163,7 @@
3002    /* will be a valid positive nr with expon = 0 */
3003    *(short *)&(even_poly.sign) = 0;
3004  
3005 -  mul64((long long *)(&argSq.sigl),
3006 -       (long long *)(&denomterm), (long long *)(&even_poly.sigl));
3007 +  mul64(&significand(&argSq), &denomterm, &significand(&even_poly));
3008  
3009    poly_add_1(&even_poly);
3010  
3011 @@ -198,7 +194,7 @@
3012  shrx(&src->sigl, 1);
3013  
3014  #ifdef OBSOLETE
3015 -if ( round ) (*(long long *)&src->sigl)++;   /* Round to even */
3016 +if ( round ) significand(src)++;   /* Round to even */
3017  #endif OBSOLETE
3018  
3019  src->sigh |= 0x80000000;
3020 diff -u --recursive --new-file pl12/linux/kernel/FPU-emu/poly_div.S linux/kernel/FPU-emu/poly_div.S
3021 --- pl12/linux/kernel/FPU-emu/poly_div.S        Tue Nov 10 12:54:54 1992
3022 +++ linux/kernel/FPU-emu/poly_div.S     Wed Sep  1 18:30:05 1993
3023 @@ -8,9 +8,9 @@
3024   |                       Australia.  E-mail apm233m@vaxc.cc.monash.edu.au    |
3025   |                                                                           |
3026   | Call from C as:                                                           |
3027 - |   void poly_div2(long long *x)                                            |
3028 - |   void poly_div4(long long *x)                                            |
3029 - |   void poly_div16(long long *x)                                           |
3030 + |   void poly_div2(unsigned long long *x)                                   |
3031 + |   void poly_div4(unsigned long long *x)                                   |
3032 + |   void poly_div16(unsigned long long *x)                                  |
3033   |                                                                           |
3034   +---------------------------------------------------------------------------*/
3035  
3036 diff -u --recursive --new-file pl12/linux/kernel/FPU-emu/poly_l2.c linux/kernel/FPU-emu/poly_l2.c
3037 --- pl12/linux/kernel/FPU-emu/poly_l2.c Sun May 23 14:48:35 1993
3038 +++ linux/kernel/FPU-emu/poly_l2.c      Wed Sep  1 18:30:05 1993
3039 @@ -45,7 +45,7 @@
3040    short                  exponent;
3041    char           zero;         /* flag for an Xx == 0 */
3042    unsigned short  bits, shift;
3043 -  long long       Xsq;
3044 +  unsigned long long       Xsq;
3045    FPU_REG        accum, denom, num, Xx;
3046  
3047  
3048 @@ -79,7 +79,7 @@
3049  
3050    denom.sigl = num.sigl;
3051    denom.sigh = num.sigh;
3052 -  poly_div4((long long *)&(denom.sigl));
3053 +  poly_div4(&significand(&denom));
3054    denom.sigh += 0x80000000;                    /* set the msb */
3055    Xx.exp = EXP_BIAS;  /* needed to prevent errors in div routine */
3056    reg_u_div(&num, &denom, &Xx, FULL_PRECISION);
3057 @@ -86,7 +86,7 @@
3058  
3059    zero = !(Xx.sigh | Xx.sigl);
3060    
3061 -  mul64((long long *)&Xx.sigl, (long long *)&Xx.sigl, &Xsq);
3062 +  mul64(&significand(&Xx), &significand(&Xx), &Xsq);
3063    poly_div16(&Xsq);
3064  
3065    accum.exp = -1;              /* exponent of accum */
3066 @@ -123,7 +123,7 @@
3067             {
3068               /* The argument is of the form 1-x */
3069               /* Use  1-1/(1-x) = x/(1-x) */
3070 -             *((long long *)&num.sigl) = - *((long long *)&(arg->sigl));
3071 +             significand(&num) = - significand(arg);
3072               normalize(&num);
3073               reg_div(&num, arg, &num, FULL_PRECISION);
3074             }
3075 @@ -149,16 +149,16 @@
3076        return;
3077      }
3078  
3079 -  mul64((long long *)&accum.sigl,
3080 -       (long long *)&Xx.sigl, (long long *)&accum.sigl);
3081 +  mul64(&significand(&accum),
3082 +       &significand(&Xx), &significand(&accum));
3083  
3084 -  *((long long *)(&accum.sigl)) += *((long long *)(&Xx.sigl));
3085 +  significand(&accum) += significand(&Xx);
3086  
3087    if ( Xx.sigh > accum.sigh )
3088      {
3089        /* There was an overflow */
3090  
3091 -      poly_div2((long long *)&accum.sigl);
3092 +      poly_div2(&significand(&accum));
3093        accum.sigh |= 0x80000000;
3094        accum.exp++;
3095      }
3096 @@ -179,11 +179,11 @@
3097           /* Shift to get exponent == 0 */
3098           if ( accum.exp < 0 )
3099             {
3100 -             poly_div2((long long *)&accum.sigl);
3101 +             poly_div2(&significand(&accum));
3102               accum.exp++;
3103             }
3104           /* Just negate, but throw away the sign */
3105 -         *((long long *)&(accum.sigl)) = - *((long long *)&(accum.sigl));
3106 +         significand(&accum) = - significand(&accum);
3107           if ( exponent < 0 )
3108             exponent++;
3109           else
3110 @@ -198,11 +198,11 @@
3111        if ( accum.exp )
3112         {
3113           accum.exp++;
3114 -         poly_div2((long long *)&accum.sigl);
3115 +         poly_div2(&significand(&accum));
3116         }
3117        while ( shift )
3118         {
3119 -         poly_div2((long long *)&accum.sigl);
3120 +         poly_div2(&significand(&accum));
3121           if ( shift & 1)
3122             accum.sigh |= 0x80000000;
3123           shift >>= 1;
3124 @@ -227,7 +227,7 @@
3125  int    poly_l2p1(FPU_REG *arg, FPU_REG *result)
3126  {
3127    char         sign = 0;
3128 -  long long     Xsq;
3129 +  unsigned long long     Xsq;
3130    FPU_REG              arg_pl1, denom, accum, local_arg, poly_arg;
3131  
3132  
3133 @@ -263,7 +263,7 @@
3134    /* Get poly_arg bits aligned as required */
3135    shrx((unsigned *)&(poly_arg.sigl), -(poly_arg.exp - EXP_BIAS + 3));
3136  
3137 -  mul64((long long *)&(poly_arg.sigl), (long long *)&(poly_arg.sigl), &Xsq);
3138 +  mul64(&significand(&poly_arg), &significand(&poly_arg), &Xsq);
3139    poly_div16(&Xsq);
3140  
3141    /* Do the basic fixed point polynomial evaluation */
3142 diff -u --recursive --new-file pl12/linux/kernel/FPU-emu/poly_sin.c linux/kernel/FPU-emu/poly_sin.c
3143 --- pl12/linux/kernel/FPU-emu/poly_sin.c        Thu Jul 22 01:11:51 1993
3144 +++ linux/kernel/FPU-emu/poly_sin.c     Wed Sep  1 18:30:05 1993
3145 @@ -82,13 +82,13 @@
3146      {
3147        /* shift the argument right by the required places */
3148        if ( shrx(&(fixed_arg.sigl), -1-exponent) >= 0x80000000U )
3149 -       (*((long long *)(&(fixed_arg.sigl))))++;        /* round up */
3150 +       significand(&fixed_arg)++;      /* round up */
3151      }
3152    
3153 -  mul64((long long *)&(fixed_arg.sigl), (long long *)&(fixed_arg.sigl),
3154 -       (long long *)&(arg_sqrd.sigl));
3155 -  mul64((long long *)&(arg_sqrd.sigl), (long long *)&(arg_sqrd.sigl),
3156 -       (long long *)&(arg_to_4.sigl));
3157 +  mul64(&significand(&fixed_arg), &significand(&fixed_arg),
3158 +       &significand(&arg_sqrd));
3159 +  mul64(&significand(&arg_sqrd), &significand(&arg_sqrd),
3160 +       &significand(&arg_to_4));
3161    
3162    /* will be a valid positive nr with expon = 0 */
3163    *(short *)&(accum.sign) = 0;
3164 @@ -103,11 +103,11 @@
3165    
3166    /* Do the basic fixed point polynomial evaluation */
3167    polynomial(&(negaccum.sigl), &(arg_to_4.sigl), negterms, HIPOWER-1);
3168 -  mul64((long long *)&(arg_sqrd.sigl), (long long *)&(negaccum.sigl),
3169 -       (long long *)&(negaccum.sigl));
3170 +  mul64(&significand(&arg_sqrd), &significand(&negaccum),
3171 +       &significand(&negaccum));
3172  
3173    /* Subtract the mantissas */
3174 -  *((long long *)(&(accum.sigl))) -= *((long long *)(&(negaccum.sigl)));
3175 +  significand(&accum) -= significand(&negaccum);
3176    
3177    /* Convert to 64 bit signed-compatible */
3178    accum.exp = EXP_BIAS - 1 + accum.exp;
3179 diff -u --recursive --new-file pl12/linux/kernel/FPU-emu/poly_tan.c linux/kernel/FPU-emu/poly_tan.c
3180 --- pl12/linux/kernel/FPU-emu/poly_tan.c        Thu Jul 22 01:11:51 1993
3181 +++ linux/kernel/FPU-emu/poly_tan.c     Wed Sep  1 18:30:05 1993
3182 @@ -54,7 +54,7 @@
3183    short                exponent;
3184    FPU_REG       odd_poly, even_poly, pos_poly, neg_poly;
3185    FPU_REG       argSq;
3186 -  long long     arg_signif, argSqSq;
3187 +  unsigned long long     arg_signif, argSqSq;
3188    
3189  
3190    exponent = arg->exp - EXP_BIAS;
3191 @@ -64,7 +64,7 @@
3192      { arith_invalid(y_reg); return; }  /* Need a positive number */
3193  #endif PARANOID
3194  
3195 -  *(long long *)&arg_signif = *(long long *)&(arg->sigl);
3196 +  arg_signif = significand(arg);
3197    if ( exponent < -1 )
3198      {
3199        /* shift the argument right by the required places */
3200 @@ -72,8 +72,8 @@
3201         arg_signif++;   /* round up */
3202      }
3203  
3204 -  mul64(&arg_signif, &arg_signif, (long long *)(&argSq.sigl));
3205 -  mul64((long long *)(&argSq.sigl), (long long *)(&argSq.sigl), &argSqSq);
3206 +  mul64(&arg_signif, &arg_signif, &significand(&argSq));
3207 +  mul64(&significand(&argSq), &significand(&argSq), &argSqSq);
3208  
3209    /* will be a valid positive nr with expon = 0 */
3210    *(short *)&(pos_poly.sign) = 0;
3211 @@ -88,11 +88,11 @@
3212  
3213    /* Do the basic fixed point polynomial evaluation */
3214    polynomial(&neg_poly.sigl, (unsigned *)&argSqSq, oddnegterms, HIPOWERon-1);
3215 -  mul64((long long *)(&argSq.sigl), (long long *)(&neg_poly.sigl),
3216 -       (long long *)(&neg_poly.sigl));
3217 +  mul64(&significand(&argSq), &significand(&neg_poly),
3218 +       &significand(&neg_poly));
3219  
3220    /* Subtract the mantissas */
3221 -  *((long long *)(&pos_poly.sigl)) -= *((long long *)(&neg_poly.sigl));
3222 +  significand(&pos_poly) -= significand(&neg_poly);
3223  
3224    /* Convert to 64 bit signed-compatible */
3225    pos_poly.exp -= 1;
3226 @@ -110,8 +110,8 @@
3227    
3228    /* Do the basic fixed point polynomial evaluation */
3229    polynomial(&pos_poly.sigl, (unsigned *)&argSqSq, evenplterms, HIPOWERep-1);
3230 -  mul64((long long *)(&argSq.sigl),
3231 -       (long long *)(&pos_poly.sigl), (long long *)(&pos_poly.sigl));
3232 +  mul64(&significand(&argSq),
3233 +       &significand(&pos_poly), &significand(&pos_poly));
3234    
3235    /* will be a valid positive nr with expon = 0 */
3236    *(short *)&(neg_poly.sign) = 0;
3237 @@ -121,7 +121,7 @@
3238    polynomial(&neg_poly.sigl, (unsigned *)&argSqSq, evennegterms, HIPOWERen-1);
3239  
3240    /* Subtract the mantissas */
3241 -  *((long long *)(&neg_poly.sigl)) -= *((long long *)(&pos_poly.sigl));
3242 +  significand(&neg_poly) -= significand(&pos_poly);
3243    /* and multiply by argSq */
3244  
3245    /* Convert argSq to a valid reg number */
3246 diff -u --recursive --new-file pl12/linux/kernel/FPU-emu/reg_constant.c linux/kernel/FPU-emu/reg_constant.c
3247 --- pl12/linux/kernel/FPU-emu/reg_constant.c    Thu Jul 22 01:11:52 1993
3248 +++ linux/kernel/FPU-emu/reg_constant.c Wed Sep  1 18:30:05 1993
3249 @@ -67,10 +67,7 @@
3250      }
3251    push();
3252    reg_move(c, FPU_st0_ptr);
3253 -#ifdef PECULIAR_486
3254 -  /* Default, this conveys no information, but an 80486 does it. */
3255    clear_C1();
3256 -#endif PECULIAR_486
3257  }
3258  
3259  
3260 diff -u --recursive --new-file pl12/linux/kernel/FPU-emu/reg_ld_str.c linux/kernel/FPU-emu/reg_ld_str.c
3261 --- pl12/linux/kernel/FPU-emu/reg_ld_str.c      Thu Jul 22 01:11:52 1993
3262 +++ linux/kernel/FPU-emu/reg_ld_str.c   Wed Sep  1 18:30:05 1993
3263 @@ -312,7 +312,7 @@
3264    }
3265  
3266    e = EXP_BIAS + 63;
3267 -  *((long long *)&FPU_loaded_data.sigl) = s;
3268 +  significand(&FPU_loaded_data) = s;
3269    FPU_loaded_data.exp = e;
3270    FPU_loaded_data.tag = TW_Valid;
3271    normalize_nuo(&FPU_loaded_data);
3272 @@ -417,7 +417,7 @@
3273      }
3274    else
3275      {
3276 -      *((long long *)&FPU_loaded_data.sigl) = l;
3277 +      significand(&FPU_loaded_data) = l;
3278        FPU_loaded_data.exp = EXP_BIAS + 63;
3279        FPU_loaded_data.tag = TW_Valid;
3280        normalize_nuo(&FPU_loaded_data);
3281 @@ -1033,7 +1033,7 @@
3282  
3283    reg_move(FPU_st0_ptr, &t);
3284    precision_loss = round_to_int(&t);
3285 -  ll = *(unsigned long long *)(&t.sigl);
3286 +  ll = significand(&t);
3287  
3288    /* Check for overflow, by comparing with 999999999999999999 decimal. */
3289    if ( (t.sigh > 0x0de0b6b3) ||
3290 @@ -1042,14 +1042,16 @@
3291        EXCEPTION(EX_Invalid);
3292        /* This is a special case: see sec 16.2.5.1 of the 80486 book */
3293      invalid_operand:
3294 -      if ( control_word & EX_Invalid )
3295 +      if ( control_word & CW_Invalid )
3296         {
3297           /* Produce the QNaN "indefinite" */
3298           RE_ENTRANT_CHECK_OFF
3299           verify_area(VERIFY_WRITE,d,10);
3300 -         put_fs_byte(0xff,(unsigned char *) d+7); /* This byte undefined */
3301 -         put_fs_byte(0xff,(unsigned char *) d+8);
3302 -         put_fs_byte(0xff,(unsigned char *) d+9);
3303 +         for ( i = 0; i < 7; i++)
3304 +           put_fs_byte(0, (unsigned char *) d+i); /* These bytes "undefined" */
3305 +         put_fs_byte(0xc0, (unsigned char *) d+7); /* This byte "undefined" */
3306 +         put_fs_byte(0xff, (unsigned char *) d+8);
3307 +         put_fs_byte(0xff, (unsigned char *) d+9);
3308           RE_ENTRANT_CHECK_ON
3309           return 1;
3310         }
3311 @@ -1058,8 +1060,8 @@
3312      }
3313    else if ( precision_loss )
3314      {
3315 -      if ( set_precision_flag(precision_loss) )
3316 -       return 0;
3317 +      /* Precision loss doesn't stop the data transfer */
3318 +      set_precision_flag(precision_loss);
3319      }
3320  
3321    verify_area(VERIFY_WRITE,d,10);
3322 @@ -1096,7 +1098,7 @@
3323    if (r->tag == TW_Zero)
3324      {
3325        /* Make sure that zero is returned */
3326 -      *(long long *)&r->sigl = 0;
3327 +      significand(r) = 0;
3328        return 0;        /* o.k. */
3329      }
3330    
3331 @@ -1118,7 +1120,7 @@
3332           || (half_or_more && (r->sigl & 1)) )  /* odd -> even */
3333         {
3334           if ( very_big ) return 1;        /* overflow */
3335 -         (*(long long *)(&r->sigl)) ++;
3336 +         significand(r) ++;
3337           return PRECISION_LOST_UP;
3338         }
3339        break;
3340 @@ -1126,7 +1128,7 @@
3341        if (frac_part && r->sign)
3342         {
3343           if ( very_big ) return 1;        /* overflow */
3344 -         (*(long long *)(&r->sigl)) ++;
3345 +         significand(r) ++;
3346           return PRECISION_LOST_UP;
3347         }
3348        break;
3349 @@ -1134,7 +1136,7 @@
3350        if (frac_part && !r->sign)
3351         {
3352           if ( very_big ) return 1;        /* overflow */
3353 -         (*(long long *)(&r->sigl)) ++;
3354 +         significand(r) ++;
3355           return PRECISION_LOST_UP;
3356         }
3357        break;
3358 diff -u --recursive --new-file pl12/linux/kernel/FPU-emu/status_w.h linux/kernel/FPU-emu/status_w.h
3359 --- pl12/linux/kernel/FPU-emu/status_w.h        Thu Jul 22 01:11:53 1993
3360 +++ linux/kernel/FPU-emu/status_w.h     Wed Sep  1 18:30:06 1993
3361 @@ -10,6 +10,7 @@
3362  #ifndef _STATUS_H_
3363  #define _STATUS_H_
3364  
3365 +#include "fpu_emu.h"    /* for definition of PECULIAR_486 */
3366  
3367  #ifdef __ASSEMBLER__
3368  #define        Const__(x)      $##x
3369 @@ -51,8 +52,13 @@
3370    partial_status &= ~(SW_C0|SW_C1|SW_C2|SW_C3); \
3371    partial_status |= (cc) & (SW_C0|SW_C1|SW_C2|SW_C3); })
3372  
3373 -/* Clear the SW_C1 bit, "other bits undefined" */
3374 -#define clear_C1()  { partial_status &= ~SW_C1; }
3375 +#ifdef PECULIAR_486
3376 +   /* Default, this conveys no information, but an 80486 does it. */
3377 +   /* Clear the SW_C1 bit, "other bits undefined". */
3378 +#  define clear_C1()  { partial_status &= ~SW_C1; }
3379 +# else
3380 +#  define clear_C1()
3381 +#endif PECULIAR_486
3382  
3383  #endif __ASSEMBLER__
3384  
3385 diff -u --recursive --new-file pl12/linux/kernel/FPU-emu/version.h linux/kernel/FPU-emu/version.h
3386 --- pl12/linux/kernel/FPU-emu/version.h Thu Jul 22 01:11:53 1993
3387 +++ linux/kernel/FPU-emu/version.h      Wed Sep  1 18:30:06 1993
3388 @@ -9,5 +9,5 @@
3389   |                                                                           |
3390   +---------------------------------------------------------------------------*/
3391  
3392 -#define FPU_VERSION "wm-FPU-emu version BETA 1.5"
3393 +#define FPU_VERSION "wm-FPU-emu version BETA 1.6"
3394  
3395 diff -u --recursive --new-file pl12/linux/kernel/blk_drv/blk.h linux/kernel/blk_drv/blk.h
3396 --- pl12/linux/kernel/blk_drv/blk.h     Sat Aug 14 23:47:22 1993
3397 +++ linux/kernel/blk_drv/blk.h  Sat Sep  4 03:21:32 1993
3398 @@ -3,6 +3,7 @@
3399  
3400  #include <linux/sched.h>
3401  #include <linux/locks.h>
3402 +#include <linux/genhd.h>
3403  
3404  /*
3405   * NR_REQUEST is the number of entries in the request-queue.
3406 diff -u --recursive --new-file pl12/linux/kernel/blk_drv/genhd.c linux/kernel/blk_drv/genhd.c
3407 --- pl12/linux/kernel/blk_drv/genhd.c   Sat Jul  3 03:01:45 1993
3408 +++ linux/kernel/blk_drv/genhd.c        Sat Sep  4 03:22:38 1993
3409 @@ -194,7 +194,7 @@
3410  }
3411         
3412  /* This may be used only once, enforced by 'static int callable' */
3413 -extern "C" int sys_setup(void * BIOS)
3414 +asmlinkage int sys_setup(void * BIOS)
3415  {
3416         static int callable = 1;
3417         struct gendisk *p;
3418 diff -u --recursive --new-file pl12/linux/kernel/blk_drv/hd.c linux/kernel/blk_drv/hd.c
3419 --- pl12/linux/kernel/blk_drv/hd.c      Wed Jul 28 00:19:32 1993
3420 +++ linux/kernel/blk_drv/hd.c   Wed Sep  1 17:04:43 1993
3421 @@ -559,7 +559,7 @@
3422                 case BLKFLSBUF:
3423                         if(!suser())  return -EACCES;
3424                         if(!inode->i_rdev) return -EINVAL;
3425 -                       sync_dev(inode->i_rdev);
3426 +                       fsync_dev(inode->i_rdev);
3427                         invalidate_buffers(inode->i_rdev);
3428                         return 0;
3429  
3430 diff -u --recursive --new-file pl12/linux/kernel/blk_drv/ramdisk.c linux/kernel/blk_drv/ramdisk.c
3431 --- pl12/linux/kernel/blk_drv/ramdisk.c Wed Aug  4 22:38:40 1993
3432 +++ linux/kernel/blk_drv/ramdisk.c      Sat Sep  4 01:48:21 1993
3433 @@ -37,7 +37,8 @@
3434  repeat:
3435         INIT_REQUEST;
3436         addr = rd_start + (CURRENT->sector << 9);
3437 -       len = CURRENT->nr_sectors << 9;
3438 +       len = CURRENT->current_nr_sectors << 9;
3439 +
3440         if ((MINOR(CURRENT->dev) != MINOR_RAMDISK) ||
3441             (addr+len > rd_start+rd_length)) {
3442                 end_request(0);
3443 diff -u --recursive --new-file pl12/linux/kernel/blk_drv/scsi/aha1542.c linux/kernel/blk_drv/scsi/aha1542.c
3444 --- pl12/linux/kernel/blk_drv/scsi/aha1542.c    Wed Jul 28 00:19:32 1993
3445 +++ linux/kernel/blk_drv/scsi/aha1542.c Sat Sep  4 01:48:21 1993
3446 @@ -15,6 +15,7 @@
3447  #include <linux/head.h>
3448  #include <linux/types.h>
3449  #include <linux/string.h>
3450 +#include <linux/ioport.h>
3451  
3452  #include <linux/sched.h>
3453  #include <asm/dma.h>
3454 @@ -663,8 +664,10 @@
3455      
3456      indx = 0;
3457      while(indx < sizeof(bases)/sizeof(bases[0])){
3458 -      i = aha1542_test_port(bases[indx]);
3459 -      if (i) break;
3460 +      if(!check_region(bases[indx], 4)){
3461 +       i = aha1542_test_port(bases[indx]);
3462 +       if (i) break;
3463 +      };
3464        indx++;
3465      }
3466      if (indx == sizeof(bases)/sizeof(bases[0])) return 0;
3467 @@ -755,6 +758,7 @@
3468           aha1542_command(0, cmd, buffer, 512);
3469        }
3470  #endif
3471 +    snarf_region(bases[indx], 4);  /* Register the IO ports that we use */
3472      aha1542_host = hostnum;
3473      return 1;
3474  }
3475 diff -u --recursive --new-file pl12/linux/kernel/blk_drv/scsi/aha1740.c linux/kernel/blk_drv/scsi/aha1740.c
3476 --- pl12/linux/kernel/blk_drv/scsi/aha1740.c    Wed Jul 28 00:19:32 1993
3477 +++ linux/kernel/blk_drv/scsi/aha1740.c Sat Sep  4 01:48:21 1993
3478 @@ -21,6 +21,7 @@
3479  #include <linux/head.h>
3480  #include <linux/types.h>
3481  #include <linux/string.h>
3482 +#include <linux/ioport.h>
3483  
3484  #include <linux/sched.h>
3485  #include <asm/dma.h>
3486 @@ -432,6 +433,12 @@
3487      for ( slot=MINEISA; slot <= MAXEISA; slot++ )
3488      {
3489         base = SLOTBASE(slot);
3490 +
3491 +       /* The ioports for eisa boards are generally beyond that used in the
3492 +          check,snarf_region code, but this may change at some point, so we
3493 +          go through the motions. */
3494 +
3495 +       if(check_region(base, 0x5c)) continue;  /* See if in use */
3496         if ( aha1740_test_port())  break;
3497      }
3498      if ( slot > MAXEISA )
3499 @@ -455,6 +462,7 @@
3500          printk("Unable to allocate IRQ for adaptec controller.\n");
3501          return 0;
3502      }
3503 +    snarf_region(base, 0x5c);  /* Reserve the space that we need to use */
3504      return 1;
3505  }
3506  
3507 diff -u --recursive --new-file pl12/linux/kernel/blk_drv/scsi/fdomain.c linux/kernel/blk_drv/scsi/fdomain.c
3508 --- pl12/linux/kernel/blk_drv/scsi/fdomain.c    Sat Aug 14 09:05:16 1993
3509 +++ linux/kernel/blk_drv/scsi/fdomain.c Sat Sep  4 01:48:21 1993
3510 @@ -138,6 +138,7 @@
3511  #include <asm/system.h>
3512  #include <linux/errno.h>
3513  #include <linux/string.h>
3514 +#include <linux/ioport.h>
3515  
3516  #define VERSION          "$Revision: 3.18 $"
3517  
3518 @@ -528,6 +529,8 @@
3519  
3520        for (i = 0; !flag && i < PORT_COUNT; i++) {
3521          port_base = ports[i];
3522 +        if(check_region(port_base, 0x10)) continue;  /* skip if I/O port in
3523 +                                                        use */
3524  #if DEBUG_DETECT
3525          printk( " %x,", port_base );
3526  #endif
3527 @@ -607,6 +610,8 @@
3528        scsi_hosts[this_host].this_id = 7;
3529     }
3530     
3531 +   snarf_region(port_base, 0x10);  /* Register */
3532 +
3533  #if DO_DETECT
3534  
3535     /* These routines are here because of the way the SCSI bus behaves after
3536 diff -u --recursive --new-file pl12/linux/kernel/blk_drv/scsi/scsi.c linux/kernel/blk_drv/scsi/scsi.c
3537 --- pl12/linux/kernel/blk_drv/scsi/scsi.c       Sun Aug 15 10:55:23 1993
3538 +++ linux/kernel/blk_drv/scsi/scsi.c    Sat Sep  4 01:48:22 1993
3539 @@ -68,6 +68,7 @@
3540  #define WAS_TIMEDOUT   0x02
3541  #define WAS_SENSE      0x04
3542  #define IS_RESETTING   0x08
3543 +#define ASKED_FOR_SENSE 0x10
3544  
3545  extern int last_reset[];
3546  
3547 @@ -661,7 +662,7 @@
3548  static void scsi_request_sense (Scsi_Cmnd * SCpnt)
3549         {
3550         cli();
3551 -       SCpnt->flags |= WAS_SENSE;
3552 +       SCpnt->flags |= WAS_SENSE | ASKED_FOR_SENSE;
3553         update_timeout(SCpnt, SENSE_TIMEOUT);
3554         sti();
3555         
3556 @@ -805,9 +806,17 @@
3557  
3558  static int check_sense (Scsi_Cmnd * SCpnt)
3559         {
3560 -  /* If there is no sense information, request it.  */
3561 -  if (((SCpnt->sense_buffer[0] & 0x70) >> 4) != 7)
3562 -    return SUGGEST_SENSE;
3563 +  /* If there is no sense information, request it.  If we have already
3564 +     requested it, there is no point in asking again - the firmware must be
3565 +     confused. */
3566 +  if (((SCpnt->sense_buffer[0] & 0x70) >> 4) != 7) {
3567 +    if(!SCpnt->flags & ASKED_FOR_SENSE)
3568 +      return SUGGEST_SENSE;
3569 +    else
3570 +      return SUGGEST_RETRY;
3571 +      }
3572 +  
3573 +  SCpnt->flags &= ~ASKED_FOR_SENSE;
3574  
3575  #ifdef DEBUG_INIT
3576         printk("scsi%d : ", SCpnt->host);
3577 diff -u --recursive --new-file pl12/linux/kernel/blk_drv/scsi/sd.c linux/kernel/blk_drv/scsi/sd.c
3578 --- pl12/linux/kernel/blk_drv/scsi/sd.c Wed Aug 11 22:36:48 1993
3579 +++ linux/kernel/blk_drv/scsi/sd.c      Sat Sep  4 01:48:22 1993
3580 @@ -324,6 +324,7 @@
3581  
3582      INIT_SCSI_REQUEST;
3583  
3584 +
3585  /* We have to be careful here.  allocate_device will get a free pointer, but
3586     there is no guarantee that it is queueable.  In normal usage, we want to
3587     call this, because other types of devices may have the host all tied up,
3588 @@ -668,6 +669,7 @@
3589    int j = 0;
3590    unsigned char cmd[10];
3591    unsigned char *buffer;
3592 +  char spintime;
3593    int the_result, retries;
3594    Scsi_Cmnd * SCpnt;
3595  
3596 @@ -677,6 +679,58 @@
3597  
3598    SCpnt = allocate_device(NULL, rscsi_disks[i].device->index, 1);
3599    buffer = (unsigned char *) scsi_malloc(512);
3600 +
3601 +  spintime = 0;
3602 +
3603 +  /* Spin up drives, as required.  Only do this at boot time */
3604 +  if (current == task[0]){
3605 +    do{
3606 +      cmd[0] = TEST_UNIT_READY;
3607 +      cmd[1] = (rscsi_disks[i].device->lun << 5) & 0xe0;
3608 +      memset ((void *) &cmd[2], 0, 8);
3609 +      SCpnt->request.dev = 0xffff;  /* Mark as really busy again */
3610 +      SCpnt->sense_buffer[0] = 0;
3611 +      SCpnt->sense_buffer[2] = 0;
3612 +      
3613 +      scsi_do_cmd (SCpnt,
3614 +                  (void *) cmd, (void *) buffer,
3615 +                  512, sd_init_done,  SD_TIMEOUT,
3616 +                  MAX_RETRIES);
3617 +      
3618 +      while(SCpnt->request.dev != 0xfffe);
3619 +      
3620 +      the_result = SCpnt->result;
3621 +      
3622 +      /* Look for non-removable devices that return NOT_READY.  Issue command
3623 +        to spin up drive for these cases. */
3624 +      if(the_result && !rscsi_disks[i].device->removable && 
3625 +        SCpnt->sense_buffer[2] == NOT_READY) {
3626 +       int time1;
3627 +       if(!spintime){
3628 +         cmd[0] = START_STOP;
3629 +         cmd[1] = (rscsi_disks[i].device->lun << 5) & 0xe0;
3630 +         memset ((void *) &cmd[2], 0, 8);
3631 +         cmd[4] = 1; /* Start spin cycle */
3632 +         SCpnt->request.dev = 0xffff;  /* Mark as really busy again */
3633 +         SCpnt->sense_buffer[0] = 0;
3634 +         SCpnt->sense_buffer[2] = 0;
3635 +         
3636 +         scsi_do_cmd (SCpnt,
3637 +                      (void *) cmd, (void *) buffer,
3638 +                      512, sd_init_done,  SD_TIMEOUT,
3639 +                      MAX_RETRIES);
3640 +         
3641 +         while(SCpnt->request.dev != 0xfffe);
3642 +
3643 +         spintime = jiffies;
3644 +       };
3645 +
3646 +       time1 = jiffies;
3647 +       while(jiffies < time1 + 100); /* Wait 1 second for next try */
3648 +      };
3649 +    } while(the_result && spintime && spintime < jiffies+1500);
3650 +  };  /* current == task[0] */
3651 +
3652  
3653    retries = 3;
3654    do {
3655 diff -u --recursive --new-file pl12/linux/kernel/blk_drv/scsi/sd_ioctl.c linux/kernel/blk_drv/scsi/sd_ioctl.c
3656 --- pl12/linux/kernel/blk_drv/scsi/sd_ioctl.c   Wed Jul 28 00:19:33 1993
3657 +++ linux/kernel/blk_drv/scsi/sd_ioctl.c        Wed Sep  1 17:04:43 1993
3658 @@ -55,7 +55,7 @@
3659                 case BLKFLSBUF:
3660                         if(!suser())  return -EACCES;
3661                         if(!inode->i_rdev) return -EINVAL;
3662 -                       sync_dev(inode->i_rdev);
3663 +                       fsync_dev(inode->i_rdev);
3664                         invalidate_buffers(inode->i_rdev);
3665                         return 0;
3666  
3667 diff -u --recursive --new-file pl12/linux/kernel/blk_drv/scsi/seagate.c linux/kernel/blk_drv/scsi/seagate.c
3668 --- pl12/linux/kernel/blk_drv/scsi/seagate.c    Sat Aug  7 11:27:00 1993
3669 +++ linux/kernel/blk_drv/scsi/seagate.c Sat Sep  4 01:48:22 1993
3670 @@ -10,6 +10,8 @@
3671   *     Note : TMC-880 boards don't work because they have two bits in 
3672   *             the status register flipped, I'll fix this "RSN"
3673   *
3674 + *      This card does all the I/O via memory mapped I/O, so there is no need
3675 + *      to check or snarf a region of the I/O address space.
3676   */
3677  
3678  /*
3679 diff -u --recursive --new-file pl12/linux/kernel/blk_drv/scsi/st.c linux/kernel/blk_drv/scsi/st.c
3680 --- pl12/linux/kernel/blk_drv/scsi/st.c Wed Aug 11 22:36:49 1993
3681 +++ linux/kernel/blk_drv/scsi/st.c      Sun Aug 29 23:07:52 1993
3682 @@ -127,9 +127,11 @@
3683  /* Convert the result to success code */
3684  static int st_chk_result(Scsi_Cmnd * SCpnt)
3685  {
3686 +#ifdef DEBUG
3687    int dev = SCpnt->request.dev;
3688 +#endif
3689    int result = SCpnt->result;
3690 -  char * sense = SCpnt->sense_buffer;
3691 +  unsigned char * sense = SCpnt->sense_buffer;
3692  
3693    if (!result)
3694      return 0;
3695 diff -u --recursive --new-file pl12/linux/kernel/blk_drv/scsi/ultrastor.c linux/kernel/blk_drv/scsi/ultrastor.c
3696 --- pl12/linux/kernel/blk_drv/scsi/ultrastor.c  Wed Jul 28 00:19:35 1993
3697 +++ linux/kernel/blk_drv/scsi/ultrastor.c       Sat Sep  4 01:48:22 1993
3698 @@ -43,6 +43,7 @@
3699  #include <linux/string.h>
3700  #include <linux/sched.h>
3701  #include <linux/kernel.h>
3702 +#include <linux/ioport.h>
3703  
3704  #include <asm/io.h>
3705  #include <asm/system.h>
3706 @@ -194,6 +195,12 @@
3707      PORT_ADDRESS = 0;
3708      for (i = 0; i < ARRAY_SIZE(ultrastor_ports_14f); i++) {
3709         PORT_ADDRESS = ultrastor_ports_14f[i];
3710 +       if(check_region(PORT_ADDRESS, 4)) continue;
3711 +#else
3712 +       if(check_region(PORT_ADDRESS, 4)) {
3713 +         printk("Ultrastor I/O space already in use\n");
3714 +         return FALSE;
3715 +       };
3716  #endif
3717  
3718  #if (ULTRASTOR_DEBUG & UD_DETECT)
3719 @@ -248,6 +255,7 @@
3720            PORT_ADDRESS);
3721  #endif
3722  
3723 +    snarf_region(PORT_ADDRESS, 4); /* Register the I/O space that we use */
3724      /* All above tests passed, must be the right thing.  Get some useful
3725         info. */
3726      *(char *)&config_1 = inb(CONFIG(PORT_ADDRESS + 0));
3727 diff -u --recursive --new-file pl12/linux/kernel/blk_drv/scsi/wd7000.c linux/kernel/blk_drv/scsi/wd7000.c
3728 --- pl12/linux/kernel/blk_drv/scsi/wd7000.c     Sat Jul  3 03:40:30 1993
3729 +++ linux/kernel/blk_drv/scsi/wd7000.c  Sat Sep  4 01:48:23 1993
3730 @@ -20,6 +20,8 @@
3731  #include <asm/system.h>
3732  #include <asm/dma.h>
3733  #include <asm/io.h>
3734 +#include <linux/ioport.h>
3735 +
3736  #include "../blk.h"
3737  #include "scsi.h"
3738  #include "hosts.h"
3739 @@ -526,6 +528,7 @@
3740      int i,j;
3741      char const *base_address = NULL;
3742  
3743 +    if(check_region(IO_BASE, 4)) return 0;  /* IO ports in use */
3744      for(i=0;i<(sizeof(wd_bases)/sizeof(char *));i++){
3745         for(j=0;j<NUM_SIGNATURES;j++){
3746             if(!memcmp((void *)(wd_bases[i] + signatures[j].offset),
3747 @@ -537,6 +540,7 @@
3748      }
3749      if (base_address == NULL) return 0;
3750  
3751 +    snarf_region(IO_BASE, 4); /* Register our ports */
3752      /* Store our host number */
3753      wd7000_host = hostnum;
3754  
3755 diff -u --recursive --new-file pl12/linux/kernel/blk_drv/xd.c linux/kernel/blk_drv/xd.c
3756 --- pl12/linux/kernel/blk_drv/xd.c      Wed Jul 28 00:19:35 1993
3757 +++ linux/kernel/blk_drv/xd.c   Wed Sep  1 17:04:43 1993
3758 @@ -222,7 +222,7 @@
3759                         case BLKFLSBUF:
3760                                 if(!suser())  return -EACCES;
3761                                 if(!inode->i_rdev) return -EINVAL;
3762 -                               sync_dev(inode->i_rdev);
3763 +                               fsync_dev(inode->i_rdev);
3764                                 invalidate_buffers(inode->i_rdev);
3765                                 return 0;
3766                                 
3767 diff -u --recursive --new-file pl12/linux/kernel/chr_drv/keyboard.c linux/kernel/chr_drv/keyboard.c
3768 --- pl12/linux/kernel/chr_drv/keyboard.c        Sat Aug 14 18:52:34 1993
3769 +++ linux/kernel/chr_drv/keyboard.c     Wed Sep  1 09:04:14 1993
3770 @@ -65,7 +65,11 @@
3771  unsigned long kbd_dead_keys = 0;
3772  unsigned long kbd_prev_dead_keys = 0;
3773  
3774 +/* shift state counters.. */
3775  static unsigned char k_down[NR_SHIFT] = {0, };
3776 +/* keyboard key bitmap */
3777 +static unsigned long key_down[8] = { 0, };
3778 +
3779  static int want_console = -1;
3780  static int last_console = 0;           /* last used VC */
3781  static char rep = 0;                   /* flag telling character repeat */
3782 @@ -149,6 +153,7 @@
3783         kbd = kbd_table + fg_console;
3784         if (vc_kbd_flag(kbd,VC_RAW)) {
3785                 memset(k_down, 0, sizeof(k_down));
3786 +               memset(key_down, 0, sizeof(key_down));
3787                 put_queue(scancode);
3788                 goto end_kbd_intr;
3789         } else
3790 @@ -160,7 +165,6 @@
3791  static inline void translate(unsigned char scancode)
3792  {
3793         char break_flag;
3794 -       static unsigned long key_down[8] = { 0, };
3795         static unsigned char e0_keys[] = {
3796                 0x1c,   /* keypad enter */
3797                 0x1d,   /* right control */
3798 @@ -584,6 +588,8 @@
3799                 value = KVAL(K_SHIFT);
3800                 clr_vc_kbd_flag(kbd, VC_CAPSLOCK);
3801         }
3802 +       if (value > 3)
3803 +               return;
3804  
3805         if (up_flag) {
3806                 if (k_down[value])
3807 diff -u --recursive --new-file pl12/linux/kernel/chr_drv/mem.c linux/kernel/chr_drv/mem.c
3808 --- pl12/linux/kernel/chr_drv/mem.c     Mon Aug  9 18:02:32 1993
3809 +++ linux/kernel/chr_drv/mem.c  Sat Aug 21 10:19:32 1993
3810 @@ -129,12 +129,28 @@
3811  static int mmap_mem(struct inode * inode, struct file * file,
3812         unsigned long addr, size_t len, int prot, unsigned long off)
3813  {
3814 +       struct vm_area_struct * mpnt;
3815 +
3816         if (off & 0xfff || off + len < off)
3817                 return -ENXIO;
3818 -
3819         if (remap_page_range(addr, off, len, prot))
3820                 return -EAGAIN;
3821 -       
3822 +/* try to create a dummy vmm-structure so that the rest of the kernel knows we are here */
3823 +       mpnt = (struct vm_area_struct * ) kmalloc(sizeof(struct vm_area_struct), GFP_KERNEL);
3824 +       if (!mpnt)
3825 +               return 0;
3826 +
3827 +       mpnt->vm_task = current;
3828 +       mpnt->vm_start = addr;
3829 +       mpnt->vm_end = addr + len;
3830 +       mpnt->vm_page_prot = prot;
3831 +       mpnt->vm_share = NULL;
3832 +       mpnt->vm_inode = inode;
3833 +       inode->i_count++;
3834 +       mpnt->vm_offset = off;
3835 +       mpnt->vm_ops = NULL;
3836 +       mpnt->vm_next = current->mmap;
3837 +       current->mmap = mpnt;
3838         return 0;
3839  }
3840  
3841 diff -u --recursive --new-file pl12/linux/kernel/chr_drv/serial.c linux/kernel/chr_drv/serial.c
3842 --- pl12/linux/kernel/chr_drv/serial.c  Fri Aug 13 21:20:52 1993
3843 +++ linux/kernel/chr_drv/serial.c       Wed Aug 18 01:13:23 1993
3844 @@ -1321,12 +1321,10 @@
3845         
3846         switch (cmd) {
3847                 case TCSBRK:    /* SVID version: non-zero arg --> no break */
3848 -                       wait_until_sent(tty);
3849                         if (!arg)
3850                                 send_break(info, HZ/4); /* 1/4 second */
3851                         return 0;
3852                 case TCSBRKP:   /* support for POSIX tcsendbreak() */
3853 -                       wait_until_sent(tty);
3854                         send_break(info, arg ? arg*(HZ/10) : HZ/4);
3855                         return 0;
3856                 case TIOCGSOFTCAR:
3857 diff -u --recursive --new-file pl12/linux/kernel/chr_drv/tty_ioctl.c linux/kernel/chr_drv/tty_ioctl.c
3858 --- pl12/linux/kernel/chr_drv/tty_ioctl.c       Thu Jul 29 12:15:25 1993
3859 +++ linux/kernel/chr_drv/tty_ioctl.c    Wed Aug 18 01:13:07 1993
3860 @@ -605,7 +605,12 @@
3861                              tty->packet = 0;
3862                            return (0);
3863                         }
3864 -
3865 +               case TCSBRK: case TCSBRKP:
3866 +                       wait_until_sent(tty);
3867 +                       if (!tty->ioctl)
3868 +                               return 0;
3869 +                       tty->ioctl(tty, file, cmd, arg);
3870 +                       return 0;
3871                 default:
3872                         if (tty->ioctl) {
3873                                 retval = (tty->ioctl)(tty, file, cmd, arg);
3874 diff -u --recursive --new-file pl12/linux/kernel/chr_drv/vt.c linux/kernel/chr_drv/vt.c
3875 --- pl12/linux/kernel/chr_drv/vt.c      Sat Jul 31 20:32:36 1993
3876 +++ linux/kernel/chr_drv/vt.c   Sat Sep  4 03:17:54 1993
3877 @@ -35,7 +35,7 @@
3878  
3879  struct vt_cons vt_cons[NR_CONSOLES];
3880  
3881 -extern "C" int sys_ioperm(unsigned long from, unsigned long num, int on);
3882 +asmlinkage int sys_ioperm(unsigned long from, unsigned long num, int on);
3883  
3884  extern void change_console(unsigned int new_console);
3885  extern void complete_change_console(unsigned int new_console);
3886 diff -u --recursive --new-file pl12/linux/kernel/exit.c linux/kernel/exit.c
3887 --- pl12/linux/kernel/exit.c    Mon Aug  2 18:16:26 1993
3888 +++ linux/kernel/exit.c Sat Sep  4 03:04:34 1993
3889 @@ -274,7 +274,7 @@
3890   * POSIX specifies that kill(-1,sig) is unspecified, but what we have
3891   * is probably wrong.  Should make it like BSD or SYSV.
3892   */
3893 -extern "C" int sys_kill(int pid,int sig)
3894 +asmlinkage int sys_kill(int pid,int sig)
3895  {
3896         int err, retval = 0, count = 0;
3897  
3898 @@ -376,7 +376,7 @@
3899                 current->mmap = NULL;
3900                 while (mpnt) {
3901                         mpnt1 = mpnt->vm_next;
3902 -                       if (mpnt->vm_ops->close)
3903 +                       if (mpnt->vm_ops && mpnt->vm_ops->close)
3904                                 mpnt->vm_ops->close(mpnt);
3905                         kfree(mpnt);
3906                         mpnt = mpnt1;
3907 @@ -491,12 +491,12 @@
3908         goto fake_volatile;
3909  }
3910  
3911 -extern "C" int sys_exit(int error_code)
3912 +asmlinkage int sys_exit(int error_code)
3913  {
3914         do_exit((error_code&0xff)<<8);
3915  }
3916  
3917 -extern "C" int sys_wait4(pid_t pid,unsigned long * stat_addr, int options, struct rusage * ru)
3918 +asmlinkage int sys_wait4(pid_t pid,unsigned long * stat_addr, int options, struct rusage * ru)
3919  {
3920         int flag, retval;
3921         struct wait_queue wait = { current, NULL };
3922 @@ -587,7 +587,7 @@
3923   * sys_waitpid() remains for compatibility. waitpid() should be
3924   * implemented by calling sys_wait4() from libc.a.
3925   */
3926 -extern "C" int sys_waitpid(pid_t pid,unsigned long * stat_addr, int options)
3927 +asmlinkage int sys_waitpid(pid_t pid,unsigned long * stat_addr, int options)
3928  {
3929         return sys_wait4(pid, stat_addr, options, NULL);
3930  }
3931 diff -u --recursive --new-file pl12/linux/kernel/fork.c linux/kernel/fork.c
3932 --- pl12/linux/kernel/fork.c    Mon Aug  9 17:41:24 1993
3933 +++ linux/kernel/fork.c Sat Sep  4 03:01:14 1993
3934 @@ -23,7 +23,7 @@
3935  #include <asm/segment.h>
3936  #include <asm/system.h>
3937  
3938 -extern "C" void ret_from_sys_call(void) __asm__("ret_from_sys_call");
3939 +asmlinkage void ret_from_sys_call(void) __asm__("ret_from_sys_call");
3940  
3941  #define MAX_TASKS_PER_USER (NR_TASKS/2)
3942  
3943 @@ -113,7 +113,7 @@
3944   * information (task[nr]) and sets up the necessary registers. It
3945   * also copies the data segment in it's entirety.
3946   */
3947 -extern "C" int sys_fork(struct pt_regs regs)
3948 +asmlinkage int sys_fork(struct pt_regs regs)
3949  {
3950         struct pt_regs * childregs;
3951         struct task_struct *p;
3952 @@ -176,7 +176,7 @@
3953         p->exit_signal = clone_flags & CSIGNAL;
3954         p->tss.ldt = _LDT(nr);
3955         if (p->ldt) {
3956 -               if (p->ldt = (struct desc_struct*) __get_free_page(GFP_KERNEL))
3957 +               if ((p->ldt = (struct desc_struct*) __get_free_page(GFP_KERNEL)) != NULL)
3958                         memcpy(p->ldt, current->ldt, PAGE_SIZE);
3959         }
3960         p->tss.bitmap = offsetof(struct tss_struct,io_bitmap);
3961 diff -u --recursive --new-file pl12/linux/kernel/info.c linux/kernel/info.c
3962 --- pl12/linux/kernel/info.c    Sat Jul  3 01:02:33 1993
3963 +++ linux/kernel/info.c Sat Sep  4 03:11:09 1993
3964 @@ -14,7 +14,7 @@
3965  #include <linux/types.h>
3966  #include <linux/mm.h>
3967  
3968 -extern "C" int sys_sysinfo(struct sysinfo *info)
3969 +asmlinkage int sys_sysinfo(struct sysinfo *info)
3970  {
3971         int error;
3972         struct sysinfo val;
3973 diff -u --recursive --new-file pl12/linux/kernel/ioport.c linux/kernel/ioport.c
3974 --- pl12/linux/kernel/ioport.c  Wed Jul 14 19:07:28 1993
3975 +++ linux/kernel/ioport.c       Sat Sep  4 03:10:28 1993
3976 @@ -9,7 +9,10 @@
3977  #include <linux/kernel.h>
3978  #include <linux/errno.h>
3979  #include <linux/types.h>
3980 +#include <linux/ioport.h>
3981  
3982 +static unsigned long ioport_registrar[IO_BITMAP_SIZE] = {0, /* ... */};
3983 +
3984  #define _IODEBUG
3985  
3986  #ifdef IODEBUG
3987 @@ -40,14 +43,76 @@
3988  }
3989  #endif
3990  
3991 +/* Set EXTENT bits starting at BASE in BITMAP to value TURN_ON. */
3992 +asmlinkage void set_bitmap(unsigned long *bitmap,
3993 +                                                  short base, short extent, int new_value)
3994 +{
3995 +       int mask;
3996 +       unsigned long *bitmap_base = bitmap + (base >> 5);
3997 +       unsigned short low_index = base & 0x1f;
3998 +       int length = low_index + extent;
3999 +
4000 +       if (low_index != 0) {
4001 +               mask = (~0 << low_index);
4002 +               if (length < 32)
4003 +                               mask &= ~(~0 << length);
4004 +               if (new_value)
4005 +                       *bitmap_base++ |= mask;
4006 +               else
4007 +                       *bitmap_base++ &= ~mask;
4008 +               length -= 32;
4009 +       }
4010 +
4011 +       mask = (new_value ? ~0 : 0);
4012 +       while (length >= 32) {
4013 +               *bitmap_base++ = mask;
4014 +               length -= 32;
4015 +       }
4016 +
4017 +       if (length > 0) {
4018 +               mask = ~(~0 << length);
4019 +               if (new_value)
4020 +                       *bitmap_base++ |= mask;
4021 +               else
4022 +                       *bitmap_base++ &= ~mask;
4023 +       }
4024 +}
4025 +
4026 +/* Check for set bits in BITMAP starting at BASE, going to EXTENT. */
4027 +asmlinkage int check_bitmap(unsigned long *bitmap, short base, short extent)
4028 +{
4029 +       int mask;
4030 +       unsigned long *bitmap_base = bitmap + (base >> 5);
4031 +       unsigned short low_index = base & 0x1f;
4032 +       int length = low_index + extent;
4033 +
4034 +       if (low_index != 0) {
4035 +               mask = (~0 << low_index);
4036 +               if (length < 32)
4037 +                               mask &= ~(~0 << length);
4038 +               if (*bitmap_base++ & mask)
4039 +                       return 1;
4040 +               length -= 32;
4041 +       }
4042 +       while (length >= 32) {
4043 +               if (*bitmap_base++ != 0)
4044 +                       return 1;
4045 +               length -= 32;
4046 +       }
4047 +
4048 +       if (length > 0) {
4049 +               mask = ~(~0 << length);
4050 +               if (*bitmap_base++ & mask)
4051 +                       return 1;
4052 +       }
4053 +       return 0;
4054 +}
4055 +
4056  /*
4057   * this changes the io permissions bitmap in the current task.
4058   */
4059 -extern "C" int sys_ioperm(unsigned long from, unsigned long num, int turn_on)
4060 +asmlinkage int sys_ioperm(unsigned long from, unsigned long num, int turn_on)
4061  {
4062 -       unsigned long froml, lindex, tnum, numl, rindex, mask;
4063 -       unsigned long *iop;
4064 -
4065         if (from + num <= from)
4066                 return -EINVAL;
4067         if (from + num > IO_BITMAP_SIZE*32)
4068 @@ -54,42 +119,11 @@
4069                 return -EINVAL;
4070         if (!suser())
4071                 return -EPERM;
4072 -       froml = from >> 5;
4073 -       lindex = from & 0x1f;
4074 -       tnum = lindex + num;
4075 -       numl = (tnum + 0x1f) >> 5;
4076 -       rindex = tnum & 0x1f;
4077  
4078  #ifdef IODEBUG
4079         printk("io: from=%d num=%d %s\n", from, num, (turn_on ? "on" : "off"));
4080  #endif
4081 -
4082 -       if (numl) {
4083 -               iop = (unsigned long *)current->tss.io_bitmap + froml;
4084 -               if (lindex != 0) {
4085 -                       mask = (~0 << lindex);
4086 -                       if (--numl == 0 && rindex)
4087 -                               mask &= ~(~0 << rindex);
4088 -                       if (turn_on)
4089 -                               *iop++ &= ~mask;
4090 -                       else
4091 -                               *iop++ |= mask;
4092 -               }
4093 -               if (numl) {
4094 -                       if (rindex)
4095 -                               --numl;
4096 -                       mask = (turn_on ? 0 : ~0);
4097 -                       while (numl--)
4098 -                               *iop++ = mask;
4099 -                       if (numl && rindex) {
4100 -                               mask = ~(~0 << rindex);
4101 -                               if (turn_on)
4102 -                                       *iop++ &= ~mask;
4103 -                               else
4104 -                                       *iop++ |= mask;
4105 -                       }
4106 -               }
4107 -       }
4108 +       set_bitmap((unsigned long *)current->tss.io_bitmap, from, num, !turn_on);
4109         return 0;
4110  }
4111  
4112 @@ -105,7 +139,7 @@
4113   * on system-call entry - see also fork() and the signal handling
4114   * code.
4115   */
4116 -extern "C" int sys_iopl(long ebx,long ecx,long edx,
4117 +asmlinkage int sys_iopl(long ebx,long ecx,long edx,
4118              long esi, long edi, long ebp, long eax, long ds,
4119              long es, long fs, long gs, long orig_eax,
4120              long eip,long cs,long eflags,long esp,long ss)
4121 @@ -118,4 +152,33 @@
4122                 return -EPERM;
4123         *(&eflags) = (eflags & 0xffffcfff) | (level << 12);
4124         return 0;
4125 +}
4126 +
4127 +
4128 +void snarf_region(unsigned int from, unsigned int num)
4129 +{
4130 +       if (from > IO_BITMAP_SIZE*32)
4131 +               return;
4132 +       if (from + num > IO_BITMAP_SIZE*32)
4133 +               num = IO_BITMAP_SIZE*32 - from;
4134 +       set_bitmap(ioport_registrar, from, num, 1);
4135 +       return;
4136 +}
4137 +
4138 +int check_region(unsigned int from, unsigned int num)
4139 +{
4140 +       if (from > IO_BITMAP_SIZE*32)
4141 +               return 0;
4142 +       if (from + num > IO_BITMAP_SIZE*32)
4143 +               num = IO_BITMAP_SIZE*32 - from;
4144 +       return check_bitmap(ioport_registrar, from, num);
4145 +}
4146 +
4147 +/* Called from init/main.c to reserve IO ports. */
4148 +void reserve_setup(char *str, int *ints)
4149 +{
4150 +       int i;
4151 +
4152 +       for (i = 1; i < ints[0]; i += 2)
4153 +               snarf_region(ints[i], ints[i+1]);
4154  }
4155 diff -u --recursive --new-file pl12/linux/kernel/irq.c linux/kernel/irq.c
4156 --- pl12/linux/kernel/irq.c     Sun Jul 18 16:01:35 1993
4157 +++ linux/kernel/irq.c  Sat Sep  4 02:59:06 1993
4158 @@ -47,7 +47,7 @@
4159   * enabled.  do_bottom_half() is atomic with respect to itself: a
4160   * bottom_half handler need not be re-entrant.
4161   */
4162 -extern "C" void do_bottom_half(void)
4163 +asmlinkage void do_bottom_half(void)
4164  {
4165         unsigned long active;
4166         unsigned long mask, left;
4167 @@ -156,7 +156,7 @@
4168   * IRQ's should use this format: notably the keyboard/timer
4169   * routines.
4170   */
4171 -extern "C" void do_IRQ(int irq, struct pt_regs * regs)
4172 +asmlinkage void do_IRQ(int irq, struct pt_regs * regs)
4173  {
4174         struct sigaction * sa = irq + irq_sigaction;
4175  
4176 @@ -168,7 +168,7 @@
4177   * stuff - the handler is also running with interrupts disabled unless
4178   * it explicitly enables them later.
4179   */
4180 -extern "C" void do_fast_IRQ(int irq)
4181 +asmlinkage void do_fast_IRQ(int irq)
4182  {
4183         struct sigaction * sa = irq + irq_sigaction;
4184  
4185 diff -u --recursive --new-file pl12/linux/kernel/itimer.c linux/kernel/itimer.c
4186 --- pl12/linux/kernel/itimer.c  Sat Jul  3 01:01:39 1993
4187 +++ linux/kernel/itimer.c       Sat Sep  4 03:10:51 1993
4188 @@ -53,7 +53,7 @@
4189         return(0);
4190  }
4191  
4192 -extern "C" int sys_getitimer(int which, struct itimerval *value)
4193 +asmlinkage int sys_getitimer(int which, struct itimerval *value)
4194  {
4195         int error;
4196         struct itimerval get_buffer;
4197 @@ -98,7 +98,7 @@
4198         return 0;
4199  }
4200  
4201 -extern "C" int sys_setitimer(int which, struct itimerval *value, struct itimerval *ovalue)
4202 +asmlinkage int sys_setitimer(int which, struct itimerval *value, struct itimerval *ovalue)
4203  {
4204         int error;
4205         struct itimerval set_buffer, get_buffer;
4206 diff -u --recursive --new-file pl12/linux/kernel/ldt.c linux/kernel/ldt.c
4207 --- pl12/linux/kernel/ldt.c     Mon Aug  9 18:02:32 1993
4208 +++ linux/kernel/ldt.c  Sat Sep  4 03:11:30 1993
4209 @@ -86,7 +86,7 @@
4210         return 0;
4211  }
4212  
4213 -extern "C" int sys_modify_ldt(int func, void *ptr, unsigned long bytecount)
4214 +asmlinkage int sys_modify_ldt(int func, void *ptr, unsigned long bytecount)
4215  {
4216         if (func == 0)
4217                 return read_ldt(ptr, bytecount);
4218 diff -u --recursive --new-file pl12/linux/kernel/panic.c linux/kernel/panic.c
4219 --- pl12/linux/kernel/panic.c   Sat Jul  3 01:03:15 1993
4220 +++ linux/kernel/panic.c        Sat Sep  4 03:01:42 1993
4221 @@ -11,7 +11,7 @@
4222  #include <linux/kernel.h>
4223  #include <linux/sched.h>
4224  
4225 -extern "C" void sys_sync(void);        /* it's really int */
4226 +asmlinkage void sys_sync(void);        /* it's really int */
4227  
4228  volatile void panic(const char * s)
4229  {
4230 diff -u --recursive --new-file pl12/linux/kernel/printk.c linux/kernel/printk.c
4231 --- pl12/linux/kernel/printk.c  Mon Aug  9 18:02:32 1993
4232 +++ linux/kernel/printk.c       Sat Sep  4 03:04:18 1993
4233 @@ -47,7 +47,7 @@
4234   *     6 -- Disable printk's to console
4235   *     7 -- Enable printk's to console
4236   */
4237 -extern "C" int sys_syslog(int type, char * buf, int len)
4238 +asmlinkage int sys_syslog(int type, char * buf, int len)
4239  {
4240         unsigned long i, j, count;
4241         int do_clear = 0;
4242 @@ -104,7 +104,7 @@
4243                                 count = logged_chars;
4244                         j = log_start + log_size - count;
4245                         for (i = 0; i < count; i++) {
4246 -                               c = *((char *) log_buf + (j++ & LOG_BUF_LEN-1));
4247 +                               c = *((char *) log_buf+(j++ & (LOG_BUF_LEN-1)));
4248                                 put_fs_byte(c, buf++);
4249                         }
4250                         if (do_clear)
4251 @@ -124,7 +124,7 @@
4252  }
4253                         
4254  
4255 -extern "C" int printk(const char *fmt, ...)
4256 +asmlinkage int printk(const char *fmt, ...)
4257  {
4258         va_list args;
4259         int i,j;
4260 @@ -133,7 +133,7 @@
4261         i=vsprintf(buf,fmt,args);
4262         va_end(args);
4263         for (j = 0; j < i ; j++) {
4264 -               log_buf[(log_start+log_size) & LOG_BUF_LEN-1] = buf[j];
4265 +               log_buf[(log_start+log_size) & (LOG_BUF_LEN-1)] = buf[j];
4266                 if (log_size < LOG_BUF_LEN)
4267                         log_size++;
4268                 else
4269 diff -u --recursive --new-file pl12/linux/kernel/ptrace.c linux/kernel/ptrace.c
4270 --- pl12/linux/kernel/ptrace.c  Mon Aug  9 18:02:32 1993
4271 +++ linux/kernel/ptrace.c       Sat Sep  4 03:10:15 1993
4272 @@ -152,7 +152,7 @@
4273         if ((addr & ~PAGE_MASK) > PAGE_SIZE-sizeof(long)) {
4274                 low = get_long(tsk,addr & ~(sizeof(long)-1));
4275                 high = get_long(tsk,(addr+sizeof(long)) & ~(sizeof(long)-1));
4276 -               switch (addr & sizeof(long)-1) {
4277 +               switch (addr & (sizeof(long)-1)) {
4278                         case 1:
4279                                 low >>= 8;
4280                                 low |= high << 24;
4281 @@ -186,7 +186,7 @@
4282         if ((addr & ~PAGE_MASK) > PAGE_SIZE-sizeof(long)) {
4283                 low = get_long(tsk,addr & ~(sizeof(long)-1));
4284                 high = get_long(tsk,(addr+sizeof(long)) & ~(sizeof(long)-1));
4285 -               switch (addr & sizeof(long)-1) {
4286 +               switch (addr & (sizeof(long)-1)) {
4287                         case 0: /* shouldn't happen, but safety first */
4288                                 low = data;
4289                                 break;
4290 @@ -216,7 +216,7 @@
4291         return 0;
4292  }
4293  
4294 -extern "C" int sys_ptrace(long request, long pid, long addr, long data)
4295 +asmlinkage int sys_ptrace(long request, long pid, long addr, long data)
4296  {
4297         struct task_struct *child;
4298  
4299 @@ -285,6 +285,10 @@
4300                         if (res)
4301                                 return res;
4302                         tmp = get_stack_long(child, sizeof(long)*addr - MAGICNUMBER);
4303 +                       if (addr == DS || addr == ES ||
4304 +                           addr == FS || addr == GS ||
4305 +                           addr == CS || addr == SS)
4306 +                               tmp &= 0xffff;
4307                         put_fs_long(tmp,(unsigned long *) data);
4308                         return 0;
4309                 }
4310 @@ -302,8 +306,11 @@
4311                                 return -EIO;
4312                         if (addr == DS || addr == ES ||
4313                             addr == FS || addr == GS ||
4314 -                           addr == CS || addr == SS)
4315 -                               return -EIO;
4316 +                           addr == CS || addr == SS) {
4317 +                               data &= 0xffff;
4318 +                               if (data && (data & 3) != 3)
4319 +                                       return -EIO;
4320 +                       }
4321                         if (addr == EFL) {   /* flags. */
4322                                 data &= FLAG_MASK;
4323                                 data |= get_stack_long(child, EFL*sizeof(long)-MAGICNUMBER)  & ~FLAG_MASK;
4324 @@ -382,7 +389,7 @@
4325         }
4326  }
4327  
4328 -extern "C" void syscall_trace(void)
4329 +asmlinkage void syscall_trace(void)
4330  {
4331         if ((current->flags & (PF_PTRACED|PF_TRACESYS))
4332                         != (PF_PTRACED|PF_TRACESYS))
4333 diff -u --recursive --new-file pl12/linux/kernel/sched.c linux/kernel/sched.c
4334 --- pl12/linux/kernel/sched.c   Mon Aug  9 18:02:32 1993
4335 +++ linux/kernel/sched.c        Sat Sep  4 02:45:09 1993
4336 @@ -51,7 +51,7 @@
4337  extern void mem_use(void);
4338  
4339  extern int timer_interrupt(void);
4340 -extern "C" int system_call(void);
4341 +asmlinkage int system_call(void);
4342  
4343  static unsigned long init_kernel_stack[1024];
4344  struct task_struct init_task = INIT_TASK;
4345 @@ -82,7 +82,7 @@
4346   * Careful.. There are problems with IBM-designed IRQ13 behaviour.
4347   * Don't touch unless you *really* know how it works.
4348   */
4349 -extern "C" void math_state_restore(void)
4350 +asmlinkage void math_state_restore(void)
4351  {
4352         __asm__ __volatile__("clts");
4353         if (last_task_used_math == current)
4354 @@ -115,7 +115,7 @@
4355   * The "confuse_gcc" goto is used only to get better assembly code..
4356   * Djikstra probably hates me.
4357   */
4358 -extern "C" void schedule(void)
4359 +asmlinkage void schedule(void)
4360  {
4361         int c;
4362         struct task_struct * p;
4363 @@ -160,7 +160,7 @@
4364         switch_to(next);
4365  }
4366  
4367 -extern "C" int sys_pause(void)
4368 +asmlinkage int sys_pause(void)
4369  {
4370         current->state = TASK_INTERRUPTIBLE;
4371         schedule();
4372 @@ -421,7 +421,7 @@
4373         sti();
4374  }
4375  
4376 -extern "C" int sys_alarm(long seconds)
4377 +asmlinkage int sys_alarm(long seconds)
4378  {
4379         struct itimerval it_new, it_old;
4380  
4381 @@ -432,37 +432,37 @@
4382         return(it_old.it_value.tv_sec + (it_old.it_value.tv_usec / 1000000));
4383  }
4384  
4385 -extern "C" int sys_getpid(void)
4386 +asmlinkage int sys_getpid(void)
4387  {
4388         return current->pid;
4389  }
4390  
4391 -extern "C" int sys_getppid(void)
4392 +asmlinkage int sys_getppid(void)
4393  {
4394         return current->p_pptr->pid;
4395  }
4396  
4397 -extern "C" int sys_getuid(void)
4398 +asmlinkage int sys_getuid(void)
4399  {
4400         return current->uid;
4401  }
4402  
4403 -extern "C" int sys_geteuid(void)
4404 +asmlinkage int sys_geteuid(void)
4405  {
4406         return current->euid;
4407  }
4408  
4409 -extern "C" int sys_getgid(void)
4410 +asmlinkage int sys_getgid(void)
4411  {
4412         return current->gid;
4413  }
4414  
4415 -extern "C" int sys_getegid(void)
4416 +asmlinkage int sys_getegid(void)
4417  {
4418         return current->egid;
4419  }
4420  
4421 -extern "C" int sys_nice(long increment)
4422 +asmlinkage int sys_nice(long increment)
4423  {
4424         int newprio;
4425  
4426 diff -u --recursive --new-file pl12/linux/kernel/signal.c linux/kernel/signal.c
4427 --- pl12/linux/kernel/signal.c  Sun Aug 15 14:28:14 1993
4428 +++ linux/kernel/signal.c       Sat Sep  4 02:44:57 1993
4429 @@ -20,14 +20,39 @@
4430  
4431  extern int core_dump(long signr,struct pt_regs * regs);
4432  
4433 -extern "C" int do_signal(unsigned long oldmask, struct pt_regs * regs);
4434 +asmlinkage int do_signal(unsigned long oldmask, struct pt_regs * regs);
4435  
4436 -extern "C" int sys_sgetmask(void)
4437 +struct sigcontext_struct {
4438 +       unsigned short gs, __gsh;
4439 +       unsigned short fs, __fsh;
4440 +       unsigned short es, __esh;
4441 +       unsigned short ds, __dsh;
4442 +       unsigned long edi;
4443 +       unsigned long esi;
4444 +       unsigned long ebp;
4445 +       unsigned long esp;
4446 +       unsigned long ebx;
4447 +       unsigned long edx;
4448 +       unsigned long ecx;
4449 +       unsigned long eax;
4450 +       unsigned long trapno;
4451 +       unsigned long err;
4452 +       unsigned long eip;
4453 +       unsigned short cs, __csh;
4454 +       unsigned long eflags;
4455 +       unsigned long esp_at_signal;
4456 +       unsigned short ss, __ssh;
4457 +       unsigned long i387;
4458 +       unsigned long oldmask;
4459 +       unsigned long cr2;
4460 +};
4461 +
4462 +asmlinkage int sys_sgetmask(void)
4463  {
4464         return current->blocked;
4465  }
4466  
4467 -extern "C" int sys_ssetmask(int newmask)
4468 +asmlinkage int sys_ssetmask(int newmask)
4469  {
4470         int old=current->blocked;
4471  
4472 @@ -35,7 +60,7 @@
4473         return old;
4474  }
4475  
4476 -extern "C" int sys_sigpending(sigset_t *set)
4477 +asmlinkage int sys_sigpending(sigset_t *set)
4478  {
4479         int error;
4480         /* fill in "set" with signals pending but blocked. */
4481 @@ -48,7 +73,7 @@
4482  /*
4483   * atomically swap in the new signal mask, and wait for a signal.
4484   */
4485 -extern "C" int sys_sigsuspend(int restart, unsigned long oldmask, unsigned long set)
4486 +asmlinkage int sys_sigsuspend(int restart, unsigned long oldmask, unsigned long set)
4487  {
4488         unsigned long mask;
4489         struct pt_regs * regs = (struct pt_regs *) &restart;
4490 @@ -98,7 +123,7 @@
4491         }       
4492  }
4493  
4494 -extern "C" int sys_signal(int signum, unsigned long handler)
4495 +asmlinkage int sys_signal(int signum, unsigned long handler)
4496  {
4497         struct sigaction tmp;
4498  
4499 @@ -116,7 +141,7 @@
4500         return handler;
4501  }
4502  
4503 -extern "C" int sys_sigaction(int signum, const struct sigaction * action,
4504 +asmlinkage int sys_sigaction(int signum, const struct sigaction * action,
4505         struct sigaction * oldaction)
4506  {
4507         struct sigaction new_sa, *p;
4508 @@ -146,20 +171,37 @@
4509         return 0;
4510  }
4511  
4512 -extern "C" int sys_waitpid(pid_t pid,unsigned long * stat_addr, int options);
4513 +asmlinkage int sys_waitpid(pid_t pid,unsigned long * stat_addr, int options);
4514  
4515  /*
4516   * This sets regs->esp even though we don't actually use sigstacks yet..
4517   */
4518 -extern "C" int sys_sigreturn(unsigned long oldmask, unsigned long eip, unsigned long esp)
4519 +asmlinkage int sys_sigreturn(unsigned long __unused)
4520  {
4521 +#define CHECK_SEG(x) if (x) x |= 3
4522 +#define COPY(x) regs->x = context.x
4523 +       struct sigcontext_struct context;
4524         struct pt_regs * regs;
4525  
4526 -       regs = (struct pt_regs *) &oldmask;
4527 -       current->blocked = oldmask & _BLOCKABLE;
4528 -       regs->eip = eip;
4529 -       regs->esp = esp;
4530 -       return 0;
4531 +       regs = (struct pt_regs *) &__unused;
4532 +       memcpy_fromfs(&context,(void *) regs->esp, sizeof(context));
4533 +       current->blocked = context.oldmask & _BLOCKABLE;
4534 +       CHECK_SEG(context.ss);
4535 +       CHECK_SEG(context.cs);
4536 +       CHECK_SEG(context.ds);
4537 +       CHECK_SEG(context.es);
4538 +       CHECK_SEG(context.fs);
4539 +       CHECK_SEG(context.gs);
4540 +       COPY(eip); COPY(eflags);
4541 +       COPY(ecx); COPY(edx);
4542 +       COPY(ebx);
4543 +       COPY(esp); COPY(ebp);
4544 +       COPY(edi); COPY(esi);
4545 +       COPY(cs); COPY(ss);
4546 +       COPY(ds); COPY(es);
4547 +       COPY(fs); COPY(gs);
4548 +       regs->orig_eax = -1;            /* disable syscall checks */
4549 +       return context.eax;
4550  }
4551  
4552  /*
4553 @@ -166,15 +208,17 @@
4554   * Set up a signal frame... Make the stack look the way iBCS2 expects
4555   * it to look.
4556   */
4557 -static void setup_frame(unsigned long ** fp, unsigned long eip,
4558 -       struct pt_regs * regs, int signr,
4559 -       unsigned long sa_handler, unsigned long oldmask)
4560 +static void setup_frame(struct sigaction * sa, unsigned long ** fp, unsigned long eip,
4561 +       struct pt_regs * regs, int signr, unsigned long oldmask)
4562  {
4563         unsigned long * frame;
4564  
4565  #define __CODE ((unsigned long)(frame+24))
4566  #define CODE(x) ((unsigned long *) ((x)+__CODE))
4567 -       frame = *fp - 32;
4568 +       frame = *fp;
4569 +       if (regs->ss != USER_DS)
4570 +               frame = (unsigned long *) sa->sa_restorer;
4571 +       frame -= 32;
4572         verify_area(VERIFY_WRITE,frame,32*4);
4573  /* set up the "normal" stack seen by the signal handler (iBCS2) */
4574         put_fs_long(__CODE,frame);
4575 @@ -186,32 +230,26 @@
4576         put_fs_long(regs->edi, frame+6);
4577         put_fs_long(regs->esi, frame+7);
4578         put_fs_long(regs->ebp, frame+8);
4579 -       put_fs_long(regs->esp, frame+9);
4580 +       put_fs_long((long)*fp, frame+9);
4581         put_fs_long(regs->ebx, frame+10);
4582         put_fs_long(regs->edx, frame+11);
4583         put_fs_long(regs->ecx, frame+12);
4584         put_fs_long(regs->eax, frame+13);
4585 -       put_fs_long(0, frame+14);               /* trapno */
4586 -       put_fs_long(0, frame+15);               /* err */
4587 -       put_fs_long(regs->eip, frame+16);
4588 +       put_fs_long(0, frame+14);               /* trapno - not implemented */
4589 +       put_fs_long(0, frame+15);               /* err - not implemented */
4590 +       put_fs_long(eip, frame+16);
4591         put_fs_long(regs->cs, frame+17);
4592         put_fs_long(regs->eflags, frame+18);
4593         put_fs_long(regs->esp, frame+19);
4594         put_fs_long(regs->ss, frame+20);
4595 -       put_fs_long(0,frame+21);                /* 387 state pointer */
4596 -/* linux extended stack - easier to handle.. */
4597 -       put_fs_long(regs->eflags, frame+22);
4598 -       put_fs_long(eip, frame+23);
4599 +       put_fs_long(0,frame+21);                /* 387 state pointer - not implemented*/
4600 +/* non-iBCS2 extensions.. */
4601 +       put_fs_long(oldmask, frame+22);
4602 +       put_fs_long(0, frame+23);               /* cr2 - not implemented */
4603  /* set up the return code... */
4604         put_fs_long(0x0000b858, CODE(0));       /* popl %eax ; movl $,%eax */
4605 -       put_fs_long(0x00bb0000, CODE(4));       /* movl $,%ebx */
4606 -       put_fs_long(0xcd000000, CODE(8));       /* int $0x80 */
4607 -       put_fs_long(0x0fa90f80, CODE(12));      /* pop %gs ; pop %fs */
4608 -       put_fs_long(0x611f07a1, CODE(16));      /* pop %es ; pop %ds ; popad */
4609 -       put_fs_long(0x20c48390, CODE(20));      /* nop ; addl $32,%esp */
4610 -       put_fs_long(0x0020c29d, CODE(24));      /* popfl ; ret $32 */
4611 -       put_fs_long(__NR_ssetmask, CODE(2));
4612 -       put_fs_long(oldmask, CODE(7));
4613 +       put_fs_long(0x80cd0000, CODE(4));       /* int $0x80 */
4614 +       put_fs_long(__NR_sigreturn, CODE(2));
4615         *fp = frame;
4616  #undef __CODE
4617  #undef CODE
4618 @@ -226,7 +264,7 @@
4619   * the kernel can handle, and then we build all the user-level signal handling
4620   * stack-frames in one go after that.
4621   */
4622 -extern "C" int do_signal(unsigned long oldmask, struct pt_regs * regs)
4623 +asmlinkage int do_signal(unsigned long oldmask, struct pt_regs * regs)
4624  {
4625         unsigned long mask = ~current->blocked;
4626         unsigned long handler_signal = 0;
4627 @@ -233,7 +271,6 @@
4628         unsigned long *frame = NULL;
4629         unsigned long eip = 0;
4630         unsigned long signr;
4631 -       unsigned long sa_handler;
4632         struct sigaction * sa;
4633  
4634         while ((signr = current->signal & mask)) {
4635 @@ -317,20 +354,20 @@
4636         frame = (unsigned long *) regs->esp;
4637         signr = 1;
4638         sa = current->sigaction;
4639 -       if (regs->cs != USER_CS || regs->ss != USER_DS)
4640 -               printk("Warning: signal handler with nonstandard code/stack segment\n");
4641         for (mask = 1 ; mask ; sa++,signr++,mask += mask) {
4642                 if (mask > handler_signal)
4643                         break;
4644                 if (!(mask & handler_signal))
4645                         continue;
4646 -               sa_handler = (unsigned long) sa->sa_handler;
4647 +               setup_frame(sa,&frame,eip,regs,signr,oldmask);
4648 +               eip = (unsigned long) sa->sa_handler;
4649                 if (sa->sa_flags & SA_ONESHOT)
4650                         sa->sa_handler = NULL;
4651  /* force a supervisor-mode page-in of the signal handler to reduce races */
4652 -               __asm__("testb $0,%%fs:%0": :"m" (*(char *) sa_handler));
4653 -               setup_frame(&frame,eip,regs,signr,sa_handler,oldmask);
4654 -               eip = sa_handler;
4655 +               __asm__("testb $0,%%fs:%0": :"m" (*(char *) eip));
4656 +               regs->cs = USER_CS; regs->ss = USER_DS;
4657 +               regs->ds = USER_DS; regs->es = USER_DS;
4658 +               regs->gs = USER_DS; regs->fs = USER_DS;
4659                 current->blocked |= sa->sa_mask;
4660                 oldmask |= sa->sa_mask;
4661         }
4662 diff -u --recursive --new-file pl12/linux/kernel/sys.c linux/kernel/sys.c
4663 --- pl12/linux/kernel/sys.c     Mon Aug  9 18:02:32 1993
4664 +++ linux/kernel/sys.c  Sat Sep  4 02:44:45 1993
4665 @@ -56,7 +56,7 @@
4666         return 0;
4667  }
4668  
4669 -extern "C" int sys_setpriority(int which, int who, int niceval)
4670 +asmlinkage int sys_setpriority(int which, int who, int niceval)
4671  {
4672         struct task_struct **p;
4673         int error = ESRCH;
4674 @@ -86,7 +86,7 @@
4675         return -error;
4676  }
4677  
4678 -extern "C" int sys_getpriority(int which, int who)
4679 +asmlinkage int sys_getpriority(int which, int who)
4680  {
4681         struct task_struct **p;
4682         int max_prio = 0;
4683 @@ -103,37 +103,37 @@
4684         return(max_prio ? max_prio : -ESRCH);
4685  }
4686  
4687 -extern "C" int sys_profil(void)
4688 +asmlinkage int sys_profil(void)
4689  {
4690         return -ENOSYS;
4691  }
4692  
4693 -extern "C" int sys_ftime(void)
4694 +asmlinkage int sys_ftime(void)
4695  {
4696         return -ENOSYS;
4697  }
4698  
4699 -extern "C" int sys_break(void)
4700 +asmlinkage int sys_break(void)
4701  {
4702         return -ENOSYS;
4703  }
4704  
4705 -extern "C" int sys_stty(void)
4706 +asmlinkage int sys_stty(void)
4707  {
4708         return -ENOSYS;
4709  }
4710  
4711 -extern "C" int sys_gtty(void)
4712 +asmlinkage int sys_gtty(void)
4713  {
4714         return -ENOSYS;
4715  }
4716  
4717 -extern "C" int sys_prof(void)
4718 +asmlinkage int sys_prof(void)
4719  {
4720         return -ENOSYS;
4721  }
4722  
4723 -extern "C" unsigned long save_v86_state(struct vm86_regs * regs)
4724 +asmlinkage unsigned long save_v86_state(struct vm86_regs * regs)
4725  {
4726         unsigned long stack;
4727  
4728 @@ -169,7 +169,7 @@
4729         }
4730  }
4731  
4732 -extern "C" int sys_vm86(struct vm86_struct * v86)
4733 +asmlinkage int sys_vm86(struct vm86_struct * v86)
4734  {
4735         struct vm86_struct info;
4736         struct pt_regs * pt_regs = (struct pt_regs *) &v86;
4737 @@ -216,7 +216,7 @@
4738   *
4739   * reboot doesn't sync: do that yourself before calling this.
4740   */
4741 -extern "C" int sys_reboot(int magic, int magic_too, int flag)
4742 +asmlinkage int sys_reboot(int magic, int magic_too, int flag)
4743  {
4744         if (!suser())
4745                 return -EPERM;
4746 @@ -258,7 +258,7 @@
4747   * 100% compatible with BSD.  A program which uses just setgid() will be
4748   * 100% compatible with POSIX w/ Saved ID's. 
4749   */
4750 -extern "C" int sys_setregid(gid_t rgid, gid_t egid)
4751 +asmlinkage int sys_setregid(gid_t rgid, gid_t egid)
4752  {
4753         int old_rgid = current->gid;
4754  
4755 @@ -287,7 +287,7 @@
4756  /*
4757   * setgid() is implemeneted like SysV w/ SAVED_IDS 
4758   */
4759 -extern "C" int sys_setgid(gid_t gid)
4760 +asmlinkage int sys_setgid(gid_t gid)
4761  {
4762         if (suser())
4763                 current->gid = current->egid = current->sgid = gid;
4764 @@ -298,37 +298,37 @@
4765         return 0;
4766  }
4767  
4768 -extern "C" int sys_acct(void)
4769 +asmlinkage int sys_acct(void)
4770  {
4771         return -ENOSYS;
4772  }
4773  
4774 -extern "C" int sys_phys(void)
4775 +asmlinkage int sys_phys(void)
4776  {
4777         return -ENOSYS;
4778  }
4779  
4780 -extern "C" int sys_lock(void)
4781 +asmlinkage int sys_lock(void)
4782  {
4783         return -ENOSYS;
4784  }
4785  
4786 -extern "C" int sys_mpx(void)
4787 +asmlinkage int sys_mpx(void)
4788  {
4789         return -ENOSYS;
4790  }
4791  
4792 -extern "C" int sys_ulimit(void)
4793 +asmlinkage int sys_ulimit(void)
4794  {
4795         return -ENOSYS;
4796  }
4797  
4798 -extern "C" int sys_old_syscall(void)
4799 +asmlinkage int sys_old_syscall(void)
4800  {
4801         return -ENOSYS;
4802  }
4803  
4804 -extern "C" int sys_time(long * tloc)
4805 +asmlinkage int sys_time(long * tloc)
4806  {
4807         int i, error;
4808  
4809 @@ -355,7 +355,7 @@
4810   * 100% compatible with BSD.  A program which uses just setuid() will be
4811   * 100% compatible with POSIX w/ Saved ID's. 
4812   */
4813 -extern "C" int sys_setreuid(uid_t ruid, uid_t euid)
4814 +asmlinkage int sys_setreuid(uid_t ruid, uid_t euid)
4815  {
4816         int old_ruid = current->uid;
4817         
4818 @@ -392,7 +392,7 @@
4819   * will allow a root program to temporarily drop privileges and be able to
4820   * regain them by swapping the real and effective uid.  
4821   */
4822 -extern "C" int sys_setuid(uid_t uid)
4823 +asmlinkage int sys_setuid(uid_t uid)
4824  {
4825         if (suser())
4826                 current->uid = current->euid = current->suid = uid;
4827 @@ -403,7 +403,7 @@
4828         return(0);
4829  }
4830  
4831 -extern "C" int sys_stime(long * tptr)
4832 +asmlinkage int sys_stime(long * tptr)
4833  {
4834         if (!suser())
4835                 return -EPERM;
4836 @@ -412,7 +412,7 @@
4837         return 0;
4838  }
4839  
4840 -extern "C" int sys_times(struct tms * tbuf)
4841 +asmlinkage int sys_times(struct tms * tbuf)
4842  {
4843         if (tbuf) {
4844                 int error = verify_area(VERIFY_WRITE,tbuf,sizeof *tbuf);
4845 @@ -426,7 +426,7 @@
4846         return jiffies;
4847  }
4848  
4849 -extern "C" int sys_brk(unsigned long brk)
4850 +asmlinkage int sys_brk(unsigned long brk)
4851  {
4852         int freepages;
4853         unsigned long rlim;
4854 @@ -487,7 +487,7 @@
4855   * only important on a multi-user system anyway, to make sure one user
4856   * can't send a signal to a process owned by another.  -TYT, 12/12/91
4857   */
4858 -extern "C" int sys_setpgid(pid_t pid, pid_t pgid)
4859 +asmlinkage int sys_setpgid(pid_t pid, pid_t pgid)
4860  {
4861         int i; 
4862  
4863 @@ -513,12 +513,12 @@
4864         return -ESRCH;
4865  }
4866  
4867 -extern "C" int sys_getpgrp(void)
4868 +asmlinkage int sys_getpgrp(void)
4869  {
4870         return current->pgrp;
4871  }
4872  
4873 -extern "C" int sys_setsid(void)
4874 +asmlinkage int sys_setsid(void)
4875  {
4876         if (current->leader && !suser())
4877                 return -EPERM;
4878 @@ -531,7 +531,7 @@
4879  /*
4880   * Supplementary group ID's
4881   */
4882 -extern "C" int sys_getgroups(int gidsetsize, gid_t *grouplist)
4883 +asmlinkage int sys_getgroups(int gidsetsize, gid_t *grouplist)
4884  {
4885         int i;
4886  
4887 @@ -551,7 +551,7 @@
4888         return(i);
4889  }
4890  
4891 -extern "C" int sys_setgroups(int gidsetsize, gid_t *grouplist)
4892 +asmlinkage int sys_setgroups(int gidsetsize, gid_t *grouplist)
4893  {
4894         int     i;
4895  
4896 @@ -583,7 +583,7 @@
4897         return 0;
4898  }
4899  
4900 -extern "C" int sys_newuname(struct new_utsname * name)
4901 +asmlinkage int sys_newuname(struct new_utsname * name)
4902  {
4903         int error;
4904  
4905 @@ -595,7 +595,7 @@
4906         return error;
4907  }
4908  
4909 -extern "C" int sys_uname(struct old_utsname * name)
4910 +asmlinkage int sys_uname(struct old_utsname * name)
4911  {
4912         int error;
4913         if (!name)
4914 @@ -616,7 +616,7 @@
4915         return 0;
4916  }
4917  
4918 -extern "C" int sys_olduname(struct oldold_utsname * name)
4919 +asmlinkage int sys_olduname(struct oldold_utsname * name)
4920  {
4921         int error;
4922         if (!name)
4923 @@ -640,7 +640,7 @@
4924  /*
4925   * Only sethostname; gethostname can be implemented by calling uname()
4926   */
4927 -extern "C" int sys_sethostname(char *name, int len)
4928 +asmlinkage int sys_sethostname(char *name, int len)
4929  {
4930         int     i;
4931         
4932 @@ -660,7 +660,7 @@
4933   * Only setdomainname; getdomainname can be implemented by calling
4934   * uname()
4935   */
4936 -extern "C" int sys_setdomainname(char *name, int len)
4937 +asmlinkage int sys_setdomainname(char *name, int len)
4938  {
4939         int     i;
4940         
4941 @@ -676,7 +676,7 @@
4942         return 0;
4943  }
4944  
4945 -extern "C" int sys_getrlimit(unsigned int resource, struct rlimit *rlim)
4946 +asmlinkage int sys_getrlimit(unsigned int resource, struct rlimit *rlim)
4947  {
4948         int error;
4949  
4950 @@ -692,7 +692,7 @@
4951         return 0;       
4952  }
4953  
4954 -extern "C" int sys_setrlimit(unsigned int resource, struct rlimit *rlim)
4955 +asmlinkage int sys_setrlimit(unsigned int resource, struct rlimit *rlim)
4956  {
4957         struct rlimit new_rlim, *old_rlim;
4958  
4959 @@ -761,7 +761,7 @@
4960         return 0;
4961  }
4962  
4963 -extern "C" int sys_getrusage(int who, struct rusage *ru)
4964 +asmlinkage int sys_getrusage(int who, struct rusage *ru)
4965  {
4966         if (who != RUSAGE_SELF && who != RUSAGE_CHILDREN)
4967                 return -EINVAL;
4968 @@ -808,7 +808,7 @@
4969  #endif /* not __i386__ */
4970  }
4971  
4972 -extern "C" int sys_gettimeofday(struct timeval *tv, struct timezone *tz)
4973 +asmlinkage int sys_gettimeofday(struct timeval *tv, struct timezone *tz)
4974  {
4975         int error;
4976  
4977 @@ -840,7 +840,7 @@
4978   * soon as possible, so that the clock can be set right.  Otherwise,
4979   * various programs will get confused when the clock gets warped.
4980   */
4981 -extern "C" int sys_settimeofday(struct timeval *tv, struct timezone *tz)
4982 +asmlinkage int sys_settimeofday(struct timeval *tv, struct timezone *tz)
4983  {
4984         static int      firsttime = 1;
4985  
4986 @@ -888,7 +888,7 @@
4987         startup_time += sys_tz.tz_minuteswest*60;
4988  }
4989  
4990 -extern "C" int sys_umask(int mask)
4991 +asmlinkage int sys_umask(int mask)
4992  {
4993         int old = current->umask;
4994  
4995 diff -u --recursive --new-file pl12/linux/kernel/traps.c linux/kernel/traps.c
4996 --- pl12/linux/kernel/traps.c   Wed Jul 14 16:57:11 1993
4997 +++ linux/kernel/traps.c        Sat Sep  4 02:44:31 1993
4998 @@ -41,31 +41,32 @@
4999  
5000  void page_exception(void);
5001  
5002 -extern "C" void divide_error(void);
5003 -extern "C" void debug(void);
5004 -extern "C" void nmi(void);
5005 -extern "C" void int3(void);
5006 -extern "C" void overflow(void);
5007 -extern "C" void bounds(void);
5008 -extern "C" void invalid_op(void);
5009 -extern "C" void device_not_available(void);
5010 -extern "C" void double_fault(void);
5011 -extern "C" void coprocessor_segment_overrun(void);
5012 -extern "C" void invalid_TSS(void);
5013 -extern "C" void segment_not_present(void);
5014 -extern "C" void stack_segment(void);
5015 -extern "C" void general_protection(void);
5016 -extern "C" void page_fault(void);
5017 -extern "C" void coprocessor_error(void);
5018 -extern "C" void reserved(void);
5019 -extern "C" void alignment_check(void);
5020 +asmlinkage void divide_error(void);
5021 +asmlinkage void debug(void);
5022 +asmlinkage void nmi(void);
5023 +asmlinkage void int3(void);
5024 +asmlinkage void overflow(void);
5025 +asmlinkage void bounds(void);
5026 +asmlinkage void invalid_op(void);
5027 +asmlinkage void device_not_available(void);
5028 +asmlinkage void double_fault(void);
5029 +asmlinkage void coprocessor_segment_overrun(void);
5030 +asmlinkage void invalid_TSS(void);
5031 +asmlinkage void segment_not_present(void);
5032 +asmlinkage void stack_segment(void);
5033 +asmlinkage void general_protection(void);
5034 +asmlinkage void page_fault(void);
5035 +asmlinkage void coprocessor_error(void);
5036 +asmlinkage void reserved(void);
5037 +asmlinkage void alignment_check(void);
5038  
5039  /*static*/ void die_if_kernel(char * str, struct pt_regs * regs, long err)
5040  {
5041         int i;
5042  
5043 -       if ((regs->eflags & VM_MASK) || ((0xffff & regs->cs) == USER_CS))
5044 +       if ((regs->eflags & VM_MASK) || (3 & regs->cs) == 3)
5045                 return;
5046 +
5047         printk("%s: %04x\n", str, err & 0xffff);
5048         printk("EIP:    %04x:%p\nEFLAGS: %p\n", 0xffff & regs->cs,regs->eip,regs->eflags);
5049         printk("eax: %08x   ebx: %08x   ecx: %08x   edx: %08x\n",
5050 @@ -82,31 +83,31 @@
5051         do_exit(SIGSEGV);
5052  }
5053  
5054 -extern "C" void do_double_fault(struct pt_regs * regs, long error_code)
5055 +asmlinkage void do_double_fault(struct pt_regs * regs, long error_code)
5056  {
5057         send_sig(SIGSEGV, current, 1);
5058         die_if_kernel("double fault",regs,error_code);
5059  }
5060  
5061 -extern "C" void do_general_protection(struct pt_regs * regs, long error_code)
5062 +asmlinkage void do_general_protection(struct pt_regs * regs, long error_code)
5063  {
5064         send_sig(SIGSEGV, current, 1);
5065         die_if_kernel("general protection",regs,error_code);
5066  }
5067  
5068 -extern "C" void do_alignment_check(struct pt_regs * regs, long error_code)
5069 +asmlinkage void do_alignment_check(struct pt_regs * regs, long error_code)
5070  {
5071         send_sig(SIGSEGV, current, 1);
5072         die_if_kernel("alignment check",regs,error_code);
5073  }
5074  
5075 -extern "C" void do_divide_error(struct pt_regs * regs, long error_code)
5076 +asmlinkage void do_divide_error(struct pt_regs * regs, long error_code)
5077  {
5078         send_sig(SIGFPE, current, 1);
5079         die_if_kernel("divide error",regs,error_code);
5080  }
5081  
5082 -extern "C" void do_int3(struct pt_regs * regs, long error_code)
5083 +asmlinkage void do_int3(struct pt_regs * regs, long error_code)
5084  {
5085         if (current->flags & PF_PTRACED)
5086                 current->blocked &= ~(1 << (SIGTRAP-1));
5087 @@ -114,12 +115,12 @@
5088         die_if_kernel("int3",regs,error_code);
5089  }
5090  
5091 -extern "C" void do_nmi(struct pt_regs * regs, long error_code)
5092 +asmlinkage void do_nmi(struct pt_regs * regs, long error_code)
5093  {
5094         printk("Uhhuh. NMI received. Dazed and confused, but trying to continue\n");
5095  }
5096  
5097 -extern "C" void do_debug(struct pt_regs * regs, long error_code)
5098 +asmlinkage void do_debug(struct pt_regs * regs, long error_code)
5099  {
5100         if (current->flags & PF_PTRACED)
5101                 current->blocked &= ~(1 << (SIGTRAP-1));
5102 @@ -127,49 +128,49 @@
5103         die_if_kernel("debug",regs,error_code);
5104  }
5105  
5106 -extern "C" void do_overflow(struct pt_regs * regs, long error_code)
5107 +asmlinkage void do_overflow(struct pt_regs * regs, long error_code)
5108  {
5109         send_sig(SIGSEGV, current, 1);
5110         die_if_kernel("overflow",regs,error_code);
5111  }
5112  
5113 -extern "C" void do_bounds(struct pt_regs * regs, long error_code)
5114 +asmlinkage void do_bounds(struct pt_regs * regs, long error_code)
5115  {
5116         send_sig(SIGSEGV, current, 1);
5117         die_if_kernel("bounds",regs,error_code);
5118  }
5119  
5120 -extern "C" void do_invalid_op(struct pt_regs * regs, long error_code)
5121 +asmlinkage void do_invalid_op(struct pt_regs * regs, long error_code)
5122  {
5123         send_sig(SIGILL, current, 1);
5124         die_if_kernel("invalid operand",regs,error_code);
5125  }
5126  
5127 -extern "C" void do_device_not_available(struct pt_regs * regs, long error_code)
5128 +asmlinkage void do_device_not_available(struct pt_regs * regs, long error_code)
5129  {
5130         send_sig(SIGSEGV, current, 1);
5131         die_if_kernel("device not available",regs,error_code);
5132  }
5133  
5134 -extern "C" void do_coprocessor_segment_overrun(struct pt_regs * regs, long error_code)
5135 +asmlinkage void do_coprocessor_segment_overrun(struct pt_regs * regs, long error_code)
5136  {
5137         send_sig(SIGFPE, last_task_used_math, 1);
5138         die_if_kernel("coprocessor segment overrun",regs,error_code);
5139  }
5140  
5141 -extern "C" void do_invalid_TSS(struct pt_regs * regs,long error_code)
5142 +asmlinkage void do_invalid_TSS(struct pt_regs * regs,long error_code)
5143  {
5144         send_sig(SIGSEGV, current, 1);
5145         die_if_kernel("invalid TSS",regs,error_code);
5146  }
5147  
5148 -extern "C" void do_segment_not_present(struct pt_regs * regs,long error_code)
5149 +asmlinkage void do_segment_not_present(struct pt_regs * regs,long error_code)
5150  {
5151         send_sig(SIGSEGV, current, 1);
5152         die_if_kernel("segment not present",regs,error_code);
5153  }
5154  
5155 -extern "C" void do_stack_segment(struct pt_regs * regs,long error_code)
5156 +asmlinkage void do_stack_segment(struct pt_regs * regs,long error_code)
5157  {
5158         send_sig(SIGSEGV, current, 1);
5159         die_if_kernel("stack segment",regs,error_code);
5160 @@ -210,13 +211,13 @@
5161         env->twd = 0xffffffff;
5162  }
5163  
5164 -extern "C" void do_coprocessor_error(struct pt_regs * regs, long error_code)
5165 +asmlinkage void do_coprocessor_error(struct pt_regs * regs, long error_code)
5166  {
5167         ignore_irq13 = 1;
5168         math_error();
5169  }
5170  
5171 -extern "C" void do_reserved(struct pt_regs * regs, long error_code)
5172 +asmlinkage void do_reserved(struct pt_regs * regs, long error_code)
5173  {
5174         send_sig(SIGSEGV, current, 1);
5175         die_if_kernel("reserved (15,17-47) error",regs,error_code);
5176 diff -u --recursive --new-file pl12/linux/mm/memory.c linux/mm/memory.c
5177 --- pl12/linux/mm/memory.c      Sun Aug 15 11:09:18 1993
5178 +++ linux/mm/memory.c   Sat Sep  4 03:34:22 1993
5179 @@ -278,7 +278,7 @@
5180         }
5181         size = (size + ~PAGE_MASK) >> PAGE_SHIFT;
5182         dir = PAGE_DIR_OFFSET(current->tss.cr3,from);
5183 -       poff = (from >> PAGE_SHIFT) & PTRS_PER_PAGE-1;
5184 +       poff = (from >> PAGE_SHIFT) & (PTRS_PER_PAGE-1);
5185         if ((pcnt = PTRS_PER_PAGE - poff) > size)
5186                 pcnt = size;
5187  
5188 @@ -337,7 +337,7 @@
5189         }
5190         dir = PAGE_DIR_OFFSET(current->tss.cr3,from);
5191         size = (size + ~PAGE_MASK) >> PAGE_SHIFT;
5192 -       poff = (from >> PAGE_SHIFT) & PTRS_PER_PAGE-1;
5193 +       poff = (from >> PAGE_SHIFT) & (PTRS_PER_PAGE-1);
5194         if ((pcnt = PTRS_PER_PAGE - poff) > size)
5195                 pcnt = size;
5196  
5197 @@ -399,7 +399,7 @@
5198         }
5199         dir = PAGE_DIR_OFFSET(current->tss.cr3,from);
5200         size = (size + ~PAGE_MASK) >> PAGE_SHIFT;
5201 -       poff = (from >> PAGE_SHIFT) & PTRS_PER_PAGE-1;
5202 +       poff = (from >> PAGE_SHIFT) & (PTRS_PER_PAGE-1);
5203         if ((pcnt = PTRS_PER_PAGE - poff) > size)
5204                 pcnt = size;
5205  
5206 @@ -484,7 +484,7 @@
5207                 *page_table = BAD_PAGETABLE | PAGE_TABLE;
5208                 return 0;
5209         }
5210 -       page_table += (address >> PAGE_SHIFT) & PTRS_PER_PAGE-1;
5211 +       page_table += (address >> PAGE_SHIFT) & (PTRS_PER_PAGE-1);
5212         if (*page_table) {
5213                 printk("put_page: page already exists\n");
5214                 *page_table = 0;
5215 @@ -523,7 +523,7 @@
5216                         page_table = (unsigned long *) tmp;
5217                 }
5218         }
5219 -       page_table += (address >> PAGE_SHIFT) & PTRS_PER_PAGE-1;
5220 +       page_table += (address >> PAGE_SHIFT) & (PTRS_PER_PAGE-1);
5221         if (*page_table) {
5222                 printk("put_dirty_page: page already exists\n");
5223                 *page_table = 0;
5224 @@ -760,7 +760,7 @@
5225  {
5226         struct task_struct ** p;
5227  
5228 -       if (!inode || inode->i_count < 2)
5229 +       if (!inode || inode->i_count < 2 || !area->vm_ops)
5230                 return 0;
5231         for (p = &LAST_TASK ; p > &FIRST_TASK ; --p) {
5232                 if (!*p)
5233 @@ -773,8 +773,8 @@
5234                            we can share pages with */
5235                         if(area){
5236                           struct vm_area_struct * mpnt;
5237 -                         for(mpnt = (*p)->mmap; mpnt; mpnt = mpnt->vm_next){
5238 -                           if(mpnt->vm_ops && mpnt->vm_ops == area->vm_ops &&
5239 +                         for (mpnt = (*p)->mmap; mpnt; mpnt = mpnt->vm_next) {
5240 +                           if (mpnt->vm_ops == area->vm_ops &&
5241                                mpnt->vm_inode->i_ino == area->vm_inode->i_ino&&
5242                                mpnt->vm_inode->i_dev == area->vm_inode->i_dev){
5243                               if (mpnt->vm_ops->share(mpnt, area, address))
5244 @@ -851,6 +851,8 @@
5245                         continue;
5246                 if (address >= ((mpnt->vm_end + PAGE_SIZE - 1) & ~(PAGE_SIZE - 1)))
5247                         continue;
5248 +               if (!mpnt->vm_ops || !mpnt->vm_ops->nopage)
5249 +                       break;
5250                 mpnt->vm_ops->nopage(error_code, mpnt, address);
5251                 return;
5252         }
5253 @@ -858,7 +860,7 @@
5254         get_empty_page(tsk,address);
5255         if (tsk != current)
5256                 return;
5257 -       if (address < tsk->brk)
5258 +       if (address >= tsk->end_data && address < tsk->brk)
5259                 return;
5260         if (address+8192 >= (user_esp & 0xfffff000) && 
5261             address <= current->start_stack)
5262 @@ -872,7 +874,7 @@
5263   * and the problem, and then passes it off to one of the appropriate
5264   * routines.
5265   */
5266 -extern "C" void do_page_fault(struct pt_regs *regs, unsigned long error_code)
5267 +asmlinkage void do_page_fault(struct pt_regs *regs, unsigned long error_code)
5268  {
5269         unsigned long address;
5270         unsigned long user_esp = 0;
5271 @@ -966,9 +968,9 @@
5272         int shared = 0;
5273  
5274         printk("Mem-info:\n");
5275 -       printk("Free pages:      %6dkB\n",nr_free_pages<<PAGE_SHIFT-10);
5276 -       printk("Secondary pages: %6dkB\n",nr_secondary_pages<<PAGE_SHIFT-10);
5277 -       printk("Free swap:       %6dkB\n",nr_swap_pages<<PAGE_SHIFT-10);
5278 +       printk("Free pages:      %6dkB\n",nr_free_pages<<(PAGE_SHIFT-10));
5279 +       printk("Secondary pages: %6dkB\n",nr_secondary_pages<<(PAGE_SHIFT-10));
5280 +       printk("Free swap:       %6dkB\n",nr_swap_pages<<(PAGE_SHIFT-10));
5281         printk("Buffer memory:   %6dkB\n",buffermem>>10);
5282         printk("Buffer heads:    %6d\n",nr_buffer_heads);
5283         printk("Buffer blocks:   %6d\n",nr_buffers);
5284 @@ -1085,9 +1087,9 @@
5285         printk("Memory: %dk/%dk available (%dk kernel code, %dk reserved, %dk data)\n",
5286                 tmp >> 10,
5287                 end_mem >> 10,
5288 -               codepages << PAGE_SHIFT-10,
5289 -               reservedpages << PAGE_SHIFT-10,
5290 -               datapages << PAGE_SHIFT-10);
5291 +               codepages << (PAGE_SHIFT-10),
5292 +               reservedpages << (PAGE_SHIFT-10),
5293 +               datapages << (PAGE_SHIFT-10));
5294         return;
5295  }
5296  
5297 diff -u --recursive --new-file pl12/linux/mm/mmap.c linux/mm/mmap.c
5298 --- pl12/linux/mm/mmap.c        Mon Aug  9 18:02:33 1993
5299 +++ linux/mm/mmap.c     Sat Sep  4 02:45:22 1993
5300 @@ -52,11 +52,11 @@
5301         switch (flags & MAP_TYPE) {
5302         case MAP_SHARED:
5303                 if ((prot & PROT_WRITE) && !(file->f_mode & 2))
5304 -                       return -EINVAL;
5305 +                       return -EACCES;
5306                 /* fall through */
5307         case MAP_PRIVATE:
5308                 if (!(file->f_mode & 1))
5309 -                       return -EINVAL;
5310 +                       return -EACCES;
5311                 break;
5312  
5313         default:
5314 @@ -121,7 +121,7 @@
5315         return -1;
5316  }
5317  
5318 -extern "C" int sys_mmap(unsigned long *buffer)
5319 +asmlinkage int sys_mmap(unsigned long *buffer)
5320  {
5321         unsigned long fd;
5322         struct file * file;
5323 @@ -133,7 +133,7 @@
5324                 get_fs_long(buffer+2), get_fs_long(buffer+3), get_fs_long(buffer+5));
5325  }
5326  
5327 -extern "C" int sys_munmap(unsigned long addr, size_t len)
5328 +asmlinkage int sys_munmap(unsigned long addr, size_t len)
5329  {
5330         struct vm_area_struct *mpnt, **p, *free;
5331  
5332 @@ -169,7 +169,7 @@
5333         while (free) {
5334                 mpnt = free;
5335                 free = free->vm_next;
5336 -               if (mpnt->vm_ops->close)
5337 +               if (mpnt->vm_ops && mpnt->vm_ops->close)
5338                         mpnt->vm_ops->close(mpnt);
5339                 kfree(mpnt);
5340         }
5341 @@ -197,11 +197,9 @@
5342         extern struct vm_operations_struct file_mmap;
5343         struct buffer_head * bh;
5344  
5345 -       if (off & (inode->i_sb->s_blocksize - 1))
5346 +       if (prot & PAGE_RW)     /* only PAGE_COW or read-only supported right now */
5347                 return -EINVAL;
5348 -       if (len > high_memory || off > high_memory - len) /* avoid overflow */
5349 -               return -ENXIO;
5350 -       if (get_limit(USER_DS)  != TASK_SIZE)
5351 +       if (off & (inode->i_sb->s_blocksize - 1))
5352                 return -EINVAL;
5353         if (!inode->i_sb || !S_ISREG(inode->i_mode))
5354                 return -EACCES;
5355 @@ -231,10 +229,6 @@
5356         mpnt->vm_ops = &file_mmap;
5357         mpnt->vm_next = current->mmap;
5358         current->mmap = mpnt;
5359 -#if 0
5360 -       printk("VFS: Loaded mmap at %08x -  %08x\n",
5361 -               mpnt->vm_start, mpnt->vm_end);
5362 -#endif
5363         return 0;
5364  }
5365  
5366 diff -u --recursive --new-file pl12/linux/mm/swap.c linux/mm/swap.c
5367 --- pl12/linux/mm/swap.c        Sat Aug 14 15:59:34 1993
5368 +++ linux/mm/swap.c     Sat Sep  4 02:45:34 1993
5369 @@ -265,7 +265,7 @@
5370   * swapping out or forgetting about. This speeds up the search when we
5371   * actually have to swap.
5372   */
5373 -extern "C" int sys_idle(void)
5374 +asmlinkage int sys_idle(void)
5375  {
5376         need_resched = 1;
5377         return 0;
5378 @@ -661,7 +661,7 @@
5379         return 0;
5380  }
5381  
5382 -extern "C" int sys_swapoff(const char * specialfile)
5383 +asmlinkage int sys_swapoff(const char * specialfile)
5384  {
5385         struct swap_info_struct * p;
5386         struct inode * inode;
5387 @@ -713,7 +713,7 @@
5388   *
5389   * The swapon system call
5390   */
5391 -extern "C" int sys_swapon(const char * specialfile)
5392 +asmlinkage int sys_swapon(const char * specialfile)
5393  {
5394         struct swap_info_struct * p;
5395         struct inode * swap_inode;
5396 diff -u --recursive --new-file pl12/linux/net/inet/3c509.c linux/net/inet/3c509.c
5397 --- pl12/linux/net/inet/3c509.c Fri Aug 13 06:35:44 1993
5398 +++ linux/net/inet/3c509.c      Fri Sep  3 22:08:32 1993
5399 @@ -1,4 +1,4 @@
5400 -/* el3.c: An 3c509 EtherLink3 ethernet driver for linux. */
5401 +/* 3c509.c: A 3c509 EtherLink3 ethernet driver for linux. */
5402  /*
5403      Written 1993 by Donald Becker.
5404  
5405 @@ -7,13 +7,13 @@
5406      distributed according to the terms of the GNU Public License,
5407      incorporated herein by reference.
5408      
5409 -    This driver should work with the 3Com EtherLinkIII series.
5410 +    This driver is for the 3Com EtherLinkIII series.
5411  
5412      The author may be reached as becker@super.org or
5413      C/O Supercomputing Research Ctr., 17100 Science Dr., Bowie MD 20715
5414  */
5415  
5416 -static char *version = "el3.c: v0.02 8/13/93 becker@super.org\n";
5417 +static char *version = "3c509.c: v0.06 9/3/93 becker@super.org\n";
5418  
5419  #include <linux/config.h>
5420  #include <linux/kernel.h>
5421 @@ -23,6 +23,14 @@
5422  #include <linux/ptrace.h>
5423  #include <linux/errno.h>
5424  #include <linux/in.h>
5425 +
5426 +#ifndef PRE_PL13
5427 +#include <linux/ioport.h>
5428 +#else
5429 +#define snarf_region(base,extent) do {;}while(0)
5430 +#define check_region(base,extent) (0)
5431 +#endif
5432 +
5433  /*#include <asm/system.h>*/
5434  #include <asm/io.h>
5435  #ifndef port_read
5436 @@ -34,10 +42,12 @@
5437  #include "skbuff.h"
5438  #include "arp.h"
5439  
5440 +#ifndef HAVE_AUTOIRQ
5441  /* From auto_irq.c, should be in a *.h file. */
5442  extern void autoirq_setup(int waittime);
5443  extern int autoirq_report(int waittime);
5444  extern struct device *irq2dev_map[16];
5445 +#endif
5446  
5447  /* These should be in <asm/io.h>. */
5448  #define port_read_l(port,buf,nr) \
5449 @@ -49,9 +59,12 @@
5450  #ifdef EL3_DEBUG
5451  int el3_debug = EL3_DEBUG;
5452  #else
5453 -int el3_debug = 1;
5454 +int el3_debug = 2;
5455  #endif
5456  
5457 +/* To minimize the size of the driver source I only define operating
5458 +   constants if they are used several times.  You'll need the manual
5459 +   if you want to understand driver details. */
5460  /* Offsets from base I/O address. */
5461  #define EL3_DATA 0x00
5462  #define EL3_CMD 0x0e
5463 @@ -59,6 +72,9 @@
5464  #define ID_PORT 0x100
5465  #define  EEPROM_READ 0x80
5466  
5467 +#define EL3WINDOW(win_num) outw(0x0800+(win_num), ioaddr + EL3_CMD)
5468 +
5469 +
5470  /* Register window 1 offsets, used in normal operation. */
5471  #define TX_FREE 0x0C
5472  #define TX_STATUS 0x0B
5473 @@ -66,11 +82,12 @@
5474  #define RX_STATUS 0x08
5475  #define RX_FIFO 0x00
5476  
5477 +#define WN4_MEDIA      0x0A
5478 +
5479  struct el3_private {
5480      struct enet_statistics stats;
5481  };
5482  
5483 -static int el3_init(struct device *dev);
5484  static int read_eeprom(int index);
5485  static int el3_open(struct device *dev);
5486  static int el3_start_xmit(struct sk_buff *skb, struct device *dev);
5487 @@ -85,7 +102,9 @@
5488  int el3_probe(struct device *dev)
5489  {
5490      short lrs_state = 0xff, i;
5491 -    unsigned short iobase = 0;
5492 +    short ioaddr, irq;
5493 +    short *phys_addr = (short *)dev->dev_addr;
5494 +    static int current_tag = 0;
5495  
5496      /* Send the ID sequence to the ID_PORT. */
5497      outb(0x00, ID_PORT);
5498 @@ -96,75 +115,57 @@
5499         lrs_state = lrs_state & 0x100 ? lrs_state ^ 0xcf : lrs_state;
5500      }
5501  
5502 -    /* The current Space.c initialization makes it difficult to have more
5503 -       than one adaptor initialized.  Send me email if you have a need for
5504 -       multiple adaptors. */
5505 -
5506 -    /* Read in EEPROM data.
5507 -       Only the highest address board will stay on-line. */
5508 +    /* For the first probe, clear all board's tag registers. */
5509 +    if (current_tag == 0)
5510 +       outb(0xd0, ID_PORT);
5511 +    else               /* Otherwise kill off already-found boards. */
5512 +       outb(0xd8, ID_PORT);
5513  
5514 -    {
5515 -       short *phys_addr = (short *)dev->dev_addr;
5516 -       phys_addr[0] = htons(read_eeprom(0));
5517 -       if (phys_addr[0] != 0x6000)
5518 -           return 1;
5519 -       phys_addr[1] = htons(read_eeprom(1));
5520 -       phys_addr[2] = htons(read_eeprom(2));
5521 +    if (read_eeprom(7) != 0x6d50) {
5522 +       return -ENODEV;
5523      }
5524  
5525 -    iobase = read_eeprom(8);
5526 -    dev->irq = read_eeprom(9) >> 12;
5527 -
5528 -    /* Activate the adaptor at the EEPROM location (if set), else 0x320. */
5529 -
5530 -    if (iobase == 0x0000) {
5531 -       dev->base_addr = 0x320;
5532 -       outb(0xf2, ID_PORT);
5533 -    } else {
5534 -       dev->base_addr = 0x200 + ((iobase & 0x1f) << 4);
5535 -       outb(0xff, ID_PORT);
5536 +    /* Read in EEPROM data, which does contention-select.
5537 +       Only the lowest address board will stay "on-line".
5538 +       3Com got the byte order backwards. */
5539 +    for (i = 0; i < 3; i++) {
5540 +       phys_addr[i] = htons(read_eeprom(i));
5541      }
5542  
5543 -    outw(0x0800, dev->base_addr + EL3_CMD);     /* Window 0. */
5544 -    printk("%s: 3c509 at %#3.3x  key %4.4x iobase %4.4x.\n",
5545 -          dev->name, dev->base_addr, inw(dev->base_addr), iobase);
5546 +    {
5547 +       unsigned short iobase = read_eeprom(8);
5548 +       dev->if_port = iobase >> 14;
5549 +       ioaddr = 0x200 + ((iobase & 0x1f) << 4);
5550 +    }
5551 +    irq = read_eeprom(9) >> 12;
5552  
5553 -    if (inw(dev->base_addr) == 0x6d50) {
5554 -       el3_init(dev);
5555 -       return 0;
5556 -    } else
5557 +    /* The current Space.c structure makes it difficult to have more
5558 +       than one adaptor initialized.  Send me email if you have a need for
5559 +       multiple adaptors, and we'll work out something.  -becker@super.org */
5560 +    if (dev->base_addr != 0
5561 +       &&  dev->base_addr != (unsigned short)ioaddr) {
5562         return -ENODEV;
5563 -}
5564 -
5565 -static int
5566 -read_eeprom(int index)
5567 -{
5568 -    int timer, bit, word = 0;
5569 -    
5570 -    /* Issue read command, and pause for at least 162 us. for it to complete.
5571 -       Assume extra-fast 16Mhz bus. */
5572 -    outb(EEPROM_READ + index, ID_PORT);
5573 +    }
5574  
5575 -    for (timer = 0; timer < 162*4 + 400; timer++)
5576 -       SLOW_DOWN_IO;
5577 +    /* Set the adaptor tag so that the next card can be found. */
5578 +    outb(0xd0 + ++current_tag, ID_PORT);
5579  
5580 -    for (bit = 15; bit >= 0; bit--)
5581 -       word = (word << 1) + (inb(ID_PORT) & 0x01);
5582 -       
5583 -    if (el3_debug > 3)
5584 -       printk("  3c509 EEPROM word %d %#4.4x.\n", index, word);
5585 +    /* Activate the adaptor at the EEPROM location. */
5586 +    outb(0xff, ID_PORT);
5587  
5588 -    return word;
5589 -}
5590 +    EL3WINDOW(0);
5591 +    if (inw(ioaddr) != 0x6d50)
5592 +       return -ENODEV;
5593  
5594 -static int
5595 -el3_init(struct device *dev)
5596 -{
5597 -    struct el3_private *lp;
5598 -    int ioaddr = dev->base_addr;
5599 -    int i;
5600 +    dev->base_addr = ioaddr;
5601 +    dev->irq = irq;
5602 +    snarf_region(dev->base_addr, 16);
5603  
5604 -    printk("%s: EL3 at %#3x, address", dev->name, ioaddr);
5605 +    {
5606 +       char *if_names[] = {"10baseT", "AUI", "undefined", "BNC"};
5607 +       printk("%s: 3c509 at %#3.3x  tag %d, %s port, address ",
5608 +              dev->name, dev->base_addr, current_tag, if_names[dev->if_port]);
5609 +    }
5610  
5611      /* Read in the station address. */
5612      for (i = 0; i < 6; i++)
5613 @@ -174,9 +175,8 @@
5614      /* Make up a EL3-specific-data structure. */
5615      dev->priv = kmalloc(sizeof(struct el3_private), GFP_KERNEL);
5616      memset(dev->priv, 0, sizeof(struct el3_private));
5617 -    lp = (struct el3_private *)dev->priv;
5618  
5619 -    if (el3_debug > 1)
5620 +    if (el3_debug > 0)
5621         printk(version);
5622  
5623      /* The EL3-specific entries in the device structure. */
5624 @@ -199,7 +199,7 @@
5625      dev->hard_header_len = ETH_HLEN;
5626      dev->mtu           = 1500; /* eth_mtu */
5627      dev->addr_len      = ETH_ALEN;
5628 -    for (i = 0; i < dev->addr_len; i++) {
5629 +    for (i = 0; i < ETH_ALEN; i++) {
5630         dev->broadcast[i]=0xff;
5631      }
5632  
5633 @@ -214,6 +214,30 @@
5634      return 0;
5635  }
5636  
5637 +
5638 +static int
5639 +read_eeprom(int index)
5640 +{
5641 +    int timer, bit, word = 0;
5642 +    
5643 +    /* Issue read command, and pause for at least 162 us. for it to complete.
5644 +       Assume extra-fast 16Mhz bus. */
5645 +    outb(EEPROM_READ + index, ID_PORT);
5646 +
5647 +    /* This should really be done by looking at one of the timer channels. */
5648 +    for (timer = 0; timer < 162*4 + 400; timer++)
5649 +       SLOW_DOWN_IO;
5650 +
5651 +    for (bit = 15; bit >= 0; bit--)
5652 +       word = (word << 1) + (inb(ID_PORT) & 0x01);
5653 +       
5654 +    if (el3_debug > 3)
5655 +       printk("  3c509 EEPROM word %d %#4.4x.\n", index, word);
5656 +
5657 +    return word;
5658 +}
5659 +
5660 +
5661  \f
5662  static int
5663  el3_open(struct device *dev)
5664 @@ -225,26 +249,36 @@
5665         return -EAGAIN;
5666      }
5667  
5668 +    EL3WINDOW(0);
5669      if (el3_debug > 3)
5670 -       printk("%s: Opening, IRQ %d  status@%x %4.4x reg4 %4.4x.\n",
5671 -              dev->name, dev->irq, ioaddr + EL3_STATUS,
5672 -              inw(ioaddr + EL3_STATUS), inw(ioaddr + 4));
5673 -    outw(0x0800, ioaddr + EL3_CMD); /* Make certain we are in window 0. */
5674 +       printk("%s: Opening, IRQ %d  status@%x %4.4x.\n", dev->name,
5675 +              dev->irq, ioaddr + EL3_STATUS, inw(ioaddr + EL3_STATUS));
5676  
5677 -    /* This is probably unnecessary. */
5678 +    /* Activate board: this is probably unnecessary. */
5679      outw(0x0001, ioaddr + 4);
5680  
5681 -    outw((dev->irq << 12) | 0x0f00, ioaddr + 8);
5682 -
5683      irq2dev_map[dev->irq] = dev;
5684  
5685 +    /* Set the IRQ line. */
5686 +    outw((dev->irq << 12) | 0x0f00, ioaddr + 8);
5687 +
5688      /* Set the station address in window 2 each time opened. */
5689 -    outw(0x0802, ioaddr + EL3_CMD);
5690 +    EL3WINDOW(2);
5691  
5692      for (i = 0; i < 6; i++)
5693         outb(dev->dev_addr[i], ioaddr + i);
5694  
5695 -    outw(0x1000, ioaddr + EL3_CMD); /* Start the thinnet transceiver. */
5696 +    if (dev->if_port == 3)
5697 +       /* Start the thinnet transceiver. We should really wait 50ms...*/
5698 +       outw(0x1000, ioaddr + EL3_CMD);
5699 +    else if (dev->if_port == 0) {
5700 +       /* 10baseT interface, enabled link beat and jabber check. */
5701 +       EL3WINDOW(4);
5702 +       outw(inw(ioaddr + WN4_MEDIA) | 0x00C0, ioaddr + WN4_MEDIA);
5703 +    }
5704 +
5705 +    /* Switch to register set 1 for normal use. */
5706 +    EL3WINDOW(1);
5707  
5708      outw(0x8005, ioaddr + EL3_CMD); /* Accept b-case and phys addr only. */
5709      outw(0xA800, ioaddr + EL3_CMD); /* Turn on statistics. */
5710 @@ -251,19 +285,15 @@
5711      outw(0x2000, ioaddr + EL3_CMD); /* Enable the receiver. */
5712      outw(0x4800, ioaddr + EL3_CMD); /* Enable transmitter. */
5713      outw(0x78ff, ioaddr + EL3_CMD); /* Allow all status bits to be seen. */
5714 +    dev->interrupt = 0;
5715 +    dev->tbusy = 0;
5716 +    dev->start = 1;
5717      outw(0x7098, ioaddr + EL3_CMD); /* Set interrupt mask. */
5718  
5719 -    /* Switch to register set 1 for normal use. */
5720 -    outw(0x0801, ioaddr + EL3_CMD);
5721 -
5722      if (el3_debug > 3)
5723         printk("%s: Opened 3c509  IRQ %d  status %4.4x.\n",
5724                dev->name, dev->irq, inw(ioaddr + EL3_STATUS));
5725  
5726 -    dev->tbusy = 0;
5727 -    dev->interrupt = 0;
5728 -    dev->start = 1;
5729 -
5730      return 0;                  /* Always succeed */
5731  }
5732  
5733 @@ -278,7 +308,7 @@
5734         int tickssofar = jiffies - dev->trans_start;
5735         if (tickssofar < 10)
5736             return 1;
5737 -       printk("%s: transmit timed out, tx_status %4.4x status %4.4x.\n",
5738 +       printk("%s: transmit timed out, tx_status %2.2x status %4.4x.\n",
5739                dev->name, inb(ioaddr + TX_STATUS), inw(ioaddr + EL3_STATUS));
5740         dev->trans_start = jiffies;
5741         /* Issue TX_RESET and TX_START commands. */
5742 @@ -308,8 +338,9 @@
5743      }
5744  
5745      if (inw(ioaddr + EL3_STATUS) & 0x0001) { /* IRQ line active, missed one. */
5746 -      printk("%s: Missed interrupt, status %4.4x.\n", dev->name,
5747 -            inw(ioaddr + EL3_STATUS));
5748 +      printk("%s: Missed interrupt, status %4.4x  Tx %2.2x Rx %4.4x.\n",
5749 +            dev->name, inw(ioaddr + EL3_STATUS), inb(ioaddr + TX_STATUS),
5750 +            inw(ioaddr + RX_STATUS));
5751        outw(0x7800, ioaddr + EL3_CMD); /* Fake interrupt trigger. */
5752        outw(0x6899, ioaddr + EL3_CMD); /* Ack IRQ */
5753        outw(0x78ff, ioaddr + EL3_CMD); /* Allow all status bits to be seen. */
5754 @@ -322,8 +353,7 @@
5755      outw(skb->len, ioaddr + TX_FIFO);
5756      outw(0x00, ioaddr + TX_FIFO);
5757      /* ... and the packet rounded to a doubleword. */
5758 -    port_write(ioaddr + TX_FIFO, (void *)(skb+1),
5759 -              ((skb->len + 3) >> 1) & ~0x1);
5760 +    port_write_l(ioaddr + TX_FIFO, (void *)(skb+1), (skb->len + 3) >> 2);
5761      
5762      dev->trans_start = jiffies;
5763      if (skb->free)
5764 @@ -360,8 +390,9 @@
5765  el3_interrupt(int reg_ptr)
5766  {
5767      int irq = -(((struct pt_regs *)reg_ptr)->orig_eax+2);
5768 -    struct device *dev = irq2dev_map[irq];
5769 +    struct device *dev = (struct device *)(irq2dev_map[irq]);
5770      int ioaddr, status;
5771 +    int i = 0;
5772  
5773      if (dev == NULL) {
5774         printk ("el3_interrupt(): irq %d for unknown device.\n", irq);
5775 @@ -380,6 +411,9 @@
5776      
5777      while ((status = inw(ioaddr + EL3_STATUS)) & 0x01) {
5778  
5779 +       if (status & 0x10)
5780 +           el3_rx(dev);
5781 +
5782         if (status & 0x08) {
5783             if (el3_debug > 5)
5784                 printk("    TX room bit was handled.\n");
5785 @@ -391,10 +425,12 @@
5786         if (status & 0x80)              /* Statistics full. */
5787             update_stats(ioaddr, dev);
5788         
5789 -       if (status & 0x10)
5790 -           el3_rx(dev);
5791 -
5792 -       /* Clear the interrupts we've handled. */
5793 +       if (++i > 10) {
5794 +           printk("%s: Infinite loop in interrupt, status %4.4x.\n",
5795 +                  dev->name, status);
5796 +           break;
5797 +       }
5798 +       /* Clear the other interrupts we have handled. */
5799         outw(0x6899, ioaddr + EL3_CMD); /* Ack IRQ */
5800      }
5801  
5802 @@ -403,16 +439,6 @@
5803                inw(ioaddr + EL3_STATUS));
5804      }
5805      
5806 -    if (inw(ioaddr + EL3_STATUS) & 0x01) {
5807 -       int i = 100000;
5808 -       printk("%s: exiting interrupt with status %4.4x.\n", dev->name,
5809 -              inw(ioaddr + EL3_STATUS));
5810 -       while (i--)             /* Delay loop to see the message. */
5811 -           inw(ioaddr + EL3_STATUS);
5812 -       while ((inw(ioaddr + EL3_STATUS) & 0x0010)  && i++ < 20)
5813 -           outw(0x00, ioaddr + RX_STATUS);
5814 -    }
5815 -
5816      dev->interrupt = 0;
5817      return;
5818  }
5819 @@ -430,7 +456,9 @@
5820  }
5821  
5822  /* Update statistics.  We change to register window 6, so this
5823 -   must be run single-threaded. */
5824 +   should be run single-threaded if the device is active. This
5825 +   is expected to be a rare operation, and not worth a special
5826 +   window-state variable. */
5827  static void update_stats(int ioaddr, struct device *dev)
5828  {
5829      struct el3_private *lp = (struct el3_private *)dev->priv;
5830 @@ -440,7 +468,7 @@
5831      /* Turn off statistics updates while reading. */
5832      outw(0xB000, ioaddr + EL3_CMD);
5833      /* Switch to the stats window, and read everything. */
5834 -    outw(0x0806, ioaddr + EL3_CMD);
5835 +    EL3WINDOW(6);
5836      lp->stats.tx_carrier_errors        += inb(ioaddr + 0);
5837      lp->stats.tx_heartbeat_errors      += inb(ioaddr + 1);
5838      /* Multiple collisions. */    inb(ioaddr + 2);
5839 @@ -454,25 +482,11 @@
5840      inw(ioaddr + 12);
5841  
5842      /* Back to window 1, and turn statistics back on. */
5843 -    outw(0x0801, ioaddr + EL3_CMD);
5844 +    EL3WINDOW(1);
5845      outw(0xA800, ioaddr + EL3_CMD);
5846      return;
5847  }
5848  
5849 -/* Print statistics on the kernel error output. */
5850 -void printk_stats(struct enet_statistics *stats)
5851 -{
5852 -
5853 -    printk("  Ethernet statistics:  Rx packets %6d  Tx packets %6d.\n",
5854 -          stats->rx_packets, stats->tx_packets);
5855 -    printk("   Carrier errors:   %6d.\n", stats->tx_carrier_errors);
5856 -    printk("   Heartbeat errors: %6d.\n", stats->tx_heartbeat_errors);
5857 -    printk("   Collisions:       %6d.\n", stats->collisions);
5858 -    printk("   Rx FIFO problems: %6d.\n", stats->rx_fifo_errors);
5859 -
5860 -    return;
5861 -}
5862 -
5863  static int
5864  el3_rx(struct device *dev)
5865  {
5866 @@ -498,21 +512,32 @@
5867         }
5868         if ( (! (rx_status & 0x4000))
5869             || ! (rx_status & 0x2000)) { /* Dribble bits are OK. */
5870 -           short length = rx_status & 0x3ff;
5871 -           int sksize = sizeof(struct sk_buff) + length + 3;
5872 +           short pkt_len = rx_status & 0x3ff;
5873 +           int sksize = sizeof(struct sk_buff) + pkt_len + 3;
5874             struct sk_buff *skb;
5875             skb = (struct sk_buff *) kmalloc(sksize, GFP_ATOMIC);
5876  
5877             if (el3_debug > 4)
5878                 printk("       Receiving packet size %d status %4.4x.\n",
5879 -                      length, rx_status);
5880 +                      pkt_len, rx_status);
5881             if (skb != NULL) {
5882 -               skb->lock = 0;
5883                 skb->mem_len = sksize;
5884                 skb->mem_addr = skb;
5885 +               skb->len = pkt_len;
5886 +               skb->dev = dev;
5887 +
5888                 /* 'skb+1' points to the start of sk_buff data area. */
5889 -               port_read(ioaddr+RX_FIFO, (void *)(skb+1), ((length + 3) >> 2) << 1);
5890 -               if (dev_rint((unsigned char *)skb, length, IN_SKBUFF,dev)== 0){
5891 +               port_read_l(ioaddr+RX_FIFO, (void *)(skb+1),
5892 +                           (pkt_len + 3) >> 2);
5893 +
5894 +#ifdef HAVE_NETIF_RX
5895 +               netif_rx(skb);
5896 +               outw(0x4000, ioaddr + EL3_CMD); /* Rx discard */
5897 +               continue;
5898 +#else
5899 +               skb->lock = 0;
5900 +               if (dev_rint((unsigned char *)skb, pkt_len,
5901 +                            IN_SKBUFF,dev)== 0){
5902                     if (el3_debug > 6)
5903                         printk("     dev_rint() happy, status %4.4x.\n",
5904                         inb(ioaddr + EL3_STATUS));
5905 @@ -527,7 +552,8 @@
5906                 } else {
5907                     printk("%s: receive buffers full.\n", dev->name);
5908                     kfree_s(skb, sksize);
5909 -               }           
5910 +               }
5911 +#endif
5912             } else if (el3_debug)
5913                 printk("%s: Couldn't allocate a sk_buff of size %d.\n",
5914                        dev->name, sksize);
5915 @@ -564,22 +590,21 @@
5916      outw(0x1800, ioaddr + EL3_CMD);
5917      outw(0x5000, ioaddr + EL3_CMD);
5918  
5919 -    /* Turn off thinnet power. */
5920 -    outw(0xb800, ioaddr + EL3_CMD);
5921 -
5922 -    if (el3_debug > 2) {
5923 -       struct el3_private *lp = (struct el3_private *)dev->priv;
5924 -       printk("%s: Status was %4.4x.\n", dev->name, inw(ioaddr + EL3_STATUS));
5925 -       printk_stats(&lp->stats);
5926 +    if (dev->if_port == 3)
5927 +       /* Turn off thinnet power. */
5928 +       outw(0xb800, ioaddr + EL3_CMD);
5929 +    else if (dev->if_port == 0) {
5930 +       /* Disable link beat and jabber, if_port may change ere next open(). */
5931 +       EL3WINDOW(4);
5932 +       outw(inw(ioaddr + WN4_MEDIA) & ~ 0x00C0, ioaddr + WN4_MEDIA);
5933      }
5934  
5935 -    /* Free the interrupt line. */
5936      free_irq(dev->irq);
5937 -    outw(0x1000, ioaddr + EL3_CMD);
5938 +    /* Switching back to window 0 disables the IRQ. */
5939 +    EL3WINDOW(0);
5940 +    /* But we explicitly zero the IRQ line select anyway. */
5941      outw(0x0f00, ioaddr + 8);
5942  
5943 -    /* Switch back to register window 0. */
5944 -    outw(0x0800, ioaddr + EL3_CMD);
5945  
5946      irq2dev_map[dev->irq] = 0;
5947  
5948 diff -u --recursive --new-file pl12/linux/net/inet/8390.c linux/net/inet/8390.c
5949 --- pl12/linux/net/inet/8390.c  Fri Aug 13 04:24:31 1993
5950 +++ linux/net/inet/8390.c       Fri Sep  3 23:27:54 1993
5951 @@ -14,15 +14,8 @@
5952  */
5953  
5954  static char *version =
5955 -    "8390.c:v0.99-12 8/9/93 for 0.99.12+ Donald Becker (becker@super.org)\n";
5956 +    "8390.c:v0.99-13 9/3/93 for 0.99.13 Donald Becker (becker@super.org)\n";
5957  #include <linux/config.h>
5958 -#if !defined(EL2) && !defined(NE2000) && !defined(WD80x3) && !defined(HPLAN)
5959 -/* They don't know what they want -- give it all to them! */
5960 -#define EL2
5961 -#define NE2000
5962 -#define WD80x3
5963 -#define HPLAN
5964 -#endif
5965  
5966  /*
5967    Braindamage remaining:
5968 @@ -94,12 +87,6 @@
5969  static void NS8390_trigger_send(struct device *dev, unsigned int length,
5970                                 int start_page);
5971  
5972 -extern int el2autoprobe(int ioaddr, struct device *dev);
5973 -extern int el2probe(int ioaddr, struct device *dev);
5974 -extern int neprobe(int ioaddr, struct device *dev);
5975 -extern int wdprobe(int ioaddr, struct device *dev);
5976 -extern int hpprobe(int ioaddr, struct device *dev);
5977 -
5978  struct sigaction ei_sigaction = { ei_interrupt, 0, 0, NULL, };
5979  \f
5980  /* Open/initialize the board.  This routine goes all-out, setting everything
5981 @@ -260,7 +247,7 @@
5982  ei_interrupt(int reg_ptr)
5983  {
5984      int irq = -(((struct pt_regs *)reg_ptr)->orig_eax+2);
5985 -    struct device *dev = irq2dev_map[irq];
5986 +    struct device *dev = (struct device *)(irq2dev_map[irq]);
5987      int e8390_base;
5988      int interrupts, boguscount = 0;
5989      struct ei_device *ei_local;
5990 @@ -580,35 +567,14 @@
5991      return &ei_local->stat;
5992  }
5993  
5994 -int
5995 -ethif_init(struct device *dev)
5996 -{
5997 -    if (1
5998 -#ifdef WD80x3
5999 -       && ! wdprobe(dev->base_addr, dev)
6000 -#endif
6001 -#ifdef EL2
6002 -       && ! el2autoprobe(dev->base_addr, dev)
6003 -#endif
6004 -#ifdef NE2000
6005 -       && ! neprobe(dev->base_addr, dev)
6006 -#endif
6007 -#ifdef HPLAN
6008 -       && ! hpprobe(dev->base_addr, dev)
6009 -#endif
6010 -       && 1 ) {
6011 -       return 1;       /* -ENODEV or -EAGAIN would be more accurate. */
6012 -    }
6013 -    if (ei_debug > 1)
6014 -       printk(version);
6015 -    return 0;
6016 -}
6017 -
6018 -/* Initialize the rest of the device structure. */
6019 +/* Initialize the rest of the 8390 device structure. */
6020  int
6021  ethdev_init(struct device *dev)
6022  {
6023      int i;
6024 +
6025 +    if (ei_debug > 1)
6026 +       printk(version);
6027  
6028      for (i = 0; i < DEV_NUMBUFFS; i++)
6029         dev->buffs[i] = NULL;
6030 diff -u --recursive --new-file pl12/linux/net/inet/8390.h linux/net/inet/8390.h
6031 --- pl12/linux/net/inet/8390.h  Fri Aug 13 04:24:32 1993
6032 +++ linux/net/inet/8390.h       Mon Aug 30 22:43:18 1993
6033 @@ -8,6 +8,7 @@
6034  #define _8390_h
6035  
6036  #include <linux/if_ether.h>
6037 +#include <linux/ioport.h>
6038  
6039  #define TX_2X_PAGES 12
6040  #define TX_1X_PAGES 6
6041 @@ -25,10 +26,12 @@
6042  extern int ei_open(struct device *dev);
6043  extern void ei_interrupt(int reg_ptr);
6044  
6045 +#ifndef HAVE_AUTOIRQ
6046  /* From auto_irq.c */
6047  extern struct device *irq2dev_map[16];
6048  extern void autoirq_setup(int waittime);
6049  extern int autoirq_report(int waittime);
6050 +#endif
6051  
6052  /* Most of these entries should be in 'struct device' (or most of the
6053     things in there should be here!) */
6054 diff -u --recursive --new-file pl12/linux/net/inet/CONFIG linux/net/inet/CONFIG
6055 --- pl12/linux/net/inet/CONFIG  Fri Aug  6 20:46:27 1993
6056 +++ linux/net/inet/CONFIG       Fri Sep  3 23:54:30 1993
6057 @@ -1,53 +1,47 @@
6058  #
6059 -# Set the address and IRQ here. The ne.c and 3c503 driver will autoprobe
6060 +# Set any special options here.  Most drivers will autoprobe/autoIRQ
6061  # if you set the address or IRQ to zero, so we do that by default.
6062 -# Cards supportted:
6063 +# Cards and options supported:
6064  #
6065 -#      WD80x3          The Western Digital (SMC) WD80x3 driver
6066 -#        WD_SHMEM=xxx  Forces the address of the shared memory
6067 -#        FORCE_8BIT    Force card into 8-bit mode (WD8003)
6068 -#      NE2000          The Novell NE-2000 driver
6069 -#      HPLAN           The HP-LAN driver
6070 -#      EL1             The 3c501 EtherLink I driver (source missing?)
6071 -#      EL2             The 3c503 EtherLink II driver
6072 -#        EL2_AUI       Selects the AUI port instead of the BNC port
6073 -#      PLIP            The Crynwe PL/IP driver
6074 -#      SLIP            The MicroWalt SLIP driver
6075 +#  EI_DEBUG            Set the debugging level for 8390-based boards
6076 +#  CONFIG_WD80x3       The Western Digital (SMC) WD80x3 driver
6077 +#      WD_SHMEM=xxx    Forces the address of the shared memory
6078 +#      WD_no_mapout    Don't map out the shared memory (faster, but
6079 +#                      your machine may not warm-boot).
6080 +#  CONFIG_NE2000       The NE-[12]000 clone driver.
6081 +#      PACKETBUF_MEMSIZE  Allows an extra-large packet buffer to be
6082 +#                      used.  Usually pointless under Linux.
6083 +#      show_all_SAPROM  Show the entire address PROM, not just the
6084 +#                      ethernet address, during boot.
6085 +#      rw_bugfix       Patch an obscure bug with a version of the 8390.
6086 +#  CONFIG_HPLAN                The HP-LAN driver (for 8390-based boards only).
6087 +#      rw_bugfix       Fix the same obscure bug.
6088 +#  CONFIG_EL1          The 3c501 driver (just joking, never released)
6089 +#  CONFIG_EL2          The 3c503 EtherLink II driver
6090 +#      EL2_AUI         Default to the AUI port instead of the BNC port
6091 +#      no_probe_nonshared_memory  Don't probe for programmed-I/O boards.
6092 +#      EL2MEMTEST      Test shared memory at boot-time.
6093 +#  CONFIG_EL3
6094 +#      EL3_DEBUG       Set the debugging message level.
6095 +#  CONFIG_AT1500
6096 +#      LANCE_DEBUG     Set the debugging message level.
6097 +#      DEFAULT_DMA     Change the default DMA to other than 5.
6098 +#  CONFIG_PLIP         The Crynwr-protocol PL/IP driver
6099 +#  SLIP                        The MicroWalt SLIP driver
6100  #        SL_DUMP       Uses the "dump frame" debug code
6101  #        SL_COMPRESSED Use CSLIP
6102 -#      D_LINK          The D-Link DE-600 Portable Ethernet Adaptor.
6103 +#  D_LINK              The D-Link DE-600 Portable Ethernet Adaptor.
6104  #        D_LINK_IO     The D-Link I/O address (0x378 == default)
6105  #        D_LINK_IRQ    The D-Link IRQ number to use (IRQ7 == default)
6106  #        D_LINK_DEBUG  Enable or disable D-Link debugging
6107  #
6108 -# Note: for most WD (SMC) cards, the AutoProbe doesn't work.  You have
6109 -#      to force those cards into operation, by specifying the I/O add-
6110 -#      ress (EI8390=xxx), the IRQ (EI8390_IRQ=xxx) and the address of
6111 -#      the shared memory (WD_SHMEM=xxxx).  All other supported cards
6112 -#      behave like they should, you can leave the values to 0. -FvK
6113 -#
6114 -
6115 -# Comment out the lines you don't want..
6116 -
6117 -#CARDS := $(CARDS) -DSLIP
6118 -#CARDS := $(CARDS) -DPLIP
6119 -CARDS  := $(CARDS) -DWD80x3
6120 -CARDS  := $(CARDS) -DNE2000
6121 -CARDS  := $(CARDS) -DHPLAN
6122 -CARDS  := $(CARDS) -DEL2
6123 -CARDS  := $(CARDS) -DD_LINK
6124 -CARDS  := $(CARDS) -DCONFIG_AT1500
6125  
6126 -# For WD and SMC cards:
6127 -#OPTS          = -DEI8390=0x280 -DEI8390_IRQ=15
6128 -#WD_OPTS               = -DWD_SHMEM=0xCC000 -UFORCE_8BIT
6129 -OPTS           = -DEI8390=0 -DEI8390_IRQ=0
6130 -WD_OPTS                = -DWD_SHMEM=0
6131 +# This is at the top level with 'make config'
6132 +CARDS =
6133  
6134 -# For all other cards:
6135 -#OPTS          = -DEI8390=0 -DEI8390_IRQ=0
6136 -#WD_OPTS       = -DUD_SHMEM=0xCC000 -UFORCE_8BIT
6137  
6138 +OPTS           = #-DEI8390=0 -DEI8390_IRQ=0
6139 +WD_OPTS                = #-DWD_SHMEM=0
6140  EL2_OPTS       = #-UEL2_AUI
6141  NE_OPTS                =
6142  HP_OPTS                =
6143 diff -u --recursive --new-file pl12/linux/net/inet/Makefile linux/net/inet/Makefile
6144 --- pl12/linux/net/inet/Makefile        Fri Aug  6 20:44:14 1993
6145 +++ linux/net/inet/Makefile     Fri Sep  3 23:57:25 1993
6146 @@ -20,7 +20,7 @@
6147  OBJS   = Space.o sock.o utils.o route.o proc.o timer.o protocol.o loopback.o \
6148           eth.o packet.o arp.o dev.o 8390.o wd.o ne.o el2.o hp.o plip.o \
6149           slip.o slhc.o d_link.o auto_irq.o ip.o raw.o icmp.o tcp.o udp.o\
6150 -         lance.o
6151 +         lance.o 3c509.o #ip-frag.o
6152  
6153  ifdef CONFIG_INET
6154  
6155 @@ -38,36 +38,39 @@
6156  include        CONFIG
6157  
6158  
6159 -Space.o:       CONFIG Space.c Makefile
6160 +Space.o:       Space.c CONFIG /usr/include/linux/autoconf.h
6161                 $(CC) $(CPPFLAGS) $(CFLAGS) $(OPTS) $(CARDS) $(DL_OPTS) \
6162 -                                                       -c Space.c -o $@
6163 +                                                       -c $< -o $@
6164  
6165 -8390.o:                CONFIG 8390.c Makefile
6166 -               $(CC) $(CPPFLAGS) $(CFLAGS) $(CARDS) -c 8390.c -o $@
6167 +8390.o:                8390.c CONFIG
6168 +               $(CC) $(CPPFLAGS) $(CFLAGS) $(CARDS) -c $< -o $@
6169  
6170 -wd.o:          CONFIG wd.c Makefile
6171 -               $(CC) $(CPPFLAGS) $(CFLAGS) $(WD_OPTS) -c wd.c -o $@
6172 +wd.o:          wd.c CONFIG
6173 +               $(CC) $(CPPFLAGS) $(CFLAGS) $(WD_OPTS) -c $< -o $@
6174  
6175 -el2.o:         CONFIG el2.c el2reg.h Makefile
6176 -               $(CC) $(CPPFLAGS) $(CFLAGS) $(EL2_OPTS) -c el2.c -o $@
6177 +el2.o:         el2.c CONFIG el2reg.h
6178 +               $(CC) $(CPPFLAGS) $(CFLAGS) $(EL2_OPTS) -c $< -o $@
6179  
6180 -ne.o:          CONFIG ne.c Makefile
6181 -               $(CC) $(CPPFLAGS) $(CFLAGS) $(NE_OPTS) -c ne.c -o $@
6182 +ne.o:          ne.c CONFIG
6183 +               $(CC) $(CPPFLAGS) $(CFLAGS) $(NE_OPTS) -c $< -o $@
6184  
6185 -hp.o:          CONFIG hp.c Makefile
6186 -               $(CC) $(CPPFLAGS) $(CFLAGS) $(HP_OPTS) -c hp.c -o $@
6187 +hp.o:          hp.c CONFIG
6188 +               $(CC) $(CPPFLAGS) $(CFLAGS) $(HP_OPTS) -c $< -o $@
6189  
6190 -plip.o:                CONFIG plip.c Makefile
6191 -               $(CC) $(CPPFLAGS) $(CFLAGS) $(PLIP_OPTS) -c plip.c -o $@
6192 +plip.o:                plip.c CONFIG
6193 +               $(CC) $(CPPFLAGS) $(CFLAGS) $(PLIP_OPTS) -c $< -o $@
6194  
6195 -slip.o:                CONFIG slip.c Makefile
6196 -               $(CC) $(CPPFLAGS) $(CFLAGS) $(SLIP_OPTS) -c slip.c -o $@
6197 +slip.o:                slip.c CONFIG
6198 +               $(CC) $(CPPFLAGS) $(CFLAGS) $(SLIP_OPTS) -c $< -o $@
6199  
6200 -d_link.o:      CONFIG d_link.c Makefile
6201 -               $(CC) $(CPPFLAGS) $(CFLAGS) $(DL_OPTS) -c d_link.c -o $@
6202 +d_link.o:      d_link.c CONFIG
6203 +               $(CC) $(CPPFLAGS) $(CFLAGS) $(DL_OPTS) -c $< -o $@
6204  
6205 -lance.o:       CONFIG lance.c Makefile
6206 -               $(CC) $(CPPFLAGS) $(CFLAGS) $(AT_OPTS) -c lance.c -o $@
6207 +lance.o:       lance.c CONFIG
6208 +               $(CC) $(CPPFLAGS) $(CFLAGS) $(AT_OPTS) -c $< -o $@
6209 +
6210 +3c509.o:       3c509.c CONFIG
6211 +               $(CC) $(CPPFLAGS) $(CFLAGS) $(EL3_OPTS) -c $< -o $@
6212  
6213  subdirs:       dummy
6214                 for i in $(SUBDIRS); do (cd $$i; $(MAKE)); done
6215 diff -u --recursive --new-file pl12/linux/net/inet/Space.c linux/net/inet/Space.c
6216 --- pl12/linux/net/inet/Space.c Fri Aug 13 04:27:58 1993
6217 +++ linux/net/inet/Space.c      Sat Sep  4 13:42:55 1993
6218 @@ -33,6 +33,73 @@
6219  #define        NEXT_DEV        NULL
6220  
6221  
6222 +/* A unifed ethernet device probe.  This is the easiest way to have every
6223 +   ethernet adaptor have the name "eth[0123...]".
6224 +   */
6225 +
6226 +extern int wd_probe(struct device *dev);
6227 +extern int el2_probe(struct device *dev);
6228 +extern int ne_probe(struct device *dev);
6229 +extern int hp_probe(struct device *dev);
6230 +extern int znet_probe(struct device *);
6231 +extern int express_probe(struct device *);
6232 +extern int el3_probe(struct device *);
6233 +extern int atp_probe(struct device *);
6234 +extern int at1500_probe(struct device *);
6235 +extern int depca_probe(struct device *);
6236 +extern int el1_probe(struct device *);
6237 +
6238 +static int
6239 +ethif_probe(struct device *dev)
6240 +{
6241 +    short base_addr = dev->base_addr;
6242 +
6243 +    if (base_addr < 0  ||  base_addr == 1)
6244 +       return 1;               /* ENXIO */
6245 +
6246 +    if (1
6247 +#if defined(CONFIG_WD80x3) || defined(WD80x3)
6248 +       && wd_probe(dev)
6249 +#endif
6250 +#if defined(CONFIG_EL2) || defined(EL2)
6251 +       && el2_probe(dev)
6252 +#endif
6253 +#if defined(CONFIG_NE2000) || defined(NE2000)
6254 +       && ne_probe(dev)
6255 +#endif
6256 +#if defined(CONFIG_HPLAN) || defined(HPLAN)
6257 +       && hp_probe(dev)
6258 +#endif
6259 +#ifdef CONFIG_AT1500
6260 +       && at1500_probe(dev)
6261 +#endif
6262 +#ifdef CONFIG_EL3
6263 +       && el3_probe(dev)
6264 +#endif
6265 +#ifdef CONFIG_ZNET
6266 +       && znet_probe(dev)
6267 +#endif
6268 +#ifdef CONFIG_EEXPRESS
6269 +       && express_probe(dev)
6270 +#endif
6271 +#ifdef CONFIG_ATP              /* AT-LAN-TEC (RealTek) pocket adaptor. */
6272 +       && atp_probe(dev)
6273 +#endif
6274 +#ifdef CONFIG_DEPCA
6275 +       && depca_probe(dev)
6276 +#endif
6277 +#ifdef CONFIG_EL1
6278 +       && el1_probe(dev)
6279 +#endif
6280 +       && 1 ) {
6281 +       return 1;       /* -ENODEV or -EAGAIN would be more accurate. */
6282 +    }
6283 +    return 0;
6284 +}
6285 +
6286 +
6287 +/* This remains seperate because it requires the addr and IRQ to be
6288 +   set. */
6289  #if defined(D_LINK) || defined(CONFIG_DE600)
6290      extern int d_link_init(struct device *);
6291      static struct device d_link_dev = {
6292 @@ -51,101 +118,32 @@
6293  #   define NEXT_DEV    (&d_link_dev)
6294  #endif
6295  
6296 -#ifdef CONFIG_EL1
6297 -#error 
6298 -#   ifndef EL1_IRQ
6299 -#      define EL1_IRQ 9
6300 -#   endif
6301 -#   ifndef EL1
6302 -#      define EL1 0
6303 -#   endif
6304 -    extern int el1_init(struct device *);
6305 -    static struct device el1_dev = {
6306 -        "el0", 0, 0, 0, 0, EL1,        EL1_IRQ, 0, 0, 0, NEXT_DEV, el1_init
6307 -    };
6308 -#   undef NEXT_DEV
6309 -#   define NEXT_DEV    (&el1_dev)
6310 -#endif  /* EL1 */
6311 -
6312 -#ifdef CONFIG_DEPCA
6313 -    extern int depca_probe(struct device *);
6314 -    static struct device depca_dev = {
6315 -        "depca0", 0,0,0,0, 0, 0, 0, 0, 0, NEXT_DEV, depca_probe,
6316 -    };
6317 -#   undef NEXT_DEV
6318 -#   define NEXT_DEV    (&depca_dev)
6319 -#endif  /* CONFIG_DEPCA */
6320 -
6321 -
6322 -#ifdef CONFIG_ATP              /* AT-LAN-TEC (RealTek) pocket adaptor. */
6323 -    extern int atp_probe(struct device *);
6324 -    static struct device atp_dev = {
6325 -        "atp0", 0,0,0,0, 0, 0, 0, 0, 0, NEXT_DEV, atp_probe,
6326 -    };
6327 -#   undef NEXT_DEV
6328 -#   define NEXT_DEV    (&atp_dev)
6329 -#endif  /* CONFIG_ATP */
6330 -
6331 -#ifdef CONFIG_EL3
6332 -    extern int el3_probe(struct device *);
6333 -    static struct device eliii0_dev = {
6334 -        "eliii0", 0,0,0,0, 0, 0, 0, 0, 0, NEXT_DEV, el3_probe,
6335 -    };
6336 -#   undef NEXT_DEV
6337 -#   define NEXT_DEV    (&eliii0_dev)
6338 -#endif  /* CONFIG_3C509 aka EL3 */
6339 -
6340 -#ifdef CONFIG_ZNET
6341 -    extern int znet_probe(struct device *);
6342 -    static struct device znet_dev = {
6343 -       "znet", 0,0,0,0, 0, 0, 0, 0, 0, NEXT_DEV, znet_probe, };
6344 -#   undef NEXT_DEV
6345 -#   define NEXT_DEV    (&znet_dev)
6346 -#endif  /* CONFIG_ZNET */
6347 +/* The first device defaults to I/O base '0', which means autoprobe. */
6348 +#ifdef EI8390
6349 +# define ETH0_ADDR EI8390
6350 +#else
6351 +# define ETH0_ADDR 0
6352 +#endif
6353 +#ifdef EI8390_IRQ
6354 +# define ETH0_IRQ EI8390_IRQ
6355 +#else
6356 +# define ETH0_IRQ 0
6357 +#endif
6358 +/* "eth0" defaults to autoprobe, other use a base of "-0x20", "don't probe".
6359 +   Enable these with boot-time setup. 0.99pl13+ can optionally autoprobe. */
6360  
6361 -#ifdef CONFIG_EEXPRESS
6362 -    extern int express_probe(struct device *);
6363 -    static struct device express0_dev = {
6364 -       "exp0", 0,0,0,0, 0, 0, 0, 0, 0, NEXT_DEV, express_probe, };
6365 -#   undef NEXT_DEV
6366 -#   define NEXT_DEV    (&express0_dev)
6367 -#endif  /* CONFIG_EEPRESS */
6368 +static struct device eth3_dev = {
6369 +    "eth3", 0,0,0,0,0xffe0 /* I/O base*/, 0,0,0,0, NEXT_DEV, ethif_probe };
6370 +static struct device eth2_dev = {
6371 +    "eth2", 0,0,0,0,0xffe0 /* I/O base*/, 0,0,0,0, &eth3_dev, ethif_probe };
6372 +static struct device eth1_dev = {
6373 +    "eth1", 0,0,0,0,0xffe0 /* I/O base*/, 0,0,0,0, &eth2_dev, ethif_probe };
6374  
6375 -#ifdef CONFIG_AT1500
6376 -    extern int at1500_probe(struct device *);
6377 -    static struct device lance_dev = {
6378 -        "le0",
6379 -       0,0,0,0, 0 /* I/O Base */, 0 /* pre-set IRQ */,
6380 -        0, 0, 0, NEXT_DEV, at1500_probe,
6381 -    };
6382 -#   undef NEXT_DEV
6383 -#   define NEXT_DEV    (&lance_dev)
6384 -#endif  /* AT1500BT */
6385 +static struct device eth0_dev = {
6386 +    "eth0", 0, 0, 0, 0, ETH0_ADDR, ETH0_IRQ, 0, 0, 0, &eth1_dev, ethif_probe };
6387  
6388 -#if defined(EI8390) || defined(CONFIG_EL2) || defined(CONFIG_NE2000) \
6389 -    || defined(CONFIG_WD80x3) || defined(CONFIG_HPLAN)
6390 -#   ifndef EI8390
6391 -#      define EI8390 0
6392 -#   endif
6393 -#   ifndef EI8390_IRQ
6394 -#      define EI8390_IRQ 0
6395 -#   endif
6396 -    extern int ethif_init(struct device *);
6397 -    static struct device ei8390_dev = {
6398 -       "eth0",
6399 -       0,                              /* auto-config                  */
6400 -       0,
6401 -       0,
6402 -       0,
6403 -       EI8390,
6404 -       EI8390_IRQ,
6405 -       0, 0, 0,
6406 -       NEXT_DEV,
6407 -       ethif_init
6408 -    };
6409  #   undef NEXT_DEV
6410 -#   define NEXT_DEV    (&ei8390_dev)
6411 -#endif  /* The EI8390 drivers. */
6412 +#   define NEXT_DEV    (&eth0_dev)
6413  
6414  #if defined(PLIP) || defined(CONFIG_PLIP)
6415      extern int plip_init(struct device *);
6416 diff -u --recursive --new-file pl12/linux/net/inet/dev.c linux/net/inet/dev.c
6417 --- pl12/linux/net/inet/dev.c   Sat Aug 14 14:32:05 1993
6418 +++ linux/net/inet/dev.c        Tue Aug 31 05:00:04 1993
6419 @@ -18,6 +18,7 @@
6420   */
6421  #include <asm/segment.h>
6422  #include <asm/system.h>
6423 +#include <asm/bitops.h>
6424  #include <linux/config.h>
6425  #include <linux/types.h>
6426  #include <linux/kernel.h>
6427 @@ -29,6 +30,7 @@
6428  #include <linux/in.h>
6429  #include <linux/errno.h>
6430  #include <linux/interrupt.h>
6431 +#include <linux/if_ether.h>
6432  #include "inet.h"
6433  #include "dev.h"
6434  #include "eth.h"
6435 @@ -368,9 +370,40 @@
6436    sti();
6437  }
6438  
6439 +/*
6440 + * Receive a packet from a device driver and queue it for the upper
6441 + * (protocol) levels.  It always succeeds.
6442 + */
6443 +void
6444 +netif_rx(struct sk_buff *skb)
6445 +{
6446 +  /* Set any necessary flags. */
6447 +  skb->lock = 0;
6448 +  skb->sk = NULL;
6449 +
6450 +  /* and add it to the "backlog" queue. */
6451 +  cli();
6452 +  if (backlog == NULL) {
6453 +       skb->prev = skb;
6454 +       skb->next = skb;
6455 +       backlog = skb;
6456 +  } else {
6457 +       skb->prev = (struct sk_buff *) backlog->prev;
6458 +       skb->next = (struct sk_buff *) backlog;
6459 +       skb->next->prev = skb;
6460 +       skb->prev->next = skb;
6461 +  }
6462 +  sti();
6463 +   
6464 +  /* If any packet arrived, mark it for processing. */
6465 +  if (backlog != NULL) mark_bh(INET_BH);
6466 +
6467 +  return;
6468 +}
6469 +
6470  
6471  /*
6472 - * Fetch a packet from a device driver.
6473 + * The old interface to fetch a packet from a device driver.
6474   * This function is the base level entry point for all drivers that
6475   * want to send a packet to the upper (protocol) levels.  It takes
6476   * care of de-multiplexing the packet to the various modules based
6477 @@ -389,18 +422,20 @@
6478    int len2;
6479  
6480    if (dev == NULL || buff == NULL || len <= 0) return(1);
6481 -  if (dropping && backlog != NULL) {
6482 -       return(1);
6483 -  }
6484 -  if (dropping) printk("INET: dev_rint: no longer dropping packets.\n");
6485 -  dropping = 0;
6486 -
6487    if (flags & IN_SKBUFF) {
6488         skb = (struct sk_buff *) buff;
6489    } else {
6490 +       if (dropping) {
6491 +         if (backlog != NULL)
6492 +             return(1);
6493 +         printk("INET: dev_rint: no longer dropping packets.\n");
6494 +         dropping = 0;
6495 +       }
6496 +
6497         skb = (struct sk_buff *) kmalloc(sizeof(*skb) + len, GFP_ATOMIC);
6498         if (skb == NULL) {
6499 -               printk("dev_rint: packet dropped (no memory) !\n");
6500 +               printk("dev_rint: packet dropped on %s (no memory) !\n",
6501 +                      dev->name);
6502                 dropping = 1;
6503                 return(1);
6504         }
6505 @@ -426,25 +461,8 @@
6506    }
6507    skb->len = len;
6508    skb->dev = dev;
6509 -  skb->sk = NULL;
6510 -
6511 -  /* Now add it to the backlog. */
6512 -  cli();
6513 -  if (backlog == NULL) {
6514 -       skb->prev = skb;
6515 -       skb->next = skb;
6516 -       backlog = skb;
6517 -  } else {
6518 -       skb->prev = (struct sk_buff *) backlog->prev;
6519 -       skb->next = (struct sk_buff *) backlog;
6520 -       skb->next->prev = skb;
6521 -       skb->prev->next = skb;
6522 -  }
6523 -  sti();
6524 -   
6525 -  /* If any packet arrived, mark it for processing. */
6526 -  if (backlog != NULL) mark_bh(INET_BH);
6527  
6528 +  netif_rx(skb);
6529    /* OK, all done. */
6530    return(0);
6531  }
6532 @@ -475,16 +493,11 @@
6533    struct packet_type *ptype;
6534    unsigned short type;
6535    unsigned char flag = 0;
6536 -  static volatile int in_bh = 0;
6537 +  static volatile char in_bh = 0;
6538  
6539 -  /* Check && mark our BUSY state. */
6540 -  cli();
6541 -  if (in_bh != 0) {
6542 -       sti();
6543 -       return;
6544 -  }
6545 -  in_bh = 1;
6546 -  sti();
6547 +  /* Atomically check and mark our BUSY state. */
6548 +  if (set_bit(1, (void*)&in_bh))
6549 +      return;
6550  
6551    /* Can we send anything now? */
6552    dev_transmit();
6553 @@ -671,14 +684,46 @@
6554    return(pos - arg);
6555  }
6556  
6557 +/* Print device statistics. */
6558 +char *sprintf_stats(char *buffer, struct device *dev)
6559 +{
6560 +  char *pos = buffer;
6561 +  struct enet_statistics *stats = (dev->get_stats ? dev->get_stats(dev): NULL);
6562 +
6563 +  if (stats)
6564 +    pos += sprintf(pos, "%6s:%7d %4d %4d %4d %4d %8d %4d %4d %4d %5d %4d\n",
6565 +                  dev->name,
6566 +                  stats->rx_packets, stats->rx_errors,
6567 +                  stats->rx_dropped + stats->rx_missed_errors,
6568 +                  stats->rx_fifo_errors,
6569 +                  stats->rx_length_errors + stats->rx_over_errors
6570 +                  + stats->rx_crc_errors + stats->rx_frame_errors,
6571 +                  stats->tx_packets, stats->tx_errors, stats->tx_dropped,
6572 +                  stats->tx_fifo_errors, stats->collisions,
6573 +                  stats->tx_carrier_errors + stats->tx_aborted_errors
6574 +                  + stats->tx_window_errors + stats->tx_heartbeat_errors);
6575 +  else
6576 +      pos += sprintf(pos, "%6s: No statistics available.\n", dev->name);
6577 +
6578 +  return pos;
6579 +}
6580  
6581  /* Called from the PROCfs module. */
6582  int
6583  dev_get_info(char *buffer)
6584  {
6585 -  return(dev_ifconf(buffer));
6586 -}
6587 +  char *pos = buffer;
6588 +  struct device *dev;
6589  
6590 +  pos +=
6591 +      sprintf(pos,
6592 +             "Inter-|   Receive                  |  Transmit\n"
6593 +             " face |packets errs drop fifo frame|packets errs drop fifo colls carrier\n");
6594 +  for (dev = dev_base; dev != NULL; dev = dev->next) {
6595 +      pos = sprintf_stats(pos, dev);
6596 +  }
6597 +  return pos - buffer;
6598 +}
6599  
6600  /* Perform the SIOCxIFxxx calls. */
6601  static int
6602 @@ -702,18 +747,18 @@
6603                 ret = 0;
6604                 break;
6605         case SIOCSIFFLAGS:
6606 -               ret = dev->flags;
6607 -               dev->flags = ifr.ifr_flags & (
6608 +               {
6609 +                 int old_flags = dev->flags;
6610 +                 dev->flags = ifr.ifr_flags & (
6611                         IFF_UP | IFF_BROADCAST | IFF_DEBUG | IFF_LOOPBACK |
6612                         IFF_POINTOPOINT | IFF_NOTRAILERS | IFF_RUNNING |
6613                         IFF_NOARP | IFF_PROMISC | IFF_ALLMULTI);
6614 -               if ((ret & IFF_UP) && ((dev->flags & IFF_UP) == 0)) {
6615 +                 if ((old_flags & IFF_UP) && ((dev->flags & IFF_UP) == 0)) {
6616                         ret = dev_close(dev);
6617 -               } else {
6618 -                       if (((ret & IFF_UP) == 0) && (dev->flags & IFF_UP)) {
6619 -                               ret = dev_open(dev);
6620 -                       } else ret = 0;
6621 -               }
6622 +                 } else
6623 +                     ret = (! (old_flags & IFF_UP) && (dev->flags & IFF_UP))
6624 +                       ? dev_open(dev) : 0;
6625 +               }
6626                 break;
6627         case SIOCGIFADDR:
6628                 (*(struct sockaddr_in *)
6629 @@ -820,9 +865,55 @@
6630    int ret;
6631  
6632    switch(cmd) {
6633 -       case IP_SET_DEV:
6634 -               printk("INET: Warning: old-style ioctl(IP_SET_DEV) called!\n");
6635 -               return(-EINVAL);
6636 +  case IP_SET_DEV:
6637 +      {          /* Maintain backwards-compatibility, to be deleted for 1.00. */
6638 +         struct device *dev;
6639 +         /* The old 'struct ip_config'. */
6640 +         struct ip_config {
6641 +             char name[MAX_IP_NAME];
6642 +             unsigned long paddr, router, net,up:1,destroy:1;
6643 +         } ipc;
6644 +         int retval, loopback;
6645 +
6646 +         printk("INET: Warning: old-style ioctl(IP_SET_DEV) called!\n");
6647 +         if (!suser())
6648 +             return (-EPERM);
6649 +         
6650 +         verify_area (VERIFY_WRITE, arg, sizeof (ipc));
6651 +         memcpy_fromfs(&ipc, arg, sizeof (ipc));
6652 +         ipc.name[MAX_IP_NAME-1] = 0;
6653 +         loopback = (strcmp(ipc.name, "loopback") == 0);
6654 +         dev = dev_get( loopback ? "lo" : ipc.name);
6655 +         if (dev == NULL)
6656 +             return -EINVAL;
6657 +         ipc.destroy = 0;
6658 +         dev->pa_addr = ipc.paddr;
6659 +         dev->family = AF_INET;
6660 +         dev->pa_mask = get_mask(dev->pa_addr);
6661 +         dev->pa_brdaddr = dev->pa_addr | ~dev->pa_mask;
6662 +         if (ipc.net != 0xffffffff) {
6663 +             dev->flags |= IFF_BROADCAST;
6664 +             dev->pa_brdaddr = ipc.net;
6665 +         }
6666 +         
6667 +         /* To be proper we should delete the route here. */
6668 +         if (ipc.up == 0)
6669 +             return (dev->flags & IFF_UP != 0) ? dev_close(dev) : 0;
6670 +
6671 +         if ((dev->flags & IFF_UP) == 0
6672 +             && (retval = dev_open(dev)) != 0)
6673 +             return retval;
6674 +         printk("%s: adding HOST route of %8.8x.\n", dev->name,
6675 +                htonl(ipc.paddr));
6676 +         rt_add(RTF_HOST, ipc.paddr, 0, dev);
6677 +         if (ipc.router != 0 && ipc.router != -1) {
6678 +             rt_add(RTF_GATEWAY, ipc.paddr, ipc.router, dev);
6679 +             printk("%s: adding GATEWAY route of %8.8x.\n",
6680 +                    dev->name, htonl(ipc.paddr));
6681 +
6682 +         }
6683 +         return 0;
6684 +      }
6685         case SIOCGIFCONF:
6686                 (void) dev_ifconf((char *) arg);
6687                 ret = 0;
6688 diff -u --recursive --new-file pl12/linux/net/inet/dev.h linux/net/inet/dev.h
6689 --- pl12/linux/net/inet/dev.h   Fri Aug 13 04:24:31 1993
6690 +++ linux/net/inet/dev.h        Sat Aug 28 00:48:47 1993
6691 @@ -169,6 +169,9 @@
6692  extern int             dev_close(struct device *dev);
6693  extern void            dev_queue_xmit(struct sk_buff *skb, struct device *dev,
6694                                        int pri);
6695 +#define HAVE_NETIF_RX 1
6696 +extern void            netif_rx(struct sk_buff *skb);
6697 +/* The old interface to netif_rx(). */
6698  extern int             dev_rint(unsigned char *buff, long len, int flags,
6699                                  struct device * dev);
6700  extern void            dev_transmit(void);
6701 diff -u --recursive --new-file pl12/linux/net/inet/el2.c linux/net/inet/el2.c
6702 --- pl12/linux/net/inet/el2.c   Fri Aug 13 04:24:27 1993
6703 +++ linux/net/inet/el2.c        Mon Aug 30 23:59:57 1993
6704 @@ -16,7 +16,7 @@
6705  */
6706  
6707  static char *version =
6708 -    "el2.c:v0.99.12B 8/12/93 Donald Becker (becker@super.org)\n";
6709 +    "el2.c:v0.99.13 8/30/93 Donald Becker (becker@super.org)\n";
6710  
6711  #include <linux/config.h>
6712  #include <linux/kernel.h>
6713 @@ -30,9 +30,9 @@
6714  #include "8390.h"
6715  #include "el2reg.h"
6716  
6717 -int el2autoprobe(int ioaddr, struct device *dev);
6718 +int el2_probe(struct device *dev);
6719  int el2_pio_autoprobe(struct device *dev);
6720 -int el2probe(int ioaddr, struct device *dev);
6721 +int el2probe1(int ioaddr, struct device *dev);
6722  
6723  static int el2_open(struct device *dev);
6724  static int el2_close(struct device *dev);
6725 @@ -55,13 +55,15 @@
6726  static int ports[] = {0x300,0x310,0x330,0x350,0x250,0x280,0x2a0,0x2e0,0};
6727  
6728  int
6729 -el2autoprobe(int ioaddr, struct device *dev)
6730 +el2_probe(struct device *dev)
6731  {
6732      int *addr, addrs[] = { 0xddffe, 0xd9ffe, 0xcdffe, 0xc9ffe, 0};
6733 +    short ioaddr = dev->base_addr;
6734  
6735 -    /* Non-autoprobe case first: */
6736 +    if (ioaddr < 0)
6737 +       return ENXIO;           /* Don't probe at all. */
6738      if (ioaddr > 0)
6739 -       return el2probe(ioaddr, dev);
6740 +       return ! el2probe1(ioaddr, dev);
6741  
6742      for (addr = addrs; *addr; addr++) {
6743         int i;
6744 @@ -70,13 +72,19 @@
6745         for(i = 7; i >= 0; i--, base_bits >>= 1)
6746             if (base_bits & 0x1)
6747                 break;
6748 -       if (base_bits == 1 &&  el2probe(ports[i], dev))
6749 -           return dev->base_addr;
6750 +       if (base_bits != 1)
6751 +           continue;
6752 +#ifdef HAVE_PORTRESERVE
6753 +       if (check_region(ports[i], 16))
6754 +           continue;
6755 +#endif
6756 +       if (el2probe1(ports[i], dev))
6757 +           return 0;
6758      }
6759 -#ifdef probe_nonshared_memory
6760 +#ifndef no_probe_nonshared_memory
6761      return el2_pio_autoprobe(dev);
6762  #else
6763 -    return 0;
6764 +    return ENODEV;
6765  #endif
6766  }
6767  
6768 @@ -87,14 +95,18 @@
6769  {
6770      int i;
6771      for (i = 0; i < 8; i++) {
6772 +#ifdef HAVE_PORTRESERVE
6773 +       if (check_region(ports[i], 16))
6774 +           continue;
6775 +#endif
6776         /* Reset and/or avoid any lurking NE2000 */
6777         if (inb_p(ports[i] + 0x408) == 0xff)
6778             continue;
6779         if (inb(ports[i] + 0x403) == (0x80 >> i) /* Preliminary check */
6780 -           && el2probe(ports[i], dev))
6781 -           return dev->base_addr;
6782 +           && el2probe1(ports[i], dev))
6783 +           return 0;
6784      }
6785 -    return 0;
6786 +    return ENODEV;
6787  }
6788  
6789  /* Probe for the Etherlink II card at I/O port base IOADDR,
6790 @@ -101,7 +113,7 @@
6791     returning non-zero on sucess.  If found, set the station
6792     address and memory parameters in DEVICE. */
6793  int
6794 -el2probe(int ioaddr, struct device *dev)
6795 +el2probe1(int ioaddr, struct device *dev)
6796  {
6797      int i, iobase_reg, membase_reg, saved_406;
6798      unsigned char *station_addr = dev->dev_addr;
6799 @@ -134,6 +146,9 @@
6800         return 0;
6801      }
6802  
6803 +#ifdef HAVE_PORTRESERVE
6804 +    snarf_region(ioaddr, 16);
6805 +#endif
6806      ethdev_init(dev);
6807  
6808      /* Map the 8390 back into the window. */
6809 diff -u --recursive --new-file pl12/linux/net/inet/hp.c linux/net/inet/hp.c
6810 --- pl12/linux/net/inet/hp.c    Fri Aug 13 04:24:29 1993
6811 +++ linux/net/inet/hp.c Tue Aug 31 00:02:40 1993
6812 @@ -13,7 +13,7 @@
6813  */
6814  
6815  static char *version =
6816 -    "hp.c:v0.99.12+ 8/12/93 Donald Becker (becker@super.org)\n";
6817 +    "hp.c:v0.99.13 8/30/93 Donald Becker (becker@super.org)\n";
6818  
6819  #include <linux/config.h>
6820  #include <linux/kernel.h>
6821 @@ -40,7 +40,7 @@
6822  #define HP_8BSTOP_PG   0x80    /* Last page +1 of RX ring */
6823  #define HP_16BSTOP_PG  0xFF    /* Last page +1 of RX ring */
6824  
6825 -int hpprobe(int ioaddr, struct device *dev);
6826 +int hp_probe(struct device *dev);
6827  int hpprobe1(int ioaddr, struct device *dev);
6828  
6829  static void hp_reset_8390(struct device *dev);
6830 @@ -59,17 +59,27 @@
6831      Also initialize the card and fill in STATION_ADDR with the station
6832     address. */
6833  
6834 -int hpprobe(int ioaddr,  struct device *dev)
6835 +int hp_probe(struct device *dev)
6836  {
6837      int *port, ports[] = {0x300, 0x320, 0x340, 0x280, 0x2C0, 0x200, 0x240, 0};
6838 +    short ioaddr = dev->base_addr;
6839  
6840 +    if (ioaddr < 0)
6841 +       return ENXIO;           /* Don't probe at all. */
6842      if (ioaddr > 0x100)
6843 -       return hpprobe1(ioaddr, dev);
6844 +       return ! hpprobe1(ioaddr, dev);
6845  
6846 -    for (port = &ports[0]; *port; port++)
6847 -       if (inb_p(*port) != 0xff && hpprobe1(*port, dev))
6848 -           return dev->base_addr;
6849 -    return 0;
6850 +    for (port = &ports[0]; *port; port++) {
6851 +#ifdef HAVE_PORTRESERVE
6852 +       if (check_region(*port, 32))
6853 +           continue;
6854 +#endif
6855 +       if (inb_p(*port) != 0xff && hpprobe1(*port, dev)) {
6856 +           return 0;
6857 +       }
6858 +    }
6859 +    dev->base_addr = ioaddr;
6860 +    return ENODEV;
6861  }
6862  
6863  int hpprobe1(int ioaddr, struct device *dev)
6864 @@ -139,6 +149,10 @@
6865           return 0;
6866        }
6867    }
6868 +
6869 +#ifdef HAVE_PORTRESERVE
6870 +    snarf_region(ioaddr, 32);
6871 +#endif
6872  
6873    if (ei_debug > 1)
6874        printk(version);
6875 diff -u --recursive --new-file pl12/linux/net/inet/ip.c linux/net/inet/ip.c
6876 --- pl12/linux/net/inet/ip.c    Fri Aug  6 20:40:18 1993
6877 +++ linux/net/inet/ip.c Sat Sep  4 00:00:14 1993
6878 @@ -5,10 +5,11 @@
6879   *
6880   *             The Internet Protocol (IP) module.
6881   *
6882 - * Version:    @(#)ip.c        1.0.16  06/02/93
6883 + * Version:    @(#)ip.c        1.0.16b 9/1/93
6884   *
6885   * Authors:    Ross Biro, <bir7@leland.Stanford.Edu>
6886   *             Fred N. van Kempen, <waltje@uWalt.NL.Mugnet.ORG>
6887 + *             Donald Becker, <becker@super.org>
6888   *
6889   *             This program is free software; you can redistribute it and/or
6890   *             modify it under the terms of the GNU General Public License
6891 @@ -382,6 +383,27 @@
6892    return(0);
6893  }
6894  
6895 +/* This is a version of ip_compute_csum() optimized for IP headers, which
6896 +   always checksum on 4 octet boundaries. */
6897 +static inline unsigned short
6898 +ip_fast_csum(unsigned char * buff, int wlen)
6899 +{
6900 +    unsigned long sum = 0;
6901 +    __asm__("\t clc\n"
6902 +           "1:\n"
6903 +           "\t lodsl\n"
6904 +           "\t adcl %%eax, %%ebx\n"
6905 +           "\t loop 1b\n"
6906 +           "\t adcl $0, %%ebx\n"
6907 +           "\t movl %%ebx, %%eax\n"
6908 +           "\t shrl $16, %%eax\n"
6909 +           "\t addw %%ax, %%bx\n"
6910 +           "\t adcw $0, %%bx\n"
6911 +           : "=b" (sum) , "=S" (buff)
6912 +           : "0" (sum), "c" (wlen) ,"1" (buff)
6913 +           : "ax", "cx", "si", "bx" );
6914 +    return (~sum) & 0xffff;
6915 +}
6916  
6917  /*
6918   * This routine does all the checksum computations that don't
6919 @@ -429,23 +451,21 @@
6920    return(sum & 0xffff);
6921  }
6922  
6923 -
6924 -/* Check the header of an incoming IP datagram. */
6925 +/* Check the header of an incoming IP datagram.  This version is still used in slhc.c. */
6926  int
6927  ip_csum(struct iphdr *iph)
6928  {
6929 -  if (iph->check == 0) return(0);
6930 -  if (ip_compute_csum((unsigned char *)iph, iph->ihl*4) == 0) return(0);
6931 +  if (iph->check == 0  || ip_fast_csum((unsigned char *)iph, iph->ihl) == 0)
6932 +      return(0);
6933    return(1);
6934  }
6935  
6936 -
6937  /* Generate a checksym for an outgoing IP datagram. */
6938  static void
6939  ip_send_check(struct iphdr *iph)
6940  {
6941     iph->check = 0;
6942 -   iph->check = ip_compute_csum((unsigned char *)iph, iph->ihl*4);
6943 +   iph->check = ip_fast_csum((unsigned char *)iph, iph->ihl);
6944  }
6945  
6946  
6947 @@ -554,21 +574,20 @@
6948  int
6949  ip_rcv(struct sk_buff *skb, struct device *dev, struct packet_type *pt)
6950  {
6951 -  struct iphdr *iph;
6952 +  struct iphdr *iph = skb->h.iph;
6953    unsigned char hash;
6954    unsigned char flag = 0;
6955 +  unsigned char opts_p = 0;    /* Set iff the packet has options. */
6956    struct inet_protocol *ipprot;
6957    static struct options opt; /* since we don't use these yet, and they
6958                                 take up stack space. */
6959    int brd;
6960  
6961 -  iph = skb->h.iph;
6962 -  memset((char *) &opt, 0, sizeof(opt));
6963    DPRINTF((DBG_IP, "<<\n"));
6964 -  ip_print(iph);
6965  
6966    /* Is the datagram acceptable? */
6967 -  if (ip_csum(iph) || do_options(iph, &opt) || iph->version != 4) {
6968 +  if (iph->version != 4
6969 +      || (iph->check != 0 && ip_fast_csum((unsigned char *)iph, iph->ihl) !=0)) {
6970         DPRINTF((DBG_IP, "\nIP: *** datagram error ***\n"));
6971         DPRINTF((DBG_IP, "    SRC = %s   ", in_ntoa(iph->saddr)));
6972         DPRINTF((DBG_IP, "    DST = %s (ignored)\n", in_ntoa(iph->daddr)));
6973 @@ -577,7 +596,15 @@
6974         return(0);
6975    }
6976  
6977 -  /* Do any IP forwarding required. */
6978 +  if (iph->ihl != 5) {         /* Fast path for the typical optionless IP packet. */
6979 +      ip_print(iph);           /* Bogus, only for debugging. */
6980 +      memset((char *) &opt, 0, sizeof(opt));
6981 +      if (do_options(iph, &opt) != 0)
6982 +         return 0;
6983 +      opts_p = 1;
6984 +  }
6985 +
6986 +  /* Do any IP forwarding required.  chk_addr() is expensive -- avoid it someday. */
6987    if ((brd = chk_addr(iph->daddr)) == 0) {
6988  #ifdef CONFIG_IP_FORWARD
6989         ip_forward(skb, dev);
6990 @@ -588,17 +615,12 @@
6991    }
6992  
6993    /*
6994 -   * Deal with fragments: not really...
6995 -   * Fragmentation is definitely a required part of IP (yeah, guys,
6996 -   * I read Linux-Activists.NET too :-), but the current "sk_buff"
6997 -   * allocation stuff doesn't make things simpler.  When we're all
6998 -   * done cleaning up the mess, we'll add Ross Biro's "mbuf" stuff
6999 -   * to the code, which will replace the sk_buff stuff completely.
7000 -   * That will (a) make the code even cleaner, (b) allow me to do
7001 -   * the DDI (Device Driver Interface) the way I want to, and (c),
7002 -   * it will allow for easy addition of fragging.  Any takers? -FvK
7003 -   */
7004 -  if ((iph->frag_off & 32) || (ntohs(iph->frag_off) & 0x1fff)) {
7005 +   * Reassemble IP fragments. */
7006 +
7007 +  if ((iph->frag_off & 0x0020) || (ntohs(iph->frag_off) & 0x1fff)) {
7008 +#ifdef CONFIG_IP_DEFRAG
7009 +      ip_defrag(skb);
7010 +#else
7011         printk("\nIP: *** datagram fragmentation not yet implemented ***\n");
7012         printk("    SRC = %s   ", in_ntoa(iph->saddr));
7013         printk("    DST = %s (ignored)\n", in_ntoa(iph->daddr));
7014 @@ -606,6 +628,7 @@
7015         skb->sk = NULL;
7016         kfree_skb(skb, FREE_WRITE);
7017         return(0);
7018 +#endif
7019    }
7020  
7021    /* Point into the IP datagram, just past the header. */
7022 @@ -646,7 +669,7 @@
7023         * based on the datagram protocol.  We should really
7024         * check the protocol handler's return values here...
7025         */
7026 -       ipprot->handler(skb2, dev, &opt, iph->daddr,
7027 +       ipprot->handler(skb2, dev, opts_p ? &opt : 0, iph->daddr,
7028                         (ntohs(iph->tot_len) - (iph->ihl * 4)),
7029                         iph->saddr, 0, ipprot);
7030  
7031 diff -u --recursive --new-file pl12/linux/net/inet/lance.c linux/net/inet/lance.c
7032 --- pl12/linux/net/inet/lance.c Fri Aug 13 04:56:54 1993
7033 +++ linux/net/inet/lance.c      Fri Sep  3 22:50:10 1993
7034 @@ -7,13 +7,14 @@
7035      distributed according to the terms of the GNU Public License,
7036      incorporated herein by reference.
7037  
7038 -    This driver should work with the Allied Telesis 1500, and NE2100 clones.
7039 +    This driver is for the Allied Telesis AT1500, and should work with
7040 +    NE2100 clones.
7041  
7042      The author may be reached as becker@super.org or
7043      C/O Supercomputing Research Ctr., 17100 Science Dr., Bowie MD 20715
7044  */
7045  
7046 -static char *version = "lance.c:v0.08 8/12/93 becker@super.org\n";
7047 +static char *version = "lance.c:v0.12 9/3/93 becker@super.org\n";
7048  
7049  #include <linux/config.h>
7050  #include <linux/kernel.h>
7051 @@ -22,6 +23,7 @@
7052  /*#include <linux/interrupt.h>*/
7053  #include <linux/ptrace.h>
7054  #include <linux/errno.h>
7055 +#include <linux/ioport.h>
7056  #include <asm/io.h>
7057  #include <asm/dma.h>
7058  /*#include <asm/system.h>*/
7059 @@ -32,12 +34,12 @@
7060  #include "skbuff.h"
7061  #include "arp.h"
7062  
7063 +#ifndef HAVE_AUTOIRQ
7064  /* From auto_irq.c, should be in a *.h file. */
7065  extern void autoirq_setup(int waittime);
7066  extern int autoirq_report(int waittime);
7067  extern struct device *irq2dev_map[16];
7068 -
7069 -extern void printk_stats(struct enet_statistics *stats);
7070 +#endif
7071  
7072  #ifdef LANCE_DEBUG
7073  int lance_debug = LANCE_DEBUG;
7074 @@ -60,6 +62,7 @@
7075  #define LANCE_ADDR 0x12
7076  #define LANCE_RESET 0x14
7077  #define LANCE_BUS_IF 0x16
7078 +#define LANCE_TOTAL_SIZE 0x18
7079  
7080  /* The LANCE Rx and Tx ring descriptors. */
7081  struct lance_rx_head {
7082 @@ -96,14 +99,17 @@
7083      int pad0, pad1;            /* Used for alignment */
7084  };
7085  
7086 -/* This is a temporary solution to the lack of a ethercard low-memory
7087 -   allocation scheme.  We need it for bus-master or DMA ethercards if
7088 -   they are to work >16M memory systems.  */
7089 +/* We need a ethercard low-memory allocation scheme for for bus-master or
7090 +   DMA ethercards if they are to work >16M memory systems. This is a
7091 +   temporary solution to the lack of one, but it limits us to a single
7092 +   AT1500 and <16M. Bummer. */
7093 +
7094  #define PKT_BUF_SZ     1550
7095  static char rx_buffs[PKT_BUF_SZ][RING_SIZE];
7096  
7097 -int at1500_init(int ioaddr, struct device *dev);
7098 +int at1500_probe1(struct device *dev);
7099  static int lance_open(struct device *dev);
7100 +static void lance_init_ring(struct device *dev);
7101  static int lance_start_xmit(struct sk_buff *skb, struct device *dev);
7102  static int lance_rx(struct device *dev);
7103  static void lance_interrupt(int reg_ptr);
7104 @@ -119,33 +125,52 @@
7105  int at1500_probe(struct device *dev)
7106  {
7107      int *port, ports[] = {0x300, 0x320, 0x340, 0x360, 0};
7108 -    int ioaddr = dev->base_addr;
7109 -
7110 -    if (ioaddr > 0x100)
7111 -       return ! at1500_init(ioaddr, dev);
7112 +    int base_addr = dev->base_addr;
7113  
7114 +    if (base_addr < 0)
7115 +       return ENXIO;           /* Don't probe at all. */
7116 +    if (base_addr > 0x100)     /* Check a single specified location. */
7117 +       return at1500_probe1(dev);
7118 +
7119 +    /* First probe for the ethercard ID, 0x57, and then look for a LANCE
7120 +       chip. */
7121 +    
7122      for (port = &ports[0]; *port; port++) {
7123 -       /* Probe for the Allied-Telesys vendor ID.  This will not detect
7124 -          other NE2100-like ethercards, which must use a hard-wired ioaddr.
7125 -          There must be a better way to detect a LANCE... */
7126 -       int ioaddr = *port;
7127 -       if (inb(ioaddr) != 0x00
7128 -           || inb(ioaddr+1) != 0x00
7129 -           || inb(ioaddr+2) != 0xF4)
7130 +       int probe_addr = *port;
7131 +       short temp;
7132 +
7133 +#ifdef HAVE_PORTRESERVE
7134 +       if (check_region(probe_addr, LANCE_TOTAL_SIZE))
7135 +           continue;
7136 +#endif
7137 +       if (inb(probe_addr + 14) != 0x57
7138 +           || inb(probe_addr + 15) != 0x57)
7139 +           continue;
7140 +
7141 +       /* Reset the LANCE. Un-Reset needed only for the real NE2100. */
7142 +       temp = inw(probe_addr+LANCE_RESET); /* Reset the LANCE */
7143 +       outw(temp, probe_addr+LANCE_RESET);     /* "Un-reset" */
7144 +       
7145 +       outw(0x0000, probe_addr+LANCE_ADDR); /* Switch to window 0 */
7146 +       if (inw(probe_addr+LANCE_DATA) != 0x0004)
7147             continue;
7148 -       if (at1500_init(ioaddr, dev))
7149 +       dev->base_addr = probe_addr;
7150 +       if (at1500_probe1(dev) == 0)
7151             return 0;
7152      }
7153 -    return 1;                  /* ENODEV would be more accurate. */
7154 +
7155 +    dev->base_addr = base_addr;
7156 +    return ENODEV;                     /* ENODEV would be more accurate. */
7157  }
7158  
7159  int
7160 -at1500_init(int ioaddr, struct device *dev)
7161 +at1500_probe1(struct device *dev)
7162  {
7163      struct lance_private *lp;
7164 +    short ioaddr = dev->base_addr;
7165 +
7166      int i;
7167  
7168 -    dev->base_addr = ioaddr;
7169      printk("%s: LANCE at %#3x, address", dev->name, ioaddr);
7170  
7171      /* There is a 16 byte station address PROM at the base address.
7172 @@ -163,12 +188,16 @@
7173  
7174      if ((int)dev->priv & 0xff000000  ||  (int) rx_buffs & 0xff000000) {
7175         printk(" disabled (buff %#x > 16M).\n", (int)rx_buffs);
7176 -       return 0;
7177 +       return -ENOMEM;
7178      }
7179  
7180      memset(dev->priv, 0, sizeof(struct lance_private));
7181      lp = (struct lance_private *)dev->priv;
7182  
7183 +    if ((int)(lp->rx_ring) & 0x07)
7184 +       printk("%s: LANCE Rx and Tx rings not on even boundary.\n",
7185 +              dev->name);
7186 +
7187      /* Un-Reset the LANCE, needed only for the NE2100. */
7188      outw(0, ioaddr+LANCE_RESET);
7189  
7190 @@ -199,11 +228,14 @@
7191             printk(", using IRQ %d.\n", dev->irq);
7192         else {
7193             printk(", failed to detect IRQ line.\n");
7194 -           return 0;
7195 +           return -EAGAIN;
7196         }
7197      } else
7198         printk(" assigned IRQ %d.\n", dev->irq);
7199  
7200 +    /* The DMA channel may be passed in on this parameter. */
7201 +    dev->dma = dev->mem_start & 0x07;
7202 +
7203  #ifndef NE2100                 /* The NE2100 might not understand */
7204      /* Turn on auto-select of media (10baseT or BNC) so that the user
7205         can watch the LEDs even if the board isn't opened. */
7206 @@ -211,9 +243,9 @@
7207      outw(0x0002, ioaddr+LANCE_BUS_IF);
7208  #endif
7209  
7210 -    if ((int)(lp->rx_ring) & 0x07)
7211 -       printk("%s: LANCE Rx and Tx rings not on even boundary.\n",
7212 -              dev->name);
7213 +#ifdef HAVE_PORTRESERVE
7214 +    snarf_region(ioaddr, LANCE_TOTAL_SIZE);
7215 +#endif
7216  
7217      if (lance_debug > 0)
7218         printk(version);
7219 @@ -225,7 +257,6 @@
7220      dev->get_stats = &lance_get_stats;
7221  
7222      dev->mem_start = 0;
7223 -    dev->rmem_end = 0x00ffffff;                /* Bogus, needed for dev_rint(). */
7224  
7225      /* Fill in the generic field of the device structure. */
7226      for (i = 0; i < DEV_NUMBUFFS; i++)
7227 @@ -253,7 +284,7 @@
7228      dev->pa_mask       = 0;
7229      dev->pa_alen       = sizeof(unsigned long);
7230  
7231 -    return ioaddr;
7232 +    return 0;
7233  }
7234  
7235  \f
7236 @@ -268,8 +299,7 @@
7237         return -EAGAIN;
7238      }
7239  
7240 -    if (lp->dma < 1)
7241 -       lp->dma = DEFAULT_DMA;
7242 +    lp->dma = dev->dma ? dev->dma : DEFAULT_DMA;
7243  
7244      if (request_dma(lp->dma)) {
7245         free_irq(dev->irq);
7246 @@ -287,7 +317,8 @@
7247      /* Un-Reset the LANCE, needed only for the NE2100. */
7248      outw(0, ioaddr+LANCE_RESET);
7249  
7250 -#ifndef NE2100                 /* The NE2100 might not understand */
7251 +#ifndef NE2100
7252 +    /* This is really 79C960-specific, NE2100 might not understand */
7253      /* Turn on auto-select of media (10baseT or BNC). */
7254      outw(0x0002, ioaddr+LANCE_ADDR);
7255      outw(0x0002, ioaddr+LANCE_BUS_IF);
7256 @@ -298,23 +329,7 @@
7257                dev->name, dev->irq, lp->dma, lp->tx_ring, lp->rx_ring,
7258                &lp->init_block);
7259  
7260 -    lp->cur_rx = lp->cur_tx = 0;
7261 -    lp->dirty_rx = lp->dirty_tx = 0;
7262 -
7263 -    for (i = 0; i < RING_SIZE; i++) {
7264 -       lp->rx_ring[i].base = (int)rx_buffs | 0x80000000 + i*PKT_BUF_SZ;
7265 -       lp->rx_ring[i].buf_length = -PKT_BUF_SZ;
7266 -       lp->tx_ring[i].base = 0;
7267 -    }
7268 -
7269 -    lp->init_block.mode = 0x0000;
7270 -    for (i = 0; i < 6; i++)
7271 -       lp->init_block.phys_addr[i] = dev->dev_addr[i];
7272 -    lp->init_block.filter[0] = 0x00000000;
7273 -    lp->init_block.filter[1] = 0x00000000;
7274 -    lp->init_block.rx_ring = (int)lp->rx_ring | RING_LEN_BITS;
7275 -    lp->init_block.tx_ring = (int)lp->tx_ring | RING_LEN_BITS;
7276 -
7277 +    lance_init_ring(dev);
7278      /* Re-initialize the LANCE, and start it when done. */
7279      outw(0x0001, ioaddr+LANCE_ADDR);
7280      outw((short) &lp->init_block, ioaddr+LANCE_DATA);
7281 @@ -343,6 +358,31 @@
7282      return 0;                  /* Always succeed */
7283  }
7284  
7285 +/* Initialize the LANCE Rx and Tx rings. */
7286 +static void
7287 +lance_init_ring(struct device *dev)
7288 +{
7289 +    struct lance_private *lp = (struct lance_private *)dev->priv;
7290 +    int i;
7291 +
7292 +    lp->cur_rx = lp->cur_tx = 0;
7293 +    lp->dirty_rx = lp->dirty_tx = 0;
7294 +
7295 +    for (i = 0; i < RING_SIZE; i++) {
7296 +       lp->rx_ring[i].base = (int)rx_buffs | 0x80000000 + i*PKT_BUF_SZ;
7297 +       lp->rx_ring[i].buf_length = -PKT_BUF_SZ;
7298 +       lp->tx_ring[i].base = 0;
7299 +    }
7300 +
7301 +    lp->init_block.mode = 0x0000;
7302 +    for (i = 0; i < 6; i++)
7303 +       lp->init_block.phys_addr[i] = dev->dev_addr[i];
7304 +    lp->init_block.filter[0] = 0x00000000;
7305 +    lp->init_block.filter[1] = 0x00000000;
7306 +    lp->init_block.rx_ring = (int)lp->rx_ring | RING_LEN_BITS;
7307 +    lp->init_block.tx_ring = (int)lp->tx_ring | RING_LEN_BITS;
7308 +}
7309 +
7310  static int
7311  lance_start_xmit(struct sk_buff *skb, struct device *dev)
7312  {
7313 @@ -352,18 +392,16 @@
7314      /* Transmitter timeout, serious problems. */
7315      if (dev->tbusy) {
7316         int tickssofar = jiffies - dev->trans_start;
7317 -       int entry = lp->cur_tx++;
7318         if (tickssofar < 5)
7319             return 1;
7320         outw(0, ioaddr+LANCE_ADDR);
7321 -       printk("%s: transmit timed out, status %4.4x.\n", dev->name,
7322 -              inw(ioaddr+LANCE_DATA));
7323 +       printk("%s: transmit timed out, status %4.4x, resetting.\n",
7324 +              dev->name, inw(ioaddr+LANCE_DATA));
7325  
7326 -       if (lp->tx_ring[(entry+1) & RING_MOD_MASK].base >= 0)
7327 -           dev->tbusy=0;
7328 -       else
7329 -           outw(0x00, ioaddr+LANCE_DATA),
7330 -           outw(0x43, ioaddr+LANCE_DATA);;
7331 +       lance_init_ring(dev);
7332 +       outw(0x43, ioaddr+LANCE_DATA);
7333 +
7334 +       dev->tbusy=0;
7335         dev->trans_start = jiffies;
7336  
7337         return 0;
7338 @@ -446,7 +484,7 @@
7339  lance_interrupt(int reg_ptr)
7340  {
7341      int irq = -(((struct pt_regs *)reg_ptr)->orig_eax+2);
7342 -    struct device *dev = irq2dev_map[irq];
7343 +    struct device *dev = (struct device *)(irq2dev_map[irq]);
7344      struct lance_private *lp;
7345      int csr0, ioaddr;
7346  
7347 @@ -510,6 +548,7 @@
7348                 kfree_skb (skb-1, FREE_WRITE);
7349             dirty_tx = ++lp->dirty_tx & RING_MOD_MASK;
7350         }
7351 +       /* mark_bh(INET_BH); */
7352      }
7353  
7354      /* Clear the interrupts we've handled. */
7355 @@ -531,21 +570,10 @@
7356      struct lance_private *lp = (struct lance_private *)dev->priv;
7357      int entry = lp->cur_rx & RING_MOD_MASK;
7358         
7359 -    /* Check to see if we own this entry. */
7360 +    /* If we own the next entry, it's a new packet. Send it up. */
7361      while (lp->rx_ring[entry].base >= 0) {
7362         int status = lp->rx_ring[entry].base >> 24;
7363 -       if (lance_debug > 5) {
7364 -           unsigned char *pkt =
7365 -               (unsigned char *)(lp->rx_ring[entry].base & 0x00ffffff);
7366 -           printk("%s: Rx packet at ring entry %d, len %d status %2.2x.\n",
7367 -                  dev->name, entry, lp->rx_ring[entry].msg_length,
7368 -                  lp->rx_ring[entry].base >> 24);
7369 -           printk("%s:  Rx %2.2x %2.2x %2.2x ... %2.2x  %2.2x %2.2x %2.2x...%2.2x len %2.2x %2.2x  %2.2x %2.2x.\n",
7370 -                  dev->name, pkt[0], pkt[1], pkt[2], pkt[5], pkt[6],
7371 -                  pkt[7], pkt[8], pkt[11], pkt[12], pkt[13],
7372 -                  pkt[14], pkt[15]);
7373 -       }
7374 -       /* If so, copy it to the upper layers. */
7375 +
7376         if (status & 0x40) {    /* There was an error. */
7377             lp->stats.rx_errors++;
7378             if (status & 0x20) lp->stats.rx_frame_errors++;
7379 @@ -553,12 +581,33 @@
7380             if (status & 0x08) lp->stats.rx_crc_errors++;
7381             if (status & 0x04) lp->stats.rx_fifo_errors++;
7382         } else {
7383 -           if (dev_rint((unsigned char *)(lp->rx_ring[entry].base
7384 -                                          & 0x00ffffff),
7385 -                        lp->rx_ring[entry].msg_length, 0, dev)) {
7386 +           /* Malloc up new buffer, compatible with net-2e. */
7387 +           short pkt_len = lp->rx_ring[entry].msg_length;
7388 +           int sksize = sizeof(struct sk_buff) + pkt_len;
7389 +           struct sk_buff *skb;
7390 +           skb = (struct sk_buff *) kmalloc(sksize, GFP_ATOMIC);
7391 +           if (skb == NULL) {
7392 +               printk("%s: Memory squeeze, deferring packet.\n", dev->name);
7393 +               lp->stats.rx_dropped++; /* Really, deferred. */
7394 +               break;
7395 +           }
7396 +           skb->mem_len = sksize;
7397 +           skb->mem_addr = skb;
7398 +           skb->len = pkt_len;
7399 +           skb->dev = dev;
7400 +           memcpy((unsigned char *) (skb + 1),
7401 +                  (unsigned char *)(lp->rx_ring[entry].base & 0x00ffffff),
7402 +                  pkt_len);
7403 +#ifdef HAVE_NETIF_RX
7404 +           netif_rx(skb);
7405 +#else
7406 +           skb->lock = 0;
7407 +           if (dev_rint((unsigned char*)skb, pkt_len, IN_SKBUFF, dev) != 0) {
7408 +               kfree_s(skb, sksize);
7409                 lp->stats.rx_dropped++;
7410                 break;
7411             }
7412 +#endif
7413             lp->stats.rx_packets++;
7414         }
7415  
7416 @@ -565,6 +614,10 @@
7417         lp->rx_ring[entry].base |= 0x80000000;
7418         entry = (entry+1) & RING_MOD_MASK;
7419      }
7420 +
7421 +    /* We should check that at least two ring entries are free.  If not,
7422 +       we should free one and mark stats->rx_dropped++. */
7423 +
7424      lp->cur_rx = entry;
7425  
7426      return 0;
7427 @@ -587,10 +640,6 @@
7428      if (lance_debug > 1)
7429         printk("%s: Shutting down ethercard, status was %2.2x.\n",
7430                dev->name, inw(ioaddr+LANCE_DATA));
7431 -#ifdef PRINTK_STATS
7432 -    if (lance_debug > 2)
7433 -       printk_stats(&lp->stats);
7434 -#endif
7435  
7436      /* We stop the LANCE here -- it occasionally polls
7437         memory if we don't. */
7438 diff -u --recursive --new-file pl12/linux/net/inet/loopback.c linux/net/inet/loopback.c
7439 --- pl12/linux/net/inet/loopback.c      Sat Jul 31 15:42:22 1993
7440 +++ linux/net/inet/loopback.c   Fri Aug 20 17:58:22 1993
7441 @@ -5,10 +5,11 @@
7442   *
7443   *             Pseudo-driver for the loopback interface.
7444   *
7445 - * Version:    @(#)loopback.c  1.0.4   05/25/93
7446 + * Version:    @(#)loopback.c  1.0.4b  08/16/93
7447   *
7448   * Authors:    Ross Biro, <bir7@leland.Stanford.Edu>
7449   *             Fred N. van Kempen, <waltje@uWalt.NL.Mugnet.ORG>
7450 + *             Donald Becker, <becker@super.org>
7451   *
7452   *             This program is free software; you can redistribute it and/or
7453   *             modify it under the terms of the GNU General Public License
7454 @@ -30,6 +31,7 @@
7455  #include <linux/errno.h>
7456  #include <linux/fcntl.h>
7457  #include <linux/in.h>
7458 +#include <linux/if_ether.h>    /* For the statistics structure. */
7459  #include "inet.h"
7460  #include "dev.h"
7461  #include "eth.h"
7462 @@ -44,6 +46,7 @@
7463  static int
7464  loopback_xmit(struct sk_buff *skb, struct device *dev)
7465  {
7466 +  struct enet_statistics *stats = (struct enet_statistics *)dev->priv;
7467    int done;
7468  
7469    DPRINTF((DBG_LOOPB, "loopback_xmit(dev=%X, skb=%X)\n", dev, skb));
7470 @@ -52,17 +55,27 @@
7471    cli();
7472    if (dev->tbusy != 0) {
7473         sti();
7474 +       stats->tx_errors++;
7475         return(1);
7476    }
7477    dev->tbusy = 1;
7478    sti();
7479  
7480 -  done = dev_rint((unsigned char *)(skb+1), skb->len, 0, dev);
7481 -  if (skb->free) kfree_skb(skb, FREE_WRITE);
7482 +  skb->lock = 0;
7483  
7484 -  while (done != 1) {
7485 -       done = dev_rint(NULL, 0, 0, dev);
7486 -  }
7487 +  stats->tx_packets++;
7488 +
7489 +  /* Copy the packet only if it isn't marked as free. */
7490 +
7491 +  done = dev_rint((unsigned char *)(skb->free ? skb : skb + 1), skb->len,
7492 +                 skb->free ? IN_SKBUFF : 0, dev);
7493 +
7494 +  if (done != 0)
7495 +      stats->rx_errors++;
7496 +  else
7497 +      stats->rx_packets++;
7498 +
7499 +
7500    dev->tbusy = 0;
7501  
7502  #if 1
7503 @@ -83,6 +96,11 @@
7504    return(0);
7505  }
7506  
7507 +static struct enet_statistics *
7508 +get_stats(struct device *dev)
7509 +{
7510 +    return (struct enet_statistics *)dev->priv;
7511 +}
7512  
7513  /* Initialize the rest of the LOOPBACK device. */
7514  int
7515 @@ -118,6 +136,9 @@
7516    dev->pa_brdaddr      = in_aton("127.255.255.255");
7517    dev->pa_mask         = in_aton("255.0.0.0");
7518    dev->pa_alen         = sizeof(unsigned long);
7519 -
7520 +  dev->priv = kmalloc(sizeof(struct enet_statistics), GFP_KERNEL);
7521 +  memset(dev->priv, 0, sizeof(struct enet_statistics));
7522 +  dev->get_stats = get_stats;
7523 +  
7524    return(0);
7525  };
7526 diff -u --recursive --new-file pl12/linux/net/inet/ne.c linux/net/inet/ne.c
7527 --- pl12/linux/net/inet/ne.c    Fri Aug 13 05:57:28 1993
7528 +++ linux/net/inet/ne.c Mon Aug 30 23:35:36 1993
7529 @@ -17,11 +17,12 @@
7530  /* Routines for the NatSemi-based designs (NE[12]000). */
7531  
7532  static char *version =
7533 -    "ne.c:v0.99-12B 8/12/93 Donald Becker (becker@super.org)\n";
7534 +    "ne.c:v0.99-13 8/30/93 Donald Becker (becker@super.org)\n";
7535  
7536  #include <linux/config.h>
7537  #include <linux/kernel.h>
7538  #include <linux/sched.h>
7539 +#include <linux/errno.h>
7540  #include <asm/system.h>
7541  #include <asm/io.h>
7542  #ifndef port_read
7543 @@ -41,7 +42,7 @@
7544  #define NESM_START_PG  0x40    /* First page of TX buffer */
7545  #define NESM_STOP_PG   0x80    /* Last page +1 of RX ring */
7546  
7547 -int neprobe(int ioaddr, struct device *dev);
7548 +int ne_probe(struct device *dev);
7549  static int neprobe1(int ioaddr, struct device *dev, int verbose);
7550  
7551  static void ne_reset_8390(struct device *dev);
7552 @@ -72,17 +73,28 @@
7553         E2010    starts at 0x100 and ends at 0x4000.
7554         E2010-x starts at 0x100 and ends at 0xffff.  */
7555  
7556 -int neprobe(int ioaddr,  struct device *dev)
7557 +int ne_probe(struct device *dev)
7558  {
7559      int *port, ports[] = {0x300, 0x280, 0x320, 0x340, 0x360, 0};
7560 +    short ioaddr = dev->base_addr;
7561  
7562 +    if (ioaddr < 0)
7563 +       return ENXIO;           /* Don't probe at all. */
7564      if (ioaddr > 0x100)
7565 -       return neprobe1(ioaddr, dev, 1);
7566 +       return ! neprobe1(ioaddr, dev, 1);
7567  
7568 -    for (port = &ports[0]; *port; port++)
7569 -       if (inb_p(*port) != 0xff && neprobe1(*port, dev, 0))
7570 -           return dev->base_addr = *port;
7571 -    return 0;
7572 +    for (port = &ports[0]; *port; port++) {
7573 +#ifdef HAVE_PORTRESERVE
7574 +       if (check_region(*port, 32))
7575 +           continue;
7576 +#endif
7577 +       if (inb_p(*port) != 0xff && neprobe1(*port, dev, 0)) {
7578 +           dev->base_addr = *port;
7579 +           return 0;
7580 +       }
7581 +    }
7582 +    dev->base_addr = ioaddr;
7583 +    return ENODEV;
7584  }
7585  
7586  static int neprobe1(int ioaddr, struct device *dev, int verbose)
7587 @@ -216,12 +228,15 @@
7588         }
7589      }
7590  
7591 -    printk("\n%s: %s found at %#x, using IRQ %d.\n",
7592 -          dev->name, name, ioaddr, dev->irq);
7593 -
7594      dev->base_addr = ioaddr;
7595  
7596 +#ifdef HAVE_PORTRESERVE
7597 +    snarf_region(ioaddr, 32);
7598 +#endif
7599 +
7600      ethdev_init(dev);
7601 +    printk("\n%s: %s found at %#x, using IRQ %d.\n",
7602 +          dev->name, name, ioaddr, dev->irq);
7603  
7604      if (ei_debug > 0)
7605         printk(version);
7606 diff -u --recursive --new-file pl12/linux/net/inet/route.c linux/net/inet/route.c
7607 --- pl12/linux/net/inet/route.c Sat Aug  7 18:36:52 1993
7608 +++ linux/net/inet/route.c      Fri Aug 20 01:18:19 1993
7609 @@ -219,8 +219,10 @@
7610         dev = dev_check(((struct sockaddr_in *) &r->rt_dst)->sin_addr.s_addr);
7611    else
7612         if ((rt = rt_route(((struct sockaddr_in *) &r->rt_gateway)->sin_addr.
7613 -           s_addr,NULL))) dev = rt->rt_dev;
7614 -       else dev = NULL;
7615 +                          s_addr,NULL)))
7616 +           dev = rt->rt_dev;
7617 +       else
7618 +           dev = NULL;
7619  
7620    DPRINTF((DBG_RT, "RT: dev for %s gw ",
7621         in_ntoa((*(struct sockaddr_in *)&r->rt_dst).sin_addr.s_addr)));
7622 @@ -258,12 +260,14 @@
7623  
7624    pos = buffer;
7625  
7626 -  pos += sprintf(pos, "Iface\tDestination\tGateway \tFlags\tRefCnt\tUse\n");
7627 +  pos += sprintf(pos,
7628 +                "Iface\tDestination\tGateway \tFlags\tRefCnt\tUse\tMetric\n");
7629    
7630 +  /* This isn't quite right -- r->rt_dst is a struct! */
7631    for (r = rt_base; r != NULL; r = r->rt_next) {
7632 -        pos += sprintf(pos, "%s\t%08X\t%08X\t%02X\t%d\t%d\n",
7633 +        pos += sprintf(pos, "%s\t%08X\t%08X\t%02X\t%d\t%d\t%d\n",
7634                 r->rt_dev->name, r->rt_dst, r->rt_gateway,
7635 -               r->rt_flags, r->rt_refcnt, r->rt_use);
7636 +               r->rt_flags, r->rt_refcnt, r->rt_use, r->rt_metric);
7637    }
7638    return(pos - buffer);
7639  }
7640 @@ -317,7 +321,9 @@
7641  int
7642  rt_ioctl(unsigned int cmd, void *arg)
7643  {
7644 +  struct device *dev;
7645    struct rtentry rt;
7646 +  char namebuf[32];
7647    int ret;
7648  
7649    switch(cmd) {
7650 @@ -325,16 +331,17 @@
7651                 ret = dbg_ioctl(arg, DBG_RT);
7652                 break;
7653         case SIOCADDRT:
7654 -               if (!suser()) return(-EPERM);
7655 -               verify_area(VERIFY_WRITE, arg, sizeof(struct rtentry));
7656 -               memcpy_fromfs(&rt, arg, sizeof(struct rtentry));
7657 -               ret = rt_new(&rt);
7658 -               break;
7659         case SIOCDELRT:
7660                 if (!suser()) return(-EPERM);
7661                 verify_area(VERIFY_WRITE, arg, sizeof(struct rtentry));
7662                 memcpy_fromfs(&rt, arg, sizeof(struct rtentry));
7663 -               ret = rt_kill(&rt);
7664 +               if (rt.rt_dev) {
7665 +                   verify_area(VERIFY_WRITE, rt.rt_dev, sizeof namebuf);
7666 +                   memcpy_fromfs(&namebuf, rt.rt_dev, sizeof namebuf);
7667 +                   dev = dev_get(namebuf);
7668 +                   rt.rt_dev = dev;
7669 +               }
7670 +               ret = (cmd == SIOCDELRT) ? rt_kill(&rt) : rt_new(&rt);
7671                 break;
7672         default:
7673                 ret = -EINVAL;
7674 diff -u --recursive --new-file pl12/linux/net/inet/slip.c linux/net/inet/slip.c
7675 --- pl12/linux/net/inet/slip.c  Sat Jul 31 15:42:22 1993
7676 +++ linux/net/inet/slip.c       Thu Aug 19 09:46:23 1993
7677 @@ -688,7 +688,7 @@
7678    if (already++ == 0) {
7679         printk("SLIP: version %s (%d channels): ",
7680                                 SLIP_VERSION, SL_NRUNIT);
7681 -
7682 +       printk("CSLIP code copyright 1989 Regents of the University of California\n");
7683         /* Fill in our LDISC request block. */
7684         sl_ldisc.flags  = 0;
7685         sl_ldisc.open   = slip_open;
7686 diff -u --recursive --new-file pl12/linux/net/inet/sock.c linux/net/inet/sock.c
7687 --- pl12/linux/net/inet/sock.c  Sat Jul 31 15:42:22 1993
7688 +++ linux/net/inet/sock.c       Wed Aug 18 19:19:51 1993
7689 @@ -967,6 +967,8 @@
7690                 sti();
7691                 return(-EADDRINUSE);
7692         }
7693 +       if (sk2->num != snum) continue;         /* more than one */
7694 +       if (sk2->saddr != sk->saddr) continue;  /* socket per slot ! -FB */
7695         if (!sk2->reuse) {
7696                 sti();
7697                 return(-EADDRINUSE);
7698 diff -u --recursive --new-file pl12/linux/net/inet/tcp.c linux/net/inet/tcp.c
7699 --- pl12/linux/net/inet/tcp.c   Wed Aug 11 20:41:15 1993
7700 +++ linux/net/inet/tcp.c        Wed Aug 18 19:20:37 1993
7701 @@ -1434,6 +1434,7 @@
7702    t1->source = th->dest;
7703    t1->seq = th->ack_seq; /* add one so it will be in the right range */
7704    t1->rst = 1;
7705 +  t1->ack_seq = ntohl(ntohl(th->seq)+1); /* send correct ack -FB */
7706    t1->window = 0;              /* should be set to 0 -FB */
7707    t1->ack = 0;
7708    t1->syn = 0;
7709 diff -u --recursive --new-file pl12/linux/net/inet/wd.c linux/net/inet/wd.c
7710 --- pl12/linux/net/inet/wd.c    Fri Aug 13 04:24:28 1993
7711 +++ linux/net/inet/wd.c Mon Aug 30 23:40:32 1993
7712 @@ -15,11 +15,12 @@
7713  */
7714  
7715  static char *version =
7716 -    "wd.c:v0.99-12 8/12/93 Donald Becker (becker@super.org)\n";
7717 +    "wd.c:v0.99-13 8/30/93 Donald Becker (becker@super.org)\n";
7718  
7719  #include <linux/config.h>
7720  #include <linux/kernel.h>
7721  #include <linux/sched.h>
7722 +#include <linux/errno.h>
7723  #include <asm/io.h>
7724  #include <asm/system.h>
7725  #include <memory.h>
7726 @@ -59,19 +60,28 @@
7727      The wdprobe1() routine initializes the card and fills the
7728      station address field. */
7729  
7730 -int wdprobe(int ioaddr,  struct device *dev)
7731 +int wd_probe(struct device *dev)
7732  {
7733      int *port, ports[] = {0x300, 0x280, 0x380, 0x240, 0};
7734 +    short ioaddr = dev->base_addr;
7735  
7736 +    if (ioaddr < 0)
7737 +       return ENXIO;           /* Don't probe at all. */
7738      if (ioaddr > 0x100)
7739 -       return wdprobe1(ioaddr, dev);
7740 +       return ! wdprobe1(ioaddr, dev);
7741  
7742 -    for (port = &ports[0]; *port; port++)
7743 +    for (port = &ports[0]; *port; port++) {
7744 +#ifdef HAVE_PORTRESERVE
7745 +       if (check_region(*port, 32))
7746 +           continue;
7747 +#endif
7748         if (inb(*port + 8) != 0xff
7749             && inb(*port + 9) != 0xff /* Extra check to avoid soundcard. */
7750             && wdprobe1(*port, dev))
7751 -           return *port;
7752 -    return 0;
7753 +           return 0;
7754 +    }
7755 +    dev->base_addr = ioaddr;
7756 +    return ENODEV;
7757  }
7758  
7759  int wdprobe1(int ioaddr, struct device *dev)
7760 @@ -93,7 +103,7 @@
7761        printk(" %2.2X", station_addr[i] = inb(ioaddr + 8 + i));
7762  
7763    /* The following PureData probe code was contributed by
7764 -     Mike Jagdis <jaggy@purplet.demon.co.uk>. Puredata seem to do software
7765 +     Mike Jagdis <jaggy@purplet.demon.co.uk>. Puredata does software
7766       configuration differently from others so we have to check for them.
7767       This detects an 8 bit, 16 bit or dumb (Toshiba, jumpered) card.
7768       */
7769 @@ -192,6 +202,9 @@
7770    }
7771  
7772    /* OK, were are certain this is going to work.  Setup the device. */
7773 +#ifdef HAVE_PORTRESERVE
7774 +  snarf_region(ioaddr, 32);
7775 +#endif
7776    ethdev_init(dev);
7777  
7778    ei_status.name = model_name;
7779 @@ -231,8 +244,9 @@
7780    ei_status.reg5 = ((dev->mem_start>>19) & 0x1f) | NIC16;
7781  
7782    if (ei_status.word16)
7783 -      outb(ISA16 | ei_status.reg5, ioaddr+WD_CMDREG5);
7784 +      outb(ei_status.reg5, ioaddr+WD_CMDREG5);
7785    outb(ei_status.reg0, ioaddr); /* WD_CMDREG */
7786 +
7787    return ei_open(dev);
7788  }
7789  
7790 @@ -273,7 +287,8 @@
7791  }
7792  
7793  /* Block input and output are easy on shared memory ethercards, and trivial
7794 -   on the Western digital card where there is no choice of how to do it. */
7795 +   on the Western digital card where there is no choice of how to do it.
7796 +   The only complication is if the ring buffer wraps. */
7797  
7798  static int
7799  wd_block_input(struct device *dev, int count, char *buf, int ring_offset)
7800 @@ -281,7 +296,7 @@
7801      void *xfer_start = (void *)(dev->mem_start + ring_offset
7802                                 - (WD_START_PG<<8));
7803  
7804 -    /* This mapout won't be necessary when wd_close_card is called. */
7805 +    /* This mapout isn't necessary if wd_close_card is called. */
7806  #if !defined(WD_no_mapout)
7807      int wd_cmdreg = dev->base_addr - WD_NIC_OFFSET; /* WD_CMDREG */
7808  
7809 @@ -299,12 +314,6 @@
7810         return dev->rmem_start + count;
7811      }
7812      memcpy(buf, xfer_start, count);
7813 -    if (ei_debug > 4) {
7814 -       unsigned short *board = (unsigned short *) xfer_start;
7815 -       printk("%s: wd8013 block_input(cnt=%d offset=%3x addr=%#x) = %2x %2x %2x...\n",
7816 -              dev->name, count, ring_offset, xfer_start,
7817 -              board[-1], board[0], board[1]);
7818 -    }
7819  
7820  #if !defined(WD_no_mapout)
7821      /* Turn off 16 bit access so that reboot works. */
7822 @@ -314,8 +323,6 @@
7823      return ring_offset + count;
7824  }
7825  
7826 -/* This could only be outputting to the transmit buffer.  The
7827 -   ping-pong transmit setup doesn't work with this yet. */
7828  static void
7829  wd_block_output(struct device *dev, int count, const unsigned char *buf,
7830                 int start_page)
7831 @@ -332,9 +339,6 @@
7832  #endif
7833  
7834      memcpy(shmem, buf, count);
7835 -    if (ei_debug > 4)
7836 -       printk("%s: wd80*3 block_output(addr=%#x cnt=%d) -> %2x=%2x %2x=%2x %d...\n",
7837 -              shmem, count, shmem[23], buf[23], shmem[24], buf[24], memcmp(shmem,buf,count));
7838  
7839  #if !defined(WD_no_mapout)
7840      /* Turn off 16 bit access so that reboot works. */
7841 diff -u --recursive --new-file pl12/linux/net/socket.c linux/net/socket.c
7842 --- pl12/linux/net/socket.c     Wed Jul  7 10:39:58 1993
7843 +++ linux/net/socket.c  Sat Sep  4 02:45:52 1993
7844 @@ -806,7 +806,7 @@
7845   * we have this level of indirection. Not a lot of overhead, since more of
7846   * the work is done via read/write/select directly.
7847   */
7848 -extern "C" int
7849 +asmlinkage int
7850  sys_socketcall(int call, unsigned long *args)
7851  {
7852    switch(call) {
7853 diff -u --recursive --new-file pl12/linux/net/unix/sock.c linux/net/unix/sock.c
7854 --- pl12/linux/net/unix/sock.c  Mon Aug  9 18:02:33 1993
7855 +++ linux/net/unix/sock.c       Sat Sep  4 14:02:42 1993
7856 @@ -737,7 +737,7 @@
7857                 if (UN_BUF_AVAIL(upd) || peerupd)
7858                         put_fs_long(UN_BUF_AVAIL(upd),(unsigned long *)arg);
7859                   else
7860 -                       put_fs_long(1,(unsigned long *)arg); /* read EOF */
7861 +                       put_fs_long(0,(unsigned long *)arg);
7862                 break;
7863         case TIOCOUTQ:
7864                 if (sock->flags & SO_ACCEPTCON) return(-EINVAL);