U-Boot
Threads by month
- ----- 2025 -----
- May
- April
- March
- February
- January
- ----- 2024 -----
- December
- November
- October
- September
- August
- July
- June
- May
- April
- March
- February
- January
- ----- 2023 -----
- December
- November
- October
- September
- August
- July
- June
- May
- April
- March
- February
- January
- ----- 2022 -----
- December
- November
- October
- September
- August
- July
- June
- May
- April
- March
- February
- January
- ----- 2021 -----
- December
- November
- October
- September
- August
- July
- June
- May
- April
- March
- February
- January
- ----- 2020 -----
- December
- November
- October
- September
- August
- July
- June
- May
- April
- March
- February
- January
- ----- 2019 -----
- December
- November
- October
- September
- August
- July
- June
- May
- April
- March
- February
- January
- ----- 2018 -----
- December
- November
- October
- September
- August
- July
- June
- May
- April
- March
- February
- January
- ----- 2017 -----
- December
- November
- October
- September
- August
- July
- June
- May
- April
- March
- February
- January
- ----- 2016 -----
- December
- November
- October
- September
- August
- July
- June
- May
- April
- March
- February
- January
- ----- 2015 -----
- December
- November
- October
- September
- August
- July
- June
- May
- April
- March
- February
- January
- ----- 2014 -----
- December
- November
- October
- September
- August
- July
- June
- May
- April
- March
- February
- January
- ----- 2013 -----
- December
- November
- October
- September
- August
- July
- June
- May
- April
- March
- February
- January
- ----- 2012 -----
- December
- November
- October
- September
- August
- July
- June
- May
- April
- March
- February
- January
- ----- 2011 -----
- December
- November
- October
- September
- August
- July
- June
- May
- April
- March
- February
- January
- ----- 2010 -----
- December
- November
- October
- September
- August
- July
- June
- May
- April
- March
- February
- January
- ----- 2009 -----
- December
- November
- October
- September
- August
- July
- June
- May
- April
- March
- February
- January
- ----- 2008 -----
- December
- November
- October
- September
- August
- July
- June
- May
- April
- March
- February
- January
- ----- 2007 -----
- December
- November
- October
- September
- August
- July
- June
- May
- April
- March
- February
- January
- ----- 2006 -----
- December
- November
- October
- September
- August
- July
- June
- May
- April
- March
- February
- January
- ----- 2005 -----
- December
- November
- October
- September
- August
- July
- June
- May
- April
- March
- February
- January
- ----- 2004 -----
- December
- November
- October
- September
- August
- July
- June
- May
- April
- March
- February
- January
- ----- 2003 -----
- December
- November
- October
- September
- August
- July
- June
- May
- April
- March
- February
- January
- ----- 2002 -----
- December
- November
- October
- September
- August
- July
- June
- May
- April
- March
- February
- January
- ----- 2001 -----
- December
- November
- October
- September
- August
- July
- June
- May
- April
- March
- February
- January
- ----- 2000 -----
- December
- November
- October
- September
- August
- July
- June
- May
- April
October 2010
- 237 participants
- 699 discussions

