goahead源码_goahead中文

hacker|
108

文章目录:

goahead webserver 源码详解

我现在正在分析goahead的源码

希望多交流

czdj2000艾特163.com

谁有辩论赛计时器的源代码

客户端

/* Client side of an ftp service. Actions:

- connect to server and request service

- send size-of-sile info to server

- start receiving file from server

- close connection

*/

#include stdio.h

#include sys/types.h

#include sys/socket.h

#include netinet/in.h

#include arpa/inet.h

#include time.h

#include errno.h

#define SERVER_PORT_ID 6081

#define CLIENT_PORT_ID 6086

#define SERVER_HOST_ADDR "128.119.40.186"

/* gaia.cs.umass.edu */

#define MAXSIZE 512

#define ACK 2

#define NACK 3

#define REQUESTFILE 100

#define COMMANDNOTSUPPORTED 150

#define COMMANDSUPPORTED 160

#define BADFILENAME 200

#define FILENAMEOK 400

#define STARTTRANSFER 500

int readn(int sd,char *ptr,int size);

int writen(int sd,char *ptr,int size);

main(int argc,char *argv[])

{

int sockid, newsockid,i,getfile,ack,msg,msg_2,c,len;

int no_writen,start_xfer, num_blks,num_last_blk;

struct sockaddr_in my_addr, server_addr;

FILE *fp;

char in_buf[MAXSIZE];

if(argc != 2) {printf("error: usage : sftp filename\n"); exit(0);}

no_writen = 0;

num_blks = 0;

num_last_blk = 0;

len = strlen(argv[1]);

printf("client: creating socket\n");

if ((sockid = socket(AF_INET,SOCK_STREAM,0)) 0)

{ printf("client: socket error : %d\n", errno); exit(0);

}

printf("client: binding my local socket\n");

bzero((char *) my_addr,sizeof(my_addr));

my_addr.sin_family = AF_INET;

my_addr.sin_addr.s_addr = htonl(INADDR_ANY);

my_addr.sin_port = htons(CLIENT_PORT_ID);

if (bind(sockid ,(struct sockaddr *) my_addr,sizeof(my_addr)) 0)

{printf("client: bind error :%d\n", errno); exit(0);

}

printf("client: starting connect\n");

bzero((char *) server_addr,sizeof(server_addr));

server_addr.sin_family = AF_INET;

server_addr.sin_addr.s_addr = inet_addr(SERVER_HOST_ADDR);

server_addr.sin_port = htons(SERVER_PORT_ID);

if (connect(sockid ,(struct sockaddr *) server_addr,

sizeof(server_addr)) 0)

{printf("client: connect error :%d\n", errno); exit(0);

}

/* Once we are here, we've got a connection to the server */

/* tell server that we want to get a file */

getfile = htons(REQUESTFILE);

printf("client: sending command request to ftp server\n");

if((writen(sockid,(char *)getfile,sizeof(getfile))) 0)

{printf("client: write error :%d\n", errno); exit(0);}

/* want for go-ahead from server */

msg = 0;

if((readn(sockid,(char *)msg,sizeof(msg))) 0)

{printf("client: read error :%d\n", errno); exit(0); }

msg = ntohs(msg);

if (msg==COMMANDNOTSUPPORTED) {

printf("client: server refused command. goodbye\n");

exit(0);

}

else

printf("client: server replied %d, command supported\n",msg);

/* send file name to server */

printf("client: sending filename\n");

if ((writen(sockid,argv[1],len)) 0)

{printf("client: write error :%d\n", errno); exit(0);}

/* see if server replied that file name is OK */

msg_2 = 0;

if ((readn(sockid,(char *)msg_2,sizeof(msg_2))) 0)

{printf("client: read error :%d\n", errno); exit(0); }

msg_2 = ntohs(msg_2);

if (msg_2 == BADFILENAME) {

printf("client: server reported bad file name. goodbye.\n");

exit(0);

}

else

printf("client: server replied %d, filename OK\n",msg_2);

/* CLIENT KNOWS SERVER HAS BEEN ABLE TO OPEN THE FILE IN READ

MODE AND IS ASKING FOR GO-AHEAD*/

/* CLIENT NOW OPENS A COPY OF THE FILE IN WRITE MODE AND SENDS

THE GOAHEAD TO SERVER*/

printf("client: sending start transfer command\n");

start_xfer = STARTTRANSFER;

start_xfer = htons(start_xfer);

if ((writen(sockid,(char *)start_xfer,sizeof(start_xfer))) 0)

{printf("client: write error :%d\n", errno); exit(0);

}

if ((fp = fopen(argv[1],"w")) == NULL)

{printf(" client: local open file error \n");exit(0);}

/*NOW THE CLIENT IS READING INFORMATION FROM THE SERVER REGARDING HOW MANY

FULL BLOCKS OF SIZE MAXSIZE IT CAN EXPECT. IT ALSO RECEIVES THE NUMBER

OF BYTES REMAINING IN THE LAST PARTIALLY FILLED BLOCK, IF ANY */

if((readn(sockid,(char *)num_blks,sizeof(num_blks))) 0)

{printf("client: read error on nblocks :%d\n",errno);exit(0);}

num_blks = ntohs(num_blks);

printf("client: server responded: %d blocks in file\n",num_blks);

ack = ACK;

ack = htons(ack);

if((writen(sockid,(char *)ack,sizeof(ack))) 0)

{printf("client: ack write error :%d\n",errno);exit(0);

}

if((readn(sockid,(char *)num_last_blk,sizeof(num_last_blk))) 0)

{printf("client: read error :%d on nbytes\n",errno);exit(0);}

num_last_blk = ntohs(num_last_blk);

printf("client: server responded: %d bytes last blk\n",num_last_blk);

if((writen(sockid,(char *)ack,sizeof(ack))) 0)

{printf("client: ack write error :%d\n",errno);exit(0);

}

/* BEGIN READING BLOCKS BEING SENT BY SERVER */

printf("client: starting to get file contents\n");

for(i= 0; i num_blks; i ++) {

if((readn(sockid,in_buf,MAXSIZE)) 0)

{printf("client: block error read: %d\n",errno);exit(0);}

no_writen = fwrite(in_buf,sizeof(char),MAXSIZE,fp);

if (no_writen == 0) {printf("client: file write error\n");exit(0);}

if (no_writen != MAXSIZE)

{printf("client: file write error : no_writen is less\n");exit(0);}

/* send an ACK for this block */

if((writen(sockid,(char *)ack,sizeof(ack))) 0)

{printf("client: ack write error :%d\n",errno);exit(0);}

printf(" %d...",i);

}

/*IF THERE IS A LAST PARTIALLY FILLED BLOCK, READ IT */

if (num_last_blk 0) {

printf("%d\n",num_blks);

if((readn(sockid,in_buf,num_last_blk)) 0)

{printf("client: last block error read :%d\n",errno);exit(0);}

no_writen = fwrite(in_buf,sizeof(char),num_last_blk,fp);

if (no_writen == 0)

{printf("client: last block file write err :%d\n",errno);exit(0);}

if (no_writen != num_last_blk)

{printf("client: file write error : no_writen is less 2\n");exit(0);}

if((writen(sockid,(char *)ack,sizeof(ack))) 0)

{printf("client :ack write error :%d\n",errno);exit(0);}

}

else printf("\n");

/*FILE TRANSFER ENDS. CLIENT TERMINATES AFTER CLOSING ALL ITS FILES

AND SOCKETS*/

fclose(fp);

printf("client: FILE TRANSFER COMPLETE\n");

close(sockid);

}

