From 77f64ce1cdb7714e1f09975b7a28a99451a112cd Mon Sep 17 00:00:00 2001 From: Oleg Mazurov Date: Fri, 1 Jul 2011 20:25:50 -0600 Subject: [PATCH] 20110701 --- adk.cpp | 403 ++++++++++++++++++--------------------------------- adk.h | 6 +- hid.h | 6 +- masstorage.h | 6 +- 4 files changed, 153 insertions(+), 268 deletions(-) diff --git a/adk.cpp b/adk.cpp index 3e61096b..8b0d365b 100644 --- a/adk.cpp +++ b/adk.cpp @@ -12,7 +12,8 @@ ADK::ADK(USB *p, const char* manufacturer, const char* uri, const char* serial) : - pUsb(p), //pointer to USB class instance - mandatory for each driver + pUsb(p), //pointer to USB class instance - mandatory + /* ADK ID Strings */ manufacturer(manufacturer), model(model), description(description), @@ -20,8 +21,8 @@ ADK::ADK(USB *p, const char* manufacturer, uri(uri), serial(serial), - bAddress(0), //device address - mandatory for each driver - bNumEP(1) //if config descriptor needs to be parsed + bAddress(0), //device address - mandatory + bNumEP(1) //if config descriptor needs to be parsed { /* initialize endpoint data structures */ for(uint8_t i=0; iRegisterDeviceClass(this); //set devConfig[] entry } - if (pUsb) - pUsb->RegisterDeviceClass(this); } -/* Android initialization. Performed in 2 steps: - 1. If new device answers to vendor-specific request, another request switched device to accessory mode. - The device is then reset and comes up on a bus with different VID/PID. - 2. After detecting by VID/PID enpoints are extracted and device is configured -*/ + +/* Connect/disconnect initialization of a phone */ uint8_t ADK::Init(uint8_t parent, uint8_t port, bool lowspeed) { const uint8_t constBufSize = sizeof(USB_DEVICE_DESCRIPTOR); @@ -56,22 +56,28 @@ uint8_t ADK::Init(uint8_t parent, uint8_t port, bool lowspeed) USBTRACE("\r\nADK Init"); - // check if address has already been assigned to an instance - if (bAddress) + if (bAddress) { + USBTRACE("\r\nAddress in use"); return USB_ERROR_CLASS_INSTANCE_ALREADY_IN_USE; + } + + //USBTRACE("\r\nHere"); + // Get pointer to pseudo device with address 0 assigned p = addrPool.GetUsbDevicePtr(0); - if (!p) + if (!p) { + USBTRACE("\r\nAddress not found"); return USB_ERROR_ADDRESS_NOT_FOUND_IN_POOL; - + } + if (!p->epinfo) { USBTRACE("epinfo is null\r\n"); return USB_ERROR_EPINFO_IS_NULL; } - + // Save old pointer to EP_RECORD of address 0 oldep_ptr = p->epinfo; @@ -82,35 +88,65 @@ uint8_t ADK::Init(uint8_t parent, uint8_t port, bool lowspeed) // Get device descriptor rcode = pUsb->getDevDescr( 0, 0, constBufSize, (uint8_t*)buf ); - + // Restore p->epinfo p->epinfo = oldep_ptr; if( rcode ){ goto FailGetDevDescr; } - - // Allocate new address according to device class - bAddress = addrPool.AllocAddress(parent, false, port); - if (!bAddress) { - return USB_ERROR_OUT_OF_ADDRESS_SPACE_IN_POOL; - } - - // Extract Max Packet Size from the device descriptor - epInfo[0].maxPktSize = (uint8_t)((USB_DEVICE_DESCRIPTOR*)buf)->bMaxPacketSize0; - + + // Allocate new address according to device class + bAddress = addrPool.AllocAddress(parent, false, port); + + // Extract Max Packet Size from device descriptor + epInfo[0].maxPktSize = (uint8_t)((USB_DEVICE_DESCRIPTOR*)buf)->bMaxPacketSize0; + + // Assign new address to the device + rcode = pUsb->setAddr( 0, 0, bAddress ); + + if (rcode) + { + p->lowspeed = false; + addrPool.FreeAddress(bAddress); + bAddress = 0; + USBTRACE2("setAddr:",rcode); + return rcode; + } + + USBTRACE2("\r\nAddr:", bAddress); + + p->lowspeed = false; + + //get pointer to assigned address record + p = addrPool.GetUsbDevicePtr(bAddress); + if (!p) { + return USB_ERROR_ADDRESS_NOT_FOUND_IN_POOL; + } + + p->lowspeed = lowspeed; + + // Assign epInfo to epinfo pointer + rcode = pUsb->setEpInfoEntry(bAddress, 1, epInfo); + + if (rcode) + goto FailSetDevTblEntry; + + /* debug code start */ num_of_conf = ((USB_DEVICE_DESCRIPTOR*)buf)->bNumConfigurations; - USBTRACE2("\r\nNum.conf: ", num_of_conf ); - for (uint8_t i=0; i HexDump; - //USBTRACE("\r\nHexdumper2: "); - //ConfigDescParser<0, 0, 0, - // 0> confDescrParser(this); - - rcode = pUsb->getConfDescr(bAddress, 0, i, &HexDump); - //rcode = pUsb->getConfDescr(bAddress, 0, i, &confDescrParser); + + USBTRACE2("\r\nNC:",num_of_conf); + USBTRACE2("\r\nNP:",epInfo[0].bmNakPower); + + for (uint8_t i=0; i HexDump; + //ConfigDescParser<0, 0, 0, 0> confDescrParser(this); + + rcode = pUsb->getConfDescr(bAddress, 0, i, &HexDump); + //rcode = pUsb->getConfDescr(bAddress, 0, i, &confDescrParser); } // for (uint8_t i=0; iidProduct == ADK_PID || ((USB_DEVICE_DESCRIPTOR*)buf)->idProduct == ADB_PID)){ USBTRACE("\r\nAcc.mode device detected"); + /* set endpoint info, config */ // Allocate new address //bAddress = addrPool.AllocAddress(parent, false, port); - if (!bAddress) { - return USB_ERROR_OUT_OF_ADDRESS_SPACE_IN_POOL; - } + //if (!bAddress) { + // return USB_ERROR_OUT_OF_ADDRESS_SPACE_IN_POOL; + //} // Extract Max Packet Size from the device descriptor - epInfo[0].maxPktSize = (uint8_t)((USB_DEVICE_DESCRIPTOR*)buf)->bMaxPacketSize0; - - // Assign new address to the device - rcode = pUsb->setAddr( 0, 0, bAddress ); - - if (rcode) { - p->lowspeed = false; - addrPool.FreeAddress(bAddress); - bAddress = 0; - USBTRACE2("setAddr:",rcode); - return rcode; - } - - USBTRACE2("\r\nAddr: ", bAddress); - - p->lowspeed = false; - - p = addrPool.GetUsbDevicePtr(bAddress); - - if (!p) { - return USB_ERROR_ADDRESS_NOT_FOUND_IN_POOL; - } - - p->lowspeed = lowspeed; - - // Assign epInfo to epinfo pointer - // rcode = pUsb->setEpInfoEntry(bAddress, 1, epInfo); -/* - if (rcode) { - goto FailSetDevTblEntry; - } - */ - /* initialize endpoint structures */ - - // Assign epInfo to epinfo pointer - //rcode = pUsb->setEpInfoEntry(bAddress, bNumEP, epInfo); - - USBTRACE2("Conf:", 1); - - // Set Configuration Value + //epInfo[0].maxPktSize = (uint8_t)((USB_DEVICE_DESCRIPTOR*)buf)->bMaxPacketSize0; + // Set Configuration Value rcode = pUsb->setConf(bAddress, 0, bConfNum); - if (rcode) { - goto FailSetConf; - } - return 0; //successful configuration }//if( buf->idVendor == ADK_VID... @@ -190,7 +185,16 @@ uint8_t ADK::Init(uint8_t parent, uint8_t port, bool lowspeed) USBTRACE2("\r\nADK protocol rev. ", adkproto ); } - //load ID strings and switch to accessory mode + //sending ID strings + sendStr( ACCESSORY_STRING_MANUFACTURER, manufacturer); + sendStr( ACCESSORY_STRING_MODEL, model); + sendStr( ACCESSORY_STRING_DESCRIPTION, description); + sendStr( ACCESSORY_STRING_VERSION, version); + sendStr( ACCESSORY_STRING_URI, uri); + sendStr( ACCESSORY_STRING_SERIAL, serial); + + //switch to accessory mode + //the phone will reset rcode = switchAcc(); if( rcode ) { goto FailSwAcc; //init fails @@ -198,98 +202,15 @@ uint8_t ADK::Init(uint8_t parent, uint8_t port, bool lowspeed) rcode = -1; goto SwAttempt; //switch to accessory mode attempted -// -// // Allocate new address according to device class -// bAddress = addrPool.AllocAddress(parent, false, port); -// -// if (!bAddress) -// return USB_ERROR_OUT_OF_ADDRESS_SPACE_IN_POOL; -// -// // Extract Max Packet Size from the device descriptor -// epInfo[0].maxPktSize = (uint8_t)((USB_DEVICE_DESCRIPTOR*)buf)->bMaxPacketSize0; -// -// // Assign new address to the device -// rcode = pUsb->setAddr( 0, 0, bAddress ); -// -// if (rcode) -// { -// p->lowspeed = false; -// addrPool.FreeAddress(bAddress); -// bAddress = 0; -// USBTRACE2("setAddr:",rcode); -// return rcode; -// } -// -// USBTRACE2("Addr:", bAddress); -// -// p->lowspeed = false; -// -// p = addrPool.GetUsbDevicePtr(bAddress); -// -// if (!p) -// return USB_ERROR_ADDRESS_NOT_FOUND_IN_POOL; -// -// p->lowspeed = lowspeed; -// -// num_of_conf = ((USB_DEVICE_DESCRIPTOR*)buf)->bNumConfigurations; -// -// // Assign epInfo to epinfo pointer -// rcode = pUsb->setEpInfoEntry(bAddress, 1, epInfo); -// -// if (rcode) -// goto FailSetDevTblEntry; -// -// USBTRACE2("NC:", num_of_conf); -// -// for (uint8_t i=0; i CdcControlParser(this); -// -// ConfigDescParser CdcDataParser(this); -// -// rcode = pUsb->getConfDescr(bAddress, 0, i, &CdcControlParser); -// rcode = pUsb->getConfDescr(bAddress, 0, i, &CdcDataParser); -// -// if (bNumEP > 1) -// break; -// } // for -// -// if (bNumEP < 4) -// return USB_DEV_CONFIG_ERROR_DEVICE_NOT_SUPPORTED; -// -// // Assign epInfo to epinfo pointer -// rcode = pUsb->setEpInfoEntry(bAddress, bNumEP, epInfo); -// -// USBTRACE2("Conf:", bConfNum); -// -// // Set Configuration Value -// rcode = pUsb->setConf(bAddress, 0, bConfNum); -// -// if (rcode) -// goto FailSetConf; -// -// rcode = pAsync->OnInit(this); -// -// if (rcode) -// goto FailOnInit; -// -// USBTRACE("ACM configured\r\n"); -// -// //bPollEnable = true; -// -// //USBTRACE("Poll enabled\r\n"); -// return 0; -// + FailGetDevDescr: USBTRACE("\r\ngetDevDescr:"); goto Fail; +FailSetDevTblEntry: + USBTRACE("\r\nsetDevTblEn:"); + goto Fail; + FailGetProto: USBTRACE("\r\ngetProto:"); goto Fail; @@ -310,9 +231,9 @@ SwAttempt: // USBTRACE("getConf:"); // goto Fail; // -FailSetConf: - USBTRACE("\r\nsetConf: "); - goto Fail; +//FailSetConf: +// USBTRACE("setConf:"); +// goto Fail; // //FailOnInit: // USBTRACE("OnInit:"); @@ -324,44 +245,44 @@ Fail: return rcode; } +/* Extracts bulk-IN and bulk-OUT endpoint information from config descriptor */ +void ADK::EndpointXtract(uint8_t conf, uint8_t iface, uint8_t alt, uint8_t proto, const USB_ENDPOINT_DESCRIPTOR *pep) +{ + ErrorMessage(PSTR("Conf.Val"), conf); + ErrorMessage(PSTR("Iface Num"),iface); + ErrorMessage(PSTR("Alt.Set"), alt); -//void ACM::EndpointXtract(uint8_t conf, uint8_t iface, uint8_t alt, uint8_t proto, const USB_ENDPOINT_DESCRIPTOR *pep) -//{ -// ErrorMessage(PSTR("Conf.Val"), conf); -// ErrorMessage(PSTR("Iface Num"),iface); -// ErrorMessage(PSTR("Alt.Set"), alt); -// -// bConfNum = conf; -// -// uint8_t index; -// -// if ((pep->bmAttributes & 0x03) == 3 && (pep->bEndpointAddress & 0x80) == 0x80) -// index = epInterruptInIndex; -// else -// if ((pep->bmAttributes & 0x02) == 2) -// index = ((pep->bEndpointAddress & 0x80) == 0x80) ? epDataInIndex : epDataOutIndex; -// else -// return; -// -// // Fill in the endpoint info structure -// epInfo[index].epAddr = (pep->bEndpointAddress & 0x0F); -// epInfo[index].maxPktSize = (uint8_t)pep->wMaxPacketSize; -// epInfo[index].epAttribs = 0; -// -// bNumEP ++; -// -// PrintEndpointDescriptor(pep); -//} + bConfNum = conf; + uint8_t index; + + + + if ((pep->bmAttributes & 0x02) == 2) { + index = ((pep->bEndpointAddress & 0x80) == 0x80) ? epDataInIndex : epDataOutIndex; + } + + + // Fill in the endpoint info structure + epInfo[index].epAddr = (pep->bEndpointAddress & 0x0F); + epInfo[index].maxPktSize = (uint8_t)pep->wMaxPacketSize; + epInfo[index].epAttribs = 0; + + bNumEP ++; + + PrintEndpointDescriptor(pep); +} + +/* Performs a cleanup after failed Init() attempt */ uint8_t ADK::Release() { -// pUsb->GetAddressPool().FreeAddress(bAddress); + pUsb->GetAddressPool().FreeAddress(bAddress); // // bControlIface = 0; // bDataIface = 0; -// bNumEP = 1; //must have to be reset to 1 + bNumEP = 1; //must have to be reset to 1 // -// bAddress = 0; + bAddress = 0; // qNextPollTime = 0; // bPollEnable = false; return 0; @@ -414,56 +335,20 @@ uint8_t ADK::SndData(uint16_t nbytes, uint8_t *dataptr) return pUsb->outTransfer(bAddress, epInfo[epDataOutIndex].epAddr, nbytes, dataptr); } -//uint8_t ACM::SetCommFeature(uint16_t fid, uint8_t nbytes, uint8_t *dataptr) -//{ -// return( pUsb->ctrlReq( bAddress, 0, bmREQ_CDCOUT, CDC_SET_COMM_FEATURE, (fid & 0xff), (fid >> 8), bControlIface, nbytes, nbytes, dataptr, NULL )); -//} -// -//uint8_t ACM::GetCommFeature(uint16_t fid, uint8_t nbytes, uint8_t *dataptr) -//{ -// return( pUsb->ctrlReq( bAddress, 0, bmREQ_CDCIN, CDC_GET_COMM_FEATURE, (fid & 0xff), (fid >> 8), bControlIface, nbytes, nbytes, dataptr, NULL )); -//} -// -//uint8_t ACM::ClearCommFeature(uint16_t fid) -//{ -// return( pUsb->ctrlReq( bAddress, 0, bmREQ_CDCOUT, CDC_CLEAR_COMM_FEATURE, (fid & 0xff), (fid >> 8), bControlIface, 0, 0, NULL, NULL )); -//} -// -//uint8_t ACM::SetLineCoding(const LINE_CODING *dataptr) -//{ -// return( pUsb->ctrlReq( bAddress, 0, bmREQ_CDCOUT, CDC_SET_LINE_CODING, 0x00, 0x00, bControlIface, sizeof(LINE_CODING), sizeof(LINE_CODING), (uint8_t*)dataptr, NULL )); -//} -// -//uint8_t ACM::GetLineCoding(LINE_CODING *dataptr) -//{ -// return( pUsb->ctrlReq( bAddress, 0, bmREQ_CDCIN, CDC_GET_LINE_CODING, 0x00, 0x00, bControlIface, sizeof(LINE_CODING), sizeof(LINE_CODING), (uint8_t*)dataptr, NULL )); -//} -// -//uint8_t ACM::SetControlLineState(uint8_t state) -//{ -// return( pUsb->ctrlReq( bAddress, 0, bmREQ_CDCOUT, CDC_SET_CONTROL_LINE_STATE, state, 0, bControlIface, 0, 0, NULL, NULL )); -//} -// -//uint8_t ACM::SendBreak(uint16_t duration) -//{ -// return( pUsb->ctrlReq( bAddress, 0, bmREQ_CDCOUT, CDC_SEND_BREAK, (duration & 0xff), (duration >> 8), bControlIface, 0, 0, NULL, NULL )); -//} -// -// -//void ACM::PrintEndpointDescriptor( const USB_ENDPOINT_DESCRIPTOR* ep_ptr ) -//{ -// Notify(PSTR("Endpoint descriptor:")); -// Notify(PSTR("\r\nLength:\t\t")); -// PrintHex(ep_ptr->bLength); -// Notify(PSTR("\r\nType:\t\t")); -// PrintHex(ep_ptr->bDescriptorType); -// Notify(PSTR("\r\nAddress:\t")); -// PrintHex(ep_ptr->bEndpointAddress); -// Notify(PSTR("\r\nAttributes:\t")); -// PrintHex(ep_ptr->bmAttributes); -// Notify(PSTR("\r\nMaxPktSize:\t")); -// PrintHex(ep_ptr->wMaxPacketSize); -// Notify(PSTR("\r\nPoll Intrv:\t")); -// PrintHex(ep_ptr->bInterval); -// Notify(PSTR("\r\n")); -//} +void ADK::PrintEndpointDescriptor( const USB_ENDPOINT_DESCRIPTOR* ep_ptr ) +{ + Notify(PSTR("Endpoint descriptor:")); + Notify(PSTR("\r\nLength:\t\t")); + PrintHex(ep_ptr->bLength); + Notify(PSTR("\r\nType:\t\t")); + PrintHex(ep_ptr->bDescriptorType); + Notify(PSTR("\r\nAddress:\t")); + PrintHex(ep_ptr->bEndpointAddress); + Notify(PSTR("\r\nAttributes:\t")); + PrintHex(ep_ptr->bmAttributes); + Notify(PSTR("\r\nMaxPktSize:\t")); + PrintHex(ep_ptr->wMaxPacketSize); + Notify(PSTR("\r\nPoll Intrv:\t")); + PrintHex(ep_ptr->bInterval); + Notify(PSTR("\r\n")); +} diff --git a/adk.h b/adk.h index 14d961c9..135bb6db 100644 --- a/adk.h +++ b/adk.h @@ -76,7 +76,7 @@ protected: /* Endpoint data structure */ EpInfo epInfo[ADK_MAX_ENDPOINTS]; - // void PrintEndpointDescriptor(const USB_ENDPOINT_DESCRIPTOR* ep_ptr); + void PrintEndpointDescriptor(const USB_ENDPOINT_DESCRIPTOR* ep_ptr); public: ADK(USB *pUsb, const char* manufacturer, @@ -97,8 +97,8 @@ public: virtual uint8_t Poll(); virtual uint8_t GetAddress() { return bAddress; }; - // UsbConfigXtracter implementation - // virtual void EndpointXtract(uint8_t conf, uint8_t iface, uint8_t alt, uint8_t proto, const USB_ENDPOINT_DESCRIPTOR *ep); + //UsbConfigXtracter implementation + virtual void EndpointXtract(uint8_t conf, uint8_t iface, uint8_t alt, uint8_t proto, const USB_ENDPOINT_DESCRIPTOR *ep); }; //class ADK : public USBDeviceConfig ... /* get ADK protocol version */ /* returns 2 bytes in *adkproto */ diff --git a/hid.h b/hid.h index 9c3be7c5..7ca81b20 100644 --- a/hid.h +++ b/hid.h @@ -10,9 +10,9 @@ #include "Usb.h" #include -#include "..\DebugTools\printhex.h" -#include "..\DebugTools\hexdump.h" -#include "..\DebugTools\message.h" +#include "printhex.h" +#include "hexdump.h" +#include "message.h" #include "confdescparser.h" diff --git a/masstorage.h b/masstorage.h index 4126c9a8..ac92e737 100644 --- a/masstorage.h +++ b/masstorage.h @@ -10,9 +10,9 @@ #include "Usb.h" #include -#include "..\DebugTools\printhex.h" -#include "..\DebugTools\hexdump.h" -#include "..\DebugTools\message.h" +#include "printhex.h" +#include "hexdump.h" +#include "message.h" #include "confdescparser.h"