Linux kernel mirror (for testing) git.kernel.org/pub/scm/linux/kernel/git/torvalds/linux.git
kernel os linux

ARM: ep93xx: use soc bus

Use the soc bus to report the silicon revision and Maverick Key. Both
are not currently exposed to the user. In addition, fill in the SoC
family and machine for completeness.

Signed-off-by: H Hartley Sweeten <hsweeten@visionengravers.com>
Acked-by: Ryan Mallon <rmallon@gmail.com>
Signed-off-by: Ryan Mallon <rmallon@gmail.com>
Cc: Alexander Shiyan <shc_work@mail.ru>
Signed-off-by: Olof Johansson <olof@lixom.net>

authored by

H Hartley Sweeten and committed by
Olof Johansson
b19e11fb 3a71ae47

+110 -2
+1
arch/arm/mach-ep93xx/Kconfig
··· 5 5 config EP93XX_SOC_COMMON 6 6 bool 7 7 default y 8 + select SOC_BUS 8 9 select LEDS_GPIO_REGISTER 9 10 10 11 config CRUNCH
+107 -1
arch/arm/mach-ep93xx/core.c
··· 21 21 #include <linux/platform_device.h> 22 22 #include <linux/interrupt.h> 23 23 #include <linux/dma-mapping.h> 24 + #include <linux/sys_soc.h> 24 25 #include <linux/timex.h> 25 26 #include <linux/irq.h> 26 27 #include <linux/io.h> ··· 45 44 #include <linux/platform_data/spi-ep93xx.h> 46 45 #include <mach/gpio-ep93xx.h> 47 46 47 + #include <asm/mach/arch.h> 48 48 #include <asm/mach/map.h> 49 49 #include <asm/mach/time.h> 50 50 ··· 927 925 } 928 926 EXPORT_SYMBOL(ep93xx_ide_release_gpio); 929 927 930 - void __init ep93xx_init_devices(void) 928 + /************************************************************************* 929 + * EP93xx Security peripheral 930 + *************************************************************************/ 931 + 932 + /* 933 + * The Maverick Key is 256 bits of micro fuses blown at the factory during 934 + * manufacturing to uniquely identify a part. 935 + * 936 + * See: http://arm.cirrus.com/forum/viewtopic.php?t=486&highlight=maverick+key 937 + */ 938 + #define EP93XX_SECURITY_REG(x) (EP93XX_SECURITY_BASE + (x)) 939 + #define EP93XX_SECURITY_SECFLG EP93XX_SECURITY_REG(0x2400) 940 + #define EP93XX_SECURITY_FUSEFLG EP93XX_SECURITY_REG(0x2410) 941 + #define EP93XX_SECURITY_UNIQID EP93XX_SECURITY_REG(0x2440) 942 + #define EP93XX_SECURITY_UNIQCHK EP93XX_SECURITY_REG(0x2450) 943 + #define EP93XX_SECURITY_UNIQVAL EP93XX_SECURITY_REG(0x2460) 944 + #define EP93XX_SECURITY_SECID1 EP93XX_SECURITY_REG(0x2500) 945 + #define EP93XX_SECURITY_SECID2 EP93XX_SECURITY_REG(0x2504) 946 + #define EP93XX_SECURITY_SECCHK1 EP93XX_SECURITY_REG(0x2520) 947 + #define EP93XX_SECURITY_SECCHK2 EP93XX_SECURITY_REG(0x2524) 948 + #define EP93XX_SECURITY_UNIQID2 EP93XX_SECURITY_REG(0x2700) 949 + #define EP93XX_SECURITY_UNIQID3 EP93XX_SECURITY_REG(0x2704) 950 + #define EP93XX_SECURITY_UNIQID4 EP93XX_SECURITY_REG(0x2708) 951 + #define EP93XX_SECURITY_UNIQID5 EP93XX_SECURITY_REG(0x270c) 952 + 953 + static char ep93xx_soc_id[33]; 954 + 955 + static const char __init *ep93xx_get_soc_id(void) 931 956 { 957 + unsigned int id, id2, id3, id4, id5; 958 + 959 + if (__raw_readl(EP93XX_SECURITY_UNIQVAL) != 1) 960 + return "bad Hamming code"; 961 + 962 + id = __raw_readl(EP93XX_SECURITY_UNIQID); 963 + id2 = __raw_readl(EP93XX_SECURITY_UNIQID2); 964 + id3 = __raw_readl(EP93XX_SECURITY_UNIQID3); 965 + id4 = __raw_readl(EP93XX_SECURITY_UNIQID4); 966 + id5 = __raw_readl(EP93XX_SECURITY_UNIQID5); 967 + 968 + if (id != id2) 969 + return "invalid"; 970 + 971 + snprintf(ep93xx_soc_id, sizeof(ep93xx_soc_id), 972 + "%08x%08x%08x%08x", id2, id3, id4, id5); 973 + 974 + return ep93xx_soc_id; 975 + } 976 + 977 + static const char __init *ep93xx_get_soc_rev(void) 978 + { 979 + int rev = ep93xx_chip_revision(); 980 + 981 + switch (rev) { 982 + case EP93XX_CHIP_REV_D0: 983 + return "D0"; 984 + case EP93XX_CHIP_REV_D1: 985 + return "D1"; 986 + case EP93XX_CHIP_REV_E0: 987 + return "E0"; 988 + case EP93XX_CHIP_REV_E1: 989 + return "E1"; 990 + case EP93XX_CHIP_REV_E2: 991 + return "E2"; 992 + default: 993 + return "unknown"; 994 + } 995 + } 996 + 997 + static const char __init *ep93xx_get_machine_name(void) 998 + { 999 + return kasprintf(GFP_KERNEL,"%s", machine_desc->name); 1000 + } 1001 + 1002 + static struct device __init *ep93xx_init_soc(void) 1003 + { 1004 + struct soc_device_attribute *soc_dev_attr; 1005 + struct soc_device *soc_dev; 1006 + 1007 + soc_dev_attr = kzalloc(sizeof(*soc_dev_attr), GFP_KERNEL); 1008 + if (!soc_dev_attr) 1009 + return NULL; 1010 + 1011 + soc_dev_attr->machine = ep93xx_get_machine_name(); 1012 + soc_dev_attr->family = "Cirrus Logic EP93xx"; 1013 + soc_dev_attr->revision = ep93xx_get_soc_rev(); 1014 + soc_dev_attr->soc_id = ep93xx_get_soc_id(); 1015 + 1016 + soc_dev = soc_device_register(soc_dev_attr); 1017 + if (IS_ERR(soc_dev)) { 1018 + kfree(soc_dev_attr->machine); 1019 + kfree(soc_dev_attr); 1020 + return NULL; 1021 + } 1022 + 1023 + return soc_device_to_device(soc_dev); 1024 + } 1025 + 1026 + struct device __init *ep93xx_init_devices(void) 1027 + { 1028 + struct device *parent; 1029 + 932 1030 /* Disallow access to MaverickCrunch initially */ 933 1031 ep93xx_devcfg_clear_bits(EP93XX_SYSCON_DEVCFG_CPENA); 934 1032 ··· 1038 936 EP93XX_SYSCON_DEVCFG_EONIDE | 1039 937 EP93XX_SYSCON_DEVCFG_GONIDE | 1040 938 EP93XX_SYSCON_DEVCFG_HONIDE); 939 + 940 + parent = ep93xx_init_soc(); 1041 941 1042 942 /* Get the GPIO working early, other devices need it */ 1043 943 platform_device_register(&ep93xx_gpio_device); ··· 1053 949 platform_device_register(&ep93xx_wdt_device); 1054 950 1055 951 gpio_led_register_device(-1, &ep93xx_led_data); 952 + 953 + return parent; 1056 954 } 1057 955 1058 956 void ep93xx_restart(enum reboot_mode mode, const char *cmd)
+2 -1
arch/arm/mach-ep93xx/include/mach/platform.h
··· 6 6 7 7 #include <linux/reboot.h> 8 8 9 + struct device; 9 10 struct i2c_gpio_platform_data; 10 11 struct i2c_board_info; 11 12 struct spi_board_info; ··· 55 54 int ep93xx_ide_acquire_gpio(struct platform_device *pdev); 56 55 void ep93xx_ide_release_gpio(struct platform_device *pdev); 57 56 58 - void ep93xx_init_devices(void); 57 + struct device *ep93xx_init_devices(void); 59 58 extern void ep93xx_timer_init(void); 60 59 61 60 void ep93xx_restart(enum reboot_mode, const char *);