|
|
1.1 ! root 1: #include <string.h> ! 2: #include <errno.h> ! 3: #include <linux/sched.h> ! 4: #include <linux/kernel.h> ! 5: #include <asm/segment.h> ! 6: ! 7: #include <fcntl.h> ! 8: #include <sys/stat.h> ! 9: ! 10: extern int sys_close(int fd); ! 11: ! 12: static int dupfd(unsigned int fd, unsigned int arg) ! 13: { ! 14: if (fd >= NR_OPEN || !current->filp[fd]) ! 15: return -EBADF; ! 16: if (arg >= NR_OPEN) ! 17: return -EINVAL; ! 18: while (arg < NR_OPEN) ! 19: if (current->filp[arg]) ! 20: arg++; ! 21: else ! 22: break; ! 23: if (arg >= NR_OPEN) ! 24: return -EMFILE; ! 25: current->close_on_exec &= ~(1<<arg); ! 26: (current->filp[arg] = current->filp[fd])->f_count++; ! 27: return arg; ! 28: } ! 29: ! 30: int sys_dup2(unsigned int oldfd, unsigned int newfd) ! 31: { ! 32: sys_close(newfd); ! 33: return dupfd(oldfd,newfd); ! 34: } ! 35: ! 36: int sys_dup(unsigned int fildes) ! 37: { ! 38: return dupfd(fildes,0); ! 39: } ! 40: ! 41: int sys_fcntl(unsigned int fd, unsigned int cmd, unsigned long arg) ! 42: { ! 43: struct file * filp; ! 44: ! 45: if (fd >= NR_OPEN || !(filp = current->filp[fd])) ! 46: return -EBADF; ! 47: switch (cmd) { ! 48: case F_DUPFD: ! 49: return dupfd(fd,arg); ! 50: case F_GETFD: ! 51: return (current->close_on_exec>>fd)&1; ! 52: case F_SETFD: ! 53: if (arg&1) ! 54: current->close_on_exec |= (1<<fd); ! 55: else ! 56: current->close_on_exec &= ~(1<<fd); ! 57: return 0; ! 58: case F_GETFL: ! 59: return filp->f_flags; ! 60: case F_SETFL: ! 61: filp->f_flags &= ~(O_APPEND | O_NONBLOCK); ! 62: filp->f_flags |= arg & (O_APPEND | O_NONBLOCK); ! 63: return 0; ! 64: case F_GETLK: case F_SETLK: case F_SETLKW: ! 65: return -1; ! 66: default: ! 67: return -1; ! 68: } ! 69: }
This archive runs on limited infrastructure. Preserving old code on modern bandwidth. Automated agents are requested to crawl responsibly.