2 * This file is part of the PCEPlib, a PCEP protocol library.
4 * Copyright (C) 2020 Volta Networks https://voltanet.io/
6 * This library is free software; you can redistribute it and/or
7 * modify it under the terms of the GNU Lesser General Public
8 * License as published by the Free Software Foundation; either
9 * version 2 of the License, or (at your option) any later version.
11 * This library is distributed in the hope that it will be useful,
12 * but WITHOUT ANY WARRANTY; without even the implied warranty of
13 * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the GNU
14 * Lesser General Public License for more details.
16 * You should have received a copy of the GNU Lesser General Public License
17 * along with this program. If not, see <https://www.gnu.org/licenses/>.
19 * Author : Brady Johnson <brady@voltanet.io>
24 * This is a High Level PCEP message object TLV API.
30 #include <arpa/inet.h>
34 #include "pcep_utils_double_linked_list.h"
41 * Regarding memory usage:
42 * When creating TLVs, any TLVs passed into messages or objects with these APIs
43 * will be free'd when the the enclosing pcep_message is free'd. That includes
44 * the double_linked_list's. So, just create the objects and TLVs, put them in
45 * their double_linked_list's, and everything will be managed internally. The
46 * enclosing message will be deleted by pcep_msg_free_message() or
47 * pcep_msg_free_message_list() which, * in turn will call one of:
48 * pcep_obj_free_object() and pcep_obj_free_tlv().
49 * For received messages, call pcep_msg_free_message() to free them.
52 /* These numbers can be found here:
53 * https://www.iana.org/assignments/pcep/pcep.xhtml */
54 enum pcep_object_tlv_types
{
55 PCEP_OBJ_TLV_TYPE_NO_PATH_VECTOR
= 1,
56 PCEP_OBJ_TLV_TYPE_OBJECTIVE_FUNCTION_LIST
= 4, /* RFC 5541 */
57 PCEP_OBJ_TLV_TYPE_VENDOR_INFO
= 7, /* RFC 7470 */
58 PCEP_OBJ_TLV_TYPE_STATEFUL_PCE_CAPABILITY
= 16, /* RFC 8231 */
59 PCEP_OBJ_TLV_TYPE_SYMBOLIC_PATH_NAME
= 17, /* RFC 8232 */
60 PCEP_OBJ_TLV_TYPE_IPV4_LSP_IDENTIFIERS
= 18, /* RFC 8231 */
61 PCEP_OBJ_TLV_TYPE_IPV6_LSP_IDENTIFIERS
= 19, /* RFC 8231 */
62 PCEP_OBJ_TLV_TYPE_LSP_ERROR_CODE
= 20, /* RFC 8232 */
63 PCEP_OBJ_TLV_TYPE_RSVP_ERROR_SPEC
= 21, /* RFC 8232 */
64 PCEP_OBJ_TLV_TYPE_LSP_DB_VERSION
= 23, /* RFC 8232 */
65 PCEP_OBJ_TLV_TYPE_SPEAKER_ENTITY_ID
= 24, /* RFC 8232 */
66 PCEP_OBJ_TLV_TYPE_SR_PCE_CAPABILITY
=
67 26, /* draft-ietf-pce-segment-routing-16 */
68 PCEP_OBJ_TLV_TYPE_PATH_SETUP_TYPE
= 28, /* RFC 8408 */
69 PCEP_OBJ_TLV_TYPE_PATH_SETUP_TYPE_CAPABILITY
=
70 34, /* RFC 8408, draft-ietf-pce-segment-routing-16 */
71 PCEP_OBJ_TLV_TYPE_SRPOLICY_POL_ID
=
72 60, /*TDB2 draft-barth-pce-segment-routing-policy-cp-04 */
73 PCEP_OBJ_TLV_TYPE_SRPOLICY_POL_NAME
=
74 61, /*TDB3 draft-barth-pce-segment-routing-policy-cp-04 */
75 PCEP_OBJ_TLV_TYPE_SRPOLICY_CPATH_ID
=
76 62, /*TDB4 draft-barth-pce-segment-routing-policy-cp-04 */
77 PCEP_OBJ_TLV_TYPE_SRPOLICY_CPATH_PREFERENCE
=
78 63, /*TDB5 draft-barth-pce-segment-routing-policy-cp-04 */
79 PCEP_OBJ_TLV_TYPE_UNKNOWN
= 128,
80 PCEP_OBJ_TYPE_CISCO_BSID
= 65505,
81 /* Max IANA To write arbitrary data */
82 PCEP_OBJ_TLV_TYPE_ARBITRARY
= 65533
86 struct pcep_object_tlv_header
{
87 enum pcep_object_tlv_types type
;
88 /* Pointer into encoded_message field from the pcep_message */
89 const uint8_t *encoded_tlv
;
90 uint16_t encoded_tlv_length
;
93 /* STATEFUL-PCE-CAPABILITY TLV, Used in Open Object. RFCs: 8231, 8232, 8281 */
94 #define TLV_STATEFUL_PCE_CAP_FLAG_U 0x01
95 #define TLV_STATEFUL_PCE_CAP_FLAG_S 0x02
96 #define TLV_STATEFUL_PCE_CAP_FLAG_I 0x04
97 #define TLV_STATEFUL_PCE_CAP_FLAG_T 0x08
98 #define TLV_STATEFUL_PCE_CAP_FLAG_D 0x10
99 #define TLV_STATEFUL_PCE_CAP_FLAG_F 0x20
101 struct pcep_object_tlv_stateful_pce_capability
{
102 struct pcep_object_tlv_header header
;
103 bool flag_u_lsp_update_capability
; /* RFC 8231 */
104 bool flag_s_include_db_version
; /* RFC 8232 */
105 bool flag_i_lsp_instantiation_capability
; /* RFC 8281 */
106 bool flag_t_triggered_resync
; /* RFC 8232 */
107 bool flag_d_delta_lsp_sync
; /* RFC 8232 */
108 bool flag_f_triggered_initial_sync
; /* RFC 8232 */
111 /* NOPATH-VECTOR TLV, Used in the Reply NoPath Object. */
112 struct pcep_object_tlv_nopath_vector
{
113 struct pcep_object_tlv_header header
;
117 /* STATEFUL-PCE-CAPABILITY TLV, Used in Open Object. RFCs: 8232 */
118 struct pcep_object_tlv_lsp_db_version
{
119 struct pcep_object_tlv_header header
;
120 uint64_t lsp_db_version
;
123 /* Speaker Entity Identifier TLV, Used in Open Object. RFCs: 8232 */
124 struct pcep_object_tlv_speaker_entity_identifier
{
125 struct pcep_object_tlv_header header
;
126 double_linked_list
*speaker_entity_id_list
; /* list of uint32_t speaker
130 /* Ipv4 LSP Identifier TLV, Used in LSP Object. RFCs: 8231 */
131 struct pcep_object_tlv_ipv4_lsp_identifier
{
132 struct pcep_object_tlv_header header
;
133 struct in_addr ipv4_tunnel_sender
;
136 struct in_addr extended_tunnel_id
;
137 struct in_addr ipv4_tunnel_endpoint
;
140 /* Ipv6 LSP Identifier TLV, Used in LSP Object. RFCs: 8231 */
141 struct pcep_object_tlv_ipv6_lsp_identifier
{
142 struct pcep_object_tlv_header header
;
143 struct in6_addr ipv6_tunnel_sender
;
146 struct in6_addr extended_tunnel_id
;
147 struct in6_addr ipv6_tunnel_endpoint
;
150 /* Symbolic Path Name TLV, Used in LSP Object. RFCs: 8231 */
151 #define MAX_SYMBOLIC_PATH_NAME 256
153 struct pcep_object_tlv_symbolic_path_name
{
154 struct pcep_object_tlv_header header
;
155 uint16_t symbolic_path_name_length
;
156 char symbolic_path_name
[MAX_SYMBOLIC_PATH_NAME
];
159 /* LSP Error Code TLV, Used in LSP Object. RFCs: 8231 */
160 enum pcep_tlv_lsp_error_codes
{
161 PCEP_TLV_LSP_ERROR_CODE_UNKNOWN
= 1,
162 PCEP_TLV_LSP_ERROR_CODE_LSP_LIMIT_REACHED
= 2,
163 PCEP_TLV_LSP_ERROR_CODE_TOO_MANY_PENDING_LSP_UPDATES
= 3,
164 PCEP_TLV_LSP_ERROR_CODE_UNACCEPTABLE_PARAMS
= 4,
165 PCEP_TLV_LSP_ERROR_CODE_INTERNAL_ERROR
= 5,
166 PCEP_TLV_LSP_ERROR_CODE_LSP_BROUGHT_DOWN
= 6,
167 PCEP_TLV_LSP_ERROR_CODE_LSP_PREEMPTED
= 7,
168 PCEP_TLV_LSP_ERROR_CODE_RSVP_SIGNALING_ERROR
= 8,
171 struct pcep_object_tlv_lsp_error_code
{
172 struct pcep_object_tlv_header header
;
173 enum pcep_tlv_lsp_error_codes lsp_error_code
;
176 /* Path Setup Type TLV, Used in RP and SRP Object. RFCs: 8408,
177 * draft-ietf-pce-segment-routing-16 */
180 struct pcep_object_tlv_path_setup_type
{
181 struct pcep_object_tlv_header header
;
182 uint8_t path_setup_type
;
185 /* Path Setup Type Capability TLV, Used in Open Object. RFCs: 8408,
186 * draft-ietf-pce-segment-routing-16 */
187 struct pcep_object_tlv_path_setup_type_capability
{
188 struct pcep_object_tlv_header header
;
189 double_linked_list
*pst_list
; /* list of uint8_t PSTs */
190 double_linked_list
*sub_tlv_list
; /* list of sub_tlvs */
193 /* SR PCE Capability sub-TLV, Used in Open Object. RFCs:
194 * draft-ietf-pce-segment-routing-16 */
195 #define TLV_SR_PCE_CAP_FLAG_X 0x01
196 #define TLV_SR_PCE_CAP_FLAG_N 0x02
198 struct pcep_object_tlv_sr_pce_capability
{
199 struct pcep_object_tlv_header header
;
202 uint8_t max_sid_depth
;
206 /* RSVP Error Spec TLV, Used in LSP Object. RFCs: 8231, 2205 */
207 #define RSVP_ERROR_SPEC_IPV4_CTYPE 1
208 #define RSVP_ERROR_SPEC_IPV6_CTYPE 2
209 #define RSVP_ERROR_SPEC_CLASS_NUM 6
211 struct pcep_object_tlv_rsvp_error_spec
{
212 struct pcep_object_tlv_header header
;
216 uint16_t error_value
;
217 /* Use the c_type to determine which union entry to use */
218 union error_spec_ip
{
219 struct in_addr ipv4_error_node_address
;
220 struct in6_addr ipv6_error_node_address
;
224 /* SR Policy Identifier TLV Used in Association Object.
225 * draft-barth-pce-segment-routing-policy-cp-04*/
226 struct pcep_object_tlv_srpag_pol_id
{
227 struct pcep_object_tlv_header header
;
232 struct in6_addr ipv6
;
236 /*draft-ietf-spring-segment-routing-policy-06*/
237 #define MAX_POLICY_NAME 256
239 /* SR Policy Name TLV Used in Association Object.
240 * draft-barth-pce-segment-routing-policy-cp-04*/
241 struct pcep_object_tlv_srpag_pol_name
{
242 struct pcep_object_tlv_header header
;
243 uint16_t name_length
;
244 char name
[MAX_POLICY_NAME
];
247 /* SR Candidate Path Id TLV Used in Association Object.
248 * draft-barth-pce-segment-routing-policy-cp-04*/
249 struct pcep_object_tlv_srpag_cp_id
{
250 struct pcep_object_tlv_header header
;
253 struct in6_addr orig_addres
; /*With ipv4 embedded*/
254 uint32_t discriminator
;
257 /* SR Candidate Preference TLV Used in Association Object.
258 * draft-barth-pce-segment-routing-policy-cp-04*/
259 struct pcep_object_tlv_srpag_cp_pref
{
260 struct pcep_object_tlv_header header
;
264 struct pcep_object_tlv_vendor_info
{
265 struct pcep_object_tlv_header header
;
266 uint32_t enterprise_number
;
267 uint32_t enterprise_specific_info
;
270 /* arbitrary TLV 65535 */
271 #define MAX_ARBITRARY_SIZE 256
272 struct pcep_object_tlv_arbitrary
{
273 struct pcep_object_tlv_header header
;
274 enum pcep_object_tlv_types arbitraty_type
;
275 uint16_t data_length
;
276 char data
[MAX_ARBITRARY_SIZE
];
279 /* Objective Functions List RFC 5541
280 * At least the following 6 OF codes must be supported */
281 enum objective_function_codes
{
282 PCEP_OF_CODE_MINIMUM_COST_PATH
= 1, /* MCP */
283 PCEP_OF_CODE_MINIMUM_LOAD_PATH
= 2, /* MLP */
284 PCEP_OF_CODE_MAXIMUM_BW_PATH
= 3, /* MBP */
285 PCEP_OF_CODE_MINIMIZE_AGGR_BW_CONSUMPTION
= 4, /* MBC */
286 PCEP_OF_CODE_MINIMIZE_MOST_LOADED_LINK
= 5, /* MLL */
287 PCEP_OF_CODE_MINIMIZE_CUMULATIVE_COST_PATHS
= 6, /* MCC */
290 struct pcep_object_tlv_of_list
{
291 struct pcep_object_tlv_header header
;
292 double_linked_list
*of_list
; /* list of uint16_t OF code points */
296 * TLV creation functions
303 struct pcep_object_tlv_stateful_pce_capability
*
304 pcep_tlv_create_stateful_pce_capability(
305 bool flag_u_lsp_update_capability
, bool flag_s_include_db_version
,
306 bool flag_i_lsp_instantiation_capability
, bool flag_t_triggered_resync
,
307 bool flag_d_delta_lsp_sync
, bool flag_f_triggered_initial_sync
);
308 struct pcep_object_tlv_lsp_db_version
*
309 pcep_tlv_create_lsp_db_version(uint64_t lsp_db_version
);
310 struct pcep_object_tlv_speaker_entity_identifier
*
311 pcep_tlv_create_speaker_entity_id(double_linked_list
*speaker_entity_id_list
);
312 struct pcep_object_tlv_path_setup_type
*
313 pcep_tlv_create_path_setup_type(uint8_t pst
);
314 struct pcep_object_tlv_path_setup_type_capability
*
315 pcep_tlv_create_path_setup_type_capability(double_linked_list
*pst_list
,
316 double_linked_list
*sub_tlv_list
);
317 struct pcep_object_tlv_sr_pce_capability
*
318 pcep_tlv_create_sr_pce_capability(bool flag_n
, bool flag_x
,
319 uint8_t max_sid_depth
);
320 struct pcep_object_tlv_of_list
*
321 pcep_tlv_create_of_list(double_linked_list
*of_list
);
327 struct pcep_object_tlv_ipv4_lsp_identifier
*
328 pcep_tlv_create_ipv4_lsp_identifiers(struct in_addr
*ipv4_tunnel_sender
,
329 struct in_addr
*ipv4_tunnel_endpoint
,
330 uint16_t lsp_id
, uint16_t tunnel_id
,
331 struct in_addr
*extended_tunnel_id
);
332 struct pcep_object_tlv_ipv6_lsp_identifier
*
333 pcep_tlv_create_ipv6_lsp_identifiers(struct in6_addr
*ipv6_tunnel_sender
,
334 struct in6_addr
*extended_tunnel_id
,
335 uint16_t lsp_id
, uint16_t tunnel_id
,
336 struct in6_addr
*ipv6_tunnel_endpoint
);
337 /* symbolic_path_name_length should NOT include the null terminator and cannot
339 struct pcep_object_tlv_symbolic_path_name
*
340 pcep_tlv_create_symbolic_path_name(const char *symbolic_path_name
,
341 uint16_t symbolic_path_name_length
);
342 struct pcep_object_tlv_lsp_error_code
*
343 pcep_tlv_create_lsp_error_code(enum pcep_tlv_lsp_error_codes lsp_error_code
);
344 struct pcep_object_tlv_rsvp_error_spec
*
345 pcep_tlv_create_rsvp_ipv4_error_spec(struct in_addr
*error_node_ip
,
346 uint8_t error_code
, uint16_t error_value
);
347 struct pcep_object_tlv_rsvp_error_spec
*
348 pcep_tlv_create_rsvp_ipv6_error_spec(struct in6_addr
*error_node_ip
,
349 uint8_t error_code
, uint16_t error_value
);
351 struct pcep_object_tlv_nopath_vector
*
352 pcep_tlv_create_nopath_vector(uint32_t error_code
);
353 struct pcep_object_tlv_vendor_info
*
354 pcep_tlv_create_vendor_info(uint32_t enterprise_number
,
355 uint32_t enterprise_specific_info
);
357 struct pcep_object_tlv_arbitrary
*
358 pcep_tlv_create_tlv_arbitrary(const char *data
, uint16_t data_length
,
361 * SRPAG (SR Association Group) TLVs
364 struct pcep_object_tlv_srpag_pol_id
*
365 pcep_tlv_create_srpag_pol_id_ipv4(uint32_t color
, struct in_addr
*ipv4
);
366 struct pcep_object_tlv_srpag_pol_id
*
367 pcep_tlv_create_srpag_pol_id_ipv6(uint32_t color
, struct in6_addr
*ipv6
);
368 struct pcep_object_tlv_srpag_pol_name
*
369 pcep_tlv_create_srpag_pol_name(const char *pol_name
, uint16_t pol_name_length
);
370 struct pcep_object_tlv_srpag_cp_id
*
371 pcep_tlv_create_srpag_cp_id(uint8_t proto_origin
, uint32_t asn
,
372 struct in6_addr
*in6_addr_with_mapped_ipv4
,
373 uint32_t discriminator
);
374 struct pcep_object_tlv_srpag_cp_pref
*
375 pcep_tlv_create_srpag_cp_pref(uint32_t pref
);
382 #endif /* PCEP_TLVS_H_ */