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

📄 mcu.c

📁 串口通信程序与IIC程序.详细说明了上位机与下位机的通信过程。
💻 C
📖 第 1 页 / 共 2 页
字号:
                                _nop_();
   	 			REG_CON=REG_CON<<1;
   	 		}
   	 	}

   	 	SMI_END();
   	}


   	/*************************************
   	名称:request()
   	功能:读取设备的工作状态
   	参数:COMD指示命命令状态
   	返回:无
   	*************************************/
   	void request(uchar COMD)
   	{
   		uint temp;
   		uchar length;
   		switch(COMD)
   		{
   			case 0x4C:

				temp=reg22>>2;
				if(temp&0x0001)		transmit[6]=0x59;// 判断电口是不是自适应
                else				transmit[6]=0x4E;

				temp=reg22>>6;
				if(temp&0x0001)    transmit[7]=0x4E;//判断电口是否连接
   				else               transmit[7]=0x59;

				temp=reg22>>4;
   				if(temp&0x0001)    transmit[8]=0x46;//判断电口是工作在全双工还是半双工
   				else				transmit[8]=0x48;

   			  	temp=reg22>>3;
   				if(temp&0x0001)    transmit[9]=100;//判断电口是工作在10M/或100M
   				else				transmit[9]=10;

   				temp=reg22>>9;
   				if(temp&0x0001)    transmit[10]=0x4E;//判断光口是否连接
   				else				transmit[10]=0x59;

   			  	temp=reg22>>8;
   				if(temp&0x0001)    transmit[11]=0x46;//判断光口是工作在全双工还是半双工
   				else				transmit[11]=0x48;

   				temp=reg22>>11;

				transmit[12]=100;//光口是工作在100M

				temp=reg22>>10;
				if(temp&0x0001)		transmit[13]=0x59;
				else				transmit[13]=0x4E;

                length=13;
   			    transmit[1]=length;
				transmit[5]=COMD;
   			    transmit[length+1]=cksum(length);
   			    transmit[length+2]=0x7E;
   			    send(length+3);
			break;

			case 0x52:
				temp=reg23>>2;
				if(temp&0x0001)		transmit[6]=0x59;// 判断电口是不是自适应
				else				transmit[6]=0x4E;

				temp=reg23>>6;
				if(temp&0x0001)    transmit[7]=0x4E;//判断电口是否连接
   				else				transmit[7]=0x59;

				temp=reg23>>4;
   				if(temp&0x0001)    transmit[8]=0x46;//判断电口是工作在全双工还是半双工
   				else				transmit[8]=0x48;

   			  	temp=reg23>>3;
   				if(temp&0x0001)    transmit[9]=100;//判断电口是工作在10M/或100M
   				else				transmit[9]=10;

   				temp=reg23>>9;
   				if(temp&0x0001)    transmit[10]=0x4E;//判断光口是否连接
   				else				transmit[10]=0x59;

   			  	temp=reg23>>8;
   				if(temp&0x0001)    transmit[11]=0x46;//判断光口是工作在全双工还是半双工
   				else				transmit[11]=0x48;

				transmit[12]=100;//光口是工作在100M

				transmit[13]=0x4E; // 对端时此位无效


   				length=13;
   			    transmit[1]=length;
				transmit[5]=COMD;
   			    transmit[length+1]=cksum(length);
   			    transmit[length+2]=0x7E;
   			    send(length+3);

   	    }
	}




   	/*************************************
   	名称:command()
   	功能:执行上位机发出的配置命令
   	参数:CMD
   	返回:无
   	*************************************/
   	void command(uchar CMD)
   	{
   		uint temp=0;
   		switch(CMD)
   		{
   				temp=SMI_READ(22);
				case 0x4F://配置局端设备的工作模式
   				if(receive[6]==0x59)
                                {
                                    temp=temp|0x0004; //配置电口为自适应
									SMI_WRITE(22,temp);
                                	temp=SMI_READ(22);
									temp=temp|0x000C;
									SMI_WRITE(22,temp);

                                        softrst();
								}
   				else
                                {
   					temp=temp&0xFFFB;
					if(receive[7]==0x46)	temp=temp|0x0010;//当不是自适应时看双工配置
					else                    temp=temp&0xFFEF;

   					if(receive[8]==100)		temp=temp|0x0008;//当不是自适应时看电口速率配置
					else                            temp=temp&0XFFF7;

					temp=temp&0X8FFF;
   					if(receive[9]==0)	temp=temp&0xE7FF;
					if(receive[9]==1)	temp=temp|0x0800;
   					if(receive[9]==2)	temp=temp|0x1000;
   					if(receive[9]==3)	temp=temp|0x1800;

   					if(receive[10]==0)	temp=temp&0x9FFF;
					if(receive[10]==1)	temp=temp|0x2000;
   					if(receive[10]==2)	temp=temp|0x4000;
   					if(receive[11]==3)	temp=temp|0x6000;
					SMI_WRITE(22,temp);
                                transmit[1]=6;
				}

					transmit[5]=CMD;
					transmit[6]=0x59;
					transmit[7]=cksum(6);
					transmit[8]=0x7E;
					send(9);
				break;

				case 0x53:
					 SMI_WRITE(24,0X0B37);
					 temp=SMI_READ(27);
                     if(receive[6]==0x59)
                     {
                     	temp=temp|0x0004; //配置电口为自适应
						SMI_WRITE(25,temp);
        				SMI_WRITE(24,0X0B77);

						SMI_WRITE(24,0X0037);
					    temp=SMI_READ(27);
						temp=temp|0x0200;
                        SMI_WRITE(25,temp);
						SMI_WRITE(24,0X0077);

                        //softrst();
                     }
   					else
   					{
   						temp=temp&0xFFFB;
						if(receive[7]==0x46)	temp=temp|0x0010;//当不是自适应时看双工配置
						else                    temp=temp&0xFFEF;

   						if(receive[8]==100)		temp=temp|0x0008;//当不是自适应时看电口速率配置
						else                            temp=temp&0XFFF7;

						temp=temp&0X8FFF;
   						if(receive[9]==0)	temp=temp&0xE7FF;
						if(receive[9]==1)	temp=temp|0x0800;
   						if(receive[9]==2)	temp=temp|0x1000;
   						if(receive[9]==3)	temp=temp|0x1800;

   						if(receive[10]==0)	temp=temp&0x9FFF;
						if(receive[10]==1)	temp=temp|0x2000;
   						if(receive[10]==2)	temp=temp|0x4000;
   						if(receive[11]==3)	temp=temp|0x6000;
						SMI_WRITE(25,temp);
        				SMI_WRITE(24,0X0B77);
					}

					transmit[1]=6;
					transmit[5]=CMD;
					transmit[6]=0x59;
					transmit[7]=cksum(6);
					transmit[8]=0x7E;
					send(9);
					break;
   		}
   	}


         /*************************************
   	名称:cksum()
   	功能:计算数据帧的较验和
   	参数:length
   	返回:sum
   	*************************************/
   	uchar cksum(uchar LEN)
   	{
   		uchar sum=0,i;
   		for(i=0;i<LEN;i++)
   			sum=sum+transmit[i];

   		return(sum);
   	}

   	/*************************************
   	名称:send()
   	功能:向后台机发送数据
   	参数:number
   	返回:无
   	*************************************/
   	 void send(uchar LEN)
   	 {
   	 	uchar i;
                ES=0;
   	 	TRCONL=1;
   	        for(i=0;i<LEN;i++)
   	 	{
   	 	  SBUF=transmit[i];
	          while(TI==0);
   	          TI=0;
   	 	}
                TRCONL=0;
                ES=1;

   	}


        void main()
	{

	  uint temp=0;
	  P1_0=0;
	  P1_1=0;
	  MADDR=1;
      SADDR=1;
      MDIO=1;
	  A_T=0;
	  SP=0x70;
	  TH1=0xFA;	/*9600BPS;*/
	  TL1=0xFA;
	  SM2=0;
	  SCON=0x50;	/*方式3,8位数据,1起/停止位,SM2=1*/
	  TMOD=0x21;	/*串口初始化,T0用于软件看门狗*/
	  TR1=1;
	  ES=1;
	  address();
	  EA=1;
	  TRCONL=0;
          reg20=SMI_READ(20);//将IP113F自动发送帧改成ICPLUS模式,以便对用户端进行监测与配置
          reg20=reg20&0xEBFF;
          reg20=reg20|0x0200;
          SMI_WRITE(20,reg20);
          reg20=SMI_READ(20);


  	while(1)
  	{
        address();
        reg22=SMI_READ(22);
        reg23=SMI_READ(23);
        if(FLAG==1)		/*判断命令状态并执行相应的操作*/
   	   {

                transmit[0]=0x7E;
   	   	transmit[2]=1;  //设备类别标识,1表示为单电口光纤收发器
   	   	transmit[3]=MADD;
   	   	transmit[4]=SADD;
   	   	CMD=receive[5];
   	    switch(CMD)
   	      {
   	    	case 0x5E:	/*5EH发送本、对端的数据*/
   	    	  request(0x4C);
   	    	  request(0x52);
   	    	  break;

   	    	case 0x4C:	/*4CH发送本端的数据*/
   	    	 request(0x4C);
   	    	break;

   	    	case 0x52:	/*52H发送对端的数据*/
   	    	request(0x52);
   	    	break;

   	    	case 0x4F:      //配置局端设备工作状态
   	    	command(0x4F);
   	    	break;

   	    	case 0x53:	//配置用户端端设备工作状态
   	    	command(0x53);
			break;

			case 0x4E:
			softrst();

   	      }
   	      FLAG=0;    }
   	      //delay();
   	}

   	}

         /*************************************
   	名称:delay()
   	功能:延时一段时间
   	参数:无
   	返回:无
   	*************************************/
   	void delay(void) using 2
   	{
   		uchar i,j;
   		for(i=0;i<1;i++)
   		{
   			for(j=0;j<127;j++)
   			 _nop_();
   		}
   	}


   	 /*************************************
   	名称:recept()
   	功能:接收后台机发送数据
   	参数:number
   	返回:无
   	*************************************/

   	    void recept(void) interrupt 4 using 1
   	    {
   	    	uchar i,sum=0,j;
   	    	RI=0;
                receive[0]=SBUF;

			TR0=0;
			TF0=0;
			TH0=0;
   	    	TL0=0;
   	    	TR0=1;
   	    	while(RI==0)
   	    	{
   	    	  	if(TF0==1)
   	    	   	goto out;
   	    	 }
   	   		RI=0;
   	    	receive[1]=SBUF;

			for(i=2;i<receive[1]+3;i++)
   	    	{
		  	    TR0=0;
				TF0=0;
   	    	  	TH0=0;
   	    	  	TL0=0;
   	    	  	TR0=1;
   	    	  	while(RI==0)
   	    	  	{
   	    	  		if(TF0==1)
   	    	   		goto out;
   	    	  	}
   	   		RI=0;
   	    	  	receive[i]=SBUF;
   	    	}
                if(receive[3]==MADD)
   	    	{
   	    	  if(receive[4]==SADD)
   	    	  {
   	    	    if(receive[0]==0x7E)
   	    	    {
   	    	       j=receive[1];
   	    	       //if(receive[j+2]==0x7E)
   	    		   //{
   	    				for(i=1;i<=receive[1];i++)
   	    				{
   	    					sum=sum+receive[i];
   	    				}

   	    				if(sum==receive[j+1])
   	    				FLAG=1;
   	    			//}
   	    	    }
   	    	  }
   	        }
   	   else  FLAG=0;
   	 out: TF0=0;

   	}









































































⌨️ 快捷键说明

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