version 1.141.2.4, 2008/03/23 02:05:01 |
version 1.155, 2008/03/21 21:55:00 |
|
|
/* uipc_socket.c,v 1.141.2.3 2008/01/09 01:56:28 matt Exp */ |
/* $NetBSD$ */ |
|
|
/*- |
/*- |
* Copyright (c) 2002, 2007, 2008 The NetBSD Foundation, Inc. |
* Copyright (c) 2002, 2007, 2008 The NetBSD Foundation, Inc. |
|
|
*/ |
*/ |
|
|
#include <sys/cdefs.h> |
#include <sys/cdefs.h> |
__KERNEL_RCSID(0, "uipc_socket.c,v 1.141.2.3 2008/01/09 01:56:28 matt Exp"); |
__KERNEL_RCSID(0, "$NetBSD$"); |
|
|
#include "opt_sock_counters.h" |
#include "opt_sock_counters.h" |
#include "opt_sosend_loan.h" |
#include "opt_sosend_loan.h" |
|
|
fsocreate(int domain, struct socket **sop, int type, int protocol, |
fsocreate(int domain, struct socket **sop, int type, int protocol, |
struct lwp *l, int *fdout) |
struct lwp *l, int *fdout) |
{ |
{ |
struct filedesc *fdp; |
|
struct socket *so; |
struct socket *so; |
struct file *fp; |
struct file *fp; |
int fd, error; |
int fd, error; |
|
|
fdp = l->l_proc->p_fd; |
if ((error = fd_allocfile(&fp, &fd)) != 0) |
/* falloc() will use the desciptor for us */ |
|
if ((error = falloc(l, &fp, &fd)) != 0) |
|
return (error); |
return (error); |
fp->f_flag = FREAD|FWRITE; |
fp->f_flag = FREAD|FWRITE; |
fp->f_type = DTYPE_SOCKET; |
fp->f_type = DTYPE_SOCKET; |
fp->f_ops = &socketops; |
fp->f_ops = &socketops; |
error = socreate(domain, &so, type, protocol, l); |
error = socreate(domain, &so, type, protocol, l); |
if (error != 0) { |
if (error != 0) { |
FILE_UNUSE(fp, l); |
fd_abort(curproc, fp, fd); |
fdremove(fdp, fd); |
|
ffree(fp); |
|
} else { |
} else { |
if (sop != NULL) |
if (sop != NULL) |
*sop = so; |
*sop = so; |
fp->f_data = so; |
fp->f_data = so; |
FILE_SET_MATURE(fp); |
fd_affix(curproc, fp, fd); |
FILE_UNUSE(fp, l); |
|
*fdout = fd; |
*fdout = fd; |
} |
} |
return error; |
return error; |
Line 1692 filt_sordetach(struct knote *kn) |
|
Line 1686 filt_sordetach(struct knote *kn) |
|
{ |
{ |
struct socket *so; |
struct socket *so; |
|
|
so = (struct socket *)kn->kn_fp->f_data; |
so = ((file_t *)kn->kn_obj)->f_data; |
SLIST_REMOVE(&so->so_rcv.sb_sel.sel_klist, kn, knote, kn_selnext); |
SLIST_REMOVE(&so->so_rcv.sb_sel.sel_klist, kn, knote, kn_selnext); |
if (SLIST_EMPTY(&so->so_rcv.sb_sel.sel_klist)) |
if (SLIST_EMPTY(&so->so_rcv.sb_sel.sel_klist)) |
so->so_rcv.sb_flags &= ~SB_KNOTE; |
so->so_rcv.sb_flags &= ~SB_KNOTE; |
Line 1704 filt_soread(struct knote *kn, long hint) |
|
Line 1698 filt_soread(struct knote *kn, long hint) |
|
{ |
{ |
struct socket *so; |
struct socket *so; |
|
|
so = (struct socket *)kn->kn_fp->f_data; |
so = ((file_t *)kn->kn_obj)->f_data; |
kn->kn_data = so->so_rcv.sb_cc; |
kn->kn_data = so->so_rcv.sb_cc; |
if (so->so_state & SS_CANTRCVMORE) { |
if (so->so_state & SS_CANTRCVMORE) { |
kn->kn_flags |= EV_EOF; |
kn->kn_flags |= EV_EOF; |
Line 1723 filt_sowdetach(struct knote *kn) |
|
Line 1717 filt_sowdetach(struct knote *kn) |
|
{ |
{ |
struct socket *so; |
struct socket *so; |
|
|
so = (struct socket *)kn->kn_fp->f_data; |
so = ((file_t *)kn->kn_obj)->f_data; |
SLIST_REMOVE(&so->so_snd.sb_sel.sel_klist, kn, knote, kn_selnext); |
SLIST_REMOVE(&so->so_snd.sb_sel.sel_klist, kn, knote, kn_selnext); |
if (SLIST_EMPTY(&so->so_snd.sb_sel.sel_klist)) |
if (SLIST_EMPTY(&so->so_snd.sb_sel.sel_klist)) |
so->so_snd.sb_flags &= ~SB_KNOTE; |
so->so_snd.sb_flags &= ~SB_KNOTE; |
Line 1735 filt_sowrite(struct knote *kn, long hint |
|
Line 1729 filt_sowrite(struct knote *kn, long hint |
|
{ |
{ |
struct socket *so; |
struct socket *so; |
|
|
so = (struct socket *)kn->kn_fp->f_data; |
so = ((file_t *)kn->kn_obj)->f_data; |
kn->kn_data = sbspace(&so->so_snd); |
kn->kn_data = sbspace(&so->so_snd); |
if (so->so_state & SS_CANTSENDMORE) { |
if (so->so_state & SS_CANTSENDMORE) { |
kn->kn_flags |= EV_EOF; |
kn->kn_flags |= EV_EOF; |
Line 1758 filt_solisten(struct knote *kn, long hin |
|
Line 1752 filt_solisten(struct knote *kn, long hin |
|
{ |
{ |
struct socket *so; |
struct socket *so; |
|
|
so = (struct socket *)kn->kn_fp->f_data; |
so = ((file_t *)kn->kn_obj)->f_data; |
|
|
/* |
/* |
* Set kn_data to number of incoming connections, not |
* Set kn_data to number of incoming connections, not |
Line 1781 soo_kqfilter(struct file *fp, struct kno |
|
Line 1775 soo_kqfilter(struct file *fp, struct kno |
|
struct socket *so; |
struct socket *so; |
struct sockbuf *sb; |
struct sockbuf *sb; |
|
|
so = (struct socket *)kn->kn_fp->f_data; |
so = ((file_t *)kn->kn_obj)->f_data; |
switch (kn->kn_filter) { |
switch (kn->kn_filter) { |
case EVFILT_READ: |
case EVFILT_READ: |
if (so->so_options & SO_ACCEPTCONN) |
if (so->so_options & SO_ACCEPTCONN) |