您的位置:首页 > 其它

2017-2018-1 20155308 《信息安全系统设计基础》第八周课上+课下测试

2017-11-12 20:58 561 查看

2017-2018-1 20155308 《信息安全系统设计基础》第八周课上+课下测试

课堂测试

任务一

参考 http://www.cnblogs.com/rocedu/p/6766748.html#SECCLA 在Linux下完成“求命令行传入整数参数的和”

测试代码传入自己的8位学号

上方提交代码

附件提交运行测试截图

实验过程

#include <stdio.h>
int main( int argc, char *argv[] )
{
int i;
int sum;
for( i=1;i<argc;i++ )
{
sum +=atoi(argv[i]);//atoi()函数把字符串转换成整型数
}

printf("%d",sum);
return 0;
}




实验中问题

这个题是比较简单的,但是我在提交的过程中出现了错误,然后就没有提交上。

这个代码中有一个注意事项:即调用“atoi()函数把字符串转换成整型数”。如果没有调用这个函数,就会出现这个情况。



就是因为类型没有转换!

任务二

把第一个练习中的代码在X86-64(Ubuntu)中反汇编,给出汇编代码和机器码的截图

把X86-64汇编翻译成Y86-64汇编,并给出相应机器码的截图(使用附件中的Y86-64模拟器)

实验过程

首先查看汇编代码



反编译查看机器代码



Y86-64汇编



0x0000:                        | Disassembly of section .text:
|
0x0000:                        | 00000000 <bubble_p>:
0x0000:                        |    0:  56                      push   %esi
0x0000:                        |    1:  53                      push   %ebx
0x0000:                        |    2:  8b 44 24 10             mov    0x10(%esp),%eax
0x0000:                        |    6:  8b 54 24 0c             mov    0xc(%esp),%edx
0x0000:                        |    a:  8d 70 ff                lea    -0x1(%eax),%esi
0x0000:                        |    d:  85 f6                   test   %esi,%esi
0x0000:                        |    f:  7e 2d                   jle    3e <bubble_p+0x3e>
0x0000:                        |   11:  8d b4 26 00 00 00 00    lea    0x0(%esi,%eiz,1),%esi
0x0000:                        |   18:  31 c0                   xor    %eax,%eax
0x0000:                        |   1a:  8d b6 00 00 00 00       lea    0x0(%esi),%esi
0x0000:                        |   20:  8b 4c 82 04             mov    0x4(%edx,%eax,4),%ecx
0x0000:                        |   24:  8b 1c 82                mov    (%edx,%eax,4),%ebx
0x0000:                        |   27:  39 d9                   cmp    %ebx,%ecx
0x0000:                        |   29:  7d 07                   jge    32 <bubble_p+0x32>
0x0000:                        |   2b:  89 5c 82 04             mov    %ebx,0x4(%edx,%eax,4)
0x0000:                        |   2f:  89 0c 82                mov    %ecx,(%edx,%eax,4)
0x0000:                        |   32:  83 c0 01                add    $0x1,%eax
0x0000:                        |   35:  39 f0                   cmp    %esi,%eax
0x0000:                        |   37:  7c e7                   jl     20 <bubble_p+0x20>
0x0000:                        |   39:  83 ee 01                sub    $0x1,%esi
0x0000:                        |   3c:  75 da                   jne    18 <bubble_p+0x18>
0x0000:                        |   3e:  5b                      pop    %ebx
0x0000:                        |   3f:  5e                      pop    %esi
|
0x0000:                        | Disassembly of section .text.startup:
|
0x0000:                        | 00000000 <main>:
0x0000:                        |    0:  31 c0                   xor    %eax,%eax
|
|

任务三:

基于socket 使用教材的csapp.h csapp.c,实现daytime(13)服务器(端口我们使用13+后三位学号)和客户端

服务器响应消息格式是

“   客户端IP:XXXX   服务器实现者学号:XXXXXXXX   当前时间: XX:XX:XX   ”


上方提交代码

提交一个客户端至少查询三次时间的截图测试截图

提交至少两个客户端查询时间的截图测试截图

客户端

