bypass_config_example.c Source File

Reference Documentation

Platform
Intel® PAC
Napatech SmartNIC
Content Type
Reference Information
Capture Software Version
Link™ Capture Software 12.10
Napatech Software Suite: examples/bypass/config/bypass_config_example.c Source File
bypass_config_example.c
Go to the documentation of this file.
1 /*
2  *
3  * Copyright 2023 Napatech A/S. All Rights Reserved.
4  *
5  * 1. Copying, modification, and distribution of this file, or executable
6  * versions of this file, is governed by the terms of the Napatech Software
7  * license agreement under which this file was made available. If you do not
8  * agree to the terms of the license do not install, copy, access or
9  * otherwise use this file.
10  *
11  * 2. Under the Napatech Software license agreement you are granted a
12  * limited, non-exclusive, non-assignable, copyright license to copy, modify
13  * and distribute this file in conjunction with Napatech SmartNIC's and
14  * similar hardware manufactured or supplied by Napatech A/S.
15  *
16  * 3. The full Napatech Software license agreement is included in this
17  * distribution, please see "NP-0405 Napatech Software license
18  * agreement.pdf"
19  *
20  * 4. Redistributions of source code must retain this copyright notice,
21  * list of conditions and the following disclaimer.
22  *
23  * THIS SOFTWARE IS PROVIDED "AS IS" WITHOUT ANY WARRANTIES, EXPRESS OR
24  * IMPLIED, AND NAPATECH DISCLAIMS ALL IMPLIED WARRANTIES INCLUDING ANY
25  * IMPLIED WARRANTY OF TITLE, MERCHANTABILITY, NONINFRINGEMENT, OR OF
26  * FITNESS FOR A PARTICULAR PURPOSE. TO THE EXTENT NOT PROHIBITED BY
27  * APPLICABLE LAW, IN NO EVENT SHALL NAPATECH BE LIABLE FOR PERSONAL INJURY,
28  * OR ANY INCIDENTAL, SPECIAL, INDIRECT OR CONSEQUENTIAL DAMAGES WHATSOEVER,
29  * INCLUDING, WITHOUT LIMITATION, DAMAGES FOR LOSS OF PROFITS, CORRUPTION OR
30  * LOSS OF DATA, FAILURE TO TRANSMIT OR RECEIVE ANY DATA OR INFORMATION,
31  * BUSINESS INTERRUPTION OR ANY OTHER COMMERCIAL DAMAGES OR LOSSES, ARISING
32  * OUT OF OR RELATED TO YOUR USE OR INABILITY TO USE NAPATECH SOFTWARE OR
33  * SERVICES OR ANY THIRD PARTY SOFTWARE OR APPLICATIONS IN CONJUNCTION WITH
34  * THE NAPATECH SOFTWARE OR SERVICES, HOWEVER CAUSED, REGARDLESS OF THE THEORY
35  * OF LIABILITY (CONTRACT, TORT OR OTHERWISE) AND EVEN IF NAPATECH HAS BEEN
36  * ADVISED OF THE POSSIBILITY OF SUCH DAMAGES. SOME JURISDICTIONS DO NOT ALLOW
37  * THE EXCLUSION OR LIMITATION OF LIABILITY FOR PERSONAL INJURY, OR OF
38  * INCIDENTAL OR CONSEQUENTIAL DAMAGES, SO THIS LIMITATION MAY NOT APPLY TO YOU.
39  *
40  *
41 
42  */
43 /**
44  * @example bypass/config/bypass_config_example.c
45  * @section Description Description
46  *
47  * This source file is an example of how to use the @ref ConfigStream
48  * "Configuration stream" interface in NTAPI for Napatech bypass accelerator and port configuration.
49  *
50  * This example switches the state of the relays every time it is run.
51  *
52  * The following NTAPI functions are used:
53  * - @ref NT_Init()
54  * - @ref NT_InfoOpen()
55  * - @ref NT_InfoRead()
56  * - @ref NT_InfoClose()
57  * - @ref NT_ConfigOpen()
58  * - @ref NT_ConfigWrite()
59  * - @ref NT_ConfigRead()
60  * - @ref NT_ConfigClose()
61  * - @ref NT_Done()
62  * - @ref NT_ExplainError()
63  *
64  * <hr>
65  * @section Prerequisites_l Prerequisites
66  * A working system is needed with a Napatech bypass accelerator.
67  *
68  * @section Flow Program flow
69  * @{
70  * The following is required to perform read and write operations on
71  * the @ref ConfigStream "configuration stream":
72  *
73  * - \#include/nt.h - Applications/Tools only need to include @ref
74  * nt.h to obtain prototypes, macros etc. from NTAPI.
75  * - @ref NT_Init(@ref NTAPI_VERSION) - Initialize the NTAPI
76  * library. @ref NTAPI_VERSION is a define that describes the version
77  * of the API described in the header files included by @ref
78  * nt.h. NT_Init() will ask the NTAPI library to convert return data
79  * to the @ref NTAPI_VERSION if possible. This will ensure that
80  * applications can run on NTAPI libraries of newer versions.
81  *
82  * - @ref NT_InfoOpen() - Open an info stream.
83  * - @ref NT_InfoRead() - Read info stream.
84  * - @ref NT_InfoClose() - Close the stream when terminating.
85  * - @ref NT_ConfigOpen() - Open a configuration stream.
86  * - @ref NT_ConfigRead() - Read configuration.
87  * - @ref NT_ConfigWrite() - Write configuration.
88  * - @ref NT_ConfigClose() - Close the stream when terminating.
89  * - @ref NT_Done() - Close down the NTAPI library.
90  * - @ref NT_ExplainError() - Explain an error code returned by NTAPI functions.
91  *
92  *<hr>
93  * @}
94  */
95 
96 
97 // Include this in order to access the Napatech API
98 #include <nt.h>
99 
100 #if defined(__linux__) || defined(__FreeBSD__)
101  #include <unistd.h>
102 #endif
103 
104 #include <stdlib.h>
105 #include <stdio.h>
106 #include <errno.h>
107 
108 
109 //
110 // main()
111 //
112 int main(void)
113 {
114  NtError_t status;
115  char errBuf[NT_ERRBUF_SIZE];
116  //
117  NtInfoStream_t hInfo;
118  NtInfo_t infoSystem;
119  NtInfo_t infoAdapter;
120  NtInfo_t infoPort;
121  //
122  NtConfigStream_t hConfig;
123  NtConfig_t configPort;
124  //
125  uint8_t adapter;
126  uint8_t port;
127  //
128  const char* aBpState[] = {"NA", "Normal", "Bypass"};
129  const char* aBpFlags[] = {"Off", "On"};
130 
131  //
132  //
133  //
134 
135  // Initialize NTAPI library
136  if ((status = NT_Init(NTAPI_VERSION)) != NT_SUCCESS) {
137  NT_ExplainError(status, errBuf, sizeof(errBuf));
138  fprintf(stderr, "ERROR: NT_Init failed. Code 0x%x = %s\n", status, errBuf);
139  return status;
140  }
141 
142  // Open the information stream
143  if ((status = NT_InfoOpen(&hInfo, "bypass_config_example")) != NT_SUCCESS) {
144  NT_ExplainError(status, errBuf, sizeof(errBuf));
145  fprintf(stderr, ">>> Error: NT_InfoOpen failed. Code 0x%x = %s\n", status, errBuf);
146  return status;
147  }
148 
149  // Read system information
150  infoSystem.cmd = NT_INFO_CMD_READ_SYSTEM;
151  if ((status = NT_InfoRead(hInfo, &infoSystem)) != NT_SUCCESS) {
152  NT_ExplainError(status, errBuf, sizeof(errBuf));
153  fprintf(stderr, "ERROR: NT_InfoRead failed. Code 0x%x = %s\n", status, errBuf);
154  return status;
155  }
156 
157  printf("System: %d.%d.%d.%d\n\n", infoSystem.u.system.data.version.major,
158  infoSystem.u.system.data.version.minor,
159  infoSystem.u.system.data.version.patch,
160  infoSystem.u.system.data.version.tag);
161  printf("Adapters: %u\n", infoSystem.u.system.data.numAdapters);
162  printf("Ports: %u\n", infoSystem.u.system.data.numPorts);
163  printf("\n");
164 
165  // Open the config stream
166  status = NT_ConfigOpen(&hConfig, "bypass_config_example");
167  if (status != NT_SUCCESS) {
168  NT_ExplainError(status, errBuf, sizeof(errBuf));
169  fprintf(stderr, ">>> Error: NT_ConfigOpen failed. Code 0x%x = %s\n", status, errBuf);
170  return status;
171  }
172 
173  for (adapter = 0; adapter < infoSystem.u.system.data.numAdapters; adapter++) {
174  infoAdapter.cmd = NT_INFO_CMD_READ_ADAPTER_V6;
175  infoAdapter.u.adapter_v6.adapterNo = adapter;
176  if ((status = NT_InfoRead(hInfo, &infoAdapter)) != 0) {
177  NT_ExplainError(status, errBuf, sizeof(errBuf));
178  fprintf(stderr, "ERROR: NT_InfoRead failed. Code 0x%x = %s\n", status, errBuf);
179  return status;
180  }
181  printf("Adapter %u (%u ports):\n", infoAdapter.u.adapter_v6.adapterNo, infoAdapter.u.adapter_v6.data.numPorts);
182 
183  configPort.parm = NT_CONFIG_PARM_BYPASS_ADAPTER;
184  configPort.u.bypassConfig.u.adapterNo = adapter;
185  status = NT_ConfigRead(hConfig, &configPort);
186  if (status != 0) {
187  NT_ExplainError(status, errBuf, sizeof(errBuf));
188  fprintf(stderr, "ERROR: NT_ConfigRead failed. Code 0x%x = %s\n", status, errBuf);
189  continue; // skip this and continue to next adapter
190  }
191  else {
192  //
193  // Invert bypass adapter state - based on the current bypass adapter state
194  // Skip this step if the already read bypass adapter state is unknown - this means that the ports can be individually configured.
195  //
202  } else {
207  }
208  }
209  //
210  // Then write the changed configuration back...
211  //
212  configPort.parm = NT_CONFIG_PARM_BYPASS_ADAPTER;
213  configPort.u.bypassConfig.u.adapterNo = adapter;
214  if ((status = NT_ConfigWrite(hConfig, &configPort)) != 0) {
215  NT_ExplainError(status, errBuf, sizeof(errBuf));
216  fprintf(stderr, "ERROR: NT_ConfigWrite failed. Code 0x%x = %s\n", status, errBuf);
217  return status;
218  }
219 
220  //
221  // Display bypass configuration for the adapter
222  //
223  configPort.parm = NT_CONFIG_PARM_BYPASS_ADAPTER;
224  configPort.u.bypassConfig.u.adapterNo = adapter;
225  if ((status = NT_ConfigRead(hConfig, &configPort)) != 0) {
226  NT_ExplainError(status, errBuf, sizeof(errBuf));
227  fprintf(stderr, "ERROR: NT_ConfigRead failed. Code 0x%x = %s\n", status, errBuf);
228  return status;
229  }
230 
231  printf(" bypass adapter current state: %s\n", aBpState[configPort.u.bypassConfig.data.currentBypassPortState]);
232  printf(" bypass adapter onInit state: %s\n", aBpState[configPort.u.bypassConfig.data.onInitBypassPortState]);
233  printf(" bypass adapter onPwrFail state: %s\n", aBpState[configPort.u.bypassConfig.data.onPowerFailBypassPortState]);
234  printf(" bypass adapter onWdtFail state: %s\n", aBpState[configPort.u.bypassConfig.data.onWatchdogFailBypassPortState]);
235  printf(" bypass adapter onPwrFail detect trigger: %s\n", aBpFlags[((configPort.u.bypassConfig.data.bypassTriggerModes & NT_BYPASS_TRIGGER_PWRFAIL)==0?0:1)]);
236  }
237  printf("\n");
238 
239  for (port = 0; port < infoAdapter.u.adapter_v6.data.numPorts; port++) {
240  infoPort.cmd = NT_INFO_CMD_READ_PORT_V9;
241  infoPort.u.port_v9.portNo = (uint8_t)(infoAdapter.u.adapter_v6.data.portOffset + port);
242  if ((status = NT_InfoRead(hInfo, &infoPort)) != 0) {
243  NT_ExplainError(status, errBuf, sizeof(errBuf));
244  fprintf(stderr, "ERROR: NT_InfoRead failed. Code 0x%x = %s\n", status, errBuf);
245  return status;
246  }
247 
248  printf(" Port %i (adapter #%i port #%i):\n", infoPort.u.port_v9.portNo, infoPort.u.port_v9.data.adapterNo, port);
249 
251  //
252  // There is no need to configure both ports in a bypass portset pair.
253  // You only need configure one of the ports in a bypass portset pair.
254  // The other port automatically will mirror the bypass configuration of the first port.
255  //
256  if ((port & 0x01) == 0) {
257  //
258  // Read current configuration
259  //
260  configPort.parm = NT_CONFIG_PARM_BYPASS_PORT;
261  configPort.u.bypassConfig.u.portNo = (uint8_t)(infoAdapter.u.adapter_v6.data.portOffset + port);
262  if ((status = NT_ConfigRead(hConfig, &configPort)) != 0) {
263  NT_ExplainError(status, errBuf, sizeof(errBuf));
264  fprintf(stderr, "ERROR: NT_ConfigRead failed. Code 0x%x = %s\n", status, errBuf);
265  return status;
266  }
267 
268  //
269  // Invert bypass portset state - based on the current bypass portset state
270  //
276  } else {
281  }
282  //
283  // Then write the changed configuration back...
284  //
285  configPort.parm = NT_CONFIG_PARM_BYPASS_PORT;
286  configPort.u.bypassConfig.u.portNo = (uint8_t)(infoAdapter.u.adapter_v6.data.portOffset + port);
287  if ((status = NT_ConfigWrite(hConfig, &configPort)) != 0) {
288  NT_ExplainError(status, errBuf, sizeof(errBuf));
289  fprintf(stderr, "ERROR: NT_ConfigWrite failed. Code 0x%x = %s\n", status, errBuf);
290  return status;
291  }
292  }
293 
294 
295  //
296  // Display result of configuration for all ports in a bypass portset
297  // The second port in a bypass portset should have mirrored the settings applied to the first port.
298  //
299  configPort.parm = NT_CONFIG_PARM_BYPASS_PORT;
300  configPort.u.bypassConfig.u.portNo = (uint8_t)(infoAdapter.u.adapter_v6.data.portOffset + port);
301  if ((status = NT_ConfigRead(hConfig, &configPort)) != 0) {
302  NT_ExplainError(status, errBuf, sizeof(errBuf));
303  fprintf(stderr, "ERROR: NT_ConfigRead failed. Code 0x%x = %s\n", status, errBuf);
304  return status;
305  }
306 
307  printf(" bypass port current state: %s\n", aBpState[configPort.u.bypassConfig.data.currentBypassPortState]);
308  printf(" bypass port onInit state: %s\n", aBpState[configPort.u.bypassConfig.data.onInitBypassPortState]);
309  printf(" bypass port onPwrFail state: %s\n", aBpState[configPort.u.bypassConfig.data.onPowerFailBypassPortState]);
310  printf(" bypass port onWdtFail state: %s\n", aBpState[configPort.u.bypassConfig.data.onWatchdogFailBypassPortState]);
311  printf(" bypass port onPwrFail detect trigger: %s\n", aBpFlags[((configPort.u.bypassConfig.data.bypassTriggerModes & NT_BYPASS_TRIGGER_PWRFAIL)==0?0:1)]);
312 
313  configPort.parm = NT_CONFIG_PARM_BYPASS_PORT;
314  configPort.u.bypassConfig.u.portNo = (uint8_t)(infoAdapter.u.adapter_v6.data.portOffset + port);
315  if ((status = NT_ConfigWrite(hConfig, &configPort)) != 0) {
316  NT_ExplainError(status, errBuf, sizeof(errBuf));
317  fprintf(stderr, "ERROR: NT_ConfigWrite failed. Code 0x%x = %s\n", status, errBuf);
318  return status;
319  }
320 
321  }
322  printf("\n");
323  }
324  printf("\n");
325  }
326  printf("\n");
327 
328  // Close down the NTAPI library
329  NT_Done();
330 
331  return 0;
332 }
333 
334 //
335 // EOF
336 //