Fixed next hop processing
[mpls-ldp-portable.git] / ldp / ldp_if.c
bloba47e266901c302a81c652ed8ce68414dc92a434d
2 /*
3 * Copyright (C) James R. Leu 2000
4 * jleu@mindspring.com
6 * This software is covered under the LGPL, for more
7 * info check out http://www.gnu.org/copyleft/lgpl.html
8 */
10 #include <stdlib.h>
11 #include <netinet/in.h>
12 #include <sys/socket.h>
13 #include "ldp_struct.h"
14 #include "ldp_entity.h"
15 #include "ldp_nortel.h"
16 #include "ldp_if.h"
17 #include "ldp_mesg.h"
18 #include "ldp_buf.h"
19 #include "ldp_hello.h"
21 #include "mpls_assert.h"
22 #include "mpls_mm_impl.h"
23 #include "mpls_socket_impl.h"
24 #include "mpls_timer_impl.h"
25 #include "mpls_ifmgr_impl.h"
26 #include "mpls_trace_impl.h"
28 extern uint32_t _ldp_sub_entity_next_index;
30 ldp_if *ldp_if_create()
32 ldp_if *i = (ldp_if *) mpls_malloc(sizeof(ldp_if));
34 if (i) {
35 memset(i, 0, sizeof(ldp_if));
36 MPLS_REFCNT_INIT(i, 0);
37 MPLS_LIST_ELEM_INIT(i, _global);
38 i->label_space = -1;
39 i->dest.addr.type = MPLS_FAMILY_IPV4;
40 i->dest.addr.u.ipv4 = INADDR_ALLRTRS_GROUP;
41 i->tx_buffer = ldp_buf_create(MPLS_PDUMAXLEN);
42 i->tx_message = ldp_mesg_create();
43 i->index = _ldp_if_get_next_index();
44 i->oper_state = MPLS_OPER_DOWN;
46 return i;
49 void ldp_if_delete(ldp_if * i)
51 LDP_PRINT(g->user_data,"if delete\n");
52 MPLS_REFCNT_ASSERT(i, 0);
53 mpls_free(i->tx_buffer);
54 mpls_free(i->tx_message);
55 mpls_free(i);
58 mpls_return_enum ldp_if_startup(ldp_global * g, ldp_if * i)
60 ldp_entity *e = NULL;
62 LDP_ENTER(g->user_data, "ldp_if_startup");
64 MPLS_ASSERT(i != NULL);
65 e = i->entity;
66 MPLS_ASSERT(e != NULL);
67 MPLS_ASSERT(e->p.iff != NULL);
69 if (mpls_ifmgr_get_address(g->ifmgr_handle, i->handle,
70 &i->local_source_address, NULL, NULL) == MPLS_FAILURE) {
71 goto ldp_if_startup_delay;
73 if (mpls_socket_multicast_if_join(g->socket_handle, g->hello_socket, i,
74 &i->dest.addr) == MPLS_FAILURE) {
75 goto ldp_if_startup_delay;
78 i->dest.port = e->remote_udp_port;
79 if (ldp_hello_send(g, e) == MPLS_FAILURE) {
80 ldp_if_shutdown(g, i);
81 return MPLS_FAILURE;
83 i->oper_state = MPLS_OPER_UP;
85 LDP_EXIT(g->user_data, "ldp_if_startup");
87 return MPLS_SUCCESS;
89 ldp_if_startup_delay:
92 * when a interface update comes in, it will search the global
93 * list of interfaces, and start up the interface then
95 i->oper_state = MPLS_OPER_DOWN;
97 LDP_EXIT(g->user_data, "ldp_if_startup-delayed");
99 return MPLS_SUCCESS;
102 mpls_return_enum ldp_if_shutdown(ldp_global * g, ldp_if * i)
104 ldp_entity *e = NULL;
106 MPLS_ASSERT(i != NULL && ((e = i->entity) != NULL));
108 LDP_ENTER(g->user_data, "ldp_if_shutdown");
110 i->oper_state = MPLS_OPER_DOWN;
112 mpls_socket_multicast_if_drop(g->socket_handle, g->hello_socket, i,
113 &i->dest.addr);
115 mpls_timer_stop(g->timer_handle, i->hellotime_send_timer);
116 mpls_timer_delete(g->timer_handle, i->hellotime_send_timer);
117 i->hellotime_send_timer_duration = 0;
118 i->hellotime_send_timer = 0;
121 * jleu: I'm not sure why these were here, I'm commenting them out,
122 * because I do not see a corresponding HOLD in ldp_if_startup
123 MPLS_REFCNT_RELEASE(e, ldp_entity_delete);
124 MPLS_ASSERT(e != NULL);
127 if (i->hello) {
128 ldp_mesg_delete(i->hello);
129 i->hello = NULL;
132 LDP_EXIT(g->user_data, "ldp_if_shutdown");
134 return MPLS_SUCCESS;
137 mpls_bool ldp_if_is_active(ldp_if * i)
139 if (i && i->entity && i->entity->admin_state == MPLS_ADMIN_ENABLE)
140 return MPLS_BOOL_TRUE;
142 return MPLS_BOOL_FALSE;
145 mpls_return_enum _ldp_if_add_entity(ldp_if * i, ldp_entity * e)
147 if (i && e) {
148 MPLS_REFCNT_HOLD(e);
149 i->entity = e;
150 return MPLS_SUCCESS;
152 return MPLS_FAILURE;
155 ldp_entity *ldp_if_get_entity(ldp_if * i)
157 return i->entity;
160 mpls_return_enum _ldp_if_del_entity(ldp_if * i)
162 if (i && i->entity) {
163 MPLS_REFCNT_RELEASE(i->entity, ldp_entity_delete);
164 i->entity = NULL;
165 return MPLS_SUCCESS;
167 return MPLS_FAILURE;
170 uint32_t _ldp_if_get_next_index()
172 uint32_t retval = _ldp_sub_entity_next_index;
174 _ldp_sub_entity_next_index++;
175 if (retval > _ldp_sub_entity_next_index) {
176 _ldp_sub_entity_next_index = 1;
178 return retval;