Back to home page

OSCL-LXR

 
 

    


0001 // SPDX-License-Identifier: GPL-2.0-only
0002 /*
0003  *  Support for Sharp SL-C6000x PDAs
0004  *  Model: (Tosa)
0005  *
0006  *  Copyright (c) 2005 Dirk Opfer
0007  *
0008  *  Based on code written by Sharp/Lineo for 2.4 kernels
0009  */
0010 
0011 #include <linux/clkdev.h>
0012 #include <linux/kernel.h>
0013 #include <linux/init.h>
0014 #include <linux/platform_device.h>
0015 #include <linux/major.h>
0016 #include <linux/fs.h>
0017 #include <linux/interrupt.h>
0018 #include <linux/delay.h>
0019 #include <linux/fb.h>
0020 #include <linux/mmc/host.h>
0021 #include <linux/mfd/tc6393xb.h>
0022 #include <linux/mfd/tmio.h>
0023 #include <linux/mtd/rawnand.h>
0024 #include <linux/mtd/partitions.h>
0025 #include <linux/mtd/physmap.h>
0026 #include <linux/pm.h>
0027 #include <linux/gpio_keys.h>
0028 #include <linux/input.h>
0029 #include <linux/gpio.h>
0030 #include <linux/gpio/machine.h>
0031 #include <linux/power/gpio-charger.h>
0032 #include <linux/spi/spi.h>
0033 #include <linux/spi/pxa2xx_spi.h>
0034 #include <linux/input/matrix_keypad.h>
0035 #include <linux/platform_data/i2c-pxa.h>
0036 #include <linux/reboot.h>
0037 #include <linux/memblock.h>
0038 
0039 #include <asm/setup.h>
0040 #include <asm/mach-types.h>
0041 
0042 #include "pxa25x.h"
0043 #include "reset.h"
0044 #include <linux/platform_data/irda-pxaficp.h>
0045 #include <linux/platform_data/mmc-pxamci.h>
0046 #include "udc.h"
0047 #include "tosa_bt.h"
0048 #include <linux/platform_data/asoc-pxa.h>
0049 #include "smemc.h"
0050 
0051 #include <asm/mach/arch.h>
0052 #include "tosa.h"
0053 
0054 #include <asm/hardware/scoop.h>
0055 #include <asm/mach/sharpsl_param.h>
0056 
0057 #include "generic.h"
0058 #include "devices.h"
0059 
0060 static unsigned long tosa_pin_config[] = {
0061     GPIO78_nCS_2, /* Scoop */
0062     GPIO80_nCS_4, /* tg6393xb */
0063     GPIO33_nCS_5, /* Scoop */
0064 
0065     // GPIO76 CARD_VCC_ON1
0066 
0067     GPIO19_GPIO, /* Reset out */
0068     GPIO1_RST | WAKEUP_ON_EDGE_FALL,
0069 
0070     GPIO0_GPIO | WAKEUP_ON_EDGE_FALL, /* WAKE_UP */
0071     GPIO2_GPIO | WAKEUP_ON_EDGE_BOTH, /* AC_IN */
0072     GPIO3_GPIO | WAKEUP_ON_EDGE_FALL, /* RECORD */
0073     GPIO4_GPIO | WAKEUP_ON_EDGE_FALL, /* SYNC */
0074     GPIO20_GPIO, /* EAR_IN */
0075     GPIO22_GPIO, /* On */
0076 
0077     GPIO5_GPIO, /* USB_IN */
0078     GPIO32_GPIO, /* Pen IRQ */
0079 
0080     GPIO7_GPIO, /* Jacket Detect */
0081     GPIO14_GPIO, /* BAT0_CRG */
0082     GPIO12_GPIO, /* BAT1_CRG */
0083     GPIO17_GPIO, /* BAT0_LOW */
0084     GPIO84_GPIO, /* BAT1_LOW */
0085     GPIO38_GPIO, /* BAT_LOCK */
0086 
0087     GPIO11_3_6MHz,
0088     GPIO15_GPIO, /* TC6393XB IRQ */
0089     GPIO18_RDY,
0090     GPIO27_GPIO, /* LCD Sync */
0091 
0092     /* MMC */
0093     GPIO6_MMC_CLK,
0094     GPIO8_MMC_CS0,
0095     GPIO9_GPIO, /* Detect */
0096     GPIO10_GPIO, /* nSD_INT */
0097 
0098     /* CF */
0099     GPIO13_GPIO, /* CD_IRQ */
0100     GPIO21_GPIO, /* Main Slot IRQ */
0101     GPIO36_GPIO, /* Jacket Slot IRQ */
0102     GPIO48_nPOE,
0103     GPIO49_nPWE,
0104     GPIO50_nPIOR,
0105     GPIO51_nPIOW,
0106     GPIO52_nPCE_1,
0107     GPIO53_nPCE_2,
0108     GPIO54_nPSKTSEL,
0109     GPIO55_nPREG,
0110     GPIO56_nPWAIT,
0111     GPIO57_nIOIS16,
0112 
0113     /* AC97 */
0114     GPIO31_AC97_SYNC,
0115     GPIO30_AC97_SDATA_OUT,
0116     GPIO28_AC97_BITCLK,
0117     GPIO29_AC97_SDATA_IN_0,
0118     // GPIO79 nAUD_IRQ
0119 
0120     /* FFUART */
0121     GPIO34_FFUART_RXD,
0122     GPIO35_FFUART_CTS,
0123     GPIO37_FFUART_DSR,
0124     GPIO39_FFUART_TXD,
0125     GPIO40_FFUART_DTR,
0126     GPIO41_FFUART_RTS,
0127 
0128     /* BTUART */
0129     GPIO42_BTUART_RXD,
0130     GPIO43_BTUART_TXD,
0131     GPIO44_BTUART_CTS,
0132     GPIO45_BTUART_RTS,
0133 
0134     /* Keybd */
0135     GPIO58_GPIO | MFP_LPM_DRIVE_LOW,    /* Column 0 */
0136     GPIO59_GPIO | MFP_LPM_DRIVE_LOW,    /* Column 1 */
0137     GPIO60_GPIO | MFP_LPM_DRIVE_LOW,    /* Column 2 */
0138     GPIO61_GPIO | MFP_LPM_DRIVE_LOW,    /* Column 3 */
0139     GPIO62_GPIO | MFP_LPM_DRIVE_LOW,    /* Column 4 */
0140     GPIO63_GPIO | MFP_LPM_DRIVE_LOW,    /* Column 5 */
0141     GPIO64_GPIO | MFP_LPM_DRIVE_LOW,    /* Column 6 */
0142     GPIO65_GPIO | MFP_LPM_DRIVE_LOW,    /* Column 7 */
0143     GPIO66_GPIO | MFP_LPM_DRIVE_LOW,    /* Column 8 */
0144     GPIO67_GPIO | MFP_LPM_DRIVE_LOW,    /* Column 9 */
0145     GPIO68_GPIO | MFP_LPM_DRIVE_LOW,    /* Column 10 */
0146     GPIO69_GPIO | MFP_LPM_DRIVE_LOW,    /* Row 0 */
0147     GPIO70_GPIO | MFP_LPM_DRIVE_LOW,    /* Row 1 */
0148     GPIO71_GPIO | MFP_LPM_DRIVE_LOW,    /* Row 2 */
0149     GPIO72_GPIO | MFP_LPM_DRIVE_LOW,    /* Row 3 */
0150     GPIO73_GPIO | MFP_LPM_DRIVE_LOW,    /* Row 4 */
0151     GPIO74_GPIO | MFP_LPM_DRIVE_LOW,    /* Row 5 */
0152     GPIO75_GPIO | MFP_LPM_DRIVE_LOW,    /* Row 6 */
0153 
0154     /* SPI */
0155     GPIO81_SSP2_CLK_OUT,
0156     GPIO82_SSP2_FRM_OUT,
0157     GPIO83_SSP2_TXD,
0158 
0159     /* IrDA is managed in other way */
0160     GPIO46_GPIO,
0161     GPIO47_GPIO,
0162 };
0163 
0164 /*
0165  * SCOOP Device
0166  */
0167 static struct resource tosa_scoop_resources[] = {
0168     [0] = {
0169         .start  = TOSA_CF_PHYS,
0170         .end    = TOSA_CF_PHYS + 0xfff,
0171         .flags  = IORESOURCE_MEM,
0172     },
0173 };
0174 
0175 static struct scoop_config tosa_scoop_setup = {
0176     .io_dir     = TOSA_SCOOP_IO_DIR,
0177     .gpio_base  = TOSA_SCOOP_GPIO_BASE,
0178 };
0179 
0180 static struct platform_device tosascoop_device = {
0181     .name       = "sharp-scoop",
0182     .id     = 0,
0183     .dev        = {
0184         .platform_data  = &tosa_scoop_setup,
0185     },
0186     .num_resources  = ARRAY_SIZE(tosa_scoop_resources),
0187     .resource   = tosa_scoop_resources,
0188 };
0189 
0190 
0191 /*
0192  * SCOOP Device Jacket
0193  */
0194 static struct resource tosa_scoop_jc_resources[] = {
0195     [0] = {
0196         .start      = TOSA_SCOOP_PHYS + 0x40,
0197         .end        = TOSA_SCOOP_PHYS + 0xfff,
0198         .flags      = IORESOURCE_MEM,
0199     },
0200 };
0201 
0202 static struct scoop_config tosa_scoop_jc_setup = {
0203     .io_dir     = TOSA_SCOOP_JC_IO_DIR,
0204     .gpio_base  = TOSA_SCOOP_JC_GPIO_BASE,
0205 };
0206 
0207 static struct platform_device tosascoop_jc_device = {
0208     .name       = "sharp-scoop",
0209     .id     = 1,
0210     .dev        = {
0211         .platform_data  = &tosa_scoop_jc_setup,
0212         .parent     = &tosascoop_device.dev,
0213     },
0214     .num_resources  = ARRAY_SIZE(tosa_scoop_jc_resources),
0215     .resource   = tosa_scoop_jc_resources,
0216 };
0217 
0218 /*
0219  * PCMCIA
0220  */
0221 static struct scoop_pcmcia_dev tosa_pcmcia_scoop[] = {
0222 {
0223     .dev        = &tosascoop_device.dev,
0224     .irq        = TOSA_IRQ_GPIO_CF_IRQ,
0225     .cd_irq     = TOSA_IRQ_GPIO_CF_CD,
0226     .cd_irq_str = "PCMCIA0 CD",
0227 },{
0228     .dev        = &tosascoop_jc_device.dev,
0229     .irq        = TOSA_IRQ_GPIO_JC_CF_IRQ,
0230     .cd_irq     = -1,
0231 },
0232 };
0233 
0234 static struct scoop_pcmcia_config tosa_pcmcia_config = {
0235     .devs         = &tosa_pcmcia_scoop[0],
0236     .num_devs     = 2,
0237 };
0238 
0239 /*
0240  * USB Device Controller
0241  */
0242 static struct gpiod_lookup_table tosa_udc_gpiod_table = {
0243     .dev_id = "gpio-vbus",
0244     .table = {
0245         GPIO_LOOKUP("gpio-pxa", TOSA_GPIO_USB_IN,
0246                 "vbus", GPIO_ACTIVE_LOW),
0247         GPIO_LOOKUP("gpio-pxa", TOSA_GPIO_USB_PULLUP,
0248                 "pullup", GPIO_ACTIVE_HIGH),
0249         { },
0250     },
0251 };
0252 
0253 static struct platform_device tosa_gpio_vbus = {
0254     .name   = "gpio-vbus",
0255     .id = -1,
0256 };
0257 
0258 /*
0259  * MMC/SD Device
0260  */
0261 static int tosa_mci_init(struct device *dev, irq_handler_t tosa_detect_int, void *data)
0262 {
0263     int err;
0264 
0265     err = gpio_request(TOSA_GPIO_nSD_INT, "SD Int");
0266     if (err) {
0267         printk(KERN_ERR "tosa_mci_init: can't request SD_PWR gpio\n");
0268         goto err_gpio_int;
0269     }
0270     err = gpio_direction_input(TOSA_GPIO_nSD_INT);
0271     if (err)
0272         goto err_gpio_int_dir;
0273 
0274     return 0;
0275 
0276 err_gpio_int_dir:
0277     gpio_free(TOSA_GPIO_nSD_INT);
0278 err_gpio_int:
0279     return err;
0280 }
0281 
0282 static void tosa_mci_exit(struct device *dev, void *data)
0283 {
0284     gpio_free(TOSA_GPIO_nSD_INT);
0285 }
0286 
0287 static struct pxamci_platform_data tosa_mci_platform_data = {
0288     .detect_delay_ms    = 250,
0289     .ocr_mask           = MMC_VDD_32_33|MMC_VDD_33_34,
0290     .init               = tosa_mci_init,
0291     .exit               = tosa_mci_exit,
0292 };
0293 
0294 static struct gpiod_lookup_table tosa_mci_gpio_table = {
0295     .dev_id = "pxa2xx-mci.0",
0296     .table = {
0297         GPIO_LOOKUP("gpio-pxa", TOSA_GPIO_nSD_DETECT,
0298                 "cd", GPIO_ACTIVE_LOW),
0299         GPIO_LOOKUP("sharp-scoop.0", TOSA_GPIO_SD_WP - TOSA_SCOOP_GPIO_BASE,
0300                 "wp", GPIO_ACTIVE_LOW),
0301         GPIO_LOOKUP("sharp-scoop.0", TOSA_GPIO_PWR_ON - TOSA_SCOOP_GPIO_BASE,
0302                 "power", GPIO_ACTIVE_HIGH),
0303         { },
0304     },
0305 };
0306 
0307 /*
0308  * Irda
0309  */
0310 static void tosa_irda_transceiver_mode(struct device *dev, int mode)
0311 {
0312     if (mode & IR_OFF) {
0313         gpio_set_value(TOSA_GPIO_IR_POWERDWN, 0);
0314         pxa2xx_transceiver_mode(dev, mode);
0315         gpio_direction_output(TOSA_GPIO_IRDA_TX, 0);
0316     } else {
0317         pxa2xx_transceiver_mode(dev, mode);
0318         gpio_set_value(TOSA_GPIO_IR_POWERDWN, 1);
0319     }
0320 }
0321 
0322 static int tosa_irda_startup(struct device *dev)
0323 {
0324     int ret;
0325 
0326     ret = gpio_request(TOSA_GPIO_IRDA_TX, "IrDA TX");
0327     if (ret)
0328         goto err_tx;
0329     ret = gpio_direction_output(TOSA_GPIO_IRDA_TX, 0);
0330     if (ret)
0331         goto err_tx_dir;
0332 
0333     ret = gpio_request(TOSA_GPIO_IR_POWERDWN, "IrDA powerdown");
0334     if (ret)
0335         goto err_pwr;
0336 
0337     ret = gpio_direction_output(TOSA_GPIO_IR_POWERDWN, 0);
0338     if (ret)
0339         goto err_pwr_dir;
0340 
0341     tosa_irda_transceiver_mode(dev, IR_SIRMODE | IR_OFF);
0342 
0343     return 0;
0344 
0345 err_pwr_dir:
0346     gpio_free(TOSA_GPIO_IR_POWERDWN);
0347 err_pwr:
0348 err_tx_dir:
0349     gpio_free(TOSA_GPIO_IRDA_TX);
0350 err_tx:
0351     return ret;
0352 }
0353 
0354 static void tosa_irda_shutdown(struct device *dev)
0355 {
0356     tosa_irda_transceiver_mode(dev, IR_SIRMODE | IR_OFF);
0357     gpio_free(TOSA_GPIO_IR_POWERDWN);
0358     gpio_free(TOSA_GPIO_IRDA_TX);
0359 }
0360 
0361 static struct pxaficp_platform_data tosa_ficp_platform_data = {
0362     .gpio_pwdown        = -1,
0363     .transceiver_cap    = IR_SIRMODE | IR_OFF,
0364     .transceiver_mode   = tosa_irda_transceiver_mode,
0365     .startup        = tosa_irda_startup,
0366     .shutdown       = tosa_irda_shutdown,
0367 };
0368 
0369 /*
0370  * Tosa AC IN
0371  */
0372 static struct gpiod_lookup_table tosa_power_gpiod_table = {
0373     .dev_id = "gpio-charger",
0374     .table = {
0375         GPIO_LOOKUP("gpio-pxa", TOSA_GPIO_AC_IN,
0376                 NULL, GPIO_ACTIVE_LOW),
0377         { },
0378     },
0379 };
0380 
0381 static char *tosa_ac_supplied_to[] = {
0382     "main-battery",
0383     "backup-battery",
0384     "jacket-battery",
0385 };
0386 
0387 static struct gpio_charger_platform_data tosa_power_data = {
0388     .name           = "charger",
0389     .type           = POWER_SUPPLY_TYPE_MAINS,
0390     .supplied_to        = tosa_ac_supplied_to,
0391     .num_supplicants    = ARRAY_SIZE(tosa_ac_supplied_to),
0392 };
0393 
0394 static struct resource tosa_power_resource[] = {
0395     {
0396         .name       = "ac",
0397         .start      = PXA_GPIO_TO_IRQ(TOSA_GPIO_AC_IN),
0398         .end        = PXA_GPIO_TO_IRQ(TOSA_GPIO_AC_IN),
0399         .flags      = IORESOURCE_IRQ |
0400                   IORESOURCE_IRQ_HIGHEDGE |
0401                   IORESOURCE_IRQ_LOWEDGE,
0402     },
0403 };
0404 
0405 static struct platform_device tosa_power_device = {
0406     .name           = "gpio-charger",
0407     .id         = -1,
0408     .dev.platform_data  = &tosa_power_data,
0409     .resource       = tosa_power_resource,
0410     .num_resources      = ARRAY_SIZE(tosa_power_resource),
0411 };
0412 
0413 /*
0414  * Tosa Keyboard
0415  */
0416 static const uint32_t tosakbd_keymap[] = {
0417     KEY(0, 1, KEY_W),
0418     KEY(0, 5, KEY_K),
0419     KEY(0, 6, KEY_BACKSPACE),
0420     KEY(0, 7, KEY_P),
0421     KEY(1, 0, KEY_Q),
0422     KEY(1, 1, KEY_E),
0423     KEY(1, 2, KEY_T),
0424     KEY(1, 3, KEY_Y),
0425     KEY(1, 5, KEY_O),
0426     KEY(1, 6, KEY_I),
0427     KEY(1, 7, KEY_COMMA),
0428     KEY(2, 0, KEY_A),
0429     KEY(2, 1, KEY_D),
0430     KEY(2, 2, KEY_G),
0431     KEY(2, 3, KEY_U),
0432     KEY(2, 5, KEY_L),
0433     KEY(2, 6, KEY_ENTER),
0434     KEY(2, 7, KEY_DOT),
0435     KEY(3, 0, KEY_Z),
0436     KEY(3, 1, KEY_C),
0437     KEY(3, 2, KEY_V),
0438     KEY(3, 3, KEY_J),
0439     KEY(3, 4, TOSA_KEY_ADDRESSBOOK),
0440     KEY(3, 5, TOSA_KEY_CANCEL),
0441     KEY(3, 6, TOSA_KEY_CENTER),
0442     KEY(3, 7, TOSA_KEY_OK),
0443     KEY(3, 8, KEY_LEFTSHIFT),
0444     KEY(4, 0, KEY_S),
0445     KEY(4, 1, KEY_R),
0446     KEY(4, 2, KEY_B),
0447     KEY(4, 3, KEY_N),
0448     KEY(4, 4, TOSA_KEY_CALENDAR),
0449     KEY(4, 5, TOSA_KEY_HOMEPAGE),
0450     KEY(4, 6, KEY_LEFTCTRL),
0451     KEY(4, 7, TOSA_KEY_LIGHT),
0452     KEY(4, 9, KEY_RIGHTSHIFT),
0453     KEY(5, 0, KEY_TAB),
0454     KEY(5, 1, KEY_SLASH),
0455     KEY(5, 2, KEY_H),
0456     KEY(5, 3, KEY_M),
0457     KEY(5, 4, TOSA_KEY_MENU),
0458     KEY(5, 6, KEY_UP),
0459     KEY(5, 10, TOSA_KEY_FN),
0460     KEY(6, 0, KEY_X),
0461     KEY(6, 1, KEY_F),
0462     KEY(6, 2, KEY_SPACE),
0463     KEY(6, 3, KEY_APOSTROPHE),
0464     KEY(6, 4, TOSA_KEY_MAIL),
0465     KEY(6, 5, KEY_LEFT),
0466     KEY(6, 6, KEY_DOWN),
0467     KEY(6, 7, KEY_RIGHT),
0468 };
0469 
0470 static struct matrix_keymap_data tosakbd_keymap_data = {
0471     .keymap     = tosakbd_keymap,
0472     .keymap_size    = ARRAY_SIZE(tosakbd_keymap),
0473 };
0474 
0475 static const int tosakbd_col_gpios[] =
0476             { 58, 59, 60, 61, 62, 63, 64, 65, 66, 67, 68 };
0477 static const int tosakbd_row_gpios[] =
0478             { 69, 70, 71, 72, 73, 74, 75 };
0479 
0480 static struct matrix_keypad_platform_data tosakbd_pdata = {
0481     .keymap_data        = &tosakbd_keymap_data,
0482     .row_gpios      = tosakbd_row_gpios,
0483     .col_gpios      = tosakbd_col_gpios,
0484     .num_row_gpios      = ARRAY_SIZE(tosakbd_row_gpios),
0485     .num_col_gpios      = ARRAY_SIZE(tosakbd_col_gpios),
0486     .col_scan_delay_us  = 10,
0487     .debounce_ms        = 10,
0488     .wakeup         = 1,
0489 };
0490 
0491 static struct platform_device tosakbd_device = {
0492     .name       = "matrix-keypad",
0493     .id     = -1,
0494     .dev        = {
0495         .platform_data = &tosakbd_pdata,
0496     },
0497 };
0498 
0499 static struct gpio_keys_button tosa_gpio_keys[] = {
0500     /*
0501      * Two following keys are directly tied to "ON" button of tosa. Why?
0502      * The first one can be used as a wakeup source, the second can't;
0503      * also the first one is OR of ac_powered and on_button.
0504      */
0505     {
0506         .type   = EV_PWR,
0507         .code   = KEY_RESERVED,
0508         .gpio   = TOSA_GPIO_POWERON,
0509         .desc   = "Poweron",
0510         .wakeup = 1,
0511         .active_low = 1,
0512     },
0513     {
0514         .type   = EV_PWR,
0515         .code   = KEY_SUSPEND,
0516         .gpio   = TOSA_GPIO_ON_KEY,
0517         .desc   = "On key",
0518         /*
0519          * can't be used as wakeup
0520          * .wakeup  = 1,
0521          */
0522         .active_low = 1,
0523     },
0524     {
0525         .type   = EV_KEY,
0526         .code   = TOSA_KEY_RECORD,
0527         .gpio   = TOSA_GPIO_RECORD_BTN,
0528         .desc   = "Record Button",
0529         .wakeup = 1,
0530         .active_low = 1,
0531     },
0532     {
0533         .type   = EV_KEY,
0534         .code   = TOSA_KEY_SYNC,
0535         .gpio   = TOSA_GPIO_SYNC,
0536         .desc   = "Sync Button",
0537         .wakeup = 1,
0538         .active_low = 1,
0539     },
0540     {
0541         .type   = EV_SW,
0542         .code   = SW_HEADPHONE_INSERT,
0543         .gpio   = TOSA_GPIO_EAR_IN,
0544         .desc   = "HeadPhone insert",
0545         .active_low = 1,
0546         .debounce_interval = 300,
0547     },
0548 };
0549 
0550 static struct gpio_keys_platform_data tosa_gpio_keys_platform_data = {
0551     .buttons    = tosa_gpio_keys,
0552     .nbuttons   = ARRAY_SIZE(tosa_gpio_keys),
0553 };
0554 
0555 static struct platform_device tosa_gpio_keys_device = {
0556     .name   = "gpio-keys",
0557     .id = -1,
0558     .dev    = {
0559         .platform_data  = &tosa_gpio_keys_platform_data,
0560     },
0561 };
0562 
0563 /*
0564  * Tosa LEDs
0565  */
0566 static struct gpio_led tosa_gpio_leds[] = {
0567     {
0568         .name           = "tosa:amber:charge",
0569         .default_trigger    = "main-battery-charging",
0570         .gpio           = TOSA_GPIO_CHRG_ERR_LED,
0571     },
0572     {
0573         .name           = "tosa:green:mail",
0574         .default_trigger    = "nand-disk",
0575         .gpio           = TOSA_GPIO_NOTE_LED,
0576     },
0577     {
0578         .name           = "tosa:dual:wlan",
0579         .default_trigger    = "none",
0580         .gpio           = TOSA_GPIO_WLAN_LED,
0581     },
0582     {
0583         .name           = "tosa:blue:bluetooth",
0584         .default_trigger    = "tosa-bt",
0585         .gpio           = TOSA_GPIO_BT_LED,
0586     },
0587 };
0588 
0589 static struct gpio_led_platform_data tosa_gpio_leds_platform_data = {
0590     .leds       = tosa_gpio_leds,
0591     .num_leds   = ARRAY_SIZE(tosa_gpio_leds),
0592 };
0593 
0594 static struct platform_device tosaled_device = {
0595     .name   = "leds-gpio",
0596     .id = -1,
0597     .dev    = {
0598         .platform_data  = &tosa_gpio_leds_platform_data,
0599     },
0600 };
0601 
0602 /*
0603  * Toshiba Mobile IO Controller
0604  */
0605 static struct resource tc6393xb_resources[] = {
0606     [0] = {
0607         .start  = TOSA_LCDC_PHYS,
0608         .end    = TOSA_LCDC_PHYS + 0x3ffffff,
0609         .flags  = IORESOURCE_MEM,
0610     },
0611 
0612     [1] = {
0613         .start  = TOSA_IRQ_GPIO_TC6393XB_INT,
0614         .end    = TOSA_IRQ_GPIO_TC6393XB_INT,
0615         .flags  = IORESOURCE_IRQ,
0616     },
0617 };
0618 
0619 static struct gpiod_lookup_table tosa_battery_gpio_table = {
0620     .dev_id = "wm97xx-battery",
0621     .table = {
0622         GPIO_LOOKUP("gpio-pxa", TOSA_GPIO_BAT0_CRG,
0623                 "main battery full", GPIO_ACTIVE_HIGH),
0624         GPIO_LOOKUP("gpio-pxa", TOSA_GPIO_BAT1_CRG,
0625                 "jacket battery full", GPIO_ACTIVE_HIGH),
0626         GPIO_LOOKUP("gpio-pxa", TOSA_GPIO_BAT0_LOW,
0627                 "main battery low", GPIO_ACTIVE_HIGH),
0628         GPIO_LOOKUP("gpio-pxa", TOSA_GPIO_BAT1_LOW,
0629                 "jacket battery low", GPIO_ACTIVE_HIGH),
0630         GPIO_LOOKUP("gpio-pxa", TOSA_GPIO_JACKET_DETECT,
0631                 "jacket detect", GPIO_ACTIVE_HIGH),
0632         { },
0633     },
0634 };
0635 
0636 static int tosa_tc6393xb_enable(struct platform_device *dev)
0637 {
0638     int rc;
0639 
0640     rc = gpio_request(TOSA_GPIO_TC6393XB_REST_IN, "tc6393xb #pclr");
0641     if (rc)
0642         goto err_req_pclr;
0643     rc = gpio_request(TOSA_GPIO_TC6393XB_SUSPEND, "tc6393xb #suspend");
0644     if (rc)
0645         goto err_req_suspend;
0646     rc = gpio_request(TOSA_GPIO_TC6393XB_L3V_ON, "tc6393xb l3v");
0647     if (rc)
0648         goto err_req_l3v;
0649     rc = gpio_direction_output(TOSA_GPIO_TC6393XB_L3V_ON, 0);
0650     if (rc)
0651         goto err_dir_l3v;
0652     rc = gpio_direction_output(TOSA_GPIO_TC6393XB_SUSPEND, 0);
0653     if (rc)
0654         goto err_dir_suspend;
0655     rc = gpio_direction_output(TOSA_GPIO_TC6393XB_REST_IN, 0);
0656     if (rc)
0657         goto err_dir_pclr;
0658 
0659     mdelay(1);
0660 
0661     gpio_set_value(TOSA_GPIO_TC6393XB_SUSPEND, 1);
0662 
0663     mdelay(10);
0664 
0665     gpio_set_value(TOSA_GPIO_TC6393XB_REST_IN, 1);
0666     gpio_set_value(TOSA_GPIO_TC6393XB_L3V_ON, 1);
0667 
0668     return 0;
0669 err_dir_pclr:
0670 err_dir_suspend:
0671 err_dir_l3v:
0672     gpio_free(TOSA_GPIO_TC6393XB_L3V_ON);
0673 err_req_l3v:
0674     gpio_free(TOSA_GPIO_TC6393XB_SUSPEND);
0675 err_req_suspend:
0676     gpio_free(TOSA_GPIO_TC6393XB_REST_IN);
0677 err_req_pclr:
0678     return rc;
0679 }
0680 
0681 static void tosa_tc6393xb_disable(struct platform_device *dev)
0682 {
0683     gpio_free(TOSA_GPIO_TC6393XB_L3V_ON);
0684     gpio_free(TOSA_GPIO_TC6393XB_SUSPEND);
0685     gpio_free(TOSA_GPIO_TC6393XB_REST_IN);
0686 }
0687 
0688 static int tosa_tc6393xb_resume(struct platform_device *dev)
0689 {
0690     gpio_set_value(TOSA_GPIO_TC6393XB_SUSPEND, 1);
0691     mdelay(10);
0692     gpio_set_value(TOSA_GPIO_TC6393XB_L3V_ON, 1);
0693     mdelay(10);
0694 
0695     return 0;
0696 }
0697 
0698 static int tosa_tc6393xb_suspend(struct platform_device *dev)
0699 {
0700     gpio_set_value(TOSA_GPIO_TC6393XB_L3V_ON, 0);
0701     gpio_set_value(TOSA_GPIO_TC6393XB_SUSPEND, 0);
0702     return 0;
0703 }
0704 
0705 static uint8_t scan_ff_pattern[] = { 0xff, 0xff };
0706 
0707 static struct nand_bbt_descr tosa_tc6393xb_nand_bbt = {
0708     .options    = 0,
0709     .offs       = 4,
0710     .len        = 2,
0711     .pattern    = scan_ff_pattern
0712 };
0713 
0714 static const char * const probes[] = {
0715     "cmdlinepart",
0716     "ofpart",
0717     "sharpslpart",
0718     NULL,
0719 };
0720 
0721 static struct tmio_nand_data tosa_tc6393xb_nand_config = {
0722     .badblock_pattern = &tosa_tc6393xb_nand_bbt,
0723     .part_parsers = probes,
0724 };
0725 
0726 #ifdef CONFIG_MFD_TC6393XB
0727 static struct fb_videomode tosa_tc6393xb_lcd_mode[] = {
0728     {
0729         .xres = 480,
0730         .yres = 640,
0731         .pixclock = 0x002cdf00,/* PLL divisor */
0732         .left_margin = 0x004c,
0733         .right_margin = 0x005b,
0734         .upper_margin = 0x0001,
0735         .lower_margin = 0x000d,
0736         .hsync_len = 0x0002,
0737         .vsync_len = 0x0001,
0738         .sync = FB_SYNC_HOR_HIGH_ACT | FB_SYNC_VERT_HIGH_ACT,
0739         .vmode = FB_VMODE_NONINTERLACED,
0740     },{
0741         .xres = 240,
0742         .yres = 320,
0743         .pixclock = 0x00e7f203,/* PLL divisor */
0744         .left_margin = 0x0024,
0745         .right_margin = 0x002f,
0746         .upper_margin = 0x0001,
0747         .lower_margin = 0x000d,
0748         .hsync_len = 0x0002,
0749         .vsync_len = 0x0001,
0750         .sync = FB_SYNC_HOR_HIGH_ACT | FB_SYNC_VERT_HIGH_ACT,
0751         .vmode = FB_VMODE_NONINTERLACED,
0752     }
0753 };
0754 
0755 static struct tmio_fb_data tosa_tc6393xb_fb_config = {
0756     .lcd_set_power  = tc6393xb_lcd_set_power,
0757     .lcd_mode   = tc6393xb_lcd_mode,
0758     .num_modes  = ARRAY_SIZE(tosa_tc6393xb_lcd_mode),
0759     .modes      = &tosa_tc6393xb_lcd_mode[0],
0760     .height     = 82,
0761     .width      = 60,
0762 };
0763 #endif
0764 
0765 static struct tc6393xb_platform_data tosa_tc6393xb_data = {
0766     .scr_pll2cr = 0x0cc1,
0767     .scr_gper   = 0x3300,
0768 
0769     .irq_base   = IRQ_BOARD_START,
0770 
0771     .enable     = tosa_tc6393xb_enable,
0772     .disable    = tosa_tc6393xb_disable,
0773     .suspend    = tosa_tc6393xb_suspend,
0774     .resume     = tosa_tc6393xb_resume,
0775 
0776     .nand_data  = &tosa_tc6393xb_nand_config,
0777 #ifdef CONFIG_MFD_TC6393XB
0778     .fb_data    = &tosa_tc6393xb_fb_config,
0779 #endif
0780 
0781     .resume_restore = 1,
0782 };
0783 
0784 
0785 static struct platform_device tc6393xb_device = {
0786     .name   = "tc6393xb",
0787     .id = -1,
0788     .dev    = {
0789         .platform_data  = &tosa_tc6393xb_data,
0790     },
0791     .num_resources  = ARRAY_SIZE(tc6393xb_resources),
0792     .resource   = tc6393xb_resources,
0793 };
0794 
0795 static struct tosa_bt_data tosa_bt_data = {
0796     .gpio_pwr   = TOSA_GPIO_BT_PWR_EN,
0797     .gpio_reset = TOSA_GPIO_BT_RESET,
0798 };
0799 
0800 static struct platform_device tosa_bt_device = {
0801     .name   = "tosa-bt",
0802     .id = -1,
0803     .dev.platform_data = &tosa_bt_data,
0804 };
0805 
0806 static struct pxa2xx_spi_controller pxa_ssp_master_info = {
0807     .num_chipselect = 1,
0808 };
0809 
0810 static struct spi_board_info spi_board_info[] __initdata = {
0811     {
0812         .modalias   = "tosa-lcd",
0813         // .platform_data
0814         .max_speed_hz   = 28750,
0815         .bus_num    = 2,
0816         .chip_select    = 0,
0817         .mode       = SPI_MODE_0,
0818     },
0819 };
0820 
0821 static struct mtd_partition sharpsl_rom_parts[] = {
0822     {
0823         .name   ="Boot PROM Filesystem",
0824         .offset = 0x00160000,
0825         .size   = MTDPART_SIZ_FULL,
0826     },
0827 };
0828 
0829 static struct physmap_flash_data sharpsl_rom_data = {
0830     .width      = 2,
0831     .nr_parts   = ARRAY_SIZE(sharpsl_rom_parts),
0832     .parts      = sharpsl_rom_parts,
0833 };
0834 
0835 static struct resource sharpsl_rom_resources[] = {
0836     {
0837         .start  = 0x00000000,
0838         .end    = 0x007fffff,
0839         .flags  = IORESOURCE_MEM,
0840     },
0841 };
0842 
0843 static struct platform_device sharpsl_rom_device = {
0844     .name   = "physmap-flash",
0845     .id = -1,
0846     .resource = sharpsl_rom_resources,
0847     .num_resources = ARRAY_SIZE(sharpsl_rom_resources),
0848     .dev.platform_data = &sharpsl_rom_data,
0849 };
0850 
0851 static struct platform_device wm9712_device = {
0852     .name   = "wm9712-codec",
0853     .id = -1,
0854 };
0855 
0856 static struct platform_device tosa_audio_device = {
0857     .name   = "tosa-audio",
0858     .id = -1,
0859 };
0860 
0861 static struct platform_device *devices[] __initdata = {
0862     &tosascoop_device,
0863     &tosascoop_jc_device,
0864     &tc6393xb_device,
0865     &tosa_power_device,
0866     &tosakbd_device,
0867     &tosa_gpio_keys_device,
0868     &tosaled_device,
0869     &tosa_bt_device,
0870     &sharpsl_rom_device,
0871     &wm9712_device,
0872     &tosa_gpio_vbus,
0873     &tosa_audio_device,
0874 };
0875 
0876 static void tosa_poweroff(void)
0877 {
0878     pxa_restart(REBOOT_GPIO, NULL);
0879 }
0880 
0881 static void tosa_restart(enum reboot_mode mode, const char *cmd)
0882 {
0883     uint32_t msc0 = __raw_readl(MSC0);
0884 
0885     /* Bootloader magic for a reboot */
0886     if((msc0 & 0xffff0000) == 0x7ff00000)
0887         __raw_writel((msc0 & 0xffff) | 0x7ee00000, MSC0);
0888 
0889     tosa_poweroff();
0890 }
0891 
0892 static void __init tosa_init(void)
0893 {
0894     pxa2xx_mfp_config(ARRAY_AND_SIZE(tosa_pin_config));
0895 
0896     pxa_set_ffuart_info(NULL);
0897     pxa_set_btuart_info(NULL);
0898     pxa_set_stuart_info(NULL);
0899 
0900     gpio_set_wake(MFP_PIN_GPIO1, 1);
0901     /* We can't pass to gpio-keys since it will drop the Reset altfunc */
0902 
0903     init_gpio_reset(TOSA_GPIO_ON_RESET, 0, 0);
0904 
0905     pm_power_off = tosa_poweroff;
0906 
0907     PCFR |= PCFR_OPDE;
0908 
0909     /* enable batt_fault */
0910     PMCR = 0x01;
0911 
0912     gpiod_add_lookup_table(&tosa_battery_gpio_table);
0913 
0914     gpiod_add_lookup_table(&tosa_mci_gpio_table);
0915     pxa_set_mci_info(&tosa_mci_platform_data);
0916     pxa_set_ficp_info(&tosa_ficp_platform_data);
0917     pxa_set_i2c_info(NULL);
0918     pxa_set_ac97_info(NULL);
0919     platform_scoop_config = &tosa_pcmcia_config;
0920 
0921     pxa2xx_set_spi_info(2, &pxa_ssp_master_info);
0922     spi_register_board_info(spi_board_info, ARRAY_SIZE(spi_board_info));
0923 
0924     clk_add_alias("CLK_CK3P6MI", tc6393xb_device.name, "GPIO11_CLK", NULL);
0925 
0926     gpiod_add_lookup_table(&tosa_udc_gpiod_table);
0927     gpiod_add_lookup_table(&tosa_power_gpiod_table);
0928     platform_add_devices(devices, ARRAY_SIZE(devices));
0929 }
0930 
0931 static void __init fixup_tosa(struct tag *tags, char **cmdline)
0932 {
0933     sharpsl_save_param();
0934     memblock_add(0xa0000000, SZ_64M);
0935 }
0936 
0937 MACHINE_START(TOSA, "SHARP Tosa")
0938     .fixup          = fixup_tosa,
0939     .map_io         = pxa25x_map_io,
0940     .nr_irqs    = TOSA_NR_IRQS,
0941     .init_irq       = pxa25x_init_irq,
0942     .handle_irq       = pxa25x_handle_irq,
0943     .init_machine   = tosa_init,
0944     .init_time  = pxa_timer_init,
0945     .restart    = tosa_restart,
0946 MACHINE_END