]>
Commit | Line | Data |
---|---|---|
828d9af5 BM |
1 | /* |
2 | * Copyright (C) 2015, Bin Meng <bmeng.cn@gmail.com> | |
3 | * | |
4 | * SPDX-License-Identifier: GPL-2.0+ | |
5 | */ | |
6 | ||
7 | #include <common.h> | |
6df7ffea | 8 | #include <mmc.h> |
e4ad6031 BM |
9 | #include <netdev.h> |
10 | #include <phy.h> | |
828d9af5 | 11 | #include <asm/io.h> |
05b98ec3 | 12 | #include <asm/irq.h> |
828d9af5 BM |
13 | #include <asm/pci.h> |
14 | #include <asm/post.h> | |
15 | #include <asm/processor.h> | |
b162257d BM |
16 | #include <asm/arch/device.h> |
17 | #include <asm/arch/msg_port.h> | |
18 | #include <asm/arch/quark.h> | |
19 | ||
6df7ffea BM |
20 | static struct pci_device_id mmc_supported[] = { |
21 | { PCI_VENDOR_ID_INTEL, PCI_DEVICE_ID_INTEL_QRK_SDIO }, | |
22 | }; | |
23 | ||
728b393f BM |
24 | /* |
25 | * TODO: | |
26 | * | |
27 | * This whole routine should be removed until we fully convert the ICH SPI | |
28 | * driver to DM and make use of DT to pass the bios control register offset | |
29 | */ | |
30 | static void unprotect_spi_flash(void) | |
31 | { | |
32 | u32 bc; | |
33 | ||
31f57c28 | 34 | bc = x86_pci_read_config32(QUARK_LEGACY_BRIDGE, 0xd8); |
728b393f | 35 | bc |= 0x1; /* unprotect the flash */ |
31f57c28 | 36 | x86_pci_write_config32(QUARK_LEGACY_BRIDGE, 0xd8, bc); |
728b393f BM |
37 | } |
38 | ||
b162257d BM |
39 | static void quark_setup_bars(void) |
40 | { | |
41 | /* GPIO - D31:F0:R44h */ | |
42 | pci_write_config_dword(QUARK_LEGACY_BRIDGE, LB_GBA, | |
43 | CONFIG_GPIO_BASE | IO_BAR_EN); | |
44 | ||
45 | /* ACPI PM1 Block - D31:F0:R48h */ | |
46 | pci_write_config_dword(QUARK_LEGACY_BRIDGE, LB_PM1BLK, | |
47 | CONFIG_ACPI_PM1_BASE | IO_BAR_EN); | |
48 | ||
49 | /* GPE0 - D31:F0:R4Ch */ | |
50 | pci_write_config_dword(QUARK_LEGACY_BRIDGE, LB_GPE0BLK, | |
51 | CONFIG_ACPI_GPE0_BASE | IO_BAR_EN); | |
52 | ||
53 | /* WDT - D31:F0:R84h */ | |
54 | pci_write_config_dword(QUARK_LEGACY_BRIDGE, LB_WDTBA, | |
55 | CONFIG_WDT_BASE | IO_BAR_EN); | |
56 | ||
57 | /* RCBA - D31:F0:RF0h */ | |
58 | pci_write_config_dword(QUARK_LEGACY_BRIDGE, LB_RCBA, | |
59 | CONFIG_RCBA_BASE | MEM_BAR_EN); | |
60 | ||
61 | /* ACPI P Block - Msg Port 04:R70h */ | |
62 | msg_port_write(MSG_PORT_RMU, PBLK_BA, | |
63 | CONFIG_ACPI_PBLK_BASE | IO_BAR_EN); | |
64 | ||
65 | /* SPI DMA - Msg Port 04:R7Ah */ | |
66 | msg_port_write(MSG_PORT_RMU, SPI_DMA_BA, | |
67 | CONFIG_SPI_DMA_BASE | IO_BAR_EN); | |
68 | ||
69 | /* PCIe ECAM */ | |
70 | msg_port_write(MSG_PORT_MEM_ARBITER, AEC_CTRL, | |
71 | CONFIG_PCIE_ECAM_BASE | MEM_BAR_EN); | |
72 | msg_port_write(MSG_PORT_HOST_BRIDGE, HEC_REG, | |
73 | CONFIG_PCIE_ECAM_BASE | MEM_BAR_EN); | |
74 | } | |
828d9af5 | 75 | |
f82a7840 BM |
76 | static void quark_enable_legacy_seg(void) |
77 | { | |
78 | u32 hmisc2; | |
79 | ||
80 | hmisc2 = msg_port_read(MSG_PORT_HOST_BRIDGE, HMISC2); | |
81 | hmisc2 |= (HMISC2_SEGE | HMISC2_SEGF | HMISC2_SEGAB); | |
82 | msg_port_write(MSG_PORT_HOST_BRIDGE, HMISC2, hmisc2); | |
83 | } | |
84 | ||
828d9af5 BM |
85 | int arch_cpu_init(void) |
86 | { | |
87 | struct pci_controller *hose; | |
88 | int ret; | |
89 | ||
90 | post_code(POST_CPU_INIT); | |
91 | #ifdef CONFIG_SYS_X86_TSC_TIMER | |
92 | timer_set_base(rdtsc()); | |
93 | #endif | |
94 | ||
95 | ret = x86_cpu_init_f(); | |
96 | if (ret) | |
97 | return ret; | |
98 | ||
99 | ret = pci_early_init_hose(&hose); | |
100 | if (ret) | |
101 | return ret; | |
102 | ||
b162257d BM |
103 | /* |
104 | * Quark SoC has some non-standard BARs (excluding PCI standard BARs) | |
105 | * which need be initialized with suggested values | |
106 | */ | |
107 | quark_setup_bars(); | |
108 | ||
f82a7840 BM |
109 | /* Turn on legacy segments (A/B/E/F) decode to system RAM */ |
110 | quark_enable_legacy_seg(); | |
111 | ||
728b393f BM |
112 | unprotect_spi_flash(); |
113 | ||
828d9af5 BM |
114 | return 0; |
115 | } | |
116 | ||
117 | int print_cpuinfo(void) | |
118 | { | |
119 | post_code(POST_CPU_INFO); | |
120 | return default_print_cpuinfo(); | |
121 | } | |
122 | ||
123 | void reset_cpu(ulong addr) | |
124 | { | |
125 | /* cold reset */ | |
ebebf059 | 126 | x86_full_reset(); |
828d9af5 | 127 | } |
6df7ffea BM |
128 | |
129 | int cpu_mmc_init(bd_t *bis) | |
130 | { | |
131 | return pci_mmc_init("Quark SDHCI", mmc_supported, | |
132 | ARRAY_SIZE(mmc_supported)); | |
133 | } | |
e4ad6031 BM |
134 | |
135 | int cpu_eth_init(bd_t *bis) | |
136 | { | |
137 | u32 base; | |
138 | int ret0, ret1; | |
139 | ||
140 | pci_read_config_dword(QUARK_EMAC0, PCI_BASE_ADDRESS_0, &base); | |
141 | ret0 = designware_initialize(base, PHY_INTERFACE_MODE_RMII); | |
142 | ||
143 | pci_read_config_dword(QUARK_EMAC1, PCI_BASE_ADDRESS_0, &base); | |
144 | ret1 = designware_initialize(base, PHY_INTERFACE_MODE_RMII); | |
145 | ||
146 | if (ret0 < 0 && ret1 < 0) | |
147 | return -1; | |
148 | else | |
149 | return 0; | |
150 | } | |
05b98ec3 BM |
151 | |
152 | void cpu_irq_init(void) | |
153 | { | |
154 | struct quark_rcba *rcba; | |
155 | u32 base; | |
156 | ||
157 | base = x86_pci_read_config32(QUARK_LEGACY_BRIDGE, LB_RCBA); | |
158 | base &= ~MEM_BAR_EN; | |
159 | rcba = (struct quark_rcba *)base; | |
160 | ||
161 | /* | |
162 | * Route Quark PCI device interrupt pin to PIRQ | |
163 | * | |
164 | * Route device#23's INTA/B/C/D to PIRQA/B/C/D | |
165 | * Route device#20,21's INTA/B/C/D to PIRQE/F/G/H | |
166 | */ | |
167 | writew(PIRQC, &rcba->rmu_ir); | |
168 | writew(PIRQA | (PIRQB << 4) | (PIRQC << 8) | (PIRQD << 12), | |
169 | &rcba->d23_ir); | |
170 | writew(PIRQD, &rcba->core_ir); | |
171 | writew(PIRQE | (PIRQF << 4) | (PIRQG << 8) | (PIRQH << 12), | |
172 | &rcba->d20d21_ir); | |
173 | } | |
174 | ||
175 | int arch_misc_init(void) | |
176 | { | |
177 | pirq_init(); | |
178 | ||
179 | return 0; | |
180 | } |