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

📄 handler_http.c

📁 《嵌入式网络系统设计-基于Atmel ARM7 系列》这个本书的光盘资料
💻 C
📖 第 1 页 / 共 2 页
字号:
//*------------------------------------------------------------------------------------------------
//* 文件名				: handler_http.c
//* 功能描述			: http协议处理函数库
//* 作者    			: 焦海波
//* 版本				: 0.1
//* 建立日期、时间		: 2006/08/07 14:58
//* 最近修改日期、时间	: 
//* 修改原因			: 
//*------------------------------------------------------------------------------------------------
//*------------------------------------------ 头文件 -----------------------------------------------
#include	"/uCOS-II/ucos_ii.h"
#include	"/at91sam7x256/drivers/flash/flash.h"
#include	"/at91sam7x256/include/AT91SAM7X256.h"
#include	"/LwIP/include/lwip/tcpip.h"
#include	"/LwIP/include/lwip/api.h"
#include	"/LwIP/dns/dns_client.h"
#include	"/tools/stringExtAPI.h"
#include	"/tools/search.h"
#include	"/tools/converter.h"
//*------------------------------------ 变量、数据类型宏定义 ---------------------------------------
#define HTTP_HTML_HEADER		"HTTP/1.1 200 OK\r\nContent-type: text/html\r\n\r\n"
#define HTTP_POST_RESP_HEADER	"HTTP/1.1 100 Continue\r\n\r\n"

//* POST参数的最大长度
#define	POST_PARAM_MAX			128

//* POST处理函数类型定义
typedef void(*pfunvPHandler)(ST_NETCONN*, INT8S*, INT32S);

#define	POST_HANDLER_NAME_LEN	31

//* POST请求处理函数列表使用的结构类型定义
typedef struct {
	INT32S			s32NameLen;
	INT8S			szHandlerName[POST_HANDLER_NAME_LEN + 1];
	pfunvPHandler	pfunvPostHandler;
} ST_POST_HANDLER;

//*-------------------------------------- 函数原型声明 ---------------------------------------------
static void __vSetNetCFGParam(ST_NETCONN *pstConn, INT8S *pszParam, INT32S s32ParamLen);
static void __vDNToIP(ST_NETCONN *pstConn, INT8S *pszParam, INT32S s32ParamLen);

//*---------------------------------------- 常量定义 ----------------------------------------------
#define	STA_PHANDLER_NB		2		//* POST请求处理函数个数
static const ST_POST_HANDLER  __staPHandlers[STA_PHANDLER_NB] = {{15, "vSetNetCFGParam", __vSetNetCFGParam}, 
												{7, "vDNToIP", __vDNToIP}};
#if	__DEBUG__ == 0												
	INT32S s32NeedReset;
