diff --git a/sw/lib/ocaml/cserial.c b/sw/lib/ocaml/cserial.c index b569ffff57..6632ee58e1 100644 --- a/sw/lib/ocaml/cserial.c +++ b/sw/lib/ocaml/cserial.c @@ -89,3 +89,31 @@ value c_set_dtr(value val_fd, value val_bit) { ioctl(fd, TIOCMSET, &status); return Val_unit; } + + +/* From the gPhoto I/O library */ +value c_serial_set_baudrate(value val_fd, value speed) +{ + struct termios tio; + int fd = Int_val(val_fd); + + if (tcgetattr(fd, &tio) < 0) { + failwith("tcgetattr"); + } + tio.c_iflag = 0; + tio.c_oflag = 0; + tio.c_cflag = CS8 | CREAD | CLOCAL; + tio.c_cc[VMIN] = 1; + tio.c_cc[VTIME] = 5; + + tio.c_lflag &= ~(ICANON | ISIG | ECHO | ECHONL | ECHOE | ECHOK); + + int br = baudrates[Int_val(speed)]; + + cfsetispeed(&tio, br); + cfsetospeed(&tio, br); + if (tcsetattr(fd, TCSANOW | TCSAFLUSH, &tio) < 0) { + failwith("tcsetattr"); + } + return Val_unit; +} diff --git a/sw/lib/ocaml/serial.ml b/sw/lib/ocaml/serial.ml index 2922ab2485..ed90482923 100644 --- a/sw/lib/ocaml/serial.ml +++ b/sw/lib/ocaml/serial.ml @@ -77,8 +77,9 @@ let string_of_payload = fun x -> x let payload_of_string = fun x -> x -external init_serial : string -> speed -> Unix.file_descr = "c_init_serial";; +external init_serial : string -> speed -> Unix.file_descr = "c_init_serial" external set_dtr : Unix.file_descr -> bool -> unit = "c_set_dtr" +external set_speed : Unix.file_descr -> speed -> unit = "c_serial_set_baudrate" let opendev device speed = try @@ -109,6 +110,10 @@ let input = fun f -> (* Printf.fprintf stderr "n'=%d\n" nb_used; flush stderr; *) if nb_used > 0 then parse (start + nb_used) (n - nb_used) + else if n = buffer_len then + (* The buffer is full and the user does not consume any. We have to + discard one char to avoid a dead lock *) + parse (start + 1) (n - 1) else wait start n in parse 0 n) diff --git a/sw/lib/ocaml/serial.mli b/sw/lib/ocaml/serial.mli index 1b70d63e37..7455f08681 100644 --- a/sw/lib/ocaml/serial.mli +++ b/sw/lib/ocaml/serial.mli @@ -52,6 +52,7 @@ val speed_of_baudrate : string -> speed val opendev : string -> speed -> Unix.file_descr val close : Unix.file_descr -> unit val set_dtr : Unix.file_descr -> bool -> unit +val set_speed : Unix.file_descr -> speed -> unit val input : (string -> int) -> (Unix.file_descr -> unit) closure (** Buffered input. [input f] Returns a closure which must be called when