Beispiel #1
0
void init_filesystem( char * filesystem_name, masterBootRecord * mbr){
	
	/*mbr sector*/
	mbr->existFS = 1;
	write_disk(vDisk->disk, 0,mbr,BLOCK_SIZE,0);
	
	/* superBlock sector */
	superblock->name = "Chinux";
	superblock->blockSize = BLOCK_SIZE;
	superblock->freeBlocks = 10000;//TODO:PONER LA CANTIDAD POSTA.
	superblock->usedBlocks = 0;
	superblock->root = NULL; 
	write_disk(vDisk->disk,1,superblock,sizeof(masterBlock),0);

	/* bitmap Sectors */
	init_bitmap();
	
	/* inodemap Sectors */
 	init_inodemap();

	/* Root node & current node */
	
	init_root();
	write_disk(vDisk->disk,1,superblock,512,0);
	current = superblock->root;

	return;
}
Beispiel #2
0
int main(int argc, char *argv[])
{
  struct direct *sp;
  static char cwd[PATH_MAX];
  //if (sizeof(struct dinode) != 4096) {
	//  dprintf(2, "sizeof(struct dinode) %d != 4096\n", sizeof(struct dinode));
	//  return -1;
  //}
  
  if (argc != 3) { dprintf(2, "Usage: mkfs fs rootdir\n"); return -1; }
  if ((disk = open(argv[1], O_RDWR | O_CREAT | O_TRUNC)) < 0) {
    dprintf(2, "open(%s) failed\n", argv[1]); return -1; }
  if ((int)(sp = (struct direct *) sbrk(16*1024*1024)) == -1) { dprintf(2, "sbrk() failed\n"); return -1; }

  // write zero bitmap
  write_disk(buf, BUFSZ);
  
  // populate file system
  getcwd(cwd, sizeof(cwd));
  chdir(argv[2]);
  add_dir(bn = 16, sp);
  chdir(cwd);

  // update bitmap
  memset(buf, 0xff, bn / 8);
  if (bn & 7) buf[bn / 8] = (1 << (bn & 7)) - 1;
  lseek(disk, 0, SEEK_SET);
  write_disk(buf, (bn + 7) / 8);
  close(disk);
  return 0;
}
Beispiel #3
0
void write_meta(uint size, uint mode, uint nlink)
{
  uint i, b, dir, idir;
  struct dinode inode;
  static uint iblock[1024];

  // compute blocks, direct, and indirect
  b = (size + 4095) / 4096;
  dir = (b > NDIR) ? NDIR : b;
  idir = (b + 1023 - NDIR) / 1024;

  // write inode
  memset(&inode, 0, 4096);
  inode.mode = mode;
  inode.nlink = nlink;
  inode.size = size;
  bn++;
  for (i=0; i<dir;  i++) inode.dir[i] = bn + idir + i;
  for (i=0; i<idir; i++) inode.idir[i] = bn++;
  write_disk(&inode, 4096);

  // write indirect blocks
  b += bn;
  bn += dir;
  while (bn < b) {
	for (i=0; i<1024; i++) iblock[i] = (bn < b) ? bn++ : 0;
	write_disk(iblock, 4096);
  }
}
Beispiel #4
0
int recursive_remove(iNode * current) {

	int ret;

	if (current->gid < currentUsr.group)
		return 1;

	if (is_base_case(current)) //CASOBASE QUE ES QUE EL DIRECTORIO ESTE VACIO O SEA UN ARCHIVO)
		return 0;

	int init_block = current->data.direct_blocks[0];
	directoryEntry * dr = (directoryEntry*) calloc(sizeof(directoryEntry), 96);
	read_disk(0, init_block, dr, BLOCK_SIZE * 12, 0);
	int i;
	for (i = 2; i < 96; i++) {
		if (dr[i].type != 0) {
			ret = recursive_remove(fs_get_inode(dr[i].inode));
			if (!ret) {
				dr[i].type = 0;
				dr[i].inode = 0;
				dr[i].lenght = 0;
			}

		}
	}
	write_disk(0, init_block, dr, BLOCK_SIZE * 12, 0);

	return ret;
}
Beispiel #5
0
dataStream * fs_init_dataStream(int size, int id, int number, iNode * current){
	
	dataStream * ret = (dataStream *)malloc(sizeof(dataStream));
	int quantityBlocks,freeblock,i;	
	directoryEntry * dr = (directoryEntry*)calloc(sizeof(directoryEntry),96);
 	directoryEntry dr1 = {DIRECTORY, number, 0, "."};
	directoryEntry dr2 = {DIRECTORY, number,0,".."};
	if ( current != NULL ){
		dr2.inode = current->iNode_number;
	}
	
	dr[0] = dr1;
	dr[1] = dr2;

	if ( id == DIRECTORY ){
		quantityBlocks = 12;
		freeblock = search_free_blocks(quantityBlocks);
		for (i=0;i<12;i++){
			ret->direct_blocks[i] = freeblock + (i);//Para aumentar esto hay uqe multiplicarlo			
		}
		write_disk(vDisk->disk,ret->direct_blocks[0],dr,BLOCK_SIZE*12,0);
	}else{
		quantityBlocks = (int)(size/BLOCK_SIZE) + 1;
		freeblock = search_free_blocks(quantityBlocks);
		if ( freeblock != -1){
			ret->direct_blocks[0] = freeblock;
			ret->direct_blocks[1] = quantityBlocks;
		}else{
			printf("FAIL: NO ENCONTRE MEMORIA LIBRE\n");
			//TODO: Implementar una seccion donde se maneje si no encuentra archiva.		
		}
	}

	return ret;
}
Beispiel #6
0
dataStream * fs_init_dataStream(int size, int id, int number, iNode * current) {

	dataStream * ret = (dataStream *) malloc(sizeof(dataStream));
	int quantityBlocks, freeblock, i;
	directoryEntry * dr = (directoryEntry*) calloc(sizeof(directoryEntry), 96);
	directoryEntry dr1 = { DIRECTORY, number, 0, "." };
	directoryEntry dr2 = { DIRECTORY, number, 0, ".." };
	if (current != NULL) {
		dr2.inode = current->iNode_number;
	}

	dr[0] = dr1;
	dr[1] = dr2;

	if (id == DIRECTORY) {
		quantityBlocks = 12;
		freeblock = search_free_blocks(quantityBlocks);
		for (i = 0; i < 12; i++) {
			ret->direct_blocks[i] = freeblock + (i); //Para aumentar esto hay uqe multiplicarlo
		}
		write_disk(0, ret->direct_blocks[0], dr, BLOCK_SIZE * 12, 0);
	} else {
		quantityBlocks = (int) (size / BLOCK_SIZE) + 1;
		freeblock = search_free_blocks(quantityBlocks);
		if (freeblock != -1) {
			ret->direct_blocks[0] = freeblock;
			ret->direct_blocks[1] = quantityBlocks;
		} else {
			printf("FAIL: not enoguht memory\n");
		}
	}
	return ret;
}
Beispiel #7
0
uint32_t apply_block()
{
	int i, j;
	static int cur_st = 0;
	while(cur_st < BITMAP_SZ / sizeof(uint32_t))
	{
		for(i = 0; i < sizeof(bitmap)/sizeof(uint32_t); i++)
		{
			if(bitmap[i] != 0xffffffff)
			{
				for(j = 31; j >= 0; j--)
				{
					if((1 & (bitmap[i] >> j)) == 0)
					{
						uint32_t mask = 1 << j;
						bitmap[i] |= mask;
						return cur_st * 32 + i * 32 + (31 - j);
					}
				}
			}
		}
		write_disk(bitmap, BITMAP_ST + cur_st * sizeof(uint32_t), sizeof(bitmap));
		cur_st += sizeof(bitmap)/sizeof(uint32_t);
		read_disk(bitmap, BITMAP_ST + cur_st * sizeof(uint32_t), sizeof(bitmap));
	}
	assert(0);
	return 0xffffffff;
}
Beispiel #8
0
void close_inode(INODE *pinode)
{
	int i = (int)(pinode - &inode[0]);
	write_disk(&inode[i], INODE_ST + pinode->inodeno * sizeof(INODE), sizeof(INODE));
	inode_dirty[i] = 0;
	return;
}
Beispiel #9
0
void init_filesystem(char * filesystem_name, masterBootRecord * mbr) {

	/*mbr sector*/
	int fd;

	user * users = calloc(sizeof(user), 100);

	memcpy(users[0].name, "chinux", str_len("chinux"));
	memcpy(users[0].password, "chinux", str_len("chinux"));
	users[0].usrID = 1;
	users[0].group = ADMIN;
	mbr->existFS = 1;

	write_disk(0, MBRSECTOR, mbr, BLOCK_SIZE, 0); //BLOCK_SIZE

	/* superBlock sector */
	superblock->name = "Chinux";
	superblock->blockSize = BLOCK_SIZE;
	superblock->freeBlocks = DISK_SIZE / BLOCK_SIZE;
	superblock->usedBlocks = 0;
	superblock->root = NULL;
	write_disk(0, SUPERBLOCKSECTOR, superblock, BLOCK_SIZE, 0);

	/* bitmap Sectors */
	init_bitmap();

	/* inodemap Sectors */
	init_inodemap();

	/* Root node & current node */

	init_root();

	write_disk(0, 1, superblock, BLOCK_SIZE, 0);

	current = superblock->root;

	makeDir("users");
	makeDir("etc");

	fd = do_creat("usersfile", 777);
	write(fd, (char *) users, sizeof(user) * 100);
	close(fd);

	return;
}
Beispiel #10
0
void init_bitmap(){
	
	int i;
	clear_all(BITMAP);
	
	for(i=0;i<HEADER_BLOCKS;i++){
		set_bit(i,BITMAP);
	}
	
	write_disk(vDisk->disk,2,bitmap->data,BITMAP_SIZE,0);
	return;
}
Beispiel #11
0
/**********************************************
Starting point of the whole OS
*************************************************/
int
kmain()
{
	int i, h;
	char * buffer = calloc(512 , 1);
	_Cli();
	k_clear_screen();
	printf("screen clear\n");
	//cache_initarray();
	printf("array init\n");
	//cache_sortarray();
	printf("array sort\n");

	initializeSemaphoreTable();
	printf("semaphore init\n");
	initializeIDT();
	unmaskPICS();
	initializePaging();
	_StartCR3();
	SetupScheduler();
	//printf("after SetupScheduler\n");

	for(h = 0; h < 200; h++){
		write_disk(0,h,buffer,BLOCK_SIZE,0);
	}

	fd_table = (filedescriptor *)calloc(100,1);
	masterBootRecord * mbr = (masterBootRecord *)malloc(512);
	superblock = (masterBlock*)malloc(512);		
	bitmap = (BM*)calloc(BITMAP_SIZE,1);	
	inodemap = (IM*)calloc(INODEMAP_SIZE,1);
	
	read_disk(0,0,mbr,BLOCK_SIZE,0);

	if ( mbr->existFS == 0 ){
		init_filesystem("Chinux", mbr);
	}else{
		load_filesystem();
	}
	
	ready = NULL;
	for(i = 0; i < 4; i++)
		startTerminal(i);

	//free(mbr);
	logPID = CreateProcessAt("Login", (int(*)(int, char**))logUser, 0, 0, (char**)0, PAGE_SIZE, 4, 1);
	_Sti();

	while(TRUE)
	;
	return 1;
}
Beispiel #12
0
void rename_file(int iNode_number, char * new_name)
{
	int i, init_block = current->data.direct_blocks[0];
	directoryEntry * dr = (directoryEntry*)calloc(sizeof(directoryEntry), 96);
	read_disk(0, init_block, dr, BLOCK_SIZE * 12, 0);
	for (i = 0; i < 96; i++){
		if ( dr[i].inode == iNode_number){
			memcpy(dr[i].name, new_name, str_len(new_name));
			break;
		}
	}
	write_disk(0, init_block, dr, BLOCK_SIZE * 12, 0);

	return;
}
Beispiel #13
0
int fs_insert_inode(iNode * node) {

	int number = node->iNode_number;
	int sector = number / 4;
	int offset = number % 4;
	void * receive = (void *) malloc(BLOCK_SIZE);

	if (get_bit(number, INODEMAP) == 0) {
		set_bit(number, INODEMAP);
	}

	read_disk(0, INODETABLESECTOR + sector, receive, BLOCK_SIZE, 0);
	memcpy(receive + (128 * offset), node, 128); //+(128*offset)
	write_disk(0, INODETABLESECTOR + sector, receive, BLOCK_SIZE, 0);

	return number;
}
Beispiel #14
0
void insert_directory_entry(iNode * newDirectory, iNode * current, char * name){
	int init_block = current->data.direct_blocks[0];
	directoryEntry * dr = (directoryEntry*)calloc(sizeof(directoryEntry),96);
	read_disk(vDisk->disk,init_block,dr,BLOCK_SIZE*12,0);
	int i;
	for ( i = 0; i < 96; i++){
		if ( dr[i].type == 0 ){
			dr[i].type = DIRECTORY;
			dr[i].inode = newDirectory->iNode_number;
			dr[i].lenght = 0;
			memcpy(dr[i].name,name,strlen(name));
			break;
		}
	}
	write_disk(vDisk->disk,init_block,dr,BLOCK_SIZE*12,0);

	return;
	
}
Beispiel #15
0
 uint32_t TestPeripheral::send_command(uint32_t command)
 {
     switch (command)
     {
         default:
         case UNKNOWN:
             std::cout << "Unknown test peripheral command: " << command << "\n";
             return -1;
         case MEMORY_REQUEST:
             return 32;
         case STATUS:
             uint_data(0, 1);
             return 0;
         case READ:
             return read_disk();
         case WRITE:
             return write_disk();
     }
     return 0;
 }
