1 /* SPDX-License-Identifier: BSD-3-Clause
2 * Copyright(c) 2010-2019 Intel Corporation
3 */
4
5 #include "opae_intel_max10.h"
6 #include <libfdt.h>
7
max10_reg_read(struct intel_max10_device * dev,unsigned int reg,unsigned int * val)8 int max10_reg_read(struct intel_max10_device *dev,
9 unsigned int reg, unsigned int *val)
10 {
11 if (!dev)
12 return -ENODEV;
13
14 dev_debug(dev, "%s: bus:0x%x, reg:0x%x\n", __func__, dev->bus, reg);
15
16 return spi_transaction_read(dev->spi_tran_dev,
17 reg, 4, (unsigned char *)val);
18 }
19
max10_reg_write(struct intel_max10_device * dev,unsigned int reg,unsigned int val)20 int max10_reg_write(struct intel_max10_device *dev,
21 unsigned int reg, unsigned int val)
22 {
23 unsigned int tmp = val;
24
25 if (!dev)
26 return -ENODEV;
27
28 dev_debug(dev, "%s: bus:0x%x, reg:0x%x, val:0x%x\n", __func__,
29 dev->bus, reg, val);
30
31 return spi_transaction_write(dev->spi_tran_dev,
32 reg, 4, (unsigned char *)&tmp);
33 }
34
max10_sys_read(struct intel_max10_device * dev,unsigned int offset,unsigned int * val)35 int max10_sys_read(struct intel_max10_device *dev,
36 unsigned int offset, unsigned int *val)
37 {
38 if (!dev)
39 return -ENODEV;
40
41
42 return max10_reg_read(dev, dev->base + offset, val);
43 }
44
max10_sys_write(struct intel_max10_device * dev,unsigned int offset,unsigned int val)45 int max10_sys_write(struct intel_max10_device *dev,
46 unsigned int offset, unsigned int val)
47 {
48 if (!dev)
49 return -ENODEV;
50
51 return max10_reg_write(dev, dev->base + offset, val);
52 }
53
max10_sys_update_bits(struct intel_max10_device * dev,unsigned int offset,unsigned int msk,unsigned int val)54 int max10_sys_update_bits(struct intel_max10_device *dev, unsigned int offset,
55 unsigned int msk, unsigned int val)
56 {
57 int ret = 0;
58 unsigned int temp = 0;
59
60 ret = max10_sys_read(dev, offset, &temp);
61 if (ret < 0)
62 return ret;
63
64 temp &= ~msk;
65 temp |= val & msk;
66
67 return max10_sys_write(dev, offset, temp);
68 }
69
70 static struct max10_compatible_id max10_id_table[] = {
71 {.compatible = MAX10_PAC,},
72 {.compatible = MAX10_PAC_N3000,},
73 {.compatible = MAX10_PAC_END,}
74 };
75
max10_match_compatible(const char * fdt_root)76 static struct max10_compatible_id *max10_match_compatible(const char *fdt_root)
77 {
78 struct max10_compatible_id *id = max10_id_table;
79
80 for (; strcmp(id->compatible, MAX10_PAC_END); id++) {
81 if (fdt_node_check_compatible(fdt_root, 0, id->compatible))
82 continue;
83
84 return id;
85 }
86
87 return NULL;
88 }
89
90 static inline bool
is_max10_pac_n3000(struct intel_max10_device * max10)91 is_max10_pac_n3000(struct intel_max10_device *max10)
92 {
93 return max10->id && !strcmp(max10->id->compatible,
94 MAX10_PAC_N3000);
95 }
96
max10_check_capability(struct intel_max10_device * max10)97 static void max10_check_capability(struct intel_max10_device *max10)
98 {
99 if (!max10->fdt_root)
100 return;
101
102 if (is_max10_pac_n3000(max10)) {
103 max10->flags |= MAX10_FLAGS_NO_I2C2 |
104 MAX10_FLAGS_NO_BMCIMG_FLASH;
105 dev_info(max10, "found %s card\n", max10->id->compatible);
106 } else
107 max10->flags |= MAX10_FLAGS_MAC_CACHE;
108 }
109
altera_nor_flash_read(struct intel_max10_device * dev,u32 offset,void * buffer,u32 len)110 static int altera_nor_flash_read(struct intel_max10_device *dev,
111 u32 offset, void *buffer, u32 len)
112 {
113 int word_len;
114 int i;
115 unsigned int *buf = (unsigned int *)buffer;
116 unsigned int value;
117 int ret;
118
119 if (!dev || !buffer || len <= 0)
120 return -ENODEV;
121
122 word_len = len/4;
123
124 for (i = 0; i < word_len; i++) {
125 ret = max10_reg_read(dev, offset + i*4,
126 &value);
127 if (ret)
128 return -EBUSY;
129
130 *buf++ = value;
131 }
132
133 return 0;
134 }
135
enable_nor_flash(struct intel_max10_device * dev,bool on)136 static int enable_nor_flash(struct intel_max10_device *dev, bool on)
137 {
138 unsigned int val = 0;
139 int ret;
140
141 ret = max10_sys_read(dev, RSU_REG, &val);
142 if (ret) {
143 dev_err(NULL "enabling flash error\n");
144 return ret;
145 }
146
147 if (on)
148 val |= RSU_ENABLE;
149 else
150 val &= ~RSU_ENABLE;
151
152 return max10_sys_write(dev, RSU_REG, val);
153 }
154
init_max10_device_table(struct intel_max10_device * max10)155 static int init_max10_device_table(struct intel_max10_device *max10)
156 {
157 struct altera_spi_device *spi = NULL;
158 struct max10_compatible_id *id;
159 struct fdt_header hdr;
160 char *fdt_root = NULL;
161 u32 dtb_magic = 0;
162 u32 dt_size, dt_addr, val;
163 int ret = 0;
164
165 spi = (struct altera_spi_device *)max10->spi_master;
166 if (!spi) {
167 dev_err(max10, "spi master is not set\n");
168 return -EINVAL;
169 }
170 if (spi->dtb)
171 dtb_magic = *(u32 *)spi->dtb;
172
173 if (dtb_magic != 0xEDFE0DD0) {
174 dev_info(max10, "read DTB from NOR flash\n");
175 ret = max10_sys_read(max10, DT_AVAIL_REG, &val);
176 if (ret) {
177 dev_err(max10 "cannot read DT_AVAIL_REG\n");
178 return ret;
179 }
180
181 if (!(val & DT_AVAIL)) {
182 dev_err(max10 "DT not available\n");
183 return -EINVAL;
184 }
185
186 ret = max10_sys_read(max10, DT_BASE_ADDR_REG, &dt_addr);
187 if (ret) {
188 dev_info(max10 "cannot get base addr of device table\n");
189 return ret;
190 }
191
192 ret = enable_nor_flash(max10, true);
193 if (ret) {
194 dev_err(max10 "fail to enable flash\n");
195 return ret;
196 }
197
198 ret = altera_nor_flash_read(max10, dt_addr, &hdr, sizeof(hdr));
199 if (ret) {
200 dev_err(max10 "read fdt header fail\n");
201 goto disable_nor_flash;
202 }
203
204 ret = fdt_check_header(&hdr);
205 if (ret) {
206 dev_err(max10 "check fdt header fail\n");
207 goto disable_nor_flash;
208 }
209
210 dt_size = fdt_totalsize(&hdr);
211 if (dt_size > DFT_MAX_SIZE) {
212 dev_err(max10 "invalid device table size\n");
213 ret = -EINVAL;
214 goto disable_nor_flash;
215 }
216
217 fdt_root = opae_malloc(dt_size);
218 if (!fdt_root) {
219 ret = -ENOMEM;
220 goto disable_nor_flash;
221 }
222
223 ret = altera_nor_flash_read(max10, dt_addr, fdt_root, dt_size);
224 if (ret) {
225 opae_free(fdt_root);
226 fdt_root = NULL;
227 dev_err(max10 "cannot read device table\n");
228 goto disable_nor_flash;
229 }
230
231 if (spi->dtb) {
232 if (*spi->dtb_sz_ptr < dt_size) {
233 dev_warn(max10,
234 "share memory for dtb is smaller than required %u\n",
235 dt_size);
236 } else {
237 *spi->dtb_sz_ptr = dt_size;
238 }
239 /* store dtb data into share memory */
240 memcpy(spi->dtb, fdt_root, *spi->dtb_sz_ptr);
241 }
242
243 disable_nor_flash:
244 enable_nor_flash(max10, false);
245 } else {
246 if (*spi->dtb_sz_ptr > 0) {
247 dev_info(max10, "read DTB from shared memory\n");
248 fdt_root = opae_malloc(*spi->dtb_sz_ptr);
249 if (fdt_root)
250 memcpy(fdt_root, spi->dtb, *spi->dtb_sz_ptr);
251 else
252 ret = -ENOMEM;
253 }
254 }
255
256 if (fdt_root) {
257 id = max10_match_compatible(fdt_root);
258 if (!id) {
259 dev_err(max10 "max10 compatible not found\n");
260 ret = -ENODEV;
261 } else {
262 max10->flags |= MAX10_FLAGS_DEVICE_TABLE;
263 max10->id = id;
264 max10->fdt_root = fdt_root;
265 }
266 }
267
268 return ret;
269 }
270
fdt_get_number(const fdt32_t * cell,int size)271 static u64 fdt_get_number(const fdt32_t *cell, int size)
272 {
273 u64 r = 0;
274
275 while (size--)
276 r = (r << 32) | fdt32_to_cpu(*cell++);
277
278 return r;
279 }
280
fdt_get_reg(const void * fdt,int node,unsigned int idx,u64 * start,u64 * size)281 static int fdt_get_reg(const void *fdt, int node, unsigned int idx,
282 u64 *start, u64 *size)
283 {
284 const fdt32_t *prop, *end;
285 int na = 0, ns = 0, len = 0, parent;
286
287 parent = fdt_parent_offset(fdt, node);
288 if (parent < 0)
289 return parent;
290
291 prop = fdt_getprop(fdt, parent, "#address-cells", NULL);
292 na = prop ? fdt32_to_cpu(*prop) : 2;
293
294 prop = fdt_getprop(fdt, parent, "#size-cells", NULL);
295 ns = prop ? fdt32_to_cpu(*prop) : 2;
296
297 prop = fdt_getprop(fdt, node, "reg", &len);
298 if (!prop)
299 return -FDT_ERR_NOTFOUND;
300
301 end = prop + len/sizeof(*prop);
302 prop = prop + (na + ns) * idx;
303
304 if (prop + na + ns > end)
305 return -FDT_ERR_NOTFOUND;
306
307 *start = fdt_get_number(prop, na);
308 *size = fdt_get_number(prop + na, ns);
309
310 return 0;
311 }
312
__fdt_stringlist_search(const void * fdt,int offset,const char * prop,const char * string)313 static int __fdt_stringlist_search(const void *fdt, int offset,
314 const char *prop, const char *string)
315 {
316 int length, len, index = 0;
317 const char *list, *end;
318
319 list = fdt_getprop(fdt, offset, prop, &length);
320 if (!list)
321 return length;
322
323 len = strlen(string) + 1;
324 end = list + length;
325
326 while (list < end) {
327 length = strnlen(list, end - list) + 1;
328
329 if (list + length > end)
330 return -FDT_ERR_BADVALUE;
331
332 if (length == len && memcmp(list, string, length) == 0)
333 return index;
334
335 list += length;
336 index++;
337 }
338
339 return -FDT_ERR_NOTFOUND;
340 }
341
fdt_get_named_reg(const void * fdt,int node,const char * name,u64 * start,u64 * size)342 static int fdt_get_named_reg(const void *fdt, int node, const char *name,
343 u64 *start, u64 *size)
344 {
345 int idx;
346
347 idx = __fdt_stringlist_search(fdt, node, "reg-names", name);
348 if (idx < 0)
349 return idx;
350
351 return fdt_get_reg(fdt, node, idx, start, size);
352 }
353
max10_sensor_uinit(struct intel_max10_device * dev)354 static void max10_sensor_uinit(struct intel_max10_device *dev)
355 {
356 struct opae_sensor_info *info;
357
358 TAILQ_FOREACH(info, &dev->opae_sensor_list, node) {
359 TAILQ_REMOVE(&dev->opae_sensor_list, info, node);
360 opae_free(info);
361 }
362 }
363
sensor_reg_valid(struct sensor_reg * reg)364 static bool sensor_reg_valid(struct sensor_reg *reg)
365 {
366 return !!reg->size;
367 }
368
max10_add_sensor(struct intel_max10_device * dev,struct raw_sensor_info * info,struct opae_sensor_info * sensor)369 static int max10_add_sensor(struct intel_max10_device *dev,
370 struct raw_sensor_info *info, struct opae_sensor_info *sensor)
371 {
372 int i;
373 int ret = 0;
374 unsigned int val;
375
376 if (!info || !sensor)
377 return -ENODEV;
378
379 sensor->id = info->id;
380 sensor->name = info->name;
381 sensor->type = info->type;
382 sensor->multiplier = info->multiplier;
383
384 for (i = SENSOR_REG_VALUE; i < SENSOR_REG_MAX; i++) {
385 if (!sensor_reg_valid(&info->regs[i]))
386 continue;
387
388 ret = max10_sys_read(dev, info->regs[i].regoff, &val);
389 if (ret)
390 break;
391
392 if (val == 0xdeadbeef) {
393 dev_debug(dev, "%s: sensor:%s invalid 0x%x at:%d\n",
394 __func__, sensor->name, val, i);
395 continue;
396 }
397
398 val *= info->multiplier;
399
400 switch (i) {
401 case SENSOR_REG_VALUE:
402 sensor->value_reg = info->regs[i].regoff;
403 sensor->flags |= OPAE_SENSOR_VALID;
404 break;
405 case SENSOR_REG_HIGH_WARN:
406 sensor->high_warn = val;
407 sensor->flags |= OPAE_SENSOR_HIGH_WARN_VALID;
408 break;
409 case SENSOR_REG_HIGH_FATAL:
410 sensor->high_fatal = val;
411 sensor->flags |= OPAE_SENSOR_HIGH_FATAL_VALID;
412 break;
413 case SENSOR_REG_LOW_WARN:
414 sensor->low_warn = val;
415 sensor->flags |= OPAE_SENSOR_LOW_WARN_VALID;
416 break;
417 case SENSOR_REG_LOW_FATAL:
418 sensor->low_fatal = val;
419 sensor->flags |= OPAE_SENSOR_LOW_FATAL_VALID;
420 break;
421 case SENSOR_REG_HYSTERESIS:
422 sensor->hysteresis = val;
423 sensor->flags |= OPAE_SENSOR_HYSTERESIS_VALID;
424 break;
425 }
426 }
427
428 return ret;
429 }
430
431 static int
max10_sensor_init(struct intel_max10_device * dev,int parent)432 max10_sensor_init(struct intel_max10_device *dev, int parent)
433 {
434 int i, ret = 0, offset = 0;
435 const fdt32_t *num;
436 const char *ptr;
437 u64 start, size;
438 struct raw_sensor_info *raw;
439 struct opae_sensor_info *sensor;
440 char *fdt_root = dev->fdt_root;
441
442 if (!fdt_root) {
443 dev_debug(dev, "skip sensor init as not find Device Tree\n");
444 return 0;
445 }
446
447 fdt_for_each_subnode(offset, fdt_root, parent) {
448 ptr = fdt_get_name(fdt_root, offset, NULL);
449 if (!ptr) {
450 dev_err(dev, "failed to fdt get name\n");
451 continue;
452 }
453
454 if (!strstr(ptr, "sensor")) {
455 dev_debug(dev, "%s is not a sensor node\n", ptr);
456 continue;
457 }
458
459 dev_debug(dev, "found sensor node %s\n", ptr);
460
461 raw = (struct raw_sensor_info *)opae_zmalloc(sizeof(*raw));
462 if (!raw) {
463 ret = -ENOMEM;
464 goto free_sensor;
465 }
466
467 raw->name = fdt_getprop(fdt_root, offset, "sensor_name", NULL);
468 if (!raw->name) {
469 ret = -EINVAL;
470 goto free_sensor;
471 }
472
473 raw->type = fdt_getprop(fdt_root, offset, "type", NULL);
474 if (!raw->type) {
475 ret = -EINVAL;
476 goto free_sensor;
477 }
478
479 for (i = SENSOR_REG_VALUE; i < SENSOR_REG_MAX; i++) {
480 ret = fdt_get_named_reg(fdt_root, offset,
481 sensor_reg_name[i], &start,
482 &size);
483 if (ret) {
484 dev_debug(dev, "no found %d: sensor node %s, %s\n",
485 ret, ptr, sensor_reg_name[i]);
486 if (i == SENSOR_REG_VALUE) {
487 ret = -EINVAL;
488 goto free_sensor;
489 }
490
491 continue;
492 }
493
494 /* This is a hack to compatible with non-secure
495 * solution. If sensors are included in root node,
496 * then it's non-secure dtb, which use absolute addr
497 * of non-secure solution.
498 */
499 if (parent)
500 raw->regs[i].regoff = start;
501 else
502 raw->regs[i].regoff = start -
503 MAX10_BASE_ADDR;
504 raw->regs[i].size = size;
505 }
506
507 num = fdt_getprop(fdt_root, offset, "id", NULL);
508 if (!num) {
509 ret = -EINVAL;
510 goto free_sensor;
511 }
512
513 raw->id = fdt32_to_cpu(*num);
514 num = fdt_getprop(fdt_root, offset, "multiplier", NULL);
515 raw->multiplier = num ? fdt32_to_cpu(*num) : 1;
516
517 dev_debug(dev, "found sensor from DTB: %s: %s: %u: %u\n",
518 raw->name, raw->type,
519 raw->id, raw->multiplier);
520
521 for (i = SENSOR_REG_VALUE; i < SENSOR_REG_MAX; i++)
522 dev_debug(dev, "sensor reg[%d]: %x: %zu\n",
523 i, raw->regs[i].regoff,
524 raw->regs[i].size);
525
526 sensor = opae_zmalloc(sizeof(*sensor));
527 if (!sensor) {
528 ret = -EINVAL;
529 goto free_sensor;
530 }
531
532 if (max10_add_sensor(dev, raw, sensor)) {
533 ret = -EINVAL;
534 opae_free(sensor);
535 goto free_sensor;
536 }
537
538 if (sensor->flags & OPAE_SENSOR_VALID) {
539 TAILQ_INSERT_TAIL(&dev->opae_sensor_list, sensor, node);
540 dev_info(dev, "found valid sensor: %s\n", sensor->name);
541 } else
542 opae_free(sensor);
543
544 opae_free(raw);
545 }
546
547 return 0;
548
549 free_sensor:
550 if (raw)
551 opae_free(raw);
552 max10_sensor_uinit(dev);
553 return ret;
554 }
555
check_max10_version(struct intel_max10_device * dev)556 static int check_max10_version(struct intel_max10_device *dev)
557 {
558 unsigned int v;
559
560 if (!max10_reg_read(dev, MAX10_SEC_BASE_ADDR + MAX10_BUILD_VER,
561 &v)) {
562 if (v != 0xffffffff) {
563 dev_info(dev, "secure MAX10 detected\n");
564 dev->base = MAX10_SEC_BASE_ADDR;
565 dev->flags |= MAX10_FLAGS_SECURE;
566 } else {
567 dev_info(dev, "non-secure MAX10 detected\n");
568 dev->base = MAX10_BASE_ADDR;
569 }
570 return 0;
571 }
572
573 return -ENODEV;
574 }
575
max10_staging_area_init(struct intel_max10_device * dev)576 static int max10_staging_area_init(struct intel_max10_device *dev)
577 {
578 char *fdt_root = dev->fdt_root;
579 int ret, offset = 0;
580 u64 start, size;
581
582 if (!fdt_root) {
583 dev_debug(dev,
584 "skip staging area init as not find Device Tree\n");
585 return -ENODEV;
586 }
587
588 dev->staging_area_size = 0;
589
590 fdt_for_each_subnode(offset, fdt_root, 0) {
591 if (fdt_node_check_compatible(fdt_root, offset,
592 "ifpga-sec-mgr,staging-area"))
593 continue;
594
595 ret = fdt_get_reg(fdt_root, offset, 0, &start, &size);
596 if (ret)
597 return ret;
598
599 if ((start & 0x3) || (start > MAX_STAGING_AREA_BASE) ||
600 (size > MAX_STAGING_AREA_SIZE))
601 return -EINVAL;
602
603 dev->staging_area_base = start;
604 dev->staging_area_size = size;
605
606 return ret;
607 }
608
609 return -ENODEV;
610 }
611
612 static int
max10_secure_hw_init(struct intel_max10_device * dev)613 max10_secure_hw_init(struct intel_max10_device *dev)
614 {
615 int offset, sysmgr_offset = 0;
616 char *fdt_root;
617
618 fdt_root = dev->fdt_root;
619 if (!fdt_root) {
620 dev_debug(dev, "skip init as not find Device Tree\n");
621 return 0;
622 }
623
624 fdt_for_each_subnode(offset, fdt_root, 0) {
625 if (!fdt_node_check_compatible(fdt_root, offset,
626 "intel-max10,system-manager")) {
627 sysmgr_offset = offset;
628 break;
629 }
630 }
631
632 max10_check_capability(dev);
633
634 max10_sensor_init(dev, sysmgr_offset);
635
636 max10_staging_area_init(dev);
637
638 return 0;
639 }
640
641 static int
max10_non_secure_hw_init(struct intel_max10_device * dev)642 max10_non_secure_hw_init(struct intel_max10_device *dev)
643 {
644 max10_check_capability(dev);
645
646 max10_sensor_init(dev, 0);
647
648 return 0;
649 }
650
651 struct intel_max10_device *
intel_max10_device_probe(struct altera_spi_device * spi,int chipselect)652 intel_max10_device_probe(struct altera_spi_device *spi,
653 int chipselect)
654 {
655 struct intel_max10_device *dev;
656 int ret;
657 unsigned int val;
658
659 dev = opae_malloc(sizeof(*dev));
660 if (!dev)
661 return NULL;
662
663 TAILQ_INIT(&dev->opae_sensor_list);
664
665 dev->spi_master = spi;
666
667 dev->spi_tran_dev = spi_transaction_init(spi, chipselect);
668 if (!dev->spi_tran_dev) {
669 dev_err(dev, "%s spi tran init fail\n", __func__);
670 goto free_dev;
671 }
672
673 /* check the max10 version */
674 ret = check_max10_version(dev);
675 if (ret) {
676 dev_err(dev, "Failed to find max10 hardware!\n");
677 goto free_dev;
678 }
679
680 /* load the MAX10 device table */
681 ret = init_max10_device_table(dev);
682 if (ret) {
683 dev_err(dev, "Init max10 device table fail\n");
684 goto free_dev;
685 }
686
687 /* init max10 devices, like sensor*/
688 if (dev->flags & MAX10_FLAGS_SECURE)
689 ret = max10_secure_hw_init(dev);
690 else
691 ret = max10_non_secure_hw_init(dev);
692 if (ret) {
693 dev_err(dev, "Failed to init max10 hardware!\n");
694 goto free_dtb;
695 }
696
697 /* read FPGA loading information */
698 ret = max10_sys_read(dev, FPGA_PAGE_INFO, &val);
699 if (ret) {
700 dev_err(dev, "fail to get FPGA loading info\n");
701 goto release_max10_hw;
702 }
703 dev_info(dev, "FPGA loaded from %s Image\n", val ? "User" : "Factory");
704
705 return dev;
706
707 release_max10_hw:
708 max10_sensor_uinit(dev);
709 free_dtb:
710 if (dev->fdt_root)
711 opae_free(dev->fdt_root);
712 if (dev->spi_tran_dev)
713 spi_transaction_remove(dev->spi_tran_dev);
714 free_dev:
715 opae_free(dev);
716
717 return NULL;
718 }
719
intel_max10_device_remove(struct intel_max10_device * dev)720 int intel_max10_device_remove(struct intel_max10_device *dev)
721 {
722 if (!dev)
723 return 0;
724
725 max10_sensor_uinit(dev);
726
727 if (dev->spi_tran_dev)
728 spi_transaction_remove(dev->spi_tran_dev);
729
730 if (dev->fdt_root)
731 opae_free(dev->fdt_root);
732
733 opae_free(dev);
734
735 return 0;
736 }
737