예제 #1
0
// Look up and return the inode for a path name.
// If parent != 0, return the inode for the parent and copy the final
// path element into name, which must have room for DIRSIZ bytes.
static struct inode*
namex(char *path, int nameiparent, char *name)
{
  struct inode *ip, *next;

  if(*path == '/')
    ip = iget(ROOTDEV, ROOTINO);
  else
    ip = idup(proc->cwd);

  while((path = skipelem(path, name)) != 0){
    ilock(ip);
    if(ip->type != T_DIR){
      iunlockput(ip);
      return 0;
    }
    if(nameiparent && *path == '\0'){
      // Stop one level early.
      iunlock(ip);
      return ip;
    }
    if((next = dirlookup(ip, name, 0)) == 0){
      iunlockput(ip);
      return 0;
    }
    iunlockput(ip);
    ip = next;
  }
  if(nameiparent){
    iput(ip);
    return 0;
  }
  return ip;
}
예제 #2
0
파일: sfs_inode.c 프로젝트: wzc11/xv6_fs
// Look up and return the inode for a path name.
// If parent != 0, return the inode for the parent and copy the final
// path element into name, which must have room for DIRSIZ bytes.
static struct inode*
namex(struct inode *ip, char *path, int nameiparent, char *name)
{
  struct inode *next;
  struct sfs_inode *sinp;

  while((path = skipelem(path, name)) != 0){
    sfs_ilock(ip);
    sinp = vop_info(ip, sfs_inode);
    if(sinp->type != T_DIR){
      sfs_iunlockput(ip);
      return 0;
    }
    if(nameiparent && *path == '\0'){
      // Stop one level early.
      sfs_iunlock(ip);
      return ip;
    }
    if((next = sfs_dirlookup(ip, name, 0)) == 0){
      sfs_iunlockput(ip);
      return 0;
    }
    sfs_iunlockput(ip);
    ip = next;
  }
  if(nameiparent){
    sfs_iput(ip);
    return 0;
  }
  return ip;
}
예제 #3
0
/**
 * Look up and return the inode for a path name.
 * If nameiparent is true, return the inode for the parent and copy the final
 * path element into name, which must have room for DIRSIZ bytes.
 * Returns 0 in the case of error.
 */
static struct inode*
namex(char *path, bool nameiparent, char *name)
{
  struct inode *ip;
  struct inode *next;
  // If path is a full path, get the pointer to the root inode. Otherwise get
  // the inode corresponding to the current working directory.
  if(*path == '/'){
    ip = inode_get(ROOTDEV, ROOTINO);
  }
  else {
    ip = inode_dup((struct inode*) tcb_get_cwd(get_curid()));
  }

  while((path = skipelem(path, name)) != 0){
	inode_lock(ip);
	if(ip -> type != T_DIR) {
		return 0;
	}
	if(nameiparent && *path == 0) {
		inode_unlock(ip);
		return ip;
	}
	next = dir_lookup(ip, name, 0);
	inode_unlockput(ip);
	ip = next;
  }
  if(nameiparent){
    inode_put(ip);
    return 0;
  }
  return ip;
}
예제 #4
0
파일: fs.c 프로젝트: ashual/xv6-ass4
// Look up and return the inode for a path name.
// If parent != 0, return the inode for the parent and copy the final
// path element into name, which must have room for DIRSIZ bytes.
static struct inode*
namex(char *path, int nameiparent, char *name, int mode) // mode - 0-reference 1-dereference
{

  struct inode *ip, *next;
  char buf[64];
  if(*path == '/')
    ip = iget(ROOTDEV, ROOTINO);
  else
    ip = idup(proc->cwd);

  while((path = skipelem(path, name)) != 0){
	  ilock(ip);

    if(ip->type != T_DIR){
      iunlockput(ip);
      return 0;
    }

    if(nameiparent && *path == '\0'){
      // Stop one level early.
      iunlock(ip);
      return ip;
    }

    if((next = dirlookup(ip, name, 0)) == 0){
      iunlockput(ip);
      return 0;
    }

    iunlockput(ip);

    if(mode || *path!='\0')
    {
    	next= recursive_readlink(buf,next, 16, 0);
    }

    ip = next;
  }
  if(nameiparent){
    iput(ip);
    return 0;
  }

  return ip;
}
예제 #5
0
// Look up and return the inode for a path name.
// If parent != 0, return the inode for the parent and copy the final
// path element into name, which must have room for DIRSIZ bytes.
static struct inode*
_namei(char *path, int parent, char *name)
{
	//cprintf("Path: %s\n", path);
  struct inode *ip, *next;

  if(*path == '/')
    ip = iget(ROOTDEV, 1);
  else
    ip = idup(cp->cwd);

  //cprintf("cp name: %s\n", cp->name);

  while((path = skipelem(path, name)) != 0){
    ilock(ip);
    if(ip->type != T_DIR){
      iunlockput(ip);
      //cprintf("HERE\n");
      return 0;
    }
    if(parent && *path == '\0'){
      // Stop one level early.
      iunlock(ip);
      //cprintf("HERE3\n");
      return ip;
    }
    if((next = dirlookup(ip, name, 0)) == 0){
      iunlockput(ip);
      //cprintf("HERE1\n");
      return 0;
    }
    iunlockput(ip);
    ip = next;
  }
  if(parent){
    iput(ip);
    //cprintf("HERE2\n");
    return 0;
  }
  //cprintf("HERE4-2: %d\n", ip);
  return ip;
}
예제 #6
0
파일: p2i.c 프로젝트: bajdcc/MiniOS
static struct inode *_path2inode(char *path, int parent, char *name) {
    struct inode *ip, *next;

