xref: /nrf52832-nimble/rt-thread/components/drivers/i2c/i2c_dev.c (revision 104654410c56c573564690304ae786df310c91fc)
1 /*
2  * Copyright (c) 2006-2018, RT-Thread Development Team
3  *
4  * SPDX-License-Identifier: Apache-2.0
5  *
6  * Change Logs:
7  * Date           Author        Notes
8  * 2012-04-25     weety         first version
9  * 2014-08-03     bernard       fix some compiling warning
10  */
11 
12 #include <rtdevice.h>
13 
i2c_bus_device_read(rt_device_t dev,rt_off_t pos,void * buffer,rt_size_t count)14 static rt_size_t i2c_bus_device_read(rt_device_t dev,
15                                      rt_off_t    pos,
16                                      void       *buffer,
17                                      rt_size_t   count)
18 {
19     rt_uint16_t addr;
20     rt_uint16_t flags;
21     struct rt_i2c_bus_device *bus = (struct rt_i2c_bus_device *)dev->user_data;
22 
23     RT_ASSERT(bus != RT_NULL);
24     RT_ASSERT(buffer != RT_NULL);
25 
26     i2c_dbg("I2C bus dev [%s] reading %u bytes.\n", dev->parent.name, count);
27 
28     addr = pos & 0xffff;
29     flags = (pos >> 16) & 0xffff;
30 
31     return rt_i2c_master_recv(bus, addr, flags, buffer, count);
32 }
33 
i2c_bus_device_write(rt_device_t dev,rt_off_t pos,const void * buffer,rt_size_t count)34 static rt_size_t i2c_bus_device_write(rt_device_t dev,
35                                       rt_off_t    pos,
36                                       const void *buffer,
37                                       rt_size_t   count)
38 {
39     rt_uint16_t addr;
40     rt_uint16_t flags;
41     struct rt_i2c_bus_device *bus = (struct rt_i2c_bus_device *)dev->user_data;
42 
43     RT_ASSERT(bus != RT_NULL);
44     RT_ASSERT(buffer != RT_NULL);
45 
46     i2c_dbg("I2C bus dev [%s] writing %u bytes.\n", dev->parent.name, count);
47 
48     addr = pos & 0xffff;
49     flags = (pos >> 16) & 0xffff;
50 
51     return rt_i2c_master_send(bus, addr, flags, buffer, count);
52 }
53 
i2c_bus_device_control(rt_device_t dev,int cmd,void * args)54 static rt_err_t i2c_bus_device_control(rt_device_t dev,
55                                        int         cmd,
56                                        void       *args)
57 {
58     rt_err_t ret;
59     struct rt_i2c_priv_data *priv_data;
60     struct rt_i2c_bus_device *bus = (struct rt_i2c_bus_device *)dev->user_data;
61 
62     RT_ASSERT(bus != RT_NULL);
63 
64     switch (cmd)
65     {
66     /* set 10-bit addr mode */
67     case RT_I2C_DEV_CTRL_10BIT:
68         bus->flags |= RT_I2C_ADDR_10BIT;
69         break;
70     case RT_I2C_DEV_CTRL_ADDR:
71         bus->addr = *(rt_uint16_t *)args;
72         break;
73     case RT_I2C_DEV_CTRL_TIMEOUT:
74         bus->timeout = *(rt_uint32_t *)args;
75         break;
76     case RT_I2C_DEV_CTRL_RW:
77         priv_data = (struct rt_i2c_priv_data *)args;
78         ret = rt_i2c_transfer(bus, priv_data->msgs, priv_data->number);
79         if (ret < 0)
80         {
81             return -RT_EIO;
82         }
83         break;
84     default:
85         break;
86     }
87 
88     return RT_EOK;
89 }
90 
91 #ifdef RT_USING_DEVICE_OPS
92 const static struct rt_device_ops i2c_ops =
93 {
94     RT_NULL,
95     RT_NULL,
96     RT_NULL,
97     i2c_bus_device_read,
98     i2c_bus_device_write,
99     i2c_bus_device_control
100 };
101 #endif
102 
rt_i2c_bus_device_device_init(struct rt_i2c_bus_device * bus,const char * name)103 rt_err_t rt_i2c_bus_device_device_init(struct rt_i2c_bus_device *bus,
104                                        const char               *name)
105 {
106     struct rt_device *device;
107     RT_ASSERT(bus != RT_NULL);
108 
109     device = &bus->parent;
110 
111     device->user_data = bus;
112 
113     /* set device type */
114     device->type    = RT_Device_Class_I2CBUS;
115     /* initialize device interface */
116 #ifdef RT_USING_DEVICE_OPS
117     device->ops     = &i2c_ops;
118 #else
119     device->init    = RT_NULL;
120     device->open    = RT_NULL;
121     device->close   = RT_NULL;
122     device->read    = i2c_bus_device_read;
123     device->write   = i2c_bus_device_write;
124     device->control = i2c_bus_device_control;
125 #endif
126 
127     /* register to device manager */
128     rt_device_register(device, name, RT_DEVICE_FLAG_RDWR);
129 
130     return RT_EOK;
131 }
132