⭐ 欢迎来到虫虫下载站! | 📦 资源下载 📁 资源专辑 ℹ️ 关于我们
⭐ 虫虫下载站

📄 ser_avrdoper.c

📁 AVR Dopper Programmer
💻 C
📖 第 1 页 / 共 2 页
字号:
                            /* fprintf(stderr, "seen product ->%s<-\n", string); */                            if(strcmp(string, productName) == 0)                                break;                        }                    }                }                usb_close(handle);                handle = NULL;            }        }        if(handle)            break;    }    if(handle != NULL){        int rval, retries = 3;        if(usb_set_configuration(handle, 1)){            fprintf(stderr, "Warning: could not set configuration: %s\n", usb_strerror());        }        /* now try to claim the interface and detach the kernel HID driver on         * linux and other operating systems which support the call.         */        while((rval = usb_claim_interface(handle, 0)) != 0 && retries-- > 0){#ifdef LIBUSB_HAS_DETACH_KERNEL_DRIVER_NP            if(usb_detach_kernel_driver_np(handle, 0) < 0){                fprintf(stderr, "Warning: could not detach kernel HID driver: %s\n", usb_strerror());            }#endif        }        if(rval != 0)            fprintf(stderr, "Warning: could not claim interface\n");/* Continue anyway, even if we could not claim the interface. Control transfers * should still work. */        errorCode = 0;        *device = handle;        usesReportIDs = _usesReportIDs;    }    return errorCode;}/* ------------------------------------------------------------------------- */static void    usbCloseDevice(usbDevice_t *device){    if(device != NULL)        usb_close(device);}/* ------------------------------------------------------------------------- */static int usbSetReport(usbDevice_t *device, int reportType, char *buffer, int len){int bytesSent;    if(!usesReportIDs){        buffer++;   /* skip dummy report ID */        len--;    }    bytesSent = usb_control_msg(device, USB_TYPE_CLASS | USB_RECIP_INTERFACE | USB_ENDPOINT_OUT, USBRQ_HID_SET_REPORT, reportType << 8 | buffer[0], 0, buffer, len, 5000);    if(bytesSent != len){        if(bytesSent < 0)            fprintf(stderr, "Error sending message: %s\n", usb_strerror());        return USB_ERROR_IO;    }    return 0;}/* ------------------------------------------------------------------------- */static int usbGetReport(usbDevice_t *device, int reportType, int reportNumber, char *buffer, int *len){int bytesReceived, maxLen = *len;    if(!usesReportIDs){        buffer++;   /* make room for dummy report ID */        maxLen--;    }    bytesReceived = usb_control_msg(device, USB_TYPE_CLASS | USB_RECIP_INTERFACE | USB_ENDPOINT_IN, USBRQ_HID_GET_REPORT, reportType << 8 | reportNumber, 0, buffer, maxLen, 5000);    if(bytesReceived < 0){        fprintf(stderr, "Error sending message: %s\n", usb_strerror());        return USB_ERROR_IO;    }    *len = bytesReceived;    if(!usesReportIDs){        buffer[-1] = reportNumber;  /* add dummy report ID */        *len++;    }    return 0;}#endif  /* WIN32NATIVE *//* ------------------------------------------------------------------------ *//* ------------------------------------------------------------------------ *//* ------------------------------------------------------------------------ */#include "ser_avrdoper.h"#include "serial.h"#define USB_VENDOR_ID   0x16c0#define USB_PRODUCT_ID  0x05dfextern char *progname;extern int verbose;static usbDevice_t  *device = NULL;/* ------------------------------------------------------------------------- */static void dumpBlock(char *prefix, unsigned char *buf, int len){int i;    if(len <= 8){   /* more compact format for short blocks */        fprintf(stderr, "%s: %d bytes: ", prefix, len);        for(i = 0; i < len; i++){            fprintf(stderr, "%02x ", buf[i]);        }        fprintf(stderr, " \"");        for(i = 0; i < len; i++){            if(buf[i] >= 0x20 && buf[i] < 0x7f){                fputc(buf[i], stderr);            }else{                fputc('.', stderr);            }        }        fprintf(stderr, "\"\n");    }else{        fprintf(stderr, "%s: %d bytes:\n", prefix, len);        while(len > 0){            for(i = 0; i < 16; i++){                if(i < len){                    fprintf(stderr, "%02x ", buf[i]);                }else{                    fprintf(stderr, "   ");                }                if(i == 7)                    fputc(' ', stderr);            }            fprintf(stderr, "  \"");            for(i = 0; i < 16; i++){                if(i < len){                    if(buf[i] >= 0x20 && buf[i] < 0x7f){                        fputc(buf[i], stderr);                    }else{                        fputc('.', stderr);                    }                }            }            fprintf(stderr, "\"\n");            buf += 16;            len -= 16;        }    }}static char *usbErrorText(int usbErrno){static char buffer[32];    switch(usbErrno){        case USB_ERROR_NONE:    return "Success.";        case USB_ERROR_ACCESS:  return "Access denied.\nIf running on Linux, check /proc/bus/usb permissions.";        case USB_ERROR_NOTFOUND:return "Device not found.";        case USB_ERROR_BUSY:    return "Device is busy.";        case USB_ERROR_IO:      return "I/O Error.";        default:            sprintf(buffer, "Unknown error %d.", usbErrno);            return buffer;    }}/* ------------------------------------------------------------------------- */static int avrdoper_open(char *port, long baud){int rval;char *vname = "obdev.at";char *devname = "AVR-Doper";    if(device != NULL){ /* we support only one open device */        fprintf(stderr, "%s: avrdoper_open(): already open, only one open device supported!\n", progname);        exit(1);    }    rval = usbOpenDevice(&device, USB_VENDOR_ID, vname, USB_PRODUCT_ID, devname, 1);    if(rval != 0){        fprintf(stderr, "%s: avrdoper_open(): %s\n", progname, usbErrorText(rval));        exit(1);    }    return 0;}/* ------------------------------------------------------------------------- */static int avrdoper_setspeed(int fd, long baud){    /* dummy */    return 0;}/* ------------------------------------------------------------------------- */static void avrdoper_close(int fd){    if(device == NULL){        fprintf(stderr, "%s: avrdoper_close(): Device never opened (fd=%d)\n", progname, fd);        exit(1);    }    usbCloseDevice(device);    device = NULL;}/* ------------------------------------------------------------------------- */static int  reportDataSizes[4] = {13, 29, 61, 125};static int  chooseDataSize(int len){int i;    for(i = 0; i < sizeof(reportDataSizes)/sizeof(reportDataSizes[0]); i++){        if(reportDataSizes[i] >= len)            return i;    }    return i - 1;}static int avrdoper_send(int fd, unsigned char *buf, size_t buflen){    if(verbose > 3)        dumpBlock("Send", buf, buflen);    while(buflen > 0){        unsigned char buffer[256];        int rval, lenIndex = chooseDataSize(buflen);        int thisLen = buflen > reportDataSizes[lenIndex] ? reportDataSizes[lenIndex] : buflen;        buffer[0] = lenIndex + 1;   /* report ID */        buffer[1] = thisLen;        memcpy(buffer + 2, buf, thisLen);        if(verbose > 3)            fprintf(stderr, "Sending %d bytes data chunk\n", thisLen);        rval = usbSetReport(device, USB_HID_REPORT_TYPE_FEATURE, (char *)buffer, reportDataSizes[lenIndex] + 2);        if(rval != 0){            fprintf(stderr, "%s: avrdoper_send(): %s\n", progname, usbErrorText(rval));            exit(1);        }        buflen -= thisLen;        buf += thisLen;    }    return 0;}/* ------------------------------------------------------------------------- */static unsigned char    avrdoperRxBuffer[280];  /* buffer for receive data */static int              avrdoperRxLength = 0;   /* amount of valid bytes in rx buffer */static int              avrdoperRxPosition = 0; /* amount of bytes already consumed in rx buffer */static void avrdoperFillBuffer(void){int bytesPending = reportDataSizes[1];  /* guess how much data is buffered in device */    avrdoperRxPosition = avrdoperRxLength = 0;    while(bytesPending > 0){        int len, usbErr, lenIndex = chooseDataSize(bytesPending);        unsigned char buffer[128];        len = sizeof(avrdoperRxBuffer) - avrdoperRxLength;  /* bytes remaining */        if(reportDataSizes[lenIndex] + 2 > len) /* requested data would not fit into buffer */            break;        len = reportDataSizes[lenIndex] + 2;        usbErr = usbGetReport(device, USB_HID_REPORT_TYPE_FEATURE, lenIndex + 1, (char *)buffer, &len);        if(usbErr != 0){            fprintf(stderr, "%s: avrdoperFillBuffer(): %s\n", progname, usbErrorText(usbErr));            exit(1);        }        if(verbose > 3)            fprintf(stderr, "Received %d bytes data chunk of total %d\n", len - 2, buffer[1]);        len -= 2;   /* compensate for report ID and length byte */        bytesPending = buffer[1] - len; /* amount still buffered */        if(len > buffer[1])             /* cut away padding */            len = buffer[1];        if(avrdoperRxLength + len > sizeof(avrdoperRxBuffer)){            fprintf(stderr, "%s: avrdoperFillBuffer(): internal error: buffer overflow\n", progname);            exit(1);        }        memcpy(avrdoperRxBuffer + avrdoperRxLength, buffer + 2, len);        avrdoperRxLength += len;    }}static int avrdoper_recv(int fd, unsigned char *buf, size_t buflen){unsigned char   *p = buf;int             remaining = buflen;    while(remaining > 0){        int len, available = avrdoperRxLength - avrdoperRxPosition;        if(available <= 0){ /* buffer is empty */            avrdoperFillBuffer();            continue;        }        len = remaining < available ? remaining : available;        memcpy(p, avrdoperRxBuffer + avrdoperRxPosition, len);        p += len;        remaining -= len;        avrdoperRxPosition += len;    }    if(verbose > 3)        dumpBlock("Receive", buf, buflen);    return 0;}/* ------------------------------------------------------------------------- */static int avrdoper_drain(int fd, int display){    do{        avrdoperFillBuffer();    }while(avrdoperRxLength > 0);    return 0;}/* ------------------------------------------------------------------------- */struct serial_device avrdoper_serdev ={  .open = avrdoper_open,  .setspeed = avrdoper_setspeed,  .close = avrdoper_close,  .send = avrdoper_send,  .recv = avrdoper_recv,  .drain = avrdoper_drain,};#endif /* defined(HAVE_LIBUSB) || defined(WIN32NATIVE) */

⌨️ 快捷键说明

复制代码 Ctrl + C
搜索代码 Ctrl + F
全屏模式 F11
切换主题 Ctrl + Shift + D
显示快捷键 ?
增大字号 Ctrl + =
减小字号 Ctrl + -