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

📄 调试程序1._c

📁 这段程序是步进电机的细分驱动程序
💻 _C
📖 第 1 页 / 共 4 页
字号:
 	outportb(D12_COMMAND, 0x40 + bEndp);//设置端点状态
	outportb(D12_DATA, bStalled);
	EIMSK=0x01;
}

//读取端点数据
uchar D12_ReadEndpoint(uchar endp, uchar len, uchar * buf)
{                                        //端点号  长度  缓冲区
	unsigned char i, j;
	EIMSK=0x00;
	outportb(D12_COMMAND, endp);
	if((inportb(D12_DATA) & 0x01) == 0)   //读缓冲区是否为空
	{
		EIMSK=0x01;
		return 0;
	}
 	outportb(D12_COMMAND, 0xF0);          //读缓冲区指针自动加1
	j = inportb(D12_DATA);
	j = inportb(D12_DATA);
 	if(j > len)                           //最大长度
		j = len;
 	for(i=0; i<j; i++)
		*(buf+i) = inportb(D12_DATA);     //数据送入缓冲区
	outportb(D12_COMMAND, 0xF2);          //清缓冲区
 	return j;
}
//----------------------------------------------------------------------------
uchar Isr_D12_ReadEndpoint(uchar endp, uchar len, uchar * buf)  //读取双缓冲区数据
{                             
	unsigned char i, j;
	
	EIMSK=0x00;
	outportb(D12_COMMAND, endp);
	if((inportb(D12_DATA) & 0x01) == 0) 
	{
		EIMSK=0x01;
		return 0;
	}
 	outportb(D12_COMMAND, 0xF0);
	j = inportb(D12_DATA);
	j = inportb(D12_DATA);
 	if(j > len)
		j = len;
 	for(i=0; i<j; i++)
		*(buf+i) = inportb(D12_DATA);
	outportb(D12_COMMAND, 0xF2);
	EIMSK=0x01;
 	return j;
}

//写端点
uchar D12_WriteEndpoint(uchar endp, uchar len, uchar * buf)//端点送出出数据
{                                                      
	unsigned char i;
	
 	EIMSK=0x00;
 	outportb(D12_COMMAND, endp);     
	i = inportb(D12_DATA);
 	outportb(D12_COMMAND, 0xF0);                          //写缓冲区
	outportb(D12_DATA, 0);
	outportb(D12_DATA, len);
	for(i=0; i<len; i++)
		outportb(D12_DATA, *(buf+i));
 	outportb(D12_COMMAND, 0xFA);                         //缓冲区有效
	EIMSK=0x01;
	return len;
}

//设置端点应答
void D12_AcknowledgeEndpoint(uchar endp)                //缓冲区确认
{	
	outportb(D12_COMMAND, endp);
	outportb(D12_COMMAND, 0xF1);
	if(endp == 0)
	outportb(D12_COMMAND, 0xF2);
}

//获取设备状态
void get_status(void)
{
	uchar endp, txdat[2];
	uchar bRecipient = ControlData.DeviceRequest.bmRequestType & (uchar)0x1F;
	uchar c;                                      //请求的后五位
	
 	if (bRecipient == (uchar)0x00) 
	{
		if(remote_wakeup == 1)     //获取远程唤醒状态
			txdat[0] = 3;
		else
		  txdat[0] = 1;
		  txdat[1]=0;
		  single_transmit(txdat, 2);
	} 
	else if (bRecipient == (uchar)0x01) 
	{//获取接口状态
		txdat[0]=0;
		txdat[1]=0;
		single_transmit(txdat, 2);      //从端点1发送2个字节的数据
	} 
	else if (bRecipient == (uchar)0x02) 
	{//获取端点状态
		endp = (uchar)(ControlData.DeviceRequest.wIndex & (uchar)0x3);
		if (ControlData.DeviceRequest.wIndex & 0x80)
			c = D12_SelectEndpoint(endp*2 + 1);	//控制输入
		else
			c = D12_SelectEndpoint(endp*2);	//控制输出
		if(c & 0x02)
			txdat[0] = 1;
		else
			txdat[0] = 0;
		txdat[1] = 0;
		single_transmit(txdat, 2);      
	} 
	else
	{
		D12_SetEndpointStatus(0, 1);      //端点01数据发送成功
		D12_SetEndpointStatus(1, 1);
	}
}

