Compare commits
2 Commits
a6c2d808eb
...
7a08c8b113
Author | SHA1 | Date | |
---|---|---|---|
|
7a08c8b113 | ||
|
455cee9ce1 |
@ -1,15 +0,0 @@
|
|||||||
#ifndef __FTDI_DEV_H__
|
|
||||||
#define __FTDI_DEV_H__
|
|
||||||
|
|
||||||
#include <ftdi.h>
|
|
||||||
|
|
||||||
struct ftdi_dev {
|
|
||||||
struct ftdi_context *ftdi;
|
|
||||||
bool is_open;
|
|
||||||
unsigned int vendor_id;
|
|
||||||
unsigned int product_id;
|
|
||||||
unsigned char bit_mask; /* Mask of used bits */
|
|
||||||
unsigned char status_mask; /* Mask of current status of used bits */
|
|
||||||
};
|
|
||||||
|
|
||||||
#endif
|
|
@ -3,7 +3,6 @@
|
|||||||
|
|
||||||
struct gpio {
|
struct gpio {
|
||||||
unsigned int pin;
|
unsigned int pin;
|
||||||
struct ftdi_dev *ftdi_dev;
|
|
||||||
};
|
};
|
||||||
|
|
||||||
int gpio_open(const struct gpio *gpio);
|
int gpio_open(const struct gpio *gpio);
|
||||||
|
82
src/gpio.c
82
src/gpio.c
@ -1,31 +1,49 @@
|
|||||||
#include <stdlib.h>
|
#include <stdlib.h>
|
||||||
#include <syslog.h>
|
#include <syslog.h>
|
||||||
#include <stdbool.h>
|
#include <stdbool.h>
|
||||||
#include <ftdi_dev.h>
|
#include <ftdi.h>
|
||||||
|
|
||||||
#include <gpio.h>
|
#include <gpio.h>
|
||||||
|
|
||||||
static int ftdi_open(const struct gpio *gpio)
|
struct ftdi_obj {
|
||||||
|
struct ftdi_context *ftdi;
|
||||||
|
bool is_open;
|
||||||
|
unsigned int vendor_id;
|
||||||
|
unsigned int product_id;
|
||||||
|
unsigned char bit_mask; /* Mask of used bits */
|
||||||
|
unsigned char status_mask; /* Mask of current status of used bits */
|
||||||
|
};
|
||||||
|
|
||||||
|
static struct ftdi_obj ftdi_obj = {
|
||||||
|
.ftdi = NULL,
|
||||||
|
.is_open = false,
|
||||||
|
.vendor_id = 0x0403,
|
||||||
|
.product_id = 0x6001,
|
||||||
|
.bit_mask = 0,
|
||||||
|
.status_mask = 0,
|
||||||
|
};
|
||||||
|
|
||||||
|
static int ftdi_open(void)
|
||||||
{
|
{
|
||||||
int res;
|
int res;
|
||||||
|
|
||||||
if((gpio->ftdi_dev->ftdi = ftdi_new()) == 0) {
|
if((ftdi_obj.ftdi = ftdi_new()) == 0) {
|
||||||
syslog(LOG_ERR, "ftdi_new failed\n");
|
syslog(LOG_ERR, "ftdi_new failed\n");
|
||||||
return EXIT_FAILURE;
|
return EXIT_FAILURE;
|
||||||
}
|
}
|
||||||
|
|
||||||
res = ftdi_usb_open(gpio->ftdi_dev->ftdi, gpio->ftdi_dev->vendor_id, gpio->ftdi_dev->product_id);
|
res = ftdi_usb_open(ftdi_obj.ftdi, ftdi_obj.vendor_id, ftdi_obj.product_id);
|
||||||
if (res < 0 && res != -5) {
|
if (res < 0 && res != -5) {
|
||||||
syslog(LOG_ERR, "unable to open ftdi device: %d (%s)\n", res,
|
syslog(LOG_ERR, "unable to open ftdi device: %d (%s)\n", res,
|
||||||
ftdi_get_error_string(gpio->ftdi_dev->ftdi));
|
ftdi_get_error_string(ftdi_obj.ftdi));
|
||||||
ftdi_free(gpio->ftdi_dev->ftdi);
|
ftdi_free(ftdi_obj.ftdi);
|
||||||
return EXIT_FAILURE;
|
return EXIT_FAILURE;
|
||||||
}
|
}
|
||||||
|
|
||||||
res = ftdi_read_data(gpio->ftdi_dev->ftdi, &(gpio->ftdi_dev->status_mask), 1);
|
res = ftdi_read_data(ftdi_obj.ftdi, &(ftdi_obj.status_mask), 1);
|
||||||
if(res < 0) {
|
if(res < 0) {
|
||||||
syslog(LOG_ERR, "unable to readfrom ftdi device: %d (%s)\n", res,
|
syslog(LOG_ERR, "unable to readfrom ftdi device: %d (%s)\n", res,
|
||||||
ftdi_get_error_string(gpio->ftdi_dev->ftdi));
|
ftdi_get_error_string(ftdi_obj.ftdi));
|
||||||
return EXIT_FAILURE;
|
return EXIT_FAILURE;
|
||||||
}
|
}
|
||||||
|
|
||||||
@ -42,33 +60,33 @@ int gpio_open(const struct gpio *gpio)
|
|||||||
return EXIT_FAILURE;
|
return EXIT_FAILURE;
|
||||||
}
|
}
|
||||||
|
|
||||||
if(!gpio->ftdi_dev->is_open) {
|
if(!ftdi_obj.is_open) {
|
||||||
res = ftdi_open(gpio);
|
res = ftdi_open();
|
||||||
if(res != EXIT_SUCCESS) {
|
if(res != EXIT_SUCCESS) {
|
||||||
return EXIT_FAILURE;
|
return EXIT_FAILURE;
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
|
|
||||||
gpio->ftdi_dev->bit_mask |= (unsigned char)gpio->pin;
|
ftdi_obj.bit_mask |= (unsigned char)gpio->pin;
|
||||||
syslog(LOG_DEBUG, "bitmask: 0x%02x\n", gpio->ftdi_dev->bit_mask);
|
syslog(LOG_DEBUG, "bitmask: 0x%02x\n", ftdi_obj.bit_mask);
|
||||||
res = ftdi_set_bitmode(gpio->ftdi_dev->ftdi, gpio->ftdi_dev->bit_mask, BITMODE_BITBANG);
|
res = ftdi_set_bitmode(ftdi_obj.ftdi, ftdi_obj.bit_mask, BITMODE_BITBANG);
|
||||||
if(res < 0) {
|
if(res < 0) {
|
||||||
syslog(LOG_ERR, "unable to set bit bang mode: %d (%s)\n", res,
|
syslog(LOG_ERR, "unable to set bit bang mode: %d (%s)\n", res,
|
||||||
ftdi_get_error_string(gpio->ftdi_dev->ftdi));
|
ftdi_get_error_string(ftdi_obj.ftdi));
|
||||||
ftdi_usb_close(gpio->ftdi_dev->ftdi);
|
ftdi_usb_close(ftdi_obj.ftdi);
|
||||||
ftdi_free(gpio->ftdi_dev->ftdi);
|
ftdi_free(ftdi_obj.ftdi);
|
||||||
return EXIT_FAILURE;
|
return EXIT_FAILURE;
|
||||||
}
|
}
|
||||||
|
|
||||||
res = gpio_write(gpio, init_value);
|
res = gpio_write(gpio, init_value);
|
||||||
if(res < 0) {
|
if(res < 0) {
|
||||||
syslog(LOG_ERR, "unable to write to gpio %u (%s)\n", gpio->pin,
|
syslog(LOG_ERR, "unable to write to gpio %u (%s)\n", gpio->pin,
|
||||||
ftdi_get_error_string(gpio->ftdi_dev->ftdi));
|
ftdi_get_error_string(ftdi_obj.ftdi));
|
||||||
ftdi_usb_close(gpio->ftdi_dev->ftdi);
|
ftdi_usb_close(ftdi_obj.ftdi);
|
||||||
ftdi_free(gpio->ftdi_dev->ftdi);
|
ftdi_free(ftdi_obj.ftdi);
|
||||||
return EXIT_FAILURE;
|
return EXIT_FAILURE;
|
||||||
}
|
}
|
||||||
gpio->ftdi_dev->is_open = true;
|
ftdi_obj.is_open = true;
|
||||||
|
|
||||||
return EXIT_SUCCESS;
|
return EXIT_SUCCESS;
|
||||||
}
|
}
|
||||||
@ -81,10 +99,10 @@ int gpio_close(const struct gpio *gpio)
|
|||||||
|
|
||||||
gpio_write(gpio, 0);
|
gpio_write(gpio, 0);
|
||||||
|
|
||||||
gpio->ftdi_dev->bit_mask &= ~(unsigned char)(gpio->pin);
|
ftdi_obj.bit_mask &= ~(unsigned char)(gpio->pin);
|
||||||
if(gpio->ftdi_dev->bit_mask == 0) {
|
if(ftdi_obj.bit_mask == 0) {
|
||||||
ftdi_usb_close(gpio->ftdi_dev->ftdi);
|
ftdi_usb_close(ftdi_obj.ftdi);
|
||||||
ftdi_free(gpio->ftdi_dev->ftdi);
|
ftdi_free(ftdi_obj.ftdi);
|
||||||
}
|
}
|
||||||
|
|
||||||
return EXIT_SUCCESS;
|
return EXIT_SUCCESS;
|
||||||
@ -96,7 +114,7 @@ int gpio_read(const struct gpio *gpio, unsigned int *value)
|
|||||||
return EXIT_FAILURE;
|
return EXIT_FAILURE;
|
||||||
}
|
}
|
||||||
|
|
||||||
if(gpio->ftdi_dev->status_mask & (unsigned char)(gpio->pin)) {
|
if(ftdi_obj.status_mask & (unsigned char)(gpio->pin)) {
|
||||||
*value = 1;
|
*value = 1;
|
||||||
} else {
|
} else {
|
||||||
*value = 0;
|
*value = 0;
|
||||||
@ -121,13 +139,13 @@ int gpio_write(const struct gpio *gpio, unsigned int value)
|
|||||||
mask |= (unsigned char)(gpio->pin);
|
mask |= (unsigned char)(gpio->pin);
|
||||||
}
|
}
|
||||||
|
|
||||||
res = ftdi_write_data(gpio->ftdi_dev->ftdi, &mask, 1);
|
res = ftdi_write_data(ftdi_obj.ftdi, &mask, 1);
|
||||||
if(res < 0) {
|
if(res < 0) {
|
||||||
syslog(LOG_ERR, "write failed for 0x%x, error %d (%s)\n", value, res,
|
syslog(LOG_ERR, "write failed for 0x%x, error %d (%s)\n", value, res,
|
||||||
ftdi_get_error_string(gpio->ftdi_dev->ftdi));
|
ftdi_get_error_string(ftdi_obj.ftdi));
|
||||||
return EXIT_FAILURE;
|
return EXIT_FAILURE;
|
||||||
}
|
}
|
||||||
gpio->ftdi_dev->status_mask = mask;
|
ftdi_obj.status_mask = mask;
|
||||||
|
|
||||||
return EXIT_SUCCESS;
|
return EXIT_SUCCESS;
|
||||||
}
|
}
|
||||||
@ -135,7 +153,7 @@ int gpio_write(const struct gpio *gpio, unsigned int value)
|
|||||||
int gpio_toggle(const struct gpio *gpio)
|
int gpio_toggle(const struct gpio *gpio)
|
||||||
{
|
{
|
||||||
int res;
|
int res;
|
||||||
unsigned char mask = gpio->ftdi_dev->status_mask;
|
unsigned char mask = ftdi_obj.status_mask;
|
||||||
|
|
||||||
if(NULL == gpio) {
|
if(NULL == gpio) {
|
||||||
return EXIT_FAILURE;
|
return EXIT_FAILURE;
|
||||||
@ -143,13 +161,13 @@ int gpio_toggle(const struct gpio *gpio)
|
|||||||
|
|
||||||
mask ^= (unsigned char)(gpio->pin);
|
mask ^= (unsigned char)(gpio->pin);
|
||||||
|
|
||||||
res = ftdi_write_data(gpio->ftdi_dev->ftdi, &mask, 1);
|
res = ftdi_write_data(ftdi_obj.ftdi, &mask, 1);
|
||||||
if(res < 0) {
|
if(res < 0) {
|
||||||
syslog(LOG_ERR, "toggle failed, error %d (%s)\n", res,
|
syslog(LOG_ERR, "toggle failed, error %d (%s)\n", res,
|
||||||
ftdi_get_error_string(gpio->ftdi_dev->ftdi));
|
ftdi_get_error_string(ftdi_obj.ftdi));
|
||||||
return EXIT_FAILURE;
|
return EXIT_FAILURE;
|
||||||
}
|
}
|
||||||
gpio->ftdi_dev->status_mask = mask;
|
ftdi_obj.status_mask = mask;
|
||||||
|
|
||||||
return EXIT_SUCCESS;
|
return EXIT_SUCCESS;
|
||||||
}
|
}
|
||||||
|
14
src/main.c
14
src/main.c
@ -2,8 +2,7 @@
|
|||||||
#include <stdlib.h>
|
#include <stdlib.h>
|
||||||
#include <unistd.h>
|
#include <unistd.h>
|
||||||
#include <syslog.h>
|
#include <syslog.h>
|
||||||
#include <stdbool.h>
|
|
||||||
#include <ftdi_dev.h>
|
|
||||||
#include <gpio.h>
|
#include <gpio.h>
|
||||||
|
|
||||||
/*
|
/*
|
||||||
@ -13,22 +12,11 @@
|
|||||||
#define GPIO4 0x14 // RTS (green on FTDI) + DTR (on SparkFun breakout)
|
#define GPIO4 0x14 // RTS (green on FTDI) + DTR (on SparkFun breakout)
|
||||||
*/
|
*/
|
||||||
|
|
||||||
static struct ftdi_dev ftdi_obj = {
|
|
||||||
.ftdi = NULL,
|
|
||||||
.is_open = false,
|
|
||||||
.vendor_id = 0x0403,
|
|
||||||
.product_id = 0x6001,
|
|
||||||
.bit_mask = 0,
|
|
||||||
.status_mask = 0,
|
|
||||||
};
|
|
||||||
|
|
||||||
static const struct gpio gpio_1 = {
|
static const struct gpio gpio_1 = {
|
||||||
.pin = 0x08, /* CTS (brown wire on FTDI cable) */
|
.pin = 0x08, /* CTS (brown wire on FTDI cable) */
|
||||||
.ftdi_dev = &ftdi_obj,
|
|
||||||
};
|
};
|
||||||
static const struct gpio gpio_2 = {
|
static const struct gpio gpio_2 = {
|
||||||
.pin = 0x01, /* TX (orange wire on FTDI cable) */
|
.pin = 0x01, /* TX (orange wire on FTDI cable) */
|
||||||
.ftdi_dev = &ftdi_obj,
|
|
||||||
};
|
};
|
||||||
|
|
||||||
int main(int argc, char *argv[])
|
int main(int argc, char *argv[])
|
||||||
|
Loading…
Reference in New Issue
Block a user