Re: Remove rti_ifp from struct rt_addrinfo
On Thu, Apr 24, 2014 at 02:52:27PM +0200, Martin Pieuchot wrote: On 24/04/14(Thu) 13:43, Henning Brauer wrote: * Martin Pieuchot mpieuc...@nolizard.org [2014-04-24 13:24]: This ifp pointer is only needed by rt_getifa() to find an address, so make it a local variable. The rtrequest1(9) change might introduce a negligible slowdown since I remove the already known ifp pointer. But this only happens in the case described in the comment just before and I would bet because of carp_setroute(), still nobody to fix this? It's not better than OpenSSL... In the rtsock chunk, the two pointers are equivalent. Ok? yup. And now with proper ifp initialization, pointed by bluhm@. OK bluhm@ Index: net/route.c === RCS file: /home/ncvs/src/sys/net/route.c,v retrieving revision 1.163 diff -u -p -r1.163 route.c --- net/route.c 23 Apr 2014 09:30:57 - 1.163 +++ net/route.c 24 Apr 2014 12:45:04 - @@ -691,16 +691,17 @@ int rt_getifa(struct rt_addrinfo *info, u_int rtid) { struct ifaddr *ifa; + struct ifnet*ifp = NULL; /* * ifp may be specified by sockaddr_dl when protocol address * is ambiguous */ - if (info-rti_ifp == NULL info-rti_info[RTAX_IFP] != NULL) { + if (info-rti_info[RTAX_IFP] != NULL) { struct sockaddr_dl *sdl; sdl = (struct sockaddr_dl *)info-rti_info[RTAX_IFP]; - info-rti_ifp = if_get(sdl-sdl_index); + ifp = if_get(sdl-sdl_index); } if (info-rti_ifa == NULL info-rti_info[RTAX_IFA] != NULL) @@ -713,8 +714,8 @@ rt_getifa(struct rt_addrinfo *info, u_in if ((sa = info-rti_info[RTAX_GATEWAY]) == NULL) sa = info-rti_info[RTAX_DST]; - if (sa != NULL info-rti_ifp != NULL) - info-rti_ifa = ifaof_ifpforaddr(sa, info-rti_ifp); + if (sa != NULL ifp != NULL) + info-rti_ifa = ifaof_ifpforaddr(sa, ifp); else if (info-rti_info[RTAX_DST] != NULL info-rti_info[RTAX_GATEWAY] != NULL) info-rti_ifa = ifa_ifwithroute(info-rti_flags, @@ -729,9 +730,6 @@ rt_getifa(struct rt_addrinfo *info, u_in if ((ifa = info-rti_ifa) == NULL) return (ENETUNREACH); - if (info-rti_ifp == NULL) - info-rti_ifp = ifa-ifa_ifp; - return (0); } @@ -828,8 +826,10 @@ rtrequest1(int req, struct rt_addrinfo * info-rti_ifa = rt-rt_ifa; } else { /* - * The interface address at the cloning route - * is not longer referenced by an interface. + * The address of the cloning route is not longer + * configured on an interface, but its descriptor + * is still there because of reference counting. + * * Try to find a similar active address and use * it for the cloned route. The cloning route * will get the new address and interface later. @@ -837,7 +837,6 @@ rtrequest1(int req, struct rt_addrinfo * info-rti_ifa = NULL; info-rti_info[RTAX_IFA] = rt-rt_ifa-ifa_addr; } - info-rti_ifp = rt-rt_ifp; info-rti_flags = rt-rt_flags ~(RTF_CLONING | RTF_STATIC); info-rti_flags |= RTF_CLONED; info-rti_info[RTAX_GATEWAY] = rt-rt_gateway; Index: net/route.h === RCS file: /home/ncvs/src/sys/net/route.h,v retrieving revision 1.91 diff -u -p -r1.91 route.h --- net/route.h 10 Apr 2014 13:47:21 - 1.91 +++ net/route.h 24 Apr 2014 12:45:04 - @@ -299,7 +299,6 @@ struct rt_addrinfo { struct sockaddr *rti_info[RTAX_MAX]; int rti_flags; struct ifaddr *rti_ifa; - struct ifnet *rti_ifp; struct rt_msghdr *rti_rtm; u_char rti_mpls; }; Index: net/rtsock.c === RCS file: /home/ncvs/src/sys/net/rtsock.c,v retrieving revision 1.142 diff -u -p -r1.142 rtsock.c --- net/rtsock.c 18 Mar 2014 10:47:34 - 1.142 +++ net/rtsock.c 24 Apr 2014 12:45:04 - @@ -768,7 +768,7 @@ report: ifafree(rt-rt_ifa); rt-rt_ifa = ifa; ifa-ifa_refcnt++; - rt-rt_ifp = info.rti_ifp; + rt-rt_ifp = ifa-ifa_ifp; #ifndef SMALL_KERNEL /* recheck link state after ifp
Re: Kill in_localaddr()
On Thu, Apr 24, 2014 at 04:41:06PM +0200, Martin Pieuchot wrote: in_localaddr() is used only once in our tree and only if the sysctl net.inet.ip.mtudisc is set to 0. It is used to optimize the size of the MSS if the forward address correspond to a host on one of our subnets. Since it's an optimization for a special case that's not enabled by default, I'd like to kill it to remove one usage of the global list of IPv4 addresses. While here get rid of the #ifdef RTV_MTU, it is here. ok? OK bluhm@ Index: netinet/in.c === RCS file: /home/ncvs/src/sys/netinet/in.c,v retrieving revision 1.95 diff -u -p -r1.95 in.c --- netinet/in.c 10 Apr 2014 13:47:21 - 1.95 +++ netinet/in.c 24 Apr 2014 14:33:43 - @@ -99,22 +99,6 @@ int in_scrubprefix(struct in_ifaddr *); int in_addhost(struct in_ifaddr *); int in_scrubhost(struct in_ifaddr *); -/* Return 1 if an internet address is for a directly connected host */ -int -in_localaddr(struct in_addr in, u_int rdomain) -{ - struct in_ifaddr *ia; - - rdomain = rtable_l2(rdomain); - TAILQ_FOREACH(ia, in_ifaddr, ia_list) { - if (ia-ia_ifp-if_rdomain != rdomain) - continue; - if ((in.s_addr ia-ia_netmask) == ia-ia_net) - return (1); - } - return (0); -} - /* * Determine whether an IP address is in a reserved set of addresses * that may not be forwarded, or whether datagrams to that destination Index: netinet/in.h === RCS file: /home/ncvs/src/sys/netinet/in.h,v retrieving revision 1.107 diff -u -p -r1.107 in.h --- netinet/in.h 21 Apr 2014 10:07:58 - 1.107 +++ netinet/in.h 24 Apr 2014 14:33:43 - @@ -778,7 +778,6 @@ int in_broadcast(struct in_addr, stru int in_canforward(struct in_addr); int in_cksum(struct mbuf *, int); int in4_cksum(struct mbuf *, u_int8_t, int, int); -int in_localaddr(struct in_addr, u_int); voidin_proto_cksum_out(struct mbuf *, struct ifnet *); voidin_ifdetach(struct ifnet *); int in_mask2len(struct in_addr *); Index: netinet/tcp_input.c === RCS file: /home/ncvs/src/sys/netinet/tcp_input.c,v retrieving revision 1.275 diff -u -p -r1.275 tcp_input.c --- netinet/tcp_input.c 21 Apr 2014 12:22:26 - 1.275 +++ netinet/tcp_input.c 24 Apr 2014 14:33:43 - @@ -3040,7 +3040,6 @@ tcp_mss(struct tcpcb *tp, int offer) goto out; } -#ifdef RTV_MTU /* * if there's an mtu associated with the route and we support * path MTU discovery for the underlying protocol family, use it. @@ -3058,23 +3057,21 @@ tcp_mss(struct tcpcb *tp, int offer) */ mss = IPV6_MMTU - iphlen - sizeof(struct ip6_frag) - sizeof(struct tcphdr); - } else - mss = rt-rt_rmx.rmx_mtu - iphlen - sizeof(struct tcphdr); - } else -#endif /* RTV_MTU */ - if (!ifp) + } else { + mss = rt-rt_rmx.rmx_mtu - iphlen - + sizeof(struct tcphdr); + } + } else if (!ifp) { /* * ifp may be null and rmx_mtu may be zero in certain * v6 cases (e.g., if ND wasn't able to resolve the * destination host. */ goto out; - else if (ifp-if_flags IFF_LOOPBACK) + } else if (ifp-if_flags IFF_LOOPBACK) { mss = ifp-if_mtu - iphlen - sizeof(struct tcphdr); - else if (tp-pf == AF_INET) { + } else if (tp-pf == AF_INET) { if (ip_mtudisc) - mss = ifp-if_mtu - iphlen - sizeof(struct tcphdr); - else if (inp in_localaddr(inp-inp_faddr, inp-inp_rtableid)) mss = ifp-if_mtu - iphlen - sizeof(struct tcphdr); } #ifdef INET6
Re: Remove rti_ifp from struct rt_addrinfo
On Thu, Apr 24, 2014 at 01:43:16PM +0200, Henning Brauer wrote: * Martin Pieuchot mpieuc...@nolizard.org [2014-04-24 13:24]: This ifp pointer is only needed by rt_getifa() to find an address, so make it a local variable. The rtrequest1(9) change might introduce a negligible slowdown since I remove the already known ifp pointer. But this only happens in the case described in the comment just before and I would bet because of carp_setroute(), still nobody to fix this? It's not better than OpenSSL... In the rtsock chunk, the two pointers are equivalent. Ok? yup. the carp route fiddling is pretty damn mad, and with the route priorities and the ability to mark routes as down there should be a much cleaner way to do this these days. heck, the entire carp route fiddling needs to be reassesed. things changed, i can\t even fully remeber why it is there (i think it was about backup nodes still being able to reach a network only present on the carp if or the like), and i seem to remember it doesn't quite work as expected anyway, but don't take my word for it, memory REALLY fuzzy on that front. Years ago mpf@ told me, that the purpose of this function is to ssh from a carp master to a carp slave via the carp address. Or was it the other way around? The carp_setroute() function starts with the encouraging comment /* XXX this mess needs fixing */. When switching carp states fast, the routing table gets messed up. In our product we removed all calls to carp_setroute(sc, RTM_DELETE). There is one carp_setroute(sc, RTM_ADD) left. I don't know wether it is needed. I would recommend to try to delete the whole function and fix fallout if any. bluhm
Re: Remove rti_ifp from struct rt_addrinfo
On Fri, Apr 25, 2014 at 09:09:03AM +0900, Ryan McBride wrote: Part of the reason it's there is to make carp work properly for services listening on the carp interface, in particular so that hosts in the BACKUP state will reach the MASTER rather than trying and failing to connect to their own carp interface. Maybe not needed in all setups, but likely to break things if we simply remove it. Why do you want to connect from the BACKUP machine to the MASTER using CARP addresses? Just add another fixed address and you can do that. The current implementation may change the routing table in subtile ways until nothing works. In IPv6 the routes are fixed and there are less problems. bluhm
Re: [Patch] Add router alert option to igmp packets
On Sat, Apr 26, 2014 at 05:36:45PM +0200, Florian Riehm wrote: our IGMP packets don't contain router alert options. According rfc 2236 (Internet Group Management Protocol, Version 2) packets without this option have to be ignored. Some layer 3 switches are blocking our igmp packets because of that. The following patch is based on a FreeBSD patch long years ago: http://svnweb.freebsd.org/base?view=revisionrevision=14622 /* * To avoid byte-swapping the same value over and over again. */ FreeBSD has code matching this comment. In OpenBSD the code is gone and so should the comment. Of course that is unrelated to this diff. + /* + * Construct a Router Alert option to use in outgoing packets + */ The * must be aligned. + ra-ipopt_dst.s_addr = 0; Use INADDR_ANY instead of 0 as it is an IP address. Otherwise OK bluhm@
Re: rtadvd prints error on receiving RA with Route Information
On Wed, May 14, 2014 at 07:55:44PM +0200, J??r??mie Courr??ges-Anglas wrote: Redirecting this to tech@ Consus has confirmed this fixed his issue. I plan to commit it this week-end if I hear no objection. j...@wxcvbn.org (J??r??mie Courr??ges-Anglas) writes: Thanks for the detailed report. This diff makes rtadvd aware of route info messages on the listening side, no functional change except that the error message goes away. We just ignore the message since in that case there's no good reason to try to validate the more specifics advertized by other routers. ok? OK bluhm@ Index: rtadvd.c === RCS file: /cvs/src/usr.sbin/rtadvd/rtadvd.c,v retrieving revision 1.45 diff -u -p -r1.45 rtadvd.c --- rtadvd.c 5 May 2013 14:25:52 - 1.45 +++ rtadvd.c 6 May 2014 14:21:42 - @@ -121,6 +121,7 @@ union nd_opts { #define NDOPT_FLAG_MTU (1 4) #define NDOPT_FLAG_RDNSS (1 5) #define NDOPT_FLAG_DNSSL (1 6) +#define NDOPT_FLAG_ROUTE_INFO(1 7) u_int32_t ndopt_flags[] = { [ND_OPT_SOURCE_LINKADDR]= NDOPT_FLAG_SRCLINKADDR, @@ -128,6 +129,7 @@ u_int32_t ndopt_flags[] = { [ND_OPT_PREFIX_INFORMATION] = NDOPT_FLAG_PREFIXINFO, [ND_OPT_REDIRECTED_HEADER] = NDOPT_FLAG_RDHDR, [ND_OPT_MTU]= NDOPT_FLAG_MTU, + [ND_OPT_ROUTE_INFO] = NDOPT_FLAG_ROUTE_INFO, [ND_OPT_RDNSS] = NDOPT_FLAG_RDNSS, [ND_OPT_DNSSL] = NDOPT_FLAG_DNSSL, }; @@ -809,7 +811,8 @@ ra_input(int len, struct nd_router_adver if (nd6_options((struct nd_opt_hdr *)(ra + 1), len - sizeof(struct nd_router_advert), ndopts, NDOPT_FLAG_SRCLINKADDR | NDOPT_FLAG_PREFIXINFO - | NDOPT_FLAG_MTU | NDOPT_FLAG_RDNSS | NDOPT_FLAG_DNSSL)) { + | NDOPT_FLAG_MTU | NDOPT_FLAG_ROUTE_INFO + | NDOPT_FLAG_RDNSS | NDOPT_FLAG_DNSSL)) { log_warnx(ND option check failed for an RA from %s on %s, inet_ntop(AF_INET6, from-sin6_addr, ntopbuf, INET6_ADDRSTRLEN), @@ -1109,6 +1112,7 @@ nd6_options(struct nd_opt_hdr *hdr, int } if (hdr-nd_opt_type ND_OPT_MTU + hdr-nd_opt_type != ND_OPT_ROUTE_INFO hdr-nd_opt_type != ND_OPT_RDNSS hdr-nd_opt_type != ND_OPT_DNSSL) { @@ -1142,6 +1146,7 @@ nd6_options(struct nd_opt_hdr *hdr, int case ND_OPT_SOURCE_LINKADDR: case ND_OPT_TARGET_LINKADDR: case ND_OPT_REDIRECTED_HEADER: + case ND_OPT_ROUTE_INFO: case ND_OPT_RDNSS: case ND_OPT_DNSSL: break; /* we don't care about these options */ -- jca | PGP : 0x1524E7EE / 5135 92C1 AD36 5293 2BDF DDCC 0DFA 74AE 1524 E7EE
Re: IFT_L2VLAN is unused
On Wed, May 14, 2014 at 11:51:13PM +0200, Henning Brauer wrote: don't kill the define, since this is userland visible, but there is never ever an interface in our kernel with if_type == IFT_L2VLAN - see my commit from 2 weeks ago or so. To clarify this once again, I didn't remove the L2VLAN use, it was never really used. ok? OK bluhm@ Index: net/if.c === RCS file: /cvs/src/sys/net/if.c,v retrieving revision 1.288 diff -u -p -r1.288 if.c --- net/if.c 13 May 2014 14:33:25 - 1.288 +++ net/if.c 14 May 2014 21:41:01 - @@ -1625,7 +1625,6 @@ ifioctl(struct socket *so, u_long cmd, c case IFT_CARP: case IFT_XETHER: case IFT_ISO88025: - case IFT_L2VLAN: bcopy((caddr_t)ifr-ifr_addr.sa_data, (caddr_t)((struct arpcom *)ifp)-ac_enaddr, ETHER_ADDR_LEN); Index: net/if_pppoe.c === RCS file: /cvs/src/sys/net/if_pppoe.c,v retrieving revision 1.38 diff -u -p -r1.38 if_pppoe.c --- net/if_pppoe.c14 Apr 2014 09:06:42 - 1.38 +++ net/if_pppoe.c24 Apr 2014 23:38:10 - @@ -924,9 +924,7 @@ pppoe_ioctl(struct ifnet *ifp, unsigned struct ifnet*eth_if; eth_if = ifunit(parms-eth_ifname); - if (eth_if == NULL || - (eth_if-if_type != IFT_ETHER - eth_if-if_type != IFT_L2VLAN)) { + if (eth_if == NULL || eth_if-if_type != IFT_ETHER) { sc-sc_eth_if = NULL; return (ENXIO); } Index: netinet6/nd6.c === RCS file: /cvs/src/sys/netinet6/nd6.c,v retrieving revision 1.116 diff -u -p -r1.116 nd6.c --- netinet6/nd6.c7 May 2014 08:14:59 - 1.116 +++ netinet6/nd6.c13 May 2014 14:38:16 - @@ -1830,7 +1830,6 @@ nd6_need_cache(struct ifnet *ifp) case IFT_ETHER: case IFT_IEEE1394: case IFT_PROPVIRTUAL: - case IFT_L2VLAN: case IFT_IEEE80211: case IFT_CARP: case IFT_GIF: /* XXX need more cases? */ Index: netinet6/nd6_nbr.c === RCS file: /cvs/src/sys/netinet6/nd6_nbr.c,v retrieving revision 1.78 diff -u -p -r1.78 nd6_nbr.c --- netinet6/nd6_nbr.c18 Apr 2014 10:48:30 - 1.78 +++ netinet6/nd6_nbr.c24 Apr 2014 23:38:10 - @@ -1064,7 +1064,6 @@ nd6_ifptomac(struct ifnet *ifp) case IFT_IEEE1394: case IFT_PROPVIRTUAL: case IFT_CARP: - case IFT_L2VLAN: case IFT_IEEE80211: return ((caddr_t)(ifp + 1)); default: -- Henning Brauer, h...@bsws.de, henn...@openbsd.org BS Web Services GmbH, http://bsws.de, Full-Service ISP Secure Hosting, Mail and DNS. Virtual Dedicated Servers, Root to Fully Managed Henning Brauer Consulting, http://henningbrauer.com/
Re: divert(4) without mbuf tags
On Tue, Jul 08, 2014 at 11:39:12PM -0400, Lawrence Teo wrote: #ifdef INET6 case AF_INET6: - if (divert6_packet(pd.m, pd.dir) == 0) + if (!divert6_packet(pd.m, pd.dir, r-divert_packet.port)) *m0 = NULL; break; This line is longer that 80 characters. OK bluhm@
Re: apmd -A induced hangs
On Sun, Jul 13, 2014 at 04:05:41PM +0200, Mark Kettenis wrote: Some people have reported that apmd -A makes their machines hang. Could those people try the diff below and see whether it helps? I am running this diff and apmd -A on a thinkpad T430s. The machine is idle, the X11 blank screen saver is on. When I type something, it hangs. The fan gets loud after I type, it sounds like the cpu starts spinning when I want to work again. It happens with this diff and apmd -A. It happens without this diff and with apmd -A or apmd -C. I did not see the crash without this diff and without running apmd. But this test was not long enough to be reliable. Next I will try with this diff and without running apmd. It crashes about once a week so testing will take a while. bluhm Index: acpicpu.c === RCS file: /home/cvs/src/sys/dev/acpi/acpicpu.c,v retrieving revision 1.60 diff -u -p -r1.60 acpicpu.c --- acpicpu.c 12 Jul 2014 18:48:17 - 1.60 +++ acpicpu.c 13 Jul 2014 14:00:03 - @@ -202,9 +202,7 @@ acpicpu_set_pdc(struct acpicpu_softc *sc static uint8_t cpu_oscuuid[16] = { 0x16, 0xA6, 0x77, 0x40, 0x0C, 0x29, 0xBE, 0x47, 0x9E, 0xBD, 0xD8, 0x70, 0x58, 0x71, 0x39, 0x53 }; - cap = ACPI_PDC_C_C1_HALT | ACPI_PDC_P_FFH | ACPI_PDC_C_C1_FFH - | ACPI_PDC_C_C2C3_FFH | ACPI_PDC_SMP_P_SWCOORD | ACPI_PDC_SMP_C2C3 - | ACPI_PDC_SMP_C1PT; + cap = ACPI_PDC_P_FFH | ACPI_PDC_C_C1_FFH; if (aml_searchname(sc-sc_devnode, _OSC)) { /* Query _OSC */ OpenBSD 5.6-beta (GENERIC.MP) #87: Fri Jul 25 18:23:23 CEST 2014 bluhm@t430s.bluhm.invalid:/usr/src/sys/arch/amd64/compile/GENERIC.MP real mem = 16845570048 (16065MB) avail mem = 16388358144 (15629MB) mpath0 at root scsibus0 at mpath0: 256 targets mainbus0 at root bios0 at mainbus0: SMBIOS rev. 2.7 @ 0xbae9d000 (68 entries) bios0: vendor LENOVO version G7ET94WW (2.54 ) date 04/30/2013 bios0: LENOVO 2355CTO acpi0 at bios0: rev 2 acpi0: sleep states S0 S3 S4 S5 acpi0: tables DSDT FACP TCPA SSDT SSDT SSDT HPET APIC MCFG ECDT FPDT ASF! UEFI UEFI MSDM SSDT SSDT UEFI DBG2 acpi0: wakeup devices LID_(S4) SLPB(S3) IGBE(S4) EXP3(S4) XHCI(S3) EHC1(S3) EHC2(S3) HDEF(S4) acpitimer0 at acpi0: 3579545 Hz, 24 bits acpihpet0 at acpi0: 14318179 Hz acpimadt0 at acpi0 addr 0xfee0: PC-AT compat cpu0 at mainbus0: apid 0 (boot processor) cpu0: Intel(R) Core(TM) i7-3520M CPU @ 2.90GHz, 2893.82 MHz cpu0: FPU,VME,DE,PSE,TSC,MSR,PAE,MCE,CX8,APIC,SEP,MTRR,PGE,MCA,CMOV,PAT,PSE36,CFLUSH,DS,ACPI,MMX,FXSR,SSE,SSE2,SS,HTT,TM,PBE,SSE3,PCLMUL,DTES64,MWAIT,DS-CPL,VMX,SMX,EST,TM2,SSSE3,CX16,xTPR,PDCM,PCID,SSE4.1,SSE4.2,x2APIC,POPCNT,DEADLINE,AES,XSAVE,AVX,F16C,RDRAND,NXE,LONG,LAHF,PERF,ITSC,FSGSBASE,SMEP,ERMS cpu0: 256KB 64b/line 8-way L2 cache cpu0: smt 0, core 0, package 0 mtrr: Pentium Pro MTRR support, 10 var ranges, 88 fixed ranges cpu0: apic clock running at 99MHz cpu0: mwait min=64, max=64, C-substates=0.2.1.1.2, IBE cpu1 at mainbus0: apid 1 (application processor) cpu1: Intel(R) Core(TM) i7-3520M CPU @ 2.90GHz, 2893.43 MHz cpu1: FPU,VME,DE,PSE,TSC,MSR,PAE,MCE,CX8,APIC,SEP,MTRR,PGE,MCA,CMOV,PAT,PSE36,CFLUSH,DS,ACPI,MMX,FXSR,SSE,SSE2,SS,HTT,TM,PBE,SSE3,PCLMUL,DTES64,MWAIT,DS-CPL,VMX,SMX,EST,TM2,SSSE3,CX16,xTPR,PDCM,PCID,SSE4.1,SSE4.2,x2APIC,POPCNT,DEADLINE,AES,XSAVE,AVX,F16C,RDRAND,NXE,LONG,LAHF,PERF,ITSC,FSGSBASE,SMEP,ERMS cpu1: 256KB 64b/line 8-way L2 cache cpu1: smt 1, core 0, package 0 cpu2 at mainbus0: apid 2 (application processor) cpu2: Intel(R) Core(TM) i7-3520M CPU @ 2.90GHz, 2893.43 MHz cpu2: FPU,VME,DE,PSE,TSC,MSR,PAE,MCE,CX8,APIC,SEP,MTRR,PGE,MCA,CMOV,PAT,PSE36,CFLUSH,DS,ACPI,MMX,FXSR,SSE,SSE2,SS,HTT,TM,PBE,SSE3,PCLMUL,DTES64,MWAIT,DS-CPL,VMX,SMX,EST,TM2,SSSE3,CX16,xTPR,PDCM,PCID,SSE4.1,SSE4.2,x2APIC,POPCNT,DEADLINE,AES,XSAVE,AVX,F16C,RDRAND,NXE,LONG,LAHF,PERF,ITSC,FSGSBASE,SMEP,ERMS cpu2: 256KB 64b/line 8-way L2 cache cpu2: smt 0, core 1, package 0 cpu3 at mainbus0: apid 3 (application processor) cpu3: Intel(R) Core(TM) i7-3520M CPU @ 2.90GHz, 2893.43 MHz cpu3: FPU,VME,DE,PSE,TSC,MSR,PAE,MCE,CX8,APIC,SEP,MTRR,PGE,MCA,CMOV,PAT,PSE36,CFLUSH,DS,ACPI,MMX,FXSR,SSE,SSE2,SS,HTT,TM,PBE,SSE3,PCLMUL,DTES64,MWAIT,DS-CPL,VMX,SMX,EST,TM2,SSSE3,CX16,xTPR,PDCM,PCID,SSE4.1,SSE4.2,x2APIC,POPCNT,DEADLINE,AES,XSAVE,AVX,F16C,RDRAND,NXE,LONG,LAHF,PERF,ITSC,FSGSBASE,SMEP,ERMS cpu3: 256KB 64b/line 8-way L2 cache cpu3: smt 1, core 1, package 0 ioapic0 at mainbus0: apid 2 pa 0xfec0, version 20, 24 pins acpimcfg0 at acpi0 addr 0xf800, bus 0-63 acpiec0 at acpi0 acpiprt0 at acpi0: bus 0 (PCI0) acpiprt1 at acpi0: bus -1 (PEG_) acpiprt2 at acpi0: bus 2 (EXP1) acpiprt3 at acpi0: bus 3 (EXP2) acpiprt4 at acpi0: bus 4 (EXP3) acpiprt5 at acpi0: bus 12 (EXP5) acpiprt6 at acpi0: bus -1 (EXP6) acpiprt7 at acpi0: bus -1 (EXP7) acpiprt8 at acpi0: bus -1 (EXP8) acpicpu0 at acpi0: C3, PSS acpicpu1 at
syslogd ipv6
Hi, I have added functionality that allows syslogd to receive and send UDP packets via inet6 sockets. I will split this diff into smaller parts to make review and discussion easier. bluhm Index: usr.sbin/syslogd/privsep.c === RCS file: /data/mirror/openbsd/cvs/src/usr.sbin/syslogd/privsep.c,v retrieving revision 1.34 diff -u -p -u -p -r1.34 privsep.c --- usr.sbin/syslogd/privsep.c 23 Nov 2008 04:29:42 - 1.34 +++ usr.sbin/syslogd/privsep.c 18 Aug 2014 23:48:18 - @@ -67,8 +67,8 @@ enum cmd_types { PRIV_OPEN_UTMP, /* open utmp for reading only */ PRIV_OPEN_CONFIG, /* open config file for reading only */ PRIV_CONFIG_MODIFIED, /* check if config file has been modified */ - PRIV_GETHOSTSERV, /* resolve host/service names */ - PRIV_GETHOSTBYADDR, /* resolve numeric address into hostname */ + PRIV_GETADDRINFO, /* resolve host/service names */ + PRIV_GETNAMEINFO, /* resolve numeric address into hostname */ PRIV_DONE_CONFIG_PARSE /* signal that the initial config parse is done */ }; @@ -76,7 +76,7 @@ static int priv_fd = -1; static volatile pid_t child_pid = -1; static char config_file[MAXPATHLEN]; static struct stat cf_info; -static int allow_gethostbyaddr = 0; +static int allow_getnameinfo = 0; static volatile sig_atomic_t cur_state = STATE_INIT; /* Queue for the allowed logfiles */ @@ -100,12 +100,12 @@ static int may_read(int, void *, size_t int priv_init(char *conf, int numeric, int lockfd, int nullfd, char *argv[]) { - int i, fd, socks[2], cmd, addr_len, addr_af, result, restart; - size_t path_len, hostname_len, servname_len; - char path[MAXPATHLEN], hostname[MAXHOSTNAMELEN]; + int i, fd, socks[2], cmd, addr_len, result, restart; + size_t path_len, protoname_len, hostname_len, servname_len; + char path[MAXPATHLEN], protoname[16], hostname[MAXHOSTNAMELEN]; char servname[MAXHOSTNAMELEN]; + struct sockaddr_storage addr; struct stat cf_stat; - struct hostent *hp; struct passwd *pw; struct addrinfo hints, *res0; struct sigaction sa; @@ -177,6 +177,8 @@ priv_init(char *conf, int numeric, int l close(pfd[PFD_UNIX_0 + i].fd); if (pfd[PFD_INET].fd != -1) close(pfd[PFD_INET].fd); + if (pfd[PFD_INET6].fd != -1) + close(pfd[PFD_INET6].fd); if (pfd[PFD_CTLSOCK].fd != -1) close(pfd[PFD_CTLSOCK].fd); if (pfd[PFD_CTLCONN].fd != -1) @@ -191,11 +193,11 @@ priv_init(char *conf, int numeric, int l if (stat(config_file, cf_info) 0) err(1, stat config file failed); - /* Save whether or not the child can have access to gethostbyaddr(3) */ + /* Save whether or not the child can have access to getnameinfo(3) */ if (numeric 0) - allow_gethostbyaddr = 0; + allow_getnameinfo = 0; else - allow_gethostbyaddr = 1; + allow_getnameinfo = 1; TAILQ_INIT(lognames); increase_state(STATE_CONFIG); @@ -210,7 +212,7 @@ priv_init(char *conf, int numeric, int l /* Expecting: length, path */ must_read(socks[0], path_len, sizeof(size_t)); if (path_len == 0 || path_len sizeof(path)) - _exit(0); + _exit(1); must_read(socks[0], path, path_len); path[path_len - 1] = '\0'; check_tty_name(path, path_len); @@ -229,7 +231,7 @@ priv_init(char *conf, int numeric, int l /* Expecting: length, path */ must_read(socks[0], path_len, sizeof(size_t)); if (path_len == 0 || path_len sizeof(path)) - _exit(0); + _exit(1); must_read(socks[0], path, path_len); path[path_len - 1] = '\0'; check_log_name(path, path_len); @@ -289,24 +291,46 @@ priv_init(char *conf, int numeric, int l increase_state(STATE_RUNNING); break; - case PRIV_GETHOSTSERV: - dprintf([priv]: msg PRIV_GETHOSTSERV received\n); - /* Expecting: len, hostname, len, servname */ + case PRIV_GETADDRINFO: + dprintf([priv]: msg PRIV_GETADDRINFO received\n); + /* Expecting: len, proto, len, host, len, serv */ + must_read(socks[0], protoname_len, sizeof(size_t)); + if (protoname_len == 0 || + protoname_len sizeof(protoname)) + _exit(1); +
Re: syslogd ipv6
On Tue, Aug 19, 2014 at 01:59:42AM +0200, Alexander Bluhm wrote: I will split this diff into smaller parts to make review and discussion easier. Let's start with the easy part, fix trailing white spaces. ok? bluhm Index: usr.sbin/syslogd/syslogd.c === RCS file: /data/mirror/openbsd/cvs/src/usr.sbin/syslogd/syslogd.c,v retrieving revision 1.111 diff -u -p -u -p -r1.111 syslogd.c --- usr.sbin/syslogd/syslogd.c 14 Jul 2014 04:02:33 - 1.111 +++ usr.sbin/syslogd/syslogd.c 19 Aug 2014 00:00:14 - @@ -1014,7 +1014,7 @@ fprintlog(struct filed *f, int flags, ch case F_MEMBUF: dprintf(\n); snprintf(line, sizeof(line), %.15s %s %s, - (char *)iov[0].iov_base, (char *)iov[2].iov_base, + (char *)iov[0].iov_base, (char *)iov[2].iov_base, (char *)iov[4].iov_base); if (ringbuf_append_line(f-f_un.f_mb.f_rb, line) == 1) f-f_un.f_mb.f_overflow = 1; @@ -1538,9 +1538,9 @@ cfline(char *line, char *prog) logerror(ebuf); break; } - addr_len = priv_gethostserv(f-f_un.f_forw.f_hname, - cp == NULL ? syslog : cp, - (struct sockaddr*)f-f_un.f_forw.f_addr, + addr_len = priv_gethostserv(f-f_un.f_forw.f_hname, + cp == NULL ? syslog : cp, + (struct sockaddr*)f-f_un.f_forw.f_addr, sizeof(f-f_un.f_forw.f_addr)); if (addr_len 1) { snprintf(ebuf, sizeof(ebuf), bad hostname \%s\, p); pgpFDZFMnCUDS.pgp Description: PGP signature
Re: syslogd ipv6
On Tue, Aug 19, 2014 at 01:59:42AM +0200, Alexander Bluhm wrote: I will split this diff into smaller parts to make review and discussion easier. Replace manually written function names with __func__. This will make renaming functions easier. ok? bluhm Index: usr.sbin/syslogd/privsep.c === RCS file: /data/mirror/openbsd/cvs/src/usr.sbin/syslogd/privsep.c,v retrieving revision 1.34 diff -u -p -u -p -r1.34 privsep.c --- usr.sbin/syslogd/privsep.c 23 Nov 2008 04:29:42 - 1.34 +++ usr.sbin/syslogd/privsep.c 19 Aug 2014 00:03:18 - @@ -531,7 +531,7 @@ priv_open_tty(const char *tty) size_t path_len; if (priv_fd 0) - errx(1, %s: called from privileged portion, priv_open_tty); + errx(1, %s: called from privileged portion, __func__); if (strlcpy(path, tty, sizeof path) = sizeof(path)) return -1; @@ -554,7 +554,7 @@ priv_open_log(const char *lognam) size_t path_len; if (priv_fd 0) - errx(1, %s: called from privileged child, priv_open_log); + errx(1, %s: called from privileged child, __func__); if (strlcpy(path, lognam, sizeof path) = sizeof(path)) return -1; @@ -579,7 +579,7 @@ priv_open_utmp(void) FILE *fp; if (priv_fd 0) - errx(1, %s: called from privileged portion, priv_open_utmp); + errx(1, %s: called from privileged portion, __func__); cmd = PRIV_OPEN_UTMP; must_write(priv_fd, cmd, sizeof(int)); @@ -605,7 +605,7 @@ priv_open_config(void) FILE *fp; if (priv_fd 0) - errx(1, %s: called from privileged portion, priv_open_config); + errx(1, %s: called from privileged portion, __func__); cmd = PRIV_OPEN_CONFIG; must_write(priv_fd, cmd, sizeof(int)); @@ -630,8 +630,7 @@ priv_config_modified(void) int cmd, res; if (priv_fd 0) - errx(1, %s: called from privileged portion, - priv_config_modified); + errx(1, %s: called from privileged portion, __func__); cmd = PRIV_CONFIG_MODIFIED; must_write(priv_fd, cmd, sizeof(int)); @@ -649,8 +648,7 @@ priv_config_parse_done(void) int cmd; if (priv_fd 0) - errx(1, %s: called from privileged portion, - priv_config_parse_done); + errx(1, %s: called from privileged portion, __func__); cmd = PRIV_DONE_CONFIG_PARSE; must_write(priv_fd, cmd, sizeof(int)); @@ -667,13 +665,13 @@ priv_gethostserv(char *host, char *serv, size_t hostname_len, servname_len; if (priv_fd 0) - errx(1, %s: called from privileged portion, priv_gethostserv); + errx(1, %s: called from privileged portion, __func__); if (strlcpy(hostcpy, host, sizeof hostcpy) = sizeof(hostcpy)) - errx(1, %s: overflow attempt in hostname, priv_gethostserv); + errx(1, %s: overflow attempt in hostname, __func__); hostname_len = strlen(hostcpy) + 1; if (strlcpy(servcpy, serv, sizeof servcpy) = sizeof(servcpy)) - errx(1, %s: overflow attempt in servname, priv_gethostserv); + errx(1, %s: overflow attempt in servname, __func__); servname_len = strlen(servcpy) + 1; cmd = PRIV_GETHOSTSERV; @@ -692,7 +690,7 @@ priv_gethostserv(char *host, char *serv, /* Make sure we aren't overflowing the passed in buffer */ if (addr_len ret_len) - errx(1, %s: overflow attempt in return, priv_gethostserv); + errx(1, %s: overflow attempt in return, __func__); /* Read the resolved address and make sure we got all of it */ memset(addr, '\0', addr_len); @@ -709,7 +707,7 @@ priv_gethostbyaddr(char *addr, int addr_ int cmd, ret_len; if (priv_fd 0) - errx(1, %s called from privileged portion, priv_gethostbyaddr); + errx(1, %s called from privileged portion, __func__); cmd = PRIV_GETHOSTBYADDR; must_write(priv_fd, cmd, sizeof(int)); @@ -726,7 +724,7 @@ priv_gethostbyaddr(char *addr, int addr_ /* Check we don't overflow the passed in buffer */ if (res_len ret_len) - errx(1, %s: overflow attempt in return, priv_gethostbyaddr); + errx(1, %s: overflow attempt in return, __func__); /* Read the resolved hostname */ must_read(priv_fd, res, ret_len); pgptuhErI0rG1.pgp Description: PGP signature
Re: syslogd ipv6
On Tue, Aug 19, 2014 at 01:59:42AM +0200, Alexander Bluhm wrote: I will split this diff into smaller parts to make review and discussion easier. The exit codes in privsep.c seem to be the wrong way around. Fatal errors should exit with 1, and regular shutdown should result in exit with 0. I have written a syslogd regression test that gets confused by the current behavior. ok? bluhm Index: usr.sbin/syslogd/privsep.c === RCS file: /data/mirror/openbsd/cvs/src/usr.sbin/syslogd/privsep.c,v retrieving revision 1.34 diff -u -p -u -p -r1.34 privsep.c --- usr.sbin/syslogd/privsep.c 23 Nov 2008 04:29:42 - 1.34 +++ usr.sbin/syslogd/privsep.c 19 Aug 2014 00:07:08 - @@ -210,7 +210,7 @@ priv_init(char *conf, int numeric, int l /* Expecting: length, path */ must_read(socks[0], path_len, sizeof(size_t)); if (path_len == 0 || path_len sizeof(path)) - _exit(0); + _exit(1); must_read(socks[0], path, path_len); path[path_len - 1] = '\0'; check_tty_name(path, path_len); @@ -229,7 +229,7 @@ priv_init(char *conf, int numeric, int l /* Expecting: length, path */ must_read(socks[0], path_len, sizeof(size_t)); if (path_len == 0 || path_len sizeof(path)) - _exit(0); + _exit(1); must_read(socks[0], path, path_len); path[path_len - 1] = '\0'; check_log_name(path, path_len); @@ -294,13 +294,13 @@ priv_init(char *conf, int numeric, int l /* Expecting: len, hostname, len, servname */ must_read(socks[0], hostname_len, sizeof(size_t)); if (hostname_len == 0 || hostname_len sizeof(hostname)) - _exit(0); + _exit(1); must_read(socks[0], hostname, hostname_len); hostname[hostname_len - 1] = '\0'; must_read(socks[0], servname_len, sizeof(size_t)); if (servname_len == 0 || servname_len sizeof(servname)) - _exit(0); + _exit(1); must_read(socks[0], servname, servname_len); servname[servname_len - 1] = '\0'; @@ -327,7 +327,7 @@ priv_init(char *conf, int numeric, int l /* Expecting: length, address, address family */ must_read(socks[0], addr_len, sizeof(int)); if (addr_len = 0 || addr_len sizeof(hostname)) - _exit(0); + _exit(1); must_read(socks[0], hostname, addr_len); must_read(socks[0], addr_af, sizeof(int)); hp = gethostbyaddr(hostname, addr_len, addr_af); @@ -362,7 +362,7 @@ priv_init(char *conf, int numeric, int l execvp(argv[0], argv); } unlink(_PATH_LOGPID); - _exit(1); + _exit(0); } static int @@ -797,7 +797,7 @@ must_read(int fd, void *buf, size_t n) if (errno == EINTR || errno == EAGAIN) continue; case 0: - _exit(0); + _exit(1); default: pos += res; } @@ -819,7 +819,7 @@ must_write(int fd, void *buf, size_t n) if (errno == EINTR || errno == EAGAIN) continue; case 0: - _exit(0); + _exit(1); default: pos += res; }
Re: syslogd ipv6 getnameinfo
On Tue, Aug 19, 2014 at 01:59:42AM +0200, Alexander Bluhm wrote: I will split this diff into smaller parts to make review and discussion easier. Replace gethostbyaddr(3) with getnameinfo(3). Note that I remove the sigprocmask() that was added in rev 1.23 before privsep. It was necessary because gethostbyaddr() is not signal safe. ok? bluhm Index: usr.sbin/syslogd/privsep.c === RCS file: /data/mirror/openbsd/cvs/src/usr.sbin/syslogd/privsep.c,v retrieving revision 1.36 diff -u -p -u -p -r1.36 privsep.c --- usr.sbin/syslogd/privsep.c 19 Aug 2014 00:53:01 - 1.36 +++ usr.sbin/syslogd/privsep.c 19 Aug 2014 20:01:12 - @@ -68,7 +68,7 @@ enum cmd_types { PRIV_OPEN_CONFIG, /* open config file for reading only */ PRIV_CONFIG_MODIFIED, /* check if config file has been modified */ PRIV_GETHOSTSERV, /* resolve host/service names */ - PRIV_GETHOSTBYADDR, /* resolve numeric address into hostname */ + PRIV_GETNAMEINFO, /* resolve numeric address into hostname */ PRIV_DONE_CONFIG_PARSE /* signal that the initial config parse is done */ }; @@ -76,7 +76,7 @@ static int priv_fd = -1; static volatile pid_t child_pid = -1; static char config_file[MAXPATHLEN]; static struct stat cf_info; -static int allow_gethostbyaddr = 0; +static int allow_getnameinfo = 0; static volatile sig_atomic_t cur_state = STATE_INIT; /* Queue for the allowed logfiles */ @@ -100,12 +100,12 @@ static int may_read(int, void *, size_t int priv_init(char *conf, int numeric, int lockfd, int nullfd, char *argv[]) { - int i, fd, socks[2], cmd, addr_len, addr_af, result, restart; + int i, fd, socks[2], cmd, addr_len, result, restart; size_t path_len, hostname_len, servname_len; char path[MAXPATHLEN], hostname[MAXHOSTNAMELEN]; char servname[MAXHOSTNAMELEN]; + struct sockaddr_storage addr; struct stat cf_stat; - struct hostent *hp; struct passwd *pw; struct addrinfo hints, *res0; struct sigaction sa; @@ -191,11 +191,11 @@ priv_init(char *conf, int numeric, int l if (stat(config_file, cf_info) 0) err(1, stat config file failed); - /* Save whether or not the child can have access to gethostbyaddr(3) */ + /* Save whether or not the child can have access to getnameinfo(3) */ if (numeric 0) - allow_gethostbyaddr = 0; + allow_getnameinfo = 0; else - allow_gethostbyaddr = 1; + allow_getnameinfo = 1; TAILQ_INIT(lognames); increase_state(STATE_CONFIG); @@ -320,24 +320,24 @@ priv_init(char *conf, int numeric, int l } break; - case PRIV_GETHOSTBYADDR: - dprintf([priv]: msg PRIV_GETHOSTBYADDR received\n); - if (!allow_gethostbyaddr) - errx(1, rejected attempt to gethostbyaddr); - /* Expecting: length, address, address family */ + case PRIV_GETNAMEINFO: + dprintf([priv]: msg PRIV_GETNAMEINFO received\n); + if (!allow_getnameinfo) + errx(1, rejected attempt to getnameinfo); + /* Expecting: length, sockaddr */ must_read(socks[0], addr_len, sizeof(int)); - if (addr_len = 0 || addr_len sizeof(hostname)) + if (addr_len = 0 || addr_len sizeof(addr)) _exit(1); - must_read(socks[0], hostname, addr_len); - must_read(socks[0], addr_af, sizeof(int)); - hp = gethostbyaddr(hostname, addr_len, addr_af); - if (hp == NULL) { + must_read(socks[0], addr, addr_len); + if (getnameinfo((struct sockaddr *)addr, addr_len, + hostname, sizeof(hostname), NULL, 0, + NI_NOFQDN|NI_NAMEREQD|NI_DGRAM) != 0) { addr_len = 0; must_write(socks[0], addr_len, sizeof(int)); } else { - addr_len = strlen(hp-h_name) + 1; + addr_len = strlen(hostname) + 1; must_write(socks[0], addr_len, sizeof(int)); - must_write(socks[0], hp-h_name, addr_len); + must_write(socks[0], hostname, addr_len); } break; default: @@ -702,33 +702,33 @@ priv_gethostserv(char *host, char *serv, /* Reverse address resolution; response is placed into res, and length of * response is returned (zero on error) */ int
Re: syslogd ipv6 getaddrinfo
On Tue, Aug 19, 2014 at 01:59:42AM +0200, Alexander Bluhm wrote: I will split this diff into smaller parts to make review and discussion easier. Rename priv_gethostserv() to priv_getaddrinfo() as this is what the function does. Change the return code semantics to match getaddrinfo(3). ok? bluhm Index: usr.sbin/syslogd/privsep.c === RCS file: /data/mirror/openbsd/cvs/src/usr.sbin/syslogd/privsep.c,v retrieving revision 1.36 diff -u -p -u -p -r1.36 privsep.c --- usr.sbin/syslogd/privsep.c 19 Aug 2014 00:53:01 - 1.36 +++ usr.sbin/syslogd/privsep.c 19 Aug 2014 21:06:35 - @@ -67,7 +67,7 @@ enum cmd_types { PRIV_OPEN_UTMP, /* open utmp for reading only */ PRIV_OPEN_CONFIG, /* open config file for reading only */ PRIV_CONFIG_MODIFIED, /* check if config file has been modified */ - PRIV_GETHOSTSERV, /* resolve host/service names */ + PRIV_GETADDRINFO, /* resolve host/service names */ PRIV_GETHOSTBYADDR, /* resolve numeric address into hostname */ PRIV_DONE_CONFIG_PARSE /* signal that the initial config parse is done */ }; @@ -289,17 +289,19 @@ priv_init(char *conf, int numeric, int l increase_state(STATE_RUNNING); break; - case PRIV_GETHOSTSERV: - dprintf([priv]: msg PRIV_GETHOSTSERV received\n); + case PRIV_GETADDRINFO: + dprintf([priv]: msg PRIV_GETADDRINFO received\n); /* Expecting: len, hostname, len, servname */ must_read(socks[0], hostname_len, sizeof(size_t)); - if (hostname_len == 0 || hostname_len sizeof(hostname)) + if (hostname_len == 0 || + hostname_len sizeof(hostname)) _exit(1); must_read(socks[0], hostname, hostname_len); hostname[hostname_len - 1] = '\0'; must_read(socks[0], servname_len, sizeof(size_t)); - if (servname_len == 0 || servname_len sizeof(servname)) + if (servname_len == 0 || + servname_len sizeof(servname)) _exit(1); must_read(socks[0], servname, servname_len); servname[servname_len - 1] = '\0'; @@ -657,7 +659,7 @@ priv_config_parse_done(void) /* Name/service to address translation. Response is placed into addr, and * the length is returned (zero on error) */ int -priv_gethostserv(char *host, char *serv, struct sockaddr *addr, +priv_getaddrinfo(char *host, char *serv, struct sockaddr *addr, size_t addr_len) { char hostcpy[MAXHOSTNAMELEN], servcpy[MAXHOSTNAMELEN]; @@ -674,7 +676,7 @@ priv_gethostserv(char *host, char *serv, errx(1, %s: overflow attempt in servname, __func__); servname_len = strlen(servcpy) + 1; - cmd = PRIV_GETHOSTSERV; + cmd = PRIV_GETADDRINFO; must_write(priv_fd, cmd, sizeof(int)); must_write(priv_fd, hostname_len, sizeof(size_t)); must_write(priv_fd, hostcpy, hostname_len); @@ -686,7 +688,7 @@ priv_gethostserv(char *host, char *serv, /* Check there was no error (indicated by a return of 0) */ if (!ret_len) - return 0; + return (-1); /* Make sure we aren't overflowing the passed in buffer */ if (addr_len ret_len) @@ -696,7 +698,7 @@ priv_gethostserv(char *host, char *serv, memset(addr, '\0', addr_len); must_read(priv_fd, addr, ret_len); - return ret_len; + return (0); } /* Reverse address resolution; response is placed into res, and length of Index: usr.sbin/syslogd/syslogd.c === RCS file: /data/mirror/openbsd/cvs/src/usr.sbin/syslogd/syslogd.c,v retrieving revision 1.112 diff -u -p -u -p -r1.112 syslogd.c --- usr.sbin/syslogd/syslogd.c 19 Aug 2014 00:24:00 - 1.112 +++ usr.sbin/syslogd/syslogd.c 19 Aug 2014 21:09:15 - @@ -1427,7 +1427,7 @@ find_dup(struct filed *f) struct filed * cfline(char *line, char *prog) { - int i, pri, addr_len; + int i, pri; size_t rb_len; char *bp, *p, *q, *cp; char buf[MAXLINE], ebuf[100]; @@ -1538,11 +1538,10 @@ cfline(char *line, char *prog) logerror(ebuf); break; } - addr_len = priv_gethostserv(f-f_un.f_forw.f_hname, + if (priv_getaddrinfo(f-f_un.f_forw.f_hname, cp == NULL ? syslog : cp, - (struct sockaddr*)f-f_un.f_forw.f_addr, - sizeof(f-f_un.f_forw.f_addr)); - if (addr_len 1) { + (struct sockaddr *)f
Re: syslogd ipv6 socket
On Tue, Aug 19, 2014 at 01:59:42AM +0200, Alexander Bluhm wrote: I will split this diff into smaller parts to make review and discussion easier. Send and receive UDP syslog packets on the IPv6 socket. ok? bluhm Index: usr.sbin/syslogd/privsep.c === RCS file: /cvs/src/usr.sbin/syslogd/privsep.c,v retrieving revision 1.38 diff -u -p -r1.38 privsep.c --- usr.sbin/syslogd/privsep.c 20 Aug 2014 20:10:17 - 1.38 +++ usr.sbin/syslogd/privsep.c 20 Aug 2014 23:16:41 - @@ -177,6 +177,8 @@ priv_init(char *conf, int numeric, int l close(pfd[PFD_UNIX_0 + i].fd); if (pfd[PFD_INET].fd != -1) close(pfd[PFD_INET].fd); + if (pfd[PFD_INET6].fd != -1) + close(pfd[PFD_INET6].fd); if (pfd[PFD_CTLSOCK].fd != -1) close(pfd[PFD_CTLSOCK].fd); if (pfd[PFD_CTLCONN].fd != -1) @@ -306,8 +308,8 @@ priv_init(char *conf, int numeric, int l must_read(socks[0], servname, servname_len); servname[servname_len - 1] = '\0'; - memset(hints, '\0', sizeof(hints)); - hints.ai_family = AF_INET; + memset(hints, 0, sizeof(hints)); + hints.ai_family = AF_UNSPEC; hints.ai_socktype = SOCK_DGRAM; i = getaddrinfo(hostname, servname, hints, res0); if (i != 0 || res0 == NULL) { Index: usr.sbin/syslogd/syslogd.c === RCS file: /cvs/src/usr.sbin/syslogd/syslogd.c,v retrieving revision 1.114 diff -u -p -r1.114 syslogd.c --- usr.sbin/syslogd/syslogd.c 20 Aug 2014 20:10:17 - 1.114 +++ usr.sbin/syslogd/syslogd.c 20 Aug 2014 23:16:42 - @@ -188,7 +188,6 @@ int Debug; /* debug flag */ intStartup = 1;/* startup flag */ char LocalHostName[MAXHOSTNAMELEN]; /* our hostname */ char *LocalDomain; /* our local domain name */ -intInetInuse = 0; /* non-zero if INET sockets are being used */ intInitialized = 0;/* set when we have initialized ourselves */ intMarkInterval = 20 * 60; /* interval between marks in seconds */ @@ -282,7 +281,7 @@ main(int argc, char *argv[]) { int ch, i, linesize, fd; struct sockaddr_un fromunix; - struct sockaddr_in frominet; + struct sockaddr_storage from; socklen_t len; char *p, *line; char resolve[MAXHOSTNAMELEN]; @@ -369,7 +368,7 @@ main(int argc, char *argv[]) } memset(hints, 0, sizeof(hints)); - hints.ai_family = AF_INET; + hints.ai_family = AF_UNSPEC; hints.ai_socktype = SOCK_DGRAM; hints.ai_protocol = IPPROTO_UDP; hints.ai_flags = AI_PASSIVE; @@ -384,13 +383,14 @@ main(int argc, char *argv[]) for (res = res0; res; res = res-ai_next) { struct pollfd *pfdp; - if (res-ai_family == AF_INET) + switch (res-ai_family) { + case AF_INET: pfdp = pfd[PFD_INET]; - else { - /* -* XXX AF_INET6 is skipped on purpose, need to -* fix '@' handling first. -*/ + break; + case AF_INET6: + pfdp = pfd[PFD_INET6]; + break; + default: continue; } @@ -410,7 +410,6 @@ main(int argc, char *argv[]) continue; } - InetInuse = 1; pfdp-fd = fd; if (SecureMode) shutdown(pfdp-fd, SHUT_RD); @@ -582,18 +581,31 @@ main(int argc, char *argv[]) } } if ((pfd[PFD_INET].revents POLLIN) != 0) { - len = sizeof(frominet); + len = sizeof(from); i = recvfrom(pfd[PFD_INET].fd, line, MAXLINE, 0, - (struct sockaddr *)frominet, len); + (struct sockaddr *)from, len); if (i 0) { line[i] = '\0'; - cvthname((struct sockaddr *)frominet, resolve, - sizeof resolve); + cvthname((struct sockaddr *)from, resolve, + sizeof(resolve)); dprintf(cvthname res: %s\n, resolve); printline(resolve, line); } else if (i 0 errno != EINTR) logerror(recvfrom inet); } + if ((pfd[PFD_INET6].revents POLLIN) != 0
Re: syslogd ipv6 man5
On Tue, Aug 19, 2014 at 01:59:42AM +0200, Alexander Bluhm wrote: I will split this diff into smaller parts to make review and discussion easier. Document square brackets for IPv6 addresses. From FreeBSD. Index: usr.sbin/syslogd/syslog.conf.5 === RCS file: /cvs/src/usr.sbin/syslogd/syslog.conf.5,v retrieving revision 1.24 diff -u -p -r1.24 syslog.conf.5 --- usr.sbin/syslogd/syslog.conf.5 20 Jan 2014 05:07:48 - 1.24 +++ usr.sbin/syslogd/syslog.conf.5 20 Aug 2014 23:36:16 - @@ -220,6 +220,13 @@ program on the named host. A port number may be optionally specified using the .Ar host:port syntax. +IPv6 addresses can be used by surrounding the address portion with +square brackets +.Po +.Ql [\ +and +.Ql ]\ +.Pc . .It A comma separated list of users. Selected messages are written to those users
Re: syslogd ipv6 hostportlen
On Tue, Aug 19, 2014 at 01:59:42AM +0200, Alexander Bluhm wrote: I will split this diff into smaller parts to make review and discussion easier. Instead of getting a nasty error message from privsep syslogd: priv_getaddrinfo: overflow attempt in hostname check the host and port length when parsing the config. ok? bluhm Index: usr.sbin/syslogd/syslogd.c === RCS file: /cvs/src/usr.sbin/syslogd/syslogd.c,v retrieving revision 1.116 diff -u -p -r1.116 syslogd.c --- usr.sbin/syslogd/syslogd.c 21 Aug 2014 17:00:34 - 1.116 +++ usr.sbin/syslogd/syslogd.c 21 Aug 2014 20:10:41 - @@ -1547,8 +1547,21 @@ cfline(char *line, char *prog) logerror(ebuf); break; } - if (priv_getaddrinfo(host, - port == NULL ? syslog : port, + if (strlen(host) = MAXHOSTNAMELEN) { + snprintf(ebuf, sizeof(ebuf), host too long \%s\, + f-f_un.f_forw.f_loghost); + logerror(ebuf); + break; + } + if (port == NULL) + port = syslog; + if (strlen(port) = NI_MAXSERV) { + snprintf(ebuf, sizeof(ebuf), port too long \%s\, + f-f_un.f_forw.f_loghost); + logerror(ebuf); + break; + } + if (priv_getaddrinfo(host, port, (struct sockaddr*)f-f_un.f_forw.f_addr, sizeof(f-f_un.f_forw.f_addr)) != 0) { snprintf(ebuf, sizeof(ebuf), bad hostname \%s\,
Re: syslogd ipv6 proto6
On Tue, Aug 19, 2014 at 01:59:42AM +0200, Alexander Bluhm wrote: I will split this diff into smaller parts to make review and discussion easier. At the moment syslogd opens both IPv4 and IPv6 sockets unconditionally. I can restrict it to a protocol family with -4 and -6 command line switches. If the log server is a FQDN, DNS chosses wether to take the IPv4 or IPv6 route. For that I have invented a udp4:// or udp6:// prefix to choose a protocol. This syntax was chosen as I want to extend it to tcp:// and tls:// later. Do we want such IPv4/IPv6 knobs? ok? bluhm ? usr.sbin/syslogd/obj Index: usr.sbin/syslogd/privsep.c === RCS file: /cvs/src/usr.sbin/syslogd/privsep.c,v retrieving revision 1.40 diff -u -p -r1.40 privsep.c --- usr.sbin/syslogd/privsep.c 21 Aug 2014 17:00:34 - 1.40 +++ usr.sbin/syslogd/privsep.c 22 Aug 2014 16:31:08 - @@ -101,8 +101,8 @@ int priv_init(char *conf, int numeric, int lockfd, int nullfd, char *argv[]) { int i, fd, socks[2], cmd, addr_len, result, restart; - size_t path_len, hostname_len, servname_len; - char path[MAXPATHLEN], hostname[MAXHOSTNAMELEN]; + size_t path_len, protoname_len, hostname_len, servname_len; + char path[MAXPATHLEN], protoname[5], hostname[MAXHOSTNAMELEN]; char servname[NI_MAXSERV]; struct sockaddr_storage addr; struct stat cf_stat; @@ -293,7 +293,14 @@ priv_init(char *conf, int numeric, int l case PRIV_GETADDRINFO: dprintf([priv]: msg PRIV_GETADDRINFO received\n); - /* Expecting: len, hostname, len, servname */ + /* Expecting: len, proto, len, host, len, serv */ + must_read(socks[0], protoname_len, sizeof(size_t)); + if (protoname_len == 0 || + protoname_len sizeof(protoname)) + _exit(1); + must_read(socks[0], protoname, protoname_len); + protoname[protoname_len - 1] = '\0'; + must_read(socks[0], hostname_len, sizeof(size_t)); if (hostname_len == 0 || hostname_len sizeof(hostname)) @@ -309,8 +316,17 @@ priv_init(char *conf, int numeric, int l servname[servname_len - 1] = '\0'; memset(hints, 0, sizeof(hints)); - hints.ai_family = AF_UNSPEC; + if (strcmp(protoname, udp) == 0) { + hints.ai_family = AF_UNSPEC; + } else if (strcmp(protoname, udp4) == 0) { + hints.ai_family = AF_INET; + } else if (strcmp(protoname, udp6) == 0) { + hints.ai_family = AF_INET6; + } else { + errx(1, unknown protocol %s, protoname); + } hints.ai_socktype = SOCK_DGRAM; + hints.ai_protocol = IPPROTO_UDP; i = getaddrinfo(hostname, servname, hints, res0); if (i != 0 || res0 == NULL) { addr_len = 0; @@ -661,25 +677,30 @@ priv_config_parse_done(void) /* Name/service to address translation. Response is placed into addr. * Return 0 for success or 0 for error like getaddrinfo(3) */ int -priv_getaddrinfo(char *host, char *serv, struct sockaddr *addr, +priv_getaddrinfo(char *proto, char *host, char *serv, struct sockaddr *addr, size_t addr_len) { - char hostcpy[MAXHOSTNAMELEN], servcpy[NI_MAXSERV]; + char protocpy[5], hostcpy[MAXHOSTNAMELEN], servcpy[NI_MAXSERV]; int cmd, ret_len; - size_t hostname_len, servname_len; + size_t protoname_len, hostname_len, servname_len; if (priv_fd 0) errx(1, %s: called from privileged portion, __func__); - if (strlcpy(hostcpy, host, sizeof hostcpy) = sizeof(hostcpy)) + if (strlcpy(protocpy, proto, sizeof(protocpy)) = sizeof(protocpy)) + errx(1, %s: overflow attempt in protoname, __func__); + protoname_len = strlen(protocpy) + 1; + if (strlcpy(hostcpy, host, sizeof(hostcpy)) = sizeof(hostcpy)) errx(1, %s: overflow attempt in hostname, __func__); hostname_len = strlen(hostcpy) + 1; - if (strlcpy(servcpy, serv, sizeof servcpy) = sizeof(servcpy)) + if (strlcpy(servcpy, serv, sizeof(servcpy)) = sizeof(servcpy)) errx(1, %s: overflow attempt in servname, __func__); servname_len = strlen(servcpy) + 1; cmd = PRIV_GETADDRINFO; must_write(priv_fd, cmd, sizeof(int)); + must_write(priv_fd, protoname_len, sizeof(size_t)); + must_write(priv_fd, protocpy, protoname_len); must_write(priv_fd, hostname_len, sizeof
syslogd comparison between signed and unsigned
Hi, When compiling syslogd with WARNINGS=yes gcc complains with many warning: comparison between signed and unsigned. I would like to fix them. ok? bluhm Index: usr.sbin/syslogd/privsep.c === RCS file: /data/mirror/openbsd/cvs/src/usr.sbin/syslogd/privsep.c,v retrieving revision 1.40 diff -u -p -r1.40 privsep.c --- usr.sbin/syslogd/privsep.c 21 Aug 2014 17:00:34 - 1.40 +++ usr.sbin/syslogd/privsep.c 22 Aug 2014 18:52:12 - @@ -330,7 +330,7 @@ priv_init(char *conf, int numeric, int l errx(1, rejected attempt to getnameinfo); /* Expecting: length, sockaddr */ must_read(socks[0], addr_len, sizeof(int)); - if (addr_len = 0 || addr_len sizeof(addr)) + if (addr_len = 0 || (size_t)addr_len sizeof(addr)) _exit(1); must_read(socks[0], addr, addr_len); if (getnameinfo((struct sockaddr *)addr, addr_len, @@ -459,7 +459,7 @@ check_tty_name(char *tty, size_t ttylen) char *p; /* Any path containing '..' is invalid. */ - for (p = tty; *p (p - tty) ttylen; p++) + for (p = tty; *p p tty + ttylen; p++) if (*p == '.' *(p + 1) == '.') goto bad_path; @@ -484,7 +484,7 @@ check_log_name(char *lognam, size_t logl char *p; /* Any path containing '..' is invalid. */ - for (p = lognam; *p (p - lognam) loglen; p++) + for (p = lognam; *p p lognam + loglen; p++) if (*p == '.' *(p + 1) == '.') goto bad_path; @@ -693,7 +693,7 @@ priv_getaddrinfo(char *host, char *serv, return (-1); /* Make sure we aren't overflowing the passed in buffer */ - if (addr_len ret_len) + if (ret_len 0 || (size_t)ret_len addr_len) errx(1, %s: overflow attempt in return, __func__); /* Read the resolved address and make sure we got all of it */ @@ -727,7 +727,7 @@ priv_getnameinfo(struct sockaddr *sa, so return (-1); /* Check we don't overflow the passed in buffer */ - if (hostlen ret_len) + if (ret_len 0 || (size_t)ret_len hostlen) errx(1, %s: overflow attempt in return, __func__); /* Read the resolved hostname */ @@ -767,7 +767,8 @@ static int may_read(int fd, void *buf, size_t n) { char *s = buf; - ssize_t res, pos = 0; + ssize_t res; + size_t pos = 0; while (n pos) { res = read(fd, s + pos, n - pos); @@ -790,7 +791,8 @@ static void must_read(int fd, void *buf, size_t n) { char *s = buf; - ssize_t res, pos = 0; + ssize_t res; + size_t pos = 0; while (n pos) { res = read(fd, s + pos, n - pos); @@ -812,7 +814,8 @@ static void must_write(int fd, void *buf, size_t n) { char *s = buf; - ssize_t res, pos = 0; + ssize_t res; + size_t pos = 0; while (n pos) { res = write(fd, s + pos, n - pos); Index: usr.sbin/syslogd/syslogd.c === RCS file: /data/mirror/openbsd/cvs/src/usr.sbin/syslogd/syslogd.c,v retrieving revision 1.117 diff -u -p -r1.117 syslogd.c --- usr.sbin/syslogd/syslogd.c 22 Aug 2014 16:14:11 - 1.117 +++ usr.sbin/syslogd/syslogd.c 22 Aug 2014 18:42:59 - @@ -868,10 +868,10 @@ fprintlog(struct filed *f, int flags, ch v = iov; if (f-f_type == F_WALL) { - if ((l = snprintf(greetings, sizeof(greetings), + l = snprintf(greetings, sizeof(greetings), \r\n\7Message from syslogd@%s at %.24s ...\r\n, - f-f_prevhost, ctime(now))) = sizeof(greetings) || - l == -1) + f-f_prevhost, ctime(now)); + if (l 0 || (size_t)l = sizeof(greetings)) l = strlen(greetings); v-iov_base = greetings; v-iov_len = l; @@ -898,9 +898,9 @@ fprintlog(struct filed *f, int flags, ch v-iov_base = msg; v-iov_len = strlen(msg); } else if (f-f_prevcount 1) { - if ((l = snprintf(repbuf, sizeof(repbuf), - last message repeated %d times, f-f_prevcount)) = - sizeof(repbuf) || l == -1) + l = snprintf(repbuf, sizeof(repbuf), + last message repeated %d times, f-f_prevcount); + if (l 0 || (size_t)l = sizeof(repbuf)) l = strlen(repbuf); v-iov_base = repbuf; v-iov_len = l; @@ -931,11 +931,12 @@ fprintlog(struct filed *f, int flags, ch fd = -1; break; } -
Re: syslogd ipv6 proto6
On Fri, Aug 22, 2014 at 06:43:47PM +0200, Alexander Bluhm wrote: At the moment syslogd opens both IPv4 and IPv6 sockets unconditionally. I can restrict it to a protocol family with -4 and -6 command line switches. If the log server is a FQDN, DNS chosses wether to take the IPv4 or IPv6 route. For that I have invented a udp4:// or udp6:// prefix to choose a protocol. This syntax was chosen as I want to extend it to tcp:// and tls:// later. Before -46 and -64 disabled both protocols. halex@ suggested to use the latter one like other programs do. updated diff changed in the getopt switch, ok? bluhm Index: usr.sbin/syslogd/privsep.c === RCS file: /data/mirror/openbsd/cvs/src/usr.sbin/syslogd/privsep.c,v retrieving revision 1.40 diff -u -p -r1.40 privsep.c --- usr.sbin/syslogd/privsep.c 21 Aug 2014 17:00:34 - 1.40 +++ usr.sbin/syslogd/privsep.c 23 Aug 2014 11:01:38 - @@ -101,8 +101,8 @@ int priv_init(char *conf, int numeric, int lockfd, int nullfd, char *argv[]) { int i, fd, socks[2], cmd, addr_len, result, restart; - size_t path_len, hostname_len, servname_len; - char path[MAXPATHLEN], hostname[MAXHOSTNAMELEN]; + size_t path_len, protoname_len, hostname_len, servname_len; + char path[MAXPATHLEN], protoname[5], hostname[MAXHOSTNAMELEN]; char servname[NI_MAXSERV]; struct sockaddr_storage addr; struct stat cf_stat; @@ -293,7 +293,14 @@ priv_init(char *conf, int numeric, int l case PRIV_GETADDRINFO: dprintf([priv]: msg PRIV_GETADDRINFO received\n); - /* Expecting: len, hostname, len, servname */ + /* Expecting: len, proto, len, host, len, serv */ + must_read(socks[0], protoname_len, sizeof(size_t)); + if (protoname_len == 0 || + protoname_len sizeof(protoname)) + _exit(1); + must_read(socks[0], protoname, protoname_len); + protoname[protoname_len - 1] = '\0'; + must_read(socks[0], hostname_len, sizeof(size_t)); if (hostname_len == 0 || hostname_len sizeof(hostname)) @@ -309,8 +316,17 @@ priv_init(char *conf, int numeric, int l servname[servname_len - 1] = '\0'; memset(hints, 0, sizeof(hints)); - hints.ai_family = AF_UNSPEC; + if (strcmp(protoname, udp) == 0) { + hints.ai_family = AF_UNSPEC; + } else if (strcmp(protoname, udp4) == 0) { + hints.ai_family = AF_INET; + } else if (strcmp(protoname, udp6) == 0) { + hints.ai_family = AF_INET6; + } else { + errx(1, unknown protocol %s, protoname); + } hints.ai_socktype = SOCK_DGRAM; + hints.ai_protocol = IPPROTO_UDP; i = getaddrinfo(hostname, servname, hints, res0); if (i != 0 || res0 == NULL) { addr_len = 0; @@ -661,25 +677,30 @@ priv_config_parse_done(void) /* Name/service to address translation. Response is placed into addr. * Return 0 for success or 0 for error like getaddrinfo(3) */ int -priv_getaddrinfo(char *host, char *serv, struct sockaddr *addr, +priv_getaddrinfo(char *proto, char *host, char *serv, struct sockaddr *addr, size_t addr_len) { - char hostcpy[MAXHOSTNAMELEN], servcpy[NI_MAXSERV]; + char protocpy[5], hostcpy[MAXHOSTNAMELEN], servcpy[NI_MAXSERV]; int cmd, ret_len; - size_t hostname_len, servname_len; + size_t protoname_len, hostname_len, servname_len; if (priv_fd 0) errx(1, %s: called from privileged portion, __func__); - if (strlcpy(hostcpy, host, sizeof hostcpy) = sizeof(hostcpy)) + if (strlcpy(protocpy, proto, sizeof(protocpy)) = sizeof(protocpy)) + errx(1, %s: overflow attempt in protoname, __func__); + protoname_len = strlen(protocpy) + 1; + if (strlcpy(hostcpy, host, sizeof(hostcpy)) = sizeof(hostcpy)) errx(1, %s: overflow attempt in hostname, __func__); hostname_len = strlen(hostcpy) + 1; - if (strlcpy(servcpy, serv, sizeof servcpy) = sizeof(servcpy)) + if (strlcpy(servcpy, serv, sizeof(servcpy)) = sizeof(servcpy)) errx(1, %s: overflow attempt in servname, __func__); servname_len = strlen(servcpy) + 1; cmd = PRIV_GETADDRINFO; must_write(priv_fd, cmd, sizeof(int)); + must_write(priv_fd, protoname_len, sizeof(size_t)); + must_write(priv_fd, protocpy, protoname_len
Re: syslogd ipv6 proto6
On Sat, Aug 23, 2014 at 01:10:52PM +0200, Alexander Bluhm wrote: On Fri, Aug 22, 2014 at 06:43:47PM +0200, Alexander Bluhm wrote: At the moment syslogd opens both IPv4 and IPv6 sockets unconditionally. I can restrict it to a protocol family with -4 and -6 command line switches. If the log server is a FQDN, DNS chosses wether to take the IPv4 or IPv6 route. For that I have invented a udp4:// or udp6:// prefix to choose a protocol. This syntax was chosen as I want to extend it to tcp:// and tls:// later. Before -46 and -64 disabled both protocols. halex@ suggested to use the latter one like other programs do. updated diff changed in the getopt switch, ok? I still need an ok for this. The -4 switch has been made especially for our ipv6 haters^W^Wipv4 lovers. I can live without it. When implementing tcp, I will need the tcp:// logic anyway. bluhm Index: usr.sbin/syslogd/privsep.c === RCS file: /data/mirror/openbsd/cvs/src/usr.sbin/syslogd/privsep.c,v retrieving revision 1.40 diff -u -p -r1.40 privsep.c --- usr.sbin/syslogd/privsep.c21 Aug 2014 17:00:34 - 1.40 +++ usr.sbin/syslogd/privsep.c23 Aug 2014 11:01:38 - @@ -101,8 +101,8 @@ int priv_init(char *conf, int numeric, int lockfd, int nullfd, char *argv[]) { int i, fd, socks[2], cmd, addr_len, result, restart; - size_t path_len, hostname_len, servname_len; - char path[MAXPATHLEN], hostname[MAXHOSTNAMELEN]; + size_t path_len, protoname_len, hostname_len, servname_len; + char path[MAXPATHLEN], protoname[5], hostname[MAXHOSTNAMELEN]; char servname[NI_MAXSERV]; struct sockaddr_storage addr; struct stat cf_stat; @@ -293,7 +293,14 @@ priv_init(char *conf, int numeric, int l case PRIV_GETADDRINFO: dprintf([priv]: msg PRIV_GETADDRINFO received\n); - /* Expecting: len, hostname, len, servname */ + /* Expecting: len, proto, len, host, len, serv */ + must_read(socks[0], protoname_len, sizeof(size_t)); + if (protoname_len == 0 || + protoname_len sizeof(protoname)) + _exit(1); + must_read(socks[0], protoname, protoname_len); + protoname[protoname_len - 1] = '\0'; + must_read(socks[0], hostname_len, sizeof(size_t)); if (hostname_len == 0 || hostname_len sizeof(hostname)) @@ -309,8 +316,17 @@ priv_init(char *conf, int numeric, int l servname[servname_len - 1] = '\0'; memset(hints, 0, sizeof(hints)); - hints.ai_family = AF_UNSPEC; + if (strcmp(protoname, udp) == 0) { + hints.ai_family = AF_UNSPEC; + } else if (strcmp(protoname, udp4) == 0) { + hints.ai_family = AF_INET; + } else if (strcmp(protoname, udp6) == 0) { + hints.ai_family = AF_INET6; + } else { + errx(1, unknown protocol %s, protoname); + } hints.ai_socktype = SOCK_DGRAM; + hints.ai_protocol = IPPROTO_UDP; i = getaddrinfo(hostname, servname, hints, res0); if (i != 0 || res0 == NULL) { addr_len = 0; @@ -661,25 +677,30 @@ priv_config_parse_done(void) /* Name/service to address translation. Response is placed into addr. * Return 0 for success or 0 for error like getaddrinfo(3) */ int -priv_getaddrinfo(char *host, char *serv, struct sockaddr *addr, +priv_getaddrinfo(char *proto, char *host, char *serv, struct sockaddr *addr, size_t addr_len) { - char hostcpy[MAXHOSTNAMELEN], servcpy[NI_MAXSERV]; + char protocpy[5], hostcpy[MAXHOSTNAMELEN], servcpy[NI_MAXSERV]; int cmd, ret_len; - size_t hostname_len, servname_len; + size_t protoname_len, hostname_len, servname_len; if (priv_fd 0) errx(1, %s: called from privileged portion, __func__); - if (strlcpy(hostcpy, host, sizeof hostcpy) = sizeof(hostcpy)) + if (strlcpy(protocpy, proto, sizeof(protocpy)) = sizeof(protocpy)) + errx(1, %s: overflow attempt in protoname, __func__); + protoname_len = strlen(protocpy) + 1; + if (strlcpy(hostcpy, host, sizeof(hostcpy)) = sizeof(hostcpy)) errx(1, %s: overflow attempt in hostname, __func__); hostname_len = strlen(hostcpy) + 1; - if (strlcpy(servcpy, serv, sizeof servcpy) = sizeof(servcpy)) + if (strlcpy(servcpy, serv, sizeof(servcpy)) = sizeof(servcpy)) errx(1, %s: overflow attempt in servname, __func__
Re: syslogd comparison between signed and unsigned
On Fri, Aug 22, 2014 at 09:14:33PM +0200, Alexander Bluhm wrote: Hi, When compiling syslogd with WARNINGS=yes gcc complains with many warning: comparison between signed and unsigned. I would like to fix them. ok? I still need an ok. Note that some checks got stricter. The (size_t) cast is only done, if the argument is not negative. I have another bugfix on top of this diff. bluhm bluhm Index: usr.sbin/syslogd/privsep.c === RCS file: /data/mirror/openbsd/cvs/src/usr.sbin/syslogd/privsep.c,v retrieving revision 1.40 diff -u -p -r1.40 privsep.c --- usr.sbin/syslogd/privsep.c21 Aug 2014 17:00:34 - 1.40 +++ usr.sbin/syslogd/privsep.c22 Aug 2014 18:52:12 - @@ -330,7 +330,7 @@ priv_init(char *conf, int numeric, int l errx(1, rejected attempt to getnameinfo); /* Expecting: length, sockaddr */ must_read(socks[0], addr_len, sizeof(int)); - if (addr_len = 0 || addr_len sizeof(addr)) + if (addr_len = 0 || (size_t)addr_len sizeof(addr)) _exit(1); must_read(socks[0], addr, addr_len); if (getnameinfo((struct sockaddr *)addr, addr_len, @@ -459,7 +459,7 @@ check_tty_name(char *tty, size_t ttylen) char *p; /* Any path containing '..' is invalid. */ - for (p = tty; *p (p - tty) ttylen; p++) + for (p = tty; *p p tty + ttylen; p++) if (*p == '.' *(p + 1) == '.') goto bad_path; @@ -484,7 +484,7 @@ check_log_name(char *lognam, size_t logl char *p; /* Any path containing '..' is invalid. */ - for (p = lognam; *p (p - lognam) loglen; p++) + for (p = lognam; *p p lognam + loglen; p++) if (*p == '.' *(p + 1) == '.') goto bad_path; @@ -693,7 +693,7 @@ priv_getaddrinfo(char *host, char *serv, return (-1); /* Make sure we aren't overflowing the passed in buffer */ - if (addr_len ret_len) + if (ret_len 0 || (size_t)ret_len addr_len) errx(1, %s: overflow attempt in return, __func__); /* Read the resolved address and make sure we got all of it */ @@ -727,7 +727,7 @@ priv_getnameinfo(struct sockaddr *sa, so return (-1); /* Check we don't overflow the passed in buffer */ - if (hostlen ret_len) + if (ret_len 0 || (size_t)ret_len hostlen) errx(1, %s: overflow attempt in return, __func__); /* Read the resolved hostname */ @@ -767,7 +767,8 @@ static int may_read(int fd, void *buf, size_t n) { char *s = buf; - ssize_t res, pos = 0; + ssize_t res; + size_t pos = 0; while (n pos) { res = read(fd, s + pos, n - pos); @@ -790,7 +791,8 @@ static void must_read(int fd, void *buf, size_t n) { char *s = buf; - ssize_t res, pos = 0; + ssize_t res; + size_t pos = 0; while (n pos) { res = read(fd, s + pos, n - pos); @@ -812,7 +814,8 @@ static void must_write(int fd, void *buf, size_t n) { char *s = buf; - ssize_t res, pos = 0; + ssize_t res; + size_t pos = 0; while (n pos) { res = write(fd, s + pos, n - pos); Index: usr.sbin/syslogd/syslogd.c === RCS file: /data/mirror/openbsd/cvs/src/usr.sbin/syslogd/syslogd.c,v retrieving revision 1.117 diff -u -p -r1.117 syslogd.c --- usr.sbin/syslogd/syslogd.c22 Aug 2014 16:14:11 - 1.117 +++ usr.sbin/syslogd/syslogd.c22 Aug 2014 18:42:59 - @@ -868,10 +868,10 @@ fprintlog(struct filed *f, int flags, ch v = iov; if (f-f_type == F_WALL) { - if ((l = snprintf(greetings, sizeof(greetings), + l = snprintf(greetings, sizeof(greetings), \r\n\7Message from syslogd@%s at %.24s ...\r\n, - f-f_prevhost, ctime(now))) = sizeof(greetings) || - l == -1) + f-f_prevhost, ctime(now)); + if (l 0 || (size_t)l = sizeof(greetings)) l = strlen(greetings); v-iov_base = greetings; v-iov_len = l; @@ -898,9 +898,9 @@ fprintlog(struct filed *f, int flags, ch v-iov_base = msg; v-iov_len = strlen(msg); } else if (f-f_prevcount 1) { - if ((l = snprintf(repbuf, sizeof(repbuf), - last message repeated %d times, f-f_prevcount)) = - sizeof(repbuf) || l == -1) + l = snprintf(repbuf, sizeof(repbuf), + last message repeated %d times, f-f_prevcount); + if (l 0 || (size_t)l = sizeof(repbuf
Re: syslogd ipv6 proto6
On Fri, Aug 22, 2014 at 06:43:47PM +0200, Alexander Bluhm wrote: At the moment syslogd opens both IPv4 and IPv6 sockets unconditionally. I can restrict it to a protocol family with -4 and -6 command line switches. If the log server is a FQDN, DNS chosses wether to take the IPv4 or IPv6 route. For that I have invented a udp4:// or udp6:// prefix to choose a protocol. This syntax was chosen as I want to extend it to tcp:// and tls:// later. And here is the documentation. ok? bluhm Index: usr.sbin/syslogd/syslog.conf.5 === RCS file: /cvs/src/usr.sbin/syslogd/syslog.conf.5,v retrieving revision 1.25 diff -u -p -r1.25 syslog.conf.5 --- usr.sbin/syslogd/syslog.conf.5 21 Aug 2014 17:16:37 - 1.25 +++ usr.sbin/syslogd/syslog.conf.5 25 Aug 2014 19:22:09 - @@ -227,6 +227,8 @@ square brackets and .Ql ]\ .Pc . +A prefix udp4:// or udp6:// in front of the hostname and after the +at sign will force IPv4 or IPv6 addresses for UDP transport. .It A comma separated list of users. Selected messages are written to those users Index: usr.sbin/syslogd/syslogd.8 === RCS file: /cvs/src/usr.sbin/syslogd/syslogd.8,v retrieving revision 1.29 diff -u -p -r1.29 syslogd.8 --- usr.sbin/syslogd/syslogd.8 23 Jul 2014 05:57:36 - 1.29 +++ usr.sbin/syslogd/syslogd.8 25 Aug 2014 19:22:09 - @@ -39,7 +39,7 @@ .Sh SYNOPSIS .Nm syslogd .Bk -words -.Op Fl dhnu +.Op Fl 46dhnu .Op Fl a Ar path .Op Fl f Ar config_file .Op Fl m Ar mark_interval @@ -54,6 +54,14 @@ configuration file. .Pp The options are as follows: .Bl -tag -width Ds +.It Fl 4 +Forces +.Nm +to use IPv4 addresses only. +.It Fl 6 +Forces +.Nm +to use IPv6 addresses only. .It Fl a Ar path Specify a location where .Nm
syslog_r newline
Hi, When writing my regression test for syslogd, I realized that with LOG_CONS and LOG_PERROR trailing new lines are printed. Of course Perl Sys::Syslog that I use for the tests has bugs and appends '\n' in cases where it should not. But then I found this sentence in our man 3 syslog: A trailing newline is added if none is present. There is no such check in our syslog_r(3) libc function. It unconditionally adds new lines when writing to stderr or console. I would recommend to remove any trailing new line before adding it. The syslog rfc does not want trailing new lines, our syslogd converts them to spaces, and contrary to the documentation syslog_r(3) prints empty lines. While there, I found that LOG_CONS uses strchr() to find the beginning of the string. The code for LOG_PERROR saves a pointer. I would like to make a consistent implementation with conp and stdp pointer. Also add a check that iov_len does not get negative, even if we remove a new line. And fix the compiler warning /usr/src/lib/libc/gen/syslog_r.c:93: warning: 'stdp' may be used uninitialized in this function ok? bluhm Index: lib/libc/gen/syslog_r.c === RCS file: /data/mirror/openbsd/cvs/src/lib/libc/gen/syslog_r.c,v retrieving revision 1.5 diff -u -p -r1.5 syslog_r.c --- lib/libc/gen/syslog_r.c 14 Jul 2014 03:52:04 - 1.5 +++ lib/libc/gen/syslog_r.c 29 Aug 2014 20:33:00 - @@ -90,7 +90,7 @@ __vsyslog_r(int pri, struct syslog_data int fd, saved_errno, error; #defineTBUF_LEN2048 #defineFMT_LEN 1024 - char *stdp, tbuf[TBUF_LEN], fmt_cpy[FMT_LEN]; + char *conp = NULL, *stdp = NULL, tbuf[TBUF_LEN], fmt_cpy[FMT_LEN]; int tbuf_left, fmt_left, prlen; #defineINTERNALLOG LOG_ERR|LOG_CONS|LOG_PERROR|LOG_PID @@ -127,6 +127,8 @@ __vsyslog_r(int pri, struct syslog_data prlen = snprintf(p, tbuf_left, %d, pri); DEC(); + if (data-log_stat LOG_CONS) + conp = p; /* * syslogd will expand time automagically for reentrant case, and @@ -195,13 +197,17 @@ __vsyslog_r(int pri, struct syslog_data prlen = vsnprintf(p, tbuf_left, fmt_cpy, ap); DEC(); cnt = p - tbuf; + if (cnt 0 p[-1] == '\n') { + *(--p) = '\0'; + --cnt; + } /* Output to stderr if requested. */ if (data-log_stat LOG_PERROR) { struct iovec iov[2]; iov[0].iov_base = stdp; - iov[0].iov_len = cnt - (stdp - tbuf); + iov[0].iov_len = cnt stdp - tbuf ? cnt - (stdp - tbuf) : 0; iov[1].iov_base = \n; iov[1].iov_len = 1; (void)writev(STDERR_FILENO, iov, 2); @@ -222,9 +228,8 @@ __vsyslog_r(int pri, struct syslog_data (fd = open(_PATH_CONSOLE, O_WRONLY|O_NONBLOCK, 0)) = 0) { struct iovec iov[2]; - p = strchr(tbuf, '') + 1; - iov[0].iov_base = p; - iov[0].iov_len = cnt - (p - tbuf); + iov[0].iov_base = conp; + iov[0].iov_len = cnt conp - tbuf ? cnt - (conp - tbuf) : 0; iov[1].iov_base = \r\n; iov[1].iov_len = 2; (void)writev(fd, iov, 2);
syslogd libevent
Hi, I am currently working on converting syslogd to libevent. Theo recommended to do that before adding tcp and tls support. With this diff all my regression tests for syslogd pass. I will try to pull parts of the diff into separate changes to make review easier. I have not tested the syslogc feature yet. So I will write more tests before committing this. bluhm Index: usr.sbin/syslogd/Makefile === RCS file: /data/mirror/openbsd/cvs/src/usr.sbin/syslogd/Makefile,v retrieving revision 1.5 diff -u -p -r1.5 Makefile --- usr.sbin/syslogd/Makefile 4 Jan 2004 08:28:49 - 1.5 +++ usr.sbin/syslogd/Makefile 29 Aug 2014 15:09:10 - @@ -1,7 +1,8 @@ # $OpenBSD: Makefile,v 1.5 2004/01/04 08:28:49 djm Exp $ -PROG= syslogd -SRCS= syslogd.c ttymsg.c privsep.c privsep_fdpass.c ringbuf.c -MAN= syslogd.8 syslog.conf.5 +PROG = syslogd +SRCS = syslogd.c ttymsg.c privsep.c privsep_fdpass.c ringbuf.c +MAN = syslogd.8 syslog.conf.5 +LDFLAGS = -levent .include bsd.prog.mk Index: usr.sbin/syslogd/privsep.c === RCS file: /data/mirror/openbsd/cvs/src/usr.sbin/syslogd/privsep.c,v retrieving revision 1.43 diff -u -p -r1.43 privsep.c --- usr.sbin/syslogd/privsep.c 25 Aug 2014 20:19:14 - 1.43 +++ usr.sbin/syslogd/privsep.c 29 Aug 2014 15:09:10 - @@ -153,7 +153,6 @@ priv_init(char *conf, int numeric, int l dup2(nullfd, STDOUT_FILENO); dup2(nullfd, STDERR_FILENO); } - if (nullfd 2) close(nullfd); @@ -172,19 +171,21 @@ priv_init(char *conf, int numeric, int l close(socks[1]); /* Close descriptors that only the unpriv child needs */ - for (i = 0; i nfunix; i++) - if (pfd[PFD_UNIX_0 + i].fd != -1) - close(pfd[PFD_UNIX_0 + i].fd); - if (pfd[PFD_INET].fd != -1) - close(pfd[PFD_INET].fd); - if (pfd[PFD_INET6].fd != -1) - close(pfd[PFD_INET6].fd); - if (pfd[PFD_CTLSOCK].fd != -1) - close(pfd[PFD_CTLSOCK].fd); - if (pfd[PFD_CTLCONN].fd != -1) - close(pfd[PFD_CTLCONN].fd); - if (pfd[PFD_KLOG].fd) - close(pfd[PFD_KLOG].fd); + if (fd_ctlconn != -1) + close(fd_ctlconn); + if (fd_ctlsock != -1) + close(fd_ctlsock); + for (i = 0; i MAXFUNIX; i++) + if (fd_funix[i] != -1) + close(fd_funix[i]); + if (fd_klog != -1) + close(fd_klog); + if (fd_pair != -1) + close(fd_pair); + if (fd_udp != -1) + close(fd_udp); + if (fd_udp6 != -1) + close(fd_udp6); /* Save the config file specified by the child process */ if (strlcpy(config_file, conf, sizeof config_file) = sizeof(config_file)) @@ -369,11 +370,11 @@ priv_init(char *conf, int numeric, int l close(socks[0]); /* Unlink any domain sockets that have been opened */ - for (i = 0; i nfunix; i++) - if (funixn[i] != NULL pfd[PFD_UNIX_0 + i].fd != -1) - (void)unlink(funixn[i]); - if (ctlsock_path != NULL pfd[PFD_CTLSOCK].fd != -1) - (void)unlink(ctlsock_path); + for (i = 0; i MAXFUNIX; i++) + if (path_funix[i] != NULL fd_funix[i] != -1) + unlink(path_funix[i]); + if (path_ctlsock != NULL fd_ctlsock != -1) + unlink(path_ctlsock); if (restart) { int r; Index: usr.sbin/syslogd/syslogd.c === RCS file: /data/mirror/openbsd/cvs/src/usr.sbin/syslogd/syslogd.c,v retrieving revision 1.119 diff -u -p -r1.119 syslogd.c --- usr.sbin/syslogd/syslogd.c 25 Aug 2014 18:19:18 - 1.119 +++ usr.sbin/syslogd/syslogd.c 29 Aug 2014 17:34:52 - @@ -65,7 +65,6 @@ #include sys/param.h #include sys/ioctl.h #include sys/stat.h -#include sys/wait.h #include sys/socket.h #include sys/msgbuf.h #include sys/uio.h @@ -81,6 +80,7 @@ #include ctype.h #include errno.h #include err.h +#include event.h #include fcntl.h #include paths.h #include poll.h @@ -183,8 +183,7 @@ char*TypeNames[9] = { struct filed *Files; struct filed consfile; -intnfunix = 1; /* Number of Unix domain sockets requested */ -char *funixn[MAXFUNIX] = { _PATH_LOG }; /* Paths to Unix domain sockets */ +char *path_funix[MAXFUNIX] = { _PATH_LOG }; /* Path to Unix domain sockets */ intDebug; /* debug flag */ intStartup = 1;/* startup flag */ char LocalHostName[MAXHOSTNAMELEN]; /* our hostname */ @@ -199,7 +198,7 @@ int IPv4Only = 0; /* when true, disable intIPv6Only = 0; /* when true, disable IPv4 */ int
Re: apmd -A induced hangs
On Tue, Jul 29, 2014 at 12:19:43AM +0200, Alexander Bluhm wrote: Next I will try with this diff and without running apmd. I was runnig with the diff and without apmd and used sysctl hw.setperf manually. In this month my thinkpad never crashed. So I have added apmd -A again to rc.conf now and will report what happens. bluhm Index: acpicpu.c === RCS file: /home/cvs/src/sys/dev/acpi/acpicpu.c,v retrieving revision 1.60 diff -u -p -r1.60 acpicpu.c --- acpicpu.c 12 Jul 2014 18:48:17 - 1.60 +++ acpicpu.c 13 Jul 2014 14:00:03 - @@ -202,9 +202,7 @@ acpicpu_set_pdc(struct acpicpu_softc *sc static uint8_t cpu_oscuuid[16] = { 0x16, 0xA6, 0x77, 0x40, 0x0C, 0x29, 0xBE, 0x47, 0x9E, 0xBD, 0xD8, 0x70, 0x58, 0x71, 0x39, 0x53 }; - cap = ACPI_PDC_C_C1_HALT | ACPI_PDC_P_FFH | ACPI_PDC_C_C1_FFH - | ACPI_PDC_C_C2C3_FFH | ACPI_PDC_SMP_P_SWCOORD | ACPI_PDC_SMP_C2C3 - | ACPI_PDC_SMP_C1PT; + cap = ACPI_PDC_P_FFH | ACPI_PDC_C_C1_FFH; if (aml_searchname(sc-sc_devnode, _OSC)) { /* Query _OSC */ OpenBSD 5.6-current (GENERIC.MP) #97: Thu Aug 28 19:25:13 CEST 2014 bluhm@t430s.bluhm.invalid:/usr/src/sys/arch/amd64/compile/GENERIC.MP real mem = 16845570048 (16065MB) avail mem = 16388411392 (15629MB) mpath0 at root scsibus0 at mpath0: 256 targets mainbus0 at root bios0 at mainbus0: SMBIOS rev. 2.7 @ 0xbae9d000 (68 entries) bios0: vendor LENOVO version G7ET94WW (2.54 ) date 04/30/2013 bios0: LENOVO 2355CTO acpi0 at bios0: rev 2 acpi0: sleep states S0 S3 S4 S5 acpi0: tables DSDT FACP TCPA SSDT SSDT SSDT HPET APIC MCFG ECDT FPDT ASF! UEFI UEFI MSDM SSDT SSDT UEFI DBG2 acpi0: wakeup devices LID_(S4) SLPB(S3) IGBE(S4) EXP3(S4) XHCI(S3) EHC1(S3) EHC2(S3) HDEF(S4) acpitimer0 at acpi0: 3579545 Hz, 24 bits acpihpet0 at acpi0: 14318179 Hz acpimadt0 at acpi0 addr 0xfee0: PC-AT compat cpu0 at mainbus0: apid 0 (boot processor) cpu0: Intel(R) Core(TM) i7-3520M CPU @ 2.90GHz, 2893.88 MHz cpu0: FPU,VME,DE,PSE,TSC,MSR,PAE,MCE,CX8,APIC,SEP,MTRR,PGE,MCA,CMOV,PAT,PSE36,CFLUSH,DS,ACPI,MMX,FXSR,SSE,SSE2,SS,HTT,TM,PBE,SSE3,PCLMUL,DTES64,MWAIT,DS-CPL,VMX,SMX,EST,TM2,SSSE3,CX16,xTPR,PDCM,PCID,SSE4.1,SSE4.2,x2APIC,POPCNT,DEADLINE,AES,XSAVE,AVX,F16C,RDRAND,NXE,LONG,LAHF,PERF,ITSC,FSGSBASE,SMEP,ERMS cpu0: 256KB 64b/line 8-way L2 cache cpu0: smt 0, core 0, package 0 mtrr: Pentium Pro MTRR support, 10 var ranges, 88 fixed ranges cpu0: apic clock running at 99MHz cpu0: mwait min=64, max=64, C-substates=0.2.1.1.2, IBE cpu1 at mainbus0: apid 1 (application processor) cpu1: Intel(R) Core(TM) i7-3520M CPU @ 2.90GHz, 2893.43 MHz cpu1: FPU,VME,DE,PSE,TSC,MSR,PAE,MCE,CX8,APIC,SEP,MTRR,PGE,MCA,CMOV,PAT,PSE36,CFLUSH,DS,ACPI,MMX,FXSR,SSE,SSE2,SS,HTT,TM,PBE,SSE3,PCLMUL,DTES64,MWAIT,DS-CPL,VMX,SMX,EST,TM2,SSSE3,CX16,xTPR,PDCM,PCID,SSE4.1,SSE4.2,x2APIC,POPCNT,DEADLINE,AES,XSAVE,AVX,F16C,RDRAND,NXE,LONG,LAHF,PERF,ITSC,FSGSBASE,SMEP,ERMS cpu1: 256KB 64b/line 8-way L2 cache cpu1: smt 1, core 0, package 0 cpu2 at mainbus0: apid 2 (application processor) cpu2: Intel(R) Core(TM) i7-3520M CPU @ 2.90GHz, 2893.43 MHz cpu2: FPU,VME,DE,PSE,TSC,MSR,PAE,MCE,CX8,APIC,SEP,MTRR,PGE,MCA,CMOV,PAT,PSE36,CFLUSH,DS,ACPI,MMX,FXSR,SSE,SSE2,SS,HTT,TM,PBE,SSE3,PCLMUL,DTES64,MWAIT,DS-CPL,VMX,SMX,EST,TM2,SSSE3,CX16,xTPR,PDCM,PCID,SSE4.1,SSE4.2,x2APIC,POPCNT,DEADLINE,AES,XSAVE,AVX,F16C,RDRAND,NXE,LONG,LAHF,PERF,ITSC,FSGSBASE,SMEP,ERMS cpu2: 256KB 64b/line 8-way L2 cache cpu2: smt 0, core 1, package 0 cpu3 at mainbus0: apid 3 (application processor) cpu3: Intel(R) Core(TM) i7-3520M CPU @ 2.90GHz, 2893.43 MHz cpu3: FPU,VME,DE,PSE,TSC,MSR,PAE,MCE,CX8,APIC,SEP,MTRR,PGE,MCA,CMOV,PAT,PSE36,CFLUSH,DS,ACPI,MMX,FXSR,SSE,SSE2,SS,HTT,TM,PBE,SSE3,PCLMUL,DTES64,MWAIT,DS-CPL,VMX,SMX,EST,TM2,SSSE3,CX16,xTPR,PDCM,PCID,SSE4.1,SSE4.2,x2APIC,POPCNT,DEADLINE,AES,XSAVE,AVX,F16C,RDRAND,NXE,LONG,LAHF,PERF,ITSC,FSGSBASE,SMEP,ERMS cpu3: 256KB 64b/line 8-way L2 cache cpu3: smt 1, core 1, package 0 ioapic0 at mainbus0: apid 2 pa 0xfec0, version 20, 24 pins acpimcfg0 at acpi0 addr 0xf800, bus 0-63 acpiec0 at acpi0 acpiprt0 at acpi0: bus 0 (PCI0) acpiprt1 at acpi0: bus -1 (PEG_) acpiprt2 at acpi0: bus 2 (EXP1) acpiprt3 at acpi0: bus 3 (EXP2) acpiprt4 at acpi0: bus 4 (EXP3) acpiprt5 at acpi0: bus 12 (EXP5) acpiprt6 at acpi0: bus -1 (EXP6) acpiprt7 at acpi0: bus -1 (EXP7) acpiprt8 at acpi0: bus -1 (EXP8) acpicpu0 at acpi0: C3, PSS acpicpu1 at acpi0: C3 acpicpu2 at acpi0: C3 acpicpu3 at acpi0: C3 acpipwrres0 at acpi0: PUBS, resource for XHCI, EHC1, EHC2 acpitz0 at acpi0: critical temperature is 103 degC acpibtn0 at acpi0: LID_ acpibtn1 at acpi0: SLPB acpibat0 at acpi0: BAT0 model 45N1143 serial 663 type LION oem Panasonic acpibat1 at acpi0: BAT1 not present acpiac0 at acpi0: AC unit online acpithinkpad0 at acpi0 cpu0: Enhanced SpeedStep 2893 MHz: speeds: 2901, 2900, 2800
Re: syslogd libevent
On Fri, Aug 29, 2014 at 11:25:52PM +0200, Alexander Bluhm wrote: I will try to pull parts of the diff into separate changes to make review easier. Let's start with an obvious bug. Do not call free() on an array in the data section. Fortunately the code was not reached. No binary change. ok? bluhm Index: usr.sbin/syslogd/syslogd.c === RCS file: /data/mirror/openbsd/cvs/src/usr.sbin/syslogd/syslogd.c,v retrieving revision 1.119 diff -u -p -r1.119 syslogd.c --- usr.sbin/syslogd/syslogd.c 25 Aug 2014 18:19:18 - 1.119 +++ usr.sbin/syslogd/syslogd.c 31 Aug 2014 20:00:14 - @@ -646,7 +646,6 @@ main(int argc, char *argv[]) } } /* NOTREACHED */ - free(pfd); return (0); }
Re: syslogd libevent handler
On Fri, Aug 29, 2014 at 11:25:52PM +0200, Alexander Bluhm wrote: I will try to pull parts of the diff into separate changes to make review easier. Move the handlers for the poll events into separate functions. They will become the libevent callbacks later. ok? bluhm Index: usr.sbin/syslogd/syslogd.c === RCS file: /data/mirror/openbsd/cvs/src/usr.sbin/syslogd/syslogd.c,v retrieving revision 1.119 diff -u -p -r1.119 syslogd.c --- usr.sbin/syslogd/syslogd.c 25 Aug 2014 18:19:18 - 1.119 +++ usr.sbin/syslogd/syslogd.c 31 Aug 2014 20:34:01 - @@ -245,6 +245,13 @@ char *reply_text;/* Start of reply tex size_t ctl_reply_size = 0; /* Number of bytes used in reply */ size_t ctl_reply_offset = 0; /* Number of bytes of reply written so far */ +char *linebuf; +int linesize; + +voidklog_read_handler(int); +voidudp_read_handler(int); +voidunix_read_handler(int); + struct pollfd pfd[N_PFD]; volatile sig_atomic_t MarkSet; @@ -283,12 +290,8 @@ void logto_ctlconn(char *); int main(int argc, char *argv[]) { - int ch, i, linesize, fd; - struct sockaddr_un fromunix; - struct sockaddr_storage from; - socklen_t len; - char *p, *line; - char resolve[MAXHOSTNAMELEN]; + int ch, i, fd; + char *p; int lockpipe[2] = { -1, -1}, pair[2], nullfd; struct addrinfo hints, *res, *res0; FILE *fp; @@ -368,7 +371,7 @@ main(int argc, char *argv[]) if (linesize MAXLINE) linesize = MAXLINE; linesize++; - if ((line = malloc(linesize)) == NULL) { + if ((linebuf = malloc(linesize)) == NULL) { logerror(Couldn't allocate line buffer); die(0); } @@ -586,41 +589,13 @@ main(int argc, char *argv[]) } if ((pfd[PFD_KLOG].revents POLLIN) != 0) { - i = read(pfd[PFD_KLOG].fd, line, linesize - 1); - if (i 0) { - line[i] = '\0'; - printsys(line); - } else if (i 0 errno != EINTR) { - logerror(klog); - pfd[PFD_KLOG].fd = -1; - pfd[PFD_KLOG].events = 0; - } + klog_read_handler(pfd[PFD_KLOG].fd); } if ((pfd[PFD_INET].revents POLLIN) != 0) { - len = sizeof(from); - i = recvfrom(pfd[PFD_INET].fd, line, MAXLINE, 0, - (struct sockaddr *)from, len); - if (i 0) { - line[i] = '\0'; - cvthname((struct sockaddr *)from, resolve, - sizeof(resolve)); - dprintf(cvthname res: %s\n, resolve); - printline(resolve, line); - } else if (i 0 errno != EINTR) - logerror(recvfrom inet); + udp_read_handler(pfd[PFD_INET].fd); } if ((pfd[PFD_INET6].revents POLLIN) != 0) { - len = sizeof(from); - i = recvfrom(pfd[PFD_INET6].fd, line, MAXLINE, 0, - (struct sockaddr *)from, len); - if (i 0) { - line[i] = '\0'; - cvthname((struct sockaddr *)from, resolve, - sizeof(resolve)); - dprintf(cvthname res: %s\n, resolve); - printline(resolve, line); - } else if (i 0 errno != EINTR) - logerror(recvfrom inet6); + udp_read_handler(pfd[PFD_INET6].fd); } if ((pfd[PFD_CTLSOCK].revents POLLIN) != 0) ctlsock_accept_handler(); @@ -631,23 +606,65 @@ main(int argc, char *argv[]) for (i = 0; i nfunix; i++) { if ((pfd[PFD_UNIX_0 + i].revents POLLIN) != 0) { - ssize_t rlen; - - len = sizeof(fromunix); - rlen = recvfrom(pfd[PFD_UNIX_0 + i].fd, line, - MAXLINE, 0, (struct sockaddr *)fromunix, - len); - if (rlen 0) { - line[rlen] = '\0'; - printline(LocalHostName, line); - } else if (rlen == -1 errno != EINTR) - logerror(recvfrom unix); + udp_read_handler(pfd[PFD_UNIX_0 + i].fd
Re: syslogd libevent
On Fri, Aug 29, 2014 at 11:25:52PM +0200, Alexander Bluhm wrote: I will try to pull parts of the diff into separate changes to make review easier. The reapchild() signal handler collects all children. This can be done easier by ignoring SIGCHLD. ok? bluhm Index: usr.sbin/syslogd/syslogd.c === RCS file: /cvs/src/usr.sbin/syslogd/syslogd.c,v retrieving revision 1.120 diff -u -p -r1.120 syslogd.c --- usr.sbin/syslogd/syslogd.c 31 Aug 2014 20:51:31 - 1.120 +++ usr.sbin/syslogd/syslogd.c 31 Aug 2014 21:00:04 - @@ -266,7 +266,6 @@ voidlogmsg(int, char *, char *, int); struct filed *find_dup(struct filed *); void printline(char *, char *); void printsys(char *); -void reapchild(int); char *ttymsg(struct iovec *, int, char *, int); void usage(void); void wallmsg(struct filed *, struct iovec *); @@ -553,7 +552,7 @@ main(int argc, char *argv[]) (void)signal(SIGTERM, dodie); (void)signal(SIGINT, Debug ? dodie : SIG_IGN); (void)signal(SIGQUIT, Debug ? dodie : SIG_IGN); - (void)signal(SIGCHLD, reapchild); + (void)signal(SIGCHLD, SIG_IGN); (void)signal(SIGALRM, domark); (void)signal(SIGPIPE, SIG_IGN); (void)alarm(TIMERINTVL); @@ -1117,18 +1116,6 @@ wallmsg(struct filed *f, struct iovec *i } (void)fclose(uf); reenter = 0; -} - -/* ARGSUSED */ -void -reapchild(int signo) -{ - int save_errno = errno; - int status; - - while (waitpid(-1, status, WNOHANG) 0) - ; - errno = save_errno; } /*
Re: apmd -A induced hangs
On Sun, Aug 31, 2014 at 09:44:11PM +0200, Alexander Bluhm wrote: On Tue, Jul 29, 2014 at 12:19:43AM +0200, Alexander Bluhm wrote: Next I will try with this diff and without running apmd. I was runnig with the diff and without apmd and used sysctl hw.setperf manually. In this month my thinkpad never crashed. So I have added apmd -A again to rc.conf now and will report what happens. With the diff and with apmd -A I had 2 hangs in less than 3 days. Next test will be with the diff and with apmd -C on my T430s. bluhm Index: acpicpu.c === RCS file: /home/cvs/src/sys/dev/acpi/acpicpu.c,v retrieving revision 1.60 diff -u -p -r1.60 acpicpu.c --- acpicpu.c 12 Jul 2014 18:48:17 - 1.60 +++ acpicpu.c 13 Jul 2014 14:00:03 - @@ -202,9 +202,7 @@ acpicpu_set_pdc(struct acpicpu_softc *sc static uint8_t cpu_oscuuid[16] = { 0x16, 0xA6, 0x77, 0x40, 0x0C, 0x29, 0xBE, 0x47, 0x9E, 0xBD, 0xD8, 0x70, 0x58, 0x71, 0x39, 0x53 }; - cap = ACPI_PDC_C_C1_HALT | ACPI_PDC_P_FFH | ACPI_PDC_C_C1_FFH - | ACPI_PDC_C_C2C3_FFH | ACPI_PDC_SMP_P_SWCOORD | ACPI_PDC_SMP_C2C3 - | ACPI_PDC_SMP_C1PT; + cap = ACPI_PDC_P_FFH | ACPI_PDC_C_C1_FFH; if (aml_searchname(sc-sc_devnode, _OSC)) { /* Query _OSC */ OpenBSD 5.6-current (GENERIC.MP) #99: Tue Sep 2 00:52:02 CEST 2014 bluhm@t430s.bluhm.invalid:/usr/src/sys/arch/amd64/compile/GENERIC.MP real mem = 16845570048 (16065MB) avail mem = 16388403200 (15629MB) mpath0 at root scsibus0 at mpath0: 256 targets mainbus0 at root bios0 at mainbus0: SMBIOS rev. 2.7 @ 0xbae9d000 (68 entries) bios0: vendor LENOVO version G7ET94WW (2.54 ) date 04/30/2013 bios0: LENOVO 2355CTO acpi0 at bios0: rev 2 acpi0: sleep states S0 S3 S4 S5 acpi0: tables DSDT FACP TCPA SSDT SSDT SSDT HPET APIC MCFG ECDT FPDT ASF! UEFI UEFI MSDM SSDT SSDT UEFI DBG2 acpi0: wakeup devices LID_(S4) SLPB(S3) IGBE(S4) EXP3(S4) XHCI(S3) EHC1(S3) EHC2(S3) HDEF(S4) acpitimer0 at acpi0: 3579545 Hz, 24 bits acpihpet0 at acpi0: 14318179 Hz acpimadt0 at acpi0 addr 0xfee0: PC-AT compat cpu0 at mainbus0: apid 0 (boot processor) cpu0: Intel(R) Core(TM) i7-3520M CPU @ 2.90GHz, 2893.86 MHz cpu0: FPU,VME,DE,PSE,TSC,MSR,PAE,MCE,CX8,APIC,SEP,MTRR,PGE,MCA,CMOV,PAT,PSE36,CFLUSH,DS,ACPI,MMX,FXSR,SSE,SSE2,SS,HTT,TM,PBE,SSE3,PCLMUL,DTES64,MWAIT,DS-CPL,VMX,SMX,EST,TM2,SSSE3,CX16,xTPR,PDCM,PCID,SSE4.1,SSE4.2,x2APIC,POPCNT,DEADLINE,AES,XSAVE,AVX,F16C,RDRAND,NXE,LONG,LAHF,PERF,ITSC,FSGSBASE,SMEP,ERMS cpu0: 256KB 64b/line 8-way L2 cache cpu0: smt 0, core 0, package 0 mtrr: Pentium Pro MTRR support, 10 var ranges, 88 fixed ranges cpu0: apic clock running at 99MHz cpu0: mwait min=64, max=64, C-substates=0.2.1.1.2, IBE cpu1 at mainbus0: apid 1 (application processor) cpu1: Intel(R) Core(TM) i7-3520M CPU @ 2.90GHz, 2893.42 MHz cpu1: FPU,VME,DE,PSE,TSC,MSR,PAE,MCE,CX8,APIC,SEP,MTRR,PGE,MCA,CMOV,PAT,PSE36,CFLUSH,DS,ACPI,MMX,FXSR,SSE,SSE2,SS,HTT,TM,PBE,SSE3,PCLMUL,DTES64,MWAIT,DS-CPL,VMX,SMX,EST,TM2,SSSE3,CX16,xTPR,PDCM,PCID,SSE4.1,SSE4.2,x2APIC,POPCNT,DEADLINE,AES,XSAVE,AVX,F16C,RDRAND,NXE,LONG,LAHF,PERF,ITSC,FSGSBASE,SMEP,ERMS cpu1: 256KB 64b/line 8-way L2 cache cpu1: smt 1, core 0, package 0 cpu2 at mainbus0: apid 2 (application processor) cpu2: Intel(R) Core(TM) i7-3520M CPU @ 2.90GHz, 2893.42 MHz cpu2: FPU,VME,DE,PSE,TSC,MSR,PAE,MCE,CX8,APIC,SEP,MTRR,PGE,MCA,CMOV,PAT,PSE36,CFLUSH,DS,ACPI,MMX,FXSR,SSE,SSE2,SS,HTT,TM,PBE,SSE3,PCLMUL,DTES64,MWAIT,DS-CPL,VMX,SMX,EST,TM2,SSSE3,CX16,xTPR,PDCM,PCID,SSE4.1,SSE4.2,x2APIC,POPCNT,DEADLINE,AES,XSAVE,AVX,F16C,RDRAND,NXE,LONG,LAHF,PERF,ITSC,FSGSBASE,SMEP,ERMS cpu2: 256KB 64b/line 8-way L2 cache cpu2: smt 0, core 1, package 0 cpu3 at mainbus0: apid 3 (application processor) cpu3: Intel(R) Core(TM) i7-3520M CPU @ 2.90GHz, 2893.42 MHz cpu3: FPU,VME,DE,PSE,TSC,MSR,PAE,MCE,CX8,APIC,SEP,MTRR,PGE,MCA,CMOV,PAT,PSE36,CFLUSH,DS,ACPI,MMX,FXSR,SSE,SSE2,SS,HTT,TM,PBE,SSE3,PCLMUL,DTES64,MWAIT,DS-CPL,VMX,SMX,EST,TM2,SSSE3,CX16,xTPR,PDCM,PCID,SSE4.1,SSE4.2,x2APIC,POPCNT,DEADLINE,AES,XSAVE,AVX,F16C,RDRAND,NXE,LONG,LAHF,PERF,ITSC,FSGSBASE,SMEP,ERMS cpu3: 256KB 64b/line 8-way L2 cache cpu3: smt 1, core 1, package 0 ioapic0 at mainbus0: apid 2 pa 0xfec0, version 20, 24 pins acpimcfg0 at acpi0 addr 0xf800, bus 0-63 acpiec0 at acpi0 acpiprt0 at acpi0: bus 0 (PCI0) acpiprt1 at acpi0: bus -1 (PEG_) acpiprt2 at acpi0: bus 2 (EXP1) acpiprt3 at acpi0: bus 3 (EXP2) acpiprt4 at acpi0: bus 4 (EXP3) acpiprt5 at acpi0: bus 12 (EXP5) acpiprt6 at acpi0: bus -1 (EXP6) acpiprt7 at acpi0: bus -1 (EXP7) acpiprt8 at acpi0: bus -1 (EXP8) acpicpu0 at acpi0: C3, PSS acpicpu1 at acpi0: C3 acpicpu2 at acpi0: C3 acpicpu3 at acpi0: C3 acpipwrres0 at acpi0: PUBS, resource for XHCI, EHC1, EHC2 acpitz0 at acpi0: critical temperature is 103 degC acpibtn0 at acpi0: LID_ acpibtn1 at acpi0: SLPB acpibat0 at acpi0: BAT0 model
Re: syslogd libevent
On Fri, Aug 29, 2014 at 11:25:52PM +0200, Alexander Bluhm wrote: So I will write more tests before committing this. My regression tests found a bug in syslogd. When adding the maximum number of paths with the -a option, the arrays for unix domain socket paths and the poll file descriptors overflow by one. - increase pfd array by one - operate on size of arrays not length - null check for path not necessary when doing fd -1 check - rename variables consistently ...unix - make number of unix fds a local variable ok? bluhm Index: usr.sbin/syslogd/privsep.c === RCS file: /data/mirror/openbsd/cvs/src/usr.sbin/syslogd/privsep.c,v retrieving revision 1.43 diff -u -p -r1.43 privsep.c --- usr.sbin/syslogd/privsep.c 25 Aug 2014 20:19:14 - 1.43 +++ usr.sbin/syslogd/privsep.c 3 Sep 2014 16:08:03 - @@ -172,7 +172,7 @@ priv_init(char *conf, int numeric, int l close(socks[1]); /* Close descriptors that only the unpriv child needs */ - for (i = 0; i nfunix; i++) + for (i = 0; i MAXUNIX + 1; i++) if (pfd[PFD_UNIX_0 + i].fd != -1) close(pfd[PFD_UNIX_0 + i].fd); if (pfd[PFD_INET].fd != -1) @@ -369,9 +369,9 @@ priv_init(char *conf, int numeric, int l close(socks[0]); /* Unlink any domain sockets that have been opened */ - for (i = 0; i nfunix; i++) - if (funixn[i] != NULL pfd[PFD_UNIX_0 + i].fd != -1) - (void)unlink(funixn[i]); + for (i = 0; i MAXUNIX; i++) + if (pfd[PFD_UNIX_0 + i].fd != -1) + (void)unlink(path_unix[i]); if (ctlsock_path != NULL pfd[PFD_CTLSOCK].fd != -1) (void)unlink(ctlsock_path); Index: usr.sbin/syslogd/syslogd.c === RCS file: /data/mirror/openbsd/cvs/src/usr.sbin/syslogd/syslogd.c,v retrieving revision 1.121 diff -u -p -r1.121 syslogd.c --- usr.sbin/syslogd/syslogd.c 31 Aug 2014 22:11:43 - 1.121 +++ usr.sbin/syslogd/syslogd.c 3 Sep 2014 16:40:54 - @@ -183,8 +183,7 @@ char*TypeNames[9] = { struct filed *Files; struct filed consfile; -intnfunix = 1; /* Number of Unix domain sockets requested */ -char *funixn[MAXFUNIX] = { _PATH_LOG }; /* Paths to Unix domain sockets */ +char *path_unix[MAXUNIX] = { _PATH_LOG }; /* Paths to Unix domain sockets */ intDebug; /* debug flag */ intStartup = 1;/* startup flag */ char LocalHostName[MAXHOSTNAMELEN]; /* our hostname */ @@ -282,7 +281,7 @@ voidlogto_ctlconn(char *); int main(int argc, char *argv[]) { - int ch, i, linesize, fd; + int ch, i, linesize, fd, nunix = 1; struct sockaddr_un fromunix; struct sockaddr_storage from; socklen_t len; @@ -292,6 +291,9 @@ main(int argc, char *argv[]) struct addrinfo hints, *res, *res0; FILE *fp; + for (i = 0; i N_PFD; i++) + pfd[i].fd = -1; + while ((ch = getopt(argc, argv, 46dhnuf:m:p:a:s:)) != -1) switch (ch) { case '4': /* disable IPv6 */ @@ -318,18 +320,18 @@ main(int argc, char *argv[]) NoDNS = 1; break; case 'p': /* path */ - funixn[0] = optarg; + path_unix[0] = optarg; break; case 'u': /* allow udp input port */ SecureMode = 0; break; case 'a': - if (nfunix = MAXFUNIX) + if (nunix = MAXUNIX) fprintf(stderr, syslogd: out of descriptors, ignoring %s\n, optarg); else - funixn[nfunix++] = optarg; + path_unix[nunix++] = optarg; break; case 's': ctlsock_path = optarg; @@ -439,8 +441,8 @@ main(int argc, char *argv[]) #ifndef SUN_LEN #define SUN_LEN(unp) (strlen((unp)-sun_path) + 2) #endif - for (i = 0; i nfunix; i++) { - if ((fd = unix_socket(funixn[i], SOCK_DGRAM, 0666)) == -1) { + for (i = 0; i nunix; i++) { + if ((fd = unix_socket(path_unix[i], SOCK_DGRAM, 0666)) == -1) { if (i == 0 !Debug) die(0); continue; @@ -450,7 +452,7 @@ main(int argc, char *argv[]) pfd[PFD_UNIX_0 + i].events = POLLIN; } - nfunix++; + nunix++; if (socketpair(AF_UNIX, SOCK_DGRAM, PF_UNSPEC, pair) == -1) die(0); fd = pair[0]; @@ -575,7 +577,7 @@ main(int
Re: splnet() and SIOCSIFADDR
On Wed, Sep 03, 2014 at 03:53:34PM +0200, Martin Pieuchot wrote: @@ -1078,7 +1079,7 @@ in6_purgeaddr(struct ifaddr *ifa) void in6_unlink_ifa(struct in6_ifaddr *ia6, struct ifnet *ifp) { - int s = splnet(); + splsoftassert(IPL_SOFTNET); ifa_del(ifp, ia6-ia_ifa); I think there are code paths that can trigger this assertion netinet6/in6.c: in6_unlink_ifa() netinet6/in6.c: in6_purgeaddr() netinet6/nd6_rtr.c: purge_detached() netinet6/nd6_rtr.c: nd6_prelist_add() netinet6/in6.c: in6_control() netinet/tcp_usrreq.c: tcp_usrreq() kern/sys_socket.c: soo_ioctl() netinet6/in6.c: in6_unlink_ifa() netinet6/in6.c: in6_purgeaddr() netinet6/nd6_rtr.c: purge_detached() netinet6/nd6_rtr.c: nd6_prelist_add() netinet6/in6_ifattach.c:in6_ifattach_linklocal() netinet/ip_carp.c carp_set_enaddr() netinet/ip_carp.c carp_ioctl() ... nd6_prelist_add() does some splsoftnet() already. I think you should put one around purge_detached() there. bluhm
Re: syslogd libevent handler
On Sun, Aug 31, 2014 at 10:46:50PM +0200, Alexander Bluhm wrote: On Fri, Aug 29, 2014 at 11:25:52PM +0200, Alexander Bluhm wrote: I will try to pull parts of the diff into separate changes to make review easier. Move the handlers for the poll events into separate functions. They will become the libevent callbacks later. ok? anyone? bluhm Index: usr.sbin/syslogd/syslogd.c === RCS file: /data/mirror/openbsd/cvs/src/usr.sbin/syslogd/syslogd.c,v retrieving revision 1.119 diff -u -p -r1.119 syslogd.c --- usr.sbin/syslogd/syslogd.c25 Aug 2014 18:19:18 - 1.119 +++ usr.sbin/syslogd/syslogd.c31 Aug 2014 20:34:01 - @@ -245,6 +245,13 @@ char *reply_text;/* Start of reply tex size_t ctl_reply_size = 0; /* Number of bytes used in reply */ size_t ctl_reply_offset = 0; /* Number of bytes of reply written so far */ +char *linebuf; +int linesize; + +void klog_read_handler(int); +void udp_read_handler(int); +void unix_read_handler(int); + struct pollfd pfd[N_PFD]; volatile sig_atomic_t MarkSet; @@ -283,12 +290,8 @@ void logto_ctlconn(char *); int main(int argc, char *argv[]) { - int ch, i, linesize, fd; - struct sockaddr_un fromunix; - struct sockaddr_storage from; - socklen_t len; - char *p, *line; - char resolve[MAXHOSTNAMELEN]; + int ch, i, fd; + char *p; int lockpipe[2] = { -1, -1}, pair[2], nullfd; struct addrinfo hints, *res, *res0; FILE *fp; @@ -368,7 +371,7 @@ main(int argc, char *argv[]) if (linesize MAXLINE) linesize = MAXLINE; linesize++; - if ((line = malloc(linesize)) == NULL) { + if ((linebuf = malloc(linesize)) == NULL) { logerror(Couldn't allocate line buffer); die(0); } @@ -586,41 +589,13 @@ main(int argc, char *argv[]) } if ((pfd[PFD_KLOG].revents POLLIN) != 0) { - i = read(pfd[PFD_KLOG].fd, line, linesize - 1); - if (i 0) { - line[i] = '\0'; - printsys(line); - } else if (i 0 errno != EINTR) { - logerror(klog); - pfd[PFD_KLOG].fd = -1; - pfd[PFD_KLOG].events = 0; - } + klog_read_handler(pfd[PFD_KLOG].fd); } if ((pfd[PFD_INET].revents POLLIN) != 0) { - len = sizeof(from); - i = recvfrom(pfd[PFD_INET].fd, line, MAXLINE, 0, - (struct sockaddr *)from, len); - if (i 0) { - line[i] = '\0'; - cvthname((struct sockaddr *)from, resolve, - sizeof(resolve)); - dprintf(cvthname res: %s\n, resolve); - printline(resolve, line); - } else if (i 0 errno != EINTR) - logerror(recvfrom inet); + udp_read_handler(pfd[PFD_INET].fd); } if ((pfd[PFD_INET6].revents POLLIN) != 0) { - len = sizeof(from); - i = recvfrom(pfd[PFD_INET6].fd, line, MAXLINE, 0, - (struct sockaddr *)from, len); - if (i 0) { - line[i] = '\0'; - cvthname((struct sockaddr *)from, resolve, - sizeof(resolve)); - dprintf(cvthname res: %s\n, resolve); - printline(resolve, line); - } else if (i 0 errno != EINTR) - logerror(recvfrom inet6); + udp_read_handler(pfd[PFD_INET6].fd); } if ((pfd[PFD_CTLSOCK].revents POLLIN) != 0) ctlsock_accept_handler(); @@ -631,23 +606,65 @@ main(int argc, char *argv[]) for (i = 0; i nfunix; i++) { if ((pfd[PFD_UNIX_0 + i].revents POLLIN) != 0) { - ssize_t rlen; - - len = sizeof(fromunix); - rlen = recvfrom(pfd[PFD_UNIX_0 + i].fd, line, - MAXLINE, 0, (struct sockaddr *)fromunix, - len); - if (rlen 0) { - line[rlen] = '\0'; - printline(LocalHostName, line); - } else if (rlen == -1 errno != EINTR) - logerror(recvfrom unix
Re: syslogd libevent handler
On Wed, Sep 03, 2014 at 04:34:47PM -0700, Doug Hogan wrote: On Sun, Aug 31, 2014 at 10:46:50PM +0200, Alexander Bluhm wrote: Move the handlers for the poll events into separate functions. They will become the libevent callbacks later. ... + udp_read_handler(pfd[PFD_UNIX_0 + i].fd); ... Shouldn't this be a call to unix_read_handler() instead of udp_read_handler()? Yes, of course. This bug can be seen in the test output: Sep 04 13:18:17 ??? syslogd-regress[21485]: syslogd regress test log message Sep 04 13:21:35 t430s syslogd-regress[23917]: syslogd regress test log message I have added a check to regress. Thanks for finding this, updated diff below. Index: usr.sbin/syslogd/syslogd.c === RCS file: /data/mirror/openbsd/cvs/src/usr.sbin/syslogd/syslogd.c,v retrieving revision 1.121 diff -u -p -r1.121 syslogd.c --- usr.sbin/syslogd/syslogd.c 31 Aug 2014 22:11:43 - 1.121 +++ usr.sbin/syslogd/syslogd.c 4 Sep 2014 11:19:05 - @@ -245,6 +245,13 @@ char *reply_text;/* Start of reply tex size_t ctl_reply_size = 0; /* Number of bytes used in reply */ size_t ctl_reply_offset = 0; /* Number of bytes of reply written so far */ +char *linebuf; +int linesize; + +voidklog_read_handler(int); +voidudp_read_handler(int); +voidunix_read_handler(int); + struct pollfd pfd[N_PFD]; volatile sig_atomic_t MarkSet; @@ -282,12 +289,8 @@ void logto_ctlconn(char *); int main(int argc, char *argv[]) { - int ch, i, linesize, fd; - struct sockaddr_un fromunix; - struct sockaddr_storage from; - socklen_t len; - char *p, *line; - char resolve[MAXHOSTNAMELEN]; + int ch, i, fd; + char *p; int lockpipe[2] = { -1, -1}, pair[2], nullfd; struct addrinfo hints, *res, *res0; FILE *fp; @@ -367,7 +370,7 @@ main(int argc, char *argv[]) if (linesize MAXLINE) linesize = MAXLINE; linesize++; - if ((line = malloc(linesize)) == NULL) { + if ((linebuf = malloc(linesize)) == NULL) { logerror(Couldn't allocate line buffer); die(0); } @@ -585,41 +588,13 @@ main(int argc, char *argv[]) } if ((pfd[PFD_KLOG].revents POLLIN) != 0) { - i = read(pfd[PFD_KLOG].fd, line, linesize - 1); - if (i 0) { - line[i] = '\0'; - printsys(line); - } else if (i 0 errno != EINTR) { - logerror(klog); - pfd[PFD_KLOG].fd = -1; - pfd[PFD_KLOG].events = 0; - } + klog_read_handler(pfd[PFD_KLOG].fd); } if ((pfd[PFD_INET].revents POLLIN) != 0) { - len = sizeof(from); - i = recvfrom(pfd[PFD_INET].fd, line, MAXLINE, 0, - (struct sockaddr *)from, len); - if (i 0) { - line[i] = '\0'; - cvthname((struct sockaddr *)from, resolve, - sizeof(resolve)); - dprintf(cvthname res: %s\n, resolve); - printline(resolve, line); - } else if (i 0 errno != EINTR) - logerror(recvfrom inet); + udp_read_handler(pfd[PFD_INET].fd); } if ((pfd[PFD_INET6].revents POLLIN) != 0) { - len = sizeof(from); - i = recvfrom(pfd[PFD_INET6].fd, line, MAXLINE, 0, - (struct sockaddr *)from, len); - if (i 0) { - line[i] = '\0'; - cvthname((struct sockaddr *)from, resolve, - sizeof(resolve)); - dprintf(cvthname res: %s\n, resolve); - printline(resolve, line); - } else if (i 0 errno != EINTR) - logerror(recvfrom inet6); + udp_read_handler(pfd[PFD_INET6].fd); } if ((pfd[PFD_CTLSOCK].revents POLLIN) != 0) ctlsock_accept_handler(); @@ -630,22 +605,64 @@ main(int argc, char *argv[]) for (i = 0; i nfunix; i++) { if ((pfd[PFD_UNIX_0 + i].revents POLLIN) != 0) { - ssize_t rlen; - - len = sizeof(fromunix); - rlen = recvfrom(pfd[PFD_UNIX_0 + i].fd, line, - MAXLINE, 0, (struct sockaddr *)fromunix
Re: syslogd maxunix
On Wed, Sep 03, 2014 at 06:46:26PM +0200, Alexander Bluhm wrote: On Fri, Aug 29, 2014 at 11:25:52PM +0200, Alexander Bluhm wrote: So I will write more tests before committing this. My regression tests found a bug in syslogd. When adding the maximum number of paths with the -a option, the arrays for unix domain socket paths and the poll file descriptors overflow by one. - increase pfd array by one - operate on size of arrays not length - null check for path not necessary when doing fd -1 check - rename variables consistently ...unix - make number of unix fds a local variable ok? After merging with my previous commit, here is the updated diff. ok? bluhm Index: usr.sbin/syslogd/privsep.c === RCS file: /data/mirror/openbsd/cvs/src/usr.sbin/syslogd/privsep.c,v retrieving revision 1.43 diff -u -p -r1.43 privsep.c --- usr.sbin/syslogd/privsep.c 25 Aug 2014 20:19:14 - 1.43 +++ usr.sbin/syslogd/privsep.c 4 Sep 2014 15:49:45 - @@ -172,7 +172,7 @@ priv_init(char *conf, int numeric, int l close(socks[1]); /* Close descriptors that only the unpriv child needs */ - for (i = 0; i nfunix; i++) + for (i = 0; i MAXUNIX + 1; i++) if (pfd[PFD_UNIX_0 + i].fd != -1) close(pfd[PFD_UNIX_0 + i].fd); if (pfd[PFD_INET].fd != -1) @@ -369,9 +369,9 @@ priv_init(char *conf, int numeric, int l close(socks[0]); /* Unlink any domain sockets that have been opened */ - for (i = 0; i nfunix; i++) - if (funixn[i] != NULL pfd[PFD_UNIX_0 + i].fd != -1) - (void)unlink(funixn[i]); + for (i = 0; i MAXUNIX; i++) + if (pfd[PFD_UNIX_0 + i].fd != -1) + (void)unlink(path_unix[i]); if (ctlsock_path != NULL pfd[PFD_CTLSOCK].fd != -1) (void)unlink(ctlsock_path); ? usr.sbin/syslogd/flags ? usr.sbin/syslogd/obj Index: usr.sbin/syslogd/privsep.c === RCS file: /cvs/src/usr.sbin/syslogd/privsep.c,v retrieving revision 1.43 diff -u -p -r1.43 privsep.c --- usr.sbin/syslogd/privsep.c 25 Aug 2014 20:19:14 - 1.43 +++ usr.sbin/syslogd/privsep.c 4 Sep 2014 16:00:26 - @@ -172,7 +172,7 @@ priv_init(char *conf, int numeric, int l close(socks[1]); /* Close descriptors that only the unpriv child needs */ - for (i = 0; i nfunix; i++) + for (i = 0; i MAXUNIX + 1; i++) if (pfd[PFD_UNIX_0 + i].fd != -1) close(pfd[PFD_UNIX_0 + i].fd); if (pfd[PFD_INET].fd != -1) @@ -369,9 +369,9 @@ priv_init(char *conf, int numeric, int l close(socks[0]); /* Unlink any domain sockets that have been opened */ - for (i = 0; i nfunix; i++) - if (funixn[i] != NULL pfd[PFD_UNIX_0 + i].fd != -1) - (void)unlink(funixn[i]); + for (i = 0; i MAXUNIX; i++) + if (pfd[PFD_UNIX_0 + i].fd != -1) + (void)unlink(path_unix[i]); if (ctlsock_path != NULL pfd[PFD_CTLSOCK].fd != -1) (void)unlink(ctlsock_path); Index: usr.sbin/syslogd/syslogd.c === RCS file: /cvs/src/usr.sbin/syslogd/syslogd.c,v retrieving revision 1.122 diff -u -p -r1.122 syslogd.c --- usr.sbin/syslogd/syslogd.c 4 Sep 2014 15:19:05 - 1.122 +++ usr.sbin/syslogd/syslogd.c 4 Sep 2014 16:00:26 - @@ -183,8 +183,7 @@ char*TypeNames[9] = { struct filed *Files; struct filed consfile; -intnfunix = 1; /* Number of Unix domain sockets requested */ -char *funixn[MAXFUNIX] = { _PATH_LOG }; /* Paths to Unix domain sockets */ +char *path_unix[MAXUNIX] = { _PATH_LOG }; /* Paths to Unix domain sockets */ intDebug; /* debug flag */ intStartup = 1;/* startup flag */ char LocalHostName[MAXHOSTNAMELEN]; /* our hostname */ @@ -289,12 +288,15 @@ void logto_ctlconn(char *); int main(int argc, char *argv[]) { - int ch, i, fd; + int ch, i, fd, nunix = 1; char *p; int lockpipe[2] = { -1, -1}, pair[2], nullfd; struct addrinfo hints, *res, *res0; FILE *fp; + for (i = 0; i N_PFD; i++) + pfd[i].fd = -1; + while ((ch = getopt(argc, argv, 46dhnuf:m:p:a:s:)) != -1) switch (ch) { case '4': /* disable IPv6 */ @@ -321,18 +323,18 @@ main(int argc, char *argv[]) NoDNS = 1; break; case 'p': /* path */ - funixn[0] = optarg; + path_unix[0] = optarg; break; case 'u': /* allow udp input port */ SecureMode = 0
Re: syslogd libevent
On Fri, Aug 29, 2014 at 11:25:52PM +0200, Alexander Bluhm wrote: With this diff all my regression tests for syslogd pass. I will try to pull parts of the diff into separate changes to make review easier. I have not tested the syslogc feature yet. So I will write more tests before committing this. The tests for syslog control sockets are commited. Next step to libevent in syslogd is to cleanup the control connection code. - Name variable path_ctlsock consistently. - Name function ctlconn_logto() consistently. - Replace the nested if/else logic in ctlconn_write_handler() with if/return. - Call ctlconn_cleanup() only if there is a control connection. ok? bluhm Index: usr.sbin/syslogd/privsep.c === RCS file: /data/mirror/openbsd/cvs/src/usr.sbin/syslogd/privsep.c,v retrieving revision 1.45 diff -u -p -u -p -r1.45 privsep.c --- usr.sbin/syslogd/privsep.c 10 Sep 2014 13:16:20 - 1.45 +++ usr.sbin/syslogd/privsep.c 13 Sep 2014 23:48:26 - @@ -374,8 +374,8 @@ priv_init(char *conf, int numeric, int l for (i = 0; i nunix; i++) if (pfd[PFD_UNIX_0 + i].fd != -1) (void)unlink(path_unix[i]); - if (ctlsock_path != NULL pfd[PFD_CTLSOCK].fd != -1) - (void)unlink(ctlsock_path); + if (path_ctlsock != NULL pfd[PFD_CTLSOCK].fd != -1) + (void)unlink(path_ctlsock); if (restart) { int r; Index: usr.sbin/syslogd/syslogd.c === RCS file: /data/mirror/openbsd/cvs/src/usr.sbin/syslogd/syslogd.c,v retrieving revision 1.124 diff -u -p -u -p -r1.124 syslogd.c --- usr.sbin/syslogd/syslogd.c 10 Sep 2014 13:16:20 - 1.124 +++ usr.sbin/syslogd/syslogd.c 14 Sep 2014 00:12:24 - @@ -199,7 +199,7 @@ int IPv4Only = 0; /* when true, disable intIPv6Only = 0; /* when true, disable IPv4 */ intIncludeHostname = 0;/* include RFC 3164 style hostnames when forwarding */ -char *ctlsock_path = NULL; /* Path to control socket */ +char *path_ctlsock = NULL; /* Path to control socket */ #define CTL_READING_CMD1 #define CTL_WRITING_REPLY 2 @@ -284,7 +284,7 @@ voidctlsock_accept_handler(void); void ctlconn_read_handler(void); void ctlconn_write_handler(void); void tailify_replytext(char *, int); -void logto_ctlconn(char *); +void ctlconn_logto(char *); int main(int argc, char *argv[]) @@ -335,7 +335,7 @@ main(int argc, char *argv[]) path_unix[nunix++] = optarg; break; case 's': - ctlsock_path = optarg; + path_ctlsock = optarg; break; default: usage(); @@ -460,8 +460,8 @@ main(int argc, char *argv[]) pfd[PFD_SENDSYS].fd = fd; pfd[PFD_SENDSYS].events = POLLIN; - if (ctlsock_path != NULL) { - fd = unix_socket(ctlsock_path, SOCK_STREAM, 0600); + if (path_ctlsock != NULL) { + fd = unix_socket(path_ctlsock, SOCK_STREAM, 0600); if (fd != -1) { if (listen(fd, 16) == -1) { logerror(ctlsock listen); @@ -1075,7 +1075,7 @@ fprintlog(struct filed *f, int flags, ch if (ringbuf_append_line(f-f_un.f_mb.f_rb, line) == 1) f-f_un.f_mb.f_overflow = 1; if (f-f_un.f_mb.f_attached) - logto_ctlconn(line); + ctlconn_logto(line); break; } f-f_prevcount = 0; @@ -1893,8 +1893,8 @@ ctlconn_cleanup(void) { struct filed *f; - if (pfd[PFD_CTLCONN].fd != -1) - close(pfd[PFD_CTLCONN].fd); + if (close(pfd[PFD_CTLCONN].fd) == -1) + logerror(close ctlconn); pfd[PFD_CTLCONN].fd = -1; pfd[PFD_CTLCONN].events = pfd[PFD_CTLCONN].revents = 0; @@ -1923,7 +1923,8 @@ ctlsock_accept_handler(void) return; } - ctlconn_cleanup(); + if (pfd[PFD_CTLCONN].fd != -1) + ctlconn_cleanup(); /* Only one connection at a time */ pfd[PFD_CTLSOCK].events = pfd[PFD_CTLSOCK].revents = 0; @@ -1984,7 +1985,6 @@ ctlconn_read_handler(void) default: ctl_cmd_bytes += n; } - if (ctl_cmd_bytes sizeof(ctl_cmd)) return; @@ -2086,7 +2086,6 @@ ctlconn_read_handler(void) /* another syslogc can kick us out */ if (ctl_state == CTL_WRITING_CONT_REPLY) pfd[PFD_CTLSOCK].events = POLLIN; - } void @@ -2101,6 +2100,7 @@ ctlconn_write_handler(void) ctlconn_cleanup(); return; } + retry: n = write(pfd[PFD_CTLCONN].fd, ctl_reply + ctl_reply_offset
Re: syslogd libevent
On Fri, Aug 29, 2014 at 11:25:52PM +0200, Alexander Bluhm wrote: try to pull parts of the diff into separate changes to make review easier. Also in debug mode, close nullfd when it is not needed anymore. ok? bluhm Index: usr.sbin/syslogd/privsep.c === RCS file: /data/mirror/openbsd/cvs/src/usr.sbin/syslogd/privsep.c,v retrieving revision 1.45 diff -u -p -u -p -r1.45 privsep.c --- usr.sbin/syslogd/privsep.c 10 Sep 2014 13:16:20 - 1.45 +++ usr.sbin/syslogd/privsep.c 25 Sep 2014 14:43:40 - @@ -153,7 +153,6 @@ priv_init(char *conf, int numeric, int l dup2(nullfd, STDOUT_FILENO); dup2(nullfd, STDERR_FILENO); } - if (nullfd 2) close(nullfd); Index: usr.sbin/syslogd/syslogd.c === RCS file: /data/mirror/openbsd/cvs/src/usr.sbin/syslogd/syslogd.c,v retrieving revision 1.124 diff -u -p -u -p -r1.124 syslogd.c --- usr.sbin/syslogd/syslogd.c 10 Sep 2014 13:16:20 - 1.124 +++ usr.sbin/syslogd/syslogd.c 25 Sep 2014 14:43:40 - @@ -539,10 +539,10 @@ main(int argc, char *argv[]) dup2(nullfd, STDIN_FILENO); dup2(nullfd, STDOUT_FILENO); dup2(nullfd, STDERR_FILENO); - if (nullfd 2) - close(nullfd); close(lockpipe[1]); } + if (nullfd 2) + close(nullfd); /* * Signal to the priv process that the initial config parsing is done
Re: syslogd libevent
Hi, After some preparation, I can convert syslogd to use libevent now. ok? bluhm Index: usr.sbin/syslogd/Makefile === RCS file: /data/mirror/openbsd/cvs/src/usr.sbin/syslogd/Makefile,v retrieving revision 1.5 diff -u -p -u -p -r1.5 Makefile --- usr.sbin/syslogd/Makefile 4 Jan 2004 08:28:49 - 1.5 +++ usr.sbin/syslogd/Makefile 3 Oct 2014 22:30:00 - @@ -1,7 +1,8 @@ # $OpenBSD: Makefile,v 1.5 2004/01/04 08:28:49 djm Exp $ -PROG= syslogd -SRCS= syslogd.c ttymsg.c privsep.c privsep_fdpass.c ringbuf.c -MAN= syslogd.8 syslog.conf.5 +PROG = syslogd +SRCS = syslogd.c ttymsg.c privsep.c privsep_fdpass.c ringbuf.c +MAN = syslogd.8 syslog.conf.5 +LDFLAGS = -levent .include bsd.prog.mk Index: usr.sbin/syslogd/privsep.c === RCS file: /data/mirror/openbsd/cvs/src/usr.sbin/syslogd/privsep.c,v retrieving revision 1.47 diff -u -p -u -p -r1.47 privsep.c --- usr.sbin/syslogd/privsep.c 3 Oct 2014 21:55:22 - 1.47 +++ usr.sbin/syslogd/privsep.c 3 Oct 2014 23:03:50 - @@ -171,21 +171,21 @@ priv_init(char *conf, int numeric, int l close(socks[1]); /* Close descriptors that only the unpriv child needs */ + if (fd_ctlconn != -1) + close(fd_ctlconn); + if (fd_ctlsock != -1) + close(fd_ctlsock); + if (fd_klog != -1) + close(fd_klog); + if (fd_sendsys != -1) + close(fd_sendsys); + if (fd_udp != -1) + close(fd_udp); + if (fd_udp6 != -1) + close(fd_udp6); for (i = 0; i nunix; i++) - if (pfd[PFD_UNIX_0 + i].fd != -1) - close(pfd[PFD_UNIX_0 + i].fd); - if (pfd[PFD_INET].fd != -1) - close(pfd[PFD_INET].fd); - if (pfd[PFD_INET6].fd != -1) - close(pfd[PFD_INET6].fd); - if (pfd[PFD_CTLSOCK].fd != -1) - close(pfd[PFD_CTLSOCK].fd); - if (pfd[PFD_CTLCONN].fd != -1) - close(pfd[PFD_CTLCONN].fd); - if (pfd[PFD_KLOG].fd != -1) - close(pfd[PFD_KLOG].fd); - if (pfd[PFD_SENDSYS].fd != -1) - close(pfd[PFD_SENDSYS].fd); + if (fd_unix[i] != -1) + close(fd_unix[i]); /* Save the config file specified by the child process */ if (strlcpy(config_file, conf, sizeof config_file) = sizeof(config_file)) @@ -371,9 +371,9 @@ priv_init(char *conf, int numeric, int l /* Unlink any domain sockets that have been opened */ for (i = 0; i nunix; i++) - if (pfd[PFD_UNIX_0 + i].fd != -1) + if (fd_unix[i] != -1) (void)unlink(path_unix[i]); - if (path_ctlsock != NULL pfd[PFD_CTLSOCK].fd != -1) + if (path_ctlsock != NULL fd_ctlsock != -1) (void)unlink(path_ctlsock); if (restart) { Index: usr.sbin/syslogd/syslogd.c === RCS file: /data/mirror/openbsd/cvs/src/usr.sbin/syslogd/syslogd.c,v retrieving revision 1.127 diff -u -p -u -p -r1.127 syslogd.c --- usr.sbin/syslogd/syslogd.c 3 Oct 2014 21:55:22 - 1.127 +++ usr.sbin/syslogd/syslogd.c 3 Oct 2014 23:09:30 - @@ -50,6 +50,7 @@ * extensive changes by Ralph Campbell * more extensive changes by Eric Allman (again) * memory buffer logging by Damien Miller + * IPv6, libevent by Alexander Bluhm */ #defineMAXLINE 1024/* maximum line length */ @@ -81,6 +82,7 @@ #include ctype.h #include errno.h #include err.h +#include event.h #include fcntl.h #include paths.h #include poll.h @@ -248,23 +250,28 @@ size_tctl_reply_offset = 0; /* Number o char *linebuf; int linesize; -voidklog_read_handler(int); -voidudp_read_handler(int); -voidunix_read_handler(int); - -struct pollfd pfd[N_PFD]; - -volatile sig_atomic_t MarkSet; -volatile sig_atomic_t WantDie; -volatile sig_atomic_t DoInit; +int fd_ctlsock, fd_ctlconn, fd_klog, fd_sendsys, +fd_udp, fd_udp6, fd_unix[MAXUNIX]; +struct eventev_ctlaccept, ev_ctlread, ev_ctlwrite, ev_klog, ev_sendsys, +ev_udp, ev_udp6, ev_unix[MAXUNIX], +ev_hup, ev_int, ev_quit, ev_term, ev_mark; + +voidklog_readcb(int, short, void *); +voidudp_readcb(int, short, void *); +voidunix_readcb(int, short, void *); +voiddie_signalcb(int, short, void *); +voidmark_timercb(int, short, void *); +voidinit_signalcb(int, short, void *); +voidctlsock_acceptcb(int, short, void *); +voidctlconn_readcb(int, short, void *); +voidctlconn_writecb(int, short, void *); +voidctlconn_logto(char *); +voidctlconn_cleanup(void); struct filed *cfline(char *, char *); void cvthname(struct sockaddr *, char *, size_t); int
Re: splnet() and SIOCSIFADDR
On Thu, Sep 11, 2014 at 10:49:33AM +0200, Martin Pieuchot wrote: --- netinet6/in6.c26 Aug 2014 21:44:29 - 1.140 +++ netinet6/in6.c11 Sep 2014 08:45:29 - @@ -561,8 +560,10 @@ in6_control(struct socket *so, u_long cm } case SIOCDIFADDR_IN6: + s = splsoftnet(); in6_purgeaddr(ia6-ia_ifa); dohooks(ifp-if_addrhooks, 0); + splx(s); break; default: In IPv4 all dohooks(if_addrhooks) are protected by a large splsoftnet(). A few lines above in SIOCAIFADDR_IN6 this is not the case. The hook carp_addr_updated() looks like it would need an splsoftnet() as it is looping over if_addrlist. But this is not part of this diff. OK bluhm@
Re: syslogd libevent
On Sat, Oct 04, 2014 at 09:03:58AM +0100, Nicholas Marriott wrote: This should be: LDADD= -levent DPADD= ${LIBEVENT} Rather than LDFLAGS. Here is the updated diff. Index: usr.sbin/syslogd/Makefile === RCS file: /data/mirror/openbsd/cvs/src/usr.sbin/syslogd/Makefile,v retrieving revision 1.5 diff -u -p -r1.5 Makefile --- usr.sbin/syslogd/Makefile 4 Jan 2004 08:28:49 - 1.5 +++ usr.sbin/syslogd/Makefile 4 Oct 2014 09:17:53 - @@ -3,5 +3,7 @@ PROG= syslogd SRCS= syslogd.c ttymsg.c privsep.c privsep_fdpass.c ringbuf.c MAN= syslogd.8 syslog.conf.5 +LDADD= -levent +DPADD= ${LIBEVENT} .include bsd.prog.mk Index: usr.sbin/syslogd/privsep.c === RCS file: /data/mirror/openbsd/cvs/src/usr.sbin/syslogd/privsep.c,v retrieving revision 1.47 diff -u -p -r1.47 privsep.c --- usr.sbin/syslogd/privsep.c 3 Oct 2014 21:55:22 - 1.47 +++ usr.sbin/syslogd/privsep.c 4 Oct 2014 09:17:25 - @@ -171,21 +171,21 @@ priv_init(char *conf, int numeric, int l close(socks[1]); /* Close descriptors that only the unpriv child needs */ + if (fd_ctlconn != -1) + close(fd_ctlconn); + if (fd_ctlsock != -1) + close(fd_ctlsock); + if (fd_klog != -1) + close(fd_klog); + if (fd_sendsys != -1) + close(fd_sendsys); + if (fd_udp != -1) + close(fd_udp); + if (fd_udp6 != -1) + close(fd_udp6); for (i = 0; i nunix; i++) - if (pfd[PFD_UNIX_0 + i].fd != -1) - close(pfd[PFD_UNIX_0 + i].fd); - if (pfd[PFD_INET].fd != -1) - close(pfd[PFD_INET].fd); - if (pfd[PFD_INET6].fd != -1) - close(pfd[PFD_INET6].fd); - if (pfd[PFD_CTLSOCK].fd != -1) - close(pfd[PFD_CTLSOCK].fd); - if (pfd[PFD_CTLCONN].fd != -1) - close(pfd[PFD_CTLCONN].fd); - if (pfd[PFD_KLOG].fd != -1) - close(pfd[PFD_KLOG].fd); - if (pfd[PFD_SENDSYS].fd != -1) - close(pfd[PFD_SENDSYS].fd); + if (fd_unix[i] != -1) + close(fd_unix[i]); /* Save the config file specified by the child process */ if (strlcpy(config_file, conf, sizeof config_file) = sizeof(config_file)) @@ -371,9 +371,9 @@ priv_init(char *conf, int numeric, int l /* Unlink any domain sockets that have been opened */ for (i = 0; i nunix; i++) - if (pfd[PFD_UNIX_0 + i].fd != -1) + if (fd_unix[i] != -1) (void)unlink(path_unix[i]); - if (path_ctlsock != NULL pfd[PFD_CTLSOCK].fd != -1) + if (path_ctlsock != NULL fd_ctlsock != -1) (void)unlink(path_ctlsock); if (restart) { Index: usr.sbin/syslogd/syslogd.c === RCS file: /data/mirror/openbsd/cvs/src/usr.sbin/syslogd/syslogd.c,v retrieving revision 1.127 diff -u -p -r1.127 syslogd.c --- usr.sbin/syslogd/syslogd.c 3 Oct 2014 21:55:22 - 1.127 +++ usr.sbin/syslogd/syslogd.c 4 Oct 2014 09:17:25 - @@ -50,6 +50,7 @@ * extensive changes by Ralph Campbell * more extensive changes by Eric Allman (again) * memory buffer logging by Damien Miller + * IPv6, libevent by Alexander Bluhm */ #defineMAXLINE 1024/* maximum line length */ @@ -81,6 +82,7 @@ #include ctype.h #include errno.h #include err.h +#include event.h #include fcntl.h #include paths.h #include poll.h @@ -248,23 +250,28 @@ size_tctl_reply_offset = 0; /* Number o char *linebuf; int linesize; -voidklog_read_handler(int); -voidudp_read_handler(int); -voidunix_read_handler(int); - -struct pollfd pfd[N_PFD]; - -volatile sig_atomic_t MarkSet; -volatile sig_atomic_t WantDie; -volatile sig_atomic_t DoInit; +int fd_ctlsock, fd_ctlconn, fd_klog, fd_sendsys, +fd_udp, fd_udp6, fd_unix[MAXUNIX]; +struct eventev_ctlaccept, ev_ctlread, ev_ctlwrite, ev_klog, ev_sendsys, +ev_udp, ev_udp6, ev_unix[MAXUNIX], +ev_hup, ev_int, ev_quit, ev_term, ev_mark; + +voidklog_readcb(int, short, void *); +voidudp_readcb(int, short, void *); +voidunix_readcb(int, short, void *); +voiddie_signalcb(int, short, void *); +voidmark_timercb(int, short, void *); +voidinit_signalcb(int, short, void *); +voidctlsock_acceptcb(int, short, void *); +voidctlconn_readcb(int, short, void *); +voidctlconn_writecb(int, short, void *); +voidctlconn_logto(char *); +voidctlconn_cleanup(void); struct filed *cfline(char *, char *); void cvthname(struct sockaddr *, char *, size_t); intdecode(const char *, const CODE *); -void dodie(int); -void doinit(int); void die(int); -void domark(int
Re: syslogd sigmask
Hi, As libevent provides safe signal callbacks instead of signal handlers, the sigprocmask(2) protection is not necessary and can be removed. ok? bluhm Index: usr.sbin/syslogd/syslogd.c === RCS file: /cvs/src/usr.sbin/syslogd/syslogd.c,v retrieving revision 1.128 diff -u -p -r1.128 syslogd.c --- usr.sbin/syslogd/syslogd.c 5 Oct 2014 18:14:01 - 1.128 +++ usr.sbin/syslogd/syslogd.c 5 Oct 2014 19:46:48 - @@ -759,18 +759,12 @@ logmsg(int pri, char *msg, char *from, i { struct filed *f; int fac, msglen, prilev, i; - sigset_t mask, omask; char *timestamp; char prog[NAME_MAX+1]; dprintf(logmsg: pri 0%o, flags 0x%x, from %s, msg %s\n, pri, flags, from, msg); - sigemptyset(mask); - sigaddset(mask, SIGALRM); - sigaddset(mask, SIGHUP); - sigprocmask(SIG_BLOCK, mask, omask); - /* * Check to see if msg looks non-standard. */ @@ -818,7 +812,6 @@ logmsg(int pri, char *msg, char *from, i (void)close(f-f_file); f-f_file = -1; } - (void)sigprocmask(SIG_SETMASK, omask, NULL); return; } for (f = Files; f; f = f-f_next) { @@ -883,7 +876,6 @@ logmsg(int pri, char *msg, char *from, i if (f-f_quick) break; } - (void)sigprocmask(SIG_SETMASK, omask, NULL); } void
Re: syslogd eintr
Hi, As libevent uses sigaction(2) with SA_RESTART, the code to handle EINTR errors can be removed. ok? bluhm Index: usr.sbin/syslogd/syslogd.c === RCS file: /cvs/src/usr.sbin/syslogd/syslogd.c,v retrieving revision 1.128 diff -u -p -r1.128 syslogd.c --- usr.sbin/syslogd/syslogd.c 5 Oct 2014 18:14:01 - 1.128 +++ usr.sbin/syslogd/syslogd.c 5 Oct 2014 19:34:53 - @@ -619,7 +619,7 @@ klog_readcb(int fd, short event, void *a if (n 0) { linebuf[n] = '\0'; printsys(linebuf); - } else if (n 0 errno != EINTR) { + } else if (n 0) { logerror(klog); event_del(ev); } @@ -641,7 +641,7 @@ udp_readcb(int fd, short event, void *ar cvthname((struct sockaddr *)sa, resolve, sizeof(resolve)); dprintf(cvthname res: %s\n, resolve); printline(resolve, linebuf); - } else if (n 0 errno != EINTR) + } else if (n 0) logerror(recvfrom udp); } @@ -657,7 +657,7 @@ unix_readcb(int fd, short event, void *a if (n 0) { linebuf[n] = '\0'; printline(LocalHostName, linebuf); - } else if (n == -1 errno != EINTR) + } else if (n 0) logerror(recvfrom unix); } @@ -1914,8 +1914,7 @@ ctlsock_acceptcb(int fd, short event, vo dprintf(Accepting control connection\n); fd = accept(fd, NULL, NULL); if (fd == -1) { - if (errno != EINTR errno != EWOULDBLOCK - errno != ECONNABORTED) + if (errno != EWOULDBLOCK errno != ECONNABORTED) logerror(accept ctlsock); return; } @@ -1972,13 +1971,10 @@ ctlconn_readcb(int fd, short event, void return; } - retry: n = read(fd, (char*)ctl_cmd + ctl_cmd_bytes, sizeof(ctl_cmd) - ctl_cmd_bytes); switch (n) { case -1: - if (errno == EINTR) - goto retry; logerror(ctlconn read); /* FALLTHROUGH */ case 0: @@ -2101,13 +2097,10 @@ ctlconn_writecb(int fd, short event, voi return; } - retry: n = write(fd, ctl_reply + ctl_reply_offset, ctl_reply_size - ctl_reply_offset); switch (n) { case -1: - if (errno == EINTR) - goto retry; if (errno != EPIPE) logerror(ctlconn write); /* FALLTHROUGH */
libevent ifdef sigaction
Hi, Can we remove the #ifdef HAVE_SIGACTION from libevent? The only reason to keep it, would be make merging with upstream easier. Do we expect any new 1.X versions from upstream? ok? bluhm Index: lib/libevent/evsignal.h === RCS file: /data/mirror/openbsd/cvs/src/lib/libevent/evsignal.h,v retrieving revision 1.4 diff -u -p -r1.4 evsignal.h --- lib/libevent/evsignal.h 21 Apr 2010 20:02:40 - 1.4 +++ lib/libevent/evsignal.h 5 Oct 2014 20:21:05 - @@ -29,8 +29,6 @@ #ifndef _EVSIGNAL_H_ #define _EVSIGNAL_H_ -typedef void (*ev_sighandler_t)(int); - struct evsignal_info { struct event ev_signal; int ev_signal_pair[2]; @@ -38,11 +36,7 @@ struct evsignal_info { volatile sig_atomic_t evsignal_caught; struct event_list evsigevents[NSIG]; sig_atomic_t evsigcaught[NSIG]; -#ifdef HAVE_SIGACTION struct sigaction **sh_old; -#else - ev_sighandler_t **sh_old; -#endif int sh_old_max; }; int evsignal_init(struct event_base *); Index: lib/libevent/signal.c === RCS file: /data/mirror/openbsd/cvs/src/lib/libevent/signal.c,v retrieving revision 1.16 diff -u -p -r1.16 signal.c --- lib/libevent/signal.c 29 Apr 2013 00:28:23 - 1.16 +++ lib/libevent/signal.c 5 Oct 2014 20:06:03 - @@ -140,11 +140,7 @@ int _evsignal_set_handler(struct event_base *base, int evsignal, void (*handler)(int)) { -#ifdef HAVE_SIGACTION struct sigaction sa; -#else - ev_sighandler_t sh; -#endif struct evsignal_info *sig = base-sig; void *p; @@ -177,7 +173,6 @@ _evsignal_set_handler(struct event_base } /* save previous handler and setup new handler */ -#ifdef HAVE_SIGACTION memset(sa, 0, sizeof(sa)); sa.sa_handler = handler; sa.sa_flags |= SA_RESTART; @@ -189,15 +184,6 @@ _evsignal_set_handler(struct event_base sig-sh_old[evsignal] = NULL; return (-1); } -#else - if ((sh = signal(evsignal, handler)) == SIG_ERR) { - event_warn(signal); - free(sig-sh_old[evsignal]); - sig-sh_old[evsignal] = NULL; - return (-1); - } - *sig-sh_old[evsignal] = sh; -#endif return (0); } @@ -240,26 +226,15 @@ _evsignal_restore_handler(struct event_b { int ret = 0; struct evsignal_info *sig = base-sig; -#ifdef HAVE_SIGACTION struct sigaction *sh; -#else - ev_sighandler_t *sh; -#endif /* restore previous handler */ sh = sig-sh_old[evsignal]; sig-sh_old[evsignal] = NULL; -#ifdef HAVE_SIGACTION if (sigaction(evsignal, sh, NULL) == -1) { event_warn(sigaction); ret = -1; } -#else - if (signal(evsignal, *sh) == SIG_ERR) { - event_warn(signal); - ret = -1; - } -#endif free(sh); return ret; @@ -299,10 +274,6 @@ evsignal_handler(int sig) evsignal_base-sig.evsigcaught[sig]++; evsignal_base-sig.evsignal_caught = 1; - -#ifndef HAVE_SIGACTION - signal(sig, evsignal_handler); -#endif /* Wake up our notification mechanism */ send(evsignal_base-sig.ev_signal_pair[0], a, 1, 0);
Re: Patch for Data::Dumper - CVE-2014-4330
On Fri, Oct 24, 2014 at 10:40:55PM +0200, Alexander Bluhm wrote: Here is the diff that applies to -current. I have compared it with the perl git and with Data::Dumper on CPAN. It looks correct. I have forgotten to cvs add dist/Data-Dumper/t/recurse.t so here is the diff with the new test. ok? bluhm Index: gnu/usr.bin/perl/MANIFEST === RCS file: /data/mirror/openbsd/cvs/src/gnu/usr.bin/perl/MANIFEST,v retrieving revision 1.29 diff -u -p -u -p -r1.29 MANIFEST --- gnu/usr.bin/perl/MANIFEST 24 Mar 2014 15:05:12 - 1.29 +++ gnu/usr.bin/perl/MANIFEST 24 Oct 2014 20:19:35 - @@ -3155,6 +3155,7 @@ dist/Data-Dumper/t/perl-74170.t Regressi dist/Data-Dumper/t/purity_deepcopy_maxdepth.t See if three Data::Dumper functions work dist/Data-Dumper/t/qr.tSee if Data::Dumper works with qr|/| dist/Data-Dumper/t/quotekeys.t See if Data::Dumper::Quotekeys works +dist/Data-Dumper/t/recurse.t See if Data::Dumper::Maxrecurse works dist/Data-Dumper/t/seen.t See if Data::Dumper::Seen works dist/Data-Dumper/t/sortkeys.t See if Data::Dumper::Sortkeys works dist/Data-Dumper/t/sparseseen.tSee if Data::Dumper::Sparseseen works Index: gnu/usr.bin/perl/patchlevel.h === RCS file: /data/mirror/openbsd/cvs/src/gnu/usr.bin/perl/patchlevel.h,v retrieving revision 1.34 diff -u -p -u -p -r1.34 patchlevel.h --- gnu/usr.bin/perl/patchlevel.h 5 Sep 2014 06:53:07 - 1.34 +++ gnu/usr.bin/perl/patchlevel.h 24 Oct 2014 20:25:05 - @@ -134,6 +134,7 @@ hunk. static const char * const local_patches[] = { NULL ,Update libnet to 1.27 + ,CVE-2014-4330 #ifdef PERL_GIT_UNCOMMITTED_CHANGES ,uncommitted-changes #endif Index: gnu/usr.bin/perl/dist/Data-Dumper/Dumper.pm === RCS file: /data/mirror/openbsd/cvs/src/gnu/usr.bin/perl/dist/Data-Dumper/Dumper.pm,v retrieving revision 1.1.1.3 diff -u -p -u -p -r1.1.1.3 Dumper.pm --- gnu/usr.bin/perl/dist/Data-Dumper/Dumper.pm 24 Mar 2014 14:58:59 - 1.1.1.3 +++ gnu/usr.bin/perl/dist/Data-Dumper/Dumper.pm 24 Oct 2014 20:19:35 - @@ -56,6 +56,7 @@ $Useperl= 0 unless defined $ $Sortkeys = 0 unless defined $Sortkeys; $Deparse= 0 unless defined $Deparse; $Sparseseen = 0 unless defined $Sparseseen; +$Maxrecurse = 1000 unless defined $Maxrecurse; # # expects an arrayref of values to be dumped. @@ -92,6 +93,7 @@ sub new { 'bless'= $Bless,# keyword to use for bless #expdepth = $Expdepth, # cutoff depth for explicit dumping maxdepth = $Maxdepth, # depth beyond which we give up + maxrecurse = $Maxrecurse, # depth beyond which we abort useperl= $Useperl,# use the pure Perl implementation sortkeys = $Sortkeys, # flag or filter for sorting hash keys deparse= $Deparse,# use B::Deparse for coderefs @@ -351,6 +353,12 @@ sub _dump { return qq['$val']; } +# avoid recursing infinitely [perl #122111] +if ($s-{maxrecurse} 0 +and $s-{level} = $s-{maxrecurse}) { +die Recursion limit of $s-{maxrecurse} exceeded; +} + # we have a blessed ref my ($blesspad); if ($realpack and !$no_bless) { @@ -683,6 +691,11 @@ sub Maxdepth { defined($v) ? (($s-{'maxdepth'} = $v), return $s) : $s-{'maxdepth'}; } +sub Maxrecurse { + my($s, $v) = @_; + defined($v) ? (($s-{'maxrecurse'} = $v), return $s) : $s-{'maxrecurse'}; +} + sub Useperl { my($s, $v) = @_; defined($v) ? (($s-{'useperl'} = $v), return $s) : $s-{'useperl'}; @@ -1105,6 +1118,16 @@ we don't venture into a structure. Has CData::Dumper::Purity is set. (Useful in debugger when we often don't want to see more than enough). Default is 0, which means there is no maximum depth. + +=item * + +$Data::Dumper::Maxrecurse Ior $IOBJ-Maxrecurse(I[NEWVAL]) + +Can be set to a positive integer that specifies the depth beyond which +recursion into a structure will throw an exception. This is intended +as a security measure to prevent perl running out of stack space when +dumping an excessively deep structure. Can be set to 0 to remove the +limit. Default is 1000. =item * Index: gnu/usr.bin/perl/dist/Data-Dumper/Dumper.xs === RCS file: /data/mirror/openbsd/cvs/src/gnu/usr.bin/perl/dist/Data-Dumper/Dumper.xs,v retrieving revision 1.1.1.3 diff -u -p -u -p -r1.1.1.3 Dumper.xs --- gnu/usr.bin/perl/dist/Data-Dumper/Dumper.xs 24 Mar 2014 14:58:59 - 1.1.1.3 +++ gnu/usr.bin/perl/dist/Data-Dumper/Dumper.xs 24 Oct 2014 20:22:57 - @@ -26,7 +26,8 @@ static I32 DD_dump (pTHX_ SV *val, const SV *pad, SV *xpad, SV *apad, SV *sep, SV *pair, SV *freezer, SV
libevent evutil.h
Hi, libevent has compatibilty wrappers in evutil. Our tree does not use them anymore, but they are still part of libevent's interface. I don't want to include them automatically, so I suggest to remove evutil.h from event.h. A version bump should not be necessary as the library itself does not change. Does my idea make sense? Is a full ports build needed with this diff? bluhm Index: lib/libevent/event.h === RCS file: /data/mirror/openbsd/cvs/src/lib/libevent/event.h,v retrieving revision 1.27 diff -u -p -r1.27 event.h --- lib/libevent/event.h8 Oct 2014 20:14:19 - 1.27 +++ lib/libevent/event.h29 Oct 2014 23:42:45 - @@ -168,8 +168,11 @@ extern C { #include stdarg.h #include stdint.h -/* For int types. */ -#include evutil.h +#define ev_uint64_t uint64_t +#define ev_int64_t int64_t +#define ev_uint32_t uint32_t +#define ev_uint16_t uint16_t +#define ev_uint8_t uint8_t #define EVLIST_TIMEOUT 0x01 #define EVLIST_INSERTED0x02
socket splicing thread
Hi, Some performance measurements showed that socket splicing for TCP can be made faster. The main slowdown was that tcp_output() got called for every incomming packet. When copying through user-land this cannot happen as the scheduler gets involved. So my idea is to do the socket splicing for TCP in a special kernel thread. One drawback might be that the struct socket gets larger. On amd64 that is from 472 to 520 bytes. I could try to put the splicing fields into a seperate struct that gets only allocated when needed. Does someone want to do some performance measurements with relayd? ok? bluhm Index: sys/kern/uipc_socket.c === RCS file: /data/mirror/openbsd/cvs/src/sys/kern/uipc_socket.c,v retrieving revision 1.133 diff -u -p -u -p -r1.133 uipc_socket.c --- sys/kern/uipc_socket.c 9 Sep 2014 02:07:17 - 1.133 +++ sys/kern/uipc_socket.c 30 Oct 2014 18:56:28 - @@ -56,6 +56,7 @@ void sbsync(struct sockbuf *, struct mbu intsosplice(struct socket *, int, off_t, struct timeval *); void sounsplice(struct socket *, struct socket *, int); void soidle(void *); +void sotask(void *, void *); intsomove(struct socket *, int); void filt_sordetach(struct knote *kn); @@ -80,12 +81,18 @@ int somaxconn = SOMAXCONN; intsominconn = SOMINCONN; struct pool socket_pool; +#ifdef SOCKET_SPLICE +struct taskq *sosplice_taskq; +#endif void soinit(void) { pool_init(socket_pool, sizeof(struct socket), 0, 0, 0, sockpl, NULL); +#ifdef SOCKET_SPLICE + sosplice_taskq = taskq_create(sosplice, 1, IPL_SOFTNET); +#endif } /* @@ -1101,6 +1108,7 @@ sosplice(struct socket *so, int fd, off_ else timerclear(so-so_idletv); timeout_set(so-so_idleto, soidle, so); + task_set(so-so_splicetask, sotask, so, NULL); /* * To prevent softnet interrupt from calling somove() while @@ -1124,6 +1132,7 @@ sounsplice(struct socket *so, struct soc { splsoftassert(IPL_SOFTNET); + task_del(sosplice_taskq, so-so_splicetask); timeout_del(so-so_idleto); sosp-so_snd.sb_flagsintr = ~SB_SPLICE; so-so_rcv.sb_flagsintr = ~SB_SPLICE; @@ -1139,13 +1148,34 @@ soidle(void *arg) int s; s = splsoftnet(); - if (so-so_splice) { + if (so-so_rcv.sb_flagsintr SB_SPLICE) { so-so_error = ETIMEDOUT; sounsplice(so, so-so_splice, 1); } splx(s); } +void +sotask(void *arg1, void *arg2) +{ + struct socket *so = arg1; + int s; + + s = splsoftnet(); + if (so-so_rcv.sb_flagsintr SB_SPLICE) { + /* +* We may not sleep here as sofree() and unsplice() may be +* called from softnet interrupt context. This would remove +* the socket during somove(). +*/ + somove(so, M_DONTWAIT); + } + splx(s); + + /* Avoid user land starvation. */ + yield(); +} + /* * Move data from receive buffer of spliced source socket to send * buffer of drain socket. Try to move as much as possible in one @@ -1414,8 +1444,20 @@ void sorwakeup(struct socket *so) { #ifdef SOCKET_SPLICE - if (so-so_rcv.sb_flagsintr SB_SPLICE) - (void) somove(so, M_DONTWAIT); + if (so-so_rcv.sb_flagsintr SB_SPLICE) { + /* +* TCP has a sendbuffer that can handle multiple packets +* at once. So queue the stream a bit to accumulate data. +* The sosplice thread will call somove() later and send +* the packets calling tcp_output() only once. +* In the UDP case, send out the packets immediately. +* Using a thread would make things slower. +*/ + if (so-so_proto-pr_flags PR_WANTRCVD) + task_add(sosplice_taskq, so-so_splicetask); + else + somove(so, M_DONTWAIT); + } if (so-so_splice) return; #endif @@ -1429,7 +1471,7 @@ sowwakeup(struct socket *so) { #ifdef SOCKET_SPLICE if (so-so_snd.sb_flagsintr SB_SPLICE) - (void) somove(so-so_spliceback, M_DONTWAIT); + task_add(sosplice_taskq, so-so_spliceback-so_splicetask); #endif sowakeup(so, so-so_snd); } Index: sys/sys/socketvar.h === RCS file: /data/mirror/openbsd/cvs/src/sys/sys/socketvar.h,v retrieving revision 1.56 diff -u -p -u -p -r1.56 socketvar.h --- sys/sys/socketvar.h 9 Sep 2014 02:07:17 - 1.56 +++ sys/sys/socketvar.h 30 Oct 2014 18:32:16 - @@ -34,6 +34,7 @@ #include sys/selinfo.h /* for struct selinfo */ #include sys/queue.h +#include sys/task.h #include sys/timeout.h #ifndef_SOCKLEN_T_DEFINED_ @@ -88,6 +89,7 @@
Re: socket splicing pool
On Thu, Oct 30, 2014 at 10:10:20PM +0100, Alexander Bluhm wrote: I could try to put the splicing fields into a seperate struct that gets only allocated when needed. This way I can shrink struct socket from 472 to 392 bytes on amd64. When splicing gets active, another 88 bytes are allocated for struct sosplice. before: NameSize Requests FailInUse Pgreq Pgrel Npage Hiwat Minpg Maxpg Idle sockpl 472749310 170 359 3302982 0 85 after: sockpl 392 30580 8210 01010 0 81 sosppl88 36202 1 0 1 1 0 80 Is is worth it? bluhm Index: sys/kern/kern_sysctl.c === RCS file: /data/mirror/openbsd/cvs/src/sys/kern/kern_sysctl.c,v retrieving revision 1.267 diff -u -p -u -p -r1.267 kern_sysctl.c --- sys/kern/kern_sysctl.c 17 Oct 2014 01:51:39 - 1.267 +++ sys/kern/kern_sysctl.c 31 Oct 2014 01:04:46 - @@ -1062,11 +1062,12 @@ fill_file(struct kinfo_file *kf, struct kf-so_family = so-so_proto-pr_domain-dom_family; kf-so_rcv_cc = so-so_rcv.sb_cc; kf-so_snd_cc = so-so_snd.sb_cc; - if (so-so_splice) { + if (isspliced(so)) { if (show_pointers) - kf-so_splice = PTRTOINT64(so-so_splice); - kf-so_splicelen = so-so_splicelen; - } else if (so-so_spliceback) + kf-so_splice = + PTRTOINT64(so-so_sp-ssp_socket); + kf-so_splicelen = so-so_sp-ssp_len; + } else if (issplicedback(so)) kf-so_splicelen = -1; if (!so-so_pcb) break; Index: sys/kern/uipc_socket.c === RCS file: /data/mirror/openbsd/cvs/src/sys/kern/uipc_socket.c,v retrieving revision 1.133 diff -u -p -u -p -r1.133 uipc_socket.c --- sys/kern/uipc_socket.c 9 Sep 2014 02:07:17 - 1.133 +++ sys/kern/uipc_socket.c 31 Oct 2014 01:04:19 - @@ -80,12 +80,19 @@ int somaxconn = SOMAXCONN; intsominconn = SOMINCONN; struct pool socket_pool; +#ifdef SOCKET_SPLICE +struct pool sosplice_pool; +#endif void soinit(void) { pool_init(socket_pool, sizeof(struct socket), 0, 0, 0, sockpl, NULL); +#ifdef SOCKET_SPLICE + pool_init(sosplice_pool, sizeof(struct sosplice), 0, 0, 0, sosppl, + NULL); +#endif } /* @@ -157,7 +164,7 @@ solisten(struct socket *so, int backlog) if (so-so_state (SS_ISCONNECTED|SS_ISCONNECTING|SS_ISDISCONNECTING)) return (EOPNOTSUPP); #ifdef SOCKET_SPLICE - if (so-so_splice || so-so_spliceback) + if (isspliced(so) || issplicedback(so)) return (EOPNOTSUPP); #endif /* SOCKET_SPLICE */ s = splsoftnet(); @@ -199,10 +206,15 @@ sofree(struct socket *so) return; } #ifdef SOCKET_SPLICE - if (so-so_spliceback) - sounsplice(so-so_spliceback, so, so-so_spliceback != so); - if (so-so_splice) - sounsplice(so, so-so_splice, 0); + if (so-so_sp) { + if (issplicedback(so)) + sounsplice(so-so_sp-ssp_soback, so, + so-so_sp-ssp_soback != so); + if (isspliced(so)) + sounsplice(so, so-so_sp-ssp_socket, 0); + pool_put(sosplice_pool, so-so_sp); + so-so_sp = NULL; + } #endif /* SOCKET_SPLICE */ sbrelease(so-so_snd); sorflush(so); @@ -647,7 +659,7 @@ restart: m = so-so_rcv.sb_mb; #ifdef SOCKET_SPLICE - if (so-so_splice) + if (isspliced(so)) m = NULL; #endif /* SOCKET_SPLICE */ /* @@ -669,7 +681,7 @@ restart: #ifdef DIAGNOSTIC if (m == NULL so-so_rcv.sb_cc) #ifdef SOCKET_SPLICE - if (so-so_splice == NULL) + if (!isspliced(so)) #endif /* SOCKET_SPLICE */ panic(receive 1); #endif @@ -1021,6 +1033,12 @@ sorflush(struct socket *so) } #ifdef SOCKET_SPLICE + +#define so_splicelen so_sp-ssp_len +#define so_splicemax so_sp-ssp_max +#define so_idletv so_sp-ssp_idletv +#define so_idleto so_sp-ssp_idleto + int sosplice(struct socket *so, int fd, off_t max, struct timeval *tv) { @@ -1035,6 +1053,8 @@ sosplice(struct socket *so, int fd, off_ if ((so-so_state (SS_ISCONNECTED|SS_ISCONNECTING)) == 0 (so-so_proto-pr_flags PR_CONNREQUIRED)) return (ENOTCONN); + if (so-so_sp == NULL) + so-so_sp = pool_get(sosplice_pool, PR_WAITOK | PR_ZERO); /* If no fd is given, unsplice by removing existing link. */ if (fd 0) { @@ -1043,8
Re: socket splicing thread
On Fri, Oct 31, 2014 at 02:50:00PM +1000, David Gwynne wrote: so without splicing, the payloads from multiple tcp packets (at least all of the ones in a single softnet run?) get bundled up into a buffer that userland reads and then writes out again in a single go. right? you're suggesting the taskq as a way to defer output till after the current softnet call has processed all its packets and queued all the tcp packet payloads onto the socket? Exactly. its worth remembering there are other memory costs too. i think a kthread (the thing taskqs run on) is 5 pages amd64, so 20KB. We can delay the creation of the sosplice thread until user-land tries to splice for the first time. I would like to get in the sosplice pool in first. The user-land part was missing in my previous diff. Updated diff that actually can do make build. ok? bluhm Index: sys/kern/kern_sysctl.c === RCS file: /data/mirror/openbsd/cvs/src/sys/kern/kern_sysctl.c,v retrieving revision 1.267 diff -u -p -u -p -r1.267 kern_sysctl.c --- sys/kern/kern_sysctl.c 17 Oct 2014 01:51:39 - 1.267 +++ sys/kern/kern_sysctl.c 31 Oct 2014 10:23:44 - @@ -1062,11 +1062,12 @@ fill_file(struct kinfo_file *kf, struct kf-so_family = so-so_proto-pr_domain-dom_family; kf-so_rcv_cc = so-so_rcv.sb_cc; kf-so_snd_cc = so-so_snd.sb_cc; - if (so-so_splice) { + if (isspliced(so)) { if (show_pointers) - kf-so_splice = PTRTOINT64(so-so_splice); - kf-so_splicelen = so-so_splicelen; - } else if (so-so_spliceback) + kf-so_splice = + PTRTOINT64(so-so_sp-ssp_socket); + kf-so_splicelen = so-so_sp-ssp_len; + } else if (issplicedback(so)) kf-so_splicelen = -1; if (!so-so_pcb) break; Index: sys/kern/uipc_socket.c === RCS file: /data/mirror/openbsd/cvs/src/sys/kern/uipc_socket.c,v retrieving revision 1.133 diff -u -p -u -p -r1.133 uipc_socket.c --- sys/kern/uipc_socket.c 9 Sep 2014 02:07:17 - 1.133 +++ sys/kern/uipc_socket.c 31 Oct 2014 10:23:44 - @@ -80,12 +80,19 @@ int somaxconn = SOMAXCONN; intsominconn = SOMINCONN; struct pool socket_pool; +#ifdef SOCKET_SPLICE +struct pool sosplice_pool; +#endif void soinit(void) { pool_init(socket_pool, sizeof(struct socket), 0, 0, 0, sockpl, NULL); +#ifdef SOCKET_SPLICE + pool_init(sosplice_pool, sizeof(struct sosplice), 0, 0, 0, sosppl, + NULL); +#endif } /* @@ -157,7 +164,7 @@ solisten(struct socket *so, int backlog) if (so-so_state (SS_ISCONNECTED|SS_ISCONNECTING|SS_ISDISCONNECTING)) return (EOPNOTSUPP); #ifdef SOCKET_SPLICE - if (so-so_splice || so-so_spliceback) + if (isspliced(so) || issplicedback(so)) return (EOPNOTSUPP); #endif /* SOCKET_SPLICE */ s = splsoftnet(); @@ -199,10 +206,15 @@ sofree(struct socket *so) return; } #ifdef SOCKET_SPLICE - if (so-so_spliceback) - sounsplice(so-so_spliceback, so, so-so_spliceback != so); - if (so-so_splice) - sounsplice(so, so-so_splice, 0); + if (so-so_sp) { + if (issplicedback(so)) + sounsplice(so-so_sp-ssp_soback, so, + so-so_sp-ssp_soback != so); + if (isspliced(so)) + sounsplice(so, so-so_sp-ssp_socket, 0); + pool_put(sosplice_pool, so-so_sp); + so-so_sp = NULL; + } #endif /* SOCKET_SPLICE */ sbrelease(so-so_snd); sorflush(so); @@ -647,7 +659,7 @@ restart: m = so-so_rcv.sb_mb; #ifdef SOCKET_SPLICE - if (so-so_splice) + if (isspliced(so)) m = NULL; #endif /* SOCKET_SPLICE */ /* @@ -669,7 +681,7 @@ restart: #ifdef DIAGNOSTIC if (m == NULL so-so_rcv.sb_cc) #ifdef SOCKET_SPLICE - if (so-so_splice == NULL) + if (!isspliced(so)) #endif /* SOCKET_SPLICE */ panic(receive 1); #endif @@ -1021,6 +1033,12 @@ sorflush(struct socket *so) } #ifdef SOCKET_SPLICE + +#define so_splicelen so_sp-ssp_len +#define so_splicemax so_sp-ssp_max +#define so_idletv so_sp-ssp_idletv +#define so_idleto so_sp-ssp_idleto + int sosplice(struct socket *so, int fd, off_t max, struct timeval *tv) { @@ -1035,6 +1053,8 @@ sosplice(struct socket *so, int fd, off_ if ((so-so_state (SS_ISCONNECTED|SS_ISCONNECTING)) == 0 (so-so_proto-pr_flags PR_CONNREQUIRED)) return (ENOTCONN); + if (so-so_sp ==
Re: socket splicing thread
On Thu, Oct 30, 2014 at 09:55:35PM -0400, Ted Unangst wrote: On Thu, Oct 30, 2014 at 22:10, Alexander Bluhm wrote: + + /* Avoid user land starvation. */ + yield(); I think this is the responsibility of the taskq thread, not the individual task. I am not sure about this. Without an explicit yield() I see user land starvation, but I only used a virtual test machine. Note that the net_livelocks detection does not work as softtimer may interrupt the kernel thread. Originally I have put the yield() there as copy through user land always calls the scheduler. I have removed it for now from this diff. It has no impact on throughput. I have merged the diff with sosplice pool. Now the struct socket size remains at 392 bytes, but struct sosplice grows from 88 to 136 bytes. To save memory the thread is only created on demand when the machine uses splicing for the first time. ok? bluhm Index: kern/uipc_socket.c === RCS file: /data/mirror/openbsd/cvs/src/sys/kern/uipc_socket.c,v retrieving revision 1.134 diff -u -p -r1.134 uipc_socket.c --- kern/uipc_socket.c 3 Nov 2014 17:20:46 - 1.134 +++ kern/uipc_socket.c 3 Nov 2014 23:03:32 - @@ -56,6 +56,7 @@ void sbsync(struct sockbuf *, struct mbu intsosplice(struct socket *, int, off_t, struct timeval *); void sounsplice(struct socket *, struct socket *, int); void soidle(void *); +void sotask(void *, void *); intsomove(struct socket *, int); void filt_sordetach(struct knote *kn); @@ -82,6 +83,7 @@ int sominconn = SOMINCONN; struct pool socket_pool; #ifdef SOCKET_SPLICE struct pool sosplice_pool; +struct taskq *sosplice_taskq; #endif void @@ -1038,6 +1040,7 @@ sorflush(struct socket *so) #define so_splicemax so_sp-ssp_max #define so_idletv so_sp-ssp_idletv #define so_idleto so_sp-ssp_idleto +#define so_splicetask so_sp-ssp_task int sosplice(struct socket *so, int fd, off_t max, struct timeval *tv) @@ -1046,6 +1049,9 @@ sosplice(struct socket *so, int fd, off_ struct socket *sosp; int s, error = 0; + if (sosplice_taskq == NULL) + sosplice_taskq = taskq_create(sosplice, 1, IPL_SOFTNET); + if ((so-so_proto-pr_flags PR_SPLICE) == 0) return (EPROTONOSUPPORT); if (so-so_options SO_ACCEPTCONN) @@ -1123,6 +1129,7 @@ sosplice(struct socket *so, int fd, off_ else timerclear(so-so_idletv); timeout_set(so-so_idleto, soidle, so); + task_set(so-so_splicetask, sotask, so, NULL); /* * To prevent softnet interrupt from calling somove() while @@ -1146,6 +1153,7 @@ sounsplice(struct socket *so, struct soc { splsoftassert(IPL_SOFTNET); + task_del(sosplice_taskq, so-so_splicetask); timeout_del(so-so_idleto); sosp-so_snd.sb_flagsintr = ~SB_SPLICE; so-so_rcv.sb_flagsintr = ~SB_SPLICE; @@ -1168,6 +1176,24 @@ soidle(void *arg) splx(s); } +void +sotask(void *arg1, void *arg2) +{ + struct socket *so = arg1; + int s; + + s = splsoftnet(); + if (so-so_rcv.sb_flagsintr SB_SPLICE) { + /* +* We may not sleep here as sofree() and unsplice() may be +* called from softnet interrupt context. This would remove +* the socket during somove(). +*/ + somove(so, M_DONTWAIT); + } + splx(s); +} + /* * Move data from receive buffer of spliced source socket to send * buffer of drain socket. Try to move as much as possible in one @@ -1435,6 +1461,7 @@ somove(struct socket *so, int wait) #undef so_splicemax #undef so_idletv #undef so_idleto +#undef so_splicetask #endif /* SOCKET_SPLICE */ @@ -1442,8 +1469,20 @@ void sorwakeup(struct socket *so) { #ifdef SOCKET_SPLICE - if (so-so_rcv.sb_flagsintr SB_SPLICE) - (void) somove(so, M_DONTWAIT); + if (so-so_rcv.sb_flagsintr SB_SPLICE) { + /* +* TCP has a sendbuffer that can handle multiple packets +* at once. So queue the stream a bit to accumulate data. +* The sosplice thread will call somove() later and send +* the packets calling tcp_output() only once. +* In the UDP case, send out the packets immediately. +* Using a thread would make things slower. +*/ + if (so-so_proto-pr_flags PR_WANTRCVD) + task_add(sosplice_taskq, so-so_sp-ssp_task); + else + somove(so, M_DONTWAIT); + } if (isspliced(so)) return; #endif @@ -1457,7 +1496,8 @@ sowwakeup(struct socket *so) { #ifdef SOCKET_SPLICE if (so-so_snd.sb_flagsintr SB_SPLICE) - (void) somove(so-so_sp-ssp_soback, M_DONTWAIT); + task_add(sosplice_taskq
Re: Diff: for hashing of carp password
On Tue, Jul 02, 2013 at 12:27:54PM +0200, Jan Klemkow wrote: Hi, This diff implements the hashing of the carp password before using it inside of the Kernel. It fix the problem that passwords like 12345678901234567890 and 12345678901234567890XXX are equal for carp. But It breaks the compatibility with older Versions. Maybe you need to increase the protocol number? bluhm@ have an other idea to solve this problem: ifconfig could XOR every 20 Byte long Chuck of the Passwort. This would not break the compatibility of setups with less than 20 char password. I would not do anyhing about that as it breaks compatibility without gain. Perhaps the XXX comment should be removed. What is actually wrong is that long passwords cannot be replaced completely with short passwords. ioctl(SIOCGVH) fills the carpr_key with the old value. strlcpy() overwrites only the beginning of the key. Jan, can you please test this? ok? bluhm Index: sbin/ifconfig/ifconfig.c === RCS file: /data/mirror/openbsd/cvs/src/sbin/ifconfig/ifconfig.c,v retrieving revision 1.264 diff -u -p -u -p -r1.264 ifconfig.c --- sbin/ifconfig/ifconfig.c31 May 2013 19:56:06 - 1.264 +++ sbin/ifconfig/ifconfig.c2 Jul 2013 11:01:38 - @@ -3390,7 +3390,7 @@ setcarp_passwd(const char *val, int d) if (ioctl(s, SIOCGVH, (caddr_t)ifr) == -1) err(1, SIOCGVH); - /* XXX Should hash the password into the key here, perhaps? */ + bzero(carpr.carpr_key, CARP_KEY_LEN); strlcpy((char *)carpr.carpr_key, val, CARP_KEY_LEN); if (ioctl(s, SIOCSVH, (caddr_t)ifr) == -1)
Re: Diff: for hashing of carp password
On Tue, Jul 02, 2013 at 02:20:05PM +0200, Jan Klemkow wrote: Your change is working. I've test this Bug with following case. FIRST: router-a: cat /etc/hostname.carp0 10.0.0.1 vhid 1 carpnodes 1:0,2:100 pass aaa balancing ip router-b: cat /etc/hostname.carp0 10.0.0.1 vhid 1 carpnodes 1:0,2:100 pass bbb balancing ip THAN: router-a: cat /etc/hostname.carp0 10.0.0.1 vhid 1 carpnodes 1:0,2:100 pass a balancing ip router-b: cat /etc/hostname.carp0 10.0.0.1 vhid 1 carpnodes 1:0,2:100 pass a balancing ip After this I get an carp0: incorrect hash. With our diffs, it is fixed. But, I would prefer my diff, cause your Diff don't fix the length problem. In my opinion it is a serious Bug, that password parts over 20 character are ignored. Even for the Hash-MAC code in carp, it looks not very secure, if we make shifting with a lot of zeros in cases of an small password. Thanks for testing. I would prefer the hashing version. I don't. If you want to get a secret into the kernel, ifconfig should just store it into the kernel. Your hash would obfuscate the algorithm and brake compatibility. What could be done is to implement a hexkey like in wpakey. This would allow to use the whole 20 byte information of the passphrase. Although I don't think that it is worth it. bluhm bye, Jan On Tue, Jul 02, 2013 at 01:04:49PM +0200, Alexander Bluhm wrote: On Tue, Jul 02, 2013 at 12:27:54PM +0200, Jan Klemkow wrote: Hi, This diff implements the hashing of the carp password before using it inside of the Kernel. It fix the problem that passwords like 12345678901234567890 and 12345678901234567890XXX are equal for carp. But It breaks the compatibility with older Versions. Maybe you need to increase the protocol number? bluhm@ have an other idea to solve this problem: ifconfig could XOR every 20 Byte long Chuck of the Passwort. This would not break the compatibility of setups with less than 20 char password. I would not do anyhing about that as it breaks compatibility without gain. Perhaps the XXX comment should be removed. What is actually wrong is that long passwords cannot be replaced completely with short passwords. ioctl(SIOCGVH) fills the carpr_key with the old value. strlcpy() overwrites only the beginning of the key. Jan, can you please test this? ok? bluhm Index: sbin/ifconfig/ifconfig.c === RCS file: /data/mirror/openbsd/cvs/src/sbin/ifconfig/ifconfig.c,v retrieving revision 1.264 diff -u -p -u -p -r1.264 ifconfig.c --- sbin/ifconfig/ifconfig.c31 May 2013 19:56:06 - 1.264 +++ sbin/ifconfig/ifconfig.c2 Jul 2013 11:01:38 - @@ -3390,7 +3390,7 @@ setcarp_passwd(const char *val, int d) if (ioctl(s, SIOCGVH, (caddr_t)ifr) == -1) err(1, SIOCGVH); - /* XXX Should hash the password into the key here, perhaps? */ + bzero(carpr.carpr_key, CARP_KEY_LEN); strlcpy((char *)carpr.carpr_key, val, CARP_KEY_LEN); if (ioctl(s, SIOCSVH, (caddr_t)ifr) == -1)
Re: Removing -Wno-format from kernel makefiles, 06/16
On Thu, Jul 04, 2013 at 06:39:03PM +0200, Stefan Fritsch wrote: diff --git sys/netinet/ip_output.c sys/netinet/ip_output.c index b59accf..43a0551 100644 --- sys/netinet/ip_output.c +++ sys/netinet/ip_output.c @@ -267,7 +267,7 @@ reroute: if (mtag != NULL) { #ifdef DIAGNOSTIC if (mtag-m_tag_len != sizeof (struct tdb_ident)) - panic(ip_output: tag of length %d (should be %d, + panic(ip_output: tag of length %hu (should be %zu, mtag-m_tag_len, sizeof (struct tdb_ident)); #endif tdbi = (struct tdb_ident *)(mtag + 1); diff --git sys/netinet6/ip6_forward.c sys/netinet6/ip6_forward.c index 6d7f971..1dff149 100644 --- sys/netinet6/ip6_forward.c +++ sys/netinet6/ip6_forward.c @@ -160,7 +160,7 @@ reroute: if (mtag != NULL) { #ifdef DIAGNOSTIC if (mtag-m_tag_len != sizeof (struct tdb_ident)) - panic(ip6_forward: tag of length %d (should be %d, + panic(ip6_forward: tag of length %hu (should be %zu, mtag-m_tag_len, sizeof (struct tdb_ident)); #endif tdbi = (struct tdb_ident *)(mtag + 1); diff --git sys/netinet6/ip6_output.c sys/netinet6/ip6_output.c index f405b31..baf4103 100644 --- sys/netinet6/ip6_output.c +++ sys/netinet6/ip6_output.c @@ -232,7 +232,7 @@ ip6_output(struct mbuf *m0, struct ip6_pktopts *opt, struct route_in6 *ro, if (mtag != NULL) { #ifdef DIAGNOSTIC if (mtag-m_tag_len != sizeof (struct tdb_ident)) - panic(ip6_output: tag of length %d (should be %d, + panic(ip6_output: tag of length %hu (should be %zu, mtag-m_tag_len, sizeof (struct tdb_ident)); #endif tdbi = (struct tdb_ident *)(mtag + 1); netinet and netinet6 is OK bluhm@ diff --git sys/nfs/nfs_socket.c sys/nfs/nfs_socket.c index e0f28e4..e1f7b3d 100644 --- sys/nfs/nfs_socket.c +++ sys/nfs/nfs_socket.c @@ -600,7 +600,7 @@ tryagain: } while (error == EWOULDBLOCK); if (!error auio.uio_resid 0) { log(LOG_INFO, - short receive (%d/%d) from nfs server %s\n, + short receive (%zd/%zd) from nfs server %s\n, sizeof(u_int32_t) - auio.uio_resid, sizeof(u_int32_t), rep-r_nmp-nm_mountp-mnt_stat.f_mntfromname); This should be %zu/%zu @@ -631,7 +631,7 @@ tryagain: error == ERESTART); if (!error auio.uio_resid 0) { log(LOG_INFO, - short receive (%d/%d) from nfs server %s\n, + short receive (%zu/%u) from nfs server %s\n, len - auio.uio_resid, len, rep-r_nmp-nm_mountp-mnt_stat.f_mntfromname); error = EPIPE; -- 1.7.6 Note that in nfs is another len that should be %u. log(LOG_ERR, %s (%d) from nfs server %s\n, impossible packet length, len, rep-r_nmp-nm_mountp-mnt_stat.f_mntfromname); bluhm
fix vmstat -M -N
Hi, $ vmstat -M bsd.0.core -N bsd.0 vmstat: undefined symbols: _uvm_km_pages_free There is no uvm_km_pages_free in our kernel. The corresponding lines in dopool_sysctl() have been removed from vmstat.c revision 1.116. Remove uvm_km_pages_free from dopool_kvm() to allow analysing a core dump. ok? bluhm Index: usr.bin/vmstat/vmstat.c === RCS file: /data/mirror/openbsd/cvs/src/usr.bin/vmstat/vmstat.c,v retrieving revision 1.121 diff -u -p -u -p -r1.121 vmstat.c --- usr.bin/vmstat/vmstat.c 14 May 2013 20:39:25 - 1.121 +++ usr.bin/vmstat/vmstat.c 18 Jul 2013 00:49:41 - @@ -78,8 +78,6 @@ struct nlist namelist[] = { { _nselcoll }, #define X_POOLHEAD 7 /* sysctl */ { _pool_head }, -#define X_KMPAGESFREE 8 /* sysctl */ - { _uvm_km_pages_free }, { }, }; @@ -1065,8 +1063,6 @@ dopool_kvm(void) inuse /= 1024; total /= 1024; - kread(X_KMPAGESFREE, kmfp, sizeof(kmfp)); - total += kmfp * (getpagesize() / 1024); printf(\nIn use %ldK, total allocated %ldK; utilization %.1f%%\n, inuse, total, (double)(100 * inuse) / total); }
ndp expire time
Hi, ndp uses an int expire_time for time calculations. This should be time_t. The routing messages and IPv6 prefixes and default router also have wrong expire time type. But this has to wait until ABI unlock. ok? bluhm Index: usr.sbin/ndp/ndp.c === RCS file: /data/mirror/openbsd/cvs/src/usr.sbin/ndp/ndp.c,v retrieving revision 1.47 diff -u -p -u -p -r1.47 ndp.c --- usr.sbin/ndp/ndp.c 21 Mar 2013 04:43:17 - 1.47 +++ usr.sbin/ndp/ndp.c 18 Jul 2013 22:49:26 - @@ -335,7 +335,8 @@ getsocket(void) struct sockaddr_in6 so_mask = {sizeof(so_mask), AF_INET6 }; struct sockaddr_in6 blank_sin = {sizeof(blank_sin), AF_INET6 }, sin_m; struct sockaddr_dl blank_sdl = {sizeof(blank_sdl), AF_LINK }, sdl_m; -intexpire_time, flags, found_entry; +time_t expire_time; +intflags, found_entry; struct { struct rt_msghdr m_rtm; charm_space[512]; @@ -379,7 +380,8 @@ set(int argc, char **argv) ea = (u_char *)LLADDR(sdl_m); if (ndp_ether_aton(eaddr, ea) == 0) sdl_m.sdl_alen = 6; - flags = expire_time = 0; + expire_time = 0; + flags = 0; while (argc-- 0) { if (strncmp(argv[0], temp, 4) == 0) { struct timeval time;
route -Wall
Hi, Can we compile /sbin/route with -Wall enabled? ok? bluhm Index: sbin/route/Makefile === RCS file: /data/mirror/openbsd/cvs/src/sbin/route/Makefile,v retrieving revision 1.12 diff -u -p -r1.12 Makefile --- sbin/route/Makefile 4 Sep 2010 09:39:56 - 1.12 +++ sbin/route/Makefile 19 Jul 2013 14:05:11 - @@ -4,6 +4,8 @@ PROG= route MAN= route.8 SRCS= route.c show.c +CFLAGS+= -Wall + route.o .depend lint tags: keywords.h .include bsd.prog.mk
route rmx_expire time_t
Hi, For 64 bit time_t the routing message rmx_expire field has to be changed from u_int to int64_t. I will do that after ABI unlock. I would like to prepare the /sbin/route source for this change. ok? bluhm Index: sbin/route/route.c === RCS file: /data/mirror/openbsd/cvs/src/sbin/route/route.c,v retrieving revision 1.162 diff -u -p -u -p -r1.162 route.c --- sbin/route/route.c 27 May 2013 14:07:25 - 1.162 +++ sbin/route/route.c 19 Jul 2013 10:21:20 - @@ -362,16 +362,19 @@ void set_metric(char *value, int key) { int flag = 0; - u_int noval, *valp = noval; const char *errstr; switch (key) { case K_MTU: - valp = rt_metrics.rmx_mtu; + rt_metrics.rmx_mtu = strtonum(value, 0, UINT_MAX, errstr); + if (errstr) + errx(1, set_metric mtu: %s is %s, value, errstr); flag = RTV_MTU; break; case K_EXPIRE: - valp = rt_metrics.rmx_expire; + rt_metrics.rmx_expire = strtonum(value, 0, UINT_MAX, errstr); + if (errstr) + errx(1, set_metric expire: %s is %s, value, errstr); flag = RTV_EXPIRE; break; case K_HOPCOUNT: @@ -390,9 +393,6 @@ set_metric(char *value, int key) rt_metrics.rmx_locks |= flag; if (locking) locking = 0; - *valp = strtonum(value, 0, UINT_MAX, errstr); - if (errstr) - errx(1, set_metric: %s is %s, value, errstr); } int @@ -1341,10 +1341,10 @@ print_rtmsg(struct rt_msghdr *rtm, int m #define lock(f)((rtm-rtm_rmx.rmx_locks __CONCAT(RTV_,f)) ? 'L' : ' ') if (rtm-rtm_rmx.rmx_expire) rtm-rtm_rmx.rmx_expire -= time(NULL); - printf(\nuse: %8llu mtu: %8u%c expire: %8d%c, + printf(\nuse: %8llu mtu: %8u%c expire: %8lld%c, rtm-rtm_rmx.rmx_pksent, rtm-rtm_rmx.rmx_mtu, lock(MTU), - rtm-rtm_rmx.rmx_expire, lock(EXPIRE)); + (long long)rtm-rtm_rmx.rmx_expire, lock(EXPIRE)); #undef lock } pmsg_common(rtm); @@ -1469,7 +1469,7 @@ print_getmsg(struct rt_msghdr *rtm, int printf(%8u%c , rtm-rtm_rmx.rmx_mtu, lock(MTU)); if (rtm-rtm_rmx.rmx_expire) rtm-rtm_rmx.rmx_expire -= time(NULL); - printf(%8d%c\n, rtm-rtm_rmx.rmx_expire, lock(EXPIRE)); + printf(%8lld%c\n, (long long)rtm-rtm_rmx.rmx_expire, lock(EXPIRE)); #undef lock #defineRTA_IGN (RTA_DST|RTA_GATEWAY|RTA_NETMASK|RTA_IFP|RTA_IFA|RTA_BRD) if (verbose)
arp expire time
Hi, I found more int expire_time that should be time_t in arp and rarpd. ok? bluhm Index: usr.sbin/arp/arp.c === RCS file: /data/mirror/openbsd/cvs/src/usr.sbin/arp/arp.c,v retrieving revision 1.52 diff -u -p -u -p -r1.52 arp.c --- usr.sbin/arp/arp.c 21 Mar 2013 04:43:17 - 1.52 +++ usr.sbin/arp/arp.c 19 Jul 2013 20:42:38 - @@ -248,8 +248,8 @@ getsocket(void) struct sockaddr_in so_mask = { 8, 0, 0, { 0x } }; struct sockaddr_inarp blank_sin = { sizeof(blank_sin), AF_INET }, sin_m; struct sockaddr_dl blank_sdl = { sizeof(blank_sdl), AF_LINK }, sdl_m; -intexpire_time, flags, export_only, doing_proxy, - found_entry; +time_t expire_time; +intflags, export_only, doing_proxy, found_entry; struct { struct rt_msghdrm_rtm; charm_space[512]; @@ -282,7 +282,8 @@ set(int argc, char *argv[]) errx(1, invalid ethernet address: %s, eaddr); memcpy(LLADDR(sdl_m), ea, sizeof(*ea)); sdl_m.sdl_alen = 6; - doing_proxy = flags = export_only = expire_time = 0; + expire_time = 0; + doing_proxy = flags = export_only = 0; while (argc-- 0) { if (strncmp(argv[0], temp, 4) == 0) { struct timeval time; Index: usr.sbin/rarpd/arptab.c === RCS file: /data/mirror/openbsd/cvs/src/usr.sbin/rarpd/arptab.c,v retrieving revision 1.18 diff -u -p -u -p -r1.18 arptab.c --- usr.sbin/rarpd/arptab.c 27 Oct 2009 23:59:54 - 1.18 +++ usr.sbin/rarpd/arptab.c 19 Jul 2013 20:39:42 - @@ -74,7 +74,8 @@ getsocket(void) struct sockaddr_in so_mask = {8, 0, 0, { 0x}}; struct sockaddr_inarp blank_sin = {sizeof(blank_sin), AF_INET }, sin_m; struct sockaddr_dl blank_sdl = {sizeof(blank_sdl), AF_LINK }, sdl_m; -intexpire_time, flags, export_only, doing_proxy; +time_t expire_time; +intflags, export_only, doing_proxy; struct { struct rt_msghdr m_rtm; @@ -104,7 +105,8 @@ arptab_set(u_char *eaddr, u_int32_t host sin-sin_addr.s_addr = host; memcpy((u_char *)LLADDR(sdl_m), (char *)eaddr, 6); sdl_m.sdl_alen = 6; - doing_proxy = flags = export_only = expire_time = 0; + expire_time = 0; + doing_proxy = flags = export_only = 0; gettimeofday(time, 0); expire_time = time.tv_sec + 20 * 60;
arp rarpd ndp warnings
Hi, Enable gcc warnings for arp, rarpd, ndp and fix findings. ok? bluhm Index: usr.sbin/arp/Makefile === RCS file: /data/mirror/openbsd/cvs/src/usr.sbin/arp/Makefile,v retrieving revision 1.3 diff -u -p -u -p -r1.3 Makefile --- usr.sbin/arp/Makefile 29 Mar 2005 23:56:30 - 1.3 +++ usr.sbin/arp/Makefile 19 Jul 2013 22:35:30 - @@ -2,6 +2,7 @@ PROG= arp MAN= arp.4 arp.8 -CFLAGS+= -Wall + +WARNINGS= Yes .include bsd.prog.mk Index: usr.sbin/arp/arp.c === RCS file: /data/mirror/openbsd/cvs/src/usr.sbin/arp/arp.c,v retrieving revision 1.52 diff -u -p -u -p -r1.52 arp.c --- usr.sbin/arp/arp.c 21 Mar 2013 04:43:17 - 1.52 +++ usr.sbin/arp/arp.c 19 Jul 2013 22:35:30 - @@ -82,7 +82,7 @@ static pid_t pid; static int replace;/* replace entries when adding */ static int nflag; /* no reverse dns lookups */ static int aflag; /* do it for all entries */ -static int s = -1; +static int rsock = -1; static int rdomain = 0; extern int h_errno; @@ -238,11 +238,11 @@ file(char *name) void getsocket(void) { - if (s = 0) + if (rsock = 0) return; - s = socket(PF_ROUTE, SOCK_RAW, 0); - if (s 0) - err(1, socket); + rsock = socket(PF_ROUTE, SOCK_RAW, 0); + if (rsock 0) + err(1, routing socket); } struct sockaddr_in so_mask = { 8, 0, 0, { 0x } }; @@ -285,10 +285,10 @@ set(int argc, char *argv[]) doing_proxy = flags = export_only = expire_time = 0; while (argc-- 0) { if (strncmp(argv[0], temp, 4) == 0) { - struct timeval time; + struct timeval now; - gettimeofday(time, 0); - expire_time = time.tv_sec + 20 * 60; + gettimeofday(now, 0); + expire_time = now.tv_sec + 20 * 60; if (flags RTF_PERMANENT_ARP) { /* temp or permanent, not both */ usage(); @@ -622,14 +622,14 @@ doit: l = rtm-rtm_msglen; rtm-rtm_seq = ++seq; rtm-rtm_type = cmd; - if (write(s, (char *)m_rtmsg, l) 0) + if (write(rsock, (char *)m_rtmsg, l) 0) if (errno != ESRCH || cmd != RTM_DELETE) { warn(writing to routing socket); return (-1); } do { - l = read(s, (char *)m_rtmsg, sizeof(m_rtmsg)); + l = read(rsock, (char *)m_rtmsg, sizeof(m_rtmsg)); } while (l 0 (rtm-rtm_version != RTM_VERSION || rtm-rtm_seq != seq || rtm-rtm_pid != pid)); Index: usr.sbin/ndp/Makefile === RCS file: /data/mirror/openbsd/cvs/src/usr.sbin/ndp/Makefile,v retrieving revision 1.2 diff -u -p -u -p -r1.2 Makefile --- usr.sbin/ndp/Makefile 25 Jan 2004 20:45:13 - 1.2 +++ usr.sbin/ndp/Makefile 19 Jul 2013 22:28:57 - @@ -6,4 +6,6 @@ MAN=ndp.8 # ndp.4 CPPFLAGS+=-DINET6 -I${.CURDIR} +WARNINGS= Yes + .include bsd.prog.mk Index: usr.sbin/ndp/ndp.c === RCS file: /data/mirror/openbsd/cvs/src/usr.sbin/ndp/ndp.c,v retrieving revision 1.48 diff -u -p -u -p -r1.48 ndp.c --- usr.sbin/ndp/ndp.c 19 Jul 2013 09:12:51 - 1.48 +++ usr.sbin/ndp/ndp.c 19 Jul 2013 22:22:26 - @@ -116,7 +116,7 @@ static pid_t pid; static int nflag; static int tflag; static int32_t thiszone; /* time difference with gmt */ -static int s = -1; +static int rsock = -1; static int repeat = 0; char ntop_buf[INET6_ADDRSTRLEN]; /* inet_ntop() */ @@ -154,12 +154,11 @@ static char *rtpref_str[] = { }; #endif -int mode = 0; -char *arg = NULL; - int main(int argc, char *argv[]) { + char *arg = NULL; + int mode = 0; int ch; pid = getpid(); @@ -323,13 +322,11 @@ file(char *name) void getsocket(void) { - if (s 0) { - s = socket(PF_ROUTE, SOCK_RAW, 0); - if (s 0) { - err(1, socket); - /* NOTREACHED */ - } - } + if (rsock = 0) + return; + rsock = socket(PF_ROUTE, SOCK_RAW, 0); + if (rsock 0) + err(1, routing socket); } struct sockaddr_in6 so_mask = {sizeof(so_mask), AF_INET6 }; @@ -384,10 +381,10 @@ set(int argc, char **argv) flags = 0; while (argc-- 0) { if (strncmp(argv[0], temp, 4) == 0) { - struct timeval time; + struct timeval now; - gettimeofday(time, 0); - expire_time = time.tv_sec + 20 * 60; + gettimeofday(now,
route warnings
Hi, Enable WARNINGS=Yes for route and fix findings. Avoid shadowing for routing socket and use global variable af. ok? bluhm Index: sbin/route/Makefile === RCS file: /data/mirror/openbsd/cvs/src/sbin/route/Makefile,v retrieving revision 1.13 diff -u -p -r1.13 Makefile --- sbin/route/Makefile 19 Jul 2013 14:41:46 - 1.13 +++ sbin/route/Makefile 19 Jul 2013 22:43:54 - @@ -4,7 +4,7 @@ PROG= route MAN= route.8 SRCS= route.c show.c -CFLAGS+= -Wall +WARNINGS= Yes route.o .depend lint tags: keywords.h Index: sbin/route/route.c === RCS file: /data/mirror/openbsd/cvs/src/sbin/route/route.c,v retrieving revision 1.163 diff -u -p -r1.163 route.c --- sbin/route/route.c 19 Jul 2013 20:10:23 - 1.163 +++ sbin/route/route.c 19 Jul 2013 22:54:46 - @@ -66,7 +66,7 @@ union sockunion so_dst, so_gate, so_mask typedef union sockunion *sup; pid_t pid; -intrtm_addrs, s; +intrtm_addrs, rsock; intforcehost, forcenet, Fflag, nflag, af, qflag, tflag, Tflag; intiflag, verbose, aflen = sizeof(struct sockaddr_in); intlocking, lockrest, debugonly; @@ -183,14 +183,14 @@ main(int argc, char **argv) break; default: if (tflag) - s = open(_PATH_DEVNULL, O_WRONLY); + rsock = open(_PATH_DEVNULL, O_WRONLY); else - s = socket(PF_ROUTE, SOCK_RAW, 0); - if (s == -1) - err(1, socket); + rsock = socket(PF_ROUTE, SOCK_RAW, 0); + if (rsock == -1) + err(1, routing socket); /* force socket onto table user requested */ if (Tflag == 1 Terr == 0 - setsockopt(s, AF_ROUTE, ROUTE_TABLEFILTER, + setsockopt(rsock, AF_ROUTE, ROUTE_TABLEFILTER, tableid, sizeof(tableid)) == -1) err(1, setsockopt(ROUTE_TABLEFILTER)); break; @@ -242,7 +242,7 @@ flushroutes(int argc, char **argv) if (uid) errx(1, must be root to alter routing table); - shutdown(s, 0); /* Don't want to read back our messages */ + shutdown(rsock, 0); /* Don't want to read back our messages */ while (--argc 0) { if (**(++argv) == '-') switch (keyword(*argv + 1)) { @@ -334,7 +334,7 @@ flushroutes(int argc, char **argv) rtm-rtm_type = RTM_DELETE; rtm-rtm_seq = seqno; rtm-rtm_tableid = tableid; - rlen = write(s, next, rtm-rtm_msglen); + rlen = write(rsock, next, rtm-rtm_msglen); if (rlen (int)rtm-rtm_msglen) { warn(write to routing socket); printf(got only %d for rlen\n, rlen); @@ -411,7 +411,7 @@ newroute(int argc, char **argv) errx(1, must be root to alter routing table); cmd = argv[0]; if (*cmd != 'g') - shutdown(s, 0); /* Don't want to read back our messages */ + shutdown(rsock, 0); /* Don't want to read back our messages */ while (--argc 0) { if (**(++argv)== '-') { switch (key = keyword(1 + *argv)) { @@ -662,8 +662,6 @@ newroute(int argc, char **argv) void show(int argc, char *argv[]) { - int af = 0; - while (--argc 0) { if (**(++argv)== '-') switch (keyword(*argv + 1)) { @@ -1058,7 +1056,6 @@ interfaces(void) void monitor(int argc, char *argv[]) { - int af = 0; unsigned int filter = 0; int n; char msg[2048]; @@ -1086,14 +1083,14 @@ monitor(int argc, char *argv[]) usage(*argv); } - s = socket(PF_ROUTE, SOCK_RAW, af); - if (s == -1) - err(1, socket); + rsock = socket(PF_ROUTE, SOCK_RAW, af); + if (rsock == -1) + err(1, routing socket); - if (setsockopt(s, AF_ROUTE, ROUTE_MSGFILTER, filter, + if (setsockopt(rsock, AF_ROUTE, ROUTE_MSGFILTER, filter, sizeof(filter)) == -1) err(1, setsockopt(ROUTE_MSGFILTER)); - if (Tflag setsockopt(s, AF_ROUTE, ROUTE_TABLEFILTER, tableid, + if (Tflag setsockopt(rsock, AF_ROUTE, ROUTE_TABLEFILTER, tableid, sizeof(tableid)) == -1) err(1, setsockopt(ROUTE_TABLEFILTER)); @@ -1103,7 +1100,7 @@ monitor(int argc, char *argv[]) exit(0); } for (;;) { - if ((n = read(s, msg, sizeof(msg))) == -1) { + if ((n = read(rsock, msg, sizeof(msg))) == -1) { if (errno == EINTR) continue; err(1, read); @@ -1179,14
tcp_ctloutput intotcpcb
Hi, For me it looks like tp is not accessed between the two assingments. intotcpcb() is a define without side effects. So it should be safe to use the same code for inet and inet6. ok? bluhm Index: netinet/tcp_usrreq.c === RCS file: /data/mirror/openbsd/cvs/src/sys/netinet/tcp_usrreq.c,v retrieving revision 1.112 diff -u -p -r1.112 tcp_usrreq.c --- netinet/tcp_usrreq.c17 May 2013 09:04:30 - 1.112 +++ netinet/tcp_usrreq.c4 Aug 2013 20:46:17 - @@ -498,9 +498,6 @@ tcp_ctloutput(op, so, level, optname, mp (void) m_free(*mp); return (ECONNRESET); } -#ifdef INET6 - tp = intotcpcb(inp); -#endif /* INET6 */ if (level != IPPROTO_TCP) { switch (so-so_proto-pr_domain-dom_family) { #ifdef INET6 @@ -518,9 +515,7 @@ tcp_ctloutput(op, so, level, optname, mp splx(s); return (error); } -#ifndef INET6 tp = intotcpcb(inp); -#endif /* !INET6 */ switch (op) {
include netinet/in_var.h in arch/dev
Hi, I have just removed a bunch of useless include netinet/in_var.h from the machine independent drivers. I suspect that they are also not needed in the architecture specific network drivers. Unfortunately I don't have any of these machines. So if you have access to one of macppc mvme68k octeon sgi sparc vax could you please test if this diff compiles. ok? bluhm Index: arch/macppc/dev/if_mc.c === RCS file: /data/mirror/openbsd/cvs/src/sys/arch/macppc/dev/if_mc.c,v retrieving revision 1.14 diff -u -p -r1.14 if_mc.c --- arch/macppc/dev/if_mc.c 21 Apr 2010 03:03:26 - 1.14 +++ arch/macppc/dev/if_mc.c 7 Aug 2013 00:57:57 - @@ -56,7 +56,6 @@ #include netinet/in.h #include netinet/if_ether.h #include netinet/in_systm.h -#include netinet/in_var.h #include netinet/ip.h #endif Index: arch/mvme68k/dev/if_ie.c === RCS file: /data/mirror/openbsd/cvs/src/sys/arch/mvme68k/dev/if_ie.c,v retrieving revision 1.40 diff -u -p -r1.40 if_ie.c --- arch/mvme68k/dev/if_ie.c10 Oct 2012 04:52:16 - 1.40 +++ arch/mvme68k/dev/if_ie.c7 Aug 2013 00:57:57 - @@ -120,7 +120,6 @@ Mode of operation: #ifdef INET #include netinet/in.h #include netinet/in_systm.h -#include netinet/in_var.h #include netinet/ip.h #include netinet/if_ether.h #endif Index: arch/mvme88k/dev/if_ie.c === RCS file: /data/mirror/openbsd/cvs/src/sys/arch/mvme88k/dev/if_ie.c,v retrieving revision 1.45 diff -u -p -r1.45 if_ie.c --- arch/mvme88k/dev/if_ie.c10 Oct 2012 04:52:16 - 1.45 +++ arch/mvme88k/dev/if_ie.c7 Aug 2013 00:57:57 - @@ -119,7 +119,6 @@ Mode of operation: #ifdef INET #include netinet/in.h #include netinet/in_systm.h -#include netinet/in_var.h #include netinet/ip.h #include netinet/if_ether.h #endif Index: arch/octeon/dev/if_cnmac.c === RCS file: /data/mirror/openbsd/cvs/src/sys/arch/octeon/dev/if_cnmac.c,v retrieving revision 1.10 diff -u -p -r1.10 if_cnmac.c --- arch/octeon/dev/if_cnmac.c 12 Apr 2013 15:22:26 - 1.10 +++ arch/octeon/dev/if_cnmac.c 7 Aug 2013 00:57:57 - @@ -66,7 +66,6 @@ #include netinet/in.h #include netinet/in_systm.h -#include netinet/in_var.h #include netinet/ip.h #include machine/bus.h Index: arch/sgi/dev/if_iec.c === RCS file: /data/mirror/openbsd/cvs/src/sys/arch/sgi/dev/if_iec.c,v retrieving revision 1.8 diff -u -p -r1.8 if_iec.c --- arch/sgi/dev/if_iec.c 22 May 2012 19:24:59 - 1.8 +++ arch/sgi/dev/if_iec.c 7 Aug 2013 00:57:57 - @@ -101,7 +101,6 @@ #ifdef INET #include netinet/in.h #include netinet/in_systm.h -#include netinet/in_var.h #include netinet/ip.h #endif Index: arch/sgi/dev/if_mec.c === RCS file: /data/mirror/openbsd/cvs/src/sys/arch/sgi/dev/if_mec.c,v retrieving revision 1.25 diff -u -p -r1.25 if_mec.c --- arch/sgi/dev/if_mec.c 3 Oct 2012 22:46:09 - 1.25 +++ arch/sgi/dev/if_mec.c 7 Aug 2013 00:57:57 - @@ -85,7 +85,6 @@ #ifdef INET #include netinet/in.h #include netinet/in_systm.h -#include netinet/in_var.h #include netinet/ip.h #endif Index: arch/sgi/hpc/if_sq.c === RCS file: /data/mirror/openbsd/cvs/src/sys/arch/sgi/hpc/if_sq.c,v retrieving revision 1.8 diff -u -p -r1.8 if_sq.c --- arch/sgi/hpc/if_sq.c28 May 2012 17:03:35 - 1.8 +++ arch/sgi/hpc/if_sq.c7 Aug 2013 00:57:57 - @@ -57,7 +57,6 @@ #ifdef INET #include netinet/in.h #include netinet/in_systm.h -#include netinet/in_var.h #include netinet/ip.h #endif Index: arch/sparc/dev/be.c === RCS file: /data/mirror/openbsd/cvs/src/sys/arch/sparc/dev/be.c,v retrieving revision 1.43 diff -u -p -r1.43 be.c --- arch/sparc/dev/be.c 28 Nov 2008 02:44:17 - 1.43 +++ arch/sparc/dev/be.c 7 Aug 2013 00:57:57 - @@ -46,7 +46,6 @@ #ifdef INET #include netinet/in.h #include netinet/in_systm.h -#include netinet/in_var.h #include netinet/ip.h #include netinet/if_ether.h #endif Index: arch/sparc/dev/hme.c === RCS file: /data/mirror/openbsd/cvs/src/sys/arch/sparc/dev/hme.c,v retrieving revision 1.62 diff -u -p -r1.62 hme.c --- arch/sparc/dev/hme.c13 Aug 2009 17:01:31 - 1.62 +++ arch/sparc/dev/hme.c7 Aug 2013 00:57:57 - @@ -59,7 +59,6 @@ #ifdef INET #include netinet/in.h #include netinet/in_systm.h -#include netinet/in_var.h #include netinet/ip.h #include netinet/if_ether.h #include netinet/tcp.h Index: arch/sparc/dev/if_gem_sbus.c
nd6 expire
Hi, To control the lifetime of IPv6 addresses, prefixes and default routers, the kernel and ndp use a bunch of expire fields. Currently they are int or long, but expire should always be time_t. Move vltime and pltime to u_int32_t everywhere. Sort struct fields by size. Struct inet6_ndpr_msghdr is not used at all, so remove it. ok? bluhm Index: netinet6/nd6.h === RCS file: /data/mirror/openbsd/cvs/src/sys/netinet6/nd6.h,v retrieving revision 1.31 diff -u -p -u -p -r1.31 nd6.h --- netinet6/nd6.h 1 Jul 2013 14:22:20 - 1.31 +++ netinet6/nd6.h 7 Aug 2013 22:54:51 - @@ -46,14 +46,14 @@ struct llinfo_nd6 { struct llinfo_nd6 *ln_prev; struct rtentry *ln_rt; struct mbuf *ln_hold; /* last packet until resolved/timeout */ - longln_asked; /* number of queries already sent for this addr */ - u_long ln_expire; /* lifetime for NDP state transition */ + time_t ln_expire; /* lifetime for NDP state transition */ + longln_asked; /* number of queries already sent for addr */ + int ln_byhint; /* # of times we made it reachable by UL hint */ short ln_state; /* reachability state */ short ln_router; /* 2^0: ND6 router bit */ - int ln_byhint; /* # of times we made it reachable by UL hint */ longln_ntick; - struct timeout ln_timer_ch; + struct timeout ln_timer_ch; }; #define ND6_LLINFO_PURGE -3 @@ -107,10 +107,10 @@ struct nd_ifinfo { struct in6_nbrinfo { char ifname[IFNAMSIZ]; /* if name, e.g. en0 */ struct in6_addr addr; /* IPv6 address of the neighbor */ - longasked; /* number of queries already sent for this addr */ + time_t expire; /* lifetime for NDP state transition */ + longasked; /* number of queries already sent for addr */ int isrouter; /* if it acts as a router */ int state; /* reachability state */ - int expire; /* lifetime for NDP state transition */ }; #define DRLSTSIZ 10 @@ -119,19 +119,19 @@ structin6_drlist { char ifname[IFNAMSIZ]; struct { struct in6_addr rtaddr; - u_char flags; + time_t expire; u_short rtlifetime; - u_long expire; - u_short if_index; + u_short if_index; + u_char flags; } defrouter[DRLSTSIZ]; }; struct in6_defrouter { struct sockaddr_in6 rtaddr; - u_char flags; + time_t expire; u_short rtlifetime; - u_long expire; - u_short if_index; + u_short if_index; + u_char flags; }; #ifdef _KERNEL @@ -139,14 +139,14 @@ structin6_oprlist { char ifname[IFNAMSIZ]; struct { struct in6_addr prefix; - struct prf_ra raflags; + struct prf_ra raflags; + time_t expire; + u_int32_t vltime; + u_int32_t pltime; + u_short if_index; + u_short advrtrs; /* number of advertisement routers */ u_char prefixlen; u_char origin; - u_long vltime; - u_long pltime; - u_long expire; - u_short if_index; - u_short advrtrs; /* number of advertisement routers */ struct in6_addr advrtr[DRLSTSIZ]; /* XXX: explicit limit */ } prefix[PRLSTSIZ]; }; @@ -156,30 +156,30 @@ structin6_prlist { char ifname[IFNAMSIZ]; struct { struct in6_addr prefix; - struct prf_ra raflags; - u_char prefixlen; - u_char origin; + struct prf_ra raflags; + time_t expire; u_int32_t vltime; u_int32_t pltime; - time_t expire; - u_short if_index; - u_short advrtrs; /* number of advertisement routers */ + u_short if_index; + u_short advrtrs; /* number of advertisement routers */ + u_char prefixlen; + u_char origin; struct in6_addr advrtr[DRLSTSIZ]; /* XXX: explicit limit */ } prefix[PRLSTSIZ]; }; struct in6_prefix { struct sockaddr_in6 prefix; - struct prf_ra raflags; - u_char prefixlen; - u_char origin; + struct prf_ra raflags; + time_t expire; u_int32_t vltime; u_int32_t pltime; - time_t expire; u_int32_t flags; - int refcnt; - u_short if_index; - u_short advrtrs; /* number of advertisement routers */ + int refcnt; + u_short if_index; + u_short advrtrs; /* number of advertisement routers */ + u_char
Re: nd6 expire
On Thu, Aug 08, 2013 at 01:47:17PM +0200, Martin Pieuchot wrote: On 08/08/13(Thu) 01:06, Alexander Bluhm wrote: Hi, To control the lifetime of IPv6 addresses, prefixes and default routers, the kernel and ndp use a bunch of expire fields. Currently they are int or long, but expire should always be time_t. Move vltime and pltime to u_int32_t everywhere. Sort struct fields by size. Struct inet6_ndpr_msghdr is not used at all, so remove it. It looks to me that the in6_oprlist structure is here only for some binary compatibility. So changing its fields makes no sense, however I think you can completely remove it as it has been introduced in 2002 and nothing use the SIOCGPRLST_IN6 ioctl(2) anymore. ;) We have the code oprl-prefix[i].expire = pr-ndpr_expire; in the kernel right now. It is wrong to leave in6_oprlist.prefix-expire as u_long and ndpr_expire as time_t. Binary compatibility for ndp will break with this diff anyway and for most programs with the big time_t diff. Ndp implements ioctl(s, SIOCGPRLST_IN6, (caddr_t)pr), but does not use it because of #ifdef. I would like to do it this way: 1. fix time_t in all structures with this diff 2. throw away #ifdef in ndp 3. remove obsolete ioctl from kernel 4. remove obsolete struct from header ok? bluhm Apart from that it looks ok to me. bluhm Index: netinet6/nd6.h === RCS file: /data/mirror/openbsd/cvs/src/sys/netinet6/nd6.h,v retrieving revision 1.31 diff -u -p -u -p -r1.31 nd6.h --- netinet6/nd6.h 1 Jul 2013 14:22:20 - 1.31 +++ netinet6/nd6.h 7 Aug 2013 22:54:51 - @@ -46,14 +46,14 @@ struct llinfo_nd6 { struct llinfo_nd6 *ln_prev; struct rtentry *ln_rt; struct mbuf *ln_hold; /* last packet until resolved/timeout */ - longln_asked; /* number of queries already sent for this addr */ - u_long ln_expire; /* lifetime for NDP state transition */ + time_t ln_expire; /* lifetime for NDP state transition */ + longln_asked; /* number of queries already sent for addr */ + int ln_byhint; /* # of times we made it reachable by UL hint */ short ln_state; /* reachability state */ short ln_router; /* 2^0: ND6 router bit */ - int ln_byhint; /* # of times we made it reachable by UL hint */ longln_ntick; - struct timeout ln_timer_ch; + struct timeout ln_timer_ch; }; #define ND6_LLINFO_PURGE -3 @@ -107,10 +107,10 @@ struct nd_ifinfo { struct in6_nbrinfo { char ifname[IFNAMSIZ]; /* if name, e.g. en0 */ struct in6_addr addr; /* IPv6 address of the neighbor */ - longasked; /* number of queries already sent for this addr */ + time_t expire; /* lifetime for NDP state transition */ + longasked; /* number of queries already sent for addr */ int isrouter; /* if it acts as a router */ int state; /* reachability state */ - int expire; /* lifetime for NDP state transition */ }; #define DRLSTSIZ 10 @@ -119,19 +119,19 @@ structin6_drlist { char ifname[IFNAMSIZ]; struct { struct in6_addr rtaddr; - u_char flags; + time_t expire; u_short rtlifetime; - u_long expire; - u_short if_index; + u_short if_index; + u_char flags; } defrouter[DRLSTSIZ]; }; struct in6_defrouter { struct sockaddr_in6 rtaddr; - u_char flags; + time_t expire; u_short rtlifetime; - u_long expire; - u_short if_index; + u_short if_index; + u_char flags; }; #ifdef _KERNEL @@ -139,14 +139,14 @@ structin6_oprlist { char ifname[IFNAMSIZ]; struct { struct in6_addr prefix; - struct prf_ra raflags; + struct prf_ra raflags; + time_t expire; + u_int32_t vltime; + u_int32_t pltime; + u_short if_index; + u_short advrtrs; /* number of advertisement routers */ u_char prefixlen; u_char origin; - u_long vltime; - u_long pltime; - u_long expire; - u_short if_index; - u_short advrtrs; /* number of advertisement routers */ struct in6_addr advrtr[DRLSTSIZ]; /* XXX: explicit limit */ } prefix[PRLSTSIZ]; }; @@ -156,30 +156,30 @@ structin6_prlist { char ifname[IFNAMSIZ]; struct { struct in6_addr prefix; - struct prf_ra raflags; - u_char prefixlen; - u_char origin; + struct prf_ra raflags; + time_t expire; u_int32_t vltime; u_int32_t pltime
ndp ifdef cleanup
Hi, Remove dead code and useless #include and #ifdef from ndp. No binary change. ok? bluhm Index: usr.sbin/ndp/Makefile === RCS file: /data/mirror/openbsd/cvs/src/usr.sbin/ndp/Makefile,v retrieving revision 1.2 diff -u -p -r1.2 Makefile --- usr.sbin/ndp/Makefile 25 Jan 2004 20:45:13 - 1.2 +++ usr.sbin/ndp/Makefile 8 Aug 2013 21:49:27 - @@ -2,7 +2,7 @@ PROG= ndp SRCS= ndp.c gmt2local.c -MAN= ndp.8 # ndp.4 +MAN= ndp.8 CPPFLAGS+=-DINET6 -I${.CURDIR} Index: usr.sbin/ndp/gmt2local.c === RCS file: /data/mirror/openbsd/cvs/src/usr.sbin/ndp/gmt2local.c,v retrieving revision 1.3 diff -u -p -r1.3 gmt2local.c --- usr.sbin/ndp/gmt2local.c2 Oct 2008 23:55:18 - 1.3 +++ usr.sbin/ndp/gmt2local.c8 Aug 2013 22:00:26 - @@ -25,14 +25,7 @@ #include sys/time.h #include stdio.h -#ifdef TIME_WITH_SYS_TIME #include time.h -#endif - -#include gnuc.h -#ifdef HAVE_OS_PROTO_H -#include os-proto.h -#endif #include gmt2local.h Index: usr.sbin/ndp/gnuc.h === RCS file: usr.sbin/ndp/gnuc.h diff -N usr.sbin/ndp/gnuc.h --- usr.sbin/ndp/gnuc.h 10 Dec 1999 07:26:56 - 1.2 +++ /dev/null 1 Jan 1970 00:00:00 - @@ -1,3 +0,0 @@ -/* $OpenBSD: gnuc.h,v 1.2 1999/12/10 07:26:56 itojun Exp $ */ - -/* this is dummy to pacify gmt2local.c. */ Index: usr.sbin/ndp/ndp.c === RCS file: /data/mirror/openbsd/cvs/src/usr.sbin/ndp/ndp.c,v retrieving revision 1.48 diff -u -p -r1.48 ndp.c --- usr.sbin/ndp/ndp.c 19 Jul 2013 09:12:51 - 1.48 +++ usr.sbin/ndp/ndp.c 8 Aug 2013 21:56:18 - @@ -145,14 +145,12 @@ static char *sec2str(time_t); static char *ether_str(struct sockaddr_dl *); static void ts_print(const struct timeval *); -#ifdef ICMPV6CTL_ND6_DRLIST static char *rtpref_str[] = { medium, /* 00 */ high, /* 01 */ rsv, /* 10 */ low /* 11 */ }; -#endif int mode = 0; char *arg = NULL; @@ -634,15 +632,8 @@ again:; getnameinfo((struct sockaddr *)sin, sin-sin6_len, host_buf, sizeof(host_buf), NULL, 0, (nflag ? NI_NUMERICHOST : 0)); if (cflag) { -#ifdef RTF_WASCLONED - if (rtm-rtm_flags RTF_WASCLONED) - delete(host_buf); -#elif defined(RTF_CLONED) if (rtm-rtm_flags RTF_CLONED) delete(host_buf); -#else - delete(host_buf); -#endif continue; } gettimeofday(time, 0); @@ -680,11 +671,6 @@ again:; case ND6_LLINFO_NOSTATE: printf( N); break; -#ifdef ND6_LLINFO_WAITDELETE - case ND6_LLINFO_WAITDELETE: -printf( W); -break; -#endif case ND6_LLINFO_INCOMPLETE: printf( I); break; @@ -893,9 +879,6 @@ ifinfo(char *ifname, int argc, char **ar struct in6_ndireq nd; int i, s; u_int32_t newflags; -#ifdef IPV6CTL_USETEMPADDR - u_int8_t nullbuf[8]; -#endif if ((s = socket(AF_INET6, SOCK_DGRAM, 0)) 0) { err(1, socket); @@ -928,12 +911,7 @@ ifinfo(char *ifname, int argc, char **ar }\ } while (0) SETFLAG(nud, ND6_IFF_PERFORMNUD); -#ifdef ND6_IFF_ACCEPT_RTADV SETFLAG(accept_rtadv, ND6_IFF_ACCEPT_RTADV); -#endif -#ifdef ND6_IFF_PREFER_SOURCE - SETFLAG(prefer_source, ND6_IFF_PREFER_SOURCE); -#endif ND.flags = newflags; if (ioctl(s, SIOCSIFINFO_FLAGS, (caddr_t)nd) 0) { @@ -954,44 +932,12 @@ ifinfo(char *ifname, int argc, char **ar ND.basereachable / 1000, ND.basereachable % 1000); printf(, reachable=%ds, ND.reachable); printf(, retrans=%ds%dms, ND.retrans / 1000, ND.retrans % 1000); -#ifdef IPV6CTL_USETEMPADDR - memset(nullbuf, 0, sizeof(nullbuf)); - if (memcmp(nullbuf, ND.randomid, sizeof(nullbuf)) != 0) { - int j; - u_int8_t *rbuf; - - for (i = 0; i 3; i++) { - switch (i) { - case 0: - printf(\nRandom seed(0): ); - rbuf = ND.randomseed0; - break; - case 1: - printf(\nRandom seed(1): ); - rbuf = ND.randomseed1; - break; - case 2: -
Re: in_proto_cksum_out: fix ICMP checksum calculation
On Mon, Aug 05, 2013 at 10:28:57AM -0400, Lawrence Teo wrote: Index: ip_output.c === RCS file: /cvs/src/sys/netinet/ip_output.c,v retrieving revision 1.244 diff -U5 -p -r1.244 ip_output.c --- ip_output.c 31 Jul 2013 15:41:52 - 1.244 +++ ip_output.c 5 Aug 2013 02:44:20 - @@ -2058,25 +2058,35 @@ ip_mloopback(struct ifnet *ifp, struct m */ void in_delayed_cksum(struct mbuf *m) { struct ip *ip; - u_int16_t csum, offset; + u_int16_t csum = 0, offset; ip = mtod(m, struct ip *); offset = ip-ip_hl 2; + + if (ip-ip_p == IPPROTO_ICMP) + if (m_copyback(m, offset + offsetof(struct icmp, icmp_cksum), + sizeof(csum), csum, M_NOWAIT)) + return; The code at the end of this function tries to avoid the m_copyback() in the common case unless (offset + sizeof(u_int16_t)) m-m_len). Do we want this optimization here? bluhm + csum = in4_cksum(m, 0, offset, m-m_pkthdr.len - offset); - if (csum == 0 ip-ip_p == IPPROTO_UDP) - csum = 0x; switch (ip-ip_p) { case IPPROTO_TCP: offset += offsetof(struct tcphdr, th_sum); break; case IPPROTO_UDP: offset += offsetof(struct udphdr, uh_sum); + if (csum == 0) + csum = 0x; + break; + + case IPPROTO_ICMP: + offset += offsetof(struct icmp, icmp_cksum); break; default: return; } @@ -2101,17 +2111,9 @@ in_proto_cksum_out(struct mbuf *m, struc ifp-if_bridgeport != NULL) { in_delayed_cksum(m); m-m_pkthdr.csum_flags = ~M_UDP_CSUM_OUT; /* Clear */ } } else if (m-m_pkthdr.csum_flags M_ICMP_CSUM_OUT) { - struct ip *ip = mtod(m, struct ip *); - int hlen; - struct icmp *icp; - - hlen = ip-ip_hl 2; - icp = (struct icmp *)(mtod(m, caddr_t) + hlen); - icp-icmp_cksum = 0; - icp-icmp_cksum = in4_cksum(m, 0, hlen, - ntohs(ip-ip_len) - hlen); + in_delayed_cksum(m); m-m_pkthdr.csum_flags = ~M_ICMP_CSUM_OUT; /* Clear */ } }
panic __mp_lock_held(sched_lock)
Hi, On my ThinkPat T430s I am trying to debug multithreaded qemu by attaching gdb. This crashes the kernel of the host system within a few minutes. Luckily I managed to attach a serial over lan with Intel AMT. login: panic: kernel diagnostic assertion __mp_lock_held(sched_lock) == 0 failed: file ../../../../kern/kern_lock.c, line 126 Stopped at Debugger+0x5: leave RUN AT LEAST 'trace' AND 'ps' AND INCLUDE OUTPUT WHEN REPORTING THIS PANIC! IF RUNNING SMP, USE 'mach ddbcpu #' AND 'trace' ON OTHER PROCESSORS, TOO. DO NOT EVEN BOTHER REPORTING THIS WITHOUT INCLUDING THAT INFORMATION! ddb{0} trace Debugger() at Debugger+0x5 panic() at panic+0xee __assert() at __assert+0x21 _kernel_lock_init() at _kernel_lock_init issignal() at issignal+0x205 sleep_setup_signal() at sleep_setup_signal+0x94 tsleep() at tsleep+0x86 sys_sigsuspend() at sys_sigsuspend+0x46 syscall() at syscall+0x249 --- syscall (number 111) --- end of kernel end trace frame: 0x7fe55fdbef0, count: -9 0x7fe50c4cdcc: PID PPID PGRPUID S FLAGS WAIT COMMAND 28380 5201 5983 1000 3 0x4100080 thrsleep qemu-system-x86_ * 5825 5201 5983 1000 7 0xc100088 pause qemu-system-x86_ 18891 5201 5983 1000 3 0xc100080 sigwait qemu-system-x86_ 5983 5201 5983 1000 3 0x880 thrsleep qemu-system-x86_ 19446 22621 19446 1000 30x80 poll gdb 5201 12983 5201 1000 30x80 wait gdb The kernel lock is acquired in mi_syscall() as sys_sigsuspend() needs it. tsleep() calls sleep_setup() which acquires the sched lock. Then sleep_setup_signal() calls issignal() via the macro CURSIG(). The function issignal() is full of side effects, especially for a traced process. There the kernel lock is acquired again, which should be fine as it is a recursive lock. But to avoid deadlocks, _kernel_lock() asserts that is is acquired before sched lock. This check is too strict, the condition is only true when the lock is taken the first time. Index: kern/kern_lock.c === RCS file: /data/mirror/openbsd/cvs/src/sys/kern/kern_lock.c,v retrieving revision 1.42 diff -u -p -u -p -r1.42 kern_lock.c --- kern/kern_lock.c6 May 2013 16:37:55 - 1.42 +++ kern/kern_lock.c11 Aug 2013 01:54:06 - @@ -123,7 +123,10 @@ _kernel_lock_init(void) void _kernel_lock(void) { - SCHED_ASSERT_UNLOCKED(); +#ifdef DIAGNOSTIC + if (__mp_lock_held(kernel_lock) == 0) + SCHED_ASSERT_UNLOCKED(); +#endif /* DIAGNOSTIC */ __mp_lock(kernel_lock); } Unfortunately this fix does not solve my problem. With that I get another panic: wakeup: p_stat is 7 login: panic: wakeup: p_stat is 7 Stopped at Debugger+0x5: leave RUN AT LEAST 'trace' AND 'ps' AND INCLUDE OUTPUT WHEN REPORTING THIS PANIC! IF RUNNING SMP, USE 'mach ddbcpu #' AND 'trace' ON OTHER PROCESSORS, TOO. DO NOT EVEN BOTHER REPORTING THIS WITHOUT INCLUDING THAT INFORMATION! ddb{3} trace Debugger() at Debugger+0x5 panic() at panic+0xee wakeup_n() at wakeup_n+0xfd sys___thrwakeup() at sys___thrwakeup+0x54 syscall() at syscall+0x249 --- syscall (number 301) --- end of kernel end trace frame: 0x684cb9237c0, count: -5 0x684bf834c2a: PID PPID PGRPUID S FLAGS WAIT COMMAND 10959 11922 10959 1000 30x80 wait gdb *11287 10959 10043 1000 7 0xc10qemu-system-x86_ 11131 10959 10043 1000 3 0xc100080 sigwait qemu-system-x86_ 10043 10959 10043 1000 7 0x800qemu-system-x86_ I will investigate further. bluhm
ddb show proc flags
Hi, The ps flags are split between thread and process. It would be useful if ddb shows both. I or them together in the ps overview and list them explicitly for the specific thread. ddb show all procs PID PPID PGRPUID S FLAGS WAIT COMMAND 18514 1 18514 0 3 0x40180 selectsendmail ddb show proc 0xd317a460 PROC (sendmail) pid=18514 stat=sleep flags process=40100SUGID,SUGIDEXEC proc=80SINTR I also synced the ddb bit names with the define names. ok? bluhm Index: kern/kern_proc.c === RCS file: /data/mirror/openbsd/cvs/src/sys/kern/kern_proc.c,v retrieving revision 1.51 diff -u -p -u -p -r1.51 kern_proc.c --- kern/kern_proc.c8 Aug 2013 23:25:06 - 1.51 +++ kern/kern_proc.c11 Aug 2013 03:29:35 - @@ -395,8 +395,9 @@ proc_printit(struct proc *p, const char else pst = pstat[(int)p-p_stat - 1]; - (*pr)(PROC (%s) pid=%d stat=%s flags=%b\n, - p-p_comm, p-p_pid, pst, p-p_flag, P_BITS); + (*pr)(PROC (%s) pid=%d stat=%s\n, p-p_comm, p-p_pid, pst); + (*pr)(flags process=%b proc=%b\n, + p-p_p-ps_flags, P_BITS, p-p_flag, P_BITS); (*pr)(pri=%u, usrpri=%u, nice=%d\n, p-p_priority, p-p_usrpri, p-p_p-ps_nice); (*pr)(forw=%p, list=%p,%p\n, @@ -474,7 +475,8 @@ db_show_all_procs(db_expr_t addr, int ha %-12.12s %-16s\n, ppr ? ppr-ps_pid : -1, pr-ps_pgrp ? pr-ps_pgrp-pg_id : -1, - pr-ps_cred-p_ruid, p-p_stat, p-p_flag, + pr-ps_cred-p_ruid, p-p_stat, + p-p_flag | p-p_p-ps_flags, (p-p_wchan p-p_wmesg) ? p-p_wmesg : , p-p_comm); break; Index: sys/proc.h === RCS file: /data/mirror/openbsd/cvs/src/sys/sys/proc.h,v retrieving revision 1.168 diff -u -p -u -p -r1.168 proc.h --- sys/proc.h 6 Jun 2013 13:09:37 - 1.168 +++ sys/proc.h 11 Aug 2013 02:51:13 - @@ -412,12 +412,14 @@ struct proc { #endif #defineP_BITS \ -(\20\02CONTROLT\03INMEM\04SIGPAUSE\05PPWAIT\06PROFIL\07SELECT \ - \010SINTR\011SUGID\012SYSTEM\013TIMEOUT\014TRACED\015WAITED\016WEXIT \ - \017EXEC\020PWEUPC\021ISPWAIT\022COREDUMPING\023SUGIDEXEC\024SUSPSINGLE \ +(\20\01INKTR\02CONTROLT\03INMEM\04SIGSUSPEND \ + \05PPWAIT\06PROFIL\07SELECT\010SINTR \ + \011SUGID\012SYSTEM\013TIMEOUT\014TRACED \ + \015WAITED\016WEXIT\017EXEC\020OWEUPC \ + \021ISPWAIT\022COREDUMP\023SUGIDEXEC\024SUSPSINGLE \ \025NOZOMBIE\026INEXEC\027SYSTRACE\030CONTINUED \ - \031SINGLEEXIT\032SINGLEUNWIND \ - \033THREAD\034SUSPSIG\035SOFTDEP\036STOPPED\037CPUPEG) + \031SINGLEEXIT\032SINGLEUNWIND\033THREAD\034SUSPSIG \ + \035SOFTDEP\036STOPPED\037CPUPEG\040EXITING) /* Macro to compute the exit signal to be delivered. */ #define P_EXITSIG(p) \
carp ifdef inet6
Hi, In the common IPv4 and IPv6 file ip_carp.c an #ifdef INET6 is missing. Especially the IN6_IS_ADDR_LINKLOCAL() macro should not be necessary in IPv4 only code. ok? bluhm Index: netinet/ip_carp.c === RCS file: /data/mirror/openbsd/cvs/src/sys/netinet/ip_carp.c,v retrieving revision 1.209 diff -u -p -u -p -r1.209 ip_carp.c --- netinet/ip_carp.c 20 Jun 2013 12:03:40 - 1.209 +++ netinet/ip_carp.c 11 Aug 2013 18:59:49 - @@ -1969,9 +1969,11 @@ carp_addr_updated(void *v) TAILQ_FOREACH(ifa, sc-sc_if.if_addrlist, ifa_list) { if (ifa-ifa_addr-sa_family == AF_INET) new_naddrs++; +#ifdef INET6 else if (ifa-ifa_addr-sa_family == AF_INET6 !IN6_IS_ADDR_LINKLOCAL(ifatoia6(ifa)-ia_addr.sin6_addr)) new_naddrs6++; +#endif /* INET6 */ } /* We received address changes from if_addrhooks callback */
rtsold ioctl sysctl
Hi, I would like to replace the obsolete ioctl(SIOCGDRLST_IN6) interface with sysctl(net.inet6.icmp6.nd6_drlist) in rtsold. Code copied from ndp. ok? bluhm Index: usr.sbin/rtsold/probe.c === RCS file: /data/mirror/openbsd/cvs/src/usr.sbin/rtsold/probe.c,v retrieving revision 1.13 diff -u -p -u -p -r1.13 probe.c --- usr.sbin/rtsold/probe.c 11 Nov 2009 17:23:16 - 1.13 +++ usr.sbin/rtsold/probe.c 14 Aug 2013 22:30:25 - @@ -34,6 +34,7 @@ #include sys/types.h #include sys/ioctl.h #include sys/socket.h +#include sys/sysctl.h #include sys/uio.h #include sys/queue.h @@ -100,40 +101,51 @@ void defrouter_probe(struct ifinfo *ifinfo) { u_char ntopbuf[INET6_ADDRSTRLEN]; - struct in6_drlist dr; - int s, i; + int mib[] = { CTL_NET, PF_INET6, IPPROTO_ICMPV6, ICMPV6CTL_ND6_DRLIST }; + char *buf; + struct in6_defrouter *p, *ep; + size_t l; int ifindex = ifinfo-sdl-sdl_index; - if ((s = socket(AF_INET6, SOCK_DGRAM, 0)) 0) { - warnmsg(LOG_ERR, __func__, socket: %s, strerror(errno)); + if (!ifindex) + return; + + if (sysctl(mib, sizeof(mib) / sizeof(mib[0]), NULL, l, NULL, 0) 0) { + warnmsg(LOG_ERR, __func__, sysctl(ICMPV6CTL_ND6_DRLIST): %s, + strerror(errno)); return; } - memset(dr, 0, sizeof(dr)); - strlcpy(dr.ifname, lo0, sizeof dr.ifname); /* dummy interface */ - if (ioctl(s, SIOCGDRLST_IN6, (caddr_t)dr) 0) { - warnmsg(LOG_ERR, __func__, ioctl(SIOCGDRLST_IN6): %s, + if (l == 0) + return; + buf = malloc(l); + if (buf == NULL) { + warnmsg(LOG_ERR, __func__, malloc: %s, strerror(errno)); + return; + } + if (sysctl(mib, sizeof(mib) / sizeof(mib[0]), buf, l, NULL, 0) 0) { + warnmsg(LOG_ERR, __func__, sysctl(ICMPV6CTL_ND6_DRLIST): %s, strerror(errno)); - goto closeandend; + free(buf); + return; } - for (i = 0; i DRLSTSIZ dr.defrouter[i].if_index; i++) { - if (ifindex dr.defrouter[i].if_index == ifindex) { + ep = (struct in6_defrouter *)(buf + l); + for (p = (struct in6_defrouter *)buf; p ep; p++) { + if (p-if_index == ifindex) { /* sanity check */ - if (!IN6_IS_ADDR_LINKLOCAL(dr.defrouter[i].rtaddr)) { + if (!IN6_IS_ADDR_LINKLOCAL(p-rtaddr.sin6_addr)) { warnmsg(LOG_ERR, __func__, default router list contains a non-link-local address(%s), inet_ntop(AF_INET6, - dr.defrouter[i].rtaddr, + p-rtaddr.sin6_addr, ntopbuf, INET6_ADDRSTRLEN)); continue; /* ignore the address */ } - sendprobe(dr.defrouter[i].rtaddr, ifinfo); + sendprobe(p-rtaddr.sin6_addr, ifinfo); } } - -closeandend: - close(s); + free(buf); } static void
warnings in arp, rarp, ndp
Hi, I would like to reduce the warnings when arp, rarp, ndp are compiled with WARNINGS=yes. Let's start with this one. warning: declaration of 'time' shadows a global declaration No binary change. ok? bluhm Index: usr.sbin/arp/arp.c === RCS file: /data/mirror/openbsd/cvs/src/usr.sbin/arp/arp.c,v retrieving revision 1.53 diff -u -p -r1.53 arp.c --- usr.sbin/arp/arp.c 20 Jul 2013 18:21:11 - 1.53 +++ usr.sbin/arp/arp.c 14 Aug 2013 23:27:40 - @@ -286,10 +286,10 @@ set(int argc, char *argv[]) doing_proxy = flags = export_only = 0; while (argc-- 0) { if (strncmp(argv[0], temp, 4) == 0) { - struct timeval time; + struct timeval now; - gettimeofday(time, 0); - expire_time = time.tv_sec + 20 * 60; + gettimeofday(now, 0); + expire_time = now.tv_sec + 20 * 60; if (flags RTF_PERMANENT_ARP) { /* temp or permanent, not both */ usage(); Index: usr.sbin/ndp/ndp.c === RCS file: /data/mirror/openbsd/cvs/src/usr.sbin/ndp/ndp.c,v retrieving revision 1.49 diff -u -p -r1.49 ndp.c --- usr.sbin/ndp/ndp.c 9 Aug 2013 17:52:12 - 1.49 +++ usr.sbin/ndp/ndp.c 14 Aug 2013 23:29:52 - @@ -382,10 +382,10 @@ set(int argc, char **argv) flags = 0; while (argc-- 0) { if (strncmp(argv[0], temp, 4) == 0) { - struct timeval time; + struct timeval now; - gettimeofday(time, 0); - expire_time = time.tv_sec + 20 * 60; + gettimeofday(now, 0); + expire_time = now.tv_sec + 20 * 60; } else if (strncmp(argv[0], proxy, 5) == 0) flags |= RTF_ANNOUNCE; argv++; @@ -549,7 +549,7 @@ dump(struct in6_addr *addr, int cflag) struct sockaddr_in6 *sin; struct sockaddr_dl *sdl; struct in6_nbrinfo *nbi; - struct timeval time; + struct timeval now; int addrwidth; int llwidth; int ifwidth; @@ -636,9 +636,9 @@ again:; delete(host_buf); continue; } - gettimeofday(time, 0); + gettimeofday(now, 0); if (tflag) - ts_print(time); + ts_print(now); addrwidth = strlen(host_buf); if (addrwidth W_ADDR) @@ -659,9 +659,9 @@ again:; /* Print neighbor discovery specific informations */ nbi = getnbrinfo(sin-sin6_addr, sdl-sdl_index, 1); if (nbi) { - if (nbi-expire time.tv_sec) { + if (nbi-expire now.tv_sec) { printf( %-9.9s, - sec2str(nbi-expire - time.tv_sec)); + sec2str(nbi-expire - now.tv_sec)); } else if (nbi-expire == 0) printf( %-9.9s, permanent); else @@ -956,7 +956,7 @@ rtrlist(void) char *buf; struct in6_defrouter *p, *ep; size_t l; - struct timeval time; + struct timeval now; if (sysctl(mib, sizeof(mib) / sizeof(mib[0]), NULL, l, NULL, 0) 0) { err(1, sysctl(ICMPV6CTL_ND6_DRLIST)); @@ -991,12 +991,12 @@ rtrlist(void) rtpref = ((p-flags ND_RA_FLAG_RTPREF_MASK) 3) 0xff; printf(, pref=%s, rtpref_str[rtpref]); - gettimeofday(time, 0); + gettimeofday(now, 0); if (p-expire == 0) printf(, expire=Never\n); else printf(, expire=%s\n, - sec2str(p-expire - time.tv_sec)); + sec2str(p-expire - now.tv_sec)); } free(buf); } @@ -1009,7 +1009,7 @@ plist(void) struct in6_prefix *p, *ep, *n; struct sockaddr_in6 *advrtr; size_t l; - struct timeval time; + struct timeval now; const int niflags = NI_NUMERICHOST; int ninflags = nflag ? NI_NUMERICHOST : 0; char namebuf[NI_MAXHOST]; @@ -1040,7 +1040,7 @@ plist(void) printf(%s/%d if=%s\n, namebuf, p-prefixlen, if_indextoname(p-if_index, ifix_buf)); - gettimeofday(time, 0); + gettimeofday(now, 0); /* * meaning of fields, especially flags, is very different * by origin. notify the difference to the users. @@ -1062,9 +1062,9 @@ plist(void)
remove obsolete nd6 ioctls
Hi, After converting the last user of ioctl(SIOCGDRLST_IN6) to sysctl, I would like to remove dead kernel ioctl code. Is it save to just delete this? ok? bluhm Index: netinet6/in6.c === RCS file: /data/mirror/openbsd/cvs/src/sys/netinet6/in6.c,v retrieving revision 1.116 diff -u -p -u -p -r1.116 in6.c --- netinet6/in6.c 20 Jun 2013 12:03:40 - 1.116 +++ netinet6/in6.c 15 Aug 2013 15:06:06 - @@ -361,10 +361,7 @@ in6_control(struct socket *so, u_long cm if (!privileged) return (EPERM); /* FALLTHROUGH */ - case OSIOCGIFINFO_IN6: case SIOCGIFINFO_IN6: - case SIOCGDRLST_IN6: - case SIOCGPRLST_IN6: case SIOCGNBRINFO_IN6: return (nd6_ioctl(cmd, data, ifp)); } Index: netinet6/in6_var.h === RCS file: /data/mirror/openbsd/cvs/src/sys/netinet6/in6_var.h,v retrieving revision 1.40 diff -u -p -u -p -r1.40 in6_var.h --- netinet6/in6_var.h 17 Jun 2013 18:02:24 - 1.40 +++ netinet6/in6_var.h 15 Aug 2013 15:03:46 - @@ -400,11 +400,6 @@ struct in6_rrenumreq { #define SIOCGIFAFLAG_IN6 _IOWR('i', 73, struct in6_ifreq) -#define SIOCGDRLST_IN6 _IOWR('i', 74, struct in6_drlist) -#define SIOCGPRLST_IN6 _IOWR('i', 75, struct in6_prlist) -#ifdef _KERNEL -#define OSIOCGIFINFO_IN6 _IOWR('i', 76, struct in6_ondireq) -#endif #define SIOCGIFINFO_IN6_IOWR('i', 108, struct in6_ndireq) #define SIOCSNDFLUSH_IN6 _IOWR('i', 77, struct in6_ifreq) #define SIOCGNBRINFO_IN6 _IOWR('i', 78, struct in6_nbrinfo) Index: netinet6/nd6.c === RCS file: /data/mirror/openbsd/cvs/src/sys/netinet6/nd6.c,v retrieving revision 1.99 diff -u -p -u -p -r1.99 nd6.c --- netinet6/nd6.c 31 May 2013 15:04:24 - 1.99 +++ netinet6/nd6.c 15 Aug 2013 15:04:50 - @@ -1238,111 +1238,13 @@ nd6_rtrequest(int req, struct rtentry *r int nd6_ioctl(u_long cmd, caddr_t data, struct ifnet *ifp) { - struct in6_drlist *drl = (struct in6_drlist *)data; - struct in6_oprlist *oprl = (struct in6_oprlist *)data; struct in6_ndireq *ndi = (struct in6_ndireq *)data; struct in6_nbrinfo *nbi = (struct in6_nbrinfo *)data; - struct nd_defrouter *dr; - struct nd_prefix *pr; struct rtentry *rt; - int i = 0, error = 0; + int error = 0; int s; switch (cmd) { - case SIOCGDRLST_IN6: - /* -* obsolete API, use sysctl under net.inet6.icmp6 -*/ - bzero(drl, sizeof(*drl)); - s = splsoftnet(); - TAILQ_FOREACH(dr, nd_defrouter, dr_entry) { - if (i = DRLSTSIZ) - break; - drl-defrouter[i].rtaddr = dr-rtaddr; - if (IN6_IS_ADDR_LINKLOCAL(drl-defrouter[i].rtaddr)) { - /* XXX: need to this hack for KAME stack */ - drl-defrouter[i].rtaddr.s6_addr16[1] = 0; - } else - log(LOG_ERR, - default router list contains a - non-linklocal address(%s)\n, - ip6_sprintf(drl-defrouter[i].rtaddr)); - - drl-defrouter[i].flags = dr-flags; - drl-defrouter[i].rtlifetime = dr-rtlifetime; - drl-defrouter[i].expire = dr-expire; - drl-defrouter[i].if_index = dr-ifp-if_index; - i++; - } - splx(s); - break; - case SIOCGPRLST_IN6: - /* -* obsolete API, use sysctl under net.inet6.icmp6 -* -* XXX the structure in6_prlist was changed in backward- -* incompatible manner. in6_oprlist is used for SIOCGPRLST_IN6, -* in6_prlist is used for nd6_sysctl() - fill_prlist(). -*/ - /* -* XXX meaning of fields, especially raflags, is very -* different between RA prefix list and RR/static prefix list. -* how about separating ioctls into two? -*/ - bzero(oprl, sizeof(*oprl)); - s = splsoftnet(); - LIST_FOREACH(pr, nd_prefix, ndpr_entry) { - struct nd_pfxrouter *pfr; - int j; - - if (i = PRLSTSIZ) - break; - oprl-prefix[i].prefix = pr-ndpr_prefix.sin6_addr; - oprl-prefix[i].raflags = pr-ndpr_raf; -
Re: include netinet/in_var.h in arch/dev
On Wed, Aug 07, 2013 at 03:39:59AM +0200, Alexander Bluhm wrote: Hi, I have just removed a bunch of useless include netinet/in_var.h from the machine independent drivers. I suspect that they are also not needed in the architecture specific network drivers. Unfortunately I don't have any of these machines. So if you have access to one of macppc mvme68k octeon sgi sparc vax could you please test if this diff compiles. These architectures are still not tested: mvme68k octeon sgi sparc Could you please compile this diff, if you posses one of these machines? bluhm Index: arch/mvme68k/dev/if_ie.c === RCS file: /data/mirror/openbsd/cvs/src/sys/arch/mvme68k/dev/if_ie.c,v retrieving revision 1.40 diff -u -p -u -p -r1.40 if_ie.c --- arch/mvme68k/dev/if_ie.c10 Oct 2012 04:52:16 - 1.40 +++ arch/mvme68k/dev/if_ie.c16 Aug 2013 23:27:02 - @@ -120,7 +120,6 @@ Mode of operation: #ifdef INET #include netinet/in.h #include netinet/in_systm.h -#include netinet/in_var.h #include netinet/ip.h #include netinet/if_ether.h #endif Index: arch/mvme88k/dev/if_ie.c === RCS file: /data/mirror/openbsd/cvs/src/sys/arch/mvme88k/dev/if_ie.c,v retrieving revision 1.45 diff -u -p -u -p -r1.45 if_ie.c --- arch/mvme88k/dev/if_ie.c10 Oct 2012 04:52:16 - 1.45 +++ arch/mvme88k/dev/if_ie.c16 Aug 2013 23:27:02 - @@ -119,7 +119,6 @@ Mode of operation: #ifdef INET #include netinet/in.h #include netinet/in_systm.h -#include netinet/in_var.h #include netinet/ip.h #include netinet/if_ether.h #endif Index: arch/octeon/dev/if_cnmac.c === RCS file: /data/mirror/openbsd/cvs/src/sys/arch/octeon/dev/if_cnmac.c,v retrieving revision 1.10 diff -u -p -u -p -r1.10 if_cnmac.c --- arch/octeon/dev/if_cnmac.c 12 Apr 2013 15:22:26 - 1.10 +++ arch/octeon/dev/if_cnmac.c 16 Aug 2013 23:27:02 - @@ -66,7 +66,6 @@ #include netinet/in.h #include netinet/in_systm.h -#include netinet/in_var.h #include netinet/ip.h #include machine/bus.h Index: arch/sgi/dev/if_iec.c === RCS file: /data/mirror/openbsd/cvs/src/sys/arch/sgi/dev/if_iec.c,v retrieving revision 1.8 diff -u -p -u -p -r1.8 if_iec.c --- arch/sgi/dev/if_iec.c 22 May 2012 19:24:59 - 1.8 +++ arch/sgi/dev/if_iec.c 16 Aug 2013 23:27:02 - @@ -101,7 +101,6 @@ #ifdef INET #include netinet/in.h #include netinet/in_systm.h -#include netinet/in_var.h #include netinet/ip.h #endif Index: arch/sgi/dev/if_mec.c === RCS file: /data/mirror/openbsd/cvs/src/sys/arch/sgi/dev/if_mec.c,v retrieving revision 1.25 diff -u -p -u -p -r1.25 if_mec.c --- arch/sgi/dev/if_mec.c 3 Oct 2012 22:46:09 - 1.25 +++ arch/sgi/dev/if_mec.c 16 Aug 2013 23:27:02 - @@ -85,7 +85,6 @@ #ifdef INET #include netinet/in.h #include netinet/in_systm.h -#include netinet/in_var.h #include netinet/ip.h #endif Index: arch/sgi/hpc/if_sq.c === RCS file: /data/mirror/openbsd/cvs/src/sys/arch/sgi/hpc/if_sq.c,v retrieving revision 1.8 diff -u -p -u -p -r1.8 if_sq.c --- arch/sgi/hpc/if_sq.c28 May 2012 17:03:35 - 1.8 +++ arch/sgi/hpc/if_sq.c16 Aug 2013 23:27:02 - @@ -57,7 +57,6 @@ #ifdef INET #include netinet/in.h #include netinet/in_systm.h -#include netinet/in_var.h #include netinet/ip.h #endif Index: arch/sparc/dev/be.c === RCS file: /data/mirror/openbsd/cvs/src/sys/arch/sparc/dev/be.c,v retrieving revision 1.43 diff -u -p -u -p -r1.43 be.c --- arch/sparc/dev/be.c 28 Nov 2008 02:44:17 - 1.43 +++ arch/sparc/dev/be.c 16 Aug 2013 23:27:02 - @@ -46,7 +46,6 @@ #ifdef INET #include netinet/in.h #include netinet/in_systm.h -#include netinet/in_var.h #include netinet/ip.h #include netinet/if_ether.h #endif Index: arch/sparc/dev/hme.c === RCS file: /data/mirror/openbsd/cvs/src/sys/arch/sparc/dev/hme.c,v retrieving revision 1.62 diff -u -p -u -p -r1.62 hme.c --- arch/sparc/dev/hme.c13 Aug 2009 17:01:31 - 1.62 +++ arch/sparc/dev/hme.c16 Aug 2013 23:27:02 - @@ -59,7 +59,6 @@ #ifdef INET #include netinet/in.h #include netinet/in_systm.h -#include netinet/in_var.h #include netinet/ip.h #include netinet/if_ether.h #include netinet/tcp.h Index: arch/sparc/dev/if_gem_sbus.c === RCS file: /data/mirror/openbsd/cvs/src/sys/arch/sparc/dev/if_gem_sbus.c,v retrieving revision 1.1 diff -u -p -u -p -r1.1 if_gem_sbus.c --- arch/sparc/dev/if_gem_sbus.c13 Jul 2009 19:53:58
Re: Don't iterate on the global list in arp_{request,input}
On Wed, Aug 28, 2013 at 03:28:18PM +0200, Martin Pieuchot wrote: Like the previous diffs, when we already have the ifp and want one of its addresses, iterate on the ifp list instead of the global one. Tested with carp here. I appreciate any comment and oks. I think the code is nicer and does the same. OK bluhm@ Index: netinet/if_ether.c === RCS file: /cvs/src/sys/netinet/if_ether.c,v retrieving revision 1.105 diff -u -p -r1.105 if_ether.c --- netinet/if_ether.c28 Aug 2013 06:58:57 - 1.105 +++ netinet/if_ether.c28 Aug 2013 07:57:01 - @@ -145,7 +145,6 @@ arp_rtrequest(int req, struct rtentry *r { struct sockaddr *gate = rt-rt_gateway; struct llinfo_arp *la = (struct llinfo_arp *)rt-rt_llinfo; - struct in_ifaddr *ia; struct ifaddr *ifa; struct mbuf *m; @@ -259,13 +258,13 @@ arp_rtrequest(int req, struct rtentry *r rt-rt_flags |= RTF_LLINFO; LIST_INSERT_HEAD(llinfo_arp, la, la_list); - TAILQ_FOREACH(ia, in_ifaddr, ia_list) { - if (ia-ia_ifp == rt-rt_ifp - SIN(rt_key(rt))-sin_addr.s_addr == - (IA_SIN(ia))-sin_addr.s_addr) + TAILQ_FOREACH(ifa, rt-rt_ifp-if_addrlist, ifa_list) { + if ((ifa-ifa_addr-sa_family == AF_INET) + ifatoia(ifa)-ia_addr.sin_addr.s_addr == + satosin(rt_key(rt))-sin_addr.s_addr) break; } - if (ia) { + if (ifa) { /* * This test used to be * if (lo0ifp-if_flags IFF_UP) @@ -294,7 +293,6 @@ arp_rtrequest(int req, struct rtentry *r * address we are using, otherwise we will have trouble * with source address selection. */ - ifa = ia-ia_ifa; if (ifa != rt-rt_ifa) { ifafree(rt-rt_ifa); ifa-ifa_refcnt++; @@ -562,11 +560,12 @@ void in_arpinput(struct mbuf *m) { struct ether_arp *ea; - struct arpcom *ac = (struct arpcom *)m-m_pkthdr.rcvif; + struct ifnet *ifp = m-m_pkthdr.rcvif; + struct arpcom *ac = (struct arpcom *)ifp; struct ether_header *eh; struct llinfo_arp *la = 0; struct rtentry *rt; - struct in_ifaddr *ia; + struct ifaddr *ifa; struct sockaddr_dl *sdl; struct sockaddr sa; struct in_addr isaddr, itaddr, myaddr; @@ -593,57 +592,55 @@ in_arpinput(struct mbuf *m) bcopy((caddr_t)ea-arp_spa, (caddr_t)isaddr, sizeof(isaddr)); /* First try: check target against our addresses */ - TAILQ_FOREACH(ia, in_ifaddr, ia_list) { - if (itaddr.s_addr != ia-ia_addr.sin_addr.s_addr) + TAILQ_FOREACH(ifa, ifp-if_addrlist, ifa_list) { + if (ifa-ifa_addr-sa_family != AF_INET) + continue; + + if (itaddr.s_addr != ifatoia(ifa)-ia_addr.sin_addr.s_addr) continue; #if NCARP 0 - if (ia-ia_ifp-if_type == IFT_CARP - ((ia-ia_ifp-if_flags (IFF_UP|IFF_RUNNING)) == + if (ifp-if_type == IFT_CARP + ((ifp-if_flags (IFF_UP|IFF_RUNNING)) == (IFF_UP|IFF_RUNNING))) { - if (ia-ia_ifp == m-m_pkthdr.rcvif) { - if (op == ARPOP_REPLY) - break; - if (carp_iamatch(ia, ea-arp_sha, - enaddr, ether_shost)) - break; - else - goto out; - } - } else -#endif - if (ia-ia_ifp == m-m_pkthdr.rcvif) + if (op == ARPOP_REPLY) + break; + if (carp_iamatch(ifatoia(ifa), ea-arp_sha, + enaddr, ether_shost)) break; + else + goto out; + } +#endif + break; } /* Second try: check source against our addresses */ - if (ia == NULL) { - TAILQ_FOREACH(ia, in_ifaddr, ia_list) { - if (isaddr.s_addr != ia-ia_addr.sin_addr.s_addr) + if (ifa == NULL) { + TAILQ_FOREACH(ifa, ifp-if_addrlist, ifa_list) { + if (ifa-ifa_addr-sa_family != AF_INET) continue; - if (ia-ia_ifp == m-m_pkthdr.rcvif) + + if (isaddr.s_addr == +
in_var.h incudes in6_var.h
Hi, The file netinet/in_var.h includes netinet6/in6_var.h. This creates a bunch of useless dependencies. For an upcomming change in in6_var.h I would like to split that up. Is this a good idea? comments/ok? Note that netinet/in.h includes netinet6/in6.h, but that is required by RFC. The important part of my diff is in sys/netinet/in_var.h: -/* INET6 stuff */ -#include netinet6/in6_var.h bluhm Index: sbin/ifconfig/ifconfig.c === RCS file: /data/mirror/openbsd/cvs/src/sbin/ifconfig/ifconfig.c,v retrieving revision 1.269 diff -u -p -u -p -r1.269 ifconfig.c --- sbin/ifconfig/ifconfig.c19 Aug 2013 11:20:57 - 1.269 +++ sbin/ifconfig/ifconfig.c27 Aug 2013 22:40:10 - @@ -70,6 +70,7 @@ #include net/if_types.h #include netinet/in.h #include netinet/in_var.h +#include netinet6/in6_var.h #include netinet6/nd6.h #include arpa/inet.h #include netinet/ip_ipsp.h Index: sys/net/bridgestp.c === RCS file: /data/mirror/openbsd/cvs/src/sys/net/bridgestp.c,v retrieving revision 1.44 diff -u -p -u -p -r1.44 bridgestp.c --- sys/net/bridgestp.c 20 Jun 2013 12:03:40 - 1.44 +++ sys/net/bridgestp.c 27 Aug 2013 22:27:28 - @@ -60,7 +60,6 @@ __FBSDID($FreeBSD: /repoman/r/ncvs/src/ #ifdef INET #include netinet/in.h #include netinet/in_systm.h -#include netinet/in_var.h #include netinet/ip.h #include netinet/if_ether.h #endif Index: sys/net/if.c === RCS file: /data/mirror/openbsd/cvs/src/sys/net/if.c,v retrieving revision 1.264 diff -u -p -u -p -r1.264 if.c --- sys/net/if.c28 Aug 2013 07:38:50 - 1.264 +++ sys/net/if.c29 Aug 2013 20:49:43 - @@ -103,6 +103,7 @@ #ifndef INET #include netinet/in.h #endif +#include netinet6/in6_var.h #include netinet6/in6_ifattach.h #include netinet6/nd6.h #include netinet/ip6.h Index: sys/net/if_bridge.c === RCS file: /data/mirror/openbsd/cvs/src/sys/net/if_bridge.c,v retrieving revision 1.214 diff -u -p -u -p -r1.214 if_bridge.c --- sys/net/if_bridge.c 21 Aug 2013 13:53:48 - 1.214 +++ sys/net/if_bridge.c 27 Aug 2013 22:27:28 - @@ -71,6 +71,7 @@ #endif #ifdef INET6 +#include netinet6/in6_var.h #include netinet/ip6.h #include netinet6/ip6_var.h #endif Index: sys/net/if_fddisubr.c === RCS file: /data/mirror/openbsd/cvs/src/sys/net/if_fddisubr.c,v retrieving revision 1.61 diff -u -p -u -p -r1.61 if_fddisubr.c --- sys/net/if_fddisubr.c 28 Mar 2013 16:55:27 - 1.61 +++ sys/net/if_fddisubr.c 27 Aug 2013 22:27:28 - @@ -103,8 +103,8 @@ #ifdef INET6 #ifndef INET #include netinet/in.h -#include netinet/in_var.h #endif +#include netinet6/in6_var.h #include netinet6/nd6.h #endif Index: sys/net/if_gif.c === RCS file: /data/mirror/openbsd/cvs/src/sys/net/if_gif.c,v retrieving revision 1.62 diff -u -p -u -p -r1.62 if_gif.c --- sys/net/if_gif.c17 Jun 2013 18:19:44 - 1.62 +++ sys/net/if_gif.c27 Aug 2013 22:27:28 - @@ -57,6 +57,7 @@ #ifndef INET #include netinet/in.h #endif +#include netinet6/in6_var.h #include netinet/ip6.h #include netinet6/ip6_var.h #include netinet6/in6_gif.h Index: sys/net/if_gre.c === RCS file: /data/mirror/openbsd/cvs/src/sys/net/if_gre.c,v retrieving revision 1.62 diff -u -p -u -p -r1.62 if_gre.c --- sys/net/if_gre.c5 Jun 2013 15:17:40 - 1.62 +++ sys/net/if_gre.c27 Aug 2013 22:27:28 - @@ -60,7 +60,6 @@ #ifdef INET #include netinet/in.h #include netinet/in_systm.h -#include netinet/in_var.h #include netinet/ip.h #include netinet/ip_var.h #include netinet/if_ether.h Index: sys/net/if_mpe.c === RCS file: /data/mirror/openbsd/cvs/src/sys/net/if_mpe.c,v retrieving revision 1.29 diff -u -p -u -p -r1.29 if_mpe.c --- sys/net/if_mpe.c28 Mar 2013 16:45:16 - 1.29 +++ sys/net/if_mpe.c27 Aug 2013 22:27:28 - @@ -37,6 +37,7 @@ #endif #ifdef INET6 +#include netinet6/in6_var.h #include netinet/ip6.h #ifndef INET #include netinet/in.h Index: sys/net/if_pflog.c === RCS file: /data/mirror/openbsd/cvs/src/sys/net/if_pflog.c,v retrieving revision 1.54 diff -u -p -u -p -r1.54 if_pflog.c --- sys/net/if_pflog.c 26 Jun 2013 09:12:39 - 1.54 +++ sys/net/if_pflog.c 27 Aug 2013 22:27:28 - @@ -63,6 +63,7 @@ #ifndef INET #include netinet/in.h #endif +#include netinet6/in6_var.h #include netinet/ip6.h #include netinet6/nd6.h #include netinet/icmp6.h Index: sys/net/if_pflow.c
Re: Do not reroll IFP_TO_IA
On Thu, Sep 05, 2013 at 10:54:53AM +0200, Martin Pieuchot wrote: Diff below makes use of IFP_TO_IA() instead of rolling our own copy. For now there's no functional change, but I'd like to get this in so that once our multicast code can stop relying on global lists, we only need to modify the macro. ok? The old code did run into the EADDRNOTAVAIL case, if the routing domain did not match. Now you don't return. I think you need someting like this; ifp = mopts-imo_multicast_ifp; if (ifp != NULL) { IFP_TO_IA(ifp, ia); if (ia == NULL || ifp-if_rdomain != rtable_l2(rtableid)) { *errorp = EADDRNOTAVAIL; return NULL; } bluhm Index: netinet/in_pcb.c === RCS file: /home/ncvs/src/sys/netinet/in_pcb.c,v retrieving revision 1.139 diff -u -p -r1.139 in_pcb.c --- netinet/in_pcb.c 1 Jun 2013 13:25:40 - 1.139 +++ netinet/in_pcb.c 5 Sep 2013 08:52:10 - @@ -794,13 +794,10 @@ in_selectsrc(struct sockaddr_in *sin, st if (IN_MULTICAST(sin-sin_addr.s_addr) mopts != NULL) { struct ifnet *ifp; - if (mopts-imo_multicast_ifp != NULL) { - ifp = mopts-imo_multicast_ifp; - TAILQ_FOREACH(ia, in_ifaddr, ia_list) - if (ia-ia_ifp == ifp - rtable_l2(rtableid) == ifp-if_rdomain) - break; - if (ia == 0) { + ifp = mopts-imo_multicast_ifp; + if (ifp != NULL ifp-if_rdomain == rtable_l2(rtableid)) { + IFP_TO_IA(ifp, ia); + if (ia == NULL) { *errorp = EADDRNOTAVAIL; return NULL; }
Re: Introduce rt_msg() (was nd6_rtmsg)
On Mon, Sep 02, 2013 at 12:43:51PM +0200, Martin Pieuchot wrote: Diff below is just a small refactoring of two similar code chunks to inform user processes that something changed regarding a route. I'd like to get this in because it removes one use of rt_addrinfo in netinet6. There's no functional change, ok? Less code is always good. OK bluhm@ Index: net/route.c === RCS file: /home/ncvs/src/sys/net/route.c,v retrieving revision 1.145 diff -u -p -r1.145 route.c --- net/route.c 28 Aug 2013 06:58:57 - 1.145 +++ net/route.c 2 Sep 2013 10:18:59 - @@ -346,17 +345,7 @@ rtalloc1(struct sockaddr *dst, int flags goto miss; } /* Inform listeners of the new route */ - bzero(info, sizeof(info)); - info.rti_info[RTAX_DST] = rt_key(rt); - info.rti_info[RTAX_NETMASK] = rt_mask(rt); - info.rti_info[RTAX_GATEWAY] = rt-rt_gateway; - if (rt-rt_ifp != NULL) { - info.rti_info[RTAX_IFP] = - TAILQ_FIRST(rt-rt_ifp-if_addrlist)-ifa_addr; - info.rti_info[RTAX_IFA] = rt-rt_ifa-ifa_addr; - } - rt_missmsg(RTM_ADD, info, rt-rt_flags, - rt-rt_ifp, 0, tableid); + rt_msg(rt, RTM_ADD, tableid); } else rt-rt_refcnt++; } else { @@ -410,6 +399,25 @@ rtfree(struct rtentry *rt) Free(rt_key(rt)); pool_put(rtentry_pool, rt); } +} + +/* tell the change to user processes watching the routing socket. */ +void +rt_msg(struct rtentry *rt, int cmd, u_int tableid) +{ + struct rt_addrinfo info; + + bzero(info, sizeof(info)); + info.rti_info[RTAX_DST] = rt_key(rt); + info.rti_info[RTAX_GATEWAY] = rt-rt_gateway; + info.rti_info[RTAX_NETMASK] = rt_mask(rt); + if (rt-rt_ifp != NULL) { + info.rti_info[RTAX_IFP] = + TAILQ_FIRST(rt-rt_ifp-if_addrlist)-ifa_addr; + info.rti_info[RTAX_IFA] = rt-rt_ifa-ifa_addr; + } + + rt_missmsg(cmd, info, rt-rt_flags, rt-rt_ifp, 0, tableid); } void Index: net/route.h === RCS file: /home/ncvs/src/sys/net/route.h,v retrieving revision 1.78 diff -u -p -r1.78 route.h --- net/route.h 19 Sep 2012 16:14:01 - 1.78 +++ net/route.h 2 Sep 2013 10:18:59 - @@ -369,6 +369,7 @@ void rt_ifmsg(struct ifnet *); void rt_ifannouncemsg(struct ifnet *, int); void rt_maskedcopy(struct sockaddr *, struct sockaddr *, struct sockaddr *); +void rt_msg(struct rtentry *, int, u_int); void rt_missmsg(int, struct rt_addrinfo *, int, struct ifnet *, int, u_int); void rt_newaddrmsg(int, struct ifaddr *, int, struct rtentry *); Index: netinet6/nd6_rtr.c === RCS file: /home/ncvs/src/sys/netinet6/nd6_rtr.c,v retrieving revision 1.72 diff -u -p -r1.72 nd6_rtr.c --- netinet6/nd6_rtr.c1 Jul 2013 14:22:20 - 1.72 +++ netinet6/nd6_rtr.c2 Sep 2013 10:18:59 - @@ -70,7 +70,6 @@ void pfxrtr_add(struct nd_prefix *, stru void pfxrtr_del(struct nd_pfxrouter *); struct nd_pfxrouter *find_pfxlist_reachable_router(struct nd_prefix *); void defrouter_delreq(struct nd_defrouter *); -void nd6_rtmsg(int, struct rtentry *); void purge_detached(struct ifnet *); void in6_init_address_ltimes(struct nd_prefix *, struct in6_addrlifetime *); @@ -410,26 +409,6 @@ nd6_ra_input(struct mbuf *m, int off, in /* * default router list processing sub routines */ - -/* tell the change to user processes watching the routing socket. */ -void -nd6_rtmsg(int cmd, struct rtentry *rt) -{ - struct rt_addrinfo info; - - bzero((caddr_t)info, sizeof(info)); - info.rti_info[RTAX_DST] = rt_key(rt); - info.rti_info[RTAX_GATEWAY] = rt-rt_gateway; - info.rti_info[RTAX_NETMASK] = rt_mask(rt); - if (rt-rt_ifp) { - info.rti_info[RTAX_IFP] = - TAILQ_FIRST(rt-rt_ifp-if_addrlist)-ifa_addr; - info.rti_info[RTAX_IFA] = rt-rt_ifa-ifa_addr; - } - - rt_missmsg(cmd, info, rt-rt_flags, rt-rt_ifp, 0, 0); -} - void defrouter_addreq(struct nd_defrouter *new) { @@ -459,7 +438,7 @@ defrouter_addreq(struct nd_defrouter *ne error = rtrequest1(RTM_ADD, info, RTP_DEFAULT, newrt, new-ifp-if_rdomain); if (newrt) { - nd6_rtmsg(RTM_ADD, newrt); /* tell user process */ + rt_msg(newrt, RTM_ADD, 0); /* tell user process */ newrt-rt_refcnt--; } if (error == 0) @@
kassert socket, inpcb, tcpcb
Hi, I have a core dump from a not quite OpenBSD 5.2 crash. There the pointers to socket, inpcb, tcpcb on the stack of tcp_input() and tcp_output() look very inconsistent. Especially the so-so_pcb is NULL, which can only happen after the inp has been detached. The whole thing reminds me of the old panic: pool_do_get(inpcbpl): free list modified. http://marc.info/?l=openbsd-bugsm=132630237316970w=2 To get more information, I would like to add some asserts that guarantee the consistency of the socket, inpcb, tcpcb linking. I suspect that we might have a freed inp stored in the pcbhashes. ok? bluhm Index: netinet/tcp_input.c === RCS file: /data/mirror/openbsd/cvs/src/sys/netinet/tcp_input.c,v retrieving revision 1.267 diff -u -p -u -p -r1.267 tcp_input.c --- netinet/tcp_input.c 13 Aug 2013 09:52:53 - 1.267 +++ netinet/tcp_input.c 5 Sep 2013 21:20:22 - @@ -641,6 +641,8 @@ findpcb: goto dropwithreset_ratelim; } } + KASSERT(sotoinpcb(inp-inp_socket) == inp); + KASSERT(intotcpcb(inp)-t_inpcb == inp); /* Check the minimum TTL for socket. */ if (inp-inp_ip_minttl inp-inp_ip_minttl ip-ip_ttl) Index: netinet/udp_usrreq.c === RCS file: /data/mirror/openbsd/cvs/src/sys/netinet/udp_usrreq.c,v retrieving revision 1.165 diff -u -p -u -p -r1.165 udp_usrreq.c --- netinet/udp_usrreq.c31 Jul 2013 15:41:52 - 1.165 +++ netinet/udp_usrreq.c5 Sep 2013 21:20:50 - @@ -592,6 +592,7 @@ udp_input(struct mbuf *m, ...) return; } } + KASSERT(sotoinpcb(inp-inp_socket) == inp); #if NPF 0 /* The statekey has finished finding the inp, it is no longer needed. */
Re: Do not reroll IFP_TO_IA
On Fri, Sep 06, 2013 at 11:02:14AM +0200, Martin Pieuchot wrote: On 05/09/13(Thu) 19:28, Alexander Bluhm wrote: On Thu, Sep 05, 2013 at 10:54:53AM +0200, Martin Pieuchot wrote: Diff below makes use of IFP_TO_IA() instead of rolling our own copy. For now there's no functional change, but I'd like to get this in so that once our multicast code can stop relying on global lists, we only need to modify the macro. ok? The old code did run into the EADDRNOTAVAIL case, if the routing domain did not match. Now you don't return. I think you need someting like this; ifp = mopts-imo_multicast_ifp; if (ifp != NULL) { IFP_TO_IA(ifp, ia); if (ia == NULL || ifp-if_rdomain != rtable_l2(rtableid)) { *errorp = EADDRNOTAVAIL; return NULL; } You're right. That means we can have a non-NULL ia only if the routing domain match. So I propose this: OK bluhm@ Index: in_pcb.c === RCS file: /home/ncvs/src/sys/netinet/in_pcb.c,v retrieving revision 1.139 diff -u -p -r1.139 in_pcb.c --- in_pcb.c 1 Jun 2013 13:25:40 - 1.139 +++ in_pcb.c 6 Sep 2013 09:00:05 - @@ -794,13 +794,12 @@ in_selectsrc(struct sockaddr_in *sin, st if (IN_MULTICAST(sin-sin_addr.s_addr) mopts != NULL) { struct ifnet *ifp; - if (mopts-imo_multicast_ifp != NULL) { - ifp = mopts-imo_multicast_ifp; - TAILQ_FOREACH(ia, in_ifaddr, ia_list) - if (ia-ia_ifp == ifp - rtable_l2(rtableid) == ifp-if_rdomain) - break; - if (ia == 0) { + ifp = mopts-imo_multicast_ifp; + if (ifp != NULL) { + if (ifp-if_rdomain == rtable_l2(rtableid)) + IFP_TO_IA(ifp, ia); + + if (ia == NULL) { *errorp = EADDRNOTAVAIL; return NULL; }
pf IPv6 atomic fragments
Hi, IPv6 atomic fragments must not go the reassembly queue. I have implemented this for the stack, but somehow forgot it for pf. With this diff, pf steps over an atomic fragment header and handles the packet like an unfragmented. ok? bluhm Index: net/pf.c === RCS file: /data/mirror/openbsd/cvs/src/sys/net/pf.c,v retrieving revision 1.839 diff -u -p -u -p -r1.839 pf.c --- net/pf.c19 Aug 2013 09:16:25 - 1.839 +++ net/pf.c6 Sep 2013 21:01:24 - @@ -6000,7 +6000,7 @@ pf_walk_header6(struct pf_pdesc *pd, str struct ip6_ext ext; struct ip6_rthdr rthdr; u_int32_tend; - int rthdr_cnt = 0; + int fraghdr_cnt = 0, rthdr_cnt = 0; pd-off += sizeof(struct ip6_hdr); end = pd-off + ntohs(h-ip6_plen); @@ -6009,7 +6009,7 @@ pf_walk_header6(struct pf_pdesc *pd, str for (;;) { switch (pd-proto) { case IPPROTO_FRAGMENT: - if (pd-fragoff != 0) { + if (fraghdr_cnt++) { DPFPRINTF(LOG_NOTICE, IPv6 multiple fragment); REASON_SET(reason, PFRES_FRAG); return (PF_DROP); @@ -6025,10 +6025,14 @@ pf_walk_header6(struct pf_pdesc *pd, str DPFPRINTF(LOG_NOTICE, IPv6 short fragment); return (PF_DROP); } - pd-fragoff = pd-off; /* stop walking over non initial fragments */ - if (ntohs((frag.ip6f_offlg IP6F_OFF_MASK)) != 0) + if (ntohs((frag.ip6f_offlg IP6F_OFF_MASK)) != 0) { + pd-fragoff = pd-off; return (PF_PASS); + } + /* RFC6946: reassemble only non atomic fragments */ + if (frag.ip6f_offlg IP6F_MORE_FRAG) + pd-fragoff = pd-off; pd-off += sizeof(frag); pd-proto = frag.ip6f_nxt; break;
Re: enc interface errno
On Fri, Sep 27, 2013 at 12:00:40PM -0400, Kenneth R Westerback wrote: I'm not sure what the 'rule' is regarding ENOMEM and ENOBUFS, but ENOMEN seems more appropriate to me. man 2 errno 12 ENOMEM Cannot allocate memory. The new process image required more memory than was allowed by the hardware or by system-imposed memory management constraints. A lack of swap space is normally temporary; however, a lack of core is not. Soft limits may be increased to their corresponding hard limits. 55 ENOBUFS No buffer space available. An operation on a socket or pipe was not performed because the system lacked sufficient buffer space or because a queue was full. According to this, ENOMEM looks very much like memory allocation failure for the user space. In my case we ran out of network device memory, so I think ENOBUFS is more appropriate. The kernel code is not very consistent there. Developers are tempted to use ENOMEM when malloc(9) fails, but the man page says something different. bluhm
Re: openbsd ioctl fix (in6.c)
On Wed, Sep 18, 2013 at 12:01:10AM -0700, Loganaden Velvindron wrote: Index: in6.c === RCS file: /cvs/src/sys/netinet6/in6.c,v retrieving revision 1.118 diff -u -p -r1.118 in6.c --- in6.c 26 Aug 2013 07:15:58 - 1.118 +++ in6.c 18 Sep 2013 06:54:13 - @@ -426,8 +426,11 @@ in6_control(struct socket *so, u_long cm sa6 = ifr-ifr_addr; break; case SIOCSIFADDR: + case SIOCSIFDSTADDR: + case SIOCSIFBRDADDR: + case SIOCSIFNETMASK: /* -* Do not pass this ioctl to driver handler since it is not +* Do not pass those ioctl to driver handler since they are not * properly setup. Instead just error out. */ return (EOPNOTSUPP); This diff uses spaces instead of tabs. Please use tabs to make diffs apply cleanly. The errno EAFNOSUPPORT Address family not supported by protocol family is more specific for that error, at least if_ppp and if_sl use that. anyway, code is correct, OK bluhm@
Re: udp6 fix for possible memory corruption
On Fri, Aug 23, 2013 at 12:47:10PM -0700, Loganaden Velvindron wrote: Hi, From NetBSD: http://cvsweb.netbsd.org/bsdweb.cgi/src/sys/netinet6/udp6_output.c?rev=1.41content-type=text/x-cvsweb-markuponly_with_tag=MAIN Under some circumstances, udp6_output() would call ip6_clearpktopts() with an uninitialized struct ip6_pktopts on the stack, opt. ip6_clearpktopts(opt, ...) could dereference dangling pointers, leading to memory corruption or a crash. Now, udp6_output() calls ip6_clearpktopts(opt, ...) only if opt was initialized. Thanks to Clement LECIGNE for reporting this bug. I checked openbsd source code and it seems that the issue is present as well. Yes, the release path looks wrong. OK bluhm@ Tentative diff: Index: udp6_output.c === RCS file: /cvs/src/sys/netinet6/udp6_output.c,v retrieving revision 1.19 diff -u -p -r1.19 udp6_output.c --- udp6_output.c 28 Mar 2013 16:45:16 - 1.19 +++ udp6_output.c 23 Aug 2013 19:30:36 - @@ -119,7 +119,8 @@ udp6_output(struct in6pcb *in6p, struct struct in6_addr *laddr, *faddr; u_short fport; int error = 0; - struct ip6_pktopts *optp, opt; + struct ip6_pktopts *optp = NULL; + struct ip6_pktopts opt; int priv; int af, hlen; int flags; @@ -284,7 +285,8 @@ release: releaseopt: if (control) { - ip6_clearpktopts(opt, -1); + if (optp == opt) + ip6_clearpktopts(opt, -1); m_freem(control); } return (error);
routing message crash
Hi, By passing invalid rtm_flags and rtm_addrs values in the routing message, I can crash the kernel from user land. login: uvm_fault(0xfe800554b388, 0x4, 0, 1) - e fatal page fault in supervisor mode trap type 6 code 0 rip 812312d7 cs 8 rflags 246 cr2 4 cpl 5 rsp 839de8a0 panic: trap type 6, code=0, pc=812312d7 Starting stack trace... panic() at panic+0xfb trap() at trap+0x710 --- trap (number 6) --- arp_rtrequest() at arp_rtrequest+0xc7 rtrequest1() at rtrequest1+0x56d route_output() at route_output+0x815 raw_usrreq() at raw_usrreq+0x227 route_usrreq() at route_usrreq+0x6e sosend() at sosend+0x466 dofilewritev() at dofilewritev+0x18b sys_write() at sys_write+0x8f syscall() at syscall+0x162 --- syscall (number 4) --- end of kernel end trace frame: 0x8439e0, count: 246 acpi_pdirpa+0x400a0a: End of stack trace. This diff prevents the crash. ok? bluhm Index: netinet/if_ether.c === RCS file: /data/mirror/openbsd/cvs/src/sys/netinet/if_ether.c,v retrieving revision 1.107 diff -u -p -u -p -r1.107 if_ether.c --- netinet/if_ether.c 3 Sep 2013 10:25:32 - 1.107 +++ netinet/if_ether.c 14 Oct 2013 13:09:40 - @@ -191,7 +191,7 @@ arp_rtrequest(int req, struct rtentry *r * such as older version of routed or gated might provide, * restore cloning bit. */ - if ((rt-rt_flags RTF_HOST) == 0 + if ((rt-rt_flags RTF_HOST) == 0 rt_mask(rt) satosin(rt_mask(rt))-sin_addr.s_addr != 0x) rt-rt_flags |= RTF_CLONING; if (rt-rt_flags RTF_CLONING) {
Re: routing message crash
On Mon, Oct 14, 2013 at 05:50:26PM +0200, Claudio Jeker wrote: Ugh, that is horrible code that works around broken userland daemons. Diff is OK but I would like to remove this check in the long run. What do you think? I have commited my quick fix. The comment speaks about older version of routed or gated. Better fix these daemons if the bug still exists there. If a daemons wants a cloning route, it should set the flag. Especially ospf6d does it that way. The comment is from 1992 http://svnweb.freebsd.org/csrg/sys/netinet/if_ether.c?r1=54715r2=54716; The code was commited in 1991 here http://svnweb.freebsd.org/csrg/sys/netinet/if_ether.c?r1=51993r2=51994; Revision 51994 - (show annotations) (download) Tue Dec 17 16:05:05 1991 UTC (21 years, 10 months ago) by sklower File MIME type: text/plain File size: 14908 byte(s) enforce cloning bit for route to interface if ((rt-rt_flags RTF_HOST) == 0) /* Route to IF? XXX*/ rt-rt_flags |= RTF_CLONING; bluhm
sbin/route 64 bit expire time
Hi, Prepare the route command for using 64 bit route expire time and fix the relative expire time calculations. ok? bluhm Index: sbin/route/route.c === RCS file: /data/mirror/openbsd/cvs/src/sbin/route/route.c,v retrieving revision 1.163 diff -u -p -u -p -r1.163 route.c --- sbin/route/route.c 19 Jul 2013 20:10:23 - 1.163 +++ sbin/route/route.c 28 Sep 2013 22:46:01 - @@ -362,17 +362,23 @@ flushroutes(int argc, char **argv) void set_metric(char *value, int key) { - int flag = 0; - u_int noval, *valp = noval; + long long relative_expire; const char *errstr; + int flag = 0; switch (key) { case K_MTU: - valp = rt_metrics.rmx_mtu; + rt_metrics.rmx_mtu = strtonum(value, 0, UINT_MAX, errstr); + if (errstr) + errx(1, set_metric mtu: %s is %s, value, errstr); flag = RTV_MTU; break; case K_EXPIRE: - valp = rt_metrics.rmx_expire; + relative_expire = strtonum(value, 0, INT_MAX, errstr); + if (errstr) + errx(1, set_metric expire: %s is %s, value, errstr); + rt_metrics.rmx_expire = relative_expire ? + relative_expire + time(NULL) : 0; flag = RTV_EXPIRE; break; case K_HOPCOUNT: @@ -391,9 +397,6 @@ set_metric(char *value, int key) rt_metrics.rmx_locks |= flag; if (locking) locking = 0; - *valp = strtonum(value, 0, UINT_MAX, errstr); - if (errstr) - errx(1, set_metric: %s is %s, value, errstr); } int @@ -1274,6 +1277,7 @@ get_linkstate(int mt, int link_state) void print_rtmsg(struct rt_msghdr *rtm, int msglen) { + long long relative_expire; struct if_msghdr *ifm; struct ifa_msghdr *ifam; struct if_announcemsghdr *ifan; @@ -1340,12 +1344,12 @@ print_rtmsg(struct rt_msghdr *rtm, int m bprintf(stdout, rtm-rtm_flags, routeflags); if (verbose) { #define lock(f)((rtm-rtm_rmx.rmx_locks __CONCAT(RTV_,f)) ? 'L' : ' ') - if (rtm-rtm_rmx.rmx_expire) - rtm-rtm_rmx.rmx_expire -= time(NULL); - printf(\nuse: %8llu mtu: %8u%c expire: %8d%c, + relative_expire = rtm-rtm_rmx.rmx_expire ? + rtm-rtm_rmx.rmx_expire - time(NULL) : 0; + printf(\nuse: %8llu mtu: %8u%c expire: %8lld%c, rtm-rtm_rmx.rmx_pksent, rtm-rtm_rmx.rmx_mtu, lock(MTU), - rtm-rtm_rmx.rmx_expire, lock(EXPIRE)); + relative_expire, lock(EXPIRE)); #undef lock } pmsg_common(rtm); @@ -1380,6 +1384,7 @@ priorityname(u_int8_t prio) void print_getmsg(struct rt_msghdr *rtm, int msglen) { + long long relative_expire; struct sockaddr *dst = NULL, *gate = NULL, *mask = NULL, *ifa = NULL; struct sockaddr_dl *ifp = NULL; struct sockaddr_rtlabel *sa_rl = NULL; @@ -1465,12 +1470,13 @@ print_getmsg(struct rt_msghdr *rtm, int printf( label: %s\n, sa_rl-sr_label); #define lock(f)((rtm-rtm_rmx.rmx_locks __CONCAT(RTV_,f)) ? 'L' : ' ') - printf(%s\n, use mtuexpire); - printf(%8llu , rtm-rtm_rmx.rmx_pksent); - printf(%8u%c , rtm-rtm_rmx.rmx_mtu, lock(MTU)); - if (rtm-rtm_rmx.rmx_expire) - rtm-rtm_rmx.rmx_expire -= time(NULL); - printf(%8d%c\n, rtm-rtm_rmx.rmx_expire, lock(EXPIRE)); + relative_expire = rtm-rtm_rmx.rmx_expire ? + rtm-rtm_rmx.rmx_expire - time(NULL) : 0; + printf( use mtuexpire\n); + printf(%8llu %8u%c %8lld%c\n, + rtm-rtm_rmx.rmx_pksent, + rtm-rtm_rmx.rmx_mtu, lock(MTU), + relative_expire, lock(EXPIRE)); #undef lock #defineRTA_IGN (RTA_DST|RTA_GATEWAY|RTA_NETMASK|RTA_IFP|RTA_IFA|RTA_BRD) if (verbose)
kernel route 64 bit expire time
Hi, Convert the route expire timestamp in kernel and routing message to 64 bit. Add a small compatibility layer that allows to set routes with old user land and new kernel. ok? bluhm Index: net/route.h === RCS file: /data/mirror/openbsd/cvs/src/sys/net/route.h,v retrieving revision 1.78 diff -u -p -u -p -r1.78 route.h --- net/route.h 19 Sep 2012 16:14:01 - 1.78 +++ net/route.h 14 Oct 2013 18:19:10 - @@ -61,10 +61,9 @@ struct route { */ struct rt_kmetrics { u_int64_t rmx_pksent; /* packets sent using this route */ + int64_t rmx_expire; /* lifetime for route, e.g. redirect */ u_int rmx_locks; /* Kernel must leave these values */ u_int rmx_mtu;/* MTU for this path */ - u_int rmx_expire; /* lifetime for route, e.g. redirect */ - u_int rmx_pad; }; /* @@ -72,9 +71,9 @@ struct rt_kmetrics { */ struct rt_metrics { u_int64_t rmx_pksent; /* packets sent using this route */ + int64_t rmx_expire; /* lifetime for route, e.g. redirect */ u_int rmx_locks; /* Kernel must leave these values */ u_int rmx_mtu;/* MTU for this path */ - u_int rmx_expire; /* lifetime for route, e.g. redirect */ u_int rmx_refcnt; /* # references hold */ /* some apps may still need these no longer used metrics */ u_int rmx_hopcount; /* max hops expected */ @@ -83,6 +82,7 @@ struct rt_metrics { u_int rmx_ssthresh; /* outbound gateway buffer limit */ u_int rmx_rtt;/* estimated round trip time */ u_int rmx_rttvar; /* estimated rtt variance */ + u_int rmx_pad; }; /* @@ -214,7 +214,47 @@ struct rt_msghdr { /* overload no longer used field */ #define rtm_usertm_rmx.rmx_pksent -#define RTM_VERSION4 /* Up the ante and ignore older versions */ +#if defined(_KERNEL) ! defined(SMALL_KERNEL) +/* + * Compatibility structures for version 4 messages. + * Remove them after OpenBSD 5.5. + */ +struct rt_ometrics { + u_int64_t rmx_pksent; /* packets sent using this route */ + u_int rmx_locks; /* Kernel must leave these values */ + u_int rmx_mtu;/* MTU for this path */ + u_int rmx_expire; /* lifetime for route, e.g. redirect */ + u_int rmx_refcnt; /* # references hold */ + /* some apps may still need these no longer used metrics */ + u_int rmx_hopcount; /* max hops expected */ + u_int rmx_recvpipe; /* inbound delay-bandwidth product */ + u_int rmx_sendpipe; /* outbound delay-bandwidth product */ + u_int rmx_ssthresh; /* outbound gateway buffer limit */ + u_int rmx_rtt;/* estimated round trip time */ + u_int rmx_rttvar; /* estimated rtt variance */ +}; +struct rt_omsghdr { + u_short rtm_msglen; /* to skip over non-understood messages */ + u_char rtm_version;/* future binary compatibility */ + u_char rtm_type; /* message type */ + u_short rtm_hdrlen; /* sizeof(rt_msghdr) to skip over the header */ + u_short rtm_index; /* index for associated ifp */ + u_short rtm_tableid;/* routing table id */ + u_char rtm_priority; /* routing priority */ + u_char rtm_mpls; /* MPLS additional infos */ + int rtm_addrs; /* bitmask identifying sockaddrs in msg */ + int rtm_flags; /* flags, incl. kern message, e.g. DONE */ + int rtm_fmask; /* bitmask used in RTM_CHANGE message */ + pid_t rtm_pid;/* identify sender */ + int rtm_seq;/* for sender to identify action */ + int rtm_errno; /* why failed */ + u_int rtm_inits; /* which metrics we are initializing */ + struct rt_ometrics rtm_rmx; /* metrics themselves */ +}; +#define RTM_OVERSION 4 /* Provide backward compatibility */ +#endif /* defined(_KERNEL) ! defined(SMALL_KERNEL) */ + +#define RTM_VERSION5 /* Up the ante and ignore older versions */ #define RTM_MAXSIZE2048/* Maximum size of an accepted route msg */ Index: net/rtsock.c === RCS file: /data/mirror/openbsd/cvs/src/sys/net/rtsock.c,v retrieving revision 1.127 diff -u -p -u -p -r1.127 rtsock.c --- net/rtsock.c28 Aug 2013 06:58:57 - 1.127 +++ net/rtsock.c14 Oct 2013 22:31:58 - @@ -101,6 +101,10 @@ struct mbuf*rt_msg1(int, struct rt_addr int rt_msg2(int, int, struct rt_addrinfo *, caddr_t, struct walkarg *); void
in6_leavegroup work queue
Hi, Ethernet drivers connected via USB might sleep when their multicast group filter is modified. Unfortunately this happens from softclock or softnet interrupt when IPv6 decides to unconfigure its addresses automatically. An obvious solution is to use a work queue. I have put the workq storage into struct in6_multi_mship. That requires to include sys/workq.h before compiling this struct. Is it a good idea to include sys/workq.h directly form netinet6/in6_var.h? An alternative is to include sys/workq.h from 50 kernel .c files. What is the right way? Note that netinet6/in6_var.h is included from user space and even from some ports. bluhm Index: netinet6/in6.c === RCS file: /data/mirror/openbsd/cvs/src/sys/netinet6/in6.c,v retrieving revision 1.120 diff -u -p -u -p -r1.120 in6.c --- netinet6/in6.c 17 Oct 2013 16:27:45 - 1.120 +++ netinet6/in6.c 18 Oct 2013 10:08:27 - @@ -124,6 +124,7 @@ int in6_lifaddr_ioctl(struct socket *, u int in6_ifinit(struct ifnet *, struct in6_ifaddr *, int); void in6_unlink_ifa(struct in6_ifaddr *, struct ifnet *); void in6_ifloop_request(int, struct ifaddr *); +void in6_leavegroup_task(void *, void *); const struct sockaddr_in6 sa6_any = { sizeof(sa6_any), AF_INET6, 0, 0, IN6ADDR_ANY_INIT, 0 @@ -1816,9 +1817,20 @@ in6_leavegroup(struct in6_multi_mship *i { if (imm-i6mm_maddr) - in6_delmulti(imm-i6mm_maddr); - free(imm, M_IPMADDR); + workq_queue_task(NULL, imm-wqt, 0, in6_leavegroup_task, imm, + NULL); + else + free(imm, M_IPMADDR); return 0; +} + +void +in6_leavegroup_task(void *arg1, void *arg2) +{ + struct in6_multi_mship *imm = arg1; + + in6_delmulti(imm-i6mm_maddr); + free(imm, M_IPMADDR); } /* Index: netinet6/in6_var.h === RCS file: /data/mirror/openbsd/cvs/src/sys/netinet6/in6_var.h,v retrieving revision 1.42 diff -u -p -u -p -r1.42 in6_var.h --- netinet6/in6_var.h 14 Oct 2013 11:07:42 - 1.42 +++ netinet6/in6_var.h 18 Oct 2013 10:09:52 - @@ -64,6 +64,8 @@ #ifndef _NETINET6_IN6_VAR_H_ #define _NETINET6_IN6_VAR_H_ +#include sys/workq.h + /* * Interface address, Internet version. One of these structures * is allocated for each interface with an Internet address. @@ -486,6 +488,7 @@ do { \ * belongs to. */ struct in6_multi_mship { + struct workq_task wqt; /* Allow network driver to sleep */ struct in6_multi *i6mm_maddr; /* Multicast address pointer */ LIST_ENTRY(in6_multi_mship) i6mm_chain; /* multicast options chain */ };
IPv6 routing header type 0
Hi, Our IPv6 stack scans all extension headers for routing header type 0 and drops the packet if it finds one. RFC 5095 demands to handle a routing header type 0 like an unrecognised routing type. This is enough to protect the own machine. To protect a network as a firewall, we have pf which does the same full scan in pf_walk_header6(). As pf is enabled by default, nothing changes for most users. If you turn off pf on your router, you should not expect extra protection. I would like to get rid of the double scanning and the old disabled code in the IPv6 stack. ok? bluhm Index: netinet6/ip6_input.c === RCS file: /data/mirror/openbsd/cvs/src/sys/netinet6/ip6_input.c,v retrieving revision 1.115 diff -u -p -u -p -r1.115 ip6_input.c --- netinet6/ip6_input.c17 Oct 2013 16:27:46 - 1.115 +++ netinet6/ip6_input.c18 Oct 2013 17:21:52 - @@ -122,7 +122,6 @@ struct ifqueue ip6intrq; struct ip6stat ip6stat; void ip6_init2(void *); -int ip6_check_rh0hdr(struct mbuf *, int *); int ip6_hopopts_input(u_int32_t *, u_int32_t *, struct mbuf **, int *); struct mbuf *ip6_pullexthdr(struct mbuf *, size_t, int); @@ -318,15 +317,6 @@ ip6_input(struct mbuf *m) } #endif - if (ip6_check_rh0hdr(m, off)) { - ip6stat.ip6s_badoptions++; - in6_ifstat_inc(m-m_pkthdr.rcvif, ifs6_in_discard); - in6_ifstat_inc(m-m_pkthdr.rcvif, ifs6_in_hdrerr); - icmp6_error(m, ICMP6_PARAM_PROB, ICMP6_PARAMPROB_HEADER, off); - /* m is already freed */ - return; - } - #if NPF 0 /* * Packet filter @@ -705,74 +695,6 @@ ip6_input(struct mbuf *m) return; bad: m_freem(m); -} - -/* scan packet for RH0 routing header. Mostly stolen from pf.c:pf_test() */ -int -ip6_check_rh0hdr(struct mbuf *m, int *offp) -{ - struct ip6_hdr *ip6 = mtod(m, struct ip6_hdr *); - struct ip6_rthdr rthdr; - struct ip6_ext opt6; - u_int8_t proto = ip6-ip6_nxt; - int done = 0, lim, off, rh_cnt = 0; - - off = ((caddr_t)ip6 - m-m_data) + sizeof(struct ip6_hdr); - lim = min(m-m_pkthdr.len, ntohs(ip6-ip6_plen) + sizeof(*ip6)); - do { - switch (proto) { - case IPPROTO_ROUTING: - *offp = off; - if (rh_cnt++) { - /* more then one rh header present */ - return (1); - } - - if (off + sizeof(rthdr) lim) { - /* packet to short to make sense */ - return (1); - } - - m_copydata(m, off, sizeof(rthdr), (caddr_t)rthdr); - - if (rthdr.ip6r_type == IPV6_RTHDR_TYPE_0) { - *offp += offsetof(struct ip6_rthdr, ip6r_type); - return (1); - } - - off += (rthdr.ip6r_len + 1) * 8; - proto = rthdr.ip6r_nxt; - break; - case IPPROTO_AH: - case IPPROTO_HOPOPTS: - case IPPROTO_DSTOPTS: - /* get next header and header length */ - if (off + sizeof(opt6) lim) { - /* -* Packet to short to make sense, we could -* reject the packet but as a router we -* should not do that so forward it. -*/ - return (0); - } - - m_copydata(m, off, sizeof(opt6), (caddr_t)opt6); - - if (proto == IPPROTO_AH) - off += (opt6.ip6e_len + 2) * 4; - else - off += (opt6.ip6e_len + 1) * 8; - proto = opt6.ip6e_nxt; - break; - case IPPROTO_FRAGMENT: - default: - /* end of header stack */ - done = 1; - break; - } - } while (!done); - - return (0); } /* Index: netinet6/route6.c === RCS file: /data/mirror/openbsd/cvs/src/sys/netinet6/route6.c,v retrieving revision 1.17 diff -u -p -u -p -r1.17 route6.c --- netinet6/route6.c 11 Jun 2008 19:00:50 - 1.17 +++ netinet6/route6.c 18 Oct 2013 17:59:45 - @@ -44,10 +44,6 @@ #include netinet/icmp6.h -#if 0 -static int ip6_rthdr0(struct mbuf *, struct ip6_hdr *, struct ip6_rthdr0 *); -#endif - /* * proto is unused */ @@ -68,43 +64,12 @@ route6_input(struct mbuf **mp, int *offp } switch
Re: in[6]_proto_cksum_out: ICMP checksum fix
On Fri, Oct 18, 2013 at 03:27:09PM -0400, Lawrence Teo wrote: Back in August I sent a diff to fix ICMP checksum calculation in in_proto_cksum_out() and in_delayed_cksum() in cases where the ICMP checksum field is not in the first mbuf of an mbuf chain (original post at http://marc.info/?l=openbsd-techm=137571298511653w=2 ). bluhm@ replied on tech@ with the following feedback: On Fri, Aug 09, 2013 at 02:21:29AM +0200, Alexander Bluhm wrote: On Mon, Aug 05, 2013 at 10:28:57AM -0400, Lawrence Teo wrote: Index: ip_output.c === RCS file: /cvs/src/sys/netinet/ip_output.c,v retrieving revision 1.244 diff -U5 -p -r1.244 ip_output.c --- ip_output.c 31 Jul 2013 15:41:52 - 1.244 +++ ip_output.c 5 Aug 2013 02:44:20 - @@ -2058,25 +2058,35 @@ ip_mloopback(struct ifnet *ifp, struct m */ void in_delayed_cksum(struct mbuf *m) { struct ip *ip; - u_int16_t csum, offset; + u_int16_t csum = 0, offset; ip = mtod(m, struct ip *); offset = ip-ip_hl 2; + + if (ip-ip_p == IPPROTO_ICMP) + if (m_copyback(m, offset + offsetof(struct icmp, icmp_cksum), + sizeof(csum), csum, M_NOWAIT)) + return; The code at the end of this function tries to avoid the m_copyback() in the common case unless (offset + sizeof(u_int16_t)) m-m_len). Do we want this optimization here? bluhm Here's my revised diff that preserves that optimization so that existing behavior won't change in the common case where the protocol checksum field is in the first mbuf. The new diff also implements similar logic in in6_proto_cksum_out(). Comments/feedback appreciated. :) Is there any good reason why you pass u_int8_t proto, u_int16_t p_off to the in_delayed_cksum() now? What was wrong with the switch in your previous diff? I think splitting the offset calculation between in_delayed_cksum() and in_proto_cksum_out() doesn't make it better. The optimisation is fine now. bluhm Thanks, Lawrence Index: netinet/in.h === RCS file: /cvs/src/sys/netinet/in.h,v retrieving revision 1.97 diff -u -p -u -p -r1.97 in.h --- netinet/in.h 9 Oct 2013 09:33:43 - 1.97 +++ netinet/in.h 16 Oct 2013 15:14:39 - @@ -835,7 +835,7 @@ int in_broadcast(struct in_addr, stru int in_canforward(struct in_addr); int in_cksum(struct mbuf *, int); int in4_cksum(struct mbuf *, u_int8_t, int, int); -voidin_delayed_cksum(struct mbuf *); +voidin_delayed_cksum(struct mbuf *, u_int8_t, u_int16_t); int in_localaddr(struct in_addr, u_int); voidin_socktrim(struct sockaddr_in *); char *inet_ntoa(struct in_addr); Index: netinet/ip_output.c === RCS file: /cvs/src/sys/netinet/ip_output.c,v retrieving revision 1.247 diff -u -p -u -p -r1.247 ip_output.c --- netinet/ip_output.c 18 Oct 2013 09:04:03 - 1.247 +++ netinet/ip_output.c 18 Oct 2013 15:14:04 - @@ -2050,34 +2050,35 @@ ip_mloopback(struct ifnet *ifp, struct m * Process a delayed payload checksum calculation. */ void -in_delayed_cksum(struct mbuf *m) +in_delayed_cksum(struct mbuf *m, u_int8_t proto, u_int16_t p_off) { struct ip *ip; - u_int16_t csum, offset; + u_int16_t csum = 0, hlen, *p = NULL; ip = mtod(m, struct ip *); - offset = ip-ip_hl 2; - csum = in4_cksum(m, 0, offset, m-m_pkthdr.len - offset); - if (csum == 0 ip-ip_p == IPPROTO_UDP) - csum = 0x; - - switch (ip-ip_p) { - case IPPROTO_TCP: - offset += offsetof(struct tcphdr, th_sum); - break; - - case IPPROTO_UDP: - offset += offsetof(struct udphdr, uh_sum); - break; - - default: + if (ip-ip_p != proto) return; + + hlen = ip-ip_hl 2; + p_off += hlen; + if ((p_off + sizeof(u_int16_t)) = m-m_len) + p = (u_int16_t *)(mtod(m, caddr_t) + p_off); + + if (proto == IPPROTO_ICMP) { + if (p) + *p = 0; + else if (m_copyback(m, p_off, sizeof(csum), csum, M_NOWAIT)) + return; } - if ((offset + sizeof(u_int16_t)) m-m_len) - m_copyback(m, offset, sizeof(csum), csum, M_NOWAIT); + csum = in4_cksum(m, 0, hlen, m-m_pkthdr.len - hlen); + if (csum == 0 proto == IPPROTO_UDP) + csum = 0x; + + if (p) + *p = csum; else - *(u_int16_t *)(mtod(m, caddr_t) + offset) = csum; + m_copyback(m, p_off, sizeof(csum), csum, M_NOWAIT); } void @@ -2086,25 +2087,20 @@ in_proto_cksum_out(struct mbuf *m, struc if (m-m_pkthdr.csum_flags M_TCP_CSUM_OUT
Re: in6_leavegroup work queue
On Fri, Oct 18, 2013 at 01:00:25PM +0200, Martin Pieuchot wrote: On 18/10/13(Fri) 12:45, Alexander Bluhm wrote: Ethernet drivers connected via USB might sleep when their multicast group filter is modified. Unfortunately this happens from softclock or softnet interrupt when IPv6 decides to unconfigure its addresses automatically. An obvious solution is to use a work queue. I have put the workq storage into struct in6_multi_mship. That requires to include sys/workq.h before compiling this struct. One problem with a work queue is that you cannot guarantee the interface will still be here when the task will be scheduled, so passing a pointer might not be a good idea. That is why I wanted to change the if_get() API to use unique index for each interface... But maybe there's another solution at this problem than using a workq... Now I use the if_index to detect that the interface is gone. I this a better approach? bluhm Index: netinet6/in6.c === RCS file: /data/mirror/openbsd/cvs/src/sys/netinet6/in6.c,v retrieving revision 1.122 diff -u -p -u -p -r1.122 in6.c --- netinet6/in6.c 24 Oct 2013 11:20:18 - 1.122 +++ netinet6/in6.c 30 Oct 2013 15:01:20 - @@ -124,6 +124,7 @@ int in6_lifaddr_ioctl(struct socket *, u int in6_ifinit(struct ifnet *, struct in6_ifaddr *, int); void in6_unlink_ifa(struct in6_ifaddr *, struct ifnet *); void in6_ifloop_request(int, struct ifaddr *); +void in6_leavegroup_task(void *, void *); const struct sockaddr_in6 sa6_any = { sizeof(sa6_any), AF_INET6, 0, 0, IN6ADDR_ANY_INIT, 0 @@ -1777,16 +1778,18 @@ in6_delmulti(struct in6_multi *in6m) ifafree(in6m-in6m_ia-ia_ifa); /* release reference */ } - /* -* Notify the network driver to update its multicast -* reception filter. -*/ - bzero(ifr.ifr_addr, sizeof(struct sockaddr_in6)); - ifr.ifr_addr.sin6_len = sizeof(struct sockaddr_in6); - ifr.ifr_addr.sin6_family = AF_INET6; - ifr.ifr_addr.sin6_addr = in6m-in6m_addr; - (*in6m-in6m_ifp-if_ioctl)(in6m-in6m_ifp, - SIOCDELMULTI, (caddr_t)ifr); + if (in6m-in6m_ifp != NULL) { + /* +* Notify the network driver to update its multicast +* reception filter. +*/ + bzero(ifr.ifr_addr, sizeof(struct sockaddr_in6)); + ifr.ifr_addr.sin6_len = sizeof(struct sockaddr_in6); + ifr.ifr_addr.sin6_family = AF_INET6; + ifr.ifr_addr.sin6_addr = in6m-in6m_addr; + (*in6m-in6m_ifp-if_ioctl)(in6m-in6m_ifp, + SIOCDELMULTI, (caddr_t)ifr); + } free(in6m, M_IPMADDR); } splx(s); @@ -1814,11 +1817,26 @@ in6_joingroup(struct ifnet *ifp, struct int in6_leavegroup(struct in6_multi_mship *imm) { - if (imm-i6mm_maddr) - in6_delmulti(imm-i6mm_maddr); - free(imm, M_IPMADDR); + workq_queue_task(NULL, imm-wqt, 0, in6_leavegroup_task, imm, + (void *)(unsigned long)imm-i6mm_maddr-in6m_ifp-if_index); + else + free(imm, M_IPMADDR); return 0; +} + +void +in6_leavegroup_task(void *arg1, void *arg2) +{ + struct in6_multi_mship *imm = arg1; + unsigned int index = (unsigned long)arg2; + + /* If interface has been be freed, avoid call to if_ioctl(). */ + if (if_get(index) != imm-i6mm_maddr-in6m_ifp) + imm-i6mm_maddr-in6m_ifp = NULL; + + in6_delmulti(imm-i6mm_maddr); + free(imm, M_IPMADDR); } /* Index: netinet6/in6_var.h === RCS file: /data/mirror/openbsd/cvs/src/sys/netinet6/in6_var.h,v retrieving revision 1.44 diff -u -p -u -p -r1.44 in6_var.h --- netinet6/in6_var.h 24 Oct 2013 11:31:43 - 1.44 +++ netinet6/in6_var.h 30 Oct 2013 15:01:20 - @@ -64,6 +64,8 @@ #ifndef _NETINET6_IN6_VAR_H_ #define _NETINET6_IN6_VAR_H_ +#include sys/workq.h + /* * Interface address, Internet version. One of these structures * is allocated for each interface with an Internet address. @@ -480,6 +482,7 @@ do { \ * belongs to. */ struct in6_multi_mship { + struct workq_task wqt; /* Allow network driver to sleep */ struct in6_multi *i6mm_maddr; /* Multicast address pointer */ LIST_ENTRY(in6_multi_mship) i6mm_chain; /* multicast options chain */ };
Re: kernel route 64 bit expire time
On Tue, Oct 15, 2013 at 12:43:16AM +0200, Alexander Bluhm wrote: Convert the route expire timestamp in kernel and routing message to 64 bit. Add a small compatibility layer that allows to set routes with old user land and new kernel. You can still config addresses with old ifconfig and new kernel. I have increased the compatibility layer, route get also works in this setup. dhclient still hangs as I have do not generate old messages for interface address changes. I would like to get that in as it is. ok? bluhm Index: net/route.h === RCS file: /data/mirror/openbsd/cvs/src/sys/net/route.h,v retrieving revision 1.82 diff -u -p -u -p -r1.82 route.h --- net/route.h 24 Oct 2013 18:50:16 - 1.82 +++ net/route.h 30 Oct 2013 16:30:40 - @@ -48,10 +48,9 @@ */ struct rt_kmetrics { u_int64_t rmx_pksent; /* packets sent using this route */ + int64_t rmx_expire; /* lifetime for route, e.g. redirect */ u_int rmx_locks; /* Kernel must leave these values */ u_int rmx_mtu;/* MTU for this path */ - u_int rmx_expire; /* lifetime for route, e.g. redirect */ - u_int rmx_pad; }; /* @@ -59,9 +58,9 @@ struct rt_kmetrics { */ struct rt_metrics { u_int64_t rmx_pksent; /* packets sent using this route */ + int64_t rmx_expire; /* lifetime for route, e.g. redirect */ u_int rmx_locks; /* Kernel must leave these values */ u_int rmx_mtu;/* MTU for this path */ - u_int rmx_expire; /* lifetime for route, e.g. redirect */ u_int rmx_refcnt; /* # references hold */ /* some apps may still need these no longer used metrics */ u_int rmx_hopcount; /* max hops expected */ @@ -70,6 +69,7 @@ struct rt_metrics { u_int rmx_ssthresh; /* outbound gateway buffer limit */ u_int rmx_rtt;/* estimated round trip time */ u_int rmx_rttvar; /* estimated rtt variance */ + u_int rmx_pad; }; /* @@ -207,7 +207,47 @@ struct rt_msghdr { /* overload no longer used field */ #define rtm_usertm_rmx.rmx_pksent -#define RTM_VERSION4 /* Up the ante and ignore older versions */ +#if defined(_KERNEL) ! defined(SMALL_KERNEL) +/* + * Compatibility structures for version 4 messages. + * Remove them after OpenBSD 5.5. + */ +struct rt_ometrics { + u_int64_t rmx_pksent; /* packets sent using this route */ + u_int rmx_locks; /* Kernel must leave these values */ + u_int rmx_mtu;/* MTU for this path */ + u_int rmx_expire; /* lifetime for route, e.g. redirect */ + u_int rmx_refcnt; /* # references hold */ + /* some apps may still need these no longer used metrics */ + u_int rmx_hopcount; /* max hops expected */ + u_int rmx_recvpipe; /* inbound delay-bandwidth product */ + u_int rmx_sendpipe; /* outbound delay-bandwidth product */ + u_int rmx_ssthresh; /* outbound gateway buffer limit */ + u_int rmx_rtt;/* estimated round trip time */ + u_int rmx_rttvar; /* estimated rtt variance */ +}; +struct rt_omsghdr { + u_short rtm_msglen; /* to skip over non-understood messages */ + u_char rtm_version;/* future binary compatibility */ + u_char rtm_type; /* message type */ + u_short rtm_hdrlen; /* sizeof(rt_msghdr) to skip over the header */ + u_short rtm_index; /* index for associated ifp */ + u_short rtm_tableid;/* routing table id */ + u_char rtm_priority; /* routing priority */ + u_char rtm_mpls; /* MPLS additional infos */ + int rtm_addrs; /* bitmask identifying sockaddrs in msg */ + int rtm_flags; /* flags, incl. kern message, e.g. DONE */ + int rtm_fmask; /* bitmask used in RTM_CHANGE message */ + pid_t rtm_pid;/* identify sender */ + int rtm_seq;/* for sender to identify action */ + int rtm_errno; /* why failed */ + u_int rtm_inits; /* which metrics we are initializing */ + struct rt_ometrics rtm_rmx; /* metrics themselves */ +}; +#define RTM_OVERSION 4 /* Provide backward compatibility */ +#endif /* defined(_KERNEL) ! defined(SMALL_KERNEL) */ + +#define RTM_VERSION5 /* Up the ante and ignore older versions */ #define RTM_MAXSIZE2048/* Maximum size of an accepted route msg */ Index: net/rtsock.c === RCS file: /data/mirror/openbsd/cvs/src/sys/net/rtsock.c,v retrieving revision 1.129 diff -u -p -u -p -r1.129
Re: kernel route 64 bit expire time
On Thu, Oct 31, 2013 at 11:44:12AM +0200, Gregory Edigarov wrote: On 10/15/2013 01:43 AM, Alexander Bluhm wrote: Hi, Convert the route expire timestamp in kernel and routing message to 64 bit. Add a small compatibility layer that allows to set routes with old user land and new kernel. ok? just out for curiosity, shouldn't the expire time be u_int64_t? Internally in the kernel rmx_expire is assigned from and compared with time_second. This variable is time_t which is __int64_t which is a signed long long. So signed is the better type. bluhm
Re: in6_leavegroup work queue
On Thu, Oct 31, 2013 at 09:56:11AM +0100, Martin Pieuchot wrote: On 30/10/13(Wed) 16:48, Alexander Bluhm wrote: Now I use the if_index to detect that the interface is gone. Do you know if the memory pointed by the imm pointer you're passing to your workq can be freed before the task got scheduled, if the interface is removed/destroyed for example? I am pretty sure that this works. The old in6_leavegroup() code called free on it, so it must not be referenced anywhere else. All imm pointer come from the ia6_memberships list, it is emptied while calling in6_leavegroup(). There's also a risk of calling in6_leavegroup() a second time before the first task get scheduled, in this case the second task will have a bogus imm pointer. This problem can be avoided by using a task(9) though. in6_leavegroup() is only called once per imm as it is the in6_multi_mship free function. Note that struct in6_multi has a reference counter, so imm-i6mm_maddr should be valid memory. Also in6_delmulti() itself calls splsoftnet() so there never was protection against timeout or softnet interrupts calling in6_leavegroup() again. I'm not sure to get the whole picture about this ioctl called in an interrupt context so feel free to correct me, but the only offending function is nd6_timer(), is that right? No, this code is also called from softnet interrupt context. An autoconfigured IPv6 address can deleted by a timeout or by a router advertisement. nd6_ra_input() - prelist_update() - nd6_prelist_add() - purge_detached() - in6_purgeaddr() - in6_leavegroup() In theory we can ignore the incomming packet, we may always loose packets and hope for a retransmit. But that would mean to avoid the sleep and do a rollback. That would be a horrible diff. Finally since we are moving away from workq(9) to task(9) I'd suggest you to use the latter. That is easy, but it does not solve the problems you describe. I have to call task_set() in in6_leavegroup() to set the if_index. May be calling task_set() can be moved to somewhere else but that does not look easy. I am still not happy with this diff although I think it does not cause memory corruption. Look at this call path: if_detach() - in6_ifdetach() - in6_purgeaddr() - in6_leavegroup() As I delay the SIOCDELMULTI after the interface is destroyed, the ioctl is never called. Perhaps we look at the problem from the wrong direction. Why do some network drivers sleep when changing multicast groups? Did they always do that or was something changed? bluhm Index: netinet6/in6.c === RCS file: /data/mirror/openbsd/cvs/src/sys/netinet6/in6.c,v retrieving revision 1.122 diff -u -p -r1.122 in6.c --- netinet6/in6.c 24 Oct 2013 11:20:18 - 1.122 +++ netinet6/in6.c 31 Oct 2013 14:40:05 - @@ -124,6 +124,7 @@ int in6_lifaddr_ioctl(struct socket *, u int in6_ifinit(struct ifnet *, struct in6_ifaddr *, int); void in6_unlink_ifa(struct in6_ifaddr *, struct ifnet *); void in6_ifloop_request(int, struct ifaddr *); +void in6_leavegroup_task(void *, void *); const struct sockaddr_in6 sa6_any = { sizeof(sa6_any), AF_INET6, 0, 0, IN6ADDR_ANY_INIT, 0 @@ -1777,16 +1778,18 @@ in6_delmulti(struct in6_multi *in6m) ifafree(in6m-in6m_ia-ia_ifa); /* release reference */ } - /* -* Notify the network driver to update its multicast -* reception filter. -*/ - bzero(ifr.ifr_addr, sizeof(struct sockaddr_in6)); - ifr.ifr_addr.sin6_len = sizeof(struct sockaddr_in6); - ifr.ifr_addr.sin6_family = AF_INET6; - ifr.ifr_addr.sin6_addr = in6m-in6m_addr; - (*in6m-in6m_ifp-if_ioctl)(in6m-in6m_ifp, - SIOCDELMULTI, (caddr_t)ifr); + if (in6m-in6m_ifp != NULL) { + /* +* Notify the network driver to update its multicast +* reception filter. +*/ + bzero(ifr.ifr_addr, sizeof(struct sockaddr_in6)); + ifr.ifr_addr.sin6_len = sizeof(struct sockaddr_in6); + ifr.ifr_addr.sin6_family = AF_INET6; + ifr.ifr_addr.sin6_addr = in6m-in6m_addr; + (*in6m-in6m_ifp-if_ioctl)(in6m-in6m_ifp, + SIOCDELMULTI, (caddr_t)ifr); + } free(in6m, M_IPMADDR); } splx(s); @@ -1814,11 +1817,27 @@ in6_joingroup(struct ifnet *ifp, struct int in6_leavegroup(struct in6_multi_mship *imm) { + if (imm-i6mm_maddr) { + task_set(imm-i6mm_task, in6_leavegroup_task, imm, + (void *)(unsigned long)imm-i6mm_maddr-in6m_ifp-if_index); + task_add(systq, imm-i6mm_task); + } else + free(imm
Re: IPv6 routing header type 0
On Fri, Oct 18, 2013 at 08:45:02PM +0200, Alexander Bluhm wrote: Our IPv6 stack scans all extension headers for routing header type 0 and drops the packet if it finds one. RFC 5095 demands to handle a routing header type 0 like an unrecognised routing type. This is enough to protect the own machine. To protect a network as a firewall, we have pf which does the same full scan in pf_walk_header6(). As pf is enabled by default, nothing changes for most users. If you turn off pf on your router, you should not expect extra protection. I would like to get rid of the double scanning and the old disabled code in the IPv6 stack. Theo and others don't like that change as it decreases security. There are hosts out there that still process RH0 and there are OpenBSD routers with pf disabled. This diff brings back the header chain scanning. As an improvement it only scans if pf has not done that before. Note that ip6_check_rh0hdr() can be easily tricked by hiding the routing header type 0 behind a fragment header. Only pf can protect you correctly as it reassembles on the forwarding path. So I am not sure wether it is worth adding it again. Comments? bluhm Index: net/pf.c === RCS file: /data/mirror/openbsd/cvs/src/sys/net/pf.c,v retrieving revision 1.857 diff -u -p -u -p -r1.857 pf.c --- net/pf.c30 Oct 2013 11:35:10 - 1.857 +++ net/pf.c13 Nov 2013 23:14:32 - @@ -6490,6 +6490,7 @@ pf_test(sa_family_t af, int fwdir, struc } } pd.eh = eh; + pd.m-m_pkthdr.pf.flags |= PF_TAG_PROCESSED; switch (pd.virtual_proto) { Index: netinet6/ip6_input.c === RCS file: /data/mirror/openbsd/cvs/src/sys/netinet6/ip6_input.c,v retrieving revision 1.120 diff -u -p -u -p -r1.120 ip6_input.c --- netinet6/ip6_input.c11 Nov 2013 09:15:35 - 1.120 +++ netinet6/ip6_input.c13 Nov 2013 23:38:22 - @@ -122,6 +122,7 @@ struct ifqueue ip6intrq; struct ip6stat ip6stat; void ip6_init2(void *); +int ip6_check_rh0hdr(struct mbuf *, int *); int ip6_hopopts_input(u_int32_t *, u_int32_t *, struct mbuf **, int *); struct mbuf *ip6_pullexthdr(struct mbuf *, size_t, int); @@ -331,6 +332,20 @@ ip6_input(struct mbuf *m) srcrt = !IN6_ARE_ADDR_EQUAL(odst, ip6-ip6_dst); #endif + /* +* Be more secure than RFC5095 and scan for type 0 routing headers. +* If pf has already scanned the header chain, do not do it twice. +*/ + if (!(m-m_pkthdr.pf.flags PF_TAG_PROCESSED) + ip6_check_rh0hdr(m, off)) { + ip6stat.ip6s_badoptions++; + in6_ifstat_inc(m-m_pkthdr.rcvif, ifs6_in_discard); + in6_ifstat_inc(m-m_pkthdr.rcvif, ifs6_in_hdrerr); + icmp6_error(m, ICMP6_PARAM_PROB, ICMP6_PARAMPROB_HEADER, off); + /* m is already freed */ + return; + } + if (IN6_IS_ADDR_LOOPBACK(ip6-ip6_src) || IN6_IS_ADDR_LOOPBACK(ip6-ip6_dst)) { ours = 1; @@ -698,6 +713,74 @@ ip6_input(struct mbuf *m) return; bad: m_freem(m); +} + +/* scan packet for RH0 routing header. Mostly stolen from pf.c:pf_test() */ +int +ip6_check_rh0hdr(struct mbuf *m, int *offp) +{ + struct ip6_hdr *ip6 = mtod(m, struct ip6_hdr *); + struct ip6_rthdr rthdr; + struct ip6_ext opt6; + u_int8_t proto = ip6-ip6_nxt; + int done = 0, lim, off, rh_cnt = 0; + + off = ((caddr_t)ip6 - m-m_data) + sizeof(struct ip6_hdr); + lim = min(m-m_pkthdr.len, ntohs(ip6-ip6_plen) + sizeof(*ip6)); + do { + switch (proto) { + case IPPROTO_ROUTING: + *offp = off; + if (rh_cnt++) { + /* more then one rh header present */ + return (1); + } + + if (off + sizeof(rthdr) lim) { + /* packet to short to make sense */ + return (1); + } + + m_copydata(m, off, sizeof(rthdr), (caddr_t)rthdr); + + if (rthdr.ip6r_type == IPV6_RTHDR_TYPE_0) { + *offp += offsetof(struct ip6_rthdr, ip6r_type); + return (1); + } + + off += (rthdr.ip6r_len + 1) * 8; + proto = rthdr.ip6r_nxt; + break; + case IPPROTO_AH: + case IPPROTO_HOPOPTS: + case IPPROTO_DSTOPTS: + /* get next header and header length */ + if (off + sizeof(opt6) lim) { + /* +* Packet to short to make sense, we could
Re: IPv6 routing header type 0
On Thu, Nov 14, 2013 at 11:00:37AM -0700, Theo de Raadt wrote: It was not shown to enough people. PERIOD. My diff was on tech@ for one day during a hackathon before I commited it. Not enough people discussed it back then. Fine. Let's discuss it now. The reasons why I removed the check in the stack are: - Scanning headers in the forwarding path is against the spirit of IPv6. - pf deals much better with fragments and headers now. - When the check was added, there was no RFC. Now I am following RFC5095. - It is pf's job to add more security. - The scanning was done twice with pf enabled. Now I am tempted to put it back because: - Theo says there a lot of OpenBSD boxes without pf attached to the internet. - Fernando Gont says there are plenty of legacy implementations supporting RH0. - Fernando Gont says it is not the most secure approach to remove the check. - I have removed the double scan when pf is enabled. bluhm
Re: IPv6 routing header type 0
On Thu, Nov 14, 2013 at 05:38:14PM -0700, Theo de Raadt wrote: Beautiful. I seems there was enough discussion. The Security argument is more important than the others. The new diff has no performance impact when pf is turned on. So I need OKs. bluhm Index: net/pf.c === RCS file: /data/mirror/openbsd/cvs/src/sys/net/pf.c,v retrieving revision 1.857 diff -u -p -u -p -r1.857 pf.c --- net/pf.c30 Oct 2013 11:35:10 - 1.857 +++ net/pf.c13 Nov 2013 23:14:32 - @@ -6490,6 +6490,7 @@ pf_test(sa_family_t af, int fwdir, struc } } pd.eh = eh; + pd.m-m_pkthdr.pf.flags |= PF_TAG_PROCESSED; switch (pd.virtual_proto) { Index: netinet6/ip6_input.c === RCS file: /data/mirror/openbsd/cvs/src/sys/netinet6/ip6_input.c,v retrieving revision 1.120 diff -u -p -u -p -r1.120 ip6_input.c --- netinet6/ip6_input.c11 Nov 2013 09:15:35 - 1.120 +++ netinet6/ip6_input.c13 Nov 2013 23:38:22 - @@ -122,6 +122,7 @@ struct ifqueue ip6intrq; struct ip6stat ip6stat; void ip6_init2(void *); +int ip6_check_rh0hdr(struct mbuf *, int *); int ip6_hopopts_input(u_int32_t *, u_int32_t *, struct mbuf **, int *); struct mbuf *ip6_pullexthdr(struct mbuf *, size_t, int); @@ -331,6 +332,20 @@ ip6_input(struct mbuf *m) srcrt = !IN6_ARE_ADDR_EQUAL(odst, ip6-ip6_dst); #endif + /* +* Be more secure than RFC5095 and scan for type 0 routing headers. +* If pf has already scanned the header chain, do not do it twice. +*/ + if (!(m-m_pkthdr.pf.flags PF_TAG_PROCESSED) + ip6_check_rh0hdr(m, off)) { + ip6stat.ip6s_badoptions++; + in6_ifstat_inc(m-m_pkthdr.rcvif, ifs6_in_discard); + in6_ifstat_inc(m-m_pkthdr.rcvif, ifs6_in_hdrerr); + icmp6_error(m, ICMP6_PARAM_PROB, ICMP6_PARAMPROB_HEADER, off); + /* m is already freed */ + return; + } + if (IN6_IS_ADDR_LOOPBACK(ip6-ip6_src) || IN6_IS_ADDR_LOOPBACK(ip6-ip6_dst)) { ours = 1; @@ -698,6 +713,74 @@ ip6_input(struct mbuf *m) return; bad: m_freem(m); +} + +/* scan packet for RH0 routing header. Mostly stolen from pf.c:pf_test() */ +int +ip6_check_rh0hdr(struct mbuf *m, int *offp) +{ + struct ip6_hdr *ip6 = mtod(m, struct ip6_hdr *); + struct ip6_rthdr rthdr; + struct ip6_ext opt6; + u_int8_t proto = ip6-ip6_nxt; + int done = 0, lim, off, rh_cnt = 0; + + off = ((caddr_t)ip6 - m-m_data) + sizeof(struct ip6_hdr); + lim = min(m-m_pkthdr.len, ntohs(ip6-ip6_plen) + sizeof(*ip6)); + do { + switch (proto) { + case IPPROTO_ROUTING: + *offp = off; + if (rh_cnt++) { + /* more then one rh header present */ + return (1); + } + + if (off + sizeof(rthdr) lim) { + /* packet to short to make sense */ + return (1); + } + + m_copydata(m, off, sizeof(rthdr), (caddr_t)rthdr); + + if (rthdr.ip6r_type == IPV6_RTHDR_TYPE_0) { + *offp += offsetof(struct ip6_rthdr, ip6r_type); + return (1); + } + + off += (rthdr.ip6r_len + 1) * 8; + proto = rthdr.ip6r_nxt; + break; + case IPPROTO_AH: + case IPPROTO_HOPOPTS: + case IPPROTO_DSTOPTS: + /* get next header and header length */ + if (off + sizeof(opt6) lim) { + /* +* Packet to short to make sense, we could +* reject the packet but as a router we +* should not do that so forward it. +*/ + return (0); + } + + m_copydata(m, off, sizeof(opt6), (caddr_t)opt6); + + if (proto == IPPROTO_AH) + off += (opt6.ip6e_len + 2) * 4; + else + off += (opt6.ip6e_len + 1) * 8; + proto = opt6.ip6e_nxt; + break; + case IPPROTO_FRAGMENT: + default: + /* end of header stack */ + done = 1; + break; + } + } while (!done); + + return (0); } /* Index: sys/mbuf.h ===
ip_stripoptions in icmp_reflect
Hi, Instead of stripping the IP options manually in icmp_reflect(), just call ip_stripoptions(). Remove an unneeded parameter and adjust the ip length in ip_stripoptions(). From FreeBSD. ok? bluhm Index: netinet/ip_icmp.c === RCS file: /data/mirror/openbsd/cvs/src/sys/netinet/ip_icmp.c,v retrieving revision 1.109 diff -u -p -u -p -r1.109 ip_icmp.c --- netinet/ip_icmp.c 11 Nov 2013 09:15:34 - 1.109 +++ netinet/ip_icmp.c 16 Nov 2013 13:36:35 - @@ -807,18 +807,7 @@ icmp_reflect(struct mbuf *m, struct mbuf printf(%d\n, opts-m_len); #endif } - /* -* Now strip out original options by copying rest of first -* mbuf's data back, and adjust the IP length. -*/ - ip-ip_len = htons(ntohs(ip-ip_len) - optlen); - ip-ip_hl = sizeof(struct ip) 2; - m-m_len -= optlen; - if (m-m_flags M_PKTHDR) - m-m_pkthdr.len -= optlen; - optlen += sizeof(struct ip); - bcopy((caddr_t)ip + optlen, (caddr_t)(ip + 1), - m-m_len - sizeof(struct ip)); + ip_stripoptions(m); } m-m_flags = ~(M_BCAST|M_MCAST); if (op) Index: netinet/ip_input.c === RCS file: /data/mirror/openbsd/cvs/src/sys/netinet/ip_input.c,v retrieving revision 1.220 diff -u -p -u -p -r1.220 ip_input.c --- netinet/ip_input.c 11 Nov 2013 09:15:34 - 1.220 +++ netinet/ip_input.c 16 Nov 2013 13:27:47 - @@ -1336,14 +1336,10 @@ ip_srcroute(struct mbuf *m0) } /* - * Strip out IP options, at higher - * level protocol in the kernel. - * Second argument is buffer to which options - * will be moved, and return value is their length. - * XXX should be deleted; last arg currently ignored. + * Strip out IP options, at higher level protocol in the kernel. */ void -ip_stripoptions(struct mbuf *m, struct mbuf *mopt) +ip_stripoptions(struct mbuf *m) { int i; struct ip *ip = mtod(m, struct ip *); @@ -1358,6 +1354,7 @@ ip_stripoptions(struct mbuf *m, struct m if (m-m_flags M_PKTHDR) m-m_pkthdr.len -= olen; ip-ip_hl = sizeof(struct ip) 2; + ip-ip_len = htons(ntohs(ip-ip_len) - olen); } int inetctlerrmap[PRC_NCMDS] = { Index: netinet/ip_var.h === RCS file: /data/mirror/openbsd/cvs/src/sys/netinet/ip_var.h,v retrieving revision 1.48 diff -u -p -u -p -r1.48 ip_var.h --- netinet/ip_var.h24 Oct 2013 11:17:36 - 1.48 +++ netinet/ip_var.h16 Nov 2013 13:18:01 - @@ -200,7 +200,7 @@ int ip_setmoptions(int, struct ip_mopti voidip_slowtimo(void); struct mbuf * ip_srcroute(struct mbuf *); -voidip_stripoptions(struct mbuf *, struct mbuf *); +voidip_stripoptions(struct mbuf *); int ip_sysctl(int *, u_int, void *, size_t *, void *, size_t); voidip_savecontrol(struct inpcb *, struct mbuf **, struct ip *, struct mbuf *);
Re: Unexpected match set prio behaviour
On Thu, Nov 14, 2013 at 12:03:21AM +0200, Alexey Suslikov wrote: This is on 5.4-stable. vlan is only used to see what resulting prio is. #match on { $int_if } inet proto icmp all icmp-type echoreq set prio 5 pass quick on { $ext_if, $int_if } Can you test wether this diff matches your expected behaviour? Please try various combinations of pass and match rules. bluhm Index: net/pf.c === RCS file: /data/mirror/openbsd/cvs/src/sys/net/pf.c,v retrieving revision 1.861 diff -u -p -r1.861 pf.c --- net/pf.c16 Nov 2013 00:36:01 - 1.861 +++ net/pf.c18 Nov 2013 00:56:55 - @@ -3110,8 +3110,10 @@ pf_rule_to_actions(struct pf_rule *r, st a-max_mss = r-max_mss; a-flags |= (r-scrub_flags (PFSTATE_NODF|PFSTATE_RANDOMID| PFSTATE_SETTOS|PFSTATE_SCRUB_TCP|PFSTATE_SETPRIO)); - a-set_prio[0] = r-set_prio[0]; - a-set_prio[1] = r-set_prio[1]; + if (r-scrub_flags PFSTATE_SETPRIO) { + a-set_prio[0] = r-set_prio[0]; + a-set_prio[1] = r-set_prio[1]; + } } #define PF_TEST_ATTRIB(t, a) \
unlink pf divert state when pcb detaches
Hi, There is an awkward behaviour after we have diverted connections to a socket. When the application removes the socket, the pf state will persist. A new connection will not hit the divert rule as the state grabs the packet. This is bigger issue with connectionless protocols, but can also happen with TCP if the connection was canceled before the three way handshake completed. The solution is to clean up the associated divert state when the socket gets destroyed. This is possible as both are linked together and a divert state without socket does not make sense. Note that this fix does not work for UDP yet as state and socket are not linked there. I have a diff for that, but it had some issues. ok? bluhm Index: netinet/in_pcb.c === RCS file: /data/mirror/openbsd/cvs/src/sys/netinet/in_pcb.c,v retrieving revision 1.146 diff -u -p -u -p -r1.146 in_pcb.c --- netinet/in_pcb.c20 Dec 2013 02:04:08 - 1.146 +++ netinet/in_pcb.c12 Jan 2014 12:06:44 - @@ -495,8 +495,21 @@ in_pcbdetach(struct inpcb *inp) ipsec_delete_policy(inp-inp_ipo); #endif #if NPF 0 - if (inp-inp_pf_sk) - inp-inp_pf_sk-inp = NULL; + if (inp-inp_pf_sk) { + struct pf_state_key *sk; + struct pf_state_item*si; + + sk = inp-inp_pf_sk; + TAILQ_FOREACH(si, sk-states, entry) + if (sk == si-s-key[PF_SK_STACK] si-s-rule.ptr + si-s-rule.ptr-divert.port) { + pf_unlink_state(si-s); + break; + } + /* pf_unlink_state() may have detached the state */ + if (inp-inp_pf_sk) + inp-inp_pf_sk-inp = NULL; + } #endif s = splnet(); LIST_REMOVE(inp, inp_lhash);