Project

General

Profile

dfly_evfilt_recv.patch

tautolog, 05/25/2018 09:48 PM

View differences:

sys/kern/kern_event.c
182 182
	&file_filtops,			/* EVFILT_EXCEPT */
183 183
	&user_filtops,			/* EVFILT_USER */
184 184
	&fs_filtops,			/* EVFILT_FS */
185
	&file_filtops,			/* EVFILT_RECV */
186
	&file_filtops,			/* EVFILT_SEND */
185 187
};
186 188

  
187 189
static struct knote_cache_list	knote_cache_lists[MAXCPU];
......
1184 1186
			 */
1185 1187
			fp = NULL;
1186 1188

  
1189
			kn->kn_sflags = kev->flags;
1187 1190
			kn->kn_sfflags = kev->fflags;
1188 1191
			kn->kn_sdata = kev->data;
1189 1192
			kev->fflags = 0;
......
1223 1226
			if (fops == &user_filtops) {
1224 1227
				filt_usertouch(kn, kev, EVENT_REGISTER);
1225 1228
			} else {
1229
				kn->kn_sflags = kev->flags;
1226 1230
				kn->kn_sfflags = kev->fflags;
1227 1231
				kn->kn_sdata = kev->data;
1228 1232
				kn->kn_kevent.udata = kev->udata;
......
1258 1262
		if (fops == &user_filtops) {
1259 1263
			filt_usertouch(kn, kev, EVENT_REGISTER);
1260 1264
		} else {
1265
			kn->kn_sflags = kev->flags;
1261 1266
			kn->kn_sfflags = kev->fflags;
1262 1267
			kn->kn_sdata = kev->data;
1263 1268
			kn->kn_kevent.udata = kev->udata;
sys/kern/uipc_socket.c
110 110
static void 	filt_sowdetach(struct knote *kn);
111 111
static int	filt_sowrite(struct knote *kn, long hint);
112 112
static int	filt_solisten(struct knote *kn, long hint);
113
static int 	filt_sorecv(struct knote *kn, long hint);
114
static int 	filt_sosend(struct knote *kn, long hint);
113 115

  
114 116
static int	soclose_sync(struct socket *so, int fflag);
115 117
static void	soclose_fast(struct socket *so);
......
122 124
	{ FILTEROP_ISFD|FILTEROP_MPSAFE, NULL, filt_sowdetach, filt_sowrite };
123 125
static struct filterops soexcept_filtops =
124 126
	{ FILTEROP_ISFD|FILTEROP_MPSAFE, NULL, filt_sordetach, filt_soread };
127
static struct filterops sorecv_filtops =
128
	{ FILTEROP_ISFD|FILTEROP_MPSAFE, NULL, filt_sordetach, filt_sorecv };
129
static struct filterops sosend_filtops =
130
	{ FILTEROP_ISFD|FILTEROP_MPSAFE, NULL, filt_sowdetach, filt_sosend };
125 131

  
126 132
MALLOC_DEFINE(M_SOCKET, "socket", "socket struct");
127 133
MALLOC_DEFINE(M_SONAME, "soname", "socket name");
......
2527 2533
		kn->kn_fop = &soexcept_filtops;
2528 2534
		ssb = &so->so_rcv;
2529 2535
		break;
2536
	case EVFILT_RECV:
2537
		kn->kn_fop = &sorecv_filtops;
2538
		ssb = &so->so_rcv;
2539
		break;
2540
	case EVFILT_SEND:
2541
		kn->kn_fop = &sosend_filtops;
2542
		ssb = &so->so_snd;
2543
		break;
2530 2544
	default:
2531 2545
		return (EOPNOTSUPP);
2532 2546
	}
......
2579 2593
		!TAILQ_EMPTY(&so->so_comp));