    ip = 0;
    if (*path == '/') {
        ip = iget(ROOT_DEV, ROOT_INO);
    } else {
        ip = idup(proc->cwd);
    }     

    while ((path = skipelem(path, name)) != 0) {
        /* read from disk */
        ilock(ip);
        if (!S_ISDIR(ip->mode)) {
            iunlockput(ip);
            return 0;
        }

        if (parent && *path == '\0') {
            iunlock(ip);
            return ip;
        }

        if ((next = dir_lookup(ip, name, 0)) == 0) {
            iunlockput(ip);
            return 0;
        }

        iunlockput(ip);
        ip = next;
    }

    if (parent) {
        iput(ip);
        return 0;
    }

    return ip;
}
예제 #7
0
파일: mkfs.c 프로젝트: tim48134/xylos
int
main(int argc, char *argv[])
{
	int i, cc, fd;
	uint rootino, inum, off, bin_inum, tests_inum, sbin_inum; //dir_inum
	struct dirent de;
	char buf[BSIZE];
	struct dinode din;


	static_assert(sizeof(int) == 4, "Integers must be 4 bytes!");

	if(argc < 2) {
		fprintf(stderr, "Usage: mkfs fs.img files...\n");
		exit(1);
	}

	assert((BSIZE % sizeof(struct dinode)) == 0);
	assert((BSIZE % sizeof(struct dirent)) == 0);

	fsfd = open(argv[1], O_RDWR | O_CREAT | O_TRUNC, 0666);
	if(fsfd < 0) {
		perror(argv[1]);
		exit(1);
	}

	// 1 fs block = 1 disk sector
	nmeta = 2 + nlog + ninodeblocks + nbitmap;
	nblocks = FSSIZE - nmeta;

	sb.size = xint(FSSIZE);
	sb.nblocks = xint(nblocks);
	sb.ninodes = xint(NINODES);
	sb.nlog = xint(nlog);
	sb.logstart = xint(2);
	sb.inodestart = xint(2 + nlog);
	sb.bmapstart = xint(2 + nlog + ninodeblocks);

	printf("nmeta %d (boot, super, log blocks %u inode blocks %u, bitmap blocks %u) blocks %d total %d\n",
		   nmeta, nlog, ninodeblocks, nbitmap, nblocks, FSSIZE);

	freeblock = nmeta;     // the first free block that we can allocate

	for(i = 0; i < FSSIZE; i++) {
		wsect(i, zeroes);
	}

	memset(buf, 0, sizeof(buf));
	memmove(buf, &sb, sizeof(sb));
	wsect(1, buf);

	rootino = ialloc(T_DIR);
	assert(rootino == ROOTINO);

	bzero(&de, sizeof(de));
	de.inum = xshort(rootino);
	strcpy(de.name, ".");
	iappend(rootino, &de, sizeof(de));

	bzero(&de, sizeof(de));
	de.inum = xshort(rootino);
	strcpy(de.name, "..");
	iappend(rootino, &de, sizeof(de));

	// create /bin folder
	bin_inum = ialloc(T_DIR);
	bzero(&de, sizeof(de));
	de.inum = xshort(bin_inum);
	strcpy(de.name, "bin");
	iappend(rootino, &de, sizeof(de));

	bzero(&de, sizeof(de));
	de.inum = xshort(bin_inum);
	strcpy(de.name, ".");
	iappend(bin_inum, &de, sizeof(de));

	bzero(&de, sizeof(de));
	de.inum = xshort(rootino);
	strcpy(de.name, "..");
	iappend(bin_inum, &de, sizeof(de));

	// create /dev folder
	inum = ialloc(T_DIR);
	bzero(&de, sizeof(de));
	de.inum = xshort(inum);
	strcpy(de.name, "dev");
	iappend(rootino, &de, sizeof(de));

	bzero(&de, sizeof(de));
	de.inum = xshort(inum);
	strcpy(de.name, ".");
	iappend(inum, &de, sizeof(de));

	bzero(&de, sizeof(de));
	de.inum = xshort(rootino);
	strcpy(de.name, "..");
	iappend(inum, &de, sizeof(de));

	// create /sbin folder
	sbin_inum = ialloc(T_DIR);
	bzero(&de, sizeof(de));
	de.inum = xshort(sbin_inum);
	strcpy(de.name, "sbin");
	iappend(rootino, &de, sizeof(de));

	bzero(&de, sizeof(de));
	de.inum = xshort(sbin_inum);
	strcpy(de.name, ".");
	iappend(sbin_inum, &de, sizeof(de));

	bzero(&de, sizeof(de));
	de.inum = xshort(rootino);
	strcpy(de.name, "..");
	iappend(sbin_inum, &de, sizeof(de));

	// create /tests folder
	tests_inum = ialloc(T_DIR);
	bzero(&de, sizeof(de));
	de.inum = xshort(tests_inum);
	strcpy(de.name, "tests");
	iappend(rootino, &de, sizeof(de));

	bzero(&de, sizeof(de));
	de.inum = xshort(tests_inum);
	strcpy(de.name, ".");
	iappend(tests_inum, &de, sizeof(de));

	bzero(&de, sizeof(de));
	de.inum = xshort(rootino);
	strcpy(de.name, "..");
	iappend(tests_inum, &de, sizeof(de));

	for(i = 2; i < argc; i++) {
		printf("argv[i]:  %s   and index:  %s\n", argv[i], index(argv[i], '/'));
		//assert(index(argv[i], '/') == 0);

		if((fd = open(argv[i], 0)) < 0) {
			perror(argv[i]);
			exit(1);
		}

		if(index(argv[i], '/') != 0) {

			char foldername[256];
			char *progname = malloc(sizeof(char) * 256);
			strcpy(progname, skipelem(argv[i], foldername));

			if(progname[0] == '_') {
				progname++;
			}

			if(strcmp(foldername, "bin") == 0) {
				inum = ialloc(T_FILE);

				bzero(&de, sizeof(de));
				de.inum = xshort(inum);
				strncpy(de.name, progname, DIRSIZ);
				iappend(bin_inum, &de, sizeof(de));

				while((cc = read(fd, buf, sizeof(buf))) > 0) {
					iappend(inum, buf, cc);
				}

				close(fd);
			} else if(strcmp(foldername, "tests") == 0) {
				inum = ialloc(T_FILE);

				bzero(&de, sizeof(de));
				de.inum = xshort(inum);
				strncpy(de.name, progname, DIRSIZ);
				iappend(tests_inum, &de, sizeof(de));

				while((cc = read(fd, buf, sizeof(buf))) > 0) {
					iappend(inum, buf, cc);
				}

				close(fd);
			} else if(strcmp(foldername, "sbin") == 0) {
				inum = ialloc(T_FILE);

				bzero(&de, sizeof(de));
				de.inum = xshort(inum);
				strncpy(de.name, progname, DIRSIZ);
				iappend(sbin_inum, &de, sizeof(de));

				while((cc = read(fd, buf, sizeof(buf))) > 0) {
					iappend(inum, buf, cc);
				}

				close(fd);
			} else if(strcmp(foldername, "docs") == 0) {
				inum = ialloc(T_FILE);

				bzero(&de, sizeof(de));
				de.inum = xshort(inum);
				strncpy(de.name, progname, DIRSIZ);
				iappend(rootino, &de, sizeof(de));

				while((cc = read(fd, buf, sizeof(buf))) > 0) {
					iappend(inum, buf, cc);
				}

				close(fd);
			} else if(strcmp(foldername, "shell") == 0) {
				inum = ialloc(T_FILE);

				bzero(&de, sizeof(de));
				de.inum = xshort(inum);
				strncpy(de.name, progname, DIRSIZ);
				iappend(bin_inum, &de, sizeof(de));

				while((cc = read(fd, buf, sizeof(buf))) > 0) {
					iappend(inum, buf, cc);
				}

				close(fd);
			} else {
				printf("\nERROR: Found folder other than bin and tests: %s\n", foldername);
				exit(1);
			}

		} else {

			// Skip leading _ in name when writing to file system.
			// The binaries are named _rm, _cat, etc. to keep the
			// build operating system from trying to execute them
			// in place of system binaries like rm and cat.
			if(argv[i][0] == '_') {
				++argv[i];
			}

			inum = ialloc(T_FILE);

			bzero(&de, sizeof(de));
			de.inum = xshort(inum);
			strncpy(de.name, argv[i], DIRSIZ);
			iappend(rootino, &de, sizeof(de));

			while((cc = read(fd, buf, sizeof(buf))) > 0) {
				iappend(inum, buf, cc);
			}

			close(fd);
		}
	}

	// fix size of root inode dir
	rinode(rootino, &din);
	off = xint(din.size);
	off = ((off / BSIZE) + 1) * BSIZE;
	din.size = xint(off);
	winode(rootino, &din);

	balloc(freeblock);

	exit(0);
}
예제 #8
0
//part 1 - signature change, and de-referencing symbolic links to the correct inode
struct inode*
namex(char *path, int nameiparent, char *name, 
      struct inode *prev, int loopCount,int noDeRef)
{
  struct inode *ip, *next;
  char buf[512];

