首页->【芯航线EDA助学小组】

24 1

quatus ii  13.1 

nios  ii 13.1   

----------------------------------------------------------------------------------------

 * main.c

 *

 *  Created on: 2013-11-2

 *      Author: Administrator

 */


#include "alt_types.h"

#include "io.h"

#include "sys/alt_irq.h"

#include "system.h"

#include <stdio.h>

#include <unistd.h>

#include <sys/alt_timestamp.h>

#include "ch395inc.h"





void Ch395Init(void); //CH395初始化


//////////////////////////////////////////////////////////////////////

//函数名:main

//功     能:主函数

//输     入:无

//返     回:alt_u8

//////////////////////////////////////////////////////////////////////

int main()

{

//串口初始化函数

Uart_init();

//CH395初始化

Ch395Init();

while(1)

{


}

return 0;

}


//////////////////////////////////////////////////////////////////////

//函数名:Ch395Init

//功     能:CH395初始化

//输     入:无

//返     回:无

//////////////////////////////////////////////////////////////////////

void Ch395Init(void)

{

alt_u8 temp;

alt_u8 mac_addr[6];

alt_u8 ip_addr[4] = {192,168,1,101};

alt_u8 gwip_addr[4] = {192,168,1,1};


//复位CH395芯片,并延时50ms

CH395CMDReset();

usleep(50000); //delay 50ms


//获取芯片以及固件版本号,并通过JTAG UART打印

temp = CH395CMDGetVer();

printf("CH395芯片以及固件版本号为:0x%x\n",temp);

//测试命令,输入0x55,返回0xaa

temp = CH395CMDCheckExist(0x55);

printf("CH395测试命令:发送数据0x55,返回数据0x%x\n",temp);

if(temp == 0xaa) printf("CH395通讯正常\n");

else printf("CH395通讯失败\n");

//读取MAC地址并打印

CH395CMDGetMACAddr(mac_addr);

printf("CH395的出厂MAC地址为:%x-%x-%x-%x-%x-%x\n",mac_addr[0],mac_addr[1],mac_addr[2],mac_addr[3],mac_addr[4],mac_addr[5]);

//设置IP地址

CH395CMDSetIPAddr(ip_addr);

//设置网关IP地址

CH395CMDSetGWIPAddr(gwip_addr);

//初始化CH395命令

CH395CMDInitCH395();

//获取命令执行状态

while(1)

{

temp = CH395GetCmdStatus();

usleep(10000); //delay 10ms

if(temp == CMD_ERR_SUCCESS) 

{

printf("CH395命令执行状态:成功\n");

break;

}

}


printf("CH395正在连接以太网\n"); 

while(1)

{                                                                 /* 等待以太网连接成功*/

if(CH395CMDGetPHYStatus() == PHY_DISCONN)                     /* 查询CH395是否连接 */

{

usleep(200000); //delay 200ms                                            /* 未连接则等待200MS后再次查询 */

}

else 

{

printf("CH395已经连接到以太网\n");                       /* CH395芯片连接到以太网,此时会产生中断 */

break;

}

}

}

-----------------------------------------------------------------------------

/*
 * ch395uart.c
 *
 *  Created on: 2013-11-2
 *      Author: Administrator
 */

#include "alt_types.h"
#include "io.h"
#include "altera_avalon_pio_regs.h"
#include "sys/alt_irq.h"
#include "system.h"
#include <stdio.h>
#include <unistd.h>
#include <sys/alt_timestamp.h>
#include "ch395inc.h"

alt_u8 uart_rx_temp;	//串口接收数据缓存
alt_u8 rx_flag;	//串口数据接收标志位

/////////////////////////////////////////////////////////////
//函数名:Handle_Uart_ISR
//功  能:串口接收数据中断服务函数
//参  数:无
//返  回:无
/////////////////////////////////////////////////////////////
void Handle_Uart_ISR(void* nirq_isr_context)
{
	alt_u8 uart_status;
	do{
		uart_status = IORD_16DIRECT(MYUART_BASE,8);//读状态寄存器
	}
    while((uart_status & 0x80) != 0x80);	//判断数据(RRDY == 1)是否接收完毕
	uart_status = IORD_16DIRECT(MYUART_BASE,8);//读状态寄存器
	uart_rx_temp = IORD_8DIRECT(MYUART_BASE,0);//读串口收到的数据
	rx_flag = 1;	//串口数据接收标志位置位
}

/////////////////////////////////////////////////////////////
//函数名:Uart_init
//功  能:串口初始化函数
//参  数:无
//返  回:无
/////////////////////////////////////////////////////////////
void Uart_init(void)
{
	rx_flag = 0;	//串口数据接收标志位清零
    IOWR_16DIRECT(MYUART_BASE,12,0xc0);//打开接收中断使能,打开传输数据使能
    IOWR_16DIRECT(MYUART_BASE,8, 0x0);//清状态标志

    //中断注册(声明中断函数名为handle_Uart_ISR)
    alt_ic_isr_register(MYUART_IRQ_INTERRUPT_CONTROLLER_ID,
    					MYUART_IRQ,
    					Handle_Uart_ISR,
                        NULL,
                        NULL);
    Uart_bps_change(UART_BAUDRATE_9600);	//波特率设置
}
/*
IOWR_16DIRECT(基地址,偏移量,数据)16位写数据函数
IORD_16DIRECT(基地址,偏移量,数据)16位读数据函数

串口的基地址是:UART_BASE
偏移量0:rxdata,接收数据寄存器
偏移量4:txdata,发送数据寄存器
偏移量8:status,状态寄存器
偏移量12:control,控制寄存器

控制寄存器:第6位,ITRDY 准备好传输中断
	    第7位,IRRDY 准备好读取中断
*/

/////////////////////////////////////////////////////////////
//函数名:Uart_bps_change
//功  能:串口波特率设置函数
//参  数:alt_u16 newbps 波特率值
//返  回:无
/////////////////////////////////////////////////////////////
void Uart_bps_change(alt_u16 newbps)
{
	alt_u16 div = (250000/(newbps))-1;

	IOWR_16DIRECT(MYUART_BASE,16,div);//设置波特率分频计数器
}

/////////////////////////////////////////////////////////////
//函数名:Uart_tx
//功  能:串口发送数据函数
//参  数:alt_u8 txdb 发送数据
//返  回:无
/////////////////////////////////////////////////////////////
void Uart_tx(alt_u8 txdb)
{
	alt_u8 uart_status;
	do{
		uart_status = IORD_16DIRECT(MYUART_BASE,8);//读状态寄存器
	}
    while((uart_status & 0x40) != 0x40);	//判断数据(TRDY == 1)是否发送完毕
	uart_status = IORD_16DIRECT(MYUART_BASE,8);	//再次读状态寄存器,清状态寄存器
	IOWR_8DIRECT(MYUART_BASE,4,txdb);	//发送数据
}

/////////////////////////////////////////////////////////////
//函数名:xWriteCH395Cmd
//功  能:向CH395写命令
//参  数:alt_u8 cmd 8位的命令码
//返  回:无
/////////////////////////////////////////////////////////////
void xWriteCH395Cmd(alt_u8 cmd)
{
	Uart_tx(SER_SYNC_CODE1);
	Uart_tx(SER_SYNC_CODE2);
	Uart_tx(cmd);
}

/////////////////////////////////////////////////////////////
//函数名: xWriteCH395Data
//功  能:向CH395写数据
//参  数:alt_u8 mdata 8位数据
//返  回:无
/////////////////////////////////////////////////////////////
void  xWriteCH395Data(alt_u8 mdata)
{
	Uart_tx(mdata);
}