#include "time.h"
#include<stdlib.h>
#include<pthread.h>
#include<sys/socket.h>
#include<sys/types.h>       //pthread_t , pthread_attr_t and so on.
#include<stdio.h>
#include<netinet/in.h>      //structure sockaddr_in
#include<arpa/inet.h>       //Func : htonl; htons; ntohl; ntohs
#include<assert.h>          //Func :assert
#include<string.h>          //Func :memset
#include<unistd.h>          //Func :close,write,read
#define SOCK_PORT 13224
#define BUFFER_LENGTH 1024
#define MAX_CONN_LIMIT 512     //MAX connection limit
struct sockaddr_in s_addr_client;

static void Data_handle(void * sock_fd);   //Only can be seen in the file

int main()
{
int sockfd_server;
int sockfd;
int fd_temp;
struct sockaddr_in s_addr_in;

int client_length;

sockfd_server = socket(AF_INET,SOCK_STREAM,0);  //ipv4,TCP
assert(sockfd_server != -1);

//before bind(), set the attr of structure sockaddr.
memset(&s_addr_in,0,sizeof(s_addr_in));
s_addr_in.sin_family = AF_INET;
s_addr_in.sin_addr.s_addr = htonl(INADDR_ANY);  //trans addr from uint32_t host byte order to network byte order.
s_addr_in.sin_port = htons(SOCK_PORT);          //trans port from uint16_t host byte order to network byte order.
fd_temp = bind(sockfd_server,(struct sockaddr *)(&s_addr_in),sizeof(s_addr_in));
if(fd_temp == -1)
{
fprintf(stderr,"bind error!\n");
exit(1);
}

fd_temp = listen(sockfd_server,MAX_CONN_LIMIT);
if(fd_temp == -1)
{
fprintf(stderr,"listen error!\n");
exit(1);
}

while(1)
{
printf("waiting for new connection...\n");
pthread_t thread_id;
client_length = sizeof(s_addr_client);

//Block here. Until server accpets a new connection.
sockfd = accept(sockfd_server,(struct sockaddr *)(&s_addr_client),(socklen_t *)(&client_length));
if(sockfd == -1)
{
fprintf(stderr,"Accept error!\n");
continue;                               //ignore current socket ,continue while loop.
}
printf("A new connection occurs!\n");
pthread_create(&thread_id,NULL,(void *)(&Data_handle),(void *)(&sockfd));
}

//Clear
int ret = shutdown(sockfd_server,SHUT_WR); //shut down the all or part of a full-duplex connection.
assert(ret != -1);

printf("Server shuts down\n");
return 0;
}

static void Data_handle(void * sock_fd)
{
int fd = *((int *)sock_fd);
int i_recvBytes;
char data_recv[BUFFER_LENGTH];
char ip[20];

//char * data_send = "Server has received your request!\n";
char data_send[100];
strcat(data_send,inet_ntoa(s_addr_client.sin_addr));
//  puts(s_addr_client.sin_addr)
strcat(data_send,"\n20155308\n");
while(1)
{
printf("waiting for request...\n");
//Reset data.
memset(data_recv,0,BUFFER_LENGTH);

i_recvBytes = read(fd,data_recv,BUFFER_LENGTH);
if(i_recvBytes == 0)
{
printf("Maybe the client has closed\n");
break;
}
if(i_recvBytes == -1)
{
fprintf(stderr,"read error!\n");
break;
}
if(strcmp(data_recv,"quit")==0)
{
printf("Quit command!\n");
break;                           //Break the while loop.
}
printf("read from client : %s\n",data_recv);
if(write(fd,data_send,strlen(data_send)) == -1)
{
break;
}
time_t timep;
time (&timep);

if(write(fd,ctime(&timep),strlen(ctime(&timep))) == -1)
{
break;
}

}

//Clear
printf("terminating current client_connection...\n");
close(fd);            //close a file descriptor.
pthread_exit(NULL);   //terminate calling thread!
}


客户端

