misc: use __weak
[platform/kernel/u-boot.git] / common / cmd_ide.c
1 /*
2  * (C) Copyright 2000-2011
3  * Wolfgang Denk, DENX Software Engineering, wd@denx.de.
4  *
5  * SPDX-License-Identifier:     GPL-2.0+
6  */
7
8 /*
9  * IDE support
10  */
11
12 #include <common.h>
13 #include <config.h>
14 #include <watchdog.h>
15 #include <command.h>
16 #include <image.h>
17 #include <asm/byteorder.h>
18 #include <asm/io.h>
19
20 #if defined(CONFIG_IDE_8xx_DIRECT) || defined(CONFIG_IDE_PCMCIA)
21 # include <pcmcia.h>
22 #endif
23
24 #include <ide.h>
25 #include <ata.h>
26
27 #ifdef CONFIG_STATUS_LED
28 # include <status_led.h>
29 #endif
30
31 #ifdef __PPC__
32 # define EIEIO          __asm__ volatile ("eieio")
33 # define SYNC           __asm__ volatile ("sync")
34 #else
35 # define EIEIO          /* nothing */
36 # define SYNC           /* nothing */
37 #endif
38
39 /* ------------------------------------------------------------------------- */
40
41 /* Current I/O Device   */
42 static int curr_device = -1;
43
44 /* Current offset for IDE0 / IDE1 bus access    */
45 ulong ide_bus_offset[CONFIG_SYS_IDE_MAXBUS] = {
46 #if defined(CONFIG_SYS_ATA_IDE0_OFFSET)
47         CONFIG_SYS_ATA_IDE0_OFFSET,
48 #endif
49 #if defined(CONFIG_SYS_ATA_IDE1_OFFSET) && (CONFIG_SYS_IDE_MAXBUS > 1)
50         CONFIG_SYS_ATA_IDE1_OFFSET,
51 #endif
52 };
53
54 static int ide_bus_ok[CONFIG_SYS_IDE_MAXBUS];
55
56 block_dev_desc_t ide_dev_desc[CONFIG_SYS_IDE_MAXDEVICE];
57 /* ------------------------------------------------------------------------- */
58
59 #ifdef CONFIG_IDE_RESET
60 static void  ide_reset (void);
61 #else
62 #define ide_reset()     /* dummy */
63 #endif
64
65 static void  ide_ident (block_dev_desc_t *dev_desc);
66 static uchar ide_wait  (int dev, ulong t);
67
68 #define IDE_TIME_OUT    2000    /* 2 sec timeout */
69
70 #define ATAPI_TIME_OUT  7000    /* 7 sec timeout (5 sec seems to work...) */
71
72 #define IDE_SPIN_UP_TIME_OUT 5000 /* 5 sec spin-up timeout */
73
74 static void ident_cpy (unsigned char *dest, unsigned char *src, unsigned int len);
75
76 #ifndef CONFIG_SYS_ATA_PORT_ADDR
77 #define CONFIG_SYS_ATA_PORT_ADDR(port) (port)
78 #endif
79
80 #ifdef CONFIG_ATAPI
81 static void     atapi_inquiry(block_dev_desc_t *dev_desc);
82 static ulong atapi_read(int device, ulong blknr, lbaint_t blkcnt,
83                         void *buffer);
84 #endif
85
86
87 /* ------------------------------------------------------------------------- */
88
89 int do_ide(cmd_tbl_t *cmdtp, int flag, int argc, char *const argv[])
90 {
91         int rcode = 0;
92
93         switch (argc) {
94         case 0:
95         case 1:
96                 return CMD_RET_USAGE;
97         case 2:
98                 if (strncmp(argv[1], "res", 3) == 0) {
99                         puts("\nReset IDE"
100 #ifdef CONFIG_IDE_8xx_DIRECT
101                              " on PCMCIA " PCMCIA_SLOT_MSG
102 #endif
103                              ": ");
104
105                         ide_init();
106                         return 0;
107                 } else if (strncmp(argv[1], "inf", 3) == 0) {
108                         int i;
109
110                         putc('\n');
111
112                         for (i = 0; i < CONFIG_SYS_IDE_MAXDEVICE; ++i) {
113                                 if (ide_dev_desc[i].type == DEV_TYPE_UNKNOWN)
114                                         continue;  /* list only known devices */
115                                 printf("IDE device %d: ", i);
116                                 dev_print(&ide_dev_desc[i]);
117                         }
118                         return 0;
119
120                 } else if (strncmp(argv[1], "dev", 3) == 0) {
121                         if ((curr_device < 0)
122                             || (curr_device >= CONFIG_SYS_IDE_MAXDEVICE)) {
123                                 puts("\nno IDE devices available\n");
124                                 return 1;
125                         }
126                         printf("\nIDE device %d: ", curr_device);
127                         dev_print(&ide_dev_desc[curr_device]);
128                         return 0;
129                 } else if (strncmp(argv[1], "part", 4) == 0) {
130                         int dev, ok;
131
132                         for (ok = 0, dev = 0;
133                              dev < CONFIG_SYS_IDE_MAXDEVICE;
134                              ++dev) {
135                                 if (ide_dev_desc[dev].part_type !=
136                                     PART_TYPE_UNKNOWN) {
137                                         ++ok;
138                                         if (dev)
139                                                 putc('\n');
140                                         print_part(&ide_dev_desc[dev]);
141                                 }
142                         }
143                         if (!ok) {
144                                 puts("\nno IDE devices available\n");
145                                 rcode++;
146                         }
147                         return rcode;
148                 }
149                 return CMD_RET_USAGE;
150         case 3:
151                 if (strncmp(argv[1], "dev", 3) == 0) {
152                         int dev = (int) simple_strtoul(argv[2], NULL, 10);
153
154                         printf("\nIDE device %d: ", dev);
155                         if (dev >= CONFIG_SYS_IDE_MAXDEVICE) {
156                                 puts("unknown device\n");
157                                 return 1;
158                         }
159                         dev_print(&ide_dev_desc[dev]);
160                         /*ide_print (dev); */
161
162                         if (ide_dev_desc[dev].type == DEV_TYPE_UNKNOWN)
163                                 return 1;
164
165                         curr_device = dev;
166
167                         puts("... is now current device\n");
168
169                         return 0;
170                 } else if (strncmp(argv[1], "part", 4) == 0) {
171                         int dev = (int) simple_strtoul(argv[2], NULL, 10);
172
173                         if (ide_dev_desc[dev].part_type != PART_TYPE_UNKNOWN) {
174                                 print_part(&ide_dev_desc[dev]);
175                         } else {
176                                 printf("\nIDE device %d not available\n",
177                                        dev);
178                                 rcode = 1;
179                         }
180                         return rcode;
181                 }
182
183                 return CMD_RET_USAGE;
184         default:
185                 /* at least 4 args */
186
187                 if (strcmp(argv[1], "read") == 0) {
188                         ulong addr = simple_strtoul(argv[2], NULL, 16);
189                         ulong cnt = simple_strtoul(argv[4], NULL, 16);
190                         ulong n;
191
192 #ifdef CONFIG_SYS_64BIT_LBA
193                         lbaint_t blk = simple_strtoull(argv[3], NULL, 16);
194
195                         printf("\nIDE read: device %d block # %lld, count %ld ... ",
196                                 curr_device, blk, cnt);
197 #else
198                         lbaint_t blk = simple_strtoul(argv[3], NULL, 16);
199
200                         printf("\nIDE read: device %d block # %ld, count %ld ... ",
201                                 curr_device, blk, cnt);
202 #endif
203
204                         n = ide_dev_desc[curr_device].block_read(curr_device,
205                                                                  blk, cnt,
206                                                                  (ulong *)addr);
207                         /* flush cache after read */
208                         flush_cache(addr,
209                                     cnt * ide_dev_desc[curr_device].blksz);
210
211                         printf("%ld blocks read: %s\n",
212                                n, (n == cnt) ? "OK" : "ERROR");
213                         if (n == cnt)
214                                 return 0;
215                         else
216                                 return 1;
217                 } else if (strcmp(argv[1], "write") == 0) {
218                         ulong addr = simple_strtoul(argv[2], NULL, 16);
219                         ulong cnt = simple_strtoul(argv[4], NULL, 16);
220                         ulong n;
221
222 #ifdef CONFIG_SYS_64BIT_LBA
223                         lbaint_t blk = simple_strtoull(argv[3], NULL, 16);
224
225                         printf("\nIDE write: device %d block # %lld, count %ld ... ",
226                                 curr_device, blk, cnt);
227 #else
228                         lbaint_t blk = simple_strtoul(argv[3], NULL, 16);
229
230                         printf("\nIDE write: device %d block # %ld, count %ld ... ",
231                                 curr_device, blk, cnt);
232 #endif
233                         n = ide_write(curr_device, blk, cnt, (ulong *) addr);
234
235                         printf("%ld blocks written: %s\n",
236                                 n, (n == cnt) ? "OK" : "ERROR");
237                         if (n == cnt)
238                                 return 0;
239                         else
240                                 return 1;
241                 } else {
242                         return CMD_RET_USAGE;
243                 }
244
245                 return rcode;
246         }
247 }
248
249 int do_diskboot(cmd_tbl_t *cmdtp, int flag, int argc, char *const argv[])
250 {
251         return common_diskboot(cmdtp, "ide", argc, argv);
252 }
253
254 /* ------------------------------------------------------------------------- */
255
256 __weak void ide_led(uchar led, uchar status)
257 {
258 #if defined(CONFIG_IDE_LED) && defined(PER8_BASE) /* required by LED_PORT */
259         static uchar led_buffer;        /* Buffer for current LED status */
260
261         uchar *led_port = LED_PORT;
262
263         if (status)             /* switch LED on        */
264                 led_buffer |= led;
265         else                    /* switch LED off       */
266                 led_buffer &= ~led;
267
268         *led_port = led_buffer;
269 #endif
270 }
271
272 #ifndef CONFIG_IDE_LED  /* define LED macros, they are not used anyways */
273 # define DEVICE_LED(x) 0
274 # define LED_IDE1 1
275 # define LED_IDE2 2
276 #endif
277
278 /* ------------------------------------------------------------------------- */
279
280 __weak void ide_outb(int dev, int port, unsigned char val)
281 {
282         debug("ide_outb (dev= %d, port= 0x%x, val= 0x%02x) : @ 0x%08lx\n",
283               dev, port, val,
284               (ATA_CURR_BASE(dev) + CONFIG_SYS_ATA_PORT_ADDR(port)));
285
286 #if defined(CONFIG_IDE_AHB)
287         if (port) {
288                 /* write command */
289                 ide_write_register(dev, port, val);
290         } else {
291                 /* write data */
292                 outb(val, (ATA_CURR_BASE(dev)));
293         }
294 #else
295         outb(val, (ATA_CURR_BASE(dev) + CONFIG_SYS_ATA_PORT_ADDR(port)));
296 #endif
297 }
298
299 __weak unsigned char ide_inb(int dev, int port)
300 {
301         uchar val;
302
303 #if defined(CONFIG_IDE_AHB)
304         val = ide_read_register(dev, port);
305 #else
306         val = inb((ATA_CURR_BASE(dev) + CONFIG_SYS_ATA_PORT_ADDR(port)));
307 #endif
308
309         debug("ide_inb (dev= %d, port= 0x%x) : @ 0x%08lx -> 0x%02x\n",
310               dev, port,
311               (ATA_CURR_BASE(dev) + CONFIG_SYS_ATA_PORT_ADDR(port)), val);
312         return val;
313 }
314
315 void ide_init(void)
316 {
317         unsigned char c;
318         int i, bus;
319
320 #ifdef CONFIG_IDE_8xx_PCCARD
321         extern int ide_devices_found;   /* Initialized in check_ide_device() */
322 #endif /* CONFIG_IDE_8xx_PCCARD */
323
324 #ifdef CONFIG_IDE_PREINIT
325         WATCHDOG_RESET();
326
327         if (ide_preinit()) {
328                 puts("ide_preinit failed\n");
329                 return;
330         }
331 #endif /* CONFIG_IDE_PREINIT */
332
333         WATCHDOG_RESET();
334
335         /*
336          * Reset the IDE just to be sure.
337          * Light LED's to show
338          */
339         ide_led((LED_IDE1 | LED_IDE2), 1);      /* LED's on     */
340
341         /* ATAPI Drives seems to need a proper IDE Reset */
342         ide_reset();
343
344 #ifdef CONFIG_IDE_INIT_POSTRESET
345         WATCHDOG_RESET();
346
347         if (ide_init_postreset()) {
348                 puts("ide_preinit_postreset failed\n");
349                 return;
350         }
351 #endif /* CONFIG_IDE_INIT_POSTRESET */
352
353         /*
354          * Wait for IDE to get ready.
355          * According to spec, this can take up to 31 seconds!
356          */
357         for (bus = 0; bus < CONFIG_SYS_IDE_MAXBUS; ++bus) {
358                 int dev =
359                         bus * (CONFIG_SYS_IDE_MAXDEVICE /
360                                CONFIG_SYS_IDE_MAXBUS);
361
362 #ifdef CONFIG_IDE_8xx_PCCARD
363                 /* Skip non-ide devices from probing */
364                 if ((ide_devices_found & (1 << bus)) == 0) {
365                         ide_led((LED_IDE1 | LED_IDE2), 0);      /* LED's off */
366                         continue;
367                 }
368 #endif
369                 printf("Bus %d: ", bus);
370
371                 ide_bus_ok[bus] = 0;
372
373                 /* Select device
374                  */
375                 udelay(100000); /* 100 ms */
376                 ide_outb(dev, ATA_DEV_HD, ATA_LBA | ATA_DEVICE(dev));
377                 udelay(100000); /* 100 ms */
378                 i = 0;
379                 do {
380                         udelay(10000);  /* 10 ms */
381
382                         c = ide_inb(dev, ATA_STATUS);
383                         i++;
384                         if (i > (ATA_RESET_TIME * 100)) {
385                                 puts("** Timeout **\n");
386                                 /* LED's off */
387                                 ide_led((LED_IDE1 | LED_IDE2), 0);
388                                 return;
389                         }
390                         if ((i >= 100) && ((i % 100) == 0))
391                                 putc('.');
392
393                 } while (c & ATA_STAT_BUSY);
394
395                 if (c & (ATA_STAT_BUSY | ATA_STAT_FAULT)) {
396                         puts("not available  ");
397                         debug("Status = 0x%02X ", c);
398 #ifndef CONFIG_ATAPI            /* ATAPI Devices do not set DRDY */
399                 } else if ((c & ATA_STAT_READY) == 0) {
400                         puts("not available  ");
401                         debug("Status = 0x%02X ", c);
402 #endif
403                 } else {
404                         puts("OK ");
405                         ide_bus_ok[bus] = 1;
406                 }
407                 WATCHDOG_RESET();
408         }
409
410         putc('\n');
411
412         ide_led((LED_IDE1 | LED_IDE2), 0);      /* LED's off    */
413
414         curr_device = -1;
415         for (i = 0; i < CONFIG_SYS_IDE_MAXDEVICE; ++i) {
416                 int led = (IDE_BUS(i) == 0) ? LED_IDE1 : LED_IDE2;
417                 ide_dev_desc[i].type = DEV_TYPE_UNKNOWN;
418                 ide_dev_desc[i].if_type = IF_TYPE_IDE;
419                 ide_dev_desc[i].dev = i;
420                 ide_dev_desc[i].part_type = PART_TYPE_UNKNOWN;
421                 ide_dev_desc[i].blksz = 0;
422                 ide_dev_desc[i].log2blksz =
423                         LOG2_INVALID(typeof(ide_dev_desc[i].log2blksz));
424                 ide_dev_desc[i].lba = 0;
425                 ide_dev_desc[i].block_read = ide_read;
426                 ide_dev_desc[i].block_write = ide_write;
427                 if (!ide_bus_ok[IDE_BUS(i)])
428                         continue;
429                 ide_led(led, 1);        /* LED on       */
430                 ide_ident(&ide_dev_desc[i]);
431                 ide_led(led, 0);        /* LED off      */
432                 dev_print(&ide_dev_desc[i]);
433
434                 if ((ide_dev_desc[i].lba > 0) && (ide_dev_desc[i].blksz > 0)) {
435                         /* initialize partition type */
436                         init_part(&ide_dev_desc[i]);
437                         if (curr_device < 0)
438                                 curr_device = i;
439                 }
440         }
441         WATCHDOG_RESET();
442 }
443
444 /* ------------------------------------------------------------------------- */
445
446 #ifdef CONFIG_PARTITIONS
447 block_dev_desc_t *ide_get_dev(int dev)
448 {
449         return (dev < CONFIG_SYS_IDE_MAXDEVICE) ? &ide_dev_desc[dev] : NULL;
450 }
451 #endif
452
453 /* ------------------------------------------------------------------------- */
454
455 /* We only need to swap data if we are running on a big endian cpu. */
456 #if defined(__LITTLE_ENDIAN)
457 __weak void ide_input_swap_data(int dev, ulong *sect_buf, int words)
458 {
459         ide_input_data(dev, sect_buf, words);
460 }
461 #else
462 __weak void ide_input_swap_data(int dev, ulong *sect_buf, int words)
463 {
464         volatile ushort *pbuf =
465                 (ushort *) (ATA_CURR_BASE(dev) + ATA_DATA_REG);
466         ushort *dbuf = (ushort *) sect_buf;
467
468         debug("in input swap data base for read is %lx\n",
469               (unsigned long) pbuf);
470
471         while (words--) {
472 #ifdef __MIPS__
473                 *dbuf++ = swab16p((u16 *) pbuf);
474                 *dbuf++ = swab16p((u16 *) pbuf);
475 #else
476                 *dbuf++ = ld_le16(pbuf);
477                 *dbuf++ = ld_le16(pbuf);
478 #endif /* !MIPS */
479         }
480 }
481 #endif /* __LITTLE_ENDIAN */
482
483
484 #if defined(CONFIG_IDE_SWAP_IO)
485 __weak void ide_output_data(int dev, const ulong *sect_buf, int words)
486 {
487         ushort *dbuf;
488         volatile ushort *pbuf;
489
490         pbuf = (ushort *) (ATA_CURR_BASE(dev) + ATA_DATA_REG);
491         dbuf = (ushort *) sect_buf;
492         while (words--) {
493                 EIEIO;
494                 *pbuf = *dbuf++;
495                 EIEIO;
496                 *pbuf = *dbuf++;
497         }
498 }
499 #else  /* ! CONFIG_IDE_SWAP_IO */
500 __weak void ide_output_data(int dev, const ulong *sect_buf, int words)
501 {
502 #if defined(CONFIG_IDE_AHB)
503         ide_write_data(dev, sect_buf, words);
504 #else
505         outsw(ATA_CURR_BASE(dev) + ATA_DATA_REG, sect_buf, words << 1);
506 #endif
507 }
508 #endif /* CONFIG_IDE_SWAP_IO */
509
510 #if defined(CONFIG_IDE_SWAP_IO)
511 __weak void ide_input_data(int dev, ulong *sect_buf, int words)
512 {
513         ushort *dbuf;
514         volatile ushort *pbuf;
515
516         pbuf = (ushort *) (ATA_CURR_BASE(dev) + ATA_DATA_REG);
517         dbuf = (ushort *) sect_buf;
518
519         debug("in input data base for read is %lx\n", (unsigned long) pbuf);
520
521         while (words--) {
522                 EIEIO;
523                 *dbuf++ = *pbuf;
524                 EIEIO;
525                 *dbuf++ = *pbuf;
526         }
527 }
528 #else  /* ! CONFIG_IDE_SWAP_IO */
529 __weak void ide_input_data(int dev, ulong *sect_buf, int words)
530 {
531 #if defined(CONFIG_IDE_AHB)
532         ide_read_data(dev, sect_buf, words);
533 #else
534         insw(ATA_CURR_BASE(dev) + ATA_DATA_REG, sect_buf, words << 1);
535 #endif
536 }
537
538 #endif /* CONFIG_IDE_SWAP_IO */
539
540 /* -------------------------------------------------------------------------
541  */
542 static void ide_ident(block_dev_desc_t *dev_desc)
543 {
544         unsigned char c;
545         hd_driveid_t iop;
546
547 #ifdef CONFIG_ATAPI
548         int retries = 0;
549 #endif
550         int device;
551
552         device = dev_desc->dev;
553         printf("  Device %d: ", device);
554
555         ide_led(DEVICE_LED(device), 1); /* LED on       */
556         /* Select device
557          */
558         ide_outb(device, ATA_DEV_HD, ATA_LBA | ATA_DEVICE(device));
559         dev_desc->if_type = IF_TYPE_IDE;
560 #ifdef CONFIG_ATAPI
561
562         retries = 0;
563
564         /* Warning: This will be tricky to read */
565         while (retries <= 1) {
566                 /* check signature */
567                 if ((ide_inb(device, ATA_SECT_CNT) == 0x01) &&
568                     (ide_inb(device, ATA_SECT_NUM) == 0x01) &&
569                     (ide_inb(device, ATA_CYL_LOW) == 0x14) &&
570                     (ide_inb(device, ATA_CYL_HIGH) == 0xEB)) {
571                         /* ATAPI Signature found */
572                         dev_desc->if_type = IF_TYPE_ATAPI;
573                         /*
574                          * Start Ident Command
575                          */
576                         ide_outb(device, ATA_COMMAND, ATAPI_CMD_IDENT);
577                         /*
578                          * Wait for completion - ATAPI devices need more time
579                          * to become ready
580                          */
581                         c = ide_wait(device, ATAPI_TIME_OUT);
582                 } else
583 #endif
584                 {
585                         /*
586                          * Start Ident Command
587                          */
588                         ide_outb(device, ATA_COMMAND, ATA_CMD_IDENT);
589
590                         /*
591                          * Wait for completion
592                          */
593                         c = ide_wait(device, IDE_TIME_OUT);
594                 }
595                 ide_led(DEVICE_LED(device), 0); /* LED off      */
596
597                 if (((c & ATA_STAT_DRQ) == 0) ||
598                     ((c & (ATA_STAT_FAULT | ATA_STAT_ERR)) != 0)) {
599 #ifdef CONFIG_ATAPI
600                         {
601                                 /*
602                                  * Need to soft reset the device
603                                  * in case it's an ATAPI...
604                                  */
605                                 debug("Retrying...\n");
606                                 ide_outb(device, ATA_DEV_HD,
607                                          ATA_LBA | ATA_DEVICE(device));
608                                 udelay(100000);
609                                 ide_outb(device, ATA_COMMAND, 0x08);
610                                 udelay(500000); /* 500 ms */
611                         }
612                         /*
613                          * Select device
614                          */
615                         ide_outb(device, ATA_DEV_HD,
616                                  ATA_LBA | ATA_DEVICE(device));
617                         retries++;
618 #else
619                         return;
620 #endif
621                 }
622 #ifdef CONFIG_ATAPI
623                 else
624                         break;
625         }                       /* see above - ugly to read */
626
627         if (retries == 2)       /* Not found */
628                 return;
629 #endif
630
631         ide_input_swap_data(device, (ulong *)&iop, ATA_SECTORWORDS);
632
633         ident_cpy((unsigned char *) dev_desc->revision, iop.fw_rev,
634                   sizeof(dev_desc->revision));
635         ident_cpy((unsigned char *) dev_desc->vendor, iop.model,
636                   sizeof(dev_desc->vendor));
637         ident_cpy((unsigned char *) dev_desc->product, iop.serial_no,
638                   sizeof(dev_desc->product));
639 #ifdef __LITTLE_ENDIAN
640         /*
641          * firmware revision, model, and serial number have Big Endian Byte
642          * order in Word. Convert all three to little endian.
643          *
644          * See CF+ and CompactFlash Specification Revision 2.0:
645          * 6.2.1.6: Identify Drive, Table 39 for more details
646          */
647
648         strswab(dev_desc->revision);
649         strswab(dev_desc->vendor);
650         strswab(dev_desc->product);
651 #endif /* __LITTLE_ENDIAN */
652
653         if ((iop.config & 0x0080) == 0x0080)
654                 dev_desc->removable = 1;
655         else
656                 dev_desc->removable = 0;
657
658 #ifdef CONFIG_ATAPI
659         if (dev_desc->if_type == IF_TYPE_ATAPI) {
660                 atapi_inquiry(dev_desc);
661                 return;
662         }
663 #endif /* CONFIG_ATAPI */
664
665 #ifdef __BIG_ENDIAN
666         /* swap shorts */
667         dev_desc->lba = (iop.lba_capacity << 16) | (iop.lba_capacity >> 16);
668 #else  /* ! __BIG_ENDIAN */
669         /*
670          * do not swap shorts on little endian
671          *
672          * See CF+ and CompactFlash Specification Revision 2.0:
673          * 6.2.1.6: Identfy Drive, Table 39, Word Address 57-58 for details.
674          */
675         dev_desc->lba = iop.lba_capacity;
676 #endif /* __BIG_ENDIAN */
677
678 #ifdef CONFIG_LBA48
679         if (iop.command_set_2 & 0x0400) {       /* LBA 48 support */
680                 dev_desc->lba48 = 1;
681                 dev_desc->lba = (unsigned long long) iop.lba48_capacity[0] |
682                         ((unsigned long long) iop.lba48_capacity[1] << 16) |
683                         ((unsigned long long) iop.lba48_capacity[2] << 32) |
684                         ((unsigned long long) iop.lba48_capacity[3] << 48);
685         } else {
686                 dev_desc->lba48 = 0;
687         }
688 #endif /* CONFIG_LBA48 */
689         /* assuming HD */
690         dev_desc->type = DEV_TYPE_HARDDISK;
691         dev_desc->blksz = ATA_BLOCKSIZE;
692         dev_desc->log2blksz = LOG2(dev_desc->blksz);
693         dev_desc->lun = 0;      /* just to fill something in... */
694
695 #if 0                           /* only used to test the powersaving mode,
696                                  * if enabled, the drive goes after 5 sec
697                                  * in standby mode */
698         ide_outb(device, ATA_DEV_HD, ATA_LBA | ATA_DEVICE(device));
699         c = ide_wait(device, IDE_TIME_OUT);
700         ide_outb(device, ATA_SECT_CNT, 1);
701         ide_outb(device, ATA_LBA_LOW, 0);
702         ide_outb(device, ATA_LBA_MID, 0);
703         ide_outb(device, ATA_LBA_HIGH, 0);
704         ide_outb(device, ATA_DEV_HD, ATA_LBA | ATA_DEVICE(device));
705         ide_outb(device, ATA_COMMAND, 0xe3);
706         udelay(50);
707         c = ide_wait(device, IDE_TIME_OUT);     /* can't take over 500 ms */
708 #endif
709 }
710
711
712 /* ------------------------------------------------------------------------- */
713
714 ulong ide_read(int device, lbaint_t blknr, lbaint_t blkcnt, void *buffer)
715 {
716         ulong n = 0;
717         unsigned char c;
718         unsigned char pwrsave = 0;      /* power save */
719
720 #ifdef CONFIG_LBA48
721         unsigned char lba48 = 0;
722
723         if (blknr & 0x0000fffff0000000ULL) {
724                 /* more than 28 bits used, use 48bit mode */
725                 lba48 = 1;
726         }
727 #endif
728         debug("ide_read dev %d start " LBAF ", blocks " LBAF " buffer at %lX\n",
729               device, blknr, blkcnt, (ulong) buffer);
730
731         ide_led(DEVICE_LED(device), 1); /* LED on       */
732
733         /* Select device
734          */
735         ide_outb(device, ATA_DEV_HD, ATA_LBA | ATA_DEVICE(device));
736         c = ide_wait(device, IDE_TIME_OUT);
737
738         if (c & ATA_STAT_BUSY) {
739                 printf("IDE read: device %d not ready\n", device);
740                 goto IDE_READ_E;
741         }
742
743         /* first check if the drive is in Powersaving mode, if yes,
744          * increase the timeout value */
745         ide_outb(device, ATA_COMMAND, ATA_CMD_CHK_PWR);
746         udelay(50);
747
748         c = ide_wait(device, IDE_TIME_OUT);     /* can't take over 500 ms */
749
750         if (c & ATA_STAT_BUSY) {
751                 printf("IDE read: device %d not ready\n", device);
752                 goto IDE_READ_E;
753         }
754         if ((c & ATA_STAT_ERR) == ATA_STAT_ERR) {
755                 printf("No Powersaving mode %X\n", c);
756         } else {
757                 c = ide_inb(device, ATA_SECT_CNT);
758                 debug("Powersaving %02X\n", c);
759                 if (c == 0)
760                         pwrsave = 1;
761         }
762
763
764         while (blkcnt-- > 0) {
765
766                 c = ide_wait(device, IDE_TIME_OUT);
767
768                 if (c & ATA_STAT_BUSY) {
769                         printf("IDE read: device %d not ready\n", device);
770                         break;
771                 }
772 #ifdef CONFIG_LBA48
773                 if (lba48) {
774                         /* write high bits */
775                         ide_outb(device, ATA_SECT_CNT, 0);
776                         ide_outb(device, ATA_LBA_LOW, (blknr >> 24) & 0xFF);
777 #ifdef CONFIG_SYS_64BIT_LBA
778                         ide_outb(device, ATA_LBA_MID, (blknr >> 32) & 0xFF);
779                         ide_outb(device, ATA_LBA_HIGH, (blknr >> 40) & 0xFF);
780 #else
781                         ide_outb(device, ATA_LBA_MID, 0);
782                         ide_outb(device, ATA_LBA_HIGH, 0);
783 #endif
784                 }
785 #endif
786                 ide_outb(device, ATA_SECT_CNT, 1);
787                 ide_outb(device, ATA_LBA_LOW, (blknr >> 0) & 0xFF);
788                 ide_outb(device, ATA_LBA_MID, (blknr >> 8) & 0xFF);
789                 ide_outb(device, ATA_LBA_HIGH, (blknr >> 16) & 0xFF);
790
791 #ifdef CONFIG_LBA48
792                 if (lba48) {
793                         ide_outb(device, ATA_DEV_HD,
794                                  ATA_LBA | ATA_DEVICE(device));
795                         ide_outb(device, ATA_COMMAND, ATA_CMD_READ_EXT);
796
797                 } else
798 #endif
799                 {
800                         ide_outb(device, ATA_DEV_HD, ATA_LBA |
801                                  ATA_DEVICE(device) | ((blknr >> 24) & 0xF));
802                         ide_outb(device, ATA_COMMAND, ATA_CMD_READ);
803                 }
804
805                 udelay(50);
806
807                 if (pwrsave) {
808                         /* may take up to 4 sec */
809                         c = ide_wait(device, IDE_SPIN_UP_TIME_OUT);
810                         pwrsave = 0;
811                 } else {
812                         /* can't take over 500 ms */
813                         c = ide_wait(device, IDE_TIME_OUT);
814                 }
815
816                 if ((c & (ATA_STAT_DRQ | ATA_STAT_BUSY | ATA_STAT_ERR)) !=
817                     ATA_STAT_DRQ) {
818                         printf("Error (no IRQ) dev %d blk " LBAF ": status "
819                                "%#02x\n", device, blknr, c);
820                         break;
821                 }
822
823                 ide_input_data(device, buffer, ATA_SECTORWORDS);
824                 (void) ide_inb(device, ATA_STATUS);     /* clear IRQ */
825
826                 ++n;
827                 ++blknr;
828                 buffer += ATA_BLOCKSIZE;
829         }
830 IDE_READ_E:
831         ide_led(DEVICE_LED(device), 0); /* LED off      */
832         return (n);
833 }
834
835 /* ------------------------------------------------------------------------- */
836
837
838 ulong ide_write(int device, lbaint_t blknr, lbaint_t blkcnt, const void *buffer)
839 {
840         ulong n = 0;
841         unsigned char c;
842
843 #ifdef CONFIG_LBA48
844         unsigned char lba48 = 0;
845
846         if (blknr & 0x0000fffff0000000ULL) {
847                 /* more than 28 bits used, use 48bit mode */
848                 lba48 = 1;
849         }
850 #endif
851
852         ide_led(DEVICE_LED(device), 1); /* LED on       */
853
854         /* Select device
855          */
856         ide_outb(device, ATA_DEV_HD, ATA_LBA | ATA_DEVICE(device));
857
858         while (blkcnt-- > 0) {
859
860                 c = ide_wait(device, IDE_TIME_OUT);
861
862                 if (c & ATA_STAT_BUSY) {
863                         printf("IDE read: device %d not ready\n", device);
864                         goto WR_OUT;
865                 }
866 #ifdef CONFIG_LBA48
867                 if (lba48) {
868                         /* write high bits */
869                         ide_outb(device, ATA_SECT_CNT, 0);
870                         ide_outb(device, ATA_LBA_LOW, (blknr >> 24) & 0xFF);
871 #ifdef CONFIG_SYS_64BIT_LBA
872                         ide_outb(device, ATA_LBA_MID, (blknr >> 32) & 0xFF);
873                         ide_outb(device, ATA_LBA_HIGH, (blknr >> 40) & 0xFF);
874 #else
875                         ide_outb(device, ATA_LBA_MID, 0);
876                         ide_outb(device, ATA_LBA_HIGH, 0);
877 #endif
878                 }
879 #endif
880                 ide_outb(device, ATA_SECT_CNT, 1);
881                 ide_outb(device, ATA_LBA_LOW, (blknr >> 0) & 0xFF);
882                 ide_outb(device, ATA_LBA_MID, (blknr >> 8) & 0xFF);
883                 ide_outb(device, ATA_LBA_HIGH, (blknr >> 16) & 0xFF);
884
885 #ifdef CONFIG_LBA48
886                 if (lba48) {
887                         ide_outb(device, ATA_DEV_HD,
888                                  ATA_LBA | ATA_DEVICE(device));
889                         ide_outb(device, ATA_COMMAND, ATA_CMD_WRITE_EXT);
890
891                 } else
892 #endif
893                 {
894                         ide_outb(device, ATA_DEV_HD, ATA_LBA |
895                                  ATA_DEVICE(device) | ((blknr >> 24) & 0xF));
896                         ide_outb(device, ATA_COMMAND, ATA_CMD_WRITE);
897                 }
898
899                 udelay(50);
900
901                 /* can't take over 500 ms */
902                 c = ide_wait(device, IDE_TIME_OUT);
903
904                 if ((c & (ATA_STAT_DRQ | ATA_STAT_BUSY | ATA_STAT_ERR)) !=
905                     ATA_STAT_DRQ) {
906                         printf("Error (no IRQ) dev %d blk " LBAF ": status "
907                                 "%#02x\n", device, blknr, c);
908                         goto WR_OUT;
909                 }
910
911                 ide_output_data(device, buffer, ATA_SECTORWORDS);
912                 c = ide_inb(device, ATA_STATUS);        /* clear IRQ */
913                 ++n;
914                 ++blknr;
915                 buffer += ATA_BLOCKSIZE;
916         }
917 WR_OUT:
918         ide_led(DEVICE_LED(device), 0); /* LED off      */
919         return (n);
920 }
921
922 /* ------------------------------------------------------------------------- */
923
924 /*
925  * copy src to dest, skipping leading and trailing blanks and null
926  * terminate the string
927  * "len" is the size of available memory including the terminating '\0'
928  */
929 static void ident_cpy(unsigned char *dst, unsigned char *src,
930                       unsigned int len)
931 {
932         unsigned char *end, *last;
933
934         last = dst;
935         end = src + len - 1;
936
937         /* reserve space for '\0' */
938         if (len < 2)
939                 goto OUT;
940
941         /* skip leading white space */
942         while ((*src) && (src < end) && (*src == ' '))
943                 ++src;
944
945         /* copy string, omitting trailing white space */
946         while ((*src) && (src < end)) {
947                 *dst++ = *src;
948                 if (*src++ != ' ')
949                         last = dst;
950         }
951 OUT:
952         *last = '\0';
953 }
954
955 /* ------------------------------------------------------------------------- */
956
957 /*
958  * Wait until Busy bit is off, or timeout (in ms)
959  * Return last status
960  */
961 static uchar ide_wait(int dev, ulong t)
962 {
963         ulong delay = 10 * t;   /* poll every 100 us */
964         uchar c;
965
966         while ((c = ide_inb(dev, ATA_STATUS)) & ATA_STAT_BUSY) {
967                 udelay(100);
968                 if (delay-- == 0)
969                         break;
970         }
971         return (c);
972 }
973
974 /* ------------------------------------------------------------------------- */
975
976 #ifdef CONFIG_IDE_RESET
977 extern void ide_set_reset(int idereset);
978
979 static void ide_reset(void)
980 {
981         int i;
982
983         curr_device = -1;
984         for (i = 0; i < CONFIG_SYS_IDE_MAXBUS; ++i)
985                 ide_bus_ok[i] = 0;
986         for (i = 0; i < CONFIG_SYS_IDE_MAXDEVICE; ++i)
987                 ide_dev_desc[i].type = DEV_TYPE_UNKNOWN;
988
989         ide_set_reset(1);       /* assert reset */
990
991         /* the reset signal shall be asserted for et least 25 us */
992         udelay(25);
993
994         WATCHDOG_RESET();
995
996         /* de-assert RESET signal */
997         ide_set_reset(0);
998
999         /* wait 250 ms */
1000         for (i = 0; i < 250; ++i)
1001                 udelay(1000);
1002 }
1003
1004 #endif /* CONFIG_IDE_RESET */
1005
1006 /* ------------------------------------------------------------------------- */
1007
1008 #if defined(CONFIG_OF_IDE_FIXUP)
1009 int ide_device_present(int dev)
1010 {
1011         if (dev >= CONFIG_SYS_IDE_MAXBUS)
1012                 return 0;
1013         return (ide_dev_desc[dev].type == DEV_TYPE_UNKNOWN ? 0 : 1);
1014 }
1015 #endif
1016 /* ------------------------------------------------------------------------- */
1017
1018 #ifdef CONFIG_ATAPI
1019 /****************************************************************************
1020  * ATAPI Support
1021  */
1022
1023 #if defined(CONFIG_IDE_SWAP_IO)
1024 /* since ATAPI may use commands with not 4 bytes alligned length
1025  * we have our own transfer functions, 2 bytes alligned */
1026 __weak void ide_output_data_shorts(int dev, ushort *sect_buf, int shorts)
1027 {
1028         ushort *dbuf;
1029         volatile ushort *pbuf;
1030
1031         pbuf = (ushort *) (ATA_CURR_BASE(dev) + ATA_DATA_REG);
1032         dbuf = (ushort *) sect_buf;
1033
1034         debug("in output data shorts base for read is %lx\n",
1035               (unsigned long) pbuf);
1036
1037         while (shorts--) {
1038                 EIEIO;
1039                 *pbuf = *dbuf++;
1040         }
1041 }
1042
1043 __weak void ide_input_data_shorts(int dev, ushort *sect_buf, int shorts)
1044 {
1045         ushort *dbuf;
1046         volatile ushort *pbuf;
1047
1048         pbuf = (ushort *) (ATA_CURR_BASE(dev) + ATA_DATA_REG);
1049         dbuf = (ushort *) sect_buf;
1050
1051         debug("in input data shorts base for read is %lx\n",
1052               (unsigned long) pbuf);
1053
1054         while (shorts--) {
1055                 EIEIO;
1056                 *dbuf++ = *pbuf;
1057         }
1058 }
1059
1060 #else  /* ! CONFIG_IDE_SWAP_IO */
1061 __weak void ide_output_data_shorts(int dev, ushort *sect_buf, int shorts)
1062 {
1063         outsw(ATA_CURR_BASE(dev) + ATA_DATA_REG, sect_buf, shorts);
1064 }
1065
1066 __weak void ide_input_data_shorts(int dev, ushort *sect_buf, int shorts)
1067 {
1068         insw(ATA_CURR_BASE(dev) + ATA_DATA_REG, sect_buf, shorts);
1069 }
1070
1071 #endif /* CONFIG_IDE_SWAP_IO */
1072
1073 /*
1074  * Wait until (Status & mask) == res, or timeout (in ms)
1075  * Return last status
1076  * This is used since some ATAPI CD ROMs clears their Busy Bit first
1077  * and then they set their DRQ Bit
1078  */
1079 static uchar atapi_wait_mask(int dev, ulong t, uchar mask, uchar res)
1080 {
1081         ulong delay = 10 * t;   /* poll every 100 us */
1082         uchar c;
1083
1084         /* prevents to read the status before valid */
1085         c = ide_inb(dev, ATA_DEV_CTL);
1086
1087         while (((c = ide_inb(dev, ATA_STATUS)) & mask) != res) {
1088                 /* break if error occurs (doesn't make sense to wait more) */
1089                 if ((c & ATA_STAT_ERR) == ATA_STAT_ERR)
1090                         break;
1091                 udelay(100);
1092                 if (delay-- == 0)
1093                         break;
1094         }
1095         return (c);
1096 }
1097
1098 /*
1099  * issue an atapi command
1100  */
1101 unsigned char atapi_issue(int device, unsigned char *ccb, int ccblen,
1102                           unsigned char *buffer, int buflen)
1103 {
1104         unsigned char c, err, mask, res;
1105         int n;
1106
1107         ide_led(DEVICE_LED(device), 1); /* LED on       */
1108
1109         /* Select device
1110          */
1111         mask = ATA_STAT_BUSY | ATA_STAT_DRQ;
1112         res = 0;
1113         ide_outb(device, ATA_DEV_HD, ATA_LBA | ATA_DEVICE(device));
1114         c = atapi_wait_mask(device, ATAPI_TIME_OUT, mask, res);
1115         if ((c & mask) != res) {
1116                 printf("ATAPI_ISSUE: device %d not ready status %X\n", device,
1117                        c);
1118                 err = 0xFF;
1119                 goto AI_OUT;
1120         }
1121         /* write taskfile */
1122         ide_outb(device, ATA_ERROR_REG, 0);     /* no DMA, no overlaped */
1123         ide_outb(device, ATA_SECT_CNT, 0);
1124         ide_outb(device, ATA_SECT_NUM, 0);
1125         ide_outb(device, ATA_CYL_LOW, (unsigned char) (buflen & 0xFF));
1126         ide_outb(device, ATA_CYL_HIGH,
1127                  (unsigned char) ((buflen >> 8) & 0xFF));
1128         ide_outb(device, ATA_DEV_HD, ATA_LBA | ATA_DEVICE(device));
1129
1130         ide_outb(device, ATA_COMMAND, ATAPI_CMD_PACKET);
1131         udelay(50);
1132
1133         mask = ATA_STAT_DRQ | ATA_STAT_BUSY | ATA_STAT_ERR;
1134         res = ATA_STAT_DRQ;
1135         c = atapi_wait_mask(device, ATAPI_TIME_OUT, mask, res);
1136
1137         if ((c & mask) != res) {        /* DRQ must be 1, BSY 0 */
1138                 printf("ATAPI_ISSUE: Error (no IRQ) before sending ccb dev %d status 0x%02x\n",
1139                         device, c);
1140                 err = 0xFF;
1141                 goto AI_OUT;
1142         }
1143
1144         /* write command block */
1145         ide_output_data_shorts(device, (unsigned short *) ccb, ccblen / 2);
1146
1147         /* ATAPI Command written wait for completition */
1148         udelay(5000);           /* device must set bsy */
1149
1150         mask = ATA_STAT_DRQ | ATA_STAT_BUSY | ATA_STAT_ERR;
1151         /*
1152          * if no data wait for DRQ = 0 BSY = 0
1153          * if data wait for DRQ = 1 BSY = 0
1154          */
1155         res = 0;
1156         if (buflen)
1157                 res = ATA_STAT_DRQ;
1158         c = atapi_wait_mask(device, ATAPI_TIME_OUT, mask, res);
1159         if ((c & mask) != res) {
1160                 if (c & ATA_STAT_ERR) {
1161                         err = (ide_inb(device, ATA_ERROR_REG)) >> 4;
1162                         debug("atapi_issue 1 returned sense key %X status %02X\n",
1163                                 err, c);
1164                 } else {
1165                         printf("ATAPI_ISSUE: (no DRQ) after sending ccb (%x)  status 0x%02x\n",
1166                                 ccb[0], c);
1167                         err = 0xFF;
1168                 }
1169                 goto AI_OUT;
1170         }
1171         n = ide_inb(device, ATA_CYL_HIGH);
1172         n <<= 8;
1173         n += ide_inb(device, ATA_CYL_LOW);
1174         if (n > buflen) {
1175                 printf("ERROR, transfer bytes %d requested only %d\n", n,
1176                        buflen);
1177                 err = 0xff;
1178                 goto AI_OUT;
1179         }
1180         if ((n == 0) && (buflen < 0)) {
1181                 printf("ERROR, transfer bytes %d requested %d\n", n, buflen);
1182                 err = 0xff;
1183                 goto AI_OUT;
1184         }
1185         if (n != buflen) {
1186                 debug("WARNING, transfer bytes %d not equal with requested %d\n",
1187                         n, buflen);
1188         }
1189         if (n != 0) {           /* data transfer */
1190                 debug("ATAPI_ISSUE: %d Bytes to transfer\n", n);
1191                 /* we transfer shorts */
1192                 n >>= 1;
1193                 /* ok now decide if it is an in or output */
1194                 if ((ide_inb(device, ATA_SECT_CNT) & 0x02) == 0) {
1195                         debug("Write to device\n");
1196                         ide_output_data_shorts(device,
1197                                 (unsigned short *) buffer, n);
1198                 } else {
1199                         debug("Read from device @ %p shorts %d\n", buffer, n);
1200                         ide_input_data_shorts(device,
1201                                 (unsigned short *) buffer, n);
1202                 }
1203         }
1204         udelay(5000);           /* seems that some CD ROMs need this... */
1205         mask = ATA_STAT_BUSY | ATA_STAT_ERR;
1206         res = 0;
1207         c = atapi_wait_mask(device, ATAPI_TIME_OUT, mask, res);
1208         if ((c & ATA_STAT_ERR) == ATA_STAT_ERR) {
1209                 err = (ide_inb(device, ATA_ERROR_REG) >> 4);
1210                 debug("atapi_issue 2 returned sense key %X status %X\n", err,
1211                       c);
1212         } else {
1213                 err = 0;
1214         }
1215 AI_OUT:
1216         ide_led(DEVICE_LED(device), 0); /* LED off      */
1217         return (err);
1218 }
1219
1220 /*
1221  * sending the command to atapi_issue. If an status other than good
1222  * returns, an request_sense will be issued
1223  */
1224
1225 #define ATAPI_DRIVE_NOT_READY   100
1226 #define ATAPI_UNIT_ATTN         10
1227
1228 unsigned char atapi_issue_autoreq(int device,
1229                                   unsigned char *ccb,
1230                                   int ccblen,
1231                                   unsigned char *buffer, int buflen)
1232 {
1233         unsigned char sense_data[18], sense_ccb[12];
1234         unsigned char res, key, asc, ascq;
1235         int notready, unitattn;
1236
1237         unitattn = ATAPI_UNIT_ATTN;
1238         notready = ATAPI_DRIVE_NOT_READY;
1239
1240 retry:
1241         res = atapi_issue(device, ccb, ccblen, buffer, buflen);
1242         if (res == 0)
1243                 return 0;       /* Ok */
1244
1245         if (res == 0xFF)
1246                 return 0xFF;    /* error */
1247
1248         debug("(auto_req)atapi_issue returned sense key %X\n", res);
1249
1250         memset(sense_ccb, 0, sizeof(sense_ccb));
1251         memset(sense_data, 0, sizeof(sense_data));
1252         sense_ccb[0] = ATAPI_CMD_REQ_SENSE;
1253         sense_ccb[4] = 18;      /* allocation Length */
1254
1255         res = atapi_issue(device, sense_ccb, 12, sense_data, 18);
1256         key = (sense_data[2] & 0xF);
1257         asc = (sense_data[12]);
1258         ascq = (sense_data[13]);
1259
1260         debug("ATAPI_CMD_REQ_SENSE returned %x\n", res);
1261         debug(" Sense page: %02X key %02X ASC %02X ASCQ %02X\n",
1262               sense_data[0], key, asc, ascq);
1263
1264         if ((key == 0))
1265                 return 0;       /* ok device ready */
1266
1267         if ((key == 6) || (asc == 0x29) || (asc == 0x28)) { /* Unit Attention */
1268                 if (unitattn-- > 0) {
1269                         udelay(200 * 1000);
1270                         goto retry;
1271                 }
1272                 printf("Unit Attention, tried %d\n", ATAPI_UNIT_ATTN);
1273                 goto error;
1274         }
1275         if ((asc == 0x4) && (ascq == 0x1)) {
1276                 /* not ready, but will be ready soon */
1277                 if (notready-- > 0) {
1278                         udelay(200 * 1000);
1279                         goto retry;
1280                 }
1281                 printf("Drive not ready, tried %d times\n",
1282                        ATAPI_DRIVE_NOT_READY);
1283                 goto error;
1284         }
1285         if (asc == 0x3a) {
1286                 debug("Media not present\n");
1287                 goto error;
1288         }
1289
1290         printf("ERROR: Unknown Sense key %02X ASC %02X ASCQ %02X\n", key, asc,
1291                ascq);
1292 error:
1293         debug("ERROR Sense key %02X ASC %02X ASCQ %02X\n", key, asc, ascq);
1294         return (0xFF);
1295 }
1296
1297
1298 static void atapi_inquiry(block_dev_desc_t *dev_desc)
1299 {
1300         unsigned char ccb[12];  /* Command descriptor block */
1301         unsigned char iobuf[64];        /* temp buf */
1302         unsigned char c;
1303         int device;
1304
1305         device = dev_desc->dev;
1306         dev_desc->type = DEV_TYPE_UNKNOWN;      /* not yet valid */
1307         dev_desc->block_read = atapi_read;
1308
1309         memset(ccb, 0, sizeof(ccb));
1310         memset(iobuf, 0, sizeof(iobuf));
1311
1312         ccb[0] = ATAPI_CMD_INQUIRY;
1313         ccb[4] = 40;            /* allocation Legnth */
1314         c = atapi_issue_autoreq(device, ccb, 12, (unsigned char *) iobuf, 40);
1315
1316         debug("ATAPI_CMD_INQUIRY returned %x\n", c);
1317         if (c != 0)
1318                 return;
1319
1320         /* copy device ident strings */
1321         ident_cpy((unsigned char *) dev_desc->vendor, &iobuf[8], 8);
1322         ident_cpy((unsigned char *) dev_desc->product, &iobuf[16], 16);
1323         ident_cpy((unsigned char *) dev_desc->revision, &iobuf[32], 5);
1324
1325         dev_desc->lun = 0;
1326         dev_desc->lba = 0;
1327         dev_desc->blksz = 0;
1328         dev_desc->log2blksz = LOG2_INVALID(typeof(dev_desc->log2blksz));
1329         dev_desc->type = iobuf[0] & 0x1f;
1330
1331         if ((iobuf[1] & 0x80) == 0x80)
1332                 dev_desc->removable = 1;
1333         else
1334                 dev_desc->removable = 0;
1335
1336         memset(ccb, 0, sizeof(ccb));
1337         memset(iobuf, 0, sizeof(iobuf));
1338         ccb[0] = ATAPI_CMD_START_STOP;
1339         ccb[4] = 0x03;          /* start */
1340
1341         c = atapi_issue_autoreq(device, ccb, 12, (unsigned char *) iobuf, 0);
1342
1343         debug("ATAPI_CMD_START_STOP returned %x\n", c);
1344         if (c != 0)
1345                 return;
1346
1347         memset(ccb, 0, sizeof(ccb));
1348         memset(iobuf, 0, sizeof(iobuf));
1349         c = atapi_issue_autoreq(device, ccb, 12, (unsigned char *) iobuf, 0);
1350
1351         debug("ATAPI_CMD_UNIT_TEST_READY returned %x\n", c);
1352         if (c != 0)
1353                 return;
1354
1355         memset(ccb, 0, sizeof(ccb));
1356         memset(iobuf, 0, sizeof(iobuf));
1357         ccb[0] = ATAPI_CMD_READ_CAP;
1358         c = atapi_issue_autoreq(device, ccb, 12, (unsigned char *) iobuf, 8);
1359         debug("ATAPI_CMD_READ_CAP returned %x\n", c);
1360         if (c != 0)
1361                 return;
1362
1363         debug("Read Cap: LBA %02X%02X%02X%02X blksize %02X%02X%02X%02X\n",
1364               iobuf[0], iobuf[1], iobuf[2], iobuf[3],
1365               iobuf[4], iobuf[5], iobuf[6], iobuf[7]);
1366
1367         dev_desc->lba = ((unsigned long) iobuf[0] << 24) +
1368                 ((unsigned long) iobuf[1] << 16) +
1369                 ((unsigned long) iobuf[2] << 8) + ((unsigned long) iobuf[3]);
1370         dev_desc->blksz = ((unsigned long) iobuf[4] << 24) +
1371                 ((unsigned long) iobuf[5] << 16) +
1372                 ((unsigned long) iobuf[6] << 8) + ((unsigned long) iobuf[7]);
1373         dev_desc->log2blksz = LOG2(dev_desc->blksz);
1374 #ifdef CONFIG_LBA48
1375         /* ATAPI devices cannot use 48bit addressing (ATA/ATAPI v7) */
1376         dev_desc->lba48 = 0;
1377 #endif
1378         return;
1379 }
1380
1381
1382 /*
1383  * atapi_read:
1384  * we transfer only one block per command, since the multiple DRQ per
1385  * command is not yet implemented
1386  */
1387 #define ATAPI_READ_MAX_BYTES    2048    /* we read max 2kbytes */
1388 #define ATAPI_READ_BLOCK_SIZE   2048    /* assuming CD part */
1389 #define ATAPI_READ_MAX_BLOCK    (ATAPI_READ_MAX_BYTES/ATAPI_READ_BLOCK_SIZE)
1390
1391 ulong atapi_read(int device, ulong blknr, lbaint_t blkcnt, void *buffer)
1392 {
1393         ulong n = 0;
1394         unsigned char ccb[12];  /* Command descriptor block */
1395         ulong cnt;
1396
1397         debug("atapi_read dev %d start %lX, blocks " LBAF " buffer at %lX\n",
1398               device, blknr, blkcnt, (ulong) buffer);
1399
1400         do {
1401                 if (blkcnt > ATAPI_READ_MAX_BLOCK)
1402                         cnt = ATAPI_READ_MAX_BLOCK;
1403                 else
1404                         cnt = blkcnt;
1405
1406                 ccb[0] = ATAPI_CMD_READ_12;
1407                 ccb[1] = 0;     /* reserved */
1408                 ccb[2] = (unsigned char) (blknr >> 24) & 0xFF;  /* MSB Block */
1409                 ccb[3] = (unsigned char) (blknr >> 16) & 0xFF;  /*  */
1410                 ccb[4] = (unsigned char) (blknr >> 8) & 0xFF;
1411                 ccb[5] = (unsigned char) blknr & 0xFF;  /* LSB Block */
1412                 ccb[6] = (unsigned char) (cnt >> 24) & 0xFF; /* MSB Block cnt */
1413                 ccb[7] = (unsigned char) (cnt >> 16) & 0xFF;
1414                 ccb[8] = (unsigned char) (cnt >> 8) & 0xFF;
1415                 ccb[9] = (unsigned char) cnt & 0xFF;    /* LSB Block */
1416                 ccb[10] = 0;    /* reserved */
1417                 ccb[11] = 0;    /* reserved */
1418
1419                 if (atapi_issue_autoreq(device, ccb, 12,
1420                                         (unsigned char *) buffer,
1421                                         cnt * ATAPI_READ_BLOCK_SIZE)
1422                     == 0xFF) {
1423                         return (n);
1424                 }
1425                 n += cnt;
1426                 blkcnt -= cnt;
1427                 blknr += cnt;
1428                 buffer += (cnt * ATAPI_READ_BLOCK_SIZE);
1429         } while (blkcnt > 0);
1430         return (n);
1431 }
1432
1433 /* ------------------------------------------------------------------------- */
1434
1435 #endif /* CONFIG_ATAPI */
1436
1437 U_BOOT_CMD(ide, 5, 1, do_ide,
1438            "IDE sub-system",
1439            "reset - reset IDE controller\n"
1440            "ide info  - show available IDE devices\n"
1441            "ide device [dev] - show or set current device\n"
1442            "ide part [dev] - print partition table of one or all IDE devices\n"
1443            "ide read  addr blk# cnt\n"
1444            "ide write addr blk# cnt - read/write `cnt'"
1445            " blocks starting at block `blk#'\n"
1446            "    to/from memory address `addr'");
1447
1448 U_BOOT_CMD(diskboot, 3, 1, do_diskboot,
1449            "boot from IDE device", "loadAddr dev:part");