version 1.250, 2017/12/09 10:51:30 |
version 1.251, 2018/01/15 07:59:48 |
Line 1553 ether_multicast_sysctl(SYSCTLFN_ARGS) |
|
Line 1553 ether_multicast_sysctl(SYSCTLFN_ARGS) |
|
|
|
/* |
/* |
* ec->ec_lock is a spin mutex so we cannot call sysctl_copyout, which |
* ec->ec_lock is a spin mutex so we cannot call sysctl_copyout, which |
* is sleepable, with holding it. Copy data to a local buffer first |
* is sleepable, while holding it. Copy data to a local buffer first |
* with holding it and then call sysctl_copyout without holding it. |
* with the lock taken and then call sysctl_copyout without holding it. |
*/ |
*/ |
retry: |
retry: |
multicnt = ec->ec_multicnt; |
multicnt = ec->ec_multicnt; |
|
|
|
if (multicnt == 0) { |
|
if_put(ifp, &psref); |
|
*oldlenp = 0; |
|
goto out; |
|
} |
|
|
addrs = kmem_alloc(sizeof(*addrs) * multicnt, KM_SLEEP); |
addrs = kmem_alloc(sizeof(*addrs) * multicnt, KM_SLEEP); |
|
|
ETHER_LOCK(ec); |
ETHER_LOCK(ec); |
if (multicnt < ec->ec_multicnt) { |
if (multicnt != ec->ec_multicnt) { |
/* The number of multicast addresses have increased */ |
/* The number of multicast addresses has changed */ |
ETHER_UNLOCK(ec); |
ETHER_UNLOCK(ec); |
kmem_free(addrs, sizeof(*addrs) * multicnt); |
kmem_free(addrs, sizeof(*addrs) * multicnt); |
goto retry; |
goto retry; |