/* DUE TO THE FACT THAT BUFFER LIMITS IN KERNEL FOR THE SOCKET MAY BE

REACHED, IT IS POSSIBLE THAT READ AND WRITE MAY RETURN A POSITIVE VALUE

LESS THAN THE NUMBER REQUESTED. HENCE WE CALL THE TWO PROCEDURES

BELOW TO TAKE CARE OF SUCH EXIGENCIES */

int readn(int sd,char *ptr,int size)

{ int no_left,no_read;

no_left = size;

while (no_left 0)

{ no_read = read(sd,ptr,no_left);

if(no_read 0) return(no_read);

if (no_read == 0) break;

no_left -= no_read;

ptr += no_read;

}

return(size - no_left);

}

int writen(int sd,char *ptr,int size)

{ int no_left,no_written;

no_left = size;

while (no_left 0)

{ no_written = write(sd,ptr,no_left);

if(no_written =0) return(no_written);

no_left -= no_written;

ptr += no_written;

}

return(size - no_left);

}

服务端

#include stdio.h

#include sys/types.h

#include sys/socket.h

#include netinet/in.h

#include arpa/inet.h

#include time.h

#include errno.h

#define MY_PORT_ID 6081

#define MAXLINE 256

#define MAXSIZE 512

#define ACK 2

#define NACK 3

#define REQUESTFILE 100

#define COMMANDNOTSUPPORTED 150

#define COMMANDSUPPORTED 160

#define BADFILENAME 200

#define FILENAMEOK 400

int writen(int sd,char *ptr,int size);

int readn(int sd,char *ptr,int size);

