Re: ssh(1), getrrsetbyname(3), SSHFP and DNSSEC
On Fri, Jul 17, 2020 at 11:45:22PM +0200, Jesper Wallin wrote: > Thoughts? > > > Yours, > Jesper Wallin I found this very interesting. Too bad you didn't quote any RFC's that support this behaviour because RFC 4033 says you shouldn't set the AD bit in a query, RFC 4035 says something similar, but then digging some further in RFC 6840 (internet standard) it says in section 5.7: 5.7. Setting the AD Bit on Queries The semantics of the Authentic Data (AD) bit in the query were previously undefined. Section 4.6 of [RFC4035] instructed resolvers to always clear the AD bit when composing queries. This document defines setting the AD bit in a query as a signal indicating that the requester understands and is interested in the value of the AD bit in the response. This allows a requester to indicate that it understands the AD bit without also requesting DNSSEC data via the DO bit. I just wanted to add this as a thought supporting your patch. Best Regards, -peter
dhclient.conf - correct typo
seonds -> seconds Index: sbin/dhclient/dhclient.conf.5 === RCS file: /cvs/src/sbin/dhclient/dhclient.conf.5,v retrieving revision 1.50 diff -u -p -r1.50 dhclient.conf.5 --- sbin/dhclient/dhclient.conf.5 10 Feb 2020 13:18:20 - 1.50 +++ sbin/dhclient/dhclient.conf.5 17 Jul 2020 21:40:44 - @@ -89,7 +89,7 @@ Sets the number of seconds to wait for a If no lease is received the first valid lease in .Xr dhclient.leases 5 will be used. -The default is 30 seonds. +The default is 30 seconds. .El .Sh DHCP OPTION DECLARATIONS .Bl -tag -width Ds
Re: xhci(4) isoc: fix bogus handling of chained TRBs
hi, On 2020/07/15 21:28, sc.dy...@gmail.com wrote: > hi, > > The patch works well on Intel PCH xhci, but not on AMD Bolton xHCI. > I'll investigate this problem. Bolton xHCI sometimes raises following events. (I added printf Completion Code.) #246 cc 13 remain 0 type 5 origlen 2048 frlengths[6] 2048 #247 cc 1 remain 0 type 1 origlen 1024 frlengths[6] 3072 It seems this behavior violates the spec. 4.10.1.1. When the remain of 1. TRB is 0, CC should be SUCCESS, not SHORT_PKT, and HC should not raise interrupt. The problem is how many length 2. TRB transferred. If real CC of 1. TRB = SUCCESS, we should add 2. TRB length to frlengths. If SHORT_PKT, we should keep frlengths as is. Actually with the latter assumption I can see video smoothly w/o errors. I changed your patch to skip adding to frlengths and actlen if previous TRB is processed AND remain == 0. --- sys/dev/usb/xhci.c.orig Sun Apr 5 10:12:37 2020 +++ sys/dev/usb/xhci.c Fri Jul 17 23:30:30 2020 @@ -931,7 +931,7 @@ xhci_event_xfer_isoc(struct usbd_xfer *xfer, struct xh { struct usbd_xfer *skipxfer; struct xhci_xfer *xx = (struct xhci_xfer *)xfer; - int trb0_idx, frame_idx = 0; + int trb0_idx, frame_idx = 0, prev_trb_processed = 0; KASSERT(xx->index >= 0); trb0_idx = @@ -945,6 +945,7 @@ xhci_event_xfer_isoc(struct usbd_xfer *xfer, struct xh if (trb0_idx++ == (xp->ring.ntrb - 1)) trb0_idx = 0; } + xp->ring.trb_processed[trb_idx] = 1; /* * If we queued two TRBs for a frame and this is the second TRB, @@ -958,15 +959,19 @@ xhci_event_xfer_isoc(struct usbd_xfer *xfer, struct xh trb0_idx = xp->ring.ntrb - 2; else trb0_idx = trb_idx - 1; - if (xfer->frlengths[frame_idx] == 0) { + prev_trb_processed = xp->ring.trb_processed[trb0_idx]; + if (prev_trb_processed == 0) { xfer->frlengths[frame_idx] = XHCI_TRB_LEN(letoh32( xp->ring.trbs[trb0_idx].trb_status)); } } - xfer->frlengths[frame_idx] += - XHCI_TRB_LEN(letoh32(xp->ring.trbs[trb_idx].trb_status)) - remain; - xfer->actlen += xfer->frlengths[frame_idx]; + if (!(prev_trb_processed != 0 && remain == 0)) { + xfer->frlengths[frame_idx] += + XHCI_TRB_LEN(letoh32(xp->ring.trbs[trb_idx].trb_status)) - + remain; + xfer->actlen += xfer->frlengths[frame_idx]; + } if (xx->index != trb_idx) return (1); @@ -1696,6 +1701,9 @@ xhci_ring_alloc(struct xhci_softc *sc, struct xhci_rin ring->ntrb = ntrb; + ring->trb_processed = malloc(ring->ntrb * sizeof(*ring->trb_processed), + M_DEVBUF, M_NOWAIT); + xhci_ring_reset(sc, ring); return (0); @@ -1704,6 +1712,8 @@ xhci_ring_alloc(struct xhci_softc *sc, struct xhci_rin void xhci_ring_free(struct xhci_softc *sc, struct xhci_ring *ring) { + free(ring->trb_processed, M_DEVBUF, + ring->ntrb * sizeof(*ring->trb_processed)); usbd_dma_contig_free(&sc->sc_bus, &ring->dma); } @@ -1715,6 +1725,8 @@ xhci_ring_reset(struct xhci_softc *sc, struct xhci_rin size = ring->ntrb * sizeof(struct xhci_trb); memset(ring->trbs, 0, size); + memset(ring->trb_processed, 0, + ring->ntrb * sizeof(*ring->trb_processed)); ring->index = 0; ring->toggle = XHCI_TRB_CYCLE; @@ -1799,6 +1811,8 @@ xhci_ring_produce(struct xhci_softc *sc, struct xhci_r ring->index = 0; ring->toggle ^= 1; } + + ring->trb_processed[(trb - &ring->trbs[0])] = 0; return (trb); }
Re: ssh(1), getrrsetbyname(3), SSHFP and DNSSEC
On Fri, 17 Jul 2020, Jeremy C. Reed wrote: > > To get a response with the AD flag set, the request itself also needs > > to have the AD flag set. I re-read your post again and see you already clarified this.
Re: ssh(1), getrrsetbyname(3), SSHFP and DNSSEC
On Fri, 17 Jul 2020, Jesper Wallin wrote: > To get a response with the AD flag set, the request itself also needs > to have the AD flag set. ... > -#define RES_DEFAULT(RES_RECURSE | RES_DEFNAMES | RES_DNSRCH) > +#define RES_DEFAULT(RES_RECURSE | RES_DEFNAMES | RES_DNSRCH | RES_USE_AD) Can you share some examples of "needs" AD flag set in combination with DO flag? It's not required to set the AD flag when the DO flag is already set. You can set the DO flag without AD flag also set and get AD flag set in the response. (As a brief explanation, if the validator already authenticated it, when setting the AD flag without the DO flag in the query, the validator can send back the AD without the RRSIG records.) (I don't have any argument with adding the feature and enabling it, but I am curious what specific example caused you to require it.)
Re: Add ability to set control values with video(1)
On Mon, Jul 13, 2020 at 07:39:41PM +0100, Laurence Tratt wrote: > video(1) allows users to adjust controls such as brightness, saturation > (etc.) depending on the input device in question. These values persist even > after video(1) has quit, allowing you to e.g. increase the brightness of a > webcam before connecting to a video call. However, the only way to adjust > values is to hold down keys in the GUI, which is slow, error prone, and > can't easily be scripted. > > This patch adds a "-c" option to video(1) which either takes the special > value "reset" or a "control=value" pair. For example: > > $ video -c reset > > resets all the controls to their default values. Assuming the input device > in question supports brightness one can set that as follows: > > $ video -c brightness=200 > > Note that the available controls, and their min/max values, will vary from > device to device. > > To keep the patch simple, only one "-c" option can be passed to video(1) at > a time. Note that passing this option causes video(1) to quit before > displaying video (in identical fashion to "-q") which makes it useful for > scripting purposes. The attached patch reworks things a bit. First, it now works with white_balance_temperature, which (at least on my C920) requires mmap_init to be called first. Second, the previous patch sometimes set controls to surprising values because it called what is (in effect) a "change control by X" function. This patch now renames the "old" function to "dev_inc_ctrl" and introduces a new "dev_set_ctrl_abs". This then provides an obvious opportunity to simplify the reset function. With this patch I can do things like: $ video -c white_balance_temperature=6500 $ video -c brightness=200 $ video && video -c reset && video and see changes being made as appropriate. Laurie Index: video.1 === RCS file: /cvs/xenocara/app/video/video.1,v retrieving revision 1.15 diff -u -r1.15 video.1 --- video.1 17 Jul 2020 07:51:23 - 1.15 +++ video.1 17 Jul 2020 21:44:49 - @@ -27,6 +27,7 @@ .Bk -words .Op Fl \&gqRv .Op Fl a Ar adaptor +.Op Fl c Ar reset | control=value .Op Fl e Ar encoding .Op Fl f Ar file .Op Fl i Ar input @@ -81,6 +82,15 @@ adaptor to use. The default is 0, the first adaptor reported by .Xr X 7 . +.It Fl c Ar reset | control=value +Set control value (e.g. brightness) and exit. The special name +.Ql reset +resets all values to their default. The available controls can be found +with +.Fl q +and the default values with +.Fl c Ar reset +.Fl v . .It Fl e Ar encoding Lowercase FOURCC name of video encoding to use. Valid arguments are Index: video.c === RCS file: /cvs/xenocara/app/video/video.c,v retrieving revision 1.31 diff -u -r1.31 video.c --- video.c 17 Jul 2020 07:51:23 - 1.31 +++ video.c 17 Jul 2020 21:44:49 - @@ -192,7 +192,10 @@ #define M_IN_FILE 0x4 #define M_OUT_FILE 0x8 #define M_QUERY0x10 +#define M_RESET0x20 +#define M_SET_CTRL 0x40 int mode; + char*set_ctrl_str; int verbose; }; @@ -212,10 +215,12 @@ void dev_dump_info(struct video *); void dev_dump_query(struct video *); int dev_init(struct video *); -void dev_set_ctrl(struct video *, int, int); +void dev_inc_ctrl(struct video *, int, int); +void dev_set_ctrl_abs(struct video *vid, int, int); void dev_set_ctrl_auto_white_balance(struct video *, int); void dev_reset_ctrls(struct video *); +int parse_ctrl(struct video *, int *, int *); int parse_size(struct video *); int choose_size(struct video *); int choose_enc(struct video *); @@ -241,9 +246,9 @@ usage(void) { fprintf(stderr, "usage: %s [-gqRv] " - "[-a adaptor] [-e encoding] [-f file] [-i input] [-O output]\n" - " %*s [-o output] [-r rate] [-s size]\n", __progname, - (int)strlen(__progname), ""); + "[-a adaptor] [-c reset|control=value] [-e encoding] [-f file]\n" + " %*s [-i input] [-O output] [-o output] [-r rate] [-s size]\n", + __progname, (int)strlen(__progname), ""); } int @@ -657,46 +662,46 @@ switch (str) { case 'A': if (vid->mode & M_IN_DEV) - dev_set_ctrl(vid, CTRL_SHARPNESS, 1); + dev_inc_ctrl(vid, CTRL_SHARPNESS, 1); break; case 'a': if (vid->mode & M_IN_DEV) - dev_set_ctrl(vid, CTRL_SHARPNESS, -1); + dev_inc_ctrl(vid, CTRL_SHARPNESS, -1); break; case 'B': if (vid-
ssh(1), getrrsetbyname(3), SSHFP and DNSSEC
Hi all, I recently decided to add SSHFP records for my servers, since I never memorize or write down my key fingerprints. I learned that if I want ssh(1) to trust these records, DNSSEC needs to be enabled for my zone. To validate these records, ssh(1) is using getrrsetbyname(3), which checks if the AD (Authentic Data) flag is set in the response. To get a response with the AD flag set, the request itself also needs to have the AD flag set. It turns out that getrrsetbyname(3) doesn't set this and will therefore never get a validated response, unless the resolver is configured to always send it, no matter what the client requested. It seems like unwind(8) behaves this way but it also responds with the RRSIG records, which is extra overhead and ignored by getrrsetbyname(3). This was mentioned a few years ago [0] and the solution suggested was to add the RES_USE_DNSSEC to _res.options, which also makes the resolver respond with the extra RRSIG records. Instead, by only setting the AD flag, both the request and the response has the same size as without the flag set. The patch below will add RES_USE_AD as an option to _res.options and set it by default. This is also the default behaviour in dig(1), which I understand is a bit different, but that sure added some confusion while debugging this. This let you run unbound(8) or any other validating resolver on your local network and getrrsetbyname(3) will trust it. Do read the CAVEATS in the manual of getrrsetbyname(3) though. As a side note, I noticed that the default value of _res.options was the same value as RES_DEFAULT, so I changed it to RES_DEFAULT instead, for the sake of consistency. Thoughts? Yours, Jesper Wallin [0] https://marc.info/?t=14998384322&r=1&w=2 Index: include/resolv.h === RCS file: /cvs/src/include/resolv.h,v retrieving revision 1.22 diff -u -p -r1.22 resolv.h --- include/resolv.h14 Jan 2019 06:23:06 - 1.22 +++ include/resolv.h17 Jul 2020 21:25:30 - @@ -191,8 +191,9 @@ struct __res_state_ext { /* DNSSEC extensions: use higher bit to avoid conflict with ISC use */ #defineRES_USE_DNSSEC 0x2000 /* use DNSSEC using OK bit in OPT */ #defineRES_USE_CD 0x1000 /* set Checking Disabled flag */ +#defineRES_USE_AD 0x8000 /* set Authentic Data flag */ -#define RES_DEFAULT(RES_RECURSE | RES_DEFNAMES | RES_DNSRCH) +#define RES_DEFAULT(RES_RECURSE | RES_DEFNAMES | RES_DNSRCH | RES_USE_AD) /* * Resolver "pfcode" values. Used by dig. Index: lib/libc/asr/asr.c === RCS file: /cvs/src/lib/libc/asr/asr.c,v retrieving revision 1.64 diff -u -p -r1.64 asr.c --- lib/libc/asr/asr.c 6 Jul 2020 13:33:05 - 1.64 +++ lib/libc/asr/asr.c 17 Jul 2020 21:25:30 - @@ -511,7 +511,7 @@ asr_ctx_create(void) if ((ac = calloc(1, sizeof(*ac))) == NULL) return (NULL); - ac->ac_options = RES_RECURSE | RES_DEFNAMES | RES_DNSRCH; + ac->ac_options = RES_DEFAULT; ac->ac_refcount = 1; ac->ac_ndots = 1; ac->ac_family[0] = AF_INET; Index: lib/libc/asr/res_mkquery.c === RCS file: /cvs/src/lib/libc/asr/res_mkquery.c,v retrieving revision 1.13 diff -u -p -r1.13 res_mkquery.c --- lib/libc/asr/res_mkquery.c 14 Jan 2019 06:49:42 - 1.13 +++ lib/libc/asr/res_mkquery.c 17 Jul 2020 21:25:30 - @@ -62,6 +62,8 @@ res_mkquery(int op, const char *dname, i h.flags |= RD_MASK; if (ac->ac_options & RES_USE_CD) h.flags |= CD_MASK; + if (ac->ac_options & RES_USE_AD) + h.flags |= AD_MASK; h.qdcount = 1; if (ac->ac_options & (RES_USE_EDNS0 | RES_USE_DNSSEC)) h.arcount = 1; Index: lib/libc/asr/res_send_async.c === RCS file: /cvs/src/lib/libc/asr/res_send_async.c,v retrieving revision 1.39 diff -u -p -r1.39 res_send_async.c --- lib/libc/asr/res_send_async.c 28 Sep 2019 11:21:07 - 1.39 +++ lib/libc/asr/res_send_async.c 17 Jul 2020 21:25:30 - @@ -378,6 +378,8 @@ setup_query(struct asr_query *as, const h.flags |= RD_MASK; if (as->as_ctx->ac_options & RES_USE_CD) h.flags |= CD_MASK; + if (as->as_ctx->ac_options & RES_USE_AD) + h.flags |= AD_MASK; h.qdcount = 1; if (as->as_ctx->ac_options & (RES_USE_EDNS0 | RES_USE_DNSSEC)) h.arcount = 1; Index: lib/libc/net/res_init.3 === RCS file: /cvs/src/lib/libc/net/res_init.3,v retrieving revision 1.4 diff -u -p -r1.4 res_init.3 --- lib/libc/net/res_init.3 25 Apr 2020 21:06:17 - 1.4 +++ lib/libc/net/res_init.3 17 Jul 2020 21:25:30 -00
Re: timekeep: fixing large skews on amd64 with RDTSCP
On Thu, Jul 16, 2020 at 4:55 PM Scott Cheloha wrote: > > On Jul 16, 2020, at 19:36, Theo de Raadt wrote: > > > >> Note the third sentence. > >> > >> Given that, I reason that a serializing instruction before *and* after > >> the RDTSC should freeze it in place. > > > > I haven't seen anyone read it that way. > > They say that instructions after RDTSC can run before it because > it isn't a serializing instruction. > > Do we want that? > > And then, consider this bit of programming advice. Also from the > ISA reference (Vol. 2B 4-547): > > > If software requires RDTSC to be executed prior to execution of any > > subsequent instruction (including any memory accesses), it can > > execute the sequence LFENCE immediately after RDTSC. > > What other reading is possible given this documentation? > > What is your interpretation? Am I missing something? > If you're trying to time a sequence of instructions via rdtsc, then you have to put an lfence after the first rdtsc (so that the sequence being timed doesn't get lifted to before it completes) and an lfence before the second rdtsc (so that the sequence is actually complete before the second one). In this case, is it a problem if instructions after the rdtsc that are not dependent on its result may be started before it's actually complete? If not, then there's no reason to bracket that side. Philip Guenther
Re: net80211: skip input block ack window gaps faster
> Next version. > > One problem with the previous patch was that it effectively limited the > size of the BA window to the arbitrarily chosen limit of 16. We should not > drop frames which arrive out of order but still fall within the BA window. > > With this version, we allow the entire block ack window (usually 64 frames) > to fill up beyond the missing frame at the head, and only then bypass the > gap timeout handler and skip over the missing frame directly. I can still > trigger this shortcut with tcpbench, and still see the timeout run sometimes. > Direct skip should be faster than having to wait for the timeout to run, > and missing just one out of 64 frames is a common case in my testing. > > Also, I am not quite sure if calling if_input() from a timeout is such a > good idea. Any opinions about that? This patch still lets the gap timeout > handler clear the leading gap but avoids flushing buffered frames there. > The peer will now need to send another frame to flush the buffer, but now > if_input() will be called from network interrupt context only. Which is > probably a good thing? > > This code still seems to recover well enough from occasional packet loss, > which is what this is all about. If you are on a really bad link, none > of this will help anyway. > > diff refs/heads/master refs/heads/ba-gap > blob - 098aa9bce19481ce09676ce3c4fc0040f14c9b93 > blob + 4f41b568311bf29e131a3f4802e0a238ba940fe0 > --- sys/net80211/ieee80211_input.c > +++ sys/net80211/ieee80211_input.c > @@ -67,6 +67,7 @@ voidieee80211_input_ba(struct ieee80211com *, > struct > struct mbuf_list *); > void ieee80211_input_ba_flush(struct ieee80211com *, struct ieee80211_node *, > struct ieee80211_rx_ba *, struct mbuf_list *); > +int ieee80211_input_ba_gap_skip(struct ieee80211_rx_ba *); > void ieee80211_input_ba_gap_timeout(void *arg); > void ieee80211_ba_move_window(struct ieee80211com *, > struct ieee80211_node *, u_int8_t, u_int16_t, struct mbuf_list *); > @@ -837,10 +838,29 @@ ieee80211_input_ba(struct ieee80211com *ic, struct mbu > rxi->rxi_flags |= IEEE80211_RXI_AMPDU_DONE; > ba->ba_buf[idx].rxi = *rxi; > > - if (ba->ba_buf[ba->ba_head].m == NULL) > - timeout_add_msec(&ba->ba_gap_to, IEEE80211_BA_GAP_TIMEOUT); > - else if (timeout_pending(&ba->ba_gap_to)) > - timeout_del(&ba->ba_gap_to); > + if (ba->ba_buf[ba->ba_head].m == NULL) { > + if (ba->ba_gapwait < (ba->ba_winsize - 1)) { > + if (ba->ba_gapwait == 0) { > + timeout_add_msec(&ba->ba_gap_to, > + IEEE80211_BA_GAP_TIMEOUT); > + } > + ba->ba_gapwait++; > + } else { > + /* > + * A full BA window worth of frames is now waiting. > + * Skip the missing frame at the head of the window. > + */ > + int skipped = ieee80211_input_ba_gap_skip(ba); > + ic->ic_stats.is_ht_rx_ba_frame_lost += skipped; > + ba->ba_gapwait = 0; > + if (timeout_pending(&ba->ba_gap_to)) > + timeout_del(&ba->ba_gap_to); > + } > + } else { > + ba->ba_gapwait = 0; > + if (timeout_pending(&ba->ba_gap_to)) > + timeout_del(&ba->ba_gap_to); > + } > > ieee80211_input_ba_flush(ic, ni, ba, ml); > } > @@ -908,10 +928,26 @@ ieee80211_input_ba_flush(struct ieee80211com *ic, stru > * A leading gap will occur if a particular A-MPDU subframe never arrives > * or if a bug in the sender causes sequence numbers to jump forward by > 1. > */ > +int > +ieee80211_input_ba_gap_skip(struct ieee80211_rx_ba *ba) > +{ > + int skipped = 0; > + > + while (skipped < ba->ba_winsize && ba->ba_buf[ba->ba_head].m == NULL) { > + /* move window forward */ > + ba->ba_head = (ba->ba_head + 1) % IEEE80211_BA_MAX_WINSZ; > + ba->ba_winstart = (ba->ba_winstart + 1) & 0xfff; > + skipped++; > + } > + if (skipped > 0) > + ba->ba_winend = (ba->ba_winstart + ba->ba_winsize - 1) & 0xfff; > + > + return skipped; > +} > + > void > ieee80211_input_ba_gap_timeout(void *arg) > { > - struct mbuf_list ml = MBUF_LIST_INITIALIZER(); > struct ieee80211_rx_ba *ba = arg; > struct ieee80211_node *ni = ba->ba_ni; > struct ieee80211com *ic = ni->ni_ic; > @@ -921,20 +957,9 @@ ieee80211_input_ba_gap_timeout(void *arg) > > s = splnet(); > > - skipped = 0; > - while (skipped < ba->ba_winsize && ba->ba_buf[ba->ba_head].m == NULL) { > - /* move window forward */ > - ba->ba_head = (ba->ba_head + 1) % IEEE80211_BA_MAX_WINSZ; > - ba->ba_winstart = (ba->ba_winstart + 1) & 0xfff; > - skipped++; > -
Re: net80211: skip input block ack window gaps faster
On Fri, Jul 17, 2020 at 03:59:38PM +0200, Stefan Sperling wrote: > While measuring Tx performance at a fixed Tx rate with iwm(4) I observed > unexpected dips in throughput measured by tcpbench. These dips coincided > with one or more gap timeouts shown in 'netstat -W iwm0', such as: > 77 input block ack window gaps timed out > Which means lost frames on the receive side were stalling subsequent frames > and thus slowing tcpbench down. > > I decided to disable the gap timeout entirely to see what would happen if > those missing frames were immediately skipped rather than waiting for them. > The result was stable throughput according to tcpbench. > > I then wrote the patch below which keeps the gap timeout intact (it is needed > in case the peer stops sending anything) but skips missing frames at the head > of the Rx block window once a certain amount of frames have queued up. This > heuristics avoids having to wait for the timeout to fire in order to get > frames flowing again if we lose one of more frames during Rx traffic bursts. > > I have picked a threshold of 16 outstanding frames based on local testing. > I have no idea if this is a good threshold for everyone. It would help to > get some feedback from tests in other RF environments and other types of > access points. Any regressions? Next version. One problem with the previous patch was that it effectively limited the size of the BA window to the arbitrarily chosen limit of 16. We should not drop frames which arrive out of order but still fall within the BA window. With this version, we allow the entire block ack window (usually 64 frames) to fill up beyond the missing frame at the head, and only then bypass the gap timeout handler and skip over the missing frame directly. I can still trigger this shortcut with tcpbench, and still see the timeout run sometimes. Direct skip should be faster than having to wait for the timeout to run, and missing just one out of 64 frames is a common case in my testing. Also, I am not quite sure if calling if_input() from a timeout is such a good idea. Any opinions about that? This patch still lets the gap timeout handler clear the leading gap but avoids flushing buffered frames there. The peer will now need to send another frame to flush the buffer, but now if_input() will be called from network interrupt context only. Which is probably a good thing? This code still seems to recover well enough from occasional packet loss, which is what this is all about. If you are on a really bad link, none of this will help anyway. diff refs/heads/master refs/heads/ba-gap blob - 098aa9bce19481ce09676ce3c4fc0040f14c9b93 blob + 4f41b568311bf29e131a3f4802e0a238ba940fe0 --- sys/net80211/ieee80211_input.c +++ sys/net80211/ieee80211_input.c @@ -67,6 +67,7 @@ void ieee80211_input_ba(struct ieee80211com *, struct struct mbuf_list *); void ieee80211_input_ba_flush(struct ieee80211com *, struct ieee80211_node *, struct ieee80211_rx_ba *, struct mbuf_list *); +intieee80211_input_ba_gap_skip(struct ieee80211_rx_ba *); void ieee80211_input_ba_gap_timeout(void *arg); void ieee80211_ba_move_window(struct ieee80211com *, struct ieee80211_node *, u_int8_t, u_int16_t, struct mbuf_list *); @@ -837,10 +838,29 @@ ieee80211_input_ba(struct ieee80211com *ic, struct mbu rxi->rxi_flags |= IEEE80211_RXI_AMPDU_DONE; ba->ba_buf[idx].rxi = *rxi; - if (ba->ba_buf[ba->ba_head].m == NULL) - timeout_add_msec(&ba->ba_gap_to, IEEE80211_BA_GAP_TIMEOUT); - else if (timeout_pending(&ba->ba_gap_to)) - timeout_del(&ba->ba_gap_to); + if (ba->ba_buf[ba->ba_head].m == NULL) { + if (ba->ba_gapwait < (ba->ba_winsize - 1)) { + if (ba->ba_gapwait == 0) { + timeout_add_msec(&ba->ba_gap_to, + IEEE80211_BA_GAP_TIMEOUT); + } + ba->ba_gapwait++; + } else { + /* +* A full BA window worth of frames is now waiting. +* Skip the missing frame at the head of the window. +*/ + int skipped = ieee80211_input_ba_gap_skip(ba); + ic->ic_stats.is_ht_rx_ba_frame_lost += skipped; + ba->ba_gapwait = 0; + if (timeout_pending(&ba->ba_gap_to)) + timeout_del(&ba->ba_gap_to); + } + } else { + ba->ba_gapwait = 0; + if (timeout_pending(&ba->ba_gap_to)) + timeout_del(&ba->ba_gap_to); + } ieee80211_input_ba_flush(ic, ni, ba, ml); } @@ -908,10 +928,26 @@ ieee80211_input_ba_flush(struct ieee80211com *ic, stru * A leading gap will occur if a particular A-MPDU subframe never arrives * or if a bug in the sender causes sequence numb
pipex(4): document global data locks
Subj. Also add NET_ASSERT_LOCKED() to pipex_{link,unlink,rele}_session() to be sure they called under NET_LOCK(). Index: sys/net/pipex.c === RCS file: /cvs/src/sys/net/pipex.c,v retrieving revision 1.120 diff -u -p -r1.120 pipex.c --- sys/net/pipex.c 17 Jul 2020 08:57:27 - 1.120 +++ sys/net/pipex.c 17 Jul 2020 14:01:10 - @@ -83,19 +83,24 @@ struct pool pipex_session_pool; struct pool mppe_key_pool; /* - * static/global variables + * Global data + * Locks used to protect global data + * A atomic operation + * I immutable after creation + * N net lock */ -intpipex_enable = 0; + +intpipex_enable = 0; /* [N] */ struct pipex_hash_head -pipex_session_list,/* master session list */ -pipex_close_wait_list, /* expired session list */ -pipex_peer_addr_hashtable[PIPEX_HASH_SIZE],/* peer's address hash */ -pipex_id_hashtable[PIPEX_HASH_SIZE]; /* peer id hash */ +pipex_session_list,/* [N] master session list */ +pipex_close_wait_list, /* [N] expired session list */ +pipex_peer_addr_hashtable[PIPEX_HASH_SIZE],/* [N] peer's address hash */ +pipex_id_hashtable[PIPEX_HASH_SIZE]; /* [N] peer id hash */ -struct radix_node_head *pipex_rd_head4 = NULL; -struct radix_node_head *pipex_rd_head6 = NULL; +struct radix_node_head *pipex_rd_head4 = NULL; /* [N] */ +struct radix_node_head *pipex_rd_head6 = NULL; /* [N] */ struct timeout pipex_timer_ch; /* callout timer context */ -int pipex_prune = 1; /* walk list every seconds */ +int pipex_prune = 1; /* [I] walk list every seconds */ /* pipex traffic queue */ struct mbuf_queue pipexinq = MBUF_QUEUE_INITIALIZER(IFQ_MAXLEN, IPL_NET); @@ -105,7 +110,7 @@ struct mbuf_queue pipexoutq = MBUF_QUEUE #define ph_ppp_proto ether_vtag #ifdef PIPEX_DEBUG -int pipex_debug = 0; /* systcl net.inet.ip.pipex_debug */ +int pipex_debug = 0; /* [A] systcl net.inet.ip.pipex_debug */ #endif /* PPP compression == MPPE is assumed, so don't answer CCP Reset-Request. */ @@ -419,6 +424,8 @@ pipex_init_session(struct pipex_session void pipex_rele_session(struct pipex_session *session) { + NET_ASSERT_LOCKED(); + if (session->mppe_recv.old_session_keys) pool_put(&mppe_key_pool, session->mppe_recv.old_session_keys); pool_put(&pipex_session_pool, session); @@ -430,6 +437,8 @@ pipex_link_session(struct pipex_session { struct pipex_hash_head *chain; + NET_ASSERT_LOCKED(); + if (!iface->pipexmode) return (ENXIO); if (pipex_lookup_by_session_id(session->protocol, @@ -463,6 +472,8 @@ pipex_link_session(struct pipex_session void pipex_unlink_session(struct pipex_session *session) { + NET_ASSERT_LOCKED(); + session->ifindex = 0; LIST_REMOVE(session, id_chain);
net80211: skip input block ack window gaps faster
While measuring Tx performance at a fixed Tx rate with iwm(4) I observed unexpected dips in throughput measured by tcpbench. These dips coincided with one or more gap timeouts shown in 'netstat -W iwm0', such as: 77 input block ack window gaps timed out Which means lost frames on the receive side were stalling subsequent frames and thus slowing tcpbench down. I decided to disable the gap timeout entirely to see what would happen if those missing frames were immediately skipped rather than waiting for them. The result was stable throughput according to tcpbench. I then wrote the patch below which keeps the gap timeout intact (it is needed in case the peer stops sending anything) but skips missing frames at the head of the Rx block window once a certain amount of frames have queued up. This heuristics avoids having to wait for the timeout to fire in order to get frames flowing again if we lose one of more frames during Rx traffic bursts. I have picked a threshold of 16 outstanding frames based on local testing. I have no idea if this is a good threshold for everyone. It would help to get some feedback from tests in other RF environments and other types of access points. Any regressions? diff e27fc20afa168944a7605737ac45330f21645404 /usr/src blob - 098aa9bce19481ce09676ce3c4fc0040f14c9b93 file + sys/net80211/ieee80211_input.c --- sys/net80211/ieee80211_input.c +++ sys/net80211/ieee80211_input.c @@ -67,6 +67,7 @@ void ieee80211_input_ba(struct ieee80211com *, struct struct mbuf_list *); void ieee80211_input_ba_flush(struct ieee80211com *, struct ieee80211_node *, struct ieee80211_rx_ba *, struct mbuf_list *); +intieee80211_input_ba_gap_skip(struct ieee80211_rx_ba *); void ieee80211_input_ba_gap_timeout(void *arg); void ieee80211_ba_move_window(struct ieee80211com *, struct ieee80211_node *, u_int8_t, u_int16_t, struct mbuf_list *); @@ -837,10 +838,24 @@ ieee80211_input_ba(struct ieee80211com *ic, struct mbu rxi->rxi_flags |= IEEE80211_RXI_AMPDU_DONE; ba->ba_buf[idx].rxi = *rxi; - if (ba->ba_buf[ba->ba_head].m == NULL) - timeout_add_msec(&ba->ba_gap_to, IEEE80211_BA_GAP_TIMEOUT); - else if (timeout_pending(&ba->ba_gap_to)) - timeout_del(&ba->ba_gap_to); + if (ba->ba_buf[ba->ba_head].m == NULL) { + if (ba->ba_gapwait < IEEE80211_BA_MAX_GAPWAIT) { + if (ba->ba_gapwait == 0) + timeout_add_msec(&ba->ba_gap_to, + IEEE80211_BA_GAP_TIMEOUT); + ba->ba_gapwait++; + } else { + int skipped = ieee80211_input_ba_gap_skip(ba); + ic->ic_stats.is_ht_rx_ba_frame_lost += skipped; + ba->ba_gapwait = 0; + if (timeout_pending(&ba->ba_gap_to)) + timeout_del(&ba->ba_gap_to); + } + } else { + ba->ba_gapwait = 0; + if (timeout_pending(&ba->ba_gap_to)) + timeout_del(&ba->ba_gap_to); + } ieee80211_input_ba_flush(ic, ni, ba, ml); } @@ -902,6 +917,23 @@ ieee80211_input_ba_flush(struct ieee80211com *ic, stru ba->ba_winend = (ba->ba_winstart + ba->ba_winsize - 1) & 0xfff; } +int +ieee80211_input_ba_gap_skip(struct ieee80211_rx_ba *ba) +{ + int skipped = 0; + + while (skipped < ba->ba_winsize && ba->ba_buf[ba->ba_head].m == NULL) { + /* move window forward */ + ba->ba_head = (ba->ba_head + 1) % IEEE80211_BA_MAX_WINSZ; + ba->ba_winstart = (ba->ba_winstart + 1) & 0xfff; + skipped++; + } + if (skipped > 0) + ba->ba_winend = (ba->ba_winstart + ba->ba_winsize - 1) & 0xfff; + + return skipped; +} + /* * Forcibly move the BA window forward to remove a leading gap which has * been causing frames to linger in the reordering buffer for too long. @@ -921,17 +953,8 @@ ieee80211_input_ba_gap_timeout(void *arg) s = splnet(); - skipped = 0; - while (skipped < ba->ba_winsize && ba->ba_buf[ba->ba_head].m == NULL) { - /* move window forward */ - ba->ba_head = (ba->ba_head + 1) % IEEE80211_BA_MAX_WINSZ; - ba->ba_winstart = (ba->ba_winstart + 1) & 0xfff; - skipped++; - ic->ic_stats.is_ht_rx_ba_frame_lost++; - } - if (skipped > 0) - ba->ba_winend = (ba->ba_winstart + ba->ba_winsize - 1) & 0xfff; - + skipped = ieee80211_input_ba_gap_skip(ba); + ic->ic_stats.is_ht_rx_ba_frame_lost += skipped; ieee80211_input_ba_flush(ic, ni, ba, &ml); if_input(&ic->ic_if, &ml); @@ -2716,6 +2739,7 @@ ieee80211_recv_addba_req(struct ieee80211com *ic, stru ba->ba_token = token; timeout_set(&ba->ba_to, ieee80211_rx_ba_timeout, ba); timeout_
ppp{ac,x}(4): document locks
Subj. Index: sys/net/if_pppx.c === RCS file: /cvs/src/sys/net/if_pppx.c,v retrieving revision 1.97 diff -u -p -r1.97 if_pppx.c --- sys/net/if_pppx.c 17 Jul 2020 08:57:27 - 1.97 +++ sys/net/if_pppx.c 17 Jul 2020 13:51:14 - @@ -115,9 +115,16 @@ int pppxdebug = 0; struct pppx_if; +/* + * Locks used to protect struct members and global data + * I immutable after creation + * K kernel lock + * N net lock + */ + struct pppx_dev { - LIST_ENTRY(pppx_dev)pxd_entry; - int pxd_unit; + LIST_ENTRY(pppx_dev)pxd_entry; /* [K] */ + int pxd_unit; /* [I] */ /* kq shizz */ struct selinfo pxd_rsel; @@ -127,34 +134,36 @@ struct pppx_dev { /* queue of packets for userland to service - protected by splnet */ struct mbuf_queue pxd_svcq; - int pxd_waiting; - LIST_HEAD(,pppx_if) pxd_pxis; + int pxd_waiting;/* [N] */ + LIST_HEAD(,pppx_if) pxd_pxis; /* [N] */ }; -LIST_HEAD(, pppx_dev) pppx_devs = LIST_HEAD_INITIALIZER(pppx_devs); +LIST_HEAD(, pppx_dev) pppx_devs = + LIST_HEAD_INITIALIZER(pppx_devs); /* [K] */ struct poolpppx_if_pl; struct pppx_dev*pppx_dev_lookup(dev_t); struct pppx_dev*pppx_dev2pxd(dev_t); struct pppx_if_key { - int pxik_session_id; - int pxik_protocol; + int pxik_session_id;/* [I] */ + int pxik_protocol; /* [I] */ }; struct pppx_if { - struct pppx_if_key pxi_key; /* must be first in the struct */ + struct pppx_if_key pxi_key;/* [I] must be first + in the struct */ - RBT_ENTRY(pppx_if) pxi_entry; - LIST_ENTRY(pppx_if) pxi_list; + RBT_ENTRY(pppx_if) pxi_entry; /* [N] */ + LIST_ENTRY(pppx_if) pxi_list; /* [N] */ - int pxi_ready; + int pxi_ready; /* [N] */ - int pxi_unit; + int pxi_unit; /* [I] */ struct ifnetpxi_if; - struct pppx_dev *pxi_dev; - struct pipex_session*pxi_session; - struct pipex_iface_context pxi_ifcontext; + struct pppx_dev *pxi_dev; /* [I] */ + struct pipex_session*pxi_session; /* [I] */ + struct pipex_iface_context pxi_ifcontext; /* [N] */ }; static inline int @@ -163,7 +172,7 @@ pppx_if_cmp(const struct pppx_if *a, con return memcmp(&a->pxi_key, &b->pxi_key, sizeof(a->pxi_key)); } -RBT_HEAD(pppx_ifs, pppx_if)pppx_ifs = RBT_INITIALIZER(&pppx_ifs); +RBT_HEAD(pppx_ifs, pppx_if) pppx_ifs = RBT_INITIALIZER(&pppx_ifs); /* [N] */ RBT_PROTOTYPE(pppx_ifs, pppx_if, pxi_entry, pppx_if_cmp); intpppx_if_next_unit(void); @@ -995,12 +1004,19 @@ RBT_GENERATE(pppx_ifs, pppx_if, pxi_entr #include +/* + * Locks used to protect struct members and global data + * I immutable after creation + * K kernel lock + * N net lock + */ + struct pppac_softc { struct ifnetsc_if; - unsigned intsc_dead; - dev_t sc_dev; + unsigned intsc_dead;/* [N] */ + dev_t sc_dev; /* [I] */ LIST_ENTRY(pppac_softc) - sc_entry; + sc_entry; /* [K] */ struct mutexsc_rsel_mtx; struct selinfo sc_rsel; @@ -1014,7 +1030,7 @@ struct pppac_softc { sc_mq; }; -LIST_HEAD(pppac_list, pppac_softc); +LIST_HEAD(pppac_list, pppac_softc);/* [K] */ static voidfilt_pppac_rdetach(struct knote *); static int filt_pppac_read(struct knote *, long);
pipex_iface_fini() release multicast session under NET_LOCK()
We are going to lock the whole pipex(4) by NET_LOCK(). So move `multicast_session' freeing undet NET_LOCK() too. Index: sys/net/pipex.c === RCS file: /cvs/src/sys/net/pipex.c,v retrieving revision 1.120 diff -u -p -r1.120 pipex.c --- sys/net/pipex.c 17 Jul 2020 08:57:27 - 1.120 +++ sys/net/pipex.c 17 Jul 2020 13:23:16 - @@ -192,8 +192,8 @@ pipex_iface_stop(struct pipex_iface_cont void pipex_iface_fini(struct pipex_iface_context *pipex_iface) { - pool_put(&pipex_session_pool, pipex_iface->multicast_session); NET_LOCK(); + pool_put(&pipex_session_pool, pipex_iface->multicast_session); pipex_iface_stop(pipex_iface); NET_UNLOCK(); }
Re: Add missing `IFXF_CLONED' to pseudo-interfaces
ping? > On 10 Jul 2020, at 14:59, Vitaliy Makkoveev wrote: > > Some pseudo interfaces have missing `IFXF_CLONED' flag. Diff below fixes > this. > > Index: sys/net/if_ppp.c > === > RCS file: /cvs/src/sys/net/if_ppp.c,v > retrieving revision 1.114 > diff -u -p -r1.114 if_ppp.c > --- sys/net/if_ppp.c 24 Jun 2020 22:03:42 - 1.114 > +++ sys/net/if_ppp.c 10 Jul 2020 11:57:39 - > @@ -220,6 +220,7 @@ ppp_clone_create(struct if_clone *ifc, i > sc->sc_if.if_output = pppoutput; > sc->sc_if.if_start = ppp_ifstart; > sc->sc_if.if_rtrequest = p2p_rtrequest; > + sc->sc_if.if_xflags = IFXF_CLONED; > IFQ_SET_MAXLEN(&sc->sc_if.if_snd, IFQ_MAXLEN); > mq_init(&sc->sc_inq, IFQ_MAXLEN, IPL_NET); > ppp_pkt_list_init(&sc->sc_rawq, IFQ_MAXLEN); > Index: sys/net/if_pppoe.c > === > RCS file: /cvs/src/sys/net/if_pppoe.c,v > retrieving revision 1.68 > diff -u -p -r1.68 if_pppoe.c > --- sys/net/if_pppoe.c16 Jun 2019 00:10:37 - 1.68 > +++ sys/net/if_pppoe.c10 Jul 2020 11:57:39 - > @@ -210,6 +210,7 @@ pppoe_clone_create(struct if_clone *ifc, > sc->sc_sppp.pp_if.if_ioctl = pppoe_ioctl; > sc->sc_sppp.pp_if.if_start = pppoe_start; > sc->sc_sppp.pp_if.if_rtrequest = p2p_rtrequest; > + sc->sc_sppp.pp_if.if_xflags = IFXF_CLONED; > sc->sc_sppp.pp_tls = pppoe_tls; > sc->sc_sppp.pp_tlf = pppoe_tlf; > IFQ_SET_MAXLEN(&sc->sc_sppp.pp_if.if_snd, IFQ_MAXLEN); > Index: sys/net/if_switch.c > === > RCS file: /cvs/src/sys/net/if_switch.c,v > retrieving revision 1.30 > diff -u -p -r1.30 if_switch.c > --- sys/net/if_switch.c 6 Nov 2019 03:51:26 - 1.30 > +++ sys/net/if_switch.c 10 Jul 2020 11:57:39 - > @@ -159,6 +159,7 @@ switch_clone_create(struct if_clone *ifc > ifp->if_start = NULL; > ifp->if_type = IFT_BRIDGE; > ifp->if_hdrlen = ETHER_HDR_LEN; > + ifp->if_xflags = IFXF_CLONED; > TAILQ_INIT(&sc->sc_swpo_list); > > sc->sc_unit = unit; > Index: sys/net/if_trunk.c > === > RCS file: /cvs/src/sys/net/if_trunk.c,v > retrieving revision 1.146 > diff -u -p -r1.146 if_trunk.c > --- sys/net/if_trunk.c17 Jun 2020 06:45:22 - 1.146 > +++ sys/net/if_trunk.c10 Jul 2020 11:57:39 - > @@ -184,6 +184,7 @@ trunk_clone_create(struct if_clone *ifc, > ifp->if_ioctl = trunk_ioctl; > ifp->if_flags = IFF_SIMPLEX | IFF_BROADCAST | IFF_MULTICAST; > ifp->if_capabilities = trunk_capabilities(tr); > + ifp->if_xflags = IFXF_CLONED; > > snprintf(ifp->if_xname, sizeof(ifp->if_xname), "%s%d", > ifc->ifc_name, unit); > Index: sys/net/if_tun.c > === > RCS file: /cvs/src/sys/net/if_tun.c,v > retrieving revision 1.222 > diff -u -p -r1.222 if_tun.c > --- sys/net/if_tun.c 13 May 2020 00:48:06 - 1.222 > +++ sys/net/if_tun.c 10 Jul 2020 11:57:39 - > @@ -236,6 +236,7 @@ tun_create(struct if_clone *ifc, int uni > ifp->if_hardmtu = TUNMRU; > ifp->if_link_state = LINK_STATE_DOWN; > IFQ_SET_MAXLEN(&ifp->if_snd, IFQ_MAXLEN); > + ifp->if_xflags = IFXF_CLONED; > > if_counters_alloc(ifp); > > Index: sys/net/if_vether.c > === > RCS file: /cvs/src/sys/net/if_vether.c,v > retrieving revision 1.30 > diff -u -p -r1.30 if_vether.c > --- sys/net/if_vether.c 9 Jan 2018 15:24:24 - 1.30 > +++ sys/net/if_vether.c 10 Jul 2020 11:57:39 - > @@ -88,6 +88,7 @@ vether_clone_create(struct if_clone *ifc > > ifp->if_hardmtu = ETHER_MAX_HARDMTU_LEN; > ifp->if_capabilities = IFCAP_VLAN_MTU; > + ifp->if_xflags = IFXF_CLONED; > > ifmedia_init(&sc->sc_media, 0, vether_media_change, > vether_media_status); > Index: sys/net/if_vxlan.c > === > RCS file: /cvs/src/sys/net/if_vxlan.c,v > retrieving revision 1.77 > diff -u -p -r1.77 if_vxlan.c > --- sys/net/if_vxlan.c12 Apr 2020 11:56:52 - 1.77 > +++ sys/net/if_vxlan.c10 Jul 2020 11:57:39 - > @@ -155,6 +155,7 @@ vxlan_clone_create(struct if_clone *ifc, > > ifp->if_hardmtu = ETHER_MAX_HARDMTU_LEN; > ifp->if_capabilities = IFCAP_VLAN_MTU; > + ifp->if_xflags = IFXF_CLONED; > > ifmedia_init(&sc->sc_media, 0, vxlan_media_change, > vxlan_media_status);
iwn: fix off-by-one in antenna calibration for iwn5000
I came across this by reading the code if_iwn.c and DPRINTFs on a kernel with IWN_DEBUG. IWN_LSB() returns an index starting with 1, however the arrays used later on (noise and gain in iwn5000_set_gains()) start with 0. The current code accounts for this difference when setting the antenna gain by accessing cmd.gain[i - 1]. However the noise array is accessed with noise[i], the chainmask is as well checked against i and more importantly the overall for() loop iterates wrongly over the antennas by always starting with i=2 (the third antenna). One consequence is, that gain calibration never happens in case of only two antennas. Secondly, the final DPRINTF in iwn5000_set_gains() assumes a two-antenna setup. In my case three antennas are connected. I don't know if there are iwn setups with one antenna, but the DPRINTF wouldn't make sense there at all. Hence I propose to move this DPRINTF up where it makes more sense (and adjust it to the new place). My diff below fixes the said off-by-one and DPRINTF. Additionally it adds another DPRINTF which I felt useful while debugging and it extends a comment - those additions may be skipped of course. Here is few details of my laptop (cvs updated and kernel built today): $ dmesg | grep iwn0 iwn0 at pci2 dev 0 function 0 "Intel WiFi Link 5300" rev 0x00: msi, MIMO 3T3R, MoW, address 00:21:6a:56:2b:36 $ sysctl hw | grep -e machine -e model -e vendor -e product hw.machine=amd64 hw.model=Intel(R) Core(TM)2 Duo CPU P8600 @ 2.40GHz hw.vendor=Dell Inc. hw.product=Studio 1555 Let me know if you need a full dmesg or anything else. Regards Holger Index: if_iwn.c === RCS file: /cvs/src/sys/dev/pci/if_iwn.c,v retrieving revision 1.234 diff -u -p -u -r1.234 if_iwn.c --- if_iwn.c10 Jul 2020 13:22:20 - 1.234 +++ if_iwn.c17 Jul 2020 10:44:14 - @@ -4596,22 +4596,27 @@ iwn5000_set_gains(struct iwn_softc *sc) cmd.code = sc->noise_gain; cmd.ngroups = 1; cmd.isvalid = 1; - /* Get first available RX antenna as referential. */ - ant = IWN_LSB(sc->rxchainmask); + /* Get first available RX antenna as referential. +* IWN_LSB() return values start with 1, but +* antenna gain array cmd.gain[] and noise array +* calib->noise[] start with 0. */ + ant = IWN_LSB(sc->rxchainmask) - 1; + /* Set differential gains for other antennas. */ for (i = ant + 1; i < 3; i++) { if (sc->chainmask & (1 << i)) { /* The delta is relative to antenna "ant". */ delta = ((int32_t)calib->noise[ant] - (int32_t)calib->noise[i]) / div; + DPRINTF(("Ant[%d] vs. Ant[%d]: delta %d\n", ant, i, delta)); /* Limit to [-4.5dB,+4.5dB]. */ - cmd.gain[i - 1] = MIN(abs(delta), 3); + cmd.gain[i] = MIN(abs(delta), 3); if (delta < 0) - cmd.gain[i - 1] |= 1 << 2; /* sign bit */ + cmd.gain[i] |= 1 << 2; /* sign bit */ + DPRINTF(("Setting differential gains for antenna %d: %x\n", + i, cmd.gain[i])); } } - DPRINTF(("setting differential gains: %x/%x (%x)\n", - cmd.gain[0], cmd.gain[1], sc->chainmask)); return iwn_cmd(sc, IWN_CMD_PHY_CALIB, &cmd, sizeof cmd, 1); }
Re: wsfontload(8): display number of characters in a loaded font
Seems useful. While it's not especially likely anyone is parsing the output of this, just in case they are it's usually more admin-friendly to add a new column at the end unless there's a good reason not to. -- Sent from a phone, apologies for poor formatting. On 16 July 2020 21:29:50 Frederic Cambus wrote: Hi tech@, Here is a diff to add a new column to wsfontload -l output, which reports the number of characters contained in a loaded font. It's especially useful with user loaded fonts as they can contain more than 256 characters. Below is the current output of wsfontload -l, without the diff: # Name Encoding W H 0 Boldface ibm 8 16 1 Spleen 6x12 iso 6 12 2 Spleen 8x16 iso 8 16 3 Spleen 12x24 iso 12 24 4 Spleen 16x32 iso 16 32 5 Spleen 32x64 iso 32 64 And now with the diff: # Name EncodingChars W H 0 Boldface ibm 254 8 16 1 Spleen 6x12 iso 96 6 12 2 Spleen 8x16 iso 224 8 16 3 Spleen 12x24 iso 224 12 24 4 Spleen 16x32 iso 224 16 32 5 Spleen 32x64 iso 224 32 64 Comments? OK? Index: usr.sbin/wsfontload/wsfontload.c === RCS file: /cvs/src/usr.sbin/wsfontload/wsfontload.c,v retrieving revision 1.21 diff -u -p -r1.21 wsfontload.c --- usr.sbin/wsfontload/wsfontload.c 28 Jun 2019 13:32:51 - 1.21 +++ usr.sbin/wsfontload/wsfontload.c 16 Jul 2020 16:11:18 - @@ -141,7 +141,8 @@ main(int argc, char *argv[]) if (list) { i = 0; - p = " # Name Encoding W H"; + p = " # Name Encoding" \ +"Chars W H"; do { f.index = i; res = ioctl(wsfd, WSDISPLAYIO_LSFONT, &f); @@ -151,10 +152,11 @@ main(int argc, char *argv[]) puts(p); p = NULL; } - printf("%2d %-32s %8s %2d %2d\n", + printf("%2d %-32s %8s %8d %2d %2d\n", f.index, f.name, encodings[f.encoding].name, -f.fontwidth, f.fontheight); +f.numchars, f.fontwidth, +f.fontheight); } } i++;
Avoid realloc
Recently a stat(2) call was added to load_server_config() of ssh to avoid reallocs. However, a buffer of 'st_size' length might be too short to hold the null terminator of the string. Add one more byte to the size, if it is sure that we can't overflow. Gerhard Index: usr.bin/ssh/servconf.c === RCS file: /cvs/src/usr.bin/ssh/servconf.c,v retrieving revision 1.367 diff -u -p -u -p -r1.367 servconf.c --- usr.bin/ssh/servconf.c 5 Jul 2020 23:59:45 - 1.367 +++ usr.bin/ssh/servconf.c 17 Jul 2020 09:27:08 - @@ -2339,7 +2339,8 @@ load_server_config(const char *filename, sshbuf_reset(conf); /* grow buffer, so realloc is avoided for large config files */ if (fstat(fileno(f), &st) == 0 && st.st_size > 0 && -(r = sshbuf_allocate(conf, st.st_size)) != 0) + st.st_size < LONG_MAX && + (r = sshbuf_allocate(conf, st.st_size + 1)) != 0) fatal("%s: allocate failed: %s", __func__, ssh_err(r)); while (getline(&line, &linesize, f) != -1) { lineno++;
Re: Add missing `IFXF_CLONED' to pseudo-interfaces
anyone? On Fri, Jul 10, 2020 at 02:59:55PM +0300, Vitaliy Makkoveev wrote: > Some pseudo interfaces have missing `IFXF_CLONED' flag. Diff below fixes > this. > > Index: sys/net/if_ppp.c > === > RCS file: /cvs/src/sys/net/if_ppp.c,v > retrieving revision 1.114 > diff -u -p -r1.114 if_ppp.c > --- sys/net/if_ppp.c 24 Jun 2020 22:03:42 - 1.114 > +++ sys/net/if_ppp.c 10 Jul 2020 11:57:39 - > @@ -220,6 +220,7 @@ ppp_clone_create(struct if_clone *ifc, i > sc->sc_if.if_output = pppoutput; > sc->sc_if.if_start = ppp_ifstart; > sc->sc_if.if_rtrequest = p2p_rtrequest; > + sc->sc_if.if_xflags = IFXF_CLONED; > IFQ_SET_MAXLEN(&sc->sc_if.if_snd, IFQ_MAXLEN); > mq_init(&sc->sc_inq, IFQ_MAXLEN, IPL_NET); > ppp_pkt_list_init(&sc->sc_rawq, IFQ_MAXLEN); > Index: sys/net/if_pppoe.c > === > RCS file: /cvs/src/sys/net/if_pppoe.c,v > retrieving revision 1.68 > diff -u -p -r1.68 if_pppoe.c > --- sys/net/if_pppoe.c16 Jun 2019 00:10:37 - 1.68 > +++ sys/net/if_pppoe.c10 Jul 2020 11:57:39 - > @@ -210,6 +210,7 @@ pppoe_clone_create(struct if_clone *ifc, > sc->sc_sppp.pp_if.if_ioctl = pppoe_ioctl; > sc->sc_sppp.pp_if.if_start = pppoe_start; > sc->sc_sppp.pp_if.if_rtrequest = p2p_rtrequest; > + sc->sc_sppp.pp_if.if_xflags = IFXF_CLONED; > sc->sc_sppp.pp_tls = pppoe_tls; > sc->sc_sppp.pp_tlf = pppoe_tlf; > IFQ_SET_MAXLEN(&sc->sc_sppp.pp_if.if_snd, IFQ_MAXLEN); > Index: sys/net/if_switch.c > === > RCS file: /cvs/src/sys/net/if_switch.c,v > retrieving revision 1.30 > diff -u -p -r1.30 if_switch.c > --- sys/net/if_switch.c 6 Nov 2019 03:51:26 - 1.30 > +++ sys/net/if_switch.c 10 Jul 2020 11:57:39 - > @@ -159,6 +159,7 @@ switch_clone_create(struct if_clone *ifc > ifp->if_start = NULL; > ifp->if_type = IFT_BRIDGE; > ifp->if_hdrlen = ETHER_HDR_LEN; > + ifp->if_xflags = IFXF_CLONED; > TAILQ_INIT(&sc->sc_swpo_list); > > sc->sc_unit = unit; > Index: sys/net/if_trunk.c > === > RCS file: /cvs/src/sys/net/if_trunk.c,v > retrieving revision 1.146 > diff -u -p -r1.146 if_trunk.c > --- sys/net/if_trunk.c17 Jun 2020 06:45:22 - 1.146 > +++ sys/net/if_trunk.c10 Jul 2020 11:57:39 - > @@ -184,6 +184,7 @@ trunk_clone_create(struct if_clone *ifc, > ifp->if_ioctl = trunk_ioctl; > ifp->if_flags = IFF_SIMPLEX | IFF_BROADCAST | IFF_MULTICAST; > ifp->if_capabilities = trunk_capabilities(tr); > + ifp->if_xflags = IFXF_CLONED; > > snprintf(ifp->if_xname, sizeof(ifp->if_xname), "%s%d", > ifc->ifc_name, unit); > Index: sys/net/if_tun.c > === > RCS file: /cvs/src/sys/net/if_tun.c,v > retrieving revision 1.222 > diff -u -p -r1.222 if_tun.c > --- sys/net/if_tun.c 13 May 2020 00:48:06 - 1.222 > +++ sys/net/if_tun.c 10 Jul 2020 11:57:39 - > @@ -236,6 +236,7 @@ tun_create(struct if_clone *ifc, int uni > ifp->if_hardmtu = TUNMRU; > ifp->if_link_state = LINK_STATE_DOWN; > IFQ_SET_MAXLEN(&ifp->if_snd, IFQ_MAXLEN); > + ifp->if_xflags = IFXF_CLONED; > > if_counters_alloc(ifp); > > Index: sys/net/if_vether.c > === > RCS file: /cvs/src/sys/net/if_vether.c,v > retrieving revision 1.30 > diff -u -p -r1.30 if_vether.c > --- sys/net/if_vether.c 9 Jan 2018 15:24:24 - 1.30 > +++ sys/net/if_vether.c 10 Jul 2020 11:57:39 - > @@ -88,6 +88,7 @@ vether_clone_create(struct if_clone *ifc > > ifp->if_hardmtu = ETHER_MAX_HARDMTU_LEN; > ifp->if_capabilities = IFCAP_VLAN_MTU; > + ifp->if_xflags = IFXF_CLONED; > > ifmedia_init(&sc->sc_media, 0, vether_media_change, > vether_media_status); > Index: sys/net/if_vxlan.c > === > RCS file: /cvs/src/sys/net/if_vxlan.c,v > retrieving revision 1.77 > diff -u -p -r1.77 if_vxlan.c > --- sys/net/if_vxlan.c12 Apr 2020 11:56:52 - 1.77 > +++ sys/net/if_vxlan.c10 Jul 2020 11:57:39 - > @@ -155,6 +155,7 @@ vxlan_clone_create(struct if_clone *ifc, > > ifp->if_hardmtu = ETHER_MAX_HARDMTU_LEN; > ifp->if_capabilities = IFCAP_VLAN_MTU; > + ifp->if_xflags = IFXF_CLONED; > > ifmedia_init(&sc->sc_media, 0, vxlan_media_change, > vxlan_media_status);
faq/pf/carp: pfsync0 does not exist by default
Without /etc/hostname.pfsync0 there will be no such interface upon boot. Feedback? OK? Index: faq/pf/carp.html === RCS file: /cvs/www/faq/pf/carp.html,v retrieving revision 1.63 diff -u -p -r1.63 carp.html --- faq/pf/carp.html28 May 2019 01:53:11 - 1.63 +++ faq/pf/carp.html13 Jul 2020 19:44:00 - @@ -323,8 +323,6 @@ Since pfsync(4) is a virtual network int pfsyncN The name of the pfsync(4) interface. -pfsync0 exists by default when using the GENERIC -kernel. syncdev The name of the physical interface used to send pfsync updates out.
Re: random toeplitz seeds
On Fri, Jun 26, 2020 at 07:55:43AM +0200, Theo Buehler wrote: > This adds an stoeplitz_random_seed() function that generates a random > Toeplitz key seed with an invertible matrix T. This is necessary and > sufficient for the hash to spread out over all 65536 possible values. > > While it is clear from T * (-1) == 0 that seeds with parity 0 are bad, > I don't have a neat and clean proof for the fact that a seed with > parity 1 always generates an invertible Toeplitz matrix. It's not hard > to check, but rather tedious. > > I'm unsure how to hook it up. I enabled random seeds by using the > function in stoeplitz_init(), but that's just for illustration. sorry, i didnt see this when you sent it out. i can't say whether the maths is right or not, but i'm happy to trust you on it. it's hooked up fine though, so ok by me. dlg > Index: sys/net/toeplitz.c > === > RCS file: /var/cvs/src/sys/net/toeplitz.c,v > retrieving revision 1.7 > diff -u -p -r1.7 toeplitz.c > --- sys/net/toeplitz.c19 Jun 2020 08:48:15 - 1.7 > +++ sys/net/toeplitz.c25 Jun 2020 18:43:02 - > @@ -69,9 +69,38 @@ static struct stoeplitz_cache stoeplitz_ > const struct stoeplitz_cache *const > stoeplitz_cache = &stoeplitz_syskey_cache; > > +/* parity of n16: count (mod 2) of ones in the binary representation. */ > +int > +parity(uint16_t n16) > +{ > + n16 = ((n16 & 0x) >> 1) ^ (n16 & 0x); > + n16 = ((n16 & 0x) >> 2) ^ (n16 & 0x); > + n16 = ((n16 & 0xf0f0) >> 4) ^ (n16 & 0x0f0f); > + n16 = ((n16 & 0xff00) >> 8) ^ (n16 & 0x00ff); > + > + return (n16); > +} > + > +/* > + * The Toeplitz matrix obtained from a seed is invertible if and only if the > + * parity of the seed is 1. Generate such a seed uniformly at random. > + */ > +stoeplitz_key > +stoeplitz_random_seed(void) > +{ > + stoeplitz_key seed; > + > + seed = arc4random() & UINT16_MAX; > + if (parity(seed) == 0) > + seed ^= 1; > + > + return (seed); > +} > + > void > stoeplitz_init(void) > { > + stoeplitz_keyseed = stoeplitz_random_seed(); > stoeplitz_cache_init(&stoeplitz_syskey_cache, stoeplitz_keyseed); > } > >
rge(4): support for Realtek RTL8125B
Hi, The following diff adds Realtek RTL8125B support to rge(4) and uses if_rxring to manage the number of filled slots on the rx ring. Tested with the TP-LINK TL-NG421 adapter. Index: share/man/man4/pci.4 === RCS file: /cvs/src/share/man/man4/pci.4,v retrieving revision 1.381 diff -u -p -u -p -r1.381 pci.4 --- share/man/man4/pci.419 Apr 2020 09:27:44 - 1.381 +++ share/man/man4/pci.417 Jul 2020 07:49:12 - @@ -251,7 +251,7 @@ AMD PCnet-PCI 10/100 Ethernet device .It Xr re 4 Realtek 8139C+/8169/816xS/811xS/8168/810xE 10/100/Gigabit Ethernet device .It Xr rge 4 -Realtek 8125 PCI Express 2.5Gb Ethernet device +Realtek 8125/8125B PCI Express 2.5Gb Ethernet device .It Xr rl 4 Realtek 8129/8139 10/100 Ethernet device .It Xr se 4 Index: share/man/man4/rge.4 === RCS file: /cvs/src/share/man/man4/rge.4,v retrieving revision 1.2 diff -u -p -u -p -r1.2 rge.4 --- share/man/man4/rge.418 Nov 2019 22:09:59 - 1.2 +++ share/man/man4/rge.417 Jul 2020 07:49:12 - @@ -1,6 +1,6 @@ .\" $OpenBSD: rge.4,v 1.2 2019/11/18 22:09:59 jmc Exp $ .\" -.\" Copyright (c) 2019 Kevin Lo +.\" Copyright (c) 2019, 2020 Kevin Lo .\" .\" Permission to use, copy, modify, and distribute this software for any .\" purpose with or without fee is hereby granted, provided that the above @@ -19,18 +19,19 @@ .Os .Sh NAME .Nm rge -.Nd Realtek 8125 PCI Express 2.5Gb Ethernet device +.Nd Realtek 8125/8125B PCI Express 2.5Gb Ethernet device .Sh SYNOPSIS .Cd "rge* at pci?" .Sh DESCRIPTION The .Nm driver provides support for PCI Express 2.5Gb Ethernet adapters based -on the Realtek RTL8125 Ethernet controller, including the following: +on the Realtek RTL8125 and RTL8125B Ethernet controllers, +including the following: .Pp .Bl -bullet -offset indent -compact .It -Realtek RTL8125 2.5GbE Adapter (2500baseT) +Realtek 8125/8125B 2.5GbE Adapter (2500baseT) .It Rivet Networks Killer E3000 Adapter (2500baseT) .El Index: sys/dev/pci/if_rge.c === RCS file: /cvs/src/sys/dev/pci/if_rge.c,v retrieving revision 1.4 diff -u -p -u -p -r1.4 if_rge.c --- sys/dev/pci/if_rge.c10 Jul 2020 13:26:38 - 1.4 +++ sys/dev/pci/if_rge.c17 Jul 2020 07:49:13 - @@ -1,7 +1,7 @@ /* $OpenBSD: if_rge.c,v 1.4 2020/07/10 13:26:38 patrick Exp $ */ /* - * Copyright (c) 2019 Kevin Lo + * Copyright (c) 2019, 2020 Kevin Lo * * Permission to use, copy, modify, and distribute this software for any * purpose with or without fee is hereby granted, provided that the above @@ -50,6 +50,13 @@ #include +#ifdef RGE_DEBUG +#define DPRINTF(x) do { if (rge_debug > 0) printf x; } while (0) +int rge_debug = 0; +#else +#define DPRINTF(x) +#endif + intrge_match(struct device *, void *, void *); void rge_attach(struct device *, struct device *, void *); intrge_intr(void *); @@ -62,16 +69,22 @@ voidrge_stop(struct ifnet *); intrge_ifmedia_upd(struct ifnet *); void rge_ifmedia_sts(struct ifnet *, struct ifmediareq *); intrge_allocmem(struct rge_softc *); -intrge_newbuf(struct rge_softc *, int); +intrge_newbuf(struct rge_softc *); void rge_discard_rxbuf(struct rge_softc *, int); -intrge_rx_list_init(struct rge_softc *); +void rge_rx_list_init(struct rge_softc *); void rge_tx_list_init(struct rge_softc *); +void rge_fill_rx_ring(struct rge_softc *); intrge_rxeof(struct rge_softc *); intrge_txeof(struct rge_softc *); void rge_reset(struct rge_softc *); void rge_iff(struct rge_softc *); void rge_set_phy_power(struct rge_softc *, int); void rge_phy_config(struct rge_softc *); +void rge_phy_config_mac_cfg2(struct rge_softc *); +void rge_phy_config_mac_cfg3(struct rge_softc *); +void rge_phy_config_mac_cfg4(struct rge_softc *); +void rge_phy_config_mac_cfg5(struct rge_softc *); +void rge_phy_config_mcu(struct rge_softc *, uint16_t); void rge_set_macaddr(struct rge_softc *, const uint8_t *); void rge_get_macaddr(struct rge_softc *, uint8_t *); void rge_hw_init(struct rge_softc *); @@ -79,6 +92,7 @@ void rge_disable_phy_ocp_pwrsave(struct void rge_patch_phy_mcu(struct rge_softc *, int); void rge_add_media_types(struct rge_softc *); void rge_config_imtype(struct rge_softc *, int); +void rge_disable_hw_im(struct rge_softc *); void rge_disable_sim_im(struct rge_softc *); void rge_setup_sim_im(struct rge_softc *); void rge_setup_intr(struct rge_softc *, int); @@ -88,6 +102,7 @@ uint32_t rge_read_csi(st