//特性清除
void clear_feature(void)
{
	uchar endp;
	uchar bRecipient = ControlData.DeviceRequest.bmRequestType & (uchar)0x1F;
	
	if (bRecipient == (uchar)0x00
		&& ControlData.DeviceRequest.wValue == 0x0001) 
	{//清除远程唤醒功能
		EIMSK=0x00;
		remote_wakeup = 0;
		EIMSK=0x01;
		single_transmit(0, 0);
	}
	else if (bRecipient == (uchar)0x02
		&& ControlData.DeviceRequest.wValue == 0x0000) 
	{//清除端点stall
		endp = (uchar)(ControlData.DeviceRequest.wIndex & (uchar)0x3);
		if (ControlData.DeviceRequest.wIndex & 0x80)
			D12_SetEndpointStatus(endp*2 + 1, 0);
		else
			D12_SetEndpointStatus(endp*2, 0);
		single_transmit(0, 0);
	} 
	else
	{
		D12_SetEndpointStatus(0, 1);
		D12_SetEndpointStatus(1, 1);
	}
}

//特性设置
void set_feature(void)
{
	uchar endp;
	uchar bRecipient = ControlData.DeviceRequest.bmRequestType & (uchar)0x1F;
		
	if (bRecipient == (uchar)0x00
		&& ControlData.DeviceRequest.wValue == 0x0001) 
	{//设置远程唤醒功能
		EIMSK=0x00;
		remote_wakeup = 1;
		EIMSK=0x01;
		single_transmit(0, 0);
	}
	else if (bRecipient == (uchar)0x02
		&& ControlData.DeviceRequest.wValue == 0x0000) 
	{//设置端点stall
		endp = (uchar)(ControlData.DeviceRequest.wIndex & (uchar)0x3);
		if (ControlData.DeviceRequest.wIndex & 0x80)
			D12_SetEndpointStatus(endp*2 + 1, 1);
		else
			D12_SetEndpointStatus(endp*2, 1);
		single_transmit(0, 0);
	} 
	else
	{
		D12_SetEndpointStatus(0, 1);
		D12_SetEndpointStatus(1, 1);
	}
}

//设置地址
void set_address(void)
{	
	D12_SetAddressEnable((uchar)(ControlData.DeviceRequest.wValue & 0x7f), 1);
	single_transmit(0, 0);
}

//获取描述符
void get_descriptor(void)
{
	uchar bDescriptor = MSB(ControlData.DeviceRequest.wValue);	
	
	if (bDescriptor == 0x01) 
	{//获取设备描述符
	
 		code_transmit((uchar *)&DeviceDescr, 0x12);
	} 
	else if (bDescriptor == 0x02) 
	{//获取配置描述符
		code_transmit((uchar *)&ConfigDescr, 0x2e);
	} 
	else
	{
		D12_SetEndpointStatus(0, 1);
		D12_SetEndpointStatus(1, 1);
	}
}

//获取配置状态
void get_configuration(void)
{
	uchar c = configuration;
	
	single_transmit(&c, 1);
}

//设置配置状态
void set_configuration(void)
{	
	if (ControlData.DeviceRequest.wValue == 0) 
	{
		//设备进入未配置状态
		single_transmit(0, 0);
		EIMSK=0x00;
		configuration = 0;
		EIMSK=0x01;
		init_unconfig();
	} 
	else if (ControlData.DeviceRequest.wValue == 1) 
	{
		//配置设备
		single_transmit(0, 0);
		init_unconfig();
		init_config();
		EIMSK=0x00;
		configuration = 1;
		EIMSK=0x01;
	} 
	else
	{
		D12_SetEndpointStatus(0, 1);
		D12_SetEndpointStatus(1, 1);
	}
}

//获取接口状态
void get_interface(void)
{
	uchar txdat = 0;     
	   
	single_transmit(&txdat, 1);
}

//设置接口状态
void set_interface(void)
{
	if (ControlData.DeviceRequest.wValue == 0 && ControlData.DeviceRequest.wIndex == 0)
		single_transmit(0, 0);
	else
	{
		D12_SetEndpointStatus(0, 1);
		D12_SetEndpointStatus(1, 1);
	}
}

