From ad9fbc05e664d9e4028ec9c17fcc7308a4524114 Mon Sep 17 00:00:00 2001 From: Michael Gernoth Date: Sun, 6 Jun 2010 17:35:00 +0200 Subject: [PATCH 1/1] add small webserver "rigold", currently only serving the contents of the LCD --- commands.c | 14 ++--- commands.h | 1 + rigol.c | 2 + rigold.c | 150 +++++++++++++++++++++++++++++++++++++++++++++++++++++ usbtmc.c | 14 ++++- usbtmc.h | 2 + 6 files changed, 175 insertions(+), 8 deletions(-) diff --git a/commands.c b/commands.c index 75e76d0..83df9c4 100644 --- a/commands.c +++ b/commands.c @@ -106,15 +106,17 @@ void do_get_buf (struct usb_dev_handle *sc) usbtmc_sendscpi (sc, ":TIM:OFFSET 0", NULL, 0); } -static unsigned char* get_lcd(struct usb_dev_handle *sc, int *imglen) +unsigned char* get_lcd(struct usb_dev_handle *sc, int *imglen, int keylock) { unsigned char screen[320*234]; unsigned char *png; int l; - /* Hide "RMT" from screen */ - l = usbtmc_sendscpi(sc, ":KEY:LOCK DISABLE", NULL, 0); - usleep(20000); + if (keylock) { + /* Hide "RMT" from screen */ + l = usbtmc_sendscpi(sc, ":KEY:LOCK DISABLE", NULL, 0); + usleep(30000); + } l = usbtmc_sendscpi(sc, ":LCD:DATA?", screen, sizeof(screen)); @@ -137,7 +139,7 @@ void do_get_screen(struct usb_dev_handle *sc) int fd; pid_t display; - png = get_lcd(sc, &imglen); + png = get_lcd(sc, &imglen, 1); if (png == NULL) { perror("get_lcd"); return; @@ -186,7 +188,7 @@ void do_display_screen(struct usb_dev_handle *sc) int pipefd[2]; pid_t display; - png = get_lcd(sc, &imglen); + png = get_lcd(sc, &imglen, 1); if (png == NULL) { perror("get_lcd"); return; diff --git a/commands.h b/commands.h index 9d20fe8..ab013dc 100644 --- a/commands.h +++ b/commands.h @@ -2,3 +2,4 @@ void do_plot (struct usb_dev_handle *sc); void do_get_buf (struct usb_dev_handle *sc); void do_get_screen(struct usb_dev_handle *sc); void do_display_screen(struct usb_dev_handle *sc); +unsigned char* get_lcd(struct usb_dev_handle *sc, int *imglen, int keylock); diff --git a/rigol.c b/rigol.c index 6ae9d73..5dfec41 100644 --- a/rigol.c +++ b/rigol.c @@ -104,6 +104,7 @@ int main(int argc, char **argv) //Initialize scope sc = usbtmc_initscope(); + usbtmc_claim(sc); buff = malloc (1024*1024); if (buff == NULL) { perror("malloc"); @@ -165,6 +166,7 @@ int main(int argc, char **argv) //Disable keylock, so the user doesn't have to press the 'force'-button l=usbtmc_sendscpi(sc, ":KEY:LOCK DISABLE",NULL,0); + usbtmc_release(sc); usbtmc_close(sc); return 0; } diff --git a/rigold.c b/rigold.c index b32c474..4d4d0b3 100644 --- a/rigold.c +++ b/rigold.c @@ -1,12 +1,162 @@ +#include +#include +#include +#include +#include +#include +#include #include #include "usbtmc.h" +#include "commands.h" + +static int send_binary(int s, char *buf, int len) +{ + int ret; + + while(len > 0) { + ret = write(s, buf, len); + if (ret == -1) { + perror("write"); + return ret; + } + buf += ret; + len -= ret; + } + + return 0; +} + +static int send_text(int s, char *buf) +{ + return send_binary(s, buf, strlen(buf)); +} + +static void serve_index(int s) +{ + send_text(s, "HTTP/1.0 200 OK"); + send_text(s, "Content-type: text/html\n\n"); + send_text(s, "Rigol DS1000\n"); + send_text(s, "\n"); + send_text(s, "\n"); +} + +static void serve_lcd(int s, struct usb_dev_handle *sc) +{ + char buf[256]; + int imglen; + unsigned char *png; + + usbtmc_claim(sc); + png = get_lcd(sc, &imglen, 0); + usbtmc_release(sc); + + if (png == NULL) + return; + + + send_text(s, "HTTP/1.0 200 OK"); + send_text(s, "Content-type: image/png\n"); + snprintf(buf, sizeof(buf), "Content-length: %u\n\n", imglen); + send_text(s, buf); + send_binary(s, (char*)png, imglen); + free(png); +} + +static void parse_request(int s, struct usb_dev_handle *sc) +{ + int ret; + char buf[1024]; + char file[1024]; + const char delim[] = " \t\x0d\x0a"; + const char crlf[] = "\x0d\x0a"; + char *saveptr; + char *token; + + ret=read(s, buf, sizeof(buf)-1); + if (ret == -1) { + perror("read"); + return; + } + buf[ret] = 0; + + token = strtok_r(buf, delim, &saveptr); + /* TODO: Only GET... */ + token = strtok_r(NULL, delim, &saveptr); + bzero(&file, sizeof(file)); + strncpy(file, token, sizeof(file)-1); + + do { + token = strtok_r(NULL, crlf, &saveptr); + /* TODO: FIXME */ + #if 0 + if (token == NULL) { + ret=read(s, buf, sizeof(buf)-1); + if (ret == -1) { + perror("read"); + return; + } + buf[ret] = 0; + token = strtok_r(buf, crlf, &saveptr); + } + #endif + } while(token != NULL); + + if (strcmp("/", file) == 0) { + serve_index(s); + } else if (strcmp("/lcd.png", file) == 0) { + serve_lcd(s, sc); + } +} int main(int argc, char **argv) { + int sock, csock; + int opt; + socklen_t slen; struct usb_dev_handle *sc; + struct sockaddr_in sin, clientsin; + unsigned short port = 8888; sc = usbtmc_initscope(); + + if ((sock = socket(AF_INET, SOCK_STREAM, 0)) == -1) { + perror("socket"); + exit(EXIT_FAILURE); + } + + if (argc == 2) { + port=atoi(argv[1]); + } + + bzero(&sin, sizeof(sin)); + sin.sin_addr.s_addr=htonl(INADDR_ANY); + sin.sin_family=AF_INET; + sin.sin_port=htons(port); + + opt = 1; + setsockopt(sock, SOL_SOCKET, SO_REUSEADDR, &opt,sizeof(opt)); + + if (bind(sock, (struct sockaddr*)&sin, sizeof(sin)) == -1) { + perror("bind"); + exit(EXIT_FAILURE); + } + + listen(sock, 32); + printf("Listening on Port %u\n", port); + + while(1) { + bzero(&clientsin, sizeof(clientsin)); + slen = sizeof(clientsin); + if ((csock = accept(sock, (struct sockaddr*)&clientsin, &slen)) == -1) { + perror("accept"); + } + + parse_request(csock, sc); + + close(csock); + } + usbtmc_close(sc); return 0; } diff --git a/usbtmc.c b/usbtmc.c index d652494..8d05b09 100644 --- a/usbtmc.c +++ b/usbtmc.c @@ -103,6 +103,16 @@ int usbtmc_sendscpi(usb_dev_handle *dev, char* cmd, return 0; } +void usbtmc_claim(usb_dev_handle *sc) +{ + usb_claim_interface(sc, 0); +} + +void usbtmc_release(usb_dev_handle *sc) +{ + usb_release_interface(sc, 0); +} + //Initialize the scope. usb_dev_handle* usbtmc_initscope(void) { int r; @@ -119,10 +129,11 @@ usb_dev_handle* usbtmc_initscope(void) { } else { printf("Scope found.\n"); } - usb_claim_interface(dev,0); + usbtmc_claim(dev); //The following code isn't really necessary, the program works //OK without it too. r=usb_control_msg(dev, 0xC8, 9, 0, 0, (char*)buff, 4, 1000); + usbtmc_release(dev); if (r < 0) { fprintf (stderr, "Error %d sending init message: %s\n", r, strerror (-r)); @@ -138,6 +149,5 @@ usb_dev_handle* usbtmc_initscope(void) { void usbtmc_close(usb_dev_handle *sc) { //Free up and exit - usb_release_interface(sc,0); usb_close(sc); } diff --git a/usbtmc.h b/usbtmc.h index 175511e..a5ee8c8 100644 --- a/usbtmc.h +++ b/usbtmc.h @@ -1,3 +1,5 @@ int usbtmc_sendscpi(usb_dev_handle *dev, char* cmd, unsigned char *resp, int resplen); usb_dev_handle* usbtmc_initscope(void); void usbtmc_close(usb_dev_handle *sc); +void usbtmc_claim(usb_dev_handle *sc); +void usbtmc_release(usb_dev_handle *sc); -- 2.39.2