BaseUsbHost example program
Dependencies: BaseUsbHost FATFileSystem mbed mbed-rtos
Revision 3:6ae9a03a6145, committed 2013-01-06
- Comitter:
- va009039
- Date:
- Sun Jan 06 11:47:51 2013 +0000
- Parent:
- 2:c10029b87439
- Child:
- 4:41ff237a64ec
- Commit message:
- update library
Changed in this revision
--- a/BaseJpegDecode.lib Tue Dec 11 15:28:00 2012 +0000 +++ /dev/null Thu Jan 01 00:00:00 1970 +0000 @@ -1,1 +0,0 @@ -http://mbed.org/users/va009039/code/BaseJpegDecode/#e243fa781e5c
--- a/BaseUsbHost.lib Tue Dec 11 15:28:00 2012 +0000 +++ b/BaseUsbHost.lib Sun Jan 06 11:47:51 2013 +0000 @@ -1,1 +1,1 @@ -http://mbed.org/users/va009039/code/BaseUsbHost/#fe1e62051d88 +http://mbed.org/users/va009039/code/BaseUsbHost/#ae77d63a1eda
--- a/EthernetInterface.lib Tue Dec 11 15:28:00 2012 +0000 +++ /dev/null Thu Jan 01 00:00:00 1970 +0000 @@ -1,1 +0,0 @@ -http://mbed.org/users/mbed_official/code/EthernetInterface/#a0ee3ae75cfa
--- a/FATFileSystem.lib Tue Dec 11 15:28:00 2012 +0000 +++ b/FATFileSystem.lib Sun Jan 06 11:47:51 2013 +0000 @@ -1,1 +1,1 @@ -http://mbed.org/users/mbed_official/code/FATFileSystem/#b6669c987c8e +http://mbed.org/users/va009039/code/FATFileSystem/#86638c0f65b0
--- a/LifeCamVX700/LifeCamVX700.cpp Tue Dec 11 15:28:00 2012 +0000 +++ /dev/null Thu Jan 01 00:00:00 1970 +0000 @@ -1,99 +0,0 @@ -// LifeCamVX700.cpp 2012/12/10 -#include "mbed.h" -#include "rtos.h" -#include "BaseUsbHost.h" -#define DEBUG -#include "BaseUsbHostDebug.h" -#define TEST -#include "BaseUsbHostTest.h" -#include "LifeCamVX700.h" - -LifeCamVX700::LifeCamVX700(int frameIndex, uint32_t interval, ControlEp* ctlEp) -{ - uint8_t buf[26]; - - if (ctlEp == NULL) { // root hub - DBG_OHCI(LPC_USB->HcRhPortStatus1); - TEST_ASSERT_FALSE(LPC_USB->HcRhPortStatus1 & 0x200); - ctlEp = new ControlEp(); - TEST_ASSERT_TRUE(ctlEp); - } - bool r = check(ctlEp); - TEST_ASSERT(r); - m_ctlEp = ctlEp; - - int addr = m_ctlEp->GetAddr(); - m_isoEp = new IsochronousEp(addr, VX700_EN, VX700_MPS); - TEST_ASSERT_TRUE(m_isoEp); - - memset(buf, 0, 26); - buf[2] = VX700_MJPEG; - buf[3] = frameIndex; - *reinterpret_cast<uint32_t*>(buf+4) = interval; - - DBG_BYTES("SET_CUR Commit", buf, 26); - int rc = Control(SET_CUR, VS_COMMIT_CONTROL, 1, buf, 26); - TEST_ASSERT(rc == USB_OK); - - rc = Control(GET_CUR, VS_COMMIT_CONTROL, 1, buf, 26); - TEST_ASSERT(rc == USB_OK); - TEST_ASSERT_EQUAL(buf[2], VX700_MJPEG); - TEST_ASSERT_EQUAL(buf[3], frameIndex); - TEST_ASSERT_EQUAL(*reinterpret_cast<uint32_t*>(buf+4), interval); - DBG_BYTES("GET_CUR Commit", buf, 26); - - rc = m_ctlEp->SetConfiguration(1); - TEST_ASSERT_EQUAL(rc, USB_OK); - - int value; - rc = m_ctlEp->GetConfiguration(&value); - TEST_ASSERT_EQUAL(rc, USB_OK); - DBG("config: %d\n", value); - TEST_ASSERT_EQUAL(value, 1); - - rc = m_ctlEp->SetInterfaceAlternate(1, VX700_IF_ALT); // alt=1 packet size = 192 - TEST_ASSERT_EQUAL(rc, USB_OK); - - rc = m_ctlEp->GetInterface(1, &value); - TEST_ASSERT_EQUAL(rc, USB_OK); - DBG("alt: %d\n", value); - TEST_ASSERT_EQUAL(value, 1); - - for(int i = 0; i < 16; i++) { - report_cc_count[i] = 0; - report_ps_cc_count[i] = 0; - } - - LPC_USB->HcControl |= OR_CONTROL_PLE; // PeriodicListEnable - LPC_USB->HcControl |= OR_CONTROL_IE; // IsochronousEnable -} - -bool LifeCamVX700::check(ControlEp* ctlEp) -{ - if (ctlEp == NULL) { - return false; - } - uint8_t buf[18]; - int r = ctlEp->GetDescriptor(1, 0, buf, 8); - if (r != USB_OK) { - return false; - } - DBG_HEX(buf, 8); - const uint8_t desc[] = {0x12,0x01,0x00,0x02,0xef,0x02,0x01,0x40}; - if (memcmp(buf, desc, sizeof(desc)) != 0) { - return false; - } - r = ctlEp->GetDescriptor(1, 0, buf, 18); - if (r != USB_OK) { - return false; - } - DBG_HEX(buf, 18); - uint16_t vid = *reinterpret_cast<uint16_t*>(buf+8); - uint16_t pid = *reinterpret_cast<uint16_t*>(buf+10); - DBG("VID PID: %04X %04X\n", vid, pid); - if (vid == VX700_VID && pid == VX700_PID) { - return true; - } - return false; -} -
--- a/LifeCamVX700/LifeCamVX700.h Tue Dec 11 15:28:00 2012 +0000 +++ /dev/null Thu Jan 01 00:00:00 1970 +0000 @@ -1,25 +0,0 @@ -// LifeCamVX700.h 2012/12/5 -#ifndef LIFECAM_VX700_H -#define LIFECAM_VX700_H - -#define VX700_VID 0x045e -#define VX700_PID 0x074a - -#define VX700_160x120 5 -#define VX700_176x144 4 -#define VX700_320x240 3 -#define VX700_352x288 2 -#define VX700_640x480 1 - -#define VX700_MJPEG 1 - -#define VX700_EN 0x81 -#define VX700_MPS 128 -#define VX700_IF_ALT 1 - -class LifeCamVX700 : public BaseUvc{ -public: - LifeCamVX700(int frameIndex = VX700_160x120, uint32_t interval = _5FPS, ControlEp* ctlEp = NULL); - static bool check(ControlEp* ctlEp); -}; -#endif //LIFECAM_VX700_H
--- a/LogitechC270/LogitechC270.cpp Tue Dec 11 15:28:00 2012 +0000 +++ b/LogitechC270/LogitechC270.cpp Sun Jan 06 11:47:51 2013 +0000 @@ -1,4 +1,4 @@ -// LogitechC270.cpp 2012/12/11 +// LogitechC270.cpp 2013/1/3 #include "mbed.h" #include "rtos.h" #include "BaseUsbHost.h" @@ -8,7 +8,7 @@ #include "BaseUsbHostTest.h" #include "LogitechC270.h" -LogitechC270::LogitechC270(int frameIndex, uint32_t interval, ControlEp* ctlEp) +LogitechC270::LogitechC270(int formatIndex, int frameIndex, uint32_t interval, ControlEp* ctlEp) { uint8_t buf[26]; @@ -47,7 +47,7 @@ DBG_BYTES("GET_CUR Probe", buf, 26); memset(buf, 0, 26); - buf[2] = C270_MJPEG; + buf[2] = formatIndex; buf[3] = frameIndex; *reinterpret_cast<uint32_t*>(buf+4) = interval; @@ -57,7 +57,7 @@ rc = Control(GET_CUR, VS_COMMIT_CONTROL, 1, buf, 26); TEST_ASSERT(rc == USB_OK); - TEST_ASSERT_EQUAL(buf[2], C270_MJPEG); + TEST_ASSERT_EQUAL(buf[2], formatIndex); TEST_ASSERT_EQUAL(buf[3], frameIndex); TEST_ASSERT_EQUAL(*reinterpret_cast<uint32_t*>(buf+4), interval); DBG_BYTES("GET_CUR Commit", buf, 26);
--- a/LogitechC270/LogitechC270.h Tue Dec 11 15:28:00 2012 +0000 +++ b/LogitechC270/LogitechC270.h Sun Jan 06 11:47:51 2013 +0000 @@ -1,6 +1,5 @@ -// LogitechC270.h 2012/12/5 -#ifndef LOGITECH_C270_H -#define LOGITECH_C270_H +// LogitechC270.h 2013/1/6 +#pragma once #define C270_VID 0x046d #define C270_PID 0x0825 @@ -27,7 +26,6 @@ class LogitechC270 : public BaseUvc { public: - LogitechC270(int frameIndex = C270_160x120, uint32_t interval = _5FPS, ControlEp* ctlEp = NULL); + LogitechC270(int formatIndex = C270_MJPEG, int frameIndex = C270_160x120, uint32_t interval = _5FPS, ControlEp* ctlEp = NULL); static bool check(ControlEp* ctlEp); }; -#endif //LOGITECH_C270_H
--- a/Terminal.lib Tue Dec 11 15:28:00 2012 +0000 +++ /dev/null Thu Jan 01 00:00:00 1970 +0000 @@ -1,1 +0,0 @@ -http://mbed.org/users/cbayley/code/Terminal/#543e8e498e09
--- a/UsbFlashDrive/UsbFlashDrive.cpp Tue Dec 11 15:28:00 2012 +0000 +++ b/UsbFlashDrive/UsbFlashDrive.cpp Sun Jan 06 11:47:51 2013 +0000 @@ -1,4 +1,4 @@ -// UsbFlashDrive.cpp 2012/12/5 +// UsbFlashDrive.cpp 2013/1/5 #include "mbed.h" #include "rtos.h" #include "BaseUsbHost.h" @@ -6,15 +6,10 @@ #include "BaseUsbHostDebug.h" #define TEST #include "BaseUsbHostTest.h" - #include "UsbFlashDrive.h" //#define WRITE_PROTECT -int LE16(const uint8_t* d) -{ - return d[0] | (d[1] << 8); -} uint32_t BE32(uint8_t* d) { @@ -46,6 +41,8 @@ TEST_ASSERT_TRUE(ctlEp); } + CTASSERT(sizeof(CBW) == 31); + CTASSERT(sizeof(CSW) == 13); TEST_ASSERT(sizeof(CBW) == 31); TEST_ASSERT(sizeof(CSW) == 13); @@ -68,18 +65,48 @@ if (ctlEp == NULL) { return false; } - uint8_t buf[8]; - int rc = ctlEp->GetDescriptor(USB_DESCRIPTOR_TYPE_CONFIGURATION, 0, buf, sizeof(buf)); + CTASSERT(sizeof(StandardDeviceDescriptor) == 18); + CTASSERT(sizeof(StandardConfigurationDescriptor) == 9); + CTASSERT(sizeof(StandardInterfaceDescriptor) == 9); + TEST_ASSERT(sizeof(StandardDeviceDescriptor) == 18); + TEST_ASSERT(sizeof(StandardConfigurationDescriptor) == 9); + TEST_ASSERT(sizeof(StandardInterfaceDescriptor) == 9); + + StandardDeviceDescriptor desc; + int rc = ctlEp->GetDescriptor(USB_DESCRIPTOR_TYPE_DEVICE, 0, reinterpret_cast<uint8_t*>(&desc), sizeof(StandardDeviceDescriptor)); if (rc != USB_OK) { return false; } - DBG_BYTES("ConfigDescriptor 8bytes", buf, sizeof(buf)); - TEST_ASSERT(buf[0] == 9); - TEST_ASSERT(buf[1] == 0x02); - if (buf[4] != 0x01) { + if (desc.bDeviceClass == 8) { + return true; + } else if (desc.bDeviceClass != 0x00) { + return false; + } + uint8_t temp[4]; + rc = ctlEp->GetDescriptor(USB_DESCRIPTOR_TYPE_CONFIGURATION, 0, temp, sizeof(temp)); + if (rc != USB_OK) { return false; - } - return true; + } + StandardConfigurationDescriptor* cfg = reinterpret_cast<StandardConfigurationDescriptor*>(temp); + uint8_t* buf = new uint8_t[cfg->wTotalLength]; + + rc = ctlEp->GetDescriptor(USB_DESCRIPTOR_TYPE_CONFIGURATION, 0, buf, cfg->wTotalLength); + if (rc != USB_OK) { + return false; + } + DBG_HEX(buf, cfg->wTotalLength); + bool ret = false; + for(int pos = 0; pos < cfg->wTotalLength; pos += buf[pos]) { + StandardInterfaceDescriptor* desc = reinterpret_cast<StandardInterfaceDescriptor*>(buf+pos); + if (desc->bDescriptorType == 4) { // interface ? + if (desc->bInterfaceClass == 8 && desc->bInterfaceSubClass == 6 && desc->bInterfaceProtocol == 0x50) { + ret = true; + } + break; + } + } + delete[] buf; + return ret; } int UsbFlashDrive::disk_initialize() @@ -165,64 +192,38 @@ int UsbFlashDrive::ParseConfiguration(ControlEp* ctlEp) { - TEST_ASSERT(ctlEp); - int rc; - uint8_t ConfigDesc[9]; - int index = 0; - rc = ctlEp->GetDescriptor(USB_DESCRIPTOR_TYPE_CONFIGURATION, index, ConfigDesc, sizeof(ConfigDesc)); - TEST_ASSERT(rc == USB_OK); - DBG_BYTES("ConfigDescriptor 9bytes", ConfigDesc, sizeof(ConfigDesc)); - TEST_ASSERT(ConfigDesc[0] == 9); - TEST_ASSERT(ConfigDesc[1] == 0x02); - int wTotalLength = *((uint16_t*)&ConfigDesc[2]); - DBG("TotalLength: %d\n", wTotalLength); - int bConfigValue = ConfigDesc[5]; - TEST_ASSERT(bConfigValue == 1); - DBG("ConfigValue: %d\n", bConfigValue); - DBG("MaxPower: %d mA\n", ConfigDesc[8]*2); - - uint8_t* buf = new uint8_t[wTotalLength]; - TEST_ASSERT(buf); - rc = ctlEp->GetDescriptor(USB_DESCRIPTOR_TYPE_CONFIGURATION, index, buf, wTotalLength); - TEST_ASSERT(rc == USB_OK); - TEST_ASSERT(ConfigDesc[1] == 0x02); - for (int pos = 0; pos < wTotalLength; pos += buf[pos]) { - DBG_BYTES("CFG", buf+pos, buf[pos]); - int type = buf[pos+1]; - if (USB_DESCRIPTOR_TYPE_INTERFACE == type) { // 0x04 - DBG("InterfaceNumber: %d\n", buf[pos+2]); - DBG("AlternateSetting: %d\n", buf[pos+3]); - DBG("NumEndpoint: %d\n", buf[pos+4]); - DBG("InterfaceClass: %02X\n", buf[pos+5]); - DBG("InterfaceSubClass: %02X\n", buf[pos+6]); - DBG("InterfaceProtocol: %02X\n", buf[pos+7]); - TEST_ASSERT(buf[pos+6] == 0x06); // SCSI - TEST_ASSERT(buf[pos+7] == 0x50); // bulk only - } - if (USB_DESCRIPTOR_TYPE_ENDPOINT == type) { - TEST_ASSERT(buf[pos] == 7); - uint8_t att = buf[pos+3]; - if (att == 2) { // bulk - uint8_t ep = buf[pos+2]; - bool dir = ep & 0x80; // true=IN - uint16_t size = LE16(buf+pos+4); - DBG("EndpointAddress: %02X\n", ep); - DBG("Attribute: %02X\n", att); - DBG("MaxPacketSize: %d\n", size); - BulkEp* pEp = new BulkEp(ctlEp->GetAddr(), ep, size); - TEST_ASSERT(pEp); - if (dir) { - m_pEpBulkIn = pEp; - } else { - m_pEpBulkOut = pEp; - } - } - } - } - delete[] buf; - TEST_ASSERT(m_pEpBulkIn); - TEST_ASSERT(m_pEpBulkOut); - return 0; + TEST_ASSERT(ctlEp); + TEST_ASSERT(sizeof(StandardEndpointDescriptor) == 7); + uint8_t temp[4]; + int rc = ctlEp->GetDescriptor(USB_DESCRIPTOR_TYPE_CONFIGURATION, 0, temp, sizeof(temp)); + if (rc != USB_OK) { + return rc; + } + StandardConfigurationDescriptor* cfg = reinterpret_cast<StandardConfigurationDescriptor*>(temp); + uint8_t* buf = new uint8_t[cfg->wTotalLength]; + rc = ctlEp->GetDescriptor(USB_DESCRIPTOR_TYPE_CONFIGURATION, 0, buf, cfg->wTotalLength); + if (rc != USB_OK) { + return rc; + } + DBG_HEX(buf, cfg->wTotalLength); + for(int pos = 0; pos < cfg->wTotalLength; pos += buf[pos]) { + StandardEndpointDescriptor* desc = reinterpret_cast<StandardEndpointDescriptor*>(buf+pos); + if (desc->bDescriptorType == USB_DESCRIPTOR_TYPE_ENDPOINT) { + if (desc->bmAttributes == 2) { // bulk + BulkEp* pEp = new BulkEp(ctlEp->GetAddr(), desc->bEndpointAddress, desc->wMaxPacketSize); + if (desc->bEndpointAddress & 0x80) { + m_pEpBulkIn = pEp; + } else { + m_pEpBulkOut = pEp; + } + } + } + } + delete[] buf; + if (m_pEpBulkIn && m_pEpBulkOut) { + return USB_OK; + } + return USB_ERROR; } int UsbFlashDrive::BulkOnlyMassStorageReset(ControlEp* ctlEp)
--- a/UsbFlashDrive/UsbFlashDrive.h Tue Dec 11 15:28:00 2012 +0000 +++ b/UsbFlashDrive/UsbFlashDrive.h Sun Jan 06 11:47:51 2013 +0000 @@ -1,6 +1,5 @@ -// usbFlashDrive.h 2012/12/5 -#ifndef USB_FLASH_DRIVE_H -#define USB_FLASH_DRIVE_H +// usbFlashDrive.h 2013/1/5 +#pragma once #include "FATFileSystem.h" @@ -74,5 +73,3 @@ uint32_t m_report_disk_status; uint32_t m_report_disk_sync; }; - -#endif // USB_FLASH_DRIVE_H \ No newline at end of file
--- a/UsbMouseHost/UsbMouseHost.cpp Tue Dec 11 15:28:00 2012 +0000 +++ /dev/null Thu Jan 01 00:00:00 1970 +0000 @@ -1,59 +0,0 @@ -// UsbMouseHost.cpp 2012/12/5 -#include "mbed.h" -#include "rtos.h" -#include "BaseUsbHost.h" -#define DEBUG -#include "BaseUsbHostDebug.h" -#define TEST -#include "BaseUsbHostTest.h" -#include "UsbMouseHost.h" - -UsbMouseHost::UsbMouseHost(ControlEp* ctlEp) -{ - if (ctlEp == NULL) { // root hub - DBG_OHCI(LPC_USB->HcRhPortStatus1); - int lowSpeed = 0; - if (LPC_USB->HcRhPortStatus1 & 0x200) { - lowSpeed = 1; - } - ctlEp = new ControlEp(lowSpeed); - TEST_ASSERT_TRUE(ctlEp); - } - bool r = check(ctlEp); - TEST_ASSERT(r); - - int rc = ctlEp->SetConfiguration(1); - TEST_ASSERT_EQUAL(rc, USB_OK); - - int addr = ctlEp->GetAddr(); - int lowSpeed = ctlEp->GetLowSpeed(); - m_intEp = new InterruptEp(addr, 0x81, 8, lowSpeed); - TEST_ASSERT_TRUE(m_intEp); -} - -bool UsbMouseHost::check(ControlEp* ctlEp) -{ - if (ctlEp == NULL) { - return false; - } - uint8_t buf[8]; - int r = ctlEp->GetDescriptor(1, 0, buf, 8); - if (r != USB_OK) { - return false; - } - DBG_HEX(buf, 8); - if (buf[4] != 0x00) { // HID ? - return false; - } - return true; -} - -int UsbMouseHost::read(uint32_t* status, int millisec) -{ - int rc = m_intEp->interruptReceive(reinterpret_cast<uint8_t*>(status), 4, millisec); - if (rc < 0) { // error? - *status = 0x00000000; - return rc; - } - return USB_OK; -}
--- a/UsbMouseHost/UsbMouseHost.h Tue Dec 11 15:28:00 2012 +0000 +++ /dev/null Thu Jan 01 00:00:00 1970 +0000 @@ -1,14 +0,0 @@ -// UsbMouseHost.h 2012/12/5 -#ifndef USB_MOUSE_HOST_H -#define USB_MOUSE_HOST_H - -class UsbMouseHost { -public: - UsbMouseHost(ControlEp* ctlEp = NULL); - static bool check(ControlEp* ctlEp); - int read(uint32_t* status, int millisec=osWaitForever); - //ControlEp* m_ctlEp; - InterruptEp* m_intEp; -}; - -#endif //USB_MOUSE_HOST_H \ No newline at end of file
--- a/UvcCam/UvcCam.cpp Tue Dec 11 15:28:00 2012 +0000 +++ /dev/null Thu Jan 01 00:00:00 1970 +0000 @@ -1,566 +0,0 @@ -// UvcCam.cpp 2012/12/9 -#include "mbed.h" -#include "rtos.h" -#include "BaseUsbHost.h" -#define DEBUG -#include "BaseUsbHostDebug.h" -#define TEST -#include "BaseUsbHostTest.h" -#include "UvcCam.h" - -UvcCam::UvcCam(int formatIndex, int frameIndex, uint32_t interval, ControlEp* ctlEp) -{ - uint8_t buf[34]; - int rc; - int alt; - int cfg2; - - if (ctlEp == NULL) { // root hub - DBG_OHCI(LPC_USB->HcRhPortStatus1); - TEST_ASSERT_FALSE(LPC_USB->HcRhPortStatus1 & 0x200); - ctlEp = new ControlEp(); - TEST_ASSERT_TRUE(ctlEp); - } - bool r = check(ctlEp); - TEST_ASSERT(r); - m_ctlEp = ctlEp; - - UvcCfg* cfg = new UvcCfg(formatIndex, frameIndex, ctlEp); - TEST_ASSERT(cfg); - - int param_len = 34; - TEST_ASSERT(cfg->bcdUVC >= 0x0100); - if (cfg->bcdUVC == 0x0100) { // UVC ver. 1.0 - param_len = 26; - } - - int addr = m_ctlEp->GetAddr(); - m_isoEp = new IsochronousEp(addr, cfg->bEndpointAddress, cfg->wMaxPacketSize); - TEST_ASSERT_TRUE(m_isoEp); - -//#define USE_PROBE - -#ifdef USE_PROBE - rc = Control(GET_INFO, VS_PROBE_CONTROL, 1, buf, 1); - TEST_ASSERT(rc == USB_OK); - DBG_BYTES("GET_INFO Prob", buf, 1); - - rc = Control(GET_DEF, VS_PROBE_CONTROL, 1, buf, param_len); - TEST_ASSERT(rc == USB_OK); - DBG_BYTES("GET_DEF Probe", buf, param_len); - - rc = Control(GET_MIN, VS_PROBE_CONTROL, 1, buf, param_len); - TEST_ASSERT(rc == USB_OK); - DBG_BYTES("GET_MIN Probe", buf, param_len); - - rc = Control(GET_MAX, VS_PROBE_CONTROL, 1, buf, param_len); - TEST_ASSERT(rc == USB_OK); - DBG_BYTES("GET_MAX Probe", buf, param_len); - - rc = Control(GET_CUR, VS_PROBE_CONTROL, 1, buf, param_len); - TEST_ASSERT(rc == USB_OK); - DBG_BYTES("GET_CUR Probe", buf, param_len); -#endif // USE_PROBE - - rc = Control(GET_INFO, VS_COMMIT_CONTROL, 1, buf, 1); - TEST_ASSERT(rc == USB_OK); - DBG_BYTES("GET_INFO Commit", buf, 1); - - memset(buf, 0, param_len); - buf[2] = cfg->FormatIndex; - buf[3] = cfg->FrameIndex; - *reinterpret_cast<uint32_t*>(buf+4) = interval; - - DBG_BYTES("SET_CUR Commit", buf, param_len); - rc = Control(SET_CUR, VS_COMMIT_CONTROL, 1, buf, param_len); - TEST_ASSERT(rc == USB_OK); - - rc = Control(GET_CUR, VS_COMMIT_CONTROL, 1, buf, param_len); - TEST_ASSERT(rc == USB_OK); - TEST_ASSERT_EQUAL(buf[2], cfg->FormatIndex); - TEST_ASSERT_EQUAL(buf[3], cfg->FrameIndex); - TEST_ASSERT_EQUAL(*reinterpret_cast<uint32_t*>(buf+4), interval); - DBG_BYTES("GET_CUR Commit", buf, param_len); - - rc = m_ctlEp->GetConfiguration(&cfg2); - TEST_ASSERT_EQUAL(rc, USB_OK); - DBG("config: %d\n", cfg2); - - rc = m_ctlEp->SetConfiguration(1); - TEST_ASSERT_EQUAL(rc, USB_OK); - - rc = m_ctlEp->GetConfiguration(&cfg2); - TEST_ASSERT_EQUAL(rc, USB_OK); - DBG("config: %d\n", cfg2); - TEST_ASSERT_EQUAL(cfg2, 1); - - rc = m_ctlEp->GetInterface(cfg->bInterface, &alt); - TEST_ASSERT_EQUAL(rc, USB_OK); - DBG("alt: %d\n", alt); - - rc = m_ctlEp->SetInterfaceAlternate(cfg->bInterface, cfg->bAlternate); - TEST_ASSERT_EQUAL(rc, USB_OK); - - rc = m_ctlEp->GetInterface(cfg->bInterface, &alt); - TEST_ASSERT_EQUAL(rc, USB_OK); - DBG("alt: %d\n", alt); - TEST_ASSERT_EQUAL(alt, cfg->bAlternate); - delete cfg; - - for(int i = 0; i < 16; i++) { - report_cc_count[i] = 0; - report_ps_cc_count[i] = 0; - } - - LPC_USB->HcControl |= OR_CONTROL_PLE; // PeriodicListEnable - LPC_USB->HcControl |= OR_CONTROL_IE; // IsochronousEnable -} - -bool UvcCam::check(ControlEp* ctlEp) -{ - if (ctlEp == NULL) { - return false; - } - uint8_t buf[18]; - int r = ctlEp->GetDescriptor(1, 0, buf, 8); - if (r != USB_OK) { - return false; - } - DBG_HEX(buf, 8); - const uint8_t desc[] = {0x12,0x01,0x00,0x02,0xef,0x02,0x01}; - if (memcmp(buf, desc, sizeof(desc)) != 0) { - return false; - } - r = ctlEp->GetDescriptor(1, 0, buf, 18); - if (r != USB_OK) { - return false; - } - DBG_HEX(buf, 18); - return true; -} - -#define DESCRIPTOR_TYPE_DEVICE 1 -#define DESCRIPTOR_TYPE_CONFIGURATION 2 -#define DESCRIPTOR_TYPE_STRING 3 -#define DESCRIPTOR_TYPE_INTERFACE 4 -#define DESCRIPTOR_TYPE_ENDPOINT 5 - -#define DESCRIPTOR_TYPE_INTERFACE_ASSOCIATION 0x0b - -#define DESCRIPTOR_TYPE_HID 0x21 -#define DESCRIPTOR_TYPE_REPORT 0x22 -#define DESCRIPTOR_TYPE_PHYSICAL 0x23 -#define DESCRIPTOR_TYPE_CS_INTERFACE 0x24 -#define DESCRIPTOR_TYPE_CS_ENDPOINT 0x25 -#define DESCRIPTOR_TYPE_HUB 0x29 - -#define CLASS_AUDIO 0x02 -#define CLASS_HUB 0x09 - -#define IF_EQ_THEN_PRINTF(A,B) if (A == B) {VERBOSE("%s\n", #A); -#define ENDIF } - -#define CC_AUDIO 0x01 -#define SC_AUDIOCONTROL 0x01 -#define SC_AUDIOSTREAMING 0x02 - -#define AC_HEADER 0x01 -#define AC_INPUT_TERMINAL 0x02 -#define AC_OUTPUT_TERMINAL 0x03 -#define AC_FEATURE_UNIT 0x06 - -// Input Terminal Types -#define ITT_CAMERA 0x0201 - -static int LE16(const uint8_t* d) -{ - return d[0] | (d[1] << 8); -} - -static int LE24(const uint8_t* d) { - return d[0] | (d[1]<<8) | (d[2] << 16); -} - -static int LE32(const uint8_t* d) { - return d[0] |(d[1]<<8) | (d[2] << 16) |(d[3] << 24) ; -} - -UvcCfg::UvcCfg(int formatIndex, int frameIndex, ControlEp* ctlEp):wMaxPacketSize(0) -{ - TEST_ASSERT(ctlEp); - switch(formatIndex) { - case UVC_MJPEG: _payload = UVC_MJPEG; break; - case UVC_YUY2: _payload = UVC_YUY2; break; - default: _payload = UVC_MJPEG; break; - } - - switch(frameIndex) { - case UVC_160x120: _width = 160; _height = 120; break; - case UVC_176x144: _width = 176; _height = 144; break; - case UVC_320x176: _width = 320; _height = 176; break; - case UVC_320x240: _width = 320; _height = 240; break; - case UVC_352x288: _width = 352; _height = 288; break; - case UVC_432x240: _width = 432; _height = 240; break; - case UVC_640x480: _width = 640; _height = 480; break; - case UVC_544x288: _width = 544; _height = 288; break; - case UVC_640x360: _width = 640; _height = 360; break; - case UVC_752x416: _width = 752; _height = 416; break; - case UVC_800x448: _width = 800; _height = 448; break; - case UVC_800x600: _width = 800; _height = 600; break; - default: _width = 160; _height = 120; break; - } - int index = 0; - uint8_t temp[4]; - int rc = ctlEp->GetDescriptor(USB_DESCRIPTOR_TYPE_CONFIGURATION, index, temp, sizeof(temp)); - TEST_ASSERT(rc == USB_OK); - DBG_BYTES("Config Descriptor 4bytes", temp, sizeof(temp)); - TEST_ASSERT(temp[0] == 9); - TEST_ASSERT(temp[1] == 0x02); - int TotalLength = LE16(temp+2); - DBG("TotalLength: %d\n", TotalLength); - - uint8_t* buf = new uint8_t[TotalLength]; - TEST_ASSERT(buf); - rc = ctlEp->GetDescriptor(USB_DESCRIPTOR_TYPE_CONFIGURATION, index, buf, TotalLength); - TEST_ASSERT(rc == USB_OK); - if (rc != USB_OK) { - delete[] buf; - return; - } - _parserConfigurationDescriptor(buf, TotalLength); - delete[] buf; -} - -void UvcCfg::_parserAudioControl(uint8_t* buf, int len) { - int subtype = buf[2]; - IF_EQ_THEN_PRINTF(AC_HEADER, subtype) - VERBOSE("ADC: %04x\n", LE16(buf+3)); - VERBOSE("TotalLength: %d\n", LE16(buf+5)); - VERBOSE("InCollection: %d\n", buf[7]); - for (int n = 1; n <= buf[7]; n++) { - VERBOSE("aInterfaceNr(%d): %d\n", n, buf[8+n-1]); - } - ENDIF - IF_EQ_THEN_PRINTF(AC_INPUT_TERMINAL, subtype) - VERBOSE("TerminalID: %d\n", buf[3]); - VERBOSE("TerminalType: %04X\n", LE16(buf+4)); - VERBOSE("AssocTermianl: %d\n", buf[6]); - VERBOSE("NrChannels: %d\n", buf[7]); - ENDIF - IF_EQ_THEN_PRINTF(AC_OUTPUT_TERMINAL, subtype) - VERBOSE("TerminalID: %d\n", buf[3]); - VERBOSE("TerminalType: %04X\n", LE16(buf+4)); - VERBOSE("AssocTermianl: %d\n", buf[6]); - ENDIF - IF_EQ_THEN_PRINTF(AC_FEATURE_UNIT, subtype) - VERBOSE("UnitID: %d\n", buf[3]); - VERBOSE("SourceID: %d\n", buf[4]); - VERBOSE("ControlSize: %d\n", buf[5]); - ENDIF -} - -#define AS_GENERAL 0x01 -#define AS_FORMAT_TYPE 0x02 - -void UvcCfg::_parserAudioStream(uint8_t* buf, int len) { - int subtype = buf[2]; - IF_EQ_THEN_PRINTF(AS_GENERAL, subtype) - VERBOSE("TerminalLink: %d\n", buf[3]); - VERBOSE("Delay: %d\n", buf[4]); - VERBOSE("FormatTag: %04x\n", LE16(buf+5)); - ENDIF - IF_EQ_THEN_PRINTF(AS_FORMAT_TYPE, subtype) - VERBOSE("FormatType: %d\n", buf[3]); - VERBOSE("NrChannels: %d\n", buf[4]); - VERBOSE("SubFrameSize: %d\n", buf[5]); - VERBOSE("BitResolution: %d\n", buf[6]); - VERBOSE("SamFreqType: %d\n", buf[7]); - VERBOSE("SamFreq(1): %d\n", LE24(buf+8)); - ENDIF -} - -#define CC_VIDEO 0x0e - -#define SC_VIDEOCONTROL 0x01 -#define SC_VIDEOSTREAMING 0x02 - -#define VC_HEADER 0x01 -#define VC_INPUT_TERMINAL 0x02 -#define VC_OUTPUT_TERMINAL 0x03 -#define VC_SELECTOR_UNIT 0x04 -#define VC_PROCESSING_UNIT 0x05 -#define VC_EXTENSION_UNIT 0x06 - -void UvcCfg::_parserVideoControl(uint8_t* buf, int len) { - int subtype = buf[2]; - IF_EQ_THEN_PRINTF(VC_HEADER, subtype) - bcdUVC = LE16(buf+3); - VERBOSE("UVC: %04x\n", bcdUVC); - VERBOSE("TotalLength: %d\n", LE16(buf+5)); - VERBOSE("ClockFrequency: %d\n", LE32(buf+7)); - VERBOSE("InCollection: %d\n", buf[11]); - VERBOSE("aInterfaceNr(1): %d\n", buf[12]); - ENDIF - IF_EQ_THEN_PRINTF(VC_INPUT_TERMINAL, subtype) - VERBOSE("TerminalID: %d\n", buf[3]); - uint16_t tt = LE16(buf+4); - VERBOSE("TerminalType: %04X\n", tt); - VERBOSE("AssocTerminal: %d\n", buf[6]); - VERBOSE("Terminal: %d\n", buf[7]); - if (tt == ITT_CAMERA) { // camera - int bControlSize = buf[14]; - VERBOSE("ControlSize: %d\n", bControlSize); - for(int i = 0; i < bControlSize; i++) { - uint8_t bControls = buf[15+i]; - VERBOSE("Controls(%d): %02X\n", i, bControls); - } - } - ENDIF - IF_EQ_THEN_PRINTF(VC_OUTPUT_TERMINAL, subtype) - VERBOSE("TerminalID: %d\n", buf[3]); - VERBOSE("TerminalType: %04X\n", LE16(buf+4)); - VERBOSE("AssocTerminal: %d\n", buf[6]); - VERBOSE("SourceID: %d\n", buf[7]); - VERBOSE("Terminal: %d\n", buf[8]); - ENDIF - IF_EQ_THEN_PRINTF(VC_SELECTOR_UNIT, subtype) - VERBOSE("UnitID: %d\n", buf[3]); - ENDIF - IF_EQ_THEN_PRINTF(VC_PROCESSING_UNIT, subtype) - VERBOSE("UnitID: %d\n", buf[3]); - VERBOSE("SourceID: %d\n", buf[4]); - VERBOSE("MaxMultiplier: %d\n", LE16(buf+5)); - VERBOSE("ControlSize: %d\n", buf[7]); - int pos = 8; - for (int n = 1; n <= buf[7]; n++) { - VERBOSE("Controls(%d): %02X\n", n , buf[pos]); - pos++; - } - VERBOSE("Processing: %d\n", buf[pos]); - pos++; - VERBOSE("VideoStanders: %02X\n", buf[pos]); - ENDIF - IF_EQ_THEN_PRINTF(VC_EXTENSION_UNIT, subtype) - VERBOSE("UnitID: %d\n", buf[3]); - ENDIF -} - -#define VS_INPUT_HEADER 0x01 -#define VS_STILL_FRAME 0x03 -#define VS_FORMAT_UNCOMPRESSED 0x04 -#define VS_FRAME_UNCOMPRESSED 0x05 -#define VS_FORMAT_MJPEG 0x06 -#define VS_FRAME_MJPEG 0x07 -#define VS_COLOR_FORMAT 0x0d - -void UvcCfg::_parserVideoStream(uint8_t* buf, int len) { - int subtype = buf[2]; - IF_EQ_THEN_PRINTF(VS_INPUT_HEADER, subtype) - VERBOSE("NumFormats: %d\n", buf[3]); - VERBOSE("TotalLength: %d\n", LE16(buf+4)); - VERBOSE("EndpointAddress: %02X\n", buf[6]); - VERBOSE("Info: %02X\n", buf[7]); - VERBOSE("TerminalLink: %d\n", buf[8]); - VERBOSE("StillCaptureMethod: %d\n", buf[9]); - VERBOSE("TriggerSupport: %d\n", buf[10]); - VERBOSE("TriggerUsage: %d\n", buf[11]); - VERBOSE("ControlSize: %d\n", buf[12]); - int pos = 13; - for (int n = 1; n <= buf[12]; n++) { - VERBOSE("Controls(%d): %02X\n", n, buf[pos]); - pos++; - } - bEndpointAddress = buf[6]; - ENDIF - IF_EQ_THEN_PRINTF(VS_STILL_FRAME, subtype) - VERBOSE("EndpointAdress: %02X\n", buf[3]); - VERBOSE("NumImageSizePatterns: %d\n", buf[4]); - int ptn = buf[4]; - int pos = 5; - for (int n = 1; n <= ptn; n++) { - VERBOSE("Width(%d): %d\n", n, LE16(buf+pos)); - VERBOSE("Height(%d): %d\n", n, LE16(buf+pos+2)); - pos += 4; - } - VERBOSE("NumCompressPtn: %d\n", buf[pos]); - ptn = buf[pos++]; - for (int n = 1; n <= ptn; n++) { - VERBOSE("Compress(%d): %d\n", n, buf[pos]); - pos++; - } - ENDIF - IF_EQ_THEN_PRINTF(VS_FORMAT_UNCOMPRESSED, subtype) - VERBOSE("FormatIndex: %d\n", buf[3]); - VERBOSE("NumFrameDescriptors: %d\n", buf[4]); - uint32_t guid = LE32(buf+5); - if (guid == 0x32595559) { - VERBOSE("GUID: YUY2\n"); - } else if (guid == 0x3231564e) { - VERBOSE("GUID: NV12\n"); - } else { - VERBOSE("GUID: %08x\n", guid); - } - VERBOSE("DefaultFrameIndex: %d\n", buf[22]); - if (_payload == UVC_YUY2) { - FormatIndex = buf[3]; - } - ENDIF - IF_EQ_THEN_PRINTF(VS_FRAME_UNCOMPRESSED, subtype) - VERBOSE("FrameIndex: %d\n", buf[3]); - VERBOSE("Capabilites: %d\n", buf[4]); - VERBOSE("Width: %d\n", LE16(buf+5)); - VERBOSE("Height: %d\n", LE16(buf+7)); - VERBOSE("MinBitRate: %d\n", LE32(buf+9)); - VERBOSE("MaxBitRate: %d\n", LE32(buf+13)); - VERBOSE("MaxVideoFrameBufferSize: %d\n", LE32(buf+17)); - VERBOSE("DefaultFrameInterval: %d\n", LE32(buf+21)); - VERBOSE("FrameIntervalType: %d\n", buf[25]); - int it = buf[25]; - uint32_t max_fi = 333333; // 30.0fps - if (it == 0) { - VERBOSE("FrameMinInterval: %d\n", buf[26]); - VERBOSE("FrameMaxInterval: %d\n", buf[30]); - VERBOSE("FrameIntervalStep: %d\n", buf[34]); - } else { - int pos = 26; - for (int n = 1; n <= it; n++) { - uint32_t fi = LE32(buf+pos); - if (fi >= max_fi) { - max_fi = fi; - } - float fps = 1e+7 / fi; - VERBOSE("FrameInterval(%u): %d (%.1f fps)\n", n, fi, fps); - pos += 4; - } - } - if (_payload == UVC_YUY2) { - if (_width == LE16(buf+5) && _height == LE16(buf+7)) { - FrameIndex = buf[3]; - } - if (dwFrameInterval == 0) { - dwFrameInterval = max_fi; - } - } - ENDIF - IF_EQ_THEN_PRINTF(VS_FORMAT_MJPEG, subtype) - VERBOSE("FormatIndex: %d\n", buf[3]); - VERBOSE("NumFrameDescriptors: %d\n", buf[4]); - VERBOSE("Flags: %d\n", buf[5]); - VERBOSE("DefaultFrameIndex: %d\n", buf[6]); - if (_payload == UVC_MJPEG) { - FormatIndex = buf[3]; - } - ENDIF - IF_EQ_THEN_PRINTF(VS_FRAME_MJPEG, subtype) - VERBOSE("FrameIndex: %d\n", buf[3]); - VERBOSE("Capabilites: %d\n", buf[4]); - VERBOSE("Width: %d\n", LE16(buf+5)); - VERBOSE("Height: %d\n", LE16(buf+7)); - VERBOSE("MinBitRate: %d\n", LE32(buf+9)); - VERBOSE("MaxBitRate: %d\n", LE32(buf+13)); - VERBOSE("MaxVideoFrameBufferSize: %d\n", LE32(buf+17)); - VERBOSE("DefaultFrameInterval: %d\n", LE32(buf+21)); - VERBOSE("FrameIntervalType: %d\n", buf[25]); - int it = buf[25]; - uint32_t max_fi = 333333; // 30.0fps - if (it == 0) { - VERBOSE("FrameMinInterval: %d\n", buf[26]); - VERBOSE("FrameMaxInterval: %d\n", buf[30]); - VERBOSE("FrameIntervalStep: %d\n", buf[34]); - } else { - int pos = 26; - for (int n = 1; n <= it; n++) { - uint32_t fi = LE32(buf+pos); - if (fi >= max_fi) { - max_fi = fi; - } - float fps = 1e+7 / fi; - VERBOSE("FrameInterval(%u): %d (%.1f fps)\n", n, fi, fps); - pos += 4; - } - } - if (_payload == UVC_MJPEG) { - if (_width == LE16(buf+5) && _height == LE16(buf+7)) { - FrameIndex = buf[3]; - } - if (dwFrameInterval == 0) { - dwFrameInterval = max_fi; - } - } - ENDIF - IF_EQ_THEN_PRINTF(VS_COLOR_FORMAT, subtype) - ENDIF -} - -void UvcCfg::_parserConfigurationDescriptor(uint8_t* buf, int len) { - int pos = 0; - _IfClass = 0; - _IfSubClass = 0; - while (pos < len) { - int type = buf[pos+1]; - //DBG_BYTES(TYPE_Str(type), buf+pos, buf[pos]); - IF_EQ_THEN_PRINTF(DESCRIPTOR_TYPE_CONFIGURATION, type) - VERBOSE("NumInterfaces: %d\n", buf[pos+4]); - ENDIF - IF_EQ_THEN_PRINTF(DESCRIPTOR_TYPE_INTERFACE_ASSOCIATION, type) - VERBOSE("FirstInterface: %d\n", buf[pos+2]); - VERBOSE("InterfaceCount: %d\n", buf[pos+3]); - VERBOSE("FunctionClass: %02X\n", buf[pos+4]); - VERBOSE("FunctionSubClass: %02X\n", buf[pos+5]); - VERBOSE("FunctionProtocol: %02X\n", buf[pos+6]); - VERBOSE("Function: %d\n", buf[pos+7]); - ENDIF - IF_EQ_THEN_PRINTF(DESCRIPTOR_TYPE_INTERFACE,type) - VERBOSE("InterfaceNumber: %d\n", buf[pos+2]); - VERBOSE("AlternateSetting: %d\n", buf[pos+3]); - VERBOSE("NumEndpoint: %d\n", buf[pos+4]); - VERBOSE("InterfaceClass: %02X\n", buf[pos+5]); - VERBOSE("InterfaceSubClass: %02X\n", buf[pos+6]); - VERBOSE("InterfaceProtocol: %02X\n", buf[pos+7]); - VERBOSE("Interface: %d\n", buf[pos+8]); - _If = buf[pos+2]; - _Ifalt = buf[pos+3]; - _IfClass = buf[pos+5]; - _IfSubClass = buf[pos+6]; - ENDIF - IF_EQ_THEN_PRINTF(DESCRIPTOR_TYPE_ENDPOINT, type) - VERBOSE("EndpointAddress: %02X\n", buf[pos+2]); - VERBOSE("Attributes: %02X\n", buf[pos+3]); - VERBOSE("MaxPacketSize: %d\n", LE16(buf+pos+4)); - VERBOSE("Interval: %d\n", buf[pos+6]); - if (_IfClass == CC_VIDEO && _IfSubClass == SC_VIDEOSTREAMING) { - if (bEndpointAddress == buf[pos+2]) { - if (wMaxPacketSize == 0) { - wMaxPacketSize = LE16(buf+pos+4); - } - if (wMaxPacketSize == LE16(buf+pos+4)) { - bInterface = _If; - bAlternate = _Ifalt; - } - } - } - ENDIF - IF_EQ_THEN_PRINTF(DESCRIPTOR_TYPE_CS_INTERFACE, type) - IF_EQ_THEN_PRINTF(CC_VIDEO, _IfClass) - IF_EQ_THEN_PRINTF(SC_VIDEOCONTROL, _IfSubClass) - _parserVideoControl(buf+pos, buf[pos]); - ENDIF - IF_EQ_THEN_PRINTF(SC_VIDEOSTREAMING, _IfSubClass) - _parserVideoStream(buf+pos, buf[pos]); - ENDIF - ENDIF - IF_EQ_THEN_PRINTF(CC_AUDIO, _IfClass) - IF_EQ_THEN_PRINTF(SC_AUDIOCONTROL, _IfSubClass) - _parserAudioControl(buf+pos, buf[pos]); - ENDIF - IF_EQ_THEN_PRINTF(SC_AUDIOSTREAMING, _IfSubClass) - _parserAudioStream(buf+pos, buf[pos]); - ENDIF - ENDIF - ENDIF - IF_EQ_THEN_PRINTF(DESCRIPTOR_TYPE_HUB, type) - ENDIF - pos += buf[pos]; - } -} -
--- a/UvcCam/UvcCam.h Tue Dec 11 15:28:00 2012 +0000 +++ /dev/null Thu Jan 01 00:00:00 1970 +0000 @@ -1,55 +0,0 @@ -// UvcCam.h 2012/12/9 -#ifndef UVC_CAM_H -#define UVC_CAM_H - -#define UVC_160x120 2 -#define UVC_176x144 3 -#define UVC_320x176 4 -#define UVC_320x240 5 -#define UVC_352x288 6 -#define UVC_432x240 7 -#define UVC_640x480 1 -#define UVC_544x288 8 -#define UVC_640x360 9 -#define UVC_752x416 10 -#define UVC_800x448 11 -#define UVC_800x600 12 - -#define UVC_MJPEG 2 -#define UVC_YUY2 1 - -#define VERBOSE(...) do{printf(__VA_ARGS__);} while(0); - -class UvcCam : public BaseUvc { -public: - UvcCam(int formatIndex = UVC_MJPEG, int frameIndex = UVC_160x120, uint32_t interval = _5FPS, ControlEp* ctlEp = NULL); - static bool check(ControlEp* ctlEp); -}; - -class UvcCfg { -public: - UvcCfg(int formatIndex, int frameIndex, ControlEp* ctlEp); - uint8_t bEndpointAddress; - uint16_t wMaxPacketSize; - uint8_t FormatIndex; - uint8_t FrameIndex; - uint32_t dwFrameInterval; - uint8_t bInterface; - uint8_t bAlternate; - uint16_t bcdUVC; -protected: - void _parserAudioControl(uint8_t* buf, int len); - void _parserAudioStream(uint8_t* buf, int len); - void _parserVideoControl(uint8_t* buf, int len); - void _parserVideoStream(uint8_t* buf, int len); - void _parserConfigurationDescriptor(uint8_t* buf, int len); - uint16_t _width; - uint16_t _height; - uint8_t _payload; - int _If; - int _Ifalt; - int _IfClass; - int _IfSubClass; -}; - -#endif //UVC_CAM_H
--- a/example2_LogitechC270.cpp Tue Dec 11 15:28:00 2012 +0000 +++ /dev/null Thu Jan 01 00:00:00 1970 +0000 @@ -1,178 +0,0 @@ -#if 1 -// example2_LogitechC270.cpp -// -// simple color tracking -// -#include "mbed.h" -#include "rtos.h" -#include "BaseUsbHost.h" -#include "LogitechC270.h" -#include "UvcCam.h" -#include "BaseJpegDecode.h" -#include "Terminal.h" -#include "MyThread.h" - -// Logitech C270 -#define WIDTH 160 -#define HEIGHT 120 - -#define THRESHOLD 200 - -DigitalOut led1(LED1), led2(LED2), led3(LED3), led4(LED4); -Terminal term(USBTX, USBRX); - -class CalcCenter : public MyThread, public BaseJpegDecode { -public: - int y_center, x_center; - int m_x_sum, m_y_sum, m_sum; - uint32_t EOI_count; - int16_t buf_Cb[WIDTH/16*HEIGHT/8]; // debug - int16_t buf_Cr[WIDTH/16*HEIGHT/8]; // debug - CalcCenter(BaseUvc* cam) { - m_cam = cam; - m_cam->setOnResult(this, &CalcCenter::callback_motion_jpeg); - EOI_count = 0; - } -protected: - void callback_motion_jpeg(uint16_t frame, uint8_t* buf, int len) { - input(buf+12, len-12); - if (buf[1]&1) { // FID - led1 = !led1; - } - } - - virtual void outputDC(int mcu, int block, int value) { - if (mcu >= (WIDTH/16*HEIGHT/8)) { - return; - } - if (block == 2) { - buf_Cb[mcu] = value * qt[1][0]; - } else if (block == 3) { // 0-1:Y 2:Cb 3:Cr - buf_Cr[mcu] = value * qt[1][0]; - value *= qt[1][0]; - if (value >= THRESHOLD) { // red - m_x_sum += value*(mcu%(WIDTH/16)); - m_y_sum += value*(mcu/(WIDTH/16)); - m_sum += value; - } - } - } - virtual void outputAC(int mcu, int block, int scan, int value){}; - virtual void outputMARK(uint8_t c){ - if (c == 0xd9) { // EOI - if(m_sum == 0) { - x_center = y_center = -1; // not found - } else { - x_center = m_x_sum / m_sum; - y_center = m_y_sum / m_sum; - } - m_x_sum = m_y_sum = m_sum = 0; // reset - EOI_count++; - led3 = !led3; - } - } - - virtual void run() { - while(true) { - if (m_cam) { - m_cam->poll(); - } - } - } - BaseUvc* m_cam; -}; - -BaseUvc* cam = NULL; -CalcCenter* calc = NULL; - -#define PI 3.14159265 - -class display_Thread : public MyThread { - virtual void run() { - term.cls(); - int fg, old_fg = 0xffffff; - while(1) { - int column = 0; - for(int y = 0; y < HEIGHT/8; y++) { - term.locate(0, column++); - for(int x = 0; x < WIDTH/16; x++) { - int value = calc->buf_Cr[y*WIDTH/16+x]; - if (value >= THRESHOLD) { - fg = 0xff0000; // red - } else { - fg = 0xffffff; // white - } - if (fg != old_fg) { - term.foreground(fg); - old_fg = fg; - } - term.printf("%+4d,", value); - } - } - term.locate(0, column++); - term.printf("Cr:(%d,%d)", calc->x_center, calc->y_center); -#if 0 - for(int y = 0; y < HEIGHT/8; y++) { - term.locate(0, column++); - for(int x = 0; x < WIDTH/16; x++) { - float Cb = calc->buf_Cb[y*WIDTH/16+x]; - float Cr = calc->buf_Cr[y*WIDTH/16+x]; - float value; - if (Cb == 0.0) { - value = 0.0; - } else { - value = (atan(Cr / Cb) + PI/2.0)* 360.0 / PI; - } - term.printf("%3.0f,", value); - } - } -#endif - term.locate(0, column++); - term.printf("width=%d height=%d yblock=%d EOI: %u]\n", - calc->width, calc->height, calc->yblock, calc->EOI_count); - term.printf("CC:"); - for(int i = 0; i < 16; i++) { - term.printf(" %u", cam->report_cc_count[i]); - } - term.printf("]\n"); - term.printf("PS:"); - for(int i = 0; i < 16; i++) { - term.printf(" %u", cam->report_ps_cc_count[i]); - } - term.printf("]\n"); - Thread::wait(200); - led2 = !led2; - } - } -}; - -int main() { - term.baud(921600); - term.printf("%s\n", __FILE__); - - BaseUsbHost* UsbHost = new BaseUsbHost; - UsbHub* hub = new UsbHub(); - - for(int port = 1; port <= MAX_HUB_PORT; port++) { - ControlEp* ctlEp = hub->GetPortEp(port); - if (LogitechC270::check(ctlEp)) { - cam = new LogitechC270(C270_160x120, _10FPS, ctlEp); - break; - } - if (UvcCam::check(ctlEp)) { - cam = new UvcCam(UVC_MJPEG, UVC_160x120, _10FPS, ctlEp); - break; - } - } - if (cam == NULL) { - error("USB camera not found\n"); - } - calc = new CalcCenter(cam); - calc->start(); - - display_Thread* th = new display_Thread; - th->start(osPriorityBelowNormal); - - Thread::wait(osWaitForever); -} -#endif
--- a/example_captureJPEG.cpp Tue Dec 11 15:28:00 2012 +0000 +++ /dev/null Thu Jan 01 00:00:00 1970 +0000 @@ -1,140 +0,0 @@ -#if 0 -// example_captureJPEG.cpp -#include "mbed.h" -#include "rtos.h" -#include "BaseUsbHost.h" -#include "LogitechC270.h" -#include "UvcCam.h" -#include "UsbFlashDrive.h" -#include "decodeMJPEG.h" -#include "MyThread.h" - -#define IMAGE_BUF_SIZE (1024*8) -#define INTERVAL_S 10 -#define SHOT_N 5 -#define BASE_PATH "usb" - -Serial pc(USBTX, USBRX); -DigitalOut led1(LED1), led2(LED2), led3(LED3), led4(LED4); - -class captureJPEG : public MyThread, public decodeMJPEG { -public: - captureJPEG(BaseUvc* cam) { - m_cam = cam; - m_cam->setOnResult(this, &captureJPEG::callback_motion_jpeg); - interval_t.start(); - shot = 0; - for(buf_size = IMAGE_BUF_SIZE; ; buf_size -= 128) { - buf = new uint8_t[buf_size]; - if (buf) { - break; - } - } - printf("%p buf size: %d\n", buf, buf_size); - } - int shot; - Timer interval_t; -protected: - virtual void outputJPEG(uint8_t c, int status) { - if (status == JPEG_START) { - pos = 0; - led2 = !led2; - } - if (pos < buf_size) { - buf[pos++] = c; - } - if (status == JPEG_END) { - led3 = !led3; - if (interval_t.read_ms() > INTERVAL_S*1000) { - interval_t.reset(); - led4 = !led4; - if (shot < SHOT_N) { - char path[32]; - snprintf(path, sizeof(path), "/%s/image%02d.jpg", BASE_PATH, shot); - printf("%d %s %d bytes\n", shot, path, pos); - FILE* fp = fopen(path, "wb"); - if (fp) { - fwrite(buf, pos, 1, fp); - fclose(fp); - } - shot++; - } - } - } - } - - void callback_motion_jpeg(uint16_t frame, uint8_t* buf, int len) { - inputPacket(buf, len); - if (buf[1]&1) { // FID - led1 = !led1; - } - if (buf[1]&2) { // EOF - led2 = !led2; - } - } - - virtual void run() { - while(true) { - if (m_cam) { - m_cam->poll(); - } - } - } - uint8_t* buf; - int buf_size; - int pos; - BaseUvc* m_cam; -}; - -int main() { - pc.baud(921600); - printf("%s\n", __FILE__); - - BaseUvc* cam = NULL; - UsbFlashDrive* drive = NULL; - BaseUsbHost* usbHost = new BaseUsbHost(); - UsbHub* hub = new UsbHub(); - - for(int i = 1; i <= MAX_HUB_PORT; i++) { - ControlEp* ctlEp = hub->GetPortEp(i); - if (drive == NULL && UsbFlashDrive::check(ctlEp)) { - drive = new UsbFlashDrive("usb", ctlEp); - } - if (cam == NULL && LogitechC270::check(ctlEp)) { - cam = new LogitechC270(C270_160x120, _5FPS, ctlEp); - } - if (cam == NULL && UvcCam::check(ctlEp)) { - cam = new UvcCam(UVC_MJPEG, UVC_160x120, _5FPS, ctlEp); - } - } - if (cam == NULL) { - error("UVC cam not found\n"); - } - if (drive == NULL) { - error("USB flash drive not found\n"); - } - - captureJPEG* capture = new captureJPEG(cam); - printf("captureJPEG: %p %d\n", capture, sizeof(captureJPEG)); - capture->set_stack(DEFAULT_STACK_SIZE+256); - capture->start(); - - for(int n = 0; ; n++) { - printf("%d captureJPEG stack used: %d/%d bytes, interval %d/%d %d/%d sec\n", - n, capture->stack_used(), capture->stack_size(), - capture->shot, SHOT_N, capture->interval_t.read_ms()/1000, INTERVAL_S); - printf("CC:"); - for(int i = 0; i < 16; i++) { - printf(" %u", cam->report_cc_count[i]); - } - printf("\n"); - printf("PS:"); - for(int i = 0; i < 16; i++) { - printf(" %u", cam->report_ps_cc_count[i]); - } - printf("\n"); - Thread::wait(3000); - } -} - -#endif
--- a/example_captureYUY2.cpp Tue Dec 11 15:28:00 2012 +0000 +++ /dev/null Thu Jan 01 00:00:00 1970 +0000 @@ -1,125 +0,0 @@ -#if 0 -#include "mbed.h" -#include "rtos.h" -#include "BaseUsbHost.h" -#include "UvcCam.h" -#include "MyThread.h" -#include <bitset> - -Serial pc(USBTX, USBRX); -DigitalOut led1(LED1), led2(LED2), led3(LED3), led4(LED4); - -class decodeYUY2 { -public: - decodeYUY2() { - xy = 0; - } -protected: - void inputPacket(uint8_t* buf, int len) { - for(int i = 12; i < len; i += 4) { - outputY(xy, buf[i]); - outputCb(xy+1, buf[i+1]); - outputY(xy+2, buf[i+2]); - outputCr(xy+3, buf[i+3]); - xy += 4; - } - if (buf[1]&2) { //EOF - xy = 0; - } - } - virtual void outputY(int xy, uint8_t c)=0; - virtual void outputCb(int xy, uint8_t c)=0; - virtual void outputCr(int xy, uint8_t c)=0; - int xy; -}; - -class captureYUY2 : public MyThread, public decodeYUY2 { -public: - captureYUY2(BaseUvc* cam) { - m_cam = cam; - m_cam->setOnResult(this, &captureYUY2::callback); - } - bitset<160*120> bitmap; - uint8_t buf[160]; -protected: - virtual void outputY(int xy, uint8_t c) { - if (xy < bitmap.size()) { - bitmap.set(xy, c > 0x80); - } - if (xy < sizeof(buf)) { - buf[xy] = c; - } - } - virtual void outputCb(int xy, uint8_t c) {} - virtual void outputCr(int xy, uint8_t c) {} - void callback(uint16_t frame, uint8_t* buf, int len) { - inputPacket(buf, len); - if (buf[1]&1) { // FID - led1 = !led1; - } - if (buf[1]&2) { // EOF - led2 = !led2; - } - } - virtual void run() { - while(true) { - if (m_cam) { - m_cam->poll(); - } - } - } - BaseUvc* m_cam; -}; - -int main() { - pc.baud(921600); - printf("%s\n", __FILE__); - - BaseUsbHost* usbHost = new BaseUsbHost(); - UsbHub* hub = new UsbHub(); - BaseUvc* cam = NULL; - for(int i = 1; i <= MAX_HUB_PORT; i++) { - ControlEp* ctlEp = hub->GetPortEp(i); - if (cam == NULL && UvcCam::check(ctlEp)) { - cam = new UvcCam(UVC_YUY2, UVC_160x120, _5FPS, ctlEp); - } - } - if (cam == NULL) { - error("cam not found\n"); - } - captureYUY2* capture = new captureYUY2(cam); - capture->set_stack(DEFAULT_STACK_SIZE-128*12); - capture->start(); - - for(int n = 0; ; n++) { - for(int y = 0; y < 120; y+= 6) { - for(int x = 0; x < 160; x+= 3) { - printf("%c", capture->bitmap[y*160+x] ? '*':'.'); - } - printf("\n"); - } - - printf("%d captureYUY2 stack used: %d/%d bytes\n", n, capture->stack_used(), capture->stack_size()); - printf("CC:"); // conditon code - for(int i = 0; i < 16; i++) { - printf(" %u", cam->report_cc_count[i]); - } - printf("\n"); - printf("PS:"); // Packet status - for(int i = 0; i < 16; i++) { - printf(" %u", cam->report_ps_cc_count[i]); - } - printf("\n"); - - for(int i = 0; i < 64; i++) { - printf("%02X ", capture->buf[i]); - if (i%16==15) { - printf("\n"); - } - } - Thread::wait(400); - led3 = !led3; - } -} - -#endif
--- /dev/null Thu Jan 01 00:00:00 1970 +0000 +++ b/main.cpp Sun Jan 06 11:47:51 2013 +0000 @@ -0,0 +1,122 @@ +// BaseUsbHost_example/main.cpp 2013/1/6 +#include "mbed.h" +#include "rtos.h" +#include "BaseUsbHost.h" +#include "LogitechC270.h" +#include "LifeCamVX700.h" +#include "UvcCam.h" +#include "UsbFlashDrive.h" +#include "decodeMJPEG.h" +#include "MyThread.h" +#include <string> + +#define IMAGE_BUF_SIZE (1024*6) +#define INTERVAL_S 20 + +Serial pc(USBTX, USBRX); +DigitalOut led1(LED1), led2(LED2), led3(LED3), led4(LED4); + +class captureJPEG : public MyThread, public decodeMJPEG { +public: + captureJPEG(BaseUvc* cam) : m_cam(cam) { + m_cam->setOnResult(this, &captureJPEG::callback_motion_jpeg); + interval_t.start(); + buf_size = IMAGE_BUF_SIZE; + buf = new uint8_t[buf_size]; + pos = 0; + } + Timer interval_t; +private: + virtual void outputJPEG(uint8_t c, int status) { + if (status == JPEG_START) { + pos = 0; + led2 = !led2; + } + if (pos < buf_size) { + buf[pos++] = c; + } + if (status == JPEG_END) { + led3 = !led3; + if (interval_t.read_ms() > INTERVAL_S*1000) { + interval_t.reset(); + time_t timestamp = time(NULL); + struct tm* tminfo = localtime(×tamp); + char tmbuf[64]; + strftime(tmbuf, sizeof(tmbuf), "/usb/img%M%S.jpg", tminfo); + string path = tmbuf; + printf("%s %d bytes\n", path.c_str(), pos); + FILE* fp = fopen(path.c_str(), "wb"); + if (fp) { + fwrite(buf, pos, 1, fp); + fclose(fp); + } + led4 = !led4; + } + } + } + + void callback_motion_jpeg(uint16_t frame, uint8_t* buf, int len) { + inputPacket(buf, len); + led1 = buf[1]&1; // FID + if (buf[1]&2) { // EOF + led2 = !led2; + } + } + + virtual void run() { + while(true) { + if (m_cam) { + m_cam->poll(); + } + } + } + uint8_t* buf; + int buf_size; + int pos; + BaseUvc* m_cam; +}; + +void no_memory () { + error("Failed to allocate memory!\n"); +} + +int main() { + pc.baud(921600); + printf("%s\n", __FILE__); + set_new_handler(no_memory); + + BaseUvc* cam = NULL; + UsbFlashDrive* drive = NULL; + BaseUsbHost* usbHost = new BaseUsbHost(); + ControlEp* ctlEp = new ControlEp; // root hub + if (!UsbHub::check(ctlEp)) { + error("USB Hub is not connected.\n"); + } + UsbHub* hub = new UsbHub(ctlEp); + for(vector<ControlEp*>::iterator it = hub->PortEp.begin(); it != hub->PortEp.end(); ++it) { + if (drive == NULL && UsbFlashDrive::check(*it)) { + drive = new UsbFlashDrive("usb", *it); + } else if (cam == NULL && LogitechC270::check(*it)) { + cam = new LogitechC270(C270_MJPEG, C270_160x120, _5FPS, *it); + } else if (cam == NULL && LifeCamVX700::check(*it)) { + cam = new LifeCamVX700(VX700_160x120, _5FPS, *it); + } else if (cam == NULL && UvcCam::check(*it)) { + cam = new UvcCam(UVC_MJPEG, UVC_160x120, _5FPS, *it); + } + } + if (cam == NULL) { + error("UVC Camera is not connected.\n"); + } + if (drive == NULL) { + error("USB flash drive is not connected.\n"); + } + + captureJPEG* capture = new captureJPEG(cam); + capture->set_stack(DEFAULT_STACK_SIZE+128*4); + capture->start(); + + for(int n = 0; ; n++) { + printf("%d captureJPEG stack used: %d/%d bytes\n", n, capture->stack_used(), capture->stack_size()); + Thread::wait(5*1000); + } +}