Emulation of LocalFileSystem with virtual COM.

Dependencies:   USBDevice

Dependents:   KL46Z-lpc81isp lpcterm2

#include "USBLocalFileSystem.h"

int main() {
    USBLocalFileSystem* usb_local = new USBLocalFileSystem(); // RamDisk(64KB)

    while(1) {
        usb_local->lock(true);
        usb_local->remount();
        char filename[32];
        if (usb_local->find(filename, sizeof(filename), "*.TXT")) {
            FILE* fp = fopen(filename, "r");
            if (fp) {
                int c;
                while((c = fgetc(fp)) != EOF) {
                    usb_local->putc(c);
                }
                fclose(fp);
            }
        }    
        usb_local->lock(false);

        wait_ms(1000*5);
    }
}



Sample application:

Import programKL46Z-lpc81isp

ISP example program.

Import programlpcterm2

semihost server example program

USBMSD2/USBMSD2.cpp

Committer:
va009039
Date:
2014-06-21
Revision:
6:528036abfb02
Parent:
4:8f6857784854

File content as of revision 6:528036abfb02:

/* Copyright (c) 2010-2011 mbed.org, MIT License
*
* Permission is hereby granted, free of charge, to any person obtaining a copy of this software
* and associated documentation files (the "Software"), to deal in the Software without
* restriction, including without limitation the rights to use, copy, modify, merge, publish,
* distribute, sublicense, and/or sell copies of the Software, and to permit persons to whom the
* Software is furnished to do so, subject to the following conditions:
*
* The above copyright notice and this permission notice shall be included in all copies or
* substantial portions of the Software.
*
* THE SOFTWARE IS PROVIDED "AS IS", WITHOUT WARRANTY OF ANY KIND, EXPRESS OR IMPLIED, INCLUDING
* BUT NOT LIMITED TO THE WARRANTIES OF MERCHANTABILITY, FITNESS FOR A PARTICULAR PURPOSE AND
* NONINFRINGEMENT. IN NO EVENT SHALL THE AUTHORS OR COPYRIGHT HOLDERS BE LIABLE FOR ANY CLAIM,
* DAMAGES OR OTHER LIABILITY, WHETHER IN AN ACTION OF CONTRACT, TORT OR OTHERWISE, ARISING FROM,
* OUT OF OR IN CONNECTION WITH THE SOFTWARE OR THE USE OR OTHER DEALINGS IN THE SOFTWARE.
*/

#include "stdint.h"
#include "USBMSD2.h"
#include "USB_MSD.h"
#include "USB_CDC.h"
#include "USB_HID.h"

#if (DEBUG2 > 3)
#define USB_DBG(...) do{fprintf(stderr,"[%s@%d] ",__PRETTY_FUNCTION__,__LINE__);fprintf(stderr,__VA_ARGS__);fprintf(stderr,"\r\n");} while(0);
#else
#define USB_DBG(...) while(0)
#endif

#define DEFAULT_CONFIGURATION (1)

USBMSD2::USBMSD2(uint16_t vendor_id, uint16_t product_id, uint16_t product_release) 
    : USBDevice(vendor_id, product_id, product_release)
{
    USB_DBG("%p vid=%04x pid=%04x", this, vendor_id, product_id);

    _msd = new USB_MSD(this, this);
    _cdc = new USB_CDC(this);
    _hid = new USB_HID(this);
}

USBMSD2::~USBMSD2() {
    _msd->disconnect();
    USBDevice::disconnect();
}

void USBMSD2::putc(int c)
{
    _cdc->putc(c);
}

int USBMSD2::getc()
{
    return _cdc->getc();
}

int USBMSD2::readable()
{
    return _cdc->readable();
}
    
int USBMSD2::writeable()
{
    return _cdc->writeable();
}

bool USBMSD2::readNB(HID_REPORT* report)
{
    return _hid->readNB(report);
}

bool USBMSD2::send(HID_REPORT* report)
{
    return _hid->send(report);
}

USB_MSD* USBMSD2::getMSD()
{
	return _msd;
}

USB_CDC* USBMSD2::getCDC()
{
	return _cdc;
}

USB_HID* USBMSD2::getHID()
{
	return _hid;
}

bool USBMSD2::connect()
{
    if (_msd->connect()) {
        USBDevice::connect();
        return true;
    }
    return false;
}