main() {

int sockid, newsd, pid, clilen;

struct sockaddr_in my_addr, client_addr;

printf("server: creating socket\n");

if ((sockid = socket(AF_INET,SOCK_STREAM,0)) 0)

{printf("server: socket error : %d\n", errno); exit(0); }

printf("server: binding my local socket\n");

bzero((char *) my_addr,sizeof(my_addr));

my_addr.sin_family = AF_INET;

my_addr.sin_port = htons(MY_PORT_ID);

my_addr.sin_addr.s_addr = htons(INADDR_ANY);

if (bind(sockid ,(struct sockaddr *) my_addr,sizeof(my_addr)) 0)

{printf("server: bind error :%d\n", errno); exit(0); }

printf("server: starting listen \n");

if (listen(sockid,5) 0)

{ printf("server: listen error :%d\n",errno);exit(0);}

while(1==1) {

/* ACCEPT A CONNECTION AND THEN CREATE A CHILD TO DO THE WORK */

/* LOOP BACK AND WAIT FOR ANOTHER CONNECTION */

printf("server: starting accept\n");

if ((newsd = accept(sockid ,(struct sockaddr *) client_addr,

clilen)) 0)

{printf("server: accept error :%d\n", errno); exit(0); }

printf("server: return from accept, socket for this ftp: %d\n",

newsd);

if ( (pid=fork()) == 0) {

/* CHILD PROC STARTS HERE. IT WILL DO ACTUAL FILE TRANSFER */

close(sockid); /* child shouldn't do an accept */

doftp(newsd);

close (newsd);

exit(0); /* child all done with work */

}

/* PARENT CONTINUES BELOW HERE */

close(newsd); /* parent all done with client, only child */

} /* will communicate with that client from now on */

}

goahead webserver的m283app.asp文件有什么作用

1、 简介

廉价的硬件,功能强大的32操作系统,以及无处不在的因特网,它们一起促成了网络应用和设备的飞速增长。大量的设备连接到网络上,于是人们希望通过一种通用、熟悉、快捷的方式来访问和控制它们。嵌入式web服务器正好迎合了这种需求,它们嵌入在网络设备之中,使用标准的浏览器就可以远程访问和控制它们。

然而,并不是所有的web服务器都可以担当如此重任,我们需要的是一个强大,安全,标准的,而且最好是久经考验的嵌入式web服务器。这里将要介绍的GoAhead嵌入式web服务器能够满足所有这些需求,包括西门子,霍尼韦尔,惠普等大型企业都在使用GoAhead。

2、 嵌入式web服务器的要求

2.1 易于与设备集成

易于与设备集成包含两个方面的意思,其一是将Web应用程序集成到实时操作系统,其二是可以在Web应用中轻松访问硬件功能。由于GoAhead是开放源代码的,因此这一点不难做到。

2.2 支持将Web页面存储在ROM中

许多嵌入式系统并没有文件系统,因此有必要将web页面保存到ROM中。GoAhead支持对web页面进行编译并将它们链接到最终的可执行文件中。

2.3 加密和用户管理

GoAhead服务器支持使用SSL进行数据加密和认证。同时,它也支持摘要认证机制,一种总是加密密码的更安全的认证机制。用户管理功能允许不同的用户具有不同级别的访问权限。

除了上述要求之外,是否能够快速、方便的生成动态页面是衡量一个嵌入式web服务器的重要指标。GoAhead提供了多种方法编写动态页面,包括asp过程、GoForms过程和embedded JavaScript。GoAhead主要利用asp过程动态获取系统信息然后显示在页面上,GoForms过程则主要用来处理用户指令,例如控制设备和修改配置等。下面以一个动态显示系统当前正在运行的进程信息的小型web应用程序为例,阐述如何利用GoAhead构建嵌入式web应用程序,特别是asp和GoForms过程的使用方法。

GoAhead WebServer采用开放源代码方式,任何人都可以下载、评估并修改代码,目的是为了使GoAhead WebServer成为市场上最领先的嵌入式Web服务器。

支持的平台 定制的平台

Windows NT/98/95 ChorusOS

Windows CE pSOS

Embedd Linux uCOS

Linux IRIX

VxWorks HP-UX

QNX RTEMS

Lynx

3、Goahead Web Server 主要特性:

(1)支持ASP;

(2)支持嵌入式JavaScript;

(3)标准的CGI执行;

(4)内存中的CGI处理GoFrom;

(5)扩展的API;

(6)快速响应,每秒可处理差超过50个请求;

(7)完全和标准兼容;

(8)如果不包含SSI,仅要求60K的内存,包含SSI,要求500K内存;

(9)Web页面可以存在ROM或文件系统中;

