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

📄 xsusbhostapi.c

📁 优龙YLP270开发板 光盘自带的BIOS和实验例程源码 强烈推荐
💻 C
📖 第 1 页 / 共 5 页
字号:
/******************************************************************************
**
**  COPYRIGHT (C) 2000, 2001, 2002 Intel Corporation.
**
**  This software as well as the software described in it is furnished under 
**  license and may only be used or copied in accordance with the terms of the 
**  license. The information in this file is furnished for informational use 
**  only, is subject to change without notice, and should not be construed as 
**  a commitment by Intel Corporation. Intel Corporation assumes no 
**  responsibility or liability for any errors or inaccuracies that may appear 
**  in this document or any software that may be provided in association with 
**  this document. 
**  Except as permitted by such license, no part of this document may be 
**  reproduced, stored in a retrieval system, or transmitted in any form or by 
**  any means without the express written consent of Intel Corporation. 
**
**  FILENAME:   XsUsbHostAPI.c
**
**  PURPOSE:    This file contains the OpenHCI driver for any OpenHCI compliant device.
**
**  LAST MODIFIED:  $Modtime: 7/17/03 1:01p $
******************************************************************************/

/*
*******************************************************************************
*   HEADER FILES
*******************************************************************************
*/                                                                      

#include <stdio.h>
#include <string.h>
#include "systypes.h"
#include "timedelays.h"
#include "DM_Debug.h"
#include "DM_Errors.h"
#include "XsUsbHostDrv.h"
#include "XsUsbHostAPI.h"
#include "xllp_udc.h"
#include "xsudc.h"
#include "USBClient.h"

#define USBX_TIMEOUT_FC 1000    // timeout in frames
#define ADDR_OFFSET     1       // port ID offset to form device address

/*----------------------------------------------------------------------
 * Simple loopback polling enable
 */
static int loopbackMode = 0;
static int debugUsbNoTimeout = 0;
static int fakeLoopbackTest = 0;

/*----------------------------------------------------------------------
 * Host port controller registers
 */
static volatile USB_HostPortRegs_T * hcP;

/*----------------------------------------------------------------------
 * Host port communication area, must be in non cached address space
 */
static volatile USB_HostControllerCommunicationArea_T * hccaP;

/*----------------------------------------------------------------------
 * Transfer descriptor list, must be in non cached address space
 */
static volatile USB_TransferDescriptor_T * tdListP;
static volatile USB_IsoTransferDescriptor_T * tdIsoListP;

/*----------------------------------------------------------------------
 * Endpoint list, must be in non cached address space
 */
static volatile USB_EndpointDescriptor_T * edListP;

/*----------------------------------------------------------------------
 * Message buffer list, could be in non cached address space
 */
static char * bufListP;
//static char bufAlloc[USBD_MAX_BUF];
static char * bufAllocP;

/*----------------------------------------------------------------------
 * Static endpoints for periodic table, must be in non cached memory
 */
static volatile USB_EndpointDescriptor_T * periodicTableP;

/*----------------------------------------------------------------------
 * Device table, can be in any memory
 */
static USBD_Device_T deviceTable[USBD_MAX_DEV];

/*----------------------------------------------------------------------
 * Device info table
 */
static USBD_DeviceInfo_T deviceInfoTable[USBD_MAX_DEV_INFO];

/*----------------------------------------------------------------------
 * Statistics
 */
typedef struct Usbx_Stats_S {
  int controlStarts;
  int isoStarts;
  int bulkStarts;
  int intStarts;

  int timeout;
  int halted;
  int doneLost;

  int noTransfer;
  int badIsoBuffer;
  int noBuffer;
  int noDevice;
  int noEndpoint;
  int badMaxPacket;
  int bufferOverflow;
  int badDevice;
  int badInterface;
  int badVersion;
  int noSuspend;
  int badBuffer;

  int haltedReset;
} Usbx_Stats_T;

static Usbx_Stats_T usbxStats;

/*----------------------------------------------------------------------
 * Descriptor definitions for debug display
 */
#define offsetof(a,b) (int)&((a*)0)->b

#define Device USB_DeviceDescriptor_T
USBD_DescriptorDefinition_T deviceDescription[] = {
  "bLength",		offsetof(Device,bLength), 1,
  "bDescriptorType",	offsetof(Device,bDescriptorType), 1,
  "bcdUSB",		offsetof(Device,bcdUSB), 2,
  "bDeviceClass",	offsetof(Device,bDeviceClass), 1,
  "bDeviceSubClass",	offsetof(Device,bDeviceSubClass), 1,
  "bDeviceProtocol",	offsetof(Device,bDeviceProtocol), 1,
  "bMaxPacketSize0",	offsetof(Device,bMaxPacketSize0), 1,
  "idVendor",		offsetof(Device,idVendor), 2,
  "idProduct",		offsetof(Device,idProduct), 2,
  "bcdDevice",		offsetof(Device,bcdDevice), 2,
  "iManfacturer",	offsetof(Device,iManfacturer), 1,
  "iProduct",		offsetof(Device,iProduct), 1,
  "iSerialNumber",	offsetof(Device,iSerialNumber), 1,
  "bNumConfigurations",	offsetof(Device,bNumConfigurations), 1,
  { 0 }
};
#undef Device