Beispiel #16
0
void recursive_cp(char * filename, iNode * origin, iNode * destination)
{
	int i;
	iNode * path;

	if(origin->gid < currentUsr.group)
		return ;

	cp_dir(filename, destination);

	//get new path
	int init_block = destination->data.direct_blocks[0];
	directoryEntry * dr = (directoryEntry*)calloc(64 * 96, 1);
	read_disk(0, init_block, dr, (BLOCK_SIZE * 12), 0);
	for(i = 2; i < 96; i++){
		if( strcmp(filename, dr[i].name)){
			path = fs_get_inode(dr[i].inode);
			break;
		}
	}

	//search for files and folders
	init_block = origin->data.direct_blocks[0];
	dr = (directoryEntry*)calloc(sizeof(directoryEntry), 96);
	read_disk(0, init_block, dr, BLOCK_SIZE * 12, 0);
	for ( i = 2; i < 96; i++)
	{
		if (dr[i].type == FILE)
		{
			cp_file(dr[i].name, origin, path);
		}
		else if(dr[i].type == DIRECTORY)
		{
			recursive_cp(dr[i].name, fs_get_inode(dr[i].inode), path);
		}
	}
	write_disk(0, init_block, dr, BLOCK_SIZE * 12, 0);

	return ;
}
Beispiel #17
0
int search_free_blocks(int quantityBlocks) {

	int i;
	int count = 0;
	int candidate = -1;
	if (superblock->freeBlocks < 100) {
		return NO_SPACE;
	}

	for (i = 0; i < (BITMAP_SIZE) && count < quantityBlocks; i++) {

		if (candidate == -1 && get_bit(i, BITMAP) == FREE) {
			candidate = i;
		}
		if (get_bit(i, BITMAP) == FREE) {
			count++;
		} else {
			count = 0;
			candidate = -1;
		}
	}

	if (candidate == -1) {
		return -1;
	}
	//If the candidate is OK, proceed tu fullfill the array of bits. 
	for (i = candidate; i < (candidate + quantityBlocks); i++) {
		set_bit(i, BITMAP);
	}

	superblock->freeBlocks = superblock->freeBlocks - quantityBlocks;
	superblock->usedBlocks = superblock->usedBlocks + quantityBlocks;

	//printf("Cantidad de bloques libres:%d\n",superblock->freeBlocks);

	write_disk(0, BITMAPSECTOR, bitmap, BITMAP_SIZE, 0);

	return candidate;

}
Beispiel #18
0
int fs_insert_inode(iNode * node){
	
	int number = node->iNode_number;
	int sector = number/4;
	int offset = number%4;
	iNode * node2 = malloc(sizeof(iNode));
	void * recieve = malloc(BLOCK_SIZE);
	void * recieve2 = malloc(BLOCK_SIZE);
	
	if ( get_bit(number, INODEMAP) == 0 ){
		set_bit(number,INODEMAP);	
	}

	recieve = read_disk(vDisk->disk,INODETABLESECTOR+sector,recieve, BLOCK_SIZE,0);
	memcpy(recieve+(128*offset),node,128);//+(128*offset)
	write_disk(vDisk->disk,INODETABLESECTOR+sector,recieve,BLOCK_SIZE,0);
	
	//recieve2 = read_disk(vDisk->disk,INODETABLESECTOR+sector,recieve2, BLOCK_SIZE,0);
	//memcpy(node2,recieve2,128);

	return number;
}
Beispiel #19
0
int write_inode(iNode * inode, char * buf, int n) {

	int file_size = inode->size;
	int posible_requeried = (int) ((file_size + n) / BLOCK_SIZE) + 1;
	int newrequeried_blocks, freeblock;
	if (posible_requeried > inode->data.direct_blocks[1]) {
		newrequeried_blocks = posible_requeried;
		freeblock = search_free_blocks(newrequeried_blocks);
	} else {
		freeblock = inode->data.direct_blocks[0];
		newrequeried_blocks = inode->data.direct_blocks[1];
	}

	int i, lastblock;
	int init_block = inode->data.direct_blocks[0];
	int quantity = inode->data.direct_blocks[1];

	if (freeblock != -1) {
		char * buffer = (char *) malloc(quantity * 512);
		char * insert_buffer = (char *) malloc(newrequeried_blocks * 512);
		read_disk(0, init_block, buffer, quantity * BLOCK_SIZE,0);

		memcpy(insert_buffer, buffer, quantity * 512);
		memcpy((insert_buffer + file_size), buf,n);
		write_disk(0, freeblock, insert_buffer, (newrequeried_blocks * 512), 0);

		inode->data.direct_blocks[0] = freeblock;
		inode->data.direct_blocks[1] = newrequeried_blocks;
		inode->size = file_size + n;

		free_used_blocks(init_block, quantity, BITMAP);

		fs_insert_inode(inode);
	}

	return n;
}
Beispiel #20
0
void init_inodemap(){
	
	clear_all(INODEMAP);
	set_bit(0,INODEMAP);
	write_disk(vDisk->disk,6,bitmap->data,INODEMAP_SIZE,0);
}
Beispiel #21
0
int fs_write(INODE *pinode, uint32_t off, uint32_t size, void *buf)
{
	buf = (uint8_t *)buf;
	int i, j, tsize, ed = off + size;
	uint32_t block_addr[64];
	if(off > pinode->filesz || size == 0)
		return 0;

	if(off < pinode->filesz)
	{
		/* write the part haven't exceed the file end
		 * write scale [off, min(filesz, off + size)
		 */
		uint32_t stblockno, edblockno;
		uint32_t preved = min(off + size, pinode->filesz);
		uint32_t stno = off / BLOCKSZ, edno = (preved - 1) / BLOCKSZ;
		/* write the first block */
		tsize = min(BLOCKSZ - off % BLOCKSZ, size);
		get_disk_blockno(pinode, stno, 1, &stblockno);
		write_disk(buf, FILE_ST + stblockno * BLOCKSZ + off % BLOCKSZ, tsize);
		buf += tsize;
		off += tsize;
		size -= tsize;
		for(i = stno + 1; i < edno; i += 64)
		{
			int t = get_disk_blockno(pinode, i, min(i + 64, edno - i), block_addr);
			for(j = 0; j < t; j++)
			{
				write_disk(buf, FILE_ST + block_addr[j] * BLOCKSZ, BLOCKSZ);
				buf += BLOCKSZ;
				off += BLOCKSZ;
				size -= BLOCKSZ;
			}
		}
		
		/* write the last block */
		tsize = preved - off;
		get_disk_blockno(pinode, edno, 1, &edblockno);
		write_disk(buf, FILE_ST + edblockno * BLOCKSZ + off % BLOCKSZ, tsize);
		buf += tsize;
		off += tsize;
		size -= tsize;
	}
	if(ed > pinode->filesz)
	{
		/* write the part which need to apply new block
		 * write scale [off, ed)
		 */

		off = pinode->filesz;
		uint32_t stblockno, edblockno;
		uint32_t stno = off / BLOCKSZ, edno = (ed - 1) / BLOCKSZ;
		/* alloc block for file */
		for(i = stno; i <= edno; i += 64)
			alloc_disk_blockno(pinode, i, min(64, edno - i + 1));
		/* write the first block */
		tsize = min(BLOCKSZ - off % BLOCKSZ, size);

		get_disk_blockno(pinode, stno, 1, &stblockno);
		write_disk(buf, FILE_ST + stblockno * BLOCKSZ + off % BLOCKSZ, tsize);
		buf += tsize;
		off += tsize;
		size -= tsize;
		for(i = stno + 1; i < edno; i += 64)
		{
			int t = get_disk_blockno(pinode, i, min(64, edno - i), block_addr);
			for(j = 0; j < t; j++)
			{
				write_disk(buf, FILE_ST + block_addr[j] * BLOCKSZ, BLOCKSZ);
				buf += BLOCKSZ;
				off += BLOCKSZ;
				size -= BLOCKSZ;
			}
		}
		
		/* write the last block */
		tsize = ed - off;
		get_disk_blockno(pinode, edno, 1, &edblockno);
		write_disk(buf, FILE_ST + edblockno * BLOCKSZ + off % BLOCKSZ, tsize);
		buf += tsize;
		off += tsize;
		size -= tsize;
	}

	pinode->filesz = max(pinode->filesz, ed);
	
	return size;
}
Beispiel #22
0
int alloc_disk_blockno(INODE *pinode, uint32_t file_blockst, uint32_t nr_block)
{
	int i, count = 0;
	int level[128] = {0};
	uint32_t addr[128] = {0}, stno[128] = {0};
	uint32_t p = 0, q = 0;
	uint32_t ll[4] = {L1_ST, L2_ST, L3_ST, L4_ST};
	uint32_t lp[4] = {1, L2_ST - L1_ST, L3_ST - L2_ST, L4_ST - L3_ST};
	uint32_t tbuf[BLOCKSZ / sizeof(uint32_t)];

	if(nr_block > 64)
		return 0;

	for(i = 0; i < 10; i++)
		if(i >= file_blockst && i < file_blockst + nr_block)
		{
			level[q] = 0;
			stno[q] = i;
			if(pinode->nr_block[i] == INVALID_BLOCKNO)
				pinode->nr_block[i] = apply_block();
			addr[q++] = pinode->nr_block[i];
		}

	for(i = 0; i < 3; i++)
		if(max(ll[i], file_blockst) < min(ll[i + 1], file_blockst + nr_block))
		{
			level[q] = i + 1;
			stno[q] = ll[i];
			if(pinode->nr_block[10 + i] == INVALID_BLOCKNO)
			{
				pinode->nr_block[10 + i] = apply_block();
				clear_block(pinode->nr_block[10 + i]);
			}
			addr[q++] = pinode->nr_block[10 + i];
		}
	

	if(q == 0)
		return 0;

	while(p < q)
	{
		if(level[p] > 0)
		{
			uint32_t disk_off = FILE_ST + addr[p] * BLOCKSZ;
			read_disk(tbuf, disk_off, sizeof(tbuf));
			for(i = 0; i < sizeof(tbuf)/sizeof(uint32_t); i++)
			{
				level[q] = level[p] - 1;
				stno[q] = stno[p] + i * lp[level[q]];
				stno[q + 1] = stno[p] + (i + 1) * lp[level[q]];
	
				if(max(stno[q], file_blockst) < min(stno[q + 1], file_blockst + nr_block))
				{
					if(tbuf[i] == INVALID_BLOCKNO)
					{
						tbuf[i] = apply_block();
						if(level[q] > 0)
							clear_block(tbuf[i]);
					}
					addr[q] = tbuf[i];
					q++;
				}
			}
			p ++;
			write_disk(tbuf, disk_off, sizeof(tbuf));
			assert(p < 128 && q < 128);
		}
		else
		{
			assert(p < 128 && q < 128);
			count ++;
			if(count >= nr_block)
			{
				return count;
			}
			p++;
		}
	}
	printk("%d, %d, %d\n", file_blockst, nr_block, count);
	return count;
}
Beispiel #23
0
void clear_block(uint32_t blockno)
{
	char buf[BLOCKSZ];
	memset(buf, 0xFFFFFFFF, sizeof(buf));
	write_disk(buf, FILE_ST + blockno * BLOCKSZ, BLOCKSZ);
}
Beispiel #24
0
void add_dir(uint parent, struct direct *sp)
{
  uint size, dsize, dseek, nlink = 2;
  int f, n, i;
  struct direct *de, *p;
  DIR *d;
  struct dirent *dp;
  struct stat st;
  static uchar zeros[4096];

  // build directory
  de = sp;
  d = opendir(".");
  sp->d_ino = bn;     xstrncpy(sp->d_name, ".",  DIRSIZ); sp++;
  sp->d_ino = parent; xstrncpy(sp->d_name, "..", DIRSIZ); sp++;
  while (dp = readdir(d)) {
	if (!strcmp(dp->d_name, ".") || !strcmp(dp->d_name, "..") || strlen(dp->d_name) > DIRSIZ) continue;
	if (stat(dp->d_name, &st)) { dprintf(2, "stat(%s) failed\n", dp->d_name); exit(-1); }
	if ((st.st_mode & S_IFMT) == S_IFREG) sp->d_ino = st.st_size;
	else if ((st.st_mode & S_IFMT) == S_IFDIR) { sp->d_ino = -1; nlink++; }
	else continue;
	xstrncpy(sp->d_name, dp->d_name, DIRSIZ);
	sp++;
  }
  closedir(d);
  parent = bn;
  
  // write inode
  write_meta(dsize = (uint)sp - (uint)de, S_IFDIR, nlink);  
  dseek = (bn - ((dsize + 4095) / 4096)) * 4096;

  // write directory
  write_disk(de, dsize);
  if (dsize & 4095) write_disk(zeros, 4096 - (dsize & 4095));

  // add directory contents
  for (p = de + 2; p < sp; p++) {
	size = p->d_ino; p->d_ino = bn;
	if (size == -1) { // subdirectory
	  chdir(p->d_name);
	  add_dir(parent, sp);
	  chdir("..");
	} else { // file
	  write_meta(size, S_IFREG, 1);
	  if (size) {
		if ((f = open(p->d_name, O_RDONLY)) < 0) { dprintf(2, "open(%s) failed\n", p->d_name); exit(-1); }
		for (n = size; n; n -= i) {
		  if ((i = read(f, buf, (n > BUFSZ) ? BUFSZ : n)) < 0) { dprintf(2, "read(%s) failed\n", p->d_name); exit(-1); }
		  write_disk(buf, i);
		}
		close(f);
		if (size & 4095) write_disk(zeros, 4096 - (size & 4095));
	  }
	}
  }
  
  // update directory
  lseek(disk, dseek, SEEK_SET);
  write_disk(de, dsize);
  lseek(disk, 0, SEEK_END);
}
Beispiel #25
0
void mv(char * filename, char * path)
{
	int i, name_length, type;
	filename[str_len(filename) - 1] = 0;
	iNode * path_inode = current;
	path_inode = parser_path(path, path_inode);
	iNode * filename_inode = current;
	filename_inode = parser_path(filename, filename_inode);

	if(filename_inode->gid < currentUsr.group)
	{
		printf("\nCan not move '%s'. Permission denied.", filename);
		return ;
	}

	if(filename_inode == NULL)
	{
		printf("\nCan not move '%s'. File doesn't exist.", filename);
		return ;
	}

	if(path_inode == NULL)
	{
		name_length = str_len(path);
		for(i = 0; i < name_length; i++)
			if(path[i] == '/')
			{
				printf("\nCan not move '%s' to '%s'. Directory doesn't exist.", filename, path);
				return;
			}
		rename_file(filename_inode->iNode_number, path);
		return ;
	}

	int init_block = current->data.direct_blocks[0];
	directoryEntry * dr = (directoryEntry*)calloc(64 * 96, 1);
	read_disk(0, init_block, dr, (BLOCK_SIZE * 12), 0);
	for(i = 1; i < 96; i++){
		if( strcmp(filename, dr[i].name) == 1){
			type = dr[i].type;
			break;
		}
	}

	if(type == DIRECTORY)
	{
		insert_directory_entry(filename_inode, path_inode, filename);

		int inode_number = filename_inode->iNode_number;
		init_block = current->data.direct_blocks[0];
		directoryEntry * dr = (directoryEntry*)calloc(sizeof(directoryEntry),96);
		read_disk(0,init_block,dr,BLOCK_SIZE*12,0);
		iNode * parent = fs_get_inode(dr[1].inode);
		int father_init_block = current->data.direct_blocks[0];
		directoryEntry * father_dr = (directoryEntry*)calloc(sizeof(directoryEntry),96);
		read_disk(0,father_init_block,father_dr,BLOCK_SIZE*12,0);

		for ( i = 2; i < 96; i++){
			if ( father_dr[i].inode == inode_number){
				dr[i].type = 0;
				dr[i].inode = 0;
				dr[i].lenght = 0;
				strcopy(dr[i].name,"\0",1 );
				break;
			}
		}
		write_disk(0,init_block,dr,BLOCK_SIZE*12,0);
	}
	else if( type == FILE)
	{
		insert_file(filename, 777, path_inode);
		rmDir(filename);
	}

	return ;
}
Beispiel #26
0
void rmDir(char * path) {

	int i, j, ret;
	iNode * posible_inode = current;
	posible_inode = parser_path(path, posible_inode);

	if (posible_inode == NULL) {
		printf("Wrong name or path\n");
		return;
	}

	if (posible_inode->gid < currentUsr.group) {
		printf("\nCan not remove %s. Permission denied.", path);
		return;
	}
	if (posible_inode->identifier != DIRECTORY) {

		int inode_number = posible_inode->iNode_number;
		int init_block = current->data.direct_blocks[0];
		directoryEntry * dr = (directoryEntry*) calloc(sizeof(directoryEntry),
				96);
		read_disk(0, init_block, dr, BLOCK_SIZE * 12, 0);
		for (i = 2; i < 96; i++) {
			if (dr[i].inode == inode_number) {
				char * empty_name = "\0";
				dr[i].type = 0;
				dr[i].inode = 0;
				dr[i].lenght = 0;
				strcopy(dr[i].name, empty_name, 1);
				break;
			}
		}
		write_disk(0, init_block, dr, BLOCK_SIZE * 12, 0);
	} else {
		//BORRADO RECURSIVO.
		ret = recursive_remove(posible_inode);

		if (ret)
			return;
		int inode_number = posible_inode->iNode_number;
		int init_block = current->data.direct_blocks[0];
		directoryEntry * dr = (directoryEntry*) calloc(sizeof(directoryEntry),
				96);
		read_disk(0, init_block, dr, BLOCK_SIZE * 12, 0);
		iNode * parent = fs_get_inode(dr[1].inode);
		int father_init_block = current->data.direct_blocks[0];
		directoryEntry * father_dr = (directoryEntry*) calloc(
				sizeof(directoryEntry), 96);
		read_disk(0, father_init_block, father_dr, BLOCK_SIZE * 12, 0);

		for (i = 2; i < 96; i++) {
			if (father_dr[i].inode == inode_number) {
				char * empty_name = "\0";
				dr[i].type = 0;
				dr[i].inode = 0;
				dr[i].lenght = 0;
				strcopy(dr[i].name, empty_name, 1);
				break;
			}
		}
		write_disk(0, init_block, dr, BLOCK_SIZE * 12, 0);
	}
	return;
}