@@ -287,7 +287,19 @@ static int error_handler(struct sockaddr_nl *nla, struct nlmsgerr *err,
int *ret = arg;
int ack_len = sizeof(*nlh) + sizeof(int) + sizeof(*nlh);
- *ret = err->error;
+ if (err->error > 0) {
+ /*
+ * This is illegal, per netlink(7), but not impossible (think
+ * "vendor commands"). Callers really expect negative error
+ * codes, so make that happen.
+ */
+ fprintf(stderr,
+ "ERROR: received positive netlink error code %d\n",
+ err->error);
+ *ret = -EPROTO;
+ } else {
+ *ret = err->error;
+ }
if (!(nlh->nlmsg_flags & NLM_F_ACK_TLVS))
return NL_STOP;
netlink(7) requires error codes to be negative, but since when does a man page stop anyone? At a minimum, we shouldn't allow a non-conforming vendor command to put us into an infinite loop in the below snippets from __handle_cmd(): err = 1; nl_cb_err(cb, NL_CB_CUSTOM, error_handler, &err); ... while (err > 0) nl_recvmsgs(state->nl_sock, cb); Signed-off-by: Brian Norris <briannorris@chromium.org> --- iw.c | 14 +++++++++++++- 1 file changed, 13 insertions(+), 1 deletion(-)