1 /* 2 * Flash and EPROM on Hitachi Solution Engine and similar boards. 3 * 4 * (C) 2001 Red Hat, Inc. 5 * 6 * GPL'd 7 */ 8 9 #include <linux/module.h> 10 #include <linux/types.h> 11 #include <linux/kernel.h> 12 #include <linux/init.h> 13 #include <asm/io.h> 14 #include <linux/mtd/mtd.h> 15 #include <linux/mtd/map.h> 16 #include <linux/mtd/partitions.h> 17 #include <linux/errno.h> 18 19 static struct mtd_info *flash_mtd; 20 static struct mtd_info *eprom_mtd; 21 22 struct map_info soleng_eprom_map = { 23 .name = "Solution Engine EPROM", 24 .size = 0x400000, 25 .bankwidth = 4, 26 }; 27 28 struct map_info soleng_flash_map = { 29 .name = "Solution Engine FLASH", 30 .size = 0x400000, 31 .bankwidth = 4, 32 }; 33 34 static const char * const probes[] = { "RedBoot", "cmdlinepart", NULL }; 35 36 #ifdef CONFIG_MTD_SUPERH_RESERVE 37 static struct mtd_partition superh_se_partitions[] = { 38 /* Reserved for boot code, read-only */ 39 { 40 .name = "flash_boot", 41 .offset = 0x00000000, 42 .size = CONFIG_MTD_SUPERH_RESERVE, 43 .mask_flags = MTD_WRITEABLE, 44 }, 45 /* All else is writable (e.g. JFFS) */ 46 { 47 .name = "Flash FS", 48 .offset = MTDPART_OFS_NXTBLK, 49 .size = MTDPART_SIZ_FULL, 50 } 51 }; 52 #define NUM_PARTITIONS ARRAY_SIZE(superh_se_partitions) 53 #else 54 #define superh_se_partitions NULL 55 #define NUM_PARTITIONS 0 56 #endif /* CONFIG_MTD_SUPERH_RESERVE */ 57 58 static int __init init_soleng_maps(void) 59 { 60 /* First probe at offset 0 */ 61 soleng_flash_map.phys = 0; 62 soleng_flash_map.virt = (void __iomem *)P2SEGADDR(0); 63 soleng_eprom_map.phys = 0x01000000; 64 soleng_eprom_map.virt = (void __iomem *)P1SEGADDR(0x01000000); 65 simple_map_init(&soleng_eprom_map); 66 simple_map_init(&soleng_flash_map); 67 68 printk(KERN_NOTICE "Probing for flash chips at 0x00000000:\n"); 69 flash_mtd = do_map_probe("cfi_probe", &soleng_flash_map); 70 if (!flash_mtd) { 71 /* Not there. Try swapping */ 72 printk(KERN_NOTICE "Probing for flash chips at 0x01000000:\n"); 73 soleng_flash_map.phys = 0x01000000; 74 soleng_flash_map.virt = P2SEGADDR(0x01000000); 75 soleng_eprom_map.phys = 0; 76 soleng_eprom_map.virt = P1SEGADDR(0); 77 flash_mtd = do_map_probe("cfi_probe", &soleng_flash_map); 78 if (!flash_mtd) { 79 /* Eep. */ 80 printk(KERN_NOTICE "Flash chips not detected at either possible location.\n"); 81 return -ENXIO; 82 } 83 } 84 printk(KERN_NOTICE "Solution Engine: Flash at 0x%08lx, EPROM at 0x%08lx\n", 85 soleng_flash_map.phys & 0x1fffffff, 86 soleng_eprom_map.phys & 0x1fffffff); 87 flash_mtd->owner = THIS_MODULE; 88 89 eprom_mtd = do_map_probe("map_rom", &soleng_eprom_map); 90 if (eprom_mtd) { 91 eprom_mtd->owner = THIS_MODULE; 92 mtd_device_register(eprom_mtd, NULL, 0); 93 } 94 95 mtd_device_parse_register(flash_mtd, probes, NULL, 96 superh_se_partitions, NUM_PARTITIONS); 97 98 return 0; 99 } 100 101 static void __exit cleanup_soleng_maps(void) 102 { 103 if (eprom_mtd) { 104 mtd_device_unregister(eprom_mtd); 105 map_destroy(eprom_mtd); 106 } 107 108 mtd_device_unregister(flash_mtd); 109 map_destroy(flash_mtd); 110 } 111 112 module_init(init_soleng_maps); 113 module_exit(cleanup_soleng_maps); 114 115 MODULE_LICENSE("GPL"); 116 MODULE_AUTHOR("David Woodhouse <dwmw2@infradead.org>"); 117 MODULE_DESCRIPTION("MTD map driver for Hitachi SolutionEngine (and similar) boards"); 118 119