FD.io VPP  v20.09-64-g4f7b92f0a
Vector Packet Processing
application_interface.c
Go to the documentation of this file.
1 /*
2  * Copyright (c) 2016-2019 Cisco and/or its affiliates.
3  * Licensed under the Apache License, Version 2.0 (the "License");
4  * you may not use this file except in compliance with the License.
5  * You may obtain a copy of the License at:
6  *
7  * http://www.apache.org/licenses/LICENSE-2.0
8  *
9  * Unless required by applicable law or agreed to in writing, software
10  * distributed under the License is distributed on an "AS IS" BASIS,
11  * WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
12  * See the License for the specific language governing permissions and
13  * limitations under the License.
14  */
17 #include <vnet/session/session.h>
18 
19 /** @file
20  VPP's application/session API bind/unbind/connect/disconnect calls
21 */
22 
23 /**
24  * unformat a vnet URI
25  *
26  * transport-proto://[hostname]ip46-addr:port
27  * eg. tcp://ip46-addr:port
28  * tls://[testtsl.fd.io]ip46-addr:port
29  *
30  * u8 ip46_address[16];
31  * u16 port_in_host_byte_order;
32  * stream_session_type_t sst;
33  * u8 *fifo_name;
34  *
35  * if (unformat (input, "%U", unformat_vnet_uri, &ip46_address,
36  * &sst, &port, &fifo_name))
37  * etc...
38  *
39  */
40 uword
41 unformat_vnet_uri (unformat_input_t * input, va_list * args)
42 {
43  session_endpoint_cfg_t *sep = va_arg (*args, session_endpoint_cfg_t *);
45 
46  if (unformat (input, "%U://%U/%d", unformat_transport_proto,
47  &transport_proto, unformat_ip4_address, &sep->ip.ip4, &port))
48  {
49  sep->transport_proto = transport_proto;
50  sep->port = clib_host_to_net_u16 (port);
51  sep->is_ip4 = 1;
52  return 1;
53  }
54  else if (unformat (input, "%U://[%s]%U/%d", unformat_transport_proto,
55  &transport_proto, &sep->hostname, unformat_ip4_address,
56  &sep->ip.ip4, &port))
57  {
58  sep->transport_proto = transport_proto;
59  sep->port = clib_host_to_net_u16 (port);
60  sep->is_ip4 = 1;
61  return 1;
62  }
63  else if (unformat (input, "%U://%U/%d", unformat_transport_proto,
64  &transport_proto, unformat_ip6_address, &sep->ip.ip6,
65  &port))
66  {
67  sep->transport_proto = transport_proto;
68  sep->port = clib_host_to_net_u16 (port);
69  sep->is_ip4 = 0;
70  return 1;
71  }
72  else if (unformat (input, "%U://[%s]%U/%d", unformat_transport_proto,
73  &transport_proto, &sep->hostname, unformat_ip6_address,
74  &sep->ip.ip6, &port))
75  {
76  sep->transport_proto = transport_proto;
77  sep->port = clib_host_to_net_u16 (port);
78  sep->is_ip4 = 0;
79  return 1;
80  }
81  else if (unformat (input, "%U://session/%lu", unformat_transport_proto,
82  &transport_proto, &sep->parent_handle))
83  {
84  sep->transport_proto = transport_proto;
85  sep->ip.ip4.as_u32 = 1; /* ip need to be non zero in vnet */
86  return 1;
87  }
88  return 0;
89 }
90 
91 static u8 *cache_uri;
93 
94 int
96 {
97  unformat_input_t _input, *input = &_input;
98 
99  if (cache_uri && !strncmp (uri, (char *) cache_uri, vec_len (cache_uri)))
100  {
101  *sep = *cache_sep;
102  return 0;
103  }
104 
105  /* Make sure */
106  uri = (char *) format (0, "%s%c", uri, 0);
107 
108  /* Parse uri */
109  unformat_init_string (input, uri, strlen (uri));
110  if (!unformat (input, "%U", unformat_vnet_uri, sep))
111  {
112  unformat_free (input);
113  return VNET_API_ERROR_INVALID_VALUE;
114  }
115  unformat_free (input);
116 
117  vec_free (cache_uri);
118  cache_uri = (u8 *) uri;
119  if (cache_sep)
121  cache_sep = clib_mem_alloc (sizeof (*sep));
122  *cache_sep = *sep;
123 
124  return 0;
125 }
126 
127 int
129 {
131  int rv;
132 
133  rv = parse_uri (a->uri, &sep);
134  if (rv)
135  return rv;
136  sep.app_wrk_index = 0;
137  clib_memcpy (&a->sep_ext, &sep, sizeof (sep));
138  return vnet_listen (a);
139 }
140 
141 int
143 {
145  application_t *app;
147  u32 table_index;
148  int rv;
149 
150  if ((rv = parse_uri (a->uri, &sep)))
151  return rv;
152 
153  app = application_get (a->app_index);
154  if (!app)
155  return VNET_API_ERROR_INVALID_VALUE;
156 
157  table_index = application_session_table (app, fib_ip_proto (!sep.is_ip4));
158  listener = session_lookup_listener (table_index,
159  (session_endpoint_t *) & sep);
160  if (!listener)
161  return VNET_API_ERROR_ADDRESS_NOT_IN_USE;
162  a->handle = listen_session_get_handle (listener);
163  return vnet_unlisten (a);
164 }
165 
166 int
168 {
170  int rv;
171 
172  if ((rv = parse_uri (a->uri, &sep)))
173  return rv;
174 
175  clib_memcpy (&a->sep_ext, &sep, sizeof (sep));
176  if ((rv = vnet_connect (a)))
177  return rv;
178  return 0;
179 }
180 
181 /*
182  * fd.io coding-style-patch-verification: ON
183  *
184  * Local Variables:
185  * eval: (c-set-style "gnu")
186  * End:
187  */
session_t * session_lookup_listener(u32 table_index, session_endpoint_t *sep)
Lookup listener, exact or proxy (inaddr_any:0) match.
a
Definition: bitmap.h:538
transport_proto
Definition: session.api:22
struct _vnet_connect_args vnet_connect_args_t
struct _vnet_unlisten_args_t vnet_unlisten_args_t
u8 * format(u8 *s, const char *fmt,...)
Definition: format.c:424
int vnet_unlisten(vnet_unlisten_args_t *a)
Definition: application.c:1056
static u8 * cache_uri
unsigned char u8
Definition: types.h:56
struct _vnet_bind_args_t vnet_listen_args_t
#define clib_memcpy(d, s, n)
Definition: string.h:180
unformat_function_t unformat_ip4_address
Definition: format.h:68
static session_endpoint_cfg_t * cache_sep
unsigned int u32
Definition: types.h:88
void unformat_init_string(unformat_input_t *input, char *string, int string_len)
Definition: unformat.c:1029
struct _session_endpoint_cfg session_endpoint_cfg_t
struct _unformat_input_t unformat_input_t
u32 application_session_table(application_t *app, u8 fib_proto)
Definition: application.c:332
static u64 listen_session_get_handle(session_t *s)
Definition: session.h:563
unformat_function_t unformat_ip6_address
Definition: format.h:89
#define vec_free(V)
Free vector&#39;s memory (no header).
Definition: vec.h:380
application_t * application_get(u32 app_index)
Definition: application.c:426
int vnet_unbind_uri(vnet_unlisten_args_t *a)
uword unformat_transport_proto(unformat_input_t *input, va_list *args)
Definition: transport.c:155
int vnet_listen(vnet_listen_args_t *a)
Definition: application.c:965
static void clib_mem_free(void *p)
Definition: mem.h:215
static void * clib_mem_alloc(uword size)
Definition: mem.h:157
int vnet_connect(vnet_connect_args_t *a)
Definition: application.c:1019
int parse_uri(char *uri, session_endpoint_cfg_t *sep)
uword unformat_vnet_uri(unformat_input_t *input, va_list *args)
unformat a vnet URI
#define vec_len(v)
Number of elements in vector (rvalue-only, NULL tolerant)
static fib_protocol_t fib_ip_proto(bool is_ip6)
Convert from boolean is_ip6 to FIB protocol.
Definition: fib_types.h:80
u64 uword
Definition: types.h:112
int vnet_bind_uri(vnet_listen_args_t *a)
static void unformat_free(unformat_input_t *i)
Definition: format.h:163
#define SESSION_ENDPOINT_CFG_NULL
Definition: session_types.h:78
u16 port
Definition: lb_types.api:72
struct _session_endpoint session_endpoint_t
int vnet_connect_uri(vnet_connect_args_t *a)
uword unformat(unformat_input_t *i, const char *fmt,...)
Definition: unformat.c:978