xref: /freebsd/sys/dev/bhnd/bhnd.h (revision 20f8619da05e2775ef7b381c5df080d621fa8332)
1 /*-
2  * Copyright (c) 2015 Landon Fuller <landon@landonf.org>
3  * All rights reserved.
4  *
5  * Redistribution and use in source and binary forms, with or without
6  * modification, are permitted provided that the following conditions
7  * are met:
8  * 1. Redistributions of source code must retain the above copyright
9  *    notice, this list of conditions and the following disclaimer,
10  *    without modification.
11  * 2. Redistributions in binary form must reproduce at minimum a disclaimer
12  *    similar to the "NO WARRANTY" disclaimer below ("Disclaimer") and any
13  *    redistribution must be conditioned upon including a substantially
14  *    similar Disclaimer requirement for further binary redistribution.
15  *
16  * NO WARRANTY
17  * THIS SOFTWARE IS PROVIDED BY THE COPYRIGHT HOLDERS AND CONTRIBUTORS
18  * ``AS IS'' AND ANY EXPRESS OR IMPLIED WARRANTIES, INCLUDING, BUT NOT
19  * LIMITED TO, THE IMPLIED WARRANTIES OF NONINFRINGEMENT, MERCHANTIBILITY
20  * AND FITNESS FOR A PARTICULAR PURPOSE ARE DISCLAIMED. IN NO EVENT SHALL
21  * THE COPYRIGHT HOLDERS OR CONTRIBUTORS BE LIABLE FOR SPECIAL, EXEMPLARY,
22  * OR CONSEQUENTIAL DAMAGES (INCLUDING, BUT NOT LIMITED TO, PROCUREMENT OF
23  * SUBSTITUTE GOODS OR SERVICES; LOSS OF USE, DATA, OR PROFITS; OR BUSINESS
24  * INTERRUPTION) HOWEVER CAUSED AND ON ANY THEORY OF LIABILITY, WHETHER
25  * IN CONTRACT, STRICT LIABILITY, OR TORT (INCLUDING NEGLIGENCE OR OTHERWISE)
26  * ARISING IN ANY WAY OUT OF THE USE OF THIS SOFTWARE, EVEN IF ADVISED OF
27  * THE POSSIBILITY OF SUCH DAMAGES.
28  *
29  * $FreeBSD$
30  */
31 
32 #ifndef _BHND_BHND_H_
33 #define _BHND_BHND_H_
34 
35 #include <sys/types.h>
36 #include <sys/bus.h>
37 
38 #include <machine/bus.h>
39 
40 #include "bhnd_ids.h"
41 #include "bhnd_types.h"
42 #include "bhnd_bus_if.h"
43 
44 extern devclass_t bhnd_devclass;
45 extern devclass_t bhnd_hostb_devclass;
46 extern devclass_t bhnd_nvram_devclass;
47 
48 /**
49  * bhnd child instance variables
50  */
51 enum bhnd_device_vars {
52 	BHND_IVAR_VENDOR,	/**< Designer's JEP-106 manufacturer ID. */
53 	BHND_IVAR_DEVICE,	/**< Part number */
54 	BHND_IVAR_HWREV,	/**< Core revision */
55 	BHND_IVAR_DEVICE_CLASS,	/**< Core class (@sa bhnd_devclass_t) */
56 	BHND_IVAR_VENDOR_NAME,	/**< Core vendor name */
57 	BHND_IVAR_DEVICE_NAME,	/**< Core name */
58 	BHND_IVAR_CORE_INDEX,	/**< Bus-assigned core number */
59 	BHND_IVAR_CORE_UNIT,	/**< Bus-assigned core unit number,
60 				     assigned sequentially (starting at 0) for
61 				     each vendor/device pair. */
62 };
63 
64 /**
65  * bhnd device probe priority bands.
66  */
67 enum {
68 	BHND_PROBE_ROOT         = 0,    /**< Nexus or host bridge */
69 	BHND_PROBE_BUS		= 1000,	/**< Busses and bridges */
70 	BHND_PROBE_CPU		= 2000,	/**< CPU devices */
71 	BHND_PROBE_INTERRUPT	= 3000,	/**< Interrupt controllers. */
72 	BHND_PROBE_TIMER	= 4000,	/**< Timers and clocks. */
73 	BHND_PROBE_RESOURCE	= 5000,	/**< Resource discovery (including NVRAM/SPROM) */
74 	BHND_PROBE_DEFAULT	= 6000,	/**< Default device priority */
75 };
76 
77 /**
78  * Constants defining fine grained ordering within a BHND_PROBE_* priority band.
79  *
80  * Example:
81  * @code
82  * BHND_PROBE_BUS + BHND_PROBE_ORDER_FIRST
83  * @endcode
84  */
85 enum {
86 	BHND_PROBE_ORDER_FIRST		= 0,
87 	BHND_PROBE_ORDER_EARLY		= 25,
88 	BHND_PROBE_ORDER_MIDDLE		= 50,
89 	BHND_PROBE_ORDER_LATE		= 75,
90 	BHND_PROBE_ORDER_LAST		= 100
91 
92 };
93 
94 /*
95  * Simplified accessors for bhnd device ivars
96  */
97 #define	BHND_ACCESSOR(var, ivar, type) \
98 	__BUS_ACCESSOR(bhnd, var, BHND, ivar, type)
99 
100 BHND_ACCESSOR(vendor,		VENDOR,		uint16_t);
101 BHND_ACCESSOR(device,		DEVICE,		uint16_t);
102 BHND_ACCESSOR(hwrev,		HWREV,		uint8_t);
103 BHND_ACCESSOR(class,		DEVICE_CLASS,	bhnd_devclass_t);
104 BHND_ACCESSOR(vendor_name,	VENDOR_NAME,	const char *);
105 BHND_ACCESSOR(device_name,	DEVICE_NAME,	const char *);
106 BHND_ACCESSOR(core_index,	CORE_INDEX,	u_int);
107 BHND_ACCESSOR(core_unit,	CORE_UNIT,	int);
108 
109 #undef	BHND_ACCESSOR
110 
111 /**
112  * Chip Identification
113  *
114  * This is read from the ChipCommon ID register; on earlier bhnd(4) devices
115  * where ChipCommon is unavailable, known values must be supplied.
116  */
117 struct bhnd_chipid {
118 	uint16_t	chip_id;	/**< chip id (BHND_CHIPID_*) */
119 	uint8_t		chip_rev;	/**< chip revision */
120 	uint8_t		chip_pkg;	/**< chip package (BHND_PKGID_*) */
121 	uint8_t		chip_type;	/**< chip type (BHND_CHIPTYPE_*) */
122 
123 	bhnd_addr_t	enum_addr;	/**< chip_type-specific enumeration
124 					  *  address; either the siba(4) base
125 					  *  core register block, or the bcma(4)
126 					  *  EROM core address. */
127 
128 	uint8_t		ncores;		/**< number of cores, if known. 0 if
129 					  *  not available. */
130 };
131 
132 /**
133 * A bhnd(4) bus resource.
134 *
135 * This provides an abstract interface to per-core resources that may require
136 * bus-level remapping of address windows prior to access.
137 */
138 struct bhnd_resource {
139 	struct resource	*res;		/**< the system resource. */
140 	bool		 direct;	/**< false if the resource requires
141 					 *   bus window remapping before it
142 					 *   is MMIO accessible. */
143 };
144 
145 /**
146  * A bhnd(4) core descriptor.
147  */
148 struct bhnd_core_info {
149 	uint16_t	vendor;		/**< vendor */
150 	uint16_t	device;		/**< device */
151 	uint16_t	hwrev;		/**< hardware revision */
152 	u_int		core_idx;	/**< bus-assigned core index */
153 	int		unit;		/**< bus-assigned core unit */
154 };
155 
156 
157 /**
158  * A hardware revision match descriptor.
159  */
160 struct bhnd_hwrev_match {
161 	uint16_t	start;	/**< first revision, or BHND_HWREV_INVALID
162 					     to match on any revision. */
163 	uint16_t	end;	/**< last revision, or BHND_HWREV_INVALID
164 					     to match on any revision. */
165 };
166 
167 /**
168  * Wildcard hardware revision match descriptor.
169  */
170 #define	BHND_HWREV_ANY		{ BHND_HWREV_INVALID, BHND_HWREV_INVALID }
171 #define	BHND_HWREV_IS_ANY(_m)	\
172 	((_m)->start == BHND_HWREV_INVALID && (_m)->end == BHND_HWREV_INVALID)
173 
174 /**
175  * Hardware revision match descriptor for an inclusive range.
176  *
177  * @param _start The first applicable hardware revision.
178  * @param _end The last applicable hardware revision, or BHND_HWREV_INVALID
179  * to match on any revision.
180  */
181 #define	BHND_HWREV_RANGE(_start, _end)	{ _start, _end }
182 
183 /**
184  * Hardware revision match descriptor for a single revision.
185  *
186  * @param _hwrev The hardware revision to match on.
187  */
188 #define	BHND_HWREV_EQ(_hwrev)	BHND_HWREV_RANGE(_hwrev, _hwrev)
189 
190 /**
191  * Hardware revision match descriptor for any revision equal to or greater
192  * than @p _start.
193  *
194  * @param _start The first hardware revision to match on.
195  */
196 #define	BHND_HWREV_GTE(_start)	BHND_HWREV_RANGE(_start, BHND_HWREV_INVALID)
197 
198 /**
199  * Hardware revision match descriptor for any revision equal to or less
200  * than @p _end.
201  *
202  * @param _end The last hardware revision to match on.
203  */
204 #define	BHND_HWREV_LTE(_end)	BHND_HWREV_RANGE(0, _end)
205 
206 
207 /** A core match descriptor. */
208 struct bhnd_core_match {
209 	uint16_t		vendor;	/**< required JEP106 device vendor or BHND_MFGID_INVALID. */
210 	uint16_t		device;	/**< required core ID or BHND_COREID_INVALID */
211 	struct bhnd_hwrev_match	hwrev;	/**< matching revisions. */
212 	bhnd_devclass_t		class;	/**< required class or BHND_DEVCLASS_INVALID */
213 	int			unit;	/**< required core unit, or -1 */
214 };
215 
216 /**
217  * Core match descriptor matching against the given @p _vendor, @p _device,
218  * and @p _hwrev match descriptors.
219  */
220 #define	BHND_CORE_MATCH(_vendor, _device, _hwrev)	\
221 	{ _vendor, _device, _hwrev, BHND_DEVCLASS_INVALID, -1 }
222 
223 /**
224  * Wildcard core match descriptor.
225  */
226 #define	BHND_CORE_MATCH_ANY			\
227 	{					\
228 		.vendor = BHND_MFGID_INVALID,	\
229 		.device = BHND_COREID_INVALID,	\
230 		.hwrev = BHND_HWREV_ANY,	\
231 		.class = BHND_DEVCLASS_INVALID,	\
232 		.unit = -1			\
233 	}
234 
235 /** A chipset match descriptor. */
236 struct bhnd_chip_match {
237 	/** Select fields to be matched */
238 	uint8_t
239 		match_id:1,
240 		match_rev:1,
241 		match_pkg:1,
242 		match_flags_unused:5;
243 
244 	uint16_t		chip_id;	/**< required chip id */
245 	struct bhnd_hwrev_match	chip_rev;	/**< matching chip revisions */
246 	uint8_t			chip_pkg;	/**< required package */
247 };
248 
249 #define	BHND_CHIP_MATCH_ANY		\
250 	{ .match_id = 0, .match_rev = 0, .match_pkg = 0 }
251 
252 #define	BHND_CHIP_MATCH_IS_ANY(_m)	\
253 	((_m)->match_id == 0 && (_m)->match_rev == 0 && (_m)->match_pkg == 0)
254 
255 /** Set the required chip ID within a bhnd_chip_match instance */
256 #define	BHND_CHIP_ID(_cid)		\
257 	.match_id = 1, .chip_id = BHND_CHIPID_BCM ## _cid
258 
259 /** Set the required revision range within a bhnd_chip_match instance */
260 #define	BHND_CHIP_REV(_rev)		\
261 	.match_rev = 1, .chip_rev = BHND_ ## _rev
262 
263 /** Set the required package ID within a bhnd_chip_match instance */
264 #define	BHND_CHIP_PKG(_pkg)		\
265 	.match_pkg = 1, .chip_pkg = BHND_PKGID_BCM ## _pkg
266 
267 /** Set the required chip and package ID within a bhnd_chip_match instance */
268 #define	BHND_CHIP_IP(_cid, _pkg)	\
269 	BHND_CHIP_ID(_cid), BHND_CHIP_PKG(_pkg)
270 
271 /** Set the required chip ID, package ID, and revision within a bhnd_chip_match
272  *  instance */
273 #define	BHND_CHIP_IPR(_cid, _pkg, _rev)	\
274 	BHND_CHIP_ID(_cid), BHND_CHIP_PKG(_pkg), BHND_CHIP_REV(_rev)
275 
276 /** Set the required chip ID and revision within a bhnd_chip_match
277  *  instance */
278 #define	BHND_CHIP_IR(_cid, _rev)	\
279 	BHND_CHIP_ID(_cid), BHND_CHIP_REV(_rev)
280 
281 /**
282  * Chipset quirk table descriptor.
283  */
284 struct bhnd_chip_quirk {
285 	const struct bhnd_chip_match	 chip;		/**< chip match descriptor */
286 	uint32_t			 quirks;	/**< quirk flags */
287 };
288 
289 #define	BHND_CHIP_QUIRK_END	{ BHND_CHIP_MATCH_ANY, 0 }
290 
291 #define	BHND_CHIP_QUIRK_IS_END(_q)	\
292 	(BHND_CHIP_MATCH_IS_ANY(&(_q)->chip) && (_q)->quirks == 0)
293 
294 /**
295  * Device quirk table descriptor.
296  */
297 struct bhnd_device_quirk {
298 	struct bhnd_hwrev_match	 hwrev;		/**< applicable hardware revisions */
299 	uint32_t		 quirks;	/**< quirk flags */
300 };
301 #define	BHND_DEVICE_QUIRK_END		{ BHND_HWREV_ANY, 0 }
302 #define	BHND_DEVICE_QUIRK_IS_END(_q)	\
303 	(BHND_HWREV_IS_ANY(&(_q)->hwrev) && (_q)->quirks == 0)
304 
305 enum {
306 	BHND_DF_ANY	= 0,
307 	BHND_DF_HOSTB	= (1<<0)	/**< core is serving as the bus'
308 					  *  host bridge */
309 };
310 
311 /** Device probe table descriptor */
312 struct bhnd_device {
313 	const struct bhnd_core_match	 core;			/**< core match descriptor */
314 	const char			*desc;			/**< device description, or NULL. */
315 	const struct bhnd_device_quirk	*quirks_table;		/**< quirks table for this device, or NULL */
316 	uint32_t			 device_flags;		/**< required BHND_DF_* flags */
317 };
318 
319 #define	_BHND_DEVICE(_device, _desc, _quirks, _flags, ...)	\
320 	{ BHND_CORE_MATCH(BHND_MFGID_BCM, BHND_COREID_ ## _device, \
321 	    BHND_HWREV_ANY), _desc, _quirks, _flags }
322 
323 #define	BHND_DEVICE(_device, _desc, _quirks, ...)	\
324 	_BHND_DEVICE(_device, _desc, _quirks, ## __VA_ARGS__, 0)
325 
326 #define	BHND_DEVICE_END			{ BHND_CORE_MATCH_ANY, NULL, NULL, 0 }
327 
328 const char			*bhnd_vendor_name(uint16_t vendor);
329 const char			*bhnd_port_type_name(bhnd_port_type port_type);
330 
331 const char 			*bhnd_find_core_name(uint16_t vendor,
332 				     uint16_t device);
333 bhnd_devclass_t			 bhnd_find_core_class(uint16_t vendor,
334 				     uint16_t device);
335 
336 const char			*bhnd_core_name(const struct bhnd_core_info *ci);
337 bhnd_devclass_t			 bhnd_core_class(const struct bhnd_core_info *ci);
338 
339 
340 device_t			 bhnd_match_child(device_t dev,
341 				     const struct bhnd_core_match *desc);
342 
343 device_t			 bhnd_find_child(device_t dev,
344 				     bhnd_devclass_t class, int unit);
345 
346 const struct bhnd_core_info	*bhnd_match_core(
347 				     const struct bhnd_core_info *cores,
348 				     u_int num_cores,
349 				     const struct bhnd_core_match *desc);
350 
351 const struct bhnd_core_info	*bhnd_find_core(
352 				     const struct bhnd_core_info *cores,
353 				     u_int num_cores, bhnd_devclass_t class);
354 
355 bool				 bhnd_core_matches(
356 				     const struct bhnd_core_info *core,
357 				     const struct bhnd_core_match *desc);
358 
359 bool				 bhnd_chip_matches(
360 				     const struct bhnd_chipid *chipid,
361 				     const struct bhnd_chip_match *desc);
362 
363 bool				 bhnd_hwrev_matches(uint16_t hwrev,
364 				     const struct bhnd_hwrev_match *desc);
365 
366 uint32_t			 bhnd_chip_quirks(device_t dev,
367 				     const struct bhnd_chip_quirk *table);
368 
369 bool				 bhnd_device_matches(device_t dev,
370 				     const struct bhnd_core_match *desc);
371 
372 const struct bhnd_device	*bhnd_device_lookup(device_t dev,
373 				     const struct bhnd_device *table,
374 				     size_t entry_size);
375 
376 uint32_t			 bhnd_device_quirks(device_t dev,
377 				     const struct bhnd_device *table,
378 				     size_t entry_size);
379 
380 struct bhnd_core_info		 bhnd_get_core_info(device_t dev);
381 
382 
383 int				 bhnd_alloc_resources(device_t dev,
384 				     struct resource_spec *rs,
385 				     struct bhnd_resource **res);
386 
387 void				 bhnd_release_resources(device_t dev,
388 				     const struct resource_spec *rs,
389 				     struct bhnd_resource **res);
390 
391 struct bhnd_chipid		 bhnd_parse_chipid(uint32_t idreg,
392 				     bhnd_addr_t enum_addr);
393 
394 int				 bhnd_read_chipid(device_t dev,
395 				     struct resource_spec *rs,
396 				     bus_size_t chipc_offset,
397 				     struct bhnd_chipid *result);
398 
399 void				 bhnd_set_custom_core_desc(device_t dev,
400 				     const char *name);
401 void				 bhnd_set_default_core_desc(device_t dev);
402 
403 
404 bool				 bhnd_bus_generic_is_hw_disabled(device_t dev,
405 				     device_t child);
406 bool				 bhnd_bus_generic_is_region_valid(device_t dev,
407 				     device_t child, bhnd_port_type type,
408 				     u_int port, u_int region);
409 int				 bhnd_bus_generic_read_nvram_var(device_t dev,
410 				     device_t child, const char *name,
411 				     void *buf, size_t *size);
412 const struct bhnd_chipid	*bhnd_bus_generic_get_chipid(device_t dev,
413 				     device_t child);
414 struct bhnd_resource		*bhnd_bus_generic_alloc_resource (device_t dev,
415 				     device_t child, int type, int *rid,
416 				     rman_res_t start, rman_res_t end,
417 				     rman_res_t count, u_int flags);
418 int				 bhnd_bus_generic_release_resource (device_t dev,
419 				     device_t child, int type, int rid,
420 				     struct bhnd_resource *r);
421 int				 bhnd_bus_generic_activate_resource (device_t dev,
422 				     device_t child, int type, int rid,
423 				     struct bhnd_resource *r);
424 int				 bhnd_bus_generic_deactivate_resource (device_t dev,
425 				     device_t child, int type, int rid,
426 				     struct bhnd_resource *r);
427 
428 
429 
430 /**
431  * Return the active host bridge core for the bhnd bus, if any, or NULL if
432  * not found.
433  *
434  * @param dev A bhnd bus device.
435  */
436 static inline device_t
437 bhnd_find_hostb_device(device_t dev) {
438 	return (BHND_BUS_FIND_HOSTB_DEVICE(dev));
439 }
440 
441 /**
442  * Return true if the hardware components required by @p dev are known to be
443  * unpopulated or otherwise unusable.
444  *
445  * In some cases, enumerated devices may have pins that are left floating, or
446  * the hardware may otherwise be non-functional; this method allows a parent
447  * device to explicitly specify if a successfully enumerated @p dev should
448  * be disabled.
449  *
450  * @param dev A bhnd bus child device.
451  */
452 static inline bool
453 bhnd_is_hw_disabled(device_t dev) {
454 	return (BHND_BUS_IS_HW_DISABLED(device_get_parent(dev), dev));
455 }
456 
457 /**
458  * Return the BHND chip identification info for the bhnd bus.
459  *
460  * @param dev A bhnd bus child device.
461  */
462 static inline const struct bhnd_chipid *
463 bhnd_get_chipid(device_t dev) {
464 	return (BHND_BUS_GET_CHIPID(device_get_parent(dev), dev));
465 };
466 
467 /**
468  * Determine an NVRAM variable's expected size.
469  *
470  * @param 	dev	A bhnd bus child device.
471  * @param	name	The variable name.
472  * @param[out]	len	On success, the variable's size, in bytes.
473  *
474  * @retval 0		success
475  * @retval ENOENT	The requested variable was not found.
476  * @retval non-zero	If reading @p name otherwise fails, a regular unix
477  *			error code will be returned.
478  */
479 static inline int
480 bhnd_nvram_getvarlen(device_t dev, const char *name, size_t *len)
481 {
482 	return (BHND_BUS_GET_NVRAM_VAR(device_get_parent(dev), dev, name, NULL,
483 	    len));
484 }
485 
486 /**
487  * Read an NVRAM variable.
488  *
489  * @param 	dev	A bhnd bus child device.
490  * @param	name	The NVRAM variable name.
491  * @param	buf	A buffer large enough to hold @p len bytes. On success,
492  * 			the requested value will be written to this buffer.
493  * @param	len	The required variable length.
494  *
495  * @retval 0		success
496  * @retval ENOENT	The requested variable was not found.
497  * @retval EINVAL	If @p len does not match the actual variable size.
498  * @retval non-zero	If reading @p name otherwise fails, a regular unix
499  *			error code will be returned.
500  */
501 static inline int
502 bhnd_nvram_getvar(device_t dev, const char *name, void *buf, size_t len)
503 {
504 	size_t	var_len;
505 	int	error;
506 
507 	if ((error = bhnd_nvram_getvarlen(dev, name, &var_len)))
508 		return (error);
509 
510 	if (len != var_len)
511 		return (EINVAL);
512 
513 	return (BHND_BUS_GET_NVRAM_VAR(device_get_parent(dev), dev, name, buf,
514 	    &len));
515 }
516 
517 /**
518  * Allocate a resource from a device's parent bhnd(4) bus.
519  *
520  * @param dev The device requesting resource ownership.
521  * @param type The type of resource to allocate. This may be any type supported
522  * by the standard bus APIs.
523  * @param rid The bus-specific handle identifying the resource being allocated.
524  * @param start The start address of the resource.
525  * @param end The end address of the resource.
526  * @param count The size of the resource.
527  * @param flags The flags for the resource to be allocated. These may be any
528  * values supported by the standard bus APIs.
529  *
530  * To request the resource's default addresses, pass @p start and
531  * @p end values of @c 0 and @c ~0, respectively, and
532  * a @p count of @c 1.
533  *
534  * @retval NULL The resource could not be allocated.
535  * @retval resource The allocated resource.
536  */
537 static inline struct bhnd_resource *
538 bhnd_alloc_resource(device_t dev, int type, int *rid, rman_res_t start,
539     rman_res_t end, rman_res_t count, u_int flags)
540 {
541 	return BHND_BUS_ALLOC_RESOURCE(device_get_parent(dev), dev, type, rid,
542 	    start, end, count, flags);
543 }
544 
545 
546 /**
547  * Allocate a resource from a device's parent bhnd(4) bus, using the
548  * resource's default start, end, and count values.
549  *
550  * @param dev The device requesting resource ownership.
551  * @param type The type of resource to allocate. This may be any type supported
552  * by the standard bus APIs.
553  * @param rid The bus-specific handle identifying the resource being allocated.
554  * @param flags The flags for the resource to be allocated. These may be any
555  * values supported by the standard bus APIs.
556  *
557  * @retval NULL The resource could not be allocated.
558  * @retval resource The allocated resource.
559  */
560 static inline struct bhnd_resource *
561 bhnd_alloc_resource_any(device_t dev, int type, int *rid, u_int flags)
562 {
563 	return bhnd_alloc_resource(dev, type, rid, 0, ~0, 1, flags);
564 }
565 
566 /**
567  * Activate a previously allocated bhnd resource.
568  *
569  * @param dev The device holding ownership of the allocated resource.
570  * @param type The type of the resource.
571  * @param rid The bus-specific handle identifying the resource.
572  * @param r A pointer to the resource returned by bhnd_alloc_resource or
573  * BHND_BUS_ALLOC_RESOURCE.
574  *
575  * @retval 0 success
576  * @retval non-zero an error occurred while activating the resource.
577  */
578 static inline int
579 bhnd_activate_resource(device_t dev, int type, int rid,
580    struct bhnd_resource *r)
581 {
582 	return BHND_BUS_ACTIVATE_RESOURCE(device_get_parent(dev), dev, type,
583 	    rid, r);
584 }
585 
586 /**
587  * Deactivate a previously activated bhnd resource.
588  *
589  * @param dev The device holding ownership of the activated resource.
590  * @param type The type of the resource.
591  * @param rid The bus-specific handle identifying the resource.
592  * @param r A pointer to the resource returned by bhnd_alloc_resource or
593  * BHND_BUS_ALLOC_RESOURCE.
594  *
595  * @retval 0 success
596  * @retval non-zero an error occurred while activating the resource.
597  */
598 static inline int
599 bhnd_deactivate_resource(device_t dev, int type, int rid,
600    struct bhnd_resource *r)
601 {
602 	return BHND_BUS_DEACTIVATE_RESOURCE(device_get_parent(dev), dev, type,
603 	    rid, r);
604 }
605 
606 /**
607  * Free a resource allocated by bhnd_alloc_resource().
608  *
609  * @param dev The device holding ownership of the resource.
610  * @param type The type of the resource.
611  * @param rid The bus-specific handle identifying the resource.
612  * @param r A pointer to the resource returned by bhnd_alloc_resource or
613  * BHND_ALLOC_RESOURCE.
614  *
615  * @retval 0 success
616  * @retval non-zero an error occurred while activating the resource.
617  */
618 static inline int
619 bhnd_release_resource(device_t dev, int type, int rid,
620    struct bhnd_resource *r)
621 {
622 	return BHND_BUS_RELEASE_RESOURCE(device_get_parent(dev), dev, type,
623 	    rid, r);
624 }
625 
626 /**
627  * Return true if @p region_num is a valid region on @p port_num of
628  * @p type attached to @p dev.
629  *
630  * @param dev A bhnd bus child device.
631  * @param type The port type being queried.
632  * @param port_num The port number being queried.
633  * @param region_num The region number being queried.
634  */
635 static inline bool
636 bhnd_is_region_valid(device_t dev, bhnd_port_type type, u_int port_num,
637     u_int region_num)
638 {
639 	return (BHND_BUS_IS_REGION_VALID(device_get_parent(dev), dev, type,
640 	    port_num, region_num));
641 }
642 
643 /**
644  * Return the number of ports of type @p type attached to @p def.
645  *
646  * @param dev A bhnd bus child device.
647  * @param type The port type being queried.
648  */
649 static inline u_int
650 bhnd_get_port_count(device_t dev, bhnd_port_type type) {
651 	return (BHND_BUS_GET_PORT_COUNT(device_get_parent(dev), dev, type));
652 }
653 
654 /**
655  * Return the number of memory regions mapped to @p child @p port of
656  * type @p type.
657  *
658  * @param dev A bhnd bus child device.
659  * @param port The port number being queried.
660  * @param type The port type being queried.
661  */
662 static inline u_int
663 bhnd_get_region_count(device_t dev, bhnd_port_type type, u_int port) {
664 	return (BHND_BUS_GET_REGION_COUNT(device_get_parent(dev), dev, type,
665 	    port));
666 }
667 
668 /**
669  * Return the resource-ID for a memory region on the given device port.
670  *
671  * @param dev A bhnd bus child device.
672  * @param type The port type.
673  * @param port The port identifier.
674  * @param region The identifier of the memory region on @p port.
675  *
676  * @retval int The RID for the given @p port and @p region on @p device.
677  * @retval -1 No such port/region found.
678  */
679 static inline int
680 bhnd_get_port_rid(device_t dev, bhnd_port_type type, u_int port, u_int region)
681 {
682 	return BHND_BUS_GET_PORT_RID(device_get_parent(dev), dev, type, port,
683 	    region);
684 }
685 
686 /**
687  * Decode a port / region pair on @p dev defined by @p rid.
688  *
689  * @param dev A bhnd bus child device.
690  * @param type The resource type.
691  * @param rid The resource identifier.
692  * @param[out] port_type The decoded port type.
693  * @param[out] port The decoded port identifier.
694  * @param[out] region The decoded region identifier.
695  *
696  * @retval 0 success
697  * @retval non-zero No matching port/region found.
698  */
699 static inline int
700 bhnd_decode_port_rid(device_t dev, int type, int rid, bhnd_port_type *port_type,
701     u_int *port, u_int *region)
702 {
703 	return BHND_BUS_DECODE_PORT_RID(device_get_parent(dev), dev, type, rid,
704 	    port_type, port, region);
705 }
706 
707 /**
708  * Get the address and size of @p region on @p port.
709  *
710  * @param dev A bhnd bus child device.
711  * @param port_type The port type.
712  * @param port The port identifier.
713  * @param region The identifier of the memory region on @p port.
714  * @param[out] region_addr The region's base address.
715  * @param[out] region_size The region's size.
716  *
717  * @retval 0 success
718  * @retval non-zero No matching port/region found.
719  */
720 static inline int
721 bhnd_get_region_addr(device_t dev, bhnd_port_type port_type, u_int port,
722     u_int region, bhnd_addr_t *region_addr, bhnd_size_t *region_size)
723 {
724 	return BHND_BUS_GET_REGION_ADDR(device_get_parent(dev), dev, port_type,
725 	    port, region, region_addr, region_size);
726 }
727 
728 /*
729  * bhnd bus-level equivalents of the bus_(read|write|set|barrier|...)
730  * macros (compatible with bhnd_resource).
731  *
732  * Generated with bhnd/tools/bus_macro.sh
733  */
734 #define bhnd_bus_barrier(r, o, l, f) \
735     ((r)->direct) ? \
736 	bus_barrier((r)->res, (o), (l), (f)) : \
737 	BHND_BUS_BARRIER( \
738 	    device_get_parent(rman_get_device((r)->res)),	\
739 	    rman_get_device((r)->res), (r), (o), (l), (f))
740 #define bhnd_bus_read_1(r, o) \
741     ((r)->direct) ? \
742 	bus_read_1((r)->res, (o)) : \
743 	BHND_BUS_READ_1( \
744 	    device_get_parent(rman_get_device((r)->res)),	\
745 	    rman_get_device((r)->res), (r), (o))
746 #define bhnd_bus_read_multi_1(r, o, d, c) \
747     ((r)->direct) ? \
748 	bus_read_multi_1((r)->res, (o), (d), (c)) : \
749 	BHND_BUS_READ_MULTI_1( \
750 	    device_get_parent(rman_get_device((r)->res)),	\
751 	    rman_get_device((r)->res), (r), (o), (d), (c))
752 #define bhnd_bus_write_1(r, o, v) \
753     ((r)->direct) ? \
754 	bus_write_1((r)->res, (o), (v)) : \
755 	BHND_BUS_WRITE_1( \
756 	    device_get_parent(rman_get_device((r)->res)),	\
757 	    rman_get_device((r)->res), (r), (o), (v))
758 #define bhnd_bus_write_multi_1(r, o, d, c) \
759     ((r)->direct) ? \
760 	bus_write_multi_1((r)->res, (o), (d), (c)) : \
761 	BHND_BUS_WRITE_MULTI_1( \
762 	    device_get_parent(rman_get_device((r)->res)),	\
763 	    rman_get_device((r)->res), (r), (o), (d), (c))
764 #define bhnd_bus_read_stream_1(r, o) \
765     ((r)->direct) ? \
766 	bus_read_stream_1((r)->res, (o)) : \
767 	BHND_BUS_READ_STREAM_1( \
768 	    device_get_parent(rman_get_device((r)->res)),	\
769 	    rman_get_device((r)->res), (r), (o))
770 #define bhnd_bus_read_multi_stream_1(r, o, d, c) \
771     ((r)->direct) ? \
772 	bus_read_multi_stream_1((r)->res, (o), (d), (c)) : \
773 	BHND_BUS_READ_MULTI_STREAM_1( \
774 	    device_get_parent(rman_get_device((r)->res)),	\
775 	    rman_get_device((r)->res), (r), (o), (d), (c))
776 #define bhnd_bus_write_stream_1(r, o, v) \
777     ((r)->direct) ? \
778 	bus_write_stream_1((r)->res, (o), (v)) : \
779 	BHND_BUS_WRITE_STREAM_1( \
780 	    device_get_parent(rman_get_device((r)->res)),	\
781 	    rman_get_device((r)->res), (r), (o), (v))
782 #define bhnd_bus_write_multi_stream_1(r, o, d, c) \
783     ((r)->direct) ? \
784 	bus_write_multi_stream_1((r)->res, (o), (d), (c)) : \
785 	BHND_BUS_WRITE_MULTI_STREAM_1( \
786 	    device_get_parent(rman_get_device((r)->res)),	\
787 	    rman_get_device((r)->res), (r), (o), (d), (c))
788 #define bhnd_bus_read_2(r, o) \
789     ((r)->direct) ? \
790 	bus_read_2((r)->res, (o)) : \
791 	BHND_BUS_READ_2( \
792 	    device_get_parent(rman_get_device((r)->res)),	\
793 	    rman_get_device((r)->res), (r), (o))
794 #define bhnd_bus_read_multi_2(r, o, d, c) \
795     ((r)->direct) ? \
796 	bus_read_multi_2((r)->res, (o), (d), (c)) : \
797 	BHND_BUS_READ_MULTI_2( \
798 	    device_get_parent(rman_get_device((r)->res)),	\
799 	    rman_get_device((r)->res), (r), (o), (d), (c))
800 #define bhnd_bus_write_2(r, o, v) \
801     ((r)->direct) ? \
802 	bus_write_2((r)->res, (o), (v)) : \
803 	BHND_BUS_WRITE_2( \
804 	    device_get_parent(rman_get_device((r)->res)),	\
805 	    rman_get_device((r)->res), (r), (o), (v))
806 #define bhnd_bus_write_multi_2(r, o, d, c) \
807     ((r)->direct) ? \
808 	bus_write_multi_2((r)->res, (o), (d), (c)) : \
809 	BHND_BUS_WRITE_MULTI_2( \
810 	    device_get_parent(rman_get_device((r)->res)),	\
811 	    rman_get_device((r)->res), (r), (o), (d), (c))
812 #define bhnd_bus_read_stream_2(r, o) \
813     ((r)->direct) ? \
814 	bus_read_stream_2((r)->res, (o)) : \
815 	BHND_BUS_READ_STREAM_2( \
816 	    device_get_parent(rman_get_device((r)->res)),	\
817 	    rman_get_device((r)->res), (r), (o))
818 #define bhnd_bus_read_multi_stream_2(r, o, d, c) \
819     ((r)->direct) ? \
820 	bus_read_multi_stream_2((r)->res, (o), (d), (c)) : \
821 	BHND_BUS_READ_MULTI_STREAM_2( \
822 	    device_get_parent(rman_get_device((r)->res)),	\
823 	    rman_get_device((r)->res), (r), (o), (d), (c))
824 #define bhnd_bus_write_stream_2(r, o, v) \
825     ((r)->direct) ? \
826 	bus_write_stream_2((r)->res, (o), (v)) : \
827 	BHND_BUS_WRITE_STREAM_2( \
828 	    device_get_parent(rman_get_device((r)->res)),	\
829 	    rman_get_device((r)->res), (r), (o), (v))
830 #define bhnd_bus_write_multi_stream_2(r, o, d, c) \
831     ((r)->direct) ? \
832 	bus_write_multi_stream_2((r)->res, (o), (d), (c)) : \
833 	BHND_BUS_WRITE_MULTI_STREAM_2( \
834 	    device_get_parent(rman_get_device((r)->res)),	\
835 	    rman_get_device((r)->res), (r), (o), (d), (c))
836 #define bhnd_bus_read_4(r, o) \
837     ((r)->direct) ? \
838 	bus_read_4((r)->res, (o)) : \
839 	BHND_BUS_READ_4( \
840 	    device_get_parent(rman_get_device((r)->res)),	\
841 	    rman_get_device((r)->res), (r), (o))
842 #define bhnd_bus_read_multi_4(r, o, d, c) \
843     ((r)->direct) ? \
844 	bus_read_multi_4((r)->res, (o), (d), (c)) : \
845 	BHND_BUS_READ_MULTI_4( \
846 	    device_get_parent(rman_get_device((r)->res)),	\
847 	    rman_get_device((r)->res), (r), (o), (d), (c))
848 #define bhnd_bus_write_4(r, o, v) \
849     ((r)->direct) ? \
850 	bus_write_4((r)->res, (o), (v)) : \
851 	BHND_BUS_WRITE_4( \
852 	    device_get_parent(rman_get_device((r)->res)),	\
853 	    rman_get_device((r)->res), (r), (o), (v))
854 #define bhnd_bus_write_multi_4(r, o, d, c) \
855     ((r)->direct) ? \
856 	bus_write_multi_4((r)->res, (o), (d), (c)) : \
857 	BHND_BUS_WRITE_MULTI_4( \
858 	    device_get_parent(rman_get_device((r)->res)),	\
859 	    rman_get_device((r)->res), (r), (o), (d), (c))
860 #define bhnd_bus_read_stream_4(r, o) \
861     ((r)->direct) ? \
862 	bus_read_stream_4((r)->res, (o)) : \
863 	BHND_BUS_READ_STREAM_4( \
864 	    device_get_parent(rman_get_device((r)->res)),	\
865 	    rman_get_device((r)->res), (r), (o))
866 #define bhnd_bus_read_multi_stream_4(r, o, d, c) \
867     ((r)->direct) ? \
868 	bus_read_multi_stream_4((r)->res, (o), (d), (c)) : \
869 	BHND_BUS_READ_MULTI_STREAM_4( \
870 	    device_get_parent(rman_get_device((r)->res)),	\
871 	    rman_get_device((r)->res), (r), (o), (d), (c))
872 #define bhnd_bus_write_stream_4(r, o, v) \
873     ((r)->direct) ? \
874 	bus_write_stream_4((r)->res, (o), (v)) : \
875 	BHND_BUS_WRITE_STREAM_4( \
876 	    device_get_parent(rman_get_device((r)->res)),	\
877 	    rman_get_device((r)->res), (r), (o), (v))
878 #define bhnd_bus_write_multi_stream_4(r, o, d, c) \
879     ((r)->direct) ? \
880 	bus_write_multi_stream_4((r)->res, (o), (d), (c)) : \
881 	BHND_BUS_WRITE_MULTI_STREAM_4( \
882 	    device_get_parent(rman_get_device((r)->res)),	\
883 	    rman_get_device((r)->res), (r), (o), (d), (c))
884 
885 #endif /* _BHND_BHND_H_ */
886