New upstream version 18.11-rc1
[deb_dpdk.git] / examples / ip_pipeline / main.c
1 /* SPDX-License-Identifier: BSD-3-Clause
2  * Copyright(c) 2010-2018 Intel Corporation
3  */
4
5 #include <stdio.h>
6 #include <string.h>
7 #include <fcntl.h>
8 #include <unistd.h>
9 #include <getopt.h>
10
11 #include <rte_launch.h>
12 #include <rte_eal.h>
13
14 #include "cli.h"
15 #include "conn.h"
16 #include "kni.h"
17 #include "cryptodev.h"
18 #include "link.h"
19 #include "mempool.h"
20 #include "pipeline.h"
21 #include "swq.h"
22 #include "tap.h"
23 #include "thread.h"
24 #include "tmgr.h"
25
26 static const char usage[] =
27         "%s EAL_ARGS -- [-h HOST] [-p PORT] [-s SCRIPT]\n";
28
29 static const char welcome[] =
30         "\n"
31         "Welcome to IP Pipeline!\n"
32         "\n";
33
34 static const char prompt[] = "pipeline> ";
35
36 static struct app_params {
37         struct conn_params conn;
38         char *script_name;
39 } app = {
40         .conn = {
41                 .welcome = welcome,
42                 .prompt = prompt,
43                 .addr = "0.0.0.0",
44                 .port = 8086,
45                 .buf_size = 1024 * 1024,
46                 .msg_in_len_max = 1024,
47                 .msg_out_len_max = 1024 * 1024,
48                 .msg_handle = cli_process,
49         },
50         .script_name = NULL,
51 };
52
53 static int
54 parse_args(int argc, char **argv)
55 {
56         char *app_name = argv[0];
57         struct option lgopts[] = {
58                 { NULL,  0, 0, 0 }
59         };
60         int opt, option_index;
61         int h_present, p_present, s_present, n_args, i;
62
63         /* Skip EAL input args */
64         n_args = argc;
65         for (i = 0; i < n_args; i++)
66                 if (strcmp(argv[i], "--") == 0) {
67                         argc -= i;
68                         argv += i;
69                         break;
70                 }
71
72         if (i == n_args)
73                 return 0;
74
75         /* Parse args */
76         h_present = 0;
77         p_present = 0;
78         s_present = 0;
79
80         while ((opt = getopt_long(argc, argv, "h:p:s:", lgopts, &option_index))
81                         != EOF)
82                 switch (opt) {
83                 case 'h':
84                         if (h_present) {
85                                 printf("Error: Multiple -h arguments\n");
86                                 return -1;
87                         }
88                         h_present = 1;
89
90                         if (!strlen(optarg)) {
91                                 printf("Error: Argument for -h not provided\n");
92                                 return -1;
93                         }
94
95                         app.conn.addr = strdup(optarg);
96                         if (app.conn.addr == NULL) {
97                                 printf("Error: Not enough memory\n");
98                                 return -1;
99                         }
100                         break;
101
102                 case 'p':
103                         if (p_present) {
104                                 printf("Error: Multiple -p arguments\n");
105                                 return -1;
106                         }
107                         p_present = 1;
108
109                         if (!strlen(optarg)) {
110                                 printf("Error: Argument for -p not provided\n");
111                                 return -1;
112                         }
113
114                         app.conn.port = (uint16_t) atoi(optarg);
115                         break;
116
117                 case 's':
118                         if (s_present) {
119                                 printf("Error: Multiple -s arguments\n");
120                                 return -1;
121                         }
122                         s_present = 1;
123
124                         if (!strlen(optarg)) {
125                                 printf("Error: Argument for -s not provided\n");
126                                 return -1;
127                         }
128
129                         app.script_name = strdup(optarg);
130                         if (app.script_name == NULL) {
131                                 printf("Error: Not enough memory\n");
132                                 return -1;
133                         }
134                         break;
135
136                 default:
137                         printf(usage, app_name);
138                         return -1;
139                 }
140
141         optind = 1; /* reset getopt lib */
142
143         return 0;
144 }
145
146 int
147 main(int argc, char **argv)
148 {
149         struct conn *conn;
150         int status;
151
152         /* Parse application arguments */
153         status = parse_args(argc, argv);
154         if (status < 0)
155                 return status;
156
157         /* EAL */
158         status = rte_eal_init(argc, argv);
159         if (status < 0) {
160                 printf("Error: EAL initialization failed (%d)\n", status);
161                 return status;
162         };
163
164         /* Connectivity */
165         conn = conn_init(&app.conn);
166         if (conn == NULL) {
167                 printf("Error: Connectivity initialization failed (%d)\n",
168                         status);
169                 return status;
170         };
171
172         /* Mempool */
173         status = mempool_init();
174         if (status) {
175                 printf("Error: Mempool initialization failed (%d)\n", status);
176                 return status;
177         }
178
179         /* Link */
180         status = link_init();
181         if (status) {
182                 printf("Error: Link initialization failed (%d)\n", status);
183                 return status;
184         }
185
186         /* SWQ */
187         status = swq_init();
188         if (status) {
189                 printf("Error: SWQ initialization failed (%d)\n", status);
190                 return status;
191         }
192
193         /* Traffic Manager */
194         status = tmgr_init();
195         if (status) {
196                 printf("Error: TMGR initialization failed (%d)\n", status);
197                 return status;
198         }
199
200         /* TAP */
201         status = tap_init();
202         if (status) {
203                 printf("Error: TAP initialization failed (%d)\n", status);
204                 return status;
205         }
206
207         /* KNI */
208         status = kni_init();
209         if (status) {
210                 printf("Error: KNI initialization failed (%d)\n", status);
211                 return status;
212         }
213
214         /* Sym Crypto */
215         status = cryptodev_init();
216         if (status) {
217                 printf("Error: Cryptodev initialization failed (%d)\n",
218                                 status);
219                 return status;
220         }
221
222         /* Action */
223         status = port_in_action_profile_init();
224         if (status) {
225                 printf("Error: Input port action profile initialization failed (%d)\n", status);
226                 return status;
227         }
228
229         status = table_action_profile_init();
230         if (status) {
231                 printf("Error: Action profile initialization failed (%d)\n",
232                         status);
233                 return status;
234         }
235
236         /* Pipeline */
237         status = pipeline_init();
238         if (status) {
239                 printf("Error: Pipeline initialization failed (%d)\n", status);
240                 return status;
241         }
242
243         /* Thread */
244         status = thread_init();
245         if (status) {
246                 printf("Error: Thread initialization failed (%d)\n", status);
247                 return status;
248         }
249
250         rte_eal_mp_remote_launch(
251                 thread_main,
252                 NULL,
253                 SKIP_MASTER);
254
255         /* Script */
256         if (app.script_name)
257                 cli_script_process(app.script_name,
258                         app.conn.msg_in_len_max,
259                         app.conn.msg_out_len_max);
260
261         /* Dispatch loop */
262         for ( ; ; ) {
263                 conn_poll_for_conn(conn);
264
265                 conn_poll_for_msg(conn);
266
267                 kni_handle_request();
268         }
269 }