xref: /freebsd/sys/compat/linuxkpi/common/include/linux/i2c.h (revision 1961a14a47437595fb7fcdc20e327440e3eb51e2)
1*1961a14aSEmmanuel Vadot /*-
2*1961a14aSEmmanuel Vadot  * Copyright (c) 2021 Beckhoff Automation GmbH & Co. KG
3*1961a14aSEmmanuel Vadot  *
4*1961a14aSEmmanuel Vadot  * Redistribution and use in source and binary forms, with or without
5*1961a14aSEmmanuel Vadot  * modification, are permitted provided that the following conditions
6*1961a14aSEmmanuel Vadot  * are met:
7*1961a14aSEmmanuel Vadot  * 1. Redistributions of source code must retain the above copyright
8*1961a14aSEmmanuel Vadot  *    notice, this list of conditions and the following disclaimer.
9*1961a14aSEmmanuel Vadot  * 2. Redistributions in binary form must reproduce the above copyright
10*1961a14aSEmmanuel Vadot  *    notice, this list of conditions and the following disclaimer in the
11*1961a14aSEmmanuel Vadot  *    documentation and/or other materials provided with the distribution.
12*1961a14aSEmmanuel Vadot  *
13*1961a14aSEmmanuel Vadot  * THIS SOFTWARE IS PROVIDED BY THE AUTHOR AND CONTRIBUTORS ``AS IS'' AND
14*1961a14aSEmmanuel Vadot  * ANY EXPRESS OR IMPLIED WARRANTIES, INCLUDING, BUT NOT LIMITED TO, THE
15*1961a14aSEmmanuel Vadot  * IMPLIED WARRANTIES OF MERCHANTABILITY AND FITNESS FOR A PARTICULAR PURPOSE
16*1961a14aSEmmanuel Vadot  * ARE DISCLAIMED. IN NO EVENT SHALL THE AUTHOR OR CONTRIBUTORS BE LIABLE
17*1961a14aSEmmanuel Vadot  * FOR ANY DIRECT, INDIRECT, INCIDENTAL, SPECIAL, EXEMPLARY, OR CONSEQUENTIAL
18*1961a14aSEmmanuel Vadot  * DAMAGES (INCLUDING, BUT NOT LIMITED TO, PROCUREMENT OF SUBSTITUTE GOODS
19*1961a14aSEmmanuel Vadot  * OR SERVICES; LOSS OF USE, DATA, OR PROFITS; OR BUSINESS INTERRUPTION)
20*1961a14aSEmmanuel Vadot  * HOWEVER CAUSED AND ON ANY THEORY OF LIABILITY, WHETHER IN CONTRACT, STRICT
21*1961a14aSEmmanuel Vadot  * LIABILITY, OR TORT (INCLUDING NEGLIGENCE OR OTHERWISE) ARISING IN ANY WAY
22*1961a14aSEmmanuel Vadot  * OUT OF THE USE OF THIS SOFTWARE, EVEN IF ADVISED OF THE POSSIBILITY OF
23*1961a14aSEmmanuel Vadot  * SUCH DAMAGE.
24*1961a14aSEmmanuel Vadot  *
25*1961a14aSEmmanuel Vadot  */
26*1961a14aSEmmanuel Vadot 
27*1961a14aSEmmanuel Vadot #ifndef _LINUX_I2C_H_
28*1961a14aSEmmanuel Vadot #define	_LINUX_I2C_H_
29*1961a14aSEmmanuel Vadot 
30*1961a14aSEmmanuel Vadot #include <sys/types.h>
31*1961a14aSEmmanuel Vadot #include <sys/errno.h>
32*1961a14aSEmmanuel Vadot #include <sys/systm.h>
33*1961a14aSEmmanuel Vadot 
34*1961a14aSEmmanuel Vadot #include <linux/device.h>
35*1961a14aSEmmanuel Vadot 
36*1961a14aSEmmanuel Vadot #define	I2C_MAX_ADAPTER_NAME_LENGTH	32
37*1961a14aSEmmanuel Vadot 
38*1961a14aSEmmanuel Vadot #define	I2C_M_RD	0x0001
39*1961a14aSEmmanuel Vadot #define	I2C_M_NOSTART	0x0002
40*1961a14aSEmmanuel Vadot #define	I2C_M_STOP	0x0004
41*1961a14aSEmmanuel Vadot 
42*1961a14aSEmmanuel Vadot /* No need for us */
43*1961a14aSEmmanuel Vadot #define	I2C_FUNC_I2C			0
44*1961a14aSEmmanuel Vadot #define	I2C_FUNC_SMBUS_EMUL		0
45*1961a14aSEmmanuel Vadot #define	I2C_FUNC_SMBUS_READ_BLOCK_DATA	0
46*1961a14aSEmmanuel Vadot #define	I2C_FUNC_SMBUS_BLOCK_PROC_CALL	0
47*1961a14aSEmmanuel Vadot #define	I2C_FUNC_10BIT_ADDR		0
48*1961a14aSEmmanuel Vadot 
49*1961a14aSEmmanuel Vadot #define	I2C_CLASS_DDC	0x8
50*1961a14aSEmmanuel Vadot #define	I2C_CLASS_SPD	0x80
51*1961a14aSEmmanuel Vadot 
52*1961a14aSEmmanuel Vadot struct i2c_adapter {
53*1961a14aSEmmanuel Vadot 	struct module *owner;
54*1961a14aSEmmanuel Vadot 	unsigned int class;
55*1961a14aSEmmanuel Vadot 
56*1961a14aSEmmanuel Vadot 	char name[I2C_MAX_ADAPTER_NAME_LENGTH];
57*1961a14aSEmmanuel Vadot 	struct device dev;
58*1961a14aSEmmanuel Vadot 
59*1961a14aSEmmanuel Vadot 	const struct i2c_lock_operations *lock_ops;
60*1961a14aSEmmanuel Vadot 	const struct i2c_algorithm *algo;
61*1961a14aSEmmanuel Vadot 	void *algo_data;
62*1961a14aSEmmanuel Vadot 
63*1961a14aSEmmanuel Vadot 	int retries;
64*1961a14aSEmmanuel Vadot 	void *data;
65*1961a14aSEmmanuel Vadot };
66*1961a14aSEmmanuel Vadot 
67*1961a14aSEmmanuel Vadot struct i2c_msg {
68*1961a14aSEmmanuel Vadot 	uint16_t addr;
69*1961a14aSEmmanuel Vadot 	uint16_t flags;
70*1961a14aSEmmanuel Vadot 	uint16_t len;
71*1961a14aSEmmanuel Vadot 	uint8_t *buf;
72*1961a14aSEmmanuel Vadot };
73*1961a14aSEmmanuel Vadot 
74*1961a14aSEmmanuel Vadot struct i2c_algorithm {
75*1961a14aSEmmanuel Vadot 	int (*master_xfer)(struct i2c_adapter *, struct i2c_msg *, int);
76*1961a14aSEmmanuel Vadot 	uint32_t (*functionality)(struct i2c_adapter *);
77*1961a14aSEmmanuel Vadot };
78*1961a14aSEmmanuel Vadot 
79*1961a14aSEmmanuel Vadot struct i2c_lock_operations {
80*1961a14aSEmmanuel Vadot 	void (*lock_bus)(struct i2c_adapter *, unsigned int);
81*1961a14aSEmmanuel Vadot 	int (*trylock_bus)(struct i2c_adapter *, unsigned int);
82*1961a14aSEmmanuel Vadot 	void (*unlock_bus)(struct i2c_adapter *, unsigned int);
83*1961a14aSEmmanuel Vadot };
84*1961a14aSEmmanuel Vadot 
85*1961a14aSEmmanuel Vadot int lkpi_i2c_add_adapter(struct i2c_adapter *adapter);
86*1961a14aSEmmanuel Vadot int lkpi_i2c_del_adapter(struct i2c_adapter *adapter);
87*1961a14aSEmmanuel Vadot 
88*1961a14aSEmmanuel Vadot int lkpi_i2cbb_transfer(struct i2c_adapter *adapter, struct i2c_msg *msgs, int nmsgs);
89*1961a14aSEmmanuel Vadot 
90*1961a14aSEmmanuel Vadot #define	i2c_add_adapter(adapter)	lkpi_i2c_add_adapter(adapter)
91*1961a14aSEmmanuel Vadot #define	i2c_del_adapter(adapter)	lkpi_i2c_del_adapter(adapter)
92*1961a14aSEmmanuel Vadot 
93*1961a14aSEmmanuel Vadot #define	i2c_get_adapter(x)	NULL
94*1961a14aSEmmanuel Vadot #define	i2c_put_adapter(x)
95*1961a14aSEmmanuel Vadot 
96*1961a14aSEmmanuel Vadot static inline int
97*1961a14aSEmmanuel Vadot do_i2c_transfer(struct i2c_adapter *adapter, struct i2c_msg *msgs, int nmsgs)
98*1961a14aSEmmanuel Vadot {
99*1961a14aSEmmanuel Vadot 	int ret, retries;
100*1961a14aSEmmanuel Vadot 
101*1961a14aSEmmanuel Vadot 	retries = adapter->retries == 0 ? 1 : adapter->retries;
102*1961a14aSEmmanuel Vadot 	for (; retries != 0; retries--) {
103*1961a14aSEmmanuel Vadot 		if (adapter->algo->master_xfer != NULL)
104*1961a14aSEmmanuel Vadot 			ret = adapter->algo->master_xfer(adapter, msgs, nmsgs);
105*1961a14aSEmmanuel Vadot 		else
106*1961a14aSEmmanuel Vadot 			ret = lkpi_i2cbb_transfer(adapter, msgs, nmsgs);
107*1961a14aSEmmanuel Vadot 		if (ret != -EAGAIN)
108*1961a14aSEmmanuel Vadot 			break;
109*1961a14aSEmmanuel Vadot 	}
110*1961a14aSEmmanuel Vadot 
111*1961a14aSEmmanuel Vadot 	return (ret);
112*1961a14aSEmmanuel Vadot }
113*1961a14aSEmmanuel Vadot 
114*1961a14aSEmmanuel Vadot static inline int
115*1961a14aSEmmanuel Vadot i2c_transfer(struct i2c_adapter *adapter, struct i2c_msg *msgs, int nmsgs)
116*1961a14aSEmmanuel Vadot {
117*1961a14aSEmmanuel Vadot 	int ret;
118*1961a14aSEmmanuel Vadot 
119*1961a14aSEmmanuel Vadot 	if (!adapter->algo)
120*1961a14aSEmmanuel Vadot 		return (-EOPNOTSUPP);
121*1961a14aSEmmanuel Vadot 
122*1961a14aSEmmanuel Vadot 	if (adapter->lock_ops)
123*1961a14aSEmmanuel Vadot 		adapter->lock_ops->lock_bus(adapter, 0);
124*1961a14aSEmmanuel Vadot 
125*1961a14aSEmmanuel Vadot 	ret = do_i2c_transfer(adapter, msgs, nmsgs);
126*1961a14aSEmmanuel Vadot 
127*1961a14aSEmmanuel Vadot 	if (adapter->lock_ops)
128*1961a14aSEmmanuel Vadot 		adapter->lock_ops->unlock_bus(adapter, 0);
129*1961a14aSEmmanuel Vadot 
130*1961a14aSEmmanuel Vadot 	return (ret);
131*1961a14aSEmmanuel Vadot }
132*1961a14aSEmmanuel Vadot 
133*1961a14aSEmmanuel Vadot /* Unlocked version of i2c_transfer */
134*1961a14aSEmmanuel Vadot static inline int
135*1961a14aSEmmanuel Vadot __i2c_transfer(struct i2c_adapter *adapter, struct i2c_msg *msgs, int nmsgs)
136*1961a14aSEmmanuel Vadot {
137*1961a14aSEmmanuel Vadot 	return (do_i2c_transfer(adapter, msgs, nmsgs));
138*1961a14aSEmmanuel Vadot }
139*1961a14aSEmmanuel Vadot 
140*1961a14aSEmmanuel Vadot static inline void
141*1961a14aSEmmanuel Vadot i2c_set_adapdata(struct i2c_adapter *adapter, void *data)
142*1961a14aSEmmanuel Vadot {
143*1961a14aSEmmanuel Vadot 	adapter->data = data;
144*1961a14aSEmmanuel Vadot }
145*1961a14aSEmmanuel Vadot 
146*1961a14aSEmmanuel Vadot static inline void *
147*1961a14aSEmmanuel Vadot i2c_get_adapdata(struct i2c_adapter *adapter)
148*1961a14aSEmmanuel Vadot {
149*1961a14aSEmmanuel Vadot 	return (adapter->data);
150*1961a14aSEmmanuel Vadot }
151*1961a14aSEmmanuel Vadot 
152*1961a14aSEmmanuel Vadot #endif	/* _LINUX_I2C_H_ */
153