Re: sparc64: find root device on hardware RAID

2019-12-28 Thread Klemens Nanni
On Sun, Dec 29, 2019 at 03:30:15AM +0100, Klemens Nanni wrote:
> > link->target isn't the right place to put this, for one thing it's only 16 
> > bits
> > and the wwn is 64 bits, and it's used throughout the driver to look up 
> > devices
> > in an array, so changing it will break things.  I think link->port_wwn is 
> > the
> > right place to store it.
> Ah, link->target was there because I played with that in earlier diffs,
> port_wwn is indeed correct here.
> 
> > The fields in the page returned by the driver are also little endian, so 
> > you'd
> > need letoh64(vpg.wwid) here.
> Thanks, I see that is done elsewhere in the driver, too.
>  
> > You should still return 0 here, as continuing on will send the SAS device
> > page 0 request to the raid volume, which will probably upset the controller
> > enough to stop talking to you.
> Oh well... that explains the hangs - I accidentially dropped the return,
> it should obviously stay and my diff should only add another page fetch.
All three points are addressed in the updated diff below, diff three to
find the root device.

mpii(4) currently leaves the port WWN empty for RAID volumes (physical
devices are populated).  autoboot(9) uses this to match the root device
as per the second diff, so we must fill in after fetching the relevant
page as suggested by mikeb and jmatthew.

Feedback? OK?

Index: mpii.c
===
RCS file: /cvs/src/sys/dev/pci/mpii.c,v
retrieving revision 1.122
diff -u -p -r1.122 mpii.c
--- mpii.c  28 Dec 2019 04:38:22 -  1.122
+++ mpii.c  29 Dec 2019 05:02:38 -
@@ -910,8 +910,28 @@ mpii_scsi_probe(struct scsi_link *link)
if (ISSET(flags, MPII_DF_HIDDEN) || ISSET(flags, MPII_DF_UNUSED))
return (1);
 
-   if (ISSET(flags, MPII_DF_VOLUME))
+   if (ISSET(flags, MPII_DF_VOLUME)) {
+   struct mpii_cfg_hdr hdr;
+   struct mpii_cfg_raid_vol_pg1 vpg;
+   size_t pagelen;
+
+   address = MPII_CFG_RAID_VOL_ADDR_HANDLE | dev->dev_handle;
+
+   if (mpii_req_cfg_header(sc, MPII_CONFIG_REQ_PAGE_TYPE_RAID_VOL,
+   1, address, MPII_PG_POLL, ) != 0)
+   return (EINVAL);
+
+   memset(, 0, sizeof(vpg));
+   pagelen = hdr.page_length * 4;
+
+   if (mpii_req_cfg_page(sc, address, MPII_PG_POLL, , 1,
+   , pagelen) != 0)
+   return (EINVAL);
+
+   link->port_wwn = letoh64(vpg.wwid);
+
return (0);
+   }
 
memset(, 0, sizeof(ehdr));
ehdr.page_type = MPII_CONFIG_REQ_PAGE_TYPE_EXTENDED;



Re: sparc64: find root device on hardware RAID

2019-12-28 Thread Klemens Nanni
On Sun, Dec 29, 2019 at 05:58:02AM +0100, Klemens Nanni wrote:
> Now I need to work around the first digit's mismatch;  for reasons still
> unknown to me, official documentation states that the RAID volume WWID's
> first digit --if it is zero-- must be replaced with three,  so the
> bootpath contains 3aa32290d5dcd16c whereas the port WWN has the correct
> aa32290d5dcd16c.
> 
> Fix that and the kernel will match the device and find its root device
> automatically.  I get around to a diff for that now.
https://jp.fujitsu.com/platform/server/sparc/manual/en/c120-e679/14.2.12.html
is the only freely available documentation I could find online which
mentions how to craft bootpaths for RAID volumes.

It says
Replace the number "0" at the beginning of WWID of the RAID volume with 
"3".

which implies to me that every WWID of such RAID volumes starts with
zero, hence it must always be replaced three;  otherwise documentation
is incomplete.

I cannot find documentation or any kind of reasoning as to *why* this
must be done, anyone who knows please enlighten me.


So to match these, simply add an additional check in the existing code
path for Fibre channel with already does what we want for hardware RAID.

This is the second of three diffs for autoconf(9) to find the root
device automatically, jmatthew previously sent the first one.  Third
one follows in a separate mail.

Feedback? OK?