// Called in ISR context to process a class specific request
bool USBMSD2::USBCallback_request(void) {
    CONTROL_TRANSFER* transfer = getTransferPtr();
    if (_msd->Request_callback(transfer)) {
        return true;
    }
    if (_cdc->Request_callback(transfer)) {
        return true;
    }
    // Find the HID descriptor, after the configuration descriptor
    uint8_t* hidDescriptor = findDescriptor(HID_DESCRIPTOR);
    if (_hid->Request_callback(transfer, hidDescriptor)) {
        return true;
    }
    return false;
}

/* virtual */ void USBMSD2::USBCallback_requestCompleted(uint8_t* buf, uint32_t length)
{
    CONTROL_TRANSFER* transfer = getTransferPtr();
    if (_cdc->RequestCompleted_callback(transfer, buf, length)) {
        return;
    }    
}

// Called in ISR context
// Set configuration. Return false if the
// configuration is not supported.
bool USBMSD2::USBCallback_setConfiguration(uint8_t configuration) {
    if (configuration != DEFAULT_CONFIGURATION) {
        return false;
    }

    // Configure endpoints > 0
    addEndpoint(EPBULK_IN, MAX_PACKET_SIZE_EPBULK);
    addEndpoint(EPBULK_OUT, MAX_PACKET_SIZE_EPBULK);

    addEndpoint(CDC_EPINT_IN, MAX_PACKET_SIZE_EPINT);
    addEndpoint(CDC_EPBULK_IN, MAX_PACKET_SIZE_EPBULK);
    addEndpoint(CDC_EPBULK_OUT, MAX_PACKET_SIZE_EPBULK);
    addEndpoint(HID_EPINT_IN, MAX_PACKET_SIZE_EPINT);
    addEndpoint(HID_EPINT_OUT, MAX_PACKET_SIZE_EPINT);

    //activate readings
    readStart(EPBULK_OUT, MAX_PACKET_SIZE_EPBULK);
    readStart(CDC_EPBULK_OUT, MAX_PACKET_SIZE_EPBULK);
    readStart(HID_EPINT_OUT, MAX_PACKET_SIZE_EPINT);

    return true;
}

/* virtual */ bool USBMSD2::EP2_OUT_callback()
{
    return _msd->EPBULK_OUT_callback();
}

/* virtual */ bool USBMSD2::EP2_IN_callback()  {
    return _msd->EPBULK_IN_callback();
}

/* virtual */ bool USBMSD2::EP3_OUT_callback()
{
    return _cdc->EPBULK_OUT_callback();
}

/* virtual */ bool USBMSD2::EP5_OUT_callback()
{
    return _cdc->EPBULK_OUT_callback();
}

uint8_t * USBMSD2::deviceDesc() {
    static uint8_t deviceDescriptor[] = {
        18,                   // bLength
        1,                    // bDescriptorType
        0x10, 0x01,           // bcdUSB
        2,                    // bDeviceClass
        0,                    // bDeviceSubClass
        0,                    // bDeviceProtocol
        MAX_PACKET_SIZE_EP0,  // bMaxPacketSize0
        (uint8_t)(LSB(VENDOR_ID)), (uint8_t)(MSB(VENDOR_ID)),  // idVendor
        (uint8_t)(LSB(PRODUCT_ID)), (uint8_t)(MSB(PRODUCT_ID)),// idProduct
        0x00, 0x01,           // bcdDevice
        1,                    // iManufacturer
        2,                    // iProduct
        3,                    // iSerialNumber
        1                     // bNumConfigurations
    };
    return deviceDescriptor;
}

uint8_t * USBMSD2::stringIinterfaceDesc() {
    static uint8_t stringIinterfaceDescriptor[] = {
        0x08,               //bLength
        STRING_DESCRIPTOR,  //bDescriptorType 0x03
        'H',0,'I',0,'D',0,  //bString iInterface - HID
    };
    return stringIinterfaceDescriptor;
}

uint8_t * USBMSD2::stringIproductDesc() {
    static uint8_t stringIproductDescriptor[] = {
        32,                                                       //bLength
        STRING_DESCRIPTOR,                                        //bDescriptorType 0x03
        'K',0,'L',0,'2',0,'5',0,'Z',0,' ',0,'C',0,'M',0,'S',0,'I',0,'S',0,'-',0,'D',0,'A',0,'P',0 // KL25Z CMSIS-DAP
    };
    return stringIproductDescriptor;
}

