]> Git Repo - J-u-boot.git/blob - arch/arm/mach-imx/imx9/soc.c
imx9: soc: Add function to get target voltage mode
[J-u-boot.git] / arch / arm / mach-imx / imx9 / soc.c
1 // SPDX-License-Identifier: GPL-2.0+
2 /*
3  * Copyright 2022 NXP
4  *
5  * Peng Fan <[email protected]>
6  */
7
8 #include <config.h>
9 #include <cpu_func.h>
10 #include <init.h>
11 #include <log.h>
12 #include <asm/arch/imx-regs.h>
13 #include <asm/global_data.h>
14 #include <asm/io.h>
15 #include <asm/arch/clock.h>
16 #include <asm/arch/ccm_regs.h>
17 #include <asm/arch/sys_proto.h>
18 #include <asm/arch/trdc.h>
19 #include <asm/mach-imx/boot_mode.h>
20 #include <asm/mach-imx/syscounter.h>
21 #include <asm/armv8/mmu.h>
22 #include <dm/device.h>
23 #include <dm/device_compat.h>
24 #include <dm/uclass.h>
25 #include <env.h>
26 #include <env_internal.h>
27 #include <errno.h>
28 #include <fdt_support.h>
29 #include <imx_thermal.h>
30 #include <linux/bitops.h>
31 #include <linux/bitfield.h>
32 #include <linux/delay.h>
33 #include <thermal.h>
34 #include <asm/setup.h>
35 #include <asm/bootm.h>
36 #include <asm/arch-imx/cpu.h>
37 #include <asm/mach-imx/ele_api.h>
38 #include <fuse.h>
39 #include <asm/arch/ddr.h>
40
41 DECLARE_GLOBAL_DATA_PTR;
42
43 struct rom_api *g_rom_api = (struct rom_api *)0x1980;
44
45 #ifdef CONFIG_ENV_IS_IN_MMC
46 __weak int board_mmc_get_env_dev(int devno)
47 {
48         return devno;
49 }
50
51 int mmc_get_env_dev(void)
52 {
53         int ret;
54         u32 boot;
55         u16 boot_type;
56         u8 boot_instance;
57
58         ret = rom_api_query_boot_infor(QUERY_BT_DEV, &boot);
59
60         if (ret != ROM_API_OKAY) {
61                 puts("ROMAPI: failure at query_boot_info\n");
62                 return CONFIG_SYS_MMC_ENV_DEV;
63         }
64
65         boot_type = boot >> 16;
66         boot_instance = (boot >> 8) & 0xff;
67
68         debug("boot_type %d, instance %d\n", boot_type, boot_instance);
69
70         /* If not boot from sd/mmc, use default value */
71         if (boot_type != BOOT_TYPE_SD && boot_type != BOOT_TYPE_MMC)
72                 return env_get_ulong("mmcdev", 10, CONFIG_SYS_MMC_ENV_DEV);
73
74         return board_mmc_get_env_dev(boot_instance);
75 }
76 #endif
77
78 /*
79  * SPEED_GRADE[5:4]    SPEED_GRADE[3:0]    MHz
80  * xx                  0000                2300
81  * xx                  0001                2200
82  * xx                  0010                2100
83  * xx                  0011                2000
84  * xx                  0100                1900
85  * xx                  0101                1800
86  * xx                  0110                1700
87  * xx                  0111                1600
88  * xx                  1000                1500
89  * xx                  1001                1400
90  * xx                  1010                1300
91  * xx                  1011                1200
92  * xx                  1100                1100
93  * xx                  1101                1000
94  * xx                  1110                900
95  * xx                  1111                800
96  */
97 u32 get_cpu_speed_grade_hz(void)
98 {
99         int ret;
100         u32 bank, word, speed, max_speed;
101         u32 val;
102
103         bank = HW_CFG1 / NUM_WORDS_PER_BANK;
104         word = HW_CFG1 % NUM_WORDS_PER_BANK;
105         ret = fuse_read(bank, word, &val);
106         if (ret)
107                 val = 0; /* If read fuse failed, return as blank fuse */
108
109         val = FIELD_GET(SPEED_GRADING_MASK, val) & 0xF;
110
111         speed = MHZ(2300) - val * MHZ(100);
112
113         if (is_imx93())
114                 max_speed = MHZ(1700);
115
116         /* In case the fuse of speed grade not programmed */
117         if (speed > max_speed)
118                 speed = max_speed;
119
120         return speed;
121 }
122
123 /*
124  * `00` - Consumer 0C to 95C
125  * `01` - Ext. Consumer -20C to 105C
126  * `10` - Industrial -40C to 105C
127  * `11` - Automotive -40C to 125C
128  */
129 u32 get_cpu_temp_grade(int *minc, int *maxc)
130 {
131         int ret;
132         u32 bank, word, val;
133
134         bank = HW_CFG1 / NUM_WORDS_PER_BANK;
135         word = HW_CFG1 % NUM_WORDS_PER_BANK;
136         ret = fuse_read(bank, word, &val);
137         if (ret)
138                 val = 0; /* If read fuse failed, return as blank fuse */
139
140         val = FIELD_GET(MARKETING_GRADING_MASK, val);
141
142         if (minc && maxc) {
143                 if (val == TEMP_AUTOMOTIVE) {
144                         *minc = -40;
145                         *maxc = 125;
146                 } else if (val == TEMP_INDUSTRIAL) {
147                         *minc = -40;
148                         *maxc = 105;
149                 } else if (val == TEMP_EXTCOMMERCIAL) {
150                         if (is_imx93()) {
151                                 /* imx93 only has extended industrial*/
152                                 *minc = -40;
153                                 *maxc = 125;
154                         } else {
155                                 *minc = -20;
156                                 *maxc = 105;
157                         }
158                 } else {
159                         *minc = 0;
160                         *maxc = 95;
161                 }
162         }
163         return val;
164 }
165
166 static void set_cpu_info(struct ele_get_info_data *info)
167 {
168         gd->arch.soc_rev = info->soc;
169         gd->arch.lifecycle = info->lc;
170         memcpy((void *)&gd->arch.uid, &info->uid, 4 * sizeof(u32));
171 }
172
173 static u32 get_cpu_variant_type(u32 type)
174 {
175         u32 bank, word, val, val2;
176         int ret;
177
178         bank = HW_CFG1 / NUM_WORDS_PER_BANK;
179         word = HW_CFG1 % NUM_WORDS_PER_BANK;
180         ret = fuse_read(bank, word, &val);
181         if (ret)
182                 val = 0; /* If read fuse failed, return as blank fuse */
183
184         bank = HW_CFG2 / NUM_WORDS_PER_BANK;
185         word = HW_CFG2 % NUM_WORDS_PER_BANK;
186         ret = fuse_read(bank, word, &val2);
187         if (ret)
188                 val2 = 0; /* If read fuse failed, return as blank fuse */
189
190         bool npu_disable = !!(val & BIT(13));
191         bool core1_disable = !!(val & BIT(15));
192         u32 pack_9x9_fused = BIT(4) | BIT(17) | BIT(19) | BIT(24);
193
194         if ((val2 & pack_9x9_fused) == pack_9x9_fused)
195                 type = MXC_CPU_IMX9322;
196
197         if (npu_disable && core1_disable)
198                 return type + 3;
199         else if (npu_disable)
200                 return type + 2;
201         else if (core1_disable)
202                 return type + 1;
203
204         return type;
205 }
206
207 u32 get_cpu_rev(void)
208 {
209         u32 rev = (gd->arch.soc_rev >> 24) - 0xa0;
210
211         return (get_cpu_variant_type(MXC_CPU_IMX93) << 12) |
212                 (CHIP_REV_1_0 + rev);
213 }
214
215 #define UNLOCK_WORD 0xD928C520 /* unlock word */
216 #define REFRESH_WORD 0xB480A602 /* refresh word */
217
218 static void disable_wdog(void __iomem *wdog_base)
219 {
220         u32 val_cs = readl(wdog_base + 0x00);
221
222         if (!(val_cs & 0x80))
223                 return;
224
225         /* default is 32bits cmd */
226         writel(REFRESH_WORD, (wdog_base + 0x04)); /* Refresh the CNT */
227
228         if (!(val_cs & 0x800)) {
229                 writel(UNLOCK_WORD, (wdog_base + 0x04));
230                 while (!(readl(wdog_base + 0x00) & 0x800))
231                         ;
232         }
233         writel(0x0, (wdog_base + 0x0C)); /* Set WIN to 0 */
234         writel(0x400, (wdog_base + 0x08)); /* Set timeout to default 0x400 */
235         writel(0x2120, (wdog_base + 0x00)); /* Disable it and set update */
236
237         while (!(readl(wdog_base + 0x00) & 0x400))
238                 ;
239 }
240
241 void init_wdog(void)
242 {
243         u32 src_val;
244
245         disable_wdog((void __iomem *)WDG3_BASE_ADDR);
246         disable_wdog((void __iomem *)WDG4_BASE_ADDR);
247         disable_wdog((void __iomem *)WDG5_BASE_ADDR);
248
249         src_val = readl(0x54460018); /* reset mask */
250         src_val &= ~0x1c;
251         writel(src_val, 0x54460018);
252 }
253
254 static struct mm_region imx93_mem_map[] = {
255         {
256                 /* ROM */
257                 .virt = 0x0UL,
258                 .phys = 0x0UL,
259                 .size = 0x100000UL,
260                 .attrs = PTE_BLOCK_MEMTYPE(MT_NORMAL) |
261                          PTE_BLOCK_OUTER_SHARE
262         }, {
263                 /* TCM */
264                 .virt = 0x201c0000UL,
265                 .phys = 0x201c0000UL,
266                 .size = 0x80000UL,
267                 .attrs = PTE_BLOCK_MEMTYPE(MT_DEVICE_NGNRNE) |
268                          PTE_BLOCK_NON_SHARE |
269                          PTE_BLOCK_PXN | PTE_BLOCK_UXN
270         }, {
271                 /* OCRAM */
272                 .virt = 0x20480000UL,
273                 .phys = 0x20480000UL,
274                 .size = 0xA0000UL,
275                 .attrs = PTE_BLOCK_MEMTYPE(MT_NORMAL) |
276                          PTE_BLOCK_OUTER_SHARE
277         }, {
278                 /* AIPS */
279                 .virt = 0x40000000UL,
280                 .phys = 0x40000000UL,
281                 .size = 0x40000000UL,
282                 .attrs = PTE_BLOCK_MEMTYPE(MT_DEVICE_NGNRNE) |
283                          PTE_BLOCK_NON_SHARE |
284                          PTE_BLOCK_PXN | PTE_BLOCK_UXN
285         }, {
286                 /* Flexible Serial Peripheral Interface */
287                 .virt = 0x28000000UL,
288                 .phys = 0x28000000UL,
289                 .size = 0x08000000UL,
290                 .attrs = PTE_BLOCK_MEMTYPE(MT_DEVICE_NGNRNE) |
291                          PTE_BLOCK_NON_SHARE |
292                          PTE_BLOCK_PXN | PTE_BLOCK_UXN
293         }, {
294                 /* DRAM1 */
295                 .virt = 0x80000000UL,
296                 .phys = 0x80000000UL,
297                 .size = PHYS_SDRAM_SIZE,
298                 .attrs = PTE_BLOCK_MEMTYPE(MT_NORMAL) |
299                          PTE_BLOCK_OUTER_SHARE
300         }, {
301                 /* empty entrie to split table entry 5 if needed when TEEs are used */
302                 0,
303         }, {
304                 /* List terminator */
305                 0,
306         }
307 };
308
309 struct mm_region *mem_map = imx93_mem_map;
310
311 static unsigned int imx9_find_dram_entry_in_mem_map(void)
312 {
313         int i;
314
315         for (i = 0; i < ARRAY_SIZE(imx93_mem_map); i++)
316                 if (imx93_mem_map[i].phys == CFG_SYS_SDRAM_BASE)
317                         return i;
318
319         hang(); /* Entry not found, this must never happen. */
320 }
321
322 void enable_caches(void)
323 {
324         /* If OPTEE runs, remove OPTEE memory from MMU table to avoid speculative prefetch
325          * If OPTEE does not run, still update the MMU table according to dram banks structure
326          * to set correct dram size from board_phys_sdram_size
327          */
328         int i = 0;
329         /*
330          * please make sure that entry initial value matches
331          * imx93_mem_map for DRAM1
332          */
333         int entry = imx9_find_dram_entry_in_mem_map();
334         u64 attrs = imx93_mem_map[entry].attrs;
335
336         while (i < CONFIG_NR_DRAM_BANKS &&
337                entry < ARRAY_SIZE(imx93_mem_map)) {
338                 if (gd->bd->bi_dram[i].start == 0)
339                         break;
340                 imx93_mem_map[entry].phys = gd->bd->bi_dram[i].start;
341                 imx93_mem_map[entry].virt = gd->bd->bi_dram[i].start;
342                 imx93_mem_map[entry].size = gd->bd->bi_dram[i].size;
343                 imx93_mem_map[entry].attrs = attrs;
344                 debug("Added memory mapping (%d): %llx %llx\n", entry,
345                       imx93_mem_map[entry].phys, imx93_mem_map[entry].size);
346                 i++; entry++;
347         }
348
349         icache_enable();
350         dcache_enable();
351 }
352
353 __weak int board_phys_sdram_size(phys_size_t *size)
354 {
355         phys_size_t start, end;
356         phys_size_t val;
357
358         if (!size)
359                 return -EINVAL;
360
361         val = readl(REG_DDR_CS0_BNDS);
362         start = (val >> 16) << 24;
363         end   = (val & 0xFFFF);
364         end   = end ? end + 1 : 0;
365         end   = end << 24;
366         *size = end - start;
367
368         val = readl(REG_DDR_CS1_BNDS);
369         start = (val >> 16) << 24;
370         end   = (val & 0xFFFF);
371         end   = end ? end + 1 : 0;
372         end   = end << 24;
373         *size += end - start;
374
375         return 0;
376 }
377
378 int dram_init(void)
379 {
380         phys_size_t sdram_size;
381         int ret;
382
383         ret = board_phys_sdram_size(&sdram_size);
384         if (ret)
385                 return ret;
386
387         /* rom_pointer[1] contains the size of TEE occupies */
388         if (!IS_ENABLED(CONFIG_SPL_BUILD) && rom_pointer[1])
389                 gd->ram_size = sdram_size - rom_pointer[1];
390         else
391                 gd->ram_size = sdram_size;
392
393         return 0;
394 }
395
396 int dram_init_banksize(void)
397 {
398         int bank = 0;
399         int ret;
400         phys_size_t sdram_size;
401         phys_size_t sdram_b1_size, sdram_b2_size;
402
403         ret = board_phys_sdram_size(&sdram_size);
404         if (ret)
405                 return ret;
406
407         /* Bank 1 can't cross over 4GB space */
408         if (sdram_size > 0x80000000) {
409                 sdram_b1_size = 0x80000000;
410                 sdram_b2_size = sdram_size - 0x80000000;
411         } else {
412                 sdram_b1_size = sdram_size;
413                 sdram_b2_size = 0;
414         }
415
416         gd->bd->bi_dram[bank].start = PHYS_SDRAM;
417         if (!IS_ENABLED(CONFIG_SPL_BUILD) && rom_pointer[1]) {
418                 phys_addr_t optee_start = (phys_addr_t)rom_pointer[0];
419                 phys_size_t optee_size = (size_t)rom_pointer[1];
420
421                 gd->bd->bi_dram[bank].size = optee_start - gd->bd->bi_dram[bank].start;
422                 if ((optee_start + optee_size) < (PHYS_SDRAM + sdram_b1_size)) {
423                         if (++bank >= CONFIG_NR_DRAM_BANKS) {
424                                 puts("CONFIG_NR_DRAM_BANKS is not enough\n");
425                                 return -1;
426                         }
427
428                         gd->bd->bi_dram[bank].start = optee_start + optee_size;
429                         gd->bd->bi_dram[bank].size = PHYS_SDRAM +
430                                 sdram_b1_size - gd->bd->bi_dram[bank].start;
431                 }
432         } else {
433                 gd->bd->bi_dram[bank].size = sdram_b1_size;
434         }
435
436         if (sdram_b2_size) {
437                 if (++bank >= CONFIG_NR_DRAM_BANKS) {
438                         puts("CONFIG_NR_DRAM_BANKS is not enough for SDRAM_2\n");
439                         return -1;
440                 }
441                 gd->bd->bi_dram[bank].start = 0x100000000UL;
442                 gd->bd->bi_dram[bank].size = sdram_b2_size;
443         }
444
445         return 0;
446 }
447
448 phys_size_t get_effective_memsize(void)
449 {
450         int ret;
451         phys_size_t sdram_size;
452         phys_size_t sdram_b1_size;
453
454         ret = board_phys_sdram_size(&sdram_size);
455         if (!ret) {
456                 /* Bank 1 can't cross over 4GB space */
457                 if (sdram_size > 0x80000000)
458                         sdram_b1_size = 0x80000000;
459                 else
460                         sdram_b1_size = sdram_size;
461
462                 if (!IS_ENABLED(CONFIG_SPL_BUILD) && rom_pointer[1]) {
463                         /* We will relocate u-boot to top of dram1. TEE position has two cases:
464                          * 1. At the top of dram1,  Then return the size removed optee size.
465                          * 2. In the middle of dram1, return the size of dram1.
466                          */
467                         if ((rom_pointer[0] + rom_pointer[1]) == (PHYS_SDRAM + sdram_b1_size))
468                                 return ((phys_addr_t)rom_pointer[0] - PHYS_SDRAM);
469                 }
470
471                 return sdram_b1_size;
472         } else {
473                 return PHYS_SDRAM_SIZE;
474         }
475 }
476
477 void imx_get_mac_from_fuse(int dev_id, unsigned char *mac)
478 {
479         u32 val[2] = {};
480         int ret;
481
482         if (dev_id == 0) {
483                 ret = fuse_read(39, 3, &val[0]);
484                 if (ret)
485                         goto err;
486
487                 ret = fuse_read(39, 4, &val[1]);
488                 if (ret)
489                         goto err;
490
491                 mac[0] = val[1] >> 8;
492                 mac[1] = val[1];
493                 mac[2] = val[0] >> 24;
494                 mac[3] = val[0] >> 16;
495                 mac[4] = val[0] >> 8;
496                 mac[5] = val[0];
497
498         } else {
499                 ret = fuse_read(39, 5, &val[0]);
500                 if (ret)
501                         goto err;
502
503                 ret = fuse_read(39, 4, &val[1]);
504                 if (ret)
505                         goto err;
506
507                 if (is_imx93() && is_soc_rev(CHIP_REV_1_0)) {
508                         mac[0] = val[1] >> 24;
509                         mac[1] = val[1] >> 16;
510                         mac[2] = val[0] >> 24;
511                         mac[3] = val[0] >> 16;
512                         mac[4] = val[0] >> 8;
513                         mac[5] = val[0];
514                 } else {
515                         mac[0] = val[0] >> 24;
516                         mac[1] = val[0] >> 16;
517                         mac[2] = val[0] >> 8;
518                         mac[3] = val[0];
519                         mac[4] = val[1] >> 24;
520                         mac[5] = val[1] >> 16;
521                 }
522         }
523
524         debug("%s: MAC%d: %02x.%02x.%02x.%02x.%02x.%02x\n",
525               __func__, dev_id, mac[0], mac[1], mac[2], mac[3], mac[4], mac[5]);
526         return;
527 err:
528         memset(mac, 0, 6);
529         printf("%s: fuse read err: %d\n", __func__, ret);
530 }
531
532 int print_cpuinfo(void)
533 {
534         u32 cpurev;
535
536         cpurev = get_cpu_rev();
537
538         printf("CPU:   i.MX93 rev%d.%d\n", (cpurev & 0x000F0) >> 4, (cpurev & 0x0000F) >> 0);
539
540         return 0;
541 }
542
543 static int fixup_thermal_trips(void *blob, const char *name)
544 {
545         int minc, maxc;
546         int node, trip;
547
548         node = fdt_path_offset(blob, "/thermal-zones");
549         if (node < 0)
550                 return node;
551
552         node = fdt_subnode_offset(blob, node, name);
553         if (node < 0)
554                 return node;
555
556         node = fdt_subnode_offset(blob, node, "trips");
557         if (node < 0)
558                 return node;
559
560         get_cpu_temp_grade(&minc, &maxc);
561
562         fdt_for_each_subnode(trip, blob, node) {
563                 const char *type;
564                 int temp, ret;
565
566                 type = fdt_getprop(blob, trip, "type", NULL);
567                 if (!type)
568                         continue;
569
570                 temp = 0;
571                 if (!strcmp(type, "critical"))
572                         temp = 1000 * maxc;
573                 else if (!strcmp(type, "passive"))
574                         temp = 1000 * (maxc - 10);
575                 if (temp) {
576                         ret = fdt_setprop_u32(blob, trip, "temperature", temp);
577                         if (ret)
578                                 return ret;
579                 }
580         }
581
582         return 0;
583 }
584
585 void build_info(void)
586 {
587         u32 fw_version, sha1, res, status;
588         int ret;
589
590         printf("\nBuildInfo:\n");
591
592         ret = ele_get_fw_status(&status, &res);
593         if (ret) {
594                 printf("  - ELE firmware status failed %d, 0x%x\n", ret, res);
595         } else if ((status & 0xff) == 1) {
596                 ret = ele_get_fw_version(&fw_version, &sha1, &res);
597                 if (ret) {
598                         printf("  - ELE firmware version failed %d, 0x%x\n", ret, res);
599                 } else {
600                         printf("  - ELE firmware version %u.%u.%u-%x",
601                                (fw_version & (0x00ff0000)) >> 16,
602                                (fw_version & (0x0000fff0)) >> 4,
603                                (fw_version & (0x0000000f)), sha1);
604                         ((fw_version & (0x80000000)) >> 31) == 1 ? puts("-dirty\n") : puts("\n");
605                 }
606         } else {
607                 printf("  - ELE firmware not included\n");
608         }
609         puts("\n");
610 }
611
612 int arch_misc_init(void)
613 {
614         build_info();
615         return 0;
616 }
617
618 struct low_drive_freq_entry {
619         const char *node_path;
620         u32 clk;
621         u32 new_rate;
622 };
623
624 static int low_drive_fdt_fix_clock(void *fdt, int node_off, u32 clk_index, u32 new_rate)
625 {
626 #define MAX_ASSIGNED_CLKS 8
627         int cnt, j;
628         u32 assignedclks[MAX_ASSIGNED_CLKS]; /* max 8 clocks*/
629
630         cnt = fdtdec_get_int_array_count(fdt, node_off, "assigned-clock-rates",
631                                          assignedclks, MAX_ASSIGNED_CLKS);
632         if (cnt > 0) {
633                 if (cnt <= clk_index)
634                         return -ENOENT;
635
636                 if (assignedclks[clk_index] <= new_rate)
637                         return 0;
638
639                 assignedclks[clk_index] = new_rate;
640                 for (j = 0; j < cnt; j++)
641                         assignedclks[j] = cpu_to_fdt32(assignedclks[j]);
642
643                 return fdt_setprop(fdt, node_off, "assigned-clock-rates", &assignedclks,
644                                    cnt * sizeof(u32));
645         }
646
647         return -ENOENT;
648 }
649
650 static int low_drive_freq_update(void *blob)
651 {
652         int nodeoff, ret;
653         int i;
654
655         /* Update kernel dtb clocks for low drive mode */
656         struct low_drive_freq_entry table[] = {
657                 {"/soc@0/bus@42800000/mmc@42850000", 0, 266666667},
658                 {"/soc@0/bus@42800000/mmc@42860000", 0, 266666667},
659                 {"/soc@0/bus@42800000/mmc@428b0000", 0, 266666667},
660         };
661
662         for (i = 0; i < ARRAY_SIZE(table); i++) {
663                 nodeoff = fdt_path_offset(blob, table[i].node_path);
664                 if (nodeoff >= 0) {
665                         ret = low_drive_fdt_fix_clock(blob, nodeoff, table[i].clk,
666                                                       table[i].new_rate);
667                         if (!ret)
668                                 printf("%s freq updated\n", table[i].node_path);
669                 }
670         }
671
672         return 0;
673 }
674
675 #ifdef CONFIG_OF_BOARD_FIXUP
676 #ifndef CONFIG_SPL_BUILD
677 int board_fix_fdt(void *fdt)
678 {
679         /* Update dtb clocks for low drive mode */
680         if (is_voltage_mode(VOLT_LOW_DRIVE)) {
681                 int nodeoff;
682                 int i;
683
684                 struct low_drive_freq_entry table[] = {
685                         {"/soc@0/bus@42800000/mmc@42850000", 0, 266666667},
686                         {"/soc@0/bus@42800000/mmc@42860000", 0, 266666667},
687                         {"/soc@0/bus@42800000/mmc@428b0000", 0, 266666667},
688                 };
689
690                 for (i = 0; i < ARRAY_SIZE(table); i++) {
691                         nodeoff = fdt_path_offset(fdt, table[i].node_path);
692                         if (nodeoff >= 0)
693                                 low_drive_fdt_fix_clock(fdt, nodeoff, table[i].clk,
694                                                         table[i].new_rate);
695                 }
696         }
697
698         return 0;
699 }
700 #endif
701 #endif
702
703 int ft_system_setup(void *blob, struct bd_info *bd)
704 {
705         if (fixup_thermal_trips(blob, "cpu-thermal"))
706                 printf("Failed to update cpu-thermal trip(s)");
707
708         if (is_voltage_mode(VOLT_LOW_DRIVE))
709                 low_drive_freq_update(blob);
710
711         return 0;
712 }
713
714 #if defined(CONFIG_ENV_VARS_UBOOT_RUNTIME_CONFIG)
715 void get_board_serial(struct tag_serialnr *serialnr)
716 {
717         printf("UID: %08x%08x%08x%08x\n", __be32_to_cpu(gd->arch.uid[0]),
718                __be32_to_cpu(gd->arch.uid[1]), __be32_to_cpu(gd->arch.uid[2]),
719                __be32_to_cpu(gd->arch.uid[3]));
720
721         serialnr->low = __be32_to_cpu(gd->arch.uid[1]);
722         serialnr->high = __be32_to_cpu(gd->arch.uid[0]);
723 }
724 #endif
725
726 static void save_reset_cause(void)
727 {
728         struct src_general_regs *src = (struct src_general_regs *)SRC_GLOBAL_RBASE;
729         u32 srsr = readl(&src->srsr);
730
731         /* clear srsr in sec mode */
732         writel(srsr, &src->srsr);
733
734         /* Save value to GPR1 to pass to nonsecure */
735         writel(srsr, &src->gpr[0]);
736 }
737
738 int arch_cpu_init(void)
739 {
740         if (IS_ENABLED(CONFIG_SPL_BUILD)) {
741                 /* Disable wdog */
742                 init_wdog();
743
744                 clock_init();
745
746                 trdc_early_init();
747
748                 /* Save SRC SRSR to GPR1 and clear it */
749                 save_reset_cause();
750         }
751
752         return 0;
753 }
754
755 int imx9_probe_mu(void)
756 {
757         struct udevice *devp;
758         int node, ret;
759         u32 res;
760         struct ele_get_info_data info;
761
762         node = fdt_node_offset_by_compatible(gd->fdt_blob, -1, "fsl,imx93-mu-s4");
763
764         ret = uclass_get_device_by_of_offset(UCLASS_MISC, node, &devp);
765         if (ret)
766                 return ret;
767
768         if (gd->flags & GD_FLG_RELOC)
769                 return 0;
770
771         ret = ele_get_info(&info, &res);
772         if (ret)
773                 return ret;
774
775         set_cpu_info(&info);
776
777         return 0;
778 }
779 EVENT_SPY_SIMPLE(EVT_DM_POST_INIT_F, imx9_probe_mu);
780 EVENT_SPY_SIMPLE(EVT_DM_POST_INIT_R, imx9_probe_mu);
781
782 int timer_init(void)
783 {
784 #ifdef CONFIG_SPL_BUILD
785         struct sctr_regs *sctr = (struct sctr_regs *)SYSCNT_CTRL_BASE_ADDR;
786         unsigned long freq = readl(&sctr->cntfid0);
787
788         /* Update with accurate clock frequency */
789         asm volatile("msr cntfrq_el0, %0" : : "r" (freq) : "memory");
790
791         clrsetbits_le32(&sctr->cntcr, SC_CNTCR_FREQ0 | SC_CNTCR_FREQ1,
792                         SC_CNTCR_FREQ0 | SC_CNTCR_ENABLE | SC_CNTCR_HDBG);
793 #endif
794
795         gd->arch.tbl = 0;
796         gd->arch.tbu = 0;
797
798         return 0;
799 }
800
801 enum env_location env_get_location(enum env_operation op, int prio)
802 {
803         enum boot_device dev = get_boot_device();
804
805         if (prio)
806                 return ENVL_UNKNOWN;
807
808         switch (dev) {
809         case QSPI_BOOT:
810                 if (CONFIG_IS_ENABLED(ENV_IS_IN_SPI_FLASH))
811                         return ENVL_SPI_FLASH;
812                 return ENVL_NOWHERE;
813         case SD1_BOOT:
814         case SD2_BOOT:
815         case SD3_BOOT:
816         case MMC1_BOOT:
817         case MMC2_BOOT:
818         case MMC3_BOOT:
819                 if (CONFIG_IS_ENABLED(ENV_IS_IN_MMC))
820                         return ENVL_MMC;
821                 else if (CONFIG_IS_ENABLED(ENV_IS_IN_EXT4))
822                         return ENVL_EXT4;
823                 else if (CONFIG_IS_ENABLED(ENV_IS_IN_FAT))
824                         return ENVL_FAT;
825                 return ENVL_NOWHERE;
826         default:
827                 return ENVL_NOWHERE;
828         }
829 }
830
831 static int mix_power_init(enum mix_power_domain pd)
832 {
833         enum src_mix_slice_id mix_id;
834         enum src_mem_slice_id mem_id;
835         struct src_mix_slice_regs *mix_regs;
836         struct src_mem_slice_regs *mem_regs;
837         struct src_general_regs *global_regs;
838         u32 scr, val;
839
840         switch (pd) {
841         case MIX_PD_MEDIAMIX:
842                 mix_id = SRC_MIX_MEDIA;
843                 mem_id = SRC_MEM_MEDIA;
844                 scr = BIT(5);
845
846                 /* Enable ELE handshake */
847                 struct blk_ctrl_s_aonmix_regs *s_regs =
848                         (struct blk_ctrl_s_aonmix_regs *)BLK_CTRL_S_ANOMIX_BASE_ADDR;
849
850                 setbits_le32(&s_regs->lp_handshake[0], BIT(13));
851                 break;
852         case MIX_PD_MLMIX:
853                 mix_id = SRC_MIX_ML;
854                 mem_id = SRC_MEM_ML;
855                 scr = BIT(4);
856                 break;
857         case MIX_PD_DDRMIX:
858                 mix_id = SRC_MIX_DDRMIX;
859                 mem_id = SRC_MEM_DDRMIX;
860                 scr = BIT(6);
861                 break;
862         default:
863                 return -EINVAL;
864         }
865
866         mix_regs = (struct src_mix_slice_regs *)(ulong)(SRC_IPS_BASE_ADDR + 0x400 * (mix_id + 1));
867         mem_regs =
868                 (struct src_mem_slice_regs *)(ulong)(SRC_IPS_BASE_ADDR + 0x3800 + 0x400 * mem_id);
869         global_regs = (struct src_general_regs *)(ulong)SRC_GLOBAL_RBASE;
870
871         /* Allow NS to set it */
872         setbits_le32(&mix_regs->authen_ctrl, BIT(9));
873
874         clrsetbits_le32(&mix_regs->psw_ack_ctrl[0], BIT(28), BIT(29));
875
876         /* mix reset will be held until boot core write this bit to 1 */
877         setbits_le32(&global_regs->scr, scr);
878
879         /* Enable mem in Low power auto sequence */
880         setbits_le32(&mem_regs->mem_ctrl, BIT(2));
881
882         /* Set the power down state */
883         val = readl(&mix_regs->func_stat);
884         if (val & SRC_MIX_SLICE_FUNC_STAT_PSW_STAT) {
885                 /* The mix is default power off, power down it to make PDN_SFT bit
886                  *  aligned with FUNC STAT
887                  */
888                 setbits_le32(&mix_regs->slice_sw_ctrl, BIT(31));
889                 val = readl(&mix_regs->func_stat);
890
891                 /* Since PSW_STAT is 1, can't be used for power off status (SW_CTRL BIT31 set)) */
892                 /* Check the MEM STAT change to ensure SSAR is completed */
893                 while (!(val & SRC_MIX_SLICE_FUNC_STAT_MEM_STAT))
894                         val = readl(&mix_regs->func_stat);
895
896                 /* wait few ipg clock cycles to ensure FSM done and power off status is correct */
897                 /* About 5 cycles at 24Mhz, 1us is enough  */
898                 udelay(1);
899         } else {
900                 /*  The mix is default power on, Do mix power cycle */
901                 setbits_le32(&mix_regs->slice_sw_ctrl, BIT(31));
902                 val = readl(&mix_regs->func_stat);
903                 while (!(val & SRC_MIX_SLICE_FUNC_STAT_PSW_STAT))
904                         val = readl(&mix_regs->func_stat);
905         }
906
907         /* power on */
908         clrbits_le32(&mix_regs->slice_sw_ctrl, BIT(31));
909         val = readl(&mix_regs->func_stat);
910         while (val & SRC_MIX_SLICE_FUNC_STAT_SSAR_STAT)
911                 val = readl(&mix_regs->func_stat);
912
913         return 0;
914 }
915
916 void disable_isolation(void)
917 {
918         struct src_general_regs *global_regs = (struct src_general_regs *)(ulong)SRC_GLOBAL_RBASE;
919         /* clear isolation for usbphy, dsi, csi*/
920         writel(0x0, &global_regs->sp_iso_ctrl);
921 }
922
923 void soc_power_init(void)
924 {
925         mix_power_init(MIX_PD_MEDIAMIX);
926         mix_power_init(MIX_PD_MLMIX);
927
928         disable_isolation();
929 }
930
931 bool m33_is_rom_kicked(void)
932 {
933         struct blk_ctrl_s_aonmix_regs *s_regs =
934                         (struct blk_ctrl_s_aonmix_regs *)BLK_CTRL_S_ANOMIX_BASE_ADDR;
935
936         if (!(readl(&s_regs->m33_cfg) & BIT(2)))
937                 return true;
938
939         return false;
940 }
941
942 int m33_prepare(void)
943 {
944         struct src_mix_slice_regs *mix_regs =
945                 (struct src_mix_slice_regs *)(ulong)(SRC_IPS_BASE_ADDR + 0x400 * (SRC_MIX_CM33 + 1));
946         struct src_general_regs *global_regs =
947                 (struct src_general_regs *)(ulong)SRC_GLOBAL_RBASE;
948         struct blk_ctrl_s_aonmix_regs *s_regs =
949                         (struct blk_ctrl_s_aonmix_regs *)BLK_CTRL_S_ANOMIX_BASE_ADDR;
950         u32 val, i;
951
952         if (m33_is_rom_kicked())
953                 return -EPERM;
954
955         /* Release reset of M33 */
956         setbits_le32(&global_regs->scr, BIT(0));
957
958         /* Check the reset released in M33 MIX func stat */
959         val = readl(&mix_regs->func_stat);
960         while (!(val & SRC_MIX_SLICE_FUNC_STAT_RST_STAT))
961                 val = readl(&mix_regs->func_stat);
962
963         /* Release ELE TROUT */
964         ele_release_m33_trout();
965
966         /* Mask WDOG1 IRQ from A55, we use it for M33 reset */
967         setbits_le32(&s_regs->ca55_irq_mask[1], BIT(6));
968
969         /* Turn on WDOG1 clock */
970         ccm_lpcg_on(CCGR_WDG1, 1);
971
972         /* Set ELE LP handshake for M33 reset */
973         setbits_le32(&s_regs->lp_handshake[0], BIT(6));
974
975         /* OSCCA enabled, reconfigure TRDC for TCM access, otherwise ECC init will raise error */
976         val = readl(BLK_CTRL_NS_ANOMIX_BASE_ADDR + 0x28);
977         if (val & BIT(0)) {
978                 trdc_mbc_set_control(0x44270000, 1, 0, 0x6600);
979
980                 for (i = 0; i < 32; i++)
981                         trdc_mbc_blk_config(0x44270000, 1, 3, 0, i, true, 0);
982
983                 for (i = 0; i < 32; i++)
984                         trdc_mbc_blk_config(0x44270000, 1, 3, 1, i, true, 0);
985         }
986
987         /* Clear M33 TCM for ECC */
988         memset((void *)(ulong)0x201e0000, 0, 0x40000);
989
990         return 0;
991 }
992
993 int psci_sysreset_get_status(struct udevice *dev, char *buf, int size)
994 {
995         static const char *reset_cause[] = {
996                 "POR ",
997                 "JTAG ",
998                 "IPP USER ",
999                 "WDOG1 ",
1000                 "WDOG2 ",
1001                 "WDOG3 ",
1002                 "WDOG4 ",
1003                 "WDOG5 ",
1004                 "TEMPSENSE ",
1005                 "CSU ",
1006                 "JTAG_SW ",
1007                 "M33_REQ ",
1008                 "M33_LOCKUP ",
1009                 "UNK ",
1010                 "UNK ",
1011                 "UNK "
1012         };
1013
1014         struct src_general_regs *src = (struct src_general_regs *)SRC_GLOBAL_RBASE;
1015         u32 srsr;
1016         u32 i;
1017         int res;
1018
1019         srsr = readl(&src->gpr[0]);
1020
1021         for (i = ARRAY_SIZE(reset_cause); i > 0; i--) {
1022                 if (srsr & (BIT(i - 1)))
1023                         break;
1024         }
1025
1026         res = snprintf(buf, size, "Reset Status: %s\n", i ? reset_cause[i - 1] : "unknown reset");
1027         if (res < 0) {
1028                 dev_err(dev, "Could not write reset status message (err = %d)\n", res);
1029                 return -EIO;
1030         }
1031
1032         return 0;
1033 }
1034
1035 enum imx9_soc_voltage_mode soc_target_voltage_mode(void)
1036 {
1037         u32 speed = get_cpu_speed_grade_hz();
1038         enum imx9_soc_voltage_mode voltage = VOLT_OVER_DRIVE;
1039
1040         if (is_imx93()) {
1041                 if (speed == 1700000000)
1042                         voltage = VOLT_OVER_DRIVE;
1043                 else if (speed == 1400000000)
1044                         voltage = VOLT_NOMINAL_DRIVE;
1045                 else if (speed == 900000000 || speed == 800000000)
1046                         voltage = VOLT_LOW_DRIVE;
1047                 else
1048                         printf("Unexpected A55 freq %u, default to OD\n", speed);
1049         }
1050
1051         return voltage;
1052 }
This page took 0.089715 seconds and 4 git commands to generate.