#endif
//*================================================================================================
//*											函	数	区
//*================================================================================================
//*------------------------------------------------------------------------------------------------
//* 函数名称 : __vHTTPRespInfo
//* 功能描述 : 向浏览器返回一个HTTP请求的响应信息
//* 入口参数 :     <pstConn>[in] 指向ST_NETCONN结构的指针,该结构保存当前的连接信息
//*          : <pszRespInfo>[in] 指向响应信息的指针
//*          :        <lLen>[IN] 响应信息长度
//* 出口参数 : 无
//*------------------------------------------------------------------------------------------------
static void __vHTTPRespInfo(ST_NETCONN *pstConn, INT8S *pszRespInfo, INT32S s32Len)
{
	netconn_write(pstConn, HTTP_HTML_HEADER, strlenExt(HTTP_HTML_HEADER), NETCONN_COPY);
	netconn_write(pstConn, pszRespInfo, s32Len, NETCONN_NOCOPY);
}
//*------------------------------------------------------------------------------------------------
//* 函数名称 : __vHTTPError
//* 功能描述 : 向浏览器返回一个HTTP请求错误
//* 入口参数 : <pstConn>[in] 指向ST_NETCONN结构的指针
//* 出口参数 : 无
//*------------------------------------------------------------------------------------------------
static void __vHTTPError(ST_NETCONN *pstConn)
{
	__vHTTPRespInfo(pstConn, 
					"<boady><br><br><h1>错误的资源请求!<a href='#'  onclick='history.back();'>返回</a></h1></body>", 
					strlenExt("<boady><br><br><h1>错误的资源请求!<a href='#'  onclick='history.back();'>返回</a></h1></body>"));
}
//*------------------------------------------------------------------------------------------------
//* 函数名称 : Handler_HTTPGet
//* 功能描述 : 处理HTTP协议的GET请求
//* 入口参数 : <pstConn>[in] 指向ST_NETCONN结构的指针
//* 出口参数 : 无
//*------------------------------------------------------------------------------------------------
static void __Handler_HTTPGet(ST_NETCONN *pstConn)
{
	INT8S			__szNetCFGParam[192];

	netconn_write(pstConn, HTTP_HTML_HEADER, strlenExt(HTTP_HTML_HEADER), NETCONN_COPY);
	netconn_write(pstConn, (INT8S*)(SET_HTML_STORE_ADDR + 4), *((INT32S*)SET_HTML_STORE_ADDR), NETCONN_COPY);
	memset(__szNetCFGParam, 0, sizeof(__szNetCFGParam));
	strcatExt(__szNetCFGParam, sizeof(__szNetCFGParam), "<p>IP:", 7);
	vReadASCIIIP(__szNetCFGParam + strlenExt(__szNetCFGParam));
	strcatExt(__szNetCFGParam, sizeof(__szNetCFGParam), "<br>子网掩码:", 14);
	vReadASCIINetMask(__szNetCFGParam + strlenExt(__szNetCFGParam));
	strcatExt(__szNetCFGParam, sizeof(__szNetCFGParam), "<br>网关:", 10);
	vReadASCIIGateway(__szNetCFGParam + strlenExt(__szNetCFGParam));
	netconn_write(pstConn, __szNetCFGParam, strlenExt(__szNetCFGParam), NETCONN_COPY);
	netconn_write(pstConn, (INT8S*)(SET1_HTML_STORE_ADDR + 4), *((INT32S*)SET1_HTML_STORE_ADDR), NETCONN_COPY);
}
//*------------------------------------------------------------------------------------------------
//* 函数名称 : __u32ParseIP
//* 功能描述 : 解析IP格式的数据
//* 入口参数 :  <pszVal>[in] 指向参数值的指针
//*          : <lValLen>[in] 参数长度
//* 出口参数 : 无
//*------------------------------------------------------------------------------------------------
static INT32U __u32ParseIP(INT8S *pszVal, INT32S s32ValLen)
{
	INT8S	*__pszNext = pszVal, *__pszStart;
	INT32U 	__u32IP = 0x00000000;
	
	__pszNext = memstrExt(__pszNext, ".", 1, 4);
	__u32IP = u8ConvertStringToOneByte_Hex(pszVal, __pszNext - pszVal);
	
	__pszStart = __pszNext + 1;
	__pszNext = memstrExt(__pszStart, ".", 1, 4);
	__u32IP |= (0x0000FF00 & (u8ConvertStringToOneByte_Hex(__pszStart, __pszNext - __pszStart) << 8));
	
	__pszStart = __pszNext + 1;
	__pszNext = memstrExt(__pszStart, ".", 1, 4);
	__u32IP |= (0x00FF0000 & (u8ConvertStringToOneByte_Hex(__pszStart, __pszNext - __pszStart) << 16));
	
	__pszStart = __pszNext + 1;
	__u32IP |= (0xFF000000 & (u8ConvertStringToOneByte_Hex(__pszStart, s32ValLen - (INT32S)(__pszStart - pszVal)) << 24));
	
	return __u32IP;
}
//*------------------------------------------------------------------------------------------------
//* 函数名称 : __vSetNetCFGParam
//* 功能描述 : 设置网络参数
//* 入口参数 :     <pstConn>[in] 指向ST_NETCONN结构的指针
//*          :    <pszParam>[in] 指向参数开始位置的指针
//*          : <s32ParamLen>[in] 参数长度
//* 出口参数 : 无
//*------------------------------------------------------------------------------------------------
static void __vSetNetCFGParam(ST_NETCONN *pstConn, INT8S *pszParam, INT32S s32ParamLen)
{	
	INT8S	*__pszNext, *__pszStart;
	INT32U	__u32IP, __u32NetMask, __u32Gateway;
	INT32S	__s32ValLen;

#if OS_CRITICAL_METHOD == 3                     
    OS_CPU_SR  		cpu_sr = 0;
#endif

	__pszStart = pszParam + 3;
	__pszNext = memstrExt(__pszStart, "&", 1, s32ParamLen);
	__s32ValLen = (INT32S)(__pszNext - __pszStart);
	__u32IP = __u32ParseIP(__pszStart, __s32ValLen);
	
	__pszStart = __pszNext + 4;
	__pszNext = memstrExt(__pszStart, "&", 1,s32ParamLen - (INT32S)(__pszStart - pszParam));
	__s32ValLen = (INT32S)(__pszNext - __pszStart);
	__u32NetMask = __u32ParseIP(__pszStart, __s32ValLen);
	
	__pszStart = __pszNext + 4;
	__s32ValLen = s32ParamLen - (INT32S)(__pszStart - pszParam);
	__u32Gateway = __u32ParseIP(__pszStart, __s32ValLen);
	
	blSetNetCFGParam(__u32IP, __u32NetMask, __u32Gateway);
	
	netconn_write(pstConn, HTTP_POST_RESP_HEADER, strlenExt(HTTP_POST_RESP_HEADER), NETCONN_COPY);
	
	__Handler_HTTPGet(pstConn);
	
#if	__DEBUG__ == 0
	OS_ENTER_CRITICAL()
	{
		s32NeedReset = OS_TRUE;
	}	
	OS_EXIT_CRITICAL()
#endif
}
//*------------------------------------------------------------------------------------------------
//* 函数名称 : __ils32PacketDNSQuestion
//* 功能描述 : 按照DNS格式封装查询参数
//* 入口参数 :        <pszParam>[in]  指向查询参数的指针
//*          :     <s32ParamLen>[in]  参数长度
//*          :     <pszQuestion>[in]  指向接收缓冲区(在这里保存封装好的包)的指针
//*          : <s32QuestionSize>[out] 接收封装包的缓冲区长度
//* 出口参数 : 返回封装后的包长度
//*------------------------------------------------------------------------------------------------
__inline INT32S __ils32PacketDNSQuestion(INT8S *pszParam, INT32S s32ParamLen, INT8S *pszQuestion, INT32S s32QuestionSize)
{
	INT32S	__s32ValLen, __s32TotLenToParsed = 0;
	INT8S	*__pszNext, *__pszStart;
	
	memset(pszQuestion, 0, s32QuestionSize);
	
	//* 按照DNS格式封装查询参数
	__pszStart = pszParam + 3;
	do{
		__pszNext = memstrExt(__pszStart, ".", 1, s32ParamLen - (INT32S)(__pszStart - pszParam));
		if(__pszNext != NULL)
			__s32ValLen = (INT32S)(__pszNext - __pszStart);
		else
			__s32ValLen = s32ParamLen - (INT32S)(__pszStart - pszParam);
				
		*(pszQuestion + __s32TotLenToParsed) = __s32ValLen;
		memcpy(pszQuestion + __s32TotLenToParsed + 1, __pszStart, __s32ValLen);
		
		__s32TotLenToParsed += (__s32ValLen + 1);
		
		__pszStart = __pszNext + 1;
	}while(__pszNext != NULL);	
	
	return __s32TotLenToParsed + 1;
}
//*------------------------------------------------------------------------------------------------
//* 函数名称 : __ilvSendIP
//* 功能描述 : 发送IP地址
//* 入口参数 : <pstConn>[in] 指向ST_NETCONN结构的指针
//*          :    <ulIP>[in] 查询得到的IP地址
//* 出口参数 : 无
//*------------------------------------------------------------------------------------------------
__inline void __ilvSendIP(ST_NETCONN *pstConn, INT32U ulIP)
{
	INT8U		*__pubIP;
	INT8S  		__szIP[16];
	INT8S		__szResp[200];
	
	memset(__szIP, 0, sizeof(__szIP));
	memset(__szResp, 0, sizeof(__szResp));
	
	__pubIP = &ulIP;
	
	sprintf(__szIP, "%d", *__pubIP);
	sprintf(__szIP + strlenExt(__szIP), ".%d", *(__pubIP + 1));
	sprintf(__szIP + strlenExt(__szIP), ".%d", *(__pubIP + 2));
	sprintf(__szIP + strlenExt(__szIP), ".%d", *(__pubIP + 3));
	
	strcatExt(__szResp, sizeof(__szResp) - 1,"<boady><br><br><h1>IP地址是:", strlenExt("<boady><br><br><h1>IP地址是:"));
	strcatExt(__szResp, sizeof(__szResp) - 1, __szIP, strlenExt(__szIP));
	strcatExt(__szResp, sizeof(__szResp) - 1, 
				",点此<a href='#'  onclick='history.back();'>返回</a></h1></body>", 

⌨️ 快捷键说明

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