uint8_t * USBMSD2::configurationDesc() {
    static uint8_t configDescriptor[] = {
        // Configuration 1
        9,      // bLength
        2,      // bDescriptorType
        LSB(122), // wTotalLength
        MSB(122),
        4,      // bNumInterfaces
        1,      // bConfigurationValue: 0x01 is used to select this configuration
        0x00,   // iConfiguration: no string to describe this configuration
        0x80,   // bmAttributes
        250,    // bMaxPower, device power consumption is 100 mA

        // Interface 0, Alternate Setting 0, MSC Class
        INTERFACE_DESCRIPTOR_LENGTH, // bLength
        INTERFACE_DESCRIPTOR,        // bDescriptorType
        0,      // bInterfaceNumber
        0,      // bAlternateSetting
        2,      // bNumEndpoints
        0x08,   // bInterfaceClass
        0x06,   // bInterfaceSubClass
        0x50,   // bInterfaceProtocol
        0x04,   // iInterface

        // endpoint descriptor, USB spec 9.6.6, page 269-271, Table 9-13
        ENDPOINT_DESCRIPTOR_LENGTH, // bLength
        ENDPOINT_DESCRIPTOR,        // bDescriptorType
        PHY_TO_DESC(EPBULK_IN),     // bEndpointAddress
        E_BULK,                     // bmAttributes (0x02=bulk)
        LSB(MAX_PACKET_SIZE_EPBULK),// wMaxPacketSize (LSB)
        MSB(MAX_PACKET_SIZE_EPBULK),// wMaxPacketSize (MSB)
        0,                          // bInterval

        // endpoint descriptor, USB spec 9.6.6, page 269-271, Table 9-13
        ENDPOINT_DESCRIPTOR_LENGTH, // bLength
        ENDPOINT_DESCRIPTOR,        // bDescriptorType
        PHY_TO_DESC(EPBULK_OUT),    // bEndpointAddress
        E_BULK,                     // bmAttributes (0x02=bulk)
        LSB(MAX_PACKET_SIZE_EPBULK),// wMaxPacketSize (LSB)
        MSB(MAX_PACKET_SIZE_EPBULK),// wMaxPacketSize (MSB)
        0,                          // bInterval

        // interface descriptor, USB spec 9.6.5, page 267-269, Table 9-12
        INTERFACE_DESCRIPTOR_LENGTH, // bLength
        INTERFACE_DESCRIPTOR,        // bDescriptorType
        1,                      // bInterfaceNumber
        0,                      // bAlternateSetting
        1,                      // bNumEndpoints
        0x02,                   // bInterfaceClass
        0x02,                   // bInterfaceSubClass
        0x01,                   // bInterfaceProtocol
        0,                      // iInterface

        // CDC Header Functional Descriptor, CDC Spec 5.2.3.1, Table 26
        5,                      // bFunctionLength
        0x24,                   // bDescriptorType
        0x00,                   // bDescriptorSubtype
        0x10, 0x01,             // bcdCDC

        // Call Management Functional Descriptor, CDC Spec 5.2.3.2, Table 27
        5,                      // bFunctionLength
        0x24,                   // bDescriptorType
        0x01,                   // bDescriptorSubtype
        0x03,                   // bmCapabilities
        2,                      // bDataInterface

        // Abstract Control Management Functional Descriptor, CDC Spec 5.2.3.3, Table 28
        4,                      // bFunctionLength
        0x24,                   // bDescriptorType
        0x02,                   // bDescriptorSubtype
        0x06,                   // bmCapabilities

        // Union Functional Descriptor, CDC Spec 5.2.3.8, Table 33
        5,                      // bFunctionLength
        0x24,                   // bDescriptorType
        0x06,                   // bDescriptorSubtype
        1,                      // bMasterInterface
        2,                      // bSlaveInterface0

        // endpoint descriptor, USB spec 9.6.6, page 269-271, Table 9-13
        ENDPOINT_DESCRIPTOR_LENGTH,     // bLength
        ENDPOINT_DESCRIPTOR,            // bDescriptorType
        PHY_TO_DESC(CDC_EPINT_IN),      // bEndpointAddress
        E_INTERRUPT,                    // bmAttributes (0x03=intr)
        LSB(MAX_PACKET_SIZE_EPINT),     // wMaxPacketSize (LSB)
        MSB(MAX_PACKET_SIZE_EPINT),     // wMaxPacketSize (MSB)
        2,                              // bInterval

        // interface descriptor, USB spec 9.6.5, page 267-269, Table 9-12
        INTERFACE_DESCRIPTOR_LENGTH, // bLength
        INTERFACE_DESCRIPTOR,        // bDescriptorType
        2,                          // bInterfaceNumber
        0,                          // bAlternateSetting
        2,                          // bNumEndpoints
        0x0A,                       // bInterfaceClass
        0x00,                       // bInterfaceSubClass
        0x00,                       // bInterfaceProtocol
        0,                          // iInterface

        // endpoint descriptor, USB spec 9.6.6, page 269-271, Table 9-13
        ENDPOINT_DESCRIPTOR_LENGTH, // bLength
        ENDPOINT_DESCRIPTOR,        // bDescriptorType
        PHY_TO_DESC(CDC_EPBULK_IN), // bEndpointAddress
        E_BULK,                     // bmAttributes (0x02=bulk)
        LSB(MAX_PACKET_SIZE_EPBULK),// wMaxPacketSize (LSB)
        MSB(MAX_PACKET_SIZE_EPBULK),// wMaxPacketSize (MSB)
        0,                          // bInterval

        // endpoint descriptor, USB spec 9.6.6, page 269-271, Table 9-13
        ENDPOINT_DESCRIPTOR_LENGTH, // bLength
        ENDPOINT_DESCRIPTOR,        // bDescriptorType
        PHY_TO_DESC(CDC_EPBULK_OUT),// bEndpointAddress
        E_BULK,                     // bmAttributes (0x02=bulk)
        LSB(MAX_PACKET_SIZE_EPBULK),// wMaxPacketSize (LSB)
        MSB(MAX_PACKET_SIZE_EPBULK),// wMaxPacketSize (MSB)
        0,                          // bInterval

        INTERFACE_DESCRIPTOR_LENGTH,    // bLength
        INTERFACE_DESCRIPTOR,           // bDescriptorType
        3,                              // bInterfaceNumber
        0,                              // bAlternateSetting
        2,                              // bNumEndpoints
        HID_CLASS,                      // bInterfaceClass
        HID_SUBCLASS_NONE,              // bInterfaceSubClass
        HID_PROTOCOL_NONE,              // bInterfaceProtocol
        0,                              // iInterface

        HID_DESCRIPTOR_LENGTH,          // bLength
        HID_DESCRIPTOR,                 // bDescriptorType
        LSB(HID_VERSION_1_11),          // bcdHID (LSB)
        MSB(HID_VERSION_1_11),          // bcdHID (MSB)
        0x00,                           // bCountryCode
        1,                              // bNumDescriptors
        REPORT_DESCRIPTOR,              // bDescriptorType
        LSB(_hid->reportDescLength()),  // wDescriptorLength (LSB)
        MSB(_hid->reportDescLength()),  // wDescriptorLength (MSB)

        ENDPOINT_DESCRIPTOR_LENGTH,     // bLength
        ENDPOINT_DESCRIPTOR,            // bDescriptorType
        PHY_TO_DESC(HID_EPINT_IN),      // bEndpointAddress
        E_INTERRUPT,                    // bmAttributes
        LSB(MAX_PACKET_SIZE_EPINT),     // wMaxPacketSize (LSB)
        MSB(MAX_PACKET_SIZE_EPINT),     // wMaxPacketSize (MSB)
        1,                              // bInterval (milliseconds)

        ENDPOINT_DESCRIPTOR_LENGTH,     // bLength
        ENDPOINT_DESCRIPTOR,            // bDescriptorType
        PHY_TO_DESC(HID_EPINT_OUT),     // bEndpointAddress
        E_INTERRUPT,                    // bmAttributes
        LSB(MAX_PACKET_SIZE_EPINT),     // wMaxPacketSize (LSB)
        MSB(MAX_PACKET_SIZE_EPINT),     // wMaxPacketSize (MSB)
        1,                              // bInterval (milliseconds)
    };
    return configDescriptor;
}