/* * tranzport 0.1 * oct 18, 2005 * arthur@artcmusic.com */ #include #include #include #include #include #include #include #include #include #define VENDORID 0x165b #define PRODUCTID 0x8101 #define READ_ENDPOINT 0x81 #define WRITE_ENDPOINT 0x02 enum { LIGHT_RECORD = 0, LIGHT_TRACKREC, LIGHT_TRACKMUTE, LIGHT_TRACKSOLO, LIGHT_ANYSOLO, LIGHT_LOOP, LIGHT_PUNCH }; #define BUTTONMASK_BATTERY 0x00004000 #define BUTTONMASK_BACKLIGHT 0x00008000 #define BUTTONMASK_TRACKLEFT 0x04000000 #define BUTTONMASK_TRACKRIGHT 0x40000000 #define BUTTONMASK_TRACKREC 0x00040000 #define BUTTONMASK_TRACKMUTE 0x00400000 #define BUTTONMASK_TRACKSOLO 0x00000400 #define BUTTONMASK_UNDO 0x80000000 #define BUTTONMASK_IN 0x02000000 #define BUTTONMASK_OUT 0x20000000 #define BUTTONMASK_PUNCH 0x00800000 #define BUTTONMASK_LOOP 0x00080000 #define BUTTONMASK_PREV 0x00020000 #define BUTTONMASK_ADD 0x00200000 #define BUTTONMASK_NEXT 0x00000200 #define BUTTONMASK_REWIND 0x01000000 #define BUTTONMASK_FASTFORWARD 0x10000000 #define BUTTONMASK_STOP 0x00010000 #define BUTTONMASK_PLAY 0x00100000 #define BUTTONMASK_RECORD 0x00000100 #define BUTTONMASK_SHIFT 0x08000000 #define STATUS_OFFLINE 0xff #define STATUS_ONLINE 0x01 #define STATUS_OK 0x00 struct tranzport_s { int *dev; int udev; }; typedef struct tranzport_s tranzport_t; void log_entry(FILE *fp, char *format, va_list ap) { vfprintf(fp, format, ap); fputc('\n', fp); } void log_error(char *format, ...) { va_list ap; va_start(ap, format); log_entry(stderr, format, ap); va_end(ap); } void vlog_error(char *format, va_list ap) { log_entry(stderr, format, ap); } void die(char *format, ...) { va_list ap; va_start(ap, format); vlog_error(format, ap); va_end(ap); exit(1); } tranzport_t *open_tranzport_core() { tranzport_t *z; int val; z = malloc(sizeof(tranzport_t)); if (!z) die("not enough memory"); memset(z, 0, sizeof(tranzport_t)); z->udev = open("/dev/tranzport0",O_RDWR); if (z->udev < 1) die("unable to open tranzport"); return z; } tranzport_t *open_tranzport() { return open_tranzport_core(); } void close_tranzport(tranzport_t *z) { int val; val = close(z->udev); if (val < 0) log_error("unable to release tranzport"); free(z); } int tranzport_write_core(tranzport_t *z, uint8_t *cmd, int timeout) { int val; val = write(z->udev, cmd, 8); if (val < 0) return val; if (val != 8) return -1; return 0; } int tranzport_lcdwrite(tranzport_t *z, uint8_t cell, char *text, int timeout) { uint8_t cmd[8]; if (cell > 9) { return -1; } cmd[0] = 0x00; cmd[1] = 0x01; cmd[2] = cell; cmd[3] = text[0]; cmd[4] = text[1]; cmd[5] = text[2]; cmd[6] = text[3]; cmd[7] = 0x00; return tranzport_write_core(z, cmd, timeout); } int tranzport_lighton(tranzport_t *z, uint8_t light, int timeout) { uint8_t cmd[8]; cmd[0] = 0x00; cmd[1] = 0x00; cmd[2] = light; cmd[3] = 0x01; cmd[4] = 0x00; cmd[5] = 0x00; cmd[6] = 0x00; cmd[7] = 0x00; return tranzport_write_core(z, &cmd[0], timeout); } int tranzport_lightoff(tranzport_t *z, uint8_t light, int timeout) { uint8_t cmd[8]; cmd[0] = 0x00; cmd[1] = 0x00; cmd[2] = light; cmd[3] = 0x00; cmd[4] = 0x00; cmd[5] = 0x00; cmd[6] = 0x00; cmd[7] = 0x00; return tranzport_write_core(z, &cmd[0], timeout); } int tranzport_read(tranzport_t *z, uint8_t *status, uint32_t *buttons, uint8_t *datawheel, int timeout) { uint8_t buf[8]; int val; memset(buf, 0xff, 8); val = read(z->udev, buf, 8); if (val < 0) { printf("errno: %d\n",errno); switch(errno) { case ENOENT: ; case ECONNRESET: ; case ESHUTDOWN: printf("dying\n"); exit(1); break; } return val; } if (val != 8) return -1; /*printf("read: %02x %02x %02x %02x %02x %02x %02x %02x\n", buf[0], buf[1], buf[2], buf[3], buf[4], buf[5], buf[6], buf[7]);*/ *status = buf[1]; *buttons = 0; *buttons |= buf[2] << 24; *buttons |= buf[3] << 16; *buttons |= buf[4] << 8; *buttons |= buf[5]; *datawheel = buf[6]; return 0; } void lights_core(tranzport_t *z, uint32_t buttons, uint32_t buttonmask, uint8_t light) { if (buttons & buttonmask) { if (buttons & BUTTONMASK_SHIFT) { tranzport_lightoff(z, light, 10); } else { tranzport_lighton(z, light, 10); } } } void do_lights(tranzport_t *z, uint32_t buttons) { lights_core(z, buttons, BUTTONMASK_RECORD, LIGHT_RECORD); lights_core(z, buttons, BUTTONMASK_TRACKREC, LIGHT_TRACKREC); lights_core(z, buttons, BUTTONMASK_TRACKMUTE, LIGHT_TRACKMUTE); lights_core(z, buttons, BUTTONMASK_TRACKSOLO, LIGHT_TRACKSOLO); lights_core(z, buttons, BUTTONMASK_TRACKSOLO, LIGHT_ANYSOLO); lights_core(z, buttons, BUTTONMASK_PUNCH, LIGHT_PUNCH); lights_core(z, buttons, BUTTONMASK_LOOP, LIGHT_LOOP); } void buttons_core(tranzport_t *z, uint32_t buttons, uint32_t buttonmask, char *str) { if (buttons & buttonmask) printf(" %s", str); } void do_buttons(tranzport_t *z, uint32_t buttons, uint8_t datawheel) { printf("buttons: %x ", buttons); buttons_core(z, buttons, BUTTONMASK_BATTERY, "battery"); buttons_core(z, buttons, BUTTONMASK_BACKLIGHT, "backlight"); buttons_core(z, buttons, BUTTONMASK_TRACKLEFT, "trackleft"); buttons_core(z, buttons, BUTTONMASK_TRACKRIGHT, "trackright"); buttons_core(z, buttons, BUTTONMASK_TRACKREC, "trackrec"); buttons_core(z, buttons, BUTTONMASK_TRACKMUTE, "trackmute"); buttons_core(z, buttons, BUTTONMASK_TRACKSOLO, "tracksolo"); buttons_core(z, buttons, BUTTONMASK_UNDO, "undo"); buttons_core(z, buttons, BUTTONMASK_IN, "in"); buttons_core(z, buttons, BUTTONMASK_OUT, "out"); buttons_core(z, buttons, BUTTONMASK_PUNCH, "punch"); buttons_core(z, buttons, BUTTONMASK_LOOP, "loop"); buttons_core(z, buttons, BUTTONMASK_PREV, "prev"); buttons_core(z, buttons, BUTTONMASK_ADD, "add"); buttons_core(z, buttons, BUTTONMASK_NEXT, "next"); buttons_core(z, buttons, BUTTONMASK_REWIND, "rewind"); buttons_core(z, buttons, BUTTONMASK_FASTFORWARD, "fastforward"); buttons_core(z, buttons, BUTTONMASK_STOP, "stop"); buttons_core(z, buttons, BUTTONMASK_PLAY, "play"); buttons_core(z, buttons, BUTTONMASK_RECORD, "record"); buttons_core(z, buttons, BUTTONMASK_SHIFT, "shift"); if (datawheel) printf(" datawheel=%02x", datawheel); printf("\n"); } void do_lcd(tranzport_t *z) { tranzport_lcdwrite(z, 0, " ", 10); tranzport_lcdwrite(z, 1, "DISL", 10); tranzport_lcdwrite(z, 2, "EXIA", 10); tranzport_lcdwrite(z, 3, " FOR", 10); tranzport_lcdwrite(z, 4, " ", 10); tranzport_lcdwrite(z, 5, " ", 10); tranzport_lcdwrite(z, 6, " CUR", 10); tranzport_lcdwrite(z, 7, "E FO", 10); tranzport_lcdwrite(z, 8, "UND ", 10); tranzport_lcdwrite(z, 9, " ", 10); } void do_lcd2(tranzport_t *z) { tranzport_lcdwrite(z, 0, "THE ", 10); tranzport_lcdwrite(z, 1, "TRAN", 10); tranzport_lcdwrite(z, 2, "ZPOR", 10); tranzport_lcdwrite(z, 3, "T RO", 10); tranzport_lcdwrite(z, 4, " KS", 10); tranzport_lcdwrite(z, 5, "AWES", 10); tranzport_lcdwrite(z, 6, "OMEE", 10); tranzport_lcdwrite(z, 7, "LEEE", 10); tranzport_lcdwrite(z, 8, "UND ", 10); tranzport_lcdwrite(z, 9, "GROK", 10); } int lights_off(tranzport_t *z) { static int i = 0; int j = 0; for(;j<2; j++,i = (i+1) % 7) { tranzport_lightoff(z, i, 10); } return 0; } int lights_on(tranzport_t *z) { static int i = 0; int j = 0; for(;j<2; j++,i = (i+1) % 7) { tranzport_lighton(z, i, 10); } return 0; } int main() { tranzport_t *z; uint8_t status; uint32_t buttons; uint8_t datawheel; int val; z = open_tranzport(); do_lcd(z); for(;;) { // do_lcd(z); lights_on(z); // do_lcd2(z); val = tranzport_read(z, &status, &buttons, &datawheel, 60000); if (val < 0) continue; if (status == STATUS_OFFLINE) { printf("offline: "); continue; } if (status == STATUS_ONLINE) { printf("online: "); do_lcd(z); } if (status == STATUS_OK) { printf("OK: "); do_lcd(z); } // do_lights(z, buttons); do_buttons(z, buttons, datawheel); lights_off(z); } close_tranzport(z); return 0; }