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

📄 exp12.c

📁 ALTERA NIOS处理器实验
💻 C
字号:
/*******************************************/
#include "excalibur.h"
#include "exp12.h"  
/*******************************************/
UCHAR USB_Buff[Bulk_Len];
UCHAR Setup_Step=FALSE,Config;
/********Main Program***********************/
int main(void)
{
   na_D12_CS->np_piodata=1;   //USB模块无效
   na_LCD_CS->np_piodata=1;   //LCD模块无效
   na_D12_WR->np_piodata=1;   //读、写信号无效
   na_D12_RD->np_piodata=1;   

   nr_installuserisr(na_D12_INT_irq,D12_INT_ISR,0);   //分配中断服务程序
   na_D12_INT->np_piodirection=0;
   na_D12_INT->np_pioedgecapture=0;
   ENABLE;   
   USB_Port_Init();    //枚举USB
   while(1);
}
/**********中断服务子程序***************/
void D12_INT_ISR(int context)
{ 
   UINT Int_Flag;
   DISABLE;
   na_D12_INT->np_pioedgecapture=0;    //清除中断标志
   Int_Flag=USB_Read_INT_Flag();    //读取中断标志
   if(Int_Flag & 0x0001)    //端点0 OUT中断
      USB_EndPoint0_OUT();
   if(Int_Flag & 0x0002)    //端点0 IN 中断
      USB_EndPoint0_IN();
   if(Int_Flag & 0x0004)    //端点1 OUT中断
      USB_EndPoint1_OUT();
   if(Int_Flag & 0x0008)    //端点1 IN 中断
      USB_EndPoint1_IN();
   if(Int_Flag & 0x0010)    //端点2 OUT中断
      USB_EndPoint2_OUT();
   if(Int_Flag & 0x0020)    //端点2 IN 中断
      USB_EndPoint2_IN();
   if(Int_Flag & 0x0040)    //总线复位
      SUSPEND=1;
   if(Int_Flag & 0x0080)    //挂起改变
      SUSPEND=1;
   printf("Interrupt:%x\n",Int_Flag);
   ENABLE;   
}
/**********延迟程序*****************/
void Delay(UINT m_Delay)
{
   while(m_Delay--);	
}
/**********D12操作程序*****************/
void USB_Write_Command(UCHAR m_Command)//写命令
{
    na_D12_DB->np_piodirection=0xff;  //数据总线:输出
    na_D12_A0->np_piodata=1;   //选择命令
    na_D12_CS->np_piodata=0;   //片选拉低
    na_D12_WR->np_piodata=0;   //写信号有效
    na_D12_DB->np_piodata=m_Command;
    na_D12_WR->np_piodata=1;   //写信号无效
    na_D12_CS->np_piodata=1;   //片选无效
}
void USB_Write_Data(UCHAR m_Data) //写数据
{
    na_D12_DB->np_piodirection=0xff;  //数据总线:输出
    na_D12_A0->np_piodata=0;   //选择数据
    na_D12_CS->np_piodata=0;   //片选拉低
    na_D12_WR->np_piodata=0;   //写信号有效
    na_D12_DB->np_piodata=m_Data;
    na_D12_WR->np_piodata=1;   //写信号无效
    na_D12_CS->np_piodata=1;   //片选无效
}
UCHAR USB_Read_Data(void)      //读数据
{
    UCHAR Temp;
    na_D12_DB->np_piodirection=0x00;  //数据总线:输入
    na_D12_A0->np_piodata=0;   //选择数据
    na_D12_CS->np_piodata=0;   //片选拉低
    na_D12_RD->np_piodata=0;   //读信号有效
    Temp=na_D12_DB->np_piodata;
    na_D12_RD->np_piodata=1;   //读信号无效
    na_D12_CS->np_piodata=1;   //片选无效
    return Temp;
}