/////////////////////////////////////////////////////////////
//函数名:xReadCH395Data
//功  能:从CH395读数据
//参  数:无
//返  回:8bit读出数据
/////////////////////////////////////////////////////////////
alt_u8  xReadCH395Data(void)
{
	alt_u32 i;

	while(rx_flag == 0);
	rx_flag = 0;
	return(uart_rx_temp);
}



------------------------------------------------------------------------------
/*
 * ch395inc.h
 *
 *  Created on: 2013-11-2
 *      Author: Administrator
 */

/* 常用类型和常量定义 */
/*#ifndef     NULL
#define     NULL    0
#endif*/

/* UART波特率设置宏定义 */
#define UART_BAUDRATE_9600		9600/100		/* 默认通讯波特率9600bps */
#define UART_BAUDRATE_57600		57600/100		/* 通讯波特率57600bps */
#define UART_BAUDRATE_115200	115200/100		/* 通讯波特率115200bps */
#define UART_BAUDRATE_230400	230400/100		/* 通讯波特率230400bps */
#define UART_BAUDRATE_460800	460800/100		/* 通讯波特率460800bps */
#define UART_BAUDRATE_921600	921600/100		/* 通讯波特率921600bps */
#define UART_BAUDRATE_1843200	1843200/100		/* 通讯波特率1843200bps */

/* CH395命令代码 */
#define CMD01_GET_IC_VER                     0X01                    /* 获取芯片以及固件版本号 */
	/* 输出: 版本号( 位7为0, 位6为1, 位5~位0为版本号 ) */
	/*       CH3395返回版本号的值为041H即版本号为01H */
#define CMD31_SET_BAUDRATE                   0x02                    /* 串口方式: 设置串口通讯波特率(上电或者复位后的默认波特率为9600bps */
	/* 输入: 3字节波特率,第字节在前 */
	/* 输出: 操作状态( CMD_RET_SUCCESS, 其它值说明操作未完成 ) */
#define CMD00_ENTER_SLEEP                    0x03                    /* 进入睡眠状态 */
#define CMD00_RESET_ALL                      0X05                    /* 执行硬件复位 */
#define CMD11_CHECK_EXIST                    0X06                    /* 测试通讯接口以及工作状态 */
	/* 输入: 任意数据 */
	/* 输出: 输入数据的按位取反 */
#define CMD10_SET_PHY                        0X20                    /* 设置PHY,默认为Auto,自动协商 */
	/* 输入:PHY参数,参考PHY参数定义 */
#define CMD60_SET_MAC_ADDR                   0X21                    /* 设置MAC地址 必须在CMD00H_INIT_CH395之前设置完毕 */
	/* 输入:6字节的MAC地址 */
#define CMD40_SET_IP_ADDR                    0X22                    /* 设置IP地址 必须在CMD00H_INIT_CH395之前设置完毕 */
	/* 输入:4字节的IP地址 */
#define CMD40_SET_GWIP_ADDR                  0X23                    /* 设置网关IP地址 必须在CMD00H_INIT_CH395之前设置完毕 */
	/* 输入:4字节的网关IP地址 */
#define CMD40_SET_MASK_ADDR                  0X24                    /* 设置子网掩码, 必须在CMD00H_INIT_CH395之前设置完毕 */
	/* 输入:4字节的子网掩码 */
#define CMD90_SET_MAC_FILT                   0X25                    /* 设置MAC过滤 可以进行广播,多播等过滤 */
	/*输入:9字节参数,第1字节为过滤类型,参考过滤类型定义,*/
	/*      第2至第5字节为HASH0,第6至第9字节为HASH1 */
#define CMD01_GET_PHY_STATUS                 0X26                    /* 获取PHY当前状态,如断开连接,10/100M FULL/HALF*/
	/*输出:当前PHY状态,状态定义请参考PHY参数定义 */
#define CMD0W_INIT_CH395                     0X27                    /* 初始化CH395 */
	/*此命令执行时间大约200MS,需要等待此命令执行成功,才可以发下一条命令*/
#define CMD08_GET_UNREACH_IPPORT             0X28                     /* 获取不可达信息 */
	/*输出:8字节,第1字节为不可达类型,参考不可达类型定义
		第2字节协议不可达协议码
		第3,4字节不可达端口
		第5-8字不可达IP*/
#define CMD01_GET_GLOB_INT_STATUS            0X29                    /* 获取全局中断状态,最大值为1S,不可以设置为0 */
	/*输出:全局中断状态,参考全局中断状态定义 */
#define CMD10_SET_RETRAN_COUNT               0X2A                    /* 重试次数,仅在TCP模式下有效 */
	/*输入:重试次数 */
#define CMD20_SET_RETRAN_PERIOD              0X2B                    /* 重试周期,最大值为20,仅在TCP模式下有效,不可以设置为0 */
	/*输入:重试周期 */
#define CMD01_GET_CMD_STATUS                 0X2C                    /* 获取命令执行状态 */
	/*输出:命令执行状态,参考命令执行状态定义 */
#define CMD06_GET_REMOT_IPP_SN               0x2D                    /* 获取远端的端口以及IP地址,该命令在TCP服务器模式下使用 */
	/*输出:6字节,第1-4字节为远端的IP地址,第5-6字节为远端的端口号*/
#define CMD10_CLEAR_RECV_BUF_SN              0X2E                    /* 清除接收缓冲区  */
	/*输入:第1字节为socket的索引值 */
#define CMD12_GET_SOCKET_STATUS_SN           0X2F                    /* 获取socket n状态 */
	/*输入:socket的索引值,*/
	/*输出:第1字节:socket n 打开或者关闭
		第2字节:TCP状态,仅在TCP模式且第1字节为打开状态下有意义*/
#define CMD11_GET_INT_STATUS_SN              0X30                    /* 获取socket n的中断状态 */
	/*输入: socket的索引值*/
	/*输出:全局中断状态,参考全局中断状态定义 */
#define CMD50_SET_IP_ADDR_SN                 0X31                    /* 设置socket n的目的IP地址 */
	/*输入:第1字节为socket的索引值,第2至5字节为IP地址*/
#define CMD30_SET_DES_PORT_SN                0X32                    /* 设置socket n的目的端口 */
	/*输入:第1字节为socket的索引值,第2至3字节为目的端口*/
#define CMD30_SET_SOUR_PORT_SN               0X33                     /* 设置socket n的源端口 */
	/*输入:第1字节为socket的索引值,第2至3字节为源端口*/
#define CMD20_SET_PROTO_TYPE_SN              0X34                    /* 设置socket n的协议类型*/
	/*输入:第1字节为socket的索引值,第2协议类型,参考协议类型定义*/
#define CMD1W_OPEN_SOCKET_SN                 0X35                    /* 打开socket n*/
	/*输入:第1字节为socket的索引值,此命令需要等待命令执行成功 */
#define CMD1W_TCP_LISTEN_SN                  0X36                    /* socket n监听,收到此命令,socket n进入服务器模式,仅对TCP模式有效 */
	/*输入:第1字节为socket的索引值,此命令需要等待命令执行成功 */
#define CMD1W_TCP_CONNECT_SN                 0X37                    /* socket n连接,收到此命令,socket n进入客户端模式,仅对TCP模式有效 */
	/*输入:第1字节为socket的索引值,此命令需要等待命令执行成功 */
