blob: 27435476668e68ceb6ce7e9af3a782fe2994d94d [file] [log] [blame]
Taniya Dasa04e1892011-11-16 14:49:12 +05301/* Copyright (c) 2009-2012, Code Aurora Forum. All rights reserved.
Bryan Huntsman3f2bc4d2011-08-16 17:27:22 -07002 *
3 * This program is free software; you can redistribute it and/or modify
4 * it under the terms of the GNU General Public License version 2 and
5 * only version 2 as published by the Free Software Foundation.
6 *
7 * This program is distributed in the hope that it will be useful,
8 * but WITHOUT ANY WARRANTY; without even the implied warranty of
9 * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the
10 * GNU General Public License for more details.
11 *
12 */
13/*
14 * SOC Info Routines
15 *
16 */
17
18#include <linux/types.h>
19#include <linux/sysdev.h>
20#include <asm/mach-types.h>
21#include <mach/socinfo.h>
22
23#include "smd_private.h"
24
25#define BUILD_ID_LENGTH 32
26
27enum {
28 HW_PLATFORM_UNKNOWN = 0,
29 HW_PLATFORM_SURF = 1,
30 HW_PLATFORM_FFA = 2,
31 HW_PLATFORM_FLUID = 3,
32 HW_PLATFORM_SVLTE_FFA = 4,
33 HW_PLATFORM_SVLTE_SURF = 5,
Jin Hong49753322011-12-15 16:55:37 -080034 HW_PLATFORM_MTP = 8,
Amir Samuelov1b0dc312011-11-17 20:43:33 +020035 HW_PLATFORM_LIQUID = 9,
Zhang Chang Ken59004eb2011-08-08 09:06:58 -040036 /* Dragonboard platform id is assigned as 10 in CDT */
37 HW_PLATFORM_DRAGON = 10,
ChandraMouli Bothsaeae28bb2012-09-20 09:57:37 +053038 HW_PLATFORM_HRD = 13,
39 HW_PLATFORM_DTV = 14,
Bryan Huntsman3f2bc4d2011-08-16 17:27:22 -070040 HW_PLATFORM_INVALID
41};
42
43const char *hw_platform[] = {
44 [HW_PLATFORM_UNKNOWN] = "Unknown",
45 [HW_PLATFORM_SURF] = "Surf",
46 [HW_PLATFORM_FFA] = "FFA",
47 [HW_PLATFORM_FLUID] = "Fluid",
48 [HW_PLATFORM_SVLTE_FFA] = "SVLTE_FFA",
Zhang Chang Kenef05b172011-07-27 15:28:13 -040049 [HW_PLATFORM_SVLTE_SURF] = "SLVTE_SURF",
Jin Hong49753322011-12-15 16:55:37 -080050 [HW_PLATFORM_MTP] = "MTP",
51 [HW_PLATFORM_LIQUID] = "Liquid",
ChandraMouli Bothsaeae28bb2012-09-20 09:57:37 +053052 [HW_PLATFORM_DRAGON] = "Dragon",
53 [HW_PLATFORM_HRD] = "HRD",
54 [HW_PLATFORM_DTV] = "DTV",
Bryan Huntsman3f2bc4d2011-08-16 17:27:22 -070055};
56
57enum {
58 ACCESSORY_CHIP_UNKNOWN = 0,
59 ACCESSORY_CHIP_CHARM = 58,
60};
61
62enum {
63 PLATFORM_SUBTYPE_UNKNOWN = 0x0,
64 PLATFORM_SUBTYPE_CHARM = 0x1,
65 PLATFORM_SUBTYPE_STRANGE = 0x2,
66 PLATFORM_SUBTYPE_STRANGE_2A = 0x3,
67 PLATFORM_SUBTYPE_INVALID,
68};
69
70const char *hw_platform_subtype[] = {
71 [PLATFORM_SUBTYPE_UNKNOWN] = "Unknown",
72 [PLATFORM_SUBTYPE_CHARM] = "charm",
73 [PLATFORM_SUBTYPE_STRANGE] = "strange",
74 [PLATFORM_SUBTYPE_STRANGE_2A] = "strange_2a,"
75};
76
77/* Used to parse shared memory. Must match the modem. */
78struct socinfo_v1 {
79 uint32_t format;
80 uint32_t id;
81 uint32_t version;
82 char build_id[BUILD_ID_LENGTH];
83};
84
85struct socinfo_v2 {
86 struct socinfo_v1 v1;
87
88 /* only valid when format==2 */
89 uint32_t raw_id;
90 uint32_t raw_version;
91};
92
93struct socinfo_v3 {
94 struct socinfo_v2 v2;
95
96 /* only valid when format==3 */
97 uint32_t hw_platform;
98};
99
100struct socinfo_v4 {
101 struct socinfo_v3 v3;
102
103 /* only valid when format==4 */
104 uint32_t platform_version;
105};
106
107struct socinfo_v5 {
108 struct socinfo_v4 v4;
109
110 /* only valid when format==5 */
111 uint32_t accessory_chip;
112};
113
114struct socinfo_v6 {
115 struct socinfo_v5 v5;
116
117 /* only valid when format==6 */
118 uint32_t hw_platform_subtype;
119};
120
Jin Hong9b556c32012-08-13 23:06:26 -0700121struct socinfo_v7 {
122 struct socinfo_v6 v6;
123
124 /* only valid when format==7 */
125 uint32_t pmic_model;
126 uint32_t pmic_die_revision;
127};
128
Bryan Huntsman3f2bc4d2011-08-16 17:27:22 -0700129static union {
130 struct socinfo_v1 v1;
131 struct socinfo_v2 v2;
132 struct socinfo_v3 v3;
133 struct socinfo_v4 v4;
134 struct socinfo_v5 v5;
135 struct socinfo_v6 v6;
Jin Hong9b556c32012-08-13 23:06:26 -0700136 struct socinfo_v7 v7;
Bryan Huntsman3f2bc4d2011-08-16 17:27:22 -0700137} *socinfo;
138
139static enum msm_cpu cpu_of_id[] = {
140
141 /* 7x01 IDs */
142 [1] = MSM_CPU_7X01,
143 [16] = MSM_CPU_7X01,
144 [17] = MSM_CPU_7X01,
145 [18] = MSM_CPU_7X01,
146 [19] = MSM_CPU_7X01,
147 [23] = MSM_CPU_7X01,
148 [25] = MSM_CPU_7X01,
149 [26] = MSM_CPU_7X01,
150 [32] = MSM_CPU_7X01,
151 [33] = MSM_CPU_7X01,
152 [34] = MSM_CPU_7X01,
153 [35] = MSM_CPU_7X01,
154
155 /* 7x25 IDs */
156 [20] = MSM_CPU_7X25,
157 [21] = MSM_CPU_7X25, /* 7225 */
158 [24] = MSM_CPU_7X25, /* 7525 */
159 [27] = MSM_CPU_7X25, /* 7625 */
160 [39] = MSM_CPU_7X25,
161 [40] = MSM_CPU_7X25,
162 [41] = MSM_CPU_7X25,
163 [42] = MSM_CPU_7X25,
164 [62] = MSM_CPU_7X25, /* 7625-1 */
165 [63] = MSM_CPU_7X25, /* 7225-1 */
166 [66] = MSM_CPU_7X25, /* 7225-2 */
167
168
169 /* 7x27 IDs */
170 [43] = MSM_CPU_7X27,
171 [44] = MSM_CPU_7X27,
172 [61] = MSM_CPU_7X27,
173 [67] = MSM_CPU_7X27, /* 7227-1 */
174 [68] = MSM_CPU_7X27, /* 7627-1 */
175 [69] = MSM_CPU_7X27, /* 7627-2 */
176
177
178 /* 8x50 IDs */
179 [30] = MSM_CPU_8X50,
180 [36] = MSM_CPU_8X50,
181 [37] = MSM_CPU_8X50,
182 [38] = MSM_CPU_8X50,
183
184 /* 7x30 IDs */
185 [59] = MSM_CPU_7X30,
186 [60] = MSM_CPU_7X30,
187
188 /* 8x55 IDs */
189 [74] = MSM_CPU_8X55,
190 [75] = MSM_CPU_8X55,
191 [85] = MSM_CPU_8X55,
192
193 /* 8x60 IDs */
194 [70] = MSM_CPU_8X60,
195 [71] = MSM_CPU_8X60,
196 [86] = MSM_CPU_8X60,
197
198 /* 8960 IDs */
199 [87] = MSM_CPU_8960,
200
201 /* 7x25A IDs */
202 [88] = MSM_CPU_7X25A,
203 [89] = MSM_CPU_7X25A,
204 [96] = MSM_CPU_7X25A,
205
206 /* 7x27A IDs */
207 [90] = MSM_CPU_7X27A,
208 [91] = MSM_CPU_7X27A,
209 [92] = MSM_CPU_7X27A,
210 [97] = MSM_CPU_7X27A,
211
212 /* FSM9xxx ID */
213 [94] = FSM_CPU_9XXX,
214 [95] = FSM_CPU_9XXX,
215
216 /* 7x25AA ID */
217 [98] = MSM_CPU_7X25AA,
218 [99] = MSM_CPU_7X25AA,
219 [100] = MSM_CPU_7X25AA,
220
Joel Kingbf2ff512011-07-22 13:43:11 -0700221 /* 7x27AA ID */
222 [101] = MSM_CPU_7X27AA,
223 [102] = MSM_CPU_7X27AA,
224 [103] = MSM_CPU_7X27AA,
Kaushal Kumardc0beb92012-06-29 19:31:05 +0530225 [136] = MSM_CPU_7X27AA,
Joel Kingbf2ff512011-07-22 13:43:11 -0700226
Rohit Vaswani8a28b4a2011-08-10 19:07:00 -0700227 /* 9x15 ID */
228 [104] = MSM_CPU_9615,
Rohit Vaswani865f2ca2011-10-03 17:40:42 -0700229 [105] = MSM_CPU_9615,
Rohit Vaswani7a83fa92012-01-11 15:05:39 -0800230 [106] = MSM_CPU_9615,
231 [107] = MSM_CPU_9615,
Rohit Vaswani8a28b4a2011-08-10 19:07:00 -0700232
Stepan Moskovchenkoa8f0a222011-10-24 18:53:17 -0700233 /* 8064 IDs */
Joel Kingbf2ff512011-07-22 13:43:11 -0700234 [109] = MSM_CPU_8064,
235
Stepan Moskovchenkoa8f0a222011-10-24 18:53:17 -0700236 /* 8930 IDs */
237 [116] = MSM_CPU_8930,
Stepan Moskovchenkodb71cd62011-11-23 14:28:57 -0800238 [117] = MSM_CPU_8930,
239 [118] = MSM_CPU_8930,
240 [119] = MSM_CPU_8930,
241
242 /* 8627 IDs */
243 [120] = MSM_CPU_8627,
244 [121] = MSM_CPU_8627,
Stepan Moskovchenkoa8f0a222011-10-24 18:53:17 -0700245
Jin Hong0698b562011-11-05 13:57:25 -0700246 /* 8660A ID */
247 [122] = MSM_CPU_8960,
248
249 /* 8260A ID */
250 [123] = MSM_CPU_8960,
251
252 /* 8060A ID */
253 [124] = MSM_CPU_8960,
254
Abhimanyu Kapur90ced6e2012-06-26 17:41:25 -0700255 /* 8974 IDs */
256 [126] = MSM_CPU_8974,
Sathish Ambleya99d6852011-10-31 15:50:55 -0700257
Taniya Dasa04e1892011-11-16 14:49:12 +0530258 /* 8625 IDs */
259 [127] = MSM_CPU_8625,
260 [128] = MSM_CPU_8625,
261 [129] = MSM_CPU_8625,
Kaushal Kumar1f8876a2012-08-21 14:53:50 +0530262 [137] = MSM_CPU_8625,
Kaushal Kumarc84b9c22012-10-12 12:47:55 +0530263 [167] = MSM_CPU_8625,
Taniya Dasa04e1892011-11-16 14:49:12 +0530264
Joel King8e0bf672012-05-18 15:40:40 -0700265 /* 8064 MPQ ID */
266 [130] = MSM_CPU_8064,
Rohit Vaswani47ee9e92012-04-23 18:42:03 -0700267
Pankaj Kumarfee56a82012-04-17 14:26:49 +0530268 /* 7x25AB IDs */
269 [131] = MSM_CPU_7X25AB,
270 [132] = MSM_CPU_7X25AB,
271 [133] = MSM_CPU_7X25AB,
Kaushal Kumardc0beb92012-06-29 19:31:05 +0530272 [135] = MSM_CPU_7X25AB,
Pankaj Kumarfee56a82012-04-17 14:26:49 +0530273
Joel King8e0bf672012-05-18 15:40:40 -0700274 /* 9625 IDs */
275 [134] = MSM_CPU_9625,
Abhimanyu Kapur0f1df242012-10-23 15:28:16 -0700276 [152] = MSM_CPU_9625,
Joel King8e0bf672012-05-18 15:40:40 -0700277
Stepan Moskovchenkoec6a8032012-07-06 15:42:01 -0700278 /* 8960AB IDs */
279 [138] = MSM_CPU_8960AB,
280 [139] = MSM_CPU_8960AB,
281 [140] = MSM_CPU_8960AB,
282 [141] = MSM_CPU_8960AB,
283
Stepan Moskovchenko8f362fe2012-07-12 19:19:52 -0700284 /* 8930AA IDs */
Stepan Moskovchenko8b38bb32012-07-06 16:57:34 -0700285 [142] = MSM_CPU_8930AA,
Stepan Moskovchenko8f362fe2012-07-12 19:19:52 -0700286 [143] = MSM_CPU_8930AA,
287 [144] = MSM_CPU_8930AA,
Stepan Moskovchenko9e83cb92012-10-22 18:52:06 -0700288 [160] = MSM_CPU_8930AA,
Stepan Moskovchenko8b38bb32012-07-06 16:57:34 -0700289
Syed Rameez Mustafad6084d32012-08-23 15:47:50 -0700290 /* 8226 IDs */
291 [145] = MSM_CPU_8226,
292
Ravi Kumar V754282d2012-08-31 22:32:20 +0530293 /* 8092 IDs */
294 [146] = MSM_CPU_8092,
295
Syed Rameez Mustafa158d6682012-09-21 18:25:50 -0700296 /* 8910 IDs */
297 [147] = MSM_CPU_8910,
298
Jay Chokshib2de5092012-09-19 18:28:12 -0700299 /* 8064AB IDs */
300 [153] = MSM_CPU_8064AB,
301
Stepan Moskovchenkoa03e7612012-10-16 18:34:17 -0700302 /* 8930AB IDs */
303 [154] = MSM_CPU_8930AB,
304 [155] = MSM_CPU_8930AB,
305 [156] = MSM_CPU_8930AB,
Utsab Bose89b32992012-11-08 11:15:45 +0530306 [157] = MSM_CPU_8930AB,
307
308 /* 8625Q IDs */
309 [168] = MSM_CPU_8625Q,
310 [169] = MSM_CPU_8625Q,
311 [170] = MSM_CPU_8625Q,
312
Stepan Moskovchenkoa03e7612012-10-16 18:34:17 -0700313
Bryan Huntsman3f2bc4d2011-08-16 17:27:22 -0700314 /* Uninitialized IDs are not known to run Linux.
315 MSM_CPU_UNKNOWN is set to 0 to ensure these IDs are
316 considered as unknown CPU. */
317};
318
319static enum msm_cpu cur_cpu;
320
321static struct socinfo_v1 dummy_socinfo = {
322 .format = 1,
323 .version = 1,
Bryan Huntsman3f2bc4d2011-08-16 17:27:22 -0700324};
325
326uint32_t socinfo_get_id(void)
327{
328 return (socinfo) ? socinfo->v1.id : 0;
329}
330EXPORT_SYMBOL_GPL(socinfo_get_id);
331
332uint32_t socinfo_get_version(void)
333{
334 return (socinfo) ? socinfo->v1.version : 0;
335}
336
337char *socinfo_get_build_id(void)
338{
339 return (socinfo) ? socinfo->v1.build_id : NULL;
340}
341
342uint32_t socinfo_get_raw_id(void)
343{
344 return socinfo ?
345 (socinfo->v1.format >= 2 ? socinfo->v2.raw_id : 0)
346 : 0;
347}
348
349uint32_t socinfo_get_raw_version(void)
350{
351 return socinfo ?
352 (socinfo->v1.format >= 2 ? socinfo->v2.raw_version : 0)
353 : 0;
354}
355
356uint32_t socinfo_get_platform_type(void)
357{
358 return socinfo ?
359 (socinfo->v1.format >= 3 ? socinfo->v3.hw_platform : 0)
360 : 0;
361}
362
363
364uint32_t socinfo_get_platform_version(void)
365{
366 return socinfo ?
367 (socinfo->v1.format >= 4 ? socinfo->v4.platform_version : 0)
368 : 0;
369}
370
371/* This information is directly encoded by the machine id */
372/* Thus no external callers rely on this information at the moment */
373static uint32_t socinfo_get_accessory_chip(void)
374{
375 return socinfo ?
376 (socinfo->v1.format >= 5 ? socinfo->v5.accessory_chip : 0)
377 : 0;
378}
379
380uint32_t socinfo_get_platform_subtype(void)
381{
382 return socinfo ?
383 (socinfo->v1.format >= 6 ? socinfo->v6.hw_platform_subtype : 0)
384 : 0;
385}
386
Jin Hong9b556c32012-08-13 23:06:26 -0700387enum pmic_model socinfo_get_pmic_model(void)
388{
389 return socinfo ?
390 (socinfo->v1.format >= 7 ? socinfo->v7.pmic_model
391 : PMIC_MODEL_UNKNOWN)
392 : PMIC_MODEL_UNKNOWN;
393}
394
395uint32_t socinfo_get_pmic_die_revision(void)
396{
397 return socinfo ?
398 (socinfo->v1.format >= 7 ? socinfo->v7.pmic_die_revision : 0)
399 : 0;
400}
401
Bryan Huntsman3f2bc4d2011-08-16 17:27:22 -0700402enum msm_cpu socinfo_get_msm_cpu(void)
403{
404 return cur_cpu;
405}
406EXPORT_SYMBOL_GPL(socinfo_get_msm_cpu);
407
408static ssize_t
409socinfo_show_id(struct sys_device *dev,
410 struct sysdev_attribute *attr,
411 char *buf)
412{
413 if (!socinfo) {
414 pr_err("%s: No socinfo found!\n", __func__);
415 return 0;
416 }
417
418 return snprintf(buf, PAGE_SIZE, "%u\n", socinfo_get_id());
419}
420
421static ssize_t
422socinfo_show_version(struct sys_device *dev,
423 struct sysdev_attribute *attr,
424 char *buf)
425{
426 uint32_t version;
427
428 if (!socinfo) {
429 pr_err("%s: No socinfo found!\n", __func__);
430 return 0;
431 }
432
433 version = socinfo_get_version();
434 return snprintf(buf, PAGE_SIZE, "%u.%u\n",
435 SOCINFO_VERSION_MAJOR(version),
436 SOCINFO_VERSION_MINOR(version));
437}
438
439static ssize_t
440socinfo_show_build_id(struct sys_device *dev,
441 struct sysdev_attribute *attr,
442 char *buf)
443{
444 if (!socinfo) {
445 pr_err("%s: No socinfo found!\n", __func__);
446 return 0;
447 }
448
449 return snprintf(buf, PAGE_SIZE, "%-.32s\n", socinfo_get_build_id());
450}
451
452static ssize_t
453socinfo_show_raw_id(struct sys_device *dev,
454 struct sysdev_attribute *attr,
455 char *buf)
456{
457 if (!socinfo) {
458 pr_err("%s: No socinfo found!\n", __func__);
459 return 0;
460 }
461 if (socinfo->v1.format < 2) {
462 pr_err("%s: Raw ID not available!\n", __func__);
463 return 0;
464 }
465
466 return snprintf(buf, PAGE_SIZE, "%u\n", socinfo_get_raw_id());
467}
468
469static ssize_t
470socinfo_show_raw_version(struct sys_device *dev,
471 struct sysdev_attribute *attr,
472 char *buf)
473{
474 if (!socinfo) {
475 pr_err("%s: No socinfo found!\n", __func__);
476 return 0;
477 }
478 if (socinfo->v1.format < 2) {
479 pr_err("%s: Raw version not available!\n", __func__);
480 return 0;
481 }
482
483 return snprintf(buf, PAGE_SIZE, "%u\n", socinfo_get_raw_version());
484}
485
486static ssize_t
487socinfo_show_platform_type(struct sys_device *dev,
488 struct sysdev_attribute *attr,
489 char *buf)
490{
491 uint32_t hw_type;
492
493 if (!socinfo) {
494 pr_err("%s: No socinfo found!\n", __func__);
495 return 0;
496 }
497 if (socinfo->v1.format < 3) {
498 pr_err("%s: platform type not available!\n", __func__);
499 return 0;
500 }
501
502 hw_type = socinfo_get_platform_type();
503 if (hw_type >= HW_PLATFORM_INVALID) {
504 pr_err("%s: Invalid hardware platform type found\n",
505 __func__);
506 hw_type = HW_PLATFORM_UNKNOWN;
507 }
508
509 return snprintf(buf, PAGE_SIZE, "%-.32s\n", hw_platform[hw_type]);
510}
511
512static ssize_t
513socinfo_show_platform_version(struct sys_device *dev,
514 struct sysdev_attribute *attr,
515 char *buf)
516{
517
518 if (!socinfo) {
519 pr_err("%s: No socinfo found!\n", __func__);
520 return 0;
521 }
522 if (socinfo->v1.format < 4) {
523 pr_err("%s: platform version not available!\n", __func__);
524 return 0;
525 }
526
527 return snprintf(buf, PAGE_SIZE, "%u\n",
528 socinfo_get_platform_version());
529}
530
531static ssize_t
532socinfo_show_accessory_chip(struct sys_device *dev,
533 struct sysdev_attribute *attr,
534 char *buf)
535{
536 if (!socinfo) {
537 pr_err("%s: No socinfo found!\n", __func__);
538 return 0;
539 }
540 if (socinfo->v1.format < 5) {
541 pr_err("%s: accessory chip not available!\n", __func__);
542 return 0;
543 }
544
545 return snprintf(buf, PAGE_SIZE, "%u\n",
546 socinfo_get_accessory_chip());
547}
548
549static ssize_t
550socinfo_show_platform_subtype(struct sys_device *dev,
551 struct sysdev_attribute *attr,
552 char *buf)
553{
554 uint32_t hw_subtype;
555 if (!socinfo) {
556 pr_err("%s: No socinfo found!\n", __func__);
557 return 0;
558 }
559 if (socinfo->v1.format < 6) {
560 pr_err("%s: platform subtype not available!\n", __func__);
561 return 0;
562 }
563
564 hw_subtype = socinfo_get_platform_subtype();
565 if (hw_subtype >= PLATFORM_SUBTYPE_INVALID) {
566 pr_err("%s: Invalid hardware platform sub type found\n",
567 __func__);
568 hw_subtype = PLATFORM_SUBTYPE_UNKNOWN;
569 }
570 return snprintf(buf, PAGE_SIZE, "%-.32s\n",
571 hw_platform_subtype[hw_subtype]);
572}
573
Jin Hong9b556c32012-08-13 23:06:26 -0700574static ssize_t
575socinfo_show_pmic_model(struct sys_device *dev,
576 struct sysdev_attribute *attr,
577 char *buf)
578{
579 if (!socinfo) {
580 pr_err("%s: No socinfo found!\n", __func__);
581 return 0;
582 }
583 if (socinfo->v1.format < 7) {
584 pr_err("%s: pmic_model not available!\n", __func__);
585 return 0;
586 }
587
588 return snprintf(buf, PAGE_SIZE, "%u\n",
589 socinfo_get_pmic_model());
590}
591
592static ssize_t
593socinfo_show_pmic_die_revision(struct sys_device *dev,
594 struct sysdev_attribute *attr,
595 char *buf)
596{
597 if (!socinfo) {
598 pr_err("%s: No socinfo found!\n", __func__);
599 return 0;
600 }
601 if (socinfo->v1.format < 7) {
602 pr_err("%s: pmic_die_revision not available!\n", __func__);
603 return 0;
604 }
605
606 return snprintf(buf, PAGE_SIZE, "%u\n",
607 socinfo_get_pmic_die_revision());
608}
609
Bryan Huntsman3f2bc4d2011-08-16 17:27:22 -0700610static struct sysdev_attribute socinfo_v1_files[] = {
611 _SYSDEV_ATTR(id, 0444, socinfo_show_id, NULL),
612 _SYSDEV_ATTR(version, 0444, socinfo_show_version, NULL),
613 _SYSDEV_ATTR(build_id, 0444, socinfo_show_build_id, NULL),
614};
615
616static struct sysdev_attribute socinfo_v2_files[] = {
617 _SYSDEV_ATTR(raw_id, 0444, socinfo_show_raw_id, NULL),
618 _SYSDEV_ATTR(raw_version, 0444, socinfo_show_raw_version, NULL),
619};
620
621static struct sysdev_attribute socinfo_v3_files[] = {
622 _SYSDEV_ATTR(hw_platform, 0444, socinfo_show_platform_type, NULL),
623};
624
625static struct sysdev_attribute socinfo_v4_files[] = {
626 _SYSDEV_ATTR(platform_version, 0444,
627 socinfo_show_platform_version, NULL),
628};
629
630static struct sysdev_attribute socinfo_v5_files[] = {
631 _SYSDEV_ATTR(accessory_chip, 0444,
632 socinfo_show_accessory_chip, NULL),
633};
634
635static struct sysdev_attribute socinfo_v6_files[] = {
636 _SYSDEV_ATTR(platform_subtype, 0444,
637 socinfo_show_platform_subtype, NULL),
638};
639
Jin Hong9b556c32012-08-13 23:06:26 -0700640static struct sysdev_attribute socinfo_v7_files[] = {
641 _SYSDEV_ATTR(pmic_model, 0444,
642 socinfo_show_pmic_model, NULL),
643 _SYSDEV_ATTR(pmic_die_revision, 0444,
644 socinfo_show_pmic_die_revision, NULL),
645};
646
Bryan Huntsman3f2bc4d2011-08-16 17:27:22 -0700647static struct sysdev_class soc_sysdev_class = {
648 .name = "soc",
649};
650
651static struct sys_device soc_sys_device = {
652 .id = 0,
653 .cls = &soc_sysdev_class,
654};
655
656static int __init socinfo_create_files(struct sys_device *dev,
657 struct sysdev_attribute files[],
658 int size)
659{
660 int i;
661 for (i = 0; i < size; i++) {
662 int err = sysdev_create_file(dev, &files[i]);
663 if (err) {
664 pr_err("%s: sysdev_create_file(%s)=%d\n",
665 __func__, files[i].attr.name, err);
666 return err;
667 }
668 }
669 return 0;
670}
671
672static int __init socinfo_init_sysdev(void)
673{
674 int err;
675
676 if (!socinfo) {
677 pr_err("%s: No socinfo found!\n", __func__);
678 return -ENODEV;
679 }
680
681 err = sysdev_class_register(&soc_sysdev_class);
682 if (err) {
683 pr_err("%s: sysdev_class_register fail (%d)\n",
684 __func__, err);
685 return err;
686 }
687 err = sysdev_register(&soc_sys_device);
688 if (err) {
689 pr_err("%s: sysdev_register fail (%d)\n",
690 __func__, err);
691 return err;
692 }
693 socinfo_create_files(&soc_sys_device, socinfo_v1_files,
694 ARRAY_SIZE(socinfo_v1_files));
695 if (socinfo->v1.format < 2)
696 return err;
697 socinfo_create_files(&soc_sys_device, socinfo_v2_files,
698 ARRAY_SIZE(socinfo_v2_files));
699
700 if (socinfo->v1.format < 3)
701 return err;
702
703 socinfo_create_files(&soc_sys_device, socinfo_v3_files,
704 ARRAY_SIZE(socinfo_v3_files));
705
706 if (socinfo->v1.format < 4)
707 return err;
708
709 socinfo_create_files(&soc_sys_device, socinfo_v4_files,
710 ARRAY_SIZE(socinfo_v4_files));
711
712 if (socinfo->v1.format < 5)
713 return err;
714
715 socinfo_create_files(&soc_sys_device, socinfo_v5_files,
716 ARRAY_SIZE(socinfo_v5_files));
717
718 if (socinfo->v1.format < 6)
719 return err;
720
Jin Hong9b556c32012-08-13 23:06:26 -0700721 socinfo_create_files(&soc_sys_device, socinfo_v6_files,
Bryan Huntsman3f2bc4d2011-08-16 17:27:22 -0700722 ARRAY_SIZE(socinfo_v6_files));
723
Jin Hong9b556c32012-08-13 23:06:26 -0700724 if (socinfo->v1.format < 7)
725 return err;
726
727 return socinfo_create_files(&soc_sys_device, socinfo_v7_files,
728 ARRAY_SIZE(socinfo_v7_files));
Bryan Huntsman3f2bc4d2011-08-16 17:27:22 -0700729}
730
731arch_initcall(socinfo_init_sysdev);
732
Stephen Boyd69a22e42012-02-22 09:16:07 -0800733static void * __init setup_dummy_socinfo(void)
Bryan Huntsman3f2bc4d2011-08-16 17:27:22 -0700734{
Syed Rameez Mustafacf645e82012-07-06 19:00:49 -0700735 if (machine_is_msm8960_cdp())
Bryan Huntsman3f2bc4d2011-08-16 17:27:22 -0700736 dummy_socinfo.id = 87;
Rohit Vaswani8a28b4a2011-08-10 19:07:00 -0700737 else if (machine_is_msm9615_mtp() || machine_is_msm9615_cdp())
738 dummy_socinfo.id = 104;
Abhimanyu Kapur90ced6e2012-06-26 17:41:25 -0700739 else if (early_machine_is_msm8974()) {
Sathish Ambleya99d6852011-10-31 15:50:55 -0700740 dummy_socinfo.id = 126;
Abhimanyu Kapur90ced6e2012-06-26 17:41:25 -0700741 strlcpy(dummy_socinfo.build_id, "msm8974 - ",
Sathish Ambley3e265ce2012-03-08 16:44:04 -0800742 sizeof(dummy_socinfo.build_id));
Rohit Vaswani47ee9e92012-04-23 18:42:03 -0700743 } else if (early_machine_is_msm9625()) {
Joel King8e0bf672012-05-18 15:40:40 -0700744 dummy_socinfo.id = 134;
Rohit Vaswani47ee9e92012-04-23 18:42:03 -0700745 strlcpy(dummy_socinfo.build_id, "msm9625 - ",
746 sizeof(dummy_socinfo.build_id));
Syed Rameez Mustafad6084d32012-08-23 15:47:50 -0700747 } else if (early_machine_is_msm8226()) {
748 dummy_socinfo.id = 145;
749 strlcpy(dummy_socinfo.build_id, "msm8226 - ",
750 sizeof(dummy_socinfo.build_id));
Sathish Ambley3e265ce2012-03-08 16:44:04 -0800751 } else if (machine_is_msm8625_rumi3())
Taniya Dasa04e1892011-11-16 14:49:12 +0530752 dummy_socinfo.id = 127;
Ravi Kumar V754282d2012-08-31 22:32:20 +0530753 else if (early_machine_is_mpq8092()) {
754 dummy_socinfo.id = 146;
755 strlcpy(dummy_socinfo.build_id, "mpq8092 - ",
756 sizeof(dummy_socinfo.build_id));
Syed Rameez Mustafa158d6682012-09-21 18:25:50 -0700757 } else if (early_machine_is_msm8910()) {
758 dummy_socinfo.id = 147;
759 strlcpy(dummy_socinfo.build_id, "msm8910 - ",
760 sizeof(dummy_socinfo.build_id));
Ravi Kumar V754282d2012-08-31 22:32:20 +0530761 }
Sathish Ambley3e265ce2012-03-08 16:44:04 -0800762 strlcat(dummy_socinfo.build_id, "Dummy socinfo",
763 sizeof(dummy_socinfo.build_id));
Bryan Huntsman3f2bc4d2011-08-16 17:27:22 -0700764 return (void *) &dummy_socinfo;
765}
766
767int __init socinfo_init(void)
768{
Jin Hong9b556c32012-08-13 23:06:26 -0700769 socinfo = smem_alloc(SMEM_HW_SW_BUILD_ID, sizeof(struct socinfo_v7));
770
771 if (!socinfo)
772 socinfo = smem_alloc(SMEM_HW_SW_BUILD_ID,
773 sizeof(struct socinfo_v6));
Bryan Huntsman3f2bc4d2011-08-16 17:27:22 -0700774
775 if (!socinfo)
776 socinfo = smem_alloc(SMEM_HW_SW_BUILD_ID,
777 sizeof(struct socinfo_v5));
778
779 if (!socinfo)
780 socinfo = smem_alloc(SMEM_HW_SW_BUILD_ID,
781 sizeof(struct socinfo_v4));
782
783 if (!socinfo)
784 socinfo = smem_alloc(SMEM_HW_SW_BUILD_ID,
785 sizeof(struct socinfo_v3));
786
787 if (!socinfo)
788 socinfo = smem_alloc(SMEM_HW_SW_BUILD_ID,
789 sizeof(struct socinfo_v2));
790
791 if (!socinfo)
792 socinfo = smem_alloc(SMEM_HW_SW_BUILD_ID,
793 sizeof(struct socinfo_v1));
794
795 if (!socinfo) {
796 pr_warn("%s: Can't find SMEM_HW_SW_BUILD_ID; falling back on "
797 "dummy values.\n", __func__);
798 socinfo = setup_dummy_socinfo();
799 }
800
801 WARN(!socinfo_get_id(), "Unknown SOC ID!\n");
802 WARN(socinfo_get_id() >= ARRAY_SIZE(cpu_of_id),
803 "New IDs added! ID => CPU mapping might need an update.\n");
804
805 if (socinfo->v1.id < ARRAY_SIZE(cpu_of_id))
806 cur_cpu = cpu_of_id[socinfo->v1.id];
807
808 switch (socinfo->v1.format) {
809 case 1:
810 pr_info("%s: v%u, id=%u, ver=%u.%u\n",
811 __func__, socinfo->v1.format, socinfo->v1.id,
812 SOCINFO_VERSION_MAJOR(socinfo->v1.version),
813 SOCINFO_VERSION_MINOR(socinfo->v1.version));
814 break;
815 case 2:
816 pr_info("%s: v%u, id=%u, ver=%u.%u, "
817 "raw_id=%u, raw_ver=%u\n",
818 __func__, socinfo->v1.format, socinfo->v1.id,
819 SOCINFO_VERSION_MAJOR(socinfo->v1.version),
820 SOCINFO_VERSION_MINOR(socinfo->v1.version),
821 socinfo->v2.raw_id, socinfo->v2.raw_version);
822 break;
823 case 3:
824 pr_info("%s: v%u, id=%u, ver=%u.%u, "
825 "raw_id=%u, raw_ver=%u, hw_plat=%u\n",
826 __func__, socinfo->v1.format, socinfo->v1.id,
827 SOCINFO_VERSION_MAJOR(socinfo->v1.version),
828 SOCINFO_VERSION_MINOR(socinfo->v1.version),
829 socinfo->v2.raw_id, socinfo->v2.raw_version,
830 socinfo->v3.hw_platform);
831 break;
832 case 4:
833 pr_info("%s: v%u, id=%u, ver=%u.%u, "
834 "raw_id=%u, raw_ver=%u, hw_plat=%u, hw_plat_ver=%u\n",
835 __func__, socinfo->v1.format, socinfo->v1.id,
836 SOCINFO_VERSION_MAJOR(socinfo->v1.version),
837 SOCINFO_VERSION_MINOR(socinfo->v1.version),
838 socinfo->v2.raw_id, socinfo->v2.raw_version,
839 socinfo->v3.hw_platform, socinfo->v4.platform_version);
840 break;
841 case 5:
842 pr_info("%s: v%u, id=%u, ver=%u.%u, "
843 "raw_id=%u, raw_ver=%u, hw_plat=%u, hw_plat_ver=%u\n"
844 " accessory_chip=%u\n", __func__, socinfo->v1.format,
845 socinfo->v1.id,
846 SOCINFO_VERSION_MAJOR(socinfo->v1.version),
847 SOCINFO_VERSION_MINOR(socinfo->v1.version),
848 socinfo->v2.raw_id, socinfo->v2.raw_version,
849 socinfo->v3.hw_platform, socinfo->v4.platform_version,
850 socinfo->v5.accessory_chip);
851 break;
852 case 6:
853 pr_info("%s: v%u, id=%u, ver=%u.%u, "
854 "raw_id=%u, raw_ver=%u, hw_plat=%u, hw_plat_ver=%u\n"
855 " accessory_chip=%u hw_plat_subtype=%u\n", __func__,
856 socinfo->v1.format,
857 socinfo->v1.id,
858 SOCINFO_VERSION_MAJOR(socinfo->v1.version),
859 SOCINFO_VERSION_MINOR(socinfo->v1.version),
860 socinfo->v2.raw_id, socinfo->v2.raw_version,
861 socinfo->v3.hw_platform, socinfo->v4.platform_version,
862 socinfo->v5.accessory_chip,
863 socinfo->v6.hw_platform_subtype);
864 break;
Jin Hong9b556c32012-08-13 23:06:26 -0700865 case 7:
866 pr_info("%s: v%u, id=%u, ver=%u.%u, raw_id=%u, raw_ver=%u, hw_plat=%u, hw_plat_ver=%u\n accessory_chip=%u, hw_plat_subtype=%u, pmic_model=%u, pmic_die_revision=%u\n",
867 __func__,
868 socinfo->v1.format,
869 socinfo->v1.id,
870 SOCINFO_VERSION_MAJOR(socinfo->v1.version),
871 SOCINFO_VERSION_MINOR(socinfo->v1.version),
872 socinfo->v2.raw_id, socinfo->v2.raw_version,
873 socinfo->v3.hw_platform, socinfo->v4.platform_version,
874 socinfo->v5.accessory_chip,
875 socinfo->v6.hw_platform_subtype,
876 socinfo->v7.pmic_model,
877 socinfo->v7.pmic_die_revision);
878 break;
Bryan Huntsman3f2bc4d2011-08-16 17:27:22 -0700879 default:
880 pr_err("%s: Unknown format found\n", __func__);
881 break;
882 }
883
884 return 0;
885}
Stepan Moskovchenkoeff783a2011-08-22 19:01:58 -0700886
887const int get_core_count(void)
888{
889 if (!(read_cpuid_mpidr() & BIT(31)))
890 return 1;
891
Jin Hongc5f5d542012-04-12 16:48:51 -0700892 if (read_cpuid_mpidr() & BIT(30))
Stepan Moskovchenkoeff783a2011-08-22 19:01:58 -0700893 return 1;
894
895 /* 1 + the PART[1:0] field of MIDR */
896 return ((read_cpuid_id() >> 4) & 3) + 1;
897}
898
899const int read_msm_cpu_type(void)
900{
Stepan Moskovchenkoa8f0a222011-10-24 18:53:17 -0700901 if (socinfo_get_msm_cpu() != MSM_CPU_UNKNOWN)
902 return socinfo_get_msm_cpu();
903
Stepan Moskovchenkoeff783a2011-08-22 19:01:58 -0700904 switch (read_cpuid_id()) {
905 case 0x510F02D0:
906 case 0x510F02D2:
907 case 0x510F02D4:
908 return MSM_CPU_8X60;
909
910 case 0x510F04D0:
911 case 0x510F04D1:
912 case 0x510F04D2:
Stepan Moskovchenkoa8f0a222011-10-24 18:53:17 -0700913 case 0x511F04D0:
914 case 0x512F04D0:
Stepan Moskovchenkoeff783a2011-08-22 19:01:58 -0700915 return MSM_CPU_8960;
916
Stepan Moskovchenkoa8f0a222011-10-24 18:53:17 -0700917 case 0x51404D11: /* We can't get here unless we are in bringup */
918 return MSM_CPU_8930;
Stepan Moskovchenkoeff783a2011-08-22 19:01:58 -0700919
920 case 0x510F06F0:
921 return MSM_CPU_8064;
922
Stepan Moskovchenko02c4d0c2012-07-26 14:33:02 -0700923 case 0x511F06F1:
924 case 0x512F06F0:
925 return MSM_CPU_8974;
926
Stepan Moskovchenkoeff783a2011-08-22 19:01:58 -0700927 default:
928 return MSM_CPU_UNKNOWN;
929 };
930}
Stepan Moskovchenko70dc7cf2011-08-22 19:08:42 -0700931
Jin Hong12b8b432012-07-18 10:00:31 -0700932const int cpu_is_krait(void)
933{
934 return ((read_cpuid_id() & 0xFF00FC00) == 0x51000400);
935}
936
Stepan Moskovchenko70dc7cf2011-08-22 19:08:42 -0700937const int cpu_is_krait_v1(void)
938{
939 switch (read_cpuid_id()) {
940 case 0x510F04D0:
941 case 0x510F04D1:
942 case 0x510F04D2:
943 return 1;
944
945 default:
946 return 0;
947 };
948}
Jin Hong12b8b432012-07-18 10:00:31 -0700949
950const int cpu_is_krait_v2(void)
951{
952 switch (read_cpuid_id()) {
953 case 0x511F04D0:
954 case 0x511F04D1:
955 case 0x511F04D2:
956 case 0x511F04D3:
957 case 0x511F04D4:
958
959 case 0x510F06F0:
960 case 0x510F06F1:
961 case 0x510F06F2:
962 return 1;
963
964 default:
965 return 0;
966 };
967}
Joel King824bd1f2012-08-19 12:55:49 -0700968
969const int cpu_is_krait_v3(void)
970{
971 switch (read_cpuid_id()) {
972 case 0x512F04D0:
973 case 0x511F06F0:
974 case 0x511F06F1:
975 case 0x510F05D0:
976 return 1;
977
978 default:
979 return 0;
980 };
981}