i2c_core.c 2.8 KB
Newer Older
1 2 3 4 5 6 7 8 9 10 11 12 13 14
/*
 * File      : i2c_core.c
 * This file is part of RT-Thread RTOS
 * COPYRIGHT (C) 2006, RT-Thread Development Team
 *
 * The license and distribution terms for this file may be
 * found in the file LICENSE in this distribution or at
 * http://www.rt-thread.org/license/LICENSE
 *
 * Change Logs:
 * Date           Author		Notes
 * 2012-04-25     weety		first version
 */

15
#include <rtdevice.h>
16 17 18

static struct rt_mutex i2c_core_lock;

19
rt_err_t rt_i2c_bus_device_register(struct rt_i2c_bus_device *bus, const char *bus_name)
20
{
21
	rt_err_t res = RT_EOK;
22

23
	rt_mutex_init(&bus->lock, "i2c_bus_lock", RT_IPC_FLAG_FIFO);
24 25 26 27 28

	rt_mutex_take(&i2c_core_lock, RT_WAITING_FOREVER);

	if (bus->timeout == 0)
		bus->timeout = RT_TICK_PER_SECOND;
29 30
		
	res = rt_i2c_bus_device_device_init(bus, bus_name);
31

32
	i2c_dbg("I2C bus [%s] registered\n", bus_name);
33 34

	rt_mutex_release(&i2c_core_lock);
35
	return res;
36 37 38
}


39
struct rt_i2c_bus_device* rt_i2c_bus_device_find(const char *bus_name)
40
{
41 42 43
	struct rt_i2c_bus_device *bus;
	rt_device_t dev = rt_device_find(bus_name);
	if (dev == RT_NULL || dev->type != RT_Device_Class_I2CBUS)
44
	{
45 46
		i2c_dbg("I2C bus %s not exist\n", bus_name);
		return RT_NULL;
47 48
	}
	
49
	bus = (struct rt_i2c_bus_device *)dev->user_data;
50
	
51
	return bus;
52 53 54
}


55
rt_size_t rt_i2c_transfer(struct rt_i2c_bus_device *bus, struct rt_i2c_msg msgs[], rt_uint32_t num)
56 57 58 59 60
{
	rt_size_t ret;

	if (bus->ops->master_xfer)
	{
61 62
	#ifdef RT_I2C_DEBUG
		for (ret = 0; ret < num; ret++)
63 64 65 66 67
		{
			i2c_dbg("msgs[%d] %c, addr=0x%02x, len=%d%s\n", ret, 
				(msgs[ret].flags & RT_I2C_RD) ? 'R' : 'W', 
				msgs[ret].addr, msgs[ret].len);
		}
68
	#endif
69 70

		rt_mutex_take(&bus->lock, RT_WAITING_FOREVER);
71
		ret = bus->ops->master_xfer(bus, msgs, num);
72 73 74 75 76 77
		rt_mutex_release(&bus->lock);

		return ret;
	}
	else
	{
78
		rt_kprintf("I2C bus operation not supported\n");
79 80 81 82 83
		return -RT_ERROR;
	}
}


84 85 86
rt_size_t rt_i2c_master_send(struct rt_i2c_bus_device *bus, rt_uint16_t addr, 
                               rt_uint16_t flags, const rt_uint8_t *buf, 
                               rt_uint32_t count)
87 88 89 90
{
	rt_size_t ret;
	struct rt_i2c_msg msg;

91 92 93
	msg.addr = addr;
	msg.flags = flags & RT_I2C_ADDR_10BIT;
	msg.len = count;
94 95 96 97
	msg.buf = (rt_uint8_t *)buf;

	ret = rt_i2c_transfer(bus, &msg, 1);

98
	return (ret > 0) ? count : ret;
99 100 101 102
}



103 104 105
rt_size_t rt_i2c_master_recv(struct rt_i2c_bus_device *bus, rt_uint16_t addr, 
                               rt_uint16_t flags, rt_uint8_t *buf, 
                               rt_uint32_t count)
106 107 108 109 110
{
	rt_size_t ret;
	struct rt_i2c_msg msg;
	RT_ASSERT(bus != RT_NULL);

111 112
	msg.addr = addr;
	msg.flags = flags & RT_I2C_ADDR_10BIT;
113
	msg.flags |= RT_I2C_RD;
114
	msg.len = count;
115 116 117 118
	msg.buf = buf;

	ret = rt_i2c_transfer(bus, &msg, 1);

119
	return (ret > 0) ? count : ret;
120 121 122
}


123
rt_err_t rt_i2c_core_init(void)
124
{
125

126
	rt_mutex_init (&i2c_core_lock, "i2c_core_lock", RT_IPC_FLAG_FIFO);
127

128 129
}