//端点0OUT中断
void ep0_rxdone(void)
{
	unsigned char ep_last, i;
	
	ep_last = D12_ReadLastTransactionStatus(0); //清中断标志
	if (ep_last & 0x20)  //接收到SETUP包
	{ 							
		ControlData.wLength = 0;
		ControlData.wCount = 0;
		if( D12_ReadEndpoint(0, sizeof(ControlData.DeviceRequest),
			(uchar *)(&(ControlData.DeviceRequest))) != 0x08 ) 
		{	  //SETUP包出错,返回			
			D12_SetEndpointStatus(0, 1);
			D12_SetEndpointStatus(1, 1);
			control_state = 0;
			return;
		}	
		D12_AcknowledgeEndpoint(0); //对控制端点的输入/输出进行应答
		D12_AcknowledgeEndpoint(1);
		ControlData.wLength = ControlData.DeviceRequest.wLength;
		ControlData.wCount = 0;
		
		if (ControlData.DeviceRequest.bmRequestType & 0x80) 
		{  //从主机传输数据			
			setup_packet = 1;
			control_state = 1; //获取命令
		}
		else 
		{
			if (ControlData.DeviceRequest.wLength == 0) 
			{
				setup_packet = 1;		
			    control_state = 0; //设置命令
			}
			else 
			{
				if(ControlData.DeviceRequest.wLength > 8) 
				{
					//接收数据长度为0
					control_state = 0;
					D12_SetEndpointStatus(0, 1);
					D12_SetEndpointStatus(1, 1);
				}
				else 
				{								  	
					control_state = 2;//设置接收状态
				}
			} 
		} 
	} 												 
	else if (control_state == 2) 
	{
		//接收数据
		i =	D12_ReadEndpoint(0, 16,
			ControlData.dataBuffer + ControlData.wCount);
		ControlData.wCount += i;
		if( i != 16 || ControlData.wCount >= ControlData.wLength) 
		{
			//数据接收完毕				     
			setup_packet = 1;				   
			control_state = 0;
		}
	}
	else 
	{									  
		control_state = 0; //进入等待状态
	}
}

//端点0IN处理
void ep0_txdone(void)
{
	short i = ControlData.wLength - ControlData.wCount;
	
	D12_ReadLastTransactionStatus(1); //清中断标志位  
	
	if (control_state != 1)
		return;//非发送状态,返回
	if( i >= 16) 
	{
		//剩下数据大于16字节,发送16字节
 		EIMSK=0x00;
 		outportb(D12_COMMAND, 1);
		num = inportb(D12_DATA);
 		outportb(D12_COMMAND, 0xF0);
		outportb(D12_DATA, 0);
		outportb(D12_DATA, 16);
		for(num=0; num<16; num++)
			outportb(D12_DATA, *(ControlData.pData + ControlData.wCount+num));
 		outportb(D12_COMMAND, 0xFA);
		EIMSK=0x01;
		ControlData.wCount += 16;		   
		control_state = 1;
	}
	else if( i != 0) 
	{
		//发送剩下数据
 		EIMSK=0x00;
 		outportb(D12_COMMAND, 1);
		num = inportb(D12_DATA);
 		outportb(D12_COMMAND, 0xF0);
		outportb(D12_DATA, 0);
		outportb(D12_DATA, i);
		for(num=0; num<i; num++)
			outportb(D12_DATA, *(ControlData.pData + ControlData.wCount+num));
 		outportb(D12_COMMAND, 0xFA);
		EIMSK=0x01;
		ControlData.wCount += i;		  
		control_state = 0;
	}
	else if (i == 0)
	{
 		EIMSK=0x00;
 		outportb(D12_COMMAND, 1);
		num = inportb(D12_DATA);
 		outportb(D12_COMMAND, 0xF0);
		outportb(D12_DATA, 0);
		outportb(D12_DATA, 0);
 		outportb(D12_COMMAND, 0xFA);
		EIMSK=0x01;
 		control_state = 0;
	}
}


//端点1OUT处理
void ep1_txdone(void)
 {  
	 D12_ReadLastTransactionStatus(3); //清中断标志位 
	 D12_WriteEndpoint(3,2,TxdBuf);
 }

//端点1IN处理
void ep1_rxdone(void)
{
    uchar Len,i;
    uchar StrLen; 
	
	D12_ReadLastTransactionStatus(2);        //清中断标志位
	Len = D12_ReadEndpoint(2, 16, RxdBuf);   //接收数据
    
 if(RxdBuf[0]==0xff)                          //进入工作状态             
	{                                        //开定时器
	 Work.mission_number = RxdBuf[1];         //任务编号 0标样 1样品 2质控
	 Work.strat_number=RxdBuf[2];             //进样盘号 0-30
	 Work.muster_volume=RxdBuf[3];            //进样量  1UL电机552步(微分系数2)
	 Work.clear_time=RxdBuf[4];               //清洗时间  (1-10)秒
	 volume=Work.muster_volume*560;
	 clear_S=Work.clear_time*59;              //延时系数59
	 Work.clear_select=RxdBuf[5];             //清洗选择  (0加酸  1正常  2推拉)
	
	     TCCR1B =0x05;                        //打开定时器1
	     TIMSK=0x04;
	     Work_flag=1;                         //工作标志置1  接收完毕 进样器工作
	}

 else if(RxdBuf[0]==0XEE)                     //进入调试状态
    {
        Debugger.place_number = RxdBuf[1];     //调试任务编号 0 标样杯位置误差写EEP,1样品杯位置误差写EEP,
                                                //2钨舟位置误差写EEP,3钨舟高度误差写EEP,4水阀开关,5气阀开关,
                                                 //6位置测试位,7生降标志,8,9升降高度高低8位
   
	    Debugger.recoup_value=RxdBuf[2];         //误差数值(0-255)
	    Debugger.water_pump=RxdBuf[3];           //水阀状态           1开,0关。
	    Debugger.air_pump=RxdBuf[4];             //气阀状态           1开,0关。
	    Debugger.init_place=RxdBuf[5];           //横杆位置状态       0清洗杯位,1标液位,2样品位,3钨舟位
	    Debugger.armup_down=RxdBuf[6];           //横杆降标志         0上升,1下降
        Debugger.setp_num=RxdBuf[7]*256+RxdBuf[8];     //升降高度高数值(0-65535)
	    Debugger.add_sub=RxdBuf[9];                    //误差数值加减标志     0加 ,1减
		debug_flag=1;                                  //调试标志置1  
	}
	    
 else if (RxdBuf[0]==0xDD)                   //重新复位
     
		reset_flag=1;                        //复位标志置1
    
 }
