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

📄 usb_isr.c

📁 包含介绍C8051F320的USB控制器的固件编程对固件设计者很有帮助
💻 C
字号:
/*
   Copyright 2003 Cygnal Integrated Products, Inc.   File:    usb_isr.c
   Author:  JS
   Created: JAN 03

   Target Device: C8051F320

   Source file for USB firmware. Includes the following routines:

   - USB_ISR(): Top-level USB interrupt handler. All USB handler
      routines are called from here.
   - Endpoint0(): Endpoint0 interrupt handler.
   - BulkOrInterruptOut(): Bulk or Interrupt OUT interrupt
      handler.
   - BulkOrInterruptIn(): Bulk or Interrupt IN interrupt
      handler.
   - USBReset (): USB Reset event handler.

******************************************/
#include "c8051F320.h"
#include "usb_regs.h"
#include "usb_structs.h"
#include "usb_main.h"
#include "usb_desc.h"#include "usb_config.h"
#include "usb_request.h"

extern DEVICE_STATUS gDeviceStatus;
extern EP0_COMMAND gEp0Command;
extern EP_STATUS gEp0Status;
extern EP_STATUS gEp1InStatus;
extern EP_STATUS gEp2OutStatus;
extern BYTE OUT_PACKET[];
extern BYTE IN_PACKET[];

