#include <glob.h>
#include <string.h>
+#include <sys/types.h>
+#include <sys/stat.h>
+#include <fcntl.h>
+#include <unistd.h>
+#include <termios.h>
+#include <stdlib.h>
#include <glib.h>
+#include "sigrok.h"
+
+
char *serial_port_glob[] = {
/* Linux */
}
+int serial_open(const char *pathname, int flags)
+{
+
+ return open(pathname, flags);
+}
+
+
+int serial_close(int fd)
+{
+
+ return close(fd);
+}
+
+
+void *serial_backup_params(int fd)
+{
+ struct termios *term;
+
+ term = malloc(sizeof(struct termios));
+ tcgetattr(fd, term);
+
+ return term;
+}
+
+
+void serial_restore_params(int fd, void *backup)
+{
+
+ tcsetattr(fd, TCSADRAIN, (struct termios *) backup);
+
+}
+
+
+/* flowcontrol 1 = rts/cts 2 = xon/xoff */
+int serial_set_params(int fd, int speed, int bits, int parity, int stopbits, int flowcontrol)
+{
+ struct termios term;
+
+ /* only supporting what we need really -- currently just the OLS driver */
+ if(speed != 115200 || bits != 8 || parity != 0 || stopbits != 1 || flowcontrol != 2)
+ return SIGROK_ERR;
+
+ if(tcgetattr(fd, &term) < 0)
+ return SIGROK_ERR;
+ if(cfsetispeed(&term, B115200) < 0)
+ return SIGROK_ERR;
+ term.c_cflag &= ~CSIZE;
+ term.c_cflag |= CS8;
+ term.c_cflag &= ~CSTOPB;
+ term.c_cflag |= IXON | IXOFF;
+ term.c_iflag |= IGNPAR;
+ if(tcsetattr(fd, TCSADRAIN, &term) < 0)
+ return SIGROK_ERR;
+
+ return SIGROK_OK;
+}
+
+
struct sigrok_device_instance *sdi;
GSList *ports, *l;
GPollFD *fds;
- struct termios term, *prev_termios;
int devcnt, final_devcnt, num_ports, fd, ret, i;
- char buf[8], **device_names;
+ char buf[8], **device_names, **serial_params;
if(deviceinfo)
ports = g_slist_append(NULL, strdup(deviceinfo));
num_ports = g_slist_length(ports);
fds = calloc(1, num_ports * sizeof(GPollFD));
device_names = malloc(num_ports * (sizeof(char *)));
- prev_termios = malloc(num_ports * sizeof(struct termios));
+ serial_params = malloc(num_ports * (sizeof(char *)));
devcnt = 0;
for(l = ports; l; l = l->next) {
/* The discovery procedure is like this: first send the Reset command (0x00) 5 times,
* first, then wait for all of them to respond with g_poll().
*/
g_message("probing %s...", (char *) l->data);
- fd = open(l->data, O_RDWR | O_NONBLOCK);
+ fd = serial_open(l->data, O_RDWR | O_NONBLOCK);
if(fd != -1) {
- tcgetattr(fd, &prev_termios[devcnt]);
- tcgetattr(fd, &term);
- cfsetispeed(&term, SERIAL_SPEED);
- term.c_cflag &= ~CSIZE;
- term.c_cflag |= CS8;
- term.c_cflag &= ~CSTOPB;
- term.c_cflag |= IXON | IXOFF;
- term.c_iflag |= IGNPAR;
- tcsetattr(fd, TCSADRAIN, &term);
+ serial_params[devcnt] = serial_backup_params(fd);
+ serial_set_params(fd, 115200, 8, 0, 1, 2);
ret = SIGROK_OK;
for(i = 0; i < 5; i++) {
if( (ret = send_shortcommand(fd, CMD_RESET)) != SIGROK_OK) {
- /* serial port is not writable... restore port settings */
- tcsetattr(fd, TCSADRAIN, &prev_termios[devcnt]);
- close(fd);
+ /* serial port is not writable */
break;
}
}
- if(ret != SIGROK_OK)
+ if(ret != SIGROK_OK) {
+ serial_restore_params(fd, serial_params[devcnt]);
+ serial_close(fd);
continue;
+ }
send_shortcommand(fd, CMD_ID);
fds[devcnt].fd = fd;
fds[devcnt].events = G_IO_IN;
sdi->serial = serial_device_instance_new(device_names[i], -1);
device_instances = g_slist_append(device_instances, sdi);
final_devcnt++;
- close(fds[i].fd);
+ serial_close(fds[i].fd);
fds[i].fd = 0;
}
}
}
if(fds[i].fd != 0) {
- tcsetattr(fds[i].fd, TCSADRAIN, &prev_termios[i]);
- close(fds[i].fd);
+ serial_restore_params(fds[i].fd, serial_params[i]);
+ serial_close(fds[i].fd);
}
+ free(serial_params[i]);
}
free(fds);
free(device_names);
- free(prev_termios);
+ free(serial_params);
g_slist_free(ports);
cur_samplerate = samplerates.low;
if(!(sdi = get_sigrok_device_instance(device_instances, device_index)))
return SIGROK_ERR;
- sdi->serial->fd = open(sdi->serial->port, O_RDWR);
+ sdi->serial->fd = serial_open(sdi->serial->port, O_RDWR);
if(sdi->serial->fd == -1)
return SIGROK_ERR;
return;
if(sdi->serial->fd != -1) {
- close(sdi->serial->fd);
+ serial_close(sdi->serial->fd);
sdi->serial->fd = -1;
sdi->status = ST_INACTIVE;
}
for(l = device_instances; l; l = l->next) {
sdi = l->data;
if(sdi->serial->fd != -1)
- close(sdi->serial->fd);
+ serial_close(sdi->serial->fd);
sigrok_device_instance_free(sdi);
}
g_slist_free(device_instances);
/* this is the main loop telling us a timeout was reached, or we've
* acquired all the samples we asked for -- we're done */
tcflush(fd, TCIOFLUSH);
- close(fd);
+ serial_close(fd);
packet.type = DF_END;
packet.length = 0;
session_bus(user_data, &packet);