xref: /netbsd-src/sys/arch/sandpoint/sandpoint/mainbus.c (revision e5fbc36ada28f9b9a5836ecffaf4a06aa1ebb687)
1 /*	$NetBSD: mainbus.c,v 1.35 2023/12/20 15:29:07 thorpej Exp $	*/
2 
3 /*
4  * Copyright (c) 1996 Christopher G. Demetriou.  All rights reserved.
5  *
6  * Redistribution and use in source and binary forms, with or without
7  * modification, are permitted provided that the following conditions
8  * are met:
9  * 1. Redistributions of source code must retain the above copyright
10  *    notice, this list of conditions and the following disclaimer.
11  * 2. Redistributions in binary form must reproduce the above copyright
12  *    notice, this list of conditions and the following disclaimer in the
13  *    documentation and/or other materials provided with the distribution.
14  * 3. All advertising materials mentioning features or use of this software
15  *    must display the following acknowledgement:
16  *      This product includes software developed by Christopher G. Demetriou
17  *	for the NetBSD Project.
18  * 4. The name of the author may not be used to endorse or promote products
19  *    derived from this software without specific prior written permission
20  *
21  * THIS SOFTWARE IS PROVIDED BY THE AUTHOR ``AS IS'' AND ANY EXPRESS OR
22  * IMPLIED WARRANTIES, INCLUDING, BUT NOT LIMITED TO, THE IMPLIED WARRANTIES
23  * OF MERCHANTABILITY AND FITNESS FOR A PARTICULAR PURPOSE ARE DISCLAIMED.
24  * IN NO EVENT SHALL THE AUTHOR BE LIABLE FOR ANY DIRECT, INDIRECT,
25  * INCIDENTAL, SPECIAL, EXEMPLARY, OR CONSEQUENTIAL DAMAGES (INCLUDING, BUT
26  * NOT LIMITED TO, PROCUREMENT OF SUBSTITUTE GOODS OR SERVICES; LOSS OF USE,
27  * DATA, OR PROFITS; OR BUSINESS INTERRUPTION) HOWEVER CAUSED AND ON ANY
28  * THEORY OF LIABILITY, WHETHER IN CONTRACT, STRICT LIABILITY, OR TORT
29  * (INCLUDING NEGLIGENCE OR OTHERWISE) ARISING IN ANY WAY OUT OF THE USE OF
30  * THIS SOFTWARE, EVEN IF ADVISED OF THE POSSIBILITY OF SUCH DAMAGE.
31  */
32 
33 #include <sys/cdefs.h>
34 __KERNEL_RCSID(0, "$NetBSD: mainbus.c,v 1.35 2023/12/20 15:29:07 thorpej Exp $");
35 
36 #include "opt_pci.h"
37 #include "pci.h"
38 
39 #include <sys/param.h>
40 #include <sys/device.h>
41 #include <sys/systm.h>
42 
43 #include <machine/autoconf.h>
44 #include <machine/bootinfo.h>
45 #include <machine/isa_machdep.h>
46 
47 #include <powerpc/oea/spr.h>
48 
49 #include <dev/pci/pcivar.h>
50 #include <dev/pci/pciconf.h>
51 
52 int	mainbus_match(device_t, cfdata_t, void *);
53 void	mainbus_attach(device_t, device_t, void *);
54 int	mainbus_print(void *, const char *);
55 
56 CFATTACH_DECL_NEW(mainbus, 0,
57     mainbus_match, mainbus_attach, NULL, NULL);
58 
59 struct powerpc_isa_chipset genppc_ict;
60 
61 #define	PCI_IO_START	0x00001000
62 #define	PCI_IO_END	0x0000ffff
63 #define	PCI_IO_SIZE	((PCI_IO_END - PCI_IO_START) + 1)
64 
65 #define	PCI_MEM_START	0x80000000U
66 #define	PCI_MEM_END	0x8fffffffU
67 #define	PCI_MEM_SIZE	((PCI_MEM_END - PCI_MEM_START) + 1)
68 
69 /*
70  * Probe for the mainbus; always succeeds.
71  */
72 int
mainbus_match(device_t parent,cfdata_t match,void * aux)73 mainbus_match(device_t parent, cfdata_t match, void *aux)
74 {
75 
76 	return 1;
77 }
78 
79 /*
80  * Attach the mainbus.
81  */
82 void
mainbus_attach(device_t parent,device_t self,void * aux)83 mainbus_attach(device_t parent, device_t self, void *aux)
84 {
85 	struct mainbus_attach_args mba;
86 	struct pcibus_attach_args pba;
87 	struct btinfo_prodfamily *pfam;
88 
89 	aprint_naive("\n");
90 	aprint_normal("\n");
91 
92 	mba.ma_name = "cpu";
93 	config_found(self, &mba, mainbus_print,
94 	    CFARGS(.iattr = "mainbus"));
95 
96 	mba.ma_name = "eumb";
97 	mba.ma_bst = &sandpoint_eumb_space_tag;
98 	config_found(self, &mba, mainbus_print,
99 	    CFARGS(.iattr = "mainbus"));
100 
101 	pfam = lookup_bootinfo(BTINFO_PRODFAMILY);
102 	if (pfam != NULL && strcmp(pfam->name, "nhnas") == 0) {
103 		/* attach nhpow(4) for NH230/231 only */
104 		mba.ma_name = "nhpow";
105 		mba.ma_bst = &sandpoint_nhgpio_space_tag;
106 		config_found(self, &mba, mainbus_print,
107 		    CFARGS(.iattr = "mainbus"));
108 	}
109 
110 	mba.ma_name = "cfi";
111 	mba.ma_bst = &sandpoint_flash_space_tag;
112 	config_found(self, &mba, mainbus_print,
113 	    CFARGS(.iattr = "mainbus"));
114 
115 	/*
116 	 * XXX Note also that the presence of a PCI bus should
117 	 * XXX _always_ be checked, and if present the bus should be
118 	 * XXX 'found'.  However, because of the structure of the code,
119 	 * XXX that's not currently possible.
120 	 */
121 #if NPCI > 0
122 #if defined(PCI_NETBSD_CONFIGURE)
123 	struct pciconf_resources *pcires = pciconf_resource_init();
124 
125 	pciconf_resource_add(pcires, PCICONF_RESOURCE_IO,
126 	    PCI_IO_START, PCI_IO_SIZE);
127 	pciconf_resource_add(pcires, PCICONF_RESOURCE_MEM,
128 	    PCI_MEM_START, PCI_MEM_SIZE);
129 
130 	pci_configure_bus(0, pcires, 0, 32);
131 
132 	pciconf_resource_fini(pcires);
133 #endif
134 
135 	pba.pba_iot = &sandpoint_io_space_tag;
136 	pba.pba_memt = &sandpoint_mem_space_tag;
137 	pba.pba_dmat = &pci_bus_dma_tag;
138 	pba.pba_dmat64 = NULL;
139 	pba.pba_bus = 0;
140 	pba.pba_pc = 0;
141 	pba.pba_bridgetag = NULL;
142 	pba.pba_flags = PCI_FLAGS_IO_OKAY | PCI_FLAGS_MEM_OKAY;
143 
144 	config_found(self, &pba, pcibusprint,
145 	    CFARGS(.iattr = "pcibus"));
146 #endif
147 }
148 
149 static int	cpu_match(device_t, cfdata_t, void *);
150 static void	cpu_attach(device_t, device_t, void *);
151 
152 CFATTACH_DECL_NEW(cpu, 0, cpu_match, cpu_attach, NULL, NULL);
153 
154 extern struct cfdriver cpu_cd;
155 
156 int
cpu_match(device_t parent,cfdata_t cf,void * aux)157 cpu_match(device_t parent, cfdata_t cf, void *aux)
158 {
159 	struct mainbus_attach_args *mba = aux;
160 
161 	if (strcmp(mba->ma_name, cpu_cd.cd_name) != 0)
162 		return 0;
163 
164 	if (cpu_info[0].ci_dev != NULL)
165 		return 0;
166 
167 	return 1;
168 }
169 
170 void
cpu_attach(device_t parent,device_t self,void * aux)171 cpu_attach(device_t parent, device_t self, void *aux)
172 {
173 	static uint8_t mem_to_cpuclk[] = {
174 		25, 30, 45, 20, 20, 00, 10, 30,
175 		30, 20, 45, 30, 25, 35, 30, 35,
176 		20, 25, 20, 30, 35, 40, 40, 20,
177 		30, 25, 40, 30, 30, 25, 35, 00
178 	};
179 	extern u_long ticks_per_sec;
180 	struct cpu_info *ci;
181 	u_int hid1, vers;
182 
183 	ci = cpu_attach_common(self, 0);
184 	if (ci == NULL)
185 		return;
186 
187 	vers = (mfpvr() >> 16) & 0xffff;
188 	if (ci->ci_khz == 0 && vers == MPC8245) {
189 		/* calculate speed from bus clock and PLL ratio */
190 		asm volatile ("mfspr %0,1009" : "=r"(hid1));
191 		ci->ci_khz = ((uint64_t)ticks_per_sec * 4 *
192 		    mem_to_cpuclk[hid1 >> 27] + 10) / 10000;
193 		aprint_normal_dev(self, "%u.%02u MHz\n",
194 		    ci->ci_khz / 1000, (ci->ci_khz / 10) % 100);
195 	}
196 }
197 
198 int
mainbus_print(void * aux,const char * pnp)199 mainbus_print(void *aux, const char *pnp)
200 {
201 	struct mainbus_attach_args *mba = aux;
202 
203 	if (pnp)
204 		aprint_normal("%s at %s", mba->ma_name, pnp);
205 	return UNCONF;
206 }
207