Skip to content
New issue

Have a question about this project? Sign up for a free GitHub account to open an issue and contact its maintainers and the community.

By clicking “Sign up for GitHub”, you agree to our terms of service and privacy statement. We’ll occasionally send you account related emails.

Already on GitHub? Sign in to your account

net/network_layer/fib: added prefix consideration for RRP registration/signaling #2915

Merged
Merged
Show file tree
Hide file tree
Changes from all commits
Commits
File filter

Filter by extension

Filter by extension

Conversations
Failed to load comments.
Loading
Jump to
Jump to file
Failed to load files.
Loading
Diff view
Diff view
19 changes: 13 additions & 6 deletions sys/include/net/ng_fib.h
Original file line number Diff line number Diff line change
Expand Up @@ -26,15 +26,15 @@ extern "C" {
#endif

/**
* @brief Reactive Routing Protocol (RRP) message content to request/reply route discovery
* @brief Routing Protocol (RP) message content to request/reply notification
*/
typedef struct rrp_address_msg_t {
typedef struct rp_address_msg_t {
uint8_t *address; /**< The pointer to the address */
uint8_t address_size; /**< The address size */
uint32_t address_flags; /**< The flags for the given address */
} rrp_address_msg_t;
} rp_address_msg_t;

#define FIB_MSG_RRP_SIGNAL (0x99) /**< message type for RRP notifications */
#define FIB_MSG_RP_SIGNAL (0x99) /**< message type for RP notifications */

/**
* @brief indicator of a lifetime that does not expire (2^32 - 1)
Expand All @@ -52,9 +52,16 @@ void fib_init(void);
void fib_deinit(void);

/**
* @brief Registration of reactive routing protocol handler function
* @brief Registration of a routing protocol handler function
*
* @param[in] prefix the prefix handled by the according RP
* @param[in] prefix_size the prefix size
* @return 0 on success
* -ENOMEM if the entry cannot be registered (mximum registrations reached)
* -EINVAL if the prefix is NULL or the provided size is 0
*
*/
void fib_register_rrp(void);
int fib_register_rp(uint8_t *prefix, size_t prefix_size);

/**
* @brief Adds a new entry in the corresponding FIB table for global destination and next hop
Expand Down
99 changes: 62 additions & 37 deletions sys/net/network_layer/fib/fib.c
Original file line number Diff line number Diff line change
Expand Up @@ -35,20 +35,25 @@
static mutex_t mtx_access = MUTEX_INIT;

/**
* @brief maximum number of handled reactive routing protocols (RRP)
* used to notify the saved kernel_pid_t
* @brief maximum number of handled routing protocols (RP)
* used to notify the saved kernel_pid_t on ureachable destination
*/
#define FIB_MAX_RRP (5)
#define FIB_MAX_REGISTERED_RP (5)

/**
* @brief registered RRPs for notifications about unreachable destinations
* @brief registered RPs for notifications about unreachable destinations
*/
static size_t notify_rrp_pos = 0;
static size_t notify_rp_pos = 0;

/**
* @brief the kernel_pid_t for notifying the RRPs
* @brief the kernel_pid_t for notifying the RPs
*/
static kernel_pid_t notify_rrp[FIB_MAX_RRP];
static kernel_pid_t notify_rp[FIB_MAX_REGISTERED_RP];

/**
* @brief the prefix handled by the RP
*/
static universal_address_container_t* prefix_rp[FIB_MAX_REGISTERED_RP];

/**
* @brief maximum number of FIB tables entries handled
Expand Down Expand Up @@ -271,8 +276,10 @@ static int fib_remove(fib_entry_t *entry)
}

/**
* @brief signals (sends a message to) all registered RRPs
* to start a route discovery for the provided destination.
* @brief signals (sends a message to) all registered routing protocols
* registered with a matching prefix (usually this should be only one).
* The message informs the recipient that no next-hop is available for the
* requested destination address.
* The receiver MUST copy the content, i.e. the address before reply.
*
* @param[in] dst the destination address
Expand All @@ -281,29 +288,32 @@ static int fib_remove(fib_entry_t *entry)
* @return 0 on a new available entry,
* -ENOENT if no suiting entry is provided.
*/
static int fib_signal_rrp(uint8_t *dst, size_t dst_size, uint32_t dst_flags)
static int fib_signal_rp(uint8_t *dst, size_t dst_size, uint32_t dst_flags)
{
msg_t msg, reply;
rrp_address_msg_t content;
rp_address_msg_t content;
content.address = dst;
content.address_size = dst_size;
content.address_flags = dst_flags;
int ret = -ENOENT;

msg.type = FIB_MSG_RRP_SIGNAL;
msg.type = FIB_MSG_RP_SIGNAL;
msg.content.ptr = (void *)&content;

for (size_t i = 0; i < FIB_MAX_RRP; ++i) {
if (notify_rrp[i] != KERNEL_PID_UNDEF) {
DEBUG("[fib_signal_rrp] send msg@: %p to pid[%d]: %d\n", \
msg.content.ptr, (int)i, (int)notify_rrp[i]);

/* the receiver, i.e. the RRP, MUST copy the content value.
* using the provided pointer after replying this message
* will lead to errors
*/
msg_send_receive(&msg, &reply, notify_rrp[i]);
DEBUG("[fib_signal_rrp] got reply.");
for (size_t i = 0; i < FIB_MAX_REGISTERED_RP; ++i) {
if (notify_rp[i] != KERNEL_PID_UNDEF) {
DEBUG("[fib_signal_rp] send msg@: %p to pid[%d]: %d\n", \
msg.content.ptr, (int)i, (int)notify_rp[i]);

/* do only signal a RP if its registered prefix matches */
if (universal_address_compare(prefix_rp[i], dst, &dst_size) == 0) {
/* the receiver, i.e. the RP, MUST copy the content value.
* using the provided pointer after replying this message
* will lead to errors
*/
msg_send_receive(&msg, &reply, notify_rp[i]);
DEBUG("[fib_signal_rp] got reply.");
}
}
}

Expand Down Expand Up @@ -395,8 +405,8 @@ int fib_get_next_hop(kernel_pid_t *iface_id,
int ret = fib_find_entry(dst, dst_size, &(entry[0]), &count);

if (!(ret == 0 || ret == 1)) {
/* notify all RRPs for route discovery if available */
if (fib_signal_rrp(dst, dst_size, dst_flags) == 0) {
/* notify all responsible RPs for unknown next-hop for the destination address */
if (fib_signal_rp(dst, dst_size, dst_flags) == 0) {
count = 1;
/* now lets see if the RRPs have found a valid next-hop */
ret = fib_find_entry(dst, dst_size, &(entry[0]), &count);
Expand Down Expand Up @@ -429,8 +439,9 @@ void fib_init(void)
DEBUG("[fib_init] hello. Initializing some stuff.");
mutex_lock(&mtx_access);

for (size_t i = 0; i < FIB_MAX_RRP; ++i) {
notify_rrp[i] = KERNEL_PID_UNDEF;
for (size_t i = 0; i < FIB_MAX_REGISTERED_RP; ++i) {
notify_rp[i] = KERNEL_PID_UNDEF;
prefix_rp[i] = NULL;
}

for (size_t i = 0; i < FIB_MAX_FIB_TABLE_ENTRIES; ++i) {
Expand All @@ -452,11 +463,12 @@ void fib_deinit(void)
DEBUG("[fib_deinit] hello. De-Initializing stuff.");
mutex_lock(&mtx_access);

for (size_t i = 0; i < FIB_MAX_RRP; ++i) {
notify_rrp[i] = KERNEL_PID_UNDEF;
for (size_t i = 0; i < FIB_MAX_REGISTERED_RP; ++i) {
notify_rp[i] = KERNEL_PID_UNDEF;
prefix_rp[i] = NULL;
}

notify_rrp_pos = 0;
notify_rp_pos = 0;

for (size_t i = 0; i < FIB_MAX_FIB_TABLE_ENTRIES; ++i) {
fib_table[i].iface_id = 0;
Expand All @@ -472,16 +484,29 @@ void fib_deinit(void)
mutex_unlock(&mtx_access);
}

void fib_register_rrp(void)
int fib_register_rrp(uint8_t *prefix, size_t prefix_size)
{
mutex_lock(&mtx_access);

if (notify_rrp_pos < FIB_MAX_RRP) {
notify_rrp[notify_rrp_pos] = sched_active_pid;
notify_rrp_pos++;
if (notify_rp_pos >= FIB_MAX_REGISTERED_RP) {
mutex_unlock(&mtx_access);
return -ENOMEM;
}

if ((prefix == NULL) || (prefix_size == 0)) {
Copy link
Member

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

So a reactive protocol isn't allowed to take care of all traffic? (I'm not quite sure if it should, but.. hmmm)

Copy link
Member Author

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

If a RRP wants to "catch all", it can provide an all 0 prefix.
However, this is usually the default gateway and should be determined for instance on 6LoWPAN level. A routing protocol is usually responsible for a specific prefix and not the complete ::/128 range.
But technically (after #2783 has been merged), you can just tell the FIB this way to inform you always on unreachable destinations.

Copy link
Member

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

Makes sense. Other than the first comment, I have no other quibbles.. ACK when the 1st comment is addressed and travis is happy :)

mutex_unlock(&mtx_access);
return -EINVAL;
}

if (notify_rp_pos < FIB_MAX_REGISTERED_RP) {
notify_rp[notify_rp_pos] = sched_active_pid;
universal_address_container_t *container = universal_address_add(prefix, prefix_size);
prefix_rp[notify_rp_pos] = container;
notify_rp_pos++;
}

mutex_unlock(&mtx_access);
return 0;
}

int fib_get_num_used_entries(void)
Expand All @@ -499,12 +524,12 @@ int fib_get_num_used_entries(void)

/* print functions */

void fib_print_notify_rrp(void)
void fib_print_notify_rp(void)
{
mutex_lock(&mtx_access);

for (size_t i = 0; i < FIB_MAX_RRP; ++i) {
printf("[fib_print_notify_rrp] pid[%d]: %d\n", (int)i, (int)notify_rrp[i]);
for (size_t i = 0; i < FIB_MAX_REGISTERED_RP; ++i) {
printf("[fib_print_notify_rp] pid[%d]: %d\n", (int)i, (int)notify_rp[i]);
}

mutex_unlock(&mtx_access);
Expand Down