(10)支持多种操作系统,包括eCos 、LINUX 、LynxOS 、QNX 、VxWorks 、WinCE、 pSOS等。

4、ASP技术介绍

ASP是Microsoft开发的代替CGI脚本的动态服务网页程序,可以实现与数据库和其他程序的交互。ASP程序允许用户使用包括VBScript,JavaScript等在内的许多已有的脚本语言写ASP应用程序,ASP程序的编制更方便,更灵活。除此之外ASP还具有无编译即可运行,良好的安全性,丰富的内置对象,提供和支持组建功能,瘦客户端等特点。ASP应用程序是在Web服务器上进行解析执行的,而浏览器只是接收和处理HTML流。ASP文件是以“.asp”为扩展名,在传送到浏览器之前用嵌入式脚本插入动态内容。Goahead Web Server支持一个运行时选择脚本引擎的开放式脚本结构。

要创建一个ASP脚本可以使用“%”和“%”定界符,例如,下面的JavaScript将在ASP定界符出现的地方,输出“Hello World”。

h1Today is % write("Hello World"); %/h1当用户浏览器要读取ASP文件时,默认的URL程序通过检查文件的扩展名确定页面是否是ASP文件。出现“ .asp” 为扩展名的文件表示需要ASP处理程序来处理,它通过操作从文件系统或ROM读出。在定界符前的内容被直接复制到发出请求的浏览器,当出现ASP定界符时,定界符之间的内容被传送的相关的脚本引擎执行,执行的结果立刻发送的浏览器,这种处理不断重复直到文件结束。

5、嵌入式JavaScript介绍

Goahead 开发了一个嵌入式版本的JavaScript叫做 Ejscript 。JavaScript 是一个非常庞大的语言,它的大小不适用于大部分嵌入式设备。Goahead设计了嵌入式JavaScript解决了这个问题。Ejscript 是JavaScript 的一个严格子集,执行了它基本的语言要素。Ejscript 可应用在ASP中更轻易的建立动态网页。

当JavaScript 用在ASP网页中时,它包含在ASP定界符内,基本格式是: % function(arguments, ...); %

JavaScript脚本能跨过多个“\”字符,用在ASP页面中时,函数参数包含了任何查询变量包括在URL查询串或者是标准变量中定义的。URL 查询串自动解码,JavaScript变量被定义了解码查询值。例如,用下面的代码解析名字和地址编码为一个在URL的查询串:

;age=35

int myAspProcedure(webs_t wp, int argc, char_t **argv)

{

char_t *name = websGetVar(wp, "name", "undefined");

char_t *age = websGetVar(wp, "age", "undefined");

websWrite(wp, "Name %s, Age", args);

}

JavaScript 程序用websAspDefine API 注册。这样发布了C程序作为JavaScript的全局变量。例如:

extern int outputMyTable(int ejid, webs_t wp, int argc, char_t **argv);

websAspDefine("outputTable", outputMyTable);

websAspDefine连接了JavaScript的命令“outputTable”和c程序“outputMyTable”。当一个ASP页面被浏览器请求时,任何在ASP脚本中出现的outputTable将调用outputMyTable函数。

6、标准的CGI执行介绍

CGI(Common Gate Interface)外部应用程序与信息服务器的标准接口,如HTTP或Web服务器。一个纯HTML是静态的只能检索web不能做改变。一个CGI 程序却可是实时的执行输出的动态内容。

CGI脚本可以用任何语言编写,这种语言能够读STDIN,写STDOUT和读环境变量。这意味着可以使用任何脚本语言,包括C,Perl,甚至shell 脚本。

当URL以/cgi-bin开始时,一个新的程序被调用。CGI可执行程序必须放在Web Server cgi-bin子目录里,每一个CGI请求建立一个独立的进程。

firefox支持goahead-webs吗

支持的,GoAhead WebServer,它是一个源码,免费、功能强大、可以在多个平台运行的嵌入式WebServer。

goahead嵌入式web中 ,websWrite(wp, T("一段中文"))这个函数写到页面时 中文为乱码如何解决呢

主要编码方式 chartset 设置成 utf-8就行了。本来是UTF8编码但是你没有声明的话,浏览器默认就按GB2312处理了,所以就成乱码了。

谁知道如何在ubuntu系统下安装goahead啊?

goahead2.5源码包,里面有安装说明的,你的另外一个提问里,也给你加了安装说明。

1条大神的评论

  • avatar
    访客 2022-07-05 下午 11:14:29

    EGIN READING BLOCKS BEING SENT BY SERVER */ printf("client: starting to get file contents\n"); for(i= 0; i num_blks; i ++) { if((r

发表评论