  // part 1 - prevent loop in symbolic links
  if(loopCount > 16)
    return 0;

  if(*path == '/') {
    ip = iget(ROOTDEV, ROOTINO);
  } else if(prev) {
    ip = idup(prev);
  } else {
    ip = idup(proc->cwd);
  }

  while( (path = skipelem(path, name)) != 0 ) {
    ilock(ip);
    if(ip->type != T_DIR){
      iunlockput(ip);
      return 0;
    }
    if(nameiparent && *path == '\0'){
      // Stop one level early.
      iunlock(ip);
      return ip;
    }
    if((next = dirlookup(ip, name, 0)) == 0){
      iunlockput(ip);
      return 0;
    }

    if(noDeRef) {
        iunlockput(ip);
    } else {
        iunlock(ip);

        //part 1
        ilock(next);

        if(next->type == T_SYMLINK) {
            if(readi(next, buf, 0, sizeof(buf)) != next->size) {
                iunlockput(ip);
                return 0;
            }
            buf[next->size] = 0;
            iunlock(next);
            next = namex(buf, 0, name, ip, loopCount++,0);
        } else {
            iunlock(next);
        }
        // End part 1

        iput(ip);
    }
    ip = next;
  }
  if(nameiparent) {
    iput(ip);
    return 0;
  }
  return ip;
}
예제 #9
0
파일: fs.c 프로젝트: bitc/3
// Same as filereadlink, but doesn't dereference the final path element
int
filereadlinki(const char *pathname, char *buf, int bufsiz)
{
  int loops_left = MAX_SYMLINK_LOOPS;
  int l;

  char name[DIRSIZ+1];
  char result[MAXPATH];
  int result_off;
  char origpath[MAXPATH];
  char *origpath_p;

  struct inode* ip;

  if(*pathname == '\0'){
    return -1;
  }

  if(pathname[0] == '/' && pathname[1] == '\0') {
    buf[0] = '/';
    buf[1] = '\0';
    return 2;
  }

  strncpy(origpath, pathname, MAXPATH);

restart:
  result_off = 0;

  if(origpath[0] == '/'){
    result[0] = '/';
    result_off = 1;
  }
  result[result_off] = '\0';

  origpath_p = origpath;

  for(;;){
    origpath_p = skipelem(origpath_p, name);
    if(!origpath_p){
      return -1;
    }

    if(*origpath_p == '\0'){
      // Last element
      // `name' contains the filename

      safestrcpy(&result[result_off], name, MAXPATH);
      result_off += strlen(name);
      result[result_off] = '\0';

      if(bufsiz < result_off + 1){
        return -1;
      } else {
        safestrcpy(buf, result, MAXPATH);
        return result_off;
      }
    } else {
      safestrcpy(&result[result_off], name, MAXPATH);
      result_off += strlen(name);
      result[result_off] = '\0';

      ip = namei(result);
      if(!ip){
        return -1;
      }
      ilock(ip);
      if(ip->type == T_FILE || ip->type == T_DEV){
        // Tried to traverse through a file/dev as if it was a directory
        return -1;
      } else if(ip->type == T_DIR) {
        result[result_off] = '/';
        result_off++;
        result[result_off] = '\0';
      } else if(ip->type == T_SYMLINK) {
        result_off -= strlen(name);
        l = readi(ip, &result[result_off], 0, MAXPATH);
        iunlock(ip);
        result[result_off+l] = '/';
        safestrcpy(&result[result_off+l+1], origpath_p, MAXPATH);
        if(result[result_off] == '/') {
          // Absolute symlink
          safestrcpy(origpath, &result[result_off], MAXPATH);
        } else {
          safestrcpy(origpath, result, MAXPATH);
        }
        loops_left--;
        if(loops_left == 0){
          return -1;
        }
        goto restart;
      } else {
        panic("filereadlink: unknown inode type");
      }
      iunlock(ip);
    }
  }
}
예제 #10
0
// Look up and return the inode for a path name.
// If parent != 0, return the inode for the parent and copy the final
// path element into name, which must have room for DIRSIZ bytes.
// Must be called inside a transaction since it calls iput().
static struct inode* namex(char* path, int nameiparent, int ignoreMounts, char* name)
{
    // cprintf("namex \n");