#define Configuration USB_ConfigurationDescriptor_T
USBD_DescriptorDefinition_T configurationDescription[] = {
  "bLength",		offsetof(Configuration,bLength), 1,
  "bDescriptorType",	offsetof(Configuration,bDescriptorType), 1,
  "wTotalLength",	offsetof(Configuration,wTotalLength), 2,
  "bNumInterfaces",	offsetof(Configuration,bNumInterfaces), 1,
  "bConfigurationValue",offsetof(Configuration,bConfigurationValue), 1,
  "iConfiguration",	offsetof(Configuration,iConfiguration), 1,
  "bmBitmap",		offsetof(Configuration,bmBitmap), 1,
  "bMaxPower",		offsetof(Configuration,bMaxPower), 1,
  { 0 }
};
#undef Config

#define Interface USB_InterfaceDescriptor_T
USBD_DescriptorDefinition_T interfaceDescription[] = {
  "bLength",		offsetof(Interface,bLength), 1,
  "bDescriptorType",	offsetof(Interface,bDescriptorType), 1,
  "bInterfaceNumber",	offsetof(Interface,bInterfaceNumber), 1,
  "bAlternateSetting",	offsetof(Interface,bAlternateSetting), 1,
  "bNumEndpoints",	offsetof(Interface,bNumEndpoints), 1,
  "bInterfaceClass",	offsetof(Interface,bInterfaceClass), 1,
  "bInterfaceSubClass",	offsetof(Interface,bInterfaceSubClass), 1,
  "bInterfaceProtocol",	offsetof(Interface,bInterfaceProtocol), 1,
  "iInterface",		offsetof(Interface,iInterface), 1,
  { 0 }
};
#undef Interface

#define Endpoint USB_EndpointDescriptorX_T
USBD_DescriptorDefinition_T endpointDescription[] = {
  "bLength",		offsetof(Endpoint,bLength), 1,
  "bDescriptorType",	offsetof(Endpoint,bDescriptorType), 1,
  "bEndpointAddress",	offsetof(Endpoint,bEndpointAddress),1,
  "bmAttributes",	offsetof(Endpoint,bmAttributes), 1,
  "wMaxPacketSize",	offsetof(Endpoint,wMaxPacketSize), 2,
  "bInterval",		offsetof(Endpoint,bInterval), 1,
  { 0 }
};
#undef Endpoint

typedef struct defList_S {
  int type;
  char * name;
  USBD_DescriptorDefinition_T * list;
} defList_T;

#define MAX_DEF 32
defList_T descriptorList[MAX_DEF] = {
  UsbDescTypeConfiguration,"Configuration Descriptor",configurationDescription,
  UsbDescTypeInterface,	   "Interface Descriptor",    interfaceDescription,
  UsbDescTypeEndpoint,     "Endpoint Descriptor",     endpointDescription,
};

/*----------------------------------------------------------------------
 * Clear stats block
 */
static
void clearUsbxStats(void)
{
  memset(&usbxStats,0,sizeof(usbxStats));
}

/*----------------------------------------------------------------------
 * Check for a registered device callback when the device changes state.
 */
static
void CheckCallback(int state, USBD_Device_T * devP)
{
  int i;
  for (i=0; i < USBD_MAX_DEV_INFO; i++) {
    if ((deviceInfoTable[i].VendorId == devP->VendorId) &&
	(deviceInfoTable[i].DeviceId == devP->DeviceId) &&
	(deviceInfoTable[i].Callback)) {

      deviceInfoTable[i].Callback(state, devP);
    }
  }
}

/*----------------------------------------------------------------------
 * This function will dump a structured region of memory. memcpy is used to
 * allow any memory alignment to be used. Note, USB descriptors are NOT
 * aligned and can not be used directly in memory unless steps are taken to
 * insure their base address alignment. The configuration descriptor is
 * particularly troubling because it contains a concatenation of unaligned
 * descriptors, yuk!
 */
static
void doStructDump(char * name, void * bufP, USBD_DescriptorDefinition_T * defP)
{
  int val;
  printf("%s\r\n", name);
  while(defP->name) {
    val = 0;
    memcpy(&val,(char*)bufP+defP->offset,defP->size);
    printf("  %s=%d(%x)\r\n",defP->name, val, val);
    defP++;
  }
}

/*----------------------------------------------------------------------
 *
 */
