xref: /illumos-gate/usr/src/uts/common/sys/pshot.h (revision dd72704bd9e794056c558153663c739e2012d721)
1 /*
2  * CDDL HEADER START
3  *
4  * The contents of this file are subject to the terms of the
5  * Common Development and Distribution License, Version 1.0 only
6  * (the "License").  You may not use this file except in compliance
7  * with the License.
8  *
9  * You can obtain a copy of the license at usr/src/OPENSOLARIS.LICENSE
10  * or http://www.opensolaris.org/os/licensing.
11  * See the License for the specific language governing permissions
12  * and limitations under the License.
13  *
14  * When distributing Covered Code, include this CDDL HEADER in each
15  * file and include the License file at usr/src/OPENSOLARIS.LICENSE.
16  * If applicable, add the following below this CDDL HEADER, with the
17  * fields enclosed by brackets "[]" replaced with your own identifying
18  * information: Portions Copyright [yyyy] [name of copyright owner]
19  *
20  * CDDL HEADER END
21  */
22 /*
23  * Copyright 2005 Sun Microsystems, Inc.  All rights reserved.
24  * Use is subject to license terms.
25  */
26 
27 #ifndef	_SYS_PSHOT_H
28 #define	_SYS_PSHOT_H
29 
30 #ifdef	__cplusplus
31 extern "C" {
32 #endif
33 
34 #include <sys/sunndi.h>
35 
36 /*
37  * user accessable features
38  */
39 
40 /* determines max pshot_minor allocation per softstate */
41 #define	PSHOT_MAX_MINOR_PERINST		2
42 #define	PSHOT_MAX_MINOR_NAMELEN		16
43 
44 #define	PSHOT_NODENAME_DEVCTL		"devctl"
45 #define	PSHOT_NODENAME_TESTCTL		"testctl"
46 
47 #define	PSHOT_PROP_DEVNAME	"dev-name"
48 #define	PSHOT_PROP_DEVNT	"dev-nt"
49 #define	PSHOT_PROP_DEVCOMPAT	"dev-compat"
50 
51 
52 #ifdef	_KERNEL
53 
54 
55 #define	PARENT_IS_PSHOT(self)	\
56 	(ddi_driver_major(self) == ddi_driver_major(ddi_get_parent(self)))
57 
58 
59 static int pshot_debug = 0;
60 static int pshot_event_test_enable = 0;
61 
62 #ifdef DEBUG
63 #define	pshot_debug pshot_debug_on
64 #define	pshot_event_test_enable pshot_event_test_on
65 
66 static int pshot_debug_on = 0;
67 static int pshot_event_test_on = 0;
68 
69 #endif
70 
71 #define	PSHOT_MAX_CBCACHE	6
72 #define	PSHOT_MAX_TSTCACHE	8
73 
74 /*
75  * soft state and minor node management
76  * (includes user features above)
77  */
78 
79 /*
80  * a "node number" is currently implemented as an index into a pshot_minor_t
81  * array, therefore the max must be less than PSHOT_MAX_MINOR_PERINST and
82  * ideally, the minor array should be fully populated, with a node number
83  * defined for each index
84  */
85 #define	PSHOT_NODENUM_DEVCTL		0
86 #define	PSHOT_NODENUM_TESTCTL		1
87 #define	PSHOT_MAX_NODENUM		PSHOT_NODENUM_TESTCTL
88 
89 typedef struct pshot_minor pshot_minor_t;
90 typedef struct pshot pshot_t;
91 
92 struct pshot_minor {
93 	pshot_t		*pshot;
94 	minor_t		minor;
95 	char		name[PSHOT_MAX_MINOR_NAMELEN];
96 };
97 
98 struct pshot {
99 	kmutex_t	lock;
100 	uint_t		state;
101 	dev_info_t	*dip;
102 	int		instance;
103 	ndi_event_hdl_t	ndi_event_hdl;
104 	ndi_event_set_t	ndi_events;
105 	ddi_iblock_cookie_t	iblock_cookie;
106 	ddi_callback_id_t 	callback_cache[PSHOT_MAX_CBCACHE];
107 	ddi_callback_id_t	test_callback_cache[PSHOT_MAX_TSTCACHE];
108 
109 	pshot_minor_t	nodes[PSHOT_MAX_MINOR_PERINST];
110 	int	level;		/* pm power level */
111 	int	busy;		/* pm busy state */
112 	int	busy_ioctl;	/* track busy and idle ioctl calls */
113 };
114 
115 
116 static size_t pshot_numbits(size_t);
117 static minor_t pshot_minor_encode(int, minor_t);
118 static int pshot_minor_decode_inst(minor_t);
119 static minor_t pshot_minor_decode_nodenum(minor_t);
120 
121 #define	PSHOT_NODENUM_BITS()	pshot_numbits(PSHOT_MAX_MINOR_PERINST)
122 
123 /*
124  * children device configuration
125  */
126 
127 typedef struct pshot_device {
128 	char *name;
129 	char *nodetype;
130 	char *compat;
131 } pshot_device_t;
132 
133 #define	PSHOT_DEV_ANYNT		0x1
134 
135 static char *pshot_str2nt(char *);
136 static pshot_device_t *pshot_devices_from_props(dev_info_t *, size_t *, int);
137 static void pshot_devices_free(pshot_device_t *, size_t);
138 static int pshot_devices_setup(dev_info_t *);
139 static int pshot_devices_grow(pshot_device_t **, size_t,
140     const pshot_device_t *, size_t);
141 
142 
143 /*
144  * softstate state bits
145  */
146 #define	IS_OPEN				0x0001
147 #define	IS_OPEN_EXCL			0x0002
148 #define	DEV_RESET_PENDING		0x0004
149 #define	BUS_RESET_PENDING		0x0008
150 #define	POWER_FLAG			0x0010
151 #define	FAIL_SUSPEND_FLAG		0x0020
152 #define	STRICT_PARENT			0x0040
153 #define	NO_INVOL_FLAG			0x0080
154 #define	PM_SUPPORTED			0x0100
155 
156 /*
157  * Leaf ops (supports hotplug controls to the device)
158  */
159 static int pshot_open(dev_t *, int, int, cred_t *);
160 static int pshot_close(dev_t, int, int, cred_t *);
161 static int pshot_ioctl(dev_t, int, intptr_t, int, cred_t *, int *);
162 static int pshot_probe(dev_info_t *);
163 static int pshot_attach(dev_info_t *, ddi_attach_cmd_t);
164 static int pshot_detach(dev_info_t *, ddi_detach_cmd_t);
165 static int pshot_info(dev_info_t *, ddi_info_cmd_t,  void *, void **);
166 static int pshot_power(dev_info_t *dip, int cmpt, int level);
167 
168 static int pshot_devctl(pshot_t *, minor_t, int, intptr_t, int, cred_t *,
169     int *);
170 static int pshot_testctl(pshot_t *, minor_t, int, intptr_t, int, cred_t *,
171     int *);
172 
173 /*
174  * Event handling prototype support.
175  */
176 #define	PSHOT_EVENT_NAME_DEV_OFFLINE	"pshot_dev_offline"
177 #define	PSHOT_EVENT_NAME_DEV_RESET	"pshot_dev_reset"
178 #define	PSHOT_EVENT_NAME_BUS_RESET	"pshot_bus_reset"
179 #define	PSHOT_EVENT_NAME_BUS_QUIESCE	"pshot_bus_quiesce"
180 #define	PSHOT_EVENT_NAME_BUS_UNQUIESCE	"pshot_bus_unquiesce"
181 #define	PSHOT_EVENT_NAME_BUS_TEST_POST	"pshot_bus_test_post"
182 #define	PSHOT_EVENT_NAME_DEBUG_SET	"pshot_debug_set"
183 #define	PSHOT_EVENT_NAME_SUB_RESET	"pshot_sub_reset"
184 						/* for hash sanity check */
185 
186 #define	PSHOT_EVENT_TAG_OFFLINE		0
187 #define	PSHOT_EVENT_TAG_DEV_RESET	1
188 #define	PSHOT_EVENT_TAG_BUS_RESET	2
189 #define	PSHOT_EVENT_TAG_BUS_QUIESCE	3
190 #define	PSHOT_EVENT_TAG_BUS_UNQUIESCE	4
191 #define	PSHOT_EVENT_TAG_TEST_POST	5
192 
193 typedef struct pshot_event_callback {
194 	dev_info_t			*dip;
195 	int				(*callback)();
196 	void				*arg;
197 	struct pshot_event_callback	*next;
198 } ps_callback_t;
199 
200 
201 static void pshot_event_cb(dev_info_t *dip, ddi_eventcookie_t cookie,
202 	void *arg, void *bus_impldata);
203 
204 static int pshot_event(pshot_t *pshot, int event_tag, dev_info_t *child,
205 	void *bus_impldata);
206 
207 #ifdef DEBUG
208 static void pshot_event_cb_test(dev_info_t *dip, ddi_eventcookie_t cookie,
209     void *arg, void *bus_impldata);
210 static void pshot_event_test(void *arg);
211 static void pshot_event_test_post_one(void *arg);
212 #endif
213 
214 /* event busops */
215 static int pshot_get_eventcookie(dev_info_t *dip, dev_info_t *rdip,
216     char *name, ddi_eventcookie_t *event_cookiep);
217 static int pshot_add_eventcall(dev_info_t *dip, dev_info_t *rdip,
218     ddi_eventcookie_t eventid, void (*callback)(), void *arg,
219     ddi_callback_id_t *cb_id);
220 static int pshot_remove_eventcall(dev_info_t *dip, ddi_callback_id_t cb_id);
221 static int pshot_post_event(dev_info_t *dip, dev_info_t *rdip,
222     ddi_eventcookie_t eventid, void *impl_data);
223 
224 /* function prototypes */
225 static int pshot_ctl(dev_info_t *dip, dev_info_t *rdip, ddi_ctl_enum_t ctlop,
226     void *arg, void *result);
227 static int pshot_initchild(dev_info_t *, dev_info_t *);
228 static int pshot_uninitchild(dev_info_t *, dev_info_t *);
229 static int pshot_bus_config(dev_info_t *, uint_t,
230 	ddi_bus_config_op_t, void *, dev_info_t **);
231 static int pshot_bus_unconfig(dev_info_t *, uint_t,
232     ddi_bus_config_op_t, void *);
233 static int pshot_bus_config_setup_nexus(dev_info_t *, char *cname, char *caddr);
234 static int pshot_bus_config_setup_leaf(dev_info_t *, char *cname, char *caddr);
235 static int pshot_bus_config_test_specials(dev_info_t *parent,
236 	char *devname, char *cname, char *caddr);
237 static int pshot_bus_introp(dev_info_t *, dev_info_t *, ddi_intr_op_t,
238 	ddi_intr_handle_impl_t *, void *);
239 
240 static void pshot_setup_autoattach(dev_info_t *);
241 static int pshot_bus_power(dev_info_t *dip, void *impl_arg,
242 	    pm_bus_power_op_t op, void *arg, void *result);
243 static void pshot_nexus_properties(dev_info_t *, dev_info_t *, char *, char *);
244 static void pshot_leaf_properties(dev_info_t *, dev_info_t *, char *, char *);
245 
246 
247 #endif /* _KERNEL */
248 
249 
250 #ifdef	__cplusplus
251 }
252 #endif
253 
254 #endif /* _SYS_PSHOT_H */
255