[U-Boot] [PATCH] ppc4xx: t3corp: Add support for the Xilinx DS617 flash chip
by Stefan Roese 17 Dec '10
by Stefan Roese 17 Dec '10
17 Dec '10
The t3corp board has an Xilinx DS617 flash chip connected to the
onboard FPGA. This patch adds support for these chips. Board
specific flash accessor functions are needed, since the chips
can only be read correctly in 16bit mode.
Additionally the FPGA chip-selects are configured for device-paced
transfers (ready is enabled).
Signed-off-by: Stefan Roese <sr(a)denx.de>
---
board/t3corp/t3corp.c | 38 ++++++++++++++++++++++++++++++++++++++
include/configs/t3corp.h | 18 ++++++++++++------
2 files changed, 50 insertions(+), 6 deletions(-)
diff --git a/board/t3corp/t3corp.c b/board/t3corp/t3corp.c
index 04d6a2e..f2853e4 100644
--- a/board/t3corp/t3corp.c
+++ b/board/t3corp/t3corp.c
@@ -23,6 +23,7 @@
#include <libfdt.h>
#include <fdt_support.h>
#include <i2c.h>
+#include <mtd/cfi_flash.h>
#include <asm/processor.h>
#include <asm/io.h>
#include <asm/mmu.h>
@@ -191,3 +192,40 @@ struct sdram_timing *ddr_scan_option(struct sdram_timing *default_val)
{
return board_scan_options;
}
+
+/*
+ * Accessor functions replacing the "weak" functions in
+ * drivers/mtd/cfi_flash.c
+ *
+ * The NOR flash devices "behind" the FPGA's (Xilinx DS617)
+ * can only be read correctly in 16bit mode. We need to emulate
+ * 8bit and 32bit reads here in the board specific code.
+ */
+u8 flash_read8(void *addr)
+{
+ u16 val = __raw_readw((void *)((u32)addr & ~1));
+
+ if ((u32)addr & 1)
+ return val;
+
+ return val >> 8;
+}
+
+u32 flash_read32(void *addr)
+{
+ return (__raw_readw(addr) << 16) | __raw_readw((void *)((u32)addr + 2));
+}
+
+void flash_cmd_reset(flash_info_t *info)
+{
+ /*
+ * FLASH at address CONFIG_SYS_FLASH_BASE is a Spansion chip and
+ * needs the Spansion type reset commands. The other flash chip
+ * is located behind a FPGA (Xilinx DS617) and needs the Intel type
+ * reset command.
+ */
+ if (info->start[0] == CONFIG_SYS_FLASH_BASE)
+ flash_write_cmd(info, 0, 0, AMD_CMD_RESET);
+ else
+ flash_write_cmd(info, 0, 0, FLASH_CMD_RESET);
+}
diff --git a/include/configs/t3corp.h b/include/configs/t3corp.h
index d00e64e..a938b6f 100644
--- a/include/configs/t3corp.h
+++ b/include/configs/t3corp.h
@@ -121,11 +121,16 @@
*/
#define CONFIG_SYS_FLASH_CFI /* The flash is CFI compatible */
#define CONFIG_FLASH_CFI_DRIVER /* Use common CFI driver */
-#define CONFIG_SYS_FLASH_CFI_AMD_RESET 1 /* Use AMD reset cmd */
+#define CONFIG_SYS_FLASH_CFI_WIDTH FLASH_CFI_16BIT
+#define CONFIG_CFI_FLASH_USE_WEAK_ACCESSORS
#define CONFIG_SYS_CFI_FLASH_STATUS_POLL /* use status poll method */
+#define CONFIG_SYS_FLASH_PROTECTION /* use hardware flash protection */
-#define CONFIG_SYS_FLASH_BANKS_LIST { CONFIG_SYS_FLASH_BASE }
-#define CONFIG_SYS_MAX_FLASH_BANKS 1 /* max num of memory banks */
+#define CONFIG_SYS_FLASH_BANKS_LIST { CONFIG_SYS_FLASH_BASE, \
+ (CONFIG_SYS_FPGA1_BASE + 0x01000000) }
+#define CONFIG_SYS_CFI_FLASH_CONFIG_REGS { 0xffff, /* don't set */ \
+ 0xbddf } /* set async read mode */
+#define CONFIG_SYS_MAX_FLASH_BANKS 2 /* max num of memory banks */
#define CONFIG_SYS_MAX_FLASH_SECT 512 /* max num of sectors p. chip*/
#define CONFIG_SYS_FLASH_ERASE_TOUT 120000 /* Timeout for Flash Erase/ms*/
@@ -356,6 +361,7 @@
"ramdisk_addr=fc200000\0" \
"pciconfighost=1\0" \
"pcie_mode=RP:RP\0" \
+ "unlock=yes\0" \
""
/*
@@ -424,7 +430,7 @@
EBC_BXAP_WBN_ENCODE(0) | \
EBC_BXAP_WBF_ENCODE(0) | \
EBC_BXAP_TH_ENCODE(1) | \
- EBC_BXAP_RE_DISABLED | \
+ EBC_BXAP_RE_ENABLED | \
EBC_BXAP_SOR_DELAYED | \
EBC_BXAP_BEM_RW | \
EBC_BXAP_PEN_DISABLED)
@@ -441,7 +447,7 @@
EBC_BXAP_WBN_ENCODE(0) | \
EBC_BXAP_WBF_ENCODE(0) | \
EBC_BXAP_TH_ENCODE(1) | \
- EBC_BXAP_RE_DISABLED | \
+ EBC_BXAP_RE_ENABLED | \
EBC_BXAP_SOR_DELAYED | \
EBC_BXAP_BEM_RW | \
EBC_BXAP_PEN_DISABLED)
@@ -458,7 +464,7 @@
EBC_BXAP_WBN_ENCODE(0) | \
EBC_BXAP_WBF_ENCODE(0) | \
EBC_BXAP_TH_ENCODE(1) | \
- EBC_BXAP_RE_DISABLED | \
+ EBC_BXAP_RE_ENABLED | \
EBC_BXAP_SOR_DELAYED | \
EBC_BXAP_BEM_RW | \
EBC_BXAP_PEN_DISABLED)
--
1.7.3.2
1
1
From: Hans Eklund <hans(a)rubico.se>
Signed-off-by: Hans Eklund <hans(a)rubico.se>
Signed-off-by: Cliff Cai <cliff.cai(a)analog.com>
Signed-off-by: Mike Frysinger <vapier(a)gentoo.org>
---
i'd like this considered for merging even though this is using the legacy
framework. there have been attempts to rewrite the driver on top of the
new framework, but all attempts thus far have failed. this driver however
is continued to be used by many people/boards in production setups. thus
i'd like this merged until we have a new working driver to replace it.
drivers/mmc/Makefile | 3 +
drivers/mmc/spi_mmc.c | 1111 +++++++++++++++++++++++++++++++++++++++++++++++++
2 files changed, 1114 insertions(+), 0 deletions(-)
create mode 100644 drivers/mmc/spi_mmc.c
diff --git a/drivers/mmc/Makefile b/drivers/mmc/Makefile
index 2ead634..5d8f05b 100644
--- a/drivers/mmc/Makefile
+++ b/drivers/mmc/Makefile
@@ -23,6 +23,9 @@
include $(TOPDIR)/config.mk
+# stick it up here to avoid conflicts
+COBJS-$(CONFIG_SPI_MMC) += spi_mmc.o
+
LIB := $(obj)libmmc.a
COBJS-$(CONFIG_ATMEL_MCI) += atmel_mci.o
diff --git a/drivers/mmc/spi_mmc.c b/drivers/mmc/spi_mmc.c
new file mode 100644
index 0000000..c106fcc
--- /dev/null
+++ b/drivers/mmc/spi_mmc.c
@@ -0,0 +1,1111 @@
+/*
+ * SPI-MMC/SD Protocol.
+ *
+ * Copyright (C) 2005-2007, Rubico AB (www.rubico.se)
+ *
+ * Developed as a part the CDT project C4 (www.cdt.ltu.se).
+ *
+ * Robert Selberg, <robert(a)rubico.se>
+ * Hans Eklund, <hans(a)rubico.se>
+ *
+ * Licensed under the GPL-2 or later.
+ */
+
+/*
+ * TODO: Correct Multiple block read and write functions. Didnt have time
+ * to make them all failsafe. Will be done soon.
+ */
+
+#include <common.h>
+#include <malloc.h>
+#include <spi.h>
+#include <mmc.h>
+
+enum {
+ MMC_INIT_TIMEOUT = 30000,
+ MMC_COMMAND_TIMEOUT = 5000,
+ MMC_PROG_TIMEOUT = 500000,
+ BUSY_BLOCK_LEN = 1,
+ BUSY_BLOCK_LEN_SHORT = 16,
+ MMC_SECTOR_SIZE = 512,
+ SD_PRE_CMD_ZEROS = 4,
+ SD_CLK_CNTRL = 2,
+ LOG_LEN = 16,
+ WRB_LEN = 256,
+
+/* Card command classes */
+
+/* Internal error codes */
+ ERR_SPI_TIMEOUT = 0xF1,
+ ERR_MMC_TIMEOUT = 0xF2,
+ ERR_MMC_PROG_TIMEOUT = 0xF3,
+ ERR_UNKNOWN_TOK = 0xF4,
+
+/* return values from functions */
+ RVAL_OK = 0,
+ RVAL_ERROR = 1,
+ RVAL_CRITICAL = 2,
+
+/* Format R1(b) response tokens (1 byte long) */
+ BUSY_TOKEN = 0x00,
+ R1_OK = 0x00,
+ R1_IDLE_STATE = 0x01,
+ R1_ERASE_STATE = 0x02,
+ R1_ILLEGAL_CMD = 0x04,
+ R1_COM_CRC_ERROR = 0x08,
+ R1_ERASE_SEQ_ERROR = 0x10,
+ R1_ADDRESS_ERROR = 0x20,
+ R1_PARAMETER_ERROR = 0x40,
+
+/* Format R2 response tokens (2 bytes long, first is same as R1 responses) */
+ R2_OK = 0x00,
+ R2_CARD_LOCKED = 0x01,
+ R2_WP_ERASE_SKIP = 0x02,
+ R2_LOCK_UNLOCK_CMD_FAIL = 0x02,
+ R2_ERROR = 0x04,
+ R2_CC_ERROR = 0x08,
+ R2_CARD_ECC_FAILED = 0x10,
+ R2_WP_VIOLATION = 0x20,
+ R2_ERASE_PARAM = 0x40,
+ R2_OUT_OF_RANGE = 0x80,
+ R2_CSD_OVERWRITE = 0x80,
+/* TODO: Format R3 response tokens */
+
+/* Data response tokens */
+ DR_MASK = 0x0F,
+ DR_ACCEPTED = 0x05,
+ DR_CRC_ERROR = 0x0B,
+ DR_WRITE_ERROR = 0x0D,
+
+/*
+ Data tokens (4 bytes to (N+3) bytes long), N is data block len
+ format of the Start Data Block Token
+*/
+ SBT_S_BLOCK_READ = 0xFE,
+ SBT_M_BLOCK_READ = 0xFE,
+ SBT_S_BLOCK_WRITE = 0xFE,
+ SBT_M_BLOCK_WRITE = 0xFC,
+ STT_M_BLOCK_WRITE = 0xFD,
+
+/* Data error tokens (1 byte long) */
+ DE_ERROR = 0x01,
+ DE_CC_ERROR = 0x02,
+ DE_CARD_ECC_FAILED = 0x04,
+ DE_OUT_OF_RANGE = 0x08,
+ DE_CARD_IS_LOCKED = 0x10,
+
+/* MMC/SD SPI mode commands */
+ GO_IDLE_STATE = 0,
+ SEND_OP_COND = 1,
+ SEND_CSD = 9,
+ SEND_CID = 10,
+ STOP_TRANSMISSION = 12,
+ SEND_STATUS = 13,
+ SET_BLOCKLEN = 16,
+ READ_SINGLE_BLOCK = 17,
+ READ_MULTIPLE_BLOCK = 18,
+ WRITE_BLOCK = 24,
+ WRITE_MULTIPLE_BLOCK = 25,
+ SD_SEND_OP_COND = 41,
+ APP_CMD = 55,
+};
+
+/* minimal local versions of CSD/CID structures,
+ somewhat ripped from linux MMC layer, the entire
+ CSD struct is larger and is not completley parsed
+*/
+struct cid_str {
+ unsigned int manfid;
+ char prod_name[8];
+ unsigned int serial;
+ unsigned short oemid;
+ unsigned short year;
+ unsigned char hwrev;
+ unsigned char fwrev;
+ unsigned char month;
+};
+
+struct csd_str { /* __csd field name__*/
+ unsigned char mmca_vsn; /* CSD_STRUCTURE */
+ unsigned short cmdclass; /* CCC */
+ unsigned short tacc_clks; /* TAAC */
+ unsigned int tacc_ns; /* NSAC */
+ unsigned int max_dtr; /* TRANS_SPEED */
+ unsigned int read_blkbits; /* READ_BL_LEN */
+ unsigned int capacity;
+};
+
+/*
+ mmc_spi_dev - Implementation need to configure this struct
+ with callback functions to read and write data that the
+ mmc_spi function can use for its operations.
+ NOTE: Every function defined here expect exclusive access to
+ any MMC/SD card it is operating on. Functions should be considered
+ critical sections. Also note that the read/write callbacks may a mutex
+ if they can be executed by another context.
+*/
+struct mmc_spi_dev {
+ int (*read)(unsigned char *buf, unsigned int nbytes, void *priv_data);
+ int (*write)(unsigned char *buf, unsigned int nbytes, void *priv_data);
+ void (*doassert)(void);
+ void (*deassert)(void);
+ void *priv_data; /* incomming pointer to private data for callbacks */
+ unsigned char raw_csd[18]; /* raw csd data to use with external parser */
+ unsigned char raw_cid[18]; /* raw cid data to use with external parser */
+ struct cid_str cid; /* internal represent. of cid data */
+ struct csd_str csd; /* internal represent. of csd data */
+ int sd; /* true if SD card found */
+ int log_len;
+ unsigned int est_write_lat; /* [bytes] */
+ unsigned short force_cs_high; /* true if write/read callbacks should ask for CS high */
+ unsigned int errors; /* total amount of errors recorded since card insertion */
+ unsigned char cmd_log[LOG_LEN];
+ unsigned short error_log[LOG_LEN];
+ unsigned short status_log[LOG_LEN]; /* Status is not checked anymore since some cards will cry */
+};
+
+
+static unsigned char mmc_cmd[6] = {0x40, 0x00, 0x00, 0x00, 0x00, 0x95};
+static unsigned char Null_Word[10] = {0xFF, 0xFF, 0xFF, 0xFF, 0xFF, 0xFF, 0xFF,
+ 0xFF, 0xFF, 0xFF};
+static unsigned char latest_cmd;
+
+static int init_mode = 1;
+
+
+#if 0
+/**********************************************************************\
+*
+* MMC CSD/CID related, could be somewhat trimmed and cleaned
+*
+\**********************************************************************/
+static unsigned char getbit(void *ptr, unsigned int n)
+{
+ unsigned int byte_nr;
+ unsigned int bit_nr;
+
+ byte_nr = n/8;
+ bit_nr = n % 8;
+
+ return (unsigned char)(((unsigned char *)ptr)[byte_nr] >> bit_nr) & 1;
+}
+
+static unsigned int getvalue(void *ptr, unsigned int n, unsigned int len)
+{
+ unsigned int value = 0;
+ int i = 0;
+
+ for (i = 0; i < len; i++)
+ value += ((unsigned int)getbit(ptr, n+i)) << i;
+ return value;
+}
+#endif
+
+static unsigned char mmc_wait_response(struct mmc_spi_dev *pdev, unsigned int timeout)
+{
+ unsigned char card_resp = 0xFF;
+ unsigned int n = 0;
+ /* reset time and set to timeout ms */
+ while (1) {
+
+ if (pdev->read(&card_resp, 1, pdev->priv_data) < 0) {
+ debug("error: mmc_wait_response read error\n");
+ return ERR_SPI_TIMEOUT;
+ }
+ if (card_resp != 0xFF)
+ return card_resp;
+ /*
+ NOTE: "timeout" in seconds may not be a good idea after all
+ (by doing pdev->elapsed_time() )
+ wait for a specific amount of polls for now.
+ */
+ if ((n++ >= timeout)) {
+ debug("hey! timed out after %d since %d bytes was maximum(latest_cmd=%d)\n", n,
+ timeout, latest_cmd);
+ return ERR_MMC_TIMEOUT;
+ }
+ }
+}
+
+static short mmc_spi_read_status(struct mmc_spi_dev *pdev)
+{
+ unsigned char b1 = 0;
+ unsigned char b2 = 0;
+ unsigned short r2 = 0xffff;
+ static unsigned char status_cmd[6] = {0x4D, 0x00, 0x00, 0x00, 0x00, 0x95};
+
+ pdev->doassert();
+
+ if (pdev->sd) {
+ if (pdev->write(Null_Word, SD_PRE_CMD_ZEROS, pdev->priv_data) < 0) {
+ debug("sending SD_PRE_CMD_ZEROS failed\n");
+ pdev->deassert();
+ return ERR_SPI_TIMEOUT;
+ }
+ }
+ if (pdev->write(status_cmd, 6, pdev->priv_data) < 0) {
+ debug("sending of SEND_STATUS command failed\n");
+ pdev->deassert();
+ return ERR_SPI_TIMEOUT;
+ }
+ b1 = mmc_wait_response(pdev, MMC_COMMAND_TIMEOUT);
+ b2 = mmc_wait_response(pdev, MMC_COMMAND_TIMEOUT);
+
+ if (b1 == ERR_MMC_TIMEOUT || b2 == ERR_MMC_TIMEOUT) {
+ debug("No status received !\n");
+ pdev->deassert();
+ return ERR_MMC_TIMEOUT;
+ }
+
+ r2 = b2 + (b1 << 8);
+
+ if (r2)
+ debug("STATUS r2: 0x%04x\n", r2);
+ pdev->deassert();
+
+ return r2;
+
+ /* TODO: Implement in a finer way */
+ switch (b1) {
+ case R1_OK:
+ break;
+ case R1_IDLE_STATE:
+ printf("R1_IDLE_STATE\n");
+ break;
+ case R1_ERASE_STATE:
+ printf("R1_ERASE_STATE\n");
+ break;
+ case R1_ILLEGAL_CMD:
+ printf("R1_ILLEGAL_COMMAND\n");
+ break;
+ case R1_COM_CRC_ERROR:
+ printf("R1_COM_CRC_ERROR\n");
+ break;
+ case R1_ERASE_SEQ_ERROR:
+ printf("R1_ERASE_SEQ_ERROR\n");
+ break;
+ case R1_ADDRESS_ERROR:
+ printf("R1_ADDRESS_ERROR\n");
+ break;
+ case R1_PARAMETER_ERROR:
+ printf("R1_PARAMETER_ERROR\n");
+ break;
+ case 0xFF:
+ printf("b1: STATUS RESPONSE TIMEOUT\n");
+ break;
+ default:
+ printf("b1: INVALID STATUS RESPONSE(0x%02x)\n", b1);
+ break;
+ }
+
+ switch (b2) {
+ case R2_OK:
+ break;
+ case R2_CARD_LOCKED:
+ printf("R2_CARD_LOCKED\n");
+ break;
+ case R2_WP_ERASE_SKIP:
+ printf("R2_WP_ERASE_SKIP/Unlock command failed\n");
+ break;
+ case R2_ERROR:
+ printf("R2_ERROR\n");
+ break;
+ case R2_CC_ERROR:
+ printf("R2_CC_ERROR\n");
+ break;
+ case R2_CARD_ECC_FAILED:
+ printf("R2_CARD_ECC_FAILED\n");
+ break;
+ case R2_WP_VIOLATION:
+ printf("R2_WP_VIOLATION\n");
+ break;
+ case R2_ERASE_PARAM:
+ printf("R2_ERASE_PARAM\n");
+ break;
+ case R2_OUT_OF_RANGE:
+ printf("R2_OUT_OF_RANGE, CSD_Overwrite\n");
+ break;
+ case 0xFF:
+ printf("b2: STATUS RESPONSE TIMEOUT\n");
+ break;
+ default:
+ printf("b2: INVALID STATUS RESPONSE(0x%02x)\n", b2);
+ break;
+ }
+
+ return r2;
+}
+
+#if 0
+static void mmc_spi_fill_card_struct(struct mmc_spi_dev *pdev)
+{
+ unsigned short c_size_mult = 0;
+ unsigned short c_size = 0;
+ unsigned char *raw_csd;
+ unsigned char *raw_cid;
+
+ /* local, shorter names, just to keep lines below shorter */
+ raw_csd = pdev->raw_csd;
+ raw_cid = pdev->raw_cid;
+ pdev->csd.mmca_vsn = (raw_csd[0] & 0x3c) >> 2;
+ pdev->csd.cmdclass = (((__u16)raw_csd[4]) << 4) | ((raw_csd[5] & 0xf0) >> 4);
+ pdev->csd.tacc_clks = raw_csd[1];
+ pdev->csd.tacc_ns = raw_csd[2];
+ pdev->csd.max_dtr = raw_csd[3];
+ pdev->csd.read_blkbits = raw_csd[5] & 0x0f;
+ /* for calculating capacity(in blocks) */
+ c_size = ((((__u16)raw_csd[6]) & 0x03) << 10) | (((__u16)raw_csd[7]) << 2) |
+ (((__u16)raw_csd[8]) & 0xc0) >> 6;
+ c_size_mult = ((raw_csd[9] & 0x03) << 1) | ((raw_csd[10] & 0x80) >> 7);
+ pdev->csd.capacity = (c_size+1) * (1 << (c_size_mult + 2));
+ pdev->cid.manfid = getvalue(raw_cid, 127-127, 8);
+ memcpy(pdev->cid.prod_name, raw_cid+3, 7);
+ pdev->cid.serial = getvalue(raw_cid, 127-47, 32);
+ pdev->cid.oemid = getvalue(raw_cid, 127-119, 16);
+ pdev->cid.year = 1997 + (getvalue(raw_cid, 127-15, 8) & 0x0F);
+ pdev->cid.hwrev = (getvalue(raw_cid, 127-55, 8) & 0xF0) >> 4;
+ pdev->cid.fwrev = getvalue(raw_cid, 127-55, 8) & 0x0F;
+ pdev->cid.month = (getvalue(raw_cid, 127-15, 8) & 0xF0) >> 4;
+}
+#endif
+
+static short mmc_spi_dummy_clocks(struct mmc_spi_dev *pdev, unsigned short nbytes)
+{
+ int i;
+
+ pdev->force_cs_high = 1;
+ for (i = 0; i < nbytes; i++) {
+ if (pdev->write(Null_Word, 1, pdev->priv_data) < 0) {
+ pdev->force_cs_high = 0;
+ return 1;
+ }
+ }
+ pdev->force_cs_high = 0;
+
+ return 0;
+}
+
+static short send_cmd_and_wait(struct mmc_spi_dev *pdev,
+ unsigned char command,
+ unsigned int argument,
+ unsigned short cmd_resp,
+ unsigned int timeout)
+{
+ unsigned short resp = 0xff;
+ unsigned short rval = 0;
+ /* Build command string */
+ mmc_cmd[0] = 0x40 + command;
+ mmc_cmd[1] = (unsigned char)(argument >> 24 & 0xff);
+ mmc_cmd[2] = (unsigned char)(argument >> 16 & 0xff);
+ mmc_cmd[3] = (unsigned char)(argument >> 8 & 0xff);
+ mmc_cmd[4] = (unsigned char)(argument & 0xff);
+ mmc_cmd[5] = 0x95;
+
+ /* record last command if not in init mode */
+ if (!init_mode)
+ latest_cmd = command;
+ if (init_mode || pdev->sd) {
+ /* Send a few zeros since SDs may be sleeping */
+ if (pdev->write(Null_Word, SD_PRE_CMD_ZEROS, pdev->priv_data) < 0) {
+ debug("sending SD_PRE_CMD_ZEROS failed\n");
+ rval = ERR_SPI_TIMEOUT;
+ goto out;
+ }
+ }
+
+ if (pdev->write(mmc_cmd, 6, pdev->priv_data) < 0) {
+ debug("sending command %d failed\n", command);
+ rval = ERR_SPI_TIMEOUT;
+ goto out;
+ }
+ resp = mmc_wait_response(pdev, timeout);
+ if (resp != cmd_resp) {
+ /* NOTE: ignore "illegal command" responses */
+ if (resp == 4) {
+ rval = 0;
+ goto out;
+ }
+ /* Will only be active during init, seems to be needed by some SDs */
+ if (init_mode) {
+ /* This delay is somewhat picky for some SDs. Dont change it */
+ udelay(10000);
+ } else {
+ debug("unexpected response to command %d, wanted 0x%x, got 0x%x)\n",
+ command, cmd_resp, resp);
+ }
+ rval = ERR_MMC_TIMEOUT;
+ goto out;
+ }
+out:
+ /*
+ if (pdev->sd) {
+ mmc_spi_dummy_clocks(pdev, SD_CLK_CNTRL);
+ }
+ */
+ return rval;
+}
+
+static short mmc_spi_error_handler(struct mmc_spi_dev *pdev, short rval)
+{
+ /* Handle log index, wrap if necessary */
+ unsigned short status = 0;
+
+ /* If error, check status and log */
+ if (rval) {
+ /* shift old log entries down */
+ memcpy(pdev->error_log+1, pdev->error_log, LOG_LEN-1);
+ memcpy(pdev->status_log+1, pdev->status_log, LOG_LEN-1);
+ memcpy(pdev->cmd_log+1, pdev->cmd_log, LOG_LEN-1);
+ pdev->cmd_log[0] = latest_cmd;
+ pdev->error_log[0] = rval;
+
+ /*
+ NOTE: status may be zero even on errors.
+ since data lines may be left low(if card pulled from socket for ex.)
+ */
+ status = mmc_spi_read_status(pdev);
+ pdev->status_log[0] = status;
+ pdev->errors++;
+
+ debug("Latest command was: %d\n", latest_cmd);
+ }
+ switch (rval) {
+ case ERR_SPI_TIMEOUT:
+ debug("ERR_SPI_TIMEOUT\n");
+ return RVAL_CRITICAL;
+ case ERR_MMC_TIMEOUT:
+ debug("ERR_MMC_TIMEOUT\n");
+ return RVAL_ERROR;
+ case ERR_MMC_PROG_TIMEOUT:
+ case ERR_UNKNOWN_TOK:
+ case DR_CRC_ERROR:
+ case DR_WRITE_ERROR:
+ default:
+ if (status) {
+ return RVAL_ERROR;
+ } else {
+ /* NOTE: could use status to determine what to do more accurately */
+ return RVAL_OK;
+ }
+ }
+ return 0;
+}
+
+#if 0
+/**
+* read_mmc_reg - reads the 128 bit CSD or CID register data + 2 byte CRC
+*
+*/
+static short read_mmc_reg(struct mmc_spi_dev *pdev, short csd)
+{
+ unsigned char resp = 0xff;
+ unsigned char *buf;
+ unsigned short rval = 0;
+
+ pdev->doassert();
+ if (csd) {
+ rval = send_cmd_and_wait(pdev, SEND_CSD, 0, R1_OK, MMC_COMMAND_TIMEOUT);
+ if (rval)
+ goto out;
+ buf = pdev->raw_csd;
+ } else {
+ rval = send_cmd_and_wait(pdev, SEND_CID, 0, R1_OK, MMC_COMMAND_TIMEOUT);
+ if (rval)
+ goto out;
+ buf = pdev->raw_cid;
+ }
+
+ /* start block token */
+ resp = mmc_wait_response(pdev, MMC_COMMAND_TIMEOUT);
+ if (resp != SBT_S_BLOCK_READ) {
+ debug("mmc did not send 0xFE(got 0x%x)\n", resp);
+ rval = resp;
+ goto out;
+ }
+ if (pdev->read(buf, 18, pdev->priv_data) < 18) {
+ debug("reading 18 bytes of data failed\n");
+ rval = ERR_SPI_TIMEOUT;
+ goto out;
+ }
+out:
+ /* send clocks for SD cards */
+ if (pdev->sd)
+ mmc_spi_dummy_clocks(pdev, SD_CLK_CNTRL);
+
+ pdev->deassert();
+
+ /* check for errors, but dont change rval */
+ mmc_spi_error_handler(pdev, rval);
+
+ return rval;
+}
+
+static short mmc_spi_get_card(struct mmc_spi_dev *pdev)
+{
+ if (read_mmc_reg(pdev, 1)) {
+ debug("CSD register read failed.\n");
+ return 1;
+ }
+ if (read_mmc_reg(pdev, 0)) {
+ debug("CID register read failed.\n");
+ return 1;
+ }
+
+ /* Parse CSD and CID data */
+ mmc_spi_fill_card_struct(pdev);
+
+ return 0;
+}
+#endif
+
+static short mmc_spi_read_mmc_block(struct mmc_spi_dev *pdev, unsigned char *buf, unsigned long address)
+{
+ unsigned char resp = 0xff;
+ unsigned short rval = 0;
+
+ pdev->doassert();
+ rval = send_cmd_and_wait(pdev, READ_SINGLE_BLOCK, address, R1_OK, MMC_COMMAND_TIMEOUT);
+ if (rval)
+ goto out;
+
+ /* Poll for start block token */
+ resp = mmc_wait_response(pdev, MMC_COMMAND_TIMEOUT);
+ if (resp != SBT_S_BLOCK_READ) {
+ debug("mmc did not send 0xFE(got 0x%x)\n", resp);
+ rval = resp;
+ goto out;
+ }
+ /* Read data */
+ if (pdev->read(buf, 512, pdev->priv_data) < 512) {
+ debug("reading 512 bytes of data failed\n");
+ rval = ERR_SPI_TIMEOUT;
+ goto out;
+ }
+ /* TODO: read CRC */
+out:;
+
+ /* send 8 clocks for SD cards */
+ if (pdev->sd)
+ mmc_spi_dummy_clocks(pdev, SD_CLK_CNTRL);
+ pdev->deassert();
+
+ return mmc_spi_error_handler(pdev, rval);
+}
+
+/*
+ Not implemented on Blackfin since DMA reads are a bit troublesome(512 bytes
+ requested could be 514 bytes read.. this could be solved with some hacks though)
+*/
+#ifdef USE_MULT_BLOCK_READS
+static short mmc_spi_read_mult_mmc_block(struct mmc_spi_dev *pdev, unsigned char *buf,
+ unsigned int address, int nblocks)
+{
+ unsigned char resp = 0xff;
+ int rval = 0;
+ int i = 0;
+
+ rval = send_cmd_and_wait(pdev, READ_MULTIPLE_BLOCK, address, R1_OK, MMC_COMMAND_TIMEOUT)
+ if (rval)
+ goto out;
+
+ /* idea: read n blocks in one swoop, Data, Garbage and Tokens
+ * GGGGGTDDD..512..DDDGGGGTDDDD..512..DDDGGGGT - - -
+ *-------'''''''''''''.....''''''''''''''
+ * Then memcpy data to the real buffer, may need a few pages of memory for this
+ */
+ for (i = 0; i < nblocks; i++) {
+ /* Poll for start block token */
+ resp = mmc_wait_response(pdev, MMC_COMMAND_TIMEOUT)
+ if (resp != SBT_M_BLOCK_READ) {
+ debug("mmc did not send 0xFE(got 0x%x)\n", resp);
+ rval = resp;
+ goto out;
+ }
+ if (pdev->read(buf+i*MMC_SECTOR_SIZE, MMC_SECTOR_SIZE, pdev->priv_data) < MMC_SECTOR_SIZE) {
+ debug("reading 512 bytes of data failed\n");
+ rval = 1;
+ goto out;
+ }
+ }
+ rval = 0;
+out:
+
+ /* send 8 clocks for SD cards */
+ if (pdev->sd)
+ mmc_spi_dummy_clocks(pdev, SD_CLK_CNTRL);
+
+ /* send stop command */
+ rval = send_cmd_and_wait(pdev, STOP_TRANSMISSION, address, R1_OK, MMC_COMMAND_TIMEOUT))) {
+
+ return mmc_spi_error_handler(pdev, rval);
+}
+
+static short mmc_spi_write_mmc_block(struct mmc_spi_dev *pdev, unsigned char *buf, unsigned int address)
+{
+ unsigned short rval = 0;
+ unsigned char resp = 0xff;
+ unsigned char token;
+ unsigned int n_polls = 0;
+
+ pdev->doassert();
+ rval = send_cmd_and_wait(pdev, WRITE_BLOCK, address, R1_OK, MMC_COMMAND_TIMEOUT);
+ if (rval) {
+ debug("write error at %08x \n", address);
+ goto out;
+ }
+
+ /* send start block token */
+ token = SBT_S_BLOCK_WRITE;
+ if (pdev->write(&token, 1, pdev->priv_data) < 0) {
+ debug("sending START_BLOCK_TOKEN failed\n");
+ rval = ERR_SPI_TIMEOUT;
+ goto out;
+
+ }
+ /* transmit data block */
+ if (pdev->write(buf, MMC_SECTOR_SIZE, pdev->priv_data) < MMC_SECTOR_SIZE) {
+ debug("transmission of 512 bytes failed\n");
+ rval = ERR_SPI_TIMEOUT;
+ goto out;
+
+ }
+ resp = mmc_wait_response(pdev, MMC_COMMAND_TIMEOUT) & DR_MASK;
+ /* wait for data response token */
+ if (resp != DR_ACCEPTED) {
+ /*
+ some card seem to send 0 or 1 at this point,
+ accet that even though not according to MMC spec.
+ */
+ if (resp != 0 && resp != 1 && resp != 4) {
+ debug("mmc did not send DR_ACCEPTED token(got R1=0x%x)\n", resp);
+ rval = ERR_MMC_TIMEOUT;
+ goto out;
+ }
+ }
+
+ while (1) {
+ /*
+ NOTE: could read response block-wise(effecive if DMA is utilized) to buffer
+ and check for tokens.
+ */
+ if (pdev->read(&resp, 1, pdev->priv_data) < 0) {
+ debug("busy token read polling failed\n");
+ rval = resp;
+ goto out;
+ }
+ switch (resp & DR_MASK) {
+ case BUSY_TOKEN:
+ break;
+ case DR_ACCEPTED:
+ goto out;
+ case DR_CRC_ERROR:
+ rval = DR_CRC_ERROR;
+ goto out;
+ case DR_WRITE_ERROR:
+ rval = DR_WRITE_ERROR;
+ goto out;
+ default:
+ goto out;
+ }
+ if (n_polls++ >= MMC_PROG_TIMEOUT) {
+ rval = ERR_MMC_PROG_TIMEOUT;
+ goto out;
+ }
+ }
+out:
+ /* send 8 clocks for SD cards */
+ if (pdev->sd)
+ mmc_spi_dummy_clocks(pdev, SD_CLK_CNTRL);
+
+ pdev->deassert();
+
+ return mmc_spi_error_handler(pdev, rval);
+}
+
+static unsigned char wrb[WRB_LEN];
+
+static short mmc_spi_write_mult_mmc_block(struct mmc_spi_dev *pdev,
+ unsigned char *buf, unsigned int address, int nblocks)
+{
+ unsigned short rval = 0;
+ unsigned char resp = 0xff;
+ unsigned char resp_last = 0xff;
+ unsigned char resp_oldest = 0xff;
+ unsigned int tc = 0;
+ int i = 0;
+ unsigned char token;
+ unsigned int n_polls = 0;
+
+
+ debug("adr(r): %08x\n", address);
+ pdev->doassert();
+ rval = send_cmd_and_wait(pdev, WRITE_MULTIPLE_BLOCK, address, R1_OK, MMC_COMMAND_TIMEOUT);
+ if (rval) {
+ debug("NO MBW!!!\n");
+ goto out;
+ }
+
+ for (i = 0; i < nblocks; i++) {
+ /* send start block token */
+ token = SBT_M_BLOCK_WRITE;
+ if (pdev->write(&token, 1, pdev->priv_data) < 0) {
+ debug("sending START_BLOCK_TOKEN failed\n");
+ rval = ERR_SPI_TIMEOUT;
+ goto stop;
+
+ }
+ /* transmit data block */
+ if (pdev->write(buf+i*MMC_SECTOR_SIZE, MMC_SECTOR_SIZE, pdev->priv_data) < MMC_SECTOR_SIZE) {
+ debug("transmission of 512 bytes failed\n");
+ rval = ERR_SPI_TIMEOUT;
+ goto stop;
+
+ }
+ /* wait for data response token */
+ resp = mmc_wait_response(pdev, MMC_COMMAND_TIMEOUT) & DR_MASK;
+ if (resp != DR_ACCEPTED) {
+ if (resp != 0 && resp != 1 && resp != 2 && resp != 4) {
+ debug("mmc did not send DR_ACCEPTED token(got R1=0x%x)\n", resp);
+ rval = ERR_MMC_TIMEOUT;
+ goto stop;
+ }
+ }
+ /* send 8 clocks for SD cards */
+ if (pdev->sd)
+ mmc_spi_dummy_clocks(pdev, SD_CLK_CNTRL);
+ /* wait on busy/error token while MMC is programming new data */
+ tc = 0;
+ n_polls = 0;
+
+ while (1) {
+ /* read response byte-wise(take one or two reads only) */
+ if (pdev->read(&resp, 1, pdev->priv_data) < 0) {
+ debug("busy token read polling failed\n");
+ rval = ERR_SPI_TIMEOUT;
+ goto stop;
+ }
+ switch (resp & DR_MASK) {
+ case BUSY_TOKEN:
+ break;
+ case DR_ACCEPTED:
+ goto next;
+ case DR_CRC_ERROR:
+ rval = DR_CRC_ERROR;
+ goto stop;
+ case DR_WRITE_ERROR:
+ rval = DR_WRITE_ERROR;
+ goto stop;
+ default:
+ goto next;
+ }
+ if (n_polls++ >= MMC_PROG_TIMEOUT) {
+ rval = ERR_MMC_PROG_TIMEOUT;
+ goto stop;
+ }
+ }
+next:;
+ }
+
+stop:
+ /* send stop tran token (STT_M_BLOCK_WRITE) */
+ token = STT_M_BLOCK_WRITE;
+ if (pdev->write(&token, 1, pdev->priv_data) < 0) {
+ debug("sending STT_M_BLOCK_WRITE failed\n");
+ rval = ERR_SPI_TIMEOUT;
+ goto out;
+ }
+
+ n_polls = 0;
+ /*
+ wait on final busy/error token while MMC is programming new data.
+ This is done in blocks of length WRB_LEN instead of 1-byte poll
+ (takes several 100 bytes to do at 20Mhz spi clock). Could decrease burst
+ preformance on very fast cards. But improves over-all system performance
+ immensley when using this driver.
+ */
+ while (1 && !rval) {
+ /* read response block wise */
+ if (pdev->read(wrb, WRB_LEN, pdev->priv_data) < 0) {
+ debug("busy token read polling failed");
+ rval = ERR_SPI_TIMEOUT;
+ goto out;
+ }
+ if (n_polls++ >= MMC_PROG_TIMEOUT) {
+ debug("POLL for last token timeout!!(resp=%x, last_resp=%x, resp_oldest=%x)\n",
+ resp, resp_last, resp_oldest);
+ rval = ERR_MMC_TIMEOUT;
+ goto out;
+ }
+
+ /*
+ Exit when card raises the data line(busy to done token transition)
+ NOTE: transition is often(allways?) 0x00, 0x00, 0x??, 0xFF, 0xFF,
+ where ?? could be anything != 0xFF for some card brands. Nothing
+ to do but ignore this last "token". This was a beast and caused trouble
+ with some off-brands. Either my interpretations of MMC/SD spec was bad.
+ Or some cards are just sloppy made.
+ */
+ if (wrb[WRB_LEN-1] == 0xFF) {
+ debug("Got final MBW busy wait done(as 0x%x after %d reads @ %08x.. "
+ "last_resp=%x, resp_oldest=%x\n", wrb[WRB_LEN-1], n_polls, address,
+ resp_last, resp_oldest);
+ goto out;
+ }
+ resp_oldest = resp_last;
+ resp_last = resp;
+ }
+out:
+
+ /* send 8 clocks for SD cards */
+ if (pdev->sd)
+ mmc_spi_dummy_clocks(pdev, SD_CLK_CNTRL);
+
+ pdev->deassert();
+
+ /* Reading status breaks compatibility with some cards, skip it */
+ return mmc_spi_error_handler(pdev, rval);
+}
+#endif
+
+static short mmc_spi_init_card(struct mmc_spi_dev *pdev)
+{
+ unsigned short cntr = 0;
+
+ /* for making init process beeing silent */
+ init_mode = 1;
+ /* save length of log for external usage */
+ pdev->log_len = LOG_LEN;
+
+ /* 10 bytes(80 cycles) with CS de-asserted */
+ mmc_spi_dummy_clocks(pdev, 10);
+ pdev->doassert();
+ if (send_cmd_and_wait(pdev, GO_IDLE_STATE, 0, R1_IDLE_STATE, MMC_INIT_TIMEOUT))
+ return 1;
+ pdev->deassert();
+ /* Send One Byte Delay */
+ if (pdev->write(Null_Word, 1, pdev->priv_data) < 0)
+ return 1;
+ pdev->doassert();
+ /* Look for SD card */
+ for (cntr = 0; cntr < 60; cntr++) {
+ /* Send One Byte Delay */
+ if (pdev->write(Null_Word, 1, pdev->priv_data) < 0)
+ return 1;
+ if (send_cmd_and_wait(pdev, APP_CMD, 0, R1_OK, MMC_INIT_TIMEOUT) == 0)
+ goto next;
+ if (send_cmd_and_wait(pdev, APP_CMD, 0, R1_IDLE_STATE, MMC_INIT_TIMEOUT))
+ continue;
+next:
+ if (send_cmd_and_wait(pdev, SD_SEND_OP_COND, 0, R1_OK, MMC_INIT_TIMEOUT) == 0) {
+ /* Send One Byte Delay and return */
+ if (pdev->write(Null_Word, 4, pdev->priv_data) < 0) {
+ pdev->deassert();
+ return 1;
+ }
+ pdev->sd = 1;
+ init_mode = 0;
+ debug("SD card found!\n");
+ pdev->deassert();
+ return 0;
+ }
+ }
+
+ /* poll card by sending CMD1 and wait for card initialization complete */
+ for (cntr = 0; cntr < 60; cntr++) {
+ if (send_cmd_and_wait(pdev, SEND_OP_COND, 0, R1_OK, MMC_INIT_TIMEOUT) == 0) {
+ if (pdev->write(Null_Word, 1, pdev->priv_data) < 0) {
+ pdev->deassert();
+ return 1;
+ }
+ pdev->sd = 0;
+ init_mode = 0;
+ debug("MMC card found!\n");
+ pdev->deassert();
+ return 0;
+ }
+ if (pdev->write(Null_Word, 1, pdev->priv_data) < 0) {
+ pdev->deassert();
+ return 1;
+ }
+ }
+ debug("doh!\n\n\n");
+ pdev->deassert();
+ return 1;
+}
+
+#ifdef DEBUG_REGS
+static short mmc_spi_mmc_spi_get_card_old(struct mmc_spi_dev *pdev)
+{
+ int i;
+ struct mmc_card *card = pdev->private_data->card;
+ unsigned char raw_csd[18];
+ unsigned char raw_cid[18];
+ unsigned short c_size_mult = 0;
+ unsigned short c_size = 0;
+ unsigned short read_bl_len = 0;
+ unsigned int cap = 0;
+
+ memset(raw_cid, 0, 18);
+ memset(raw_csd, 0, 18);
+
+ if (read_mmc_reg(pdev, raw_cid, 0)) {
+ debug("CSD register read failed.\n");
+ return 1;
+ };
+ if (read_mmc_reg(pdev, raw_csd, 1)) {
+ debug("CID register read failed.\n");
+ return 1;
+ }
+
+ /********** NO DEBUG CODE FROM HERE *********************/
+ card->csd.mmca_vsn = (raw_csd[0] & 0x3c) >> 2;
+ card->csd.cmdclass = (((__u16)raw_csd[4]) << 4) | ((raw_csd[5] & 0xf0) >> 4);
+ card->csd.tacc_clks = raw_csd[1];
+ card->csd.tacc_ns = raw_csd[2];
+ card->csd.max_dtr = raw_csd[3];
+ card->csd.read_blkbits = raw_csd[5] & 0x0f;
+
+ /* for calculating capacity(in blocks) */
+ c_size = ((((__u16)raw_csd[6]) & 0x03) << 10) | (((__u16)raw_csd[7]) << 2) | (((__u16)raw_csd[8]) & 0xc0) >> 6;
+ c_size_mult = ((raw_csd[9] & 0x03) << 1) | ((raw_csd[10] & 0x80) >> 7);
+ read_bl_len = raw_csd[5] & 0x0f;
+ card->csd.capacity = (c_size+1) * (1 << (c_size_mult + 2));
+
+ /* for printing capacity in bytes */
+ cap = (c_size+1) * (1 << (c_size_mult + 2)) * (1 << read_bl_len);
+
+ card->cid.manfid = getvalue(raw_cid, 127-127, 8);
+ memcpy(card.cid.prod_name, raw_cid+3, 7);
+ card->cid.serial = getvalue(raw_cid, 127-47, 32);
+ card->cid.oemid = getvalue(raw_cid, 127-119, 16);
+ card->cid.year = 1997 + (getvalue(raw_cid, 127-15, 8) & 0x0F);
+ card->cid.hwrev = (getvalue(raw_cid, 127-55, 8) & 0xF0) >> 4;
+ card->cid.fwrev = getvalue(raw_cid, 127-55, 8) & 0x0F;
+ card->cid.month = (getvalue(raw_cid, 127-15, 8) & 0xF0) >> 4;
+
+ printf("MMC found:\n\t Capacity: %dM\n\t Name: %s \n\t Rev: %d.%d \n\t"
+ "Date: %d/%d \n\t Serial: 0x%x (%u)\n", cap/(1024*1024),
+ card.cid.prod_name, card.cid.hwrev, card.cid.fwrev,
+ card.cid.year, card.cid.month, card.cid.serial, card.cid.serial);
+ return 0;
+}
+#endif
+
+
+#ifndef CONFIG_SPI_MMC_DEFAULT_CS
+# define CONFIG_SPI_MMC_DEFAULT_CS 1
+#endif
+#ifndef CONFIG_SPI_MMC_DEFAULT_SPEED
+# define CONFIG_SPI_MMC_DEFAULT_SPEED 30000000
+#endif
+#ifndef CONFIG_SPI_MMC_DEFAULT_MODE
+# define CONFIG_SPI_MMC_DEFAULT_MODE SPI_MODE_3
+#endif
+
+#define MMC_BLOCK_SIZE 512
+
+static block_dev_desc_t mmc_block_dev_desc;
+static struct mmc_spi_dev msdev;
+
+block_dev_desc_t *mmc_get_dev(int dev)
+{
+ debug("mmc_get_dev\n");
+ return (block_dev_desc_t *)&mmc_block_dev_desc;
+}
+
+static int r;
+unsigned long mmc_block_read(int dev, unsigned long blk_start, lbaint_t blkcnt, void *dst2)
+{
+ int i;
+ unsigned char *dst = dst2;
+
+ for (i = 0; i < blkcnt; i++, blk_start++, dst += MMC_BLOCK_SIZE) {
+ r += MMC_BLOCK_SIZE;
+ if (mmc_spi_read_mmc_block(&msdev, dst, blk_start * MMC_BLOCK_SIZE) != RVAL_OK)
+ printf("error in mmc_block_read\n");;
+ }
+ debug("mmc_block_read: %d bytes\n", r);
+ return blkcnt;
+}
+
+static struct spi_slave *slave;
+
+static void spi_assert(void)
+{
+ spi_cs_activate(slave);
+}
+
+static void spi_deassert(void)
+{
+ spi_cs_deactivate(slave);
+}
+
+static int spi_wait_write(unsigned char *buffer, unsigned int count, void *dummy)
+{
+ spi_xfer(slave, count * 8, buffer, NULL, 0);
+ return count;
+}
+
+static int spi_wait_read(unsigned char *buffer, unsigned int count, void *dummy)
+{
+ spi_xfer(slave, count * 8, NULL, buffer, 0);
+ return count;
+}
+
+static int spi_mmc_init(void)
+{
+ char *s;
+ int cs, hz, mode;
+
+ if (slave) {
+ spi_release_bus(slave);
+ spi_free_slave(slave);
+ }
+
+ if ((s = getenv("mmc_cs")))
+ cs = simple_strtoul(s, NULL, 10);
+ else
+ cs = CONFIG_SPI_MMC_DEFAULT_CS;
+
+ if ((s = getenv("mmc_hz")))
+ hz = simple_strtoul(s, NULL, 10);
+ else
+ hz = CONFIG_SPI_MMC_DEFAULT_SPEED;
+
+ if ((s = getenv("mmc_mode")))
+ mode = simple_strtoul(s, NULL, 10);
+ else
+ mode = CONFIG_SPI_MMC_DEFAULT_MODE;
+
+ printf("using spi0.%i at %i hz with mode %x\n", cs, hz, mode);
+ slave = spi_setup_slave(0, cs, hz, mode);
+ if (!slave)
+ return -1;
+ spi_claim_bus(slave);
+
+ return 0;
+}
+
+int mmc_legacy_init(int verbose)
+{
+ int ret;
+
+ ret = spi_mmc_init();
+ if (ret)
+ return ret;
+ msdev.read = &spi_wait_read;
+ msdev.write = &spi_wait_write;
+ msdev.doassert = &spi_assert;
+ msdev.deassert = &spi_deassert;
+ ret = mmc_spi_init_card(&msdev);
+ if (ret)
+ return ret;
+ mmc_block_dev_desc.if_type = IF_TYPE_MMC;
+ mmc_block_dev_desc.part_type = PART_TYPE_DOS;
+ mmc_block_dev_desc.dev = 0;
+ mmc_block_dev_desc.blksz = MMC_BLOCK_SIZE;
+ mmc_block_dev_desc.block_read = mmc_block_read;
+ sprintf(mmc_block_dev_desc.vendor, "Rubico AB <www.rubico.se>");
+ init_part(&mmc_block_dev_desc);
+ return 0;
+}
--
1.7.3.2
2
5
These id tables need not be writable.
Signed-off-by: Mike Frysinger <vapier(a)gentoo.org>
---
drivers/mtd/nand/nand_base.c | 6 +++---
drivers/mtd/nand/nand_ids.c | 4 ++--
include/linux/mtd/nand.h | 4 ++--
3 files changed, 7 insertions(+), 7 deletions(-)
diff --git a/drivers/mtd/nand/nand_base.c b/drivers/mtd/nand/nand_base.c
index 21cc5a3..b74d040 100644
--- a/drivers/mtd/nand/nand_base.c
+++ b/drivers/mtd/nand/nand_base.c
@@ -2409,11 +2409,11 @@ static void nand_set_defaults(struct nand_chip *chip, int busw)
/*
* Get the flash and manufacturer id and lookup if the type is supported
*/
-static struct nand_flash_dev *nand_get_flash_type(struct mtd_info *mtd,
+static const struct nand_flash_dev *nand_get_flash_type(struct mtd_info *mtd,
struct nand_chip *chip,
int busw, int *maf_id)
{
- struct nand_flash_dev *type = NULL;
+ const struct nand_flash_dev *type = NULL;
int i, dev_id, maf_idx;
int tmp_id, tmp_manf;
@@ -2587,7 +2587,7 @@ int nand_scan_ident(struct mtd_info *mtd, int maxchips)
{
int i, busw, nand_maf_id;
struct nand_chip *chip = mtd->priv;
- struct nand_flash_dev *type;
+ const struct nand_flash_dev *type;
/* Get buswidth to select the correct functions */
busw = chip->options & NAND_BUSWIDTH_16;
diff --git a/drivers/mtd/nand/nand_ids.c b/drivers/mtd/nand/nand_ids.c
index 25b22ec..8d7ea76 100644
--- a/drivers/mtd/nand/nand_ids.c
+++ b/drivers/mtd/nand/nand_ids.c
@@ -22,7 +22,7 @@
+ 256 256 Byte page size
* 512 512 Byte page size
*/
-struct nand_flash_dev nand_flash_ids[] = {
+const struct nand_flash_dev nand_flash_ids[] = {
#ifdef CONFIG_MTD_NAND_MUSEUM_IDS
{"NAND 1MiB 5V 8-bit", 0x6e, 256, 1, 0x1000, 0},
@@ -132,7 +132,7 @@ struct nand_flash_dev nand_flash_ids[] = {
/*
* Manufacturer ID list
*/
-struct nand_manufacturers nand_manuf_ids[] = {
+const struct nand_manufacturers nand_manuf_ids[] = {
{NAND_MFR_TOSHIBA, "Toshiba"},
{NAND_MFR_SAMSUNG, "Samsung"},
{NAND_MFR_FUJITSU, "Fujitsu"},
diff --git a/include/linux/mtd/nand.h b/include/linux/mtd/nand.h
index 94ad0c0..519f47e 100644
--- a/include/linux/mtd/nand.h
+++ b/include/linux/mtd/nand.h
@@ -470,8 +470,8 @@ struct nand_manufacturers {
char * name;
};
-extern struct nand_flash_dev nand_flash_ids[];
-extern struct nand_manufacturers nand_manuf_ids[];
+extern const struct nand_flash_dev nand_flash_ids[];
+extern const struct nand_manufacturers nand_manuf_ids[];
extern int nand_scan_bbt(struct mtd_info *mtd, struct nand_bbt_descr *bd);
extern int nand_update_bbt(struct mtd_info *mtd, loff_t offs);
--
1.7.3.1
2
3
This patch is for onenand support of s5p6442 SoC.
Cc: Minkyu Kang <mk7.kang(a)samsung.com>
Cc: Kyungmin Park <kyungmin.park(a)samsung.com>
Signed-off-by: Joonyoung Shim <jy0922.shim(a)samsung.com>
---
drivers/mtd/onenand/samsung.c | 6 +++---
1 files changed, 3 insertions(+), 3 deletions(-)
diff --git a/drivers/mtd/onenand/samsung.c b/drivers/mtd/onenand/samsung.c
index f2be687..cbcf83b 100644
--- a/drivers/mtd/onenand/samsung.c
+++ b/drivers/mtd/onenand/samsung.c
@@ -67,7 +67,7 @@ do { \
#define MAP_01 (0x1 << 24)
#define MAP_10 (0x2 << 24)
#define MAP_11 (0x3 << 24)
-#elif defined(CONFIG_S5PC1XX)
+#elif defined(CONFIG_S5PC1XX) || defined(CONFIG_S5P64XX)
#define MAP_00 (0x0 << 26)
#define MAP_01 (0x1 << 26)
#define MAP_10 (0x2 << 26)
@@ -121,7 +121,7 @@ static unsigned int s3c_mem_addr(int fba, int fpa, int fsa)
{
return (fba << 12) | (fpa << 6) | (fsa << 4);
}
-#elif defined(CONFIG_S5PC1XX)
+#elif defined(CONFIG_S5PC1XX) || defined(CONFIG_S5P64XX)
static unsigned int s3c_mem_addr(int fba, int fpa, int fsa)
{
return (fba << 13) | (fpa << 7) | (fsa << 5);
@@ -614,7 +614,7 @@ void s3c_onenand_init(struct mtd_info *mtd)
#if defined(CONFIG_S3C64XX)
onenand->base = (void *)0x70100000;
onenand->ahb_addr = (void *)0x20000000;
-#elif defined(CONFIG_S5PC1XX)
+#elif defined(CONFIG_S5PC1XX) || defined(CONFIG_S5P64XX)
onenand->base = (void *)0xE7100000;
onenand->ahb_addr = (void *)0xB0000000;
#endif
--
1.6.3.3
2
2
From: Reinhard Meyer <info(a)emk-elektronik.de>
Adds support for the EMK TOP9000 CPU Module which is
based on ATMELs ARM926EJS AT91SAM9XE SoC.
Signed-off-by: Reinhard Meyer <u-boot(a)emk-elektronik.de>
---
MAINTAINERS | 3 +-
board/emk/top9000/Makefile | 54 ++++++++
board/emk/top9000/spi.c | 61 +++++++++
board/emk/top9000/top9000.c | 290 +++++++++++++++++++++++++++++++++++++++
boards.cfg | 2 +
include/configs/top9000.h | 314 +++++++++++++++++++++++++++++++++++++++++++
6 files changed, 723 insertions(+), 1 deletions(-)
create mode 100644 board/emk/top9000/Makefile
create mode 100644 board/emk/top9000/spi.c
create mode 100644 board/emk/top9000/top9000.c
create mode 100644 include/configs/top9000.h
diff --git a/MAINTAINERS b/MAINTAINERS
index 9258cb1..ccece74 100644
--- a/MAINTAINERS
+++ b/MAINTAINERS
@@ -310,10 +310,11 @@ Tirumala Marri <tmarri(a)apm.com>
bluestone APM821XX
-Reinhard Meyer <r.meyer(a)emk-elektronik.de>
+Reinhard Meyer <reinhard.meyer(a)emk-elektronik.de>
TOP860 MPC860T
TOP5200 MPC5200
+ TOP9000 ARM926EJS (AT91SAM9xxx SoC)
Tolunay Orkun <torkun(a)nextio.com>
diff --git a/board/emk/top9000/Makefile b/board/emk/top9000/Makefile
new file mode 100644
index 0000000..9b28048
--- /dev/null
+++ b/board/emk/top9000/Makefile
@@ -0,0 +1,54 @@
+#
+# (C) Copyright 2003-2008
+# Wolfgang Denk, DENX Software Engineering, wd(a)denx.de.
+#
+# (C) Copyright 2010
+# Reinhard Meyer, EMK Elektronik, reinhard.meyer(a)emk-elektronik.de
+#
+# 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
+#
+
+include $(TOPDIR)/config.mk
+
+LIB = $(obj)lib$(BOARD).a
+
+COBJS-y += top9000.o
+COBJS-$(CONFIG_ATMEL_SPI) += spi.o
+
+SRCS := $(SOBJS:.o=.S) $(COBJS-y:.o=.c)
+OBJS := $(addprefix $(obj),$(COBJS-y))
+SOBJS := $(addprefix $(obj),$(SOBJS))
+
+$(LIB): $(obj).depend $(OBJS) $(SOBJS)
+ $(AR) $(ARFLAGS) $@ $(OBJS) $(SOBJS)
+
+clean:
+ rm -f $(SOBJS) $(OBJS)
+
+distclean: clean
+ rm -f $(LIB) core *.bak $(obj).depend
+
+#########################################################################
+
+# defines $(obj).depend target
+include $(SRCTREE)/rules.mk
+
+sinclude $(obj).depend
+
+#########################################################################
diff --git a/board/emk/top9000/spi.c b/board/emk/top9000/spi.c
new file mode 100644
index 0000000..b468948
--- /dev/null
+++ b/board/emk/top9000/spi.c
@@ -0,0 +1,61 @@
+/*
+ * Copyright (C) 2010
+ * Reinhard Meyer, EMK Elektronik, reinhard.meyer(a)emk-elektronik.de
+ *
+ * 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
+ */
+
+#include <common.h>
+#include <asm/arch/hardware.h>
+#include <asm/arch/at91_spi.h>
+#include <asm/arch/gpio.h>
+#include <spi.h>
+
+static const struct {
+ u32 port;
+ u32 bit;
+} cs_to_portbit[2][4] = {
+ {{AT91_PIO_PORTA, 3}, {AT91_PIO_PORTC, 11},
+ {AT91_PIO_PORTC, 16}, {AT91_PIO_PORTC, 17} },
+ {{AT91_PIO_PORTB, 3}, {AT91_PIO_PORTC, 5},
+ {AT91_PIO_PORTC, 4}, {AT91_PIO_PORTC, 3} }
+};
+
+int spi_cs_is_valid(unsigned int bus, unsigned int cs)
+{
+ debug("spi_cs_is_valid: bus=%u cs=%u\n", bus, cs);
+ if (bus < 2 && cs < 4)
+ return 1;
+ return 0;
+}
+
+void spi_cs_activate(struct spi_slave *slave)
+{
+ debug("spi_cs_activate: bus=%u cs=%u\n", slave->bus, slave->cs);
+ at91_set_pio_output(cs_to_portbit[slave->bus][slave->cs].port,
+ cs_to_portbit[slave->bus][slave->cs].bit, 0);
+}
+
+void spi_cs_deactivate(struct spi_slave *slave)
+{
+ debug("spi_cs_deactivate: bus=%u cs=%u\n", slave->bus, slave->cs);
+ at91_set_pio_output(cs_to_portbit[slave->bus][slave->cs].port,
+ cs_to_portbit[slave->bus][slave->cs].bit, 1);
+}
+
diff --git a/board/emk/top9000/top9000.c b/board/emk/top9000/top9000.c
new file mode 100644
index 0000000..b0fe2d6
--- /dev/null
+++ b/board/emk/top9000/top9000.c
@@ -0,0 +1,290 @@
+/*
+ * (C) Copyright 2007-2008
+ * Stelian Pop <stelian.pop(a)leadtechdesign.com>
+ * Lead Tech Design <www.leadtechdesign.com>
+ *
+ * (C) Copyright 2010
+ * Reinhard Meyer, EMK Elektronik, reinhard.meyer(a)emk-elektronik.de
+ *
+ * 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
+ */
+
+#include <common.h>
+#include <net.h>
+#include <netdev.h>
+#include <mmc.h>
+#include <i2c.h>
+#include <spi.h>
+#include <asm/arch/at91sam9260.h>
+#include <asm/arch/at91sam9260_matrix.h>
+#include <asm/arch/at91sam9_smc.h>
+#include <asm/arch/at91_common.h>
+#include <asm/arch/at91_pmc.h>
+#include <asm/arch/at91_rstc.h>
+#include <asm/arch/at91_shdwn.h>
+#include <asm/arch/gpio.h>
+#include <asm/arch/io.h>
+#include <asm/arch/hardware.h>
+
+DECLARE_GLOBAL_DATA_PTR;
+
+#ifdef CONFIG_CMD_NAND
+static void nand_hw_init(void)
+{
+ unsigned long csa;
+
+ /* Enable CS3 */
+ csa = at91_sys_read(AT91_MATRIX_EBICSA);
+ at91_sys_write(AT91_MATRIX_EBICSA,
+ csa | AT91_MATRIX_CS3A_SMC_SMARTMEDIA);
+
+ /* Configure SMC CS3 for NAND/SmartMedia */
+ at91_sys_write(AT91_SMC_SETUP(3),
+ AT91_SMC_NWESETUP_(1) | AT91_SMC_NCS_WRSETUP_(0) |
+ AT91_SMC_NRDSETUP_(1) | AT91_SMC_NCS_RDSETUP_(0));
+ at91_sys_write(AT91_SMC_PULSE(3),
+ AT91_SMC_NWEPULSE_(3) | AT91_SMC_NCS_WRPULSE_(3) |
+ AT91_SMC_NRDPULSE_(3) | AT91_SMC_NCS_RDPULSE_(3));
+ at91_sys_write(AT91_SMC_CYCLE(3),
+ AT91_SMC_NWECYCLE_(5) | AT91_SMC_NRDCYCLE_(5));
+ at91_sys_write(AT91_SMC_MODE(3),
+ AT91_SMC_READMODE | AT91_SMC_WRITEMODE |
+ AT91_SMC_EXNWMODE_DISABLE |
+ AT91_SMC_DBW_8 |
+ AT91_SMC_TDF_(2));
+
+ /* Configure RDY/BSY */
+ at91_set_gpio_input(CONFIG_SYS_NAND_READY_PIN, 1);
+
+ /* Enable NandFlash */
+ at91_set_gpio_output(CONFIG_SYS_NAND_ENABLE_PIN, 1);
+}
+#endif
+
+#ifdef CONFIG_MACB
+static void macb_hw_init(void)
+{
+ /* Enable EMAC clock */
+ at91_sys_write(AT91_PMC_PCER, 1 << AT91SAM9260_ID_EMAC);
+
+ /* Initialize EMAC=MACB hardware */
+ at91_macb_hw_init();
+}
+#endif
+
+#ifdef CONFIG_GENERIC_ATMEL_MCI
+/* this is a weak define that we are overriding */
+int board_mmc_init(bd_t *bd)
+{
+ /* Enable MCI clock */
+ at91_sys_write(AT91_PMC_PCER, 1 << AT91SAM9260_ID_MCI);
+
+ /* Initialize MCI hardware */
+ at91_mci_hw_init();
+
+ /* This calls the atmel_mmc_init in gen_atmel_mci.c */
+ return atmel_mci_init((void *)AT91_BASE_MCI);
+}
+
+/* this is a weak define that we are overriding */
+int board_mmc_getcd(u8 *cd, struct mmc *mmc)
+{
+ /*
+ * the only currently existing use of this function
+ * (fsl_esdhc.c) suggests this function must return
+ * *cs = TRUE if a card is NOT detected -> in most
+ * cases the value of the pin when the detect switch
+ * closes to GND
+ */
+ *cd = at91_get_gpio_value(CONFIG_SYS_MMC_CD_PIN) ? 1 : 0;
+ return 0;
+}
+
+#endif
+
+int board_early_init_f(void)
+{
+ at91_shdwn_t *shdwn = (at91_shdwn_t *)AT91_SHDWN_BASE;
+
+ /*
+ * make sure the board can be powered on by
+ * any transition on WKUP
+ */
+ writel(AT91_SHDW_MR_WKMODE0H2L | AT91_SHDW_MR_WKMODE0L2H,
+ &shdwn->mr);
+
+ /* Enable clocks for all PIOs */
+ at91_sys_write(AT91_PMC_PCER, 1 << AT91SAM9260_ID_PIOA);
+ at91_sys_write(AT91_PMC_PCER, 1 << AT91SAM9260_ID_PIOB);
+ at91_sys_write(AT91_PMC_PCER, 1 << AT91SAM9260_ID_PIOC);
+
+ /* set SCL0 and SDA0 to open drain */
+ at91_set_pio_output(I2C0_PORT, SCL0_PIN, 1);
+ at91_set_pio_multi_drive(I2C0_PORT, SCL0_PIN, 1);
+ at91_set_pio_pullup(I2C0_PORT, SCL0_PIN, 1);
+ at91_set_pio_output(I2C0_PORT, SDA0_PIN, 1);
+ at91_set_pio_multi_drive(I2C0_PORT, SDA0_PIN, 1);
+ at91_set_pio_pullup(I2C0_PORT, SDA0_PIN, 1);
+
+ /* set SCL1 and SDA1 to open drain */
+ at91_set_pio_output(I2C1_PORT, SCL1_PIN, 1);
+ at91_set_pio_multi_drive(I2C1_PORT, SCL1_PIN, 1);
+ at91_set_pio_pullup(I2C1_PORT, SCL1_PIN, 1);
+ at91_set_pio_output(I2C1_PORT, SDA1_PIN, 1);
+ at91_set_pio_multi_drive(I2C1_PORT, SDA1_PIN, 1);
+ at91_set_pio_pullup(I2C1_PORT, SDA1_PIN, 1);
+ return 0;
+}
+
+int board_init(void)
+{
+ /* arch number of TOP9000 Board */
+ gd->bd->bi_arch_number = MACH_TYPE_TOP9000;
+ /* adress of boot parameters */
+ gd->bd->bi_boot_params = CONFIG_SYS_SDRAM_BASE + 0x100;
+
+ at91_serial_hw_init();
+#ifdef CONFIG_CMD_NAND
+ nand_hw_init();
+#endif
+#ifdef CONFIG_MACB
+ macb_hw_init();
+#endif
+#ifdef CONFIG_ATMEL_SPI0
+ /* (n+4) denotes to use nSPISEL(0) in GPIO mode! */
+ at91_spi0_hw_init(1 << (FRAM_CS_NUM + 4));
+#endif
+#ifdef CONFIG_ATMEL_SPI1
+ at91_spi1_hw_init(1 << (ENC_CS_NUM + 4));
+#endif
+ return 0;
+}
+
+#ifdef CONFIG_MISC_INIT_R
+int misc_init_r(void)
+{
+ /* read 'factory' part of EEPROM */
+ read_factory_r();
+ return 0;
+}
+#endif
+
+int dram_init(void)
+{
+ gd->ram_size = get_ram_size(
+ (void *)CONFIG_SYS_SDRAM_BASE,
+ CONFIG_SYS_SDRAM_SIZE);
+ return 0;
+}
+
+#ifdef CONFIG_RESET_PHY_R
+void reset_phy(void)
+{
+ /*
+ * Initialize ethernet HW addresses prior to starting Linux,
+ * needed for nfsroot.
+ * TODO: We need to investigate if that is really necessary.
+ */
+ eth_init(gd->bd);
+}
+#endif
+
+int board_eth_init(bd_t *bis)
+{
+ int rc = 0;
+ int num = 0;
+#ifdef CONFIG_MACB
+ rc = macb_eth_initialize(0,
+ (void *)AT91_EMAC_BASE,
+ CONFIG_SYS_PHY_ID);
+ if (!rc)
+ num++;
+#endif
+#ifdef CONFIG_ENC28J60
+ rc = enc28j60_initialize(ENC_SPI_BUS, ENC_CS_NUM,
+ ENC_SPI_CLOCK, SPI_MODE_0);
+ if (!rc)
+ num++;
+# ifdef CONFIG_ENC28J60_2
+ rc = enc28j60_initialize(ENC_SPI_BUS, ENC_CS_NUM+1,
+ ENC_SPI_CLOCK, SPI_MODE_0);
+ if (!rc)
+ num++;
+# ifdef CONFIG_ENC28J60_3
+ rc = enc28j60_initialize(ENC_SPI_BUS, ENC_CS_NUM+2,
+ ENC_SPI_CLOCK, SPI_MODE_0);
+ if (!rc)
+ num++;
+# endif
+# endif
+#endif
+ return num;
+}
+
+/*
+ * I2C access functions
+ *
+ * Note:
+ * We need to access Bus 0 before relocation to access the
+ * environment settings.
+ * However i2c_get_bus_num() cannot be called before
+ * relocation.
+ */
+#ifdef CONFIG_SOFT_I2C
+void iic_init(void)
+{
+ /* ports are now initialized in board_early_init_f() */
+}
+
+int iic_read(void)
+{
+ switch ((gd->flags & GD_FLG_RELOC) ? i2c_get_bus_num() : 0) {
+ case 0:
+ return at91_get_pio_value(I2C0_PORT, SDA0_PIN);
+ case 1:
+ return at91_get_pio_value(I2C1_PORT, SDA1_PIN);
+ }
+ return 1;
+}
+
+void iic_sda(int bit)
+{
+ switch ((gd->flags & GD_FLG_RELOC) ? i2c_get_bus_num() : 0) {
+ case 0:
+ at91_set_pio_value(I2C0_PORT, SDA0_PIN, bit);
+ break;
+ case 1:
+ at91_set_pio_value(I2C1_PORT, SDA1_PIN, bit);
+ break;
+ }
+}
+
+void iic_scl(int bit)
+{
+ switch ((gd->flags & GD_FLG_RELOC) ? i2c_get_bus_num() : 0) {
+ case 0:
+ at91_set_pio_value(I2C0_PORT, SCL0_PIN, bit);
+ break;
+ case 1:
+ at91_set_pio_value(I2C1_PORT, SCL1_PIN, bit);
+ break;
+ }
+}
+
+#endif
diff --git a/boards.cfg b/boards.cfg
index 6c2a667..7373a6e 100644
--- a/boards.cfg
+++ b/boards.cfg
@@ -47,6 +47,8 @@ cm4008 arm arm920t - - ks8695
cm41xx arm arm920t - - ks8695
VCMA9 arm arm920t vcma9 mpl s3c24x0
netstar arm arm925t
+top9000eval_xe arm arm926ejs top9000 emk at91 top9000:EVAL9000
+top9000su_xe arm arm926ejs top9000 emk at91 top9000:SU9000
meesc arm arm926ejs - esd at91
otc570 arm arm926ejs - esd at91
pm9261 arm arm926ejs - ronetix at91
diff --git a/include/configs/top9000.h b/include/configs/top9000.h
new file mode 100644
index 0000000..ff3933b
--- /dev/null
+++ b/include/configs/top9000.h
@@ -0,0 +1,314 @@
+/*
+ * (C) Copyright 2010
+ * Reinhard Meyer, EMK Elektronik, reinhard.meyer(a)emk-elektronik.de
+ *
+ * Configuation settings for the TOP9000 CPU module with AT91SAM9XE.
+ *
+ * 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
+ */
+/*
+ * top9000 with at91sam9xe256 or at91sam9xe512
+ *
+ * Initial Bootloader is in embedded flash.
+ * Vital Product Data, U-Boot Environment are in I2C-EEPROM.
+ * U-Boot is in embedded flash, a backup U-Boot can be in NAND flash.
+ * kernel and file system are either in NAND flash or on a micro SD card.
+ * NAND flash is optional.
+ * I2C EEPROM is never optional.
+ * SPI FRAM is optional.
+ * SPI ENC28J60 is optional.
+ * 16 or 32 bit wide SDRAM.
+ */
+#ifndef __CONFIG_H
+#define __CONFIG_H
+
+/*
+ * Warning: changing CONFIG_SYS_TEXT_BASE requires
+ * adapting the initial boot program
+ */
+#define CONFIG_SYS_TEXT_BASE 0x21f00000 /* 31 MB into RAM */
+
+/* Command line configuration */
+#include <config_cmd_default.h>
+#undef CONFIG_CMD_FPGA
+#undef CONFIG_CMD_SETGETDCR
+#undef CONFIG_CMD_XIMG
+#define CONFIG_CMD_ASKENV
+#define CONFIG_SYS_CBSIZE 256
+#define CONFIG_SYS_MAXARGS 16
+#define CONFIG_SYS_PBSIZE \
+ (CONFIG_SYS_CBSIZE + sizeof(CONFIG_SYS_PROMPT) + 16)
+#define CONFIG_SYS_PROMPT "TOP9000> "
+#define CONFIG_SYS_LONGHELP
+#define CONFIG_CMDLINE_EDITING
+#define CONFIG_CMD_BDI
+#define CONFIG_CMD_CACHE
+
+/* ARM asynchronous clock */
+#define CONFIG_SYS_AT91_MAIN_CLOCK 18432000 /* 18.432 MHz xtal */
+#define CONFIG_SYS_HZ 1000
+
+/* SoC */
+#define CONFIG_ARM926EJS /* ARM926EJS Core */
+#define CONFIG_AT91FAMILY /* it's a member of AT91 */
+#define CONFIG_AT91SAM9260 /* Atmel AT91SAM9260 based SoC */
+#define CONFIG_AT91SAM9XE
+
+/* Misc CPU related */
+#define CONFIG_AT91_LEGACY
+#define CONFIG_ARCH_CPU_INIT
+#undef CONFIG_USE_IRQ /* we don't need IRQ/FIQ stuff */
+#define CONFIG_CMDLINE_TAG /* enable passing of ATAGs */
+#define CONFIG_SETUP_MEMORY_TAGS
+#define CONFIG_INITRD_TAG
+#define CONFIG_SKIP_LOWLEVEL_INIT
+#define CONFIG_BOARD_EARLY_INIT_F
+#define CONFIG_DISPLAY_CPUINFO
+#define CONFIG_AT91RESET_EXTRST /* assert external reset */
+
+/* general purpose I/O */
+#define CONFIG_AT91_GPIO
+#define CONFIG_AT91_GPIO_PULLUP 1 /* keep pullups on peripheral pins */
+
+/* serial console */
+#define CONFIG_ATMEL_USART
+#define CONFIG_USART3 /* USART 3 is DBGU !!! */
+#define CONFIG_BAUDRATE 115200
+#define CONFIG_SYS_BAUDRATE_TABLE {115200 , 19200, 38400, 57600, 9600 }
+
+/* SD/MMC card */
+#define CONFIG_MMC
+#define CONFIG_GENERIC_MMC
+#define CONFIG_GENERIC_ATMEL_MCI
+#define CONFIG_SYS_MMC_CD_PIN AT91_PIN_PC9
+#define CONFIG_CMD_MMC
+
+/* Ethernet */
+#define CONFIG_MACB
+#define CONFIG_SYS_PHY_ID 1
+#define CONFIG_RMII
+#define CONFIG_NET_MULTI
+#define CONFIG_NET_RETRY_COUNT 20
+
+/* real time clock */
+#define CONFIG_RTC_AT91SAM9_RTT
+#define CONFIG_CMD_DATE
+
+#if defined(CONFIG_AT91SAM9XE)
+/*
+ * NOR flash - use embedded flash of SAM9XE256/512
+ * U-Boot will not fit into 128K !
+ * 2010.09 will not fit into 256K with all options enabled !
+ *
+ * Layout:
+ * 16kB 1st Bootloader
+ * Rest U-Boot
+ * the first sector (16kB) of EFLASH cannot be unprotected
+ * with u-boot commands
+ */
+# define CONFIG_AT91_EFLASH
+# define CONFIG_SYS_FLASH_BASE 0x200000
+# define CONFIG_SYS_MAX_FLASH_SECT 32
+# define CONFIG_SYS_MAX_FLASH_BANKS 1
+# define CONFIG_SYS_FLASH_PROTECTION
+# define CONFIG_EFLASH_PROTSECTORS 1 /* protect first sector */
+#endif
+
+/* SPI */
+#define CONFIG_ATMEL_SPI
+#define CONFIG_CMD_SPI
+
+/* RAMTRON FRAM */
+#define CONFIG_CMD_SF
+#define CONFIG_ATMEL_SPI0 /* SPI used for FRAM is SPI0 */
+#define FRAM_SPI_BUS 0
+#define FRAM_CS_NUM 0
+#define CONFIG_SPI_FLASH /* RAMTRON FRAM on SPI bus */
+#define CONFIG_SPI_FRAM_RAMTRON
+#define CONFIG_SF_DEFAULT_SPEED 1000000 /* be conservative here... */
+#define CONFIG_SF_DEFAULT_MODE SPI_MODE_0
+#define CONFIG_SPI_FRAM_RAMTRON_NON_JEDEC "FM25H20"
+
+/* Microchip ENC28J60 (second LAN) */
+#if defined(CONFIG_EVAL9000)
+# define CONFIG_ENC28J60
+# define CONFIG_ATMEL_SPI1 /* SPI used for ENC28J60 is SPI1 */
+# define ENC_SPI_BUS 1
+# define ENC_CS_NUM 0
+# define ENC_SPI_CLOCK 1000000
+#endif /* CONFIG_EVAL9000 */
+
+/*
+ * SDRAM: 1 bank, min 32, max 128 MB
+ * Initialized before u-boot gets started.
+ */
+#define CONFIG_NR_DRAM_BANKS 1
+#define CONFIG_SYS_SDRAM_BASE 0x20000000
+#define CONFIG_SYS_SDRAM_SIZE 0x08000000
+#define CONFIG_SYS_MEMTEST_START CONFIG_SYS_SDRAM_BASE
+#define CONFIG_SYS_MEMTEST_END 0x21e00000
+#define CONFIG_SYS_LOAD_ADDR \
+ (CONFIG_SYS_SDRAM_BASE + 0x01000000)
+/*
+ * Initial stack pointer: 16k - GENERATED_GBL_DATA_SIZE in internal SRAM,
+ * leaving the correct space for initial global data structure above
+ * that address while providing maximum stack area below.
+ */
+#define CONFIG_SYS_INIT_SP_ADDR \
+ (0x00300000 + 0x4000 - GENERATED_GBL_DATA_SIZE)
+
+/*
+ * NAND flash: 256 MB (optional)
+ *
+ * Layout:
+ * 640kB: u-boot (includes space for spare sectors, handled by
+ * initial loader)
+ * 2MB: kernel
+ * rest: file system
+ */
+#define CONFIG_NAND_ATMEL
+#define CONFIG_SYS_MAX_NAND_DEVICE 1
+#define CONFIG_SYS_NAND_BASE 0x40000000
+#define CONFIG_SYS_NAND_DBW_8
+#define CONFIG_SYS_NAND_MASK_ALE (1 << 21)
+#define CONFIG_SYS_NAND_MASK_CLE (1 << 22)
+#define CONFIG_SYS_NAND_ENABLE_PIN AT91_PIN_PC14
+#define CONFIG_SYS_NAND_READY_PIN AT91_PIN_PC13
+#define CONFIG_CMD_NAND
+
+/* USB */
+#define CONFIG_USB_ATMEL
+#define CONFIG_USB_OHCI_NEW
+#define CONFIG_DOS_PARTITION
+#define CONFIG_SYS_USB_OHCI_CPU_INIT
+#define CONFIG_SYS_USB_OHCI_REGS_BASE 0x00500000
+#define CONFIG_SYS_USB_OHCI_SLOT_NAME "top9000"
+#define CONFIG_SYS_USB_OHCI_MAX_ROOT_PORTS 2
+#define CONFIG_USB_STORAGE
+#define CONFIG_CMD_USB
+
+/* I2C support must always be enabled */
+#define CONFIG_SOFT_I2C
+#define CONFIG_CMD_I2C
+#define CONFIG_SYS_I2C_SPEED 400000
+#define CONFIG_SYS_I2C_SLAVE 0x7F
+#define CONFIG_I2C_MULTI_BUS
+#define I2C0_PORT AT91_PIO_PORTA
+#define SDA0_PIN 23
+#define SCL0_PIN 24
+#define I2C1_PORT AT91_PIO_PORTB
+#define SDA1_PIN 12
+#define SCL1_PIN 13
+#define I2C_SOFT_DECLARATIONS void iic_init(void);\
+ int iic_read(void);\
+ void iic_sda(int);\
+ void iic_scl(int);
+#define I2C_ACTIVE
+#define I2C_TRISTATE
+#define I2C_INIT iic_init()
+#define I2C_READ iic_read()
+#define I2C_SDA(bit) iic_sda(bit)
+#define I2C_SCL(bit) iic_scl(bit)
+#define I2C_DELAY udelay(3)
+/* EEPROM configuration */
+#define CONFIG_SYS_EEPROM_PAGE_WRITE_BITS 5
+#define CONFIG_SYS_EEPROM_PAGE_WRITE_DELAY_MS 5
+#define CONFIG_SYS_I2C_EEPROM_ADDR_LEN 2
+#define CONFIG_SYS_EEPROM_SIZE 0x2000
+#define CONFIG_SYS_I2C_EEPROM_ADDR 0x57
+/* later: #define CONFIG_I2C_ENV_EEPROM_BUS 0 */
+/* ENV is always in I2C-EEPROM */
+#define CONFIG_ENV_IS_IN_EEPROM
+#define CONFIG_ENV_OFFSET 0x1000
+#define CONFIG_ENV_SIZE 0x0f00
+/* VPD settings */
+#define CONFIG_SYS_I2C_FACT_ADDR 0x57
+#define CONFIG_SYS_FACT_OFFSET 0x1F00
+#define CONFIG_SYS_FACT_SIZE 0x0100
+/* later: #define CONFIG_MISC_INIT_R */
+/* define the next only if you want to allow users to enter VPD data */
+#define CONFIG_SYS_FACT_ENTRY
+#ifndef __ASSEMBLY__
+extern void read_factory_r(void);
+#endif
+
+/*
+ * Only interrupt autoboot if <space> is pressed. Otherwise, garbage
+ * data on the serial line may interrupt the boot sequence.
+ */
+#define CONFIG_BOOTDELAY 1
+#define CONFIG_AUTOBOOT
+#define CONFIG_AUTOBOOT_KEYED
+#define CONFIG_AUTOBOOT_PROMPT \
+ "Press SPACE to abort autoboot in %d seconds\n", bootdelay
+#define CONFIG_AUTOBOOT_DELAY_STR "d"
+#define CONFIG_AUTOBOOT_STOP_STR " "
+
+/*
+ * add filesystem commands if we have at least 1 storage
+ * media with filesystem
+ */
+#if defined(CONFIG_NAND_ATMEL) \
+ || defined(CONFIG_USB_ATMEL) \
+ || defined(CONFIG_MMC)
+# define CONFIG_DOS_PARTITION
+# define CONFIG_CMD_FAT
+# define CONFIG_CMD_EXT2
+/* later: #define CONFIG_CMD_JFFS2 */
+#endif
+
+/* add NET commands if we have at least 1 LAN */
+#if defined(CONFIG_MACB) || defined(CONFIG_ENC28J60)
+# define CONFIG_CMD_PING
+# define CONFIG_CMD_DHCP
+# define CONFIG_CMD_MII
+/* is this really needed ? */
+# define CONFIG_RESET_PHY_R
+/* BOOTP options */
+# define CONFIG_BOOTP_BOOTFILESIZE
+# define CONFIG_BOOTP_BOOTPATH
+# define CONFIG_BOOTP_GATEWAY
+# define CONFIG_BOOTP_HOSTNAME
+#endif
+
+/* linux in NAND flash */
+#define CONFIG_BOOTCOUNT_LIMIT 1
+#define CONFIG_BOOTCOMMAND \
+ "nand read 0x21000000 0xA0000 0x200000; bootm"
+#define CONFIG_BOOTARGS \
+ "console=ttyS0,115200 " \
+ "root=/dev/mtdblock2 " \
+ "mtdparts=atmel_nand:" \
+ "640k(uboot)ro," \
+ "2M(linux)," \
+ "16M(root)," \
+ "-(rest) " \
+ "rw "\
+ "rootfstype=jffs2"
+
+/* Size of malloc() pool */
+#define CONFIG_SYS_MALLOC_LEN \
+ ROUND(3 * CONFIG_ENV_SIZE + 128*1024, 0x1000)
+#define CONFIG_STACKSIZE (32*1024)
+#ifdef CONFIG_USE_IRQ
+#error CONFIG_USE_IRQ not supported
+#endif
+
+#endif
+
--
1.5.6.5
1
1
Incremental patch. Should be applied above its v2:
http://lists.denx.de/pipermail/u-boot/2010-April/070729.html
(Sorry for inconvenience. I will use --in-reply-to option next time)
In the patch:
- Fix for hcu4 board;
- post.h - preprocessor conditional inclusions optimization.
Signed-off-by: Michael Zaidman <michael.zaidman(a)gmail.com>
---
include/configs/hcu4.h | 2 +-
include/post.h | 18 +++++-------------
2 files changed, 6 insertions(+), 14 deletions(-)
diff --git a/include/configs/hcu4.h b/include/configs/hcu4.h
index b01f8b1..26992e7 100644
--- a/include/configs/hcu4.h
+++ b/include/configs/hcu4.h
@@ -72,7 +72,7 @@
#define CONFIG_SYS_INIT_RAM_END CONFIG_SYS_OCM_DATA_SIZE
#define CONFIG_SYS_GBL_DATA_SIZE 256 /* num bytes initial data */
#define CONFIG_SYS_GBL_DATA_OFFSET (CONFIG_SYS_INIT_RAM_END - CONFIG_SYS_GBL_DATA_SIZE)
-#define CONFIG_SYS_INIT_SP_OFFSET CONFIG_SYS_POST_WORD_ADDR
+#define CONFIG_SYS_INIT_SP_OFFSET (CONFIG_SYS_GBL_DATA_OFFSET - 0x4)
/*-----------------------------------------------------------------------
* Serial Port
diff --git a/include/post.h b/include/post.h
index 296e1d5..939310b 100644
--- a/include/post.h
+++ b/include/post.h
@@ -35,31 +35,24 @@
#ifdef CONFIG_MPC5xxx
#define _POST_WORD_ADDR (MPC5XXX_SRAM + MPC5XXX_SRAM_POST_SIZE)
-#endif
-#if defined(CONFIG_MPC821) || defined(CONFIG_MPC823) || \
- defined(CONFIG_MPC855) || defined(CONFIG_MPC855T)|| \
- defined(CONFIG_MPC850) || defined(CONFIG_MPC86x)
+#elif defined(CONFIG_8xx)
#define _POST_WORD_ADDR \
(((immap_t *)CONFIG_SYS_IMMR)->im_cpm.cp_dpmem + CPM_POST_WORD_ADDR)
-#endif
-#ifdef CONFIG_MPC8260
+#elif defined(CONFIG_MPC8260)
#include <asm/cpm_8260.h>
#define _POST_WORD_ADDR (CONFIG_SYS_IMMR + CPM_POST_WORD_ADDR)
-#endif
-#ifdef CONFIG_MPC8360
+#elif defined(CONFIG_MPC8360)
#include <asm/immap_qe.h>
#define _POST_WORD_ADDR (CONFIG_SYS_IMMR + CPM_POST_WORD_ADDR)
-#endif
-#ifdef CONFIG_MPC85xx
+#elif defined (CONFIG_MPC85xx)
#include <asm/cpm_85xx.h>
#define _POST_WORD_ADDR (CONFIG_SYS_IMMR + CPM_POST_WORD_ADDR)
-#endif
-#ifdef CONFIG_4xx
+#elif defined (CONFIG_4xx)
#define _POST_WORD_ADDR \
(CONFIG_SYS_OCM_DATA_ADDR + CONFIG_SYS_GBL_DATA_OFFSET - 0x4)
#endif
@@ -67,7 +60,6 @@
#ifndef _POST_WORD_ADDR
#error "_POST_WORD_ADDR currently not implemented for this platform!"
#endif
-
#endif /* CONFIG_SYS_POST_WORD_ADDR */
static inline ulong post_word_load (void)
--
1.6.3.3
4
22

[U-Boot] [PATCH 3/4] UBIFS: Change "ubifs mount" to "ubifsmount" in ubifsls output
by Stefan Roese 03 Dec '10
by Stefan Roese 03 Dec '10
03 Dec '10
Signed-off-by: Stefan Roese <sr(a)denx.de>
---
common/cmd_ubifs.c | 2 +-
1 files changed, 1 insertions(+), 1 deletions(-)
diff --git a/common/cmd_ubifs.c b/common/cmd_ubifs.c
index 30b23d3..9526780 100644
--- a/common/cmd_ubifs.c
+++ b/common/cmd_ubifs.c
@@ -98,7 +98,7 @@ int do_ubifs_ls(cmd_tbl_t *cmdtp, int flag, int argc, char * const argv[])
int ret;
if (!ubifs_mounted) {
- printf("UBIFS not mounted, use ubifs mount to mount volume first!\n");
+ printf("UBIFS not mounted, use ubifsmount to mount volume first!\n");
return -1;
}
--
1.7.3.2
2
2

[U-Boot] [PATCH 2/4] UBIFS: Add ubifsumount command to unmount an active volume
by Stefan Roese 03 Dec '10
by Stefan Roese 03 Dec '10
03 Dec '10
This new ubifsumount command allows the user to unmount a previously
mounted UBIFS volume.
Signed-off-by: Stefan Roese <sr(a)denx.de>
---
common/cmd_ubifs.c | 31 +++++++++++++++++++++++++++++++
fs/ubifs/super.c | 2 +-
2 files changed, 32 insertions(+), 1 deletions(-)
diff --git a/common/cmd_ubifs.c b/common/cmd_ubifs.c
index a0ec184..30b23d3 100644
--- a/common/cmd_ubifs.c
+++ b/common/cmd_ubifs.c
@@ -33,12 +33,17 @@
#include <config.h>
#include <command.h>
+#include "../fs/ubifs/ubifs.h"
+
static int ubifs_initialized;
static int ubifs_mounted;
+extern struct super_block *ubifs_sb;
+
/* Prototypes */
int ubifs_init(void);
int ubifs_mount(char *vol_name);
+void ubifs_umount(struct ubifs_info *c);
int ubifs_ls(char *dir_name);
int ubifs_load(char *filename, u32 addr, u32 size);
@@ -67,6 +72,26 @@ int do_ubifs_mount(cmd_tbl_t *cmdtp, int flag, int argc, char * const argv[])
return 0;
}
+int do_ubifs_umount(cmd_tbl_t *cmdtp, int flag, int argc, char * const argv[])
+{
+ if (argc != 1)
+ return cmd_usage(cmdtp);
+
+ if (ubifs_initialized == 0) {
+ printf("No UBIFS volume mounted!\n");
+ return -1;
+ }
+
+ if (ubifs_sb)
+ ubifs_umount(ubifs_sb->s_fs_info);
+
+ ubifs_sb = NULL;
+ ubifs_mounted = 0;
+ ubifs_initialized = 0;
+
+ return 0;
+}
+
int do_ubifs_ls(cmd_tbl_t *cmdtp, int flag, int argc, char * const argv[])
{
char *filename = "/";
@@ -132,6 +157,12 @@ U_BOOT_CMD(
);
U_BOOT_CMD(
+ ubifsumount, 1, 0, do_ubifs_umount,
+ "unmount UBIFS volume",
+ " - unmount current volume"
+);
+
+U_BOOT_CMD(
ubifsls, 2, 0, do_ubifs_ls,
"list files in a directory",
"[directory]\n"
diff --git a/fs/ubifs/super.c b/fs/ubifs/super.c
index 39e3efe..63b2164 100644
--- a/fs/ubifs/super.c
+++ b/fs/ubifs/super.c
@@ -824,7 +824,7 @@ out_free:
* through mounting (error path cleanup function). So it has to make sure the
* resource was actually allocated before freeing it.
*/
-static void ubifs_umount(struct ubifs_info *c)
+void ubifs_umount(struct ubifs_info *c)
{
dbg_gen("un-mounting UBI device %d, volume %d", c->vi.ubi_num,
c->vi.vol_id);
--
1.7.3.2
2
2

03 Dec '10
1. Fix preprocessor statements
2. Clean coding style
Signed-off-by: Michal Simek <monstr(a)monstr.eu>
---
include/configs/microblaze-generic.h | 227 ++++++++++++++++++----------------
1 files changed, 123 insertions(+), 104 deletions(-)
diff --git a/include/configs/microblaze-generic.h b/include/configs/microblaze-generic.h
index 28cee47..9301a6b 100644
--- a/include/configs/microblaze-generic.h
+++ b/include/configs/microblaze-generic.h
@@ -1,5 +1,5 @@
/*
- * (C) Copyright 2007-2008 Michal Simek
+ * (C) Copyright 2007-2010 Michal Simek
*
* Michal SIMEK <monstr(a)monstr.eu>
*
@@ -27,31 +27,33 @@
#include "../board/xilinx/microblaze-generic/xparameters.h"
-#define CONFIG_MICROBLAZE 1 /* MicroBlaze CPU */
+/* MicroBlaze CPU */
+#define CONFIG_MICROBLAZE 1
#define MICROBLAZE_V5 1
/* uart */
#ifdef XILINX_UARTLITE_BASEADDR
- #define CONFIG_XILINX_UARTLITE
- #define CONFIG_SERIAL_BASE XILINX_UARTLITE_BASEADDR
- #define CONFIG_BAUDRATE XILINX_UARTLITE_BAUDRATE
- #define CONFIG_SYS_BAUDRATE_TABLE { CONFIG_BAUDRATE }
- #define CONSOLE_ARG "console=console=ttyUL0,115200\0"
+# define CONFIG_XILINX_UARTLITE
+# define CONFIG_SERIAL_BASE XILINX_UARTLITE_BASEADDR
+# define CONFIG_BAUDRATE XILINX_UARTLITE_BAUDRATE
+# define CONFIG_SYS_BAUDRATE_TABLE { CONFIG_BAUDRATE }
+# define CONSOLE_ARG "console=console=ttyUL0,115200\0"
#elif XILINX_UART16550_BASEADDR
- #define CONFIG_SYS_NS16550 1
- #define CONFIG_SYS_NS16550_SERIAL
- #define CONFIG_SYS_NS16550_REG_SIZE -4
- #define CONFIG_CONS_INDEX 1
- #define CONFIG_SYS_NS16550_COM1 (XILINX_UART16550_BASEADDR + 0x1000 + 0x3)
- #define CONFIG_SYS_NS16550_CLK XILINX_UART16550_CLOCK_HZ
- #define CONFIG_BAUDRATE 115200
-
- /* The following table includes the supported baudrates */
- #define CONFIG_SYS_BAUDRATE_TABLE \
- {300, 600, 1200, 2400, 4800, 9600, 19200, 38400, 57600, 115200, 230400}
- #define CONSOLE_ARG "console=console=ttyS0,115200\0"
+# define CONFIG_SYS_NS16550 1
+# define CONFIG_SYS_NS16550_SERIAL
+# define CONFIG_SYS_NS16550_REG_SIZE -4
+# define CONFIG_CONS_INDEX 1
+# define CONFIG_SYS_NS16550_COM1 \
+ (XILINX_UART16550_BASEADDR + 0x1000 + 0x3)
+# define CONFIG_SYS_NS16550_CLK XILINX_UART16550_CLOCK_HZ
+# define CONFIG_BAUDRATE 115200
+
+/* The following table includes the supported baudrates */
+# define CONFIG_SYS_BAUDRATE_TABLE \
+ {300, 600, 1200, 2400, 4800, 9600, 19200, 38400, 57600, 115200, 230400}
+# define CONSOLE_ARG "console=console=ttyS0,115200\0"
#else
- #error Undefined uart
+# error Undefined uart
#endif
/* setting reset address */
@@ -59,41 +61,41 @@
/* ethernet */
#ifdef XILINX_EMACLITE_BASEADDR
- #define CONFIG_XILINX_EMACLITE 1
- #define CONFIG_SYS_ENET
+# define CONFIG_XILINX_EMACLITE 1
+# define CONFIG_SYS_ENET
#elif XILINX_LLTEMAC_BASEADDR
- #define CONFIG_XILINX_LL_TEMAC 1
- #define CONFIG_SYS_ENET
+# define CONFIG_XILINX_LL_TEMAC 1
+# define CONFIG_SYS_ENET
#endif
#undef ET_DEBUG
/* gpio */
#ifdef XILINX_GPIO_BASEADDR
- #define CONFIG_SYS_GPIO_0 1
- #define CONFIG_SYS_GPIO_0_ADDR XILINX_GPIO_BASEADDR
+# define CONFIG_SYS_GPIO_0 1
+# define CONFIG_SYS_GPIO_0_ADDR XILINX_GPIO_BASEADDR
#endif
/* interrupt controller */
#ifdef XILINX_INTC_BASEADDR
- #define CONFIG_SYS_INTC_0 1
- #define CONFIG_SYS_INTC_0_ADDR XILINX_INTC_BASEADDR
- #define CONFIG_SYS_INTC_0_NUM XILINX_INTC_NUM_INTR_INPUTS
+# define CONFIG_SYS_INTC_0 1
+# define CONFIG_SYS_INTC_0_ADDR XILINX_INTC_BASEADDR
+# define CONFIG_SYS_INTC_0_NUM XILINX_INTC_NUM_INTR_INPUTS
#endif
/* timer */
#ifdef XILINX_TIMER_BASEADDR
- #if (XILINX_TIMER_IRQ != -1)
- #define CONFIG_SYS_TIMER_0 1
- #define CONFIG_SYS_TIMER_0_ADDR XILINX_TIMER_BASEADDR
- #define CONFIG_SYS_TIMER_0_IRQ XILINX_TIMER_IRQ
- #define FREQUENCE XILINX_CLOCK_FREQ
- #define CONFIG_SYS_TIMER_0_PRELOAD ( FREQUENCE/1000 )
- #endif
+# if (XILINX_TIMER_IRQ != -1)
+# define CONFIG_SYS_TIMER_0 1
+# define CONFIG_SYS_TIMER_0_ADDR XILINX_TIMER_BASEADDR
+# define CONFIG_SYS_TIMER_0_IRQ XILINX_TIMER_IRQ
+# define FREQUENCE XILINX_CLOCK_FREQ
+# define CONFIG_SYS_TIMER_0_PRELOAD ( FREQUENCE/1000 )
+# endif
#elif XILINX_CLOCK_FREQ
- #define CONFIG_XILINX_CLOCK_FREQ XILINX_CLOCK_FREQ
+# define CONFIG_XILINX_CLOCK_FREQ XILINX_CLOCK_FREQ
#else
- #error BAD CLOCK FREQ
+# error BAD CLOCK FREQ
#endif
/* FSL */
/* #define CONFIG_SYS_FSL_2 */
@@ -135,15 +137,20 @@
/* global pointer */
#define CONFIG_SYS_GBL_DATA_SIZE 128 /* size of global data */
/* start of global data */
-#define CONFIG_SYS_GBL_DATA_OFFSET (CONFIG_SYS_SDRAM_BASE + CONFIG_SYS_SDRAM_SIZE - CONFIG_SYS_GBL_DATA_SIZE)
+#define CONFIG_SYS_GBL_DATA_OFFSET \
+ (CONFIG_SYS_SDRAM_BASE + CONFIG_SYS_SDRAM_SIZE \
+ - CONFIG_SYS_GBL_DATA_SIZE)
/* monitor code */
-#define SIZE 0x40000
+#define SIZE 0x40000
#define CONFIG_SYS_MONITOR_LEN (SIZE - CONFIG_SYS_GBL_DATA_SIZE)
-#define CONFIG_SYS_MONITOR_BASE (CONFIG_SYS_GBL_DATA_OFFSET - CONFIG_SYS_MONITOR_LEN)
-#define CONFIG_SYS_MONITOR_END (CONFIG_SYS_MONITOR_BASE + CONFIG_SYS_MONITOR_LEN)
+#define CONFIG_SYS_MONITOR_BASE \
+ (CONFIG_SYS_GBL_DATA_OFFSET - CONFIG_SYS_MONITOR_LEN)
+#define CONFIG_SYS_MONITOR_END \
+ (CONFIG_SYS_MONITOR_BASE + CONFIG_SYS_MONITOR_LEN)
#define CONFIG_SYS_MALLOC_LEN SIZE
-#define CONFIG_SYS_MALLOC_BASE (CONFIG_SYS_MONITOR_BASE - CONFIG_SYS_MALLOC_LEN)
+#define CONFIG_SYS_MALLOC_BASE \
+ (CONFIG_SYS_MONITOR_BASE - CONFIG_SYS_MALLOC_LEN)
/* stack */
#define CONFIG_SYS_INIT_SP_OFFSET CONFIG_SYS_MALLOC_BASE
@@ -152,55 +159,62 @@
#define FLASH
#ifdef FLASH
- #define CONFIG_SYS_FLASH_BASE XILINX_FLASH_START
- #define CONFIG_SYS_FLASH_SIZE XILINX_FLASH_SIZE
- #define CONFIG_SYS_FLASH_CFI 1
- #define CONFIG_FLASH_CFI_DRIVER 1
- #define CONFIG_SYS_FLASH_EMPTY_INFO 1 /* ?empty sector */
- #define CONFIG_SYS_MAX_FLASH_BANKS 1 /* max number of memory banks */
- #define CONFIG_SYS_MAX_FLASH_SECT 512 /* max number of sectors on one chip */
- #define CONFIG_SYS_FLASH_PROTECTION /* hardware flash protection */
-
- #ifdef RAMENV
- #define CONFIG_ENV_IS_NOWHERE 1
- #define CONFIG_ENV_SIZE 0x1000
- #define CONFIG_ENV_ADDR (CONFIG_SYS_MONITOR_BASE - CONFIG_ENV_SIZE)
-
- #else /* !RAMENV */
- #define CONFIG_ENV_IS_IN_FLASH 1
- #define CONFIG_ENV_SECT_SIZE 0x20000 /* 128K(one sector) for env */
- #define CONFIG_ENV_ADDR (CONFIG_SYS_FLASH_BASE + (2 * CONFIG_ENV_SECT_SIZE))
- #define CONFIG_ENV_SIZE 0x20000
- #endif /* !RAMBOOT */
+# define CONFIG_SYS_FLASH_BASE XILINX_FLASH_START
+# define CONFIG_SYS_FLASH_SIZE XILINX_FLASH_SIZE
+# define CONFIG_SYS_FLASH_CFI 1
+# define CONFIG_FLASH_CFI_DRIVER 1
+/* ?empty sector */
+# define CONFIG_SYS_FLASH_EMPTY_INFO 1
+/* max number of memory banks */
+# define CONFIG_SYS_MAX_FLASH_BANKS 1
+/* max number of sectors on one chip */
+# define CONFIG_SYS_MAX_FLASH_SECT 512
+/* hardware flash protection */
+# define CONFIG_SYS_FLASH_PROTECTION
+
+# ifdef RAMENV
+# define CONFIG_ENV_IS_NOWHERE 1
+# define CONFIG_ENV_SIZE 0x1000
+# define CONFIG_ENV_ADDR (CONFIG_SYS_MONITOR_BASE - CONFIG_ENV_SIZE)
+
+# else /* !RAMENV */
+# define CONFIG_ENV_IS_IN_FLASH 1
+/* 128K(one sector) for env */
+# define CONFIG_ENV_SECT_SIZE 0x20000
+# define CONFIG_ENV_ADDR \
+ (CONFIG_SYS_FLASH_BASE + (2 * CONFIG_ENV_SECT_SIZE))
+# define CONFIG_ENV_SIZE 0x20000
+# endif /* !RAMBOOT */
#else /* !FLASH */
- /* ENV in RAM */
- #define CONFIG_SYS_NO_FLASH 1
- #define CONFIG_ENV_IS_NOWHERE 1
- #define CONFIG_ENV_SIZE 0x1000
- #define CONFIG_ENV_ADDR (CONFIG_SYS_MONITOR_BASE - CONFIG_ENV_SIZE)
- #define CONFIG_SYS_FLASH_PROTECTION /* hardware flash protection */
+/* ENV in RAM */
+# define CONFIG_SYS_NO_FLASH 1
+# define CONFIG_ENV_IS_NOWHERE 1
+# define CONFIG_ENV_SIZE 0x1000
+# define CONFIG_ENV_ADDR (CONFIG_SYS_MONITOR_BASE - CONFIG_ENV_SIZE)
+/* hardware flash protection */
+# define CONFIG_SYS_FLASH_PROTECTION
#endif /* !FLASH */
/* system ace */
#ifdef XILINX_SYSACE_BASEADDR
- #define CONFIG_SYSTEMACE
- /* #define DEBUG_SYSTEMACE */
- #define SYSTEMACE_CONFIG_FPGA
- #define CONFIG_SYS_SYSTEMACE_BASE XILINX_SYSACE_BASEADDR
- #define CONFIG_SYS_SYSTEMACE_WIDTH XILINX_SYSACE_MEM_WIDTH
- #define CONFIG_DOS_PARTITION
+# define CONFIG_SYSTEMACE
+/* #define DEBUG_SYSTEMACE */
+# define SYSTEMACE_CONFIG_FPGA
+# define CONFIG_SYS_SYSTEMACE_BASE XILINX_SYSACE_BASEADDR
+# define CONFIG_SYS_SYSTEMACE_WIDTH XILINX_SYSACE_MEM_WIDTH
+# define CONFIG_DOS_PARTITION
#endif
#if defined(XILINX_USE_ICACHE)
- #define CONFIG_ICACHE
+# define CONFIG_ICACHE
#else
- #undef CONFIG_ICACHE
+# undef CONFIG_ICACHE
#endif
#if defined(XILINX_USE_DCACHE)
- #define CONFIG_DCACHE
+# define CONFIG_DCACHE
#else
- #undef CONFIG_DCACHE
+# undef CONFIG_DCACHE
#endif
/*
@@ -222,37 +236,37 @@
#define CONFIG_CMD_ECHO
#if defined(CONFIG_DCACHE) || defined(CONFIG_ICACHE)
- #define CONFIG_CMD_CACHE
+# define CONFIG_CMD_CACHE
#else
- #undef CONFIG_CMD_CACHE
+# undef CONFIG_CMD_CACHE
#endif
#ifndef CONFIG_SYS_ENET
- #undef CONFIG_CMD_NET
+# undef CONFIG_CMD_NET
#else
- #define CONFIG_CMD_PING
- #define CONFIG_CMD_DHCP
+# define CONFIG_CMD_PING
+# define CONFIG_CMD_DHCP
#endif
#if defined(CONFIG_SYSTEMACE)
- #define CONFIG_CMD_EXT2
- #define CONFIG_CMD_FAT
+# define CONFIG_CMD_EXT2
+# define CONFIG_CMD_FAT
#endif
#if defined(FLASH)
- #define CONFIG_CMD_ECHO
- #define CONFIG_CMD_FLASH
- #define CONFIG_CMD_IMLS
- #define CONFIG_CMD_JFFS2
-
- #if !defined(RAMENV)
- #define CONFIG_CMD_SAVEENV
- #define CONFIG_CMD_SAVES
- #endif
+# define CONFIG_CMD_ECHO
+# define CONFIG_CMD_FLASH
+# define CONFIG_CMD_IMLS
+# define CONFIG_CMD_JFFS2
+
+# if !defined(RAMENV)
+# define CONFIG_CMD_SAVEENV
+# define CONFIG_CMD_SAVES
+# endif
#else
- #undef CONFIG_CMD_IMLS
- #undef CONFIG_CMD_FLASH
- #undef CONFIG_CMD_JFFS2
+# undef CONFIG_CMD_IMLS
+# undef CONFIG_CMD_FLASH
+# undef CONFIG_CMD_JFFS2
#endif
#if defined(CONFIG_CMD_JFFS2)
@@ -270,11 +284,16 @@
/* Miscellaneous configurable options */
#define CONFIG_SYS_PROMPT "U-Boot-mONStR> "
-#define CONFIG_SYS_CBSIZE 512 /* size of console buffer */
-#define CONFIG_SYS_PBSIZE (CONFIG_SYS_CBSIZE + sizeof(CONFIG_SYS_PROMPT) + 16) /* print buffer size */
-#define CONFIG_SYS_MAXARGS 15 /* max number of command args */
+/* size of console buffer */
+#define CONFIG_SYS_CBSIZE 512
+ /* print buffer size */
+#define CONFIG_SYS_PBSIZE \
+ (CONFIG_SYS_CBSIZE + sizeof(CONFIG_SYS_PROMPT) + 16)
+/* max number of command args */
+#define CONFIG_SYS_MAXARGS 15
#define CONFIG_SYS_LONGHELP
-#define CONFIG_SYS_LOAD_ADDR XILINX_RAM_START /* default load address */
+/* default load address */
+#define CONFIG_SYS_LOAD_ADDR XILINX_RAM_START
#define CONFIG_BOOTDELAY -1 /* -1 disables auto-boot */
#define CONFIG_BOOTARGS "root=romfs"
@@ -291,7 +310,7 @@
#define CONFIG_PREBOOT "echo U-BOOT for ${hostname};setenv preboot;echo"
-#define CONFIG_EXTRA_ENV_SETTINGS "unlock=yes\0" /* hardware flash protection */\
+#define CONFIG_EXTRA_ENV_SETTINGS "unlock=yes\0" \
"nor0=flash-0\0"\
"mtdparts=mtdparts=flash-0:"\
"256k(u-boot),256k(env),3m(kernel),"\
@@ -302,7 +321,7 @@
/* Use the HUSH parser */
#define CONFIG_SYS_HUSH_PARSER
#ifdef CONFIG_SYS_HUSH_PARSER
-#define CONFIG_SYS_PROMPT_HUSH_PS2 "> "
+# define CONFIG_SYS_PROMPT_HUSH_PS2 "> "
#endif
#endif /* __CONFIG_H */
--
1.5.5.6
3
9
Use C structs for registers, and use readl/writel instead of custom
accessors.
Acked-by: Michael Brandt <michael.brandt(a)stericsson.com>
Signed-off-by: Rabin Vincent <rabin.vincent(a)stericsson.com>
---
drivers/serial/serial_pl01x.c | 56 ++++++++++++++++++++++------------------
drivers/serial/serial_pl01x.h | 41 ++++++++++++++++--------------
2 files changed, 53 insertions(+), 44 deletions(-)
diff --git a/drivers/serial/serial_pl01x.c b/drivers/serial/serial_pl01x.c
index c645cef..d2609d6 100644
--- a/drivers/serial/serial_pl01x.c
+++ b/drivers/serial/serial_pl01x.c
@@ -29,12 +29,10 @@
#include <common.h>
#include <watchdog.h>
+#include <asm/io.h>
#include "serial_pl01x.h"
-#define IO_WRITE(addr, val) (*(volatile unsigned int *)(addr) = (val))
-#define IO_READ(addr) (*(volatile unsigned int *)(addr))
-
/*
* Integrator AP has two UARTs, we use the first one, at 38400-8-N-1
* Integrator CP has two UARTs, use the first one, at 38400-8-N-1
@@ -49,16 +47,22 @@ static void pl01x_putc (int portnum, char c);
static int pl01x_getc (int portnum);
static int pl01x_tstc (int portnum);
+static struct pl01x_regs *pl01x_get_regs(int portnum)
+{
+ return (struct pl01x_regs *) port[portnum];
+}
+
#ifdef CONFIG_PL010_SERIAL
int serial_init (void)
{
+ struct pl01x_regs *regs = pl01x_get_regs(CONSOLE_PORT);
unsigned int divisor;
/*
** First, disable everything.
*/
- IO_WRITE (port[CONSOLE_PORT] + UART_PL010_CR, 0x0);
+ writel(0, ®s->pl010_cr);
/*
** Set baud rate
@@ -89,20 +93,18 @@ int serial_init (void)
divisor = UART_PL010_BAUD_38400;
}
- IO_WRITE (port[CONSOLE_PORT] + UART_PL010_LCRM,
- ((divisor & 0xf00) >> 8));
- IO_WRITE (port[CONSOLE_PORT] + UART_PL010_LCRL, (divisor & 0xff));
+ writel((divisor & 0xf00) >> 8, ®s->pl010_lcrm);
+ writel(divisor & 0xff, ®s->pl010_lcrl);
/*
** Set the UART to be 8 bits, 1 stop bit, no parity, fifo enabled.
*/
- IO_WRITE (port[CONSOLE_PORT] + UART_PL010_LCRH,
- (UART_PL010_LCRH_WLEN_8 | UART_PL010_LCRH_FEN));
+ writel(UART_PL010_LCRH_WLEN_8 | UART_PL010_LCRH_FEN, ®s->pl010_lcrh);
/*
** Finally, enable the UART
*/
- IO_WRITE (port[CONSOLE_PORT] + UART_PL010_CR, (UART_PL010_CR_UARTEN));
+ writel(UART_PL010_CR_UARTEN, ®s->pl010_cr);
return 0;
}
@@ -113,6 +115,7 @@ int serial_init (void)
int serial_init (void)
{
+ struct pl01x_regs *regs = pl01x_get_regs(CONSOLE_PORT);
unsigned int temp;
unsigned int divider;
unsigned int remainder;
@@ -121,7 +124,7 @@ int serial_init (void)
/*
** First, disable everything.
*/
- IO_WRITE (port[CONSOLE_PORT] + UART_PL011_CR, 0x0);
+ writel(0, ®s->pl011_cr);
/*
** Set baud rate
@@ -135,21 +138,20 @@ int serial_init (void)
temp = (8 * remainder) / baudRate;
fraction = (temp >> 1) + (temp & 1);
- IO_WRITE (port[CONSOLE_PORT] + UART_PL011_IBRD, divider);
- IO_WRITE (port[CONSOLE_PORT] + UART_PL011_FBRD, fraction);
+ writel(divider, ®s->pl011_ibrd);
+ writel(fraction, ®s->pl011_fbrd);
/*
** Set the UART to be 8 bits, 1 stop bit, no parity, fifo enabled.
*/
- IO_WRITE (port[CONSOLE_PORT] + UART_PL011_LCRH,
- (UART_PL011_LCRH_WLEN_8 | UART_PL011_LCRH_FEN));
+ writel(UART_PL011_LCRH_WLEN_8 | UART_PL011_LCRH_FEN,
+ ®s->pl011_lcrh);
/*
** Finally, enable the UART
*/
- IO_WRITE (port[CONSOLE_PORT] + UART_PL011_CR,
- (UART_PL011_CR_UARTEN | UART_PL011_CR_TXE |
- UART_PL011_CR_RXE));
+ writel(UART_PL011_CR_UARTEN | UART_PL011_CR_TXE | UART_PL011_CR_RXE,
+ ®s->pl011_cr);
return 0;
}
@@ -187,28 +189,31 @@ void serial_setbrg (void)
static void pl01x_putc (int portnum, char c)
{
+ struct pl01x_regs *regs = pl01x_get_regs(portnum);
+
/* Wait until there is space in the FIFO */
- while (IO_READ (port[portnum] + UART_PL01x_FR) & UART_PL01x_FR_TXFF)
+ while (readl(®s->fr) & UART_PL01x_FR_TXFF)
WATCHDOG_RESET();
/* Send the character */
- IO_WRITE (port[portnum] + UART_PL01x_DR, c);
+ writel(c, ®s->dr);
}
static int pl01x_getc (int portnum)
{
+ struct pl01x_regs *regs = pl01x_get_regs(portnum);
unsigned int data;
/* Wait until there is data in the FIFO */
- while (IO_READ (port[portnum] + UART_PL01x_FR) & UART_PL01x_FR_RXFE)
+ while (readl(®s->fr) & UART_PL01x_FR_RXFE)
WATCHDOG_RESET();
- data = IO_READ (port[portnum] + UART_PL01x_DR);
+ data = readl(®s->dr);
/* Check for an error flag */
if (data & 0xFFFFFF00) {
/* Clear the error */
- IO_WRITE (port[portnum] + UART_PL01x_ECR, 0xFFFFFFFF);
+ writel(0xFFFFFFFF, ®s->ecr);
return -1;
}
@@ -217,7 +222,8 @@ static int pl01x_getc (int portnum)
static int pl01x_tstc (int portnum)
{
+ struct pl01x_regs *regs = pl01x_get_regs(portnum);
+
WATCHDOG_RESET();
- return !(IO_READ (port[portnum] + UART_PL01x_FR) &
- UART_PL01x_FR_RXFE);
+ return !(readl(®s->fr) & UART_PL01x_FR_RXFE);
}
diff --git a/drivers/serial/serial_pl01x.h b/drivers/serial/serial_pl01x.h
index 5f20fdd..b670c24 100644
--- a/drivers/serial/serial_pl01x.h
+++ b/drivers/serial/serial_pl01x.h
@@ -29,10 +29,28 @@
* Definitions common to both PL010 & PL011
*
*/
-#define UART_PL01x_DR 0x00 /* Data read or written from the interface. */
-#define UART_PL01x_RSR 0x04 /* Receive status register (Read). */
-#define UART_PL01x_ECR 0x04 /* Error clear register (Write). */
-#define UART_PL01x_FR 0x18 /* Flag register (Read only). */
+
+#ifndef __ASSEMBLY__
+/*
+ * We can use a combined structure for PL010 and PL011, because they overlap
+ * only in common registers.
+ */
+struct pl01x_regs {
+ u32 dr; /* 0x00 Data register */
+ u32 ecr; /* 0x04 Error clear register (Write) */
+ u32 pl010_lcrh; /* 0x08 Line control register, high byte */
+ u32 pl010_lcrm; /* 0x0C Line control register, middle byte */
+ u32 pl010_lcrl; /* 0x10 Line control register, low byte */
+ u32 pl010_cr; /* 0x14 Control register */
+ u32 fr; /* 0x18 Flag register (Read only) */
+ u32 reserved;
+ u32 ilpr; /* 0x20 IrDA low-power counter register */
+ u32 pl011_ibrd; /* 0x24 Integer baud rate register */
+ u32 pl011_fbrd; /* 0x28 Fractional baud rate register */
+ u32 pl011_lcrh; /* 0x2C Line control register */
+ u32 pl011_cr; /* 0x30 Control register */
+};
+#endif
#define UART_PL01x_RSR_OE 0x08
#define UART_PL01x_RSR_BE 0x04
@@ -50,14 +68,6 @@
* PL010 definitions
*
*/
-#define UART_PL010_LCRH 0x08 /* Line control register, high byte. */
-#define UART_PL010_LCRM 0x0C /* Line control register, middle byte. */
-#define UART_PL010_LCRL 0x10 /* Line control register, low byte. */
-#define UART_PL010_CR 0x14 /* Control register. */
-#define UART_PL010_IIR 0x1C /* Interrupt indentification register (Read). */
-#define UART_PL010_ICR 0x1C /* Interrupt clear register (Write). */
-#define UART_PL010_ILPR 0x20 /* IrDA low power counter register. */
-
#define UART_PL010_CR_LPE (1 << 7)
#define UART_PL010_CR_RTIE (1 << 6)
#define UART_PL010_CR_TIE (1 << 5)
@@ -93,13 +103,6 @@
* PL011 definitions
*
*/
-#define UART_PL011_IBRD 0x24
-#define UART_PL011_FBRD 0x28
-#define UART_PL011_LCRH 0x2C
-#define UART_PL011_CR 0x30
-#define UART_PL011_IMSC 0x38
-#define UART_PL011_PERIPH_ID0 0xFE0
-
#define UART_PL011_LCRH_SPS (1 << 7)
#define UART_PL011_LCRH_WLEN_8 (3 << 5)
#define UART_PL011_LCRH_WLEN_7 (2 << 5)
--
1.7.0
2
1