aboutsummaryrefslogtreecommitdiff
path: root/common
diff options
context:
space:
mode:
authorwdenk <wdenk>2002-11-18 00:14:45 +0000
committerwdenk <wdenk>2002-11-18 00:14:45 +0000
commit2262cfeef91458b01a1bfe3812ccbbfdf8b82807 (patch)
tree3657d48c8ce9089fc96682848859d035a1e8f115 /common
parent1d0350ed0b1b0f63e3fb5db6b19397b84a2ea1c7 (diff)
downloadu-boot-linaro-stable-2262cfeef91458b01a1bfe3812ccbbfdf8b82807.tar.gz
* Patch by Daniel Engström, 13 Nov 2002:LABEL_2002_11_18_0115
Add support for i386 architecture and AMD SC520 board * Patch by Pierre Aubert, 12 Nov 2002: Add support for DOS filesystem and booting from DOS floppy disk
Diffstat (limited to 'common')
-rw-r--r--common/Makefile2
-rw-r--r--common/cmd_bootm.c37
-rw-r--r--common/cmd_fdc.c93
-rw-r--r--common/cmd_fdos.c145
-rw-r--r--common/cmd_ide.c174
-rw-r--r--common/command.c3
6 files changed, 382 insertions, 72 deletions
diff --git a/common/Makefile b/common/Makefile
index 3f4ff0190..67387ef64 100644
--- a/common/Makefile
+++ b/common/Makefile
@@ -31,7 +31,7 @@ COBJS = main.o altera.o bedbug.o \
cmd_autoscript.o cmd_bedbug.o cmd_boot.o \
cmd_bootm.o cmd_cache.o cmd_console.o cmd_date.o \
cmd_dcr.o cmd_diag.o cmd_doc.o cmd_dtt.o \
- cmd_eeprom.o cmd_elf.o cmd_fdc.o cmd_flash.o \
+ cmd_eeprom.o cmd_elf.o cmd_fdc.o cmd_fdos.o cmd_flash.o \
cmd_fpga.o cmd_i2c.o cmd_ide.o cmd_immap.o \
cmd_jffs2.o cmd_log.o cmd_mem.o cmd_mii.o cmd_misc.o \
cmd_net.o cmd_nvedit.o env_common.o \
diff --git a/common/cmd_bootm.c b/common/cmd_bootm.c
index 70ca999c0..a0587d019 100644
--- a/common/cmd_bootm.c
+++ b/common/cmd_bootm.c
@@ -70,6 +70,10 @@ static int image_info (unsigned long addr);
#endif
static void print_type (image_header_t *hdr);
+#ifdef __I386__
+image_header_t *fake_header(image_header_t *hdr, void *ptr, int size);
+#endif
+
/*
* Continue booting an OS image; caller already has:
* - copied image header to global variable `header'
@@ -84,7 +88,7 @@ typedef void boot_os_Fcn (cmd_tbl_t *cmdtp, int flag,
ulong *len_ptr, /* multi-file image length table */
int verify); /* getenv("verify")[0] != 'n' */
-#ifndef CONFIG_ARM
+#ifdef CONFIG_PPC
static boot_os_Fcn do_bootm_linux;
#else
extern boot_os_Fcn do_bootm_linux;
@@ -128,9 +132,21 @@ int do_bootm (cmd_tbl_t *cmdtp, int flag, int argc, char *argv[])
memmove (&header, (char *)addr, sizeof(image_header_t));
if (ntohl(hdr->ih_magic) != IH_MAGIC) {
+#ifdef __I386__ /* correct image format not implemented yet - fake it */
+ if (fake_header(hdr, (void*)addr, -1) != NULL) {
+ /* to compensate for the addition below */
+ addr -= sizeof(image_header_t);
+ /* turnof verify,
+ * fake_header() does not fake the data crc
+ */
+ verify = 0;
+ } else
+#endif /* __I386__ */
+ {
printf ("Bad Magic Number\n");
SHOW_BOOT_PROGRESS (-1);
return 1;
+ }
}
SHOW_BOOT_PROGRESS (2);
@@ -148,7 +164,7 @@ int do_bootm (cmd_tbl_t *cmdtp, int flag, int argc, char *argv[])
SHOW_BOOT_PROGRESS (3);
/* for multi-file images we need the data part, too */
- print_image_hdr ((image_header_t *)addr);
+ print_image_hdr (hdr);
data = addr + sizeof(image_header_t);
len = ntohl(hdr->ih_size);
@@ -166,8 +182,17 @@ int do_bootm (cmd_tbl_t *cmdtp, int flag, int argc, char *argv[])
len_ptr = (ulong *)data;
- if (hdr->ih_arch != IH_CPU_PPC && hdr->ih_arch != IH_CPU_ARM) {
- printf ("Unsupported Architecture\n");
+#if defined(__PPC__)
+ if (hdr->ih_arch != IH_CPU_PPC)
+#elif defined(__ARM__)
+ if (hdr->ih_arch != IH_CPU_ARM)
+#elif defined(__I386__)
+ if (hdr->ih_arch != IH_CPU_I386)
+#else
+# error Unknown CPU type
+#endif
+ {
+ printf ("Unsupported Architecture 0x%x\n", hdr->ih_arch);
SHOW_BOOT_PROGRESS (-4);
return 1;
}
@@ -201,7 +226,7 @@ int do_bootm (cmd_tbl_t *cmdtp, int flag, int argc, char *argv[])
switch (hdr->ih_comp) {
case IH_COMP_NONE:
- if(hdr->ih_load == addr) {
+ if(ntohl(hdr->ih_load) == addr) {
printf (" XIP %s ... ", name);
} else {
#if defined(CONFIG_HW_WATCHDOG) || defined(CONFIG_WATCHDOG)
@@ -294,7 +319,7 @@ int do_bootm (cmd_tbl_t *cmdtp, int flag, int argc, char *argv[])
return 1;
}
-#ifndef CONFIG_ARM
+#ifdef CONFIG_PPC
static void
do_bootm_linux (cmd_tbl_t *cmdtp, int flag,
int argc, char *argv[],
diff --git a/common/cmd_fdc.c b/common/cmd_fdc.c
index 8e6b7350c..e45b3361c 100644
--- a/common/cmd_fdc.c
+++ b/common/cmd_fdc.c
@@ -51,7 +51,7 @@
#include <rtc.h>
#endif
-#if (CONFIG_COMMANDS & CFG_CMD_FDC)
+#if ((CONFIG_COMMANDS & CFG_CMD_FDC) || (CONFIG_COMMANDS & CFG_CMD_FDOS))
typedef struct {
@@ -192,7 +192,10 @@ static FDC_COMMAND_STRUCT cmd; /* global command struct */
/* reads a Register of the FDC */
unsigned char read_fdc_reg(unsigned int addr)
{
- volatile unsigned char *val = (volatile unsigned char *)(CFG_ISA_IO_BASE_ADDRESS + (addr * CFG_ISA_IO_STRIDE) + CFG_ISA_IO_OFFSET);
+ volatile unsigned char *val =
+ (volatile unsigned char *)(CFG_ISA_IO_BASE_ADDRESS +
+ (addr * CFG_ISA_IO_STRIDE) +
+ CFG_ISA_IO_OFFSET);
return val [0];
}
@@ -200,7 +203,10 @@ unsigned char read_fdc_reg(unsigned int addr)
/* writes a Register of the FDC */
void write_fdc_reg(unsigned int addr, unsigned char val)
{
- volatile unsigned char *tmp = (volatile unsigned char *)(CFG_ISA_IO_BASE_ADDRESS + (addr * CFG_ISA_IO_STRIDE) + CFG_ISA_IO_OFFSET);
+ volatile unsigned char *tmp =
+ (volatile unsigned char *)(CFG_ISA_IO_BASE_ADDRESS +
+ (addr * CFG_ISA_IO_STRIDE) +
+ CFG_ISA_IO_OFFSET);
tmp[0]=val;
}
@@ -279,7 +285,8 @@ int fdc_issue_cmd(FDC_COMMAND_STRUCT *pCMD,FD_GEO_STRUCT *pFG)
head = sect / pFG->sect; /* head nr */
sect = sect % pFG->sect; /* remaining blocks */
sect++; /* sectors are 1 based */
- PRINTF("Cmd 0x%02x Track %ld, Head %ld, Sector %ld, Drive %d (blnr %ld)\n",pCMD->cmd[0],track,head,sect,pCMD->drive,pCMD->blnr);
+ PRINTF("Cmd 0x%02x Track %ld, Head %ld, Sector %ld, Drive %d (blnr %ld)\n",
+ pCMD->cmd[0],track,head,sect,pCMD->drive,pCMD->blnr);
if(head|=0) { /* max heads = 2 */
pCMD->cmd[DRIVE]=pCMD->drive | 0x04; /* head 1 */
@@ -588,7 +595,7 @@ int fdc_check_drive(FDC_COMMAND_STRUCT *pCMD, FD_GEO_STRUCT *pFG)
* setup the fdc according the datasheet
* assuming in PS2 Mode
*/
-int fdc_setup(FDC_COMMAND_STRUCT *pCMD, FD_GEO_STRUCT *pFG)
+int fdc_setup(int drive, FDC_COMMAND_STRUCT *pCMD, FD_GEO_STRUCT *pFG)
{
int i;
@@ -601,7 +608,7 @@ int fdc_setup(FDC_COMMAND_STRUCT *pCMD, FD_GEO_STRUCT *pFG)
for(i=0; i<255; i++) /* then we wait some time */
udelay(500);
/* then, we clear the reset in the DOR */
- pCMD->drive=CFG_FDC_DRIVE_NUMBER;
+ pCMD->drive=drive;
select_fdc_drive(pCMD);
/* initialize the CCR */
write_fdc_reg(FDC_CCR,pFG->rate);
@@ -621,9 +628,8 @@ int fdc_setup(FDC_COMMAND_STRUCT *pCMD, FD_GEO_STRUCT *pFG)
PRINTF("Sense Interrupt for drive %d failed\n",i);
}
}
- /* assuming drive 0 for rest of configuration
- * issue the configure command */
- pCMD->drive=CFG_FDC_DRIVE_NUMBER;
+ /* issue the configure command */
+ pCMD->drive=drive;
select_fdc_drive(pCMD);
pCMD->cmd[COMMAND]=FDC_CMD_CONFIGURE;
if(fdc_issue_cmd(pCMD,pFG)==FALSE) {
@@ -644,7 +650,74 @@ int fdc_setup(FDC_COMMAND_STRUCT *pCMD, FD_GEO_STRUCT *pFG)
/* write_fdc_reg(FDC_DOR,0x04); */
return TRUE;
}
+#endif /* ((CONFIG_COMMANDS & CFG_CMD_FDC)||(CONFIG_COMMANDS & CFG_CMD_FDOS))*/
+
+#if (CONFIG_COMMANDS & CFG_CMD_FDOS)
+
+/* Low level functions for the Floppy-DOS layer */
+/**************************************************************************
+* int fdc_fdos_init
+* initialize the FDC layer
+*
+*/
+int fdc_fdos_init (int drive)
+{
+ FD_GEO_STRUCT *pFG = (FD_GEO_STRUCT *)floppy_type;
+ FDC_COMMAND_STRUCT *pCMD = &cmd;
+
+ /* setup FDC and scan for drives */
+ if(fdc_setup(drive,pCMD,pFG)==FALSE) {
+ printf("\n** Error in setup FDC **\n");
+ return FALSE;
+ }
+ if(fdc_check_drive(pCMD,pFG)==FALSE) {
+ printf("\n** Error in check_drives **\n");
+ return FALSE;
+ }
+ if((pCMD->flags&(1<<drive))==0) {
+ /* drive not available */
+ printf("\n** Drive %d not available **\n",drive);
+ return FALSE;
+ }
+ if((pCMD->flags&(0x10<<drive))==0) {
+ /* no disk inserted */
+ printf("\n** No disk inserted in drive %d **\n",drive);
+ return FALSE;
+ }
+ /* ok, we have a valid source */
+ pCMD->drive=drive;
+
+ /* read first block */
+ pCMD->blnr=0;
+ return TRUE;
+}
+/**************************************************************************
+* int fdc_fdos_seek
+* parameter is a block number
+*/
+int fdc_fdos_seek (int where)
+{
+ FD_GEO_STRUCT *pFG = (FD_GEO_STRUCT *)floppy_type;
+ FDC_COMMAND_STRUCT *pCMD = &cmd;
+
+ pCMD -> blnr = where ;
+ return (fdc_seek (pCMD, pFG));
+}
+/**************************************************************************
+* int fdc_fdos_read
+* the length is in block number
+*/
+int fdc_fdos_read (void *buffer, int len)
+{
+ FD_GEO_STRUCT *pFG = (FD_GEO_STRUCT *)floppy_type;
+ FDC_COMMAND_STRUCT *pCMD = &cmd;
+
+ return (fdc_read_data (buffer, len, pCMD, pFG));
+}
+#endif /* (CONFIG_COMMANDS & CFG_CMD_FDOS) */
+
+#if (CONFIG_COMMANDS & CFG_CMD_FDC)
/****************************************************************************
* main routine do_fdcboot
*/
@@ -677,7 +750,7 @@ int do_fdcboot (cmd_tbl_t *cmdtp, int flag, int argc, char *argv[])
return 1;
}
/* setup FDC and scan for drives */
- if(fdc_setup(pCMD,pFG)==FALSE) {
+ if(fdc_setup(boot_drive,pCMD,pFG)==FALSE) {
printf("\n** Error in setup FDC **\n");
return 1;
}
diff --git a/common/cmd_fdos.c b/common/cmd_fdos.c
new file mode 100644
index 000000000..763f4181a
--- /dev/null
+++ b/common/cmd_fdos.c
@@ -0,0 +1,145 @@
+/*
+ * (C) Copyright 2002
+ * Stäubli Faverges - <www.staubli.com>
+ * Pierre AUBERT p.aubert@staubli.com
+ *
+ * See file CREDITS for list of people who contributed to this
+ * project.
+ *
+ * This program is free software; you can redistribute it and/or
+ * modify it under the terms of the GNU General Public License as
+ * published by the Free Software Foundation; either version 2 of
+ * the License, or (at your option) any later version.
+ *
+ * This program is distributed in the hope that it will be useful,
+ * but WITHOUT ANY WARRANTY; without even the implied warranty of
+ * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the
+ * GNU General Public License for more details.
+ *
+ * You should have received a copy of the GNU General Public License
+ * along with this program; if not, write to the Free Software
+ * Foundation, Inc., 59 Temple Place, Suite 330, Boston,
+ * MA 02111-1307 USA
+ */
+
+/*
+ * Dos floppy support
+ */
+
+#include <common.h>
+#include <config.h>
+#include <command.h>
+#include <fdc.h>
+
+#if (CONFIG_COMMANDS & CFG_CMD_FDOS)
+
+/*-----------------------------------------------------------------------------
+ * do_fdosboot --
+ *-----------------------------------------------------------------------------
+ */
+int do_fdosboot(cmd_tbl_t *cmdtp, int flag, int argc, char *argv[])
+{
+ char *name;
+ char *ep;
+ int size;
+ int rcode = 0;
+ char buf [10];
+ int drive = CFG_FDC_DRIVE_NUMBER;
+
+ /* pre-set load_addr */
+ if ((ep = getenv("loadaddr")) != NULL) {
+ load_addr = simple_strtoul(ep, NULL, 16);
+ }
+
+ /* pre-set Boot file name */
+ if ((name = getenv("bootfile")) == NULL) {
+ name = "pImage";
+ }
+
+ switch (argc) {
+ case 1:
+ break;
+ case 2:
+ /* only one arg - accept two forms:
+ * just load address, or just boot file name.
+ * The latter form must be written "filename" here.
+ */
+ if (argv[1][0] == '"') { /* just boot filename */
+ name = argv [1];
+ } else { /* load address */
+ load_addr = simple_strtoul(argv[1], NULL, 16);
+ }
+ break;
+ case 3:
+ load_addr = simple_strtoul(argv[1], NULL, 16);
+ name = argv [2];
+ break;
+ default:
+ printf ("Usage:\n%s\n", cmdtp->usage);
+ break;
+ }
+
+ /* Init physical layer */
+ if (!fdc_fdos_init (drive)) {
+ return (-1);
+ }
+
+ /* Open file */
+ if (dos_open (name) < 0) {
+ printf ("Unable to open %s\n", name);
+ return 1;
+ }
+ if ((size = dos_read (load_addr)) < 0) {
+ printf ("boot error\n");
+ return 1;
+ }
+ flush_cache (load_addr, size);
+
+ sprintf(buf, "%x", size);
+ setenv("filesize", buf);
+
+ printf("Floppy DOS load complete: %d bytes loaded to 0x%lx\n",
+ size, load_addr);
+
+ /* Check if we should attempt an auto-start */
+ if (((ep = getenv("autostart")) != NULL) && (strcmp(ep,"yes") == 0)) {
+ char *local_args[2];
+ extern int do_bootm (cmd_tbl_t *, int, int, char *[]);
+ local_args[0] = argv[0];
+ local_args[1] = NULL;
+ printf ("Automatic boot of image at addr 0x%08lX ...\n", load_addr);
+ rcode = do_bootm (cmdtp, 0, 1, local_args);
+ }
+ return rcode;
+}
+
+/*-----------------------------------------------------------------------------
+ * do_fdosls --
+ *-----------------------------------------------------------------------------
+ */
+int do_fdosls(cmd_tbl_t *cmdtp, int flag, int argc, char *argv[])
+{
+ char *path = "";
+ int drive = CFG_FDC_DRIVE_NUMBER;
+
+ switch (argc) {
+ case 1:
+ break;
+ case 2:
+ path = argv [1];
+ break;
+ }
+
+ /* Init physical layer */
+ if (!fdc_fdos_init (drive)) {
+ return (-1);
+ }
+ /* Open directory */
+ if (dos_open (path) < 0) {
+ printf ("Unable to open %s\n", path);
+ return 1;
+ }
+ return (dos_dir ());
+}
+
+#endif
diff --git a/common/cmd_ide.c b/common/cmd_ide.c
index 9cbfe1bb0..e514cf71e 100644
--- a/common/cmd_ide.c
+++ b/common/cmd_ide.c
@@ -44,6 +44,9 @@
#ifdef CONFIG_STATUS_LED
# include <status_led.h>
#endif
+#ifdef __I386__
+#include <asm/io.h>
+#endif
#ifdef CONFIG_SHOW_BOOT_PROGRESS
# include <status_led.h>
@@ -114,7 +117,9 @@ ulong ide_bus_offset[CFG_IDE_MAXBUS] = {
#endif
};
+#ifdef __PPC__
#define ATA_CURR_BASE(dev) (CFG_ATA_BASE_ADDR+ide_bus_offset[IDE_BUS(dev)])
+#endif
static int ide_bus_ok[CFG_IDE_MAXBUS];
@@ -142,9 +147,11 @@ static uchar ide_wait (int dev, ulong t);
#define IDE_SPIN_UP_TIME_OUT 5000 /* 5 sec spin-up timeout */
-static void __inline__ outb(int dev, int port, unsigned char val);
-static unsigned char __inline__ inb(int dev, int port);
+static void __inline__ ide_outb(int dev, int port, unsigned char val);
+static unsigned char __inline__ ide_inb(int dev, int port);
+#ifdef __PPC__
static void input_swap_data(int dev, ulong *sect_buf, int words);
+#endif
static void input_data(int dev, ulong *sect_buf, int words);
static void output_data(int dev, ulong *sect_buf, int words);
static void ident_cpy (unsigned char *dest, unsigned char *src, unsigned int len);
@@ -517,14 +524,14 @@ void ide_init (void)
/* Select device
*/
udelay (100000); /* 100 ms */
- outb (dev, ATA_DEV_HD, ATA_LBA | ATA_DEVICE(dev));
+ ide_outb (dev, ATA_DEV_HD, ATA_LBA | ATA_DEVICE(dev));
udelay (100000); /* 100 ms */
i = 0;
do {
udelay (10000); /* 10 ms */
- c = inb (dev, ATA_STATUS);
+ c = ide_inb (dev, ATA_STATUS);
i++;
if (i > (ATA_RESET_TIME * 100)) {
puts ("** Timeout **\n");
@@ -679,30 +686,48 @@ set_pcmcia_timing (int pmode)
/* ------------------------------------------------------------------------- */
+#ifdef __PPC__
static void __inline__
-outb(int dev, int port, unsigned char val)
+ide_outb(int dev, int port, unsigned char val)
{
/* Ensure I/O operations complete */
__asm__ volatile("eieio");
*((uchar *)(ATA_CURR_BASE(dev)+port)) = val;
#if 0
- printf ("OUTB: 0x%08lx <== 0x%02x\n", ATA_CURR_BASE(dev)+port, val);
+ printf ("ide_outb: 0x%08lx <== 0x%02x\n", ATA_CURR_BASE(dev)+port, val);
#endif
}
+#else /* ! __PPC__ */
+static void __inline__
+ide_outb(int dev, int port, unsigned char val)
+{
+ outb(val, port);
+}
+#endif /* __PPC__ */
+
+#ifdef __PPC__
static unsigned char __inline__
-inb(int dev, int port)
+ide_inb(int dev, int port)
{
uchar val;
/* Ensure I/O operations complete */
__asm__ volatile("eieio");
val = *((uchar *)(ATA_CURR_BASE(dev)+port));
#if 0
- printf ("INB: 0x%08lx ==> 0x%02x\n", ATA_CURR_BASE(dev)+port, val);
+ printf ("ide_inb: 0x%08lx ==> 0x%02x\n", ATA_CURR_BASE(dev)+port, val);
#endif
return (val);
}
+#else /* ! __PPC__ */
+static unsigned char __inline__
+ide_inb(int dev, int port)
+{
+ return inb(port);
+}
+#endif /* __PPC__ */
+#ifdef __PPC__
__inline__ unsigned ld_le16(const volatile unsigned short *addr)
{
unsigned val;
@@ -722,7 +747,14 @@ input_swap_data(int dev, ulong *sect_buf, int words)
*dbuf++ = ld_le16(pbuf);
}
}
+#else /* ! __PPC__ */
+#define input_swap_data(x,y,z) input_data(x,y,z)
+#endif /* __PPC__ */
+
+
+
+#ifdef __PPC__
static void
output_data(int dev, ulong *sect_buf, int words)
{
@@ -738,7 +770,15 @@ output_data(int dev, ulong *sect_buf, int words)
*pbuf = *dbuf++;
}
}
+#else /* ! __PPC__ */
+static void
+output_data(int dev, ulong *sect_buf, int words)
+{
+ outsw(ATA_DATA_REG, sect_buf, words<<1);
+}
+#endif /* __PPC__ */
+#ifdef __PPC__
static void
input_data(int dev, ulong *sect_buf, int words)
{
@@ -754,6 +794,14 @@ input_data(int dev, ulong *sect_buf, int words)
*dbuf++ = *pbuf;
}
}
+#else /* ! __PPC__ */
+static void
+input_data(int dev, ulong *sect_buf, int words)
+{
+ insw(ATA_DATA_REG, sect_buf, words << 1);
+}
+
+#endif /* __PPC__ */
/* -------------------------------------------------------------------------
*/
@@ -773,19 +821,19 @@ static void ide_ident (block_dev_desc_t *dev_desc)
ide_led (DEVICE_LED(device), 1); /* LED on */
/* Select device
*/
- outb (device, ATA_DEV_HD, ATA_LBA | ATA_DEVICE(device));
+ ide_outb (device, ATA_DEV_HD, ATA_LBA | ATA_DEVICE(device));
dev_desc->if_type=IF_TYPE_IDE;
#ifdef CONFIG_ATAPI
/* check signature */
- if ((inb(device,ATA_SECT_CNT)==0x01) &&
- (inb(device,ATA_SECT_NUM)==0x01) &&
- (inb(device,ATA_CYL_LOW)==0x14) &&
- (inb(device,ATA_CYL_HIGH)==0xEB)) {
+ if ((ide_inb(device,ATA_SECT_CNT) == 0x01) &&
+ (ide_inb(device,ATA_SECT_NUM) == 0x01) &&
+ (ide_inb(device,ATA_CYL_LOW) == 0x14) &&
+ (ide_inb(device,ATA_CYL_HIGH) == 0xEB)) {
/* ATAPI Signature found */
dev_desc->if_type=IF_TYPE_ATAPI;
/* Start Ident Command
*/
- outb (device, ATA_COMMAND, ATAPI_CMD_IDENT);
+ ide_outb (device, ATA_COMMAND, ATAPI_CMD_IDENT);
/*
* Wait for completion - ATAPI devices need more time
* to become ready
@@ -797,7 +845,7 @@ static void ide_ident (block_dev_desc_t *dev_desc)
{
/* Start Ident Command
*/
- outb (device, ATA_COMMAND, ATA_CMD_IDENT);
+ ide_outb (device, ATA_COMMAND, ATA_CMD_IDENT);
/* Wait for completion
*/
@@ -867,15 +915,15 @@ static void ide_ident (block_dev_desc_t *dev_desc)
#if 0 /* only used to test the powersaving mode,
* if enabled, the drive goes after 5 sec
* in standby mode */
- outb (device, ATA_DEV_HD, ATA_LBA | ATA_DEVICE(device));
+ ide_outb (device, ATA_DEV_HD, ATA_LBA | ATA_DEVICE(device));
c = ide_wait (device, IDE_TIME_OUT);
- outb (device, ATA_SECT_CNT, 1);
- outb (device, ATA_LBA_LOW, 0);
- outb (device, ATA_LBA_MID, 0);
- outb (device, ATA_LBA_HIGH, 0);
- outb (device, ATA_DEV_HD, ATA_LBA |
+ ide_outb (device, ATA_SECT_CNT, 1);
+ ide_outb (device, ATA_LBA_LOW, 0);
+ ide_outb (device, ATA_LBA_MID, 0);
+ ide_outb (device, ATA_LBA_HIGH, 0);
+ ide_outb (device, ATA_DEV_HD, ATA_LBA |
ATA_DEVICE(device));
- outb (device, ATA_COMMAND, 0xe3);
+ ide_outb (device, ATA_COMMAND, 0xe3);
udelay (50);
c = ide_wait (device, IDE_TIME_OUT); /* can't take over 500 ms */
#endif
@@ -897,7 +945,7 @@ ulong ide_read (int device, ulong blknr, ulong blkcnt, ulong *buffer)
/* Select device
*/
- outb (device, ATA_DEV_HD, ATA_LBA | ATA_DEVICE(device));
+ ide_outb (device, ATA_DEV_HD, ATA_LBA | ATA_DEVICE(device));
c = ide_wait (device, IDE_TIME_OUT);
if (c & ATA_STAT_BUSY) {
@@ -907,7 +955,7 @@ ulong ide_read (int device, ulong blknr, ulong blkcnt, ulong *buffer)
/* first check if the drive is in Powersaving mode, if yes,
* increase the timeout value */
- outb (device, ATA_COMMAND, ATA_CMD_CHK_PWR);
+ ide_outb (device, ATA_COMMAND, ATA_CMD_CHK_PWR);
udelay (50);
c = ide_wait (device, IDE_TIME_OUT); /* can't take over 500 ms */
@@ -919,7 +967,7 @@ ulong ide_read (int device, ulong blknr, ulong blkcnt, ulong *buffer)
if ((c & ATA_STAT_ERR) == ATA_STAT_ERR) {
printf ("No Powersaving mode %X\n", c);
} else {
- c = inb(device,ATA_SECT_CNT);
+ c = ide_inb(device,ATA_SECT_CNT);
PRINTF("Powersaving %02X\n",c);
if(c==0)
pwrsave=1;
@@ -935,14 +983,14 @@ ulong ide_read (int device, ulong blknr, ulong blkcnt, ulong *buffer)
break;
}
- outb (device, ATA_SECT_CNT, 1);
- outb (device, ATA_LBA_LOW, (blknr >> 0) & 0xFF);
- outb (device, ATA_LBA_MID, (blknr >> 8) & 0xFF);
- outb (device, ATA_LBA_HIGH, (blknr >> 16) & 0xFF);
- outb (device, ATA_DEV_HD, ATA_LBA |
+ ide_outb (device, ATA_SECT_CNT, 1);
+ ide_outb (device, ATA_LBA_LOW, (blknr >> 0) & 0xFF);
+ ide_outb (device, ATA_LBA_MID, (blknr >> 8) & 0xFF);
+ ide_outb (device, ATA_LBA_HIGH, (blknr >> 16) & 0xFF);
+ ide_outb (device, ATA_DEV_HD, ATA_LBA |
ATA_DEVICE(device) |
((blknr >> 24) & 0xF) );
- outb (device, ATA_COMMAND, ATA_CMD_READ);
+ ide_outb (device, ATA_COMMAND, ATA_CMD_READ);
udelay (50);
@@ -960,7 +1008,7 @@ ulong ide_read (int device, ulong blknr, ulong blkcnt, ulong *buffer)
}
input_data (device, buffer, ATA_SECTORWORDS);
- (void) inb (device, ATA_STATUS); /* clear IRQ */
+ (void) ide_inb (device, ATA_STATUS); /* clear IRQ */
++n;
++blknr;
@@ -983,7 +1031,7 @@ ulong ide_write (int device, ulong blknr, ulong blkcnt, ulong *buffer)
/* Select device
*/
- outb (device, ATA_DEV_HD, ATA_LBA | ATA_DEVICE(device));
+ ide_outb (device, ATA_DEV_HD, ATA_LBA | ATA_DEVICE(device));
while (blkcnt-- > 0) {
@@ -994,14 +1042,14 @@ ulong ide_write (int device, ulong blknr, ulong blkcnt, ulong *buffer)
goto WR_OUT;
}
- outb (device, ATA_SECT_CNT, 1);
- outb (device, ATA_LBA_LOW, (blknr >> 0) & 0xFF);
- outb (device, ATA_LBA_MID, (blknr >> 8) & 0xFF);
- outb (device, ATA_LBA_HIGH, (blknr >> 16) & 0xFF);
- outb (device, ATA_DEV_HD, ATA_LBA |
+ ide_outb (device, ATA_SECT_CNT, 1);
+ ide_outb (device, ATA_LBA_LOW, (blknr >> 0) & 0xFF);
+ ide_outb (device, ATA_LBA_MID, (blknr >> 8) & 0xFF);
+ ide_outb (device, ATA_LBA_HIGH, (blknr >> 16) & 0xFF);
+ ide_outb (device, ATA_DEV_HD, ATA_LBA |
ATA_DEVICE(device) |
((blknr >> 24) & 0xF) );
- outb (device, ATA_COMMAND, ATA_CMD_WRITE);
+ ide_outb (device, ATA_COMMAND, ATA_CMD_WRITE);
udelay (50);
@@ -1014,7 +1062,7 @@ ulong ide_write (int device, ulong blknr, ulong blkcnt, ulong *buffer)
}
output_data (device, buffer, ATA_SECTORWORDS);
- c = inb (device, ATA_STATUS); /* clear IRQ */
+ c = ide_inb (device, ATA_STATUS); /* clear IRQ */
++n;
++blknr;
buffer += ATA_SECTORWORDS;
@@ -1063,7 +1111,7 @@ static uchar ide_wait (int dev, ulong t)
ulong delay = 10 * t; /* poll every 100 us */
uchar c;
- while ((c = inb(dev, ATA_STATUS)) & ATA_STAT_BUSY) {
+ while ((c = ide_inb(dev, ATA_STATUS)) & ATA_STAT_BUSY) {
udelay (100);
if (delay-- == 0) {
break;
@@ -1188,6 +1236,7 @@ static void ide_led (uchar led, uchar status)
#define AT_PRINTF(fmt,args...)
#endif
+#ifdef __PPC__
/* since ATAPI may use commands with not 4 bytes alligned length
* we have our own transfer functions, 2 bytes alligned */
static void
@@ -1218,6 +1267,22 @@ input_data_shorts(int dev, ushort *sect_buf, int shorts)
}
}
+#else /* ! __PPC__ */
+static void
+output_data_shorts(int dev, ushort *sect_buf, int shorts)
+{
+ outsw(ATA_DATA_REG, sect_buf, shorts);
+}
+
+
+static void
+input_data_shorts(int dev, ushort *sect_buf, int shorts)
+{
+ insw(ATA_DATA_REG, sect_buf, shorts);
+}
+
+#endif /* __PPC__ */
+
/*
* Wait until (Status & mask) == res, or timeout (in ms)
* Return last status
@@ -1229,9 +1294,8 @@ static uchar atapi_wait_mask (int dev, ulong t,uchar mask, uchar res)
ulong delay = 10 * t; /* poll every 100 us */
uchar c;
- c = inb(dev,ATA_DEV_CTL); /* prevents to read the status before valid */
- while (((c = inb(dev, ATA_STATUS)) & mask)
- != res) {
+ c = ide_inb(dev,ATA_DEV_CTL); /* prevents to read the status before valid */
+ while (((c = ide_inb(dev, ATA_STATUS)) & mask) != res) {
/* break if error occurs (doesn't make sense to wait more) */
if((c & ATA_STAT_ERR)==ATA_STAT_ERR)
break;
@@ -1256,7 +1320,7 @@ unsigned char atapi_issue(int device,unsigned char* ccb,int ccblen, unsigned cha
*/
mask = ATA_STAT_BUSY|ATA_STAT_DRQ;
res = 0;
- outb (device, ATA_DEV_HD, ATA_LBA | ATA_DEVICE(device));
+ ide_outb (device, ATA_DEV_HD, ATA_LBA | ATA_DEVICE(device));
c = atapi_wait_mask(device,ATAPI_TIME_OUT,mask,res);
if ((c & mask) != res) {
printf ("ATAPI_ISSUE: device %d not ready status %X\n", device,c);
@@ -1264,12 +1328,12 @@ unsigned char atapi_issue(int device,unsigned char* ccb,int ccblen, unsigned cha
goto AI_OUT;
}
/* write taskfile */
- outb (device, ATA_ERROR_REG, 0); /* no DMA, no overlaped */
- outb (device, ATA_CYL_LOW, (unsigned char)(buflen & 0xFF));
- outb (device, ATA_CYL_HIGH, (unsigned char)((buflen<<8) & 0xFF));
- outb (device, ATA_DEV_HD, ATA_LBA | ATA_DEVICE(device));
+ ide_outb (device, ATA_ERROR_REG, 0); /* no DMA, no overlaped */
+ ide_outb (device, ATA_CYL_LOW, (unsigned char)(buflen & 0xFF));
+ ide_outb (device, ATA_CYL_HIGH, (unsigned char)((buflen<<8) & 0xFF));
+ ide_outb (device, ATA_DEV_HD, ATA_LBA | ATA_DEVICE(device));
- outb (device, ATA_COMMAND, ATAPI_CMD_PACKET);
+ ide_outb (device, ATA_COMMAND, ATAPI_CMD_PACKET);
udelay (50);
mask = ATA_STAT_DRQ|ATA_STAT_BUSY|ATA_STAT_ERR;
@@ -1295,7 +1359,7 @@ unsigned char atapi_issue(int device,unsigned char* ccb,int ccblen, unsigned cha
c = atapi_wait_mask(device,ATAPI_TIME_OUT,mask,res);
if ((c & mask) != res ) {
if (c & ATA_STAT_ERR) {
- err=(inb(device,ATA_ERROR_REG))>>4;
+ err=(ide_inb(device,ATA_ERROR_REG))>>4;
AT_PRINTF("atapi_issue 1 returned sense key %X status %02X\n",err,c);
} else {
printf ("ATTAPI_ISSUE: (no DRQ) after sending ccb (%x) status 0x%02x\n", ccb[0],c);
@@ -1303,9 +1367,9 @@ unsigned char atapi_issue(int device,unsigned char* ccb,int ccblen, unsigned cha
}
goto AI_OUT;
}
- n=inb(device, ATA_CYL_HIGH);
+ n=ide_inb(device, ATA_CYL_HIGH);
n<<=8;
- n+=inb(device, ATA_CYL_LOW);
+ n+=ide_inb(device, ATA_CYL_LOW);
if(n>buflen) {
printf("ERROR, transfer bytes %d requested only %d\n",n,buflen);
err=0xff;
@@ -1324,7 +1388,7 @@ unsigned char atapi_issue(int device,unsigned char* ccb,int ccblen, unsigned cha
/* we transfer shorts */
n>>=1;
/* ok now decide if it is an in or output */
- if ((inb(device, ATA_SECT_CNT)&0x02)==0) {
+ if ((ide_inb(device, ATA_SECT_CNT)&0x02)==0) {
AT_PRINTF("Write to device\n");
output_data_shorts(device,(unsigned short *)buffer,n);
} else {
@@ -1337,7 +1401,7 @@ unsigned char atapi_issue(int device,unsigned char* ccb,int ccblen, unsigned cha
res=0;
c = atapi_wait_mask(device,ATAPI_TIME_OUT,mask,res);
if ((c & ATA_STAT_ERR) == ATA_STAT_ERR) {
- err=(inb(device,ATA_ERROR_REG) >> 4);
+ err=(ide_inb(device,ATA_ERROR_REG) >> 4);
AT_PRINTF("atapi_issue 2 returned sense key %X status %X\n",err,c);
} else {
err = 0;
diff --git a/common/command.c b/common/command.c
index f70cad8cb..cab68abf8 100644
--- a/common/command.c
+++ b/common/command.c
@@ -70,6 +70,7 @@
#include <cmd_vfd.h> /* load a bitmap to the VFDs on TRAB */
#include <cmd_log.h>
+#include <cmd_fdos.h>
/*
* HELP command
@@ -253,6 +254,8 @@ cmd_tbl_t cmd_tbl[] = {
CMD_TBL_FCCINFO
CMD_TBL_FLERASE
CMD_TBL_FDC
+ CMD_TBL_FDOS_BOOT
+ CMD_TBL_FDOS_LS
CMD_TBL_FLINFO
CMD_TBL_FPGA
CMD_TBL_JFFS2_FSINFO