diff --git a/.gitignore b/.gitignore index 845cda6..65e98b7 100644 --- a/.gitignore +++ b/.gitignore @@ -1,3 +1,21 @@ +# +# .gitignore +# + +# primary configure file +./src/config.mk + +./thirdparty/cppfront/cppfront-compiler + +./src/tools/compiler/xdp2-compiler + +__pycache__/ +./src/tools/packets/falcon/__pycache__/ +./src/tools/packets/sue/__pycache__/ +./src/tools/packets/uet/__pycache__/ + +*.pcap + # Prerequisites *.d diff --git a/documentation/getting-started.md b/documentation/getting-started.md new file mode 100644 index 0000000..e00d0bc --- /dev/null +++ b/documentation/getting-started.md @@ -0,0 +1,587 @@ +# Getting started with XDP2 + +## Introduction + +This document is a guide to getting started with XDP2 + +It is intended for developers who are new to XDP2 and want to learn how to use it to program network devices + +This document covers both: +- "native" ( no nix ) +- with Nix + +## Prerequisites + +We are assuming access to a Ubuntu 22.04.3 LTS machine + +We also assume you have updated the packages ( because you are security concious ) +``` +sudo apt update +sudo apt --yes upgrade +``` + +Walkthrough machine has details: +``` +das@ubuntu2404-no-nix:~/xdp2/src$ cat /etc/lsb-release +DISTRIB_ID=Ubuntu +DISTRIB_RELEASE=24.04 +DISTRIB_CODENAME=noble +DISTRIB_DESCRIPTION="Ubuntu 24.04.3 LTS" +das@ubuntu2404-no-nix:~/xdp2/src$ uname -a +Linux ubuntu2404-no-nix 6.8.0-87-generic #88-Ubuntu SMP PREEMPT_DYNAMIC Sat Oct 11 09:28:41 UTC 2025 x86_64 x86_64 x86_64 GNU/Linux +``` + +## Native usage + +This section covers getting started with xdp2 using native Ubuntu ( without Nix ) + +### Overview of the steps + +1. Package installs +2. git clone +3. ./configure.sh +3.5 make clean +4. make cppfront +5. make +6. make install +7. ports_parser example + + +### Walkthrough + +#### 1. Package installs + +**Ubuntu Packages** Ubuntu has x2 forms of packages: un-numbered / numbered + +The most simple method is using no version specified. These seems to default to a version 18 of clang (as of 2025 November). ./src/configure was designed for this style of package names. +``` +sudo apt --yes install build-essential gcc gcc-multilib pkg-config bison flex \ + libboost-all-dev libpcap-dev python3-scapy graphviz libelf-dev libbpf-dev + +sudo apt-get --yes install llvm-dev clang libclang-dev clang-tools lld +sudo apt-get --yes install linux-tools-$(uname -r) +``` + +Ubuntu also has other specific versions available. We have been testing with version 20, but 17 and 19 is available also (untested currently). + +(Unfortunately?) the names of important binaries, like /usr/bin/llvm-config change to /usr/bin/llvm-config-20. + +Originally, the ./src/configure script didn't work with the versioned packages. There is an experimental ./src/configure.sh which adds the extra complexity of supporting the unverioned and versioned forms. + +``` +sudo apt install --yes build-essential gcc gcc-multilib pkg-config bison flex \ + libboost-all-dev libpcap-dev python3-scapy graphviz libelf-dev libbpf-dev + +sudo apt-get --yes install llvm-20-dev clang-20 libclang-20-dev clang-tools-20 lld-20 +sudo apt-get --yes install linux-tools-$(uname -r) +``` + +This walk through is designed to support both styles, so you are welcome to choose which you would prefer. + + +#### 2. git clone + +We will assume starting in your home directory "~". + +``` +git clone https://github.com/xdp2/xdp2.git +``` + +#### 3. configure.sh + +For this walk through, use the ".sh" version of configure + +``` +cd ~xdp2/src +./configure.sh +``` + +**Debugging configure** To allow debugging configure.sh, it supports an arugment --debug-level, which takes integer 0-7 (liek syslog levels). +``` +cd ~xdp2/src +./configure.sh --debug-level 7 +``` + +Example outputs + +Ubuntu with no versions: +``` +das@ubuntu2404-no-nix-no-version:~/xdp2/src$ ./configure.sh + + +Platform is default +Architecture is x86_64 +Architecture includes for x86_64 not found, using generic +Target Architecture is +COMPILER is gcc +LLVM_VER:18.1.3 +HOST_LLVM_CONFIG:/usr/bin/llvm-config +XDP2_CLANG_VERSION=18.1.3 +XDP2_C_INCLUDE_PATH=/usr/lib/llvm-18/lib/clang/18/include +XDP2_CLANG_RESOURCE_PATH=/usr/lib/llvm-18/lib/clang/18 + +das@ubuntu2404-no-nix-no-version:~/xdp2/src$ + +``` + +Ubuntu with versions, example with 20: +``` +das@ubuntu2404-no-nix:~/xdp2/src$ ./configure.sh + + +Platform is default +Architecture is x86_64 +Architecture includes for x86_64 not found, using generic +Target Architecture is +COMPILER is gcc +LLVM_VER:20.1.2 +HOST_LLVM_CONFIG:/usr/bin/llvm-config-20 +XDP2_CLANG_VERSION=20.1.2 +XDP2_C_INCLUDE_PATH=/usr/lib/llvm-20/lib/clang/20/include +XDP2_CLANG_RESOURCE_PATH=/usr/lib/llvm-20/lib/clang/20 + +das@ubuntu2404-no-nix:~/xdp2/src$ +``` + +configure.sh with debug-level 4 +``` +das@ubuntu2404-no-nix:~/xdp2/src$ ./configure.sh --debug-level 4 + + +Platform is default +Architecture is x86_64 +Architecture includes for x86_64 not found, using generic +Target Architecture is +COMPILER is gcc +[DEBUG-1] Tool Detection: Starting llvm-config detection +[DEBUG-2] Tool Detection: Auto-detecting llvm-config... +[DEBUG-3] Tool Detection: Checking for llvm-config +[DEBUG-3] Tool Detection: Checking for llvm-config-20 +[DEBUG-3] Tool Detection: Found llvm-config-20 at /usr/bin/llvm-config-20 +[DEBUG-1] Tool Detection: Selected llvm-config-20 (version 20.1.2) +LLVM_VER:20.1.2 +[DEBUG-1] Tool Detection: Using HOST_LLVM_CONFIG=/usr/bin/llvm-config-20 +HOST_LLVM_CONFIG:/usr/bin/llvm-config-20 +[DEBUG-1] Configuration: Platform=default, Architecture=x86_64, Compiler=gcc +[DEBUG-1] Clang.Lib: Starting check +[DEBUG-4] Clang.Lib: HOST_CXX=g++ +[DEBUG-4] Clang.Lib: HOST_LLVM_CONFIG=/usr/bin/llvm-config-20 +[DEBUG-4] Clang.Lib: llvm-config --ldflags: -L/usr/lib/llvm-20/lib +[DEBUG-4] Clang.Lib: llvm-config --cxxflags: -I/usr/lib/llvm-20/include -std=c++17 -fno-exceptions -funwind-tables -D_GNU_SOURCE -D__STDC_CONSTANT_MACROS -D__STDC_FORMAT_MACROS -D__STDC_LIMIT_MACROS +[DEBUG-4] Clang.Lib: llvm-config --libdir: /usr/lib/llvm-20/lib +[DEBUG-4] Clang.Lib: llvm-config --libs: -lLLVM-20 +[DEBUG-4] Clang.Lib: Found clang-cpp: libclang-cpp.so.20.1 -> using full path +[DEBUG-4] Clang.Lib: Found clangTooling: libclangTooling.a -> -lclangTooling +[DEBUG-3] Clang.Lib: Discovered clang libraries: /usr/lib/llvm-20/lib/libclang-cpp.so.20.1 -lclangTooling +[DEBUG-3] Clang.Lib: Attempting link with discovered libs: /usr/lib/llvm-20/lib/libclang-cpp.so.20.1 -lclangTooling +[DEBUG-1] Clang.Lib: Check PASSED with libraries: /usr/lib/llvm-20/lib/libclang-cpp.so.20.1 -lclangTooling +XDP2_CLANG_VERSION=20.1.2 +XDP2_C_INCLUDE_PATH=/usr/lib/llvm-20/lib/clang/20/include +XDP2_CLANG_RESOURCE_PATH=/usr/lib/llvm-20/lib/clang/20 + +das@ubuntu2404-no-nix:~/xdp2/src$ +``` + +If you succeed at using xdp2 on something other than ubuntu, please let us know! ( Please note xdp2 with nix on Fedora _is_ tested ) + +#### 3.3 make clean + +It will never hurt to run `make clean` before all of this ;) +``` +cd ~/xdp2/src/ +make clean +``` + +#### 4. make cppfront + +xdp2 uses an old version of cppfront, which should be built before anything else, as this is a dependancy. + +``` +cd ~/xdp2/thirdparty/cppfront +make +``` + +Example from ubuntu no versions +``` +das@ubuntu2404-no-nix-no-version:~/xdp2/src$ cd ~/xdp2/thirdparty/cppfront +das@ubuntu2404-no-nix-no-version:~/xdp2/thirdparty/cppfront$ make +g++ -std=c++20 source/cppfront.cpp -o cppfront-compiler +das@ubuntu2404-no-nix-no-version:~/xdp2/thirdparty/cppfront$ ls -la +total 5208 +drwxr-xr-x 4 das das 4096 Nov 6 17:56 . +drwxr-xr-x 5 das das 4096 Oct 2 00:22 .. +-rw-r--r-- 1 das das 5756 Oct 2 00:22 CODE_OF_CONDUCT.md +-rw-r--r-- 1 das das 1027 Oct 2 00:22 CONTRIBUTING.md +-rwxrwxr-x 1 das das 5270624 Nov 6 17:56 cppfront-compiler <------------ +-rw-r--r-- 1 das das 253 Oct 2 00:22 .gitignore +drwxr-xr-x 2 das das 4096 Nov 5 05:14 include +-rw-r--r-- 1 das das 530 Oct 2 00:22 LICENSE +-rw-r--r-- 1 das das 255 Oct 2 00:22 Makefile +-rw-r--r-- 1 das das 19485 Oct 2 00:22 README.md +drwxr-xr-x 2 das das 4096 Oct 2 00:22 source +das@ubuntu2404-no-nix-no-version:~/xdp2/thirdparty/cppfront$ sha256sum cppfront-compiler +d941dd0c74f37377770f9e3a4aefaa43df7403a9b24215d3256a4e62863ba482 cppfront-compiler +das@ubuntu2404-no-nix-no-version:~/xdp2/thirdparty/cppfront$ +``` + +Ubuntu llvm20 +``` +das@ubuntu2404-no-nix:~/xdp2/thirdparty/cppfront$ sha256sum cppfront-compiler +26d37f784f43a7766e5f892c49a7337e7e0b7858d4fd3b65dec59e8c23846569 cppfront-compiler +``` + +#### 5. make +Once cppfront is compiled, it's time to build xdp2 + +``` +cd ~/xdp2/src +make clean +make +``` + +Example output +``` +das@ubuntu2404-no-nix-no-version:~/xdp2/src$ make + +tools +include/xdp2gen/llvm/patterns.h2... ok (mixed Cpp1/Cpp2, Cpp2 code passes safety checks) + +include/xdp2gen/ast-consumer/patterns.h2... ok (mixed Cpp1/Cpp2, Cpp2 code passes safety checks) + +... + LINK test_bitmap + CC main.o + CC cli.o + CC test_packets_rx.o + CC test_packets_tx.o + CC test_packets.o + LINK test_uet + CC main.o + CC cli.o + CC test_packets_rx.o + CC test_packets_tx.o + CC test_packets.o + LINK test_falcon +das@ubuntu2404-no-nix-no-version:~/xdp2/src$ +das@ubuntu2404-no-nix-no-version:~/xdp2/src$ ls -la ./tools/compiler/xdp2-compiler +-rwxrwxr-x 1 das das 38783152 Nov 6 19:46 ./tools/compiler/xdp2-compiler +das@ubuntu2404-no-nix-no-version:~/xdp2/src$ file ./tools/compiler/xdp2-compiler +./tools/compiler/xdp2-compiler: ELF 64-bit LSB pie executable, x86-64, version 1 (GNU/Linux), dynamically linked, interpreter /lib64/ld-linux-x86-64.so.2, BuildID[sha1]=5003d9629f8319c0c7fcdbfb3abae7c215c540d2, for GNU/Linux 3.2.0, with debug_info, not stripped +das@ubuntu2404-no-nix-no-version:~/xdp2/src$ sha256sum ./tools/compiler/xdp2-compiler +5ee68877f374f9493b4e156cdc554b571dcf25d4096710388eba82dd0a70f5e0 ./tools/compiler/xdp2-compiler +``` + +``` +das@ubuntu2404-no-nix:~/xdp2/src$ make + +tools +include/xdp2gen/llvm/patterns.h2... ok (mixed Cpp1/Cpp2, Cpp2 code passes safety checks) + +include/xdp2gen/ast-consumer/patterns.h2... ok (mixed Cpp1/Cpp2, Cpp2 code passes safety checks) + +... + LINK test_bitmap + CC main.o + CC cli.o + CC test_packets_rx.o + CC test_packets_tx.o + CC test_packets.o + LINK test_uet + CC main.o + CC cli.o + CC test_packets_rx.o + CC test_packets_tx.o + CC test_packets.o + LINK test_falcon +das@ubuntu2404-no-nix:~/xdp2/src$ +das@ubuntu2404-no-nix:~/xdp2/src$ ls -la ./tools/compiler/xdp2-compiler +-rwxrwxr-x 1 das das 39306864 Nov 6 19:46 ./tools/compiler/xdp2-compiler +das@ubuntu2404-no-nix:~/xdp2/src$ file ./tools/compiler/xdp2-compiler +./tools/compiler/xdp2-compiler: ELF 64-bit LSB pie executable, x86-64, version 1 (GNU/Linux), dynamically linked, interpreter /lib64/ld-linux-x86-64.so.2, BuildID[sha1]=c7409d48c698a5a871307d8369fdf15d881d5d7d, for GNU/Linux 3.2.0, with debug_info, not stripped +das@ubuntu2404-no-nix:~/xdp2/src$ sha256sum ./tools/compiler/xdp2-compiler +b21e4b9f3074b25d8c62c2ed8f12aedecf2bf3d96881cc18c0d75459452cc7e6 ./tools/compiler/xdp2-compiler +das@ubuntu2404-no-nix:~/xdp2/src$ +``` + +#### 6. make install + +The default INSTALLDIR is `../install/x86_64` from `src/`, which resolves to `~/xdp2/install/x86_64/` (keeps everything in the xdp2 repository directory). + +``` +cd ~/xdp2/src +make install +``` + +``` +das@ubuntu2404-no-nix-no-version:~$ cd ~/xdp2/src +das@ubuntu2404-no-nix-no-version:~/xdp2/src$ make install + +tools +include/xdp2gen/llvm/patterns.h2... ok (mixed Cpp1/Cpp2, Cpp2 code passes safety checks) + +include/xdp2gen/ast-consumer/patterns.h2... ok (mixed Cpp1/Cpp2, Cpp2 code passes safety checks) + +... + +test + INSTALL test_vstructs + INSTALL test_switch + INSTALL + INSTALL test_timer + INSTALL test_pvbuf + INSTALL test_parser + INSTALL + INSTALL test_accel + INSTALL + INSTALL test_bitmap + INSTALL + INSTALL + +xdp2 installed into directory: /home/das/xdp2/src/../install/x86_64 +das@ubuntu2404-no-nix-no-version:~/xdp2/src$ +``` + +#### 7. xdp2 samples + +With xdp2-compiler built and installed, we can now try using some of the samples, which are in ~/xdp2/samples/ + +**Important:** The sample Makefile-s needs to know where xdp2 is installed. Set `XDP2DIR` to point to your installation directory (without the architecture suffix). + +The samples rely on the environment variable XDP2DIR, which should be set to the same as INSTALLDIR. +``` +das@ubuntu2404-no-nix-no-version:~/xdp2/samples$ cat ~/xdp2/src/config.mk | grep INSTALLDIR +INSTALLDIR ?= /home/das/xdp2/src/../install/x86_64 +``` + + +Example output: +``` +das@ubuntu2404-no-nix-no-version:~/xdp2/samples$ make XDP2DIR=~/xdp2/install/x86_64 +make[1]: Entering directory '/home/das/xdp2/samples/parser' +make[2]: Entering directory '/home/das/xdp2/samples/parser/offset_parser' +gcc -I/home/das/xdp2/install/x86_64/include -g -c -o parser.o parser.c +parser.c: In function ‘extract_network’: +parser.c:62:40: error: ‘const struct xdp2_ctrl_data’ has no member named ‘hdr’ + 62 | metadata->network_offset = ctrl.hdr.hdr_offset; + | ^ +parser.c: In function ‘extract_transport’: +parser.c:71:42: error: ‘const struct xdp2_ctrl_data’ has no member named ‘hdr’ + 71 | metadata->transport_offset = ctrl.hdr.hdr_offset; + | ^ +In file included from parser.c:42: +parser.c: At top level: +parser.c:77:47: warning: initialization of ‘void (*)(const void *, size_t, size_t, void *, void *, const struct xdp2_ctrl_data *)’ {aka ‘void (*)(const void *, long unsigned int, long unsigned int, void *, void *, const struct xdp2_ctrl_data *)’} from incompatible pointer type ‘void (*)(const void *, void *, const struct xdp2_ctrl_data)’ [-Wincompatible-pointer-types] + 77 | (.ops.extract_metadata = extract_network)); + | ^~~~~~~~~~~~~~~ +/home/das/xdp2/install/x86_64/include/xdp2/parser.h:209:49: note: in definition of macro ‘__XDP2_MAKE_PARSE_NODE_OPT_ONE’ + 209 | #define __XDP2_MAKE_PARSE_NODE_OPT_ONE(OPT) .pn OPT, + | ^~~ +/home/das/xdp2/install/x86_64/include/xdp2/pmacro.h:54:25: note: in expansion of macro ‘__XDP2_PMACRO_APPLY1’ + 54 | __XDP2_PMACRO_APPLY##NUM(ACT, __VA_ARGS__) + | ^~~~~~~~~~~~~~~~~~~ +/home/das/xdp2/install/x86_64/include/xdp2/pmacro.h:57:25: note: in expansion of macro ‘__XDP2_PMACRO_APPLY_ALL_3’ + 57 | __XDP2_PMACRO_APPLY_ALL_3(ACT, NUM, __VA_ARGS__) + | ^~~~~~~~~~~~~~~~~~~~~~~~~ +/home/das/xdp2/install/x86_64/include/xdp2/pmacro.h:60:9: note: in expansion of macro ‘__XDP2_PMACRO_APPLY_ALL_2’ + 60 | __XDP2_PMACRO_APPLY_ALL_2(ACT, \ + | ^~~~~~~~~~~~~~~~~~~~~~~~~ +/home/das/xdp2/install/x86_64/include/xdp2/parser.h:218:17: note: in expansion of macro ‘XDP2_PMACRO_APPLY_ALL’ + 218 | XDP2_PMACRO_APPLY_ALL( \ + | ^~~~~~~~~~~~~~~~~~~~~ +/home/das/xdp2/install/x86_64/include/xdp2/utility.h:80:24: note: in expansion of macro ‘XDP2_DEPAIR2’ + 80 | #define XDP2_DEPAIR(X) XDP2_DEPAIR2 X + | ^~~~~~~~~~~~ +/home/das/xdp2/install/x86_64/include/xdp2/parser.h:220:33: note: in expansion of macro ‘XDP2_DEPAIR’ + 220 | XDP2_DEPAIR(EXTRA)) + | ^~~~~~~~~~~ +/home/das/xdp2/install/x86_64/include/xdp2/parser.h:228:17: note: in expansion of macro ‘__XDP2_MAKE_PARSE_NODE_COMMON’ + 228 | __XDP2_MAKE_PARSE_NODE_COMMON(PARSE_NODE, PROTO_DEF, \ + | ^~~~~~~~~~~~~~~~~~~~~~~~~~~~~ +parser.c:76:1: note: in expansion of macro ‘XDP2_MAKE_PARSE_NODE’ + 76 | XDP2_MAKE_PARSE_NODE(ipv4_node, xdp2_parse_ipv4, ip_table, + | ^~~~~~~~~~~~~~~~~~~~ +parser.c:77:47: note: (near initialization for ‘ipv4_node.pn.ops.extract_metadata’) + 77 | (.ops.extract_metadata = extract_network)); + | ^~~~~~~~~~~~~~~ +/home/das/xdp2/install/x86_64/include/xdp2/parser.h:209:49: note: in definition of macro ‘__XDP2_MAKE_PARSE_NODE_OPT_ONE’ + 209 | #define __XDP2_MAKE_PARSE_NODE_OPT_ONE(OPT) .pn OPT, + | ^~~ +/home/das/xdp2/install/x86_64/include/xdp2/pmacro.h:54:25: note: in expansion of macro ‘__XDP2_PMACRO_APPLY1’ + 54 | __XDP2_PMACRO_APPLY##NUM(ACT, __VA_ARGS__) + | ^~~~~~~~~~~~~~~~~~~ +/home/das/xdp2/install/x86_64/include/xdp2/pmacro.h:57:25: note: in expansion of macro ‘__XDP2_PMACRO_APPLY_ALL_3’ + 57 | __XDP2_PMACRO_APPLY_ALL_3(ACT, NUM, __VA_ARGS__) + | ^~~~~~~~~~~~~~~~~~~~~~~~~ +/home/das/xdp2/install/x86_64/include/xdp2/pmacro.h:60:9: note: in expansion of macro ‘__XDP2_PMACRO_APPLY_ALL_2’ + 60 | __XDP2_PMACRO_APPLY_ALL_2(ACT, \ + | ^~~~~~~~~~~~~~~~~~~~~~~~~ +/home/das/xdp2/install/x86_64/include/xdp2/parser.h:218:17: note: in expansion of macro ‘XDP2_PMACRO_APPLY_ALL’ + 218 | XDP2_PMACRO_APPLY_ALL( \ + | ^~~~~~~~~~~~~~~~~~~~~ +/home/das/xdp2/install/x86_64/include/xdp2/utility.h:80:24: note: in expansion of macro ‘XDP2_DEPAIR2’ + 80 | #define XDP2_DEPAIR(X) XDP2_DEPAIR2 X + | ^~~~~~~~~~~~ +/home/das/xdp2/install/x86_64/include/xdp2/parser.h:220:33: note: in expansion of macro ‘XDP2_DEPAIR’ + 220 | XDP2_DEPAIR(EXTRA)) + | ^~~~~~~~~~~ +/home/das/xdp2/install/x86_64/include/xdp2/parser.h:228:17: note: in expansion of macro ‘__XDP2_MAKE_PARSE_NODE_COMMON’ + 228 | __XDP2_MAKE_PARSE_NODE_COMMON(PARSE_NODE, PROTO_DEF, \ + | ^~~~~~~~~~~~~~~~~~~~~~~~~~~~~ +parser.c:76:1: note: in expansion of macro ‘XDP2_MAKE_PARSE_NODE’ + 76 | XDP2_MAKE_PARSE_NODE(ipv4_node, xdp2_parse_ipv4, ip_table, + | ^~~~~~~~~~~~~~~~~~~~ +parser.c:79:47: warning: initialization of ‘void (*)(const void *, size_t, size_t, void *, void *, const struct xdp2_ctrl_data *)’ {aka ‘void (*)(const void *, long unsigned int, long unsigned int, void *, void *, const struct xdp2_ctrl_data *)’} from incompatible pointer type ‘void (*)(const void *, void *, const struct xdp2_ctrl_data)’ [-Wincompatible-pointer-types] + 79 | (.ops.extract_metadata = extract_network)); + | ^~~~~~~~~~~~~~~ +/home/das/xdp2/install/x86_64/include/xdp2/parser.h:209:49: note: in definition of macro ‘__XDP2_MAKE_PARSE_NODE_OPT_ONE’ + 209 | #define __XDP2_MAKE_PARSE_NODE_OPT_ONE(OPT) .pn OPT, + | ^~~ +/home/das/xdp2/install/x86_64/include/xdp2/pmacro.h:54:25: note: in expansion of macro ‘__XDP2_PMACRO_APPLY1’ + 54 | __XDP2_PMACRO_APPLY##NUM(ACT, __VA_ARGS__) + | ^~~~~~~~~~~~~~~~~~~ +/home/das/xdp2/install/x86_64/include/xdp2/pmacro.h:57:25: note: in expansion of macro ‘__XDP2_PMACRO_APPLY_ALL_3’ + 57 | __XDP2_PMACRO_APPLY_ALL_3(ACT, NUM, __VA_ARGS__) + | ^~~~~~~~~~~~~~~~~~~~~~~~~ +/home/das/xdp2/install/x86_64/include/xdp2/pmacro.h:60:9: note: in expansion of macro ‘__XDP2_PMACRO_APPLY_ALL_2’ + 60 | __XDP2_PMACRO_APPLY_ALL_2(ACT, \ + | ^~~~~~~~~~~~~~~~~~~~~~~~~ +/home/das/xdp2/install/x86_64/include/xdp2/parser.h:218:17: note: in expansion of macro ‘XDP2_PMACRO_APPLY_ALL’ + 218 | XDP2_PMACRO_APPLY_ALL( \ + | ^~~~~~~~~~~~~~~~~~~~~ +/home/das/xdp2/install/x86_64/include/xdp2/utility.h:80:24: note: in expansion of macro ‘XDP2_DEPAIR2’ + 80 | #define XDP2_DEPAIR(X) XDP2_DEPAIR2 X + | ^~~~~~~~~~~~ +/home/das/xdp2/install/x86_64/include/xdp2/parser.h:220:33: note: in expansion of macro ‘XDP2_DEPAIR’ + 220 | XDP2_DEPAIR(EXTRA)) + | ^~~~~~~~~~~ +/home/das/xdp2/install/x86_64/include/xdp2/parser.h:228:17: note: in expansion of macro ‘__XDP2_MAKE_PARSE_NODE_COMMON’ + 228 | __XDP2_MAKE_PARSE_NODE_COMMON(PARSE_NODE, PROTO_DEF, \ + | ^~~~~~~~~~~~~~~~~~~~~~~~~~~~~ +parser.c:78:1: note: in expansion of macro ‘XDP2_MAKE_PARSE_NODE’ + 78 | XDP2_MAKE_PARSE_NODE(ipv6_node, xdp2_parse_ipv6, ip_table, + | ^~~~~~~~~~~~~~~~~~~~ +parser.c:79:47: note: (near initialization for ‘ipv6_node.pn.ops.extract_metadata’) + 79 | (.ops.extract_metadata = extract_network)); + | ^~~~~~~~~~~~~~~ +/home/das/xdp2/install/x86_64/include/xdp2/parser.h:209:49: note: in definition of macro ‘__XDP2_MAKE_PARSE_NODE_OPT_ONE’ + 209 | #define __XDP2_MAKE_PARSE_NODE_OPT_ONE(OPT) .pn OPT, + | ^~~ +/home/das/xdp2/install/x86_64/include/xdp2/pmacro.h:54:25: note: in expansion of macro ‘__XDP2_PMACRO_APPLY1’ + 54 | __XDP2_PMACRO_APPLY##NUM(ACT, __VA_ARGS__) + | ^~~~~~~~~~~~~~~~~~~ +/home/das/xdp2/install/x86_64/include/xdp2/pmacro.h:57:25: note: in expansion of macro ‘__XDP2_PMACRO_APPLY_ALL_3’ + 57 | __XDP2_PMACRO_APPLY_ALL_3(ACT, NUM, __VA_ARGS__) + | ^~~~~~~~~~~~~~~~~~~~~~~~~ +/home/das/xdp2/install/x86_64/include/xdp2/pmacro.h:60:9: note: in expansion of macro ‘__XDP2_PMACRO_APPLY_ALL_2’ + 60 | __XDP2_PMACRO_APPLY_ALL_2(ACT, \ + | ^~~~~~~~~~~~~~~~~~~~~~~~~ +/home/das/xdp2/install/x86_64/include/xdp2/parser.h:218:17: note: in expansion of macro ‘XDP2_PMACRO_APPLY_ALL’ + 218 | XDP2_PMACRO_APPLY_ALL( \ + | ^~~~~~~~~~~~~~~~~~~~~ +/home/das/xdp2/install/x86_64/include/xdp2/utility.h:80:24: note: in expansion of macro ‘XDP2_DEPAIR2’ + 80 | #define XDP2_DEPAIR(X) XDP2_DEPAIR2 X + | ^~~~~~~~~~~~ +/home/das/xdp2/install/x86_64/include/xdp2/parser.h:220:33: note: in expansion of macro ‘XDP2_DEPAIR’ + 220 | XDP2_DEPAIR(EXTRA)) + | ^~~~~~~~~~~ +/home/das/xdp2/install/x86_64/include/xdp2/parser.h:228:17: note: in expansion of macro ‘__XDP2_MAKE_PARSE_NODE_COMMON’ + 228 | __XDP2_MAKE_PARSE_NODE_COMMON(PARSE_NODE, PROTO_DEF, \ + | ^~~~~~~~~~~~~~~~~~~~~~~~~~~~~ +parser.c:78:1: note: in expansion of macro ‘XDP2_MAKE_PARSE_NODE’ + 78 | XDP2_MAKE_PARSE_NODE(ipv6_node, xdp2_parse_ipv6, ip_table, + | ^~~~~~~~~~~~~~~~~~~~ +parser.c:81:47: warning: initialization of ‘void (*)(const void *, size_t, size_t, void *, void *, const struct xdp2_ctrl_data *)’ {aka ‘void (*)(const void *, long unsigned int, long unsigned int, void *, void *, const struct xdp2_ctrl_data *)’} from incompatible pointer type ‘void (*)(const void *, void *, const struct xdp2_ctrl_data)’ [-Wincompatible-pointer-types] + 81 | (.ops.extract_metadata = extract_transport)); + | ^~~~~~~~~~~~~~~~~ +/home/das/xdp2/install/x86_64/include/xdp2/parser.h:209:49: note: in definition of macro ‘__XDP2_MAKE_PARSE_NODE_OPT_ONE’ + 209 | #define __XDP2_MAKE_PARSE_NODE_OPT_ONE(OPT) .pn OPT, + | ^~~ +/home/das/xdp2/install/x86_64/include/xdp2/pmacro.h:54:25: note: in expansion of macro ‘__XDP2_PMACRO_APPLY1’ + 54 | __XDP2_PMACRO_APPLY##NUM(ACT, __VA_ARGS__) + | ^~~~~~~~~~~~~~~~~~~ +/home/das/xdp2/install/x86_64/include/xdp2/pmacro.h:57:25: note: in expansion of macro ‘__XDP2_PMACRO_APPLY_ALL_3’ + 57 | __XDP2_PMACRO_APPLY_ALL_3(ACT, NUM, __VA_ARGS__) + | ^~~~~~~~~~~~~~~~~~~~~~~~~ +/home/das/xdp2/install/x86_64/include/xdp2/pmacro.h:60:9: note: in expansion of macro ‘__XDP2_PMACRO_APPLY_ALL_2’ + 60 | __XDP2_PMACRO_APPLY_ALL_2(ACT, \ + | ^~~~~~~~~~~~~~~~~~~~~~~~~ +/home/das/xdp2/install/x86_64/include/xdp2/parser.h:218:17: note: in expansion of macro ‘XDP2_PMACRO_APPLY_ALL’ + 218 | XDP2_PMACRO_APPLY_ALL( \ + | ^~~~~~~~~~~~~~~~~~~~~ +/home/das/xdp2/install/x86_64/include/xdp2/utility.h:80:24: note: in expansion of macro ‘XDP2_DEPAIR2’ + 80 | #define XDP2_DEPAIR(X) XDP2_DEPAIR2 X + | ^~~~~~~~~~~~ +/home/das/xdp2/install/x86_64/include/xdp2/parser.h:220:33: note: in expansion of macro ‘XDP2_DEPAIR’ + 220 | XDP2_DEPAIR(EXTRA)) + | ^~~~~~~~~~~ +/home/das/xdp2/install/x86_64/include/xdp2/parser.h:248:17: note: in expansion of macro ‘__XDP2_MAKE_PARSE_NODE_COMMON’ + 248 | __XDP2_MAKE_PARSE_NODE_COMMON(PARSE_NODE, PROTO_DEF, \ + | ^~~~~~~~~~~~~~~~~~~~~~~~~~~~~ +parser.c:80:1: note: in expansion of macro ‘XDP2_MAKE_LEAF_PARSE_NODE’ + 80 | XDP2_MAKE_LEAF_PARSE_NODE(ports_node, xdp2_parse_ports, + | ^~~~~~~~~~~~~~~~~~~~~~~~~ +parser.c:81:47: note: (near initialization for ‘ports_node.pn.ops.extract_metadata’) + 81 | (.ops.extract_metadata = extract_transport)); + | ^~~~~~~~~~~~~~~~~ +/home/das/xdp2/install/x86_64/include/xdp2/parser.h:209:49: note: in definition of macro ‘__XDP2_MAKE_PARSE_NODE_OPT_ONE’ + 209 | #define __XDP2_MAKE_PARSE_NODE_OPT_ONE(OPT) .pn OPT, + | ^~~ +/home/das/xdp2/install/x86_64/include/xdp2/pmacro.h:54:25: note: in expansion of macro ‘__XDP2_PMACRO_APPLY1’ + 54 | __XDP2_PMACRO_APPLY##NUM(ACT, __VA_ARGS__) + | ^~~~~~~~~~~~~~~~~~~ +/home/das/xdp2/install/x86_64/include/xdp2/pmacro.h:57:25: note: in expansion of macro ‘__XDP2_PMACRO_APPLY_ALL_3’ + 57 | __XDP2_PMACRO_APPLY_ALL_3(ACT, NUM, __VA_ARGS__) + | ^~~~~~~~~~~~~~~~~~~~~~~~~ +/home/das/xdp2/install/x86_64/include/xdp2/pmacro.h:60:9: note: in expansion of macro ‘__XDP2_PMACRO_APPLY_ALL_2’ + 60 | __XDP2_PMACRO_APPLY_ALL_2(ACT, \ + | ^~~~~~~~~~~~~~~~~~~~~~~~~ +/home/das/xdp2/install/x86_64/include/xdp2/parser.h:218:17: note: in expansion of macro ‘XDP2_PMACRO_APPLY_ALL’ + 218 | XDP2_PMACRO_APPLY_ALL( \ + | ^~~~~~~~~~~~~~~~~~~~~ +/home/das/xdp2/install/x86_64/include/xdp2/utility.h:80:24: note: in expansion of macro ‘XDP2_DEPAIR2’ + 80 | #define XDP2_DEPAIR(X) XDP2_DEPAIR2 X + | ^~~~~~~~~~~~ +/home/das/xdp2/install/x86_64/include/xdp2/parser.h:220:33: note: in expansion of macro ‘XDP2_DEPAIR’ + 220 | XDP2_DEPAIR(EXTRA)) + | ^~~~~~~~~~~ +/home/das/xdp2/install/x86_64/include/xdp2/parser.h:248:17: note: in expansion of macro ‘__XDP2_MAKE_PARSE_NODE_COMMON’ + 248 | __XDP2_MAKE_PARSE_NODE_COMMON(PARSE_NODE, PROTO_DEF, \ + | ^~~~~~~~~~~~~~~~~~~~~~~~~~~~~ +parser.c:80:1: note: in expansion of macro ‘XDP2_MAKE_LEAF_PARSE_NODE’ + 80 | XDP2_MAKE_LEAF_PARSE_NODE(ports_node, xdp2_parse_ports, + | ^~~~~~~~~~~~~~~~~~~~~~~~~ +parser.c: In function ‘run_parser’: +parser.c:111:33: error: storage size of ‘pdata’ isn’t known + 111 | struct xdp2_packet_data pdata; + | ^~~~~ +parser.c:122:17: warning: implicit declaration of function ‘XDP2_SET_BASIC_PDATA_LEN_SEQNO’ [-Wimplicit-function-declaration] + 122 | XDP2_SET_BASIC_PDATA_LEN_SEQNO(pdata, packet, plen, + | ^~~~~~~~~~~~~~~~~~~~~~~~~~~~~~ +parser.c:125:44: warning: passing argument 3 of ‘xdp2_parse’ makes integer from pointer without a cast [-Wint-conversion] + 125 | xdp2_parse(parser, &pdata, &metadata, 0); + | ^~~~~~~~~ + | | + | struct metadata * +/home/das/xdp2/install/x86_64/include/xdp2/parser.h:297:48: note: expected ‘size_t’ {aka ‘long unsigned int’} but argument is of type ‘struct metadata *’ + 297 | void *hdr, size_t len, + | ~~~~~~~^~~ +parser.c:125:17: error: too few arguments to function ‘xdp2_parse’ + 125 | xdp2_parse(parser, &pdata, &metadata, 0); + | ^~~~~~~~~~ +/home/das/xdp2/install/x86_64/include/xdp2/parser.h:296:19: note: declared here + 296 | static inline int xdp2_parse(const struct xdp2_parser *parser, + | ^~~~~~~~~~ +make[2]: *** [: parser.o] Error 1 +make[2]: Leaving directory '/home/das/xdp2/samples/parser/offset_parser' +make[1]: *** [Makefile:14: offset_parser] Error 2 +make[1]: Leaving directory '/home/das/xdp2/samples/parser' +make: *** [Makefile:14: parser] Error 2 +das@ubuntu2404-no-nix-no-version:~/xdp2/samples$ +``` + + +## Nix usage + +This section covers how to get started with xdp2 using the Nix development environment. + + \ No newline at end of file diff --git a/flake.nix b/flake.nix index ff12506..ef57bc6 100644 --- a/flake.nix +++ b/flake.nix @@ -1,6 +1,8 @@ # # flake.nix for XDP2 - Development Shell Only # +# WARNING - THIS FLAKE IS CURRENTLY BROKEN (2025/11/06) FIXES COMING SOON +# # This flake.nix provides a fast development environment for the XDP2 project # # To enter the development environment: @@ -151,7 +153,11 @@ # Clang environment variables for xdp2-compiler export XDP2_CLANG_VERSION="$(${llvmP.llvm.dev}/bin/llvm-config --version)" export XDP2_C_INCLUDE_PATH="${llvmP.clang-unwrapped.dev}/include/clang" - export XDP2_CLANG_RESOURCE_PATH="${llvmP.clang-unwrapped.dev}/include/clang" + + # NOTE: We intentionally do NOT set XDP2_CLANG_RESOURCE_PATH here. + # Let clang auto-detect its resource directory, which works correctly in Nix + # via the clang-wrapper that sets up the resource-root symlink. + # export XDP2_CLANG_RESOURCE_PATH="${llvmP.clang-unwrapped.dev}/include/clang" # Python environment export CFLAGS_PYTHON="$(pkg-config --cflags python3-embed)" @@ -216,7 +222,7 @@ echo "config.mk not found, running configure script..." cd src || return 1 rm -f config.mk - ./configure --build-opt-parser --installdir "/tmp/xdp2-install" + ./configure.sh --build-opt-parser # Apply PATH_ARG fix for Nix environment if grep -q 'PATH_ARG="--with-path=' config.mk; then @@ -332,7 +338,7 @@ echo "[DEBUG] build-cppfront completed in $duration seconds" fi - echo "cppfront-compiler built and validated successfully" + echo "cppfront-compiler built and validated successfully ( ./thirdparty/cppfront/cppfront-compiler )" } ''; @@ -489,7 +495,7 @@ echo "[DEBUG] build-xdp2-compiler completed in $duration seconds" fi - echo "xdp2-compiler built and validated successfully" + echo "xdp2-compiler built and validated successfully ( ./src/tools/compiler/xdp2-compiler )" } ''; @@ -778,32 +784,32 @@ Exiting development shell..." 🐛 Debugging tools: gdb, valgrind, strace, ltrace 🔍 DEBUGGING: - XDP2_NIX_DEBUG=0 - No extra debug. Default - XDP2_NIX_DEBUG=3 - Basic debug - XDP2_NIX_DEBUG=5 - Show compiler selection and config.mk - XDP2_NIX_DEBUG=7 - Show all debug info + XDP2_NIX_DEBUG=0 - No extra debug. Default + XDP2_NIX_DEBUG=3 - Basic debug + XDP2_NIX_DEBUG=5 - Show compiler selection and config.mk + XDP2_NIX_DEBUG=7 - Show all debug info 🔧 BUILD COMMANDS: - build-cppfront - Build cppfront compiler - build-xdp2-compiler - Build xdp2 compiler - build-xdp2 - Build main XDP2 project - build-all - Build all components + build-cppfront - Build cppfront compiler + build-xdp2-compiler - Build xdp2 compiler + build-xdp2 - Build main XDP2 project + build-all - Build all components 🧹 CLEAN COMMANDS: - clean-cppfront - Clean cppfront build artifacts - clean-xdp2-compiler - Clean xdp2-compiler build artifacts - clean-xdp2 - Clean xdp2 build artifacts - clean-all - Clean all build artifacts + clean-cppfront - Clean cppfront build artifacts + clean-xdp2-compiler - Clean xdp2-compiler build artifacts + clean-xdp2 - Clean xdp2 build artifacts + clean-all - Clean all build artifacts 🔍 VALIDATION: - run-shellcheck - Validate all shell functions + run-shellcheck - Validate all shell functions 📁 PROJECT STRUCTURE: - • src/ - Main source code - • tools/ - Build tools and utilities - • thirdparty/ - Third-party dependencies - • samples/ - Example code and parsers - • documentation/ - Project documentation + • src/ - Main source code + • tools/ - Build tools and utilities + • thirdparty/ - Third-party dependencies + • samples/ - Example code and parsers + • documentation/ - Project documentation 🎯 Ready to develop! 'xdp2-help' for help" } diff --git a/samples/README.md b/samples/README.md new file mode 100644 index 0000000..5bb35ae --- /dev/null +++ b/samples/README.md @@ -0,0 +1,21 @@ +# xdp2 samples + +This folder contains the samples for the xdp2 project. + +## Usage + +Set XDP2DIR to the install directory for XDP2 like +``` +make XDP2DIR=~/xdp2/install +``` + +This should probably be set to the same as: +``` +das@ubuntu2404-no-nix-no-version:~/xdp2/samples$ cat ~/xdp2/src/config.mk | grep INSTALLDIR +INSTALLDIR ?= /home/das/xdp2/src/../install/x86_64 +``` + +Therefore, recommend: +``` +make XDP2DIR=~/xdp2/install/x86_64/ +``` \ No newline at end of file diff --git a/src/Makefile b/src/Makefile index 6267bbe..407e222 100644 --- a/src/Makefile +++ b/src/Makefile @@ -7,10 +7,13 @@ TOP_LEVEL_MAKE= ifeq ($(VERBOSE),0) MAKEFLAGS += --no-print-directory -s +export MAKEFLAGS MFLAGS += -s endif ifneq ($(V), 1) +MAKEFLAGS += -s +export MAKEFLAGS MFLAGS += -s endif @@ -73,7 +76,7 @@ SUBDIRS= tools include lib test all: config.mk $(EXTRA_TARGETS) @set -e; \ for i in $(SUBDIRS); \ - do echo; echo $$i; $(MAKE) $(MFLAGS) -C $$i; done + do echo; echo $$i; $(MAKE) -C $$i; done config.mk: bash configure $(KERNEL_INCLUDE) @@ -85,7 +88,9 @@ install: all @install -m 0755 -d $(INSTALLDIR)$(ETCDIR) @install -m 0755 -d $(INSTALLDIR)$(HDRDIR) @for i in $(SUBDIRS); \ - do echo; echo $$i; $(MAKE) $(MFLAGS) -C $$i install; done + do echo; echo $$i; $(MAKE) -C $$i install; done + @echo "" + @echo "xdp2 installed into directory: $(INSTALLDIR)" install_data: install @rm -rf $(INSTALLDIR)/data @@ -105,7 +110,7 @@ install_all_tar: install_all .PHONY: kernel kernel: - @$(MAKE) $(MFLAGS) -C kernel KDIR=$(KDIR) + @$(MAKE) -C kernel KDIR=$(KDIR) snapshot: echo "static const char SNAPSHOT[] = \""`date +%y%m%d`"\";" \ @@ -117,11 +122,11 @@ help: clean: @rm -rf $(INSTALLDIR) @for i in $(SUBDIRS) ; \ - do $(MAKE) $(MFLAGS) -C $$i clean; done + do $(MAKE) -C $$i clean; done clobber: touch config.mk - $(MAKE) $(MFLAGS) clean + $(MAKE) clean rm -f config.mk cscope.* distclean: clobber diff --git a/src/configure.sh b/src/configure.sh new file mode 100755 index 0000000..9caf6b5 --- /dev/null +++ b/src/configure.sh @@ -0,0 +1,795 @@ +#!/bin/bash +# +# configure.sh +# +# configure.sh is an experimental version of ./configure, which has some tweaks +# Major changes including: +# - supporting detection of different versions of clang on ubuntu systems +# - adjustments to the c++ embedded code to support clang18 and clang20 +# +# This is not autoconf generated +# +INCLUDE=${1:-"$PWD/include"} + +# Output file which is input to Makefile +CONFIG=config.mk +# Make a temp directory in build tree +TMPDIR=$(mktemp -d config.XXXXXX) +trap 'status=$?; rm -rf $TMPDIR; exit $status' EXIT HUP INT QUIT TERM + +# Global variable to store discovered clang libraries +CLANG_LIBS_DISCOVERED="" + +# Debug function for progressive debugging (0-7, like syslog) +# Level 0: No debug output (default) +# Level 1-2: Basic information (detected tools, paths) +# Level 3-4: Command execution details +# Level 5-6: Full command output, environment variables +# Level 7: Maximum verbosity (all intermediate steps, test program contents) +debug_print() { + local level=$1 + shift + if [ "${CONFIGURE_DEBUG_LEVEL:-0}" -ge "$level" ]; then + echo "[DEBUG-$level] $*" >&2 + fi +} + +check_prog() +{ + echo -n "$2" + # fails shellcheck SC2015 + command -v "$1" >/dev/null 2>&1 && (echo "$3:=y" >> $CONFIG; echo "yes") || + (echo "no"; return 1) +} + +check_libpcap() +{ + cat >"$TMPDIR"/pcaptest.c < +int main(int argc, char **argv) +{ + pcap_t *p; + char errbuf[PCAP_ERRBUF_SIZE]; + + p = pcap_open_offline("foo", &errbuf[0]); + pcap_close(p); + return (0); +} +EOF + $CC_GCC -o "$TMPDIR"/pcaptest "$TMPDIR"/pcaptest.c \ + -lpcap > /dev/null 2>"$TMPDIR"/pcaplog + + case $? in + 0) ;; + *) echo libpcap missing or broken\! 1>&2 + echo ERROR LOG: + cat "$TMPDIR"/pcaplog + exit 1 + ;; + esac + rm -f "$TMPDIR"/pcaptest.c "$TMPDIR"/pcaptest +} + +check_boostwave() +{ + cat >"$TMPDIR"/wavetest.cpp < + +struct test : boost::wave::context_policies::default_preprocessing_hooks { +}; + +int main(int argc, char **argv) +{ + return (0); +} +EOF + $HOST_CXX -o "$TMPDIR"/wavetest "$TMPDIR"/wavetest.cpp \ + -lboost_system -lboost_wave + case $? in + 0) ;; + *) echo Boost.Wave missing or broken\! 1>&2 + exit 1 + ;; + esac + rm -f "$TMPDIR"/wavetest.cpp "$TMPDIR"/wavetest +} + +check_boostthread() +{ + cat >"$TMPDIR"/threadtest.cpp < + +int main(int argc, char **argv) +{ + { + boost::mutex m; + } + return (0); +} +EOF + $HOST_CXX -o "$TMPDIR"/threadtest "$TMPDIR"/threadtest.cpp \ + -lboost_thread -lboost_system >/dev/null 2>&1 + case $? in + 0) ;; + *) echo Boost.Thread missing or broken\! 1>&2 + exit 1 + ;; + esac + rm -f "$TMPDIR"/threadtest.cpp "$TMPDIR"/threadtest +} + +check_boostsystem() +{ + debug_print 6 "Boost.System: Starting check" + cat >"$TMPDIR"/systemtest.cpp < + +int main(int argc, char **argv) +{ + { + boost::system::error_code ec; + } + return (0); +} +EOF + if [ "${CONFIGURE_DEBUG_LEVEL:-0}" -ge 5 ]; then + $HOST_CXX -o "$TMPDIR"/systemtest "$TMPDIR"/systemtest.cpp -lboost_system + COMPILE_EXIT=$? + else + $HOST_CXX -o "$TMPDIR"/systemtest "$TMPDIR"/systemtest.cpp \ + -lboost_system > /dev/null 2>&1 + COMPILE_EXIT=$? + fi + case $COMPILE_EXIT in + 0) + debug_print 6 "Boost.System: Check PASSED" + ;; + *) + debug_print 6 "Boost.System: Check FAILED (exit code: $COMPILE_EXIT)" + echo Boost.System missing or broken\! 1>&2 + exit 1 + ;; + esac + rm -f "$TMPDIR"/systemtest.cpp "$TMPDIR"/systemtest +} + +check_boostfilesystem() +{ + cat >"$TMPDIR"/filesystemtest.cpp < + +int main(int argc, char **argv) +{ + { + boost::filesystem::path p; + } + return (0); +} +EOF + $HOST_CXX -o "$TMPDIR"/filesystemtest "$TMPDIR"/filesystemtest.cpp \ + -lboost_system -lboost_filesystem > /dev/null 2>&1 + case $? in + 0) ;; + *) echo Boost.Filesystem missing or broken\! 1>&2 + exit 1 + ;; + esac + rm -f "$TMPDIR"/filesystemtest.cpp "$TMPDIR"/filesystemtest +} + +check_clang_lib() +{ + debug_print 1 "Clang.Lib: Starting check" + debug_print 4 "Clang.Lib: HOST_CXX=$HOST_CXX" + debug_print 4 "Clang.Lib: HOST_LLVM_CONFIG=$HOST_LLVM_CONFIG" + + cat > "$TMPDIR"/clang_lib.cpp < +#include "clang/Tooling/CommonOptionsParser.h" +#include "clang/Tooling/Tooling.h" +#include "llvm/Support/CommandLine.h" +#include "clang/Lex/PreprocessorOptions.h" + +static llvm::cl::OptionCategory MyToolCategory("my-tool options"); + +int main(int argc, const char **argv) +{ + // Define our own category to be compatible with all Clang versions, + // avoiding issues with getClangSyntaxOnlyCategory/getSyntaxOnlyToolCategory. + static llvm::cl::OptionCategory TestCategory("Test Tool"); + auto ExpectedParser = clang::tooling::CommonOptionsParser::create(argc, argv, TestCategory); + return 0; +} +EOF + + debug_print 7 "Clang.Lib: Test program created at $TMPDIR/clang_lib.cpp" + if [ "${CONFIGURE_DEBUG_LEVEL:-0}" -ge 7 ]; then + debug_print 7 "Clang.Lib: Test program contents:" + cat "$TMPDIR"/clang_lib.cpp >&2 + fi + + # Test if llvm-config exists and works before using it + if ! command -v "$HOST_LLVM_CONFIG" >/dev/null 2>&1 && [ ! -f "$HOST_LLVM_CONFIG" ]; then + debug_print 1 "Clang.Lib: Error: $HOST_LLVM_CONFIG not found!" + echo "Error: $HOST_LLVM_CONFIG not found!" 1>&2 + echo "Clang library missing or broken! (Failed in check_clang_lib() #1)" 1>&2 + exit 1 + fi + + # Get llvm-config flags + LLVM_LDFLAGS=`$HOST_LLVM_CONFIG --ldflags 2>&1` + LLVM_CXXFLAGS=`$HOST_LLVM_CONFIG --cxxflags 2>&1` + LLVM_LIBDIR=`$HOST_LLVM_CONFIG --libdir 2>&1` + debug_print 4 "Clang.Lib: llvm-config --ldflags: $LLVM_LDFLAGS" + debug_print 4 "Clang.Lib: llvm-config --cxxflags: $LLVM_CXXFLAGS" + debug_print 4 "Clang.Lib: llvm-config --libdir: $LLVM_LIBDIR" + LLVM_LIBS=`$HOST_LLVM_CONFIG --libs 2>/dev/null` + debug_print 4 "Clang.Lib: llvm-config --libs: $LLVM_LIBS" + + # Discover clang libraries needed for the test program + # The test program uses clang::tooling::CommonOptionsParser, so we need: + # 1. clang-cpp (C++ interface library) - shared library preferred + # 2. clangTooling (tooling functionality) - exact match libclangTooling.a/so + CLANG_LIBS_FOUND="" + + if [ -d "$LLVM_LIBDIR" ]; then + debug_print 5 "Clang.Lib: Scanning $LLVM_LIBDIR for required clang libraries..." + + # Find clang-cpp shared library - look for exact name first, then versioned + # Try exact match first: libclang-cpp.so + CLANG_CPP_LIB="" + if [ -f "$LLVM_LIBDIR/libclang-cpp.so" ] || [ -L "$LLVM_LIBDIR/libclang-cpp.so" ]; then + CLANG_CPP_LIB="$LLVM_LIBDIR/libclang-cpp.so" + else + # Find versioned: libclang-cpp.so.18.1 or libclang-cpp.so.18 + # Include both regular files and symlinks + CLANG_CPP_LIB=$(find "$LLVM_LIBDIR" -maxdepth 1 -name "libclang-cpp.so*" \( -type f -o -type l \) 2>/dev/null | sort -V | head -1) + fi + + if [ -n "$CLANG_CPP_LIB" ] && { [ -f "$CLANG_CPP_LIB" ] || [ -L "$CLANG_CPP_LIB" ]; }; then + # Check if there's a symlink libclang-cpp.so (without version) + if [ -L "$LLVM_LIBDIR/libclang-cpp.so" ] || [ -f "$LLVM_LIBDIR/libclang-cpp.so" ]; then + # Use -l flag if symlink exists + CLANG_LIBS_FOUND="$CLANG_LIBS_FOUND -lclang-cpp" + debug_print 4 "Clang.Lib: Found clang-cpp: $(basename $CLANG_CPP_LIB) -> -lclang-cpp (via symlink)" + else + # Use full path if no symlink exists + CLANG_LIBS_FOUND="$CLANG_LIBS_FOUND $CLANG_CPP_LIB" + debug_print 4 "Clang.Lib: Found clang-cpp: $(basename $CLANG_CPP_LIB) -> using full path" + fi + else + debug_print 2 "Clang.Lib: Warning: clang-cpp library not found in $LLVM_LIBDIR" + fi + + # Find clangTooling library - must be exact match libclangTooling.a or .so + # This provides CommonOptionsParser and other tooling functionality + CLANG_TOOLING_LIB="" + if [ -f "$LLVM_LIBDIR/libclangTooling.so" ]; then + CLANG_TOOLING_LIB="$LLVM_LIBDIR/libclangTooling.so" + elif [ -f "$LLVM_LIBDIR/libclangTooling.a" ]; then + CLANG_TOOLING_LIB="$LLVM_LIBDIR/libclangTooling.a" + fi + + if [ -n "$CLANG_TOOLING_LIB" ] && [ -f "$CLANG_TOOLING_LIB" ]; then + # Static libraries can use -l flag, shared libraries too if symlink exists + if echo "$CLANG_TOOLING_LIB" | grep -q "\.a$"; then + # Static library - use -l flag + CLANG_LIBS_FOUND="$CLANG_LIBS_FOUND -lclangTooling" + debug_print 4 "Clang.Lib: Found clangTooling: $(basename $CLANG_TOOLING_LIB) -> -lclangTooling" + else + # Shared library - check for symlink + if [ -L "$LLVM_LIBDIR/libclangTooling.so" ] || [ -f "$LLVM_LIBDIR/libclangTooling.so" ]; then + CLANG_LIBS_FOUND="$CLANG_LIBS_FOUND -lclangTooling" + debug_print 4 "Clang.Lib: Found clangTooling: $(basename $CLANG_TOOLING_LIB) -> -lclangTooling" + else + CLANG_LIBS_FOUND="$CLANG_LIBS_FOUND $CLANG_TOOLING_LIB" + debug_print 4 "Clang.Lib: Found clangTooling: $(basename $CLANG_TOOLING_LIB) -> using full path" + fi + fi + fi + + # Clean up the library list + CLANG_LIBS_FOUND=$(echo "$CLANG_LIBS_FOUND" | sed 's/^ *//;s/ *$//') + + if [ -n "$CLANG_LIBS_FOUND" ]; then + debug_print 3 "Clang.Lib: Discovered clang libraries: $CLANG_LIBS_FOUND" + else + debug_print 2 "Clang.Lib: Required clang libraries not found in $LLVM_LIBDIR" + fi + fi + + # Create a temporary output file + TMPO=$(mktemp "$TMPDIR/clang_lib.XXXXXX") + + # Build compilation command with discovered libraries + ALL_LIBS="$LLVM_LIBS $CLANG_LIBS_FOUND" + CMD="$HOST_CXX -o $TMPO $TMPDIR/clang_lib.cpp $LLVM_LDFLAGS $LLVM_CXXFLAGS $ALL_LIBS" + + debug_print 3 "Clang.Lib: Attempting link with discovered libs: $CLANG_LIBS_FOUND" + debug_print 5 "Clang.Lib: Full command: $CMD" + + # Try compilation + if [ "${CONFIGURE_DEBUG_LEVEL:-0}" -ge 5 ]; then + $CMD + COMPILE_EXIT=$? + else + $CMD >/dev/null 2>&1 + COMPILE_EXIT=$? + fi + + if [ $COMPILE_EXIT -eq 0 ]; then + debug_print 1 "Clang.Lib: Check PASSED with libraries: $CLANG_LIBS_FOUND" + # Store discovered libraries in global variable for writing to config.mk + # Include LLVM library flag from llvm-config --libs along with discovered clang libraries + CLANG_LIBS_DISCOVERED="$LLVM_LIBS $CLANG_LIBS_FOUND" + debug_print 3 "Clang.Lib: Stored CLANG_LIBS_DISCOVERED: $CLANG_LIBS_DISCOVERED" + rm -f "$TMPDIR"/clang_lib.cpp "$TMPO" + return 0 + fi + + # If compilation failed, exit with error + debug_print 1 "Clang.Lib: Check FAILED (exit code: $COMPILE_EXIT)" + debug_print 3 "Clang.Lib: Attempted libraries: $CLANG_LIBS_FOUND" + debug_print 3 "Clang.Lib: Library directory: $LLVM_LIBDIR" + if [ "${CONFIGURE_DEBUG_LEVEL:-0}" -ge 3 ]; then + debug_print 3 "Clang.Lib: Available clang libraries in $LLVM_LIBDIR:" + ls -1 "$LLVM_LIBDIR"/libclang* 2>/dev/null | sed 's/^/ /' >&2 || echo " (none found)" >&2 + fi + echo "Clang library missing or broken!" 1>&2 + echo "Failed command was: $CMD" 1>&2 + exit 1 + + #unreachable shellcheck SC2317? + rm -f "$TMPDIR"/clang_lib.cpp "$TMPDIR"/clang +} + +check_python() +{ + cat >"$TMPDIR"/check_python.cpp < + +int main(int argc, char **argv) +{ + return (0); +} +EOF + $HOST_CXX -o "$TMPDIR"/check_python "$TMPDIR"/check_python.cpp \ + `$PKG_CONFIG --cflags --libs python3-embed` + case $? in + 0) ;; + *) echo Python missing or broken\! 1>&2 + exit 1 + ;; + esac + rm -f "$TMPDIR"/check_python.cpp "$TMPDIR"/check_python +} + +check_scapy() +{ + python3 -c "import scapy.all; print('scapy OK')" >/dev/null 2>&1 + case $? in + 0) echo "HAVE_SCAPY:=y" >> $CONFIG + ;; + *) echo "ERROR: scapy is required but not found!" 1>&2 + echo "Please install scapy: ( pip3 install scapy | apt install python3-scapy )" 1>&2 + exit 1 + ;; + esac +} + +check_cross_compiler_environment() +{ + if [ ! -d "$DEF_CC_ENV_LOC" ]; then + echo "$DEF_CC_ENV_LOC is not found!" + # SC2242 shellcheck + exit -1 + fi + + if [ ! -d "$SYSROOT_LOC" ]; then + echo "$SYSROOT_LOC is not found!" + # SC2242 shellcheck + exit -1 + fi + + if [ ! -d "$CC_ENV_TOOLCHAIN" ]; then + echo "$CC_ENV_TOOLCHAIN is not found!" + # SC2242 shellcheck + exit -1 + fi +} + +quiet_config() +{ + cat < ]" +} + +PLATFORMS=($(ls ../platforms)) + +PLATFORM="default" + +if [ "$1" == "--platform" ]; then + PLATFORM=$2 + PLATFORM_TEXT=$2 + shift 2 +fi + +for i in ${PLATFORMS[@]}; do + if [ "$PLATFORM" == "$i" ]; then + FOUND_PLAT="true" + fi +done + +if [ "$FOUND_PLAT" != "true" ]; then + usage_platforms "${PLATFORMS[*]}" + exit +fi + +usage() +{ + echo -n "Usage: $0" + if [ -n "$PLATFORM_TEXT" ]; then + echo -n " --platform $PLATFORM_TEXT" + fi + + echo " [--config-defines ]" + echo " [--ccarch ]" + echo " [--arch ]" + echo " [--compiler ]" + echo " [--installdir ]" + echo " [--build-opt-parser]" + echo " [--build-parser-json]" + echo " [--no-build-compiler]" + echo " [--pkg-config-path ]" + echo " [--llvm-config ]" + echo " [--debug-level <0-7>]" + echo "" + echo " ( also VERBOSE like kernel builds, see also quiet_config() )" + + platform_usage + + exit 1 +} + +source ../platforms/"$PLATFORM"/src/configure + +init_platform + +COMPILER="gcc" + +# Show debug level if set +if [ -n "${CONFIGURE_DEBUG_LEVEL}" ]; then + debug_print 1 "Debug Level: ${CONFIGURE_DEBUG_LEVEL}" +fi + + while [ -n "$1" ]; do + case $1 in + "--config-defines") CONFIG_DEFINES=$2; shift;; + "--ccarch") TARGET_ARCH=$2; shift;; + "--arch") ARCH=$2; shift;; + "--compiler") COMPILER=$2; shift;; + "--pkg-config-path") MY_PKG_CONFIG_PATH=$2; shift;; + "--installdir") INSTALLDIR=$2; shift;; + "--build-opt-parser") BUILD_OPT_PARSER="y";; + "--build-parser-json") BUILD_PARSER_JSON="y";; + "--no-build-compiler") NO_BUILD_COMPILER="y";; + "--llvm-config") HOST_LLVM_CONFIG=$2; shift;; + "--debug-level") CONFIGURE_DEBUG_LEVEL=$2; shift;; + *) parse_platform_opts $1;; + esac + shift +done + +if [ -n "$MY_PKG_CONFIG_PATH" ]; then + if [ -n "$PKG_CONFIG_PATH" ]; then + export PKG_CONFIG_PATH="$MY_PKG_CONFIG_PATH:$PKG_CONFIG_PATH" + else + export PKG_CONFIG_PATH="$MY_PKG_CONFIG_PATH" + fi +fi + +if [ "$NO_BUILD_COMPILER" == "y" ]; then + if [ "$BUILD_OPT_PARSER" == "y" ]; then + echo -n "No build compiler and optimized parser cannot be " + echo "configured at the same time" + # SC2242 shellcheck + exit -1 + fi + if [ "$BUILD_PARSER_JSON" == "y" ]; then + echo -n "No build compiler an build parser .json cannot be " + echo "configured at the same time" + # SC2242 shellcheck + exit -1 + fi +fi + +echo "# Generated config based on" $INCLUDE >$CONFIG +echo "ifneq (\$(TOP_LEVEL_MAKE),y)" >> $CONFIG +quiet_config >> $CONFIG + +if [ -n "$PKG_CONFIG_PATH" ]; then + echo "PKG_CONFIG_PATH=$PKG_CONFIG_PATH" >> $CONFIG + # PATH_ARG is empty because pkg-config automatically uses PKG_CONFIG_PATH from environment + echo "PATH_ARG=\"\"" >> $CONFIG +else + echo "PATH_ARG=\"\"" >> $CONFIG +fi + +echo -n 'CFLAGS_PYTHON=`$(PKG_CONFIG) $(PATH_ARG)' >> $CONFIG +echo ' --cflags python3-embed`' >> $CONFIG +echo -n 'LDFLAGS_PYTHON=`$(PKG_CONFIG) $(PATH_ARG) --libs' >> $CONFIG +echo ' python3-embed`' >> $CONFIG +echo 'CAT=cat' >> $CONFIG + +# Set up architecture variables +LLVM_CONFIG="llvm-config" +CC_GCC="gcc" +if [ "$COMPILER" == "clang" ]; then + CC_GCC="clang" +fi +CC_CXX="g++" +CC_AR="ar" +CFLAGS_N="" +LIBS_N="" +LIBS_NL="" + +if [ -z "$ARCH" ]; then + # Architecture was not set from command line, try to determine + + if [ -n "$TARGET_ARCH" ]; then + ARCH="$TARGET_ARCH" + else + ARCH="`uname -m`" + fi +fi + +set_platform_opts + +: ${PKG_CONFIG:=pkg-config} +: ${AR:="$CC_AR"} +: ${HOST_CC:=gcc} +: ${HOST_CXX:=g++} +: ${HOST_CLANG:=clang} +: ${LDLIBS:="$LIBS_N $LIBS_NL"} + +echo "CC_ISA_EXT_FLAGS := $CC_ISA_EXT_FLAGS" >> $CONFIG +echo "ASM_ISA_EXT_FLAGS := $ASM_ISA_EXT_FLAGS" >> $CONFIG +echo "C_MARCH_FLAGS := $C_MARCH_FLAGS" >>$CONFIG +echo "ASM_MARCH_FLAGS := $ASM_MARCH_FLAGS" >>$CONFIG +echo "HOST_CC := gcc" >> $CONFIG +echo "HOST_CXX := g++" >> $CONFIG +echo "HOST_CLANG := clang" >> $CONFIG +echo "CC_ELF := $CC_ELF" >> $CONFIG +echo "LDLIBS = $LDLIBS" >> $CONFIG +echo "LDLIBS += \$(LDLIBS_LOCAL) -ldl" >> $CONFIG +echo "LDLIBS_STATIC = $LIBS_N" >> $CONFIG +echo "LDLIBS_STATIC += \$(LDLIBS_LOCAL) -ldl" >> $CONFIG +echo "TEST_TARGET_STATIC = \$(TEST_TARGET:%=%_static)" >> $CONFIG +echo "OBJ = \$(TEST_TARGET:%=%.o)" >> $CONFIG +echo "STATIC_OBJ = \$(TEST_TARGET_STATIC:%=%.o)" >> $CONFIG +echo "TARGETS = \$(TEST_TARGET)" >> $CONFIG +echo "PKG_CONFIG := $PKG_CONFIG" >> $CONFIG +echo "TARGET_ARCH := $TARGET_ARCH" >> $CONFIG + + +if [ -z "$INSTALLDIR" ]; then + # Default to install directory in the xdp2 repo root (one level up from src/) + INSTALLDIR=$PWD/../install/$ARCH +fi + +if [ -z "$INSTALLTARNAME" ]; then + INSTALLTARNAME=install.tgz +fi + +echo "XDP2_ARCH := $ARCH" >> $CONFIG +echo "XDP2_CFLAGS += -DARCH_$ARCH" >> $CONFIG + +if [ -n "$TARGET_ARCH" ]; then + echo "CFLAGS += -DTARGET_ARCH_$TARGET_ARCH" >> $CONFIG +fi + +if [ "$SOFT_FLOAT_BUILD" == "yes" ]; then + echo "XDP2_CFLAGS += -DFPGA_SOFT_FLAG" >> $CONFIG +fi + +echo >> $CONFIG + +echo "Platform is $PLATFORM" + +unlink ../platform 2>/dev/null +ln -s platforms/"$PLATFORM" ../platform + +echo "Architecture is $ARCH" + +unlink ./include/arch 2>/dev/null + +if [ -d ../platform/src/include/arch/arch_$ARCH ]; then + ln -s ../../platform/src/include/arch/arch_$ARCH ./include/arch + echo "Architecture includes are ./include/arch_$ARCH" + CFLAGS_N+=" -fcommon" +else + ln -s ../../platform/src/include/arch/arch_generic ./include/arch + echo "Architecture includes for $ARCH not found, using generic" +fi + +echo "Target Architecture is $TARGET_ARCH" + +echo "COMPILER is $COMPILER" + +: ${CC:="$CC_GCC $CFLAGS_N"} +: ${CXX:="$CC_CXX $CFLAGS_N"} +: ${LD:="$LD_GCC"} + +# Auto-detect llvm-config if not explicitly set or verify the one provided +debug_print 1 "Tool Detection: Starting llvm-config detection" +FOUND_LLVM_CONFIG="" +if [ -n "$HOST_LLVM_CONFIG" ]; then + # If HOST_LLVM_CONFIG is set, verify it works + debug_print 2 "Tool Detection: HOST_LLVM_CONFIG is set to: $HOST_LLVM_CONFIG" + LLVM_CONFIG_PATH=$(command -v "$HOST_LLVM_CONFIG" 2>/dev/null) + if [ -n "$LLVM_CONFIG_PATH" ] && "$LLVM_CONFIG_PATH" --version >/dev/null 2>&1; then + FOUND_LLVM_CONFIG="$LLVM_CONFIG_PATH" + debug_print 1 "Tool Detection: Verified user-provided HOST_LLVM_CONFIG: $FOUND_LLVM_CONFIG" + LLVM_VER=`$FOUND_LLVM_CONFIG --version 2>/dev/null` + debug_print 2 "Tool Detection: Version: $LLVM_VER" + else + debug_print 2 "Tool Detection: User-provided HOST_LLVM_CONFIG not found or invalid, will auto-detect" + fi +fi + +if [ -z "$FOUND_LLVM_CONFIG" ]; then + # Auto-detect: try unversioned first, then versioned variants (llvm-config-20, etc.) + # Verify each tool works by testing --version + debug_print 2 "Tool Detection: Auto-detecting llvm-config..." + for llvm_config_tool in llvm-config llvm-config-20 llvm-config-19 llvm-config-18 llvm-config-17 llvm-config-16; do + debug_print 3 "Tool Detection: Checking for $llvm_config_tool" + LLVM_CONFIG_PATH=$(command -v "$llvm_config_tool" 2>/dev/null) + if [ -n "$LLVM_CONFIG_PATH" ]; then + debug_print 3 "Tool Detection: Found $llvm_config_tool at $LLVM_CONFIG_PATH" + if "$LLVM_CONFIG_PATH" --version >/dev/null 2>&1; then + FOUND_LLVM_CONFIG="$LLVM_CONFIG_PATH" + LLVM_VER=`$FOUND_LLVM_CONFIG --version 2>/dev/null` + debug_print 1 "Tool Detection: Selected $llvm_config_tool (version $LLVM_VER)" + break + else + debug_print 3 "Tool Detection: $llvm_config_tool found but --version test failed" + fi + fi + done +fi +echo "LLVM_VER:$LLVM_VER" + +if [ -n "$FOUND_LLVM_CONFIG" ]; then + HOST_LLVM_CONFIG="$FOUND_LLVM_CONFIG" + debug_print 1 "Tool Detection: Using HOST_LLVM_CONFIG=$HOST_LLVM_CONFIG" +else + # Fallback to default (will fail later if it doesn't exist) + HOST_LLVM_CONFIG="/usr/bin/llvm-config" + debug_print 2 "Tool Detection: No llvm-config found, falling back to default: $HOST_LLVM_CONFIG" +fi +echo "HOST_LLVM_CONFIG:$HOST_LLVM_CONFIG" + +: ${LLVM_CONFIG:="$LLVM_CONFIG"} +echo "CC := $CC" >> $CONFIG +echo "LD := $LD" >> $CONFIG +echo "CXX := $CXX" >> $CONFIG +echo "HOST_LLVM_CONFIG := $HOST_LLVM_CONFIG" >> $CONFIG +echo "LLVM_CONFIG := $LLVM_CONFIG" >> $CONFIG +echo "LDFLAGS := $LDFLAGS" >> $CONFIG +echo "PYTHON := python3" >> $CONFIG + +# If we didn't get an architecture from the command line set it base +# on the running host + +debug_print 1 "Configuration: Platform=$PLATFORM, Architecture=$ARCH, Compiler=$COMPILER" + +check_libpcap +check_boostsystem +check_boostwave +check_boostthread +check_boostfilesystem +check_clang_lib +check_python +check_scapy + +if [ -n "$CLANG_LIBS_DISCOVERED" ]; then + echo "CLANG_LIBS := $CLANG_LIBS_DISCOVERED" >> $CONFIG + debug_print 1 "Configuration: Wrote CLANG_LIBS to config.mk: $CLANG_LIBS_DISCOVERED" +else + debug_print 2 "Configuration: Warning: CLANG_LIBS_DISCOVERED is empty, Makefile will use default" +fi + +echo "ifneq (\$(USE_HOST_TOOLS),y)" >> $CONFIG + +echo "%.o: %.c" >> $CONFIG +echo ' $(QUIET_CC)$(CC) $(CFLAGS) $(XDP2_CFLAGS) $(EXTRA_CFLAGS) $(C_MARCH_FLAGS)\ + -c -o $@ $<' >> $CONFIG + +echo "%_static.o: %.c" >> $CONFIG +echo ' $(QUIET_CC)$(CC) $(CFLAGS) $(XDP2_CFLAGS) $(EXTRA_CFLAGS) -DXDP2_NO_DYNAMIC $(C_MARCH_FLAGS)\ + -c -o $@ $<' >> $CONFIG + +echo "%.o: %.cpp" >> $CONFIG +echo ' $(QUIET_CXX)$(CXX) $(CXXFLAGS) $(EXTRA_CXXFLAGS) $(C_MARCH_FLAGS)\ + -c -o $@ $<' >> $CONFIG + +echo "%.o: %.s" >> $CONFIG +echo ' $(QUIET_ASM)$(CC) $(ASM_MARCH_FLAGS)\ + -c -o $@ $<' >> $CONFIG + +echo "else" >> $CONFIG + +echo "%.o: %.c" >> $CONFIG +echo ' $(QUIET_CC)$(HOST_CC) $(CFLAGS) $(XDP2_CFLAGS) $(EXTRA_CFLAGS) -c -o $@ $<' >> $CONFIG + +echo "%.o: %.cpp" >> $CONFIG +echo ' $(QUIET_CXX)$(HOST_CXX) $(XDP2_CXXFLAGS) $(CXXFLAGS) $(EXTRA_CXXFLAGS) \ + -c -o $@ $<' >> $CONFIG + +echo "endif" >> $CONFIG + +echo "%.ll: %.c" >> $CONFIG +echo ' $(QUIET_CC)$(HOST_CLANG) $(CFLAGS) $(XDP2_CFLAGS) $(EXTRA_CFLAGS) $(C_MARCH_FLAGS)\ + -S $< -emit-llvm' >> $CONFIG + +echo >> $CONFIG +if [ -f ${HOST_LLVM_CONFIG} ]; then +XDP2_CLANG_VERSION=`${HOST_LLVM_CONFIG} --version` +else +XDP2_CLANG_VERSION=`/usr/bin/llvm-config --version` +fi + +echo "XDP2_CLANG_VERSION=${XDP2_CLANG_VERSION}" +echo "XDP2_CLANG_VERSION=${XDP2_CLANG_VERSION}" >> $CONFIG +XDP2_CLANG_RESOURCE_PATH="`${HOST_LLVM_CONFIG} --libdir`/clang/`echo ${XDP2_CLANG_VERSION} | cut -d'.' -f1`" +XDP2_C_INCLUDE_PATH="`${HOST_LLVM_CONFIG} --libdir`/clang/`echo ${XDP2_CLANG_VERSION} | cut -d'.' -f1`/include" +echo "XDP2_C_INCLUDE_PATH=${XDP2_C_INCLUDE_PATH}" +echo "XDP2_C_INCLUDE_PATH=${XDP2_C_INCLUDE_PATH}" >> $CONFIG +echo "XDP2_CLANG_RESOURCE_PATH=${XDP2_CLANG_RESOURCE_PATH}" +echo "XDP2_CLANG_RESOURCE_PATH=${XDP2_CLANG_RESOURCE_PATH}" >> $CONFIG +echo >> $CONFIG + +output_platform_config + +# TBD +#OPTIMIZE_PARSER- may have to be enhanced with commandline options +# + +echo >> $CONFIG +echo "endif # !TOP_LEVEL_MAKE" >> $CONFIG +echo >> $CONFIG +echo "INSTALLDIR ?= $INSTALLDIR" >> $CONFIG +echo "INSTALLTARNAME ?= $INSTALLTARNAME" >> $CONFIG +echo "BUILD_OPT_PARSER ?= $BUILD_OPT_PARSER" >> $CONFIG +echo "BUILD_PARSER_JSON ?= $BUILD_PARSER_JSON" >> $CONFIG +echo "NO_BUILD_COMPILER ?= $NO_BUILD_COMPILER" >> $CONFIG + +echo "CONFIG_DEFINES := $CONFIG_DEFINES" >> $CONFIG diff --git a/src/include/Makefile b/src/include/Makefile index ca7f2f0..f1f02f9 100644 --- a/src/include/Makefile +++ b/src/include/Makefile @@ -9,6 +9,6 @@ SUBDIRS = cli siphash xdp2 parselite uet falcon sue $(TOPTARGETS) : $(SUBDIRS) $(SUBDIRS): - @make -C $@ $(MAKECMDGOALS) + @$(MAKE) -C $@ $(MAKECMDGOALS) .PHONY: $(TOPTARGETS) $(SUBDIRS) diff --git a/src/include/sue/Makefile b/src/include/sue/Makefile index 0fcd368..5e21b27 100644 --- a/src/include/sue/Makefile +++ b/src/include/sue/Makefile @@ -6,9 +6,9 @@ TOPTARGETS := all clean install .PHONY: $(TOPTARGETS) -INCDIR=$(INSTALLDIR)$(HDRDIR)/falcon +INCDIR=$(INSTALLDIR)$(HDRDIR)/sue -TARGETS = +TARGETS = sue.h proto_sue.h parser_test.h all: diff --git a/src/include/sue/README.md b/src/include/sue/README.md new file mode 100644 index 0000000..cf6f2a1 --- /dev/null +++ b/src/include/sue/README.md @@ -0,0 +1,3 @@ +Scale Up Ethernet (SUE) Protocol + +https://docs.broadcom.com/doc/scale-up-ethernet-framework \ No newline at end of file diff --git a/src/include/uet/README.md b/src/include/uet/README.md new file mode 100644 index 0000000..01e0df7 --- /dev/null +++ b/src/include/uet/README.md @@ -0,0 +1,3 @@ +Ultra Ethernet Transport (UET) + +https://ultraethernet.org/ultra-ethernet-specification-update/ \ No newline at end of file diff --git a/src/include/xdp2/Makefile b/src/include/xdp2/Makefile index 97718c2..324cf2f 100644 --- a/src/include/xdp2/Makefile +++ b/src/include/xdp2/Makefile @@ -9,7 +9,7 @@ SUBDIRS = proto_defs parsers $(TOPTARGETS) : $(SUBDIRS) $(SUBDIRS): - @make -C $@ $(MAKECMDGOALS) + @$(MAKE) -C $@ $(MAKECMDGOALS) .PHONY: $(TOPTARGETS) $(SUBDIRS) diff --git a/src/lib/Makefile b/src/lib/Makefile index 0a0fc78..d7795f9 100644 --- a/src/lib/Makefile +++ b/src/lib/Makefile @@ -8,7 +8,7 @@ SUBDIRS = cli siphash crc flowdis lzf murmur3hash xdp2 parselite $(TOPTARGETS) : $(SUBDIRS) $(SUBDIRS): - @make -C $@ $(MAKECMDGOALS) + @$(MAKE) -C $@ $(MAKECMDGOALS) .PHONY: $(TOPTARGETS) $(SUBDIRS) diff --git a/src/test/Makefile b/src/test/Makefile index 3bfe562..a4c52e5 100644 --- a/src/test/Makefile +++ b/src/test/Makefile @@ -8,7 +8,7 @@ SUBDIRS += accelerator router bitmaps uet falcon $(TOPTARGETS) : $(SUBDIRS) $(SUBDIRS): - @make -C $@ $(MAKECMDGOALS) + @$(MAKE) -C $@ $(MAKECMDGOALS) .PHONY: $(TOPTARGETS) $(SUBDIRS) diff --git a/src/tools/Makefile b/src/tools/Makefile index f850778..f2b677d 100644 --- a/src/tools/Makefile +++ b/src/tools/Makefile @@ -11,6 +11,6 @@ endif $(TOPTARGETS) : $(SUBDIRS) $(SUBDIRS): - @make -C $@ $(MAKECMDGOALS) + @$(MAKE) -C $@ $(MAKECMDGOALS) .PHONY: $(TOPTARGETS) $(SUBDIRS) diff --git a/src/tools/compiler/Makefile b/src/tools/compiler/Makefile index bdd28a8..9c61eee 100644 --- a/src/tools/compiler/Makefile +++ b/src/tools/compiler/Makefile @@ -45,7 +45,15 @@ xdp2-define-test: $(TESTOBJS) $(TESTFILES) for i in $(TESTFILES); \ do ./$@ $$i; done -gen-patterns-cpp: +.PHONY: check-cppfront +check-cppfront: + @if [ ! -f "$(CPPFRONT)" ]; then \ + echo "cppfront-compiler not found at $(CPPFRONT)" >&2; \ + echo "Building cppfront..." >&2; \ + $(MAKE) -C ../../../thirdparty/cppfront || exit 1; \ + fi + +gen-patterns-cpp: check-cppfront $(CPPFRONT) $(PATTERNS_LLVM_CPP2) && $(CPPFRONT) $(PATTERNS_CLANG_AST_CPP2) all: $(TARGETS) diff --git a/src/tools/compiler/src/main.cpp b/src/tools/compiler/src/main.cpp index ed64a21..ec547c4 100644 --- a/src/tools/compiler/src/main.cpp +++ b/src/tools/compiler/src/main.cpp @@ -197,6 +197,10 @@ clang::tooling::ClangTool create_clang_tool( { std::string version = XDP2_STRINGIFY(XDP2_CLANG_VERSION); version = version.substr(0, version.find("git")); + + // NOTE: This is hardcoded debug output showing a typical system path. + // It does NOT represent the actual resource directory being used. + // The actual resource directory is set via -resource-dir flag below. plog::log(std::cout) << "/usr/lib/clang/" << version << "/include" << std::endl; if (getenv("XDP2_C_INCLUDE_PATH")) @@ -222,6 +226,12 @@ clang::tooling::ClangTool create_clang_tool( {"-resource-dir", *resource_path}, clang::tooling::ArgumentInsertPosition::BEGIN)); } + // NOTE: We intentionally let clang auto-detect its resource directory. + // This works correctly in Nix environments via the clang-wrapper which sets + // up the resource-root symlink. If we need to explicitly set it in the future, + // we should call `clang -print-resource-dir` at build time and use that value. + // Previously, we used XDP2_CLANG_RESOURCE_PATH compiled in at build time, + // but this was set incorrectly in flake.nix, causing incomplete type information. #ifdef XDP2_CLANG_RESOURCE_PATH else { Tool.appendArgumentsAdjuster(clang::tooling::getInsertArgumentAdjuster( diff --git a/src/tools/packets/Makefile b/src/tools/packets/Makefile index b408bc4..40f2b1c 100644 --- a/src/tools/packets/Makefile +++ b/src/tools/packets/Makefile @@ -7,6 +7,6 @@ SUBDIRS = uet falcon sue $(TOPTARGETS) : $(SUBDIRS) $(SUBDIRS): - @make -C $@ $(MAKECMDGOALS) + @$(MAKE) -C $@ $(MAKECMDGOALS) .PHONY: $(TOPTARGETS) $(SUBDIRS) diff --git a/src/tools/packets/falcon/Makefile b/src/tools/packets/falcon/Makefile index aa6378d..d001e6f 100644 --- a/src/tools/packets/falcon/Makefile +++ b/src/tools/packets/falcon/Makefile @@ -6,8 +6,10 @@ TARGETS = get_falcon_udp_port falcon.pcap all: $(TARGETS) -%.pcap: make_%.py - $(QUIET_PYTHON)$(PYTHON) $< `./get_falcon_udp_port` +GET_UDP_PORT = get_falcon_udp_port + +%.pcap: make_%.py $(GET_UDP_PORT) + $(QUIET_PYTHON)$(PYTHON) $< `./$(GET_UDP_PORT)` get_falcon_udp_port: get_falcon_udp_port.c $(QUIET_CC)$(HOST_CC) $(CCOPTS) -I$(SRCDIR)/include $(CONFIG_DEFINES) $^ -o $@ diff --git a/src/tools/packets/sue/Makefile b/src/tools/packets/sue/Makefile index 318160a..0505f2f 100644 --- a/src/tools/packets/sue/Makefile +++ b/src/tools/packets/sue/Makefile @@ -6,8 +6,10 @@ TARGETS = get_sue_udp_port sue.pcap all: $(TARGETS) -%.pcap: make_%.py - $(QUIET_PYTHON)$(PYTHON) $< `./get_sue_udp_port` +GET_UDP_PORT = get_sue_udp_port + +%.pcap: make_%.py $(GET_UDP_PORT) + $(QUIET_PYTHON)$(PYTHON) $< `./$(GET_UDP_PORT)` get_sue_udp_port: get_sue_udp_port.c $(QUIET_CC)$(HOST_CC) $(CCOPTS) -I$(SRCDIR)/include $(CONFIG_DEFINES) $^ -o $@ diff --git a/src/tools/packets/uet/Makefile b/src/tools/packets/uet/Makefile index 74dd77d..6c7b0f0 100644 --- a/src/tools/packets/uet/Makefile +++ b/src/tools/packets/uet/Makefile @@ -6,8 +6,10 @@ TARGETS = get_uet_udp_port uet_pds.pcap uet_ses.pcap all: $(TARGETS) -%.pcap: make_%.py - $(QUIET_PYTHON)$(PYTHON) $< `./get_uet_udp_port` +GET_UDP_PORT = get_uet_udp_port + +%.pcap: make_%.py $(GET_UDP_PORT) + $(QUIET_PYTHON)$(PYTHON) $< `./$(GET_UDP_PORT)` get_uet_udp_port: get_uet_udp_port.c $(QUIET_CC)$(HOST_CC) $(CCOPTS) -I$(SRCDIR)/include $(CONFIG_DEFINES) $^ -o $@ diff --git a/thirdparty/cppfront/.gitignore b/thirdparty/cppfront/.gitignore index 4104530..c0291df 100644 --- a/thirdparty/cppfront/.gitignore +++ b/thirdparty/cppfront/.gitignore @@ -1,3 +1,5 @@ +# don't accidently commit the binary +cppfront *.vcxproj *.filters diff --git a/thirdparty/cppfront/cppfront-compiler b/thirdparty/cppfront/cppfront-compiler deleted file mode 100755 index c2f16d9..0000000 Binary files a/thirdparty/cppfront/cppfront-compiler and /dev/null differ