]> git.pld-linux.org Git - packages/kernel.git/blob - linux-2.4.20-rc1-IDE.patch
- added description of djurban's branch
[packages/kernel.git] / linux-2.4.20-rc1-IDE.patch
1 diff -Nur linux-2.4.19/drivers/ide/Config.in linux-2.4.19.new/drivers/ide/Config.in
2 --- linux-2.4.19/drivers/ide/Config.in  Sat Aug  3 02:39:44 2002
3 +++ linux-2.4.19.new/drivers/ide/Config.in      Wed Nov 13 09:49:39 2002
4 @@ -65,14 +65,14 @@
5             dep_mbool '      ALI M15x3 WDC support (DANGEROUS)' CONFIG_WDC_ALI15X3 $CONFIG_BLK_DEV_ALI15X3
6             dep_bool '    AMD Viper support' CONFIG_BLK_DEV_AMD74XX $CONFIG_BLK_DEV_IDEDMA_PCI
7             dep_mbool '      AMD Viper ATA-66 Override (WIP)' CONFIG_AMD74XX_OVERRIDE $CONFIG_BLK_DEV_AMD74XX $CONFIG_IDEDMA_PCI_WIP
8 -           dep_bool '    CMD64X chipset support' CONFIG_BLK_DEV_CMD64X $CONFIG_BLK_DEV_IDEDMA_PCI
9 +           dep_bool '    CMD64X and CMD680 chipset support' CONFIG_BLK_DEV_CMD64X $CONFIG_BLK_DEV_IDEDMA_PCI
10             dep_bool '    CMD680 chipset tuning support' CONFIG_BLK_DEV_CMD680 $CONFIG_BLK_DEV_CMD64X
11             dep_bool '    CY82C693 chipset support' CONFIG_BLK_DEV_CY82C693 $CONFIG_BLK_DEV_IDEDMA_PCI
12             dep_bool '    Cyrix CS5530 MediaGX chipset support' CONFIG_BLK_DEV_CS5530 $CONFIG_BLK_DEV_IDEDMA_PCI
13             dep_bool '    HPT34X chipset support' CONFIG_BLK_DEV_HPT34X $CONFIG_BLK_DEV_IDEDMA_PCI
14             dep_mbool '      HPT34X AUTODMA support (WIP)' CONFIG_HPT34X_AUTODMA $CONFIG_BLK_DEV_HPT34X $CONFIG_IDEDMA_PCI_WIP
15             dep_bool '    HPT366/368/370 chipset support' CONFIG_BLK_DEV_HPT366 $CONFIG_BLK_DEV_IDEDMA_PCI
16 -           if [ "$CONFIG_X86" = "y" -o "$CONFIG_IA64" = "y" ]; then
17 +           if [ "$CONFIG_X86" = "y" -o "$CONFIG_IA64" = "y" -o "$CONFIG_MIPS" = "y" ]; then
18                dep_mbool '    Intel PIIXn chipsets support' CONFIG_BLK_DEV_PIIX $CONFIG_BLK_DEV_IDEDMA_PCI
19                dep_mbool '      PIIXn Tuning support' CONFIG_PIIX_TUNING $CONFIG_BLK_DEV_PIIX $CONFIG_IDEDMA_PCI_AUTO
20             fi
21 @@ -108,7 +108,7 @@
22          fi
23        fi
24        if [ "$CONFIG_SIBYTE_SWARM" = "y" ]; then
25 -        bool '  SWARM onboard IDE support' CONFIG_BLK_DEV_IDE_SWARM
26 +        bool '  Broadcom SiByte onboard IDE support' CONFIG_BLK_DEV_IDE_SIBYTE
27        fi
28        if [ "$CONFIG_ARCH_ACORN" = "y" ]; then
29          dep_bool '    ICS IDE interface support' CONFIG_BLK_DEV_IDE_ICSIDE $CONFIG_ARCH_ACORN
30 @@ -144,7 +144,8 @@
31                  EXT_DIRECT     CONFIG_IDE_EXT_DIRECT"  8xx_PCCARD
32        fi
33  
34 -      bool '  Other IDE chipset support' CONFIG_IDE_CHIPSETS
35 +      # no isa -> no vlb
36 +      dep_bool '  Other IDE chipset support' CONFIG_IDE_CHIPSETS $CONFIG_ISA
37        if [ "$CONFIG_IDE_CHIPSETS" = "y" ]; then
38          comment 'Note: most of these also require special kernel boot parameters'
39          bool '    Generic 4 drives/port support' CONFIG_BLK_DEV_4DRIVES
40 @@ -209,8 +210,8 @@
41     define_bool CONFIG_BLK_DEV_IDE_MODES n
42  fi
43  
44 -dep_tristate 'Support for IDE Raid controllers' CONFIG_BLK_DEV_ATARAID $CONFIG_BLK_DEV_IDE $CONFIG_EXPERIMENTAL
45 -dep_tristate '   Support Promise software RAID (Fasttrak(tm))' CONFIG_BLK_DEV_ATARAID_PDC $CONFIG_BLK_DEV_IDE $CONFIG_EXPERIMENTAL $CONFIG_BLK_DEV_ATARAID
46 -dep_tristate '   Highpoint 370 software RAID' CONFIG_BLK_DEV_ATARAID_HPT $CONFIG_BLK_DEV_IDE $CONFIG_EXPERIMENTAL $CONFIG_BLK_DEV_ATARAID
47 +dep_tristate 'Support for IDE Raid controllers (EXPERIMENTAL)' CONFIG_BLK_DEV_ATARAID $CONFIG_BLK_DEV_IDE $CONFIG_EXPERIMENTAL
48 +dep_tristate '   Support Promise software RAID (Fasttrak(tm)) (EXPERIMENTAL)' CONFIG_BLK_DEV_ATARAID_PDC $CONFIG_BLK_DEV_IDE $CONFIG_EXPERIMENTAL $CONFIG_BLK_DEV_ATARAID
49 +dep_tristate '   Highpoint 370 software RAID (EXPERIMENTAL)' CONFIG_BLK_DEV_ATARAID_HPT $CONFIG_BLK_DEV_IDE $CONFIG_EXPERIMENTAL $CONFIG_BLK_DEV_ATARAID
50  
51  endmenu
52 diff -Nur linux-2.4.19/drivers/ide/Makefile linux-2.4.19.new/drivers/ide/Makefile
53 --- linux-2.4.19/drivers/ide/Makefile   Sat Aug  3 02:39:44 2002
54 +++ linux-2.4.19.new/drivers/ide/Makefile       Wed Nov 13 09:49:39 2002
55 @@ -49,7 +49,7 @@
56  ide-obj-$(CONFIG_BLK_DEV_IDEPCI)       += ide-pci.o
57  ide-obj-$(CONFIG_BLK_DEV_ISAPNP)       += ide-pnp.o
58  ide-obj-$(CONFIG_BLK_DEV_IDE_PMAC)     += ide-pmac.o
59 -ide-obj-$(CONFIG_BLK_DEV_IDE_SWARM)    += ide-swarm.o
60 +ide-obj-$(CONFIG_BLK_DEV_IDE_SIBYTE)   += ide-sibyte.o
61  ide-obj-$(CONFIG_BLK_DEV_MAC_IDE)      += macide.o
62  ide-obj-$(CONFIG_BLK_DEV_NS87415)      += ns87415.o
63  ide-obj-$(CONFIG_BLK_DEV_OPTI621)      += opti621.o
64 diff -Nur linux-2.4.19/drivers/ide/ide-cd.c linux-2.4.19.new/drivers/ide/ide-cd.c
65 --- linux-2.4.19/drivers/ide/ide-cd.c   Sat Aug  3 02:39:44 2002
66 +++ linux-2.4.19.new/drivers/ide/ide-cd.c       Wed Nov 13 09:49:39 2002
67 @@ -2194,6 +2194,8 @@
68            layer. the packet must be complete, as we do not
69            touch it at all. */
70         memset(&pc, 0, sizeof(pc));
71 +       if (cgc->sense)
72 +               memset(cgc->sense, 0, sizeof(struct request_sense));
73         memcpy(pc.c, cgc->cmd, CDROM_PACKET_SIZE);
74         pc.buffer = cgc->buffer;
75         pc.buflen = cgc->buflen;
76 diff -Nur linux-2.4.19/drivers/ide/ide-cs.c linux-2.4.19.new/drivers/ide/ide-cs.c
77 --- linux-2.4.19/drivers/ide/ide-cs.c   Sat Aug  3 02:39:44 2002
78 +++ linux-2.4.19.new/drivers/ide/ide-cs.c       Wed Nov 13 09:49:39 2002
79 @@ -15,7 +15,7 @@
80      rights and limitations under the License.
81  
82      The initial developer of the original code is David A. Hinds
83 -    <dhinds@pcmcia.sourceforge.org>.  Portions created by David A. Hinds
84 +    <dahinds@users.sourceforge.net>.  Portions created by David A. Hinds
85      are Copyright (C) 1999 David A. Hinds.  All Rights Reserved.
86  
87      Alternatively, the contents of this file may be used under the
88 diff -Nur linux-2.4.19/drivers/ide/ide-disk.c linux-2.4.19.new/drivers/ide/ide-disk.c
89 --- linux-2.4.19/drivers/ide/ide-disk.c Sat Aug  3 02:39:44 2002
90 +++ linux-2.4.19.new/drivers/ide/ide-disk.c     Wed Nov 13 09:49:39 2002
91 @@ -29,6 +29,7 @@
92   * Version 1.10                request queue changes, Ultra DMA 100
93   * Version 1.11                added 48-bit lba
94   * Version 1.12                adding taskfile io access method
95 + *                     Highmem I/O support, Jens Axboe <axboe@suse.de>
96   */
97  
98  #define IDEDISK_VERSION        "1.12"
99 @@ -158,7 +159,9 @@
100         byte stat;
101         int i;
102         unsigned int msect, nsect;
103 +       unsigned long flags;
104         struct request *rq;
105 +       char *to;
106  
107         /* new way for dealing with premature shared PCI interrupts */
108         if (!OK_STAT(stat=GET_STAT(),DATA_READY,BAD_R_STAT)) {
109 @@ -169,8 +172,8 @@
110                 ide_set_handler(drive, &read_intr, WAIT_CMD, NULL);
111                 return ide_started;
112         }
113 +
114         msect = drive->mult_count;
115 -       
116  read_next:
117         rq = HWGROUP(drive)->rq;
118         if (msect) {
119 @@ -179,14 +182,15 @@
120                 msect -= nsect;
121         } else
122                 nsect = 1;
123 -       idedisk_input_data(drive, rq->buffer, nsect * SECTOR_WORDS);
124 +       to = ide_map_buffer(rq, &flags);
125 +       idedisk_input_data(drive, to, nsect * SECTOR_WORDS);
126  #ifdef DEBUG
127         printk("%s:  read: sectors(%ld-%ld), buffer=0x%08lx, remaining=%ld\n",
128                 drive->name, rq->sector, rq->sector+nsect-1,
129                 (unsigned long) rq->buffer+(nsect<<9), rq->nr_sectors-nsect);
130  #endif
131 +       ide_unmap_buffer(to, &flags);
132         rq->sector += nsect;
133 -       rq->buffer += nsect<<9;
134         rq->errors = 0;
135         i = (rq->nr_sectors -= nsect);
136         if (((long)(rq->current_nr_sectors -= nsect)) <= 0)
137 @@ -220,14 +224,16 @@
138  #endif
139                 if ((rq->nr_sectors == 1) ^ ((stat & DRQ_STAT) != 0)) {
140                         rq->sector++;
141 -                       rq->buffer += 512;
142                         rq->errors = 0;
143                         i = --rq->nr_sectors;
144                         --rq->current_nr_sectors;
145                         if (((long)rq->current_nr_sectors) <= 0)
146                                 ide_end_request(1, hwgroup);
147                         if (i > 0) {
148 -                               idedisk_output_data (drive, rq->buffer, SECTOR_WORDS);
149 +                               unsigned long flags;
150 +                               char *to = ide_map_buffer(rq, &flags);
151 +                               idedisk_output_data (drive, to, SECTOR_WORDS);
152 +                               ide_unmap_buffer(to, &flags);
153                                 ide_set_handler (drive, &write_intr, WAIT_CMD, NULL);
154                                  return ide_started;
155                         }
156 @@ -257,14 +263,14 @@
157         do {
158                 char *buffer;
159                 int nsect = rq->current_nr_sectors;
160
161 +               unsigned long flags;
162 +
163                 if (nsect > mcount)
164                         nsect = mcount;
165                 mcount -= nsect;
166 -               buffer = rq->buffer;
167  
168 +               buffer = ide_map_buffer(rq, &flags);
169                 rq->sector += nsect;
170 -               rq->buffer += nsect << 9;
171                 rq->nr_sectors -= nsect;
172                 rq->current_nr_sectors -= nsect;
173  
174 @@ -278,7 +284,7 @@
175                         } else {
176                                 rq->bh = bh;
177                                 rq->current_nr_sectors = bh->b_size >> 9;
178 -                               rq->buffer             = bh->b_data;
179 +                               rq->hard_cur_sectors = rq->current_nr_sectors;
180                         }
181                 }
182  
183 @@ -287,6 +293,7 @@
184                  * re-entering us on the last transfer.
185                  */
186                 idedisk_output_data(drive, buffer, nsect<<7);
187 +               ide_unmap_buffer(buffer, &flags);
188         } while (mcount);
189  
190          return 0;
191 @@ -695,8 +702,11 @@
192                                 return ide_stopped;
193                         }
194                 } else {
195 +                       unsigned long flags;
196 +                       char *buffer = ide_map_buffer(rq, &flags);
197                         ide_set_handler (drive, &write_intr, WAIT_CMD, NULL);
198 -                       idedisk_output_data(drive, rq->buffer, SECTOR_WORDS);
199 +                       idedisk_output_data(drive, buffer, SECTOR_WORDS);
200 +                       ide_unmap_buffer(buffer, &flags);
201                 }
202                 return ide_started;
203         }
204 diff -Nur linux-2.4.19/drivers/ide/ide-dma.c linux-2.4.19.new/drivers/ide/ide-dma.c
205 --- linux-2.4.19/drivers/ide/ide-dma.c  Sat Aug  3 02:39:44 2002
206 +++ linux-2.4.19.new/drivers/ide/ide-dma.c      Wed Nov 13 09:49:39 2002
207 @@ -252,33 +252,53 @@
208  {
209         struct buffer_head *bh;
210         struct scatterlist *sg = hwif->sg_table;
211 +       unsigned long lastdataend = ~0UL;
212         int nents = 0;
213  
214         if (hwif->sg_dma_active)
215                 BUG();
216 -               
217 +
218         if (rq->cmd == READ)
219                 hwif->sg_dma_direction = PCI_DMA_FROMDEVICE;
220         else
221                 hwif->sg_dma_direction = PCI_DMA_TODEVICE;
222 +
223         bh = rq->bh;
224         do {
225 -               unsigned char *virt_addr = bh->b_data;
226 -               unsigned int size = bh->b_size;
227 +               struct scatterlist *sge;
228 +
229 +               /*
230 +                * continue segment from before?
231 +                */
232 +               if (bh_phys(bh) == lastdataend) {
233 +                       sg[nents - 1].length += bh->b_size;
234 +                       lastdataend += bh->b_size;
235 +                       continue;
236 +               }
237  
238 +               /*
239 +                * start new segment
240 +                */
241                 if (nents >= PRD_ENTRIES)
242                         return 0;
243  
244 -               while ((bh = bh->b_reqnext) != NULL) {
245 -                       if ((virt_addr + size) != (unsigned char *) bh->b_data)
246 -                               break;
247 -                       size += bh->b_size;
248 +               sge = &sg[nents];
249 +               memset(sge, 0, sizeof(*sge));
250 +
251 +               if (bh->b_page) {
252 +                       sge->page = bh->b_page;
253 +                       sge->offset = bh_offset(bh);
254 +               } else {
255 +                       if (((unsigned long) bh->b_data) < PAGE_SIZE)
256 +                               BUG();
257 +
258 +                       sge->address = bh->b_data;
259                 }
260 -               memset(&sg[nents], 0, sizeof(*sg));
261 -               sg[nents].address = virt_addr;
262 -               sg[nents].length = size;
263 +
264 +               sge->length = bh->b_size;
265 +               lastdataend = bh_phys(bh) + bh->b_size;
266                 nents++;
267 -       } while (bh != NULL);
268 +       } while ((bh = bh->b_reqnext) != NULL);
269  
270         return pci_map_sg(hwif->pci_dev, sg, nents, hwif->sg_dma_direction);
271  }
272 @@ -340,7 +360,7 @@
273                 return 0;
274  
275         sg = HWIF(drive)->sg_table;
276 -       while (i && sg_dma_len(sg)) {
277 +       while (i) {
278                 u32 cur_addr;
279                 u32 cur_len;
280  
281 @@ -354,36 +374,35 @@
282                  */
283  
284                 while (cur_len) {
285 -                       if (count++ >= PRD_ENTRIES) {
286 -                               printk("%s: DMA table too small\n", drive->name);
287 -                               goto use_pio_instead;
288 -                       } else {
289 -                               u32 xcount, bcount = 0x10000 - (cur_addr & 0xffff);
290 -
291 -                               if (bcount > cur_len)
292 -                                       bcount = cur_len;
293 -                               *table++ = cpu_to_le32(cur_addr);
294 -                               xcount = bcount & 0xffff;
295 -                               if (is_trm290_chipset)
296 -                                       xcount = ((xcount >> 2) - 1) << 16;
297 -                               if (xcount == 0x0000) {
298 -                                       /* 
299 -                                        * Most chipsets correctly interpret a length of 0x0000 as 64KB,
300 -                                        * but at least one (e.g. CS5530) misinterprets it as zero (!).
301 -                                        * So here we break the 64KB entry into two 32KB entries instead.
302 -                                        */
303 -                                       if (count++ >= PRD_ENTRIES) {
304 -                                               printk("%s: DMA table too small\n", drive->name);
305 -                                               goto use_pio_instead;
306 -                                       }
307 -                                       *table++ = cpu_to_le32(0x8000);
308 -                                       *table++ = cpu_to_le32(cur_addr + 0x8000);
309 -                                       xcount = 0x8000;
310 -                               }
311 -                               *table++ = cpu_to_le32(xcount);
312 -                               cur_addr += bcount;
313 -                               cur_len -= bcount;
314 +                       u32 xcount, bcount = 0x10000 - (cur_addr & 0xffff);
315 +                       
316 +                       if (count++ >= PRD_ENTRIES)
317 +                               BUG();
318 +
319 +                       if (bcount > cur_len)
320 +                               bcount = cur_len;
321 +                       *table++ = cpu_to_le32(cur_addr);
322 +                       xcount = bcount & 0xffff;
323 +                       if (is_trm290_chipset)
324 +                               xcount = ((xcount >> 2) - 1) << 16;
325 +                       if (xcount == 0x0000) {
326 +                               /* 
327 +                                * Most chipsets correctly interpret a length
328 +                                * of 0x0000 as 64KB, but at least one
329 +                                * (e.g. CS5530) misinterprets it as zero (!).
330 +                                * So here we break the 64KB entry into two
331 +                                * 32KB entries instead.
332 +                                */
333 +                               if (count++ >= PRD_ENTRIES)
334 +                                       goto use_pio_instead;
335 +
336 +                               *table++ = cpu_to_le32(0x8000);
337 +                               *table++ = cpu_to_le32(cur_addr + 0x8000);
338 +                               xcount = 0x8000;
339                         }
340 +                       *table++ = cpu_to_le32(xcount);
341 +                       cur_addr += bcount;
342 +                       cur_len -= bcount;
343                 }
344  
345                 sg++;
346 @@ -584,6 +603,23 @@
347  }
348  #endif /* CONFIG_BLK_DEV_IDEDMA_TIMEOUT */
349  
350 +static inline void ide_toggle_bounce(ide_drive_t *drive, int on)
351 +{
352 +       dma64_addr_t addr = BLK_BOUNCE_HIGH;
353 +
354 +       if (HWIF(drive)->no_highio || HWIF(drive)->pci_dev == NULL)
355 +               return;
356 +
357 +       if (on && drive->media == ide_disk) {
358 +               if (!PCI_DMA_BUS_IS_PHYS)
359 +                       addr = BLK_BOUNCE_ANY;
360 +               else
361 +                       addr = HWIF(drive)->pci_dev->dma_mask;
362 +       }
363 +
364 +       blk_queue_bounce_limit(&drive->queue, addr);
365 +}
366 +
367  /*
368   * ide_dmaproc() initiates/aborts DMA read/write operations on a drive.
369   *
370 @@ -606,18 +642,20 @@
371         ide_hwif_t *hwif                = HWIF(drive);
372         unsigned long dma_base          = hwif->dma_base;
373         byte unit                       = (drive->select.b.unit & 0x01);
374 -       unsigned int count, reading     = 0;
375 +       unsigned int count, reading = 0, set_high = 1;
376         byte dma_stat;
377  
378         switch (func) {
379                 case ide_dma_off:
380                         printk("%s: DMA disabled\n", drive->name);
381                 case ide_dma_off_quietly:
382 +                       set_high = 0;
383                         outb(inb(dma_base+2) & ~(1<<(5+unit)), dma_base+2);
384                 case ide_dma_on:
385                         drive->using_dma = (func == ide_dma_on);
386                         if (drive->using_dma)
387                                 outb(inb(dma_base+2)|(1<<(5+unit)), dma_base+2);
388 +                       ide_toggle_bounce(drive, set_high);
389                         return 0;
390                 case ide_dma_check:
391                         return config_drive_for_dma (drive);
392 @@ -759,8 +797,8 @@
393         request_region(dma_base, num_ports, hwif->name);
394         hwif->dma_base = dma_base;
395         hwif->dmatable_cpu = pci_alloc_consistent(hwif->pci_dev,
396 -                                                 PRD_ENTRIES * PRD_BYTES,
397 -                                                 &hwif->dmatable_dma);
398 +                                                   PRD_ENTRIES * PRD_BYTES,
399 +                                                   &hwif->dmatable_dma);
400         if (hwif->dmatable_cpu == NULL)
401                 goto dma_alloc_failure;
402  
403 diff -Nur linux-2.4.19/drivers/ide/ide-geometry.c linux-2.4.19.new/drivers/ide/ide-geometry.c
404 --- linux-2.4.19/drivers/ide/ide-geometry.c     Sat Aug  3 02:39:44 2002
405 +++ linux-2.4.19.new/drivers/ide/ide-geometry.c Wed Nov 13 09:49:39 2002
406 @@ -32,7 +32,7 @@
407   * for us during initialization.  I have the necessary docs -- any takers?  -ml
408   */
409  /*
410 - * I did this, but it doesnt work - there is no reasonable way to find the
411 + * I did this, but it doesn't work - there is no reasonable way to find the
412   * correspondence between the BIOS numbering of the disks and the Linux
413   * numbering. -aeb
414   *
415 diff -Nur linux-2.4.19/drivers/ide/ide-pci.c linux-2.4.19.new/drivers/ide/ide-pci.c
416 --- linux-2.4.19/drivers/ide/ide-pci.c  Sat Aug  3 02:39:44 2002
417 +++ linux-2.4.19.new/drivers/ide/ide-pci.c      Wed Nov 13 09:49:39 2002
418 @@ -405,7 +405,7 @@
419  #ifndef CONFIG_PDC202XX_FORCE
420          {DEVID_PDC20246,"PDC20246",    PCI_PDC202XX,   NULL,           INIT_PDC202XX,  NULL,           {{0x00,0x00,0x00}, {0x00,0x00,0x00}},   OFF_BOARD,      16 },
421          {DEVID_PDC20262,"PDC20262",    PCI_PDC202XX,   ATA66_PDC202XX, INIT_PDC202XX,  NULL,           {{0x00,0x00,0x00}, {0x00,0x00,0x00}},   OFF_BOARD,      48 },
422 -        {DEVID_PDC20265,"PDC20265",    PCI_PDC202XX,   ATA66_PDC202XX, INIT_PDC202XX,  NULL,           {{0x00,0x00,0x00}, {0x00,0x00,0x00}},   ON_BOARD,       48 },
423 +        {DEVID_PDC20265,"PDC20265",    PCI_PDC202XX,   ATA66_PDC202XX, INIT_PDC202XX,  NULL,           {{0x00,0x00,0x00}, {0x00,0x00,0x00}},   OFF_BOARD,      48 },
424          {DEVID_PDC20267,"PDC20267",    PCI_PDC202XX,   ATA66_PDC202XX, INIT_PDC202XX,  NULL,           {{0x00,0x00,0x00}, {0x00,0x00,0x00}},   OFF_BOARD,      48 },
425  #else /* !CONFIG_PDC202XX_FORCE */
426         {DEVID_PDC20246,"PDC20246",     PCI_PDC202XX,   NULL,           INIT_PDC202XX,  NULL,           {{0x50,0x02,0x02}, {0x50,0x04,0x04}},   OFF_BOARD,      16 },
427 @@ -623,8 +623,12 @@
428         }
429  
430         if (pci_enable_device(dev)) {
431 -               printk(KERN_WARNING "%s: (ide_setup_pci_device:) Could not enable device.\n", d->name);
432 -               return;
433 +               if(pci_enable_device_bars(dev, 1<<4))
434 +               {
435 +                       printk(KERN_WARNING "%s: (ide_setup_pci_device:) Could not enable device.\n", d->name);
436 +                       return;
437 +               }
438 +               printk(KERN_INFO "%s: BIOS setup was incomplete.\n", d->name);
439         }
440  
441  check_if_enabled:
442 @@ -669,18 +673,27 @@
443          */
444         pciirq = dev->irq;
445         
446 -#ifdef CONFIG_PDC202XX_FORCE
447 -       if (dev->class >> 8 == PCI_CLASS_STORAGE_RAID) {
448 -               /*
449 -                * By rights we want to ignore Promise FastTrak and SuperTrak
450 -                * series here, those use own driver.
451 +       if (dev->class >> 8 == PCI_CLASS_STORAGE_RAID)
452 +       {
453 +           /*  By rights we want to ignore these, but the Promise Fastrak
454 +                *      people have some strange ideas about proprietary so we have
455 +                *      to act otherwise on those. The supertrak however we need
456 +                *      to skip 
457                  */
458 -               if (dev->vendor == PCI_VENDOR_ID_PROMISE) {
459 -                       printk(KERN_INFO "ide: Skipping Promise RAID controller.\n");
460 -                       return;
461 +               if (IDE_PCI_DEVID_EQ(d->devid, DEVID_PDC20265))
462 +               {
463 +                       printk(KERN_INFO "ide: Found promise 20265 in RAID mode.\n");
464 +                       if(dev->bus->self && dev->bus->self->vendor == PCI_VENDOR_ID_INTEL &&
465 +                          dev->bus->self->device == PCI_DEVICE_ID_INTEL_I960)
466 +                       {
467 +                               printk(KERN_INFO "ide: Skipping Promise PDC20265 attached to I2O RAID controller.\n");
468 +                               return;
469 +                       }
470                 }
471 +               /* Its attached to something else, just a random bridge.
472 +                  Suspect a fastrak and fall through */
473         }
474 -#endif /* CONFIG_PDC202XX_FORCE */
475 +
476         if ((dev->class & ~(0xfa)) != ((PCI_CLASS_STORAGE_IDE << 8) | 5)) {
477                 printk("%s: not 100%% native mode: will probe irqs later\n", d->name);
478                 /*
479 diff -Nur linux-2.4.19/drivers/ide/ide-pmac.c linux-2.4.19.new/drivers/ide/ide-pmac.c
480 --- linux-2.4.19/drivers/ide/ide-pmac.c Sat Aug  3 02:39:44 2002
481 +++ linux-2.4.19.new/drivers/ide/ide-pmac.c     Wed Nov 13 09:49:39 2002
482 @@ -114,8 +114,7 @@
483   *    well, despite a comment that would lead to think it has a
484   *    min value of 45ns.
485   * Apple also add 60ns to the write data setup (or cycle time ?) on
486 - * reads. I can't explain that, I tried it and it broke everything
487 - * here.
488 + * reads.
489   */
490  #define TR_66_UDMA_MASK                        0xfff00000
491  #define TR_66_UDMA_EN                  0x00100000 /* Enable Ultra mode for DMA */
492 @@ -401,7 +400,6 @@
493  pmac_ide_do_setfeature(ide_drive_t *drive, byte command)
494  {
495         int result = 1;
496 -       unsigned long flags;
497         ide_hwif_t *hwif = HWIF(drive);
498         
499         disable_irq(hwif->irq); /* disable_irq_nosync ?? */
500 @@ -420,10 +418,7 @@
501         OUT_BYTE(SETFEATURES_XFER, IDE_FEATURE_REG);
502         OUT_BYTE(WIN_SETFEATURES, IDE_COMMAND_REG);
503         udelay(1);
504 -       __save_flags(flags);    /* local CPU only */
505 -       ide__sti();             /* local CPU only -- for jiffies */
506         result = wait_for_ready(drive);
507 -       __restore_flags(flags); /* local CPU only */
508         OUT_BYTE(drive->ctl, IDE_CONTROL_REG);
509         if (result)
510                 printk(KERN_ERR "pmac_ide_do_setfeature disk not ready after SET_FEATURE !\n");
511 @@ -956,6 +951,8 @@
512                 hwif->noprobe = !hwif->io_ports[IDE_DATA_OFFSET] || in_bay;
513                 hwif->udma_four = (pmhw->kind == controller_kl_ata4_80);
514                 hwif->pci_dev = pdev;
515 +               hwif->drives[0].unmask = 1;
516 +               hwif->drives[1].unmask = 1;
517  #ifdef CONFIG_PMAC_PBOOK
518                 if (in_bay && check_media_bay_by_base(base, MB_CD) == 0)
519                         hwif->noprobe = 0;
520 @@ -1032,33 +1029,48 @@
521         struct pmac_ide_hwif *pmif = &pmac_ide[ix];
522         struct buffer_head *bh;
523         struct scatterlist *sg = pmif->sg_table;
524 +       unsigned long lastdataend = ~0UL;
525         int nents = 0;
526  
527         if (hwif->sg_dma_active)
528                 BUG();
529 -               
530 +
531         if (rq->cmd == READ)
532                 pmif->sg_dma_direction = PCI_DMA_FROMDEVICE;
533         else
534                 pmif->sg_dma_direction = PCI_DMA_TODEVICE;
535 +
536         bh = rq->bh;
537         do {
538 -               unsigned char *virt_addr = bh->b_data;
539 +               struct scatterlist *sge;
540                 unsigned int size = bh->b_size;
541  
542 +               /* continue segment from before? */
543 +               if (bh_phys(bh) == lastdataend) {
544 +                       sg[nents-1].length += size;
545 +                       lastdataend += size;
546 +                       continue;
547 +               }
548 +
549 +               /* start new segment */
550                 if (nents >= MAX_DCMDS)
551                         return 0;
552  
553 -               while ((bh = bh->b_reqnext) != NULL) {
554 -                       if ((virt_addr + size) != (unsigned char *) bh->b_data)
555 -                               break;
556 -                       size += bh->b_size;
557 +               sge = &sg[nents];
558 +               memset(sge, 0, sizeof(*sge));
559 +
560 +               if (bh->b_page) {
561 +                       sge->page = bh->b_page;
562 +                       sge->offset = bh_offset(bh);
563 +               } else {
564 +                       if ((unsigned long)bh->b_data < PAGE_SIZE)
565 +                               BUG();
566 +                       sge->address = bh->b_data;
567                 }
568 -               memset(&sg[nents], 0, sizeof(*sg));
569 -               sg[nents].address = virt_addr;
570 -               sg[nents].length = size;
571 +               sge->length = size;
572 +               lastdataend = bh_phys(bh) + size;
573                 nents++;
574 -       } while (bh != NULL);
575 +       } while ((bh = bh->b_reqnext) != NULL);
576  
577         return pci_map_sg(hwif->pci_dev, sg, nents, pmif->sg_dma_direction);
578  }
579 @@ -1330,6 +1342,23 @@
580         return 0;
581  }
582  
583 +static inline void pmac_ide_toggle_bounce(ide_drive_t *drive, int on)
584 +{
585 +       dma64_addr_t addr = BLK_BOUNCE_HIGH;
586 +
587 +       if (HWIF(drive)->no_highio || HWIF(drive)->pci_dev == NULL)
588 +               return;
589 +
590 +       if (on && drive->media == ide_disk) {
591 +               if (!PCI_DMA_BUS_IS_PHYS)
592 +                       addr = BLK_BOUNCE_ANY;
593 +               else
594 +                       addr = HWIF(drive)->pci_dev->dma_mask;
595 +       }
596 +
597 +       blk_queue_bounce_limit(&drive->queue, addr);
598 +}
599 +
600  static int __pmac
601  pmac_ide_dmaproc(ide_dma_action_t func, ide_drive_t *drive)
602  {
603 @@ -1354,10 +1383,13 @@
604                 printk(KERN_INFO "%s: DMA disabled\n", drive->name);
605         case ide_dma_off_quietly:
606                 drive->using_dma = 0;
607 +               pmac_ide_toggle_bounce(drive, 0);
608                 break;
609         case ide_dma_on:
610         case ide_dma_check:
611                 pmac_ide_check_dma(drive);
612 +               if (drive->using_dma)
613 +                       pmac_ide_toggle_bounce(drive, 1);
614                 break;
615         case ide_dma_read:
616                 reading = 1;
617 @@ -1612,7 +1644,14 @@
618  
619  /* Note: We support only master drives for now. This will have to be
620   * improved if we want to handle sleep on the iMacDV where the CD-ROM
621 - * is a slave
622 + * is a slave.
623 + * 
624 + * Well, actually, that sorta works on the iBook2 when the CD-ROM is
625 + * a slave, though it will fail to spin_wait_hwgroup for the slave
626 + * device as it is marked busy by the master sleep code. Well, it's
627 + * probably not worth fixing now as we don't have sleep code for
628 + * ATAPI devices anyway. Future kernels will hopefully deal with
629 + * IDE PM in a more generic way.
630   */
631  static int __pmac
632  idepmac_notify_sleep(struct pmu_sleep_notifier *self, int when)
633 diff -Nur linux-2.4.19/drivers/ide/ide-probe.c linux-2.4.19.new/drivers/ide/ide-probe.c
634 --- linux-2.4.19/drivers/ide/ide-probe.c        Sat Aug  3 02:39:44 2002
635 +++ linux-2.4.19.new/drivers/ide/ide-probe.c    Wed Nov 13 09:49:39 2002
636 @@ -785,6 +785,7 @@
637         gd        = kmalloc (sizeof(struct gendisk), GFP_KERNEL);
638         if (!gd)
639                 goto err_kmalloc_gd;
640 +       memset (gd, 0, sizeof(struct gendisk));
641         gd->sizes = kmalloc (minors * sizeof(int), GFP_KERNEL);
642         if (!gd->sizes)
643                 goto err_kmalloc_gd_sizes;
644 diff -Nur linux-2.4.19/drivers/ide/ide-sibyte.c linux-2.4.19.new/drivers/ide/ide-sibyte.c
645 --- linux-2.4.19/drivers/ide/ide-sibyte.c       Thu Jan  1 01:00:00 1970
646 +++ linux-2.4.19.new/drivers/ide/ide-sibyte.c   Wed Nov 13 09:49:39 2002
647 @@ -0,0 +1,333 @@
648 +/*
649 + * Copyright (C) 2001 Broadcom Corporation
650 + *
651 + * This program is free software; you can redistribute it and/or
652 + * modify it under the terms of the GNU General Public License
653 + * as published by the Free Software Foundation; either version 2
654 + * of the License, or (at your option) any later version.
655 + *
656 + * This program is distributed in the hope that it will be useful,
657 + * but WITHOUT ANY WARRANTY; without even the implied warranty of
658 + * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE.  See the
659 + * GNU General Public License for more details.
660 + * 
661 + * You should have received a copy of the GNU General Public License
662 + * along with this program; if not, write to the Free Software
663 + * Foundation, Inc., 59 Temple Place - Suite 330, Boston, MA  02111-1307, USA.
664 + */
665 +
666 +/*  Derived loosely from ide-pmac.c, so:
667 + *  
668 + *  Copyright (C) 1998 Paul Mackerras.
669 + *  Copyright (C) 1995-1998 Mark Lord
670 + */
671 +#include <linux/config.h>
672 +#include <linux/types.h>
673 +#include <linux/kernel.h>
674 +#include <linux/sched.h>
675 +#include <linux/init.h>
676 +#include <linux/delay.h>
677 +#include <linux/ide.h>
678 +
679 +#include <asm/irq.h>
680 +#include <asm/io.h>
681 +#include <asm/sibyte/sb1250_regs.h>
682 +#include <asm/sibyte/sb1250_int.h>
683 +#include <asm/sibyte/sb1250_genbus.h>
684 +#include <asm/sibyte/64bit.h>
685 +#include <asm/sibyte/board.h>
686 +
687 +/* Note: this should be general for any board using IDE on GenBus */
688 +
689 +extern struct ide_ops std_ide_ops;
690 +
691 +static ide_hwif_t *sb_ide_hwif = NULL;
692 +static unsigned long ide_base;
693 +
694 +#define SIBYTE_IDE_BASE        (KSEG1ADDR(ide_base)-mips_io_port_base)
695 +#define SIBYTE_IDE_REG(pcaddr) (SIBYTE_IDE_BASE + ((pcaddr)<<5))
696 +
697 +/*
698 + * We are limiting the number of PCI-IDE devices to leave room for
699 + * GenBus IDE (and possibly PCMCIA/CF?)
700 + */
701 +static int sibyte_ide_default_irq(ide_ioreg_t base)
702 +{
703 +       return 0;
704 +}
705 +
706 +static ide_ioreg_t sibyte_ide_default_io_base(int index)
707 +{
708 +       return 0;
709 +}
710 +
711 +static void sibyte_ide_init_hwif_ports (hw_regs_t *hw, ide_ioreg_t data_port,
712 +                                      ide_ioreg_t ctrl_port, int *irq)
713 +{
714 +       std_ide_ops.ide_init_hwif_ports(hw, data_port, ctrl_port, irq);
715 +}
716 +
717 +static int sibyte_ide_request_irq(unsigned int irq,
718 +                                void (*handler)(int,void *, struct pt_regs *),
719 +                                unsigned long flags, const char *device,
720 +                                void *dev_id)
721 +{
722 +       return request_irq(irq, handler, flags, device, dev_id);
723 +}
724 +
725 +static void sibyte_ide_free_irq(unsigned int irq, void *dev_id)
726 +{
727 +       free_irq(irq, dev_id);
728 +}
729 +
730 +static inline int is_sibyte_ide(ide_ioreg_t from)
731 +{
732 +       return (sb_ide_hwif &&
733 +               ((from == sb_ide_hwif->io_ports[IDE_DATA_OFFSET]) ||
734 +                (from == sb_ide_hwif->io_ports[IDE_ERROR_OFFSET]) ||
735 +                (from == sb_ide_hwif->io_ports[IDE_NSECTOR_OFFSET]) ||
736 +                (from == sb_ide_hwif->io_ports[IDE_SECTOR_OFFSET]) ||
737 +                (from == sb_ide_hwif->io_ports[IDE_LCYL_OFFSET]) ||
738 +                (from == sb_ide_hwif->io_ports[IDE_HCYL_OFFSET]) ||
739 +                (from == sb_ide_hwif->io_ports[IDE_SELECT_OFFSET]) ||
740 +                (from == sb_ide_hwif->io_ports[IDE_STATUS_OFFSET]) ||
741 +                (from == sb_ide_hwif->io_ports[IDE_CONTROL_OFFSET])));
742 +}
743 +
744 +static int sibyte_ide_check_region(ide_ioreg_t from, unsigned int extent)
745 +{
746 +       /* Figure out if it's the SiByte IDE; if so, don't do anything
747 +           since our I/O space is in a weird place. */
748 +       if (is_sibyte_ide(from))
749 +               return 0;
750 +       else
751 +#ifdef CONFIG_BLK_DEV_IDE
752 +               return std_ide_ops.ide_check_region(from, extent);
753 +#else
754 +               return 0;
755 +#endif
756 +}
757 +
758 +static void sibyte_ide_request_region(ide_ioreg_t from, unsigned int extent,
759 +                                    const char *name)
760 +{
761 +#ifdef CONFIG_BLK_DEV_IDE
762 +       if (!is_sibyte_ide(from))
763 +               std_ide_ops.ide_request_region(from, extent, name);
764 +#endif
765 +}
766 +
767 +static void sibyte_ide_release_region(ide_ioreg_t from, unsigned int extent)
768 +{
769 +#ifdef CONFIG_BLK_DEV_IDE
770 +       if (!is_sibyte_ide(from))
771 +               std_ide_ops.ide_release_region(from, extent);
772 +#endif
773 +}
774 +
775 +struct ide_ops sibyte_ide_ops = {
776 +       &sibyte_ide_default_irq,
777 +       &sibyte_ide_default_io_base,
778 +       &sibyte_ide_init_hwif_ports,
779 +       &sibyte_ide_request_irq,
780 +       &sibyte_ide_free_irq,
781 +       &sibyte_ide_check_region,
782 +       &sibyte_ide_request_region,
783 +       &sibyte_ide_release_region
784 +};
785 +
786 +/*
787 + * I/O operations. The FPGA for SiByte generic bus IDE deals with
788 + * byte-swapping for us, so we can't share the I/O macros with other
789 + * IDE (e.g. PCI-IDE) devices.
790 + */
791 +
792 +#define sibyte_outb(val,port)                                  \
793 +do {                                                           \
794 +       *(volatile u8 *)(mips_io_port_base + (port)) = val;     \
795 +} while(0)
796 +
797 +#define sibyte_outw(val,port)                                  \
798 +do {                                                           \
799 +       *(volatile u16 *)(mips_io_port_base + (port)) = val;    \
800 +} while(0)
801 +
802 +#define sibyte_outl(val,port)                                  \
803 +do {                                                           \
804 +       *(volatile u32 *)(mips_io_port_base + (port)) = val;    \
805 +} while(0)
806 +
807 +static inline unsigned char sibyte_inb(unsigned long port)
808 +{
809 +       return (*(volatile u8 *)(mips_io_port_base + (port)));
810 +}
811 +
812 +static inline unsigned short sibyte_inw(unsigned long port)
813 +{
814 +       return (*(volatile u16 *)(mips_io_port_base + (port)));
815 +}
816 +
817 +static inline unsigned int sibyte_inl(unsigned long port)
818 +{
819 +       return (*(volatile u32 *)(mips_io_port_base + (port)));
820 +}
821 +
822 +
823 +static inline void sibyte_outsb(unsigned long port, void *addr, unsigned int count)
824 +{
825 +       while (count--) {
826 +               sibyte_outb(*(u8 *)addr, port);
827 +               addr++;
828 +       }
829 +}
830 +
831 +static inline void sibyte_insb(unsigned long port, void *addr, unsigned int count)
832 +{
833 +       while (count--) {
834 +               *(u8 *)addr = sibyte_inb(port);
835 +               addr++;
836 +       }
837 +}
838 +
839 +static inline void sibyte_outsw(unsigned long port, void *addr, unsigned int count)
840 +{
841 +       while (count--) {
842 +               sibyte_outw(*(u16 *)addr, port);
843 +               addr += 2;
844 +       }
845 +}
846 +
847 +static inline void sibyte_insw(unsigned long port, void *addr, unsigned int count)
848 +{
849 +       while (count--) {
850 +               *(u16 *)addr = sibyte_inw(port);
851 +               addr += 2;
852 +       }
853 +}
854 +
855 +static inline void sibyte_outsl(unsigned long port, void *addr, unsigned int count)
856 +{
857 +       while (count--) {
858 +               sibyte_outl(*(u32 *)addr, port);
859 +               addr += 4;
860 +       }
861 +}
862 +
863 +static inline void sibyte_insl(unsigned long port, void *addr, unsigned int count)
864 +{
865 +       while (count--) {
866 +               *(u32 *)addr = sibyte_inl(port);
867 +               addr += 4;
868 +       }
869 +}
870 +
871 +static void sibyte_ideproc(ide_ide_action_t action, ide_drive_t *drive,
872 +                          void *buffer, unsigned int count)
873 +{
874 +       /*  slow? vlb_sync? */
875 +       switch (action) {
876 +       case ideproc_ide_input_data:
877 +               if (drive->io_32bit) {
878 +                       sibyte_insl(IDE_DATA_REG, buffer, count);
879 +               } else {
880 +                       sibyte_insw(IDE_DATA_REG, buffer, count<<1);
881 +               }
882 +               break;
883 +       case ideproc_ide_output_data:
884 +               if (drive->io_32bit) {
885 +                       sibyte_outsl(IDE_DATA_REG, buffer, count);
886 +               } else {
887 +                       sibyte_outsw(IDE_DATA_REG, buffer, count<<1);
888 +               }
889 +               break;
890 +       case ideproc_atapi_input_bytes:
891 +               count++;
892 +               if (drive->io_32bit) {
893 +                       sibyte_insl(IDE_DATA_REG, buffer, count>>2);
894 +               } else {
895 +                       sibyte_insw(IDE_DATA_REG, buffer, count>>1);
896 +               }
897 +               if ((count & 3) >= 2)
898 +                       sibyte_insw(IDE_DATA_REG, (char *)buffer + (count & ~3), 1);
899 +               break;
900 +       case ideproc_atapi_output_bytes:
901 +               count++;
902 +               if (drive->io_32bit) {
903 +                       sibyte_outsl(IDE_DATA_REG, buffer, count>>2);
904 +               } else {
905 +                       sibyte_outsw(IDE_DATA_REG, buffer, count>>1);
906 +               }
907 +               if ((count & 3) >= 2)
908 +                       sibyte_outsw(IDE_DATA_REG, (char *)buffer + (count & ~3), 1);
909 +               break;
910 +       }
911 +}
912 +
913 +/*
914 + * selectproc and intrproc aren't really necessary, since
915 + * byte-swapping doesn't affect byte ops; they are included for
916 + * consistency.
917 + */
918 +static void sibyte_selectproc(ide_drive_t *drive)
919 +{
920 +       sibyte_outb(drive->select.all, IDE_SELECT_REG);
921 +}
922 +
923 +static void sibyte_intrproc(ide_drive_t *drive)
924 +{
925 +       sibyte_outb(drive->ctl|2, IDE_CONTROL_REG);
926 +}
927 +
928 +void __init sibyte_ide_probe(void)
929 +{
930 +       int i;
931 +       ide_hwif_t *hwif;
932 +       /* 
933 +        * Find the first untaken slot in hwifs 
934 +        */
935 +       for (i = 0; i < MAX_HWIFS; i++) {
936 +               if (!ide_hwifs[i].io_ports[IDE_DATA_OFFSET]) {
937 +                       break;
938 +               }
939 +       }
940 +       if (i == MAX_HWIFS) {
941 +               printk("No space for SiByte onboard IDE driver in ide_hwifs[].  Not enabled.\n");
942 +               return;
943 +       }
944 +
945 +       /* Find memory base address */
946 +#ifdef __MIPSEL__
947 +       /* Pass1 workaround (bug 1624) */
948 +       if (sb1250_pass == K_SYS_REVISION_PASS1)
949 +               ide_base = G_IO_START_ADDR(csr_in32(4+(IO_SPACE_BASE|A_IO_EXT_REG(R_IO_EXT_REG(R_IO_EXT_START_ADDR, IDE_CS))))) << S_IO_ADDRBASE;
950 +       else
951 +#endif
952 +               ide_base = G_IO_START_ADDR(csr_in32(IO_SPACE_BASE|A_IO_EXT_REG(R_IO_EXT_REG(R_IO_EXT_START_ADDR, IDE_CS)))) << S_IO_ADDRBASE;
953 +
954 +       /*
955 +        * Set up our stuff; we're a little odd because our io_ports
956 +        * aren't in the usual place, and byte-swapping isn't
957 +        * necessary.
958 +        */
959 +       hwif = &ide_hwifs[i];
960 +       hwif->hw.io_ports[IDE_DATA_OFFSET]    = SIBYTE_IDE_REG(0x1f0);
961 +       hwif->hw.io_ports[IDE_ERROR_OFFSET]   = SIBYTE_IDE_REG(0x1f1);
962 +       hwif->hw.io_ports[IDE_NSECTOR_OFFSET] = SIBYTE_IDE_REG(0x1f2);
963 +       hwif->hw.io_ports[IDE_SECTOR_OFFSET]  = SIBYTE_IDE_REG(0x1f3);
964 +       hwif->hw.io_ports[IDE_LCYL_OFFSET]    = SIBYTE_IDE_REG(0x1f4);
965 +       hwif->hw.io_ports[IDE_HCYL_OFFSET]    = SIBYTE_IDE_REG(0x1f5);
966 +       hwif->hw.io_ports[IDE_SELECT_OFFSET]  = SIBYTE_IDE_REG(0x1f6);
967 +       hwif->hw.io_ports[IDE_STATUS_OFFSET]  = SIBYTE_IDE_REG(0x1f7);
968 +       hwif->hw.io_ports[IDE_CONTROL_OFFSET] = SIBYTE_IDE_REG(0x3f6);
969 +       hwif->hw.irq                          = K_INT_GB_IDE;
970 +       hwif->irq                             = K_INT_GB_IDE;
971 +       hwif->noprobe                         = 0;
972 +       /* Use our own non-byte-swapping routines */
973 +       hwif->ideproc                         = sibyte_ideproc;
974 +       hwif->selectproc                      = sibyte_selectproc;
975 +       hwif->intrproc                        = sibyte_intrproc;
976 +
977 +       memcpy(hwif->io_ports, hwif->hw.io_ports, sizeof(hwif->io_ports));
978 +       printk("SiByte onboard IDE configured as device %i\n", i);
979 +       sb_ide_hwif = hwif;
980 +}
981 diff -Nur linux-2.4.19/drivers/ide/ide-swarm.c linux-2.4.19.new/drivers/ide/ide-swarm.c
982 --- linux-2.4.19/drivers/ide/ide-swarm.c        Sat Aug  3 02:39:44 2002
983 +++ linux-2.4.19.new/drivers/ide/ide-swarm.c    Thu Jan  1 01:00:00 1970
984 @@ -1,73 +0,0 @@
985 -/*
986 - * Copyright (C) 2001 Broadcom Corporation
987 - *
988 - * This program is free software; you can redistribute it and/or
989 - * modify it under the terms of the GNU General Public License
990 - * as published by the Free Software Foundation; either version 2
991 - * of the License, or (at your option) any later version.
992 - *
993 - * This program is distributed in the hope that it will be useful,
994 - * but WITHOUT ANY WARRANTY; without even the implied warranty of
995 - * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE.  See the
996 - * GNU General Public License for more details.
997 - * 
998 - * You should have received a copy of the GNU General Public License
999 - * along with this program; if not, write to the Free Software
1000 - * Foundation, Inc., 59 Temple Place - Suite 330, Boston, MA  02111-1307, USA.
1001 - */
1002 -
1003 -/*  Derived loosely from ide-pmac.c, so:
1004 - *  
1005 - *  Copyright (C) 1998 Paul Mackerras.
1006 - *  Copyright (C) 1995-1998 Mark Lord
1007 - */
1008 -#include <linux/config.h>
1009 -#include <linux/types.h>
1010 -#include <linux/kernel.h>
1011 -#include <linux/sched.h>
1012 -#include <linux/init.h>
1013 -#include <linux/delay.h>
1014 -#include <linux/ide.h>
1015 -#include <asm/irq.h>
1016 -#include <asm/io.h>
1017 -#include <asm/sibyte/sb1250_int.h>
1018 -#include <asm/sibyte/swarm_ide.h>
1019 -
1020 -void __init swarm_ide_probe(void)
1021 -{
1022 -       int i;
1023 -       ide_hwif_t *hwif;
1024 -       /* 
1025 -        * Find the first untaken slot in hwifs 
1026 -        */
1027 -       for (i = 0; i < MAX_HWIFS; i++) {
1028 -               if (!ide_hwifs[i].io_ports[IDE_DATA_OFFSET]) {
1029 -                       break;
1030 -               }
1031 -       }
1032 -       if (i == MAX_HWIFS) {
1033 -               printk("No space for SWARM onboard IDE driver in ide_hwifs[].  Not enabled.\n");
1034 -               return;
1035 -       }
1036 -
1037 -       /* Set up our stuff */
1038 -       hwif = &ide_hwifs[i];
1039 -       hwif->hw.io_ports[IDE_DATA_OFFSET]    = SWARM_IDE_REG(0x1f0);
1040 -       hwif->hw.io_ports[IDE_ERROR_OFFSET]   = SWARM_IDE_REG(0x1f1);
1041 -       hwif->hw.io_ports[IDE_NSECTOR_OFFSET] = SWARM_IDE_REG(0x1f2);
1042 -       hwif->hw.io_ports[IDE_SECTOR_OFFSET]  = SWARM_IDE_REG(0x1f3);
1043 -       hwif->hw.io_ports[IDE_LCYL_OFFSET]    = SWARM_IDE_REG(0x1f4);
1044 -       hwif->hw.io_ports[IDE_HCYL_OFFSET]    = SWARM_IDE_REG(0x1f5);
1045 -       hwif->hw.io_ports[IDE_SELECT_OFFSET]  = SWARM_IDE_REG(0x1f6);
1046 -       hwif->hw.io_ports[IDE_STATUS_OFFSET]  = SWARM_IDE_REG(0x1f7);
1047 -       hwif->hw.io_ports[IDE_CONTROL_OFFSET] = SWARM_IDE_REG(0x3f6);
1048 -       hwif->hw.io_ports[IDE_IRQ_OFFSET]     = SWARM_IDE_REG(0x3f7);
1049 -//     hwif->hw->ack_intr                     = swarm_ide_ack_intr;
1050 -       hwif->hw.irq                          = SWARM_IDE_INT;
1051 -       hwif->ideproc                         = swarm_ideproc;
1052 -
1053 -       memcpy(hwif->io_ports, hwif->hw.io_ports, sizeof(hwif->io_ports));
1054 -       hwif->irq = hwif->hw.irq;
1055 -       printk("SWARM onboard IDE configured as device %i\n", i);
1056 -}
1057 -
1058 diff -Nur linux-2.4.19/drivers/ide/ide.c linux-2.4.19.new/drivers/ide/ide.c
1059 --- linux-2.4.19/drivers/ide/ide.c      Sat Aug  3 02:39:44 2002
1060 +++ linux-2.4.19.new/drivers/ide/ide.c  Wed Nov 13 09:49:39 2002
1061 @@ -3418,7 +3418,7 @@
1062                 const char *ide_words[] = {
1063                         "noprobe", "serialize", "autotune", "noautotune", "reset", "dma", "ata66",
1064                         "minus8", "minus9", "minus10",
1065 -                       "four", "qd65xx", "ht6560b", "cmd640_vlb", "dtc2278", "umc8672", "ali14xx", "dc4030", NULL };
1066 +                       "four", "qd65xx", "ht6560b", "cmd640_vlb", "dtc2278", "umc8672", "ali14xx", "dc4030", "nohighio", NULL };
1067                 hw = s[3] - '0';
1068                 hwif = &ide_hwifs[hw];
1069                 i = match_parm(&s[4], ide_words, vals, 3);
1070 @@ -3437,6 +3437,10 @@
1071                 }
1072  
1073                 switch (i) {
1074 +                       case -19: /* nohighio */
1075 +                               hwif->no_highio = 1;
1076 +                               printk("%s: disabled high i/o capability\n", hwif->name);
1077 +                               goto done;
1078  #ifdef CONFIG_BLK_DEV_PDC4030
1079                         case -18: /* "dc4030" */
1080                         {
1081 @@ -3616,12 +3620,12 @@
1082                 pmac_ide_probe();
1083         }
1084  #endif /* CONFIG_BLK_DEV_IDE_PMAC */
1085 -#ifdef CONFIG_BLK_DEV_IDE_SWARM
1086 +#ifdef CONFIG_BLK_DEV_IDE_SIBYTE
1087         {
1088 -               extern void swarm_ide_probe(void);
1089 -               swarm_ide_probe();
1090 +               extern void sibyte_ide_probe(void);
1091 +               sibyte_ide_probe();
1092         }
1093 -#endif /* CONFIG_BLK_DEV_IDE_SWARM */
1094 +#endif /* CONFIG_BLK_DEV_IDE_SIBYTE */
1095  #ifdef CONFIG_BLK_DEV_IDE_ICSIDE
1096         {
1097                 extern void icside_init(void);
1098 diff -Nur linux-2.4.19/drivers/ide/q40ide.c linux-2.4.19.new/drivers/ide/q40ide.c
1099 --- linux-2.4.19/drivers/ide/q40ide.c   Thu Oct 25 22:53:47 2001
1100 +++ linux-2.4.19.new/drivers/ide/q40ide.c       Wed Nov 13 09:49:39 2002
1101 @@ -82,8 +82,8 @@
1102      for (i = 0; i < Q40IDE_NUM_HWIFS; i++) {
1103         hw_regs_t hw;
1104  
1105 -       ide_setup_ports(&hw,(ide_ioreg_t) pcide_bases[i], (int *)pcide_offsets, 
1106 -                       pcide_bases[i]+0x206, 
1107 +       ide_setup_ports(&hw, (ide_ioreg_t)pcide_bases[i], (int *)pcide_offsets,
1108 +                       (ide_ioreg_t)pcide_bases[i]+0x206,
1109                         0, NULL, q40ide_default_irq(pcide_bases[i]));
1110         ide_register_hw(&hw, NULL);
1111      }
1112 diff -Naur -X /home/marcelo/lib/dontdiff linux-2.4.19/include/linux/ide.h linux-2.4.20/include/linux/ide.h
1113 --- linux-2.4.19/include/linux/ide.h    2002-08-03 00:39:45.000000000 +0000
1114 +++ linux-2.4.20/include/linux/ide.h    2002-10-29 11:18:34.000000000 +0000
1115 @@ -552,6 +552,7 @@
1116         unsigned        reset      : 1; /* reset after probe */
1117         unsigned        autodma    : 1; /* automatically try to enable DMA at boot */
1118         unsigned        udma_four  : 1; /* 1=ATA-66 capable, 0=default */
1119 +       unsigned        no_highio  : 1; /* don't trust pci dma mask, bounce */
1120         byte            channel;        /* for dual-port chips: 0=primary, 1=secondary */
1121  #ifdef CONFIG_BLK_DEV_IDEPCI
1122         struct pci_dev  *pci_dev;       /* for pci chipsets */
1123 @@ -874,6 +875,21 @@
1124  } ide_action_t;
1125  
1126  /*
1127 + * temporarily mapping a (possible) highmem bio
1128 + */
1129 +#define ide_rq_offset(rq) (((rq)->hard_cur_sectors - (rq)->current_nr_sectors) << 9)
1130 +
1131 +extern inline void *ide_map_buffer(struct request *rq, unsigned long *flags)
1132 +{
1133 +       return bh_kmap_irq(rq->bh, flags) + ide_rq_offset(rq);
1134 +}
1135 +
1136 +extern inline void ide_unmap_buffer(char *buffer, unsigned long *flags)
1137 +{
1138 +       bh_kunmap_irq(buffer, flags);
1139 +}
1140 +
1141 +/*
1142   * This function issues a special IDE device request
1143   * onto the request queue.
1144   *
1145 diff -Naur -X /home/marcelo/lib/dontdiff linux-2.4.19/include/linux/blkdev.h linux-2.4.20/include/linux/blkdev.h
1146 --- linux-2.4.19/include/linux/blkdev.h 2002-08-03 00:39:45.000000000 +0000
1147 +++ linux-2.4.20/include/linux/blkdev.h 2002-10-29 11:18:34.000000000 +0000
1148 @@ -6,6 +6,9 @@
1149  #include <linux/genhd.h>
1150  #include <linux/tqueue.h>
1151  #include <linux/list.h>
1152 +#include <linux/mm.h>
1153 +
1154 +#include <asm/io.h>
1155  
1156  struct request_queue;
1157  typedef struct request_queue request_queue_t;
1158 @@ -36,7 +39,7 @@
1159         unsigned long hard_sector, hard_nr_sectors;
1160         unsigned int nr_segments;
1161         unsigned int nr_hw_segments;
1162 -       unsigned long current_nr_sectors;
1163 +       unsigned long current_nr_sectors, hard_cur_sectors;
1164         void * special;
1165         char * buffer;
1166         struct completion * waiting;
1167 @@ -123,6 +126,8 @@
1168          */
1169         char                    head_active;
1170  
1171 +       unsigned long           bounce_pfn;
1172 +
1173         /*
1174          * Is meant to protect the queue in the future instead of
1175          * io_request_lock
1176 @@ -135,6 +140,38 @@
1177         wait_queue_head_t       wait_for_requests[2];
1178  };
1179  
1180 +extern unsigned long blk_max_low_pfn, blk_max_pfn;
1181 +
1182 +#define BLK_BOUNCE_HIGH                (blk_max_low_pfn << PAGE_SHIFT)
1183 +#define BLK_BOUNCE_ANY         (blk_max_pfn << PAGE_SHIFT)
1184 +
1185 +extern void blk_queue_bounce_limit(request_queue_t *, u64);
1186 +
1187 +#ifdef CONFIG_HIGHMEM
1188 +extern struct buffer_head *create_bounce(int, struct buffer_head *);
1189 +extern inline struct buffer_head *blk_queue_bounce(request_queue_t *q, int rw,
1190 +                                                  struct buffer_head *bh)
1191 +{
1192 +       struct page *page = bh->b_page;
1193 +
1194 +#ifndef CONFIG_DISCONTIGMEM
1195 +       if (page - mem_map <= q->bounce_pfn)
1196 +#else
1197 +       if ((page - page_zone(page)->zone_mem_map) + (page_zone(page)->zone_start_paddr >> PAGE_SHIFT) <= q->bounce_pfn)
1198 +#endif
1199 +               return bh;
1200 +
1201 +       return create_bounce(rw, bh);
1202 +}
1203 +#else
1204 +#define blk_queue_bounce(q, rw, bh)    (bh)
1205 +#endif
1206 +
1207 +#define bh_phys(bh)            (page_to_phys((bh)->b_page) + bh_offset((bh)))
1208 +
1209 +#define BH_CONTIG(b1, b2)      (bh_phys((b1)) + (b1)->b_size == bh_phys((b2)))
1210 +#define BH_PHYS_4G(b1, b2)     ((bh_phys((b1)) | 0xffffffff) == ((bh_phys((b2)) + (b2)->b_size - 1) | 0xffffffff))
1211 +
1212  struct blk_dev_struct {
1213         /*
1214          * queue_proc has to be atomic
1215 @@ -174,6 +211,7 @@
1216  extern void blk_queue_headactive(request_queue_t *, int);
1217  extern void blk_queue_make_request(request_queue_t *, make_request_fn *);
1218  extern void generic_unplug_device(void *);
1219 +extern inline int blk_seg_merge_ok(struct buffer_head *, struct buffer_head *);
1220  
1221  extern int * blk_size[MAX_BLKDEV];
1222  
1223 diff -Naur -X /home/marcelo/lib/dontdiff linux-2.4.19/include/linux/highmem.h linux-2.4.20/include/linux/highmem.h
1224 --- linux-2.4.19/include/linux/highmem.h        2002-08-03 00:39:45.000000000 +0000
1225 +++ linux-2.4.20/include/linux/highmem.h        2002-10-29 11:18:34.000000000 +0000
1226 @@ -13,8 +13,7 @@
1227  /* declarations for linux/mm/highmem.c */
1228  unsigned int nr_free_highpages(void);
1229  
1230 -extern struct buffer_head * create_bounce(int rw, struct buffer_head * bh_orig);
1231 -
1232 +extern struct buffer_head *create_bounce(int rw, struct buffer_head * bh_orig);
1233  
1234  static inline char *bh_kmap(struct buffer_head *bh)
1235  {
1236 @@ -26,6 +25,42 @@
1237         kunmap(bh->b_page);
1238  }
1239  
1240 +/*
1241 + * remember to add offset! and never ever reenable interrupts between a
1242 + * bh_kmap_irq and bh_kunmap_irq!!
1243 + */
1244 +static inline char *bh_kmap_irq(struct buffer_head *bh, unsigned long *flags)
1245 +{
1246 +       unsigned long addr;
1247 +
1248 +       __save_flags(*flags);
1249 +
1250 +       /*
1251 +        * could be low
1252 +        */
1253 +       if (!PageHighMem(bh->b_page))
1254 +               return bh->b_data;
1255 +
1256 +       /*
1257 +        * it's a highmem page
1258 +        */
1259 +       __cli();
1260 +       addr = (unsigned long) kmap_atomic(bh->b_page, KM_BH_IRQ);
1261 +
1262 +       if (addr & ~PAGE_MASK)
1263 +               BUG();
1264 +
1265 +       return (char *) addr + bh_offset(bh);
1266 +}
1267 +
1268 +static inline void bh_kunmap_irq(char *buffer, unsigned long *flags)
1269 +{
1270 +       unsigned long ptr = (unsigned long) buffer & PAGE_MASK;
1271 +
1272 +       kunmap_atomic((void *) ptr, KM_BH_IRQ);
1273 +       __restore_flags(*flags);
1274 +}
1275 +
1276  #else /* CONFIG_HIGHMEM */
1277  
1278  static inline unsigned int nr_free_highpages(void) { return 0; }
1279 @@ -37,8 +72,10 @@
1280  #define kmap_atomic(page,idx)          kmap(page)
1281  #define kunmap_atomic(page,idx)                kunmap(page)
1282  
1283 -#define bh_kmap(bh)    ((bh)->b_data)
1284 -#define bh_kunmap(bh)  do { } while (0)
1285 +#define bh_kmap(bh)                    ((bh)->b_data)
1286 +#define bh_kunmap(bh)                  do { } while (0)
1287 +#define bh_kmap_irq(bh, flags)         ((bh)->b_data)
1288 +#define bh_kunmap_irq(bh, flags)       do { *(flags) = 0; } while (0)
1289  
1290  #endif /* CONFIG_HIGHMEM */
1291  
1292 diff -Naur -X /home/marcelo/lib/dontdiff linux-2.4.19/include/asm-i386/kmap_types.h linux-2.4.20/include/asm-i386/kmap_types.h
1293 --- linux-2.4.19/include/asm-i386/kmap_types.h  2001-09-17 20:16:30.000000000 +0000
1294 +++ linux-2.4.20/include/asm-i386/kmap_types.h  2002-10-29 11:18:49.000000000 +0000
1295 @@ -3,10 +3,11 @@
1296  
1297  enum km_type {
1298         KM_BOUNCE_READ,
1299 -       KM_SKB_DATA,
1300 +       KM_SKB_SUNRPC_DATA,
1301         KM_SKB_DATA_SOFTIRQ,
1302         KM_USER0,
1303         KM_USER1,
1304 +       KM_BH_IRQ,
1305         KM_BIO_IRQ,
1306         KM_TYPE_NR
1307  };
1308 diff -Naur -X /home/marcelo/lib/dontdiff linux-2.4.19/include/asm-ppc/kmap_types.h linux-2.4.20/include/asm-ppc/kmap_types.h
1309 --- linux-2.4.19/include/asm-ppc/kmap_types.h   2001-09-17 20:16:30.000000000 +0000
1310 +++ linux-2.4.20/include/asm-ppc/kmap_types.h   2002-10-29 11:18:34.000000000 +0000
1311 @@ -7,10 +7,11 @@
1312  
1313  enum km_type {
1314         KM_BOUNCE_READ,
1315 -       KM_SKB_DATA,
1316 +       KM_SKB_SUNRPC_DATA,
1317         KM_SKB_DATA_SOFTIRQ,
1318         KM_USER0,
1319         KM_USER1,
1320 +       KM_BH_IRQ,
1321         KM_BIO_IRQ,
1322         KM_TYPE_NR
1323  }; 
1324 diff -Naur -X /home/marcelo/lib/dontdiff linux-2.4.19/include/asm-sparc/kmap_types.h linux-2.4.20/include/asm-sparc/kmap_types.h
1325 --- linux-2.4.19/include/asm-sparc/kmap_types.h 2001-09-17 20:16:30.000000000 +0000
1326 +++ linux-2.4.20/include/asm-sparc/kmap_types.h 2002-10-29 11:18:34.000000000 +0000
1327 @@ -3,10 +3,11 @@
1328  
1329  enum km_type {
1330         KM_BOUNCE_READ,
1331 -       KM_SKB_DATA,
1332 +       KM_SKB_SUNRPC_DATA,
1333         KM_SKB_DATA_SOFTIRQ,
1334         KM_USER0,
1335         KM_USER1,
1336 +       KM_BH_IRQ,
1337         KM_BIO_IRQ,
1338         KM_TYPE_NR
1339  };
1340 diff -Naur -X /home/marcelo/lib/dontdiff linux-2.4.19/include/asm-x86_64/kmap_types.h linux-2.4.20/include/asm-x86_64/kmap_types.h
1341 --- linux-2.4.19/include/asm-x86_64/kmap_types.h        1970-01-01 00:00:00.000000000 +0000
1342 +++ linux-2.4.20/include/asm-x86_64/kmap_types.h        2002-10-29 11:18:39.000000000 +0000
1343 @@ -0,0 +1,14 @@
1344 +#ifndef _ASM_KMAP_TYPES_H
1345 +#define _ASM_KMAP_TYPES_H
1346 +
1347 +enum km_type {
1348 +       KM_BOUNCE_READ,
1349 +       KM_SKB_SUNRPC_DATA,
1350 +       KM_SKB_DATA_SOFTIRQ,
1351 +       KM_USER0,
1352 +       KM_USER1,
1353 +       KM_BH_IRQ,
1354 +       KM_TYPE_NR
1355 +};
1356 +
1357 +#endif
1358 diff -Naur -X /home/marcelo/lib/dontdiff linux-2.4.19/drivers/block/ll_rw_blk.c linux-2.4.20/drivers/block/ll_rw_blk.c
1359 --- linux-2.4.19/drivers/block/ll_rw_blk.c      2002-08-03 00:39:43.000000000 +0000
1360 +++ linux-2.4.20/drivers/block/ll_rw_blk.c      2002-10-29 11:18:33.000000000 +0000
1361 @@ -23,6 +23,7 @@
1362  #include <linux/init.h>
1363  #include <linux/smp_lock.h>
1364  #include <linux/completion.h>
1365 +#include <linux/bootmem.h>
1366  
1367  #include <asm/system.h>
1368  #include <asm/io.h>
1369 @@ -117,6 +118,9 @@
1370   */
1371  int * max_sectors[MAX_BLKDEV];
1372  
1373 +unsigned long blk_max_low_pfn, blk_max_pfn;
1374 +int blk_nohighio = 0;
1375 +
1376  static inline int get_max_sectors(kdev_t dev)
1377  {
1378         if (!max_sectors[MAJOR(dev)])
1379 @@ -238,6 +242,55 @@
1380         q->make_request_fn = mfn;
1381  }
1382  
1383 +/**
1384 + * blk_queue_bounce_limit - set bounce buffer limit for queue
1385 + * @q:  the request queue for the device
1386 + * @dma_addr:   bus address limit
1387 + *
1388 + * Description:
1389 + *    Different hardware can have different requirements as to what pages
1390 + *    it can do I/O directly to. A low level driver can call
1391 + *    blk_queue_bounce_limit to have lower memory pages allocated as bounce
1392 + *    buffers for doing I/O to pages residing above @page. By default
1393 + *    the block layer sets this to the highest numbered "low" memory page.
1394 + **/
1395 +void blk_queue_bounce_limit(request_queue_t *q, u64 dma_addr)
1396 +{
1397 +       unsigned long bounce_pfn = dma_addr >> PAGE_SHIFT;
1398 +       unsigned long mb = dma_addr >> 20;
1399 +       static request_queue_t *old_q;
1400 +
1401 +       /*
1402 +        * keep this for debugging for now...
1403 +        */
1404 +       if (dma_addr != BLK_BOUNCE_HIGH && q != old_q) {
1405 +               old_q = q;
1406 +               printk("blk: queue %p, ", q);
1407 +               if (dma_addr == BLK_BOUNCE_ANY)
1408 +                       printk("no I/O memory limit\n");
1409 +               else
1410 +                       printk("I/O limit %luMb (mask 0x%Lx)\n", mb,
1411 +                              (long long) dma_addr);
1412 +       }
1413 +
1414 +       q->bounce_pfn = bounce_pfn;
1415 +}
1416 +
1417 +
1418 +/*
1419 + * can we merge the two segments, or do we need to start a new one?
1420 + */
1421 +inline int blk_seg_merge_ok(struct buffer_head *bh, struct buffer_head *nxt)
1422 +{
1423 +       /*
1424 +        * if bh and nxt are contigous and don't cross a 4g boundary, it's ok
1425 +        */
1426 +       if (BH_CONTIG(bh, nxt) && BH_PHYS_4G(bh, nxt))
1427 +               return 1;
1428 +
1429 +       return 0;
1430 +}
1431 +
1432  static inline int ll_new_segment(request_queue_t *q, struct request *req, int max_segments)
1433  {
1434         if (req->nr_segments < max_segments) {
1435 @@ -250,16 +303,18 @@
1436  static int ll_back_merge_fn(request_queue_t *q, struct request *req, 
1437                             struct buffer_head *bh, int max_segments)
1438  {
1439 -       if (req->bhtail->b_data + req->bhtail->b_size == bh->b_data)
1440 +       if (blk_seg_merge_ok(req->bhtail, bh))
1441                 return 1;
1442 +
1443         return ll_new_segment(q, req, max_segments);
1444  }
1445  
1446  static int ll_front_merge_fn(request_queue_t *q, struct request *req, 
1447                              struct buffer_head *bh, int max_segments)
1448  {
1449 -       if (bh->b_data + bh->b_size == req->bh->b_data)
1450 +       if (blk_seg_merge_ok(bh, req->bh))
1451                 return 1;
1452 +
1453         return ll_new_segment(q, req, max_segments);
1454  }
1455  
1456 @@ -268,9 +323,9 @@
1457  {
1458         int total_segments = req->nr_segments + next->nr_segments;
1459  
1460 -       if (req->bhtail->b_data + req->bhtail->b_size == next->bh->b_data)
1461 +       if (blk_seg_merge_ok(req->bhtail, next->bh))
1462                 total_segments--;
1463 -    
1464 +
1465         if (total_segments > max_segments)
1466                 return 0;
1467  
1468 @@ -444,6 +499,8 @@
1469          */
1470         q->plug_device_fn       = generic_plug_device;
1471         q->head_active          = 1;
1472 +
1473 +       blk_queue_bounce_limit(q, BLK_BOUNCE_HIGH);
1474  }
1475  
1476  #define blkdev_free_rq(list) list_entry((list)->next, struct request, queue);
1477 @@ -540,7 +597,7 @@
1478                 if (q->rq[rw].count == 0)
1479                         schedule();
1480                 spin_lock_irq(&io_request_lock);
1481 -               rq = get_request(q,rw);
1482 +               rq = get_request(q, rw);
1483                 spin_unlock_irq(&io_request_lock);
1484         } while (rq == NULL);
1485         remove_wait_queue(&q->wait_for_requests[rw], &wait);
1486 @@ -594,9 +651,14 @@
1487                 printk(KERN_ERR "drive_stat_acct: cmd not R/W?\n");
1488  }
1489  
1490 -/* Return up to two hd_structs on which to do IO accounting for a given
1491 - * request.  On a partitioned device, we want to account both against
1492 - * the partition and against the whole disk.  */
1493 +#ifdef CONFIG_BLK_STATS
1494 +/*
1495 + * Return up to two hd_structs on which to do IO accounting for a given
1496 + * request.
1497 + *
1498 + * On a partitioned device, we want to account both against the partition
1499 + * and against the whole disk.
1500 + */
1501  static void locate_hd_struct(struct request *req, 
1502                              struct hd_struct **hd1,
1503                              struct hd_struct **hd2)
1504 @@ -611,22 +673,26 @@
1505                 /* Mask out the partition bits: account for the entire disk */
1506                 int devnr = MINOR(req->rq_dev) >> gd->minor_shift;
1507                 int whole_minor = devnr << gd->minor_shift;
1508 +
1509                 *hd1 = &gd->part[whole_minor];
1510                 if (whole_minor != MINOR(req->rq_dev))
1511                         *hd2= &gd->part[MINOR(req->rq_dev)];
1512         }
1513  }
1514  
1515 -/* Round off the performance stats on an hd_struct.  The average IO
1516 - * queue length and utilisation statistics are maintained by observing
1517 - * the current state of the queue length and the amount of time it has
1518 - * been in this state for.  Normally, that accounting is done on IO
1519 - * completion, but that can result in more than a second's worth of IO
1520 - * being accounted for within any one second, leading to >100%
1521 - * utilisation.  To deal with that, we do a round-off before returning
1522 - * the results when reading /proc/partitions, accounting immediately for
1523 - * all queue usage up to the current jiffies and restarting the counters
1524 - * again. */
1525 +/*
1526 + * Round off the performance stats on an hd_struct.
1527 + *
1528 + * The average IO queue length and utilisation statistics are maintained
1529 + * by observing the current state of the queue length and the amount of
1530 + * time it has been in this state for.
1531 + * Normally, that accounting is done on IO completion, but that can result
1532 + * in more than a second's worth of IO being accounted for within any one
1533 + * second, leading to >100% utilisation.  To deal with that, we do a
1534 + * round-off before returning the results when reading /proc/partitions,
1535 + * accounting immediately for all queue usage up to the current jiffies and
1536 + * restarting the counters again.
1537 + */
1538  void disk_round_stats(struct hd_struct *hd)
1539  {
1540         unsigned long now = jiffies;
1541 @@ -639,7 +705,6 @@
1542         hd->last_idle_time = now;       
1543  }
1544  
1545 -
1546  static inline void down_ios(struct hd_struct *hd)
1547  {
1548         disk_round_stats(hd);   
1549 @@ -690,6 +755,7 @@
1550  void req_new_io(struct request *req, int merge, int sectors)
1551  {
1552         struct hd_struct *hd1, *hd2;
1553 +
1554         locate_hd_struct(req, &hd1, &hd2);
1555         if (hd1)
1556                 account_io_start(hd1, req, merge, sectors);
1557 @@ -697,15 +763,29 @@
1558                 account_io_start(hd2, req, merge, sectors);
1559  }
1560  
1561 +void req_merged_io(struct request *req)
1562 +{
1563 +       struct hd_struct *hd1, *hd2;
1564 +
1565 +       locate_hd_struct(req, &hd1, &hd2);
1566 +       if (hd1)
1567 +               down_ios(hd1);
1568 +       if (hd2)        
1569 +               down_ios(hd2);
1570 +}
1571 +
1572  void req_finished_io(struct request *req)
1573  {
1574         struct hd_struct *hd1, *hd2;
1575 +
1576         locate_hd_struct(req, &hd1, &hd2);
1577         if (hd1)
1578                 account_io_end(hd1, req);
1579         if (hd2)        
1580                 account_io_end(hd2, req);
1581  }
1582 +EXPORT_SYMBOL(req_finished_io);
1583 +#endif /* CONFIG_BLK_STATS */
1584  
1585  /*
1586   * add-request adds a request to the linked list.
1587 @@ -764,7 +844,6 @@
1588                           int max_segments)
1589  {
1590         struct request *next;
1591 -       struct hd_struct *hd1, *hd2;
1592    
1593         next = blkdev_next_request(req);
1594         if (req->sector + req->nr_sectors != next->sector)
1595 @@ -791,12 +870,8 @@
1596  
1597         /* One last thing: we have removed a request, so we now have one
1598            less expected IO to complete for accounting purposes. */
1599 +       req_merged_io(req);
1600  
1601 -       locate_hd_struct(req, &hd1, &hd2);
1602 -       if (hd1)
1603 -               down_ios(hd1);
1604 -       if (hd2)        
1605 -               down_ios(hd2);
1606         blkdev_release_request(next);
1607  }
1608  
1609 @@ -866,9 +941,7 @@
1610          * driver. Create a bounce buffer if the buffer data points into
1611          * high memory - keep the original buffer otherwise.
1612          */
1613 -#if CONFIG_HIGHMEM
1614 -       bh = create_bounce(rw, bh);
1615 -#endif
1616 +       bh = blk_queue_bounce(q, rw, bh);
1617  
1618  /* look for a free request. */
1619         /*
1620 @@ -900,7 +973,6 @@
1621                                 insert_here = &req->queue;
1622                                 break;
1623                         }
1624 -                       elevator->elevator_merge_cleanup_fn(q, req, count);
1625                         req->bhtail->b_reqnext = bh;
1626                         req->bhtail = bh;
1627                         req->nr_sectors = req->hard_nr_sectors += count;
1628 @@ -915,11 +987,15 @@
1629                                 insert_here = req->queue.prev;
1630                                 break;
1631                         }
1632 -                       elevator->elevator_merge_cleanup_fn(q, req, count);
1633                         bh->b_reqnext = req->bh;
1634                         req->bh = bh;
1635 +                       /*
1636 +                        * may not be valid, but queues not having bounce
1637 +                        * enabled for highmem pages must not look at
1638 +                        * ->buffer anyway
1639 +                        */
1640                         req->buffer = bh->b_data;
1641 -                       req->current_nr_sectors = count;
1642 +                       req->current_nr_sectors = req->hard_cur_sectors = count;
1643                         req->sector = req->hard_sector = sector;
1644                         req->nr_sectors = req->hard_nr_sectors += count;
1645                         blk_started_io(count);
1646 @@ -978,7 +1054,7 @@
1647         req->errors = 0;
1648         req->hard_sector = req->sector = sector;
1649         req->hard_nr_sectors = req->nr_sectors = count;
1650 -       req->current_nr_sectors = count;
1651 +       req->current_nr_sectors = req->hard_cur_sectors = count;
1652         req->nr_segments = 1; /* Always 1 for a new request. */
1653         req->nr_hw_segments = 1; /* Always 1 for a new request. */
1654         req->buffer = bh->b_data;
1655 @@ -1286,6 +1362,7 @@
1656                         req->nr_sectors = req->hard_nr_sectors;
1657  
1658                         req->current_nr_sectors = bh->b_size >> 9;
1659 +                       req->hard_cur_sectors = req->current_nr_sectors;
1660                         if (req->nr_sectors < req->current_nr_sectors) {
1661                                 req->nr_sectors = req->current_nr_sectors;
1662                                 printk("end_request: buffer-list destroyed\n");
1663 @@ -1324,6 +1401,9 @@
1664         memset(max_readahead, 0, sizeof(max_readahead));
1665         memset(max_sectors, 0, sizeof(max_sectors));
1666  
1667 +       blk_max_low_pfn = max_low_pfn - 1;
1668 +       blk_max_pfn = max_pfn - 1;
1669 +
1670  #ifdef CONFIG_AMIGA_Z2RAM
1671         z2_init();
1672  #endif
1673 @@ -1439,5 +1519,9 @@
1674  EXPORT_SYMBOL(blk_queue_make_request);
1675  EXPORT_SYMBOL(generic_make_request);
1676  EXPORT_SYMBOL(blkdev_release_request);
1677 -EXPORT_SYMBOL(req_finished_io);
1678  EXPORT_SYMBOL(generic_unplug_device);
1679 +EXPORT_SYMBOL(blk_queue_bounce_limit);
1680 +EXPORT_SYMBOL(blk_max_low_pfn);
1681 +EXPORT_SYMBOL(blk_max_pfn);
1682 +EXPORT_SYMBOL(blk_seg_merge_ok);
1683 +EXPORT_SYMBOL(blk_nohighio);
1684 diff -Naur -X /home/marcelo/lib/dontdiff linux-2.4.19/include/linux/bootmem.h linux-2.4.20/include/linux/bootmem.h
1685 --- linux-2.4.19/include/linux/bootmem.h        2001-11-22 19:47:23.000000000 +0000
1686 +++ linux-2.4.20/include/linux/bootmem.h        2002-10-29 11:18:49.000000000 +0000
1687 @@ -16,6 +16,7 @@
1688  
1689  extern unsigned long max_low_pfn;
1690  extern unsigned long min_low_pfn;
1691 +extern unsigned long max_pfn;
1692  
1693  /*
1694   * node_bootmem_map is a map pointer - the bits represent all physical 
This page took 2.25271 seconds and 3 git commands to generate.