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

Configure Feed

Select the types of activity you want to include in your feed.

at v5.9 358 lines 9.1 kB view raw
1// SPDX-License-Identifier: GPL-2.0-only 2/* 3 * Copyright (c) 2013-2014, NVIDIA CORPORATION. All rights reserved. 4 */ 5 6#include <linux/device.h> 7#include <linux/clk.h> 8#include <linux/err.h> 9#include <linux/io.h> 10#include <linux/kernel.h> 11#include <linux/nvmem-consumer.h> 12#include <linux/of_device.h> 13#include <linux/of_address.h> 14#include <linux/platform_device.h> 15#include <linux/random.h> 16 17#include <soc/tegra/fuse.h> 18 19#include "fuse.h" 20 21#define FUSE_BEGIN 0x100 22 23/* Tegra30 and later */ 24#define FUSE_VENDOR_CODE 0x100 25#define FUSE_FAB_CODE 0x104 26#define FUSE_LOT_CODE_0 0x108 27#define FUSE_LOT_CODE_1 0x10c 28#define FUSE_WAFER_ID 0x110 29#define FUSE_X_COORDINATE 0x114 30#define FUSE_Y_COORDINATE 0x118 31 32#define FUSE_HAS_REVISION_INFO BIT(0) 33 34#if defined(CONFIG_ARCH_TEGRA_3x_SOC) || \ 35 defined(CONFIG_ARCH_TEGRA_114_SOC) || \ 36 defined(CONFIG_ARCH_TEGRA_124_SOC) || \ 37 defined(CONFIG_ARCH_TEGRA_132_SOC) || \ 38 defined(CONFIG_ARCH_TEGRA_210_SOC) || \ 39 defined(CONFIG_ARCH_TEGRA_186_SOC) || \ 40 defined(CONFIG_ARCH_TEGRA_194_SOC) 41static u32 tegra30_fuse_read_early(struct tegra_fuse *fuse, unsigned int offset) 42{ 43 if (WARN_ON(!fuse->base)) 44 return 0; 45 46 return readl_relaxed(fuse->base + FUSE_BEGIN + offset); 47} 48 49static u32 tegra30_fuse_read(struct tegra_fuse *fuse, unsigned int offset) 50{ 51 u32 value; 52 int err; 53 54 err = clk_prepare_enable(fuse->clk); 55 if (err < 0) { 56 dev_err(fuse->dev, "failed to enable FUSE clock: %d\n", err); 57 return 0; 58 } 59 60 value = readl_relaxed(fuse->base + FUSE_BEGIN + offset); 61 62 clk_disable_unprepare(fuse->clk); 63 64 return value; 65} 66 67static void __init tegra30_fuse_add_randomness(void) 68{ 69 u32 randomness[12]; 70 71 randomness[0] = tegra_sku_info.sku_id; 72 randomness[1] = tegra_read_straps(); 73 randomness[2] = tegra_read_chipid(); 74 randomness[3] = tegra_sku_info.cpu_process_id << 16; 75 randomness[3] |= tegra_sku_info.soc_process_id; 76 randomness[4] = tegra_sku_info.cpu_speedo_id << 16; 77 randomness[4] |= tegra_sku_info.soc_speedo_id; 78 randomness[5] = tegra_fuse_read_early(FUSE_VENDOR_CODE); 79 randomness[6] = tegra_fuse_read_early(FUSE_FAB_CODE); 80 randomness[7] = tegra_fuse_read_early(FUSE_LOT_CODE_0); 81 randomness[8] = tegra_fuse_read_early(FUSE_LOT_CODE_1); 82 randomness[9] = tegra_fuse_read_early(FUSE_WAFER_ID); 83 randomness[10] = tegra_fuse_read_early(FUSE_X_COORDINATE); 84 randomness[11] = tegra_fuse_read_early(FUSE_Y_COORDINATE); 85 86 add_device_randomness(randomness, sizeof(randomness)); 87} 88 89static void __init tegra30_fuse_init(struct tegra_fuse *fuse) 90{ 91 fuse->read_early = tegra30_fuse_read_early; 92 fuse->read = tegra30_fuse_read; 93 94 tegra_init_revision(); 95 96 if (fuse->soc->speedo_init) 97 fuse->soc->speedo_init(&tegra_sku_info); 98 99 tegra30_fuse_add_randomness(); 100} 101#endif 102 103#ifdef CONFIG_ARCH_TEGRA_3x_SOC 104static const struct tegra_fuse_info tegra30_fuse_info = { 105 .read = tegra30_fuse_read, 106 .size = 0x2a4, 107 .spare = 0x144, 108}; 109 110const struct tegra_fuse_soc tegra30_fuse_soc = { 111 .init = tegra30_fuse_init, 112 .speedo_init = tegra30_init_speedo_data, 113 .info = &tegra30_fuse_info, 114 .soc_attr_group = &tegra_soc_attr_group, 115}; 116#endif 117 118#ifdef CONFIG_ARCH_TEGRA_114_SOC 119static const struct tegra_fuse_info tegra114_fuse_info = { 120 .read = tegra30_fuse_read, 121 .size = 0x2a0, 122 .spare = 0x180, 123}; 124 125const struct tegra_fuse_soc tegra114_fuse_soc = { 126 .init = tegra30_fuse_init, 127 .speedo_init = tegra114_init_speedo_data, 128 .info = &tegra114_fuse_info, 129 .soc_attr_group = &tegra_soc_attr_group, 130}; 131#endif 132 133#if defined(CONFIG_ARCH_TEGRA_124_SOC) || defined(CONFIG_ARCH_TEGRA_132_SOC) 134static const struct nvmem_cell_lookup tegra124_fuse_lookups[] = { 135 { 136 .nvmem_name = "fuse", 137 .cell_name = "xusb-pad-calibration", 138 .dev_id = "7009f000.padctl", 139 .con_id = "calibration", 140 }, { 141 .nvmem_name = "fuse", 142 .cell_name = "sata-calibration", 143 .dev_id = "70020000.sata", 144 .con_id = "calibration", 145 }, { 146 .nvmem_name = "fuse", 147 .cell_name = "tsensor-common", 148 .dev_id = "700e2000.thermal-sensor", 149 .con_id = "common", 150 }, { 151 .nvmem_name = "fuse", 152 .cell_name = "tsensor-realignment", 153 .dev_id = "700e2000.thermal-sensor", 154 .con_id = "realignment", 155 }, { 156 .nvmem_name = "fuse", 157 .cell_name = "tsensor-cpu0", 158 .dev_id = "700e2000.thermal-sensor", 159 .con_id = "cpu0", 160 }, { 161 .nvmem_name = "fuse", 162 .cell_name = "tsensor-cpu1", 163 .dev_id = "700e2000.thermal-sensor", 164 .con_id = "cpu1", 165 }, { 166 .nvmem_name = "fuse", 167 .cell_name = "tsensor-cpu2", 168 .dev_id = "700e2000.thermal-sensor", 169 .con_id = "cpu2", 170 }, { 171 .nvmem_name = "fuse", 172 .cell_name = "tsensor-cpu3", 173 .dev_id = "700e2000.thermal-sensor", 174 .con_id = "cpu3", 175 }, { 176 .nvmem_name = "fuse", 177 .cell_name = "tsensor-mem0", 178 .dev_id = "700e2000.thermal-sensor", 179 .con_id = "mem0", 180 }, { 181 .nvmem_name = "fuse", 182 .cell_name = "tsensor-mem1", 183 .dev_id = "700e2000.thermal-sensor", 184 .con_id = "mem1", 185 }, { 186 .nvmem_name = "fuse", 187 .cell_name = "tsensor-gpu", 188 .dev_id = "700e2000.thermal-sensor", 189 .con_id = "gpu", 190 }, { 191 .nvmem_name = "fuse", 192 .cell_name = "tsensor-pllx", 193 .dev_id = "700e2000.thermal-sensor", 194 .con_id = "pllx", 195 }, 196}; 197 198static const struct tegra_fuse_info tegra124_fuse_info = { 199 .read = tegra30_fuse_read, 200 .size = 0x300, 201 .spare = 0x200, 202}; 203 204const struct tegra_fuse_soc tegra124_fuse_soc = { 205 .init = tegra30_fuse_init, 206 .speedo_init = tegra124_init_speedo_data, 207 .info = &tegra124_fuse_info, 208 .lookups = tegra124_fuse_lookups, 209 .num_lookups = ARRAY_SIZE(tegra124_fuse_lookups), 210 .soc_attr_group = &tegra_soc_attr_group, 211}; 212#endif 213 214#if defined(CONFIG_ARCH_TEGRA_210_SOC) 215static const struct nvmem_cell_lookup tegra210_fuse_lookups[] = { 216 { 217 .nvmem_name = "fuse", 218 .cell_name = "tsensor-cpu1", 219 .dev_id = "700e2000.thermal-sensor", 220 .con_id = "cpu1", 221 }, { 222 .nvmem_name = "fuse", 223 .cell_name = "tsensor-cpu2", 224 .dev_id = "700e2000.thermal-sensor", 225 .con_id = "cpu2", 226 }, { 227 .nvmem_name = "fuse", 228 .cell_name = "tsensor-cpu0", 229 .dev_id = "700e2000.thermal-sensor", 230 .con_id = "cpu0", 231 }, { 232 .nvmem_name = "fuse", 233 .cell_name = "xusb-pad-calibration", 234 .dev_id = "7009f000.padctl", 235 .con_id = "calibration", 236 }, { 237 .nvmem_name = "fuse", 238 .cell_name = "tsensor-cpu3", 239 .dev_id = "700e2000.thermal-sensor", 240 .con_id = "cpu3", 241 }, { 242 .nvmem_name = "fuse", 243 .cell_name = "sata-calibration", 244 .dev_id = "70020000.sata", 245 .con_id = "calibration", 246 }, { 247 .nvmem_name = "fuse", 248 .cell_name = "tsensor-gpu", 249 .dev_id = "700e2000.thermal-sensor", 250 .con_id = "gpu", 251 }, { 252 .nvmem_name = "fuse", 253 .cell_name = "tsensor-mem0", 254 .dev_id = "700e2000.thermal-sensor", 255 .con_id = "mem0", 256 }, { 257 .nvmem_name = "fuse", 258 .cell_name = "tsensor-mem1", 259 .dev_id = "700e2000.thermal-sensor", 260 .con_id = "mem1", 261 }, { 262 .nvmem_name = "fuse", 263 .cell_name = "tsensor-pllx", 264 .dev_id = "700e2000.thermal-sensor", 265 .con_id = "pllx", 266 }, { 267 .nvmem_name = "fuse", 268 .cell_name = "tsensor-common", 269 .dev_id = "700e2000.thermal-sensor", 270 .con_id = "common", 271 }, { 272 .nvmem_name = "fuse", 273 .cell_name = "gpu-calibration", 274 .dev_id = "57000000.gpu", 275 .con_id = "calibration", 276 }, { 277 .nvmem_name = "fuse", 278 .cell_name = "xusb-pad-calibration-ext", 279 .dev_id = "7009f000.padctl", 280 .con_id = "calibration-ext", 281 }, 282}; 283 284static const struct tegra_fuse_info tegra210_fuse_info = { 285 .read = tegra30_fuse_read, 286 .size = 0x300, 287 .spare = 0x280, 288}; 289 290const struct tegra_fuse_soc tegra210_fuse_soc = { 291 .init = tegra30_fuse_init, 292 .speedo_init = tegra210_init_speedo_data, 293 .info = &tegra210_fuse_info, 294 .lookups = tegra210_fuse_lookups, 295 .num_lookups = ARRAY_SIZE(tegra210_fuse_lookups), 296 .soc_attr_group = &tegra_soc_attr_group, 297}; 298#endif 299 300#if defined(CONFIG_ARCH_TEGRA_186_SOC) 301static const struct nvmem_cell_lookup tegra186_fuse_lookups[] = { 302 { 303 .nvmem_name = "fuse", 304 .cell_name = "xusb-pad-calibration", 305 .dev_id = "3520000.padctl", 306 .con_id = "calibration", 307 }, { 308 .nvmem_name = "fuse", 309 .cell_name = "xusb-pad-calibration-ext", 310 .dev_id = "3520000.padctl", 311 .con_id = "calibration-ext", 312 }, 313}; 314 315static const struct tegra_fuse_info tegra186_fuse_info = { 316 .read = tegra30_fuse_read, 317 .size = 0x300, 318 .spare = 0x280, 319}; 320 321const struct tegra_fuse_soc tegra186_fuse_soc = { 322 .init = tegra30_fuse_init, 323 .info = &tegra186_fuse_info, 324 .lookups = tegra186_fuse_lookups, 325 .num_lookups = ARRAY_SIZE(tegra186_fuse_lookups), 326 .soc_attr_group = &tegra_soc_attr_group, 327}; 328#endif 329 330#if defined(CONFIG_ARCH_TEGRA_194_SOC) 331static const struct nvmem_cell_lookup tegra194_fuse_lookups[] = { 332 { 333 .nvmem_name = "fuse", 334 .cell_name = "xusb-pad-calibration", 335 .dev_id = "3520000.padctl", 336 .con_id = "calibration", 337 }, { 338 .nvmem_name = "fuse", 339 .cell_name = "xusb-pad-calibration-ext", 340 .dev_id = "3520000.padctl", 341 .con_id = "calibration-ext", 342 }, 343}; 344 345static const struct tegra_fuse_info tegra194_fuse_info = { 346 .read = tegra30_fuse_read, 347 .size = 0x300, 348 .spare = 0x280, 349}; 350 351const struct tegra_fuse_soc tegra194_fuse_soc = { 352 .init = tegra30_fuse_init, 353 .info = &tegra194_fuse_info, 354 .lookups = tegra194_fuse_lookups, 355 .num_lookups = ARRAY_SIZE(tegra194_fuse_lookups), 356 .soc_attr_group = &tegra194_soc_attr_group, 357}; 358#endif