From 4147b3f690ea42bd015c9077ae49137621134f19 Mon Sep 17 00:00:00 2001 From: Bill Joy Date: Sun, 25 Jul 1982 01:12:27 -0800 Subject: [PATCH] merge with calder SCCS-vsn: sys/kern/kern_descrip.c 5.2 SCCS-vsn: sys/sys/file.h 4.11 SCCS-vsn: sys/sys/socket.h 4.17 SCCS-vsn: sys/kern/kern_proc.c 4.28 SCCS-vsn: sys/sys/socketvar.h 4.17 SCCS-vsn: sys/kern/kern_prot.c 5.3 SCCS-vsn: sys/kern/kern_resource.c 4.10 SCCS-vsn: sys/kern/kern_sig.c 5.2 SCCS-vsn: sys/kern/kern_time.c 5.2 SCCS-vsn: sys/kern/subr_xxx.c 4.13 SCCS-vsn: sys/kern/uipc_domain.c 5.2 SCCS-vsn: sys/kern/sys_generic.c 5.3 SCCS-vsn: sys/kern/sys_process.c 5.2 SCCS-vsn: sys/kern/uipc_syscalls.c 4.21 SCCS-vsn: sys/kern/tty.c 4.24 SCCS-vsn: sys/kern/vfs_vnops.c 4.25 SCCS-vsn: sys/ufs/ffs/ffs_inode.c 4.19 SCCS-vsn: sys/ufs/ffs/ufs_inode.c 4.19 SCCS-vsn: sys/ufs/lfs/lfs_inode.c 4.19 SCCS-vsn: sys/ufs/ufs/ufs_inode.c 4.19 SCCS-vsn: sys/kern/vfs_syscalls.c 4.30 SCCS-vsn: sys/ufs/ffs/ffs_vnops.c 4.30 SCCS-vsn: sys/ufs/ffs/ufs_vnops.c 4.30 SCCS-vsn: sys/ufs/lfs/lfs_vnops.c 4.30 SCCS-vsn: sys/ufs/ufs/ufs_vnops.c 4.30 --- usr/src/sys/kern/kern_descrip.c | 419 ++++++++++++++-- usr/src/sys/kern/kern_proc.c | 76 +-- usr/src/sys/kern/kern_prot.c | 154 +++++- usr/src/sys/kern/kern_resource.c | 61 ++- usr/src/sys/kern/kern_sig.c | 361 ++++---------- usr/src/sys/kern/kern_time.c | 27 +- usr/src/sys/kern/subr_xxx.c | 17 +- usr/src/sys/kern/sys_generic.c | 21 +- usr/src/sys/kern/sys_process.c | 180 ++++++- usr/src/sys/kern/tty.c | 820 ++++++++++++++++++++++++++++++- usr/src/sys/kern/uipc_domain.c | 7 +- usr/src/sys/kern/uipc_syscalls.c | 128 ++++- usr/src/sys/kern/vfs_syscalls.c | 14 +- usr/src/sys/kern/vfs_vnops.c | 169 +------ usr/src/sys/sys/file.h | 28 +- usr/src/sys/sys/socket.h | 3 +- usr/src/sys/sys/socketvar.h | 40 +- usr/src/sys/ufs/ffs/ffs_inode.c | 32 +- usr/src/sys/ufs/ffs/ffs_vnops.c | 14 +- usr/src/sys/ufs/ffs/ufs_inode.c | 32 +- usr/src/sys/ufs/ffs/ufs_vnops.c | 14 +- usr/src/sys/ufs/lfs/lfs_inode.c | 32 +- usr/src/sys/ufs/lfs/lfs_vnops.c | 14 +- usr/src/sys/ufs/ufs/ufs_inode.c | 32 +- usr/src/sys/ufs/ufs/ufs_vnops.c | 14 +- 25 files changed, 2095 insertions(+), 614 deletions(-) diff --git a/usr/src/sys/kern/kern_descrip.c b/usr/src/sys/kern/kern_descrip.c index a04b4fae40..c3c87f5d0c 100644 --- a/usr/src/sys/kern/kern_descrip.c +++ b/usr/src/sys/kern/kern_descrip.c @@ -1,70 +1,172 @@ -/* kern_descrip.c 5.1 82/07/15 */ +/* kern_descrip.c 5.2 82/07/24 */ #include "../h/param.h" #include "../h/systm.h" #include "../h/dir.h" #include "../h/user.h" -#include "../h/reg.h" #include "../h/inode.h" #include "../h/proc.h" -#include "../h/clock.h" -#include "../h/mtpr.h" -#include "../h/timeb.h" -#include "../h/times.h" -#include "../h/reboot.h" -#include "../h/fs.h" #include "../h/conf.h" -#include "../h/buf.h" -#include "../h/mount.h" #include "../h/file.h" #include "../h/inline.h" #include "../h/socket.h" #include "../h/socketvar.h" +#include "../h/mount.h" + +#include "../h/descrip.h" + +/* + * Descriptor management. + */ + +/* + * TODO: + * getf should be renamed + * ufalloc side effects are gross + */ /* - * the dup system call. + * System calls on descriptors. */ +dstd() +{ + + u.u_r.r_val1 = NOFILE; +} + dup() { + register struct a { + int i; + } *uap = (struct a *) u.u_ap; register struct file *fp; + register int j; + + if (uap->i &~ 077) { uap->i &= 077; dup2(); return; } /* XXX */ + + fp = getf(uap->i); + if (fp == 0) + return; + j = ufalloc(); + if (j < 0) + return; + u.u_ofile[j] = fp; + fp->f_count++; +} + +dup2() +{ register struct a { - int fdes; - int fdes2; - } *uap; - register i, m; + int i, j; + } *uap = (struct a *) u.u_ap; + register struct file *fp; - uap = (struct a *)u.u_ap; - m = uap->fdes & ~077; - uap->fdes &= 077; - fp = getf(uap->fdes); - if (fp == NULL) + fp = getf(uap->i); + if (fp == 0) + return; + if (uap->j < 0 || uap->j >= NOFILE) { + u.u_error = EBADF; return; - if ((m&0100) == 0) { - if ((i = ufalloc()) < 0) - return; - } else { - i = uap->fdes2; - if (i<0 || i>=NOFILE) { - u.u_error = EBADF; - return; - } - u.u_r.r_val1 = i; } - if (i != uap->fdes) { - if (u.u_ofile[i]!=NULL) - closef(u.u_ofile[i], 0); + u.u_r.r_val1 = uap->j; + if (uap->i == uap->j) + return; + if (u.u_ofile[uap->j]) { + closef(u.u_ofile[uap->j], 0); if (u.u_error) return; - u.u_ofile[i] = fp; - fp->f_count++; + /* u.u_ofile[uap->j] = 0; */ + } + u.u_ofile[uap->j] = fp; + fp->f_count++; +} + +close() +{ + register struct a { + int i; + } *uap = (struct a *)u.u_ap; + register struct file *fp; + + fp = getf(uap->i); + if (fp == 0) + return; + u.u_ofile[uap->i] = 0; + closef(fp, 0); + /* WHAT IF u.u_error ? */ +} + +dtype() +{ + register struct a { + int d; + struct dtype *dtypeb; + } *uap = (struct a *)u.u_ap; + register struct file *fp; + struct dtype adtype; + + fp = getf(uap->d); + if (fp == 0) + return; + adtype.dt_type = 0; /* XXX */ + adtype.dt_protocol = 0; /* XXX */ + if (copyout((caddr_t)&adtype, (caddr_t)uap->dtypeb, + sizeof (struct dtype)) < 0) { + u.u_error = EFAULT; + return; + } +} + +dwrap() +{ + register struct a { + int d; + struct dtype *dtypeb; + } *uap = (struct a *)u.u_ap; + register struct file *fp; + struct dtype adtype; + + fp = getf(uap->d); + if (fp == 0) + return; + if (copyin((caddr_t)uap->dtypeb, (caddr_t)&adtype, + sizeof (struct dtype)) < 0) { + u.u_error = EFAULT; + return; } + /* DO WRAP */ +} + +dselect() +{ + +} + +dnblock() +{ + register struct a { + int d; + int how; + } *uap = (struct a *)u.u_ap; + + /* XXX */ +} + +dsignal() +{ + register struct a { + int d; + int how; + } *uap = (struct a *)u.u_ap; + + /* XXX */ } int nselcoll; /* * Select system call. */ -select() +oselect() { register struct uap { int nfd; @@ -154,7 +256,7 @@ selscan(nfd, fds, nfdp, flag) u.u_error = EBADF; return (0); } - if (fp->f_flag & FSOCKET) + if (fp->f_type == DTYPE_SOCKET) able = soselect(fp->f_socket, flag); else { ip = fp->f_inode; @@ -172,6 +274,7 @@ selscan(nfd, fds, nfdp, flag) able = 1; break; } + } if (able) { res |= (1<<(i-1)); @@ -212,24 +315,244 @@ selwakeup(p, coll) } } + /* - * Close system call + * Allocate a user file descriptor. */ -close() +ufalloc() +{ + register i; + + for (i=0; if_count == 0) + goto slot; + for (fp = file; fp < lastf; fp++) + if (fp->f_count == 0) + goto slot; + tablefull("file"); + u.u_error = ENFILE; + return (NULL); +slot: + u.u_ofile[i] = fp; + fp->f_count++; + fp->f_offset = 0; + fp->f_inode = 0; + lastf = fp + 1; + return (fp); +} +/* + * Convert a user supplied file descriptor into a pointer + * to a file structure. Only task is to check range of the descriptor. + * Critical paths should use the GETF macro, defined in inline.h. + */ +struct file * +getf(f) + register int f; { register struct file *fp; - register struct a { - int fdes; - } *uap; - uap = (struct a *)u.u_ap; - fp = getf(uap->fdes); + if ((unsigned)f >= NOFILE || (fp = u.u_ofile[f]) == NULL) { + u.u_error = EBADF; + return (NULL); + } + return (fp); +} + +/* + * Internal form of close. + * Decrement reference count on + * file structure. + * Also make sure the pipe protocol + * does not constipate. + * + * Decrement reference count on the inode following + * removal to the referencing file structure. + * Call device handler on last close. + * Nouser indicates that the user isn't available to present + * errors to. + */ +closef(fp, nouser) + register struct file *fp; +{ + register struct inode *ip; + register struct mount *mp; + int flag, mode; + dev_t dev; + register int (*cfunc)(); + if (fp == NULL) return; - if (u.u_vrpages[uap->fdes]) { - u.u_error = ETXTBSY; + if (fp->f_count > 1) { + fp->f_count--; return; } - u.u_ofile[uap->fdes] = NULL; - closef(fp, 0); + if (fp->f_type == DTYPE_SOCKET) { + u.u_error = 0; /* XXX */ + soclose(fp->f_socket, nouser); + if (nouser == 0 && u.u_error) + return; + fp->f_socket = 0; + fp->f_count = 0; + return; + } + flag = fp->f_flag; + ip = fp->f_inode; + dev = (dev_t)ip->i_rdev; + mode = ip->i_mode & IFMT; + ilock(ip); + iput(ip); + fp->f_count = 0; + + switch (mode) { + + case IFCHR: + cfunc = cdevsw[major(dev)].d_close; +#ifdef EFS + /* + * Every close() must call the driver if the + * extended file system is being used -- not + * just the last close. Pass along the file + * pointer for reference later. + */ + if (major(dev) == efs_major) { + (*cfunc)(dev, flag, fp, nouser); + return; + } +#endif + break; + + case IFBLK: + /* + * We don't want to really close the device if it is mounted + */ + for (mp = mount; mp < &mount[NMOUNT]; mp++) + if (mp->m_bufp != NULL && mp->m_dev == dev) + return; + cfunc = bdevsw[major(dev)].d_close; + break; + + default: + return; + } + for (fp = file; fp < fileNFILE; fp++) { + if (fp->f_type == DTYPE_SOCKET) /* XXX */ + continue; + if (fp->f_count && (ip = fp->f_inode) && + ip->i_rdev == dev && (ip->i_mode&IFMT) == mode) + return; + } + if (mode == IFBLK) { + /* + * On last close of a block device (that isn't mounted) + * we must invalidate any in core blocks + */ + bflush(dev); + binval(dev); + } + (*cfunc)(dev, flag, fp); +} + +#ifdef CAD +/* + * chfile -- change all references to the inode named by + * device/inum to the file referred to by fd. + * Used by init to remove all references to the device. + */ +chfile() +{ + register struct file *fp; + register struct inode *from; + register struct inode *to; + off_t offset; + dev_t dev; + int rw; + struct a { + int device; /* actually dev_t */ + int inum; /* actually ino_t */ + int fd; + } *uap; + + if (!suser()) { + u.u_error = EPERM; + return; + } + uap = (struct a *) u.u_ap; + fp = getf(uap->fd); + if (fp == NULL) { + u.u_error = EBADF; + return; + } + if (fp->f_type == DTYPE_SOCKET) { + u.u_error = EINVAL; + return; + } + for (from = &inode[0]; from < &inode[ninode]; from++) + if (from->i_number == (ino_t)uap->inum + && from->i_dev == (dev_t)uap->device) + break; + if (from >= &inode[ninode]) { + u.u_error = ENXIO; + return; + } + offset = fp->f_offset; + to = fp->f_inode; + from->i_count++; + for (fp = &file[0]; fp < &file[nfile]; fp++) { + if (fp->f_count > 0 && fp->f_inode == from) { + fp->f_inode = to; + to->i_count++; + fp->f_offset = offset; + rw |= fp->f_flag & FWRITE; + iput(from); + } + } + /* + * This inode is no longer referenced. + * Switch out to the appropriate close + * routine, if required + */ + dev = (dev_t)from->i_un.i_rdev; + switch(from->i_mode & IFMT) { + + case IFCHR: + (*cdevsw[major(dev)].d_close)(dev, rw); + break; + + case IFBLK: + (*bdevsw[major(dev)].d_close)(dev, rw); + break; + + default: + break; + } + iput(from); } +#endif diff --git a/usr/src/sys/kern/kern_proc.c b/usr/src/sys/kern/kern_proc.c index 903b0f3ba4..8ca80235f0 100644 --- a/usr/src/sys/kern/kern_proc.c +++ b/usr/src/sys/kern/kern_proc.c @@ -1,4 +1,4 @@ -/* kern_proc.c 4.27 82/07/22 */ +/* kern_proc.c 4.28 82/07/24 */ #include "../h/param.h" #include "../h/systm.h" @@ -20,6 +20,7 @@ #include "../h/vlimit.h" #include "../h/file.h" #include "../h/quota.h" +#include "../h/descrip.h" /* * exec system call, with and without environments. @@ -301,9 +302,8 @@ register struct inode *ip; register struct file *fp; for (fp = file; fp < fileNFILE; fp++) { - if (fp->f_flag & FSOCKET) - continue; - if (fp->f_inode == ip && (fp->f_flag&FWRITE)) { + if (fp->f_type == DTYPE_FILE && + fp->f_inode == ip && (fp->f_flag&FWRITE)) { u.u_error = ETXTBSY; goto bad; } @@ -758,35 +758,49 @@ out: u.u_r.r_val2 = 0; } +spgrp(top, npgrp) +register struct proc *top; +{ + register struct proc *pp, *p; + int f = 0; + + for (p = top; npgrp == -1 || u.u_uid == p->p_uid || + !u.u_uid || inferior(p); p = pp) { + if (npgrp == -1) { +#define bit(a) (1<<(a-1)) + p->p_sig &= ~(bit(SIGTSTP)|bit(SIGTTIN)|bit(SIGTTOU)); + } else + p->p_pgrp = npgrp; + f++; + /* + * Search for children. + */ + for (pp = proc; pp < procNPROC; pp++) + if (pp->p_pptr == p) + goto cont; + /* + * Search for siblings. + */ + for (; p != top; p = p->p_pptr) + for (pp = p + 1; pp < procNPROC; pp++) + if (pp->p_pptr == p->p_pptr) + goto cont; + break; + cont: + ; + } + return (f); +} + /* - * break system call. - * -- bad planning: "break" is a dirty word in C. + * Is p an inferior of the current process? */ -sbreak() +inferior(p) +register struct proc *p; { - struct a { - char *nsiz; - }; - register int n, d; - - /* - * set n to new data size - * set d to new-old - */ - n = btoc(((struct a *)u.u_ap)->nsiz); - if (!u.u_sep) - n -= ctos(u.u_tsize) * stoc(1); - if (n < 0) - n = 0; - d = clrnd(n - u.u_dsize); - if (ctob(u.u_dsize+d) > u.u_limit[LIM_DATA]) { - u.u_error = ENOMEM; - return; - } - if (chksize(u.u_tsize, u.u_dsize+d, u.u_ssize)) - return; - if (swpexpand(u.u_dsize+d, u.u_ssize, &u.u_dmap, &u.u_smap)==0) - return; - expand(d, P0BR); + for (; p != u.u_procp; p = p->p_pptr) + if (p->p_ppid == 0) + return (0); + return (1); } diff --git a/usr/src/sys/kern/kern_prot.c b/usr/src/sys/kern/kern_prot.c index 520e631fff..d8113e2539 100644 --- a/usr/src/sys/kern/kern_prot.c +++ b/usr/src/sys/kern/kern_prot.c @@ -1,9 +1,11 @@ -/* kern_prot.c 5.2 82/07/22 */ +/* kern_prot.c 5.3 82/07/24 */ /* - * System calls related to protection + * System calls related to processes and protection */ +/* NEED ALLOCATION AND PROTECTION MECHANISM FOR PROCESS GROUPS */ + #include "../h/param.h" #include "../h/systm.h" #include "../h/dir.h" @@ -22,6 +24,30 @@ #include "../h/mount.h" #include "../h/quota.h" +getpid() +{ + + u.u_r.r_val1 = u.u_procp->p_pid; + u.u_r.r_val2 = u.u_procp->p_ppid; +} + +getpgrp() +{ + register struct a { + int pid; + } *uap = (struct a *)u.u_ap; + register struct proc *p; + + if (uap->pid == 0) + uap->pid = u.u_procp->p_pid; + p = pfind(uap->pid); + if (p == 0) { + u.u_error = ESRCH; + return; + } + u.u_r.r_val1 = p->p_pgrp; +} + getuid() { @@ -29,6 +55,48 @@ getuid() u.u_r.r_val2 = u.u_uid; } +getgid() +{ + + u.u_r.r_val1 = u.u_rgid; + u.u_r.r_val2 = u.u_gid; +} + +getgrp() +{ + register struct a { + int *gidset; + } *uap = (struct a *)u.u_ap; + + if (copyout((caddr_t)u.u_grps, (caddr_t)uap->gidset, + sizeof (u.u_grps))) { + u.u_error = EFAULT; + return; + } +} + +setpgrp() +{ + register struct proc *p; + register struct a { + int pid; + int pgrp; + } *uap = (struct a *)u.u_ap; + + if (uap->pid == 0) + uap->pid = u.u_procp->p_pid; + p = pfind(uap->pid); + if (p == 0) { + u.u_error = ESRCH; + return; + } + if (p->p_uid != u.u_uid && u.u_uid && !inferior(p)) { + u.u_error = EPERM; + return; + } + p->p_pgrp = uap->pgrp; +} + setuid() { register uid; @@ -51,13 +119,6 @@ setuid() } } -getgid() -{ - - u.u_r.r_val1 = u.u_rgid; - u.u_r.r_val2 = u.u_gid; -} - setgid() { register gid; @@ -72,3 +133,78 @@ setgid() u.u_rgid = gid; } } + +setgrp() +{ + register struct a { + int *gidset; + } *uap = (struct a *)u.u_ap; + + if (suser()) + return; + if (copyin((caddr_t)uap->gidset, (caddr_t)u.u_grps, + sizeof (u.u_grps))) { + u.u_error = EFAULT; + return; + } +} + +/* BEGIN DEFUNCT */ +osetgrp() +{ + register struct a { + int *ngrps; + int *ogrps; + } *uap = (struct a *)u.u_ap; + int thegroups[NGRPS/(sizeof(int)*8)]; + + if (uap->ogrps && copyout((caddr_t)u.u_grps, (caddr_t)uap->ogrps, + sizeof (thegroups))) { + u.u_error = EFAULT; + return; + } + if (uap->ngrps == 0) + return; + if (copyin((caddr_t)uap->ngrps, (caddr_t)thegroups, + sizeof (thegroups))) { + u.u_error = EFAULT; + return; + } + if (suser()) + bcopy((caddr_t)thegroups, (caddr_t)u.u_grps, sizeof (u.u_grps)); +} + +/* + * Pid of zero implies current process. + * Pgrp -1 is getpgrp system call returning + * current process group. + */ +osetpgrp() +{ + register struct proc *p; + register struct a { + int pid; + int pgrp; + } *uap; + + uap = (struct a *)u.u_ap; + if (uap->pid == 0) + p = u.u_procp; + else { + p = pfind(uap->pid); + if (p == 0) { + u.u_error = ESRCH; + return; + } + } + if (uap->pgrp <= 0) { + u.u_r.r_val1 = p->p_pgrp; + return; + } + if (p->p_uid != u.u_uid && u.u_uid && !inferior(p)) { + u.u_error = EPERM; + return; + } + p->p_pgrp = uap->pgrp; +} +/* END DEFUNCT */ diff --git a/usr/src/sys/kern/kern_resource.c b/usr/src/sys/kern/kern_resource.c index 1358ee8177..bbe6284b51 100644 --- a/usr/src/sys/kern/kern_resource.c +++ b/usr/src/sys/kern/kern_resource.c @@ -1,4 +1,4 @@ -/* kern_resource.c 4.9 82/07/12 */ +/* kern_resource.c 4.10 82/07/24 */ #include "../h/param.h" #include "../h/systm.h" @@ -8,8 +8,13 @@ #include "../h/inode.h" #include "../h/proc.h" #include "../h/seg.h" +#include "../h/fs.h" struct inode *acctp; +struct inode *savacctp; + +long acctlow = 2; /* stop accounting when < 2% data space left */ +long accthigh = 4; /* resume when space risen to > 4% */ /* * Perform process accounting functions. @@ -23,6 +28,10 @@ sysacct() uap = (struct a *)u.u_ap; if (suser()) { + if (savacctp) { + acctp = savacctp; + savacctp = NULL; + } if (uap->fname==NULL) { if (ip = acctp) { irele(ip); @@ -57,8 +66,21 @@ acct() off_t siz; register struct acct *ap = &acctbuf; + if (savacctp && savacctp->i_fs->fs_cstotal.cs_nbfree > + accthigh * savacctp->i_fs->fs_dsize / 100) { + acctp = savacctp; + savacctp = NULL; + printf("Accounting resumed\n"); + } if ((ip=acctp)==NULL) return; + if (acctp->i_fs->fs_cstotal.cs_nbfree < + acctlow * acctp->i_fs->fs_dsize / 100) { + savacctp = acctp; + acctp = NULL; + printf("Accounting suspended\n"); + return; + } ilock(ip); for (i=0; iac_comm); i++) ap->ac_comm[i] = u.u_comm[i]; @@ -112,3 +134,40 @@ register long t; } return((exp<<13) + t); } + +vtimes() +{ + register struct a { + struct vtimes *par_vm; + struct vtimes *ch_vm; + } *uap = (struct a *)u.u_ap; + + if (uap->par_vm == 0) + goto onlych; + if (copyout((caddr_t)&u.u_vm, (caddr_t)uap->par_vm, + sizeof(struct vtimes)) < 0) + u.u_error = EFAULT; +onlych: + if (uap->ch_vm == 0) + return; + if (copyout((caddr_t)&u.u_cvm, (caddr_t)uap->ch_vm, + sizeof(struct vtimes)) < 0) + u.u_error = EFAULT; +} + +vmsadd(vp, wp) + register struct vtimes *vp, *wp; +{ + + vp->vm_utime += wp->vm_utime; + vp->vm_stime += wp->vm_stime; + vp->vm_nswap += wp->vm_nswap; + vp->vm_idsrss += wp->vm_idsrss; + vp->vm_ixrss += wp->vm_ixrss; + if (vp->vm_maxrss < wp->vm_maxrss) + vp->vm_maxrss = wp->vm_maxrss; + vp->vm_majflt += wp->vm_majflt; + vp->vm_minflt += wp->vm_minflt; + vp->vm_inblk += wp->vm_inblk; + vp->vm_oublk += wp->vm_oublk; +} diff --git a/usr/src/sys/kern/kern_sig.c b/usr/src/sys/kern/kern_sig.c index 3a89c2c990..7f88677a13 100644 --- a/usr/src/sys/kern/kern_sig.c +++ b/usr/src/sys/kern/kern_sig.c @@ -1,4 +1,4 @@ -/* kern_sig.c 5.1 82/07/15 */ +/* kern_sig.c 5.2 82/07/24 */ #include "../h/param.h" #include "../h/systm.h" @@ -22,70 +22,35 @@ #include "../h/vlimit.h" #include "../h/acct.h" -ssig() +/* KILL CODE SHOULDNT KNOW ABOUT PROCESS INTERNALS !?! */ + +sigvec() +{ + +} + +sigblock() +{ + +} + +sigsetmask() { - register int (*f)(); - struct a { - int signo; - int (*fun)(); - } *uap; - register struct proc *p = u.u_procp; - register a; - long sigmask; - uap = (struct a *)u.u_ap; - a = uap->signo & SIGNUMMASK; - f = uap->fun; - if (a<=0 || a>=NSIG || a==SIGKILL || a==SIGSTOP || - a==SIGCONT && (f == SIG_IGN || f == SIG_HOLD)) { - u.u_error = EINVAL; - return; - } - if ((uap->signo &~ SIGNUMMASK) || (f != SIG_DFL && f != SIG_IGN && - SIGISDEFER(f))) - u.u_procp->p_flag |= SNUSIG; - /* - * Don't clobber registers if we are to simulate - * a ret+rti. - */ - if ((uap->signo&SIGDORTI) == 0) - u.u_r.r_val1 = (int)u.u_signal[a]; - /* - * Change setting atomically. - */ - (void) spl6(); - sigmask = 1L << (a-1); - if (u.u_signal[a] == SIG_IGN) - p->p_sig &= ~sigmask; /* never to be seen again */ - u.u_signal[a] = f; - if (f != SIG_DFL && f != SIG_IGN && f != SIG_HOLD) - f = SIG_CATCH; - if ((int)f & 1) - p->p_siga0 |= sigmask; - else - p->p_siga0 &= ~sigmask; - if ((int)f & 2) - p->p_siga1 |= sigmask; - else - p->p_siga1 &= ~sigmask; - (void) spl0(); - /* - * Now handle options. - */ - if (uap->signo & SIGDOPAUSE) { - /* - * Simulate a PDP11 style wait instrution which - * atomically lowers priority, enables interrupts - * and hangs. - */ - pause(); - /*NOTREACHED*/ - } - if (uap->signo & SIGDORTI) - u.u_eosys = SIMULATERTI; } -kill() +sigpause() +{ + +} + +sigstack() +{ + +} + +/* BEGIN DEFUNCT */ +okill() { register struct proc *p; register a, sig; @@ -152,25 +117,68 @@ kill() u.u_error = ESRCH; } -/* - * Priority for tracing - */ -#define IPCPRI PZERO +ossig() +{ + register int (*f)(); + struct a { + int signo; + int (*fun)(); + } *uap; + register struct proc *p = u.u_procp; + register a; + long sigmask; -/* - * Tracing variables. - * Used to pass trace command from - * parent to child being traced. - * This data base cannot be - * shared and is locked - * per user. - */ -struct { - int ip_lock; - int ip_req; - int *ip_addr; - int ip_data; -} ipc; + uap = (struct a *)u.u_ap; + a = uap->signo & SIGNUMMASK; + f = uap->fun; + if (a<=0 || a>=NSIG || a==SIGKILL || a==SIGSTOP || + a==SIGCONT && (f == SIG_IGN || f == SIG_HOLD)) { + u.u_error = EINVAL; + return; + } + if ((uap->signo &~ SIGNUMMASK) || (f != SIG_DFL && f != SIG_IGN && + SIGISDEFER(f))) + u.u_procp->p_flag |= SNUSIG; + /* + * Don't clobber registers if we are to simulate + * a ret+rti. + */ + if ((uap->signo&SIGDORTI) == 0) + u.u_r.r_val1 = (int)u.u_signal[a]; + /* + * Change setting atomically. + */ + (void) spl6(); + sigmask = 1L << (a-1); + if (u.u_signal[a] == SIG_IGN) + p->p_sig &= ~sigmask; /* never to be seen again */ + u.u_signal[a] = f; + if (f != SIG_DFL && f != SIG_IGN && f != SIG_HOLD) + f = SIG_CATCH; + if ((int)f & 1) + p->p_siga0 |= sigmask; + else + p->p_siga0 &= ~sigmask; + if ((int)f & 2) + p->p_siga1 |= sigmask; + else + p->p_siga1 &= ~sigmask; + (void) spl0(); + /* + * Now handle options. + */ + if (uap->signo & SIGDOPAUSE) { + /* + * Simulate a PDP11 style wait instrution which + * atomically lowers priority, enables interrupts + * and hangs. + */ + opause(); + /*NOTREACHED*/ + } + if (uap->signo & SIGDORTI) + u.u_eosys = SIMULATERTI; +} /* * Send the specified signal to @@ -551,21 +559,6 @@ send: return (sig); } -#ifndef vax -ffs(mask) - register long mask; -{ - register int i; - - for(i=1; i>= 1; - } - return (0); -} -#endif - /* * Put the argument process into the stopped * state and notify the parent via wakeup and/or signal. @@ -716,184 +709,32 @@ core() iput(ip); return (u.u_error==0); } - /* - * grow the stack to include the SP - * true return if successful. + * alarm clock signal */ -grow(sp) - unsigned sp; -{ - register si; - - if (sp >= USRSTACK-ctob(u.u_ssize)) - return (0); - si = clrnd(btoc((USRSTACK-sp)) - u.u_ssize + SINCR); - if (ctob(u.u_ssize+si) > u.u_limit[LIM_STACK]) - return (0); - if (chksize(u.u_tsize, u.u_dsize, u.u_ssize+si)) - return (0); - if (swpexpand(u.u_dsize, u.u_ssize+si, &u.u_dmap, &u.u_smap)==0) - return (0); - - expand(si, P1BR); - return (1); -} - -/* - * sys-trace system call. - */ -ptrace() +oalarm() { register struct proc *p; + register c; register struct a { - int req; - int pid; - int *addr; - int data; + int deltat; } *uap; uap = (struct a *)u.u_ap; - if (uap->req <= 0) { - u.u_procp->p_flag |= STRC; - return; - } - p = pfind(uap->pid); - if (p == 0 || p->p_stat != SSTOP || p->p_ppid != u.u_procp->p_pid) { - u.u_error = ESRCH; - return; - } - while (ipc.ip_lock) - sleep((caddr_t)&ipc, IPCPRI); - ipc.ip_lock = p->p_pid; - ipc.ip_data = uap->data; - ipc.ip_addr = uap->addr; - ipc.ip_req = uap->req; - p->p_flag &= ~SWTED; - while (ipc.ip_req > 0) { - if (p->p_stat==SSTOP) - setrun(p); - sleep((caddr_t)&ipc, IPCPRI); - } - u.u_r.r_val1 = ipc.ip_data; - if (ipc.ip_req < 0) - u.u_error = EIO; - ipc.ip_lock = 0; - wakeup((caddr_t)&ipc); + p = u.u_procp; + c = p->p_clktim; + p->p_clktim = uap->deltat; + u.u_r.r_val1 = c; } -int ipcreg[] = {R0,R1,R2,R3,R4,R5,R6,R7,R8,R9,R10,R11,AP,FP,SP,PC}; /* - * Code that the child process - * executes to implement the command - * of the parent process in tracing. + * indefinite wait. + * no one should wakeup(&u) */ -procxmt() +opause() { - register int i; - register *p; - register struct text *xp; - if (ipc.ip_lock != u.u_procp->p_pid) - return (0); - u.u_procp->p_slptime = 0; - i = ipc.ip_req; - ipc.ip_req = 0; - switch (i) { - - /* read user I */ - case 1: - if (!useracc((caddr_t)ipc.ip_addr, 4, B_READ)) - goto error; - ipc.ip_data = fuiword((caddr_t)ipc.ip_addr); - break; - - /* read user D */ - case 2: - if (!useracc((caddr_t)ipc.ip_addr, 4, B_READ)) - goto error; - ipc.ip_data = fuword((caddr_t)ipc.ip_addr); - break; - - /* read u */ - case 3: - i = (int)ipc.ip_addr; - if (i<0 || i >= ctob(UPAGES)) - goto error; - ipc.ip_data = ((physadr)&u)->r[i>>2]; - break; - - /* write user I */ - /* Must set up to allow writing */ - case 4: - /* - * If text, must assure exclusive use - */ - if (xp = u.u_procp->p_textp) { - if (xp->x_count!=1 || xp->x_iptr->i_mode&ISVTX) - goto error; - xp->x_iptr->i_flag &= ~ITEXT; - } - i = -1; - if (chgprot((caddr_t)ipc.ip_addr, RW) && - chgprot((caddr_t)ipc.ip_addr+(sizeof(int)-1), RW)) - i = suiword((caddr_t)ipc.ip_addr, ipc.ip_data); - (void) chgprot((caddr_t)ipc.ip_addr, RO); - (void) chgprot((caddr_t)ipc.ip_addr+(sizeof(int)-1), RO); - if (i < 0) - goto error; - if (xp) - xp->x_flag |= XWRIT; - break; - - /* write user D */ - case 5: - if (suword((caddr_t)ipc.ip_addr, 0) < 0) - goto error; - (void) suword((caddr_t)ipc.ip_addr, ipc.ip_data); - break; - - /* write u */ - case 6: - i = (int)ipc.ip_addr; - p = (int *)&((physadr)&u)->r[i>>2]; - for (i=0; i<16; i++) - if (p == &u.u_ar0[ipcreg[i]]) - goto ok; - if (p == &u.u_ar0[PS]) { - ipc.ip_data |= PSL_CURMOD|PSL_PRVMOD; - ipc.ip_data &= ~PSL_USERCLR; - goto ok; - } - goto error; - - ok: - *p = ipc.ip_data; - break; - - /* set signal and continue */ - /* one version causes a trace-trap */ - case 9: - case 7: - if ((int)ipc.ip_addr != 1) - u.u_ar0[PC] = (int)ipc.ip_addr; - if ((unsigned)ipc.ip_data > NSIG) - goto error; - u.u_procp->p_cursig = ipc.ip_data; /* see issig */ - if (i == 9) - u.u_ar0[PS] |= PSL_T; - wakeup((caddr_t)&ipc); - return (1); - - /* force exit */ - case 8: - wakeup((caddr_t)&ipc); - exit(u.u_procp->p_cursig); - - default: - error: - ipc.ip_req = -1; - } - wakeup((caddr_t)&ipc); - return (0); + for (;;) + sleep((caddr_t)&u, PSLEP); } + diff --git a/usr/src/sys/kern/kern_time.c b/usr/src/sys/kern/kern_time.c index 18dfa9ca4e..3647231655 100644 --- a/usr/src/sys/kern/kern_time.c +++ b/usr/src/sys/kern/kern_time.c @@ -1,4 +1,4 @@ -/* kern_time.c 5.1 82/07/15 */ +/* kern_time.c 5.2 82/07/24 */ #include "../h/param.h" #include "../h/systm.h" @@ -17,11 +17,25 @@ #include "../h/buf.h" #include "../h/mount.h" -/* - * return the current time (old-style entry) - */ -gtime() +rtime() +{ + +} + +rusage() { + +} + +itimer() +{ + +} + +/* BEGIN DEPRECATED */ +ogtime() +{ + u.u_r.r_time = time; if (clkwrap()) clkset(); @@ -31,7 +45,7 @@ gtime() * New time entry-- return TOD with milliseconds, timezone, * DST flag */ -ftime() +oftime() { register struct a { struct timeb *tp; @@ -56,6 +70,7 @@ ftime() if (clkwrap()) clkset(); } +/* END DEPRECATED */ /* * Set the time diff --git a/usr/src/sys/kern/subr_xxx.c b/usr/src/sys/kern/subr_xxx.c index 281c5bbe49..d497c1c5c7 100644 --- a/usr/src/sys/kern/subr_xxx.c +++ b/usr/src/sys/kern/subr_xxx.c @@ -1,4 +1,4 @@ -/* subr_xxx.c 4.12 82/07/15 */ +/* subr_xxx.c 4.13 82/07/24 */ #include "../h/param.h" #include "../h/systm.h" @@ -172,3 +172,18 @@ ffs(mask) return (0); } #endif +#ifndef vax +ffs(mask) + register long mask; +{ + register int i; + + for(i=1; i>= 1; + } + return (0); +} +#endif + diff --git a/usr/src/sys/kern/sys_generic.c b/usr/src/sys/kern/sys_generic.c index ca3ef369e2..30b6ed0984 100644 --- a/usr/src/sys/kern/sys_generic.c +++ b/usr/src/sys/kern/sys_generic.c @@ -1,10 +1,11 @@ -/* sys_generic.c 5.2 82/07/22 */ +/* sys_generic.c 5.3 82/07/24 */ #include "../h/param.h" #include "../h/systm.h" #include "../h/dir.h" #include "../h/user.h" #include "../h/tty.h" +#include "../h/fcntl.h" #include "../h/file.h" #include "../h/inode.h" #include "../h/buf.h" @@ -22,6 +23,7 @@ #else #define CHARGE(nothing) #endif +#include "../h/descrip.h" /* * Read system call. @@ -52,7 +54,7 @@ read() if ((u.u_procp->p_flag&SNUSIG) && setjmp(u.u_qsav)) { if (u.u_count == uap->count) u.u_eosys = RESTARTSYS; - } else if (fp->f_flag & FSOCKET) + } else if (fp->f_type == DTYPE_SOCKET) u.u_error = soreceive(fp->f_socket, (struct sockaddr *)0); else { ip = fp->f_inode; @@ -97,10 +99,12 @@ write() if ((u.u_procp->p_flag&SNUSIG) && setjmp(u.u_qsav)) { if (u.u_count == uap->count) u.u_eosys = RESTARTSYS; - } else if (fp->f_flag & FSOCKET) + } else if (fp->f_type == DTYPE_SOCKET) u.u_error = sosend(fp->f_socket, (struct sockaddr *)0); else { ip = fp->f_inode; + if (fp->f_flag & O_APPEND) + fp->f_offset = ip->i_size; u.u_offset = fp->f_offset; if ((ip->i_mode&IFMT) == IFREG) { ilock(ip); @@ -113,6 +117,15 @@ write() u.u_r.r_val1 = uap->count - u.u_count; } +readv() +{ + +} + +writev() +{ + +} /* * Ioctl system call @@ -146,7 +159,7 @@ ioctl() u.u_pofile[uap->fdes] &= ~EXCLOSE; return; } - if (fp->f_flag & FSOCKET) { + if (fp->f_type == DTYPE_SOCKET) { soioctl(fp->f_socket, uap->cmd, uap->cmarg); return; } diff --git a/usr/src/sys/kern/sys_process.c b/usr/src/sys/kern/sys_process.c index 69b816a502..9d999f13b1 100644 --- a/usr/src/sys/kern/sys_process.c +++ b/usr/src/sys/kern/sys_process.c @@ -1,4 +1,4 @@ -/* sys_process.c 5.1 82/07/15 */ +/* sys_process.c 5.2 82/07/24 */ #include "../h/param.h" #include "../h/systm.h" @@ -17,3 +17,181 @@ #include "../h/vlimit.h" #include "../h/acct.h" + +/* + * Priority for tracing + */ +#define IPCPRI PZERO + +/* + * Tracing variables. + * Used to pass trace command from + * parent to child being traced. + * This data base cannot be + * shared and is locked + * per user. + */ +struct { + int ip_lock; + int ip_req; + int *ip_addr; + int ip_data; +} ipc; + +/* + * sys-trace system call. + */ +ptrace() +{ + register struct proc *p; + register struct a { + int req; + int pid; + int *addr; + int data; + } *uap; + + uap = (struct a *)u.u_ap; + if (uap->req <= 0) { + u.u_procp->p_flag |= STRC; + return; + } + p = pfind(uap->pid); + if (p == 0 || p->p_stat != SSTOP || p->p_ppid != u.u_procp->p_pid) { + u.u_error = ESRCH; + return; + } + while (ipc.ip_lock) + sleep((caddr_t)&ipc, IPCPRI); + ipc.ip_lock = p->p_pid; + ipc.ip_data = uap->data; + ipc.ip_addr = uap->addr; + ipc.ip_req = uap->req; + p->p_flag &= ~SWTED; + while (ipc.ip_req > 0) { + if (p->p_stat==SSTOP) + setrun(p); + sleep((caddr_t)&ipc, IPCPRI); + } + u.u_r.r_val1 = ipc.ip_data; + if (ipc.ip_req < 0) + u.u_error = EIO; + ipc.ip_lock = 0; + wakeup((caddr_t)&ipc); +} + +int ipcreg[] = {R0,R1,R2,R3,R4,R5,R6,R7,R8,R9,R10,R11,AP,FP,SP,PC}; +/* + * Code that the child process + * executes to implement the command + * of the parent process in tracing. + */ +procxmt() +{ + register int i; + register *p; + register struct text *xp; + + if (ipc.ip_lock != u.u_procp->p_pid) + return (0); + u.u_procp->p_slptime = 0; + i = ipc.ip_req; + ipc.ip_req = 0; + switch (i) { + + /* read user I */ + case 1: + if (!useracc((caddr_t)ipc.ip_addr, 4, B_READ)) + goto error; + ipc.ip_data = fuiword((caddr_t)ipc.ip_addr); + break; + + /* read user D */ + case 2: + if (!useracc((caddr_t)ipc.ip_addr, 4, B_READ)) + goto error; + ipc.ip_data = fuword((caddr_t)ipc.ip_addr); + break; + + /* read u */ + case 3: + i = (int)ipc.ip_addr; + if (i<0 || i >= ctob(UPAGES)) + goto error; + ipc.ip_data = ((physadr)&u)->r[i>>2]; + break; + + /* write user I */ + /* Must set up to allow writing */ + case 4: + /* + * If text, must assure exclusive use + */ + if (xp = u.u_procp->p_textp) { + if (xp->x_count!=1 || xp->x_iptr->i_mode&ISVTX) + goto error; + xp->x_iptr->i_flag &= ~ITEXT; + } + i = -1; + if (chgprot((caddr_t)ipc.ip_addr, RW) && + chgprot((caddr_t)ipc.ip_addr+(sizeof(int)-1), RW)) + i = suiword((caddr_t)ipc.ip_addr, ipc.ip_data); + (void) chgprot((caddr_t)ipc.ip_addr, RO); + (void) chgprot((caddr_t)ipc.ip_addr+(sizeof(int)-1), RO); + if (i < 0) + goto error; + if (xp) + xp->x_flag |= XWRIT; + break; + + /* write user D */ + case 5: + if (suword((caddr_t)ipc.ip_addr, 0) < 0) + goto error; + (void) suword((caddr_t)ipc.ip_addr, ipc.ip_data); + break; + + /* write u */ + case 6: + i = (int)ipc.ip_addr; + p = (int *)&((physadr)&u)->r[i>>2]; + for (i=0; i<16; i++) + if (p == &u.u_ar0[ipcreg[i]]) + goto ok; + if (p == &u.u_ar0[PS]) { + ipc.ip_data |= PSL_CURMOD|PSL_PRVMOD; + ipc.ip_data &= ~PSL_USERCLR; + goto ok; + } + goto error; + + ok: + *p = ipc.ip_data; + break; + + /* set signal and continue */ + /* one version causes a trace-trap */ + case 9: + case 7: + if ((int)ipc.ip_addr != 1) + u.u_ar0[PC] = (int)ipc.ip_addr; + if ((unsigned)ipc.ip_data > NSIG) + goto error; + u.u_procp->p_cursig = ipc.ip_data; /* see issig */ + if (i == 9) + u.u_ar0[PS] |= PSL_T; + wakeup((caddr_t)&ipc); + return (1); + + /* force exit */ + case 8: + wakeup((caddr_t)&ipc); + exit(u.u_procp->p_cursig); + + default: + error: + ipc.ip_req = -1; + } + wakeup((caddr_t)&ipc); + return (0); +} diff --git a/usr/src/sys/kern/tty.c b/usr/src/sys/kern/tty.c index e0b7538985..b0a5156be6 100644 --- a/usr/src/sys/kern/tty.c +++ b/usr/src/sys/kern/tty.c @@ -1,4 +1,4 @@ -/* tty.c 4.23 82/07/15 */ +/* tty.c 4.24 82/07/24 */ /* * TTY subroutines common to more than one line discipline @@ -615,3 +615,821 @@ win: return (1); } +#define OBUFSIZ 100 + +/* + * routine called on opens while tp->t_line == NTTYDISC + * establishes a process group for distribution of + * quits and interrupts from the tty. + * (actually, pp->p_pgrp can't be 0 when this routine + * is called since NTTYDISC is not the default discipline) + */ +ttyopen(dev, tp) +dev_t dev; +register struct tty *tp; +{ + register struct proc *pp; + + pp = u.u_procp; + tp->t_dev = dev; + if(pp->p_pgrp == 0) { + u.u_ttyp = tp; + u.u_ttyd = dev; + if (tp->t_pgrp == 0) + tp->t_pgrp = pp->p_pid; + pp->p_pgrp = tp->t_pgrp; + } + tp->t_state &= ~TS_WOPEN; + tp->t_state |= TS_ISOPEN; + if (tp->t_line != NTTYDISC) + wflushtty(tp); +} + +/* + * clean tp on last close + */ +ttyclose(tp) +register struct tty *tp; +{ + + if (tp->t_line) { + wflushtty(tp); + tp->t_line = 0; + return; + } + tp->t_pgrp = 0; + wflushtty(tp); + tp->t_state = 0; +} + +/* + * reinput pending characters after state switch + * call at spl5(). + */ +ttypend(tp) +register struct tty *tp; +{ + struct clist tq; + register c; + + tp->t_local &= ~LPENDIN; + tp->t_lstate |= LSTYPEN; + tq = tp->t_rawq; + tp->t_rawq.c_cc = 0; + tp->t_rawq.c_cf = tp->t_rawq.c_cl = 0; + while ((c = getc(&tq)) >= 0) + ttyinput(c, tp); + tp->t_lstate &= ~LSTYPEN; +} + +/* + * Place a character on raw TTY input queue, putting in delimiters + * and waking up top half as needed. + * Also echo if required. + * The arguments are the character and the appropriate + * tty structure. + */ +ttyinput(c, tp) +register c; +register struct tty *tp; +{ + register int t_flags; + int i; + + if (tp->t_local&LPENDIN) + ttypend(tp); + tk_nin++; + c &= 0377; + t_flags = tp->t_flags; + if (t_flags&TANDEM) + ttyblock(tp); + if ((t_flags&RAW)==0) { + if ((tp->t_lstate&LSTYPEN) == 0) + c &= 0177; + /* check for literal nexting very first */ + if (tp->t_lstate&LSLNCH) { + c |= 0200; + tp->t_lstate &= ~LSLNCH; + } + if (tp->t_line == NTTYDISC && c==tlun.t_lnextc) { + if (tp->t_flags&ECHO) + ttyout("^\b", tp); + tp->t_lstate |= LSLNCH; + /* check for output control functions */ + } else if (c==tun.t_stopc) { + if ((tp->t_state&TS_TTSTOP)==0) { + tp->t_state |= TS_TTSTOP; + (*cdevsw[major(tp->t_dev)].d_stop)(tp, 0); + return; + } + if (c!=tun.t_startc) + return; + } else if (c==tun.t_startc) { + tp->t_state &= ~TS_TTSTOP; + tp->t_local &= ~LFLUSHO; + ttstart(tp); + return; + } else if (tp->t_line == NTTYDISC && c==tlun.t_flushc) { + if (tp->t_local & LFLUSHO) + tp->t_local &= ~LFLUSHO; + else { + flushtty(tp, FWRITE); + ttyecho(c, tp); + if (tp->t_rawq.c_cc+tp->t_canq.c_cc) + ttyretype(tp); + tp->t_local |= LFLUSHO; + } + ttstart(tp); + return; + } else if (c==tun.t_intrc || c==tun.t_quitc || + (tp->t_line == NTTYDISC && c==tlun.t_suspc)) { + if ((tp->t_local & LNOFLSH) == 0) + flushtty(tp, + c==tlun.t_suspc ? FREAD : FREAD|FWRITE); + ttyecho(c, tp); + c = c==tun.t_intrc ? SIGINT : + ((c==tun.t_quitc) ? SIGQUIT : SIGTSTP); + ttsignal(tp, c); + /* check for buffer editing functions - cooked mode */ + } else if ((t_flags&CBREAK) == 0) { + if ((tp->t_lstate&LSQUOT) && + (c==tp->t_erase||c==tp->t_kill)) { + ttyrub(unputc(&tp->t_rawq), tp); + c |= 0200; + } + if (c==tp->t_erase) { + if (tp->t_rawq.c_cc) + ttyrub(unputc(&tp->t_rawq), tp); + } else if (c==tp->t_kill) { + if (tp->t_local&LCRTKIL && + tp->t_rawq.c_cc == tp->t_rocount) { + while (tp->t_rawq.c_cc) + ttyrub(unputc(&tp->t_rawq), tp); + } else { + ttyecho(c, tp); + ttyecho('\n', tp); + while (getc(&tp->t_rawq) > 0) + ; + tp->t_rocount = 0; + } + tp->t_lstate = 0; + } else if (tp->t_line == NTTYDISC && c==tlun.t_werasc) { + if (tp->t_rawq.c_cc == 0) + goto out; + do { + c = unputc(&tp->t_rawq); + if (c != ' ' && c != '\t') + goto erasenb; + ttyrub(c, tp); + } while (tp->t_rawq.c_cc); + goto out; + erasenb: + do { + ttyrub(c, tp); + if (tp->t_rawq.c_cc == 0) + goto out; + c = unputc(&tp->t_rawq); + } while (c != ' ' && c != '\t'); + (void) putc(c, &tp->t_rawq); + } else if (tp->t_line == NTTYDISC && c==tlun.t_rprntc) { + ttyretype(tp); + /* check for cooked mode input buffer overflow */ + } else if (tp->t_rawq.c_cc+tp->t_canq.c_cc >= TTYHOG) { + ; + /* put data char in q for user and wakeup if a break char */ + } else if (putc(c, &tp->t_rawq) >= 0) { + if (tp->t_rawq.c_cc+tp->t_canq.c_cc==TTYHOG + && tp->t_line == NTTYDISC) + (void) ttyoutput(CTRL(g), tp); + if (!ttbreakc(c, tp)) { + if (tp->t_rocount++ == 0) + tp->t_rocol = tp->t_col; + } else { + tp->t_rocount = 0; + catq(&tp->t_rawq, &tp->t_canq); + /* IF (TP->T_CHAN) (VOID) SDATA(TP->T_CHAN); */ + ttwakeup(tp); + } + tp->t_lstate &= ~LSQUOT; + if (c == '\\') + tp->t_lstate |= LSQUOT; + if (tp->t_lstate&LSERASE) { + tp->t_lstate &= ~LSERASE; + (void) ttyoutput('/', tp); + } + i = tp->t_col; + ttyecho(c, tp); + if (c==tun.t_eofc && tp->t_flags&ECHO) { + i = MIN(2, tp->t_col - i); + while (i > 0) { + (void) ttyoutput('\b', tp); + i--; + } + } + } + /* CBREAK mode */ + } else if (tp->t_rawq.c_cc > TTYHOG) { + if (tp->t_outq.c_cc < TTHIWAT(tp) && + tp->t_line == NTTYDISC) + (void) ttyoutput(CTRL(g), tp); + } else if (putc(c, &tp->t_rawq) >= 0) { + ttwakeup(tp); + ttyecho(c, tp); + } + /* RAW mode */ + } else if (tp->t_rawq.c_cc > TTYHOG) + flushtty(tp, FREAD|FWRITE); + else { + if (putc(c, &tp->t_rawq) >= 0) + ttwakeup(tp); + ttyecho(c, tp); + } +out: + if (tp->t_local & LDECCTQ && tp->t_state & TS_TTSTOP && + tun.t_startc != tun.t_stopc) + return; + tp->t_state &= ~TS_TTSTOP; + tp->t_local &= ~LFLUSHO; + ttstart(tp); +} + +/* + * put character on TTY output queue, adding delays, + * expanding tabs, and handling the CR/NL bit. + * It is called both from the top half for output, and from + * interrupt level for echoing. + * The arguments are the character and the tty structure. + * Returns < 0 if putc succeeds, otherwise returns char to resend + * Must be recursive. + */ +ttyoutput(c, tp) + register c; + register struct tty *tp; +{ + register char *colp; + register ctype; + + if (tp->t_flags&RAW || tp->t_local&LLITOUT) { + if (tp->t_local&LFLUSHO) + return (-1); + if (putc(c, &tp->t_outq)) + return(c); + tk_nout++; + return (-1); + } + /* + * Ignore EOT in normal mode to avoid hanging up + * certain terminals. + */ + c &= 0177; + if (c==CEOT && (tp->t_flags&CBREAK)==0) + return (-1); + /* + * Turn tabs to spaces as required + */ + if (c=='\t' && (tp->t_flags&TBDELAY)==XTABS) { + register int s; + + c = 8 - (tp->t_col&7); + if ((tp->t_local&LFLUSHO) == 0) { + s = spl5(); /* don't interrupt tabs */ + c -= b_to_q(" ", c, &tp->t_outq); + tk_nout += c; + splx(s); + } + tp->t_col += c; + return (c ? -1 : '\t'); + } + tk_nout++; + /* + * for upper-case-only terminals, + * generate escapes. + */ + if (tp->t_flags&LCASE) { + colp = "({)}!|^~'`"; + while(*colp++) + if(c == *colp++) { + if (ttyoutput('\\', tp) >= 0) + return (c); + c = colp[-2]; + break; + } + if ('A'<=c && c<='Z') { + if (ttyoutput('\\', tp) >= 0) + return (c); + } else if ('a'<=c && c<='z') + c += 'A' - 'a'; + } + /* + * turn to if desired. + */ + if (c=='\n' && tp->t_flags&CRMOD) + if (ttyoutput('\r', tp) >= 0) + return (c); + if (c=='~' && tp->t_local<ILDE) + c = '`'; + if ((tp->t_local&LFLUSHO) == 0 && putc(c, &tp->t_outq)) + return (c); + /* + * Calculate delays. + * The numbers here represent clock ticks + * and are not necessarily optimal for all terminals. + * The delays are indicated by characters above 0200. + * In raw mode there are no delays and the + * transmission path is 8 bits wide. + */ + colp = &tp->t_col; + ctype = partab[c]; + c = 0; + switch (ctype&077) { + + case ORDINARY: + (*colp)++; + + case CONTROL: + break; + + case BACKSPACE: + if (*colp) + (*colp)--; + break; + + case NEWLINE: + ctype = (tp->t_flags >> 8) & 03; + if(ctype == 1) { /* tty 37 */ + if (*colp) + c = max(((unsigned)*colp>>4) + 3, (unsigned)6); + } else + if(ctype == 2) { /* vt05 */ + c = 6; + } + *colp = 0; + break; + + case TAB: + ctype = (tp->t_flags >> 10) & 03; + if(ctype == 1) { /* tty 37 */ + c = 1 - (*colp | ~07); + if(c < 5) + c = 0; + } + *colp |= 07; + (*colp)++; + break; + + case VTAB: + if(tp->t_flags & VTDELAY) /* tty 37 */ + c = 0177; + break; + + case RETURN: + ctype = (tp->t_flags >> 12) & 03; + if(ctype == 1) { /* tn 300 */ + c = 5; + } else if(ctype == 2) { /* ti 700 */ + c = 10; + } else if(ctype == 3) { /* concept 100 */ + int i; + if ((i = *colp) >= 0) + for (; i<9; i++) + (void) putc(0177, &tp->t_outq); + } + *colp = 0; + } + if(c && (tp->t_local&LFLUSHO) == 0) + (void) putc(c|0200, &tp->t_outq); + return (-1); +} + +/* + * Called from device's read routine after it has + * calculated the tty-structure given as argument. + */ +ttread(tp) +register struct tty *tp; +{ + register struct clist *qp; + register c, first; + + if ((tp->t_state&TS_CARR_ON)==0) + return(0); +loop: + (void) spl5(); + if (tp->t_local&LPENDIN) + ttypend(tp); + (void) spl0(); + while (tp == u.u_ttyp && u.u_procp->p_pgrp != tp->t_pgrp) { + if (u.u_signal[SIGTTIN] == SIG_IGN || + u.u_signal[SIGTTIN] == SIG_HOLD || +/* + (u.u_procp->p_flag&SDETACH) || +*/ + u.u_procp->p_flag&SVFORK) + return (0); + gsignal(u.u_procp->p_pgrp, SIGTTIN); + sleep((caddr_t)&lbolt, TTIPRI); + } + if (tp->t_flags&RAW) { + (void) spl5(); + if (tp->t_rawq.c_cc <= 0) { + if ((tp->t_state&TS_CARR_ON)==0 || + (tp->t_state&TS_NBIO)) { + (void) spl0(); + return (0); + } + sleep((caddr_t)&tp->t_rawq, TTIPRI); + (void) spl0(); + goto loop; + } + (void) spl0(); + while (tp->t_rawq.c_cc && passc(getc(&tp->t_rawq))>=0) + ; + return (0); + } else { + qp = tp->t_flags & CBREAK ? &tp->t_rawq : &tp->t_canq; + (void) spl5(); + if (qp->c_cc <= 0) { + if ((tp->t_state&TS_CARR_ON)==0 || + (tp->t_state&TS_NBIO)) { + (void) spl0(); + return (0); + } + sleep((caddr_t)&tp->t_rawq, TTIPRI); + (void) spl0(); + goto loop; + } + (void) spl0(); + first = 1; + while ((c = getc(qp)) >= 0) { + if (tp->t_flags&CRMOD && c == '\r') + c = '\n'; + if (tp->t_flags&LCASE && c <= 0177) + if (tp->t_lstate&LSBKSL) { + if (maptab[c]) + c = maptab[c]; + tp->t_lstate &= ~LSBKSL; + } else if (c >= 'A' && c <= 'Z') + c += 'a' - 'A'; + else if (c == '\\') { + tp->t_lstate |= LSBKSL; + continue; + } + if (c == tlun.t_dsuspc) { + ttsignal(tp, SIGTSTP); + if (first) { + sleep((caddr_t)&lbolt, TTIPRI); + goto loop; + } + break; + } + if (c == tun.t_eofc && (tp->t_flags&CBREAK)==0) + break; + if (passc(c & 0177) < 0) + break; + if ((tp->t_flags&CBREAK)==0 && ttbreakc(c, tp)) + break; + first = 0; + } + tp->t_lstate &= ~LSBKSL; + } + + if (tp->t_state&TS_TBLOCK && tp->t_rawq.c_cc < TTYHOG/5) { + if (putc(tun.t_startc, &tp->t_outq)==0) { + tp->t_state &= ~TS_TBLOCK; + ttstart(tp); + } + tp->t_char = 0; + } + + return (tp->t_rawq.c_cc + tp->t_canq.c_cc); +} + +/* + * Called from the device's write routine after it has + * calculated the tty-structure given as argument. + */ +caddr_t +ttwrite(tp) +register struct tty *tp; +{ +#ifdef vax + /* + * THE POSITIONING OF CP, CC, AND CE ARE CRITICAL + * AND MUST NOT BE CHANGED WITHOUT PATCHING + * THE 'ASM' INLINES BELOW. WATCH OUT. + */ +#endif + register char *cp; + register int cc, ce; + register i; + char obuf[OBUFSIZ]; + register c; + int hiwat = TTHIWAT(tp); + int cnt = u.u_count; + + if ((tp->t_state&TS_CARR_ON)==0) + return (NULL); +loop: + while (u.u_procp->p_pgrp != tp->t_pgrp && tp == u.u_ttyp && + (tp->t_local<OSTOP) && (u.u_procp->p_flag&SVFORK)==0 && + u.u_signal[SIGTTOU] != SIG_IGN && + u.u_signal[SIGTTOU] != SIG_HOLD +/* + && + (u.u_procp->p_flag&SDETACH)==0) { +*/ + ) { + gsignal(u.u_procp->p_pgrp, SIGTTOU); + sleep((caddr_t)&lbolt, TTIPRI); + } + while (u.u_count) { + cc = MIN(u.u_count, OBUFSIZ); + cp = obuf; + iomove(cp, (unsigned)cc, B_WRITE); + if (u.u_error) + break; + if (tp->t_outq.c_cc > hiwat) + goto ovhiwat; + if (tp->t_local&LFLUSHO) + continue; + if (tp->t_flags&LCASE || tp->t_local<ILDE) { + while (cc) { + c = *cp++; + tp->t_rocount = 0; + while((c = ttyoutput(c, tp)) >= 0) { + /* out of clists, wait a bit */ + ttstart(tp); + sleep((caddr_t)&lbolt, TTOPRI); + tp->t_rocount = 0; + } + --cc; + if (tp->t_outq.c_cc > hiwat) + goto ovhiwat; + } + continue; + } + while (cc) { + if (tp->t_flags&RAW || tp->t_local&LLITOUT) + ce = cc; + else { +#ifdef vax + asm(" scanc r9,(r10),_partab,$077"); + asm(" subl3 r0,r9,r8"); +#else + ce=0; + while(((partab[*(unsigned char *)(cp+ce)]&077)==0)&&(cet_rocount = 0; + if (ttyoutput(*cp, tp) >= 0) { + ttstart(tp); + sleep((caddr_t)&lbolt, TTOPRI); + continue; + } + cp++; + cc--; + if (tp->t_outq.c_cc > hiwat) + goto ovhiwat; + } + } + tp->t_rocount = 0; + i=b_to_q(cp,ce,&tp->t_outq); + ce-=i; + tk_nout+=ce; + tp->t_col+=ce; + cp+=ce; + cc-=ce; + if (i) { + ttstart(tp); + sleep((caddr_t)&lbolt, TTOPRI); + } + if (ce || tp->t_outq.c_cc > hiwat) + goto ovhiwat; + } + } + ttstart(tp); + return(NULL); + +ovhiwat: + (void) spl5(); + u.u_base -= cc; + u.u_offset -= cc; + u.u_count += cc; + if (tp->t_outq.c_cc <= hiwat) { + (void) spl0(); + goto loop; + } + ttstart(tp); + if (tp->t_state & TS_NBIO) { + if (u.u_count == cnt) + u.u_error = EWOULDBLOCK; + return (NULL); + } + tp->t_state |= TS_ASLEEP; + sleep((caddr_t)&tp->t_outq, TTOPRI); + (void) spl0(); + goto loop; +} + +/* + * Rubout one character from the rawq of tp + * as cleanly as possible. + */ +ttyrub(c, tp) +register c; +register struct tty *tp; +{ + register char *cp; + register int savecol; + int s; + char *nextc(); + + if ((tp->t_flags&ECHO)==0) + return; + tp->t_local &= ~LFLUSHO; + c &= 0377; + if (tp->t_local&LCRTBS) { + if (tp->t_rocount == 0) { + /* + * Screwed by ttwrite; retype + */ + ttyretype(tp); + return; + } + if (c==('\t'|0200) || c==('\n'|0200)) + ttyrubo(tp, 2); + else switch(partab[c&=0177] & 0177) { + + case ORDINARY: + if (tp->t_flags&LCASE && c >= 'A' && c <= 'Z') + ttyrubo(tp, 2); + else + ttyrubo(tp, 1); + break; + + case VTAB: + case BACKSPACE: + case CONTROL: + case RETURN: + if (tp->t_local & LCTLECH) + ttyrubo(tp, 2); + break; + + case TAB: + if (tp->t_rocount < tp->t_rawq.c_cc) { + ttyretype(tp); + return; + } + s = spl5(); + savecol = tp->t_col; + tp->t_lstate |= LSCNTTB; + tp->t_local |= LFLUSHO; + tp->t_col = tp->t_rocol; + for (cp = tp->t_rawq.c_cf; cp; cp = nextc(&tp->t_rawq, cp)) + ttyecho(*cp, tp); + tp->t_local &= ~LFLUSHO; + tp->t_lstate &= ~LSCNTTB; + splx(s); + /* + * savecol will now be length of the tab + */ + savecol -= tp->t_col; + tp->t_col += savecol; + if (savecol > 8) + savecol = 8; /* overflow screw */ + while (--savecol >= 0) + (void) ttyoutput('\b', tp); + break; + + default: + panic("ttyrub"); + } + } else if (tp->t_local&LPRTERA) { + if ((tp->t_lstate&LSERASE) == 0) { + (void) ttyoutput('\\', tp); + tp->t_lstate |= LSERASE; + } + ttyecho(c, tp); + } else + ttyecho(tp->t_erase, tp); + tp->t_rocount--; +} + +/* + * Crt back over cnt chars perhaps + * erasing them. + */ +ttyrubo(tp, cnt) +register struct tty *tp; +int cnt; +{ + + while (--cnt >= 0) + ttyout(tp->t_local&LCRTERA ? "\b \b" : "\b", tp); +} + +/* + * Reprint the rawq line. + * We assume c_cc has already been checked. + */ +ttyretype(tp) +register struct tty *tp; +{ + register char *cp; + char *nextc(); + int s; + + if (tlun.t_rprntc != 0377) + ttyecho(tlun.t_rprntc, tp); + (void) ttyoutput('\n', tp); + s = spl5(); + for (cp = tp->t_canq.c_cf; cp; cp = nextc(&tp->t_canq, cp)) + ttyecho(*cp, tp); + for (cp = tp->t_rawq.c_cf; cp; cp = nextc(&tp->t_rawq, cp)) + ttyecho(*cp, tp); + tp->t_lstate &= ~LSERASE; + splx(s); + tp->t_rocount = tp->t_rawq.c_cc; + tp->t_rocol = 0; +} + +/* + * Echo a typed character to the terminal + */ +ttyecho(c, tp) +register c; +register struct tty *tp; +{ + + if ((tp->t_lstate & LSCNTTB) == 0) + tp->t_local &= ~LFLUSHO; + if ((tp->t_flags&ECHO) == 0) + return; + c &= 0377; + if (tp->t_flags&RAW) { + (void) ttyoutput(c, tp); + return; + } + if (c == '\r' && tp->t_flags&CRMOD) + c = '\n'; + if (tp->t_local&LCTLECH) { + if ((c&0177) <= 037 && c!='\t' && c!='\n' || (c&0177)==0177) { + (void) ttyoutput('^', tp); + c &= 0177; + if (c == 0177) + c = '?'; + else if (tp->t_flags&LCASE) + c += 'a' - 1; + else + c += 'A' - 1; + } + } + if ((tp->t_flags&LCASE) && (c >= 'A' && c <= 'Z')) + c += 'a' - 'A'; + (void) ttyoutput(c & 0177, tp); +} + +/* + * Is c a break char for tp? + */ +ttbreakc(c, tp) +register c; +register struct tty *tp; +{ + return (c == '\n' || c == tun.t_eofc || c == tun.t_brkc || + c == '\r' && (tp->t_flags&CRMOD)); +} + +/* + * send string cp to tp + */ +ttyout(cp, tp) +register char *cp; +register struct tty *tp; +{ + register char c; + + while (c = *cp++) + (void) ttyoutput(c, tp); +} + +ttwakeup(tp) + struct tty *tp; +{ + + if (tp->t_rsel) { + selwakeup(tp->t_rsel, tp->t_state&TS_RCOLL); + tp->t_state &= ~TS_RCOLL; + tp->t_rsel = 0; + } + wakeup((caddr_t)&tp->t_rawq); +} + +ttsignal(tp, signo) + struct tty *tp; + int signo; +{ + + gsignal(tp->t_pgrp, signo); +} diff --git a/usr/src/sys/kern/uipc_domain.c b/usr/src/sys/kern/uipc_domain.c index fa95045cee..72bcca78d1 100644 --- a/usr/src/sys/kern/uipc_domain.c +++ b/usr/src/sys/kern/uipc_domain.c @@ -1,4 +1,4 @@ -/* uipc_domain.c 5.1 82/07/15 */ +/* uipc_domain.c 5.2 82/07/24 */ #include "../h/param.h" #include "../h/systm.h" @@ -17,3 +17,8 @@ #include "../h/buf.h" #include "../h/mount.h" +cdomain() +{ + + /* return a descriptor for the domain */ +} diff --git a/usr/src/sys/kern/uipc_syscalls.c b/usr/src/sys/kern/uipc_syscalls.c index 7c0de7842a..810a7eb372 100644 --- a/usr/src/sys/kern/uipc_syscalls.c +++ b/usr/src/sys/kern/uipc_syscalls.c @@ -1,4 +1,4 @@ -/* uipc_syscalls.c 4.20 82/06/20 */ +/* uipc_syscalls.c 4.21 82/07/24 */ #include "../h/param.h" #include "../h/systm.h" @@ -14,6 +14,72 @@ #include "../h/socketvar.h" #include "../net/in.h" #include "../net/in_systm.h" +#include "../h/descrip.h" + +ssocreate() +{ + +} + +ssobind() +{ + +} + +ssolisten() +{ + +} + +ssoaccept() +{ + +} + +ssoconnect() +{ + +} + +ssocreatepair() +{ + +} + +ssosendto() +{ + +} + +ssosend() +{ + +} + +ssorecvfrom() +{ + +} + +ssorecv() +{ + +} + +ssosendm() +{ + +} + +ssorecvm() +{ + +} + +ssoshutdown() +{ + +} /* * Socket system call interface. @@ -47,12 +113,14 @@ spipe() if (rf == NULL) goto free2; r = u.u_r.r_val1; - rf->f_flag = FREAD|FSOCKET; + rf->f_flag = FREAD; + rf->f_type = DTYPE_SOCKET; rf->f_socket = rso; wf = falloc(); if (wf == NULL) goto free3; - wf->f_flag = FWRITE|FSOCKET; + wf->f_flag = FWRITE; + wf->f_type = DTYPE_SOCKET; wf->f_socket = wso; u.u_r.r_val2 = u.u_r.r_val1; u.u_r.r_val1 = r; @@ -66,10 +134,10 @@ free3: rf->f_count = 0; u.u_ofile[r] = 0; free2: - wso->so_state |= SS_USERGONE; + wso->so_state |= SS_NOFDREF; sofree(wso); free: - rso->so_state |= SS_USERGONE; + rso->so_state |= SS_NOFDREF; sofree(rso); } @@ -93,7 +161,8 @@ ssocket() if ((fp = falloc()) == NULL) return; - fp->f_flag = FSOCKET|FREAD|FWRITE; + fp->f_flag = FREAD|FWRITE; + fp->f_type = DTYPE_SOCKET; if (uap->asp && copyin((caddr_t)uap->asp, (caddr_t)&sp, sizeof (sp)) || uap->asa && copyin((caddr_t)uap->asa, (caddr_t)&sa, sizeof (sa))) { u.u_error = EFAULT; @@ -131,19 +200,23 @@ saccept() fp = getf(uap->fdes); if (fp == 0) return; - if ((fp->f_flag & FSOCKET) == 0) { + if (fp->f_type != DTYPE_SOCKET) { u.u_error = ENOTSOCK; return; } s = splnet(); so = fp->f_socket; - if ((so->so_state & SS_NBIO) && - (so->so_state & SS_CONNAWAITING) == 0) { + if ((so->so_options & SO_ACCEPTCONN) == 0) { + u.u_error = EINVAL; + splx(s); + return; + } + if ((so->so_state & SS_NBIO) && so->so_qlen == 0) { u.u_error = EWOULDBLOCK; splx(s); return; } - while ((so->so_state & SS_CONNAWAITING) == 0 && so->so_error == 0) { + while (so->so_qlen == 0 && so->so_error == 0) { if (so->so_state & SS_CANTRCVMORE) { so->so_error = ECONNABORTED; break; @@ -155,15 +228,34 @@ saccept() splx(s); return; } - u.u_error = soaccept(so, &sa); - if (u.u_error) { + if ((so->so_options & SO_NEWFDONCONN) == 0) { + struct socket *nso = so->so_q; + (void) soqremque(nso, 1); + soclose(so, 1); + fp->f_socket = nso; + nso->so_q = 0; + so = nso; + goto ret; + } + if (ufalloc() < 0) { + splx(s); + return; + } + fp = falloc(); + if (fp == 0) { + u.u_ofile[u.u_r.r_val1] = 0; splx(s); return; } + fp->f_type = DTYPE_SOCKET; + fp->f_flag = FREAD|FWRITE; + fp->f_socket = so->so_q; + so->so_q = so->so_q->so_q; + so->so_qlen--; +ret: + soaccept(so, &sa); if (uap->asa) (void) copyout((caddr_t)&sa, (caddr_t)uap->asa, sizeof (sa)); - /* deal with new file descriptor case */ - /* u.u_r.r_val1 = ... */ splx(s); } @@ -189,7 +281,7 @@ sconnect() fp = getf(uap->fdes); if (fp == 0) return; - if ((fp->f_flag & FSOCKET) == 0) { + if (fp->f_type != DTYPE_SOCKET) { u.u_error = ENOTSOCK; return; } @@ -228,7 +320,7 @@ ssend() fp = getf(uap->fdes); if (fp == 0) return; - if ((fp->f_flag & FSOCKET) == 0) { + if (fp->f_type != DTYPE_SOCKET) { u.u_error = ENOTSOCK; return; } @@ -261,7 +353,7 @@ sreceive() fp = getf(uap->fdes); if (fp == 0) return; - if ((fp->f_flag & FSOCKET) == 0) { + if (fp->f_type != DTYPE_SOCKET) { u.u_error = ENOTSOCK; return; } @@ -297,7 +389,7 @@ ssocketaddr() fp = getf(uap->fdes); if (fp == 0) return; - if ((fp->f_flag & FSOCKET) == 0) { + if (fp->f_type != DTYPE_SOCKET) { u.u_error = ENOTSOCK; return; } diff --git a/usr/src/sys/kern/vfs_syscalls.c b/usr/src/sys/kern/vfs_syscalls.c index 6863d76aee..1fb6a4d4c2 100644 --- a/usr/src/sys/kern/vfs_syscalls.c +++ b/usr/src/sys/kern/vfs_syscalls.c @@ -1,4 +1,4 @@ -/* vfs_syscalls.c 4.29 82/07/22 */ +/* vfs_syscalls.c 4.30 82/07/24 */ #include "../h/param.h" #include "../h/systm.h" @@ -16,6 +16,7 @@ #include "../h/efs.h" #endif #include "../h/quota.h" +#include "../h/descrip.h" chdir() { @@ -78,7 +79,7 @@ open() /* * Creat system call. */ -creat() +ocreat() { register struct inode *ip; register struct a { @@ -130,6 +131,7 @@ open1(ip, mode, trf) if ((fp = falloc()) == NULL) goto out; fp->f_flag = mode&(FREAD|FWRITE); + fp->f_type = DTYPE_FILE; i = u.u_r.r_val1; fp->f_inode = ip; #ifdef EFS @@ -346,6 +348,8 @@ unlink() /* * first entry in block, so set d_ino to zero. */ +/*ZZ*/if(u.u_offset&0x1ff)printf("missed dir compact dir %s/%d off %d file %s\n" +/*ZZ*/,pp->i_fs->fs_fsmnt,pp->i_number,u.u_offset,u.u_dent.d_name); u.u_base = (caddr_t)&u.u_dent; u.u_count = DIRSIZ(&u.u_dent); u.u_dent.d_ino = 0; @@ -365,6 +369,8 @@ unlink() } ((struct direct *)(bp->b_un.b_addr + base))->d_reclen += u.u_dent.d_reclen; +/*ZZ*/if(((int)(bp->b_un.b_addr + base)&0x1ff)+u.u_dent.d_reclen>512) +/*ZZ*/ panic("unlink: reclen"); bwrite(bp); pp->i_flag |= IUPD|ICHG; } @@ -396,7 +402,7 @@ seek() fp = getf(uap->fdes); if (fp == NULL) return; - if (fp->f_flag&FSOCKET) { + if (fp->f_type == DTYPE_SOCKET) { u.u_error = ESPIPE; return; } @@ -479,7 +485,7 @@ fstat() return; } #endif - if (fp->f_flag & FSOCKET) + if (fp->f_type == DTYPE_SOCKET) u.u_error = sostat(fp->f_socket, uap->sb); else stat1(fp->f_inode, uap->sb); diff --git a/usr/src/sys/kern/vfs_vnops.c b/usr/src/sys/kern/vfs_vnops.c index 36b49aa3c8..ba39e7f8e0 100644 --- a/usr/src/sys/kern/vfs_vnops.c +++ b/usr/src/sys/kern/vfs_vnops.c @@ -1,6 +1,4 @@ -/* vfs_vnops.c 4.24 82/07/15 */ - -/* merged into kernel: @(#)fio.c 2.2 4/8/82 */ +/* fio.c 4.25 82/07/17 */ #include "../h/param.h" #include "../h/systm.h" @@ -21,118 +19,6 @@ #include "../h/efs.h" #endif -/* - * Convert a user supplied file descriptor into a pointer - * to a file structure. Only task is to check range of the descriptor. - * Critical paths should use the GETF macro, defined in inline.h. - */ -struct file * -getf(f) - register int f; -{ - register struct file *fp; - - if ((unsigned)f >= NOFILE || (fp = u.u_ofile[f]) == NULL) { - u.u_error = EBADF; - return (NULL); - } - return (fp); -} - -/* - * Internal form of close. - * Decrement reference count on - * file structure. - * Also make sure the pipe protocol - * does not constipate. - * - * Decrement reference count on the inode following - * removal to the referencing file structure. - * Call device handler on last close. - * Nouser indicates that the user isn't available to present - * errors to. - */ -closef(fp, nouser) - register struct file *fp; -{ - register struct inode *ip; - register struct mount *mp; - int flag, mode; - dev_t dev; - register int (*cfunc)(); - - if (fp == NULL) - return; - if (fp->f_count > 1) { - fp->f_count--; - return; - } - flag = fp->f_flag; - if (flag & FSOCKET) { - u.u_error = 0; /* XXX */ - soclose(fp->f_socket, nouser); - if (nouser == 0 && u.u_error) - return; - fp->f_socket = 0; - fp->f_count = 0; - return; - } - ip = fp->f_inode; - dev = (dev_t)ip->i_rdev; - mode = ip->i_mode & IFMT; - ilock(ip); - iput(ip); - fp->f_count = 0; - - switch (mode) { - - case IFCHR: - cfunc = cdevsw[major(dev)].d_close; -#ifdef EFS - /* - * Every close() must call the driver if the - * extended file system is being used -- not - * just the last close. Pass along the file - * pointer for reference later. - */ - if (major(dev) == efs_major) { - (*cfunc)(dev, flag, fp, nouser); - return; - } -#endif - break; - - case IFBLK: - /* - * We don't want to really close the device if it is mounted - */ - for (mp = mount; mp < &mount[NMOUNT]; mp++) - if (mp->m_bufp != NULL && mp->m_dev == dev) - return; - cfunc = bdevsw[major(dev)].d_close; - break; - - default: - return; - } - for (fp = file; fp < fileNFILE; fp++) { - if (fp->f_flag & FSOCKET) - continue; - if (fp->f_count && (ip = fp->f_inode) && - ip->i_rdev == dev && (ip->i_mode&IFMT) == mode) - return; - } - if (mode == IFBLK) { - /* - * On last close of a block device (that isn't mounted) - * we must invalidate any in core blocks - */ - bflush(dev); - binval(dev); - } - (*cfunc)(dev, flag, fp); -} - /* * Openi called to allow handler * of special files to initialize and @@ -267,56 +153,3 @@ suser() u.u_error = EPERM; return (0); } - -/* - * Allocate a user file descriptor. - */ -ufalloc() -{ - register i; - - for (i=0; if_count == 0) - goto slot; - for (fp = file; fp < lastf; fp++) - if (fp->f_count == 0) - goto slot; - tablefull("file"); - u.u_error = ENFILE; - return (NULL); -slot: - u.u_ofile[i] = fp; - fp->f_count++; - fp->f_offset = 0; - fp->f_inode = 0; - lastf = fp + 1; - return (fp); -} diff --git a/usr/src/sys/sys/file.h b/usr/src/sys/sys/file.h index 6a4bf60fe7..9009857f02 100644 --- a/usr/src/sys/sys/file.h +++ b/usr/src/sys/sys/file.h @@ -1,27 +1,25 @@ -/* file.h 4.10 81/11/14 */ +/* file.h 4.11 82/07/24 */ /* - * One file structure is allocated - * for each open/creat/pipe call. - * Main use is to hold the read/write - * pointer associated with each open - * file. + * Descriptor table entry. + * One for each kernel object. */ struct file { short f_flag; /* see below */ + short f_type; /* descriptor type */ + char f_nbhow; /* state from dnblock */ + char f_sighow; /* state from dsignal */ short f_count; /* reference count */ +/* begin XXX */ struct inode *f_inode; /* inode */ union { - struct f_in { - off_t fi_offset; - } f_in; - struct f_so { - struct socket *fs_socket; - } f_so; + struct f_in { off_t fi_offset; } f_in; + struct f_so { struct socket *fs_socket; } f_so; } f_un; -}; #define f_offset f_un.f_in.fi_offset #define f_socket f_un.f_so.fs_socket +/* end XXX */ +}; #ifdef KERNEL struct file *file, *fileNFILE; @@ -31,8 +29,6 @@ struct file *falloc(); #endif /* flags */ -#define FINODE 0x0 /* descriptor of an inode (pseudo) */ #define FREAD 0x1 /* descriptor read/receive'able */ #define FWRITE 0x2 /* descriptor write/send'able */ -#define FSOCKET 0x4 /* descriptor of a socket */ -#define FPORTAL 0x8 /* descriptor of a portal */ +/* note: other flags for f_flag defined in fcntl.h */ diff --git a/usr/src/sys/sys/socket.h b/usr/src/sys/sys/socket.h index 7dc85bac2a..e752e9a173 100644 --- a/usr/src/sys/sys/socket.h +++ b/usr/src/sys/sys/socket.h @@ -1,4 +1,4 @@ -/* socket.h 4.16 82/06/08 */ +/* socket.h 4.17 82/07/21 */ /* * Externally visible attributes of sockets. @@ -24,6 +24,7 @@ #define SO_DONTLINGER 0x04 /* don't linger on close */ #define SO_KEEPALIVE 0x08 /* keep connections alive */ #define SO_DONTROUTE 0x10 /* just use interface addresses */ +#define SO_NEWFDONCONN 0x20 /* give new fd on connection */ /* * Generic socket protocol format. diff --git a/usr/src/sys/sys/socketvar.h b/usr/src/sys/sys/socketvar.h index 9d3ced169c..63334ea4d7 100644 --- a/usr/src/sys/sys/socketvar.h +++ b/usr/src/sys/sys/socketvar.h @@ -1,4 +1,4 @@ -/* socketvar.h 4.16 82/04/10 */ +/* socketvar.h 4.17 82/07/21 */ /* * Kernel structure per socket. @@ -13,6 +13,26 @@ struct socket { short so_state; /* internal state flags SS_*, below */ caddr_t so_pcb; /* protocol control block */ struct protosw *so_proto; /* protocol handle */ +/* + * Variables for connection queueing. + * Socket where accepts occur is so_head in all subsidiary sockets. + * If so_head is 0, socket is not related to an accept. + * For head socket so_q0 queues partially completed connections, + * while so_q is a queue of connections ready to be accepted. + * If a connection is aborted and it has so_head set, then + * it has to be pulled out of either so_q0 or so_q. + * We allow connections to queue up based on current queue lengths + * and limit on number of queued connections for this socket. + */ + struct socket *so_head; /* back pointer to accept socket */ + struct socket *so_q0; /* queue of partial connections */ + short so_q0len; /* partials on so_q0 */ + struct socket *so_q; /* queue of incoming connections */ + short so_qlen; /* number of connections on so_q */ + short so_qlimit; /* max number queued connections */ +/* + * Variables for socket buffering. + */ struct sockbuf { short sb_cc; /* actual chars in buffer */ short sb_hiwat; /* max actual char count */ @@ -38,18 +58,18 @@ struct socket { /* * Socket state bits. */ -#define SS_USERGONE 0x001 /* no file table ref any more */ +#define SS_NOFDREF 0x001 /* no file table ref any more */ #define SS_ISCONNECTED 0x002 /* socket connected to a peer */ #define SS_ISCONNECTING 0x004 /* in process of connecting to peer */ #define SS_ISDISCONNECTING 0x008 /* in process of disconnecting */ #define SS_CANTSENDMORE 0x010 /* can't send more data to peer */ #define SS_CANTRCVMORE 0x020 /* can't receive more data from peer */ -#define SS_CONNAWAITING 0x040 /* connections awaiting acceptance */ -#define SS_RCVATMARK 0x080 /* at mark on input */ +#define SS_RCVATMARK 0x040 /* at mark on input */ + +#define SS_PRIV 0x080 /* privileged for broadcast, raw... */ +#define SS_NBIO 0x100 /* non-blocking ops */ +#define SS_ASYNC 0x200 /* async i/o notify */ -#define SS_PRIV 0x100 /* privileged for broadcast, raw... */ -#define SS_NBIO 0x200 /* non-blocking ops */ -#define SS_ASYNC 0x400 /* async i/o notify */ /* * Macros for sockets and socket buffering. @@ -65,7 +85,7 @@ struct socket { /* can we read something from so? */ #define soreadable(so) \ - ((so)->so_rcv.sb_cc || ((so)->so_state & (SS_CANTRCVMORE|SS_CONNAWAITING))) + ((so)->so_rcv.sb_cc || ((so)->so_state & SS_CANTRCVMORE) || (so)->so_qlen) /* can we write something to so? */ #define sowriteable(so) \ @@ -110,3 +130,7 @@ struct socket { #define sorwakeup(so) sbwakeup(&(so)->so_rcv) #define sowwakeup(so) sbwakeup(&(so)->so_snd) + +#ifdef KERNEL +struct socket *sonewconn(); +#endif diff --git a/usr/src/sys/ufs/ffs/ffs_inode.c b/usr/src/sys/ufs/ffs/ffs_inode.c index 67ba0ffe4a..1e1adfc0ce 100644 --- a/usr/src/sys/ufs/ffs/ffs_inode.c +++ b/usr/src/sys/ufs/ffs/ffs_inode.c @@ -1,4 +1,4 @@ -/* ffs_inode.c 4.18 82/07/22 */ +/* ffs_inode.c 4.19 82/07/24 */ #include "../h/param.h" #include "../h/systm.h" @@ -10,6 +10,9 @@ #include "../h/conf.h" #include "../h/buf.h" #include "../h/inline.h" +#ifdef QUOTA +#include "../h/quota.h" +#endif #define INOHSZ 63 #if ((INOHSZ&(INOHSZ-1)) == 0) @@ -208,6 +211,7 @@ loop: return (ip); } +int badinum = -1; /* * Decrement reference count of * an inode structure. @@ -221,6 +225,11 @@ iput(ip) if ((ip->i_flag & ILOCK) == 0) panic("iput"); +/* XXX */ + if (ip->i_number == badinum && (ip->i_mode&IFMT) == IFCHR && + (major(ip->i_dev) != 3 || minor(ip->i_dev) != 2)) + panic("/dev/null"); +/* XXX */ iunlock(ip); irele(ip); } @@ -543,6 +552,7 @@ wdir(ip) u.u_dent.d_reclen = DIRBLKSIZ; u.u_count = newsize; u.u_base = (caddr_t)&u.u_dent; +/*ZZ*/if((u.u_offset&0x1ff))panic("wdir: newblk"); writei(u.u_pdir); iput(u.u_pdir); return; @@ -556,7 +566,12 @@ wdir(ip) base = blkoff(fs, u.u_offset); bn = fsbtodb(fs, bmap(u.u_pdir, lbn, B_WRITE, base + u.u_count)); if (u.u_offset + u.u_count > u.u_pdir->i_size) +/*ZZ*/{if((u.u_offset+u.u_count-1&~0x1ff)!=(u.u_pdir->i_size-1&~0x1ff)) +/*ZZ*/ printf("wdir i_size dir %s/%d (of=%d,cnt=%d,psz=%d))\n", +/*ZZ*/ u.u_pdir->i_fs->fs_fsmnt,u.u_pdir->i_number,u.u_offset, +/*ZZ*/ u.u_count,u.u_pdir->i_size); u.u_pdir->i_size = u.u_offset + u.u_count; +/*ZZ*/} bp = bread(u.u_pdir->i_dev, bn, blksize(fs, u.u_pdir, lbn)); if (bp->b_flags & B_ERROR) { brelse(bp); @@ -581,6 +596,10 @@ wdir(ip) } dsize = DIRSIZ(ndp); spccnt += ndp->d_reclen - dsize; +/*ZZ*/if(spccnt>512)panic("wdir spccnt"); +/*ZZ*/if((loc&~0x1ff)!=(loc+ndp->d_reclen-1&~0x1ff)) +/*ZZ*/printf("wdir: compact loc %d reclen %d (dir %s/%d)\n",loc,ndp->d_reclen, +/*ZZ*/u.u_pdir->i_fs->fs_fsmnt,u.u_pdir->i_number); loc += ndp->d_reclen; bcopy(ndp, dp, dsize); } @@ -590,15 +609,18 @@ wdir(ip) */ if (dp->d_ino == 0) { if (spccnt + dsize < newsize) - panic("wdir: compact failed"); + panic("wdir: compact failed (1)"); +/*ZZ*/if(spccnt+dsize>512)panic("wdir: compact screwup"); u.u_dent.d_reclen = spccnt + dsize; } else { if (spccnt < newsize) - panic("wdir: compact failed"); + panic("wdir: compact failed (2)"); u.u_dent.d_reclen = spccnt; +/*ZZ*/if ((((char *)dp-bp->b_un.b_addr)&0x1ff)+dsize>512) panic("wdir: reclen"); dp->d_reclen = dsize; dp = (struct direct *)((char *)dp + dsize); } +/*ZZ*/if((((char*)dp-bp->b_un.b_addr)&0x1ff)+u.u_dent.d_reclen>512)panic("wdir: botch"); bcopy(&u.u_dent, dp, newsize); bwrite(bp); u.u_pdir->i_flag |= IUPD|ICHG; @@ -619,9 +641,9 @@ wdir(ip) * this is called from sumount()/sys3.c when dev is being unmounted */ #ifdef QUOTA -iflush(dev, qi); +iflush(dev, iq) dev_t dev; - struct inode *qi; + struct inode *iq; #else iflush(dev) dev_t dev; diff --git a/usr/src/sys/ufs/ffs/ffs_vnops.c b/usr/src/sys/ufs/ffs/ffs_vnops.c index 3b1656adbb..ecac9dccd0 100644 --- a/usr/src/sys/ufs/ffs/ffs_vnops.c +++ b/usr/src/sys/ufs/ffs/ffs_vnops.c @@ -1,4 +1,4 @@ -/* ffs_vnops.c 4.29 82/07/22 */ +/* ffs_vnops.c 4.30 82/07/24 */ #include "../h/param.h" #include "../h/systm.h" @@ -16,6 +16,7 @@ #include "../h/efs.h" #endif #include "../h/quota.h" +#include "../h/descrip.h" chdir() { @@ -78,7 +79,7 @@ open() /* * Creat system call. */ -creat() +ocreat() { register struct inode *ip; register struct a { @@ -130,6 +131,7 @@ open1(ip, mode, trf) if ((fp = falloc()) == NULL) goto out; fp->f_flag = mode&(FREAD|FWRITE); + fp->f_type = DTYPE_FILE; i = u.u_r.r_val1; fp->f_inode = ip; #ifdef EFS @@ -346,6 +348,8 @@ unlink() /* * first entry in block, so set d_ino to zero. */ +/*ZZ*/if(u.u_offset&0x1ff)printf("missed dir compact dir %s/%d off %d file %s\n" +/*ZZ*/,pp->i_fs->fs_fsmnt,pp->i_number,u.u_offset,u.u_dent.d_name); u.u_base = (caddr_t)&u.u_dent; u.u_count = DIRSIZ(&u.u_dent); u.u_dent.d_ino = 0; @@ -365,6 +369,8 @@ unlink() } ((struct direct *)(bp->b_un.b_addr + base))->d_reclen += u.u_dent.d_reclen; +/*ZZ*/if(((int)(bp->b_un.b_addr + base)&0x1ff)+u.u_dent.d_reclen>512) +/*ZZ*/ panic("unlink: reclen"); bwrite(bp); pp->i_flag |= IUPD|ICHG; } @@ -396,7 +402,7 @@ seek() fp = getf(uap->fdes); if (fp == NULL) return; - if (fp->f_flag&FSOCKET) { + if (fp->f_type == DTYPE_SOCKET) { u.u_error = ESPIPE; return; } @@ -479,7 +485,7 @@ fstat() return; } #endif - if (fp->f_flag & FSOCKET) + if (fp->f_type == DTYPE_SOCKET) u.u_error = sostat(fp->f_socket, uap->sb); else stat1(fp->f_inode, uap->sb); diff --git a/usr/src/sys/ufs/ffs/ufs_inode.c b/usr/src/sys/ufs/ffs/ufs_inode.c index 6cf76b5e20..8f33e6361f 100644 --- a/usr/src/sys/ufs/ffs/ufs_inode.c +++ b/usr/src/sys/ufs/ffs/ufs_inode.c @@ -1,4 +1,4 @@ -/* ufs_inode.c 4.18 82/07/22 */ +/* ufs_inode.c 4.19 82/07/24 */ #include "../h/param.h" #include "../h/systm.h" @@ -10,6 +10,9 @@ #include "../h/conf.h" #include "../h/buf.h" #include "../h/inline.h" +#ifdef QUOTA +#include "../h/quota.h" +#endif #define INOHSZ 63 #if ((INOHSZ&(INOHSZ-1)) == 0) @@ -208,6 +211,7 @@ loop: return (ip); } +int badinum = -1; /* * Decrement reference count of * an inode structure. @@ -221,6 +225,11 @@ iput(ip) if ((ip->i_flag & ILOCK) == 0) panic("iput"); +/* XXX */ + if (ip->i_number == badinum && (ip->i_mode&IFMT) == IFCHR && + (major(ip->i_dev) != 3 || minor(ip->i_dev) != 2)) + panic("/dev/null"); +/* XXX */ iunlock(ip); irele(ip); } @@ -543,6 +552,7 @@ wdir(ip) u.u_dent.d_reclen = DIRBLKSIZ; u.u_count = newsize; u.u_base = (caddr_t)&u.u_dent; +/*ZZ*/if((u.u_offset&0x1ff))panic("wdir: newblk"); writei(u.u_pdir); iput(u.u_pdir); return; @@ -556,7 +566,12 @@ wdir(ip) base = blkoff(fs, u.u_offset); bn = fsbtodb(fs, bmap(u.u_pdir, lbn, B_WRITE, base + u.u_count)); if (u.u_offset + u.u_count > u.u_pdir->i_size) +/*ZZ*/{if((u.u_offset+u.u_count-1&~0x1ff)!=(u.u_pdir->i_size-1&~0x1ff)) +/*ZZ*/ printf("wdir i_size dir %s/%d (of=%d,cnt=%d,psz=%d))\n", +/*ZZ*/ u.u_pdir->i_fs->fs_fsmnt,u.u_pdir->i_number,u.u_offset, +/*ZZ*/ u.u_count,u.u_pdir->i_size); u.u_pdir->i_size = u.u_offset + u.u_count; +/*ZZ*/} bp = bread(u.u_pdir->i_dev, bn, blksize(fs, u.u_pdir, lbn)); if (bp->b_flags & B_ERROR) { brelse(bp); @@ -581,6 +596,10 @@ wdir(ip) } dsize = DIRSIZ(ndp); spccnt += ndp->d_reclen - dsize; +/*ZZ*/if(spccnt>512)panic("wdir spccnt"); +/*ZZ*/if((loc&~0x1ff)!=(loc+ndp->d_reclen-1&~0x1ff)) +/*ZZ*/printf("wdir: compact loc %d reclen %d (dir %s/%d)\n",loc,ndp->d_reclen, +/*ZZ*/u.u_pdir->i_fs->fs_fsmnt,u.u_pdir->i_number); loc += ndp->d_reclen; bcopy(ndp, dp, dsize); } @@ -590,15 +609,18 @@ wdir(ip) */ if (dp->d_ino == 0) { if (spccnt + dsize < newsize) - panic("wdir: compact failed"); + panic("wdir: compact failed (1)"); +/*ZZ*/if(spccnt+dsize>512)panic("wdir: compact screwup"); u.u_dent.d_reclen = spccnt + dsize; } else { if (spccnt < newsize) - panic("wdir: compact failed"); + panic("wdir: compact failed (2)"); u.u_dent.d_reclen = spccnt; +/*ZZ*/if ((((char *)dp-bp->b_un.b_addr)&0x1ff)+dsize>512) panic("wdir: reclen"); dp->d_reclen = dsize; dp = (struct direct *)((char *)dp + dsize); } +/*ZZ*/if((((char*)dp-bp->b_un.b_addr)&0x1ff)+u.u_dent.d_reclen>512)panic("wdir: botch"); bcopy(&u.u_dent, dp, newsize); bwrite(bp); u.u_pdir->i_flag |= IUPD|ICHG; @@ -619,9 +641,9 @@ wdir(ip) * this is called from sumount()/sys3.c when dev is being unmounted */ #ifdef QUOTA -iflush(dev, qi); +iflush(dev, iq) dev_t dev; - struct inode *qi; + struct inode *iq; #else iflush(dev) dev_t dev; diff --git a/usr/src/sys/ufs/ffs/ufs_vnops.c b/usr/src/sys/ufs/ffs/ufs_vnops.c index f06ca840a9..883f021d38 100644 --- a/usr/src/sys/ufs/ffs/ufs_vnops.c +++ b/usr/src/sys/ufs/ffs/ufs_vnops.c @@ -1,4 +1,4 @@ -/* ufs_vnops.c 4.29 82/07/22 */ +/* ufs_vnops.c 4.30 82/07/24 */ #include "../h/param.h" #include "../h/systm.h" @@ -16,6 +16,7 @@ #include "../h/efs.h" #endif #include "../h/quota.h" +#include "../h/descrip.h" chdir() { @@ -78,7 +79,7 @@ open() /* * Creat system call. */ -creat() +ocreat() { register struct inode *ip; register struct a { @@ -130,6 +131,7 @@ open1(ip, mode, trf) if ((fp = falloc()) == NULL) goto out; fp->f_flag = mode&(FREAD|FWRITE); + fp->f_type = DTYPE_FILE; i = u.u_r.r_val1; fp->f_inode = ip; #ifdef EFS @@ -346,6 +348,8 @@ unlink() /* * first entry in block, so set d_ino to zero. */ +/*ZZ*/if(u.u_offset&0x1ff)printf("missed dir compact dir %s/%d off %d file %s\n" +/*ZZ*/,pp->i_fs->fs_fsmnt,pp->i_number,u.u_offset,u.u_dent.d_name); u.u_base = (caddr_t)&u.u_dent; u.u_count = DIRSIZ(&u.u_dent); u.u_dent.d_ino = 0; @@ -365,6 +369,8 @@ unlink() } ((struct direct *)(bp->b_un.b_addr + base))->d_reclen += u.u_dent.d_reclen; +/*ZZ*/if(((int)(bp->b_un.b_addr + base)&0x1ff)+u.u_dent.d_reclen>512) +/*ZZ*/ panic("unlink: reclen"); bwrite(bp); pp->i_flag |= IUPD|ICHG; } @@ -396,7 +402,7 @@ seek() fp = getf(uap->fdes); if (fp == NULL) return; - if (fp->f_flag&FSOCKET) { + if (fp->f_type == DTYPE_SOCKET) { u.u_error = ESPIPE; return; } @@ -479,7 +485,7 @@ fstat() return; } #endif - if (fp->f_flag & FSOCKET) + if (fp->f_type == DTYPE_SOCKET) u.u_error = sostat(fp->f_socket, uap->sb); else stat1(fp->f_inode, uap->sb); diff --git a/usr/src/sys/ufs/lfs/lfs_inode.c b/usr/src/sys/ufs/lfs/lfs_inode.c index ccbe9400b2..4a0f13acf9 100644 --- a/usr/src/sys/ufs/lfs/lfs_inode.c +++ b/usr/src/sys/ufs/lfs/lfs_inode.c @@ -1,4 +1,4 @@ -/* lfs_inode.c 4.18 82/07/22 */ +/* lfs_inode.c 4.19 82/07/24 */ #include "../h/param.h" #include "../h/systm.h" @@ -10,6 +10,9 @@ #include "../h/conf.h" #include "../h/buf.h" #include "../h/inline.h" +#ifdef QUOTA +#include "../h/quota.h" +#endif #define INOHSZ 63 #if ((INOHSZ&(INOHSZ-1)) == 0) @@ -208,6 +211,7 @@ loop: return (ip); } +int badinum = -1; /* * Decrement reference count of * an inode structure. @@ -221,6 +225,11 @@ iput(ip) if ((ip->i_flag & ILOCK) == 0) panic("iput"); +/* XXX */ + if (ip->i_number == badinum && (ip->i_mode&IFMT) == IFCHR && + (major(ip->i_dev) != 3 || minor(ip->i_dev) != 2)) + panic("/dev/null"); +/* XXX */ iunlock(ip); irele(ip); } @@ -543,6 +552,7 @@ wdir(ip) u.u_dent.d_reclen = DIRBLKSIZ; u.u_count = newsize; u.u_base = (caddr_t)&u.u_dent; +/*ZZ*/if((u.u_offset&0x1ff))panic("wdir: newblk"); writei(u.u_pdir); iput(u.u_pdir); return; @@ -556,7 +566,12 @@ wdir(ip) base = blkoff(fs, u.u_offset); bn = fsbtodb(fs, bmap(u.u_pdir, lbn, B_WRITE, base + u.u_count)); if (u.u_offset + u.u_count > u.u_pdir->i_size) +/*ZZ*/{if((u.u_offset+u.u_count-1&~0x1ff)!=(u.u_pdir->i_size-1&~0x1ff)) +/*ZZ*/ printf("wdir i_size dir %s/%d (of=%d,cnt=%d,psz=%d))\n", +/*ZZ*/ u.u_pdir->i_fs->fs_fsmnt,u.u_pdir->i_number,u.u_offset, +/*ZZ*/ u.u_count,u.u_pdir->i_size); u.u_pdir->i_size = u.u_offset + u.u_count; +/*ZZ*/} bp = bread(u.u_pdir->i_dev, bn, blksize(fs, u.u_pdir, lbn)); if (bp->b_flags & B_ERROR) { brelse(bp); @@ -581,6 +596,10 @@ wdir(ip) } dsize = DIRSIZ(ndp); spccnt += ndp->d_reclen - dsize; +/*ZZ*/if(spccnt>512)panic("wdir spccnt"); +/*ZZ*/if((loc&~0x1ff)!=(loc+ndp->d_reclen-1&~0x1ff)) +/*ZZ*/printf("wdir: compact loc %d reclen %d (dir %s/%d)\n",loc,ndp->d_reclen, +/*ZZ*/u.u_pdir->i_fs->fs_fsmnt,u.u_pdir->i_number); loc += ndp->d_reclen; bcopy(ndp, dp, dsize); } @@ -590,15 +609,18 @@ wdir(ip) */ if (dp->d_ino == 0) { if (spccnt + dsize < newsize) - panic("wdir: compact failed"); + panic("wdir: compact failed (1)"); +/*ZZ*/if(spccnt+dsize>512)panic("wdir: compact screwup"); u.u_dent.d_reclen = spccnt + dsize; } else { if (spccnt < newsize) - panic("wdir: compact failed"); + panic("wdir: compact failed (2)"); u.u_dent.d_reclen = spccnt; +/*ZZ*/if ((((char *)dp-bp->b_un.b_addr)&0x1ff)+dsize>512) panic("wdir: reclen"); dp->d_reclen = dsize; dp = (struct direct *)((char *)dp + dsize); } +/*ZZ*/if((((char*)dp-bp->b_un.b_addr)&0x1ff)+u.u_dent.d_reclen>512)panic("wdir: botch"); bcopy(&u.u_dent, dp, newsize); bwrite(bp); u.u_pdir->i_flag |= IUPD|ICHG; @@ -619,9 +641,9 @@ wdir(ip) * this is called from sumount()/sys3.c when dev is being unmounted */ #ifdef QUOTA -iflush(dev, qi); +iflush(dev, iq) dev_t dev; - struct inode *qi; + struct inode *iq; #else iflush(dev) dev_t dev; diff --git a/usr/src/sys/ufs/lfs/lfs_vnops.c b/usr/src/sys/ufs/lfs/lfs_vnops.c index ddb9287063..62113452d1 100644 --- a/usr/src/sys/ufs/lfs/lfs_vnops.c +++ b/usr/src/sys/ufs/lfs/lfs_vnops.c @@ -1,4 +1,4 @@ -/* lfs_vnops.c 4.29 82/07/22 */ +/* lfs_vnops.c 4.30 82/07/24 */ #include "../h/param.h" #include "../h/systm.h" @@ -16,6 +16,7 @@ #include "../h/efs.h" #endif #include "../h/quota.h" +#include "../h/descrip.h" chdir() { @@ -78,7 +79,7 @@ open() /* * Creat system call. */ -creat() +ocreat() { register struct inode *ip; register struct a { @@ -130,6 +131,7 @@ open1(ip, mode, trf) if ((fp = falloc()) == NULL) goto out; fp->f_flag = mode&(FREAD|FWRITE); + fp->f_type = DTYPE_FILE; i = u.u_r.r_val1; fp->f_inode = ip; #ifdef EFS @@ -346,6 +348,8 @@ unlink() /* * first entry in block, so set d_ino to zero. */ +/*ZZ*/if(u.u_offset&0x1ff)printf("missed dir compact dir %s/%d off %d file %s\n" +/*ZZ*/,pp->i_fs->fs_fsmnt,pp->i_number,u.u_offset,u.u_dent.d_name); u.u_base = (caddr_t)&u.u_dent; u.u_count = DIRSIZ(&u.u_dent); u.u_dent.d_ino = 0; @@ -365,6 +369,8 @@ unlink() } ((struct direct *)(bp->b_un.b_addr + base))->d_reclen += u.u_dent.d_reclen; +/*ZZ*/if(((int)(bp->b_un.b_addr + base)&0x1ff)+u.u_dent.d_reclen>512) +/*ZZ*/ panic("unlink: reclen"); bwrite(bp); pp->i_flag |= IUPD|ICHG; } @@ -396,7 +402,7 @@ seek() fp = getf(uap->fdes); if (fp == NULL) return; - if (fp->f_flag&FSOCKET) { + if (fp->f_type == DTYPE_SOCKET) { u.u_error = ESPIPE; return; } @@ -479,7 +485,7 @@ fstat() return; } #endif - if (fp->f_flag & FSOCKET) + if (fp->f_type == DTYPE_SOCKET) u.u_error = sostat(fp->f_socket, uap->sb); else stat1(fp->f_inode, uap->sb); diff --git a/usr/src/sys/ufs/ufs/ufs_inode.c b/usr/src/sys/ufs/ufs/ufs_inode.c index 6cf76b5e20..8f33e6361f 100644 --- a/usr/src/sys/ufs/ufs/ufs_inode.c +++ b/usr/src/sys/ufs/ufs/ufs_inode.c @@ -1,4 +1,4 @@ -/* ufs_inode.c 4.18 82/07/22 */ +/* ufs_inode.c 4.19 82/07/24 */ #include "../h/param.h" #include "../h/systm.h" @@ -10,6 +10,9 @@ #include "../h/conf.h" #include "../h/buf.h" #include "../h/inline.h" +#ifdef QUOTA +#include "../h/quota.h" +#endif #define INOHSZ 63 #if ((INOHSZ&(INOHSZ-1)) == 0) @@ -208,6 +211,7 @@ loop: return (ip); } +int badinum = -1; /* * Decrement reference count of * an inode structure. @@ -221,6 +225,11 @@ iput(ip) if ((ip->i_flag & ILOCK) == 0) panic("iput"); +/* XXX */ + if (ip->i_number == badinum && (ip->i_mode&IFMT) == IFCHR && + (major(ip->i_dev) != 3 || minor(ip->i_dev) != 2)) + panic("/dev/null"); +/* XXX */ iunlock(ip); irele(ip); } @@ -543,6 +552,7 @@ wdir(ip) u.u_dent.d_reclen = DIRBLKSIZ; u.u_count = newsize; u.u_base = (caddr_t)&u.u_dent; +/*ZZ*/if((u.u_offset&0x1ff))panic("wdir: newblk"); writei(u.u_pdir); iput(u.u_pdir); return; @@ -556,7 +566,12 @@ wdir(ip) base = blkoff(fs, u.u_offset); bn = fsbtodb(fs, bmap(u.u_pdir, lbn, B_WRITE, base + u.u_count)); if (u.u_offset + u.u_count > u.u_pdir->i_size) +/*ZZ*/{if((u.u_offset+u.u_count-1&~0x1ff)!=(u.u_pdir->i_size-1&~0x1ff)) +/*ZZ*/ printf("wdir i_size dir %s/%d (of=%d,cnt=%d,psz=%d))\n", +/*ZZ*/ u.u_pdir->i_fs->fs_fsmnt,u.u_pdir->i_number,u.u_offset, +/*ZZ*/ u.u_count,u.u_pdir->i_size); u.u_pdir->i_size = u.u_offset + u.u_count; +/*ZZ*/} bp = bread(u.u_pdir->i_dev, bn, blksize(fs, u.u_pdir, lbn)); if (bp->b_flags & B_ERROR) { brelse(bp); @@ -581,6 +596,10 @@ wdir(ip) } dsize = DIRSIZ(ndp); spccnt += ndp->d_reclen - dsize; +/*ZZ*/if(spccnt>512)panic("wdir spccnt"); +/*ZZ*/if((loc&~0x1ff)!=(loc+ndp->d_reclen-1&~0x1ff)) +/*ZZ*/printf("wdir: compact loc %d reclen %d (dir %s/%d)\n",loc,ndp->d_reclen, +/*ZZ*/u.u_pdir->i_fs->fs_fsmnt,u.u_pdir->i_number); loc += ndp->d_reclen; bcopy(ndp, dp, dsize); } @@ -590,15 +609,18 @@ wdir(ip) */ if (dp->d_ino == 0) { if (spccnt + dsize < newsize) - panic("wdir: compact failed"); + panic("wdir: compact failed (1)"); +/*ZZ*/if(spccnt+dsize>512)panic("wdir: compact screwup"); u.u_dent.d_reclen = spccnt + dsize; } else { if (spccnt < newsize) - panic("wdir: compact failed"); + panic("wdir: compact failed (2)"); u.u_dent.d_reclen = spccnt; +/*ZZ*/if ((((char *)dp-bp->b_un.b_addr)&0x1ff)+dsize>512) panic("wdir: reclen"); dp->d_reclen = dsize; dp = (struct direct *)((char *)dp + dsize); } +/*ZZ*/if((((char*)dp-bp->b_un.b_addr)&0x1ff)+u.u_dent.d_reclen>512)panic("wdir: botch"); bcopy(&u.u_dent, dp, newsize); bwrite(bp); u.u_pdir->i_flag |= IUPD|ICHG; @@ -619,9 +641,9 @@ wdir(ip) * this is called from sumount()/sys3.c when dev is being unmounted */ #ifdef QUOTA -iflush(dev, qi); +iflush(dev, iq) dev_t dev; - struct inode *qi; + struct inode *iq; #else iflush(dev) dev_t dev; diff --git a/usr/src/sys/ufs/ufs/ufs_vnops.c b/usr/src/sys/ufs/ufs/ufs_vnops.c index f06ca840a9..883f021d38 100644 --- a/usr/src/sys/ufs/ufs/ufs_vnops.c +++ b/usr/src/sys/ufs/ufs/ufs_vnops.c @@ -1,4 +1,4 @@ -/* ufs_vnops.c 4.29 82/07/22 */ +/* ufs_vnops.c 4.30 82/07/24 */ #include "../h/param.h" #include "../h/systm.h" @@ -16,6 +16,7 @@ #include "../h/efs.h" #endif #include "../h/quota.h" +#include "../h/descrip.h" chdir() { @@ -78,7 +79,7 @@ open() /* * Creat system call. */ -creat() +ocreat() { register struct inode *ip; register struct a { @@ -130,6 +131,7 @@ open1(ip, mode, trf) if ((fp = falloc()) == NULL) goto out; fp->f_flag = mode&(FREAD|FWRITE); + fp->f_type = DTYPE_FILE; i = u.u_r.r_val1; fp->f_inode = ip; #ifdef EFS @@ -346,6 +348,8 @@ unlink() /* * first entry in block, so set d_ino to zero. */ +/*ZZ*/if(u.u_offset&0x1ff)printf("missed dir compact dir %s/%d off %d file %s\n" +/*ZZ*/,pp->i_fs->fs_fsmnt,pp->i_number,u.u_offset,u.u_dent.d_name); u.u_base = (caddr_t)&u.u_dent; u.u_count = DIRSIZ(&u.u_dent); u.u_dent.d_ino = 0; @@ -365,6 +369,8 @@ unlink() } ((struct direct *)(bp->b_un.b_addr + base))->d_reclen += u.u_dent.d_reclen; +/*ZZ*/if(((int)(bp->b_un.b_addr + base)&0x1ff)+u.u_dent.d_reclen>512) +/*ZZ*/ panic("unlink: reclen"); bwrite(bp); pp->i_flag |= IUPD|ICHG; } @@ -396,7 +402,7 @@ seek() fp = getf(uap->fdes); if (fp == NULL) return; - if (fp->f_flag&FSOCKET) { + if (fp->f_type == DTYPE_SOCKET) { u.u_error = ESPIPE; return; } @@ -479,7 +485,7 @@ fstat() return; } #endif - if (fp->f_flag & FSOCKET) + if (fp->f_type == DTYPE_SOCKET) u.u_error = sostat(fp->f_socket, uap->sb); else stat1(fp->f_inode, uap->sb); -- 2.20.1