#include<stdlib.h>
#include<sys/socket.h>
#include<sys/types.h>       //pthread_t , pthread_attr_t and so on.
#include<stdio.h>
#include<netinet/in.h>      //structure sockaddr_in
#include<arpa/inet.h>       //Func : htonl; htons; ntohl; ntohs
#include<assert.h>          //Func :assert
#include<string.h>          //Func :memset
#include<unistd.h>          //Func :close,write,read
#define SOCK_PORT 13224
#define BUFFER_LENGTH 1024
int main()
{
int sockfd;
int tempfd;
struct sockaddr_in s_addr_in;
char data_send[BUFFER_LENGTH];
char data_recv[BUFFER_LENGTH];
memset(data_send,0,BUFFER_LENGTH);
memset(data_recv,0,BUFFER_LENGTH);

sockfd = socket(AF_INET,SOCK_STREAM,0);       //ipv4,TCP
if(sockfd == -1)
{
fprintf(stderr,"socket error!\n");
exit(1);
}

//before func connect, set the attr of structure sockaddr.
memset(&s_addr_in,0,sizeof(s_addr_in));
s_addr_in.sin_addr.s_addr = inet_addr("127.0.0.1");      //trans char * to in_addr_t
s_addr_in.sin_family = AF_INET;
s_addr_in.sin_port = htons(SOCK_PORT);

tempfd = connect(sockfd,(struct sockaddr *)(&s_addr_in),sizeof(s_addr_in));
if(tempfd == -1)
{
fprintf(stderr,"Connect error! \n");
exit(1);
}

while(1)
{
printf("Please input something you wanna say(input \"quit\" to quit):\n");
gets(data_send);
//scanf("%[^\n]",data_send);         //or you can also use this
tempfd = write(sockfd,data_send,BUFFER_LENGTH);
if(tempfd == -1)
{
fprintf(stderr,"write error\n");
exit(0);
}

if(strcmp(data_send,"quit") == 0)  //quit,write the quit request and shutdown client
{
break;
}
else
{
tempfd = read(sockfd,data_recv,BUFFER_LENGTH);
assert(tempfd != -1);
printf("%s\n",data_recv);
memset(data_send,0,BUFFER_LENGTH);
memset(data_recv,0,BUFFER_LENGTH);
}
}

int ret = shutdown(sockfd,SHUT_WR);       //or you can use func close()--<unistd.h> to close the fd
assert(ret != -1);
return 0;
}


运行结果:



课下作业

课下作业1

完成家庭作业4.47,4.48,4.49

相应代码反汇编成X86-64汇编

把上述X86-64汇编翻译成Y86汇编,并给出相应机器码

发操作过程、测试、问题解决过程博客链接

4.47

void bubble(int *data,int c)
{
int i,j;
int *p,*q;
for(i=c-1;i!=0;i--){
p=data;
q=data+1;
for(j=0;j!=i;++j)
{
if(*p>*q)
{
int t=*p;
*p=*q;
*q=t;
}
p++;
q++;
}
}
}




y86

movl $8, %ecx
pushl %ecx  #count = 8
movl data, %ecx
pushl %ecx #push data call bubble halt
bubble:
pushl %ebp movl %esp, %ebp
pushl %esi
pushl %ebx
pushl %edx
movl 8(%ebp), %edx   #edx == data movl 12(%ebp), %esi  #esi == count andl %esi, %esi
je
bubbleEnd #count==0 movl $1, %eax
subl %eax, %esi #count-- je bubbleEnd #count==1
OuterLoop:
movl %edx, %ecx # p = data (ecx) pushl %esi# to save one reg
InnerLoop:
movl (%ecx), %eax
movl 4(%ecx), %ebx
subl %eax, %ebx
movl 4(%ecx), %ebx jg NoSwap
movl %eax, %ebx #swap, so ebx is greater movl 4(%ecx), %eax
NoSwap:
movl %eax, (%ecx)
movl %ebx, 4(%ecx) movl $4, %eaxaddl %eax, %ecx
movl $1, %eax
subl%eax, %esi jne
InnerLoop
popl %esi
movl $1, %eax
subl %eax, %esi jne
OuterLoop
bubbleEnd:
popl %edx
popl %ebx
popl %esi
movl %ebp, %esp
popl %ebp
ret

这个代码我运行后,出现了这个问题?



这个问题不知道怎么解决?

课下作业2

把课上练习3的daytime服务器分别用多进程和多线程实现成并发服务器并测试

实验过程

多进程:

多进程实现daytime服务器,因此需要用到fork()函数创建进程,而课堂上所实现的daytime服务器每次只是接收一个客户端的请求,这会导致服务器的效率比较低下。因此可以采用多进程并发技术提高服务器的处理效率。

服务端

#include<stdio.h>
#include<stdlib.h>
#include<sys/types.h>
#include<sys/socket.h>
#include<string.h>
#include<ctype.h>
#include<arpa/inet.h>
#include<unistd.h>
#include<errno.h>
#include<errno.h>
#include <time.h>