//---------------------------//  USB ISR//---------------------------//
// This is the top level USB ISR. All endpoint interrupt/request
// handlers are called from this function.
//
// Handler routines for any configured interrupts should be
// added in the appropriate endpoint handler call slots.
//void USB_ISR () interrupt 8{
   BYTE bCommonInt, bInInt, bOutInt;
   // Read interrupt registers
   UREAD_BYTE(CMINT, bCommonInt);   UREAD_BYTE(IN1INT, bInInt);   UREAD_BYTE(OUT1INT, bOutInt);   // Check for reset interrupt   if (bCommonInt & rbRSTINT)
   {
      // Call reset handler
      USBReset();   }
   // Check for Endpoint0 interrupt   if (bInInt & rbEP0)
   {
      // Call Endpoint0 handler
      Endpoint0 ();
   }   // Endpoint1 IN   if (bInInt & rbIN1)
   {
      // Call Endpoint1 IN handler
      BulkOrInterruptIn(&gEp1InStatus);
   }

   // Endpoint2 OUT   if (bOutInt & rbOUT2)
   {
      // Call Endpoint2 OUT handler
      BulkOrInterruptOut(&gEp2OutStatus);
   }}//---------------------------//  Endpoint0 Handler//---------------------------void Endpoint0 (){
   BYTE bTemp = 0;
   BYTE bCsr1, uTxBytes;

   UWRITE_BYTE(INDEX, 0);                 // Target ep0
   UREAD_BYTE(E0CSR, bCsr1);

   // Handle Setup End
   if (bCsr1 & rbSUEND)                   // Check for setup end
   {                                      // Indicate setup end serviced
      UWRITE_BYTE(E0CSR, rbSSUEND);
      gEp0Status.bEpState = EP_IDLE;      // ep0 state to idle
   }

   // Handle sent stall
   if (bCsr1 & rbSTSTL)                   // If last state requested a stall
   {                                      // Clear Sent Stall bit (STSTL)
      UWRITE_BYTE(E0CSR, 0);
      gEp0Status.bEpState = EP_IDLE;      // ep0 state to idle
   }

   // Handle incoming packet
   if (bCsr1 & rbOPRDY)
   {
      // Read the 8-byte command from Endpoint0 FIFO
      FIFORead(0, 8, (BYTE*)&gEp0Command);

      // Byte-swap the wIndex field
      bTemp = gEp0Command.wIndex.c[1];
      gEp0Command.wIndex.c[1] = gEp0Command.wIndex.c[0];
      gEp0Command.wIndex.c[0] = bTemp;

      // Byte-swap the wValue field
      bTemp = gEp0Command.wValue.c[1];
      gEp0Command.wValue.c[1] = gEp0Command.wValue.c[0];
      gEp0Command.wValue.c[0] = bTemp;

      // Byte-swap the wLength field
      bTemp = gEp0Command.wLength.c[1];
      gEp0Command.wLength.c[1] = gEp0Command.wLength.c[0];
      gEp0Command.wLength.c[0] = bTemp;

      // Decode received command
      switch (gEp0Command.bmRequestType & CMD_MASK_COMMON)
      {
         case  CMD_STD_DEV_OUT:           // Standard device requests
            // Decode standard OUT request
            switch (gEp0Command.bRequest)
            {
               case SET_ADDRESS:
                  SetAddressRequest();
                  break;
               case SET_FEATURE:
                  SetFeatureRequest();
                  break;
               case CLEAR_FEATURE:
                  ClearFeatureRequest();
                  break;
               case SET_CONFIGURATION:
                  SetConfigurationRequest();
                  break;
               case SET_INTERFACE:
                  SetInterfaceRequest();
                  break;
               // All other OUT requests not supported
               case SET_DESCRIPTOR:
               default:
                  gEp0Status.bEpState = EP_ERROR;
                  break;
            }
            break;

         // Decode standard IN request
         case CMD_STD_DEV_IN:
            switch (gEp0Command.bRequest)
            {
               case GET_STATUS:
                  GetStatusRequest();
                  break;
               case GET_DESCRIPTOR:
                  GetDescriptorRequest();
                  break;
               case GET_CONFIGURATION:
                  GetConfigurationRequest();
                  break;
               case GET_INTERFACE:
                  GetInterfaceRequest();
                  break;
               // All other IN requests not supported
               case SYNCH_FRAME:
               default:
                  gEp0Status.bEpState = EP_ERROR;
                  break;
            }
            break;
         // All other requests not supported
         default:
            gEp0Status.bEpState = EP_ERROR;
      }

      // Write E0CSR according to the result of the serviced out packet
      bTemp = rbSOPRDY;
      if (gEp0Status.bEpState == EP_ERROR)
      {
         bTemp |= rbSDSTL;                // Error condition handled
                                          // with STALL
         gEp0Status.bEpState = EP_IDLE;   // Reset state to idle
      }

      UWRITE_BYTE(E0CSR, bTemp);
   }

   bTemp = 0;                             // Reset temporary variable

   // If state is transmit, call transmit routine
   if (gEp0Status.bEpState == EP_TX)
   {
      // Check the number of bytes ready for transmit
      // If less than the maximum packet size, packet will
      // not be of the maximum size
      if (gEp0Status.uNumBytes <= EP0_MAXP)
      {
         uTxBytes = gEp0Status.uNumBytes;
         gEp0Status.uNumBytes = 0;        // update byte counter
         bTemp |= rbDATAEND;              // This will be the last
                                          // packet for this transfer
         gEp0Status.bEpState = EP_IDLE;   // Reset endpoint state
      }

      // Otherwise, transmit maximum-length packet
      else
      {
         uTxBytes = EP0_MAXP;
         gEp0Status.uNumBytes -= EP0_MAXP;// update byte counter
      }

      // Load FIFO
      FIFOWrite(0, uTxBytes, (BYTE*)gEp0Status.pData);

      // Update data pointer
      gEp0Status.pData = (BYTE*)gEp0Status.pData + uTxBytes;

      // Update Endpoint0 Control/Status register
      bTemp |= rbINPRDY;                  // Always transmit a packet
                                          // when this routine is called
                                          // (may be zero-length)

      UWRITE_BYTE(E0CSR, bTemp);          // Write to Endpoint0 Control/Status
   }

}
//---------------------------// Bulk or Interrupt OUT Handler//---------------------------void BulkOrInterruptOut(PEP_STATUS pEpOutStatus){
   UINT uBytes;
   BYTE bTemp = 0;
   BYTE bCsrL, bCsrH;

   UWRITE_BYTE(INDEX, pEpOutStatus->bEp); // Index to current endpoint
   UREAD_BYTE(EOUTCSRL, bCsrL);
   UREAD_BYTE(EOUTCSRH, bCsrH);

   // Make sure this endpoint is not halted
   if (pEpOutStatus->bEpState != EP_HALTED)
   {
      // Handle STALL condition sent
      if (bCsrL & rbOutSTSTL)
      {
         // Clear Send Stall, Sent Stall, and data toggle
         UWRITE_BYTE(EOUTCSRL, rbOutCLRDT);
      }

      // Read received packet(s)
      // If double-buffering is enabled, multiple packets may be ready
      while(bCsrL & rbOutOPRDY)
      {
         // Get packet length
         UREAD_BYTE(EOUTCNTL, bTemp);     // Low byte
         uBytes = (UINT)bTemp & 0x00FF;

         UREAD_BYTE(EOUTCNTH, bTemp);     // High byte
         uBytes |= (UINT)bTemp << 8;

         if (uBytes == 8)
         {
            // Read FIFO
            FIFORead(pEpOutStatus->bEp, uBytes, (BYTE*)&OUT_PACKET);
            pEpOutStatus->uNumBytes = uBytes;
         }

         // If a data packet of anything but 8 bytes is received, ignore
         // and flush the FIFO
         else
         {
            UWRITE_BYTE(EOUTCSRL, rbOutFLUSH);
         }

         // Clear out-packet-ready
         UWRITE_BYTE(INDEX, pEpOutStatus->bEp);
         UWRITE_BYTE(EOUTCSRL, 0);

         // Read updated status register
         UREAD_BYTE(EOUTCSRL, bCsrL);
      }
   }
}
//---------------------------//  Endpoint Bulk or Interrupt IN Handler//---------------------------void BulkOrInterruptIn (PEP_STATUS pEpInStatus){
   BYTE bCsrL, bCsrH;

   UWRITE_BYTE(INDEX, pEpInStatus->bEp);  // Index to current endpoint
   UREAD_BYTE(EINCSRL, bCsrL);
   UREAD_BYTE(EINCSRH, bCsrH);

   // Make sure this endpoint is not halted
   if (pEpInStatus->bEpState != EP_HALTED)
   {
      // Handle STALL condition sent
      if (bCsrL & rbInSTSTL)
      {
         UWRITE_BYTE(EINCSRL, rbInCLRDT); // Clear Send Stall and Sent Stall,
                                          // and clear data toggle
      }

      // If a FIFO slot is open, write a new packet to the IN FIFO
      while (!(bCsrL & rbInINPRDY))
      {
         pEpInStatus->uNumBytes = 8;
         pEpInStatus->pData = (BYTE*)&IN_PACKET;

         // Write <uNumBytes> bytes to the <bEp> FIFO
         FIFOWrite(pEpInStatus->bEp, pEpInStatus->uNumBytes,
            (BYTE*)pEpInStatus->pData);

         // Set Packet Ready bit (INPRDY)
         UWRITE_BYTE(EINCSRL, rbInINPRDY);

         // Check updated endopint status
         UREAD_BYTE(EINCSRL, bCsrL);
      }
   }
}