    struct inode* ip, *next;
    // cprintf("path %s nameparent %d , name %s bootfrom %d\n", path, nameiparent, name, bootfrom);
    if (*path == '/')
        ip = iget(ROOTDEV, ROOTINO, bootfrom);
    else
        ip = idup(proc->cwd);

    while ((path = skipelem(path, name)) != 0) {
//cprintf("namex path %s \n",path);
        ilock(ip);
        if (ip->type != T_DIR) {
            iunlockput(ip);
            return 0;
        }
        if (nameiparent && *path == '\0') {
            // Stop one level early.
            //  cprintf("fileread \n");

            iunlock(ip);
            return ip;
        }

        if ((next = dirlookup(ip, name, 0)) == 0) {
           // cprintf("next is zero \n");
            iunlockput(ip);
            return 0;
        }
        iunlockput(ip);
        ilock(next);
       //  cprintf("next %d , type %d major %d minor %d \n",next->inum,next->type,next->major,next->minor);
        if (!ignoreMounts && next->type == T_DIR && next->major != 0 && next->major != MOUNTING_POINT) {
         //   cprintf("major used ,we are f****d \n");
        }
        // handle mounting points

        if (!ignoreMounts  && next->type == T_DIR && next->major == MOUNTING_POINT) {
           // cprintf("got into condition \n");
                        iunlock(next);

            // iunlockput(ip);
            uint partitionNumnber = next->minor;
            ip = iget(ROOTDEV, 1, partitionNumnber);
        }
        else{
            iunlock(next);

        // testing

        ip = next;
    }
        }
       
    if (nameiparent) {
        iput(ip);
        return 0;
    }
    // cprintf("ip returned is %d \n", ip->inum);
    return ip;
}