#include <stdio.h>
#include <linux/types.h>
#include <stdlib.h>
#include <stdint.h>
#include <stdbool.h>
#include <fcntl.h>
#include <unistd.h>
#include <sys/types.h>
#include <sys/ioctl.h>
#include <errno.h>
#include <assert.h>
#include <string.h>
#include <linux/i2c.h>
#include <linux/i2c-dev.h>
#include <stdio.h>
#include <map>
#include <string.h>
#include <termios.h>
#include <fcntl.h>
#include <sys/select.h>
#include <unistd.h>
#include <errno.h>
#include <sys/time.h>
#include <pthread.h>
#include <semaphore.h>
#include <stdint.h>
#define I2C_BUS "/dev/i2c-1"
#define ISL2108_ADDR 0x6F
static int i2c_write_bytes(int fd, uint8_t slave_addr, uint8_t reg_addr, uint8_t *values, uint8_t len);
typedef struct time_datas
{
int _weeks;
int _weeks_enable; //
int _months;
int _months_enable;
int _days;
int _days_enable;
int _hours;
int _hours_enable; //
int _minutes;
int _minutes_enable; //
int _seconds;
int _seconds_enable;
uint8_t _time_data[10];
} time_datas;
// 指定的某一位数置1
#define SET_BIT(x, bit) (x |= (1 << bit)) /* 置位第bit位 */
// 指定的某一位数置0
#define SET_PIN(PIN, N) (PIN &= ~(1 << N)) /* 置位第bit位 */
int IntToBCD(int i) // 十进制转BCD
{
return (((i / 10) << 4) + ((i % 10) & 0x0f));
}
int BCDToInt(int bcd) // BCD转十进制
{
return (0xff & (bcd >> 4)) * 10 + (0xf & bcd);
}
time_datas gettimedate(time_datas _time_datas)
{
time_datas framev;
framev._time_data[0] = 0x00;
framev._time_data[1] = 0x00;
framev._time_data[2] = 0x00;
framev._time_data[3] = 0x00;
framev._time_data[4] = 0x00;
framev._time_data[5] = 0x00;
framev._time_data[6] = 0x00;
framev._time_data[7] = 0x00;
framev._time_data[8] = 0x00;
framev._time_data[9] = 0x00;
framev._weeks = IntToBCD(_time_datas._weeks);
printf("报警时钟星期[%d],_enable:=[%d]\n", _time_datas._weeks, _time_datas._weeks_enable);
if (_time_datas._weeks_enable == 1)
{
SET_BIT(framev._weeks, 6);
}
if (_time_datas._weeks_enable == 0)
{
SET_PIN(framev._weeks, 6);
}
printf("十六进制输出:\n"); // 以十六进制形式输出
printf("报警时钟星期=[%#X]\n", framev._weeks); // X大写,则输出的前缀和字母都大写
//
framev._hours = IntToBCD(_time_datas._hours);
printf("报警时钟小时[%d],_enable:=[%d]\n", _time_datas._hours, _time_datas._hours_enable);
if (_time_datas._hours_enable == 1)
{
SET_BIT(framev._hours, 7);
}
if (_time_datas._hours_enable == 0)
{
SET_PIN(framev._hours, 7);
}
printf("十六进制输出:\n"); // 以十六进制形式输出
printf("报警时钟小时=[%#X]\n", framev._hours); // X大写,则输出的前缀和字母都大写
///
//
framev._minutes = IntToBCD(_time_datas._minutes);
printf("报警时钟分[%d],_enable:=[%d]\n", _time_datas._minutes, _time_datas._minutes_enable);
if (_time_datas._minutes_enable == 1)
{
SET_BIT(framev._minutes, 7);
}
if (_time_datas._minutes_enable == 0)
{
SET_PIN(framev._minutes, 7);
}
printf("十六进制输出:\n"); // 以十六进制形式输出
printf("报警时钟分=[%#X]\n", framev._minutes); // X大写,则输出的前缀和字母都大写
///
framev._time_data[1] = framev._minutes;
framev._time_data[2] = framev._hours;
framev._time_data[5] = framev._weeks;
printf("Data SET: \n");
for (int i = 0; i < 11; i++)
printf("%.2X ", framev._time_data[i]);
printf("\n");
return framev;
}
static int i2c_write_bytes(int fd, uint8_t slave_addr, uint8_t reg_addr, uint8_t *values, uint8_t len)
{
uint8_t *outbuf = NULL;
struct i2c_rdwr_ioctl_data packets;
struct i2c_msg messages[1];
outbuf = (uint8_t *)malloc(len + 1);
if (!outbuf)
{
printf("Error: No memory for buffer\n");
return -1;
}
outbuf[0] = reg_addr; // i2c设备要操作的reg地址
memcpy(outbuf + 1, values, len);
messages[0].addr = slave_addr; // i2c设备地址
messages[0].flags = 0; // write flag
messages[0].len = len + 1;
messages[0].buf = outbuf; // 向reg写入的值
/* Transfer the i2c packets to the kernel and verify it worked */
packets.msgs = messages;
packets.nmsgs = 1;
if (ioctl(fd, I2C_RDWR, &packets) < 0)
{
printf("Error: Unable to send data");
free(outbuf);
return -1;
}
free(outbuf);
return 0;
}
int Auto_Time_Set(time_datas _time_datas)
{
int i2c_fd;
unsigned long len;
uint8_t buffer[1024];
// 打开I2C总线
i2c_fd = open(I2C_BUS, O_RDWR);
if (i2c_fd < 0)
{
perror("Failed to open I2C bus");
return -1;
}
time_datas get_time_datas;
get_time_datas = gettimedate(_time_datas);
// 读取ISL2108的数据
len = 10;
buffer[0] = 0x00;
buffer[1] = 0x00;
// Alarm
i2c_write_bytes(i2c_fd, ISL2108_ADDR, 0x0c, get_time_datas._time_data, len);
// 关闭I2C总线
close(i2c_fd);
return 0;
}
int main()
{
time_datas time_datas_V;
time_datas_V._hours_enable = 1;
time_datas_V._hours = 9; // 小时
time_datas_V._weeks = 1; // 周
time_datas_V._weeks_enable = 1;
time_datas_V._minutes = 03; // 分钟
time_datas_V._minutes_enable = 1;
Auto_Time_Set(time_datas_V);
return 0;
}
ISL1208时钟芯片 Linux下 i2c 设置报警时钟。
最新推荐文章于 2024-09-06 18:06:22 发布