//主端点OUT控制
void main_txdone(void)
{
	D12_ReadLastTransactionStatus(5); //清中断标志位	
}

//主端点IN控制
void main_rxdone(void)
{	
	uchar Len;
    uchar StrLen; 
	
	D12_ReadLastTransactionStatus(4); //清中断标志位
	Len = D12_ReadEndpoint(4, 64, RxdBuf);//接收数据
	
}

//通讯处理程序[*d:待发送的数据指针]
void MainSend(void)
{
    uchar StrLen; 
	EIMSK=0x00;
	outportb(D12_COMMAND, 3);
	StrLen = inportb(D12_DATA);
	outportb(D12_COMMAND, 0xF0);
	outportb(D12_DATA, 0);
	outportb(D12_DATA, 16);
	for(StrLen=0; StrLen<16; StrLen++)
		outportb(D12_DATA, *(RxdBuf+StrLen));
	outportb(D12_COMMAND, 0xFA);
	EIMSK=0x01;
}

//USB中断服务子程序
#pragma interrupt_handler INTHandler:2
void INTHandler(void)
{
	uint i_st;
	EIMSK=0x00;
	i_st = D12_ReadInterruptRegister();	//读取中断寄存器
	if(i_st != 0) 
	{   	
		if(i_st & 0x01)
		{
			ep0_rxdone();				//端点0OUT中断
		}
		if(i_st & 0x02)
		{
			ep0_txdone();				//端点0IN中断
		}
		if(i_st & 0x04)
		{
			ep1_rxdone();				//端点1OUT中断
		}
		if(i_st & 0x08)
		{
			ep1_txdone();				//端点1IN中断
		}
		if(i_st & 0x10)
		{
			main_rxdone();				//端点2OUT中断
		}
		if(i_st & 0x20)
		{
			main_txdone();				//端点2IN中断 	
		}		
	}
	EIMSK=0x01;
}

//断开USB总线
void disconnect_USB(void)
{
	D12_SetMode(0x02, 0x40 | 0x03);
}

//连接USB总线
void connect_USB(void)
{
	
	D12_SetDMA(0x80 | 0x40|0X10);
	D12_SetMode(0x02|0x10, 0x40 | 0x03);
}

//重新连接到USB总线
void reconnect_USB(void)
{
	ulong clk_cnt;
	disconnect_USB();
	for(clk_cnt=0;clk_cnt<0x800;clk_cnt++);
	connect_USB();
}

//恢复到未配置状态
void init_unconfig(void)
{
	D12_SetEndpointEnable(0);	
}

//设置配置状态
void init_config(void)
{
	D12_SetEndpointEnable(1);	
}

//从端点号1发送数据
void single_transmit(uchar * buf, uchar len)
{
	if( len <= 16) {
		D12_WriteEndpoint(1, len, buf);
	}
}

//发送端点号1建立代码
void code_transmit(uchar * pRomData, ushort len)
{
	ControlData.wCount = 0;
	if(ControlData.wLength > len)
		ControlData.wLength = len;
	ControlData.pData = pRomData;
	if( ControlData.wLength >= 16) 
	{
		D12_WriteEndpoint(1, 16, ControlData.pData);//发送16字节数据
		ControlData.wCount += 16;
		EIMSK=0x00;							   
		control_state = 1;
		EIMSK=0x01;
	}
	else 
	{
		D12_WriteEndpoint(1, ControlData.wLength, pRomData);//发送16字节内数据

⌨️ 快捷键说明

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