examples/pipeline: add message passing mechanism
[dpdk.git] / examples / pipeline / main.c
1 /* SPDX-License-Identifier: BSD-3-Clause
2  * Copyright(c) 2020 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 "conn.h"
15 #include "obj.h"
16 #include "thread.h"
17
18 static const char usage[] =
19         "%s EAL_ARGS -- [-h HOST] [-p PORT] [-s SCRIPT]\n";
20
21 static struct app_params {
22         struct conn_params conn;
23         char *script_name;
24 } app = {
25         .conn = {
26                 .welcome = "\nWelcome!\n\n",
27                 .prompt = "pipeline> ",
28                 .addr = "0.0.0.0",
29                 .port = 8086,
30                 .buf_size = 1024 * 1024,
31                 .msg_in_len_max = 1024,
32                 .msg_out_len_max = 1024 * 1024,
33                 .msg_handle = NULL,
34                 .msg_handle_arg = NULL, /* set later. */
35         },
36         .script_name = NULL,
37 };
38
39 static int
40 parse_args(int argc, char **argv)
41 {
42         char *app_name = argv[0];
43         struct option lgopts[] = {
44                 { NULL,  0, 0, 0 }
45         };
46         int opt, option_index;
47         int h_present, p_present, s_present, n_args, i;
48
49         /* Skip EAL input args */
50         n_args = argc;
51         for (i = 0; i < n_args; i++)
52                 if (strcmp(argv[i], "--") == 0) {
53                         argc -= i;
54                         argv += i;
55                         break;
56                 }
57
58         if (i == n_args)
59                 return 0;
60
61         /* Parse args */
62         h_present = 0;
63         p_present = 0;
64         s_present = 0;
65
66         while ((opt = getopt_long(argc, argv, "h:p:s:", lgopts, &option_index))
67                         != EOF)
68                 switch (opt) {
69                 case 'h':
70                         if (h_present) {
71                                 printf("Error: Multiple -h arguments\n");
72                                 return -1;
73                         }
74                         h_present = 1;
75
76                         if (!strlen(optarg)) {
77                                 printf("Error: Argument for -h not provided\n");
78                                 return -1;
79                         }
80
81                         app.conn.addr = strdup(optarg);
82                         if (app.conn.addr == NULL) {
83                                 printf("Error: Not enough memory\n");
84                                 return -1;
85                         }
86                         break;
87
88                 case 'p':
89                         if (p_present) {
90                                 printf("Error: Multiple -p arguments\n");
91                                 return -1;
92                         }
93                         p_present = 1;
94
95                         if (!strlen(optarg)) {
96                                 printf("Error: Argument for -p not provided\n");
97                                 return -1;
98                         }
99
100                         app.conn.port = (uint16_t) atoi(optarg);
101                         break;
102
103                 case 's':
104                         if (s_present) {
105                                 printf("Error: Multiple -s arguments\n");
106                                 return -1;
107                         }
108                         s_present = 1;
109
110                         if (!strlen(optarg)) {
111                                 printf("Error: Argument for -s not provided\n");
112                                 return -1;
113                         }
114
115                         app.script_name = strdup(optarg);
116                         if (app.script_name == NULL) {
117                                 printf("Error: Not enough memory\n");
118                                 return -1;
119                         }
120                         break;
121
122                 default:
123                         printf(usage, app_name);
124                         return -1;
125                 }
126
127         optind = 1; /* reset getopt lib */
128
129         return 0;
130 }
131
132 int
133 main(int argc, char **argv)
134 {
135         struct conn *conn;
136         struct obj *obj;
137         int status;
138
139         /* Parse application arguments */
140         status = parse_args(argc, argv);
141         if (status < 0)
142                 return status;
143
144         /* EAL */
145         status = rte_eal_init(argc, argv);
146         if (status < 0) {
147                 printf("Error: EAL initialization failed (%d)\n", status);
148                 return status;
149         };
150
151         /* Obj */
152         obj = obj_init();
153         if (!obj) {
154                 printf("Error: Obj initialization failed (%d)\n", status);
155                 return status;
156         }
157
158         /* Thread */
159         status = thread_init();
160         if (status) {
161                 printf("Error: Thread initialization failed (%d)\n", status);
162                 return status;
163         }
164
165         rte_eal_mp_remote_launch(
166                 thread_main,
167                 NULL,
168                 SKIP_MASTER);
169
170         /* Connectivity */
171         app.conn.msg_handle_arg = obj;
172         conn = conn_init(&app.conn);
173         if (!conn) {
174                 printf("Error: Connectivity initialization failed (%d)\n",
175                         status);
176                 return status;
177         };
178
179         /* Dispatch loop */
180         for ( ; ; ) {
181                 conn_poll_for_conn(conn);
182
183                 conn_poll_for_msg(conn);
184         }
185 }