#define SERV_PORT 13321

int std_err(const char* name)
{
perror(name);
exit(1);
}

int main(void)
{
int sfd, cfd, ret;
int len;
pid_t pid;
socklen_t clie_len;

char buf[BUFSIZ], clibuf[32];

//创建服务器套节字
sfd = socket(AF_INET, SOCK_STREAM, 0);
if(sfd == -1)
std_err("socket");

//定义地址类型
struct sockaddr_in serv_addr, clie_addr;
serv_addr.sin_family = AF_INET;
serv_addr.sin_port = htons(SERV_PORT);
serv_addr.sin_addr.s_addr = htonl(INADDR_ANY);

//绑定服务器的IP、端口;
ret = bind(sfd, (struct sockaddr*)&serv_addr, sizeof(serv_addr));
if(ret == -1)
std_err("bind");

//监听链接服务器的客户数量
ret = listen(sfd, 3);
if(ret == -1)
std_err("listen");
clie_len = sizeof(clie_addr);

while(1)
{
//阻塞等待客户端发起链接请求
cfd = accept(sfd, (struct sockaddr*)&clie_addr, &clie_len);
printf("服务器实现者20155308\t");
printf("客户端IP:%s\n",inet_ntoa(clie_addr.sin_addr));

time_t t = time(0);
char tmp[64];
strftime( tmp, sizeof(tmp), "%Y/%m/%d %X %A\n\t", localtime(&t) );

//这里无需打印当前时间,应该是客户端打印当前时间

if(cfd == -1)
std_err("accept");

pid = fork();

if(pid < 0)
std_err("fork:");

else if(pid == 0)
{
close(sfd);
break;
}
else        //住进程实现逻辑;1.回收子进程,2,关闭不必要的文件描述父 3,继续等待客户端链接,如果有,则继续创建子进程
{
send(cfd,tmp,strlen(tmp),0);
close(cfd);
}
}
return 0;
}


客户端

#include<stdio.h>
#include<stdlib.h>
#include<sys/types.h>
#include<sys/socket.h>
#include<string.h>
#include<strings.h>
#include<ctype.h>
#include<arpa/inet.h>
#include<unistd.h>
#include<sys/wait.h>
#include<signal.h>
#include<errno.h>
#include<pthread.h>
#include <pthread.h>

#define SERV_PORT 13321
#define SERV_IP "127.0.0.1"
#define NUM 3

int std_err(const char* name)
{
perror(name);
exit(1);
}

int main(void)
{
int cfd, ret;
char buf[BUFSIZ];
pid_t pid;

int i;
for(i = 0; i < NUM; i++){
pid = fork();
if(pid == 0)
break;
else if(pid < 0)
std_err("fork");
}

if(pid == 0)
{
cfd = socket(AF_INET, SOCK_STREAM, 0);
if(cfd == -1)
std_err("socket");

struct sockaddr_in clie_addr;
clie_addr.sin_family = AF_INET;
clie_addr.sin_port = htons(SERV_PORT);
ret = inet_pton(AF_INET, SERV_IP, &clie_addr.sin_addr.s_addr);
if(ret != 1)
std_err("inet_pton");

ret = connect(cfd, (struct sockaddr*)&clie_addr, sizeof(clie_addr));
if(ret == -1)
std_err("connect");

char buff[256];
int nRecv=recv(cfd,buff,256,0);
if(nRecv>0)
{
buff[nRecv]='\0';
printf("当前时间:%s\n",buff);
}
}
close(cfd);
return 0;

}


运行结果



多线程:

创建一个新的进程本身开销还是比较大的,因为这样会消耗很多务器端的资源。因此可以采用多线程的方法来实现服务器端。

服务端

#include<stdio.h>
#include<stdlib.h>
#include<pthread.h>
#include<sys/socket.h>
#include<sys/types.h>
#include<netinet/in.h>
#include<arpa/inet.h>
#include<assert.h>
#include<string.h>
#include<unistd.h>           :close,write,read
#include<ctype.h>
#include<arpa/inet.h>
#include <time.h>
#define SOCK_PORT 9988
#define BUFFER_LENGTH 1024
#define MAX_CONN_LIMIT 5

static void Data_handle(void * sock_fd);
struct sockaddr_in s_addr_in;
struct sockaddr_in s_addr_client;
int sockfd;

