⭐ 欢迎来到虫虫下载站! | 📦 资源下载 📁 资源专辑 ℹ️ 关于我们
⭐ 虫虫下载站

📄 test2.cpp

📁 在Linux Red Hat下用C++设计并实现一个多用户多级目录结构的文件系统。
💻 CPP
📖 第 1 页 / 共 4 页
字号:
#include<sys/types.h>
#include<sys/stat.h>
#include<fcntl.h>
#include<unistd.h>
#include<iostream.h>
#include<string.h>
#include<iomanip.h>
block::block()
{
	char buf[bsize+1];
	if(vp==-1)		//当文件卷未建立时,创建新的文件卷,并将大小定在1M
	{
		vp=open("myfile",O_RDWR|O_CREAT,S_IRWXU|S_IRGRP|S_IXGRP|S_IROTH|S_IXOTH);
		lseek(vp,bsize*2047,0);
		write(vp,buf,512);
	}
	if(bread(0,buf)==BLKREADERR)	//读取的0#块的信息
	{
		cout<<"BLOCK READ ERROR"<<endl;
		return;
	}
	if((int)buf[477]!=1)			//0#的479字节非1,即系统第一次登陆
	{
		//将0#的前479个字节存放名为icon.gif的图标
		int iflag=open("icon.gif",O_RDWR,S_IRWXU|S_IRGRP|S_IXGRP|S_IROTH|S_IXOTH);
		if(iflag!=-1)
		{
			char picture[318];
			lseek(iflag,0,0);
			read(iflag,picture,359);
			lseek(vp,0,0);
			write(vp,picture,359);
		}
		//初始化空闲块链,并存储在1#~8#块中
		unsigned short int k=1;
		unsigned short int byteno=0;
		for(unsigned short int freeblockno=9;freeblockno<2048;)
		{
			if(byteno%512==510)
			{
				buf[byteno%512]=char((k+1)/256);
				byteno++;
				buf[byteno%512]=char((k+1)%256);
				byteno++;
				buf[512]='\0';
				if(bwrite(k,buf)==BLKWRITEERR)
				{
					cout<<"BLOCK WRITE ERROR"<<endl;
					return;
				}
				k++;
			}
			else
			{
				buf[byteno%512]=char(freeblockno/256);
				byteno++;
				buf[byteno%512]=char(freeblockno%256);
				byteno++;
				freeblockno++;
			}
		}
		for(;;)
		{
			buf[byteno%512]=char(0/256);
			byteno++;
			buf[byteno%512]=char(0%256);
			if(byteno%512==511)
			{
				buf[512]='\0';
				if(bwrite(k,buf)==BLKWRITEERR)
				{
					cout<<"BLOCK WRITE ERROR"<<endl;
					return;
				}
				break;
			}
			byteno++;
		}
		bread(0,buf);
		buf[477]=(char)1;
		buf[478]=(char)(1/256);
		buf[479]=char(1%256);
		bwrite(0,buf);
	}
	point=-1;
}
//读指定的物理块的信息
int block::bread(int bno,char*buf)
{
    int nbyte;
    lseek(vp,bno*bsize,0);
    nbyte=read(vp,buf,bsize);
    if(nbyte!=bsize)
		return BLKREADERR;	//失败;
	else
    {
		buf[bsize]='\0';
		return nbyte;		//成功
    }
}
//将信息写到指定的物理块
int block::bwrite(int bno,char*buf)
{
	int nbyte;
    lseek(vp,bno*bsize,0);
    nbyte=write(vp,buf,bsize);
    if(nbyte!=bsize)
		return BLKWRITEERR;	//失败 
    else
		return nbyte;			//成功 
}
//分配块
int block::balloc()
{
	char buf[bsize+1];
	if(point==-1)
	{
		bread(0,buf);
		int phead=int((unsigned char)buf[478])*256+int((unsigned char)buf[479]);
		if(phead==0)
		{
			cout<<"NO SPACE!please exit the programme"<<endl;
			return NOSPACE;
		}
		if(bread(phead,buf)==BLKREADERR)
		{
			cout<<"BLOCK READ ERROR"<<endl;
			return BLOCKERR;
		}
		for(int num=0;num<256;num++)
		{
			freeblock[num]=int((unsigned char)buf[num*2])*256+int((unsigned char)buf[num*2+1]);
		}
		point=0;
		for(;;point++)
		{
			if(freeblock[point%256]==0)
				continue;
			else
				break;
		}
		return phead;
	}
	if(point%256==255&&freeblock[point%256]==0)  //到达空闲块号链的尾部,并且空闲块号栈中的空闲块号也用完
	{
		cout<<"not enough space\n";
		return NOSPACE;	//空间不足
	}
	else
		if(point%256==255)	//空闲块号栈中无空闲块
		{
			//从物理块中读出新的信息,并放到空闲块号栈中
			if(bread(freeblock[255],buf)==BLKREADERR)
			{
				cout<<"BLOCK READ ERROR\n";
				return BLOCKERR;
			}
			int temp=freeblock[255];
			for(int num=0;num<256;num++)
			{
				freeblock[num]=int((unsigned char)buf[num*2])*256+int((unsigned char)buf[num*2+1]);
			}
			point++;
			for(;;point++)
			{
				if(freeblock[point%256]==0)
					continue;
				else
					break;
			}
			return temp;
		}
	for(;;point++)  //分配空闲块,
	{
		if(freeblock[point%256]==0)
		{
			if(point%256==255)
			{
				cout<<"not enough space\n";
				return NOSPACE;
			}
			else
				continue;
		}
		point++;
		return freeblock[(point-1)%256];
	}
}
//回收空闲块
int block::brelse(int tofree)
{
 
	char buf[bsize+1];
	if(point==-1)
	{
		bread(0,buf);
		int phead=int((unsigned char)buf[478])*256+int((unsigned char)buf[479]);
		if(phead==0)
		{
			cout<<"NO SPACE!please exit the programme"<<endl;
			return NOSPACE;
		}
		if(bread(phead,buf)==BLKREADERR)
		{
			cout<<"BLOCK READ ERROR"<<endl;
			return BLOCKERR;
		}
		for(int num=0;num<256;num++)
		{
			freeblock[num]=int((unsigned char)buf[num*2])*256+int((unsigned char)buf[num*2+1]);
		}
		point=0;
		for(;;point++)
		{
			if(freeblock[point%256]==0)
				continue;
			else
				break;
		}
		return brelse(phead);
	}
	if(point%256==0)  //空闲块栈满,则将该栈中的信息存储到物理块中
	{
		char buf[bsize+1];
		for(int ppoint=0;ppoint<256;ppoint++)
		{
			buf[ppoint*2]=(char)(freeblock[ppoint]/256);
			buf[ppoint*2+1]=(char)(freeblock[ppoint]%256);
		}
		buf[512]='\0';
		if(bwrite(tofree,buf)==BLKWRITEERR)
		{
			cout<<"BLOCK WRITE ERROR\n";
			return BLOCKERR;
		}
		point--;
		freeblock[point%256]=tofree;
		return tofree;
	}
	else  //未满,则分配空闲块
	{
		point--;
		freeblock[point%256]=tofree;
		return tofree;
	}    
}
block::~block()
{
	//将空闲块栈,用0填充满,再将其信息存储到物理块中
	if(point!=-1)
	{
		char buf[bsize+1];
		if(point%256==255&&freeblock[point%256]==0)
		{
			bread(0,buf);
			buf[478]=char(0/256);
			buf[479]=char(0%256);
			bwrite(0,buf);
			return;
		}    
		int one=balloc();
		if(point%256!=0)
		{
			point--;
			for(;;point--)
			{
				if(point%256==255||point==-1)
					break;
				freeblock[point%256]=0;
			}
		}
		for(int ppoint=0;ppoint<256;ppoint++)
		{
			buf[ppoint*2]=(char)(freeblock[ppoint]/256);
			buf[ppoint*2+1]=(char)(freeblock[ppoint]%256);
		}
		buf[512]='\0';
		if(bwrite(one,buf)==BLKWRITEERR)
		{
			cout<<"BLOCK WRITE ERROR\n";
			return;
		}
		bread(0,buf);
		buf[478]=char(one/256);
		buf[479]=char(one%256);
		bwrite(0,buf);
	}
}


