armadaxp_machdep.c revision 1.7 1 /* $NetBSD: armadaxp_machdep.c,v 1.7 2014/03/18 06:17:55 matt Exp $ */
2 /*******************************************************************************
3 Copyright (C) Marvell International Ltd. and its affiliates
4
5 Developed by Semihalf
6
7 ********************************************************************************
8 Marvell BSD License
9
10 If you received this File from Marvell, you may opt to use, redistribute and/or
11 modify this File under the following licensing terms.
12 Redistribution and use in source and binary forms, with or without modification,
13 are permitted provided that the following conditions are met:
14
15 * Redistributions of source code must retain the above copyright notice,
16 this list of conditions and the following disclaimer.
17
18 * Redistributions in binary form must reproduce the above copyright
19 notice, this list of conditions and the following disclaimer in the
20 documentation and/or other materials provided with the distribution.
21
22 * Neither the name of Marvell nor the names of its contributors may be
23 used to endorse or promote products derived from this software without
24 specific prior written permission.
25
26 THIS SOFTWARE IS PROVIDED BY THE COPYRIGHT HOLDERS AND CONTRIBUTORS "AS IS" AND
27 ANY EXPRESS OR IMPLIED WARRANTIES, INCLUDING, BUT NOT LIMITED TO, THE IMPLIED
28 WARRANTIES OF MERCHANTABILITY AND FITNESS FOR A PARTICULAR PURPOSE ARE
29 DISCLAIMED. IN NO EVENT SHALL THE COPYRIGHT OWNER OR CONTRIBUTORS BE LIABLE FOR
30 ANY DIRECT, INDIRECT, INCIDENTAL, SPECIAL, EXEMPLARY, OR CONSEQUENTIAL DAMAGES
31 (INCLUDING, BUT NOT LIMITED TO, PROCUREMENT OF SUBSTITUTE GOODS OR SERVICES;
32 LOSS OF USE, DATA, OR PROFITS; OR BUSINESS INTERRUPTION) HOWEVER CAUSED AND ON
33 ANY THEORY OF LIABILITY, WHETHER IN CONTRACT, STRICT LIABILITY, OR TORT
34 (INCLUDING NEGLIGENCE OR OTHERWISE) ARISING IN ANY WAY OUT OF THE USE OF THIS
35 SOFTWARE, EVEN IF ADVISED OF THE POSSIBILITY OF SUCH DAMAGE.
36
37 *******************************************************************************/
38
39 #include <sys/cdefs.h>
40 __KERNEL_RCSID(0, "$NetBSD: armadaxp_machdep.c,v 1.7 2014/03/18 06:17:55 matt Exp $");
41
42 #include "opt_machdep.h"
43 #include "opt_mvsoc.h"
44 #include "opt_evbarm_boardtype.h"
45 #include "opt_com.h"
46 #include "opt_ddb.h"
47 #include "opt_kgdb.h"
48 #include "opt_pci.h"
49 #include "opt_ipkdb.h"
50
51 #include <sys/bus.h>
52 #include <sys/param.h>
53 #include <sys/device.h>
54 #include <sys/systm.h>
55 #include <sys/kernel.h>
56 #include <sys/exec.h>
57 #include <sys/proc.h>
58 #include <sys/msgbuf.h>
59 #include <sys/reboot.h>
60 #include <sys/termios.h>
61 #include <sys/ksyms.h>
62
63 #include <uvm/uvm_extern.h>
64
65 #include <sys/conf.h>
66 #include <dev/cons.h>
67 #include <dev/md.h>
68
69 #include <dev/pci/pcireg.h>
70 #include <dev/pci/pcivar.h>
71 #include <machine/pci_machdep.h>
72
73 #include <machine/db_machdep.h>
74 #include <ddb/db_sym.h>
75 #include <ddb/db_extern.h>
76 #ifdef KGDB
77 #include <sys/kgdb.h>
78 #endif
79
80 #include <machine/bootconfig.h>
81 #include <machine/autoconf.h>
82 #include <machine/cpu.h>
83 #include <machine/frame.h>
84 #include <arm/armreg.h>
85 #include <arm/undefined.h>
86
87 #include <arm/arm32/machdep.h>
88
89 #include <arm/marvell/mvsocreg.h>
90 #include <arm/marvell/mvsocvar.h>
91 #include <arm/marvell/armadaxpreg.h>
92
93 #include <evbarm/marvell/marvellreg.h>
94 #include <evbarm/marvell/marvellvar.h>
95
96 #include "mvpex.h"
97 #include "com.h"
98 #if NCOM > 0
99 #include <dev/ic/comreg.h>
100 #include <dev/ic/comvar.h>
101 #endif
102
103 /*
104 * Address to call from cpu_reset() to reset the machine.
105 * This is machine architecture dependent as it varies depending
106 * on where the ROM appears when you turn the MMU off.
107 */
108
109
110 /* Define various stack sizes in pages */
111 #define IRQ_STACK_SIZE 1
112 #define ABT_STACK_SIZE 1
113 #ifdef IPKDB
114 #define UND_STACK_SIZE 2
115 #else
116 #define UND_STACK_SIZE 1
117 #endif
118
119 BootConfig bootconfig; /* Boot config storage */
120 char *boot_args = NULL;
121 char *boot_file = NULL;
122
123 extern int KERNEL_BASE_phys[];
124
125 /*extern char KERNEL_BASE_phys[];*/
126 extern char etext[], __data_start[], _edata[], __bss_start[], __bss_end__[];
127 extern char _end[];
128
129 /*
130 * Put some bogus settings of the MEMSTART and MEMSIZE
131 * if they are not defined in kernel configuration file.
132 */
133 #ifndef MEMSTART
134 #define MEMSTART 0x00000000UL
135 #endif
136 #ifndef MEMSIZE
137 #define MEMSIZE 0x40000000UL
138 #endif
139
140 #ifndef STARTUP_PAGETABLE_ADDR
141 #define STARTUP_PAGETABLE_ADDR 0x00000000UL
142 #endif
143
144 /* Physical offset of the kernel from MEMSTART */
145 #define KERNEL_OFFSET (paddr_t)&KERNEL_BASE_phys
146 /* Kernel base virtual address */
147 #define KERNEL_TEXT_BASE (KERNEL_BASE + KERNEL_OFFSET)
148
149 #define KERNEL_VM_BASE (KERNEL_BASE + 0x01000000)
150 #define KERNEL_VM_SIZE 0x10000000
151
152 /* Prototypes */
153 extern int armadaxp_l2_init(bus_addr_t);
154 extern void armadaxp_io_coherency_init(void);
155
156 void consinit(void);
157 #ifdef KGDB
158 static void kgdb_port_init(void);
159 #endif
160
161 static void axp_device_register(device_t dev, void *aux);
162
163 static void
164 axp_system_reset(void)
165 {
166 extern vaddr_t misc_base;
167
168 #define write_miscreg(r, v) (*(volatile uint32_t *)(misc_base + (r)) = (v))
169
170 cpu_reset_address = 0;
171
172 /* Unmask soft reset */
173 write_miscreg(ARMADAXP_MISC_RSTOUTNMASKR,
174 ARMADAXP_MISC_RSTOUTNMASKR_GLOBALSOFTRSTOUTEN);
175 /* Assert soft reset */
176 write_miscreg(ARMADAXP_MISC_SSRR, ARMADAXP_MISC_SSRR_GLOBALSOFTRST);
177
178 while (1);
179 }
180
181 /*
182 * Static device mappings. These peripheral registers are mapped at
183 * fixed virtual addresses very early in initarm() so that we can use
184 * them while booting the kernel, and stay at the same address
185 * throughout whole kernel's life time.
186 *
187 * We use this table twice; once with bootstrap page table, and once
188 * with kernel's page table which we build up in initarm().
189 *
190 * Since we map these registers into the bootstrap page table using
191 * pmap_devmap_bootstrap() which calls pmap_map_chunk(), we map
192 * registers segment-aligned and segment-rounded in order to avoid
193 * using the 2nd page tables.
194 */
195
196 #define _A(a) ((a) & ~L1_S_OFFSET)
197 #define _S(s) (((s) + L1_S_SIZE - 1) & ~(L1_S_SIZE-1))
198
199 static const struct pmap_devmap devmap[] = {
200 {
201 /* Internal registers */
202 .pd_va = _A(MARVELL_INTERREGS_VBASE),
203 .pd_pa = _A(MARVELL_INTERREGS_PBASE),
204 .pd_size = _S(MARVELL_INTERREGS_SIZE),
205 .pd_prot = VM_PROT_READ|VM_PROT_WRITE,
206 .pd_cache = PTE_NOCACHE
207 },
208 {0, 0, 0, 0, 0}
209 };
210
211 #undef _A
212 #undef _S
213
214 static inline
215 pd_entry_t *
216 read_ttb(void)
217 {
218 long ttb;
219
220 __asm volatile("mrc p15, 0, %0, c2, c0, 0" : "=r" (ttb));
221
222 return (pd_entry_t *)(ttb & ~((1<<14)-1));
223 }
224
225 static int
226 axp_pcie_free_win(void)
227 {
228 int i;
229 /* Find first disabled window */
230 for (i = 0; i < ARMADAXP_MLMB_NWINDOW; i++) {
231 if ((read_mlmbreg(MVSOC_MLMB_WCR(i)) &
232 MVSOC_MLMB_WCR_WINEN) == 0) {
233 return i;
234 }
235 }
236 /* If there is no free window, return erroneous value */
237 return (-1);
238 }
239
240 static void
241 reset_axp_pcie_win(void)
242 {
243 uint32_t target, attr;
244 int memtag = 0, iotag = 0, window, i;
245 uint32_t membase;
246 uint32_t iobase;
247 uint32_t tags[] = { ARMADAXP_TAG_PEX00_MEM, ARMADAXP_TAG_PEX00_IO,
248 ARMADAXP_TAG_PEX01_MEM, ARMADAXP_TAG_PEX01_IO,
249 ARMADAXP_TAG_PEX02_MEM, ARMADAXP_TAG_PEX02_IO,
250 ARMADAXP_TAG_PEX03_MEM, ARMADAXP_TAG_PEX03_IO,
251 ARMADAXP_TAG_PEX2_MEM, ARMADAXP_TAG_PEX2_IO,
252 ARMADAXP_TAG_PEX3_MEM, ARMADAXP_TAG_PEX3_IO};
253
254 nwindow = ARMADAXP_MLMB_NWINDOW;
255 nremap = ARMADAXP_MLMB_NREMAP;
256 membase = MARVELL_PEXMEM_PBASE;
257 iobase = MARVELL_PEXIO_PBASE;
258 for (i = 0; i < __arraycount(tags) / 2; i++) {
259 memtag = tags[2 * i];
260 iotag = tags[(2 * i) + 1];
261
262 /* Reset PCI-Express space to window register. */
263 window = mvsoc_target(memtag, &target, &attr, NULL, NULL);
264
265 /* Find free window if we've got spurious one */
266 if (window >= nwindow) {
267 window = axp_pcie_free_win();
268 /* Just break if there is no free windows left */
269 if (window < 0) {
270 aprint_error(": no free windows for PEX MEM\n");
271 break;
272 }
273 }
274 write_mlmbreg(MVSOC_MLMB_WCR(window),
275 MVSOC_MLMB_WCR_WINEN |
276 MVSOC_MLMB_WCR_TARGET(target) |
277 MVSOC_MLMB_WCR_ATTR(attr) |
278 MVSOC_MLMB_WCR_SIZE(MARVELL_PEXMEM_SIZE));
279 write_mlmbreg(MVSOC_MLMB_WBR(window),
280 membase & MVSOC_MLMB_WBR_BASE_MASK);
281 #ifdef PCI_NETBSD_CONFIGURE
282 if (window < nremap) {
283 write_mlmbreg(MVSOC_MLMB_WRLR(window),
284 membase & MVSOC_MLMB_WRLR_REMAP_MASK);
285 write_mlmbreg(MVSOC_MLMB_WRHR(window), 0);
286 }
287 #endif
288 window = mvsoc_target(iotag, &target, &attr, NULL, NULL);
289
290 /* Find free window if we've got spurious one */
291 if (window >= nwindow) {
292 window = axp_pcie_free_win();
293 /* Just break if there is no free windows left */
294 if (window < 0) {
295 aprint_error(": no free windows for PEX I/O\n");
296 break;
297 }
298 }
299 write_mlmbreg(MVSOC_MLMB_WCR(window),
300 MVSOC_MLMB_WCR_WINEN |
301 MVSOC_MLMB_WCR_TARGET(target) |
302 MVSOC_MLMB_WCR_ATTR(attr) |
303 MVSOC_MLMB_WCR_SIZE(MARVELL_PEXIO_SIZE));
304 write_mlmbreg(MVSOC_MLMB_WBR(window),
305 iobase & MVSOC_MLMB_WBR_BASE_MASK);
306 #ifdef PCI_NETBSD_CONFIGURE
307 if (window < nremap) {
308 write_mlmbreg(MVSOC_MLMB_WRLR(window),
309 iobase & MVSOC_MLMB_WRLR_REMAP_MASK);
310 write_mlmbreg(MVSOC_MLMB_WRHR(window), 0);
311 }
312 #endif
313 membase += MARVELL_PEXMEM_SIZE;
314 iobase += MARVELL_PEXIO_SIZE;
315 }
316 }
317
318 /*
319 * u_int initarm(...)
320 *
321 * Initial entry point on startup. This gets called before main() is
322 * entered.
323 * It should be responsible for setting up everything that must be
324 * in place when main is called.
325 * This includes
326 * Taking a copy of the boot configuration structure.
327 * Initialising the physical console so characters can be printed.
328 * Setting up page tables for the kernel
329 * Relocating the kernel to the bottom of physical memory
330 */
331 u_int
332 initarm(void *arg)
333 {
334 cpu_reset_address = axp_system_reset;
335
336 mvsoc_bootstrap(MARVELL_INTERREGS_VBASE);
337
338 /* Set CPU functions */
339 if (set_cpufuncs())
340 panic("cpu not recognized!");
341
342 /*
343 * Map devices into the initial page table
344 * in order to use early console during initialization process.
345 * consinit is going to use this mapping.
346 */
347 pmap_devmap_bootstrap((vaddr_t)read_ttb(), devmap);
348
349 /* Initialize system console */
350 consinit();
351
352 /* Reset PCI-Express space to window register. */
353 reset_axp_pcie_win();
354
355 /* Get CPU, system and timebase frequencies */
356 extern vaddr_t misc_base;
357 misc_base = MARVELL_INTERREGS_VBASE + ARMADAXP_MISC_BASE;
358 armadaxp_getclks();
359 mvsoc_clkgating = armadaxp_clkgating;
360
361 /* Preconfigure interrupts */
362 armadaxp_intr_bootstrap(MARVELL_INTERREGS_PBASE);
363
364 #ifdef L2CACHE_ENABLE
365 /* Initialize L2 Cache */
366 (void)armadaxp_l2_init(MARVELL_INTERREGS_PBASE);
367 #endif
368
369 #ifdef AURORA_IO_CACHE_COHERENCY
370 /* Initialize cache coherency */
371 armadaxp_io_coherency_init();
372 #endif
373
374 #ifdef KGDB
375 kgdb_port_init();
376 #endif
377
378 #ifdef VERBOSE_INIT_ARM
379 /* Talk to the user */
380 #define BDSTR(s) _BDSTR(s)
381 #define _BDSTR(s) #s
382 printf("\nNetBSD/evbarm (" BDSTR(EVBARM_BOARDTYPE) ") booting ...\n");
383 #endif
384
385
386 #ifdef VERBOSE_INIT_ARM
387 printf("initarm: Configuring system ...\n");
388 #endif
389 /* Fake bootconfig structure for the benefit of pmap.c. */
390 bootconfig.dramblocks = 1;
391 bootconfig.dram[0].address = MEMSTART;
392 bootconfig.dram[0].pages = MEMSIZE / PAGE_SIZE;
393
394 physical_start = bootconfig.dram[0].address;
395 physical_end = physical_start + (bootconfig.dram[0].pages * PAGE_SIZE);
396
397 arm32_bootmem_init(0, physical_end, (uintptr_t) KERNEL_BASE_phys);
398 arm32_kernel_vm_init(KERNEL_VM_BASE, ARM_VECTORS_LOW, 0,
399 devmap, false);
400
401 /* we've a specific device_register routine */
402 evbarm_device_register = axp_device_register;
403
404 return initarm_common(KERNEL_VM_BASE, KERNEL_VM_SIZE, NULL, 0);
405 }
406
407 #ifndef CONSADDR
408 #error Specify the address of the UART with the CONSADDR option.
409 #endif
410 #ifndef CONSPEED
411 #define CONSPEED B115200
412 #endif
413 #ifndef CONMODE
414 #define CONMODE ((TTYDEF_CFLAG & ~(CSIZE | CSTOPB | PARENB)) | CS8) /* 8N1 */
415 #endif
416 #ifndef CONSFREQ
417 #define CONSFREQ 0
418 #endif
419 static const int comcnspeed = CONSPEED;
420 static const int comcnfreq = CONSFREQ;
421 static const tcflag_t comcnmode = CONMODE;
422 static const bus_addr_t comcnaddr = (bus_addr_t)CONSADDR;
423
424 void
425 consinit(void)
426 {
427 static bool consinit_called = false;
428
429 if (consinit_called)
430 return;
431 consinit_called = true;
432
433 #if NCOM > 0
434 extern int mvuart_cnattach(bus_space_tag_t, bus_addr_t, int,
435 uint32_t, int);
436
437 if (mvuart_cnattach(&mvsoc_bs_tag, comcnaddr, comcnspeed,
438 comcnfreq ? comcnfreq : mvTclk , comcnmode))
439 panic("Serial console can not be initialized.");
440 #endif
441 }
442
443 #ifdef KGDB
444 #ifndef KGDB_DEVADDR
445 #error Specify the address of the kgdb UART with the KGDB_DEVADDR option.
446 #endif
447 #ifndef KGDB_DEVRATE
448 #define KGDB_DEVRATE B115200
449 #endif
450 #define MVUART_SIZE 0x20
451
452 #ifndef KGDB_DEVMODE
453 #define KGDB_DEVMODE ((TTYDEF_CFLAG & ~(CSIZE | CSTOPB | PARENB)) | CS8) /* 8N1 */
454 #endif
455 static const vaddr_t comkgdbaddr = KGDB_DEVADDR;
456 static const int comkgdbspeed = KGDB_DEVRATE;
457 static const int comkgdbmode = KGDB_DEVMODE;
458
459 void
460 static kgdb_port_init(void)
461 {
462 static int kgdbsinit_called = 0;
463
464 if (kgdbsinit_called != 0)
465 return;
466 kgdbsinit_called = 1;
467
468 if (com_kgdb_attach(&mvsoc_bs_tag, comkgdbaddr, comkgdbspeed,
469 MVUART_SIZE, COM_TYPE_16550_NOERS, comkgdbmode))
470 panic("KGDB uart can not be initialized.");
471 }
472 #endif
473
474 #if NMVPEX > 0
475 static void
476 marvell_startend_by_tag(int tag, uint64_t *start, uint64_t *end)
477 {
478
479 uint32_t base, size;
480 int win;
481
482 win = mvsoc_target(tag, NULL, NULL, &base, &size);
483 if (size != 0) {
484 if (win < nremap)
485 *start = read_mlmbreg(MVSOC_MLMB_WRLR(win)) |
486 ((read_mlmbreg(MVSOC_MLMB_WRHR(win)) << 16) << 16);
487 else
488 *start = base;
489 *end = *start + size - 1;
490 } else
491 *start = *end = 0;
492 }
493 #endif
494
495 static void
496 axp_device_register(device_t dev, void *aux)
497 {
498 prop_dictionary_t dict = device_properties(dev);
499
500 #if NCOM > 0
501 if (device_is_a(dev, "com") &&
502 device_is_a(device_parent(dev), "mvsoc"))
503 prop_dictionary_set_uint32(dict, "frequency", mvTclk);
504 #endif
505
506 #if NMVPEX > 0
507 extern struct bus_space
508 armadaxp_pex00_io_bs_tag, armadaxp_pex00_mem_bs_tag,
509 armadaxp_pex01_io_bs_tag, armadaxp_pex01_mem_bs_tag,
510 armadaxp_pex02_io_bs_tag, armadaxp_pex02_mem_bs_tag,
511 armadaxp_pex03_io_bs_tag, armadaxp_pex03_mem_bs_tag,
512 armadaxp_pex2_io_bs_tag, armadaxp_pex2_mem_bs_tag,
513 armadaxp_pex3_io_bs_tag, armadaxp_pex3_mem_bs_tag;
514 extern struct arm32_pci_chipset arm32_mvpex0_chipset,
515 arm32_mvpex1_chipset, arm32_mvpex2_chipset,
516 arm32_mvpex3_chipset, arm32_mvpex4_chipset,
517 arm32_mvpex5_chipset;
518
519 struct marvell_attach_args *mva = aux;
520
521 if (device_is_a(dev, "mvpex")) {
522 struct bus_space *mvpex_io_bs_tag, *mvpex_mem_bs_tag;
523 struct arm32_pci_chipset *arm32_mvpex_chipset;
524 prop_data_t io_bs_tag, mem_bs_tag, pc;
525 uint64_t start, end;
526 int iotag, memtag;
527
528 if (mva->mva_offset == MVSOC_PEX_BASE) {
529 mvpex_io_bs_tag = &armadaxp_pex00_io_bs_tag;
530 mvpex_mem_bs_tag = &armadaxp_pex00_mem_bs_tag;
531 arm32_mvpex_chipset = &arm32_mvpex0_chipset;
532 iotag = ARMADAXP_TAG_PEX00_IO;
533 memtag = ARMADAXP_TAG_PEX00_MEM;
534 } else if (mva->mva_offset == MVSOC_PEX_BASE + 0x4000) {
535 mvpex_io_bs_tag = &armadaxp_pex01_io_bs_tag;
536 mvpex_mem_bs_tag = &armadaxp_pex01_mem_bs_tag;
537 arm32_mvpex_chipset = &arm32_mvpex1_chipset;
538 iotag = ARMADAXP_TAG_PEX01_IO;
539 memtag = ARMADAXP_TAG_PEX01_MEM;
540 } else if (mva->mva_offset == MVSOC_PEX_BASE + 0x8000) {
541 mvpex_io_bs_tag = &armadaxp_pex02_io_bs_tag;
542 mvpex_mem_bs_tag = &armadaxp_pex02_mem_bs_tag;
543 arm32_mvpex_chipset = &arm32_mvpex2_chipset;
544 iotag = ARMADAXP_TAG_PEX02_IO;
545 memtag = ARMADAXP_TAG_PEX02_MEM;
546 } else if (mva->mva_offset == MVSOC_PEX_BASE + 0xc000) {
547 mvpex_io_bs_tag = &armadaxp_pex03_io_bs_tag;
548 mvpex_mem_bs_tag = &armadaxp_pex03_mem_bs_tag;
549 arm32_mvpex_chipset = &arm32_mvpex3_chipset;
550 iotag = ARMADAXP_TAG_PEX03_IO;
551 memtag = ARMADAXP_TAG_PEX03_MEM;
552 } else if (mva->mva_offset == MVSOC_PEX_BASE + 0x2000) {
553 mvpex_io_bs_tag = &armadaxp_pex2_io_bs_tag;
554 mvpex_mem_bs_tag = &armadaxp_pex2_mem_bs_tag;
555 arm32_mvpex_chipset = &arm32_mvpex4_chipset;
556 iotag = ARMADAXP_TAG_PEX2_IO;
557 memtag = ARMADAXP_TAG_PEX2_MEM;
558 } else {
559 mvpex_io_bs_tag = &armadaxp_pex3_io_bs_tag;
560 mvpex_mem_bs_tag = &armadaxp_pex3_mem_bs_tag;
561 arm32_mvpex_chipset = &arm32_mvpex5_chipset;
562 iotag = ARMADAXP_TAG_PEX3_IO;
563 memtag = ARMADAXP_TAG_PEX3_MEM;
564 }
565
566 arm32_mvpex_chipset->pc_conf_v = device_private(dev);
567 arm32_mvpex_chipset->pc_intr_v = device_private(dev);
568
569 io_bs_tag = prop_data_create_data_nocopy(
570 mvpex_io_bs_tag, sizeof(struct bus_space));
571 KASSERT(io_bs_tag != NULL);
572 prop_dictionary_set(dict, "io-bus-tag", io_bs_tag);
573 prop_object_release(io_bs_tag);
574 mem_bs_tag = prop_data_create_data_nocopy(
575 mvpex_mem_bs_tag, sizeof(struct bus_space));
576 KASSERT(mem_bs_tag != NULL);
577 prop_dictionary_set(dict, "mem-bus-tag", mem_bs_tag);
578 prop_object_release(mem_bs_tag);
579
580 pc = prop_data_create_data_nocopy(arm32_mvpex_chipset,
581 sizeof(struct arm32_pci_chipset));
582 KASSERT(pc != NULL);
583 prop_dictionary_set(dict, "pci-chipset", pc);
584 prop_object_release(pc);
585
586 marvell_startend_by_tag(iotag, &start, &end);
587 prop_dictionary_set_uint64(dict, "iostart", start);
588 prop_dictionary_set_uint64(dict, "ioend", end);
589 marvell_startend_by_tag(memtag, &start, &end);
590 prop_dictionary_set_uint64(dict, "memstart", start);
591 prop_dictionary_set_uint64(dict, "memend", end);
592 prop_dictionary_set_uint32(dict,
593 "cache-line-size", arm_dcache_align);
594 }
595 #endif
596 }
597