#define CMD1W_TCP_DISNCONNECT_SN             0X38                    /* socket n断开连接,收到此命令,socket n断开已有连接,仅对TCP模式有效 */
	/*输入:第1字节为socket的索引值,此命令需要等待命令执行成功 */
#define CMD30_WRITE_SEND_BUF_SN              0X39                    /* 向socket n缓冲区写入数据 */
	/*输入:第1字节为socket的索引值,第2至3字节为长度*/
#define CMD12_GET_RECV_LEN_SN                0X3B                    /* 获取socket n接收数据的长度 */
	/*输入:socket的索引值*/
	/*输出:2字节的接收长度*/
#define CMD30_READ_RECV_BUF_SN               0X3C                    /* 读取socket n接收缓冲区数据*/
	/*输入:第1字节为socket的索引值,第2至3字节为读取的长度n,低位在前 */
	/*输出:n个数据*/
#define CMD1W_CLOSE_SOCKET_SN                0X3D                    /* 关闭socket n*/
	/*输入:socket的索引值*/
#define CMD20_SET_IPRAW_PRO_SN               0X3E                    /* 在IP RAW下,设置socket n的IP包协议类型 */
	/*输入:第1字节为socket的索引值,第2字节为IP RAW协议类型 */
#define CMD01_PING_ENABLE                    0X3F                    /* 开启/关闭PING */
	/*输入:1字节,0为关闭PING,1为开启PING,默认开启 */
#define CMD06_GET_MAC_ADDR                   0X40                    /* 获取MAC地址 */
	/* 输出:6字节的MAC地址 */
	/*37*/

/* CH395增加命令 */
#define CMD10_DHCP_ENABLE                    0X41                    /* DHCP使能 */
	/* 输入:1字节,1启动DHCP,0关闭DHCP */
#define CMD01_GET_DHCP_STATUS                0X42                    /* 获取DHCP状态 */
	/* 输出:1字节状态码,0表示成功,其他值失败 */
#define CMD014_GET_IP_INF                    0X43                    /* IP,子网掩码,网关 */
	/* 输出:20字节,分别为4字节IP,4字节网关,4字节掩码,4字节的DNS1,4字节的DNS2 */
#define CMD00_PPPOE_SET_USER_NAME            0X44                    /* 设置PPPOE用户名 */
	/* 输入:N个字节,0为结束符 */
#define CMD00_PPPOE_SET_PASSWORD             0X45                    /* 设置密码 */
	/* 输入:N个字节,0为结束符 */
#define CMD10_PPPOE_ENABLE                   0X46                    /* PPPOE使能 */
	/* 输入:1字节,1启动PPPOE,0关闭PPPOE */
#define CMD01_GET_PPPOE_STATUS                0X47                    /* 获取pppoe状态 */
	/* 输出:1字节状态码,0表示成功,其他值失败 */

/* 协议类型 */
#define PROTO_TYPE_IP_RAW                    0                       /* IP层原始数据 */
#define PROTO_TYPE_MAC_RAW                   1                       /* MAC层原始数据 */
#define PROTO_TYPE_UDP                       2                       /* UDP协议类型 */
#define PROTO_TYPE_TCP                       3                       /* TCP协议类型 */

/* PHY 命令参数/状态 */
#define PHY_DISCONN                          (1<<0)                  /* PHY断开 */
#define PHY_10M_FLL                          (1<<1)                  /* 10M全双工 */
#define PHY_10M_HALF                         (1<<2)                  /* 10M半双工 */
#define PHY_100M_FLL                         (1<<3)                  /* 100M全双工 */
#define PHY_100M_HALF                        (1<<4)                  /* 100M半双工 */
#define PHY_AUTO                             (1<<5)                  /* PHY自动模式,CMD10H_SET_PHY */

/*CH395 MAC过滤*/
#define MAC_FILT_RECV_BORADPKT               (1<<0)                  /* 使能接收广播包 */
#define MAC_FILT_RECV_ALL                    (1<<1)                  /* 使能接收所有数据包 */
#define MAC_FILT_RECV_MULTIPKT               (1<<2)                  /* 使能接收多播包 */
#define MAC_FILT_RECV_ENABLE                 (1<<3)                  /* 使能接收 */
#define MAC_FILT_SEND_ENABLE                 (1<<4)                  /* 使能发送 */

/* 中断状态 */
/* 以下为GLOB_INT会产生的状态 */
#define GINT_STAT_UNREACH                    (1<<0)                  /* 不可达中断*/
#define GINT_STAT_IP_CONFLI                  (1<<1)                  /* IP冲突*/
#define GINT_STAT_PHY_CHANGE                 (1<<2)                  /* PHY状态改变 */
#define GINT_STAT_DHCP                       (1<<3)                  /* PHY状态改变 */
#define GINT_STAT_SOCK0                      (1<<4)                  /* socket0 产生中断 */
#define GINT_STAT_SOCK1                      (1<<5)                  /* socket1 产生中断 */
#define GINT_STAT_SOCK2                      (1<<6)                  /* socket2 产生中断 */
#define GINT_STAT_SOCK3                      (1<<7)                  /* socket3 产生中断 */

/*以下为Sn_INT会产生的状态*/
#define SINT_STAT_SENBUF_FREE                (1<<0)                  /* 发送缓冲区空闲 */
#define SINT_STAT_SEND_OK                    (1<<1)                  /* 发送成功 */
#define SINT_STAT_RECV                       (1<<2)                  /* socket端口接收到数据或者接收缓冲区不为空 */
#define SINT_STAT_CONNECT                    (1<<3)                  /* 连接成功,TCP模式下产生此中断 */
#define SINT_STAT_DISCONNECT                 (1<<4)                  /* 连接断开,TCP模式下产生此中断 */
#define SINT_STAT_TIM_OUT                    (1<<6)                  /* ARP和TCP模式下会发生此中断 */

/* 获取命令状态 */
#define CMD_ERR_SUCCESS                      0x00                    /* 命令操作成功 */
#define CMD_RET_ABORT                        0x5F                    /* 命令操作失败 */
#define CH395_ERR_BUSY                       0x10                    /* 忙状态,表示当前正在执行命令 */
#define CH395_ERR_MEM                        0x11                    /* 内存错误 */
#define CH395_ERR_BUF                        0x12                    /* 缓冲区错误 */
#define CH395_ERR_TIMEOUT                    0x13                    /* 超时 */
#define CH395_ERR_RTE                        0x14                    /* 路由错误*/
#define CH395_ERR_ABRT                       0x15                    /* 连接停止*/
#define CH395_ERR_RST                        0x16                    /* 连接复位 */
#define CH395_ERR_CLSD                       0x17                    /* 连接关闭/socket 在关闭状态*/
#define CH395_ERR_CONN                       0x18                    /* 无连接 */
#define CH395_ERR_VAL                        0x19                    /* 错误的值 */
#define CH395_ERR_ARG                        0x1a                    /* 错误的参数 */
#define CH395_ERR_USE                        0x1b                    /* 已经被使用 */
#define CH395_ERR_IF                         0x1c                    /* MAC错误  */
#define CH395_ERR_ISCONN                     0x1d                    /* 已连接 */
#define CH395_ERR_UNKNOW                     0xFA                    /* 未知错误 */