//---------------------------
// USBReset
//---------------------------
// - Initialize the global Device Status structure (all zeros)
// - Resets all endpoints
//void USBReset (){
   BYTE i, bPower = 0;
   BYTE * pDevStatus;  // Reset device status structure to all zeros (undefined)
   pDevStatus = (BYTE *)&gDeviceStatus;
   for (i=0;i<sizeof(DEVICE_STATUS);i++)
   {
      *pDevStatus++ = 0x00;
   }

   // Set device state to default
   gDeviceStatus.bDevState = DEV_DEFAULT;

   // REMOTE_WAKEUP_SUPPORT and SELF_POWERED_SUPPORT
   // defined in file "usb_desc.h"
   gDeviceStatus.bRemoteWakeupSupport = REMOTE_WAKEUP_SUPPORT;
   gDeviceStatus.bSelfPoweredStatus = SELF_POWERED_SUPPORT;   // Reset all endpoints

   // Reset Endpoint0
   gEp0Status.bEpState = EP_IDLE;         // Reset Endpoint0 state
   gEp0Status.bEp = 0;                    // Set endpoint number
   gEp0Status.uMaxP = EP0_MAXP;           // Set maximum packet size
   // Reset Endpoint1 IN
   gEp1InStatus.bEpState = EP_HALTED;     // Reset state
   gEp1InStatus.uNumBytes = 0;            // Reset byte counter

   // Reset Endpoint2 OUT
   gEp2OutStatus.bEpState = EP_HALTED;    // Reset state
   gEp2OutStatus.uNumBytes = 0;           // Reset byte counter

   // Get Suspend enable/disable status. If enabled, prepare temporary
   // variable bPower.
   if (SUSPEND_ENABLE)
   {
      bPower = 0x01;                      // Set bit0 (Suspend Enable)
   }

   // Get ISO Update enable/disable status. If enabled, prepare temporary
   // variable bPower.
   if (ISO_UPDATE_ENABLE)
   {
      bPower |= 0x80;                     // Set bit7 (ISO Update Enable)
   }

   UWRITE_BYTE(POWER, bPower);}

⌨️ 快捷键说明

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