linux下文件二级系统设计
2015-07-13 23:23
477 查看
#include <iostream> #include <stdlib.h> #include<string.h> #include<curses.h> using namespace std; typedef struct User { string name[30]; string passwd[30]; int n; }User,u; typedef struct Priv { char read; char write; char execute; }Priv,priv[3]; typedef struct DataStock { int name; int stock_num; struct DataStock *next; }DataStock,*ds; typedef struct Inode { int inode_num; int type; float size; Priv *priv; char* owneruser; struct tm *createtime; struct Inode** childnode; struct DataStock *datastock; }Inode; typedef struct Dentry { string name; struct Inode *inode; }Dentry; int number = 1000; string rootDirect = "/home"; string currentUser=" "; string currentPath = rootDirect; User user; Dentry dentry[1000]; int of_record = 0; int record = -1; int disk_record = 0; int disk_stock = 3; string *disk =new string[number]; //模拟磁盘存储 int firstempty=0; int command_number = 10; int command_record=0; string *commandsave =new string[command_number]; int umask_direct = 775; int umask_file = 664; void test(){ for(int i =0;i<disk_record;i++) { cout<<disk[i]; } } void showDisk(){ for(int i =0;i<disk_record;i++) { cout<<"第"<<i<<"个磁盘块:"<<disk[i]<<endl; } } void output(){ cout<<"["<<currentUser<<"@"<<"localhost"<<currentPath<<"]#"; } //数据块节点初始化 DataStock *initializeStock() { DataStock *head; head = (DataStock*)malloc(sizeof(DataStock)); head->name = -1; head->next = NULL; return head; } //inode节点初始化 Inode *initializeInode(int type,string u,int p) { Inode *inode=NULL; inode = (Inode*)malloc(sizeof(Inode)); inode->childnode = (Inode**)malloc(100*sizeof(Inode*)); inode->inode_num = 0; inode->type = type; inode->datastock = initializeStock(); inode->size = 0; if(p==0) inode->owneruser = (char*)u.data(); else inode->owneruser = (char*)currentUser.data(); time_t ctime; time(&ctime); inode->createtime=localtime(&ctime); //权限初始化 Priv *priv = (Priv*)malloc(sizeof(Priv)); if(type==0) { priv[0].read='r';priv[0].write='w';priv[0].execute='-'; priv[1].read='r';priv[1].write='w';priv[1].execute='-'; priv[2].read='r';priv[2].write='-';priv[2].execute='-'; } else { priv[0].read='r';priv[0].write='w';priv[0].execute='x'; priv[1].read='r';priv[1].write='w';priv[1].execute='x'; priv[2].read='r'; priv[2].write='-'; priv[2].execute='-'; } inode->priv = priv; return inode; } //根据目录项名字找对应的目录项 Dentry findDentry(char *dentryname) { Dentry temp; for(int i = 0;i<=record;i++) { if(strcmp((char*)dentry[i].name.data(),dentryname)==0) { temp = dentry[i]; break; } } return temp; } //根据inode节点找相对应的目录项 Dentry searchDentry(Inode *inode){ Dentry temp; for(int i = 0;i<=record;i++) { if(dentry[i].inode==inode) { temp = dentry[i]; break; } } return temp; } //得到当前路径,如/home/root/sxw,最终返回结果为sxw int getEndPath(string endname) { int i = 0; for(i = endname.size();i>=0;i--) { if(endname[i]!='/') { continue; } break; } return (i+1); } int judge(string path) { int result = 0; int position = getEndPath(currentPath); char* dentryname = (char*)currentPath.substr(position,currentPath.size()).data(); Dentry parent_dt = findDentry(dentryname); Inode *parent_inode = parent_dt.inode; Inode *child_inode = NULL; Dentry child_dt; for(int i = 0;i<parent_inode->inode_num;i++) { if((child_inode=parent_inode->childnode[i])!=NULL) { child_dt = searchDentry(child_inode); if(child_dt.name==path) { if(child_dt.inode->type==0) { result = -1; } else { result = 1; break; } } } } return result; } void split(string command,string end[],char flag) { int count = 0; int j=0; for(int i=0;i<=command.size();i++) { if(command[i]==flag||i==command.size()){ end[j] = command.substr(count,i-count); count=i+1; j++; } } } void chagePriv(Inode *inode,string seond_result[],char f,int flag) { if(f=='+') { if(seond_result[1]=="r") inode->priv[flag].read='r'; else if(seond_result[1]=="w") inode->priv[flag].write='w'; else if(seond_result[1]=="x") inode->priv[flag].execute='x'; } else { if(seond_result[1]=="r") inode->priv[flag].read='-'; else if(seond_result[1]=="w") inode->priv[flag].write='-'; else if(seond_result[1]=="x") inode->priv[flag].execute='-'; } } void chomd(string command) { string result[3]; string seond_result[2]; split(command,result,' '); int results = judge(result[2]); if(results == 0) { cout<<"your input is not found!!"<<endl; return; } else { split(result[1],seond_result,result[1][1]); Dentry parent_dt = findDentry((char*)result[2].data()); Inode *inode = parent_dt.inode; if(strcmp((char*)currentUser.data(),inode->owneruser)==0||currentUser=="root") { if(seond_result[0]=="u") chagePriv(inode,seond_result,result[1][1],0); else if(seond_result[0]=="g") chagePriv(inode,seond_result,result[1][1],1); else if(seond_result[0]=="o") chagePriv(inode,seond_result,result[1][1],2); } else { cout<<"sorry,当前用户不允许授权!"<<endl; } } } //权限判断 bool isLeagl(string filename,int target,int flag) { if(currentUser=="root") return true; int user=0; char* dentryname; if(target==-1) { int position = getEndPath(currentPath); dentryname = (char*)currentPath.substr(position,currentPath.size()).data(); } else dentryname = (char*)filename.data(); Dentry dt = findDentry(dentryname); Inode *inode = dt.inode; if(strcmp((char*)currentUser.data(),inode->owneruser)!=0) { user = 2; } switch(flag) { case 0: if(inode->priv[user].read=='-') { cout<<"对不起,权限不够!"<<endl; return false; } break; case 1: if(inode->priv[user].write=='-') { cout<<"对不起,权限不够!"<<endl; return false; } break; case 2: if(inode->priv[user].execute=='-') { cout<<"对不起,权限不够!"<<endl; return false; } break; } return true; } //创建文件,目录 void createDirect(string directname,int type,int p){ Inode *inode = NULL; if(directname == "home") { inode = initializeInode(type,directname,p); record++; dentry[record].name = directname; dentry[record].inode = inode; } else{ if(isLeagl(directname,-1,1)) { int position = getEndPath(currentPath); char* dentryname = (char*)currentPath.substr(position,currentPath.size()).data(); Dentry dt = findDentry(dentryname); record++; Inode *temp = NULL; temp = initializeInode(type,directname,p); dt.inode->childnode[dt.inode->inode_num] = temp; dt.inode->inode_num++; dentry[record].name = directname; dentry[record].inode = temp; // test(); } else return; } } void readFile(string filename) { if(isLeagl(filename,1,0)) { int result = judge(filename); if(result == 1) { cout<<"your input is not file!!"<<endl; return; } else if(result == 0) { cout<<"your input is not found!!"<<endl; return; } else { Dentry dt = findDentry((char*)filename.data()); Inode *inode = dt.inode; DataStock *ds = inode->datastock; while(ds->next!=NULL) { DataStock *temp = ds->next; ds = temp; int name =temp->name; cout<<disk[name]; } } cout<<endl; } else return; } void writeFile(string filename) { if(isLeagl(filename,1,1)) { int result = judge(filename); if(result == 1) { cout<<"your input is not file!!"<<endl; return; } else if(result == 0) { cout<<"your input is not found!!"<<endl; return; } else { Dentry dt = findDentry((char*)filename.data()); Inode *inode = dt.inode; string content = " "; getline(cin,content); int size = content.size(); float stock_num = (size/disk_stock)+1; inode->size += size; DataStock *first = inode->datastock; while(first->next!=NULL) { first=first->next; } DataStock *head =first; int count = 0; for(int i = 0;i<number;i++) { if(i>=disk_record) disk_record++; if(disk[i]=="") { DataStock *temp = (DataStock*)malloc(sizeof(DataStock)); temp->name = i; temp->next=NULL; head->next=temp; head=temp; if(stock_num>1) { disk[i] = content.substr(count,disk_stock); stock_num--; count = disk_stock+count; } else { disk[i] = content.substr(count,content.size()); break; } } } //修改文件夹的大小 int position = getEndPath(currentPath); char* dentryname = (char*)currentPath.substr(position,currentPath.size()).data(); Dentry parent_dt = findDentry(dentryname); Inode *parent_inode = parent_dt.inode; parent_inode->size = 0; for(int i=0;i<parent_inode->inode_num;i++) { parent_inode->size += parent_inode->childnode[i]->size; } } // test(); } else return; } void moveInode(Inode *inode,int pos){ if(pos!=inode->inode_num-1) { for(;pos<inode->inode_num-1;pos++) { inode->childnode[pos] = inode->childnode[pos+1]; } inode->inode_num--; } else {inode->inode_num--;return;} return; } //删除文件,目录操作 void deleteDirect(string directname,int type){ if(isLeagl(directname,-1,1)) { int result = judge(directname); if(result == 0) { cout<<"your input is not found!!"<<endl; return; } else { int position = getEndPath(currentPath); char* dentryname = (char*)currentPath.substr(position,currentPath.size()).data(); Dentry parent_dt = findDentry(dentryname); Dentry current_dt = findDentry((char*)directname.data()); Inode *parent_inode = parent_dt.inode; Inode *current_inode = current_dt.inode; for(int i = 0;i<parent_inode->inode_num;i++) { if(parent_inode->childnode[i]==current_inode) { parent_inode->childnode[i] = NULL; moveInode(parent_inode,i); if(type==0) { DataStock *ds = current_inode->datastock; // free(current_inode); while(ds->next!=NULL) { DataStock *temp = ds->next; ds = temp; int name =temp->name; disk[name]=""; memset((char*)disk[name].data(),0,3); } } } } } // test(); } else return; } //实现ls命令操作列举出当前目录下的所有文件,目录的详细信息 void dir(){ int position = getEndPath(currentPath); char* dentryname = (char*)currentPath.substr(position,currentPath.size()).data(); Dentry parent_dt = findDentry(dentryname); Inode *parent_inode = parent_dt.inode; Inode *child_inode = NULL; Dentry child_dt; string file_type; for(int i = 0;i<parent_inode->inode_num;i++) { if((child_inode=parent_inode->childnode[i])!=NULL) { child_dt = searchDentry(child_inode); if(child_inode->type==0) file_type = "文件"; else if(child_inode->type==1) file_type = "目录"; cout<<file_type<<'\t'; for(int i=0;i<3;i++) { cout<<child_dt.inode->priv[i].read<<child_dt.inode->priv[i].write<<child_dt.inode->priv[i].execute<<'\t'; } cout<<child_dt.inode->owneruser<<'\t'<<child_dt.inode->size<<"字节"<<'\t'<<(child_dt.inode->createtime->tm_mon+1)<<"月"<<'\t'<< child_dt.inode->createtime->tm_mday<<'\t'<<child_dt.inode->createtime->tm_hour<<":"<<child_dt.inode->createtime->tm_min <<'\t'<<child_dt.name<<'\t'<<endl; } } } //string cinPasswd(){ // initscr(); // char ch; // string str=""; // while((ch=getchar())!='\r') // { // cout<<"*"; // str+= ch; // } // endwin(); // return str; //} //用户登录 void login(string username){ bool record = false; cout<<"input your passwd please!!"<<endl; output(); string temp; cin>>temp; for(int i = 0;i<user.n;i++){ if((user.name[i])==username){ if(user.passwd[i]==temp){ currentUser = username; record = true; cout<<username<<" login successfully!"<<endl; cin.ignore(); return; } } } if(!record) { cout<<"sorry!"<<" "<<username<<" "<<"not found"<<endl; } return; } void logout(string username){ currentUser = user.name[0]; cout<<"current user logout successfully!!"<<endl; } //实现在root用户下添加新用户 void addUser(string username){ if(currentUser!="root") { cout<<"sorry!current user is not root!!"<<endl; return; } else{ string passwd; cout<<"input your passwd please!!"<<endl; output(); cin>>passwd; user.name[user.n] = username; user.passwd[user.n] = passwd; user.n++; cout<<"add user successfully!!"<<endl; cin.ignore(); createDirect(username,1,0); return; } } //实现cd操作进入下个目录 void intoNext(string path){ if(path=="..") { int position = getEndPath(currentPath); currentPath = currentPath.substr(0,position-1); } else { int result = judge(path); if(result == -1) cout<<"sorry!your entry is not direct"<<endl; else if(result==1) currentPath = currentPath+"/"+path; else if(result == 0) cout<<"your entry is not found!"<<endl; } } void help(){ cout<<"ls 列举当前目录下所有目录项"<<endl; cout<<"pwd 显示当前目录结构 "<<endl; cout<<"adduser uu 添加新用户uu "<<endl; cout<<"login root root用户登录 "<<endl; cout<<"logout 当前用户登出 "<<endl; cout<<"create ss 创建文件ss "<<endl; cout<<"rm ss 删除文件ss "<<endl; cout<<"mkdir ss 创建目录ss "<<endl; cout<<"rmdir ss 删除目录ss "<<endl; cout<<"read ss 读文件ss "<<endl; cout<<"write ss 写文件ss "<<endl; cout<<"chmod o+w ss 给ss的other用户赋予写的权限 "<<endl; } void showWindow() { cout<<'\t'<<"***************************************************************"<<endl; cout<<'\t'<<"**"<<" "<<"**"<<endl; cout<<'\t'<<"**"<<" 操作系统文件系统设计 "<<"**"<<endl; cout<<'\t'<<"**"<<" "<<"**"<<endl; cout<<'\t'<<"**"<<" 1,实现文件,目录的创建,删除,读取,列举,授权等操作 "<<"**"<<endl; cout<<'\t'<<"**"<<" "<<"**"<<endl; cout<<'\t'<<"**"<<" 2.模拟linux下如cd,ls,pwd,adduser,chmod等基本命令 "<<"**"<<endl; cout<<'\t'<<"**"<<" "<<"**"<<endl; cout<<'\t'<<"**"<<" 3.文件存储使用内存模拟外存实现,具体操作请使用help命令查询 "<<"**"<<endl; cout<<'\t'<<"***************************************************************"<<endl; } //实现pwd操作,显示当前目录 void showPath(){ cout<<currentPath<<endl; } //程序启动时初始化root用户,创建home和root目录 void Initialize(){ user.name[0] = "root"; user.passwd[0] = "linux"; user.n++; currentUser = user.name[0]; createDirect("home",1,-1); createDirect("root",1,-1); } void saveCommand(string command){ if(command_record==number) { command_record=0; commandsave[command_record] = command; commandsave[command_record++]=""; } commandsave[command_record] = command; command_record++; } void Up_BackOpreation(string command) { if(command=="w") { if(command_record!=0) command_record--; else if(command_record==0&&commandsave[command_number]!="") command_record = command_number; } else if(command=="s") { if(commandsave[command_record+1]!="") command_record++; else if(command[command_record+1]==command_number) command_record=0;; } cout<<command[command_record]; } int commandSolve(string input){ string first =input.substr(0,input.find(" ")); string second =input.substr(input.find(" ")+1,input.size()); if(first=="create") createDirect(second,0,-1); else if(first=="mkdir") createDirect(second,1,-1); else if(first=="read") readFile(second); else if(first=="write") writeFile(second); else if(first=="rmdir") deleteDirect(second,1); else if(first=="rm") deleteDirect(second,0); else if(first=="chmod") chomd(input); else if(first=="login") login(second); else if(first=="logout") logout(currentUser); else if(first=="adduser") addUser(second); else if(first=="pwd") showPath(); else if(first=="cd") intoNext(second); else if(first=="ls") dir(); else if(first=="help") help(); else if(input=="showdisk") showDisk(); else if(input=="") return 0; else { cout<<"command error!"<<endl; } return 0; } int main() { showWindow(); Initialize(); string input = " "; while(true) { output(); getline(cin,input); commandSolve(input); } return 0; }
相关文章推荐
- linux 第一个hello world
- Linux crontab定时执行任务 命令格式
- Linux内核源码针对S3C2440的初步框架交叉编译过程分享
- 《coredump问题原理探究》Linux x86版7.9节list相关的iterator对象
- 每天一个linux命令(1):ls命令
- linux程序设计——命名管道FIFO(第十三章)
- 在虚拟机下安装Linux操作系统遇到的问题
- linux下压缩工具总结与使用(参考私房菜)
- CentOS 7 折腾小记
- 第二章、Linux操作系统及常用命令
- 七月十三日 Linux操作系统c语言学习笔记
- 马哥Linux笔记整理
- U盘安装linux(ubuntu)
- Linux Makefile学习(一)
- ffmpeg linux编译
- 在GNU/Linux下使用命令行自动挂载与卸载USB磁盘
- Linux操作杂记
- linux find命令小结
- linux yum命令详解
- CentOS yum 源的配置与使用