/* PPP状态 */
#define CH395_PPP_SUCCESS                   0                         /* 成功 */
#define CH395_PPPERR_PARM                   1                         /* 无效参数 */
#define CH395_PPPERR_OPEN                   2		                  /* 无法打开PPP会话 */
#define CH395_PPPERR_DEVICE                 3		                  /* 无效的PPP设备 */
#define CH395_PPPERR_ALLOC                  4		                  /* 资源分配失败 */
#define CH395_PPPERR_USER                   5		                  /* 用户中断 */
#define CH395_PPPERR_CONNECT                6		                  /* 连接断开 */
#define CH395_PPPERR_AUTHFAIL               7		                  /* 挑战鉴别失败 */
#define CH395_PPPERR_PROTOCOL               8		                  /* 握手协议失败 */
#define CH395_PPPERR_TIME_OUT               9		                  /* 超时失败 */
#define CH395_PPPERR_CLOSE                  10		                  /* 关闭失败 */

/* 不可达代码 */
#define UNREACH_CODE_HOST                    0                        /* 主机不可达 */
#define UNREACH_CODE_NET                     1                        /* 网络不可达 */
#define UNREACH_CODE_PROTOCOL                2                        /* 协议不可达 */
#define UNREACH_CODE_PROT                    3                        /* 端口不可达 */
/*其他值请参考RFC792文档*/

/* 命令包头 */
#define SER_SYNC_CODE1                       0X57                     /* 串口命令同步码1 */
#define SER_SYNC_CODE2                       0XAB                     /* 串口命令同步码2 */

/* TCP状态 */
#define TCP_CLOSED                           0
#define TCP_LISTEN                           1
#define TCP_SYN_SENT                         2
#define TCP_SYN_RCVD                         3
#define TCP_ESTABLISHED                      4
#define TCP_FIN_WAIT_1                       5
#define TCP_FIN_WAIT_2                       6
#define TCP_CLOSE_WAIT                       7
#define TCP_CLOSING                          8
#define TCP_LAST_ACK                         9
#define TCP_TIME_WAIT                        10

/*CH395UART.C函数申明*/
extern void Handle_Uart_ISR(void* nirq_isr_context);
extern void Uart_init(void);
extern void Uart_bps_change(alt_u16 newbps);
extern void Uart_tx(alt_u8 txdb);
extern void xWriteCH395Cmd(alt_u8 cmd);
extern void  xWriteCH395Data(alt_u8 mdata);
extern alt_u8 xReadCH395Data(void);

extern alt_u8 uart_rx_temp;	//串口接收数据缓存
extern alt_u8 rx_flag;	//串口数据接收标志位

/* CH395芯片命令接口常用子函数申明 */
extern void CH395CMDReset(void);                                            /* 复位 */
extern void CH395CMDSleep(void);                                            /* 睡眠 */
extern alt_u8 CH395CMDGetVer(void);                                          /* 获取芯片及固件版本号 */
extern alt_u8 CH395CMDCheckExist(alt_u8 testdata);                            /* 测试命令 */
extern void CH395CMDSetPHY(alt_u8 phystat);                                  /* 设置PHY状态  */
extern alt_u8 CH395CMDGetPHYStatus(void);                                    /* 获取PHY状态 */
extern alt_u8 CH395CMDGetGlobIntStatus(void);                                /* 获取CH395全局中断状态 */
extern alt_u8 CH395CMDInitCH395(void);                                       /* 初始化CH395 */
extern void CH395CMDSetUartBaudRate(alt_u32 baudrate);                       /* 设置波特率 */
extern alt_u8 CH395GetCmdStatus(void);                                       /* 获取命令执行状态 */
extern void CH395CMDSetIPAddr(alt_u8 *ipaddr);                               /* 设置CH395的IP地址 */
extern void CH395CMDSetGWIPAddr(alt_u8 *gwipaddr);                           /* 设置CH395的网关IP地址 */
extern void CH395CMDSetMASKAddr(alt_u8 *maskaddr);                           /* 设置子网掩码 */
extern void CH395CMDSetMACAddr(alt_u8 *amcaddr);                             /* 设置CH395的MAC地址 */
extern void CH395CMDGetMACAddr(alt_u8 *amcaddr);                             /* 获取MAC地址 */
extern void CH395CMDSetMACFilt(alt_u8 filtype,alt_u32 table0,alt_u32 table1);  /* 设置CH395的MAC过滤 */
extern void CH395CMDGetUnreachIPPT(alt_u8 *list);                            /* 获取不可达地址以及端口 */
extern void CH395CMDGetRemoteIPP(alt_u8 sockindex,alt_u8 *list);              /* 获取远端IP和端口,一般在TCP Server下使用 */
extern void CH395SetSocketDesIP(alt_u8 sockindex,alt_u8 *ipaddr);             /* 设置scoket n的目的IP地址 */
extern void CH395SetSocketProtType(alt_u8 sockindex,alt_u8 prottype);         /* 设置socket n的协议类型 */
extern void CH395SetSocketDesPort(alt_u8 sockindex,alt_u16 desprot);          /* 设置socket n的目的端口 */
extern void CH395SetSocketSourPort(alt_u8 sockindex,alt_u16 surprot);         /* 设置socket n的源端口 */
extern void CH395SetSocketIPRAWProto(alt_u8 sockindex,alt_u8 prototype);      /* 在IPRAW模式下,设置socket n的IP包协议字段 */
extern void CH395SetRecvThresLen(alt_u8 sockindex,alt_u16 len);               /* 设置socket n的接收中断阀值 */
extern void CH395SendData(alt_u8 sockindex,alt_u8 *databuf,alt_u16 len);       /* 向socket n的发送缓冲区写数据 */
extern alt_u16 CH395GetRecvLength(alt_u8 sockindex);                          /* 获取socket n的接收长度 */
extern void CH395ClearRecvBuf(alt_u8 sockindex);                             /* 清除socket n的接收缓冲区 */
extern void CH395GetRecvData(alt_u8 sockindex,alt_u16 len,alt_u8 *pbuf);       /* 获取接收数据 */
extern void CH395CMDSetRetryCount(alt_u8 count);                             /* 设置最大重试次数 */
extern void CH395CMDSetRetryPeriod(alt_u16 period);                          /* 设置最大重试周期 单位 毫秒*/
extern void CH395CMDGetSocketStatus(alt_u8 sockindex,alt_u8 *status) ;        /* 获取socket n的状态 */
extern alt_u8 CH395OpenSocket(alt_u8 sockindex);                             /* 打开socket n*/
extern alt_u8 CH395CloseSocket(alt_u8 sockindex);                             /* 关闭socket n*/
extern alt_u8 CH395TCPConnect(alt_u8 sockindex);                               /* TCP连接 */
extern alt_u8 CH395TCPListen(alt_u8 sockindex);                                /* TCP监听 */
extern alt_u8 CH395TCPDisconnect(alt_u8 sockindex);                            /* TCP断开连接 */
extern alt_u8 CH395GetSocketInt(alt_u8 sockindex);                            /* 获取socket n的中断状态 */
extern alt_u8 CH395CRCRet6Bit(alt_u8 *mac_addr);                              /* 多播地址CRC32,用于HASH过滤 */
extern void CH395GetIPInf(alt_u8 *addr);
extern alt_u8 CH395DHCPEnable(alt_u8 flag);

