From 002c1265bf9676475d08e73e8d873cea9ee4a82e Mon Sep 17 00:00:00 2001 From: Matthew Dillon Date: Tue, 14 Sep 2010 16:28:53 -0700 Subject: [PATCH] network - Major netmsg retooling, part 1 * Remove all the netmsg shims and make all pr_usrreqs and some proto->pr_* requests directly netmsg'd. * Fix issues with tcp implied connects and tcp6->tcp4 fallbacks with implied connects. * Fix an issue with a stack-based udp netmsg (allocate it) * Consolidate struct ip6protosw and struct protosw into a single structure and normalize the API functions which differed between the two (primarily proto->pr_input()). * Remove protosw->pr_soport() * Replace varargs protocol *_input() functions (ongoing) with fixed arguments. --- sys/bus/usb/usb_ethersubr.c | 4 +- sys/dev/acpica5/acpi_cpu_pstate.c | 79 ++-- sys/dev/netif/aue/if_aue.c | 2 +- sys/kern/kern_poll.c | 138 ++++--- sys/kern/sys_socket.c | 9 +- sys/kern/uipc_domain.c | 26 +- sys/kern/uipc_msg.c | 474 +++++++--------------- sys/kern/uipc_proto.c | 61 +-- sys/kern/uipc_socket.c | 17 +- sys/kern/uipc_socket2.c | 98 +---- sys/kern/uipc_syscalls.c | 36 +- sys/kern/uipc_usrreq.c | 255 ++++++------ sys/net/bpf.c | 12 +- sys/net/bridge/bridgestp.c | 10 +- sys/net/bridge/if_bridge.c | 184 +++++---- sys/net/bridge/if_bridgevar.h | 6 +- sys/net/dummynet/ip_dummynet.c | 30 +- sys/net/dummynet/ip_dummynet_glue.c | 79 ++-- sys/net/gre/if_gre.c | 44 ++- sys/net/if.c | 49 +-- sys/net/if_ethersubr.c | 13 +- sys/net/if_poll.c | 154 ++++---- sys/net/if_var.h | 4 +- sys/net/ip_mroute/ip_mroute.c | 82 ++-- sys/net/ipfw/ip_fw2.c | 170 ++++---- sys/net/ipfw/ip_fw2_glue.c | 15 +- sys/net/netisr.c | 68 ++-- sys/net/netisr.h | 66 +--- sys/net/netmsg.h | 176 ++++++--- sys/net/netmsg2.h | 8 +- sys/net/pf/pf.c | 26 +- sys/net/pfil.c | 28 +- sys/net/ppp/if_ppp.c | 4 +- sys/net/raw_cb.h | 4 +- sys/net/raw_usrreq.c | 212 +++++----- sys/net/route.c | 135 ++++--- sys/net/rtsock.c | 160 ++++---- sys/net/stf/if_stf.c | 44 ++- sys/net/stf/if_stf.h | 2 +- sys/net/vlan/if_vlan.c | 108 +++-- sys/net/vlan/if_vlan_ether.c | 6 +- sys/net/vlan/if_vlan_ether.h | 4 +- sys/netbt/bt_input.c | 2 +- sys/netbt/bt_proto.c | 4 - sys/netbt/hci.h | 5 +- sys/netbt/hci_socket.c | 315 ++++++++------- sys/netbt/l2cap.h | 3 +- sys/netbt/l2cap_socket.c | 242 +++++++----- sys/netbt/rfcomm.h | 3 +- sys/netbt/rfcomm_socket.c | 255 +++++++----- sys/netbt/sco.h | 4 +- sys/netbt/sco_socket.c | 239 ++++++----- sys/netgraph/netgraph/ng_base.c | 8 +- sys/netgraph/socket/ng_socket.c | 222 ++++++----- sys/netinet/if_ether.c | 48 +-- sys/netinet/igmp.c | 33 +- sys/netinet/igmp_var.h | 2 +- sys/netinet/in.c | 117 +++--- sys/netinet/in_gif.c | 44 ++- sys/netinet/in_gif.h | 2 +- sys/netinet/in_pcb.c | 19 + sys/netinet/in_pcb.h | 4 + sys/netinet/in_proto.c | 571 +++++++++++++++++++-------- sys/netinet/in_var.h | 3 +- sys/netinet/ip_carp.c | 24 +- sys/netinet/ip_carp.h | 2 +- sys/netinet/ip_demux.c | 14 - sys/netinet/ip_divert.c | 145 ++++--- sys/netinet/ip_divert.h | 2 +- sys/netinet/ip_encap.c | 42 +- sys/netinet/ip_encap.h | 2 +- sys/netinet/ip_flow.c | 18 +- sys/netinet/ip_gre.c | 36 +- sys/netinet/ip_gre.h | 4 +- sys/netinet/ip_icmp.c | 28 +- sys/netinet/ip_icmp.h | 2 +- sys/netinet/ip_input.c | 54 ++- sys/netinet/ip_output.c | 18 +- sys/netinet/ip_var.h | 15 +- sys/netinet/pim_var.h | 2 +- sys/netinet/raw_ip.c | 227 ++++++----- sys/netinet/sctp_input.c | 33 +- sys/netinet/sctp_usrreq.c | 592 +++++++++++----------------- sys/netinet/sctp_var.h | 47 +-- sys/netinet/tcp_input.c | 35 +- sys/netinet/tcp_subr.c | 122 +++--- sys/netinet/tcp_syncache.c | 12 +- sys/netinet/tcp_timer.c | 16 +- sys/netinet/tcp_timer.h | 2 +- sys/netinet/tcp_usrreq.c | 530 ++++++++++++++----------- sys/netinet/tcp_var.h | 10 +- sys/netinet/udp_usrreq.c | 310 ++++++++------- sys/netinet/udp_var.h | 8 +- sys/netinet6/ah.h | 2 +- sys/netinet6/ah_input.c | 26 +- sys/netinet6/esp.h | 2 +- sys/netinet6/esp6.h | 3 +- sys/netinet6/esp_input.c | 42 +- sys/netinet6/icmp6.c | 18 +- sys/netinet6/in6.c | 15 + sys/netinet6/in6_gif.c | 28 +- sys/netinet6/in6_pcb.c | 39 ++ sys/netinet6/in6_pcb.h | 5 + sys/netinet6/in6_proto.c | 330 +++++++++++----- sys/netinet6/in6_var.h | 5 +- sys/netinet6/ip6_input.c | 34 +- sys/netinet6/ip6_output.c | 13 + sys/netinet6/ip6_var.h | 9 +- sys/netinet6/ip6protosw.h | 44 +-- sys/netinet6/ipcomp.h | 2 +- sys/netinet6/ipcomp_input.c | 26 +- sys/netinet6/raw_ip6.c | 214 ++++++---- sys/netinet6/sctp6_usrreq.c | 307 ++++++++------- sys/netinet6/tcp6_var.h | 3 +- sys/netinet6/udp6_usrreq.c | 193 +++++---- sys/netinet6/udp6_var.h | 2 +- sys/netproto/atalk/aarp.c | 4 +- sys/netproto/atalk/at_control.c | 2 +- sys/netproto/atalk/at_extern.h | 8 +- sys/netproto/atalk/at_proto.c | 20 +- sys/netproto/atalk/ddp_input.c | 8 +- sys/netproto/atalk/ddp_usrreq.c | 293 ++++++++------ sys/netproto/atm/atm_aal5.c | 501 ++++++++++++----------- sys/netproto/atm/atm_proto.c | 146 ++----- sys/netproto/atm/atm_subr.c | 10 +- sys/netproto/atm/atm_usrreq.c | 230 ++++++----- sys/netproto/atm/atm_var.h | 11 +- sys/netproto/atm/kern_include.h | 3 + sys/netproto/ipsec/ipsec6.h | 3 +- sys/netproto/ipsec/ipsec_input.c | 2 +- sys/netproto/ipx/ipx_ip.c | 24 +- sys/netproto/ipx/ipx_ip.h | 6 +- sys/netproto/key/keysock.c | 212 ++++++---- sys/sys/protosw.h | 173 ++++---- sys/sys/socketops.h | 15 +- sys/sys/un.h | 2 +- 136 files changed, 5595 insertions(+), 5039 deletions(-) diff --git a/sys/bus/usb/usb_ethersubr.c b/sys/bus/usb/usb_ethersubr.c index c284b98ced..3d0dfbce8b 100644 --- a/sys/bus/usb/usb_ethersubr.c +++ b/sys/bus/usb/usb_ethersubr.c @@ -75,9 +75,9 @@ static int netisr_inited = 0; static void -usbintr(struct netmsg *msg) +usbintr(netmsg_t msg) { - struct mbuf *m = ((struct netmsg_packet *)msg)->nm_packet; + struct mbuf *m = msg->packet.nm_packet; struct ifnet *ifp; /* not MPSAFE */ diff --git a/sys/dev/acpica5/acpi_cpu_pstate.c b/sys/dev/acpica5/acpi_cpu_pstate.c index dd155a9973..6fcf086a74 100644 --- a/sys/dev/acpica5/acpi_cpu_pstate.c +++ b/sys/dev/acpica5/acpi_cpu_pstate.c @@ -68,8 +68,7 @@ struct acpi_pst_softc; LIST_HEAD(acpi_pst_list, acpi_pst_softc); struct netmsg_acpi_pst { - struct netmsg nmsg; - + struct netmsg_base base; const struct acpi_pst_res *ctrl; const struct acpi_pst_res *status; }; @@ -133,11 +132,11 @@ static const struct acpi_pstate * static int acpi_pst_alloc_resource(device_t, ACPI_OBJECT *, int, struct acpi_pst_res *); -static void acpi_pst_check_csr_handler(struct netmsg *); -static void acpi_pst_check_pstates_handler(struct netmsg *); -static void acpi_pst_init_handler(struct netmsg *); -static void acpi_pst_set_pstate_handler(struct netmsg *); -static void acpi_pst_get_pstate_handler(struct netmsg *); +static void acpi_pst_check_csr_handler(netmsg_t); +static void acpi_pst_check_pstates_handler(netmsg_t); +static void acpi_pst_init_handler(netmsg_t); +static void acpi_pst_set_pstate_handler(netmsg_t); +static void acpi_pst_get_pstate_handler(netmsg_t); static int acpi_pst_sysctl_freqs(SYSCTL_HANDLER_ARGS); static int acpi_pst_sysctl_members(SYSCTL_HANDLER_ARGS); @@ -944,13 +943,13 @@ acpi_pst_sysctl_global(SYSCTL_HANDLER_ARGS) } static void -acpi_pst_check_csr_handler(struct netmsg *nmsg) +acpi_pst_check_csr_handler(netmsg_t msg) { - struct netmsg_acpi_pst *msg = (struct netmsg_acpi_pst *)nmsg; + struct netmsg_acpi_pst *rmsg = (struct netmsg_acpi_pst *)msg; int error; - error = acpi_pst_md->pmd_check_csr(msg->ctrl, msg->status); - lwkt_replymsg(&nmsg->nm_lmsg, error); + error = acpi_pst_md->pmd_check_csr(rmsg->ctrl, rmsg->status); + lwkt_replymsg(&rmsg->base.lmsg, error); } static int @@ -961,45 +960,45 @@ acpi_pst_check_csr(struct acpi_pst_softc *sc) if (acpi_pst_md == NULL) return 0; - netmsg_init(&msg.nmsg, NULL, &curthread->td_msgport, + netmsg_init(&msg.base, NULL, &curthread->td_msgport, MSGF_PRIORITY, acpi_pst_check_csr_handler); msg.ctrl = &sc->pst_creg; msg.status = &sc->pst_sreg; - return lwkt_domsg(cpu_portfn(sc->pst_cpuid), &msg.nmsg.nm_lmsg, 0); + return lwkt_domsg(cpu_portfn(sc->pst_cpuid), &msg.base.lmsg, 0); } static void -acpi_pst_check_pstates_handler(struct netmsg *nmsg) +acpi_pst_check_pstates_handler(netmsg_t msg) { int error; error = acpi_pst_md->pmd_check_pstates(acpi_pstates, acpi_npstates); - lwkt_replymsg(&nmsg->nm_lmsg, error); + lwkt_replymsg(&msg->lmsg, error); } static int acpi_pst_check_pstates(struct acpi_pst_softc *sc) { - struct netmsg nmsg; + struct netmsg_base msg; if (acpi_pst_md == NULL) return 0; - netmsg_init(&nmsg, NULL, &curthread->td_msgport, + netmsg_init(&msg, NULL, &curthread->td_msgport, MSGF_PRIORITY, acpi_pst_check_pstates_handler); - return lwkt_domsg(cpu_portfn(sc->pst_cpuid), &nmsg.nm_lmsg, 0); + return lwkt_domsg(cpu_portfn(sc->pst_cpuid), &msg.lmsg, 0); } static void -acpi_pst_init_handler(struct netmsg *nmsg) +acpi_pst_init_handler(netmsg_t msg) { - struct netmsg_acpi_pst *msg = (struct netmsg_acpi_pst *)nmsg; + struct netmsg_acpi_pst *rmsg = (struct netmsg_acpi_pst *)msg; int error; - error = acpi_pst_md->pmd_init(msg->ctrl, msg->status); - lwkt_replymsg(&nmsg->nm_lmsg, error); + error = acpi_pst_md->pmd_init(rmsg->ctrl, rmsg->status); + lwkt_replymsg(&rmsg->base.lmsg, error); } static int @@ -1010,23 +1009,23 @@ acpi_pst_init(struct acpi_pst_softc *sc) if (acpi_pst_md == NULL) return 0; - netmsg_init(&msg.nmsg, NULL, &curthread->td_msgport, + netmsg_init(&msg.base, NULL, &curthread->td_msgport, MSGF_PRIORITY, acpi_pst_init_handler); msg.ctrl = &sc->pst_creg; msg.status = &sc->pst_sreg; - return lwkt_domsg(cpu_portfn(sc->pst_cpuid), &msg.nmsg.nm_lmsg, 0); + return lwkt_domsg(cpu_portfn(sc->pst_cpuid), &msg.base.lmsg, 0); } static void -acpi_pst_set_pstate_handler(struct netmsg *nmsg) +acpi_pst_set_pstate_handler(netmsg_t msg) { - struct netmsg_acpi_pst *msg = (struct netmsg_acpi_pst *)nmsg; + struct netmsg_acpi_pst *rmsg = (struct netmsg_acpi_pst *)msg; int error; - error = acpi_pst_md->pmd_set_pstate(msg->ctrl, msg->status, - nmsg->nm_lmsg.u.ms_resultp); - lwkt_replymsg(&nmsg->nm_lmsg, error); + error = acpi_pst_md->pmd_set_pstate(rmsg->ctrl, rmsg->status, + rmsg->base.lmsg.u.ms_resultp); + lwkt_replymsg(&rmsg->base.lmsg, error); } static int @@ -1036,25 +1035,25 @@ acpi_pst_set_pstate(struct acpi_pst_softc *sc, const struct acpi_pstate *pstate) KKASSERT(acpi_pst_md != NULL); - netmsg_init(&msg.nmsg, NULL, &curthread->td_msgport, + netmsg_init(&msg.base, NULL, &curthread->td_msgport, MSGF_PRIORITY, acpi_pst_set_pstate_handler); - msg.nmsg.nm_lmsg.u.ms_resultp = __DECONST(void *, pstate); + msg.base.lmsg.u.ms_resultp = __DECONST(void *, pstate); msg.ctrl = &sc->pst_creg; msg.status = &sc->pst_sreg; - return lwkt_domsg(cpu_portfn(sc->pst_cpuid), &msg.nmsg.nm_lmsg, 0); + return lwkt_domsg(cpu_portfn(sc->pst_cpuid), &msg.base.lmsg, 0); } static void -acpi_pst_get_pstate_handler(struct netmsg *nmsg) +acpi_pst_get_pstate_handler(netmsg_t msg) { - struct netmsg_acpi_pst *msg = (struct netmsg_acpi_pst *)nmsg; + struct netmsg_acpi_pst *rmsg = (struct netmsg_acpi_pst *)msg; const struct acpi_pstate *pstate; - pstate = acpi_pst_md->pmd_get_pstate(msg->status, acpi_pstates, + pstate = acpi_pst_md->pmd_get_pstate(rmsg->status, acpi_pstates, acpi_npstates); - nmsg->nm_lmsg.u.ms_resultp = __DECONST(void *, pstate); - lwkt_replymsg(&nmsg->nm_lmsg, 0); + rmsg->base.lmsg.u.ms_resultp = __DECONST(void *, pstate); + lwkt_replymsg(&rmsg->base.lmsg, 0); } static const struct acpi_pstate * @@ -1065,12 +1064,12 @@ acpi_pst_get_pstate(struct acpi_pst_softc *sc) if (acpi_pst_md == NULL) return 0; - netmsg_init(&msg.nmsg, NULL, &curthread->td_msgport, + netmsg_init(&msg.base, NULL, &curthread->td_msgport, MSGF_PRIORITY, acpi_pst_get_pstate_handler); msg.status = &sc->pst_sreg; - lwkt_domsg(cpu_portfn(sc->pst_cpuid), &msg.nmsg.nm_lmsg, 0); - return msg.nmsg.nm_lmsg.u.ms_resultp; + lwkt_domsg(cpu_portfn(sc->pst_cpuid), &msg.base.lmsg, 0); + return msg.base.lmsg.u.ms_resultp; } static int diff --git a/sys/dev/netif/aue/if_aue.c b/sys/dev/netif/aue/if_aue.c index f424d56d73..a3ae47b2ab 100644 --- a/sys/dev/netif/aue/if_aue.c +++ b/sys/dev/netif/aue/if_aue.c @@ -971,7 +971,7 @@ static void aue_start_ipifunc(void *arg) { struct ifnet *ifp = arg; - struct lwkt_msg *lmsg = &ifp->if_start_nmsg[mycpuid].nm_lmsg; + struct lwkt_msg *lmsg = &ifp->if_start_nmsg[mycpuid].lmsg; crit_enter(); if (lmsg->ms_flags & MSGF_DONE) diff --git a/sys/kern/kern_poll.c b/sys/kern/kern_poll.c index 97a983eb4d..a627bb1658 100644 --- a/sys/kern/kern_poll.c +++ b/sys/kern/kern_poll.c @@ -136,8 +136,8 @@ struct pollctx { int polling_enabled; /* tunable */ int pollhz; /* tunable */ - struct netmsg poll_netmsg; - struct netmsg poll_more_netmsg; + struct netmsg_base poll_netmsg; + struct netmsg_base poll_more_netmsg; }; static struct pollctx *poll_context[POLLCTX_MAX]; @@ -169,15 +169,15 @@ static int poll_each_burst = POLL_EACH_BURST; TUNABLE_INT("kern.polling.each_burst", &poll_each_burst); /* Netisr handlers */ -static void netisr_poll(struct netmsg *); -static void netisr_pollmore(struct netmsg *); -static void poll_register(struct netmsg *); -static void poll_deregister(struct netmsg *); -static void poll_sysctl_pollhz(struct netmsg *); -static void poll_sysctl_polling(struct netmsg *); -static void poll_sysctl_regfrac(struct netmsg *); -static void poll_sysctl_burstmax(struct netmsg *); -static void poll_sysctl_eachburst(struct netmsg *); +static void netisr_poll(netmsg_t); +static void netisr_pollmore(netmsg_t); +static void poll_register(netmsg_t); +static void poll_deregister(netmsg_t); +static void poll_sysctl_pollhz(netmsg_t); +static void poll_sysctl_polling(netmsg_t); +static void poll_sysctl_regfrac(netmsg_t); +static void poll_sysctl_burstmax(netmsg_t); +static void poll_sysctl_eachburst(netmsg_t); /* Systimer handler */ static void pollclock(systimer_t, struct intrframe *); @@ -191,8 +191,6 @@ static int sysctl_eachburst(SYSCTL_HANDLER_ARGS); static void poll_add_sysctl(struct sysctl_ctx_list *, struct sysctl_oid_list *, struct pollctx *); -static void schedpoll_oncpu(struct netmsg *); - void init_device_poll_pcpu(int); /* per-cpu init routine */ #define POLL_KTR_STRING "ifp=%p" @@ -260,13 +258,13 @@ init_device_poll_pcpu(int cpuid) netmsg_init(&pctx->poll_netmsg, NULL, &netisr_adone_rport, 0, netisr_poll); #ifdef INVARIANTS - pctx->poll_netmsg.nm_lmsg.u.ms_resultp = pctx; + pctx->poll_netmsg.lmsg.u.ms_resultp = pctx; #endif netmsg_init(&pctx->poll_more_netmsg, NULL, &netisr_adone_rport, 0, netisr_pollmore); #ifdef INVARIANTS - pctx->poll_more_netmsg.nm_lmsg.u.ms_resultp = pctx; + pctx->poll_more_netmsg.lmsg.u.ms_resultp = pctx; #endif KASSERT(cpuid < POLLCTX_MAX, ("cpu id must < %d", cpuid)); @@ -301,24 +299,24 @@ init_device_poll_pcpu(int cpuid) } static void -schedpoll_oncpu(struct netmsg *msg) +schedpoll_oncpu(netmsg_t msg) { - if (msg->nm_lmsg.ms_flags & MSGF_DONE) - lwkt_sendmsg(cpu_portfn(mycpuid), &msg->nm_lmsg); + if (msg->lmsg.ms_flags & MSGF_DONE) + lwkt_sendmsg(cpu_portfn(mycpuid), &msg->lmsg); } static __inline void schedpoll(struct pollctx *pctx) { crit_enter(); - schedpoll_oncpu(&pctx->poll_netmsg); + schedpoll_oncpu((netmsg_t)&pctx->poll_netmsg); crit_exit(); } static __inline void schedpollmore(struct pollctx *pctx) { - schedpoll_oncpu(&pctx->poll_more_netmsg); + schedpoll_oncpu((netmsg_t)&pctx->poll_more_netmsg); } /* @@ -328,7 +326,7 @@ static int sysctl_pollhz(SYSCTL_HANDLER_ARGS) { struct pollctx *pctx = arg1; - struct netmsg msg; + struct netmsg_base msg; lwkt_port_t port; int error, phz; @@ -343,10 +341,10 @@ sysctl_pollhz(SYSCTL_HANDLER_ARGS) netmsg_init(&msg, NULL, &curthread->td_msgport, 0, poll_sysctl_pollhz); - msg.nm_lmsg.u.ms_result = phz; + msg.lmsg.u.ms_result = phz; port = cpu_portfn(pctx->poll_cpuid); - lwkt_domsg(port, &msg.nm_lmsg, 0); + lwkt_domsg(port, &msg.lmsg, 0); return 0; } @@ -357,7 +355,7 @@ static int sysctl_polling(SYSCTL_HANDLER_ARGS) { struct pollctx *pctx = arg1; - struct netmsg msg; + struct netmsg_base msg; lwkt_port_t port; int error, enabled; @@ -368,10 +366,10 @@ sysctl_polling(SYSCTL_HANDLER_ARGS) netmsg_init(&msg, NULL, &curthread->td_msgport, 0, poll_sysctl_polling); - msg.nm_lmsg.u.ms_result = enabled; + msg.lmsg.u.ms_result = enabled; port = cpu_portfn(pctx->poll_cpuid); - lwkt_domsg(port, &msg.nm_lmsg, 0); + lwkt_domsg(port, &msg.lmsg, 0); return 0; } @@ -379,7 +377,7 @@ static int sysctl_regfrac(SYSCTL_HANDLER_ARGS) { struct pollctx *pctx = arg1; - struct netmsg msg; + struct netmsg_base msg; lwkt_port_t port; uint32_t reg_frac; int error; @@ -391,10 +389,10 @@ sysctl_regfrac(SYSCTL_HANDLER_ARGS) netmsg_init(&msg, NULL, &curthread->td_msgport, 0, poll_sysctl_regfrac); - msg.nm_lmsg.u.ms_result = reg_frac; + msg.lmsg.u.ms_result = reg_frac; port = cpu_portfn(pctx->poll_cpuid); - lwkt_domsg(port, &msg.nm_lmsg, 0); + lwkt_domsg(port, &msg.lmsg, 0); return 0; } @@ -402,7 +400,7 @@ static int sysctl_burstmax(SYSCTL_HANDLER_ARGS) { struct pollctx *pctx = arg1; - struct netmsg msg; + struct netmsg_base msg; lwkt_port_t port; uint32_t burst_max; int error; @@ -418,10 +416,10 @@ sysctl_burstmax(SYSCTL_HANDLER_ARGS) netmsg_init(&msg, NULL, &curthread->td_msgport, 0, poll_sysctl_burstmax); - msg.nm_lmsg.u.ms_result = burst_max; + msg.lmsg.u.ms_result = burst_max; port = cpu_portfn(pctx->poll_cpuid); - lwkt_domsg(port, &msg.nm_lmsg, 0); + lwkt_domsg(port, &msg.lmsg, 0); return 0; } @@ -429,7 +427,7 @@ static int sysctl_eachburst(SYSCTL_HANDLER_ARGS) { struct pollctx *pctx = arg1; - struct netmsg msg; + struct netmsg_base msg; lwkt_port_t port; uint32_t each_burst; int error; @@ -441,10 +439,10 @@ sysctl_eachburst(SYSCTL_HANDLER_ARGS) netmsg_init(&msg, NULL, &curthread->td_msgport, 0, poll_sysctl_eachburst); - msg.nm_lmsg.u.ms_result = each_burst; + msg.lmsg.u.ms_result = each_burst; port = cpu_portfn(pctx->poll_cpuid); - lwkt_domsg(port, &msg.nm_lmsg, 0); + lwkt_domsg(port, &msg.lmsg, 0); return 0; } @@ -518,7 +516,7 @@ pollclock(systimer_t info, struct intrframe *frame __unused) /* ARGSUSED */ static void -netisr_pollmore(struct netmsg *msg) +netisr_pollmore(netmsg_t msg) { struct pollctx *pctx; struct timeval t; @@ -531,9 +529,9 @@ netisr_pollmore(struct netmsg *msg) pctx = poll_context[cpuid]; KKASSERT(pctx != NULL); KKASSERT(pctx->poll_cpuid == cpuid); - KKASSERT(pctx == msg->nm_lmsg.u.ms_resultp); + KKASSERT(pctx == msg->lmsg.u.ms_resultp); - lwkt_replymsg(&msg->nm_lmsg, 0); + lwkt_replymsg(&msg->lmsg, 0); if (pctx->poll_handlers == 0) return; @@ -594,7 +592,7 @@ netisr_pollmore(struct netmsg *msg) */ /* ARGSUSED */ static void -netisr_poll(struct netmsg *msg) +netisr_poll(netmsg_t msg) { struct pollctx *pctx; int i, cycles, cpuid; @@ -606,10 +604,10 @@ netisr_poll(struct netmsg *msg) pctx = poll_context[cpuid]; KKASSERT(pctx != NULL); KKASSERT(pctx->poll_cpuid == cpuid); - KKASSERT(pctx == msg->nm_lmsg.u.ms_resultp); + KKASSERT(pctx == msg->lmsg.u.ms_resultp); crit_enter(); - lwkt_replymsg(&msg->nm_lmsg, 0); + lwkt_replymsg(&msg->lmsg, 0); crit_exit(); if (pctx->poll_handlers == 0) @@ -657,9 +655,9 @@ netisr_poll(struct netmsg *msg) } static void -poll_register(struct netmsg *msg) +poll_register(netmsg_t msg) { - struct ifnet *ifp = msg->nm_lmsg.u.ms_resultp; + struct ifnet *ifp = msg->lmsg.u.ms_resultp; struct pollctx *pctx; int rc, cpuid; @@ -706,7 +704,7 @@ poll_register(struct netmsg *msg) } } back: - lwkt_replymsg(&msg->nm_lmsg, rc); + lwkt_replymsg(&msg->lmsg, rc); } /* @@ -728,7 +726,7 @@ ether_poll_register(struct ifnet *ifp) int ether_pollcpu_register(struct ifnet *ifp, int cpuid) { - struct netmsg msg; + struct netmsg_base msg; lwkt_port_t port; int rc; @@ -768,12 +766,12 @@ ether_pollcpu_register(struct ifnet *ifp, int cpuid) netmsg_init(&msg, NULL, &curthread->td_msgport, 0, poll_register); - msg.nm_lmsg.u.ms_resultp = ifp; + msg.lmsg.u.ms_resultp = ifp; port = cpu_portfn(cpuid); - lwkt_domsg(port, &msg.nm_lmsg, 0); + lwkt_domsg(port, &msg.lmsg, 0); - if (msg.nm_lmsg.ms_error) { + if (msg.lmsg.ms_error) { ifnet_serialize_all(ifp); ifp->if_flags &= ~IFF_POLLING; ifp->if_poll_cpuid = -1; @@ -790,9 +788,9 @@ ether_pollcpu_register(struct ifnet *ifp, int cpuid) } static void -poll_deregister(struct netmsg *msg) +poll_deregister(netmsg_t msg) { - struct ifnet *ifp = msg->nm_lmsg.u.ms_resultp; + struct ifnet *ifp = msg->lmsg.u.ms_resultp; struct pollctx *pctx; int rc, i, cpuid; @@ -823,7 +821,7 @@ poll_deregister(struct netmsg *msg) } rc = 0; } - lwkt_replymsg(&msg->nm_lmsg, rc); + lwkt_replymsg(&msg->lmsg, rc); } /* @@ -833,7 +831,7 @@ poll_deregister(struct netmsg *msg) int ether_poll_deregister(struct ifnet *ifp) { - struct netmsg msg; + struct netmsg_base msg; lwkt_port_t port; int rc, cpuid; @@ -862,12 +860,12 @@ ether_poll_deregister(struct ifnet *ifp) netmsg_init(&msg, NULL, &curthread->td_msgport, 0, poll_deregister); - msg.nm_lmsg.u.ms_resultp = ifp; + msg.lmsg.u.ms_resultp = ifp; port = cpu_portfn(cpuid); - lwkt_domsg(port, &msg.nm_lmsg, 0); + lwkt_domsg(port, &msg.lmsg, 0); - if (!msg.nm_lmsg.ms_error) { + if (!msg.lmsg.ms_error) { ifnet_serialize_all(ifp); if (ifp->if_flags & IFF_RUNNING) ifp->if_poll(ifp, POLL_DEREGISTER, 1); @@ -942,7 +940,7 @@ poll_add_sysctl(struct sysctl_ctx_list *ctx, struct sysctl_oid_list *parent, } static void -poll_sysctl_pollhz(struct netmsg *msg) +poll_sysctl_pollhz(netmsg_t msg) { struct pollctx *pctx; int cpuid; @@ -960,7 +958,7 @@ poll_sysctl_pollhz(struct netmsg *msg) * Polling systimer frequency will be adjusted once polling * is enabled and there are registered devices. */ - pctx->pollhz = msg->nm_lmsg.u.ms_result; + pctx->pollhz = msg->lmsg.u.ms_result; if (pctx->polling_enabled && pctx->poll_handlers) systimer_adjust_periodic(&pctx->pollclock, pctx->pollhz); @@ -973,11 +971,11 @@ poll_sysctl_pollhz(struct netmsg *msg) pctx->reg_frac_count = pctx->reg_frac - 1; } - lwkt_replymsg(&msg->nm_lmsg, 0); + lwkt_replymsg(&msg->lmsg, 0); } static void -poll_sysctl_polling(struct netmsg *msg) +poll_sysctl_polling(netmsg_t msg) { struct pollctx *pctx; int cpuid; @@ -993,7 +991,7 @@ poll_sysctl_polling(struct netmsg *msg) * If polling is disabled or there is no device registered, * cut the polling systimer frequency to 1hz. */ - pctx->polling_enabled = msg->nm_lmsg.u.ms_result; + pctx->polling_enabled = msg->lmsg.u.ms_result; if (pctx->polling_enabled && pctx->poll_handlers) { systimer_adjust_periodic(&pctx->pollclock, pctx->pollhz); } else { @@ -1030,11 +1028,11 @@ poll_sysctl_polling(struct netmsg *msg) pctx->poll_handlers = 0; } - lwkt_replymsg(&msg->nm_lmsg, 0); + lwkt_replymsg(&msg->lmsg, 0); } static void -poll_sysctl_regfrac(struct netmsg *msg) +poll_sysctl_regfrac(netmsg_t msg) { struct pollctx *pctx; uint32_t reg_frac; @@ -1047,7 +1045,7 @@ poll_sysctl_regfrac(struct netmsg *msg) KKASSERT(pctx != NULL); KKASSERT(pctx->poll_cpuid == cpuid); - reg_frac = msg->nm_lmsg.u.ms_result; + reg_frac = msg->lmsg.u.ms_result; if (reg_frac > pctx->pollhz) reg_frac = pctx->pollhz; else if (reg_frac < 1) @@ -1057,11 +1055,11 @@ poll_sysctl_regfrac(struct netmsg *msg) if (pctx->reg_frac_count > pctx->reg_frac) pctx->reg_frac_count = pctx->reg_frac - 1; - lwkt_replymsg(&msg->nm_lmsg, 0); + lwkt_replymsg(&msg->lmsg, 0); } static void -poll_sysctl_burstmax(struct netmsg *msg) +poll_sysctl_burstmax(netmsg_t msg) { struct pollctx *pctx; int cpuid; @@ -1073,7 +1071,7 @@ poll_sysctl_burstmax(struct netmsg *msg) KKASSERT(pctx != NULL); KKASSERT(pctx->poll_cpuid == cpuid); - pctx->poll_burst_max = msg->nm_lmsg.u.ms_result; + pctx->poll_burst_max = msg->lmsg.u.ms_result; if (pctx->poll_each_burst > pctx->poll_burst_max) pctx->poll_each_burst = pctx->poll_burst_max; if (pctx->poll_burst > pctx->poll_burst_max) @@ -1081,11 +1079,11 @@ poll_sysctl_burstmax(struct netmsg *msg) if (pctx->residual_burst > pctx->poll_burst_max) pctx->residual_burst = pctx->poll_burst_max; - lwkt_replymsg(&msg->nm_lmsg, 0); + lwkt_replymsg(&msg->lmsg, 0); } static void -poll_sysctl_eachburst(struct netmsg *msg) +poll_sysctl_eachburst(netmsg_t msg) { struct pollctx *pctx; uint32_t each_burst; @@ -1098,12 +1096,12 @@ poll_sysctl_eachburst(struct netmsg *msg) KKASSERT(pctx != NULL); KKASSERT(pctx->poll_cpuid == cpuid); - each_burst = msg->nm_lmsg.u.ms_result; + each_burst = msg->lmsg.u.ms_result; if (each_burst > pctx->poll_burst_max) each_burst = pctx->poll_burst_max; else if (each_burst < 1) each_burst = 1; pctx->poll_each_burst = each_burst; - lwkt_replymsg(&msg->nm_lmsg, 0); + lwkt_replymsg(&msg->lmsg, 0); } diff --git a/sys/kern/sys_socket.c b/sys/kern/sys_socket.c index 92527aa161..504234c5ce 100644 --- a/sys/kern/sys_socket.c +++ b/sys/kern/sys_socket.c @@ -175,12 +175,13 @@ soo_ioctl(struct file *fp, u_long cmd, caddr_t data, * interface and routing ioctls should have a * different entry since a socket's unnecessary */ - if (IOCGROUP(cmd) == 'i') + if (IOCGROUP(cmd) == 'i') { error = ifioctl(so, cmd, data, cred); - else if (IOCGROUP(cmd) == 'r') + } else if (IOCGROUP(cmd) == 'r') { error = rtioctl(cmd, data, cred); - else - error = so_pru_control(so, cmd, data, NULL); + } else { + error = so_pru_control_direct(so, cmd, data, NULL); + } break; } rel_mplock(); diff --git a/sys/kern/uipc_domain.c b/sys/kern/uipc_domain.c index 7fd6efc27c..a0555c4ea9 100644 --- a/sys/kern/uipc_domain.c +++ b/sys/kern/uipc_domain.c @@ -78,12 +78,13 @@ static struct callout pfslowtimo_ch; * Note: you cant unload it again because a socket may be using it. * XXX can't fail at this time. */ +#define PR_NOTSUPP(pr, label) \ + if (pr->pr_ ## label == NULL) \ + pr->pr_ ## label = pr_generic_notsupp; + #define PRU_NOTSUPP(pu, label) \ if (pu->pru_ ## label == NULL) \ - pu->pru_ ## label = pru_ ## label ## _notsupp; -#define PRU_NULL(pu, label) \ - if (pu->pru_ ## label == NULL) \ - pu->pru_ ## label = pru_ ## label ## _null; + pu->pru_ ## label = pr_generic_notsupp; static void net_init_domain(struct domain *dp) @@ -92,13 +93,17 @@ net_init_domain(struct domain *dp) struct pr_usrreqs *pu; crit_enter(); + if (dp->dom_init) (*dp->dom_init)(); + for (pr = dp->dom_protosw; pr < dp->dom_protoswNPROTOSW; pr++) { pu = pr->pr_usrreqs; - if (pu == NULL) + if (pu == NULL) { panic("domaininit: %ssw[%ld] has no usrreqs!", dp->dom_name, (long)(pr - dp->dom_protosw)); + } + PR_NOTSUPP(pr, ctloutput); PRU_NOTSUPP(pu, accept); PRU_NOTSUPP(pu, bind); PRU_NOTSUPP(pu, connect); @@ -109,12 +114,15 @@ net_init_domain(struct domain *dp) PRU_NOTSUPP(pu, peeraddr); PRU_NOTSUPP(pu, rcvd); PRU_NOTSUPP(pu, rcvoob); - PRU_NULL(pu, sense); PRU_NOTSUPP(pu, shutdown); PRU_NOTSUPP(pu, sockaddr); - PRU_NOTSUPP(pu, sosend); - PRU_NOTSUPP(pu, soreceive); - PRU_NOTSUPP(pu, ctloutput); + + if (pu->pru_sense == NULL) + pu->pru_sense = pru_sense_null; + if (pu->pru_sosend == NULL) + pu->pru_sosend = pru_sosend_notsupp; + if (pu->pru_soreceive == NULL) + pu->pru_soreceive = pru_soreceive_notsupp; if (pr->pr_init) (*pr->pr_init)(); diff --git a/sys/kern/uipc_msg.c b/sys/kern/uipc_msg.c index 1c9e786e02..61a4cc26a5 100644 --- a/sys/kern/uipc_msg.c +++ b/sys/kern/uipc_msg.c @@ -58,10 +58,9 @@ so_pru_abort(struct socket *so) { struct netmsg_pru_abort msg; - netmsg_init(&msg.nm_netmsg, so, &curthread->td_msgport, - 0, netmsg_pru_abort); - msg.nm_prufn = so->so_proto->pr_usrreqs->pru_abort; - (void)lwkt_domsg(so->so_port, &msg.nm_netmsg.nm_lmsg, 0); + netmsg_init(&msg.base, so, &curthread->td_msgport, + 0, so->so_proto->pr_usrreqs->pru_abort); + (void)lwkt_domsg(so->so_port, &msg.base.lmsg, 0); } /* @@ -74,10 +73,9 @@ so_pru_aborta(struct socket *so) struct netmsg_pru_abort *msg; msg = kmalloc(sizeof(*msg), M_LWKTMSG, M_WAITOK | M_ZERO); - netmsg_init(&msg->nm_netmsg, so, &netisr_afree_rport, - 0, netmsg_pru_abort); - msg->nm_prufn = so->so_proto->pr_usrreqs->pru_abort; - lwkt_sendmsg(so->so_port, &msg->nm_netmsg.nm_lmsg); + netmsg_init(&msg->base, so, &netisr_afree_rport, + 0, so->so_proto->pr_usrreqs->pru_abort); + lwkt_sendmsg(so->so_port, &msg->base.lmsg); } /* @@ -87,286 +85,278 @@ so_pru_aborta(struct socket *so) void so_pru_abort_oncpu(struct socket *so) { - so->so_proto->pr_usrreqs->pru_abort(so); + struct netmsg_pru_abort msg; + netisr_fn_t func = so->so_proto->pr_usrreqs->pru_abort; + + netmsg_init(&msg.base, so, &netisr_adone_rport, 0, func); + msg.base.lmsg.ms_flags &= ~(MSGF_REPLY | MSGF_DONE); + msg.base.lmsg.ms_flags |= MSGF_SYNC; + func((netmsg_t)&msg); } +/* + * WARNING! Synchronous call from user context + */ int -so_pru_accept(struct socket *so, struct sockaddr **nam) +so_pru_accept_direct(struct socket *so, struct sockaddr **nam) { - /* Block (memory allocation) in process context. XXX JH */ - return ((*so->so_proto->pr_usrreqs->pru_accept)(so, nam)); - -#ifdef notdef - int error; struct netmsg_pru_accept msg; + netisr_fn_t func = so->so_proto->pr_usrreqs->pru_accept; - netmsg_init(&msg.nm_netmsg, so, &curthread->td_msgport, - 0, netmsg_pru_accept); - msg.nm_prufn = so->so_proto->pr_usrreqs->pru_accept; + netmsg_init(&msg.base, so, &netisr_adone_rport, 0, func); + msg.base.lmsg.ms_flags &= ~(MSGF_REPLY | MSGF_DONE); + msg.base.lmsg.ms_flags |= MSGF_SYNC; msg.nm_nam = nam; - error = lwkt_domsg(so->so_port, &msg.nm_netmsg.nm_lmsg, 0); - return (error); -#endif + func((netmsg_t)&msg); + return(msg.base.lmsg.ms_error); } int so_pru_attach(struct socket *so, int proto, struct pru_attach_info *ai) { - int error; struct netmsg_pru_attach msg; + int error; - netmsg_init(&msg.nm_netmsg, so, &curthread->td_msgport, - 0, netmsg_pru_attach); - msg.nm_prufn = so->so_proto->pr_usrreqs->pru_attach; + netmsg_init(&msg.base, so, &curthread->td_msgport, + 0, so->so_proto->pr_usrreqs->pru_attach); msg.nm_proto = proto; msg.nm_ai = ai; - error = lwkt_domsg(so->so_port, &msg.nm_netmsg.nm_lmsg, 0); + error = lwkt_domsg(so->so_port, &msg.base.lmsg, 0); return (error); } +int +so_pru_attach_direct(struct socket *so, int proto, struct pru_attach_info *ai) +{ + struct netmsg_pru_attach msg; + netisr_fn_t func = so->so_proto->pr_usrreqs->pru_attach; + + netmsg_init(&msg.base, so, &netisr_adone_rport, 0, func); + msg.base.lmsg.ms_flags &= ~(MSGF_REPLY | MSGF_DONE); + msg.base.lmsg.ms_flags |= MSGF_SYNC; + msg.nm_proto = proto; + msg.nm_ai = ai; + func((netmsg_t)&msg); + return(msg.base.lmsg.ms_error); +} + /* * NOTE: If the target port changes the bind operation will deal with it. */ int so_pru_bind(struct socket *so, struct sockaddr *nam, struct thread *td) { - int error; struct netmsg_pru_bind msg; + int error; -#if 0 - port = so->so_proto->pr_mport(NULL, nam, NULL); -#endif - netmsg_init(&msg.nm_netmsg, so, &curthread->td_msgport, - 0, netmsg_pru_bind); - msg.nm_prufn = so->so_proto->pr_usrreqs->pru_bind; + netmsg_init(&msg.base, so, &curthread->td_msgport, + 0, so->so_proto->pr_usrreqs->pru_bind); msg.nm_nam = nam; - msg.nm_td = td; /* used only for prison_ip() XXX JH */ - error = lwkt_domsg(so->so_port, &msg.nm_netmsg.nm_lmsg, 0); + msg.nm_td = td; /* used only for prison_ip() */ + error = lwkt_domsg(so->so_port, &msg.base.lmsg, 0); return (error); } int so_pru_connect(struct socket *so, struct sockaddr *nam, struct thread *td) { - int error; struct netmsg_pru_connect msg; + int error; - netmsg_init(&msg.nm_netmsg, so, &curthread->td_msgport, - 0, netmsg_pru_connect); - msg.nm_prufn = so->so_proto->pr_usrreqs->pru_connect; + netmsg_init(&msg.base, so, &curthread->td_msgport, + 0, so->so_proto->pr_usrreqs->pru_connect); msg.nm_nam = nam; msg.nm_td = td; - error = lwkt_domsg(so->so_port, &msg.nm_netmsg.nm_lmsg, 0); + msg.nm_m = NULL; + msg.nm_flags = 0; + msg.nm_reconnect = 0; + error = lwkt_domsg(so->so_port, &msg.base.lmsg, 0); return (error); } int so_pru_connect2(struct socket *so1, struct socket *so2) { - int error; struct netmsg_pru_connect2 msg; + int error; - netmsg_init(&msg.nm_netmsg, so1, &curthread->td_msgport, - 0, netmsg_pru_connect2); - msg.nm_prufn = so1->so_proto->pr_usrreqs->pru_connect2; + netmsg_init(&msg.base, so1, &curthread->td_msgport, + 0, so1->so_proto->pr_usrreqs->pru_connect2); msg.nm_so1 = so1; msg.nm_so2 = so2; - error = lwkt_domsg(so1->so_port, &msg.nm_netmsg.nm_lmsg, 0); + error = lwkt_domsg(so1->so_port, &msg.base.lmsg, 0); return (error); } +/* + * WARNING! Synchronous call from user context. Control function may do + * copyin/copyout. + */ int -so_pru_control(struct socket *so, u_long cmd, caddr_t data, struct ifnet *ifp) +so_pru_control_direct(struct socket *so, u_long cmd, caddr_t data, + struct ifnet *ifp) { - return ((*so->so_proto->pr_usrreqs->pru_control)( - so, cmd, data, ifp, curthread)); -#ifdef gag /* does copyin and copyout deep inside stack XXX JH */ - int error; struct netmsg_pru_control msg; + netisr_fn_t func = so->so_proto->pr_usrreqs->pru_control; - netmsg_init(&msg.nm_netmsg, so, &curthread->td_msgport, - 0, netmsg_pru_control); - msg.nm_prufn = so->so_proto->pr_usrreqs->pru_control; + netmsg_init(&msg.base, so, &netisr_adone_rport, 0, func); + msg.base.lmsg.ms_flags &= ~(MSGF_REPLY | MSGF_DONE); + msg.base.lmsg.ms_flags |= MSGF_SYNC; msg.nm_cmd = cmd; msg.nm_data = data; msg.nm_ifp = ifp; - msg.nm_td = td; - error = lwkt_domsg(so->so_port, &msg.nm_netmsg.nm_lmsg, 0); - return (error); -#endif + msg.nm_td = curthread; + func((netmsg_t)&msg); + return(msg.base.lmsg.ms_error); } int so_pru_detach(struct socket *so) { - int error; struct netmsg_pru_detach msg; + int error; - netmsg_init(&msg.nm_netmsg, so, &curthread->td_msgport, - 0, netmsg_pru_detach); - msg.nm_prufn = so->so_proto->pr_usrreqs->pru_detach; - error = lwkt_domsg(so->so_port, &msg.nm_netmsg.nm_lmsg, 0); + netmsg_init(&msg.base, so, &curthread->td_msgport, + 0, so->so_proto->pr_usrreqs->pru_detach); + error = lwkt_domsg(so->so_port, &msg.base.lmsg, 0); return (error); } int so_pru_disconnect(struct socket *so) { - int error; struct netmsg_pru_disconnect msg; + int error; - netmsg_init(&msg.nm_netmsg, so, &curthread->td_msgport, - 0, netmsg_pru_disconnect); - msg.nm_prufn = so->so_proto->pr_usrreqs->pru_disconnect; - error = lwkt_domsg(so->so_port, &msg.nm_netmsg.nm_lmsg, 0); + netmsg_init(&msg.base, so, &curthread->td_msgport, + 0, so->so_proto->pr_usrreqs->pru_disconnect); + error = lwkt_domsg(so->so_port, &msg.base.lmsg, 0); return (error); } int so_pru_listen(struct socket *so, struct thread *td) { - int error; struct netmsg_pru_listen msg; + int error; - netmsg_init(&msg.nm_netmsg, so, &curthread->td_msgport, - 0, netmsg_pru_listen); - msg.nm_prufn = so->so_proto->pr_usrreqs->pru_listen; + netmsg_init(&msg.base, so, &curthread->td_msgport, + 0, so->so_proto->pr_usrreqs->pru_listen); msg.nm_td = td; /* used only for prison_ip() XXX JH */ - error = lwkt_domsg(so->so_port, &msg.nm_netmsg.nm_lmsg, 0); + error = lwkt_domsg(so->so_port, &msg.base.lmsg, 0); return (error); } int so_pru_peeraddr(struct socket *so, struct sockaddr **nam) { - int error; struct netmsg_pru_peeraddr msg; + int error; - netmsg_init(&msg.nm_netmsg, so, &curthread->td_msgport, - 0, netmsg_pru_peeraddr); - msg.nm_prufn = so->so_proto->pr_usrreqs->pru_peeraddr; + netmsg_init(&msg.base, so, &curthread->td_msgport, + 0, so->so_proto->pr_usrreqs->pru_peeraddr); msg.nm_nam = nam; - error = lwkt_domsg(so->so_port, &msg.nm_netmsg.nm_lmsg, 0); + error = lwkt_domsg(so->so_port, &msg.base.lmsg, 0); return (error); } int so_pru_rcvd(struct socket *so, int flags) { - int error; struct netmsg_pru_rcvd msg; + int error; - netmsg_init(&msg.nm_netmsg, so, &curthread->td_msgport, - 0, netmsg_pru_rcvd); - msg.nm_prufn = so->so_proto->pr_usrreqs->pru_rcvd; + netmsg_init(&msg.base, so, &curthread->td_msgport, + 0, so->so_proto->pr_usrreqs->pru_rcvd); msg.nm_flags = flags; - error = lwkt_domsg(so->so_port, &msg.nm_netmsg.nm_lmsg, 0); + error = lwkt_domsg(so->so_port, &msg.base.lmsg, 0); return (error); } int so_pru_rcvoob(struct socket *so, struct mbuf *m, int flags) { - int error; struct netmsg_pru_rcvoob msg; + int error; - netmsg_init(&msg.nm_netmsg, so, &curthread->td_msgport, - 0, netmsg_pru_rcvoob); - msg.nm_prufn = so->so_proto->pr_usrreqs->pru_rcvoob; + netmsg_init(&msg.base, so, &curthread->td_msgport, + 0, so->so_proto->pr_usrreqs->pru_rcvoob); msg.nm_m = m; msg.nm_flags = flags; - error = lwkt_domsg(so->so_port, &msg.nm_netmsg.nm_lmsg, 0); + error = lwkt_domsg(so->so_port, &msg.base.lmsg, 0); return (error); } /* - * NOTE: so_pru_send() is the only code which uses pr_mport() now. - * * NOTE: If the target port changes the implied connect will deal with it. */ int so_pru_send(struct socket *so, int flags, struct mbuf *m, struct sockaddr *addr, struct mbuf *control, struct thread *td) { - int error; struct netmsg_pru_send msg; - lwkt_port_t port; - - port = so->so_proto->pr_mport(so, addr, &m); - if (port == NULL) { - KKASSERT(m == NULL); - return EINVAL; - } + int error; - netmsg_init(&msg.nm_netmsg, so, &curthread->td_msgport, - 0, netmsg_pru_send); - msg.nm_prufn = so->so_proto->pr_usrreqs->pru_send; + netmsg_init(&msg.base, so, &curthread->td_msgport, + 0, so->so_proto->pr_usrreqs->pru_send); msg.nm_flags = flags; msg.nm_m = m; msg.nm_addr = addr; msg.nm_control = control; msg.nm_td = td; - error = lwkt_domsg(port, &msg.nm_netmsg.nm_lmsg, 0); + error = lwkt_domsg(so->so_port, &msg.base.lmsg, 0); return (error); } -/* - * MPSAFE - */ int so_pru_sense(struct socket *so, struct stat *sb) { - int error; struct netmsg_pru_sense msg; + int error; - netmsg_init(&msg.nm_netmsg, so, &curthread->td_msgport, - 0, netmsg_pru_sense); - msg.nm_prufn = so->so_proto->pr_usrreqs->pru_sense; + netmsg_init(&msg.base, so, &curthread->td_msgport, + 0, so->so_proto->pr_usrreqs->pru_sense); msg.nm_stat = sb; - error = lwkt_domsg(so->so_port, &msg.nm_netmsg.nm_lmsg, 0); + error = lwkt_domsg(so->so_port, &msg.base.lmsg, 0); return (error); } int so_pru_shutdown(struct socket *so) { - int error; struct netmsg_pru_shutdown msg; + int error; - netmsg_init(&msg.nm_netmsg, so, &curthread->td_msgport, - 0, netmsg_pru_shutdown); - msg.nm_prufn = so->so_proto->pr_usrreqs->pru_shutdown; - error = lwkt_domsg(so->so_port, &msg.nm_netmsg.nm_lmsg, 0); + netmsg_init(&msg.base, so, &curthread->td_msgport, + 0, so->so_proto->pr_usrreqs->pru_shutdown); + error = lwkt_domsg(so->so_port, &msg.base.lmsg, 0); return (error); } int so_pru_sockaddr(struct socket *so, struct sockaddr **nam) { - int error; struct netmsg_pru_sockaddr msg; + int error; - netmsg_init(&msg.nm_netmsg, so, &curthread->td_msgport, - 0, netmsg_pru_sockaddr); - msg.nm_prufn = so->so_proto->pr_usrreqs->pru_sockaddr; + netmsg_init(&msg.base, so, &curthread->td_msgport, + 0, so->so_proto->pr_usrreqs->pru_sockaddr); msg.nm_nam = nam; - error = lwkt_domsg(so->so_port, &msg.nm_netmsg.nm_lmsg, 0); + error = lwkt_domsg(so->so_port, &msg.base.lmsg, 0); return (error); } int -so_pru_ctloutput(struct socket *so, struct sockopt *sopt) +so_pr_ctloutput(struct socket *so, struct sockopt *sopt) { - struct netmsg_pru_ctloutput msg; + struct netmsg_pr_ctloutput msg; int error; KKASSERT(!sopt->sopt_val || kva_p(sopt->sopt_val)); - netmsg_init(&msg.nm_netmsg, so, &curthread->td_msgport, - 0, netmsg_pru_ctloutput); - /* TBD: move pr_ctloutput to pr_usrreqs */ - msg.nm_prufn = so->so_proto->pr_ctloutput; + netmsg_init(&msg.base, so, &curthread->td_msgport, + 0, so->so_proto->pr_ctloutput); msg.nm_sopt = sopt; - error = lwkt_domsg(so->so_port, &msg.nm_netmsg.nm_lmsg, 0); + error = lwkt_domsg(so->so_port, &msg.base.lmsg, 0); return (error); } @@ -392,13 +382,12 @@ so_pru_ctlinput(struct protosw *pr, int cmd, struct sockaddr *arg, void *extra) port = pr->pr_ctlport(cmd, arg, extra); if (port == NULL) return; - netmsg_init(&msg.nm_netmsg, NULL, &curthread->td_msgport, - 0, netmsg_pru_ctlinput); - msg.nm_prufn = pr->pr_ctlinput; + netmsg_init(&msg.base, NULL, &curthread->td_msgport, + 0, pr->pr_ctlinput); msg.nm_cmd = cmd; msg.nm_arg = arg; msg.nm_extra = extra; - lwkt_domsg(port, &msg.nm_netmsg.nm_lmsg, 0); + lwkt_domsg(port, &msg.base.lmsg, 0); } /* @@ -408,213 +397,29 @@ so_pru_ctlinput(struct protosw *pr, int cmd, struct sockaddr *arg, void *extra) * the replymsg ourselves we return EASYNC by convention. */ -/* - * Abort and destroy a socket. - * - * The originator referenced the socket so we must dereference it when - * done. - */ -void -netmsg_pru_abort(netmsg_t msg) -{ - struct netmsg_pru_abort *nm = (void *)msg; - struct socket *so = msg->nm_so; - int error; - - error = nm->nm_prufn(so); - sofree(so); /* from soabort*() */ - lwkt_replymsg(&msg->nm_lmsg, error); -} - -#ifdef notused -void -netmsg_pru_accept(netmsg_t msg) -{ - struct netmsg_pru_accept *nm = (void *)msg; - - lwkt_replymsg(&msg->nm_lmsg, nm->nm_prufn(msg->nm_so, nm->nm_nam)); -} -#endif - -void -netmsg_pru_attach(netmsg_t msg) -{ - struct netmsg_pru_attach *nm = (void *)msg; - - lwkt_replymsg(&msg->nm_lmsg, - nm->nm_prufn(msg->nm_so, nm->nm_proto, nm->nm_ai)); -} - -void -netmsg_pru_bind(netmsg_t msg) -{ - struct netmsg_pru_bind *nm = (void *)msg; - - lwkt_replymsg(&msg->nm_lmsg, - nm->nm_prufn(msg->nm_so, nm->nm_nam, nm->nm_td)); -} - -void -netmsg_pru_connect(netmsg_t msg) -{ - struct netmsg_pru_connect *nm = (void *)msg; - - lwkt_replymsg(&msg->nm_lmsg, - nm->nm_prufn(msg->nm_so, nm->nm_nam, nm->nm_td)); -} - -void -netmsg_pru_connect2(netmsg_t msg) -{ - struct netmsg_pru_connect2 *nm = (void *)msg; - - lwkt_replymsg(&msg->nm_lmsg, nm->nm_prufn(nm->nm_so1, nm->nm_so2)); -} - -void -netmsg_pru_control(netmsg_t msg) -{ - struct netmsg_pru_control *nm = (void *)msg; - int error; - - error = nm->nm_prufn(msg->nm_so, nm->nm_cmd, nm->nm_data, - nm->nm_ifp, nm->nm_td); - lwkt_replymsg(&msg->nm_lmsg, error); -} - -void -netmsg_pru_detach(netmsg_t msg) -{ - struct netmsg_pru_detach *nm = (void *)msg; - - lwkt_replymsg(&msg->nm_lmsg, nm->nm_prufn(msg->nm_so)); -} - -void -netmsg_pru_disconnect(netmsg_t msg) -{ - struct netmsg_pru_disconnect *nm = (void *)msg; - - lwkt_replymsg(&msg->nm_lmsg, nm->nm_prufn(msg->nm_so)); -} - -void -netmsg_pru_listen(netmsg_t msg) -{ - struct netmsg_pru_listen *nm = (void *)msg; - - lwkt_replymsg(&msg->nm_lmsg, nm->nm_prufn(msg->nm_so, nm->nm_td)); -} - -void -netmsg_pru_peeraddr(netmsg_t msg) -{ - struct netmsg_pru_peeraddr *nm = (void *)msg; - - lwkt_replymsg(&msg->nm_lmsg, nm->nm_prufn(msg->nm_so, nm->nm_nam)); -} - -void -netmsg_pru_rcvd(netmsg_t msg) -{ - struct netmsg_pru_rcvd *nm = (void *)msg; - - lwkt_replymsg(&msg->nm_lmsg, nm->nm_prufn(msg->nm_so, nm->nm_flags)); -} - -void -netmsg_pru_rcvoob(netmsg_t msg) -{ - struct netmsg_pru_rcvoob *nm = (void *)msg; - - lwkt_replymsg(&msg->nm_lmsg, - nm->nm_prufn(msg->nm_so, nm->nm_m, nm->nm_flags)); -} - -void -netmsg_pru_send(netmsg_t msg) -{ - struct netmsg_pru_send *nm = (void *)msg; - int error; - - error = nm->nm_prufn(msg->nm_so, nm->nm_flags, nm->nm_m, - nm->nm_addr, nm->nm_control, nm->nm_td); - lwkt_replymsg(&msg->nm_lmsg, error); -} - -void -netmsg_pru_sense(netmsg_t msg) -{ - struct netmsg_pru_sense *nm = (void *)msg; - - lwkt_replymsg(&msg->nm_lmsg, nm->nm_prufn(msg->nm_so, nm->nm_stat)); -} - -void -netmsg_pru_shutdown(netmsg_t msg) -{ - struct netmsg_pru_shutdown *nm = (void *)msg; - - lwkt_replymsg(&msg->nm_lmsg, nm->nm_prufn(msg->nm_so)); -} - -void -netmsg_pru_sockaddr(netmsg_t msg) -{ - struct netmsg_pru_sockaddr *nm = (void *)msg; - - lwkt_replymsg(&msg->nm_lmsg, nm->nm_prufn(msg->nm_so, nm->nm_nam)); -} - -void -netmsg_pru_ctloutput(netmsg_t msg) -{ - struct netmsg_pru_ctloutput *nm = (void *)msg; - - lwkt_replymsg(&msg->nm_lmsg, nm->nm_prufn(msg->nm_so, nm->nm_sopt)); -} - -void -netmsg_pru_ctlinput(netmsg_t msg) -{ - struct netmsg_pru_ctlinput *nm = (void *)msg; - - nm->nm_prufn(nm->nm_cmd, nm->nm_arg, nm->nm_extra); - lwkt_replymsg(&nm->nm_netmsg.nm_lmsg, 0); -} - -void -netmsg_pr_timeout(netmsg_t msg) -{ - struct netmsg_pr_timeout *nm = (void *)msg; - - lwkt_replymsg(&msg->nm_lmsg, nm->nm_prfn()); -} - /* * Handle a predicate event request. This function is only called once * when the predicate message queueing request is received. */ void -netmsg_so_notify(netmsg_t netmsg) +netmsg_so_notify(netmsg_t msg) { - struct netmsg_so_notify *msg = (void *)netmsg; struct signalsockbuf *ssb; - ssb = (msg->nm_etype & NM_REVENT) ? - &msg->nm_so->so_rcv : - &msg->nm_so->so_snd; + ssb = (msg->notify.nm_etype & NM_REVENT) ? + &msg->base.nm_so->so_rcv : + &msg->base.nm_so->so_snd; /* * Reply immediately if the event has occured, otherwise queue the * request. */ - if (msg->nm_predicate(&msg->nm_netmsg)) { - lwkt_replymsg(&msg->nm_netmsg.nm_lmsg, - msg->nm_netmsg.nm_lmsg.ms_error); + if (msg->notify.nm_predicate(&msg->notify)) { + lwkt_replymsg(&msg->base.lmsg, + msg->base.lmsg.ms_error); } else { lwkt_gettoken(&kq_token); - TAILQ_INSERT_TAIL(&ssb->ssb_kq.ki_mlist, msg, nm_list); + TAILQ_INSERT_TAIL(&ssb->ssb_kq.ki_mlist, &msg->notify, nm_list); atomic_set_int(&ssb->ssb_flags, SSB_MEVENT); lwkt_reltoken(&kq_token); } @@ -639,10 +444,10 @@ netmsg_so_notify_doabort(lwkt_msg_t lmsg) struct netmsg_so_notify_abort msg; if ((lmsg->ms_flags & (MSGF_DONE | MSGF_REPLY)) == 0) { - netmsg_init(&msg.nm_netmsg, NULL, &curthread->td_msgport, + netmsg_init(&msg.base, NULL, &curthread->td_msgport, 0, netmsg_so_notify_abort); msg.nm_notifymsg = (void *)lmsg; - lwkt_domsg(lmsg->ms_target_port, &msg.nm_netmsg.nm_lmsg, 0); + lwkt_domsg(lmsg->ms_target_port, &msg.base.lmsg, 0); } } @@ -663,29 +468,28 @@ netmsg_so_notify_doabort(lwkt_msg_t lmsg) * reply reaches the originating cpu. Test both bits anyway. */ void -netmsg_so_notify_abort(netmsg_t netmsg) +netmsg_so_notify_abort(netmsg_t msg) { - struct netmsg_so_notify_abort *abrtmsg = (void *)netmsg; - struct netmsg_so_notify *msg = abrtmsg->nm_notifymsg; + struct netmsg_so_notify_abort *abrtmsg = &msg->notify_abort; + struct netmsg_so_notify *nmsg = abrtmsg->nm_notifymsg; struct signalsockbuf *ssb; /* * The original notify message is not destroyed until after the * abort request is returned, so we can check its state. */ - if ((msg->nm_netmsg.nm_lmsg.ms_flags & (MSGF_DONE | MSGF_REPLY)) == 0) { - ssb = (msg->nm_etype & NM_REVENT) ? - &msg->nm_so->so_rcv : - &msg->nm_so->so_snd; + if ((nmsg->base.lmsg.ms_flags & (MSGF_DONE | MSGF_REPLY)) == 0) { + ssb = (nmsg->nm_etype & NM_REVENT) ? + &nmsg->base.nm_so->so_rcv : + &nmsg->base.nm_so->so_snd; lwkt_gettoken(&kq_token); - TAILQ_REMOVE(&ssb->ssb_kq.ki_mlist, msg, nm_list); + TAILQ_REMOVE(&ssb->ssb_kq.ki_mlist, nmsg, nm_list); lwkt_reltoken(&kq_token); - lwkt_replymsg(&msg->nm_netmsg.nm_lmsg, EINTR); + lwkt_replymsg(&nmsg->base.lmsg, EINTR); } /* * Reply to the abort message */ - lwkt_replymsg(&abrtmsg->nm_netmsg.nm_lmsg, 0); + lwkt_replymsg(&abrtmsg->base.lmsg, 0); } - diff --git a/sys/kern/uipc_proto.c b/sys/kern/uipc_proto.c index 67740a4478..c8dd4994cc 100644 --- a/sys/kern/uipc_proto.c +++ b/sys/kern/uipc_proto.c @@ -51,30 +51,40 @@ */ static struct protosw localsw[] = { -{ SOCK_STREAM, &localdomain, 0, PR_CONNREQUIRED|PR_WANTRCVD|PR_RIGHTS, - NULL, NULL, NULL, &uipc_ctloutput, - sync_soport, NULL, - NULL, NULL, NULL, NULL, - &uipc_usrreqs -}, -{ SOCK_SEQPACKET, &localdomain, 0, PR_CONNREQUIRED|PR_WANTRCVD|PR_RIGHTS|PR_ATOMIC, - NULL, NULL, NULL, &uipc_ctloutput, - sync_soport, NULL, - NULL, NULL, NULL, NULL, - &uipc_usrreqs -}, -{ SOCK_DGRAM, &localdomain, 0, PR_ATOMIC|PR_ADDR|PR_RIGHTS, - NULL, NULL, NULL, NULL, - sync_soport, NULL, - NULL, NULL, NULL, NULL, - &uipc_usrreqs -}, -{ 0, NULL, 0, 0, - NULL, NULL, raw_ctlinput, NULL, - sync_soport, cpu0_ctlport, - raw_init, NULL, NULL, NULL, - &raw_usrreqs -} + { + .pr_type = SOCK_STREAM, + .pr_domain = &localdomain, + .pr_protocol = 0, + .pr_flags = PR_CONNREQUIRED|PR_WANTRCVD|PR_RIGHTS|PR_SYNC_PORT, + .pr_ctloutput = uipc_ctloutput, + .pr_usrreqs = &uipc_usrreqs + }, + { + .pr_type = SOCK_SEQPACKET, + .pr_domain = &localdomain, + .pr_protocol = 0, + .pr_flags = PR_CONNREQUIRED|PR_WANTRCVD|PR_RIGHTS|PR_SYNC_PORT| + PR_ATOMIC, + .pr_ctloutput = uipc_ctloutput, + .pr_usrreqs = &uipc_usrreqs + }, + { + .pr_type = SOCK_DGRAM, + .pr_domain = &localdomain, + .pr_protocol = 0, + .pr_flags = PR_RIGHTS|PR_SYNC_PORT|PR_ATOMIC|PR_ADDR, + .pr_ctloutput = NULL, + .pr_usrreqs = &uipc_usrreqs + }, + { + .pr_type = 0, + .pr_protocol = 0, + .pr_flags = PR_SYNC_PORT, + .pr_ctlinput = raw_ctlinput, + .pr_ctloutput = NULL, + .pr_init = raw_init, + .pr_usrreqs = &raw_usrreqs + } }; struct domain localdomain = { @@ -86,5 +96,6 @@ DOMAIN_SET(local); SYSCTL_NODE(_net, PF_LOCAL, local, CTLFLAG_RW, 0, "Local domain"); SYSCTL_NODE(_net_local, SOCK_STREAM, stream, CTLFLAG_RW, 0, "SOCK_STREAM"); -SYSCTL_NODE(_net_local, SOCK_SEQPACKET, seqpacket, CTLFLAG_RW, 0, "SOCK_SEQPACKET"); +SYSCTL_NODE(_net_local, SOCK_SEQPACKET, seqpacket, CTLFLAG_RW, 0, + "SOCK_SEQPACKET"); SYSCTL_NODE(_net_local, SOCK_DGRAM, dgram, CTLFLAG_RW, 0, "SOCK_DGRAM"); diff --git a/sys/kern/uipc_socket.c b/sys/kern/uipc_socket.c index 4ec07d3cad..3139912c86 100644 --- a/sys/kern/uipc_socket.c +++ b/sys/kern/uipc_socket.c @@ -206,8 +206,15 @@ socreate(int dom, struct socket **aso, int type, * on the socket on this port until an inpcb is attached to it and * is able to match incoming packets, or until the socket becomes * available to userland. + * + * We normally default the socket to the protocol thread on cpu 0. + * If PR_SYNC_PORT is set (unix domain sockets) there is no protocol + * thread and all pr_*()/pru_*() calls are executed synchronously. */ - so->so_port = cpu0_soport(so, NULL, NULL); + if (prp->pr_flags & PR_SYNC_PORT) + so->so_port = &netisr_sync_port; + else + so->so_port = cpu_portfn(0); TAILQ_INIT(&so->so_incomp); TAILQ_INIT(&so->so_comp); @@ -454,7 +461,7 @@ soaccept(struct socket *so, struct sockaddr **nam) panic("soaccept: !NOFDREF"); soreference(so); /* create ref */ soclrstate(so, SS_NOFDREF); /* owned by lack of SS_NOFDREF */ - error = so_pru_accept(so, nam); + error = so_pru_accept_direct(so, nam); return (error); } @@ -1336,7 +1343,7 @@ sosetopt(struct socket *so, struct sockopt *sopt) sopt->sopt_dir = SOPT_SET; if (sopt->sopt_level != SOL_SOCKET) { if (so->so_proto && so->so_proto->pr_ctloutput) { - return (so_pru_ctloutput(so, sopt)); + return (so_pr_ctloutput(so, sopt)); } error = ENOPROTOOPT; } else { @@ -1471,7 +1478,7 @@ sosetopt(struct socket *so, struct sockopt *sopt) break; } if (error == 0 && so->so_proto && so->so_proto->pr_ctloutput) { - (void) so_pru_ctloutput(so, sopt); + (void) so_pr_ctloutput(so, sopt); } } bad: @@ -1529,7 +1536,7 @@ sogetopt(struct socket *so, struct sockopt *sopt) sopt->sopt_dir = SOPT_GET; if (sopt->sopt_level != SOL_SOCKET) { if (so->so_proto && so->so_proto->pr_ctloutput) { - return (so_pru_ctloutput(so, sopt)); + return (so_pr_ctloutput(so, sopt)); } else return (ENOPROTOOPT); } else { diff --git a/sys/kern/uipc_socket2.c b/sys/kern/uipc_socket2.c index f4c6bc93b8..6a1fabedd6 100644 --- a/sys/kern/uipc_socket2.c +++ b/sys/kern/uipc_socket2.c @@ -50,6 +50,7 @@ #include #include #include +#include #include #include #include /* for aio_swake proto */ @@ -358,12 +359,12 @@ sonewconn(struct socket *head, int connstatus) ai.fd_rdir = NULL; /* jail code cruft XXX JH */ /* - * Reserve space and call pru_attach. We can directl call the + * Reserve space and call pru_attach. We can direct-call the * function since we're already in the protocol thread. */ if (soreserve(so, head->so_snd.ssb_hiwat, head->so_rcv.ssb_hiwat, NULL) || - (*so->so_proto->pr_usrreqs->pru_attach)(so, 0, &ai)) { + so_pru_attach_direct(so, 0, &ai)) { so->so_head = NULL; soclrstate(so, SS_ASSERTINPROG); sofree(so); /* remove implied pcb ref */ @@ -500,10 +501,10 @@ sowakeup(struct socket *so, struct signalsockbuf *ssb) lwkt_gettoken(&kq_token); lwkt_gettoken_hard(&ssb->ssb_token); TAILQ_FOREACH_MUTABLE(msg, &kqinfo->ki_mlist, nm_list, nmsg) { - if (msg->nm_predicate(&msg->nm_netmsg)) { + if (msg->nm_predicate(msg)) { TAILQ_REMOVE(&kqinfo->ki_mlist, msg, nm_list); - lwkt_replymsg(&msg->nm_netmsg.nm_lmsg, - msg->nm_netmsg.nm_lmsg.ms_error); + lwkt_replymsg(&msg->base.lmsg, + msg->base.lmsg.ms_error); } } if (TAILQ_EMPTY(&ssb->ssb_kq.ki_mlist)) @@ -646,77 +647,10 @@ ssb_release(struct signalsockbuf *ssb, struct socket *so) * Some routines that return EOPNOTSUPP for entry points that are not * supported by a protocol. Fill in as needed. */ -int -pru_accept_notsupp(struct socket *so, struct sockaddr **nam) -{ - return EOPNOTSUPP; -} - -int -pru_bind_notsupp(struct socket *so, struct sockaddr *nam, struct thread *td) -{ - return EOPNOTSUPP; -} - -int -pru_connect_notsupp(struct socket *so, struct sockaddr *nam, struct thread *td) -{ - return EOPNOTSUPP; -} - -int -pru_connect2_notsupp(struct socket *so1, struct socket *so2) -{ - return EOPNOTSUPP; -} - -int -pru_control_notsupp(struct socket *so, u_long cmd, caddr_t data, - struct ifnet *ifp, struct thread *td) -{ - return EOPNOTSUPP; -} - -int -pru_disconnect_notsupp(struct socket *so) -{ - return EOPNOTSUPP; -} - -int -pru_listen_notsupp(struct socket *so, struct thread *td) -{ - return EOPNOTSUPP; -} - -int -pru_peeraddr_notsupp(struct socket *so, struct sockaddr **nam) -{ - return EOPNOTSUPP; -} - -int -pru_rcvd_notsupp(struct socket *so, int flags) -{ - return EOPNOTSUPP; -} - -int -pru_rcvoob_notsupp(struct socket *so, struct mbuf *m, int flags) -{ - return EOPNOTSUPP; -} - -int -pru_shutdown_notsupp(struct socket *so) -{ - return EOPNOTSUPP; -} - -int -pru_sockaddr_notsupp(struct socket *so, struct sockaddr **nam) +void +pr_generic_notsupp(netmsg_t msg) { - return EOPNOTSUPP; + lwkt_replymsg(&msg->lmsg, EOPNOTSUPP); } int @@ -739,21 +673,15 @@ pru_soreceive_notsupp(struct socket *so, struct sockaddr **paddr, return (EOPNOTSUPP); } -int -pru_ctloutput_notsupp(struct socket *so, struct sockopt *sopt) -{ - return (EOPNOTSUPP); -} - /* * This isn't really a ``null'' operation, but it's the default one * and doesn't do anything destructive. */ -int -pru_sense_null(struct socket *so, struct stat *sb) +void +pru_sense_null(netmsg_t msg) { - sb->st_blksize = so->so_snd.ssb_hiwat; - return 0; + msg->sense.nm_stat->st_blksize = msg->base.nm_so->so_snd.ssb_hiwat; + lwkt_replymsg(&msg->lmsg, 0); } /* diff --git a/sys/kern/uipc_syscalls.c b/sys/kern/uipc_syscalls.c index 192c5cc778..16f7cb56cf 100644 --- a/sys/kern/uipc_syscalls.c +++ b/sys/kern/uipc_syscalls.c @@ -216,33 +216,32 @@ sys_listen(struct listen_args *uap) * Returns the accepted socket as well. */ static boolean_t -soaccept_predicate(struct netmsg *msg0) +soaccept_predicate(struct netmsg_so_notify *msg) { - struct netmsg_so_notify *msg = (struct netmsg_so_notify *)msg0; - struct socket *head = msg->nm_so; + struct socket *head = msg->base.nm_so; if (head->so_error != 0) { - msg->nm_netmsg.nm_lmsg.ms_error = head->so_error; + msg->base.lmsg.ms_error = head->so_error; return (TRUE); } lwkt_gettoken(&head->so_rcv.ssb_token); if (!TAILQ_EMPTY(&head->so_comp)) { /* Abuse nm_so field as copy in/copy out parameter. XXX JH */ - msg->nm_so = TAILQ_FIRST(&head->so_comp); - TAILQ_REMOVE(&head->so_comp, msg->nm_so, so_list); + msg->base.nm_so = TAILQ_FIRST(&head->so_comp); + TAILQ_REMOVE(&head->so_comp, msg->base.nm_so, so_list); head->so_qlen--; - msg->nm_netmsg.nm_lmsg.ms_error = 0; + msg->base.lmsg.ms_error = 0; lwkt_reltoken(&head->so_rcv.ssb_token); return (TRUE); } lwkt_reltoken(&head->so_rcv.ssb_token); if (head->so_state & SS_CANTRCVMORE) { - msg->nm_netmsg.nm_lmsg.ms_error = ECONNABORTED; + msg->base.lmsg.ms_error = ECONNABORTED; return (TRUE); } if (msg->nm_fflags & FNONBLOCK) { - msg->nm_netmsg.nm_lmsg.ms_error = EWOULDBLOCK; + msg->base.lmsg.ms_error = EWOULDBLOCK; return (TRUE); } @@ -296,20 +295,19 @@ kern_accept(int s, int fflags, struct sockaddr **name, int *namelen, int *res) fflags = lfp->f_flag; /* optimize for uniprocessor case later XXX JH */ - netmsg_init_abortable(&msg.nm_netmsg, head, &curthread->td_msgport, + netmsg_init_abortable(&msg.base, head, &curthread->td_msgport, 0, netmsg_so_notify, netmsg_so_notify_doabort); msg.nm_predicate = soaccept_predicate; msg.nm_fflags = fflags; - msg.nm_so = head; msg.nm_etype = NM_REVENT; - error = lwkt_domsg(head->so_port, &msg.nm_netmsg.nm_lmsg, PCATCH); + error = lwkt_domsg(head->so_port, &msg.base.lmsg, PCATCH); if (error) goto done; /* * At this point we have the connection that's ready to be accepted. */ - so = msg.nm_so; + so = msg.base.nm_so; fflag = lfp->f_flag; @@ -453,14 +451,13 @@ sys_extaccept(struct extaccept_args *uap) * Returns TRUE if predicate satisfied. */ static boolean_t -soconnected_predicate(struct netmsg *msg0) +soconnected_predicate(struct netmsg_so_notify *msg) { - struct netmsg_so_notify *msg = (struct netmsg_so_notify *)msg0; - struct socket *so = msg->nm_so; + struct socket *so = msg->base.nm_so; /* check predicate */ if (!(so->so_state & SS_ISCONNECTING) || so->so_error != 0) { - msg->nm_netmsg.nm_lmsg.ms_error = so->so_error; + msg->base.lmsg.ms_error = so->so_error; return (TRUE); } @@ -502,15 +499,14 @@ kern_connect(int s, int fflags, struct sockaddr *sa) if ((so->so_state & SS_ISCONNECTING) && so->so_error == 0) { struct netmsg_so_notify msg; - netmsg_init_abortable(&msg.nm_netmsg, so, + netmsg_init_abortable(&msg.base, so, &curthread->td_msgport, 0, netmsg_so_notify, netmsg_so_notify_doabort); msg.nm_predicate = soconnected_predicate; - msg.nm_so = so; msg.nm_etype = NM_REVENT; - error = lwkt_domsg(so->so_port, &msg.nm_netmsg.nm_lmsg, PCATCH); + error = lwkt_domsg(so->so_port, &msg.base.lmsg, PCATCH); if (error == EINTR || error == ERESTART) interrupted = 1; } diff --git a/sys/kern/uipc_usrreq.c b/sys/kern/uipc_usrreq.c index 17e77196c6..b3740765a9 100644 --- a/sys/kern/uipc_usrreq.c +++ b/sys/kern/uipc_usrreq.c @@ -60,6 +60,7 @@ #include #include #include +#include static MALLOC_DEFINE(M_UNPCB, "unpcb", "unpcb struct"); static unp_gen_t unp_gencnt; @@ -107,14 +108,14 @@ static void unp_fp_externalize(struct lwp *lp, struct file *fp, int fd); * NOTE: (so) is referenced from soabort*() and netmsg_pru_abort() * will sofree() it when we return. */ -static int -uipc_abort(struct socket *so) +static void +uipc_abort(netmsg_t msg) { struct unpcb *unp; int error; lwkt_gettoken(&unp_token); - unp = so->so_pcb; + unp = msg->base.nm_so->so_pcb; if (unp) { unp_drop(unp, ECONNABORTED); unp_detach(unp); @@ -124,113 +125,117 @@ uipc_abort(struct socket *so) } lwkt_reltoken(&unp_token); - return error; + lwkt_replymsg(&msg->lmsg, error); } -static int -uipc_accept(struct socket *so, struct sockaddr **nam) +static void +uipc_accept(netmsg_t msg) { struct unpcb *unp; + int error; lwkt_gettoken(&unp_token); - unp = so->so_pcb; + unp = msg->base.nm_so->so_pcb; if (unp == NULL) { - lwkt_reltoken(&unp_token); - return EINVAL; - } - - /* - * Pass back name of connected socket, - * if it was bound and we are still connected - * (our peer may have closed already!). - */ - if (unp->unp_conn && unp->unp_conn->unp_addr) { - *nam = dup_sockaddr((struct sockaddr *)unp->unp_conn->unp_addr); + error = EINVAL; } else { - *nam = dup_sockaddr((struct sockaddr *)&sun_noname); + /* + * Pass back name of connected socket, + * if it was bound and we are still connected + * (our peer may have closed already!). + */ + if (unp->unp_conn && unp->unp_conn->unp_addr) { + *msg->accept.nm_nam = dup_sockaddr( + (struct sockaddr *)unp->unp_conn->unp_addr); + } else { + *msg->accept.nm_nam = dup_sockaddr( + (struct sockaddr *)&sun_noname); + } + error = 0; } lwkt_reltoken(&unp_token); - return 0; + lwkt_replymsg(&msg->lmsg, error); } -static int -uipc_attach(struct socket *so, int proto, struct pru_attach_info *ai) +static void +uipc_attach(netmsg_t msg) { struct unpcb *unp; int error; lwkt_gettoken(&unp_token); - unp = so->so_pcb; + unp = msg->base.nm_so->so_pcb; if (unp) error = EISCONN; else - error = unp_attach(so, ai); + error = unp_attach(msg->base.nm_so, msg->attach.nm_ai); lwkt_reltoken(&unp_token); - - return error; + lwkt_replymsg(&msg->lmsg, error); } -static int -uipc_bind(struct socket *so, struct sockaddr *nam, struct thread *td) +static void +uipc_bind(netmsg_t msg) { struct unpcb *unp; int error; lwkt_gettoken(&unp_token); - unp = so->so_pcb; + unp = msg->base.nm_so->so_pcb; if (unp) - error = unp_bind(unp, nam, td); + error = unp_bind(unp, msg->bind.nm_nam, msg->bind.nm_td); else error = EINVAL; lwkt_reltoken(&unp_token); - - return error; + lwkt_replymsg(&msg->lmsg, error); } -static int -uipc_connect(struct socket *so, struct sockaddr *nam, struct thread *td) +static void +uipc_connect(netmsg_t msg) { struct unpcb *unp; int error; lwkt_gettoken(&unp_token); - unp = so->so_pcb; - if (unp) - error = unp_connect(so, nam, td); - else + unp = msg->base.nm_so->so_pcb; + if (unp) { + error = unp_connect(msg->base.nm_so, + msg->connect.nm_nam, + msg->connect.nm_td); + } else { error = EINVAL; + } lwkt_reltoken(&unp_token); - - return error; + lwkt_replymsg(&msg->lmsg, error); } -static int -uipc_connect2(struct socket *so1, struct socket *so2) +static void +uipc_connect2(netmsg_t msg) { struct unpcb *unp; int error; lwkt_gettoken(&unp_token); - unp = so1->so_pcb; - if (unp) - error = unp_connect2(so1, so2); - else + unp = msg->connect2.nm_so1->so_pcb; + if (unp) { + error = unp_connect2(msg->connect2.nm_so1, + msg->connect2.nm_so2); + } else { error = EINVAL; + } lwkt_reltoken(&unp_token); - - return error; + lwkt_replymsg(&msg->lmsg, error); } /* control is EOPNOTSUPP */ -static int -uipc_detach(struct socket *so) +static void +uipc_detach(netmsg_t msg) { struct unpcb *unp; int error; lwkt_gettoken(&unp_token); - unp = so->so_pcb; + unp = msg->base.nm_so->so_pcb; if (unp) { unp_detach(unp); error = 0; @@ -238,18 +243,17 @@ uipc_detach(struct socket *so) error = EINVAL; } lwkt_reltoken(&unp_token); - - return error; + lwkt_replymsg(&msg->lmsg, error); } -static int -uipc_disconnect(struct socket *so) +static void +uipc_disconnect(netmsg_t msg) { struct unpcb *unp; int error; lwkt_gettoken(&unp_token); - unp = so->so_pcb; + unp = msg->base.nm_so->so_pcb; if (unp) { unp_disconnect(unp); error = 0; @@ -257,39 +261,38 @@ uipc_disconnect(struct socket *so) error = EINVAL; } lwkt_reltoken(&unp_token); - - return error; + lwkt_replymsg(&msg->lmsg, error); } -static int -uipc_listen(struct socket *so, struct thread *td) +static void +uipc_listen(netmsg_t msg) { struct unpcb *unp; int error; lwkt_gettoken(&unp_token); - unp = so->so_pcb; + unp = msg->base.nm_so->so_pcb; if (unp == NULL || unp->unp_vnode == NULL) error = EINVAL; else - error = unp_listen(unp, td); + error = unp_listen(unp, msg->listen.nm_td); lwkt_reltoken(&unp_token); - - return error; + lwkt_replymsg(&msg->lmsg, error); } -static int -uipc_peeraddr(struct socket *so, struct sockaddr **nam) +static void +uipc_peeraddr(netmsg_t msg) { struct unpcb *unp; int error; lwkt_gettoken(&unp_token); - unp = so->so_pcb; + unp = msg->base.nm_so->so_pcb; if (unp == NULL) { error = EINVAL; } else if (unp->unp_conn && unp->unp_conn->unp_addr) { - *nam = dup_sockaddr((struct sockaddr *)unp->unp_conn->unp_addr); + *msg->peeraddr.nm_nam = dup_sockaddr( + (struct sockaddr *)unp->unp_conn->unp_addr); error = 0; } else { /* @@ -297,25 +300,28 @@ uipc_peeraddr(struct socket *so, struct sockaddr **nam) * connection is established. So, this else clause is * added as workaround to return PF_LOCAL sockaddr. */ - *nam = dup_sockaddr((struct sockaddr *)&sun_noname); + *msg->peeraddr.nm_nam = dup_sockaddr( + (struct sockaddr *)&sun_noname); error = 0; } lwkt_reltoken(&unp_token); - - return error; + lwkt_replymsg(&msg->lmsg, error); } -static int -uipc_rcvd(struct socket *so, int flags) +static void +uipc_rcvd(netmsg_t msg) { struct unpcb *unp; + struct socket *so; struct socket *so2; + int error; lwkt_gettoken(&unp_token); + so = msg->base.nm_so; unp = so->so_pcb; if (unp == NULL) { - lwkt_reltoken(&unp_token); - return EINVAL; + error = EINVAL; + goto done; } switch (so->so_type) { @@ -343,34 +349,40 @@ uipc_rcvd(struct socket *so, int flags) panic("uipc_rcvd unknown socktype"); /*NOTREACHED*/ } + error = 0; +done: lwkt_reltoken(&unp_token); - - return 0; + lwkt_replymsg(&msg->lmsg, error); } /* pru_rcvoob is EOPNOTSUPP */ -static int -uipc_send(struct socket *so, int flags, struct mbuf *m, struct sockaddr *nam, - struct mbuf *control, struct thread *td) +static void +uipc_send(netmsg_t msg) { struct unpcb *unp; + struct socket *so; struct socket *so2; + struct mbuf *control; + struct mbuf *m; int error = 0; lwkt_gettoken(&unp_token); - + so = msg->base.nm_so; + control = msg->send.nm_control; + m = msg->send.nm_m; unp = so->so_pcb; + if (unp == NULL) { error = EINVAL; goto release; } - if (flags & PRUS_OOB) { + if (msg->send.nm_flags & PRUS_OOB) { error = EOPNOTSUPP; goto release; } - if (control && (error = unp_internalize(control, td))) + if (control && (error = unp_internalize(control, msg->send.nm_td))) goto release; switch (so->so_type) { @@ -378,12 +390,14 @@ uipc_send(struct socket *so, int flags, struct mbuf *m, struct sockaddr *nam, { struct sockaddr *from; - if (nam) { + if (msg->send.nm_addr) { if (unp->unp_conn) { error = EISCONN; break; } - error = unp_connect(so, nam, td); + error = unp_connect(so, + msg->send.nm_addr, + msg->send.nm_td); if (error) break; } else { @@ -404,7 +418,7 @@ uipc_send(struct socket *so, int flags, struct mbuf *m, struct sockaddr *nam, } else { error = ENOBUFS; } - if (nam) + if (msg->send.nm_addr) unp_disconnect(unp); break; } @@ -417,8 +431,10 @@ uipc_send(struct socket *so, int flags, struct mbuf *m, struct sockaddr *nam, * if not equal to the peer's address. */ if (!(so->so_state & SS_ISCONNECTED)) { - if (nam) { - error = unp_connect(so, nam, td); + if (msg->send.nm_addr) { + error = unp_connect(so, + msg->send.nm_addr, + msg->send.nm_td); if (error) break; /* XXX */ } else { @@ -472,7 +488,7 @@ uipc_send(struct socket *so, int flags, struct mbuf *m, struct sockaddr *nam, /* * SEND_EOF is equivalent to a SEND followed by a SHUTDOWN. */ - if (flags & PRUS_EOF) { + if (msg->send.nm_flags & PRUS_EOF) { socantsendmore(so); unp_shutdown(unp); } @@ -487,22 +503,27 @@ release: m_freem(control); if (m) m_freem(m); - return error; + lwkt_replymsg(&msg->lmsg, error); } /* * MPSAFE */ -static int -uipc_sense(struct socket *so, struct stat *sb) +static void +uipc_sense(netmsg_t msg) { struct unpcb *unp; + struct socket *so; + struct stat *sb; + int error; lwkt_gettoken(&unp_token); + so = msg->base.nm_so; + sb = msg->sense.nm_stat; unp = so->so_pcb; if (unp == NULL) { - lwkt_reltoken(&unp_token); - return EINVAL; + error = EINVAL; + goto done; } sb->st_blksize = so->so_snd.ssb_hiwat; sb->st_dev = NOUDEV; @@ -512,18 +533,21 @@ uipc_sense(struct socket *so, struct stat *sb) spin_unlock(&unp_ino_spin); } sb->st_ino = unp->unp_ino; + error = 0; +done: lwkt_reltoken(&unp_token); - - return (0); + lwkt_replymsg(&msg->lmsg, error); } -static int -uipc_shutdown(struct socket *so) +static void +uipc_shutdown(netmsg_t msg) { + struct socket *so; struct unpcb *unp; int error; lwkt_gettoken(&unp_token); + so = msg->base.nm_so; unp = so->so_pcb; if (unp) { socantsendmore(so); @@ -533,28 +557,28 @@ uipc_shutdown(struct socket *so) error = EINVAL; } lwkt_reltoken(&unp_token); - - return error; + lwkt_replymsg(&msg->lmsg, error); } -static int -uipc_sockaddr(struct socket *so, struct sockaddr **nam) +static void +uipc_sockaddr(netmsg_t msg) { struct unpcb *unp; int error; lwkt_gettoken(&unp_token); - unp = so->so_pcb; + unp = msg->base.nm_so->so_pcb; if (unp) { - if (unp->unp_addr) - *nam = dup_sockaddr((struct sockaddr *)unp->unp_addr); + if (unp->unp_addr) { + *msg->sockaddr.nm_nam = + dup_sockaddr((struct sockaddr *)unp->unp_addr); + } error = 0; } else { error = EINVAL; } lwkt_reltoken(&unp_token); - - return error; + lwkt_replymsg(&msg->lmsg, error); } struct pr_usrreqs uipc_usrreqs = { @@ -564,13 +588,13 @@ struct pr_usrreqs uipc_usrreqs = { .pru_bind = uipc_bind, .pru_connect = uipc_connect, .pru_connect2 = uipc_connect2, - .pru_control = pru_control_notsupp, + .pru_control = pr_generic_notsupp, .pru_detach = uipc_detach, .pru_disconnect = uipc_disconnect, .pru_listen = uipc_listen, .pru_peeraddr = uipc_peeraddr, .pru_rcvd = uipc_rcvd, - .pru_rcvoob = pru_rcvoob_notsupp, + .pru_rcvoob = pr_generic_notsupp, .pru_send = uipc_send, .pru_sense = uipc_sense, .pru_shutdown = uipc_shutdown, @@ -579,13 +603,17 @@ struct pr_usrreqs uipc_usrreqs = { .pru_soreceive = soreceive }; -int -uipc_ctloutput(struct socket *so, struct sockopt *sopt) +void +uipc_ctloutput(netmsg_t msg) { + struct socket *so; + struct sockopt *sopt; struct unpcb *unp; int error = 0; lwkt_gettoken(&unp_token); + so = msg->base.nm_so; + sopt = msg->ctloutput.nm_sopt; unp = so->so_pcb; switch (sopt->sopt_dir) { @@ -615,8 +643,7 @@ uipc_ctloutput(struct socket *so, struct sockopt *sopt) break; } lwkt_reltoken(&unp_token); - - return (error); + lwkt_replymsg(&msg->lmsg, error); } /* @@ -665,6 +692,7 @@ unp_attach(struct socket *so, struct pru_attach_info *ai) int error; lwkt_gettoken(&unp_token); + if (so->so_snd.ssb_hiwat == 0 || so->so_rcv.ssb_hiwat == 0) { switch (so->so_type) { @@ -699,7 +727,6 @@ unp_attach(struct socket *so, struct pru_attach_info *ai) : &unp_shead, unp, unp_link); so->so_pcb = (caddr_t)unp; soreference(so); - so->so_port = sync_soport(so, NULL, NULL); error = 0; failed: lwkt_reltoken(&unp_token); diff --git a/sys/net/bpf.c b/sys/net/bpf.c index d8bbda106e..f54e78c639 100644 --- a/sys/net/bpf.c +++ b/sys/net/bpf.c @@ -78,7 +78,7 @@ #include struct netmsg_bpf_output { - struct netmsg nm_netmsg; + struct netmsg_base base; struct mbuf *nm_mbuf; struct ifnet *nm_ifp; struct sockaddr *nm_dst; @@ -540,9 +540,9 @@ bpf_timed_out(void *arg) } static void -bpf_output_dispatch(struct netmsg *nmsg) +bpf_output_dispatch(netmsg_t msg) { - struct netmsg_bpf_output *bmsg = (struct netmsg_bpf_output *)nmsg; + struct netmsg_bpf_output *bmsg = (struct netmsg_bpf_output *)msg; struct ifnet *ifp = bmsg->nm_ifp; int error; @@ -550,7 +550,7 @@ bpf_output_dispatch(struct netmsg *nmsg) * The driver frees the mbuf. */ error = ifp->if_output(ifp, bmsg->nm_mbuf, bmsg->nm_dst, NULL); - lwkt_replymsg(&nmsg->nm_lmsg, error); + lwkt_replymsg(&msg->lmsg, error); } static int @@ -586,13 +586,13 @@ bpfwrite(struct dev_write_args *ap) if (d->bd_hdrcmplt) dst.sa_family = pseudo_AF_HDRCMPLT; - netmsg_init(&bmsg.nm_netmsg, NULL, &curthread->td_msgport, + netmsg_init(&bmsg.base, NULL, &curthread->td_msgport, 0, bpf_output_dispatch); bmsg.nm_mbuf = m; bmsg.nm_ifp = ifp; bmsg.nm_dst = &dst; - return lwkt_domsg(cpu_portfn(0), &bmsg.nm_netmsg.nm_lmsg, 0); + return lwkt_domsg(cpu_portfn(0), &bmsg.base.lmsg, 0); } /* diff --git a/sys/net/bridge/bridgestp.c b/sys/net/bridge/bridgestp.c index 56683b16c3..7c7edc5be8 100644 --- a/sys/net/bridge/bridgestp.c +++ b/sys/net/bridge/bridgestp.c @@ -923,7 +923,7 @@ bstp_stop(struct bridge_softc *sc) bstp_timer_stop(&sc->sc_hello_timer); crit_enter(); - lmsg = &sc->sc_bstptimemsg.nm_lmsg; + lmsg = &sc->sc_bstptimemsg.lmsg; if ((lmsg->ms_flags & MSGF_DONE) == 0) { /* Pending to be processed; drop it */ lwkt_dropmsg(lmsg); @@ -1122,7 +1122,7 @@ bstp_tick(void *arg) } callout_deactivate(&sc->sc_bstpcallout); - lmsg = &sc->sc_bstptimemsg.nm_lmsg; + lmsg = &sc->sc_bstptimemsg.lmsg; KKASSERT(lmsg->ms_flags & MSGF_DONE); lwkt_sendmsg(BRIDGE_CFGPORT, lmsg); @@ -1130,15 +1130,15 @@ bstp_tick(void *arg) } void -bstp_tick_handler(struct netmsg *nmsg) +bstp_tick_handler(netmsg_t msg) { - struct bridge_softc *sc = nmsg->nm_lmsg.u.ms_resultp; + struct bridge_softc *sc = msg->lmsg.u.ms_resultp; struct bridge_iflist *bif; KKASSERT(&curthread->td_msgport == BRIDGE_CFGPORT); crit_enter(); /* Reply ASAP */ - lwkt_replymsg(&nmsg->nm_lmsg, 0); + lwkt_replymsg(&msg->lmsg, 0); crit_exit(); ifnet_serialize_all(sc->sc_ifp); diff --git a/sys/net/bridge/if_bridge.c b/sys/net/bridge/if_bridge.c index 58ca156646..70871f3e62 100644 --- a/sys/net/bridge/if_bridge.c +++ b/sys/net/bridge/if_bridge.c @@ -314,14 +314,14 @@ typedef int (*bridge_ctl_t)(struct bridge_softc *, void *); struct netmsg_brctl { - struct netmsg bc_nmsg; + struct netmsg_base base; bridge_ctl_t bc_func; struct bridge_softc *bc_sc; void *bc_arg; }; struct netmsg_brsaddr { - struct netmsg br_nmsg; + struct netmsg_base base; struct bridge_softc *br_softc; struct ifnet *br_dst_if; struct bridge_rtinfo *br_rtinfo; @@ -331,21 +331,21 @@ struct netmsg_brsaddr { }; struct netmsg_braddbif { - struct netmsg br_nmsg; + struct netmsg_base base; struct bridge_softc *br_softc; struct bridge_ifinfo *br_bif_info; struct ifnet *br_bif_ifp; }; struct netmsg_brdelbif { - struct netmsg br_nmsg; + struct netmsg_base base; struct bridge_softc *br_softc; struct bridge_ifinfo *br_bif_info; struct bridge_iflist_head *br_bif_list; }; struct netmsg_brsflags { - struct netmsg br_nmsg; + struct netmsg_base base; struct bridge_softc *br_softc; struct bridge_ifinfo *br_bif_info; uint32_t br_bif_flags; @@ -373,7 +373,7 @@ static int bridge_output(struct ifnet *, struct mbuf *); static void bridge_forward(struct bridge_softc *, struct mbuf *m); -static void bridge_timer_handler(struct netmsg *); +static void bridge_timer_handler(netmsg_t); static void bridge_timer(void *); static void bridge_start_bcast(struct bridge_softc *, struct mbuf *); @@ -394,8 +394,8 @@ static int bridge_rtdaddr(struct bridge_softc *, const uint8_t *); static int bridge_rtsaddr(struct bridge_softc *, const uint8_t *, struct ifnet *, uint8_t); static void bridge_rtmsg_sync(struct bridge_softc *sc); -static void bridge_rtreap_handler(struct netmsg *); -static void bridge_rtinstall_handler(struct netmsg *); +static void bridge_rtreap_handler(netmsg_t); +static void bridge_rtinstall_handler(netmsg_t); static int bridge_rtinstall_oncpu(struct bridge_softc *, const uint8_t *, struct ifnet *, int, uint8_t, struct bridge_rtinfo **); @@ -458,12 +458,12 @@ static int bridge_ip6_checkbasic(struct mbuf **mp); #endif /* INET6 */ static int bridge_fragment(struct ifnet *, struct mbuf *, struct ether_header *, int, struct llc *); -static void bridge_enqueue_handler(struct netmsg *); +static void bridge_enqueue_handler(netmsg_t); static void bridge_handoff(struct ifnet *, struct mbuf *); -static void bridge_del_bif_handler(struct netmsg *); -static void bridge_add_bif_handler(struct netmsg *); -static void bridge_set_bifflags_handler(struct netmsg *); +static void bridge_del_bif_handler(netmsg_t); +static void bridge_add_bif_handler(netmsg_t); +static void bridge_set_bifflags_handler(netmsg_t); static void bridge_del_bif(struct bridge_softc *, struct bridge_ifinfo *, struct bridge_iflist_head *); static void bridge_add_bif(struct bridge_softc *, struct bridge_ifinfo *, @@ -655,12 +655,12 @@ bridge_clone_create(struct if_clone *ifc, int unit, caddr_t param __unused) callout_init(&sc->sc_brcallout); netmsg_init(&sc->sc_brtimemsg, NULL, &netisr_adone_rport, MSGF_DROPABLE, bridge_timer_handler); - sc->sc_brtimemsg.nm_lmsg.u.ms_resultp = sc; + sc->sc_brtimemsg.lmsg.u.ms_resultp = sc; callout_init(&sc->sc_bstpcallout); netmsg_init(&sc->sc_bstptimemsg, NULL, &netisr_adone_rport, MSGF_DROPABLE, bstp_tick_handler); - sc->sc_bstptimemsg.nm_lmsg.u.ms_resultp = sc; + sc->sc_bstptimemsg.lmsg.u.ms_resultp = sc; /* Initialize per-cpu member iface lists */ sc->sc_iflists = kmalloc(sizeof(*sc->sc_iflists) * ncpus, @@ -707,10 +707,9 @@ bridge_clone_create(struct if_clone *ifc, int unit, caddr_t param __unused) } static void -bridge_delete_dispatch(struct netmsg *nmsg) +bridge_delete_dispatch(netmsg_t msg) { - struct lwkt_msg *lmsg = &nmsg->nm_lmsg; - struct bridge_softc *sc = lmsg->u.ms_resultp; + struct bridge_softc *sc = msg->lmsg.u.ms_resultp; struct ifnet *bifp = sc->sc_ifp; struct bridge_iflist *bif; @@ -724,7 +723,7 @@ bridge_delete_dispatch(struct netmsg *nmsg) ifnet_deserialize_all(bifp); - lwkt_replymsg(lmsg, 0); + lwkt_replymsg(&msg->lmsg, 0); } /* @@ -736,8 +735,7 @@ static void bridge_clone_destroy(struct ifnet *ifp) { struct bridge_softc *sc = ifp->if_softc; - struct lwkt_msg *lmsg; - struct netmsg nmsg; + struct netmsg_base msg; ifnet_serialize_all(ifp); @@ -746,11 +744,10 @@ bridge_clone_destroy(struct ifnet *ifp) ifnet_deserialize_all(ifp); - netmsg_init(&nmsg, NULL, &curthread->td_msgport, + netmsg_init(&msg, NULL, &curthread->td_msgport, 0, bridge_delete_dispatch); - lmsg = &nmsg.nm_lmsg; - lmsg->u.ms_resultp = sc; - lwkt_domsg(BRIDGE_CFGPORT, lmsg, 0); + msg.lmsg.u.ms_resultp = sc; + lwkt_domsg(BRIDGE_CFGPORT, &msg.lmsg, 0); crit_enter(); /* XXX MP */ LIST_REMOVE(sc, sc_list); @@ -1098,7 +1095,7 @@ bridge_ioctl_stop(struct bridge_softc *sc, void *arg __unused) callout_stop(&sc->sc_brcallout); crit_enter(); - lmsg = &sc->sc_brtimemsg.nm_lmsg; + lmsg = &sc->sc_brtimemsg.lmsg; if ((lmsg->ms_flags & MSGF_DONE) == 0) { /* Pending to be processed; drop it */ lwkt_dropmsg(lmsg); @@ -1721,14 +1718,13 @@ bridge_ioctl_delspan(struct bridge_softc *sc, void *arg) } static void -bridge_ifdetach_dispatch(struct netmsg *nmsg) +bridge_ifdetach_dispatch(netmsg_t msg) { - struct lwkt_msg *lmsg = &nmsg->nm_lmsg; struct ifnet *ifp, *bifp; struct bridge_softc *sc; struct bridge_iflist *bif; - ifp = lmsg->u.ms_resultp; + ifp = msg->lmsg.u.ms_resultp; sc = ifp->if_bridge; /* Check if the interface is a bridge member */ @@ -1768,7 +1764,7 @@ bridge_ifdetach_dispatch(struct netmsg *nmsg) crit_exit(); reply: - lwkt_replymsg(lmsg, 0); + lwkt_replymsg(&msg->lmsg, 0); } /* @@ -1780,15 +1776,13 @@ reply: static void bridge_ifdetach(void *arg __unused, struct ifnet *ifp) { - struct lwkt_msg *lmsg; - struct netmsg nmsg; + struct netmsg_base msg; - netmsg_init(&nmsg, NULL, &curthread->td_msgport, + netmsg_init(&msg, NULL, &curthread->td_msgport, 0, bridge_ifdetach_dispatch); - lmsg = &nmsg.nm_lmsg; - lmsg->u.ms_resultp = ifp; + msg.lmsg.u.ms_resultp = ifp; - lwkt_domsg(BRIDGE_CFGPORT, lmsg, 0); + lwkt_domsg(BRIDGE_CFGPORT, &msg.lmsg, 0); } /* @@ -1825,12 +1819,12 @@ bridge_enqueue(struct ifnet *dst_ifp, struct mbuf *m) struct netmsg_packet *nmp; nmp = &m->m_hdr.mh_netmsg; - netmsg_init(&nmp->nm_netmsg, NULL, &netisr_apanic_rport, + netmsg_init(&nmp->base, NULL, &netisr_apanic_rport, 0, bridge_enqueue_handler); nmp->nm_packet = m; - nmp->nm_netmsg.nm_lmsg.u.ms_resultp = dst_ifp; + nmp->base.lmsg.u.ms_resultp = dst_ifp; - lwkt_sendmsg(ifnet_portfn(mycpu->gd_cpuid), &nmp->nm_netmsg.nm_lmsg); + lwkt_sendmsg(ifnet_portfn(mycpu->gd_cpuid), &nmp->base.lmsg); } /* @@ -2506,21 +2500,21 @@ bridge_span(struct bridge_softc *sc, struct mbuf *m) } static void -bridge_rtmsg_sync_handler(struct netmsg *nmsg) +bridge_rtmsg_sync_handler(netmsg_t msg) { - ifnet_forwardmsg(&nmsg->nm_lmsg, mycpuid + 1); + ifnet_forwardmsg(&msg->lmsg, mycpuid + 1); } static void bridge_rtmsg_sync(struct bridge_softc *sc) { - struct netmsg nmsg; + struct netmsg_base msg; ASSERT_IFNET_NOT_SERIALIZED_ALL(sc->sc_ifp); - netmsg_init(&nmsg, NULL, &curthread->td_msgport, + netmsg_init(&msg, NULL, &curthread->td_msgport, 0, bridge_rtmsg_sync_handler); - ifnet_domsg(&nmsg.nm_lmsg, 0); + ifnet_domsg(&msg.lmsg, 0); } static __inline void @@ -2595,9 +2589,9 @@ bridge_rtinstall_oncpu(struct bridge_softc *sc, const uint8_t *dst, } static void -bridge_rtinstall_handler(struct netmsg *nmsg) +bridge_rtinstall_handler(netmsg_t msg) { - struct netmsg_brsaddr *brmsg = (struct netmsg_brsaddr *)nmsg; + struct netmsg_brsaddr *brmsg = (struct netmsg_brsaddr *)msg; int error; error = bridge_rtinstall_oncpu(brmsg->br_softc, @@ -2606,15 +2600,15 @@ bridge_rtinstall_handler(struct netmsg *nmsg) &brmsg->br_rtinfo); if (error) { KKASSERT(mycpuid == 0 && brmsg->br_rtinfo == NULL); - lwkt_replymsg(&nmsg->nm_lmsg, error); + lwkt_replymsg(&brmsg->base.lmsg, error); return; } else if (brmsg->br_rtinfo == NULL) { /* rtnode already exists for 'dst' */ KKASSERT(mycpuid == 0); - lwkt_replymsg(&nmsg->nm_lmsg, 0); + lwkt_replymsg(&brmsg->base.lmsg, 0); return; } - ifnet_forwardmsg(&nmsg->nm_lmsg, mycpuid + 1); + ifnet_forwardmsg(&brmsg->base.lmsg, mycpuid + 1); } /* @@ -2642,7 +2636,7 @@ bridge_rtupdate(struct bridge_softc *sc, const uint8_t *dst, if (brmsg == NULL) return ENOMEM; - netmsg_init(&brmsg->br_nmsg, NULL, &netisr_afree_rport, + netmsg_init(&brmsg->base, NULL, &netisr_afree_rport, 0, bridge_rtinstall_handler); memcpy(brmsg->br_dst, dst, ETHER_ADDR_LEN); brmsg->br_dst_if = dst_if; @@ -2651,7 +2645,7 @@ bridge_rtupdate(struct bridge_softc *sc, const uint8_t *dst, brmsg->br_softc = sc; brmsg->br_rtinfo = NULL; - ifnet_sendmsg(&brmsg->br_nmsg.nm_lmsg, 0); + ifnet_sendmsg(&brmsg->base.lmsg, 0); return 0; } bridge_rtinfo_update(brt->brt_info, dst_if, 0, flags, @@ -2667,7 +2661,7 @@ bridge_rtsaddr(struct bridge_softc *sc, const uint8_t *dst, ASSERT_IFNET_NOT_SERIALIZED_ALL(sc->sc_ifp); - netmsg_init(&brmsg.br_nmsg, NULL, &curthread->td_msgport, + netmsg_init(&brmsg.base, NULL, &curthread->td_msgport, 0, bridge_rtinstall_handler); memcpy(brmsg.br_dst, dst, ETHER_ADDR_LEN); brmsg.br_dst_if = dst_if; @@ -2676,7 +2670,7 @@ bridge_rtsaddr(struct bridge_softc *sc, const uint8_t *dst, brmsg.br_softc = sc; brmsg.br_rtinfo = NULL; - return ifnet_domsg(&brmsg.br_nmsg.nm_lmsg, 0); + return ifnet_domsg(&brmsg.base.lmsg, 0); } /* @@ -2695,44 +2689,44 @@ bridge_rtlookup(struct bridge_softc *sc, const uint8_t *addr) } static void -bridge_rtreap_handler(struct netmsg *nmsg) +bridge_rtreap_handler(netmsg_t msg) { - struct bridge_softc *sc = nmsg->nm_lmsg.u.ms_resultp; + struct bridge_softc *sc = msg->lmsg.u.ms_resultp; struct bridge_rtnode *brt, *nbrt; LIST_FOREACH_MUTABLE(brt, &sc->sc_rtlists[mycpuid], brt_list, nbrt) { if (brt->brt_info->bri_dead) bridge_rtnode_destroy(sc, brt); } - ifnet_forwardmsg(&nmsg->nm_lmsg, mycpuid + 1); + ifnet_forwardmsg(&msg->lmsg, mycpuid + 1); } static void bridge_rtreap(struct bridge_softc *sc) { - struct netmsg nmsg; + struct netmsg_base msg; ASSERT_IFNET_NOT_SERIALIZED_ALL(sc->sc_ifp); - netmsg_init(&nmsg, NULL, &curthread->td_msgport, + netmsg_init(&msg, NULL, &curthread->td_msgport, 0, bridge_rtreap_handler); - nmsg.nm_lmsg.u.ms_resultp = sc; + msg.lmsg.u.ms_resultp = sc; - ifnet_domsg(&nmsg.nm_lmsg, 0); + ifnet_domsg(&msg.lmsg, 0); } static void bridge_rtreap_async(struct bridge_softc *sc) { - struct netmsg *nmsg; + struct netmsg_base *msg; - nmsg = kmalloc(sizeof(*nmsg), M_LWKTMSG, M_WAITOK); + msg = kmalloc(sizeof(*msg), M_LWKTMSG, M_WAITOK); - netmsg_init(nmsg, NULL, &netisr_afree_rport, + netmsg_init(msg, NULL, &netisr_afree_rport, 0, bridge_rtreap_handler); - nmsg->nm_lmsg.u.ms_resultp = sc; + msg->lmsg.u.ms_resultp = sc; - ifnet_sendmsg(&nmsg->nm_lmsg, 0); + ifnet_sendmsg(&msg->lmsg, 0); } /* @@ -2804,7 +2798,7 @@ static void bridge_timer(void *arg) { struct bridge_softc *sc = arg; - struct lwkt_msg *lmsg; + struct netmsg_base *msg; KKASSERT(mycpuid == BRIDGE_CFGCPU); @@ -2817,23 +2811,23 @@ bridge_timer(void *arg) } callout_deactivate(&sc->sc_brcallout); - lmsg = &sc->sc_brtimemsg.nm_lmsg; - KKASSERT(lmsg->ms_flags & MSGF_DONE); - lwkt_sendmsg(BRIDGE_CFGPORT, lmsg); + msg = &sc->sc_brtimemsg; + KKASSERT(msg->lmsg.ms_flags & MSGF_DONE); + lwkt_sendmsg(BRIDGE_CFGPORT, &msg->lmsg); crit_exit(); } static void -bridge_timer_handler(struct netmsg *nmsg) +bridge_timer_handler(netmsg_t msg) { - struct bridge_softc *sc = nmsg->nm_lmsg.u.ms_resultp; + struct bridge_softc *sc = msg->lmsg.u.ms_resultp; KKASSERT(&curthread->td_msgport == BRIDGE_CFGPORT); crit_enter(); /* Reply ASAP */ - lwkt_replymsg(&nmsg->nm_lmsg, 0); + lwkt_replymsg(&msg->lmsg, 0); crit_exit(); bridge_rtage(sc); @@ -3636,15 +3630,15 @@ out: } static void -bridge_enqueue_handler(struct netmsg *nmsg) +bridge_enqueue_handler(netmsg_t msg) { struct netmsg_packet *nmp; struct ifnet *dst_ifp; struct mbuf *m; - nmp = (struct netmsg_packet *)nmsg; + nmp = &msg->packet; m = nmp->nm_packet; - dst_ifp = nmp->nm_netmsg.nm_lmsg.u.ms_resultp; + dst_ifp = nmp->base.lmsg.u.ms_resultp; bridge_handoff(dst_ifp, m); } @@ -3669,9 +3663,9 @@ bridge_handoff(struct ifnet *dst_ifp, struct mbuf *m) } static void -bridge_control_dispatch(struct netmsg *nmsg) +bridge_control_dispatch(netmsg_t msg) { - struct netmsg_brctl *bc_msg = (struct netmsg_brctl *)nmsg; + struct netmsg_brctl *bc_msg = (struct netmsg_brctl *)msg; struct ifnet *bifp = bc_msg->bc_sc->sc_ifp; int error; @@ -3679,7 +3673,7 @@ bridge_control_dispatch(struct netmsg *nmsg) error = bc_msg->bc_func(bc_msg->bc_sc, bc_msg->bc_arg); ifnet_deserialize_all(bifp); - lwkt_replymsg(&nmsg->nm_lmsg, error); + lwkt_replymsg(&bc_msg->base.lmsg, error); } static int @@ -3688,30 +3682,28 @@ bridge_control(struct bridge_softc *sc, u_long cmd, { struct ifnet *bifp = sc->sc_ifp; struct netmsg_brctl bc_msg; - struct netmsg *nmsg; int error; ASSERT_IFNET_SERIALIZED_ALL(bifp); bzero(&bc_msg, sizeof(bc_msg)); - nmsg = &bc_msg.bc_nmsg; - netmsg_init(nmsg, NULL, &curthread->td_msgport, + netmsg_init(&bc_msg.base, NULL, &curthread->td_msgport, 0, bridge_control_dispatch); bc_msg.bc_func = bc_func; bc_msg.bc_sc = sc; bc_msg.bc_arg = bc_arg; ifnet_deserialize_all(bifp); - error = lwkt_domsg(BRIDGE_CFGPORT, &nmsg->nm_lmsg, 0); + error = lwkt_domsg(BRIDGE_CFGPORT, &bc_msg.base.lmsg, 0); ifnet_serialize_all(bifp); return error; } static void -bridge_add_bif_handler(struct netmsg *nmsg) +bridge_add_bif_handler(netmsg_t msg) { - struct netmsg_braddbif *amsg = (struct netmsg_braddbif *)nmsg; + struct netmsg_braddbif *amsg = (struct netmsg_braddbif *)msg; struct bridge_softc *sc; struct bridge_iflist *bif; @@ -3725,7 +3717,7 @@ bridge_add_bif_handler(struct netmsg *nmsg) LIST_INSERT_HEAD(&sc->sc_iflists[mycpuid], bif, bif_next); - ifnet_forwardmsg(&nmsg->nm_lmsg, mycpuid + 1); + ifnet_forwardmsg(&amsg->base.lmsg, mycpuid + 1); } static void @@ -3736,19 +3728,19 @@ bridge_add_bif(struct bridge_softc *sc, struct bridge_ifinfo *bif_info, ASSERT_IFNET_NOT_SERIALIZED_ALL(sc->sc_ifp); - netmsg_init(&amsg.br_nmsg, NULL, &curthread->td_msgport, + netmsg_init(&amsg.base, NULL, &curthread->td_msgport, 0, bridge_add_bif_handler); amsg.br_softc = sc; amsg.br_bif_info = bif_info; amsg.br_bif_ifp = ifp; - ifnet_domsg(&amsg.br_nmsg.nm_lmsg, 0); + ifnet_domsg(&amsg.base.lmsg, 0); } static void -bridge_del_bif_handler(struct netmsg *nmsg) +bridge_del_bif_handler(netmsg_t msg) { - struct netmsg_brdelbif *dmsg = (struct netmsg_brdelbif *)nmsg; + struct netmsg_brdelbif *dmsg = (struct netmsg_brdelbif *)msg; struct bridge_softc *sc; struct bridge_iflist *bif; @@ -3768,7 +3760,7 @@ bridge_del_bif_handler(struct netmsg *nmsg) /* Save the removed bif for later freeing */ LIST_INSERT_HEAD(dmsg->br_bif_list, bif, bif_next); - ifnet_forwardmsg(&nmsg->nm_lmsg, mycpuid + 1); + ifnet_forwardmsg(&dmsg->base.lmsg, mycpuid + 1); } static void @@ -3779,19 +3771,19 @@ bridge_del_bif(struct bridge_softc *sc, struct bridge_ifinfo *bif_info, ASSERT_IFNET_NOT_SERIALIZED_ALL(sc->sc_ifp); - netmsg_init(&dmsg.br_nmsg, NULL, &curthread->td_msgport, + netmsg_init(&dmsg.base, NULL, &curthread->td_msgport, 0, bridge_del_bif_handler); dmsg.br_softc = sc; dmsg.br_bif_info = bif_info; dmsg.br_bif_list = saved_bifs; - ifnet_domsg(&dmsg.br_nmsg.nm_lmsg, 0); + ifnet_domsg(&dmsg.base.lmsg, 0); } static void -bridge_set_bifflags_handler(struct netmsg *nmsg) +bridge_set_bifflags_handler(netmsg_t msg) { - struct netmsg_brsflags *smsg = (struct netmsg_brsflags *)nmsg; + struct netmsg_brsflags *smsg = (struct netmsg_brsflags *)msg; struct bridge_softc *sc; struct bridge_iflist *bif; @@ -3806,7 +3798,7 @@ bridge_set_bifflags_handler(struct netmsg *nmsg) bif->bif_flags = smsg->br_bif_flags; - ifnet_forwardmsg(&nmsg->nm_lmsg, mycpuid + 1); + ifnet_forwardmsg(&smsg->base.lmsg, mycpuid + 1); } static void @@ -3817,11 +3809,11 @@ bridge_set_bifflags(struct bridge_softc *sc, struct bridge_ifinfo *bif_info, ASSERT_IFNET_NOT_SERIALIZED_ALL(sc->sc_ifp); - netmsg_init(&smsg.br_nmsg, NULL, &curthread->td_msgport, + netmsg_init(&smsg.base, NULL, &curthread->td_msgport, 0, bridge_set_bifflags_handler); smsg.br_softc = sc; smsg.br_bif_info = bif_info; smsg.br_bif_flags = bif_flags; - ifnet_domsg(&smsg.br_nmsg.nm_lmsg, 0); + ifnet_domsg(&smsg.base.lmsg, 0); } diff --git a/sys/net/bridge/if_bridgevar.h b/sys/net/bridge/if_bridgevar.h index 333a1a0abe..ab6bb5f4aa 100644 --- a/sys/net/bridge/if_bridgevar.h +++ b/sys/net/bridge/if_bridgevar.h @@ -332,9 +332,9 @@ struct bridge_softc { uint32_t sc_brtcnt; /* cur. # of addresses */ uint32_t sc_brttimeout; /* rt timeout in seconds */ struct callout sc_brcallout; /* bridge callout */ - struct netmsg sc_brtimemsg; /* bridge callout msg */ + struct netmsg_base sc_brtimemsg; /* bridge callout msg */ struct callout sc_bstpcallout; /* STP callout */ - struct netmsg sc_bstptimemsg; /* STP callout msg */ + struct netmsg_base sc_bstptimemsg; /* STP callout msg */ struct bridge_iflist_head *sc_iflists; /* percpu member if lists */ struct bridge_rtnode_head **sc_rthashs; /* percpu forwarding tables */ struct bridge_rtnode_head *sc_rtlists; /* percpu lists of the above */ @@ -359,7 +359,7 @@ void bstp_linkstate(struct ifnet *, int); void bstp_stop(struct bridge_softc *); void bstp_input(struct bridge_softc *, struct bridge_iflist *, struct mbuf *); -void bstp_tick_handler(struct netmsg *); +void bstp_tick_handler(netmsg_t); void bridge_enqueue(struct ifnet *, struct mbuf *); diff --git a/sys/net/dummynet/ip_dummynet.c b/sys/net/dummynet/ip_dummynet.c index 86df63df4b..5912120a4c 100644 --- a/sys/net/dummynet/ip_dummynet.c +++ b/sys/net/dummynet/ip_dummynet.c @@ -138,7 +138,7 @@ static struct dn_flowset_head flowset_table[DN_NR_HASH_MAX]; /* * Variables for dummynet systimer */ -static struct netmsg dn_netmsg; +static struct netmsg_base dn_netmsg; static struct systimer dn_clock; static int dn_hz = 1000; @@ -187,7 +187,7 @@ static int config_pipe(struct dn_ioc_pipe *); static void dummynet_flush(void); static void dummynet_clock(systimer_t, struct intrframe *); -static void dummynet(struct netmsg *); +static void dummynet(netmsg_t); static struct dn_pipe *dn_find_pipe(int); static struct dn_flow_set *dn_locate_flowset(int, int); @@ -644,7 +644,7 @@ dn_expire_pipe_cb(struct dn_pipe *pipe, void *dummy __unused) * increment the current tick counter and schedule expired events. */ static void -dummynet(struct netmsg *msg) +dummynet(netmsg_t msg) { void *p; struct dn_heap *h; @@ -657,7 +657,7 @@ dummynet(struct netmsg *msg) /* Reply ASAP */ crit_enter(); - lwkt_replymsg(&msg->nm_lmsg, 0); + lwkt_replymsg(&msg->lmsg, 0); crit_exit(); curr_time++; @@ -1875,8 +1875,8 @@ dummynet_clock(systimer_t info __unused, struct intrframe *frame __unused) mycpuid, ip_dn_cpu)); crit_enter(); - if (DUMMYNET_LOADED && (dn_netmsg.nm_lmsg.ms_flags & MSGF_DONE)) - lwkt_sendmsg(cpu_portfn(mycpuid), &dn_netmsg.nm_lmsg); + if (DUMMYNET_LOADED && (dn_netmsg.lmsg.ms_flags & MSGF_DONE)) + lwkt_sendmsg(cpu_portfn(mycpuid), &dn_netmsg.lmsg); crit_exit(); } @@ -1903,7 +1903,7 @@ sysctl_dn_hz(SYSCTL_HANDLER_ARGS) } static void -ip_dn_init_dispatch(struct netmsg *msg) +ip_dn_init_dispatch(netmsg_t msg) { int i, error = 0; @@ -1945,13 +1945,13 @@ ip_dn_init_dispatch(struct netmsg *msg) back: crit_exit(); - lwkt_replymsg(&msg->nm_lmsg, error); + lwkt_replymsg(&msg->lmsg, error); } static int ip_dn_init(void) { - struct netmsg smsg; + struct netmsg_base smsg; if (ip_dn_cpu >= ncpus) { kprintf("%s: CPU%d does not exist, switch to CPU0\n", @@ -1961,14 +1961,14 @@ ip_dn_init(void) netmsg_init(&smsg, NULL, &curthread->td_msgport, 0, ip_dn_init_dispatch); - lwkt_domsg(cpu_portfn(ip_dn_cpu), &smsg.nm_lmsg, 0); - return smsg.nm_lmsg.ms_error; + lwkt_domsg(cpu_portfn(ip_dn_cpu), &smsg.lmsg, 0); + return smsg.lmsg.ms_error; } #ifdef KLD_MODULE static void -ip_dn_stop_dispatch(struct netmsg *msg) +ip_dn_stop_dispatch(netmsg_t msg) { crit_enter(); @@ -1980,18 +1980,18 @@ ip_dn_stop_dispatch(struct netmsg *msg) systimer_del(&dn_clock); crit_exit(); - lwkt_replymsg(&msg->nm_lmsg, 0); + lwkt_replymsg(&msg->lmsg, 0); } static void ip_dn_stop(void) { - struct netmsg smsg; + struct netmsg_base smsg; netmsg_init(&smsg, NULL, &curthread->td_msgport, 0, ip_dn_stop_dispatch); - lwkt_domsg(cpu_portfn(ip_dn_cpu), &smsg.nm_lmsg, 0); + lwkt_domsg(cpu_portfn(ip_dn_cpu), &smsg.lmsg, 0); netmsg_service_sync(); } diff --git a/sys/net/dummynet/ip_dummynet_glue.c b/sys/net/dummynet/ip_dummynet_glue.c index 214ae095a7..4467d47e5c 100644 --- a/sys/net/dummynet/ip_dummynet_glue.c +++ b/sys/net/dummynet/ip_dummynet_glue.c @@ -55,14 +55,14 @@ #include -static void ip_dn_ether_output(struct netmsg *); -static void ip_dn_ether_demux(struct netmsg *); -static void ip_dn_ip_input(struct netmsg *); -static void ip_dn_ip_output(struct netmsg *); +static void ip_dn_ether_output(netmsg_t); +static void ip_dn_ether_demux(netmsg_t); +static void ip_dn_ip_input(netmsg_t); +static void ip_dn_ip_output(netmsg_t); -static void ip_dn_sockopt_dispatch(struct netmsg *); -static void ip_dn_freepkt_dispatch(struct netmsg *); -static void ip_dn_dispatch(struct netmsg *); +static void ip_dn_sockopt_dispatch(netmsg_t); +static void ip_dn_freepkt_dispatch(netmsg_t); +static void ip_dn_dispatch(netmsg_t); static void ip_dn_freepkt(struct dn_pkt *); @@ -90,12 +90,12 @@ ip_dn_queue(struct mbuf *m) ("mbuf is not tagged for dummynet!\n")); nmp = &m->m_hdr.mh_netmsg; - netmsg_init(&nmp->nm_netmsg, NULL, &netisr_apanic_rport, + netmsg_init(&nmp->base, NULL, &netisr_apanic_rport, 0, ip_dn_dispatch); nmp->nm_packet = m; port = cpu_portfn(ip_dn_cpu); - lwkt_sendmsg(port, &nmp->nm_netmsg.nm_lmsg); + lwkt_sendmsg(port, &nmp->base.lmsg); } void @@ -109,11 +109,11 @@ ip_dn_packet_free(struct dn_pkt *pkt) ("mbuf is not tagged for dummynet!\n")); nmp = &m->m_hdr.mh_netmsg; - netmsg_init(&nmp->nm_netmsg, NULL, &netisr_apanic_rport, + netmsg_init(&nmp->base, NULL, &netisr_apanic_rport, 0, ip_dn_freepkt_dispatch); nmp->nm_packet = m; - lwkt_sendmsg(pkt->msgport, &nmp->nm_netmsg.nm_lmsg); + lwkt_sendmsg(pkt->msgport, &nmp->base.lmsg); } void @@ -145,11 +145,10 @@ ip_dn_packet_redispatch(struct dn_pkt *pkt) ("mbuf is not tagged for dummynet!\n")); nmp = &m->m_hdr.mh_netmsg; - netmsg_init(&nmp->nm_netmsg, NULL, &netisr_apanic_rport, - 0, dispatch); + netmsg_init(&nmp->base, NULL, &netisr_apanic_rport, 0, dispatch); nmp->nm_packet = m; - lwkt_sendmsg(pkt->msgport, &nmp->nm_netmsg.nm_lmsg); + lwkt_sendmsg(pkt->msgport, &nmp->base.lmsg); } int @@ -208,14 +207,14 @@ ip_dn_freepkt(struct dn_pkt *pkt) } static void -ip_dn_freepkt_dispatch(struct netmsg *nmsg) +ip_dn_freepkt_dispatch(netmsg_t nmsg) { struct netmsg_packet *nmp; struct mbuf *m; struct m_tag *mtag; struct dn_pkt *pkt; - nmp = (struct netmsg_packet *)nmsg; + nmp = &nmsg->packet; m = nmp->nm_packet; M_ASSERTPKTHDR(m); KASSERT(m->m_pkthdr.fw_flags & DUMMYNET_MBUF_TAGGED, @@ -234,7 +233,7 @@ ip_dn_freepkt_dispatch(struct netmsg *nmsg) } static void -ip_dn_dispatch(struct netmsg *nmsg) +ip_dn_dispatch(netmsg_t nmsg) { struct netmsg_packet *nmp; struct mbuf *m; @@ -246,7 +245,7 @@ ip_dn_dispatch(struct netmsg *nmsg) "dummynet cpuid %d, mycpuid %d\n", __func__, ip_dn_cpu, mycpuid)); - nmp = (struct netmsg_packet *)nmsg; + nmp = &nmsg->packet; m = nmp->nm_packet; M_ASSERTPKTHDR(m); KASSERT(m->m_pkthdr.fw_flags & DUMMYNET_MBUF_TAGGED, @@ -268,7 +267,7 @@ ip_dn_dispatch(struct netmsg *nmsg) } static void -ip_dn_ip_output(struct netmsg *nmsg) +ip_dn_ip_output(netmsg_t nmsg) { struct netmsg_packet *nmp; struct mbuf *m; @@ -278,7 +277,7 @@ ip_dn_ip_output(struct netmsg *nmsg) ip_dn_unref_priv_t unref_priv; void *priv; - nmp = (struct netmsg_packet *)nmsg; + nmp = &nmsg->packet; m = nmp->nm_packet; M_ASSERTPKTHDR(m); KASSERT(m->m_pkthdr.fw_flags & DUMMYNET_MBUF_TAGGED, @@ -317,7 +316,7 @@ ip_dn_ip_output(struct netmsg *nmsg) } static void -ip_dn_ip_input(struct netmsg *nmsg) +ip_dn_ip_input(netmsg_t nmsg) { struct netmsg_packet *nmp; struct mbuf *m; @@ -326,7 +325,7 @@ ip_dn_ip_input(struct netmsg *nmsg) ip_dn_unref_priv_t unref_priv; void *priv; - nmp = (struct netmsg_packet *)nmsg; + nmp = &nmsg->packet; m = nmp->nm_packet; M_ASSERTPKTHDR(m); KASSERT(m->m_pkthdr.fw_flags & DUMMYNET_MBUF_TAGGED, @@ -356,7 +355,7 @@ ip_dn_ip_input(struct netmsg *nmsg) } static void -ip_dn_ether_demux(struct netmsg *nmsg) +ip_dn_ether_demux(netmsg_t nmsg) { struct netmsg_packet *nmp; struct mbuf *m; @@ -365,7 +364,7 @@ ip_dn_ether_demux(struct netmsg *nmsg) ip_dn_unref_priv_t unref_priv; void *priv; - nmp = (struct netmsg_packet *)nmsg; + nmp = &nmsg->packet; m = nmp->nm_packet; M_ASSERTPKTHDR(m); KASSERT(m->m_pkthdr.fw_flags & DUMMYNET_MBUF_TAGGED, @@ -403,7 +402,7 @@ back: } static void -ip_dn_ether_output(struct netmsg *nmsg) +ip_dn_ether_output(netmsg_t nmsg) { struct netmsg_packet *nmp; struct mbuf *m; @@ -412,7 +411,7 @@ ip_dn_ether_output(struct netmsg *nmsg) ip_dn_unref_priv_t unref_priv; void *priv; - nmp = (struct netmsg_packet *)nmsg; + nmp = &nmsg->packet; m = nmp->nm_packet; M_ASSERTPKTHDR(m); KASSERT(m->m_pkthdr.fw_flags & DUMMYNET_MBUF_TAGGED, @@ -442,9 +441,9 @@ ip_dn_ether_output(struct netmsg *nmsg) } static void -ip_dn_sockopt_dispatch(struct netmsg *nmsg) +ip_dn_sockopt_dispatch(netmsg_t nmsg) { - lwkt_msg *msg = &nmsg->nm_lmsg; + lwkt_msg *msg = &nmsg->lmsg; struct dn_sopt *dn_sopt = msg->u.ms_resultp; int error; @@ -464,24 +463,24 @@ static int ip_dn_sockopt_flush(struct sockopt *sopt) { struct dn_sopt dn_sopt; - struct netmsg smsg; + struct netmsg_base smsg; bzero(&dn_sopt, sizeof(dn_sopt)); dn_sopt.dn_sopt_name = sopt->sopt_name; netmsg_init(&smsg, NULL, &curthread->td_msgport, 0, ip_dn_sockopt_dispatch); - smsg.nm_lmsg.u.ms_resultp = &dn_sopt; - lwkt_domsg(cpu_portfn(ip_dn_cpu), &smsg.nm_lmsg, 0); + smsg.lmsg.u.ms_resultp = &dn_sopt; + lwkt_domsg(cpu_portfn(ip_dn_cpu), &smsg.lmsg, 0); - return smsg.nm_lmsg.ms_error; + return smsg.lmsg.ms_error; } static int ip_dn_sockopt_get(struct sockopt *sopt) { struct dn_sopt dn_sopt; - struct netmsg smsg; + struct netmsg_base smsg; int error; bzero(&dn_sopt, sizeof(dn_sopt)); @@ -489,10 +488,10 @@ ip_dn_sockopt_get(struct sockopt *sopt) netmsg_init(&smsg, NULL, &curthread->td_msgport, 0, ip_dn_sockopt_dispatch); - smsg.nm_lmsg.u.ms_resultp = &dn_sopt; - lwkt_domsg(cpu_portfn(ip_dn_cpu), &smsg.nm_lmsg, 0); + smsg.lmsg.u.ms_resultp = &dn_sopt; + lwkt_domsg(cpu_portfn(ip_dn_cpu), &smsg.lmsg, 0); - error = smsg.nm_lmsg.ms_error; + error = smsg.lmsg.ms_error; if (error) { KKASSERT(dn_sopt.dn_sopt_arg == NULL); KKASSERT(dn_sopt.dn_sopt_arglen == 0); @@ -509,7 +508,7 @@ ip_dn_sockopt_config(struct sockopt *sopt) { struct dn_ioc_pipe tmp_ioc_pipe; struct dn_sopt dn_sopt; - struct netmsg smsg; + struct netmsg_base smsg; int error; error = soopt_to_kbuf(sopt, &tmp_ioc_pipe, sizeof tmp_ioc_pipe, @@ -524,8 +523,8 @@ ip_dn_sockopt_config(struct sockopt *sopt) netmsg_init(&smsg, NULL, &curthread->td_msgport, 0, ip_dn_sockopt_dispatch); - smsg.nm_lmsg.u.ms_resultp = &dn_sopt; - lwkt_domsg(cpu_portfn(ip_dn_cpu), &smsg.nm_lmsg, 0); + smsg.lmsg.u.ms_resultp = &dn_sopt; + lwkt_domsg(cpu_portfn(ip_dn_cpu), &smsg.lmsg, 0); - return smsg.nm_lmsg.ms_error; + return smsg.lmsg.ms_error; } diff --git a/sys/net/gre/if_gre.c b/sys/net/gre/if_gre.c index 8143671856..1f224c331e 100644 --- a/sys/net/gre/if_gre.c +++ b/sys/net/gre/if_gre.c @@ -115,21 +115,41 @@ static int gre_compute_route(struct gre_softc *sc); static void greattach(void); #ifdef INET + extern struct domain inetdomain; + static const struct protosw in_gre_protosw = -{ SOCK_RAW, &inetdomain, IPPROTO_GRE, PR_ATOMIC|PR_ADDR, - gre_input, rip_output, rip_ctlinput, rip_ctloutput, - cpu0_soport, cpu0_ctlport, - 0, 0, 0, 0, - &rip_usrreqs -}; + { + .pr_type = SOCK_RAW, + .pr_domain = &inetdomain, + .pr_protocol = IPPROTO_GRE, + .pr_flags = PR_ATOMIC|PR_ADDR, + + .pr_input = gre_input, + .pr_output = rip_output, + .pr_ctlinput = rip_ctlinput, + .pr_ctloutput = rip_ctloutput, + + .pr_ctlport = cpu0_ctlport, + .pr_usrreqs = &rip_usrreqs + }; + static const struct protosw in_mobile_protosw = -{ SOCK_RAW, &inetdomain, IPPROTO_MOBILE, PR_ATOMIC|PR_ADDR, - gre_mobile_input, rip_output, rip_ctlinput, rip_ctloutput, - cpu0_soport, cpu0_ctlport, - 0, 0, 0, 0, - &rip_usrreqs -}; + { + .pr_type = SOCK_RAW, + .pr_domain = &inetdomain, + .pr_protocol = IPPROTO_MOBILE, + .pr_flags = PR_ATOMIC|PR_ADDR, + + .pr_input = gre_mobile_input, + .pr_output = rip_output, + .pr_ctlinput = rip_ctlinput, + .pr_ctloutput = rip_ctloutput, + + .pr_ctlport = cpu0_ctlport, + .pr_usrreqs = &rip_usrreqs + }; + #endif SYSCTL_DECL(_net_link); diff --git a/sys/net/if.c b/sys/net/if.c index 38002d0651..7cdead343e 100644 --- a/sys/net/if.c +++ b/sys/net/if.c @@ -96,7 +96,7 @@ #endif /* COMPAT_43 */ struct netmsg_ifaddr { - struct netmsg netmsg; + struct netmsg_base base; struct ifaddr *ifa; struct ifnet *ifp; int tail; @@ -253,7 +253,7 @@ static void if_start_ipifunc(void *arg) { struct ifnet *ifp = arg; - struct lwkt_msg *lmsg = &ifp->if_start_nmsg[mycpuid].nm_lmsg; + struct lwkt_msg *lmsg = &ifp->if_start_nmsg[mycpuid].lmsg; crit_enter(); if (lmsg->ms_flags & MSGF_DONE) @@ -322,9 +322,9 @@ if_start_need_schedule(struct ifaltq *ifq, int running) } static void -if_start_dispatch(struct netmsg *nmsg) +if_start_dispatch(netmsg_t msg) { - struct lwkt_msg *lmsg = &nmsg->nm_lmsg; + struct lwkt_msg *lmsg = &msg->base.lmsg; struct ifnet *ifp = lmsg->u.ms_resultp; struct ifaltq *ifq = &ifp->if_snd; int running = 0; @@ -518,12 +518,12 @@ if_attach(struct ifnet *ifp, lwkt_serialize_t serializer) ifp->if_start_cpuid = if_start_cpuid_poll; #endif - ifp->if_start_nmsg = kmalloc(ncpus * sizeof(struct netmsg), + ifp->if_start_nmsg = kmalloc(ncpus * sizeof(*ifp->if_start_nmsg), M_LWKTMSG, M_WAITOK); for (i = 0; i < ncpus; ++i) { netmsg_init(&ifp->if_start_nmsg[i], NULL, &netisr_adone_rport, 0, if_start_dispatch); - ifp->if_start_nmsg[i].nm_lmsg.u.ms_resultp = ifp; + ifp->if_start_nmsg[i].lmsg.u.ms_resultp = ifp; } TAILQ_INSERT_TAIL(&ifnet, ifp, if_link); @@ -1803,15 +1803,16 @@ ifioctl(struct socket *so, u_long cmd, caddr_t data, struct ucred *cred) case OSIOCGIFNETMASK: cmd = SIOCGIFNETMASK; } - error = so_pru_control(so, cmd, data, ifp); - switch (ocmd) { + error = so_pru_control_direct(so, cmd, data, ifp); + + switch (ocmd) { case OSIOCGIFADDR: case OSIOCGIFDSTADDR: case OSIOCGIFBRDADDR: case OSIOCGIFNETMASK: *(u_short *)&ifr->ifr_addr = ifr->ifr_addr.sa_family; - + break; } } #endif /* COMPAT_43 */ @@ -2559,7 +2560,7 @@ ifac_free(struct ifaddr_container *ifac, int cpu_id) } static void -ifa_iflink_dispatch(struct netmsg *nmsg) +ifa_iflink_dispatch(netmsg_t nmsg) { struct netmsg_ifaddr *msg = (struct netmsg_ifaddr *)nmsg; struct ifaddr *ifa = msg->ifa; @@ -2582,7 +2583,7 @@ ifa_iflink_dispatch(struct netmsg *nmsg) crit_exit(); - ifa_forwardmsg(&nmsg->nm_lmsg, cpu + 1); + ifa_forwardmsg(&nmsg->lmsg, cpu + 1); } void @@ -2590,17 +2591,17 @@ ifa_iflink(struct ifaddr *ifa, struct ifnet *ifp, int tail) { struct netmsg_ifaddr msg; - netmsg_init(&msg.netmsg, NULL, &curthread->td_msgport, + netmsg_init(&msg.base, NULL, &curthread->td_msgport, 0, ifa_iflink_dispatch); msg.ifa = ifa; msg.ifp = ifp; msg.tail = tail; - ifa_domsg(&msg.netmsg.nm_lmsg, 0); + ifa_domsg(&msg.base.lmsg, 0); } static void -ifa_ifunlink_dispatch(struct netmsg *nmsg) +ifa_ifunlink_dispatch(netmsg_t nmsg) { struct netmsg_ifaddr *msg = (struct netmsg_ifaddr *)nmsg; struct ifaddr *ifa = msg->ifa; @@ -2620,7 +2621,7 @@ ifa_ifunlink_dispatch(struct netmsg *nmsg) crit_exit(); - ifa_forwardmsg(&nmsg->nm_lmsg, cpu + 1); + ifa_forwardmsg(&nmsg->lmsg, cpu + 1); } void @@ -2628,21 +2629,21 @@ ifa_ifunlink(struct ifaddr *ifa, struct ifnet *ifp) { struct netmsg_ifaddr msg; - netmsg_init(&msg.netmsg, NULL, &curthread->td_msgport, + netmsg_init(&msg.base, NULL, &curthread->td_msgport, 0, ifa_ifunlink_dispatch); msg.ifa = ifa; msg.ifp = ifp; - ifa_domsg(&msg.netmsg.nm_lmsg, 0); + ifa_domsg(&msg.base.lmsg, 0); } static void -ifa_destroy_dispatch(struct netmsg *nmsg) +ifa_destroy_dispatch(netmsg_t nmsg) { struct netmsg_ifaddr *msg = (struct netmsg_ifaddr *)nmsg; IFAFREE(msg->ifa); - ifa_forwardmsg(&nmsg->nm_lmsg, mycpuid + 1); + ifa_forwardmsg(&nmsg->lmsg, mycpuid + 1); } void @@ -2650,11 +2651,11 @@ ifa_destroy(struct ifaddr *ifa) { struct netmsg_ifaddr msg; - netmsg_init(&msg.netmsg, NULL, &curthread->td_msgport, + netmsg_init(&msg.base, NULL, &curthread->td_msgport, 0, ifa_destroy_dispatch); msg.ifa = ifa; - ifa_domsg(&msg.netmsg.nm_lmsg, 0); + ifa_domsg(&msg.base.lmsg, 0); } struct lwkt_port * @@ -2695,11 +2696,11 @@ ifnet_sendmsg(struct lwkt_msg *lmsg, int cpu) static void ifnet_service_loop(void *arg __unused) { - struct netmsg *msg; + netmsg_t msg; while ((msg = lwkt_waitport(&curthread->td_msgport, 0))) { - KASSERT(msg->nm_dispatch, ("ifnet_service: badmsg")); - msg->nm_dispatch(msg); + KASSERT(msg->base.nm_dispatch, ("ifnet_service: badmsg")); + msg->base.nm_dispatch(msg); } } diff --git a/sys/net/if_ethersubr.c b/sys/net/if_ethersubr.c index 14a5603e12..8f2c83e567 100644 --- a/sys/net/if_ethersubr.c +++ b/sys/net/if_ethersubr.c @@ -1041,7 +1041,7 @@ ether_input_ipifunc(void *arg) do { next = m->m_nextpkt; m->m_nextpkt = NULL; - lwkt_sendmsg(port, &m->m_hdr.mh_netmsg.nm_netmsg.nm_lmsg); + lwkt_sendmsg(port, &m->m_hdr.mh_netmsg.base.lmsg); m = next; } while (m != NULL); } @@ -1484,9 +1484,9 @@ failed: } static void -ether_input_handler(struct netmsg *nmsg) +ether_input_handler(netmsg_t nmsg) { - struct netmsg_packet *nmp = (struct netmsg_packet *)nmsg; + struct netmsg_packet *nmp = &nmsg->packet; /* actual size */ struct ether_header *eh; struct ifnet *ifp; struct mbuf *m; @@ -1528,10 +1528,10 @@ ether_dispatch(int isr, struct mbuf *m, struct mbuf_chain *chain) KKASSERT(m->m_flags & M_HASH); pmsg = &m->m_hdr.mh_netmsg; - netmsg_init(&pmsg->nm_netmsg, NULL, &netisr_apanic_rport, + netmsg_init(&pmsg->base, NULL, &netisr_apanic_rport, 0, ether_input_handler); pmsg->nm_packet = m; - pmsg->nm_netmsg.nm_lmsg.u.ms_result = isr; + pmsg->base.lmsg.u.ms_result = isr; if (chain != NULL) { int cpuid = m->m_pkthdr.hash; @@ -1546,8 +1546,7 @@ ether_dispatch(int isr, struct mbuf *m, struct mbuf_chain *chain) } m->m_nextpkt = NULL; } else { - lwkt_sendmsg(cpu_portfn(m->m_pkthdr.hash), - &pmsg->nm_netmsg.nm_lmsg); + lwkt_sendmsg(cpu_portfn(m->m_pkthdr.hash), &pmsg->base.lmsg); } } diff --git a/sys/net/if_poll.c b/sys/net/if_poll.c index 3a11cb0ffd..407259fde7 100644 --- a/sys/net/if_poll.c +++ b/sys/net/if_poll.c @@ -139,7 +139,7 @@ struct iopoll_ctx { uint32_t stalled; /* statistics */ uint32_t pending_polls; /* state */ - struct netmsg poll_netmsg; + struct netmsg_base poll_netmsg; int poll_cpuid; int pollhz; @@ -151,7 +151,7 @@ struct iopoll_ctx { uint32_t poll_handlers; /* next free entry in pr[]. */ struct iopoll_rec pr[IFPOLL_LIST_LEN]; - struct netmsg poll_more_netmsg; + struct netmsg_base poll_more_netmsg; uint32_t poll_burst; /* state */ uint32_t poll_burst_max; /* tunable */ @@ -185,7 +185,7 @@ struct stpoll_rec { }; struct stpoll_ctx { - struct netmsg poll_netmsg; + struct netmsg_base poll_netmsg; int pollhz; @@ -197,19 +197,19 @@ struct stpoll_ctx { }; struct iopoll_sysctl_netmsg { - struct netmsg nmsg; + struct netmsg_base base; struct iopoll_ctx *ctx; }; void ifpoll_init_pcpu(int); -static void ifpoll_register_handler(struct netmsg *); -static void ifpoll_deregister_handler(struct netmsg *); +static void ifpoll_register_handler(netmsg_t); +static void ifpoll_deregister_handler(netmsg_t); /* * Status polling */ static void stpoll_init(void); -static void stpoll_handler(struct netmsg *); +static void stpoll_handler(netmsg_t); static void stpoll_clock(struct stpoll_ctx *); static int stpoll_register(struct ifnet *, const struct ifpoll_status *); static int stpoll_deregister(struct ifnet *); @@ -219,8 +219,8 @@ static int stpoll_deregister(struct ifnet *); */ static struct iopoll_ctx *iopoll_ctx_create(int, int); static void iopoll_init(int); -static void iopoll_handler(struct netmsg *); -static void iopollmore_handler(struct netmsg *); +static void iopoll_handler(netmsg_t); +static void iopollmore_handler(netmsg_t); static void iopoll_clock(struct iopoll_ctx *); static int iopoll_register(struct ifnet *, struct iopoll_ctx *, const struct ifpoll_io *); @@ -228,9 +228,9 @@ static int iopoll_deregister(struct ifnet *, struct iopoll_ctx *); static void iopoll_add_sysctl(struct sysctl_ctx_list *, struct sysctl_oid_list *, struct iopoll_ctx *); -static void sysctl_burstmax_handler(struct netmsg *); +static void sysctl_burstmax_handler(netmsg_t); static int sysctl_burstmax(SYSCTL_HANDLER_ARGS); -static void sysctl_eachburst_handler(struct netmsg *); +static void sysctl_eachburst_handler(netmsg_t); static int sysctl_eachburst(SYSCTL_HANDLER_ARGS); /* @@ -241,9 +241,9 @@ static void poll_comm_start(int); static void poll_comm_adjust_pollhz(struct poll_comm *); static void poll_comm_systimer0(systimer_t, struct intrframe *); static void poll_comm_systimer(systimer_t, struct intrframe *); -static void sysctl_pollhz_handler(struct netmsg *); -static void sysctl_stfrac_handler(struct netmsg *); -static void sysctl_txfrac_handler(struct netmsg *); +static void sysctl_pollhz_handler(netmsg_t); +static void sysctl_stfrac_handler(netmsg_t); +static void sysctl_txfrac_handler(netmsg_t); static int sysctl_pollhz(SYSCTL_HANDLER_ARGS); static int sysctl_stfrac(SYSCTL_HANDLER_ARGS); static int sysctl_txfrac(SYSCTL_HANDLER_ARGS); @@ -272,28 +272,28 @@ TUNABLE_INT("net.ifpoll.status_frac", &ifpoll_stfrac); TUNABLE_INT("net.ifpoll.tx_frac", &ifpoll_txfrac); static __inline void -ifpoll_sendmsg_oncpu(struct netmsg *msg) +ifpoll_sendmsg_oncpu(netmsg_t msg) { - if (msg->nm_lmsg.ms_flags & MSGF_DONE) - ifnet_sendmsg(&msg->nm_lmsg, mycpuid); + if (msg->lmsg.ms_flags & MSGF_DONE) + ifnet_sendmsg(&msg->lmsg, mycpuid); } static __inline void sched_stpoll(struct stpoll_ctx *st_ctx) { - ifpoll_sendmsg_oncpu(&st_ctx->poll_netmsg); + ifpoll_sendmsg_oncpu((netmsg_t)&st_ctx->poll_netmsg); } static __inline void sched_iopoll(struct iopoll_ctx *io_ctx) { - ifpoll_sendmsg_oncpu(&io_ctx->poll_netmsg); + ifpoll_sendmsg_oncpu((netmsg_t)&io_ctx->poll_netmsg); } static __inline void sched_iopollmore(struct iopoll_ctx *io_ctx) { - ifpoll_sendmsg_oncpu(&io_ctx->poll_more_netmsg); + ifpoll_sendmsg_oncpu((netmsg_t)&io_ctx->poll_more_netmsg); } static __inline void @@ -346,7 +346,7 @@ int ifpoll_register(struct ifnet *ifp) { struct ifpoll_info info; - struct netmsg nmsg; + struct netmsg_base nmsg; int error; if (ifp->if_qpoll == NULL) { @@ -376,9 +376,9 @@ ifpoll_register(struct ifnet *ifp) netmsg_init(&nmsg, NULL, &curthread->td_msgport, 0, ifpoll_register_handler); - nmsg.nm_lmsg.u.ms_resultp = &info; + nmsg.lmsg.u.ms_resultp = &info; - error = ifnet_domsg(&nmsg.nm_lmsg, 0); + error = ifnet_domsg(&nmsg.lmsg, 0); if (error) { if (!ifpoll_deregister(ifp)) { if_printf(ifp, "ifpoll_register: " @@ -391,7 +391,7 @@ ifpoll_register(struct ifnet *ifp) int ifpoll_deregister(struct ifnet *ifp) { - struct netmsg nmsg; + struct netmsg_base nmsg; int error; if (ifp->if_qpoll == NULL) @@ -409,9 +409,9 @@ ifpoll_deregister(struct ifnet *ifp) netmsg_init(&nmsg, NULL, &curthread->td_msgport, 0, ifpoll_deregister_handler); - nmsg.nm_lmsg.u.ms_resultp = ifp; + nmsg.lmsg.u.ms_resultp = ifp; - error = ifnet_domsg(&nmsg.nm_lmsg, 0); + error = ifnet_domsg(&nmsg.lmsg, 0); if (!error) { ifnet_serialize_all(ifp); ifp->if_qpoll(ifp, NULL); @@ -421,9 +421,9 @@ ifpoll_deregister(struct ifnet *ifp) } static void -ifpoll_register_handler(struct netmsg *nmsg) +ifpoll_register_handler(netmsg_t nmsg) { - const struct ifpoll_info *info = nmsg->nm_lmsg.u.ms_resultp; + const struct ifpoll_info *info = nmsg->lmsg.u.ms_resultp; int cpuid = mycpuid, nextcpu; int error; @@ -451,18 +451,18 @@ ifpoll_register_handler(struct netmsg *nmsg) nextcpu = cpuid + 1; if (nextcpu < ifpoll_ncpus) - ifnet_forwardmsg(&nmsg->nm_lmsg, nextcpu); + ifnet_forwardmsg(&nmsg->lmsg, nextcpu); else - lwkt_replymsg(&nmsg->nm_lmsg, 0); + lwkt_replymsg(&nmsg->lmsg, 0); return; failed: - lwkt_replymsg(&nmsg->nm_lmsg, error); + lwkt_replymsg(&nmsg->lmsg, error); } static void -ifpoll_deregister_handler(struct netmsg *nmsg) +ifpoll_deregister_handler(netmsg_t nmsg) { - struct ifnet *ifp = nmsg->nm_lmsg.u.ms_resultp; + struct ifnet *ifp = nmsg->lmsg.u.ms_resultp; int cpuid = mycpuid, nextcpu; KKASSERT(cpuid < ifpoll_ncpus); @@ -479,9 +479,9 @@ ifpoll_deregister_handler(struct netmsg *nmsg) nextcpu = cpuid + 1; if (nextcpu < ifpoll_ncpus) - ifnet_forwardmsg(&nmsg->nm_lmsg, nextcpu); + ifnet_forwardmsg(&nmsg->lmsg, nextcpu); else - lwkt_replymsg(&nmsg->nm_lmsg, 0); + lwkt_replymsg(&nmsg->lmsg, 0); } static void @@ -512,7 +512,7 @@ stpoll_init(void) * once per polling systimer tick. */ static void -stpoll_handler(struct netmsg *msg) +stpoll_handler(netmsg_t msg) { struct stpoll_ctx *st_ctx = &stpoll_context; struct thread *td = curthread; @@ -523,7 +523,7 @@ stpoll_handler(struct netmsg *msg) crit_enter_quick(td); /* Reply ASAP */ - lwkt_replymsg(&msg->nm_lmsg, 0); + lwkt_replymsg(&msg->lmsg, 0); if (st_ctx->poll_handlers == 0) { crit_exit_quick(td); @@ -692,11 +692,11 @@ iopoll_ctx_create(int cpuid, int poll_type) netmsg_init(&io_ctx->poll_netmsg, NULL, &netisr_adone_rport, 0, iopoll_handler); - io_ctx->poll_netmsg.nm_lmsg.u.ms_resultp = io_ctx; + io_ctx->poll_netmsg.lmsg.u.ms_resultp = io_ctx; netmsg_init(&io_ctx->poll_more_netmsg, NULL, &netisr_adone_rport, 0, iopollmore_handler); - io_ctx->poll_more_netmsg.nm_lmsg.u.ms_resultp = io_ctx; + io_ctx->poll_more_netmsg.lmsg.u.ms_resultp = io_ctx; /* * Initialize per-cpu sysctl nodes @@ -779,19 +779,19 @@ iopoll_clock(struct iopoll_ctx *io_ctx) * ISR to be scheduled in the handler. */ static void -iopoll_handler(struct netmsg *msg) +iopoll_handler(netmsg_t msg) { struct iopoll_ctx *io_ctx; struct thread *td = curthread; int i, cycles; - io_ctx = msg->nm_lmsg.u.ms_resultp; + io_ctx = msg->lmsg.u.ms_resultp; KKASSERT(&td->td_msgport == ifnet_portfn(io_ctx->poll_cpuid)); crit_enter_quick(td); /* Reply ASAP */ - lwkt_replymsg(&msg->nm_lmsg, 0); + lwkt_replymsg(&msg->lmsg, 0); if (io_ctx->poll_handlers == 0) { crit_exit_quick(td); @@ -848,7 +848,7 @@ iopoll_handler(struct netmsg *msg) * work performed in low level handling. */ static void -iopollmore_handler(struct netmsg *msg) +iopollmore_handler(netmsg_t msg) { struct thread *td = curthread; struct iopoll_ctx *io_ctx; @@ -856,13 +856,13 @@ iopollmore_handler(struct netmsg *msg) int kern_load; uint32_t pending_polls; - io_ctx = msg->nm_lmsg.u.ms_resultp; + io_ctx = msg->lmsg.u.ms_resultp; KKASSERT(&td->td_msgport == ifnet_portfn(io_ctx->poll_cpuid)); crit_enter_quick(td); /* Replay ASAP */ - lwkt_replymsg(&msg->nm_lmsg, 0); + lwkt_replymsg(&msg->lmsg, 0); if (io_ctx->poll_handlers == 0) { crit_exit_quick(td); @@ -967,7 +967,7 @@ iopoll_add_sysctl(struct sysctl_ctx_list *ctx, struct sysctl_oid_list *parent, } static void -sysctl_burstmax_handler(struct netmsg *nmsg) +sysctl_burstmax_handler(netmsg_t nmsg) { struct iopoll_sysctl_netmsg *msg = (struct iopoll_sysctl_netmsg *)nmsg; struct iopoll_ctx *io_ctx; @@ -975,7 +975,7 @@ sysctl_burstmax_handler(struct netmsg *nmsg) io_ctx = msg->ctx; KKASSERT(&curthread->td_msgport == ifnet_portfn(io_ctx->poll_cpuid)); - io_ctx->poll_burst_max = nmsg->nm_lmsg.u.ms_result; + io_ctx->poll_burst_max = nmsg->lmsg.u.ms_result; if (io_ctx->poll_each_burst > io_ctx->poll_burst_max) io_ctx->poll_each_burst = io_ctx->poll_burst_max; if (io_ctx->poll_burst > io_ctx->poll_burst_max) @@ -983,7 +983,7 @@ sysctl_burstmax_handler(struct netmsg *nmsg) if (io_ctx->residual_burst > io_ctx->poll_burst_max) io_ctx->residual_burst = io_ctx->poll_burst_max; - lwkt_replymsg(&nmsg->nm_lmsg, 0); + lwkt_replymsg(&nmsg->lmsg, 0); } static int @@ -991,7 +991,6 @@ sysctl_burstmax(SYSCTL_HANDLER_ARGS) { struct iopoll_ctx *io_ctx = arg1; struct iopoll_sysctl_netmsg msg; - struct netmsg *nmsg; uint32_t burst_max; int error; @@ -1004,17 +1003,16 @@ sysctl_burstmax(SYSCTL_HANDLER_ARGS) else if (burst_max > MAX_IOPOLL_BURST_MAX) burst_max = MAX_IOPOLL_BURST_MAX; - nmsg = &msg.nmsg; - netmsg_init(nmsg, NULL, &curthread->td_msgport, + netmsg_init(&msg.base, NULL, &curthread->td_msgport, 0, sysctl_burstmax_handler); - nmsg->nm_lmsg.u.ms_result = burst_max; + msg.base.lmsg.u.ms_result = burst_max; msg.ctx = io_ctx; - return ifnet_domsg(&nmsg->nm_lmsg, io_ctx->poll_cpuid); + return ifnet_domsg(&msg.base.lmsg, io_ctx->poll_cpuid); } static void -sysctl_eachburst_handler(struct netmsg *nmsg) +sysctl_eachburst_handler(netmsg_t nmsg) { struct iopoll_sysctl_netmsg *msg = (struct iopoll_sysctl_netmsg *)nmsg; struct iopoll_ctx *io_ctx; @@ -1023,14 +1021,14 @@ sysctl_eachburst_handler(struct netmsg *nmsg) io_ctx = msg->ctx; KKASSERT(&curthread->td_msgport == ifnet_portfn(io_ctx->poll_cpuid)); - each_burst = nmsg->nm_lmsg.u.ms_result; + each_burst = nmsg->lmsg.u.ms_result; if (each_burst > io_ctx->poll_burst_max) each_burst = io_ctx->poll_burst_max; else if (each_burst < 1) each_burst = 1; io_ctx->poll_each_burst = each_burst; - lwkt_replymsg(&nmsg->nm_lmsg, 0); + lwkt_replymsg(&nmsg->lmsg, 0); } static int @@ -1038,7 +1036,6 @@ sysctl_eachburst(SYSCTL_HANDLER_ARGS) { struct iopoll_ctx *io_ctx = arg1; struct iopoll_sysctl_netmsg msg; - struct netmsg *nmsg; uint32_t each_burst; int error; @@ -1047,13 +1044,12 @@ sysctl_eachburst(SYSCTL_HANDLER_ARGS) if (error || req->newptr == NULL) return error; - nmsg = &msg.nmsg; - netmsg_init(nmsg, NULL, &curthread->td_msgport, + netmsg_init(&msg.base, NULL, &curthread->td_msgport, 0, sysctl_eachburst_handler); - nmsg->nm_lmsg.u.ms_result = each_burst; + msg.base.lmsg.u.ms_result = each_burst; msg.ctx = io_ctx; - return ifnet_domsg(&nmsg->nm_lmsg, io_ctx->poll_cpuid); + return ifnet_domsg(&msg.base.lmsg, io_ctx->poll_cpuid); } static int @@ -1257,7 +1253,7 @@ static int sysctl_pollhz(SYSCTL_HANDLER_ARGS) { struct poll_comm *comm = arg1; - struct netmsg nmsg; + struct netmsg_base nmsg; int error, phz; phz = comm->pollhz; @@ -1271,20 +1267,20 @@ sysctl_pollhz(SYSCTL_HANDLER_ARGS) netmsg_init(&nmsg, NULL, &curthread->td_msgport, 0, sysctl_pollhz_handler); - nmsg.nm_lmsg.u.ms_result = phz; + nmsg.lmsg.u.ms_result = phz; - return ifnet_domsg(&nmsg.nm_lmsg, comm->poll_cpuid); + return ifnet_domsg(&nmsg.lmsg, comm->poll_cpuid); } static void -sysctl_pollhz_handler(struct netmsg *nmsg) +sysctl_pollhz_handler(netmsg_t nmsg) { struct poll_comm *comm = poll_common[mycpuid]; KKASSERT(&curthread->td_msgport == ifnet_portfn(comm->poll_cpuid)); /* Save polling frequency */ - comm->pollhz = nmsg->nm_lmsg.u.ms_result; + comm->pollhz = nmsg->lmsg.u.ms_result; /* * Adjust cached pollhz @@ -1300,14 +1296,14 @@ sysctl_pollhz_handler(struct netmsg *nmsg) */ poll_comm_adjust_pollhz(comm); - lwkt_replymsg(&nmsg->nm_lmsg, 0); + lwkt_replymsg(&nmsg->lmsg, 0); } static int sysctl_stfrac(SYSCTL_HANDLER_ARGS) { struct poll_comm *comm = arg1; - struct netmsg nmsg; + struct netmsg_base nmsg; int error, stfrac; KKASSERT(comm->poll_cpuid == 0); @@ -1321,16 +1317,16 @@ sysctl_stfrac(SYSCTL_HANDLER_ARGS) netmsg_init(&nmsg, NULL, &curthread->td_msgport, 0, sysctl_stfrac_handler); - nmsg.nm_lmsg.u.ms_result = stfrac; + nmsg.lmsg.u.ms_result = stfrac; - return ifnet_domsg(&nmsg.nm_lmsg, comm->poll_cpuid); + return ifnet_domsg(&nmsg.lmsg, comm->poll_cpuid); } static void -sysctl_stfrac_handler(struct netmsg *nmsg) +sysctl_stfrac_handler(netmsg_t nmsg) { struct poll_comm *comm = poll_common[mycpuid]; - int stfrac = nmsg->nm_lmsg.u.ms_result; + int stfrac = nmsg->lmsg.u.ms_result; KKASSERT(&curthread->td_msgport == ifnet_portfn(comm->poll_cpuid)); @@ -1340,14 +1336,14 @@ sysctl_stfrac_handler(struct netmsg *nmsg) comm->stfrac_count = comm->poll_stfrac; crit_exit(); - lwkt_replymsg(&nmsg->nm_lmsg, 0); + lwkt_replymsg(&nmsg->lmsg, 0); } static int sysctl_txfrac(SYSCTL_HANDLER_ARGS) { struct poll_comm *comm = arg1; - struct netmsg nmsg; + struct netmsg_base nmsg; int error, txfrac; txfrac = comm->poll_txfrac; @@ -1359,16 +1355,16 @@ sysctl_txfrac(SYSCTL_HANDLER_ARGS) netmsg_init(&nmsg, NULL, &curthread->td_msgport, 0, sysctl_txfrac_handler); - nmsg.nm_lmsg.u.ms_result = txfrac; + nmsg.lmsg.u.ms_result = txfrac; - return ifnet_domsg(&nmsg.nm_lmsg, comm->poll_cpuid); + return ifnet_domsg(&nmsg.lmsg, comm->poll_cpuid); } static void -sysctl_txfrac_handler(struct netmsg *nmsg) +sysctl_txfrac_handler(netmsg_t nmsg) { struct poll_comm *comm = poll_common[mycpuid]; - int txfrac = nmsg->nm_lmsg.u.ms_result; + int txfrac = nmsg->lmsg.u.ms_result; KKASSERT(&curthread->td_msgport == ifnet_portfn(comm->poll_cpuid)); @@ -1378,5 +1374,5 @@ sysctl_txfrac_handler(struct netmsg *nmsg) comm->txfrac_count = comm->poll_txfrac; crit_exit(); - lwkt_replymsg(&nmsg->nm_lmsg, 0); + lwkt_replymsg(&nmsg->lmsg, 0); } diff --git a/sys/net/if_var.h b/sys/net/if_var.h index 3334f052ac..f88573f2b9 100644 --- a/sys/net/if_var.h +++ b/sys/net/if_var.h @@ -88,7 +88,7 @@ struct ifaddr_container; struct ifaddr; struct lwkt_port; struct lwkt_msg; -struct netmsg; +union netmsg; struct pktinfo; struct ifpoll_info; @@ -273,7 +273,7 @@ struct ifnet { struct lwkt_serialize *if_serializer; /* serializer or MP lock */ struct lwkt_serialize if_default_serializer; /* if not supplied */ int if_cpuid; - struct netmsg *if_start_nmsg; /* percpu messages to schedule if_start */ + struct netmsg_base *if_start_nmsg; /* percpu msgs to sched if_start */ void *if_pf_kif; /* pf interface abstraction */ union { void *carp_s; /* carp structure (used by !carp ifs) */ diff --git a/sys/net/ip_mroute/ip_mroute.c b/sys/net/ip_mroute/ip_mroute.c index c7ab5393cc..8c2ac22e4d 100644 --- a/sys/net/ip_mroute/ip_mroute.c +++ b/sys/net/ip_mroute/ip_mroute.c @@ -1708,16 +1708,19 @@ encap_send(struct ip *ip, struct vif *vifp, struct mbuf *m) * * This is similar to mroute_encapcheck() + mroute_encap_input() in -current. */ -static void -X_ipip_input(struct mbuf *m, int off, int proto) +static int +X_ipip_input(struct mbuf **mp, int *offp, int proto) { + struct mbuf *m = *mp; struct ip *ip = mtod(m, struct ip *); int hlen = ip->ip_hl << 2; if (!have_encap_tunnel) { - rip_input(m, off, proto); - return; + rip_input(mp, offp, proto); + return(IPPROTO_DONE); } + *mp = NULL; + /* * dump the packet if it's not to a multicast destination or if * we don't have an encapsulating tunnel with the source. @@ -1728,7 +1731,7 @@ X_ipip_input(struct mbuf *m, int off, int proto) if (!IN_MULTICAST(ntohl(((struct ip *)((char *)ip+hlen))->ip_dst.s_addr))) { ++mrtstat.mrts_bad_tunnel; m_freem(m); - return; + return(IPPROTO_DONE); } if (ip->ip_src.s_addr != last_encap_src) { struct vif *vifp = viftable; @@ -1751,7 +1754,7 @@ X_ipip_input(struct mbuf *m, int off, int proto) if (mrtdebug) log(LOG_DEBUG, "ip_mforward: no tunnel with %lx\n", (u_long)ntohl(ip->ip_src.s_addr)); - return; + return(IPPROTO_DONE); } if (hlen > sizeof(struct ip)) @@ -1762,6 +1765,7 @@ X_ipip_input(struct mbuf *m, int off, int proto) m->m_pkthdr.rcvif = last_encap_vif->v_ifp; netisr_queue(NETISR_IP, m); + return(IPPROTO_DONE); } /* @@ -2108,26 +2112,24 @@ X_ip_rsvp_force_done(struct socket *so) lwkt_reltoken(&mroute_token); } -static void -X_rsvp_input(struct mbuf *m, ...) +static int +X_rsvp_input(struct mbuf **mp, int *offp, int proto) { int vifi; + struct mbuf *m = *mp; struct ip *ip = mtod(m, struct ip *); struct sockaddr_in rsvp_src = { sizeof rsvp_src, AF_INET }; struct ifnet *ifp; - int off, proto; + int off; #ifdef ALTQ /* support IP_RECVIF used by rsvpd rel4.2a1 */ struct inpcb *inp; struct socket *so; struct mbuf *opts; #endif - __va_list ap; - __va_start(ap, m); - off = __va_arg(ap, int); - proto = __va_arg(ap, int); - __va_end(ap); + off = *offp; + *mp = NULL; if (rsvpdebug) kprintf("rsvp_input: rsvp_on %d\n",rsvp_on); @@ -2138,7 +2140,7 @@ X_rsvp_input(struct mbuf *m, ...) */ if (!rsvp_on) { m_freem(m); - return; + return(IPPROTO_DONE); } lwkt_gettoken(&mroute_token); @@ -2170,7 +2172,8 @@ X_rsvp_input(struct mbuf *m, ...) if (ip_rsvpd != NULL) { if (rsvpdebug) kprintf("rsvp_input: Sending packet up old-style socket\n"); - rip_input(m, off, proto); /* xxx */ + *mp = m; + rip_input(mp, offp, proto); /* xxx */ } else { if (rsvpdebug && vifi == numvifs) kprintf("rsvp_input: Can't find vif for packet.\n"); @@ -2179,7 +2182,7 @@ X_rsvp_input(struct mbuf *m, ...) m_freem(m); } lwkt_reltoken(&mroute_token); - return; + return(IPPROTO_DONE); } rsvp_src.sin_addr = ip->ip_src; @@ -2191,8 +2194,9 @@ X_rsvp_input(struct mbuf *m, ...) opts = NULL; inp = (struct inpcb *)so->so_pcb; if (inp->inp_flags & INP_CONTROLOPTS || - inp->inp_socket->so_options & SO_TIMESTAMP) + inp->inp_socket->so_options & SO_TIMESTAMP) { ip_savecontrol(inp, &opts, ip, m); + } if (ssb_appendaddr(&so->so_rcv, (struct sockaddr *)&rsvp_src,m, opts) == 0) { m_freem(m); @@ -2215,8 +2219,8 @@ X_rsvp_input(struct mbuf *m, ...) kprintf("rsvp_input: send packet up\n"); } #endif /* !ALTQ */ - lwkt_reltoken(&mroute_token); + return(IPPROTO_DONE); } /* @@ -3017,24 +3021,19 @@ pim_register_send_rp(struct ip *ip, struct vif *vifp, * (used by PIM-SM): the PIM header is stripped off, and the inner packet * is passed to if_simloop(). */ -void -pim_input(struct mbuf *m, ...) +int +pim_input(struct mbuf **mp, int *offp, int proto) { - int off, proto; + struct mbuf *m = *mp; struct ip *ip = mtod(m, struct ip *); struct pim *pim; int minlen; int datalen = ip->ip_len; int ip_tos; int iphlen; - __va_list ap; - __va_start(ap, m); - off = __va_arg(ap, int); - proto = __va_arg(ap, int); - __va_end(ap); - - iphlen = off; + iphlen = *offp; + *mp = NULL; /* Keep statistics */ pimstat.pims_rcv_total_msgs++; @@ -3048,7 +3047,7 @@ pim_input(struct mbuf *m, ...) log(LOG_ERR, "pim_input: packet size too small %d from %lx\n", datalen, (u_long)ip->ip_src.s_addr); m_freem(m); - return; + return(IPPROTO_DONE); } /* @@ -3067,7 +3066,7 @@ pim_input(struct mbuf *m, ...) if ((m->m_flags & M_EXT || m->m_len < minlen) && (m = m_pullup(m, minlen)) == 0) { log(LOG_ERR, "pim_input: m_pullup failure\n"); - return; + return(IPPROTO_DONE); } /* m_pullup() may have given us a new mbuf so reset ip. */ ip = mtod(m, struct ip *); @@ -3092,7 +3091,7 @@ pim_input(struct mbuf *m, ...) if (mrtdebug & DEBUG_PIM) log(LOG_DEBUG, "pim_input: invalid checksum"); m_freem(m); - return; + return(IPPROTO_DONE); } /* PIM version check */ @@ -3101,7 +3100,7 @@ pim_input(struct mbuf *m, ...) log(LOG_ERR, "pim_input: incorrect version %d, expecting %d\n", PIM_VT_V(pim->pim_vt), PIM_VERSION); m_freem(m); - return; + return(IPPROTO_DONE); } /* restore mbuf back to the outer IP */ @@ -3124,7 +3123,7 @@ pim_input(struct mbuf *m, ...) log(LOG_DEBUG, "pim_input: register vif not set: %d\n", reg_vif_num); m_freem(m); - return; + return(IPPROTO_DONE); } /* @@ -3137,7 +3136,7 @@ pim_input(struct mbuf *m, ...) "pim_input: register packet size too small %d from %lx\n", datalen, (u_long)ip->ip_src.s_addr); m_freem(m); - return; + return(IPPROTO_DONE); } reghdr = (u_int32_t *)(pim + 1); @@ -3159,7 +3158,7 @@ pim_input(struct mbuf *m, ...) "of the inner packet\n", encap_ip->ip_v); } m_freem(m); - return; + return(IPPROTO_DONE); } /* verify the inner packet is destined to a mcast group */ @@ -3171,7 +3170,7 @@ pim_input(struct mbuf *m, ...) "multicast %lx\n", (u_long)ntohl(encap_ip->ip_dst.s_addr)); m_freem(m); - return; + return(IPPROTO_DONE); } /* If a NULL_REGISTER, pass it to the daemon */ @@ -3211,7 +3210,7 @@ pim_input(struct mbuf *m, ...) log(LOG_ERR, "pim_input: pim register: could not copy register head\n"); m_freem(m); - return; + return(IPPROTO_DONE); } /* Keep statistics */ @@ -3247,9 +3246,10 @@ pim_input_to_daemon: * XXX: the outer IP header pkt size of a Register is not adjust to * reflect the fact that the inner multicast data is truncated. */ - rip_input(m, iphlen, proto); - - return; + *mp = m; + *offp = iphlen; + rip_input(mp, offp, proto); + return(IPPROTO_DONE); } #endif /* PIM */ diff --git a/sys/net/ipfw/ip_fw2.c b/sys/net/ipfw/ip_fw2.c index f6d3090dc3..2fe5cf017e 100644 --- a/sys/net/ipfw/ip_fw2.c +++ b/sys/net/ipfw/ip_fw2.c @@ -223,7 +223,7 @@ do { \ #define IPFW_DEFAULT_SET 31 /* set number for the default rule */ struct netmsg_ipfw { - struct netmsg nmsg; + struct netmsg_base base; const struct ipfw_ioc_rule *ioc_rule; struct ip_fw *next_rule; struct ip_fw *prev_rule; @@ -232,7 +232,7 @@ struct netmsg_ipfw { }; struct netmsg_del { - struct netmsg nmsg; + struct netmsg_base base; struct ip_fw *start_rule; struct ip_fw *prev_rule; uint16_t rulenum; @@ -241,7 +241,7 @@ struct netmsg_del { }; struct netmsg_zent { - struct netmsg nmsg; + struct netmsg_base base; struct ip_fw *start_rule; uint16_t rulenum; uint16_t log_only; @@ -370,7 +370,7 @@ static uint32_t curr_dyn_buckets = 256; /* must be power of 2 */ static uint32_t dyn_buckets_gen; /* generation of dyn buckets array */ static struct lock dyn_lock; /* dynamic rules' hash table lock */ -static struct netmsg ipfw_timeout_netmsg; /* schedule ipfw timeout */ +static struct netmsg_base ipfw_timeout_netmsg; /* schedule ipfw timeout */ static struct callout ipfw_timeout_h; /* @@ -2581,7 +2581,7 @@ ipfw_create_rule(const struct ipfw_ioc_rule *ioc_rule, struct ip_fw_stub *stub) } static void -ipfw_add_rule_dispatch(struct netmsg *nmsg) +ipfw_add_rule_dispatch(netmsg_t nmsg) { struct netmsg_ipfw *fwmsg = (struct netmsg_ipfw *)nmsg; struct ipfw_context *ctx = ipfw_ctx[mycpuid]; @@ -2632,16 +2632,16 @@ ipfw_add_rule_dispatch(struct netmsg *nmsg) ipfw_inc_static_count(rule); /* Return the rule on CPU0 */ - nmsg->nm_lmsg.u.ms_resultp = rule; + nmsg->lmsg.u.ms_resultp = rule; } - ifnet_forwardmsg(&nmsg->nm_lmsg, mycpuid + 1); + ifnet_forwardmsg(&nmsg->lmsg, mycpuid + 1); } static void -ipfw_enable_state_dispatch(struct netmsg *nmsg) +ipfw_enable_state_dispatch(netmsg_t nmsg) { - struct lwkt_msg *lmsg = &nmsg->nm_lmsg; + struct lwkt_msg *lmsg = &nmsg->lmsg; struct ip_fw *rule = lmsg->u.ms_resultp; struct ipfw_context *ctx = ipfw_ctx[mycpuid]; @@ -2667,7 +2667,7 @@ ipfw_add_rule(struct ipfw_ioc_rule *ioc_rule, uint32_t rule_flags) { struct ipfw_context *ctx = ipfw_ctx[mycpuid]; struct netmsg_ipfw fwmsg; - struct netmsg *nmsg; + struct netmsg_base *nmsg; struct ip_fw *f, *prev, *rule; struct ip_fw_stub *stub; @@ -2729,7 +2729,7 @@ ipfw_add_rule(struct ipfw_ioc_rule *ioc_rule, uint32_t rule_flags) * The rule duplicated on CPU0 will be returned. */ bzero(&fwmsg, sizeof(fwmsg)); - nmsg = &fwmsg.nmsg; + nmsg = &fwmsg.base; netmsg_init(nmsg, NULL, &curthread->td_msgport, 0, ipfw_add_rule_dispatch); fwmsg.ioc_rule = ioc_rule; @@ -2737,10 +2737,10 @@ ipfw_add_rule(struct ipfw_ioc_rule *ioc_rule, uint32_t rule_flags) fwmsg.next_rule = prev == NULL ? NULL : f; fwmsg.stub = stub; - ifnet_domsg(&nmsg->nm_lmsg, 0); + ifnet_domsg(&nmsg->lmsg, 0); KKASSERT(fwmsg.prev_rule == NULL && fwmsg.next_rule == NULL); - rule = nmsg->nm_lmsg.u.ms_resultp; + rule = nmsg->lmsg.u.ms_resultp; KKASSERT(rule != NULL && rule->cpuid == mycpuid); if (rule_flags & IPFW_RULE_F_STATE) { @@ -2751,10 +2751,10 @@ ipfw_add_rule(struct ipfw_ioc_rule *ioc_rule, uint32_t rule_flags) bzero(nmsg, sizeof(*nmsg)); netmsg_init(nmsg, NULL, &curthread->td_msgport, 0, ipfw_enable_state_dispatch); - nmsg->nm_lmsg.u.ms_resultp = rule; + nmsg->lmsg.u.ms_resultp = rule; - ifnet_domsg(&nmsg->nm_lmsg, 0); - KKASSERT(nmsg->nm_lmsg.u.ms_resultp == NULL); + ifnet_domsg(&nmsg->lmsg, 0); + KKASSERT(nmsg->lmsg.u.ms_resultp == NULL); } DPRINTF("++ installed rule %d, static count now %d\n", @@ -2815,9 +2815,9 @@ ipfw_delete_rule(struct ipfw_context *ctx, } static void -ipfw_flush_dispatch(struct netmsg *nmsg) +ipfw_flush_dispatch(netmsg_t nmsg) { - struct lwkt_msg *lmsg = &nmsg->nm_lmsg; + struct lwkt_msg *lmsg = &nmsg->lmsg; int kill_default = lmsg->u.ms_result; struct ipfw_context *ctx = ipfw_ctx[mycpuid]; struct ip_fw *rule; @@ -2832,7 +2832,7 @@ ipfw_flush_dispatch(struct netmsg *nmsg) } static void -ipfw_disable_rule_state_dispatch(struct netmsg *nmsg) +ipfw_disable_rule_state_dispatch(netmsg_t nmsg) { struct netmsg_del *dmsg = (struct netmsg_del *)nmsg; struct ipfw_context *ctx = ipfw_ctx[mycpuid]; @@ -2861,7 +2861,7 @@ ipfw_disable_rule_state_dispatch(struct netmsg *nmsg) rule = rule->next; } - ifnet_forwardmsg(&nmsg->nm_lmsg, mycpuid + 1); + ifnet_forwardmsg(&nmsg->lmsg, mycpuid + 1); } /* @@ -2873,7 +2873,7 @@ static void ipfw_flush(int kill_default) { struct netmsg_del dmsg; - struct netmsg nmsg; + struct netmsg_base nmsg; struct lwkt_msg *lmsg; struct ip_fw *rule; struct ipfw_context *ctx = ipfw_ctx[mycpuid]; @@ -2899,9 +2899,9 @@ ipfw_flush(int kill_default) * will be created. */ bzero(&dmsg, sizeof(dmsg)); - netmsg_init(&dmsg.nmsg, NULL, &curthread->td_msgport, + netmsg_init(&dmsg.base, NULL, &curthread->td_msgport, 0, ipfw_disable_rule_state_dispatch); - ifnet_domsg(&dmsg.nmsg.nm_lmsg, 0); + ifnet_domsg(&dmsg.base.lmsg, 0); /* * This actually nukes all states (dyn rules) @@ -2926,7 +2926,7 @@ ipfw_flush(int kill_default) bzero(&nmsg, sizeof(nmsg)); netmsg_init(&nmsg, NULL, &curthread->td_msgport, 0, ipfw_flush_dispatch); - lmsg = &nmsg.nm_lmsg; + lmsg = &nmsg.lmsg; lmsg->u.ms_result = kill_default; ifnet_domsg(lmsg, 0); @@ -2959,7 +2959,7 @@ ipfw_flush(int kill_default) } static void -ipfw_alt_delete_rule_dispatch(struct netmsg *nmsg) +ipfw_alt_delete_rule_dispatch(netmsg_t nmsg) { struct netmsg_del *dmsg = (struct netmsg_del *)nmsg; struct ipfw_context *ctx = ipfw_ctx[mycpuid]; @@ -2988,7 +2988,7 @@ ipfw_alt_delete_rule_dispatch(struct netmsg *nmsg) while (rule && rule->rulenum == dmsg->rulenum) rule = ipfw_delete_rule(ctx, prev, rule); - ifnet_forwardmsg(&nmsg->nm_lmsg, mycpuid + 1); + ifnet_forwardmsg(&nmsg->lmsg, mycpuid + 1); } static int @@ -2997,7 +2997,7 @@ ipfw_alt_delete_rule(uint16_t rulenum) struct ip_fw *prev, *rule, *f; struct ipfw_context *ctx = ipfw_ctx[mycpuid]; struct netmsg_del dmsg; - struct netmsg *nmsg; + struct netmsg_base *nmsg; int state; /* @@ -3028,13 +3028,13 @@ ipfw_alt_delete_rule(uint16_t rulenum) * created based the rules numbered 'rulenum'. */ bzero(&dmsg, sizeof(dmsg)); - nmsg = &dmsg.nmsg; + nmsg = &dmsg.base; netmsg_init(nmsg, NULL, &curthread->td_msgport, 0, ipfw_disable_rule_state_dispatch); dmsg.start_rule = rule; dmsg.rulenum = rulenum; - ifnet_domsg(&nmsg->nm_lmsg, 0); + ifnet_domsg(&nmsg->lmsg, 0); KKASSERT(dmsg.start_rule == NULL); /* @@ -3059,20 +3059,20 @@ ipfw_alt_delete_rule(uint16_t rulenum) * Get rid of the rule duplications on all CPUs */ bzero(&dmsg, sizeof(dmsg)); - nmsg = &dmsg.nmsg; + nmsg = &dmsg.base; netmsg_init(nmsg, NULL, &curthread->td_msgport, 0, ipfw_alt_delete_rule_dispatch); dmsg.prev_rule = prev; dmsg.start_rule = rule; dmsg.rulenum = rulenum; - ifnet_domsg(&nmsg->nm_lmsg, 0); + ifnet_domsg(&nmsg->lmsg, 0); KKASSERT(dmsg.prev_rule == NULL && dmsg.start_rule == NULL); return 0; } static void -ipfw_alt_delete_ruleset_dispatch(struct netmsg *nmsg) +ipfw_alt_delete_ruleset_dispatch(netmsg_t nmsg) { struct netmsg_del *dmsg = (struct netmsg_del *)nmsg; struct ipfw_context *ctx = ipfw_ctx[mycpuid]; @@ -3098,11 +3098,11 @@ ipfw_alt_delete_ruleset_dispatch(struct netmsg *nmsg) } KASSERT(del, ("no match set?!\n")); - ifnet_forwardmsg(&nmsg->nm_lmsg, mycpuid + 1); + ifnet_forwardmsg(&nmsg->lmsg, mycpuid + 1); } static void -ipfw_disable_ruleset_state_dispatch(struct netmsg *nmsg) +ipfw_disable_ruleset_state_dispatch(netmsg_t nmsg) { struct netmsg_del *dmsg = (struct netmsg_del *)nmsg; struct ipfw_context *ctx = ipfw_ctx[mycpuid]; @@ -3123,14 +3123,14 @@ ipfw_disable_ruleset_state_dispatch(struct netmsg *nmsg) } KASSERT(cleared, ("no match set?!\n")); - ifnet_forwardmsg(&nmsg->nm_lmsg, mycpuid + 1); + ifnet_forwardmsg(&nmsg->lmsg, mycpuid + 1); } static int ipfw_alt_delete_ruleset(uint8_t set) { struct netmsg_del dmsg; - struct netmsg *nmsg; + struct netmsg_base *nmsg; int state, del; struct ip_fw *rule; struct ipfw_context *ctx = ipfw_ctx[mycpuid]; @@ -3160,12 +3160,12 @@ ipfw_alt_delete_ruleset(uint8_t set) * created based the rules in this set. */ bzero(&dmsg, sizeof(dmsg)); - nmsg = &dmsg.nmsg; + nmsg = &dmsg.base; netmsg_init(nmsg, NULL, &curthread->td_msgport, 0, ipfw_disable_ruleset_state_dispatch); dmsg.from_set = set; - ifnet_domsg(&nmsg->nm_lmsg, 0); + ifnet_domsg(&nmsg->lmsg, 0); /* * Nuke all related states @@ -3192,17 +3192,17 @@ ipfw_alt_delete_ruleset(uint8_t set) * Delete this set */ bzero(&dmsg, sizeof(dmsg)); - nmsg = &dmsg.nmsg; + nmsg = &dmsg.base; netmsg_init(nmsg, NULL, &curthread->td_msgport, 0, ipfw_alt_delete_ruleset_dispatch); dmsg.from_set = set; - ifnet_domsg(&nmsg->nm_lmsg, 0); + ifnet_domsg(&nmsg->lmsg, 0); return 0; } static void -ipfw_alt_move_rule_dispatch(struct netmsg *nmsg) +ipfw_alt_move_rule_dispatch(netmsg_t nmsg) { struct netmsg_del *dmsg = (struct netmsg_del *)nmsg; struct ip_fw *rule; @@ -3221,14 +3221,14 @@ ipfw_alt_move_rule_dispatch(struct netmsg *nmsg) rule->set = dmsg->to_set; rule = rule->next; } - ifnet_forwardmsg(&nmsg->nm_lmsg, mycpuid + 1); + ifnet_forwardmsg(&nmsg->lmsg, mycpuid + 1); } static int ipfw_alt_move_rule(uint16_t rulenum, uint8_t set) { struct netmsg_del dmsg; - struct netmsg *nmsg; + struct netmsg_base *nmsg; struct ip_fw *rule; struct ipfw_context *ctx = ipfw_ctx[mycpuid]; @@ -3244,20 +3244,20 @@ ipfw_alt_move_rule(uint16_t rulenum, uint8_t set) return 0; /* XXX error? */ bzero(&dmsg, sizeof(dmsg)); - nmsg = &dmsg.nmsg; + nmsg = &dmsg.base; netmsg_init(nmsg, NULL, &curthread->td_msgport, 0, ipfw_alt_move_rule_dispatch); dmsg.start_rule = rule; dmsg.rulenum = rulenum; dmsg.to_set = set; - ifnet_domsg(&nmsg->nm_lmsg, 0); + ifnet_domsg(&nmsg->lmsg, 0); KKASSERT(dmsg.start_rule == NULL); return 0; } static void -ipfw_alt_move_ruleset_dispatch(struct netmsg *nmsg) +ipfw_alt_move_ruleset_dispatch(netmsg_t nmsg) { struct netmsg_del *dmsg = (struct netmsg_del *)nmsg; struct ipfw_context *ctx = ipfw_ctx[mycpuid]; @@ -3267,28 +3267,28 @@ ipfw_alt_move_ruleset_dispatch(struct netmsg *nmsg) if (rule->set == dmsg->from_set) rule->set = dmsg->to_set; } - ifnet_forwardmsg(&nmsg->nm_lmsg, mycpuid + 1); + ifnet_forwardmsg(&nmsg->lmsg, mycpuid + 1); } static int ipfw_alt_move_ruleset(uint8_t from_set, uint8_t to_set) { struct netmsg_del dmsg; - struct netmsg *nmsg; + struct netmsg_base *nmsg; bzero(&dmsg, sizeof(dmsg)); - nmsg = &dmsg.nmsg; + nmsg = &dmsg.base; netmsg_init(nmsg, NULL, &curthread->td_msgport, 0, ipfw_alt_move_ruleset_dispatch); dmsg.from_set = from_set; dmsg.to_set = to_set; - ifnet_domsg(&nmsg->nm_lmsg, 0); + ifnet_domsg(&nmsg->lmsg, 0); return 0; } static void -ipfw_alt_swap_ruleset_dispatch(struct netmsg *nmsg) +ipfw_alt_swap_ruleset_dispatch(netmsg_t nmsg) { struct netmsg_del *dmsg = (struct netmsg_del *)nmsg; struct ipfw_context *ctx = ipfw_ctx[mycpuid]; @@ -3300,23 +3300,23 @@ ipfw_alt_swap_ruleset_dispatch(struct netmsg *nmsg) else if (rule->set == dmsg->to_set) rule->set = dmsg->from_set; } - ifnet_forwardmsg(&nmsg->nm_lmsg, mycpuid + 1); + ifnet_forwardmsg(&nmsg->lmsg, mycpuid + 1); } static int ipfw_alt_swap_ruleset(uint8_t set1, uint8_t set2) { struct netmsg_del dmsg; - struct netmsg *nmsg; + struct netmsg_base *nmsg; bzero(&dmsg, sizeof(dmsg)); - nmsg = &dmsg.nmsg; + nmsg = &dmsg.base; netmsg_init(nmsg, NULL, &curthread->td_msgport, 0, ipfw_alt_swap_ruleset_dispatch); dmsg.from_set = set1; dmsg.to_set = set2; - ifnet_domsg(&nmsg->nm_lmsg, 0); + ifnet_domsg(&nmsg->lmsg, 0); return 0; } @@ -3396,7 +3396,7 @@ clear_counters(struct ip_fw *rule, int log_only) } static void -ipfw_zero_entry_dispatch(struct netmsg *nmsg) +ipfw_zero_entry_dispatch(netmsg_t nmsg) { struct netmsg_zent *zmsg = (struct netmsg_zent *)nmsg; struct ipfw_context *ctx = ipfw_ctx[mycpuid]; @@ -3428,7 +3428,7 @@ ipfw_zero_entry_dispatch(struct netmsg *nmsg) */ zmsg->start_rule = start->sibling; } - ifnet_forwardmsg(&nmsg->nm_lmsg, mycpuid + 1); + ifnet_forwardmsg(&nmsg->lmsg, mycpuid + 1); } /** @@ -3441,12 +3441,12 @@ static int ipfw_ctl_zero_entry(int rulenum, int log_only) { struct netmsg_zent zmsg; - struct netmsg *nmsg; + struct netmsg_base *nmsg; const char *msg; struct ipfw_context *ctx = ipfw_ctx[mycpuid]; bzero(&zmsg, sizeof(zmsg)); - nmsg = &zmsg.nmsg; + nmsg = &zmsg.base; netmsg_init(nmsg, NULL, &curthread->td_msgport, 0, ipfw_zero_entry_dispatch); zmsg.log_only = log_only; @@ -3472,7 +3472,7 @@ ipfw_ctl_zero_entry(int rulenum, int log_only) msg = log_only ? "ipfw: Entry %d logging count reset.\n" : "ipfw: Entry %d cleared.\n"; } - ifnet_domsg(&nmsg->nm_lmsg, 0); + ifnet_domsg(&nmsg->lmsg, 0); KKASSERT(zmsg.start_rule == NULL); if (fw_verbose) @@ -3872,9 +3872,9 @@ skip: } static void -ipfw_set_disable_dispatch(struct netmsg *nmsg) +ipfw_set_disable_dispatch(netmsg_t nmsg) { - struct lwkt_msg *lmsg = &nmsg->nm_lmsg; + struct lwkt_msg *lmsg = &nmsg->lmsg; struct ipfw_context *ctx = ipfw_ctx[mycpuid]; ctx->ipfw_gen++; @@ -3886,7 +3886,7 @@ ipfw_set_disable_dispatch(struct netmsg *nmsg) static void ipfw_ctl_set_disable(uint32_t disable, uint32_t enable) { - struct netmsg nmsg; + struct netmsg_base nmsg; struct lwkt_msg *lmsg; uint32_t set_disable; @@ -3897,7 +3897,7 @@ ipfw_ctl_set_disable(uint32_t disable, uint32_t enable) bzero(&nmsg, sizeof(nmsg)); netmsg_init(&nmsg, NULL, &curthread->td_msgport, 0, ipfw_set_disable_dispatch); - lmsg = &nmsg.nm_lmsg; + lmsg = &nmsg.lmsg; lmsg->u.ms_result32 = set_disable; ifnet_domsg(lmsg, 0); @@ -3984,7 +3984,7 @@ ipfw_ctl(struct sockopt *sopt) * every dyn_keepalive_period */ static void -ipfw_tick_dispatch(struct netmsg *nmsg) +ipfw_tick_dispatch(netmsg_t nmsg) { time_t keep_alive; uint32_t gen; @@ -3995,7 +3995,7 @@ ipfw_tick_dispatch(struct netmsg *nmsg) /* Reply ASAP */ crit_enter(); - lwkt_replymsg(&nmsg->nm_lmsg, 0); + lwkt_replymsg(&nmsg->lmsg, 0); crit_exit(); if (ipfw_dyn_v == NULL || dyn_count == 0) @@ -4085,7 +4085,7 @@ done: static void ipfw_tick(void *dummy __unused) { - struct lwkt_msg *lmsg = &ipfw_timeout_netmsg.nm_lmsg; + struct lwkt_msg *lmsg = &ipfw_timeout_netmsg.lmsg; KKASSERT(mycpuid == IPFW_CFGCPUID); @@ -4270,9 +4270,9 @@ ipfw_dehook(void) } static void -ipfw_sysctl_enable_dispatch(struct netmsg *nmsg) +ipfw_sysctl_enable_dispatch(netmsg_t nmsg) { - struct lwkt_msg *lmsg = &nmsg->nm_lmsg; + struct lwkt_msg *lmsg = &nmsg->lmsg; int enable = lmsg->u.ms_result; if (fw_enable == enable) @@ -4290,7 +4290,7 @@ reply: static int ipfw_sysctl_enable(SYSCTL_HANDLER_ARGS) { - struct netmsg nmsg; + struct netmsg_base nmsg; struct lwkt_msg *lmsg; int enable, error; @@ -4301,7 +4301,7 @@ ipfw_sysctl_enable(SYSCTL_HANDLER_ARGS) netmsg_init(&nmsg, NULL, &curthread->td_msgport, 0, ipfw_sysctl_enable_dispatch); - lmsg = &nmsg.nm_lmsg; + lmsg = &nmsg.lmsg; lmsg->u.ms_result = enable; return lwkt_domsg(IPFW_CFGPORT, lmsg, 0); @@ -4358,7 +4358,7 @@ ipfw_sysctl_dyn_rst(SYSCTL_HANDLER_ARGS) } static void -ipfw_ctx_init_dispatch(struct netmsg *nmsg) +ipfw_ctx_init_dispatch(netmsg_t nmsg) { struct netmsg_ipfw *fwmsg = (struct netmsg_ipfw *)nmsg; struct ipfw_context *ctx; @@ -4395,11 +4395,11 @@ ipfw_ctx_init_dispatch(struct netmsg *nmsg) if (mycpuid == 0) ipfw_inc_static_count(def_rule); - ifnet_forwardmsg(&nmsg->nm_lmsg, mycpuid + 1); + ifnet_forwardmsg(&nmsg->lmsg, mycpuid + 1); } static void -ipfw_init_dispatch(struct netmsg *nmsg) +ipfw_init_dispatch(netmsg_t nmsg) { struct netmsg_ipfw fwmsg; int error = 0; @@ -4411,9 +4411,9 @@ ipfw_init_dispatch(struct netmsg *nmsg) } bzero(&fwmsg, sizeof(fwmsg)); - netmsg_init(&fwmsg.nmsg, NULL, &curthread->td_msgport, + netmsg_init(&fwmsg.base, NULL, &curthread->td_msgport, 0, ipfw_ctx_init_dispatch); - ifnet_domsg(&fwmsg.nmsg.nm_lmsg, 0); + ifnet_domsg(&fwmsg.base.lmsg, 0); ip_fw_chk_ptr = ipfw_chk; ip_fw_ctl_ptr = ipfw_ctl; @@ -4450,23 +4450,23 @@ ipfw_init_dispatch(struct netmsg *nmsg) if (fw_enable) ipfw_hook(); reply: - lwkt_replymsg(&nmsg->nm_lmsg, error); + lwkt_replymsg(&nmsg->lmsg, error); } static int ipfw_init(void) { - struct netmsg smsg; + struct netmsg_base smsg; netmsg_init(&smsg, NULL, &curthread->td_msgport, 0, ipfw_init_dispatch); - return lwkt_domsg(IPFW_CFGPORT, &smsg.nm_lmsg, 0); + return lwkt_domsg(IPFW_CFGPORT, &smsg.lmsg, 0); } #ifdef KLD_MODULE static void -ipfw_fini_dispatch(struct netmsg *nmsg) +ipfw_fini_dispatch(netmsg_t nmsg) { int error = 0, cpu; @@ -4483,11 +4483,11 @@ ipfw_fini_dispatch(struct netmsg *nmsg) netmsg_service_sync(); crit_enter(); - if ((ipfw_timeout_netmsg.nm_lmsg.ms_flags & MSGF_DONE) == 0) { + if ((ipfw_timeout_netmsg.lmsg.ms_flags & MSGF_DONE) == 0) { /* * Callout message is pending; drop it */ - lwkt_dropmsg(&ipfw_timeout_netmsg.nm_lmsg); + lwkt_dropmsg(&ipfw_timeout_netmsg.lmsg); } crit_exit(); @@ -4502,17 +4502,17 @@ ipfw_fini_dispatch(struct netmsg *nmsg) kprintf("IP firewall unloaded\n"); reply: - lwkt_replymsg(&nmsg->nm_lmsg, error); + lwkt_replymsg(&nmsg->lmsg, error); } static int ipfw_fini(void) { - struct netmsg smsg; + struct netmsg_base smsg; netmsg_init(&smsg, NULL, &curthread->td_msgport, 0, ipfw_fini_dispatch); - return lwkt_domsg(IPFW_CFGPORT, &smsg.nm_lmsg, 0); + return lwkt_domsg(IPFW_CFGPORT, &smsg.lmsg, 0); } #endif /* KLD_MODULE */ diff --git a/sys/net/ipfw/ip_fw2_glue.c b/sys/net/ipfw/ip_fw2_glue.c index 3a1c9472d2..13c48c5e16 100644 --- a/sys/net/ipfw/ip_fw2_glue.c +++ b/sys/net/ipfw/ip_fw2_glue.c @@ -51,12 +51,12 @@ int ip_fw_loaded; int fw_enable = 1; int fw_one_pass = 1; -static void ip_fw_sockopt_dispatch(struct netmsg *); +static void ip_fw_sockopt_dispatch(netmsg_t msg); int ip_fw_sockopt(struct sockopt *sopt) { - struct netmsg smsg; + struct netmsg_base smsg; /* * Disallow modifications in really-really secure mode, but still allow @@ -70,15 +70,14 @@ ip_fw_sockopt(struct sockopt *sopt) netmsg_init(&smsg, NULL, &curthread->td_msgport, 0, ip_fw_sockopt_dispatch); - smsg.nm_lmsg.u.ms_resultp = sopt; - return lwkt_domsg(IPFW_CFGPORT, &smsg.nm_lmsg, 0); + smsg.lmsg.u.ms_resultp = sopt; + return lwkt_domsg(IPFW_CFGPORT, &smsg.lmsg, 0); } static void -ip_fw_sockopt_dispatch(struct netmsg *nmsg) +ip_fw_sockopt_dispatch(netmsg_t msg) { - struct lwkt_msg *msg = &nmsg->nm_lmsg; - struct sockopt *sopt = msg->u.ms_resultp; + struct sockopt *sopt = msg->lmsg.u.ms_resultp; int error; KKASSERT(mycpuid == 0); @@ -87,5 +86,5 @@ ip_fw_sockopt_dispatch(struct netmsg *nmsg) error = ip_fw_ctl_ptr(sopt); else error = ENOPROTOOPT; - lwkt_replymsg(msg, error); + lwkt_replymsg(&msg->lmsg, error); } diff --git a/sys/net/netisr.c b/sys/net/netisr.c index 7c0771acf5..911aba6366 100644 --- a/sys/net/netisr.c +++ b/sys/net/netisr.c @@ -58,7 +58,7 @@ #include #include -static void netmsg_sync_func(struct netmsg *msg); +static void netmsg_sync_func(netmsg_t msg); static void netmsg_service_loop(void *arg); static void cpu0_cpufn(struct mbuf **mp, int hoff); @@ -107,18 +107,17 @@ netisr_autofree_reply(lwkt_port_t port, lwkt_msg_t msg) * synchronously, effectively turning the message into a glorified direct * procedure call back into the protocol stack. The operation must be * complete on return or we will deadlock, so panic if it isn't. + * + * However, the target function is under no obligation to immediately + * reply the message. It may forward it elsewhere. */ static int netmsg_put_port(lwkt_port_t port, lwkt_msg_t lmsg) { - netmsg_t netmsg = (void *)lmsg; + netmsg_base_t nmsg = (void *)lmsg; if ((lmsg->ms_flags & MSGF_SYNC) && port == &curthread->td_msgport) { - netmsg->nm_dispatch(netmsg); - if ((lmsg->ms_flags & MSGF_DONE) == 0) { - panic("netmsg_put_port: self-referential " - "deadlock on netport"); - } + nmsg->nm_dispatch((netmsg_t)nmsg); return(EASYNC); } else { return(netmsg_fwd_port_fn(port, lmsg)); @@ -138,12 +137,12 @@ netmsg_put_port(lwkt_port_t port, lwkt_msg_t lmsg) static int netmsg_sync_putport(lwkt_port_t port, lwkt_msg_t lmsg) { - netmsg_t netmsg = (void *)lmsg; + netmsg_base_t nmsg = (void *)lmsg; KKASSERT((lmsg->ms_flags & MSGF_DONE) == 0); lmsg->ms_target_port = port; /* required for abort */ - netmsg->nm_dispatch(netmsg); + nmsg->nm_dispatch((netmsg_t)nmsg); return(EASYNC); } @@ -227,12 +226,12 @@ void netmsg_service_sync(void) { struct netmsg_port_registration *reg; - struct netmsg smsg; + struct netmsg_base smsg; netmsg_init(&smsg, NULL, &curthread->td_msgport, 0, netmsg_sync_func); TAILQ_FOREACH(reg, &netreglist, npr_entry) { - lwkt_domsg(reg->npr_port, &smsg.nm_lmsg, 0); + lwkt_domsg(reg->npr_port, &smsg.lmsg, 0); } } @@ -241,9 +240,9 @@ netmsg_service_sync(void) * EASYNC to be returned if the netmsg function disposes of the message. */ static void -netmsg_sync_func(struct netmsg *msg) +netmsg_sync_func(netmsg_t msg) { - lwkt_replymsg(&msg->nm_lmsg, 0); + lwkt_replymsg(&msg->lmsg, 0); } /* @@ -254,7 +253,7 @@ static void netmsg_service_loop(void *arg) { struct netmsg_rollup *ru; - struct netmsg *msg; + netmsg_base_t msg; thread_t td = curthread;; int limit; @@ -266,7 +265,7 @@ netmsg_service_loop(void *arg) do { KASSERT(msg->nm_dispatch != NULL, ("netmsg_service isr %d badmsg\n", - msg->nm_lmsg.u.ms_result)); + msg->lmsg.u.ms_result)); if (msg->nm_so && msg->nm_so->so_port != &td->td_msgport) { /* @@ -277,12 +276,12 @@ netmsg_service_loop(void *arg) kprintf("netmsg_service_loop: Warning, " "port changed so=%p\n", msg->nm_so); lwkt_forwardmsg(msg->nm_so->so_port, - &msg->nm_lmsg); + &msg->lmsg); } else { /* * We are on the correct port, dispatch it. */ - msg->nm_dispatch(msg); + msg->nm_dispatch((netmsg_t)msg); } if (--limit == 0) break; @@ -347,11 +346,11 @@ netisr_queue(int num, struct mbuf *m) */ port = cpu_portfn(m->m_pkthdr.hash); pmsg = &m->m_hdr.mh_netmsg; - netmsg_init(&pmsg->nm_netmsg, NULL, &netisr_apanic_rport, + netmsg_init(&pmsg->base, NULL, &netisr_apanic_rport, 0, ni->ni_handler); pmsg->nm_packet = m; - pmsg->nm_netmsg.nm_lmsg.u.ms_result = num; - lwkt_sendmsg(port, &pmsg->nm_netmsg.nm_lmsg); + pmsg->base.lmsg.u.ms_result = num; + lwkt_sendmsg(port, &pmsg->base.lmsg); return (0); } @@ -455,16 +454,6 @@ cur_netport(void) return(cpu_portfn(mycpu->gd_cpuid)); } -/* - * Return a default protocol mbuf processing thread port - */ -lwkt_port_t -cpu0_soport(struct socket *so __unused, struct sockaddr *nam __unused, - struct mbuf **dummy __unused) -{ - return (&netisr_cpu[0].td_msgport); -} - /* * Return a default protocol control message processing thread port */ @@ -475,17 +464,6 @@ cpu0_ctlport(int cmd __unused, struct sockaddr *sa __unused, return (&netisr_cpu[0].td_msgport); } -/* - * This is a dummy port that causes a message to be executed synchronously - * instead of being queued to a port. - */ -lwkt_port_t -sync_soport(struct socket *so __unused, struct sockaddr *nam __unused, - struct mbuf **dummy __unused) -{ - return (&netisr_sync_port); -} - /* * This is a default netisr packet characterization function which * sets M_HASH. If a netisr is registered with a NULL cpufn function @@ -520,13 +498,13 @@ schednetisr_remote(void *data) int num = (int)(intptr_t)data; struct netisr *ni = &netisrs[num]; lwkt_port_t port = &netisr_cpu[0].td_msgport; - struct netmsg *pmsg; + netmsg_base_t pmsg; pmsg = &netisrs[num].ni_netmsg; - if (pmsg->nm_lmsg.ms_flags & MSGF_DONE) { + if (pmsg->lmsg.ms_flags & MSGF_DONE) { netmsg_init(pmsg, NULL, &netisr_adone_rport, 0, ni->ni_handler); - pmsg->nm_lmsg.u.ms_result = num; - lwkt_sendmsg(port, &pmsg->nm_lmsg); + pmsg->lmsg.u.ms_result = num; + lwkt_sendmsg(port, &pmsg->lmsg); } } diff --git a/sys/net/netisr.h b/sys/net/netisr.h index 9a90419fee..4d897d9f9e 100644 --- a/sys/net/netisr.h +++ b/sys/net/netisr.h @@ -122,73 +122,10 @@ #include #endif -TAILQ_HEAD(notifymsglist, netmsg_so_notify); - -typedef __boolean_t (*msg_predicate_fn_t)(struct netmsg *); - -/* - * Base class. All net messages must start with the same fields. - */ - -struct netmsg_packet { - struct netmsg nm_netmsg; - struct mbuf *nm_packet; - int nm_nxt; -}; - -struct netmsg_pr_timeout { - struct netmsg nm_netmsg; - int (*nm_prfn) (void); -}; - -struct netmsg_so_notify { - struct netmsg nm_netmsg; - msg_predicate_fn_t nm_predicate; - struct socket *nm_so; - int nm_fflags; /* flags e.g. FNONBLOCK */ - int nm_etype; /* receive or send event */ - TAILQ_ENTRY(netmsg_so_notify) nm_list; -}; - -struct netmsg_so_notify_abort { - struct netmsg nm_netmsg; - struct netmsg_so_notify *nm_notifymsg; -}; - -#define NM_REVENT 0x1 /* event on receive buffer */ -#define NM_SEVENT 0x2 /* event on send buffer */ - #endif #ifdef _KERNEL -/* - * for dispatching pr_ functions, - * until they can be converted to message-passing - */ -void netmsg_pru_abort(netmsg_t); -void netmsg_pru_accept(netmsg_t); -void netmsg_pru_attach(netmsg_t); -void netmsg_pru_bind(netmsg_t); -void netmsg_pru_connect(netmsg_t); -void netmsg_pru_connect2(netmsg_t); -void netmsg_pru_control(netmsg_t); -void netmsg_pru_detach(netmsg_t); -void netmsg_pru_disconnect(netmsg_t); -void netmsg_pru_listen(netmsg_t); -void netmsg_pru_peeraddr(netmsg_t); -void netmsg_pru_rcvd(netmsg_t); -void netmsg_pru_rcvoob(netmsg_t); -void netmsg_pru_send(netmsg_t); -void netmsg_pru_sense(netmsg_t); -void netmsg_pru_shutdown(netmsg_t); -void netmsg_pru_sockaddr(netmsg_t); - -void netmsg_pru_ctloutput(netmsg_t); -void netmsg_pru_ctlinput(netmsg_t); - -void netmsg_pr_timeout(netmsg_t); - void netmsg_so_notify(netmsg_t); void netmsg_so_notify_abort(netmsg_t); void netmsg_so_notify_doabort(lwkt_msg_t); @@ -216,7 +153,7 @@ struct netisr { netisr_fn_t ni_handler; /* packet handler function */ netisr_ru_t ni_rufunc; /* rollup function */ netisr_cpufn_t ni_cpufn; /* characterize pkt return cpu */ - struct netmsg ni_netmsg; /* for sched_netisr() (no-data) */ + struct netmsg_base ni_netmsg; /* for sched_netisr() (no-data) */ }; #endif @@ -229,6 +166,7 @@ struct netisr { extern lwkt_port netisr_adone_rport; extern lwkt_port netisr_afree_rport; extern lwkt_port netisr_apanic_rport; +extern lwkt_port netisr_sync_port; lwkt_port_t cpu_portfn(int cpu); lwkt_port_t cur_netport(void); diff --git a/sys/net/netmsg.h b/sys/net/netmsg.h index 328f2d0ff7..5e68985656 100644 --- a/sys/net/netmsg.h +++ b/sys/net/netmsg.h @@ -40,68 +40,106 @@ #include #endif -struct netmsg; - -typedef void (*netisr_fn_t)(struct netmsg *); +typedef void (*netisr_fn_t)(netmsg_t); typedef void (*netisr_ru_t)(void); typedef void (*netisr_cpufn_t)(struct mbuf **, int); +#if defined(_KERNEL) || defined(_KERNEL_STRUCTURES) + /* - * Base netmsg + * The base netmsg prefixes all netmsgs and includes an embedded LWKT + * message. */ -typedef struct netmsg { - struct lwkt_msg nm_lmsg; +struct netmsg_base { + struct lwkt_msg lmsg; netisr_fn_t nm_dispatch; struct socket *nm_so; -} *netmsg_t; +}; -#if defined(_KERNEL) || defined(_KERNEL_STRUCTURES) +typedef struct netmsg_base *netmsg_base_t; + +/* + * NETISR messages + * + * NOTE: netmsg_packet is embedded in mbufs. + */ +TAILQ_HEAD(notifymsglist, netmsg_so_notify); + +struct netmsg_packet { + struct netmsg_base base; + struct mbuf *nm_packet; + int nm_nxt; +}; + +struct netmsg_pr_timeout { + struct netmsg_base base; +}; + +struct netmsg_so_notify; +typedef __boolean_t (*msg_predicate_fn_t)(struct netmsg_so_notify *); + +struct netmsg_so_notify { + struct netmsg_base base; + msg_predicate_fn_t nm_predicate; + int nm_fflags; /* flags e.g. FNONBLOCK */ + int nm_etype; /* receive or send event */ + TAILQ_ENTRY(netmsg_so_notify) nm_list; +}; + +struct netmsg_so_notify_abort { + struct netmsg_base base; + struct netmsg_so_notify *nm_notifymsg; +}; + +#define NM_REVENT 0x1 /* event on receive buffer */ +#define NM_SEVENT 0x2 /* event on send buffer */ /* * User protocol requests messages. */ struct netmsg_pru_abort { - struct netmsg nm_netmsg; - pru_abort_fn_t nm_prufn; + struct netmsg_base base; }; struct netmsg_pru_accept { - struct netmsg nm_netmsg; - pru_accept_fn_t nm_prufn; + struct netmsg_base base; struct sockaddr **nm_nam; }; struct netmsg_pru_attach { - struct netmsg nm_netmsg; - pru_attach_fn_t nm_prufn; + struct netmsg_base base; int nm_proto; struct pru_attach_info *nm_ai; }; struct netmsg_pru_bind { - struct netmsg nm_netmsg; - pru_bind_fn_t nm_prufn; + struct netmsg_base base; struct sockaddr *nm_nam; struct thread *nm_td; }; struct netmsg_pru_connect { - struct netmsg nm_netmsg; - pru_connect_fn_t nm_prufn; + struct netmsg_base base; struct sockaddr *nm_nam; struct thread *nm_td; + struct mbuf *nm_m; /* connect with send */ + int nm_flags; /* connect with send */ + int nm_reconnect; /* message control */ }; +#define NMSG_RECONNECT_RECONNECT 0x0001 /* thread port change */ +#define NMSG_RECONNECT_NAMALLOC 0x0002 /* nm_nam allocated */ +#define NMSG_RECONNECT_PUSH 0x0004 /* call tcp_output */ +#define NMSG_RECONNECT_FALLBACK 0x0008 /* fallback to ipv4 */ + struct netmsg_pru_connect2 { - struct netmsg nm_netmsg; - pru_connect2_fn_t nm_prufn; + struct netmsg_base base; struct socket *nm_so1; struct socket *nm_so2; }; struct netmsg_pru_control { - struct netmsg nm_netmsg; - pru_control_fn_t nm_prufn; + struct netmsg_base base; u_long nm_cmd; caddr_t nm_data; struct ifnet *nm_ifp; @@ -109,70 +147,70 @@ struct netmsg_pru_control { }; struct netmsg_pru_detach { - struct netmsg nm_netmsg; - pru_detach_fn_t nm_prufn; + struct netmsg_base base; }; struct netmsg_pru_disconnect { - struct netmsg nm_netmsg; - pru_disconnect_fn_t nm_prufn; + struct netmsg_base base; }; struct netmsg_pru_listen { - struct netmsg nm_netmsg; - pru_listen_fn_t nm_prufn; + struct netmsg_base base; struct thread *nm_td; }; struct netmsg_pru_peeraddr { - struct netmsg nm_netmsg; - pru_peeraddr_fn_t nm_prufn; + struct netmsg_base base; struct sockaddr **nm_nam; }; struct netmsg_pru_rcvd { - struct netmsg nm_netmsg; - pru_rcvd_fn_t nm_prufn; + struct netmsg_base base; int nm_flags; }; struct netmsg_pru_rcvoob { - struct netmsg nm_netmsg; - pru_rcvoob_fn_t nm_prufn; + struct netmsg_base base; struct mbuf *nm_m; int nm_flags; }; struct netmsg_pru_send { - struct netmsg nm_netmsg; - pru_send_fn_t nm_prufn; - int nm_flags; + struct netmsg_base base; + int nm_flags; /* PRUS_xxx */ struct mbuf *nm_m; struct sockaddr *nm_addr; struct mbuf *nm_control; struct thread *nm_td; + /* + * XXX hack to be 100% certain netmsg_pru_send can be overwritten + * by netmsg_pru_connect + */ + char nm_dummy[sizeof(struct netmsg_pru_connect) - + sizeof(struct netmsg_base)]; }; +#define PRUS_OOB 0x1 +#define PRUS_EOF 0x2 +#define PRUS_MORETOCOME 0x4 +#define PRUS_NAMALLOC 0x8 + struct netmsg_pru_sense { - struct netmsg nm_netmsg; - pru_sense_fn_t nm_prufn; + struct netmsg_base base; struct stat *nm_stat; }; struct netmsg_pru_shutdown { - struct netmsg nm_netmsg; - pru_shutdown_fn_t nm_prufn; + struct netmsg_base base; }; struct netmsg_pru_sockaddr { - struct netmsg nm_netmsg; - pru_sockaddr_fn_t nm_prufn; + struct netmsg_base base; struct sockaddr **nm_nam; }; struct netmsg_pru_sosend { - struct netmsg nm_netmsg; - pru_sosend_fn_t nm_prufn; + struct netmsg_base base; struct sockaddr *nm_addr; struct uio *nm_uio; struct mbuf *nm_top; @@ -182,7 +220,7 @@ struct netmsg_pru_sosend { }; struct netmsg_pru_soreceive { - struct netmsg nm_netmsg; + struct netmsg_base base; struct sockaddr *nm_addr; struct sockaddr **nm_paddr; struct uio *nm_uio; @@ -191,20 +229,56 @@ struct netmsg_pru_soreceive { int *nm_flagsp; }; -struct netmsg_pru_ctloutput { - struct netmsg nm_netmsg; - pru_ctloutput_fn_t nm_prufn; +struct netmsg_pr_ctloutput { + struct netmsg_base base; struct sockopt *nm_sopt; }; struct netmsg_pru_ctlinput { - struct netmsg nm_netmsg; - pru_ctlinput_fn_t nm_prufn; + struct netmsg_base base; int nm_cmd; struct sockaddr *nm_arg; void *nm_extra; }; +/* + * Union of all possible netmsgs. Note that when a netmsg is sent the + * actual allocated storage is likely only the size of the particular + * class of message, and not sizeof(union netmsg). + */ +union netmsg { + struct lwkt_msg lmsg; /* base embedded */ + struct netmsg_base base; /* base embedded */ + + struct netmsg_packet packet; /* mbuf embedded */ + struct netmsg_pr_timeout timeout; + struct netmsg_so_notify notify; + struct netmsg_so_notify_abort notify_abort; + + struct netmsg_pr_ctloutput ctloutput; + + struct netmsg_pru_abort abort; + struct netmsg_pru_accept accept; /* synchronous */ + struct netmsg_pru_attach attach; + struct netmsg_pru_bind bind; + struct netmsg_pru_connect connect; + struct netmsg_pru_connect2 connect2; + struct netmsg_pru_control control; /* synchronous */ + struct netmsg_pru_detach detach; + struct netmsg_pru_disconnect disconnect; + struct netmsg_pru_listen listen; + struct netmsg_pru_peeraddr peeraddr; + struct netmsg_pru_rcvd rcvd; + struct netmsg_pru_rcvoob rcvoob; + struct netmsg_pru_send send; + struct netmsg_pru_sense sense; + struct netmsg_pru_shutdown shutdown; + struct netmsg_pru_sockaddr sockaddr; + struct netmsg_pru_sosend sosend; /* synchronous */ + struct netmsg_pru_soreceive soreceive; /* synchronous */ + struct netmsg_pru_ctlinput ctlinput; +}; + #endif /* _KERNEL || _KERNEL_STRUCTURES */ #endif /* !_NET_NETMSG_H_ */ diff --git a/sys/net/netmsg2.h b/sys/net/netmsg2.h index da5299b1fe..c951a13248 100644 --- a/sys/net/netmsg2.h +++ b/sys/net/netmsg2.h @@ -46,20 +46,20 @@ * dispatch function. */ static __inline void -netmsg_init(netmsg_t msg, struct socket *so, lwkt_port_t rport, +netmsg_init(netmsg_base_t msg, struct socket *so, lwkt_port_t rport, int flags, netisr_fn_t dispatch) { - lwkt_initmsg(&msg->nm_lmsg, rport, flags); + lwkt_initmsg(&msg->lmsg, rport, flags); msg->nm_dispatch = dispatch; msg->nm_so = so; } static __inline void -netmsg_init_abortable(netmsg_t msg, struct socket *so, lwkt_port_t rport, +netmsg_init_abortable(netmsg_base_t msg, struct socket *so, lwkt_port_t rport, int flags, netisr_fn_t dispatch, void (*abortfn)(lwkt_msg_t)) { - lwkt_initmsg_abortable(&msg->nm_lmsg, rport, flags, abortfn); + lwkt_initmsg_abortable(&msg->lmsg, rport, flags, abortfn); msg->nm_dispatch = dispatch; msg->nm_so = so; } diff --git a/sys/net/pf/pf.c b/sys/net/pf/pf.c index ac0d484d5d..7df9f772c2 100644 --- a/sys/net/pf/pf.c +++ b/sys/net/pf/pf.c @@ -2629,7 +2629,7 @@ pf_get_translation(struct pf_pdesc *pd, struct mbuf *m, int off, int direction, #ifdef SMP struct netmsg_hashlookup { - struct netmsg nm_netmsg; + struct netmsg_base base; struct inpcb **nm_pinp; struct inpcbinfo *nm_pcbinfo; struct pf_addr *nm_saddr; @@ -2640,21 +2640,21 @@ struct netmsg_hashlookup { }; static void -in_pcblookup_hash_handler(struct netmsg *msg0) +in_pcblookup_hash_handler(netmsg_t msg) { - struct netmsg_hashlookup *msg = (struct netmsg_hashlookup *)msg0; + struct netmsg_hashlookup *rmsg = (struct netmsg_hashlookup *)msg; - if (msg->nm_af == AF_INET) - *msg->nm_pinp = in_pcblookup_hash(msg->nm_pcbinfo, - msg->nm_saddr->v4, msg->nm_sport, msg->nm_daddr->v4, - msg->nm_dport, INPLOOKUP_WILDCARD, NULL); + if (rmsg->nm_af == AF_INET) + *rmsg->nm_pinp = in_pcblookup_hash(rmsg->nm_pcbinfo, + rmsg->nm_saddr->v4, rmsg->nm_sport, rmsg->nm_daddr->v4, + rmsg->nm_dport, INPLOOKUP_WILDCARD, NULL); #ifdef INET6 else - *msg->nm_pinp = in6_pcblookup_hash(msg->nm_pcbinfo, - &msg->nm_saddr->v6, msg->nm_sport, &msg->nm_daddr->v6, - msg->nm_dport, INPLOOKUP_WILDCARD, NULL); + *rmsg->nm_pinp = in6_pcblookup_hash(rmsg->nm_pcbinfo, + &rmsg->nm_saddr->v6, rmsg->nm_sport, &rmsg->nm_daddr->v6, + rmsg->nm_dport, INPLOOKUP_WILDCARD, NULL); #endif /* INET6 */ - lwkt_replymsg(&msg->nm_netmsg.nm_lmsg, 0); + lwkt_replymsg(&rmsg->base.lmsg, 0); } #endif /* SMP */ @@ -2704,7 +2704,7 @@ pf_socket_lookup(int direction, struct pf_pdesc *pd) */ if (pi_cpu != mycpu->gd_cpuid) { msg = kmalloc(sizeof(*msg), M_LWKTMSG, M_INTWAIT); - netmsg_init(&msg->nm_netmsg, NULL, &netisr_afree_rport, + netmsg_init(&msg->base, NULL, &netisr_afree_rport, 0, in_pcblookup_hash_handler); msg->nm_pinp = &inp; msg->nm_pcbinfo = pi; @@ -2762,7 +2762,7 @@ pf_socket_lookup(int direction, struct pf_pdesc *pd) #ifdef SMP if (msg != NULL) { lwkt_domsg(cpu_portfn(pi_cpu), - &msg->nm_netmsg.nm_lmsg, 0); + &msg->base.lmsg, 0); } else #endif /* SMP */ { diff --git a/sys/net/pfil.c b/sys/net/pfil.c index 4dbc9c0e76..d45b50538d 100644 --- a/sys/net/pfil.c +++ b/sys/net/pfil.c @@ -69,7 +69,7 @@ struct packet_filter_hook { }; struct netmsg_pfil { - struct netmsg pfil_nmsg; + struct netmsg_base base; pfil_func_t pfil_func; void *pfil_arg; int pfil_flags; @@ -88,8 +88,8 @@ static struct packet_filter_hook * pfil_list_find(const pfil_list_t *, pfil_func_t, const void *); -static void pfil_remove_hook_dispatch(struct netmsg *); -static void pfil_add_hook_dispatch(struct netmsg *); +static void pfil_remove_hook_dispatch(netmsg_t); +static void pfil_add_hook_dispatch(netmsg_t); /* * pfil_run_hooks() runs the specified packet filter hooks. @@ -176,7 +176,7 @@ pfil_head_get(int type, u_long val) } static void -pfil_add_hook_dispatch(struct netmsg *nmsg) +pfil_add_hook_dispatch(netmsg_t nmsg) { struct netmsg_pfil *pfilmsg = (struct netmsg_pfil *)nmsg; pfil_func_t func = pfilmsg->pfil_func; @@ -252,7 +252,7 @@ pfil_add_hook_dispatch(struct netmsg *nmsg) if (old_list_out != NULL) pfil_list_free(old_list_out); reply: - lwkt_replymsg(&nmsg->nm_lmsg, err); + lwkt_replymsg(&nmsg->base.lmsg, err); } /* @@ -267,9 +267,10 @@ int pfil_add_hook(pfil_func_t func, void *arg, int flags, struct pfil_head *ph) { struct netmsg_pfil pfilmsg; - struct netmsg *nmsg; + netmsg_base_t nmsg; + int error; - nmsg = &pfilmsg.pfil_nmsg; + nmsg = &pfilmsg.base; netmsg_init(nmsg, NULL, &curthread->td_msgport, 0, pfil_add_hook_dispatch); pfilmsg.pfil_func = func; @@ -277,11 +278,12 @@ pfil_add_hook(pfil_func_t func, void *arg, int flags, struct pfil_head *ph) pfilmsg.pfil_flags = flags; pfilmsg.pfil_ph = ph; - return lwkt_domsg(PFIL_CFGPORT, &nmsg->nm_lmsg, 0); + error = lwkt_domsg(PFIL_CFGPORT, &nmsg->lmsg, 0); + return error; } static void -pfil_remove_hook_dispatch(struct netmsg *nmsg) +pfil_remove_hook_dispatch(netmsg_t nmsg) { struct netmsg_pfil *pfilmsg = (struct netmsg_pfil *)nmsg; pfil_func_t func = pfilmsg->pfil_func; @@ -358,7 +360,7 @@ pfil_remove_hook_dispatch(struct netmsg *nmsg) if (old_list_out != NULL) pfil_list_free(old_list_out); reply: - lwkt_replymsg(&nmsg->nm_lmsg, err); + lwkt_replymsg(&nmsg->base.lmsg, err); } /* @@ -369,9 +371,9 @@ int pfil_remove_hook(pfil_func_t func, void *arg, int flags, struct pfil_head *ph) { struct netmsg_pfil pfilmsg; - struct netmsg *nmsg; + netmsg_base_t nmsg; - nmsg = &pfilmsg.pfil_nmsg; + nmsg = &pfilmsg.base; netmsg_init(nmsg, NULL, &curthread->td_msgport, 0, pfil_remove_hook_dispatch); pfilmsg.pfil_func = func; @@ -379,7 +381,7 @@ pfil_remove_hook(pfil_func_t func, void *arg, int flags, struct pfil_head *ph) pfilmsg.pfil_flags = flags; pfilmsg.pfil_ph = ph; - return lwkt_domsg(PFIL_CFGPORT, &nmsg->nm_lmsg, 0); + return lwkt_domsg(PFIL_CFGPORT, &nmsg->lmsg, 0); } static void diff --git a/sys/net/ppp/if_ppp.c b/sys/net/ppp/if_ppp.c index 94fc7512f9..9590a247d8 100644 --- a/sys/net/ppp/if_ppp.c +++ b/sys/net/ppp/if_ppp.c @@ -199,7 +199,7 @@ static struct compressor *ppp_compressors[8] = { * Software interrupt routine, called at spl[soft]net. */ static void -pppintr(struct netmsg *msg) +pppintr(netmsg_t msg) { struct mbuf *m; struct ppp_softc *sc; @@ -210,7 +210,7 @@ pppintr(struct netmsg *msg) * be replied. Interlock processing and notification by replying * the message first. */ - lwkt_replymsg(&msg->nm_lmsg, 0); + lwkt_replymsg(&msg->lmsg, 0); get_mplock(); diff --git a/sys/net/raw_cb.h b/sys/net/raw_cb.h index 50fc11305f..a2c6ea1fa4 100644 --- a/sys/net/raw_cb.h +++ b/sys/net/raw_cb.h @@ -74,8 +74,10 @@ struct rawcb { #ifdef _KERNEL extern LIST_HEAD(rawcb_list_head, rawcb) rawcb_list; +union netmsg; + int raw_attach (struct socket *, int, struct rlimit *); -void raw_ctlinput (int, struct sockaddr *, void *); +void raw_ctlinput (union netmsg *); void raw_detach (struct rawcb *); void raw_disconnect (struct rawcb *); void raw_init (void); diff --git a/sys/net/raw_usrreq.c b/sys/net/raw_usrreq.c index cfc7f30483..19f6f39eab 100644 --- a/sys/net/raw_usrreq.c +++ b/sys/net/raw_usrreq.c @@ -45,6 +45,7 @@ #include #include +#include #include @@ -135,118 +136,145 @@ raw_input(struct mbuf *m0, const struct sockproto *proto, lwkt_reltoken(&raw_token); } -/*ARGSUSED*/ +/* + * nm_cmd, nm_arg, nm_extra + */ void -raw_ctlinput(int cmd, struct sockaddr *arg, void *dummy) +raw_ctlinput(netmsg_t msg) { + int error = 0; - if (cmd < 0 || cmd > PRC_NCMDS) - return; - /* INCOMPLETE */ + if (msg->ctlinput.nm_cmd < 0 || msg->ctlinput.nm_cmd > PRC_NCMDS) + ; + lwkt_replymsg(&msg->lmsg, error); } /* * NOTE: (so) is referenced from soabort*() and netmsg_pru_abort() * will sofree() it when we return. */ -static int -raw_uabort(struct socket *so) +static void +raw_uabort(netmsg_t msg) { - struct rawcb *rp = sotorawcb(so); + struct rawcb *rp = sotorawcb(msg->base.nm_so); + int error; - if (rp == NULL) - return EINVAL; - raw_disconnect(rp); - soisdisconnected(so); - return 0; + if (rp) { + raw_disconnect(rp); + soisdisconnected(msg->base.nm_so); + error = 0; + } else { + error = EINVAL; + } + lwkt_replymsg(&msg->lmsg, error); } /* pru_accept is EOPNOTSUPP */ -static int -raw_uattach(struct socket *so, int proto, struct pru_attach_info *ai) +static void +raw_uattach(netmsg_t msg) { - struct rawcb *rp = sotorawcb(so); + struct socket *so = msg->base.nm_so; + int proto = msg->attach.nm_proto; + struct pru_attach_info *ai = msg->attach.nm_ai; + struct rawcb *rp; int error; - if (rp == NULL) - return EINVAL; - if ((error = priv_check_cred(ai->p_ucred, PRIV_ROOT, NULL_CRED_OKAY)) != 0) - return error; - return raw_attach(so, proto, ai->sb_rlimit); + rp = sotorawcb(so); + if (rp) { + error = priv_check_cred(ai->p_ucred, PRIV_ROOT, NULL_CRED_OKAY); + if (error == 0) + error = raw_attach(so, proto, ai->sb_rlimit); + } else { + error = EINVAL; + } + lwkt_replymsg(&msg->lmsg, error); } -static int -raw_ubind(struct socket *so, struct sockaddr *nam, struct thread *td) +static void +raw_ubind(netmsg_t msg) { - return EINVAL; + lwkt_replymsg(&msg->lmsg, EINVAL); } -static int -raw_uconnect(struct socket *so, struct sockaddr *nam, struct thread *td) +static void +raw_uconnect(netmsg_t msg) { - return EINVAL; + lwkt_replymsg(&msg->lmsg, EINVAL); } /* pru_connect2 is EOPNOTSUPP */ /* pru_control is EOPNOTSUPP */ -static int -raw_udetach(struct socket *so) +static void +raw_udetach(netmsg_t msg) { - struct rawcb *rp = sotorawcb(so); - - if (rp == NULL) - return EINVAL; + struct rawcb *rp = sotorawcb(msg->base.nm_so); + int error; - raw_detach(rp); - return 0; + if (rp) { + raw_detach(rp); + error = 0; + } else { + error = EINVAL; + } + lwkt_replymsg(&msg->lmsg, error); } -static int -raw_udisconnect(struct socket *so) +static void +raw_udisconnect(netmsg_t msg) { - struct rawcb *rp = sotorawcb(so); + struct socket *so = msg->base.nm_so; + struct rawcb *rp; + int error; - if (rp == NULL) - return EINVAL; - if (rp->rcb_faddr == NULL) { - return ENOTCONN; + rp = sotorawcb(so); + if (rp == NULL) { + error = EINVAL; + } else if (rp->rcb_faddr == NULL) { + error = ENOTCONN; + } else { + soreference(so); + raw_disconnect(rp); + soisdisconnected(so); + sofree(so); + error = 0; } - soreference(so); - raw_disconnect(rp); - soisdisconnected(so); - sofree(so); - - return 0; + lwkt_replymsg(&msg->lmsg, error); } /* pru_listen is EOPNOTSUPP */ -static int -raw_upeeraddr(struct socket *so, struct sockaddr **nam) +static void +raw_upeeraddr(netmsg_t msg) { - struct rawcb *rp = sotorawcb(so); + struct rawcb *rp = sotorawcb(msg->base.nm_so); + int error; - if (rp == NULL) - return EINVAL; - if (rp->rcb_faddr == NULL) { - return ENOTCONN; + if (rp == NULL) { + error = EINVAL; + } else if (rp->rcb_faddr == NULL) { + error = ENOTCONN; + } else { + *msg->peeraddr.nm_nam = dup_sockaddr(rp->rcb_faddr); + error = 0; } - *nam = dup_sockaddr(rp->rcb_faddr); - return 0; + lwkt_replymsg(&msg->lmsg, error); } /* pru_rcvd is EOPNOTSUPP */ /* pru_rcvoob is EOPNOTSUPP */ -static int -raw_usend(struct socket *so, int flags, struct mbuf *m, - struct sockaddr *nam, struct mbuf *control, struct thread *td) +static void +raw_usend(netmsg_t msg) { - int error; + struct socket *so = msg->base.nm_so; + struct mbuf *m = msg->send.nm_m; + struct mbuf *control = msg->send.nm_control; struct rawcb *rp = sotorawcb(so); struct pr_output_info oi; + int flags = msg->send.nm_flags; + int error; if (rp == NULL) { error = EINVAL; @@ -262,67 +290,75 @@ raw_usend(struct socket *so, int flags, struct mbuf *m, error = EOPNOTSUPP; goto release; } - if (nam) { + if (msg->send.nm_addr) { if (rp->rcb_faddr) { error = EISCONN; goto release; } - rp->rcb_faddr = nam; + rp->rcb_faddr = msg->send.nm_addr; } else if (rp->rcb_faddr == NULL) { error = ENOTCONN; goto release; } - oi.p_pid = td->td_proc->p_pid; + oi.p_pid = msg->send.nm_td->td_proc->p_pid; error = (*so->so_proto->pr_output)(m, so, &oi); m = NULL; - if (nam) + if (msg->send.nm_addr) rp->rcb_faddr = NULL; release: if (m != NULL) m_freem(m); - return (error); + lwkt_replymsg(&msg->lmsg, error); } /* pru_sense is null */ -static int -raw_ushutdown(struct socket *so) +static void +raw_ushutdown(netmsg_t msg) { - struct rawcb *rp = sotorawcb(so); + struct rawcb *rp = sotorawcb(msg->base.nm_so); + int error; - if (rp == NULL) - return EINVAL; - socantsendmore(so); - return 0; + if (rp) { + socantsendmore(msg->base.nm_so); + error = 0; + } else { + error = EINVAL; + } + lwkt_replymsg(&msg->lmsg, error); } -static int -raw_usockaddr(struct socket *so, struct sockaddr **nam) +static void +raw_usockaddr(netmsg_t msg) { - struct rawcb *rp = sotorawcb(so); + struct rawcb *rp = sotorawcb(msg->base.nm_so); + int error; - if (rp == NULL) - return EINVAL; - if (rp->rcb_laddr == NULL) - return EINVAL; - *nam = dup_sockaddr(rp->rcb_laddr); - return 0; + if (rp == NULL) { + error = EINVAL; + } else if (rp->rcb_laddr == NULL) { + error = EINVAL; + } else { + *msg->sockaddr.nm_nam = dup_sockaddr(rp->rcb_laddr); + error = 0; + } + lwkt_replymsg(&msg->lmsg, error); } struct pr_usrreqs raw_usrreqs = { .pru_abort = raw_uabort, - .pru_accept = pru_accept_notsupp, + .pru_accept = pr_generic_notsupp, .pru_attach = raw_uattach, .pru_bind = raw_ubind, .pru_connect = raw_uconnect, - .pru_connect2 = pru_connect2_notsupp, - .pru_control = pru_control_notsupp, + .pru_connect2 = pr_generic_notsupp, + .pru_control = pr_generic_notsupp, .pru_detach = raw_udetach, .pru_disconnect = raw_udisconnect, - .pru_listen = pru_listen_notsupp, + .pru_listen = pr_generic_notsupp, .pru_peeraddr = raw_upeeraddr, - .pru_rcvd = pru_rcvd_notsupp, - .pru_rcvoob = pru_rcvoob_notsupp, + .pru_rcvd = pr_generic_notsupp, + .pru_rcvoob = pr_generic_notsupp, .pru_send = raw_usend, .pru_sense = pru_sense_null, .pru_shutdown = raw_ushutdown, diff --git a/sys/net/route.c b/sys/net/route.c index f3ebb80222..75cb594e20 100644 --- a/sys/net/route.c +++ b/sys/net/route.c @@ -115,12 +115,11 @@ static void rtinit_rtrequest_callback(int, int, struct rt_addrinfo *, struct rtentry *, void *); #ifdef SMP -static void rtredirect_msghandler(struct netmsg *netmsg); -static void rtrequest1_msghandler(struct netmsg *netmsg); +static void rtredirect_msghandler(netmsg_t msg); +static void rtrequest1_msghandler(netmsg_t msg); #endif -static void rtsearch_msghandler(struct netmsg *netmsg); - -static void rtmask_add_msghandler(struct netmsg *netmsg); +static void rtsearch_msghandler(netmsg_t msg); +static void rtmask_add_msghandler(netmsg_t msg); static int rt_setshims(struct rtentry *, struct sockaddr **); @@ -160,7 +159,7 @@ route_init(void) } static void -rtable_init_oncpu(struct netmsg *nmsg) +rtable_init_oncpu(netmsg_t msg) { struct domain *dom; int cpu = mycpuid; @@ -172,17 +171,16 @@ rtable_init_oncpu(struct netmsg *nmsg) dom->dom_rtoffset); } } - ifnet_forwardmsg(&nmsg->nm_lmsg, cpu + 1); + ifnet_forwardmsg(&msg->lmsg, cpu + 1); } static void rtable_init(void) { - struct netmsg nmsg; + struct netmsg_base msg; - netmsg_init(&nmsg, NULL, &curthread->td_msgport, - 0, rtable_init_oncpu); - ifnet_domsg(&nmsg.nm_lmsg, 0); + netmsg_init(&msg, NULL, &curthread->td_msgport, 0, rtable_init_oncpu); + ifnet_domsg(&msg.lmsg, 0); } /* @@ -195,13 +193,13 @@ rtable_init(void) static void rtable_service_loop(void *dummy __unused) { - struct netmsg *netmsg; + netmsg_base_t msg; thread_t td = curthread; get_mplock(); /* XXX is this mpsafe yet? */ - while ((netmsg = lwkt_waitport(&td->td_msgport, 0)) != NULL) { - netmsg->nm_dispatch(netmsg); + while ((msg = lwkt_waitport(&td->td_msgport, 0)) != NULL) { + msg->nm_dispatch((netmsg_t)msg); } } @@ -364,9 +362,9 @@ rtfree_oncpu(struct rtentry *rt) } static void -rtfree_remote_dispatch(struct netmsg *nmsg) +rtfree_remote_dispatch(netmsg_t msg) { - struct lwkt_msg *lmsg = &nmsg->nm_lmsg; + struct lwkt_msg *lmsg = &msg->lmsg; struct rtentry *rt = lmsg->u.ms_resultp; rtfree_oncpu(rt); @@ -376,7 +374,7 @@ rtfree_remote_dispatch(struct netmsg *nmsg) void rtfree_remote(struct rtentry *rt, int allow_panic) { - struct netmsg nmsg; + struct netmsg_base msg; struct lwkt_msg *lmsg; KKASSERT(rt->rt_cpuid != mycpuid); @@ -390,9 +388,9 @@ rtfree_remote(struct rtentry *rt, int allow_panic) print_backtrace(-1); } - netmsg_init(&nmsg, NULL, &curthread->td_msgport, + netmsg_init(&msg, NULL, &curthread->td_msgport, 0, rtfree_remote_dispatch); - lmsg = &nmsg.nm_lmsg; + lmsg = &msg.lmsg; lmsg->u.ms_resultp = rt; lwkt_domsg(rtable_portfn(rt->rt_cpuid), lmsg, 0); @@ -502,7 +500,7 @@ out: #ifdef SMP struct netmsg_rtredirect { - struct netmsg netmsg; + struct netmsg_base base; struct sockaddr *dst; struct sockaddr *gateway; struct sockaddr *netmask; @@ -529,14 +527,14 @@ rtredirect(struct sockaddr *dst, struct sockaddr *gateway, #ifdef SMP struct netmsg_rtredirect msg; - netmsg_init(&msg.netmsg, NULL, &curthread->td_msgport, + netmsg_init(&msg.base, NULL, &curthread->td_msgport, 0, rtredirect_msghandler); msg.dst = dst; msg.gateway = gateway; msg.netmask = netmask; msg.flags = flags; msg.src = src; - error = lwkt_domsg(rtable_portfn(0), &msg.netmsg.nm_lmsg, 0); + error = lwkt_domsg(rtable_portfn(0), &msg.base.lmsg, 0); #else error = rtredirect_oncpu(dst, gateway, netmask, flags, src); #endif @@ -551,18 +549,18 @@ rtredirect(struct sockaddr *dst, struct sockaddr *gateway, #ifdef SMP static void -rtredirect_msghandler(struct netmsg *netmsg) +rtredirect_msghandler(netmsg_t msg) { - struct netmsg_rtredirect *msg = (void *)netmsg; + struct netmsg_rtredirect *rmsg = (void *)msg; int nextcpu; - rtredirect_oncpu(msg->dst, msg->gateway, msg->netmask, - msg->flags, msg->src); + rtredirect_oncpu(rmsg->dst, rmsg->gateway, rmsg->netmask, + rmsg->flags, rmsg->src); nextcpu = mycpuid + 1; if (nextcpu < ncpus) - lwkt_forwardmsg(rtable_portfn(nextcpu), &netmsg->nm_lmsg); + lwkt_forwardmsg(rtable_portfn(nextcpu), &msg->lmsg); else - lwkt_replymsg(&netmsg->nm_lmsg, 0); + lwkt_replymsg(&msg->lmsg, 0); } #endif @@ -732,7 +730,7 @@ rtrequest_global( #ifdef SMP struct netmsg_rtq { - struct netmsg netmsg; + struct netmsg_base base; int req; struct rt_addrinfo *rtinfo; rtrequest1_callback_func_t callback; @@ -749,14 +747,14 @@ rtrequest1_global(int req, struct rt_addrinfo *rtinfo, #ifdef SMP struct netmsg_rtq msg; - netmsg_init(&msg.netmsg, NULL, &curthread->td_msgport, + netmsg_init(&msg.base, NULL, &curthread->td_msgport, 0, rtrequest1_msghandler); - msg.netmsg.nm_lmsg.ms_error = -1; + msg.base.lmsg.ms_error = -1; msg.req = req; msg.rtinfo = rtinfo; msg.callback = callback; msg.arg = arg; - error = lwkt_domsg(rtable_portfn(0), &msg.netmsg.nm_lmsg, 0); + error = lwkt_domsg(rtable_portfn(0), &msg.base.lmsg, 0); #else struct rtentry *rt = NULL; @@ -777,9 +775,9 @@ rtrequest1_global(int req, struct rt_addrinfo *rtinfo, #ifdef SMP static void -rtrequest1_msghandler(struct netmsg *netmsg) +rtrequest1_msghandler(netmsg_t msg) { - struct netmsg_rtq *msg = (void *)netmsg; + struct netmsg_rtq *rmsg = (void *)msg; struct rt_addrinfo rtinfo; struct rtentry *rt = NULL; int nextcpu; @@ -791,13 +789,13 @@ rtrequest1_msghandler(struct netmsg *netmsg) * _not_ be changed; else the next CPU on the netmsg forwarding * path will see a different rtinfo than what this CPU has seen. */ - rtinfo = *msg->rtinfo; + rtinfo = *rmsg->rtinfo; - error = rtrequest1(msg->req, &rtinfo, &rt); + error = rtrequest1(rmsg->req, &rtinfo, &rt); if (rt) --rt->rt_refcnt; - if (msg->callback) - msg->callback(msg->req, error, &rtinfo, rt, msg->arg); + if (rmsg->callback) + rmsg->callback(rmsg->req, error, &rtinfo, rt, rmsg->arg); /* * RTM_DELETE's are propogated even if an error occurs, since a @@ -805,21 +803,20 @@ rtrequest1_msghandler(struct netmsg *netmsg) * are not necessarily replicated. An overall error is returned * only if no cpus have the route in question. */ - if (msg->netmsg.nm_lmsg.ms_error < 0 || error == 0) - msg->netmsg.nm_lmsg.ms_error = error; + if (rmsg->base.lmsg.ms_error < 0 || error == 0) + rmsg->base.lmsg.ms_error = error; nextcpu = mycpuid + 1; - if (error && msg->req != RTM_DELETE) { + if (error && rmsg->req != RTM_DELETE) { if (mycpuid != 0) { panic("rtrequest1_msghandler: rtrequest table " "error was not on cpu #0"); } - lwkt_replymsg(&msg->netmsg.nm_lmsg, error); + lwkt_replymsg(&rmsg->base.lmsg, error); } else if (nextcpu < ncpus) { - lwkt_forwardmsg(rtable_portfn(nextcpu), &msg->netmsg.nm_lmsg); + lwkt_forwardmsg(rtable_portfn(nextcpu), &rmsg->base.lmsg); } else { - lwkt_replymsg(&msg->netmsg.nm_lmsg, - msg->netmsg.nm_lmsg.ms_error); + lwkt_replymsg(&rmsg->base.lmsg, rmsg->base.lmsg.ms_error); } } @@ -1649,7 +1646,7 @@ rtinit_rtrequest_callback(int cmd, int error, } struct netmsg_rts { - struct netmsg netmsg; + struct netmsg_base base; int req; struct rt_addrinfo *rtinfo; rtsearch_callback_func_t callback; @@ -1665,7 +1662,7 @@ rtsearch_global(int req, struct rt_addrinfo *rtinfo, { struct netmsg_rts msg; - netmsg_init(&msg.netmsg, NULL, &curthread->td_msgport, + netmsg_init(&msg.base, NULL, &curthread->td_msgport, 0, rtsearch_msghandler); msg.req = req; msg.rtinfo = rtinfo; @@ -1673,13 +1670,13 @@ rtsearch_global(int req, struct rt_addrinfo *rtinfo, msg.arg = arg; msg.exact_match = exact_match; msg.found_cnt = 0; - return lwkt_domsg(rtable_portfn(0), &msg.netmsg.nm_lmsg, 0); + return lwkt_domsg(rtable_portfn(0), &msg.base.lmsg, 0); } static void -rtsearch_msghandler(struct netmsg *netmsg) +rtsearch_msghandler(netmsg_t msg) { - struct netmsg_rts *msg = (void *)netmsg; + struct netmsg_rts *rmsg = (void *)msg; struct rt_addrinfo rtinfo; struct radix_node_head *rnh; struct rtentry *rt; @@ -1691,7 +1688,7 @@ rtsearch_msghandler(struct netmsg *netmsg) * _not_ be changed; else the next CPU on the netmsg forwarding * path will see a different rtinfo than what this CPU has seen. */ - rtinfo = *msg->rtinfo; + rtinfo = *rmsg->rtinfo; /* * Find the correct routing tree to use for this Address Family @@ -1699,7 +1696,7 @@ rtsearch_msghandler(struct netmsg *netmsg) if ((rnh = rt_tables[mycpuid][rtinfo.rti_dst->sa_family]) == NULL) { if (mycpuid != 0) panic("partially initialized routing tables\n"); - lwkt_replymsg(&msg->netmsg.nm_lmsg, EAFNOSUPPORT); + lwkt_replymsg(&rmsg->base.lmsg, EAFNOSUPPORT); return; } @@ -1720,7 +1717,7 @@ rtsearch_msghandler(struct netmsg *netmsg) * that host route searching got a host route while a network * route searching got a network route. */ - if (rt != NULL && msg->exact_match && + if (rt != NULL && rmsg->exact_match && ((rt->rt_flags ^ rtinfo.rti_flags) & RTF_HOST)) rt = NULL; @@ -1733,22 +1730,22 @@ rtsearch_msghandler(struct netmsg *netmsg) */ error = 0; } else { - msg->found_cnt++; + rmsg->found_cnt++; rt->rt_refcnt++; - error = msg->callback(msg->req, &rtinfo, rt, msg->arg, - msg->found_cnt); + error = rmsg->callback(rmsg->req, &rtinfo, rt, rmsg->arg, + rmsg->found_cnt); rt->rt_refcnt--; if (error == EJUSTRETURN) { - lwkt_replymsg(&msg->netmsg.nm_lmsg, 0); + lwkt_replymsg(&rmsg->base.lmsg, 0); return; } } nextcpu = mycpuid + 1; if (error) { - KKASSERT(msg->found_cnt > 0); + KKASSERT(rmsg->found_cnt > 0); /* * Under following cases, unrecoverable error has @@ -1757,32 +1754,32 @@ rtsearch_msghandler(struct netmsg *netmsg) * o The first time that we find the route, but the * modification fails. */ - if (msg->req != RTM_GET && msg->found_cnt > 1) { + if (rmsg->req != RTM_GET && rmsg->found_cnt > 1) { panic("rtsearch_msghandler: unrecoverable error " "cpu %d", mycpuid); } - lwkt_replymsg(&msg->netmsg.nm_lmsg, error); + lwkt_replymsg(&rmsg->base.lmsg, error); } else if (nextcpu < ncpus) { - lwkt_forwardmsg(rtable_portfn(nextcpu), &msg->netmsg.nm_lmsg); + lwkt_forwardmsg(rtable_portfn(nextcpu), &rmsg->base.lmsg); } else { - if (msg->found_cnt == 0) { + if (rmsg->found_cnt == 0) { /* The requested route was never seen ... */ error = ESRCH; } - lwkt_replymsg(&msg->netmsg.nm_lmsg, error); + lwkt_replymsg(&rmsg->base.lmsg, error); } } int rtmask_add_global(struct sockaddr *mask) { - struct netmsg nmsg; + struct netmsg_base msg; - netmsg_init(&nmsg, NULL, &curthread->td_msgport, + netmsg_init(&msg, NULL, &curthread->td_msgport, 0, rtmask_add_msghandler); - nmsg.nm_lmsg.u.ms_resultp = mask; + msg.lmsg.u.ms_resultp = mask; - return lwkt_domsg(rtable_portfn(0), &nmsg.nm_lmsg, 0); + return lwkt_domsg(rtable_portfn(0), &msg.lmsg, 0); } struct sockaddr * @@ -1804,9 +1801,9 @@ _rtmask_lookup(struct sockaddr *mask, boolean_t search) } static void -rtmask_add_msghandler(struct netmsg *nmsg) +rtmask_add_msghandler(netmsg_t msg) { - struct lwkt_msg *lmsg = &nmsg->nm_lmsg; + struct lwkt_msg *lmsg = &msg->lmsg; struct sockaddr *mask = lmsg->u.ms_resultp; int error = 0, nextcpu; diff --git a/sys/net/rtsock.c b/sys/net/rtsock.c index 2783b81f83..ee6ab7f181 100644 --- a/sys/net/rtsock.c +++ b/sys/net/rtsock.c @@ -129,27 +129,31 @@ static void rt_setmetrics (u_long, struct rt_metrics *, * It really doesn't make any sense at all for this code to share much * with raw_usrreq.c, since its functionality is so restricted. XXX */ -static int -rts_abort(struct socket *so) +static void +rts_abort(netmsg_t msg) { - int error; - crit_enter(); - error = raw_usrreqs.pru_abort(so); + raw_usrreqs.pru_abort(msg); + /* msg invalid now */ crit_exit(); - return error; } /* pru_accept is EOPNOTSUPP */ -static int -rts_attach(struct socket *so, int proto, struct pru_attach_info *ai) +static void +rts_attach(netmsg_t msg) { + struct socket *so = msg->base.nm_so; + struct pru_attach_info *ai = msg->attach.nm_ai; struct rawcb *rp; + int proto = msg->attach.nm_proto; int error; - if (sotorawcb(so) != NULL) - return EISCONN; /* XXX panic? */ + crit_enter(); + if (sotorawcb(so) != NULL) { + error = EISCONN; + goto done; + } rp = kmalloc(sizeof *rp, M_PCB, M_WAITOK | M_ZERO); @@ -160,15 +164,13 @@ rts_attach(struct socket *so, int proto, struct pru_attach_info *ai) * Probably we should try to do more of this work beforehand and * eliminate the critical section. */ - crit_enter(); so->so_pcb = rp; soreference(so); /* so_pcb assignment */ error = raw_attach(so, proto, ai->sb_rlimit); rp = sotorawcb(so); if (error) { - crit_exit(); kfree(rp, M_PCB); - return error; + goto done; } switch(rp->rcb_proto.sp_protocol) { case AF_INET: @@ -188,40 +190,38 @@ rts_attach(struct socket *so, int proto, struct pru_attach_info *ai) route_cb.any_count++; soisconnected(so); so->so_options |= SO_USELOOPBACK; + error = 0; +done: crit_exit(); - return 0; + lwkt_replymsg(&msg->lmsg, error); } -static int -rts_bind(struct socket *so, struct sockaddr *nam, struct thread *td) +static void +rts_bind(netmsg_t msg) { - int error; - crit_enter(); - error = raw_usrreqs.pru_bind(so, nam, td); /* xxx just EINVAL */ + raw_usrreqs.pru_bind(msg); /* xxx just EINVAL */ + /* msg invalid now */ crit_exit(); - return error; } -static int -rts_connect(struct socket *so, struct sockaddr *nam, struct thread *td) +static void +rts_connect(netmsg_t msg) { - int error; - crit_enter(); - error = raw_usrreqs.pru_connect(so, nam, td); /* XXX just EINVAL */ + raw_usrreqs.pru_connect(msg); /* XXX just EINVAL */ + /* msg invalid now */ crit_exit(); - return error; } /* pru_connect2 is EOPNOTSUPP */ /* pru_control is EOPNOTSUPP */ -static int -rts_detach(struct socket *so) +static void +rts_detach(netmsg_t msg) { + struct socket *so = msg->base.nm_so; struct rawcb *rp = sotorawcb(so); - int error; crit_enter(); if (rp != NULL) { @@ -241,88 +241,77 @@ rts_detach(struct socket *so) } route_cb.any_count--; } - error = raw_usrreqs.pru_detach(so); + raw_usrreqs.pru_detach(msg); + /* msg invalid now */ crit_exit(); - return error; } -static int -rts_disconnect(struct socket *so) +static void +rts_disconnect(netmsg_t msg) { - int error; - crit_enter(); - error = raw_usrreqs.pru_disconnect(so); + raw_usrreqs.pru_disconnect(msg); + /* msg invalid now */ crit_exit(); - return error; } /* pru_listen is EOPNOTSUPP */ -static int -rts_peeraddr(struct socket *so, struct sockaddr **nam) +static void +rts_peeraddr(netmsg_t msg) { - int error; - crit_enter(); - error = raw_usrreqs.pru_peeraddr(so, nam); + raw_usrreqs.pru_peeraddr(msg); + /* msg invalid now */ crit_exit(); - return error; } /* pru_rcvd is EOPNOTSUPP */ /* pru_rcvoob is EOPNOTSUPP */ -static int -rts_send(struct socket *so, int flags, struct mbuf *m, struct sockaddr *nam, - struct mbuf *control, struct thread *td) +static void +rts_send(netmsg_t msg) { - int error; - crit_enter(); - error = raw_usrreqs.pru_send(so, flags, m, nam, control, td); + raw_usrreqs.pru_send(msg); + /* msg invalid now */ crit_exit(); - return error; } /* pru_sense is null */ -static int -rts_shutdown(struct socket *so) +static void +rts_shutdown(netmsg_t msg) { - int error; - crit_enter(); - error = raw_usrreqs.pru_shutdown(so); + raw_usrreqs.pru_shutdown(msg); + /* msg invalid now */ crit_exit(); - return error; } -static int -rts_sockaddr(struct socket *so, struct sockaddr **nam) +static void +rts_sockaddr(netmsg_t msg) { - int error; - crit_enter(); - error = raw_usrreqs.pru_sockaddr(so, nam); + raw_usrreqs.pru_sockaddr(msg); + /* msg invalid now */ crit_exit(); - return error; } static struct pr_usrreqs route_usrreqs = { .pru_abort = rts_abort, - .pru_accept = pru_accept_notsupp, + .pru_accept = pr_generic_notsupp, .pru_attach = rts_attach, .pru_bind = rts_bind, .pru_connect = rts_connect, - .pru_connect2 = pru_connect2_notsupp, - .pru_control = pru_control_notsupp, + .pru_connect2 = pr_generic_notsupp, + .pru_control = pr_generic_notsupp, .pru_detach = rts_detach, .pru_disconnect = rts_disconnect, - .pru_listen = pru_listen_notsupp, + .pru_listen = pr_generic_notsupp, .pru_peeraddr = rts_peeraddr, - .pru_rcvd = pru_rcvd_notsupp, - .pru_rcvoob = pru_rcvoob_notsupp, + .pru_rcvd = pr_generic_notsupp, + .pru_rcvoob = pr_generic_notsupp, .pru_send = rts_send, .pru_sense = pru_sense_null, .pru_shutdown = rts_shutdown, @@ -345,17 +334,16 @@ familyof(struct sockaddr *sa) * can send a message to the routing socket. */ static void -rts_input_handler(struct netmsg *msg) +rts_input_handler(netmsg_t msg) { static const struct sockaddr route_dst = { 2, PF_ROUTE, }; struct sockproto route_proto; - struct netmsg_packet *pmsg; + struct netmsg_packet *pmsg = &msg->packet; struct mbuf *m; sa_family_t family; struct rawcb *skip; - pmsg = (void *)msg; - family = pmsg->nm_netmsg.nm_lmsg.u.ms_result; + family = pmsg->base.lmsg.u.ms_result; route_proto.sp_family = PF_ROUTE; route_proto.sp_protocol = family; @@ -376,14 +364,14 @@ rts_input_skip(struct mbuf *m, sa_family_t family, struct rawcb *skip) M_ASSERTPKTHDR(m); - port = cpu0_soport(NULL, NULL, NULL); /* same as for routing socket */ + port = cpu_portfn(0); /* XXX same as for routing socket */ pmsg = &m->m_hdr.mh_netmsg; - netmsg_init(&pmsg->nm_netmsg, NULL, &netisr_apanic_rport, + netmsg_init(&pmsg->base, NULL, &netisr_apanic_rport, 0, rts_input_handler); pmsg->nm_packet = m; - pmsg->nm_netmsg.nm_lmsg.u.ms_result = family; + pmsg->base.lmsg.u.ms_result = family; m->m_pkthdr.header = skip; /* XXX steal field in pkthdr */ - lwkt_sendmsg(port, &pmsg->nm_netmsg.nm_lmsg); + lwkt_sendmsg(port, &pmsg->base.lmsg); } static __inline void @@ -1459,12 +1447,20 @@ SYSCTL_NODE(_net, PF_ROUTE, routetable, CTLFLAG_RD, sysctl_rtsock, ""); static struct domain routedomain; /* or at least forward */ static struct protosw routesw[] = { -{ SOCK_RAW, &routedomain, 0, PR_ATOMIC|PR_ADDR, - 0, route_output, raw_ctlinput, 0, - cpu0_soport, cpu0_ctlport, - raw_init, 0, 0, 0, - &route_usrreqs -} + { + .pr_type = SOCK_RAW, + .pr_domain = &routedomain, + .pr_protocol = 0, + .pr_flags = PR_ATOMIC|PR_ADDR, + .pr_input = NULL, + .pr_output = route_output, + .pr_ctlinput = raw_ctlinput, + .pr_ctloutput = NULL, + .pr_ctlport = cpu0_ctlport, + + .pr_init = raw_init, + .pr_usrreqs = &route_usrreqs + } }; static struct domain routedomain = { diff --git a/sys/net/stf/if_stf.c b/sys/net/stf/if_stf.c index 5d6d2b2c7c..1386c58bbf 100644 --- a/sys/net/stf/if_stf.c +++ b/sys/net/stf/if_stf.c @@ -135,12 +135,19 @@ static int ip_stf_ttl = 40; extern struct domain inetdomain; struct protosw in_stf_protosw = -{ SOCK_RAW, &inetdomain, IPPROTO_IPV6, PR_ATOMIC|PR_ADDR, - in_stf_input, rip_output, 0, rip_ctloutput, - NULL, NULL, - 0, 0, 0, 0, - &rip_usrreqs -}; + { + .pr_type = SOCK_RAW, + .pr_domain = &inetdomain, + .pr_protocol = IPPROTO_IPV6, + .pr_flags = PR_ATOMIC|PR_ADDR, + + .pr_input = in_stf_input, + .pr_output = rip_output, + .pr_ctlinput = NULL, + .pr_ctloutput = rip_ctloutput, + + .pr_usrreqs = &rip_usrreqs + }; static int stfmodevent (module_t, int, void *); static int stf_encapcheck (const struct mbuf *, int, int, void *); @@ -503,26 +510,24 @@ stf_checkaddr6(struct stf_softc *sc, struct in6_addr *in6, struct ifnet *inifp) return 0; } -void -in_stf_input(struct mbuf *m, ...) +int +in_stf_input(struct mbuf **mp, int *offp, int proto) { + struct mbuf *m; struct stf_softc *sc; struct ip *ip; struct ip6_hdr *ip6; u_int8_t otos, itos; struct ifnet *ifp; - int off, proto; + int off; static const uint32_t af = AF_INET6; - __va_list ap; - __va_start(ap, m); - off = __va_arg(ap, int); - proto = __va_arg(ap, int); - __va_end(ap); + m = *mp; + off = *offp; if (proto != IPPROTO_IPV6) { m_freem(m); - return; + return(IPPROTO_DONE); } ip = mtod(m, struct ip *); @@ -531,7 +536,7 @@ in_stf_input(struct mbuf *m, ...) if (sc == NULL || (sc->sc_if.if_flags & IFF_UP) == 0) { m_freem(m); - return; + return(IPPROTO_DONE); } ifp = &sc->sc_if; @@ -543,7 +548,7 @@ in_stf_input(struct mbuf *m, ...) if (stf_checkaddr4(sc, &ip->ip_dst, NULL) < 0 || stf_checkaddr4(sc, &ip->ip_src, m->m_pkthdr.rcvif) < 0) { m_freem(m); - return; + return(IPPROTO_DONE); } otos = ip->ip_tos; @@ -552,7 +557,7 @@ in_stf_input(struct mbuf *m, ...) if (m->m_len < sizeof(*ip6)) { m = m_pullup(m, sizeof(*ip6)); if (!m) - return; + return(IPPROTO_DONE); } ip6 = mtod(m, struct ip6_hdr *); @@ -563,7 +568,7 @@ in_stf_input(struct mbuf *m, ...) if (stf_checkaddr6(sc, &ip6->ip6_dst, NULL) < 0 || stf_checkaddr6(sc, &ip6->ip6_src, m->m_pkthdr.rcvif) < 0) { m_freem(m); - return; + return(IPPROTO_DONE); } itos = (ntohl(ip6->ip6_flow) >> 20) & 0xff; @@ -588,6 +593,7 @@ in_stf_input(struct mbuf *m, ...) ifp->if_ipackets++; ifp->if_ibytes += m->m_pkthdr.len; netisr_queue(NETISR_IPV6, m); + return(IPPROTO_DONE); } /* ARGSUSED */ diff --git a/sys/net/stf/if_stf.h b/sys/net/stf/if_stf.h index 130e856f0a..0134fc7ca2 100644 --- a/sys/net/stf/if_stf.h +++ b/sys/net/stf/if_stf.h @@ -34,6 +34,6 @@ #ifndef _NET_IF_STF_H_ #define _NET_IF_STF_H_ -void in_stf_input (struct mbuf *, ...); +int in_stf_input (struct mbuf **, int *, int); #endif /* _NET_IF_STF_H_ */ diff --git a/sys/net/vlan/if_vlan.c b/sys/net/vlan/if_vlan.c index d505c437fc..cdbcb5f232 100644 --- a/sys/net/vlan/if_vlan.c +++ b/sys/net/vlan/if_vlan.c @@ -111,7 +111,7 @@ struct vlan_trunk { }; struct netmsg_vlan { - struct netmsg nv_nmsg; + struct netmsg_base base; struct ifvlan *nv_ifv; struct ifnet *nv_ifp_p; const char *nv_parent_name; @@ -148,13 +148,13 @@ static int vlan_unconfig(struct ifvlan *); static void vlan_link(struct ifvlan *, struct ifnet *); static void vlan_unlink(struct ifvlan *, struct ifnet *); -static void vlan_config_dispatch(struct netmsg *); -static void vlan_unconfig_dispatch(struct netmsg *); -static void vlan_link_dispatch(struct netmsg *); -static void vlan_unlink_dispatch(struct netmsg *); -static void vlan_multi_dispatch(struct netmsg *); -static void vlan_flags_dispatch(struct netmsg *); -static void vlan_ifdetach_dispatch(struct netmsg *); +static void vlan_config_dispatch(netmsg_t); +static void vlan_unconfig_dispatch(netmsg_t); +static void vlan_link_dispatch(netmsg_t); +static void vlan_unlink_dispatch(netmsg_t); +static void vlan_multi_dispatch(netmsg_t); +static void vlan_flags_dispatch(netmsg_t); +static void vlan_ifdetach_dispatch(netmsg_t); /* Special flags we should propagate to parent */ static struct { @@ -343,9 +343,9 @@ static moduledata_t vlan_mod = { DECLARE_MODULE(if_vlan, vlan_mod, SI_SUB_PSEUDO, SI_ORDER_ANY); static void -vlan_ifdetach_dispatch(struct netmsg *nmsg) +vlan_ifdetach_dispatch(netmsg_t msg) { - struct netmsg_vlan *vmsg = (struct netmsg_vlan *)nmsg; + struct netmsg_vlan *vmsg = (struct netmsg_vlan *)msg; struct ifnet *ifp_p = vmsg->nv_ifp_p; struct vlan_trunk *vlantrunks, *trunk; struct vlan_entry *ifve; @@ -359,25 +359,23 @@ vlan_ifdetach_dispatch(struct netmsg *nmsg) (ifve = LIST_FIRST(&trunk->vlan_list)) != NULL) vlan_unconfig(ifve->ifv); reply: - lwkt_replymsg(&nmsg->nm_lmsg, 0); + lwkt_replymsg(&vmsg->base.lmsg, 0); } static void vlan_ifdetach(void *arg __unused, struct ifnet *ifp) { struct netmsg_vlan vmsg; - struct netmsg *nmsg; ASSERT_IFNET_NOT_SERIALIZED_ALL(ifp); bzero(&vmsg, sizeof(vmsg)); - nmsg = &vmsg.nv_nmsg; - netmsg_init(nmsg, NULL, &curthread->td_msgport, + netmsg_init(&vmsg.base, NULL, &curthread->td_msgport, 0, vlan_ifdetach_dispatch); vmsg.nv_ifp_p = ifp; - lwkt_domsg(cpu_portfn(0), &nmsg->nm_lmsg, 0); + lwkt_domsg(cpu_portfn(0), &vmsg.base.lmsg, 0); } static int @@ -465,7 +463,6 @@ vlan_start(struct ifnet *ifp) for (;;) { struct netmsg_packet *nmp; - struct netmsg *nmsg; struct lwkt_port *port; m = ifq_dequeue(&ifp->if_snd, NULL); @@ -496,15 +493,14 @@ vlan_start(struct ifnet *ifp) m->m_flags |= M_VLANTAG; nmp = &m->m_hdr.mh_netmsg; - nmsg = &nmp->nm_netmsg; - netmsg_init(nmsg, NULL, &netisr_apanic_rport, + netmsg_init(&nmp->base, NULL, &netisr_apanic_rport, 0, vlan_start_dispatch); nmp->nm_packet = m; - nmsg->nm_lmsg.u.ms_resultp = ifp_p; + nmp->base.lmsg.u.ms_resultp = ifp_p; port = cpu_portfn(ifp_p->if_index % ncpus /* XXX */); - lwkt_sendmsg(port, &nmp->nm_netmsg.nm_lmsg); + lwkt_sendmsg(port, &nmp->base.lmsg); ifp->if_opackets++; } } @@ -559,9 +555,9 @@ vlan_input(struct mbuf *m) } static void -vlan_link_dispatch(struct netmsg *nmsg) +vlan_link_dispatch(netmsg_t msg) { - struct netmsg_vlan *vmsg = (struct netmsg_vlan *)nmsg; + struct netmsg_vlan *vmsg = (struct netmsg_vlan *)msg; struct ifvlan *ifv = vmsg->nv_ifv; struct ifnet *ifp_p = vmsg->nv_ifp_p; struct vlan_entry *entry; @@ -579,14 +575,13 @@ vlan_link_dispatch(struct netmsg *nmsg) LIST_INSERT_HEAD(&trunk->vlan_list, entry, ifv_link); crit_exit(); - ifnet_forwardmsg(&nmsg->nm_lmsg, cpu + 1); + ifnet_forwardmsg(&vmsg->base.lmsg, cpu + 1); } static void vlan_link(struct ifvlan *ifv, struct ifnet *ifp_p) { struct netmsg_vlan vmsg; - struct netmsg *nmsg; /* Assert in netisr0 */ ASSERT_IFNET_NOT_SERIALIZED_ALL(&ifv->ifv_if); @@ -604,20 +599,19 @@ vlan_link(struct ifvlan *ifv, struct ifnet *ifp_p) } bzero(&vmsg, sizeof(vmsg)); - nmsg = &vmsg.nv_nmsg; - netmsg_init(nmsg, NULL, &curthread->td_msgport, + netmsg_init(&vmsg.base, NULL, &curthread->td_msgport, 0, vlan_link_dispatch); vmsg.nv_ifv = ifv; vmsg.nv_ifp_p = ifp_p; - ifnet_domsg(&nmsg->nm_lmsg, 0); + ifnet_domsg(&vmsg.base.lmsg, 0); } static void -vlan_config_dispatch(struct netmsg *nmsg) +vlan_config_dispatch(netmsg_t msg) { - struct netmsg_vlan *vmsg = (struct netmsg_vlan *)nmsg; + struct netmsg_vlan *vmsg = (struct netmsg_vlan *)msg; struct ifvlan *ifv; struct ifnet *ifp_p, *ifp; struct sockaddr_dl *sdl1, *sdl2; @@ -702,33 +696,31 @@ vlan_config_dispatch(struct netmsg *nmsg) ifv->ifv_p = ifp_p; error = 0; reply: - lwkt_replymsg(&nmsg->nm_lmsg, error); + lwkt_replymsg(&vmsg->base.lmsg, error); } static int vlan_config(struct ifvlan *ifv, const char *parent_name, uint16_t vlantag) { struct netmsg_vlan vmsg; - struct netmsg *nmsg; ASSERT_IFNET_NOT_SERIALIZED_ALL(&ifv->ifv_if); bzero(&vmsg, sizeof(vmsg)); - nmsg = &vmsg.nv_nmsg; - netmsg_init(nmsg, NULL, &curthread->td_msgport, + netmsg_init(&vmsg.base, NULL, &curthread->td_msgport, 0, vlan_config_dispatch); vmsg.nv_ifv = ifv; vmsg.nv_parent_name = parent_name; vmsg.nv_vlantag = vlantag; - return lwkt_domsg(cpu_portfn(0), &nmsg->nm_lmsg, 0); + return lwkt_domsg(cpu_portfn(0), &vmsg.base.lmsg, 0); } static void -vlan_unlink_dispatch(struct netmsg *nmsg) +vlan_unlink_dispatch(netmsg_t msg) { - struct netmsg_vlan *vmsg = (struct netmsg_vlan *)nmsg; + struct netmsg_vlan *vmsg = (struct netmsg_vlan *)msg; struct ifvlan *ifv = vmsg->nv_ifv; struct vlan_entry *entry; int cpu = mycpuid; @@ -741,7 +733,7 @@ vlan_unlink_dispatch(struct netmsg *nmsg) LIST_REMOVE(entry, ifv_link); crit_exit(); - ifnet_forwardmsg(&nmsg->nm_lmsg, cpu + 1); + ifnet_forwardmsg(&vmsg->base.lmsg, cpu + 1); } static void @@ -749,7 +741,6 @@ vlan_unlink(struct ifvlan *ifv, struct ifnet *ifp_p) { struct vlan_trunk *vlantrunks = ifp_p->if_vlantrunks; struct netmsg_vlan vmsg; - struct netmsg *nmsg; /* Assert in netisr0 */ ASSERT_IFNET_NOT_SERIALIZED_ALL(&ifv->ifv_if); @@ -758,14 +749,13 @@ vlan_unlink(struct ifvlan *ifv, struct ifnet *ifp_p) ("vlan trunk has not been initialized yet\n")); bzero(&vmsg, sizeof(vmsg)); - nmsg = &vmsg.nv_nmsg; - netmsg_init(nmsg, NULL, &curthread->td_msgport, + netmsg_init(&vmsg.base, NULL, &curthread->td_msgport, 0, vlan_unlink_dispatch); vmsg.nv_ifv = ifv; vmsg.nv_ifp_p = ifp_p; - ifnet_domsg(&nmsg->nm_lmsg, 0); + ifnet_domsg(&vmsg.base.lmsg, 0); crit_enter(); if (LIST_EMPTY(&vlantrunks[mycpuid].vlan_list)) { @@ -781,9 +771,9 @@ vlan_unlink(struct ifvlan *ifv, struct ifnet *ifp_p) } static void -vlan_unconfig_dispatch(struct netmsg *nmsg) +vlan_unconfig_dispatch(netmsg_t msg) { - struct netmsg_vlan *vmsg = (struct netmsg_vlan *)nmsg; + struct netmsg_vlan *vmsg = (struct netmsg_vlan *)msg; struct sockaddr_dl *sdl; struct ifvlan *ifv; struct ifnet *ifp_p, *ifp; @@ -846,25 +836,23 @@ vlan_unconfig_dispatch(struct netmsg *nmsg) vlan_unlink(ifv, ifp_p); error = 0; - lwkt_replymsg(&nmsg->nm_lmsg, error); + lwkt_replymsg(&vmsg->base.lmsg, error); } static int vlan_unconfig(struct ifvlan *ifv) { struct netmsg_vlan vmsg; - struct netmsg *nmsg; ASSERT_IFNET_NOT_SERIALIZED_ALL(&ifv->ifv_if); bzero(&vmsg, sizeof(vmsg)); - nmsg = &vmsg.nv_nmsg; - netmsg_init(nmsg, NULL, &curthread->td_msgport, + netmsg_init(&vmsg.base, NULL, &curthread->td_msgport, 0, vlan_unconfig_dispatch); vmsg.nv_ifv = ifv; - return lwkt_domsg(cpu_portfn(0), &nmsg->nm_lmsg, 0); + return lwkt_domsg(cpu_portfn(0), &vmsg.base.lmsg, 0); } static int @@ -978,9 +966,9 @@ vlan_ioctl(struct ifnet *ifp, u_long cmd, caddr_t data, struct ucred *cr) } static void -vlan_multi_dispatch(struct netmsg *nmsg) +vlan_multi_dispatch(netmsg_t msg) { - struct netmsg_vlan *vmsg = (struct netmsg_vlan *)nmsg; + struct netmsg_vlan *vmsg = (struct netmsg_vlan *)msg; struct ifvlan *ifv = vmsg->nv_ifv; int error = 0; @@ -990,31 +978,29 @@ vlan_multi_dispatch(struct netmsg *nmsg) */ if (ifv->ifv_p != NULL) error = vlan_setmulti(ifv, ifv->ifv_p); - lwkt_replymsg(&nmsg->nm_lmsg, error); + lwkt_replymsg(&vmsg->base.lmsg, error); } static int vlan_config_multi(struct ifvlan *ifv) { struct netmsg_vlan vmsg; - struct netmsg *nmsg; ASSERT_IFNET_NOT_SERIALIZED_ALL(&ifv->ifv_if); bzero(&vmsg, sizeof(vmsg)); - nmsg = &vmsg.nv_nmsg; - netmsg_init(nmsg, NULL, &curthread->td_msgport, + netmsg_init(&vmsg.base, NULL, &curthread->td_msgport, 0, vlan_multi_dispatch); vmsg.nv_ifv = ifv; - return lwkt_domsg(cpu_portfn(0), &nmsg->nm_lmsg, 0); + return lwkt_domsg(cpu_portfn(0), &vmsg.base.lmsg, 0); } static void -vlan_flags_dispatch(struct netmsg *nmsg) +vlan_flags_dispatch(netmsg_t msg) { - struct netmsg_vlan *vmsg = (struct netmsg_vlan *)nmsg; + struct netmsg_vlan *vmsg = (struct netmsg_vlan *)msg; struct ifvlan *ifv = vmsg->nv_ifv; int error = 0; @@ -1024,23 +1010,21 @@ vlan_flags_dispatch(struct netmsg *nmsg) */ if (ifv->ifv_p != NULL) error = vlan_setflags(ifv, ifv->ifv_p, 1); - lwkt_replymsg(&nmsg->nm_lmsg, error); + lwkt_replymsg(&vmsg->base.lmsg, error); } static int vlan_config_flags(struct ifvlan *ifv) { struct netmsg_vlan vmsg; - struct netmsg *nmsg; ASSERT_IFNET_NOT_SERIALIZED_ALL(&ifv->ifv_if); bzero(&vmsg, sizeof(vmsg)); - nmsg = &vmsg.nv_nmsg; - netmsg_init(nmsg, NULL, &curthread->td_msgport, + netmsg_init(&vmsg.base, NULL, &curthread->td_msgport, 0, vlan_flags_dispatch); vmsg.nv_ifv = ifv; - return lwkt_domsg(cpu_portfn(0), &nmsg->nm_lmsg, 0); + return lwkt_domsg(cpu_portfn(0), &vmsg.base.lmsg, 0); } diff --git a/sys/net/vlan/if_vlan_ether.c b/sys/net/vlan/if_vlan_ether.c index bac789d86d..1e82042005 100644 --- a/sys/net/vlan/if_vlan_ether.c +++ b/sys/net/vlan/if_vlan_ether.c @@ -45,15 +45,15 @@ #include void -vlan_start_dispatch(struct netmsg *nmsg) +vlan_start_dispatch(netmsg_t msg) { - struct netmsg_packet *nmp = (struct netmsg_packet *)nmsg; + struct netmsg_packet *nmp = &msg->packet; struct mbuf *m; struct ifnet *ifp; struct altq_pktattr pktattr; m = nmp->nm_packet; - ifp = nmsg->nm_lmsg.u.ms_resultp; + ifp = msg->lmsg.u.ms_resultp; M_ASSERTPKTHDR(m); KASSERT(m->m_flags & M_VLANTAG, ("mbuf has not been vlan tagged!\n")); diff --git a/sys/net/vlan/if_vlan_ether.h b/sys/net/vlan/if_vlan_ether.h index 13d186059c..dcf5a60eca 100644 --- a/sys/net/vlan/if_vlan_ether.h +++ b/sys/net/vlan/if_vlan_ether.h @@ -35,11 +35,11 @@ #ifdef _KERNEL -struct netmsg; +union netmsg; struct bpf_if; struct mbuf; -void vlan_start_dispatch(struct netmsg *); +void vlan_start_dispatch(union netmsg *); void vlan_ether_ptap(struct bpf_if *, struct mbuf *, uint16_t); void vlan_ether_decap(struct mbuf **); diff --git a/sys/netbt/bt_input.c b/sys/netbt/bt_input.c index 92ce6f51dc..3e580b0a80 100644 --- a/sys/netbt/bt_input.c +++ b/sys/netbt/bt_input.c @@ -29,7 +29,7 @@ #include void -btintr(struct netmsg *msg) +btintr(netmsg_t msg) { struct hci_unit *unit; diff --git a/sys/netbt/bt_proto.c b/sys/netbt/bt_proto.c index 2ccfca52cf..9aede9ae10 100644 --- a/sys/netbt/bt_proto.c +++ b/sys/netbt/bt_proto.c @@ -77,7 +77,6 @@ struct protosw btsw[] = { .pr_output = 0, .pr_ctlinput = 0, .pr_ctloutput = hci_ctloutput, - .pr_mport = cpu0_soport, .pr_ctlport = NULL, .pr_init = 0, .pr_fasttimo = 0, @@ -94,7 +93,6 @@ struct protosw btsw[] = { .pr_output = 0, .pr_ctlinput = 0, .pr_ctloutput = sco_ctloutput, - .pr_mport = cpu0_soport, .pr_ctlport = NULL, .pr_init = 0, .pr_fasttimo = 0, @@ -112,7 +110,6 @@ struct protosw btsw[] = { .pr_output = 0, .pr_ctlinput = 0, .pr_ctloutput = l2cap_ctloutput, - .pr_mport = cpu0_soport, .pr_ctlport = NULL, .pr_init = 0, .pr_fasttimo = 0, @@ -129,7 +126,6 @@ struct protosw btsw[] = { .pr_output = 0, .pr_ctlinput = 0, .pr_ctloutput = rfcomm_ctloutput, - .pr_mport = cpu0_soport, .pr_ctlport = NULL, .pr_init = 0, .pr_fasttimo = 0, diff --git a/sys/netbt/hci.h b/sys/netbt/hci.h index 0535d290ef..5be20901d4 100644 --- a/sys/netbt/hci.h +++ b/sys/netbt/hci.h @@ -2510,6 +2510,7 @@ extern TAILQ_HEAD(hci_unit_list, hci_unit) hci_unit_list; /* * HCI layer function prototypes */ +union netmsg; /* hci_event.c */ void hci_event(struct mbuf *, struct hci_unit *); @@ -2547,7 +2548,7 @@ void hci_memo_free(struct hci_memo *); /* hci_socket.c */ void hci_drop(void *); int hci_usrreq(struct socket *, int, struct mbuf *, struct mbuf *, struct mbuf *); -int hci_ctloutput(struct socket *so, struct sockopt *sopt); +void hci_ctloutput(union netmsg *); void hci_mtap(struct mbuf *, struct hci_unit *); /* hci_unit.c */ @@ -2565,7 +2566,7 @@ void hci_output_cmd(struct hci_unit *, struct mbuf *); void hci_output_acl(struct hci_unit *, struct mbuf *); void hci_output_sco(struct hci_unit *, struct mbuf *); void hci_intr(void *); -void btintr(struct netmsg *msg); +void btintr(union netmsg *); /* XXX mimic NetBSD for now, although we don't have these interfaces */ #define M_GETCTX(m, t) ((t)(m)->m_pkthdr.rcvif) diff --git a/sys/netbt/hci_socket.c b/sys/netbt/hci_socket.c index 9bc0a1a832..20e5cfb859 100644 --- a/sys/netbt/hci_socket.c +++ b/sys/netbt/hci_socket.c @@ -55,6 +55,7 @@ #include #include +#include #include #include @@ -92,23 +93,7 @@ int hci_recvspace = 4096; extern struct pr_usrreqs hci_usrreqs; /* Prototypes for usrreqs methods. */ -static int hci_sabort (struct socket *so); -static int hci_sdetach(struct socket *so); -static int hci_sdisconnect (struct socket *so); -static int hci_scontrol (struct socket *so, u_long cmd, caddr_t data, - struct ifnet *ifp, struct thread *td); -static int hci_sattach (struct socket *so, int proto, - struct pru_attach_info *ai); -static int hci_sbind (struct socket *so, struct sockaddr *nam, - struct thread *td); -static int hci_sconnect (struct socket *so, struct sockaddr *nam, - struct thread *td); -static int hci_speeraddr (struct socket *so, struct sockaddr **nam); -static int hci_ssockaddr (struct socket *so, struct sockaddr **nam); -static int hci_sshutdown (struct socket *so); -static int hci_ssend (struct socket *so, int flags, struct mbuf *m, - struct sockaddr *addr, struct mbuf *control, - struct thread *td); +static void hci_sdetach(netmsg_t msg); /* supported commands opcode table */ static const struct { @@ -562,81 +547,95 @@ bad: * NOTE: (so) is referenced from soabort*() and netmsg_pru_abort() * will sofree() it when we return. */ -static int -hci_sabort (struct socket *so) +static void +hci_sabort(netmsg_t msg) { - int error; - /* struct hci_pcb *pcb = (struct hci_pcb *)so->so_pcb; */ - soisdisconnected(so); - error = hci_sdetach(so); - return (error); + soisdisconnected(msg->abort.base.nm_so); + hci_sdetach(msg); + /* msg now invalid */ } -static int -hci_sdetach(struct socket *so) +static void +hci_sdetach(netmsg_t msg) { + struct socket *so = msg->detach.base.nm_so; struct hci_pcb *pcb = (struct hci_pcb *)so->so_pcb; + int error; - if (pcb == NULL) - return EINVAL; - if (so->so_snd.ssb_mb != NULL) - hci_cmdwait_flush(so); - - so->so_pcb = NULL; - sofree(so); /* remove pcb ref */ - - LIST_REMOVE(pcb, hp_next); - kfree(pcb, M_PCB); - - return 0; + if (pcb == NULL) { + error = EINVAL; + } else { + if (so->so_snd.ssb_mb != NULL) + hci_cmdwait_flush(so); + + so->so_pcb = NULL; + sofree(so); /* remove pcb ref */ + + LIST_REMOVE(pcb, hp_next); + kfree(pcb, M_PCB); + error = 0; + } + lwkt_replymsg(&msg->detach.base.lmsg, error); } -static int -hci_sdisconnect (struct socket *so) +static void +hci_sdisconnect(netmsg_t msg) { + struct socket *so = msg->disconnect.base.nm_so; struct hci_pcb *pcb = (struct hci_pcb *)so->so_pcb; + int error; - if (pcb==NULL) - return EINVAL; - - bdaddr_copy(&pcb->hp_raddr, BDADDR_ANY); - /* - * XXX We cannot call soisdisconnected() here, as it sets - * SS_CANTRCVMORE and SS_CANTSENDMORE. The problem is that - * soisconnected() does not clear these and if you try to reconnect - * this socket (which is permitted) you get a broken pipe when you - * try to write any data. - */ - soclrstate(so, SS_ISCONNECTED); - - return 0; + if (pcb) { + bdaddr_copy(&pcb->hp_raddr, BDADDR_ANY); + /* + * XXX We cannot call soisdisconnected() here, as it sets + * SS_CANTRCVMORE and SS_CANTSENDMORE. The problem is that + * soisconnected() does not clear these and if you try to + * reconnect this socket (which is permitted) you get a + * broken pipe when you try to write any data. + */ + soclrstate(so, SS_ISCONNECTED); + error = 0; + } else { + error = EINVAL; + } + lwkt_replymsg(&msg->disconnect.base.lmsg, error); } -static int -hci_scontrol (struct socket *so, u_long cmd, caddr_t data, struct ifnet *ifp, - struct thread *td) +static void +hci_scontrol(netmsg_t msg) { - return hci_ioctl(cmd, (void*)data, NULL); + int error; + + error = hci_ioctl(msg->control.nm_cmd, + (void *)msg->control.nm_data, + NULL); + lwkt_replymsg(&msg->control.base.lmsg, error); } -static int -hci_sattach (struct socket *so, int proto, struct pru_attach_info *ai) +static void +hci_sattach(netmsg_t msg) { + struct socket *so = msg->attach.base.nm_so; struct hci_pcb *pcb = (struct hci_pcb *)so->so_pcb; - int err = 0; + int error; - if (pcb) - return EINVAL; + if (pcb) { + error = EINVAL; + goto out; + } - err = soreserve(so, hci_sendspace, hci_recvspace,NULL); - if (err) - return err; + error = soreserve(so, hci_sendspace, hci_recvspace,NULL); + if (error) + goto out; pcb = kmalloc(sizeof *pcb, M_PCB, M_NOWAIT | M_ZERO); - if (pcb == NULL) - return ENOMEM; + if (pcb == NULL) { + error = ENOMEM; + goto out; + } soreference(so); so->so_pcb = pcb; @@ -656,25 +655,32 @@ hci_sattach (struct socket *so, int proto, struct pru_attach_info *ai) crit_enter(); LIST_INSERT_HEAD(&hci_pcb, pcb, hp_next); crit_exit(); - - return 0; + error = 0; +out: + lwkt_replymsg(&msg->attach.base.lmsg, error); } -static int -hci_sbind (struct socket *so, struct sockaddr *nam, - struct thread *td) +static void +hci_sbind(netmsg_t msg) { + struct socket *so = msg->bind.base.nm_so; + struct sockaddr *nam = msg->bind.nm_nam; struct hci_pcb *pcb = (struct hci_pcb *)so->so_pcb; struct sockaddr_bt *sa; + int error; KKASSERT(nam != NULL); sa = (struct sockaddr_bt *)nam; - if (sa->bt_len != sizeof(struct sockaddr_bt)) - return EINVAL; + if (sa->bt_len != sizeof(struct sockaddr_bt)) { + error = EINVAL; + goto out; + } - if (sa->bt_family != AF_BLUETOOTH) - return EAFNOSUPPORT; + if (sa->bt_family != AF_BLUETOOTH) { + error = EAFNOSUPPORT; + goto out; + } bdaddr_copy(&pcb->hp_laddr, &sa->bt_bdaddr); @@ -682,37 +688,49 @@ hci_sbind (struct socket *so, struct sockaddr *nam, pcb->hp_flags |= HCI_PROMISCUOUS; else pcb->hp_flags &= ~HCI_PROMISCUOUS; - - return 0; + error = 0; +out: + lwkt_replymsg(&msg->bind.base.lmsg, error); } -static int -hci_sconnect (struct socket *so, struct sockaddr *nam, - struct thread *td) +static void +hci_sconnect(netmsg_t msg) { + struct socket *so = msg->connect.base.nm_so; + struct sockaddr *nam = msg->connect.nm_nam; struct hci_pcb *pcb = (struct hci_pcb *)so->so_pcb; struct sockaddr_bt *sa; + int error; + KKASSERT(nam != NULL); sa = (struct sockaddr_bt *)nam; - if (sa->bt_len != sizeof(struct sockaddr_bt)) - return EINVAL; - - if (sa->bt_family != AF_BLUETOOTH) - return EAFNOSUPPORT; + if (sa->bt_len != sizeof(struct sockaddr_bt)) { + error = EINVAL; + goto out; + } - if (hci_unit_lookup(&sa->bt_bdaddr) == NULL) - return EADDRNOTAVAIL; + if (sa->bt_family != AF_BLUETOOTH) { + error = EAFNOSUPPORT; + goto out; + } + if (hci_unit_lookup(&sa->bt_bdaddr) == NULL) { + error = EADDRNOTAVAIL; + goto out; + } bdaddr_copy(&pcb->hp_raddr, &sa->bt_bdaddr); soisconnected(so); - - return 0; + error = 0; +out: + lwkt_replymsg(&msg->connect.base.lmsg, error); } -static int -hci_speeraddr (struct socket *so, struct sockaddr **nam) +static void +hci_speeraddr(netmsg_t msg) { + struct socket *so = msg->peeraddr.base.nm_so; + struct sockaddr **nam = msg->peeraddr.nm_nam; struct hci_pcb *pcb = (struct hci_pcb *)so->so_pcb; struct sockaddr_bt *sa; @@ -724,12 +742,14 @@ hci_speeraddr (struct socket *so, struct sockaddr **nam) sa->bt_family = AF_BLUETOOTH; bdaddr_copy(&sa->bt_bdaddr, &pcb->hp_raddr); - return 0; + lwkt_replymsg(&msg->connect.base.lmsg, 0); } -static int -hci_ssockaddr (struct socket *so, struct sockaddr **nam) +static void +hci_ssockaddr(netmsg_t msg) { + struct socket *so = msg->sockaddr.base.nm_so; + struct sockaddr **nam = msg->sockaddr.nm_nam; struct hci_pcb *pcb = (struct hci_pcb *)so->so_pcb; struct sockaddr_bt *sa; @@ -741,69 +761,85 @@ hci_ssockaddr (struct socket *so, struct sockaddr **nam) sa->bt_family = AF_BLUETOOTH; bdaddr_copy(&sa->bt_bdaddr, &pcb->hp_laddr); - return 0; + lwkt_replymsg(&msg->connect.base.lmsg, 0); } -static int -hci_sshutdown (struct socket *so) +static void +hci_sshutdown(netmsg_t msg) { + struct socket *so = msg->shutdown.base.nm_so; + socantsendmore(so); - return 0; + lwkt_replymsg(&msg->connect.base.lmsg, 0); } -static int -hci_ssend (struct socket *so, int flags, struct mbuf *m, - struct sockaddr *addr, struct mbuf *control, - struct thread *td) +static void +hci_ssend(netmsg_t msg) { - int err = 0; + struct socket *so = msg->send.base.nm_so; + struct mbuf *m = msg->send.nm_m; + struct sockaddr *addr = msg->send.nm_addr; + struct mbuf *control = msg->send.nm_control; struct hci_pcb *pcb = (struct hci_pcb *)so->so_pcb; struct sockaddr_bt *sa; + int error; sa = NULL; if (addr) { sa = (struct sockaddr_bt *)addr; if (sa->bt_len != sizeof(struct sockaddr_bt)) { - err = EINVAL; - if (m) m_freem(m); - if (control) m_freem(control); - return err; + error = EINVAL; + goto out; } if (sa->bt_family != AF_BLUETOOTH) { - err = EAFNOSUPPORT; - if (m) m_freem(m); - if (control) m_freem(control); - return err; + error = EAFNOSUPPORT; + goto out; } } - if (control) /* have no use for this */ + /* have no use for this */ + if (control) { m_freem(control); + control = NULL; + } + error = hci_send(pcb, m, (sa ? &sa->bt_bdaddr : &pcb->hp_raddr)); + m = NULL; - return hci_send(pcb, m, (sa ? &sa->bt_bdaddr : &pcb->hp_raddr)); +out: + if (m) + m_freem(m); + if (control) + m_freem(control); + lwkt_replymsg(&msg->send.base.lmsg, error); } /* * get/set socket options */ -int -hci_ctloutput (struct socket *so, struct sockopt *sopt) +void +hci_ctloutput(netmsg_t msg) { + struct socket *so = msg->ctloutput.base.nm_so; + struct sockopt *sopt = msg->ctloutput.nm_sopt; struct hci_pcb *pcb = (struct hci_pcb *)so->so_pcb; int idir = 0; - int err = 0; + int error = 0; #ifdef notyet /* XXX */ DPRINTFN(2, "req %s\n", prcorequests[req]); #endif - if (pcb == NULL) - return EINVAL; + if (pcb == NULL) { + error = EINVAL; + goto out; + } - if (sopt->sopt_level != BTPROTO_HCI) - return ENOPROTOOPT; + if (sopt->sopt_level != BTPROTO_HCI) { + error = ENOPROTOOPT; + goto out; + } switch(sopt->sopt_dir) { case PRCO_GETOPT: @@ -827,7 +863,7 @@ hci_ctloutput (struct socket *so, struct sockopt *sopt) break; default: - err = ENOPROTOOPT; + error = ENOPROTOOPT; break; } break; @@ -835,21 +871,22 @@ hci_ctloutput (struct socket *so, struct sockopt *sopt) case PRCO_SETOPT: switch (sopt->sopt_name) { case SO_HCI_EVT_FILTER: /* set event filter */ - err = soopt_to_kbuf(sopt, &pcb->hp_efilter, + error = soopt_to_kbuf(sopt, &pcb->hp_efilter, sizeof(struct hci_filter), sizeof(struct hci_filter)); break; case SO_HCI_PKT_FILTER: /* set packet filter */ - err = soopt_to_kbuf(sopt, &pcb->hp_pfilter, - sizeof(struct hci_filter), - sizeof(struct hci_filter)); + error = soopt_to_kbuf(sopt, &pcb->hp_pfilter, + sizeof(struct hci_filter), + sizeof(struct hci_filter)); break; case SO_HCI_DIRECTION: /* request direction ctl messages */ - err = soopt_to_kbuf(sopt, &idir, sizeof(int), - sizeof(int)); - if (err) break; + error = soopt_to_kbuf(sopt, &idir, sizeof(int), + sizeof(int)); + if (error) + break; if (idir) pcb->hp_flags |= HCI_DIRECTION; else @@ -857,17 +894,17 @@ hci_ctloutput (struct socket *so, struct sockopt *sopt) break; default: - err = ENOPROTOOPT; + error = ENOPROTOOPT; break; } break; default: - err = ENOPROTOOPT; + error = ENOPROTOOPT; break; } - - return err; +out: + lwkt_replymsg(&msg->ctloutput.base.lmsg, error); } /* @@ -976,18 +1013,18 @@ hci_mtap(struct mbuf *m, struct hci_unit *unit) struct pr_usrreqs hci_usrreqs = { .pru_abort = hci_sabort, - .pru_accept = pru_accept_notsupp, + .pru_accept = pr_generic_notsupp, .pru_attach = hci_sattach, .pru_bind = hci_sbind, .pru_connect = hci_sconnect, - .pru_connect2 = pru_connect2_notsupp, + .pru_connect2 = pr_generic_notsupp, .pru_control = hci_scontrol, .pru_detach = hci_sdetach, .pru_disconnect = hci_sdisconnect, - .pru_listen = pru_listen_notsupp, + .pru_listen = pr_generic_notsupp, .pru_peeraddr = hci_speeraddr, - .pru_rcvd = pru_rcvd_notsupp, - .pru_rcvoob = pru_rcvoob_notsupp, + .pru_rcvd = pr_generic_notsupp, + .pru_rcvoob = pr_generic_notsupp, .pru_send = hci_ssend, .pru_sense = pru_sense_null, .pru_shutdown = hci_sshutdown, diff --git a/sys/netbt/l2cap.h b/sys/netbt/l2cap.h index 55147f0ed6..fe2286a48e 100644 --- a/sys/netbt/l2cap.h +++ b/sys/netbt/l2cap.h @@ -446,6 +446,7 @@ struct l2cap_pdu { extern struct pr_usrreqs l2cap_usrreqs; struct socket; struct mbuf; +union netmsg; /* l2cap_lower.c */ void l2cap_close(struct l2cap_channel *, int); @@ -471,7 +472,7 @@ int l2cap_send_connect_rsp(struct hci_link *, uint8_t, uint16_t, uint16_t, uint1 /* l2cap_socket.c */ int l2cap_usrreq(struct socket *, int, struct mbuf *, struct mbuf *, struct mbuf *); -int l2cap_ctloutput(struct socket *, struct sockopt *); +void l2cap_ctloutput(union netmsg *); /* l2cap_upper.c */ int l2cap_attach(struct l2cap_channel **, const struct btproto *, void *); diff --git a/sys/netbt/l2cap_socket.c b/sys/netbt/l2cap_socket.c index 355479f683..fe7bf2f9e2 100644 --- a/sys/netbt/l2cap_socket.c +++ b/sys/netbt/l2cap_socket.c @@ -46,6 +46,9 @@ #include #include #include + +#include + #include #include @@ -88,49 +91,55 @@ int l2cap_recvspace = 4096; * Apply configuration commands to channel. This corresponds to * "Reconfigure Channel Request" in the L2CAP specification. */ -int -l2cap_ctloutput(struct socket *so, struct sockopt *sopt) +void +l2cap_ctloutput(netmsg_t msg) { + struct socket *so = msg->ctloutput.base.nm_so; + struct sockopt *sopt = msg->ctloutput.nm_sopt; struct l2cap_channel *pcb = (struct l2cap_channel *) so->so_pcb; struct mbuf *m; - int err = 0; + int error = 0; #ifdef notyet /* XXX */ DPRINTFN(2, "%s\n", prcorequests[req]); #endif - if (pcb == NULL) - return EINVAL; + if (pcb == NULL) { + error = EINVAL; + goto out; + } - if (sopt->sopt_level != BTPROTO_L2CAP) - return ENOPROTOOPT; + if (sopt->sopt_level != BTPROTO_L2CAP) { + error = ENOPROTOOPT; + goto out; + } switch(sopt->sopt_dir) { case PRCO_GETOPT: m = m_get(M_NOWAIT, MT_DATA); if (m == NULL) { - err = ENOMEM; + error = ENOMEM; break; } m->m_len = l2cap_getopt(pcb, sopt->sopt_name, mtod(m, void *)); if (m->m_len == 0) { m_freem(m); m = NULL; - err = ENOPROTOOPT; + error = ENOPROTOOPT; } soopt_from_kbuf(sopt, mtod(m, void *), m->m_len); break; case PRCO_SETOPT: - err = l2cap_setopt2(pcb, sopt->sopt_name, so, sopt); + error = l2cap_setopt2(pcb, sopt->sopt_name, so, sopt); break; default: - err = ENOPROTOOPT; + error = ENOPROTOOPT; break; } - - return err; +out: + lwkt_replymsg(&msg->ctloutput.base.lmsg, error); } /********************************************************************** @@ -235,193 +244,228 @@ l2cap_input(void *arg, struct mbuf *m) /* * Implementation of usrreqs. */ -static int -l2cap_sdetach(struct socket *so) +static void +l2cap_sdetach(netmsg_t msg) { - return l2cap_detach((struct l2cap_channel **)&so->so_pcb); + struct socket *so = msg->detach.base.nm_so; + int error; + + error = l2cap_detach((struct l2cap_channel **)&so->so_pcb); + lwkt_replymsg(&msg->detach.base.lmsg, error); } /* * NOTE: (so) is referenced from soabort*() and netmsg_pru_abort() * will sofree() it when we return. */ -static int -l2cap_sabort (struct socket *so) +static void +l2cap_sabort(netmsg_t msg) { + struct socket *so = msg->abort.base.nm_so; struct l2cap_channel *pcb = so->so_pcb; - int error; l2cap_disconnect(pcb, 0); soisdisconnected(so); - error = l2cap_sdetach(so); - return error; + l2cap_sdetach(msg); + /* msg invalid now */ } -static int -l2cap_sdisconnect (struct socket *so) +static void +l2cap_sdisconnect(netmsg_t msg) { + struct socket *so = msg->disconnect.base.nm_so; struct l2cap_channel *pcb = so->so_pcb; + int error; soisdisconnecting(so); - return l2cap_disconnect(pcb, so->so_linger); + error = l2cap_disconnect(pcb, so->so_linger); + lwkt_replymsg(&msg->disconnect.base.lmsg, error); } -static int -l2cap_scontrol (struct socket *so, u_long cmd, caddr_t data, - struct ifnet *ifp, struct thread *td) +static void +l2cap_scontrol(netmsg_t msg) { - return EPASSTHROUGH; + lwkt_replymsg(&msg->control.base.lmsg, EPASSTHROUGH); } -static int -l2cap_sattach (struct socket *so, int proto, - struct pru_attach_info *ai) +static void +l2cap_sattach(netmsg_t msg) { + struct socket *so = msg->attach.base.nm_so; struct l2cap_channel *pcb = so->so_pcb; - int err = 0; + int error; - if (pcb != NULL) - return EINVAL; + if (pcb != NULL) { + error = EINVAL; + goto out; + } /* * For L2CAP socket PCB we just use an l2cap_channel structure * since we have nothing to add.. */ - err = soreserve(so, l2cap_sendspace, l2cap_recvspace, NULL); - if (err) - return err; - - return l2cap_attach((struct l2cap_channel **)&so->so_pcb, - &l2cap_proto, so); + error = soreserve(so, l2cap_sendspace, l2cap_recvspace, NULL); + if (error == 0) { + error = l2cap_attach((struct l2cap_channel **)&so->so_pcb, + &l2cap_proto, so); + } +out: + lwkt_replymsg(&msg->attach.base.lmsg, error); } -static int -l2cap_sbind (struct socket *so, struct sockaddr *nam, - struct thread *td) +static void +l2cap_sbind (netmsg_t msg) { + struct socket *so = msg->bind.base.nm_so; + struct sockaddr *nam = msg->bind.nm_nam; struct l2cap_channel *pcb = so->so_pcb; struct sockaddr_bt *sa; + int error; KKASSERT(nam != NULL); sa = (struct sockaddr_bt *)nam; - if (sa->bt_len != sizeof(struct sockaddr_bt)) - return EINVAL; - - if (sa->bt_family != AF_BLUETOOTH) - return EAFNOSUPPORT; - - return l2cap_bind(pcb, sa); + if (sa->bt_len != sizeof(struct sockaddr_bt)) { + error = EINVAL; + } else if (sa->bt_family != AF_BLUETOOTH) { + error = EAFNOSUPPORT; + } else { + error = l2cap_bind(pcb, sa); + } + lwkt_replymsg(&msg->bind.base.lmsg, error); } -static int -l2cap_sconnect (struct socket *so, struct sockaddr *nam, - struct thread *td) +static void +l2cap_sconnect(netmsg_t msg) { + struct socket *so = msg->connect.base.nm_so; + struct sockaddr *nam = msg->connect.nm_nam; struct l2cap_channel *pcb = so->so_pcb; struct sockaddr_bt *sa; + int error; KKASSERT(nam != NULL); sa = (struct sockaddr_bt *)nam; - if (sa->bt_len != sizeof(struct sockaddr_bt)) - return EINVAL; - - if (sa->bt_family != AF_BLUETOOTH) - return EAFNOSUPPORT; - - soisconnecting(so); - return l2cap_connect(pcb, sa); + if (sa->bt_len != sizeof(struct sockaddr_bt)) { + error = EINVAL; + } else if (sa->bt_family != AF_BLUETOOTH) { + error = EAFNOSUPPORT; + } else { + soisconnecting(so); + error = l2cap_connect(pcb, sa); + } + lwkt_replymsg(&msg->connect.base.lmsg, error); } -static int -l2cap_speeraddr (struct socket *so, struct sockaddr **nam) +static void +l2cap_speeraddr(netmsg_t msg) { + struct socket *so = msg->peeraddr.base.nm_so; + struct sockaddr **nam = msg->peeraddr.nm_nam; struct l2cap_channel *pcb = so->so_pcb; struct sockaddr_bt *sa, ssa; - int e; + int error; sa = &ssa; bzero(sa, sizeof *sa); sa->bt_len = sizeof(struct sockaddr_bt); sa->bt_family = AF_BLUETOOTH; - e = l2cap_peeraddr(pcb, sa); + error = l2cap_peeraddr(pcb, sa); *nam = dup_sockaddr((struct sockaddr *)sa); - return (e); + lwkt_replymsg(&msg->peeraddr.base.lmsg, error); } -static int -l2cap_ssockaddr (struct socket *so, struct sockaddr **nam) +static void +l2cap_ssockaddr(netmsg_t msg) { + struct socket *so = msg->sockaddr.base.nm_so; + struct sockaddr **nam = msg->sockaddr.nm_nam; struct l2cap_channel *pcb = so->so_pcb; struct sockaddr_bt *sa, ssa; - int e; + int error; sa = &ssa; bzero(sa, sizeof *sa); sa->bt_len = sizeof(struct sockaddr_bt); sa->bt_family = AF_BLUETOOTH; - e = l2cap_sockaddr(pcb, sa); + error = l2cap_sockaddr(pcb, sa); *nam = dup_sockaddr((struct sockaddr *)sa); - return (e); + lwkt_replymsg(&msg->sockaddr.base.lmsg, error); } -static int -l2cap_sshutdown (struct socket *so) +static void +l2cap_sshutdown(netmsg_t msg) { + struct socket *so = msg->shutdown.base.nm_so; + socantsendmore(so); - return 0; + + lwkt_replymsg(&msg->shutdown.base.lmsg, 0); } -static int -l2cap_ssend (struct socket *so, int flags, struct mbuf *m, - struct sockaddr *addr, struct mbuf *control, struct thread *td) +static void +l2cap_ssend(netmsg_t msg) { + struct socket *so = msg->send.base.nm_so; + struct mbuf *m = msg->send.nm_m; + struct mbuf *control = msg->send.nm_control; struct l2cap_channel *pcb = so->so_pcb; struct mbuf *m0; - - int err = 0; + int error; KKASSERT(m != NULL); - if (m->m_pkthdr.len == 0) - goto error; + if (m->m_pkthdr.len == 0) { + error = 0; + goto out; + } if (m->m_pkthdr.len > pcb->lc_omtu) { - err = EMSGSIZE; - goto error; + error = EMSGSIZE; + goto out; } m0 = m_copym(m, 0, M_COPYALL, MB_DONTWAIT); if (m0 == NULL) { - err = ENOMEM; - goto error; + error = ENOMEM; + goto out; } - if (control) /* no use for that */ - m_freem(control); + m0 = m_copym(m, 0, M_COPYALL, MB_DONTWAIT); + if (m0 == NULL) { + error = ENOMEM; + goto out; + } + /* no use for that */ + if (control) { + m_freem(control); + control = NULL; + } sbappendrecord(&so->so_snd.sb, m); - return l2cap_send(pcb, m0); - -error: + error = l2cap_send(pcb, m0); + m = NULL; +out: if (m) m_freem(m); if (control) m_freem(control); - return err; + lwkt_replymsg(&msg->send.base.lmsg, error); } -static int -l2cap_saccept(struct socket *so, struct sockaddr **nam) +static void +l2cap_saccept(netmsg_t msg) { + struct socket *so = msg->accept.base.nm_so; + struct sockaddr **nam = msg->accept.nm_nam; struct l2cap_channel *pcb = so->so_pcb; struct sockaddr_bt sa; - int e; + int error; KKASSERT(nam != NULL); @@ -429,10 +473,10 @@ l2cap_saccept(struct socket *so, struct sockaddr **nam) sa.bt_len = sizeof(struct sockaddr_bt); sa.bt_family = AF_BLUETOOTH; - e = l2cap_peeraddr(pcb, &sa); + error = l2cap_peeraddr(pcb, &sa); *nam = dup_sockaddr((struct sockaddr *)&sa); - return e; + lwkt_replymsg(&msg->accept.base.lmsg, error); } static int @@ -449,14 +493,14 @@ struct pr_usrreqs l2cap_usrreqs = { .pru_attach = l2cap_sattach, .pru_bind = l2cap_sbind, .pru_connect = l2cap_sconnect, - .pru_connect2 = pru_connect2_notsupp, + .pru_connect2 = pr_generic_notsupp, .pru_control = l2cap_scontrol, .pru_detach = l2cap_sdetach, .pru_disconnect = l2cap_sdisconnect, .pru_listen = l2cap_slisten, .pru_peeraddr = l2cap_speeraddr, - .pru_rcvd = pru_rcvd_notsupp, - .pru_rcvoob = pru_rcvoob_notsupp, + .pru_rcvd = pr_generic_notsupp, + .pru_rcvoob = pr_generic_notsupp, .pru_send = l2cap_ssend, .pru_sense = pru_sense_null, .pru_shutdown = l2cap_sshutdown, diff --git a/sys/netbt/rfcomm.h b/sys/netbt/rfcomm.h index 54134617d2..ff9c324ad5 100644 --- a/sys/netbt/rfcomm.h +++ b/sys/netbt/rfcomm.h @@ -385,6 +385,7 @@ struct rfcomm_dlc { extern struct pr_usrreqs rfcomm_usrreqs; struct socket; +union netmsg; /* rfcomm_dlc.c */ struct rfcomm_dlc *rfcomm_dlc_lookup(struct rfcomm_session *, int); @@ -408,7 +409,7 @@ void rfcomm_session_timeout(void *); /* rfcomm_socket.c */ int rfcomm_usrreq(struct socket *, int, struct mbuf *, struct mbuf *, struct mbuf *); -int rfcomm_ctloutput(struct socket *so, struct sockopt *sopt); +void rfcomm_ctloutput(union netmsg *); /* rfcomm_upper.c */ int rfcomm_attach(struct rfcomm_dlc **, const struct btproto *, void *); diff --git a/sys/netbt/rfcomm_socket.c b/sys/netbt/rfcomm_socket.c index 78664fa579..18bf2d53dc 100644 --- a/sys/netbt/rfcomm_socket.c +++ b/sys/netbt/rfcomm_socket.c @@ -48,6 +48,9 @@ #include #include #include + +#include + #include #include @@ -86,22 +89,28 @@ int rfcomm_recvspace = 4096; * rfcomm_ctloutput(request, socket, level, optname, opt) * */ -int -rfcomm_ctloutput(struct socket *so, struct sockopt *sopt) +void +rfcomm_ctloutput(netmsg_t msg) { + struct socket *so = msg->ctloutput.base.nm_so; + struct sockopt *sopt = msg->ctloutput.nm_sopt; struct rfcomm_dlc *pcb = (struct rfcomm_dlc *) so->so_pcb; struct mbuf *m; - int err = 0; + int error = 0; #ifdef notyet /* XXX */ DPRINTFN(2, "%s\n", prcorequests[sopt->sopt_dir]); #endif - if (pcb == NULL) - return EINVAL; + if (pcb == NULL) { + error = EINVAL; + goto out; + } - if (sopt->sopt_level != BTPROTO_RFCOMM) - return ENOPROTOOPT; + if (sopt->sopt_level != BTPROTO_RFCOMM) { + error = ENOPROTOOPT; + goto out; + } switch(sopt->sopt_dir) { case PRCO_GETOPT: @@ -112,22 +121,22 @@ rfcomm_ctloutput(struct socket *so, struct sockopt *sopt) if (m->m_len == 0) { m_freem(m); m = NULL; - err = ENOPROTOOPT; + error = ENOPROTOOPT; } soopt_from_kbuf(sopt, mtod(m, void *), m->m_len); break; case PRCO_SETOPT: - err = rfcomm_setopt2(pcb, sopt->sopt_name, so, sopt); + error = rfcomm_setopt2(pcb, sopt->sopt_name, so, sopt); break; default: - err = ENOPROTOOPT; + error = ENOPROTOOPT; break; } - - return err; +out: + lwkt_replymsg(&msg->ctloutput.base.lmsg, error); } /********************************************************************** @@ -245,203 +254,241 @@ rfcomm_input(void *arg, struct mbuf *m) /* * Implementation of usrreqs. */ -static int -rfcomm_sdetach(struct socket *so) +static void +rfcomm_sdetach(netmsg_t msg) { - return rfcomm_detach((struct rfcomm_dlc **)&so->so_pcb); + struct socket *so = msg->detach.base.nm_so; + int error; + + error = rfcomm_detach((struct rfcomm_dlc **)&so->so_pcb); + lwkt_replymsg(&msg->detach.base.lmsg, error); } /* * NOTE: (so) is referenced from soabort*() and netmsg_pru_abort() * will sofree() it when we return. */ -static int -rfcomm_sabort (struct socket *so) +static void +rfcomm_sabort(netmsg_t msg) { + struct socket *so = msg->abort.base.nm_so; struct rfcomm_dlc *pcb = (struct rfcomm_dlc *) so->so_pcb; - int error; rfcomm_disconnect(pcb, 0); soisdisconnected(so); - error = rfcomm_sdetach(so); - return error; + rfcomm_sdetach(msg); + /* msg invalid now */ } -static int -rfcomm_sdisconnect (struct socket *so) +static void +rfcomm_sdisconnect(netmsg_t msg) { + struct socket *so = msg->abort.base.nm_so; struct rfcomm_dlc *pcb = (struct rfcomm_dlc *) so->so_pcb; + int error; soisdisconnecting(so); - return rfcomm_disconnect(pcb, so->so_linger); + error = rfcomm_disconnect(pcb, so->so_linger); + lwkt_replymsg(&msg->disconnect.base.lmsg, error); } -static int -rfcomm_scontrol (struct socket *so, u_long cmd, caddr_t data, - struct ifnet *ifp, struct thread *td) +static void +rfcomm_scontrol(netmsg_t msg) { - return EPASSTHROUGH; + lwkt_replymsg(&msg->control.base.lmsg, EPASSTHROUGH); } -static int -rfcomm_sattach (struct socket *so, int proto, - struct pru_attach_info *ai) +static void +rfcomm_sattach(netmsg_t msg) { + struct socket *so = msg->attach.base.nm_so; struct rfcomm_dlc *pcb = (struct rfcomm_dlc *) so->so_pcb; + int error; - int err=0; - if (pcb != NULL) - return EINVAL; + if (pcb != NULL) { + error = EINVAL; + goto out; + } /* * Since we have nothing to add, we attach the DLC * structure directly to our PCB pointer. */ - err = soreserve(so, rfcomm_sendspace, rfcomm_recvspace, NULL); - if (err) - return err; + error = soreserve(so, rfcomm_sendspace, rfcomm_recvspace, NULL); + if (error) + goto out; - err = rfcomm_attach((struct rfcomm_dlc **)&so->so_pcb, - &rfcomm_proto, so); - if (err) - return err; + error = rfcomm_attach((struct rfcomm_dlc **)&so->so_pcb, + &rfcomm_proto, so); + if (error) + goto out; - err = rfcomm_rcvd(so->so_pcb, sbspace(&so->so_rcv)); - if (err) { + error = rfcomm_rcvd(so->so_pcb, sbspace(&so->so_rcv)); + if (error) rfcomm_detach((struct rfcomm_dlc **)&so->so_pcb); - return err; - } - - return 0; +out: + lwkt_replymsg(&msg->attach.base.lmsg, error); } -static int -rfcomm_sbind (struct socket *so, struct sockaddr *nam, - struct thread *td) +static void +rfcomm_sbind(netmsg_t msg) { + struct socket *so = msg->bind.base.nm_so; + struct sockaddr *nam = msg->bind.nm_nam; struct rfcomm_dlc *pcb = (struct rfcomm_dlc *) so->so_pcb; struct sockaddr_bt *sa; + int error; KKASSERT(nam != NULL); sa = (struct sockaddr_bt *)nam; - if (sa->bt_len != sizeof(struct sockaddr_bt)) - return EINVAL; - - if (sa->bt_family != AF_BLUETOOTH) - return EAFNOSUPPORT; - - return rfcomm_bind(pcb, sa); + if (sa->bt_len != sizeof(struct sockaddr_bt)) { + error = EINVAL; + } else if (sa->bt_family != AF_BLUETOOTH) { + error = EAFNOSUPPORT; + } else { + error = rfcomm_bind(pcb, sa); + } + lwkt_replymsg(&msg->bind.base.lmsg, error); } -static int -rfcomm_sconnect (struct socket *so, struct sockaddr *nam, - struct thread *td) +static void +rfcomm_sconnect(netmsg_t msg) { + struct socket *so = msg->connect.base.nm_so; + struct sockaddr *nam = msg->connect.nm_nam; struct rfcomm_dlc *pcb = (struct rfcomm_dlc *) so->so_pcb; struct sockaddr_bt *sa; + int error; KKASSERT(nam != NULL); sa = (struct sockaddr_bt *)nam; - if (sa->bt_len != sizeof(struct sockaddr_bt)) - return EINVAL; - - if (sa->bt_family != AF_BLUETOOTH) - return EAFNOSUPPORT; - - soisconnecting(so); - return rfcomm_connect(pcb, sa); + if (sa->bt_len != sizeof(struct sockaddr_bt)) { + error = EINVAL; + } else if (sa->bt_family != AF_BLUETOOTH) { + error = EAFNOSUPPORT; + } else { + soisconnecting(so); + error = rfcomm_connect(pcb, sa); + } + lwkt_replymsg(&msg->connect.base.lmsg, error); } -static int -rfcomm_speeraddr (struct socket *so, struct sockaddr **nam) +static void +rfcomm_speeraddr(netmsg_t msg) { + struct socket *so = msg->peeraddr.base.nm_so; + struct sockaddr **nam = msg->peeraddr.nm_nam; struct rfcomm_dlc *pcb = (struct rfcomm_dlc *) so->so_pcb; struct sockaddr_bt *sa, ssa; - int e; + int error; sa = &ssa; bzero(sa, sizeof *sa); sa->bt_len = sizeof(struct sockaddr_bt); sa->bt_family = AF_BLUETOOTH; - e = rfcomm_peeraddr(pcb, sa);; + error = rfcomm_peeraddr(pcb, sa);; *nam = dup_sockaddr((struct sockaddr *)sa); - return (e); + + lwkt_replymsg(&msg->peeraddr.base.lmsg, error); } -static int -rfcomm_ssockaddr (struct socket *so, struct sockaddr **nam) +static void +rfcomm_ssockaddr(netmsg_t msg) { + struct socket *so = msg->sockaddr.base.nm_so; + struct sockaddr **nam = msg->sockaddr.nm_nam; struct rfcomm_dlc *pcb = (struct rfcomm_dlc *) so->so_pcb; struct sockaddr_bt *sa, ssa; - int e; + int error; sa = &ssa; bzero(sa, sizeof *sa); sa->bt_len = sizeof(struct sockaddr_bt); sa->bt_family = AF_BLUETOOTH; - e = rfcomm_sockaddr(pcb, sa);; + error = rfcomm_sockaddr(pcb, sa);; *nam = dup_sockaddr((struct sockaddr *)sa); - return (e); + + lwkt_replymsg(&msg->sockaddr.base.lmsg, error); } -static int -rfcomm_sshutdown (struct socket *so) +static void +rfcomm_sshutdown(netmsg_t msg) { + struct socket *so = msg->shutdown.base.nm_so; + socantsendmore(so); - return 0; + lwkt_replymsg(&msg->shutdown.base.lmsg, 0); } -static int -rfcomm_ssend (struct socket *so, int flags, struct mbuf *m, - struct sockaddr *addr, struct mbuf *control, struct thread *td) +static void +rfcomm_ssend(netmsg_t msg) { + struct socket *so = msg->send.base.nm_so; + struct mbuf *m = msg->send.nm_m; + struct mbuf *control = msg->send.nm_control; struct rfcomm_dlc *pcb = (struct rfcomm_dlc *) so->so_pcb; struct mbuf *m0; + int error; KKASSERT(m != NULL); - if (control) /* no use for that */ + /* no use for that */ + if (control) { m_freem(control); + control = NULL; + } m0 = m_copym(m, 0, M_COPYALL, MB_DONTWAIT); - if (m0 == NULL) - return ENOMEM; - - sbappendstream(&so->so_snd.sb, m); - - return rfcomm_send(pcb, m0); + if (m0) { + sbappendstream(&so->so_snd.sb, m); + error = rfcomm_send(pcb, m0); + } else { + error = ENOMEM; + } + lwkt_replymsg(&msg->send.base.lmsg, error); } -static int -rfcomm_saccept(struct socket *so, struct sockaddr **nam) +static void +rfcomm_saccept(netmsg_t msg) { + struct socket *so = msg->accept.base.nm_so; + struct sockaddr **nam = msg->accept.nm_nam; struct rfcomm_dlc *pcb = (struct rfcomm_dlc *) so->so_pcb; struct sockaddr_bt *sa, ssa; - int e; + int error; sa = &ssa; bzero(sa, sizeof *sa); sa->bt_len = sizeof(struct sockaddr_bt); sa->bt_family = AF_BLUETOOTH; - e = rfcomm_peeraddr(pcb, sa);; + error = rfcomm_peeraddr(pcb, sa);; *nam = dup_sockaddr((struct sockaddr *)sa); - return (e); + + lwkt_replymsg(&msg->accept.base.lmsg, error); } -static int -rfcomm_slisten(struct socket *so, struct thread *td) +static void +rfcomm_slisten(netmsg_t msg) { - struct rfcomm_dlc *pcb = (struct rfcomm_dlc *) so->so_pcb; - return rfcomm_listen(pcb); + struct socket *so = msg->listen.base.nm_so; + struct rfcomm_dlc *pcb = (struct rfcomm_dlc *)so->so_pcb; + int error; + + error = rfcomm_listen(pcb); + lwkt_replymsg(&msg->listen.base.lmsg, error); } -static int -rfcomm_srcvd(struct socket *so, int flags) +static void +rfcomm_srcvd(netmsg_t msg) { + struct socket *so = msg->rcvd.base.nm_so; struct rfcomm_dlc *pcb = (struct rfcomm_dlc *) so->so_pcb; - return rfcomm_rcvd(pcb, sbspace(&so->so_rcv)); + int error; + + error = rfcomm_rcvd(pcb, sbspace(&so->so_rcv)); + lwkt_replymsg(&msg->rcvd.base.lmsg, error); } struct pr_usrreqs rfcomm_usrreqs = { @@ -450,14 +497,14 @@ struct pr_usrreqs rfcomm_usrreqs = { .pru_attach = rfcomm_sattach, .pru_bind = rfcomm_sbind, .pru_connect = rfcomm_sconnect, - .pru_connect2 = pru_connect2_notsupp, + .pru_connect2 = pr_generic_notsupp, .pru_control = rfcomm_scontrol, .pru_detach = rfcomm_sdetach, .pru_disconnect = rfcomm_sdisconnect, .pru_listen = rfcomm_slisten, .pru_peeraddr = rfcomm_speeraddr, .pru_rcvd = rfcomm_srcvd, - .pru_rcvoob = pru_rcvoob_notsupp, + .pru_rcvoob = pr_generic_notsupp, .pru_send = rfcomm_ssend, .pru_sense = pru_sense_null, .pru_shutdown = rfcomm_sshutdown, diff --git a/sys/netbt/sco.h b/sys/netbt/sco.h index c6d734386c..1821dc9322 100644 --- a/sys/netbt/sco.h +++ b/sys/netbt/sco.h @@ -63,12 +63,14 @@ extern struct sco_pcb_list sco_pcb; /* sco_socket.c */ struct socket; +union netmsg; + extern struct pr_usrreqs sco_usrreqs; extern int sco_sendspace; extern int sco_recvspace; int sco_usrreq(struct socket *, int, struct mbuf *, struct mbuf *, struct mbuf *); -int sco_ctloutput(struct socket *so, struct sockopt *sopt); +void sco_ctloutput(union netmsg *); /* sco_upper.c */ int sco_attach(struct sco_pcb **, const struct btproto *, void *); diff --git a/sys/netbt/sco_socket.c b/sys/netbt/sco_socket.c index 09cfb2f289..701d5bdafe 100644 --- a/sys/netbt/sco_socket.c +++ b/sys/netbt/sco_socket.c @@ -1,6 +1,3 @@ -/* $OpenBSD: sco_socket.c,v 1.1 2007/06/01 02:46:12 uwe Exp $ */ -/* $NetBSD: sco_socket.c,v 1.9 2007/04/21 06:15:23 plunky Exp $ */ - /*- * Copyright (c) 2006 Itronix Inc. * All rights reserved. @@ -28,6 +25,9 @@ * CONTRACT, STRICT LIABILITY, OR TORT (INCLUDING NEGLIGENCE OR OTHERWISE) * ARISING IN ANY WAY OUT OF THE USE OF THIS SOFTWARE, EVEN IF ADVISED OF THE * POSSIBILITY OF SUCH DAMAGE. + * + * $OpenBSD: sco_socket.c,v 1.1 2007/06/01 02:46:12 uwe Exp $ + * $NetBSD: sco_socket.c,v 1.9 2007/04/21 06:15:23 plunky Exp $ */ /* load symbolic names */ @@ -47,6 +47,8 @@ #include #include +#include + #include #include #include @@ -80,9 +82,11 @@ int sco_recvspace = 4096; /* * get/set socket options */ -int -sco_ctloutput(struct socket *so, struct sockopt *sopt) +void +sco_ctloutput(netmsg_t msg) { + struct socket *so = msg->ctloutput.base.nm_so; + struct sockopt *sopt = msg->ctloutput.nm_sopt; struct sco_pcb *pcb = (struct sco_pcb *)so->so_pcb; struct mbuf *m; int err = 0; @@ -91,11 +95,15 @@ sco_ctloutput(struct socket *so, struct sockopt *sopt) DPRINTFN(2, "req %s\n", prcorequests[req]); #endif - if (pcb == NULL) - return EINVAL; + if (pcb == NULL) { + err = EINVAL; + goto out; + } - if (sopt->sopt_level != BTPROTO_SCO) - return ENOPROTOOPT; + if (sopt->sopt_level != BTPROTO_SCO) { + err = ENOPROTOOPT; + goto out; + } switch(sopt->sopt_dir) { case PRCO_GETOPT: @@ -130,8 +138,8 @@ sco_ctloutput(struct socket *so, struct sockopt *sopt) err = ENOPROTOOPT; break; } - - return err; +out: + lwkt_replymsg(&msg->ctloutput.base.lmsg, err); } /***************************************************************************** @@ -222,196 +230,225 @@ sco_input(void *arg, struct mbuf *m) /* * Implementation of usrreqs. */ -static int -sco_sdetach(struct socket *so) +static void +sco_sdetach(netmsg_t msg) { - return sco_detach((struct sco_pcb **)&so->so_pcb); + struct socket *so = msg->detach.base.nm_so;; + int error; + + error = sco_detach((struct sco_pcb **)&so->so_pcb); + lwkt_replymsg(&msg->detach.base.lmsg, error); } /* * NOTE: (so) is referenced from soabort*() and netmsg_pru_abort() * will sofree() it when we return. */ -static int -sco_sabort (struct socket *so) +static void +sco_sabort (netmsg_t msg) { + struct socket *so = msg->abort.base.nm_so; struct sco_pcb *pcb = (struct sco_pcb *)so->so_pcb; - int error; sco_disconnect(pcb, 0); soisdisconnected(so); - error = sco_sdetach(so); - - return error; + sco_sdetach(msg); + /* msg invalid now */ } -static int -sco_sdisconnect (struct socket *so) +static void +sco_sdisconnect (netmsg_t msg) { + struct socket *so = msg->abort.base.nm_so; struct sco_pcb *pcb = (struct sco_pcb *)so->so_pcb; + int error; soisdisconnecting(so); - return sco_disconnect(pcb, so->so_linger); + error = sco_disconnect(pcb, so->so_linger); + lwkt_replymsg(&msg->disconnect.base.lmsg, error); } -static int -sco_sattach (struct socket *so, int proto, - struct pru_attach_info *ai) +static void +sco_sattach(netmsg_t msg) { + struct socket *so = msg->attach.base.nm_so; struct sco_pcb *pcb = (struct sco_pcb *)so->so_pcb; - int err=0; - - if (pcb) - return EINVAL; - - err = soreserve(so, sco_sendspace, sco_recvspace,NULL); - if (err) - return err; + int error; - return sco_attach((struct sco_pcb **)&so->so_pcb, - &sco_proto, so); + if (pcb) { + error = EINVAL; + } else { + error = soreserve(so, sco_sendspace, sco_recvspace,NULL); + if (error == 0) { + error = sco_attach((struct sco_pcb **)&so->so_pcb, + &sco_proto, so); + } + } + lwkt_replymsg(&msg->attach.base.lmsg, error); } -static int -sco_sbind (struct socket *so, struct sockaddr *nam, - struct thread *td) +static void +sco_sbind(netmsg_t msg) { + struct socket *so = msg->bind.base.nm_so; + struct sockaddr *nam = msg->bind.nm_nam; struct sco_pcb *pcb = (struct sco_pcb *)so->so_pcb; struct sockaddr_bt *sa; + int error; KKASSERT(nam != NULL); sa = (struct sockaddr_bt *)nam; - if (sa->bt_len != sizeof(struct sockaddr_bt)) - return EINVAL; - - if (sa->bt_family != AF_BLUETOOTH) - return EAFNOSUPPORT; - - return sco_bind(pcb, sa); + if (sa->bt_len != sizeof(struct sockaddr_bt)) { + error = EINVAL; + } else if (sa->bt_family != AF_BLUETOOTH) { + error = EAFNOSUPPORT; + } else { + error = sco_bind(pcb, sa); + } + lwkt_replymsg(&msg->bind.base.lmsg, error); } -static int -sco_sconnect (struct socket *so, struct sockaddr *nam, - struct thread *td) +static void +sco_sconnect(netmsg_t msg) { + struct socket *so = msg->connect.base.nm_so; + struct sockaddr *nam = msg->connect.nm_nam; struct sco_pcb *pcb = (struct sco_pcb *)so->so_pcb; struct sockaddr_bt *sa; + int error; KKASSERT(nam != NULL); sa = (struct sockaddr_bt *)nam; - if (sa->bt_len != sizeof(struct sockaddr_bt)) - return EINVAL; - - if (sa->bt_family != AF_BLUETOOTH) - return EAFNOSUPPORT; - - soisconnecting(so); - return sco_connect(pcb, sa); + if (sa->bt_len != sizeof(struct sockaddr_bt)) { + error = EINVAL; + } else if (sa->bt_family != AF_BLUETOOTH) { + error = EAFNOSUPPORT; + } else { + soisconnecting(so); + error = sco_connect(pcb, sa); + } + lwkt_replymsg(&msg->connect.base.lmsg, error); } -static int -sco_speeraddr (struct socket *so, struct sockaddr **nam) +static void +sco_speeraddr(netmsg_t msg) { + struct socket *so = msg->peeraddr.base.nm_so; + struct sockaddr **nam = msg->peeraddr.nm_nam; struct sco_pcb *pcb = (struct sco_pcb *)so->so_pcb; struct sockaddr_bt *sa, ssa; - int e; + int error; sa = &ssa; bzero(sa, sizeof *sa); sa->bt_len = sizeof(struct sockaddr_bt); sa->bt_family = AF_BLUETOOTH; - e = sco_peeraddr(pcb, sa); + error = sco_peeraddr(pcb, sa); *nam = dup_sockaddr((struct sockaddr *)sa); - - return (e); + lwkt_replymsg(&msg->peeraddr.base.lmsg, error); } -static int -sco_ssockaddr (struct socket *so, struct sockaddr **nam) +static void +sco_ssockaddr(netmsg_t msg) { + struct socket *so = msg->sockaddr.base.nm_so; + struct sockaddr **nam = msg->sockaddr.nm_nam; struct sco_pcb *pcb = (struct sco_pcb *)so->so_pcb; struct sockaddr_bt *sa, ssa; - int e; + int error; sa = &ssa; bzero(sa, sizeof *sa); sa->bt_len = sizeof(struct sockaddr_bt); sa->bt_family = AF_BLUETOOTH; - e = sco_sockaddr(pcb, sa); + error = sco_sockaddr(pcb, sa); *nam = dup_sockaddr((struct sockaddr *)sa); - return (e); + lwkt_replymsg(&msg->sockaddr.base.lmsg, error); } -static int -sco_sshutdown (struct socket *so) +static void +sco_sshutdown(netmsg_t msg) { - socantsendmore(so); - return 0; + socantsendmore(msg->shutdown.base.nm_so); + lwkt_replymsg(&msg->shutdown.base.lmsg, 0); } -static int -sco_ssend (struct socket *so, int flags, struct mbuf *m, - struct sockaddr *addr, struct mbuf *control, struct thread *td) +static void +sco_ssend(netmsg_t msg) { + struct socket *so = msg->send.base.nm_so; + struct mbuf *m = msg->send.nm_m; + struct sockaddr *addr = msg->send.nm_addr; + struct mbuf *control = msg->send.nm_control; struct sco_pcb *pcb = (struct sco_pcb *)so->so_pcb; struct mbuf *m0; - int err = 0; + int error = 0; KKASSERT(m != NULL); if (m->m_pkthdr.len == 0) - goto error; + goto out; if (m->m_pkthdr.len > pcb->sp_mtu) { - err = EMSGSIZE; - goto error; + error = EMSGSIZE; + goto out; } m0 = m_copym(m, 0, M_COPYALL, MB_DONTWAIT); if (m0 == NULL) { - err = ENOMEM; - goto error; + error = ENOMEM; + goto out; } - if (control) /* no use for that */ + /* no use for that */ + if (control) { m_freem(control); + control = NULL; + } sbappendrecord(&so->so_snd.sb, m); - return sco_send(pcb, m0); - -error: - if (m) m_freem(m); - if (control) m_freem(control); - return err; + error = sco_send(pcb, m0); + m = NULL; +out: + if (m) + m_freem(m); + if (control) + m_freem(control); + lwkt_replymsg(&msg->send.base.lmsg, error); } -static int -sco_saccept(struct socket *so, struct sockaddr **nam) +static void +sco_saccept(netmsg_t msg) { + struct socket *so = msg->accept.base.nm_so; + struct sockaddr **nam = msg->accept.nm_nam; struct sco_pcb *pcb = (struct sco_pcb *)so->so_pcb; struct sockaddr_bt *sa, ssa; - int e; + int error; sa = &ssa; bzero(sa, sizeof *sa); sa->bt_len = sizeof(struct sockaddr_bt); sa->bt_family = AF_BLUETOOTH; - e = sco_peeraddr(pcb, sa); + error = sco_peeraddr(pcb, sa); *nam = dup_sockaddr((struct sockaddr *)sa); - return (e); + lwkt_replymsg(&msg->accept.base.lmsg, error); } -static int -sco_slisten(struct socket *so, struct thread *td) +static void +sco_slisten(netmsg_t msg) { + struct socket *so = msg->listen.base.nm_so; struct sco_pcb *pcb = (struct sco_pcb *)so->so_pcb; - return sco_listen(pcb); -} + int error; + error = sco_listen(pcb); + lwkt_replymsg(&msg->accept.base.lmsg, error); +} struct pr_usrreqs sco_usrreqs = { .pru_abort = sco_sabort, @@ -419,14 +456,14 @@ struct pr_usrreqs sco_usrreqs = { .pru_attach = sco_sattach, .pru_bind = sco_sbind, .pru_connect = sco_sconnect, - .pru_connect2 = pru_connect2_notsupp, - .pru_control = pru_control_notsupp, + .pru_connect2 = pr_generic_notsupp, + .pru_control = pr_generic_notsupp, .pru_detach = sco_sdetach, .pru_disconnect = sco_sdisconnect, .pru_listen = sco_slisten, .pru_peeraddr = sco_speeraddr, - .pru_rcvd = pru_rcvd_notsupp, - .pru_rcvoob = pru_rcvoob_notsupp, + .pru_rcvd = pr_generic_notsupp, + .pru_rcvoob = pr_generic_notsupp, .pru_send = sco_ssend, .pru_sense = pru_sense_null, .pru_shutdown = sco_sshutdown, diff --git a/sys/netgraph/netgraph/ng_base.c b/sys/netgraph/netgraph/ng_base.c index c17a4ad149..7ec19b29bd 100644 --- a/sys/netgraph/netgraph/ng_base.c +++ b/sys/netgraph/netgraph/ng_base.c @@ -72,6 +72,8 @@ MODULE_VERSION(netgraph, NG_ABI_VERSION); +union netmsg; + /* List of all nodes */ static LIST_HEAD(, ng_node) nodelist; @@ -91,7 +93,7 @@ static int ng_generic_msg(node_p here, struct ng_mesg *msg, const char *retaddr, struct ng_mesg ** resp); static ng_ID_t ng_decodeidname(const char *name); static int ngb_mod_event(module_t mod, int event, void *data); -static void ngintr(struct netmsg *); +static void ngintr(union netmsg *); static int ng_load_module(const char *); static int ng_unload_module(const char *); @@ -2039,7 +2041,7 @@ ng_queue_msg(node_p here, struct ng_mesg *msg, const char *address) * Pick an item off the queue, process it, and dispose of the queue entry. */ static void -ngintr(struct netmsg *pmsg) +ngintr(netmsg_t pmsg) { hook_p hook; struct mbuf *m; @@ -2055,7 +2057,7 @@ ngintr(struct netmsg *pmsg) * be replied. Interlock processing and notification by replying * the message first. */ - lwkt_replymsg(&pmsg->nm_lmsg, 0); + lwkt_replymsg(&pmsg->lmsg, 0); get_mplock(); diff --git a/sys/netgraph/socket/ng_socket.c b/sys/netgraph/socket/ng_socket.c index 45654053a3..9fd145847a 100644 --- a/sys/netgraph/socket/ng_socket.c +++ b/sys/netgraph/socket/ng_socket.c @@ -70,6 +70,7 @@ #include #include +#include #include #include @@ -161,39 +162,53 @@ LIST_HEAD(, ngpcb) ngsocklist; Control sockets ***************************************************************/ -static int -ngc_attach(struct socket *so, int proto, struct pru_attach_info *ai) +static void +ngc_attach(netmsg_t msg) { + struct socket *so = msg->attach.base.nm_so; + struct pru_attach_info *ai = msg->attach.nm_ai; struct ngpcb *const pcbp = sotongpcb(so); + int error; if (priv_check_cred(ai->p_ucred, PRIV_ROOT, NULL_CRED_OKAY) != 0) - return (EPERM); - if (pcbp != NULL) - return (EISCONN); - return (ng_attach_cntl(so)); + error = EPERM; + else if (pcbp != NULL) + error = EISCONN; + else + error = ng_attach_cntl(so); + lwkt_replymsg(&msg->attach.base.lmsg, error); } -static int -ngc_detach(struct socket *so) +static void +ngc_detach(netmsg_t msg) { + struct socket *so = msg->detach.base.nm_so; struct ngpcb *const pcbp = sotongpcb(so); + int error; - if (pcbp == NULL) - return (EINVAL); - ng_detach_common(pcbp, NG_CONTROL); - return (0); + if (pcbp) { + ng_detach_common(pcbp, NG_CONTROL); + error = 0; + } else { + error = EINVAL; + } + lwkt_replymsg(&msg->detach.base.lmsg, error); } -static int -ngc_send(struct socket *so, int flags, struct mbuf *m, struct sockaddr *addr, - struct mbuf *control, struct thread *td) +static void +ngc_send(netmsg_t msg) { + struct socket *so = msg->send.base.nm_so; + struct mbuf *m = msg->send.nm_m; + struct sockaddr *addr = msg->send.nm_addr; + struct mbuf *control = msg->send.nm_control; struct ngpcb *const pcbp = sotongpcb(so); struct sockaddr_ng *const sap = (struct sockaddr_ng *) addr; struct ng_mesg *resp; struct mbuf *m0; - char *msg, *path = NULL; - int len, error = 0; + char *xmsg, *path = NULL; + int len; + int error = 0; if (pcbp == NULL) { error = EINVAL; @@ -233,12 +248,12 @@ ngc_send(struct socket *so, int flags, struct mbuf *m, struct sockaddr *addr, /* Move the data into a linear buffer as well. Messages are not * delivered in mbufs. */ - MALLOC(msg, char *, len + 1, M_NETGRAPH, M_WAITOK); - m_copydata(m, 0, len, msg); + MALLOC(xmsg, char *, len + 1, M_NETGRAPH, M_WAITOK); + m_copydata(m, 0, len, xmsg); - /* The callee will free the msg when done. The addr is our business. */ + /* The callee will free the xmsg when done. The addr is our business. */ error = ng_send_msg(pcbp->sockdata->node, - (struct ng_mesg *) msg, path, &resp); + (struct ng_mesg *) xmsg, path, &resp); /* If the callee responded with a synchronous response, then put it * back on the receive side of the socket; sap is source address. */ @@ -252,58 +267,80 @@ release: m_freem(control); if (m != NULL) m_freem(m); - return (error); + lwkt_replymsg(&msg->send.base.lmsg, error); } -static int -ngc_bind(struct socket *so, struct sockaddr *nam, struct thread *td) +static void +ngc_bind(netmsg_t msg) { + struct socket *so = msg->bind.base.nm_so; + struct sockaddr *nam = msg->bind.nm_nam; struct ngpcb *const pcbp = sotongpcb(so); + int error; - if (pcbp == 0) - return (EINVAL); - return (ng_bind(nam, pcbp)); + if (pcbp) + error = ng_bind(nam, pcbp); + else + error = EINVAL; + lwkt_replymsg(&msg->bind.base.lmsg, error); } -static int -ngc_connect(struct socket *so, struct sockaddr *nam, struct thread *td) +static void +ngc_connect(netmsg_t msg) { + struct socket *so = msg->connect.base.nm_so; + struct sockaddr *nam = msg->connect.nm_nam; struct ngpcb *const pcbp = sotongpcb(so); + int error; - if (pcbp == 0) - return (EINVAL); - return (ng_connect_cntl(nam, pcbp)); + if (pcbp) + error = ng_connect_cntl(nam, pcbp); + else + error = EINVAL; + lwkt_replymsg(&msg->connect.base.lmsg, error); } /*************************************************************** Data sockets ***************************************************************/ -static int -ngd_attach(struct socket *so, int proto, struct pru_attach_info *ai) +static void +ngd_attach(netmsg_t msg) { + struct socket *so = msg->attach.base.nm_so; struct ngpcb *const pcbp = sotongpcb(so); + int error; - if (pcbp != NULL) - return (EISCONN); - return (ng_attach_data(so)); + if (pcbp) + error = EISCONN; + else + error = ng_attach_data(so); + lwkt_replymsg(&msg->connect.base.lmsg, error); } -static int -ngd_detach(struct socket *so) +static void +ngd_detach(netmsg_t msg) { + struct socket *so = msg->detach.base.nm_so; struct ngpcb *const pcbp = sotongpcb(so); + int error; - if (pcbp == NULL) - return (EINVAL); - ng_detach_common(pcbp, NG_DATA); - return (0); + if (pcbp) { + ng_detach_common(pcbp, NG_DATA); + error = 0; + } else { + error = EINVAL; + } + lwkt_replymsg(&msg->detach.base.lmsg, error); } -static int -ngd_send(struct socket *so, int flags, struct mbuf *m, struct sockaddr *addr, - struct mbuf *control, struct thread *td) +static void +ngd_send(netmsg_t msg) { + struct socket *so = msg->send.base.nm_so; + struct mbuf *m = msg->send.nm_m; + struct sockaddr *addr = msg->send.nm_addr; + struct mbuf *control = msg->send.nm_control; struct ngpcb *const pcbp = sotongpcb(so); struct sockaddr_ng *const sap = (struct sockaddr_ng *) addr; meta_p mp = NULL; @@ -365,28 +402,37 @@ release: m_freem(control); if (m != NULL) m_freem(m); - return (error); + lwkt_replymsg(&msg->send.base.lmsg, error); } -static int -ngd_connect(struct socket *so, struct sockaddr *nam, struct thread *td) +static void +ngd_connect(netmsg_t msg) { + struct socket *so = msg->connect.base.nm_so; + struct sockaddr *nam = msg->connect.nm_nam; struct ngpcb *const pcbp = sotongpcb(so); + int error; - if (pcbp == 0) - return (EINVAL); - return (ng_connect_data(nam, pcbp)); + if (pcbp) { + error = ng_connect_data(nam, pcbp); + } else { + error = EINVAL; + } + lwkt_replymsg(&msg->connect.base.lmsg, error); } /* * Used for both data and control sockets */ -static int -ng_setsockaddr(struct socket *so, struct sockaddr **addr) +static void +ng_setsockaddr(netmsg_t msg) { + struct socket *so = msg->sockaddr.base.nm_so; + struct sockaddr **addr = msg->sockaddr.nm_nam; struct ngpcb *pcbp; struct sockaddr_ng *sg; int sg_len, namelen; + int error; /* Why isn't sg_data a `char[1]' ? :-( */ sg_len = sizeof(struct sockaddr_ng) - sizeof(sg->sg_data) + 1; @@ -395,7 +441,8 @@ ng_setsockaddr(struct socket *so, struct sockaddr **addr) pcbp = sotongpcb(so); if ((pcbp == 0) || (pcbp->sockdata == NULL)) { crit_exit(); - return (EINVAL); + error = EINVAL; + goto out; } namelen = 0; /* silence compiler ! */ @@ -412,8 +459,9 @@ ng_setsockaddr(struct socket *so, struct sockaddr **addr) sg->sg_len = sg_len; sg->sg_family = AF_NETGRAPH; *addr = (struct sockaddr *)sg; - - return (0); + error = 0; +out: + lwkt_replymsg(&msg->sockaddr.base.lmsg, error); } /* @@ -838,7 +886,7 @@ ngs_disconnect(hook_p hook) struct ngsock *const sockdata = hook->node->private; if ((sockdata->flags & NGS_FLAG_NOLINGER ) - && (hook->node->numhooks == 0)) { + && (hook->node->numhooks == 0)) { ng_rmnode(hook->node); } return (0); @@ -883,18 +931,18 @@ ngs_rmnode(node_p node) static struct pr_usrreqs ngc_usrreqs = { .pru_abort = NULL, - .pru_accept = pru_accept_notsupp, + .pru_accept = pr_generic_notsupp, .pru_attach = ngc_attach, .pru_bind = ngc_bind, .pru_connect = ngc_connect, - .pru_connect2 = pru_connect2_notsupp, - .pru_control = pru_control_notsupp, + .pru_connect2 = pr_generic_notsupp, + .pru_control = pr_generic_notsupp, .pru_detach = ngc_detach, .pru_disconnect = NULL, - .pru_listen = pru_listen_notsupp, + .pru_listen = pr_generic_notsupp, .pru_peeraddr = NULL, - .pru_rcvd = pru_rcvd_notsupp, - .pru_rcvoob = pru_rcvoob_notsupp, + .pru_rcvd = pr_generic_notsupp, + .pru_rcvoob = pr_generic_notsupp, .pru_send = ngc_send, .pru_sense = pru_sense_null, .pru_shutdown = NULL, @@ -905,18 +953,18 @@ static struct pr_usrreqs ngc_usrreqs = { static struct pr_usrreqs ngd_usrreqs = { .pru_abort = NULL, - .pru_accept = pru_accept_notsupp, + .pru_accept = pr_generic_notsupp, .pru_attach = ngd_attach, .pru_bind = NULL, .pru_connect = ngd_connect, - .pru_connect2 = pru_connect2_notsupp, - .pru_control = pru_control_notsupp, + .pru_connect2 = pr_generic_notsupp, + .pru_control = pr_generic_notsupp, .pru_detach = ngd_detach, .pru_disconnect = NULL, - .pru_listen = pru_listen_notsupp, + .pru_listen = pr_generic_notsupp, .pru_peeraddr = NULL, - .pru_rcvd = pru_rcvd_notsupp, - .pru_rcvoob = pru_rcvoob_notsupp, + .pru_rcvd = pr_generic_notsupp, + .pru_rcvoob = pr_generic_notsupp, .pru_send = ngd_send, .pru_sense = pru_sense_null, .pru_shutdown = NULL, @@ -932,26 +980,20 @@ static struct pr_usrreqs ngd_usrreqs = { extern struct domain ngdomain; /* stop compiler warnings */ static struct protosw ngsw[] = { - { - SOCK_DGRAM, - &ngdomain, - NG_CONTROL, - PR_ATOMIC | PR_ADDR /* | PR_RIGHTS */, - 0, 0, 0, 0, - cpu0_soport, NULL, - 0, 0, 0, 0, - &ngc_usrreqs - }, - { - SOCK_DGRAM, - &ngdomain, - NG_DATA, - PR_ATOMIC | PR_ADDR, - 0, 0, 0, 0, - cpu0_soport, NULL, - 0, 0, 0, 0, - &ngd_usrreqs - } + { + .pr_type = SOCK_DGRAM, + .pr_domain = &ngdomain, + .pr_protocol = NG_CONTROL, + .pr_flags = PR_ATOMIC | PR_ADDR /* | PR_RIGHTS */, + .pr_usrreqs = &ngc_usrreqs + }, + { + .pr_type = SOCK_DGRAM, + .pr_domain = &ngdomain, + .pr_protocol = NG_DATA, + .pr_flags = PR_ATOMIC | PR_ADDR, + .pr_usrreqs = &ngd_usrreqs + } }; struct domain ngdomain = { diff --git a/sys/netinet/if_ether.c b/sys/netinet/if_ether.c index 02a4702b17..09026e73ef 100644 --- a/sys/netinet/if_ether.c +++ b/sys/netinet/if_ether.c @@ -154,7 +154,7 @@ static void arprequest(struct ifnet *, const struct in_addr *, const struct in_addr *, const u_char *); static void arprequest_async(struct ifnet *, const struct in_addr *, const struct in_addr *, const u_char *); -static void arpintr(struct netmsg *); +static void arpintr(netmsg_t msg); static void arptfree(struct llinfo_arp *); static void arptimer(void *); static struct llinfo_arp * @@ -382,10 +382,10 @@ arpreq_send(struct ifnet *ifp, struct mbuf *m) } static void -arpreq_send_handler(struct netmsg *nmsg) +arpreq_send_handler(netmsg_t msg) { - struct mbuf *m = ((struct netmsg_packet *)nmsg)->nm_packet; - struct ifnet *ifp = nmsg->nm_lmsg.u.ms_resultp; + struct mbuf *m = msg->packet.nm_packet; + struct ifnet *ifp = msg->lmsg.u.ms_resultp; arpreq_send(ifp, m); /* nmsg was embedded in the mbuf, do not reply! */ @@ -428,12 +428,12 @@ arprequest_async(struct ifnet *ifp, const struct in_addr *sip, return; pmsg = &m->m_hdr.mh_netmsg; - netmsg_init(&pmsg->nm_netmsg, NULL, &netisr_apanic_rport, + netmsg_init(&pmsg->base, NULL, &netisr_apanic_rport, 0, arpreq_send_handler); pmsg->nm_packet = m; - pmsg->nm_netmsg.nm_lmsg.u.ms_resultp = ifp; + pmsg->base.lmsg.u.ms_resultp = ifp; - lwkt_sendmsg(cpu_portfn(mycpuid), &pmsg->nm_netmsg.nm_lmsg); + lwkt_sendmsg(cpu_portfn(mycpuid), &pmsg->base.lmsg); } /* @@ -550,9 +550,9 @@ arpresolve(struct ifnet *ifp, struct rtentry *rt0, struct mbuf *m, * then the protocol-specific routine is called. */ static void -arpintr(struct netmsg *msg) +arpintr(netmsg_t msg) { - struct mbuf *m = ((struct netmsg_packet *)msg)->nm_packet; + struct mbuf *m = msg->packet.nm_packet; struct arphdr *ar; u_short ar_hrd; @@ -623,13 +623,13 @@ SYSCTL_INT(_net_link_ether_inet, OID_AUTO, log_arp_permanent_modify, CTLFLAG_RW, static void -arp_hold_output(struct netmsg *nmsg) +arp_hold_output(netmsg_t msg) { - struct mbuf *m = ((struct netmsg_packet *)nmsg)->nm_packet; + struct mbuf *m = msg->packet.nm_packet; struct rtentry *rt; struct ifnet *ifp; - rt = nmsg->nm_lmsg.u.ms_resultp; + rt = msg->lmsg.u.ms_resultp; ifp = m->m_pkthdr.rcvif; m->m_pkthdr.rcvif = NULL; @@ -742,16 +742,16 @@ arp_update_oncpu(struct mbuf *m, in_addr_t saddr, boolean_t create, rt->rt_refcnt++; pmsg = &m->m_hdr.mh_netmsg; - netmsg_init(&pmsg->nm_netmsg, NULL, + netmsg_init(&pmsg->base, NULL, &netisr_apanic_rport, MSGF_PRIORITY, arp_hold_output); pmsg->nm_packet = m; /* Record necessary information */ m->m_pkthdr.rcvif = ifp; - pmsg->nm_netmsg.nm_lmsg.u.ms_resultp = rt; + pmsg->base.lmsg.u.ms_resultp = rt; - lwkt_sendmsg(port, &pmsg->nm_netmsg.nm_lmsg); + lwkt_sendmsg(port, &pmsg->base.lmsg); } } } @@ -759,13 +759,13 @@ arp_update_oncpu(struct mbuf *m, in_addr_t saddr, boolean_t create, #ifdef SMP struct netmsg_arp_update { - struct netmsg netmsg; + struct netmsg_base base; struct mbuf *m; in_addr_t saddr; boolean_t create; }; -static void arp_update_msghandler(struct netmsg *); +static void arp_update_msghandler(netmsg_t msg); #endif @@ -906,12 +906,12 @@ match: if (ifp->if_flags & IFF_STATICARP) goto reply; #ifdef SMP - netmsg_init(&msg.netmsg, NULL, &curthread->td_msgport, + netmsg_init(&msg.base, NULL, &curthread->td_msgport, 0, arp_update_msghandler); msg.m = m; msg.saddr = isaddr.s_addr; msg.create = (itaddr.s_addr == myaddr.s_addr); - lwkt_domsg(rtable_portfn(0), &msg.netmsg.nm_lmsg, 0); + lwkt_domsg(rtable_portfn(0), &msg.base.lmsg, 0); #else arp_update_oncpu(m, isaddr.s_addr, (itaddr.s_addr == myaddr.s_addr), RTL_REPORTMSG, TRUE); @@ -996,24 +996,24 @@ reply: #ifdef SMP static void -arp_update_msghandler(struct netmsg *netmsg) +arp_update_msghandler(netmsg_t msg) { - struct netmsg_arp_update *msg = (struct netmsg_arp_update *)netmsg; + struct netmsg_arp_update *rmsg = (struct netmsg_arp_update *)msg; int nextcpu; /* * This message handler will be called on all of the CPUs, * however, we only need to generate rtmsg on CPU0. */ - arp_update_oncpu(msg->m, msg->saddr, msg->create, + arp_update_oncpu(rmsg->m, rmsg->saddr, rmsg->create, mycpuid == 0 ? RTL_REPORTMSG : RTL_DONTREPORT, mycpuid == 0); nextcpu = mycpuid + 1; if (nextcpu < ncpus) - lwkt_forwardmsg(rtable_portfn(nextcpu), &msg->netmsg.nm_lmsg); + lwkt_forwardmsg(rtable_portfn(nextcpu), &rmsg->base.lmsg); else - lwkt_replymsg(&msg->netmsg.nm_lmsg, 0); + lwkt_replymsg(&rmsg->base.lmsg, 0); } #endif /* SMP */ diff --git a/sys/netinet/igmp.c b/sys/netinet/igmp.c index 7e844cf107..164c32d658 100644 --- a/sys/netinet/igmp.c +++ b/sys/netinet/igmp.c @@ -149,10 +149,11 @@ find_rti(struct ifnet *ifp) return rti; } -void -igmp_input(struct mbuf *m, ...) +int +igmp_input(struct mbuf **mp, int *offp, int proto) { - int iphlen, off, proto; + struct mbuf *m = *mp; + int iphlen; struct igmp *igmp; struct ip *ip; int igmplen; @@ -162,16 +163,10 @@ igmp_input(struct mbuf *m, ...) struct in_ifaddr *ia; struct in_multistep step; struct router_info *rti; - __va_list ap; - int timer; /** timer value in the igmp query header **/ - __va_start(ap, m); - off = __va_arg(ap, int); - proto = __va_arg(ap, int); - __va_end(ap); - - iphlen = off; + iphlen = *offp; + *mp = NULL; ++igmpstat.igps_rcv_total; @@ -184,13 +179,13 @@ igmp_input(struct mbuf *m, ...) if (igmplen < IGMP_MINLEN) { ++igmpstat.igps_rcv_tooshort; m_freem(m); - return; + return(IPPROTO_DONE); } minlen = iphlen + IGMP_MINLEN; if ((m->m_flags & M_EXT || m->m_len < minlen) && (m = m_pullup(m, minlen)) == 0) { ++igmpstat.igps_rcv_tooshort; - return; + return(IPPROTO_DONE); } /* @@ -202,7 +197,7 @@ igmp_input(struct mbuf *m, ...) if (in_cksum(m, igmplen)) { ++igmpstat.igps_rcv_badsum; m_freem(m); - return; + return(IPPROTO_DONE); } m->m_data -= iphlen; m->m_len += iphlen; @@ -248,7 +243,7 @@ igmp_input(struct mbuf *m, ...) igmp->igmp_group.s_addr != 0) { ++igmpstat.igps_rcv_badqueries; m_freem(m); - return; + return(IPPROTO_DONE); } } else { /* @@ -259,7 +254,7 @@ igmp_input(struct mbuf *m, ...) !IN_MULTICAST(ntohl(igmp->igmp_group.s_addr))) { ++igmpstat.igps_rcv_badqueries; m_freem(m); - return; + return(IPPROTO_DONE); } } @@ -311,7 +306,7 @@ igmp_input(struct mbuf *m, ...) if (!IN_MULTICAST(ntohl(igmp->igmp_group.s_addr))) { ++igmpstat.igps_rcv_badreports; m_freem(m); - return; + return(IPPROTO_DONE); } /* @@ -346,7 +341,9 @@ igmp_input(struct mbuf *m, ...) * Pass all valid IGMP packets up to any process(es) listening * on a raw IGMP socket. */ - rip_input(m, off, proto); + *mp = m; + rip_input(mp, offp, proto); + return(IPPROTO_DONE); } void diff --git a/sys/netinet/igmp_var.h b/sys/netinet/igmp_var.h index 2ed8e5b2ed..09b243bc36 100644 --- a/sys/netinet/igmp_var.h +++ b/sys/netinet/igmp_var.h @@ -102,7 +102,7 @@ struct mbuf; struct in_multi; void igmp_init (void); -void igmp_input (struct mbuf *, ...); +int igmp_input (struct mbuf **, int *, int); void igmp_joingroup (struct in_multi *); void igmp_leavegroup (struct in_multi *); void igmp_fasttimo (void); diff --git a/sys/netinet/in.c b/sys/netinet/in.c index 6a9a7645ff..bf16151a38 100644 --- a/sys/netinet/in.c +++ b/sys/netinet/in.c @@ -72,7 +72,6 @@ static void in_socktrim (struct sockaddr_in *); static int in_ifinit(struct ifnet *, struct in_ifaddr *, const struct sockaddr_in *, int); -static void in_control_dispatch(struct netmsg *); static int in_control_internal(u_long, caddr_t, struct ifnet *, struct thread *); @@ -194,22 +193,16 @@ in_len2mask(struct in_addr *mask, int len) static int in_interfaces; /* number of external internet interfaces */ -struct in_control_arg { - u_long cmd; - caddr_t data; - struct ifnet *ifp; - struct thread *td; -}; - -static void -in_control_dispatch(struct netmsg *nmsg) +void +in_control_dispatch(netmsg_t msg) { - struct lwkt_msg *msg = &nmsg->nm_lmsg; - const struct in_control_arg *arg = msg->u.ms_resultp; int error; - error = in_control_internal(arg->cmd, arg->data, arg->ifp, arg->td); - lwkt_replymsg(msg, error); + error = in_control_internal(msg->control.nm_cmd, + msg->control.nm_data, + msg->control.nm_ifp, + msg->control.nm_td); + lwkt_replymsg(&msg->lmsg, error); } /* @@ -223,9 +216,7 @@ int in_control(struct socket *so, u_long cmd, caddr_t data, struct ifnet *ifp, struct thread *td) { - struct netmsg nmsg; - struct in_control_arg arg; - struct lwkt_msg *msg; + struct netmsg_pru_control msg; int error; switch (cmd) { @@ -254,29 +245,26 @@ in_control(struct socket *so, u_long cmd, caddr_t data, struct ifnet *ifp, case SIOCSIFNETMASK: case SIOCAIFADDR: case SIOCDIFADDR: - bzero(&arg, sizeof(arg)); - arg.cmd = cmd; - arg.data = data; - arg.ifp = ifp; - arg.td = td; - - netmsg_init(&nmsg, NULL, &curthread->td_msgport, + netmsg_init(&msg.base, NULL, &curthread->td_msgport, 0, in_control_dispatch); - msg = &nmsg.nm_lmsg; - msg->u.ms_resultp = &arg; - - lwkt_domsg(cpu_portfn(0), msg, 0); - return msg->ms_error; + msg.nm_cmd = cmd; + msg.nm_data = data; + msg.nm_ifp = ifp; + msg.nm_td = td; + lwkt_domsg(cpu_portfn(0), &msg.base.lmsg, 0); + error = msg.base.lmsg.ms_error; + break; default: - return in_control_internal(cmd, data, ifp, td); + error = in_control_internal(cmd, data, ifp, td); + break; } + return error; } static void -in_ialink_dispatch(struct netmsg *nmsg) +in_ialink_dispatch(netmsg_t msg) { - struct lwkt_msg *lmsg = &nmsg->nm_lmsg; - struct in_ifaddr *ia = lmsg->u.ms_resultp; + struct in_ifaddr *ia = msg->lmsg.u.ms_resultp; struct ifaddr_container *ifac; struct in_ifaddr_container *iac; int cpu = mycpuid; @@ -294,14 +282,13 @@ in_ialink_dispatch(struct netmsg *nmsg) crit_exit(); - ifa_forwardmsg(lmsg, cpu + 1); + ifa_forwardmsg(&msg->lmsg, cpu + 1); } static void -in_iaunlink_dispatch(struct netmsg *nmsg) +in_iaunlink_dispatch(netmsg_t msg) { - struct lwkt_msg *lmsg = &nmsg->nm_lmsg; - struct in_ifaddr *ia = lmsg->u.ms_resultp; + struct in_ifaddr *ia = msg->lmsg.u.ms_resultp; struct ifaddr_container *ifac; struct in_ifaddr_container *iac; int cpu = mycpuid; @@ -319,14 +306,13 @@ in_iaunlink_dispatch(struct netmsg *nmsg) crit_exit(); - ifa_forwardmsg(lmsg, cpu + 1); + ifa_forwardmsg(&msg->lmsg, cpu + 1); } static void -in_iahashins_dispatch(struct netmsg *nmsg) +in_iahashins_dispatch(netmsg_t msg) { - struct lwkt_msg *lmsg = &nmsg->nm_lmsg; - struct in_ifaddr *ia = lmsg->u.ms_resultp; + struct in_ifaddr *ia = msg->lmsg.u.ms_resultp; struct ifaddr_container *ifac; struct in_ifaddr_container *iac; int cpu = mycpuid; @@ -345,14 +331,13 @@ in_iahashins_dispatch(struct netmsg *nmsg) crit_exit(); - ifa_forwardmsg(lmsg, cpu + 1); + ifa_forwardmsg(&msg->lmsg, cpu + 1); } static void -in_iahashrem_dispatch(struct netmsg *nmsg) +in_iahashrem_dispatch(netmsg_t msg) { - struct lwkt_msg *lmsg = &nmsg->nm_lmsg; - struct in_ifaddr *ia = lmsg->u.ms_resultp; + struct in_ifaddr *ia = msg->lmsg.u.ms_resultp; struct ifaddr_container *ifac; struct in_ifaddr_container *iac; int cpu = mycpuid; @@ -370,63 +355,55 @@ in_iahashrem_dispatch(struct netmsg *nmsg) crit_exit(); - ifa_forwardmsg(lmsg, cpu + 1); + ifa_forwardmsg(&msg->lmsg, cpu + 1); } static void in_ialink(struct in_ifaddr *ia) { - struct netmsg nmsg; - struct lwkt_msg *lmsg; + struct netmsg_base msg; - netmsg_init(&nmsg, NULL, &curthread->td_msgport, + netmsg_init(&msg, NULL, &curthread->td_msgport, 0, in_ialink_dispatch); - lmsg = &nmsg.nm_lmsg; - lmsg->u.ms_resultp = ia; + msg.lmsg.u.ms_resultp = ia; - ifa_domsg(lmsg, 0); + ifa_domsg(&msg.lmsg, 0); } void in_iaunlink(struct in_ifaddr *ia) { - struct netmsg nmsg; - struct lwkt_msg *lmsg; + struct netmsg_base msg; - netmsg_init(&nmsg, NULL, &curthread->td_msgport, + netmsg_init(&msg, NULL, &curthread->td_msgport, 0, in_iaunlink_dispatch); - lmsg = &nmsg.nm_lmsg; - lmsg->u.ms_resultp = ia; + msg.lmsg.u.ms_resultp = ia; - ifa_domsg(lmsg, 0); + ifa_domsg(&msg.lmsg, 0); } void in_iahash_insert(struct in_ifaddr *ia) { - struct netmsg nmsg; - struct lwkt_msg *lmsg; + struct netmsg_base msg; - netmsg_init(&nmsg, NULL, &curthread->td_msgport, + netmsg_init(&msg, NULL, &curthread->td_msgport, 0, in_iahashins_dispatch); - lmsg = &nmsg.nm_lmsg; - lmsg->u.ms_resultp = ia; + msg.lmsg.u.ms_resultp = ia; - ifa_domsg(lmsg, 0); + ifa_domsg(&msg.lmsg, 0); } void in_iahash_remove(struct in_ifaddr *ia) { - struct netmsg nmsg; - struct lwkt_msg *lmsg; + struct netmsg_base msg; - netmsg_init(&nmsg, NULL, &curthread->td_msgport, + netmsg_init(&msg, NULL, &curthread->td_msgport, 0, in_iahashrem_dispatch); - lmsg = &nmsg.nm_lmsg; - lmsg->u.ms_resultp = ia; + msg.lmsg.u.ms_resultp = ia; - ifa_domsg(lmsg, 0); + ifa_domsg(&msg.lmsg, 0); } static __inline struct in_ifaddr * diff --git a/sys/netinet/in_gif.c b/sys/netinet/in_gif.c index 2534cae5e3..0805bfdf84 100644 --- a/sys/netinet/in_gif.c +++ b/sys/netinet/in_gif.c @@ -76,12 +76,20 @@ static int gif_validate4 (const struct ip *, struct gif_softc *, extern struct domain inetdomain; const struct protosw in_gif_protosw = -{ SOCK_RAW, &inetdomain, 0/*IPPROTO_IPV[46]*/, PR_ATOMIC|PR_ADDR, - in_gif_input, rip_output, 0, rip_ctloutput, - cpu0_soport, NULL, - 0, 0, 0, 0, - &rip_usrreqs -}; + { + .pr_type = SOCK_RAW, + .pr_domain = &inetdomain, + .pr_protocol = 0 /*IPPROTO_IPV[46]*/, + .pr_flags = PR_ATOMIC|PR_ADDR, + + .pr_input = in_gif_input, + .pr_output = rip_output, + .pr_ctlinput = NULL, + .pr_ctloutput = rip_ctloutput, + + .pr_ctlport = NULL, + .pr_usrreqs = &rip_usrreqs + }; int ip_gif_ttl = GIF_TTL; SYSCTL_INT(_net_inet_ip, IPCTL_GIF_TTL, gifttl, CTLFLAG_RW, @@ -211,20 +219,18 @@ in_gif_output(struct ifnet *ifp, int family, struct mbuf *m) return(error); } -void -in_gif_input(struct mbuf *m, ...) +int +in_gif_input(struct mbuf **mp, int *offp, int proto) { + struct mbuf *m = *mp; struct ifnet *gifp = NULL; struct ip *ip; int af; u_int8_t otos; - int off, proto; - __va_list ap; + int off; - __va_start(ap, m); - off = __va_arg(ap, int); - proto = __va_arg(ap, int); - __va_end(ap); + off = *offp; + *mp = NULL; ip = mtod(m, struct ip *); @@ -233,7 +239,7 @@ in_gif_input(struct mbuf *m, ...) if (gifp == NULL || (gifp->if_flags & IFF_UP) == 0) { m_freem(m); ipstat.ips_nogif++; - return; + return(IPPROTO_DONE); } otos = ip->ip_tos; @@ -248,7 +254,7 @@ in_gif_input(struct mbuf *m, ...) if (m->m_len < sizeof *ip) { m = m_pullup(m, sizeof *ip); if (!m) - return; + return(IPPROTO_DONE); } ip = mtod(m, struct ip *); if (gifp->if_flags & IFF_LINK1) @@ -267,7 +273,7 @@ in_gif_input(struct mbuf *m, ...) if (m->m_len < sizeof *ip6) { m = m_pullup(m, sizeof *ip6); if (!m) - return; + return(IPPROTO_DONE); } ip6 = mtod(m, struct ip6_hdr *); itos = (ntohl(ip6->ip6_flow) >> 20) & 0xff; @@ -283,10 +289,10 @@ in_gif_input(struct mbuf *m, ...) default: ipstat.ips_nogif++; m_freem(m); - return; + return(IPPROTO_DONE); } gif_input(m, af, gifp); - return; + return(IPPROTO_DONE); } /* diff --git a/sys/netinet/in_gif.h b/sys/netinet/in_gif.h index 83973d2594..a5f081ff9a 100644 --- a/sys/netinet/in_gif.h +++ b/sys/netinet/in_gif.h @@ -42,7 +42,7 @@ struct gif_softc; struct mbuf; struct ifnet; -void in_gif_input (struct mbuf *, ...); +int in_gif_input (struct mbuf **, int *, int); int in_gif_output (struct ifnet *, int, struct mbuf *); int gif_encapcheck4 (const struct mbuf *, int, int, void *); int in_gif_attach (struct gif_softc *); diff --git a/sys/netinet/in_pcb.c b/sys/netinet/in_pcb.c index 3e07cd4934..819dcef10c 100644 --- a/sys/netinet/in_pcb.c +++ b/sys/netinet/in_pcb.c @@ -87,6 +87,7 @@ #include #include +#include #include @@ -770,6 +771,15 @@ in_setsockaddr(struct socket *so, struct sockaddr **nam) return (0); } +void +in_setsockaddr_dispatch(netmsg_t msg) +{ + int error; + + error = in_setsockaddr(msg->base.nm_so, msg->peeraddr.nm_nam); + lwkt_replymsg(&msg->lmsg, error); +} + int in_setpeeraddr(struct socket *so, struct sockaddr **nam) { @@ -799,6 +809,15 @@ in_setpeeraddr(struct socket *so, struct sockaddr **nam) return (0); } +void +in_setpeeraddr_dispatch(netmsg_t msg) +{ + int error; + + error = in_setpeeraddr(msg->base.nm_so, msg->peeraddr.nm_nam); + lwkt_replymsg(&msg->lmsg, error); +} + void in_pcbnotifyall(struct inpcbhead *head, struct in_addr faddr, int err, void (*notify)(struct inpcb *, int)) diff --git a/sys/netinet/in_pcb.h b/sys/netinet/in_pcb.h index 39e5e14bd5..6cf34f9c0c 100644 --- a/sys/netinet/in_pcb.h +++ b/sys/netinet/in_pcb.h @@ -379,6 +379,8 @@ extern int ipport_lastauto; extern int ipport_hifirstauto; extern int ipport_hilastauto; +union netmsg; + void in_pcbpurgeif0 (struct inpcb *, struct ifnet *); void in_losing (struct inpcb *); void in_rtchange (struct inpcb *, int); @@ -406,7 +408,9 @@ struct inpcb * void in_pcbnotifyall (struct inpcbhead *, struct in_addr, int, void (*)(struct inpcb *, int)); int in_setpeeraddr (struct socket *so, struct sockaddr **nam); +void in_setpeeraddr_dispatch(union netmsg *); int in_setsockaddr (struct socket *so, struct sockaddr **nam); +void in_setsockaddr_dispatch(netmsg_t msg); void in_pcbremwildcardhash(struct inpcb *inp); void in_pcbremwildcardhash_oncpu(struct inpcb *, struct inpcbinfo *); void in_pcbremconnhash(struct inpcb *inp); diff --git a/sys/netinet/in_proto.c b/sys/netinet/in_proto.c index ece006f8c9..08a71fdc74 100644 --- a/sys/netinet/in_proto.c +++ b/sys/netinet/in_proto.c @@ -116,201 +116,428 @@ extern struct domain inetdomain; static struct pr_usrreqs nousrreqs; struct protosw inetsw[] = { -{ 0, &inetdomain, 0, 0, - 0, 0, 0, 0, - cpu0_soport, NULL, - ip_init, 0, ip_slowtimo, ip_drain, - &nousrreqs -}, -{ SOCK_DGRAM, &inetdomain, IPPROTO_UDP, PR_ATOMIC|PR_ADDR|PR_MPSAFE, - udp_input, 0, udp_ctlinput, ip_ctloutput, - udp_soport, udp_ctlport, - udp_init, 0, 0, 0, - &udp_usrreqs -}, -{ SOCK_STREAM, &inetdomain, IPPROTO_TCP, PR_CONNREQUIRED | - PR_IMPLOPCL | PR_WANTRCVD | - PR_MPSAFE, - tcp_input, 0, tcp_ctlinput, tcp_ctloutput, - tcp_soport, tcp_ctlport, - tcp_init, 0, tcp_slowtimo, tcp_drain, - &tcp_usrreqs -}, + { + .pr_type = 0, + .pr_domain = &inetdomain, + .pr_protocol = 0, + .pr_flags = 0, + + .pr_ctlport = NULL, + + .pr_init = ip_init, + .pr_fasttimo = NULL, + .pr_slowtimo = ip_slowtimo, + .pr_drain = ip_drain, + .pr_usrreqs = &nousrreqs + }, + { + .pr_type = SOCK_DGRAM, + .pr_domain = &inetdomain, + .pr_protocol = IPPROTO_UDP, + .pr_flags = PR_ATOMIC|PR_ADDR|PR_MPSAFE, + + .pr_input = udp_input, + .pr_output = NULL, + .pr_ctlinput = udp_ctlinput, + .pr_ctloutput = ip_ctloutput, + + .pr_ctlport = udp_ctlport, + .pr_init = udp_init, + .pr_usrreqs = &udp_usrreqs + }, + { + .pr_type = SOCK_STREAM, + .pr_domain = &inetdomain, + .pr_protocol = IPPROTO_TCP, + .pr_flags = PR_CONNREQUIRED|PR_IMPLOPCL|PR_WANTRCVD|PR_MPSAFE, + + .pr_input = tcp_input, + .pr_output = NULL, + .pr_ctlinput = tcp_ctlinput, + .pr_ctloutput = tcp_ctloutput, + + .pr_ctlport = tcp_ctlport, + .pr_init = tcp_init, + .pr_fasttimo = NULL, + .pr_slowtimo = tcp_slowtimo, + .pr_drain = tcp_drain, + .pr_usrreqs = &tcp_usrreqs + }, #ifdef SCTP -/* - * Order is very important here, we add the good one in - * in this postion so it maps to the right ip_protox[] - * postion for SCTP. Don't move the one above below - * this one or IPv6/4 compatability will break - */ -{ SOCK_DGRAM, &inetdomain, IPPROTO_SCTP, PR_ADDR_OPT|PR_WANTRCVD, - sctp_input, 0, sctp_ctlinput, sctp_ctloutput, - cpu0_soport, cpu0_ctlport, - sctp_init, 0, 0, sctp_drain, - &sctp_usrreqs -}, -{ SOCK_SEQPACKET,&inetdomain, IPPROTO_SCTP, PR_ADDR_OPT|PR_WANTRCVD, - sctp_input, 0, sctp_ctlinput, sctp_ctloutput, - cpu0_soport, cpu0_ctlport, - 0, 0, 0, sctp_drain, - &sctp_usrreqs -}, - -{ SOCK_STREAM, &inetdomain, IPPROTO_SCTP, PR_CONNREQUIRED|PR_ADDR_OPT|PR_WANTRCVD, - sctp_input, 0, sctp_ctlinput, sctp_ctloutput, - cpu0_soport, cpu0_ctlport, - 0, 0, 0, sctp_drain, - &sctp_usrreqs -}, + /* + * Order is very important here, we add the good one in + * in this postion so it maps to the right ip_protox[] + * postion for SCTP. Don't move the one above below + * this one or IPv6/4 compatability will break + */ + { + .pr_type = SOCK_DGRAM, + .pr_domain = &inetdomain, + .pr_protocol = IPPROTO_SCTP, + .pr_flags = PR_ADDR_OPT|PR_WANTRCVD, + + .pr_input = sctp_input, + .pr_output = NULL, + .pr_ctlinput = sctp_ctlinput, + .pr_ctloutput = sctp_ctloutput, + + .pr_ctlport = cpu0_ctlport, + .pr_init = sctp_init, + .pr_drain = sctp_drain, + .pr_usrreqs = &sctp_usrreqs + }, + { + .pr_type = SOCK_SEQPACKET, + .pr_domain = &inetdomain, + .pr_protocol = IPPROTO_SCTP, + .pr_flags = PR_ADDR_OPT|PR_WANTRCVD, + + .pr_input = sctp_input, + .pr_output = NULL, + .pr_ctlinput = sctp_ctlinput, + .pr_ctloutput = sctp_ctloutput, + + .pr_ctlport = cpu0_ctlport, + .pr_drain = sctp_drain, + .pr_usrreqs = &sctp_usrreqs + }, + + { + .pr_type = SOCK_STREAM, + .pr_domain = &inetdomain, + .pr_protocol = IPPROTO_SCTP, + .pr_flags = PR_CONNREQUIRED|PR_ADDR_OPT|PR_WANTRCVD, + + .pr_input = sctp_input, + .pr_output = NULL, + .pr_ctlinput = sctp_ctlinput, + .pr_ctloutput = sctp_ctloutput, + + .pr_ctlport = cpu0_ctlport, + .pr_drain = sctp_drain, + .pr_usrreqs = &sctp_usrreqs + }, #endif /* SCTP */ -{ SOCK_RAW, &inetdomain, IPPROTO_RAW, PR_ATOMIC|PR_ADDR, - rip_input, 0, rip_ctlinput, rip_ctloutput, - cpu0_soport, cpu0_ctlport, - 0, 0, 0, 0, - &rip_usrreqs -}, -{ SOCK_RAW, &inetdomain, IPPROTO_ICMP, PR_ATOMIC|PR_ADDR|PR_LASTHDR, - icmp_input, 0, 0, rip_ctloutput, - cpu0_soport, NULL, - 0, 0, 0, 0, - &rip_usrreqs -}, -{ SOCK_RAW, &inetdomain, IPPROTO_IGMP, PR_ATOMIC|PR_ADDR|PR_LASTHDR, - igmp_input, 0, 0, rip_ctloutput, - cpu0_soport, NULL, - igmp_init, igmp_fasttimo, igmp_slowtimo, 0, - &rip_usrreqs -}, -{ SOCK_RAW, &inetdomain, IPPROTO_RSVP, PR_ATOMIC|PR_ADDR|PR_LASTHDR, - rsvp_input, 0, 0, rip_ctloutput, - cpu0_soport, NULL, - 0, 0, 0, 0, - &rip_usrreqs -}, + { + .pr_type = SOCK_RAW, + .pr_domain = &inetdomain, + .pr_protocol = IPPROTO_RAW, + .pr_flags = PR_ATOMIC|PR_ADDR, + + .pr_input = rip_input, + .pr_output = NULL, + .pr_ctlinput = rip_ctlinput, + .pr_ctloutput = rip_ctloutput, + + .pr_ctlport = cpu0_ctlport, + .pr_usrreqs = &rip_usrreqs + }, + { + .pr_type = SOCK_RAW, + .pr_domain = &inetdomain, + .pr_protocol = IPPROTO_ICMP, + .pr_flags = PR_ATOMIC|PR_ADDR|PR_LASTHDR, + + .pr_input = icmp_input, + .pr_output = NULL, + .pr_ctlinput = NULL, + .pr_ctloutput = rip_ctloutput, + + .pr_usrreqs = &rip_usrreqs + }, + { + .pr_type = SOCK_RAW, + .pr_domain = &inetdomain, + .pr_protocol = IPPROTO_IGMP, + .pr_flags = PR_ATOMIC|PR_ADDR|PR_LASTHDR, + + .pr_input = igmp_input, + .pr_output = NULL, + .pr_ctlinput = NULL, + .pr_ctloutput = rip_ctloutput, + + .pr_init = igmp_init, + .pr_fasttimo = igmp_fasttimo, + .pr_slowtimo = igmp_slowtimo, + .pr_drain = NULL, + .pr_usrreqs = &rip_usrreqs + }, + { + .pr_type = SOCK_RAW, + .pr_domain = &inetdomain, + .pr_protocol = IPPROTO_RSVP, + .pr_flags = PR_ATOMIC|PR_ADDR|PR_LASTHDR, + + .pr_input = rsvp_input, + .pr_output = NULL, + .pr_ctlinput = NULL, + .pr_ctloutput = rip_ctloutput, + + .pr_usrreqs = &rip_usrreqs + }, #ifdef IPSEC -{ SOCK_RAW, &inetdomain, IPPROTO_AH, PR_ATOMIC|PR_ADDR, - ah4_input, 0, 0, 0, - cpu0_soport, NULL, - 0, 0, 0, 0, - &nousrreqs -}, + { + .pr_type = SOCK_RAW, + .pr_domain = &inetdomain, + .pr_protocol = IPPROTO_AH, + .pr_flags = PR_ATOMIC|PR_ADDR, + + .pr_input = ah4_input, + .pr_output = NULL, + .pr_ctlinput = NULL, + .pr_ctloutput = NULL, + + .pr_ctlport = NULL, + .pr_usrreqs = &nousrreqs + }, #ifdef IPSEC_ESP -{ SOCK_RAW, &inetdomain, IPPROTO_ESP, PR_ATOMIC|PR_ADDR, - esp4_input, 0, 0, 0, - cpu0_soport, NULL, - 0, 0, 0, 0, - &nousrreqs -}, + { + .pr_type = SOCK_RAW, + .pr_domain = &inetdomain, + .pr_protocol = IPPROTO_ESP, + .pr_flags = PR_ATOMIC|PR_ADDR, + + .pr_input = esp4_input, + .pr_output = NULL, + .pr_ctlinput = NULL, + .pr_ctloutput = NULL, + + .pr_ctlport = NULL, + .pr_usrreqs = &nousrreqs + }, #endif -{ SOCK_RAW, &inetdomain, IPPROTO_IPCOMP, PR_ATOMIC|PR_ADDR, - ipcomp4_input, 0, 0, 0, - cpu0_soport, NULL, - 0, 0, 0, 0, - &nousrreqs -}, + { + .pr_type = SOCK_RAW, + .pr_domain = &inetdomain, + .pr_protocol = IPPROTO_IPCOMP, + .pr_flags = PR_ATOMIC|PR_ADDR, + + .pr_input = ipcomp4_input, + .pr_output = 0, + .pr_ctlinput = NULL, + .pr_ctloutput = NULL, + + .pr_ctlport = NULL, + .pr_usrreqs = &nousrreqs + }, #endif /* IPSEC */ #ifdef FAST_IPSEC -{ SOCK_RAW, &inetdomain, IPPROTO_AH, PR_ATOMIC|PR_ADDR, - ipsec4_common_input, 0, 0, 0, - cpu0_soport, NULL, - 0, 0, 0, 0, - &nousrreqs -}, -{ SOCK_RAW, &inetdomain, IPPROTO_ESP, PR_ATOMIC|PR_ADDR, - ipsec4_common_input, 0, 0, 0, - cpu0_soport, NULL, - 0, 0, 0, 0, - &nousrreqs -}, -{ SOCK_RAW, &inetdomain, IPPROTO_IPCOMP, PR_ATOMIC|PR_ADDR, - ipsec4_common_input, 0, 0, 0, - cpu0_soport, NULL, - 0, 0, 0, 0, - &nousrreqs -}, + { + .pr_type = SOCK_RAW, + .pr_domain = &inetdomain, + .pr_protocol = IPPROTO_AH, + .pr_flags = PR_ATOMIC|PR_ADDR, + + .pr_input = ipsec4_common_input, + .pr_output = NULL, + .pr_ctlinput = NULL, + .pr_ctloutput = NULL, + + .pr_ctlport = NULL, + .pr_usrreqs = &nousrreqs + }, + { + .pr_type = SOCK_RAW, + .pr_domain = &inetdomain, + .pr_protocol = IPPROTO_ESP, + .pr_flags = PR_ATOMIC|PR_ADDR, + + .pr_input = ipsec4_common_input, + .pr_output = NULL + .pr_ctlinput = NULL, + .pr_ctloutput = NULL, + + .pr_ctlport = NULL, + .pr_usrreqs = &nousrreqs + }, + { + .pr_type = SOCK_RAW, + .pr_domain = &inetdomain, + .pr_protocol = IPPROTO_IPCOMP, + .pr_flags = PR_ATOMIC|PR_ADDR, + + .pr_input = ipsec4_common_input, + .pr_output = NULL, + .pr_ctlinput = NULL, + .pr_ctloutput = NULL, + + .pr_ctlport = NULL, + .pr_usrreqs = &nousrreqs + }, #endif /* FAST_IPSEC */ -{ SOCK_RAW, &inetdomain, IPPROTO_IPV4, PR_ATOMIC|PR_ADDR|PR_LASTHDR, - encap4_input, 0, 0, rip_ctloutput, - cpu0_soport, NULL, - encap_init, 0, 0, 0, - &rip_usrreqs -}, -{ SOCK_RAW, &inetdomain, IPPROTO_MOBILE, PR_ATOMIC|PR_ADDR|PR_LASTHDR, - encap4_input, 0, 0, rip_ctloutput, - cpu0_soport, NULL, - encap_init, 0, 0, 0, - &rip_usrreqs -}, -{ SOCK_RAW, &inetdomain, IPPROTO_GRE, PR_ATOMIC|PR_ADDR|PR_LASTHDR, - encap4_input, 0, 0, rip_ctloutput, - cpu0_soport, NULL, - encap_init, 0, 0, 0, - &rip_usrreqs -}, -# ifdef INET6 -{ SOCK_RAW, &inetdomain, IPPROTO_IPV6, PR_ATOMIC|PR_ADDR|PR_LASTHDR, - encap4_input, 0, 0, rip_ctloutput, - cpu0_soport, NULL, - encap_init, 0, 0, 0, - &rip_usrreqs -}, + { + .pr_type = SOCK_RAW, + .pr_domain = &inetdomain, + .pr_protocol = IPPROTO_IPV4, + .pr_flags = PR_ATOMIC|PR_ADDR|PR_LASTHDR, + .pr_input = encap4_input, + .pr_output = NULL, + .pr_ctlinput = NULL, + .pr_ctloutput = rip_ctloutput, + + .pr_ctlport = NULL, + .pr_init = encap_init, + .pr_usrreqs = &rip_usrreqs + }, + { + .pr_type = SOCK_RAW, + .pr_domain = &inetdomain, + .pr_protocol = IPPROTO_MOBILE, + .pr_flags = PR_ATOMIC|PR_ADDR|PR_LASTHDR, + + .pr_input = encap4_input, + .pr_output = NULL, + .pr_ctlinput = NULL, + .pr_ctloutput = rip_ctloutput, + + .pr_ctlport = NULL, + .pr_init = encap_init, + .pr_usrreqs = &rip_usrreqs + }, + { + .pr_type = SOCK_RAW, + .pr_domain = &inetdomain, + .pr_protocol = IPPROTO_GRE, + .pr_flags = PR_ATOMIC|PR_ADDR|PR_LASTHDR, + + .pr_input = encap4_input, + .pr_output = NULL, + .pr_ctlinput = NULL, + .pr_ctloutput = rip_ctloutput, + + .pr_ctlport = NULL, + .pr_init = encap_init, + .pr_usrreqs = &rip_usrreqs + }, +#ifdef INET6 + { + .pr_type = SOCK_RAW, + .pr_domain = &inetdomain, + .pr_protocol = IPPROTO_IPV6, + .pr_flags = PR_ATOMIC|PR_ADDR|PR_LASTHDR, + + .pr_input = encap4_input, + .pr_output = NULL, + .pr_ctlinput = NULL, + .pr_ctloutput = rip_ctloutput, + + .pr_ctlport = NULL, + .pr_init = encap_init, + .pr_usrreqs = &rip_usrreqs + }, #endif #ifdef IPDIVERT -{ SOCK_RAW, &inetdomain, IPPROTO_DIVERT, PR_ATOMIC|PR_ADDR, - div_input, 0, 0, ip_ctloutput, - div_soport, NULL, - div_init, 0, 0, 0, - &div_usrreqs, -}, + { + .pr_type = SOCK_RAW, + .pr_domain = &inetdomain, + .pr_protocol = IPPROTO_DIVERT, + .pr_flags = PR_ATOMIC|PR_ADDR, + + .pr_input = div_input, + .pr_output = NULL, + .pr_ctlinput = NULL, + .pr_ctloutput = ip_ctloutput, + + .pr_ctlport = NULL, + .pr_init = div_init, + .pr_usrreqs = &div_usrreqs + }, #endif #ifdef IPXIP -{ SOCK_RAW, &inetdomain, IPPROTO_IDP, PR_ATOMIC|PR_ADDR|PR_LASTHDR, - ipxip_input, 0, ipxip_ctlinput, 0, - cpu0_soport, cpu0_ctlport, - 0, 0, 0, 0, - &rip_usrreqs -}, + { + .pr_type = SOCK_RAW, + .pr_domain = &inetdomain, + .pr_protocol = IPPROTO_IDP, + .pr_flags = PR_ATOMIC|PR_ADDR|PR_LASTHDR, + + .pr_input = ipxip_input, + .pr_output = NULL, + .pr_ctlinput = ipxip_ctlinput, + .pr_ctloutput = NULL, + + .pr_ctlport = cpu0_ctlport, + .pr_usrreqs = &rip_usrreqs + }, #endif #ifdef NSIP -{ SOCK_RAW, &inetdomain, IPPROTO_IDP, PR_ATOMIC|PR_ADDR|PR_LASTHDR, - idpip_input, 0, nsip_ctlinput, 0, - cpu0_soport, cpu0_ctlport, - 0, 0, 0, 0, - &rip_usrreqs -}, + { + .pr_type = SOCK_RAW, + .pr_domain = &inetdomain, + .pr_protocol = IPPROTO_IDP, + .pr_flags = PR_ATOMIC|PR_ADDR|PR_LASTHDR, + + .pr_input = idpip_input, + .pr_output = NULL, + .pr_ctlinput = nsip_ctlinput, + .pr_ctloutput = NULL, + + .pr_ctlport = cpu0_ctlport, + .pr_usrreqs = &rip_usrreqs + }, #endif #ifdef PIM -{ SOCK_RAW, &inetdomain, IPPROTO_PIM, PR_ATOMIC|PR_ADDR|PR_LASTHDR, - pim_input, 0, 0, rip_ctloutput, - cpu0_soport, NULL, - 0, 0, 0, 0, - &rip_usrreqs -}, + { + .pr_type = SOCK_RAW, + .pr_domain = &inetdomain, + .pr_protocol = IPPROTO_PIM, + .pr_flags = PR_ATOMIC|PR_ADDR|PR_LASTHDR, + + .pr_input = pim_input, + .pr_output = NULL, + .pr_ctlinput = NULL, + .pr_ctloutput = rip_ctloutput, + + .pr_ctlport = NULL, + .pr_usrreqs = &rip_usrreqs + }, #endif #ifdef NPFSYNC -{ SOCK_RAW, &inetdomain, IPPROTO_PFSYNC, PR_ATOMIC|PR_ADDR, - pfsync_input, 0, 0, rip_ctloutput, - cpu0_soport, NULL, - 0, 0, 0, 0, - &rip_usrreqs -}, + { + .pr_type = SOCK_RAW, + .pr_domain = &inetdomain, + .pr_protocol = IPPROTO_PFSYNC, + .pr_flags = PR_ATOMIC|PR_ADDR, + + .pr_input = pfsync_input, + .pr_output = NULL, + .pr_ctlinput = NULL, + .pr_ctloutput = rip_ctloutput, + + .pr_ctlport = NULL, + .pr_usrreqs = &rip_usrreqs + }, #endif /* NPFSYNC */ + { /* raw wildcard */ -{ SOCK_RAW, &inetdomain, 0, PR_ATOMIC|PR_ADDR, - rip_input, 0, 0, rip_ctloutput, - cpu0_soport, NULL, - rip_init, 0, 0, 0, - &rip_usrreqs -}, + .pr_type = SOCK_RAW, + .pr_domain = &inetdomain, + .pr_protocol = 0, + .pr_flags = PR_ATOMIC|PR_ADDR, + + .pr_input = rip_input, + .pr_output = NULL, + .pr_ctlinput = NULL, + .pr_ctloutput = rip_ctloutput, + .pr_init = rip_init, + .pr_ctlport = NULL, + .pr_usrreqs = &rip_usrreqs + }, #ifdef CARP -{ SOCK_RAW, &inetdomain, IPPROTO_CARP, PR_ATOMIC|PR_ADDR, - carp_input, rip_output, 0, rip_ctloutput, - cpu0_soport, NULL, - 0, 0, 0, 0, - &rip_usrreqs -}, + { + .pr_type = SOCK_RAW, + .pr_domain = &inetdomain, + .pr_protocol = IPPROTO_CARP, + .pr_flags = PR_ATOMIC|PR_ADDR, + + .pr_input = carp_input, + .pr_output = rip_output, + .pr_ctlinput = NULL, + .pr_ctloutput = rip_ctloutput, + .pr_ctlport = NULL, + .pr_usrreqs = &rip_usrreqs + }, #endif }; diff --git a/sys/netinet/in_var.h b/sys/netinet/in_var.h index a8283a1fa0..03e4b46fbe 100644 --- a/sys/netinet/in_var.h +++ b/sys/netinet/in_var.h @@ -237,14 +237,15 @@ do { \ } while(0) struct route; -struct netmsg; struct lwkt_serialize; +union netmsg; void in_ifdetach(struct ifnet *ifp); struct in_multi *in_addmulti (struct in_addr *, struct ifnet *); void in_delmulti (struct in_multi *); int in_control (struct socket *, u_long, caddr_t, struct ifnet *, struct thread *); +void in_control_dispatch(union netmsg *); void in_rtqdrain (void); void ip_input (struct mbuf *); void ip_forward (struct mbuf *, boolean_t, struct sockaddr_in *); diff --git a/sys/netinet/ip_carp.c b/sys/netinet/ip_carp.c index dc933ea430..12acb75402 100644 --- a/sys/netinet/ip_carp.c +++ b/sys/netinet/ip_carp.c @@ -489,23 +489,22 @@ carp_ifdetach(void *arg __unused, struct ifnet *ifp) * we have rearranged checks order compared to the rfc, * but it seems more efficient this way or not possible otherwise. */ -void -carp_input(struct mbuf *m, ...) +int +carp_input(struct mbuf **mp, int *offp, int proto) { + struct mbuf *m = *mp; struct ip *ip = mtod(m, struct ip *); struct carp_header *ch; int len, iphlen; - __va_list ap; - __va_start(ap, m); - iphlen = __va_arg(ap, int); - __va_end(ap); + iphlen = *offp; + *mp = NULL; carpstats.carps_ipackets++; if (!carp_opts[CARPCTL_ALLOW]) { m_freem(m); - return; + return(IPPROTO_DONE); } /* Check if received on a valid carp interface */ @@ -515,7 +514,7 @@ carp_input(struct mbuf *m, ...) "interface: %s\n", m->m_pkthdr.rcvif->if_xname); m_freem(m); - return; + return(IPPROTO_DONE); } /* Verify that the IP TTL is CARP_DFLTTL. */ @@ -525,7 +524,7 @@ carp_input(struct mbuf *m, ...) ip->ip_ttl, CARP_DFLTTL, m->m_pkthdr.rcvif->if_xname); m_freem(m); - return; + return(IPPROTO_DONE); } /* Minimal CARP packet size */ @@ -540,7 +539,7 @@ carp_input(struct mbuf *m, ...) CARP_LOG("packet too short %d on %s\n", m->m_pkthdr.len, m->m_pkthdr.rcvif->if_xname); m_freem(m); - return; + return(IPPROTO_DONE); } /* Make sure that CARP header is contiguous */ @@ -549,7 +548,7 @@ carp_input(struct mbuf *m, ...) if (m == NULL) { carpstats.carps_hdrops++; CARP_LOG("carp_input: m_pullup failed\n"); - return; + return(IPPROTO_DONE); } ip = mtod(m, struct ip *); } @@ -561,9 +560,10 @@ carp_input(struct mbuf *m, ...) CARP_LOG("carp_input: checksum failed on %s\n", m->m_pkthdr.rcvif->if_xname); m_freem(m); - return; + return(IPPROTO_DONE); } carp_input_c(m, ch, AF_INET); + return(IPPROTO_DONE); } #ifdef INET6 diff --git a/sys/netinet/ip_carp.h b/sys/netinet/ip_carp.h index 656eb05888..886ff7af93 100644 --- a/sys/netinet/ip_carp.h +++ b/sys/netinet/ip_carp.h @@ -171,7 +171,7 @@ struct ifcarpvhaddr { #ifdef _KERNEL void carp_carpdev_state(void *); void carp_group_demote_adj(struct ifnet *, int); -void carp_input(struct mbuf *, ...); +int carp_input(struct mbuf **, int *, int); int carp6_input(struct mbuf **, int *, int); int carp_output(struct ifnet *, struct mbuf *, struct sockaddr *, struct rtentry *); diff --git a/sys/netinet/ip_demux.c b/sys/netinet/ip_demux.c index 998deedccc..b4fa649315 100644 --- a/sys/netinet/ip_demux.c +++ b/sys/netinet/ip_demux.c @@ -441,20 +441,6 @@ udp_addrport(in_addr_t faddr, in_port_t fport, in_addr_t laddr, in_port_t lport) return(cpu_portfn(udp_addrcpu(faddr, fport, laddr, lport))); } -/* - * This is used to map a socket to a message port for sendmsg() and friends. - * It is not called for any other purpose. - * - * In the case of UDP we just return the port already installed in the socket, - * regardless of what (nam) is. - */ -lwkt_port_t -udp_soport(struct socket *so, struct sockaddr *nam, - struct mbuf **dummy __unused) -{ - return(so->so_port); -} - /* * Used to route icmp messages to the proper protocol thread for ctlinput * operation. diff --git a/sys/netinet/ip_divert.c b/sys/netinet/ip_divert.c index 08e259069e..5c0f8903b1 100644 --- a/sys/netinet/ip_divert.c +++ b/sys/netinet/ip_divert.c @@ -153,11 +153,14 @@ div_init(void) * IPPROTO_DIVERT is not a real IP protocol; don't allow any packets * with that protocol number to enter the system from the outside. */ -void -div_input(struct mbuf *m, ...) +int +div_input(struct mbuf **mp, int *offp, int proto) { + struct mbuf *m = *mp; + ipstat.ips_noproto++; m_freem(m); + return(IPPROTO_DONE); } struct lwkt_port * @@ -333,24 +336,22 @@ div_packet(struct mbuf *m, int incoming, int port) } #ifdef SMP + static void -div_packet_handler(struct netmsg *nmsg) +div_packet_handler(netmsg_t msg) { - struct netmsg_packet *nmp; - struct lwkt_msg *msg; struct mbuf *m; int port, incoming = 0; - nmp = (struct netmsg_packet *)nmsg; - m = nmp->nm_packet; + m = msg->packet.nm_packet; - msg = &nmsg->nm_lmsg; - port = msg->u.ms_result32 & 0xffff; - if (msg->u.ms_result32 & DIV_INPUT) + port = msg->lmsg.u.ms_result32 & 0xffff; + if (msg->lmsg.u.ms_result32 & DIV_INPUT) incoming = 1; - div_packet(m, incoming, port); + /* no reply, msg embedded in mbuf */ } + #endif /* SMP */ static void @@ -377,21 +378,19 @@ divert_packet(struct mbuf *m, int incoming) #ifdef SMP if (mycpuid != 0) { struct netmsg_packet *nmp; - struct lwkt_msg *msg; nmp = &m->m_hdr.mh_netmsg; - netmsg_init(&nmp->nm_netmsg, NULL, &netisr_apanic_rport, + netmsg_init(&nmp->base, NULL, &netisr_apanic_rport, 0, div_packet_handler); nmp->nm_packet = m; - msg = &nmp->nm_netmsg.nm_lmsg; - msg->u.ms_result32 = port; /* port is 16bits */ + nmp->base.lmsg.u.ms_result32 = port; /* port is 16bits */ if (incoming) - msg->u.ms_result32 |= DIV_INPUT; + nmp->base.lmsg.u.ms_result32 |= DIV_INPUT; else - msg->u.ms_result32 |= DIV_OUTPUT; + nmp->base.lmsg.u.ms_result32 |= DIV_OUTPUT; - lwkt_sendmsg(cpu_portfn(0), &nmp->nm_netmsg.nm_lmsg); + lwkt_sendmsg(cpu_portfn(0), &nmp->base.lmsg); } else #endif div_packet(m, incoming, port); @@ -464,27 +463,31 @@ cantsend: return error; } -static int -div_attach(struct socket *so, int proto, struct pru_attach_info *ai) +static void +div_attach(netmsg_t msg) { + struct socket *so = msg->attach.base.nm_so; + int proto = msg->attach.nm_proto; + struct pru_attach_info *ai = msg->attach.nm_ai; struct inpcb *inp; int error; inp = so->so_pcb; if (inp) panic("div_attach"); - if ((error = priv_check_cred(ai->p_ucred, PRIV_ROOT, NULL_CRED_OKAY)) != 0) - return error; + error = priv_check_cred(ai->p_ucred, PRIV_ROOT, NULL_CRED_OKAY); + if (error) + goto out; error = soreserve(so, div_sendspace, div_recvspace, ai->sb_rlimit); if (error) - return error; + goto out; lwkt_gettoken(&div_token); so->so_port = cpu0_soport(so, NULL, NULL); error = in_pcballoc(so, &divcbinfo); if (error) { lwkt_reltoken(&div_token); - return error; + goto out; } inp = (struct inpcb *)so->so_pcb; inp->inp_ip_p = proto; @@ -496,53 +499,60 @@ div_attach(struct socket *so, int proto, struct pru_attach_info *ai) */ sosetstate(so, SS_ISCONNECTED); lwkt_reltoken(&div_token); - return 0; + error = 0; +out: + lwkt_replymsg(&msg->attach.base.lmsg, error); } -static int -div_detach(struct socket *so) +static void +div_detach(netmsg_t msg) { + struct socket *so = msg->detach.base.nm_so; struct inpcb *inp; inp = so->so_pcb; if (inp == NULL) panic("div_detach"); in_pcbdetach(inp); - return 0; + lwkt_replymsg(&msg->detach.base.lmsg, 0); } /* * NOTE: (so) is referenced from soabort*() and netmsg_pru_abort() * will sofree() it when we return. */ -static int -div_abort(struct socket *so) +static void +div_abort(netmsg_t msg) { - int error; + struct socket *so = msg->abort.base.nm_so; soisdisconnected(so); - error = div_detach(so); - - return error; + div_detach(msg); + /* msg invalid now */ } -static int -div_disconnect(struct socket *so) +static void +div_disconnect(netmsg_t msg) { + struct socket *so = msg->disconnect.base.nm_so; int error; - if (!(so->so_state & SS_ISCONNECTED)) - return ENOTCONN; - soreference(so); - error = div_abort(so); - sofree(so); - - return error; + if (so->so_state & SS_ISCONNECTED) { + soreference(so); + div_abort(msg); + /* msg invalid now */ + sofree(so); + return; + } + error = ENOTCONN; + lwkt_replymsg(&msg->disconnect.base.lmsg, error); } -static int -div_bind(struct socket *so, struct sockaddr *nam, struct thread *td) +static void +div_bind(netmsg_t msg) { + struct socket *so = msg->bind.base.nm_so; + struct sockaddr *nam = msg->bind.nm_nam; int error; /* @@ -557,27 +567,36 @@ div_bind(struct socket *so, struct sockaddr *nam, struct thread *td) error = EAFNOSUPPORT; } else { ((struct sockaddr_in *)nam)->sin_addr.s_addr = INADDR_ANY; - error = in_pcbbind(so->so_pcb, nam, td); + error = in_pcbbind(so->so_pcb, nam, msg->bind.nm_td); } - return error; + lwkt_replymsg(&msg->bind.base.lmsg, error); } -static int -div_shutdown(struct socket *so) +static void +div_shutdown(netmsg_t msg) { + struct socket *so = msg->shutdown.base.nm_so; + socantsendmore(so); - return 0; + + lwkt_replymsg(&msg->shutdown.base.lmsg, 0); } -static int -div_send(struct socket *so, int flags, struct mbuf *m, struct sockaddr *nam, - struct mbuf *control, struct thread *td) +static void +div_send(netmsg_t msg) { + struct socket *so = msg->send.base.nm_so; + struct mbuf *m = msg->send.nm_m; + struct sockaddr *nam = msg->send.nm_addr; + struct mbuf *control = msg->send.nm_control; + int error; + /* Length check already done in ip_cpufn() */ KASSERT(m->m_len >= sizeof(struct ip), ("IP header not in one mbuf")); /* Send packet */ - return div_output(so, m, (struct sockaddr_in *)nam, control); + error = div_output(so, m, (struct sockaddr_in *)nam, control); + lwkt_replymsg(&msg->send.base.lmsg, error); } SYSCTL_DECL(_net_inet_divert); @@ -586,22 +605,22 @@ SYSCTL_PROC(_net_inet_divert, OID_AUTO, pcblist, CTLFLAG_RD, &divcbinfo, 0, struct pr_usrreqs div_usrreqs = { .pru_abort = div_abort, - .pru_accept = pru_accept_notsupp, + .pru_accept = pr_generic_notsupp, .pru_attach = div_attach, .pru_bind = div_bind, - .pru_connect = pru_connect_notsupp, - .pru_connect2 = pru_connect2_notsupp, - .pru_control = in_control, + .pru_connect = pr_generic_notsupp, + .pru_connect2 = pr_generic_notsupp, + .pru_control = in_control_dispatch, .pru_detach = div_detach, .pru_disconnect = div_disconnect, - .pru_listen = pru_listen_notsupp, - .pru_peeraddr = in_setpeeraddr, - .pru_rcvd = pru_rcvd_notsupp, - .pru_rcvoob = pru_rcvoob_notsupp, + .pru_listen = pr_generic_notsupp, + .pru_peeraddr = in_setpeeraddr_dispatch, + .pru_rcvd = pr_generic_notsupp, + .pru_rcvoob = pr_generic_notsupp, .pru_send = div_send, .pru_sense = pru_sense_null, .pru_shutdown = div_shutdown, - .pru_sockaddr = in_setsockaddr, + .pru_sockaddr = in_setsockaddr_dispatch, .pru_sosend = sosend, .pru_soreceive = soreceive }; diff --git a/sys/netinet/ip_divert.h b/sys/netinet/ip_divert.h index f029e31b91..b050095a05 100644 --- a/sys/netinet/ip_divert.h +++ b/sys/netinet/ip_divert.h @@ -49,7 +49,7 @@ struct divert_info { }; void div_init(void); -void div_input(struct mbuf *, ...); +int div_input(struct mbuf **, int *offp, int); struct lwkt_port * div_soport(struct socket *, struct sockaddr *, struct mbuf **); diff --git a/sys/netinet/ip_encap.c b/sys/netinet/ip_encap.c index 9f8e06301d..cfdd03fb2b 100644 --- a/sys/netinet/ip_encap.c +++ b/sys/netinet/ip_encap.c @@ -106,7 +106,7 @@ LIST_HEAD(, encaptab) encaptab; LIST_HEAD(, encaptab) encaptab = LIST_HEAD_INITIALIZER(&encaptab); #endif -void (*ipip_input)(struct mbuf *, int, int); /* hook for mrouting */ +int (*ipip_input)(struct mbuf **, int *, int); /* hook for mrouting */ void encap_init(void) @@ -129,23 +129,19 @@ encap_init(void) } #ifdef INET -void -encap4_input(struct mbuf *m, ...) +int +encap4_input(struct mbuf **mp, int *offp, int proto) { - int off, proto; + struct mbuf *m = *mp; + int off = *offp; struct ip *ip; struct sockaddr_in s, d; const struct protosw *psw; struct encaptab *ep, *match; int prio, matchprio; - __va_list ap; - - __va_start(ap, m); - off = __va_arg(ap, int); - proto = __va_arg(ap, int); - __va_end(ap); ip = mtod(m, struct ip *); + *mp = NULL; bzero(&s, sizeof s); s.sin_family = AF_INET; @@ -170,8 +166,9 @@ encap4_input(struct mbuf *m, ...) * it's inbound traffic, we need to match in reverse * order */ - prio = mask_match(ep, (struct sockaddr *)&d, - (struct sockaddr *)&s); + prio = mask_match(ep, + (struct sockaddr *)&d, + (struct sockaddr *)&s); } /* @@ -205,20 +202,25 @@ encap4_input(struct mbuf *m, ...) psw = match->psw; if (psw && psw->pr_input) { encap_fillarg(m, match); - (*psw->pr_input)(m, off, proto); - } else + *mp = m; + (*psw->pr_input)(mp, offp, proto); + } else { m_freem(m); - return; + } + return(IPPROTO_DONE); } /* for backward compatibility */ if (proto == IPPROTO_IPV4 && ipip_input) { - ipip_input(m, off, proto); - return; + *mp = m; + ipip_input(mp, offp, proto); + return(IPPROTO_DONE); } /* last resort: inject to raw socket */ - rip_input(m, off, proto); + *mp = m; + rip_input(mp, offp, proto); + return(IPPROTO_DONE); } #endif @@ -229,7 +231,7 @@ encap6_input(struct mbuf **mp, int *offp, int proto) struct mbuf *m = *mp; struct ip6_hdr *ip6; struct sockaddr_in6 s, d; - const struct ip6protosw *psw; + const struct protosw *psw; struct encaptab *ep, *match; int prio, matchprio; @@ -273,7 +275,7 @@ encap6_input(struct mbuf **mp, int *offp, int proto) if (match) { /* found a match */ - psw = (const struct ip6protosw *)match->psw; + psw = match->psw; if (psw && psw->pr_input) { encap_fillarg(m, match); return (*psw->pr_input)(mp, offp, proto); diff --git a/sys/netinet/ip_encap.h b/sys/netinet/ip_encap.h index 86e149fb0e..62e21713a5 100644 --- a/sys/netinet/ip_encap.h +++ b/sys/netinet/ip_encap.h @@ -63,7 +63,7 @@ struct encaptab { #ifdef _KERNEL void encap_init(void); -void encap4_input(struct mbuf *, ...); +int encap4_input(struct mbuf **, int *, int); int encap6_input(struct mbuf **, int *, int); const struct encaptab *encap_attach(int, int, const struct sockaddr *, const struct sockaddr *, const struct sockaddr *, diff --git a/sys/netinet/ip_flow.c b/sys/netinet/ip_flow.c index 5c8f19b645..439384bd6c 100644 --- a/sys/netinet/ip_flow.c +++ b/sys/netinet/ip_flow.c @@ -71,7 +71,7 @@ ((rt)->rt_ifp->if_flags & IFF_UP) == 0) struct netmsg_ipfaddr { - struct netmsg ipf_nmsg; + struct netmsg_base base; struct in_addr ipf_addr; }; @@ -106,7 +106,7 @@ LIST_HEAD(ipflowhead, ipflow); static struct ipflowhead ipflowtable_pcpu[MAXCPU][IPFLOW_HASHSIZE]; static struct ipflowhead ipflowlist_pcpu[MAXCPU]; static int ipflow_inuse_pcpu[MAXCPU]; -static struct netmsg ipflow_timo_netmsgs[MAXCPU]; +static struct netmsg_base ipflow_timo_netmsgs[MAXCPU]; static int ipflow_active = 0; #define IPFLOW_REFCNT_INIT 1 @@ -395,12 +395,12 @@ done: } static void -ipflow_timo_dispatch(struct netmsg *nmsg) +ipflow_timo_dispatch(netmsg_t nmsg) { struct ipflow *ipf, *next_ipf; crit_enter(); - lwkt_replymsg(&nmsg->nm_lmsg, 0); /* reply ASAP */ + lwkt_replymsg(&nmsg->lmsg, 0); /* reply ASAP */ crit_exit(); LIST_FOREACH_MUTABLE(ipf, &ipflowlist, ipf_list, next_ipf) { @@ -421,7 +421,7 @@ ipflow_timo_dispatch(struct netmsg *nmsg) static void ipflow_timo_ipi(void *arg __unused) { - struct lwkt_msg *msg = &ipflow_timo_netmsgs[mycpuid].nm_lmsg; + struct lwkt_msg *msg = &ipflow_timo_netmsgs[mycpuid].lmsg; crit_enter(); if (msg->ms_flags & MSGF_DONE) @@ -524,7 +524,7 @@ ipflow_flush_oncpu(void) } static void -ipflow_ifaddr_handler(struct netmsg *nmsg) +ipflow_ifaddr_handler(netmsg_t nmsg) { struct netmsg_ipfaddr *amsg = (struct netmsg_ipfaddr *)nmsg; struct ipflow *ipf, *next_ipf; @@ -536,7 +536,7 @@ ipflow_ifaddr_handler(struct netmsg *nmsg) IPFLOW_FREE(ipf); } } - ifnet_forwardmsg(&nmsg->nm_lmsg, mycpuid + 1); + ifnet_forwardmsg(&nmsg->lmsg, mycpuid + 1); } static void @@ -558,11 +558,11 @@ ipflow_ifaddr(void *arg __unused, struct ifnet *ifp __unused, return; } - netmsg_init(&amsg.ipf_nmsg, NULL, &curthread->td_msgport, + netmsg_init(&amsg.base, NULL, &curthread->td_msgport, MSGF_PRIORITY, ipflow_ifaddr_handler); amsg.ipf_addr = ifatoia(ifa)->ia_addr.sin_addr; - ifnet_domsg(&amsg.ipf_nmsg.nm_lmsg, 0); + ifnet_domsg(&amsg.base.lmsg, 0); } static void diff --git a/sys/netinet/ip_gre.c b/sys/netinet/ip_gre.c index 7ecf5cbb84..77a6c3ffb1 100644 --- a/sys/netinet/ip_gre.c +++ b/sys/netinet/ip_gre.c @@ -106,15 +106,15 @@ static int gre_input2(struct mbuf *, int, u_char); * IPPROTO_GRE and a local destination address). * This really is simple */ -void -gre_input(struct mbuf *m, ...) +int +gre_input(struct mbuf **mp, int *offp, int proto) { - int ret, off, proto; - __va_list ap; + struct mbuf *m; + int ret, off; - __va_start(ap, m); - off = __va_arg(ap, int); - __va_end(ap); + off = *offp; + m = *mp; + *mp = NULL; proto = (mtod(m, struct ip *))->ip_p; @@ -124,8 +124,11 @@ gre_input(struct mbuf *m, ...) * no matching tunnel that is up is found. * we inject it to raw ip socket to see if anyone picks it up. */ - if (ret == 0) - rip_input(m, off, proto); + if (ret == 0) { + *mp = m; + rip_input(mp, offp, proto); + } + return(IPPROTO_DONE); } /* @@ -217,25 +220,23 @@ gre_input2(struct mbuf *m ,int hlen, u_char proto) * between IP header and payload */ -void -gre_mobile_input(struct mbuf *m, ...) +int +gre_mobile_input(struct mbuf **mp, int *offp, int proto) { static const uint32_t af = AF_INET; + struct mbuf *m = *mp; struct ip *ip = mtod(m, struct ip *); struct mobip_h *mip = mtod(m, struct mobip_h *); struct gre_softc *sc; u_char osrc = 0; int msiz, hlen; - __va_list ap; - __va_start(ap, m); - hlen = __va_arg(ap, int); - __va_end(ap); + hlen = *offp; if ((sc = gre_lookup(m, IPPROTO_MOBILE)) == NULL) { /* No matching tunnel or tunnel is down. */ m_freem(m); - return; + return(IPPROTO_DONE); } sc->sc_if.if_ipackets++; @@ -253,7 +254,7 @@ gre_mobile_input(struct mbuf *m, ...) if (gre_in_cksum((u_short*)&mip->mh,msiz) != 0) { m_freem(m); - return; + return(IPPROTO_DONE); } bcopy((caddr_t)(ip) + (ip->ip_hl << 2) + msiz, (caddr_t)(ip) + @@ -279,6 +280,7 @@ gre_mobile_input(struct mbuf *m, ...) m->m_pkthdr.rcvif = &sc->sc_if; netisr_queue(NETISR_IP, m); + return(IPPROTO_DONE); } /* diff --git a/sys/netinet/ip_gre.h b/sys/netinet/ip_gre.h index 6883047d21..e416bd582e 100644 --- a/sys/netinet/ip_gre.h +++ b/sys/netinet/ip_gre.h @@ -44,8 +44,8 @@ struct mbuf; -void gre_input(struct mbuf *, ...); -void gre_mobile_input(struct mbuf *, ...); +int gre_input(struct mbuf **, int *, int); +int gre_mobile_input(struct mbuf **, int *, int); #endif /* _KERNEL */ diff --git a/sys/netinet/ip_icmp.c b/sys/netinet/ip_icmp.c index 521c463491..1945f897b6 100644 --- a/sys/netinet/ip_icmp.c +++ b/sys/netinet/ip_icmp.c @@ -251,26 +251,22 @@ freeit: /* * Process a received ICMP message. */ -void -icmp_input(struct mbuf *m, ...) +int +icmp_input(struct mbuf **mp, int *offp, int proto) { struct sockaddr_in icmpsrc = { sizeof(struct sockaddr_in), AF_INET }; struct sockaddr_in icmpdst = { sizeof(struct sockaddr_in), AF_INET }; struct sockaddr_in icmpgw = { sizeof(struct sockaddr_in), AF_INET }; struct icmp *icp; struct in_ifaddr *ia; + struct mbuf *m = *mp; struct ip *ip = mtod(m, struct ip *); int icmplen = ip->ip_len; int i, hlen; - int code, off, proto; - __va_list ap; - - __va_start(ap, m); - off = __va_arg(ap, int); - proto = __va_arg(ap, int); - __va_end(ap); + int code; - hlen = off; + *mp = NULL; + hlen = *offp; /* * Locate icmp structure in mbuf, and check @@ -292,7 +288,7 @@ icmp_input(struct mbuf *m, ...) i = hlen + min(icmplen, ICMP_ADVLENMIN); if (m->m_len < i && (m = m_pullup(m, i)) == 0) { icmpstat.icps_tooshort++; - return; + return(IPPROTO_DONE); } ip = mtod(m, struct ip *); m->m_len -= hlen; @@ -533,7 +529,7 @@ reflect: icmpstat.icps_reflect++; icmpstat.icps_outhist[icp->icmp_type]++; icmp_reflect(m); - return; + return(IPPROTO_DONE); case ICMP_REDIRECT: if (log_redirect) { @@ -604,11 +600,13 @@ reflect: } raw: - rip_input(m, off, proto); - return; + *mp = m; + rip_input(mp, offp, proto); + return(IPPROTO_DONE); freeit: m_freem(m); + return(IPPROTO_DONE); } /* @@ -807,8 +805,8 @@ static void icmp_send(struct mbuf *m, struct mbuf *opts, struct route *rt) { struct ip *ip = mtod(m, struct ip *); - int hlen; struct icmp *icp; + int hlen; hlen = IP_VHL_HL(ip->ip_vhl) << 2; m->m_data += hlen; diff --git a/sys/netinet/ip_icmp.h b/sys/netinet/ip_icmp.h index dc204a1f16..1b1f74c014 100644 --- a/sys/netinet/ip_icmp.h +++ b/sys/netinet/ip_icmp.h @@ -215,7 +215,7 @@ struct icmp { #ifdef _KERNEL void icmp_error (struct mbuf *, int, int, n_long, int); -void icmp_input (struct mbuf *, ...); +int icmp_input (struct mbuf **, int *, int); int ip_next_mtu (int, int); #endif diff --git a/sys/netinet/ip_input.c b/sys/netinet/ip_input.c index 171a39f0d7..e12702be39 100644 --- a/sys/netinet/ip_input.c +++ b/sys/netinet/ip_input.c @@ -312,7 +312,7 @@ static struct malloc_pipe ipq_mpipe; static void save_rte(struct mbuf *, u_char *, struct in_addr); static int ip_dooptions(struct mbuf *m, int, struct sockaddr_in *); static void ip_freef(struct ipq *); -static void ip_input_handler(struct netmsg *); +static void ip_input_handler(netmsg_t); /* * IP initialization: fill in IP protocol switch table. @@ -391,31 +391,29 @@ transport_processing_oncpu(struct mbuf *m, int hlen, struct ip *ip) * Switch out to protocol's input routine. */ PR_GET_MPLOCK(pr); - pr->pr_input(m, hlen, ip->ip_p); + pr->pr_input(&m, &hlen, ip->ip_p); PR_REL_MPLOCK(pr); } static void -transport_processing_handler(netmsg_t netmsg) +transport_processing_handler(netmsg_t msg) { - struct netmsg_packet *pmsg = (struct netmsg_packet *)netmsg; + struct netmsg_packet *pmsg = &msg->packet; struct ip *ip; int hlen; ip = mtod(pmsg->nm_packet, struct ip *); - hlen = pmsg->nm_netmsg.nm_lmsg.u.ms_result; + hlen = pmsg->base.lmsg.u.ms_result; transport_processing_oncpu(pmsg->nm_packet, hlen, ip); - /* netmsg was embedded in the mbuf, do not reply! */ + /* msg was embedded in the mbuf, do not reply! */ } static void -ip_input_handler(struct netmsg *msg0) +ip_input_handler(netmsg_t msg) { - struct mbuf *m = ((struct netmsg_packet *)msg0)->nm_packet; - - ip_input(m); - /* msg0 was embedded in the mbuf, do not reply! */ + ip_input(msg->packet.nm_packet); + /* msg was embedded in the mbuf, do not reply! */ } /* @@ -951,12 +949,11 @@ DPRINTF(("ip_input: no SP, packet discarded\n"));/*XXX*/ ++ip_dispatch_slow; pmsg = &m->m_hdr.mh_netmsg; - netmsg_init(&pmsg->nm_netmsg, NULL, &netisr_apanic_rport, + netmsg_init(&pmsg->base, NULL, &netisr_apanic_rport, 0, transport_processing_handler); pmsg->nm_packet = m; - pmsg->nm_netmsg.nm_lmsg.u.ms_result = hlen; - - lwkt_sendmsg(port, &pmsg->nm_netmsg.nm_lmsg); + pmsg->base.lmsg.u.ms_result = hlen; + lwkt_sendmsg(port, &pmsg->base.lmsg); } else { ++ip_dispatch_fast; transport_processing_oncpu(m, hlen, ip); @@ -2233,20 +2230,19 @@ ip_rsvp_done(void) return 0; } -void -rsvp_input(struct mbuf *m, ...) /* XXX must fixup manually */ +int +rsvp_input(struct mbuf **mp, int *offp, int proto) { - int off, proto; - __va_list ap; + struct mbuf *m = *mp; + int off; - __va_start(ap, m); - off = __va_arg(ap, int); - proto = __va_arg(ap, int); - __va_end(ap); + off = *offp; + *mp = NULL; if (rsvp_input_p) { /* call the real one if loaded */ - rsvp_input_p(m, off, proto); - return; + *mp = m; + rsvp_input_p(mp, offp, proto); + return(IPPROTO_DONE); } /* Can still get packets with rsvp_on = 0 if there is a local member @@ -2256,13 +2252,15 @@ rsvp_input(struct mbuf *m, ...) /* XXX must fixup manually */ if (!rsvp_on) { m_freem(m); - return; + return(IPPROTO_DONE); } if (ip_rsvpd != NULL) { - rip_input(m, off, proto); - return; + *mp = m; + rip_input(mp, offp, proto); + return(IPPROTO_DONE); } /* Drop the packet */ m_freem(m); + return(IPPROTO_DONE); } diff --git a/sys/netinet/ip_output.c b/sys/netinet/ip_output.c index d59e840dc1..5be2b832b4 100644 --- a/sys/netinet/ip_output.c +++ b/sys/netinet/ip_output.c @@ -57,6 +57,7 @@ #include #include +#include #include #include @@ -1346,15 +1347,18 @@ ip_optcopy(struct ip *ip, struct ip *jp) /* * IP socket option processing. */ -int -ip_ctloutput(struct socket *so, struct sockopt *sopt) +void +ip_ctloutput(netmsg_t msg) { + struct socket *so = msg->base.nm_so; + struct sockopt *sopt = msg->ctloutput.nm_sopt; struct inpcb *inp = so->so_pcb; int error, optval; error = optval = 0; if (sopt->sopt_level != IPPROTO_IP) { - return (EINVAL); + error = EINVAL; + goto done; } switch (sopt->sopt_dir) { @@ -1378,8 +1382,9 @@ ip_ctloutput(struct socket *so, struct sockopt *sopt) m->m_len = sopt->sopt_valsize; error = soopt_to_kbuf(sopt, mtod(m, void *), m->m_len, m->m_len); - return (ip_pcbopts(sopt->sopt_name, &inp->inp_options, - m)); + error = ip_pcbopts(sopt->sopt_name, + &inp->inp_options, m); + goto done; } case IP_TOS: @@ -1616,7 +1621,8 @@ ip_ctloutput(struct socket *so, struct sockopt *sopt) } break; } - return (error); +done: + lwkt_replymsg(&msg->lmsg, error); } /* diff --git a/sys/netinet/ip_var.h b/sys/netinet/ip_var.h index 140ccbaff4..6a1640a814 100644 --- a/sys/netinet/ip_var.h +++ b/sys/netinet/ip_var.h @@ -179,6 +179,7 @@ struct route; struct sockopt; struct lwkt_port; struct pktinfo; +union netmsg; extern u_short ip_id; /* ip packet ctr, for ids */ extern int ip_defttl; /* default IP ttl */ @@ -191,7 +192,7 @@ extern u_long (*ip_mcast_src)(int); extern int rsvp_on; extern struct pr_usrreqs rip_usrreqs; -int ip_ctloutput(struct socket *, struct sockopt *sopt); +void ip_ctloutput(union netmsg *); void ip_drain(void); int ip_fragment(struct ip *ip, struct mbuf **m_frag, int mtu, u_long if_hwassist_flags, int sw_csum); @@ -219,18 +220,18 @@ struct mbuf * ip_srcroute(struct mbuf *); void ip_stripoptions(struct mbuf *); u_int16_t ip_randomid(void); -int rip_ctloutput(struct socket *, struct sockopt *); -void rip_ctlinput(int, struct sockaddr *, void *); +void rip_ctloutput(union netmsg *); +void rip_ctlinput(union netmsg *); void rip_init(void); -void rip_input(struct mbuf *, ...); +int rip_input(struct mbuf **, int *, int); int rip_output(struct mbuf *, struct socket *, ...); -extern void (*ipip_input)(struct mbuf *, int, int); -void rsvp_input(struct mbuf *, ...); +extern int (*ipip_input)(struct mbuf **, int *, int); +int rsvp_input(struct mbuf **, int *, int); int ip_rsvp_init(struct socket *); int ip_rsvp_done(void); extern int (*ip_rsvp_vif)(struct socket *, struct sockopt *); extern void (*ip_rsvp_force_done)(struct socket *); -extern void (*rsvp_input_p)(struct mbuf *m, ...); +extern int (*rsvp_input_p)(struct mbuf **, int *, int); extern struct pfil_head inet_pfil_hook; diff --git a/sys/netinet/pim_var.h b/sys/netinet/pim_var.h index 99fde855d8..707da73026 100644 --- a/sys/netinet/pim_var.h +++ b/sys/netinet/pim_var.h @@ -87,7 +87,7 @@ struct pimstat { struct mbuf; -void pim_input(struct mbuf *, ...); +int pim_input(struct mbuf **, int *, int); SYSCTL_DECL(_net_inet_pim); #endif diff --git a/sys/netinet/raw_ip.c b/sys/netinet/raw_ip.c index 20be825f0d..a824dcc33d 100644 --- a/sys/netinet/raw_ip.c +++ b/sys/netinet/raw_ip.c @@ -53,6 +53,7 @@ #include #include +#include #include @@ -106,7 +107,7 @@ int (*mrt_ioctl)(int, caddr_t); int (*legal_vif_num)(int); u_long (*ip_mcast_src)(int); -void (*rsvp_input_p)(struct mbuf *m, ...); +int (*rsvp_input_p)(struct mbuf **, int *, int); int (*ip_rsvp_vif)(struct socket *, struct sockopt *); void (*ip_rsvp_force_done)(struct socket *); @@ -144,21 +145,19 @@ rip_init(void) * for raw_input routine, then pass them along with * mbuf chain. */ -void -rip_input(struct mbuf *m, ...) +int +rip_input(struct mbuf **mp, int *offp, int proto) { struct sockaddr_in ripsrc = { sizeof ripsrc, AF_INET }; + struct mbuf *m = *mp; struct ip *ip = mtod(m, struct ip *); struct inpcb *inp; struct inpcb *last = NULL; struct mbuf *opts = NULL; - int off, proto; - __va_list ap; + int off; - __va_start(ap, m); - off = __va_arg(ap, int); - proto = __va_arg(ap, int); - __va_end(ap); + off = *offp; + *mp = NULL; ripsrc.sin_addr = ip->ip_src; lwkt_gettoken(&raw_token); @@ -257,6 +256,7 @@ rip_input(struct mbuf *m, ...) ipstat.ips_delivered--; } lwkt_reltoken(&raw_token); + return(IPPROTO_DONE); } /* @@ -341,14 +341,18 @@ rip_output(struct mbuf *m, struct socket *so, ...) /* * Raw IP socket option processing. */ -int -rip_ctloutput(struct socket *so, struct sockopt *sopt) +void +rip_ctloutput(netmsg_t msg) { + struct socket *so = msg->base.nm_so; + struct sockopt *sopt = msg->ctloutput.nm_sopt; struct inpcb *inp = so->so_pcb; int error, optval; - if (sopt->sopt_level != IPPROTO_IP) - return (EINVAL); + if (sopt->sopt_level != IPPROTO_IP) { + error = EINVAL; + goto done; + } error = 0; @@ -389,8 +393,9 @@ rip_ctloutput(struct socket *so, struct sockopt *sopt) break; default: - error = ip_ctloutput(so, sopt); - break; + ip_ctloutput(msg); + /* msg invalid now */ + return; } break; @@ -455,13 +460,14 @@ rip_ctloutput(struct socket *so, struct sockopt *sopt) break; default: - error = ip_ctloutput(so, sopt); - break; + ip_ctloutput(msg); + /* msg invalid now */ + return; } break; } - - return (error); +done: + lwkt_replymsg(&msg->lmsg, error); } /* @@ -472,8 +478,10 @@ rip_ctloutput(struct socket *so, struct sockopt *sopt) * interface routes. */ void -rip_ctlinput(int cmd, struct sockaddr *sa, void *vip) +rip_ctlinput(netmsg_t msg) { + int cmd = msg->ctlinput.nm_cmd; + struct sockaddr *sa = msg->ctlinput.nm_arg; struct in_ifaddr *ia; struct in_ifaddr_container *iac; struct ifnet *ifp; @@ -512,7 +520,7 @@ rip_ctlinput(int cmd, struct sockaddr *sa, void *vip) } } if (ia == NULL || (ia->ia_flags & IFA_ROUTE)) - return; + goto done; flags = RTF_UP; ifp = ia->ia_ifa.ifa_ifp; @@ -525,6 +533,8 @@ rip_ctlinput(int cmd, struct sockaddr *sa, void *vip) ia->ia_flags |= IFA_ROUTE; break; } +done: + lwkt_replymsg(&msg->lmsg, 0); } u_long rip_sendspace = RIPSNDQ; @@ -535,9 +545,12 @@ SYSCTL_INT(_net_inet_raw, OID_AUTO, maxdgram, CTLFLAG_RW, SYSCTL_INT(_net_inet_raw, OID_AUTO, recvspace, CTLFLAG_RW, &rip_recvspace, 0, "Maximum incoming raw IP datagram size"); -static int -rip_attach(struct socket *so, int proto, struct pru_attach_info *ai) +static void +rip_attach(netmsg_t msg) { + struct socket *so = msg->base.nm_so; + int proto = msg->attach.nm_proto; + struct pru_attach_info *ai = msg->attach.nm_ai; struct inpcb *inp; int error; @@ -546,11 +559,12 @@ rip_attach(struct socket *so, int proto, struct pru_attach_info *ai) panic("rip_attach"); error = priv_check_cred(ai->p_ucred, PRIV_NETINET_RAW, NULL_CRED_OKAY); if (error) - return error; + goto done; error = soreserve(so, rip_sendspace, rip_recvspace, ai->sb_rlimit); if (error) - return error; + goto done; + lwkt_gettoken(&raw_token); error = in_pcballoc(so, &ripcbinfo); if (error == 0) { @@ -560,12 +574,15 @@ rip_attach(struct socket *so, int proto, struct pru_attach_info *ai) inp->inp_ip_ttl = ip_defttl; } lwkt_reltoken(&raw_token); - return 0; + error = 0; +done: + lwkt_replymsg(&msg->lmsg, error); } -static int -rip_detach(struct socket *so) +static void +rip_detach(netmsg_t msg) { + struct socket *so = msg->base.nm_so; struct inpcb *inp; inp = so->so_pcb; @@ -578,105 +595,135 @@ rip_detach(struct socket *so) if (so == ip_rsvpd) ip_rsvp_done(); in_pcbdetach(inp); - return 0; + lwkt_replymsg(&msg->lmsg, 0); } /* * NOTE: (so) is referenced from soabort*() and netmsg_pru_abort() * will sofree() it when we return. */ -static int -rip_abort(struct socket *so) +static void +rip_abort(netmsg_t msg) { + struct socket *so = msg->base.nm_so; int error; soisdisconnected(so); - if (so->so_state & SS_NOFDREF) /* XXX not sure why this test */ - error = rip_detach(so); - else - error = 0; - - return error; + if (so->so_state & SS_NOFDREF) { /* XXX not sure why this test */ + rip_detach(msg); + /* msg invalid now */ + return; + } + error = 0; + lwkt_replymsg(&msg->lmsg, error); } -static int -rip_disconnect(struct socket *so) +static void +rip_disconnect(netmsg_t msg) { + struct socket *so = msg->base.nm_so; int error; - if ((so->so_state & SS_ISCONNECTED) == 0) - return ENOTCONN; - soreference(so); - error = rip_abort(so); - sofree(so); - - return error; + if (so->so_state & SS_ISCONNECTED) { + soreference(so); + rip_abort(msg); + /* msg invalid now */ + sofree(so); + return; + } + error = ENOTCONN; + lwkt_replymsg(&msg->lmsg, error); } -static int -rip_bind(struct socket *so, struct sockaddr *nam, struct thread *td) +static void +rip_bind(netmsg_t msg) { + struct socket *so = msg->base.nm_so; + struct sockaddr *nam = msg->bind.nm_nam; struct inpcb *inp = so->so_pcb; struct sockaddr_in *addr = (struct sockaddr_in *)nam; + int error; - if (nam->sa_len != sizeof(*addr)) - return EINVAL; - - if (TAILQ_EMPTY(&ifnet) || ((addr->sin_family != AF_INET) && - (addr->sin_family != AF_IMPLINK)) || - (addr->sin_addr.s_addr != INADDR_ANY && - ifa_ifwithaddr((struct sockaddr *)addr) == 0)) - return EADDRNOTAVAIL; - inp->inp_laddr = addr->sin_addr; - return 0; + if (nam->sa_len == sizeof(*addr)) { + if (TAILQ_EMPTY(&ifnet) || + ((addr->sin_family != AF_INET) && + (addr->sin_family != AF_IMPLINK)) || + (addr->sin_addr.s_addr != INADDR_ANY && + ifa_ifwithaddr((struct sockaddr *)addr) == 0)) { + error = EADDRNOTAVAIL; + } else { + inp->inp_laddr = addr->sin_addr; + error = 0; + } + } else { + error = EINVAL; + } + lwkt_replymsg(&msg->lmsg, error); } -static int -rip_connect(struct socket *so, struct sockaddr *nam, struct thread *td) +static void +rip_connect(netmsg_t msg) { + struct socket *so = msg->base.nm_so; + struct sockaddr *nam = msg->connect.nm_nam; struct inpcb *inp = so->so_pcb; struct sockaddr_in *addr = (struct sockaddr_in *)nam; + int error; - if (nam->sa_len != sizeof(*addr)) - return EINVAL; - if (TAILQ_EMPTY(&ifnet)) - return EADDRNOTAVAIL; - if ((addr->sin_family != AF_INET) && - (addr->sin_family != AF_IMPLINK)) - return EAFNOSUPPORT; - inp->inp_faddr = addr->sin_addr; - soisconnected(so); - return 0; + if (nam->sa_len != sizeof(*addr)) { + error = EINVAL; + } else if (TAILQ_EMPTY(&ifnet)) { + error = EADDRNOTAVAIL; + } else { + if ((addr->sin_family != AF_INET) && + (addr->sin_family != AF_IMPLINK)) { + error = EAFNOSUPPORT; + } else { + inp->inp_faddr = addr->sin_addr; + soisconnected(so); + error = 0; + } + } + lwkt_replymsg(&msg->lmsg, error); } -static int -rip_shutdown(struct socket *so) +static void +rip_shutdown(netmsg_t msg) { - socantsendmore(so); - return 0; + socantsendmore(msg->base.nm_so); + lwkt_replymsg(&msg->lmsg, 0); } -static int -rip_send(struct socket *so, int flags, struct mbuf *m, struct sockaddr *nam, - struct mbuf *control, struct thread *td) +static void +rip_send(netmsg_t msg) { + struct socket *so = msg->base.nm_so; + struct mbuf *m = msg->send.nm_m; + /*struct mbuf *control = msg->send.nm_control;*/ + struct sockaddr *nam = msg->send.nm_addr; + /*int flags = msg->send.nm_flags;*/ struct inpcb *inp = so->so_pcb; u_long dst; + int error; if (so->so_state & SS_ISCONNECTED) { if (nam) { m_freem(m); - return EISCONN; + error = EISCONN; + } else { + dst = inp->inp_faddr.s_addr; + error = rip_output(m, so, dst); } - dst = inp->inp_faddr.s_addr; } else { if (nam == NULL) { m_freem(m); - return ENOTCONN; + error = ENOTCONN; + } else { + dst = ((struct sockaddr_in *)nam)->sin_addr.s_addr; + error = rip_output(m, so, dst); } - dst = ((struct sockaddr_in *)nam)->sin_addr.s_addr; } - return rip_output(m, so, dst); + lwkt_replymsg(&msg->lmsg, error); } SYSCTL_PROC(_net_inet_raw, OID_AUTO/*XXX*/, pcblist, CTLFLAG_RD, &ripcbinfo, 0, @@ -684,22 +731,22 @@ SYSCTL_PROC(_net_inet_raw, OID_AUTO/*XXX*/, pcblist, CTLFLAG_RD, &ripcbinfo, 0, struct pr_usrreqs rip_usrreqs = { .pru_abort = rip_abort, - .pru_accept = pru_accept_notsupp, + .pru_accept = pr_generic_notsupp, .pru_attach = rip_attach, .pru_bind = rip_bind, .pru_connect = rip_connect, - .pru_connect2 = pru_connect2_notsupp, - .pru_control = in_control, + .pru_connect2 = pr_generic_notsupp, + .pru_control = in_control_dispatch, .pru_detach = rip_detach, .pru_disconnect = rip_disconnect, - .pru_listen = pru_listen_notsupp, - .pru_peeraddr = in_setpeeraddr, - .pru_rcvd = pru_rcvd_notsupp, - .pru_rcvoob = pru_rcvoob_notsupp, + .pru_listen = pr_generic_notsupp, + .pru_peeraddr = in_setpeeraddr_dispatch, + .pru_rcvd = pr_generic_notsupp, + .pru_rcvoob = pr_generic_notsupp, .pru_send = rip_send, .pru_sense = pru_sense_null, .pru_shutdown = rip_shutdown, - .pru_sockaddr = in_setsockaddr, + .pru_sockaddr = in_setsockaddr_dispatch, .pru_sosend = sosend, .pru_soreceive = soreceive }; diff --git a/sys/netinet/sctp_input.c b/sys/netinet/sctp_input.c index 14511d9def..5f7ee39ddc 100644 --- a/sys/netinet/sctp_input.c +++ b/sys/netinet/sctp_input.c @@ -4075,15 +4075,11 @@ sctp_saveopt(struct sctp_inpcb *inp, struct mbuf **mp, struct ip *ip, extern int sctp_no_csum_on_loopback; -#if defined(__FreeBSD__) || defined(__APPLE__) -void -sctp_input(struct mbuf *m, int off) -#else -void -sctp_input(struct mbuf *m, ...) -#endif +int +sctp_input(struct mbuf **mp, int *offp, int proto) { int iphlen; + struct mbuf *m = *mp; u_int8_t ecn_bits; struct ip *ip; struct sctphdr *sh; @@ -4108,22 +4104,7 @@ sctp_input(struct mbuf *m, ...) int error; #endif -#if !(defined(__FreeBSD__) || defined(__APPLE__)) -#ifdef __DragonFly__ - __va_list ap; - __va_start(ap, m); - iphlen = __va_arg(ap, int); - __va_end(ap); -#else - va_list ap; - - va_start(ap, m); - iphlen = va_arg(ap, int); - va_end(ap); -#endif -#else - iphlen = off; -#endif + iphlen = *offp; net = NULL; sctp_pegs[SCTP_INPKTS]++; #ifdef SCTP_DEBUG @@ -4152,7 +4133,7 @@ sctp_input(struct mbuf *m, ...) if (m->m_len < offset) { if ((m = m_pullup(m, offset)) == 0) { sctp_pegs[SCTP_HDR_DROPS]++; - return; + return(IPPROTO_DONE); } ip = mtod(m, struct ip *); } @@ -4398,7 +4379,7 @@ sctp_input(struct mbuf *m, ...) SCTP_INP_WUNLOCK(inp); } - return; + return(IPPROTO_DONE); bad: if (stcb) SCTP_TCB_UNLOCK(stcb); @@ -4415,5 +4396,5 @@ bad: } if (opts) sctp_m_freem(opts); - return; + return(IPPROTO_DONE); } diff --git a/sys/netinet/sctp_usrreq.c b/sys/netinet/sctp_usrreq.c index 3526f85984..54ce337260 100644 --- a/sys/netinet/sctp_usrreq.c +++ b/sys/netinet/sctp_usrreq.c @@ -63,7 +63,10 @@ #include #include #include + #include +#include + #include #include #if defined(__FreeBSD__) || defined(__APPLE__) || defined(__DragonFly__) @@ -448,34 +451,23 @@ sctp_notify(struct sctp_inpcb *inp, } } -#if defined(__FreeBSD__) || defined(__APPLE__) || defined(__DragonFly__) void -#else -void * -#endif -sctp_ctlinput(int cmd, struct sockaddr *sa, void *vip) +sctp_ctlinput(netmsg_t msg) { - struct ip *ip = vip; + int cmd = msg->ctlinput.nm_cmd; + struct sockaddr *sa = msg->ctlinput.nm_arg; + struct ip *ip = msg->ctlinput.nm_extra; struct sctphdr *sh; - if (sa->sa_family != AF_INET || ((struct sockaddr_in *)sa)->sin_addr.s_addr == INADDR_ANY) { -#if defined(__FreeBSD__) || defined(__APPLE__) || defined(__DragonFly__) - return; -#else - return (NULL); -#endif + goto out; } if (PRC_IS_REDIRECT(cmd)) { ip = 0; } else if ((unsigned)cmd >= PRC_NCMDS || inetctlerrmap[cmd] == 0) { -#if defined(__FreeBSD__) || defined(__APPLE__) || defined(__DragonFly__) - return; -#else - return (NULL); -#endif + goto out; } if (ip) { struct sctp_inpcb *inp; @@ -498,7 +490,6 @@ sctp_ctlinput(int cmd, struct sockaddr *sa, void *vip) * 'from' holds our local endpoint address. * Thus we reverse the to and the from in the lookup. */ - crit_enter(); stcb = sctp_findassociation_addr_sa((struct sockaddr *)&from, (struct sockaddr *)&to, &inp, &net, 1); @@ -533,13 +524,9 @@ sctp_ctlinput(int cmd, struct sockaddr *sa, void *vip) } } - crit_exit(); } -#if defined(__FreeBSD__) || defined(__APPLE__) || defined(__DragonFly__) - return; -#else - return (NULL); -#endif +out: + lwkt_replymsg(&msg->lmsg, 0); } #if defined(__FreeBSD__) || defined(__DragonFly__) @@ -563,7 +550,6 @@ sctp_getcred(SYSCTL_HANDLER_ARGS) if (error) return (error); - crit_enter(); stcb = sctp_findassociation_addr_sa(sintosa(&addrs[0]), sintosa(&addrs[1]), &inp, &net, 1); @@ -580,7 +566,6 @@ sctp_getcred(SYSCTL_HANDLER_ARGS) error = SYSCTL_OUT(req, inp->sctp_socket->so_cred, sizeof(struct ucred)); SCTP_TCB_UNLOCK(stcb); out: - crit_exit(); return (error); } @@ -702,9 +687,10 @@ SYSCTL_INT(_net_inet_sctp, OID_AUTO, debug, CTLFLAG_RW, * NOTE: (so) is referenced from soabort*() and netmsg_pru_abort() * will sofree() it when we return. */ -static int -sctp_abort(struct socket *so) +static void +sctp_abort(netmsg_t msg) { + struct socket *so = msg->abort.base.nm_so; struct sctp_inpcb *inp; int error; @@ -715,57 +701,42 @@ sctp_abort(struct socket *so) } else { error = EINVAL; } - return error; + lwkt_replymsg(&msg->lmsg, error); } -static int -#if defined(__FreeBSD__) && __FreeBSD_version >= 500000 -sctp_attach(struct socket *so, int proto, struct thread *p) -#elif defined(__DragonFly__) -sctp_attach(struct socket *so, int proto, struct pru_attach_info *ai) -#else -sctp_attach(struct socket *so, int proto, struct proc *p) -#endif +static void +sctp_attach(netmsg_t msg) { + struct socket *so = msg->attach.base.nm_so; struct sctp_inpcb *inp; struct inpcb *ip_inp; int error; - crit_enter(); inp = (struct sctp_inpcb *)so->so_pcb; - if (inp != 0) { - crit_exit(); - return EINVAL; + if (inp) { + error = EINVAL; + goto out; } error = soreserve(so, sctp_sendspace, sctp_recvspace, NULL); - if (error) { - crit_exit(); - return error; - } + if (error) + goto out; error = sctp_inpcb_alloc(so); - if (error) { - crit_exit(); - return error; - } + if (error) + goto out; inp = (struct sctp_inpcb *)so->so_pcb; SCTP_INP_WLOCK(inp); inp->sctp_flags &= ~SCTP_PCB_FLAGS_BOUND_V6; /* I'm not v6! */ ip_inp = &inp->ip_inp.inp; -#if defined(__FreeBSD__) || defined(__APPLE__) || defined(__DragonFly__) ip_inp->inp_vflag |= INP_IPV4; ip_inp->inp_ip_ttl = ip_defttl; -#else - inp->inp_vflag |= INP_IPV4; - inp->inp_ip_ttl = ip_defttl; -#endif #ifdef IPSEC #if !(defined(__OpenBSD__) || defined(__APPLE__)) error = ipsec_init_policy(so, &ip_inp->inp_sp); if (error != 0) { sctp_inpcb_free(inp, 1); - return error; + goto out; } #endif #endif /*IPSEC*/ @@ -773,82 +744,73 @@ sctp_attach(struct socket *so, int proto, struct proc *p) #if defined(__NetBSD__) so->so_send = sctp_sosend; #endif - crit_exit(); - return 0; + error = 0; +out: + lwkt_replymsg(&msg->lmsg, error); } -static int -#if (defined(__FreeBSD__) && __FreeBSD_version >= 500000) || defined(__DragonFly__) -sctp_bind(struct socket *so, struct sockaddr *addr, struct thread *p) -{ -#elif defined(__FreeBSD__) || defined(__APPLE__) -sctp_bind(struct socket *so, struct sockaddr *addr, struct proc *p) -{ -#else -sctp_bind(struct socket *so, struct mbuf *nam, struct proc *p) +static void +sctp_bind(netmsg_t msg) { - struct sockaddr *addr = nam ? mtod(nam, struct sockaddr *) : NULL; -#endif + struct socket *so = msg->bind.base.nm_so; + struct sockaddr *addr = msg->bind.nm_nam; + thread_t td = msg->bind.nm_td; struct sctp_inpcb *inp; int error; #ifdef INET6 - if (addr && addr->sa_family != AF_INET) + if (addr && addr->sa_family != AF_INET) { /* must be a v4 address! */ - return EINVAL; + error= EINVAL; + goto out; + } #endif /* INET6 */ inp = (struct sctp_inpcb *)so->so_pcb; - if (inp == 0) - return EINVAL; - - crit_enter(); - error = sctp_inpcb_bind(so, addr, p); - crit_exit(); - return error; + if (inp) { + error = sctp_inpcb_bind(so, addr, td); + } else { + error = EINVAL; + } +out: + lwkt_replymsg(&msg->lmsg, error); } -static int -sctp_detach(struct socket *so) +static void +sctp_detach(netmsg_t msg) { + struct socket *so = msg->detach.base.nm_so; struct sctp_inpcb *inp; + int error; inp = (struct sctp_inpcb *)so->so_pcb; - if (inp == 0) - return EINVAL; - crit_enter(); + if (inp == NULL) { + error = EINVAL; + goto out; + } if (((so->so_options & SO_LINGER) && (so->so_linger == 0)) || (so->so_rcv.ssb_cc > 0)) { sctp_inpcb_free(inp, 1); } else { sctp_inpcb_free(inp, 0); } - crit_exit(); - return 0; + error = 0; +out: + lwkt_replymsg(&msg->lmsg, error); } -int -#if (defined(__FreeBSD__) && __FreeBSD_version >= 500000) || defined(__DragonFly__) -sctp_send(struct socket *so, int flags, struct mbuf *m, struct sockaddr *addr, - struct mbuf *control, struct thread *p); -#else -sctp_send(struct socket *so, int flags, struct mbuf *m, struct sockaddr *addr, - struct mbuf *control, struct proc *p); -#endif - -int -#if (defined(__FreeBSD__) && __FreeBSD_version >= 500000) || defined(__DragonFly__) -sctp_send(struct socket *so, int flags, struct mbuf *m, struct sockaddr *addr, - struct mbuf *control, struct thread *p) -{ -#else -sctp_send(struct socket *so, int flags, struct mbuf *m, struct sockaddr *addr, - struct mbuf *control, struct proc *p) +void +sctp_send(netmsg_t msg) { -#endif - struct sctp_inpcb *inp; + struct socket *so = msg->send.base.nm_so; + int flags = msg->send.nm_flags; + struct mbuf *m = msg->send.nm_m; + struct mbuf *control = msg->send.nm_control; + struct sockaddr *addr = msg->send.nm_addr; + struct thread *td = msg->send.nm_td; int error; + struct sctp_inpcb *inp; inp = (struct sctp_inpcb *)so->so_pcb; if (inp == 0) { if (control) { @@ -856,7 +818,8 @@ sctp_send(struct socket *so, int flags, struct mbuf *m, struct sockaddr *addr, control = NULL; } sctp_m_freem(m); - return EINVAL; + error = EINVAL; + goto out; } /* Got to have an to address if we are NOT a connected socket */ if ((addr == NULL) && @@ -871,7 +834,7 @@ sctp_send(struct socket *so, int flags, struct mbuf *m, struct sockaddr *addr, sctp_m_freem(control); control = NULL; } - return (error); + goto out; } #ifdef INET6 if (addr->sa_family != AF_INET) { @@ -881,8 +844,9 @@ sctp_send(struct socket *so, int flags, struct mbuf *m, struct sockaddr *addr, sctp_m_freem(control); control = NULL; } - error = EDESTADDRREQ; - return EINVAL; + error = EDESTADDRREQ; /* XXX huh? */ + error = EINVAL; + goto out; } #endif /* INET6 */ connected_type: @@ -932,34 +896,40 @@ sctp_send(struct socket *so, int flags, struct mbuf *m, struct sockaddr *addr, * optionally switch back to this code (by changing back the * definitions) but this is not advisable. */ - int ret; - ret = sctp_output(inp, inp->pkt, addr, inp->control, p, flags); + error = sctp_output(inp, inp->pkt, addr, + inp->control, td, flags); inp->pkt = NULL; inp->control = NULL; - return (ret); } else { - return (0); + error = 0; } +out: + if (msg->send.nm_flags & PRUS_NAMALLOC) { + kfree(msg->send.nm_addr, M_LWKTMSG); + msg->send.nm_addr = NULL; + } + lwkt_replymsg(&msg->lmsg, error); } -static int -sctp_disconnect(struct socket *so) +static void +sctp_disconnect(netmsg_t msg) { + struct socket *so = msg->disconnect.base.nm_so; struct sctp_inpcb *inp; + int error; - crit_enter(); inp = (struct sctp_inpcb *)so->so_pcb; if (inp == NULL) { - crit_exit(); - return (ENOTCONN); + error = ENOTCONN; + goto out; } SCTP_INP_RLOCK(inp); if (inp->sctp_flags & SCTP_PCB_FLAGS_TCPTYPE) { if (LIST_EMPTY(&inp->sctp_asoc_list)) { /* No connection */ - crit_exit(); SCTP_INP_RUNLOCK(inp); - return (0); + error = 0; + goto out; } else { int some_on_streamwheel = 0; struct sctp_association *asoc; @@ -967,9 +937,9 @@ sctp_disconnect(struct socket *so) stcb = LIST_FIRST(&inp->sctp_asoc_list); if (stcb == NULL) { - crit_exit(); SCTP_INP_RUNLOCK(inp); - return (EINVAL); + error = EINVAL; + goto out; } asoc = &stcb->asoc; SCTP_TCB_LOCK(stcb); @@ -995,8 +965,8 @@ sctp_disconnect(struct socket *so) SCTP_INP_RUNLOCK(inp); sctp_free_assoc(inp, stcb); /* No unlock tcb assoc is gone */ - crit_exit(); - return (0); + error = 0; + goto out; } if (!TAILQ_EMPTY(&asoc->out_wheel)) { /* Check to see if some data queued */ @@ -1053,28 +1023,29 @@ sctp_disconnect(struct socket *so) } SCTP_TCB_UNLOCK(stcb); SCTP_INP_RUNLOCK(inp); - crit_exit(); - return (0); + error = 0; } - /* not reached */ } else { /* UDP model does not support this */ SCTP_INP_RUNLOCK(inp); - crit_exit(); - return EOPNOTSUPP; + error = EOPNOTSUPP; } +out: + lwkt_replymsg(&msg->lmsg, error); } -int -sctp_shutdown(struct socket *so) +/* also called from ipv6 sctp code */ +void +sctp_shutdown(netmsg_t msg) { + struct socket *so = msg->shutdown.base.nm_so; struct sctp_inpcb *inp; + int error; - crit_enter(); inp = (struct sctp_inpcb *)so->so_pcb; - if (inp == 0) { - crit_exit(); - return EINVAL; + if (inp == NULL) { + error = EINVAL; + goto out; } SCTP_INP_RLOCK(inp); /* For UDP model this is a invalid call */ @@ -1086,9 +1057,9 @@ sctp_shutdown(struct socket *so) soclrstate(so, SS_CANTRCVMORE); #endif /* This proc will wakeup for read and do nothing (I hope) */ - crit_exit(); SCTP_INP_RUNLOCK(inp); - return (EOPNOTSUPP); + error = EOPNOTSUPP; + goto out; } /* * Ok if we reach here its the TCP model and it is either a SHUT_WR @@ -1106,8 +1077,8 @@ sctp_shutdown(struct socket *so) * Ok we hit the case that the shutdown call was made * after an abort or something. Nothing to do now. */ - crit_exit(); - return (0); + error = 0; + goto out; } SCTP_TCB_LOCK(stcb); asoc = &stcb->asoc; @@ -1157,8 +1128,9 @@ sctp_shutdown(struct socket *so) SCTP_TCB_UNLOCK(stcb); } SCTP_INP_RUNLOCK(inp); - crit_exit(); - return 0; + error = 0; +out: + lwkt_replymsg(&msg->lmsg, error); } /* @@ -1449,11 +1421,9 @@ sctp_do_connect_x(struct socket *so, } #endif /* SCTP_DEBUG */ - crit_enter(); if ((inp->sctp_flags & SCTP_PCB_FLAGS_TCPTYPE) && (inp->sctp_flags & SCTP_PCB_FLAGS_CONNECTED)) { /* We are already connected AND the TCP model */ - crit_exit(); return (EADDRINUSE); } if (inp->sctp_flags & SCTP_PCB_FLAGS_CONNECTED) { @@ -1462,7 +1432,6 @@ sctp_do_connect_x(struct socket *so, SCTP_INP_RUNLOCK(inp); } if (stcb) { - crit_exit(); return (EALREADY); } @@ -1470,7 +1439,6 @@ sctp_do_connect_x(struct socket *so, if ((inp->sctp_flags & SCTP_PCB_FLAGS_SOCKET_GONE) || (inp->sctp_flags & SCTP_PCB_FLAGS_SOCKET_GONE)) { SCTP_ASOC_CREATE_UNLOCK(inp); - crit_exit(); return (EFAULT); } @@ -1492,7 +1460,6 @@ sctp_do_connect_x(struct socket *so, if (IN6_IS_ADDR_V4MAPPED(&sin6->sin6_addr)) { /* Must be non-mapped for connectx */ SCTP_ASOC_CREATE_UNLOCK(inp); - crit_exit(); return EINVAL; } num_v6++; @@ -1506,7 +1473,6 @@ sctp_do_connect_x(struct socket *so, /* Already have or am bring up an association */ SCTP_ASOC_CREATE_UNLOCK(inp); SCTP_TCB_UNLOCK(stcb); - crit_exit(); return (EALREADY); } if ((at + incr) > m->m_len) { @@ -1522,7 +1488,6 @@ sctp_do_connect_x(struct socket *so, #ifdef INET6 if (((inp->sctp_flags & SCTP_PCB_FLAGS_BOUND_V6) == 0) && (num_v6 > 0)) { - crit_exit(); SCTP_INP_WUNLOCK(inp); SCTP_ASOC_CREATE_UNLOCK(inp); return (EINVAL); @@ -1546,7 +1511,6 @@ sctp_do_connect_x(struct socket *so, */ SCTP_INP_WUNLOCK(inp); SCTP_ASOC_CREATE_UNLOCK(inp); - crit_exit(); return EINVAL; } } @@ -1558,7 +1522,6 @@ sctp_do_connect_x(struct socket *so, error = sctp_inpcb_bind(so, NULL, p); if (error) { SCTP_ASOC_CREATE_UNLOCK(inp); - crit_exit(); return (error); } } else { @@ -1569,7 +1532,6 @@ sctp_do_connect_x(struct socket *so, if (stcb == NULL) { /* Gak! no memory */ SCTP_ASOC_CREATE_UNLOCK(inp); - crit_exit(); return (error); } /* move to second address */ @@ -1585,7 +1547,6 @@ sctp_do_connect_x(struct socket *so, /* assoc gone no un-lock */ sctp_free_assoc(inp, stcb); SCTP_ASOC_CREATE_UNLOCK(inp); - crit_exit(); return (ENOBUFS); } @@ -1595,7 +1556,6 @@ sctp_do_connect_x(struct socket *so, /* assoc gone no un-lock */ sctp_free_assoc(inp, stcb); SCTP_ASOC_CREATE_UNLOCK(inp); - crit_exit(); return (ENOBUFS); } } @@ -1617,7 +1577,6 @@ sctp_do_connect_x(struct socket *so, soisconnecting(so); } SCTP_ASOC_CREATE_UNLOCK(inp); - crit_exit(); return error; } @@ -2876,10 +2835,8 @@ sctp_optsset(struct socket *so, } sctp_send_str_reset_req(stcb, strrst->strrst_num_streams, strrst->strrst_list, two_way, not_peer); - crit_enter(); sctp_chunk_output(inp, stcb, 12); SCTP_TCB_UNLOCK(stcb); - crit_exit(); } break; @@ -3571,32 +3528,32 @@ sctp_optsset(struct socket *so, return (error); } - -#if defined(__FreeBSD__) || defined(__APPLE__) || defined(__DragonFly__) -int -sctp_ctloutput(struct socket *so, struct sockopt *sopt) +void +sctp_ctloutput(netmsg_t msg) { + struct socket *so = msg->ctloutput.base.nm_so; + struct sockopt *sopt = msg->ctloutput.nm_sopt; struct mbuf *m = NULL; struct sctp_inpcb *inp; int error; inp = (struct sctp_inpcb *)so->so_pcb; - crit_enter(); + if (inp == 0) { - crit_exit(); /* I made the same as TCP since we are not setup? */ - return (ECONNRESET); + error = ECONNRESET; + goto out; } if (sopt->sopt_level != IPPROTO_SCTP) { /* wrong proto level... send back up to IP */ #ifdef INET6 if (INP_CHECK_SOCKAF(so, AF_INET6)) - error = ip6_ctloutput(so, sopt); + ip6_ctloutput_dispatch(msg); else #endif /* INET6 */ - error = ip_ctloutput(so, sopt); - crit_exit(); - return (error); + ip_ctloutput(msg); + /* msg invalid now */ + return; } if (sopt->sopt_valsize > MCLBYTES) { /* @@ -3612,8 +3569,8 @@ sctp_ctloutput(struct socket *so, struct sockopt *sopt) MCLGET(m, MB_DONTWAIT); if ((m->m_flags & M_EXT) == 0) { sctp_m_freem(m); - crit_exit(); - return (ENOBUFS); + error = ENOBUFS; + goto out; } } error = sooptcopyin(sopt, mtod(m, caddr_t), sopt->sopt_valsize, @@ -3646,101 +3603,17 @@ sctp_ctloutput(struct socket *so, struct sockopt *sopt) sctp_m_freem(m); } out: - crit_exit(); - return (error); + lwkt_replymsg(&msg->lmsg, error); } -#else -/* NetBSD and OpenBSD */ -int -sctp_ctloutput(int op, struct socket *so, int level, int optname, - struct mbuf **mp) -{ - int s, error; - struct inpcb *inp; -#ifdef INET6 - struct in6pcb *in6p; -#endif - int family; /* family of the socket */ - - family = so->so_proto->pr_domain->dom_family; - error = 0; - crit_exit(); - switch (family) { - case PF_INET: - inp = sotoinpcb(so); -#ifdef INET6 - in6p = NULL; -#endif - break; -#ifdef INET6 - case PF_INET6: - inp = NULL; - in6p = sotoin6pcb(so); - break; -#endif - default: - crit_exit(); - return EAFNOSUPPORT; - } -#ifndef INET6 - if (inp == NULL) -#else - if (inp == NULL && in6p == NULL) -#endif - { - crit_exit(); - if (op == PRCO_SETOPT && *mp) - m_free(*mp); - return (ECONNRESET); - } - if (level != IPPROTO_SCTP) { - switch (family) { - case PF_INET: - error = ip_ctloutput(op, so, level, optname, mp); - break; -#ifdef INET6 - case PF_INET6: - error = ip6_ctloutput(op, so, level, optname, mp); - break; -#endif - } - crit_exit(); - return (error); - } - /* Ok if we reach here it is a SCTP option we hope */ - if (op == PRCO_SETOPT) { - error = sctp_optsset(so, optname, mp, NULL); - if (*mp) - m_free(*mp); - } else if (op == PRCO_GETOPT) { - error = sctp_optsget(so, optname, mp, NULL); - } else { - error = EINVAL; - } - crit_exit(); - return (error); -} - -#endif - -static int -#if (defined(__FreeBSD__) && __FreeBSD_version >= 500000) || defined(__DragonFly__) -sctp_connect(struct socket *so, struct sockaddr *addr, struct thread *p) -{ -#else -#if defined(__FreeBSD__) || defined(__APPLE__) -sctp_connect(struct socket *so, struct sockaddr *addr, struct proc *p) -{ -#else -sctp_connect(struct socket *so, struct mbuf *nam, struct proc *p) +static void +sctp_connect(netmsg_t msg) { - struct sockaddr *addr = mtod(nam, struct sockaddr *); -#endif -#endif - int error = 0; + struct socket *so = msg->connect.base.nm_so; + struct sockaddr *addr = msg->connect.nm_nam; struct sctp_inpcb *inp; struct sctp_tcb *stcb; + int error = 0; #ifdef SCTP_DEBUG if (sctp_debug_on & SCTP_DEBUG_PCB1) { @@ -3749,12 +3622,11 @@ sctp_connect(struct socket *so, struct mbuf *nam, struct proc *p) kprintf("Port %d\n", ntohs(((struct sockaddr_in *)addr)->sin_port)); } #endif /* SCTP_DEBUG */ - crit_enter(); inp = (struct sctp_inpcb *)so->so_pcb; - if (inp == 0) { - crit_exit(); + if (inp == NULL) { /* I made the same as TCP since we are not setup? */ - return (ECONNRESET); + error = ECONNRESET; + goto out; } SCTP_ASOC_CREATE_LOCK(inp); SCTP_INP_WLOCK(inp); @@ -3763,27 +3635,26 @@ sctp_connect(struct socket *so, struct mbuf *nam, struct proc *p) /* Should I really unlock ? */ SCTP_INP_WUNLOCK(inp); SCTP_ASOC_CREATE_UNLOCK(inp); - crit_exit(); - return (EFAULT); + error = EFAULT; + goto out; } #ifdef INET6 if (((inp->sctp_flags & SCTP_PCB_FLAGS_BOUND_V6) == 0) && (addr->sa_family == AF_INET6)) { SCTP_INP_WUNLOCK(inp); SCTP_ASOC_CREATE_UNLOCK(inp); - crit_exit(); - return (EINVAL); + error = EINVAL; + goto out; } #endif /* INET6 */ if ((inp->sctp_flags & SCTP_PCB_FLAGS_UNBOUND) == SCTP_PCB_FLAGS_UNBOUND) { /* Bind a ephemeral port */ SCTP_INP_WUNLOCK(inp); - error = sctp_inpcb_bind(so, NULL, p); + error = sctp_inpcb_bind(so, NULL, msg->connect.nm_td); if (error) { SCTP_ASOC_CREATE_UNLOCK(inp); - crit_exit(); - return (error); + goto out; } SCTP_INP_WLOCK(inp); } @@ -3791,10 +3662,10 @@ sctp_connect(struct socket *so, struct mbuf *nam, struct proc *p) if ((inp->sctp_flags & SCTP_PCB_FLAGS_TCPTYPE) && (inp->sctp_flags & SCTP_PCB_FLAGS_CONNECTED)) { /* We are already connected AND the TCP model */ - crit_exit(); SCTP_INP_WUNLOCK(inp); SCTP_ASOC_CREATE_UNLOCK(inp); - return (EADDRINUSE); + error = EADDRINUSE; + goto out; } if (inp->sctp_flags & SCTP_PCB_FLAGS_CONNECTED) { stcb = LIST_FIRST(&inp->sctp_asoc_list); @@ -3815,15 +3686,14 @@ sctp_connect(struct socket *so, struct mbuf *nam, struct proc *p) /* Already have or am bring up an association */ SCTP_ASOC_CREATE_UNLOCK(inp); SCTP_TCB_UNLOCK(stcb); - crit_exit(); - return (EALREADY); + error = EALREADY; + goto out; } /* We are GOOD to go */ stcb = sctp_aloc_assoc(inp, addr, 1, &error, 0); if (stcb == NULL) { /* Gak! no memory */ - crit_exit(); - return (error); + goto out; } if (stcb->sctp_ep->sctp_flags & SCTP_PCB_FLAGS_TCPTYPE) { stcb->sctp_ep->sctp_flags |= SCTP_PCB_FLAGS_CONNECTED; @@ -3835,14 +3705,18 @@ sctp_connect(struct socket *so, struct mbuf *nam, struct proc *p) sctp_send_initiate(inp, stcb); SCTP_ASOC_CREATE_UNLOCK(inp); SCTP_TCB_UNLOCK(stcb); - crit_exit(); - return error; +out: + lwkt_replymsg(&msg->lmsg, error); } -int -sctp_usr_recvd(struct socket *so, int flags) +void +sctp_usr_recvd(netmsg_t msg) { - struct sctp_socket_q_list *sq=NULL; + struct socket *so = msg->rcvd.base.nm_so; + struct sctp_socket_q_list *sq = NULL; + int flags = msg->rcvd.nm_flags; + int error; + /* * The user has received some data, we may be able to stuff more * up the socket. And we need to possibly update the rwnd. @@ -3863,9 +3737,9 @@ sctp_usr_recvd(struct socket *so, int flags) if (sctp_debug_on & SCTP_DEBUG_USRREQ2) kprintf("Nope, connection reset\n"); #endif - return (ECONNRESET); + error = ECONNRESET; + goto out; } - crit_enter(); /* * Grab the first one on the list. It will re-insert itself if * it runs out of room @@ -3974,17 +3848,17 @@ sctp_usr_recvd(struct socket *so, int flags) if (stcb) SCTP_TCB_UNLOCK(stcb); SCTP_INP_WUNLOCK(inp); - crit_exit(); - return (0); + error = 0; +out: + lwkt_replymsg(&msg->lmsg, error); } -int -#if (defined(__FreeBSD__) && __FreeBSD_version >= 500000) || defined(__DragonFly__) -sctp_listen(struct socket *so, struct thread *p) -#else -sctp_listen(struct socket *so, struct proc *p) -#endif +void +sctp_listen(netmsg_t msg) { + struct socket *so = msg->listen.base.nm_so; + int error; + /* * Note this module depends on the protocol processing being * called AFTER any socket level flags and backlog are applied @@ -3993,31 +3867,28 @@ sctp_listen(struct socket *so, struct proc *p) * to the sys/kern/uipc_socket.c module to reverse this but this * MUST be in place if the socket API for SCTP is to work properly. */ - int error = 0; struct sctp_inpcb *inp; - crit_enter(); inp = (struct sctp_inpcb *)so->so_pcb; - if (inp == 0) { - crit_exit(); + if (inp == NULL) { /* I made the same as TCP since we are not setup? */ - return (ECONNRESET); + error = ECONNRESET; + goto out; } SCTP_INP_RLOCK(inp); if ((inp->sctp_flags & SCTP_PCB_FLAGS_TCPTYPE) && (inp->sctp_flags & SCTP_PCB_FLAGS_CONNECTED)) { /* We are already connected AND the TCP model */ - crit_exit(); SCTP_INP_RUNLOCK(inp); - return (EADDRINUSE); + error = EADDRINUSE; + goto out; } if (inp->sctp_flags & SCTP_PCB_FLAGS_UNBOUND) { /* We must do a bind. */ SCTP_INP_RUNLOCK(inp); - if ((error = sctp_inpcb_bind(so, NULL, p))) { + if ((error = sctp_inpcb_bind(so, NULL, msg->listen.nm_td))) { /* bind error, probably perm */ - crit_exit(); - return (error); + goto out; } } else { SCTP_INP_RUNLOCK(inp); @@ -4047,41 +3918,38 @@ sctp_listen(struct socket *so, struct proc *p) } SCTP_INP_WUNLOCK(inp); SOCK_UNLOCK(so); - crit_exit(); - return (error); + error = 0; +out: + lwkt_replymsg(&msg->lmsg, error); } -int -#if defined(__FreeBSD__) || defined(__APPLE__) || defined(__DragonFly__) -sctp_accept(struct socket *so, struct sockaddr **addr) -{ -#else -sctp_accept(struct socket *so, struct mbuf *nam) +void +sctp_accept(netmsg_t msg) { - struct sockaddr *addr = mtod(nam, struct sockaddr *); -#endif + struct socket *so = msg->accept.base.nm_so; + struct sockaddr **addr = msg->accept.nm_nam; struct sctp_tcb *stcb; struct sockaddr *prim; struct sctp_inpcb *inp; + int error; - crit_enter(); inp = (struct sctp_inpcb *)so->so_pcb; - if (inp == 0) { - crit_exit(); - return (ECONNRESET); + if (inp == NULL) { + error = ECONNRESET; + goto out; } SCTP_INP_RLOCK(inp); if (so->so_state & SS_ISDISCONNECTED) { - crit_exit(); SCTP_INP_RUNLOCK(inp); - return (ECONNABORTED); + error = ECONNABORTED; + goto out; } stcb = LIST_FIRST(&inp->sctp_asoc_list); if (stcb == NULL) { - crit_exit(); SCTP_INP_RUNLOCK(inp); - return (ECONNRESET); + error = ECONNRESET; + goto out; } SCTP_TCB_LOCK(stcb); SCTP_INP_RUNLOCK(inp); @@ -4152,22 +4020,26 @@ sctp_accept(struct socket *so, struct mbuf *nam) } SCTP_INP_WUNLOCK(inp); - crit_exit(); - return (0); + error = 0; +out: + lwkt_replymsg(&msg->lmsg, error); +} + +static +void +sctp_ingetaddr(netmsg_t msg) +{ + int error; + + error = sctp_ingetaddr_oncpu(msg->sockaddr.base.nm_so, + msg->sockaddr.nm_nam); + lwkt_replymsg(&msg->lmsg, error); } int -#if defined(__FreeBSD__) || defined(__APPLE__) || defined(__DragonFly__) -sctp_ingetaddr(struct socket *so, struct sockaddr **addr) -#else -sctp_ingetaddr(struct socket *so, struct mbuf *nam) -#endif +sctp_ingetaddr_oncpu(struct socket *so, struct sockaddr **addr) { -#if defined(__FreeBSD__) || defined(__APPLE__) || defined(__DragonFly__) struct sockaddr_in *sin; -#else - struct sockaddr_in *sin = mtod(nam, struct sockaddr_in *); -#endif struct sctp_inpcb *inp; /* * Do the malloc first in case it blocks. @@ -4181,10 +4053,8 @@ sctp_ingetaddr(struct socket *so, struct mbuf *nam) #endif sin->sin_family = AF_INET; sin->sin_len = sizeof(*sin); - crit_enter(); inp = (struct sctp_inpcb *)so->so_pcb; if (!inp) { - crit_exit(); #if defined(__FreeBSD__) || defined(__APPLE__) || defined(__DragonFly__) FREE(sin, M_SONAME); #endif @@ -4241,7 +4111,6 @@ sctp_ingetaddr(struct socket *so, struct mbuf *nam) } } if (!fnd) { - crit_exit(); #if defined(__FreeBSD__) || defined(__APPLE__) || defined(__DragonFly__) FREE(sin, M_SONAME); #endif @@ -4250,39 +4119,44 @@ sctp_ingetaddr(struct socket *so, struct mbuf *nam) } } SCTP_INP_RUNLOCK(inp); - crit_exit(); #if defined(__FreeBSD__) || defined(__APPLE__) || defined(__DragonFly__) (*addr) = (struct sockaddr *)sin; #endif return (0); } +void +sctp_peeraddr(netmsg_t msg) +{ + int error; + + error = sctp_peeraddr_oncpu(msg->peeraddr.base.nm_so, + msg->peeraddr.nm_nam); + lwkt_replymsg(&msg->lmsg, error); +} + int -#if defined(__FreeBSD__) || defined(__APPLE__) || defined(__DragonFly__) -sctp_peeraddr(struct socket *so, struct sockaddr **addr) +sctp_peeraddr_oncpu(struct socket *so, struct sockaddr **addr) { struct sockaddr_in *sin = (struct sockaddr_in *)*addr; -#else -sctp_peeraddr(struct socket *so, struct mbuf *nam) -{ - struct sockaddr_in *sin = mtod(nam, struct sockaddr_in *); -#endif - int fnd; struct sockaddr_in *sin_a; struct sctp_inpcb *inp; struct sctp_tcb *stcb; struct sctp_nets *net; + int fnd; + int error; /* Do the malloc first in case it blocks. */ inp = (struct sctp_inpcb *)so->so_pcb; if ((inp == NULL) || ((inp->sctp_flags & SCTP_PCB_FLAGS_CONNECTED) == 0)) { /* UDP type and listeners will drop out here */ - return (ENOTCONN); + error = ENOTCONN; + goto out; } - crit_enter(); #if defined(__FreeBSD__) || defined(__APPLE__) || defined(__DragonFly__) + /* XXX huh? why assign it above and then allocate it here? */ MALLOC(sin, struct sockaddr_in *, sizeof *sin, M_SONAME, M_WAITOK | M_ZERO); #else @@ -4295,11 +4169,11 @@ sctp_peeraddr(struct socket *so, struct mbuf *nam) /* We must recapture incase we blocked */ inp = (struct sctp_inpcb *)so->so_pcb; if (!inp) { - crit_exit(); #if defined(__FreeBSD__) || defined(__APPLE__) || defined(__DragonFly__) FREE(sin, M_SONAME); #endif - return ECONNRESET; + error = ECONNRESET; + goto out; } SCTP_INP_RLOCK(inp); stcb = LIST_FIRST(&inp->sctp_asoc_list); @@ -4307,11 +4181,11 @@ sctp_peeraddr(struct socket *so, struct mbuf *nam) SCTP_TCB_LOCK(stcb); SCTP_INP_RUNLOCK(inp); if (stcb == NULL) { - crit_exit(); #if defined(__FreeBSD__) || defined(__APPLE__) || defined(__DragonFly__) FREE(sin, M_SONAME); #endif - return ECONNRESET; + error = ECONNRESET; + goto out; } fnd = 0; TAILQ_FOREACH(net, &stcb->asoc.nets, sctp_next) { @@ -4326,14 +4200,15 @@ sctp_peeraddr(struct socket *so, struct mbuf *nam) SCTP_TCB_UNLOCK(stcb); if (!fnd) { /* No IPv4 address */ - crit_exit(); #if defined(__FreeBSD__) || defined(__APPLE__) || defined(__DragonFly__) FREE(sin, M_SONAME); #endif - return ENOENT; + error = ENOENT; + } else { + error = 0; } - crit_exit(); - return (0); +out: + return error; } #if defined(__FreeBSD__) || defined(__APPLE__) || defined(__DragonFly__) @@ -4343,14 +4218,14 @@ struct pr_usrreqs sctp_usrreqs = { .pru_attach = sctp_attach, .pru_bind = sctp_bind, .pru_connect = sctp_connect, - .pru_connect2 = pru_connect2_notsupp, - .pru_control = in_control, + .pru_connect2 = pr_generic_notsupp, + .pru_control = in_control_dispatch, .pru_detach = sctp_detach, .pru_disconnect = sctp_disconnect, .pru_listen = sctp_listen, .pru_peeraddr = sctp_peeraddr, .pru_rcvd = sctp_usr_recvd, - .pru_rcvoob = pru_rcvoob_notsupp, + .pru_rcvoob = pr_generic_notsupp, .pru_send = sctp_send, .pru_sense = pru_sense_null, .pru_shutdown = sctp_shutdown, @@ -4366,6 +4241,7 @@ sctp_usrreq(struct socket *so, int req, struct mbuf *m, struct mbuf *nam, struct mbuf *control, struct proc *p) { #else +#error x int sctp_usrreq(struct socket *so, int req, struct mbuf *m, struct mbuf *nam, struct mbuf *control) @@ -4377,7 +4253,6 @@ sctp_usrreq(struct socket *so, int req, struct mbuf *m, struct mbuf *nam, family = so->so_proto->pr_domain->dom_family; - crit_enter(); if (req == PRU_CONTROL) { switch (family) { case PF_INET: @@ -4391,13 +4266,12 @@ sctp_usrreq(struct socket *so, int req, struct mbuf *m, struct mbuf *nam, #ifdef INET6 case PF_INET6: error = in6_control(so, (long)m, (caddr_t)nam, - (struct ifnet *)control, p); + (struct ifnet *)control, p); break; #endif default: error = EAFNOSUPPORT; } - crit_exit(); return (error); } #ifdef __NetBSD__ @@ -4420,10 +4294,8 @@ sctp_usrreq(struct socket *so, int req, struct mbuf *m, struct mbuf *nam, break; #endif /* INET6 */ default: - crit_exit(); return (EAFNOSUPPORT); } - crit_exit(); return (0); } #endif @@ -4436,7 +4308,6 @@ sctp_usrreq(struct socket *so, int req, struct mbuf *m, struct mbuf *nam, break; case PRU_BIND: if (nam == NULL) { - crit_exit(); return (EINVAL); } error = sctp_bind(so, nam, p); @@ -4446,7 +4317,6 @@ sctp_usrreq(struct socket *so, int req, struct mbuf *m, struct mbuf *nam, break; case PRU_CONNECT: if (nam == NULL) { - crit_exit(); return (EINVAL); } error = sctp_connect(so, nam, p); @@ -4456,7 +4326,6 @@ sctp_usrreq(struct socket *so, int req, struct mbuf *m, struct mbuf *nam, break; case PRU_ACCEPT: if (nam == NULL) { - crit_exit(); return (EINVAL); } error = sctp_accept(so, nam); @@ -4517,7 +4386,6 @@ sctp_usrreq(struct socket *so, int req, struct mbuf *m, struct mbuf *nam, default: break; } - crit_exit(); return (error); } #endif diff --git a/sys/netinet/sctp_var.h b/sys/netinet/sctp_var.h index 8931d7d135..048861a33a 100644 --- a/sys/netinet/sctp_var.h +++ b/sys/netinet/sctp_var.h @@ -180,14 +180,16 @@ struct sctphdr; void sctp_fasttim(void); #endif +union netmsg; + #if defined(__FreeBSD__) || defined(__APPLE__) void sctp_ctlinput(int, struct sockaddr *, void *); int sctp_ctloutput(struct socket *, struct sockopt *); void sctp_input(struct mbuf *, int); #elif defined(__DragonFly__) -void sctp_ctlinput(int, struct sockaddr *, void *); -int sctp_ctloutput(struct socket *, struct sockopt *); -void sctp_input(struct mbuf *, ... ); +void sctp_ctlinput(union netmsg *); +void sctp_ctloutput(union netmsg *); +int sctp_input(struct mbuf **, int *, int); #else void* sctp_ctlinput(int, struct sockaddr *, void *); int sctp_ctloutput(int, struct socket *, int, int, struct mbuf **); @@ -195,11 +197,11 @@ void sctp_input(struct mbuf *, ... ); #endif void sctp_drain(void); void sctp_init(void); -int sctp_shutdown(struct socket *); +void sctp_shutdown(union netmsg *); void sctp_notify(struct sctp_inpcb *, int, struct sctphdr *, struct sockaddr *, struct sctp_tcb *, struct sctp_nets *); -int sctp_usr_recvd(struct socket *, int); +void sctp_usr_recvd(union netmsg *); #if defined(INET6) void ip_2_ip6_hdr(struct ip6_hdr *, struct ip *); @@ -214,35 +216,12 @@ int sctp_peeloff(struct socket *, struct socket *, int, caddr_t, int *); sctp_assoc_t sctp_getassocid(struct sockaddr *); - - -int sctp_ingetaddr(struct socket *, -#if defined(__FreeBSD__) || defined(__APPLE__) || defined(__DragonFly__) - struct sockaddr ** -#else - struct mbuf * -#endif -); - -int sctp_peeraddr(struct socket *, -#if defined(__FreeBSD__) || defined(__APPLE__) || defined(__DragonFly__) - struct sockaddr ** -#else - struct mbuf * -#endif -); - -#if (defined(__FreeBSD__) && __FreeBSD_version >= 500000) || defined(__DragonFly__) -int sctp_listen(struct socket *, struct thread *); -#else -int sctp_listen(struct socket *, struct proc *); -#endif - -#if defined(__FreeBSD__) || defined(__APPLE__) || defined(__DragonFly__) -int sctp_accept(struct socket *, struct sockaddr **); -#else -int sctp_accept(struct socket *, struct mbuf *); -#endif +int sctp_ingetaddr_oncpu(struct socket *, struct sockaddr **); +int sctp_peeraddr_oncpu(struct socket *, struct sockaddr **); +void sctp_peeraddr(union netmsg *); +void sctp_listen(union netmsg *); +void sctp_accept(union netmsg *); +void sctp_send(union netmsg *); #if defined(__NetBSD__) || defined(__OpenBSD__) int sctp_sysctl(int *, u_int, void *, size_t *, void *, size_t); diff --git a/sys/netinet/tcp_input.c b/sys/netinet/tcp_input.c index f97379a3c3..f2f79a19bf 100644 --- a/sys/netinet/tcp_input.c +++ b/sys/netinet/tcp_input.c @@ -511,16 +511,15 @@ tcp6_input(struct mbuf **mp, int *offp, int proto) return (IPPROTO_DONE); } - tcp_input(m, *offp, proto); + tcp_input(mp, offp, proto); return (IPPROTO_DONE); } #endif -void -tcp_input(struct mbuf *m, ...) +int +tcp_input(struct mbuf **mp, int *offp, int proto) { - __va_list ap; - int off0, proto; + int off0; struct tcphdr *th; struct ip *ip = NULL; struct ipovly *ipov; @@ -542,6 +541,7 @@ tcp_input(struct mbuf *m, ...) int rstreason; /* For badport_bandlim accounting purposes */ int cpu; struct ip6_hdr *ip6 = NULL; + struct mbuf *m; #ifdef INET6 boolean_t isipv6; #else @@ -551,10 +551,9 @@ tcp_input(struct mbuf *m, ...) short ostate = 0; #endif - __va_start(ap, m); - off0 = __va_arg(ap, int); - proto = __va_arg(ap, int); - __va_end(ap); + off0 = *offp; + m = *mp; + *mp = NULL; tcpstat.tcps_rcvtotal++; @@ -650,7 +649,7 @@ tcp_input(struct mbuf *m, ...) tlen -= off; /* tlen is used instead of ti->ti_len */ if (off > sizeof(struct tcphdr)) { if (isipv6) { - IP6_EXTHDR_CHECK(m, off0, off, ); + IP6_EXTHDR_CHECK(m, off0, off, IPPROTO_DONE); ip6 = mtod(m, struct ip6_hdr *); th = (struct tcphdr *)((caddr_t)ip6 + off0); } else { @@ -907,7 +906,7 @@ findpcb: * syncache will free mbuf. */ if (so == NULL) - return; + return(IPPROTO_DONE); /* * We must be in the correct protocol thread @@ -1044,7 +1043,7 @@ findpcb: * send SYN,ACK packet. */ if (so == NULL) - return; + return(IPPROTO_DONE); /* * We must be in the correct protocol thread for @@ -1284,7 +1283,7 @@ after_listen: sowwakeup(so); if (so->so_snd.ssb_cc > 0) tcp_output(tp); - return; + return(IPPROTO_DONE); } } else if (tiwin == tp->snd_wnd && th->th_ack == tp->snd_una && @@ -1425,7 +1424,7 @@ after_listen: tp->t_flags |= TF_ACKNOW; tcp_output(tp); } - return; + return(IPPROTO_DONE); } } @@ -2570,7 +2569,7 @@ dodata: /* XXX */ */ if (needoutput || (tp->t_flags & TF_ACKNOW)) tcp_output(tp); - return; + return(IPPROTO_DONE); dropafterack: /* @@ -2601,7 +2600,7 @@ dropafterack: m_freem(m); tp->t_flags |= TF_ACKNOW; tcp_output(tp); - return; + return(IPPROTO_DONE); dropwithreset: /* @@ -2647,7 +2646,7 @@ dropwithreset: tcp_respond(tp, mtod(m, void *), th, m, th->th_seq + tlen, (tcp_seq)0, TH_RST | TH_ACK); } - return; + return(IPPROTO_DONE); drop: /* @@ -2658,7 +2657,7 @@ drop: tcp_trace(TA_DROP, ostate, tp, tcp_saveipgen, &tcp_savetcp, 0); #endif m_freem(m); - return; + return(IPPROTO_DONE); } /* diff --git a/sys/netinet/tcp_subr.c b/sys/netinet/tcp_subr.c index fce0bc251a..686a8dec4f 100644 --- a/sys/netinet/tcp_subr.c +++ b/sys/netinet/tcp_subr.c @@ -748,7 +748,7 @@ tcp_drop(struct tcpcb *tp, int error) #ifdef SMP struct netmsg_remwildcard { - struct netmsg nm_netmsg; + struct netmsg_base base; struct inpcb *nm_inp; struct inpcbinfo *nm_pcbinfo; #if defined(INET6) @@ -764,27 +764,27 @@ struct netmsg_remwildcard { * on the cpu controlling the inp last and then doing the disconnect. */ static void -in_pcbremwildcardhash_handler(struct netmsg *msg0) +in_pcbremwildcardhash_handler(netmsg_t msg) { - struct netmsg_remwildcard *msg = (struct netmsg_remwildcard *)msg0; + struct netmsg_remwildcard *nmsg = (struct netmsg_remwildcard *)msg; int cpu; - cpu = msg->nm_pcbinfo->cpu; + cpu = nmsg->nm_pcbinfo->cpu; - if (cpu == msg->nm_inp->inp_pcbinfo->cpu) { + if (cpu == nmsg->nm_inp->inp_pcbinfo->cpu) { /* note: detach removes any wildcard hash entry */ #ifdef INET6 - if (msg->nm_isinet6) - in6_pcbdetach(msg->nm_inp); + if (nmsg->nm_isinet6) + in6_pcbdetach(nmsg->nm_inp); else #endif - in_pcbdetach(msg->nm_inp); - lwkt_replymsg(&msg->nm_netmsg.nm_lmsg, 0); + in_pcbdetach(nmsg->nm_inp); + lwkt_replymsg(&nmsg->base.lmsg, 0); } else { - in_pcbremwildcardhash_oncpu(msg->nm_inp, msg->nm_pcbinfo); + in_pcbremwildcardhash_oncpu(nmsg->nm_inp, nmsg->nm_pcbinfo); cpu = (cpu + 1) % ncpus2; - msg->nm_pcbinfo = &tcbinfo[cpu]; - lwkt_forwardmsg(cpu_portfn(cpu), &msg->nm_netmsg.nm_lmsg); + nmsg->nm_pcbinfo = &tcbinfo[cpu]; + lwkt_forwardmsg(cpu_portfn(cpu), &nmsg->base.lmsg); } } @@ -975,19 +975,19 @@ no_valid_rt: */ #ifdef SMP if (inp->inp_flags & INP_WILDCARD_MP) { - struct netmsg_remwildcard *msg; + struct netmsg_remwildcard *nmsg; cpu = (inp->inp_pcbinfo->cpu + 1) % ncpus2; - msg = kmalloc(sizeof(struct netmsg_remwildcard), - M_LWKTMSG, M_INTWAIT); - netmsg_init(&msg->nm_netmsg, NULL, &netisr_afree_rport, + nmsg = kmalloc(sizeof(struct netmsg_remwildcard), + M_LWKTMSG, M_INTWAIT); + netmsg_init(&nmsg->base, NULL, &netisr_afree_rport, 0, in_pcbremwildcardhash_handler); #ifdef INET6 - msg->nm_isinet6 = isafinet6; + nmsg->nm_isinet6 = isafinet6; #endif - msg->nm_inp = inp; - msg->nm_pcbinfo = &tcbinfo[cpu]; - lwkt_sendmsg(cpu_portfn(cpu), &msg->nm_netmsg.nm_lmsg); + nmsg->nm_inp = inp; + nmsg->nm_pcbinfo = &tcbinfo[cpu]; + lwkt_sendmsg(cpu_portfn(cpu), &nmsg->base.lmsg); } else #endif { @@ -1038,17 +1038,17 @@ tcp_drain_oncpu(struct inpcbhead *head) #ifdef SMP struct netmsg_tcp_drain { - struct netmsg nm_netmsg; + struct netmsg_base base; struct inpcbhead *nm_head; }; static void -tcp_drain_handler(netmsg_t netmsg) +tcp_drain_handler(netmsg_t msg) { - struct netmsg_tcp_drain *nm = (void *)netmsg; + struct netmsg_tcp_drain *nm = (void *)msg; tcp_drain_oncpu(nm->nm_head); - lwkt_replymsg(&nm->nm_netmsg.nm_lmsg, 0); + lwkt_replymsg(&nm->base.lmsg, 0); } #endif @@ -1072,19 +1072,19 @@ tcp_drain(void) */ #ifdef SMP for (cpu = 0; cpu < ncpus2; cpu++) { - struct netmsg_tcp_drain *msg; + struct netmsg_tcp_drain *nm; if (cpu == mycpu->gd_cpuid) { tcp_drain_oncpu(&tcbinfo[cpu].pcblisthead); } else { - msg = kmalloc(sizeof(struct netmsg_tcp_drain), - M_LWKTMSG, M_NOWAIT); - if (msg == NULL) + nm = kmalloc(sizeof(struct netmsg_tcp_drain), + M_LWKTMSG, M_NOWAIT); + if (nm == NULL) continue; - netmsg_init(&msg->nm_netmsg, NULL, &netisr_afree_rport, + netmsg_init(&nm->base, NULL, &netisr_afree_rport, 0, tcp_drain_handler); - msg->nm_head = &tcbinfo[cpu].pcblisthead; - lwkt_sendmsg(cpu_portfn(cpu), &msg->nm_netmsg.nm_lmsg); + nm->nm_head = &tcbinfo[cpu].pcblisthead; + lwkt_sendmsg(cpu_portfn(cpu), &nm->base.lmsg); } } #else @@ -1323,32 +1323,34 @@ SYSCTL_PROC(_net_inet6_tcp6, OID_AUTO, getcred, (CTLTYPE_OPAQUE | CTLFLAG_RW), #endif struct netmsg_tcp_notify { - struct netmsg nm_nmsg; + struct netmsg_base base; void (*nm_notify)(struct inpcb *, int); struct in_addr nm_faddr; int nm_arg; }; static void -tcp_notifyall_oncpu(struct netmsg *netmsg) +tcp_notifyall_oncpu(netmsg_t msg) { - struct netmsg_tcp_notify *nmsg = (struct netmsg_tcp_notify *)netmsg; + struct netmsg_tcp_notify *nm = (struct netmsg_tcp_notify *)msg; int nextcpu; - in_pcbnotifyall(&tcbinfo[mycpuid].pcblisthead, nmsg->nm_faddr, - nmsg->nm_arg, nmsg->nm_notify); + in_pcbnotifyall(&tcbinfo[mycpuid].pcblisthead, nm->nm_faddr, + nm->nm_arg, nm->nm_notify); nextcpu = mycpuid + 1; if (nextcpu < ncpus2) - lwkt_forwardmsg(cpu_portfn(nextcpu), &netmsg->nm_lmsg); + lwkt_forwardmsg(cpu_portfn(nextcpu), &nm->base.lmsg); else - lwkt_replymsg(&netmsg->nm_lmsg, 0); + lwkt_replymsg(&nm->base.lmsg, 0); } void -tcp_ctlinput(int cmd, struct sockaddr *sa, void *vip) +tcp_ctlinput(netmsg_t msg) { - struct ip *ip = vip; + int cmd = msg->ctlinput.nm_cmd; + struct sockaddr *sa = msg->ctlinput.nm_arg; + struct ip *ip = msg->ctlinput.nm_extra; struct tcphdr *th; struct in_addr faddr; struct inpcb *inp; @@ -1358,12 +1360,12 @@ tcp_ctlinput(int cmd, struct sockaddr *sa, void *vip) int arg, cpu; if ((unsigned)cmd >= PRC_NCMDS || inetctlerrmap[cmd] == 0) { - return; + goto done; } faddr = ((struct sockaddr_in *)sa)->sin_addr; if (sa->sa_family != AF_INET || faddr.s_addr == INADDR_ANY) - return; + goto done; arg = inetctlerrmap[cmd]; if (cmd == PRC_QUENCH) { @@ -1415,23 +1417,30 @@ tcp_ctlinput(int cmd, struct sockaddr *sa, void *vip) } crit_exit(); } else { - struct netmsg_tcp_notify nmsg; + struct netmsg_tcp_notify *nm; KKASSERT(&curthread->td_msgport == cpu_portfn(0)); - netmsg_init(&nmsg.nm_nmsg, NULL, &curthread->td_msgport, + nm = kmalloc(sizeof(*nm), M_LWKTMSG, M_INTWAIT); + netmsg_init(&nm->base, NULL, &netisr_afree_rport, 0, tcp_notifyall_oncpu); - nmsg.nm_faddr = faddr; - nmsg.nm_arg = arg; - nmsg.nm_notify = notify; + nm->nm_faddr = faddr; + nm->nm_arg = arg; + nm->nm_notify = notify; - lwkt_domsg(cpu_portfn(0), &nmsg.nm_nmsg.nm_lmsg, 0); + lwkt_sendmsg(cpu_portfn(0), &nm->base.lmsg); } +done: + lwkt_replymsg(&msg->lmsg, 0); } #ifdef INET6 + void -tcp6_ctlinput(int cmd, struct sockaddr *sa, void *d) +tcp6_ctlinput(netmsg_t msg) { + int cmd = msg->ctlinput.nm_cmd; + struct sockaddr *sa = msg->ctlinput.nm_arg; + void *d = msg->ctlinput.nm_extra; struct tcphdr th; void (*notify) (struct inpcb *, int) = tcp_notify; struct ip6_hdr *ip6; @@ -1446,8 +1455,9 @@ tcp6_ctlinput(int cmd, struct sockaddr *sa, void *d) int arg; if (sa->sa_family != AF_INET6 || - sa->sa_len != sizeof(struct sockaddr_in6)) - return; + sa->sa_len != sizeof(struct sockaddr_in6)) { + goto out; + } arg = 0; if (cmd == PRC_QUENCH) @@ -1460,7 +1470,7 @@ tcp6_ctlinput(int cmd, struct sockaddr *sa, void *d) notify = tcp_mtudisc; } else if (!PRC_IS_REDIRECT(cmd) && ((unsigned)cmd > PRC_NCMDS || inet6ctlerrmap[cmd] == 0)) { - return; + goto out; } /* if the parameter is from icmp6, decode it. */ @@ -1486,7 +1496,7 @@ tcp6_ctlinput(int cmd, struct sockaddr *sa, void *d) /* check if we can safely examine src and dst ports */ if (m->m_pkthdr.len < off + sizeof *thp) - return; + goto out; bzero(&th, sizeof th); m_copydata(m, off, sizeof *thp, (caddr_t)&th); @@ -1501,10 +1511,14 @@ tcp6_ctlinput(int cmd, struct sockaddr *sa, void *d) inc.inc6_laddr = ip6cp->ip6c_src->sin6_addr; inc.inc_isipv6 = 1; syncache_unreach(&inc, &th); - } else + } else { in6_pcbnotify(&tcbinfo[0].pcblisthead, sa, 0, (const struct sockaddr *)sa6_src, 0, cmd, arg, notify); + } +out: + lwkt_replymsg(&msg->ctlinput.base.lmsg, 0); } + #endif /* diff --git a/sys/netinet/tcp_syncache.c b/sys/netinet/tcp_syncache.c index ebdb2d1075..a8c59d1336 100644 --- a/sys/netinet/tcp_syncache.c +++ b/sys/netinet/tcp_syncache.c @@ -162,7 +162,7 @@ static struct syncache *syncookie_lookup(struct in_conninfo *, #define TCP_SYNCACHE_BUCKETLIMIT 30 struct netmsg_sc_timer { - struct netmsg nm_netmsg; + struct netmsg_base base; struct msgrec *nm_mrec; /* back pointer to containing msgrec */ }; @@ -335,7 +335,7 @@ syncache_init(void) syncache_percpu->mrec[i].port = cpu_portfn(cpu); syncache_percpu->mrec[i].msg.nm_mrec = &syncache_percpu->mrec[i]; - netmsg_init(&syncache_percpu->mrec[i].msg.nm_netmsg, + netmsg_init(&syncache_percpu->mrec[i].msg.base, NULL, &syncache_null_rport, 0, syncache_timer_handler); } @@ -475,7 +475,7 @@ syncache_timer(void *p) { struct netmsg_sc_timer *msg = p; - lwkt_sendmsg(msg->nm_mrec->port, &msg->nm_netmsg.nm_lmsg); + lwkt_sendmsg(msg->nm_mrec->port, &msg->base.lmsg); } /* @@ -490,7 +490,7 @@ syncache_timer(void *p) * a timer has been deactivated here can it be restarted by syncache_timeout(). */ static void -syncache_timer_handler(netmsg_t netmsg) +syncache_timer_handler(netmsg_t msg) { struct tcp_syncache_percpu *syncache_percpu; struct syncache *sc; @@ -499,7 +499,7 @@ syncache_timer_handler(netmsg_t netmsg) struct inpcb *inp; int slot; - slot = ((struct netmsg_sc_timer *)netmsg)->nm_mrec->slot; + slot = ((struct netmsg_sc_timer *)msg)->nm_mrec->slot; syncache_percpu = &tcp_syncache_percpu[mycpu->gd_cpuid]; list = &syncache_percpu->timerq[slot]; @@ -556,7 +556,7 @@ syncache_timer_handler(netmsg_t netmsg) } else { callout_deactivate(&syncache_percpu->tt_timerq[slot]); } - lwkt_replymsg(&netmsg->nm_lmsg, 0); + lwkt_replymsg(&msg->base.lmsg, 0); } /* diff --git a/sys/netinet/tcp_timer.c b/sys/netinet/tcp_timer.c index ddd7b7369e..eb45646fe3 100644 --- a/sys/netinet/tcp_timer.c +++ b/sys/netinet/tcp_timer.c @@ -229,8 +229,8 @@ tcp_send_timermsg(struct tcpcb *tp, uint32_t task) tmsg->tt_tcb != NULL); tmsg->tt_tasks |= task; - if (tmsg->tt_nmsg.nm_lmsg.ms_flags & MSGF_DONE) - lwkt_sendmsg(tmsg->tt_msgport, &tmsg->tt_nmsg.nm_lmsg); + if (tmsg->tt_msg.lmsg.ms_flags & MSGF_DONE) + lwkt_sendmsg(tmsg->tt_msgport, &tmsg->tt_msg.lmsg); } int tcp_syn_backoff[TCP_MAXRXTSHIFT + 1] = @@ -651,9 +651,9 @@ tcp_timer_rexmt(void *xtp) } static void -tcp_timer_handler(struct netmsg *nmsg) +tcp_timer_handler(netmsg_t msg) { - struct netmsg_tcp_timer *tmsg = (struct netmsg_tcp_timer *)nmsg; + struct netmsg_tcp_timer *tmsg = (struct netmsg_tcp_timer *)msg; const struct tcp_timer *tt; struct tcpcb *tp; @@ -668,7 +668,7 @@ tcp_timer_handler(struct netmsg *nmsg) tmsg->tt_tasks = 0; /* Reply ASAP */ - lwkt_replymsg(&tmsg->tt_nmsg.nm_lmsg, 0); + lwkt_replymsg(&tmsg->tt_msg.lmsg, 0); if (tmsg->tt_running_tasks == 0) { /* @@ -700,7 +700,7 @@ tcp_create_timermsg(struct tcpcb *tp, struct lwkt_port *msgport) { struct netmsg_tcp_timer *tmsg = tp->tt_msg; - netmsg_init(&tmsg->tt_nmsg, NULL, &netisr_adone_rport, + netmsg_init(&tmsg->tt_msg, NULL, &netisr_adone_rport, MSGF_DROPABLE | MSGF_PRIORITY, tcp_timer_handler); tmsg->tt_cpuid = mycpuid; tmsg->tt_msgport = msgport; @@ -719,12 +719,12 @@ tcp_destroy_timermsg(struct tcpcb *tp) KKASSERT(tmsg->tt_cpuid == mycpuid); crit_enter(); - if ((tmsg->tt_nmsg.nm_lmsg.ms_flags & MSGF_DONE) == 0) { + if ((tmsg->tt_msg.lmsg.ms_flags & MSGF_DONE) == 0) { /* * This message is still pending to be processed; * drop it. */ - lwkt_dropmsg(&tmsg->tt_nmsg.nm_lmsg); + lwkt_dropmsg(&tmsg->tt_msg.lmsg); } crit_exit(); } diff --git a/sys/netinet/tcp_timer.h b/sys/netinet/tcp_timer.h index 30ad18fbef..78eac74ea7 100644 --- a/sys/netinet/tcp_timer.h +++ b/sys/netinet/tcp_timer.h @@ -132,7 +132,7 @@ static const char *tcptimers[] = struct tcpcb; struct netmsg_tcp_timer { - struct netmsg tt_nmsg; + struct netmsg_base tt_msg; struct tcpcb *tt_tcb; int tt_cpuid; /* owner cpuid */ lwkt_port_t tt_msgport; /* owner msgport */ diff --git a/sys/netinet/tcp_usrreq.c b/sys/netinet/tcp_usrreq.c index b990389e0c..a1d30d202f 100644 --- a/sys/netinet/tcp_usrreq.c +++ b/sys/netinet/tcp_usrreq.c @@ -135,12 +135,11 @@ extern char *tcpstates[]; /* XXX ??? */ static int tcp_attach (struct socket *, struct pru_attach_info *); -static int tcp_connect (struct tcpcb *, int flags, struct mbuf *m, - struct sockaddr *, struct thread *); +static void tcp_connect (netmsg_t msg); #ifdef INET6 -static int tcp6_connect (struct tcpcb *, int flags, struct mbuf *m, - struct sockaddr *, struct thread *); -static int tcp6_connect_oncpu(struct tcpcb *tp, int flags, struct mbuf *m, +static void tcp6_connect (netmsg_t msg); +static int tcp6_connect_oncpu(struct tcpcb *tp, int flags, + struct mbuf **mp, struct sockaddr_in6 *sin6, struct in6_addr *addr6); #endif /* INET6 */ @@ -165,9 +164,11 @@ static struct tcpcb * * and an internet control block. This is likely occuring on * cpu0 and may have to move later when we bind/connect. */ -static int -tcp_usr_attach(struct socket *so, int proto, struct pru_attach_info *ai) +static void +tcp_usr_attach(netmsg_t msg) { + struct socket *so = msg->base.nm_so; + struct pru_attach_info *ai = msg->attach.nm_ai; int error; struct inpcb *inp; struct tcpcb *tp = 0; @@ -191,7 +192,7 @@ tcp_usr_attach(struct socket *so, int proto, struct pru_attach_info *ai) out: sofree(so); /* from ref above */ TCPDEBUG2(PRU_ATTACH); - return error; + lwkt_replymsg(&msg->lmsg, error); } /* @@ -201,9 +202,10 @@ out: * which may finish later; embryonic TCB's can just * be discarded here. */ -static int -tcp_usr_detach(struct socket *so) +static void +tcp_usr_detach(netmsg_t msg) { + struct socket *so = msg->base.nm_so; int error = 0; struct inpcb *inp; struct tcpcb *tp; @@ -214,48 +216,58 @@ tcp_usr_detach(struct socket *so) /* * If the inp is already detached it may have been due to an async * close. Just return as if no error occured. - */ - if (inp == NULL) - return 0; - - /* + * * It's possible for the tcpcb (tp) to disconnect from the inp due * to tcp_drop()->tcp_close() being called. This may occur *after* * the detach message has been queued so we may find a NULL tp here. */ - if ((tp = intotcpcb(inp)) != NULL) { - TCPDEBUG1(); - tp = tcp_disconnect(tp); - TCPDEBUG2(PRU_DETACH); + if (inp) { + if ((tp = intotcpcb(inp)) != NULL) { + TCPDEBUG1(); + tp = tcp_disconnect(tp); + TCPDEBUG2(PRU_DETACH); + } } - return error; + lwkt_replymsg(&msg->lmsg, error); } /* - * Note: ignore_error is non-zero for certain disconnection races + * NOTE: ignore_error is non-zero for certain disconnection races * which we want to silently allow, otherwise close() may return * an unexpected error. + * + * NOTE: The variables (msg) and (tp) are assumed. */ #define COMMON_START(so, inp, ignore_error) \ - TCPDEBUG0; \ - \ - inp = so->so_pcb; \ - do { \ + TCPDEBUG0; \ + \ + inp = so->so_pcb; \ + do { \ if (inp == NULL) { \ - return (ignore_error ? 0 : EINVAL); \ + error = ignore_error ? 0 : EINVAL; \ + tp = NULL; \ + goto out; \ } \ tp = intotcpcb(inp); \ TCPDEBUG1(); \ } while(0) -#define COMMON_END(req) out: TCPDEBUG2(req); return error; goto out +#define COMMON_END(req) \ + out: do { \ + TCPDEBUG2(req); \ + lwkt_replymsg(&msg->lmsg, error); \ + return; \ + } while(0) /* * Give the socket an address. */ -static int -tcp_usr_bind(struct socket *so, struct sockaddr *nam, struct thread *td) +static void +tcp_usr_bind(netmsg_t msg) { + struct socket *so = msg->bind.base.nm_so; + struct sockaddr *nam = msg->bind.nm_nam; + struct thread *td = msg->bind.nm_td; int error = 0; struct inpcb *inp; struct tcpcb *tp; @@ -281,9 +293,13 @@ tcp_usr_bind(struct socket *so, struct sockaddr *nam, struct thread *td) } #ifdef INET6 -static int -tcp6_usr_bind(struct socket *so, struct sockaddr *nam, struct thread *td) + +static void +tcp6_usr_bind(netmsg_t msg) { + struct socket *so = msg->bind.base.nm_so; + struct sockaddr *nam = msg->bind.nm_nam; + struct thread *td = msg->bind.nm_td; int error = 0; struct inpcb *inp; struct tcpcb *tp; @@ -324,28 +340,32 @@ tcp6_usr_bind(struct socket *so, struct sockaddr *nam, struct thread *td) #endif /* INET6 */ #ifdef SMP + struct netmsg_inswildcard { - struct netmsg nm_netmsg; + struct netmsg_base base; struct inpcb *nm_inp; struct inpcbinfo *nm_pcbinfo; }; static void -in_pcbinswildcardhash_handler(struct netmsg *msg0) +in_pcbinswildcardhash_handler(netmsg_t msg) { - struct netmsg_inswildcard *msg = (struct netmsg_inswildcard *)msg0; + struct netmsg_inswildcard *nm = (struct netmsg_inswildcard *)msg; - in_pcbinswildcardhash_oncpu(msg->nm_inp, msg->nm_pcbinfo); - lwkt_replymsg(&msg->nm_netmsg.nm_lmsg, 0); + in_pcbinswildcardhash_oncpu(nm->nm_inp, nm->nm_pcbinfo); + lwkt_replymsg(&nm->base.lmsg, 0); } + #endif /* * Prepare to accept connections. */ -static int -tcp_usr_listen(struct socket *so, struct thread *td) +static void +tcp_usr_listen(netmsg_t msg) { + struct socket *so = msg->listen.base.nm_so; + struct thread *td = msg->listen.nm_td; int error = 0; struct inpcb *inp; struct tcpcb *tp; @@ -369,20 +389,20 @@ tcp_usr_listen(struct socket *so, struct thread *td) */ inp->inp_flags |= INP_WILDCARD_MP; for (cpu = 0; cpu < ncpus2; cpu++) { - struct netmsg_inswildcard *msg; + struct netmsg_inswildcard *nm; if (cpu == mycpu->gd_cpuid) { in_pcbinswildcardhash(inp); continue; } - msg = kmalloc(sizeof(struct netmsg_inswildcard), M_LWKTMSG, - M_INTWAIT); - netmsg_init(&msg->nm_netmsg, NULL, &netisr_afree_rport, + nm = kmalloc(sizeof(struct netmsg_inswildcard), + M_LWKTMSG, M_INTWAIT); + netmsg_init(&nm->base, NULL, &netisr_afree_rport, 0, in_pcbinswildcardhash_handler); - msg->nm_inp = inp; - msg->nm_pcbinfo = &tcbinfo[cpu]; - lwkt_sendmsg(cpu_portfn(cpu), &msg->nm_netmsg.nm_lmsg); + nm->nm_inp = inp; + nm->nm_pcbinfo = &tcbinfo[cpu]; + lwkt_sendmsg(cpu_portfn(cpu), &nm->base.lmsg); } #else in_pcbinswildcardhash(inp); @@ -391,9 +411,12 @@ tcp_usr_listen(struct socket *so, struct thread *td) } #ifdef INET6 -static int -tcp6_usr_listen(struct socket *so, struct thread *td) + +static void +tcp6_usr_listen(netmsg_t msg) { + struct socket *so = msg->listen.base.nm_so; + struct thread *td = msg->listen.nm_td; int error = 0; struct inpcb *inp; struct tcpcb *tp; @@ -418,20 +441,20 @@ tcp6_usr_listen(struct socket *so, struct thread *td) */ inp->inp_flags |= INP_WILDCARD_MP; for (cpu = 0; cpu < ncpus2; cpu++) { - struct netmsg_inswildcard *msg; + struct netmsg_inswildcard *nm; if (cpu == mycpu->gd_cpuid) { in_pcbinswildcardhash(inp); continue; } - msg = kmalloc(sizeof(struct netmsg_inswildcard), M_LWKTMSG, - M_INTWAIT); - netmsg_init(&msg->nm_netmsg, NULL, &netisr_afree_rport, + nm = kmalloc(sizeof(struct netmsg_inswildcard), + M_LWKTMSG, M_INTWAIT); + netmsg_init(&nm->base, NULL, &netisr_afree_rport, 0, in_pcbinswildcardhash_handler); - msg->nm_inp = inp; - msg->nm_pcbinfo = &tcbinfo[cpu]; - lwkt_sendmsg(cpu_portfn(cpu), &msg->nm_netmsg.nm_lmsg); + nm->nm_inp = inp; + nm->nm_pcbinfo = &tcbinfo[cpu]; + lwkt_sendmsg(cpu_portfn(cpu), &nm->base.lmsg); } #else in_pcbinswildcardhash(inp); @@ -447,9 +470,12 @@ tcp6_usr_listen(struct socket *so, struct thread *td) * Start keep-alive timer, and seed output sequence space. * Send initial segment on connection. */ -static int -tcp_usr_connect(struct socket *so, struct sockaddr *nam, struct thread *td) +static void +tcp_usr_connect(netmsg_t msg) { + struct socket *so = msg->connect.base.nm_so; + struct sockaddr *nam = msg->connect.nm_nam; + struct thread *td = msg->connect.nm_td; int error = 0; struct inpcb *inp; struct tcpcb *tp; @@ -472,15 +498,25 @@ tcp_usr_connect(struct socket *so, struct sockaddr *nam, struct thread *td) goto out; } - if ((error = tcp_connect(tp, 0, NULL, nam, td)) != 0) - goto out; - COMMON_END(PRU_CONNECT); + tcp_connect(msg); + /* msg is invalid now */ + return; +out: + if (msg->connect.nm_m) { + m_freem(msg->connect.nm_m); + msg->connect.nm_m = NULL; + } + lwkt_replymsg(&msg->lmsg, error); } #ifdef INET6 -static int -tcp6_usr_connect(struct socket *so, struct sockaddr *nam, struct thread *td) + +static void +tcp6_usr_connect(netmsg_t msg) { + struct socket *so = msg->connect.base.nm_so; + struct sockaddr *nam = msg->connect.nm_nam; + struct thread *td = msg->connect.nm_td; int error = 0; struct inpcb *inp; struct tcpcb *tp; @@ -504,29 +540,38 @@ tcp6_usr_connect(struct socket *so, struct sockaddr *nam, struct thread *td) } if (IN6_IS_ADDR_V4MAPPED(&sin6p->sin6_addr)) { - struct sockaddr_in sin; + struct sockaddr_in *sinp; if ((inp->inp_flags & IN6P_IPV6_V6ONLY) != 0) { error = EINVAL; goto out; } - - in6_sin6_2_sin(&sin, sin6p); + sinp = kmalloc(sizeof(*sinp), M_LWKTMSG, M_INTWAIT); + in6_sin6_2_sin(sinp, sin6p); inp->inp_vflag |= INP_IPV4; inp->inp_vflag &= ~INP_IPV6; - error = tcp_connect(tp, 0, NULL, (struct sockaddr *)&sin, td); - if (error) - goto out; - goto out; + msg->connect.nm_nam = (struct sockaddr *)sinp; + msg->connect.nm_reconnect |= NMSG_RECONNECT_NAMALLOC; + tcp_connect(msg); + /* msg is invalid now */ + return; } inp->inp_vflag &= ~INP_IPV4; inp->inp_vflag |= INP_IPV6; inp->inp_inc.inc_isipv6 = 1; - if ((error = tcp6_connect(tp, 0, NULL, nam, td)) != 0) - goto out; - error = tcp_output(tp); - COMMON_END(PRU_CONNECT); + + msg->connect.nm_reconnect |= NMSG_RECONNECT_FALLBACK; + tcp6_connect(msg); + /* msg is invalid now */ + return; +out: + if (msg->connect.nm_m) { + m_freem(msg->connect.nm_m); + msg->connect.nm_m = NULL; + } + lwkt_replymsg(&msg->lmsg, error); } + #endif /* INET6 */ /* @@ -540,9 +585,10 @@ tcp6_usr_connect(struct socket *so, struct sockaddr *nam, struct thread *td) * * SHOULD IMPLEMENT LATER PRU_CONNECT VIA REALLOC TCPCB. */ -static int -tcp_usr_disconnect(struct socket *so) +static void +tcp_usr_disconnect(netmsg_t msg) { + struct socket *so = msg->disconnect.base.nm_so; int error = 0; struct inpcb *inp; struct tcpcb *tp; @@ -557,9 +603,11 @@ tcp_usr_disconnect(struct socket *so) * done at higher levels; just return the address * of the peer, storing through addr. */ -static int -tcp_usr_accept(struct socket *so, struct sockaddr **nam) +static void +tcp_usr_accept(netmsg_t msg) { + struct socket *so = msg->accept.base.nm_so; + struct sockaddr **nam = msg->accept.nm_nam; int error = 0; struct inpcb *inp; struct tcpcb *tp = NULL; @@ -570,8 +618,10 @@ tcp_usr_accept(struct socket *so, struct sockaddr **nam) error = ECONNABORTED; goto out; } - if (inp == 0) - return (EINVAL); + if (inp == 0) { + error = EINVAL; + goto out; + } tp = intotcpcb(inp); TCPDEBUG1(); @@ -580,9 +630,11 @@ tcp_usr_accept(struct socket *so, struct sockaddr **nam) } #ifdef INET6 -static int -tcp6_usr_accept(struct socket *so, struct sockaddr **nam) +static void +tcp6_usr_accept(netmsg_t msg) { + struct socket *so = msg->accept.base.nm_so; + struct sockaddr **nam = msg->accept.nm_nam; int error = 0; struct inpcb *inp; struct tcpcb *tp = NULL; @@ -594,8 +646,10 @@ tcp6_usr_accept(struct socket *so, struct sockaddr **nam) error = ECONNABORTED; goto out; } - if (inp == 0) - return (EINVAL); + if (inp == 0) { + error = EINVAL; + goto out; + } tp = intotcpcb(inp); TCPDEBUG1(); in6_mapped_peeraddr(so, nam); @@ -605,9 +659,10 @@ tcp6_usr_accept(struct socket *so, struct sockaddr **nam) /* * Mark the connection as being incapable of further output. */ -static int -tcp_usr_shutdown(struct socket *so) +static void +tcp_usr_shutdown(netmsg_t msg) { + struct socket *so = msg->shutdown.base.nm_so; int error = 0; struct inpcb *inp; struct tcpcb *tp; @@ -623,9 +678,10 @@ tcp_usr_shutdown(struct socket *so) /* * After a receive, possibly send window update to peer. */ -static int -tcp_usr_rcvd(struct socket *so, int flags) +static void +tcp_usr_rcvd(netmsg_t msg) { + struct socket *so = msg->rcvd.base.nm_so; int error = 0; struct inpcb *inp; struct tcpcb *tp; @@ -642,10 +698,15 @@ tcp_usr_rcvd(struct socket *so, int flags) * must either enqueue them or free them. The other pru_* routines * generally are caller-frees. */ -static int -tcp_usr_send(struct socket *so, int flags, struct mbuf *m, - struct sockaddr *nam, struct mbuf *control, struct thread *td) +static void +tcp_usr_send(netmsg_t msg) { + struct socket *so = msg->send.base.nm_so; + int flags = msg->send.nm_flags; + struct mbuf *m = msg->send.nm_m; + struct sockaddr *nam = msg->send.nm_addr; + struct mbuf *control = msg->send.nm_control; + struct thread *td = msg->send.nm_td; int error = 0; struct inpcb *inp; struct tcpcb *tp; @@ -704,18 +765,20 @@ tcp_usr_send(struct socket *so, int flags, struct mbuf *m, * NOTE! PROTOCOL THREAD MAY BE CHANGED BY THE CONNECT! */ if (nam && tp->t_state < TCPS_SYN_SENT) { + kprintf("implied fallback\n"); + msg->connect.nm_nam = nam; + msg->connect.nm_td = td; + msg->connect.nm_m = m; + msg->connect.nm_flags = flags; + msg->connect.nm_reconnect = NMSG_RECONNECT_FALLBACK; #ifdef INET6 if (isipv6) - error = tcp6_connect(tp, flags, m, nam, td); + tcp6_connect(msg); else #endif /* INET6 */ - error = tcp_connect(tp, flags, m, nam, td); -#if 0 - /* WTF is this doing here? */ - tp->snd_wnd = TTCP_CLIENT_SND_WND; - tcp_mss(tp, -1); -#endif - goto out; + tcp_connect(msg); + /* msg invalid now */ + return; } /* @@ -761,9 +824,10 @@ tcp_usr_send(struct socket *so, int flags, struct mbuf *m, * NOTE: (so) is referenced from soabort*() and netmsg_pru_abort() * will sofree() it when we return. */ -static int -tcp_usr_abort(struct socket *so) +static void +tcp_usr_abort(netmsg_t msg) { + struct socket *so = msg->abort.base.nm_so; int error = 0; struct inpcb *inp; struct tcpcb *tp; @@ -776,9 +840,12 @@ tcp_usr_abort(struct socket *so) /* * Receive out-of-band data. */ -static int -tcp_usr_rcvoob(struct socket *so, struct mbuf *m, int flags) +static void +tcp_usr_rcvoob(netmsg_t msg) { + struct socket *so = msg->rcvoob.base.nm_so; + struct mbuf *m = msg->rcvoob.nm_m; + int flags = msg->rcvoob.nm_flags; int error = 0; struct inpcb *inp; struct tcpcb *tp; @@ -809,18 +876,18 @@ struct pr_usrreqs tcp_usrreqs = { .pru_attach = tcp_usr_attach, .pru_bind = tcp_usr_bind, .pru_connect = tcp_usr_connect, - .pru_connect2 = pru_connect2_notsupp, - .pru_control = in_control, + .pru_connect2 = pr_generic_notsupp, + .pru_control = in_control_dispatch, .pru_detach = tcp_usr_detach, .pru_disconnect = tcp_usr_disconnect, .pru_listen = tcp_usr_listen, - .pru_peeraddr = in_setpeeraddr, + .pru_peeraddr = in_setpeeraddr_dispatch, .pru_rcvd = tcp_usr_rcvd, .pru_rcvoob = tcp_usr_rcvoob, .pru_send = tcp_usr_send, .pru_sense = pru_sense_null, .pru_shutdown = tcp_usr_shutdown, - .pru_sockaddr = in_setsockaddr, + .pru_sockaddr = in_setsockaddr_dispatch, .pru_sosend = sosend, .pru_soreceive = soreceive }; @@ -832,18 +899,18 @@ struct pr_usrreqs tcp6_usrreqs = { .pru_attach = tcp_usr_attach, .pru_bind = tcp6_usr_bind, .pru_connect = tcp6_usr_connect, - .pru_connect2 = pru_connect2_notsupp, - .pru_control = in6_control, + .pru_connect2 = pr_generic_notsupp, + .pru_control = in6_control_dispatch, .pru_detach = tcp_usr_detach, .pru_disconnect = tcp_usr_disconnect, .pru_listen = tcp6_usr_listen, - .pru_peeraddr = in6_mapped_peeraddr, + .pru_peeraddr = in6_mapped_peeraddr_dispatch, .pru_rcvd = tcp_usr_rcvd, .pru_rcvoob = tcp_usr_rcvoob, .pru_send = tcp_usr_send, .pru_sense = pru_sense_null, .pru_shutdown = tcp_usr_shutdown, - .pru_sockaddr = in6_mapped_sockaddr, + .pru_sockaddr = in6_mapped_sockaddr_dispatch, .pru_sosend = sosend, .pru_soreceive = soreceive }; @@ -858,10 +925,10 @@ tcp_connect_oncpu(struct tcpcb *tp, int flags, struct mbuf *m, struct route *ro = &inp->inp_route; oinp = in_pcblookup_hash(&tcbinfo[mycpu->gd_cpuid], - sin->sin_addr, sin->sin_port, - inp->inp_laddr.s_addr != INADDR_ANY ? - inp->inp_laddr : if_sin->sin_addr, - inp->inp_lport, 0, NULL); + sin->sin_addr, sin->sin_port, + (inp->inp_laddr.s_addr != INADDR_ANY ? + inp->inp_laddr : if_sin->sin_addr), + inp->inp_lport, 0, NULL); if (oinp != NULL) { m_freem(m); return (EADDRINUSE); @@ -936,58 +1003,6 @@ tcp_connect_oncpu(struct tcpcb *tp, int flags, struct mbuf *m, return (tcp_output(tp)); } -#ifdef SMP - -struct netmsg_tcp_connect { - struct netmsg nm_netmsg; - struct tcpcb *nm_tp; - struct sockaddr_in *nm_sin; - struct sockaddr_in *nm_ifsin; - int nm_flags; - struct mbuf *nm_m; -}; - -/* - * This is called in the target protocol processing thread. We must - * re-link our pcb to the new tcpcb - */ -static void -tcp_connect_handler(netmsg_t netmsg) -{ - struct netmsg_tcp_connect *msg = (void *)netmsg; - struct socket *so = netmsg->nm_so; - int error; - - in_pcblink(so->so_pcb, &tcbinfo[mycpu->gd_cpuid]); - error = tcp_connect_oncpu(msg->nm_tp, msg->nm_flags, msg->nm_m, - msg->nm_sin, msg->nm_ifsin); - lwkt_replymsg(&msg->nm_netmsg.nm_lmsg, error); -} - -struct netmsg_tcp6_connect { - struct netmsg nm_netmsg; - struct tcpcb *nm_tp; - struct sockaddr_in6 *nm_sin6; - struct in6_addr *nm_addr6; - int nm_flags; - struct mbuf *nm_m; -}; - -#ifdef INET6 -static void -tcp6_connect_handler(netmsg_t netmsg) -{ - struct netmsg_tcp6_connect *msg = (void *)netmsg; - int error; - - error = tcp6_connect_oncpu(msg->nm_tp, msg->nm_flags, msg->nm_m, - msg->nm_sin6, msg->nm_addr6); - lwkt_replymsg(&msg->nm_netmsg.nm_lmsg, error); -} -#endif - -#endif /* SMP */ - /* * Common subroutine to open a TCP connection to remote host specified * by struct sockaddr_in in mbuf *nam. Call in_pcbbind to assign a local @@ -995,28 +1010,38 @@ tcp6_connect_handler(netmsg_t netmsg) * a local host address (interface). * Initialize connection parameters and enter SYN-SENT state. */ -static int -tcp_connect(struct tcpcb *tp, int flags, struct mbuf *m, - struct sockaddr *nam, struct thread *td) +static void +tcp_connect(netmsg_t msg) { - struct inpcb *inp = tp->t_inpcb; + struct socket *so = msg->connect.base.nm_so; + struct sockaddr *nam = msg->connect.nm_nam; + struct thread *td = msg->connect.nm_td; struct sockaddr_in *sin = (struct sockaddr_in *)nam; struct sockaddr_in *if_sin; - struct socket *so; + struct inpcb *inp; + struct tcpcb *tp; int error; #ifdef SMP lwkt_port_t port; #endif + COMMON_START(so, inp, 0); + + /* + * Reconnect our pcb if we have to + */ + if (msg->connect.nm_reconnect & NMSG_RECONNECT_RECONNECT) { + msg->connect.nm_reconnect &= ~NMSG_RECONNECT_RECONNECT; + in_pcblink(so->so_pcb, &tcbinfo[mycpu->gd_cpuid]); + } + /* * Bind if we have to */ if (inp->inp_lport == 0) { error = in_pcbbind(inp, NULL, td); - if (error) { - m_freem(m); - return (error); - } + if (error) + goto out; } so = inp->inp_socket; KKASSERT(so); @@ -1027,19 +1052,16 @@ tcp_connect(struct tcpcb *tp, int flags, struct mbuf *m, * forward the message or it will get bounced right back to us. */ error = in_pcbladdr(inp, nam, &if_sin, td); - if (error) { - m_freem(m); - return (error); - } + if (error) + goto out; #ifdef SMP port = tcp_addrport(sin->sin_addr.s_addr, sin->sin_port, - inp->inp_laddr.s_addr ? - inp->inp_laddr.s_addr : if_sin->sin_addr.s_addr, - inp->inp_lport); + (inp->inp_laddr.s_addr ? + inp->inp_laddr.s_addr : if_sin->sin_addr.s_addr), + inp->inp_lport); if (port != &curthread->td_msgport) { - struct netmsg_tcp_connect msg; struct route *ro = &inp->inp_route; /* @@ -1058,32 +1080,42 @@ tcp_connect(struct tcpcb *tp, int flags, struct mbuf *m, */ in_pcbunlink(so->so_pcb, &tcbinfo[mycpu->gd_cpuid]); sosetport(so, port); + msg->connect.nm_reconnect |= NMSG_RECONNECT_RECONNECT; + msg->connect.base.nm_dispatch = tcp_connect; - netmsg_init(&msg.nm_netmsg, so, &curthread->td_msgport, - 0, tcp_connect_handler); - msg.nm_tp = tp; - msg.nm_sin = sin; - msg.nm_ifsin = if_sin; - msg.nm_flags = flags; - msg.nm_m = m; - error = lwkt_domsg(port, &msg.nm_netmsg.nm_lmsg, 0); - } else { - error = tcp_connect_oncpu(tp, flags, m, sin, if_sin); + lwkt_forwardmsg(port, &msg->connect.base.lmsg); + /* msg invalid now */ + return; } #else KKASSERT(so->so_port == &curthread->td_msgport); - error = tcp_connect_oncpu(tp, flags, m, sin, if_sin); #endif - return (error); + error = tcp_connect_oncpu(tp, msg->connect.nm_flags, + msg->connect.nm_m, sin, if_sin); + msg->connect.nm_m = NULL; +out: + if (msg->connect.nm_m) { + m_freem(msg->connect.nm_m); + msg->connect.nm_m = NULL; + } + if (msg->connect.nm_reconnect & NMSG_RECONNECT_NAMALLOC) { + kfree(msg->connect.nm_nam, M_LWKTMSG); + msg->connect.nm_nam = NULL; + } + lwkt_replymsg(&msg->connect.base.lmsg, error); + /* msg invalid now */ } #ifdef INET6 -static int -tcp6_connect(struct tcpcb *tp, int flags, struct mbuf *m, - struct sockaddr *nam, struct thread *td) +static void +tcp6_connect(netmsg_t msg) { - struct inpcb *inp = tp->t_inpcb; + struct tcpcb *tp; + struct socket *so = msg->connect.base.nm_so; + struct sockaddr *nam = msg->connect.nm_nam; + struct thread *td = msg->connect.nm_td; + struct inpcb *inp; struct sockaddr_in6 *sin6 = (struct sockaddr_in6 *)nam; struct in6_addr *addr6; #ifdef SMP @@ -1091,12 +1123,23 @@ tcp6_connect(struct tcpcb *tp, int flags, struct mbuf *m, #endif int error; + COMMON_START(so, inp, 0); + + /* + * Reconnect our pcb if we have to + */ + if (msg->connect.nm_reconnect & NMSG_RECONNECT_RECONNECT) { + msg->connect.nm_reconnect &= ~NMSG_RECONNECT_RECONNECT; + in_pcblink(so->so_pcb, &tcbinfo[mycpu->gd_cpuid]); + } + + /* + * Bind if we have to + */ if (inp->inp_lport == 0) { error = in6_pcbbind(inp, NULL, td); - if (error) { - m_freem(m); - return (error); - } + if (error) + goto out; } /* @@ -1105,16 +1148,13 @@ tcp6_connect(struct tcpcb *tp, int flags, struct mbuf *m, * TIME_WAIT state, creating an ADDRINUSE error. */ error = in6_pcbladdr(inp, nam, &addr6, td); - if (error) { - m_freem(m); - return (error); - } + if (error) + goto out; #ifdef SMP port = tcp6_addrport(); /* XXX hack for now, always cpu0 */ if (port != &curthread->td_msgport) { - struct netmsg_tcp6_connect msg; struct route *ro = &inp->inp_route; /* @@ -1126,27 +1166,42 @@ tcp6_connect(struct tcpcb *tp, int flags, struct mbuf *m, RTFREE(ro->ro_rt); bzero(ro, sizeof(*ro)); - netmsg_init(&msg.nm_netmsg, NULL, &curthread->td_msgport, - 0, tcp6_connect_handler); - msg.nm_tp = tp; - msg.nm_sin6 = sin6; - msg.nm_addr6 = addr6; - msg.nm_flags = flags; - msg.nm_m = m; - error = lwkt_domsg(port, &msg.nm_netmsg.nm_lmsg, 0); - } else { - error = tcp6_connect_oncpu(tp, flags, m, sin6, addr6); + in_pcbunlink(so->so_pcb, &tcbinfo[mycpu->gd_cpuid]); + sosetport(so, port); + msg->connect.nm_reconnect |= NMSG_RECONNECT_RECONNECT; + msg->connect.base.nm_dispatch = tcp6_connect; + + lwkt_forwardmsg(port, &msg->connect.base.lmsg); + /* msg invalid now */ + return; } -#else - error = tcp6_connect_oncpu(tp, flags, m, sin6, addr6); #endif - return (error); + error = tcp6_connect_oncpu(tp, msg->connect.nm_flags, + &msg->connect.nm_m, sin6, addr6); + /* nm_m may still be intact */ +out: + if (error && (msg->connect.nm_reconnect & NMSG_RECONNECT_FALLBACK)) { + tcp_connect(msg); + /* msg invalid now */ + } else { + if (msg->connect.nm_m) { + m_freem(msg->connect.nm_m); + msg->connect.nm_m = NULL; + } + if (msg->connect.nm_reconnect & NMSG_RECONNECT_NAMALLOC) { + kfree(msg->connect.nm_nam, M_LWKTMSG); + msg->connect.nm_nam = NULL; + } + lwkt_replymsg(&msg->connect.base.lmsg, error); + /* msg invalid now */ + } } static int -tcp6_connect_oncpu(struct tcpcb *tp, int flags, struct mbuf *m, +tcp6_connect_oncpu(struct tcpcb *tp, int flags, struct mbuf **mp, struct sockaddr_in6 *sin6, struct in6_addr *addr6) { + struct mbuf *m = *mp; struct inpcb *inp = tp->t_inpcb; struct socket *so = inp->inp_socket; struct inpcb *oinp; @@ -1158,13 +1213,12 @@ tcp6_connect_oncpu(struct tcpcb *tp, int flags, struct mbuf *m, */ oinp = in6_pcblookup_hash(inp->inp_cpcbinfo, &sin6->sin6_addr, sin6->sin6_port, - IN6_IS_ADDR_UNSPECIFIED(&inp->in6p_laddr) ? - addr6 : &inp->in6p_laddr, + (IN6_IS_ADDR_UNSPECIFIED(&inp->in6p_laddr) ? + addr6 : &inp->in6p_laddr), inp->inp_lport, 0, NULL); - if (oinp) { - m_freem(m); + if (oinp) return (EADDRINUSE); - } + if (IN6_IS_ADDR_UNSPECIFIED(&inp->in6p_laddr)) inp->in6p_laddr = *addr6; inp->in6p_faddr = sin6->sin6_addr; @@ -1198,7 +1252,7 @@ tcp6_connect_oncpu(struct tcpcb *tp, int flags, struct mbuf *m, tcp_sendseqinit(tp); if (m) { ssb_appendstream(&so->so_snd, m); - m = NULL; + *mp = NULL; if (flags & PRUS_OOB) tp->snd_up = tp->snd_una + so->so_snd.ssb_cc; } @@ -1223,26 +1277,31 @@ tcp6_connect_oncpu(struct tcpcb *tp, int flags, struct mbuf *m, * both now use TSM, there probably isn't any need for this function to * run in a critical section any more. This needs more examination.) */ -int -tcp_ctloutput(struct socket *so, struct sockopt *sopt) +void +tcp_ctloutput(netmsg_t msg) { + struct socket *so = msg->base.nm_so; + struct sockopt *sopt = msg->ctloutput.nm_sopt; int error, opt, optval; struct inpcb *inp; struct tcpcb *tp; error = 0; inp = so->so_pcb; - if (inp == NULL) - return (ECONNRESET); + if (inp == NULL) { + error = ECONNRESET; + goto done; + } if (sopt->sopt_level != IPPROTO_TCP) { #ifdef INET6 if (INP_CHECK_SOCKAF(so, AF_INET6)) - error = ip6_ctloutput(so, sopt); + ip6_ctloutput_dispatch(msg); else #endif /* INET6 */ - error = ip_ctloutput(so, sopt); - return (error); + ip_ctloutput(msg); + /* msg invalid now */ + return; } tp = intotcpcb(inp); @@ -1343,7 +1402,8 @@ tcp_ctloutput(struct socket *so, struct sockopt *sopt) soopt_from_kbuf(sopt, &optval, sizeof optval); break; } - return (error); +done: + lwkt_replymsg(&msg->lmsg, error); } /* diff --git a/sys/netinet/tcp_var.h b/sys/netinet/tcp_var.h index 29b4cbe5cf..20810b99e4 100644 --- a/sys/netinet/tcp_var.h +++ b/sys/netinet/tcp_var.h @@ -565,6 +565,8 @@ extern int tcp_minmss; extern int tcp_delack_enabled; extern int path_mtu_discovery; +union netmsg; + int tcp_addrcpu(in_addr_t faddr, in_port_t fport, in_addr_t laddr, in_port_t lport); struct lwkt_port * @@ -574,17 +576,15 @@ struct lwkt_port *tcp_addrport0(void); void tcp_canceltimers (struct tcpcb *); struct tcpcb * tcp_close (struct tcpcb *); -void tcp_ctlinput (int, struct sockaddr *, void *); -int tcp_ctloutput (struct socket *, struct sockopt *); -struct lwkt_port * - tcp_cport(int cpu); +void tcp_ctlinput(union netmsg *); +void tcp_ctloutput(union netmsg *); struct tcpcb * tcp_drop (struct tcpcb *, int); void tcp_drain (void); void tcp_fasttimo (void); void tcp_init (void); void tcp_thread_init (void); -void tcp_input (struct mbuf *, ...); +int tcp_input (struct mbuf **, int *, int); void tcp_mss (struct tcpcb *, int); int tcp_mssopt (struct tcpcb *); void tcp_drop_syn_sent (struct inpcb *, int); diff --git a/sys/netinet/udp_usrreq.c b/sys/netinet/udp_usrreq.c index 0d7b7fcee3..025f6bde66 100644 --- a/sys/netinet/udp_usrreq.c +++ b/sys/netinet/udp_usrreq.c @@ -177,9 +177,8 @@ static void ip_2_ip6_hdr (struct ip6_hdr *ip6, struct ip *ip); static int udp_connect_oncpu(struct socket *so, struct thread *td, struct sockaddr_in *sin, struct sockaddr_in *if_sin); -static int udp_detach (struct socket *so); -static int udp_output (struct inpcb *, struct mbuf *, struct sockaddr *, - struct mbuf *, struct thread *); +static int udp_output (struct inpcb *, struct mbuf *, struct sockaddr *, + struct mbuf *, struct thread *); void udp_init(void) @@ -225,23 +224,22 @@ check_multicast_membership(struct ip *ip, struct inpcb *inp, struct mbuf *m) return (-1); } -void -udp_input(struct mbuf *m, ...) +int +udp_input(struct mbuf **mp, int *offp, int proto) { int iphlen; struct ip *ip; struct udphdr *uh; struct inpcb *inp; + struct mbuf *m; struct mbuf *opts = NULL; - int len, off, proto; + int len, off; struct ip save_ip; struct sockaddr *append_sa; - __va_list ap; - __va_start(ap, m); - off = __va_arg(ap, int); - proto = __va_arg(ap, int); - __va_end(ap); + off = *offp; + m = *mp; + *mp = NULL; iphlen = off; udpstat.udps_ipackets++; @@ -314,7 +312,7 @@ udp_input(struct mbuf *m, ...) if (uh->uh_sum) { udpstat.udps_badsum++; m_freem(m); - return; + return(IPPROTO_DONE); } } else udpstat.udps_nosum++; @@ -433,7 +431,7 @@ udp_input(struct mbuf *m, ...) goto bad; #endif /*FAST_IPSEC*/ udp_append(last, ip, m, iphlen + sizeof(struct udphdr)); - return; + return(IPPROTO_DONE); } /* * Locate pcb for datagram. @@ -464,7 +462,7 @@ udp_input(struct mbuf *m, ...) *ip = save_ip; ip->ip_len += iphlen; icmp_error(m, ICMP_UNREACH, ICMP_UNREACH_PORT, 0, 0); - return; + return(IPPROTO_DONE); } #ifdef IPSEC if (ipsec4_in_reject_so(m, inp->inp_socket)) { @@ -516,12 +514,12 @@ udp_input(struct mbuf *m, ...) goto bad; } sorwakeup(inp->inp_socket); - return; + return(IPPROTO_DONE); bad: m_freem(m); if (opts) m_freem(opts); - return; + return(IPPROTO_DONE); } #ifdef INET6 @@ -602,31 +600,31 @@ udp_notify(struct inpcb *inp, int error) } struct netmsg_udp_notify { - struct netmsg nm_nmsg; + struct netmsg_base base; void (*nm_notify)(struct inpcb *, int); struct in_addr nm_faddr; int nm_arg; }; static void -udp_notifyall_oncpu(struct netmsg *netmsg) +udp_notifyall_oncpu(netmsg_t msg) { - struct netmsg_udp_notify *nmsg = (struct netmsg_udp_notify *)netmsg; + struct netmsg_udp_notify *nm = (struct netmsg_udp_notify *)msg; #if 0 int nextcpu; #endif - in_pcbnotifyall(&udbinfo.pcblisthead, nmsg->nm_faddr, nmsg->nm_arg, - nmsg->nm_notify); - lwkt_replymsg(&netmsg->nm_lmsg, 0); + in_pcbnotifyall(&udbinfo.pcblisthead, nm->nm_faddr, + nm->nm_arg, nm->nm_notify); + lwkt_replymsg(&nm->base.lmsg, 0); #if 0 /* XXX currently udp only runs on cpu 0 */ nextcpu = mycpuid + 1; if (nextcpu < ncpus2) - lwkt_forwardmsg(cpu_portfn(nextcpu), &netmsg->nm_lmsg); + lwkt_forwardmsg(cpu_portfn(nextcpu), &nm->base.lmsg); else - lwkt_replymsg(&netmsg->nm_lmsg, 0); + lwkt_replymsg(&nmsg->base.lmsg, 0); #endif } @@ -649,9 +647,11 @@ udp_rtchange(struct inpcb *inp, int err) } void -udp_ctlinput(int cmd, struct sockaddr *sa, void *vip) +udp_ctlinput(netmsg_t msg) { - struct ip *ip = vip; + struct sockaddr *sa = msg->ctlinput.nm_arg; + struct ip *ip = msg->ctlinput.nm_extra; + int cmd = msg->ctlinput.nm_cmd; struct udphdr *uh; void (*notify) (struct inpcb *, int) = udp_notify; struct in_addr faddr; @@ -659,15 +659,17 @@ udp_ctlinput(int cmd, struct sockaddr *sa, void *vip) faddr = ((struct sockaddr_in *)sa)->sin_addr; if (sa->sa_family != AF_INET || faddr.s_addr == INADDR_ANY) - return; + goto done; if (PRC_IS_REDIRECT(cmd)) { ip = NULL; notify = udp_rtchange; - } else if (cmd == PRC_HOSTDEAD) + } else if (cmd == PRC_HOSTDEAD) { ip = NULL; - else if ((unsigned)cmd >= PRC_NCMDS || inetctlerrmap[cmd] == 0) - return; + } else if ((unsigned)cmd >= PRC_NCMDS || inetctlerrmap[cmd] == 0) { + goto done; + } + if (ip) { uh = (struct udphdr *)((caddr_t)ip + (ip->ip_hl << 2)); inp = in_pcblookup_hash(&udbinfo, faddr, uh->uh_dport, @@ -675,16 +677,16 @@ udp_ctlinput(int cmd, struct sockaddr *sa, void *vip) if (inp != NULL && inp->inp_socket != NULL) (*notify)(inp, inetctlerrmap[cmd]); } else if (PRC_IS_REDIRECT(cmd)) { - struct netmsg_udp_notify nmsg; + struct netmsg_udp_notify *nm; KKASSERT(&curthread->td_msgport == cpu_portfn(0)); - netmsg_init(&nmsg.nm_nmsg, NULL, &curthread->td_msgport, + nm = kmalloc(sizeof(*nm), M_LWKTMSG, M_INTWAIT); + netmsg_init(&nm->base, NULL, &netisr_afree_rport, 0, udp_notifyall_oncpu); - nmsg.nm_faddr = faddr; - nmsg.nm_arg = inetctlerrmap[cmd]; - nmsg.nm_notify = notify; - - lwkt_sendmsg(cpu_portfn(0), &nmsg.nm_nmsg.nm_lmsg); + nm->nm_faddr = faddr; + nm->nm_arg = inetctlerrmap[cmd]; + nm->nm_notify = notify; + lwkt_sendmsg(cpu_portfn(0), &nm->base.lmsg); } else { /* * XXX We should forward msg upon PRC_HOSTHEAD and ip == NULL, @@ -694,6 +696,8 @@ udp_ctlinput(int cmd, struct sockaddr *sa, void *vip) in_pcbnotifyall(&udbinfo.pcblisthead, faddr, inetctlerrmap[cmd], notify); } +done: + lwkt_replymsg(&msg->lmsg, 0); } SYSCTL_PROC(_net_inet_udp, UDPCTL_PCBLIST, pcblist, CTLFLAG_RD, &udbinfo, 0, @@ -888,9 +892,10 @@ SYSCTL_INT(_net_inet_udp, UDPCTL_RECVSPACE, recvspace, CTLFLAG_RW, * NOTE: (so) is referenced from soabort*() and netmsg_pru_abort() * will sofree() it when we return. */ -static int -udp_abort(struct socket *so) +static void +udp_abort(netmsg_t msg) { + struct socket *so = msg->abort.base.nm_so; struct inpcb *inp; int error; @@ -902,25 +907,28 @@ udp_abort(struct socket *so) } else { error = EINVAL; } - return error; + lwkt_replymsg(&msg->abort.base.lmsg, error); } -static int -udp_attach(struct socket *so, int proto, struct pru_attach_info *ai) +static void +udp_attach(netmsg_t msg) { + struct socket *so = msg->attach.base.nm_so; + struct pru_attach_info *ai = msg->attach.nm_ai; struct inpcb *inp; int error; inp = so->so_pcb; - if (inp != NULL) - return EINVAL; - + if (inp != NULL) { + error = EINVAL; + goto out; + } error = soreserve(so, udp_sendspace, udp_recvspace, ai->sb_rlimit); if (error) - return error; + goto out; error = in_pcballoc(so, &udbinfo); if (error) - return error; + goto out; /* * Set default port for protocol processing prior to bind/connect. @@ -930,56 +938,41 @@ udp_attach(struct socket *so, int proto, struct pru_attach_info *ai) inp = (struct inpcb *)so->so_pcb; inp->inp_vflag |= INP_IPV4; inp->inp_ip_ttl = ip_defttl; - return 0; + error = 0; +out: + lwkt_replymsg(&msg->attach.base.lmsg, error); } -static int -udp_bind(struct socket *so, struct sockaddr *nam, struct thread *td) +static void +udp_bind(netmsg_t msg) { + struct socket *so = msg->bind.base.nm_so; + struct sockaddr *nam = msg->bind.nm_nam; + struct thread *td = msg->bind.nm_td; struct sockaddr_in *sin = (struct sockaddr_in *)nam; struct inpcb *inp; int error; inp = so->so_pcb; - if (inp == NULL) - return EINVAL; - error = in_pcbbind(inp, nam, td); - if (error == 0) { - if (sin->sin_addr.s_addr != INADDR_ANY) - inp->inp_flags |= INP_WASBOUND_NOTANY; - in_pcbinswildcardhash(inp); + if (inp) { + error = in_pcbbind(inp, nam, td); + if (error == 0) { + if (sin->sin_addr.s_addr != INADDR_ANY) + inp->inp_flags |= INP_WASBOUND_NOTANY; + in_pcbinswildcardhash(inp); + } + } else { + error = EINVAL; } - return error; + lwkt_replymsg(&msg->bind.base.lmsg, error); } -#ifdef SMP - -struct netmsg_udp_connect { - struct netmsg nm_netmsg; - struct socket *nm_so; - struct sockaddr_in *nm_sin; - struct sockaddr_in *nm_ifsin; - struct thread *nm_td; -}; - static void -udp_connect_handler(netmsg_t netmsg) -{ - struct netmsg_udp_connect *msg = (void *)netmsg; - int error; - - in_pcblink(msg->nm_so->so_pcb, &udbinfo); - /* in_pcblink(msg->nm_so->so_pcb, &udbinfo[mycpu->gd_cpuid]); */ - error = udp_connect_oncpu(msg->nm_so, msg->nm_td, - msg->nm_sin, msg->nm_ifsin); - lwkt_replymsg(&msg->nm_netmsg.nm_lmsg, error); -} - -#endif - -static int -udp_connect(struct socket *so, struct sockaddr *nam, struct thread *td) +udp_connect(netmsg_t msg) { + struct socket *so = msg->connect.base.nm_so; + struct sockaddr *nam = msg->connect.nm_nam; + struct thread *td = msg->connect.nm_td; struct inpcb *inp; struct sockaddr_in *sin = (struct sockaddr_in *)nam; struct sockaddr_in *if_sin; @@ -987,10 +980,20 @@ udp_connect(struct socket *so, struct sockaddr *nam, struct thread *td) int error; inp = so->so_pcb; - if (inp == NULL) - return EINVAL; - if (inp->inp_faddr.s_addr != INADDR_ANY) - return EISCONN; + if (inp == NULL) { + error = EINVAL; + goto out; + } + + if (msg->connect.nm_reconnect & NMSG_RECONNECT_RECONNECT) { + msg->connect.nm_reconnect &= ~NMSG_RECONNECT_RECONNECT; + in_pcblink(inp, &udbinfo); + } + + if (inp->inp_faddr.s_addr != INADDR_ANY) { + error = EISCONN; + goto out; + } error = 0; /* @@ -1000,7 +1003,7 @@ udp_connect(struct socket *so, struct sockaddr *nam, struct thread *td) inp->inp_laddr.s_addr == INADDR_ANY) { error = in_pcbbind(inp, NULL, td); if (error) - return (error); + goto out; } /* @@ -1009,15 +1012,16 @@ udp_connect(struct socket *so, struct sockaddr *nam, struct thread *td) */ error = in_pcbladdr(inp, nam, &if_sin, td); if (error) - return(error); - if (!prison_remote_ip(td, nam)) - return(EAFNOSUPPORT); /* IPv6 only jail */ + goto out; + if (!prison_remote_ip(td, nam)) { + error = EAFNOSUPPORT; /* IPv6 only jail */ + goto out; + } port = udp_addrport(sin->sin_addr.s_addr, sin->sin_port, inp->inp_laddr.s_addr, inp->inp_lport); #ifdef SMP if (port != &curthread->td_msgport) { - struct netmsg_udp_connect msg; struct route *ro = &inp->inp_route; panic("UDP should only be in one protocol thread %p %p", @@ -1040,26 +1044,19 @@ udp_connect(struct socket *so, struct sockaddr *nam, struct thread *td) in_pcbunlink(so->so_pcb, &udbinfo); /* in_pcbunlink(so->so_pcb, &udbinfo[mycpu->gd_cpuid]); */ sosetport(so, port); + msg->connect.nm_reconnect |= NMSG_RECONNECT_RECONNECT; + msg->connect.base.nm_dispatch = udp_connect; - /* - * NOTE: We haven't set so->so_port yet do not pass so - * to netmsg_init() or it will be improperly forwarded. - */ - netmsg_init(&msg.nm_netmsg, NULL, &curthread->td_msgport, - 0, udp_connect_handler); - msg.nm_so = so; - msg.nm_sin = sin; - msg.nm_ifsin = if_sin; - msg.nm_td = td; - error = lwkt_domsg(port, &msg.nm_netmsg.nm_lmsg, 0); - } else { - error = udp_connect_oncpu(so, td, sin, if_sin); + lwkt_forwardmsg(port, &msg->connect.base.lmsg); + /* msg invalid now */ + return; } -#else +#endif KKASSERT(port == &curthread->td_msgport); error = udp_connect_oncpu(so, td, sin, if_sin); -#endif - return (error); +out: + KKASSERT(msg->connect.nm_m == NULL); + lwkt_replymsg(&msg->connect.base.lmsg, error); } static int @@ -1095,29 +1092,40 @@ udp_connect_oncpu(struct socket *so, struct thread *td, return error; } -static int -udp_detach(struct socket *so) +static void +udp_detach(netmsg_t msg) { + struct socket *so = msg->detach.base.nm_so; struct inpcb *inp; + int error; inp = so->so_pcb; - if (inp == NULL) - return EINVAL; - in_pcbdetach(inp); - return 0; + if (inp) { + in_pcbdetach(inp); + error = 0; + } else { + error = EINVAL; + } + lwkt_replymsg(&msg->detach.base.lmsg, error); } -static int -udp_disconnect(struct socket *so) +static void +udp_disconnect(netmsg_t msg) { + struct socket *so = msg->disconnect.base.nm_so; struct route *ro; struct inpcb *inp; + int error; inp = so->so_pcb; - if (inp == NULL) - return EINVAL; - if (inp->inp_faddr.s_addr == INADDR_ANY) - return ENOTCONN; + if (inp == NULL) { + error = EINVAL; + goto out; + } + if (inp->inp_faddr.s_addr == INADDR_ANY) { + error = ENOTCONN; + goto out; + } soreference(so); in_pcbdisconnect(inp); @@ -1128,54 +1136,68 @@ udp_disconnect(struct socket *so) if (ro->ro_rt != NULL) RTFREE(ro->ro_rt); bzero(ro, sizeof(*ro)); - - return 0; + error = 0; +out: + lwkt_replymsg(&msg->disconnect.base.lmsg, error); } -static int -udp_send(struct socket *so, int flags, struct mbuf *m, struct sockaddr *addr, - struct mbuf *control, struct thread *td) +static void +udp_send(netmsg_t msg) { + struct socket *so = msg->send.base.nm_so; struct inpcb *inp; + int error; inp = so->so_pcb; - if (inp == NULL) { - m_freem(m); - return EINVAL; + if (inp) { + error = udp_output(inp, + msg->send.nm_m, + msg->send.nm_addr, + msg->send.nm_control, + msg->send.nm_td); + } else { + m_freem(msg->send.nm_m); + error = EINVAL; } - return udp_output(inp, m, addr, control, td); + msg->send.nm_m = NULL; + lwkt_replymsg(&msg->send.base.lmsg, error); } -int -udp_shutdown(struct socket *so) +void +udp_shutdown(netmsg_t msg) { + struct socket *so = msg->shutdown.base.nm_so; struct inpcb *inp; + int error; inp = so->so_pcb; - if (inp == NULL) - return EINVAL; - socantsendmore(so); - return 0; + if (inp) { + socantsendmore(so); + error = 0; + } else { + error = EINVAL; + } + lwkt_replymsg(&msg->shutdown.base.lmsg, error); } struct pr_usrreqs udp_usrreqs = { .pru_abort = udp_abort, - .pru_accept = pru_accept_notsupp, + .pru_accept = pr_generic_notsupp, .pru_attach = udp_attach, .pru_bind = udp_bind, .pru_connect = udp_connect, - .pru_connect2 = pru_connect2_notsupp, - .pru_control = in_control, + .pru_connect2 = pr_generic_notsupp, + .pru_control = in_control_dispatch, .pru_detach = udp_detach, .pru_disconnect = udp_disconnect, - .pru_listen = pru_listen_notsupp, - .pru_peeraddr = in_setpeeraddr, - .pru_rcvd = pru_rcvd_notsupp, - .pru_rcvoob = pru_rcvoob_notsupp, + .pru_listen = pr_generic_notsupp, + .pru_peeraddr = in_setpeeraddr_dispatch, + .pru_rcvd = pr_generic_notsupp, + .pru_rcvoob = pr_generic_notsupp, .pru_send = udp_send, .pru_sense = pru_sense_null, .pru_shutdown = udp_shutdown, - .pru_sockaddr = in_setsockaddr, + .pru_sockaddr = in_setsockaddr_dispatch, .pru_sosend = sosendudp, .pru_soreceive = soreceive }; diff --git a/sys/netinet/udp_var.h b/sys/netinet/udp_var.h index e0c8b7fa03..ef41eb638a 100644 --- a/sys/netinet/udp_var.h +++ b/sys/netinet/udp_var.h @@ -149,14 +149,12 @@ int udp_addrcpu (in_addr_t faddr, in_port_t fport, in_addr_t laddr, in_port_t lport); struct lwkt_port *udp_addrport (in_addr_t faddr, in_port_t fport, in_addr_t laddr, in_port_t lport); -void udp_ctlinput (int, struct sockaddr *, void *); +void udp_ctlinput(netmsg_t msg); void udp_init (void); void udp_thread_init (void); -void udp_input (struct mbuf *, ...); +int udp_input (struct mbuf **, int *, int); void udp_notify (struct inpcb *inp, int error); -int udp_shutdown (struct socket *so); -struct lwkt_port *udp_soport (struct socket *, struct sockaddr *, - struct mbuf **); +void udp_shutdown (union netmsg *); struct lwkt_port *udp_ctlport (int, struct sockaddr *, void *); struct lwkt_port *udp_cport (int); diff --git a/sys/netinet6/ah.h b/sys/netinet6/ah.h index 7b5ea4e13e..09c65ba377 100644 --- a/sys/netinet6/ah.h +++ b/sys/netinet6/ah.h @@ -93,7 +93,7 @@ extern const struct ah_algorithm *ah_algorithm_lookup (int); extern int ah_hdrlen (struct secasvar *); extern size_t ah_hdrsiz (struct ipsecrequest *); -extern void ah4_input (struct mbuf *, ...); +extern int ah4_input (struct mbuf **, int *, int); extern int ah4_output (struct mbuf *, struct ipsecrequest *); extern int ah4_calccksum (struct mbuf *, caddr_t, size_t, const struct ah_algorithm *, struct secasvar *); diff --git a/sys/netinet6/ah_input.c b/sys/netinet6/ah_input.c index b81e32c8d7..dfc1dfa7b3 100644 --- a/sys/netinet6/ah_input.c +++ b/sys/netinet6/ah_input.c @@ -98,10 +98,11 @@ #ifdef INET extern struct protosw inetsw[]; -void -ah4_input(struct mbuf *m, ...) +int +ah4_input(struct mbuf **mp, int *offp, int proto) { - int off, proto; + int off; + struct mbuf *m; struct ip *ip; struct ah *ah; u_int32_t spi; @@ -113,12 +114,10 @@ ah4_input(struct mbuf *m, ...) u_int16_t nxt; size_t hlen; size_t stripsiz = 0; - __va_list ap; - __va_start(ap, m); - off = __va_arg(ap, int); - proto = __va_arg(ap, int); - __va_end(ap); + off = *offp; + m = *mp; + *mp = NULL; #ifndef PULLDOWN_TEST if (m->m_len < off + sizeof(struct newah)) { @@ -540,9 +539,12 @@ ah4_input(struct mbuf *m, ...) /* freed in ip_lengthcheck() */ goto fail; } - (*inetsw[ip_protox[nxt]].pr_input)(m, off, nxt); - } else + *mp = m; + *offp = off; + (*inetsw[ip_protox[nxt]].pr_input)(mp, offp, nxt); + } else { m_freem(m); + } m = NULL; } @@ -552,7 +554,7 @@ ah4_input(struct mbuf *m, ...) key_freesav(sav); } ipsecstat.in_success++; - return; + return(IPPROTO_DONE); fail: if (sav) { @@ -562,7 +564,7 @@ fail: } if (m) m_freem(m); - return; + return(IPPROTO_DONE); } #endif /* INET */ diff --git a/sys/netinet6/esp.h b/sys/netinet6/esp.h index 4305f878f9..5ea5e1e863 100644 --- a/sys/netinet6/esp.h +++ b/sys/netinet6/esp.h @@ -101,7 +101,7 @@ extern int esp_max_ivlen (void); /* crypt routines */ extern int esp4_output (struct mbuf *, struct ipsecrequest *); -extern void esp4_input(struct mbuf *, ...); +extern int esp4_input(struct mbuf **, int *, int); extern size_t esp_hdrsiz (struct ipsecrequest *); extern int esp_schedule (const struct esp_algorithm *, struct secasvar *); diff --git a/sys/netinet6/esp6.h b/sys/netinet6/esp6.h index 3b549410f6..76c1e6c763 100644 --- a/sys/netinet6/esp6.h +++ b/sys/netinet6/esp6.h @@ -47,12 +47,13 @@ struct mbuf; struct ipsecrequest; struct sockaddr; +union netmsg; extern int esp6_output (struct mbuf *, u_char *, struct mbuf *, struct ipsecrequest *); extern int esp6_input (struct mbuf **, int *, int); -extern void esp6_ctlinput (int, struct sockaddr *, void *); +extern void esp6_ctlinput (union netmsg *); #endif /*_KERNEL*/ diff --git a/sys/netinet6/esp_input.c b/sys/netinet6/esp_input.c index fa4900c634..239230426c 100644 --- a/sys/netinet6/esp_input.c +++ b/sys/netinet6/esp_input.c @@ -48,6 +48,9 @@ #include #include +#include +#include + #include #include #include @@ -100,13 +103,14 @@ #ifdef INET extern struct protosw inetsw[]; -void -esp4_input(struct mbuf *m, ...) +int +esp4_input(struct mbuf **mp, int *offp, int proto) { - int off, proto; + int off; struct ip *ip; struct esp *esp; struct esptail esptail; + struct mbuf *m; u_int32_t spi; struct secasvar *sav = NULL; size_t taillen; @@ -115,12 +119,10 @@ esp4_input(struct mbuf *m, ...) int ivlen; size_t hlen; size_t esplen; - __va_list ap; - __va_start(ap, m); - off = __va_arg(ap, int); - proto = __va_arg(ap, int); - __va_end(ap); + off = *offp; + m = *mp; + *mp = NULL; /* sanity check for alignment. */ if (off % 4 != 0 || m->m_pkthdr.len % 4 != 0) { @@ -438,9 +440,12 @@ noreplaycheck: /* freed in ip_lengthcheck() */ goto bad; } - (*inetsw[ip_protox[nxt]].pr_input)(m, off, nxt); - } else + *mp = m; + *offp = off; + (*inetsw[ip_protox[nxt]].pr_input)(mp, offp, nxt); + } else { m_freem(m); + } m = NULL; } @@ -450,7 +455,7 @@ noreplaycheck: key_freesav(sav); } ipsecstat.in_success++; - return; + return(IPPROTO_DONE); bad: if (sav) { @@ -460,7 +465,7 @@ bad: } if (m) m_freem(m); - return; + return(IPPROTO_DONE); } #endif /* INET */ @@ -870,8 +875,11 @@ bad: } void -esp6_ctlinput(int cmd, struct sockaddr *sa, void *d) +esp6_ctlinput(netmsg_t msg) { + int cmd = msg->ctlinput.nm_cmd; + struct sockaddr *sa = msg->ctlinput.nm_arg; + void *d = msg->ctlinput.nm_extra; const struct newesp *espp; struct newesp esp; struct ip6ctlparam *ip6cp = NULL, ip6cp1; @@ -883,9 +891,9 @@ esp6_ctlinput(int cmd, struct sockaddr *sa, void *d) if (sa->sa_family != AF_INET6 || sa->sa_len != sizeof(struct sockaddr_in6)) - return; + goto out; if ((unsigned)cmd >= PRC_NCMDS) - return; + goto out; /* if the parameter is from icmp6, decode it. */ if (d != NULL) { @@ -925,7 +933,7 @@ esp6_ctlinput(int cmd, struct sockaddr *sa, void *d) /* check if we can safely examine src and dst ports */ if (m->m_pkthdr.len < off + sizeof(esp)) - return; + goto out; if (m->m_len < off + sizeof(esp)) { /* @@ -971,5 +979,7 @@ esp6_ctlinput(int cmd, struct sockaddr *sa, void *d) } else { /* we normally notify any pcb here */ } +out: + lwkt_replymsg(&msg->ctlinput.base.lmsg, 0); } #endif /* INET6 */ diff --git a/sys/netinet6/icmp6.c b/sys/netinet6/icmp6.c index 9d454e6b72..ff2388b539 100644 --- a/sys/netinet6/icmp6.c +++ b/sys/netinet6/icmp6.c @@ -83,6 +83,9 @@ #include #include +#include +#include + #include #include #include @@ -146,7 +149,7 @@ #define HAVE_PPSRATECHECK extern struct domain inet6domain; -extern struct ip6protosw inet6sw[]; +extern struct protosw inet6sw[]; extern u_char ip6_protox[]; struct icmp6stat icmp6stat; @@ -2602,9 +2605,11 @@ fail: /* * ICMPv6 socket option processing. */ -int -icmp6_ctloutput(struct socket *so, struct sockopt *sopt) +void +icmp6_ctloutput(netmsg_t msg) { + struct socket *so = msg->ctloutput.base.nm_so; + struct sockopt *sopt = msg->ctloutput.nm_sopt; int error = 0; int optlen; struct inpcb *inp = so->so_pcb; @@ -2619,7 +2624,8 @@ icmp6_ctloutput(struct socket *so, struct sockopt *sopt) level = op = optname = optlen = 0; if (level != IPPROTO_ICMPV6) { - return EINVAL; + error = EINVAL; + goto out; } switch (op) { @@ -2667,8 +2673,8 @@ icmp6_ctloutput(struct socket *so, struct sockopt *sopt) } break; } - - return (error); +out: + lwkt_replymsg(&msg->ctloutput.base.lmsg, error); } #ifdef HAVE_NRL_INPCB #undef in6pcb diff --git a/sys/netinet6/in6.c b/sys/netinet6/in6.c index 7488143ac5..c1e703f378 100644 --- a/sys/netinet6/in6.c +++ b/sys/netinet6/in6.c @@ -81,7 +81,9 @@ #include #include #include + #include +#include #include #include @@ -375,6 +377,19 @@ in6_len2mask(struct in6_addr *mask, int len) #define ifa2ia6(ifa) ((struct in6_ifaddr *)(ifa)) #define ia62ifa(ia6) (&((ia6)->ia_ifa)) +void +in6_control_dispatch(netmsg_t msg) +{ + int error; + + error = in6_control(msg->control.base.nm_so, + msg->control.nm_cmd, + msg->control.nm_data, + msg->control.nm_ifp, + msg->control.nm_td); + lwkt_replymsg(&msg->control.base.lmsg, error); +} + int in6_control(struct socket *so, u_long cmd, caddr_t data, struct ifnet *ifp, struct thread *td) diff --git a/sys/netinet6/in6_gif.c b/sys/netinet6/in6_gif.c index 0c1c0d94c1..8881552391 100644 --- a/sys/netinet6/in6_gif.c +++ b/sys/netinet6/in6_gif.c @@ -76,18 +76,26 @@ static int gif_validate6(const struct ip6_hdr *, struct gif_softc *, struct ifnet *); extern struct domain inet6domain; -struct ip6protosw in6_gif_protosw = -{ SOCK_RAW, &inet6domain, 0/*IPPROTO_IPV[46]*/, PR_ATOMIC|PR_ADDR, - in6_gif_input, rip6_output, 0, rip6_ctloutput, - cpu0_soport, NULL, - 0, 0, 0, 0, - &rip6_usrreqs -}; +struct protosw in6_gif_protosw = + { + .pr_type = SOCK_RAW, + .pr_domain = &inet6domain, + .pr_protocol = 0/*IPPROTO_IPV[46]*/, + .pr_flags = PR_ATOMIC|PR_ADDR, + .pr_input = in6_gif_input, + .pr_output = rip6_output, + .pr_ctlinput = NULL, + .pr_ctloutput = rip6_ctloutput, + + .pr_usrreqs = &rip6_usrreqs + }; + +/* + * family = family of the packet to be encapsulate. + */ int -in6_gif_output(struct ifnet *ifp, - int family, /* family of the packet to be encapsulate. */ - struct mbuf *m) +in6_gif_output(struct ifnet *ifp, int family, struct mbuf *m) { struct gif_softc *sc = (struct gif_softc*)ifp; struct sockaddr_in6 *dst = (struct sockaddr_in6 *)&sc->gif_ro6.ro_dst; diff --git a/sys/netinet6/in6_pcb.c b/sys/netinet6/in6_pcb.c index c78d7171d6..b353fb5e16 100644 --- a/sys/netinet6/in6_pcb.c +++ b/sys/netinet6/in6_pcb.c @@ -85,7 +85,9 @@ #include #include #include + #include +#include #include @@ -713,6 +715,15 @@ in6_pcbdetach(struct inpcb *inp) * (or in this case trap) if the PCB is invalid. (Actually, we don't trap * because there actually /is/ a programming error somewhere... XXX) */ +void +in6_setsockaddr_dispatch(netmsg_t msg) +{ + int error; + + error = in6_setsockaddr(msg->sockaddr.base.nm_so, msg->sockaddr.nm_nam); + lwkt_replymsg(&msg->sockaddr.base.lmsg, error); +} + int in6_setsockaddr(struct socket *so, struct sockaddr **nam) { @@ -748,6 +759,15 @@ in6_setsockaddr(struct socket *so, struct sockaddr **nam) return 0; } +void +in6_setpeeraddr_dispatch(netmsg_t msg) +{ + int error; + + error = in6_setpeeraddr(msg->peeraddr.base.nm_so, msg->peeraddr.nm_nam); + lwkt_replymsg(&msg->peeraddr.base.lmsg, error); +} + int in6_setpeeraddr(struct socket *so, struct sockaddr **nam) { @@ -783,6 +803,16 @@ in6_setpeeraddr(struct socket *so, struct sockaddr **nam) return 0; } +void +in6_mapped_sockaddr_dispatch(netmsg_t msg) +{ + int error; + + error = in6_mapped_sockaddr(msg->sockaddr.base.nm_so, + msg->sockaddr.nm_nam); + lwkt_replymsg(&msg->sockaddr.base.lmsg, error); +} + int in6_mapped_sockaddr(struct socket *so, struct sockaddr **nam) { @@ -821,6 +851,15 @@ in6_mapped_peeraddr(struct socket *so, struct sockaddr **nam) return error; } +void +in6_mapped_peeraddr_dispatch(netmsg_t msg) +{ + int error; + + error = in6_mapped_peeraddr(msg->base.nm_so, msg->peeraddr.nm_nam); + lwkt_replymsg(&msg->base.lmsg, error); +} + /* * Pass some notification to all connections of a protocol * associated with address dst. The local address and/or port numbers diff --git a/sys/netinet6/in6_pcb.h b/sys/netinet6/in6_pcb.h index 1608117ad5..75ba325a28 100644 --- a/sys/netinet6/in6_pcb.h +++ b/sys/netinet6/in6_pcb.h @@ -94,6 +94,7 @@ struct ip6_pktopts; struct in6_addr; struct route_in6; struct sockaddr_in6; +union netmsg; void in6_pcbpurgeif0 (struct in6pcb *, struct ifnet *); void in6_losing (struct inpcb *); @@ -115,10 +116,14 @@ void in6_pcbnotify (struct inpcbhead *, struct sockaddr *, in_port_t, const struct sockaddr *, in_port_t, int, int, void (*)(struct inpcb *, int)); void in6_rtchange (struct inpcb *, int); +void in6_setpeeraddr_dispatch (union netmsg *); +void in6_setsockaddr_dispatch (union netmsg *); int in6_setpeeraddr (struct socket *so, struct sockaddr **nam); int in6_setsockaddr (struct socket *so, struct sockaddr **nam); +void in6_mapped_sockaddr_dispatch(union netmsg *msg); int in6_mapped_sockaddr (struct socket *so, struct sockaddr **nam); int in6_mapped_peeraddr (struct socket *so, struct sockaddr **nam); +void in6_mapped_peeraddr_dispatch(netmsg_t msg); struct in6_addr *in6_selectsrc (struct sockaddr_in6 *, struct ip6_pktopts *, struct ip6_moptions *, diff --git a/sys/netinet6/in6_proto.c b/sys/netinet6/in6_proto.c index badf0f7f87..2e908baf19 100644 --- a/sys/netinet6/in6_proto.c +++ b/sys/netinet6/in6_proto.c @@ -156,122 +156,240 @@ static struct pr_usrreqs nousrreqs; #define PR_LISTEN 0 #define PR_ABRTACPTDIS 0 -struct ip6protosw inet6sw[] = { -{ 0, &inet6domain, IPPROTO_IPV6, 0, - 0, 0, 0, 0, - cpu0_soport, NULL, - ip6_init, 0, frag6_slowtimo, frag6_drain, - &nousrreqs, -}, -{ SOCK_DGRAM, &inet6domain, IPPROTO_UDP, PR_ATOMIC | PR_ADDR | - PR_MPSAFE | PR_LASTHDR, - udp6_input, 0, udp6_ctlinput, ip6_ctloutput, - cpu0_soport, cpu0_ctlport, - 0, 0, 0, 0, - &udp6_usrreqs, -}, -{ SOCK_STREAM, &inet6domain, IPPROTO_TCP, PR_CONNREQUIRED | - PR_WANTRCVD | PR_LISTEN | - PR_MPSAFE | PR_LASTHDR, - tcp6_input, 0, tcp6_ctlinput, tcp_ctloutput, - tcp6_soport, cpu0_ctlport, -#ifdef INET /* don't call initialization and timeout routines twice */ - 0, 0, 0, tcp_drain, -#else - tcp_init, tcp_fasttimo, tcp_slowtimo, tcp_drain, +struct protosw inet6sw[] = { + { + .pr_type = 0, + .pr_domain = &inet6domain, + .pr_protocol = IPPROTO_IPV6, + .pr_flags = 0, + + .pr_init = ip6_init, + .pr_fasttimo = NULL, + .pr_slowtimo = frag6_slowtimo, + .pr_drain = frag6_drain, + .pr_usrreqs = &nousrreqs + }, + { + .pr_type = SOCK_DGRAM, + .pr_domain = &inet6domain, + .pr_protocol = IPPROTO_UDP, + .pr_flags = PR_ATOMIC | PR_ADDR | PR_MPSAFE | PR_LASTHDR, + + .pr_input = udp6_input, + .pr_output = 0, + .pr_ctlinput = udp6_ctlinput, + .pr_ctloutput = ip6_ctloutput_dispatch, + + .pr_ctlport = cpu0_ctlport, + .pr_usrreqs = &udp6_usrreqs + }, + { + .pr_type = SOCK_STREAM, + .pr_domain = &inet6domain, + .pr_protocol = IPPROTO_TCP, + .pr_flags = PR_CONNREQUIRED | PR_WANTRCVD | PR_LISTEN | + PR_MPSAFE | PR_LASTHDR, + + .pr_input = tcp6_input, + .pr_output = NULL, + .pr_ctlinput = tcp6_ctlinput, + .pr_ctloutput = tcp_ctloutput, + + .pr_ctlport = cpu0_ctlport, +#ifndef INET + /* don't call initialization and timeout routines twice */ + .pr_init = tcp_init, + .pr_fasttimo = tcp_fasttimo, + .pr_slowtimo = tcp_slowtimo, #endif - &tcp6_usrreqs, -}, -{ SOCK_RAW, &inet6domain, IPPROTO_RAW, PR_ATOMIC|PR_ADDR|PR_LASTHDR, - rip6_input, rip6_output, rip6_ctlinput, rip6_ctloutput, - cpu0_soport, cpu0_ctlport, - 0, 0, 0, 0, - &rip6_usrreqs -}, -{ SOCK_RAW, &inet6domain, IPPROTO_ICMPV6, PR_ATOMIC|PR_ADDR|PR_LASTHDR, - icmp6_input, rip6_output, rip6_ctlinput, rip6_ctloutput, - cpu0_soport, cpu0_ctlport, - icmp6_init, icmp6_fasttimo, 0, 0, - &rip6_usrreqs -}, -{ SOCK_RAW, &inet6domain, IPPROTO_DSTOPTS, PR_ATOMIC|PR_ADDR, - dest6_input, 0, 0, 0, - cpu0_soport, NULL, - 0, 0, 0, 0, - &nousrreqs -}, -{ SOCK_RAW, &inet6domain, IPPROTO_ROUTING, PR_ATOMIC|PR_ADDR, - route6_input, 0, 0, 0, - cpu0_soport, NULL, - 0, 0, 0, 0, - &nousrreqs -}, -{ SOCK_RAW, &inet6domain, IPPROTO_FRAGMENT, PR_ATOMIC|PR_ADDR, - frag6_input, 0, 0, 0, - cpu0_soport, NULL, - 0, 0, 0, 0, - &nousrreqs -}, + .pr_drain = tcp_drain, + .pr_usrreqs = &tcp6_usrreqs + }, + { + .pr_type = SOCK_RAW, + .pr_domain = &inet6domain, + .pr_protocol = IPPROTO_RAW, + .pr_flags = PR_ATOMIC|PR_ADDR|PR_LASTHDR, + + .pr_input = rip6_input, + .pr_output = rip6_output, + .pr_ctlinput = rip6_ctlinput, + .pr_ctloutput = rip6_ctloutput, + + .pr_ctlport = cpu0_ctlport, + .pr_usrreqs = &rip6_usrreqs + }, + { + .pr_type = SOCK_RAW, + .pr_domain = &inet6domain, + .pr_protocol = IPPROTO_ICMPV6, + .pr_flags = PR_ATOMIC|PR_ADDR|PR_LASTHDR, + + .pr_input = icmp6_input, + .pr_output = rip6_output, + .pr_ctlinput = rip6_ctlinput, + .pr_ctloutput = rip6_ctloutput, + + .pr_ctlport = cpu0_ctlport, + .pr_init = icmp6_init, + .pr_fasttimo = icmp6_fasttimo, + .pr_slowtimo = NULL, + .pr_drain = NULL, + + .pr_usrreqs = &rip6_usrreqs + }, + { + .pr_type = SOCK_RAW, + .pr_domain = &inet6domain, + .pr_protocol = IPPROTO_DSTOPTS, PR_ATOMIC|PR_ADDR, + + .pr_input = dest6_input, + .pr_output = NULL, + .pr_ctlinput = NULL, + .pr_ctloutput = NULL, + + .pr_usrreqs = &nousrreqs + }, + { + .pr_type = SOCK_RAW, + .pr_domain = &inet6domain, + .pr_protocol = IPPROTO_ROUTING, PR_ATOMIC|PR_ADDR, + + .pr_input = route6_input, + .pr_output = NULL, + .pr_ctlinput = NULL, + .pr_ctloutput = NULL, + + .pr_usrreqs = &nousrreqs + }, + { + .pr_type = SOCK_RAW, + .pr_domain = &inet6domain, + .pr_protocol = IPPROTO_FRAGMENT, PR_ATOMIC|PR_ADDR, + + .pr_input = frag6_input, + .pr_output = NULL, + .pr_ctlinput = NULL, + .pr_ctloutput = NULL, + + .pr_usrreqs = &nousrreqs + }, #ifdef IPSEC -{ SOCK_RAW, &inet6domain, IPPROTO_AH, PR_ATOMIC|PR_ADDR, - ah6_input, 0, 0, 0, - cpu0_soport, NULL, - 0, 0, 0, 0, - &nousrreqs, -}, + { + .pr_type = SOCK_RAW, + .pr_domain = &inet6domain, + .pr_protocol = IPPROTO_AH, + .pr_flags = PR_ATOMIC|PR_ADDR, + + .pr_input = ah6_input, + .pr_output = NULL, + .pr_ctlinput = NULL, + .pr_ctloutput = NULL, + + .pr_usrreqs = &nousrreqs + }, #ifdef IPSEC_ESP -{ SOCK_RAW, &inet6domain, IPPROTO_ESP, PR_ATOMIC|PR_ADDR, - esp6_input, 0, - esp6_ctlinput, - 0, - cpu0_soport, NULL, - 0, 0, 0, 0, - &nousrreqs, -}, + { + .pr_type = SOCK_RAW, + .pr_domain = &inet6domain, + .pr_protocol = IPPROTO_ESP, + .pr_flags = PR_ATOMIC|PR_ADDR, + + .pr_input = esp6_input, + .pr_output = NULL, + .pr_ctlinput = esp6_ctlinput, + .pr_ctloutput = NULL, + + .pr_usrreqs = &nousrreqs + }, #endif -{ SOCK_RAW, &inet6domain, IPPROTO_IPCOMP, PR_ATOMIC|PR_ADDR, - ipcomp6_input, 0, 0, 0, - cpu0_soport, NULL, - 0, 0, 0, 0, - &nousrreqs, -}, + { + .pr_type = SOCK_RAW, + .pr_domain = &inet6domain, + .pr_protocol = IPPROTO_IPCOMP, + .pr_flags = PR_ATOMIC|PR_ADDR, + + .pr_input = ipcomp6_input, + .pr_output = NULL, + .pr_ctlinput = NULL, + .pr_ctloutput = NULL, + + .pr_usrreqs = &nousrreqs + }, #endif /* IPSEC */ #ifdef INET -{ SOCK_RAW, &inet6domain, IPPROTO_IPV4, PR_ATOMIC|PR_ADDR|PR_LASTHDR, - encap6_input, rip6_output, 0, rip6_ctloutput, - cpu0_soport, NULL, - encap_init, 0, 0, 0, - &rip6_usrreqs -}, + { + .pr_type = SOCK_RAW, + .pr_domain = &inet6domain, + .pr_protocol = IPPROTO_IPV4, + .pr_flags = PR_ATOMIC|PR_ADDR|PR_LASTHDR, + + .pr_input = encap6_input, + .pr_output = rip6_output, + .pr_ctlinput = NULL, + .pr_ctloutput = rip6_ctloutput, + + .pr_init = encap_init, + .pr_usrreqs = &rip6_usrreqs + }, #endif /* INET */ -{ SOCK_RAW, &inet6domain, IPPROTO_IPV6, PR_ATOMIC|PR_ADDR|PR_LASTHDR, - encap6_input, rip6_output, 0, rip6_ctloutput, - cpu0_soport, NULL, - encap_init, 0, 0, 0, - &rip6_usrreqs -}, -{ SOCK_RAW, &inet6domain, IPPROTO_PIM, PR_ATOMIC|PR_ADDR|PR_LASTHDR, - pim6_input, rip6_output, 0, rip6_ctloutput, - cpu0_soport, NULL, - 0, 0, 0, 0, - &rip6_usrreqs -}, + { + .pr_type = SOCK_RAW, + .pr_domain = &inet6domain, + .pr_protocol = IPPROTO_IPV6, + .pr_flags = PR_ATOMIC|PR_ADDR|PR_LASTHDR, + + .pr_input = encap6_input, + .pr_output = rip6_output, + .pr_ctlinput = NULL, + .pr_ctloutput = rip6_ctloutput, + + .pr_init = encap_init, + .pr_usrreqs = &rip6_usrreqs + }, + { + .pr_type = SOCK_RAW, + .pr_domain = &inet6domain, + .pr_protocol = IPPROTO_PIM, + .pr_flags = PR_ATOMIC|PR_ADDR|PR_LASTHDR, + + .pr_input = pim6_input, + .pr_output = rip6_output, + .pr_ctlinput = NULL, + .pr_ctloutput = rip6_ctloutput, + + .pr_usrreqs = &rip6_usrreqs + }, #ifdef CARP -{ SOCK_RAW, &inet6domain, IPPROTO_CARP, PR_ATOMIC|PR_ADDR, - carp6_input, rip6_output, 0, rip6_ctloutput, - cpu0_soport, NULL, - 0, 0, 0, 0, - &rip6_usrreqs -}, + { + .pr_type = SOCK_RAW, + .pr_domain = &inet6domain, + .pr_protocol = IPPROTO_CARP, + .pr_flags = PR_ATOMIC|PR_ADDR, + + .pr_input = carp6_input, + .pr_output = rip6_output, + .pr_ctlinput = NULL, + .pr_ctloutput = rip6_ctloutput, + + .pr_usrreqs = &rip6_usrreqs + }, #endif /* CARP */ -/* raw wildcard */ -{ SOCK_RAW, &inet6domain, 0, PR_ATOMIC|PR_ADDR, - rip6_input, rip6_output, 0, rip6_ctloutput, - cpu0_soport, NULL, - 0, 0, 0, 0, - &rip6_usrreqs -}, + /* raw wildcard */ + { + .pr_type = SOCK_RAW, + .pr_domain = &inet6domain, + .pr_protocol = 0, + .pr_flags = PR_ATOMIC|PR_ADDR, + + .pr_input = rip6_input, + .pr_output = rip6_output, + .pr_ctlinput = NULL, + .pr_ctloutput = rip6_ctloutput, + + .pr_usrreqs = &rip6_usrreqs + }, }; extern int in6_inithead (void **, int); diff --git a/sys/netinet6/in6_var.h b/sys/netinet6/in6_var.h index af120acb0f..e5d799cdcf 100644 --- a/sys/netinet6/in6_var.h +++ b/sys/netinet6/in6_var.h @@ -605,10 +605,11 @@ int in6_leavegroup(struct in6_multi_mship *); extern int in6_ifindex2scopeid (int); extern int in6_mask2len (struct in6_addr *, u_char *); extern void in6_len2mask (struct in6_addr *, int); +void in6_control_dispatch(netmsg_t msg); int in6_control (struct socket *, - u_long, caddr_t, struct ifnet *, struct thread *); + u_long, caddr_t, struct ifnet *, struct thread *); int in6_update_ifa (struct ifnet *, struct in6_aliasreq *, - struct in6_ifaddr *); + struct in6_ifaddr *); void in6_purgeaddr (struct ifaddr *); int in6if_do_dad (struct ifnet *); void in6_purgeif (struct ifnet *); diff --git a/sys/netinet6/ip6_input.c b/sys/netinet6/ip6_input.c index d240870fb6..292ae5b9f8 100644 --- a/sys/netinet6/ip6_input.c +++ b/sys/netinet6/ip6_input.c @@ -136,7 +136,7 @@ #include extern struct domain inet6domain; -extern struct ip6protosw inet6sw[]; +extern struct protosw inet6sw[]; u_char ip6_protox[IPPROTO_MAX]; struct in6_ifaddr *in6_ifaddr; @@ -161,7 +161,7 @@ struct ip6stat ip6stat; static void ip6_init2 (void *); static struct ip6aux *ip6_setdstifaddr (struct mbuf *, struct in6_ifaddr *); static int ip6_hopopts_input (u_int32_t *, u_int32_t *, struct mbuf **, int *); -static void ip6_input(struct netmsg *msg); +static void ip6_input(netmsg_t msg); #ifdef PULLDOWN_TEST static struct mbuf *ip6_pullexthdr (struct mbuf *, size_t, int); #endif @@ -174,21 +174,17 @@ static void transport6_processing_handler(netmsg_t netmsg); void ip6_init(void) { - struct ip6protosw *pr; + struct protosw *pr; int i; struct timeval tv; -#ifdef DIAGNOSTIC - if (sizeof(struct protosw) != sizeof(struct ip6protosw)) - panic("sizeof(protosw) != sizeof(ip6protosw)"); -#endif - pr = (struct ip6protosw *)pffindproto(PF_INET6, IPPROTO_RAW, SOCK_RAW); + pr = pffindproto(PF_INET6, IPPROTO_RAW, SOCK_RAW); if (pr == 0) panic("ip6_init"); for (i = 0; i < IPPROTO_MAX; i++) ip6_protox[i] = pr - inet6sw; - for (pr = (struct ip6protosw *)inet6domain.dom_protosw; - pr < (struct ip6protosw *)inet6domain.dom_protoswNPROTOSW; pr++) + for (pr = inet6domain.dom_protosw; + pr < inet6domain.dom_protoswNPROTOSW; pr++) if (pr->pr_domain->dom_family == PF_INET6 && pr->pr_protocol && pr->pr_protocol != IPPROTO_RAW) ip6_protox[pr->pr_protocol] = pr - inet6sw; @@ -242,9 +238,9 @@ extern struct route_in6 ip6_forward_rt; static void -ip6_input(struct netmsg *msg) +ip6_input(netmsg_t msg) { - struct mbuf *m = ((struct netmsg_packet *)msg)->nm_packet; + struct mbuf *m = msg->packet.nm_packet; struct ip6_hdr *ip6; int off = sizeof(struct ip6_hdr), nest; u_int32_t plen; @@ -797,7 +793,7 @@ hbhcheck: rh_present = 0; while (nxt != IPPROTO_DONE) { - struct ip6protosw *sw6; + struct protosw *sw6; if (ip6_hdrnestlimit && (++nest > ip6_hdrnestlimit)) { ip6stat.ip6s_toomanyhdr++; @@ -860,16 +856,16 @@ hbhcheck: struct netmsg_packet *pmsg; lwkt_port_t port; - port = sw6->pr_soport(NULL, NULL, &m); + port = cpu_portfn(0); /* XXX */ KKASSERT(port != NULL); pmsg = &m->m_hdr.mh_netmsg; - netmsg_init(&pmsg->nm_netmsg, NULL, + netmsg_init(&pmsg->base, NULL, &netisr_apanic_rport, 0, transport6_processing_handler); pmsg->nm_packet = m; pmsg->nm_nxt = nxt; - pmsg->nm_netmsg.nm_lmsg.u.ms_result = off; - lwkt_sendmsg(port, &pmsg->nm_netmsg.nm_lmsg); + pmsg->base.lmsg.u.ms_result = off; + lwkt_sendmsg(port, &pmsg->base.lmsg); /* done with m */ nxt = IPPROTO_DONE; } else { @@ -894,12 +890,12 @@ static void transport6_processing_handler(netmsg_t netmsg) { struct netmsg_packet *pmsg = (struct netmsg_packet *)netmsg; - struct ip6protosw *sw6; + struct protosw *sw6; int hlen; int nxt; sw6 = &inet6sw[ip6_protox[pmsg->nm_nxt]]; - hlen = pmsg->nm_netmsg.nm_lmsg.u.ms_result; + hlen = pmsg->base.lmsg.u.ms_result; nxt = sw6->pr_input(&pmsg->nm_packet, &hlen, pmsg->nm_nxt); KKASSERT(nxt == IPPROTO_DONE); diff --git a/sys/netinet6/ip6_output.c b/sys/netinet6/ip6_output.c index 381d7b7215..c7b0e81a75 100644 --- a/sys/netinet6/ip6_output.c +++ b/sys/netinet6/ip6_output.c @@ -83,6 +83,9 @@ #include #include +#include +#include + #include #include #include @@ -1370,6 +1373,16 @@ ip6_getpmtu(struct route_in6 *ro_pmtu, struct route_in6 *ro, /* * IP6 socket option processing. */ +void +ip6_ctloutput_dispatch(netmsg_t msg) +{ + int error; + + error = ip6_ctloutput(msg->ctloutput.base.nm_so, + msg->ctloutput.nm_sopt); + lwkt_replymsg(&msg->ctloutput.base.lmsg, error); +} + int ip6_ctloutput(struct socket *so, struct sockopt *sopt) { diff --git a/sys/netinet6/ip6_var.h b/sys/netinet6/ip6_var.h index adb2e71473..58d7773c23 100644 --- a/sys/netinet6/ip6_var.h +++ b/sys/netinet6/ip6_var.h @@ -338,9 +338,9 @@ struct inpcb; struct sockopt; struct in6_ifaddr; struct ip6_hdr; -struct netmsg; +union netmsg; -int icmp6_ctloutput (struct socket *, struct sockopt *sopt); +void icmp6_ctloutput (union netmsg *); void ip6_init (void); void ip6intr (void); @@ -373,6 +373,7 @@ int ip6_output (struct mbuf *, struct ip6_pktopts *, int, struct ip6_moptions *, struct ifnet **, struct inpcb *); +void ip6_ctloutput_dispatch(netmsg_t msg); int ip6_ctloutput (struct socket *, struct sockopt *sopt); int ip6_raw_ctloutput (struct socket *, struct sockopt *); void init_ip6pktopts (struct ip6_pktopts *); @@ -392,8 +393,8 @@ void frag6_drain (void); void rip6_init (void); int rip6_input (struct mbuf **mp, int *offp, int proto); -void rip6_ctlinput (int, struct sockaddr *, void *); -int rip6_ctloutput (struct socket *so, struct sockopt *sopt); +void rip6_ctlinput (union netmsg *); +void rip6_ctloutput (union netmsg *); int rip6_output (struct mbuf *, struct socket *, ...); int rip6_usrreq (struct socket *, int, struct mbuf *, struct mbuf *, struct mbuf *, struct proc *); diff --git a/sys/netinet6/ip6protosw.h b/sys/netinet6/ip6protosw.h index 350eb1a5cd..3f0925b704 100644 --- a/sys/netinet6/ip6protosw.h +++ b/sys/netinet6/ip6protosw.h @@ -1,7 +1,3 @@ -/* $FreeBSD: src/sys/netinet6/ip6protosw.h,v 1.2.2.4 2002/04/28 05:40:27 suz Exp $ */ -/* $DragonFly: src/sys/netinet6/ip6protosw.h,v 1.9 2008/10/27 02:56:30 sephe Exp $ */ -/* $KAME: ip6protosw.h,v 1.25 2001/09/26 06:13:03 keiichi Exp $ */ - /* * Copyright (C) 1995, 1996, 1997, and 1998 WIDE Project. * All rights reserved. @@ -30,6 +26,9 @@ * OUT OF THE USE OF THIS SOFTWARE, EVEN IF ADVISED OF THE POSSIBILITY OF * SUCH DAMAGE. * + * $FreeBSD: src/sys/netinet6/ip6protosw.h,v 1.2.2.4 2002/04/28 05:40:27 suz Exp $ + * $DragonFly: src/sys/netinet6/ip6protosw.h,v 1.9 2008/10/27 02:56:30 sephe Exp $ + * $KAME: ip6protosw.h,v 1.25 2001/09/26 06:13:03 keiichi Exp $ */ /* BSDI protosw.h,v 2.3 1996/10/11 16:02:40 pjd Exp */ @@ -122,41 +121,4 @@ struct ip6ctlparam { u_int8_t ip6c_nxt; /* final next header field */ }; -struct lwkt_port; - -struct ip6protosw { - short pr_type; /* socket type used for */ - const struct domain *pr_domain; /* domain protocol a member of */ - short pr_protocol; /* protocol number */ - short pr_flags; /* see below */ - -/* protocol-protocol hooks */ - int (*pr_input) /* input to protocol (from below) */ - (struct mbuf **, int *, int); - int (*pr_output) /* output to protocol (from above) */ - (struct mbuf *, struct socket *, ...); - void (*pr_ctlinput) /* control input (from below) */ - (int, struct sockaddr *, void *); - int (*pr_ctloutput) /* control output (from above) */ - (struct socket *, struct sockopt *); - -/* user-protocol hook */ - struct lwkt_port *(*pr_soport) - (struct socket *, struct sockaddr *, - struct mbuf **); - struct lwkt_port *(*pr_ctlport)(int, struct sockaddr *, void *); - -/* utility hooks */ - void (*pr_init) /* initialization hook */ - (void); - - void (*pr_fasttimo) /* fast timeout (200ms) */ - (void); - void (*pr_slowtimo) /* slow timeout (500ms) */ - (void); - void (*pr_drain) /* flush any excess space possible */ - (void); - const struct pr_usrreqs *pr_usrreqs; /* supersedes pr_usrreq() */ -}; - #endif /* !_NETINET6_IP6PROTOSW_H_ */ diff --git a/sys/netinet6/ipcomp.h b/sys/netinet6/ipcomp.h index adddc62963..aef645841f 100644 --- a/sys/netinet6/ipcomp.h +++ b/sys/netinet6/ipcomp.h @@ -72,7 +72,7 @@ struct ipcomp_algorithm { }; extern const struct ipcomp_algorithm *ipcomp_algorithm_lookup (int); -extern void ipcomp4_input (struct mbuf *, ...); +extern int ipcomp4_input (struct mbuf **, int *, int); extern int ipcomp4_output (struct mbuf *, struct ipsecrequest *); #endif /* KERNEL */ diff --git a/sys/netinet6/ipcomp_input.c b/sys/netinet6/ipcomp_input.c index effb97cb29..20778172f0 100644 --- a/sys/netinet6/ipcomp_input.c +++ b/sys/netinet6/ipcomp_input.c @@ -86,11 +86,12 @@ #ifdef INET extern struct protosw inetsw[]; -void -ipcomp4_input(struct mbuf *m, ...) +int +ipcomp4_input(struct mbuf **mp, int *offp, int proto) { - int off, proto; + int off; struct mbuf *md; + struct mbuf *m; struct ip *ip; struct ipcomp *ipcomp; const struct ipcomp_algorithm *algo; @@ -100,12 +101,10 @@ ipcomp4_input(struct mbuf *m, ...) int error; size_t newlen, olen; struct secasvar *sav = NULL; - __va_list ap; - __va_start(ap, m); - off = __va_arg(ap, int); - proto = __va_arg(ap, int); - __va_end(ap); + off = *offp; + m = *mp; + *mp = NULL; if (m->m_pkthdr.len < off + sizeof(struct ipcomp)) { ipseclog((LOG_DEBUG, "IPv4 IPComp input: assumption failed " @@ -225,20 +224,23 @@ ipcomp4_input(struct mbuf *m, ...) ipsecstat.in_polvio++; goto fail; } - (*inetsw[ip_protox[nxt]].pr_input)(m, off, nxt); - } else + *mp = m; + *offp = off; + (*inetsw[ip_protox[nxt]].pr_input)(mp, offp, nxt); + } else { m_freem(m); + } m = NULL; ipsecstat.in_success++; - return; + return(IPPROTO_DONE); fail: if (sav) key_freesav(sav); if (m) m_freem(m); - return; + return(IPPROTO_DONE); } #endif /* INET */ diff --git a/sys/netinet6/raw_ip6.c b/sys/netinet6/raw_ip6.c index c795a9e502..713ad47d19 100644 --- a/sys/netinet6/raw_ip6.c +++ b/sys/netinet6/raw_ip6.c @@ -82,6 +82,7 @@ #include #include +#include #include #include @@ -270,8 +271,11 @@ rip6_input(struct mbuf **mp, int *offp, int proto) } void -rip6_ctlinput(int cmd, struct sockaddr *sa, void *d) +rip6_ctlinput(netmsg_t msg) { + int cmd = msg->ctlinput.nm_cmd; + struct sockaddr *sa = msg->ctlinput.nm_arg; + void *d = msg->ctlinput.nm_extra; struct ip6_hdr *ip6; struct mbuf *m; int off = 0; @@ -281,16 +285,16 @@ rip6_ctlinput(int cmd, struct sockaddr *sa, void *d) if (sa->sa_family != AF_INET6 || sa->sa_len != sizeof(struct sockaddr_in6)) - return; + goto out; if ((unsigned)cmd >= PRC_NCMDS) - return; + goto out; if (PRC_IS_REDIRECT(cmd)) notify = in6_rtchange, d = NULL; else if (cmd == PRC_HOSTDEAD) d = NULL; else if (inet6ctlerrmap[cmd] == 0) - return; + goto out; /* if the parameter is from icmp6, decode it. */ if (d != NULL) { @@ -307,6 +311,8 @@ rip6_ctlinput(int cmd, struct sockaddr *sa, void *d) in6_pcbnotify(&ripcbinfo.pcblisthead, sa, 0, (const struct sockaddr *)sa6_src, 0, cmd, 0, notify); +out: + lwkt_replymsg(&msg->ctlinput.base.lmsg, 0); } /* @@ -491,19 +497,26 @@ freectl: /* * Raw IPv6 socket option processing. */ -int -rip6_ctloutput(struct socket *so, struct sockopt *sopt) +void +rip6_ctloutput(netmsg_t msg) { + struct socket *so = msg->ctloutput.base.nm_so;; + struct sockopt *sopt = msg->ctloutput.nm_sopt; int error; - if (sopt->sopt_level == IPPROTO_ICMPV6) + if (sopt->sopt_level == IPPROTO_ICMPV6) { /* * XXX: is it better to call icmp6_ctloutput() directly * from protosw? */ - return (icmp6_ctloutput(so, sopt)); - else if (sopt->sopt_level != IPPROTO_IPV6) - return (EINVAL); + icmp6_ctloutput(msg); + /* msg invalid now */ + return; + } + if (sopt->sopt_level != IPPROTO_IPV6) { + error = EINVAL; + goto out; + } error = 0; @@ -548,13 +561,16 @@ rip6_ctloutput(struct socket *so, struct sockopt *sopt) } break; } - - return (error); +out: + lwkt_replymsg(&msg->ctloutput.base.lmsg, error); } -static int -rip6_attach(struct socket *so, int proto, struct pru_attach_info *ai) +static void +rip6_attach(netmsg_t msg) { + struct socket *so = msg->attach.base.nm_so; + int proto = msg->attach.nm_proto; + struct pru_attach_info *ai = msg->attach.nm_ai; struct inpcb *inp; int error; @@ -563,16 +579,16 @@ rip6_attach(struct socket *so, int proto, struct pru_attach_info *ai) panic("rip6_attach"); error = priv_check_cred(ai->p_ucred, PRIV_NETINET_RAW, NULL_CRED_OKAY); if (error) - return error; + goto out; error = soreserve(so, rip_sendspace, rip_recvspace, ai->sb_rlimit); if (error) - return error; + goto out; crit_enter(); error = in_pcballoc(so, &ripcbinfo); crit_exit(); if (error) - return error; + goto out; inp = (struct inpcb *)so->so_pcb; inp->inp_vflag |= INP_IPV6; inp->in6p_ip6_nxt = (long)proto; @@ -582,12 +598,15 @@ rip6_attach(struct socket *so, int proto, struct pru_attach_info *ai) sizeof(struct icmp6_filter), M_PCB, M_NOWAIT); if (inp->in6p_icmp6filt != NULL) ICMP6_FILTER_SETPASSALL(inp->in6p_icmp6filt); - return 0; + error = 0; +out: + lwkt_replymsg(&msg->attach.base.lmsg, error); } -static int -rip6_detach(struct socket *so) +static void +rip6_detach(netmsg_t msg) { + struct socket *so = msg->detach.base.nm_so; struct inpcb *inp; inp = so->so_pcb; @@ -601,73 +620,85 @@ rip6_detach(struct socket *so) inp->in6p_icmp6filt = NULL; } in6_pcbdetach(inp); - return 0; + lwkt_replymsg(&msg->detach.base.lmsg, 0); } /* * NOTE: (so) is referenced from soabort*() and netmsg_pru_abort() * will sofree() it when we return. */ -static int -rip6_abort(struct socket *so) +static void +rip6_abort(netmsg_t msg) { - int error; - - soisdisconnected(so); - error = rip6_detach(so); - - return error; + soisdisconnected(msg->abort.base.nm_so); + rip6_detach(msg); + /* msg invalid now */ } -static int -rip6_disconnect(struct socket *so) +static void +rip6_disconnect(netmsg_t msg) { + struct socket *so = msg->disconnect.base.nm_so; struct inpcb *inp = so->so_pcb; - int error; - if (!(so->so_state & SS_ISCONNECTED)) - return ENOTCONN; - inp->in6p_faddr = kin6addr_any; - soreference(so); - error = rip6_abort(so); - sofree(so); - - return error; + if (so->so_state & SS_ISCONNECTED) { + inp->in6p_faddr = kin6addr_any; + soreference(so); + rip6_abort(msg); + /* msg invalid now */ + sofree(so); + return; + } + lwkt_replymsg(&msg->disconnect.base.lmsg, ENOTCONN); } -static int -rip6_bind(struct socket *so, struct sockaddr *nam, struct thread *td) +static void +rip6_bind(netmsg_t msg) { + struct socket *so = msg->bind.base.nm_so; + struct sockaddr *nam = msg->bind.nm_nam; struct inpcb *inp = so->so_pcb; struct sockaddr_in6 *addr = (struct sockaddr_in6 *)nam; struct ifaddr *ia = NULL; + int error; - if (nam->sa_len != sizeof(*addr)) - return EINVAL; + if (nam->sa_len != sizeof(*addr)) { + error = EINVAL; + goto out; + } - if (TAILQ_EMPTY(&ifnet) || addr->sin6_family != AF_INET6) - return EADDRNOTAVAIL; + if (TAILQ_EMPTY(&ifnet) || addr->sin6_family != AF_INET6) { + error = EADDRNOTAVAIL; + goto out; + } #ifdef ENABLE_DEFAULT_SCOPE if (addr->sin6_scope_id == 0) { /* not change if specified */ addr->sin6_scope_id = scope6_addr2default(&addr->sin6_addr); } #endif if (!IN6_IS_ADDR_UNSPECIFIED(&addr->sin6_addr) && - (ia = ifa_ifwithaddr((struct sockaddr *)addr)) == NULL) - return EADDRNOTAVAIL; + (ia = ifa_ifwithaddr((struct sockaddr *)addr)) == NULL) { + error = EADDRNOTAVAIL; + goto out; + } if (ia && ((struct in6_ifaddr *)ia)->ia6_flags & (IN6_IFF_ANYCAST|IN6_IFF_NOTREADY| IN6_IFF_DETACHED|IN6_IFF_DEPRECATED)) { - return (EADDRNOTAVAIL); + error = EADDRNOTAVAIL; + goto out; } inp->in6p_laddr = addr->sin6_addr; - return 0; + error = 0; +out: + lwkt_replymsg(&msg->bind.base.lmsg, error); } -static int -rip6_connect(struct socket *so, struct sockaddr *nam, struct thread *td) +static void +rip6_connect(netmsg_t msg) { + struct socket *so = msg->connect.base.nm_so; + struct sockaddr *nam = msg->connect.nm_nam; struct inpcb *inp = so->so_pcb; struct sockaddr_in6 *addr = (struct sockaddr_in6 *)nam; struct in6_addr *in6a = NULL; @@ -676,12 +707,18 @@ rip6_connect(struct socket *so, struct sockaddr *nam, struct thread *td) struct sockaddr_in6 tmp; #endif - if (nam->sa_len != sizeof(*addr)) - return EINVAL; - if (TAILQ_EMPTY(&ifnet)) - return EADDRNOTAVAIL; - if (addr->sin6_family != AF_INET6) - return EAFNOSUPPORT; + if (nam->sa_len != sizeof(*addr)) { + error = EINVAL; + goto out; + } + if (TAILQ_EMPTY(&ifnet)) { + error = EADDRNOTAVAIL; + goto out; + } + if (addr->sin6_family != AF_INET6) { + error = EAFNOSUPPORT; + goto out; + } #ifdef ENABLE_DEFAULT_SCOPE if (addr->sin6_scope_id == 0) { /* not change if specified */ /* avoid overwrites */ @@ -694,34 +731,44 @@ rip6_connect(struct socket *so, struct sockaddr *nam, struct thread *td) in6a = in6_selectsrc(addr, inp->in6p_outputopts, inp->in6p_moptions, &inp->in6p_route, &inp->in6p_laddr, &error, NULL); - if (in6a == NULL) - return (error ? error : EADDRNOTAVAIL); - inp->in6p_laddr = *in6a; - inp->in6p_faddr = addr->sin6_addr; - soisconnected(so); - return 0; + if (in6a == NULL) { + if (error == 0) + error = EADDRNOTAVAIL; + } else { + inp->in6p_laddr = *in6a; + inp->in6p_faddr = addr->sin6_addr; + soisconnected(so); + error = 0; + } +out: + lwkt_replymsg(&msg->connect.base.lmsg, error); } -static int -rip6_shutdown(struct socket *so) +static void +rip6_shutdown(netmsg_t msg) { - socantsendmore(so); - return 0; + socantsendmore(msg->shutdown.base.nm_so); + lwkt_replymsg(&msg->shutdown.base.lmsg, 0); } -static int -rip6_send(struct socket *so, int flags, struct mbuf *m, struct sockaddr *nam, - struct mbuf *control, struct thread *td) +static void +rip6_send(netmsg_t msg) { + struct socket *so = msg->send.base.nm_so; + struct mbuf *m = msg->send.nm_m; + struct sockaddr *nam = msg->send.nm_addr; + struct mbuf *control = msg->send.nm_control; struct inpcb *inp = so->so_pcb; struct sockaddr_in6 tmp; struct sockaddr_in6 *dst; + int error; /* always copy sockaddr to avoid overwrites */ if (so->so_state & SS_ISCONNECTED) { if (nam) { m_freem(m); - return EISCONN; + error = EISCONN; + goto out; } /* XXX */ bzero(&tmp, sizeof(tmp)); @@ -733,7 +780,8 @@ rip6_send(struct socket *so, int flags, struct mbuf *m, struct sockaddr *nam, } else { if (nam == NULL) { m_freem(m); - return ENOTCONN; + error = ENOTCONN; + goto out; } tmp = *(struct sockaddr_in6 *)nam; dst = &tmp; @@ -743,27 +791,29 @@ rip6_send(struct socket *so, int flags, struct mbuf *m, struct sockaddr *nam, dst->sin6_scope_id = scope6_addr2default(&dst->sin6_addr); } #endif - return rip6_output(m, so, dst, control); + error = rip6_output(m, so, dst, control); +out: + lwkt_replymsg(&msg->send.base.lmsg, error); } struct pr_usrreqs rip6_usrreqs = { .pru_abort = rip6_abort, - .pru_accept = pru_accept_notsupp, + .pru_accept = pr_generic_notsupp, .pru_attach = rip6_attach, .pru_bind = rip6_bind, .pru_connect = rip6_connect, - .pru_connect2 = pru_connect2_notsupp, - .pru_control = in6_control, + .pru_connect2 = pr_generic_notsupp, + .pru_control = in6_control_dispatch, .pru_detach = rip6_detach, .pru_disconnect = rip6_disconnect, - .pru_listen = pru_listen_notsupp, - .pru_peeraddr = in6_setpeeraddr, - .pru_rcvd = pru_rcvd_notsupp, - .pru_rcvoob = pru_rcvoob_notsupp, + .pru_listen = pr_generic_notsupp, + .pru_peeraddr = in6_setpeeraddr_dispatch, + .pru_rcvd = pr_generic_notsupp, + .pru_rcvoob = pr_generic_notsupp, .pru_send = rip6_send, .pru_sense = pru_sense_null, .pru_shutdown = rip6_shutdown, - .pru_sockaddr = in6_setsockaddr, + .pru_sockaddr = in6_setsockaddr_dispatch, .pru_sosend = sosend, .pru_soreceive = soreceive }; diff --git a/sys/netinet6/sctp6_usrreq.c b/sys/netinet6/sctp6_usrreq.c index d6a0a6d981..6db6065d76 100644 --- a/sys/netinet6/sctp6_usrreq.c +++ b/sys/netinet6/sctp6_usrreq.c @@ -65,7 +65,10 @@ #include #include #include + #include +#include + #include #include #include @@ -122,8 +125,6 @@ extern struct protosw inetsw[]; extern u_int32_t sctp_debug_on; #endif -static int sctp6_detach(struct socket *so); - #if !(defined(__FreeBSD__) || defined(__APPLE__) || defined(__DragonFly__)) extern void in6_sin_2_v4mapsin6 (struct sockaddr_in *sin, struct sockaddr_in6 *sin6); @@ -174,14 +175,13 @@ in6_sin6_2_sin_in_sock(struct sockaddr *nam) #endif /* !(__FreeBSD__ || __APPLE__) */ +static int sctp6_bind_oncpu(struct socket *so, struct sockaddr *addr, thread_t td); + + extern int sctp_no_csum_on_loopback; int -#if defined(__APPLE__) -sctp6_input(struct mbuf **mp, int *offp) -#else sctp6_input(struct mbuf **mp, int *offp, int proto) -#endif { struct mbuf *m = *mp; struct ip6_hdr *ip6; @@ -728,9 +728,10 @@ SYSCTL_PROC(_net_inet6_sctp6, OID_AUTO, getcred, CTLTYPE_OPAQUE|CTLFLAG_RW, * NOTE: (so) is referenced from soabort*() and netmsg_pru_abort() * will sofree() it when we return. */ -static int -sctp6_abort(struct socket *so) +static void +sctp6_abort(netmsg_t msg) { + struct socket *so = msg->abort.base.nm_so; struct sctp_inpcb *inp; int error; @@ -742,37 +743,33 @@ sctp6_abort(struct socket *so) } else { error = EINVAL; } - - return error; + lwkt_replymsg(&msg->lmsg, error); } -static int -#if defined(__FreeBSD__) && __FreeBSD_version >= 500000 -sctp6_attach(struct socket *so, int proto, struct thread *p) -#elif defined(__DragonFly__) -sctp6_attach(struct socket *so, int proto, struct pru_attach_info *ai) -#else -sctp6_attach(struct socket *so, int proto, struct proc *p) -#endif +static void +sctp6_attach(netmsg_t msg) { + struct socket *so = msg->attach.base.nm_so; struct in6pcb *inp6; int error; struct sctp_inpcb *inp; inp = (struct sctp_inpcb *)so->so_pcb; - if (inp != NULL) - return EINVAL; + if (inp != NULL) { + error = EINVAL; + goto out; + } if (so->so_snd.ssb_hiwat == 0 || so->so_rcv.ssb_hiwat == 0) { error = soreserve(so, sctp_sendspace, sctp_recvspace, NULL); if (error) - return error; + goto out; } crit_enter(); error = sctp_inpcb_alloc(so); crit_exit(); if (error) - return error; + goto out; inp = (struct sctp_inpcb *)so->so_pcb; inp->sctp_flags |= SCTP_PCB_FLAGS_BOUND_V6; /* I'm v6! */ inp6 = (struct in6pcb *)inp; @@ -811,30 +808,34 @@ sctp6_attach(struct socket *so, int proto, struct proc *p) * Hmm what about the IPSEC stuff that is missing here but * in sctp_attach()? */ - return 0; + error = 0; +out: + lwkt_replymsg(&msg->lmsg, error); } -static int -#if (defined(__FreeBSD__) && __FreeBSD_version >= 500000) || defined(__DragonFly__) -sctp6_bind(struct socket *so, struct sockaddr *addr, struct thread *p) -{ -#else -#if defined(__FreeBSD__) || defined(__APPLE__) -sctp6_bind(struct socket *so, struct sockaddr *addr, struct proc *p) +static void +sctp6_bind(netmsg_t msg) { -#else -sctp6_bind(struct socket *so, struct mbuf *nam, struct proc *p) + int error; + + error = sctp6_bind_oncpu(msg->bind.base.nm_so, + msg->bind.nm_nam, + msg->bind.nm_td); + lwkt_replymsg(&msg->lmsg, error); +} + +static int +sctp6_bind_oncpu(struct socket *so, struct sockaddr *addr, thread_t td) { - struct sockaddr *addr = nam ? mtod(nam, struct sockaddr *) : NULL; -#endif -#endif struct sctp_inpcb *inp; struct in6pcb *inp6; int error; inp = (struct sctp_inpcb *)so->so_pcb; - if (inp == NULL) - return EINVAL; + if (inp == NULL) { + error = EINVAL; + goto out; + } inp6 = (struct in6pcb *)inp; #if defined(__FreeBSD__) || defined(__APPLE__) || defined(__DragonFly__) @@ -904,41 +905,51 @@ sctp6_bind(struct socket *so, struct mbuf *nam, struct proc *p) #endif #endif crit_enter(); - error = sctp_inpcb_bind(so, (struct sockaddr *)&sin, p); + error = sctp_inpcb_bind(so, + (struct sockaddr *)&sin, + td); crit_exit(); - return error; + goto out; } } } else if (addr != NULL) { /* IPV6_V6ONLY socket */ if (addr->sa_family == AF_INET) { /* can't bind v4 addr to v6 only socket! */ - return EINVAL; + error = EINVAL; + goto out; } else { struct sockaddr_in6 *sin6_p; sin6_p = (struct sockaddr_in6 *)addr; - if (IN6_IS_ADDR_V4MAPPED(&sin6_p->sin6_addr)) + if (IN6_IS_ADDR_V4MAPPED(&sin6_p->sin6_addr)) { /* can't bind v4-mapped addrs either! */ /* NOTE: we don't support SIIT */ - return EINVAL; + error = EINVAL; + goto out; + } } } crit_enter(); - error = sctp_inpcb_bind(so, addr, p); + error = sctp_inpcb_bind(so, addr, td); crit_exit(); +out: return error; } /*This could be made common with sctp_detach() since they are identical */ -static int -sctp6_detach(struct socket *so) +static void +sctp6_detach(netmsg_t msg) { + struct socket *so = msg->detach.base.nm_so; struct sctp_inpcb *inp; + int error; inp = (struct sctp_inpcb *)so->so_pcb; - if (inp == NULL) - return EINVAL; + if (inp == NULL) { + error = EINVAL; + goto out; + } crit_enter(); if (((so->so_options & SO_LINGER) && (so->so_linger == 0)) || (so->so_rcv.ssb_cc > 0)) @@ -946,25 +957,30 @@ sctp6_detach(struct socket *so) else sctp_inpcb_free(inp, 0); crit_exit(); - return 0; + error = 0; +out: + lwkt_replymsg(&msg->lmsg, error); } -static int -sctp6_disconnect(struct socket *so) +static void +sctp6_disconnect(netmsg_t msg) { + struct socket *so = msg->disconnect.base.nm_so; struct sctp_inpcb *inp; + int error; crit_enter(); inp = (struct sctp_inpcb *)so->so_pcb; if (inp == NULL) { crit_exit(); - return (ENOTCONN); + error = ENOTCONN; + goto out; } if (inp->sctp_flags & SCTP_PCB_FLAGS_TCPTYPE) { if (LIST_EMPTY(&inp->sctp_asoc_list)) { /* No connection */ crit_exit(); - return (ENOTCONN); + error = ENOTCONN; } else { int some_on_streamwheel = 0; struct sctp_association *asoc; @@ -973,7 +989,8 @@ sctp6_disconnect(struct socket *so) stcb = LIST_FIRST(&inp->sctp_asoc_list); if (stcb == NULL) { crit_exit(); - return (EINVAL); + error = EINVAL; + goto out; } asoc = &stcb->asoc; if (!TAILQ_EMPTY(&asoc->out_wheel)) { @@ -1029,48 +1046,33 @@ sctp6_disconnect(struct socket *so) asoc->state |= SCTP_STATE_SHUTDOWN_PENDING; } crit_exit(); - return (0); + error = 0; } } else { /* UDP model does not support this */ crit_exit(); - return EOPNOTSUPP; + error = EOPNOTSUPP; } +out: + lwkt_replymsg(&msg->lmsg, error); } -int -#if (defined(__FreeBSD__) && __FreeBSD_version >= 500000) || defined(__DragonFly__) -sctp_send(struct socket *so, int flags, struct mbuf *m, struct sockaddr *addr, - struct mbuf *control, struct thread *p); -#else -sctp_send(struct socket *so, int flags, struct mbuf *m, struct sockaddr *addr, - struct mbuf *control, struct proc *p); -#endif - - -static int -#if (defined(__FreeBSD__) && __FreeBSD_version >= 500000) || defined(__DragonFly__) -sctp6_send(struct socket *so, int flags, struct mbuf *m, struct sockaddr *addr, - struct mbuf *control, struct thread *p) -{ -#else -#if defined(__FreeBSD__) || defined(__APPLE__) -sctp6_send(struct socket *so, int flags, struct mbuf *m, struct sockaddr *addr, - struct mbuf *control, struct proc *p) -{ -#else -sctp6_send(struct socket *so, int flags, struct mbuf *m, struct mbuf *nam, - struct mbuf *control, struct proc *p) +static +void +sctp6_send(netmsg_t msg) { - struct sockaddr *addr = nam ? mtod(nam, struct sockaddr *) : NULL; -#endif -#endif + struct socket *so = msg->send.base.nm_so; + struct mbuf *m = msg->send.nm_m; + struct mbuf *control = msg->send.nm_control; + struct sockaddr *addr = msg->send.nm_addr; struct sctp_inpcb *inp; struct inpcb *in_inp; struct in6pcb *inp6; + int flags = msg->send.nm_flags; #ifdef INET struct sockaddr_in6 *sin6; #endif /* INET */ + int error; /* No SPL needed since sctp_output does this */ inp = (struct sctp_inpcb *)so->so_pcb; @@ -1080,7 +1082,8 @@ sctp6_send(struct socket *so, int flags, struct mbuf *m, struct mbuf *nam, control = NULL; } m_freem(m); - return EINVAL; + error = EINVAL; + goto out; } in_inp = (struct inpcb *)inp; inp6 = (struct in6pcb *)inp; @@ -1097,7 +1100,8 @@ sctp6_send(struct socket *so, int flags, struct mbuf *m, struct mbuf *nam, m_freem(control); control = NULL; } - return (EDESTADDRREQ); + error = EDESTADDRREQ; + goto out; } #ifdef INET @@ -1117,23 +1121,31 @@ sctp6_send(struct socket *so, int flags, struct mbuf *m, struct mbuf *nam, * destined to a v4 addr or v4-mapped addr */ if (addr->sa_family == AF_INET) { - return EINVAL; + error = EINVAL; + goto out; } if (IN6_IS_ADDR_V4MAPPED(&sin6->sin6_addr)) { - return EINVAL; + error = EINVAL; + goto out; } } if (IN6_IS_ADDR_V4MAPPED(&sin6->sin6_addr)) { if (!ip6_v6only) { - struct sockaddr_in sin; + struct sockaddr_in *sin; + + sin = kmalloc(sizeof(*sin), M_LWKTMSG, M_INTWAIT); /* convert v4-mapped into v4 addr and send */ - in6_sin6_2_sin(&sin, sin6); - return sctp_send(so, flags, m, (struct sockaddr *)&sin, - control, p); + in6_sin6_2_sin(sin, sin6); + msg->send.nm_addr = (struct sockaddr *)sin; + msg->send.nm_flags |= PRUS_NAMALLOC; + sctp_send(msg); + /* msg invalid now */ + return; } else { /* mapped addresses aren't enabled */ - return EINVAL; + error = EINVAL; + goto out; } } #endif /* INET */ @@ -1185,31 +1197,22 @@ connected_type: * optionaly switch back to this code (by changing back * the defininitions but this is not advisable. */ - int ret; - ret = sctp_output(inp, inp->pkt , addr, inp->control, p, flags); + error = sctp_output(inp, inp->pkt, addr, + inp->control, msg->send.nm_td, flags); inp->pkt = NULL; inp->control = NULL; - return (ret); } else { - return (0); + error = 0; } +out: + lwkt_replymsg(&msg->lmsg, error); } -static int -#if (defined(__FreeBSD__) && __FreeBSD_version >= 500000) || defined(__DragonFly__) -sctp6_connect(struct socket *so, struct sockaddr *addr, struct thread *p) -{ -#else -#if defined(__FreeBSD__) || defined(__APPLE__) -sctp6_connect(struct socket *so, struct sockaddr *addr, struct proc *p) -{ -#else -sctp6_connect(struct socket *so, struct mbuf *nam, struct proc *p) +static void +sctp6_connect(netmsg_t msg) { - struct sockaddr *addr = mtod(nam, struct sockaddr *); -#endif -#endif - int error = 0; + struct socket *so = msg->connect.base.nm_so; + struct sockaddr *addr = msg->connect.nm_nam; struct sctp_inpcb *inp; struct in6pcb *inp6; struct sctp_tcb *stcb; @@ -1217,14 +1220,16 @@ sctp6_connect(struct socket *so, struct mbuf *nam, struct proc *p) struct sockaddr_in6 *sin6; struct sockaddr_storage ss; #endif /* INET */ + int error = 0; crit_enter(); inp6 = (struct in6pcb *)so->so_pcb; inp = (struct sctp_inpcb *)so->so_pcb; if (inp == NULL) { crit_exit(); - return (ECONNRESET); /* I made the same as TCP since + error = ECONNRESET; /* I made the same as TCP since * we are not setup? */ + goto out; } SCTP_ASOC_CREATE_LOCK(inp); SCTP_INP_RLOCK(inp); @@ -1232,12 +1237,11 @@ sctp6_connect(struct socket *so, struct mbuf *nam, struct proc *p) SCTP_PCB_FLAGS_UNBOUND) { /* Bind a ephemeral port */ SCTP_INP_RUNLOCK(inp); - error = sctp6_bind(so, NULL, p); + error = sctp6_bind_oncpu(so, NULL, msg->connect.nm_td); if (error) { crit_exit(); SCTP_ASOC_CREATE_UNLOCK(inp); - - return (error); + goto out; } SCTP_INP_RLOCK(inp); } @@ -1248,7 +1252,8 @@ sctp6_connect(struct socket *so, struct mbuf *nam, struct proc *p) crit_exit(); SCTP_INP_RUNLOCK(inp); SCTP_ASOC_CREATE_UNLOCK(inp); - return (EADDRINUSE); + error = EADDRINUSE; + goto out; } #ifdef INET @@ -1270,13 +1275,15 @@ sctp6_connect(struct socket *so, struct mbuf *nam, struct proc *p) crit_exit(); SCTP_INP_RUNLOCK(inp); SCTP_ASOC_CREATE_UNLOCK(inp); - return EINVAL; + error = EINVAL; + goto out; } if (IN6_IS_ADDR_V4MAPPED(&sin6->sin6_addr)) { crit_exit(); SCTP_INP_RUNLOCK(inp); SCTP_ASOC_CREATE_UNLOCK(inp); - return EINVAL; + error = EINVAL; + goto out; } } @@ -1290,7 +1297,8 @@ sctp6_connect(struct socket *so, struct mbuf *nam, struct proc *p) crit_exit(); SCTP_INP_RUNLOCK(inp); SCTP_ASOC_CREATE_UNLOCK(inp); - return EINVAL; + error = EINVAL; + goto out; } } else #endif /* INET */ @@ -1320,7 +1328,8 @@ sctp6_connect(struct socket *so, struct mbuf *nam, struct proc *p) SCTP_ASOC_CREATE_UNLOCK(inp); SCTP_TCB_UNLOCK (stcb); crit_exit(); - return (EALREADY); + error = EALREADY; + goto out; } /* We are GOOD to go */ stcb = sctp_aloc_assoc(inp, addr, 1, &error, 0); @@ -1328,7 +1337,7 @@ sctp6_connect(struct socket *so, struct mbuf *nam, struct proc *p) if (stcb == NULL) { /* Gak! no memory */ crit_exit(); - return (error); + goto out; } if (stcb->sctp_ep->sctp_flags & SCTP_PCB_FLAGS_TCPTYPE) { stcb->sctp_ep->sctp_flags |= SCTP_PCB_FLAGS_CONNECTED; @@ -1340,7 +1349,8 @@ sctp6_connect(struct socket *so, struct mbuf *nam, struct proc *p) sctp_send_initiate(inp, stcb); SCTP_TCB_UNLOCK (stcb); crit_exit(); - return error; +out: + lwkt_replymsg(&msg->lmsg, error); } static int @@ -1513,31 +1523,29 @@ sctp6_peeraddr(struct socket *so, struct mbuf *nam) return (0); } -static int -#if defined(__FreeBSD__) || defined(__APPLE__) || defined(__DragonFly__) -sctp6_in6getaddr(struct socket *so, struct sockaddr **nam) +static void +sctp6_in6getaddr(netmsg_t msg) { + struct socket *so = msg->sockaddr.base.nm_so;; + struct sockaddr **nam = msg->sockaddr.nm_nam; struct sockaddr *addr; -#else -sctp6_in6getaddr(struct socket *so, struct mbuf *nam) -{ - struct sockaddr *addr = mtod(nam, struct sockaddr *); -#endif struct in6pcb *inp6 = sotoin6pcb(so); int error; - if (inp6 == NULL) - return EINVAL; + if (inp6 == NULL) { + error = EINVAL; + goto out; + } crit_enter(); /* allow v6 addresses precedence */ error = sctp6_getaddr(so, nam); if (error) { /* try v4 next if v6 failed */ - error = sctp_ingetaddr(so, nam); + error = sctp_ingetaddr_oncpu(so, nam); if (error) { crit_exit(); - return (error); + goto out; } #if defined(__FreeBSD__) || defined(__APPLE__) || defined(__DragonFly__) addr = *nam; @@ -1569,35 +1577,33 @@ sctp6_in6getaddr(struct socket *so, struct mbuf *nam) #endif } crit_exit(); - return (error); +out: + lwkt_replymsg(&msg->lmsg, error); } - -static int -#if defined(__FreeBSD__) || defined(__APPLE__) || defined(__DragonFly__) -sctp6_getpeeraddr(struct socket *so, struct sockaddr **nam) +static void +sctp6_getpeeraddr(netmsg_t msg) { + struct socket *so = msg->peeraddr.base.nm_so; + struct sockaddr **nam = msg->peeraddr.nm_nam; struct sockaddr *addr = *nam; -#else -sctp6_getpeeraddr(struct socket *so, struct mbuf *nam) -{ - struct sockaddr *addr = mtod(nam, struct sockaddr *); -#endif struct in6pcb *inp6 = sotoin6pcb(so); int error; - if (inp6 == NULL) - return EINVAL; + if (inp6 == NULL) { + error = EINVAL; + goto out; + } crit_enter(); /* allow v6 addresses precedence */ error = sctp6_peeraddr(so, nam); if (error) { /* try v4 next if v6 failed */ - error = sctp_peeraddr(so, nam); + error = sctp_peeraddr_oncpu(so, nam); if (error) { crit_exit(); - return (error); + goto out; } /* if I'm V6ONLY, convert it to v4-mapped */ if ( @@ -1626,7 +1632,8 @@ sctp6_getpeeraddr(struct socket *so, struct mbuf *nam) #endif } crit_exit(); - return error; +out: + lwkt_replymsg(&msg->lmsg, error); } #if defined(__FreeBSD__) || defined(__APPLE__) || defined(__DragonFly__) @@ -1636,14 +1643,14 @@ struct pr_usrreqs sctp6_usrreqs = { .pru_attach = sctp6_attach, .pru_bind = sctp6_bind, .pru_connect = sctp6_connect, - .pru_connect2 = pru_connect2_notsupp, - .pru_control = in6_control, + .pru_connect2 = pr_generic_notsupp, + .pru_control = in6_control_dispatch, .pru_detach = sctp6_detach, .pru_disconnect = sctp6_disconnect, .pru_listen = sctp_listen, .pru_peeraddr = sctp6_getpeeraddr, .pru_rcvd = sctp_usr_recvd, - .pru_rcvoob = pru_rcvoob_notsupp, + .pru_rcvoob = pr_generic_notsupp, .pru_send = sctp6_send, .pru_sense = pru_sense_null, .pru_shutdown = sctp_shutdown, @@ -1654,6 +1661,8 @@ struct pr_usrreqs sctp6_usrreqs = { #else +#error x + int sctp6_usrreq(struct socket *so, int req, struct mbuf *m, struct mbuf *nam, struct mbuf *control, struct proc *p) diff --git a/sys/netinet6/tcp6_var.h b/sys/netinet6/tcp6_var.h index 6dd92c8e7e..47246907bc 100644 --- a/sys/netinet6/tcp6_var.h +++ b/sys/netinet6/tcp6_var.h @@ -81,8 +81,9 @@ struct ip6_hdr; struct sockaddr; struct in_conninfo; struct lwkt_port; +union netmsg; -void tcp6_ctlinput (int, struct sockaddr *, void *); +void tcp6_ctlinput(union netmsg *); void tcp6_init (void); int tcp6_input (struct mbuf **, int *, int); struct rtentry *tcp_rtlookup6(struct in_conninfo *); diff --git a/sys/netinet6/udp6_usrreq.c b/sys/netinet6/udp6_usrreq.c index 04ef9e7f4e..f3b9bf02f7 100644 --- a/sys/netinet6/udp6_usrreq.c +++ b/sys/netinet6/udp6_usrreq.c @@ -86,6 +86,7 @@ #include #include +#include #include #include @@ -123,7 +124,6 @@ extern struct protosw inetsw[]; static int in6_mcmatch (struct inpcb *, struct in6_addr *, struct ifnet *); -static int udp6_detach (struct socket *so); static int in6_mcmatch(struct inpcb *in6p, struct in6_addr *ia6, struct ifnet *ifp) @@ -424,8 +424,11 @@ bad: } void -udp6_ctlinput(int cmd, struct sockaddr *sa, void *d) +udp6_ctlinput(netmsg_t msg) { + int cmd = msg->ctlinput.nm_cmd; + struct sockaddr *sa = msg->ctlinput.nm_arg; + void *d = msg->ctlinput.nm_extra; struct udphdr uh; struct ip6_hdr *ip6; struct mbuf *m; @@ -440,16 +443,16 @@ udp6_ctlinput(int cmd, struct sockaddr *sa, void *d) if (sa->sa_family != AF_INET6 || sa->sa_len != sizeof(struct sockaddr_in6)) - return; + goto out; if ((unsigned)cmd >= PRC_NCMDS) - return; + goto out; if (PRC_IS_REDIRECT(cmd)) notify = in6_rtchange, d = NULL; else if (cmd == PRC_HOSTDEAD) d = NULL; else if (inet6ctlerrmap[cmd] == 0) - return; + goto out; /* if the parameter is from icmp6, decode it. */ if (d != NULL) { @@ -480,10 +483,13 @@ udp6_ctlinput(int cmd, struct sockaddr *sa, void *d) in6_pcbnotify(&udbinfo.pcblisthead, sa, uh.uh_dport, (struct sockaddr *)ip6cp->ip6c_src, uh.uh_sport, cmd, 0, notify); - } else + } else { in6_pcbnotify(&udbinfo.pcblisthead, sa, 0, (const struct sockaddr *)sa6_src, 0, cmd, 0, notify); + } +out: + lwkt_replymsg(&msg->ctlinput.base.lmsg, 0); } static int @@ -529,9 +535,10 @@ SYSCTL_PROC(_net_inet6_udp6, OID_AUTO, getcred, CTLTYPE_OPAQUE|CTLFLAG_RW, * NOTE: (so) is referenced from soabort*() and netmsg_pru_abort() * will sofree() it when we return. */ -static int -udp6_abort(struct socket *so) +static void +udp6_abort(netmsg_t msg) { + struct socket *so = msg->abort.base.nm_so; struct inpcb *inp; int error; @@ -543,31 +550,34 @@ udp6_abort(struct socket *so) } else { error = EINVAL; } - - return error; + lwkt_replymsg(&msg->abort.base.lmsg, error); } -static int -udp6_attach(struct socket *so, int proto, struct pru_attach_info *ai) +static void +udp6_attach(netmsg_t msg) { + struct socket *so = msg->attach.base.nm_so; + struct pru_attach_info *ai = msg->attach.nm_ai; struct inpcb *inp; int error; inp = so->so_pcb; - if (inp != NULL) - return EINVAL; + if (inp != NULL) { + error = EINVAL; + goto out; + } if (so->so_snd.ssb_hiwat == 0 || so->so_rcv.ssb_hiwat == 0) { error = soreserve(so, udp_sendspace, udp_recvspace, ai->sb_rlimit); if (error) - return error; + goto out; } crit_enter(); error = in_pcballoc(so, &udbinfo); crit_exit(); if (error) - return error; + goto out; sosetport(so, cpu_portfn(0)); inp = (struct inpcb *)so->so_pcb; inp->inp_vflag |= INP_IPV6; @@ -582,19 +592,26 @@ udp6_attach(struct socket *so, int proto, struct pru_attach_info *ai) * which may match an IPv4-mapped IPv6 address. */ inp->inp_ip_ttl = ip_defttl; - return 0; + error = 0; +out: + lwkt_replymsg(&msg->attach.base.lmsg, error); } -static int -udp6_bind(struct socket *so, struct sockaddr *nam, struct thread *td) +static void +udp6_bind(netmsg_t msg) { + struct socket *so =msg->bind.base.nm_so; + struct sockaddr *nam = msg->bind.nm_nam; + struct thread *td = msg->bind.nm_td; struct sockaddr_in6 *sin6_p = (struct sockaddr_in6 *)nam; struct inpcb *inp; int error; inp = so->so_pcb; - if (inp == NULL) - return EINVAL; + if (inp == NULL) { + error = EINVAL; + goto out; + } inp->inp_vflag &= ~INP_IPV4; inp->inp_vflag |= INP_IPV6; @@ -610,7 +627,7 @@ udp6_bind(struct socket *so, struct sockaddr *nam, struct thread *td) crit_enter(); error = in_pcbbind(inp, (struct sockaddr *)&sin, td); crit_exit(); - return error; + goto out; } } @@ -622,18 +639,24 @@ udp6_bind(struct socket *so, struct sockaddr *nam, struct thread *td) inp->inp_flags |= INP_WASBOUND_NOTANY; in_pcbinswildcardhash(inp); } - return error; +out: + lwkt_replymsg(&msg->bind.base.lmsg, error); } -static int -udp6_connect(struct socket *so, struct sockaddr *nam, struct thread *td) +static void +udp6_connect(netmsg_t msg) { + struct socket *so = msg->connect.base.nm_so; + struct sockaddr *nam = msg->connect.nm_nam; + struct thread *td = msg->connect.nm_td; struct inpcb *inp; int error; inp = so->so_pcb; - if (inp == NULL) - return EINVAL; + if (inp == NULL) { + error = EINVAL; + goto out; + } if (!(inp->inp_flags & IN6P_IPV6_V6ONLY)) { struct sockaddr_in6 *sin6_p; @@ -642,8 +665,10 @@ udp6_connect(struct socket *so, struct sockaddr *nam, struct thread *td) if (IN6_IS_ADDR_V4MAPPED(&sin6_p->sin6_addr)) { struct sockaddr_in sin; - if (inp->inp_faddr.s_addr != INADDR_ANY) - return EISCONN; + if (inp->inp_faddr.s_addr != INADDR_ANY) { + error = EISCONN; + goto out; + } in6_sin6_2_sin(&sin, sin6_p); crit_enter(); error = in_pcbconnect(inp, (struct sockaddr *)&sin, td); @@ -653,15 +678,19 @@ udp6_connect(struct socket *so, struct sockaddr *nam, struct thread *td) inp->inp_vflag &= ~INP_IPV6; soisconnected(so); } - return error; + goto out; } } - if (!IN6_IS_ADDR_UNSPECIFIED(&inp->in6p_faddr)) - return EISCONN; + if (!IN6_IS_ADDR_UNSPECIFIED(&inp->in6p_faddr)) { + error = EISCONN; + goto out; + } if (inp->inp_flags & INP_WILDCARD) in_pcbremwildcardhash(inp); - if (!prison_remote_ip(td, nam)) - return(EAFNOSUPPORT); /* IPv4 only jail */ + if (!prison_remote_ip(td, nam)) { + error = EAFNOSUPPORT; /* IPv4 only jail */ + goto out; + } crit_enter(); error = in6_pcbconnect(inp, nam, td); crit_exit(); @@ -681,53 +710,71 @@ udp6_connect(struct socket *so, struct sockaddr *nam, struct thread *td) inp->in6p_laddr = kin6addr_any; in_pcbinswildcardhash(inp); } - return error; +out: + lwkt_replymsg(&msg->connect.base.lmsg, error); } -static int -udp6_detach(struct socket *so) +static void +udp6_detach(netmsg_t msg) { + struct socket *so = msg->detach.base.nm_so; struct inpcb *inp; + int error; inp = so->so_pcb; - if (inp == NULL) - return EINVAL; - crit_enter(); - in6_pcbdetach(inp); - crit_exit(); - return 0; + if (inp) { + crit_enter(); + in6_pcbdetach(inp); + crit_exit(); + error = 0; + } else { + error = EINVAL; + } + lwkt_replymsg(&msg->detach.base.lmsg, error); } -static int -udp6_disconnect(struct socket *so) +static void +udp6_disconnect(netmsg_t msg) { + struct socket *so = msg->disconnect.base.nm_so; struct inpcb *inp; + int error; inp = so->so_pcb; - if (inp == NULL) - return EINVAL; + if (inp == NULL) { + error = EINVAL; + goto out; + } if (inp->inp_vflag & INP_IPV4) { const struct pr_usrreqs *pru; pru = inetsw[ip_protox[IPPROTO_UDP]].pr_usrreqs; - return ((*pru->pru_disconnect)(so)); + pru->pru_disconnect(msg); /* XXX on right port? */ + return; } - if (IN6_IS_ADDR_UNSPECIFIED(&inp->in6p_faddr)) - return ENOTCONN; - - crit_enter(); - in6_pcbdisconnect(inp); - crit_exit(); - soclrstate(so, SS_ISCONNECTED); /* XXX */ - return 0; + if (IN6_IS_ADDR_UNSPECIFIED(&inp->in6p_faddr)) { + error = ENOTCONN; + } else { + crit_enter(); + in6_pcbdisconnect(inp); + crit_exit(); + soclrstate(so, SS_ISCONNECTED); /* XXX */ + error = 0; + } +out: + lwkt_replymsg(&msg->disconnect.base.lmsg, error); } -static int -udp6_send(struct socket *so, int flags, struct mbuf *m, struct sockaddr *addr, - struct mbuf *control, struct thread *td) +static void +udp6_send(netmsg_t msg) { + struct socket *so = msg->send.base.nm_so; + struct mbuf *m = msg->send.nm_m; + struct sockaddr *addr = msg->send.nm_addr; + struct mbuf *control = msg->send.nm_control; + struct thread *td = msg->send.nm_td; struct inpcb *inp; int error = 0; @@ -765,38 +812,36 @@ udp6_send(struct socket *so, int flags, struct mbuf *m, struct sockaddr *addr, if (sin6) in6_sin6_2_sin_in_sock(addr); pru = inetsw[ip_protox[IPPROTO_UDP]].pr_usrreqs; - error = ((*pru->pru_send)(so, flags, m, addr, - control, td)); - /* addr will just be freed in sendit(). */ - return error; + pru->pru_send(msg); + /* msg invalid now */ + return; } } - return udp6_output(inp, m, addr, control, td); - + error = udp6_output(inp, m, addr, control, td); bad: m_freem(m); - return (error); + lwkt_replymsg(&msg->send.base.lmsg, error); } struct pr_usrreqs udp6_usrreqs = { .pru_abort = udp6_abort, - .pru_accept = pru_accept_notsupp, + .pru_accept = pr_generic_notsupp, .pru_attach = udp6_attach, .pru_bind = udp6_bind, .pru_connect = udp6_connect, - .pru_connect2 = pru_connect2_notsupp, - .pru_control = in6_control, + .pru_connect2 = pr_generic_notsupp, + .pru_control = in6_control_dispatch, .pru_detach = udp6_detach, .pru_disconnect = udp6_disconnect, - .pru_listen = pru_listen_notsupp, - .pru_peeraddr = in6_mapped_peeraddr, - .pru_rcvd = pru_rcvd_notsupp, - .pru_rcvoob = pru_rcvoob_notsupp, + .pru_listen = pr_generic_notsupp, + .pru_peeraddr = in6_mapped_peeraddr_dispatch, + .pru_rcvd = pr_generic_notsupp, + .pru_rcvoob = pr_generic_notsupp, .pru_send = udp6_send, .pru_sense = pru_sense_null, .pru_shutdown = udp_shutdown, - .pru_sockaddr = in6_mapped_sockaddr, + .pru_sockaddr = in6_mapped_sockaddr_dispatch, .pru_sosend = sosend, .pru_soreceive = soreceive }; diff --git a/sys/netinet6/udp6_var.h b/sys/netinet6/udp6_var.h index b504fa4d71..f0725197d1 100644 --- a/sys/netinet6/udp6_var.h +++ b/sys/netinet6/udp6_var.h @@ -83,7 +83,7 @@ struct mbuf; struct inpcb; struct sockaddr; -void udp6_ctlinput (int, struct sockaddr *, void *); +void udp6_ctlinput (union netmsg *); int udp6_input (struct mbuf **, int *, int); int udp6_output (struct inpcb *inp, struct mbuf *m, struct sockaddr *addr, struct mbuf *control, diff --git a/sys/netproto/atalk/aarp.c b/sys/netproto/atalk/aarp.c index 79f75f381a..6197f2b836 100644 --- a/sys/netproto/atalk/aarp.c +++ b/sys/netproto/atalk/aarp.c @@ -245,9 +245,9 @@ aarpresolve(struct arpcom *ac, struct mbuf *m, struct sockaddr_at *destsat, } void -aarpintr(struct netmsg *msg) +aarpintr(netmsg_t msg) { - struct mbuf *m = ((struct netmsg_packet *)msg)->nm_packet; + struct mbuf *m = msg->packet.nm_packet; struct arphdr *ar; struct arpcom *ac; diff --git a/sys/netproto/atalk/at_control.c b/sys/netproto/atalk/at_control.c index 40787c132e..ef6c9711a9 100644 --- a/sys/netproto/atalk/at_control.c +++ b/sys/netproto/atalk/at_control.c @@ -46,7 +46,7 @@ static int aa_claim_addr(struct ifaddr *ifa, struct sockaddr *gw); int at_control(struct socket *so, u_long cmd, caddr_t data, - struct ifnet *ifp, struct thread *td ) + struct ifnet *ifp, struct thread *td ) { struct ifreq *ifr = (struct ifreq *)data; struct sockaddr_at *sat; diff --git a/sys/netproto/atalk/at_extern.h b/sys/netproto/atalk/at_extern.h index c1b9f3d170..584d0a8670 100644 --- a/sys/netproto/atalk/at_extern.h +++ b/sys/netproto/atalk/at_extern.h @@ -18,13 +18,13 @@ extern void aarptfree (struct aarptab *); #endif struct ifnet; -struct netmsg; +union netmsg; struct proc; struct socket; -extern void aarpintr (struct netmsg *); -extern void at1intr (struct netmsg *); -extern void at2intr (struct netmsg *); +extern void aarpintr (union netmsg *); +extern void at1intr (union netmsg *); +extern void at2intr (union netmsg *); extern void aarp_clean (void); extern int at_control ( struct socket *so, u_long cmd, diff --git a/sys/netproto/atalk/at_proto.c b/sys/netproto/atalk/at_proto.c index d89956aefb..40f2196012 100644 --- a/sys/netproto/atalk/at_proto.c +++ b/sys/netproto/atalk/at_proto.c @@ -41,7 +41,11 @@ static struct domain atalkdomain; static struct protosw atalksw[] = { { /* Identifiers */ - SOCK_DGRAM, &atalkdomain, ATPROTO_DDP, PR_ATOMIC|PR_ADDR, + .pr_type = SOCK_DGRAM, + .pr_domain = &atalkdomain, + .pr_protocol = ATPROTO_DDP, + .pr_flags = PR_ATOMIC|PR_ADDR, + /* * protocol-protocol interface. * fields are pr_input, pr_output, pr_ctlinput, and pr_ctloutput. @@ -50,12 +54,14 @@ static struct protosw atalksw[] = { * pr_output can be used by higher level appletalk protocols, should * they be included in the kernel. */ - 0, ddp_output, 0, 0, - cpu0_soport, NULL, - /* utility routines. */ - ddp_init, 0, 0, 0, - &ddp_usrreqs - }, + .pr_input = NULL, + .pr_output = ddp_output, + .pr_ctlinput = NULL, + .pr_ctloutput = NULL, + + .pr_init = ddp_init, + .pr_usrreqs = &ddp_usrreqs + } }; static struct domain atalkdomain = { diff --git a/sys/netproto/atalk/ddp_input.c b/sys/netproto/atalk/ddp_input.c index 1302048b30..aa5e962915 100644 --- a/sys/netproto/atalk/ddp_input.c +++ b/sys/netproto/atalk/ddp_input.c @@ -40,9 +40,9 @@ static void ddp_input(struct mbuf *, struct ifnet *, struct elaphdr *, int); * Could probably merge these two code segments a little better... */ void -at2intr(struct netmsg *msg) +at2intr(netmsg_t msg) { - struct mbuf *m = ((struct netmsg_packet *)msg)->nm_packet; + struct mbuf *m = msg->packet.nm_packet; /* * Phase 2 packet handling @@ -54,9 +54,9 @@ at2intr(struct netmsg *msg) } void -at1intr(struct netmsg *msg) +at1intr(netmsg_t msg) { - struct mbuf *m = ((struct netmsg_packet *)msg)->nm_packet; + struct mbuf *m = msg->packet.nm_packet; struct elaphdr *elhp, elh; get_mplock(); diff --git a/sys/netproto/atalk/ddp_usrreq.c b/sys/netproto/atalk/ddp_usrreq.c index f523a296c9..133b0be07b 100644 --- a/sys/netproto/atalk/ddp_usrreq.c +++ b/sys/netproto/atalk/ddp_usrreq.c @@ -11,12 +11,15 @@ #include #include #include -#include #include #include -#include #include + #include +#include +#include +#include + #include #include #include @@ -40,153 +43,181 @@ struct ddpcb *ddpcb = NULL; static u_long ddp_sendspace = DDP_MAXSZ; /* Max ddp size + 1 (ddp_type) */ static u_long ddp_recvspace = 10 * ( 587 + sizeof( struct sockaddr_at )); -static int -ddp_attach(struct socket *so, int proto, struct pru_attach_info *ai) +static void +ddp_attach(netmsg_t msg) { + struct socket *so = msg->attach.base.nm_so; + struct pru_attach_info *ai = msg->attach.nm_ai; struct ddpcb *ddp; - int error = 0; - + int error; - ddp = sotoddpcb( so ); - if ( ddp != NULL ) { - return( EINVAL); + ddp = sotoddpcb(so); + if (ddp != NULL) { + error = EINVAL; + goto out; } - error = at_pcballoc( so ); - if (error) { - return (error); + error = at_pcballoc(so); + if (error == 0) { + error = soreserve(so, ddp_sendspace, ddp_recvspace, + ai->sb_rlimit); } - return (soreserve( so, ddp_sendspace, ddp_recvspace, ai->sb_rlimit )); +out: + lwkt_replymsg(&msg->attach.base.lmsg, error); } -static int -ddp_detach(struct socket *so) +static void +ddp_detach(netmsg_t msg) { + struct socket *so = msg->detach.base.nm_so; struct ddpcb *ddp; + int error; - ddp = sotoddpcb( so ); - if ( ddp == NULL ) { - return( EINVAL); + ddp = sotoddpcb(so); + if (ddp == NULL) { + error = EINVAL; + } else { + at_pcbdetach(so, ddp); + error = 0; } - at_pcbdetach( so, ddp ); - return(0); + lwkt_replymsg(&msg->detach.base.lmsg, error); } -static int -ddp_bind(struct socket *so, struct sockaddr *nam, struct thread *td) +static void +ddp_bind(netmsg_t msg) { - struct ddpcb *ddp; - int error = 0; + struct socket *so = msg->bind.base.nm_so; + struct ddpcb *ddp; + int error; - ddp = sotoddpcb( so ); - if ( ddp == NULL ) { - return( EINVAL); + ddp = sotoddpcb(so); + if (ddp) { + error = at_pcbsetaddr(ddp, msg->bind.nm_nam, msg->bind.nm_td); + } else { + error = EINVAL; } - error = at_pcbsetaddr(ddp, nam, td); - return (error); + lwkt_replymsg(&msg->bind.base.lmsg, error); } -static int -ddp_connect(struct socket *so, struct sockaddr *nam, struct thread *td) +static void +ddp_connect(netmsg_t msg) { - struct ddpcb *ddp; - int error = 0; + struct socket *so = msg->connect.base.nm_so; + struct ddpcb *ddp; + int error; - ddp = sotoddpcb( so ); - if ( ddp == NULL ) { - return( EINVAL); - } - - if ( ddp->ddp_fsat.sat_port != ATADDR_ANYPORT ) { - return(EISCONN); + ddp = sotoddpcb(so); + if (ddp == NULL) { + error = EINVAL; + } else if (ddp->ddp_fsat.sat_port != ATADDR_ANYPORT ) { + error = EISCONN; + } else { + error = at_pcbconnect(ddp, msg->connect.nm_nam, + msg->connect.nm_td); + if (error == 0) + soisconnected(so); } - - error = at_pcbconnect( ddp, nam, td ); - if ( error == 0 ) - soisconnected( so ); - return(error); + lwkt_replymsg(&msg->connect.base.lmsg, error); } -static int -ddp_disconnect(struct socket *so) +static void +ddp_disconnect(netmsg_t msg) { - - struct ddpcb *ddp; + struct socket *so = msg->disconnect.base.nm_so; + struct ddpcb *ddp; + int error; - ddp = sotoddpcb( so ); - if ( ddp == NULL ) { - return( EINVAL); - } - if ( ddp->ddp_fsat.sat_addr.s_node == ATADDR_ANYNODE ) { - return(ENOTCONN); + ddp = sotoddpcb(so); + if (ddp == NULL) { + error = EINVAL; + } else if (ddp->ddp_fsat.sat_addr.s_node == ATADDR_ANYNODE) { + error = ENOTCONN; + } else { + soreference(so); + at_pcbdisconnect(ddp); + ddp->ddp_fsat.sat_addr.s_node = ATADDR_ANYNODE; + soisdisconnected(so); + sofree(so); /* soref above */ + error = 0; } - - soreference(so); - at_pcbdisconnect( ddp ); - ddp->ddp_fsat.sat_addr.s_node = ATADDR_ANYNODE; - soisdisconnected( so ); - sofree(so); /* soref above */ - return(0); + lwkt_replymsg(&msg->disconnect.base.lmsg, error); } -static int -ddp_shutdown(struct socket *so) +static void +ddp_shutdown(netmsg_t msg) { + struct socket *so = msg->shutdown.base.nm_so; struct ddpcb *ddp; + int error; - ddp = sotoddpcb( so ); - if ( ddp == NULL ) { - return( EINVAL); + ddp = sotoddpcb(so); + if (ddp) { + socantsendmore(so); + error = 0; + } else { + error = EINVAL; } - socantsendmore( so ); - return(0); + lwkt_replymsg(&msg->shutdown.base.lmsg, error); } -static int -ddp_send(struct socket *so, int flags, struct mbuf *m, struct sockaddr *addr, - struct mbuf *control, struct thread *td) +static void +ddp_send(netmsg_t msg) { - struct ddpcb *ddp; - int error = 0; + struct socket *so = msg->send.base.nm_so; + struct mbuf *m = msg->send.nm_m; + struct sockaddr *addr = msg->send.nm_addr; + struct mbuf *control = msg->send.nm_control; + struct ddpcb *ddp; + int error; - ddp = sotoddpcb( so ); - if ( ddp == NULL ) { - return(EINVAL); + ddp = sotoddpcb(so); + if (ddp == NULL) { + error = EINVAL; + goto out; } - if ( control && control->m_len ) { - return(EINVAL); + if (control && control->m_len) { + error = EINVAL; + goto out; } - if ( addr ) { - if ( ddp->ddp_fsat.sat_port != ATADDR_ANYPORT ) { - return(EISCONN); + if (addr) { + if (ddp->ddp_fsat.sat_port != ATADDR_ANYPORT) { + error = EISCONN; + goto out; } - error = at_pcbconnect(ddp, addr, td); - if ( error ) { - return(error); - } + error = at_pcbconnect(ddp, addr, msg->send.nm_td); + if (error) + goto out; } else { - if ( ddp->ddp_fsat.sat_port == ATADDR_ANYPORT ) { - return(ENOTCONN); + if (ddp->ddp_fsat.sat_port == ATADDR_ANYPORT) { + error = ENOTCONN; + goto out; } } - error = ddp_output( m, so ); - if ( addr ) { - at_pcbdisconnect( ddp ); + error = ddp_output(m, so); + m = NULL; + if (addr) { + at_pcbdisconnect(ddp); } - return(error); +out: + if (m) + m_freem(m); + if (control) + m_freem(control); + lwkt_replymsg(&msg->send.base.lmsg, error); } /* * NOTE: (so) is referenced from soabort*() and netmsg_pru_abort() * will sofree() it when we return. */ -static int -ddp_abort(struct socket *so) +static void +ddp_abort(netmsg_t msg) { + struct socket *so = msg->abort.base.nm_so; struct ddpcb *ddp; int error; @@ -198,7 +229,44 @@ ddp_abort(struct socket *so) } else { error = EINVAL; } - return error; + lwkt_replymsg(&msg->abort.base.lmsg, error); +} + +static void +ddp_setpeeraddr(netmsg_t msg) +{ + lwkt_replymsg(&msg->peeraddr.base.lmsg, EOPNOTSUPP); +} + +static void +ddp_setsockaddr(netmsg_t msg) +{ + struct socket *so = msg->sockaddr.base.nm_so; + struct sockaddr **nam = msg->sockaddr.nm_nam; + struct ddpcb *ddp; + int error; + + ddp = sotoddpcb(so); + if (ddp) { + at_sockaddr(ddp, nam); + error = 0; + } else { + error = EINVAL; + } + lwkt_replymsg(&msg->sockaddr.base.lmsg, error); +} + +static void +ddp_control(netmsg_t msg) +{ + struct socket *so = msg->control.base.nm_so; + int error; + + error = at_control(so, msg->control.nm_cmd, + msg->control.nm_data, + msg->control.nm_ifp, + msg->control.nm_td); + lwkt_replymsg(&msg->control.base.lmsg, error); } @@ -513,25 +581,6 @@ ddp_search( struct sockaddr_at *from, struct sockaddr_at *to, } return( ddp ); } -static int -at_setpeeraddr(struct socket *so, struct sockaddr **nam) -{ - return(EOPNOTSUPP); -} - -static int -at_setsockaddr(struct socket *so, struct sockaddr **nam) -{ - struct ddpcb *ddp; - - ddp = sotoddpcb( so ); - if ( ddp == NULL ) { - return( EINVAL); - } - at_sockaddr( ddp, nam ); - return(0); -} - void ddp_init(void) @@ -555,22 +604,22 @@ ddp_clean(void) struct pr_usrreqs ddp_usrreqs = { .pru_abort = ddp_abort, - .pru_accept = pru_accept_notsupp, + .pru_accept = pr_generic_notsupp, .pru_attach = ddp_attach, .pru_bind = ddp_bind, .pru_connect = ddp_connect, - .pru_connect2 = pru_connect2_notsupp, - .pru_control = at_control, + .pru_connect2 = pr_generic_notsupp, + .pru_control = ddp_control, .pru_detach = ddp_detach, .pru_disconnect = ddp_disconnect, - .pru_listen = pru_listen_notsupp, - .pru_peeraddr = at_setpeeraddr, - .pru_rcvd = pru_rcvd_notsupp, - .pru_rcvoob = pru_rcvoob_notsupp, + .pru_listen = pr_generic_notsupp, + .pru_peeraddr = ddp_setpeeraddr, + .pru_rcvd = pr_generic_notsupp, + .pru_rcvoob = pr_generic_notsupp, .pru_send = ddp_send, .pru_sense = pru_sense_null, .pru_shutdown = ddp_shutdown, - .pru_sockaddr = at_setsockaddr, + .pru_sockaddr = ddp_setsockaddr, .pru_sosend = sosend, .pru_soreceive = soreceive }; diff --git a/sys/netproto/atm/atm_aal5.c b/sys/netproto/atm/atm_aal5.c index 3d52712f26..b941b66ba7 100644 --- a/sys/netproto/atm/atm_aal5.c +++ b/sys/netproto/atm/atm_aal5.c @@ -48,25 +48,21 @@ u_long atm_aal5_recvspace = 64 * 1024; /* XXX */ /* * Local functions */ -static int atm_aal5_attach (struct socket *, int, - struct pru_attach_info *); -static int atm_aal5_detach (struct socket *); -static int atm_aal5_bind (struct socket *, struct sockaddr *, - struct thread *); -static int atm_aal5_listen (struct socket *, struct thread *); -static int atm_aal5_connect (struct socket *, struct sockaddr *, - struct thread *); -static int atm_aal5_accept (struct socket *, struct sockaddr **); -static int atm_aal5_disconnect (struct socket *); -static int atm_aal5_shutdown (struct socket *); -static int atm_aal5_send (struct socket *, int, KBuffer *, - struct sockaddr *, KBuffer *, struct thread *); -static int atm_aal5_abort (struct socket *); -static int atm_aal5_control (struct socket *, u_long, caddr_t, - struct ifnet *, struct thread *); -static int atm_aal5_sense (struct socket *, struct stat *); -static int atm_aal5_sockaddr (struct socket *, struct sockaddr **); -static int atm_aal5_peeraddr (struct socket *, struct sockaddr **); +static void atm_aal5_abort(netmsg_t); +static void atm_aal5_accept(netmsg_t); +static void atm_aal5_attach(netmsg_t); +static void atm_aal5_bind(netmsg_t); +static void atm_aal5_connect(netmsg_t); +static void atm_aal5_control(netmsg_t); +static void atm_aal5_detach(netmsg_t); +static void atm_aal5_listen(netmsg_t); +static void atm_aal5_peeraddr(netmsg_t); +static void atm_aal5_send(netmsg_t); +static void atm_aal5_sense(netmsg_t); +static void atm_aal5_disconnect(netmsg_t); +static void atm_aal5_shutdown(netmsg_t); +static void atm_aal5_sockaddr(netmsg_t); + static int atm_aal5_incoming (void *, Atm_connection *, Atm_attributes *, void **); static void atm_aal5_cpcs_data (void *, KBuffer *); @@ -82,14 +78,14 @@ struct pr_usrreqs atm_aal5_usrreqs = { .pru_attach = atm_aal5_attach, .pru_bind = atm_aal5_bind, .pru_connect = atm_aal5_connect, - .pru_connect2 = pru_connect2_notsupp, + .pru_connect2 = pr_generic_notsupp, .pru_control = atm_aal5_control, .pru_detach = atm_aal5_detach, .pru_disconnect = atm_aal5_disconnect, .pru_listen = atm_aal5_listen, .pru_peeraddr = atm_aal5_peeraddr, - .pru_rcvd = pru_rcvd_notsupp, - .pru_rcvoob = pru_rcvoob_notsupp, + .pru_rcvd = pr_generic_notsupp, + .pru_rcvoob = pr_generic_notsupp, .pru_send = atm_aal5_send, .pru_sense = atm_aal5_sense, .pru_shutdown = atm_aal5_shutdown, @@ -175,8 +171,9 @@ static Atm_attributes atm_aal5_defattr = { * Handy common code macros */ #ifdef DIAGNOSTIC + #define ATM_INTRO(f) \ - int err = 0; \ + do { \ crit_enter(); \ ATM_DEBUG2("aal5 socket %s (%p)\n", f, so); \ /* \ @@ -184,28 +181,81 @@ static Atm_attributes atm_aal5_defattr = { */ \ if (atm_stackq_head != NULL) \ panic("atm_aal5: stack queue not empty"); \ - ; + } while(0) + #else /* !DIAGNOSTIC */ + #define ATM_INTRO(f) \ - int err = 0; \ + do { \ crit_enter(); \ - ; + } while(0) + #endif /* DIAGNOSTIC */ #define ATM_OUTRO() \ + out: do { \ /* \ * Drain any deferred calls \ */ \ STACK_DRAIN(); \ crit_exit(); \ - return (err); \ - ; - -#define ATM_RETERR(error) { \ - err = error; \ + lwkt_replymsg(&msg->lmsg, error); \ + return; \ goto out; \ + } while(0) \ + +/* + * Abnormally terminate service + * + * Arguments: + * so pointer to socket + * + * Returns: + * 0 request processed + * error error processing request - reason indicated + * + * NOTE: (so) is referenced from soabort*() and netmsg_pru_abort() + * will sofree() it when we return. + */ +static void +atm_aal5_abort(netmsg_t msg) +{ + struct socket *so = msg->abort.base.nm_so; + int error; + + ATM_INTRO("abort"); + so->so_error = ECONNABORTED; + error = atm_sock_detach(so); + ATM_OUTRO(); } +/* + * Accept pending connection + * + * Arguments: + * so pointer to socket + * addr pointer to pointer to contain protocol address + * + * Returns: + * 0 request processed + * error error processing request - reason indicated + * + */ +static void +atm_aal5_accept(netmsg_t msg) +{ + struct socket *so = msg->accept.base.nm_so; + int error; + + ATM_INTRO("accept"); + + /* + * Everything is pretty much done already, we just need to + * return the caller's address to the user. + */ + error = atm_sock_peeraddr(so, msg->accept.nm_nam); + ATM_OUTRO(); +} /* * Attach protocol to socket @@ -220,20 +270,23 @@ static Atm_attributes atm_aal5_defattr = { * error error processing request - reason indicated * */ -static int -atm_aal5_attach(struct socket *so, int proto, struct pru_attach_info *ai) +static void +atm_aal5_attach(netmsg_t msg) { - Atm_pcb *atp; + struct socket *so = msg->attach.base.nm_so; + struct pru_attach_info *ai = msg->attach.nm_ai; + Atm_pcb *atp; + int error; ATM_INTRO("attach"); /* * Do general attach stuff */ - err = atm_sock_attach(so, atm_aal5_sendspace, atm_aal5_recvspace, - ai->sb_rlimit); - if (err) - ATM_RETERR(err); + error = atm_sock_attach(so, atm_aal5_sendspace, atm_aal5_recvspace, + ai->sb_rlimit); + if (error) + goto out; /* * Finish up any protocol specific stuff @@ -247,11 +300,9 @@ atm_aal5_attach(struct socket *so, int proto, struct pru_attach_info *ai) atp->atp_attr = atm_aal5_defattr; strncpy(atp->atp_name, "(AAL5)", T_ATM_APP_NAME_LEN); -out: ATM_OUTRO(); } - /* * Detach protocol from socket * @@ -263,17 +314,19 @@ out: * error error processing request - reason indicated * */ -static int -atm_aal5_detach(struct socket *so) +static void +atm_aal5_detach(netmsg_t msg) { + struct socket *so = msg->detach.base.nm_so; + int error; + ATM_INTRO("detach"); - err = atm_sock_detach(so); + error = atm_sock_detach(so); ATM_OUTRO(); } - /* * Bind address to socket * @@ -287,17 +340,19 @@ atm_aal5_detach(struct socket *so) * error error processing request - reason indicated * */ -static int -atm_aal5_bind(struct socket *so, struct sockaddr *addr, struct thread *td) +static void +atm_aal5_bind(netmsg_t msg) { + struct socket *so = msg->bind.base.nm_so; + int error; + ATM_INTRO("bind"); - err = atm_sock_bind(so, addr); + error = atm_sock_bind(so, msg->bind.nm_nam); ATM_OUTRO(); } - /* * Listen for incoming connections * @@ -310,12 +365,15 @@ atm_aal5_bind(struct socket *so, struct sockaddr *addr, struct thread *td) * error error processing request - reason indicated * */ -static int -atm_aal5_listen(struct socket *so, struct thread *td) +static void +atm_aal5_listen(netmsg_t msg) { + struct socket *so = msg->listen.base.nm_so; + int error; + ATM_INTRO("listen"); - err = atm_sock_listen(so, &atm_aal5_endpt); + error = atm_sock_listen(so, &atm_aal5_endpt); ATM_OUTRO(); } @@ -334,10 +392,13 @@ atm_aal5_listen(struct socket *so, struct thread *td) * error error processing request - reason indicated * */ -static int -atm_aal5_connect(struct socket *so, struct sockaddr *addr, thread_t td) +static void +atm_aal5_connect(netmsg_t msg) { - Atm_pcb *atp; + struct socket *so = msg->connect.base.nm_so; + struct thread *td = msg->connect.nm_td; + Atm_pcb *atp; + int error; ATM_INTRO("connect"); @@ -347,54 +408,26 @@ atm_aal5_connect(struct socket *so, struct sockaddr *addr, thread_t td) * Resize send socket buffer to maximum sdu size */ if (atp->atp_attr.aal.tag == T_ATM_PRESENT) { - long size; + long size; size = atp->atp_attr.aal.v.aal5.forward_max_SDU_size; - if (size != T_ATM_ABSENT) + if (size != T_ATM_ABSENT) { if (!ssb_reserve(&so->so_snd, size, so, &td->td_proc->p_rlimit[RLIMIT_SBSIZE])) { - err = ENOBUFS; - ATM_OUTRO(); + error = ENOBUFS; + goto out; } - + } } /* * Now get the socket connected */ - err = atm_sock_connect(so, addr, &atm_aal5_endpt); - - ATM_OUTRO(); -} - - -/* - * Accept pending connection - * - * Arguments: - * so pointer to socket - * addr pointer to pointer to contain protocol address - * - * Returns: - * 0 request processed - * error error processing request - reason indicated - * - */ -static int -atm_aal5_accept(struct socket *so, struct sockaddr **addr) -{ - ATM_INTRO("accept"); - - /* - * Everything is pretty much done already, we just need to - * return the caller's address to the user. - */ - err = atm_sock_peeraddr(so, addr); + error = atm_sock_connect(so, msg->connect.nm_nam, &atm_aal5_endpt); ATM_OUTRO(); } - /* * Disconnect connected socket * @@ -406,12 +439,15 @@ atm_aal5_accept(struct socket *so, struct sockaddr **addr) * error error processing request - reason indicated * */ -static int -atm_aal5_disconnect(struct socket *so) +static void +atm_aal5_disconnect(netmsg_t msg) { + struct socket *so = msg->disconnect.base.nm_so; + int error; + ATM_INTRO("disconnect"); - err = atm_sock_disconnect(so); + error = atm_sock_disconnect(so); ATM_OUTRO(); } @@ -428,12 +464,16 @@ atm_aal5_disconnect(struct socket *so) * error error processing request - reason indicated * */ -static int -atm_aal5_shutdown(struct socket *so) +static void +atm_aal5_shutdown(netmsg_t msg) { + struct socket *so = msg->shutdown.base.nm_so; + int error; + ATM_INTRO("shutdown"); socantsendmore(so); + error = 0; ATM_OUTRO(); } @@ -455,16 +495,14 @@ atm_aal5_shutdown(struct socket *so) * error error processing request - reason indicated * */ -static int -atm_aal5_send( - struct socket *so, - int flags, - KBuffer *m, - struct sockaddr *addr, - KBuffer *control, - struct thread *td -) { - Atm_pcb *atp; +static void +atm_aal5_send(netmsg_t msg) +{ + struct socket *so = msg->send.base.nm_so; + KBuffer *m = msg->send.nm_m; + KBuffer *control = msg->send.nm_control; + Atm_pcb *atp; + int error; ATM_INTRO("send"); @@ -472,30 +510,32 @@ atm_aal5_send( * We don't support any control functions */ if (control) { - int clen; + int clen; clen = KB_LEN(control); KB_FREEALL(control); if (clen) { KB_FREEALL(m); - ATM_RETERR(EINVAL); + error = EINVAL; + goto out; } } /* * We also don't support any flags or send-level addressing */ - if (flags || addr) { + if (msg->send.nm_flags || msg->send.nm_addr) { KB_FREEALL(m); - ATM_RETERR(EINVAL); + error = EINVAL; + goto out; } /* * All we've got left is the data, so push it out */ atp = sotoatmpcb(so); - err = atm_cm_cpcs_data(atp->atp_conn, m); - if (err) { + error = atm_cm_cpcs_data(atp->atp_conn, m); + if (error) { /* * Output problem, drop packet */ @@ -503,31 +543,6 @@ atm_aal5_send( KB_FREEALL(m); } -out: - ATM_OUTRO(); -} - - -/* - * Abnormally terminate service - * - * Arguments: - * so pointer to socket - * - * Returns: - * 0 request processed - * error error processing request - reason indicated - * - * NOTE: (so) is referenced from soabort*() and netmsg_pru_abort() - * will sofree() it when we return. - */ -static int -atm_aal5_abort(struct socket *so) -{ - ATM_INTRO("abort"); - - so->so_error = ECONNABORTED; - err = atm_sock_detach(so); ATM_OUTRO(); } @@ -547,20 +562,18 @@ atm_aal5_abort(struct socket *so) * error error processing request - reason indicated * */ -static int -atm_aal5_control( - struct socket *so, - u_long cmd, - caddr_t data, - struct ifnet *ifp, - struct thread *td -) { - ATM_INTRO("control"); +static void +atm_aal5_control(netmsg_t msg) +{ + struct socket *so = msg->control.base.nm_so; + int error; - switch (cmd) { + ATM_INTRO("control"); + switch (msg->control.nm_cmd) { default: - err = EOPNOTSUPP; + error = EOPNOTSUPP; + break; } ATM_OUTRO(); @@ -578,15 +591,20 @@ atm_aal5_control( * error error processing request - reason indicated * */ -static int -atm_aal5_sense(struct socket *so, struct stat *st) +static void +atm_aal5_sense(netmsg_t msg) { + struct socket *so = msg->sense.base.nm_so; + struct stat *st = msg->sense.nm_stat; + int error; + ATM_INTRO("sense"); /* * Just return the max sdu size for the connection */ st->st_blksize = so->so_snd.ssb_hiwat; + error = 0; ATM_OUTRO(); } @@ -604,12 +622,15 @@ atm_aal5_sense(struct socket *so, struct stat *st) * error error processing request - reason indicated * */ -static int -atm_aal5_sockaddr(struct socket *so, struct sockaddr **addr) +static void +atm_aal5_sockaddr(netmsg_t msg) { + struct socket *so = msg->sockaddr.base.nm_so; + int error; + ATM_INTRO("sockaddr"); - err = atm_sock_sockaddr(so, addr); + error = atm_sock_sockaddr(so, msg->sockaddr.nm_nam); ATM_OUTRO(); } @@ -627,16 +648,104 @@ atm_aal5_sockaddr(struct socket *so, struct sockaddr **addr) * error error processing request - reason indicated * */ -static int -atm_aal5_peeraddr(struct socket *so, struct sockaddr **addr) +static void +atm_aal5_peeraddr(netmsg_t msg) { + struct socket *so = msg->peeraddr.base.nm_so; + int error; + ATM_INTRO("peeraddr"); - err = atm_sock_peeraddr(so, addr); + error = atm_sock_peeraddr(so, msg->peeraddr.nm_nam); ATM_OUTRO(); } +/* + * Process getsockopt/setsockopt system calls + * + * Arguments: + * so pointer to socket + * sopt pointer to socket option info + * + * Returns: + * 0 request processed + * error error processing request - reason indicated + * + */ +void +atm_aal5_ctloutput(netmsg_t msg) +{ + struct socket *so = msg->ctloutput.base.nm_so; + struct sockopt *sopt = msg->ctloutput.nm_sopt; + Atm_pcb *atp; + int error; + + ATM_INTRO("ctloutput"); + + /* + * Make sure this is for us + */ + if (sopt->sopt_level != T_ATM_SIGNALING) { + error = EINVAL; + goto out; + } + atp = sotoatmpcb(so); + if (atp == NULL) { + error = ENOTCONN; + goto out; + } + + switch (sopt->sopt_dir) { + case SOPT_SET: + /* + * setsockopt() + */ + + /* + * Validate socket state + */ + switch (sopt->sopt_name) { + case T_ATM_ADD_LEAF: + case T_ATM_DROP_LEAF: + if ((so->so_state & SS_ISCONNECTED) == 0) { + error = ENOTCONN; + goto out; + } + break; + case T_ATM_CAUSE: + case T_ATM_APP_NAME: + break; + default: + if (so->so_state & SS_ISCONNECTED) { + error = EISCONN; + goto out; + } + break; + } + + /* + * Validate and save user-supplied option data + */ + error = atm_sock_setopt(so, sopt, atp); + break; + case SOPT_GET: + /* + * getsockopt() + */ + + /* + * Return option data + */ + error = atm_sock_getopt(so, sopt, atp); + break; + default: + error = EINVAL; + break; + } + + ATM_OUTRO(); +} /* * Process Incoming Calls @@ -740,92 +849,6 @@ atm_aal5_cpcs_data(void *tok, KBuffer *m) return; } - -/* - * Process getsockopt/setsockopt system calls - * - * Arguments: - * so pointer to socket - * sopt pointer to socket option info - * - * Returns: - * 0 request processed - * error error processing request - reason indicated - * - */ -int -atm_aal5_ctloutput(struct socket *so, struct sockopt *sopt) -{ - Atm_pcb *atp; - - ATM_INTRO("ctloutput"); - - /* - * Make sure this is for us - */ - if (sopt->sopt_level != T_ATM_SIGNALING) { - ATM_RETERR(EINVAL); - } - atp = sotoatmpcb(so); - if (atp == NULL) { - ATM_RETERR(ENOTCONN); - } - - switch (sopt->sopt_dir) { - - case SOPT_SET: - /* - * setsockopt() - */ - - /* - * Validate socket state - */ - switch (sopt->sopt_name) { - - case T_ATM_ADD_LEAF: - case T_ATM_DROP_LEAF: - if ((so->so_state & SS_ISCONNECTED) == 0) { - ATM_RETERR(ENOTCONN); - } - break; - - case T_ATM_CAUSE: - case T_ATM_APP_NAME: - break; - - default: - if (so->so_state & SS_ISCONNECTED) { - ATM_RETERR(EISCONN); - } - break; - } - - /* - * Validate and save user-supplied option data - */ - err = atm_sock_setopt(so, sopt, atp); - - break; - - case SOPT_GET: - /* - * getsockopt() - */ - - /* - * Return option data - */ - err = atm_sock_getopt(so, sopt, atp); - - break; - } - -out: - ATM_OUTRO(); -} - - /* * Initialize AAL5 Sockets * diff --git a/sys/netproto/atm/atm_proto.c b/sys/netproto/atm/atm_proto.c index 55071d394f..b880386ef4 100644 --- a/sys/netproto/atm/atm_proto.c +++ b/sys/netproto/atm/atm_proto.c @@ -38,45 +38,36 @@ #include "kern_include.h" struct protosw atmsw[] = { -{ SOCK_DGRAM, /* ioctl()-only */ - &atmdomain, - 0, - 0, - 0, /* pr_input */ - 0, /* pr_output */ - 0, /* pr_ctlinput */ - 0, /* pr_ctloutput */ - cpu0_soport, /* pr_mport */ - NULL, /* pr_ctlport */ - 0, /* pr_init */ - 0, /* pr_fasttimo */ - 0, /* pr_slowtimo */ - 0, /* pr_drain */ - &atm_dgram_usrreqs, /* pr_usrreqs */ -}, + { + .pr_type = SOCK_DGRAM, /* ioctl()-only */ + .pr_domain = &atmdomain, + .pr_protocol = 0, + .pr_flags = 0, -{ SOCK_SEQPACKET, /* AAL-5 */ - &atmdomain, - ATM_PROTO_AAL5, - PR_ATOMIC|PR_CONNREQUIRED, - 0, /* pr_input */ - 0, /* pr_output */ - 0, /* pr_ctlinput */ - atm_aal5_ctloutput, /* pr_ctloutput */ - cpu0_soport, /* pr_mport */ - NULL, /* pr_ctlport */ - 0, /* pr_init */ - 0, /* pr_fasttimo */ - 0, /* pr_slowtimo */ - 0, /* pr_drain */ - &atm_aal5_usrreqs, /* pr_usrreqs */ -}, + .pr_usrreqs = &atm_dgram_usrreqs + }, + + { + .pr_type = SOCK_SEQPACKET, /* AAL-5 */ + .pr_domain = &atmdomain, + .pr_protocol = ATM_PROTO_AAL5, + .pr_flags = PR_ATOMIC|PR_CONNREQUIRED, + + .pr_input = NULL, + .pr_output = NULL, + .pr_ctlinput = NULL, + .pr_ctloutput = atm_aal5_ctloutput, + + .pr_usrreqs = &atm_aal5_usrreqs, + }, #ifdef XXX -{ SOCK_SEQPACKET, /* SSCOP */ - &atmdomain, - ATM_PROTO_SSCOP, - PR_ATOMIC|PR_CONNREQUIRED|PR_WANTRCVD, + { + .pr_type = SOCK_SEQPACKET, /* SSCOP */ + .pr_domain = &atmdomain, + .pr_protocol = ATM_PROTO_SSCOP, + .pr_flags = PR_ATOMIC|PR_CONNREQUIRED|PR_WANTRCVD, + x, /* pr_input */ x, /* pr_output */ x, /* pr_ctlinput */ @@ -88,7 +79,7 @@ struct protosw atmsw[] = { 0, /* pr_slowtimo */ x, /* pr_drain */ x, /* pr_usrreqs */ -}, + }, #endif }; @@ -98,84 +89,3 @@ struct domain atmdomain = { }; DOMAIN_SET(atm); - -/* - * Protocol request not supported - * - * Arguments: - * so pointer to socket - * - * Returns: - * errno error - operation not supported - * - */ -int -atm_proto_notsupp1(struct socket *so) -{ - return (EOPNOTSUPP); -} - - -/* - * Protocol request not supported - * - * Arguments: - * so pointer to socket - * addr pointer to protocol address - * p pointer to process - * - * Returns: - * errno error - operation not supported - * - */ -int -atm_proto_notsupp2(struct socket *so, struct sockaddr *addr, thread_t td) -{ - return (EOPNOTSUPP); -} - - -/* - * Protocol request not supported - * - * Arguments: - * so pointer to socket - * addr pointer to pointer to protocol address - * - * Returns: - * errno error - operation not supported - * - */ -int -atm_proto_notsupp3(struct socket *so, struct sockaddr **addr) -{ - return (EOPNOTSUPP); -} - - -/* - * Protocol request not supported - * - * Arguments: - * so pointer to socket - * i integer - * m pointer to kernel buffer - * addr pointer to protocol address - * m2 pointer to kernel buffer - * p pointer to process - * - * Returns: - * errno error - operation not supported - * - */ -int -atm_proto_notsupp4( - struct socket *so, - int i, - KBuffer *m, - struct sockaddr *addr, - KBuffer *m2, - struct thread *td -) { - return (EOPNOTSUPP); -} diff --git a/sys/netproto/atm/atm_subr.c b/sys/netproto/atm/atm_subr.c index bc4e91f763..e1cc4a3a1f 100644 --- a/sys/netproto/atm/atm_subr.c +++ b/sys/netproto/atm/atm_subr.c @@ -37,10 +37,6 @@ #include "kern_include.h" -#include -#include -#include - /* * Global variables */ @@ -72,7 +68,7 @@ static struct callout atm_timexp_ch; */ static void atm_compact (struct atm_time *); static KTimeout_ret atm_timexp (void *); -static void atm_intr(struct netmsg *); +static void atm_intr(netmsg_t msg); /* * Local variables @@ -849,9 +845,9 @@ atm_stack_drain(void) * */ static void -atm_intr(struct netmsg *msg) +atm_intr(netmsg_t msg) { - struct mbuf *m = ((struct netmsg_packet *)msg)->nm_packet; + struct mbuf *m = msg->packet.nm_packet; caddr_t cp; atm_intr_func_t func; void *token; diff --git a/sys/netproto/atm/atm_usrreq.c b/sys/netproto/atm/atm_usrreq.c index 4d043e6fa7..35ea218ae7 100644 --- a/sys/netproto/atm/atm_usrreq.c +++ b/sys/netproto/atm/atm_usrreq.c @@ -40,33 +40,31 @@ /* * Local functions */ -static int atm_dgram_attach (struct socket *, int, - struct pru_attach_info *); -static int atm_dgram_control (struct socket *, u_long, caddr_t, - struct ifnet *, struct thread *); +static void atm_dgram_attach(netmsg_t msg); +static void atm_dgram_control(netmsg_t msg); static int atm_dgram_info (caddr_t); /* * New-style socket request routines */ struct pr_usrreqs atm_dgram_usrreqs = { - .pru_abort = atm_proto_notsupp1, - .pru_accept = pru_accept_notsupp, + .pru_abort = pr_generic_notsupp, + .pru_accept = pr_generic_notsupp, .pru_attach = atm_dgram_attach, - .pru_bind = atm_proto_notsupp2, - .pru_connect = pru_connect_notsupp, - .pru_connect2 = pru_connect2_notsupp, + .pru_bind = pr_generic_notsupp, + .pru_connect = pr_generic_notsupp, + .pru_connect2 = pr_generic_notsupp, .pru_control = atm_dgram_control, - .pru_detach = atm_proto_notsupp1, - .pru_disconnect = atm_proto_notsupp1, - .pru_listen = pru_listen_notsupp, - .pru_peeraddr = atm_proto_notsupp3, - .pru_rcvd = pru_rcvd_notsupp, - .pru_rcvoob = pru_rcvoob_notsupp, - .pru_send = atm_proto_notsupp4, + .pru_detach = pr_generic_notsupp, + .pru_disconnect = pr_generic_notsupp, + .pru_listen = pr_generic_notsupp, + .pru_peeraddr = pr_generic_notsupp, + .pru_rcvd = pr_generic_notsupp, + .pru_rcvoob = pr_generic_notsupp, + .pru_send = pr_generic_notsupp, .pru_sense = pru_sense_null, - .pru_shutdown = atm_proto_notsupp1, - .pru_sockaddr = atm_proto_notsupp3, + .pru_shutdown = pr_generic_notsupp, + .pru_sockaddr = pr_generic_notsupp, .pru_sosend = sosend, .pru_soreceive = soreceive }; @@ -75,36 +73,37 @@ struct pr_usrreqs atm_dgram_usrreqs = { * Handy common code macros */ #ifdef DIAGNOSTIC + #define ATM_INTRO() \ - int err = 0; \ + do { \ crit_enter(); \ /* \ * Stack queue should have been drained \ */ \ if (atm_stackq_head != NULL) \ panic("atm_usrreq: stack queue not empty"); \ - ; + } while(0) + #else + #define ATM_INTRO() \ - int err = 0; \ + do { \ crit_enter(); \ - ; + } while(0) + #endif #define ATM_OUTRO() \ + out: do { \ /* \ * Drain any deferred calls \ */ \ STACK_DRAIN(); \ crit_exit(); \ - return (err); \ - ; - -#define ATM_RETERR(errno) { \ - err = errno; \ + lwkt_replymsg(&msg->lmsg, error); \ + return; \ goto out; \ -} - + } while(0) /* * Attach protocol to socket @@ -119,14 +118,18 @@ struct pr_usrreqs atm_dgram_usrreqs = { * errno error processing request - reason indicated * */ -static int -atm_dgram_attach(struct socket *so, int proto, struct pru_attach_info *ai) +static void +atm_dgram_attach(netmsg_t msg) { + int error; + ATM_INTRO(); /* * Nothing to do here for ioctl()-only sockets */ + error = 0; + ATM_OUTRO(); } @@ -146,10 +149,15 @@ atm_dgram_attach(struct socket *so, int proto, struct pru_attach_info *ai) * errno error processing request - reason indicated * */ -static int -atm_dgram_control(struct socket *so, u_long cmd, caddr_t data, - struct ifnet *ifp, struct thread *td) +static void +atm_dgram_control(netmsg_t msg) { + u_long cmd = msg->control.nm_cmd; + caddr_t data = msg->control.nm_data; + struct thread *td = msg->control.nm_td; + int error; + + error = 0; ATM_INTRO(); /* @@ -157,13 +165,14 @@ atm_dgram_control(struct socket *so, u_long cmd, caddr_t data, * then process it based on the sub-op code */ switch (cmd) { - case AIOCCFG: { struct atmcfgreq *acp = (struct atmcfgreq *)data; struct atm_pif *pip; - if (priv_check(td, PRIV_ROOT)) - ATM_RETERR(EPERM); + if (priv_check(td, PRIV_ROOT)) { + error = EPERM; + goto out; + } switch (acp->acr_opcode) { @@ -171,22 +180,27 @@ atm_dgram_control(struct socket *so, u_long cmd, caddr_t data, /* * Attach signalling manager */ - if ((pip = atm_pifname(acp->acr_att_intf)) == NULL) - ATM_RETERR(ENXIO); - err = atm_sigmgr_attach(pip, acp->acr_att_proto); + if ((pip = atm_pifname(acp->acr_att_intf)) == NULL) { + error = ENXIO; + goto out; + } + error = atm_sigmgr_attach(pip, acp->acr_att_proto); break; case AIOCS_CFG_DET: /* * Detach signalling manager */ - if ((pip = atm_pifname(acp->acr_det_intf)) == NULL) - ATM_RETERR(ENXIO); - err = atm_sigmgr_detach(pip); + if ((pip = atm_pifname(acp->acr_det_intf)) == NULL) { + error = ENXIO; + goto out; + } + error = atm_sigmgr_detach(pip); break; default: - err = EOPNOTSUPP; + error = EOPNOTSUPP; + break; } break; } @@ -195,8 +209,10 @@ atm_dgram_control(struct socket *so, u_long cmd, caddr_t data, struct atmaddreq *aap = (struct atmaddreq *)data; Atm_endpoint *epp; - if (priv_check(td, PRIV_ROOT)) - ATM_RETERR(EPERM); + if (priv_check(td, PRIV_ROOT)) { + error = EPERM; + goto out; + } switch (aap->aar_opcode) { @@ -210,13 +226,15 @@ atm_dgram_control(struct socket *so, u_long cmd, caddr_t data, */ epp = aap->aar_pvc_sap > ENDPT_MAX ? NULL : atm_endpoints[aap->aar_pvc_sap]; - if (epp == NULL) - ATM_RETERR(ENOPROTOOPT); + if (epp == NULL) { + error = ENOPROTOOPT; + goto out; + } /* * Let endpoint service handle it from here */ - err = (*epp->ep_ioctl)(AIOCS_ADD_PVC, data, NULL); + error = (*epp->ep_ioctl)(AIOCS_ADD_PVC, data, NULL); break; case AIOCS_ADD_ARP: @@ -224,17 +242,19 @@ atm_dgram_control(struct socket *so, u_long cmd, caddr_t data, * Add an ARP mapping */ epp = atm_endpoints[ENDPT_IP]; - if (epp == NULL) - ATM_RETERR(ENOPROTOOPT); + if (epp == NULL) { + error = ENOPROTOOPT; + goto out; + } /* * Let IP/ATM endpoint handle this */ - err = (*epp->ep_ioctl) (AIOCS_ADD_ARP, data, NULL); + error = (*epp->ep_ioctl) (AIOCS_ADD_ARP, data, NULL); break; default: - err = EOPNOTSUPP; + error = EOPNOTSUPP; } break; } @@ -245,8 +265,10 @@ atm_dgram_control(struct socket *so, u_long cmd, caddr_t data, struct sigmgr *smp; Atm_endpoint *epp; - if (priv_check(td, PRIV_ROOT)) - ATM_RETERR(EPERM); + if (priv_check(td, PRIV_ROOT)) { + error = EPERM; + goto out; + } switch (adp->adr_opcode) { @@ -259,15 +281,19 @@ atm_dgram_control(struct socket *so, u_long cmd, caddr_t data, /* * Locate appropriate sigmgr */ - if ((pip = atm_pifname(adp->adr_pvc_intf)) == NULL) - ATM_RETERR(ENXIO); - if ((smp = pip->pif_sigmgr) == NULL) - ATM_RETERR(ENOENT); + if ((pip = atm_pifname(adp->adr_pvc_intf)) == NULL) { + error = ENXIO; + goto out; + } + if ((smp = pip->pif_sigmgr) == NULL) { + error = ENOENT; + goto out; + } /* * Let sigmgr handle it from here */ - err = (*smp->sm_ioctl)(adp->adr_opcode, data, + error = (*smp->sm_ioctl)(adp->adr_opcode, data, (caddr_t)pip->pif_siginst); break; @@ -276,17 +302,19 @@ atm_dgram_control(struct socket *so, u_long cmd, caddr_t data, * Delete an ARP mapping */ epp = atm_endpoints[ENDPT_IP]; - if (epp == NULL) - ATM_RETERR(ENOPROTOOPT); + if (epp == NULL) { + error = ENOPROTOOPT; + goto out; + } /* * Let IP/ATM endpoint handle this */ - err = (*epp->ep_ioctl) (AIOCS_DEL_ARP, data, NULL); + error = (*epp->ep_ioctl) (AIOCS_DEL_ARP, data, NULL); break; default: - err = EOPNOTSUPP; + error = EOPNOTSUPP; } break; } @@ -298,8 +326,10 @@ atm_dgram_control(struct socket *so, u_long cmd, caddr_t data, struct sigmgr *smp; struct ifnet *ifp2; - if (priv_check(td, PRIV_ROOT)) - ATM_RETERR(EPERM); + if (priv_check(td, PRIV_ROOT)) { + error = EPERM; + goto out; + } switch (asp->asr_opcode) { @@ -311,16 +341,20 @@ atm_dgram_control(struct socket *so, u_long cmd, caddr_t data, /* * Locate appropriate sigmgr */ - if ((nip = atm_nifname(asp->asr_arp_intf)) == NULL) - ATM_RETERR(ENXIO); + if ((nip = atm_nifname(asp->asr_arp_intf)) == NULL) { + error = ENXIO; + goto out; + } pip = nip->nif_pif; - if ((smp = pip->pif_sigmgr) == NULL) - ATM_RETERR(ENOENT); + if ((smp = pip->pif_sigmgr) == NULL) { + error = ENOENT; + goto out; + } /* * Let sigmgr handle it from here */ - err = (*smp->sm_ioctl)(AIOCS_SET_ASV, data, + error = (*smp->sm_ioctl)(AIOCS_SET_ASV, data, (caddr_t)nip); break; @@ -332,14 +366,18 @@ atm_dgram_control(struct socket *so, u_long cmd, caddr_t data, /* * Locate physical interface */ - if ((pip = atm_pifname(asp->asr_mac_intf)) == NULL) - ATM_RETERR(ENXIO); + if ((pip = atm_pifname(asp->asr_mac_intf)) == NULL) { + error = ENXIO; + goto out; + } /* * Interface must be detached */ - if (pip->pif_sigmgr != NULL) - ATM_RETERR(EADDRINUSE); + if (pip->pif_sigmgr != NULL) { + error = EADDRINUSE; + goto out; + } /* * Just plunk the address into the pif @@ -353,15 +391,20 @@ atm_dgram_control(struct socket *so, u_long cmd, caddr_t data, /* * Define network interfaces */ - if ((pip = atm_pifname(asp->asr_nif_intf)) == NULL) - ATM_RETERR(ENXIO); + if ((pip = atm_pifname(asp->asr_nif_intf)) == NULL) { + error = ENXIO; + goto out; + } /* * Validate interface count - logical interfaces * are differentiated by the atm address selector. */ - if ((asp->asr_nif_cnt <= 0) || (asp->asr_nif_cnt > 256)) - ATM_RETERR(EINVAL); + if ((asp->asr_nif_cnt <= 0) || + (asp->asr_nif_cnt > 256)) { + error = EINVAL; + goto out; + } /* * Make sure prefix name is unique @@ -379,15 +422,16 @@ atm_dgram_control(struct socket *so, u_long cmd, caddr_t data, } if (nip) continue; - ATM_RETERR(EEXIST); + error = EEXIST; + goto out; } } /* * Let interface handle it from here */ - err = (*pip->pif_ioctl)(AIOCS_SET_NIF, data, - (caddr_t)pip); + error = (*pip->pif_ioctl)(AIOCS_SET_NIF, data, + (caddr_t)pip); break; case AIOCS_SET_PRF: @@ -398,33 +442,37 @@ atm_dgram_control(struct socket *so, u_long cmd, caddr_t data, /* * Locate appropriate sigmgr */ - if ((pip = atm_pifname(asp->asr_prf_intf)) == NULL) - ATM_RETERR(ENXIO); - if ((smp = pip->pif_sigmgr) == NULL) - ATM_RETERR(ENOENT); + if ((pip = atm_pifname(asp->asr_prf_intf)) == NULL) { + error = ENXIO; + goto out; + } + if ((smp = pip->pif_sigmgr) == NULL) { + error = ENOENT; + goto out; + } /* * Let sigmgr handle it from here */ - err = (*smp->sm_ioctl)(AIOCS_SET_PRF, data, + error = (*smp->sm_ioctl)(AIOCS_SET_PRF, data, (caddr_t)pip->pif_siginst); break; default: - err = EOPNOTSUPP; + error = EOPNOTSUPP; + break; } break; } case AIOCINFO: - err = atm_dgram_info(data); + error = atm_dgram_info(data); break; default: - err = EOPNOTSUPP; + error = EOPNOTSUPP; } -out: ATM_OUTRO(); } diff --git a/sys/netproto/atm/atm_var.h b/sys/netproto/atm/atm_var.h index adb78ab3a0..b66b09d9ab 100644 --- a/sys/netproto/atm/atm_var.h +++ b/sys/netproto/atm/atm_var.h @@ -71,12 +71,13 @@ extern struct sp_info atm_attributes_pool; extern struct pr_usrreqs atm_dgram_usrreqs; struct lwkt_serialize; +union netmsg; /* * Global function declarations */ /* atm_aal5.c */ -int atm_aal5_ctloutput (struct socket *, struct sockopt *); +void atm_aal5_ctloutput (union netmsg *); void atm_aal5_init (void); /* atm_cm.c */ @@ -132,14 +133,6 @@ struct atm_pif * struct atm_nif * atm_nifname (char *); - /* atm_proto.c */ -int atm_proto_notsupp1 (struct socket *); -int atm_proto_notsupp2 (struct socket *, struct sockaddr *, - struct thread *); -int atm_proto_notsupp3 (struct socket *, struct sockaddr **); -int atm_proto_notsupp4 (struct socket *, int, KBuffer *, - struct sockaddr *, KBuffer *, struct thread *); - /* atm_signal.c */ int atm_sigmgr_register (struct sigmgr *); int atm_sigmgr_deregister (struct sigmgr *); diff --git a/sys/netproto/atm/kern_include.h b/sys/netproto/atm/kern_include.h index 4709a82a4f..0f7cd25134 100644 --- a/sys/netproto/atm/kern_include.h +++ b/sys/netproto/atm/kern_include.h @@ -62,7 +62,10 @@ #include #include #include + #include +#include +#include #include #include diff --git a/sys/netproto/ipsec/ipsec6.h b/sys/netproto/ipsec/ipsec6.h index 011edb6a4b..6fc1b22e2e 100644 --- a/sys/netproto/ipsec/ipsec6.h +++ b/sys/netproto/ipsec/ipsec6.h @@ -50,6 +50,7 @@ extern int ip6_ipsec_ecn; extern int ip6_esp_randpad; struct inpcb; +union netmsg; /* KAME compatibility shims */ #define ipsec6_getpolicybyaddr ipsec_getpolicybyaddr @@ -78,7 +79,7 @@ struct m_tag; extern int ipsec6_common_input(struct mbuf **mp, int *offp, int proto); extern int ipsec6_common_input_cb(struct mbuf *m, struct secasvar *sav, int skip, int protoff, struct m_tag *mt); -extern void esp6_ctlinput(int, struct sockaddr *, void *); +extern void esp6_ctlinput(union netmsg *); struct ipsec_output_state; extern int ipsec6_output_trans (struct ipsec_output_state *, u_char *, diff --git a/sys/netproto/ipsec/ipsec_input.c b/sys/netproto/ipsec/ipsec_input.c index 18227a4f92..2376d41cac 100644 --- a/sys/netproto/ipsec/ipsec_input.c +++ b/sys/netproto/ipsec/ipsec_input.c @@ -560,7 +560,7 @@ esp6_ctlinput(int cmd, struct sockaddr *sa, void *d) } } -extern struct ip6protosw inet6sw[]; +extern struct protosw inet6sw[]; extern u_char ip6_protox[]; /* diff --git a/sys/netproto/ipx/ipx_ip.c b/sys/netproto/ipx/ipx_ip.c index 5602ddffba..b2e000c831 100644 --- a/sys/netproto/ipx/ipx_ip.c +++ b/sys/netproto/ipx/ipx_ip.c @@ -158,9 +158,10 @@ static struct mbuf *ipxip_badlen; static struct mbuf *ipxip_lastin; static int ipxip_hold_input; -void -ipxip_input(struct mbuf *m, ...) +int +ipxip_input(struct mbuf **mp, int *offp, int proto) { + struct mbuf *m = *mp; struct ip *ip; struct ipx *ipx; int len, s; @@ -179,7 +180,7 @@ ipxip_input(struct mbuf *m, ...) if (((m->m_flags & M_EXT) || m->m_len < s) && (m = m_pullup(m, s)) == NULL) { ipxipif.if_ierrors++; - return; + return(IPPROTO_DONE); } ip = mtod(m, struct ip *); if (ip->ip_hl > (sizeof(struct ip) >> 2)) { @@ -187,7 +188,7 @@ ipxip_input(struct mbuf *m, ...) if (m->m_len < s) { if ((m = m_pullup(m, s)) == NULL) { ipxipif.if_ierrors++; - return; + return(IPPROTO_DONE); } ip = mtod(m, struct ip *); } @@ -210,7 +211,7 @@ ipxip_input(struct mbuf *m, ...) if (ipxip_badlen) m_freem(ipxip_badlen); ipxip_badlen = m; - return; + return(IPPROTO_DONE); } /* Any extra will be trimmed off by the IPX routines */ } @@ -219,6 +220,7 @@ ipxip_input(struct mbuf *m, ...) * Deliver to IPX */ netisr_queue(NETISR_IPX, m); + return(IPPROTO_DONE); } static int @@ -411,17 +413,19 @@ ipxip_free(struct ifnet *ifp) } void -ipxip_ctlinput(int cmd, struct sockaddr *sa, void *dummy) +ipxip_ctlinput(netmsg_t msg) { + int cmd = msg->ctlinput.nm_cmd; + struct sockaddr *sa = msg->ctlinput.nm_data; struct sockaddr_in *sin; if ((unsigned)cmd >= PRC_NCMDS) - return; + goto out; if (sa->sa_family != AF_INET && sa->sa_family != AF_IMPLINK) - return; + goto out; sin = (struct sockaddr_in *)sa; if (sin->sin_addr.s_addr == INADDR_ANY) - return; + goto out; switch (cmd) { @@ -433,6 +437,8 @@ ipxip_ctlinput(int cmd, struct sockaddr *sa, void *dummy) ipxip_rtchange(&sin->sin_addr); break; } +out: + lwkt_replymsg(&msg->lmsg, 0); } static void diff --git a/sys/netproto/ipx/ipx_ip.h b/sys/netproto/ipx/ipx_ip.h index 0fefe7bb85..597da358f6 100644 --- a/sys/netproto/ipx/ipx_ip.h +++ b/sys/netproto/ipx/ipx_ip.h @@ -52,8 +52,10 @@ struct ifnet_en { #ifdef _KERNEL -void ipxip_ctlinput (int cmd, struct sockaddr *sa, void *arg); -void ipxip_input (struct mbuf *m, ...); +union netmsg; + +void ipxip_ctlinput (union netmsg *); +int ipxip_input (struct mbuf **mp, int *offp, int); int ipxip_route (struct socket *so, struct sockopt *sopt); #endif diff --git a/sys/netproto/key/keysock.c b/sys/netproto/key/keysock.c index 37d925fccf..903ce5dd6b 100644 --- a/sys/netproto/key/keysock.c +++ b/sys/netproto/key/keysock.c @@ -1,7 +1,3 @@ -/* $FreeBSD: src/sys/netkey/keysock.c,v 1.1.2.4 2003/01/11 19:10:59 ume Exp $ */ -/* $DragonFly: src/sys/netproto/key/keysock.c,v 1.21 2008/11/01 04:22:16 sephe Exp $ */ -/* $KAME: keysock.c,v 1.25 2001/08/13 20:07:41 itojun Exp $ */ - /* * Copyright (C) 1995, 1996, 1997, and 1998 WIDE Project. * All rights reserved. @@ -29,6 +25,10 @@ * LIABILITY, OR TORT (INCLUDING NEGLIGENCE OR OTHERWISE) ARISING IN ANY WAY * OUT OF THE USE OF THIS SOFTWARE, EVEN IF ADVISED OF THE POSSIBILITY OF * SUCH DAMAGE. + * + * $FreeBSD: src/sys/netkey/keysock.c,v 1.1.2.4 2003/01/11 19:10:59 ume Exp $ + * $DragonFly: src/sys/netproto/key/keysock.c,v 1.21 2008/11/01 04:22:16 sephe Exp $ + * $KAME: keysock.c,v 1.25 2001/08/13 20:07:41 itojun Exp $ */ #include "opt_ipsec.h" @@ -47,13 +47,18 @@ #include #include #include + #include +#include #include #include +#include #include #include +#include + #include "keydb.h" #include "key.h" #include "keysock.h" @@ -368,31 +373,38 @@ key_sendup_mbuf(struct socket *so, struct mbuf *m, int target) * key_abort() * derived from net/rtsock.c:rts_abort() */ -static int -key_abort(struct socket *so) +static void +key_abort(netmsg_t msg) { - int error; - lwkt_gettoken(&key_token); - error = raw_usrreqs.pru_abort(so); - lwkt_reltoken(&key_token); - return error; + raw_usrreqs.pru_abort(msg); + /* msg invalid now */ + + lwkt_reltoken(&key_token); } /* * key_attach() * derived from net/rtsock.c:rts_attach() */ -static int -key_attach(struct socket *so, int proto, struct pru_attach_info *ai) +static void +key_attach(netmsg_t msg) { + struct socket *so = msg->attach.base.nm_so; + int proto = msg->attach.nm_proto; + struct pru_attach_info *ai = msg->attach.nm_ai; struct keycb *kp; + struct netmsg_pru_attach smsg; int error; - if (sotorawcb(so) != 0) - return EISCONN; /* XXX panic? */ - kp = (struct keycb *)kmalloc(sizeof *kp, M_PCB, M_WAITOK | M_ZERO); /* XXX */ + if (sotorawcb(so) != 0) { + error = EISCONN; /* XXX panic? */ + goto out; + } + + /* XXX */ + kp = kmalloc(sizeof *kp, M_PCB, M_WAITOK | M_ZERO); /* * The critical section is necessary to block protocols from sending @@ -403,13 +415,22 @@ key_attach(struct socket *so, int proto, struct pru_attach_info *ai) */ lwkt_gettoken(&key_token); so->so_pcb = (caddr_t)kp; - error = raw_usrreqs.pru_attach(so, proto, ai); + + netmsg_init(&smsg.base, so, &netisr_adone_rport, 0, + raw_usrreqs.pru_attach); + smsg.base.lmsg.ms_flags &= ~(MSGF_REPLY | MSGF_DONE); + smsg.base.lmsg.ms_flags |= MSGF_SYNC; + smsg.nm_proto = proto; + smsg.nm_ai = ai; + raw_usrreqs.pru_attach((netmsg_t)&smsg); + error = smsg.base.lmsg.ms_error; + kp = (struct keycb *)sotorawcb(so); if (error) { kfree(kp, M_PCB); so->so_pcb = (caddr_t) 0; lwkt_reltoken(&key_token); - return error; + goto out; } kp->kp_promisc = kp->kp_registered = 0; @@ -423,147 +444,163 @@ key_attach(struct socket *so, int proto, struct pru_attach_info *ai) so->so_options |= SO_USELOOPBACK; lwkt_reltoken(&key_token); - return 0; + error = 0; +out: + lwkt_replymsg(&msg->attach.base.lmsg, error); } /* * key_bind() * derived from net/rtsock.c:rts_bind() */ -static int -key_bind(struct socket *so, struct sockaddr *nam, struct thread *td) +static void +key_bind(netmsg_t msg) { - int error; - lwkt_gettoken(&key_token); - error = raw_usrreqs.pru_bind(so, nam, td); /* xxx just EINVAL */ + + raw_usrreqs.pru_bind(msg); /* xxx just EINVAL */ + /* msg invalid now */ + lwkt_reltoken(&key_token); - return error; } /* * key_connect() * derived from net/rtsock.c:rts_connect() */ -static int -key_connect(struct socket *so, struct sockaddr *nam, struct thread *td) +static void +key_connect(netmsg_t msg) { - int error; - lwkt_gettoken(&key_token); - error = raw_usrreqs.pru_connect(so, nam, td); /* XXX just EINVAL */ + + raw_usrreqs.pru_connect(msg); /* XXX just EINVAL */ + /* msg invalid now */ + lwkt_reltoken(&key_token); - return error; } /* * key_detach() * derived from net/rtsock.c:rts_detach() */ -static int -key_detach(struct socket *so) +static void +key_detach(netmsg_t msg) { + struct socket *so = msg->detach.base.nm_so; struct keycb *kp = (struct keycb *)sotorawcb(so); - int error; lwkt_gettoken(&key_token); - if (kp != 0) { - if (kp->kp_raw.rcb_proto.sp_protocol - == PF_KEY) /* XXX: AF_KEY */ + + if (kp != NULL) { + if (kp->kp_raw.rcb_proto.sp_protocol == PF_KEY) { + /* XXX: AF_KEY */ key_cb.key_count--; + } key_cb.any_count--; key_freereg(so); } - error = raw_usrreqs.pru_detach(so); + raw_usrreqs.pru_detach(msg); + /* msg invalid now */ + lwkt_reltoken(&key_token); - return error; } /* * key_disconnect() * derived from net/rtsock.c:key_disconnect() */ -static int -key_disconnect(struct socket *so) +static void +key_disconnect(netmsg_t msg) { - int error; - lwkt_gettoken(&key_token); - error = raw_usrreqs.pru_disconnect(so); + + raw_usrreqs.pru_disconnect(msg); + /* msg invalid now */ + lwkt_reltoken(&key_token); - return error; } /* * key_peeraddr() * derived from net/rtsock.c:rts_peeraddr() */ -static int -key_peeraddr(struct socket *so, struct sockaddr **nam) +static void +key_peeraddr(netmsg_t msg) { - int error; - lwkt_gettoken(&key_token); - error = raw_usrreqs.pru_peeraddr(so, nam); + + raw_usrreqs.pru_peeraddr(msg); + /* msg invalid now */ + lwkt_reltoken(&key_token); - return error; } /* * key_send() * derived from net/rtsock.c:rts_send() */ -static int -key_send(struct socket *so, int flags, struct mbuf *m, struct sockaddr *nam, - struct mbuf *control, struct thread *td) +static void +key_send(netmsg_t msg) { - int error; - lwkt_gettoken(&key_token); - error = raw_usrreqs.pru_send(so, flags, m, nam, control, td); + + raw_usrreqs.pru_send(msg); + /* msg invalid now */ + lwkt_reltoken(&key_token); - return error; } /* * key_shutdown() * derived from net/rtsock.c:rts_shutdown() */ -static int -key_shutdown(struct socket *so) +static void +key_shutdown(netmsg_t msg) { - int error; - lwkt_gettoken(&key_token); - error = raw_usrreqs.pru_shutdown(so); + + raw_usrreqs.pru_shutdown(msg); + /* msg invalid now */ + lwkt_reltoken(&key_token); - return error; } /* * key_sockaddr() * derived from net/rtsock.c:rts_sockaddr() */ -static int -key_sockaddr(struct socket *so, struct sockaddr **nam) +static void +key_sockaddr(netmsg_t msg) { - int error; - lwkt_gettoken(&key_token); - error = raw_usrreqs.pru_sockaddr(so, nam); + + raw_usrreqs.pru_sockaddr(msg); + /* msg invalid now */ + lwkt_reltoken(&key_token); - return error; } struct pr_usrreqs key_usrreqs = { - key_abort, pru_accept_notsupp, key_attach, key_bind, - key_connect, - pru_connect2_notsupp, pru_control_notsupp, key_detach, - key_disconnect, pru_listen_notsupp, key_peeraddr, - pru_rcvd_notsupp, - pru_rcvoob_notsupp, key_send, pru_sense_null, key_shutdown, - key_sockaddr, sosend, soreceive + .pru_abort = key_abort, + .pru_accept = pr_generic_notsupp, + .pru_attach = key_attach, + .pru_bind = key_bind, + .pru_connect = key_connect, + .pru_connect2 = pr_generic_notsupp, + .pru_control = pr_generic_notsupp, + .pru_detach = key_detach, + .pru_disconnect = key_disconnect, + .pru_listen = pr_generic_notsupp, + .pru_peeraddr = key_peeraddr, + .pru_rcvd = pr_generic_notsupp, + .pru_rcvoob = pr_generic_notsupp, + .pru_send = key_send, + .pru_sense = pru_sense_null, + .pru_shutdown = key_shutdown, + .pru_sockaddr = key_sockaddr, + .pru_sosend = sosend, + .pru_soreceive = soreceive }; /* sysctl */ @@ -576,12 +613,21 @@ SYSCTL_NODE(_net, PF_KEY, key, CTLFLAG_RW, 0, "Key Family"); extern struct domain keydomain; struct protosw keysw[] = { -{ SOCK_RAW, &keydomain, PF_KEY_V2, PR_ATOMIC|PR_ADDR, - 0, key_output, raw_ctlinput, 0, - cpu0_soport, cpu0_ctlport, - raw_init, 0, 0, 0, - &key_usrreqs -} + { + .pr_type = SOCK_RAW, + .pr_domain = &keydomain, + .pr_protocol = PF_KEY_V2, + .pr_flags = PR_ATOMIC|PR_ADDR, + + .pr_input = NULL, + .pr_output = key_output, + .pr_ctlinput = raw_ctlinput, + .pr_ctloutput = NULL, + + .pr_ctlport = cpu0_ctlport, + .pr_init = raw_init, + .pr_usrreqs = &key_usrreqs + } }; struct domain keydomain = { diff --git a/sys/sys/protosw.h b/sys/sys/protosw.h index f7166950bb..37ea1e2734 100644 --- a/sys/sys/protosw.h +++ b/sys/sys/protosw.h @@ -55,6 +55,11 @@ struct pr_output_info { #if defined(_KERNEL) || defined(_KERNEL_STRUCTURES) +/* + * netmsg_t union of possible netmsgs typically sent to protocol threads. + */ +typedef union netmsg *netmsg_t; + /* * Protocol switch table. * @@ -82,29 +87,37 @@ struct protosw { const struct domain *pr_domain; /* domain protocol a member of */ short pr_protocol; /* protocol number */ short pr_flags; /* see below */ -/* protocol-protocol hooks */ - void (*pr_input) (struct mbuf *, ...); + + /* + * Protocol hooks. These are typically called directly within the + * context of a protocol thread based on the toeplitz hash. + * + * pr_input() is called using the port supplied by the toeplitz + * hash via the netisr port function. + * + * pr_ctlinput() is called using the port supplied by pr_ctlport + * + * pr_ctloutput() and pr_output() are typically called + */ + int (*pr_input)(struct mbuf **, int *, int); /* input to protocol (from below) */ - int (*pr_output) (struct mbuf *, struct socket *, ...); + int (*pr_output)(struct mbuf *, struct socket *, ...); /* output to protocol (from above) */ - void (*pr_ctlinput)(int, struct sockaddr *, void *); + void (*pr_ctlinput)(union netmsg *); /* control input (from below) */ - int (*pr_ctloutput)(struct socket *, struct sockopt *); + void (*pr_ctloutput)(union netmsg *); /* control output (from above) */ -/* user-protocol hooks */ - struct lwkt_port *(*pr_mport)(struct socket *, struct sockaddr *, - struct mbuf **); struct lwkt_port *(*pr_ctlport)(int, struct sockaddr *, void *); -/* utility hooks */ + /* + * Utility hooks, not called with any particular context. + */ void (*pr_init) (void); /* initialization hook */ - void (*pr_fasttimo) (void); - /* fast timeout (200ms) */ - void (*pr_slowtimo) (void); - /* slow timeout (500ms) */ - void (*pr_drain) (void); - /* flush any excess space possible */ - struct pr_usrreqs *pr_usrreqs; /* supersedes pr_usrreq() */ + void (*pr_fasttimo) (void); /* fast timeout (200ms) */ + void (*pr_slowtimo) (void); /* slow timeout (500ms) */ + void (*pr_drain) (void); /* flush any excess space possible */ + + struct pr_usrreqs *pr_usrreqs; /* messaged requests to proto thread */ }; #endif @@ -130,6 +143,7 @@ struct protosw { #define PR_LASTHDR 0x40 /* enforce ipsec policy; last header */ #define PR_ADDR_OPT 0x80 /* allow addresses during delivery */ #define PR_MPSAFE 0x0100 /* protocal is MPSAFE */ +#define PR_SYNC_PORT 0x0200 /* synchronous port (no proto thrds) */ /* * The arguments to usrreq are: @@ -200,49 +214,46 @@ struct pru_attach_info { }; /* - * If the ordering here looks odd, that's because it's alphabetical. - * Having this structure separated out from the main protoswitch is allegedly - * a big (12 cycles per call) lose on high-end CPUs. We will eventually - * migrate this stuff back into the main structure. + * These are netmsg'd requests almost universally in the context of the + * appropriate protocol thread. Exceptions: + * + * pru_accept() - called synchronously from user context + * + * pru_sosend() - called synchronously from user context, typically + * runs generic kernel code and then messages via + * pru_send(). + * + * pru_soreceive() - called synchronously from user context. Typically + * runs generic kernel code and remains synchronous. */ struct pr_usrreqs { - int (*pru_abort) (struct socket *so); - int (*pru_accept) (struct socket *so, struct sockaddr **nam); - int (*pru_attach) (struct socket *so, int proto, - struct pru_attach_info *ai); - int (*pru_bind) (struct socket *so, struct sockaddr *nam, - struct thread *td); - int (*pru_connect) (struct socket *so, struct sockaddr *nam, - struct thread *td); - int (*pru_connect2) (struct socket *so1, struct socket *so2); - int (*pru_control) (struct socket *so, u_long cmd, caddr_t data, - struct ifnet *ifp, struct thread *td); - int (*pru_detach) (struct socket *so); - int (*pru_disconnect) (struct socket *so); - int (*pru_listen) (struct socket *so, struct thread *td); - int (*pru_peeraddr) (struct socket *so, - struct sockaddr **nam); - int (*pru_rcvd) (struct socket *so, int flags); - int (*pru_rcvoob) (struct socket *so, struct mbuf *m, - int flags); - int (*pru_send) (struct socket *so, int flags, struct mbuf *m, - struct sockaddr *addr, struct mbuf *control, - struct thread *td); -#define PRUS_OOB 0x1 -#define PRUS_EOF 0x2 -#define PRUS_MORETOCOME 0x4 - int (*pru_sense) (struct socket *so, struct stat *sb); - int (*pru_shutdown) (struct socket *so); - int (*pru_sockaddr) (struct socket *so, - struct sockaddr **nam); - + void (*pru_abort) (netmsg_t msg); + void (*pru_accept) (netmsg_t msg); /* synchronous call */ + void (*pru_attach) (netmsg_t msg); + void (*pru_bind) (netmsg_t msg); + void (*pru_connect) (netmsg_t msg); + void (*pru_connect2) (netmsg_t msg); + void (*pru_control) (netmsg_t msg); + void (*pru_detach) (netmsg_t msg); + void (*pru_disconnect) (netmsg_t msg); + void (*pru_listen) (netmsg_t msg); + void (*pru_peeraddr) (netmsg_t msg); + void (*pru_rcvd) (netmsg_t msg); + void (*pru_rcvoob) (netmsg_t msg); + void (*pru_send) (netmsg_t msg); + void (*pru_sense) (netmsg_t msg); + void (*pru_shutdown) (netmsg_t msg); + void (*pru_sockaddr) (netmsg_t msg); + /* - * These three added later, so they are out of order. They are used - * for shortcutting (fast path input/output) in some protocols. - * XXX - that's a lie, they are not implemented yet - * Rather than calling sosend() etc. directly, calls are made - * through these entry points. For protocols which still use - * the generic code, these just point to those routines. + * These are direct calls. Note that sosend() will sometimes + * be converted into an implied connect (pru_connect) with the + * mbufs and flags forwarded in pru_connect's netmsg. It is + * otherwise typically converted to a send (pru_send). + * + * soreceive() typically remains synchronous in the user's context. + * + * Any converted calls are netmsg's to the socket's protocol thread. */ int (*pru_sosend) (struct socket *so, struct sockaddr *addr, struct uio *uio, struct mbuf *top, @@ -253,34 +264,8 @@ struct pr_usrreqs { struct uio *uio, struct sockbuf *sio, struct mbuf **controlp, int *flagsp); - int (*pru_ctloutput) (struct socket *so, struct sockopt *sopt); }; -typedef int (*pru_abort_fn_t) (struct socket *so); -typedef int (*pru_accept_fn_t) (struct socket *so, struct sockaddr **nam); -typedef int (*pru_attach_fn_t) (struct socket *so, int proto, - struct pru_attach_info *ai); -typedef int (*pru_bind_fn_t) (struct socket *so, struct sockaddr *nam, - struct thread *td); -typedef int (*pru_connect_fn_t) (struct socket *so, struct sockaddr *nam, - struct thread *td); -typedef int (*pru_connect2_fn_t) (struct socket *so1, struct socket *so2); -typedef int (*pru_control_fn_t) (struct socket *so, u_long cmd, caddr_t data, - struct ifnet *ifp, - struct thread *td); -typedef int (*pru_detach_fn_t) (struct socket *so); -typedef int (*pru_disconnect_fn_t) (struct socket *so); -typedef int (*pru_listen_fn_t) (struct socket *so, struct thread *td); -typedef int (*pru_peeraddr_fn_t) (struct socket *so, struct sockaddr **nam); -typedef int (*pru_rcvd_fn_t) (struct socket *so, int flags); -typedef int (*pru_rcvoob_fn_t) (struct socket *so, struct mbuf *m, int flags); -typedef int (*pru_send_fn_t) (struct socket *so, int flags, struct mbuf *m, - struct sockaddr *addr, - struct mbuf *control, - struct thread *td); -typedef int (*pru_sense_fn_t) (struct socket *so, struct stat *sb); -typedef int (*pru_shutdown_fn_t) (struct socket *so); -typedef int (*pru_sockaddr_fn_t) (struct socket *so, struct sockaddr **nam); typedef int (*pru_sosend_fn_t) (struct socket *so, struct sockaddr *addr, struct uio *uio, struct mbuf *top, struct mbuf *control, int flags, @@ -290,24 +275,10 @@ typedef int (*pru_soreceive_fn_t) (struct socket *so, struct sockaddr **paddr, struct sockbuf *sio, struct mbuf **controlp, int *flagsp); -typedef int (*pru_ctloutput_fn_t) (struct socket *so, struct sockopt *sopt); -typedef void (*pru_ctlinput_fn_t) (int cmd, struct sockaddr *arg, void *extra); -int pru_accept_notsupp (struct socket *so, struct sockaddr **nam); -int pru_bind_notsupp (struct socket *so, struct sockaddr *nam, - struct thread *td); -int pru_connect_notsupp (struct socket *so, struct sockaddr *nam, - struct thread *td); -int pru_connect2_notsupp (struct socket *so1, struct socket *so2); -int pru_control_notsupp (struct socket *so, u_long cmd, caddr_t data, - struct ifnet *ifp, struct thread *td); -int pru_disconnect_notsupp (struct socket *so); -int pru_listen_notsupp (struct socket *so, struct thread *td); -int pru_peeraddr_notsupp (struct socket *so, struct sockaddr **nam); -int pru_rcvd_notsupp (struct socket *so, int flags); -int pru_rcvoob_notsupp (struct socket *so, struct mbuf *m, int flags); -int pru_shutdown_notsupp(struct socket *so); -int pru_sockaddr_notsupp(struct socket *so, struct sockaddr **nam); +void pr_generic_notsupp(netmsg_t msg); +void pru_sense_null(netmsg_t msg); + int pru_sosend_notsupp(struct socket *so, struct sockaddr *addr, struct uio *uio, struct mbuf *top, struct mbuf *control, int flags, @@ -317,14 +288,10 @@ int pru_soreceive_notsupp(struct socket *so, struct uio *uio, struct sockbuf *sio, struct mbuf **controlp, int *flagsp); -int pru_ctloutput_notsupp(struct socket *so, struct sockopt *sopt); -int pru_sense_null (struct socket *so, struct stat *sb); struct lwkt_port *cpu0_soport(struct socket *, struct sockaddr *, struct mbuf **); struct lwkt_port *cpu0_ctlport(int, struct sockaddr *, void *); -struct lwkt_port *sync_soport(struct socket *, struct sockaddr *, - struct mbuf **); #endif /* _KERNEL || _KERNEL_STRUCTURES */ diff --git a/sys/sys/socketops.h b/sys/sys/socketops.h index d965fcd3c2..e2f2d474fc 100644 --- a/sys/sys/socketops.h +++ b/sys/sys/socketops.h @@ -59,15 +59,16 @@ */ static __inline int so_pru_sosend(struct socket *so, struct sockaddr *addr, struct uio *uio, - struct mbuf *top, struct mbuf *control, int flags, struct thread *td) + struct mbuf *top, struct mbuf *control, int flags, + struct thread *td) { return ((*so->so_proto->pr_usrreqs->pru_sosend)(so, addr, uio, top, - control, flags, td)); + control, flags, td)); } static __inline int so_pru_soreceive(struct socket *so, struct sockaddr **paddr, struct uio *uio, - struct sockbuf *sio, struct mbuf **controlp, int *flagsp) + struct sockbuf *sio, struct mbuf **controlp, int *flagsp) { return ((*so->so_proto->pr_usrreqs->pru_soreceive)(so, paddr, uio, sio, controlp, flagsp)); @@ -76,12 +77,14 @@ so_pru_soreceive(struct socket *so, struct sockaddr **paddr, struct uio *uio, void so_pru_abort (struct socket *so); void so_pru_aborta (struct socket *so); void so_pru_abort_oncpu (struct socket *so); -int so_pru_accept (struct socket *so, struct sockaddr **nam); +int so_pru_accept_direct(struct socket *so, struct sockaddr **nam); int so_pru_attach (struct socket *so, int proto, struct pru_attach_info *ai); +int so_pru_attach_direct(struct socket *so, int proto, + struct pru_attach_info *ai); int so_pru_bind (struct socket *so, struct sockaddr *nam, struct thread *td); int so_pru_connect (struct socket *so, struct sockaddr *nam, struct thread *td); int so_pru_connect2 (struct socket *so1, struct socket *so2); -int so_pru_control (struct socket *so, u_long cmd, caddr_t data, +int so_pru_control_direct(struct socket *so, u_long cmd, caddr_t data, struct ifnet *ifp); int so_pru_detach (struct socket *so); int so_pru_disconnect (struct socket *so); @@ -95,7 +98,7 @@ int so_pru_send (struct socket *so, int flags, struct mbuf *m, int so_pru_sense (struct socket *so, struct stat *sb); int so_pru_shutdown (struct socket *so); int so_pru_sockaddr (struct socket *so, struct sockaddr **nam); -int so_pru_ctloutput(struct socket *so, struct sockopt *sopt); +int so_pr_ctloutput(struct socket *so, struct sockopt *sopt); void so_pru_ctlinput(struct protosw *pr, int cmd, struct sockaddr *arg, void *extra); diff --git a/sys/sys/un.h b/sys/sys/un.h index b47b8eb2af..3cb4c7f37c 100644 --- a/sys/sys/un.h +++ b/sys/sys/un.h @@ -65,7 +65,7 @@ struct sockopt; int uipc_usrreq (struct socket *so, int req, struct mbuf *m, struct mbuf *nam, struct mbuf *control); -int uipc_ctloutput (struct socket *so, struct sockopt *sopt); +void uipc_ctloutput (union netmsg *msg); int unp_connect2 (struct socket *so, struct socket *so2); void unp_dispose (struct mbuf *m); void unp_revoke_gc (struct file *fx); -- 2.41.0