Index: sparc64/autoconf.c
===
RCS file: /cvs/src/sys/arch/sparc64/sparc64/autoconf.c,v
retrieving revision 1.133
diff -u -p -r1.133 autoconf.c
--- sparc64/autoconf.c  15 Oct 2019 05:21:16 -  1.133
+++ sparc64/autoconf.c  29 Dec 2019 06:05:44 -
@@ -1455,8 +1455,9 @@ device_register(struct device *dev, void
u_int lun = bp->val[1];
 
if (bp->val[0] & 0x && bp->val[0] != -1) {
-   /* Fibre channel? */
-   if (bp->val[0] == sl->port_wwn && lun == sl->lun) {
+   /* Hardware RAID or Fibre channel? */
+   if ((bp->val[0] == sl->port_wwn + 0x3000 ||
+bp->val[0] == sl->port_wwn) && lun == sl->lun) {
nail_bootdev(dev, bp);
}
 



Re: sparc64: find root device on hardware RAID

2019-12-28 Thread Klemens Nanni
On Sun, Dec 29, 2019 at 01:59:38PM +1000, Jonathan Matthew wrote:
> I think we have the wrong size for the volume name, hence the difference
> between the size reported by the controller and the size of vpg.
Indeed, good catch!

OBP's `create-raid*-volume' commands also prompt for names no longer
than that:

{0} ok 9 b c d create-raid0-volume
...
Enter a volume name:  [0 to 15 characters] foo
{0} ok

> try this out?
Just works, the WWID is no longer clobbered and autoconf eventually sees
it in the port WWN:

mpii0 at pci15 dev 0 function 0 "Symbios Logic SAS2008" rev 0x03: msi
mpii0: Solana On-Board, firmware 9.0.0.0 IR, MPI 2.0
scsibus1 at mpii0: 834 targets
mpii_scsi_probe: target 0 lun 0 port_wwn 0 node_wwn 0 has 
MPII_DF_VOLUME set in flags 10
struct mpii_cfg_raid_vol_pg1 vpg:
volume_id: 81, tvolume_bus: 3, volume_ioc: 0
wwid: aa32290d5dcd16c
sd0 at scsibus1 targ 0 lun 0:  
naa.600508e06cd1dcd59022a30a
device_register: RAID:
bp->val[]: 3aa32290d5dcd16c, 0, 0
target: d5dcd16c, sl->target: 0
lun: 0, sl->lun: 0
sl->port_wwn: aa32290d5dcd16c, sl->node_wwn: 0

sd0: 713824MB, 512 bytes/sector, 1461911552 sectors

Thanks a lot,
OK kn

Now I need to work around the first digit's mismatch;  for reasons still
unknown to me, official documentation states that the RAID volume WWID's
first digit --if it is zero-- must be replaced with three,  so the
bootpath contains 3aa32290d5dcd16c whereas the port WWN has the correct
aa32290d5dcd16c.

Fix that and the kernel will match the device and find its root device
automatically.  I get around to a diff for that now.



Re: sparc64: find root device on hardware RAID

2019-12-28 Thread Jonathan Matthew
On Sun, Dec 29, 2019 at 03:30:15AM +0100, Klemens Nanni wrote:
> On Sun, Dec 29, 2019 at 10:29:48AM +1000, Jonathan Matthew wrote:
> > > + memset(, 0, sizeof(vpg));
> > > + pagelen = hdr.page_length * 4;
> > 
> > We probably should check that this isn't larger than the size of vpg.
> pagelen is 64, sizeof(vpg) is 80.
> 
> > link->target isn't the right place to put this, for one thing it's only 16 
> > bits
> > and the wwn is 64 bits, and it's used throughout the driver to look up 
> > devices
> > in an array, so changing it will break things.  I think link->port_wwn is 
> > the
> > right place to store it.
> Ah, link->target was there because I played with that in earlier diffs,
> port_wwn is indeed correct here.
> 
> > The fields in the page returned by the driver are also little endian, so 
> > you'd
> > need letoh64(vpg.wwid) here.
> Thanks, I see that is done elsewhere in the driver, too.
>  
> > You should still return 0 here, as continuing on will send the SAS device
> > page 0 request to the raid volume, which will probably upset the controller
> > enough to stop talking to you.
> Oh well... that explains the hangs - I accidentially dropped the return,
> it should obviously stay and my diff should only add another page fetch.
> 
> With the return the kernel no longer loops in mpii_wait() and boots fine.
> 
> vpg.wwid however is zero;  the other members volume_id, volume_bus, and
> volume_ioc are set/non-zero, guid contains "LSI" and name contains
> "ssd1e" which I how I named this RAID volume in OBP.
> 
> So why are those bits filled in but not the WWID?

I think we have the wrong size for the volume name, hence the difference
between the size reported by the controller and the size of vpg.

try this out?


diff --git sys/dev/pci/mpiireg.h sys/dev/pci/mpiireg.h
index 638f31171d1..11dacf86953 100644
--- sys/dev/pci/mpiireg.h
+++ sys/dev/pci/mpiireg.h
@@ -1355,7 +1355,7 @@ struct mpii_cfg_raid_vol_pg1 {
 
u_int8_tguid[24];
 
-   u_int8_tname[32];
+   u_int8_tname[16];
 
u_int64_t   wwid;
 



Re: sparc64: find root device on hardware RAID

2019-12-28 Thread Klemens Nanni
On Sun, Dec 29, 2019 at 10:29:48AM +1000, Jonathan Matthew wrote:
> > +   memset(, 0, sizeof(vpg));
> > +   pagelen = hdr.page_length * 4;
> 
> We probably should check that this isn't larger than the size of vpg.
pagelen is 64, sizeof(vpg) is 80.

> link->target isn't the right place to put this, for one thing it's only 16 
> bits
> and the wwn is 64 bits, and it's used throughout the driver to look up devices
> in an array, so changing it will break things.  I think link->port_wwn is the
> right place to store it.
Ah, link->target was there because I played with that in earlier diffs,
port_wwn is indeed correct here.

> The fields in the page returned by the driver are also little endian, so you'd
> need letoh64(vpg.wwid) here.
Thanks, I see that is done elsewhere in the driver, too.
 
> You should still return 0 here, as continuing on will send the SAS device
> page 0 request to the raid volume, which will probably upset the controller
> enough to stop talking to you.
Oh well... that explains the hangs - I accidentially dropped the return,
it should obviously stay and my diff should only add another page fetch.

With the return the kernel no longer loops in mpii_wait() and boots fine.

vpg.wwid however is zero;  the other members volume_id, volume_bus, and
volume_ioc are set/non-zero, guid contains "LSI" and name contains
"ssd1e" which I how I named this RAID volume in OBP.

So why are those bits filled in but not the WWID?



Re: net80211: post-bgscan RSSI threshold check

2019-12-28 Thread Patrick Dohman


> On Dec 28, 2019, at 6:11 AM, Stefan Sperling  wrote:
> 
> Access points at 36c3 use low transmit power on purpose, and often fall below
> the RSSI threshold which trigger background scans. At some locations (e.g.
> at the lake in CCL) I've seen iwm(4) ping-pong between APs repeatedly even
> while the laptop is stationary.
> 
> I am now running with the diff below which prevents roaming to a new AP
> with an RSSI level below the background scan threshold. In other words,
> if we can tell ahead of time that the new candiate AP will also trigger
> background scans then there is little point in switching to it.

My understanding is that RSSI is a valid consideration in a soft handover.
Do you consider soft handovers a secure roaming implementation?
Is a hard handover option safer & simpler?



Re: cdio(1): remove CDDB support

2019-12-28 Thread Bryan Steele
On Sat, Dec 28, 2019 at 08:03:17PM -0500, Bryan Steele wrote:
> On Sat, Dec 28, 2019 at 07:48:47PM -0500, Bryan Steele wrote:
> > With FreeDB announcing[0] that the service will be shutting down as of
> > March 31st of 2020, and the only other alternative (MusicBrainz) already
> > having shutdown their freedb/cddb gateway in favour of their own API
> > early this year, it likely makes sense to remove support from cdio(1).
> > 
> > CDDB is used to retrieve music CD metadata over the Internet, e.g:
> > Artist and Track names.
> > 
> > I left in support for the "cdid" command as it may be useful for
> > archival(?) purposes, if not that can go too.
> > 
> > Cc: espie@ as he wrote this code, & maybe he still has music on CDs.
> > 
> > ok?
> > 
> > -Bryan.
> > 
> > [0] http://www.freedb.org/en/
> > [1] 
> > https://blog.metabrainz.org/2018/09/18/freedb-gateway-end-of-life-notice-march-18-2019/
> 
> First diff missed a few things..

Not looking for okays now, too soon. Maybe a replacement will show up.
Sorry for jumping the gun.



Re: cdio(1): remove CDDB support

2019-12-28 Thread Bryan Steele
On Sat, Dec 28, 2019 at 07:48:47PM -0500, Bryan Steele wrote:
> With FreeDB announcing[0] that the service will be shutting down as of
> March 31st of 2020, and the only other alternative (MusicBrainz) already
> having shutdown their freedb/cddb gateway in favour of their own API
> early this year, it likely makes sense to remove support from cdio(1).
> 
> CDDB is used to retrieve music CD metadata over the Internet, e.g:
> Artist and Track names.
> 
> I left in support for the "cdid" command as it may be useful for
> archival(?) purposes, if not that can go too.
> 
> Cc: espie@ as he wrote this code, & maybe he still has music on CDs.
> 
> ok?
> 
> -Bryan.
> 
> [0] http://www.freedb.org/en/
> [1] 
> https://blog.metabrainz.org/2018/09/18/freedb-gateway-end-of-life-notice-march-18-2019/

First diff missed a few things..

Index: Makefile
===
RCS file: /cvs/src/usr.bin/cdio/Makefile,v
retrieving revision 1.6
diff -u -p -u -r1.6 Makefile
--- usr.bin/cdio/Makefile   29 Nov 2008 08:57:10 -  1.6
+++ usr.bin/cdio/Makefile   29 Dec 2019 00:58:58 -
@@ -3,7 +3,7 @@
 PROG=  cdio
 DPADD= ${LIBUTIL} ${LIBEDIT} ${LIBTERMCAP}
 LDADD= -lutil -ledit -ltermcap -lsndio
-SRCS=  cdio.c cddb.c mmc.c rip.c
+SRCS=  cdio.c mmc.c rip.c
 CDIAGFLAGS=-Wall -W -Wmissing-prototypes -pedantic
 
 .include 
Index: cddb.c
===
RCS file: cddb.c
diff -N cddb.c
--- usr.bin/cdio/cddb.c 7 Dec 2017 02:08:44 -   1.22
+++ /dev/null   1 Jan 1970 00:00:00 -
@@ -1,396 +0,0 @@
-/* $OpenBSD: cddb.c,v 1.22 2017/12/07 02:08:44 krw Exp $ */
-/*
- * Copyright (c) 2002 Marc Espie.
- *
- * Redistribution and use in source and binary forms, with or without
- * modification, are permitted provided that the following conditions
- * are met:
- * 1. Redistributions of source code must retain the above copyright
- *notice, this list of conditions and the following disclaimer.
- * 2. Redistributions in binary form must reproduce the above copyright
- *notice, this list of conditions and the following disclaimer in the
- *documentation and/or other materials provided with the distribution.
- *
- * THIS SOFTWARE IS PROVIDED BY THE OPENBSD PROJECT AND CONTRIBUTORS
- * ``AS IS'' AND ANY EXPRESS OR IMPLIED WARRANTIES, INCLUDING, BUT NOT
- * LIMITED TO, THE IMPLIED WARRANTIES OF MERCHANTABILITY AND FITNESS FOR
- * A PARTICULAR PURPOSE ARE DISCLAIMED.  IN NO EVENT SHALL THE OPENBSD
- * PROJECT OR CONTRIBUTORS BE LIABLE FOR ANY DIRECT, INDIRECT, INCIDENTAL,
- * SPECIAL, EXEMPLARY, OR CONSEQUENTIAL DAMAGES (INCLUDING, BUT NOT
- * LIMITED TO, PROCUREMENT OF SUBSTITUTE GOODS OR SERVICES; LOSS OF USE,
- * DATA, OR PROFITS; OR BUSINESS INTERRUPTION) HOWEVER CAUSED AND ON ANY
- * THEORY OF LIABILITY, WHETHER IN CONTRACT, STRICT LIABILITY, OR TORT
- * (INCLUDING NEGLIGENCE OR OTHERWISE) ARISING IN ANY WAY OUT OF THE USE
- * OF THIS SOFTWARE, EVEN IF ADVISED OF THE POSSIBILITY OF SUCH DAMAGE.
- */
-
-#include 
-#include 
-#include 
-#include 
-#include 
-#include 
-#include 
-#include 
-#include 
-#include 
-#include 
-#include "extern.h"
-
-unsigned long  cddb_sum(unsigned long);
-void   send_hello(FILE *);
-void   send_query(FILE *, int, struct cd_toc_entry *);
-intfurther_query(FILE *, char *);
-intconnect_to(const char *, const char *);
-intparse_connect_to(const char *, const char *);
-char * get_line(FILE *);
-char * get_answer(FILE *);
-void   verify_track_names(char **, int, struct cd_toc_entry *);
-void   safe_copy(char **, const char *);
-
-unsigned long
-cddb_sum(unsigned long v)
-{
-   unsigned long sum = 0;
-
-   while (v > 0) {
-   sum += v % 10;
-   v /= 10;
-   }
-   return (sum);
-}
-
-unsigned long
-cddb_discid(int n, struct cd_toc_entry *e)
-{
-   unsigned long sum;
-   int i;
-
-   sum = 0;
-   for (i =0; i < n; i++)
-   sum += cddb_sum(entry2time(e+i));
-   return (((sum % 0xff) << 24) |
-   ((entry2time(e+n) - entry2time(e)) << 8) | n);
-}
-
-void
-send_hello(FILE *cout)
-{
-   char hostname[HOST_NAME_MAX+1];
-
-   if (gethostname(hostname, sizeof(hostname)) == -1)
-   strlcpy(hostname, "unknown", sizeof hostname);
-   fprintf(cout, "CDDB HELLO %s %s cdio " VERSION "\r\n",
-   getlogin(), hostname);
-   fflush(cout);
-}
-
-void
-send_query(FILE *f, int n, struct cd_toc_entry *e)
-{
-   int i;
-
-   fprintf(f, "cddb query %8lx %d", cddb_discid(n, e), n);
-   for (i = 0; i < n; i++)
-   fprintf(f, " %lu", entry2frames(e+i));
-   fprintf(f, " %lu\r\n", (entry2frames(e+n)-entry2frames(e)) /75);
-   fflush(f);
-}
-
-#define MAXSIZE 256
-char copy_buffer[MAXSIZE];
-
-void
-safe_copy(char **p, const char *title)
-{
-   strnvis(copy_buffer, title, MAXSIZE-1, 

cdio(1): remove CDDB support

2019-12-28 Thread Bryan Steele
With FreeDB announcing[0] that the service will be shutting down as of
March 31st of 2020, and the only other alternative (MusicBrainz) already
having shutdown their freedb/cddb gateway in favour of their own API
early this year, it likely makes sense to remove support from cdio(1).

CDDB is used to retrieve music CD metadata over the Internet, e.g:
Artist and Track names.

I left in support for the "cdid" command as it may be useful for
archival(?) purposes, if not that can go too.

Cc: espie@ as he wrote this code, & maybe he still has music on CDs.

ok?

-Bryan.

[0] http://www.freedb.org/en/
[1] 
https://blog.metabrainz.org/2018/09/18/freedb-gateway-end-of-life-notice-march-18-2019/

Index: Makefile
===
RCS file: /cvs/src/usr.bin/cdio/Makefile,v
retrieving revision 1.6
diff -u -p -u -r1.6 Makefile
--- Makefile29 Nov 2008 08:57:10 -  1.6
+++ Makefile29 Dec 2019 00:34:51 -
@@ -3,7 +3,7 @@
 PROG=  cdio
 DPADD= ${LIBUTIL} ${LIBEDIT} ${LIBTERMCAP}
 LDADD= -lutil -ledit -ltermcap -lsndio
-SRCS=  cdio.c cddb.c mmc.c rip.c
+SRCS=  cdio.c mmc.c rip.c
 CDIAGFLAGS=-Wall -W -Wmissing-prototypes -pedantic
 
 .include 
Index: cddb.c
===
RCS file: cddb.c
diff -N cddb.c
--- cddb.c  7 Dec 2017 02:08:44 -   1.22
+++ /dev/null   1 Jan 1970 00:00:00 -
@@ -1,396 +0,0 @@
-/* $OpenBSD: cddb.c,v 1.22 2017/12/07 02:08:44 krw Exp $ */
-/*
- * Copyright (c) 2002 Marc Espie.
- *
- * Redistribution and use in source and binary forms, with or without
- * modification, are permitted provided that the following conditions
- * are met:
- * 1. Redistributions of source code must retain the above copyright
- *notice, this list of conditions and the following disclaimer.
- * 2. Redistributions in binary form must reproduce the above copyright
- *notice, this list of conditions and the following disclaimer in the
- *documentation and/or other materials provided with the distribution.
- *
- * THIS SOFTWARE IS PROVIDED BY THE OPENBSD PROJECT AND CONTRIBUTORS
- * ``AS IS'' AND ANY EXPRESS OR IMPLIED WARRANTIES, INCLUDING, BUT NOT
- * LIMITED TO, THE IMPLIED WARRANTIES OF MERCHANTABILITY AND FITNESS FOR
- * A PARTICULAR PURPOSE ARE DISCLAIMED.  IN NO EVENT SHALL THE OPENBSD
- * PROJECT OR CONTRIBUTORS BE LIABLE FOR ANY DIRECT, INDIRECT, INCIDENTAL,
- * SPECIAL, EXEMPLARY, OR CONSEQUENTIAL DAMAGES (INCLUDING, BUT NOT
- * LIMITED TO, PROCUREMENT OF SUBSTITUTE GOODS OR SERVICES; LOSS OF USE,
- * DATA, OR PROFITS; OR BUSINESS INTERRUPTION) HOWEVER CAUSED AND ON ANY
- * THEORY OF LIABILITY, WHETHER IN CONTRACT, STRICT LIABILITY, OR TORT
- * (INCLUDING NEGLIGENCE OR OTHERWISE) ARISING IN ANY WAY OUT OF THE USE
- * OF THIS SOFTWARE, EVEN IF ADVISED OF THE POSSIBILITY OF SUCH DAMAGE.
- */
-
-#include 
-#include 
-#include 
-#include 
-#include 
-#include 
-#include 
-#include 
-#include 
-#include 
-#include 
-#include "extern.h"
-
-unsigned long  cddb_sum(unsigned long);
-void   send_hello(FILE *);
-void   send_query(FILE *, int, struct cd_toc_entry *);
-intfurther_query(FILE *, char *);
-intconnect_to(const char *, const char *);
-intparse_connect_to(const char *, const char *);
-char * get_line(FILE *);
-char * get_answer(FILE *);
-void   verify_track_names(char **, int, struct cd_toc_entry *);
-void   safe_copy(char **, const char *);
-
-unsigned long
-cddb_sum(unsigned long v)
-{
-   unsigned long sum = 0;
-
-   while (v > 0) {
-   sum += v % 10;
-   v /= 10;
-   }
-   return (sum);
-}
-
-unsigned long
-cddb_discid(int n, struct cd_toc_entry *e)
-{
-   unsigned long sum;
-   int i;
-
-   sum = 0;
-   for (i =0; i < n; i++)
-   sum += cddb_sum(entry2time(e+i));
-   return (((sum % 0xff) << 24) |
-   ((entry2time(e+n) - entry2time(e)) << 8) | n);
-}
-
-void
-send_hello(FILE *cout)
-{
-   char hostname[HOST_NAME_MAX+1];
-
-   if (gethostname(hostname, sizeof(hostname)) == -1)
-   strlcpy(hostname, "unknown", sizeof hostname);
-   fprintf(cout, "CDDB HELLO %s %s cdio " VERSION "\r\n",
-   getlogin(), hostname);
-   fflush(cout);
-}
-
-void
-send_query(FILE *f, int n, struct cd_toc_entry *e)
-{
-   int i;
-
-   fprintf(f, "cddb query %8lx %d", cddb_discid(n, e), n);
-   for (i = 0; i < n; i++)
-   fprintf(f, " %lu", entry2frames(e+i));
-   fprintf(f, " %lu\r\n", (entry2frames(e+n)-entry2frames(e)) /75);
-   fflush(f);
-}
-
-#define MAXSIZE 256
-char copy_buffer[MAXSIZE];
-
-void
-safe_copy(char **p, const char *title)
-{
-   strnvis(copy_buffer, title, MAXSIZE-1, VIS_TAB|VIS_NL);
-   if (*p == NULL)
-   *p = strdup(copy_buffer);
-   else {
-   char *n;
-
-   if (asprintf(, "%s%s", *p, copy_buffer) == 

Re: sparc64: find root device on hardware RAID

2019-12-28 Thread Jonathan Matthew
On Fri, Dec 27, 2019 at 07:50:34PM +0100, Klemens Nanni wrote:
> On Fri, Dec 27, 2019 at 09:46:56AM +0100, Mike Belopuhov wrote:
> > Looks like WWID for the RAID volume can be read from the RAID Volume
> > Page 1 (mpii_cfg_raid_vol_pg1).
> jmatthew also suggested that, thanks.
> 
> I'm looking into now mpii(4) and already had a rather naive attempt at
> setting the SCSI target to the volume's WWID, but with no avail.
> 
> Diff below is what I booted last, but for reasons yet unkown to me the
> kernel just hangs afer debug printf()
> 
>   ...
>   mpii0 at pci15 dev 0 function 0 "Symbios Logic SAS2008" rev 0x03: msi   
>
>   mpii0: Solana On-Board, firmware 9.0.0.0 IR, MPI 2.0
>
>   scsibus1 at mpii0: 834 targets  
>
>   mpii_scsi_probe: target 0 lun 0 port_wwn 0 node_wwn 0 has 
> MPII_DF_VOLUME set in flags 10
> 
> and the machine must be reset.  So something is wrong with this diff and
> I need to get more familiar with this code, but one can also observe
> lun->target = vpg.wwid = 0 which I did not expect;  perhaps the driver
> currently does not obtain the volume's WWID at all or incorrectly?  Or
> perhaps I am missing steps prior to fetching the page;  current mpii(4)
> does not seem to use struct mpii_cfg_raid_vol_pg1 at all.
> 
> Index: mpii.c
> ===
> RCS file: /cvs/src/sys/dev/pci/mpii.c,v
> retrieving revision 1.121
> diff -u -p -r1.121 mpii.c
> --- mpii.c12 Sep 2019 22:22:53 -  1.121
> +++ mpii.c27 Dec 2019 14:51:36 -
> @@ -909,8 +909,33 @@ mpii_scsi_probe(struct scsi_link *link)
>   if (ISSET(flags, MPII_DF_HIDDEN) || ISSET(flags, MPII_DF_UNUSED))
>   return (1);
>  
> - if (ISSET(flags, MPII_DF_VOLUME))
> - return (0);
> + if (ISSET(flags, MPII_DF_VOLUME)) {
> + struct mpii_cfg_hdr hdr;
> + struct mpii_cfg_raid_vol_pg1 vpg;
> + size_t pagelen;
> +
> + address = MPII_CFG_RAID_VOL_ADDR_HANDLE | dev->dev_handle;
> +
> + if (mpii_req_cfg_header(sc, MPII_CONFIG_REQ_PAGE_TYPE_RAID_VOL,
> + 1, address, MPII_PG_POLL, ) != 0)
> + return (EINVAL);
> +
> + memset(, 0, sizeof(vpg));
> + pagelen = hdr.page_length * 4;

We probably should check that this isn't larger than the size of vpg.

> +
> + if (mpii_req_cfg_page(sc, address, MPII_PG_POLL, , 1,
> + , pagelen) != 0)
> + return (EINVAL);
> +
> + link->target = vpg.wwid;

link->target isn't the right place to put this, for one thing it's only 16 bits
and the wwn is 64 bits, and it's used throughout the driver to look up devices
in an array, so changing it will break things.  I think link->port_wwn is the
right place to store it.

The fields in the page returned by the driver are also little endian, so you'd
need letoh64(vpg.wwid) here.

> +
> + printf("%s: target %x lun %x"
> + " port_wwn %llx node_wwn %llx"
> + " has MPII_DF_VOLUME set in flags %x\n",
> + __func__, link->target, link->lun,
> + link->port_wwn, link->node_wwn,
> + flags);


You should still return 0 here, as continuing on will send the SAS device
page 0 request to the raid volume, which will probably upset the controller
enough to stop talking to you.

> + }
>  
>   memset(, 0, sizeof(ehdr));
>   ehdr.page_type = MPII_CONFIG_REQ_PAGE_TYPE_EXTENDED;
> 
> 
> The previous version of this diff put vpg on the heap, e.g.
> 
> + struct mpii_cfg_raid_vol_pg1 *vpg;
> + vpg = malloc(pagelen, M_TEMP, M_WAITOK | M_CANFAIL | M_ZERO);
>   ...
> 
> just like it is done for the mpii_cfg_raid_vol_pg0 struct in
> mpii_ioctl_cache(), which is where I copied the code from to fetch pages.
> 
> But with this, the kernel paniced:
> 
> mpii_scsi_probe: target beef lun 0 port_wwn 0 node_wwn 0 has MPII_DF_VOLUME 
> set in flags 10
> panic: kernel data fault: pc=165e310 addr=40090fae000
> panic: Unable to send mondo 1011fa4 to cpu 0: 6
> Stopped at  db_enter+0x8:   nop
> TIDPIDUID PRFLAGS PFLAGS  CPU  COMMAND
> * 0  0  0 0x1  0x2000K swapper
> sun4v_send_ipi(0, 1011fa4, 0, 6, 0, 16) at sun4v_send_ipi+0xac
> db_enter_ddb(419aa7f8000, a, 1c3, 2007c68, 3f, 78) at db_enter_ddb+0x244
> db_ktrap(101, 20074a0, 1, 0, 0, 2007728) at db_ktrap+0x104
> trap(20074a0, 101, 11e55e4, 820006, 0, 78) at trap+0x2c0
> Lslowtrap_reenter(1, 20077f8, 175adf8, 20077f8, 193f570, cb) at 
> Lslowtrap_reenter+0xf8
> panic(175adf8, 165e310, 40090fae000, 20077f8, 1ca1000, 100) at panic+0xb8
> data_access_fault(20078f0, 31, 165e310, 40090fae000, 40090fae000, 1) at 
> 

Re: sparc64: find root device on hardware RAID

2019-12-28 Thread Klemens Nanni
On Fri, Dec 27, 2019 at 07:50:34PM +0100, Klemens Nanni wrote:
> Diff below is what I booted last, but for reasons yet unkown to me the
> kernel just hangs afer debug printf()
>
>   ...
>   mpii0 at pci15 dev 0 function 0 "Symbios Logic SAS2008" rev 0x03: msi
>   mpii0: Solana On-Board, firmware 9.0.0.0 IR, MPI 2.0
>   scsibus1 at mpii0: 834 targets
>   mpii_scsi_probe: target 0 lun 0 port_wwn 0 node_wwn 0 has 
> MPII_DF_VOLUME set in flags 10
More specifically, the driver hangs here:

2839 void
2840 mpii_wait(struct mpii_softc *sc, struct mpii_ccb *ccb)
2841 {
2842struct mutexmtx = MUTEX_INITIALIZER(IPL_BIO);
2843void(*done)(struct mpii_ccb *);
2844void*cookie;
2845
2846done = ccb->ccb_done;
2847cookie = ccb->ccb_cookie;
2848
2849ccb->ccb_done = mpii_wait_done;
2850ccb->ccb_cookie = 
2851
2852/* XXX this will wait forever for the ccb to complete */
2853
2854mpii_start(sc, ccb);
2855
2856mtx_enter();
2857while (ccb->ccb_cookie != NULL)
2858msleep(ccb, , PRIBIO, "mpiiwait", 0);
2859mtx_leave();
2860
2861ccb->ccb_cookie = cookie;
2862done(ccb);
2863 }

mpii_start() returns then mpii_wait() "wait[s] forever".  I'm still
practically lost in this area.

Why does it hang there only if I fetch the `struct mpii_cfg_raid_vol_pg1'
page for its wwid member in mpii_scsi_probe() as per the previous diff?

The commit which introduced the XXX:

revision 1.31
date: 2010/07/07 10:29:17;  author: dlg;  state: Exp;  lines: +52 -34;
bring mpi_wait over to mpii for an mpsafe mechanism to sleep while 
waiting
for a command to complete. this also replaces all the while (!ready) \
tsleep() wrapped in splbio code with mpii_wait.

tested with bioctl runs and sensor updates on a raid volume



sort: do not perform top level comparison if -k supplied with -c

2019-12-28 Thread Richard Ipsum
Hi,

I think there may be a bug in OpenBSD's sort utility.
The bug is that when -c is used in combination with a key field,
a "top level" sort is performed when the key field does not have
disorder. This differs from what might be expected and certainly from
what occurs with other versions of sort.

Given the input file 'unsorted_csv':

,,
,,
,,
,,
,,
,,

On Linux:

$ sort -c -t , -k 2f unsorted_csv 
$ echo $?
0

On OpenBSD:

$ sort -c -t , -k 2f unsorted_csv
sort: unsorted_csv:2: disorder: ,,
$ echo $?
1

The patch below seems to fix this issue.

Thanks,
Richard

diff --git file.c file.c
index 9d84d7cb4f6..b6bbf1e2b4c 100644
--- file.c
+++ file.c
@@ -387,7 +387,8 @@ check(const char *fn)
printf("; cmp1=%d", cmp);
 
if (!cmp && sort_opts_vals.complex_sort &&
-   !(sort_opts_vals.uflag) && !(sort_opts_vals.sflag)) {
+   !(sort_opts_vals.uflag) && !(sort_opts_vals.sflag) &&
+   !(sort_opts_vals.kflag)) {
cmp = top_level_str_coll(s2, s1);
if (debug_sort)
printf("; cmp2=%d", cmp);



Re: ksh: support "function name()"

2019-12-28 Thread Andras Farkas
On Sat, Dec 28, 2019 at 10:08 AM Mark Kettenis  wrote:
> [snip]
> Are there other ksh implementations that have this "feature"?
As for this question, I can at least confirm that no version of ksh93 has it.



Re: ksh: support "function name()"

2019-12-28 Thread Klemens Nanni
On Sat, Dec 28, 2019 at 04:07:02PM +0100, Mark Kettenis wrote:
> Are there other ksh implementations that have this "feature"?
MirBSD's ksh allows all three forms but treats `function name()' like
`name()', that is $0 stays the same and will not be set to the funtion's
name:

$ echo $KSH_VERSION
@(#)MIRBSD KSH R57 2019/03/01
$ function f { echo $0; }
$ f2() { echo $0; }
$ function f3() { echo $0; }
$ typeset -f
function f {
\echo $0 
} 
f2() {
\echo $0 
} 
f3() {
\echo $0 
} 
$ f
f
$ f2
mksh
$ f3
mksh



Re: ksh: support "function name()"

2019-12-28 Thread Klemens Nanni
On Sat, Dec 28, 2019 at 09:53:28AM -0500, Andras Farkas wrote:
> That said, I personally think to define a function with both
> 'function' and '()' is a genuine syntax error.
Right now it definitely is a syntax error, what that is what this diff
tries to fix ;-)

I think compatibility to other Bourne-like shells is preffered to
pedantic behaviour here, especially since it comes at no cost.



Re: ksh: support "function name()"

2019-12-28 Thread Mark Kettenis
> From: Jeremie Courreges-Anglas 
> Date: Sat, 28 Dec 2019 14:40:27 +0100
> 
> We have a few ports (~12) patched because of shell script constructs
> like
> 
>   function usage()
>   {

What is the #! for those scripts?

> which are rejected by our ksh.  Indeed ksh only supports either
> 
>   usage()
>   {
> 
> or
> 
>   function usage
>   {
> 
> Both bash and zsh also allow an optional "()".  The diff below
> implements the missing bits.

But our ksh isn't bash or zsh!

Are there other ksh implementations that have this "feature"?

> Since the "reject = true;" mechanism bypasses yylex(), I have to
> pass token() the same flags as with the musthave('{') call below.
> 
> ok?
> 
> 
> Index: ksh.1
> ===
> RCS file: /d/cvs/src/bin/ksh/ksh.1,v
> retrieving revision 1.208
> diff -u -p -r1.208 ksh.1
> --- ksh.1 26 Nov 2019 22:49:01 -  1.208
> +++ ksh.1 27 Dec 2019 12:27:37 -
> @@ -679,7 +679,7 @@ The exit status of a
>  statement is the last exit status of the
>  .Ar list
>  in the body of the loop; if the body is not executed, the exit status is 
> zero.
> -.It Xo Ic function Ar name
> +.It Xo Ic function Ar name Op ()
>  .No { Ar list ; No }
>  .Xc
>  Defines the function
> Index: syn.c
> ===
> RCS file: /d/cvs/src/bin/ksh/syn.c,v
> retrieving revision 1.39
> diff -u -p -r1.39 syn.c
> --- syn.c 24 Apr 2018 08:25:16 -  1.39
> +++ syn.c 27 Dec 2019 11:25:41 -
> @@ -555,6 +555,12 @@ function_body(char *name,
>* an open-brace.
>*/
>   if (ksh_func) {
> + /* allow optional () after function name */
> + if (token(CONTIN|KEYWORD|ALIAS) == '(')
> + musthave(')', 0);
> + else
> + reject = true;
> +
>   musthave('{', CONTIN|KEYWORD|ALIAS); /* } */
>   reject = true;
>   }
> 
> 
> -- 
> jca | PGP : 0x1524E7EE / 5135 92C1 AD36 5293 2BDF  DDCC 0DFA 74AE 1524 E7EE
> 
> 



Re: ksh: support "function name()"

2019-12-28 Thread Klemens Nanni
On Sat, Dec 28, 2019 at 02:40:27PM +0100, Jeremie Courreges-Anglas wrote:
> We have a few ports (~12) patched because of shell script constructs
> like
> 
>   function usage()
>   {
> 
> which are rejected by our ksh.  Indeed ksh only supports either
> 
>   usage()
>   {
> 
> or
> 
>   function usage
>   {
> 
> Both bash and zsh also allow an optional "()".  The diff below
> implements the missing bits.
Thanks, I wanted this as well for some time.

> Since the "reject = true;" mechanism bypasses yylex(), I have to
> pass token() the same flags as with the musthave('{') call below.
> 
> ok?
Defining, listing and undefining works.  As per the differences between
`function name' and `name()', your new `function name()' behaves like
the former.  This should be clarified in the manual.

The Functions paragraph starts with repeating the currently two possible
forms, either remove the duplicate work there or adjust accordingly.  It
also goes into detail about the differences, e.g. `$0' being different;
strictly speaking this must be clarified as well, since the new form
`funtion name()' now satisfies both criteria: "Functions defined with
the function reserved word" and "functions defined with the () notation".

> Index: ksh.1
> ===
> RCS file: /d/cvs/src/bin/ksh/ksh.1,v
> retrieving revision 1.208
> diff -u -p -r1.208 ksh.1
> --- ksh.1 26 Nov 2019 22:49:01 -  1.208
> +++ ksh.1 27 Dec 2019 12:27:37 -
> @@ -679,7 +679,7 @@ The exit status of a
>  statement is the last exit status of the
>  .Ar list
>  in the body of the loop; if the body is not executed, the exit status is 
> zero.
> -.It Xo Ic function Ar name
> +.It Xo Ic function Ar name Op ()
There must be no space between `name' and `['.

>  .No { Ar list ; No }
>  .Xc
>  Defines the function



Re: ksh: support "function name()"

2019-12-28 Thread Andras Farkas
If this diff gets accepted, in ksh's man page, you'll probably have to
change the following line as it's not entirely disambiguous how a
function would behave if it had both 'function' and '()' where it was
defined:
"Functions defined with the function reserved word are treated
differently in the following ways from functions defined with the ()
notation:"
Notably, would someone learning ksh realise 'function funname()' isn't
being defined with both notations at once?
Examples might be:
"Functions defined with the function reserved word are treated
differently in the following ways from functions defined solely with
the () notation:"
"Functions defined with the function reserved word are treated
differently in the following ways from functions defined without it:"

That said, I personally think to define a function with both
'function' and '()' is a genuine syntax error.

On Sat, Dec 28, 2019 at 8:42 AM Jeremie Courreges-Anglas  
wrote:
>
>
> We have a few ports (~12) patched because of shell script constructs
> like
>
>   function usage()
>   {
>
> which are rejected by our ksh.  Indeed ksh only supports either
>
>   usage()
>   {
>
> or
>
>   function usage
>   {
>
> Both bash and zsh also allow an optional "()".  The diff below
> implements the missing bits.
>
> Since the "reject = true;" mechanism bypasses yylex(), I have to
> pass token() the same flags as with the musthave('{') call below.
>
> ok?
>
>
> Index: ksh.1
> ===
> RCS file: /d/cvs/src/bin/ksh/ksh.1,v
> retrieving revision 1.208
> diff -u -p -r1.208 ksh.1
> --- ksh.1   26 Nov 2019 22:49:01 -  1.208
> +++ ksh.1   27 Dec 2019 12:27:37 -
> @@ -679,7 +679,7 @@ The exit status of a
>  statement is the last exit status of the
>  .Ar list
>  in the body of the loop; if the body is not executed, the exit status is 
> zero.
> -.It Xo Ic function Ar name
> +.It Xo Ic function Ar name Op ()
>  .No { Ar list ; No }
>  .Xc
>  Defines the function
> Index: syn.c
> ===
> RCS file: /d/cvs/src/bin/ksh/syn.c,v
> retrieving revision 1.39
> diff -u -p -r1.39 syn.c
> --- syn.c   24 Apr 2018 08:25:16 -  1.39
> +++ syn.c   27 Dec 2019 11:25:41 -
> @@ -555,6 +555,12 @@ function_body(char *name,
>  * an open-brace.
>  */
> if (ksh_func) {
> +   /* allow optional () after function name */
> +   if (token(CONTIN|KEYWORD|ALIAS) == '(')
> +   musthave(')', 0);
> +   else
> +   reject = true;
> +
> musthave('{', CONTIN|KEYWORD|ALIAS); /* } */
> reject = true;
> }
>
>
> --
> jca | PGP : 0x1524E7EE / 5135 92C1 AD36 5293 2BDF  DDCC 0DFA 74AE 1524 E7EE
>



Re: increase IEEE80211_CACHE_SIZE

2019-12-28 Thread Peter Hessler
OK


On 2019 Dec 28 (Sat) at 14:27:01 +0100 (+0100), Stefan Sperling wrote:
:The number of entries in the node cache is currently capped to 100.
:
:This limit is outdated. Modern hardware like iwm(4) 8265 supports 46
:distinct channels (1-13, 36-165) each of which can host multiple APs.
:
:The limit is easily reached at 36c6 which makes use of much of the
:available spectrum and provides at least 3 SSIDs on each channel:
:
:$ ifconfig iwm0 scan | grep nwid | wc -l
:  96
:
:So we may be missing out on the best AP to use.
:
:The cache uses an RB tree so performance impact should be negligible.
:
:ok?
:
:diff 5181eb992cbbf64c135f177197957b0e0b427e21 /usr/src
:blob - 7fada592641e683415ffc42cded1c8b27bf39c5c
:file + sys/net80211/ieee80211_node.h
:--- sys/net80211/ieee80211_node.h
:+++ sys/net80211/ieee80211_node.h
:@@ -39,7 +39,7 @@
: #define   IEEE80211_TRANS_WAIT5   /* transition wait */
: #define   IEEE80211_INACT_WAIT5   /* inactivity timer 
interval */
: #define   IEEE80211_INACT_MAX (300/IEEE80211_INACT_WAIT)
:-#define   IEEE80211_CACHE_SIZE100
:+#define   IEEE80211_CACHE_SIZE512
: #define   IEEE80211_CACHE_WAIT30
: #define   IEEE80211_INACT_SCAN10  /* for station mode */
: 
:

-- 
When I was a boy I was told that anybody could become President.
Now I'm beginning to believe it.
-- Clarence Darrow



ksh: support "function name()"

2019-12-28 Thread Jeremie Courreges-Anglas


We have a few ports (~12) patched because of shell script constructs
like

  function usage()
  {

which are rejected by our ksh.  Indeed ksh only supports either

  usage()
  {

or

  function usage
  {

Both bash and zsh also allow an optional "()".  The diff below
implements the missing bits.

Since the "reject = true;" mechanism bypasses yylex(), I have to
pass token() the same flags as with the musthave('{') call below.

ok?


Index: ksh.1
===
RCS file: /d/cvs/src/bin/ksh/ksh.1,v
retrieving revision 1.208
diff -u -p -r1.208 ksh.1
--- ksh.1   26 Nov 2019 22:49:01 -  1.208
+++ ksh.1   27 Dec 2019 12:27:37 -
@@ -679,7 +679,7 @@ The exit status of a
 statement is the last exit status of the
 .Ar list
 in the body of the loop; if the body is not executed, the exit status is zero.
-.It Xo Ic function Ar name
+.It Xo Ic function Ar name Op ()
 .No { Ar list ; No }
 .Xc
 Defines the function
Index: syn.c
===
RCS file: /d/cvs/src/bin/ksh/syn.c,v
retrieving revision 1.39
diff -u -p -r1.39 syn.c
--- syn.c   24 Apr 2018 08:25:16 -  1.39
+++ syn.c   27 Dec 2019 11:25:41 -
@@ -555,6 +555,12 @@ function_body(char *name,
 * an open-brace.
 */
if (ksh_func) {
+   /* allow optional () after function name */
+   if (token(CONTIN|KEYWORD|ALIAS) == '(')
+   musthave(')', 0);
+   else
+   reject = true;
+
musthave('{', CONTIN|KEYWORD|ALIAS); /* } */
reject = true;
}


-- 
jca | PGP : 0x1524E7EE / 5135 92C1 AD36 5293 2BDF  DDCC 0DFA 74AE 1524 E7EE



Re: OpenBSD perl 5.30.1 - Call for Testing

2019-12-28 Thread Stuart Henderson
On 2019/12/26 18:08, Andrew Hewus Fresh wrote:
> Anyone running a speedy bulk ports cluster who could do a full build for
> me would be appreciated.

The only failure in the build which looks like it can be attributed to
the perl update is japanese/kanjips which I've just fixed.

../text2x/text2c -f outheader -o outfile headerfile > header.c
$* is no longer supported as of Perl 5.30 at ../text2x/text2c line 8.

(other failures look like random build errors: gnucash out-of-memory
in guile, and a linker segfault in krita).

No build-time problems seen due to Locale::Codes. I am in favour of this
going in ASAP so we can pick up runtime problems sooner (as far as
Locale::Codes is concerned, we already have it in ports so it would just
be a case of adding the dependency).

OK sthen



increase IEEE80211_CACHE_SIZE

2019-12-28 Thread Stefan Sperling
The number of entries in the node cache is currently capped to 100.

This limit is outdated. Modern hardware like iwm(4) 8265 supports 46
distinct channels (1-13, 36-165) each of which can host multiple APs.

The limit is easily reached at 36c6 which makes use of much of the
available spectrum and provides at least 3 SSIDs on each channel:

$ ifconfig iwm0 scan | grep nwid | wc -l
  96

So we may be missing out on the best AP to use.

The cache uses an RB tree so performance impact should be negligible.

ok?

diff 5181eb992cbbf64c135f177197957b0e0b427e21 /usr/src
blob - 7fada592641e683415ffc42cded1c8b27bf39c5c
file + sys/net80211/ieee80211_node.h
--- sys/net80211/ieee80211_node.h
+++ sys/net80211/ieee80211_node.h
@@ -39,7 +39,7 @@
 #defineIEEE80211_TRANS_WAIT5   /* transition wait */
 #defineIEEE80211_INACT_WAIT5   /* inactivity timer 
interval */
 #defineIEEE80211_INACT_MAX (300/IEEE80211_INACT_WAIT)
-#defineIEEE80211_CACHE_SIZE100
+#defineIEEE80211_CACHE_SIZE512
 #defineIEEE80211_CACHE_WAIT30
 #defineIEEE80211_INACT_SCAN10  /* for station mode */
 



net80211: post-bgscan RSSI threshold check

2019-12-28 Thread Stefan Sperling
Access points at 36c3 use low transmit power on purpose, and often fall below
the RSSI threshold which trigger background scans. At some locations (e.g.
at the lake in CCL) I've seen iwm(4) ping-pong between APs repeatedly even
while the laptop is stationary.

I am now running with the diff below which prevents roaming to a new AP
with an RSSI level below the background scan threshold. In other words,
if we can tell ahead of time that the new candiate AP will also trigger
background scans then there is little point in switching to it.

ok?

diff 5181eb992cbbf64c135f177197957b0e0b427e21 /usr/src
blob - 535c281bdd8e0d4eb22fd5476c8df2e24cb62be8
file + sys/net80211/ieee80211_node.c
--- sys/net80211/ieee80211_node.c
+++ sys/net80211/ieee80211_node.c
@@ -1429,10 +1429,12 @@ ieee80211_end_scan(struct ifnet *ifp)
 
/* 
 * After a background scan we might end up choosing the
-* same AP again. Do not change ic->ic_bss in this case,
-* and make background scans less frequent.
+* same AP again. Or the newly selected AP's RSSI level
+* might be low enough to trigger another background scan.
+* Do not change ic->ic_bss in these cases and make
+* background scans less frequent.
 */
-   if (selbs == curbs) {
+   if (selbs == curbs || !(*ic->ic_node_checkrssi)(ic, selbs)) {
if (ic->ic_bgscan_fail < IEEE80211_BGSCAN_FAIL_MAX) {
if (ic->ic_bgscan_fail <= 0)
ic->ic_bgscan_fail = 1;