0001
0002
0003
0004
0005
0006
0007
0008 #define pr_fmt(fmt) KBUILD_MODNAME ": " fmt
0009
0010 #include <linux/kernel.h>
0011 #include <linux/init.h>
0012 #include <linux/sysfs.h>
0013 #include <linux/platform_device.h>
0014 #include <linux/mv643xx_eth.h>
0015 #include <linux/ata_platform.h>
0016 #include <linux/mtd/platnand.h>
0017 #include <linux/timeriomem-rng.h>
0018 #include <asm/mach-types.h>
0019 #include <asm/mach/arch.h>
0020 #include <asm/mach/map.h>
0021 #include "common.h"
0022 #include "mpp.h"
0023 #include "orion5x.h"
0024 #include "ts78xx-fpga.h"
0025
0026
0027
0028
0029
0030
0031
0032
0033 #define TS78XX_FPGA_REGS_PHYS_BASE 0xe8000000
0034 #define TS78XX_FPGA_REGS_VIRT_BASE IOMEM(0xff900000)
0035 #define TS78XX_FPGA_REGS_SIZE SZ_1M
0036
0037 static struct ts78xx_fpga_data ts78xx_fpga = {
0038 .id = 0,
0039 .state = 1,
0040
0041 };
0042
0043
0044
0045
0046 static struct map_desc ts78xx_io_desc[] __initdata = {
0047 {
0048 .virtual = (unsigned long)TS78XX_FPGA_REGS_VIRT_BASE,
0049 .pfn = __phys_to_pfn(TS78XX_FPGA_REGS_PHYS_BASE),
0050 .length = TS78XX_FPGA_REGS_SIZE,
0051 .type = MT_DEVICE,
0052 },
0053 };
0054
0055 static void __init ts78xx_map_io(void)
0056 {
0057 orion5x_map_io();
0058 iotable_init(ts78xx_io_desc, ARRAY_SIZE(ts78xx_io_desc));
0059 }
0060
0061
0062
0063
0064 static struct mv643xx_eth_platform_data ts78xx_eth_data = {
0065 .phy_addr = MV643XX_ETH_PHY_ADDR(0),
0066 };
0067
0068
0069
0070
0071 static struct mv_sata_platform_data ts78xx_sata_data = {
0072 .n_ports = 2,
0073 };
0074
0075
0076
0077
0078 #define TS_RTC_CTRL (TS78XX_FPGA_REGS_PHYS_BASE + 0x808)
0079 #define TS_RTC_DATA (TS78XX_FPGA_REGS_PHYS_BASE + 0x80c)
0080
0081 static struct resource ts78xx_ts_rtc_resources[] = {
0082 DEFINE_RES_MEM(TS_RTC_CTRL, 0x01),
0083 DEFINE_RES_MEM(TS_RTC_DATA, 0x01),
0084 };
0085
0086 static struct platform_device ts78xx_ts_rtc_device = {
0087 .name = "rtc-m48t86",
0088 .id = -1,
0089 .resource = ts78xx_ts_rtc_resources,
0090 .num_resources = ARRAY_SIZE(ts78xx_ts_rtc_resources),
0091 };
0092
0093 static int ts78xx_ts_rtc_load(void)
0094 {
0095 int rc;
0096
0097 if (ts78xx_fpga.supports.ts_rtc.init == 0) {
0098 rc = platform_device_register(&ts78xx_ts_rtc_device);
0099 if (!rc)
0100 ts78xx_fpga.supports.ts_rtc.init = 1;
0101 } else {
0102 rc = platform_device_add(&ts78xx_ts_rtc_device);
0103 }
0104
0105 if (rc)
0106 pr_info("RTC could not be registered: %d\n", rc);
0107
0108 return rc;
0109 }
0110
0111 static void ts78xx_ts_rtc_unload(void)
0112 {
0113 platform_device_del(&ts78xx_ts_rtc_device);
0114 }
0115
0116
0117
0118
0119 #define TS_NAND_CTRL (TS78XX_FPGA_REGS_VIRT_BASE + 0x800)
0120 #define TS_NAND_DATA (TS78XX_FPGA_REGS_PHYS_BASE + 0x804)
0121
0122
0123
0124
0125
0126
0127
0128
0129
0130 static void ts78xx_ts_nand_cmd_ctrl(struct nand_chip *this, int cmd,
0131 unsigned int ctrl)
0132 {
0133 if (ctrl & NAND_CTRL_CHANGE) {
0134 unsigned char bits;
0135
0136 bits = (ctrl & NAND_NCE) << 2;
0137 bits |= ctrl & NAND_CLE;
0138 bits |= (ctrl & NAND_ALE) >> 2;
0139
0140 writeb((readb(TS_NAND_CTRL) & ~0x7) | bits, TS_NAND_CTRL);
0141 }
0142
0143 if (cmd != NAND_CMD_NONE)
0144 writeb(cmd, this->legacy.IO_ADDR_W);
0145 }
0146
0147 static int ts78xx_ts_nand_dev_ready(struct nand_chip *chip)
0148 {
0149 return readb(TS_NAND_CTRL) & 0x20;
0150 }
0151
0152 static void ts78xx_ts_nand_write_buf(struct nand_chip *chip,
0153 const uint8_t *buf, int len)
0154 {
0155 void __iomem *io_base = chip->legacy.IO_ADDR_W;
0156 unsigned long off = ((unsigned long)buf & 3);
0157 int sz;
0158
0159 if (off) {
0160 sz = min_t(int, 4 - off, len);
0161 writesb(io_base, buf, sz);
0162 buf += sz;
0163 len -= sz;
0164 }
0165
0166 sz = len >> 2;
0167 if (sz) {
0168 u32 *buf32 = (u32 *)buf;
0169 writesl(io_base, buf32, sz);
0170 buf += sz << 2;
0171 len -= sz << 2;
0172 }
0173
0174 if (len)
0175 writesb(io_base, buf, len);
0176 }
0177
0178 static void ts78xx_ts_nand_read_buf(struct nand_chip *chip,
0179 uint8_t *buf, int len)
0180 {
0181 void __iomem *io_base = chip->legacy.IO_ADDR_R;
0182 unsigned long off = ((unsigned long)buf & 3);
0183 int sz;
0184
0185 if (off) {
0186 sz = min_t(int, 4 - off, len);
0187 readsb(io_base, buf, sz);
0188 buf += sz;
0189 len -= sz;
0190 }
0191
0192 sz = len >> 2;
0193 if (sz) {
0194 u32 *buf32 = (u32 *)buf;
0195 readsl(io_base, buf32, sz);
0196 buf += sz << 2;
0197 len -= sz << 2;
0198 }
0199
0200 if (len)
0201 readsb(io_base, buf, len);
0202 }
0203
0204 static struct mtd_partition ts78xx_ts_nand_parts[] = {
0205 {
0206 .name = "mbr",
0207 .offset = 0,
0208 .size = SZ_128K,
0209 .mask_flags = MTD_WRITEABLE,
0210 }, {
0211 .name = "kernel",
0212 .offset = MTDPART_OFS_APPEND,
0213 .size = SZ_4M,
0214 }, {
0215 .name = "initrd",
0216 .offset = MTDPART_OFS_APPEND,
0217 .size = SZ_4M,
0218 }, {
0219 .name = "rootfs",
0220 .offset = MTDPART_OFS_APPEND,
0221 .size = MTDPART_SIZ_FULL,
0222 }
0223 };
0224
0225 static struct platform_nand_data ts78xx_ts_nand_data = {
0226 .chip = {
0227 .nr_chips = 1,
0228 .partitions = ts78xx_ts_nand_parts,
0229 .nr_partitions = ARRAY_SIZE(ts78xx_ts_nand_parts),
0230 .chip_delay = 15,
0231 .bbt_options = NAND_BBT_USE_FLASH,
0232 },
0233 .ctrl = {
0234
0235
0236
0237
0238
0239
0240
0241 .cmd_ctrl = ts78xx_ts_nand_cmd_ctrl,
0242 .dev_ready = ts78xx_ts_nand_dev_ready,
0243 .write_buf = ts78xx_ts_nand_write_buf,
0244 .read_buf = ts78xx_ts_nand_read_buf,
0245 },
0246 };
0247
0248 static struct resource ts78xx_ts_nand_resources
0249 = DEFINE_RES_MEM(TS_NAND_DATA, 4);
0250
0251 static struct platform_device ts78xx_ts_nand_device = {
0252 .name = "gen_nand",
0253 .id = -1,
0254 .dev = {
0255 .platform_data = &ts78xx_ts_nand_data,
0256 },
0257 .resource = &ts78xx_ts_nand_resources,
0258 .num_resources = 1,
0259 };
0260
0261 static int ts78xx_ts_nand_load(void)
0262 {
0263 int rc;
0264
0265 if (ts78xx_fpga.supports.ts_nand.init == 0) {
0266 rc = platform_device_register(&ts78xx_ts_nand_device);
0267 if (!rc)
0268 ts78xx_fpga.supports.ts_nand.init = 1;
0269 } else
0270 rc = platform_device_add(&ts78xx_ts_nand_device);
0271
0272 if (rc)
0273 pr_info("NAND could not be registered: %d\n", rc);
0274 return rc;
0275 };
0276
0277 static void ts78xx_ts_nand_unload(void)
0278 {
0279 platform_device_del(&ts78xx_ts_nand_device);
0280 }
0281
0282
0283
0284
0285 #define TS_RNG_DATA (TS78XX_FPGA_REGS_PHYS_BASE | 0x044)
0286
0287 static struct resource ts78xx_ts_rng_resource
0288 = DEFINE_RES_MEM(TS_RNG_DATA, 4);
0289
0290 static struct timeriomem_rng_data ts78xx_ts_rng_data = {
0291 .period = 1000000,
0292 };
0293
0294 static struct platform_device ts78xx_ts_rng_device = {
0295 .name = "timeriomem_rng",
0296 .id = -1,
0297 .dev = {
0298 .platform_data = &ts78xx_ts_rng_data,
0299 },
0300 .resource = &ts78xx_ts_rng_resource,
0301 .num_resources = 1,
0302 };
0303
0304 static int ts78xx_ts_rng_load(void)
0305 {
0306 int rc;
0307
0308 if (ts78xx_fpga.supports.ts_rng.init == 0) {
0309 rc = platform_device_register(&ts78xx_ts_rng_device);
0310 if (!rc)
0311 ts78xx_fpga.supports.ts_rng.init = 1;
0312 } else
0313 rc = platform_device_add(&ts78xx_ts_rng_device);
0314
0315 if (rc)
0316 pr_info("RNG could not be registered: %d\n", rc);
0317 return rc;
0318 };
0319
0320 static void ts78xx_ts_rng_unload(void)
0321 {
0322 platform_device_del(&ts78xx_ts_rng_device);
0323 }
0324
0325
0326
0327
0328 static void ts78xx_fpga_devices_zero_init(void)
0329 {
0330 ts78xx_fpga.supports.ts_rtc.init = 0;
0331 ts78xx_fpga.supports.ts_nand.init = 0;
0332 ts78xx_fpga.supports.ts_rng.init = 0;
0333 }
0334
0335 static void ts78xx_fpga_supports(void)
0336 {
0337
0338 switch (ts78xx_fpga.id) {
0339 case TS7800_REV_1:
0340 case TS7800_REV_2:
0341 case TS7800_REV_3:
0342 case TS7800_REV_4:
0343 case TS7800_REV_5:
0344 case TS7800_REV_6:
0345 case TS7800_REV_7:
0346 case TS7800_REV_8:
0347 case TS7800_REV_9:
0348 ts78xx_fpga.supports.ts_rtc.present = 1;
0349 ts78xx_fpga.supports.ts_nand.present = 1;
0350 ts78xx_fpga.supports.ts_rng.present = 1;
0351 break;
0352 default:
0353
0354 switch ((ts78xx_fpga.id >> 8) & 0xffffff) {
0355 case TS7800_FPGA_MAGIC:
0356 pr_warn("unrecognised FPGA revision 0x%.2x\n",
0357 ts78xx_fpga.id & 0xff);
0358 ts78xx_fpga.supports.ts_rtc.present = 1;
0359 ts78xx_fpga.supports.ts_nand.present = 1;
0360 ts78xx_fpga.supports.ts_rng.present = 1;
0361 break;
0362 default:
0363 ts78xx_fpga.supports.ts_rtc.present = 0;
0364 ts78xx_fpga.supports.ts_nand.present = 0;
0365 ts78xx_fpga.supports.ts_rng.present = 0;
0366 }
0367 }
0368 }
0369
0370 static int ts78xx_fpga_load_devices(void)
0371 {
0372 int tmp, ret = 0;
0373
0374 if (ts78xx_fpga.supports.ts_rtc.present == 1) {
0375 tmp = ts78xx_ts_rtc_load();
0376 if (tmp)
0377 ts78xx_fpga.supports.ts_rtc.present = 0;
0378 ret |= tmp;
0379 }
0380 if (ts78xx_fpga.supports.ts_nand.present == 1) {
0381 tmp = ts78xx_ts_nand_load();
0382 if (tmp)
0383 ts78xx_fpga.supports.ts_nand.present = 0;
0384 ret |= tmp;
0385 }
0386 if (ts78xx_fpga.supports.ts_rng.present == 1) {
0387 tmp = ts78xx_ts_rng_load();
0388 if (tmp)
0389 ts78xx_fpga.supports.ts_rng.present = 0;
0390 ret |= tmp;
0391 }
0392
0393 return ret;
0394 }
0395
0396 static int ts78xx_fpga_unload_devices(void)
0397 {
0398
0399 if (ts78xx_fpga.supports.ts_rtc.present == 1)
0400 ts78xx_ts_rtc_unload();
0401 if (ts78xx_fpga.supports.ts_nand.present == 1)
0402 ts78xx_ts_nand_unload();
0403 if (ts78xx_fpga.supports.ts_rng.present == 1)
0404 ts78xx_ts_rng_unload();
0405
0406 return 0;
0407 }
0408
0409 static int ts78xx_fpga_load(void)
0410 {
0411 ts78xx_fpga.id = readl(TS78XX_FPGA_REGS_VIRT_BASE);
0412
0413 pr_info("FPGA magic=0x%.6x, rev=0x%.2x\n",
0414 (ts78xx_fpga.id >> 8) & 0xffffff,
0415 ts78xx_fpga.id & 0xff);
0416
0417 ts78xx_fpga_supports();
0418
0419 if (ts78xx_fpga_load_devices()) {
0420 ts78xx_fpga.state = -1;
0421 return -EBUSY;
0422 }
0423
0424 return 0;
0425 };
0426
0427 static int ts78xx_fpga_unload(void)
0428 {
0429 unsigned int fpga_id;
0430
0431 fpga_id = readl(TS78XX_FPGA_REGS_VIRT_BASE);
0432
0433
0434
0435
0436
0437
0438
0439
0440 if (ts78xx_fpga.id != fpga_id) {
0441 pr_err("FPGA magic/rev mismatch\n"
0442 "TS-78xx FPGA: was 0x%.6x/%.2x but now 0x%.6x/%.2x\n",
0443 (ts78xx_fpga.id >> 8) & 0xffffff, ts78xx_fpga.id & 0xff,
0444 (fpga_id >> 8) & 0xffffff, fpga_id & 0xff);
0445 ts78xx_fpga.state = -1;
0446 return -EBUSY;
0447 }
0448
0449 if (ts78xx_fpga_unload_devices()) {
0450 ts78xx_fpga.state = -1;
0451 return -EBUSY;
0452 }
0453
0454 return 0;
0455 };
0456
0457 static ssize_t ts78xx_fpga_show(struct kobject *kobj,
0458 struct kobj_attribute *attr, char *buf)
0459 {
0460 if (ts78xx_fpga.state < 0)
0461 return sprintf(buf, "borked\n");
0462
0463 return sprintf(buf, "%s\n", (ts78xx_fpga.state) ? "online" : "offline");
0464 }
0465
0466 static ssize_t ts78xx_fpga_store(struct kobject *kobj,
0467 struct kobj_attribute *attr, const char *buf, size_t n)
0468 {
0469 int value, ret;
0470
0471 if (ts78xx_fpga.state < 0) {
0472 pr_err("FPGA borked, you must powercycle ASAP\n");
0473 return -EBUSY;
0474 }
0475
0476 if (strncmp(buf, "online", sizeof("online") - 1) == 0)
0477 value = 1;
0478 else if (strncmp(buf, "offline", sizeof("offline") - 1) == 0)
0479 value = 0;
0480 else
0481 return -EINVAL;
0482
0483 if (ts78xx_fpga.state == value)
0484 return n;
0485
0486 ret = (ts78xx_fpga.state == 0)
0487 ? ts78xx_fpga_load()
0488 : ts78xx_fpga_unload();
0489
0490 if (!(ret < 0))
0491 ts78xx_fpga.state = value;
0492
0493 return n;
0494 }
0495
0496 static struct kobj_attribute ts78xx_fpga_attr =
0497 __ATTR(ts78xx_fpga, 0644, ts78xx_fpga_show, ts78xx_fpga_store);
0498
0499
0500
0501
0502 static unsigned int ts78xx_mpp_modes[] __initdata = {
0503 MPP0_UNUSED,
0504 MPP1_GPIO,
0505 MPP2_GPIO,
0506 MPP3_GPIO,
0507 MPP4_GPIO,
0508 MPP5_GPIO,
0509 MPP6_GPIO,
0510 MPP7_GPIO,
0511 MPP8_UNUSED,
0512 MPP9_UNUSED,
0513 MPP10_UNUSED,
0514 MPP11_UNUSED,
0515 MPP12_UNUSED,
0516 MPP13_UNUSED,
0517 MPP14_UNUSED,
0518 MPP15_UNUSED,
0519 MPP16_UART,
0520 MPP17_UART,
0521 MPP18_UART,
0522 MPP19_UART,
0523
0524
0525
0526
0527
0528
0529
0530
0531 0,
0532 };
0533
0534 static void __init ts78xx_init(void)
0535 {
0536 int ret;
0537
0538
0539
0540
0541 orion5x_init();
0542
0543 orion5x_mpp_conf(ts78xx_mpp_modes);
0544
0545
0546
0547
0548 orion5x_ehci0_init();
0549 orion5x_ehci1_init();
0550 orion5x_eth_init(&ts78xx_eth_data);
0551 orion5x_sata_init(&ts78xx_sata_data);
0552 orion5x_uart0_init();
0553 orion5x_uart1_init();
0554 orion5x_xor_init();
0555
0556
0557 ts78xx_fpga_devices_zero_init();
0558 ret = ts78xx_fpga_load();
0559 ret = sysfs_create_file(firmware_kobj, &ts78xx_fpga_attr.attr);
0560 if (ret)
0561 pr_err("sysfs_create_file failed: %d\n", ret);
0562 }
0563
0564 MACHINE_START(TS78XX, "Technologic Systems TS-78xx SBC")
0565
0566 .atag_offset = 0x100,
0567 .nr_irqs = ORION5X_NR_IRQS,
0568 .init_machine = ts78xx_init,
0569 .map_io = ts78xx_map_io,
0570 .init_early = orion5x_init_early,
0571 .init_irq = orion5x_init_irq,
0572 .init_time = orion5x_timer_init,
0573 .restart = orion5x_restart,
0574 MACHINE_END