#define bsize 512     //块大小
#define blkmax 2048   //块数目
class block           //第一层,块管理层 
{
public:
	block();
	int bread(int bno,char*buf);//读取一块
	int bwrite(int bno,char*buf);//写一块
	int balloc();		//块分配
	int brelse(int tofree);//块释放
	~block();   
private:
	unsigned short int freeblock[256];//空闲块号栈
	int point;			//空闲块号栈指针
};

#define NOSPACE 00		//空间不足
#define BLOCKERR 01		//块错误
//BLOCK
#define BLKREADERR 002	//块读错误
#define BLKWRITEERR 003	//块写错误
//FCB
#define FCBREADERR -1	//FCB读错误
#define FCBWRITEERR -2	//FCB写错误
#define ERROR 0003;		//一般的错误
#define OK -4;			//正常

ifcb::ifcb()
{
//初始化curfp,iadd[],fcbnum
	curfp=NULL;
	for(int i=0;i<fcbmax;i++)
	{
		fcbi[i]=NULL;
	}
	for(int k=0;k<256;k++)
	{
		iadd[k]=0;
	}
	fcbnum=0;
}
ifcb::~ifcb()
{
//存储iadd[]以及fcbi[]中的信息
	if(curfp!=NULL)
		putiadd(curfp);
	for(int f=0;f<16;f++)
	{
		if(fcbi[f]!=NULL)
			iput(fcbi[f]);
	}
}
int ifcb::getiadd(fcb *fp)
{
//读出指定fcb的一级间接寻址的信息
	if(fp==NULL)
		return OK;
	if(fp->f_add[8]==0)
	{
		for(int i=0;i<256;i++)
		{
			iadd[i]=0;
		}
		return OK;
	}
	else
	{
		char buf[bsize+1];
		if(iblock.bread(fp->f_add[8],buf)==BLKREADERR)
		{
			cout<<"GET IADD ERROR\n";
			return BLKREADERR;
		}
		for(int num=0;num<256;num++)
		{
			iadd[num]=int((unsigned char)buf[num*2])*256+int((unsigned char)buf[num*2+1]);
		}
		return OK;
	}
}
int ifcb::putiadd(fcb *fp)
{
//存储iadd[]中的内容
	if(fp==NULL)
		return OK;
	if(fp->f_add[8]==0)
		return OK;
	else
	{
		char buf[bsize+1];
		for(int num=0;num<256;num++)
		{
			buf[num*2]=char(iadd[num]/256);
			buf[num*2+1]=char(iadd[num]%256);
		}
		buf[512]='\0';
		if(iblock.bwrite(fp->f_add[8],buf)==BLKWRITEERR)
		{
			cout<<"PUT IADD ERROR\n";
			return BLKWRITEERR;
		}
		return OK;
	}
}
int ifcb::addblock(fcb *fp,int pblock)
{
//增加空闲块到指定的FCB的空间里
	int i=0;
	for(;i<263;i++)
	{
		if(getblock(fp,i)==0)
			break;
	}
	if(i>=263)
	{
		cout<<"ADD BLOCK ERROR\n";
		return ERROR;
	}
	if(i<8)
	{
		fp->f_add[i]=pblock;
		return OK;
	}
	else
	{
		if(i==8)
		{
			char buf[bsize+1];
			for(int j=0;j<512;j++)
			{
				buf[j]=(char)0;
			}
			buf[512]='\0';
			buf[0]=char(pblock/256);
			buf[1]=char(pblock%256);
			int blkno=iblock.balloc();
			if(blkno==NOSPACE||blkno==BLOCKERR)
			{
				cout<<"ADD BLOCK ERROR\n";
				return blkno;
			}
			if(iblock.bwrite(blkno,buf)==BLKWRITEERR)
			{
				cout<<"ADD BLOCK ERROR\n";
				return BLKWRITEERR;
			}
			fp->f_add[8]=blkno;
			iadd[0]=pblock;
			for(int t=1;t<256;t++)
			{ 
				iadd[t]=0;
			}
			curfp=fp;
			return OK;
		}
		else
		{
			if(i>8)
			{  
				iadd[i-8]=pblock;
				return OK;
			}
		}
	}
}
int ifcb::getblock(fcb *fp,int lblock)
{
//得到指定FCB空间的指定逻辑块对应的物理块
	if(lblock<8&&lblock>=0)
		return fp->f_add[lblock];
	else
	{
		if(lblock>=8)
		{
			if(fp->f_add[8]==0)
				return 0;
			else
			{
				if(fp!=curfp)
				{
					if(curfp!=NULL)
						putiadd(curfp);
					getiadd(fp);
					curfp=fp;
				}
				return iadd[lblock-8];
			} 
		}
	}
}
int ifcb::readi(fcb *fp,int offset,int count,char*base)
{

⌨️ 快捷键说明

复制代码 Ctrl + C
搜索代码 Ctrl + F
全屏模式 F11
切换主题 Ctrl + Shift + D
显示快捷键 ?
增大字号 Ctrl + =
减小字号 Ctrl + -