/* 以下为CH395不常用命令函数 */
extern void CH395WriteRegister(alt_u32 addr,alt_u32 mdata);                   /* 写CH395内部寄存器 */
extern void CH395WriteProtRegister(alt_u32 addr,alt_u32 mdata);               /* 写CH395内部保护寄存器 */
extern alt_u32 CH395ReadRegister(alt_u32 addr);                               /* 读CH395内部寄存器 */
extern alt_u8 CH395ReadVar8(alt_u8 index ,alt_u8 addr);                        /* 读8位内部变量 */
extern void CH395WriteVar8(alt_u8 index ,alt_u8 addr,alt_u8 mdata);            /* 写8位内部变量 */
extern alt_u32 CH395ReadVar32(alt_u8 index ,alt_u8 addr);                      /* 读内部32位变量 */
extern void CH395WriteVar32(alt_u8 index ,alt_u8 addr,alt_u32 mdata);          /* 写内部32位变量 */
extern void CH395WriteRAM(alt_u8 *buf);                                      /* 测试使用,写内部4K SRAM */
extern void CH395ReadRAM(alt_u8 *buf);                                       /* 测试使用,读内部4K SRAM */


-------------------------------------------------------------------------------------------------


/********************************** (C) COPYRIGHT *******************************

* File Name          : CH395CMD.C

* Author             : tech9

* Version            : V1.0

* Date               : 2012/12/01

* Description        : CH395芯片命令接口文件

*

*******************************************************************************/


#include "alt_types.h"

#include "io.h"

#include "altera_avalon_pio_regs.h"

#include "sys/alt_irq.h"

#include "system.h"

#include <stdio.h>

#include <unistd.h>

#include <sys/alt_timestamp.h>

#include "ch395inc.h"


/********************************************************************************

* Function Name  : CH395CMDReset

* Description    : 复位CH395芯片

* Input          : None

* Output         : None

* Return         : None

*******************************************************************************/

void CH395CMDReset(void)

{

    xWriteCH395Cmd(CMD00_RESET_ALL);

}


/*******************************************************************************

* Function Name  : CH395CMDSleep

* Description    : 使CH395进入睡眠状态

* Input          : None

* Output         : None

* Return         : None

*******************************************************************************/

void CH395CMDSleep(void)

{

    xWriteCH395Cmd(CMD00_ENTER_SLEEP);

}


/********************************************************************************

* Function Name  : CH395CMDSleep

* Description    : 获取芯片以及固件版本号,1字节,高四位表示芯片版本,

                   低四位表示固件版本

* Input          : None

* Output         : None

* Return         : 1字节芯片及固件版本号

*******************************************************************************/

alt_u8 CH395CMDGetVer(void)

{

    alt_u8 i;


    xWriteCH395Cmd(CMD01_GET_IC_VER);

    i = xReadCH395Data();

    return i;

}


/********************************************************************************

* Function Name  : CH395CMDCheckExist

* Description    : 测试命令,用于测试硬件以及接口通讯

* Input          : testdata 1字节测试数据

* Output         : None

* Return         : 硬件OK,返回 testdata按位取反

*******************************************************************************/

alt_u8 CH395CMDCheckExist(alt_u8 testdata)

{

    alt_u8 i;


    xWriteCH395Cmd(CMD11_CHECK_EXIST);

    xWriteCH395Data(testdata);

    i = xReadCH395Data();

    return i;

}


/********************************************************************************

* Function Name  : CH395CMDSetPHY

* Description    : 设置PHY,主要设置CH395 PHY为100/10M 或者全双工半双工,CH395默

                    为自动协商。

* Input          : phystat 参考PHY 命令参数/状态

* Output         : None

* Return         : None

*******************************************************************************/

void CH395CMDSetPHY(alt_u8 phystat)

{

    xWriteCH395Cmd(CMD10_SET_PHY);

    xWriteCH395Data(phystat);

}


/*******************************************************************************

* Function Name  : CH395CMDGetPHYStatus

* Description    : 获取PHY的状态

* Input          : None

* Output         : None

* Return         : 当前CH395PHY状态,参考PHY参数/状态定义

*******************************************************************************/

alt_u8 CH395CMDGetPHYStatus(void)

{

    alt_u8 i;


    xWriteCH395Cmd(CMD01_GET_PHY_STATUS);

    i = xReadCH395Data();

    return i;

}


/*******************************************************************************

* Function Name  : CH395CMDGetGlobIntStatus

* Description    : 获取全局中断状态,收到此命令CH395自动取消中断

* Input          : None

* Output         : None

* Return         : 返回当前的全局中断状态

*******************************************************************************/

alt_u8 CH395CMDGetGlobIntStatus(void)

{

    alt_u8 init_status;


    xWriteCH395Cmd(CMD01_GET_GLOB_INT_STATUS);

    init_status = xReadCH395Data();

    return  init_status;

}


/********************************************************************************

* Function Name  : CH395CMDInitCH395

* Description    : 初始化CH395芯片。

* Input          : None

* Output         : None

* Return         : 返回执行结果

*******************************************************************************/

alt_u8 CH395CMDInitCH395(void)

{

    alt_u8 i = 0;

    alt_u8 s = 0;


    xWriteCH395Cmd(CMD0W_INIT_CH395);

    while(1)

    {

        usleep(5000);      //delay 5ms                                           /* 延时查询,建议2MS以上*/

        s = CH395GetCmdStatus();                                     /* 不能过于频繁查询*/

        if(s !=CH395_ERR_BUSY)break;                                 /* 如果CH395芯片返回忙状态*/

        if(i++ > 200)return CH395_ERR_UNKNOW;                        /* 超时退出,本函数需要500MS以上执行完毕 */

    }

    return s;

}


/********************************************************************************

* Function Name  : CH395CMDSetUartBaudRate

* Description    : 设置CH395串口波特率,仅在串口模式下有效

* Input          : baudrate 串口波特率

* Output         : None

* Return         : None

*******************************************************************************/

void CH395CMDSetUartBaudRate(alt_u32 baudrate)

{

    xWriteCH395Cmd(CMD31_SET_BAUDRATE);

    xWriteCH395Data((alt_u8)baudrate);

    xWriteCH395Data((alt_u8)((alt_u16)baudrate >> 8));

    xWriteCH395Data((alt_u8)(baudrate >> 16));

}


/*******************************************************************************

* Function Name  : CH395GetCmdStatus

* Description    : 获取命令执行状态,某些命令需要等待命令执行结果

* Input          : None

* Output         : None

* Return         : 返回上一条命令执行状态

*******************************************************************************/

alt_u8 CH395GetCmdStatus(void)

{

    alt_u8 i;


    xWriteCH395Cmd(CMD01_GET_CMD_STATUS);

    i = xReadCH395Data();

    return i;

}


/********************************************************************************

* Function Name  : CH395CMDSetIPAddr

* Description    : 设置CH395的IP地址

* Input          : ipaddr 指IP地址

* Output         : None

* Return         : None

*******************************************************************************/

void CH395CMDSetIPAddr(alt_u8 *ipaddr)

{

    alt_u8 i;


    xWriteCH395Cmd(CMD40_SET_IP_ADDR);

    for(i = 0; i < 4;i++)xWriteCH395Data(*ipaddr++);

}


/********************************************************************************

* Function Name  : CH395CMDSetGWIPAddr

* Description    : 设置CH395的网关IP地址

* Input          : ipaddr 指向网关IP地址

* Output         : None

* Return         : None

*******************************************************************************/

void CH395CMDSetGWIPAddr(alt_u8 *gwipaddr)

{

    alt_u8 i;


    xWriteCH395Cmd(CMD40_SET_GWIP_ADDR);

    for(i = 0; i < 4;i++)xWriteCH395Data(*gwipaddr++);

}


/********************************************************************************

* Function Name  : CH395CMDSetMASKAddr

* Description    : 设置CH395的子网掩码,默认为255.255.255.0

* Input          : maskaddr 指子网掩码地址

* Output         : None

* Return         : None

*******************************************************************************/

