ldpd: Fix to release MPLS label if its not used anymore

LDP should release labels allocated from zebra if its not getting used.

Signed-off-by: Binu <binu_abraham@looptelecom.com>
This commit is contained in:
Binu Abraham 2019-07-10 15:13:08 +08:00
parent 96e109772d
commit f4ec681c81
3 changed files with 43 additions and 0 deletions

View File

@ -1653,6 +1653,19 @@ lde_del_label_chunk(void *val)
free(val); free(val);
} }
static int
lde_release_label_chunk(uint32_t start, uint32_t end)
{
int ret;
ret = lm_release_label_chunk(zclient_sync, start, end);
if (ret < 0) {
log_warnx("Error releasing label chunk!");
return (-1);
}
return (0);
}
static int static int
lde_get_label_chunk(void) lde_get_label_chunk(void)
{ {
@ -1709,6 +1722,32 @@ on_get_label_chunk_response(uint32_t start, uint32_t end)
current_label_chunk = listtail(label_chunk_list); current_label_chunk = listtail(label_chunk_list);
} }
void
lde_free_label(uint32_t label)
{
struct listnode *node;
struct label_chunk *label_chunk;
uint64_t pos;
for (ALL_LIST_ELEMENTS_RO(label_chunk_list, node, label_chunk)) {
if (label <= label_chunk->end && label >= label_chunk->start) {
pos = 1ULL << (label - label_chunk->start);
label_chunk->used_mask &= ~pos;
/* if nobody is using this chunk and it's not current_label_chunk, then free it */
if (!label_chunk->used_mask && (current_label_chunk != node)) {
if (lde_release_label_chunk(label_chunk->start, label_chunk->end) != 0)
log_warnx("%s: Error releasing label chunk!", __func__);
else {
listnode_delete(label_chunk_list, label_chunk);
lde_del_label_chunk(label_chunk);
}
}
break;
}
}
return;
}
static uint32_t static uint32_t
lde_get_next_label(void) lde_get_next_label(void)
{ {

View File

@ -147,6 +147,7 @@ void lde_imsg_compose_parent_sync(int, pid_t, void *, uint16_t);
int lde_imsg_compose_ldpe(int, uint32_t, pid_t, void *, uint16_t); int lde_imsg_compose_ldpe(int, uint32_t, pid_t, void *, uint16_t);
int lde_acl_check(char *, int, union ldpd_addr *, uint8_t); int lde_acl_check(char *, int, union ldpd_addr *, uint8_t);
uint32_t lde_update_label(struct fec_node *); uint32_t lde_update_label(struct fec_node *);
void lde_free_label(uint32_t label);
void lde_send_change_klabel(struct fec_node *, struct fec_nh *); void lde_send_change_klabel(struct fec_node *, struct fec_nh *);
void lde_send_delete_klabel(struct fec_node *, struct fec_nh *); void lde_send_delete_klabel(struct fec_node *, struct fec_nh *);
void lde_fec2map(struct fec *, struct map *); void lde_fec2map(struct fec *, struct map *);

View File

@ -919,6 +919,9 @@ lde_gc_timer(struct thread *thread)
!RB_EMPTY(lde_map_head, &fn->upstream)) !RB_EMPTY(lde_map_head, &fn->upstream))
continue; continue;
if (fn->local_label != NO_LABEL)
lde_free_label(fn->local_label);
fec_remove(&ft, &fn->fec); fec_remove(&ft, &fn->fec);
free(fn); free(fn);
count++; count++;