dumpwebpage.c
来自「Keil下移植好的lwip基于c166」· C语言 代码 · 共 252 行
C
252 行
/***************************************************************************
** **
** Simple HTTP server which will dump a HTML page at each request **
** **
** It is based on lwIP (CVS version 06.03.2003) by Adam Dunkels of **
** Swedish Institute of Computer Science. See www.sics.se/~adam/lwip/ **
** **
** Ported 03/2003 by Christian Scheurer (www.ChristianScheurer.ch) **
** **
*************************************************************************** */
#include "webpage.h"
#include "lwip/tcp.h"
/* *** GLOBAL DATA AND DEFINITIONS ***************************************** */
struct dumpwebpage_state {
int bytes_left; // bytes left in send buffer
int page_offset; // offset within page
int page_size; // total page size
};
const unsigned char http_get_response[] = {
"HTTP/1.0 200 OK\r\nContent-Type: text/html\r\n\r\n"
};
/* *** END OF GLOBAL DATA AND DEFINITIONS ********************************** */
/*****************************************************************************
* dumpwebpage_init() *
* This function must be called on system startup to init "dumpwebpage" *
*****************************************************************************/
void dumpwebpage_init(void)
{
struct tcp_pcb *pcb;
pcb = tcp_new(); // create a TCP control block
tcp_bind(pcb, IP_ADDR_ANY, 80); // bind the new connection to port 80
pcb = tcp_listen(pcb); // start listening
}
/*****************************************************************************
* send_buf() *
* This function is called to send a block of the web page *
*****************************************************************************/
static void send_buf(struct tcp_pcb *pcb, struct dumpwebpage_state *es)
{
int len;
// send HTTP response if this is the first call of send_buf
if(es->page_offset == -1){
printf(" Starting transmission of %d bytes by sending HTTP response (%d bytes)...",
es->page_size + sizeof(http_get_response)-1, sizeof(http_get_response)-1);
// abort if there is not enough memory for the HTTP response in the send buffer
len = tcp_sndbuf(pcb); // get availabe space in send buffer
if(len < sizeof(http_get_response)-1){
printf("ERROR! (not enough memory to buffer HTTP response)\n");
return;
}
tcp_write(pcb, (unsigned char *)http_get_response, sizeof(http_get_response)-1, 1);
es->bytes_left+=sizeof(http_get_response)-1;
es->page_offset=0;
printf("OK\n");
}
len = tcp_sndbuf(pcb); // get availabe space in send buffer
if(es->page_offset >= es->page_size){ // abort if the whole page has been sent
return;
}
if(len == 0){ // abort if the whole page has been sent
return;
}
if(len > (es->page_size - es->page_offset)){ // send rest of the page
len = es->page_size - es->page_offset;
}
tcp_write(pcb, (unsigned char *)WebPage+es->page_offset, len, 1);
es->bytes_left+=len;
es->page_offset+=len;
tcp_output(pcb); // flush buffer
}
/*****************************************************************************
* close_conn() *
* This function is called to close an active connection *
*****************************************************************************/
static void close_conn(struct tcp_pcb *pcb, struct dumpwebpage_state *es)
{
tcp_arg(pcb, NULL);
if(es != NULL){
mem_free(es);
}
printf(" Closing connection...");
if(tcp_close(pcb) == ERR_OK){
printf("OK\n");
}
else {
printf("ERROR!\n");
}
}
/*****************************************************************************
* dumpwebpage_poll() *
* This callback function is called periodically to continue sending data or *
* to close the connection *
*****************************************************************************/
static err_t dumpwebpage_poll(void *arg, struct tcp_pcb *pcb)
{
struct dumpwebpage_state *es;
es = arg;
if(es == NULL){
return ERR_CONN;
}
send_buf(pcb, es); // try to send more data
if(es->page_offset >= es->page_size){ // everything sent => close connection
printf(" Ending transmission (page size == %d, page offset == %d), calling close_conn()\n",
es->page_size, es->page_offset);
close_conn(pcb, es);
return ERR_CLSD;
}
return ERR_OK;
}
/*****************************************************************************
* dumpwebpage_sent() *
* This callback function is called when data has been physically transmitted*
*****************************************************************************/
static err_t dumpwebpage_sent(void *arg, struct tcp_pcb *pcb, u16_t len)
{
struct dumpwebpage_state *es;
es = arg;
if(es != NULL){
if(len > 1){
es->bytes_left-=len; // adjust send buffer
}
}
return ERR_OK;
}
/*****************************************************************************
* dumpwebpage_recv() *
* This callback function is called when new data has been received *
*****************************************************************************/
static err_t dumpwebpage_recv(void *arg, struct tcp_pcb *pcb, struct pbuf *p, err_t err)
{
struct dumpwebpage_state *es;
es = arg;
pbuf_free(p); // do not process received data, just
// free the allocated memory
return ERR_OK;
}
/*****************************************************************************
* dumpwebpage_accept() *
* This callback function is called when a new connection is opened *
*****************************************************************************/
static err_t dumpwebpage_accept(void *arg, struct tcp_pcb *pcb, err_t err)
{
struct dumpwebpage_state *es;
tcp_setprio(pcb, TCP_PRIO_MIN);
printf(" Accepting new connection (assuming a HTTP GET request)...");
// alloc memory to hold the connection state
es = mem_malloc(sizeof(struct dumpwebpage_state));
if(es == NULL){
printf("ERROR! (out of memory)\n");
return ERR_MEM;
}
// initialize state information
es->bytes_left = 0; // no buffered bytes in queue yet
es->page_offset = -1; // use "-1" to signal the the HTTP response is not sent
es->page_size = sizeof(WebPage) - 1; // set the size of the web page
tcp_arg(pcb, es); // TCP shall pass the structure "es" with
printf("OK\n"); // the state information to all callbacks
tcp_poll(pcb, dumpwebpage_poll, 0); // TCP shall call dumpwebpage_poll() when
// incoming data is detected
return ERR_OK;
}
/*****************************************************************************
* dumpwebpage_err() *
* This callback function is called in case of errors *
*****************************************************************************/
static void dumpwebpage_err(void *arg, err_t err)
{
printf(" Error occurred: err == %d\n", err);
if(arg != NULL){
mem_free(arg);
}
}
/*****************************************************************************
* lwip_tcp_event() *
* This function is called to handle lwip events *
*****************************************************************************/
err_t lwip_tcp_event(void *arg, struct tcp_pcb *pcb, enum lwip_event ev, struct pbuf *p, u16_t size, err_t err)
{
int retvalue = ERR_OK;
switch(ev){
case LWIP_EVENT_ACCEPT:
retvalue = dumpwebpage_accept(arg, pcb, err);
break;
case LWIP_EVENT_SENT:
retvalue = dumpwebpage_sent(arg, pcb, size);
break;
case LWIP_EVENT_RECV:
retvalue = dumpwebpage_recv(arg, pcb, p, err);
break;
case LWIP_EVENT_ERR:
dumpwebpage_err(arg, err);
break;
case LWIP_EVENT_POLL:
retvalue = dumpwebpage_poll(arg, pcb);
break;
default:
break;
}
return retvalue;
}
⌨️ 快捷键说明
复制代码Ctrl + C
搜索代码Ctrl + F
全屏模式F11
增大字号Ctrl + =
减小字号Ctrl + -
显示快捷键?