void CH395CMDSetMASKAddr(alt_u8 *maskaddr)

{

    alt_u8 i;


    xWriteCH395Cmd(CMD40_SET_MASK_ADDR);

    for(i = 0; i < 4;i++)xWriteCH395Data(*maskaddr++);

}


/********************************************************************************

* Function Name  : CH395CMDSetMACAddr

* Description    : 设置CH395的MAC地址。

* Input          : amcaddr MAC地址指针

* Output         : None

* Return         : None

*******************************************************************************/

void CH395CMDSetMACAddr(alt_u8 *amcaddr)

{

    alt_u8 i;


    xWriteCH395Cmd(CMD60_SET_MAC_ADDR);

    for(i = 0; i < 6;i++)xWriteCH395Data(*amcaddr++);

    usleep(100000); //delay 100ms

}


/********************************************************************************

* Function Name  : CH395CMDGetMACAddr

* Description    : 获取CH395的MAC地址。

* Input          : amcaddr MAC地址指针

* Output         : None

* Return         : None

*******************************************************************************/

void CH395CMDGetMACAddr(alt_u8 *amcaddr)

{

    alt_u8 i;


    xWriteCH395Cmd(CMD06_GET_MAC_ADDR);

    for(i = 0; i < 6;i++)*amcaddr++ = xReadCH395Data();

 }


/*******************************************************************************

* Function Name  : CH395CMDSetMACFilt

* Description    : 设置MAC过滤。

* Input          : filtype 参考 MAC过滤

                   table0 Hash0

                   table1 Hash1

* Output         : None

* Return         : None

*******************************************************************************/

void CH395CMDSetMACFilt(alt_u8 filtype,alt_u32 table0,alt_u32 table1)

{

    xWriteCH395Cmd(CMD90_SET_MAC_FILT);

    xWriteCH395Data(filtype);

    xWriteCH395Data((alt_u8)table0);

    xWriteCH395Data((alt_u8)((alt_u16)table0 >> 8));

    xWriteCH395Data((alt_u8)(table0 >> 16));

    xWriteCH395Data((alt_u8)(table0 >> 24));


    xWriteCH395Data((alt_u8)table1);

    xWriteCH395Data((alt_u8)((alt_u16)table1 >> 8));

    xWriteCH395Data((alt_u8)(table1 >> 16));

    xWriteCH395Data((alt_u8)(table1 >> 24));

}


/********************************************************************************

* Function Name  : CH395CMDGetUnreachIPPT

* Description    : 获取不可达信息 (IP,Port,Protocol Type)

* Input          : list 保存获取到的不可达

                        第1个字节为不可达代码,请参考 不可达代码(CH395INC.H)

                        第2个字节为IP包协议类型

                        第3-4字节为端口号

                        第4-8字节为IP地址

* Output         : None

* Return         : None

*******************************************************************************/

void CH395CMDGetUnreachIPPT(alt_u8 *list)

{

    alt_u8 i;


    xWriteCH395Cmd(CMD08_GET_UNREACH_IPPORT);

    for(i = 0; i < 8; i++)

    {

        *list++ = xReadCH395Data();

    }

}


/********************************************************************************

* Function Name  : CH395CMDGetRemoteIPP

* Description    : 获取远端的IP和端口地址,一般在TCP Server模式下使用

* Input          : sockindex Socket索引

                   list 保存IP和端口

* Output         : None

* Return         : None

*******************************************************************************/

void CH395CMDGetRemoteIPP(alt_u8 sockindex,alt_u8 *list)

{

    alt_u8 i;


    xWriteCH395Cmd(CMD06_GET_REMOT_IPP_SN);

    xWriteCH395Data(sockindex);

    for(i = 0; i < 6; i++)

    {

        *list++ = xReadCH395Data();

    }

}


/*******************************************************************************

* Function Name  : CH395SetSocketDesIP

* Description    : 设置socket n的目的IP地址

* Input          : sockindex Socket索引

                   ipaddr 指向IP地址

* Output         : None

* Return         : None

*******************************************************************************/

void CH395SetSocketDesIP(alt_u8 sockindex,alt_u8 *ipaddr)

{

    xWriteCH395Cmd(CMD50_SET_IP_ADDR_SN);

    xWriteCH395Data(sockindex);

    xWriteCH395Data(*ipaddr++);

    xWriteCH395Data(*ipaddr++);

    xWriteCH395Data(*ipaddr++);

    xWriteCH395Data(*ipaddr++);

}


/*******************************************************************************

* Function Name  : CH395SetSocketProtType

* Description    : 设置socket 的协议类型

* Input          : sockindex Socket索引

                   prottype 协议类型,请参考 socket协议类型定义(CH395INC.H)

* Output         : None

* Return         : None

*******************************************************************************/

void CH395SetSocketProtType(alt_u8 sockindex,alt_u8 prottype)

{

    xWriteCH395Cmd(CMD20_SET_PROTO_TYPE_SN);

    xWriteCH395Data(sockindex);

    xWriteCH395Data(prottype);

}


/*******************************************************************************


* Function Name  : CH395SetSocketDesPort

* Description    : 设置socket n的协议类型

* Input          : sockindex Socket索引

                   desprot 2字节目的端口

* Output         : None

* Return         : None

*******************************************************************************/

void CH395SetSocketDesPort(alt_u8 sockindex,alt_u16 desprot)

{

    xWriteCH395Cmd(CMD30_SET_DES_PORT_SN);

    xWriteCH395Data(sockindex);

    xWriteCH395Data((alt_u8)desprot);

    xWriteCH395Data((alt_u8)(desprot >> 8));

}


/*******************************************************************************

* Function Name  : CH395SetSocketSourPort

* Description    : 设置socket n的协议类型

* Input          : sockindex Socket索引

                   desprot 2字节源端口

* Output         : None

* Return         : None

*******************************************************************************/

void CH395SetSocketSourPort(alt_u8 sockindex,alt_u16 surprot)

{

    xWriteCH395Cmd(CMD30_SET_SOUR_PORT_SN);

    xWriteCH395Data(sockindex);

    xWriteCH395Data((alt_u8)surprot);

    xWriteCH395Data((alt_u8)(surprot>>8));

}


/******************************************************************************

* Function Name  : CH395SetSocketIPRAWProto

* Description    : IP模式下,socket IP包协议字段

* Input          : sockindex Socket索引

                   prototype IPRAW模式1字节协议字段

* Output         : None

* Return         : None

*******************************************************************************/

void CH395SetSocketIPRAWProto(alt_u8 sockindex,alt_u8 prototype)

{

    xWriteCH395Cmd(CMD20_SET_IPRAW_PRO_SN);

    xWriteCH395Data(sockindex);

    xWriteCH395Data(prototype);

}


/********************************************************************************

* Function Name  : CH395EnablePing

* Description    : 开启/关闭 PING

* Input          : enable : 1  开启PING

                          :0  关闭PING

* Output         : None

* Return         : None

*******************************************************************************/

void CH395EnablePing(alt_u8 enable)

{

    xWriteCH395Cmd(CMD01_PING_ENABLE);

    xWriteCH395Data(enable);

}


/********************************************************************************

* Function Name  : CH395SendData

* Description    : 向发送缓冲区写数据

* Input          : sockindex Socket索引

                   databuf  数据缓冲区

                   len   长度

* Output         : None

* Return         : None

*******************************************************************************/

void CH395SendData(alt_u8 sockindex,alt_u8 *databuf,alt_u16 len)