void USB_Port_Init(void)
{
   SUSPEND=0;               //唤醒USB芯片
   USB_SetDMA_Mode(0x00);   //设置USB DMA
   USB_Connect(0x02,0x4b);  //断开USB
   nr_delay(1000);          //等待大约1秒钟
   USB_Connect(0x12,0x45);  //重新连接USB
   USB_Read_INT_Flag();   
}
void USB_Connect(UCHAR m_Mode,UCHAR m_Clk)
{
   USB_Write_Command(0xf3);
   USB_Write_Data(m_Mode);
   USB_Write_Data(m_Clk);
}
void USB_SetAddr_Enable(UCHAR m_Addr,UCHAR m_Enable)
{
   USB_Write_Command(0xd0);
   if(m_Enable)
      USB_Write_Data(m_Addr | 0x80);
   else
      USB_Write_Data(m_Addr);
}
void USB_SetEndPoint_Enable(UCHAR m_Enable)
{
   USB_Write_Command(0xd8);
   if(m_Enable)
      USB_Write_Data(0x01);
   else
      USB_Write_Data(0x00);
}
void USB_SetDMA_Mode(UCHAR m_Mode)
{
   USB_Write_Command(0xfb);
   USB_Write_Data(m_Mode);
}
UINT USB_Read_INT_Flag(void)       //读中断标志
{
   UINT Temp1,Temp2;
   USB_Write_Command(0xf4);
   Temp2=USB_Read_Data();
   Temp1=USB_Read_Data();
   Temp1<<=8;
   return Temp1+Temp2;
}
UCHAR USB_Read_LastStatus(UCHAR m_EndPoint)    //读最后处理状态寄存器
{
   UCHAR Temp;
   USB_Write_Command(0x40+m_EndPoint);
   Temp=USB_Read_Data();
   return Temp;
}
UCHAR USB_Read_EndPoint_Buff(UCHAR m_EndPoint,UCHAR m_Len,UCHAR *m_Buff)  //读缓冲区
{
   UCHAR len,i,Temp;
   USB_Write_Command(m_EndPoint);
   if(USB_Read_Data() & 0x01==0)  //如果缓冲区为空,则返回
      return 0;
   else
   {
      USB_Write_Command(0xf0);
      na_D12_DB->np_piodirection=0x00;  //数据总线:输入
      na_D12_A0->np_piodata=0;   //选择数据
      na_D12_CS->np_piodata=0;   //片选拉低
      //Temp=USB_Read_Data();
      na_D12_RD->np_piodata=0;   //读信号有效
      Temp=na_D12_DB->np_piodata;
      na_D12_RD->np_piodata=1;   //读信号无效
      //len=USB_Read_Data();
      na_D12_RD->np_piodata=0;   //读信号有效
      len=na_D12_DB->np_piodata;
      na_D12_RD->np_piodata=1;   //读信号无效
      if(len>m_Len)
         len=m_Len;
      for(i=0;i<len;i++)
      {
         //m_Buff[i]=USB_Read_Data();
         na_D12_RD->np_piodata=0;   //读信号有效
         m_Buff[i]=na_D12_DB->np_piodata;
         na_D12_RD->np_piodata=1;   //读信号无效
      }
      USB_Write_Command(0xf2);  //清除缓冲区
      return len;      
   }
}
void USB_Write_EndPoint_Buff(UCHAR m_EndPoint,UCHAR m_Len,UCHAR *m_Buff)    //写缓冲区
{
   UCHAR i;
   USB_Write_Command(m_EndPoint);
   USB_Write_Command(0xf0);
   na_D12_A0->np_piodata=0;   //选择数据
   na_D12_CS->np_piodata=0;   //片选拉低
   //USB_Write_Data(0);
   na_D12_WR->np_piodata=0;   //写信号有效
   na_D12_DB->np_piodata=0;
   na_D12_WR->np_piodata=1;   //写信号无效
   //USB_Write_Data(m_Len);
   na_D12_WR->np_piodata=0;   //写信号有效
   na_D12_DB->np_piodata=m_Len;
   na_D12_WR->np_piodata=1;   //写信号无效
   for(i=0;i<m_Len;i++)
   {
      //USB_Write_Data(m_Buff[i]);
      na_D12_WR->np_piodata=0;   //写信号有效
      na_D12_DB->np_piodata=m_Buff[i];
      na_D12_WR->np_piodata=1;   //写信号无效
   }
   USB_Write_Command(0xfa);    //使缓冲区有效
}
void USB_EndPoint_Setup_Ack(UCHAR m_EndPoint)   //SetUp包应答
{
   USB_Write_Command(m_EndPoint);
   USB_Write_Command(0xf1);
   if(m_EndPoint == 0)
      USB_Write_Command(0xf2);
}
void USB_SetEndPoint_Status(UCHAR m_EndPoint,UCHAR m_Stall)    //设置端点状态
{
   USB_Write_Command(0x40+m_EndPoint);
   USB_Write_Data(m_Stall);
}
UCHAR USB_GetEndPoint_Status(UCHAR m_EndPoint)    //获取端点状态
{
   UCHAR Temp;
   USB_Write_Command(0x40+m_EndPoint);
   Temp=USB_Read_Data();
   return Temp;
}
void USB_Stall(void)         //设备停止
{
   USB_SetEndPoint_Status(0,1);
   USB_SetEndPoint_Status(1,1);
}

