服务端编程思路:
1、先完成网络编程下的服务端,形成框架
2、api理解:
A、strtok:用于cd put get 函数获取文件名;
#include <string.h>
char* getDesDir(char* cmd)
{
char* p=NULL;
p=strtok(cmd," ");
p=strtok(NULL," ");
return p;
}
B、popen: FILE *popen(const char *command, const char *type);
int pclose(FILE *stream);要用pclose来关闭。
FILE* fp;
char ret[1024]={0};
fp=popen("ps","r");
int n_read=fread(ret,1,1024,fp);
printf("byte:%d ret=%s\n",n_read,ret);
return 0;
C、int chdir(const char *path);
int fchdir(int fd);
chdir()将调用进程的当前工作目录更改为路径中指定的目录。
D、int access(const char *pathname, int mode);//测试文件是否存在:
if(access(file,F_OK) == -1){
strcpy(msg.cmd,"NO THIS FILE");
write(fd,&msg,sizeof(msg));
}
3、利用strcmp和strstr封装一个得到类型的函数
int get_cmd_type(char*cmd)
{
if(!strcmp(cmd,"ls")) return LS;
if(!strcmp(cmd,"pwd")) return PWD;
if(!strcmp(cmd,"quit")) return QUIT;
if(strstr(cmd,"cd")!=NULL) return CD;
if(strstr(cmd,"get")!=NULL) return GET;
if(strstr(cmd,"put")!=NULL) return PUT;
return 24;
}
4、完成数据处理函数封装:
switch(ret){
case LS:
case PWD:
msg.type=0;
FILE* fp=popen(msg.cmd,"r");
memset(msg.cmd,0,sizeof(msg.cmd));
fread(msg.cmd,sizeof(msg.cmd),1,fp);
write(fd,&msg,sizeof(msg));
pclose(fp);
break;
case CD:
msg.type=1;
char* dir=getDesDir(msg.cmd);
printf("dir:%s\n",dir);
chdir(dir);
break;
case GET:
file=getDesDir(msg.cmd);
printf("file: %s\n",file);
if(access(file,F_OK) == -1){
strcpy(msg.cmd,"NO THIS FILE");
write(fd,&msg,sizeof(msg));
}
else{
msg.type=DOFILE;
file_fd=open(file,O_RDWR );
int N_read=read(file_fd,dataBuf,sizeof(dataBuf));
close(file_fd);
strcpy(msg.cmd,dataBuf);
int N_write=write(fd,&msg,sizeof(msg));
}
break;
case PUT:
file=getDesDir(msg.cmd);
printf("file: %s\n",file);
file_fd=open(file,O_RDWR|O_CREAT,0666 );
int N_write=write(file_fd,msg.secondBuf,sizeof(msg.secondBuf));
close(file_fd);
break;
case QUIT:
printf("Client quit!\n");
exit(0);
}