2580 2594
}
2581 2595

  
2596
/*ARGSUSED*/
2597
static int
2598
filt_sorecv(struct knote *kn, long hint __unused)
2599
{
2600
	struct socket *so = (struct socket *)kn->kn_fp->f_data;
2601
	int flags = 0;
2602
	int trigger = 0;
2603

  
2604
	kn->kn_flags |= EV_DISPATCH;
2605

  
2606
	kn->kn_data = so->so_rcv.ssb_cc;
2607
	if (kn->kn_sdata != kn->kn_data) {
2608
		kn->kn_sdata = kn->kn_data;
2609
		trigger = 1;
2610
	}
2611

  
2612
	if (so->so_state & SS_CANTRCVMORE) {
2613
		/*
2614
		 * Only set NODATA if all data has been exhausted.
2615
		 */
2616
		if (kn->kn_data == 0)
2617
			flags |= EV_NODATA;
2618
		flags |= EV_EOF;
2619
	}
2620

  
2621
	kn->kn_flags |= flags;
2622
	if ((kn->kn_sflags & kn->kn_flags) != kn->kn_flags) {
2623
		kn->kn_sflags = kn->kn_flags;
2624
		trigger = 1;
2625
	}
2626

  
2627
	kn->kn_fflags = so->so_error;
2628
	if (kn->kn_sfflags != kn->kn_fflags) {
2629
		kn->kn_sfflags = kn->kn_fflags;
2630
		trigger = 1;
2631
	}
2632

  
2633
	if (trigger && kn->kn_status & KN_DISABLED) {
2634
		kn->kn_status &= ~KN_DISABLED;
2635
	}
2636

  
2637
	return 1;
2638
}
2639

  
2582 2640
static void
2583 2641
filt_sowdetach(struct knote *kn)
2584 2642
{
......
2615 2673
	return (kn->kn_data >= so->so_snd.ssb_lowat);
2616 2674
}
2617 2675

  
2676
/*ARGSUSED*/
2677
static int
2678
filt_sosend(struct knote *kn, long hint __unused)
2679
{
2680
	struct socket *so = (struct socket *)kn->kn_fp->f_data;
2681
	int flags = 0;
2682
	int trigger = 0;
2683

  
2684
	kn->kn_flags |= EV_DISPATCH;
2685

  
2686
	if (((so->so_state & SS_ISCONNECTED) == 0) &&
2687
	    (so->so_proto->pr_flags & PR_CONNREQUIRED))
2688
		return (0);
2689

  
2690
	if (so->so_snd.ssb_flags & SSB_PREALLOC) {
2691
		kn->kn_data = ssb_space_prealloc(&so->so_snd);
2692
	} else {
2693
		kn->kn_data = ssb_space(&so->so_snd);
2694
	}
2695
	if (kn->kn_sdata != kn->kn_data) {
2696
		kn->kn_sdata = kn->kn_data;
2697
		trigger = 1;
2698
	}
2699

  
2700
	if (so->so_state & SS_CANTSENDMORE) {
2701
		flags |= (EV_EOF | EV_NODATA);
2702
	}
2703

  
2704
	kn->kn_flags |= flags;
2705
	if ((kn->kn_sflags & kn->kn_flags) != kn->kn_flags) {
2706
		kn->kn_sflags = kn->kn_flags;
2707
		trigger = 1;
2708
	}
2709

  
2710
	kn->kn_fflags = so->so_error;
2711
	if (kn->kn_sfflags != kn->kn_fflags) {
2712
		kn->kn_sfflags = kn->kn_fflags;
2713
		trigger = 1;
2714
	}
2715

  
2716
	if (trigger && kn->kn_status & KN_DISABLED) {
2717
		kn->kn_status &= ~KN_DISABLED;
2718
	}
2719

  
2720
	return 1;
2721
}
2722

  
2618 2723
/*ARGSUSED*/
2619 2724
static int
2620 2725
filt_solisten(struct knote *kn, long hint __unused)
sys/sys/event.h
47 47
#define EVFILT_EXCEPT		(-8)	/* exceptional conditions */
48 48
#define EVFILT_USER		(-9)	/* user events */
49 49
#define EVFILT_FS		(-10)	/* filesystem events */
50
#define EVFILT_RECV		(-11)	/* socket recv buffer */
51
#define EVFILT_SEND		(-12)	/* socket send buffer */
50 52

  
51 53
#define EVFILT_MARKER		0xF	/* placemarker for tailq */
52 54

  
53
#define EVFILT_SYSCOUNT		10
55
#define EVFILT_SYSCOUNT		12
54 56

  
55 57
#define EV_SET(kevp_, a, b, c, d, e, f) do {	\
56 58
	struct kevent *kevp = (kevp_);		\
......
203 205
	struct			kqueue *kn_kq;	/* which queue we are on */
204 206
	struct 			kevent kn_kevent;
205 207
	int			kn_status;
208
	int			kn_sflags;	/* saved flags */
206 209
	int			kn_sfflags;	/* saved filter flags */
207 210
	intptr_t		kn_sdata;	/* saved data field */
208 211
	union {