static
void displayDeviceDescriptor(void * bufP)
{
  doStructDump("Device Descriptor",bufP,deviceDescription);
}

/*----------------------------------------------------------------------
 *
 */
static
void displayUnknownDescriptor(USB_GenericDescriptor_T * gP)
{
  char * p = (char*)gP;
  char buffer[64];
  int i;

  printf("Unknown %d(%x) Descriptor\r\n",
	  gP->bDescriptorType,
	  gP->bDescriptorType);

  buffer[0] = '\0';
  for (i=0; i < gP->bLength; i++) {
    sprintf(buffer,"%s %02X ", buffer, p[i]);
    if ((i % 8) == 7) {
      printf("%s\r\n", buffer);
      buffer[0] = '\0';
    }
  }
  if ((i % 8) != 0)
    printf("%s\r\n", buffer);
}

/*----------------------------------------------------------------------
 *
 */
static
defList_T * findDescriptorList(int type)
{
  int i;
  for (i=0; i < MAX_DEF; i++) {
    if (descriptorList[i].type == type)
      return &descriptorList[i];
  }
  return NULL;
}

/*----------------------------------------------------------------------
 *
 */
static
void displayConfigurationDescriptorAll(int numConfig,
				       USB_ConfigurationDescriptor_T * confP)
{
  USB_GenericDescriptor_T * gP;
  defList_T * listP;
  int i, j;

  for (j=0; j < numConfig; j++) {
    gP = (USB_GenericDescriptor_T*)confP;
    for(i=0; (i > 0) && (i < confP->wTotalLength); ) {
      if ((listP=findDescriptorList(gP->bDescriptorType)) != NULL)
	doStructDump(listP->name, (void*)gP, listP->list);
      else
	displayUnknownDescriptor((USB_GenericDescriptor_T *)gP);

      i += gP->bLength;
      gP = (USB_GenericDescriptor_T*)((char*)gP + gP->bLength);
    }
    confP = (USB_ConfigurationDescriptor_T *)gP;
  }
}

/*----------------------------------------------------------------------
 * Debug function to display a buffer
 */
static
void dumpBuffer(char * p, int length)
{
  char buffer[64];
  int i;

  DM_CwDbgPrintf(DM_CW_USB_HOST_0, "Received %d bytes\n", length);

  buffer[0] = '\0';
  for (i=0; i < length; i++) {
    sprintf(buffer,"%s %02X ", buffer, p[i]);
    if ((i % 8) == 7) {
      DM_CwDbgPrintf(DM_CW_USB_HOST_0, "%s\n", buffer);

      buffer[0] = '\0';
    }
  }
  if ((i % 8) != 0)
    DM_CwDbgPrintf(DM_CW_USB_HOST_0, "%s\n", buffer);
}

/*----------------------------------------------------------------------
 * Function to display a buffer
 */
extern
void XsUsbHostDisplayBuffer(char * banner, char * p, int length)
{
  char buffer[64];
  int i;

  printf("%s %d bytes\r\n", banner, length);

  buffer[0] = '\0';
  for (i=0; i < length; i++) {
    sprintf(buffer,"%s %02X ", buffer, p[i]);
    if ((i % 8) == 7) {
      printf("%s\r\n", buffer);
      buffer[0] = '\0';
    }
  }
  if ((i % 8) != 0)
    printf("%s\r\n", buffer);
}

/*----------------------------------------------------------------------
 * Debug function to display a list of transfer descriptors
 */
static
void dumpTransferList(USB_TransferDescriptor_T * tdP)
{
  while(tdP) {
    DM_CwDbgPrintf(DM_CW_USB_HOST_0, "List %08X  %08X %08X %08X %08X\n",
	    tdP,
	    tdP->Control.d,
	    tdP->CurrentBufferPointer.p,
	    tdP->NextTD.p,
	    tdP->BufferEnd.p);
    tdP = tdP->NextTD.p;
  }
}

/*----------------------------------------------------------------------
 * Get/free message buffers. Very simple allocation mechanism and fixed
 * length buffers.
 */
static
void freeBuffer(void * p)
{
  int i = ((char*)p - bufListP) / USBD_BUFSIZ;
  if ((i < 0) || (i > USBD_MAX_BUF))
    DM_CwDbgPrintf(DM_CW_USB_HOST_0, "Free buffer index out of range, %d\n", i);
  else {
//    if (!bufAlloc[i])
      if (!(*(bufAllocP + i)))
      DM_CwDbgPrintf(DM_CW_USB_HOST_0, "Free buffer %d not allocated\n", i);
//    bufAlloc[i] = 0;
    *(bufAllocP + i) = 0;

  }
}

/*----------------------------------------------------------------------
 *
 */
static
void * newBuffer(void)
{
  int i;

  for (i=0; i < USBD_MAX_BUF; i++) {
/*
    if (bufAlloc[i] == 0) {

⌨️ 快捷键说明

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