diff options
-rw-r--r-- | sys/net/pf_table.c | 22 |
1 files changed, 20 insertions, 2 deletions
diff --git a/sys/net/pf_table.c b/sys/net/pf_table.c index f4d76f3805a..ab56c8d5ece 100644 --- a/sys/net/pf_table.c +++ b/sys/net/pf_table.c @@ -1,4 +1,4 @@ -/* $OpenBSD: pf_table.c,v 1.87 2010/10/23 15:38:18 tedu Exp $ */ +/* $OpenBSD: pf_table.c,v 1.88 2010/11/20 23:58:13 tedu Exp $ */ /* * Copyright (c) 2002 Cedric Berger @@ -61,6 +61,8 @@ copyout((from), (to), (size)) : \ (bcopy((from), (to), (size)), 0)) +#define YIELD(cnt, ok) do { if ((cnt % 1024 == 1023) && (ok)) yield(); } while (0) + #define FILLIN_SIN(sin, addr) \ do { \ (sin).sin_len = sizeof(sin); \ @@ -261,6 +263,7 @@ pfr_add_addrs(struct pfr_table *tbl, struct pfr_addr *addr, int size, return (ENOMEM); SLIST_INIT(&workq); for (i = 0; i < size; i++) { + YIELD(i, flags & PFR_FLAG_USERIOCTL); if (COPYIN(addr+i, &ad, sizeof(ad), flags)) senderr(EFAULT); if (pfr_validate_addr(&ad)) @@ -349,6 +352,7 @@ pfr_del_addrs(struct pfr_table *tbl, struct pfr_addr *addr, int size, } else { /* iterate over addresses to delete */ for (i = 0; i < size; i++) { + YIELD(i, flags & PFR_FLAG_USERIOCTL); if (COPYIN(addr+i, &ad, sizeof(ad), flags)) return (EFAULT); if (pfr_validate_addr(&ad)) @@ -360,6 +364,7 @@ pfr_del_addrs(struct pfr_table *tbl, struct pfr_addr *addr, int size, } SLIST_INIT(&workq); for (i = 0; i < size; i++) { + YIELD(i, flags & PFR_FLAG_USERIOCTL); if (COPYIN(addr+i, &ad, sizeof(ad), flags)) senderr(EFAULT); if (pfr_validate_addr(&ad)) @@ -429,6 +434,7 @@ pfr_set_addrs(struct pfr_table *tbl, struct pfr_addr *addr, int size, SLIST_INIT(&delq); SLIST_INIT(&changeq); for (i = 0; i < size; i++) { + YIELD(i, flags & PFR_FLAG_USERIOCTL); if (COPYIN(addr+i, &ad, sizeof(ad), flags)) senderr(EFAULT); if (pfr_validate_addr(&ad)) @@ -527,6 +533,7 @@ pfr_tst_addrs(struct pfr_table *tbl, struct pfr_addr *addr, int size, return (ESRCH); for (i = 0; i < size; i++) { + YIELD(i, flags & PFR_FLAG_USERIOCTL); if (COPYIN(addr+i, &ad, sizeof(ad), flags)) return (EFAULT); if (pfr_validate_addr(&ad)) @@ -650,6 +657,7 @@ pfr_clr_astats(struct pfr_table *tbl, struct pfr_addr *addr, int size, return (ESRCH); SLIST_INIT(&workq); for (i = 0; i < size; i++) { + YIELD(i, flags & PFR_FLAG_USERIOCTL); if (COPYIN(addr+i, &ad, sizeof(ad), flags)) senderr(EFAULT); if (pfr_validate_addr(&ad)) @@ -823,8 +831,10 @@ void pfr_destroy_kentries(struct pfr_kentryworkq *workq) { struct pfr_kentry *p, *q; + int i; - for (p = SLIST_FIRST(workq); p != NULL; p = q) { + for (i = 0, p = SLIST_FIRST(workq); p != NULL; i++, p = q) { + YIELD(i, 1); q = SLIST_NEXT(p, pfrke_workq); pfr_destroy_kentry(p); } @@ -855,6 +865,7 @@ pfr_insert_kentries(struct pfr_ktable *kt, } p->pfrke_tzero = tzero; ++n; + YIELD(n, 1); } kt->pfrkt_cnt += n; } @@ -892,6 +903,7 @@ pfr_remove_kentries(struct pfr_ktable *kt, SLIST_FOREACH(p, workq, pfrke_workq) { pfr_unroute_kentry(kt, p); ++n; + YIELD(n, 1); } kt->pfrkt_cnt -= n; pfr_destroy_kentries(workq); @@ -934,6 +946,7 @@ pfr_reset_feedback(struct pfr_addr *addr, int size, int flags) int i; for (i = 0; i < size; i++) { + YIELD(i, flags & PFR_FLAG_USERIOCTL); if (COPYIN(addr+i, &ad, sizeof(ad), flags)) break; ad.pfra_fback = PFR_FB_NONE; @@ -1171,6 +1184,7 @@ pfr_add_tables(struct pfr_table *tbl, int size, int *nadd, int flags) SLIST_INIT(&addq); SLIST_INIT(&changeq); for (i = 0; i < size; i++) { + YIELD(i, flags & PFR_FLAG_USERIOCTL); if (COPYIN(tbl+i, &key.pfrkt_t, sizeof(key.pfrkt_t), flags)) senderr(EFAULT); if (pfr_validate_table(&key.pfrkt_t, PFR_TFLAG_USRMASK, @@ -1247,6 +1261,7 @@ pfr_del_tables(struct pfr_table *tbl, int size, int *ndel, int flags) ACCEPT_FLAGS(flags, PFR_FLAG_DUMMY); SLIST_INIT(&workq); for (i = 0; i < size; i++) { + YIELD(i, flags & PFR_FLAG_USERIOCTL); if (COPYIN(tbl+i, &key.pfrkt_t, sizeof(key.pfrkt_t), flags)) return (EFAULT); if (pfr_validate_table(&key.pfrkt_t, 0, @@ -1364,6 +1379,7 @@ pfr_clr_tstats(struct pfr_table *tbl, int size, int *nzero, int flags) ACCEPT_FLAGS(flags, PFR_FLAG_DUMMY | PFR_FLAG_ADDRSTOO); SLIST_INIT(&workq); for (i = 0; i < size; i++) { + YIELD(i, flags & PFR_FLAG_USERIOCTL); if (COPYIN(tbl+i, &key.pfrkt_t, sizeof(key.pfrkt_t), flags)) return (EFAULT); if (pfr_validate_table(&key.pfrkt_t, 0, 0)) @@ -1397,6 +1413,7 @@ pfr_set_tflags(struct pfr_table *tbl, int size, int setflag, int clrflag, return (EINVAL); SLIST_INIT(&workq); for (i = 0; i < size; i++) { + YIELD(i, flags & PFR_FLAG_USERIOCTL); if (COPYIN(tbl+i, &key.pfrkt_t, sizeof(key.pfrkt_t), flags)) return (EFAULT); if (pfr_validate_table(&key.pfrkt_t, 0, @@ -1525,6 +1542,7 @@ _skip: } SLIST_INIT(&addrq); for (i = 0; i < size; i++) { + YIELD(i, flags & PFR_FLAG_USERIOCTL); if (COPYIN(addr+i, &ad, sizeof(ad), flags)) senderr(EFAULT); if (pfr_validate_addr(&ad)) |