xref: /illumos-gate/usr/src/uts/sun4u/opl/sys/drmach.h (revision 25cf1a30)
1*25cf1a30Sjl /*
2*25cf1a30Sjl  * CDDL HEADER START
3*25cf1a30Sjl  *
4*25cf1a30Sjl  * The contents of this file are subject to the terms of the
5*25cf1a30Sjl  * Common Development and Distribution License (the "License").
6*25cf1a30Sjl  * You may not use this file except in compliance with the License.
7*25cf1a30Sjl  *
8*25cf1a30Sjl  * You can obtain a copy of the license at usr/src/OPENSOLARIS.LICENSE
9*25cf1a30Sjl  * or http://www.opensolaris.org/os/licensing.
10*25cf1a30Sjl  * See the License for the specific language governing permissions
11*25cf1a30Sjl  * and limitations under the License.
12*25cf1a30Sjl  *
13*25cf1a30Sjl  * When distributing Covered Code, include this CDDL HEADER in each
14*25cf1a30Sjl  * file and include the License file at usr/src/OPENSOLARIS.LICENSE.
15*25cf1a30Sjl  * If applicable, add the following below this CDDL HEADER, with the
16*25cf1a30Sjl  * fields enclosed by brackets "[]" replaced with your own identifying
17*25cf1a30Sjl  * information: Portions Copyright [yyyy] [name of copyright owner]
18*25cf1a30Sjl  *
19*25cf1a30Sjl  * CDDL HEADER END
20*25cf1a30Sjl  */
21*25cf1a30Sjl /*
22*25cf1a30Sjl  * Copyright 2006 Sun Microsystems, Inc.  All rights reserved.
23*25cf1a30Sjl  * Use is subject to license terms.
24*25cf1a30Sjl  */
25*25cf1a30Sjl 
26*25cf1a30Sjl #ifndef _SYS_DRMACH_H_
27*25cf1a30Sjl #define	_SYS_DRMACH_H_
28*25cf1a30Sjl 
29*25cf1a30Sjl #pragma ident	"%Z%%M%	%I%	%E% SMI"
30*25cf1a30Sjl 
31*25cf1a30Sjl #ifdef	__cplusplus
32*25cf1a30Sjl extern "C" {
33*25cf1a30Sjl #endif
34*25cf1a30Sjl 
35*25cf1a30Sjl #ifndef _ASM
36*25cf1a30Sjl #include <sys/types.h>
37*25cf1a30Sjl #include <sys/memlist.h>
38*25cf1a30Sjl #include <sys/processor.h>
39*25cf1a30Sjl #include <sys/cpuvar.h>
40*25cf1a30Sjl #include <sys/sbd_ioctl.h>
41*25cf1a30Sjl #include <sys/sysevent.h>
42*25cf1a30Sjl #include <sys/ddi.h>
43*25cf1a30Sjl #include <sys/sunddi.h>
44*25cf1a30Sjl #include <sys/sunndi.h>
45*25cf1a30Sjl #include <sys/ddi_impldefs.h>
46*25cf1a30Sjl #include <sys/pte.h>
47*25cf1a30Sjl #include <sys/opl.h>
48*25cf1a30Sjl #endif
49*25cf1a30Sjl 
50*25cf1a30Sjl 
51*25cf1a30Sjl #define	MAX_BOARDS		plat_max_boards()
52*25cf1a30Sjl #define	MAX_CPU_UNITS_PER_BOARD	plat_max_cpu_units_per_board()
53*25cf1a30Sjl #define	MAX_MEM_UNITS_PER_BOARD	plat_max_mem_units_per_board()
54*25cf1a30Sjl #define	MAX_IO_UNITS_PER_BOARD	plat_max_io_units_per_board()
55*25cf1a30Sjl #define	MAX_CMP_UNITS_PER_BOARD	plat_max_cmp_units_per_board()
56*25cf1a30Sjl /*
57*25cf1a30Sjl  * DR uses MAX_CORES_PER_CMP as number of virtual CPU within a CMP
58*25cf1a30Sjl  */
59*25cf1a30Sjl #define	MAX_CORES_PER_CMP	OPL_MAX_CPU_PER_CMP
60*25cf1a30Sjl 
61*25cf1a30Sjl 
62*25cf1a30Sjl /* returned with drmach_board_find_devices callback */
63*25cf1a30Sjl #define	DRMACH_DEVTYPE_CPU	"cpu"
64*25cf1a30Sjl #define	DRMACH_DEVTYPE_MEM	"memory"
65*25cf1a30Sjl #define	DRMACH_DEVTYPE_PCI	"pci"
66*25cf1a30Sjl 
67*25cf1a30Sjl #define	FMEM_LOOP_START		1
68*25cf1a30Sjl #define	FMEM_LOOP_COPY_READY	2
69*25cf1a30Sjl #define	FMEM_LOOP_COPY_DONE	3
70*25cf1a30Sjl #define	FMEM_LOOP_FMEM_READY	4
71*25cf1a30Sjl #define	FMEM_LOOP_RENAME_DONE	5
72*25cf1a30Sjl #define	FMEM_LOOP_DONE		6
73*25cf1a30Sjl #define	FMEM_LOOP_EXIT		7
74*25cf1a30Sjl 
75*25cf1a30Sjl #define	FMEM_NO_ERROR		0
76*25cf1a30Sjl #define	FMEM_OBP_FAIL		1
77*25cf1a30Sjl #define	FMEM_XC_TIMEOUT		2
78*25cf1a30Sjl #define	FMEM_COPY_TIMEOUT	3
79*25cf1a30Sjl #define	FMEM_SCF_BUSY		4
80*25cf1a30Sjl #define	FMEM_RETRY_OUT		5
81*25cf1a30Sjl #define	FMEM_TIMEOUT		6
82*25cf1a30Sjl #define	FMEM_HW_ERROR		7
83*25cf1a30Sjl #define	FMEM_TERMINATE		8
84*25cf1a30Sjl #define	FMEM_COPY_ERROR		9
85*25cf1a30Sjl #define	FMEM_SCF_ERR		10
86*25cf1a30Sjl 
87*25cf1a30Sjl #define	SCF_CMD_BUSY		0x8000
88*25cf1a30Sjl #define	SCF_STATUS_READY	0x8000
89*25cf1a30Sjl #define	SCF_STATUS_SHUTDOWN	0x4000
90*25cf1a30Sjl #define	SCF_STATUS_POFF		0x2000
91*25cf1a30Sjl #define	SCF_STATUS_EVENT	0x1000
92*25cf1a30Sjl #define	SCF_STATUS_TIMER_ADJUST	0x0800
93*25cf1a30Sjl #define	SCF_STATUS_ALIVE	0x0400
94*25cf1a30Sjl #define	SCF_STATUS_MODE_CHANGED	0x0200
95*25cf1a30Sjl #define	SCF_STATUS_CMD_U_PARITY	0x0100
96*25cf1a30Sjl #define	SCF_STATUS_CMD_RTN_CODE	0x00f0
97*25cf1a30Sjl #define	SCF_STATUS_MODE_SWITCH	0x000c
98*25cf1a30Sjl #define	SCF_STATUS_CMD_COMPLETE	0x0002
99*25cf1a30Sjl #define	SCF_STATUS_CMD_L_PARITY	0x0001
100*25cf1a30Sjl 
101*25cf1a30Sjl #define	SCF_RETRY_CNT		15
102*25cf1a30Sjl 
103*25cf1a30Sjl #ifndef _ASM
104*25cf1a30Sjl 
105*25cf1a30Sjl /*
106*25cf1a30Sjl  * OPL platform specific routines currently only defined
107*25cf1a30Sjl  * in opl.c and referenced by DR.
108*25cf1a30Sjl  */
109*25cf1a30Sjl 
110*25cf1a30Sjl typedef void *drmachid_t;
111*25cf1a30Sjl 
112*25cf1a30Sjl /*
113*25cf1a30Sjl  *	We have to split up the copy rename data structure
114*25cf1a30Sjl  *	into several pieces:
115*25cf1a30Sjl  *	1. critical region that must be locked in TLB and must
116*25cf1a30Sjl  *	   be physically contiguous/no ecache conflict.
117*25cf1a30Sjl  *	   This region contains the assembly code that handles
118*25cf1a30Sjl  *	   the rename programming, the slave code that loops
119*25cf1a30Sjl  *	   until the master script completes and all data
120*25cf1a30Sjl  *	   required to do the programming.
121*25cf1a30Sjl  *
122*25cf1a30Sjl  *	   It also contains the status of each CPU because the
123*25cf1a30Sjl  *	   master must wait for all the slaves to get ready before
124*25cf1a30Sjl  *	   it can program the SCF.
125*25cf1a30Sjl  *
126*25cf1a30Sjl  *	   We do not need the error code in the critical section.
127*25cf1a30Sjl  *	   It is not set until the FMEM is done.
128*25cf1a30Sjl  *	2. relocatable section that must be locked in TLB.  All data
129*25cf1a30Sjl  *	   referenced in this section must also be locked in TLB to
130*25cf1a30Sjl  *	   avoid tlbmiss.
131*25cf1a30Sjl  *
132*25cf1a30Sjl  *	   We will also put everything else in this section even it
133*25cf1a30Sjl  *	   does not need such protection.
134*25cf1a30Sjl  */
135*25cf1a30Sjl typedef struct {
136*25cf1a30Sjl 	int16_t	scf_command;
137*25cf1a30Sjl 	int8_t	scf_rsv1[2];
138*25cf1a30Sjl 	int16_t	scf_status;
139*25cf1a30Sjl 	int8_t	scf_rsv2[2];
140*25cf1a30Sjl 	int8_t	scf_version;
141*25cf1a30Sjl 	int8_t	scf_rsv3[3];
142*25cf1a30Sjl 	int8_t	scf_rsv4[4];
143*25cf1a30Sjl 	uint8_t	scf_tdata[16];
144*25cf1a30Sjl 	uint8_t	scf_rdata[16];
145*25cf1a30Sjl } drmach_scf_regs_t;
146*25cf1a30Sjl 
147*25cf1a30Sjl 
148*25cf1a30Sjl 
149*25cf1a30Sjl typedef struct {
150*25cf1a30Sjl 	volatile uint_t	stat;
151*25cf1a30Sjl 	volatile uint_t	error;
152*25cf1a30Sjl 	int	op;
153*25cf1a30Sjl #define	OPL_FMEM_SCF_START 	0x1
154*25cf1a30Sjl #define	OPL_FMEM_MC_SUSPEND	0x2
155*25cf1a30Sjl } drmach_fmem_mbox_t;
156*25cf1a30Sjl 
157*25cf1a30Sjl typedef struct {
158*25cf1a30Sjl 	uint64_t		scf_reg_base;
159*25cf1a30Sjl 	uint8_t			scf_td[16];
160*25cf1a30Sjl 	uint64_t		save_log[8];
161*25cf1a30Sjl 	uint64_t		save_local[8];
162*25cf1a30Sjl 	uint64_t		pstate;
163*25cf1a30Sjl 	uint64_t		delay;
164*25cf1a30Sjl 	int			(*run)(void *arg, int cpuid);
165*25cf1a30Sjl 	int			(*fmem)(void *arg, size_t sz);
166*25cf1a30Sjl 	int			(*loop)(void *arg1, size_t sz, void *arg2);
167*25cf1a30Sjl 	void			(*loop_rtn)(void *arg);
168*25cf1a30Sjl 	uint64_t		inst_loop_ret;
169*25cf1a30Sjl 	int			fmem_issued;
170*25cf1a30Sjl 	volatile uchar_t 	stat[NCPU];
171*25cf1a30Sjl } drmach_copy_rename_critical_t;
172*25cf1a30Sjl 
173*25cf1a30Sjl typedef struct {
174*25cf1a30Sjl 	uint64_t		s_copybasepa;
175*25cf1a30Sjl 	uint64_t		t_copybasepa;
176*25cf1a30Sjl 	drmachid_t		s_mem;
177*25cf1a30Sjl 	drmachid_t		t_mem;
178*25cf1a30Sjl 	cpuset_t		cpu_ready_set;
179*25cf1a30Sjl 	cpuset_t		cpu_slave_set;
180*25cf1a30Sjl 	cpuset_t		cpu_copy_set;
181*25cf1a30Sjl 	processorid_t		cpuid;
182*25cf1a30Sjl 	drmach_fmem_mbox_t	fmem_status;
183*25cf1a30Sjl 	volatile uchar_t 	error[NCPU];
184*25cf1a30Sjl 	struct memlist		*c_ml;
185*25cf1a30Sjl 	struct memlist		*cpu_ml[NCPU];
186*25cf1a30Sjl 	caddr_t			locked_va;
187*25cf1a30Sjl 	tte_t			locked_tte;
188*25cf1a30Sjl 	void			(*mc_resume)(void);
189*25cf1a30Sjl 	int			(*scf_fmem_end)(void);
190*25cf1a30Sjl 	int			(*scf_fmem_cancel)(void);
191*25cf1a30Sjl 	uint64_t		copy_delay;
192*25cf1a30Sjl 	uint64_t		stick_freq;
193*25cf1a30Sjl 	uint64_t		copy_wait_time;
194*25cf1a30Sjl 	processorid_t		slowest_cpuid;
195*25cf1a30Sjl } drmach_copy_rename_data_t;
196*25cf1a30Sjl 
197*25cf1a30Sjl typedef struct {
198*25cf1a30Sjl 	uint64_t	nbytes[NCPU];
199*25cf1a30Sjl } drmach_cr_stat_t;
200*25cf1a30Sjl 
201*25cf1a30Sjl typedef struct {
202*25cf1a30Sjl 	drmach_copy_rename_critical_t	*critical;
203*25cf1a30Sjl 	drmach_copy_rename_data_t	*data;
204*25cf1a30Sjl 	caddr_t				memlist_buffer;
205*25cf1a30Sjl 	struct memlist			*free_mlist;
206*25cf1a30Sjl 	drmach_cr_stat_t		*stat;
207*25cf1a30Sjl } drmach_copy_rename_program_t;
208*25cf1a30Sjl 
209*25cf1a30Sjl #define	DRMACH_FMEM_LOCKED_PAGES	4
210*25cf1a30Sjl #define	DRMACH_FMEM_DATA_PAGE		0
211*25cf1a30Sjl #define	DRMACH_FMEM_CRITICAL_PAGE	1
212*25cf1a30Sjl #define	DRMACH_FMEM_MLIST_PAGE		2
213*25cf1a30Sjl #define	DRMACH_FMEM_STAT_PAGE		3
214*25cf1a30Sjl 
215*25cf1a30Sjl /*
216*25cf1a30Sjl  * layout of the FMEM buffers:
217*25cf1a30Sjl  * 1st 8k page
218*25cf1a30Sjl  * +--------------------------------+
219*25cf1a30Sjl  * |drmach_copy_rename_program_t    |
220*25cf1a30Sjl  * +--------------------------------+
221*25cf1a30Sjl  * |drmach_copy_rename_data_t       |
222*25cf1a30Sjl  * |                                |
223*25cf1a30Sjl  * +--------------------------------+
224*25cf1a30Sjl  *
225*25cf1a30Sjl  * 2nd 8k page
226*25cf1a30Sjl  * +--------------------------------+
227*25cf1a30Sjl  * |drmach_copy_rename_critical_t   |
228*25cf1a30Sjl  * |                                |
229*25cf1a30Sjl  * +--------------------------------+
230*25cf1a30Sjl  * |run (drmach_copy_rename_prog__relocatable)
231*25cf1a30Sjl  * |(roundup boundary to 1K)        |
232*25cf1a30Sjl  * +--------------------------------+
233*25cf1a30Sjl  * | fmem_script                    |
234*25cf1a30Sjl  * |(roundup boundary to 1K)        |
235*25cf1a30Sjl  * +--------------------------------+
236*25cf1a30Sjl  * |loop_script                     |
237*25cf1a30Sjl  * |                                |
238*25cf1a30Sjl  * +--------------------------------+
239*25cf1a30Sjl  * |at least 1K NOP/0's             |
240*25cf1a30Sjl  * |                                |
241*25cf1a30Sjl  * +--------------------------------+
242*25cf1a30Sjl  *
243*25cf1a30Sjl  * 3rd 8k page
244*25cf1a30Sjl  * +--------------------------------+
245*25cf1a30Sjl  * |memlist_buffer (free_mlist)     |
246*25cf1a30Sjl  * |                                |
247*25cf1a30Sjl  * +--------------------------------+
248*25cf1a30Sjl  *
249*25cf1a30Sjl  * 4th 8k page - drmach_cr_stat_t.
250*25cf1a30Sjl  *
251*25cf1a30Sjl  */
252*25cf1a30Sjl 
253*25cf1a30Sjl typedef struct {
254*25cf1a30Sjl 	boolean_t	assigned;
255*25cf1a30Sjl 	boolean_t	powered;
256*25cf1a30Sjl 	boolean_t	configured;
257*25cf1a30Sjl 	boolean_t	busy;
258*25cf1a30Sjl 	boolean_t	empty;
259*25cf1a30Sjl 	sbd_cond_t	cond;
260*25cf1a30Sjl 	char		type[MAXNAMELEN];
261*25cf1a30Sjl 	char		info[MAXPATHLEN];	/* TODO: what size? */
262*25cf1a30Sjl } drmach_status_t;
263*25cf1a30Sjl 
264*25cf1a30Sjl typedef struct {
265*25cf1a30Sjl 	int	size;
266*25cf1a30Sjl 	char	*copts;
267*25cf1a30Sjl } drmach_opts_t;
268*25cf1a30Sjl 
269*25cf1a30Sjl typedef struct {
270*25cf1a30Sjl 	uint64_t mi_basepa;
271*25cf1a30Sjl 	uint64_t mi_size;
272*25cf1a30Sjl 	uint64_t mi_slice_size;
273*25cf1a30Sjl 	uint64_t mi_alignment_mask;
274*25cf1a30Sjl } drmach_mem_info_t;
275*25cf1a30Sjl 
276*25cf1a30Sjl extern sbd_error_t	*drmach_mem_get_info(drmachid_t, drmach_mem_info_t *);
277*25cf1a30Sjl extern int		drmach_board_is_floating(drmachid_t);
278*25cf1a30Sjl 
279*25cf1a30Sjl extern sbd_error_t	*drmach_copy_rename_init(
280*25cf1a30Sjl 				drmachid_t dst_id,
281*25cf1a30Sjl 				drmachid_t src_id, struct memlist *src_copy_ml,
282*25cf1a30Sjl 				drmachid_t *pgm_id);
283*25cf1a30Sjl extern sbd_error_t	*drmach_copy_rename_fini(drmachid_t id);
284*25cf1a30Sjl extern void		 drmach_copy_rename(drmachid_t id);
285*25cf1a30Sjl 
286*25cf1a30Sjl extern sbd_error_t	*drmach_pre_op(int cmd, drmachid_t id,
287*25cf1a30Sjl 						drmach_opts_t *opts);
288*25cf1a30Sjl extern sbd_error_t	*drmach_post_op(int cmd, drmachid_t id,
289*25cf1a30Sjl 						drmach_opts_t *opts);
290*25cf1a30Sjl 
291*25cf1a30Sjl extern sbd_error_t	*drmach_board_assign(int bnum, drmachid_t *id);
292*25cf1a30Sjl extern sbd_error_t	*drmach_board_connect(drmachid_t id,
293*25cf1a30Sjl 						drmach_opts_t *opts);
294*25cf1a30Sjl extern sbd_error_t	*drmach_board_deprobe(drmachid_t id);
295*25cf1a30Sjl extern sbd_error_t	*drmach_board_disconnect(drmachid_t id,
296*25cf1a30Sjl 						drmach_opts_t *opts);
297*25cf1a30Sjl extern sbd_error_t	*drmach_board_find_devices(drmachid_t id, void *a,
298*25cf1a30Sjl 		sbd_error_t *(*found)(void *a, const char *, int, drmachid_t));
299*25cf1a30Sjl extern int		drmach_board_lookup(int bnum, drmachid_t *id);
300*25cf1a30Sjl extern sbd_error_t	*drmach_passthru(drmachid_t id,
301*25cf1a30Sjl 						drmach_opts_t *opts);
302*25cf1a30Sjl 
303*25cf1a30Sjl extern sbd_error_t	*drmach_board_name(int bnum, char *buf, int buflen);
304*25cf1a30Sjl 
305*25cf1a30Sjl extern sbd_error_t	*drmach_board_poweroff(drmachid_t id);
306*25cf1a30Sjl extern sbd_error_t	*drmach_board_poweron(drmachid_t id);
307*25cf1a30Sjl extern sbd_error_t	*drmach_board_test(drmachid_t id, drmach_opts_t *opts,
308*25cf1a30Sjl 				int force);
309*25cf1a30Sjl 
310*25cf1a30Sjl extern sbd_error_t	*drmach_board_unassign(drmachid_t id);
311*25cf1a30Sjl 
312*25cf1a30Sjl extern sbd_error_t	*drmach_configure(drmachid_t id, int flags);
313*25cf1a30Sjl 
314*25cf1a30Sjl extern sbd_error_t	*drmach_cpu_disconnect(drmachid_t id);
315*25cf1a30Sjl extern sbd_error_t	*drmach_cpu_get_id(drmachid_t id, processorid_t *cpuid);
316*25cf1a30Sjl extern sbd_error_t	*drmach_cpu_get_impl(drmachid_t id, int *ip);
317*25cf1a30Sjl extern void		 drmach_cpu_flush_ecache_sync(void);
318*25cf1a30Sjl 
319*25cf1a30Sjl extern sbd_error_t	*drmach_get_dip(drmachid_t id, dev_info_t **dip);
320*25cf1a30Sjl 
321*25cf1a30Sjl extern sbd_error_t	*drmach_io_is_attached(drmachid_t id, int *yes);
322*25cf1a30Sjl extern sbd_error_t	*drmach_io_post_attach(drmachid_t id);
323*25cf1a30Sjl extern sbd_error_t	*drmach_io_post_release(drmachid_t id);
324*25cf1a30Sjl extern sbd_error_t	*drmach_io_pre_release(drmachid_t id);
325*25cf1a30Sjl extern sbd_error_t	*drmach_io_unrelease(drmachid_t id);
326*25cf1a30Sjl 
327*25cf1a30Sjl extern sbd_error_t	*drmach_mem_add_span(drmachid_t id,
328*25cf1a30Sjl 				uint64_t basepa, uint64_t size);
329*25cf1a30Sjl extern sbd_error_t	*drmach_mem_del_span(drmachid_t id,
330*25cf1a30Sjl 				uint64_t basepa, uint64_t size);
331*25cf1a30Sjl extern sbd_error_t	*drmach_mem_disable(drmachid_t id);
332*25cf1a30Sjl extern sbd_error_t	*drmach_mem_enable(drmachid_t id);
333*25cf1a30Sjl extern sbd_error_t	*drmach_mem_get_base_physaddr(drmachid_t id,
334*25cf1a30Sjl 				uint64_t *pa);
335*25cf1a30Sjl extern sbd_error_t	*drmach_mem_get_memlist(drmachid_t id,
336*25cf1a30Sjl 				struct memlist **ml);
337*25cf1a30Sjl extern sbd_error_t	*drmach_mem_get_slice_size(drmachid_t, uint64_t *);
338*25cf1a30Sjl 
339*25cf1a30Sjl extern sbd_error_t	*drmach_release(drmachid_t id);
340*25cf1a30Sjl extern sbd_error_t	*drmach_status(drmachid_t id, drmach_status_t *stat);
341*25cf1a30Sjl extern sbd_error_t	*drmach_unconfigure(drmachid_t id, int flags);
342*25cf1a30Sjl extern int		drmach_log_sysevent(int board, char *hint, int flag,
343*25cf1a30Sjl 					    int verbose);
344*25cf1a30Sjl 
345*25cf1a30Sjl extern int		drmach_verify_sr(dev_info_t *dip, int sflag);
346*25cf1a30Sjl extern void		drmach_suspend_last();
347*25cf1a30Sjl extern void		drmach_resume_first();
348*25cf1a30Sjl 
349*25cf1a30Sjl #endif
350*25cf1a30Sjl 
351*25cf1a30Sjl #ifdef __cplusplus
352*25cf1a30Sjl }
353*25cf1a30Sjl #endif
354*25cf1a30Sjl 
355*25cf1a30Sjl #endif /* _SYS_DRMACH_H_ */
356