From bd39813883e172767d59100339bb51e47a24d3b7 Mon Sep 17 00:00:00 2001 From: Xiang Xiao Date: Thu, 16 Apr 2020 13:50:20 +0800 Subject: [PATCH] netlink: Add netlink_add_broadcast function Signed-off-by: Xiang Xiao Change-Id: I1bee7933dca1bdd118d0034a564b4306e1ae5684 --- include/nuttx/net/netlink.h | 21 ++++++++++- net/netlink/netlink_conn.c | 72 +++++++++++++++++++++++++++++++++++++ 2 files changed, 92 insertions(+), 1 deletion(-) diff --git a/include/nuttx/net/netlink.h b/include/nuttx/net/netlink.h index 04f9eaa5ff..37962717c3 100644 --- a/include/nuttx/net/netlink.h +++ b/include/nuttx/net/netlink.h @@ -72,7 +72,7 @@ typedef FAR void *NETLINK_HANDLE; struct netlink_response_s { sq_entry_t flink; - FAR struct nlmsghdr msg; + struct nlmsghdr msg; /* Message-specific data may follow */ }; @@ -113,6 +113,25 @@ extern "C" void netlink_add_response(NETLINK_HANDLE handle, FAR struct netlink_response_s *resp); +/**************************************************************************** + * Name: netlink_add_broadcast + * + * Description: + * Add broadcast data to all interested netlink connections. + * + * Note: The network will be momentarily locked to support exclusive + * access to the pending response list. + * + * Input Parameters: + * group - The broadcast group index. + * data - The broadcast data. The memory referenced by 'data' + * must have been allocated via kmm_malloc(). It will be freed + * using kmm_free() after it has been consumed. + * + ****************************************************************************/ + +void netlink_add_broadcast(int group, FAR struct netlink_response_s *data); + #undef EXTERN #ifdef __cplusplus } diff --git a/net/netlink/netlink_conn.c b/net/netlink/netlink_conn.c index fc25ad0094..9145ef225a 100644 --- a/net/netlink/netlink_conn.c +++ b/net/netlink/netlink_conn.c @@ -289,6 +289,78 @@ void netlink_add_response(NETLINK_HANDLE handle, net_unlock(); } +/**************************************************************************** + * Name: netlink_add_broadcast + * + * Description: + * Add broadcast data to all interested netlink connections. + * + * Note: The network will be momentarily locked to support exclusive + * access to the pending response list. + * + * Input Parameters: + * group - The broadcast group index. + * data - The broadcast data. The memory referenced by 'data' + * must have been allocated via kmm_malloc(). It will be freed + * using kmm_free() after it has been consumed. + * + ****************************************************************************/ + +void netlink_add_broadcast(int group, FAR struct netlink_response_s *data) +{ + FAR struct netlink_conn_s *conn = NULL; + int first = 1; + + DEBUGASSERT(data != NULL); + + net_lock(); + + while ((conn = netlink_nextconn(conn)) != NULL) + { + if (conn->groups & (1 << (group - 1)) == 0) + { + continue; + } + + /* Duplicate the package except the first loop */ + + if (!first) + { + FAR struct netlink_response_s *tmp; + size_t len; + + len = sizeof(sq_entry_t) + data->msg.nlmsg_len; + tmp = kmm_malloc(len); + if (tmp == NULL) + { + break; + } + + memcpy(tmp, data, len); + data = tmp; + } + + first = 0; + + /* Add the response to the end of the FIFO list */ + + sq_addlast(&data->flink, &conn->resplist); + + /* Notify any waiters that a response is available */ + + netlink_notifier_signal(conn); + } + + net_unlock(); + + /* Drop the package if nobody is interested in */ + + if (first) + { + kmm_free(data); + } +} + /**************************************************************************** * Name: netlink_tryget_response *