/*===========================================================================* * do_open * *===========================================================================*/ int do_open() { /* Perform the open(name, flags,...) system call. * syscall might provide 'name' embedded in message when not creating file */ int create_mode; /* is really mode_t but this gives problems */ int open_mode = 0; /* is really mode_t but this gives problems */ int r = OK; char fullpath[PATH_MAX]; vir_bytes vname; size_t vname_length; open_mode = (mode_t) job_m_in.mode; create_mode = job_m_in.c_mode; /* If O_CREAT is set, open has three parameters, otherwise two. */ if (open_mode & O_CREAT) { vname = (vir_bytes) job_m_in.name1; vname_length = (size_t) job_m_in.name1_length; r = fetch_name(vname, vname_length, fullpath); } else { vname = (vir_bytes) job_m_in.name; vname_length = (size_t) job_m_in.name_length; create_mode = 0; if (copy_name(vname_length, fullpath) != OK) { /* Direct copy failed, try fetching from user space */ if (fetch_name(vname, vname_length, fullpath) != OK) r = err_code; } } if (r != OK) return(err_code); /* name was bad */ return common_open(fullpath, open_mode, create_mode); }
void send_opponent_name(int i) { char buf[17] = "N"; int sock = clients[i].sock; if (i % 2 == 0) i++; else i--; if (i < num_clients) { copy_name(buf+1, clients[i].name); writebytes(sock, buf, 17); } }
/*===========================================================================* * do_chroot * *===========================================================================*/ int do_chroot() { /* Perform the chroot(name) system call. * syscall might provide 'name' embedded in the message. */ int r; struct vnode *vp; struct vmnt *vmp; char fullpath[PATH_MAX]; struct lookup resolve; vir_bytes vname; size_t vname_length; vname = (vir_bytes) job_m_in.name; vname_length = (size_t) job_m_in.name_length; if (!super_user) return(EPERM); /* only su may chroot() */ if (copy_name(vname_length, fullpath) != OK) { /* Direct copy failed, try fetching from user space */ if (fetch_name(vname, vname_length, fullpath) != OK) return(err_code); } /* Try to open the directory */ lookup_init(&resolve, fullpath, PATH_NOFLAGS, &vmp, &vp); resolve.l_vmnt_lock = VMNT_READ; resolve.l_vnode_lock = VNODE_READ; if ((vp = eat_path(&resolve, fp)) == NULL) return(err_code); r = change_into(&fp->fp_rd, vp); unlock_vnode(vp); unlock_vmnt(vmp); put_vnode(vp); return(r); }
/*===========================================================================* * do_creat * *===========================================================================*/ int do_creat() { /* Perform the creat(name, mode) system call. * syscall might provide 'name' embedded in the message. */ char fullpath[PATH_MAX]; vir_bytes vname; size_t vname_length; mode_t open_mode; vname = (vir_bytes) job_m_in.name; vname_length = (size_t) job_m_in.name_length; open_mode = (mode_t) job_m_in.mode; if (copy_name(vname_length, fullpath) != OK) { /* Direct copy failed, try fetching from user space */ if (fetch_name(vname, vname_length, fullpath) != OK) return(err_code); } return common_open(fullpath, O_WRONLY | O_CREAT | O_TRUNC, open_mode); }
/*===========================================================================* * do_umount * *===========================================================================*/ int do_umount(void) { /* Perform the umount(name) system call. * syscall might provide 'name' embedded in the message. */ char label[LABEL_MAX]; dev_t dev; int r; char fullpath[PATH_MAX]; vir_bytes vname; size_t vname_length; vname = (vir_bytes) job_m_in.name; vname_length = (size_t) job_m_in.name_length; /* Only the super-user may do umount. */ if (!super_user) return(EPERM); /* If 'name' is not for a block special file or mountpoint, return error. */ if (copy_name(vname_length, fullpath) != OK) { /* Direct copy failed, try fetching from user space */ if (fetch_name(vname, vname_length, fullpath) != OK) return(err_code); } if ((dev = name_to_dev(TRUE /*allow_mountpt*/, fullpath)) == NO_DEV) return(err_code); if ((r = unmount(dev, label)) != OK) return(r); /* Return the label of the mounted file system, so that the caller * can shut down the corresponding server process. */ if (strlen(label) >= M3_LONG_STRING) /* should never evaluate to true */ label[M3_LONG_STRING-1] = 0; strlcpy(m_out.umount_label, label, M3_LONG_STRING); return(OK); }
/*===========================================================================* * do_unlink * *===========================================================================*/ int do_unlink() { /* Perform the unlink(name) or rmdir(name) system call. The code for these two * is almost the same. They differ only in some condition testing. Unlink() * may be used by the superuser to do dangerous things; rmdir() may not. * The syscall might provide 'name' embedded in the message. */ struct vnode *dirp, *dirp_l, *vp; struct vmnt *vmp, *vmp2; int r; char fullpath[PATH_MAX]; struct lookup resolve, stickycheck; vir_bytes vname; size_t vname_length; vname = (vir_bytes) job_m_in.name; vname_length = job_m_in.name_length; if (copy_name(vname_length, fullpath) != OK) { /* Direct copy failed, try fetching from user space */ if (fetch_name(vname, vname_length, fullpath) != OK) /* CSC2025 Mod Start */ logfserr_nopath(FSOP_UNLNK, err_code); /* CSC2025 Mod End */ return(err_code); } lookup_init(&resolve, fullpath, PATH_RET_SYMLINK, &vmp, &dirp_l); resolve.l_vmnt_lock = VMNT_WRITE; resolve.l_vnode_lock = VNODE_WRITE; /* Get the last directory in the path. */ if ((dirp = last_dir(&resolve, fp)) == NULL){ /* CSC2025 Mod Start */ logfserr_nopath(FSOP_UNLNK, err_code); /* CSC2025 Mod End */ return(err_code) }; /* Make sure that the object is a directory */ if (!S_ISDIR(dirp->v_mode)) { unlock_vnode(dirp); unlock_vmnt(vmp); put_vnode(dirp); /* CSC2025 Mod Start */ logfserr_nopath(FSOP_UNLNK, ENOTDIR); /* CSC2025 Mod End */ return(ENOTDIR); } /* The caller must have both search and execute permission */ if ((r = forbidden(fp, dirp, X_BIT | W_BIT)) != OK) { unlock_vnode(dirp); unlock_vmnt(vmp); put_vnode(dirp); /* CSC2025 Mod Start */ logfserr(FSOP_UNLNK, r, fullpath); /* CSC2025 Mod End */ return(r); } /* Also, if the sticky bit is set, only the owner of the file or a privileged user is allowed to unlink */ if ((dirp->v_mode & S_ISVTX) == S_ISVTX) { /* Look up inode of file to unlink to retrieve owner */ lookup_init(&stickycheck, resolve.l_path, PATH_RET_SYMLINK, &vmp2, &vp); stickycheck.l_vmnt_lock = VMNT_READ; stickycheck.l_vnode_lock = VNODE_READ; vp = advance(dirp, &stickycheck, fp); assert(vmp2 == NULL); if (vp != NULL) { if (vp->v_uid != fp->fp_effuid && fp->fp_effuid != SU_UID) r = EPERM; unlock_vnode(vp); put_vnode(vp); } else r = err_code; if (r != OK) { unlock_vnode(dirp); unlock_vmnt(vmp); put_vnode(dirp); /* CSC2025 Mod Start */ logfserr(FSOP_UNLNK, r, fullpath); /* CSC2025 Mod End */ return(r); } } upgrade_vmnt_lock(vmp); if (job_call_nr == UNLINK) r = req_unlink(dirp->v_fs_e, dirp->v_inode_nr, fullpath); else r = req_rmdir(dirp->v_fs_e, dirp->v_inode_nr, fullpath); unlock_vnode(dirp); unlock_vmnt(vmp); put_vnode(dirp); /* CSC2025 Mod Start */ if(r == OK){ logfsop(FSOP_UNLNK, r, fullpath, scratch(fp).file.fd_nr, vp->v_mode, vp->v_uid, vp->v_gid, vp->v_size}; } else {