{

    alt_u16 i;


    xWriteCH395Cmd(CMD30_WRITE_SEND_BUF_SN);

    xWriteCH395Data((alt_u8)sockindex);

    xWriteCH395Data((alt_u8)len);

    xWriteCH395Data((alt_u8)(len>>8));


    for(i = 0; i < len; i++)

    {

        xWriteCH395Data(*databuf++);

    }

}


/*******************************************************************************

* Function Name  : CH395GetRecvLength

* Description    : 获取接收缓冲区长度

* Input          : sockindex Socket索引

* Output         : None

* Return         : 返回接收缓冲区有效长度

*******************************************************************************/

alt_u16 CH395GetRecvLength(alt_u8 sockindex)

{

    alt_u16 i;


    xWriteCH395Cmd(CMD12_GET_RECV_LEN_SN);

    xWriteCH395Data((alt_u8)sockindex);

    i = xReadCH395Data();

    i = (alt_u16)(xReadCH395Data()<<8) + i;

    return i;

}


/*******************************************************************************

* Function Name  : CH395ClearRecvBuf

* Description    : 清除接收缓冲区

* Input          : sockindex Socket索引

* Output         : None

* Return         : None

*******************************************************************************/

void CH395ClearRecvBuf(alt_u8 sockindex)

{

    xWriteCH395Cmd(CMD10_CLEAR_RECV_BUF_SN);

    xWriteCH395Data((alt_u8)sockindex);

}


/********************************************************************************

* Function Name  : CH395GetRecvLength

* Description    : 读取接收缓冲区数据

* Input          : sockindex Socket索引

                   len   长度

                   pbuf  缓冲区

* Output         : None

* Return         : None

*******************************************************************************/

void CH395GetRecvData(alt_u8 sockindex,alt_u16 len,alt_u8 *pbuf)

{

    alt_u16 i;

    if(!len)return;

    xWriteCH395Cmd(CMD30_READ_RECV_BUF_SN);

    xWriteCH395Data(sockindex);

    xWriteCH395Data((alt_u8)len);

    xWriteCH395Data((alt_u8)(len>>8));

usleep(1); //delay 1us

    for(i = 0; i < len; i++)

    {

       *pbuf = xReadCH395Data();

       pbuf++;

    }

}


/********************************************************************************

* Function Name  : CH395CMDSetRetryCount

* Description    : 设置重试次数

* Input          : count 重试值,最大为20次

* Output         : None

* Return         : None

********************************************************************************/

void CH395CMDSetRetryCount(alt_u8 count)

{

    xWriteCH395Cmd(CMD10_SET_RETRAN_COUNT);

    xWriteCH395Data(count);

}


/********************************************************************************

* Function Name  : CH395CMDSetRetryPeriod

* Description    : 设置重试周期

* Input          : period 重试周期单位为毫秒,最大1000ms

* Output         : None

* Return         : None

*******************************************************************************/

void CH395CMDSetRetryPeriod(alt_u16 period)

{

    xWriteCH395Cmd(CMD10_SET_RETRAN_COUNT);

    xWriteCH395Data((alt_u8)period);

    xWriteCH395Data((alt_u8)(period>>8));

}


/********************************************************************************

* Function Name  : CH395CMDGetSocketStatus

* Description    : 获取socket

* Input          : None

* Output         : socket n的状态信息,第1字节为socket 打开或者关闭

                   第2字节为TCP状态

* Return         : None

*******************************************************************************/

void CH395CMDGetSocketStatus(alt_u8 sockindex,alt_u8 *status)

{

    xWriteCH395Cmd(CMD12_GET_SOCKET_STATUS_SN);

    xWriteCH395Data(sockindex);

    *status++ = xReadCH395Data();

    *status++ = xReadCH395Data();

}


/*******************************************************************************

* Function Name  : CH395OpenSocket

* Description    : 打开socket,此命令需要等待执行成功

* Input          : sockindex Socket索引

* Output         : None

* Return         : 返回执行结果

*******************************************************************************/

alt_u8  CH395OpenSocket(alt_u8 sockindex)

{

    alt_u8 i = 0;

    alt_u8 s = 0;


    xWriteCH395Cmd(CMD1W_OPEN_SOCKET_SN);

    xWriteCH395Data(sockindex);

    while(1)

    {

        usleep(5000); //delay 5ms                                                 /* 延时查询,建议2MS以上*/

        s = CH395GetCmdStatus();                                     /* 不能过于频繁查询*/

        if(s !=CH395_ERR_BUSY)break;                                 /* 如果CH395芯片返回忙状态*/

        if(i++ > 200)return CH395_ERR_UNKNOW;                        /* 超时退出*/

    }

    return s;

}


/********************************************************************************

* Function Name  : CH395OpenSocket

* Description    : 关闭socket,

* Input          : sockindex Socket索引

* Output         : None

* Return         : 返回执行结果

*******************************************************************************/

alt_u8  CH395CloseSocket(alt_u8 sockindex)

{

    alt_u8 i = 0;

    alt_u8 s = 0;


    xWriteCH395Cmd(CMD1W_CLOSE_SOCKET_SN);

    xWriteCH395Data(sockindex);

    while(1)

    {

    usleep(5000); //delay 5ms                                  /* 延时查询,建议2MS以上*/

        s = CH395GetCmdStatus();                                     /* 不能过于频繁查询*/

        if(s !=CH395_ERR_BUSY)break;                                 /* 如果CH395芯片返回忙状态*/

        if(i++ > 200)return CH395_ERR_UNKNOW;                        /* 超时退出*/

    }

    return s;

}


/********************************************************************************

* Function Name  : CH395TCPConnect

* Description    : TCP连接,仅在TCP模式下有效,此命令需要等待执行成功

* Input          : sockindex Socket索引

* Output         : None

* Return         : 返回执行结果

*******************************************************************************/

alt_u8 CH395TCPConnect(alt_u8 sockindex)

{

    alt_u8 i = 0;

    alt_u8 s = 0;


    xWriteCH395Cmd(CMD1W_TCP_CONNECT_SN);

    xWriteCH395Data(sockindex);

    while(1)

    {

        usleep(5000); //delay 5ms                                                 /* 延时查询,建议2MS以上*/

        s = CH395GetCmdStatus();                                     /* 不能过于频繁查询*/

        if(s !=CH395_ERR_BUSY)break;                                 /* 如果CH395芯片返回忙状态*/

        if(i++ > 200)return CH395_ERR_UNKNOW;                        /* 超时退出*/

    }

    return s;

}


/******************************************************************************

* Function Name  : CH395TCPListen

* Description    : TCP监听,仅在TCP模式下有效,此命令需要等待执行成功

* Input          : sockindex Socket索引

* Output         : None

* Return         : 返回执行结果

*******************************************************************************/

alt_u8 CH395TCPListen(alt_u8 sockindex)

{

    alt_u8 i = 0;

    alt_u8 s = 0;


    xWriteCH395Cmd(CMD1W_TCP_LISTEN_SN);

    xWriteCH395Data(sockindex);

    while(1)

    {

    usleep(5000); //delay 5ms                                  /* 延时查询,建议2MS以上*/

        s = CH395GetCmdStatus();                                     /* 不能过于频繁查询*/

        if(s !=CH395_ERR_BUSY)break;                                 /* 如果CH395芯片返回忙状态*/

        if(i++ > 200)return CH395_ERR_UNKNOW;                        /* 超时退出*/

    }

    return s;


}


