home *** CD-ROM | disk | FTP | other *** search
/ DP Tool Club 31 / CDASC_31_1996_juillet_aout.iso / vrac / prept205.zip / PREPT205.GZ / PREPT205
Text File  |  1996-05-17  |  416KB  |  13,410 lines

  1. diff -u --recursive --new-file pre2.0.4/linux/CREDITS linux/CREDITS
  2. --- pre2.0.4/linux/CREDITS    Mon May 13 23:02:46 1996
  3. +++ linux/CREDITS    Thu May 16 17:16:52 1996
  4. @@ -221,7 +221,12 @@
  5.  
  6.  N: Juan Jose Ciarlante
  7.  E: jjciarla@raiz.uncu.edu.ar
  8. +E: juanjo@irriga.uncu.edu.ar
  9.  D: Network driver alias support
  10. +D: IP masq hashing and app modules
  11. +S: Las Cuevas 2385 - Bo Guemes
  12. +S: Las Heras, Mendoza CP 5539
  13. +S: Argentina
  14.  
  15.  N: Hamish Coleman
  16.  E: hamish@zot.apana.org.au
  17. @@ -436,6 +441,16 @@
  18.  S: Poltava 314023
  19.  S: Ukraine
  20.  
  21. +N: Paul Gortmaker
  22. +E: gpg109@rsphy1.anu.edu.au
  23. +W: http://rsphy1.anu.edu.au/~gpg109
  24. +D: Real Time Clock driver author.
  25. +D: 8390 net driver hacker (ne2000, wd8013, smc-ultra, 3c503, etc.) 
  26. +D: Ethernet-HowTo and BootPrompt-HowTo author.
  27. +D: Added many new CONFIG options (modules, ramdisk, generic-serial, etc.)
  28. +D: Implemented 1st "official" kernel thread (moved user bdflush to kflushd)
  29. +D: Various other random hacks, patches and utilities.
  30. +
  31.  N: John E. Gotts
  32.  E: jgotts@engin.umich.edu
  33.  D: kernel hacker
  34. @@ -472,6 +487,14 @@
  35.  S: Atlanta, Georgia 30332
  36.  S: USA
  37.  
  38. +N: Angelo Haritsis
  39. +E: ah@doc.ic.ac.uk
  40. +D: kernel patches (serial, watchdog)
  41. +D: xringd, vuzkern, greekXfonts
  42. +S: 58 Henfield Close
  43. +S: London N19 3UL
  44. +S: United Kingdom
  45. +
  46.  N: Kai Harrekilde-Petersen
  47.  E: khp@dolphinics.no
  48.  W: http://www.pip.dknet.dk/~pip93
  49. @@ -1048,6 +1071,13 @@
  50.  E: rubini@ipvvis.unipv.it
  51.  D: the gpm mouse server and kernel support for it
  52.  
  53. +N: Thomas Sailer
  54. +E: sailer@ife.ee.ethz.ch
  55. +D: Baycom radio modem driver
  56. +S: Weinbergstrasse 76
  57. +S: 8408 Winterthur
  58. +S: Switzerland
  59. +
  60.  N: Robert Sanders
  61.  E: gt8134b@prism.gatech.edu
  62.  D: Dosemu
  63. @@ -1156,13 +1186,14 @@
  64.  S: Canada M2N 2Z1
  65.  
  66.  N: Tommy Thorn
  67. -E: Tommy.Thorn@daimi.aau.dk
  68. +E: Tommy.Thorn@irisa.fr
  69. +W: http://www.irisa.fr/prive/thorn/index.html
  70. +P: 512/B4AFC909 BC BF 6D B1 52 26 1E D6  E3 2F A3 24 2A 84 FE 21
  71.  D: Device driver hacker (aha1542 & plip)
  72. -S: Aarhus University
  73. -S: Computer Science Department
  74. -S: Ny Munkegade 116
  75. -S: DK-8000 Aarhus C
  76. -S: Denmark
  77. +S: IRISA
  78. +S: Universit=E9 de Rennes I
  79. +S: F-35042 Rennes Cedex
  80. +S: FRANCE
  81.  
  82.  N: Jon Tombs
  83.  E: jon@gtex02.us.es
  84. diff -u --recursive --new-file pre2.0.4/linux/Documentation/Changes linux/Documentation/Changes
  85. --- pre2.0.4/linux/Documentation/Changes    Wed May 15 11:01:14 1996
  86. +++ linux/Documentation/Changes    Wed May 15 09:09:00 1996
  87. @@ -26,6 +26,7 @@
  88.  - Linux C++ Library     2.7.1.4
  89.  - Termcap         2.0.8
  90.  - Procps         0.99a
  91. +- Kbd             0.91
  92.  - Gpm             1.06
  93.  - SysVinit         2.60
  94.  - Util-linux         2.5
  95. @@ -188,6 +189,14 @@
  96.  
  97.     Better yet, just get the latest official Linux termcap from
  98.  ftp://sunsite.unc.edu/pub/Linux/GCC/termcap-2.0.8.tar.gz
  99. +
  100. +   The console driver keeps track of the correspondence between character
  101. +codes and glyph bitmaps loaded into the character ROM of your video card.
  102. +Say
  103. +
  104. +   loadunimap def
  105. +
  106. +to get back to the default correspondence.
  107.  
  108.  Hdparm
  109.  ======
  110. diff -u --recursive --new-file pre2.0.4/linux/Documentation/Configure.help linux/Documentation/Configure.help
  111. --- pre2.0.4/linux/Documentation/Configure.help    Mon May 13 23:02:46 1996
  112. +++ linux/Documentation/Configure.help    Thu May 16 16:35:39 1996
  113. @@ -1666,6 +1666,18 @@
  114.    inserted in and removed from the running kernel whenever you want),
  115.    say M here and read Documentation/modules.txt.
  116.  
  117. +BAYCOM ser12 and par96 kiss emulation driver for AX.25
  118. +CONFIG_BAYCOM
  119. +  This is an experimental driver for Baycom style simple amateur radio
  120. +  modems that connect to either a serial interface or a parallel 
  121. +  interface. The driver supports the ser12 and par96 designs. To configure
  122. +  the driver, use the setbaycom utility available from
  123. +  http://www.ife.ee.ethz.ch/~sailer/ham/ham.html#lnxbay. For informations
  124. +  on the modems, see http://www.baycom.de.
  125. +  If you want to compile this as a module ( = code which can be
  126. +  inserted in and removed from the running kernel whenever you want),
  127. +  say M here and read Documentation/modules.txt. This is recommended.
  128. +
  129.  PLIP (parallel port) support
  130.  CONFIG_PLIP
  131.    PLIP (Parallel Line Internet Protocol) is used to create a mini
  132. @@ -2060,18 +2072,20 @@
  133.    Multiple-Ethernet-mini-HOWTO, available from
  134.    sunsite.unc.edu:/pub/Linux/docs/HOWTO/mini.
  135.  
  136. -FMV-181/182 support
  137. +FMV-181/182/183/184 support
  138.  CONFIG_FMV18X
  139. -  If you have a Fujitsu FMV-181/182 network (ethernet) card, say Y and
  140. -  read the Ethernet-HOWTO, available via ftp (user: anonymous) in
  141. -  sunsite.unc.edu:/pub/Linux/docs/HOWTO. This driver is also available
  142. -  as a module ( = code which can be inserted in and removed from the
  143. -  running kernel whenever you want). If you want to compile it as a
  144. -  module, say M here and read Documentation/modules.txt as well as
  145. +  If you have a Fujitsu FMV-181/182/183/184 network (ethernet) card,
  146. +  say Y and read the Ethernet-HOWTO, available via ftp (user: anonymous)
  147. +  in sunsite.unc.edu:/pub/Linux/docs/HOWTO. This driver is also
  148. +  available as a module ( = code which can be inserted in and removed
  149. +  from the running kernel whenever you want). If you want to compile it
  150. +  as a module, say M here and read Documentation/modules.txt as well as
  151.    Documentation/networking/net-modules.txt. If you plan to use more
  152.    than one network card under linux, read the
  153.    Multiple-Ethernet-mini-HOWTO, available from
  154. -  sunsite.unc.edu:/pub/Linux/docs/HOWTO/mini.
  155. +  sunsite.unc.edu:/pub/Linux/docs/HOWTO/mini. If you use FMV-183 or
  156. +  FMV-184 and it is not working, you may need to disable Plug & Play
  157. +  mode of the card.
  158.  
  159.  EtherExpressPro support
  160.  CONFIG_EEXPRESS_PRO
  161. diff -u --recursive --new-file pre2.0.4/linux/Documentation/cdrom/cdrom-standard.tex linux/Documentation/cdrom/cdrom-standard.tex
  162. --- pre2.0.4/linux/Documentation/cdrom/cdrom-standard.tex    Mon May 13 23:02:46 1996
  163. +++ linux/Documentation/cdrom/cdrom-standard.tex    Wed May 15 17:30:36 1996
  164. @@ -1,5 +1,5 @@
  165.  \documentclass{article}
  166. -\def\version{$Id: cdrom-standard.tex,v 0.5 1996/05/12 22:00:00 emoenke Exp $}
  167. +\def\version{$Id: cdrom-standard.tex,v 0.6 1996/05/14 15:42:39 david Exp david $}
  168.  
  169.  \evensidemargin=0pt
  170.  \oddsidemargin=0pt
  171. @@ -9,6 +9,7 @@
  172.  \def\linux{{\sc Linux}}
  173.  \def\cdrom{{\sc CDrom}}
  174.  \def\cdromc{{\tt cdrom.c}}
  175. +\def\cdromh{{\tt cdrom.h}}
  176.  \def\ucdrom{{\tt ucdrom.h}}
  177.  
  178.  \everymath{\it} \everydisplay{\it}
  179. @@ -35,7 +36,7 @@
  180.  hardware devices, but also to a certain divergence in behavior. Especially
  181.  for \cdrom\ devices, the way a particular drive reacts to a `standard'
  182.  $ioctl()$ call varies a lot from one brand to another; until today, the
  183. -\linux \cdrom\ driver writers kept away from wilderness by a good practice:
  184. +\linux\ \cdrom\ driver writers kept away from wilderness by a good practice:
  185.  to evolve a new driver by copying, understanding and changing an existing
  186.  one.
  187.  
  188. @@ -57,37 +58,36 @@
  189.  But history has delivered us \cdrom\ support for many different interfaces.
  190.  
  191.  Some of the \linux\ \cdrom\ driver writers look at the existing standard
  192. -which is expressed through <linux/cdrom.h> as to a rather wild set of
  193. +which is expressed through \cdromh\ as to a rather wild set of
  194.  commands and data formats and feel that any structure is lost, and from
  195.  this point of view, this documentation shall help to achieve a common
  196.  programming interface.
  197.   
  198. -Others - mainly those who used the already existing drivers not only as
  199. -a coding example, but also as a `user interface' reference during their
  200. -own development - have taken care that <linux/cdrom.h> reflects a
  201. -software interface to `user programs' which is unique between all drivers
  202. -as much as possible; these driver writers will continue to refine the
  203. -existing <linux/cdrom.h> where it seems necessary, and they tend to look
  204. -if any newly requested functionality isn't already there before they are
  205. -ready to define new structures. The sbpcd driver gives an example that
  206. -it is possible to let a robot arm play juke box - either with audio or
  207. -with data CDs -, and that it is possible to let the juke box work on
  208. -even if a disk has fallen upon the floor and the drive door has closed 
  209. -without having a disk inside; without any new software layer or any
  210. -structures which are not already present in <linux/cdrom.h>.
  211. -This `other' group of \linux\ \cdrom\ driver writers explicitely does
  212. -NOT support the idea to define an additional software layer between driver
  213. -and user program.
  214. -
  215. +Others---mainly those who used the already existing drivers not only
  216. +as a coding example, but also as a `user interface' reference during
  217. +their own development---have taken care that \cdromh\ reflects a
  218. +software interface to `user programs' which is unique between all
  219. +drivers as much as possible; these driver writers will continue to
  220. +refine the existing \cdromh\ where it seems necessary, and they tend
  221. +to look if any newly requested functionality isn't already there
  222. +before they are ready to define new structures. The sbpcd driver gives
  223. +an example that it is possible to let a robot arm play juke
  224. +box---either with audio or with data CDs---and that it is possible to
  225. +let the juke box work on even if a disk has fallen upon the floor and
  226. +the drive door has closed without having a disk inside; without any
  227. +new software layer or any structures which are not already present in
  228. +\cdromh.  This `other' group of \linux\ \cdrom\ driver writers
  229. +explicitely does {\em not\/} support the idea to define an additional
  230. +software layer between driver and user program.
  231.  
  232.  The following text reflects the opinion of the first mentioned \linux\ 
  233.  \cdrom\ driver writer group only; the other group (not only the `silent
  234.  majority') sees this text as a good base for a future documentation of the
  235.  existing common \linux\ \cdrom\ programming interface, as it is stated 
  236. -within <linux/cdrom.h>. Where <linux/cdrom.h> needs some external 
  237. -explanation, this text can give it if the reader is aware that - at least
  238. -at the moment - this text claims to be the proposal of something else than
  239. -<linux/cdrom.h>.
  240. +within \cdromh. Where \cdromh\ needs some external 
  241. +explanation, this text can give it if the reader is aware that---at least
  242. +at the moment---this text claims to be the proposal of something else than
  243. +\cdromh.
  244.  
  245.  
  246.  Apart from the somewhat unstructured interfacing with software, the
  247. @@ -139,8 +139,8 @@
  248.  \halign{$#$\ \hfil&$#$\ \hfil&$/*$ \rm# $*/$\hfil\cr
  249.  struct& file_operations\ cdrom_fops = \{\hidewidth\cr
  250.          &NULL,                  & lseek \cr
  251. -        &block_read,            & read - general\ block-dev\ read \cr
  252. -        &block_write,           & write - general block-dev write \cr
  253. +        &block_read,            & read---general\ block-dev\ read \cr
  254. +        &block_write,           & write---general block-dev write \cr
  255.          &NULL,                  & readdir \cr
  256.          &NULL,                  & select \cr
  257.          &cdrom_ioctl,           & ioctl \cr
  258. diff -u --recursive --new-file pre2.0.4/linux/Documentation/ioctl-number.txt linux/Documentation/ioctl-number.txt
  259. --- pre2.0.4/linux/Documentation/ioctl-number.txt    Sun May 12 10:16:05 1996
  260. +++ linux/Documentation/ioctl-number.txt    Thu May 16 16:35:39 1996
  261. @@ -63,9 +63,10 @@
  262.  0x09    linux/md.h
  263.  0x12    linux/fs.h
  264.  0x20    linux/cm206.h
  265. -0x22    linux/scc.h        conflict!
  266. +0x22    linux/scc.h        conflict! (version 2.01 of z8530drv)
  267.  0x22    scsi/sg.h        conflict!
  268.  'A'    linux/apm_bios.h
  269. +'B'    linux/baycom.h
  270.  'C'    linux/soundcard.h
  271.  'F'    linux/fb.h
  272.  'I'    linux/isdn.h
  273. @@ -82,6 +83,7 @@
  274.  'T'    asm/ioctls.h        conflict!
  275.  'V'    linux/vt.h
  276.  'Y'    linux/cyclades.h    codes in 0x004359NN
  277. +'Z'    linux/scc.h        version 2.2 of z8530drv
  278.  'a'    various, see http://lrcwww.epfl.ch/linux-atm/magic.html
  279.  'c'    linux/comstats.h
  280.  'f'    linux/ext2_fs.h
  281. diff -u --recursive --new-file pre2.0.4/linux/Documentation/locks.txt linux/Documentation/locks.txt
  282. --- pre2.0.4/linux/Documentation/locks.txt    Sun May  5 08:51:57 1996
  283. +++ linux/Documentation/locks.txt    Wed May 15 11:22:04 1996
  284. @@ -2,7 +2,7 @@
  285.  
  286.          Andy Walker <andy@lysaker.kvaerner.no>
  287.  
  288. -               15 April 1996
  289. +                15 May 1996
  290.  
  291.  
  292.  What's New?
  293. @@ -42,15 +42,23 @@
  294.  over time, or under a very heavy mail load, would eventually cause the kernel
  295.  to lock solid with deadlocked processes.
  296.  
  297. -I have chosen the rather cruel solution of returning an error when such a
  298. -deadlock would occur. I can't see any other way to handle this situation
  299. -gracefully. The other options are to maintain two entirely separate lists
  300. -for flock() and fcntl() locks, thus defeating any protection between the
  301. -two, or to free locks placed by one method when the same process later
  302. -tries to lock the same file by the other method. Neither option seems
  303. -satisfactory.
  304. +Disallow Mixed Locks
  305. +--------------------
  306. +I have chosen the rather cruel solution of disallowing mixed locking styles
  307. +on a given file at a given time. Attempts to lock a file with flock() when
  308. +fcntl() locks exist, or vice versa, return with an error status of EBUSY.
  309. +This seemed to be the only way to avoid all possible deadlock conditions,
  310. +as flock() locks do not strictly have one owner process and so can't be
  311. +checked for deadlocking in the usual manner.
  312. +
  313. +The process that created a lock with flock() might have forked multiple
  314. +children and exited. Previously the parent process would have been marked
  315. +as the owner of the lock, but deadlocks could just have easily occurred in
  316. +one or more of the children, which we would not have been able to identify
  317. +and avoid.
  318.  
  319.  Some programs may break (again, groan). In particular the aforementioned
  320.  sendmail may have problems running in 'newaliases' mode. It will no longer
  321.  deadlock though. Recompile sendmail to use flock() and your troubles will
  322.  be over.
  323. +
  324. diff -u --recursive --new-file pre2.0.4/linux/Documentation/magic-number.txt linux/Documentation/magic-number.txt
  325. --- pre2.0.4/linux/Documentation/magic-number.txt    Sun May 12 10:16:06 1996
  326. +++ linux/Documentation/magic-number.txt    Thu May 16 16:35:39 1996
  327. @@ -59,3 +59,5 @@
  328.  STL_BOARDMAGIC      0xa2267f52  stlbrd_t             include/linux/stallion.h
  329.  STL_PORTMAGIC       0x5a7182c9  stlport_t            include/linux/stallion.h
  330.  PCXX_MAGIC          0x5c6df104  struct channel       drivers/char/pcxx.h
  331. +BAYCOM_MAGIC        0x3105bac0  struct baycom_state  drivers/char/baycom.c
  332. +
  333. diff -u --recursive --new-file pre2.0.4/linux/Documentation/smp.ez linux/Documentation/smp.ez
  334. --- pre2.0.4/linux/Documentation/smp.ez    Fri Apr 12 15:51:45 1996
  335. +++ linux/Documentation/smp.ez    Thu Jan  1 02:00:00 1970
  336. @@ -1,413 +0,0 @@
  337. -\begindata{text,748928}
  338. -\textdsversion{12}
  339. -\template{default}
  340. -\center{\underline{\bigger{\bigger{\bigger{An Implementation Of 
  341. -Multiprocessor Linux
  342. -
  343. -}}}}}
  344. -\italic{
  345. -}\indent{\indent{This document describes the implementation of a simple SMP 
  346. -Linux kernel extension and how to use this to develop SMP Linux kernels for 
  347. -architectures other than the Intel MP v1.1 architecture for Pentium and 486 
  348. -processors.}\italic{
  349. -
  350. -}}\italic{
  351. -
  352. -
  353. -Alan Cox, 1995
  354. -
  355. -
  356. -The author wishes to thank Caldera Inc whose donation of an ASUS dual 
  357. -pentium board made this project possible, and Thomas Radke, whose initial 
  358. -work on multiprocessor Linux formed the backbone of this project.
  359. -
  360. -\begindata{bp,941568}
  361. -\enddata{bp,941568}
  362. -\view{bpv,941568,0,0,0}
  363. -}
  364. -\heading{Background: The Intel MP specification.
  365. -
  366. -}
  367. -    Most IBM PC style multiprocessor motherboards combine Intel 486 or Pentium 
  368. -processors and glue chipsets with a hardware/software specification. The 
  369. -specification places much of the onus for hard work on the chipset and 
  370. -hardware rather than the operating system.
  371. -
  372. -
  373. -    The Intel pentium processors have a wide variety of inbuilt facilities for 
  374. -supporting multiprocessing, including hardware cache coherency, built in 
  375. -interprocessor interrupt handling and a set of atomic test and set, 
  376. -exchange and similar operations. The cache coherency in particular makes the 
  377. -operating systems job far easier.
  378. -
  379. -
  380. -    The specification defines a detailed configuration structure in ROM that 
  381. -the boot up processor can read to find the full configuration of the 
  382. -processors and busses. It also defines a procedure for starting up the 
  383. -other processors.
  384. -
  385. -
  386. -\heading{Mutual Exclusion Within A Single Processor Linux Kernel
  387. -
  388. -}
  389. -    For any kernel to function in a sane manner it has to provide internal 
  390. -locking and protection of its own tables to prevent two processes updating 
  391. -them at once and for example allocating the same memory block. There are 
  392. -two strategies for this within current Unix and Unixlike kernels. 
  393. -Traditional unix systems from the earliest of days use a scheme of 'Coarse 
  394. -Grained Locking' where the entire kernel is protected as a small number of 
  395. -locks only. Some modern systems use fine grained locking. Because fine 
  396. -grained locking has more overhead it is normally used only on 
  397. -multiprocessor kernels and real time kernels. In a real time kernel the 
  398. -fine grained locking reduces the amount of time locks are held and reduces 
  399. -the critical (to real time programming at least) latency times.
  400. -
  401. -
  402. -    Within the Linux kernel certain guarantees are made. No process running in 
  403. -kernel mode will be pre-empted by another kernel mode process unless it 
  404. -voluntarily sleeps.  This ensures that blocks of kernel code are 
  405. -effectively atomic with respect to other processes and greatly simplifies 
  406. -many operation. Secondly interrupts may pre-empt a kernel running process, 
  407. -but will always return to that process. A process in kernel mode may 
  408. -disable interrupts on the processor and guarantee such an interruption will 
  409. -not occur. The final guarantee is that an interrupt will not bne pre-empted 
  410. -by a kernel task. That is interrupts will run to completion or be 
  411. -pre-empted by other interrupts only.
  412. -
  413. -
  414. -    The SMP kernel chooses to continue these basic guarantees in order to make 
  415. -initial implementation and deployment easier.  A single lock is maintained 
  416. -across all processors. This lock is required to access the kernel space. 
  417. -Any processor may hold it and once it is held may also re-enter the kernel 
  418. -for interrupts and other services whenever it likes until the lock is 
  419. -relinquished. This lock ensures that a kernel mode process will not be 
  420. -pre-empted and ensures that blocking interrupts in kernel mode behaves 
  421. -correctly. This is guaranteed because only the processor holding the lock 
  422. -can be in kernel mode, only kernel mode processes can disable interrupts 
  423. -and only the processor holding the lock may handle an interrupt.
  424. -
  425. -
  426. -    Such a choice is however poor for performance. In the longer term it is 
  427. -necessary to move to finer grained parallelism in order to get the best 
  428. -system performance. This can be done hierarchically by gradually refining 
  429. -the locks to cover smaller areas. With the current kernel highly CPU bound 
  430. -process sets perform well but I/O bound task sets can easily degenerate to 
  431. -near single processor performance levels. This refinement will be needed to 
  432. -get the best from Linux/SMP.
  433. -
  434. -
  435. -\subheading{\heading{Changes To The Portable Kernel Components
  436. -
  437. -
  438. -}}    The kernel changes are split into generic SMP support changes and 
  439. -architecture specific changes necessary to accommodate each different 
  440. -processor type Linux is ported to.
  441. -
  442. -
  443. -\subsection{Initialisation}
  444. -
  445. -
  446. -    The first problem with a multiprocessor kernel is starting the other 
  447. -processors up. Linux/SMP defines that a single processor enters the normal 
  448. -kernel entry point start_kernel(). Other processors are assumed not to be 
  449. -started or to have been captured elsewhere. The first processor begins the 
  450. -normal Linux initialisation sequences and sets up paging, interrupts and 
  451. -trap handlers. After it has obtained the processor information about the 
  452. -boot CPU, the architecture specific function \
  453. -
  454. -
  455. -\description{
  456. -\leftindent{\bold{void smp_store_cpu_info(int processor_id)
  457. -
  458. -}}}
  459. -is called to store any information about the processor into a per processor 
  460. -array. This includes things like the bogomips speed ratings.
  461. -
  462. -
  463. -    Having completed the kernel initialisation the architecture specific 
  464. -function
  465. -
  466. -
  467. -\description{\leftindent{\bold{void smp_boot_cpus(void)
  468. -
  469. -}}}
  470. -is called and is expected to start up each other processor and cause it to 
  471. -enter start_kernel() with its paging registers and other control 
  472. -information correctly loaded. Each other processor skips the setup except 
  473. -for calling the trap and irq initialisation functions that are needed on 
  474. -some processors to set each CPU up correctly.  These functions will 
  475. -probably need to be modified in existing kernels to cope with this.
  476. -
  477. -
  478. -    Each additional CPU the calls the architecture specific function
  479. -
  480. -
  481. -\description{\leftindent{\bold{void smp_callin(void)
  482. -
  483. -
  484. -}}}which does any final setup and then spins the processor while the boot 
  485. -up processor forks off enough idle threads for each processor. This is 
  486. -necessary because the scheduler assumes there is always something to run. 
  487. - Having generated these threads and forked init the architecture specific \
  488. -
  489. -
  490. -
  491. -\bold{\description{\leftindent{void smp_commence(void)}}}
  492. -
  493. -
  494. -function is invoked. This does any final setup and indicates to the system 
  495. -that multiprocessor mode is now active. All the processors spinning in the 
  496. -smp_callin() function are now released to run the idle processes, which 
  497. -they will run when they have no real work to process.
  498. -
  499. -
  500. -\subsection{Scheduling
  501. -
  502. -}
  503. -    The kernel scheduler implements a simple but very and effective task 
  504. -scheduler. The basic structure of this scheduler is unchanged in the 
  505. -multiprocessor kernel. A processor field is added to each task, and this 
  506. -maintains the number of the processor executing a given task, or a magic 
  507. -constant (NO_PROC_ID)  indicating the job is not allocated to a processor. \
  508. -
  509. -
  510. -    \
  511. -
  512. -
  513. -    Each processor executes the scheduler itself and will select the next task 
  514. -to run from all runnable processes not allocated to a different processor. 
  515. -The algorithm used by the selection is otherwise unchanged. This is 
  516. -actually inadequate for the final system because there are advantages to 
  517. -keeping a process on the same CPU, especially on processor boards with per 
  518. -processor second level caches.
  519. -
  520. -
  521. -    Throughout the kernel the variable 'current' is used as a global for the 
  522. -current process. In Linux/SMP this becomes a macro which expands to 
  523. -current_set[smp_processor_id()]. This enables almost the entire kernel to 
  524. -be unaware of the array of running processors, but still allows the SMP 
  525. -aware kernel modules to see all of the running processes.
  526. -
  527. -
  528. -    The fork system call is modified to generate multiple processes with a 
  529. -process id of zero until the SMP kernel starts up properly. This is 
  530. -necessary because process number 1 must be init, and it is desirable that 
  531. -all the system threads are process 0. \
  532. -
  533. -
  534. -
  535. -    The final area within the scheduling of processes that does cause problems 
  536. -is the fact the uniprocessor kernel hard codes tests for the idle threads 
  537. -as task[0] and the init process as task[1]. Because there are multiple idle 
  538. -threads it is necessary to replace these with tests that the process id is 
  539. -0 and a search for process ID 1, respectively.
  540. -
  541. -\subheading{
  542. -}\subsection{Memory Management}\heading{
  543. -
  544. -
  545. -}    The memory management core of the existing Linux system functions 
  546. -adequately within the multiprocessor framework providing the locking is 
  547. -used. Certain processor specific areas do need changing, in particular 
  548. -invalidate() must invalidate the TLB's of all processors before it returns.
  549. -
  550. -
  551. -\subsection{Miscellaneous Functions}
  552. -
  553. -\heading{
  554. -}    The portable SMP code rests on a small set of functions and variables 
  555. -that are provided by the processor specification functionality. These are
  556. -
  557. -
  558. -\display{\bold{int smp_processor_id(void)
  559. -
  560. -
  561. -}}which returns the identity of the process the call is executed upon. This 
  562. -call is assumed to be valid at all times. This may mean additional tests 
  563. -are needed during initialisation.
  564. -
  565. -
  566. -    \display{\bold{int smp_num_cpus;
  567. -
  568. -}}
  569. -    This is the number of processors in the system. \
  570. -
  571. -
  572. -
  573. -    \bold{void smp_message_pass(int target, int msg, unsigned long data,
  574. -
  575. -        int wait)
  576. -
  577. -}
  578. -    This function passes messages between processors. At the moment it is not 
  579. -sufficiently defined to sensibly document and needs cleaning up and further 
  580. -work. Refer to the processor specific code documentation for more details.
  581. -
  582. -
  583. -\heading{Architecture Specific Code For the Intel MP Port
  584. -
  585. -}
  586. -    The architecture specific code for the intel port splits fairly cleanly 
  587. -into four sections. Firstly the initialisation code used to boot the 
  588. -system, secondly the message handling and support code, thirdly the 
  589. -interrupt and kernel syscall entry function handling and finally the 
  590. -extensions to standard kernel facilities to cope with multiple processors.
  591. -
  592. -
  593. -\subsection{Initialisation
  594. -
  595. -
  596. -}    The intel MP architecture captures all the processors except for a single 
  597. -processor known as the 'boot processor' in the BIOS at boot time. Thus a 
  598. -single processor enters the kernel bootup code. The first processor 
  599. -executes the bootstrap code, loads and uncompresses the kernel. Having 
  600. -unpacked the kernel it sets up the paging and control registers then enters 
  601. -the C kernel startup.
  602. -
  603. -
  604. -    The assembler startup code for the kernel is modified so that it can be 
  605. -used by the other processors to do the processor identification and various 
  606. -other low level configurations but does not execute those parts of the 
  607. -startup code that would damage the running system (such as clearing the BSS 
  608. -segment). \
  609. -
  610. -
  611. -
  612. -    In the initialisation done by the first processor the arch/i386/mm/init 
  613. -code is modified to scan the low page, top page and BIOS for intel MP 
  614. -signature blocks. This is necessary because the MP signature blocks must 
  615. -be read and processed before the kernel is allowed to allocate and destroy 
  616. -the page at the top of low memory. Having established the number of 
  617. -processors it reserves a set of pages to provide a stack come boot up area 
  618. -for each processor in the system. These must be allocated at startup to 
  619. -ensure they fall below the 1Mb boundary.
  620. -
  621. -
  622. -    Further processors are started up in smp_boot_cpus() by programming the 
  623. -APIC controller registers and sending an inter-processor interrupt (IPI) to 
  624. -the processor. This message causes the target processor to begin executing 
  625. -code at the start of any page of memory within the lowest 1Mb, in 16bit 
  626. -real mode. The kernel uses the single page it allocated for each processor 
  627. -to use as stack. Before booting a given CPU the relocatable code from 
  628. -trampoline.S and trampoline32.S is copied to the bottom of its stack page 
  629. -and used as the target for the startup. \
  630. -
  631. -
  632. -
  633. -    The trampoline code calculates the desired stack base from the code 
  634. -segment (since the code segment on startup is the bottom of the stack), 
  635. - enters 32bit mode and jumps to the kernel entry assembler. This as 
  636. -described above is modified to only execute the parts necessary for each 
  637. -processor, and then to enter start_kernel(). On entering the kernel the 
  638. -processor initialises its trap and interrupt handlers before entering 
  639. -smp_callin(), where it reports its status and sets a flag that causes the 
  640. -boot processor to continue and look for further processors. The processor 
  641. -then spins until smp_commence() is invoked.
  642. -
  643. -
  644. -    Having started each processor up the smp_commence( ) function flips a 
  645. -flag. Each processor spinning in smp_callin() then loads the task register 
  646. -with the task state segment (TSS) of its idle thread as is needed for task 
  647. -switching.
  648. -
  649. -
  650. -\subsection{Message Handling and Support Code}
  651. -
  652. -
  653. -    The architecture specific code implements the smp_processor_id() function 
  654. -by querying the APIC logical identity register. Because the APIC isn't 
  655. -mapped into the kernel address space at boot, the initial value returned is 
  656. -rigged by setting the APIC base pointer to point at a suitable constant. 
  657. -Once the system starts doing the SMP setup (in smp_boot_cpus()), the APIC 
  658. -is mapped with a vremap() call and the apic pointer is adjusted 
  659. -appropriately. From then on the real APIC logical identity register is 
  660. -read.
  661. -
  662. -
  663. -    Message passing is accomplished using a pair of IPI's on interrupt 13 
  664. -(unused by the 80486 FPU's in SMP mode) and interrupt 16. Two are used in 
  665. -order to separate messages that cannot be processed until the receiver 
  666. -obtains the kernel spinlock from messages that can be processed 
  667. -immediately. In effect IRQ 13 is a fast IRQ handler that does not obtain 
  668. -the locks, and cannot cause a reschedule, while IRQ 16 is a slow IRQ that 
  669. -must acquire the kernel spinlocks and can cause a reschedule. This 
  670. -interrupt is used for passing on slave timer messages from the processor 
  671. -that receives the timer interrupt to the rest of the processors, so that 
  672. -they can reschedule running tasks.
  673. -
  674. -
  675. -\subsection{Entry And Exit Code}
  676. -
  677. -
  678. -    A single spinlock protects the entire kernel. The interrupt handlers, the 
  679. -syscall entry code and the exception handlers all acquire the lock before 
  680. -entering the kernel proper. When the processor is trying to acquire the 
  681. -spinlock it spins continually on the lock with interrupts disabled. This 
  682. -causes a specific deadlock problem. The lock owner may need to send an 
  683. -invalidate request to the rest of the processors and wait for these to 
  684. -complete before continuing. A processor spinning on the lock would not be 
  685. -able to do thus. Thus the loop of the spinlock tests and handles invalidate 
  686. -requests. If the invalidate bit for the spinning CPU is set the processor 
  687. -invalidates its TLB and atomically clears the bit. When the spinlock is 
  688. -obtained that processor will take an IPI and in the IPI test the bit and 
  689. -skip the invalidate as the bit is clear.
  690. -
  691. -
  692. -    One complexity of the spinlock is that a process running in kernel mode 
  693. -can sleep voluntarily and be pre-empted. A switch from such a process to a 
  694. -process executing in user space may reduce the lock count. To track this 
  695. -the kernel uses a syscall_count and a per process lock_depth parameter to 
  696. -track the kernel lock state. The switch_to() function is modified in SMP 
  697. -mode to adjust the lock appropriately.
  698. -
  699. -
  700. -    The final problem is the idle thread. In the single processor kernel the 
  701. -idle thread executes 'hlt' instructions. This saves power and reduces the 
  702. -running temperature of the processors when they are idle. However it means 
  703. -the process spends all its time in kernel mode and would thus hold the 
  704. -kernel spinlock. The SMP idle thread continually reschedules a new task and 
  705. -returns to user mode. This is far from ideal and will be modified to use 
  706. -'hlt' instructions and release the spinlock soon. Using 'hlt' is even more 
  707. -beneficial on a multiprocessor system as it almost completely takes an idle 
  708. -processor off the bus.
  709. -
  710. -
  711. -    Interrupts are distributed by an i82489 APIC. This chip is set up to work 
  712. -as an emulation of the traditional PC interrupt controllers when the 
  713. -machine boots (so that an Intel MP machine boots one CPU and PC 
  714. -compatible). The kernel has all the relevant locks but does not yet 
  715. -reprogram the 82489 to deliver interrupts to arbitrary processors as it 
  716. -should. This requires further modification of the standard Linux interrupt 
  717. -handling code, and is particularly messy as the interrupt handler behaviour 
  718. -has to change as soon as the 82489 is switched into SMP mode.
  719. -
  720. -
  721. -\subsection{Extensions To Standard Facilities}
  722. -
  723. -
  724. -    The kernel maintains a set of per processor control information such as 
  725. -the speed of the processor for delay loops. These functions on the SMP 
  726. -kernel look the values up in a per processor array that is set up from the 
  727. -data generated at boot up by the smp_store_cpu_info() function. This 
  728. -includes other facts such as whether there is an FPU on the processor. The 
  729. -current kernel does not handle only some processors having floating point.
  730. -
  731. -
  732. -    The highly useful atomic bit operations are prefixed with the 'lock' 
  733. -prefix in the SMP kernel to maintain their atomic properties when used 
  734. -outside of (and by) the spinlock and message code. Amongst other things 
  735. -this is needed for the invalidate handler, as all  CPU's will invalidate at 
  736. -the same time without any locks.
  737. -
  738. -
  739. -    Interrupt 13 floating point error reporting is removed. This facility is 
  740. -not usable on a multiprocessor board, nor relevant to the Intel MP 
  741. -architecture which does not cover the 80386/80387 processor pair. \
  742. -
  743. -
  744. -
  745. -    The /proc filesystem support is changed so that the /proc/cpuinfo file 
  746. -contains a column for each processor present. This information is extracted 
  747. -from the data save by smp_store_cpu_info().
  748. -
  749. -\enddata{text,748928}
  750. diff -u --recursive --new-file pre2.0.4/linux/Documentation/smp.tex linux/Documentation/smp.tex
  751. --- pre2.0.4/linux/Documentation/smp.tex    Fri Apr 12 15:51:45 1996
  752. +++ linux/Documentation/smp.tex    Thu May 16 16:35:39 1996
  753. @@ -24,9 +24,10 @@
  754.  \hfill Alan Cox, 1995
  755.  
  756.  
  757. -The author wishes to thank Caldera Inc whose donation of an ASUS dual 
  758. -pentium board made this project possible, and Thomas Radke, whose initial 
  759. -work on multiprocessor Linux formed the backbone of this project.
  760. +The author wishes to thank Caldera Inc ( http://www.caldera.com )
  761. +whose donation of an ASUS dual pentium board made this project possible, 
  762. +and Thomas Radke, whose initial work on multiprocessor Linux formed 
  763. +the backbone of this project.
  764.  
  765.  \section{Background: The Intel MP specification.}
  766.  Most IBM PC style multiprocessor motherboards combine Intel 486 or Pentium 
  767. diff -u --recursive --new-file pre2.0.4/linux/Makefile linux/Makefile
  768. --- pre2.0.4/linux/Makefile    Wed May 15 11:01:14 1996
  769. +++ linux/Makefile    Tue May 14 14:38:38 1996
  770. @@ -1,6 +1,6 @@
  771.  VERSION = 1
  772.  PATCHLEVEL = 99
  773. -SUBLEVEL = 4
  774. +SUBLEVEL = 5
  775.  
  776.  ARCH = i386
  777.  
  778. diff -u --recursive --new-file pre2.0.4/linux/arch/alpha/boot/main.c linux/arch/alpha/boot/main.c
  779. --- pre2.0.4/linux/arch/alpha/boot/main.c    Wed Apr  3 16:06:55 1996
  780. +++ linux/arch/alpha/boot/main.c    Wed May 15 10:49:36 1996
  781. @@ -228,10 +228,11 @@
  782.  
  783.      nbytes = dispatch(CCB_GET_ENV, ENV_BOOTED_OSFLAGS,
  784.                envval, sizeof(envval));
  785. -    if (nbytes > 0) {
  786. -        envval[nbytes] = '\0';
  787. -        strcpy((char*)ZERO_PAGE, envval);
  788. +    if (nbytes < 0) {
  789. +        nbytes = 0;
  790.      }
  791. +    envval[nbytes] = '\0';
  792. +    strcpy((char*)ZERO_PAGE, envval);
  793.  
  794.      printk(" Ok\nNow booting the kernel\n");
  795.      runkernel();
  796. diff -u --recursive --new-file pre2.0.4/linux/arch/alpha/boot/tools/build.c linux/arch/alpha/boot/tools/build.c
  797. --- pre2.0.4/linux/arch/alpha/boot/tools/build.c    Mon Jan 16 07:17:34 1995
  798. +++ linux/arch/alpha/boot/tools/build.c    Wed May 15 10:49:36 1996
  799. @@ -8,7 +8,7 @@
  800.  #include <unistd.h>
  801.  #include <fcntl.h>
  802.  
  803. -#include <a.out.h>
  804. +#include <linux/a.out.h>
  805.  
  806.  #include <asm/system.h>
  807.  
  808. diff -u --recursive --new-file pre2.0.4/linux/arch/alpha/config.in linux/arch/alpha/config.in
  809. --- pre2.0.4/linux/arch/alpha/config.in    Tue May  7 16:22:16 1996
  810. +++ linux/arch/alpha/config.in    Wed May 15 10:49:37 1996
  811. @@ -40,6 +40,7 @@
  812.       EB66+        CONFIG_ALPHA_EB66P        \
  813.       EB64+        CONFIG_ALPHA_EB64P        \
  814.       EB164        CONFIG_ALPHA_EB164        \
  815. +     PC164        CONFIG_ALPHA_PC164        \
  816.       Jensen        CONFIG_ALPHA_JENSEN        \
  817.       Noname        CONFIG_ALPHA_NONAME        \
  818.       Platform2000    CONFIG_ALPHA_P2K" Cabriolet
  819. @@ -56,14 +57,10 @@
  820.  if [ "$CONFIG_ALPHA_CABRIOLET" = "y" -o "$CONFIG_ALPHA_AVANTI" = "y" \
  821.      -o "$CONFIG_ALPHA_EB64P" = "y" ]
  822.  then
  823. -    if [ "$CONFIG_ALPHA_XL" = "n" ]
  824. -    then
  825. -        bool 'Using SRM as bootloader' CONFIG_ALPHA_SRM
  826. -    fi
  827.      define_bool CONFIG_PCI y
  828.      define_bool CONFIG_ALPHA_APECS y
  829.  fi
  830. -if [ "$CONFIG_ALPHA_EB164" = "y" ]
  831. +if [ "$CONFIG_ALPHA_EB164" = "y" -o "$CONFIG_ALPHA_PC164" = "y" ]
  832.  then
  833.      define_bool CONFIG_PCI y
  834.      define_bool CONFIG_ALPHA_EV5 y
  835. @@ -76,7 +73,10 @@
  836.  if [ "$CONFIG_ALPHA_CABRIOLET" = "y" -o "$CONFIG_ALPHA_AVANTI" = "y" \
  837.      -o "$CONFIG_ALPHA_EB64P" = "y" -o "$CONFIG_ALPHA_JENSEN" = "y" ]
  838.  then
  839. -    bool 'Using SRM as bootloader' CONFIG_ALPHA_SRM
  840. +    if [ "$CONFIG_ALPHA_XL" = "n" ]
  841. +    then
  842. +        bool 'Using SRM as bootloader' CONFIG_ALPHA_SRM
  843. +    fi
  844.  fi
  845.  
  846.  bool 'Echo console messages on /dev/ttyS1' CONFIG_SERIAL_ECHO
  847. diff -u --recursive --new-file pre2.0.4/linux/arch/alpha/kernel/bios32.c linux/arch/alpha/kernel/bios32.c
  848. --- pre2.0.4/linux/arch/alpha/kernel/bios32.c    Tue May  7 16:22:16 1996
  849. +++ linux/arch/alpha/kernel/bios32.c    Tue May 14 14:38:08 1996
  850. @@ -607,6 +607,67 @@
  851.  
  852.  
  853.  /*
  854. + * The PC164 has 19 PCI interrupts, four from each of the four PCI
  855. + * slots, the SIO, PCI/IDE, and USB.
  856. + * 
  857. + * Each of the interrupts can be individually masked. This is
  858. + * accomplished by setting the appropriate bit in the mask register.
  859. + * A bit is set by writing a "1" to the desired position in the mask
  860. + * register and cleared by writing a "0". There are 3 mask registers
  861. + * located at ISA address 804h, 805h and 806h.
  862. + * 
  863. + * An I/O read at ISA address 804h, 805h, 806h will return the
  864. + * state of the 11 PCI interrupts and not the state of the MASKED
  865. + * interrupts.
  866. + * 
  867. + * Note: A write to I/O 804h, 805h, and 806h the mask register will be
  868. + * updated.
  869. + * 
  870. + * 
  871. + *                 ISA DATA<7:0>
  872. + * ISA     +--------------------------------------------------------------+
  873. + * ADDRESS |   7   |   6   |   5   |   4   |   3   |   2  |   1   |   0   |
  874. + *         +==============================================================+
  875. + * 0x804   | INTB0 |  USB  |  IDE  |  SIO  | INTA3 |INTA2 | INTA1 | INTA0 |
  876. + *         +--------------------------------------------------------------+
  877. + * 0x805   | INTD0 | INTC3 | INTC2 | INTC1 | INTC0 |INTB3 | INTB2 | INTB1 |
  878. + *         +--------------------------------------------------------------+
  879. + * 0x806   | Rsrv  | Rsrv  | Rsrv  | Rsrv  | Rsrv  |INTD3 | INTD2 | INTD1 |
  880. + *         +--------------------------------------------------------------+
  881. + *         * Rsrv = reserved bits
  882. + *         Note: The mask register is write-only.
  883. + * 
  884. + * IdSel    
  885. + *   5     32 bit PCI option slot 2
  886. + *   6     64 bit PCI option slot 0
  887. + *   7     64 bit PCI option slot 1
  888. + *   8     Saturn I/O
  889. + *   9     32 bit PCI option slot 3
  890. + *  10     USB
  891. + *  11     IDE
  892. + * 
  893. + */
  894. +
  895. +static inline void alphapc164_fixup(void)
  896. +{
  897. +    char irq_tab[7][5] = {
  898. +      /*
  899. +       *      int   intA  intB   intC   intD
  900. +       *      ----  ----  ----   ----   ----
  901. +       */
  902. +        { 16+2, 16+2, 16+9,  16+13, 16+17},    /* IdSel  5,  slot 2, J20 */
  903. +        { 16+0, 16+0, 16+7,  16+11, 16+15},    /* IdSel  6,  slot 0, J29 */
  904. +        { 16+1, 16+1, 16+8,  16+12, 16+16},    /* IdSel  7,  slot 1, J26 */
  905. +        {   -1,   -1,   -1,    -1,    -1},    /* IdSel  8,  SIO         */
  906. +        { 16+3, 16+3, 16+10, 16+14, 16+18},    /* IdSel  9,  slot 3, J19 */
  907. +        { 16+6, 16+6, 16+6,  16+6,  16+6},    /* IdSel 10,  USB */
  908. +        { 16+5, 16+5, 16+5,  16+5,  16+5}    /* IdSel 11,  IDE */
  909. +    };
  910. +
  911. +    common_fixup(5, 11, 5, irq_tab, 0);
  912. +}
  913. +
  914. +/*
  915.   * The AlphaPC64 is very similar to the EB66+ except that its slots
  916.   * are numbered differently.  In the code below, I have used slot
  917.   * number to refer to the id select line and *not* the slot number
  918. @@ -860,6 +921,8 @@
  919.      sio_fixup();
  920.  #elif defined(CONFIG_ALPHA_CABRIOLET) || defined(CONFIG_ALPHA_EB164)
  921.      cabriolet_fixup();
  922. +#elif defined(CONFIG_ALPHA_PC164)
  923. +    alphapc164_fixup();
  924.  #elif defined(CONFIG_ALPHA_EB66P)
  925.      eb66p_fixup();
  926.  #elif defined(CONFIG_ALPHA_EB66)
  927. diff -u --recursive --new-file pre2.0.4/linux/arch/i386/kernel/traps.c linux/arch/i386/kernel/traps.c
  928. --- pre2.0.4/linux/arch/i386/kernel/traps.c    Tue May  7 16:22:17 1996
  929. +++ linux/arch/i386/kernel/traps.c    Wed May 15 07:56:41 1996
  930. @@ -221,16 +221,6 @@
  931.  }
  932.  
  933.  /*
  934. - * Allow the process which triggered the interrupt to recover the error
  935. - * condition.
  936. - *  - the status word is saved in the cs selector.
  937. - *  - the tag word is saved in the operand selector.
  938. - *  - the status word is then cleared and the tags all set to Empty.
  939. - *
  940. - * This will give sufficient information for complete recovery provided that
  941. - * the affected process knows or can deduce the code and data segments
  942. - * which were in force when the exception condition arose.
  943. - *
  944.   * Note that we play around with the 'TS' bit to hopefully get
  945.   * the correct behaviour even in the presence of the asynchronous
  946.   * IRQ13 behaviour
  947. diff -u --recursive --new-file pre2.0.4/linux/arch/m68k/atari/atafb.c linux/arch/m68k/atari/atafb.c
  948. --- pre2.0.4/linux/arch/m68k/atari/atafb.c    Tue May  7 16:22:18 1996
  949. +++ linux/arch/m68k/atari/atafb.c    Thu May 16 09:05:09 1996
  950. @@ -515,6 +515,7 @@
  951.      fix->xpanstep=0;
  952.      fix->ypanstep=1;
  953.      fix->ywrapstep=0;
  954. +    fix->line_length = 0;
  955.      for (i=0; i<arraysize(fix->reserved); i++)
  956.          fix->reserved[i]=0;
  957.      return 0;
  958. @@ -832,6 +833,7 @@
  959.          fix->xpanstep = 1;
  960.      fix->ypanstep = 1;
  961.      fix->ywrapstep = 0;
  962. +    fix->line_length = 0;
  963.      for (i=0; i<arraysize(fix->reserved); i++)
  964.          fix->reserved[i]=0;
  965.      return 0;
  966. @@ -1717,6 +1719,7 @@
  967.      else
  968.          fix->ypanstep = 0;
  969.      fix->ywrapstep = 0;
  970. +    fix->line_length = 0;
  971.      for (i=0; i<arraysize(fix->reserved); i++)
  972.          fix->reserved[i]=0;
  973.      return 0;
  974. @@ -2049,6 +2052,7 @@
  975.      fix->xpanstep = 0;
  976.      fix->ypanstep = 0;
  977.      fix->ywrapstep = 0;
  978. +    fix->line_length = 0;
  979.      for (i=0; i<arraysize(fix->reserved); i++)
  980.          fix->reserved[i]=0;
  981.      return 0;
  982. @@ -2592,6 +2596,7 @@
  983.      disp[con].type_aux = fix.type_aux;
  984.      disp[con].ypanstep = fix.ypanstep;
  985.      disp[con].ywrapstep = fix.ywrapstep;
  986. +    disp[con].line_length = fix.line_length;
  987.      if (fix.visual != FB_VISUAL_PSEUDOCOLOR &&
  988.          fix.visual != FB_VISUAL_DIRECTCOLOR)
  989.          disp[con].can_soft_blank = 0;
  990. diff -u --recursive --new-file pre2.0.4/linux/arch/m68k/atari/config.c linux/arch/m68k/atari/config.c
  991. --- pre2.0.4/linux/arch/m68k/atari/config.c    Tue May  7 16:22:19 1996
  992. +++ linux/arch/m68k/atari/config.c    Thu May 16 09:05:09 1996
  993. @@ -1054,6 +1054,7 @@
  994.        jmp_addr_label040:
  995.          __asm__ __volatile__
  996.            ("moveq #0,%/d0\n\t"
  997. +       "nop\n\t"
  998.         ".word 0xf4d8\n\t"        /* cinva i/d */
  999.         ".word 0xf518\n\t"        /* pflusha */
  1000.             ".long 0x4e7b0003\n\t"    /* movec d0,tc */
  1001. diff -u --recursive --new-file pre2.0.4/linux/arch/m68k/atari/ksyms.c linux/arch/m68k/atari/ksyms.c
  1002. --- pre2.0.4/linux/arch/m68k/atari/ksyms.c    Tue Apr 23 13:57:03 1996
  1003. +++ linux/arch/m68k/atari/ksyms.c    Thu May 16 09:05:10 1996
  1004. @@ -7,9 +7,6 @@
  1005.  #include <asm/atarikb.h>
  1006.  #include <asm/atari_joystick.h>
  1007.  #include <asm/atari_stdma.h>
  1008. -#if 0
  1009. -#include <asm/atari_acsi.h>
  1010. -#endif
  1011.  
  1012.  static struct symbol_table mach_atari_symbol_table = {
  1013.  #include <linux/symtab_begin.h>
  1014. @@ -29,20 +26,6 @@
  1015.      X(ikbd_mouse_thresh),
  1016.      X(ikbd_mouse_rel_pos),
  1017.      X(ikbd_mouse_disable),
  1018. -
  1019. -#if 0
  1020. -#ifdef CONFIG_ATARI_ACSI
  1021. -    X(acsi_wait_for_IRQ),
  1022. -    X(acsi_wait_for_noIRQ),
  1023. -    X(acsicmd_nodma),
  1024. -    X(acsi_getstatus),
  1025. -#ifdef CONFIG_ATARI_SLM
  1026. -    X(acsi_extstatus),
  1027. -    X(acsi_end_extstatus),
  1028. -    X(acsi_extcmd),
  1029. -#endif
  1030. -#endif
  1031. -#endif /* 0 */
  1032.  
  1033.  #include <linux/symtab_end.h>
  1034.  };
  1035. diff -u --recursive --new-file pre2.0.4/linux/arch/m68k/kernel/entry.S linux/arch/m68k/kernel/entry.S
  1036. --- pre2.0.4/linux/arch/m68k/kernel/entry.S    Sat Apr 27 15:19:47 1996
  1037. +++ linux/arch/m68k/kernel/entry.S    Thu May 16 09:05:10 1996
  1038. @@ -593,7 +593,7 @@
  1039.      .long SYMBOL_NAME(sys_clone)        /* 120 */
  1040.      .long SYMBOL_NAME(sys_setdomainname)
  1041.      .long SYMBOL_NAME(sys_newuname)
  1042. -    .long SYMBOL_NAME(sys_ni_syscall)    /* modify_ldt for i386 */
  1043. +    .long SYMBOL_NAME(sys_cacheflush)    /* modify_ldt for i386 */
  1044.      .long SYMBOL_NAME(sys_adjtimex)
  1045.      .long SYMBOL_NAME(sys_mprotect)        /* 125 */
  1046.      .long SYMBOL_NAME(sys_sigprocmask)
  1047. diff -u --recursive --new-file pre2.0.4/linux/arch/m68k/kernel/head.S linux/arch/m68k/kernel/head.S
  1048. --- pre2.0.4/linux/arch/m68k/kernel/head.S    Tue May  7 16:22:19 1996
  1049. +++ linux/arch/m68k/kernel/head.S    Thu May 16 09:05:10 1996
  1050. @@ -1,6 +1,6 @@
  1051.  /* -*- mode: asm -*-
  1052.  **
  1053. -** head.S -- This file contains the initial boot code for the the
  1054. +** head.S -- This file contains the initial boot code for the
  1055.  **         Linux/68k kernel.
  1056.  **
  1057.  ** Copyright 1993 by Hamish Macdonald
  1058. @@ -12,13 +12,13 @@
  1059.  ** and Bjoern Brauel
  1060.  **
  1061.  ** 94/11/14 Andreas Schwab: put kernel at PAGESIZE
  1062. -** 94/11/18 Andreas Schwab: remove identity mapping of STRAM for Atari 
  1063. +** 94/11/18 Andreas Schwab: remove identity mapping of STRAM for Atari
  1064.  ** ++ Bjoern & Roman: ATARI-68040 support for the Medusa
  1065.  ** 96/04/26 G|nther Kelleter: fixed identity mapping for Falcon with
  1066. -**                            Magnum- and FX-alternate ram
  1067. +**                   Magnum- and FX-alternate ram
  1068.  **
  1069.  ** This file is subject to the terms and conditions of the GNU General Public
  1070. -** License.  See the file README.legal in the main directory of this archive
  1071. +** License. See the file README.legal in the main directory of this archive
  1072.  ** for more details.
  1073.  **
  1074.  */
  1075. @@ -49,34 +49,36 @@
  1076.   * that should be applied to pages containing descriptors. This mode is
  1077.   * non-cached/non-serialized for the '040 and cacheable/write-through for
  1078.   * the '060.
  1079. + *
  1080. + * General register usage:
  1081. + *   a6 - start of unused memory
  1082. + *      new pages can be allocated from here
  1083. + *   a5 - mmu root table
  1084. + *   a4 - mmu pointer table
  1085. + *   a3 - mmu page tables
  1086. + *   a2 - points to the page table entry for a6
  1087. + *      cache status can be changed (used for '0[46]0)
  1088. + *      you must increase a2 if alloc a new page
  1089. + *   d7 - used for debug output and some macros
  1090. + *   d6 - cpu type and cache mode
  1091. + *   d5 - physical start address of kernel
  1092. + *   d4 - machine type
  1093.   */
  1094.  
  1095. +#include <linux/autoconf.h>
  1096.  #include <linux/linkage.h>
  1097.  #include <asm/bootinfo.h>
  1098. +#include <asm/pgtable.h>
  1099.  
  1100. -.text
  1101.  .globl SYMBOL_NAME(kernel_pg_dir), SYMBOL_NAME(kpt)
  1102.  .globl SYMBOL_NAME(availmem), SYMBOL_NAME(is_medusa)
  1103.  .globl SYMBOL_NAME(m68k_pgtable_cachemode)
  1104.  .globl SYMBOL_NAME(kernel_pmd_table), SYMBOL_NAME(swapper_pg_dir)
  1105.  
  1106. -PAGESIZE = 4096
  1107. -BI_CPU = 4
  1108. -BI_MACH = 0
  1109. -BI_AMIGA_ECLK = 1234
  1110. -LF   = 10
  1111. -CR   = 13
  1112. -BI_BIT040 = 2    /* CPU bits in bootinfo */
  1113. -BI_BIT060 = 3
  1114. -BIT0460   = 16    /* indicates '0[46]0 in d6 */
  1115. -BIT060    = 17    /* indicates '060 in d6 */
  1116. -D6VAL_040 = 0x00010000
  1117. -D6VAL_060 = 0x00030000
  1118. -/* BIT040 = 2 */
  1119. -
  1120. -     /* Some definitions for the special registers of the 68040.
  1121. -      * (MMU, caches)
  1122. -      */
  1123. +D6B_0460 = 16        /* indicates 680[46]0 in d6 */
  1124. +D6B_060  = 17        /* indicates 68060 in d6 */
  1125. +D6F_040  = 1<<D6B_0460
  1126. +D6F_060  = (1<<D6B_0460)+(1<<D6B_060)
  1127.  
  1128.  /* Translation control register */
  1129.  TC_ENABLE = 0x8000
  1130. @@ -84,78 +86,96 @@
  1131.  TC_PAGE4K = 0x0000
  1132.  
  1133.  /* Transparent translation registers */
  1134. -TTR_ENABLE = 0x8000
  1135. -
  1136. -/* Some bits used in the page and table descriptors as well as in the 
  1137. - * special registers.
  1138. - */
  1139. -
  1140. -CM_CACHE_WT     = 0x0000          /* cacheable, write-through */
  1141. -CM_CACHE_CB     = 0x0020          /* cacheable, copyback */
  1142. -CM_NONCACHE_SER = 0x0040          /* noncacheable, serialized */
  1143. -CM_NONCACHE     = 0x0060          /* noncacheable */
  1144. -CM_MASK         = 0xffffff9f      /* mask */
  1145. -
  1146. -MODIFIED        = 0x0010
  1147. -WRITE_PROT      = 0x0004
  1148. -USED            = 0x0008
  1149. -GLOBAL          = 0x0400
  1150. -SV_ONLY         = 0x0080
  1151. -PAGEDESC    = 0x0001
  1152. -TABLEDESC    = 0x0002
  1153. -INVALID         = 0x0000
  1154. -
  1155. -/* Cache enabling */
  1156. -I_HALF        = 0x00002000    /* half-cache mode for I-cache ('060) */
  1157. -I_FREEZE    = 0x00004000    /* freeze I-cache ('060) */
  1158. -I_ENABLE        = 0x00008000    /* enable I-cache */
  1159. -BC_CLRU        = 0x00200000    /* clear user entries in branch cache ('060) */
  1160. -BC_CLRA        = 0x00400000    /* clear all entries in branch cache ('060) */
  1161. -BC_ENABLE    = 0x00800000    /* enable branch cache ('060) */
  1162. -D_HALF        = 0x08000000    /* half-cache mode for D-cache ('060) */
  1163. -PUSH_DPI    = 0x10000000    /* disable CPUSH invalidation ('060) */
  1164. -SB_ENABLE    = 0x20000000    /* enable store buffer ('060) */
  1165. -D_FREEZE    = 0x40000000    /* freeze D-cache ('060) */
  1166. -D_ENABLE        = 0x80000000    /* enable D-cache */
  1167. +TTR_ENABLE    = 0x8000    /* enable transparent translation */
  1168. +TTR_ANYMODE    = 0x4000    /* user and kernel mode access */
  1169. +TTR_KERNELMODE    = 0x2000    /* only kernel mode access */
  1170. +TTR_USERMODE    = 0x0000    /* only user mode access */
  1171. +TTR_CI        = 0x0400    /* inhibit cache */
  1172. +TTR_RW        = 0x0200    /* read/write mode */
  1173. +TTR_RWM        = 0x0100    /* read/write mask */
  1174. +TTR_FCB2    = 0x0040    /* function code base bit 2 */
  1175. +TTR_FCB1    = 0x0020    /* function code base bit 1 */
  1176. +TTR_FCB0    = 0x0010    /* function code base bit 0 */
  1177. +TTR_FCM2    = 0x0004    /* function code mask bit 2 */
  1178. +TTR_FCM1    = 0x0002    /* function code mask bit 1 */
  1179. +TTR_FCM0    = 0x0001    /* function code mask bit 0 */
  1180. +
  1181. +/* Cache Control registers */
  1182. +CC6_ENABLE_D    = 0x80000000    /* enable data cache (680[46]0) */
  1183. +CC6_FREEZE_D    = 0x40000000    /* freeze data cache (68060) */
  1184. +CC6_ENABLE_SB    = 0x20000000    /* enable store buffer (68060) */
  1185. +CC6_PUSH_DPI    = 0x10000000    /* disable CPUSH invalidation (68060) */
  1186. +CC6_HALF_D    = 0x08000000    /* half-cache mode for data cache (68060) */
  1187. +CC6_ENABLE_B    = 0x00800000    /* enable branch cache (68060) */
  1188. +CC6_CLRA_B    = 0x00400000    /* clear all entries in branch cache (68060) */
  1189. +CC6_CLRU_B    = 0x00200000    /* clear user entries in branch cache (68060) */
  1190. +CC6_ENABLE_I    = 0x00008000    /* enable instruction cache (680[46]0) */
  1191. +CC6_FREEZE_I    = 0x00004000    /* freeze instruction cache (68060) */
  1192. +CC6_HALF_I    = 0x00002000    /* half-cache mode for instruction cache (68060) */
  1193. +CC3_ALLOC_WRITE    = 0x00002000    /* write allocate mode(68030) */
  1194. +CC3_ENABLE_DB    = 0x00001000    /* enable data burst (68030) */
  1195. +CC3_CLR_D    = 0x00000800    /* clear data cache (68030) */
  1196. +CC3_CLRE_D    = 0x00000400    /* clear entry in data cache (68030) */
  1197. +CC3_FREEZE_D    = 0x00000200    /* freeze data cache (68030) */
  1198. +CC3_ENABLE_D    = 0x00000100    /* enable data cache (68030) */
  1199. +CC3_ENABLE_IB    = 0x00000010    /* enable instruction burst (68030) */
  1200. +CC3_CLR_I    = 0x00000008    /* clear instruction cache (68030) */
  1201. +CC3_CLRE_I    = 0x00000004    /* clear entry in instruction cache (68030) */
  1202. +CC3_FREEZE_I    = 0x00000002    /* freeze instruction cache (68030) */
  1203. +CC3_ENABLE_I    = 0x00000001    /* enable instruction cache (68030) */
  1204.  
  1205.  /* Miscellaneous definitions */
  1206. -PAGE_MASK       = (~(PAGESIZE-1))
  1207. +PAGESIZE    = 4096
  1208.  
  1209. -ROOT_TABLE_SIZE = 128
  1210. -PTR_TABLE_SIZE  = 128
  1211. -PAGE_TABLE_SIZE = 64
  1212. +ROOT_TABLE_SIZE    = 128
  1213. +PTR_TABLE_SIZE    = 128
  1214. +PAGE_TABLE_SIZE    = 64
  1215.  ROOT_INDEX_SHIFT = 25
  1216. +PTR_INDEX_SHIFT  = 18
  1217.  PAGE_INDEX_SHIFT = 12
  1218.  
  1219. +TABLENR_4MB    = 16    /* # of page tables needed to page 4 MB */
  1220. +TABLENR_16MB    = 64    /* same for 16 MB */
  1221. +
  1222. +#define putc(ch) moveq &ch,%d7; jbsr Lserial_putc
  1223. +#define putr() putc(13); putc(10)
  1224. +#define putn(nr) movel nr,%d7; jbsr Lserial_putnum
  1225. +
  1226. +#define is_not_amiga(lab) moveq &MACH_AMIGA,%d7; cmpl %d4,%d7; jne lab
  1227. +#define is_not_atari(lab) moveq &MACH_ATARI,%d7; cmpl %d4,%d7; jne lab
  1228. +
  1229. +#define is_040_or_060(lab) btst &D6B_0460,%d6; jne lab
  1230. +#define is_not_040_or_060(lab) btst &D6B_0460,%d6; jeq lab
  1231. +#define is_060(lab) btst &D6B_060,%d6; jne lab
  1232. +#define is_not_060(lab) btst &D6B_060,%d6; jeq lab
  1233. +
  1234. +.text
  1235.  ENTRY(_stext)
  1236. -ENTRY(_start)
  1237. -    bras    1f /* Jump over bootinfo version numbers */
  1238.  /*
  1239.   * Version numbers of the bootinfo interface
  1240. + * The area from _stext to _start will later be used as kernel pointer table
  1241.   */
  1242. +    bras    1f    /* Jump over bootinfo version numbers */
  1243.  
  1244.      .long    BOOTINFOV_MAGIC
  1245.      .long    MACH_AMIGA, AMIGA_BOOTI_VERSION
  1246.      .long    MACH_ATARI, ATARI_BOOTI_VERSION
  1247.      .long    0
  1248. +1:    jra    SYMBOL_NAME(_start)
  1249.  
  1250. -1:
  1251. +.equ    SYMBOL_NAME(kernel_pmd_table),SYMBOL_NAME(_stext)
  1252. +.equ    SYMBOL_NAME(kernel_pg_dir),SYMBOL_NAME(kernel_pmd_table)
  1253. +.equ    SYMBOL_NAME(swapper_pg_dir),SYMBOL_NAME(kernel_pg_dir)+(ROOT_TABLE_SIZE<<2)
  1254. +.equ    Lavail_pmd_table,SYMBOL_NAME(swapper_pg_dir)+(ROOT_TABLE_SIZE<<2)
  1255.  
  1256. -/*
  1257. - * raise interrupt level
  1258. - */
  1259. +.equ    .,SYMBOL_NAME(_stext)+PAGESIZE
  1260.  
  1261. -    movew    #0x2700,%sr
  1262. +ENTRY(_start)
  1263.  
  1264.  /*
  1265.   * Setup initial stack pointer
  1266.   */
  1267. -    lea    %pc@(SYMBOL_NAME(_start)),%sp
  1268. -
  1269. -/* clear the fpu */
  1270. -    lea    %pc@(mmu),%a0
  1271. -    clrl    %a0@
  1272. -    frestore %a0@
  1273. +    lea    %pc@(SYMBOL_NAME(_stext):w),%sp
  1274.  
  1275.  /*
  1276.   * Copy bootinfo from position after BSS to final resting place
  1277. @@ -171,75 +191,89 @@
  1278.   * Record the CPU and machine type.
  1279.   */
  1280.      lea    %pc@(SYMBOL_NAME(boot_info)),%a0
  1281. -    movel    %a0@(BI_MACH),%d4
  1282. -    movel    %a0@(BI_CPU),%d0
  1283. -    movel    %a0@(BI_CPU),%d6      /* !!!!!!!!!!!!!!!! */
  1284. +    movel    %a0@(BI_machtype),%d4
  1285. +    movel    %a0@(BI_cputype),%d0
  1286.  
  1287. -    btst    #BI_BIT060,%d0
  1288. -    beq    1f
  1289. +    btst    #CPUB_68060,%d0
  1290. +    jeq    1f
  1291.      /* '060: d6 := BIT0460|BIT060, cache mode 0x60 (no-cache/non-ser) */
  1292. -    movel    #(D6VAL_060+CM_NONCACHE),%d6
  1293. -    bra    2f
  1294. -1:    btst    #BI_BIT040,%d0
  1295. -    beq    1f
  1296. +    movel    #D6F_060+_PAGE_NOCACHE,%d6
  1297. +    jra    2f
  1298. +1:    btst    #CPUB_68040,%d0
  1299. +    jeq    1f
  1300.      /* '040: d6 := BIT0460, cache mode 0x00 (write-through) */
  1301. -    movel    #(D6VAL_040+CM_CACHE_WT),%d6
  1302. -    bra    2f
  1303. +    movel    #D6F_040+_PAGE_CACHE040W,%d6
  1304. +    jra    2f
  1305.  1:    /* '020 or '030: d6 := no CPU bit, cache mode unused */
  1306.      moveq    #0,%d6
  1307.  
  1308.  2:    lea    %pc@(SYMBOL_NAME(m68k_pgtable_cachemode)),%a0
  1309. -    movel    %d6,%a0@        /* save cache mode for page tables */
  1310. -    andl    #0x0000ffff,%a0@
  1311. +    moveq    #0,%d0
  1312. +    movew    %d6,%d0
  1313. +    movel    %d0,%a0@        /* save cache mode for page tables */
  1314. +
  1315. +/*
  1316. + * raise interrupt level with MASTER bit set, copy isp to msp (if not 68060)
  1317. + */
  1318. +#ifdef FROM_PL9
  1319. +    movew    #0x3700,%sr
  1320. +    is_060(1f)
  1321. +    movec    %isp,%d0
  1322. +    movel    %d0,%sp
  1323. +1:
  1324. +#else
  1325. +    movew    #0x2700,%sr
  1326. +#endif
  1327.  
  1328.  /*
  1329.   * Initialize serial port
  1330.   */
  1331.      jbsr Lserial_init
  1332.  
  1333. -    moveq    #CR,%d7
  1334. -    jbsr    Lserial_putc
  1335. -    moveq    #LF,%d7
  1336. -    jbsr    Lserial_putc
  1337. -    moveq    #'A',%d7
  1338. -    jbsr    Lserial_putc
  1339. +    putr()
  1340. +    putc('A')
  1341.  
  1342.  /*
  1343.   * Get address at end of kernel code/data/bss and
  1344.   * mask off at a page boundary.
  1345.   */
  1346.      lea    %pc@(SYMBOL_NAME(_end)),%a0
  1347. +    addw    #PAGESIZE-1,%a0
  1348.      movel    %a0,%d0
  1349. -    addl    #(PAGESIZE-1),%d0
  1350. -    andl    #PAGE_MASK,%d0
  1351. +    andl    #-PAGESIZE,%d0
  1352.      movel    %d0,%a6
  1353.  
  1354. -    moveq    #'B',%d7
  1355. -    jbsr    Lserial_putc
  1356. +    putc('B')
  1357. +
  1358. +/*
  1359. + * Save physical start address of kernel
  1360. + */
  1361. +    lea    %pc@(SYMBOL_NAME(_stext)-PAGESIZE:w),%a0
  1362. +    movel    %a0,%d5
  1363. +#ifdef HACKER_KERNEL
  1364. +    lea    %pc@(Lkernel_start),%a0
  1365. +    movel    %d5,%a0@
  1366. +#endif
  1367.  
  1368.  /*
  1369.   * initialize the kernel root table.
  1370.   */
  1371. -    lea    %pc@(SYMBOL_NAME(kernel_pg_dir)),%a4
  1372. -    movel    %a4,%a0
  1373. -    moveq    #0,%d0
  1374. -    moveq    #(ROOT_TABLE_SIZE-1),%d1
  1375. -1:    movel    %d0,%a0@+
  1376. +    lea    %pc@(SYMBOL_NAME(kernel_pg_dir):w),%a5
  1377. +    movel    %a5,%a0
  1378. +    moveq    #ROOT_TABLE_SIZE-1,%d1
  1379. +1:    clrl    %a0@+
  1380.      dbra    %d1,1b
  1381.  
  1382.      /*
  1383.       * Initialize root table descriptor pointing to the kernel pointer
  1384.       * table.
  1385.       */
  1386. -    movel    %a6,%a5
  1387. -    addw    #PAGESIZE,%a6
  1388. +    lea    %pc@(Lavail_pmd_table:w),%a4
  1389. +    moveq    #_PAGE_TABLE,%d0
  1390. +    addl    %a4,%d0
  1391. +    movel    %d0,%a5@
  1392.  
  1393. -    movel    %a5,%a0
  1394. -    addql    #TABLEDESC,%a0
  1395. -    movel    %a0,%a4@
  1396. -
  1397. -    moveq    #'C',%d7
  1398. -    jbsr    Lserial_putc
  1399. +    putc('C')
  1400.  
  1401.  /*
  1402.   * Initialize the pointer tables referred to above.  They either point
  1403. @@ -258,13 +292,12 @@
  1404.   */
  1405.  
  1406.      /* clear the kernel pointer table */
  1407. -    movel    %a5,%a0
  1408. -    moveq    #0,%d0
  1409. -    moveq    #(PTR_TABLE_SIZE-1),%d1
  1410. -1:    movel    %d0,%a0@+
  1411. +    movel    %a4,%a0
  1412. +    moveq    #PTR_TABLE_SIZE-1,%d1
  1413. +1:    clrl    %a0@+
  1414.      dbra    %d1,1b
  1415.  
  1416. -    movel    %a5,%a0
  1417. +    movel    %a4,%a0
  1418.      moveq    #15,%d1
  1419.  
  1420.      /*
  1421. @@ -272,29 +305,28 @@
  1422.       * the address of the first page table (680[46]0)
  1423.       * or the base address of physical memory (68030).
  1424.       */
  1425. -    btst    #BIT0460,%d6
  1426. -    bne    1f
  1427. +    is_040_or_060(1f)
  1428.  
  1429.      /* 680[23]0 */
  1430. -    lea    %pc@(SYMBOL_NAME(_stext)-PAGESIZE:w),%a1  /* base address */
  1431. -    addql    #PAGEDESC,%a1    /* descriptor type */
  1432. -    movel    #0x40000,%d2    /* increment */
  1433. -    bra    2f
  1434. +    movel    %d5,%a1                /* base address */
  1435. +    addql    #_PAGE_PRESENT,%a1        /* descriptor type */
  1436. +    movel    #PAGE_TABLE_SIZE*PAGESIZE,%d2    /* increment */
  1437. +    jra    2f
  1438.  
  1439.  1:    /* 680[46]0 */
  1440. -    movel    %a6,%a1        /* base address */
  1441. -    addw    #PAGESIZE,%a6    /* allocate the page table */
  1442. -    lea    %pc@(SYMBOL_NAME(kpt)),%a3
  1443. -    movel    %a1,%a3@        /* save address of page table */
  1444. -    addql    #TABLEDESC,%a1    /* descriptor type */
  1445. -    movel    #256,%d2     /* increment */
  1446. +    movel    %a6,%a3            /* base address */
  1447. +    addw    #PAGESIZE,%a6        /* allocate page for 16 page tables */
  1448. +    lea    %pc@(SYMBOL_NAME(kpt)),%a1
  1449. +    movel    %a3,%a1@        /* save address of page table */
  1450. +    movel    %a3,%a1
  1451. +    addql    #_PAGE_TABLE,%a1    /* descriptor type */
  1452. +    movel    #PAGE_TABLE_SIZE<<2,%d2 /* increment */
  1453.  
  1454.  2:    movel    %a1,%a0@+
  1455.      addl    %d2,%a1
  1456.      dbra    %d1,2b
  1457.  
  1458. -    moveq    #'D',%d7
  1459. -    jbsr    Lserial_putc
  1460. +    putc('D')
  1461.  
  1462.  /*
  1463.   * If we are running on a 680[46]0, we have a kernel page table and
  1464. @@ -303,20 +335,15 @@
  1465.   * Set the cache mode bits to Cacheable, Copyback.  Set the Global bits
  1466.   * in the descriptors also.
  1467.   */
  1468. +    is_not_040_or_060(Lnot040)
  1469.  
  1470. -    btst    #BIT0460,%d6
  1471. -    jeq    Lnot040
  1472. -
  1473. -    moveq    #'F',%d7
  1474. -    jbsr    Lserial_putc
  1475. -
  1476. -    movel    %pc@(SYMBOL_NAME(kpt)),%a0
  1477. -    lea    %pc@(SYMBOL_NAME(_stext)-PAGESIZE:w),%a1
  1478. +    putc('F')
  1479.  
  1480. -    addw    #(GLOBAL+CM_CACHE_CB+PAGEDESC),%a1
  1481. -    movew    #((PAGESIZE/4)-1),%d1
  1482. +    movel    %a3,%a0
  1483. +    movel    %d5,%a1
  1484. +    addw    #_PAGE_GLOBAL040+_PAGE_CACHE040+_PAGE_PRESENT,%a1
  1485. +    movew    #(PAGE_TABLE_SIZE*TABLENR_4MB)-1,%d1
  1486.      movel    #PAGESIZE,%d2
  1487. -
  1488.  1:    movel    %a1,%a0@+
  1489.      addl    %d2,%a1
  1490.      dbra    %d1,1b
  1491. @@ -328,52 +355,46 @@
  1492.       * all pointer tables utilized thus far) and the
  1493.       * kernel page table.
  1494.       */
  1495. -    lea    %pc@(SYMBOL_NAME(_stext)-PAGESIZE:w),%a0
  1496. -    movel    %a4,%d0        /* address of root table */
  1497. -    subl    %a0,%d0        /* determine offset of root table page */
  1498. -    moveq    #PAGE_INDEX_SHIFT,%d1    /* determine offset into kernel page table */
  1499. -    lsrl    %d1,%d0        /* i.e. page number of the address offset */
  1500. -    movel    %pc@(SYMBOL_NAME(kpt)),%a0
  1501. -    lea    %a0@(%d0:l:4),%a0
  1502. -    movel    %a0@,%d1
  1503. -    andl    #CM_MASK,%d1
  1504. +    movel    %a5,%d0
  1505. +    subl    %d5,%d0
  1506. +    moveq    #PAGE_INDEX_SHIFT,%d2
  1507. +    lsrl    %d2,%d0
  1508. +    lea    %a3@(%d0:l:4),%a2
  1509. +    movel    %a2@,%d1
  1510. +    andw    #_CACHEMASK040,%d1
  1511.      orw    %d6,%d1
  1512. -    movel    %d1,%a0@+
  1513. -
  1514. -    movel    %a0@,%d1    /* do the same for the kernel page table */
  1515. -    bclr    #5,%d1        /* the kernel page table resides in the  */
  1516. -    bset    #6,%d1        /* page after the page containing the     */
  1517. -    movel    %d1,%a0@    /* root table                 */
  1518. +    movel    %d1,%a2@
  1519.  
  1520. +    movel    %a3,%d0
  1521. +    subl    %d5,%d0
  1522. +    lsrl    %d2,%d0
  1523. +    lea    %a3@(%d0:l:4),%a2
  1524. +    movel    %a2@,%d1
  1525. +    andw    #_CACHEMASK040,%d1
  1526. +    orw    %d6,%d1
  1527. +    movel    %d1,%a2@+
  1528. +    /*
  1529. +     * %a2 points now to the page table entry for available pages at %a6,
  1530. +     * hence caching modes for new pages can easiely set unless increasing
  1531. +     * of %a2 are forgotten.
  1532. +     */
  1533.  Lnot040:
  1534.  /*
  1535.   * Do any machine specific page table initializations.
  1536.   */
  1537. -    moveq    #MACH_AMIGA,%d0
  1538. -    cmpl    %d4,%d0
  1539. -    bne    Lnotami
  1540. +#ifdef CONFIG_AMIGA
  1541. +    is_not_amiga(Lnotami)
  1542.  
  1543.  /*
  1544. - * On the Amiga:
  1545. - * Our current stack (in CHIP ram) may become invalid after the remapping
  1546. - * of the kernel virtual address space, so set it to point to PAGE_SIZE.
  1547. - * This will be in CHIP ram until after the remapping, and in the unused
  1548. - * first page (temporarily) after that.
  1549. - *
  1550.   * Setup a mapping of the first 16M of physical address space at virtual
  1551.   * address 0x80000000, using early termination page descriptors for the
  1552.   * 68030, and proper page tables for the 680[46]0.  Set this area as
  1553.   * non-cacheable.
  1554.   */
  1555.  
  1556. -    moveq    #'H',%d7
  1557. -    jbsr    Lserial_putc
  1558. -
  1559. -    move.w    #PAGESIZE,%sp
  1560. -
  1561. -    btst    #BIT0460,%d6
  1562. -    bne    Lspami68040
  1563. +    putc('H')
  1564.  
  1565. +    is_040_or_060(Lspami68040)
  1566.  
  1567.      /*
  1568.       * for the 68030, just setup a translation to map in the first
  1569. @@ -381,13 +402,12 @@
  1570.           * using an early termination page descriptor.
  1571.       */
  1572.  
  1573. -    moveq    #'I',%d7
  1574. -    jbsr    Lserial_putc
  1575. +    putc('I')
  1576.  
  1577. -    moveq    #0x41,%d0
  1578. -    movel    %d0,%a4@(64*4)
  1579. +    moveq    #_PAGE_NOCACHE030+_PAGE_PRESENT,%d0
  1580. +    movel    %d0,%a5@(0x40<<2)
  1581.  
  1582. -    bra    Lmapphys
  1583. +    jra    Lmapphys
  1584.  
  1585.  Lspami68040:
  1586.  
  1587. @@ -399,41 +419,39 @@
  1588.       */
  1589.  
  1590.      /* clear the amiga pointer table */
  1591. -    lea    %a5@(512),%a0
  1592. -    moveq    #0,%d0
  1593. -    moveq    #(PTR_TABLE_SIZE-1),%d1
  1594. -1:    movel    %d0,%a0@+
  1595. +    lea    %a4@(PTR_TABLE_SIZE<<2),%a4
  1596. +    moveq    #PTR_TABLE_SIZE-1,%d1
  1597. +1:    clrl    %a0@+
  1598.      dbra    %d1,1b
  1599.  
  1600. -    /* allocate 4 page tables */
  1601. +    /* allocate 4 pages for 64 page tables */
  1602.      movel    %a6,%a3
  1603. -    addw    #(4*PAGESIZE),%a6
  1604. +    addw    #4*PAGESIZE,%a6
  1605.  
  1606.      /* initialize the pointer table */
  1607. -    lea    %a5@(512),%a0
  1608. +    movel    %a4,%a0
  1609.      movel    %a3,%a1
  1610. -    addql    #TABLEDESC,%a1    /* base descriptor */
  1611. -    movel    #256,%d2     /* increment */
  1612. -    moveq    #(PAGE_TABLE_SIZE-1),%d1
  1613. +    addql    #_PAGE_TABLE,%a1    /* base descriptor */
  1614. +    movel    #PAGE_TABLE_SIZE<<2,%d2 /* increment */
  1615. +    moveq    #TABLENR_16MB-1,%d1
  1616.  
  1617.  1:    movel    %a1,%a0@+
  1618.      addl    %d2,%a1
  1619.      dbra    %d1,1b
  1620.  
  1621.      /* ensure that the root table points to the pointer table */
  1622. -    lea    %a5@(512),%a0
  1623. -    addql    #TABLEDESC,%a0
  1624. -    movel    %a0,%a4@(256)    /* 0x80000000>>(ROOT_INDEX_SHIFT-2) doesn't
  1625. -                   work */
  1626. +    movel    %a4,%a0
  1627. +    addql    #_PAGE_TABLE,%a0
  1628. +    movel    %a0,%a5@(0x40<<2)
  1629.  
  1630.      /*
  1631.       * initialize the page tables
  1632.       * descriptor bits include noncachable/serialized and global bits.
  1633.       */
  1634.      movel    %a3,%a0
  1635. -    movew    #(GLOBAL+CM_NONCACHE_SER+PAGEDESC),%a1
  1636. +    movew    #_PAGE_GLOBAL040+_PAGE_NOCACHE_S+_PAGE_PRESENT,%a1
  1637.      movel    #PAGESIZE,%d2
  1638. -    movew    #PAGESIZE-1,%d1
  1639. +    movew    #(PAGE_TABLE_SIZE*TABLENR_16MB)-1,%d1
  1640.  
  1641.  1:    movel    %a1,%a0@+
  1642.      addl    %d2,%a1
  1643. @@ -444,29 +462,20 @@
  1644.       * the virtual mapping of the 4 page tables indicates
  1645.       * noncachable/serialized.
  1646.       */
  1647. -    movel    %a3,%d0        /* ami page table start address */
  1648. -    lea    %pc@(SYMBOL_NAME(_stext)-PAGESIZE:w),%a0
  1649. -    subl    %a0,%d0        /* determine offset of root table page */
  1650. -    moveq    #PAGE_INDEX_SHIFT,%d1    /* determine offset into kernel page table */
  1651. -    lsrl    %d1,%d0
  1652. -    movel    %pc@(SYMBOL_NAME(kpt)),%a0
  1653. -    movel    #3,%d2
  1654. -1:    lea    %a0@(%d0:l:4),%a1
  1655. -    movel    %a1@,%d1
  1656. -    bclr    #5,%d1
  1657. -    bset    #6,%d1
  1658. -    movel    %d1,%a1@
  1659. -    addql    #1,%d0
  1660. -    dbra    %d2,1b
  1661. -
  1662. -    bra    Lmapphys
  1663. +    moveq    #3,%d0
  1664. +1:    movel    %a2@,%d1    /* a2 already points to root table offset */
  1665. +    andw    #_CACHEMASK040,%d1
  1666. +    orw    %d6,%d1
  1667. +    movel    %d1,%a2@+
  1668. +    dbra    %d0,1b
  1669.  
  1670. +    jra    Lmapphys
  1671.  
  1672. -Lnotami:    /* other machines specific mappings go here! */
  1673. +Lnotami:
  1674. +#endif
  1675.  
  1676. -    moveq    #MACH_ATARI,%d0
  1677. -    cmpl    %d4,%d0
  1678. -    bne    Lnotatari
  1679. +#ifdef CONFIG_ATARI
  1680. +    is_not_atari(Lnotatari)
  1681.  
  1682.      move.w    #PAGESIZE,%sp
  1683.  
  1684. @@ -490,7 +499,7 @@
  1685.  
  1686.      moveq    #0,%d3            /* base addr for others: 0x00000000 */
  1687.      movec    %d3,%vbr
  1688. -    lea        %pc@(Ltest_berr),%a0
  1689. +    lea    %pc@(Ltest_berr),%a0
  1690.      movel    %a0,0x8
  1691.      movel    %sp,%a0
  1692.      moveb    0x0,%d1
  1693. @@ -507,46 +516,45 @@
  1694.      movel    %d3,%a0@
  1695.  
  1696.      /* Let the root table point to the new pointer table */
  1697. -    lea    %a5@(512),%a0
  1698. -    addl    #TABLEDESC,%a0
  1699. -    movel    %a0,%a4@(508)        /* 0xFE000000 - 0xFFFFFFFF */
  1700. +    lea    %a4@(PTR_TABLE_SIZE<<2),%a4
  1701. +    movel    %a4,%a0
  1702. +    addl    #_PAGE_TABLE,%a0
  1703. +    movel    %a0,%a5@(0x7f<<2)       /* 0xFE000000 - 0xFFFFFFFF */
  1704.  
  1705.      /* clear lower half of the pointer table (0xfexxxxxx) */
  1706. -    lea     %a5@(512),%a0
  1707. -    movel    #0,%d0
  1708. -    movel    #63,%d2
  1709. -1:    movel    %d0,%a0@+
  1710. +    movel    %a4,%a0
  1711. +    movel    #(PTR_TABLE_SIZE/2)-1,%d2
  1712. +1:    clrl    %a0@+
  1713.      dbra    %d2,1b
  1714.  
  1715. -    btst    #BIT0460,%d6
  1716. -    bne    Lspata68040
  1717. +    is_040_or_060(Lspata68040)
  1718.  
  1719.  /* Mapping of the last 16M of virtual address space to the first 16M
  1720.     for efficient addressing of hardware registers */
  1721. -    movel    #0x40000,%d1
  1722. -    movel    #63,%d2
  1723. +    movel    #PAGE_TABLE_SIZE*PAGESIZE,%d1
  1724. +    movel    #(PTR_TABLE_SIZE/2)-1,%d2
  1725.      movel    %d3,%d0
  1726. -    addl    #PAGEDESC,%d0
  1727. +    addl    #_PAGE_PRESENT,%d0
  1728.  1:    movel    %d0,%a0@+
  1729.      addl    %d1,%d0
  1730.      dbra    %d2,1b
  1731. -    moveq    #0x40,%d0    /* make non-cachable */
  1732. -    addl    %d0,%a5@(1020)    /* 0xFFFC0000-0xFFFFFFFF (I/O space) */
  1733. +    moveq    #_PAGE_NOCACHE030,%d0    /* make non-cachable */
  1734. +    addl    %d0,%a4@(0x7f<<2)    /* 0xFFFC0000-0xFFFFFFFF (I/O space) */
  1735.  /* GK: 0xFFF00000-0xFFF3FFFF (IDE-bus) has to be non-cachable too */
  1736. -    addl    %d0,%a5@(1008)
  1737. +    addl    %d0,%a4@(0x7c<<2)
  1738.  
  1739. -    bra    Lmapphys
  1740. +    jra    Lmapphys
  1741.  
  1742.  Lspata68040:
  1743.      /* allocate 4 page tables */
  1744.      movel    %a6,%a3
  1745. -    addw    #(4*PAGESIZE),%a6
  1746. +    addw    #4*PAGESIZE,%a6
  1747.  
  1748. -/* Initialize the upper half of the pointer table (a0 is still valid) */
  1749. +    /* Initialize the upper half of the pointer table (a0 is still valid) */
  1750.      movel    %a3,%a1
  1751. -    addql    #TABLEDESC,%a1
  1752. -    movel    #256,%d2
  1753. -    moveq    #63,%d1
  1754. +    addql    #_PAGE_TABLE,%a1
  1755. +    movel    #PAGE_TABLE_SIZE<<2,%d2
  1756. +    moveq    #TABLENR_16MB-1,%d1
  1757.  1:    movel    %a1,%a0@+
  1758.      addl    %d2,%a1
  1759.      dbra     %d1,1b
  1760. @@ -554,9 +562,9 @@
  1761.      /* Initialize the page tables as noncacheable/serialized! */
  1762.      movel    %a3,%a0
  1763.      movel    %d3,%a1
  1764. -    addw    #(GLOBAL+CM_NONCACHE_SER+PAGEDESC),%a1
  1765. +    addw    #_PAGE_GLOBAL040+_PAGE_NOCACHE_S+_PAGE_PRESENT,%a1
  1766.      movel    #PAGESIZE,%d2
  1767. -    movew    #(PAGESIZE-1),%d1
  1768. +    movew    #(PAGE_TABLE_SIZE*TABLENR_16MB)-1,%d1
  1769.  1:    movel    %a1,%a0@+
  1770.      addl    %d2,%a1
  1771.      dbra    %d1,1b
  1772. @@ -566,23 +574,15 @@
  1773.       * the virtual mapping of the 4 page tables indicates
  1774.       * noncachable or write-through.
  1775.       */
  1776. -    movel    %a3,%d0        /* page table start address */
  1777. -    lea    %pc@(SYMBOL_NAME(_stext)-PAGESIZE:w),%a0
  1778. -    subl    %a0,%d0        /* determine offset of root table page */
  1779. -    moveq    #PAGE_INDEX_SHIFT,%d1 /* determine offset into 
  1780. -                                         kernel page table */
  1781. -    lsrl    %d1,%d0
  1782. -    movel    %pc@(SYMBOL_NAME(kpt)),%a0
  1783. -    moveq    #3,%d2
  1784. -1:    lea    %a0@(%d0:l:4),%a1
  1785. -    movel    %a1@,%d1
  1786. -    andl    #CM_MASK,%d1
  1787. +    moveq    #3,%d0
  1788. +1:    movel    %a2@,%d1    /* a2 already points to root table offset */
  1789. +    andw    #_CACHEMASK040,%d1
  1790.      orw    %d6,%d1
  1791. -    movel    %d1,%a1@
  1792. -    addql    #1,%d0
  1793. -    dbra    %d2,1b
  1794. +    movel    %d1,%a2@+
  1795. +    dbra    %d0,1b
  1796.  
  1797.  Lnotatari:
  1798. +#endif
  1799.  
  1800.  /*
  1801.   * Setup a transparent mapping of the physical memory we are executing in.
  1802. @@ -591,225 +591,180 @@
  1803.   * an Amiga since the first 16M is already identity mapped on the Amiga.
  1804.   */
  1805.  Lmapphys:
  1806. -    moveq    #'J',%d7
  1807. -    jbsr    Lserial_putc
  1808. -
  1809. -    clrl    %d5        /* indicate that no cleanup is required */
  1810. +    putc('J')
  1811.  
  1812. -    cmpl    #MACH_AMIGA,%d4
  1813. -    bne    Lmapphysnotamiga    /* other machines will probably have
  1814. -                     * to put in code and jump to it here
  1815. -                     */
  1816. +#ifdef CONFIG_AMIGA
  1817. +    is_not_amiga(Lmapphysnotamiga)
  1818.  
  1819.  /*
  1820. - * The virtual address of the start of the kernel is 0x1000.  On ALL
  1821. - * Amigas, there is CHIP RAM in this area.  Hence we will copy the MMU
  1822. - * enabling code to CHIP RAM (to the same physical address as the kernel
  1823. - * virtual address) and jump to it.  When the MMU is enabled, we will be
  1824. - * running from the code in the kernel virtual space, rather than the
  1825. - * physical space.
  1826. + * The virtual address of the start of the kernel is 0x1000. We transparently
  1827. + * translate the memory where we running in and can enable then the MMU. Hence
  1828. + * we have now two locations of the kernel in memory and can jump to the final
  1829. + * place. Except if the physical location is in the first 16MB, translation
  1830. + * will overlap later virtual location, but as we already mapped the first
  1831. + * 16MB to 0x80000000, we can jump there after translation and MMU is enabled
  1832. + * and then we can switch off translation and go to the final place.
  1833. + * When MMU is enabled, stack pointer and Lcustom will become again valid and
  1834. + * points to the unused first page.
  1835.   */
  1836.  
  1837.  /*
  1838.   * Setup Supervisor Root Pointer register to point to page directory,
  1839.   * setup translation register contents and enable translation.
  1840.   */
  1841. -    btst    #BIT0460,%d6
  1842. -    bne    Lamimmu68040
  1843. +    putc('K')
  1844.  
  1845. -    moveq    #'K',%d7
  1846. -    jbsr    Lserial_putc
  1847. +    movew    #PAGESIZE,%sp
  1848. +
  1849. +    /* fixup the Amiga custom register location before printing */
  1850. +    lea    %pc@(Lcustom),%a0
  1851. +    movel    #0x80000000,%a0@
  1852.  
  1853. -    lea    %pc@(mmu),%a0
  1854. -    movel    #0x80000002,%a0@   /* no limit, 4byte descriptors */
  1855. -    movel    %a4,%a0@(4)
  1856. -    pmove    %a0@,%srp
  1857. -    pmove    %a0@,%crp
  1858. +    is_040_or_060(Lamimmu68040)
  1859. +
  1860. +    lea    2f:w,%a0
  1861. +    movel    %d5,%d0
  1862. +    andl    #0xff000000,%d0
  1863. +    jne    1f
  1864. +    lea    %pc@(2f+0x80000000),%a0
  1865. +1:    orw    #TTR_ENABLE+TTR_CI+TTR_RWM+TTR_FCB2+TTR_FCM1+TTR_FCM0,%d0
  1866. +    lea    %pc@(Lmmu),%a3
  1867. +    movel    %d0,%a3@
  1868. +    .long    0xf0130800    /* pmove %a3@,%tt0 */
  1869. +    /* no limit, 4byte descriptors */
  1870. +    movel    #0x80000002,%a3@
  1871. +    movel    %a5,%a3@(4)
  1872. +    .long    0xf0134800    /* pmove %a3@,%srp */
  1873. +    .long    0xf0134c00    /* pmove %a3@,%crp */
  1874. +    .long    0xf0002400    /* pflusha */
  1875.      /*
  1876.       * enable,super root enable,4096 byte pages,7 bit root index,
  1877.       * 7 bit pointer index, 6 bit page table index.
  1878.       */
  1879. -    movel    #0x82c07760,%a0@
  1880. -
  1881. -    /* setup registers for jumping MMU enabling code */
  1882. -    lea    %pc@(Ldoit030ami),%a2
  1883. -    lea    Ldoit030ami,%a1
  1884. -
  1885. -    moveq    #CR,%d7
  1886. -    jbsr    Lserial_putc
  1887. -    moveq    #LF,%d7
  1888. -    jbsr    Lserial_putc
  1889. -    movel    %a2,%d7
  1890. -    jbsr    Lserial_putnum
  1891. -    moveq    #' ',%d7
  1892. -    jbsr    Lserial_putc
  1893. -    movel    %a1,%d7
  1894. -    jbsr    Lserial_putnum
  1895. -
  1896. -    bra    LdoitAmiga
  1897. -
  1898. -#ifdef __ELF__
  1899. -    .align    16
  1900. -#else
  1901. -    .align    4
  1902. -#endif
  1903. -Ldoit030ami:
  1904. -    pmove    %a0@,%tc    /* enable the MMU */
  1905. -    jra    LdoneMMUenable    /* branch to continuation of startup */
  1906. +    movel    #0x82c07760,%a3@
  1907. +    .long    0xf0134000    /* pmove %a3@,%tc (enable the MMU) */
  1908. +    jmp    %a0@
  1909. +2:    clrl    %a3@
  1910. +    .long    0xf0130800    /* pmove %a3@,%tt0 */
  1911. +    jmp    LdoneMMUenable:w
  1912.  
  1913.  Lamimmu68040:
  1914. -    moveq    #'L',%d7
  1915. -    jbsr    Lserial_putc
  1916. -    
  1917. -    .word    0xf4d8        /* CINVA I/D */
  1918. -    .word    0xf518        /* pflusha    */
  1919. -    .long    0x4e7bc807    /* movec a4,srp */
  1920. -    .long    0x4e7bc806    /* movec a4,urp */
  1921. -    movel    #(TC_ENABLE+TC_PAGE4K),%d0
  1922. -
  1923. -    /* setup registers for jumping MMU enabling code */
  1924. -    lea    Ldoit040ami,%a1
  1925. -    lea    %pc@(Ldoit040ami),%a2
  1926. -    bra    LdoitAmiga
  1927. -
  1928. -#ifdef __ELF__
  1929. -    .align    16
  1930. -#else
  1931. -    .align    4
  1932. -#endif
  1933. -Ldoit040ami:
  1934. -    .long    0x4e7b0003    /* movec d0,tc  (enable the MMU) */
  1935. -    jra    LdoneMMUenable    /* branch to continuation of startup */
  1936. -
  1937. -LdoitAmiga:
  1938. -    /* copy the appropriate code (two longwords) to chipmem */
  1939. -    movel    %a2@,%a1@
  1940. -    movel    %a2@(4),%a1@(4)
  1941.  
  1942. +    lea    2f:w,%a0
  1943. +    movel    %d5,%d0
  1944. +    andl    #0xff000000,%d0
  1945. +    jne    1f
  1946. +    lea    %pc@(2f+0x80000000),%a0
  1947. +1:    orw    #TTR_ENABLE+TTR_KERNELMODE+_PAGE_NOCACHE_S,%d0
  1948. +    .long    0x4e7b0004    /* movec %d0,%itt0 */
  1949. +    .long    0x4e7bd806    /* movec %a5,%urp */
  1950. +    .long    0x4e7bd807    /* movec %a5,%srp */
  1951. +    .word    0xf518        /* pflusha */
  1952. +    movel    #TC_ENABLE+TC_PAGE4K,%d0
  1953.      /*
  1954. -      * save physaddr of phys mem in register a3
  1955. +     * this value is also ok for the 68060, we don`t use the cache
  1956. +     * mode/protection defaults
  1957.       */
  1958. -    lea    %pc@(SYMBOL_NAME(_stext)-PAGESIZE:w),%a3
  1959. -
  1960. -    /* jump to the physical address in chipmem */
  1961. -    jmp    %a1@
  1962. +    .long    0x4e7b0003    /* movec %d0,%tc (enable the MMU) */
  1963. +    jmp    %a0@
  1964. +2:    moveq    #0,%d0
  1965. +    .long    0x4e7b0004    /* movec %d0,%itt0 */
  1966. +    jmp    LdoneMMUenable:w
  1967.  
  1968.  Lmapphysnotamiga:
  1969. +#endif
  1970.  
  1971. -    cmpl    #MACH_ATARI,%d4
  1972. -    bne    Lmapphysnotatari
  1973. +#ifdef CONFIG_ATARI
  1974. +    is_not_atari(Lmapphysnotatari)
  1975.  
  1976. -    lea    %pc@(SYMBOL_NAME(_stext)-PAGESIZE),%a0
  1977. -    tstl    %a0
  1978. -    jeq    Lnophys2
  1979. -
  1980. -    /* The kernel physical address is different from its virtual
  1981. -       address.  Temporarily set up an identity mapping of the
  1982. -       16MB chunk where the kernel is executing. */
  1983. -  
  1984. -    /* 680[46]0? */
  1985. -    btst    #BIT0460,%d6
  1986. -    jeq    1f
  1987. -
  1988. -    /*
  1989. -     * For the 68040, we will use the transparent translation
  1990. -     * registers to identity map the 16M chunk that contains
  1991. -     * the physical memory.
  1992. -     */
  1993. -    movel    %a0,%d2
  1994. -    andl    #0xff000000,%d2        /* logical address base */
  1995. -    orw    #0xc040,%d2        /* add in magic bits */
  1996. -    .long    0x4e7b2004        /* movec d2,ittr0 */
  1997. -    .long    0x4e7b2006        /* movec d2,dttr0 */
  1998. -
  1999. -    /* d5 is kept 0 to do no cleanup. This didn't work in head.S, I don't
  2000. -     * know why... The transparent translation is turned off in
  2001. -     * atari/config.c instead.
  2002. -     */
  2003. -    jra    Lnophys2
  2004. +/*
  2005. + * If the kernel physical address is different from its virtual address, we
  2006. + * will temporarily set up an identity mapping of the 16MB chunk with
  2007. + * transparent translation where the kernel is executing.
  2008. + */
  2009. +    putc('L')
  2010.  
  2011. -    /* Transparent translation for the 68030 via transparent translation
  2012. -       register */
  2013. +    /* fixup the  Atari iobase register location before printing */
  2014. +    lea    %pc@(Liobase),%a0
  2015. +    movel    #0xff000000,%a0@
  2016.  
  2017. -1:
  2018. -    /* cleanup is needed; note it */
  2019. -    moveq    #1,%d5
  2020. +    is_040_or_060(Latarimmu68040)
  2021.  
  2022. +    lea    %pc@(Lmmu),%a3
  2023. +    movel    %d5,%d0
  2024. +    jne    1f
  2025. +    lea    LdoneMMUenable:w,%a0
  2026. +    jra    3f
  2027. +1:    lea    4f:w,%a0
  2028. +    andl    #0xff000000,%d0 /* logical address base */
  2029. +    jeq    2f
  2030. +    orw    #TTR_ENABLE+TTR_CI+TTR_RWM+TTR_FCB2+TTR_FCM1+TTR_FCM0,%d0
  2031. +    movel    %d0,%a3@
  2032. +    .long    0xf0130800    /* pmove %a3@,%tt0 */
  2033. +    jra    3f
  2034.      /* tt0 doesn't work if physical and virtual address of kernel is in
  2035.       * the same 16M area (Falcon with Magnum/FX, kernel in alternate ram)
  2036. -     */
  2037. -    movel    %a0,%d2
  2038. -    andl    #0xff000000,%d2        /* logical address base */
  2039. -    jeq    1f
  2040. -    orw    #0x8143,%d2        /* add in magic bits */
  2041. -    lea    %pc@(mmu),%a0
  2042. -    movel    %d2,%a0@
  2043. -    pmove    %a0@,%tt0
  2044. -    jra    Lnophys2
  2045. -1:
  2046. -    /* Transparent translation through kernel pointer table
  2047. +     * Transparent translation through kernel pointer table
  2048.       * Requires that this code until after MMU enabling lies in
  2049. -     * the 256K page around %a0
  2050. +     * the 256K page around %d5
  2051.       */
  2052. -    movel    %a0,%d2
  2053. -    moveq    #ROOT_INDEX_SHIFT,%d1
  2054. -    lsrl    %d1,%d2
  2055. -    movel    %a4@(%d2:l:4),%d0
  2056. -    andw    #0xfff0,%d0
  2057. -    movel    %d0,%a1
  2058. -    movel    %a0,%d2
  2059. -    andl    #0x01ffffff,%d2
  2060. -    moveq    #(ROOT_INDEX_SHIFT-7),%d1
  2061. -    lsrl    %d1,%d2
  2062. -    movel    %a0,%d0
  2063. -    addql    #PAGEDESC,%d0
  2064. -    movel    %a1@(%d2:l:4),%a2    /* save old_entry */
  2065. -    movel    %d0,%a1@(%d2:l:4)
  2066. -
  2067. -Lnophys2:
  2068. -    /*
  2069. -      * save physaddr of phys mem in register a3
  2070. -     */
  2071. -    lea    %pc@(SYMBOL_NAME(_stext)-PAGESIZE:w),%a3
  2072. -
  2073. -    btst    #BIT0460,%d6
  2074. -    jne    Latarimmu68040
  2075. -
  2076. -    moveq    #'K',%d7
  2077. -    jbsr    Lserial_putc
  2078. -
  2079. -    lea    %pc@(mmu),%a0
  2080. -    movel    #0x80000002,%a0@   /* no limit, 4byte descriptors */
  2081. -    movel    %a4,%a0@(4)
  2082. -    pmove    %a0@,%srp
  2083. -    pmove    %a0@,%crp
  2084. +2:    movel    %a4@,%d1
  2085. +    andw    #0xfff0,%d1
  2086. +    movel    %d1,%a1
  2087. +    movel    %d5,%d1
  2088. +    moveq    #PTR_INDEX_SHIFT,%d0
  2089. +    lsrl    %d0,%d1
  2090. +    lea    %a1@(%d1:l:4),%a1
  2091. +    movel    %d5,%d1
  2092. +    addql    #_PAGE_PRESENT,%d1
  2093. +    movel    %a1@,%d2
  2094. +    movel    %d1,%a1@
  2095. +    lea    5f:w,%a0
  2096. +    /* no limit, 4byte descriptors */
  2097. +3:    movel    #0x80000002,%a3@
  2098. +    movel    %a5,%a3@(4)
  2099. +    .long    0xf0134800    /* pmove %a3@,%srp */
  2100. +    .long    0xf0134c00    /* pmove %a3@,%crp */
  2101. +    .long    0xf0002400    /* pflusha */
  2102.      /*
  2103.       * enable,super root enable,4096 byte pages,7 bit root index,
  2104.       * 7 bit pointer index, 6 bit page table index.
  2105.       */
  2106. -    movel    #0x82c07760,%a0@
  2107. -    pmove    %a0@,%tc        /* enable the MMU */
  2108. -
  2109. -    /* Jump to the virtual address of continuation of startup. */
  2110. -    jmp    LdoneMMUenable
  2111. +    movel    #0x82c07760,%a3@
  2112. +    .long    0xf0134000    /* pmove %a3@,%tc (enable the MMU) */
  2113. +    jmp    %a0@
  2114. +4:    clrl    %a3@
  2115. +    .long    0xf0130800    /* pmove %a3@,%tt0 */
  2116. +    jra    LdoneMMUenable
  2117. +5:    movel    %d2,%a1@
  2118. +    jra    LdoneMMUenable
  2119.  
  2120.  Latarimmu68040:
  2121. -    moveq    #'L',%d7
  2122. -    jbsr    Lserial_putc
  2123. -
  2124. -    .word    0xf4d8        /* CINVA I/D */
  2125. -    .word    0xf518        /* pflusha    */
  2126. -    .long    0x4e7bc807    /* movec a4,srp */
  2127. -    .long    0x4e7bc806    /* movec a4,urp */
  2128. -    movel    #(TC_ENABLE+TC_PAGE4K),%d0
  2129. -    /* this value is also ok for the '060, we don't use the cache
  2130. -     * mode/protection defaults */
  2131. -    .long    0x4e7b0003    /* movec d0,tc  (enable the MMU) */
  2132. -    jmp    LdoneMMUenable    /* jump to virtual address of
  2133. -                   continuation of startup */
  2134. +    movel    %d5,%d0
  2135. +    jne    1f
  2136. +    lea    LdoneMMUenable:w,%a0
  2137. +    jra    2f
  2138. +1:    lea    3f:w,%a0
  2139. +    andl    #0xff000000,%d0 /* logical address base */
  2140. +    orw    #TTR_ENABLE+TTR_KERNELMODE+_PAGE_NOCACHE_S,%d0
  2141. +    .long    0x4e7b0004    /* movec %d0,%itt0 */
  2142. +2:    .word    0xf518        /* pflusha */
  2143. +    .long    0x4e7bd807    /* movec %a5,%srp */
  2144. +    .long    0x4e7bd806    /* movec %a5,%urp */
  2145. +    movel    #TC_ENABLE+TC_PAGE4K,%d0
  2146. +    /*
  2147. +     * this value is also ok for the 68060, we don`t use the cache
  2148. +     * mode/protection defaults
  2149. +     */
  2150. +    .long    0x4e7b0003    /* movec %d0,%tc (enable the MMU) */
  2151. +    jmp    %a0@
  2152. +3:    moveq    #0,%d0
  2153. +    .long    0x4e7b0004    /* movec %d0,%itt0 */
  2154. +    tstl    %a1
  2155. +    jra    LdoneMMUenable
  2156.  
  2157.  Lmapphysnotatari:
  2158. -
  2159. +#endif
  2160.  
  2161.  LdoneMMUenable:
  2162.  
  2163. @@ -818,128 +773,72 @@
  2164.   * Convert them from physical addresses to virtual addresses.
  2165.   */
  2166.  
  2167. -    /*
  2168. -     * fixup the Amiga custom register location before printing
  2169. -     */
  2170. -    addl    #0x80000000,Lcustom
  2171. -
  2172. -    /* The same for the Atari */
  2173. -    movel    #0xff000000,Liobase
  2174. -
  2175. -    moveq    #'M',%d7
  2176. -    jbsr    Lserial_putc
  2177. +    putc('M')
  2178.  
  2179.      /*
  2180. -     * a3 contains physaddr of kernel start
  2181. +     * d5 contains physaddr of kernel start
  2182.       */
  2183. -    movel    SYMBOL_NAME(kpt),%d1
  2184. -    subl    %a3,%d1
  2185. -    movel    %d1,SYMBOL_NAME(kpt)
  2186. +    subl    %d5,SYMBOL_NAME(kpt)
  2187.  
  2188.      /*
  2189.       * do the same conversion on the first available memory
  2190.       * address (in a6).
  2191.       */
  2192. -    subl    %a3,%a6
  2193. -
  2194. -    /* Allocate a page to be used by get_kpointer_table.  */
  2195. -    movel    %a6,SYMBOL_NAME(kernel_pmd_table)
  2196. -    addl    #PAGESIZE,%a6
  2197. +    subl    %d5,%a6
  2198.      movel    %a6,SYMBOL_NAME(availmem) /* first available memory address */
  2199.  
  2200. -    moveq    #'N',%d7
  2201. -    jbsr    Lserial_putc
  2202. -
  2203. -    /*
  2204. -     * Clean up the temporary physical mapping (if necessary)
  2205. -     */
  2206. -
  2207. -    tstl    %d5
  2208. -    jeq    Lnoclean
  2209. -
  2210. -    btst    #BIT0460,%d6
  2211. -    jne    Loff040
  2212. -
  2213. -    /* clean up physical identity mapping for 68020/68030 */
  2214. -    /* Is this needed for the Amiga anymore? */
  2215. -    /* it's not in 1.2.13pl6 - Jes */
  2216. -    cmpl    #MACH_AMIGA,%d4
  2217. -    jeq    Lclean030
  2218. -    cmpl    #MACH_ATARI,%d4
  2219. -    jne    Lnoclean
  2220. -
  2221. -    movel    %a3,%d2
  2222. -    andl    #0xff000000,%d2
  2223. -    jeq    1f
  2224. -    /* clear transparent translation register */
  2225. -    lea    %pc@(mmu),%a0
  2226. -    clrl    %a0@
  2227. -    pmove    %a0@,%tt0
  2228. -    jra    Lnoclean
  2229. -1:
  2230. -    movel    %a3,%d2
  2231. -    moveq    #ROOT_INDEX_SHIFT,%d1
  2232. -    lsrl    %d1,%d2
  2233. -    movel    %a4@(%d2:l:4),%d0
  2234. -    andw    #0xfff0,%d0
  2235. -    subl    %a3,%d0        /* to virtual address */
  2236. -    movel    %d0,%a0
  2237. -    movel    %a3,%d2
  2238. -    andl    #0x01ffffff,%d2
  2239. -    moveq    #(ROOT_INDEX_SHIFT-7),%d1
  2240. -    lsrl    %d1,%d2
  2241. -    movel    %a2,%a0@(%d2:l:4)    /* restore old entry */
  2242. -    jra    Lnoclean
  2243. -
  2244. -Lclean030:
  2245. -    movel    %a0,%d2        /* a0 contains physical start address */
  2246. -    moveq    #25,%d3        /* find appropriate index in root table */
  2247. -    lsrl    %d3,%d2
  2248. -    moveq    #0,%d0
  2249. -    movel    %d0,%a4@(%d2:l:4)  /* clear descriptor */
  2250. -
  2251. -    jra    Lnoclean
  2252. -
  2253. -Loff040:
  2254. -    /* turn off transparent translation registers for '0[46]0 */
  2255. -    moveq    #0,%d0
  2256. -    .long    0x4e7b0004    /* movec d0,ittr0 */
  2257. -    .long    0x4e7b0006    /* movec d0,dttr0 */
  2258. -
  2259. -Lnoclean:
  2260. -    moveq    #'O',%d7
  2261. -    jbsr    Lserial_putc
  2262. -
  2263. +    putc('N')
  2264.  
  2265. +#if 0
  2266. +    putr()
  2267. +    lea    SYMBOL_NAME(kernel_pmd_table),%a0
  2268. +    moveq    #63,%d0
  2269. +1:    moveq    #7,%d1
  2270. +    putn(%a0)
  2271. +    putc(':')
  2272. +    putc(' ')
  2273. +2:    putn(%a0@+)
  2274. +    dbra    %d1,2b
  2275. +    putr()
  2276. +    dbra    %d0,1b
  2277. +    putr()
  2278. +    movel    SYMBOL_NAME(kpt),%a0
  2279. +    moveq    #639,%d0
  2280. +1:    moveq    #7,%d1
  2281. +    putn(%a0)
  2282. +    putc(':')
  2283. +    putc(' ')
  2284. +2:    putn(%a0@+)
  2285. +    dbra    %d1,2b
  2286. +    putr()
  2287. +    dbra    %d0,1b
  2288. +#endif
  2289.  /*
  2290.   * Enable caches
  2291.   */
  2292. -    btst    #BIT0460,%d6
  2293. -    jne    Lcache680460
  2294. +    is_040_or_060(Lcache680460)
  2295.  
  2296. -    movel    #0x00001919,%d0
  2297. -    movec   %d0,%cacr
  2298. +    movel    #CC3_ENABLE_DB+CC3_CLR_D+CC3_ENABLE_D+CC3_ENABLE_IB+CC3_CLR_I+CC3_ENABLE_I,%d0
  2299. +    movec    %d0,%cacr
  2300.      jra    1f
  2301.  
  2302.  Lcache680460:
  2303. -    btst    #BIT060,%d6
  2304. -    jne    Lcache68060
  2305. +    .word    0xf4f8        /* cpusha %bc */
  2306.  
  2307. -    .word    0xf4d8         /* CINVA I/D */
  2308. -    movel    #I_ENABLE+D_ENABLE,%d0
  2309. +    is_060(Lcache68060)
  2310. +
  2311. +    movel    #CC6_ENABLE_D+CC6_ENABLE_I,%d0
  2312.      /* MMU stuff works in copyback mode now, so enable the cache */
  2313.      movec    %d0,%cacr
  2314.      jra    1f
  2315.  
  2316.  Lcache68060:
  2317. -    .word    0xf4d8         /* CINVA I/D */
  2318. -    movel    #I_ENABLE+D_ENABLE+SB_ENABLE+PUSH_DPI+BC_ENABLE+BC_CLRA,%d0
  2319. +    movel    #CC6_ENABLE_D+CC6_ENABLE_I+CC6_ENABLE_SB+CC6_PUSH_DPI+CC6_ENABLE_B+CC6_CLRA_B,%d0
  2320.      /* MMU stuff works in copyback mode now, so enable the cache */
  2321.      movec    %d0,%cacr
  2322.      /* enable superscalar dispatch in PCR */
  2323.      moveq    #1,%d0
  2324.      .long    0x4e7b0808    /* movec d0,pcr */
  2325. -
  2326.  1:
  2327.  
  2328.  /*
  2329. @@ -948,40 +847,35 @@
  2330.      lea    SYMBOL_NAME(init_user_stack)+PAGESIZE,%sp
  2331.  
  2332.  /* jump to the kernel start */
  2333. +    putr()
  2334.  
  2335.      jbsr    SYMBOL_NAME(start_kernel)
  2336.  
  2337. -#if 0
  2338. -tmp_fault_handler:
  2339. -     lea       %pc@(tfh_1st_str),%a0
  2340. -     jbsr       Lserial_puts
  2341. -     move.l    %sp@(2),%d7                     /* PC */
  2342. -     jbsr       Lserial_putnum
  2343. -     move.w    %sp@(0xa),%d7
  2344. -     swap      %d7
  2345. -     move.w    %sp@(0x6),%d7
  2346. -     jbsr       Lserial_putnum
  2347. -     lea       %pc@(tfh_2nd_str),%a0
  2348. -     jbsr       Lserial_puts
  2349. -     move.l    %sp@(0x10),%d7                  /* Fault address */
  2350. -     jbsr       Lserial_putnum
  2351. -     moveq     #CR,%d7
  2352. -     jbsr       Lserial_putc
  2353. -     moveq     #LF,%d7
  2354. -     jbsr       Lserial_putc
  2355. -1:   jra       1b
  2356. -
  2357. -tfh_1st_str:
  2358. -     .byte     CR
  2359. -     .byte     LF
  2360. -     .ascii    "Access fault occurred. PC = "
  2361. -     .byte     0
  2362. -
  2363. -tfh_2nd_str:
  2364. -     .byte     CR
  2365. -     .byte     LF
  2366. -     .ascii    "FaultAddress = "
  2367. -     .byte     0
  2368. +/*
  2369. + * switch off mmu and exit
  2370. + */
  2371. +
  2372. +#ifdef HACKER_KERNEL
  2373. +ENTRY(kernel_exit)
  2374. +    lea    2f:w,%a0
  2375. +    movel    %pc@(Lkernel_start),%a0
  2376. +    lea    %a0@(2f:w),%a1
  2377. +    movel    %a1,%d0
  2378. +    andl    #0xff000000,%d0
  2379. +    jne    1f
  2380. +    jmp    %a0@(1f+0x80000000)
  2381. +1:    orw    #TTR_ENABLE+TTR_KERNELMODE+_PAGE_NOCACHE_S,%d0
  2382. +    .long    0x4e7b0004    /* movec %d0,%itt0 */
  2383. +    jmp    %a1@
  2384. +2:    moveq    #0,%d0
  2385. +    .long    0x4e7b0003    /* movec %d0,%tc (disable the MMU) */
  2386. +    .word    0xf518        /* pflusha */
  2387. +    .long    0x4e7b0004    /* movec %d0,%itt0 */
  2388. +    movec    %d0,%cacr
  2389. +    .word    0xf4f8        /* cpusha %bc */
  2390. +
  2391. +    lea    %pc@(SYMBOL_NAME(boot_info)),%a0
  2392. +    jmp    %a0@(BI_amiga_exit_func:w)@(0:w)
  2393.  #endif
  2394.  
  2395.  /*
  2396. @@ -991,7 +885,7 @@
  2397.  LSERDAT      = 0xdff030
  2398.  LSERDATR     = 0xdff018
  2399.  LNTSC_PERIOD = 371
  2400. -LPAL_PERIOD  = 368/2        /* /2 for 19200 baud */
  2401. +LPAL_PERIOD  = 368
  2402.  LNTSC_ECLOCK = 7159090
  2403.  LSERIAL_CNTRL = 0xbfd000
  2404.  LSERIAL_DTR   = 7
  2405. @@ -1002,6 +896,7 @@
  2406.   * from the MFP or a serial port of the SCC
  2407.   */
  2408.  
  2409. +#ifdef CONFIG_ATARI
  2410.  /* #define USE_PRINTER */
  2411.  /* #define USE_SCC */
  2412.  #define USE_MFP
  2413. @@ -1048,6 +943,7 @@
  2414.  LMFP_UDR     = 0xfffa2f
  2415.  
  2416.  #endif
  2417. +#endif
  2418.  
  2419.  /*
  2420.   * Initialize serial port hardware for 9600/8/1
  2421. @@ -1056,16 +952,21 @@
  2422.   */
  2423.      .even
  2424.  Lserial_init:
  2425. +#ifdef CONFIG_AMIGA
  2426.      cmpil    #MACH_AMIGA,%d4
  2427.      jne    1f
  2428. +    lea    %pc@(SYMBOL_NAME(boot_info)),%a0
  2429.      bclr    #LSERIAL_DTR,LSERIAL_CNTRL
  2430.      movew    #LNTSC_PERIOD,LSERPER
  2431. -    cmpl    #LNTSC_ECLOCK,%a0@(BI_AMIGA_ECLK)
  2432. +    cmpl    #LNTSC_ECLOCK,%a0@(BI_amiga_eclock)
  2433.      jeq    9f
  2434.      movew    #LPAL_PERIOD,LSERPER
  2435.      jra    9f
  2436. -1:    cmpil   #MACH_ATARI,%d4
  2437. -    jne    9f
  2438. +1:
  2439. +#endif
  2440. +#ifdef CONFIG_ATARI
  2441. +    cmpil   #MACH_ATARI,%d4
  2442. +    jne    4f
  2443.  #ifdef USE_PRINTER
  2444.      bclr    #0,LSTMFP_IERB
  2445.      bclr    #0,LSTMFP_DDR
  2446. @@ -1094,6 +995,8 @@
  2447.      orb    #1,LMFP_TDCDR
  2448.      bset    #1,LMFP_TSR
  2449.  #endif
  2450. +4:
  2451. +#endif
  2452.  9:
  2453.      rts
  2454.  
  2455. @@ -1103,6 +1006,7 @@
  2456.   */
  2457.  Lserial_putc:
  2458.      moveml    %a0/%a1,%sp@-
  2459. +#ifdef CONFIG_AMIGA
  2460.      cmpil    #MACH_AMIGA,%d4
  2461.      jne    2f
  2462.      andw    #0x00ff,%d7
  2463. @@ -1113,8 +1017,11 @@
  2464.      andw    #0x2000,%d7
  2465.      jeq    1b
  2466.      jra    9f
  2467. -2:    cmpil   #MACH_ATARI,%d4
  2468. -    jne    9f
  2469. +2:
  2470. +#endif
  2471. +#ifdef CONFIG_ATARI
  2472. +    cmpil   #MACH_ATARI,%d4
  2473. +    jne    4f
  2474.      movel    %pc@(Liobase),%a1
  2475.  #ifdef USE_PRINTER
  2476.  3:    btst    #0,%a1@(LSTMFP_GPIP)
  2477. @@ -1138,6 +1045,8 @@
  2478.      jeq    3b
  2479.      moveb    %d7,%a1@(LMFP_UDR)
  2480.  #endif
  2481. +4:
  2482. +#endif
  2483.  9:
  2484.      moveml    %sp@+,%a0/%a1
  2485.      rts
  2486. @@ -1170,7 +1079,7 @@
  2487.      moveb    %d1,%d7
  2488.      andb    #0x0f,%d7
  2489.      cmpb    #0x0a,%d7
  2490. -    bccs    1f
  2491. +    jcc    1f
  2492.      addb    #'0',%d7
  2493.      jra    2f
  2494.  1:    addb    #'A'-10,%d7
  2495. @@ -1180,79 +1089,46 @@
  2496.      jbsr    Lserial_putc
  2497.      moveml    %sp@+,%d0-%d2/%d7
  2498.      rts
  2499. -#if 0
  2500. -.globl showtest
  2501. -showtest:
  2502. -    moveml    %a1/%d7,%sp@-
  2503. -    moveq    #'A',%d7
  2504. -    jbsr    Lserial_putc
  2505. -    moveq    #'=',%d7
  2506. -    jbsr    Lserial_putc
  2507. -    movel    %a0,%d7
  2508. -    jbsr    Lserial_putnum
  2509. -
  2510. -    ptestr    #5,%a0@,#7,%a1
  2511. -
  2512. -    moveq    #'D',%d7
  2513. -    jbsr    Lserial_putc
  2514. -    moveq    #'A',%d7
  2515. -    jbsr    Lserial_putc
  2516. -    moveq    #'=',%d7
  2517. -    jbsr    Lserial_putc
  2518. -
  2519. -    movel    %a1,%d7
  2520. -    jbsr    Lserial_putnum
  2521. -
  2522. -    moveq    #'D',%d7
  2523. -    jbsr    Lserial_putc
  2524. -    moveq    #'=',%d7
  2525. -    jbsr    Lserial_putc
  2526. -    movel    %a1@,%d7
  2527. -    jbsr    Lserial_putnum
  2528.  
  2529. -    moveq    #'S',%d7
  2530. -    jbsr    Lserial_putc
  2531. -    moveq    #'=',%d7
  2532. -    jbsr    Lserial_putc
  2533. -
  2534. -    lea    %pc@(mmu),%a1
  2535. -    pmove    %psr,%a1@
  2536. +Lshowtest:
  2537. +    moveml    %a0/%d7,%sp@-
  2538. +    putc('A')
  2539. +    putc('=')
  2540. +    putn(%a1)
  2541. +
  2542. +    ptestr    #5,%a1@,#7,%a0
  2543. +
  2544. +    putc('D')
  2545. +    putc('A')
  2546. +    putc('=')
  2547. +    putn(%a0)
  2548. +
  2549. +    putc('D')
  2550. +    putc('=')
  2551. +    putn(%a0@)
  2552. +
  2553. +    putc('S')
  2554. +    putc('=')
  2555. +    lea    %pc@(Lmmu),%a0
  2556. +    pmove    %psr,%a0@
  2557.      clrl    %d7
  2558. -    movew    %a1@,%d7
  2559. +    movew    %a0@,%d7
  2560.      jbsr    Lserial_putnum
  2561.  
  2562. -    moveq    #CR,%d7
  2563. -    jbsr    Lserial_putc
  2564. -    moveq    #LF,%d7
  2565. -    jbsr    Lserial_putc
  2566. -
  2567. -    moveml    %sp@+,%a1/%d7
  2568. +    putr()
  2569. +    moveml    %sp@+,%a0/%d7
  2570.      rts
  2571. -#endif
  2572. -
  2573. -#ifdef __ELF__
  2574. -    .align 512
  2575. -#else
  2576. -    .align 9
  2577. -#endif            /*
  2578. -             * MMU root-pointers need to be 512-byte
  2579. -             * aligned on the 680[46]0 - Jes
  2580. -             */
  2581. -
  2582. -SYMBOL_NAME_LABEL(swapper_pg_dir)
  2583. -    .skip ROOT_TABLE_SIZE * 4
  2584. -SYMBOL_NAME_LABEL(kernel_pg_dir)
  2585. -    .skip ROOT_TABLE_SIZE * 4
  2586.  
  2587.      .data
  2588.      .even
  2589. -Lcustom:
  2590. +#ifdef HACKER_KERNEL
  2591. +Lkernel_start:
  2592.      .long 0
  2593. +#endif
  2594. +Lcustom:
  2595.  Liobase:
  2596.      .long 0
  2597. -mmu:    .quad 0
  2598. -SYMBOL_NAME_LABEL(kernel_pmd_table)
  2599. -    .long 0
  2600. +Lmmu:    .quad 0
  2601.  SYMBOL_NAME_LABEL(kpt)
  2602.      .long 0
  2603.  SYMBOL_NAME_LABEL(availmem)
  2604. diff -u --recursive --new-file pre2.0.4/linux/arch/m68k/kernel/ksyms.c linux/arch/m68k/kernel/ksyms.c
  2605. --- pre2.0.4/linux/arch/m68k/kernel/ksyms.c    Tue Apr 23 13:57:07 1996
  2606. +++ linux/arch/m68k/kernel/ksyms.c    Thu May 16 09:05:10 1996
  2607. @@ -3,9 +3,12 @@
  2608.  #include <linux/linkage.h>
  2609.  #include <linux/string.h>
  2610.  #include <linux/mm.h>
  2611. +#include <linux/user.h>
  2612. +#include <linux/elfcore.h>
  2613.  
  2614.  #include <asm/bootinfo.h>
  2615.  #include <asm/pgtable.h>
  2616. +#include <asm/irq.h>
  2617.  
  2618.  asmlinkage long long __ashrdi3 (long long, int);
  2619.  extern char m68k_debug_device[];
  2620. @@ -20,6 +23,9 @@
  2621.  extern void mach_mac_syms_export (void);
  2622.  #endif
  2623.  
  2624. +extern void dump_thread(struct pt_regs *, struct user *);
  2625. +extern int dump_fpu(elf_fpregset_t *);
  2626. +
  2627.  static struct symbol_table arch_symbol_table = {
  2628.  #include <linux/symtab_begin.h>
  2629.      /* platform dependent support */
  2630. @@ -32,6 +38,10 @@
  2631.      X(mm_vtop),
  2632.      X(mm_ptov),
  2633.      X(m68k_debug_device),
  2634. +    X(add_isr),
  2635. +    X(remove_isr),
  2636. +    X(dump_fpu),
  2637. +    X(dump_thread),
  2638.  
  2639.      /* The following are special because they're not called
  2640.         explicitly (the C compiler generates them).  Fortunately,
  2641. diff -u --recursive --new-file pre2.0.4/linux/arch/m68k/kernel/ptrace.c linux/arch/m68k/kernel/ptrace.c
  2642. --- pre2.0.4/linux/arch/m68k/kernel/ptrace.c    Tue Apr 23 13:57:08 1996
  2643. +++ linux/arch/m68k/kernel/ptrace.c    Thu May 16 09:05:10 1996
  2644. @@ -342,8 +342,10 @@
  2645.              return -EPERM;
  2646.          if ((!child->dumpable ||
  2647.              (current->uid != child->euid) ||
  2648. +            (current->uid != child->suid) ||
  2649.              (current->uid != child->uid) ||
  2650.               (current->gid != child->egid) ||
  2651. +            (current->gid != child->sgid) ||
  2652.               (current->gid != child->gid)) && !suser())
  2653.              return -EPERM;
  2654.          /* the same process cannot be attached many times */
  2655. diff -u --recursive --new-file pre2.0.4/linux/arch/m68k/kernel/setup.c linux/arch/m68k/kernel/setup.c
  2656. --- pre2.0.4/linux/arch/m68k/kernel/setup.c    Tue May  7 16:22:19 1996
  2657. +++ linux/arch/m68k/kernel/setup.c    Thu May 16 09:05:10 1996
  2658. @@ -72,6 +72,7 @@
  2659.  #ifdef CONFIG_BLK_DEV_FD
  2660.  int (*mach_floppy_init) (void) = NULL;
  2661.  void (*mach_floppy_setup) (char *, int *) = NULL;
  2662. +void (*mach_floppy_eject) (void) = NULL;
  2663.  #endif
  2664.  
  2665.  extern void config_amiga(void);
  2666. @@ -115,6 +116,12 @@
  2667.      else if (boot_info.cputype & CPU_68060)
  2668.          m68k_is040or060 = 6;
  2669.  
  2670. +    /* clear the fpu if we have one */
  2671. +    if (boot_info.cputype & (FPU_68881|FPU_68882|FPU_68040|FPU_68060)) {
  2672. +        volatile int zero = 0;
  2673. +        asm __volatile__ ("frestore %0" : : "m" (zero));
  2674. +    }
  2675. +
  2676.      memory_start = availmem;
  2677.      memory_end = 0;
  2678.  
  2679. @@ -240,7 +247,7 @@
  2680.             "FPU:\t\t%s\n"
  2681.             "Clockspeed:\t%lu.%1luMHz\n"
  2682.             "BogoMips:\t%lu.%02lu\n",
  2683. -           cpu, mmu, fpu, clockfreq/1000000,
  2684. +           cpu, mmu, fpu, (clockfreq+50000)/1000000,
  2685.             ((clockfreq+50000)/100000)%10, loops_per_sec/500000,
  2686.             (loops_per_sec/5000)%100));
  2687.  }
  2688. @@ -311,6 +318,12 @@
  2689.  {
  2690.      if (mach_floppy_setup)
  2691.          mach_floppy_setup (str, ints);
  2692. +}
  2693. +
  2694. +void floppy_eject(void)
  2695. +{
  2696. +    if (mach_floppy_eject)
  2697. +        mach_floppy_eject();
  2698.  }
  2699.  #endif
  2700.  
  2701. diff -u --recursive --new-file pre2.0.4/linux/arch/m68k/kernel/sys_m68k.c linux/arch/m68k/kernel/sys_m68k.c
  2702. --- pre2.0.4/linux/arch/m68k/kernel/sys_m68k.c    Sat Apr 27 15:19:47 1996
  2703. +++ linux/arch/m68k/kernel/sys_m68k.c    Thu May 16 09:05:10 1996
  2704. @@ -17,6 +17,7 @@
  2705.  #include <linux/mman.h>
  2706.  
  2707.  #include <asm/segment.h>
  2708. +#include <asm/cachectl.h>
  2709.  
  2710.  /*
  2711.   * sys_pipe() is the normal C calling standard for creating
  2712. @@ -182,4 +183,324 @@
  2713.  asmlinkage int sys_ioperm(unsigned long from, unsigned long num, int on)
  2714.  {
  2715.    return -ENOSYS;
  2716. +}
  2717. +
  2718. +/* Convert virtual address VADDR to physical address PADDR, recording
  2719. +   in VALID whether the virtual address is actually mapped.  */
  2720. +#define virt_to_phys_040(vaddr, paddr, valid)                \
  2721. +{                                    \
  2722. +  register unsigned long _tmp1 __asm__ ("a0") = (vaddr);        \
  2723. +  register unsigned long _tmp2 __asm__ ("d0");                \
  2724. +  unsigned long _mmusr;                            \
  2725. +                                    \
  2726. +  __asm__ __volatile__ (".word 0xf568 /* ptestr (%1) */\n\t"        \
  2727. +            ".long 0x4e7a0805 /* movec %%mmusr,%0 */"    \
  2728. +            : "=d" (_tmp2)                    \
  2729. +            : "a" (_tmp1));                    \
  2730. +  _mmusr = _tmp2;                            \
  2731. +  if (0 /* XXX _mmusr & MMU_?_040 */)                    \
  2732. +    (valid) = 0;                            \
  2733. +  else                                    \
  2734. +    {                                    \
  2735. +      (valid) = 1;                            \
  2736. +      (paddr) = _mmusr & ~0xfff;                    \
  2737. +    }                                    \
  2738. +}
  2739. +
  2740. +static inline int
  2741. +cache_flush_040 (unsigned long addr, int scope, int cache, unsigned long len)
  2742. +{
  2743. +  unsigned long paddr;
  2744. +  int valid;
  2745. +
  2746. +  switch (scope)
  2747. +    {
  2748. +    case FLUSH_SCOPE_ALL:
  2749. +      switch (cache)
  2750. +    {
  2751. +    case FLUSH_CACHE_DATA:
  2752. +      /* This nop is needed for some broken versions of the 68040.  */
  2753. +      __asm__ __volatile__ ("nop\n\t"
  2754. +                ".word 0xf478 /* cpusha %%dc */");
  2755. +      break;
  2756. +    case FLUSH_CACHE_INSN:
  2757. +      __asm__ __volatile__ ("nop\n\t"
  2758. +                ".word 0xf4b8 /* cpusha %%ic */");
  2759. +      break;
  2760. +    default:
  2761. +    case FLUSH_CACHE_BOTH:
  2762. +      __asm__ __volatile__ ("nop\n\t"
  2763. +                ".word 0xf4f8 /* cpusha %%bc */");
  2764. +      break;
  2765. +    }
  2766. +      break;
  2767. +
  2768. +    case FLUSH_SCOPE_LINE:
  2769. +      len >>= 4;
  2770. +      for (;;)
  2771. +    {
  2772. +      virt_to_phys_040 (addr, paddr, valid);
  2773. +      if (valid)
  2774. +        break;
  2775. +      if (len <= PAGE_SIZE / 16)
  2776. +        return 0;
  2777. +      len -= PAGE_SIZE / 16;
  2778. +      addr += PAGE_SIZE;
  2779. +    }
  2780. +      while (len--)
  2781. +    {
  2782. +      register unsigned long tmp __asm__ ("a0") = paddr;
  2783. +      switch (cache)
  2784. +        {
  2785. +        case FLUSH_CACHE_DATA:
  2786. +          __asm__ __volatile__ ("nop\n\t"
  2787. +                    ".word 0xf468 /* cpushl %%dc,(%0) */"
  2788. +                    : : "a" (tmp));
  2789. +          break;
  2790. +        case FLUSH_CACHE_INSN:
  2791. +          __asm__ __volatile__ ("nop\n\t"
  2792. +                    ".word 0xf4a8 /* cpushl %%ic,(%0) */"
  2793. +                    : : "a" (tmp));
  2794. +          break;
  2795. +        default:
  2796. +        case FLUSH_CACHE_BOTH:
  2797. +          __asm__ __volatile__ ("nop\n\t"
  2798. +                    ".word 0xf4e8 /* cpushl %%bc,(%0) */"
  2799. +                    : : "a" (paddr));
  2800. +          break;
  2801. +        }
  2802. +      addr += 16;
  2803. +      if (len)
  2804. +        {
  2805. +          if ((addr & (PAGE_SIZE-1)) < 16)
  2806. +        {
  2807. +          /* Recompute physical address when crossing a page
  2808. +             boundary. */
  2809. +          for (;;)
  2810. +            {
  2811. +              virt_to_phys_040 (addr, paddr, valid);
  2812. +              if (valid)
  2813. +            break;
  2814. +              if (len <= PAGE_SIZE / 16)
  2815. +            return 0;
  2816. +              len -= PAGE_SIZE / 16;
  2817. +              addr += PAGE_SIZE;
  2818. +            }
  2819. +        }
  2820. +          else
  2821. +        paddr += 16;
  2822. +        }
  2823. +    }
  2824. +      break;
  2825. +
  2826. +    default:
  2827. +    case FLUSH_SCOPE_PAGE:
  2828. +      for (len >>= PAGE_SHIFT; len--; addr += PAGE_SIZE)
  2829. +    {
  2830. +      register unsigned long tmp __asm__ ("a0");
  2831. +      virt_to_phys_040 (addr, paddr, valid);
  2832. +      if (!valid)
  2833. +        continue;
  2834. +      tmp = paddr;
  2835. +      switch (cache)
  2836. +        {
  2837. +        case FLUSH_CACHE_DATA:
  2838. +          __asm__ __volatile__ ("nop\n\t"
  2839. +                    ".word 0xf470 /* cpushp %%dc,(%0) */"
  2840. +                    : : "a" (tmp));
  2841. +          break;
  2842. +        case FLUSH_CACHE_INSN:
  2843. +          __asm__ __volatile__ ("nop\n\t"
  2844. +                    ".word 0xf4b0 /* cpushp %%ic,(%0) */"
  2845. +                    : : "a" (tmp));
  2846. +          break;
  2847. +        default:
  2848. +        case FLUSH_CACHE_BOTH:
  2849. +          __asm__ __volatile__ ("nop\n\t"
  2850. +                    ".word 0xf4f0 /* cpushp %%bc,(%0) */"
  2851. +                    : : "a" (tmp));
  2852. +          break;
  2853. +        }
  2854. +    }
  2855. +      break;
  2856. +    }
  2857. +  return 0;
  2858. +}
  2859. +
  2860. +#define virt_to_phys_060(vaddr, paddr, valid)        \
  2861. +{                            \
  2862. +  register unsigned long _tmp __asm__ ("a0") = (vaddr);    \
  2863. +                            \
  2864. +  __asm__ __volatile__ (".word 0xf5c8 /* plpar (%1) */"    \
  2865. +            : "=a" (_tmp)            \
  2866. +            : "0" (_tmp));            \
  2867. +  (valid) = 1; /* XXX */                \
  2868. +  (paddr) = _tmp;                    \
  2869. +}
  2870. +
  2871. +static inline int
  2872. +cache_flush_060 (unsigned long addr, int scope, int cache, unsigned long len)
  2873. +{
  2874. +  unsigned long paddr;
  2875. +  int valid;
  2876. +
  2877. +  switch (scope)
  2878. +    {
  2879. +    case FLUSH_SCOPE_ALL:
  2880. +      switch (cache)
  2881. +    {
  2882. +    case FLUSH_CACHE_DATA:
  2883. +      __asm__ __volatile__ (".word 0xf478 /* cpusha %%dc */\n\t"
  2884. +                ".word 0xf458 /* cinva %%dc */");
  2885. +      break;
  2886. +    case FLUSH_CACHE_INSN:
  2887. +      __asm__ __volatile__ (".word 0xf4b8 /* cpusha %%ic */\n\t"
  2888. +                ".word 0xf498 /* cinva %%ic */");
  2889. +      break;
  2890. +    default:
  2891. +    case FLUSH_CACHE_BOTH:
  2892. +      __asm__ __volatile__ (".word 0xf4f8 /* cpusha %%bc */\n\t"
  2893. +                ".word 0xf4d8 /* cinva %%bc */");
  2894. +      break;
  2895. +    }
  2896. +      break;
  2897. +
  2898. +    case FLUSH_SCOPE_LINE:
  2899. +      len >>= 4;
  2900. +      for (;;)
  2901. +    {
  2902. +      virt_to_phys_060 (addr, paddr, valid);
  2903. +      if (valid)
  2904. +        break;
  2905. +      if (len <= PAGE_SIZE / 16)
  2906. +        return 0;
  2907. +      len -= PAGE_SIZE / 16;
  2908. +      addr += PAGE_SIZE;
  2909. +    }
  2910. +      while (len--)
  2911. +    {
  2912. +      register unsigned long tmp __asm__ ("a0") = paddr;
  2913. +      switch (cache)
  2914. +        {
  2915. +        case FLUSH_CACHE_DATA:
  2916. +          __asm__ __volatile__ (".word 0xf468 /* cpushl %%dc,(%0) */\n\t"
  2917. +                    ".word 0xf448 /* cinv %%dc,(%0) */"
  2918. +                    : : "a" (tmp));
  2919. +          break;
  2920. +        case FLUSH_CACHE_INSN:
  2921. +          __asm__ __volatile__ (".word 0xf4a8 /* cpushl %%ic,(%0) */\n\t"
  2922. +                    ".word 0xf488 /* cinv %%ic,(%0) */"
  2923. +                    : : "a" (tmp));
  2924. +          break;
  2925. +        default:
  2926. +        case FLUSH_CACHE_BOTH:
  2927. +          __asm__ __volatile__ (".word 0xf4e8 /* cpushl %%bc,(%0) */\n\t"
  2928. +                    ".word 0xf4c8 /* cinv %%bc,(%0) */"
  2929. +                    : : "a" (paddr));
  2930. +          break;
  2931. +        }
  2932. +      addr += 16;
  2933. +      if (len)
  2934. +        {
  2935. +          if ((addr & (PAGE_SIZE-1)) < 16)
  2936. +        {
  2937. +          /* Recompute the physical address when crossing a
  2938. +             page boundary.  */
  2939. +          for (;;)
  2940. +            {
  2941. +              virt_to_phys_060 (addr, paddr, valid);
  2942. +              if (valid)
  2943. +            break;
  2944. +              if (len <= PAGE_SIZE / 16)
  2945. +            return 0;
  2946. +              len -= PAGE_SIZE / 16;
  2947. +              addr += PAGE_SIZE;
  2948. +            }
  2949. +        }
  2950. +          else
  2951. +        paddr += 16;
  2952. +        }
  2953. +    }
  2954. +      break;
  2955. +
  2956. +    default:
  2957. +    case FLUSH_SCOPE_PAGE:
  2958. +      for (len >>= PAGE_SHIFT; len--; addr += PAGE_SIZE)
  2959. +    {
  2960. +      register unsigned long tmp __asm__ ("a0");
  2961. +      virt_to_phys_060 (addr, paddr, valid);
  2962. +      if (!valid)
  2963. +        continue;
  2964. +      tmp = paddr;
  2965. +      switch (cache)
  2966. +        {
  2967. +        case FLUSH_CACHE_DATA:
  2968. +          __asm__ __volatile__ (".word 0xf470 /* cpushp %%dc,(%0) */\n\t"
  2969. +                    ".word 0xf450 /* cinv %%dc,(%0) */"
  2970. +                    : : "a" (tmp));
  2971. +          break;
  2972. +        case FLUSH_CACHE_INSN:
  2973. +          __asm__ __volatile__ (".word 0xf4b0 /* cpushp %%ic,(%0) */\n\t"
  2974. +                    ".word 0xf490 /* cinv %%ic,(%0) */"
  2975. +                    : : "a" (tmp));
  2976. +          break;
  2977. +        default:
  2978. +        case FLUSH_CACHE_BOTH:
  2979. +          __asm__ __volatile__ (".word 0xf4f0 /* cpushp %%bc,(%0) */\n\t"
  2980. +                    ".word 0xf4d0 /* cinv %%bc,(%0) */"
  2981. +                    : : "a" (tmp));
  2982. +          break;
  2983. +        }
  2984. +    }
  2985. +      break;
  2986. +    }
  2987. +  return 0;
  2988. +}
  2989. +
  2990. +/* sys_cacheflush -- flush (part of) the processor cache.  */
  2991. +asmlinkage int
  2992. +sys_cacheflush (unsigned long addr, int scope, int cache, unsigned long len)
  2993. +{
  2994. +  struct vm_area_struct *vma;
  2995. +
  2996. +  if (scope < FLUSH_SCOPE_LINE || scope > FLUSH_SCOPE_ALL
  2997. +      || cache & ~FLUSH_CACHE_BOTH)
  2998. +    return -EINVAL;
  2999. +
  3000. +  if (scope == FLUSH_SCOPE_ALL)
  3001. +    {
  3002. +      /* Only the superuser may flush the whole cache. */
  3003. +      if (!suser ())
  3004. +    return -EPERM;
  3005. +    }
  3006. +  else
  3007. +    {
  3008. +      /* Verify that the specified address region actually belongs to
  3009. +     this process.  */
  3010. +      vma = find_vma (current, addr);
  3011. +      if (vma == NULL || addr < vma->vm_start || addr + len > vma->vm_end)
  3012. +    return -EINVAL;
  3013. +    }
  3014. +
  3015. +  switch (m68k_is040or060)
  3016. +    {
  3017. +    default: /* 030 */
  3018. +      /* Always flush the whole cache, everything else would not be
  3019. +     worth the hassle.  */
  3020. +      __asm__ __volatile__
  3021. +    ("movec %%cacr, %%d0\n\t"
  3022. +     "or %0, %%d0\n\t"
  3023. +     "movec %%d0, %%cacr"
  3024. +     : /* no outputs */
  3025. +     : "di" ((cache & FLUSH_CACHE_INSN ? 8 : 0)
  3026. +         | (cache & FLUSH_CACHE_DATA ? 0x800 : 0))
  3027. +     : "d0");
  3028. +      return 0;
  3029. +
  3030. +    case 4: /* 040 */
  3031. +      return cache_flush_040 (addr, scope, cache, len);
  3032. +
  3033. +    case 6: /* 060 */
  3034. +      return cache_flush_060 (addr, scope, cache, len);
  3035. +    }
  3036.  }
  3037. diff -u --recursive --new-file pre2.0.4/linux/arch/m68k/kernel/time.c linux/arch/m68k/kernel/time.c
  3038. --- pre2.0.4/linux/arch/m68k/kernel/time.c    Tue Apr 23 13:57:08 1996
  3039. +++ linux/arch/m68k/kernel/time.c    Thu May 16 09:05:10 1996
  3040. @@ -137,7 +137,7 @@
  3041.  
  3042.      xtime = *tv;
  3043.      time_state = TIME_BAD;
  3044. -    time_maxerror = 0x70000000;
  3045. -    time_esterror = 0x70000000;
  3046. +    time_maxerror = MAXPHASE;
  3047. +    time_esterror = MAXPHASE;
  3048.      sti();
  3049.  }
  3050. diff -u --recursive --new-file pre2.0.4/linux/arch/m68k/mm/init.c linux/arch/m68k/mm/init.c
  3051. --- pre2.0.4/linux/arch/m68k/mm/init.c    Sat Apr 27 15:19:47 1996
  3052. +++ linux/arch/m68k/mm/init.c    Thu May 16 09:05:10 1996
  3053. @@ -12,7 +12,7 @@
  3054.  #include <linux/kernel.h>
  3055.  #include <linux/string.h>
  3056.  #include <linux/types.h>
  3057. -#ifdef CONFIG_BLK_DEV_INITRD
  3058. +#ifdef CONFIG_BLK_DEV_RAM
  3059.  #include <linux/blk.h>
  3060.  #endif
  3061.  
  3062. @@ -24,6 +24,7 @@
  3063.  #include <asm/machdep.h>
  3064.  
  3065.  extern void die_if_kernel(char *,struct pt_regs *,long);
  3066. +extern void init_kpointer_table(void);
  3067.  extern void show_net_buffers(void);
  3068.  extern unsigned long mm_phys_to_virt (unsigned long addr);
  3069.  extern char *rd_start;
  3070. @@ -304,6 +305,7 @@
  3071.      }
  3072.  #endif
  3073.  
  3074. +    init_kpointer_table();
  3075.  #if 0
  3076.      /*
  3077.       * Setup cache bits
  3078. @@ -416,6 +418,7 @@
  3079.      printk ("before free_area_init\n");
  3080.  #endif
  3081.  
  3082. +#ifdef CONFIG_BLK_DEV_RAM
  3083.  #ifndef CONFIG_BLK_DEV_INITRD
  3084.      /*
  3085.       * Since the initialization of the ramdisk's has been changed
  3086. @@ -440,6 +443,7 @@
  3087.        start_mem += ramdisk_length;
  3088.        rd_doload = 1;     /* tell rd_load to load this thing */
  3089.      }
  3090. +#endif
  3091.  #endif
  3092.  
  3093.      return free_area_init (start_mem, end_mem);
  3094. diff -u --recursive --new-file pre2.0.4/linux/arch/m68k/mm/memory.c linux/arch/m68k/mm/memory.c
  3095. --- pre2.0.4/linux/arch/m68k/mm/memory.c    Tue May  7 16:22:20 1996
  3096. +++ linux/arch/m68k/mm/memory.c    Thu May 16 09:05:10 1996
  3097. @@ -20,6 +20,15 @@
  3098.  
  3099.  extern pte_t *kernel_page_table (unsigned long *memavailp);
  3100.  
  3101. +/* Strings for `extern inline' functions in <asm/pgtable.h>.  If put
  3102. +   directly into these functions, they are output for every file that
  3103. +   includes pgtable.h */
  3104. +
  3105. +const char PgtabStr_bad_pmd[] = "Bad pmd in pte_alloc: %08lx\n";
  3106. +const char PgtabStr_bad_pgd[] = "Bad pgd in pmd_alloc: %08lx\n";
  3107. +const char PgtabStr_bad_pmdk[] = "Bad pmd in pte_alloc_kernel: %08lx\n";
  3108. +const char PgtabStr_bad_pgdk[] = "Bad pgd in pmd_alloc_kernel: %08lx\n";
  3109. +
  3110.  static struct ptable_desc {
  3111.      struct ptable_desc *prev;
  3112.      struct ptable_desc *next;
  3113. @@ -145,40 +154,100 @@
  3114.      }
  3115.  }
  3116.  
  3117. -static unsigned char alloced = 0;
  3118. -extern pmd_t (*kernel_pmd_table)[PTRS_PER_PMD]; /* initialized in head.S */
  3119. +/* maximum pages used for kpointer tables */
  3120. +#define KPTR_PAGES      4
  3121. +/* # of reserved slots */
  3122. +#define RESERVED_KPTR    4
  3123. +extern pmd_tablepage kernel_pmd_table; /* reserved in head.S */
  3124. +
  3125. +static struct kpointer_pages {
  3126. +        pmd_tablepage *page[KPTR_PAGES];
  3127. +        u_char alloced[KPTR_PAGES];
  3128. +} kptr_pages;
  3129. +
  3130. +void init_kpointer_table(void) {
  3131. +    short i = KPTR_PAGES-1;
  3132. +
  3133. +    /* first page is reserved in head.S */
  3134. +    kptr_pages.page[i] = &kernel_pmd_table;
  3135. +    kptr_pages.alloced[i] = ~(0xff>>RESERVED_KPTR);
  3136. +    for (i--; i>=0; i--) {
  3137. +        kptr_pages.page[i] = NULL;
  3138. +        kptr_pages.alloced[i] = 0;
  3139. +    }
  3140. +}
  3141.  
  3142.  pmd_t *get_kpointer_table (void)
  3143.  {
  3144.      /* For pointer tables for the kernel virtual address space,
  3145. -     * use a page that is allocated in head.S that can hold up to
  3146. -     * 8 pointer tables.  This allows mapping of 8 * 32M = 256M of
  3147. -     * physical memory.  This should be sufficient for now.
  3148. +     * use the page that is reserved in head.S that can hold up to
  3149. +     * 8 pointer tables. 3 of these tables are always reserved
  3150. +     * (kernel_pg_dir, swapper_pg_dir and kernel pointer table for
  3151. +     * the first 16 MB of RAM). In addition, the 4th pointer table
  3152. +     * in this page is reserved. On Amiga and Atari, it is used to
  3153. +     * map in the hardware registers. It may be used for other
  3154. +     * purposes on other 68k machines. This leaves 4 pointer tables
  3155. +     * available for use by the kernel. 1 of them are usually used
  3156. +     * for the vmalloc tables. This allows mapping of 3 * 32 = 96 MB
  3157. +     * of physical memory. But these pointer tables are also used
  3158. +     * for other purposes, like kernel_map(), so further pages can
  3159. +     * now be allocated.
  3160.       */
  3161. -    pmd_t *ptable;
  3162. -    int i;
  3163. -
  3164. -    for (i = 0; i < PAGE_SIZE/(PTRS_PER_PMD*sizeof(pmd_t)); i++)
  3165. -        if ((alloced & (1 << i)) == 0) {
  3166. -            ptable = kernel_pmd_table[i];
  3167. -            memset (ptable, 0, PTRS_PER_PMD*sizeof(pmd_t));
  3168. -            alloced |= (1 << i);
  3169. -            return ptable;
  3170. +    pmd_tablepage *page;
  3171. +    pmd_table *table;
  3172. +    long nr, offset = -8;
  3173. +    short i;
  3174. +
  3175. +    for (i=KPTR_PAGES-1; i>=0; i--) {
  3176. +        asm volatile("bfffo %1{%2,#8},%0"
  3177. +            : "=d" (nr)
  3178. +            : "d" ((u_char)~kptr_pages.alloced[i]), "d" (offset));
  3179. +        if (nr)
  3180. +            break;
  3181. +    }
  3182. +    if (i < 0) {
  3183. +        printk("No space for kernel pointer table!\n");
  3184. +        return NULL;
  3185. +    }
  3186. +    if (!(page = kptr_pages.page[i])) {
  3187. +        if (!(page = (pmd_tablepage *)__get_free_page(GFP_KERNEL))) {
  3188. +            printk("No space for kernel pointer table!\n");
  3189. +            return NULL;
  3190.          }
  3191. -    printk ("no space for kernel pointer table\n");
  3192. -    return NULL;
  3193. +        nocache_page((u_long)(kptr_pages.page[i] = page));
  3194. +    }
  3195. +    asm volatile("bfset %0@{%1,#1}"
  3196. +        : /* no output */
  3197. +        : "a" (&kptr_pages.alloced[i]), "d" (nr-offset));
  3198. +    table = &(*page)[nr-offset];
  3199. +    memset(table, 0, sizeof(pmd_table));
  3200. +    return ((pmd_t *)table);
  3201.  }
  3202.  
  3203.  void free_kpointer_table (pmd_t *pmdp)
  3204.  {
  3205. -    int index = (pmd_t (*)[PTRS_PER_PMD])pmdp - kernel_pmd_table;
  3206. +    pmd_table *table = (pmd_table *)pmdp;
  3207. +    pmd_tablepage *page = (pmd_tablepage *)((u_long)table & PAGE_MASK);
  3208. +    long nr;
  3209. +    short i;
  3210.  
  3211. -    if (index < 0 || index > 7 ||
  3212. -        /* This works because kernel_pmd_table is page aligned. */
  3213. -        ((unsigned long)pmdp & (sizeof(pmd_t) * PTRS_PER_PMD - 1)))
  3214. -        panic("attempt to free invalid kernel pointer table");
  3215. -    else
  3216. -        alloced &= ~(1 << index);
  3217. +    for (i=KPTR_PAGES-1; i>=0; i--) {
  3218. +        if (kptr_pages.page[i] == page)
  3219. +            break;
  3220. +    }
  3221. +    nr = ((u_long)table - (u_long)page) / sizeof(pmd_table);
  3222. +    if (!table || i < 0 || (i == KPTR_PAGES-1 && nr < RESERVED_KPTR)) {
  3223. +        printk("Attempt to free invalid kernel pointer table: %p\n", table);
  3224. +        return;
  3225. +    }
  3226. +    asm volatile("bfclr %0@{%1,#1}"
  3227. +        : /* no output */
  3228. +        : "a" (&kptr_pages.alloced[i]), "d" (nr));
  3229. +    if (!kptr_pages.alloced[i]) {
  3230. +        kptr_pages.page[i] = 0;
  3231. +        cache_page ((u_long)page);
  3232. +        free_page ((u_long)page);
  3233. +    }
  3234.  }
  3235.  
  3236.  /*
  3237. @@ -319,22 +388,41 @@
  3238.      return paddr;
  3239.  }
  3240.  
  3241. +/* invalidate page in both caches */
  3242.  #define    clear040(paddr) __asm__ __volatile__ ("movel %0,%/a0\n\t"\
  3243. +                          "nop\n\t"\
  3244.                            ".word 0xf4d0"\
  3245.                            /* CINVP I/D (a0) */\
  3246.                            : : "g" ((paddr))\
  3247.                            : "a0")
  3248.  
  3249. +/* invalidate page in i-cache */
  3250. +#define    cleari040(paddr) __asm__ __volatile__ ("movel %0,%/a0\n\t"\
  3251. +                           /* CINVP I (a0) */\
  3252. +                           "nop\n\t"\
  3253. +                           ".word 0xf490"\
  3254. +                           : : "g" ((paddr))\
  3255. +                           : "a0")
  3256. +
  3257. +/* push page in both caches */
  3258.  #define    push040(paddr) __asm__ __volatile__ ("movel %0,%/a0\n\t"\
  3259. +                          "nop\n\t"\
  3260.                           ".word 0xf4f0"\
  3261.                           /* CPUSHP I/D (a0) */\
  3262.                           : : "g" ((paddr))\
  3263.                           : "a0")
  3264.  
  3265. +/* push and invalidate page in both caches */
  3266.  #define    pushcl040(paddr) do { push040((paddr));\
  3267.                    if (m68k_is040or060 == 6) clear040((paddr));\
  3268.               } while(0)
  3269.  
  3270. +/* push page in both caches, invalidate in i-cache */
  3271. +#define    pushcli040(paddr) do { push040((paddr));\
  3272. +                   if (m68k_is040or060 == 6) cleari040((paddr));\
  3273. +              } while(0)
  3274. +
  3275. +/* push page defined by virtual address in both caches */
  3276.  #define    pushv040(vaddr) __asm__ __volatile__ ("movel %0,%/a0\n\t"\
  3277.                            /* ptestr (a0) */\
  3278.                            ".word 0xf568\n\t"\
  3279. @@ -343,10 +431,12 @@
  3280.                            "andw #0xf000,%/d0\n\t"\
  3281.                            "movel %/d0,%/a0\n\t"\
  3282.                            /* CPUSHP I/D (a0) */\
  3283. +                          "nop\n\t"\
  3284.                            ".word 0xf4f0"\
  3285.                            : : "g" ((vaddr))\
  3286.                            : "a0", "d0")
  3287.  
  3288. +/* push page defined by virtual address in both caches */
  3289.  #define    pushv060(vaddr) __asm__ __volatile__ ("movel %0,%/a0\n\t"\
  3290.                            /* plpar (a0) */\
  3291.                            ".word 0xf5c8\n\t"\
  3292. @@ -374,6 +464,14 @@
  3293.   * the DPI bit in the CACR; would it cause problems with temporarily changing
  3294.   * this?). So we have to push first and then additionally to invalidate.
  3295.   */
  3296. +
  3297. +/*
  3298. + * cache_clear() semantics: Clear any cache entries for the area in question,
  3299. + * without writing back dirty entries first. This is useful if the data will
  3300. + * be overwritten anyway, e.g. by DMA to memory. The range is defined by a
  3301. + * _physical_ address.
  3302. + */
  3303. +
  3304.  void cache_clear (unsigned long paddr, int len)
  3305.  {
  3306.      if (m68k_is040or060) {
  3307. @@ -419,6 +517,12 @@
  3308.  }
  3309.  
  3310.  
  3311. +/*
  3312. + * cache_push() semantics: Write back any dirty cache data in the given area,
  3313. + * and invalidate the range in the instruction cache. It needs not (but may)
  3314. + * invalidate those entries also in the data cache. The range is defined by a
  3315. + * _physical_ address.
  3316. + */
  3317.  
  3318.  void cache_push (unsigned long paddr, int len)
  3319.  {
  3320. @@ -429,18 +533,18 @@
  3321.       * the '060!
  3322.       */
  3323.      while (len > PAGE_SIZE) {
  3324. -        push040(paddr);
  3325. +        pushcli040(paddr);
  3326.          len -= PAGE_SIZE;
  3327.          paddr += PAGE_SIZE;
  3328.          }
  3329.      if (len > 0) {
  3330. -        push040(paddr);
  3331. +        pushcli040(paddr);
  3332.  #if 0
  3333.          if (((paddr + len - 1) / PAGE_SIZE) != (paddr / PAGE_SIZE)) {
  3334.  #endif
  3335.          if (((paddr + len - 1) ^ paddr) & PAGE_MASK) {
  3336.          /* a page boundary gets crossed at the end */
  3337. -        push040(paddr + len - 1);
  3338. +        pushcli040(paddr + len - 1);
  3339.          }
  3340.          }
  3341.      }
  3342. @@ -463,6 +567,15 @@
  3343.                : "d0");
  3344.  }
  3345.  
  3346. +
  3347. +/*
  3348. + * cache_push_v() semantics: Write back any dirty cache data in the given
  3349. + * area, and invalidate those entries at least in the instruction cache. This
  3350. + * is intended to be used after data has been written that can be executed as
  3351. + * code later. The range is defined by a _user_mode_ _virtual_ address  (or,
  3352. + * more exactly, the space is defined by the %sfc/%dfc register.)
  3353. + */
  3354. +
  3355.  void cache_push_v (unsigned long vaddr, int len)
  3356.  {
  3357.      if (m68k_is040or060 == 4) {
  3358. @@ -506,65 +619,12 @@
  3359.                : : "i" (FLUSH_I)
  3360.                : "d0");
  3361.  }
  3362. -#if 1
  3363. -void flush_cache_all(void)
  3364. -{
  3365. -    if (m68k_is040or060 >= 4)
  3366. -        __asm__ __volatile__ (".word 0xf478\n" ::);
  3367. -    else /* 68030 or 68020 */
  3368. -    asm volatile ("movec %/cacr,%/d0\n\t"
  3369. -              "oriw %0,%/d0\n\t"
  3370. -              "movec %/d0,%/cacr"
  3371. -              : : "i" (FLUSH_I_AND_D)
  3372. -              : "d0");
  3373. -}
  3374. -
  3375. -void flush_cache_mm(struct mm_struct *mm){
  3376. -
  3377. -    if (mm == current->mm)
  3378. -        flush_cache_all();
  3379. -}
  3380. -
  3381. -void flush_cache_range(struct mm_struct *mm, unsigned long start,
  3382. -               unsigned long end){
  3383. -    if (mm == current->mm)
  3384. -        cache_push_v(start, end-start);
  3385. -}
  3386. -
  3387. -void flush_cache_page (struct vm_area_struct *vma, unsigned long vaddr)
  3388. -{
  3389. -    if (m68k_is040or060 >= 4)
  3390. -        pushv040(vaddr); /*
  3391. -              * the 040 always invalidates the I-cache when
  3392. -              * pushing its contents to ram.
  3393. -              */
  3394. -
  3395. -    /* 68030/68020 have no writeback cache; still need to clear icache. */
  3396. -    else /* 68030 or 68020 */
  3397. -        asm volatile ("movec %/cacr,%/d0\n\t"
  3398. -              "oriw %0,%/d0\n\t"
  3399. -              "movec %/d0,%/cacr"
  3400. -              : : "i" (FLUSH_I_AND_D)
  3401. -              : "d0");
  3402. -}
  3403. -
  3404. -void flush_page_to_ram (unsigned long vaddr)
  3405. -{
  3406. -    if (m68k_is040or060 >= 4)
  3407. -        pushcl040(VTOP(vaddr));
  3408. -
  3409. -    /* 68030/68020 have no writeback cache; still need to clear icache. */
  3410. -    else /* 68030 or 68020 */
  3411. -    asm volatile ("movec %/cacr,%/d0\n\t"
  3412. -              "oriw %0,%/d0\n\t"
  3413. -              "movec %/d0,%/cacr"
  3414. -              : : "i" (FLUSH_I_AND_D)
  3415. -              : "d0");
  3416. -}
  3417. -#endif
  3418.  
  3419.  #undef clear040
  3420. +#undef cleari040
  3421.  #undef push040
  3422. +#undef pushcl040
  3423. +#undef pushcli040
  3424.  #undef pushv040
  3425.  #undef pushv060
  3426.  
  3427. diff -u --recursive --new-file pre2.0.4/linux/drivers/block/Config.in linux/drivers/block/Config.in
  3428. --- pre2.0.4/linux/drivers/block/Config.in    Tue May  7 16:22:22 1996
  3429. +++ linux/drivers/block/Config.in    Thu May 16 16:35:39 1996
  3430. @@ -16,36 +16,38 @@
  3431.    bool '   Support removable IDE interfaces (PCMCIA)' CONFIG_BLK_DEV_IDE_PCMCIA
  3432.    bool '   CMD640 chipset bugfix/support' CONFIG_BLK_DEV_CMD640
  3433.    if [ "$CONFIG_PCI" = "y" ]; then
  3434. -    bool '   RZ1000 chipset bugfix/support' CONFIG_BLK_DEV_RZ1000
  3435.      bool '   Intel 430FX (Triton) chipset DMA support' CONFIG_BLK_DEV_TRITON
  3436. +    bool '   RZ1000 chipset bugfix/support' CONFIG_BLK_DEV_RZ1000
  3437.    fi
  3438.    bool '   Other IDE chipset support' CONFIG_IDE_CHIPSETS
  3439.    if [ "$CONFIG_IDE_CHIPSETS" = "y" ]; then
  3440.      comment 'Note: most of these also require special kernel boot parameters'
  3441. +    bool '      ALI M1439/M1445 support' CONFIG_BLK_DEV_ALI14XX
  3442.      bool '      DTC-2278        support' CONFIG_BLK_DEV_DTC2278
  3443.      bool '      Holtek HT6560B  support' CONFIG_BLK_DEV_HT6560B
  3444. +    bool '      PROMISE DC4030  support (ALPHA)' CONFIG_BLK_DEV_PROMISE
  3445.      bool '      QDI QD6580      support' CONFIG_BLK_DEV_QD6580
  3446.      bool '      UMC 8672        support' CONFIG_BLK_DEV_UMC8672
  3447. -    bool '      ALI M1439/M1445 support' CONFIG_BLK_DEV_ALI14XX
  3448. -    bool '      PROMISE DC4030  support (ALPHA)' CONFIG_BLK_DEV_PROMISE
  3449.    fi
  3450.  fi
  3451.  
  3452. +comment 'Additional Block Devices'
  3453. +
  3454. +tristate 'Loopback device support' CONFIG_BLK_DEV_LOOP
  3455. +bool 'Multiple devices driver support' CONFIG_BLK_DEV_MD
  3456. +if [ "$CONFIG_BLK_DEV_MD" = "y" ]; then
  3457. +  tristate '   Linear (append) mode' CONFIG_MD_LINEAR
  3458. +  tristate '   RAID-0 (striping) mode' CONFIG_MD_STRIPED
  3459. +fi
  3460.  tristate 'RAM disk support' CONFIG_BLK_DEV_RAM
  3461.  if [ "$CONFIG_BLK_DEV_RAM" = "y" ]; then
  3462.    bool '   Initial RAM disk (initrd) support' CONFIG_BLK_DEV_INITRD
  3463.  fi
  3464. +tristate 'XT harddisk support' CONFIG_BLK_DEV_XD
  3465.  
  3466. -tristate 'Loopback device support' CONFIG_BLK_DEV_LOOP
  3467.  
  3468.  if [ "$CONFIG_BLK_DEV_HD_IDE" = "y" -o "$CONFIG_BLK_DEV_HD_ONLY" = "y" ]; then
  3469.    define_bool CONFIG_BLK_DEV_HD y
  3470.  fi
  3471.  
  3472. -tristate 'XT harddisk support' CONFIG_BLK_DEV_XD
  3473. -bool 'Multiple devices driver support' CONFIG_BLK_DEV_MD
  3474. -if [ "$CONFIG_BLK_DEV_MD" = "y" ]; then
  3475. -  tristate '   Linear (append) mode' CONFIG_MD_LINEAR
  3476. -  tristate '   RAID-0 (striping) mode' CONFIG_MD_STRIPED
  3477. -fi
  3478.  endmenu
  3479. diff -u --recursive --new-file pre2.0.4/linux/drivers/block/amiflop.c linux/drivers/block/amiflop.c
  3480. --- pre2.0.4/linux/drivers/block/amiflop.c    Tue May  7 16:22:22 1996
  3481. +++ linux/drivers/block/amiflop.c    Thu May 16 09:05:10 1996
  3482. @@ -1780,12 +1780,3 @@
  3483.  
  3484.    return 0;
  3485.  }
  3486. -
  3487. -#ifndef MODULE
  3488. -/*
  3489. - * This is just a dummy function to keep fs/super.c happy.
  3490. - */
  3491. -void floppy_eject(void)
  3492. -{
  3493. -}
  3494. -#endif
  3495. diff -u --recursive --new-file pre2.0.4/linux/drivers/block/ataflop.c linux/drivers/block/ataflop.c
  3496. --- pre2.0.4/linux/drivers/block/ataflop.c    Tue May  7 16:22:22 1996
  3497. +++ linux/drivers/block/ataflop.c    Thu May 16 09:05:10 1996
  3498. @@ -608,11 +608,11 @@
  3499.      if (!CURRENT) return;
  3500.      CURRENT->errors++;
  3501.      if (CURRENT->errors >= MAX_ERRORS) {
  3502. -        printk( "fd%d: too many errors.\n", SelectedDrive );
  3503. +        printk(KERN_ERR "fd%d: too many errors.\n", SelectedDrive );
  3504.          end_request( 0 );
  3505.      }
  3506.      else if (CURRENT->errors == RECALIBRATE_ERRORS) {
  3507. -        printk( "fd%d: recalibrating\n", SelectedDrive );
  3508. +        printk(KERN_WARNING "fd%d: recalibrating\n", SelectedDrive );
  3509.          if (SelectedDrive != -1)
  3510.              SUD.track = -1;
  3511.      }
  3512. @@ -793,7 +793,7 @@
  3513.      if (ATARIHW_PRESENT(FDCSPEED))
  3514.          dma_wd.fdc_speed = SUDT->fdc_speed;
  3515.      if (status & FDCSTAT_RECNF) {
  3516. -        printk( "fd%d: restore failed\n", SelectedDrive );
  3517. +        printk(KERN_ERR "fd%d: restore failed\n", SelectedDrive );
  3518.          fd_error();
  3519.      }
  3520.      else {
  3521. @@ -841,7 +841,7 @@
  3522.      if (ATARIHW_PRESENT(FDCSPEED))
  3523.          dma_wd.fdc_speed = SUDT->fdc_speed;
  3524.      if (status & FDCSTAT_RECNF) {
  3525. -        printk( "fd%d: seek error (to track %d)\n",
  3526. +        printk(KERN_ERR "fd%d: seek error (to track %d)\n",
  3527.                  SelectedDrive, ReqTrack );
  3528.          /* we don't know exactly which track we are on now! */
  3529.          SUD.track = -1;
  3530. @@ -1049,14 +1049,14 @@
  3531.          dma_wd.dma_mode_status = 0x90;
  3532.          MFPDELAY();
  3533.          if (!(dma_wd.dma_mode_status & 0x01)) {
  3534. -            printk( "fd%d: DMA error\n", SelectedDrive );
  3535. +            printk(KERN_ERR "fd%d: DMA error\n", SelectedDrive );
  3536.              goto err_end;
  3537.          }
  3538.      }
  3539.      MFPDELAY();
  3540.  
  3541.      if (ReqCmd == WRITE && (status & FDCSTAT_WPROT)) {
  3542. -        printk( "fd%d: is write protected\n", SelectedDrive );
  3543. +        printk(KERN_NOTICE "fd%d: is write protected\n", SelectedDrive );
  3544.          goto err_end;
  3545.      }    
  3546.      if ((status & FDCSTAT_RECNF) &&
  3547. @@ -1071,7 +1071,7 @@
  3548.              }
  3549.              else {
  3550.                  if (SUD.flags & FTD_MSG)
  3551. -                    printk( "fd%d: Auto-detected floppy type %s\n",
  3552. +                    printk(KERN_INFO "fd%d: Auto-detected floppy type %s\n",
  3553.                             SelectedDrive, SUDT->name );
  3554.                  Probing=0;
  3555.              }
  3556. @@ -1094,17 +1094,17 @@
  3557.              return;
  3558.          }
  3559.  
  3560. -        printk( "fd%d: sector %d not found (side %d, track %d)\n",
  3561. +        printk(KERN_ERR "fd%d: sector %d not found (side %d, track %d)\n",
  3562.                 SelectedDrive, FDC_READ (FDCREG_SECTOR), ReqSide, ReqTrack );
  3563.          goto err_end;
  3564.      }
  3565.      if (status & FDCSTAT_CRC) {
  3566. -        printk( "fd%d: CRC error (side %d, track %d, sector %d)\n",
  3567. +        printk(KERN_ERR "fd%d: CRC error (side %d, track %d, sector %d)\n",
  3568.                 SelectedDrive, ReqSide, ReqTrack, FDC_READ (FDCREG_SECTOR) );
  3569.          goto err_end;
  3570.      }
  3571.      if (status & FDCSTAT_LOST) {
  3572. -        printk( "fd%d: lost data (side %d, track %d, sector %d)\n",
  3573. +        printk(KERN_ERR "fd%d: lost data (side %d, track %d, sector %d)\n",
  3574.                 SelectedDrive, ReqSide, ReqTrack, FDC_READ (FDCREG_SECTOR) );
  3575.          goto err_end;
  3576.      }
  3577. @@ -1214,11 +1214,11 @@
  3578.      STOP_TIMEOUT();
  3579.  
  3580.      if (status & FDCSTAT_WPROT) {
  3581. -        printk( "fd%d: is write protected\n", SelectedDrive );
  3582. +        printk(KERN_NOTICE "fd%d: is write protected\n", SelectedDrive );
  3583.          goto err_end;
  3584.      }    
  3585.      if (status & FDCSTAT_LOST) {
  3586. -        printk( "fd%d: lost data (side %d, track %d)\n",
  3587. +        printk(KERN_ERR "fd%d: lost data (side %d, track %d)\n",
  3588.                  SelectedDrive, ReqSide, ReqTrack );
  3589.          goto err_end;
  3590.      }
  3591. @@ -1244,7 +1244,7 @@
  3592.      FDC_WRITE( FDCREG_CMD, FDCCMD_FORCI );
  3593.      udelay( 25 );
  3594.      
  3595. -    printk( "floppy timeout\n" );
  3596. +    printk(KERN_ERR "floppy timeout\n" );
  3597.      fd_error();
  3598.    end:
  3599.      atari_enable_irq( IRQ_MFP_FDC );
  3600. @@ -1345,7 +1345,7 @@
  3601.      unsigned int drive = MINOR(dev) & 0x03;
  3602.  
  3603.      if (MAJOR(dev) != MAJOR_NR) {
  3604. -        printk("floppy_changed: not a floppy\n");
  3605. +        printk(KERN_ERR "floppy_changed: not a floppy\n");
  3606.          return 0;
  3607.      }
  3608.      
  3609. @@ -1445,7 +1445,7 @@
  3610.      
  3611.      if (!UD.connected) {
  3612.          /* drive not connected */
  3613. -        printk( "Unknown Device: fd%d\n", drive );
  3614. +        printk(KERN_ERR "Unknown Device: fd%d\n", drive );
  3615.          end_request(0);
  3616.          goto repeat;
  3617.      }
  3618. @@ -1461,12 +1461,12 @@
  3619.      else {
  3620.          /* user supplied disk type */
  3621.          if (--type >= NUM_DISK_MINORS) {
  3622. -            printk( "fd%d: invalid disk format", drive );
  3623. +            printk(KERN_WARNING "fd%d: invalid disk format", drive );
  3624.              end_request( 0 );
  3625.              goto repeat;
  3626.          }
  3627.          if (minor2disktype[type].drive_types > DriveType)  {
  3628. -            printk( "fd%d: unsupported disk format", drive );
  3629. +            printk(KERN_WARNING "fd%d: unsupported disk format", drive );
  3630.              end_request( 0 );
  3631.              goto repeat;
  3632.          }
  3633. @@ -1712,11 +1712,11 @@
  3634.      if (ATARIHW_PRESENT(FDCSPEED))
  3635.          dma_wd.fdc_speed = 0;
  3636.  
  3637. -    printk("Probing floppy drive(s):\n");
  3638. +    printk(KERN_INFO "Probing floppy drive(s):\n");
  3639.      for( drive = 0; drive < FD_MAX_UNITS; drive++ ) {
  3640.          fd_probe( drive );
  3641.          if (UD.connected) {
  3642. -            printk("fd%d\n", drive);
  3643. +            printk(KERN_INFO "fd%d\n", drive);
  3644.              ++cnt;
  3645.          }
  3646.      }
  3647. @@ -1789,6 +1789,8 @@
  3648.    if (filp->f_mode & 2)
  3649.      filp->f_mode |= OPEN_WRITE_BIT;
  3650.  
  3651. +  MOD_INC_USE_COUNT;
  3652. +
  3653.    if (filp->f_flags & O_NDELAY)
  3654.      return 0;
  3655.  
  3656. @@ -1821,9 +1823,11 @@
  3657.      fd_ref[drive] = 0;
  3658.    else if (!fd_ref[drive]--)
  3659.      {
  3660. -      printk("floppy_release with fd_ref == 0");
  3661. +      printk(KERN_ERR "floppy_release with fd_ref == 0");
  3662.        fd_ref[drive] = 0;
  3663.      }
  3664. +
  3665. +  MOD_DEC_USE_COUNT;
  3666.  }
  3667.  
  3668.  static struct file_operations floppy_fops = {
  3669. @@ -1847,7 +1851,7 @@
  3670.      int i;
  3671.  
  3672.      if (register_blkdev(MAJOR_NR,"fd",&floppy_fops)) {
  3673. -        printk("Unable to get major %d for floppy\n",MAJOR_NR);
  3674. +        printk(KERN_ERR "Unable to get major %d for floppy\n",MAJOR_NR);
  3675.          return -EBUSY;
  3676.      }
  3677.  
  3678. @@ -1868,7 +1872,7 @@
  3679.  
  3680.      DMABuffer = kmalloc(BUFFER_SIZE + 512, GFP_KERNEL | GFP_DMA);
  3681.      if (!DMABuffer) {
  3682. -        printk("atari_floppy_init: cannot get dma buffer\n");
  3683. +        printk(KERN_ERR "atari_floppy_init: cannot get dma buffer\n");
  3684.          unregister_blkdev(MAJOR_NR, "fd");
  3685.          return -ENOMEM;
  3686.      }
  3687. @@ -1893,7 +1897,7 @@
  3688.      blksize_size[MAJOR_NR] = floppy_blocksizes;
  3689.      blk_dev[MAJOR_NR].request_fn = DEVICE_REQUEST;
  3690.  
  3691. -    printk("Atari floppy driver: max. %cD, %strack buffering\n",
  3692. +    printk(KERN_INFO "Atari floppy driver: max. %cD, %strack buffering\n",
  3693.             DriveType == 0 ? 'D' : DriveType == 1 ? 'H' : 'E',
  3694.             UseTrackbuffer ? "" : "no ");
  3695.      config_types();
  3696. @@ -1907,15 +1911,15 @@
  3697.      int i;
  3698.      
  3699.      if (ints[0] < 1) {
  3700. -        printk( "ataflop_setup: no arguments!\n" );
  3701. +        printk(KERN_ERR "ataflop_setup: no arguments!\n" );
  3702.          return;
  3703.      }
  3704.      else if (ints[0] > 2+FD_MAX_UNITS) {
  3705. -        printk( "ataflop_setup: too many arguments\n" );
  3706. +        printk(KERN_ERR "ataflop_setup: too many arguments\n" );
  3707.      }
  3708.  
  3709.      if (ints[1] < 0 || ints[1] > 2)
  3710. -        printk( "ataflop_setup: bad drive type\n" );
  3711. +        printk(KERN_ERR "ataflop_setup: bad drive type\n" );
  3712.      else
  3713.          DriveType = ints[1];
  3714.  
  3715. @@ -1924,7 +1928,7 @@
  3716.  
  3717.      for( i = 3; i <= ints[0] && i-3 < FD_MAX_UNITS; ++i ) {
  3718.          if (ints[i] != 2 && ints[i] != 3 && ints[i] != 6 && ints[i] != 12)
  3719. -            printk( "ataflop_setup: bad steprate\n" );
  3720. +            printk(KERN_ERR "ataflop_setup: bad steprate\n" );
  3721.          else
  3722.              UserSteprate[i-3] = ints[i];
  3723.      }
  3724. @@ -1933,6 +1937,8 @@
  3725.  #ifdef MODULE
  3726.  int init_module (void)
  3727.  {
  3728. +    if (!MACH_IS_ATARI)
  3729. +        return -ENXIO;
  3730.      return atari_floppy_init ();
  3731.  }
  3732.  
  3733. @@ -1944,13 +1950,6 @@
  3734.      timer_active &= ~(1 << FLOPPY_TIMER);
  3735.      timer_table[FLOPPY_TIMER].fn = 0;
  3736.      kfree (DMABuffer);
  3737. -}
  3738. -#else
  3739. -/*
  3740. - * This is just a dummy function to keep fs/super.c happy.
  3741. - */
  3742. -void floppy_eject(void)
  3743. -{
  3744.  }
  3745.  #endif
  3746.  
  3747. diff -u --recursive --new-file pre2.0.4/linux/drivers/block/floppy.c linux/drivers/block/floppy.c
  3748. --- pre2.0.4/linux/drivers/block/floppy.c    Wed May 15 11:01:14 1996
  3749. +++ linux/drivers/block/floppy.c    Wed May 15 10:08:25 1996
  3750. @@ -482,7 +482,6 @@
  3751.  static void process_fd_request(void);
  3752.  static void recalibrate_floppy(void);
  3753.  static void floppy_shutdown(void);
  3754. -static void unexpected_floppy_interrupt(void);
  3755.  
  3756.  static int floppy_grab_irq_and_dma(void);
  3757.  static void floppy_release_irq_and_dma(void);
  3758. @@ -525,21 +524,9 @@
  3759.  static long current_count_sectors = 0;
  3760.  static unsigned char sector_t; /* sector in track */
  3761.  
  3762. -
  3763.  #ifndef fd_eject
  3764. -#ifdef __sparc__
  3765. -static int fd_eject(int drive)
  3766. -{
  3767. -    set_dor(0, ~0, 0x90);
  3768. -    udelay(500);
  3769. -    set_dor(0, ~0x80, 0);
  3770. -    udelay(500);
  3771. -    return 0;
  3772. -}
  3773. -#else
  3774.  #define fd_eject(x) -EINVAL
  3775.  #endif
  3776. -#endif
  3777.  
  3778.  
  3779.  #ifdef DEBUGT
  3780. @@ -930,7 +917,7 @@
  3781.  }
  3782.  
  3783.  static struct tq_struct floppy_tq =
  3784. -{ 0, 0, (void *) (void *) unexpected_floppy_interrupt, 0 };
  3785. +{ 0, 0, 0, 0 };
  3786.  
  3787.  static struct timer_list fd_timer ={ NULL, NULL, 0, 0, 0 };
  3788.  
  3789. @@ -1660,40 +1647,22 @@
  3790.      floppy_ready();
  3791.  }
  3792.  
  3793. -/*
  3794. - * Unexpected interrupt - Print as much debugging info as we can...
  3795. - * All bets are off...
  3796. - */
  3797. -static void unexpected_floppy_interrupt(void)
  3798. +static void print_result(char *message, int inr)
  3799.  {
  3800.      int i;
  3801. -    if (initialising)
  3802. -        return;
  3803. -    if (print_unex){
  3804. -        DPRINT("unexpected interrupt\n");
  3805. -        if (inr >= 0)
  3806. -            for (i=0; i<inr; i++)
  3807. -                printk("%d %x\n", i, reply_buffer[i]);
  3808. -    }
  3809. -    FDCS->reset = 0;        /* Allow SENSEI to be sent. */
  3810. -    while(1){
  3811. -        output_byte(FD_SENSEI);
  3812. -        inr=result();
  3813. -        if (inr != 2)
  3814. -            break;
  3815. -        if (print_unex){
  3816. -            printk("sensei\n");
  3817. -            for (i=0; i<inr; i++)
  3818. -                printk("%d %x\n", i, reply_buffer[i]);
  3819. -        }
  3820. -    }
  3821. -    FDCS->reset = 1;
  3822. +
  3823. +    DPRINT("%s ", message);
  3824. +    if (inr >= 0)
  3825. +        for (i=0; i<inr; i++)
  3826. +            printk("repl[%d]=%x ", i, reply_buffer[i]);
  3827. +    printk("\n");
  3828.  }
  3829.  
  3830.  /* interrupt handler */
  3831.  void floppy_interrupt(int irq, void *dev_id, struct pt_regs * regs)
  3832.  {
  3833.      void (*handler)(void) = DEVICE_INTR;
  3834. +    int do_print;
  3835.  
  3836.      lasthandler = handler;
  3837.      interruptjiffies = jiffies;
  3838. @@ -1709,20 +1678,36 @@
  3839.          is_alive("bizarre fdc");
  3840.          return;
  3841.      }
  3842. +
  3843. +    FDCS->reset = 0;
  3844. +    /* We have to clear the reset flag here, because apparently on boxes
  3845. +     * with level triggered interrupts (PS/2, Sparc, ...), it is needed to
  3846. +     * emit SENSEI's to clear the interrupt line. And FDCS->reset blocks the
  3847. +     * emission of the SENSEI's.
  3848. +     * It is OK to emit floppy commands because we are in an interrupt
  3849. +     * handler here, and thus we have to fear no interference of other
  3850. +     * activity.
  3851. +     */
  3852. +
  3853. +    do_print = !handler && print_unex && !initialising;
  3854. +
  3855.      inr = result();
  3856. -    if (!handler){
  3857. -        unexpected_floppy_interrupt();
  3858. -        is_alive("unexpected");
  3859. -        return;
  3860. -    }
  3861. +    if(do_print)
  3862. +        print_result("unexpected interrupt", inr);
  3863.      if (inr == 0){
  3864.          do {
  3865.              output_byte(FD_SENSEI);
  3866.              inr = result();
  3867. +            if(do_print)
  3868. +                print_result("sensei", inr);
  3869.          } while ((ST0 & 0x83) != UNIT(current_drive) && inr == 2);
  3870.      }
  3871. -    floppy_tq.routine = (void *)(void *) handler;
  3872. -    queue_task_irq(&floppy_tq, &tq_timer);
  3873. +    if (handler) {
  3874. +        /* expected interrupt */
  3875. +        floppy_tq.routine = (void *)(void *) handler;
  3876. +        queue_task_irq(&floppy_tq, &tq_timer);
  3877. +    } else
  3878. +        FDCS->reset = 1;
  3879.      is_alive("normal interrupt end");
  3880.  }
  3881.  
  3882. @@ -4098,12 +4083,13 @@
  3883.      sti();
  3884.      MOD_INC_USE_COUNT;
  3885.      for (i=0; i< N_FDC; i++){
  3886. -        if (FDCS->address != -1){
  3887. +        if (fdc_state[i].address != -1){
  3888.              fdc = i;
  3889.              reset_fdc_info(1);
  3890.              fd_outb(FDCS->dor, FD_DOR);
  3891.          }
  3892.      }
  3893. +    fdc = 0;
  3894.      set_dor(0, ~0, 8);  /* avoid immediate interrupt */
  3895.  
  3896.      if (fd_request_irq()) {
  3897. diff -u --recursive --new-file pre2.0.4/linux/drivers/block/ide.c linux/drivers/block/ide.c
  3898. --- pre2.0.4/linux/drivers/block/ide.c    Sun May 12 22:54:22 1996
  3899. +++ linux/drivers/block/ide.c    Wed May 15 10:33:05 1996
  3900. @@ -1,5 +1,5 @@
  3901.  /*
  3902. - *  linux/drivers/block/ide.c    Version 5.42  May 12, 1996
  3903. + *  linux/drivers/block/ide.c    Version 5.43  May 14, 1996
  3904.   *
  3905.   *  Copyright (C) 1994-1996  Linus Torvalds & authors (see below)
  3906.   */
  3907. @@ -237,6 +237,7 @@
  3908.   *            disable io_32bit by default on drive reset
  3909.   * Version 5.42        simplify irq-masking after probe
  3910.   *            fix NULL pointer deref in save_match()
  3911. + * Version 5.43        Ugh.. unexpected_intr is back: try to exterminate it
  3912.   *
  3913.   *  Some additional driver compile-time options are in ide.h
  3914.   *
  3915. @@ -2421,11 +2422,14 @@
  3916.      } else
  3917.          rc = 2;            /* drive refused ID */
  3918.      if (!HWIF(drive)->irq) {
  3919. -        OUT_BYTE(drive->ctl|2,IDE_CONTROL_REG); /* mask device irq */
  3920. -        udelay(5);
  3921.          irqs = probe_irq_off(irqs);    /* get our irq number */
  3922.          if (irqs > 0) {
  3923.              HWIF(drive)->irq = irqs; /* save it for later */
  3924. +            irqs = probe_irq_on();
  3925. +            OUT_BYTE(drive->ctl|2,IDE_CONTROL_REG); /* mask device irq */
  3926. +            udelay(5);
  3927. +            (void) GET_STAT();    /* clear drive IRQ */
  3928. +            (void) probe_irq_off(irqs);
  3929.          } else {    /* Mmmm.. multiple IRQs.. don't know which was ours */
  3930.              printk("%s: IRQ probe failed (%d)\n", drive->name, irqs);
  3931.  #ifdef CONFIG_BLK_DEV_CMD640
  3932. diff -u --recursive --new-file pre2.0.4/linux/drivers/block/linear.c linux/drivers/block/linear.c
  3933. --- pre2.0.4/linux/drivers/block/linear.c    Mon May 13 23:02:47 1996
  3934. +++ linux/drivers/block/linear.c    Wed May 15 09:09:00 1996
  3935. @@ -193,10 +193,7 @@
  3936.  
  3937.  void cleanup_module (void)
  3938.  {
  3939. -  if (MOD_IN_USE)
  3940. -    printk ("md linear : module still busy...\n");
  3941. -  else
  3942. -    unregister_md_personality (LINEAR);
  3943. +  unregister_md_personality (LINEAR);
  3944.  }
  3945.  
  3946.  #endif
  3947. diff -u --recursive --new-file pre2.0.4/linux/drivers/block/raid0.c linux/drivers/block/raid0.c
  3948. --- pre2.0.4/linux/drivers/block/raid0.c    Sun Apr 21 19:22:02 1996
  3949. +++ linux/drivers/block/raid0.c    Wed May 15 09:09:00 1996
  3950. @@ -291,10 +291,7 @@
  3951.  
  3952.  void cleanup_module (void)
  3953.  {
  3954. -  if (MOD_IN_USE)
  3955. -    printk ("md raid0 : module still busy...\n");
  3956. -  else
  3957. -    unregister_md_personality (RAID0);
  3958. +  unregister_md_personality (RAID0);
  3959.  }
  3960.  
  3961.  #endif
  3962. diff -u --recursive --new-file pre2.0.4/linux/drivers/cdrom/Config.in linux/drivers/cdrom/Config.in
  3963. --- pre2.0.4/linux/drivers/cdrom/Config.in    Mon Apr 29 18:05:17 1996
  3964. +++ linux/drivers/cdrom/Config.in    Thu May 16 16:35:39 1996
  3965. @@ -1,9 +1,8 @@
  3966.  #
  3967.  # CDROM driver configuration
  3968.  #
  3969. -tristate 'Sony CDU31A/CDU33A CDROM support' CONFIG_CDU31A
  3970. -tristate 'Standard Mitsumi [no XA/Multisession] CDROM support' CONFIG_MCD
  3971. -tristate 'Mitsumi [XA/MultiSession] CDROM support' CONFIG_MCDX
  3972. +tristate 'Aztech/Orchid/Okano/Wearnes/TXC/CyDROM  CDROM support' CONFIG_AZTCD
  3973. +tristate 'Goldstar R420 CDROM support' CONFIG_GSCD
  3974.  tristate 'Matsushita/Panasonic/Creative, Longshine, TEAC CDROM support' CONFIG_SBPCD
  3975.  if [ "$CONFIG_SBPCD" = "y" ]; then
  3976.    bool 'Matsushita/Panasonic, ... second CDROM controller support' CONFIG_SBPCD2
  3977. @@ -14,13 +13,14 @@
  3978.      fi
  3979.    fi
  3980.  fi
  3981. -tristate 'Aztech/Orchid/Okano/Wearnes/TXC/CyDROM  CDROM support' CONFIG_AZTCD
  3982. -tristate 'Sony CDU535 CDROM support' CONFIG_CDU535
  3983. -tristate 'Goldstar R420 CDROM support' CONFIG_GSCD
  3984. -tristate 'Philips/LMS CM206 CDROM support' CONFIG_CM206
  3985. +tristate 'Mitsumi (standard) [no XA/Multisession] CDROM support' CONFIG_MCD
  3986. +tristate 'Mitsumi [XA/MultiSession] CDROM support' CONFIG_MCDX
  3987.  tristate 'Optics Storage DOLPHIN 8000AT CDROM support' CONFIG_OPTCD
  3988. +tristate 'Philips/LMS CM206 CDROM support' CONFIG_CM206
  3989.  tristate 'Sanyo CDR-H94A CDROM support' CONFIG_SJCD
  3990.  bool 'Soft configurable cdrom interface card support' CONFIG_CDI_INIT
  3991.  if [ "$CONFIG_CDI_INIT" = "y" ]; then
  3992.    tristate 'ISP16/MAD16/Mozart soft configurable cdrom interface support' CONFIG_ISP16_CDI
  3993.  fi
  3994. +tristate 'Sony CDU31A/CDU33A CDROM support' CONFIG_CDU31A
  3995. +tristate 'Sony CDU535 CDROM support' CONFIG_CDU535
  3996. diff -u --recursive --new-file pre2.0.4/linux/drivers/cdrom/mcdx.c linux/drivers/cdrom/mcdx.c
  3997. --- pre2.0.4/linux/drivers/cdrom/mcdx.c    Mon May 13 23:02:47 1996
  3998. +++ linux/drivers/cdrom/mcdx.c    Fri May 17 15:24:15 1996
  3999. @@ -1,7 +1,7 @@
  4000.  /*
  4001.   * The Mitsumi CDROM interface
  4002.   * Copyright (C) 1995 Heiko Schlittermann <heiko@lotte.sax.de>
  4003. - * VERSION: 2.2
  4004. + * VERSION: 2.3
  4005.   * 
  4006.   * This program is free software; you can redistribute it and/or modify
  4007.   * it under the terms of the GNU General Public License as published by
  4008. @@ -35,8 +35,13 @@
  4009.   * 2.2  1996/05/06 Marcin Dalecki <dalecki@namu03.gwdg.de>
  4010.   *      Mostly fixes to some silly bugs in the previous release :-).
  4011.   *      (Hi Michael Thimm! Thank's for lending me Your's double speed drive.)
  4012. + * 2.3  1996/05/15 Marcin Dalecki <dalecki@namu03.gwdg.de>
  4013. + *    Fixed stereo support. 
  4014. + * NOTE:
  4015. + *    There will be propably a 3.0 adhering to the new generic non ATAPI
  4016. + *    cdrom interface in the unforseen future.
  4017.   */
  4018. -#define VERSION "2.2"
  4019. +#define VERSION "2.3"
  4020.  
  4021.  #include <linux/version.h>
  4022.  #include <linux/module.h>
  4023. @@ -794,7 +799,7 @@
  4024.          memcpy_fromfs(&volctrl, (char *) arg, sizeof(volctrl));
  4025.          /* Adjust for the wiredness of workman. */
  4026.          volctrl.channel2 = volctrl.channel1;
  4027. -        volctrl.channel1 = volctrl.channel3 = 0xff;
  4028. +        volctrl.channel1 = volctrl.channel3 = 0x00;
  4029.          return talk(stuffp, MCDX_CMD_SET_ATTENATOR,
  4030.                  &volctrl, sizeof(volctrl),
  4031.                  &volctrl, sizeof(volctrl), 2 * HZ);
  4032. @@ -1022,7 +1027,8 @@
  4033.      }
  4034.      /*
  4035.       * Check if a disk is in.
  4036. -     */ bang = jiffies + 10 * HZ;
  4037. +     */ 
  4038. +    bang = jiffies + 10 * HZ;
  4039.      while (jiffies < bang) {
  4040.          st = issue_command(stuffp, MCDX_CMD_GET_STATUS, 5 * HZ);
  4041.          if (st != -1 && (st & MCDX_RBIT_DISKSET))
  4042. @@ -1232,7 +1238,6 @@
  4043.  #else
  4044.      printk(KERN_INFO "Mitsumi driver version " VERSION "\n");
  4045.  #endif
  4046. -    printk("%d\n", MCDX_NDRIVES);
  4047.      for (drive = 0; drive < MCDX_NDRIVES; drive++) {
  4048.          struct {
  4049.              u_char code;
  4050. diff -u --recursive --new-file pre2.0.4/linux/drivers/char/Makefile linux/drivers/char/Makefile
  4051. --- pre2.0.4/linux/drivers/char/Makefile    Mon May 13 23:02:48 1996
  4052. +++ linux/drivers/char/Makefile    Thu May 16 16:35:39 1996
  4053. @@ -190,6 +190,14 @@
  4054.    endif
  4055.  endif  
  4056.  
  4057. +ifeq ($(CONFIG_BAYCOM),y)
  4058. +L_OBJS += baycom.o
  4059. +else
  4060. +  ifeq ($(CONFIG_BAYCOM),m)
  4061. +  M_OBJS += baycom.o
  4062. +  endif
  4063. +endif  
  4064. +
  4065.  ifdef CONFIG_TGA_CONSOLE
  4066.  L_OBJS += tga.o
  4067.  else
  4068. diff -u --recursive --new-file pre2.0.4/linux/drivers/char/README.baycom linux/drivers/char/README.baycom
  4069. --- pre2.0.4/linux/drivers/char/README.baycom    Thu Jan  1 02:00:00 1970
  4070. +++ linux/drivers/char/README.baycom    Thu May 16 16:35:39 1996
  4071. @@ -0,0 +1,164 @@
  4072. +            LINUX DRIVER FOR BAYCOM MODEMS
  4073. +
  4074. +         Thomas M. Sailer <hb9jnx@radio.amiv.ethz.ch>
  4075. +
  4076. +This document describes the Linux Kernel Driver for simple Baycom style
  4077. +amateur radio modems. The driver supports the following modems:
  4078. +
  4079. +ser12: This is a very simple 1200 baud AFSK modem. The modem consists only
  4080. +       of a modulator/demodulator chip, usually a TI TCM3105. The computer
  4081. +       is responsible for regenerating the receiver bit clock, as well as
  4082. +       for handling the HDLC protocol. The modem connects to a serial port,
  4083. +       hence the name. Since the serial port is not used as an async serial
  4084. +       port, the kernel driver for serial ports cannot be used, and this
  4085. +       driver only supports standard serial hardware (8250, 16450, 16550)
  4086. +
  4087. +par96: This is a modem for 9600 baud FSK compatible to the G3RUH standard.
  4088. +       The modem does all the filtering and regenerates the receiver clock.
  4089. +       Data is transferred from and to the PC via a shift register.
  4090. +       The shift register is filled with 16 bits and an interrupt is signalled.
  4091. +       The PC then empties the shift register in a burst. This modem connects
  4092. +       to the parallel port, hence the name. The modem leaves the 
  4093. +       implementation of the HDLC protocol and the scrambler polynomial to
  4094. +       the PC.
  4095. +
  4096. +par97: This is a redesign of the par96 modem by Henning Rech, DF9IC. The modem
  4097. +       is protocol compatible to par96, but uses only three low power ICs
  4098. +       and can therefore be fed from the parallel port and does not require
  4099. +       an additional power supply.
  4100. +
  4101. +All of the above modems only support half duplex communications. However,
  4102. +the driver supports the KISS (see below) fullduplex command. It then simply
  4103. +starts to send as soon as there's a packet to transmit and does not care
  4104. +about DCD, i.e. it starts to send even if there's someone else on the channel.
  4105. +This command is required by some implementations of the DAMA channel 
  4106. +access protocol.
  4107. +
  4108. +
  4109. +The Interface of the driver
  4110. +
  4111. +The driver interfaces to the AX25 stack via a KISS interface. The driver
  4112. +can be accessed as a character device with major 60. Major 60 is the first
  4113. +number of the local/experimental range. I did no steps to coordinate a
  4114. +major number for this driver, but I plan to do so in the near future.
  4115. +The driver supports multiple modems (currently four, as defined with
  4116. +NR_PORTS). It therefore responds to minor numbers 0 to 3. I recommend
  4117. +to access the driver via the special device files /dev/bc[0-3], which
  4118. +can be created with 'make bc'.
  4119. +
  4120. +
  4121. +Compiling and installing the driver
  4122. +
  4123. +First unpack the source files into a directory. Then enter the following: (you
  4124. +must be root to do it)
  4125. +
  4126. +  make dep
  4127. +  make
  4128. +
  4129. +This will create the files baycom.o and setbaycom. baycom.o is as well copied
  4130. +to /lib/modules/`uname -n`/misc. If you plan to use kerneld, do the following:
  4131. +
  4132. +  depmod -a
  4133. +
  4134. +Do not forget to create the device special files if you install the driver the
  4135. +first time. This can be done with:
  4136. +
  4137. +  make bc
  4138. +
  4139. +You are now ready to use the driver. You can now activate the driver manually
  4140. +by entering
  4141. +
  4142. +  insmod baycom
  4143. +
  4144. +or leave this task to kerneld (if installed). Add the following line to
  4145. +/etc/conf.modules
  4146. +
  4147. +  alias char-major-60 baycom
  4148. +
  4149. +
  4150. +
  4151. +Configuring the driver
  4152. +
  4153. +Everytime the driver is inserted into the kernel, it has to know which
  4154. +modems it should access at which ports. This can be done with the setbaycom
  4155. +utility. If you are only using one modem, you can also configure the
  4156. +driver from the insmod command line (or by means of an option line in
  4157. +/etc/conf.modules).
  4158. +
  4159. +Examples:
  4160. +  insmod baycom modem=1 iobase=0x3f8 irq=4 options=1
  4161. +  setbaycom -i /dev/bc0 -p ser12 0x3f8 4 1
  4162. +
  4163. +Both lines configure the first port to drive a ser12 modem at the first
  4164. +serial port (COM1 under DOS). options=1 instructs the driver to use
  4165. +the software DCD algorithm (see below).
  4166. +
  4167. +  insmod baycom modem=2 iobase=0x378 irq=7 options=1
  4168. +  setbaycom -i /dev/bc0 -p par96 0x378 7 1
  4169. +
  4170. +Both lines configure the first port to drive a par96 or par97 modem at the
  4171. +first parallel port (LPT1 under DOS). options=1 instructs the driver to use
  4172. +the software DCD algorithm (see below).
  4173. +  
  4174. +The channel access parameters must be set through KISS parameter frames. The
  4175. +AX25 stack may be used to generate such frames. KA9Q NET derivatives such
  4176. +as WAMPES or TNOS offer the 'param' command for this purpose.
  4177. +
  4178. +
  4179. +
  4180. +Hardware DCD versus Software DCD
  4181. +
  4182. +To avoid collisions on the air, the driver must know when the channel is
  4183. +busy. This is the task of the DCD circuitry/software. The driver may either
  4184. +utilise a software DCD algorithm (options=1) or use a DCD signal from
  4185. +the hardware (options=0).
  4186. +
  4187. +ser12: if software DCD is utilised, the radio's squelch should always be
  4188. +       open. It is highly recommended to use the software DCD algorithm,
  4189. +       as it is much faster than most hardware squelch circuitry. The
  4190. +       disadvantage is a slightly higher load on the system.
  4191. +
  4192. +par96: the software DCD algorithm for this type of modem is rather poor.
  4193. +       The modem simply does not provide enough information to implement
  4194. +       a reasonable DCD algorithm in software. Therefore, if your radio
  4195. +       feeds the DCD input of the PAR96 modem, the use of the hardware
  4196. +       DCD circuitry is recommended.
  4197. +
  4198. +par97: as far as I know it is in this respect equivalent to par96.
  4199. +
  4200. +
  4201. +
  4202. +Compatibility with the rest of the Linux kernel
  4203. +
  4204. +The tty interface gave me some headaches. I did not find a reasonable
  4205. +documentation of its interfaces, so I'm not particularly sure if I implemented
  4206. +it the way I should. Perhaps someone with a more profound knowledge about
  4207. +tty drivers could check the interface routines.
  4208. +The driver produces a rather high interrupt load. par96/par97 generates 600
  4209. +interrupts per second, ser12 1200 while transmitting and 2400 if hardware
  4210. +DCD is used, 3600 otherwise. If other device drivers disable interrupts
  4211. +too long, the performance of the driver drops (the packet loss rate increases),
  4212. +especially with the ser12 modem.
  4213. +There were also reports that under rather high load situations the driver
  4214. +drops frames. This might be either an interrupt problem, or an AX25 stack
  4215. +running in user mode might not get enough CPU time to process the packets
  4216. +before the drivers internal buffers overflow. There is no way to throttle
  4217. +the other radio stations from this layer, throttling must be done in the
  4218. +AX25 layer.
  4219. +
  4220. +The serial driver, the line printer (lp) driver and the baycom driver compete
  4221. +for the same hardware resources. Of course only one driver can access a given
  4222. +interface at a time. The serial driver grabs all interfaces it can find at
  4223. +startup time. Therefore the baycom driver subsequently won't be able to
  4224. +access a serial port. You might therefore find it necessary to release
  4225. +a port owned by the serial driver with 'setserial /dev/ttyS# uart none', where
  4226. +# is the number of the interface. The baycom driver does not reserve any
  4227. +port at startup, unless one is specified on the 'insmod' command line. Another
  4228. +method to solve the problem is to compile all three drivers as modules and
  4229. +leave it to kerneld to load the correct driver depending on the application.
  4230. +
  4231. +
  4232. +
  4233. +vy 73s de
  4234. +Tom Sailer, hb9jnx@radio.amiv.ethz.ch
  4235. +hb9jnx @ hb9w.ampr.org
  4236. diff -u --recursive --new-file pre2.0.4/linux/drivers/char/apm_bios.c linux/drivers/char/apm_bios.c
  4237. --- pre2.0.4/linux/drivers/char/apm_bios.c    Sun May  5 08:51:59 1996
  4238. +++ linux/drivers/char/apm_bios.c    Wed May 15 09:06:55 1996
  4239. @@ -25,6 +25,7 @@
  4240.   *    (Thanks to Ulrich Windl <Ulrich.Windl@rz.uni-regensburg.de>)
  4241.   * April 1996, Stephen Rothwell (Stephen.Rothwell@canb.auug.org.au)
  4242.   *    Version 1.0 and 1.1
  4243. + * May 1996, Version 1.2
  4244.   *
  4245.   * History:
  4246.   *    0.6b: first version in official kernel, Linux 1.3.46
  4247. @@ -35,6 +36,10 @@
  4248.   *         Linux 1.3.85
  4249.   *    1.1: support user-space standby and suspend, power off after system
  4250.   *         halted, Linux 1.3.98
  4251. + *    1.2: When resetting RTC after resume, take care so that the the time
  4252. + *         is only incorrect by 30-60mS (vs. 1S previously) (Gabor J. Toth
  4253. + *         <jtoth@princeton.edu>); improve interaction between
  4254. + *         screen-blanking and gpm (Stephen Rothwell); Linux 1.99.4
  4255.   *
  4256.   * Reference:
  4257.   *
  4258. @@ -334,7 +339,7 @@
  4259.  
  4260.  static struct timer_list    apm_timer;
  4261.  
  4262. -static char            driver_version[] = "1.1";/* no spaces */
  4263. +static char            driver_version[] = "1.2";/* no spaces */
  4264.  
  4265.  #ifdef APM_DEBUG
  4266.  static char *    apm_event_name[] = {
  4267. @@ -625,8 +630,9 @@
  4268.                  /* Estimate time zone so that set_time can
  4269.                                     update the clock */
  4270.      save_flags(flags);
  4271. +    clock_cmos_diff = -get_cmos_time();
  4272.      cli();
  4273. -    clock_cmos_diff = CURRENT_TIME - get_cmos_time();
  4274. +    clock_cmos_diff += CURRENT_TIME;
  4275.      got_clock_diff = 1;
  4276.      restore_flags(flags);
  4277.      
  4278. diff -u --recursive --new-file pre2.0.4/linux/drivers/char/baycom.c linux/drivers/char/baycom.c
  4279. --- pre2.0.4/linux/drivers/char/baycom.c    Thu Jan  1 02:00:00 1970
  4280. +++ linux/drivers/char/baycom.c    Thu May 16 16:35:39 1996
  4281. @@ -0,0 +1,2168 @@
  4282. +/*****************************************************************************/
  4283. +
  4284. +/*
  4285. + *    baycom.c  -- baycom ser12 and par96 radio modem driver.
  4286. + *
  4287. + *    Copyright (C) 1996  Thomas Sailer (sailer@ife.ee.ethz.ch)
  4288. + *
  4289. + *    This program is free software; you can redistribute it and/or modify
  4290. + *    it under the terms of the GNU General Public License as published by
  4291. + *    the Free Software Foundation; either version 2 of the License, or
  4292. + *    (at your option) any later version.
  4293. + *
  4294. + *    This program is distributed in the hope that it will be useful,
  4295. + *    but WITHOUT ANY WARRANTY; without even the implied warranty of
  4296. + *    MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE.  See the
  4297. + *    GNU General Public License for more details.
  4298. + *
  4299. + *    You should have received a copy of the GNU General Public License
  4300. + *    along with this program; if not, write to the Free Software
  4301. + *    Foundation, Inc., 675 Mass Ave, Cambridge, MA 02139, USA.
  4302. + *
  4303. + *  Please note that the GPL allows you to use the driver, NOT the radio.
  4304. + *  In order to use the radio, you need a license from the communications
  4305. + *  authority of your country.
  4306. + *
  4307. + *
  4308. + *  Supported modems
  4309. + *
  4310. + *  ser12: This is a very simple 1200 baud AFSK modem. The modem consists only
  4311. + *         of a modulator/demodulator chip, usually a TI TCM3105. The computer
  4312. + *         is responsible for regenerating the receiver bit clock, as well as
  4313. + *         for handling the HDLC protocol. The modem connects to a serial port,
  4314. + *         hence the name. Since the serial port is not used as an async serial
  4315. + *         port, the kernel driver for serial ports cannot be used, and this
  4316. + *         driver only supports standard serial hardware (8250, 16450, 16550)
  4317. + *  
  4318. + *  par96: This is a modem for 9600 baud FSK compatible to the G3RUH standard.
  4319. + *         The modem does all the filtering and regenerates the receiver clock.
  4320. + *         Data is transferred from and to the PC via a shift register.
  4321. + *         The shift register is filled with 16 bits and an interrupt is
  4322. + *         signalled. The PC then empties the shift register in a burst. This
  4323. + *         modem connects to the parallel port, hence the name. The modem
  4324. + *         leaves the implementation of the HDLC protocol and the scrambler
  4325. + *         polynomial to the PC.
  4326. + *  
  4327. + *  par97: This is a redesign of the par96 modem by Henning Rech, DF9IC. The
  4328. + *         modem is protocol compatible to par96, but uses only three low
  4329. + *         power ICs and can therefore be fed from the parallel port and
  4330. + *         does not require an additional power supply.
  4331. + *
  4332. + *
  4333. + *  Command line options (insmod command line)
  4334. + * 
  4335. + *  major    major number the driver should use; default 60 
  4336. + *  modem    modem type of the first channel (minor 0); 1=ser12,
  4337. + *           2=par96/par97, any other value invalid
  4338. + *  iobase   base address of the port; common values are for ser12 0x3f8,
  4339. + *           0x2f8, 0x3e8, 0x2e8 and for par96/par97 0x378, 0x278, 0x3bc
  4340. + *  irq      interrupt line of the port; common values are for ser12 3,4
  4341. + *           and for par96/par97 7
  4342. + *  options  0=use hardware DCD, 1=use software DCD
  4343. + * 
  4344. + *
  4345. + *  History:
  4346. + *   0.1  03.05.96  Renamed from ser12 0.5 and added support for par96
  4347. + *                  Various resource allocation cleanups
  4348. + *   0.2  12.05.96  Changed major to allocated 51. Integrated into kernel
  4349. + *                  source tree
  4350. + */
  4351. +
  4352. +/*****************************************************************************/
  4353. +
  4354. +#include <linux/module.h>
  4355. +#include <linux/version.h>
  4356. +
  4357. +#include <linux/kernel.h>
  4358. +#include <linux/errno.h>
  4359. +#include <linux/fs.h>
  4360. +#include <linux/major.h>
  4361. +#include <asm/segment.h>
  4362. +#include <linux/kernel.h>
  4363. +#include <linux/signal.h>
  4364. +#include <linux/sched.h>
  4365. +#include <linux/malloc.h>
  4366. +#include <asm/io.h>
  4367. +#include <asm/irq.h>
  4368. +#include <linux/fs.h>
  4369. +#include <linux/mm.h>
  4370. +#include <linux/ioport.h>
  4371. +#include <linux/tty.h>
  4372. +#include <linux/tty_flip.h>
  4373. +
  4374. +#include <linux/baycom.h>
  4375. +
  4376. +/* --------------------------------------------------------------------- */
  4377. +
  4378. +#define BAYCOM_TYPE_NORMAL 0        /* not used */
  4379. +#define TTY_DRIVER_TYPE_BAYCOM 6
  4380. +
  4381. +/*
  4382. + * ser12 options:
  4383. + * BAYCOM_OPTIONS_SOFTDCD: if undefined, you must use the transmitters
  4384. + * hardware carrier detect circuitry, the driver will report DCD as soon as
  4385. + * there are transitions on the input line. Advantage: lower interrupt load
  4386. + * on the system. Disadvantage: slower, since hardware carrier detect
  4387. + * circuitry is usually slow.
  4388. + */
  4389. +
  4390. +#define BUFLEN_RX 16384
  4391. +#define BUFLEN_TX 16384
  4392. +
  4393. +#define NR_PORTS 4
  4394. +
  4395. +#define KISS_VERBOSE
  4396. +#undef HDLC_LOOPBACK
  4397. +
  4398. +#define BAYCOM_MAGIC 0x3105bac0
  4399. +
  4400. +/* --------------------------------------------------------------------- */
  4401. +
  4402. +/*
  4403. + * user settable parameters (from the command line)
  4404. + */
  4405. +#ifndef MODULE
  4406. +static
  4407. +#endif /* MODULE */
  4408. +int major = BAYCOM_MAJOR;
  4409. +
  4410. +/* --------------------------------------------------------------------- */
  4411. +
  4412. +static struct tty_struct *baycom_table[NR_PORTS];
  4413. +static struct termios *baycom_termios[NR_PORTS];
  4414. +static struct termios *baycom_termios_locked[NR_PORTS];
  4415. +
  4416. +static int baycom_refcount;
  4417. +
  4418. +static struct tty_driver baycom_driver;
  4419. +
  4420. +static struct {
  4421. +    int modem, iobase, irq, options;
  4422. +} baycom_ports[NR_PORTS] = { { BAYCOM_MODEM_INVALID, 0, 0, 0, }, };
  4423. +
  4424. +/* --------------------------------------------------------------------- */
  4425. +
  4426. +#define RBR(iobase) (iobase+0)
  4427. +#define THR(iobase) (iobase+0)
  4428. +#define IER(iobase) (iobase+1)
  4429. +#define IIR(iobase) (iobase+2)
  4430. +#define FCR(iobase) (iobase+2)
  4431. +#define LCR(iobase) (iobase+3)
  4432. +#define MCR(iobase) (iobase+4)
  4433. +#define LSR(iobase) (iobase+5)
  4434. +#define MSR(iobase) (iobase+6)
  4435. +#define SCR(iobase) (iobase+7)
  4436. +#define DLL(iobase) (iobase+0)
  4437. +#define DLM(iobase) (iobase+1)
  4438. +
  4439. +#define SER12_EXTENT 8
  4440. +
  4441. +#define LPT_DATA(iobase)    (iobase+0)
  4442. +#define LPT_STATUS(iobase)  (iobase+1)
  4443. +#define LPT_CONTROL(iobase) (iobase+2)
  4444. +#define LPT_IRQ_ENABLE      0x10
  4445. +#define PAR96_BURSTBITS 16
  4446. +#define PAR96_BURST     4
  4447. +#define PAR96_PTT       2
  4448. +#define PAR96_TXBIT     1
  4449. +#define PAR96_ACK       0x40
  4450. +#define PAR96_RXBIT     0x20
  4451. +#define PAR96_DCD       0x10
  4452. +#define PAR97_POWER     0xf8
  4453. +
  4454. +#define PAR96_EXTENT 3
  4455. +
  4456. +/* ---------------------------------------------------------------------- */
  4457. +
  4458. +struct access_params {
  4459. +    int tx_delay;
  4460. +    int tx_tail;
  4461. +    int slottime;
  4462. +    int ppersist;
  4463. +    int fulldup;
  4464. +};
  4465. +
  4466. +struct hdlc_state_rx {
  4467. +    int rx_state;    /* 0 = sync hunt, != 0 receiving */
  4468. +    unsigned char lastbit;
  4469. +    unsigned int bitstream;
  4470. +    unsigned int assembly;
  4471. +    
  4472. +    int len;
  4473. +    unsigned char *bp;
  4474. +    unsigned char buffer[BAYCOM_MAXFLEN+2];       /* make room for CRC */
  4475. +};
  4476. +
  4477. +struct hdlc_state_tx {
  4478. +    /*
  4479. +     * 0 = send flags
  4480. +     * 1 = send txtail (flags)
  4481. +     * 2 = send packet
  4482. +     */
  4483. +    int tx_state;    
  4484. +    int numflags;
  4485. +    unsigned int bitstream;
  4486. +    unsigned int current_byte;
  4487. +    unsigned char ptt;
  4488. +
  4489. +    int len;
  4490. +    unsigned char *bp;
  4491. +    unsigned char buffer[BAYCOM_MAXFLEN+2];        /* make room for CRC */
  4492. +};
  4493. +
  4494. +struct modem_state_ser12 {
  4495. +    unsigned char last_sample;
  4496. +    unsigned char interm_sample;
  4497. +    unsigned int bit_pll;
  4498. +    unsigned int dcd_shreg;
  4499. +    int dcd_sum0, dcd_sum1, dcd_sum2;
  4500. +    unsigned int dcd_time;
  4501. +    unsigned char last_rxbit;
  4502. +    unsigned char tx_bit;
  4503. +};
  4504. +
  4505. +struct modem_state_par96 {
  4506. +    int dcd_count;
  4507. +    unsigned int dcd_shreg;
  4508. +    unsigned long descram;
  4509. +    unsigned long scram;
  4510. +    unsigned int tx_bits;
  4511. +};
  4512. +
  4513. +struct modem_state {
  4514. +    unsigned char dcd;
  4515. +    short arb_divider;
  4516. +    struct modem_state_ser12 ser12;
  4517. +    struct modem_state_par96 par96;
  4518. +};
  4519. +
  4520. +struct packet_buffer {
  4521. +    unsigned int rd;
  4522. +    unsigned int wr;
  4523. +    
  4524. +    unsigned int buflen;
  4525. +    unsigned char *buffer;
  4526. +};
  4527. +
  4528. +struct packet_hdr {
  4529. +    unsigned int next;
  4530. +    unsigned int len;
  4531. +    /* packet following */
  4532. +};
  4533. +
  4534. +#ifdef BAYCOM_DEBUG
  4535. +struct bit_buffer {
  4536. +    unsigned int rd;
  4537. +    unsigned int wr;
  4538. +    unsigned int shreg;
  4539. +    unsigned char buffer[64];
  4540. +};
  4541. +
  4542. +struct debug_vals {
  4543. +    unsigned long last_jiffies;
  4544. +    unsigned cur_intcnt;
  4545. +    unsigned last_intcnt;
  4546. +    int cur_pllcorr;
  4547. +    int last_pllcorr;
  4548. +};
  4549. +#endif /* BAYCOM_DEBUG */
  4550. +
  4551. +struct kiss_decode {
  4552. +    unsigned char dec_state; /* 0 = hunt FEND */
  4553. +    unsigned char escaped;
  4554. +    unsigned char pkt_buf[BAYCOM_MAXFLEN+1];
  4555. +    unsigned int wr;
  4556. +};
  4557. +
  4558. +/* ---------------------------------------------------------------------- */
  4559. +
  4560. +struct baycom_state {
  4561. +    int magic;
  4562. +
  4563. +    unsigned char modem_type;
  4564. +
  4565. +    unsigned int iobase;
  4566. +    unsigned int irq;
  4567. +    unsigned int options;
  4568. +
  4569. +    int opened;
  4570. +    struct tty_struct *tty;
  4571. +
  4572. +    struct packet_buffer rx_buf;
  4573. +    struct packet_buffer tx_buf;
  4574. +
  4575. +    struct access_params ch_params;
  4576. +
  4577. +    struct hdlc_state_rx hdlc_rx;
  4578. +    struct hdlc_state_tx hdlc_tx;
  4579. +
  4580. +    int calibrate;
  4581. +
  4582. +    struct modem_state modem;
  4583. +
  4584. +#ifdef BAYCOM_DEBUG
  4585. +    struct bit_buffer bitbuf_channel;
  4586. +    struct bit_buffer bitbuf_hdlc;
  4587. +    
  4588. +    struct debug_vals debug_vals;
  4589. +#endif /* BAYCOM_DEBUG */
  4590. +
  4591. +    struct kiss_decode kiss_decode;
  4592. +
  4593. +    struct baycom_statistics stat;
  4594. +};
  4595. +
  4596. +/* --------------------------------------------------------------------- */
  4597. +
  4598. +struct baycom_state baycom_state[NR_PORTS];
  4599. +
  4600. +/* --------------------------------------------------------------------- */
  4601. +
  4602. +/*
  4603. + * the CRC routines are stolen from WAMPES
  4604. + * by Dieter Deyke
  4605. + */
  4606. +
  4607. +static const unsigned short crc_ccitt_table[] = {
  4608. +    0x0000, 0x1189, 0x2312, 0x329b, 0x4624, 0x57ad, 0x6536, 0x74bf,
  4609. +    0x8c48, 0x9dc1, 0xaf5a, 0xbed3, 0xca6c, 0xdbe5, 0xe97e, 0xf8f7,
  4610. +    0x1081, 0x0108, 0x3393, 0x221a, 0x56a5, 0x472c, 0x75b7, 0x643e,
  4611. +    0x9cc9, 0x8d40, 0xbfdb, 0xae52, 0xdaed, 0xcb64, 0xf9ff, 0xe876,
  4612. +    0x2102, 0x308b, 0x0210, 0x1399, 0x6726, 0x76af, 0x4434, 0x55bd,
  4613. +    0xad4a, 0xbcc3, 0x8e58, 0x9fd1, 0xeb6e, 0xfae7, 0xc87c, 0xd9f5,
  4614. +    0x3183, 0x200a, 0x1291, 0x0318, 0x77a7, 0x662e, 0x54b5, 0x453c,
  4615. +    0xbdcb, 0xac42, 0x9ed9, 0x8f50, 0xfbef, 0xea66, 0xd8fd, 0xc974,
  4616. +    0x4204, 0x538d, 0x6116, 0x709f, 0x0420, 0x15a9, 0x2732, 0x36bb,
  4617. +    0xce4c, 0xdfc5, 0xed5e, 0xfcd7, 0x8868, 0x99e1, 0xab7a, 0xbaf3,
  4618. +    0x5285, 0x430c, 0x7197, 0x601e, 0x14a1, 0x0528, 0x37b3, 0x263a,
  4619. +    0xdecd, 0xcf44, 0xfddf, 0xec56, 0x98e9, 0x8960, 0xbbfb, 0xaa72,
  4620. +    0x6306, 0x728f, 0x4014, 0x519d, 0x2522, 0x34ab, 0x0630, 0x17b9,
  4621. +    0xef4e, 0xfec7, 0xcc5c, 0xddd5, 0xa96a, 0xb8e3, 0x8a78, 0x9bf1,
  4622. +    0x7387, 0x620e, 0x5095, 0x411c, 0x35a3, 0x242a, 0x16b1, 0x0738,
  4623. +    0xffcf, 0xee46, 0xdcdd, 0xcd54, 0xb9eb, 0xa862, 0x9af9, 0x8b70,
  4624. +    0x8408, 0x9581, 0xa71a, 0xb693, 0xc22c, 0xd3a5, 0xe13e, 0xf0b7,
  4625. +    0x0840, 0x19c9, 0x2b52, 0x3adb, 0x4e64, 0x5fed, 0x6d76, 0x7cff,
  4626. +    0x9489, 0x8500, 0xb79b, 0xa612, 0xd2ad, 0xc324, 0xf1bf, 0xe036,
  4627. +    0x18c1, 0x0948, 0x3bd3, 0x2a5a, 0x5ee5, 0x4f6c, 0x7df7, 0x6c7e,
  4628. +    0xa50a, 0xb483, 0x8618, 0x9791, 0xe32e, 0xf2a7, 0xc03c, 0xd1b5,
  4629. +    0x2942, 0x38cb, 0x0a50, 0x1bd9, 0x6f66, 0x7eef, 0x4c74, 0x5dfd,
  4630. +    0xb58b, 0xa402, 0x9699, 0x8710, 0xf3af, 0xe226, 0xd0bd, 0xc134,
  4631. +    0x39c3, 0x284a, 0x1ad1, 0x0b58, 0x7fe7, 0x6e6e, 0x5cf5, 0x4d7c,
  4632. +    0xc60c, 0xd785, 0xe51e, 0xf497, 0x8028, 0x91a1, 0xa33a, 0xb2b3,
  4633. +    0x4a44, 0x5bcd, 0x6956, 0x78df, 0x0c60, 0x1de9, 0x2f72, 0x3efb,
  4634. +    0xd68d, 0xc704, 0xf59f, 0xe416, 0x90a9, 0x8120, 0xb3bb, 0xa232,
  4635. +    0x5ac5, 0x4b4c, 0x79d7, 0x685e, 0x1ce1, 0x0d68, 0x3ff3, 0x2e7a,
  4636. +    0xe70e, 0xf687, 0xc41c, 0xd595, 0xa12a, 0xb0a3, 0x8238, 0x93b1,
  4637. +    0x6b46, 0x7acf, 0x4854, 0x59dd, 0x2d62, 0x3ceb, 0x0e70, 0x1ff9,
  4638. +    0xf78f, 0xe606, 0xd49d, 0xc514, 0xb1ab, 0xa022, 0x92b9, 0x8330,
  4639. +    0x7bc7, 0x6a4e, 0x58d5, 0x495c, 0x3de3, 0x2c6a, 0x1ef1, 0x0f78
  4640. +};
  4641. +
  4642. +/*---------------------------------------------------------------------------*/
  4643. +
  4644. +static inline void append_crc_ccitt(unsigned char *buffer, int len)
  4645. +{
  4646. +     unsigned int crc = 0xffff;
  4647. +
  4648. +    for (;len>0;len--)
  4649. +        crc = (crc >> 8) ^ crc_ccitt_table[(crc ^ *buffer++) & 0xff];
  4650. +    crc ^= 0xffff;
  4651. +    *buffer++ = crc;
  4652. +    *buffer++ = crc >> 8;
  4653. +}
  4654. +
  4655. +/*---------------------------------------------------------------------------*/
  4656. +
  4657. +static inline int check_crc_ccitt(const unsigned char *buf,int cnt)
  4658. +{
  4659. +    unsigned int crc = 0xffff;
  4660. +
  4661. +    for (; cnt > 0; cnt--)
  4662. +        crc = (crc >> 8) ^ crc_ccitt_table[(crc ^ *buf++) & 0xff];
  4663. +    return (crc & 0xffff) == 0xf0b8;
  4664. +}
  4665. +
  4666. +/*---------------------------------------------------------------------------*/
  4667. +
  4668. +#if 0
  4669. +static int calc_crc_ccitt(const unsigned char *buf,int cnt)
  4670. +{
  4671. +    unsigned int crc = 0xffff;
  4672. +
  4673. +    for (; cnt > 0; cnt--)
  4674. +        crc = (crc >> 8) ^ crc_ccitt_table[(crc ^ *buf++) & 0xff];
  4675. +    crc ^= 0xffff;
  4676. +    return (crc & 0xffff);
  4677. +}
  4678. +#endif
  4679. +
  4680. +/* ---------------------------------------------------------------------- */
  4681. +
  4682. +static int store_packet(struct packet_buffer *buf, unsigned char *data,
  4683. +    char from_user, unsigned int len)
  4684. +{
  4685. +    unsigned int free;
  4686. +    struct packet_hdr *hdr;
  4687. +    unsigned int needed = sizeof(struct packet_hdr)+len;
  4688. +    
  4689. +    free = buf->rd-buf->wr;
  4690. +    if(buf->rd <= buf->wr) {
  4691. +        free = buf->buflen - buf->wr;
  4692. +        if((free < needed) && (buf->rd >= needed)) {
  4693. +            hdr = (struct packet_hdr *)(buf->buffer+buf->wr);
  4694. +            hdr->next = 0;
  4695. +            hdr->len = 0;
  4696. +            buf->wr = 0;
  4697. +            free = buf->rd;
  4698. +        }
  4699. +    }
  4700. +    if(free < needed) return 0;        /* buffer overrun */
  4701. +    hdr = (struct packet_hdr *)(buf->buffer+buf->wr);
  4702. +    if (from_user) 
  4703. +        memcpy_fromfs(hdr+1,data,len);
  4704. +    else
  4705. +        memcpy(hdr+1,data,len);
  4706. +    hdr->len = len;
  4707. +    hdr->next = buf->wr+needed;
  4708. +    if (hdr->next + sizeof(struct packet_hdr) >= buf->buflen)
  4709. +        hdr->next = 0;
  4710. +    buf->wr = hdr->next;
  4711. +    return 1;
  4712. +}
  4713. +    
  4714. +/* ---------------------------------------------------------------------- */
  4715. +
  4716. +static void get_packet(struct packet_buffer *buf, unsigned char **data,
  4717. +    unsigned int *len)
  4718. +{
  4719. +    struct packet_hdr *hdr;
  4720. +    
  4721. +    *data = NULL;
  4722. +    *len = 0;
  4723. +    if (buf->rd == buf->wr)
  4724. +        return;
  4725. +    hdr = (struct packet_hdr *)(buf->buffer+buf->rd);
  4726. +    while (!(hdr->len)) {
  4727. +        buf->rd = hdr->next;
  4728. +        if (buf->rd == buf->wr)
  4729. +            return;
  4730. +        hdr = (struct packet_hdr *)(buf->buffer+buf->rd);
  4731. +    }
  4732. +    *data = (unsigned char *)(hdr+1);
  4733. +    *len = hdr->len;
  4734. +}
  4735. +
  4736. +/* ---------------------------------------------------------------------- */
  4737. +
  4738. +static void ack_packet(struct packet_buffer *buf)
  4739. +{
  4740. +    struct packet_hdr *hdr;
  4741. +    
  4742. +    if (buf->rd == buf->wr)
  4743. +        return;
  4744. +    hdr = (struct packet_hdr *)(buf->buffer+buf->rd);
  4745. +    buf->rd = hdr->next;
  4746. +}
  4747. +
  4748. +/* ---------------------------------------------------------------------- */
  4749. +
  4750. +static int store_kiss_packet(struct packet_buffer *buf, unsigned char *data,
  4751. +    unsigned int len)
  4752. +{
  4753. +    unsigned char *bp = data;
  4754. +    int ln = len;
  4755. +    /*
  4756. +     * variables of buf
  4757. +     */
  4758. +    unsigned int rd;
  4759. +    unsigned int wr;
  4760. +    unsigned int buflen;
  4761. +    unsigned char *buffer;
  4762. +
  4763. +    if (!len || !data || !buf)
  4764. +        return 0;
  4765. +    buflen = buf->buflen;
  4766. +    rd = buf->rd;
  4767. +    wr = buf->wr;
  4768. +    buffer = buf->buffer;
  4769. +    
  4770. +#define ADD_CHAR(c) {\
  4771. +        buffer[wr++] = c;\
  4772. +        if (wr >= buflen) wr = 0;\
  4773. +        if (wr == rd) return 0;\
  4774. +    }
  4775. +#define ADD_KISSCHAR(c) {\
  4776. +        if (((c) & 0xff) == KISS_FEND) {\
  4777. +            ADD_CHAR(KISS_FESC);\
  4778. +            ADD_CHAR(KISS_TFEND);\
  4779. +        } else if (((c) & 0xff) == KISS_FESC) {\
  4780. +            ADD_CHAR(KISS_FESC);\
  4781. +            ADD_CHAR(KISS_TFESC);\
  4782. +        } else {\
  4783. +            ADD_CHAR(c);\
  4784. +        }\
  4785. +    }
  4786. +
  4787. +    ADD_CHAR(KISS_FEND);
  4788. +    ADD_KISSCHAR(KISS_CMD_DATA);
  4789. +    for(; ln > 0; ln--,bp++) {
  4790. +        ADD_KISSCHAR(*bp);
  4791. +    }
  4792. +    ADD_CHAR(KISS_FEND);
  4793. +    buf->wr = wr;
  4794. +#undef ADD_CHAR
  4795. +#undef ADD_KISSCHAR
  4796. +    return 1;
  4797. +}
  4798. +
  4799. +/* ---------------------------------------------------------------------- */
  4800. +
  4801. +#ifdef BAYCOM_DEBUG
  4802. +static inline void add_bitbuffer(struct bit_buffer * buf, unsigned int bit)
  4803. +{
  4804. +    if (!buf) return;
  4805. +    buf->shreg <<= 1;
  4806. +    if (bit)
  4807. +        buf->shreg |= 1;
  4808. +    if (buf->shreg & 0x100) {
  4809. +        buf->buffer[buf->wr] = buf->shreg;
  4810. +        buf->wr = (buf->wr+1) % sizeof(buf->buffer);
  4811. +        buf->shreg = 1;
  4812. +    }
  4813. +}
  4814. +#endif /* BAYCOM_DEBUG */
  4815. +
  4816. +/* ---------------------------------------------------------------------- */
  4817. +
  4818. +static inline unsigned int tenms_to_flags(struct baycom_state *bc, 
  4819. +                      unsigned int tenms)
  4820. +{
  4821. +    switch (bc->modem_type) {
  4822. +    case BAYCOM_MODEM_SER12:
  4823. +        return tenms * 12 / 8;
  4824. +    case BAYCOM_MODEM_PAR96:
  4825. +        return tenms * 12;
  4826. +    default:
  4827. +        return 0;
  4828. +    }
  4829. +}
  4830. +
  4831. +/* ---------------------------------------------------------------------- */
  4832. +/*
  4833. + * The HDLC routines could be more efficient; they could take more than
  4834. + * one bit per call
  4835. + */
  4836. +
  4837. +static void hdlc_rx_bit(struct baycom_state *bc, unsigned int bit)
  4838. +{
  4839. +    if (!bc) return;
  4840. +
  4841. +    bc->hdlc_rx.bitstream <<= 1;
  4842. +    if (bit)
  4843. +        bc->hdlc_rx.bitstream |= 1;
  4844. +#ifdef BAYCOM_DEBUG
  4845. +    add_bitbuffer(&bc->bitbuf_hdlc, bc->hdlc_rx.bitstream & 1);
  4846. +#endif /* BAYCOM_DEBUG */
  4847. +    if(bc->hdlc_rx.rx_state) {
  4848. +        if ((bc->hdlc_rx.bitstream & 0x3f) != 0x3e) {
  4849. +            /* not a stuffed bit */
  4850. +            if (bc->hdlc_rx.bitstream & 1)
  4851. +                bc->hdlc_rx.assembly |= 0x100;
  4852. +            if (bc->hdlc_rx.assembly & 1) {
  4853. +                /* store byte */
  4854. +                if (bc->hdlc_rx.len >= sizeof(bc->hdlc_rx.buffer)) {
  4855. +                    bc->hdlc_rx.rx_state = 0;
  4856. +                } else {
  4857. +                    *bc->hdlc_rx.bp++ = bc->hdlc_rx.assembly>>1;
  4858. +                    bc->hdlc_rx.len++;
  4859. +                    bc->hdlc_rx.assembly = 0x80;
  4860. +                }
  4861. +            } else {
  4862. +                bc->hdlc_rx.assembly >>= 1;
  4863. +            }
  4864. +        }
  4865. +        if ((bc->hdlc_rx.bitstream & 0x7f) == 0x7e) {
  4866. +            if (bc->hdlc_rx.len >= 4) {
  4867. +                if (check_crc_ccitt(bc->hdlc_rx.buffer,bc->hdlc_rx.len)) {
  4868. +                    bc->stat.rx_packets++;
  4869. +                    if (!store_kiss_packet(&bc->rx_buf,bc->hdlc_rx.buffer,bc->hdlc_rx.len-2))
  4870. +                        bc->stat.rx_bufferoverrun++;
  4871. +                }
  4872. +            }
  4873. +            bc->hdlc_rx.len = 0;
  4874. +            bc->hdlc_rx.bp = bc->hdlc_rx.buffer;
  4875. +            bc->hdlc_rx.assembly = 0x80;
  4876. +        }
  4877. +        if ((bc->hdlc_rx.bitstream & 0x7f) == 0x7f)
  4878. +            bc->hdlc_rx.rx_state = 0;
  4879. +    } else {
  4880. +        if ((bc->hdlc_rx.bitstream & 0x7f) == 0x7e) {
  4881. +            bc->hdlc_rx.len = 0;
  4882. +            bc->hdlc_rx.bp = bc->hdlc_rx.buffer;
  4883. +            bc->hdlc_rx.assembly = 0x80;
  4884. +            bc->hdlc_rx.rx_state = 1;
  4885. +        }
  4886. +    }
  4887. +}
  4888. +
  4889. +/* ---------------------------------------------------------------------- */
  4890. +
  4891. +static unsigned char hdlc_tx_bit(struct baycom_state *bc)
  4892. +{
  4893. +    unsigned char bit;
  4894. +
  4895. +    if (!bc || !bc->hdlc_tx.ptt)
  4896. +        return 0;
  4897. +    for(;;) {
  4898. +        switch (bc->hdlc_tx.tx_state) {
  4899. +        default:
  4900. +            bc->hdlc_tx.ptt = 0;
  4901. +            bc->hdlc_tx.tx_state = 0;
  4902. +            return 0;
  4903. +        case 0:
  4904. +        case 1:
  4905. +            if (bc->hdlc_tx.current_byte > 1) {
  4906. +                /*
  4907. +                 * return bit 
  4908. +                 */
  4909. +                bit = bc->hdlc_tx.current_byte & 1;
  4910. +                bc->hdlc_tx.current_byte >>= 1;
  4911. +                return bit;
  4912. +            }
  4913. +            /*
  4914. +             * get new bit 
  4915. +             */
  4916. +            if (bc->hdlc_tx.numflags) {
  4917. +                bc->hdlc_tx.numflags--;
  4918. +                bc->hdlc_tx.current_byte = 0x17e;
  4919. +            } else {
  4920. +                if (bc->hdlc_tx.tx_state == 1) {
  4921. +                    bc->hdlc_tx.ptt = 0;
  4922. +                    return 0;
  4923. +                }
  4924. +                get_packet(&bc->tx_buf, &bc->hdlc_tx.bp,
  4925. +                       &bc->hdlc_tx.len);
  4926. +                if (!bc->hdlc_tx.bp || !bc->hdlc_tx.len) {
  4927. +                    bc->hdlc_tx.tx_state = 1;
  4928. +                    bc->hdlc_tx.current_byte = 0;
  4929. +                    bc->hdlc_tx.numflags = tenms_to_flags
  4930. +                        (bc, bc->ch_params.tx_tail);
  4931. +                } else if (bc->hdlc_tx.len >= BAYCOM_MAXFLEN) {
  4932. +                    bc->hdlc_tx.tx_state = 0;
  4933. +                    bc->hdlc_tx.current_byte = 0;
  4934. +                    bc->hdlc_tx.numflags = 1;
  4935. +                    ack_packet(&bc->tx_buf);
  4936. +                } else {
  4937. +                    memcpy(bc->hdlc_tx.buffer,
  4938. +                           bc->hdlc_tx.bp, 
  4939. +                           bc->hdlc_tx.len);
  4940. +                    ack_packet(&bc->tx_buf);
  4941. +                    bc->hdlc_tx.bp = bc->hdlc_tx.buffer;
  4942. +                    append_crc_ccitt(bc->hdlc_tx.buffer,
  4943. +                             bc->hdlc_tx.len);
  4944. +                    /* the appended CRC */
  4945. +                    bc->hdlc_tx.len += 2; 
  4946. +                    bc->hdlc_tx.tx_state = 2;
  4947. +                    bc->hdlc_tx.current_byte = 0;
  4948. +                    bc->hdlc_tx.bitstream = 0;
  4949. +                    bc->stat.tx_packets++;
  4950. +                }
  4951. +            }
  4952. +            break;
  4953. +        case 2:
  4954. +            if ((bc->hdlc_tx.bitstream & 0x1f) == 0x1f) {
  4955. +                /*
  4956. +                 * bit stuffing
  4957. +                 */
  4958. +                bc->hdlc_tx.bitstream <<= 1;
  4959. +                return 0;
  4960. +            }
  4961. +            if (bc->hdlc_tx.current_byte > 1) {
  4962. +                /*
  4963. +                 * return bit 
  4964. +                 */
  4965. +                bc->hdlc_tx.bitstream <<= 1;
  4966. +                bit = bc->hdlc_tx.current_byte & 1;
  4967. +                bc->hdlc_tx.bitstream |= bit;
  4968. +                bc->hdlc_tx.current_byte >>= 1;
  4969. +                return bit;
  4970. +            }
  4971. +            if (!bc->hdlc_tx.len) {
  4972. +                bc->hdlc_tx.tx_state = 0;
  4973. +                bc->hdlc_tx.current_byte = 0;
  4974. +                bc->hdlc_tx.numflags = 1;
  4975. +            } else {
  4976. +                bc->hdlc_tx.len--;
  4977. +                bc->hdlc_tx.current_byte = 0x100 | 
  4978. +                    (*bc->hdlc_tx.bp++);
  4979. +            }
  4980. +            break;
  4981. +        }
  4982. +    }
  4983. +}
  4984. +
  4985. +/* ---------------------------------------------------------------------- */
  4986. +
  4987. +static unsigned short random_seed;
  4988. +
  4989. +static inline unsigned short random_num(void)
  4990. +{
  4991. +    random_seed = 28629 * random_seed + 157;
  4992. +    return random_seed;
  4993. +}
  4994. +
  4995. +/* ---------------------------------------------------------------------- */
  4996. +
  4997. +static inline void tx_arbitrate(struct baycom_state *bc)
  4998. +{
  4999. +    unsigned char *bp;
  5000. +    unsigned int len;
  5001. +    
  5002. +    if (!bc || bc->hdlc_tx.ptt || bc->modem.dcd)
  5003. +        return;
  5004. +    get_packet(&bc->tx_buf,&bp,&len);
  5005. +    if (!bp || !len)
  5006. +        return;
  5007. +    
  5008. +    if (!bc->ch_params.fulldup) {
  5009. +        if ((random_num() % 256) > bc->ch_params.ppersist)
  5010. +            return;
  5011. +    }
  5012. +    bc->hdlc_tx.ptt = 1;
  5013. +    bc->hdlc_tx.tx_state = 0;
  5014. +    bc->hdlc_tx.numflags = tenms_to_flags(bc, bc->ch_params.tx_delay);
  5015. +    bc->stat.ptt_keyed++;
  5016. +}
  5017. +
  5018. +/* --------------------------------------------------------------------- */
  5019. +
  5020. +#ifdef BAYCOM_DEBUG
  5021. +static void inline baycom_int_freq(struct baycom_state *bc)
  5022. +{
  5023. +    unsigned long cur_jiffies = jiffies;
  5024. +    /* 
  5025. +     * measure the interrupt frequency
  5026. +     */
  5027. +    bc->debug_vals.cur_intcnt++;
  5028. +    if ((cur_jiffies - bc->debug_vals.last_jiffies) >= HZ) {
  5029. +        bc->debug_vals.last_jiffies = cur_jiffies;
  5030. +        bc->debug_vals.last_intcnt = bc->debug_vals.cur_intcnt;
  5031. +        bc->debug_vals.cur_intcnt = 0;
  5032. +        bc->debug_vals.last_pllcorr = bc->debug_vals.cur_pllcorr;
  5033. +        bc->debug_vals.cur_pllcorr = 0;
  5034. +    }
  5035. +}
  5036. +#endif /* BAYCOM_DEBUG */
  5037. +
  5038. +/* --------------------------------------------------------------------- */
  5039. +
  5040. +static inline void rx_chars_to_flip(struct baycom_state *bc) 
  5041. +{
  5042. +    int flip_free;
  5043. +    unsigned int cnt;
  5044. +    unsigned int new_rd;
  5045. +    unsigned long flags;
  5046. +
  5047. +    if ((!bc) || (!bc->tty) || (bc->tty->flip.count >= TTY_FLIPBUF_SIZE) ||
  5048. +        (bc->rx_buf.rd == bc->rx_buf.wr) || 
  5049. +        (!bc->tty->flip.char_buf_ptr) ||
  5050. +        (!bc->tty->flip.flag_buf_ptr))
  5051. +        return;
  5052. +    for(;;) {
  5053. +        flip_free = TTY_FLIPBUF_SIZE - bc->tty->flip.count;
  5054. +        if (bc->rx_buf.rd <= bc->rx_buf.wr)
  5055. +            cnt = bc->rx_buf.wr - bc->rx_buf.rd;
  5056. +        else
  5057. +            cnt = bc->rx_buf.buflen - bc->rx_buf.rd;
  5058. +        if ((flip_free <= 0) || (!cnt)) {
  5059. +            tty_schedule_flip(bc->tty);
  5060. +            return;
  5061. +        }
  5062. +        if (cnt > flip_free)
  5063. +            cnt = flip_free;
  5064. +        save_flags(flags); cli();
  5065. +        memcpy(bc->tty->flip.char_buf_ptr, bc->rx_buf.buffer+bc->rx_buf.rd, cnt);
  5066. +        memset(bc->tty->flip.flag_buf_ptr, TTY_NORMAL, cnt);
  5067. +        bc->tty->flip.count += cnt;
  5068. +        bc->tty->flip.char_buf_ptr += cnt;
  5069. +        bc->tty->flip.flag_buf_ptr += cnt;
  5070. +        restore_flags(flags);
  5071. +        new_rd = bc->rx_buf.rd+cnt;
  5072. +        if (new_rd >= bc->rx_buf.buflen)
  5073. +            new_rd -= bc->rx_buf.buflen;
  5074. +        bc->rx_buf.rd = new_rd;
  5075. +    }
  5076. +}
  5077. +
  5078. +/* --------------------------------------------------------------------- */
  5079. +/*
  5080. + * ===================== SER12 specific routines =========================
  5081. + */
  5082. +
  5083. +static void inline ser12_set_divisor(struct baycom_state *bc, 
  5084. +                     unsigned char divisor)
  5085. +{
  5086. +    outb(0x81, LCR(bc->iobase));    /* DLAB = 1 */
  5087. +    outb(divisor, DLL(bc->iobase));
  5088. +    outb(0, DLM(bc->iobase));
  5089. +    outb(0x01, LCR(bc->iobase));    /* word length = 6 */
  5090. +}
  5091. +
  5092. +/* --------------------------------------------------------------------- */
  5093. +
  5094. +/*
  5095. + * must call the TX arbitrator every 10ms
  5096. + */
  5097. +#define SER12_ARB_DIVIDER(bc) ((bc->options & BAYCOM_OPTIONS_SOFTDCD) ? \
  5098. +                   36 : 24)
  5099. +#define SER12_DCD_INTERVAL(bc) ((bc->options & BAYCOM_OPTIONS_SOFTDCD) ? \
  5100. +                240 : 12)
  5101. +
  5102. +static void baycom_ser12_interrupt(int irq, void *dev_id, struct pt_regs *regs)
  5103. +{
  5104. +    struct baycom_state *bc = (struct baycom_state *)dev_id;
  5105. +    unsigned char cur_s;
  5106. +    
  5107. +    if (!bc || bc->magic != BAYCOM_MAGIC)
  5108. +        return;
  5109. +    /*
  5110. +     * make sure the next interrupt is generated;
  5111. +     * 0 must be used to power the modem; the modem draws its
  5112. +     * power from the TxD line
  5113. +     */    
  5114. +    outb(0x00, THR(bc->iobase));
  5115. +    rx_chars_to_flip(bc);
  5116. +#ifdef BAYCOM_DEBUG
  5117. +    baycom_int_freq(bc);
  5118. +#endif /* BAYCOM_DEBUG */
  5119. +    /*
  5120. +     * check if transmitter active
  5121. +     */
  5122. +    if (bc->hdlc_tx.ptt || bc->calibrate > 0) {
  5123. +        ser12_set_divisor(bc, 12); /* one interrupt per channel bit */
  5124. +        /*
  5125. +         * first output the last bit (!) then call HDLC transmitter,
  5126. +         * since this may take quite long
  5127. +         */
  5128. +        outb(0x0e | (bc->modem.ser12.tx_bit ? 1 : 0), MCR(bc->iobase));
  5129. +        if (bc->calibrate > 0) {
  5130. +            bc->modem.ser12.tx_bit = !bc->modem.ser12.tx_bit;
  5131. +            bc->calibrate--;
  5132. +            return;
  5133. +        }
  5134. +#ifdef HDLC_LOOPBACK
  5135. +        hdlc_rx_bit(bc, bc->modem.ser12.tx_bit == 
  5136. +                bc->modem.ser12.last_rxbit);
  5137. +        bc->modem.ser12.last_rxbit = bc->modem.ser12.tx_bit;
  5138. +#endif /* HDLC_LOOPBACK */
  5139. +        if (!hdlc_tx_bit(bc))
  5140. +            bc->modem.ser12.tx_bit = !bc->modem.ser12.tx_bit;
  5141. +        return;
  5142. +    }
  5143. +    /*
  5144. +     * do demodulator
  5145. +     */
  5146. +    outb(0x0d, MCR(bc->iobase));            /* transmitter off */
  5147. +    cur_s = inb(MSR(bc->iobase)) & 0x10;    /* the CTS line */
  5148. +#ifdef BAYCOM_DEBUG
  5149. +    add_bitbuffer(&bc->bitbuf_channel, cur_s);
  5150. +#endif /* BAYCOM_DEBUG */
  5151. +    bc->modem.ser12.dcd_shreg <<= 1;
  5152. +    if(cur_s != bc->modem.ser12.last_sample) {
  5153. +        bc->modem.ser12.dcd_shreg |= 1;
  5154. +
  5155. +        if (bc->options & BAYCOM_OPTIONS_SOFTDCD) {
  5156. +            unsigned int dcdspos, dcdsneg;
  5157. +
  5158. +            dcdspos = dcdsneg = 0;
  5159. +            dcdspos += ((bc->modem.ser12.dcd_shreg >> 1) & 1);
  5160. +            if (!(bc->modem.ser12.dcd_shreg & 0x7ffffffe))
  5161. +                dcdspos += 2;
  5162. +            dcdsneg += ((bc->modem.ser12.dcd_shreg >> 2) & 1);
  5163. +            dcdsneg += ((bc->modem.ser12.dcd_shreg >> 3) & 1);
  5164. +            dcdsneg += ((bc->modem.ser12.dcd_shreg >> 4) & 1);
  5165. +
  5166. +            bc->modem.ser12.dcd_sum0 += 16*dcdspos - dcdsneg;
  5167. +        } else
  5168. +            bc->modem.ser12.dcd_sum0--;
  5169. +    }
  5170. +    bc->modem.ser12.last_sample = cur_s;
  5171. +    if(!bc->modem.ser12.dcd_time) {
  5172. +        bc->modem.dcd = (bc->modem.ser12.dcd_sum0 + 
  5173. +                 bc->modem.ser12.dcd_sum1 +
  5174. +                 bc->modem.ser12.dcd_sum2) < 0;
  5175. +        bc->modem.ser12.dcd_sum2 = bc->modem.ser12.dcd_sum1;
  5176. +        bc->modem.ser12.dcd_sum1 = bc->modem.ser12.dcd_sum0;
  5177. +        /* offset to ensure DCD off on silent input */
  5178. +        bc->modem.ser12.dcd_sum0 = 2;
  5179. +        bc->modem.ser12.dcd_time = SER12_DCD_INTERVAL(bc);
  5180. +    }
  5181. +    bc->modem.ser12.dcd_time--;
  5182. +    if (bc->options & BAYCOM_OPTIONS_SOFTDCD) {
  5183. +        /*
  5184. +         * PLL code for the improved software DCD algorithm
  5185. +         */
  5186. +        if (bc->modem.ser12.interm_sample) {
  5187. +            /*
  5188. +             * intermediate sample; set timing correction to normal
  5189. +             */
  5190. +            ser12_set_divisor(bc, 4);
  5191. +        } else {
  5192. +            /*
  5193. +             * do PLL correction and call HDLC receiver
  5194. +             */
  5195. +            switch (bc->modem.ser12.dcd_shreg & 7) {
  5196. +            case 1: /* transition too late */
  5197. +                ser12_set_divisor(bc, 5);
  5198. +#ifdef BAYCOM_DEBUG
  5199. +                bc->debug_vals.cur_pllcorr++;
  5200. +#endif /* BAYCOM_DEBUG */
  5201. +                break;
  5202. +            case 4:    /* transition too early */
  5203. +                ser12_set_divisor(bc, 3);
  5204. +#ifdef BAYCOM_DEBUG
  5205. +                bc->debug_vals.cur_pllcorr--;
  5206. +#endif /* BAYCOM_DEBUG */
  5207. +                break;
  5208. +            default:
  5209. +                ser12_set_divisor(bc, 4);
  5210. +                break;
  5211. +            }
  5212. +            hdlc_rx_bit(bc, bc->modem.ser12.last_sample == 
  5213. +                bc->modem.ser12.last_rxbit);
  5214. +            bc->modem.ser12.last_rxbit = 
  5215. +                bc->modem.ser12.last_sample;
  5216. +        }
  5217. +        if (++bc->modem.ser12.interm_sample >= 3)
  5218. +            bc->modem.ser12.interm_sample = 0;        
  5219. +    } else {
  5220. +        /*
  5221. +         * PLL algorithm for the hardware squelch DCD algorithm
  5222. +         */
  5223. +        if (bc->modem.ser12.interm_sample) {
  5224. +            /*
  5225. +             * intermediate sample; set timing correction to normal
  5226. +             */
  5227. +            ser12_set_divisor(bc, 6);
  5228. +        } else {
  5229. +            /*
  5230. +             * do PLL correction and call HDLC receiver
  5231. +             */
  5232. +            switch (bc->modem.ser12.dcd_shreg & 3) {
  5233. +            case 1: /* transition too late */
  5234. +                ser12_set_divisor(bc, 7);
  5235. +#ifdef BAYCOM_DEBUG
  5236. +                bc->debug_vals.cur_pllcorr++;
  5237. +#endif /* BAYCOM_DEBUG */
  5238. +                break;
  5239. +            case 2:    /* transition too early */
  5240. +                ser12_set_divisor(bc, 5);
  5241. +#ifdef BAYCOM_DEBUG
  5242. +                bc->debug_vals.cur_pllcorr--;
  5243. +#endif /* BAYCOM_DEBUG */
  5244. +                break;
  5245. +            default:
  5246. +                ser12_set_divisor(bc, 6);
  5247. +                break;
  5248. +            }
  5249. +            hdlc_rx_bit(bc, bc->modem.ser12.last_sample == 
  5250. +                bc->modem.ser12.last_rxbit);
  5251. +            bc->modem.ser12.last_rxbit = 
  5252. +                bc->modem.ser12.last_sample;
  5253. +        }
  5254. +        bc->modem.ser12.interm_sample = !bc->modem.ser12.interm_sample;
  5255. +    }
  5256. +    if (--bc->modem.arb_divider <= 0) {
  5257. +        tx_arbitrate(bc);
  5258. +        bc->modem.arb_divider = bc->ch_params.slottime * 
  5259. +            SER12_ARB_DIVIDER(bc);
  5260. +    }
  5261. +}
  5262. +
  5263. +/* --------------------------------------------------------------------- */
  5264. +
  5265. +enum uart { c_uart_unknown, c_uart_8250,
  5266. +    c_uart_16450, c_uart_16550, c_uart_16550A};
  5267. +static const char *uart_str[] =
  5268. +    { "unknown", "8250", "16450", "16550", "16550A" };
  5269. +
  5270. +static enum uart ser12_check_uart(unsigned int iobase)
  5271. +{
  5272. +    unsigned char b1,b2,b3;
  5273. +    enum uart u;
  5274. +    enum uart uart_tab[] =
  5275. +        { c_uart_16450, c_uart_unknown, c_uart_16550, c_uart_16550A };
  5276. +
  5277. +    b1 = inb(MCR(iobase));
  5278. +    outb(b1 | 0x10, MCR(iobase));    /* loopback mode */
  5279. +    b2 = inb(MSR(iobase));
  5280. +    outb(0x1a, MCR(iobase));
  5281. +    b3 = inb(MSR(iobase)) & 0xf0;
  5282. +    outb(b1, MCR(iobase));            /* restore old values */
  5283. +    outb(b2, MSR(iobase));
  5284. +    if (b3 != 0x90) 
  5285. +        return c_uart_unknown;
  5286. +    inb(RBR(iobase));
  5287. +    inb(RBR(iobase));
  5288. +    outb(0x01, FCR(iobase));        /* enable FIFOs */
  5289. +    u = uart_tab[(inb(IIR(iobase)) >> 6) & 3];
  5290. +    if (u == c_uart_16450) {
  5291. +        outb(0x5a, SCR(iobase));
  5292. +        b1 = inb(SCR(iobase));
  5293. +        outb(0xa5, SCR(iobase));
  5294. +        b2 = inb(SCR(iobase));
  5295. +        if ((b1 != 0x5a) || (b2 != 0xa5)) 
  5296. +            u = c_uart_8250;
  5297. +    }
  5298. +    return u;
  5299. +}
  5300. +
  5301. +/* --------------------------------------------------------------------- */
  5302. +
  5303. +static int ser12_allocate_resources(unsigned int iobase, unsigned int irq,
  5304. +                    unsigned int options)
  5305. +{
  5306. +    enum uart u;
  5307. +
  5308. +    if (!iobase || iobase > 0xfff || irq < 2 || irq > 15)
  5309. +        return -ENXIO;
  5310. +    if (check_region(iobase, SER12_EXTENT))
  5311. +        return -EACCES;
  5312. +    if ((u = ser12_check_uart(iobase)) == c_uart_unknown)
  5313. +        return -EIO;
  5314. +    request_region(iobase, SER12_EXTENT, "baycom_ser12");
  5315. +    outb(0, FCR(iobase));        /* disable FIFOs */
  5316. +    outb(0x0d, MCR(iobase));
  5317. +    printk(KERN_INFO "baycom: ser12 at iobase 0x%x irq %u options 0x%x "
  5318. +           "uart %s\n", iobase, irq, options, uart_str[u]);
  5319. +    return 0;
  5320. +}
  5321. +    
  5322. +/* --------------------------------------------------------------------- */
  5323. +
  5324. +static void ser12_deallocate_resources(struct baycom_state *bc) 
  5325. +{
  5326. +    if (!bc || bc->modem_type != BAYCOM_MODEM_SER12)
  5327. +        return;
  5328. +    /*
  5329. +     * disable interrupts
  5330. +     */
  5331. +    outb(0, IER(bc->iobase));
  5332. +    outb(1, MCR(bc->iobase));
  5333. +    /* 
  5334. +     * this should prevent kernel: Trying to free IRQx
  5335. +     * messages
  5336. +     */
  5337. +    if (bc->opened > 0)
  5338. +        free_irq(bc->irq, bc);
  5339. +    release_region(bc->iobase, SER12_EXTENT);
  5340. +    bc->modem_type = BAYCOM_MODEM_INVALID;
  5341. +    printk(KERN_INFO "baycom: release ser12 at iobase 0x%x irq %u\n",
  5342. +           bc->iobase, bc->irq);
  5343. +    bc->iobase = bc->irq = bc->options = 0;
  5344. +}
  5345. +
  5346. +/* --------------------------------------------------------------------- */
  5347. +
  5348. +static int ser12_on_open(struct baycom_state *bc) 
  5349. +{
  5350. +    if (!bc || bc->modem_type != BAYCOM_MODEM_SER12)
  5351. +        return -ENXIO;
  5352. +    /*
  5353. +     * set the SIO to 6 Bits/character and 19200 or 28800 baud, so that
  5354. +     * we get exactly (hopefully) 2 or 3 interrupts per radio symbol,
  5355. +     * depending on the usage of the software DCD routine
  5356. +     */
  5357. +    ser12_set_divisor(bc, (bc->options & BAYCOM_OPTIONS_SOFTDCD) ? 4 : 6);
  5358. +    outb(0x0d, MCR(bc->iobase));
  5359. +    outb(0, IER(bc->iobase));
  5360. +    if (request_irq(bc->irq, baycom_ser12_interrupt, 0, 
  5361. +            "baycom_ser12", bc))
  5362. +        return -EBUSY;
  5363. +    /*
  5364. +     * enable transmitter empty interrupt
  5365. +     */
  5366. +    outb(2, IER(bc->iobase));  
  5367. +    /* 
  5368. +     * the value here serves to power the modem
  5369. +     */     
  5370. +    outb(0x00, THR(bc->iobase));
  5371. +    return 0;
  5372. +}
  5373. +
  5374. +/* --------------------------------------------------------------------- */
  5375. +
  5376. +static void ser12_on_close(struct baycom_state *bc) 
  5377. +{
  5378. +    if (!bc || bc->modem_type != BAYCOM_MODEM_SER12)
  5379. +        return;
  5380. +    /*
  5381. +     * disable interrupts
  5382. +     */
  5383. +    outb(0, IER(bc->iobase));
  5384. +    outb(1, MCR(bc->iobase));
  5385. +    free_irq(bc->irq, bc);    
  5386. +}
  5387. +
  5388. +/* --------------------------------------------------------------------- */
  5389. +/*
  5390. + * ===================== PAR96 specific routines =========================
  5391. + */
  5392. +
  5393. +#define PAR96_DESCRAM_TAP1 0x20000
  5394. +#define PAR96_DESCRAM_TAP2 0x01000
  5395. +#define PAR96_DESCRAM_TAP3 0x00001
  5396. +
  5397. +#define PAR96_DESCRAM_TAPSH1 17
  5398. +#define PAR96_DESCRAM_TAPSH2 12
  5399. +#define PAR96_DESCRAM_TAPSH3 0
  5400. +
  5401. +#define PAR96_SCRAM_TAP1 0x20000 /* X^17 */
  5402. +#define PAR96_SCRAM_TAPN 0x00021 /* X^0+X^5 */
  5403. +
  5404. +/* --------------------------------------------------------------------- */
  5405. +
  5406. +static void baycom_par96_interrupt(int irq, void *dev_id, struct pt_regs *regs)
  5407. +{
  5408. +    register struct baycom_state *bc = (struct baycom_state *)dev_id;
  5409. +    int i;
  5410. +    unsigned int data, mask, mask2;
  5411. +    
  5412. +    if (!bc || bc->magic != BAYCOM_MAGIC)
  5413. +        return;
  5414. +
  5415. +    rx_chars_to_flip(bc);
  5416. +#ifdef BAYCOM_DEBUG
  5417. +    baycom_int_freq(bc);
  5418. +#endif /* BAYCOM_DEBUG */
  5419. +    /*
  5420. +     * check if transmitter active
  5421. +     */
  5422. +    if (bc->hdlc_tx.ptt || bc->calibrate > 0) {
  5423. +        /*
  5424. +         * first output the last 16 bits (!) then call HDLC
  5425. +         * transmitter, since this may take quite long
  5426. +         * do the differential encoder and the scrambler on the fly
  5427. +         */
  5428. +        data = bc->modem.par96.tx_bits;
  5429. +        for(i = 0; i < PAR96_BURSTBITS; i++, data <<= 1) {
  5430. +            unsigned char val = PAR97_POWER;
  5431. +            bc->modem.par96.scram = ((bc->modem.par96.scram << 1) |
  5432. +                         (bc->modem.par96.scram & 1));
  5433. +            if (!(data & 0x8000))
  5434. +                bc->modem.par96.scram ^= 1;
  5435. +            if (bc->modem.par96.scram & (PAR96_SCRAM_TAP1 << 1))
  5436. +                bc->modem.par96.scram ^= 
  5437. +                    (PAR96_SCRAM_TAPN << 1);
  5438. +            if (bc->modem.par96.scram & (PAR96_SCRAM_TAP1 << 2))
  5439. +                val |= PAR96_TXBIT;
  5440. +            outb(val, LPT_DATA(bc->iobase));
  5441. +            outb(val | PAR96_BURST, LPT_DATA(bc->iobase));
  5442. +        }
  5443. +        if (bc->calibrate > 0) {
  5444. +            bc->modem.par96.tx_bits = 0;
  5445. +            bc->calibrate--;
  5446. +            return;
  5447. +        }
  5448. +#ifdef HDLC_LOOPBACK
  5449. +        for(mask = 0x8000, i = 0; i < PAR96_BURSTBITS; i++, mask >>= 1)
  5450. +            hdlc_rx_bit(bc, bc->modem.par96.tx_bits & mask);
  5451. +#endif /* HDLC_LOOPBACK */
  5452. +        bc->modem.par96.tx_bits = 0;
  5453. +        for(i = 0; i < PAR96_BURSTBITS; i++) {
  5454. +            bc->modem.par96.tx_bits <<= 1;
  5455. +            if (hdlc_tx_bit(bc))
  5456. +                bc->modem.par96.tx_bits |= 1;
  5457. +        }
  5458. +        return;
  5459. +    }
  5460. +    /*
  5461. +     * do receiver; differential decode and descramble on the fly
  5462. +     */
  5463. +    for(data = i = 0; i < PAR96_BURSTBITS; i++) {
  5464. +        unsigned int descx;
  5465. +        bc->modem.par96.descram = (bc->modem.par96.descram << 1);
  5466. +        if (inb(LPT_STATUS(bc->iobase)) & PAR96_RXBIT)
  5467. +            bc->modem.par96.descram |= 1;
  5468. +        descx = bc->modem.par96.descram ^ 
  5469. +            (bc->modem.par96.descram >> 1);
  5470. +        /* now the diff decoded data is inverted in descram */
  5471. +        outb(PAR97_POWER | PAR96_PTT, LPT_DATA(bc->iobase));
  5472. +        descx ^= ((descx >> PAR96_DESCRAM_TAPSH1) ^
  5473. +              (descx >> PAR96_DESCRAM_TAPSH2));
  5474. +        data <<= 1;
  5475. +        data |= !(descx & 1);
  5476. +        outb(PAR97_POWER | PAR96_PTT | PAR96_BURST, 
  5477. +             LPT_DATA(bc->iobase));
  5478. +    }
  5479. +    for(mask = 0x8000, i = 0; i < PAR96_BURSTBITS; i++, mask >>= 1)
  5480. +        hdlc_rx_bit(bc, data & mask);
  5481. +    /*
  5482. +     * do DCD algorithm
  5483. +     */
  5484. +    if (bc->options & BAYCOM_OPTIONS_SOFTDCD) {
  5485. +        bc->modem.par96.dcd_shreg = (bc->modem.par96.dcd_shreg << 16)
  5486. +            | data;
  5487. +        /* search for flags and set the dcd counter appropriately */
  5488. +        for(mask = 0x7f8000, mask2 = 0x3f0000, i = 0; 
  5489. +            i < PAR96_BURSTBITS; i++, mask >>= 1, mask2 >>= 1)
  5490. +            if ((bc->modem.par96.dcd_shreg & mask) == mask2)
  5491. +                bc->modem.par96.dcd_count = BAYCOM_MAXFLEN+4;
  5492. +        /* check for abort/noise sequences */
  5493. +        for(mask = 0x3f8000, mask2 = 0x3f8000, i = 0; 
  5494. +            i < PAR96_BURSTBITS; i++, mask >>= 1, mask2 >>= 1)
  5495. +            if ((bc->modem.par96.dcd_shreg & mask) == mask2)
  5496. +                if (bc->modem.par96.dcd_count >= 0)
  5497. +                    bc->modem.par96.dcd_count -= 
  5498. +                        BAYCOM_MAXFLEN-10;
  5499. +        /* decrement and set the dcd variable */
  5500. +        if (bc->modem.par96.dcd_count >= 0)
  5501. +            bc->modem.par96.dcd_count -= 2;
  5502. +        bc->modem.dcd = bc->modem.par96.dcd_count > 0;
  5503. +    } else {
  5504. +        bc->modem.dcd = !!(inb(LPT_STATUS(bc->iobase)) & PAR96_DCD);
  5505. +    }
  5506. +    if (--bc->modem.arb_divider <= 0) {
  5507. +        tx_arbitrate(bc);
  5508. +        bc->modem.arb_divider = bc->ch_params.slottime * 6;
  5509. +    }
  5510. +}
  5511. +
  5512. +/* --------------------------------------------------------------------- */
  5513. +
  5514. +static int par96_check_lpt(unsigned int iobase)
  5515. +{
  5516. +    unsigned char b1,b2;
  5517. +    int i;
  5518. +
  5519. +    b1 = inb(LPT_DATA(iobase));
  5520. +    b2 = inb(LPT_CONTROL(iobase));
  5521. +    outb(0xaa, LPT_DATA(iobase));
  5522. +    i = inb(LPT_DATA(iobase)) == 0xaa;
  5523. +    outb(0x55, LPT_DATA(iobase));
  5524. +    i &= inb(LPT_DATA(iobase)) == 0x55;
  5525. +    outb(0x0a, LPT_CONTROL(iobase));
  5526. +    i &= (inb(LPT_CONTROL(iobase)) & 0xf) == 0x0a;
  5527. +    outb(0x05, LPT_CONTROL(iobase));
  5528. +    i &= (inb(LPT_CONTROL(iobase)) & 0xf) == 0x05;
  5529. +    outb(b1, LPT_DATA(iobase));
  5530. +    outb(b2, LPT_CONTROL(iobase));
  5531. +    return !i;
  5532. +}
  5533. +
  5534. +/* --------------------------------------------------------------------- */
  5535. +
  5536. +static int par96_allocate_resources(unsigned int iobase, unsigned int irq,
  5537. +                    unsigned int options)
  5538. +{
  5539. +    if (!iobase || iobase > 0xfff || irq < 2 || irq > 15)
  5540. +        return -ENXIO;
  5541. +    if (check_region(iobase, PAR96_EXTENT))
  5542. +        return -EACCES;
  5543. +    if (par96_check_lpt(iobase))
  5544. +        return -EIO;
  5545. +    request_region(iobase, PAR96_EXTENT, "baycom_par96");
  5546. +    outb(0, LPT_CONTROL(iobase));                 /* disable interrupt */
  5547. +    outb(PAR96_PTT | PAR97_POWER, LPT_DATA(iobase)); /* switch off PTT */
  5548. +    printk(KERN_INFO "baycom: par96 at iobase 0x%x irq %u options 0x%x\n", 
  5549. +           iobase, irq, options);
  5550. +    return 0;
  5551. +}
  5552. +    
  5553. +/* --------------------------------------------------------------------- */
  5554. +
  5555. +static void par96_deallocate_resources(struct baycom_state *bc) 
  5556. +{
  5557. +    if (!bc || bc->modem_type != BAYCOM_MODEM_PAR96)
  5558. +        return;
  5559. +    outb(0, LPT_CONTROL(bc->iobase));      /* disable interrupt */
  5560. +    outb(PAR96_PTT, LPT_DATA(bc->iobase)); /* switch off PTT */
  5561. +    /* 
  5562. +     * this should prevent kernel: Trying to free IRQx
  5563. +     * messages
  5564. +     */
  5565. +    if (bc->opened > 0)
  5566. +        free_irq(bc->irq, bc);
  5567. +    release_region(bc->iobase, PAR96_EXTENT);
  5568. +    bc->modem_type = BAYCOM_MODEM_INVALID;
  5569. +    printk(KERN_INFO "baycom: release par96 at iobase 0x%x irq %u\n",
  5570. +           bc->iobase, bc->irq);
  5571. +    bc->iobase = bc->irq = bc->options = 0;
  5572. +}
  5573. +
  5574. +/* --------------------------------------------------------------------- */
  5575. +
  5576. +static int par96_on_open(struct baycom_state *bc) 
  5577. +{
  5578. +    if (!bc || bc->modem_type != BAYCOM_MODEM_PAR96)
  5579. +        return -ENXIO;
  5580. +    outb(0, LPT_CONTROL(bc->iobase));      /* disable interrupt */
  5581. +     /* switch off PTT */
  5582. +    outb(PAR96_PTT | PAR97_POWER, LPT_DATA(bc->iobase));
  5583. +    if (request_irq(bc->irq, baycom_par96_interrupt, 0, 
  5584. +            "baycom_par96", bc))
  5585. +        return -EBUSY;
  5586. +    outb(LPT_IRQ_ENABLE, LPT_CONTROL(bc->iobase));  /* enable interrupt */
  5587. +    return 0;
  5588. +}
  5589. +
  5590. +/* --------------------------------------------------------------------- */
  5591. +
  5592. +static void par96_on_close(struct baycom_state *bc) 
  5593. +{
  5594. +    if (!bc || bc->modem_type != BAYCOM_MODEM_PAR96)
  5595. +        return;
  5596. +    outb(0, LPT_CONTROL(bc->iobase));  /* disable interrupt */
  5597. +    /* switch off PTT */
  5598. +    outb(PAR96_PTT | PAR97_POWER, LPT_DATA(bc->iobase));
  5599. +    free_irq(bc->irq, bc);    
  5600. +}
  5601. +
  5602. +/* --------------------------------------------------------------------- */
  5603. +/*
  5604. + * ===================== TTY interface routines ==========================
  5605. + */
  5606. +
  5607. +static inline int baycom_paranoia_check(struct baycom_state *bc, 
  5608. +                    const char *routine)
  5609. +{
  5610. +    if (!bc || bc->magic != BAYCOM_MAGIC) {
  5611. +        printk(KERN_ERR "baycom: bad magic number for baycom struct "
  5612. +               "in routine %s\n", routine);
  5613. +        return 1;
  5614. +    }
  5615. +    return 0;
  5616. +}
  5617. +
  5618. +/* --------------------------------------------------------------------- */
  5619. +/*
  5620. + * Here the tty driver code starts
  5621. + */
  5622. +
  5623. +static void baycom_put_fend(struct baycom_state *bc)
  5624. +{
  5625. +    if (bc->kiss_decode.wr <= 0 ||
  5626. +        (bc->kiss_decode.pkt_buf[0] & 0xf0) != 0)
  5627. +        return;
  5628. +
  5629. +    switch (bc->kiss_decode.pkt_buf[0] & 0xf) {
  5630. +    case KISS_CMD_DATA:
  5631. +        if (bc->kiss_decode.wr <= 8) 
  5632. +            break;
  5633. +        if (!store_packet(&bc->tx_buf, bc->kiss_decode.pkt_buf+1, 0, 
  5634. +                  bc->kiss_decode.wr-1))
  5635. +            bc->stat.tx_bufferoverrun++;
  5636. +        break;
  5637. +
  5638. +    case KISS_CMD_TXDELAY:
  5639. +        if (bc->kiss_decode.wr < 2) 
  5640. +            break;
  5641. +        bc->ch_params.tx_delay = bc->kiss_decode.pkt_buf[1];
  5642. +#ifdef KISS_VERBOSE
  5643. +        printk(KERN_INFO "baycom: TX delay = %ums\n", 
  5644. +               bc->ch_params.tx_delay * 10);
  5645. +#endif /* KISS_VERBOSE */
  5646. +        break;
  5647. +
  5648. +    case KISS_CMD_PPERSIST:
  5649. +        if (bc->kiss_decode.wr < 2) 
  5650. +            break;
  5651. +        bc->ch_params.ppersist = bc->kiss_decode.pkt_buf[1];
  5652. +#ifdef KISS_VERBOSE
  5653. +        printk("KERN_INFO baycom: p-persistence = %u\n", 
  5654. +               bc->ch_params.ppersist);
  5655. +#endif /* KISS_VERBOSE */
  5656. +        break;
  5657. +
  5658. +    case KISS_CMD_SLOTTIME:
  5659. +        if (bc->kiss_decode.wr < 2) 
  5660. +            break;
  5661. +        bc->ch_params.slottime = bc->kiss_decode.pkt_buf[1];
  5662. +#ifdef KISS_VERBOSE
  5663. +        printk("baycom: slottime = %ums\n", 
  5664. +               bc->ch_params.slottime * 10);
  5665. +#endif /* KISS_VERBOSE */
  5666. +        break;
  5667. +
  5668. +    case KISS_CMD_TXTAIL:
  5669. +        if (bc->kiss_decode.wr < 2) 
  5670. +            break;
  5671. +        bc->ch_params.tx_tail = bc->kiss_decode.pkt_buf[1];
  5672. +#ifdef KISS_VERBOSE
  5673. +        printk(KERN_INFO "baycom: TX tail = %ums\n",
  5674. +               bc->ch_params.tx_tail * 10);
  5675. +#endif /* KISS_VERBOSE */
  5676. +        break;
  5677. +
  5678. +    case KISS_CMD_FULLDUP:
  5679. +        if (bc->kiss_decode.wr < 2) 
  5680. +            break;
  5681. +        bc->ch_params.fulldup = bc->kiss_decode.pkt_buf[1];
  5682. +#ifdef KISS_VERBOSE
  5683. +        printk(KERN_INFO "baycom: %s duplex\n", 
  5684. +               bc->ch_params.fulldup ? "full" : "half");
  5685. +#endif /* KISS_VERBOSE */
  5686. +        break;
  5687. +
  5688. +    default:
  5689. +#ifdef KISS_VERBOSE
  5690. +        printk(KERN_INFO "baycom: unhandled KISS packet code %u\n",
  5691. +               bc->kiss_decode.pkt_buf[0] & 0xf);
  5692. +#endif /* KISS_VERBOSE */
  5693. +        break;
  5694. +    }
  5695. +}
  5696. +
  5697. +/* --------------------------------------------------------------------- */
  5698. +
  5699. +static void baycom_put_char(struct tty_struct *tty, unsigned char ch)
  5700. +{
  5701. +    struct baycom_state *bc;
  5702. +        
  5703. +    if (!tty)
  5704. +        return;
  5705. +    if (baycom_paranoia_check(bc = tty->driver_data, "put_char"))
  5706. +        return;
  5707. +        
  5708. +    if (ch == KISS_FEND) {
  5709. +        baycom_put_fend(bc);
  5710. +        bc->kiss_decode.wr = 0;
  5711. +        bc->kiss_decode.escaped = 0;
  5712. +        bc->kiss_decode.dec_state = 1;
  5713. +        return;
  5714. +    }
  5715. +    if (!bc->kiss_decode.dec_state)
  5716. +        return;
  5717. +    if (bc->kiss_decode.wr >= sizeof(bc->kiss_decode.pkt_buf)) {
  5718. +        bc->kiss_decode.wr = 0;
  5719. +        bc->kiss_decode.dec_state = 0;
  5720. +        return;
  5721. +    }
  5722. +    if (bc->kiss_decode.escaped) {
  5723. +        if (ch == KISS_TFEND)
  5724. +            bc->kiss_decode.pkt_buf[bc->kiss_decode.wr++] = 
  5725. +                KISS_FEND;
  5726. +        else if (ch == KISS_TFESC)
  5727. +            bc->kiss_decode.pkt_buf[bc->kiss_decode.wr++] = 
  5728. +                KISS_FESC;
  5729. +        else {
  5730. +            bc->kiss_decode.wr = 0;
  5731. +            bc->kiss_decode.dec_state = 0;
  5732. +        }
  5733. +        bc->kiss_decode.escaped = 0;
  5734. +        return;
  5735. +    }
  5736. +    bc->kiss_decode.pkt_buf[bc->kiss_decode.wr++] = ch;
  5737. +}
  5738. +    
  5739. +/* --------------------------------------------------------------------- */
  5740. +
  5741. +static int baycom_write(struct tty_struct * tty, int from_user,
  5742. +    const unsigned char *buf, int count)
  5743. +{
  5744. +    int c;
  5745. +    const unsigned char *bp;
  5746. +    struct baycom_state *bc;
  5747. +        
  5748. +    if (!tty || !buf || count <= 0)
  5749. +        return count;
  5750. +    
  5751. +    if (baycom_paranoia_check(bc = tty->driver_data, "write"))
  5752. +        return count; 
  5753. +        
  5754. +    if (from_user) {
  5755. +        for(c = count, bp = buf; c > 0; c--,bp++)
  5756. +            baycom_put_char(tty, get_user(bp));
  5757. +    } else {
  5758. +        for(c = count, bp = buf; c > 0; c--,bp++)
  5759. +            baycom_put_char(tty, *bp);
  5760. +    }
  5761. +    return count;
  5762. +}
  5763. +
  5764. +/* --------------------------------------------------------------------- */
  5765. +
  5766. +static int baycom_write_room(struct tty_struct *tty)
  5767. +{
  5768. +    int free;
  5769. +    struct baycom_state *bc;
  5770. +        
  5771. +    if (!tty)
  5772. +        return 0;
  5773. +    if (baycom_paranoia_check(bc = tty->driver_data, "write_room"))
  5774. +        return 0;
  5775. +        
  5776. +    free = bc->tx_buf.rd - bc->tx_buf.wr;
  5777. +    if (free <= 0) {
  5778. +        free = bc->tx_buf.buflen - bc->tx_buf.wr;
  5779. +        if (free < bc->tx_buf.rd)
  5780. +            free = bc->tx_buf.rd;    /* we may fold */
  5781. +    }
  5782. +
  5783. +    return free / 2; /* a rather pessimistic estimate */
  5784. +}
  5785. +
  5786. +/* --------------------------------------------------------------------- */
  5787. +
  5788. +static int baycom_chars_in_buffer(struct tty_struct *tty)
  5789. +{
  5790. +    int cnt;
  5791. +    struct baycom_state *bc;
  5792. +        
  5793. +    if (!tty)
  5794. +        return 0;
  5795. +    if (baycom_paranoia_check(bc = tty->driver_data, "chars_in_buffer"))
  5796. +        return 0;
  5797. +        
  5798. +    cnt = bc->rx_buf.wr - bc->rx_buf.rd;
  5799. +    if (cnt < 0)
  5800. +        cnt += bc->rx_buf.buflen;
  5801. +        
  5802. +    return cnt;
  5803. +}
  5804. +
  5805. +/* --------------------------------------------------------------------- */
  5806. +
  5807. +static void baycom_flush_buffer(struct tty_struct *tty)
  5808. +{
  5809. +    struct baycom_state *bc;
  5810. +        
  5811. +    if (!tty)
  5812. +        return;
  5813. +    if (baycom_paranoia_check(bc = tty->driver_data, "flush_buffer"))
  5814. +        return;
  5815. +
  5816. +    wake_up_interruptible(&tty->write_wait);
  5817. +    if ((tty->flags & (1 << TTY_DO_WRITE_WAKEUP)) &&
  5818. +        tty->ldisc.write_wakeup)
  5819. +            (tty->ldisc.write_wakeup)(tty);
  5820. +}
  5821. +
  5822. +/* --------------------------------------------------------------------- */
  5823. +
  5824. +static inline void baycom_dealloc_hw(struct baycom_state *bc) 
  5825. +{
  5826. +    if (!bc || bc->magic != BAYCOM_MAGIC || 
  5827. +        bc->modem_type == BAYCOM_MODEM_INVALID)
  5828. +        return;
  5829. +    switch(bc->modem_type) {
  5830. +    case BAYCOM_MODEM_SER12:
  5831. +        ser12_deallocate_resources(bc);
  5832. +        break;
  5833. +    case BAYCOM_MODEM_PAR96:
  5834. +        par96_deallocate_resources(bc);
  5835. +        break;
  5836. +    }
  5837. +}
  5838. +
  5839. +/* --------------------------------------------------------------------- */
  5840. +
  5841. +static int baycom_set_hardware(struct baycom_state *bc,
  5842. +                   unsigned int modem_type, unsigned int iobase, 
  5843. +                   unsigned int irq, unsigned int options)
  5844. +{
  5845. +    int i;
  5846. +
  5847. +    if (!bc)
  5848. +        return -EINVAL;
  5849. +
  5850. +    if (modem_type == BAYCOM_MODEM_SER12) {
  5851. +        i = ser12_allocate_resources(iobase, irq, options);
  5852. +        if (i < 0)
  5853. +            return i;
  5854. +    } else if (modem_type == BAYCOM_MODEM_PAR96) {
  5855. +        i = par96_allocate_resources(iobase, irq, options);
  5856. +        if (i < 0)
  5857. +            return i;
  5858. +    } else if (modem_type == BAYCOM_MODEM_INVALID) {
  5859. +        iobase = irq = options = 0;
  5860. +    } else {
  5861. +        return -ENXIO;
  5862. +    }
  5863. +    baycom_dealloc_hw(bc);
  5864. +    bc->modem_type = modem_type;
  5865. +    bc->iobase = iobase;
  5866. +    bc->irq = irq;
  5867. +    bc->options = options;
  5868. +    i = 0;
  5869. +    if (bc->opened > 0) {
  5870. +        switch(bc->modem_type) {
  5871. +        case BAYCOM_MODEM_SER12:
  5872. +            i = ser12_on_open(bc);
  5873. +            break;
  5874. +        case BAYCOM_MODEM_PAR96:
  5875. +            i = par96_on_open(bc);
  5876. +            break;
  5877. +        }
  5878. +    }
  5879. +    return i;
  5880. +}
  5881. +
  5882. +/* --------------------------------------------------------------------- */
  5883. +
  5884. +static int baycom_ioctl(struct tty_struct *tty, struct file * file,
  5885. +    unsigned int cmd, unsigned long arg)
  5886. +{
  5887. +    int i;
  5888. +    struct baycom_state *bc;
  5889. +    struct baycom_params par;
  5890. +        
  5891. +    if (!tty)
  5892. +        return -EINVAL;
  5893. +    if (baycom_paranoia_check(bc = tty->driver_data, "ioctl"))
  5894. +        return -EINVAL;
  5895. +        
  5896. +    switch (cmd) {
  5897. +    default:
  5898. +        return -ENOIOCTLCMD;
  5899. +
  5900. +    case TIOCMGET:
  5901. +        i = verify_area(VERIFY_WRITE, (void *) arg, sizeof(int));
  5902. +        if (i)
  5903. +            return i;
  5904. +        i = (bc->modem.dcd ? TIOCM_CAR : 0) |
  5905. +            (bc->hdlc_tx.ptt ? TIOCM_RTS : 0);
  5906. +        put_user(i, (int *) arg);
  5907. +        return 0;
  5908. +        
  5909. +    case BAYCOMCTL_GETDCD:
  5910. +        i = verify_area(VERIFY_WRITE, (void *) arg,
  5911. +                sizeof(unsigned char));
  5912. +        if (!i)
  5913. +            put_user(bc->modem.dcd, (unsigned char *) arg);
  5914. +        return i;
  5915. +        
  5916. +    case BAYCOMCTL_GETPTT:
  5917. +        i = verify_area(VERIFY_WRITE, (void *) arg, 
  5918. +                sizeof(unsigned char));
  5919. +        if (!i)
  5920. +            put_user(bc->hdlc_tx.ptt, (unsigned char *) arg);
  5921. +        return i;
  5922. +        
  5923. +    case BAYCOMCTL_PARAM_TXDELAY:
  5924. +        if (arg > 255)
  5925. +            return -EINVAL;
  5926. +        bc->ch_params.tx_delay = arg;
  5927. +        return 0;
  5928. +        
  5929. +    case BAYCOMCTL_PARAM_PPERSIST:
  5930. +        if (arg > 255)
  5931. +            return -EINVAL;
  5932. +        bc->ch_params.ppersist = arg;
  5933. +        return 0;
  5934. +        
  5935. +    case BAYCOMCTL_PARAM_SLOTTIME:
  5936. +        if (arg > 255)
  5937. +            return -EINVAL;
  5938. +        bc->ch_params.slottime = arg;
  5939. +        return 0;
  5940. +        
  5941. +    case BAYCOMCTL_PARAM_TXTAIL:
  5942. +        if (arg > 255)
  5943. +            return -EINVAL;
  5944. +        bc->ch_params.tx_tail = arg;
  5945. +        return 0;
  5946. +        
  5947. +    case BAYCOMCTL_PARAM_FULLDUP:
  5948. +        bc->ch_params.fulldup = arg ? 1 : 0;
  5949. +        return 0;
  5950. +        
  5951. +    case BAYCOMCTL_CALIBRATE:
  5952. +        bc->calibrate = arg * ((bc->modem_type == BAYCOM_MODEM_PAR96) ?
  5953. +                       600 : 1200);
  5954. +        return 0;
  5955. +
  5956. +    case BAYCOMCTL_GETPARAMS:
  5957. +        i = verify_area(VERIFY_WRITE, (void *) arg, 
  5958. +                sizeof(par));
  5959. +        if (i)
  5960. +            return i;
  5961. +        par.modem_type = bc->modem_type;
  5962. +        par.iobase = bc->iobase;
  5963. +        par.irq = bc->irq;
  5964. +        par.options = bc->options;
  5965. +        par.tx_delay = bc->ch_params.tx_delay;
  5966. +        par.tx_tail = bc->ch_params.tx_tail;
  5967. +        par.slottime = bc->ch_params.slottime;
  5968. +        par.ppersist = bc->ch_params.ppersist;
  5969. +        par.fulldup = bc->ch_params.fulldup;
  5970. +        memcpy_tofs((void *)arg, &par, sizeof(par));
  5971. +        return 0;
  5972. +
  5973. +    case BAYCOMCTL_SETPARAMS:
  5974. +        if (!suser())
  5975. +            return -EPERM;
  5976. +        i = verify_area(VERIFY_READ, (void *) arg, 
  5977. +                sizeof(par));
  5978. +        if (i)
  5979. +            return i;
  5980. +        memcpy_fromfs(&par, (void *)arg, sizeof(par));
  5981. +        printk(KERN_INFO "baycom: changing hardware type: modem %u "
  5982. +               "iobase 0x%x irq %u options 0x%x\n", par.modem_type,
  5983. +               par.iobase, par.irq, par.options);
  5984. +        i = baycom_set_hardware(bc, par.modem_type, par.iobase,
  5985. +                    par.irq, par.options); 
  5986. +        if (i)
  5987. +            return i;
  5988. +        bc->ch_params.tx_delay = par.tx_delay;
  5989. +        bc->ch_params.tx_tail = par.tx_tail;
  5990. +        bc->ch_params.slottime = par.slottime;
  5991. +        bc->ch_params.ppersist = par.ppersist;
  5992. +        bc->ch_params.fulldup = par.fulldup;
  5993. +        return 0;
  5994. +
  5995. +    case BAYCOMCTL_GETSTAT:
  5996. +        i = verify_area(VERIFY_WRITE, (void *) arg, 
  5997. +                sizeof(struct baycom_statistics));
  5998. +        if (i)
  5999. +            return i;
  6000. +        memcpy_tofs((void *)arg, &bc->stat, 
  6001. +                sizeof(struct baycom_statistics));
  6002. +        return 0;
  6003. +        
  6004. +
  6005. +#ifdef BAYCOM_DEBUG
  6006. +    case BAYCOMCTL_GETSAMPLES:
  6007. +        if (bc->bitbuf_channel.rd == bc->bitbuf_channel.wr) 
  6008. +            return -EAGAIN;
  6009. +        i = verify_area(VERIFY_WRITE, (void *) arg, 
  6010. +                sizeof(unsigned char));
  6011. +        if (!i) {
  6012. +            put_user(bc->bitbuf_channel.buffer
  6013. +                 [bc->bitbuf_channel.rd],
  6014. +                 (unsigned char *) arg);
  6015. +            bc->bitbuf_channel.rd = (bc->bitbuf_channel.rd+1) %
  6016. +                sizeof(bc->bitbuf_channel.buffer);
  6017. +        }
  6018. +        return i;
  6019. +        
  6020. +    case BAYCOMCTL_GETBITS:
  6021. +        if (bc->bitbuf_hdlc.rd == bc->bitbuf_hdlc.wr) 
  6022. +            return -EAGAIN;
  6023. +        i = verify_area(VERIFY_WRITE, (void *) arg, 
  6024. +                sizeof(unsigned char));
  6025. +        if (!i) {
  6026. +            put_user(bc->bitbuf_hdlc.buffer[bc->bitbuf_hdlc.rd],
  6027. +                 (unsigned char *) arg);
  6028. +            bc->bitbuf_hdlc.rd = (bc->bitbuf_hdlc.rd+1) %
  6029. +                sizeof(bc->bitbuf_hdlc.buffer);
  6030. +        }
  6031. +        return i;
  6032. +        
  6033. +    case BAYCOMCTL_DEBUG1:
  6034. +        i = verify_area(VERIFY_WRITE, (void *) arg,
  6035. +                sizeof(unsigned long));
  6036. +        if (!i)
  6037. +            put_user((bc->rx_buf.wr-bc->rx_buf.rd) % 
  6038. +                 bc->rx_buf.buflen, (unsigned long *)arg);
  6039. +        return i;
  6040. +        
  6041. +    case BAYCOMCTL_DEBUG2:
  6042. +        i = verify_area(VERIFY_WRITE, (void *) arg,
  6043. +                sizeof(unsigned long));
  6044. +        if (!i)
  6045. +            put_user(bc->debug_vals.last_intcnt, 
  6046. +                 (unsigned long *)arg);
  6047. +        return i;
  6048. +        
  6049. +    case BAYCOMCTL_DEBUG3:
  6050. +        i = verify_area(VERIFY_WRITE, (void *) arg, 
  6051. +                sizeof(unsigned long));
  6052. +        if (!i)
  6053. +            put_user((long)bc->debug_vals.last_pllcorr,
  6054. +                 (long *)arg);
  6055. +        return i;        
  6056. +#endif /* BAYCOM_DEBUG */
  6057. +    }
  6058. +}
  6059. +
  6060. +/* --------------------------------------------------------------------- */
  6061. +
  6062. +int baycom_open(struct tty_struct *tty, struct file * filp)
  6063. +{
  6064. +    int line;
  6065. +    struct baycom_state *bc;
  6066. +    int i;
  6067. +
  6068. +    if(!tty)
  6069. +        return -ENODEV;
  6070. +
  6071. +    line = MINOR(tty->device) - tty->driver.minor_start;
  6072. +    if (line < 0 || line >= NR_PORTS)
  6073. +        return -ENODEV;
  6074. +    bc = baycom_state+line;
  6075. +
  6076. +    if (bc->opened > 0) {
  6077. +        bc->opened++;
  6078. +        MOD_INC_USE_COUNT;
  6079. +        return 0;
  6080. +    }
  6081. +    /*
  6082. +     * initialise some variables
  6083. +     */
  6084. +    bc->calibrate = 0;
  6085. +
  6086. +    /*
  6087. +     * allocate the buffer space
  6088. +     */
  6089. +    if (bc->rx_buf.buffer)
  6090. +        kfree_s(bc->rx_buf.buffer, bc->rx_buf.buflen);
  6091. +    if (bc->tx_buf.buffer)
  6092. +        kfree_s(bc->tx_buf.buffer, bc->tx_buf.buflen);
  6093. +    bc->rx_buf.buflen = BUFLEN_RX;
  6094. +    bc->tx_buf.buflen = BUFLEN_TX;
  6095. +    bc->rx_buf.rd = bc->rx_buf.wr = 0;
  6096. +    bc->tx_buf.rd = bc->tx_buf.wr = 0;
  6097. +    bc->rx_buf.buffer = kmalloc(bc->rx_buf.buflen, GFP_KERNEL);
  6098. +    bc->tx_buf.buffer = kmalloc(bc->tx_buf.buflen, GFP_KERNEL);
  6099. +    if (!bc->rx_buf.buffer || !bc->tx_buf.buffer) {
  6100. +        if (bc->rx_buf.buffer)
  6101. +            kfree_s(bc->rx_buf.buffer, bc->rx_buf.buflen);
  6102. +        if (bc->tx_buf.buffer)
  6103. +            kfree_s(bc->tx_buf.buffer, bc->tx_buf.buflen);
  6104. +        bc->rx_buf.buffer = bc->tx_buf.buffer = NULL;
  6105. +        bc->rx_buf.buflen = bc->tx_buf.buflen = 0;
  6106. +        return -ENOMEM;
  6107. +    }
  6108. +    /*
  6109. +     * check if the modem type has been set
  6110. +     */
  6111. +    switch(bc->modem_type) {
  6112. +    case BAYCOM_MODEM_SER12:
  6113. +        i = ser12_on_open(bc);
  6114. +        break;
  6115. +    case BAYCOM_MODEM_PAR96:
  6116. +        i = par96_on_open(bc);
  6117. +        break;
  6118. +    case BAYCOM_MODEM_INVALID:
  6119. +        /*
  6120. +         * may open even if no hardware specified, in order to
  6121. +         * subsequently allow the BAYCOMCTL_SETPARAMS ioctl
  6122. +         */
  6123. +        i = 0;
  6124. +        break;
  6125. +    default:
  6126. +        return -ENODEV;
  6127. +    }
  6128. +    if (i) 
  6129. +        return i;
  6130. +
  6131. +    bc->opened++;
  6132. +    MOD_INC_USE_COUNT;
  6133. +
  6134. +    tty->driver_data = bc;
  6135. +    bc->tty = tty;
  6136. +
  6137. +    return 0;   
  6138. +}
  6139. +
  6140. +
  6141. +/* --------------------------------------------------------------------- */
  6142. +    
  6143. +static void baycom_close(struct tty_struct *tty, struct file * filp)
  6144. +{
  6145. +    struct baycom_state *bc;
  6146. +        
  6147. +    if(!tty) return;
  6148. +    if (baycom_paranoia_check(bc = tty->driver_data, "close"))
  6149. +        return;
  6150. +
  6151. +    MOD_DEC_USE_COUNT;
  6152. +    bc->opened--;
  6153. +    if (bc->opened <= 0) {
  6154. +        switch(bc->modem_type) {
  6155. +        case BAYCOM_MODEM_SER12:
  6156. +            ser12_on_close(bc);
  6157. +            break;
  6158. +        case BAYCOM_MODEM_PAR96:
  6159. +            par96_on_close(bc);
  6160. +            break;
  6161. +        }
  6162. +        tty->driver_data = NULL;
  6163. +        bc->tty = NULL;
  6164. +        bc->opened = 0;
  6165. +        /*
  6166. +         * free the buffers 
  6167. +         */
  6168. +        bc->rx_buf.rd = bc->rx_buf.wr = 0;
  6169. +        bc->tx_buf.rd = bc->tx_buf.wr = 0;
  6170. +        if (bc->rx_buf.buffer)
  6171. +            kfree_s(bc->rx_buf.buffer, bc->rx_buf.buflen);
  6172. +        if (bc->tx_buf.buffer)
  6173. +            kfree_s(bc->tx_buf.buffer, bc->tx_buf.buflen);
  6174. +        bc->rx_buf.buffer = bc->tx_buf.buffer = NULL;
  6175. +        bc->rx_buf.buflen = bc->tx_buf.buflen = 0;
  6176. +    }
  6177. +}
  6178. +
  6179. +/* --------------------------------------------------------------------- */
  6180. +/*
  6181. + * And now the modules code and kernel interface.
  6182. + */
  6183. +
  6184. +static void init_channel(struct baycom_state *bc)
  6185. +{
  6186. +    struct access_params dflt_ch_params = { 20, 2, 10, 40, 0 };
  6187. +
  6188. +    if (!bc)
  6189. +        return;
  6190. +
  6191. +    bc->hdlc_rx.rx_state = 0;
  6192. +
  6193. +    bc->hdlc_tx.tx_state = bc->hdlc_tx.numflags = 0;
  6194. +    bc->hdlc_tx.bitstream = 0;
  6195. +    bc->hdlc_tx.current_byte = bc->hdlc_tx.ptt = 0;
  6196. +
  6197. +    memset(&bc->modem, 0, sizeof(bc->modem));
  6198. +
  6199. +#ifdef BAYCOM_DEBUG
  6200. +    bc->bitbuf_channel.rd = bc->bitbuf_channel.wr = 0;
  6201. +    bc->bitbuf_channel.shreg = 1;
  6202. +
  6203. +    bc->bitbuf_hdlc.rd = bc->bitbuf_hdlc.wr = 0;
  6204. +    bc->bitbuf_hdlc.shreg = 1;
  6205. +#endif /* BAYCOM_DEBUG */
  6206. +
  6207. +    bc->kiss_decode.dec_state = bc->kiss_decode.escaped = 
  6208. +    bc->kiss_decode.wr = 0;
  6209. +
  6210. +    bc->ch_params = dflt_ch_params;
  6211. +}
  6212. +
  6213. +static void init_datastructs(void)
  6214. +{
  6215. +    int i;
  6216. +
  6217. +    for(i = 0; i < NR_PORTS; i++) {
  6218. +        struct baycom_state *bc = baycom_state+i;
  6219. +
  6220. +        bc->magic = BAYCOM_MAGIC;
  6221. +        bc->modem_type = BAYCOM_MODEM_INVALID;
  6222. +        bc->iobase = bc->irq = bc->options = bc->opened = 0;
  6223. +        bc->tty = NULL;
  6224. +
  6225. +        bc->rx_buf.rd = bc->rx_buf.wr = 0;
  6226. +        bc->rx_buf.buflen = 0;
  6227. +        bc->rx_buf.buffer = NULL;
  6228. +
  6229. +        bc->tx_buf.rd = bc->tx_buf.wr = 0;
  6230. +        bc->tx_buf.buflen = 0;
  6231. +        bc->tx_buf.buffer = NULL;
  6232. +
  6233. +        memset(&bc->stat, 0, sizeof(bc->stat));
  6234. +
  6235. +        init_channel(bc);
  6236. +    }
  6237. +}
  6238. +
  6239. +int baycom_init(void) {
  6240. +    int i, j;
  6241. +
  6242. +    /*
  6243. +     * initialize the data structures
  6244. +     */
  6245. +    init_datastructs();
  6246. +    /*
  6247. +     * register the driver as tty driver
  6248. +     */
  6249. +    memset(&baycom_driver, 0, sizeof(struct tty_driver));
  6250. +    baycom_driver.magic = TTY_DRIVER_MAGIC;
  6251. +    baycom_driver.name = "baycom";
  6252. +    baycom_driver.major = major;
  6253. +    baycom_driver.minor_start = 0;
  6254. +    baycom_driver.num = NR_PORTS;
  6255. +    baycom_driver.type = TTY_DRIVER_TYPE_BAYCOM;
  6256. +    baycom_driver.subtype = BAYCOM_TYPE_NORMAL;
  6257. +    baycom_driver.init_termios.c_iflag = 0;
  6258. +    baycom_driver.init_termios.c_oflag = 0;
  6259. +    baycom_driver.init_termios.c_cflag = CS8 | B1200 | CREAD | CLOCAL;
  6260. +    baycom_driver.init_termios.c_lflag = 0;
  6261. +    baycom_driver.flags = TTY_DRIVER_REAL_RAW;
  6262. +    baycom_driver.refcount = &baycom_refcount;
  6263. +    baycom_driver.table = baycom_table;
  6264. +    baycom_driver.termios = baycom_termios;
  6265. +    baycom_driver.termios_locked = baycom_termios_locked;
  6266. +    /*
  6267. +     * the functions
  6268. +     */
  6269. +    baycom_driver.open = baycom_open;
  6270. +    baycom_driver.close = baycom_close;
  6271. +    baycom_driver.write = baycom_write;
  6272. +    baycom_driver.put_char = baycom_put_char;
  6273. +    baycom_driver.flush_chars = NULL;
  6274. +    baycom_driver.write_room = baycom_write_room;
  6275. +    baycom_driver.chars_in_buffer = baycom_chars_in_buffer;
  6276. +    baycom_driver.flush_buffer = baycom_flush_buffer;
  6277. +    baycom_driver.ioctl = baycom_ioctl;
  6278. +    /*
  6279. +     * cannot throttle the transmitter on this layer
  6280. +     */
  6281. +    baycom_driver.throttle = NULL;
  6282. +    baycom_driver.unthrottle = NULL;
  6283. +    /*
  6284. +     * no special actions on termio changes
  6285. +     */
  6286. +    baycom_driver.set_termios = NULL;
  6287. +    /*
  6288. +     * no XON/XOFF and no hangup on the radio port
  6289. +     */
  6290. +    baycom_driver.stop = NULL;
  6291. +    baycom_driver.start = NULL;
  6292. +    baycom_driver.hangup = NULL;
  6293. +    baycom_driver.set_ldisc = NULL;
  6294. +
  6295. +    if (tty_register_driver(&baycom_driver)) {
  6296. +        printk(KERN_WARNING "baycom: tty_register_driver failed\n");
  6297. +        return -EIO;
  6298. +    }
  6299. +
  6300. +    for (i = 0; i < NR_PORTS && 
  6301. +         baycom_ports[i].modem != BAYCOM_MODEM_INVALID; i++) {
  6302. +        j = baycom_set_hardware(baycom_state+i, 
  6303. +                    baycom_ports[i].modem,
  6304. +                    baycom_ports[i].iobase, 
  6305. +                    baycom_ports[i].irq, 
  6306. +                    baycom_ports[i].options);
  6307. +        if (j < 0) {
  6308. +            const char *s;
  6309. +            switch (-j) {
  6310. +            case ENXIO:
  6311. +                s = "invalid iobase and/or irq";
  6312. +                break;
  6313. +            case EACCES:
  6314. +                s = "io region already used";
  6315. +                break;
  6316. +            case EIO:
  6317. +                s = "no uart/lpt port at iobase";
  6318. +                break;
  6319. +            case EBUSY:
  6320. +                s = "interface already in use";
  6321. +                break;
  6322. +            case EINVAL:
  6323. +                s = "internal error";
  6324. +                break;
  6325. +            default:
  6326. +                s = "unknown error";
  6327. +                break;
  6328. +            }
  6329. +            printk(KERN_WARNING "baycom: modem %u iobase 0x%x "
  6330. +                   "irq %u: (%i) %s\n", baycom_ports[i].modem, 
  6331. +                   baycom_ports[i].iobase, baycom_ports[i].irq, 
  6332. +                   j, s);
  6333. +        }
  6334. +    }
  6335. +
  6336. +    return 0;
  6337. +}
  6338. +
  6339. +/* --------------------------------------------------------------------- */
  6340. +
  6341. +#ifdef MODULE
  6342. +
  6343. +int modem = BAYCOM_MODEM_INVALID;
  6344. +int iobase = 0x3f8;
  6345. +int irq = 4;
  6346. +int options = BAYCOM_OPTIONS_SOFTDCD;
  6347. +
  6348. +int init_module(void)
  6349. +{
  6350. +    int i;
  6351. +
  6352. +    printk(KERN_INFO "baycom: init_module called\n");
  6353. +
  6354. +    baycom_ports[0].modem = modem;
  6355. +    baycom_ports[0].iobase = iobase;
  6356. +    baycom_ports[0].irq = irq;
  6357. +    baycom_ports[0].options = options;
  6358. +    baycom_ports[1].modem = BAYCOM_MODEM_INVALID;
  6359. +
  6360. +    i = baycom_init();
  6361. +    if (i)
  6362. +        return i;
  6363. +
  6364. +    printk(KERN_INFO "baycom: version 0.2; "
  6365. +           "(C) 1996 by Thomas Sailer HB9JNX, sailer@ife.ee.ethz.ch\n");
  6366. +
  6367. +    return 0;
  6368. +}
  6369. +
  6370. +/* --------------------------------------------------------------------- */
  6371. +
  6372. +void cleanup_module(void)
  6373. +{
  6374. +    int i;
  6375. +
  6376. +#if 0
  6377. +    if (MOD_IN_USE)
  6378. +        printk(KERN_INFO "baycom: device busy, remove delayed\n");
  6379. +#endif
  6380. +    printk(KERN_INFO "baycom: cleanup_module called\n");
  6381. +
  6382. +    if (tty_unregister_driver(&baycom_driver))
  6383. +        printk(KERN_WARNING "baycom: failed to unregister tty "
  6384. +               "driver\n");
  6385. +    for(i = 0; i < NR_PORTS; i++) {
  6386. +        struct baycom_state *bc = baycom_state+i;
  6387. +
  6388. +        if (bc->magic != BAYCOM_MAGIC)
  6389. +            printk(KERN_ERR "baycom: invalid magic in "
  6390. +                   "cleanup_module\n");
  6391. +        else {
  6392. +            baycom_dealloc_hw(bc);
  6393. +            /*
  6394. +             * free the buffers 
  6395. +             */
  6396. +            bc->rx_buf.rd = bc->rx_buf.wr = 0;
  6397. +            bc->tx_buf.rd = bc->tx_buf.wr = 0;
  6398. +            if (bc->rx_buf.buffer)
  6399. +                kfree_s(bc->rx_buf.buffer, bc->rx_buf.buflen);
  6400. +            if (bc->tx_buf.buffer)
  6401. +                kfree_s(bc->tx_buf.buffer, bc->tx_buf.buflen);
  6402. +            bc->rx_buf.buffer = bc->tx_buf.buffer = NULL;
  6403. +            bc->rx_buf.buflen = bc->tx_buf.buflen = 0;
  6404. +        }
  6405. +    }
  6406. +}
  6407. +
  6408. +#else /* MODULE */
  6409. +/* --------------------------------------------------------------------- */
  6410. +/*
  6411. + * format: baycom=modem,io,irq,options[,modem,io,irq,options]
  6412. + * modem=1: ser12, modem=2: par96
  6413. + * options=0: hardware DCD, options=1: software DCD
  6414. + */
  6415. +
  6416. +void baycom_setup(char *str, int *ints)
  6417. +{
  6418. +    int i;
  6419. +
  6420. +    for (i = 0; i < NR_PORTS; i++) 
  6421. +        if (ints[0] >= 4*i+4) {
  6422. +            baycom_ports[i].modem = ints[4*i+1];
  6423. +            baycom_ports[i].iobase = ints[4*i+2];
  6424. +            baycom_ports[i].irq = ints[4*i+3];
  6425. +            baycom_ports[i].options = ints[4*i+4];
  6426. +        } else
  6427. +            baycom_ports[i].modem = BAYCOM_MODEM_INVALID;
  6428. +
  6429. +}
  6430. +
  6431. +#endif /* MODULE */
  6432. +/* --------------------------------------------------------------------- */
  6433. +
  6434. +/*
  6435. + * Overrides for Emacs so that we follow Linus's tabbing style.
  6436. + * Emacs will notice this stuff at the end of the file and automatically
  6437. + * adjust the settings for this buffer only.  This must remain at the end
  6438. + * of the file.
  6439. + * ---------------------------------------------------------------------------
  6440. + * Local variables:
  6441. + * c-indent-level: 8
  6442. + * c-brace-imaginary-offset: 0
  6443. + * c-brace-offset: -8
  6444. + * c-argdecl-indent: 8
  6445. + * c-label-offset: -8
  6446. + * c-continued-statement-offset: 8
  6447. + * c-continued-brace-offset: 0
  6448. + * End:
  6449. + */
  6450. diff -u --recursive --new-file pre2.0.4/linux/drivers/char/console.c linux/drivers/char/console.c
  6451. --- pre2.0.4/linux/drivers/char/console.c    Tue May  7 16:22:23 1996
  6452. +++ linux/drivers/char/console.c    Wed May 15 09:06:55 1996
  6453. @@ -2116,11 +2116,6 @@
  6454.  {
  6455.      int currcons;
  6456.  
  6457. -#ifdef CONFIG_APM
  6458. -    if (apm_display_blank())
  6459. -        return;
  6460. -#endif
  6461. -
  6462.      if (console_blanked)
  6463.          return;
  6464.  
  6465. @@ -2146,6 +2141,10 @@
  6466.      hide_cursor();
  6467.      console_blanked = fg_console + 1;
  6468.  
  6469. +#ifdef CONFIG_APM
  6470. +    if (apm_display_blank())
  6471. +        return;
  6472. +#endif
  6473.      if(!nopowersave)
  6474.          vesa_blank();
  6475.  }
  6476. @@ -2156,11 +2155,6 @@
  6477.      int resetorg;
  6478.      long offset;
  6479.  
  6480. -#ifdef CONFIG_APM
  6481. -    if (apm_display_unblank())
  6482. -        return;
  6483. -#endif
  6484. -
  6485.      if (!console_blanked)
  6486.          return;
  6487.      if (!vc_cons_allocated(fg_console)) {
  6488. @@ -2193,6 +2187,10 @@
  6489.          __set_origin(blank__origin);
  6490.  
  6491.      vesa_unblank();
  6492. +#ifdef CONFIG_APM
  6493. +    if (apm_display_unblank())
  6494. +        return;
  6495. +#endif
  6496.  }
  6497.  
  6498.  /*
  6499. diff -u --recursive --new-file pre2.0.4/linux/drivers/char/tty_io.c linux/drivers/char/tty_io.c
  6500. --- pre2.0.4/linux/drivers/char/tty_io.c    Wed Apr 24 17:00:39 1996
  6501. +++ linux/drivers/char/tty_io.c    Thu May 16 16:35:39 1996
  6502. @@ -1874,6 +1874,9 @@
  6503.  #ifdef CONFIG_RISCOM8
  6504.      riscom8_init();
  6505.  #endif
  6506. +#ifdef CONFIG_BAYCOM
  6507. +    baycom_init();
  6508. +#endif
  6509.      pty_init();
  6510.      vcs_init();
  6511.      return 0;
  6512. diff -u --recursive --new-file pre2.0.4/linux/drivers/isdn/Config.in linux/drivers/isdn/Config.in
  6513. --- pre2.0.4/linux/drivers/isdn/Config.in    Sun Apr 21 19:22:06 1996
  6514. +++ linux/drivers/isdn/Config.in    Thu May 16 16:35:39 1996
  6515. @@ -8,6 +8,6 @@
  6516.      bool 'Support generic MP (RFC 1717)' CONFIG_ISDN_MPP
  6517.    fi
  6518.  fi
  6519. -dep_tristate 'Teles/NICCY1016PC/Creatix support' CONFIG_ISDN_DRV_TELES $CONFIG_ISDN
  6520.  dep_tristate 'ICN B1 and B2 support' CONFIG_ISDN_DRV_ICN $CONFIG_ISDN
  6521.  dep_tristate 'PCBIT-D support' CONFIG_ISDN_DRV_PCBIT $CONFIG_ISDN
  6522. +dep_tristate 'Teles/NICCY1016PC/Creatix support' CONFIG_ISDN_DRV_TELES $CONFIG_ISDN
  6523. diff -u --recursive --new-file pre2.0.4/linux/drivers/isdn/pcbit/module.c linux/drivers/isdn/pcbit/module.c
  6524. --- pre2.0.4/linux/drivers/isdn/pcbit/module.c    Wed Apr 24 17:00:39 1996
  6525. +++ linux/drivers/isdn/pcbit/module.c    Wed May 15 09:09:00 1996
  6526. @@ -93,11 +93,6 @@
  6527.  {
  6528.      int board;
  6529.  
  6530. -    if (MOD_IN_USE) {
  6531. -        printk(KERN_WARNING "pcbit: device busy, remove cancelled\n");
  6532. -        return;
  6533. -    }
  6534. -
  6535.      for (board = 0; board < num_boards; board++)
  6536.          pcbit_terminate(board);
  6537.      printk(KERN_INFO 
  6538. diff -u --recursive --new-file pre2.0.4/linux/drivers/net/3c509.c linux/drivers/net/3c509.c
  6539. --- pre2.0.4/linux/drivers/net/3c509.c    Sat Apr 27 15:19:53 1996
  6540. +++ linux/drivers/net/3c509.c    Wed May 15 09:09:00 1996
  6541. @@ -784,16 +784,11 @@
  6542.  void
  6543.  cleanup_module(void)
  6544.  {
  6545. -    if (MOD_IN_USE)
  6546. -        printk("3c509: device busy, remove delayed\n");
  6547. -    else
  6548. -    {
  6549. -        unregister_netdev(&dev_3c509);
  6550. -        kfree_s(dev_3c509.priv,sizeof(struct el3_private));
  6551. -        dev_3c509.priv=NULL;
  6552. -        /* If we don't do this, we can't re-insmod it later. */
  6553. -        release_region(dev_3c509.base_addr, EL3_IO_EXTENT);
  6554. -    }
  6555. +    unregister_netdev(&dev_3c509);
  6556. +    kfree_s(dev_3c509.priv,sizeof(struct el3_private));
  6557. +    dev_3c509.priv=NULL;
  6558. +    /* If we don't do this, we can't re-insmod it later. */
  6559. +    release_region(dev_3c509.base_addr, EL3_IO_EXTENT);
  6560.  }
  6561.  #endif /* MODULE */
  6562.  
  6563. diff -u --recursive --new-file pre2.0.4/linux/drivers/net/8390.c linux/drivers/net/8390.c
  6564. --- pre2.0.4/linux/drivers/net/8390.c    Tue May  7 16:22:26 1996
  6565. +++ linux/drivers/net/8390.c    Thu May 16 11:18:50 1996
  6566. @@ -29,6 +29,7 @@
  6567.                ei_block_input() for eth_io_copy_and_sum().
  6568.    Paul Gortmaker    : exchange static int ei_pingpong for a #define,
  6569.                also add better Tx error handling.
  6570. +  Paul Gortmaker    : rewrite Rx overrun handling as per NS specs.
  6571.  
  6572.  
  6573.    Sources:
  6574. @@ -377,6 +378,7 @@
  6575.      int e8390_base = dev->base_addr;
  6576.      unsigned char txsr = inb_p(e8390_base+EN0_TSR);
  6577.      unsigned char tx_was_aborted = txsr & (ENTSR_ABT+ENTSR_FU);
  6578. +    struct ei_device *ei_local = (struct ei_device *) dev->priv;
  6579.  
  6580.  #ifdef VERBOSE_ERROR_DUMP
  6581.      printk(KERN_DEBUG "%s: transmitter error (%#2x): ", dev->name, txsr);
  6582. @@ -398,6 +400,13 @@
  6583.      if (tx_was_aborted)
  6584.          ei_tx_intr(dev);
  6585.  
  6586. +    /*
  6587. +     * Note: NCR reads zero on 16 collisions so we add them
  6588. +     * in by hand. Somebody might care...
  6589. +     */
  6590. +    if (txsr & ENTSR_ABT)
  6591. +    ei_local->stat.collisions += 16;
  6592. +    
  6593.  }
  6594.  
  6595.  /* We have finished a transmit: check for errors and then trigger the next
  6596. @@ -580,43 +589,76 @@
  6597.      return;
  6598.  }
  6599.  
  6600. -/* We have a receiver overrun: we have to kick the 8390 to get it started
  6601. -   again.*/
  6602. +/* 
  6603. + * We have a receiver overrun: we have to kick the 8390 to get it started
  6604. + * again. Problem is that you have to kick it exactly as NS prescribes in
  6605. + * the updated datasheets, or "the NIC may act in an unpredictable manner."
  6606. + * This includes causing "the NIC to defer indefinitely when it is stopped
  6607. + * on a busy network."  Ugh.
  6608. + */
  6609.  static void ei_rx_overrun(struct device *dev)
  6610.  {
  6611.      int e8390_base = dev->base_addr;
  6612. -    int reset_start_time = jiffies;
  6613. +    unsigned long wait_start_time;
  6614. +    unsigned char was_txing, must_resend = 0;
  6615.      struct ei_device *ei_local = (struct ei_device *) dev->priv;
  6616.      
  6617. -    /* We should already be stopped and in page0.  Remove after testing. */
  6618. +    /*
  6619. +     * Record whether a Tx was in progress and then issue the
  6620. +     * stop command.
  6621. +     */
  6622. +    was_txing = inb_p(e8390_base+E8390_CMD) & E8390_TRANS;
  6623.      outb_p(E8390_NODMA+E8390_PAGE0+E8390_STOP, e8390_base+E8390_CMD);
  6624.      
  6625.      if (ei_debug > 1)
  6626. -        printk("%s: Receiver overrun.\n", dev->name);
  6627. +    printk("%s: Receiver overrun.\n", dev->name);
  6628.      ei_local->stat.rx_over_errors++;
  6629.      
  6630. -    /* The old Biro driver does dummy = inb_p( RBCR[01] ); at this point.
  6631. -       It might mean something -- magic to speed up a reset?  A 8390 bug?*/
  6632. -    
  6633. -    /* Wait for the reset to complete.    This should happen almost instantly,
  6634. -       but could take up to 1.5msec in certain rare instances.  There is no
  6635. -       easy way of timing something in that range, so we use 'jiffies' as
  6636. -       a sanity check. */
  6637. -    while ((inb_p(e8390_base+EN0_ISR) & ENISR_RESET) == 0)
  6638. -        if (jiffies - reset_start_time > 2*HZ/100) {
  6639. -            printk("%s: reset did not complete at ei_rx_overrun.\n",
  6640. -                   dev->name);
  6641. -            NS8390_init(dev, 1);
  6642. -            return;
  6643. -        }
  6644. -    
  6645. -    /* Remove packets right away. */
  6646. +    /* 
  6647. +     * Wait a full Tx time (1.2ms) + some guard time, NS says 1.6ms total.
  6648. +     * Early datasheets said to poll the reset bit, but now they say that
  6649. +     * it "is not a reliable indicator and subequently should be ignored."
  6650. +     * We wait at least 10ms.
  6651. +     */
  6652. +    wait_start_time = jiffies;
  6653. +    while (jiffies - wait_start_time <= 1*HZ/100)
  6654. +    barrier();
  6655. +
  6656. +    /*
  6657. +     * Reset RBCR[01] back to zero as per magic incantation.
  6658. +     */
  6659. +    outb_p(0x00, e8390_base+EN0_RCNTLO);
  6660. +    outb_p(0x00, e8390_base+EN0_RCNTHI);
  6661. +
  6662. +    /*
  6663. +     * See if any Tx was interrupted or not. According to NS, this
  6664. +     * step is vital, and skipping it will cause no end of havoc.
  6665. +     */
  6666. +    if (was_txing) { 
  6667. +    unsigned char tx_completed = inb_p(e8390_base+EN0_ISR) & (ENISR_TX+ENISR_TX_ERR);
  6668. +    if (!tx_completed) must_resend = 1;
  6669. +    }
  6670. +
  6671. +    /*
  6672. +     * Have to enter loopback mode and then restart the NIC before
  6673. +     * you are allowed to slurp packets up off the ring.
  6674. +     */
  6675. +    outb_p(E8390_TXOFF, e8390_base + EN0_TXCR);
  6676. +    outb_p(E8390_NODMA + E8390_PAGE0 + E8390_START, e8390_base + E8390_CMD);
  6677. +
  6678. +    /*
  6679. +     * Clear the Rx ring of all the debris, and ack the interrupt.
  6680. +     */
  6681.      ei_receive(dev);
  6682. -    
  6683.      outb_p(ENISR_OVER, e8390_base+EN0_ISR);
  6684. -    /* Generic 8390 insns to start up again, same as in open_8390(). */
  6685. -    outb_p(E8390_NODMA + E8390_PAGE0 + E8390_START, e8390_base + E8390_CMD);
  6686. -    outb_p(E8390_TXCONFIG, e8390_base + EN0_TXCR); /* xmit on. */
  6687. +
  6688. +    /*
  6689. +     * Leave loopback mode, and resend any packet that got stopped.
  6690. +     */
  6691. +    outb_p(E8390_TXCONFIG, e8390_base + EN0_TXCR); 
  6692. +    if (must_resend)
  6693. +        outb_p(E8390_NODMA + E8390_PAGE0 + E8390_START + E8390_TRANS, e8390_base + E8390_CMD);
  6694. +    
  6695.  }
  6696.  
  6697.  static struct enet_statistics *get_stats(struct device *dev)
  6698. diff -u --recursive --new-file pre2.0.4/linux/drivers/net/CONFIG linux/drivers/net/CONFIG
  6699. --- pre2.0.4/linux/drivers/net/CONFIG    Sun Apr 21 12:39:01 1996
  6700. +++ linux/drivers/net/CONFIG    Thu May 16 20:12:56 1996
  6701. @@ -59,6 +59,8 @@
  6702.  #                       For manual 100Mb/s mode selection  (DC21140) = _100Mb
  6703.  #                       The DC21040 will default to TP if TP_NW is specified
  6704.  #                       The DC21041 will default to BNC if BNC_AUI is specified
  6705. +#     DE4X5_DO_MEMCPY   Forces the Intels to use memory copies into sk_buffs
  6706. +#                    rather than straight DMA.
  6707.  #
  6708.  #  TULIP        Tulip (dc21040/dc21041/ds21140) driver
  6709.  #    TULIP_PORT    specify default if_port
  6710. diff -u --recursive --new-file pre2.0.4/linux/drivers/net/Config.in linux/drivers/net/Config.in
  6711. --- pre2.0.4/linux/drivers/net/Config.in    Mon May 13 23:02:49 1996
  6712. +++ linux/drivers/net/Config.in    Thu May 16 20:12:57 1996
  6713. @@ -25,15 +25,16 @@
  6714.  bool 'Radio network interfaces' CONFIG_NET_RADIO
  6715.  if [ "$CONFIG_NET_RADIO" != "n" ]; then
  6716.    if [ "$CONFIG_AX25" = "y" ]; then
  6717. +    if [ "$CONFIG_EXPERIMENTAL" = "y" ]; then
  6718. +      tristate 'BAYCOM ser12 and par96 kiss emulation driver for AX.25' CONFIG_BAYCOM
  6719. +    fi
  6720.      bool 'Gracilis PackeTwin support' CONFIG_PT
  6721.      bool 'Ottawa PI and PI/2 support' CONFIG_PI
  6722.    fi
  6723.    tristate 'STRIP (Metricom starmode radio IP)' CONFIG_STRIP
  6724.    tristate 'WaveLAN support' CONFIG_WAVELAN
  6725.    tristate 'WIC Radio IP bridge (EXPERIMENTAL)' CONFIG_WIC
  6726. -  if [ "$CONFIG_AX25" = "y" ]; then
  6727. -    tristate 'Z8530 SCC kiss emulation driver for AX.25' CONFIG_SCC
  6728. -  fi
  6729. +  tristate 'Z8530 SCC kiss emulation driver for AX.25' CONFIG_SCC
  6730.  fi
  6731.  #
  6732.  #    Ethernet
  6733. @@ -67,12 +68,12 @@
  6734.        tristate 'AT1700 support (EXPERIMENTAL)' CONFIG_AT1700
  6735.      fi
  6736.      tristate 'Cabletron E21xx support' CONFIG_E2100
  6737. -    tristate 'DEPCA support' CONFIG_DEPCA
  6738. -    tristate 'EtherWorks 3 support' CONFIG_EWRK3
  6739. +    tristate 'DEPCA, DE10x, DE200, DE201, DE202, DE422 support' CONFIG_DEPCA
  6740. +    tristate 'EtherWORKS 3 (DE203, DE204, DE205) support' CONFIG_EWRK3
  6741.      tristate 'EtherExpress 16 support' CONFIG_EEXPRESS
  6742.      if [ "$CONFIG_EXPERIMENTAL" = "y" ]; then
  6743.        tristate 'EtherExpressPro support' CONFIG_EEXPRESS_PRO
  6744. -      tristate 'FMV-181/182 support' CONFIG_FMV18X
  6745. +      tristate 'FMV-181/182/183/184 support' CONFIG_FMV18X
  6746.      fi
  6747.      tristate 'HP PCLAN+ (27247B and 27252A) support' CONFIG_HPLAN_PLUS
  6748.      tristate 'HP PCLAN (27245 and other 27xxx series) support' CONFIG_HPLAN
  6749. @@ -96,7 +97,7 @@
  6750.        tristate 'Ansel Communications EISA 3200 support (EXPERIMENTAL)' CONFIG_AC3200
  6751.      fi
  6752.      tristate 'Apricot Xen-II on board ethernet' CONFIG_APRICOT
  6753. -    tristate 'DE425, DE434, DE435, DE500 support' CONFIG_DE4X5
  6754. +    tristate 'DE425, DE434, DE435, DE450, DE500 support' CONFIG_DE4X5
  6755.      tristate 'DECchip Tulip (dc21x4x) PCI support' CONFIG_DEC_ELCP
  6756.      tristate 'Digi Intl. RightSwitch SE-X support' CONFIG_DGRS
  6757.      if [ "$CONFIG_EXPERIMENTAL" = "y" ]; then
  6758. diff -u --recursive --new-file pre2.0.4/linux/drivers/net/de4x5.c linux/drivers/net/de4x5.c
  6759. --- pre2.0.4/linux/drivers/net/de4x5.c    Sat Apr 27 15:19:53 1996
  6760. +++ linux/drivers/net/de4x5.c    Thu May 16 20:12:56 1996
  6761. @@ -53,7 +53,7 @@
  6762.      achieved by letting the driver autoprobe as if it were compiled into the
  6763.      kernel, except that there is no autoprobing of the IRQ lines. This is of
  6764.      no great  consequence except do make sure  you're not sharing interrupts
  6765. -    with  anything that cannot  accommodate  interrupt sharing!  The existing
  6766. +    with  anything that cannot  accommodate  interrupt sharing! The existing
  6767.      register_netdevice() code will only allow one device to be registered at
  6768.      a time. 
  6769.  
  6770. @@ -108,7 +108,7 @@
  6771.      applies most particularly to the DC21140 based cards).
  6772.  
  6773.      I've changed the timing routines to  use the kernel timer and scheduling
  6774. -    functions  so that the  hangs  and other assorted  problems that occurred
  6775. +    functions  so that the  hangs  and other assorted problems that occurred
  6776.      while autosensing the  media  should be gone.  A  bonus  for the DC21040
  6777.      auto  media sense algorithm is  that it can now  use one that is more in
  6778.      line with the  rest (the DC21040  chip doesn't  have a hardware  timer).
  6779. @@ -820,7 +820,7 @@
  6780.      ** Set up the RX descriptor ring (Intels)
  6781.      ** Allocate contiguous receive buffers, long word aligned (Alphas) 
  6782.      */
  6783. -#ifndef __alpha__
  6784. +#if !defined(__alpha__) && !defined(DE4X5_DO_MEMCPY)
  6785.      for (i=0; i<NUM_RX_DESC; i++) {
  6786.          lp->rx_ring[i].status = 0;
  6787.          lp->rx_ring[i].des1 = RX_BUFF_SZ;
  6788. @@ -2627,7 +2627,7 @@
  6789.      struct de4x5_private *lp = (struct de4x5_private *)dev->priv;
  6790.      struct sk_buff *p;
  6791.  
  6792. -#ifndef __alpha__
  6793. +#if !defined(__alpha__) && !defined(DE4X5_DO_MEMCPY)
  6794.      struct sk_buff *ret;
  6795.      u_long i=0, tmp;
  6796.  
  6797. diff -u --recursive --new-file pre2.0.4/linux/drivers/net/fmv18x.c linux/drivers/net/fmv18x.c
  6798. --- pre2.0.4/linux/drivers/net/fmv18x.c    Fri Apr 12 15:51:55 1996
  6799. +++ linux/drivers/net/fmv18x.c    Thu May 16 16:35:40 1996
  6800. @@ -1,4 +1,4 @@
  6801. -/* fmv18x.c: A network device driver for  the Fujitsu FMV-181/182.
  6802. +/* fmv18x.c: A network device driver for the Fujitsu FMV-181/182/183/184.
  6803.  
  6804.      Original: at1700.c (1993-94 by Donald Becker).
  6805.          Copyright 1993 United States Government as represented by the
  6806. @@ -22,8 +22,8 @@
  6807.      This software may be used and distributed according to the terms
  6808.      of the GNU Public License, incorporated herein by reference.
  6809.  
  6810. -    This is a device driver for the Fujitsu FMV-181/182, which is a
  6811. -    straight-forward Fujitsu MB86965 implementation.
  6812. +    This is a device driver for the Fujitsu FMV-181/182/183/184, which
  6813. +    is a straight-forward Fujitsu MB86965 implementation.
  6814.  
  6815.    Sources:
  6816.      at1700.c
  6817. diff -u --recursive --new-file pre2.0.4/linux/drivers/net/sdla.c linux/drivers/net/sdla.c
  6818. --- pre2.0.4/linux/drivers/net/sdla.c    Tue May  7 16:22:30 1996
  6819. +++ linux/drivers/net/sdla.c    Wed May 15 10:38:35 1996
  6820. @@ -5,7 +5,7 @@
  6821.   *
  6822.   *        Global definitions for the Frame relay interface.
  6823.   *
  6824. - * Version:    @(#)sdla.c   0.20    13 Apr 1996
  6825. + * Version:    @(#)sdla.c   0.25    14 May 1996
  6826.   *
  6827.   * Credits:    Sangoma Technologies, for the use of 2 cards for an extended
  6828.   *            period of time.
  6829. @@ -20,7 +20,9 @@
  6830.   *        0.15    Mike McLagan    Improved error handling, packet dropping
  6831.   *        0.20    Mike McLagan    New transmit/receive flags for config
  6832.   *                    If in FR mode, don't accept packets from
  6833. - *                    non-DLCI devices.
  6834. + *                    non DLCI devices.
  6835. + *        0.25    Mike McLagan    Fixed problem with rejecting packets
  6836. + *                    from non DLCI devices.
  6837.   *
  6838.   *
  6839.   *        This program is free software; you can redistribute it and/or
  6840. @@ -56,7 +58,7 @@
  6841.  
  6842.  #include <linux/sdla.h>
  6843.  
  6844. -static const char* version = "SDLA driver v0.20, 13 Apr 1996, mike.mclagan@linux.org";
  6845. +static const char* version = "SDLA driver v0.25, 14 May 1996, mike.mclagan@linux.org";
  6846.  
  6847.  static const char* devname = "sdla";
  6848.  
  6849. @@ -327,7 +329,7 @@
  6850.     struct _dlci_stat *pstatus;
  6851.     short             *pdlci;
  6852.     int               i;
  6853. -   char              *state;
  6854. +   char              *state, line[30];
  6855.  
  6856.     switch (ret)
  6857.     {
  6858. @@ -364,8 +366,10 @@
  6859.                    if (pstatus->flags & SDLA_DLCI_ACTIVE)
  6860.                       state = "active";
  6861.                    else
  6862. -                     state = "unknown status";
  6863. +                  {
  6864. +                     sprintf(line, "uknown status: %02X", pstatus->flags);
  6865. +                     state = line;
  6866. +                  }
  6867.              printk(KERN_INFO "%s: DLCI %i: %s.\n", dev->name, pstatus->dlci, state);
  6868.  /* same here */
  6869.           }
  6870. @@ -637,13 +641,14 @@
  6871.  static int sdla_transmit(struct sk_buff *skb, struct device *dev)
  6872.  {
  6873.     struct frad_local *flp;
  6874. -   int               ret, addr;
  6875. +   int               ret, addr, accept;
  6876.     short             size;
  6877.     unsigned long     flags;
  6878.     struct buf_entry  *pbuf;
  6879.  
  6880.     flp = dev->priv;
  6881.     ret = 0;
  6882. +   accept = 1;
  6883.  
  6884.     if (dev->tbusy) 
  6885.        return(1);
  6886. @@ -655,75 +660,77 @@
  6887.        printk(KERN_WARNING "%s: transmitter access conflict.\n", dev->name);
  6888.     else
  6889.     {
  6890.        /*
  6891.         * stupid GateD insists on setting up the multicast router thru us
  6892.         * and we're ill equipped to handle a non Frame Relay packet at this
  6893.         * time!
  6894.         */
  6895.  
  6896. +      accept = 1;
  6897.        switch (dev->type)
  6898.        {
  6899.           case ARPHRD_FRAD:
  6900.              if (skb->dev->type != ARPHRD_DLCI)
  6901.              {
  6902. -               printk(KERN_WARNING "%s: FRAD module accepts packets from DLCI ONLY!\n", dev->name);
  6903. -               dev_kfree_skb(skb, FREE_WRITE);
  6904. -               return(0);
  6905. +               printk(KERN_WARNING "%s: Non DLCI device, type %i, tried to send on FRAD module.\n", dev->name, skb->dev->type);
  6906. +               accept = 0;
  6907.              }
  6908.              break;
  6909.  
  6910.           default:
  6911.              printk(KERN_WARNING "%s: unknown firmware type 0x%4.4X\n", dev->name, dev->type);
  6912. -            dev_kfree_skb(skb, FREE_WRITE);
  6913. -            return(0);
  6914. -      }
  6915. -
  6916. -      /* this is frame specific, but till there's a PPP module, it's the default */
  6917. -      switch (flp->type)
  6918. -      {
  6919. -         case SDLA_S502A:
  6920. -         case SDLA_S502E:
  6921. -            ret = sdla_cmd(dev, SDLA_INFORMATION_WRITE, *(short *)(skb->dev->dev_addr), 0, skb->data, skb->len, NULL, NULL);
  6922. -            break;
  6923. -
  6924. -         case SDLA_S508:
  6925. -            size = sizeof(addr);
  6926. -            ret = sdla_cmd(dev, SDLA_INFORMATION_WRITE, *(short *)(skb->dev->dev_addr), 0, NULL, skb->len, &addr, &size);
  6927. -            if (ret == SDLA_RET_OK)
  6928. -            {
  6929. -               save_flags(flags); 
  6930. -               cli();
  6931. -               SDLA_WINDOW(dev, addr);
  6932. -               pbuf = (void *)(((int) dev->mem_start) + (addr & SDLA_ADDR_MASK));
  6933. -
  6934. -               sdla_write(dev, pbuf->buf_addr, skb->data, skb->len);
  6935. -
  6936. -               SDLA_WINDOW(dev, addr);
  6937. -               pbuf->opp_flag = 1;
  6938. -               restore_flags(flags);
  6939. -            }
  6940. +            accept = 0;
  6941.              break;
  6942.        }
  6943. -      switch (ret)
  6944. +
  6945. +      if (accept)
  6946.        {
  6947. -         case SDLA_RET_OK:
  6948. -            flp->stats.tx_packets++;
  6949. -            ret = DLCI_RET_OK;
  6950. -            break;
  6951. -         case SDLA_RET_CIR_OVERFLOW:
  6952. -         case SDLA_RET_BUF_OVERSIZE:
  6953. -         case SDLA_RET_NO_BUFS:
  6954. -            flp->stats.tx_dropped++;
  6955. -            ret = DLCI_RET_DROP;
  6956. -            break;
  6957. +         /* this is frame specific, but till there's a PPP module, it's the default */
  6958. +         switch (flp->type)
  6959. +         {
  6960. +            case SDLA_S502A:
  6961. +            case SDLA_S502E:
  6962. +               ret = sdla_cmd(dev, SDLA_INFORMATION_WRITE, *(short *)(skb->dev->dev_addr), 0, skb->data, skb->len, NULL, NULL);
  6963. +               break;
  6964. +
  6965. +            case SDLA_S508:
  6966. +               size = sizeof(addr);
  6967. +               ret = sdla_cmd(dev, SDLA_INFORMATION_WRITE, *(short *)(skb->dev->dev_addr), 0, NULL, skb->len, &addr, &size);
  6968. +               if (ret == SDLA_RET_OK)
  6969. +               {
  6970. +                  save_flags(flags); 
  6971. +                  cli();
  6972. +                  SDLA_WINDOW(dev, addr);
  6973. +                  pbuf = (void *)(((int) dev->mem_start) + (addr & SDLA_ADDR_MASK));
  6974. +
  6975. +                  sdla_write(dev, pbuf->buf_addr, skb->data, skb->len);
  6976. +
  6977. +                  SDLA_WINDOW(dev, addr);
  6978. +                  pbuf->opp_flag = 1;
  6979. +                  restore_flags(flags);
  6980. +               }
  6981. +               break;
  6982. +         }
  6983.  
  6984. -         default:
  6985. -            flp->stats.tx_errors++;
  6986. -            ret = DLCI_RET_ERR;
  6987. -            break;
  6988. +         switch (ret)
  6989. +         {
  6990. +            case SDLA_RET_OK:
  6991. +               flp->stats.tx_packets++;
  6992. +               ret = DLCI_RET_OK;
  6993. +               break;
  6994. +
  6995. +            case SDLA_RET_CIR_OVERFLOW:
  6996. +            case SDLA_RET_BUF_OVERSIZE:
  6997. +            case SDLA_RET_NO_BUFS:
  6998. +               flp->stats.tx_dropped++;
  6999. +               ret = DLCI_RET_DROP;
  7000. +               break;
  7001. +
  7002. +            default:
  7003. +               flp->stats.tx_errors++;
  7004. +               ret = DLCI_RET_ERR;
  7005. +               break;
  7006. +         }
  7007.        }
  7008.        dev->tbusy = 0;
  7009.     }
  7010. diff -u --recursive --new-file pre2.0.4/linux/drivers/scsi/BusLogic.c linux/drivers/scsi/BusLogic.c
  7011. --- pre2.0.4/linux/drivers/scsi/BusLogic.c    Fri Apr 19 10:07:59 1996
  7012. +++ linux/drivers/scsi/BusLogic.c    Fri May 17 10:02:01 1996
  7013. @@ -24,8 +24,8 @@
  7014.  */
  7015.  
  7016.  
  7017. -#define BusLogic_DriverVersion        "1.3.2"
  7018. -#define BusLogic_DriverDate        "16 April 1996"
  7019. +#define BusLogic_DriverVersion        "2.0.3"
  7020. +#define BusLogic_DriverDate        "17 May 1996"
  7021.  
  7022.  
  7023.  #include <linux/module.h>
  7024. @@ -69,6 +69,15 @@
  7025.  
  7026.  
  7027.  /*
  7028. +  BusLogic_ProbeOptions is a bit mask of Probe Options to be applied
  7029. +  across all Host Adapters.
  7030. +*/
  7031. +
  7032. +static int
  7033. +  BusLogic_ProbeOptions =        0;
  7034. +
  7035. +
  7036. +/*
  7037.    BusLogic_GlobalOptions is a bit mask of Global Options to be applied
  7038.    across all Host Adapters.
  7039.  */
  7040. @@ -570,7 +579,7 @@
  7041.  
  7042.  static void BusLogic_InitializeAddressProbeList(void)
  7043.  {
  7044. -  int DestinationIndex = 0, SourceIndex = 0;
  7045. +  int ProbeAddressCount = 0, StandardAddressIndex = 0;
  7046.    /*
  7047.      If BusLogic_Setup has provided an I/O Address probe list, do not override
  7048.      the Kernel Command Line specifications.
  7049. @@ -601,31 +610,35 @@
  7050.          (BaseAddress0 & PCI_BASE_ADDRESS_SPACE) ==
  7051.            PCI_BASE_ADDRESS_SPACE_IO)
  7052.        {
  7053. -        BusLogic_IO_AddressProbeList[DestinationIndex] =
  7054. +        BusLogic_IO_AddressProbeList[ProbeAddressCount] =
  7055.            BaseAddress0 & PCI_BASE_ADDRESS_IO_MASK;
  7056. -        BusDeviceFunction[DestinationIndex] = (Bus << 8) | DeviceFunction;
  7057. -        if (DestinationIndex > 0 &&
  7058. -        BusDeviceFunction[DestinationIndex] <
  7059. -          BusDeviceFunction[DestinationIndex-1])
  7060. +        BusDeviceFunction[ProbeAddressCount] = (Bus << 8) | DeviceFunction;
  7061. +        if (ProbeAddressCount > 0 &&
  7062. +        BusDeviceFunction[ProbeAddressCount] <
  7063. +          BusDeviceFunction[ProbeAddressCount-1])
  7064.            NonIncreasingScanningOrder = true;
  7065. -        DestinationIndex++;
  7066. +        ProbeAddressCount++;
  7067.        }
  7068.        /*
  7069.      If there are multiple BusLogic PCI SCSI Host Adapters present and if
  7070.      they are enumerated by the PCI BIOS in an order other than by strictly
  7071.      increasing Bus Number and Device Number, then interrogate the setting
  7072.      of the AutoSCSI "Use Bus And Device # For PCI Scanning Seq." option.
  7073. -    If it is ON, sort the PCI Host Adapter I/O Addresses by increasing Bus
  7074. -    Number and Device Number so that the Host Adapters are recognized in
  7075. -    the same order by the Linux kernel as by the Host Adapter's BIOS.
  7076. +    If it is ON, and if the first enumeratedBusLogic Host Adapter is a
  7077. +    BT-948/958/958D, then sort the PCI Host Adapter I/O Addresses by
  7078. +    increasing Bus Number and Device Number so that the Host Adapters are
  7079. +    recognized in the same order by the Linux kernel as by the Host
  7080. +    Adapter's BIOS.
  7081.        */
  7082. -      if (DestinationIndex > 1 && NonIncreasingScanningOrder)
  7083. +      if (ProbeAddressCount > 1 && NonIncreasingScanningOrder &&
  7084. +      !(BusLogic_ProbeOptions & BusLogic_NoSortPCI))
  7085.      {
  7086. +      BusLogic_HostAdapter_T HostAdapterPrototype;
  7087. +      BusLogic_HostAdapter_T *HostAdapter = &HostAdapterPrototype;
  7088.        BusLogic_FetchHostAdapterLocalRAMRequest_T
  7089.          FetchHostAdapterLocalRAMRequest;
  7090.        BusLogic_AutoSCSIByte45_T AutoSCSIByte45;
  7091. -      BusLogic_HostAdapter_T HostAdapterPrototype;
  7092. -      BusLogic_HostAdapter_T *HostAdapter = &HostAdapterPrototype;
  7093. +      BusLogic_BoardID_T BoardID;
  7094.        HostAdapter->IO_Address = BusLogic_IO_AddressProbeList[0];
  7095.        FetchHostAdapterLocalRAMRequest.ByteOffset =
  7096.          BusLogic_AutoSCSI_BaseOffset + 45;
  7097. @@ -636,13 +649,18 @@
  7098.                 &FetchHostAdapterLocalRAMRequest,
  7099.                 sizeof(FetchHostAdapterLocalRAMRequest),
  7100.                 &AutoSCSIByte45, sizeof(AutoSCSIByte45));
  7101. -      if (AutoSCSIByte45.ForceBusDeviceScanningOrder)
  7102. +      BoardID.FirmwareVersion1stDigit = '\0';
  7103. +      BusLogic_Command(HostAdapter, BusLogic_InquireBoardID,
  7104. +               NULL, 0, &BoardID, sizeof(BoardID));
  7105. +      if (BoardID.FirmwareVersion1stDigit == '5' &&
  7106. +          AutoSCSIByte45.ForceBusDeviceScanningOrder)
  7107.          {
  7108.            /*
  7109. -        Sort the I/O Addresses such that the corresponding PCI devices
  7110. -        are in ascending order by Bus Number and Device Number.
  7111. +        Sort the I/O Addresses such that the corresponding
  7112. +        PCI devices are in ascending order by Bus Number and
  7113. +        Device Number.
  7114.            */
  7115. -          int LastInterchange = DestinationIndex-1, Bound, j;
  7116. +          int LastInterchange = ProbeAddressCount-1, Bound, j;
  7117.            while (LastInterchange > 0)
  7118.          {
  7119.            Bound = LastInterchange;
  7120. @@ -668,11 +686,12 @@
  7121.    /*
  7122.      Append the list of standard BusLogic ISA I/O Addresses.
  7123.    */
  7124. -  while (DestinationIndex < BusLogic_IO_MaxProbeAddresses &&
  7125. -     BusLogic_IO_StandardAddresses[SourceIndex] > 0)
  7126. -    BusLogic_IO_AddressProbeList[DestinationIndex++] =
  7127. -      BusLogic_IO_StandardAddresses[SourceIndex++];
  7128. -  BusLogic_IO_AddressProbeList[DestinationIndex] = 0;
  7129. +  if (!(BusLogic_ProbeOptions & BusLogic_NoProbeISA))
  7130. +    while (ProbeAddressCount < BusLogic_IO_MaxProbeAddresses &&
  7131. +       BusLogic_IO_StandardAddresses[StandardAddressIndex] > 0)
  7132. +      BusLogic_IO_AddressProbeList[ProbeAddressCount++] =
  7133. +    BusLogic_IO_StandardAddresses[StandardAddressIndex++];
  7134. +  BusLogic_IO_AddressProbeList[ProbeAddressCount] = 0;
  7135.  }
  7136.  
  7137.  
  7138. @@ -1871,6 +1890,7 @@
  7139.  {
  7140.    int BusLogicHostAdapterCount = 0, CommandLineEntryIndex = 0;
  7141.    int AddressProbeIndex = 0;
  7142. +  if (BusLogic_ProbeOptions & BusLogic_NoProbe) return 0;
  7143.    BusLogic_InitializeAddressProbeList();
  7144.    while (BusLogic_IO_AddressProbeList[AddressProbeIndex] > 0)
  7145.      {
  7146. @@ -2851,6 +2871,12 @@
  7147.        Result = SCSI_RESET_PENDING;
  7148.        goto Done;
  7149.      }
  7150. +      else if (HostAdapter->BusDeviceResetPendingCCB[TargetID] != NULL)
  7151. +    {
  7152. +      printk("scsi%d: Bus Device Reset already pending to Target %d\n",
  7153. +         HostAdapter->HostNumber, TargetID);
  7154. +      goto Done;
  7155. +    }
  7156.      }
  7157.    /*
  7158.      If this is a Synchronous Reset and a Bus Device Reset is already pending
  7159. @@ -2863,6 +2889,8 @@
  7160.        {
  7161.      Command->reset_chain = CCB->Command;
  7162.      CCB->Command = Command;
  7163. +    printk("scsi%d: Unable to Reset Command to Target %d - "
  7164. +           "Reset Pending\n", HostAdapter->HostNumber, TargetID);
  7165.      Result = SCSI_RESET_PENDING;
  7166.      goto Done;
  7167.        }
  7168. @@ -3139,9 +3167,8 @@
  7169.    defaults to 0.  Note that Global Options are applied across all Host
  7170.    Adapters.
  7171.  
  7172. -  The string options are used to provide control over Tagged Queuing and Error
  7173. -  Recovery. If both Tagged Queuing and Error Recovery strings are provided, the
  7174. -  Tagged Queuing specification string must come first.
  7175. +  The string options are used to provide control over Tagged Queuing, Error
  7176. +  Recovery, and Host Adapter Probing.
  7177.  
  7178.    The Tagged Queuing specification begins with "TQ:" and allows for explicitly
  7179.    specifying whether Tagged Queuing is permitted on Target Devices that support
  7180. @@ -3207,6 +3234,20 @@
  7181.              the sequence of "D", "H", "B", and "N" characters does
  7182.              not cover all the possible Target Devices, unspecified
  7183.              characters are assumed to be "D".
  7184. +
  7185. +  The Host Adapter Probing specification comprises the following strings:
  7186. +
  7187. +  NoProbe        No probing of any kind is to be performed, and hence
  7188. +            no BusLogic Host Adapters will be detected.
  7189. +
  7190. +  NoProbeISA        No probing of the standard ISA I/O Addresses will
  7191. +            be done, and hence only PCI Host Adapters will be
  7192. +            detected.
  7193. +
  7194. +  NoSortPCI        PCI Host Adapters will be enumerated in the order
  7195. +            provided by the PCI BIOS, ignoring any setting of
  7196. +            the AutoSCSI "Use Bus And Device # For PCI Scanning
  7197. +            Seq." option.
  7198.  */
  7199.  
  7200.  void BusLogic_Setup(char *Strings, int *Integers)
  7201. @@ -3277,97 +3318,120 @@
  7202.        return;
  7203.      }
  7204.    if (Strings == NULL) return;
  7205. -  if (strncmp(Strings, "TQ:", 3) == 0)
  7206. +  while (*Strings != '\0')
  7207.      {
  7208. -      Strings += 3;
  7209. -      if (strncmp(Strings, "Default", 7) == 0)
  7210. -    Strings += 7;
  7211. -      else if (strncmp(Strings, "Enable", 6) == 0)
  7212. -    {
  7213. -      Strings += 6;
  7214. -      CommandLineEntry->TaggedQueuingPermitted = 0xFFFF;
  7215. -      CommandLineEntry->TaggedQueuingPermittedMask = 0xFFFF;
  7216. -    }
  7217. -      else if (strncmp(Strings, "Disable", 7) == 0)
  7218. +      if (strncmp(Strings, "TQ:", 3) == 0)
  7219.      {
  7220. -      Strings += 7;
  7221. -      CommandLineEntry->TaggedQueuingPermitted = 0x0000;
  7222. -      CommandLineEntry->TaggedQueuingPermittedMask = 0xFFFF;
  7223. +      Strings += 3;
  7224. +      if (strncmp(Strings, "Default", 7) == 0)
  7225. +        Strings += 7;
  7226. +      else if (strncmp(Strings, "Enable", 6) == 0)
  7227. +        {
  7228. +          Strings += 6;
  7229. +          CommandLineEntry->TaggedQueuingPermitted = 0xFFFF;
  7230. +          CommandLineEntry->TaggedQueuingPermittedMask = 0xFFFF;
  7231. +        }
  7232. +      else if (strncmp(Strings, "Disable", 7) == 0)
  7233. +        {
  7234. +          Strings += 7;
  7235. +          CommandLineEntry->TaggedQueuingPermitted = 0x0000;
  7236. +          CommandLineEntry->TaggedQueuingPermittedMask = 0xFFFF;
  7237. +        }
  7238. +      else
  7239. +        for (TargetID = 0; TargetID < BusLogic_MaxTargetDevices; TargetID++)
  7240. +          switch (*Strings++)
  7241. +        {
  7242. +        case 'Y':
  7243. +          CommandLineEntry->TaggedQueuingPermitted |= 1 << TargetID;
  7244. +          CommandLineEntry->TaggedQueuingPermittedMask |= 1 << TargetID;
  7245. +          break;
  7246. +        case 'N':
  7247. +          CommandLineEntry->TaggedQueuingPermittedMask |= 1 << TargetID;
  7248. +          break;
  7249. +        case 'X':
  7250. +          break;
  7251. +        default:
  7252. +          Strings--;
  7253. +          TargetID = BusLogic_MaxTargetDevices;
  7254. +          break;
  7255. +        }
  7256.      }
  7257. -      else
  7258. -    for (TargetID = 0; TargetID < BusLogic_MaxTargetDevices; TargetID++)
  7259. -      switch (*Strings++)
  7260. +      else if (strncmp(Strings, "ER:", 3) == 0)
  7261. +    {
  7262. +      Strings += 3;
  7263. +      if (strncmp(Strings, "Default", 7) == 0)
  7264. +        Strings += 7;
  7265. +      else if (strncmp(Strings, "HardReset", 9) == 0)
  7266.          {
  7267. -        case 'Y':
  7268. -          CommandLineEntry->TaggedQueuingPermitted |= 1 << TargetID;
  7269. -          CommandLineEntry->TaggedQueuingPermittedMask |= 1 << TargetID;
  7270. -          break;
  7271. -        case 'N':
  7272. -          CommandLineEntry->TaggedQueuingPermittedMask |= 1 << TargetID;
  7273. -          break;
  7274. -        case 'X':
  7275. -          break;
  7276. -        default:
  7277. -          Strings--;
  7278. -          TargetID = BusLogic_MaxTargetDevices;
  7279. -          break;
  7280. +          Strings += 9;
  7281. +          memset(CommandLineEntry->ErrorRecoveryStrategy,
  7282. +             BusLogic_ErrorRecovery_HardReset,
  7283. +             sizeof(CommandLineEntry->ErrorRecoveryStrategy));
  7284.          }
  7285. -    }
  7286. -  if (*Strings == ',') Strings++;
  7287. -  if (strncmp(Strings, "ER:", 3) == 0)
  7288. -    {
  7289. -      Strings += 3;
  7290. -      if (strncmp(Strings, "Default", 7) == 0)
  7291. -    Strings += 7;
  7292. -      else if (strncmp(Strings, "HardReset", 9) == 0)
  7293. +      else if (strncmp(Strings, "BusDeviceReset", 14) == 0)
  7294. +        {
  7295. +          Strings += 14;
  7296. +          memset(CommandLineEntry->ErrorRecoveryStrategy,
  7297. +             BusLogic_ErrorRecovery_BusDeviceReset,
  7298. +             sizeof(CommandLineEntry->ErrorRecoveryStrategy));
  7299. +        }
  7300. +      else if (strncmp(Strings, "None", 4) == 0)
  7301. +        {
  7302. +          Strings += 4;
  7303. +          memset(CommandLineEntry->ErrorRecoveryStrategy,
  7304. +             BusLogic_ErrorRecovery_None,
  7305. +             sizeof(CommandLineEntry->ErrorRecoveryStrategy));
  7306. +        }
  7307. +      else
  7308. +        for (TargetID = 0; TargetID < BusLogic_MaxTargetDevices; TargetID++)
  7309. +          switch (*Strings++)
  7310. +        {
  7311. +        case 'D':
  7312. +          CommandLineEntry->ErrorRecoveryStrategy[TargetID] =
  7313. +            BusLogic_ErrorRecovery_Default;
  7314. +          break;
  7315. +        case 'H':
  7316. +          CommandLineEntry->ErrorRecoveryStrategy[TargetID] =
  7317. +            BusLogic_ErrorRecovery_HardReset;
  7318. +          break;
  7319. +        case 'B':
  7320. +          CommandLineEntry->ErrorRecoveryStrategy[TargetID] =
  7321. +            BusLogic_ErrorRecovery_BusDeviceReset;
  7322. +          break;
  7323. +        case 'N':
  7324. +          CommandLineEntry->ErrorRecoveryStrategy[TargetID] =
  7325. +            BusLogic_ErrorRecovery_None;
  7326. +          break;
  7327. +        default:
  7328. +          Strings--;
  7329. +          TargetID = BusLogic_MaxTargetDevices;
  7330. +          break;
  7331. +        }
  7332. +    }
  7333. +      else if (strcmp(Strings, "NoProbe") == 0 ||
  7334. +           strcmp(Strings, "noprobe") == 0)
  7335. +    {
  7336. +      Strings += 7;
  7337. +      BusLogic_ProbeOptions |= BusLogic_NoProbe;
  7338. +    }
  7339. +      else if (strncmp(Strings, "NoProbeISA", 10) == 0)
  7340. +    {
  7341. +      Strings += 10;
  7342. +      BusLogic_ProbeOptions |= BusLogic_NoProbeISA;
  7343. +    }
  7344. +      else if (strncmp(Strings, "NoSortPCI", 9) == 0)
  7345.      {
  7346.        Strings += 9;
  7347. -      memset(CommandLineEntry->ErrorRecoveryStrategy,
  7348. -         BusLogic_ErrorRecovery_HardReset,
  7349. -         sizeof(CommandLineEntry->ErrorRecoveryStrategy));
  7350. -    }
  7351. -      else if (strncmp(Strings, "BusDeviceReset", 14) == 0)
  7352. -    {
  7353. -      Strings += 14;
  7354. -      memset(CommandLineEntry->ErrorRecoveryStrategy,
  7355. -         BusLogic_ErrorRecovery_BusDeviceReset,
  7356. -         sizeof(CommandLineEntry->ErrorRecoveryStrategy));
  7357. -    }
  7358. -      else if (strncmp(Strings, "None", 4) == 0)
  7359. -    {
  7360. -      Strings += 4;
  7361. -      memset(CommandLineEntry->ErrorRecoveryStrategy,
  7362. -         BusLogic_ErrorRecovery_None,
  7363. -         sizeof(CommandLineEntry->ErrorRecoveryStrategy));
  7364. +      BusLogic_ProbeOptions |= BusLogic_NoSortPCI;
  7365.      }
  7366.        else
  7367. -    for (TargetID = 0; TargetID < BusLogic_MaxTargetDevices; TargetID++)
  7368. -      switch (*Strings++)
  7369. -        {
  7370. -        case 'D':
  7371. -          CommandLineEntry->ErrorRecoveryStrategy[TargetID] =
  7372. -        BusLogic_ErrorRecovery_Default;
  7373. -          break;
  7374. -        case 'H':
  7375. -          CommandLineEntry->ErrorRecoveryStrategy[TargetID] =
  7376. -        BusLogic_ErrorRecovery_HardReset;
  7377. -          break;
  7378. -        case 'B':
  7379. -          CommandLineEntry->ErrorRecoveryStrategy[TargetID] =
  7380. -        BusLogic_ErrorRecovery_BusDeviceReset;
  7381. -          break;
  7382. -        case 'N':
  7383. -          CommandLineEntry->ErrorRecoveryStrategy[TargetID] =
  7384. -        BusLogic_ErrorRecovery_None;
  7385. -          break;
  7386. -        default:
  7387. -          Strings--;
  7388. -          TargetID = BusLogic_MaxTargetDevices;
  7389. -          break;
  7390. -        }
  7391. +    {
  7392. +      printk("BusLogic: Unexpected Command Line String '%s' ignored\n",
  7393. +         Strings);
  7394. +      break;
  7395. +    }
  7396. +      if (*Strings == ',') Strings++;
  7397.      }
  7398. -  if (*Strings != '\0')
  7399. -    printk("BusLogic: Unexpected Command Line String '%s' ignored\n", Strings);
  7400.  }
  7401.  
  7402.  
  7403. diff -u --recursive --new-file pre2.0.4/linux/drivers/scsi/BusLogic.h linux/drivers/scsi/BusLogic.h
  7404. --- pre2.0.4/linux/drivers/scsi/BusLogic.h    Mon Apr 15 12:20:19 1996
  7405. +++ linux/drivers/scsi/BusLogic.h    Fri May 17 10:02:01 1996
  7406. @@ -147,6 +147,15 @@
  7407.  
  7408.  
  7409.  /*
  7410. +  Define the possible Probe Options.
  7411. +*/
  7412. +
  7413. +#define BusLogic_NoProbe            1
  7414. +#define BusLogic_NoProbeISA            2
  7415. +#define BusLogic_NoSortPCI            4
  7416. +
  7417. +
  7418. +/*
  7419.    Define the possible Global Options.
  7420.  */
  7421.  
  7422. diff -u --recursive --new-file pre2.0.4/linux/drivers/scsi/ChangeLog linux/drivers/scsi/ChangeLog
  7423. --- pre2.0.4/linux/drivers/scsi/ChangeLog    Tue May  7 16:22:32 1996
  7424. +++ linux/drivers/scsi/ChangeLog    Fri May 17 10:50:58 1996
  7425. @@ -1,3 +1,7 @@
  7426. +Fri May 17 00:00:00 1996  Leonard N. Zubkoff <lnz@dandelion.com>
  7427. +
  7428. +    * BusLogic Driver Version 2.0.3 Released.
  7429. +
  7430.  Tue Apr 16 21:00:00 1996  Leonard N. Zubkoff <lnz@dandelion.com>
  7431.  
  7432.      * BusLogic Driver Version 1.3.2 Released.
  7433. diff -u --recursive --new-file pre2.0.4/linux/drivers/scsi/README.BusLogic linux/drivers/scsi/README.BusLogic
  7434. --- pre2.0.4/linux/drivers/scsi/README.BusLogic    Fri Apr 19 10:07:59 1996
  7435. +++ linux/drivers/scsi/README.BusLogic    Fri May 17 10:02:01 1996
  7436. @@ -1,9 +1,9 @@
  7437.            BusLogic MultiMaster SCSI Driver for Linux
  7438.  
  7439. -               Version 1.2.2 for Linux 1.2.13
  7440. -               Version 1.3.2 for Linux 1.3.88
  7441. +               Version 1.2.3 for Linux 1.2.13
  7442. +               Version 2.0.3 for Linux 2.0.0
  7443.  
  7444. -                 16 April 1996
  7445. +                  17 May 1996
  7446.  
  7447.                     Leonard N. Zubkoff
  7448.                     Dandelion Digital
  7449. @@ -114,7 +114,7 @@
  7450.    level parts of the SCSI subsystem request that a command be reset, action is
  7451.    taken to restore proper operation of the host adapter and SCSI bus.  On Linux
  7452.    1.2.13, by default a full host adapter hard reset and SCSI bus reset is
  7453. -  performed.  On Linux 1.3.x, by default a selection is made between a full
  7454. +  performed.  On Linux 2.0.x, by default a selection is made between a full
  7455.    host adapter hard reset and SCSI bus reset versus sending a bus device reset
  7456.    message to the individual target device based on the recommendation of the
  7457.    SCSI subsystem.  Error recovery strategies are selectable from the kernel
  7458. @@ -167,7 +167,7 @@
  7459.    All BusLogic MultiMaster SCSI Host Adapters share a common programming
  7460.    interface, except for the inevitable improvements and extensions as new
  7461.    models are released, so support for Wide SCSI data transfer has automatically
  7462. -  been available without explicit driver support.  When used with Linux 1.3.x,
  7463. +  been available without explicit driver support.  When used with Linux 2.0.x,
  7464.    this driver adds explicit support for up to 15 target devices and 64 logical
  7465.    units per target device, to fully exploit the capabilities of the newest
  7466.    BusLogic Wide SCSI Host Adapters.
  7467. @@ -299,12 +299,14 @@
  7468.      such as disk drives, but should not be disabled for tape drives or other
  7469.      devices where a single command may take over a second to execute.
  7470.  
  7471. -  "BusLogic=0,0,10"
  7472. +  "BusLogic=0,0,30"
  7473.  
  7474.      This command line selects default probing and automatic tagged queue depth
  7475. -    selection, but changes the bus settle time to 10 seconds.  It may be useful
  7476. +    selection, but changes the bus settle time to 30 seconds.  It may be useful
  7477.      with SCSI devices that take an unusually long time to become ready to
  7478. -    accept commands after a SCSI bus reset.
  7479. +    accept commands after a SCSI bus reset.  Some tape drives will not respond
  7480. +    properly immediately after a SCSI bus reset, especially if a tape is
  7481. +    present in the drive.
  7482.  
  7483.    "BusLogic=TQ:Disable"
  7484.  
  7485. @@ -323,19 +325,20 @@
  7486.                   INSTALLATION
  7487.  
  7488.  This distribution was prepared for Linux kernel version 1.2.13
  7489. -(BusLogic-1.2.2.tar.gz) or Linux kernel version 1.3.88 (BusLogic-1.3.2.tar.gz).
  7490. +(BusLogic-1.2.3.tar.gz) or Linux kernel version 2.0.0 (BusLogic-2.0.3.tar.gz).
  7491.  Installation in later versions will probably be successful as well, though
  7492.  BusLogic.patch may not be required.  Installation in earlier versions is not
  7493.  recommended.
  7494.  
  7495.  To install the BusLogic SCSI driver, you may use the following commands,
  7496.  replacing "/usr/src" with wherever you keep your Linux kernel source tree
  7497. -(substitute '2' or '3' for 'x' in the tar command as appropriate):
  7498. +(substitute "1.2" or "2.0" for "x.y" in the tar command as appropriate):
  7499.  
  7500.    cd /usr/src
  7501. -  tar -xvzf BusLogic-1.x.2.tar.gz
  7502. +  tar -xvzf BusLogic-x.y.3.tar.gz
  7503.    mv README.* BusLogic.[ch] linux/drivers/scsi
  7504. -  patch -p < BusLogic.patch
  7505. +  patch -p < BusLogic.patch        (on Linux 1.2.13 only)
  7506. +  patch -p < BusLogic.elf_patch        (on Linux 1.2.13 ELF systems only)
  7507.    cd linux
  7508.    make config
  7509.    make depend
  7510. diff -u --recursive --new-file pre2.0.4/linux/drivers/scsi/aha152x.c linux/drivers/scsi/aha152x.c
  7511. --- pre2.0.4/linux/drivers/scsi/aha152x.c    Sat May 11 10:42:05 1996
  7512. +++ linux/drivers/scsi/aha152x.c    Thu May 16 16:38:16 1996
  7513. @@ -1830,6 +1830,13 @@
  7514.  #endif
  7515.            break;
  7516.  
  7517. +        case RESTORE_POINTERS:
  7518. +#if defined(DEBUG_MSGI)
  7519. +        if(HOSTDATA(shpnt)->debug & debug_msgi)
  7520. +          printk("inbound message (RESTORE DATA POINTERS), ");
  7521. +#endif
  7522. +          break;
  7523. +
  7524.          case EXTENDED_MESSAGE:
  7525.            { 
  7526.                char buffer[16];
  7527. diff -u --recursive --new-file pre2.0.4/linux/drivers/scsi/atari_NCR5380.c linux/drivers/scsi/atari_NCR5380.c
  7528. --- pre2.0.4/linux/drivers/scsi/atari_NCR5380.c    Sat Apr 27 15:19:56 1996
  7529. +++ linux/drivers/scsi/atari_NCR5380.c    Thu May 16 09:05:11 1996
  7530. @@ -53,65 +53,25 @@
  7531.   *    Since most scatter-gather operations work on a page (4K) of
  7532.   *    4 buffers (1K), in more than 90% of all cases three interrupts and
  7533.   *    DMA setup actions are saved.
  7534. - * 
  7535. - */
  7536. -
  7537. -/*
  7538. - * +++roman: I've deleted all the stuff for AUTOPROBE_IRQ, REAL_DMA_POLL,
  7539. - * PSEUDO_DMA and USLEEP, because these were messing up
  7540. - * readability and will never be needed for Atari SCSI.
  7541. - */
  7542. -
  7543. -
  7544. -/*
  7545. - * $Log: atari_NCR5380.c,v $
  7546. - * Revision 1.2  1996/04/04 13:30:22  root
  7547. - * interrupts more like the pc
  7548. - *
  7549. - * Revision 1.1  1996/03/20 17:51:35  root
  7550. - * Initial revision
  7551. - *
  7552. - * Revision 1.2  1994/11/26  03:38:32  hamish
  7553. - * v0.9pl4
  7554.   *
  7555. - * Revision 1.1  1994/11/08  03:25:43  hamish
  7556. - * Initial revision
  7557. - *
  7558. - * Revision 1.5  1994/01/19  09:14:57  drew
  7559. - * Fixed udelay() hack that was being used on DATAOUT phases
  7560. - * instead of a proper wait for the final handshake.
  7561. - *
  7562. - * Revision 1.4  1994/01/19  06:44:25  drew
  7563. - * *** empty log message ***
  7564. - *
  7565. - * Revision 1.3  1994/01/19  05:24:40  drew
  7566. - * Added support for TCR LAST_BYTE_SENT bit.
  7567. - *
  7568. - * Revision 1.2  1994/01/15  06:14:11  drew
  7569. - * REAL DMA support, bug fixes.
  7570. - *
  7571. - * Revision 1.1  1994/01/15  06:00:54  drew
  7572. - * Initial revision
  7573. + * - I've deleted all the stuff for AUTOPROBE_IRQ, REAL_DMA_POLL, PSEUDO_DMA
  7574. + *    and USLEEP, because these were messing up readability and will never be
  7575. + *    needed for Atari SCSI.
  7576. + * 
  7577. + * - I've revised the NCR5380_main() calling scheme (relax the 'main_running'
  7578. + *   stuff), and 'main' is executed in a bottom half if awoken by an
  7579. + *   interrupt.
  7580. + *
  7581. + * - The code was quite cluttered up by "#if (NDEBUG & NDEBUG_*) printk..."
  7582. + *   constructs. In my eyes, this made the source rather unreadable, so I
  7583. + *   finally replaced that by the *_PRINTK() macros.
  7584.   *
  7585.   */
  7586.  
  7587.  /*
  7588.   * Further development / testing that should be done : 
  7589. - * 1.  Cleanup the NCR5380_transfer_dma function and DMA operation complete
  7590. - *     code so that everything does the same thing that's done at the 
  7591. - *     end of a pseudo-DMA read operation.
  7592. - *
  7593. - * 2.  Fix REAL_DMA (interrupt driven, polled works fine) -
  7594. - *     basically, transfer size needs to be reduced by one 
  7595. - *     and the last byte read as is done with PSEUDO_DMA.
  7596. - * 
  7597. - * 3.  Test USLEEP code 
  7598. - *
  7599. - * 4.  Test SCSI-II tagged queueing (I have no devices which support 
  7600. - *    tagged queueing)
  7601. - *
  7602. - * 5.  Test linked command handling code after Eric is ready with 
  7603. - *      the high level code.
  7604. + * 1.  Test linked command handling code after Eric is ready with 
  7605. + *     the high level code.
  7606.   */
  7607.  
  7608.  #if (NDEBUG & NDEBUG_LISTS)
  7609. @@ -404,10 +364,8 @@
  7610.      return( 0 );
  7611.      if (TagAlloc[cmd->target][cmd->lun].nr_allocated >=
  7612.      TagAlloc[cmd->target][cmd->lun].queue_size ) {
  7613. -#if (NDEBUG & NDEBUG_TAGS)
  7614. -    printk( "scsi%d: target %d lun %d: no free tags\n",
  7615. -        H_NO(cmd), cmd->target, cmd->lun );
  7616. -#endif
  7617. +    TAG_PRINTK( "scsi%d: target %d lun %d: no free tags\n",
  7618. +            H_NO(cmd), cmd->target, cmd->lun );
  7619.      return( 1 );
  7620.      }
  7621.      return( 0 );
  7622. @@ -430,10 +388,8 @@
  7623.      !setup_use_tagged_queuing || !cmd->device->tagged_supported) {
  7624.      cmd->tag = TAG_NONE;
  7625.      hostdata->busy[cmd->target] |= (1 << cmd->lun);
  7626. -#if (NDEBUG & NDEBUG_TAGS)
  7627. -    printk( "scsi%d: target %d lun %d now allocated by untagged command\n",
  7628. -        H_NO(cmd), cmd->target, cmd->lun );
  7629. -#endif
  7630. +    TAG_PRINTK( "scsi%d: target %d lun %d now allocated by untagged "
  7631. +            "command\n", H_NO(cmd), cmd->target, cmd->lun );
  7632.      }
  7633.      else {
  7634.      TAG_ALLOC *ta = &TagAlloc[cmd->target][cmd->lun];
  7635. @@ -441,12 +397,10 @@
  7636.      cmd->tag = find_first_zero_bit( &ta->allocated, MAX_TAGS );
  7637.      set_bit( cmd->tag, &ta->allocated );
  7638.      ta->nr_allocated++;
  7639. -#if (NDEBUG & NDEBUG_TAGS)
  7640. -    printk( "scsi%d: using tag %d for target %d lun %d "
  7641. -        "(now %d tags in use)\n",
  7642. -        H_NO(cmd), cmd->tag, cmd->target, cmd->lun,
  7643. -        ta->nr_allocated );
  7644. -#endif
  7645. +    TAG_PRINTK( "scsi%d: using tag %d for target %d lun %d "
  7646. +            "(now %d tags in use)\n",
  7647. +            H_NO(cmd), cmd->tag, cmd->target, cmd->lun,
  7648. +            ta->nr_allocated );
  7649.      }
  7650.  }
  7651.  
  7652. @@ -461,28 +415,24 @@
  7653.  
  7654.      if (cmd->tag == TAG_NONE) {
  7655.      hostdata->busy[cmd->target] &= ~(1 << cmd->lun);
  7656. -#if (NDEBUG & NDEBUG_TAGS)
  7657. -    printk( "scsi%d: target %d lun %d untagged cmd finished\n",
  7658. -        H_NO(cmd), cmd->target, cmd->lun );
  7659. -#endif
  7660. +    TAG_PRINTK( "scsi%d: target %d lun %d untagged cmd finished\n",
  7661. +            H_NO(cmd), cmd->target, cmd->lun );
  7662.      }
  7663.      else if (cmd->tag >= MAX_TAGS) {
  7664. -    printk( "scsi%d: trying to free bad tag %d!\n",
  7665. +    printk(KERN_NOTICE "scsi%d: trying to free bad tag %d!\n",
  7666.          H_NO(cmd), cmd->tag );
  7667.      }
  7668.      else {
  7669.      TAG_ALLOC *ta = &TagAlloc[cmd->target][cmd->lun];
  7670.      clear_bit( cmd->tag, &ta->allocated );
  7671.      ta->nr_allocated--;
  7672. -#if (NDEBUG & NDEBUG_TAGS)
  7673. -    printk( "scsi%d: freed tag %d for target %d lun %d\n",
  7674. -        H_NO(cmd), cmd->tag, cmd->target, cmd->lun );
  7675. -#endif
  7676. +    TAG_PRINTK( "scsi%d: freed tag %d for target %d lun %d\n",
  7677. +            H_NO(cmd), cmd->tag, cmd->target, cmd->lun );
  7678.      }
  7679.  }
  7680.  
  7681.  
  7682. -#if 0
  7683. +#if 1
  7684.  static void free_all_tags( void )
  7685.  {
  7686.      int target, lun;
  7687. @@ -537,9 +487,9 @@
  7688.       cmd->SCp.buffers_residual &&
  7689.       VTOP( (cmd->SCp.buffer+1)->address ) == endadr + 1; ) {
  7690.      
  7691. +    MER_PRINTK( "%08lx == %08lx -> merging\n",
  7692. +            VTOP( (cmd->SCp.buffer+1)->address ), endadr );
  7693.  #if (NDEBUG & NDEBUG_MERGING)
  7694. -    printk( "%08lx == %08lx -> merging\n",
  7695. -        VTOP( (cmd->SCp.buffer+1)->address ), endadr );
  7696.      ++cnt;
  7697.  #endif
  7698.      ++cmd->SCp.buffer;
  7699. @@ -549,8 +499,8 @@
  7700.      }
  7701.  #if (NDEBUG & NDEBUG_MERGING)
  7702.      if (oldlen != cmd->SCp.this_residual)
  7703. -    printk( "merged %d buffers from %08lx, new length %08lx\n",
  7704. -        cnt, (long)(cmd->SCp.ptr), cmd->SCp.this_residual );
  7705. +    MER_PRINTK( "merged %d buffers from %08lx, new length %08lx\n",
  7706. +            cnt, (long)(cmd->SCp.ptr), cmd->SCp.this_residual );
  7707.  #endif
  7708.  }
  7709.  
  7710. @@ -590,7 +540,7 @@
  7711.  #include <linux/config.h>
  7712.  #include <linux/delay.h>
  7713.  
  7714. -#ifdef NDEBUG
  7715. +#if NDEBUG
  7716.  static struct {
  7717.      unsigned char mask;
  7718.      const char * name;} 
  7719. @@ -671,63 +621,58 @@
  7720.  
  7721.      status = NCR5380_read(STATUS_REG);
  7722.      if (!(status & SR_REQ)) 
  7723. -    printk("scsi%d: REQ not asserted, phase unknown.\n", HOSTNO);
  7724. +    printk(KERN_DEBUG "scsi%d: REQ not asserted, phase unknown.\n", HOSTNO);
  7725.      else {
  7726.      for (i = 0; (phases[i].value != PHASE_UNKNOWN) && 
  7727.          (phases[i].value != (status & PHASE_MASK)); ++i); 
  7728. -    printk("scsi%d: phase %s\n", HOSTNO, phases[i].name);
  7729. +    printk(KERN_DEBUG "scsi%d: phase %s\n", HOSTNO, phases[i].name);
  7730.      }
  7731.  }
  7732. -#endif
  7733.  
  7734. -/*
  7735. - * We need to have our coroutine active given these constraints : 
  7736. - * 1.  The mutex flag, main_running, can only be set when the main 
  7737. - *     routine can actually process data, otherwise SCSI commands
  7738. - *     will never get issued.
  7739. - *
  7740. - * 2.  NCR5380_main() shouldn't be called before it has exited, because
  7741. - *     other drivers have had kernel stack overflows in similar
  7742. - *     situations.
  7743. - *
  7744. - * 3.  We don't want to inline NCR5380_main() because of space concerns,
  7745. - *     even though it is only called in two places.
  7746. - *
  7747. - * So, the solution is to set the mutex in an inline wrapper for the 
  7748. - * main coroutine, and have the main coroutine exit with interrupts 
  7749. - * disabled after the final search through the queues so that no race 
  7750. - * conditions are possible.
  7751. - */
  7752. +#else /* !NDEBUG */
  7753.  
  7754. -static volatile int main_running = 0;
  7755. +/* dummys... */
  7756. +__inline__ void NCR5380_print(struct Scsi_Host *instance) { };
  7757. +__inline__ void NCR5380_print_phase(struct Scsi_Host *instance) { };
  7758.  
  7759. -/* 
  7760. - * Function : run_main(void)
  7761. +#endif
  7762. +
  7763. +/*
  7764. + * ++roman: New scheme of calling NCR5380_main()
  7765.   * 
  7766. - * Purpose : insure that the coroutine is running and will process our 
  7767. - *     request.  main_running is checked/set here (in an inline function)
  7768. - *    rather than in NCR5380_main itself to reduce the chances of stack
  7769. - *    overflow.
  7770. - *
  7771. + * If we're not in an interrupt, we can call our main directly, it cannot be
  7772. + * already running. Else, we queue it on a task queue, if not 'main_running'
  7773. + * tells us that a lower level is already executing it. This way,
  7774. + * 'main_running' needs not be protected in a special way.
  7775. + *
  7776. + * queue_main() is a utility function for putting our main onto the task
  7777. + * queue, if main_running is false. It should be called only from a
  7778. + * interrupt or bottom half.
  7779.   */
  7780.  
  7781. -static void NCR5380_main_a ( unsigned long flags );
  7782. +#include <linux/tqueue.h>
  7783. +#include <linux/interrupt.h>
  7784.  
  7785. -static __inline__ void run_main(void)
  7786. -{
  7787. -    unsigned long flags;
  7788. +static volatile int main_running = 0;
  7789. +static struct tq_struct NCR5380_tqueue = {
  7790. +    NULL,        /* next */
  7791. +    0,            /* sync */
  7792. +    (void (*)(void*))NCR5380_main,  /* routine, must have (void *) arg... */
  7793. +    NULL        /* data */
  7794. +};
  7795.  
  7796. -    save_flags(flags);
  7797. -    cli();
  7798. +static __inline__ void queue_main(void)
  7799. +{
  7800.      if (!main_running) {
  7801. -    main_running = 1;
  7802. -        NCR5380_main_a( flags );
  7803. -    /* 
  7804. -         * main_running is cleared in NCR5380_main once it can't do 
  7805. -     * more work, and NCR5380_main exits with interrupts disabled.
  7806. -     */
  7807. +    /* If in interrupt and NCR5380_main() not already running,
  7808. +       queue it on the 'immediate' task queue, to be processed
  7809. +       immediately after the current interrupt processing has
  7810. +       finished. */
  7811. +    queue_task_irq(&NCR5380_tqueue, &tq_immediate);
  7812. +    mark_bh(IMMEDIATE_BH);
  7813.      }
  7814. -    restore_flags(flags);
  7815. +    /* else: nothing to do: the running NCR5380_main() will pick up
  7816. +       any newly queued command. */
  7817.  }
  7818.  
  7819.  
  7820. @@ -735,9 +680,7 @@
  7821.  {
  7822.      static int done = 0;
  7823.      if (!done) {
  7824. -#if (NDEBUG & NDEBUG_INIT)
  7825. -    printk("scsi : NCR5380_all_init()\n");
  7826. -#endif
  7827. +    INI_PRINTK("scsi : NCR5380_all_init()\n");
  7828.      done = 1;
  7829.      }
  7830.  }
  7831. @@ -786,13 +729,8 @@
  7832.      char *start;
  7833.      int len;
  7834.  
  7835. -    printk("NCR5380: coroutine is%s running.\n",
  7836. -    main_running ? "" : "n't");
  7837. -    
  7838. -#ifdef NDEBUG
  7839. -    NCR5380_print (instance);
  7840. -    NCR5380_print_phase (instance);
  7841. -#endif
  7842. +    NCR_PRINT(NDEBUG_ANY);
  7843. +    NCR_PRINT_PHASE(NDEBUG_ANY);
  7844.  
  7845.      len = NCR5380_proc_info(pr_bfr, &start, 0, sizeof(pr_bfr), HOSTNO, 0);
  7846.      pr_bfr[len] = 0;
  7847. @@ -993,7 +931,7 @@
  7848.      switch (cmd->cmnd[0]) {
  7849.      case WRITE_6:
  7850.      case WRITE_10:
  7851. -    printk("scsi%d: WRITE attempted with NO_WRITE debugging flag set\n",
  7852. +    printk(KERN_NOTICE "scsi%d: WRITE attempted with NO_WRITE debugging flag set\n",
  7853.             H_NO(cmd));
  7854.      cmd->result = (DID_ERROR << 16);
  7855.      done(cmd);
  7856. @@ -1081,13 +1019,20 @@
  7857.      }
  7858.      restore_flags(flags);
  7859.  
  7860. -#if (NDEBUG & NDEBUG_QUEUES)
  7861. -    printk("scsi%d: command added to %s of queue\n", H_NO(cmd),
  7862. -    (cmd->cmnd[0] == REQUEST_SENSE) ? "head" : "tail");
  7863. -#endif
  7864. +    QU_PRINTK("scsi%d: command added to %s of queue\n", H_NO(cmd),
  7865. +          (cmd->cmnd[0] == REQUEST_SENSE) ? "head" : "tail");
  7866.  
  7867. -/* Run the coroutine if it isn't already running. */
  7868. -    run_main();
  7869. +    /* If queue_command() is called from an interrupt (real one or bottom
  7870. +     * half), we let queue_main() do the job of taking care about main. If it
  7871. +     * is already running, this is a no-op, else main will be queued.
  7872. +     *
  7873. +     * If we're not in an interrupt, we can call NCR5380_main()
  7874. +     * unconditionally, because it cannot be already running.
  7875. +     */
  7876. +    if (intr_count > 0)
  7877. +    queue_main();
  7878. +    else
  7879. +    NCR5380_main();
  7880.      return 0;
  7881.  }
  7882.  
  7883. @@ -1103,14 +1048,13 @@
  7884.   *  reenable them.  This prevents reentrancy and kernel stack overflow.
  7885.   */     
  7886.      
  7887. -static inline void NCR5380_main () {}
  7888. -
  7889. -static void NCR5380_main_a ( unsigned long flags )
  7890. +static void NCR5380_main (void)
  7891.  {
  7892.      Scsi_Cmnd *tmp, *prev;
  7893.      struct Scsi_Host *instance = first_instance;
  7894.      struct NCR5380_hostdata *hostdata = HOSTDATA(instance);
  7895.      int done;
  7896. +    unsigned long flags;
  7897.      
  7898.      /*
  7899.       * We run (with interrupts disabled) until we're sure that none of 
  7900. @@ -1128,14 +1072,20 @@
  7901.       * alter queues and touch the Falcon lock.
  7902.       */
  7903.  
  7904. +    /* Tell int handlers main() is now already executing.  Note that
  7905. +       no races are possible here. If an int comes in before
  7906. +       'main_running' is set here, and queues/executes main via the
  7907. +       task queue, it doesn't do any harm, just this instance of main
  7908. +       won't find any work left to do. */
  7909. +    main_running = 1;
  7910. +
  7911. +    save_flags(flags);
  7912.      do {
  7913.      cli(); /* Freeze request queues */
  7914.      done = 1;
  7915.      
  7916.      if (!hostdata->connected) {
  7917. -#if (NDEBUG & NDEBUG_MAIN)
  7918. -        printk("scsi%d: not connected\n", HOSTNO);
  7919. -#endif
  7920. +        MAIN_PRINTK( "scsi%d: not connected\n", HOSTNO );
  7921.          /*
  7922.           * Search through the issue_queue for a command destined
  7923.           * for a target that's not busy.
  7924. @@ -1185,11 +1135,10 @@
  7925.               * On failure, we must add the command back to the
  7926.               *   issue queue so we can keep trying.    
  7927.               */
  7928. -#if (NDEBUG & (NDEBUG_MAIN | NDEBUG_QUEUES))
  7929. -            printk("scsi%d: main(): command for target %d lun %d "
  7930. -               "removed from issue_queue\n",
  7931. -               HOSTNO, tmp->target, tmp->lun);
  7932. -#endif
  7933. +            DPRINTK(NDEBUG_MAIN | NDEBUG_QUEUES,
  7934. +                "scsi%d: main(): command for target %d lun %d "
  7935. +                "removed from issue_queue\n",
  7936. +                HOSTNO, tmp->target, tmp->lun);
  7937.              /* 
  7938.               * REQUEST SENSE commands are issued without tagged
  7939.               * queueing, even on SCSI-II devices because the 
  7940. @@ -1220,10 +1169,9 @@
  7941.  #endif
  7942.              falcon_dont_release--;
  7943.              restore_flags(flags);
  7944. -#if (NDEBUG & (NDEBUG_MAIN | NDEBUG_QUEUES))
  7945. -            printk("scsi%d: main(): select() failed, "
  7946. -                   "returned to issue_queue\n", HOSTNO);
  7947. -#endif
  7948. +            DPRINTK(NDEBUG_MAIN | NDEBUG_QUEUES,
  7949. +                "scsi%d: main(): select() failed, "
  7950. +                "returned to issue_queue\n", HOSTNO);
  7951.              if (hostdata->connected)
  7952.                  break;
  7953.              }
  7954. @@ -1237,21 +1185,19 @@
  7955.  #endif
  7956.          ) {
  7957.          restore_flags(flags);
  7958. -#if (NDEBUG & NDEBUG_MAIN)
  7959. -        printk("scsi%d: main() : performing information transfer\n",
  7960. -           HOSTNO);
  7961. -#endif
  7962. +        MAIN_PRINTK("scsi%d: main: performing information transfer\n",
  7963. +            HOSTNO);
  7964.          NCR5380_information_transfer(instance);
  7965. -#if (NDEBUG & NDEBUG_MAIN)
  7966. -        printk("scsi%d: main() : done set false\n", HOSTNO);
  7967. -#endif
  7968. +        MAIN_PRINTK("scsi%d: main: done set false\n", HOSTNO);
  7969.          done = 0;
  7970. -    } else {
  7971. -        cli(); /* ++guenther: be sure to protect main_running */
  7972. -        break;
  7973.      }
  7974.      } while (!done);
  7975. +
  7976. +    /* Better allow ints _after_ 'main_running' has been cleared, else
  7977. +       an interrupt could believe we'll pick up the work it left for
  7978. +       us, but we won't see it anymore here... */
  7979.      main_running = 0;
  7980. +    restore_flags(flags);
  7981.  }
  7982.  
  7983.  
  7984. @@ -1274,8 +1220,8 @@
  7985.      volatile int  *count;
  7986.  
  7987.      if (!hostdata->connected) {
  7988. -    printk("scsi%d: received end of DMA interrupt with no connected cmd\n",
  7989. -           HOSTNO);
  7990. +    printk(KERN_WARNING "scsi%d: received end of DMA interrupt with "
  7991. +           "no connected cmd\n", HOSTNO);
  7992.      return;
  7993.      }
  7994.      
  7995. @@ -1288,18 +1234,14 @@
  7996.           (BASR_PHASE_MATCH|BASR_ACK))) {
  7997.          saved_data = NCR5380_read(INPUT_DATA_REG);
  7998.          overrun = 1;
  7999. -#if (NDEBUG & NDEBUG_DMA)
  8000. -        printk( "scsi%d: read overrun handled\n", HOSTNO );
  8001. -#endif
  8002. +        DMA_PRINTK("scsi%d: read overrun handled\n", HOSTNO);
  8003.          }
  8004.      }
  8005.      }
  8006.  
  8007. -#if (NDEBUG & NDEBUG_DMA)
  8008. -    printk("scsi%d: real DMA transfer complete, basr 0x%X, sr 0x%X\n",
  8009. -       HOSTNO, NCR5380_read(BUS_AND_STATUS_REG),
  8010. -       NCR5380_read(STATUS_REG));
  8011. -#endif
  8012. +    DMA_PRINTK("scsi%d: real DMA transfer complete, basr 0x%X, sr 0x%X\n",
  8013. +           HOSTNO, NCR5380_read(BUS_AND_STATUS_REG),
  8014. +           NCR5380_read(STATUS_REG));
  8015.  
  8016.      (void) NCR5380_read(RESET_PARITY_INTERRUPT_REG);
  8017.      NCR5380_write(MODE_REG, MR_BASE);
  8018. @@ -1317,18 +1259,13 @@
  8019.      if ((NCR5380_read(STATUS_REG) & PHASE_MASK) == p && (p & SR_IO)) {
  8020.          cnt = toPIO = atari_read_overruns;
  8021.          if (overrun) {
  8022. -#if (NDEBUG & NDEBUG_DMA)
  8023. -        printk("Got an input overrun, using saved byte\n");
  8024. -#endif
  8025. +        DMA_PRINTK("Got an input overrun, using saved byte\n");
  8026.          *(*data)++ = saved_data;
  8027.          (*count)--;
  8028.          cnt--;
  8029.          toPIO--;
  8030.          }
  8031. -#if (NDEBUG & NDEBUG_DMA)
  8032. -        printk( "Doing %d-byte PIO to 0x%08lx\n", cnt, (long)*data );
  8033. -#endif
  8034. -
  8035. +        DMA_PRINTK("Doing %d-byte PIO to 0x%08lx\n", cnt, (long)*data);
  8036.          NCR5380_transfer_pio(instance, &p, &cnt, data);
  8037.          *count -= toPIO - cnt;
  8038.      }
  8039. @@ -1354,39 +1291,27 @@
  8040.      int done = 1;
  8041.      unsigned char basr;
  8042.  
  8043. -#if (NDEBUG & NDEBUG_INTR)
  8044. -    printk("scsi%d: NCR5380 irq triggered\n", HOSTNO);
  8045. -#endif
  8046. +    INT_PRINTK("scsi%d: NCR5380 irq triggered\n", HOSTNO);
  8047.  
  8048.      /* Look for pending interrupts */
  8049.      basr = NCR5380_read(BUS_AND_STATUS_REG);
  8050. -#if (NDEBUG & NDEBUG_INTR)
  8051. -    printk( "scsi%d: BASR=%02x\n", HOSTNO, basr );
  8052. -#endif
  8053. +    INT_PRINTK("scsi%d: BASR=%02x\n", HOSTNO, basr);
  8054.      /* dispatch to appropriate routine if found and done=0 */
  8055.      if (basr & BASR_IRQ) {
  8056. -#if (NDEBUG & NDEBUG_INTR)
  8057. -    NCR5380_print(instance);
  8058. -#endif
  8059. +    NCR_PRINT(NDEBUG_INTR);
  8060.      if ((NCR5380_read(STATUS_REG) & (SR_SEL|SR_IO)) == (SR_SEL|SR_IO)) {
  8061.          done = 0;
  8062.          ENABLE_IRQ();
  8063. -#if (NDEBUG & NDEBUG_INTR)
  8064. -        printk("scsi%d: SEL interrupt\n", HOSTNO);
  8065. -#endif
  8066. +        INT_PRINTK("scsi%d: SEL interrupt\n", HOSTNO);
  8067.          NCR5380_reselect(instance);
  8068.          (void) NCR5380_read(RESET_PARITY_INTERRUPT_REG);
  8069.      }
  8070.      else if (basr & BASR_PARITY_ERROR) {
  8071. -#if (NDEBUG & NDEBUG_INTR)
  8072. -        printk("scsi%d: PARITY interrupt\n", HOSTNO);
  8073. -#endif
  8074. +        INT_PRINTK("scsi%d: PARITY interrupt\n", HOSTNO);
  8075.          (void) NCR5380_read(RESET_PARITY_INTERRUPT_REG);
  8076.      }
  8077.      else if ((NCR5380_read(STATUS_REG) & SR_RST) == SR_RST) {
  8078. -#if (NDEBUG & NDEBUG_INTR)
  8079. -        printk("scsi%d: RESET interrupt\n", HOSTNO);
  8080. -#endif
  8081. +        INT_PRINTK("scsi%d: RESET interrupt\n", HOSTNO);
  8082.          (void)NCR5380_read(RESET_PARITY_INTERRUPT_REG);
  8083.      }
  8084.      else {
  8085. @@ -1406,41 +1331,34 @@
  8086.          ((basr & BASR_END_DMA_TRANSFER) || 
  8087.           !(basr & BASR_PHASE_MATCH))) {
  8088.              
  8089. -#if (NDEBUG & NDEBUG_INTR)
  8090. -        printk("scsi%d: PHASE MISM or EOP interrupt\n", HOSTNO);
  8091. -#endif
  8092. +        INT_PRINTK("scsi%d: PHASE MISM or EOP interrupt\n", HOSTNO);
  8093.          NCR5380_dma_complete( instance );
  8094.          done = 0;
  8095.          ENABLE_IRQ();
  8096.          } else
  8097.  #endif /* REAL_DMA */
  8098.          {
  8099. -#if 1 || (NDEBUG & NDEBUG_INTR)
  8100.  /* MS: Ignore unknown phase mismatch interrupts (caused by EOP interrupt) */
  8101.          if (basr & BASR_PHASE_MATCH)
  8102. -            printk("scsi%d: unknown interrupt, "
  8103. +            printk(KERN_NOTICE "scsi%d: unknown interrupt, "
  8104.                 "BASR 0x%x, MR 0x%x, SR 0x%x\n",
  8105.                 HOSTNO, basr, NCR5380_read(MODE_REG),
  8106.                 NCR5380_read(STATUS_REG));
  8107. -#endif
  8108.          (void) NCR5380_read(RESET_PARITY_INTERRUPT_REG);
  8109.          }
  8110.      } /* if !(SELECTION || PARITY) */
  8111.      } /* BASR & IRQ */
  8112.      else {
  8113. -#if 1 || (NDEBUG & NDEBUG_INTR)
  8114. -    printk("scsi%d: interrupt without IRQ bit set in BASR, "
  8115. +    printk(KERN_NOTICE "scsi%d: interrupt without IRQ bit set in BASR, "
  8116.             "BASR 0x%X, MR 0x%X, SR 0x%x\n", HOSTNO, basr,
  8117.             NCR5380_read(MODE_REG), NCR5380_read(STATUS_REG));
  8118. -#endif
  8119.      (void) NCR5380_read(RESET_PARITY_INTERRUPT_REG);
  8120.      }
  8121.      
  8122.      if (!done) {
  8123. -#if (NDEBUG & NDEBUG_INTR)
  8124. -    printk("scsi%d: in int routine, calling main\n", HOSTNO );
  8125. -#endif
  8126. -    run_main();
  8127. +    INT_PRINTK("scsi%d: in int routine, calling main\n", HOSTNO);
  8128. +    /* Put a call to NCR5380_main() on the queue... */
  8129. +    queue_main();
  8130.      }
  8131.  }
  8132.  
  8133. @@ -1511,11 +1429,9 @@
  8134.      unsigned long flags;
  8135.  
  8136.      hostdata->restart_select = 0;
  8137. -#if defined (NDEBUG) && (NDEBUG & NDEBUG_ARBITRATION) 
  8138. -    NCR5380_print(instance);
  8139. -    printk("scsi%d: starting arbitration, id = %d\n", HOSTNO,
  8140. -    instance->this_id);
  8141. -#endif
  8142. +    NCR_PRINT(NDEBUG_ARBITRATION);
  8143. +    ARB_PRINTK("scsi%d: starting arbitration, id = %d\n", HOSTNO,
  8144. +           instance->this_id);
  8145.  
  8146.      /* 
  8147.       * Set the phase bits to 0, otherwise the NCR5380 won't drive the 
  8148. @@ -1561,11 +1477,7 @@
  8149.       && !hostdata->connected);
  8150.  #endif
  8151.  
  8152. -#if (NDEBUG & NDEBUG_ARBITRATION) 
  8153. -    printk("scsi%d: arbitration complete\n", HOSTNO);
  8154. -/* Avoid GCC 2.4.5 asm needs to many reloads error */
  8155. -    __asm__("nop");
  8156. -#endif
  8157. +    ARB_PRINTK("scsi%d: arbitration complete\n", HOSTNO);
  8158.  
  8159.      if (hostdata->connected) {
  8160.      NCR5380_write(MODE_REG, MR_BASE); 
  8161. @@ -1586,9 +1498,8 @@
  8162.      (NCR5380_read(INITIATOR_COMMAND_REG) & ICR_ARBITRATION_LOST) ||
  8163.      hostdata->connected) {
  8164.      NCR5380_write(MODE_REG, MR_BASE); 
  8165. -#if (NDEBUG & NDEBUG_ARBITRATION)
  8166. -    printk("scsi%d: lost arbitration, deasserting MR_ARBITRATE\n", HOSTNO);
  8167. -#endif
  8168. +    ARB_PRINTK("scsi%d: lost arbitration, deasserting MR_ARBITRATE\n",
  8169. +           HOSTNO);
  8170.      return -1;
  8171.      }
  8172.  
  8173. @@ -1602,9 +1513,8 @@
  8174.      hostdata->connected) {
  8175.      NCR5380_write(MODE_REG, MR_BASE);
  8176.      NCR5380_write(INITIATOR_COMMAND_REG, ICR_BASE);
  8177. -#if (NDEBUG & NDEBUG_ARBITRATION)
  8178. -    printk("scsi%d: lost arbitration, deasserting ICR_ASSERT_SEL\n", HOSTNO);
  8179. -#endif
  8180. +    ARB_PRINTK("scsi%d: lost arbitration, deasserting ICR_ASSERT_SEL\n",
  8181. +           HOSTNO);
  8182.      return -1;
  8183.      }
  8184.  
  8185. @@ -1626,10 +1536,7 @@
  8186.      return -1;
  8187.      }
  8188.  
  8189. -#if (NDEBUG & NDEBUG_ARBITRATION)
  8190. -    printk("scsi%d: won arbitration\n", HOSTNO);
  8191. -#endif
  8192. -
  8193. +    ARB_PRINTK("scsi%d: won arbitration\n", HOSTNO);
  8194.  
  8195.      /* 
  8196.       * Now that we have won arbitration, start Selection process, asserting 
  8197. @@ -1689,9 +1596,7 @@
  8198.  
  8199.      udelay(1);
  8200.  
  8201. -#if (NDEBUG & NDEBUG_SELECTION)
  8202. -    printk("scsi%d: selecting target %d\n", HOSTNO, cmd->target);
  8203. -#endif
  8204. +    SEL_PRINTK("scsi%d: selecting target %d\n", HOSTNO, cmd->target);
  8205.  
  8206.      /* 
  8207.       * The SCSI specification calls for a 250 ms timeout for the actual 
  8208. @@ -1721,7 +1626,8 @@
  8209.          (SR_SEL | SR_IO)) {
  8210.          NCR5380_write(INITIATOR_COMMAND_REG, ICR_BASE);
  8211.          NCR5380_reselect(instance);
  8212. -        printk ("scsi%d: reselection after won arbitration?\n", HOSTNO);
  8213. +        printk (KERN_ERR "scsi%d: reselection after won arbitration?\n",
  8214. +            HOSTNO);
  8215.          NCR5380_write(SELECT_ENABLE_REG, hostdata->id_mask);
  8216.          return -1;
  8217.      }
  8218. @@ -1742,12 +1648,10 @@
  8219.      if (!(NCR5380_read(STATUS_REG) & SR_BSY)) {
  8220.      NCR5380_write(INITIATOR_COMMAND_REG, ICR_BASE);
  8221.      if (hostdata->targets_present & (1 << cmd->target)) {
  8222. -        printk("scsi%d: weirdness\n", HOSTNO);
  8223. +        printk(KERN_ERR "scsi%d: weirdness\n", HOSTNO);
  8224.          if (hostdata->restart_select)
  8225. -        printk("\trestart select\n");
  8226. -#ifdef NDEBUG
  8227. -        NCR5380_print (instance);
  8228. -#endif
  8229. +        printk(KERN_NOTICE "\trestart select\n");
  8230. +        NCR_PRINT(NDEBUG_ANY);
  8231.          NCR5380_write(SELECT_ENABLE_REG, hostdata->id_mask);
  8232.          return -1;
  8233.      }
  8234. @@ -1760,9 +1664,7 @@
  8235.  #endif
  8236.      cmd->scsi_done(cmd);
  8237.      NCR5380_write(SELECT_ENABLE_REG, hostdata->id_mask);
  8238. -#if (NDEBUG & NDEBUG_SELECTION)
  8239. -    printk("scsi%d: target did not respond within 250ms\n", HOSTNO);
  8240. -#endif
  8241. +    SEL_PRINTK("scsi%d: target did not respond within 250ms\n", HOSTNO);
  8242.      NCR5380_write(SELECT_ENABLE_REG, hostdata->id_mask);
  8243.      return 0;
  8244.      } 
  8245. @@ -1787,10 +1689,8 @@
  8246.      /* Wait for start of REQ/ACK handshake */
  8247.      while (!(NCR5380_read(STATUS_REG) & SR_REQ));
  8248.  
  8249. -#if (NDEBUG & NDEBUG_SELECTION)
  8250. -    printk("scsi%d: target %d selected, going into MESSAGE OUT phase.\n",
  8251. -       HOSTNO, cmd->target);
  8252. -#endif
  8253. +    SEL_PRINTK("scsi%d: target %d selected, going into MESSAGE OUT phase.\n",
  8254. +           HOSTNO, cmd->target);
  8255.      tmp[0] = IDENTIFY(1, cmd->lun);
  8256.  
  8257.  #ifdef SUPPORT_TAGS
  8258. @@ -1809,9 +1709,7 @@
  8259.      data = tmp;
  8260.      phase = PHASE_MSGOUT;
  8261.      NCR5380_transfer_pio(instance, &phase, &len, &data);
  8262. -#if (NDEBUG & NDEBUG_SELECTION)
  8263. -    printk("scsi%d: nexus established.\n", HOSTNO);
  8264. -#endif
  8265. +    SEL_PRINTK("scsi%d: nexus established.\n", HOSTNO);
  8266.      /* XXX need to handle errors here */
  8267.      hostdata->connected = cmd;
  8268.  #ifndef SUPPORT_TAGS
  8269. @@ -1872,16 +1770,12 @@
  8270.       */
  8271.      while (!((tmp = NCR5380_read(STATUS_REG)) & SR_REQ));
  8272.  
  8273. -#if (NDEBUG & NDEBUG_HANDSHAKE)
  8274. -    printk("scsi%d: REQ detected\n", HOSTNO);
  8275. -#endif
  8276. +    HSH_PRINTK("scsi%d: REQ detected\n", HOSTNO);
  8277.  
  8278.      /* Check for phase mismatch */    
  8279.      if ((tmp & PHASE_MASK) != p) {
  8280. -#if (NDEBUG & NDEBUG_PIO)
  8281. -        printk("scsi%d: phase mismatch\n", HOSTNO);
  8282. -        NCR5380_print_phase(instance);
  8283. -#endif
  8284. +        PIO_PRINTK("scsi%d: phase mismatch\n", HOSTNO);
  8285. +        NCR_PRINT_PHASE(NDEBUG_PIO);
  8286.          break;
  8287.      }
  8288.  
  8289. @@ -1904,32 +1798,24 @@
  8290.          if (!((p & SR_MSG) && c > 1)) {
  8291.          NCR5380_write(INITIATOR_COMMAND_REG, ICR_BASE | 
  8292.              ICR_ASSERT_DATA);
  8293. -#if (NDEBUG & NDEBUG_PIO)
  8294. -        NCR5380_print(instance);
  8295. -#endif
  8296. +        NCR_PRINT(NDEBUG_PIO);
  8297.          NCR5380_write(INITIATOR_COMMAND_REG, ICR_BASE | 
  8298.              ICR_ASSERT_DATA | ICR_ASSERT_ACK);
  8299.          } else {
  8300.          NCR5380_write(INITIATOR_COMMAND_REG, ICR_BASE |
  8301.              ICR_ASSERT_DATA | ICR_ASSERT_ATN);
  8302. -#if (NDEBUG & NDEBUG_PIO)
  8303. -        NCR5380_print(instance);
  8304. -#endif
  8305. +        NCR_PRINT(NDEBUG_PIO);
  8306.          NCR5380_write(INITIATOR_COMMAND_REG, ICR_BASE | 
  8307.              ICR_ASSERT_DATA | ICR_ASSERT_ATN | ICR_ASSERT_ACK);
  8308.          }
  8309.      } else {
  8310. -#if (NDEBUG & NDEBUG_PIO)
  8311. -        NCR5380_print(instance);
  8312. -#endif
  8313. +        NCR_PRINT(NDEBUG_PIO);
  8314.          NCR5380_write(INITIATOR_COMMAND_REG, ICR_BASE | ICR_ASSERT_ACK);
  8315.      }
  8316.  
  8317.      while (NCR5380_read(STATUS_REG) & SR_REQ);
  8318.  
  8319. -#if (NDEBUG & NDEBUG_HANDSHAKE)
  8320. -    printk("scsi%d: req false, handshake complete\n", HOSTNO);
  8321. -#endif
  8322. +    HSH_PRINTK("scsi%d: req false, handshake complete\n", HOSTNO);
  8323.  
  8324.  /*
  8325.   * We have several special cases to consider during REQ/ACK handshaking : 
  8326. @@ -1950,9 +1836,7 @@
  8327.      } 
  8328.      } while (--c);
  8329.  
  8330. -#if (NDEBUG & NDEBUG_PIO) 
  8331. -    printk("scsi%d: residual %d\n", HOSTNO, c);
  8332. -#endif
  8333. +    PIO_PRINTK("scsi%d: residual %d\n", HOSTNO, c);
  8334.  
  8335.      *count = c;
  8336.      *data = d;
  8337. @@ -2064,11 +1948,9 @@
  8338.      c -= atari_read_overruns;
  8339.      }
  8340.  
  8341. -#if (NDEBUG & NDEBUG_DMA)
  8342. -    printk("scsi%d: initializing DMA channel %d for %s, %d bytes %s %0x\n",
  8343. -       HOSTNO, instance->dma_channel, (p & SR_IO) ? "reading" :
  8344. -       "writing", c, (p & SR_IO) ? "to" : "from", (unsigned) d);
  8345. -#endif
  8346. +    DMA_PRINTK("scsi%d: initializing DMA for %s, %d bytes %s %p\n",
  8347. +           HOSTNO, (p & SR_IO) ? "reading" : "writing",
  8348. +           c, (p & SR_IO) ? "to" : "from", d);
  8349.  
  8350.      NCR5380_write(TARGET_COMMAND_REG, PHASE_SR_TO_TCR(p));
  8351.  
  8352. @@ -2148,9 +2030,7 @@
  8353.          phase = (tmp & PHASE_MASK); 
  8354.          if (phase != old_phase) {
  8355.          old_phase = phase;
  8356. -#if (NDEBUG & NDEBUG_INFORMATION)
  8357. -        NCR5380_print_phase(instance);
  8358. -#endif
  8359. +        NCR_PRINT_PHASE(NDEBUG_INFORMATION);
  8360.          }
  8361.          
  8362.          if (sink && (phase != PHASE_MSGOUT)) {
  8363. @@ -2191,11 +2071,9 @@
  8364.               * they are at consecutive physical addresses.
  8365.               */
  8366.              merge_consecutive_buffers( cmd );
  8367. -#if (NDEBUG & NDEBUG_INFORMATION)
  8368. -            printk("scsi%d: %d bytes and %d buffers left\n",
  8369. -               HOSTNO, cmd->SCp.this_residual,
  8370. -               cmd->SCp.buffers_residual);
  8371. -#endif
  8372. +            INF_PRINTK("scsi%d: %d bytes and %d buffers left\n",
  8373. +                   HOSTNO, cmd->SCp.this_residual,
  8374. +                   cmd->SCp.buffers_residual);
  8375.          }
  8376.  
  8377.          /*
  8378. @@ -2224,8 +2102,9 @@
  8379.               * If the watchdog timer fires, all future
  8380.               * accesses to this device will use the
  8381.               * polled-IO. */ 
  8382. -            printk("scsi%d: switching target %d lun %d to slow "
  8383. -                   "handshake\n", HOSTNO, cmd->target, cmd->lun);
  8384. +            printk(KERN_NOTICE "scsi%d: switching target %d "
  8385. +                   "lun %d to slow handshake\n", HOSTNO,
  8386. +                   cmd->target, cmd->lun);
  8387.              cmd->device->borken = 1;
  8388.              NCR5380_write(INITIATOR_COMMAND_REG, ICR_BASE | 
  8389.                  ICR_ASSERT_ATN);
  8390. @@ -2276,10 +2155,9 @@
  8391.              /* Accept message by clearing ACK */
  8392.              NCR5380_write(INITIATOR_COMMAND_REG, ICR_BASE);
  8393.              
  8394. -#if (NDEBUG & NDEBUG_LINKED) 
  8395. -            printk("scsi%d: target %d lun %d linked command complete.\n",
  8396. -            HOSTNO, cmd->target, cmd->lun);
  8397. -#endif
  8398. +            LNK_PRINTK("scsi%d: target %d lun %d linked command "
  8399. +                   "complete.\n", HOSTNO, cmd->target, cmd->lun);
  8400. +
  8401.              /* Enable reselect interrupts */
  8402.              NCR5380_write(SELECT_ENABLE_REG, hostdata->id_mask);
  8403.              /*
  8404. @@ -2289,8 +2167,8 @@
  8405.               */
  8406.  
  8407.              if (!cmd->next_link) {
  8408. -             printk("scsi%d: target %d lun %d linked command "
  8409. -                "complete, no next_link\n",
  8410. +             printk(KERN_NOTICE "scsi%d: target %d lun %d "
  8411. +                "linked command complete, no next_link\n",
  8412.                  HOSTNO, cmd->target, cmd->lun);
  8413.                  sink = 1;
  8414.                  do_abort (instance);
  8415. @@ -2302,11 +2180,9 @@
  8416.               * and don't free it! */
  8417.              cmd->next_link->tag = cmd->tag;
  8418.              cmd->result = cmd->SCp.Status | (cmd->SCp.Message << 8); 
  8419. -#if (NDEBUG & NDEBUG_LINKED) 
  8420. -            printk("scsi%d: target %d lun %d linked request done, "
  8421. -               "calling scsi_done().\n",
  8422. -               HOSTNO, cmd->target, cmd->lun);
  8423. -#endif
  8424. +            LNK_PRINTK("scsi%d: target %d lun %d linked request "
  8425. +                   "done, calling scsi_done().\n",
  8426. +                   HOSTNO, cmd->target, cmd->lun);
  8427.  #ifdef NCR5380_STATS
  8428.              collect_stats(hostdata, cmd);
  8429.  #endif
  8430. @@ -2321,10 +2197,8 @@
  8431.              /* ++guenther: possible race with Falcon locking */
  8432.              falcon_dont_release++;
  8433.              hostdata->connected = NULL;
  8434. -#if (NDEBUG & NDEBUG_QUEUES)
  8435. -            printk("scsi%d: command for target %d, lun %d completed\n",
  8436. -               HOSTNO, cmd->target, cmd->lun);
  8437. -#endif
  8438. +            QU_PRINTK("scsi%d: command for target %d, lun %d "
  8439. +                  "completed\n", HOSTNO, cmd->target, cmd->lun);
  8440.  #ifdef SUPPORT_TAGS
  8441.              cmd_free_tag( cmd );
  8442.              if (cmd->SCp.Status == QUEUE_FULL) {
  8443. @@ -2335,12 +2209,10 @@
  8444.               * commands now.
  8445.               */
  8446.              TAG_ALLOC *ta = &TagAlloc[cmd->target][cmd->lun];
  8447. -#if (NDEBUG & NDEBUG_TAGS)
  8448. -            printk( "scsi%d: target %d lun %d returned "
  8449. -                "QUEUE_FULL after %d commands\n",
  8450. -                HOSTNO, cmd->target, cmd->lun,
  8451. -                ta->nr_allocated );
  8452. -#endif
  8453. +            TAG_PRINTK("scsi%d: target %d lun %d returned "
  8454. +                   "QUEUE_FULL after %d commands\n",
  8455. +                   HOSTNO, cmd->target, cmd->lun,
  8456. +                   ta->nr_allocated);
  8457.              if (ta->queue_size > ta->nr_allocated)
  8458.                  ta->nr_allocated = ta->queue_size;
  8459.              cmd->SCp.Status = BUSY;
  8460. @@ -2375,9 +2247,8 @@
  8461.  #ifdef AUTOSENSE
  8462.              if ((cmd->cmnd[0] != REQUEST_SENSE) && 
  8463.              (cmd->SCp.Status == CHECK_CONDITION)) {
  8464. -#if (NDEBUG & NDEBUG_AUTOSENSE) 
  8465. -            printk("scsi%d: performing request sense\n", HOSTNO);
  8466. -#endif
  8467. +            ASEN_PRINTK("scsi%d: performing request sense\n",
  8468. +                    HOSTNO);
  8469.              cmd->cmnd[0] = REQUEST_SENSE;
  8470.              cmd->cmnd[1] &= 0xe0;
  8471.              cmd->cmnd[2] = 0;
  8472. @@ -2396,10 +2267,8 @@
  8473.              NEXT(cmd) = hostdata->issue_queue;
  8474.                  hostdata->issue_queue = (Scsi_Cmnd *) cmd;
  8475.                  restore_flags(flags);
  8476. -#if (NDEBUG & NDEBUG_QUEUES)
  8477. -            printk("scsi%d: REQUEST SENSE added to head of "
  8478. -                   "issue queue\n", H_NO(cmd));
  8479. -#endif
  8480. +            QU_PRINTK("scsi%d: REQUEST SENSE added to head of "
  8481. +                  "issue queue\n", H_NO(cmd));
  8482.             } else
  8483.  #endif /* def AUTOSENSE */
  8484.             {
  8485. @@ -2444,11 +2313,10 @@
  8486.              cmd->device->tagged_supported = 0;
  8487.              hostdata->busy[cmd->target] |= (1 << cmd->lun);
  8488.              cmd->tag = TAG_NONE;
  8489. -#if (NDEBUG & NDEBUG_TAGS)
  8490. -            printk( "scsi%d: target %d lun %d rejected QUEUE_TAG "
  8491. -                "message; tagged queuing disabled\n",
  8492. -                HOSTNO, cmd->target, cmd->lun );
  8493. -#endif
  8494. +            TAG_PRINTK("scsi%d: target %d lun %d rejected "
  8495. +                   "QUEUE_TAG message; tagged queuing "
  8496. +                   "disabled\n",
  8497. +                   HOSTNO, cmd->target, cmd->lun);
  8498.              break;
  8499.              }
  8500.              break;
  8501. @@ -2463,11 +2331,10 @@
  8502.              hostdata->connected = NULL;
  8503.              hostdata->disconnected_queue = cmd;
  8504.              restore_flags(flags);
  8505. -#if (NDEBUG & NDEBUG_QUEUES)
  8506. -            printk("scsi%d: command for target %d lun %d was moved from connected to"
  8507. -                   "  the disconnected_queue\n", HOSTNO, 
  8508. -                cmd->target, cmd->lun);
  8509. -#endif
  8510. +            QU_PRINTK("scsi%d: command for target %d lun %d was "
  8511. +                  "moved from connected to the "
  8512. +                  "disconnected_queue\n", HOSTNO, 
  8513. +                  cmd->target, cmd->lun);
  8514.              /* 
  8515.               * Restore phase bits to 0 so an interrupted selection, 
  8516.               * arbitration can resume.
  8517. @@ -2514,20 +2381,14 @@
  8518.              /* Accept first byte by clearing ACK */
  8519.              NCR5380_write(INITIATOR_COMMAND_REG, ICR_BASE);
  8520.  
  8521. -#if (NDEBUG & NDEBUG_EXTENDED)
  8522. -            printk("scsi%d: receiving extended message\n", HOSTNO);
  8523. -#endif
  8524. +            EXT_PRINTK("scsi%d: receiving extended message\n", HOSTNO);
  8525.  
  8526.              len = 2;
  8527.              data = extended_msg + 1;
  8528.              phase = PHASE_MSGIN;
  8529.              NCR5380_transfer_pio(instance, &phase, &len, &data);
  8530. -
  8531. -#if (NDEBUG & NDEBUG_EXTENDED)
  8532. -            printk("scsi%d: length=%d, code=0x%02x\n", HOSTNO,
  8533. -               (int) extended_msg[1],
  8534. -               (int) extended_msg[2]);
  8535. -#endif
  8536. +            EXT_PRINTK("scsi%d: length=%d, code=0x%02x\n", HOSTNO,
  8537. +                   (int)extended_msg[1], (int)extended_msg[2]);
  8538.  
  8539.              if (!len && extended_msg[1] <= 
  8540.              (sizeof (extended_msg) - 1)) {
  8541. @@ -2538,11 +2399,8 @@
  8542.              phase = PHASE_MSGIN;
  8543.  
  8544.              NCR5380_transfer_pio(instance, &phase, &len, &data);
  8545. -
  8546. -#if (NDEBUG & NDEBUG_EXTENDED)
  8547. -            printk("scsi%d: message received, residual %d\n",
  8548. -               HOSTNO, len);
  8549. -#endif
  8550. +            EXT_PRINTK("scsi%d: message received, residual %d\n",
  8551. +                   HOSTNO, len);
  8552.  
  8553.              switch (extended_msg[2]) {
  8554.              case EXTENDED_SDTR:
  8555. @@ -2552,11 +2410,12 @@
  8556.                  tmp = 0;
  8557.              }
  8558.              } else if (len) {
  8559. -            printk("scsi%d: error receiving extended message\n",
  8560. -                   HOSTNO);
  8561. +            printk(KERN_NOTICE "scsi%d: error receiving "
  8562. +                   "extended message\n", HOSTNO);
  8563.              tmp = 0;
  8564.              } else {
  8565. -            printk("scsi%d: extended message code %02x length %d is too long\n",
  8566. +            printk(KERN_NOTICE "scsi%d: extended message "
  8567. +                   "code %02x length %d is too long\n",
  8568.                     HOSTNO, extended_msg[2], extended_msg[1]);
  8569.              tmp = 0;
  8570.              }
  8571. @@ -2568,14 +2427,16 @@
  8572.           */
  8573.          default:
  8574.              if (!tmp) {
  8575. -            printk("scsi%d: rejecting message ", HOSTNO);
  8576. +            printk(KERN_DEBUG "scsi%d: rejecting message ", HOSTNO);
  8577.              print_msg (extended_msg);
  8578.              printk("\n");
  8579.              } else if (tmp != EXTENDED_MESSAGE)
  8580. -            printk("scsi%d: rejecting unknown message %02x from target %d, lun %d\n",
  8581. +            printk(KERN_DEBUG "scsi%d: rejecting unknown "
  8582. +                   "message %02x from target %d, lun %d\n",
  8583.                     HOSTNO, tmp, cmd->target, cmd->lun);
  8584.              else
  8585. -            printk("scsi%d: rejecting unknown extended message "
  8586. +            printk(KERN_DEBUG "scsi%d: rejecting unknown "
  8587. +                   "extended message "
  8588.                     "code %02x, length %d from target %d, lun %d\n",
  8589.                     HOSTNO, extended_msg[1], extended_msg[0],
  8590.                     cmd->target, cmd->lun);
  8591. @@ -2629,9 +2490,7 @@
  8592.          break;
  8593.          default:
  8594.          printk("scsi%d: unknown phase\n", HOSTNO);
  8595. -#ifdef NDEBUG
  8596. -        NCR5380_print(instance);
  8597. -#endif
  8598. +        NCR_PRINT(NDEBUG_ANY);
  8599.          } /* switch(phase) */
  8600.      } /* if (tmp * SR_REQ) */ 
  8601.      } /* while (1) */
  8602. @@ -2673,9 +2532,7 @@
  8603.  
  8604.      target_mask = NCR5380_read(CURRENT_SCSI_DATA_REG) & ~(hostdata->id_mask);
  8605.  
  8606. -#if (NDEBUG & NDEBUG_RESELECTION)
  8607. -    printk("scsi%d: reselect\n", HOSTNO);
  8608. -#endif
  8609. +    RSL_PRINTK("scsi%d: reselect\n", HOSTNO);
  8610.  
  8611.      /* 
  8612.       * At this point, we have detected that our SCSI ID is on the bus,
  8613. @@ -2703,7 +2560,7 @@
  8614.      NCR5380_transfer_pio(instance, &phase, &len, &data);
  8615.  
  8616.      if (!msg[0] & 0x80) {
  8617. -    printk("scsi%d: expecting IDENTIFY message, got ", HOSTNO);
  8618. +    printk(KERN_DEBUG "scsi%d: expecting IDENTIFY message, got ", HOSTNO);
  8619.      print_msg(msg);
  8620.      do_abort(instance);
  8621.      return;
  8622. @@ -2724,10 +2581,8 @@
  8623.      if (!NCR5380_transfer_pio(instance, &phase, &len, &data) &&
  8624.          msg[1] == SIMPLE_QUEUE_TAG)
  8625.          tag = msg[2];
  8626. -#if (NDEBUG & NDEBUG_TAGS)
  8627. -    printk("scsi%d: target mask %02x, lun %d sent tag %d at reselection\n",
  8628. -           HOSTNO, target_mask, lun, tag );
  8629. -#endif
  8630. +    TAG_PRINTK("scsi%d: target mask %02x, lun %d sent tag %d at "
  8631. +           "reselection\n", HOSTNO, target_mask, lun, tag);
  8632.      }
  8633.  #endif
  8634.      
  8635. @@ -2758,7 +2613,7 @@
  8636.      }
  8637.      
  8638.      if (!tmp) {
  8639. -    printk( "scsi%d: warning: target bitmask %02x lun %d "
  8640. +    printk(KERN_WARNING "scsi%d: warning: target bitmask %02x lun %d "
  8641.  #ifdef SUPPORT_TAGS
  8642.          "tag %d "
  8643.  #endif
  8644. @@ -2780,10 +2635,8 @@
  8645.      NCR5380_write(INITIATOR_COMMAND_REG, ICR_BASE);
  8646.  
  8647.      hostdata->connected = tmp;
  8648. -#if (NDEBUG & NDEBUG_RESELECTION)
  8649. -    printk("scsi%d: nexus established, target = %d, lun = %d, tag = %d\n",
  8650. -       HOSTNO, tmp->target, tmp->lun, tmp->tag);
  8651. -#endif
  8652. +    RSL_PRINTK("scsi%d: nexus established, target = %d, lun = %d, tag = %d\n",
  8653. +           HOSTNO, tmp->target, tmp->lun, tmp->tag);
  8654.      falcon_dont_release--;
  8655.  }
  8656.  
  8657. @@ -2815,7 +2668,7 @@
  8658.      Scsi_Cmnd *tmp, **prev;
  8659.      unsigned long flags;
  8660.  
  8661. -    printk("scsi%d: aborting command\n", HOSTNO);
  8662. +    printk(KERN_NOTICE "scsi%d: aborting command\n", HOSTNO);
  8663.      print_Scsi_Cmnd (cmd);
  8664.  
  8665.      NCR5380_print_status (instance);
  8666. @@ -2824,16 +2677,14 @@
  8667.      cli();
  8668.      
  8669.      if (!IS_A_TT() && !falcon_got_lock)
  8670. -    printk("scsi%d: !!BINGO!! Falcon has no lock in NCR5380_abort\n",
  8671. +    printk(KERN_ERR "scsi%d: !!BINGO!! Falcon has no lock in NCR5380_abort\n",
  8672.             HOSTNO);
  8673.  
  8674. -#if (NDEBUG & NDEBUG_ABORT)
  8675. -    printk("scsi%d: abort called basr 0x%02x, sr 0x%02x\n", HOSTNO,
  8676. -       NCR5380_read(BUS_AND_STATUS_REG),
  8677. -       NCR5380_read(STATUS_REG));
  8678. -#endif
  8679. +    ABRT_PRINTK("scsi%d: abort called basr 0x%02x, sr 0x%02x\n", HOSTNO,
  8680. +        NCR5380_read(BUS_AND_STATUS_REG),
  8681. +        NCR5380_read(STATUS_REG));
  8682.  
  8683. -#if 0
  8684. +#if 1
  8685.  /* 
  8686.   * Case 1 : If the command is the currently executing command, 
  8687.   * we'll set the aborted flag and return control so that 
  8688. @@ -2841,16 +2692,16 @@
  8689.   */
  8690.  
  8691.      if (hostdata->connected == cmd) {
  8692. -#if (NDEBUG & NDEBUG_ABORT)
  8693. -    printk("scsi%d: aborting connected command\n", HOSTNO);
  8694. -#endif
  8695. +    int rv;
  8696. +
  8697. +    ABRT_PRINTK("scsi%d: aborting connected command\n", HOSTNO);
  8698.      hostdata->aborted = 1;
  8699.  /*
  8700.   * We should perform BSY checking, and make sure we haven't slipped
  8701.   * into BUS FREE.
  8702.   */
  8703.  
  8704. -    NCR5380_write(INITIATOR_COMMAND_REG, ICR_ASSERT_ATN);
  8705. +/*    NCR5380_write(INITIATOR_COMMAND_REG, ICR_ASSERT_ATN); */
  8706.  /* 
  8707.   * Since we can't change phases until we've completed the current 
  8708.   * handshake, we have to source or sink a byte of data if the current
  8709. @@ -2858,11 +2709,30 @@
  8710.   */
  8711.  
  8712.  /* 
  8713. + * MSch: use the do_abort function instead ... unless there is need to wait
  8714. + * a longer period for the target to go into MSGOUT.
  8715. + */
  8716. +    rv = do_abort(instance);
  8717. +
  8718. +    save_flags(flags);
  8719. +    cli();
  8720. +
  8721. +    cmd->result = DID_ABORT << 16; 
  8722. +#ifdef SUPPORT_TAGS
  8723. +    cmd_free_tag( cmd );
  8724. +#else
  8725. +    hostdata->busy[cmd->target] &= ~(1 << cmd->lun);
  8726. +#endif
  8727. +    restore_flags(flags);
  8728. +    cmd->done(cmd);
  8729. +    falcon_release_lock_if_possible( hostdata );
  8730. +
  8731. +/* 
  8732.   * Return control to the executing NCR drive so we can clear the
  8733.   * aborted flag and get back into our main loop.
  8734.   */ 
  8735.   
  8736. -    return 0;
  8737. +    return rv ? SCSI_ABORT_SUCCESS : SCSI_ABORT_ERROR;
  8738.      }
  8739.  #endif
  8740.  
  8741. @@ -2879,10 +2749,8 @@
  8742.          NEXT(tmp) = NULL;
  8743.          tmp->result = DID_ABORT << 16;
  8744.          restore_flags(flags);
  8745. -#if (NDEBUG & NDEBUG_ABORT)
  8746. -        printk("scsi%d: abort removed command from issue queue.\n",
  8747. -           HOSTNO);
  8748. -#endif
  8749. +        ABRT_PRINTK("scsi%d: abort removed command from issue queue.\n",
  8750. +            HOSTNO);
  8751.          /* Tagged queuing note: no tag to free here, hasn't been assigned
  8752.           * yet... */
  8753.          tmp->done(tmp);
  8754. @@ -2903,10 +2771,8 @@
  8755.  
  8756.      if (hostdata->connected) {
  8757.      restore_flags(flags);
  8758. -#if (NDEBUG & NDEBUG_ABORT)
  8759. -    printk("scsi%d: abort failed, command connected.\n", HOSTNO);
  8760. -#endif
  8761. -        return SCSI_ABORT_NOT_RUNNING;
  8762. +    ABRT_PRINTK("scsi%d: abort failed, command connected.\n", HOSTNO);
  8763. +        return SCSI_ABORT_SNOOZE;
  8764.      }
  8765.  
  8766.  /*
  8767. @@ -2938,16 +2804,12 @@
  8768.       tmp = NEXT(tmp)) 
  8769.          if (cmd == tmp) {
  8770.              restore_flags(flags);
  8771. -#if (NDEBUG & NDEBUG_ABORT)
  8772. -    printk("scsi%d: aborting disconnected command.\n", HOSTNO);
  8773. -#endif
  8774. +        ABRT_PRINTK("scsi%d: aborting disconnected command.\n", HOSTNO);
  8775.    
  8776.              if (NCR5380_select (instance, cmd, (int) cmd->tag)) 
  8777.          return SCSI_ABORT_BUSY;
  8778.  
  8779. -#if (NDEBUG & NDEBUG_ABORT)
  8780. -    printk("scsi%d: nexus reestablished.\n", HOSTNO);
  8781. -#endif
  8782. +        ABRT_PRINTK("scsi%d: nexus reestablished.\n", HOSTNO);
  8783.  
  8784.          do_abort (instance);
  8785.  
  8786. @@ -2988,8 +2850,8 @@
  8787.   */
  8788.  
  8789.      restore_flags(flags);
  8790. -    printk("scsi%d: warning : SCSI command probably completed successfully\n"
  8791. -           "        before abortion\n", HOSTNO); 
  8792. +    printk(KERN_INFO "scsi%d: warning : SCSI command probably completed successfully\n"
  8793. +           KERN_INFO "        before abortion\n", HOSTNO); 
  8794.  
  8795.  /* Maybe it is sufficient just to release the ST-DMA lock... (if
  8796.   * possible at all) At least, we should check if the lock could be
  8797. @@ -3012,15 +2874,13 @@
  8798.  
  8799.  static int NCR5380_reset( Scsi_Cmnd *cmd, unsigned int reset_flags)
  8800.  {
  8801. -#if 0
  8802.      SETUP_HOSTDATA(cmd->host);
  8803.      int           i;
  8804.      unsigned long flags;
  8805.      Scsi_Cmnd *connected, *disconnected_queue;
  8806. -#endif
  8807.  
  8808.      if (!IS_A_TT() && !falcon_got_lock)
  8809. -    printk("scsi%d: !!BINGO!! Falcon has no lock in NCR5380_reset\n",
  8810. +    printk(KERN_ERR "scsi%d: !!BINGO!! Falcon has no lock in NCR5380_reset\n",
  8811.             H_NO(cmd) );
  8812.  
  8813.      NCR5380_print_status (cmd->host);
  8814. @@ -3040,7 +2900,7 @@
  8815.       * through anymore ... */
  8816.      (void)NCR5380_read( RESET_PARITY_INTERRUPT_REG );
  8817.  
  8818. -#if 0 /* XXX Now done by midlevel code XXX */
  8819. +#if 1 /* XXX Should now be done by midlevel code, bug isn't XXX */
  8820.  
  8821.      /* After the reset, there are no more connected or disconnected commands
  8822.       * and no busy units; to avoid problems with re-inserting the commands
  8823. @@ -3064,9 +2924,7 @@
  8824.      restore_flags(flags);
  8825.  
  8826.      if ((cmd = connected)) {
  8827. -#if (NDEBUG & NDEBUG_ABORT)
  8828. -    printk( "scsi%d: reset aborted a connected command\n", H_NO(cmd));
  8829. -#endif
  8830. +    ABRT_PRINTK("scsi%d: reset aborted a connected command\n", H_NO(cmd));
  8831.      cmd->result = (cmd->result & 0xffff) | (DID_RESET << 16);
  8832.      cmd->scsi_done( cmd );
  8833.      }
  8834. @@ -3077,10 +2935,8 @@
  8835.      cmd->result = (cmd->result & 0xffff) | (DID_RESET << 16);
  8836.      cmd->scsi_done( cmd );
  8837.      }
  8838. -#if (NDEBUG & NDEBUG_ABORT)
  8839.      if (i > 0)
  8840. -    printk( "scsi : reset aborted %d disconnected command(s)\n", i );
  8841. -#endif
  8842. +    ABRT_PRINTK("scsi: reset aborted %d disconnected command(s)\n", i);
  8843.  
  8844.  /* The Falcon lock should be released after a reset...
  8845.   */
  8846. @@ -3089,7 +2945,7 @@
  8847.   */
  8848.  /*    falcon_release_lock_if_possible( hostdata );*/
  8849.  
  8850. -#endif /* 0 */
  8851. +#endif /* 1 */
  8852.  
  8853.      return SCSI_RESET_WAKEUP;
  8854.  }
  8855. diff -u --recursive --new-file pre2.0.4/linux/drivers/scsi/atari_scsi.c linux/drivers/scsi/atari_scsi.c
  8856. --- pre2.0.4/linux/drivers/scsi/atari_scsi.c    Sat Apr 27 15:19:57 1996
  8857. +++ linux/drivers/scsi/atari_scsi.c    Thu May 16 09:05:11 1996
  8858. @@ -68,7 +68,11 @@
  8859.  #include <linux/config.h>
  8860.  #include <linux/module.h>
  8861.  
  8862. -/* #define NDEBUG (NDEBUG_DMA) */
  8863. +#define NDEBUG (0)
  8864. +
  8865. +#define NDEBUG_ABORT    0x800000
  8866. +#define NDEBUG_TAGS    0x1000000
  8867. +#define NDEBUG_MERGING    0x2000000
  8868.  
  8869.  #define AUTOSENSE
  8870.  /* For the Atari version, use only polled IO or REAL_DMA */
  8871. @@ -101,7 +105,7 @@
  8872.  #include <asm/atari_stdma.h>
  8873.  #include <asm/io.h>
  8874.  
  8875. -#include<linux/stat.h>
  8876. +#include <linux/stat.h>
  8877.  
  8878.  struct proc_dir_entry proc_scsi_atari = {
  8879.      PROC_SCSI_ATARI, 5, "Atari",
  8880. @@ -186,7 +190,6 @@
  8881.  
  8882.  #ifdef REAL_DMA
  8883.  static int scsi_dma_is_ignored_buserr( unsigned char dma_stat );
  8884. -static void scsi_dma_buserr( int irq, struct pt_regs *fp, void *dummy);
  8885.  static void atari_scsi_fetch_restbytes( void );
  8886.  static long atari_scsi_dma_residual( struct Scsi_Host *instance );
  8887.  static int falcon_classify_cmd( Scsi_Cmnd *cmd );
  8888. @@ -268,6 +271,11 @@
  8889.  }
  8890.  
  8891.  
  8892. +#if 0
  8893. +/* Dead code... wasn't called anyway :-) and causes some trouble, because at
  8894. + * end-of-DMA, both SCSI ints are triggered simultaneously, so the NCR int has
  8895. + * to clear the DMA int pending bit before it allows other level 6 interrupts.
  8896. + */
  8897.  static void scsi_dma_buserr (int irq, struct pt_regs *fp, void *dummy)
  8898.  {
  8899.      unsigned char    dma_stat = tt_scsi_dma.dma_ctrl;
  8900. @@ -292,45 +300,29 @@
  8901.          printk( "SCSI DMA intr ?? -- this shouldn't happen!\n" );
  8902.      }
  8903.  }
  8904. +#endif
  8905.  
  8906.  #endif
  8907.  
  8908.  
  8909.  static void scsi_tt_intr (int irq, struct pt_regs *fp, void *dummy)
  8910.  {
  8911. -    unsigned long    flags;
  8912.  #ifdef REAL_DMA
  8913.      int dma_stat;
  8914. -#endif
  8915.  
  8916. -    /* If we got this interrupt, we don't need the other one from the DMA any
  8917. -     * more. So clear it. */
  8918. -    atari_clear_pending_irq( IRQ_TT_MFP_SCSIDMA );
  8919. -    /* After this has been done, we can make this int handler "slow", i.e.
  8920. -     * mask the NCR int and lower the IPL, as a slow int would do (see
  8921. -     * arch/m68k/atari/ataints.c) */
  8922. -    atari_disable_irq( IRQ_TT_MFP_SCSI );
  8923. -    save_flags(flags);
  8924. -    flags &= 0xf8ff;
  8925. -    flags |= fp->sr & 0x0700;
  8926. -    restore_flags(flags);
  8927. -    
  8928. -#ifdef REAL_DMA
  8929.      dma_stat = tt_scsi_dma.dma_ctrl;
  8930.  
  8931. -#if (NDEBUG & NDEBUG_INTR)
  8932. -    printk("scsi%d: NCR5380 interrupt, DMA status = %02x\n",
  8933. -           atari_scsi_host->host_no, dma_stat & 0xff);
  8934. -#endif
  8935. +    INT_PRINTK("scsi%d: NCR5380 interrupt, DMA status = %02x\n",
  8936. +           atari_scsi_host->host_no, dma_stat & 0xff);
  8937.  
  8938.      /* Look if it was the DMA that has interrupted: First possibility
  8939.       * is that a bus error occurred...
  8940.       */
  8941.      if (dma_stat & 0x80) {
  8942.          if (!scsi_dma_is_ignored_buserr( dma_stat )) {
  8943. -            printk( "SCSI DMA caused bus error near 0x%08lx\n",
  8944. -                    SCSI_DMA_READ_P( dma_addr ));
  8945. -            panic( "SCSI DMA bus error -- bad DMA programming!" );
  8946. +            printk(KERN_ERR "SCSI DMA caused bus error near 0x%08lx\n",
  8947. +                   SCSI_DMA_READ_P(dma_addr));
  8948. +            printk(KERN_CRIT "SCSI DMA bus error -- bad DMA programming!");
  8949.          }
  8950.      }
  8951.  
  8952. @@ -346,10 +338,10 @@
  8953.      if ((dma_stat & 0x02) && !(dma_stat & 0x40)) {
  8954.          atari_dma_residual = HOSTDATA_DMALEN - (SCSI_DMA_READ_P( dma_addr ) -
  8955.                                                  atari_dma_startaddr);
  8956. -#if (NDEBUG & NDEBUG_DMA)
  8957. -        printk( "SCSI DMA: There are %ld residual bytes.\n",
  8958. -                atari_dma_residual );
  8959. -#endif
  8960. +
  8961. +        DMA_PRINTK("SCSI DMA: There are %ld residual bytes.\n",
  8962. +               atari_dma_residual);
  8963. +
  8964.          if ((signed int)atari_dma_residual < 0)
  8965.              atari_dma_residual = 0;
  8966.          if ((dma_stat & 1) == 0) {
  8967. @@ -376,10 +368,9 @@
  8968.                 other command.  These shouldn't disconnect anyway.
  8969.                 */
  8970.              if (atari_dma_residual & 0x1ff) {
  8971. -#if (NDEBUG & NDEBUG_DMA)
  8972. -                printk("SCSI DMA: DMA bug corrected, difference %ld bytes\n",
  8973. -                       512 - (atari_dma_residual & 0x1ff));
  8974. -#endif
  8975. +                DMA_PRINTK("SCSI DMA: DMA bug corrected, "
  8976. +                       "difference %ld bytes\n",
  8977. +                       512 - (atari_dma_residual & 0x1ff));
  8978.                  atari_dma_residual = (atari_dma_residual + 511) & ~0x1ff;
  8979.              }
  8980.          }
  8981. @@ -398,8 +389,10 @@
  8982.      
  8983.      NCR5380_intr (0, 0, 0);
  8984.  
  8985. +#if 0
  8986.      /* To be sure the int is not masked */
  8987.      atari_enable_irq( IRQ_TT_MFP_SCSI );
  8988. +#endif
  8989.  }
  8990.  
  8991.  
  8992. @@ -419,7 +412,7 @@
  8993.       */
  8994.      if (!(dma_stat & 0x01)) {
  8995.          /* DMA error */
  8996. -        printk( "SCSI DMA error near 0x%08lx!\n", SCSI_DMA_GETADR() );
  8997. +        printk(KERN_CRIT "SCSI DMA error near 0x%08lx!\n", SCSI_DMA_GETADR());
  8998.      }
  8999.  
  9000.      /* If the DMA was active, but now bit 1 is not clear, it is some
  9001. @@ -437,14 +430,12 @@
  9002.           * lost somewhere in outer space.
  9003.           */
  9004.          if (transferred & 15)
  9005. -            printk( "SCSI DMA error: %ld bytes lost in ST-DMA fifo :-((\n",
  9006. -                   transferred & 15 );
  9007. +            printk(KERN_ERR "SCSI DMA error: %ld bytes lost in "
  9008. +                   "ST-DMA fifo\n", transferred & 15);
  9009.  
  9010.          atari_dma_residual = HOSTDATA_DMALEN - transferred;
  9011. -#if (NDEBUG & NDEBUG_DMA)
  9012. -        printk( "SCSI DMA: There are %ld residual bytes.\n",
  9013. -               atari_dma_residual );
  9014. -#endif
  9015. +        DMA_PRINTK("SCSI DMA: There are %ld residual bytes.\n",
  9016. +               atari_dma_residual);
  9017.      }
  9018.      else
  9019.          atari_dma_residual = 0;
  9020. @@ -477,15 +468,11 @@
  9021.          /* there are 'nr' bytes left for the last long address before the
  9022.             DMA pointer */
  9023.          dst = (char *)( (unsigned long)dst & ~3 );
  9024. -#if (NDEBUG & NDEBUG_DMA)
  9025. -        printk( "SCSI DMA: there are %d rest bytes for phys addr 0x%08lx",
  9026. -               nr, (long)dst );
  9027. -#endif
  9028. +        DMA_PRINTK("SCSI DMA: there are %d rest bytes for phys addr 0x%08lx",
  9029. +               nr, (long)dst);
  9030.          dst = (char *)PTOV(dst);  /* The content of the DMA pointer
  9031.                         * is a physical address! */
  9032. -#if (NDEBUG & NDEBUG_DMA)
  9033. -        printk( " = virt addr 0x%08lx\n", (long)dst );
  9034. -#endif
  9035. +        DMA_PRINTK(" = virt addr 0x%08lx\n", (long)dst);
  9036.          for( src = (char *)&tt_scsi_dma.dma_restdata; nr > 0; --nr )
  9037.              *dst++ = *src++;
  9038.      }
  9039. @@ -697,18 +684,10 @@
  9040.          /* This int is actually "pseudo-slow", i.e. it acts like a slow
  9041.           * interrupt after having cleared the pending flag for the DMA
  9042.           * interrupt. */
  9043. -        add_isr(IRQ_TT_MFP_SCSI, scsi_tt_intr, IRQ_TYPE_PRIO,
  9044. +        add_isr(IRQ_TT_MFP_SCSI, scsi_tt_intr, IRQ_TYPE_SLOW,
  9045.              NULL, "SCSI NCR5380");
  9046.          tt_mfp.active_edge |= 0x80;        /* SCSI int on L->H */
  9047.  #ifdef REAL_DMA
  9048. -        /* On the TT, we got a second interrupt for DMA ready and DMA buserror.
  9049. -         * Since on DMA ready we get a "normal" interrupt, too, the service
  9050. -         * routine for the second int just checks for buserrs.
  9051. -         */
  9052. -        add_isr(IRQ_TT_MFP_SCSIDMA, scsi_dma_buserr, IRQ_TYPE_SLOW,
  9053. -            NULL, "SCSI DMA");
  9054. -        tt_mfp.active_edge &= ~0x20;    /* DMA int on H->L */
  9055. -
  9056.          tt_scsi_dma.dma_ctrl = 0;
  9057.          atari_dma_residual = 0;
  9058.  #endif /* REAL_DMA */
  9059. @@ -744,7 +723,7 @@
  9060.  #endif
  9061.      }
  9062.  
  9063. -    printk( "scsi%d: options CAN_QUEUE=%d CMD_PER_LUN=%d SCAT-GAT=%d "
  9064. +    printk(KERN_INFO "scsi%d: options CAN_QUEUE=%d CMD_PER_LUN=%d SCAT-GAT=%d "
  9065.  #ifdef SUPPORT_TAGS
  9066.              "TAGGED-QUEUING=%s "
  9067.  #endif
  9068. @@ -766,12 +745,8 @@
  9069.  #ifdef MODULE
  9070.  int atari_scsi_release (struct Scsi_Host *sh)
  9071.  {
  9072. -    if (IS_A_TT()) {
  9073. +    if (IS_A_TT())
  9074.          remove_isr (IRQ_TT_MFP_SCSI, scsi_tt_intr);
  9075. -#ifdef REAL_DMA
  9076. -        remove_isr (IRQ_TT_MFP_SCSIDMA, scsi_dma_buserr);
  9077. -#endif
  9078. -    }
  9079.      if (atari_dma_buffer)
  9080.          scsi_init_free (atari_dma_buffer, STRAM_BUFFER_SIZE);
  9081.      return 1;
  9082. @@ -926,10 +901,8 @@
  9083.  {
  9084.      unsigned long addr = VTOP( data );
  9085.  
  9086. -#if (NDEBUG & NDEBUG_DMA)
  9087. -    printk ("scsi%d: setting up dma, data = %p, phys = %lx, count = %ld, dir = %d\n",
  9088. -        instance->host_no, data, addr, count, dir);
  9089. -#endif
  9090. +    DMA_PRINTK("scsi%d: setting up dma, data = %p, phys = %lx, count = %ld, "
  9091. +           "dir = %d\n", instance->host_no, data, addr, count, dir);
  9092.  
  9093.      if (!IS_A_TT() && !STRAM_ADDR(addr)) {
  9094.          /* If we have a non-DMAable address on a Falcon, use the dribble
  9095. @@ -958,7 +931,7 @@
  9096.      dma_cache_maintenance( addr, count, dir );
  9097.  
  9098.      if (count == 0)
  9099. -        printk("SCSI warning: DMA programmed for 0 bytes !\n");
  9100. +        printk(KERN_NOTICE "SCSI warning: DMA programmed for 0 bytes !\n");
  9101.  
  9102.      if (IS_A_TT()) {
  9103.          tt_scsi_dma.dma_ctrl = dir;
  9104. @@ -1111,11 +1084,8 @@
  9105.      if (possible_len > limit)
  9106.          possible_len = limit;
  9107.  
  9108. -#if (NDEBUG & NDEBUG_DMA)
  9109. -    if (possible_len != wanted_len)
  9110. -        printk( "Sorry, must cut DMA transfer size to %ld bytes instead of %ld\n",
  9111. -                possible_len, wanted_len );
  9112. -#endif
  9113. +    DMA_PRINTK("Sorry, must cut DMA transfer size to %ld bytes instead "
  9114. +           "of %ld\n", possible_len, wanted_len);
  9115.  
  9116.      return( possible_len );
  9117.  }
  9118. diff -u --recursive --new-file pre2.0.4/linux/drivers/scsi/atari_scsi.h linux/drivers/scsi/atari_scsi.h
  9119. --- pre2.0.4/linux/drivers/scsi/atari_scsi.h    Sat Apr 27 15:19:57 1996
  9120. +++ linux/drivers/scsi/atari_scsi.h    Thu May 16 09:05:11 1996
  9121. @@ -92,6 +92,103 @@
  9122.  #define    NCR5380_dma_xfer_len(i,cmd,phase) \
  9123.      atari_dma_xfer_len(cmd->SCp.this_residual,cmd,((phase) & SR_IO) ? 0 : 1)
  9124.  
  9125. +/* Debugging printk definitions:
  9126. + * DPRINTK() is the generic one, takes an NDEBUG_* mask as argument;
  9127. + * all others are hardcoded to one NDEBUG_* code:
  9128. + *
  9129. + *  ARB  -> arbitration
  9130. + *  ASEN -> auto-sense
  9131. + *  DMA  -> DMA
  9132. + *  HSH  -> PIO handshake
  9133. + *  INF  -> information transfer
  9134. + *  INI  -> initialization
  9135. + *  INT  -> interrupt
  9136. + *  LNK  -> linked commands
  9137. + *  MAIN -> NCR5380_main() control flow
  9138. + *  NDAT -> no data-out phase
  9139. + *  NWR  -> no write commands
  9140. + *  PIO  -> PIO tansfers
  9141. + *  PDMA -> pseudo DMA (unused on Atari)
  9142. + *  QU   -> queues
  9143. + *  RSL  -> reselections
  9144. + *  SEL  -> selections
  9145. + *  USL  -> usleep cpde (unused on Atari)
  9146. + *  LBS  -> last byte sent (unused on Atari)
  9147. + *  RSS  -> restarting of selections
  9148. + *  EXT  -> extended messages
  9149. + *  ABRT -> aborting and resetting
  9150. + *  TAG  -> queue tag handling
  9151. + *  MER  -> merging of consec. buffers
  9152. + *
  9153. + */
  9154. +
  9155. +#define DPRINTK(mask, format, args...)                \
  9156. +    do {                            \
  9157. +        if (NDEBUG & (mask))                \
  9158. +            printk(KERN_DEBUG format , ## args);    \
  9159. +    } while(0)
  9160. +
  9161. +#define ARB_PRINTK(format, args...) \
  9162. +    DPRINTK(NDEBUG_ARBITRATION, format , ##args)
  9163. +#define ASEN_PRINTK(format, args...) \
  9164. +    DPRINTK(NDEBUG_AUTOSENSE, format , ##args)
  9165. +#define DMA_PRINTK(format, args...) \
  9166. +    DPRINTK(NDEBUG_DMA, format , ##args)
  9167. +#define HSH_PRINTK(format, args...) \
  9168. +    DPRINTK(NDEBUG_HANDSHAKE, format , ##args)
  9169. +#define INF_PRINTK(format, args...) \
  9170. +    DPRINTK(NDEBUG_INFORMATION, format , ##args)
  9171. +#define INI_PRINTK(format, args...) \
  9172. +    DPRINTK(NDEBUG_INIT, format , ##args)
  9173. +#define INT_PRINTK(format, args...) \
  9174. +    DPRINTK(NDEBUG_INTR, format , ##args)
  9175. +#define LNK_PRINTK(format, args...) \
  9176. +    DPRINTK(NDEBUG_LINKED, format , ##args)
  9177. +#define MAIN_PRINTK(format, args...) \
  9178. +    DPRINTK(NDEBUG_MAIN, format , ##args)
  9179. +#define NDAT_PRINTK(format, args...) \
  9180. +    DPRINTK(NDEBUG_NO_DATAOUT, format , ##args)
  9181. +#define NWR_PRINTK(format, args...) \
  9182. +    DPRINTK(NDEBUG_NO_WRITE, format , ##args)
  9183. +#define PIO_PRINTK(format, args...) \
  9184. +    DPRINTK(NDEBUG_PIO, format , ##args)
  9185. +#define PDMA_PRINTK(format, args...) \
  9186. +    DPRINTK(NDEBUG_PSEUDO_DMA, format , ##args)
  9187. +#define QU_PRINTK(format, args...) \
  9188. +    DPRINTK(NDEBUG_QUEUES, format , ##args)
  9189. +#define RSL_PRINTK(format, args...) \
  9190. +    DPRINTK(NDEBUG_RESELECTION, format , ##args)
  9191. +#define SEL_PRINTK(format, args...) \
  9192. +    DPRINTK(NDEBUG_SELECTION, format , ##args)
  9193. +#define USL_PRINTK(format, args...) \
  9194. +    DPRINTK(NDEBUG_USLEEP, format , ##args)
  9195. +#define LBS_PRINTK(format, args...) \
  9196. +    DPRINTK(NDEBUG_LAST_BYTE_SENT, format , ##args)
  9197. +#define RSS_PRINTK(format, args...) \
  9198. +    DPRINTK(NDEBUG_RESTART_SELECT, format , ##args)
  9199. +#define EXT_PRINTK(format, args...) \
  9200. +    DPRINTK(NDEBUG_EXTENDED, format , ##args)
  9201. +#define ABRT_PRINTK(format, args...) \
  9202. +    DPRINTK(NDEBUG_ABORT, format , ##args)
  9203. +#define TAG_PRINTK(format, args...) \
  9204. +    DPRINTK(NDEBUG_TAGS, format , ##args)
  9205. +#define MER_PRINTK(format, args...) \
  9206. +    DPRINTK(NDEBUG_MERGING, format , ##args)
  9207. +
  9208. +/* conditional macros for NCR5380_print_{,phase,status} */
  9209. +
  9210. +#define NCR_PRINT(mask)    \
  9211. +    ((NDEBUG & (mask)) ? NCR5380_print(instance) : (void)0)
  9212. +
  9213. +#define NCR_PRINT_PHASE(mask) \
  9214. +    ((NDEBUG & (mask)) ? NCR5380_print_phase(instance) : (void)0)
  9215. +
  9216. +#define NCR_PRINT_STATUS(mask) \
  9217. +    ((NDEBUG & (mask)) ? NCR5380_print_status(instance) : (void)0)
  9218. +
  9219. +#define NDEBUG_ANY    0xffffffff
  9220. +
  9221. +
  9222.  #endif /* else def HOSTS_C */
  9223.  #endif /* ndef ASM */
  9224.  #endif /* ATARI_SCSI_H */
  9225. diff -u --recursive --new-file pre2.0.4/linux/drivers/sound/dmasound.c linux/drivers/sound/dmasound.c
  9226. --- pre2.0.4/linux/drivers/sound/dmasound.c    Sat Apr 27 15:19:57 1996
  9227. +++ linux/drivers/sound/dmasound.c    Thu May 16 09:05:11 1996
  9228. @@ -1534,7 +1534,7 @@
  9229.      order++;
  9230.      a_size <<= 1;
  9231.      }
  9232. -    free_pages (obj, order);
  9233. +    free_pages ((unsigned long) obj, order);
  9234.  }
  9235.  
  9236.  static int AtaIrqInit(void)
  9237. diff -u --recursive --new-file pre2.0.4/linux/drivers/sound/soundcard.c linux/drivers/sound/soundcard.c
  9238. --- pre2.0.4/linux/drivers/sound/soundcard.c    Mon Apr 15 12:20:20 1996
  9239. +++ linux/drivers/sound/soundcard.c    Wed May 15 09:09:00 1996
  9240. @@ -440,11 +440,6 @@
  9241.  {
  9242.    int             i;
  9243.  
  9244. -  if (MOD_IN_USE)
  9245. -    {
  9246. -      return;
  9247. -    }
  9248. -
  9249.    if (chrdev_registered)
  9250.      module_unregister_chrdev (sound_major, "sound");
  9251.  
  9252. diff -u --recursive --new-file pre2.0.4/linux/fs/Config.in linux/fs/Config.in
  9253. --- pre2.0.4/linux/fs/Config.in    Mon May 13 23:02:49 1996
  9254. +++ linux/fs/Config.in    Wed May 15 09:47:27 1996
  9255. @@ -35,10 +35,11 @@
  9256.  tristate 'ISO9660 cdrom filesystem support' CONFIG_ISO9660_FS
  9257.  tristate 'OS/2 HPFS filesystem support (read only)' CONFIG_HPFS_FS
  9258.  tristate 'System V and Coherent filesystem support' CONFIG_SYSV_FS
  9259. -tristate 'Amiga FFS filesystem support (EXPERIMENTAL)' CONFIG_AFFS_FS
  9260. -if [ "$CONFIG_AFFS_FS" = "y" -o "$CONFIG_AFFS_FS" = "m" ]; then
  9261. -  define_bool CONFIG_AMIGA_PARTITION y
  9262. -fi
  9263. +# AFFS disabled until they can get that BYTE/WORD/LONG crap sorted out
  9264. +#tristate 'Amiga FFS filesystem support (EXPERIMENTAL)' CONFIG_AFFS_FS
  9265. +#if [ "$CONFIG_AFFS_FS" = "y" -o "$CONFIG_AFFS_FS" = "m" ]; then
  9266. +#  define_bool CONFIG_AMIGA_PARTITION y
  9267. +#fi
  9268.  tristate 'UFS filesystem support (read only)' CONFIG_UFS_FS
  9269.  if [ "$CONFIG_UFS_FS" != "n" ]; then
  9270.    bool "BSD disklabel (FreeBSD partition tables) support" CONFIG_BSD_DISKLABEL
  9271. diff -u --recursive --new-file pre2.0.4/linux/fs/affs/amigaffs.c linux/fs/affs/amigaffs.c
  9272. --- pre2.0.4/linux/fs/affs/amigaffs.c    Sat May 11 10:42:06 1996
  9273. +++ linux/fs/affs/amigaffs.c    Thu May 16 09:05:11 1996
  9274. @@ -1,7 +1,7 @@
  9275.  /*
  9276.   *  linux/fs/affs/amigaffs.c
  9277.   *
  9278. - *  (c) 1996  Hans-Joachim Widmaier - Modified for larger blocks.
  9279. + *  (c) 1996  Hans-Joachim Widmaier - rewritten
  9280.   *
  9281.   *  (C) 1993  Ray Burr - Amiga FFS filesystem.
  9282.   *
  9283. @@ -78,7 +78,7 @@
  9284.      retval  = -ENOENT;
  9285.      lock_super(startino->i_sb);
  9286.      while (1) {
  9287. -        pr_debug("AFFS: fix_hash_pred(): next key=%d, offset=%d\n", nextkey, startoffset);
  9288. +        pr_debug("AFFS: fix_hash_pred(): next key=%d, offset=%d\n",nextkey,startoffset);
  9289.          if (nextkey == 0)
  9290.              break;
  9291.          if (!(bh = affs_bread(startino->i_dev,nextkey,AFFS_I2BSIZE(startino))))
  9292. @@ -128,7 +128,7 @@
  9293.      while (1) {
  9294.          if (nextkey == 0)
  9295.              break;
  9296. -        pr_debug("AFFS: find_link_pred(): next key=%d\n", nextkey);
  9297. +        pr_debug("AFFS: find_link_pred(): next key=%d\n",nextkey);
  9298.          if (!(bh = affs_bread(startino->i_dev,nextkey,AFFS_I2BSIZE(startino))))
  9299.              break;
  9300.          if (affs_checksum_block(AFFS_I2BSIZE(startino),bh->b_data,&ptype,&stype)
  9301. diff -u --recursive --new-file pre2.0.4/linux/fs/affs/bitmap.c linux/fs/affs/bitmap.c
  9302. --- pre2.0.4/linux/fs/affs/bitmap.c    Tue May  7 16:22:35 1996
  9303. +++ linux/fs/affs/bitmap.c    Thu May 16 09:05:11 1996
  9304. @@ -185,7 +185,7 @@
  9305.                  z->z_ino      = 0;
  9306.                  z->z_zone_no  = zone;
  9307.                  pr_debug("  ++ found zone (%d) in bh %d at offset %d with %d free blocks\n",
  9308. -                     zone,(zone >> (sb->s_blocksize_bits - 8)),offs,free);
  9309. +                    zone,(zone >> (sb->s_blocksize_bits - 8)),offs,free);
  9310.                  break;
  9311.              }
  9312.              clear_bit(zone,sb->u.affs_sb.s_zonemap);
  9313. diff -u --recursive --new-file pre2.0.4/linux/fs/affs/dir.c linux/fs/affs/dir.c
  9314. --- pre2.0.4/linux/fs/affs/dir.c    Sun May 12 22:54:24 1996
  9315. +++ linux/fs/affs/dir.c    Thu May 16 09:05:11 1996
  9316. @@ -1,8 +1,8 @@
  9317.  /*
  9318.   *  linux/fs/affs/dir.c
  9319.   *
  9320. - *  (c) 1996  Hans-Joachim Widmaier - Modifications for larger blocks
  9321. - *        and hard links.
  9322. + *  (c) 1996  Hans-Joachim Widmaier - rewritten
  9323. + *
  9324.   *  (C) 1993  Ray Burr - Modified for Amiga FFS filesystem.
  9325.   *
  9326.   *  (C) 1992  Eric Youngdale Modified for ISO9660 filesystem.
  9327. diff -u --recursive --new-file pre2.0.4/linux/fs/affs/file.c linux/fs/affs/file.c
  9328. --- pre2.0.4/linux/fs/affs/file.c    Tue May  7 16:22:35 1996
  9329. +++ linux/fs/affs/file.c    Thu May 16 09:05:11 1996
  9330. @@ -1,7 +1,7 @@
  9331.  /*
  9332.   *  linux/fs/affs/file.c
  9333.   *
  9334. - *  (c) 1996  Hans-Joachim Widmaier - Rewritten
  9335. + *  (c) 1996  Hans-Joachim Widmaier - rewritten
  9336.   *
  9337.   *  (C) 1993  Ray Burr - Modified for Amiga FFS filesystem.
  9338.   *
  9339. @@ -78,7 +78,7 @@
  9340.      NULL,            /* ioctl - default */
  9341.      NULL,            /* mmap */
  9342.      NULL,            /* no special open is needed */
  9343. -    NULL,            /* release */
  9344. +    affs_release_file,    /* release */
  9345.      file_fsync        /* brute force, but works */
  9346.  };
  9347.  
  9348. @@ -98,7 +98,7 @@
  9349.      NULL,            /* readpage */
  9350.      NULL,            /* writepage */
  9351.      NULL,            /* bmap */
  9352. -    affs_truncate_ofs,    /* truncate */
  9353. +    affs_truncate,        /* truncate */
  9354.      NULL,            /* permission */
  9355.      NULL            /* smap */
  9356.  };
  9357. @@ -262,6 +262,145 @@
  9358.      return affs_bread(inode->i_dev,key,AFFS_I2BSIZE(inode));
  9359.  }
  9360.  
  9361. +struct buffer_head *
  9362. +affs_getblock_ofs(struct inode *inode, LONG block, LONG *blk_key)
  9363. +{
  9364. +    struct buffer_head    *bh;
  9365. +    struct buffer_head    *pbh;
  9366. +    struct buffer_head    *ebh;
  9367. +    LONG             key;
  9368. +    LONG             ext;
  9369. +    LONG             cnt, j, pt;
  9370. +
  9371. +    pr_debug("AFFS: getblock(%lu,%d)\n",inode->i_ino,block);
  9372. +
  9373. +    if (block < 0)
  9374. +        return NULL;
  9375. +    key = inode->i_ino;
  9376. +    pt  = T_SHORT;
  9377. +
  9378. +    ext = block / (AFFS_I2HSIZE(inode) - 24);
  9379. +    if (ext) {
  9380. +        if (ext > inode->u.affs_i.i_max_ext)
  9381. +            ext = inode->u.affs_i.i_max_ext;
  9382. +        if (ext) {
  9383. +            key    = inode->u.affs_i.i_ext[ext - 1];
  9384. +            block -= ext * AFFS_I2HSIZE(inode);
  9385. +            pt     = T_LIST;
  9386. +        }
  9387. +    }
  9388. +
  9389. +    pbh = NULL;
  9390. +    for (;;) {
  9391. +        bh = affs_bread(inode->i_dev,key,AFFS_I2BSIZE(inode));
  9392. +        if (!bh)
  9393. +            return NULL;
  9394. +        if (affs_checksum_block(AFFS_I2BSIZE(inode),bh->b_data,&cnt,&j) ||
  9395. +            cnt != pt || j != ST_FILE) {
  9396. +                printk("AFFS: getblock(): inode %d is not a valid %s\n",key,
  9397. +                   pt == T_SHORT ? "file header" : "extension block");
  9398. +            affs_brelse(bh);
  9399. +            return NULL;
  9400. +        }
  9401. +        j = htonl(((struct file_front *)bh->b_data)->block_count);
  9402. +        while (j < AFFS_I2HSIZE(inode) && j <= block) {
  9403. +            if (!pbh && inode->u.affs_i.i_lastblock >= 0) {
  9404. +                pbh = affs_getblock_ofs(inode,inode->u.affs_i.i_lastblock,&key);
  9405. +                if (!pbh) {
  9406. +                    printk("AFFS: getblock(): cannot get last block in file\n");
  9407. +                    break;
  9408. +                }
  9409. +            }
  9410. +            key = affs_new_data(inode);
  9411. +            if (!key)
  9412. +                break;
  9413. +            lock_super(inode->i_sb);
  9414. +            if (AFFS_BLOCK(bh->b_data,inode,j)) {
  9415. +                unlock_super(inode->i_sb);
  9416. +                printk("AFFS: getblock(): block already allocated\n");
  9417. +                affs_free_block(inode->i_sb,key);
  9418. +                j++;
  9419. +                continue;
  9420. +            }
  9421. +            AFFS_BLOCK(bh->b_data,inode,j) = ntohl(key);
  9422. +            unlock_super(inode->i_sb);
  9423. +            ebh = affs_bread(inode->i_dev,key,AFFS_I2BSIZE(inode));
  9424. +            if (!ebh) {
  9425. +                printk("AFFS: getblock(): cannot get block %d\n",key);
  9426. +                affs_free_block(inode->i_sb,key);
  9427. +                AFFS_BLOCK(bh->b_data,inode,j) = 0;
  9428. +                break;
  9429. +            }
  9430. +            inode->u.affs_i.i_lastblock++;
  9431. +            DATA_FRONT(ebh)->primary_type    = ntohl(T_DATA);
  9432. +            DATA_FRONT(ebh)->header_key      = ntohl(inode->i_ino);
  9433. +            DATA_FRONT(ebh)->sequence_number = ntohl(inode->u.affs_i.i_lastblock + 1);
  9434. +            DATA_FRONT(pbh)->data_size       = ntohl(AFFS_I2HSIZE(inode) - 24);
  9435. +            DATA_FRONT(pbh)->next_data       = ntohl(key);
  9436. +            affs_fix_checksum(AFFS_I2HSIZE(inode),pbh->b_data,5);
  9437. +            mark_buffer_dirty(pbh,0);
  9438. +            mark_buffer_dirty(ebh,0);
  9439. +            affs_brelse(pbh);
  9440. +            pbh = ebh;
  9441. +            j++;
  9442. +        }
  9443. +        if (pt == T_SHORT)
  9444. +            ((struct file_front *)bh->b_data)->first_data =
  9445. +                                AFFS_BLOCK(bh->b_data,inode,0);
  9446. +        ((struct file_front *)bh->b_data)->block_count = ntohl(j);
  9447. +        affs_fix_checksum(AFFS_I2BSIZE(inode),bh->b_data,5);
  9448. +        mark_buffer_dirty(bh,1);
  9449. +
  9450. +        if (block < j) {
  9451. +            if (pbh)
  9452. +                affs_brelse(pbh);
  9453. +            break;
  9454. +        }
  9455. +        if (j < AFFS_I2HSIZE(inode)) {
  9456. +            affs_brelse(bh);
  9457. +            return NULL;
  9458. +        }
  9459. +
  9460. +        block -= AFFS_I2HSIZE(inode);
  9461. +        key    = htonl(FILE_END(bh->b_data,inode)->extension);
  9462. +        if (!key) {
  9463. +            key = affs_new_header(inode);
  9464. +            if (!key) {
  9465. +                affs_brelse(bh);
  9466. +                return NULL;
  9467. +            }
  9468. +            ebh = affs_bread(inode->i_dev,key,AFFS_I2BSIZE(inode));
  9469. +            if (!ebh) {
  9470. +                affs_free_block(inode->i_sb,key);
  9471. +                return NULL;
  9472. +            }
  9473. +            ((struct file_front *)ebh->b_data)->primary_type = ntohl(T_LIST);
  9474. +            ((struct file_front *)ebh->b_data)->own_key      = ntohl(key);
  9475. +            FILE_END(ebh->b_data,inode)->secondary_type      = ntohl(ST_FILE);
  9476. +            FILE_END(ebh->b_data,inode)->parent              = ntohl(inode->i_ino);
  9477. +            affs_fix_checksum(AFFS_I2BSIZE(inode),ebh->b_data,5);
  9478. +            FILE_END(bh->b_data,inode)->extension = ntohl(key);
  9479. +            affs_fix_checksum(AFFS_I2BSIZE(inode),bh->b_data,5);
  9480. +            mark_buffer_dirty(bh,1);
  9481. +            affs_brelse(bh);
  9482. +            bh = ebh;
  9483. +        }
  9484. +        affs_brelse(bh);
  9485. +        pt = T_LIST;
  9486. +        if (ext < EXT_CACHE_SIZE - 1) {
  9487. +            inode->u.affs_i.i_ext[ext] = key;
  9488. +            inode->u.affs_i.i_max_ext  = ++ext;
  9489. +        }
  9490. +    }
  9491. +    key = htonl(AFFS_BLOCK(bh->b_data,inode,block));
  9492. +    affs_brelse(bh);
  9493. +    if (!key)
  9494. +        return NULL;
  9495. +    *blk_key = key;
  9496. +
  9497. +    return affs_bread(inode->i_dev,key,AFFS_I2BSIZE(inode));
  9498. +}
  9499. +
  9500.  /* This could be made static, regardless of what the former comment said.
  9501.   * You cannot directly read affs directories.
  9502.   */
  9503. @@ -395,101 +534,91 @@
  9504.  static int
  9505.  affs_file_write_ofs(struct inode *inode, struct file *filp, const char *buf, int count)
  9506.  {
  9507. -    pr_debug("AFFS: file_write_ofs(ino=%lu,pos=%lu,count=%d)\n",inode->i_ino,
  9508. -        (unsigned long)filp->f_pos,count);
  9509. -
  9510. -    return -ENOSPC;
  9511. -}
  9512. -
  9513. -void
  9514. -affs_truncate(struct inode *inode)
  9515. -{
  9516. +    off_t             pos;
  9517. +    int             written;
  9518. +    int             c;
  9519. +    int             blocksize;
  9520.      struct buffer_head    *bh;
  9521.      struct inode        *ino;
  9522. -    LONG     first;
  9523. -    LONG     block;
  9524. -    LONG     key;
  9525. -    LONG    *keyp;
  9526. -    LONG     ekey;
  9527. -    LONG     ptype, stype;
  9528. -    int     freethis;
  9529. -    int     ext;
  9530. +    char            *p;
  9531.  
  9532. -    pr_debug("AFFS: file_truncate(inode=%ld,size=%lu)\n",inode->i_ino,inode->i_size);
  9533. +    pr_debug("AFFS: file_write_ofs(ino=%lu,pos=%lu,count=%d)\n",inode->i_ino,
  9534. +        (unsigned long)filp->f_pos,count);
  9535.  
  9536. +    if (!inode) {
  9537. +        printk("AFFS: file_write(): inode=NULL\n");
  9538. +        return -EINVAL;
  9539. +    }
  9540.      ino = NULL;
  9541.      if (inode->u.affs_i.i_original) {
  9542.          ino = iget(inode->i_sb,inode->u.affs_i.i_original);
  9543.          if (!ino) {
  9544. -            printk("AFFS: truncate(): cannot follow link from %lu to %u\n",
  9545. +            printk("AFFS: could not follow link from inode %lu to %d\n",
  9546.                     inode->i_ino,inode->u.affs_i.i_original);
  9547. -            return;
  9548. +            return -EINVAL;
  9549.          }
  9550.          inode = ino;
  9551.      }
  9552. -    first = (inode->i_size + AFFS_I2BSIZE(inode) - 1) / AFFS_I2BSIZE(inode);
  9553. -    ekey  = inode->i_ino;
  9554. -    ext   = 0;
  9555. +    if (!S_ISREG(inode->i_mode)) {
  9556. +        printk("AFFS: file_write(): mode=%07o\n",inode->i_mode);
  9557. +        iput(inode);
  9558. +        return -EINVAL;
  9559. +    }
  9560. +    if (filp->f_flags & O_APPEND)
  9561. +        pos = inode->i_size;
  9562. +    else
  9563. +        pos = filp->f_pos;
  9564.  
  9565. -    while (ekey) {
  9566. -        if (!(bh = affs_bread(inode->i_dev,ekey,AFFS_I2BSIZE(inode)))) {
  9567. -            printk("AFFS: truncate(): Can't read block %d\n",ekey);
  9568. -            break;
  9569. -        }
  9570. -        ptype = htonl(((struct file_front *)bh->b_data)->primary_type);
  9571. -        stype = htonl(FILE_END(bh->b_data,inode)->secondary_type);
  9572. -        if (ekey == inode->i_ino && ptype == T_SHORT && stype == ST_LINKFILE &&
  9573. -            LINK_END(bh->b_data,inode)->original == 0) {
  9574. -            pr_debug("AFFS: truncate(): dumping link\n");
  9575. -            affs_brelse(bh);
  9576. -            break;
  9577. -        }
  9578. -        if (stype != ST_FILE || (ptype != T_SHORT && ptype != T_LIST)) {
  9579. -            printk("AFFS: truncate(): bad block (ptype=%d, stype=%d)\n",
  9580. -                    ptype,stype);
  9581. -            affs_brelse(bh);
  9582. +    bh        = NULL;
  9583. +    blocksize = AFFS_I2BSIZE(inode) - 24;
  9584. +    written   = 0;
  9585. +    while (written < count) {
  9586. +        bh = affs_getblock(inode,pos / blocksize);
  9587. +        if (!bh) {
  9588. +            if (!written)
  9589. +                written = -ENOSPC;
  9590.              break;
  9591.          }
  9592. -        /* Do not throw away file header */
  9593. -        freethis = first == 0 && ekey != inode->i_ino;
  9594. -        for ( block = first; block < AFFS_I2HSIZE(inode); block++) {
  9595. -            keyp = &AFFS_BLOCK(bh->b_data,inode,block);
  9596. -            key  = htonl(*keyp);
  9597. -            if (key) {
  9598. -                *keyp = 0;
  9599. -                affs_free_block(inode->i_sb,key);
  9600. -            } else {
  9601. -                block = AFFS_I2HSIZE(inode);
  9602. +        c = blocksize - (pos % blocksize);
  9603. +        if (c > count - written)
  9604. +            c = count - written;
  9605. +        if (c != blocksize && !buffer_uptodate(bh)) {
  9606. +            ll_rw_block(READ,1,&bh);
  9607. +            wait_on_buffer(bh);
  9608. +            if (!buffer_uptodate(bh)) {
  9609. +                affs_brelse(bh);
  9610. +                if (!written)
  9611. +                    written = -EIO;
  9612.                  break;
  9613.              }
  9614.          }
  9615. -        keyp = &GET_END_PTR(struct file_end,bh->b_data,AFFS_I2BSIZE(inode))->extension;
  9616. -        key  = htonl(*keyp);
  9617. -        if (first <= AFFS_I2HSIZE(inode)) {
  9618. -            ((struct file_front *)bh->b_data)->block_count = htonl(first);
  9619. -            first = 0;
  9620. -            *keyp = 0;
  9621. -        } else {
  9622. -            first -= AFFS_I2HSIZE(inode);
  9623. -        }
  9624. -        if (freethis) {        /* Don't bother fixing checksum */
  9625. -            affs_brelse(bh);
  9626. -            affs_free_block(inode->i_sb,ekey);
  9627. -        } else {
  9628. -            affs_fix_checksum(AFFS_I2BSIZE(inode),bh->b_data,5);
  9629. -            mark_buffer_dirty(bh,1);
  9630. -            affs_brelse(bh);
  9631. -        }
  9632. -        ekey = key;
  9633. +        p = (pos % blocksize) + bh->b_data + 24;
  9634. +        memcpy_fromfs(p,buf,c);
  9635. +        update_vm_cache(inode,pos,p,c);
  9636. +
  9637. +        pos     += c;
  9638. +        buf     += c;
  9639. +        written += c;
  9640. +        DATA_FRONT(bh)->data_size = ntohl(htonl(DATA_FRONT(bh)->data_size) + c);
  9641. +        affs_fix_checksum(AFFS_I2BSIZE(inode),bh->b_data,5);
  9642. +        mark_buffer_uptodate(bh,1);
  9643. +        mark_buffer_dirty(bh,0);
  9644. +        affs_brelse(bh);
  9645.      }
  9646. -    inode->u.affs_i.i_max_ext = 0;        /* invalidate cache */
  9647. +    if (pos > inode->i_size)
  9648. +        inode->i_size = pos;
  9649. +    filp->f_pos = pos;
  9650. +    inode->i_mtime = inode->i_ctime = CURRENT_TIME;
  9651. +    inode->i_dirt  = 1;
  9652.      iput(ino);
  9653. +    return written;
  9654.  }
  9655.  
  9656.  void
  9657. -affs_truncate_ofs(struct inode *inode)
  9658. +affs_truncate(struct inode *inode)
  9659.  {
  9660.      struct buffer_head    *bh;
  9661. +    struct buffer_head    *ebh;
  9662.      struct inode        *ino;
  9663.      LONG     first;
  9664.      LONG     block;
  9665. @@ -499,8 +628,10 @@
  9666.      LONG     ptype, stype;
  9667.      int     freethis;
  9668.      int     blocksize;
  9669. +    int     rem;
  9670. +    int     ext;
  9671.  
  9672. -    pr_debug("AFFS: file_truncate_ofs(inode=%ld,size=%lu)\n",inode->i_ino,inode->i_size);
  9673. +    pr_debug("AFFS: file_truncate(inode=%ld,size=%lu)\n",inode->i_ino,inode->i_size);
  9674.  
  9675.      ino = NULL;
  9676.      if (inode->u.affs_i.i_original) {
  9677. @@ -512,9 +643,25 @@
  9678.          }
  9679.          inode = ino;
  9680.      }
  9681. -    blocksize = AFFS_I2BSIZE(inode) - 24;
  9682. +    blocksize = AFFS_I2BSIZE(inode) - ((inode->i_sb->u.affs_sb.s_flags & SF_OFS) ? 24 : 0);
  9683.      first = (inode->i_size + blocksize - 1) / blocksize;
  9684. +    if (inode->u.affs_i.i_lastblock < first - 1) {
  9685. +        bh = affs_getblock(inode,first - 1);
  9686. +        if (!bh) {
  9687. +            printk("AFFS: truncate(): Cannot extend file\n");
  9688. +            inode->i_size = blocksize * (inode->u.affs_i.i_lastblock + 1);
  9689. +        } else if (inode->i_sb->u.affs_sb.s_flags & SF_OFS) {
  9690. +            rem = inode->i_size % blocksize;
  9691. +            DATA_FRONT(bh)->data_size = ntohl(rem ? rem : blocksize);
  9692. +            affs_fix_checksum(AFFS_I2BSIZE(inode),bh->b_data,5);
  9693. +            mark_buffer_dirty(bh,0);
  9694. +        }
  9695. +        affs_brelse(bh);
  9696. +        iput(ino);
  9697. +        return;
  9698. +    }
  9699.      ekey  = inode->i_ino;
  9700. +    ext   = 0;
  9701.  
  9702.      while (ekey) {
  9703.          if (!(bh = affs_bread(inode->i_dev,ekey,AFFS_I2BSIZE(inode)))) {
  9704. @@ -538,9 +685,8 @@
  9705.          /* Do not throw away file header */
  9706.          freethis = first == 0 && ekey != inode->i_ino;
  9707.          for ( block = first; block < AFFS_I2HSIZE(inode); block++) {
  9708. -            keyp  = &((struct file_front *)bh->b_data)->
  9709. -                 blocks[AFFS_I2HSIZE(inode) - 1 - block];
  9710. -            key   = htonl(*keyp);
  9711. +            keyp = &AFFS_BLOCK(bh->b_data,inode,block);
  9712. +            key  = htonl(*keyp);
  9713.              if (key) {
  9714.                  *keyp = 0;
  9715.                  affs_free_block(inode->i_sb,key);
  9716. @@ -555,6 +701,21 @@
  9717.              ((struct file_front *)bh->b_data)->block_count = htonl(first);
  9718.              first = 0;
  9719.              *keyp = 0;
  9720. +            if ((inode->i_sb->u.affs_sb.s_flags & SF_OFS) && first > 0) {
  9721. +                block = htonl(AFFS_BLOCK(bh->b_data,inode,first - 1));
  9722. +                if ((ebh = affs_bread(inode->i_dev,block,AFFS_I2BSIZE(inode)))) {
  9723. +                    if(!(affs_checksum_block(AFFS_I2BSIZE(inode),ebh->b_data,
  9724. +                         &ptype,NULL))) {
  9725. +                        rem = inode->i_size % blocksize;
  9726. +                        rem = ntohl(rem ? blocksize : rem);
  9727. +                        ((struct data_front *)ebh->b_data)->data_size = rem;
  9728. +                        ((struct data_front *)ebh->b_data)->next_data = 0;
  9729. +                        affs_fix_checksum(AFFS_I2BSIZE(inode),ebh->b_data,5);
  9730. +                        mark_buffer_dirty(ebh,1);
  9731. +                    }
  9732. +                    affs_brelse(ebh);
  9733. +                }
  9734. +            }
  9735.          } else {
  9736.              first -= AFFS_I2HSIZE(inode);
  9737.          }
  9738. @@ -568,19 +729,31 @@
  9739.          }
  9740.          ekey = key;
  9741.      }
  9742. -    inode->u.affs_i.i_max_ext = 0;        /* invalidate cache */
  9743. +    inode->u.affs_i.i_lastblock = ((inode->i_size + blocksize - 1) / blocksize) - 1;
  9744. +    inode->u.affs_i.i_max_ext   = 0;
  9745.      iput(ino);
  9746.  }
  9747.  
  9748.  static void
  9749.  affs_release_file(struct inode *inode, struct file *filp)
  9750.  {
  9751. +    struct affs_zone    *zone;
  9752. +
  9753. +    pr_debug("AFFS: release_file(ino=%lu)\n",inode->i_ino);
  9754. +
  9755.      if (filp->f_mode & 2) {        /* Free preallocated blocks */
  9756.          while (inode->u.affs_i.i_pa_cnt) {
  9757.              affs_free_block(inode->i_sb,
  9758.                      inode->u.affs_i.i_data[inode->u.affs_i.i_pa_next++]);
  9759.              inode->u.affs_i.i_pa_next &= MAX_PREALLOC - 1;
  9760.              inode->u.affs_i.i_pa_cnt--;
  9761. +        }
  9762. +        if (inode->u.affs_i.i_zone) {
  9763. +            lock_super(inode->i_sb);
  9764. +            zone = &inode->i_sb->u.affs_sb.s_zones[inode->u.affs_i.i_zone];
  9765. +            if (zone->z_ino == inode->i_ino)
  9766. +                zone->z_ino = 0;
  9767. +            unlock_super(inode->i_sb);
  9768.          }
  9769.      }
  9770.  }
  9771. diff -u --recursive --new-file pre2.0.4/linux/fs/affs/inode.c linux/fs/affs/inode.c
  9772. --- pre2.0.4/linux/fs/affs/inode.c    Sun May 12 10:16:07 1996
  9773. +++ linux/fs/affs/inode.c    Fri May 17 12:34:40 1996
  9774. @@ -1,7 +1,7 @@
  9775.  /*
  9776.   *  linux/fs/affs/inode.c
  9777.   *
  9778. - *  (c) 1996  Hans-Joachim Widmaier - Modified for larger blocks.
  9779. + *  (c) 1996  Hans-Joachim Widmaier - rewritten
  9780.   *
  9781.   *  (C) 1993  Ray Burr - Modified for Amiga FFS filesystem.
  9782.   * 
  9783. @@ -23,15 +23,16 @@
  9784.  #include <linux/locks.h>
  9785.  #include <linux/errno.h>
  9786.  #include <linux/genhd.h>
  9787. -#include <linux/major.h>
  9788.  #include <linux/amigaffs.h>
  9789. +#include <linux/major.h>
  9790.  #include <asm/system.h>
  9791.  #include <asm/segment.h>
  9792.  
  9793.  extern int *blk_size[];
  9794.  extern struct timezone sys_tz;
  9795.  
  9796. -void affs_put_super(struct super_block *sb)
  9797. +void
  9798. +affs_put_super(struct super_block *sb)
  9799.  {
  9800.      int     i;
  9801.  
  9802. @@ -58,7 +59,8 @@
  9803.      return;
  9804.  }
  9805.  
  9806. -static void affs_write_super(struct super_block *sb)
  9807. +static void
  9808. +affs_write_super(struct super_block *sb)
  9809.  {
  9810.      int     i, clean = 2;
  9811.  
  9812. @@ -92,7 +94,8 @@
  9813.      NULL            /* remount */
  9814.  };
  9815.  
  9816. -int affs_parent_ino(struct inode *dir)
  9817. +int
  9818. +affs_parent_ino(struct inode *dir)
  9819.  {
  9820.      int root_ino = (dir->i_sb->u.affs_sb.s_root_block);
  9821.  
  9822. @@ -107,9 +110,8 @@
  9823.  
  9824.  
  9825.  static int
  9826. -parse_options(char *options, uid_t *uid, gid_t *gid, int *mode,
  9827. -          int *reserved, int *root,    int *blocksize, char **prefix,
  9828. -          char *volume, unsigned long *mount_opts)
  9829. +parse_options(char *options, uid_t *uid, gid_t *gid, int *mode, int *reserved, int *root,
  9830. +        int *blocksize, char **prefix, char *volume, unsigned long *mount_opts)
  9831.  {
  9832.      char    *this_char, *value;
  9833.      int     f;
  9834. @@ -242,8 +244,7 @@
  9835.               || !strcmp (this_char, "usrquota"))
  9836.              ;
  9837.          else {
  9838. -            printk("AFFS: Unrecognized mount option %s\n",
  9839. -                   this_char);
  9840. +            printk("AFFS: Unrecognized mount option %s\n", this_char);
  9841.              return 0;
  9842.          }
  9843.      }
  9844. @@ -319,12 +320,12 @@
  9845.          num_bm = 4096;
  9846.      }
  9847.      for (blocksize = chksum; blocksize <= num_bm; blocksize <<= 1, size >>= 1) {
  9848. -        if (root_block < 0)
  9849. +            if (root_block < 0){
  9850.              if (MAJOR(dev) == FLOPPY_MAJOR)
  9851.                  s->u.affs_sb.s_root_block = size/4;
  9852.              else
  9853.              s->u.affs_sb.s_root_block = (reserved + size - 1) / 2;
  9854. -        else
  9855. +        }else
  9856.              s->u.affs_sb.s_root_block = root_block;
  9857.          pr_debug("Trying bs=%d bytes, root at %d, size=%d blocks (%d reserved)\n",
  9858.              blocksize,s->u.affs_sb.s_root_block,size,reserved);
  9859. @@ -461,9 +462,9 @@
  9860.              if (bb) {
  9861.                  if (affs_checksum_block(s->s_blocksize,bb->b_data,NULL,NULL) /*&&
  9862.                      !(s->s_flags & MS_RDONLY)*/) {
  9863. -                    printk("AFFS: Bitmap (%d,key=%lu) invalid - mounting %s read only.\n",
  9864. -                           mapidx, htonl(bm[i]),
  9865. -                           kdevname(dev));
  9866. +                    printk("AFFS: Bitmap (%d,key=%lu) invalid - "
  9867. +                           "mounting %s read only.\n",mapidx,htonl(bm[i]),
  9868. +                        kdevname(dev));
  9869.                      s->s_flags |= MS_RDONLY;
  9870.                  }
  9871.                  if (size <= s->s_blocksize * 8 - 32) {    /* last bitmap */
  9872. @@ -487,14 +488,14 @@
  9873.                  s->u.affs_sb.s_bitmap[mapidx].bm_size     = ptype;
  9874.                  s->u.affs_sb.s_bitmap[mapidx].bm_bh       = bb;
  9875.                  s->u.affs_sb.s_bitmap[mapidx].bm_free     =
  9876. -                  affs_count_free_bits(ptype/8,bb->b_data + 4);
  9877. +                        affs_count_free_bits(ptype / 8,bb->b_data + 4);
  9878.                  offset += ptype;
  9879.              } else {
  9880.                  printk("AFFS: Can't read bitmap.\n");
  9881.                  goto out;
  9882.              }
  9883.          }
  9884. -        key   = htonl(bm[stype]);   /* Next block of bitmap pointers */
  9885. +        key   = htonl(bm[stype]);        /* Next block of bitmap pointers    */
  9886.          ptype = 0;
  9887.          stype = s->s_blocksize / 4 - 1;
  9888.          affs_brelse(bh);
  9889. @@ -507,11 +508,10 @@
  9890.              bh = NULL;
  9891.      }
  9892.      if (mapidx != num_bm) {
  9893. -        printk("AFFS: Got only %d bitmap blocks, expected %d\n",
  9894. -               mapidx, num_bm);
  9895. +        printk("AFFS: Got only %d bitmap blocks, expected %d\n",mapidx,num_bm);
  9896.          goto out;
  9897.      }
  9898. -    s->u.affs_sb.s_num_zones = ((num_bm - 1) << (s->s_blocksize_bits - 8))+
  9899. +    s->u.affs_sb.s_num_zones = ((num_bm - 1) << (s->s_blocksize_bits - 8)) +
  9900.                     (s->u.affs_sb.s_bitmap[num_bm - 1].bm_size + 2047) / 2048;
  9901.  nobitmap:
  9902.      s->u.affs_sb.s_bm_count  = mapidx;
  9903. @@ -547,9 +547,9 @@
  9904.              s->u.affs_sb.s_bitmap[i].bm_bh = NULL;
  9905.          }
  9906.      }
  9907. +        
  9908.  
  9909. -
  9910. -    pr_debug("AFFS: s_flags=%lX\n", s->s_flags);
  9911. +    pr_debug("AFFS: s_flags=%lX\n",s->s_flags);
  9912.      return s;
  9913.  
  9914.   out: /* Kick out for various error conditions */
  9915. @@ -572,8 +572,8 @@
  9916.      ULONG         free;
  9917.      struct statfs     tmp;
  9918.  
  9919. -    pr_debug("AFFS: statfs() partsize=%d, reserved=%d\n",
  9920. -        sb->u.affs_sb.s_partition_size, sb->u.affs_sb.s_reserved);
  9921. +    pr_debug("AFFS: statfs() partsize=%d, reserved=%d\n",sb->u.affs_sb.s_partition_size,
  9922. +         sb->u.affs_sb.s_reserved);
  9923.  
  9924.      free          = affs_count_free_blocks(sb);
  9925.      tmp.f_type    = AFFS_SUPER_MAGIC;
  9926. @@ -606,7 +606,7 @@
  9927.      }
  9928.      if (affs_checksum_block(AFFS_I2BSIZE(inode),bh->b_data,&ptype,&stype) || ptype != T_SHORT) {
  9929.          printk("AFFS: read_inode(): checksum or type (ptype=%d) error on inode %d\n",
  9930. -               ptype, block);
  9931. +               ptype,block);
  9932.          affs_brelse(bh);
  9933.          return;
  9934.      }
  9935. @@ -615,18 +615,19 @@
  9936.      file_end   = GET_END_PTR(struct file_end, bh->b_data,AFFS_I2BSIZE(inode));
  9937.      prot       = (htonl(file_end->protect) & ~0x10) ^ FIBF_OWNER;
  9938.  
  9939. -    inode->u.affs_i.i_protect  = prot;
  9940. -    inode->u.affs_i.i_parent   = htonl(file_end->parent);
  9941. -    inode->u.affs_i.i_original = 0;    
  9942. -    inode->u.affs_i.i_zone     = 0;
  9943. -    inode->u.affs_i.i_hlink    = 0;
  9944. -    inode->u.affs_i.i_pa_cnt   = 0;
  9945. -    inode->u.affs_i.i_pa_next  = 0;
  9946. -    inode->u.affs_i.i_pa_last  = 0;
  9947. -    inode->u.affs_i.i_ext[0]   = 0;
  9948. -    inode->u.affs_i.i_max_ext  = 0;
  9949. -    inode->i_nlink             = 1;
  9950. -    inode->i_mode              = 0;
  9951. +    inode->u.affs_i.i_protect   = prot;
  9952. +    inode->u.affs_i.i_parent    = htonl(file_end->parent);
  9953. +    inode->u.affs_i.i_original  = 0;    
  9954. +    inode->u.affs_i.i_zone      = 0;
  9955. +    inode->u.affs_i.i_hlink     = 0;
  9956. +    inode->u.affs_i.i_pa_cnt    = 0;
  9957. +    inode->u.affs_i.i_pa_next   = 0;
  9958. +    inode->u.affs_i.i_pa_last   = 0;
  9959. +    inode->u.affs_i.i_ext[0]    = 0;
  9960. +    inode->u.affs_i.i_max_ext   = 0;
  9961. +    inode->u.affs_i.i_lastblock = -1;
  9962. +    inode->i_nlink              = 1;
  9963. +    inode->i_mode               = 0;
  9964.  
  9965.      if (inode->i_sb->u.affs_sb.s_flags & SF_SETMODE)
  9966.          inode->i_mode = inode->i_sb->u.affs_sb.s_mode;
  9967. @@ -691,6 +692,11 @@
  9968.          case ST_FILE:
  9969.              inode->i_mode |= S_IFREG;
  9970.              inode->i_size  = htonl(file_end->byte_size);
  9971. +            if (inode->i_sb->u.affs_sb.s_flags & SF_OFS)
  9972. +                block = AFFS_I2BSIZE(inode) - 24;
  9973. +            else
  9974. +                block = AFFS_I2BSIZE(inode);
  9975. +            inode->u.affs_i.i_lastblock = ((inode->i_size + block - 1) / block) - 1;
  9976.              break;
  9977.          case ST_SOFTLINK:
  9978.              inode->i_mode |= S_IFLNK;
  9979. @@ -709,10 +715,11 @@
  9980.      
  9981.      inode->i_op = NULL;
  9982.      if (S_ISREG(inode->i_mode)) {
  9983. -        if (inode->i_sb->u.affs_sb.s_flags & SF_OFS)
  9984. +        if (inode->i_sb->u.affs_sb.s_flags & SF_OFS) {
  9985.              inode->i_op = &affs_file_inode_operations_ofs;
  9986. -        else
  9987. +        } else {
  9988.              inode->i_op = &affs_file_inode_operations;
  9989. +        }
  9990.      } else if (S_ISDIR(inode->i_mode))
  9991.          inode->i_op = &affs_dir_inode_operations;
  9992.      else if (S_ISLNK(inode->i_mode))
  9993. @@ -768,8 +775,7 @@
  9994.  {
  9995.      int error;
  9996.  
  9997. -    pr_debug("AFFS: notify_change(%lu,0x%x)\n",
  9998. -        inode->i_ino,attr->ia_valid);
  9999. +    pr_debug("AFFS: notify_change(%lu,0x%x)\n",inode->i_ino,attr->ia_valid);
  10000.  
  10001.      error = inode_change_ok(inode,attr);
  10002.      if (error)
  10003. @@ -795,8 +801,7 @@
  10004.  void
  10005.  affs_put_inode(struct inode *inode)
  10006.  {
  10007. -    pr_debug("AFFS: put_inode(ino=%lu, nlink=%u)\n",
  10008. -        inode->i_ino,inode->i_nlink);
  10009. +    pr_debug("AFFS: put_inode(ino=%lu, nlink=%u)\n",inode->i_ino,inode->i_nlink);
  10010.      if (inode->i_nlink) {
  10011.          return;
  10012.      }
  10013. @@ -840,15 +845,16 @@
  10014.      inode->i_blksize = 0;
  10015.      inode->i_mtime   = inode->i_atime = inode->i_ctime = CURRENT_TIME;
  10016.  
  10017. -    inode->u.affs_i.i_original = 0;
  10018. -    inode->u.affs_i.i_parent   = dir->i_ino;
  10019. -    inode->u.affs_i.i_zone     = 0;
  10020. -    inode->u.affs_i.i_hlink    = 0;
  10021. -    inode->u.affs_i.i_pa_cnt   = 0;
  10022. -    inode->u.affs_i.i_pa_next  = 0;
  10023. -    inode->u.affs_i.i_pa_last  = 0;
  10024. -    inode->u.affs_i.i_ext[0]   = 0;
  10025. -    inode->u.affs_i.i_max_ext  = 0;
  10026. +    inode->u.affs_i.i_original  = 0;
  10027. +    inode->u.affs_i.i_parent    = dir->i_ino;
  10028. +    inode->u.affs_i.i_zone      = 0;
  10029. +    inode->u.affs_i.i_hlink     = 0;
  10030. +    inode->u.affs_i.i_pa_cnt    = 0;
  10031. +    inode->u.affs_i.i_pa_next   = 0;
  10032. +    inode->u.affs_i.i_pa_last   = 0;
  10033. +    inode->u.affs_i.i_ext[0]    = 0;
  10034. +    inode->u.affs_i.i_max_ext   = 0;
  10035. +    inode->u.affs_i.i_lastblock = -1;
  10036.  
  10037.      insert_inode_hash(inode);
  10038.  
  10039. @@ -864,12 +870,12 @@
  10040.      struct buffer_head    *link_bh;
  10041.      ULONG             hash;
  10042.  
  10043. -    pr_debug("AFFS: add_entry(dir=%lu,inode=%lu,\"%*s\",type=%ld\n",
  10044. -        dir->i_ino,inode->i_ino, len,name,type);
  10045. +    pr_debug("AFFS: add_entry(dir=%lu,inode=%lu,\"%*s\",type=%ld\n",dir->i_ino,inode->i_ino,
  10046. +        len,name,type);
  10047.  
  10048. -    dir_bh     = affs_bread(dir->i_dev,dir->i_ino,AFFS_I2BSIZE(dir));
  10049. -    inode_bh   = affs_bread(inode->i_dev,inode->i_ino,AFFS_I2BSIZE(inode));
  10050. -    link_bh    = NULL;
  10051. +    dir_bh      = affs_bread(dir->i_dev,dir->i_ino,AFFS_I2BSIZE(dir));
  10052. +    inode_bh    = affs_bread(inode->i_dev,inode->i_ino,AFFS_I2BSIZE(inode));
  10053. +    link_bh     = NULL;
  10054.      if (!dir_bh || !inode_bh) {
  10055.          affs_brelse(dir_bh);
  10056.          affs_brelse(inode_bh);
  10057. @@ -896,12 +902,12 @@
  10058.  
  10059.      lock_super(inode->i_sb);
  10060.      DIR_END(inode_bh->b_data,inode)->hash_chain = 
  10061. -             ((struct dir_front *)dir_bh->b_data)->hashtable[hash];
  10062. +                ((struct dir_front *)dir_bh->b_data)->hashtable[hash];
  10063.      ((struct dir_front *)dir_bh->b_data)->hashtable[hash] = ntohl(inode->i_ino);
  10064.      if (link_bh) {
  10065.          LINK_END(inode_bh->b_data,inode)->original   = ntohl(link->i_ino);
  10066.          LINK_END(inode_bh->b_data,inode)->link_chain = 
  10067. -                    FILE_END(link_bh->b_data,link)->link_chain;
  10068. +                        FILE_END(link_bh->b_data,link)->link_chain;
  10069.          FILE_END(link_bh->b_data,link)->link_chain   = ntohl(inode->i_ino);
  10070.          affs_fix_checksum(AFFS_I2BSIZE(link),link_bh->b_data,5);
  10071.          link->i_version = ++event;
  10072. diff -u --recursive --new-file pre2.0.4/linux/fs/affs/namei.c linux/fs/affs/namei.c
  10073. --- pre2.0.4/linux/fs/affs/namei.c    Sat May 11 10:42:06 1996
  10074. +++ linux/fs/affs/namei.c    Thu May 16 09:05:11 1996
  10075. @@ -1,7 +1,7 @@
  10076.  /*
  10077.   *  linux/fs/affs/namei.c
  10078.   *
  10079. - *  (c) 1996  Hans-Joachim Widmaier - Heavily hacked up.
  10080. + *  (c) 1996  Hans-Joachim Widmaier - rewritten
  10081.   *
  10082.   *  (C) 1993  Ray Burr - Modified for Amiga FFS filesystem.
  10083.   *
  10084. @@ -235,9 +235,13 @@
  10085.          iput (dir);
  10086.          return -ENOSPC;
  10087.      }
  10088. -    inode->i_op   = &affs_file_inode_operations;
  10089.      inode->i_mode = mode;
  10090. -    error         = affs_add_entry(dir,NULL,inode,name,len,ST_FILE);
  10091. +    if (dir->i_sb->u.affs_sb.s_flags & SF_OFS)
  10092. +        inode->i_op = &affs_file_inode_operations_ofs;
  10093. +    else
  10094. +        inode->i_op = &affs_file_inode_operations;
  10095. +
  10096. +    error = affs_add_entry(dir,NULL,inode,name,len,ST_FILE);
  10097.      if (error) {
  10098.          iput(dir);
  10099.          inode->i_nlink = 0;
  10100. @@ -603,7 +607,7 @@
  10101.          if (affs_parent_ino(old_inode) != old_dir->i_ino)
  10102.              goto end_rename;
  10103.      }
  10104. -    /* Unlink destination if existent */
  10105. +    /* Unlink destination if existant */
  10106.      if (new_inode) {
  10107.          if ((retval = affs_fix_hash_pred(new_dir,affs_hash_name(new_name,new_len,
  10108.                                           AFFS_I2FSTYPE(new_dir),AFFS_I2HSIZE(new_dir)) + 6,
  10109. diff -u --recursive --new-file pre2.0.4/linux/fs/affs/symlink.c linux/fs/affs/symlink.c
  10110. --- pre2.0.4/linux/fs/affs/symlink.c    Tue May  7 16:22:36 1996
  10111. +++ linux/fs/affs/symlink.c    Thu May 16 09:05:11 1996
  10112. @@ -1,7 +1,7 @@
  10113.  /*
  10114.   *  linux/fs/affs/symlink.c
  10115.   *
  10116. - *  1995  Hans-Joachim Widmaier - modified for AFFS.
  10117. + *  1995  Hans-Joachim Widmaier - modified for affs.
  10118.   *
  10119.   *  Copyright (C) 1991, 1992  Linus Torvalds
  10120.   *
  10121. @@ -15,7 +15,6 @@
  10122.  #include <linux/stat.h>
  10123.  #include <linux/affs_fs.h>
  10124.  #include <linux/amigaffs.h>
  10125. -
  10126.  #include <asm/segment.h>
  10127.  
  10128.  #define MIN(a,b) (((a) < (b)) ? (a) : (b))
  10129. diff -u --recursive --new-file pre2.0.4/linux/fs/locks.c linux/fs/locks.c
  10130. --- pre2.0.4/linux/fs/locks.c    Wed May 15 11:01:15 1996
  10131. +++ linux/fs/locks.c    Wed May 15 11:22:04 1996
  10132. @@ -76,9 +76,15 @@
  10133.   *  flock() and fcntl().
  10134.   *  Andy Walker (andy@lysaker.kvaerner.no), April 29, 1996.
  10135.   *
  10136. - *    BUG: MUST DISALLOW MANDATORY LOCK ON NFS/SMB/NCP FILE SYSTEM 
  10137. - *    TO MATCH SYS5.4 SEMANTICS.
  10138. + *  Allow only one type of locking scheme (F_POSIX or F_FLOCK) to be in use
  10139. + *  for a given file at a time. Changed the CONFIG_MANDATORY_OPTION scheme to
  10140. + *  guarantee sensible behaviour in the case where file system modules might
  10141. + *  be compiled with different options than the kernel itself.
  10142. + *  Andy Walker (andy@lysaker.kvaerner.no), May 15, 1996.
  10143.   *
  10144. + *  TODO: Do not honour mandatory locks on remote file systems. This matches
  10145. + *        the SVR4 semantics and neatly sidesteps a pile of awkward issues that
  10146. + *        would otherwise have to be addressed.
  10147.   */
  10148.  
  10149.  #include <linux/config.h>
  10150. @@ -107,9 +113,11 @@
  10151.                 unsigned int wait);
  10152.  static int posix_lock_file(struct file *filp, struct file_lock *caller,
  10153.                 unsigned int wait);
  10154. -static int locks_deadlock(struct task_struct *my_task,
  10155. -              struct task_struct *blocked_task);
  10156. +static int posix_locks_deadlock(struct task_struct *my_task,
  10157. +                struct task_struct *blocked_task);
  10158.  static int locks_overlap(struct file_lock *fl1, struct file_lock *fl2);
  10159. +static void posix_remove_locks(struct file_lock **before, struct task_struct *task);
  10160. +static void flock_remove_locks(struct file_lock **before, struct file *filp);
  10161.  
  10162.  static struct file_lock *locks_alloc_lock(struct file_lock *fl);
  10163.  static void locks_insert_lock(struct file_lock **pos, struct file_lock *fl);
  10164. @@ -212,16 +220,19 @@
  10165.      if (!filp->f_inode || !posix_make_lock(filp, &file_lock, &flock))
  10166.          return (-EINVAL);
  10167.  
  10168. -    for (fl = filp->f_inode->i_flock; fl != NULL; fl = fl->fl_next) {
  10169. -        if (posix_locks_conflict(&file_lock, fl)) {
  10170. -            flock.l_pid = fl->fl_owner->pid;
  10171. -            flock.l_start = fl->fl_start;
  10172. -            flock.l_len = fl->fl_end == OFFSET_MAX ? 0 :
  10173. -                fl->fl_end - fl->fl_start + 1;
  10174. -            flock.l_whence = 0;
  10175. -            flock.l_type = fl->fl_type;
  10176. -            memcpy_tofs(l, &flock, sizeof(flock));
  10177. -            return (0);
  10178. +    if ((fl = filp->f_inode->i_flock) && (fl->fl_flags & F_POSIX)) { 
  10179. +        while (fl != NULL) {
  10180. +            if (posix_locks_conflict(&file_lock, fl)) {
  10181. +                flock.l_pid = fl->fl_owner->pid;
  10182. +                flock.l_start = fl->fl_start;
  10183. +                flock.l_len = fl->fl_end == OFFSET_MAX ? 0 :
  10184. +                    fl->fl_end - fl->fl_start + 1;
  10185. +                flock.l_whence = 0;
  10186. +                flock.l_type = fl->fl_type;
  10187. +                memcpy_tofs(l, &flock, sizeof(flock));
  10188. +                return (0);
  10189. +            }
  10190. +            fl = fl->fl_next;
  10191.          }
  10192.      }
  10193.  
  10194. @@ -313,17 +324,41 @@
  10195.  void locks_remove_locks(struct task_struct *task, struct file *filp)
  10196.  {
  10197.      struct file_lock *fl;
  10198. -    struct file_lock **before;
  10199.  
  10200.      /* For POSIX locks we free all locks on this file for the given task.
  10201.       * For FLOCK we only free locks on this *open* file if it is the last
  10202.       * close on that file.
  10203.       */
  10204. -    before = &filp->f_inode->i_flock;
  10205. +    if ((fl = filp->f_inode->i_flock) != NULL) {
  10206. +        if (fl->fl_flags & F_POSIX)
  10207. +            posix_remove_locks(&filp->f_inode->i_flock, task);
  10208. +        else
  10209. +            flock_remove_locks(&filp->f_inode->i_flock, filp);
  10210. +    }
  10211. +
  10212. +    return;
  10213. +}
  10214. +
  10215. +static void posix_remove_locks(struct file_lock **before, struct task_struct *task)
  10216. +{
  10217. +    struct file_lock *fl;
  10218. +
  10219.      while ((fl = *before) != NULL) {
  10220. -        if (((fl->fl_flags & F_POSIX) && (fl->fl_owner == task)) ||
  10221. -            ((fl->fl_flags & F_FLOCK) && (fl->fl_file == filp) &&
  10222. -             (filp->f_count == 1)))
  10223. +        if (fl->fl_owner == task)
  10224. +            locks_delete_lock(before, 0);
  10225. +        else
  10226. +            before = &fl->fl_next;
  10227. +    }
  10228. +
  10229. +    return;
  10230. +}
  10231. +
  10232. +static void flock_remove_locks(struct file_lock **before, struct file *filp)
  10233. +{
  10234. +    struct file_lock *fl;
  10235. +
  10236. +    while ((fl = *before) != NULL) {
  10237. +        if ((fl->fl_file == filp) && (filp->f_count == 1))
  10238.              locks_delete_lock(before, 0);
  10239.          else
  10240.              before = &fl->fl_next;
  10241. @@ -358,17 +393,22 @@
  10242.      return (0);
  10243.  }
  10244.  
  10245. -#ifdef CONFIG_LOCK_MANDATORY    
  10246.  int locks_mandatory_locked(struct inode *inode)
  10247.  {
  10248. +#ifdef CONFIG_LOCK_MANDATORY    
  10249.      struct file_lock *fl;
  10250.  
  10251.      /* Search the lock list for this inode for any POSIX locks.
  10252.       */
  10253. -    for (fl = inode->i_flock; fl != NULL; fl = fl->fl_next) {
  10254. -        if ((fl->fl_flags & F_POSIX) && (fl->fl_owner != current))
  10255. +    if ((fl = inode->i_flock) && (fl->fl_flags & F_FLOCK))
  10256. +        return (0);
  10257. +    
  10258. +    while (fl != NULL) {
  10259. +        if (fl->fl_owner != current)
  10260.              return (-EAGAIN);
  10261. +        fl = fl->fl_next;
  10262.      }
  10263. +#endif
  10264.      return (0);
  10265.  }
  10266.  
  10267. @@ -376,47 +416,53 @@
  10268.               struct file *filp, unsigned int offset,
  10269.               unsigned int count)
  10270.  {
  10271. +#ifdef CONFIG_LOCK_MANDATORY    
  10272.      struct file_lock *fl;
  10273.  
  10274.  repeat:
  10275. +    /* Check that there are locks, and that they're not F_FLOCK locks.
  10276. +     */
  10277. +    if ((fl = inode->i_flock) && (fl->fl_flags & F_FLOCK))
  10278. +        return (0);
  10279. +    
  10280.      /*
  10281.       * Search the lock list for this inode for locks that conflict with
  10282.       * the proposed read/write.
  10283.       */
  10284. -    for (fl = inode->i_flock; fl != NULL; fl = fl->fl_next) {
  10285. -        if ((fl->fl_flags & F_FLOCK) ||
  10286. -            ((fl->fl_flags & F_POSIX) && (fl->fl_owner == current)))
  10287. -            continue;
  10288. -        if (fl->fl_end < offset ||
  10289. -            fl->fl_start >= offset + count)
  10290. -            continue;
  10291. +    while (fl != NULL) {
  10292. +        if (fl->fl_owner == current ||
  10293. +            fl->fl_end < offset || fl->fl_start >= offset + count)
  10294. +            goto next_lock;
  10295. +
  10296.          /*
  10297. -         * Block for writes against a "read" lock, and both reads and
  10298. -         * writes against a "write" lock.
  10299. +         * Block for writes against a "read" lock,
  10300. +         * and both reads and writes against a "write" lock.
  10301.           */
  10302. -        if (read_write == FLOCK_VERIFY_WRITE ||
  10303. -            fl->fl_type == F_WRLCK) {
  10304. +        if ((read_write == FLOCK_VERIFY_WRITE) ||
  10305. +            (fl->fl_type == F_WRLCK)) {
  10306.              if (filp && (filp->f_flags & O_NONBLOCK))
  10307.                  return (-EAGAIN);
  10308.              if (current->signal & ~current->blocked)
  10309.                  return (-ERESTARTSYS);
  10310. -            if (locks_deadlock(current, fl->fl_owner))
  10311. +            if (posix_locks_deadlock(current, fl->fl_owner))
  10312.                  return (-EDEADLOCK);
  10313.              interruptible_sleep_on(&fl->fl_wait);
  10314.              if (current->signal & ~current->blocked)
  10315.                  return (-ERESTARTSYS);
  10316.              /*
  10317. -             * If we've been sleeping someone might have changed
  10318. -             * the permissions behind our back.
  10319. +             * If we've been sleeping someone might have
  10320. +             * changed the permissions behind our back.
  10321.               */
  10322.              if ((inode->i_mode & (S_ISGID | S_IXGRP)) != S_ISGID)
  10323.                  break;
  10324.              goto repeat;
  10325.          }
  10326. +    next_lock:
  10327. +        fl = fl->fl_next;
  10328.      }
  10329. +#endif
  10330.      return (0);
  10331.  }
  10332. -#endif
  10333.  
  10334.  /* Verify a "struct flock" and copy it to a "struct file_lock" as a POSIX
  10335.   * style lock.
  10336. @@ -500,7 +546,7 @@
  10337.      fl->fl_start = 0;
  10338.      fl->fl_end = OFFSET_MAX;
  10339.      fl->fl_file = filp;
  10340. -    fl->fl_owner = current;
  10341. +    fl->fl_owner = NULL;
  10342.      fl->fl_wait = NULL;        /* just for cleanliness */
  10343.      
  10344.      return (1);
  10345. @@ -514,8 +560,7 @@
  10346.      /* POSIX locks owned by the same process do not conflict with
  10347.       * each other.
  10348.       */
  10349. -    if ((sys_fl->fl_flags & F_POSIX) &&
  10350. -        (caller_fl->fl_owner == sys_fl->fl_owner))
  10351. +    if (caller_fl->fl_owner == sys_fl->fl_owner)
  10352.          return (0);
  10353.  
  10354.      return (locks_conflict(caller_fl, sys_fl));
  10355. @@ -529,8 +574,7 @@
  10356.      /* FLOCK locks referring to the same filp do not conflict with
  10357.       * each other.
  10358.       */
  10359. -    if ((sys_fl->fl_flags & F_FLOCK) &&
  10360. -        (caller_fl->fl_file == sys_fl->fl_file))
  10361. +    if (caller_fl->fl_file == sys_fl->fl_file)
  10362.          return (0);
  10363.  
  10364.      return (locks_conflict(caller_fl, sys_fl));
  10365. @@ -577,8 +621,8 @@
  10366.   * with blocked_task equal to that queue's owner, until either blocked_task
  10367.   * isn't found, or blocked_task is found on a queue owned by my_task.
  10368.   */
  10369. -static int locks_deadlock(struct task_struct *my_task,
  10370. -              struct task_struct *blocked_task)
  10371. +static int posix_locks_deadlock(struct task_struct *my_task,
  10372. +                struct task_struct *blocked_task)
  10373.  {
  10374.      struct wait_queue *dlock_wait;
  10375.      struct file_lock *fl;
  10376. @@ -604,9 +648,8 @@
  10377.      return (0);
  10378.  }
  10379.  
  10380. -/* Try to create a FLOCK lock on filp. We rely on FLOCK locks being sorted
  10381. - * first in an inode's lock list, and always insert new locks at the head
  10382. - * of the list.
  10383. +/* Try to create a FLOCK lock on filp. We always insert new locks at
  10384. + * the head of the list.
  10385.   */
  10386.  static int flock_lock_file(struct file *filp, struct file_lock *caller,
  10387.                 unsigned int wait)
  10388. @@ -616,11 +659,12 @@
  10389.      struct file_lock **before;
  10390.      int change = 0;
  10391.  
  10392. -    /* This a compact little algorithm based on us always placing FLOCK
  10393. -     * locks at the front of the list.
  10394. -     */
  10395.      before = &filp->f_inode->i_flock;
  10396. -    while ((fl = *before) && (fl->fl_flags & F_FLOCK)) {
  10397. +
  10398. +    if ((fl = *before) && (fl->fl_flags & F_POSIX))
  10399. +        return (-EBUSY);
  10400. +
  10401. +    while ((fl = *before) != NULL) {
  10402.          if (caller->fl_file == fl->fl_file) {
  10403.              if (caller->fl_type == fl->fl_type)
  10404.                  return (0);
  10405. @@ -638,12 +682,18 @@
  10406.          return (0);
  10407.      if ((new_fl = locks_alloc_lock(caller)) == NULL)
  10408.          return (-ENOLCK);
  10409. - repeat:
  10410. -    for (fl = filp->f_inode->i_flock; fl != NULL; fl = fl->fl_next) {
  10411. -        if (!flock_locks_conflict(new_fl, fl))
  10412. -            continue;
  10413. -        
  10414. -        if (wait) {
  10415. +repeat:
  10416. +    if ((fl = filp->f_inode->i_flock) && (fl->fl_flags & F_POSIX)) {
  10417. +        locks_free_lock(new_fl);
  10418. +        return (-EBUSY);
  10419. +    }
  10420. +
  10421. +    while (fl != NULL) {
  10422. +        if (flock_locks_conflict(new_fl, fl)) {
  10423. +            if (!wait) {
  10424. +                locks_free_lock(new_fl);
  10425. +                return (-EAGAIN);
  10426. +            }
  10427.              if (current->signal & ~current->blocked) {
  10428.                  /* Note: new_fl is not in any queue at this
  10429.                   * point, so we must use locks_free_lock()
  10430. @@ -653,14 +703,6 @@
  10431.                  locks_free_lock(new_fl);
  10432.                  return (-ERESTARTSYS);
  10433.              }
  10434. -            /* Try to avoid deadlocks due to pathological programs that
  10435. -             * mix calls to flock() and fcntl(). Return EAGAIN, because
  10436. -             * EDEADLOCK isn't a documented return value for flock().
  10437. -             */
  10438. -            if (locks_deadlock(new_fl->fl_owner, fl->fl_owner)) {
  10439. -                locks_free_lock(new_fl);
  10440. -                return (-EAGAIN);
  10441. -            }
  10442.              locks_insert_block(fl, new_fl);
  10443.              interruptible_sleep_on(&new_fl->fl_wait);
  10444.              wake_up(&new_fl->fl_wait);
  10445. @@ -677,9 +719,7 @@
  10446.              }
  10447.              goto repeat;
  10448.          }
  10449. -        
  10450. -        locks_free_lock(new_fl);
  10451. -        return (-EAGAIN);
  10452. +        fl = fl->fl_next;
  10453.      }
  10454.      locks_insert_lock(&filp->f_inode->i_flock, new_fl);
  10455.      return (0);
  10456. @@ -707,22 +747,25 @@
  10457.      struct file_lock **before;
  10458.      int added = 0;
  10459.  
  10460. -    if (caller->fl_type != F_UNLCK) {
  10461.  repeat:
  10462. -        for (fl = filp->f_inode->i_flock; fl != NULL; fl = fl->fl_next) {
  10463. -            if (!posix_locks_conflict(caller, fl))
  10464. -                continue;
  10465. -            if (wait) {
  10466. +    if ((fl = filp->f_inode->i_flock) && (fl->fl_flags & F_FLOCK))
  10467. +        return (-EBUSY);
  10468. +
  10469. +    if (caller->fl_type != F_UNLCK) {
  10470. +        while (fl != NULL) {
  10471. +            if (posix_locks_conflict(caller, fl)) {
  10472. +                if (!wait)
  10473. +                    return (-EAGAIN);
  10474.                  if (current->signal & ~current->blocked)
  10475.                      return (-ERESTARTSYS);
  10476. -                if (locks_deadlock(caller->fl_owner, fl->fl_owner))
  10477. +                if (posix_locks_deadlock(caller->fl_owner, fl->fl_owner))
  10478.                      return (-EDEADLOCK);
  10479.                  interruptible_sleep_on(&fl->fl_wait);
  10480.                  if (current->signal & ~current->blocked)
  10481.                      return (-ERESTARTSYS);
  10482.                  goto repeat;
  10483.              }
  10484. -            return (-EAGAIN);
  10485. +            fl = fl->fl_next;
  10486.            }
  10487.        }
  10488.      /*
  10489. @@ -733,8 +776,7 @@
  10490.  
  10491.      /* First skip FLOCK locks and locks owned by other processes.
  10492.       */
  10493. -    while ((fl = *before) && ((fl->fl_flags & F_FLOCK) ||
  10494. -                  (caller->fl_owner != fl->fl_owner))) {
  10495. +    while ((fl = *before) && (caller->fl_owner != fl->fl_owner)) {
  10496.          before = &fl->fl_next;
  10497.      }
  10498.      
  10499. @@ -956,7 +998,8 @@
  10500.      }
  10501.      p += sprintf(p, "%s ", (fl->fl_type == F_RDLCK) ? "READ " : "WRITE");
  10502.      p += sprintf(p, "%d %s:%ld %ld %ld ",
  10503. -             fl->fl_owner->pid, kdevname(fl->fl_file->f_inode->i_dev),
  10504. +             fl->fl_owner ? fl->fl_owner->pid : 0,
  10505. +             kdevname(fl->fl_file->f_inode->i_dev),
  10506.               fl->fl_file->f_inode->i_ino, fl->fl_start,
  10507.               fl->fl_end);
  10508.      p += sprintf(p, "%08lx %08lx %08lx %08lx %08lx\n%d:%s",
  10509. diff -u --recursive --new-file pre2.0.4/linux/fs/ncpfs/sock.c linux/fs/ncpfs/sock.c
  10510. --- pre2.0.4/linux/fs/ncpfs/sock.c    Fri Apr 19 10:08:01 1996
  10511. +++ linux/fs/ncpfs/sock.c    Thu May 16 16:35:42 1996
  10512. @@ -41,7 +41,7 @@
  10513.          msg.msg_namelen   = 0;
  10514.          if (addr_len)
  10515.                  msg.msg_namelen = *addr_len;
  10516. -        msg.msg_accrights = NULL;
  10517. +        msg.msg_control = NULL;
  10518.          msg.msg_iov       = &iov;
  10519.          msg.msg_iovlen    = 1;
  10520.  
  10521. @@ -61,7 +61,7 @@
  10522.  
  10523.          msg.msg_name      = (void *)sa;
  10524.          msg.msg_namelen   = addr_len;
  10525. -        msg.msg_accrights = NULL;
  10526. +        msg.msg_control = NULL;
  10527.          msg.msg_iov       = &iov;
  10528.          msg.msg_iovlen    = 1;
  10529.  
  10530. diff -u --recursive --new-file pre2.0.4/linux/fs/nfs/nfsroot.c linux/fs/nfs/nfsroot.c
  10531. --- pre2.0.4/linux/fs/nfs/nfsroot.c    Tue May  7 16:22:36 1996
  10532. +++ linux/fs/nfs/nfsroot.c    Thu May 16 16:35:42 1996
  10533. @@ -580,7 +580,7 @@
  10534.      msg.msg_name = NULL;
  10535.      msg.msg_iov = &iov;
  10536.      msg.msg_iovlen = 1;
  10537. -    msg.msg_accrights = NULL;
  10538. +    msg.msg_control = NULL;
  10539.      result = sock->ops->sendmsg(sock, &msg, size, 0, 0);
  10540.      set_fs(oldfs);
  10541.      return (result != size);
  10542. @@ -604,7 +604,7 @@
  10543.      msg.msg_name = NULL;
  10544.      msg.msg_iov = &iov;
  10545.      msg.msg_iovlen = 1;
  10546. -    msg.msg_accrights = NULL;
  10547. +    msg.msg_control = NULL;
  10548.      msg.msg_namelen = 0;
  10549.      result = sock->ops->recvmsg(sock, &msg, size, O_NONBLOCK, 0, &msg.msg_namelen);
  10550.      set_fs(oldfs);
  10551. diff -u --recursive --new-file pre2.0.4/linux/fs/nfs/rpcsock.c linux/fs/nfs/rpcsock.c
  10552. --- pre2.0.4/linux/fs/nfs/rpcsock.c    Mon Apr  8 19:01:45 1996
  10553. +++ linux/fs/nfs/rpcsock.c    Thu May 16 16:35:42 1996
  10554. @@ -115,7 +115,7 @@
  10555.      msg.msg_iovlen    = nr;
  10556.      msg.msg_name    = sap;
  10557.      msg.msg_namelen = salen;
  10558. -    msg.msg_accrights = NULL;
  10559. +    msg.msg_control = NULL;
  10560.  
  10561.      oldfs = get_fs();
  10562.      set_fs(get_ds());
  10563. @@ -142,7 +142,7 @@
  10564.      msg.msg_iovlen    = nr;
  10565.      msg.msg_name    = &sa;
  10566.      msg.msg_namelen = sizeof(sa);
  10567. -    msg.msg_accrights = NULL;
  10568. +    msg.msg_control = NULL;
  10569.  
  10570.      oldfs = get_fs();
  10571.      set_fs(get_ds());
  10572. diff -u --recursive --new-file pre2.0.4/linux/fs/read_write.c linux/fs/read_write.c
  10573. --- pre2.0.4/linux/fs/read_write.c    Wed May 15 11:01:15 1996
  10574. +++ linux/fs/read_write.c    Thu May 16 16:35:42 1996
  10575. @@ -180,7 +180,7 @@
  10576.          return -EOPNOTSUPP;
  10577.      msg.msg_name = NULL;
  10578.      msg.msg_namelen = 0;
  10579. -    msg.msg_accrights = NULL;
  10580. +    msg.msg_control = NULL;
  10581.      msg.msg_iov = (struct iovec *) iov;
  10582.      msg.msg_iovlen = count;
  10583.  
  10584. diff -u --recursive --new-file pre2.0.4/linux/fs/smbfs/sock.c linux/fs/smbfs/sock.c
  10585. --- pre2.0.4/linux/fs/smbfs/sock.c    Fri Apr 12 15:52:05 1996
  10586. +++ linux/fs/smbfs/sock.c    Thu May 16 16:35:42 1996
  10587. @@ -37,7 +37,7 @@
  10588.          msg.msg_namelen   = 0;
  10589.          if (addr_len)
  10590.                  msg.msg_namelen = *addr_len;
  10591. -        msg.msg_accrights = NULL;
  10592. +        msg.msg_control = NULL;
  10593.          msg.msg_iov       = &iov;
  10594.          msg.msg_iovlen    = 1;
  10595.  
  10596. @@ -53,7 +53,7 @@
  10597.  
  10598.          msg.msg_name      = NULL;
  10599.          msg.msg_namelen   = 0;
  10600. -        msg.msg_accrights = NULL;
  10601. +        msg.msg_control = NULL;
  10602.          msg.msg_iov       = &iov;
  10603.          msg.msg_iovlen    = 1;
  10604.  
  10605. diff -u --recursive --new-file pre2.0.4/linux/include/asm-alpha/irq.h linux/include/asm-alpha/irq.h
  10606. --- pre2.0.4/linux/include/asm-alpha/irq.h    Wed Feb 28 11:36:37 1996
  10607. +++ linux/include/asm-alpha/irq.h    Tue May 14 14:38:08 1996
  10608. @@ -10,7 +10,7 @@
  10609.  #include <linux/linkage.h>
  10610.  #include <linux/config.h>
  10611.  
  10612. -#if defined(CONFIG_ALPHA_CABRIOLET) || defined(CONFIG_ALPHA_EB66P) || defined(CONFIG_ALPHA_EB164)
  10613. +#if defined(CONFIG_ALPHA_CABRIOLET) || defined(CONFIG_ALPHA_EB66P) || defined(CONFIG_ALPHA_EB164) || defined(CONFIG_ALPHA_PC164)
  10614.  # define NR_IRQS    33
  10615.  #elif defined(CONFIG_ALPHA_EB66) || defined(CONFIG_ALPHA_EB64P)
  10616.  # define NR_IRQS    32
  10617. diff -u --recursive --new-file pre2.0.4/linux/include/asm-alpha/unistd.h linux/include/asm-alpha/unistd.h
  10618. --- pre2.0.4/linux/include/asm-alpha/unistd.h    Mon Mar  4 11:46:31 1996
  10619. +++ linux/include/asm-alpha/unistd.h    Wed May 15 10:49:37 1996
  10620. @@ -142,7 +142,7 @@
  10621.  #define __NR_mlockall        316
  10622.  #define __NR_munlockall        317
  10623.  #define __NR_sysinfo        318
  10624. -#define __NR_sysctl        319
  10625. +#define __NR__sysctl        319
  10626.  #define __NR_idle        320
  10627.  #define __NR_umount        321
  10628.  #define __NR_swapon        322
  10629. diff -u --recursive --new-file pre2.0.4/linux/include/asm-m68k/atari_SCCserial.h linux/include/asm-m68k/atari_SCCserial.h
  10630. --- pre2.0.4/linux/include/asm-m68k/atari_SCCserial.h    Thu Jan  1 02:00:00 1970
  10631. +++ linux/include/asm-m68k/atari_SCCserial.h    Thu May 16 09:05:11 1996
  10632. @@ -0,0 +1,60 @@
  10633. +#ifndef _ATARI_SCCSERIAL_H
  10634. +#define _ATARI_SCCSERIAL_H
  10635. +
  10636. +/* Special configuration ioctls for the Atari SCC5380 Serial
  10637. + * Communications Controller
  10638. + */
  10639. +
  10640. +/* ioctl command codes */
  10641. +
  10642. +#define TIOCGATSCC    0x54c0    /* get SCC configuration */
  10643. +#define TIOCSATSCC    0x54c1    /* set SCC configuration */
  10644. +#define TIOCDATSCC    0x54c2    /* reset configuration to defaults */
  10645. +
  10646. +/* Clock sources */
  10647. +
  10648. +#define CLK_RTxC    0
  10649. +#define CLK_TRxC    1
  10650. +#define CLK_PCLK    2
  10651. +
  10652. +/* baud_bases for the common clocks in the Atari. These are the real
  10653. + * frequencies divided by 16.
  10654. + */
  10655. +   
  10656. +#define SCC_BAUD_BASE_TIMC    19200    /* 0.3072 MHz from TT-MFP, Timer C */
  10657. +#define SCC_BAUD_BASE_BCLK    153600    /* 2.4576 MHz */
  10658. +#define SCC_BAUD_BASE_PCLK4    229500    /* 3.6720 MHz */
  10659. +#define SCC_BAUD_BASE_PCLK    503374    /* 8.0539763 MHz */
  10660. +#define SCC_BAUD_BASE_NONE    0        /* for not connected or unused
  10661. +                         * clock sources */
  10662. +
  10663. +/* The SCC configuration structure */
  10664. +
  10665. +struct atari_SCCserial {
  10666. +    unsigned    RTxC_base;    /* base_baud of RTxC */
  10667. +    unsigned    TRxC_base;    /* base_baud of TRxC */
  10668. +    unsigned    PCLK_base;    /* base_baud of PCLK, for both channels! */
  10669. +    struct {
  10670. +        unsigned clksrc;    /* CLK_RTxC, CLK_TRxC or CLK_PCLK */
  10671. +        unsigned divisor;    /* divisor for base baud, valid values:
  10672. +                     * see below */
  10673. +    } baud_table[17];        /* For 50, 75, 110, 135, 150, 200, 300,
  10674. +                     * 600, 1200, 1800, 2400, 4800, 9600,
  10675. +                     * 19200, 38400, 57600 and 115200 bps. The
  10676. +                     * last two could be replaced by other
  10677. +                     * rates > 38400 if they're not possible.
  10678. +                     */
  10679. +};
  10680. +
  10681. +/* The following divisors are valid:
  10682. + *
  10683. + *   - CLK_RTxC: 1 or even (1, 2 and 4 are the direct modes, > 4 use
  10684. + *               the BRG)
  10685. + *
  10686. + *   - CLK_TRxC: 1, 2 or 4 (no BRG, only direct modes possible)
  10687. + *
  10688. + *   - CLK_PCLK: >= 4 and even (no direct modes, only BRG)
  10689. + *
  10690. + */
  10691. +
  10692. +#endif /* _ATARI_SCCSERIAL_H */
  10693. diff -u --recursive --new-file pre2.0.4/linux/include/asm-m68k/bootinfo.h linux/include/asm-m68k/bootinfo.h
  10694. --- pre2.0.4/linux/include/asm-m68k/bootinfo.h    Sat Apr 27 15:19:59 1996
  10695. +++ linux/include/asm-m68k/bootinfo.h    Thu May 16 09:05:11 1996
  10696. @@ -17,8 +17,6 @@
  10697.  #ifndef BOOTINFO_H
  10698.  #define BOOTINFO_H
  10699.  
  10700. -#ifndef __ASSEMBLY__
  10701. -
  10702.  #include <asm/zorro.h>
  10703.  
  10704.  /*
  10705. @@ -27,6 +25,8 @@
  10706.  
  10707.  #define NUM_AUTO    16
  10708.  
  10709. +#ifndef __ASSEMBLY__
  10710. +
  10711.  #define AMIGAHW_DECLARE(name)    unsigned name : 1
  10712.  #define AMIGAHW_SET(name)    (boot_info.bi_amiga.hw_present.name = 1)
  10713.  #define AMIGAHW_PRESENT(name)    (boot_info.bi_amiga.hw_present.name)
  10714. @@ -35,6 +35,10 @@
  10715.    int model;                /* Amiga Model (3000?) */
  10716.    int num_autocon;            /* # of autoconfig devices found */
  10717.    struct ConfigDev autocon[NUM_AUTO];    /* up to 16 autoconfig devices */
  10718. +#ifdef HACKER_KERNEL
  10719. +  void (*exit_func)(void);        /* addr of function to exit kernel */
  10720. +  unsigned long chip_addr;        /* start of chip memory (bytes) */
  10721. +#endif
  10722.    unsigned long chip_size;        /* size of chip memory (bytes) */
  10723.    unsigned char vblank;         /* VBLANK frequency */
  10724.    unsigned char psfreq;         /* power supply frequency */
  10725. @@ -79,6 +83,25 @@
  10726.    } hw_present;
  10727.  };
  10728.  
  10729. +#else    /* __ASSEMBLY__ */
  10730. +BI_amiga_model        = BI_un
  10731. +BI_amiga_num_autcon    = BI_amiga_model+4
  10732. +BI_amiga_autocon    = BI_amiga_num_autcon+4
  10733. +#ifdef HACKER_KERNEL
  10734. +BI_amiga_exit_func    = BI_amiga_autocon+(CD_sizeof*NUM_AUTO)
  10735. +BI_amiga_chip_addr    = BI_amiga_exit_func+4
  10736. +BI_amiga_chip_size    = BI_amiga_chip_addr+4
  10737. +#else
  10738. +BI_amiga_chip_size    = BI_amiga_autocon+(CD_sizeof*NUM_AUTO)
  10739. +#endif
  10740. +BI_amiga_vblank        = BI_amiga_chip_size+4
  10741. +BI_amiga_psfreq        = BI_amiga_vblank+1
  10742. +BI_amiga_eclock        = BI_amiga_psfreq+1
  10743. +BI_amiga_chipset    = BI_amiga_eclock+4
  10744. +BI_amiga_hw_present    = BI_amiga_chipset+4
  10745. +
  10746. +#endif    /* __ASSEMBLY__ */
  10747.  
  10748.  /* Atari specific part of bootinfo */
  10749.  
  10750. @@ -90,6 +113,8 @@
  10751.  
  10752.  /* ++roman 08/08/95: rewritten from ORing constants to a C bitfield */
  10753.  
  10754. +#ifndef __ASSEMBLY__
  10755. +
  10756.  #define ATARIHW_DECLARE(name)    unsigned name : 1
  10757.  #define ATARIHW_SET(name)    (boot_info.bi_atari.hw_present.name = 1)
  10758.  #define ATARIHW_PRESENT(name)    (boot_info.bi_atari.hw_present.name)
  10759. @@ -143,39 +168,55 @@
  10760.  #define    ATARI_MCH_TT        2
  10761.  #define    ATARI_MCH_FALCON    3
  10762.  
  10763. -/*
  10764. - * CPU and FPU types
  10765. - */
  10766. -#define CPU_68020    (1)
  10767. -#define CPU_68030    (2)
  10768. -#define CPU_68040    (4)
  10769. -#define CPU_68060    (8)
  10770. -#define CPU_MASK     (31)
  10771. -#define FPU_68881    (32)
  10772. -#define FPU_68882    (64)
  10773. -#define FPU_68040    (128)    /* Internal FPU */
  10774. -#define FPU_68060    (256)    /* Internal FPU */
  10775. -
  10776.  struct mem_info {
  10777.    unsigned long addr;        /* physical address of memory chunk */
  10778.    unsigned long size;        /* length of memory chunk (in bytes) */
  10779.  };
  10780.  
  10781. -#define NUM_MEMINFO  4
  10782. +#else    /* __ASSEMBLY__ */
  10783. +
  10784. +MI_addr        = 0
  10785. +MI_size        = MI_addr+4
  10786. +MI_sizeof    = MI_size+4
  10787.  
  10788.  #endif /* __ASSEMBLY__ */
  10789.  
  10790. +#define NUM_MEMINFO  4
  10791. +
  10792.  #define MACH_AMIGA   1
  10793.  #define MACH_ATARI   2
  10794.  #define MACH_MAC     3
  10795.  
  10796. +/*
  10797. + * CPU and FPU types
  10798. + */
  10799. +
  10800. +#define CPUB_68020 0
  10801. +#define CPUB_68030 1
  10802. +#define CPUB_68040 2
  10803. +#define CPUB_68060 3
  10804. +#define FPUB_68881 5
  10805. +#define FPUB_68882 6
  10806. +#define FPUB_68040 7    /* Internal FPU */
  10807. +#define FPUB_68060 8    /* Internal FPU */
  10808. +
  10809. +#define CPU_68020    (1<<CPUB_68020)
  10810. +#define CPU_68030    (1<<CPUB_68030)
  10811. +#define CPU_68040    (1<<CPUB_68040)
  10812. +#define CPU_68060    (1<<CPUB_68060)
  10813. +#define CPU_MASK     (31)
  10814. +#define FPU_68881    (1<<FPUB_68881)
  10815. +#define FPU_68882    (1<<FPUB_68882)
  10816. +#define FPU_68040    (1<<FPUB_68040)    /* Internal FPU */
  10817. +#define FPU_68060    (1<<FPUB_68060)    /* Internal FPU */
  10818. +
  10819. +#define CL_SIZE      (256)
  10820. +
  10821.  #ifndef __ASSEMBLY__
  10822.  
  10823.  #define MACH_IS_AMIGA    (boot_info.machtype == MACH_AMIGA)
  10824.  #define MACH_IS_ATARI    (boot_info.machtype == MACH_ATARI)
  10825.  
  10826. -#define CL_SIZE      (256)
  10827. -
  10828.  struct bootinfo {
  10829.    unsigned long machtype;        /* machine type */
  10830.    unsigned long cputype;        /* system CPU & FPU */
  10831. @@ -195,6 +236,17 @@
  10832.  
  10833.  extern struct bootinfo
  10834.      boot_info;
  10835. +
  10836. +#else    /* __ASSEMBLY__ */
  10837. +
  10838. +BI_machtype    = 0
  10839. +BI_cputype    = BI_machtype+4
  10840. +BI_memory    = BI_cputype+4
  10841. +BI_num_memory    = BI_memory+(MI_sizeof*NUM_MEMINFO)
  10842. +BI_ramdisk_size    = BI_num_memory+4
  10843. +BI_ramdisk_addr    = BI_ramdisk_size+4
  10844. +BI_command_line    = BI_ramdisk_addr+4
  10845. +BI_un        = BI_command_line+CL_SIZE
  10846.  
  10847.  #endif /* __ASSEMBLY__ */
  10848.  
  10849. diff -u --recursive --new-file pre2.0.4/linux/include/asm-m68k/cachectl.h linux/include/asm-m68k/cachectl.h
  10850. --- pre2.0.4/linux/include/asm-m68k/cachectl.h    Thu Jan  1 02:00:00 1970
  10851. +++ linux/include/asm-m68k/cachectl.h    Thu May 16 09:05:11 1996
  10852. @@ -0,0 +1,14 @@
  10853. +#ifndef _M68K_CACHECTL_H
  10854. +#define _M68K_CACHECTL_H
  10855. +
  10856. +/* Definitions for the cacheflush system call.  */
  10857. +
  10858. +#define FLUSH_SCOPE_LINE    1    /* Flush a cache line */
  10859. +#define FLUSH_SCOPE_PAGE    2    /* Flush a page */
  10860. +#define FLUSH_SCOPE_ALL     3    /* Flush the whole cache -- superuser only */
  10861. +
  10862. +#define FLUSH_CACHE_DATA    1    /* Writeback and flush data cache */
  10863. +#define FLUSH_CACHE_INSN    2    /* Flush instruction cache */
  10864. +#define FLUSH_CACHE_BOTH    3    /* Flush both caches */
  10865. +
  10866. +#endif /* _M68K_CACHECTL_H */
  10867. diff -u --recursive --new-file pre2.0.4/linux/include/asm-m68k/checksum.h linux/include/asm-m68k/checksum.h
  10868. --- pre2.0.4/linux/include/asm-m68k/checksum.h    Tue May  7 16:22:37 1996
  10869. +++ linux/include/asm-m68k/checksum.h    Thu May 16 09:05:11 1996
  10870. @@ -62,6 +62,21 @@
  10871.      return ~sum;
  10872.  }
  10873.  
  10874. +/*
  10875. + *    Fold a partial checksum
  10876. + */
  10877. +
  10878. +static inline unsigned int csum_fold(unsigned int sum)
  10879. +{
  10880. +    unsigned int tmp = sum;
  10881. +    __asm__("swap %1\n\t"
  10882. +        "addw %1, %0\n\t"
  10883. +        "clrw %1\n\t"
  10884. +        "addxw %1, %0"
  10885. +        : "=&d" (sum), "=&d" (tmp)
  10886. +        : "0" (sum), "1" (sum));
  10887. +    return ~sum;
  10888. +}
  10889.  
  10890.  
  10891.  /*
  10892. @@ -76,31 +91,12 @@
  10893.      __asm__ ("addl  %1,%0\n\t"
  10894.           "addxl %4,%0\n\t"
  10895.           "addxl %5,%0\n\t"
  10896. -         "movl  %0,%1\n\t"
  10897. -         "swap  %1\n\t"
  10898. -         "addxw %1,%0\n\t"
  10899. -         "clrw  %1\n\t"
  10900. -         "addxw %1,%0\n\t"
  10901. +         "clrl %1\n\t"
  10902. +         "addxl %1,%0"
  10903.           : "=&d" (sum), "=&d" (saddr)
  10904.           : "0" (daddr), "1" (saddr), "d" (len + proto),
  10905.             "d"(sum));
  10906. -    return ~sum;
  10907. -}
  10908. -
  10909. -/*
  10910. - *    Fold a partial checksum without adding pseudo headers
  10911. - */
  10912. -
  10913. -static inline unsigned int csum_fold(unsigned int sum)
  10914. -{
  10915. -    unsigned int tmp = sum;
  10916. -    __asm__("swap %1\n\t"
  10917. -        "addw %1, %0\n\t"
  10918. -        "clrw %1\n\t"
  10919. -        "addxw %1, %0"
  10920. -        : "=&d" (sum), "=&d" (tmp)
  10921. -        : "0" (sum), "1" (sum));
  10922. -    return ~sum;
  10923. +    return csum_fold(sum);
  10924.  }
  10925.  
  10926.  /*
  10927. @@ -111,17 +107,7 @@
  10928.  static inline unsigned short
  10929.  ip_compute_csum(unsigned char * buff, int len)
  10930.  {
  10931. -    unsigned int sum;
  10932. -    unsigned int scratch;
  10933. -
  10934. -    __asm__("movel %0,%1\n\t"
  10935. -        "swap  %1\n\t"
  10936. -        "addw  %1,%0\n\t"
  10937. -        "clrw  %1\n\t"
  10938. -        "addxw %1,%0\n\t"
  10939. -        : "=d" (sum), "=d" (scratch)
  10940. -        : "0" (csum_partial(buff, len, 0)));
  10941. -    return ~sum;
  10942. +    return csum_fold (csum_partial(buff, len, 0));
  10943.  }
  10944.  
  10945.  #endif /* _M68K_CHECKSUM_H */
  10946. diff -u --recursive --new-file pre2.0.4/linux/include/asm-m68k/delay.h linux/include/asm-m68k/delay.h
  10947. --- pre2.0.4/linux/include/asm-m68k/delay.h    Tue Apr 23 13:57:12 1996
  10948. +++ linux/include/asm-m68k/delay.h    Thu May 16 09:05:11 1996
  10949. @@ -9,7 +9,8 @@
  10950.  
  10951.  extern __inline__ void __delay(int loops)
  10952.  {
  10953. -    __asm__("\n\tmovel %0,%/d0\n1:\tsubql #1,%/d0\n\tbpls 1b\n"
  10954. +    __asm__ __volatile__ ("\n\tmovel %0,%/d0\n1:\tsubql #1,%/d0\n\t"
  10955. +                  "bpls 1b\n"
  10956.          : /* no outputs */
  10957.          : "g" (loops)
  10958.          : "d0");
  10959. @@ -26,7 +27,7 @@
  10960.  {
  10961.      usecs *= 0x000010c6;        /* 2**32 / 1000000 */
  10962.  
  10963. -    asm ("mulul %1,%0:%2"
  10964. +    __asm__ __volatile__ ("mulul %1,%0:%2"
  10965.           : "=d" (usecs)
  10966.           : "d" (usecs),
  10967.             "d" (loops_per_sec));
  10968. @@ -35,12 +36,12 @@
  10969.  
  10970.  extern __inline__ unsigned long muldiv(unsigned long a, unsigned long b, unsigned long c)
  10971.  {
  10972. -    __asm__("mulul %1,%/d0:%0\n\tdivul %2,%/d0:%0"
  10973. -        :"=d" (a)
  10974. -        :"d" (b),
  10975. -        "d" (c),
  10976. -        "0" (a)
  10977. -        :"d0");
  10978. +    __asm__ ("mulul %1,%/d0:%0\n\tdivul %2,%/d0:%0"
  10979. +         :"=d" (a)
  10980. +         :"d" (b),
  10981. +         "d" (c),
  10982. +         "0" (a)
  10983. +         :"d0");
  10984.      return a;
  10985.  }
  10986.  
  10987. diff -u --recursive --new-file pre2.0.4/linux/include/asm-m68k/machdep.h linux/include/asm-m68k/machdep.h
  10988. --- pre2.0.4/linux/include/asm-m68k/machdep.h    Tue Apr 23 13:57:12 1996
  10989. +++ linux/include/asm-m68k/machdep.h    Thu May 16 09:05:11 1996
  10990. @@ -30,7 +30,6 @@
  10991.                 int *min, int *sec);
  10992.  extern int (*mach_hwclk)(int, struct hwclk_time*);
  10993.  extern int (*mach_set_clock_mmss)(unsigned long);
  10994. -extern void (*mach_check_partition) (struct gendisk *hd, unsigned int dev);
  10995.  extern void (*mach_mksound)( unsigned int count, unsigned int ticks );
  10996.  extern void (*mach_reset)( void );
  10997.  extern int (*mach_floppy_init) (void);
  10998. @@ -42,5 +41,6 @@
  10999.  extern void (*mach_debug_init)(void);
  11000.  extern void (*mach_video_setup)(char *, int *);
  11001.  extern void (*mach_floppy_setup)(char *, int *);
  11002. +extern void (*mach_floppy_eject)(void);
  11003.  
  11004.  #endif /* _M68K_MACHDEP_H */
  11005. diff -u --recursive --new-file pre2.0.4/linux/include/asm-m68k/pgtable.h linux/include/asm-m68k/pgtable.h
  11006. --- pre2.0.4/linux/include/asm-m68k/pgtable.h    Tue May  7 16:22:37 1996
  11007. +++ linux/include/asm-m68k/pgtable.h    Thu May 16 09:05:11 1996
  11008. @@ -1,6 +1,8 @@
  11009.  #ifndef _M68K_PGTABLE_H
  11010.  #define _M68K_PGTABLE_H
  11011.  
  11012. +#ifndef __ASSEMBLY__
  11013. +
  11014.  /*
  11015.   * This file contains the functions and defines necessary to modify and use
  11016.   * the m68k page table tree.
  11017. @@ -74,6 +76,18 @@
  11018.  /* the no. of pointers that fit on a page: this will go away */
  11019.  #define PTRS_PER_PAGE    (PAGE_SIZE/sizeof(void*))
  11020.  
  11021. +typedef pgd_t pgd_table[PTRS_PER_PGD];
  11022. +typedef pmd_t pmd_table[PTRS_PER_PMD];
  11023. +typedef pte_t pte_table[PTRS_PER_PTE];
  11024. +
  11025. +#define PGD_TABLES_PER_PAGE (PAGE_SIZE/sizeof(pgd_table))
  11026. +#define PMD_TABLES_PER_PAGE (PAGE_SIZE/sizeof(pmd_table))
  11027. +#define PTE_TABLES_PER_PAGE (PAGE_SIZE/sizeof(pte_table))
  11028. +
  11029. +typedef pgd_table pgd_tablepage[PGD_TABLES_PER_PAGE];
  11030. +typedef pmd_table pmd_tablepage[PMD_TABLES_PER_PAGE];
  11031. +typedef pte_table pte_tablepage[PTE_TABLES_PER_PAGE];
  11032. +
  11033.  /* Just any arbitrary offset to the start of the vmalloc VM area: the
  11034.   * current 8MB value just means that there will be a 8MB "hole" after the
  11035.   * physical memory until the kernel virtual memory starts.  That means that
  11036. @@ -85,6 +99,8 @@
  11037.  #define VMALLOC_START ((high_memory + VMALLOC_OFFSET) & ~(VMALLOC_OFFSET-1))
  11038.  #define VMALLOC_VMADDR(x) ((unsigned long)(x))
  11039.  
  11040. +#endif /* __ASSEMBLY__ */
  11041. +
  11042.  /*
  11043.   * Definitions for MMU descriptors
  11044.   */
  11045. @@ -109,6 +125,8 @@
  11046.  #define _PAGE_TABLE    (_PAGE_SHORT)
  11047.  #define _PAGE_CHG_MASK  (PAGE_MASK | _PAGE_ACCESSED | _PAGE_DIRTY | _PAGE_NOCACHE)
  11048.  
  11049. +#ifndef __ASSEMBLY__
  11050. +
  11051.  #define PAGE_NONE    __pgprot(_PAGE_PRESENT | _PAGE_RONLY | _PAGE_ACCESSED | _PAGE_CACHE040)
  11052.  #define PAGE_SHARED    __pgprot(_PAGE_PRESENT | _PAGE_ACCESSED | _PAGE_CACHE040)
  11053.  #define PAGE_COPY    __pgprot(_PAGE_PRESENT | _PAGE_RONLY | _PAGE_ACCESSED | _PAGE_CACHE040)
  11054. @@ -230,9 +248,9 @@
  11055.  #define pmd_present(pmd) pmd_present2(&(pmd))
  11056.  extern inline void pmd_clear(pmd_t * pmdp)
  11057.  {
  11058. -    int i;
  11059. +    short i;
  11060.  
  11061. -    for (i = 0; i < 16; i++)
  11062. +    for (i = 15; i >= 0; i--)
  11063.          pmdp->pmd[i] = 0;
  11064.  }
  11065.  
  11066. @@ -358,6 +376,11 @@
  11067.  }
  11068.  
  11069.  
  11070. +extern const char PgtabStr_bad_pmd[];
  11071. +extern const char PgtabStr_bad_pgd[];
  11072. +extern const char PgtabStr_bad_pmdk[];
  11073. +extern const char PgtabStr_bad_pgdk[];
  11074. +
  11075.  extern inline void pte_free(pte_t * pte)
  11076.  {
  11077.      cache_page((unsigned long)pte);
  11078. @@ -381,7 +404,7 @@
  11079.          free_page((unsigned long)page);
  11080.      }
  11081.      if (pmd_bad(*pmd)) {
  11082. -        printk("Bad pmd in pte_alloc: %08lx\n", pmd_val(*pmd));
  11083. +        printk(PgtabStr_bad_pmd, pmd_val(*pmd));
  11084.          pmd_set(pmd, BAD_PAGETABLE);
  11085.          return NULL;
  11086.      }
  11087. @@ -414,7 +437,7 @@
  11088.          free_pointer_table(page);
  11089.      }
  11090.      if (pgd_bad(*pgd)) {
  11091. -        printk("Bad pgd in pmd_alloc: %08lx\n", pgd_val(*pgd));
  11092. +        printk(PgtabStr_bad_pgd, pgd_val(*pgd));
  11093.          pgd_set(pgd, (pmd_t *)BAD_PAGETABLE);
  11094.          return NULL;
  11095.      }
  11096. @@ -444,7 +467,7 @@
  11097.          free_page((unsigned long) page);
  11098.      }
  11099.      if (pmd_bad(*pmd)) {
  11100. -        printk("Bad pmd in pte_alloc_kernel: %08lx\n", pmd_val(*pmd));
  11101. +        printk(PgtabStr_bad_pmdk, pmd_val(*pmd));
  11102.          pmd_set(pmd, BAD_PAGETABLE);
  11103.          return NULL;
  11104.      }
  11105. @@ -472,7 +495,7 @@
  11106.          free_kpointer_table(page);
  11107.      }
  11108.      if (pgd_bad(*pgd)) {
  11109. -        printk("Bad pgd in pmd_alloc_kernel: %08lx\n", pgd_val(*pgd));
  11110. +        printk(PgtabStr_bad_pgdk, pgd_val(*pgd));
  11111.          pgd_set(pgd, (pmd_t *)BAD_PAGETABLE);
  11112.          return NULL;
  11113.      }
  11114. @@ -492,7 +515,7 @@
  11115.  #define flush_icache() \
  11116.  do { \
  11117.      if (m68k_is040or060) \
  11118. -        asm (".word 0xf498"); /* CINVA I */ \
  11119. +        asm ("nop; .word 0xf498 /* cinva %%ic */"); \
  11120.      else \
  11121.          asm ("movec %/cacr,%/d0;" \
  11122.               "oriw %0,%/d0;" \
  11123. @@ -521,19 +544,99 @@
  11124.   */
  11125.  extern void cache_push_v (unsigned long vaddr, int len);
  11126.  
  11127. -/*
  11128. - * Could someone take a look at these?
  11129. - */
  11130. -extern void flush_cache_all(void);
  11131. -#define flush_cache_mm(mm)           flush_cache_all()
  11132. -#define flush_cache_range(mm, start, end)  flush_cache_all()
  11133. -#define flush_cache_page(vma, addr)       flush_cache_all()
  11134. -extern void flush_page_to_ram(unsigned long addr);
  11135. -
  11136.  /* cache code */
  11137.  #define FLUSH_I_AND_D    (0x00000808)
  11138.  #define FLUSH_I     (0x00000008)
  11139.  
  11140. +/* This is needed whenever the virtual mapping of the current
  11141. +   process changes.  */
  11142. +#define __flush_cache_all()                        \
  11143. +    do {                                \
  11144. +    if (m68k_is040or060)                            \
  11145. +               __asm__ __volatile__ ("nop; .word 0xf478\n" ::);         \
  11146. +        else                                                            \
  11147. +           __asm__ __volatile__ ("movec %%cacr,%%d0\n\t"        \
  11148. +                     "orw %0,%%d0\n\t"            \
  11149. +                     "movec %%d0,%%cacr"        \
  11150. +                     : : "di" (FLUSH_I_AND_D) : "d0");    \
  11151. +    } while (0)
  11152. +
  11153. +#define __flush_cache_030()                        \
  11154. +    do {                                \
  11155. +    if (m68k_is040or060 == 0)                    \
  11156. +           __asm__ __volatile__ ("movec %%cacr,%%d0\n\t"        \
  11157. +                     "orw %0,%%d0\n\t"            \
  11158. +                     "movec %%d0,%%cacr"        \
  11159. +                     : : "di" (FLUSH_I_AND_D) : "d0");    \
  11160. +    } while (0)
  11161. +
  11162. +#define flush_cache_all() __flush_cache_all()
  11163. +
  11164. +extern inline void flush_cache_mm(struct mm_struct *mm)
  11165. +{
  11166. +    if (mm == current->mm) __flush_cache_all();
  11167. +}
  11168. +
  11169. +extern inline void flush_cache_range(struct mm_struct *mm,
  11170. +                     unsigned long start,
  11171. +                     unsigned long end)
  11172. +{
  11173. +    if (mm == current->mm){
  11174. +        if (m68k_is040or060)
  11175. +            cache_push_v(start, end-start);
  11176. +        else
  11177. +            __flush_cache_030();
  11178. +    }
  11179. +}
  11180. +
  11181. +extern inline void flush_cache_page(struct vm_area_struct *vma,
  11182. +                    unsigned long vmaddr)
  11183. +{
  11184. +    if (vma->vm_mm == current->mm){
  11185. +        if (m68k_is040or060)
  11186. +            cache_push_v(vmaddr, PAGE_SIZE);
  11187. +        else
  11188. +            __flush_cache_030();
  11189. +    }
  11190. +}
  11191. +
  11192. +/* Push the page at kernel virtual address and clear the icache */
  11193. +extern inline void flush_page_to_ram (unsigned long address)
  11194. +{
  11195. +    if (m68k_is040or060) {
  11196. +    register unsigned long tmp __asm ("a0") = VTOP(address);
  11197. +    __asm__ __volatile__ ("nop\n\t"
  11198. +                  ".word 0xf470 /* cpushp %%dc,(%0) */\n\t"
  11199. +                  ".word 0xf490 /* cinvp %%ic,(%0) */"
  11200. +                  : : "a" (tmp));
  11201. +    }
  11202. +    else
  11203. +    __asm volatile ("movec %%cacr,%%d0\n\t"
  11204. +            "orw %0,%%d0\n\t"
  11205. +            "movec %%d0,%%cacr"
  11206. +            : : "di" (FLUSH_I) : "d0");
  11207. +}
  11208. +
  11209. +/* Push n pages at kernel virtual address and clear the icache */
  11210. +extern inline void flush_pages_to_ram (unsigned long address, int n)
  11211. +{
  11212. +    if (m68k_is040or060) {
  11213. +    while (n--) {
  11214. +        register unsigned long tmp __asm ("a0") = VTOP(address);
  11215. +        __asm__ __volatile__ ("nop\n\t"
  11216. +                  ".word 0xf470 /* cpushp %%dc,(%0) */\n\t"
  11217. +                  ".word 0xf490 /* cinvp %%ic,(%0) */"
  11218. +                  : : "a" (tmp));
  11219. +        address += PAGE_SIZE;
  11220. +    }
  11221. +    }
  11222. +    else
  11223. +    __asm volatile ("movec %%cacr,%%d0\n\t"
  11224. +            "orw %0,%%d0\n\t"
  11225. +            "movec %%d0,%%cacr"
  11226. +            : : "di" (FLUSH_I) : "d0");
  11227. +}
  11228. +
  11229.  /*
  11230.   * Check if the addr/len goes up to the end of a physical
  11231.   * memory chunk.  Used for DMA functions.
  11232. @@ -580,5 +683,7 @@
  11233.  #define SWP_OFFSET(entry) ((entry) >> PAGE_SHIFT)
  11234.  #define SWP_ENTRY(type,offset) (((type) << 2) | ((offset) << PAGE_SHIFT))
  11235.  #endif
  11236. +
  11237. +#endif /* __ASSEMBLY__ */
  11238.  
  11239.  #endif /* _M68K_PGTABLE_H */
  11240. diff -u --recursive --new-file pre2.0.4/linux/include/asm-m68k/segment.h linux/include/asm-m68k/segment.h
  11241. --- pre2.0.4/linux/include/asm-m68k/segment.h    Tue Apr 23 13:57:12 1996
  11242. +++ linux/include/asm-m68k/segment.h    Thu May 16 09:05:11 1996
  11243. @@ -155,7 +155,7 @@
  11244.               : "0" (from), "1" (to)
  11245.               : "d0", "memory");
  11246.      if (tmp & 1)
  11247. -        __asm__ ("moveb %0@,%/d0\n\t"
  11248. +        __asm__ __volatile__ ("moveb %0@,%/d0\n\t"
  11249.               "movesb %/d0,%1@\n\t"
  11250.               : /* no outputs */
  11251.               : "a" (from), "a" (to)
  11252. @@ -251,7 +251,7 @@
  11253.               : "0" (from), "1" (to)
  11254.               : "d0", "memory");
  11255.      if (tmp & 1)
  11256. -        __asm__ ("movesb %0@,%/d0\n\t"
  11257. +        __asm__ __volatile__ ("movesb %0@,%/d0\n\t"
  11258.               "moveb %/d0,%1@\n\t"
  11259.               : /* no outputs */
  11260.               : "a" (from), "a" (to)
  11261. diff -u --recursive --new-file pre2.0.4/linux/include/asm-m68k/unistd.h linux/include/asm-m68k/unistd.h
  11262. --- pre2.0.4/linux/include/asm-m68k/unistd.h    Tue Apr 23 13:57:12 1996
  11263. +++ linux/include/asm-m68k/unistd.h    Thu May 16 09:05:11 1996
  11264. @@ -128,7 +128,7 @@
  11265.  #define __NR_clone        120
  11266.  #define __NR_setdomainname    121
  11267.  #define __NR_uname        122
  11268. -#define __NR_modify_ldt        123
  11269. +#define __NR_cacheflush        123
  11270.  #define __NR_adjtimex        124
  11271.  #define __NR_mprotect        125
  11272.  #define __NR_sigprocmask    126
  11273. diff -u --recursive --new-file pre2.0.4/linux/include/asm-m68k/zorro.h linux/include/asm-m68k/zorro.h
  11274. --- pre2.0.4/linux/include/asm-m68k/zorro.h    Tue Apr 23 13:57:12 1996
  11275. +++ linux/include/asm-m68k/zorro.h    Thu May 16 09:05:11 1996
  11276. @@ -11,6 +11,8 @@
  11277.  #ifndef _ASM_M68K_ZORRO_H_
  11278.  #define _ASM_M68K_ZORRO_H_
  11279.  
  11280. +#ifndef __ASSEMBLY__
  11281. +
  11282.  #include <linux/config.h>
  11283.  #include <asm/amigatypes.h>
  11284.  
  11285. @@ -302,6 +304,44 @@
  11286.      u_long        cd_Unused[4];    /* for whatever the driver wants */
  11287.  };
  11288.  
  11289. +#else    /* __ASSEMBLY__ */
  11290. +
  11291. +LN_Succ        = 0
  11292. +LN_Pred        = LN_Succ+4
  11293. +LN_Type        = LN_Pred+4
  11294. +LN_Pri        = LN_Type+1
  11295. +LN_Name        = LN_Pri+1
  11296. +LN_sizeof    = LN_Name+4
  11297. +
  11298. +ER_Type        = 0
  11299. +ER_Product    = ER_Type+1
  11300. +ER_Flags    = ER_Product+1
  11301. +ER_Reserved03    = ER_Flags+1
  11302. +ER_Manufacturer    = ER_Reserved03+1
  11303. +ER_SerialNumber    = ER_Manufacturer+2
  11304. +ER_InitDiagVec    = ER_SerialNumber+4
  11305. +ER_Reserved0c    = ER_InitDiagVec+2
  11306. +ER_Reserved0d    = ER_Reserved0c+1
  11307. +ER_Reserved0e    = ER_Reserved0d+1
  11308. +ER_Reserved0f    = ER_Reserved0e+1
  11309. +ER_sizeof    = ER_Reserved0f+1
  11310. +
  11311. +CD_Node        = 0
  11312. +CD_Flags    = CD_Node+LN_sizeof
  11313. +CD_Pad        = CD_Flags+1
  11314. +CD_Rom        = CD_Pad+1
  11315. +CD_BoardAddr    = CD_Rom+ER_sizeof
  11316. +CD_BoardSize    = CD_BoardAddr+4
  11317. +CD_SlotAddr    = CD_BoardSize+4
  11318. +CD_SlotSize    = CD_SlotAddr+2
  11319. +CD_Driver    = CD_SlotSize+2
  11320. +CD_NextCD    = CD_Driver+4
  11321. +CD_Unused    = CD_NextCD+4
  11322. +CD_sizeof    = CD_Unused+(4*4)
  11323. +
  11324. +#endif    /* __ASSEMBLY__ */
  11325. +
  11326. +#ifndef __ASSEMBLY__
  11327.  
  11328.  /*
  11329.   * Zorro Functions
  11330. @@ -341,5 +381,6 @@
  11331.  extern int zorro_get_list(char *buffer);
  11332.  #endif CONFIG_ZORRO
  11333.  
  11334. +#endif    /* __ASSEMBLY__ */
  11335.  
  11336.  #endif /* _ASM_M68K_ZORRO_H_ */
  11337. diff -u --recursive --new-file pre2.0.4/linux/include/linux/affs_fs.h linux/include/linux/affs_fs.h
  11338. --- pre2.0.4/linux/include/linux/affs_fs.h    Tue May  7 16:22:38 1996
  11339. +++ linux/include/linux/affs_fs.h    Thu May 16 09:05:12 1996
  11340. @@ -26,24 +26,24 @@
  11341.  /* amigaffs.c */
  11342.  
  11343.  extern int           affs_get_key_entry(int bsize, void *data, int entry_pos);
  11344. -extern int           affs_find_next_hash_entry(int bsize, void *dir_data, ULONG *hash_pos);
  11345. +extern int           affs_find_next_hash_entry(int bsize, void *dir_data, __u32 *hash_pos);
  11346.  extern int           affs_get_file_name(int bsize, void *fh_data, char **name);
  11347. -extern ULONG           affs_checksum_block(int bsize, void *data, LONG *ptype, LONG *stype);
  11348. +extern __u32           affs_checksum_block(int bsize, void *data, __s32 *ptype, __s32 *stype);
  11349.  extern void           affs_fix_checksum(int bsize, void *data, int cspos);
  11350.  extern void           secs_to_datestamp(int secs, struct DateStamp *ds);
  11351. -extern int           prot_to_mode(ULONG prot);
  11352. -extern ULONG           mode_to_prot(int mode);
  11353. +extern int           prot_to_mode(__u32 prot);
  11354. +extern __u32           mode_to_prot(int mode);
  11355.  extern int           affs_fix_hash_pred(struct inode *startino, int startoffset,
  11356. -                           LONG key, LONG newkey);
  11357. -extern int           affs_fix_link_pred(struct inode *startino, LONG key, LONG newkey);
  11358. +                           __s32 key, __s32 newkey);
  11359. +extern int           affs_fix_link_pred(struct inode *startino, __s32 key, __s32 newkey);
  11360.  
  11361.  /* bitmap. c */
  11362.  
  11363.  extern int           affs_count_free_blocks(struct super_block *s);
  11364. -extern int           affs_count_free_bits(int blocksize, const UBYTE *data);
  11365. -extern void           affs_free_block(struct super_block *sb, LONG block);
  11366. -extern LONG           affs_new_header(struct inode *inode);
  11367. -extern LONG           affs_new_data(struct inode *inode);
  11368. +extern int           affs_count_free_bits(int blocksize, const __u8 *data);
  11369. +extern void           affs_free_block(struct super_block *sb, __s32 block);
  11370. +extern __s32           affs_new_header(struct inode *inode);
  11371. +extern __s32           affs_new_data(struct inode *inode);
  11372.  extern void           affs_make_zones(struct super_block *sb);
  11373.  
  11374.  /* namei.c */
  11375. @@ -78,7 +78,7 @@
  11376.  extern void           affs_put_inode(struct inode *);
  11377.  extern struct inode      *affs_new_inode(const struct inode *dir);
  11378.  extern int           affs_add_entry(struct inode *dir, struct inode *link, struct inode *inode,
  11379. -                      const char *name, int len, LONG type);
  11380. +                      const char *name, int len, __s32 type);
  11381.  
  11382.  /* file.c */
  11383.  
  11384. @@ -101,4 +101,5 @@
  11385.  extern struct inode_operations     affs_blkdev_inode_operations;
  11386.  
  11387.  extern int init_affs_fs(void);
  11388. +
  11389.  #endif
  11390. diff -u --recursive --new-file pre2.0.4/linux/include/linux/affs_hardblocks.h linux/include/linux/affs_hardblocks.h
  11391. --- pre2.0.4/linux/include/linux/affs_hardblocks.h    Tue May  7 16:22:38 1996
  11392. +++ linux/include/linux/affs_hardblocks.h    Wed May 15 09:44:59 1996
  11393. @@ -8,59 +8,59 @@
  11394.  #endif
  11395.  
  11396.  struct RigidDiskBlock {
  11397. -    ULONG    rdb_ID;
  11398. -    ULONG    rdb_SummedLongs;
  11399. -    LONG    rdb_ChkSum;
  11400. -    ULONG    rdb_HostID;
  11401. -    ULONG    rdb_BlockBytes;
  11402. -    ULONG    rdb_Flags;
  11403. -    ULONG    rdb_BadBlockList;
  11404. -    ULONG    rdb_PartitionList;
  11405. -    ULONG    rdb_FileSysHeaderList;
  11406. -    ULONG    rdb_DriveInit;
  11407. -    ULONG    rdb_Reserved1[6];
  11408. -    ULONG    rdb_Cylinders;
  11409. -    ULONG    rdb_Sectors;
  11410. -    ULONG    rdb_Heads;
  11411. -    ULONG    rdb_Interleave;
  11412. -    ULONG    rdb_Park;
  11413. -    ULONG    rdb_Reserved2[3];
  11414. -    ULONG    rdb_WritePreComp;
  11415. -    ULONG    rdb_ReducedWrite;
  11416. -    ULONG    rdb_StepRate;
  11417. -    ULONG    rdb_Reserved3[5];
  11418. -    ULONG    rdb_RDBBlocksLo;
  11419. -    ULONG    rdb_RDBBlocksHi;
  11420. -    ULONG    rdb_LoCylinder;
  11421. -    ULONG    rdb_HiCylinder;
  11422. -    ULONG    rdb_CylBlocks;
  11423. -    ULONG    rdb_AutoParkSeconds;
  11424. -    ULONG    rdb_HighRDSKBlock;
  11425. -    ULONG    rdb_Reserved4;
  11426. +    __u32    rdb_ID;
  11427. +    __u32    rdb_SummedLongs;
  11428. +    __s32    rdb_ChkSum;
  11429. +    __u32    rdb_HostID;
  11430. +    __u32    rdb_BlockBytes;
  11431. +    __u32    rdb_Flags;
  11432. +    __u32    rdb_BadBlockList;
  11433. +    __u32    rdb_PartitionList;
  11434. +    __u32    rdb_FileSysHeaderList;
  11435. +    __u32    rdb_DriveInit;
  11436. +    __u32    rdb_Reserved1[6];
  11437. +    __u32    rdb_Cylinders;
  11438. +    __u32    rdb_Sectors;
  11439. +    __u32    rdb_Heads;
  11440. +    __u32    rdb_Interleave;
  11441. +    __u32    rdb_Park;
  11442. +    __u32    rdb_Reserved2[3];
  11443. +    __u32    rdb_WritePreComp;
  11444. +    __u32    rdb_ReducedWrite;
  11445. +    __u32    rdb_StepRate;
  11446. +    __u32    rdb_Reserved3[5];
  11447. +    __u32    rdb_RDBBlocksLo;
  11448. +    __u32    rdb_RDBBlocksHi;
  11449. +    __u32    rdb_LoCylinder;
  11450. +    __u32    rdb_HiCylinder;
  11451. +    __u32    rdb_CylBlocks;
  11452. +    __u32    rdb_AutoParkSeconds;
  11453. +    __u32    rdb_HighRDSKBlock;
  11454. +    __u32    rdb_Reserved4;
  11455.      char    rdb_DiskVendor[8];
  11456.      char    rdb_DiskProduct[16];
  11457.      char    rdb_DiskRevision[4];
  11458.      char    rdb_ControllerVendor[8];
  11459.      char    rdb_ControllerProduct[16];
  11460.      char    rdb_ControllerRevision[4];
  11461. -    ULONG    rdb_Reserved5[10];
  11462. +    __u32    rdb_Reserved5[10];
  11463.  };
  11464.  
  11465.  #define    IDNAME_RIGIDDISK    0x5244534B    /* "RDSK" */
  11466.  
  11467.  struct PartitionBlock {
  11468. -    ULONG    pb_ID;
  11469. -    ULONG    pb_SummedLongs;
  11470. -    LONG    pb_ChkSum;
  11471. -    ULONG    pb_HostID;
  11472. -    ULONG    pb_Next;
  11473. -    ULONG    pb_Flags;
  11474. -    ULONG    pb_Reserved1[2];
  11475. -    ULONG    pb_DevFlags;
  11476. -    UBYTE    pb_DriveName[32];
  11477. -    ULONG    pb_Reserved2[15];
  11478. -    ULONG    pb_Environment[17];
  11479. -    ULONG    pb_EReserved[15];
  11480. +    __u32    pb_ID;
  11481. +    __u32    pb_SummedLongs;
  11482. +    __s32    pb_ChkSum;
  11483. +    __u32    pb_HostID;
  11484. +    __u32    pb_Next;
  11485. +    __u32    pb_Flags;
  11486. +    __u32    pb_Reserved1[2];
  11487. +    __u32    pb_DevFlags;
  11488. +    __u8    pb_DriveName[32];
  11489. +    __u32    pb_Reserved2[15];
  11490. +    __u32    pb_Environment[17];
  11491. +    __u32    pb_EReserved[15];
  11492.  };
  11493.  
  11494.  #define    IDNAME_PARTITION    0x50415254    /* "PART" */
  11495. diff -u --recursive --new-file pre2.0.4/linux/include/linux/amigaffs.h linux/include/linux/amigaffs.h
  11496. --- pre2.0.4/linux/include/linux/amigaffs.h    Sat May 11 10:42:07 1996
  11497. +++ linux/include/linux/amigaffs.h    Thu May 16 09:05:12 1996
  11498. @@ -15,6 +15,7 @@
  11499.  #define DIR_END(p,i)    GET_END_PTR(struct dir_end,p,AFFS_I2BSIZE(i))
  11500.  #define LINK_END(p,i)    GET_END_PTR(struct hlink_end,p,AFFS_I2BSIZE(i))
  11501.  #define ROOT_END_S(p,s)    GET_END_PTR(struct root_end,p,(s)->s_blocksize)
  11502. +#define DATA_FRONT(bh)    ((struct data_front *)(bh)->b_data)
  11503.  
  11504.  /* Only for easier debugging if need be */
  11505.  #define affs_bread    bread
  11506. @@ -44,19 +45,11 @@
  11507.  #define MUFS_DCOFS    0x6d754604   /* 'muF\4' */
  11508.  #define MUFS_DCFFS    0x6d754605   /* 'muF\5' */
  11509.  
  11510. -typedef __u32    ULONG;
  11511. -typedef __u16    UWORD;
  11512. -typedef __u8    UBYTE;
  11513. -
  11514. -typedef __s32    LONG;
  11515. -typedef __s16    WORD;
  11516. -typedef __s8    BYTE;
  11517. -
  11518.  struct DateStamp
  11519.  {
  11520. -  ULONG ds_Days;
  11521. -  ULONG ds_Minute;
  11522. -  ULONG ds_Tick;
  11523. +  __u32 ds_Days;
  11524. +  __u32 ds_Minute;
  11525. +  __u32 ds_Tick;
  11526.  };
  11527.  
  11528.  #define T_SHORT        2
  11529. @@ -72,120 +65,120 @@
  11530.  
  11531.  struct root_front
  11532.  {
  11533. -  LONG primary_type;
  11534. -  ULONG spare1[2];
  11535. -  ULONG hash_size;
  11536. -  ULONG spare2;
  11537. -  ULONG checksum;
  11538. -  ULONG hashtable[0];
  11539. +  __s32 primary_type;
  11540. +  __u32 spare1[2];
  11541. +  __u32 hash_size;
  11542. +  __u32 spare2;
  11543. +  __u32 checksum;
  11544. +  __u32 hashtable[0];
  11545.  };
  11546.  
  11547.  struct root_end
  11548.  {
  11549. -  LONG bm_flag;
  11550. -  ULONG bm_keys[25];
  11551. -  ULONG bm_extend;
  11552. +  __s32 bm_flag;
  11553. +  __u32 bm_keys[25];
  11554. +  __u32 bm_extend;
  11555.    struct DateStamp dir_altered;
  11556. -  UBYTE disk_name[40];
  11557. +  __u8 disk_name[40];
  11558.    struct DateStamp disk_altered;
  11559.    struct DateStamp disk_made;
  11560. -  ULONG spare1[3];
  11561. -  LONG secondary_type;
  11562. +  __u32 spare1[3];
  11563. +  __s32 secondary_type;
  11564.  };
  11565.  
  11566.  struct dir_front
  11567.  {
  11568. -  LONG primary_type;
  11569. -  ULONG own_key;
  11570. -  ULONG spare1[3];
  11571. -  ULONG checksum;
  11572. -  ULONG hashtable[0];
  11573. +  __s32 primary_type;
  11574. +  __u32 own_key;
  11575. +  __u32 spare1[3];
  11576. +  __u32 checksum;
  11577. +  __u32 hashtable[0];
  11578.  };
  11579.  
  11580.  struct dir_end
  11581.  {
  11582. -  ULONG spare1;
  11583. -  UWORD owner_uid;
  11584. -  UWORD owner_gid;
  11585. -  ULONG protect;
  11586. -  ULONG spare2;
  11587. -  UBYTE comment[92];
  11588. +  __u32 spare1;
  11589. +  __u16 owner_uid;
  11590. +  __u16 owner_gid;
  11591. +  __u32 protect;
  11592. +  __u32 spare2;
  11593. +  __u8 comment[92];
  11594.    struct DateStamp created;
  11595. -  UBYTE dir_name[32];
  11596. -  ULONG spare3[2];
  11597. -  ULONG link_chain;
  11598. -  ULONG spare4[5];
  11599. -  ULONG hash_chain;
  11600. -  ULONG parent;
  11601. -  ULONG spare5;
  11602. -  LONG secondary_type;
  11603. +  __u8 dir_name[32];
  11604. +  __u32 spare3[2];
  11605. +  __u32 link_chain;
  11606. +  __u32 spare4[5];
  11607. +  __u32 hash_chain;
  11608. +  __u32 parent;
  11609. +  __u32 spare5;
  11610. +  __s32 secondary_type;
  11611.  };
  11612.  
  11613.  struct file_front
  11614.  {
  11615. -  LONG primary_type;
  11616. -  ULONG own_key;
  11617. -  ULONG block_count;
  11618. -  ULONG unknown1;
  11619. -  ULONG first_data;
  11620. -  ULONG checksum;
  11621. -  ULONG blocks[0];
  11622. +  __s32 primary_type;
  11623. +  __u32 own_key;
  11624. +  __u32 block_count;
  11625. +  __u32 unknown1;
  11626. +  __u32 first_data;
  11627. +  __u32 checksum;
  11628. +  __u32 blocks[0];
  11629.  };
  11630.  
  11631.  struct file_end
  11632.  {
  11633. -  ULONG spare1;
  11634. -  UWORD owner_uid;
  11635. -  UWORD owner_gid;
  11636. -  ULONG protect;
  11637. -  ULONG byte_size;
  11638. -  UBYTE comment[92];
  11639. +  __u32 spare1;
  11640. +  __u16 owner_uid;
  11641. +  __u16 owner_gid;
  11642. +  __u32 protect;
  11643. +  __u32 byte_size;
  11644. +  __u8 comment[92];
  11645.    struct DateStamp created;
  11646. -  UBYTE file_name[32];
  11647. -  ULONG spare2;
  11648. -  ULONG original;    /* not really in file_end */
  11649. -  ULONG link_chain;
  11650. -  ULONG spare3[5];
  11651. -  ULONG hash_chain;
  11652. -  ULONG parent;
  11653. -  ULONG extension;
  11654. -  LONG secondary_type;
  11655. +  __u8 file_name[32];
  11656. +  __u32 spare2;
  11657. +  __u32 original;    /* not really in file_end */
  11658. +  __u32 link_chain;
  11659. +  __u32 spare3[5];
  11660. +  __u32 hash_chain;
  11661. +  __u32 parent;
  11662. +  __u32 extension;
  11663. +  __s32 secondary_type;
  11664.  };
  11665.  
  11666.  struct hlink_front
  11667.  {
  11668. -  LONG primary_type;
  11669. -  ULONG own_key;
  11670. -  ULONG spare1[3];
  11671. -  ULONG checksum;
  11672. +  __s32 primary_type;
  11673. +  __u32 own_key;
  11674. +  __u32 spare1[3];
  11675. +  __u32 checksum;
  11676.  };
  11677.  
  11678.  struct hlink_end
  11679.  {
  11680. -  ULONG spare1;
  11681. -  UWORD owner_uid;
  11682. -  UWORD owner_gid;
  11683. -  ULONG protect;
  11684. -  UBYTE comment[92];
  11685. +  __u32 spare1;
  11686. +  __u16 owner_uid;
  11687. +  __u16 owner_gid;
  11688. +  __u32 protect;
  11689. +  __u8 comment[92];
  11690.    struct DateStamp created;
  11691. -  UBYTE link_name[32];
  11692. -  ULONG spare2;
  11693. -  ULONG original;
  11694. -  ULONG link_chain;
  11695. -  ULONG spare3[5];
  11696. -  ULONG hash_chain;
  11697. -  ULONG parent;
  11698. -  ULONG spare4;
  11699. -  LONG secondary_type;
  11700. +  __u8 link_name[32];
  11701. +  __u32 spare2;
  11702. +  __u32 original;
  11703. +  __u32 link_chain;
  11704. +  __u32 spare3[5];
  11705. +  __u32 hash_chain;
  11706. +  __u32 parent;
  11707. +  __u32 spare4;
  11708. +  __s32 secondary_type;
  11709.  };
  11710.  
  11711.  struct slink_front
  11712.  {
  11713. -  LONG primary_type;
  11714. -  ULONG own_key;
  11715. -  ULONG spare1[3];
  11716. -  ULONG checksum;
  11717. -  UBYTE    symname[288];    /* depends on block size */
  11718. +  __s32 primary_type;
  11719. +  __u32 own_key;
  11720. +  __u32 spare1[3];
  11721. +  __u32 checksum;
  11722. +  __u8    symname[288];    /* depends on block size */
  11723.  };
  11724.  
  11725.  /* Permission bits */
  11726. diff -u --recursive --new-file pre2.0.4/linux/include/linux/baycom.h linux/include/linux/baycom.h
  11727. --- pre2.0.4/linux/include/linux/baycom.h    Thu Jan  1 02:00:00 1970
  11728. +++ linux/include/linux/baycom.h    Thu May 16 16:35:42 1996
  11729. @@ -0,0 +1,123 @@
  11730. +/*
  11731. + * The Linux BAYCOM driver for the Baycom serial 1200 baud modem
  11732. + * and the parallel 9600 baud modem
  11733. + * (C) 1996 by Thomas Sailer, HB9JNX
  11734. + */
  11735. +
  11736. +#ifndef _BAYCOM_H
  11737. +#define _BAYCOM_H
  11738. +
  11739. +#include <linux/ioctl.h>
  11740. +
  11741. +/* -------------------------------------------------------------------- */
  11742. +
  11743. +struct baycom_statistics {
  11744. +    unsigned long rx_packets, tx_packets;
  11745. +    unsigned long ptt_keyed;
  11746. +    unsigned long rx_bufferoverrun, tx_bufferoverrun;
  11747. +};
  11748. +
  11749. +struct baycom_params {
  11750. +    int modem_type;
  11751. +    int iobase;
  11752. +    int irq;
  11753. +    int options;
  11754. +    int tx_delay;  /* the transmitter keyup delay in 10ms units */
  11755. +    int tx_tail;   /* the transmitter keyoff delay in 10ms units */
  11756. +    int slottime;  /* the slottime in 10ms; usually 10 = 100ms */
  11757. +    int ppersist;  /* the p-persistence 0..255 */
  11758. +    int fulldup;   /* the driver does not support full duplex, setting */
  11759. +                   /* this just makes the driver send even if DCD is on */
  11760. +};    
  11761. +
  11762. +/* -------------------------------------------------------------------- */
  11763. +
  11764. +#define BAYCOM_MAJOR         51
  11765. +
  11766. +/* maximum packet length, excluding CRC */
  11767. +#define BAYCOM_MAXFLEN         400    
  11768. +
  11769. +/* the ioctl type of this driver */
  11770. +#define BAYCOM_IOCTL_TYPE       'B'
  11771. +
  11772. +#define KISS_FEND   ((unsigned char)0300)
  11773. +#define KISS_FESC   ((unsigned char)0333)
  11774. +#define KISS_TFEND  ((unsigned char)0334)
  11775. +#define KISS_TFESC  ((unsigned char)0335)
  11776. +
  11777. +#define KISS_CMD_DATA       0
  11778. +#define KISS_CMD_TXDELAY    1
  11779. +#define KISS_CMD_PPERSIST   2
  11780. +#define KISS_CMD_SLOTTIME   3
  11781. +#define KISS_CMD_TXTAIL     4
  11782. +#define KISS_CMD_FULLDUP    5
  11783. +
  11784. +/*
  11785. + * modem types
  11786. + */
  11787. +
  11788. +#define BAYCOM_MODEM_INVALID 0
  11789. +#define BAYCOM_MODEM_SER12   1
  11790. +#define BAYCOM_MODEM_PAR96   2
  11791. +
  11792. +/*
  11793. + * modem options; bit mask
  11794. + */
  11795. +#define BAYCOM_OPTIONS_SOFTDCD  1
  11796. +
  11797. +
  11798. +/*
  11799. + * ioctl constants
  11800. + */
  11801. +#define BAYCOMCTL_GETDCD           _IOR(BAYCOM_IOCTL_TYPE, 0, unsigned char)
  11802. +#define BAYCOMCTL_GETPTT           _IOR(BAYCOM_IOCTL_TYPE, 1, unsigned char)
  11803. +#define BAYCOMCTL_PARAM_TXDELAY    _IO(BAYCOM_IOCTL_TYPE, 2)
  11804. +#define BAYCOMCTL_PARAM_PPERSIST   _IO(BAYCOM_IOCTL_TYPE, 3)
  11805. +#define BAYCOMCTL_PARAM_SLOTTIME   _IO(BAYCOM_IOCTL_TYPE, 4)
  11806. +#define BAYCOMCTL_PARAM_TXTAIL     _IO(BAYCOM_IOCTL_TYPE, 5)
  11807. +#define BAYCOMCTL_PARAM_FULLDUP    _IO(BAYCOM_IOCTL_TYPE, 6)
  11808. +
  11809. +#define BAYCOMCTL_GETSTAT          _IOR(BAYCOM_IOCTL_TYPE, 7, \
  11810. +                    struct baycom_statistics)
  11811. +
  11812. +#define BAYCOMCTL_GETPARAMS        _IOR(BAYCOM_IOCTL_TYPE, 8, \
  11813. +                    struct baycom_params)
  11814. +#define BAYCOMCTL_SETPARAMS        _IOR(BAYCOM_IOCTL_TYPE, 9, \
  11815. +                    struct baycom_params)
  11816. +
  11817. +#define BAYCOMCTL_CALIBRATE        _IO(BAYCOM_IOCTL_TYPE, 10)
  11818. +
  11819. +#ifdef BAYCOM_DEBUG
  11820. +/*
  11821. + * these are mainly for debugging purposes
  11822. + */
  11823. +#define BAYCOMCTL_GETSAMPLES       _IOR(BAYCOM_IOCTL_TYPE, 16, unsigned char)
  11824. +#define BAYCOMCTL_GETBITS          _IOR(BAYCOM_IOCTL_TYPE, 17, unsigned char)
  11825. +
  11826. +#define BAYCOMCTL_DEBUG1           _IOR(BAYCOM_IOCTL_TYPE, 18, unsigned long)
  11827. +#define BAYCOMCTL_DEBUG2           _IOR(BAYCOM_IOCTL_TYPE, 19, unsigned long)
  11828. +#define BAYCOMCTL_DEBUG3           _IOR(BAYCOM_IOCTL_TYPE, 20, unsigned long)
  11829. +#endif /* BAYCOM_DEBUG */
  11830. +
  11831. +/* -------------------------------------------------------------------- */
  11832. +
  11833. +#endif /* _BAYCOM_H */
  11834. +
  11835. +/* --------------------------------------------------------------------- */
  11836. +
  11837. +/*
  11838. + * Overrides for Emacs so that we follow Linus's tabbing style.
  11839. + * Emacs will notice this stuff at the end of the file and automatically
  11840. + * adjust the settings for this buffer only.  This must remain at the end
  11841. + * of the file.
  11842. + * ---------------------------------------------------------------------------
  11843. + * Local variables:
  11844. + * c-indent-level: 8
  11845. + * c-brace-imaginary-offset: 0
  11846. + * c-brace-offset: -8
  11847. + * c-argdecl-indent: 8
  11848. + * c-label-offset: -8
  11849. + * c-continued-statement-offset: 8
  11850. + * c-continued-brace-offset: 0
  11851. + * End:
  11852. + */
  11853. diff -u --recursive --new-file pre2.0.4/linux/include/linux/cm206.h linux/include/linux/cm206.h
  11854. --- pre2.0.4/linux/include/linux/cm206.h    Mon May 13 23:02:49 1996
  11855. +++ linux/include/linux/cm206.h    Wed May 15 10:06:26 1996
  11856. @@ -5,6 +5,8 @@
  11857.  #ifndef LINUX_CM206_H
  11858.  #define LINUX_CM206_H
  11859.  
  11860. +#include <linux/ioctl.h>
  11861. +
  11862.  /* First, the cm260 stuff */
  11863.  /* The ports and irq used. Although CM206_BASE and CM206_IRQ are defined
  11864.     below, the values are not used unless autoprobing is turned off and 
  11865. @@ -128,13 +130,13 @@
  11866.  
  11867.  /* finally some ioctls for the driver */
  11868.  
  11869. -#define CM206CTL_GET_STAT 0x2000
  11870. -#define CM206CTL_GET_LAST_STAT 0x2001
  11871. +#define CM206CTL_GET_STAT _IO( 0x20, 0 )
  11872. +#define CM206CTL_GET_LAST_STAT _IO( 0x20, 1 )
  11873.  
  11874.  /* for kernel 1.2.n */
  11875.  #if !defined(CDROM_GET_UPC)
  11876. -#define CDROM_GET_UPC 0x5311
  11877. -#define CDROMRESET 0x5312
  11878. +#define CDROM_GET_UPC _IO( 'S', 0x11 )
  11879. +#define CDROMRESET _IO( 'S', 0x12 )
  11880.  #endif
  11881.  
  11882.  #ifdef STATISTICS
  11883. diff -u --recursive --new-file pre2.0.4/linux/include/linux/fs.h linux/include/linux/fs.h
  11884. --- pre2.0.4/linux/include/linux/fs.h    Wed May 15 11:01:15 1996
  11885. +++ linux/include/linux/fs.h    Fri May 17 15:05:01 1996
  11886. @@ -272,7 +272,7 @@
  11887.      uid_t        i_uid;
  11888.      gid_t        i_gid;
  11889.      kdev_t        i_rdev;
  11890. -    off_t        i_size;
  11891. +    unsigned long    i_size;
  11892.      time_t        i_atime;
  11893.      time_t        i_mtime;
  11894.      time_t        i_ctime;
  11895. @@ -359,12 +359,10 @@
  11896.  #define FLOCK_VERIFY_READ  1
  11897.  #define FLOCK_VERIFY_WRITE 2
  11898.  
  11899. -#ifdef CONFIG_LOCK_MANDATORY     
  11900.  extern int locks_mandatory_locked(struct inode *inode);
  11901.  extern int locks_mandatory_area(int read_write, struct inode *inode,
  11902.                  struct file *filp, unsigned int offset,
  11903.                  unsigned int count);
  11904. -#endif
  11905.  
  11906.  extern inline int locks_verify_locked(struct inode *inode)
  11907.  {
  11908. diff -u --recursive --new-file pre2.0.4/linux/include/linux/iso_fs.h linux/include/linux/iso_fs.h
  11909. --- pre2.0.4/linux/include/linux/iso_fs.h    Sat Apr 13 18:22:07 1996
  11910. +++ linux/include/linux/iso_fs.h    Wed May 15 09:09:00 1996
  11911. @@ -124,21 +124,6 @@
  11912.  #define ISOFS_BUFFER_BITS(INODE) ((INODE)->i_sb->s_blocksize_bits)
  11913.  #define ISOFS_ZONE_BITS(INODE)   ((INODE)->i_sb->u.isofs_sb.s_log_zone_size)
  11914.  
  11915. -#if 0
  11916. -#ifdef ISOFS_FIXED_BLOCKSIZE
  11917. -/* We use these until the buffer cache supports 2048 */
  11918. -#define ISOFS_BUFFER_BITS 10
  11919. -#define ISOFS_BUFFER_SIZE 1024
  11920. -
  11921. -#define ISOFS_BLOCK_NUMBER(X) (X<<1)
  11922. -#else
  11923. -#define ISOFS_BUFFER_BITS 11
  11924. -#define ISOFS_BUFFER_SIZE 2048
  11925. -
  11926. -#define ISOFS_BLOCK_NUMBER(X) (X)
  11927. -#endif
  11928. -#endif
  11929. -
  11930.  #define ISOFS_SUPER_MAGIC 0x9660
  11931.  #define ISOFS_FILE_UNKNOWN 0
  11932.  #define ISOFS_FILE_TEXT 1
  11933. diff -u --recursive --new-file pre2.0.4/linux/include/linux/mcdx.h linux/include/linux/mcdx.h
  11934. --- pre2.0.4/linux/include/linux/mcdx.h    Mon May 13 23:02:49 1996
  11935. +++ linux/include/linux/mcdx.h    Fri May 17 15:24:15 1996
  11936. @@ -1,7 +1,7 @@
  11937.  /*
  11938.   * Definitions for the Mitsumi CDROM interface
  11939.   * Copyright (C) 1995 Heiko Schlittermann <heiko@lotte.sax.de>
  11940. - * VERSION: 2.2
  11941. + * VERSION: 2.3
  11942.   * 
  11943.   * This program is free software; you can redistribute it and/or modify
  11944.   * it under the terms of the GNU General Public License as published by
  11945. @@ -40,11 +40,13 @@
  11946.   *      o       MCDX_NDRIVES  :  number of used entries of the following table
  11947.   *      o       MCDX_DRIVEMAP :  table of {i/o base, irq} per controller
  11948.   *
  11949. - *      NOTE: I didn't get a drive at irq 9(2) working.  Not even alone.
  11950. + *      NOTE: Don't even think about connecting the drive to IRQ 9(2).
  11951. + *    In the AT architecture this interrupt is used to cascade the two
  11952. + *    interrupt controllers and isn't therefore usable for enything else!
  11953.   */
  11954.   /* #define I_WAS_IN_MCDX_H */
  11955.  #define MCDX_NDRIVES 1
  11956. -#define MCDX_DRIVEMAP {    {0x300, 11},    \
  11957. +#define MCDX_DRIVEMAP {    {0x230, 11},    \
  11958.              {0x304, 05},      \
  11959.              {0x000, 00},      \
  11960.              {0x000, 00},      \
  11961. diff -u --recursive --new-file pre2.0.4/linux/include/linux/module.h linux/include/linux/module.h
  11962. --- pre2.0.4/linux/include/linux/module.h    Sun Mar 17 16:15:05 1996
  11963. +++ linux/include/linux/module.h    Tue May 14 14:55:51 1996
  11964. @@ -28,6 +28,7 @@
  11965.  
  11966.  /* magic marker for modules inserted from kerneld, to be auto-reaped */
  11967.  #define MOD_AUTOCLEAN 0x40000000 /* big enough, but no sign problems... */
  11968. +#define MOD_VISITED   0x20000000 /* Thanks Jacques! */
  11969.  
  11970.  /* maximum length of symbol name */
  11971.  #define SYM_MAX_NAME 60
  11972. @@ -88,9 +89,9 @@
  11973.  #ifdef MODULE
  11974.  
  11975.  extern long mod_use_count_;
  11976. -#define MOD_INC_USE_COUNT      mod_use_count_++
  11977. -#define MOD_DEC_USE_COUNT      mod_use_count_--
  11978. -#define MOD_IN_USE           ((mod_use_count_ & ~MOD_AUTOCLEAN) != 0)
  11979. +#define MOD_INC_USE_COUNT      (mod_use_count_++, mod_use_count_ |= MOD_VISITED)
  11980. +#define MOD_DEC_USE_COUNT      (mod_use_count_--, mod_use_count_ |= MOD_VISITED)
  11981. +#define MOD_IN_USE           ((mod_use_count_ & ~(MOD_AUTOCLEAN | MOD_VISITED)) != 0)
  11982.  
  11983.  #ifndef __NO_VERSION__
  11984.  #include <linux/version.h>
  11985. diff -u --recursive --new-file pre2.0.4/linux/include/linux/socket.h linux/include/linux/socket.h
  11986. --- pre2.0.4/linux/include/linux/socket.h    Fri Apr 12 15:52:08 1996
  11987. +++ linux/include/linux/socket.h    Thu May 16 16:35:42 1996
  11988. @@ -16,22 +16,22 @@
  11989.      int        l_linger;    /* How long to linger for    */
  11990.  };
  11991.  
  11992. +/*
  11993. + *    As we do 4.4BSD message passing we use a 4.4BSD message passing
  11994. + *    system, not 4.3. Thus msg_accrights(len) are now missing. They
  11995. + *    belong in an obscure libc emulation or the bin.
  11996. + */
  11997.  struct msghdr 
  11998.  {
  11999.      void    *    msg_name;    /* Socket name            */
  12000.      int        msg_namelen;    /* Length of name        */
  12001.      struct iovec *    msg_iov;    /* Data blocks            */
  12002.      int         msg_iovlen;    /* Number of blocks        */
  12003. -    void     *    msg_accrights;    /* Per protocol magic (eg BSD file descriptor passing) */
  12004. -    int        msg_accrightslen;    /* Length of rights list */
  12005. +    void     *    msg_control;    /* Per protocol magic (eg BSD file descriptor passing) */
  12006. +    int        msg_controllen;    /* Length of rights list */
  12007. +    int        msg_flags;    /* 4.4 BSD item we dont use      */
  12008.  };
  12009. -
  12010. -/*
  12011. - *    4.4BSD changed to these new names for no apparent reason.
  12012. - */
  12013. -#define msg_control    msg_accrights    
  12014. -#define msg_controllen    msg_accrightslen
  12015.  
  12016.  /* Control Messages */
  12017.  
  12018. diff -u --recursive --new-file pre2.0.4/linux/include/linux/tty.h linux/include/linux/tty.h
  12019. --- pre2.0.4/linux/include/linux/tty.h    Wed Apr 24 17:00:43 1996
  12020. +++ linux/include/linux/tty.h    Fri May 17 15:05:01 1996
  12021. @@ -292,6 +292,7 @@
  12022.  extern int stl_init(void);
  12023.  extern int stli_init(void);
  12024.  extern int riscom8_init(void);
  12025. +extern int baycom_init(void);
  12026.  
  12027.  extern int tty_paranoia_check(struct tty_struct *tty, kdev_t device,
  12028.                    const char *routine);
  12029. diff -u --recursive --new-file pre2.0.4/linux/include/net/ip_masq.h linux/include/net/ip_masq.h
  12030. --- pre2.0.4/linux/include/net/ip_masq.h    Tue Apr 23 13:57:14 1996
  12031. +++ linux/include/net/ip_masq.h    Fri May 17 15:10:53 1996
  12032. @@ -84,7 +84,7 @@
  12033.  /*
  12034.   *    functions called from ip layer
  12035.   */
  12036. -extern void ip_fw_masquerade(struct sk_buff **, struct device *);
  12037. +extern int ip_fw_masquerade(struct sk_buff **, struct device *);
  12038.  extern int ip_fw_demasquerade(struct sk_buff **, struct device *);
  12039.  
  12040.  /*
  12041. @@ -149,6 +149,7 @@
  12042.   *    service routine(s).
  12043.   */
  12044.  extern struct ip_masq * ip_masq_out_get_2(int protocol, __u32 s_addr, __u16 s_port, __u32 d_addr, __u16 d_port);
  12045. +extern struct ip_masq * ip_masq_in_get_2(int protocol, __u32 s_addr, __u16 s_port, __u32 d_addr, __u16 d_port);
  12046.  
  12047.  /*
  12048.   *    /proc/net entry
  12049. diff -u --recursive --new-file pre2.0.4/linux/include/net/netlink.h linux/include/net/netlink.h
  12050. --- pre2.0.4/linux/include/net/netlink.h    Tue May  7 16:22:39 1996
  12051. +++ linux/include/net/netlink.h    Fri May 17 15:10:43 1996
  12052. @@ -2,8 +2,8 @@
  12053.  #define __NET_NETLINK_H
  12054.  
  12055.  #define NET_MAJOR 36        /* Major 18 is reserved for networking                         */
  12056. -#define MAX_LINKS 9        /* 18,0 for route updates, 18,1 for SKIP, 18,2 debug tap 18,3 PPP reserved     */
  12057. -                /* 4-7 are psi0-psi3 */
  12058. +#define MAX_LINKS 10        /* 18,0 for route updates, 18,1 for SKIP, 18,2 debug tap 18,3 PPP reserved     */
  12059. +                /* 4-7 are psi0-psi3  8 is arpd 9 is ppp */
  12060.  #define MAX_QBYTES 32768    /* Maximum bytes in the queue                             */
  12061.  
  12062.  #include <linux/config.h>
  12063. @@ -20,6 +20,7 @@
  12064.  #define NETLINK_FIREWALL    3    /* Firewalling hook                */
  12065.  #define NETLINK_PSI        4    /* PSI devices - 4 to 7 */
  12066.  #define NETLINK_ARPD        8
  12067. +#define NETLINK_NET_PPP        9    /* Non tty PPP devices */
  12068.  
  12069.  #ifdef CONFIG_RTNETLINK
  12070.  extern void ip_netlink_msg(unsigned long, __u32, __u32, __u32, short, short, char *);
  12071. diff -u --recursive --new-file pre2.0.4/linux/include/net/sock.h linux/include/net/sock.h
  12072. --- pre2.0.4/linux/include/net/sock.h    Tue May  7 16:22:39 1996
  12073. +++ linux/include/net/sock.h    Fri May 17 15:07:07 1996
  12074. @@ -195,8 +195,8 @@
  12075.      struct sock        *next;
  12076.      struct sock        *prev; /* Doubly linked chain.. */
  12077.      struct sock        *pair;
  12078. -    struct sk_buff        * volatile send_head;
  12079. -    struct sk_buff        * volatile send_tail;
  12080. +    struct sk_buff        * send_head;
  12081. +    struct sk_buff        * send_tail;
  12082.      struct sk_buff_head    back_log;
  12083.      struct sk_buff        *partial;
  12084.      struct timer_list    partial_timer;
  12085. @@ -211,33 +211,34 @@
  12086.      unsigned short        max_unacked;
  12087.      unsigned short        window;
  12088.      __u32                   lastwin_seq;    /* sequence number when we last updated the window we offer */
  12089. -    volatile unsigned long  ato;            /* ack timeout */
  12090. -    volatile unsigned long  lrcvtime;       /* jiffies at last rcv */
  12091. +    __u32            high_seq;    /* sequence number when we did current fast retransmit */
  12092. +    unsigned long        ato;            /* ack timeout */
  12093. +    unsigned long        lrcvtime;       /* jiffies at last rcv */
  12094.      unsigned short        bytes_rcv;
  12095.  /*
  12096.   *    mss is min(mtu, max_window) 
  12097.   */
  12098.      unsigned short        mtu;       /* mss negotiated in the syn's */
  12099. -    volatile unsigned short    mss;       /* current eff. mss - can change */
  12100. -    volatile unsigned short    user_mss;  /* mss requested by user in ioctl */
  12101. -    volatile unsigned short    max_window;
  12102. +    unsigned short        mss;       /* current eff. mss - can change */
  12103. +    unsigned short        user_mss;  /* mss requested by user in ioctl */
  12104. +    unsigned short        max_window;
  12105.      unsigned long         window_clamp;
  12106. +    unsigned int        ssthresh;
  12107.      unsigned short        num;
  12108. -    volatile unsigned short    cong_window;
  12109. -    volatile unsigned short    cong_count;
  12110. -    volatile unsigned short    ssthresh;
  12111. -    volatile unsigned short    packets_out;
  12112. -    volatile unsigned short    shutdown;
  12113. -    volatile unsigned long    rtt;
  12114. -    volatile unsigned long    mdev;
  12115. -    volatile unsigned long    rto;
  12116. +    unsigned short        cong_window;
  12117. +    unsigned short        cong_count;
  12118. +    unsigned short        packets_out;
  12119. +    unsigned short        shutdown;
  12120. +    unsigned long        rtt;
  12121. +    unsigned long        mdev;
  12122. +    unsigned long        rto;
  12123.  
  12124.  /*
  12125.   *    currently backoff isn't used, but I'm maintaining it in case
  12126.   *    we want to go back to a backoff formula that needs it
  12127.   */
  12128.   
  12129. -    volatile unsigned short    backoff;
  12130. +    unsigned short        backoff;
  12131.      int            err, err_soft;    /* Soft holds errors that don't
  12132.                             cause failure but are the cause
  12133.                             of a persistent failure not just
  12134. @@ -412,7 +413,7 @@
  12135.  
  12136.  static inline void lock_sock(struct sock *sk)
  12137.  {
  12138. -#if 1
  12139. +#if 0
  12140.  /* debugging code: the test isn't even 100% correct, but it can catch bugs */
  12141.  /* Note that a double lock is ok in theory - it's just _usually_ a bug */
  12142.      if (sk->users) {
  12143. @@ -428,7 +429,7 @@
  12144.  static inline void release_sock(struct sock *sk)
  12145.  {
  12146.      barrier();
  12147. -#if 1
  12148. +#if 0
  12149.  /* debugging code: remove me when ok */
  12150.      if (sk->users == 0) {
  12151.          __label__ here;
  12152. @@ -437,7 +438,7 @@
  12153.  here:
  12154.      }
  12155.  #endif
  12156. -    if (!--sk->users)
  12157. +    if ((sk->users = sk->users-1) == 0)
  12158.          __release_sock(sk);
  12159.  }
  12160.  
  12161. diff -u --recursive --new-file pre2.0.4/linux/include/net/tcp.h linux/include/net/tcp.h
  12162. --- pre2.0.4/linux/include/net/tcp.h    Sun May 12 10:16:07 1996
  12163. +++ linux/include/net/tcp.h    Fri May 17 15:10:17 1996
  12164. @@ -155,7 +155,7 @@
  12165.  extern void tcp_send_synack(struct sock *, struct sock *, struct sk_buff *);
  12166.  extern void tcp_send_skb(struct sock *, struct sk_buff *);
  12167.  extern void tcp_send_ack(struct sock *sk);
  12168. -extern void tcp_send_delayed_ack(struct sock *sk, int timeout);
  12169. +extern void tcp_send_delayed_ack(struct sock *sk, int max_timeout, unsigned long timeout);
  12170.  extern void tcp_send_reset(unsigned long saddr, unsigned long daddr, struct tcphdr *th,
  12171.        struct proto *prot, struct options *opt, struct device *dev, int tos, int ttl);
  12172.  
  12173. diff -u --recursive --new-file pre2.0.4/linux/init/main.c linux/init/main.c
  12174. --- pre2.0.4/linux/init/main.c    Sat May 11 10:42:07 1996
  12175. +++ linux/init/main.c    Thu May 16 16:35:55 1996
  12176. @@ -156,6 +156,9 @@
  12177.  #ifdef CONFIG_RISCOM8
  12178.  extern void riscom8_setup(char *str, int *ints);
  12179.  #endif
  12180. +#ifdef CONFIG_BAYCOM
  12181. +extern void baycom_setup(char *str, int *ints);
  12182. +#endif
  12183.  
  12184.  
  12185.  #if defined(CONFIG_SYSVIPC) || defined(CONFIG_KERNELD)
  12186. @@ -391,6 +394,9 @@
  12187.  #endif
  12188.  #ifdef CONFIG_RISCOM8
  12189.      { "riscom8=", riscom8_setup },
  12190. +#endif
  12191. +#ifdef CONFIG_BAYCOM
  12192. +    { "baycom=", baycom_setup },
  12193.  #endif
  12194.      { 0, 0 }
  12195.  };
  12196. diff -u --recursive --new-file pre2.0.4/linux/kernel/module.c linux/kernel/module.c
  12197. --- pre2.0.4/linux/kernel/module.c    Tue May  7 16:22:40 1996
  12198. +++ linux/kernel/module.c    Tue May 14 14:55:51 1996
  12199. @@ -55,8 +55,6 @@
  12200.  static int get_mod_name( char *user_name, char *buf);
  12201.  static int free_modules( void);
  12202.  
  12203. -static int module_init_flag = 0; /* Hmm... */
  12204. -
  12205.  extern struct symbol_table symbol_table; /* in kernel/ksyms.c */
  12206.  
  12207.  /*
  12208. @@ -147,7 +145,7 @@
  12209.      /* A little bit of protection... we "know" where the user stack is... */
  12210.  
  12211.      if (symtab && ((unsigned long)symtab > 0xb0000000)) {
  12212. -        printk("warning: you are using an old insmod, no symbols will be inserted!\n");
  12213. +        printk(KERN_WARNING "warning: you are using an old insmod, no symbols will be inserted!\n");
  12214.          symtab = NULL;
  12215.      }
  12216.  #endif
  12217. @@ -211,7 +209,7 @@
  12218.              newtab->n_refs * sizeof(struct module_ref);
  12219.  
  12220.          if ((newtab->n_symbols < 0) || (newtab->n_refs < 0) || (legal_start > size)) {
  12221. -            printk("Rejecting illegal symbol table (n_symbols=%d,n_refs=%d)\n",
  12222. +            printk(KERN_WARNING "Rejecting illegal symbol table (n_symbols=%d,n_refs=%d)\n",
  12223.                     newtab->n_symbols, newtab->n_refs);
  12224.              kfree_s(newtab, size);
  12225.              return -EINVAL;
  12226. @@ -220,7 +218,7 @@
  12227.          /* relocate name pointers, index referred from start of table */
  12228.          for (sym = &(newtab->symbol[0]), i = 0; i < newtab->n_symbols; ++sym, ++i) {
  12229.              if ((unsigned long)sym->name < legal_start || size <= (unsigned long)sym->name) {
  12230. -                printk("Rejecting illegal symbol table\n");
  12231. +                printk(KERN_WARNING "Rejecting illegal symbol table\n");
  12232.                  kfree_s(newtab, size);
  12233.                  return -EINVAL;
  12234.              }
  12235. @@ -246,7 +244,7 @@
  12236.                  link = link->next;
  12237.  
  12238.              if (link == (struct module *)0) {
  12239. -                printk("Non-module reference! Rejected!\n");
  12240. +                printk(KERN_WARNING "Non-module reference! Rejected!\n");
  12241.                  return -EINVAL;
  12242.              }
  12243.  
  12244. @@ -256,12 +254,12 @@
  12245.          }
  12246.      }
  12247.  
  12248. -    module_init_flag = 1; /* Hmm... */
  12249. +    GET_USE_COUNT(mp) += 1;
  12250.      if ((*rt.init)() != 0) {
  12251. -        module_init_flag = 0; /* Hmm... */
  12252. +        GET_USE_COUNT(mp) = 0;
  12253.          return -EBUSY;
  12254.      }
  12255. -    module_init_flag = 0; /* Hmm... */
  12256. +    GET_USE_COUNT(mp) -= 1;
  12257.      mp->state = MOD_RUNNING;
  12258.  
  12259.      return 0;
  12260. @@ -282,9 +280,10 @@
  12261.              return error;
  12262.          if ((mp = find_module(name)) == NULL)
  12263.              return -ENOENT;
  12264. -        if ((mp->ref != NULL) || ((GET_USE_COUNT(mp) & ~MOD_AUTOCLEAN) != 0))
  12265. +        if ((mp->ref != NULL) ||
  12266. +            ((GET_USE_COUNT(mp) & ~(MOD_AUTOCLEAN | MOD_VISITED)) != 0))
  12267.              return -EBUSY;
  12268. -        GET_USE_COUNT(mp) &= ~MOD_AUTOCLEAN;
  12269. +        GET_USE_COUNT(mp) &= ~(MOD_AUTOCLEAN | MOD_VISITED);
  12270.          if (mp->state == MOD_RUNNING)
  12271.              (*mp->cleanup)();
  12272.          mp->state = MOD_DELETED;
  12273. @@ -293,11 +292,17 @@
  12274.      /* for automatic reaping */
  12275.      else {
  12276.          for (mp = module_list; mp != &kernel_module; mp = mp->next) {
  12277. -            if ((mp->ref == NULL) && (GET_USE_COUNT(mp) == MOD_AUTOCLEAN) &&
  12278. -                (mp->state == MOD_RUNNING)) {
  12279. -                GET_USE_COUNT(mp) &= ~MOD_AUTOCLEAN;
  12280. -                (*mp->cleanup)();
  12281. -                mp->state = MOD_DELETED;
  12282. +            if ((mp->ref == NULL) && (mp->state == MOD_RUNNING) &&
  12283. +                ((GET_USE_COUNT(mp) & ~(MOD_AUTOCLEAN | MOD_VISITED)) == 0)) {
  12284. +                    if ((GET_USE_COUNT(mp) & MOD_VISITED)) {
  12285. +                    /* Don't reap until one "cycle" after last _use_ */
  12286. +                       GET_USE_COUNT(mp) &= ~MOD_VISITED;
  12287. +                }
  12288. +                else {
  12289. +                    GET_USE_COUNT(mp) &= ~(MOD_AUTOCLEAN | MOD_VISITED);
  12290. +                    (*mp->cleanup)();
  12291. +                    mp->state = MOD_DELETED;
  12292. +                }
  12293.              }
  12294.          }
  12295.          free_modules();
  12296. @@ -534,7 +539,7 @@
  12297.          }
  12298.          if (mp->state == MOD_RUNNING) {
  12299.              sprintf(size,"\t%ld%s",
  12300. -                GET_USE_COUNT(mp) & ~MOD_AUTOCLEAN,
  12301. +                GET_USE_COUNT(mp) & ~(MOD_AUTOCLEAN | MOD_VISITED),
  12302.                  ((GET_USE_COUNT(mp) & MOD_AUTOCLEAN)?
  12303.                      " (autoclean)":""));
  12304.              q = size;
  12305. @@ -639,11 +644,17 @@
  12306.              intab->n_symbols +=1;
  12307.      }
  12308.  
  12309. -#if 1
  12310. -    if (module_init_flag == 0) { /* Hmm... */
  12311. -#else
  12312. -    if (module_list == &kernel_module) {
  12313. -#endif
  12314. +    for (mp = module_list; intab && mp != &kernel_module; mp = mp->next) {
  12315. +        /*
  12316. +         * New table stored within memory belonging to a module?
  12317. +         * (Always true for a module)
  12318. +         */
  12319. +        if (((unsigned long)(mp->addr) < (unsigned long)intab) &&
  12320. +            ((unsigned long)intab < ((unsigned long)(mp->addr) + mp->size * PAGE_SIZE)))
  12321. +            break;
  12322. +    }
  12323. +
  12324. +    if (mp == &kernel_module) {
  12325.          /* Aha! Called from an "internal" module */
  12326.          if (!intab)
  12327.              return 0; /* or -ESILLY_PROGRAMMER :-) */
  12328. @@ -651,7 +662,7 @@
  12329.          /* create a pseudo module! */
  12330.          if (!(mp = (struct module*) kmalloc(MODSIZ, GFP_KERNEL))) {
  12331.              /* panic time! */
  12332. -            printk("Out of memory for new symbol table!\n");
  12333. +            printk(KERN_ERR "Out of memory for new symbol table!\n");
  12334.              return -ENOMEM;
  12335.          }
  12336.          /* else  OK */
  12337. @@ -674,7 +685,6 @@
  12338.       * call to  init_module  i.e. when loading the module!!
  12339.       * Or else...
  12340.       */
  12341. -    mp = module_list; /* true when doing init_module! */
  12342.  
  12343.      /* Any table there before? */
  12344.      if ((oldtab = mp->symtab) == (struct symbol_table*)0) {
  12345. @@ -684,12 +694,6 @@
  12346.      }
  12347.  
  12348.      /* else  ****** we have to replace the module symbol table ******/
  12349. -#if 0
  12350. -    if (oldtab->n_symbols > 0) {
  12351. -        /* Oh dear, I have to drop the old ones... */
  12352. -        printk("Warning, dropping old symbols\n");
  12353. -    }
  12354. -#endif
  12355.  
  12356.      if (oldtab->n_refs == 0) { /* no problems! */
  12357.          mp->symtab = intab;
  12358. @@ -714,7 +718,7 @@
  12359.              oldtab->n_refs * REFSIZ,
  12360.          GFP_KERNEL))) {
  12361.          /* panic time! */
  12362. -        printk("Out of memory for new symbol table!\n");
  12363. +        printk(KERN_ERR "Out of memory for new symbol table!\n");
  12364.          return -ENOMEM;
  12365.      }
  12366.  
  12367. diff -u --recursive --new-file pre2.0.4/linux/mm/filemap.c linux/mm/filemap.c
  12368. --- pre2.0.4/linux/mm/filemap.c    Tue May  7 16:22:40 1996
  12369. +++ linux/mm/filemap.c    Thu May 16 11:31:43 1996
  12370. @@ -117,11 +117,17 @@
  12371.      struct page * page;
  12372.      unsigned long limit = MAP_NR(high_memory);
  12373.      struct buffer_head *tmp, *bh;
  12374. +    int count_max, count_min;
  12375. +
  12376. +    count_max = (limit<<1) >> (priority>>1);
  12377. +    count_min = (limit<<1) >> (priority);
  12378.  
  12379. -    priority = (limit<<2) >> priority;
  12380.      page = mem_map + clock;
  12381.      do {
  12382. -        priority--;
  12383. +        count_max--;
  12384. +        if (page->inode || page->buffers)
  12385. +            count_min--;
  12386. +
  12387.          if (PageLocked(page))
  12388.              goto next;
  12389.          if (dma && !PageDMA(page))
  12390. @@ -179,7 +185,7 @@
  12391.              clock = 0;
  12392.              page = mem_map;
  12393.          }
  12394. -    } while (priority > 0);
  12395. +    } while (count_max > 0 && count_min > 0);
  12396.      return 0;
  12397.  }
  12398.  
  12399. diff -u --recursive --new-file pre2.0.4/linux/mm/memory.c linux/mm/memory.c
  12400. --- pre2.0.4/linux/mm/memory.c    Sat Apr 27 15:20:09 1996
  12401. +++ linux/mm/memory.c    Thu May 16 15:15:36 1996
  12402. @@ -76,7 +76,7 @@
  12403.   */
  12404.  void oom(struct task_struct * task)
  12405.  {
  12406. -    printk("\nOut of memory for %s.\n", current->comm);
  12407. +    printk("\nOut of memory for %s.\n", task->comm);
  12408.      task->sig->action[SIGKILL-1].sa_handler = NULL;
  12409.      task->blocked &= ~(1<<(SIGKILL-1));
  12410.      send_sig(SIGKILL,task,1);
  12411. diff -u --recursive --new-file pre2.0.4/linux/net/Makefile linux/net/Makefile
  12412. --- pre2.0.4/linux/net/Makefile    Fri Apr 12 15:52:10 1996
  12413. +++ linux/net/Makefile    Thu May 16 16:35:55 1996
  12414. @@ -8,7 +8,7 @@
  12415.  # Note 2! The CFLAGS definition is now in the main makefile...
  12416.  
  12417.  MOD_SUB_DIRS := ipv4
  12418. -ALL_SUB_DIRS := 802 ax25 bridge core ethernet ipv4 ipx unix appletalk netrom 
  12419. +ALL_SUB_DIRS := 802 ax25 bridge core ethernet ipv4 ipx unix appletalk netrom #decnet
  12420.  SUB_DIRS     := core ethernet unix
  12421.  MOD_LIST_NAME := NET_MISC_MODULES
  12422.  
  12423. diff -u --recursive --new-file pre2.0.4/linux/net/ax25/af_ax25.c linux/net/ax25/af_ax25.c
  12424. --- pre2.0.4/linux/net/ax25/af_ax25.c    Mon May 13 23:02:51 1996
  12425. +++ linux/net/ax25/af_ax25.c    Thu May 16 16:35:55 1996
  12426. @@ -1950,7 +1950,7 @@
  12427.          return sock_error(sk);
  12428.      }
  12429.  
  12430. -    if (flags|| msg->msg_accrights)
  12431. +    if (flags|| msg->msg_control)
  12432.          return -EINVAL;
  12433.  
  12434.      if (sk->zapped)
  12435. diff -u --recursive --new-file pre2.0.4/linux/net/core/dev.c linux/net/core/dev.c
  12436. --- pre2.0.4/linux/net/core/dev.c    Mon May 13 23:02:51 1996
  12437. +++ linux/net/core/dev.c    Thu May 16 16:35:55 1996
  12438. @@ -45,6 +45,8 @@
  12439.   *        Alan Cox    :    Cleaned up the backlog initialise.
  12440.   *        Craig Metz    :    SIOCGIFCONF fix if space for under
  12441.   *                    1 device.
  12442. + *        Thomas Bogendoerfer :    Return ENODEV for dev_open, if there
  12443. + *                    is no device open function.
  12444.   *
  12445.   */
  12446.  
  12447. @@ -236,7 +238,7 @@
  12448.   
  12449.  int dev_open(struct device *dev)
  12450.  {
  12451. -    int ret = 0;
  12452. +    int ret = -ENODEV;
  12453.  
  12454.      /*
  12455.       *    Call device private open method
  12456. diff -u --recursive --new-file pre2.0.4/linux/net/core/iovec.c linux/net/core/iovec.c
  12457. --- pre2.0.4/linux/net/core/iovec.c    Sat Apr 27 15:20:10 1996
  12458. +++ linux/net/core/iovec.c    Thu May 16 16:35:55 1996
  12459. @@ -41,9 +41,9 @@
  12460.              return err;
  12461.          m->msg_name = address;
  12462.      }
  12463. -    if(m->msg_accrights!=NULL)
  12464. +    if(m->msg_control!=NULL)
  12465.      {
  12466. -        err=verify_area(mode, m->msg_accrights, m->msg_accrightslen);
  12467. +        err=verify_area(mode, m->msg_control, m->msg_controllen);
  12468.          if(err)
  12469.              return err;
  12470.      }
  12471. diff -u --recursive --new-file pre2.0.4/linux/net/core/net_alias.c linux/net/core/net_alias.c
  12472. --- pre2.0.4/linux/net/core/net_alias.c    Mon May 13 23:02:51 1996
  12473. +++ linux/net/core/net_alias.c    Thu May 16 16:35:55 1996
  12474. @@ -509,7 +509,7 @@
  12475.    {
  12476.      if (!(alias = prevdev->next->my_alias))
  12477.      {
  12478. -      printk(KERN_ERR "ERROR: net_alias_dev_delete(): incorrect non-alias device after maindev\n");
  12479. +      printk(KERN_ERR "net_alias_dev_delete(): incorrect non-alias device after maindev\n");
  12480.        continue;            /* or should give up? */
  12481.      }
  12482.      if (alias->slot == slot) break;
  12483. @@ -537,7 +537,7 @@
  12484.        printk(KERN_WARNING "net_alias_dev_delete(%s): bad hashing recovered\n", alias->name);
  12485.      else
  12486.      {
  12487. -      printk(KERN_ERR "ERROR: net_alias_dev_delete(%s): unhashed alias!\n",alias->name);
  12488. +      printk(KERN_ERR "net_alias_dev_delete(%s): unhashed alias!\n",alias->name);
  12489.        return NULL;        /* ENODEV */
  12490.      }
  12491.    
  12492. @@ -760,7 +760,7 @@
  12493.    
  12494.    if (!sa)
  12495.    {
  12496. -    printk(KERN_ERR "ERROR: net_alias_rehash(): NULL sockaddr passed\n");
  12497. +    printk(KERN_ERR "net_alias_rehash(): NULL sockaddr passed\n");
  12498.      return -1;
  12499.    }
  12500.  
  12501. @@ -770,7 +770,7 @@
  12502.  
  12503.    if ( (main_dev = alias->main_dev) == NULL )
  12504.    {
  12505. -    printk(KERN_ERR "ERROR: net_alias_rehash for %s: NULL maindev\n", alias->name);
  12506. +    printk(KERN_ERR "net_alias_rehash for %s: NULL maindev\n", alias->name);
  12507.      return -1;
  12508.    }
  12509.  
  12510. @@ -780,7 +780,7 @@
  12511.  
  12512.    if (!(alias_info=main_dev->alias_info))
  12513.    {
  12514. -    printk(KERN_ERR "ERROR: net_alias_rehash for %s: NULL alias_info\n", alias->name);
  12515. +    printk(KERN_ERR "net_alias_rehash for %s: NULL alias_info\n", alias->name);
  12516.      return -1;
  12517.    }
  12518.    
  12519. @@ -791,7 +791,7 @@
  12520.    o_nat = alias->nat;
  12521.    if (!o_nat)
  12522.    {
  12523. -    printk(KERN_ERR "ERROR: net_alias_rehash(%s): unbound alias.\n", alias->name);
  12524. +    printk(KERN_ERR "net_alias_rehash(%s): unbound alias.\n", alias->name);
  12525.      return -1;
  12526.    }
  12527.  
  12528. @@ -806,7 +806,7 @@
  12529.      n_nat = nat_getbytype(sa->sa_family);
  12530.      if (!n_nat)
  12531.      {
  12532. -      printk(KERN_ERR "ERROR: net_alias_rehash(%s): unreg family==%d.\n", alias->name, sa->sa_family);
  12533. +      printk(KERN_ERR "net_alias_rehash(%s): unreg family==%d.\n", alias->name, sa->sa_family);
  12534.        return -1;
  12535.      }
  12536.    }
  12537. @@ -835,7 +835,7 @@
  12538.        printk(KERN_WARNING "net_alias_rehash(%s): bad hashing recovered\n", alias->name);
  12539.      else
  12540.      {
  12541. -      printk(KERN_ERR "ERROR: net_alias_rehash(%s): unhashed alias!\n", alias->name);
  12542. +      printk(KERN_ERR "net_alias_rehash(%s): unhashed alias!\n", alias->name);
  12543.        return -1;
  12544.      }
  12545.    
  12546. diff -u --recursive --new-file pre2.0.4/linux/net/decnet/README linux/net/decnet/README
  12547. --- pre2.0.4/linux/net/decnet/README    Thu Jan  1 02:00:00 1970
  12548. +++ linux/net/decnet/README    Thu May 16 16:35:55 1996
  12549. @@ -0,0 +1,6 @@
  12550. +Yes.. its being worked on.
  12551. +
  12552. +If you want to get involved email me <Alan.Cox@linux.org> and I'll put you
  12553. +in touch with the people doing the work.
  12554. +
  12555. +Alan
  12556. diff -u --recursive --new-file pre2.0.4/linux/net/ipv4/Config.in linux/net/ipv4/Config.in
  12557. --- pre2.0.4/linux/net/ipv4/Config.in    Mon May 13 23:02:51 1996
  12558. +++ linux/net/ipv4/Config.in    Thu May 16 16:35:55 1996
  12559. @@ -12,10 +12,14 @@
  12560.    tristate 'IP: tunneling' CONFIG_NET_IPIP
  12561.    if [ "$CONFIG_IP_FIREWALL" = "y" ]; then
  12562.      bool 'IP: firewall packet logging' CONFIG_IP_FIREWALL_VERBOSE
  12563. -    bool 'IP: masquerading (ALPHA)' CONFIG_IP_MASQUERADE
  12564. +    if [ "$CONFIG_EXPERIMENTAL" = "y" ]; then
  12565. +      bool 'IP: masquerading (ALPHA)' CONFIG_IP_MASQUERADE
  12566. +    fi
  12567.    fi
  12568.    if [ "$CONFIG_IP_MULTICAST" = "y" ]; then
  12569. -    bool 'IP: multicast routing (EXPERIMENTAL)' CONFIG_IP_MROUTE
  12570. +      if [ "$CONFIG_EXPERIMENTAL" = "y" ]; then
  12571. +        bool 'IP: multicast routing (EXPERIMENTAL)' CONFIG_IP_MROUTE
  12572. +      fi        
  12573.    fi
  12574.  fi
  12575.  if [ "$CONFIG_NET_ALIAS" = "y" ]; then
  12576. diff -u --recursive --new-file pre2.0.4/linux/net/ipv4/icmp.c linux/net/ipv4/icmp.c
  12577. --- pre2.0.4/linux/net/ipv4/icmp.c    Sat Apr 27 15:20:10 1996
  12578. +++ linux/net/ipv4/icmp.c    Thu May 16 16:35:55 1996
  12579. @@ -24,6 +24,8 @@
  12580.   *        Martin Mares    :    Echo requests may be configured to be ignored (RFC 1812).
  12581.   *        Martin Mares    :    Limitation of ICMP error message transmit rate (RFC 1812).
  12582.   *        Martin Mares    :    TOS and Precedence set correctly (RFC 1812).
  12583. + *        Martin Mares    :    Now copying as much data from the original packet
  12584. + *                    as we can without exceeding 576 bytes (RFC 1812).
  12585.   *
  12586.   *
  12587.   *
  12588. @@ -98,7 +100,7 @@
  12589.   *   MUST initialize TTL when originating an ICMP message (OK)
  12590.   *  4.3.2.3 (Original Message Header)
  12591.   *   SHOULD copy as much data from the offending packet as possible without
  12592. - *     the length of the ICMP datagram exceeding 576 bytes (NOT YET)
  12593. + *     the length of the ICMP datagram exceeding 576 bytes (OK)
  12594.   *   MUST leave original IP header of the offending packet, but we're not
  12595.   *     required to undo modifications made (OK)
  12596.   *  4.3.2.4 (Original Message Source Address)
  12597. @@ -171,8 +173,8 @@
  12598.   *     compile-time option)
  12599.   *   SHOULD have option for each interface for AMRe's, MUST default to NO (NOT YET)
  12600.   *   MUST NOT reply to AMRq before knows the correct AM (OK)
  12601. - *   MUST NOT respond to AMRq with source address 0.0.0.0 and the AM's for
  12602. - *     logical i-faces for the physical i-face are not the same (NOT YET)
  12603. + *   MUST NOT respond to AMRq with source address 0.0.0.0 on physical interfaces
  12604. + *     having multiple logical i-faces with different masks (NOT YET)
  12605.   *   SHOULD examine all AMRe's it receives and check them (NOT YET)
  12606.   *   SHOULD log invalid AMRe's (AM+sender) (NOT YET)
  12607.   *   MUST NOT use contents of AMRe to determine correct AM (OK)
  12608. @@ -188,7 +190,7 @@
  12609.   *   SHOULD choose a best-match response code (OK)
  12610.   *   SHOULD NOT generate Host Isolated codes (OK)
  12611.   *   SHOULD use Communication Administratively Prohibited when administratively
  12612. - *     filtering packets (NOT YET)
  12613. + *     filtering packets (NOT YET -- bug-to-bug compatibility)
  12614.   *   MAY include config option for not generating the above and silently discard
  12615.   *     the packets instead (OK)
  12616.   *   MAY include config option for not generating Precedence Violation and
  12617. @@ -496,7 +498,7 @@
  12618.  /*
  12619.   *    Send an ICMP message in response to a situation
  12620.   *
  12621. - *    RFC 1122: 3.2.2    MUST send at least the IP header and 8 bytes of header. MAY send more (we don't).
  12622. + *    RFC 1122: 3.2.2    MUST send at least the IP header and 8 bytes of header. MAY send more (we do).
  12623.   *            MUST NOT change this header information.
  12624.   *            MUST NOT reply to a multicast/broadcast IP address.
  12625.   *            MUST NOT reply to a multicast/broadcast MAC address.
  12626. @@ -507,7 +509,7 @@
  12627.  {
  12628.      struct iphdr *iph;
  12629.      struct icmphdr *icmph;
  12630. -    int atype;
  12631. +    int atype, room;
  12632.      struct icmp_bxm icmp_param;
  12633.      __u32 saddr;
  12634.      
  12635. @@ -572,25 +574,33 @@
  12636.  #endif    
  12637.  
  12638.      /*
  12639. -     *    Tell our driver what to send
  12640. +     *    Construct source address and options.
  12641.       */
  12642.       
  12643.      saddr=iph->daddr;
  12644.      if(saddr!=dev->pa_addr && ip_chk_addr(saddr)!=IS_MYADDR)
  12645.          saddr=dev->pa_addr;
  12646. -    
  12647. +    if(ip_options_echo(&icmp_param.replyopts, NULL, saddr, iph->saddr, skb_in))
  12648. +        return;
  12649. +
  12650. +    /*
  12651. +     *    Prepare data for ICMP header.
  12652. +     */
  12653. +
  12654.      icmp_param.icmph.type=type;
  12655.      icmp_param.icmph.code=code;
  12656.      icmp_param.icmph.un.gateway = info;
  12657.      icmp_param.data_ptr=iph;
  12658. -    icmp_param.data_len=(iph->ihl<<2)+8;    /* RFC says return header + 8 bytes */
  12659. +    room = 576 - sizeof(struct iphdr) - icmp_param.replyopts.optlen;
  12660. +    icmp_param.data_len=(iph->ihl<<2)+skb_in->len;    /* RFC says return as much as we can without exceeding 576 bytes */
  12661. +    if (icmp_param.data_len > room)
  12662. +        icmp_param.data_len = room;
  12663.      
  12664.      /*
  12665. -     *    Set it to build.
  12666. +     *    Build and send the packet.
  12667.       */
  12668.  
  12669. -    if (ip_options_echo(&icmp_param.replyopts, NULL, saddr, iph->saddr, skb_in) == 0)
  12670. -      icmp_build_xmit(&icmp_param, saddr, iph->saddr, ((iph->tos & 0x38) | 6));
  12671. +    icmp_build_xmit(&icmp_param, saddr, iph->saddr, ((iph->tos & 0x38) | 6));
  12672.  }
  12673.  
  12674.  
  12675. diff -u --recursive --new-file pre2.0.4/linux/net/ipv4/ip_forward.c linux/net/ipv4/ip_forward.c
  12676. --- pre2.0.4/linux/net/ipv4/ip_forward.c    Mon May 13 23:02:52 1996
  12677. +++ linux/net/ipv4/ip_forward.c    Wed May 15 10:30:15 1996
  12678. @@ -250,7 +250,15 @@
  12679.           * (Don't masquerade de-masqueraded fragments)
  12680.           */
  12681.          if (!(is_frag&IPFWD_MASQUERADED) && fw_res==FW_MASQUERADE)
  12682. -            ip_fw_masquerade(&skb, dev2);
  12683. +            if (ip_fw_masquerade(&skb, dev2) < 0)
  12684. +            {
  12685. +                /*
  12686. +                 * Masquerading failed; silently discard this packet.
  12687. +                 */
  12688. +                if (rt)
  12689. +                    ip_rt_put(rt);
  12690. +                return -1;
  12691. +            }
  12692.  #endif
  12693.          IS_SKB(skb);
  12694.  
  12695. diff -u --recursive --new-file pre2.0.4/linux/net/ipv4/ip_masq.c linux/net/ipv4/ip_masq.c
  12696. --- pre2.0.4/linux/net/ipv4/ip_masq.c    Tue May  7 16:22:41 1996
  12697. +++ linux/net/ipv4/ip_masq.c    Thu May 16 16:35:56 1996
  12698. @@ -12,7 +12,7 @@
  12699.   *    Juan Jose Ciarlante    :    Added hashed lookup by proto,maddr,mport and proto,saddr,sport
  12700.   *    Juan Jose Ciarlante    :    Fixed deadlock if free ports get exhausted
  12701.   *    Juan Jose Ciarlante    :    Added NO_ADDR status flag.
  12702. - *
  12703. + *    Nigel Metheringham    :    ICMP handling.
  12704.   *    
  12705.   */
  12706.  
  12707. @@ -27,8 +27,10 @@
  12708.  #include <linux/in.h>
  12709.  #include <linux/ip.h>
  12710.  #include <net/protocol.h>
  12711. +#include <net/icmp.h>
  12712.  #include <net/tcp.h>
  12713.  #include <net/udp.h>
  12714. +#include <net/checksum.h>
  12715.  #include <net/ip_masq.h>
  12716.  
  12717.  #define IP_MASQ_TAB_SIZE 256    /* must be power of 2 */
  12718. @@ -192,8 +194,6 @@
  12719.  struct ip_masq *
  12720.  ip_masq_in_get(struct iphdr *iph)
  12721.  {
  12722. -        unsigned hash;
  12723. -        struct ip_masq *ms;
  12724.       __u16 *portptr;
  12725.          int protocol;
  12726.          __u32 s_addr, d_addr;
  12727. @@ -206,6 +206,29 @@
  12728.          d_addr = iph->daddr;
  12729.          d_port = portptr[1];
  12730.  
  12731. +        return ip_masq_in_get_2(protocol, s_addr, s_port, d_addr, d_port);
  12732. +}
  12733. +
  12734. +/*
  12735. + *    Returns ip_masq associated with supplied parameters, either
  12736. + *    broken out of the ip/tcp headers or directly supplied for those
  12737. + *    pathological protocols with address/port in the data stream
  12738. + *    (ftp, irc).  addresses and ports are in network order.
  12739. + *    called for pkts coming from INside-to-outside the firewall.
  12740. + *
  12741. + *     NB. Cannot check destination address, just for the incoming port.
  12742. + *     reason: archie.doc.ac.uk has 6 interfaces, you send to
  12743. + *     phoenix and get a reply from any other interface(==dst)!
  12744. + *
  12745. + *     [Only for UDP] - AC
  12746. + */
  12747. +
  12748. +struct ip_masq *
  12749. +ip_masq_in_get_2(int protocol, __u32 s_addr, __u16 s_port, __u32 d_addr, __u16 d_port)
  12750. +{
  12751. +        unsigned hash;
  12752. +        struct ip_masq *ms;
  12753. +
  12754.          hash = ip_masq_hash_key(protocol, d_addr, d_port);
  12755.          for(ms = ip_masq_m_tab[hash]; ms ; ms = ms->m_link) {
  12756.           if ( protocol==ms->protocol &&
  12757. @@ -293,7 +316,7 @@
  12758.  #ifdef DEBUG_CONFIG_IP_MASQUERADE
  12759.      printk("Masqueraded %s %lX:%X expired\n",
  12760.              masq_proto_name(ms->protocol),
  12761. -            ntohl(ms->src),ntohs(ms->sport));
  12762. +            ntohl(ms->saddr),ntohs(ms->sport));
  12763.  #endif
  12764.      
  12765.      save_flags(flags);
  12766. @@ -424,7 +447,7 @@
  12767.          uh->check=0xFFFF;
  12768.  }
  12769.      
  12770. -void ip_fw_masquerade(struct sk_buff **skb_ptr, struct device *dev)
  12771. +int ip_fw_masquerade(struct sk_buff **skb_ptr, struct device *dev)
  12772.  {
  12773.      struct sk_buff  *skb=*skb_ptr;
  12774.      struct iphdr    *iph = skb->h.iph;
  12775. @@ -438,7 +461,7 @@
  12776.       */
  12777.  
  12778.      if (iph->protocol!=IPPROTO_UDP && iph->protocol!=IPPROTO_TCP)
  12779. -        return;
  12780. +        return -1;
  12781.  
  12782.      /*
  12783.       *    Now hunt the list to see if we have an old entry
  12784. @@ -467,7 +490,7 @@
  12785.                                   iph->daddr, portptr[1],
  12786.                                   0);
  12787.                  if (ms == NULL)
  12788. -            return;
  12789. +            return -1;
  12790.       }
  12791.  
  12792.       /*
  12793. @@ -535,8 +558,92 @@
  12794.   #ifdef DEBUG_CONFIG_IP_MASQUERADE
  12795.       printk("O-routed from %lX:%X over %s\n",ntohl(ms->maddr),ntohs(ms->mport),dev->name);
  12796.   #endif
  12797. +
  12798. +    return 0;
  12799.   }
  12800.  
  12801. +/*
  12802. + *    Handle ICMP messages.
  12803. + *    Find any that might be relevant, check against existing connections,
  12804. + *    forward to masqueraded host if relevant.
  12805. + *    Currently handles error types - unreachable, quench, ttl exceeded
  12806. + */
  12807. +
  12808. +int ip_fw_demasq_icmp(struct sk_buff **skb_p, struct device *dev)
  12809. +{
  12810. +        struct sk_buff     *skb   = *skb_p;
  12811. +     struct iphdr    *iph   = skb->h.iph;
  12812. +    struct icmphdr  *icmph = (struct icmphdr *)((char *)iph + (iph->ihl<<2));
  12813. +    struct iphdr    *ciph;    /* The ip header contained within the ICMP */
  12814. +    __u16    *portptr;    /* port numbers from TCP/UDP contained header */
  12815. +    struct ip_masq    *ms;
  12816. +
  12817. +#ifdef DEBUG_CONFIG_IP_MASQUERADE
  12818. +     printk("Incoming ICMP (%d) %lX -> %lX\n",
  12819. +            icmph->type,
  12820. +         ntohl(iph->saddr), ntohl(iph->daddr));
  12821. +#endif
  12822. +
  12823. +    if ((icmph->type != ICMP_DEST_UNREACH) &&
  12824. +        (icmph->type != ICMP_SOURCE_QUENCH) &&
  12825. +        (icmph->type != ICMP_TIME_EXCEEDED))
  12826. +        return 0;
  12827. +
  12828. +    /* Now find the contained IP header */
  12829. +    ciph = (struct iphdr *) (icmph + 1);
  12830. +
  12831. +    /* We are only interested ICMPs generated from TCP or UDP packets */
  12832. +    if ((ciph->protocol != IPPROTO_UDP) && (ciph->protocol != IPPROTO_TCP))
  12833. +        return 0;
  12834. +
  12835. +    /* 
  12836. +     * Find the ports involved - remember this packet was 
  12837. +     * *outgoing* so the ports are reversed (and addresses)
  12838. +     */
  12839. +    portptr = (__u16 *)&(((char *)ciph)[ciph->ihl*4]);
  12840. +    if (ntohs(portptr[0]) < PORT_MASQ_BEGIN ||
  12841. +         ntohs(portptr[0]) > PORT_MASQ_END)
  12842. +         return 0;
  12843. +
  12844. +#ifdef DEBUG_CONFIG_IP_MASQUERADE
  12845. +     printk("Handling ICMP for %lX:%X -> %lX:%X\n",
  12846. +           ntohl(ciph->saddr), ntohs(portptr[0]),
  12847. +           ntohl(ciph->daddr), ntohs(portptr[1]));
  12848. +#endif
  12849. +
  12850. +    /* This is pretty much what ip_masq_in_get() does, except params are wrong way round */
  12851. +    ms = ip_masq_in_get_2(ciph->protocol, ciph->daddr, portptr[1], ciph->saddr, portptr[0]);
  12852. +
  12853. +    if (ms == NULL)
  12854. +        return 0;
  12855. +
  12856. +    /* Now we do real damage to this packet...! */
  12857. +    /* First change the dest IP address, and recalc checksum */
  12858. +    iph->daddr = ms->saddr;
  12859. +    ip_send_check(iph);
  12860. +    
  12861. +    /* Now change the *source* address in the contained IP */
  12862. +    ciph->saddr = ms->saddr;
  12863. +    ip_send_check(ciph);
  12864. +    
  12865. +    /* the TCP/UDP source port - cannot redo check */
  12866. +    portptr[0] = ms->sport;
  12867. +
  12868. +    /* And finally the ICMP checksum */
  12869. +    icmph->checksum = 0;
  12870. +    icmph->checksum = ip_compute_csum((unsigned char *) icmph, 
  12871. +                      skb->len - sizeof(struct iphdr));
  12872. +
  12873. +#ifdef DEBUG_CONFIG_IP_MASQUERADE
  12874. +     printk("Rewrote ICMP to %lX:%X -> %lX:%X\n",
  12875. +           ntohl(ciph->saddr), ntohs(portptr[0]),
  12876. +           ntohl(ciph->daddr), ntohs(portptr[1]));
  12877. +#endif
  12878. +
  12879. +    return 1;
  12880. +}
  12881. +
  12882. +
  12883.   /*
  12884.    *    Check if it's an masqueraded port, look it up,
  12885.    *    and send it on its way...
  12886. @@ -554,7 +661,8 @@
  12887.       struct ip_masq    *ms;
  12888.      unsigned short  frag;
  12889.  
  12890. -     if (iph->protocol!=IPPROTO_UDP && iph->protocol!=IPPROTO_TCP)
  12891. +     if (iph->protocol!=IPPROTO_UDP && iph->protocol!=IPPROTO_TCP 
  12892. +        && iph->protocol!=IPPROTO_ICMP)
  12893.           return 0;
  12894.  
  12895.      /*
  12896. @@ -567,6 +675,9 @@
  12897.      {
  12898.          return 0;
  12899.      }
  12900. +
  12901. +    if (iph->protocol == IPPROTO_ICMP)
  12902. +        return ip_fw_demasq_icmp(skb_p, dev);
  12903.  
  12904.       portptr = (__u16 *)&(((char *)iph)[iph->ihl*4]);
  12905.       if (ntohs(portptr[1]) < PORT_MASQ_BEGIN ||
  12906. diff -u --recursive --new-file pre2.0.4/linux/net/ipv4/route.c linux/net/ipv4/route.c
  12907. --- pre2.0.4/linux/net/ipv4/route.c    Tue May  7 16:22:42 1996
  12908. +++ linux/net/ipv4/route.c    Thu May 16 16:35:56 1996
  12909. @@ -1712,8 +1712,13 @@
  12910.  
  12911.  void ip_rt_update(int event, struct device *dev)
  12912.  {
  12913. +/*
  12914. + *    This causes too much grief to do now.
  12915. + */
  12916. +#ifdef COMING_IN_2_1
  12917.      if (event == NETDEV_UP)
  12918.          rt_add(RTF_HOST|RTF_UP, dev->pa_addr, ~0, 0, dev, 0, 0, 0, 0);
  12919.      else if (event == NETDEV_DOWN)
  12920.          rt_del(dev->pa_addr, ~0, dev, 0, RTF_HOST|RTF_UP, 0);
  12921. +#endif        
  12922.  }
  12923. diff -u --recursive --new-file pre2.0.4/linux/net/ipv4/tcp.c linux/net/ipv4/tcp.c
  12924. --- pre2.0.4/linux/net/ipv4/tcp.c    Mon May 13 23:02:53 1996
  12925. +++ linux/net/ipv4/tcp.c    Fri May 17 09:42:00 1996
  12926. @@ -200,7 +200,8 @@
  12927.   *                    against machines running Solaris,
  12928.   *                    and seems to result in general
  12929.   *                    improvement.
  12930. - *
  12931. + *    Stefan Magdalinski    :    adjusted tcp_readable() to fix FIONREAD
  12932. + *                    
  12933.   * To Fix:
  12934.   *        Fast path the code. Two things here - fix the window calculation
  12935.   *        so it doesn't iterate over the queue, also spot packets with no funny
  12936. @@ -519,11 +520,13 @@
  12937.      {
  12938.          /*
  12939.           * FIXME:
  12940. -         * For now we will just trigger a linear backoff.
  12941. -         * The slow start code should cause a real backoff here.
  12942. +         * Follow BSD for now and just reduce cong_window to 1 again.
  12943. +         * It is possible that we just want to reduce the
  12944. +         * window by 1/2, or that we want to reduce ssthresh by 1/2
  12945. +         * here as well.
  12946.           */
  12947. -        if (sk->cong_window > 4)
  12948. -            sk->cong_window--;
  12949. +        sk->cong_window = 1;
  12950. +        sk->high_seq = sk->sent_seq;
  12951.          return;
  12952.      }
  12953.  
  12954. @@ -644,7 +647,7 @@
  12955.           */
  12956.          if (skb->h.th->urg)
  12957.              amount--;    /* don't count urg data */
  12958. -        if (amount && skb->h.th->psh) break;
  12959. +/*        if (amount && skb->h.th->psh) break;*/
  12960.          skb = skb->next;
  12961.      }
  12962.      while(skb != (struct sk_buff *)&sk->receive_queue);
  12963. diff -u --recursive --new-file pre2.0.4/linux/net/ipv4/tcp_input.c linux/net/ipv4/tcp_input.c
  12964. --- pre2.0.4/linux/net/ipv4/tcp_input.c    Mon May 13 23:02:53 1996
  12965. +++ linux/net/ipv4/tcp_input.c    Fri May 17 09:42:00 1996
  12966. @@ -21,6 +21,10 @@
  12967.   *
  12968.   * FIXES
  12969.   *        Pedro Roque    :    Double ACK bug
  12970. + *        Eric Schenk    :    Fixes to slow start algorithm.
  12971. + *        Eric Schenk    :    Yet another double ACK bug.
  12972. + *        Eric Schenk    :    Delayed ACK bug fixes.
  12973. + *        Eric Schenk    :    Floyd style fast retrans war avoidance.
  12974.   */
  12975.  
  12976.  #include <linux/config.h>
  12977. @@ -57,7 +61,15 @@
  12978.          if (m <= 0)
  12979.              m = 1;
  12980.  
  12981. -        if (m > (sk->rtt >> 3)) 
  12982. +        /* Yikes. This used to test if m was larger than rtt/8.
  12983. +         * Maybe on a long delay high speed link this would be
  12984. +             * good initial guess, but over a slow link where the
  12985. +             * delay is dominated by transmission time this will
  12986. +             * be very bad, since ato will almost always be something
  12987. +         * more like rtt/2. Better to discard data points that
  12988. +         * are larger than the rtt estimate.
  12989. +             */
  12990. +        if (m > sk->rtt)
  12991.          {
  12992.              sk->ato = sk->rtt >> 3;
  12993.              /*
  12994. @@ -66,6 +78,11 @@
  12995.          }
  12996.          else 
  12997.          {
  12998. +            /*
  12999. +              * Very fast acting estimator.
  13000. +              * May fluctuate too much. Probably we should be
  13001. +             * doing something like the rtt estimator here.
  13002. +             */
  13003.              sk->ato = (sk->ato >> 1) + m;
  13004.              /*
  13005.               * printk(KERN_DEBUG "ato: m %lu\n", sk->ato);
  13006. @@ -104,14 +121,14 @@
  13007.      } else {
  13008.          /* no previous measure. */
  13009.          sk->rtt = m<<3;        /* take the measured time to be rtt */
  13010. -        sk->mdev = m<<2;    /* make sure rto = 3*rtt */
  13011. +        sk->mdev = m<<1;    /* make sure rto = 3*rtt */
  13012.      }
  13013.  
  13014.      /*
  13015.       *    Now update timeout.  Note that this removes any backoff.
  13016.       */
  13017.               
  13018. -    sk->rto = ((sk->rtt >> 2) + sk->mdev) >> 1;
  13019. +    sk->rto = (sk->rtt >> 3) + sk->mdev;
  13020.      if (sk->rto > 120*HZ)
  13021.          sk->rto = 120*HZ;
  13022.      if (sk->rto < HZ/5)    /* Was 1*HZ - keep .2 as minimum cos of the BSD delayed acks */
  13023. @@ -180,11 +197,9 @@
  13024.      }
  13025.  
  13026.      /*
  13027. -     *    4.3reno machines look for these kind of acks so they can do fast
  13028. -     *    recovery. Three identical 'old' acks lets it know that one frame has
  13029. -     *    been lost and should be resent. Because this is before the whole window
  13030. -     *    of data has timed out it can take one lost frame per window without
  13031. -     *    stalling. [See Jacobson RFC1323, Stevens TCP/IP illus vol2]
  13032. +     *     This packet is old news. Usually this is just a resend
  13033. +     *     from the far end, but sometimes it means the far end lost
  13034. +     *    an ACK we send, so we better send an ACK.
  13035.       */
  13036.      tcp_send_ack(sk);
  13037.  }
  13038. @@ -398,13 +413,19 @@
  13039.      newsk->send_head = NULL;
  13040.      newsk->send_tail = NULL;
  13041.      skb_queue_head_init(&newsk->back_log);
  13042. -    newsk->rtt = 0;        /*TCP_CONNECT_TIME<<3*/
  13043. +    newsk->rtt = 0;
  13044.      newsk->rto = TCP_TIMEOUT_INIT;
  13045. -    newsk->mdev = TCP_TIMEOUT_INIT<<1;
  13046. +    newsk->mdev = TCP_TIMEOUT_INIT;
  13047.      newsk->max_window = 0;
  13048. +    /*
  13049. +     * See draft-stevens-tcpca-spec-01 for discussion of the
  13050. +     * initialization of these values.
  13051. +     */
  13052.      newsk->cong_window = 1;
  13053.      newsk->cong_count = 0;
  13054. -    newsk->ssthresh = 0;
  13055. +    newsk->ssthresh = 0x7fffffff;
  13056. +
  13057. +    newsk->high_seq = 0;
  13058.      newsk->backoff = 0;
  13059.      newsk->blog = 0;
  13060.      newsk->intr = 0;
  13061. @@ -684,7 +705,7 @@
  13062.           * interpreting "new data is acked" as including data that has
  13063.           * been retransmitted but is just now being acked.
  13064.           */
  13065. -        if (sk->cong_window < sk->ssthresh)  
  13066. +        if (sk->cong_window <= sk->ssthresh)
  13067.              /* 
  13068.               *    In "safe" area, increase
  13069.               */
  13070. @@ -720,6 +741,8 @@
  13071.       * (2) it has the same window as the last ACK,
  13072.       * (3) we have outstanding data that has not been ACKed
  13073.       * (4) The packet was not carrying any data.
  13074. +     * (5) [From Floyds paper on fast retransmit wars]
  13075. +     *     The packet acked data after high_seq;
  13076.       * I've tried to order these in occurrence of most likely to fail
  13077.       * to least likely to fail.
  13078.       * [These are the rules BSD stacks use to determine if an ACK is a
  13079. @@ -729,7 +752,8 @@
  13080.      if (sk->rcv_ack_seq == ack
  13081.          && sk->window_seq == window_seq
  13082.          && !(flag&1)
  13083. -        && before(ack, sk->sent_seq))
  13084. +        && before(ack, sk->sent_seq)
  13085. +        && after(ack, sk->high_seq))
  13086.      {
  13087.          /* See draft-stevens-tcpca-spec-01 for explanation
  13088.           * of what we are doing here.
  13089. @@ -738,12 +762,16 @@
  13090.          if (sk->rcv_ack_cnt == MAX_DUP_ACKS+1) {
  13091.              sk->ssthresh = max(sk->cong_window >> 1, 2);
  13092.              sk->cong_window = sk->ssthresh+MAX_DUP_ACKS+1;
  13093. -            tcp_do_retransmit(sk,0);
  13094. -            /* reduce the count. We don't want to be
  13095. -            * seen to be in "retransmit" mode if we
  13096. -            * are doing a fast retransmit.
  13097. -            */
  13098. +            /* FIXME:
  13099. +             * reduce the count. We don't want to be
  13100. +             * seen to be in "retransmit" mode if we
  13101. +             * are doing a fast retransmit.
  13102. +             * This is also a signal to tcp_do_retransmit
  13103. +             * not to set sk->high_seq.
  13104. +             * This is a horrible ugly hack.
  13105. +             */
  13106.              sk->retransmits--;
  13107. +            tcp_do_retransmit(sk,0);
  13108.          } else if (sk->rcv_ack_cnt > MAX_DUP_ACKS+1) {
  13109.              sk->cong_window++;
  13110.              /*
  13111. @@ -795,7 +823,18 @@
  13112.               *    Recompute rto from rtt.  this eliminates any backoff.
  13113.               */
  13114.  
  13115. -            sk->rto = ((sk->rtt >> 2) + sk->mdev) >> 1;
  13116. +            /*
  13117. +             * Appendix C of Van Jacobson's final version of
  13118. +             * the SIGCOMM 88 paper states that although
  13119. +             * the original paper suggested that
  13120. +             *  RTO = R*2V
  13121. +             * was the correct calculation experience showed
  13122. +             * better results using
  13123. +             *  RTO = R*4V
  13124. +             * In particular this gives better performance over
  13125. +             * slow links, and should not effect fast links.
  13126. +             */
  13127. +            sk->rto = (sk->rtt >> 3) + sk->mdev;
  13128.              if (sk->rto > 120*HZ)
  13129.                  sk->rto = 120*HZ;
  13130.              if (sk->rto < HZ/5)    /* Was 1*HZ, then 1 - turns out we must allow about
  13131. @@ -827,7 +866,7 @@
  13132.              break;
  13133.  
  13134.          if (sk->retransmits) 
  13135. -        {    
  13136. +        {
  13137.              /*
  13138.               *    We were retransmitting.  don't count this in RTT est 
  13139.               */
  13140. @@ -1322,7 +1361,7 @@
  13141.              int delay = HZ/2;
  13142.              if (th->psh)
  13143.                  delay = HZ/50;
  13144. -            tcp_send_delayed_ack(sk, delay);
  13145. +            tcp_send_delayed_ack(sk, delay, sk->ato);
  13146.          }
  13147.  
  13148.          /*
  13149. @@ -1357,7 +1396,15 @@
  13150.              if(sk->debug)
  13151.                  printk("Ack past end of seq packet.\n");
  13152.              tcp_send_ack(sk);
  13153. -            tcp_send_delayed_ack(sk,HZ/2);
  13154. +            /*
  13155. +             * We need to be very careful here. We must
  13156. +             * not violate Jacobsons packet conservation condition.
  13157. +             * This means we should only send an ACK when a packet
  13158. +             * leaves the network. We can say a packet left the
  13159. +             * network when we see a packet leave the network, or
  13160. +             * when an rto measure expires.
  13161. +             */
  13162. +            tcp_send_delayed_ack(sk,sk->rto,sk->rto);
  13163.          }
  13164.      }
  13165.  }
  13166. @@ -1397,7 +1444,8 @@
  13167.          kfree_skb(skb, FREE_READ);
  13168.          return(0);
  13169.      }
  13170. -    
  13171. +
  13172. +
  13173.      /*
  13174.       *    We no longer have anyone receiving data on this connection.
  13175.       */
  13176. @@ -1455,6 +1503,11 @@
  13177.  
  13178.  #endif
  13179.  
  13180. +    /*
  13181. +       * We should only call this if there is data in the frame.
  13182. +      */
  13183. +    tcp_delack_estimator(sk);
  13184. +
  13185.      tcp_queue(skb, sk, th);
  13186.  
  13187.      return(0);
  13188. @@ -1900,8 +1953,6 @@
  13189.          return tcp_reset(sk,skb);    
  13190.      }
  13191.  
  13192. -    tcp_delack_estimator(sk);
  13193. -    
  13194.      /*
  13195.       *    Process the ACK
  13196.       */
  13197. diff -u --recursive --new-file pre2.0.4/linux/net/ipv4/tcp_output.c linux/net/ipv4/tcp_output.c
  13198. --- pre2.0.4/linux/net/ipv4/tcp_output.c    Mon May 13 23:02:53 1996
  13199. +++ linux/net/ipv4/tcp_output.c    Fri May 17 09:42:46 1996
  13200. @@ -188,7 +188,7 @@
  13201.          tcp_send_check(th, sk->saddr, sk->daddr, size, skb);
  13202.  
  13203.          sk->sent_seq = sk->write_seq;
  13204. -        
  13205. +
  13206.          /*
  13207.           *    This is mad. The tcp retransmit queue is put together
  13208.           *    by the ip layer. This causes half the problems with
  13209. @@ -527,6 +527,7 @@
  13210.              }
  13211.          }
  13212.          
  13213. +
  13214.          /*
  13215.           *    Count retransmissions
  13216.           */
  13217. @@ -535,6 +536,13 @@
  13218.          sk->retransmits++;
  13219.          sk->prot->retransmits++;
  13220.          tcp_statistics.TcpRetransSegs++;
  13221. +
  13222. +        /*
  13223. +         * Record the high sequence number to help avoid doing
  13224. +         * to much fast retransmission.
  13225. +         */
  13226. +        if (sk->retransmits)
  13227. +            sk->high_seq = sk->sent_seq;
  13228.          
  13229.  
  13230.          /*
  13231. @@ -821,20 +829,27 @@
  13232.   *      - delay time <= 0.5 HZ
  13233.   *      - must send at least every 2 full sized packets
  13234.   *      - we don't have a window update to send
  13235. + *
  13236. + *     additional thoughts:
  13237. + *    - we should not delay sending an ACK if we have ato > 0.5 HZ.
  13238. + *      My thinking about this is that in this case we will just be
  13239. + *      systematically skewing the RTT calculation. (The rule about
  13240. + *      sending every two full sized packets will never need to be
  13241. + *      invoked, the delayed ack will be sent before the ATO timeout
  13242. + *      every time. Of course, the relies on our having a good estimate
  13243. + *      for packet interarrival times.
  13244.   */
  13245. -void tcp_send_delayed_ack(struct sock * sk, int max_timeout)
  13246. +void tcp_send_delayed_ack(struct sock * sk, int max_timeout, unsigned long timeout)
  13247.  {
  13248. -    unsigned long timeout, now;
  13249. +    unsigned long now;
  13250.  
  13251.      /* Calculate new timeout */
  13252.      now = jiffies;
  13253. -    timeout = sk->ato;
  13254. -    if (timeout > max_timeout)
  13255. -        timeout = max_timeout;
  13256. -    timeout += now;
  13257. -    if (sk->bytes_rcv > sk->max_unacked) {
  13258. +    if (timeout > max_timeout || sk->bytes_rcv >= sk->max_unacked) {
  13259.          timeout = now;
  13260.          mark_bh(TIMER_BH);
  13261. +    } else {
  13262. +        timeout += now;
  13263.      }
  13264.  
  13265.      /* Use new timeout only if there wasn't a older one earlier  */
  13266. @@ -894,7 +909,7 @@
  13267.           *    resend packets. 
  13268.           */
  13269.  
  13270. -        tcp_send_delayed_ack(sk, HZ/2);
  13271. +        tcp_send_delayed_ack(sk, HZ/2, HZ/2);
  13272.          return;
  13273.      }
  13274.  
  13275. diff -u --recursive --new-file pre2.0.4/linux/net/socket.c linux/net/socket.c
  13276. --- pre2.0.4/linux/net/socket.c    Mon May 13 23:02:54 1996
  13277. +++ linux/net/socket.c    Thu May 16 16:35:56 1996
  13278. @@ -351,7 +351,7 @@
  13279.      msg.msg_name=NULL;
  13280.      msg.msg_iov=&iov;
  13281.      msg.msg_iovlen=1;
  13282. -    msg.msg_accrights=NULL;
  13283. +    msg.msg_control=NULL;
  13284.      iov.iov_base=ubuf;
  13285.      iov.iov_len=size;
  13286.  
  13287. @@ -386,7 +386,7 @@
  13288.      msg.msg_name=NULL;
  13289.      msg.msg_iov=&iov;
  13290.      msg.msg_iovlen=1;
  13291. -    msg.msg_accrights=NULL;
  13292. +    msg.msg_control=NULL;
  13293.      iov.iov_base=(void *)ubuf;
  13294.      iov.iov_len=size;
  13295.      
  13296. @@ -919,7 +919,7 @@
  13297.      msg.msg_name=NULL;
  13298.      msg.msg_iov=&iov;
  13299.      msg.msg_iovlen=1;
  13300. -    msg.msg_accrights=NULL;
  13301. +    msg.msg_control=NULL;
  13302.      return(sock->ops->sendmsg(sock, &msg, len, (file->f_flags & O_NONBLOCK), flags));
  13303.  }
  13304.  
  13305. @@ -959,7 +959,7 @@
  13306.      msg.msg_namelen=addr_len;
  13307.      msg.msg_iov=&iov;
  13308.      msg.msg_iovlen=1;
  13309. -    msg.msg_accrights=NULL;
  13310. +    msg.msg_control=NULL;
  13311.      return(sock->ops->sendmsg(sock, &msg, len, (file->f_flags & O_NONBLOCK),
  13312.          flags));
  13313.  }
  13314. @@ -994,7 +994,7 @@
  13315.      msg.msg_name=NULL;
  13316.      msg.msg_iov=&iov;
  13317.      msg.msg_iovlen=1;
  13318. -    msg.msg_accrights=NULL;
  13319. +    msg.msg_control=NULL;
  13320.      iov.iov_base=ubuf;
  13321.      iov.iov_len=size;
  13322.  
  13323. @@ -1030,7 +1030,7 @@
  13324.      if(err)
  13325.            return err;
  13326.    
  13327. -      msg.msg_accrights=NULL;
  13328. +      msg.msg_control=NULL;
  13329.        msg.msg_iovlen=1;
  13330.        msg.msg_iov=&iov;
  13331.        iov.iov_len=size;
  13332. diff -u --recursive --new-file pre2.0.4/linux/net/unix/af_unix.c linux/net/unix/af_unix.c
  13333. --- pre2.0.4/linux/net/unix/af_unix.c    Wed May 15 11:01:16 1996
  13334. +++ linux/net/unix/af_unix.c    Thu May 16 16:35:56 1996
  13335. @@ -361,6 +361,9 @@
  13336.       *    Linux we behave like files and pipes do and wait for the last dereference.
  13337.       */
  13338.       
  13339. +    sock->data = NULL;
  13340. +    sk->socket = NULL;
  13341. +    
  13342.      return 0;
  13343.  }
  13344.  
  13345. @@ -916,14 +919,14 @@
  13346.      /*
  13347.       *    A control message has been attached.
  13348.       */
  13349. -    if(msg->msg_accrights) 
  13350. +    if(msg->msg_control) 
  13351.      {
  13352. -        struct cmsghdr *cm=unix_copyrights(msg->msg_accrights, 
  13353. -                        msg->msg_accrightslen);
  13354. -        if(cm==NULL || msg->msg_accrightslen<sizeof(struct cmsghdr) ||
  13355. +        struct cmsghdr *cm=unix_copyrights(msg->msg_control, 
  13356. +                        msg->msg_controllen);
  13357. +        if(cm==NULL || msg->msg_controllen<sizeof(struct cmsghdr) ||
  13358.             cm->cmsg_type!=SCM_RIGHTS ||
  13359.             cm->cmsg_level!=SOL_SOCKET ||
  13360. -           msg->msg_accrightslen!=cm->cmsg_len)
  13361. +           msg->msg_controllen!=cm->cmsg_len)
  13362.          {
  13363.              kfree(cm);
  13364.                 return -EINVAL;
  13365. @@ -1072,22 +1075,22 @@
  13366.      if(sk->err)
  13367.          return sock_error(sk);
  13368.  
  13369. -    if(msg->msg_accrights) 
  13370. +    if(msg->msg_control) 
  13371.      {
  13372. -        cm=unix_copyrights(msg->msg_accrights, 
  13373. -            msg->msg_accrightslen);
  13374. -        if(msg->msg_accrightslen<sizeof(struct cmsghdr)
  13375. +        cm=unix_copyrights(msg->msg_control, 
  13376. +            msg->msg_controllen);
  13377. +        if(msg->msg_controllen<sizeof(struct cmsghdr)
  13378.  #if 0 
  13379.  /*        investigate this further -- Stevens example doesn't seem to care */
  13380.          ||
  13381.             cm->cmsg_type!=SCM_RIGHTS ||
  13382.             cm->cmsg_level!=SOL_SOCKET ||
  13383. -           msg->msg_accrightslen!=cm->cmsg_len
  13384. +           msg->msg_controllen!=cm->cmsg_len
  13385.  #endif
  13386.          )
  13387.          {
  13388.              kfree(cm);
  13389. -/*            printk("recvmsg: Bad msg_accrights\n");*/
  13390. +/*            printk("recvmsg: Bad msg_control\n");*/
  13391.                 return -EINVAL;
  13392.          }
  13393.      }
  13394. @@ -1160,7 +1163,7 @@
  13395.  out:
  13396.      up(&sk->protinfo.af_unix.readsem);
  13397.      if(cm)
  13398. -        unix_returnrights(msg->msg_accrights,msg->msg_accrightslen,cm);
  13399. +        unix_returnrights(msg->msg_control,msg->msg_controllen,cm);
  13400.      return copied;
  13401.  }
  13402.  
  13403.