1、- 1 -第一部分:移植类 1一、实验目的; 1二、实验内容 1三、实验环境 1四、实验步骤 2五、实验结果与讨论 3第二部分:代码类 3一、实验目的 3二、实验内容与要求 4三、主要仪器设备 4四、实验内容 44.1、实验基本功能 .44.2 主要代码编写: 44.2.1、实现服务器功能的主要代码编写 54.2.2、实现客户端功能的主要代码编写 14五、实验内容运行结果: 215.1 客户端和服务端均在虚拟机 linux 下运行 .215.2 虚拟机 linux 运行服务端,开发板运行客户端 22六、实验结果与讨论 24第一部分:移植类一、实验目的;利用虚拟机,在 redhat linux
2、下编译一个能在开发板上成功运行的应用软件二、实验内容在嵌入式 Linux 中移植一个能播放 U 盘上的 mp3 音频文件的应用程序MadPlay。三、实验环境Win7、虚拟机中的 redhat linux- 2 -四、实验步骤首先通过 ftp 把四个所需安装包拷贝到虚拟机的 linux 中,然后依次进行如下操作:1、创建工作目录:2、创建如下子目录以存放不同的源文件目录说明:tarball 目录用来存放所有的源代码包src-x86 目录用来存放 X86 版本的所有源代码文件src-arm 目录用来存放 ARM 版本的所有源代码文件target-x86 目录是 X86 版本的安装目录target
3、-arm 目录是 ARM 版本的安装目录设置环境变量:将相关安装包拷贝到工作目录中:3、编译安装 zlib-1.2.3.tar.zip配置4、然后 make-make install 即可5、编译安装 libid3tag-0.15.1b- 3 -(注:截图中的第一行代码后面部分为:-I$TARGET_DIR/include)6、然后 make-make install 即可7、编译安装 libmad-0.15.1b配置8、然后 make-make install 即可9、编译安装 madplay-0.15.2b配置10、然后 make-make install 即可Make install 完
4、成后,会在 target-arm/bin 目录生成在 arm 开发板上可以运行的二进制文件 madplay,拷贝到 user-ftp 目录下;打开超级终端,连接到开发板上,在超级终端上通过 ftp 连接到虚拟机,然后使用 get 命令获取 madplay 和 mp3 文件,退出 ftp,运行“./madplay music.mp3”即可播放视频。五、实验结果与讨论成功播发音频文件 music.mp3,并演示给老师看,但在实验结束后忘记截取了相关图像,因此结果的图像未展现。第二部分:代码类一、实验目的按照教学计划,本课程要求初步掌握嵌入式基本知识,懂得在开发板使用wince 和 linux 基本
5、操作,本实验是利用 socket 是的开发板与主机通信。- 4 -二、实验内容与要求Wince/Linux 平台与 windows 主机间使用以太网实现通信,要求在linux/wince/windows 上编写一个 TCP socket 数据包收发程序,实现数据的通信,如实现文件发送。 (也可以是 2 个开发板间的网络通信)三、主要仪器设备1、已连接网络的计算机。2、安装 red hat9 的虚拟机。3、装有 linux 的开发板四、实验内容4.1、实验基本功能在 linux 下用 C 语言编写,实现如下功能:数据的上传、下载4.2 主要代码编写:Linux 系统下,用文本编辑器编写 ftp
6、客户端与服务器端的 C 语言代码,另外几个包含的头文件。下面是在 ftp 客户端和服务器功能实现中比较重要的代码。服务器端客户端- 5 -4.2.1、实现服务器功能的主要代码编写Main 主函数定义一些相关的变量等代码:int main(int argc,char* argv) int sockfd;int clientfd;uint16_t port;int ret;pid_t pid;struct sockaddr_in server_addr;if ( 2 != argc )printf(“usage: command listen_portn“);return -1;port = at
7、oi(argv1);server_addr.sin_family = AF_INET;server_addr.sin_addr.s_addr = INADDR_ANY;server_addr.sin_port = htons(port);sockfd = socket(PF_INET,SOCK_STREAM,0);if (sockfd body_len = ntohl(msg-body_len);- 9 -msg-command = ntohl(msg-command);/ printf(“len = %d, msg = %sn“, msg-body_len, msg-msg_body);如果
8、服务器出现 quit 的时候就推出 if ( COMMAND_QUIT = msg-command )printf(“client closed connection!n“);close(sockfd);return ;处理下载请求ret = handle_request(msg, sockfd);if ( SOCK_ERROR = ret )return;free(msg);处理客户端的下载int handle_get(msg_head_ctrl_t * msg, int sockfd)int fd;int ret;bool exist;uint32_t body_len;msg_head_
9、ctrl_t *ack_msg;ssize_t read_bytes;ssize_t sent_bytes;- 10 -检查所需下载的文件所否存在exist = file_exist( msg-msg_body );printf(“%s , %d“, msg-msg_body, exist);if ( false = exist )printf(“File %s doesnt exist!n“,msg-msg_body);body_len = msg-body_len;msg-body_len = htonl(msg-body_len);msg-command = htonl(COMMAND_
10、NO_FILE);ret = send(sockfd, msg, sizeof(msg_head_ctrl_t) + body_len, 0);if ( ( sizeof(msg_head_ctrl_t) + body_len ) != ret)printf(“send error,%s:%d“,_FUNCTION_, _LINE_);return SOCK_ERROR;return FAILED;传送下载数据while(true)read_bytes = read(fd, ack_msg-msg_body, MAX_READ_BYTES);if ( read_bytes 0 )/printf
11、(“len %d, %dn“, read_bytes, ack_msg-body_len);ack_msg-body_len = htonl(read_bytes);ack_msg-command = htonl(msg-command);ret = SUCCESSFUL;else if ( -1 = read_bytes )read_bytes = 0;ack_msg-body_len = 0;- 11 -ack_msg-command = htonl(COMMAND_ERROR_FILE);ret = FAILED;else if ( 0 = read_bytes ) /传送完退出ack_
12、msg-body_len = 0;ack_msg-command = htonl(COMMAND_END_FILE);ret = SUCCESSFUL;sent_bytes = send( sockfd, ack_msg, read_bytes + sizeof(msg_head_ctrl_t), 0);if ( sent_bytes != (read_bytes + sizeof(msg_head_ctrl_t)ret = SOCK_ERROR;printf(“send data error!%s:%d“,_FUNCTION_, _LINE_);break;if ( 0 = ack_msg-
13、body_len ) break;close(fd);return ret;处理显示服务端目录内容和打印服务端路径int handle_ls_pwd(msg_head_ctrl_t * msg, int sockfd)FILE *file;msg_head_ctrl_t *ack_msg;size_t read_bytes;size_t ret;- 12 -printf(“%sn“, msg-msg_body);file = popen( msg-msg_body, “r“);if ( NULL = file )printf(“execute command failed! %sn“, msg
14、-msg_body);return FAILED;ack_msg = malloc(sizeof(msg_head_ctrl_t) + MAX_READ_BYTES);if ( NULL = ack_msg )printf(“out of memory!n“);return FAILED;ack_msg-command = htonl( msg-command );while(true)read_bytes = fread(ack_msg-msg_body,1, MAX_READ_BYTES, file);if ( ferror(file)break;ack_msg-body_len = ht
15、onl(read_bytes);ret = send(sockfd, ack_msg, read_bytes+sizeof(msg_head_ctrl_t), 0);if ( (read_bytes+sizeof(msg_head_ctrl_t) != ret )printf(“sock error!n“);return SOCK_ERROR;if ( feof(file ) ) printf(“send over!n“); break;pclose(file);- 13 -处理服务器的请求int handle_request( msg_head_ctrl_t * msg, int sockf
16、d) char *cmd;int ret;switch(msg-command)case COMMAND_CD: /处理 cd 命令cmd = trim_all_space( msg-msg_body+2);/skip “cd“ charatcerret = chdir(cmd);if ( -1 = ret )printf(“%s, |%s|n“, strerror(errno), cmd);break;case COMMAND_LS:case COMMAND_PWD:ret = handle_ls_pwd(msg, sockfd);break;case COMMAND_GET:ret = h
17、andle_get(msg, sockfd);break;case COMMAND_PUT:break;default:ret = FAILED;break;return ret;- 14 -4.2.2、实现客户端功能的主要代码编写建立套接字sockfd = socket(PF_INET, SOCK_STREAM , 0);if(sockfd body_len = ntohl(msg-body_len);msg-command = ntohl(msg-command);if ( (COMMAND_LS=msg-command) | (COMMAND_PWD=msg-command) )- 16
18、 -printf(“n%sn“,msg-msg_body);else if ( COMMAND_GET = msg-command )save_file_to_disk(msg-msg_body);free(msg);把命令传送到服务端int send_command_to_server( int sockfd, char *user_input, command_type_t type)ssize_t ret;msg_head_ctrl_t *msg;int body_len;int total_len;body_len = strlen(user_input);total_len = bo
19、dy_len + sizeof(msg_head_ctrl_t);msg = malloc(total_len);if ( NULL = msg )printf(“out of memeory!n“);return FAILED;msg-command = htonl(type);msg-body_len = htonl(body_len);memcpy(msg-msg_body, user_input, body_len);ret = send(sockfd, msg, total_len, 0);if ( ret body_len), MSG_PEEK);if (ret body_len
20、= ntohl(msg-body_len);msg-command = ntohl(msg-command);- 19 -if ( COMMAND_NO_FILE = msg-command )printf(“File %s doesnt exist on servern“, user_input);ret = FAILED;goto Exit;if ( -1 = fd)fd = open(user_input, O_WRONLY|O_CREAT|O_EXCL, 0660);if ( -1 = fd)printf(“create file %s failed! %sn“, user_input
21、, strerror(errno);ret = FAILED;goto Exit;/save to fileret = write(fd, msg-msg_body, msg-body_len);if ( msg-body_len != ret )printf(“Write file failed!n“);ret = FAILED;goto Exit;if ( COMMAND_END_FILE = msg-command ) ret = SUCCESSFUL;goto Exit;Exit:free(msg);if (SUCCESSFUL != ret )- 20 -unlink(user_in
22、put);close(fd);return ret;客户端进程函数void clinet_process(int sockfd )fd_set fs_read;int max_sock;char buf255;int ret;max_sock = sockfd STDIN_FILENO ? sockfd : STDIN_FILENO;print_client_prompt();while(1)FD_ZERO( FD_SET( STDIN_FILENO, FD_SET( sockfd, if ( select ( max_sock+1, fflush(stdout);4.2.3 由于篇幅有限,这
23、里只是列举一些重要的源代码,其他的代码在源文件里。五、实验内容运行结果:说明:在 linux 系统目录/home/user-ftp 下建立一个文件夹 ts,tc,arm_tc(1) ts 文件夹中存放编译好的 server 文件和服务端准备传送的文件 ts.txt 和arm_ts.txt(ts.txt 在虚拟机中传输,arm_ts.txt 在虚拟机和开发板见传输)(2) tc 文件夹中存放编译好的 client 文件和客户端端准备传送的文件 tc.txt(3) arm_tc 文件夹中存放经交叉编译好的 client 文件和客户端准备传送的文arm_tc.txt- 22 -5.1 客户端和服务端
24、均在虚拟机 linux 下运行就在虚拟机 ip 为 192.168.10.101 里,以 client 客户端,以 server 服务器端,进行此次实验。1. 在虚拟机 linux 目录/home/user-ftp/ts 中运行服务端2. 在虚拟机 linux 目录/home/user-ftp/tc 中运行客户端3. 在虚拟机 linux 目录/home/user-ftp/tc 中下载文件下载文件 ts.txt 成功4. 在虚拟机 linux 目录/home/user-ftp/tc 中上传文件返回到目录 ts 中查看文件,文件上传不成功。截图忘了截了5.2 虚拟机 linux 运行服务端,开发
25、板运行客户端在虚拟机 ip 为 192.168.10.101 里,以 server 服务器端;在开发板 linux 系统洗,一 client 为客户端进行此次实验。- 23 -1、在虚拟机 linux 目录/home/user-ftp/ts 中运行服务端2、在开发板中运行客户端3、在开发板中下载文件下载文件 ts.txt 成功5. 在开发板中上传文件客户端截图服务端截图- 24 -返回到目录 ts 中查看文件,文件上传不成功六、实验结果与讨论在做本次实验的时候,一开始是自己用 java 写了一个文件传输代码,只能在虚拟机上运行,并不能在开发板上运行,后来发现不符合老师要求,参考网上代码又重新编写了 C 的程序,成功的在虚拟机和开发板上运行,文件查看和下载功能均实现,但不足的地方是不能实现上传功能,这部分还有待改进但是通过这次试验,也让我懂得了很多,不仅了解了 linux 平台上如何编译和交叉编译 C、C+更让我深刻的体会到课 java 跨平台的好处,由于一开始是用 java 写的所以感触比较深。同时也让我对 socket 编程也有课进一步的了解。