/********************************************************************************

* Function Name  : CH395TCPDisconnect

* Description    : TCP断开,仅在TCP模式下有效,此命令需要等待执行成功

* Input          : sockindex Socket索引

* Output         : None

* Return         : None

*******************************************************************************/

alt_u8 CH395TCPDisconnect(alt_u8 sockindex)

{

    alt_u8 i = 0;

    alt_u8 s = 0;


    xWriteCH395Cmd(CMD1W_TCP_DISNCONNECT_SN);

    xWriteCH395Data(sockindex);


    while(1)

    {

    usleep(5000); //delay 5ms                                                /* 延时查询,建议2MS以上*/

        s = CH395GetCmdStatus();                                     /* 不能过于频繁查询*/

        if(s !=CH395_ERR_BUSY)break;                                 /* 如果CH395芯片返回忙状态*/

        if(i++ > 200)return CH395_ERR_UNKNOW;                        /* 超时退出*/

    }

    return s;


}


/*******************************************************************************

* Function Name  : CH395GetSocketInt

* Description    : 获取socket n的中断状态

* Input          : sockindex   socket索引

* Output         : None

* Return         : 中断状态

*******************************************************************************/

alt_u8 CH395GetSocketInt(alt_u8 sockindex)

{

    alt_u8 intstatus;

    xWriteCH395Cmd(CMD11_GET_INT_STATUS_SN);

usleep(2); //delay 2us

    xWriteCH395Data(sockindex);

    intstatus = xReadCH395Data();

    return intstatus;

}


/*******************************************************************************

* Function Name  : CH395CRCRet6Bit

* Description    : 对多播地址进行CRC运算,并取高6位。

* Input          : mac_addr   MAC地址

* Output         : None

* Return         : 返回CRC32的高6位

*******************************************************************************/

alt_u8 CH395CRCRet6Bit(alt_u8 *mac_addr)

{

    alt_u32 perByte;

    alt_u32 perBit;

    const alt_u32 poly = 0x04C11DB7;

    alt_u32 crc_value = 0xFFFFFFFF;

    alt_u8 c;

    for ( perByte = 0; perByte < 6; perByte ++ )

    {

        c = *(mac_addr++);

        for ( perBit = 0; perBit < 8; perBit++ )

        {

            crc_value = (crc_value<<1)^((((crc_value>>31)^c)&0x01)?poly:0);

            c >>= 1;

        }

    }

    crc_value=crc_value>>26;

    return ((alt_u8)crc_value);

}


/******************************************************************************

* Function Name  : CH395DHCPEnable

* Description    : 启动/停止DHCP

* Input          : flag   1:启动DHCP;0:停止DHCP

* Output         : None

* Return         : 执行状态

*******************************************************************************/

alt_u8  CH395DHCPEnable(alt_u8 flag)

{

    alt_u8 i = 0;

alt_u8 s;


xWriteCH395Cmd(CMD10_DHCP_ENABLE);

    xWriteCH395Data(flag);


    while(1)

    {

    usleep(20000); //delay 20ms

        s = CH395GetCmdStatus();                                     /* 不能过于频繁查询*/

if(s !=CH395_ERR_BUSY)break;                                 /* 如果CH395芯片返回忙状态*/

        if(i++ > 200)return CH395_ERR_UNKNOW;                        /* 超时退出*/

    }

    return s;

}


/******************************************************************************

* Function Name  : CH395GetDHCPStatus

* Description    : 获取DHCP状态

* Input          : None

* Output         : None

* Return         : DHCP状态,0为成功,其他值表示错误

*******************************************************************************/

alt_u8 CH395GetDHCPStatus(void)

{

    alt_u8 status;


xWriteCH395Cmd(CMD01_GET_DHCP_STATUS);

status = xReadCH395Data();

return status;

}


/*******************************************************************************

* Function Name  : CH395GetIPInf

* Description    : 获取IP,子网掩码和网关地址

* Input          : None

* Output         : 12个字节的IP,子网掩码和网关地址

* Return         : None

*******************************************************************************/

void CH395GetIPInf(alt_u8 *addr)

{

alt_u8 i;


xWriteCH395Cmd(CMD014_GET_IP_INF);

for(i = 0; i < 20; i++)

{

  *addr++ = xReadCH395Data();

}

}


/******************************************************************************

* Function Name  : CH395PPPOEEnable

* Description    : 启动/停止PPPOE

* Input          : flag   1:启动PPPOE;0:停止PPPOE

* Output         : None

* Return         : 执行状态

*******************************************************************************/

alt_u8  CH395PPPOEEnable(alt_u8 flag)

{

    alt_u8 i = 0;

alt_u8 s;


xWriteCH395Cmd(CMD10_PPPOE_ENABLE);

    xWriteCH395Data(flag);


    while(1)

    {

    usleep(20000); //delay 20ms

        s = CH395GetCmdStatus();                                     /* 不能过于频繁查询*/

if(s !=CH395_ERR_BUSY)break;                                 /* 如果CH395芯片返回忙状态*/

        if(i++ > 200)return CH395_ERR_UNKNOW;                        /* 超时退出*/

    }

    return s;

}


/*******************************************************************************

* Function Name  : CH395PPPOESetUserName

* Description    : 设置PPPOE用户名

* Input          : uname 用户名指针

* Output         : None

* Return         : 执行状态

*******************************************************************************/

void CH395PPPOESetUserName(alt_u8 *uname)

{

    alt_u8 i = 0;


xWriteCH395Cmd(CMD00_PPPOE_SET_USER_NAME);

i = strlen((const char*)uname);

if(i > 31)i = 31;                                               /* 检查长度是否正确,不能大于31 */

xWriteCH395Data(i);

while(i--)

{

   xWriteCH395Data(*uname++);

}

}

/*******************************************************************************

* Function Name  : CH395PPPOESetPassWord

* Description    : 设置PPPOE密码

* Input          : psword 密码指针

* Output         : None

* Return         : 执行状态

*******************************************************************************/

void CH395PPPOESetPassWord(alt_u8 *psword)

{

    alt_u8 i = 0;


xWriteCH395Cmd(CMD00_PPPOE_SET_PASSWORD);

i = strlen((const char*)psword);

if(i > 31)i = 31;                                               /* 检查长度是否正确,不能大于31 */

xWriteCH395Data(i);

while(i--)

{

   xWriteCH395Data(*psword++);

}

}


/*******************************************************************************

* Function Name  : CH395GetPPPOEStatus

* Description    : 获取DHCP状态

* Input          : None

* Output         : None

* Return         : DHCP状态,0为成功,其他值表示错误

*******************************************************************************/

alt_u8 CH395GetPPPOEStatus(void)

{

    alt_u8 status;


xWriteCH395Cmd(CMD01_GET_PPPOE_STATUS);

status = xReadCH395Data();

return status;

}


/******************************************************************************

* Function Name  : CH395PPPOEStart

* Description    : 启动PPPOE

* Input          : uname 用户名指针

*                :psword 密码指针

* Output         : None

* Return         : 执行状态

*******************************************************************************/

alt_u8 CH395PPPOEStart(alt_u8 *uname,alt_u8 *psword)

{

    alt_u8 s;


if((uname == NULL)||(psword == NULL))return CH395_ERR_UNKNOW;    /* 检查参数是否合法 */


CH395PPPOESetUserName(uname);

    CH395PPPOESetPassWord(psword);

s = CH395PPPOEEnable(1);

return s;

}



楼主可见

  1. 小梅哥 1#

    建议debug,查看程序运行情况