source: trunk/target/linux/lantiq/patches-3.0/0013-MIPS-lantiq-adds-FALC-ON-spi-driver.patch @ 28405

Last change on this file since 28405 was 28405, checked in by blogic, 5 years ago

[lantiq]

  • update patches to 3.0
  • add basic vr9 support
  • backport 3.1 fixes
  • backport 3.2 queue (falcon)
File size: 17.8 KB
  • arch/mips/lantiq/falcon/devices.c

    From 2bd534c30688bcb3f70f1816fbcff813fc746103 Mon Sep 17 00:00:00 2001
    From: John Crispin <blogic@openwrt.org>
    Date: Sat, 27 Aug 2011 18:12:26 +0200
    Subject: [PATCH 13/24] MIPS: lantiq: adds FALC-ON spi driver
    
    The external bus unit (EBU) found on the FALC-ON SoC has spi emulation that is
    designed for serial flash access.
    
    Signed-off-by: Thomas Langer <thomas.langer@lantiq.com>
    Signed-off-by: John Crispin <blogic@openwrt.org>
    ---
     arch/mips/lantiq/falcon/devices.c        |   12 +-
     arch/mips/lantiq/falcon/devices.h        |    4 +
     arch/mips/lantiq/falcon/mach-easy98000.c |   27 ++
     drivers/spi/Kconfig                      |    4 +
     drivers/spi/Makefile                     |    1 +
     drivers/spi/spi-falcon.c                 |  477 ++++++++++++++++++++++++++++++
     6 files changed, 523 insertions(+), 2 deletions(-)
     create mode 100644 drivers/spi/spi-falcon.c
    
    old new  
    129129 
    130130/* i2c */ 
    131131static struct resource falcon_i2c_resources[] = { 
    132         MEM_RES("i2c", GPON_I2C_BASE,GPON_I2C_END), 
     132        MEM_RES("i2c", LTQ_I2C_BASE_ADDR, LTQ_I2C_SIZE), 
    133133        IRQ_RES("i2c_lb", FALCON_IRQ_I2C_LBREQ), 
    134134        IRQ_RES("i2c_b", FALCON_IRQ_I2C_BREQ), 
    135135        IRQ_RES("i2c_err", FALCON_IRQ_I2C_I2C_ERR), 
     
    140140{ 
    141141        platform_device_register_simple("i2c-falcon", 0, 
    142142        falcon_i2c_resources, ARRAY_SIZE(falcon_i2c_resources)); 
    143         sys1_hw_activate(ACTS_I2C_ACT); 
     143        ltq_sysctl_activate(SYSCTL_SYS1, ACTS_I2C_ACT); 
    144144} 
    145145 
    146 void __init falcon_register_crypto(void) 
     146/* spi flash */ 
     147static struct platform_device ltq_spi = { 
     148        .name                   = "falcon_spi", 
     149        .num_resources          = 0, 
     150}; 
     151 
     152void __init 
     153falcon_register_spi_flash(struct spi_board_info *data) 
    147154{ 
    148         platform_device_register_simple("ltq_falcon_deu", 0, NULL, 0); 
     155        spi_register_board_info(data, 1); 
     156        platform_device_register(&ltq_spi); 
    149157} 
  • arch/mips/lantiq/falcon/devices.h

    old new  
    1111#ifndef _FALCON_DEVICES_H__ 
    1212#define _FALCON_DEVICES_H__ 
    1313 
     14#include <linux/spi/spi.h> 
     15#include <linux/spi/flash.h> 
     16 
    1417#include "../devices.h" 
    1518 
    1619extern void falcon_register_nand(void); 
    1720extern void falcon_register_gpio(void); 
    1821extern void falcon_register_gpio_extra(void); 
    1922extern void falcon_register_i2c(void); 
     23extern void falcon_register_spi_flash(struct spi_board_info *data); 
    2024 
    2125#endif 
  • arch/mips/lantiq/falcon/mach-easy98000.c

    old new  
    4040        .parts          = easy98000_nor_partitions, 
    4141}; 
    4242 
     43static struct flash_platform_data easy98000_spi_flash_platform_data = { 
     44        .name = "sflash", 
     45        .parts = easy98000_nor_partitions, 
     46        .nr_parts = ARRAY_SIZE(easy98000_nor_partitions) 
     47}; 
     48 
     49static struct spi_board_info easy98000_spi_flash_data __initdata = { 
     50        .modalias               = "m25p80", 
     51        .bus_num                = 0, 
     52        .chip_select            = 0, 
     53        .max_speed_hz           = 10 * 1000 * 1000, 
     54        .mode                   = SPI_MODE_3, 
     55        .platform_data          = &easy98000_spi_flash_platform_data 
     56}; 
     57 
    4358/* setup gpio based spi bus/device for access to the eeprom on the board */ 
    4459#define SPI_GPIO_MRST           102 
    4560#define SPI_GPIO_MTSR           103 
     
    93108} 
    94109 
    95110static void __init 
     111easy98000sf_init(void) 
     112{ 
     113        easy98000_init_common(); 
     114        falcon_register_spi_flash(&easy98000_spi_flash_data); 
     115} 
     116 
     117static void __init 
    96118easy98000nand_init(void) 
    97119{ 
    98120        easy98000_init_common(); 
     
    104126                        "EASY98000 Eval Board", 
    105127                        easy98000_init); 
    106128 
     129MIPS_MACHINE(LANTIQ_MACH_EASY98000SF, 
     130                        "EASY98000SF", 
     131                        "EASY98000 Eval Board (Serial Flash)", 
     132                        easy98000sf_init); 
     133 
    107134MIPS_MACHINE(LANTIQ_MACH_EASY98000NAND, 
    108135                        "EASY98000NAND", 
    109136                        "EASY98000 Eval Board (NAND Flash)", 
  • drivers/spi/Kconfig

    old new  
    219219          This drivers supports the MPC52xx SPI controller in master SPI 
    220220          mode. 
    221221 
     222config SPI_FALCON 
     223        tristate "Falcon SPI controller support" 
     224        depends on SOC_FALCON 
     225 
    222226config SPI_MPC52xx_PSC 
    223227        tristate "Freescale MPC52xx PSC SPI controller" 
    224228        depends on PPC_MPC52xx && EXPERIMENTAL 
  • drivers/spi/Makefile

    old new  
    5656obj-$(CONFIG_SPI_SH_MSIOF)              += spi_sh_msiof.o 
    5757obj-$(CONFIG_SPI_STMP3XXX)              += spi_stmp.o 
    5858obj-$(CONFIG_SPI_NUC900)                += spi_nuc900.o 
     59obj-$(CONFIG_SPI_FALCON)                += spi-falcon.o 
    5960 
    6061# special build for s3c24xx spi driver with fiq support 
    6162spi_s3c24xx_hw-y                        := spi_s3c24xx.o 
  • new file linux-3.0.3/drivers/spi/spi-falcon.c

    - +  
     1/* 
     2 *  This program is free software; you can redistribute it and/or modify it 
     3 *  under the terms of the GNU General Public License version 2 as published 
     4 *  by the Free Software Foundation. 
     5 * 
     6 *  Copyright (C) 2010 Thomas Langer <thomas.langer@lantiq.com> 
     7 */ 
     8 
     9#include <linux/module.h> 
     10#include <linux/device.h> 
     11#include <linux/platform_device.h> 
     12#include <linux/spi/spi.h> 
     13#include <linux/delay.h> 
     14#include <linux/workqueue.h> 
     15 
     16#include <lantiq_soc.h> 
     17 
     18#define DRV_NAME                        "falcon_spi" 
     19 
     20#define FALCON_SPI_XFER_BEGIN           (1 << 0) 
     21#define FALCON_SPI_XFER_END             (1 << 1) 
     22 
     23/* Bus Read Configuration Register0 */ 
     24#define LTQ_BUSRCON0    0x00000010 
     25/* Bus Write Configuration Register0 */ 
     26#define LTQ_BUSWCON0    0x00000018 
     27/* Serial Flash Configuration Register */ 
     28#define LTQ_SFCON       0x00000080 
     29/* Serial Flash Time Register */ 
     30#define LTQ_SFTIME      0x00000084 
     31/* Serial Flash Status Register */ 
     32#define LTQ_SFSTAT      0x00000088 
     33/* Serial Flash Command Register */ 
     34#define LTQ_SFCMD       0x0000008C 
     35/* Serial Flash Address Register */ 
     36#define LTQ_SFADDR      0x00000090 
     37/* Serial Flash Data Register */ 
     38#define LTQ_SFDATA      0x00000094 
     39/* Serial Flash I/O Control Register */ 
     40#define LTQ_SFIO        0x00000098 
     41/* EBU Clock Control Register */ 
     42#define LTQ_EBUCC       0x000000C4 
     43 
     44/* Dummy Phase Length */ 
     45#define SFCMD_DUMLEN_OFFSET     16 
     46#define SFCMD_DUMLEN_MASK       0x000F0000 
     47/* Chip Select */ 
     48#define SFCMD_CS_OFFSET         24 
     49#define SFCMD_CS_MASK           0x07000000 
     50/* field offset */ 
     51#define SFCMD_ALEN_OFFSET       20 
     52#define SFCMD_ALEN_MASK         0x00700000 
     53/* SCK Rise-edge Position */ 
     54#define SFTIME_SCKR_POS_OFFSET  8 
     55#define SFTIME_SCKR_POS_MASK    0x00000F00 
     56/* SCK Period */ 
     57#define SFTIME_SCK_PER_OFFSET   0 
     58#define SFTIME_SCK_PER_MASK     0x0000000F 
     59/* SCK Fall-edge Position */ 
     60#define SFTIME_SCKF_POS_OFFSET  12 
     61#define SFTIME_SCKF_POS_MASK    0x0000F000 
     62/* Device Size */ 
     63#define SFCON_DEV_SIZE_A23_0    0x03000000 
     64#define SFCON_DEV_SIZE_MASK     0x0F000000 
     65/* Read Data Position */ 
     66#define SFTIME_RD_POS_MASK      0x000F0000 
     67/* Data Output */ 
     68#define SFIO_UNUSED_WD_MASK     0x0000000F 
     69/* Command Opcode mask */ 
     70#define SFCMD_OPC_MASK          0x000000FF 
     71/* dlen bytes of data to write */ 
     72#define SFCMD_DIR_WRITE         0x00000100 
     73/* Data Length offset */ 
     74#define SFCMD_DLEN_OFFSET       9 
     75/* Command Error */ 
     76#define SFSTAT_CMD_ERR          0x20000000 
     77/* Access Command Pending */ 
     78#define SFSTAT_CMD_PEND         0x00400000 
     79/* Frequency set to 100MHz. */ 
     80#define EBUCC_EBUDIV_SELF100    0x00000001 
     81/* Serial Flash */ 
     82#define BUSRCON0_AGEN_SERIAL_FLASH      0xF0000000 
     83/* 8-bit multiplexed */ 
     84#define BUSRCON0_PORTW_8_BIT_MUX        0x00000000 
     85/* Serial Flash */ 
     86#define BUSWCON0_AGEN_SERIAL_FLASH      0xF0000000 
     87/* Chip Select after opcode */ 
     88#define SFCMD_KEEP_CS_KEEP_SELECTED     0x00008000 
     89 
     90struct falcon_spi { 
     91        u32 sfcmd; /* for caching of opcode, direction, ... */ 
     92        struct spi_master *master; 
     93}; 
     94 
     95int 
     96falcon_spi_xfer(struct spi_device *spi, 
     97                    struct spi_transfer *t, 
     98                    unsigned long flags) 
     99{ 
     100        struct device *dev = &spi->dev; 
     101        struct falcon_spi *priv = spi_master_get_devdata(spi->master); 
     102        const u8 *txp = t->tx_buf; 
     103        u8 *rxp = t->rx_buf; 
     104        unsigned int bytelen = ((8 * t->len + 7) / 8); 
     105        unsigned int len, alen, dumlen; 
     106        u32 val; 
     107        enum { 
     108                state_init, 
     109                state_command_prepare, 
     110                state_write, 
     111                state_read, 
     112                state_disable_cs, 
     113                state_end 
     114        } state = state_init; 
     115 
     116        do { 
     117                switch (state) { 
     118                case state_init: /* detect phase of upper layer sequence */ 
     119                { 
     120                        /* initial write ? */ 
     121                        if (flags & FALCON_SPI_XFER_BEGIN) { 
     122                                if (!txp) { 
     123                                        dev_err(dev, 
     124                                                "BEGIN without tx data!\n"); 
     125                                        return -1; 
     126                                } 
     127                                /* 
     128                                 * Prepare the parts of the sfcmd register, 
     129                                 * which should not 
     130                                 * change during a sequence! 
     131                                 * Only exception are the length fields, 
     132                                 * especially alen and dumlen. 
     133                                 */ 
     134 
     135                                priv->sfcmd = ((spi->chip_select 
     136                                                << SFCMD_CS_OFFSET) 
     137                                               & SFCMD_CS_MASK); 
     138                                priv->sfcmd |= SFCMD_KEEP_CS_KEEP_SELECTED; 
     139                                priv->sfcmd |= *txp; 
     140                                txp++; 
     141                                bytelen--; 
     142                                if (bytelen) { 
     143                                        /* more data: 
     144                                         * maybe address and/or dummy */ 
     145                                        state = state_command_prepare; 
     146                                        break; 
     147                                } else { 
     148                                        dev_dbg(dev, "write cmd %02X\n", 
     149                                                priv->sfcmd & SFCMD_OPC_MASK); 
     150                                } 
     151                        } 
     152                        /* continued write ? */ 
     153                        if (txp && bytelen) { 
     154                                state = state_write; 
     155                                break; 
     156                        } 
     157                        /* read data? */ 
     158                        if (rxp && bytelen) { 
     159                                state = state_read; 
     160                                break; 
     161                        } 
     162                        /* end of sequence? */ 
     163                        if (flags & FALCON_SPI_XFER_END) 
     164                                state = state_disable_cs; 
     165                        else 
     166                                state = state_end; 
     167                        break; 
     168                } 
     169                case state_command_prepare: /* collect tx data for 
     170                                               address and dummy phase */ 
     171                { 
     172                        /* txp is valid, already checked */ 
     173                        val = 0; 
     174                        alen = 0; 
     175                        dumlen = 0; 
     176                        while (bytelen > 0) { 
     177                                if (alen < 3) { 
     178                                        val = (val<<8)|(*txp++); 
     179                                        alen++; 
     180                                } else if ((dumlen < 15) && (*txp == 0)) { 
     181                                        /* 
     182                                         * assume dummy bytes are set to 0 
     183                                         * from upper layer 
     184                                         */ 
     185                                        dumlen++; 
     186                                        txp++; 
     187                                } else 
     188                                        break; 
     189                                bytelen--; 
     190                        } 
     191                        priv->sfcmd &= ~(SFCMD_ALEN_MASK | SFCMD_DUMLEN_MASK); 
     192                        priv->sfcmd |= (alen << SFCMD_ALEN_OFFSET) | 
     193                                         (dumlen << SFCMD_DUMLEN_OFFSET); 
     194                        if (alen > 0) 
     195                                ltq_ebu_w32(val, LTQ_SFADDR); 
     196 
     197                        dev_dbg(dev, "write cmd %02X, alen=%d " 
     198                                "(addr=%06X) dumlen=%d\n", 
     199                                priv->sfcmd & SFCMD_OPC_MASK, 
     200                                alen, val, dumlen); 
     201 
     202                        if (bytelen > 0) { 
     203                                /* continue with write */ 
     204                                state = state_write; 
     205                        } else if (flags & FALCON_SPI_XFER_END) { 
     206                                /* end of sequence? */ 
     207                                state = state_disable_cs; 
     208                        } else { 
     209                                /* go to end and expect another 
     210                                 * call (read or write) */ 
     211                                state = state_end; 
     212                        } 
     213                        break; 
     214                } 
     215                case state_write: 
     216                { 
     217                        /* txp still valid */ 
     218                        priv->sfcmd |= SFCMD_DIR_WRITE; 
     219                        len = 0; 
     220                        val = 0; 
     221                        do { 
     222                                if (bytelen--) 
     223                                        val |= (*txp++) << (8 * len++); 
     224                                if ((flags & FALCON_SPI_XFER_END) 
     225                                    && (bytelen == 0)) { 
     226                                        priv->sfcmd &= 
     227                                                ~SFCMD_KEEP_CS_KEEP_SELECTED; 
     228                                } 
     229                                if ((len == 4) || (bytelen == 0)) { 
     230                                        ltq_ebu_w32(val, LTQ_SFDATA); 
     231                                        ltq_ebu_w32(priv->sfcmd 
     232                                                | (len<<SFCMD_DLEN_OFFSET), 
     233                                                LTQ_SFCMD); 
     234                                        len = 0; 
     235                                        val = 0; 
     236                                        priv->sfcmd &= ~(SFCMD_ALEN_MASK 
     237                                                         | SFCMD_DUMLEN_MASK); 
     238                                } 
     239                        } while (bytelen); 
     240                        state = state_end; 
     241                        break; 
     242                } 
     243                case state_read: 
     244                { 
     245                        /* read data */ 
     246                        priv->sfcmd &= ~SFCMD_DIR_WRITE; 
     247                        do { 
     248                                if ((flags & FALCON_SPI_XFER_END) 
     249                                    && (bytelen <= 4)) { 
     250                                        priv->sfcmd &= 
     251                                                ~SFCMD_KEEP_CS_KEEP_SELECTED; 
     252                                } 
     253                                len = (bytelen > 4) ? 4 : bytelen; 
     254                                bytelen -= len; 
     255                                ltq_ebu_w32(priv->sfcmd 
     256                                        |(len<<SFCMD_DLEN_OFFSET), LTQ_SFCMD); 
     257                                priv->sfcmd &= ~(SFCMD_ALEN_MASK 
     258                                                 | SFCMD_DUMLEN_MASK); 
     259                                do { 
     260                                        val = ltq_ebu_r32(LTQ_SFSTAT); 
     261                                        if (val & SFSTAT_CMD_ERR) { 
     262                                                /* reset error status */ 
     263                                                dev_err(dev, "SFSTAT: CMD_ERR " 
     264                                                        "(%x)\n", val); 
     265                                                ltq_ebu_w32(SFSTAT_CMD_ERR, 
     266                                                        LTQ_SFSTAT); 
     267                                                return -1; 
     268                                        } 
     269                                } while (val & SFSTAT_CMD_PEND); 
     270                                val = ltq_ebu_r32(LTQ_SFDATA); 
     271                                do { 
     272                                        *rxp = (val & 0xFF); 
     273                                        rxp++; 
     274                                        val >>= 8; 
     275                                        len--; 
     276                                } while (len); 
     277                        } while (bytelen); 
     278                        state = state_end; 
     279                        break; 
     280                } 
     281                case state_disable_cs: 
     282                { 
     283                        priv->sfcmd &= ~SFCMD_KEEP_CS_KEEP_SELECTED; 
     284                        ltq_ebu_w32(priv->sfcmd | (0 << SFCMD_DLEN_OFFSET), 
     285                                LTQ_SFCMD); 
     286                        val = ltq_ebu_r32(LTQ_SFSTAT); 
     287                        if (val & SFSTAT_CMD_ERR) { 
     288                                /* reset error status */ 
     289                                dev_err(dev, "SFSTAT: CMD_ERR (%x)\n", val); 
     290                                ltq_ebu_w32(SFSTAT_CMD_ERR, LTQ_SFSTAT); 
     291                                return -1; 
     292                        } 
     293                        state = state_end; 
     294                        break; 
     295                } 
     296                case state_end: 
     297                        break; 
     298                } 
     299        } while (state != state_end); 
     300 
     301        return 0; 
     302} 
     303 
     304static int 
     305falcon_spi_setup(struct spi_device *spi) 
     306{ 
     307        struct device *dev = &spi->dev; 
     308        const u32 ebuclk = CLOCK_100M; 
     309        unsigned int i; 
     310        unsigned long flags; 
     311 
     312        dev_dbg(dev, "setup\n"); 
     313 
     314        if (spi->master->bus_num > 0 || spi->chip_select > 0) 
     315                return -ENODEV; 
     316 
     317        spin_lock_irqsave(&ebu_lock, flags); 
     318 
     319        if (ebuclk < spi->max_speed_hz) { 
     320                /* set EBU clock to 100 MHz */ 
     321                ltq_sys1_w32_mask(0, EBUCC_EBUDIV_SELF100, LTQ_EBUCC); 
     322                i = 1; /* divider */ 
     323        } else { 
     324                /* set EBU clock to 50 MHz */ 
     325                ltq_sys1_w32_mask(EBUCC_EBUDIV_SELF100, 0, LTQ_EBUCC); 
     326 
     327                /* search for suitable divider */ 
     328                for (i = 1; i < 7; i++) { 
     329                        if (ebuclk / i <= spi->max_speed_hz) 
     330                                break; 
     331                } 
     332        } 
     333 
     334        /* setup period of serial clock */ 
     335        ltq_ebu_w32_mask(SFTIME_SCKF_POS_MASK 
     336                     | SFTIME_SCKR_POS_MASK 
     337                     | SFTIME_SCK_PER_MASK, 
     338                     (i << SFTIME_SCKR_POS_OFFSET) 
     339                     | (i << (SFTIME_SCK_PER_OFFSET + 1)), 
     340                     LTQ_SFTIME); 
     341 
     342        /* set some bits of unused_wd, to not trigger HOLD/WP 
     343         * signals on non QUAD flashes */ 
     344        ltq_ebu_w32((SFIO_UNUSED_WD_MASK & (0x8 | 0x4)), LTQ_SFIO); 
     345 
     346        ltq_ebu_w32(BUSRCON0_AGEN_SERIAL_FLASH | BUSRCON0_PORTW_8_BIT_MUX, 
     347                LTQ_BUSRCON0); 
     348        ltq_ebu_w32(BUSWCON0_AGEN_SERIAL_FLASH, LTQ_BUSWCON0); 
     349        /* set address wrap around to maximum for 24-bit addresses */ 
     350        ltq_ebu_w32_mask(SFCON_DEV_SIZE_MASK, SFCON_DEV_SIZE_A23_0, LTQ_SFCON); 
     351 
     352        spin_unlock_irqrestore(&ebu_lock, flags); 
     353 
     354        return 0; 
     355} 
     356 
     357static int 
     358falcon_spi_transfer(struct spi_device *spi, struct spi_message *m) 
     359{ 
     360        struct falcon_spi *priv = spi_master_get_devdata(spi->master); 
     361        struct spi_transfer *t; 
     362        unsigned long spi_flags; 
     363        unsigned long flags; 
     364        int ret = 0; 
     365 
     366        priv->sfcmd = 0; 
     367        m->actual_length = 0; 
     368 
     369        spi_flags = FALCON_SPI_XFER_BEGIN; 
     370        list_for_each_entry(t, &m->transfers, transfer_list) { 
     371                if (list_is_last(&t->transfer_list, &m->transfers)) 
     372                        spi_flags |= FALCON_SPI_XFER_END; 
     373 
     374                spin_lock_irqsave(&ebu_lock, flags); 
     375                ret = falcon_spi_xfer(spi, t, spi_flags); 
     376                spin_unlock_irqrestore(&ebu_lock, flags); 
     377 
     378                if (ret) 
     379                        break; 
     380 
     381                m->actual_length += t->len; 
     382 
     383                if (t->delay_usecs || t->cs_change) 
     384                        BUG(); 
     385 
     386                spi_flags = 0; 
     387        } 
     388 
     389        m->status = ret; 
     390        m->complete(m->context); 
     391 
     392        return 0; 
     393} 
     394 
     395static void 
     396falcon_spi_cleanup(struct spi_device *spi) 
     397{ 
     398        struct device *dev = &spi->dev; 
     399 
     400        dev_dbg(dev, "cleanup\n"); 
     401} 
     402 
     403static int __devinit 
     404falcon_spi_probe(struct platform_device *pdev) 
     405{ 
     406        struct device *dev = &pdev->dev; 
     407        struct falcon_spi *priv; 
     408        struct spi_master *master; 
     409        int ret; 
     410 
     411        dev_dbg(dev, "probing\n"); 
     412 
     413        master = spi_alloc_master(&pdev->dev, sizeof(*priv)); 
     414        if (!master) { 
     415                dev_err(dev, "no memory for spi_master\n"); 
     416                return -ENOMEM; 
     417        } 
     418 
     419        priv = spi_master_get_devdata(master); 
     420        priv->master = master; 
     421 
     422        master->mode_bits = SPI_MODE_3; 
     423        master->num_chipselect = 1; 
     424        master->bus_num = 0; 
     425 
     426        master->setup = falcon_spi_setup; 
     427        master->transfer = falcon_spi_transfer; 
     428        master->cleanup = falcon_spi_cleanup; 
     429 
     430        platform_set_drvdata(pdev, priv); 
     431 
     432        ret = spi_register_master(master); 
     433        if (ret) 
     434                spi_master_put(master); 
     435 
     436        return ret; 
     437} 
     438 
     439static int __devexit 
     440falcon_spi_remove(struct platform_device *pdev) 
     441{ 
     442        struct device *dev = &pdev->dev; 
     443        struct falcon_spi *priv = platform_get_drvdata(pdev); 
     444 
     445        dev_dbg(dev, "removed\n"); 
     446 
     447        spi_unregister_master(priv->master); 
     448 
     449        return 0; 
     450} 
     451 
     452static struct platform_driver falcon_spi_driver = { 
     453        .probe  = falcon_spi_probe, 
     454        .remove = __devexit_p(falcon_spi_remove), 
     455        .driver = { 
     456                .name   = DRV_NAME, 
     457                .owner  = THIS_MODULE 
     458        } 
     459}; 
     460 
     461static int __init 
     462falcon_spi_init(void) 
     463{ 
     464        return platform_driver_register(&falcon_spi_driver); 
     465} 
     466 
     467static void __exit 
     468falcon_spi_exit(void) 
     469{ 
     470        platform_driver_unregister(&falcon_spi_driver); 
     471} 
     472 
     473module_init(falcon_spi_init); 
     474module_exit(falcon_spi_exit); 
     475 
     476MODULE_LICENSE("GPL"); 
     477MODULE_DESCRIPTION("Lantiq Falcon SPI controller driver"); 
  • arch/mips/include/asm/mach-lantiq/falcon/lantiq_soc.h

    old new  
    4848 
    4949#define LTQ_EBU_MODCON  0x000C 
    5050 
     51/* I2C */ 
     52#define LTQ_I2C_BASE_ADDR       0x1E200000 
     53#define LTQ_I2C_SIZE            0x00010000 
     54 
    5155/* GPIO */ 
    5256#define LTQ_GPIO0_BASE_ADDR     0x1D810000 
    5357#define LTQ_GPIO0_SIZE          0x0080 
     
    9296 
    9397/* Activation Status Register */ 
    9498#define ACTS_ASC1_ACT   0x00000800 
     99#define ACTS_I2C_ACT    0x00004000 
    95100#define ACTS_P0         0x00010000 
    96101#define ACTS_P1         0x00010000 
    97102#define ACTS_P2         0x00020000 
Note: See TracBrowser for help on using the repository browser.