FreeBSD kernel IICBUS device code
iiconf.c
Go to the documentation of this file.
1/*-
2 * SPDX-License-Identifier: BSD-2-Clause-FreeBSD
3 *
4 * Copyright (c) 1998 Nicolas Souchu
5 * All rights reserved.
6 *
7 * Redistribution and use in source and binary forms, with or without
8 * modification, are permitted provided that the following conditions
9 * are met:
10 * 1. Redistributions of source code must retain the above copyright
11 * notice, this list of conditions and the following disclaimer.
12 * 2. Redistributions in binary form must reproduce the above copyright
13 * notice, this list of conditions and the following disclaimer in the
14 * documentation and/or other materials provided with the distribution.
15 *
16 * THIS SOFTWARE IS PROVIDED BY THE AUTHOR AND CONTRIBUTORS ``AS IS'' AND
17 * ANY EXPRESS OR IMPLIED WARRANTIES, INCLUDING, BUT NOT LIMITED TO, THE
18 * IMPLIED WARRANTIES OF MERCHANTABILITY AND FITNESS FOR A PARTICULAR PURPOSE
19 * ARE DISCLAIMED. IN NO EVENT SHALL THE AUTHOR OR CONTRIBUTORS BE LIABLE
20 * FOR ANY DIRECT, INDIRECT, INCIDENTAL, SPECIAL, EXEMPLARY, OR CONSEQUENTIAL
21 * DAMAGES (INCLUDING, BUT NOT LIMITED TO, PROCUREMENT OF SUBSTITUTE GOODS
22 * OR SERVICES; LOSS OF USE, DATA, OR PROFITS; OR BUSINESS INTERRUPTION)
23 * HOWEVER CAUSED AND ON ANY THEORY OF LIABILITY, WHETHER IN CONTRACT, STRICT
24 * LIABILITY, OR TORT (INCLUDING NEGLIGENCE OR OTHERWISE) ARISING IN ANY WAY
25 * OUT OF THE USE OF THIS SOFTWARE, EVEN IF ADVISED OF THE POSSIBILITY OF
26 * SUCH DAMAGE.
27 */
28
29#include <sys/cdefs.h>
30__FBSDID("$FreeBSD$");
31
32#include <sys/param.h>
33#include <sys/systm.h>
34#include <sys/lock.h>
35#include <sys/malloc.h>
36#include <sys/module.h>
37#include <sys/mutex.h>
38#include <sys/bus.h>
39
40#include <dev/iicbus/iiconf.h>
41#include <dev/iicbus/iicbus.h>
42#include "iicbus_if.h"
43
44/*
45 * Encode a system errno value into the IIC_Exxxxx space by setting the
46 * IIC_ERRNO marker bit, so that iic2errno() can turn it back into a plain
47 * system errno value later. This lets controller- and bus-layer code get
48 * important system errno values (such as EINTR/ERESTART) back to the caller.
49 */
50int
51errno2iic(int errno)
52{
53 return ((errno == 0) ? 0 : errno | IIC_ERRNO);
54}
55
56/*
57 * Translate IIC_Exxxxx status values to vaguely-equivelent errno values.
58 */
59int
60iic2errno(int iic_status)
61{
62 switch (iic_status) {
63 case IIC_NOERR: return (0);
64 case IIC_EBUSERR: return (EALREADY);
65 case IIC_ENOACK: return (EIO);
66 case IIC_ETIMEOUT: return (ETIMEDOUT);
67 case IIC_EBUSBSY: return (EWOULDBLOCK);
68 case IIC_ESTATUS: return (EPROTO);
69 case IIC_EUNDERFLOW: return (EIO);
70 case IIC_EOVERFLOW: return (EOVERFLOW);
71 case IIC_ENOTSUPP: return (EOPNOTSUPP);
72 case IIC_ENOADDR: return (EADDRNOTAVAIL);
73 case IIC_ERESOURCE: return (ENOMEM);
74 default:
75 /*
76 * If the high bit is set, that means it's a system errno value
77 * that was encoded into the IIC_Exxxxxx space by setting the
78 * IIC_ERRNO marker bit. If lots of high-order bits are set,
79 * then it's one of the negative pseudo-errors such as ERESTART
80 * and we return it as-is. Otherwise it's a plain "small
81 * positive integer" errno, so just remove the IIC_ERRNO marker
82 * bit. If it's some unknown number without the high bit set,
83 * there isn't much we can do except call it an I/O error.
84 */
85 if ((iic_status & IIC_ERRNO) == 0)
86 return (EIO);
87 if ((iic_status & 0xFFFF0000) != 0)
88 return (iic_status);
89 return (iic_status & ~IIC_ERRNO);
90 }
91}
92
93/*
94 * iicbus_intr()
95 */
96void
97iicbus_intr(device_t bus, int event, char *buf)
98{
99 struct iicbus_softc *sc = (struct iicbus_softc *)device_get_softc(bus);
100
101 /* call owner's intr routine */
102 if (sc->owner)
103 IICBUS_INTR(sc->owner, event, buf);
104
105 return;
106}
107
108static int
109iicbus_poll(struct iicbus_softc *sc, int how)
110{
111 int error;
112
114 switch (how & IIC_INTRWAIT) {
115 case IIC_WAIT | IIC_INTR:
116 error = mtx_sleep(sc, &sc->lock, IICPRI|PCATCH, "iicreq", 0);
117 break;
118
119 case IIC_WAIT | IIC_NOINTR:
120 error = mtx_sleep(sc, &sc->lock, IICPRI, "iicreq", 0);
121 break;
122
123 default:
124 return (IIC_EBUSBSY);
125 }
126
127 return (errno2iic(error));
128}
129
130/*
131 * iicbus_request_bus()
132 *
133 * Allocate the device to perform transfers.
134 *
135 * how : IIC_WAIT or IIC_DONTWAIT
136 */
137int
138iicbus_request_bus(device_t bus, device_t dev, int how)
139{
140 struct iic_reqbus_data reqdata;
141 struct iicbus_softc *sc = (struct iicbus_softc *)device_get_softc(bus);
142 int error = 0;
143
144 IICBUS_LOCK(sc);
145
146 for (;;) {
147 if (sc->owner == NULL)
148 break;
149 if ((how & IIC_RECURSIVE) && sc->owner == dev)
150 break;
151 if ((error = iicbus_poll(sc, how)) != 0)
152 break;
153 }
154
155 if (error == 0) {
156 ++sc->owncount;
157 if (sc->owner == NULL) {
158 sc->owner = dev;
159 /*
160 * Mark the device busy while it owns the bus, to
161 * prevent detaching the device, bus, or hardware
162 * controller, until ownership is relinquished. If the
163 * device is doing IO from its probe method before
164 * attaching, it cannot be busied; mark the bus busy.
165 */
166 if (device_get_state(dev) < DS_ATTACHING)
167 sc->busydev = bus;
168 else
169 sc->busydev = dev;
170 device_busy(sc->busydev);
171 /*
172 * Drop the lock around the call to the bus driver, it
173 * should be allowed to sleep in the IIC_WAIT case.
174 * Drivers might also need to grab locks that would
175 * cause a LOR if our lock is held.
176 */
177 IICBUS_UNLOCK(sc);
178 /* Ask the underlying layers if the request is ok */
179 reqdata.dev = dev;
180 reqdata.bus = bus;
181 reqdata.flags = how | IIC_REQBUS_DEV;
182 error = IICBUS_CALLBACK(device_get_parent(bus),
183 IIC_REQUEST_BUS, (caddr_t)&reqdata);
184 IICBUS_LOCK(sc);
185
186 if (error != 0) {
187 sc->owner = NULL;
188 sc->owncount = 0;
189 wakeup_one(sc);
190 device_unbusy(sc->busydev);
191 }
192 }
193 }
194
195 IICBUS_UNLOCK(sc);
196
197 return (error);
198}
199
200/*
201 * iicbus_release_bus()
202 *
203 * Release the device allocated with iicbus_request_dev()
204 */
205int
206iicbus_release_bus(device_t bus, device_t dev)
207{
208 struct iic_reqbus_data reqdata;
209 struct iicbus_softc *sc = (struct iicbus_softc *)device_get_softc(bus);
210
211 IICBUS_LOCK(sc);
212
213 if (sc->owner != dev) {
214 IICBUS_UNLOCK(sc);
215 return (IIC_EBUSBSY);
216 }
217
218 if (--sc->owncount == 0) {
219 /* Drop the lock while informing the low-level driver. */
220 IICBUS_UNLOCK(sc);
221 reqdata.dev = dev;
222 reqdata.bus = bus;
223 reqdata.flags = IIC_REQBUS_DEV;
224 IICBUS_CALLBACK(device_get_parent(bus), IIC_RELEASE_BUS,
225 (caddr_t)&reqdata);
226 IICBUS_LOCK(sc);
227 sc->owner = NULL;
228 wakeup_one(sc);
229 device_unbusy(sc->busydev);
230 }
231 IICBUS_UNLOCK(sc);
232 return (0);
233}
234
235/*
236 * iicbus_started()
237 *
238 * Test if the iicbus is started by the controller
239 */
240int
241iicbus_started(device_t bus)
242{
243 struct iicbus_softc *sc = (struct iicbus_softc *)device_get_softc(bus);
244
245 return (sc->started);
246}
247
248/*
249 * iicbus_start()
250 *
251 * Send start condition to the slave addressed by 'slave'
252 */
253int
254iicbus_start(device_t bus, u_char slave, int timeout)
255{
256 struct iicbus_softc *sc = (struct iicbus_softc *)device_get_softc(bus);
257 int error = 0;
258
259 if (sc->started)
260 return (IIC_ESTATUS); /* protocol error, bus already started */
261
262 if (!(error = IICBUS_START(device_get_parent(bus), slave, timeout)))
263 sc->started = slave;
264 else
265 sc->started = 0;
266
267 return (error);
268}
269
270/*
271 * iicbus_repeated_start()
272 *
273 * Send start condition to the slave addressed by 'slave'
274 */
275int
276iicbus_repeated_start(device_t bus, u_char slave, int timeout)
277{
278 struct iicbus_softc *sc = (struct iicbus_softc *)device_get_softc(bus);
279 int error = 0;
280
281 if (!sc->started)
282 return (IIC_ESTATUS); /* protocol error, bus not started */
283
284 if (!(error = IICBUS_REPEATED_START(device_get_parent(bus), slave, timeout)))
285 sc->started = slave;
286 else
287 sc->started = 0;
288
289 return (error);
290}
291
292/*
293 * iicbus_stop()
294 *
295 * Send stop condition to the bus
296 */
297int
298iicbus_stop(device_t bus)
299{
300 struct iicbus_softc *sc = (struct iicbus_softc *)device_get_softc(bus);
301 int error = 0;
302
303 if (!sc->started)
304 return (IIC_ESTATUS); /* protocol error, bus not started */
305
306 error = IICBUS_STOP(device_get_parent(bus));
307
308 /* refuse any further access */
309 sc->started = 0;
310
311 return (error);
312}
313
314/*
315 * iicbus_write()
316 *
317 * Write a block of data to the slave previously started by
318 * iicbus_start() call
319 */
320int
321iicbus_write(device_t bus, const char *buf, int len, int *sent, int timeout)
322{
323 struct iicbus_softc *sc = (struct iicbus_softc *)device_get_softc(bus);
324
325 /* a slave must have been started for writing */
326 if (sc->started == 0 || (sc->strict != 0 && (sc->started & LSB) != 0))
327 return (IIC_ESTATUS);
328
329 return (IICBUS_WRITE(device_get_parent(bus), buf, len, sent, timeout));
330}
331
332/*
333 * iicbus_read()
334 *
335 * Read a block of data from the slave previously started by
336 * iicbus_read() call
337 */
338int
339iicbus_read(device_t bus, char *buf, int len, int *read, int last, int delay)
340{
341 struct iicbus_softc *sc = (struct iicbus_softc *)device_get_softc(bus);
342
343 /* a slave must have been started for reading */
344 if (sc->started == 0 || (sc->strict != 0 && (sc->started & LSB) == 0))
345 return (IIC_ESTATUS);
346
347 return (IICBUS_READ(device_get_parent(bus), buf, len, read, last, delay));
348}
349
350/*
351 * iicbus_write_byte()
352 *
353 * Write a byte to the slave previously started by iicbus_start() call
354 */
355int
356iicbus_write_byte(device_t bus, char byte, int timeout)
357{
358 struct iicbus_softc *sc = device_get_softc(bus);
359 char data = byte;
360 int sent;
361
362 /* a slave must have been started for writing */
363 if (sc->started == 0 || (sc->strict != 0 && (sc->started & LSB) != 0))
364 return (IIC_ESTATUS);
365
366 return (iicbus_write(bus, &data, 1, &sent, timeout));
367}
368
369/*
370 * iicbus_read_byte()
371 *
372 * Read a byte from the slave previously started by iicbus_start() call
373 */
374int
375iicbus_read_byte(device_t bus, char *byte, int timeout)
376{
377 struct iicbus_softc *sc = device_get_softc(bus);
378 int read;
379
380 /* a slave must have been started for reading */
381 if (sc->started == 0 || (sc->strict != 0 && (sc->started & LSB) == 0))
382 return (IIC_ESTATUS);
383
384 return (iicbus_read(bus, byte, 1, &read, IIC_LAST_READ, timeout));
385}
386
387/*
388 * iicbus_block_write()
389 *
390 * Write a block of data to slave ; start/stop protocol managed
391 */
392int
393iicbus_block_write(device_t bus, u_char slave, char *buf, int len, int *sent)
394{
395 u_char addr = slave & ~LSB;
396 int error;
397
398 if ((error = iicbus_start(bus, addr, 0)))
399 return (error);
400
401 error = iicbus_write(bus, buf, len, sent, 0);
402
403 iicbus_stop(bus);
404
405 return (error);
406}
407
408/*
409 * iicbus_block_read()
410 *
411 * Read a block of data from slave ; start/stop protocol managed
412 */
413int
414iicbus_block_read(device_t bus, u_char slave, char *buf, int len, int *read)
415{
416 u_char addr = slave | LSB;
417 int error;
418
419 if ((error = iicbus_start(bus, addr, 0)))
420 return (error);
421
422 error = iicbus_read(bus, buf, len, read, IIC_LAST_READ, 0);
423
424 iicbus_stop(bus);
425
426 return (error);
427}
428
429/*
430 * iicbus_transfer()
431 *
432 * Do an aribtrary number of transfers on the iicbus. We pass these
433 * raw requests to the bridge driver. If the bridge driver supports
434 * them directly, then it manages all the details. If not, it can use
435 * the helper function iicbus_transfer_gen() which will do the
436 * transfers at a low level.
437 *
438 * Pointers passed in as part of iic_msg must be kernel pointers.
439 * Callers that have user addresses to manage must do so on their own.
440 */
441int
442iicbus_transfer(device_t bus, struct iic_msg *msgs, uint32_t nmsgs)
443{
444
445 return (IICBUS_TRANSFER(device_get_parent(bus), msgs, nmsgs));
446}
447
448int
449iicbus_transfer_excl(device_t dev, struct iic_msg *msgs, uint32_t nmsgs,
450 int how)
451{
452 device_t bus;
453 int error;
454
455 bus = device_get_parent(dev);
456 error = iicbus_request_bus(bus, dev, how);
457 if (error == 0)
458 error = IICBUS_TRANSFER(bus, msgs, nmsgs);
460 return (error);
461}
462
463/*
464 * Generic version of iicbus_transfer that calls the appropriate
465 * routines to accomplish this. See note above about acceptable
466 * buffer addresses.
467 */
468int
469iicbus_transfer_gen(device_t dev, struct iic_msg *msgs, uint32_t nmsgs)
470{
471 int i, error, lenread, lenwrote, nkid, rpstart, addr;
472 device_t *children, bus;
473 bool started;
474
475 if ((error = device_get_children(dev, &children, &nkid)) != 0)
476 return (IIC_ERESOURCE);
477 if (nkid != 1) {
478 free(children, M_TEMP);
479 return (IIC_ENOTSUPP);
480 }
481 bus = children[0];
482 rpstart = 0;
483 free(children, M_TEMP);
484 started = false;
485 for (i = 0, error = 0; i < nmsgs && error == 0; i++) {
486 addr = msgs[i].slave;
487 if (msgs[i].flags & IIC_M_RD)
488 addr |= LSB;
489 else
490 addr &= ~LSB;
491
492 if (!(msgs[i].flags & IIC_M_NOSTART)) {
493 if (rpstart)
494 error = iicbus_repeated_start(bus, addr, 0);
495 else
496 error = iicbus_start(bus, addr, 0);
497 if (error != 0)
498 break;
499 started = true;
500 }
501
502 if (msgs[i].flags & IIC_M_RD)
503 error = iicbus_read(bus, msgs[i].buf, msgs[i].len,
504 &lenread, IIC_LAST_READ, 0);
505 else
506 error = iicbus_write(bus, msgs[i].buf, msgs[i].len,
507 &lenwrote, 0);
508 if (error != 0)
509 break;
510
511 if (!(msgs[i].flags & IIC_M_NOSTOP)) {
512 rpstart = 0;
513 iicbus_stop(bus);
514 } else {
515 rpstart = 1; /* Next message gets repeated start */
516 }
517 }
518 if (error != 0 && started)
519 iicbus_stop(bus);
520 return (error);
521}
522
523int
524iicdev_readfrom(device_t slavedev, uint8_t regaddr, void *buffer,
525 uint16_t buflen, int waithow)
526{
527 struct iic_msg msgs[2];
528 uint8_t slaveaddr;
529
530 /*
531 * Two transfers back to back with a repeat-start between them; first we
532 * write the address-within-device, then we read from the device.
533 */
534 slaveaddr = iicbus_get_addr(slavedev);
535
536 msgs[0].slave = slaveaddr;
538 msgs[0].len = 1;
539 msgs[0].buf = &regaddr;
540
541 msgs[1].slave = slaveaddr;
542 msgs[1].flags = IIC_M_RD;
543 msgs[1].len = buflen;
544 msgs[1].buf = buffer;
545
546 return (iicbus_transfer_excl(slavedev, msgs, nitems(msgs), waithow));
547}
548
549int iicdev_writeto(device_t slavedev, uint8_t regaddr, void *buffer,
550 uint16_t buflen, int waithow)
551{
552 struct iic_msg msg;
553 uint8_t local_buffer[32];
554 uint8_t *bufptr;
555 size_t bufsize;
556 int error;
557
558 /*
559 * Ideally, we would do two transfers back to back with no stop or start
560 * between them using an array of 2 iic_msgs; first we'd write the
561 * address byte using the IIC_M_NOSTOP flag, then we write the data
562 * using IIC_M_NOSTART, all in a single transfer. Unfortunately,
563 * several i2c hardware drivers don't support that (perhaps because the
564 * hardware itself can't support it). So instead we gather the
565 * scattered bytes into a single buffer here before writing them using a
566 * single iic_msg. This function is typically used to write a few bytes
567 * at a time, so we try to use a small local buffer on the stack, but
568 * fall back to allocating a temporary buffer when necessary.
569 */
570
571 bufsize = buflen + 1;
572 if (bufsize <= sizeof(local_buffer)) {
573 bufptr = local_buffer;
574 } else {
575 bufptr = malloc(bufsize, M_DEVBUF,
576 (waithow & IIC_WAIT) ? M_WAITOK : M_NOWAIT);
577 if (bufptr == NULL)
578 return (errno2iic(ENOMEM));
579 }
580
581 bufptr[0] = regaddr;
582 memcpy(&bufptr[1], buffer, buflen);
583
584 msg.slave = iicbus_get_addr(slavedev);
585 msg.flags = IIC_M_WR;
586 msg.len = bufsize;
587 msg.buf = bufptr;
588
589 error = iicbus_transfer_excl(slavedev, &msg, 1, waithow);
590
591 if (bufptr != local_buffer)
592 free(bufptr, M_DEVBUF);
593
594 return (error);
595}
#define IIC_M_WR
Definition: ad7418.c:45
#define IIC_M_RD
Definition: iic.h:42
#define IIC_M_NOSTOP
Definition: iic.h:43
#define IIC_M_NOSTART
Definition: iic.h:44
caddr_t data
Definition: iicbb_if.m:61
u_char addr
Definition: iicbb_if.m:116
#define IICBUS_LOCK(sc)
Definition: iicbus.h:70
#define IICBUS_UNLOCK(sc)
Definition: iicbus.h:71
#define IICBUS_ASSERT_LOCKED(sc)
Definition: iicbus.h:72
char * buf
Definition: iicbus_if.m:55
int timeout
Definition: iicbus_if.m:77
int delay
Definition: iicbus_if.m:105
int last
Definition: iicbus_if.m:104
METHOD int read
Definition: iicbus_if.m:99
u_char slave
Definition: iicbus_if.m:76
struct iic_msg * msgs
Definition: iicbus_if.m:134
int event
Definition: iicbus_if.m:54
uint32_t nmsgs
Definition: iicbus_if.m:135
int len
Definition: iicbus_if.m:102
int errno2iic(int errno)
Definition: iiconf.c:51
int iicbus_request_bus(device_t bus, device_t dev, int how)
Definition: iiconf.c:138
void iicbus_intr(device_t bus, int event, char *buf)
Definition: iiconf.c:97
int iicbus_block_read(device_t bus, u_char slave, char *buf, int len, int *read)
Definition: iiconf.c:414
int iicbus_transfer(device_t bus, struct iic_msg *msgs, uint32_t nmsgs)
Definition: iiconf.c:442
int iicbus_read(device_t bus, char *buf, int len, int *read, int last, int delay)
Definition: iiconf.c:339
int iic2errno(int iic_status)
Definition: iiconf.c:60
int iicbus_release_bus(device_t bus, device_t dev)
Definition: iiconf.c:206
int iicbus_started(device_t bus)
Definition: iiconf.c:241
int iicdev_readfrom(device_t slavedev, uint8_t regaddr, void *buffer, uint16_t buflen, int waithow)
Definition: iiconf.c:524
int iicbus_read_byte(device_t bus, char *byte, int timeout)
Definition: iiconf.c:375
int iicbus_write(device_t bus, const char *buf, int len, int *sent, int timeout)
Definition: iiconf.c:321
__FBSDID("$FreeBSD$")
int iicbus_transfer_excl(device_t dev, struct iic_msg *msgs, uint32_t nmsgs, int how)
Definition: iiconf.c:449
int iicbus_stop(device_t bus)
Definition: iiconf.c:298
int iicdev_writeto(device_t slavedev, uint8_t regaddr, void *buffer, uint16_t buflen, int waithow)
Definition: iiconf.c:549
int iicbus_repeated_start(device_t bus, u_char slave, int timeout)
Definition: iiconf.c:276
int iicbus_start(device_t bus, u_char slave, int timeout)
Definition: iiconf.c:254
int iicbus_write_byte(device_t bus, char byte, int timeout)
Definition: iiconf.c:356
int iicbus_block_write(device_t bus, u_char slave, char *buf, int len, int *sent)
Definition: iiconf.c:393
static int iicbus_poll(struct iicbus_softc *sc, int how)
Definition: iiconf.c:109
int iicbus_transfer_gen(device_t dev, struct iic_msg *msgs, uint32_t nmsgs)
Definition: iiconf.c:469
#define IIC_NOINTR
Definition: iiconf.h:45
#define IIC_RECURSIVE
Definition: iiconf.h:49
#define IIC_ENOADDR
Definition: iiconf.h:116
#define IIC_ENOTSUPP
Definition: iiconf.h:115
#define IIC_EOVERFLOW
Definition: iiconf.h:114
#define IIC_ERRNO
Definition: iiconf.h:118
#define IIC_ETIMEOUT
Definition: iiconf.h:110
#define IIC_INTRWAIT
Definition: iiconf.h:48
#define IIC_WAIT
Definition: iiconf.h:46
#define IIC_LAST_READ
Definition: iiconf.h:85
#define LSB
Definition: iiconf.h:39
#define IIC_EBUSERR
Definition: iiconf.h:108
#define IIC_RELEASE_BUS
Definition: iiconf.h:91
#define IIC_NOERR
Definition: iiconf.h:107
#define IIC_INTR
Definition: iiconf.h:47
#define IIC_EBUSBSY
Definition: iiconf.h:111
#define IIC_ENOACK
Definition: iiconf.h:109
#define IICPRI
Definition: iiconf.h:37
#define IIC_ERESOURCE
Definition: iiconf.h:117
#define IIC_ESTATUS
Definition: iiconf.h:112
#define IIC_EUNDERFLOW
Definition: iiconf.h:113
#define IIC_REQUEST_BUS
Definition: iiconf.h:90
#define IIC_REQBUS_DEV
Definition: iiconf.h:50
device_t dev
Definition: ofw_iicbus_if.m:38
Definition: iic.h:38
uint16_t slave
Definition: iic.h:39
uint16_t len
Definition: iic.h:45
uint8_t * buf
Definition: iic.h:46
uint16_t flags
Definition: iic.h:40
device_t bus
Definition: iiconf.h:66
device_t dev
Definition: iiconf.h:67
device_t owner
Definition: iicbus.h:43
device_t busydev
Definition: iicbus.h:44
u_char started
Definition: iicbus.h:46
u_char strict
Definition: iicbus.h:48
u_int owncount
Definition: iicbus.h:45
struct mtx lock
Definition: iicbus.h:50