On Thu, Jan 27, 2022 at 11:50:25PM +1100, Ross L Richardson wrote:
> [I'm not subscribed to bugs@, but will monitor using MARC.]
>
> >Synopsis: On resume, igc does not pass packets
> >Category: kernel
> >Environment:
> System : OpenBSD 7.0
> Details : OpenBSD 7.0-current (GENERIC.MP) #59: Thu Jan 27 10:27:09
> AEDT 2022
>
> [email protected]:/sys/arch/amd64/compile/GENERIC.MP
>
> Architecture: OpenBSD.amd64
> Machine : amd64
> >Description:
> The problem has been present since the introduction of igc(4).
>
> igc0 is configured with a static IPv4 address.
>
> It works until suspend, but on resume, no packets are passed;
> tcpdump -i igc0 detects 0 packets when trying to ping the gateway.
>
> Everything looks normal (comparing ifconfig output before/after):
> # ifconfig igc0
> igc0: flags=8847<UP,BROADCAST,RUNNING,SIMPLEX,MULTICAST> mtu 1500
> lladdr xx:xx:xx:xx:xx:xx
> index 2 priority 0 llprio 3
> groups: egress
> media: Ethernet autoselect (1000baseT full-duplex)
> status: active
> inet 192.168.1.123 netmask 0xffffff00 broadcast 192.168.1.255
>
> This happens whether or not dhcpleased/resolvd are running, and
> the same problem exists with IPv6.
>
> Nothing extra is logged with ifconfig igc0 debug.
>
> The em(4) card does work across suspend/resume.
>
> (Might it be a hardware issue?)
> >How-To-Repeat:
> Suspend/resume the system.
> >Fix:
> Things usually start working again after
> # ifconfig igc0 down -inet && /bin/sh /etc/netstart
> but not always on the first attempt, and sometimes only after
> a few seconds.
does this activate function adapted from em(4) help?
Index: sys/dev/pci/if_igc.c
===================================================================
RCS file: /cvs/src/sys/dev/pci/if_igc.c,v
retrieving revision 1.6
diff -u -p -r1.6 if_igc.c
--- sys/dev/pci/if_igc.c 9 Jan 2022 23:28:19 -0000 1.6
+++ sys/dev/pci/if_igc.c 28 Jan 2022 04:03:26 -0000
@@ -86,6 +86,7 @@ const struct pci_matchid igc_devices[] =
int igc_match(struct device *, void *, void *);
void igc_attach(struct device *, struct device *, void *);
int igc_detach(struct device *, int);
+int igc_activate(struct device *, int);
void igc_identify_hardware(struct igc_softc *);
int igc_allocate_pci_resources(struct igc_softc *);
@@ -151,7 +152,8 @@ struct cfdriver igc_cd = {
};
struct cfattach igc_ca = {
- sizeof(struct igc_softc), igc_match, igc_attach, igc_detach
+ sizeof(struct igc_softc), igc_match, igc_attach, igc_detach,
+ igc_activate
};
/*********************************************************************
@@ -315,6 +317,30 @@ igc_detach(struct device *self, int flag
free(sc->mta, M_DEVBUF, ETHER_ADDR_LEN * MAX_NUM_MULTICAST_ADDRESSES);
return 0;
+}
+
+int
+igc_activate(struct device *self, int act)
+{
+ struct igc_softc *sc = (struct igc_softc *)self;
+ struct ifnet *ifp = &sc->sc_ac.ac_if;
+ int rv = 0;
+
+ switch (act) {
+ case DVACT_SUSPEND:
+ if (ifp->if_flags & IFF_RUNNING)
+ igc_stop(sc);
+ rv = config_activate_children(self, act);
+ break;
+ case DVACT_RESUME:
+ if (ifp->if_flags & IFF_UP)
+ igc_init(sc);
+ break;
+ default:
+ rv = config_activate_children(self, act);
+ break;
+ }
+ return rv;
}
void