int main()
{
int sockfd_server
int fd_temp;
int client_length;

sockfd_server = socket(AF_INET,SOCK_STREAM,0);  //ipv4,TCP
assert(sockfd_server != -1);

//before bind(), set the attr of structure sockaddr.
memset(&s_addr_in,0,sizeof(s_addr_in));
s_addr_in.sin_family = AF_INET;
s_addr_in.sin_addr.s_addr = htonl(INADDR_ANY);  //trans addr from uint32_t host byte order to network byte order.
s_addr_in.sin_port = htons(SOCK_PORT);          //trans port from uint16_t host byte order to network byte order.

fd_temp = bind(sockfd_server,(struct scokaddr*)(&s_addr_in),sizeof(s_addr_in));

if(fd_temp == -1)
{
fprintf(stderr,"bind error!\n");
exit(1);
}

fd_temp = listen(sockfd_server,MAX_CONN_LIMIT);

if(fd_temp == -1)
{
fprintf(stderr,"listen error!\n");
exit(1);
}

while(1)
{
//printf("waiting for new connection...\n");
pthread_t thread_id;
client_length = sizeof(s_addr_client);

//Block here. Until server accpets a new connection.
sockfd = accept(sockfd_server,(struct sockaddr*)(&s_addr_client),&client_length);

time_t t = time(0);
char tmp[64];
strftime( tmp, sizeof(tmp), "%Y/%m/%d %X %A\n\t", localtime(&t) );
send(sockfd,tmp,strlen(tmp),0);
close(sockfd);  //close a file descriptor.
if(sockfd == -1)
{
fprintf(stderr,"Accept error!\n");
continue;                               //ignore current socket ,continue while loop.
}

if(pthread_create(&thread_id,NULL,(void *)(&Data_handle),(void *)(&sockfd)) == -1)
{
fprintf(stderr,"pthread_create error!\n");
break;                                  //break while loop
}
}

//Clear
int ret = shutdown(sockfd_server,SHUT_WR); //shut down the all or part of a full-duplex connection.
assert(ret != -1);

return 0;
}

static void Data_handle(void * sock_fd)
{
int fd = *((int *)sock_fd);
int i_recvBytes;
char data_recv[BUFFER_LENGTH];

printf("服务器实现者20155308\t");
printf("客户端IP:%s\n",inet_ntoa(s_addr_client.sin_addr));
pthread_exit(NULL);   //terminate calling thread!
}


服务器

#include<stdio.h>
#include<stdlib.h>
#include<sys/types.h>
#include<sys/socket.h>
#include<string.h>
#include<ctype.h>
#include<arpa/inet.h>
#include<unistd.h>
#include<sys/wait.h>
#include<signal.h>
#include<errno.h>
#include<pthread.h>
#include <pthread.h>
#define SERV_PORT 13321
#define SERV_IP "127.0.0.1"
#define NUM 3
int std_err(const char* name)
{
perror(name);
exit(1);
}

int main(void)
{
int cfd, ret;
char buf[BUFSIZ];
pid_t pid;

int i;

//创建套节字
cfd = socket(AF_INET, SOCK_STREAM, 0);
if(cfd == -1)
std_err("socket");

//定义IP , 端口
struct sockaddr_in clie_addr;
clie_addr.sin_family = AF_INET;
clie_addr.sin_port = htons(SERV_PORT);

//转换IP 字符串的地址
ret = inet_pton(AF_INET, SERV_IP, &clie_addr.sin_addr.s_addr);
if(ret != 1)
std_err("inet_pton");

//链接服务器
ret = connect(cfd, (struct sockaddr*)&clie_addr, sizeof(clie_addr));
if(ret == -1)
std_err("connect");
char buff[256];
int nRecv=recv(cfd,buff,256,0);
if(nRecv>0)
{
buff[nRecv]='\0';
printf("当前时间:%s\n",buff);
}
}
//关闭套节字
close(cfd);
return 0;
}


代码中出现的问题

问题1



解决过程:记得要加上-lpthread参数,这样编译就可以顺利通过了。lpthread是表示要连接到pthread的库是这里省略的lib,你应该可以找到共享库libpthread.so的。





这样就可以编译成功了!

问题2



连接不上?不知道为什么?正在解决中。。。。
内容来自用户分享和网络整理,不保证内容的准确性,如有侵权内容,可联系管理员处理 点击这里给我发消息
标签: 
相关文章推荐