void USB_EndPoint0_IN(void)     //端点0 IN 中断服务子程序
{
   UCHAR m_Status;
   m_Status=USB_Read_LastStatus(1);
   if(Setup_Step==USB_Device_Setup_Flag)            //发送设备描述符剩下的2字节
   {
      USB_Write_EndPoint_Buff(1,2,DEVICE_DISCRIPTOR+16);
      Setup_Step=FALSE;
   }
   else if(Setup_Step==USB_Interface_Setup_Flag)     //发送接口描述符
   {
      USB_Write_EndPoint_Buff(1,16,CONFIG_DISCRIPTOR+16);
      Setup_Step=USB_EndPoint_Setup_Flag;
   }
   else if(Setup_Step==USB_EndPoint_Setup_Flag)     //发送端点描述符
   {
      USB_Write_EndPoint_Buff(1,14,CONFIG_DISCRIPTOR+32);
      Setup_Step=FALSE;
   }
   else 
      USB_Write_EndPoint_Buff(1,0,0);
}
void USB_EndPoint0_OUT(void)    //端点0 OUT中断服务子程序
{
   UCHAR m_Status,i;
   UINT Data_Len;
   m_Status=USB_Read_LastStatus(0);
   printf("Status:%x\n",m_Status);
   Data_Len=USB_Read_EndPoint_Buff(0,8,USB_Buff);   //读取数据到USB_Buff
   USB_EndPoint_Setup_Ack(0);    //应答Setup包
   USB_EndPoint_Setup_Ack(1);
   Data_Len = USB_Buff[7]*255 + USB_Buff[6];   //获取字节长度
   printf("Data:");
   for(i=0;i<8;i++)
      printf(" %x  ",USB_Buff[i]);
   printf("\n\n");
   if((m_Status & 0x21) == 0x21)  //接收到正确的setup包
   {
      if(USB_Buff[0]==0x00)
      {
         if(USB_Buff[1]==0x05)   //设置地址
         {
            USB_SetAddr_Enable(USB_Buff[2],TRUE);
            USB_Write_EndPoint_Buff(1,0,0);
         }
         else if(USB_Buff[1]==0x09)  //设置配置
         {
            if(USB_Buff[2]==0x00 && USB_Buff[3]==0x00)
            {
               Config=0;
               USB_Write_EndPoint_Buff(1,0,0);
               USB_SetEndPoint_Enable(0);
            }   
            else if(USB_Buff[2]==0x01 && USB_Buff[3]==0x00)
            {
               Config=1;
               USB_Write_EndPoint_Buff(1,0,0);
               USB_SetEndPoint_Enable(1);
            }
            else   //使端点0处于停止状态
               USB_Stall();
         }
         else      //使端点0处于停止状态
            USB_Stall();
      }
      else if(USB_Buff[0]==0x80)
      {
         if(USB_Buff[1]==0x06)    //获取描述符
         {
            if(USB_Buff[3]==0x01)   //设备描述符
            {  
               USB_Write_EndPoint_Buff(1,16,DEVICE_DISCRIPTOR);
               if(Data_Len==18)
                  Setup_Step=USB_Device_Setup_Flag;
            }
            else if(USB_Buff[3]==0x02)   //获取配置描述符
            {
               printf("config");
               if(Data_Len==9)
                  USB_Write_EndPoint_Buff(1,9,CONFIG_DISCRIPTOR);
               else if(Data_Len>16)
               {
                  USB_Write_EndPoint_Buff(1,16,CONFIG_DISCRIPTOR);
                  Setup_Step=USB_Interface_Setup_Flag;
               }
            }
            else    //使端点0处于停止状态
               USB_Stall();              
         }
         else if(USB_Buff[1]==0x08)   //读取配置状态
            USB_Write_EndPoint_Buff(1,1,&Config);
         else    //使端点0处于停止状态
            USB_Stall();
      }
      else if(USB_Buff[0]==0x81)
      {
         if(USB_Buff[1]==0x0a)      //获取接口状态
         { 
            USB_Buff[7]=0x00;
            USB_Write_EndPoint_Buff(1,1,USB_Buff+7);                  
         }
         else   //使端点0处于停止状态
            USB_Stall();            
      }
      else    //使端点0处于停止状态
         USB_Stall();
   }  
}
void USB_EndPoint1_IN(void)      //端点1 IN中断服务子程序
{

}
void USB_EndPoint1_OUT(void)     //端点1 OUT中断服务子程序
{ 

}
void USB_EndPoint2_IN(void)      //端点02 IN中断服务子程序
{

}
void USB_EndPoint2_OUT(void)     //端点2 OUT中断服务子程序
{

}

⌨️ 快捷键说明

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