diff --git a/platform/nvidia-bluefield/bfscripts/.gitignore b/platform/nvidia-bluefield/bfscripts/.gitignore new file mode 100644 index 00000000000..4ccfa41db02 --- /dev/null +++ b/platform/nvidia-bluefield/bfscripts/.gitignore @@ -0,0 +1,4 @@ + +* +!.gitignore +!Makefile diff --git a/platform/nvidia-bluefield/bfscripts/Makefile b/platform/nvidia-bluefield/bfscripts/Makefile new file mode 100644 index 00000000000..f3c92a7b19b --- /dev/null +++ b/platform/nvidia-bluefield/bfscripts/Makefile @@ -0,0 +1,41 @@ +# +# Copyright (c) 2024 NVIDIA CORPORATION & AFFILIATES. +# Apache-2.0 +# +# Licensed under the Apache License, Version 2.0 (the "License"); +# you may not use this file except in compliance with the License. +# You may obtain a copy of the License at +# +# http://www.apache.org/licenses/LICENSE-2.0 +# +# Unless required by applicable law or agreed to in writing, software +# distributed under the License is distributed on an "AS IS" BASIS, +# WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied. +# See the License for the specific language governing permissions and +# limitations under the License. +# + +.ONESHELL: +SHELL = /bin/bash +.SHELLFLAGS += -ex + +$(addprefix $(DEST)/, $(MLNX_BLUEFIELD_BUILD_SCRIPTS)): $(DEST)/% : + rm -rf ./tmp/ + mkdir ./tmp/ + pushd ./tmp/ + + wget -O ${MLNX_BLUEFIELD_BUILD_SCRIPTS} "${BSD_BASE_URL}/build/install/distro/DEBS/${MLNX_BLUEFIELD_BUILD_SCRIPTS}" + + mkdir -p bfscripts/DEBIAN + dpkg -e ${MLNX_BLUEFIELD_BUILD_SCRIPTS} bfscripts/DEBIAN + dpkg -x ${MLNX_BLUEFIELD_BUILD_SCRIPTS} bfscripts + rm -f ${MLNX_BLUEFIELD_BUILD_SCRIPTS} + + # Remove postinst script as we don't want to enable systemd services from the package. + # We are interested only in a couple of scripts that package has. + rm -f bfscripts/DEBIAN/postinst + + dpkg -b bfscripts ./ + + mv ${MLNX_BLUEFIELD_BUILD_SCRIPTS} $(DEST)/ + popd diff --git a/platform/nvidia-bluefield/bluefield-platform-modules/Makefile b/platform/nvidia-bluefield/bluefield-platform-modules/Makefile new file mode 100644 index 00000000000..7c31ad1716d --- /dev/null +++ b/platform/nvidia-bluefield/bluefield-platform-modules/Makefile @@ -0,0 +1,46 @@ +# +# Copyright (c) 2024 NVIDIA CORPORATION & AFFILIATES. +# Apache-2.0 +# +# Licensed under the Apache License, Version 2.0 (the "License"); +# you may not use this file except in compliance with the License. +# You may obtain a copy of the License at +# +# http://www.apache.org/licenses/LICENSE-2.0 +# +# Unless required by applicable law or agreed to in writing, software +# distributed under the License is distributed on an "AS IS" BASIS, +# WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied. +# See the License for the specific language governing permissions and +# limitations under the License. +# + +.ONESHELL: +SHELL = /bin/bash +.SHELLFLAGS += -e + +$(addprefix $(DEST)/, $(BF_PLATFORM_MODULE)): $(DEST)/% : + + # Clean up + rm -rf drivers/* \ + cfg/bluefield-modules.conf \ + debian/bluefield-platform-modules.postinst + + mkdir -p drivers/ + mkdir -p cfg/ + + $(foreach kernel_module, $(BF_PLATFORM_DRIVERS), \ + cp $(PROJECT_ROOT)/$(FILES_PATH)/$(kernel_module) drivers/ + ) + + export driver_targets="$(BF_PLATFORM_DRIVERS)" + export kversion="$(KVERSION)" + j2 templates/bluefield-platform-modules.postinst.j2 > debian/bluefield-platform-modules.postinst + j2 templates/bluefield-modules.conf.j2 > cfg/bluefield-modules.conf + + chmod +x debian/bluefield-platform-modules.postinst + chmod 0644 cfg/bluefield-modules.conf + + DEB_BUILD_OPTIONS=nocheck dpkg-buildpackage -rfakeroot -us -uc -b -j$(SONIC_CONFIG_MAKE_JOBS) + + mv ../$(BF_PLATFORM_MODULE) $(DEST)/ diff --git a/platform/nvidia-bluefield/bluefield-platform-modules/bin/bfnet.sh b/platform/nvidia-bluefield/bluefield-platform-modules/bin/bfnet.sh new file mode 100755 index 00000000000..0c74cfbe506 --- /dev/null +++ b/platform/nvidia-bluefield/bluefield-platform-modules/bin/bfnet.sh @@ -0,0 +1,67 @@ +#!/bin/bash +# +# Copyright (c) 2024 NVIDIA CORPORATION & AFFILIATES. +# Apache-2.0 +# +# Licensed under the Apache License, Version 2.0 (the "License"); +# you may not use this file except in compliance with the License. +# You may obtain a copy of the License at +# +# http://www.apache.org/licenses/LICENSE-2.0 +# +# Unless required by applicable law or agreed to in writing, software +# distributed under the License is distributed on an "AS IS" BASIS, +# WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied. +# See the License for the specific language governing permissions and +# limitations under the License. +# + +cp_iface=Ethernet0 +pidfile=/run/dhcl-internal.$cp_iface.pid +leasefile=/var/lib/dhcp/dhcl-internal.$cp_iface.leases + +stop_cp_dhclient() +{ + if [[ -f $pidfile ]]; then + kill $(cat $pidfile) + rm -f $pidfile + fi + rm -f $leasefile +} + +start_cp_dhclient() +{ + stop_cp_dhclient + + /sbin/dhclient -pf $pidfile -lf $leasefile $cp_iface -nw +} + +start() +{ + modprobe mlx5_core + /usr/bin/mst start + + hwsku=$(sonic-cfggen -d -v 'DEVICE_METADATA["localhost"]["hwsku"]') + if [[ $hwsku == *"-C1" ]]; then + start_cp_dhclient + fi +} + +stop() +{ + stop_cp_dhclient + + /usr/bin/mst stop + rmmod mlx5_ib mlx5_core +} + +case "$1" in + start|stop) + $1 + ;; + *) + echo "Usage: $0 {start|stop}" + exit 1 + ;; +esac + diff --git a/platform/nvidia-bluefield/bluefield-platform-modules/bin/platform-dump.sh b/platform/nvidia-bluefield/bluefield-platform-modules/bin/platform-dump.sh new file mode 100755 index 00000000000..80dd4e059b1 --- /dev/null +++ b/platform/nvidia-bluefield/bluefield-platform-modules/bin/platform-dump.sh @@ -0,0 +1,53 @@ +#!/bin/bash +# +# Copyright (c) 2024 NVIDIA CORPORATION & AFFILIATES. +# Apache-2.0 +# +# Licensed under the Apache License, Version 2.0 (the "License"); +# you may not use this file except in compliance with the License. +# You may obtain a copy of the License at +# +# http://www.apache.org/licenses/LICENSE-2.0 +# +# Unless required by applicable law or agreed to in writing, software +# distributed under the License is distributed on an "AS IS" BASIS, +# WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied. +# See the License for the specific language governing permissions and +# limitations under the License. +# + +DUMP_FOLDER="/tmp/platform-dump" + +dump_cmd () { + cmd=$1 + output_fname=$2 + timeout=$3 + cmd_name=${cmd%% *} + + if [ -x "$(command -v $cmd_name)" ]; + then + # ignore shellcheck message SC2016. Arguments should be single-quoted (') + run_cmd="$cmd > $DUMP_FOLDER/$output_fname" + timeout "$timeout" bash -c "$run_cmd" + fi +} + +rm -rf $DUMP_FOLDER +mkdir $DUMP_FOLDER + +ls -Rla /sys/ > $DUMP_FOLDER/sysfs_tree +uname -a > $DUMP_FOLDER/sys_version +mkdir $DUMP_FOLDER/bin/ +cp /usr/bin/platform-dump.sh $DUMP_FOLDER/bin/ +cat /etc/os-release >> $DUMP_FOLDER/sys_version +cat /proc/interrupts > $DUMP_FOLDER/interrupts + +dump_cmd "dmesg" "dmesg" "10" +dump_cmd "dmidecode -t1 -t2 -t 11" "dmidecode" "3" +dump_cmd "lsmod" "lsmod" "3" +dump_cmd "lspci -vvv" "lspci" "5" +dump_cmd "top -SHb -n 1 | tail -n +8 | sort -nrk 11" "top" "5" +dump_cmd "tail /sys/kernel/debug/mlxbf-ptm/monitors/status/*" "mlxbf-ptm-dump" "3" + +tar czf /tmp/platform-dump.tar.gz -C $DUMP_FOLDER . +rm -rf $DUMP_FOLDER diff --git a/platform/nvidia-bluefield/bluefield-platform-modules/debian/bluefield-platform-modules.install b/platform/nvidia-bluefield/bluefield-platform-modules/debian/bluefield-platform-modules.install new file mode 100644 index 00000000000..04aca12dc01 --- /dev/null +++ b/platform/nvidia-bluefield/bluefield-platform-modules/debian/bluefield-platform-modules.install @@ -0,0 +1,5 @@ +cfg/bluefield-modules.conf etc/modules-load.d/ +udev/* etc/udev/rules.d/ +modprobe.d/* etc/modprobe.d/ +bin/* usr/bin/ +systemd/* /lib/systemd/system/ diff --git a/platform/nvidia-bluefield/bluefield-platform-modules/debian/changelog b/platform/nvidia-bluefield/bluefield-platform-modules/debian/changelog new file mode 100644 index 00000000000..2fbfbadd6ef --- /dev/null +++ b/platform/nvidia-bluefield/bluefield-platform-modules/debian/changelog @@ -0,0 +1,5 @@ +bluefield-platform-modules (1.0) unstable; urgency=low + + * Initial Release + + -- Oleksandr Ivantsiv Fri, 23 Feb 2024 15:57:40 -0800 diff --git a/platform/nvidia-bluefield/bluefield-platform-modules/debian/compat b/platform/nvidia-bluefield/bluefield-platform-modules/debian/compat new file mode 100644 index 00000000000..f599e28b8ab --- /dev/null +++ b/platform/nvidia-bluefield/bluefield-platform-modules/debian/compat @@ -0,0 +1 @@ +10 diff --git a/platform/nvidia-bluefield/bluefield-platform-modules/debian/control b/platform/nvidia-bluefield/bluefield-platform-modules/debian/control new file mode 100644 index 00000000000..74f0b130410 --- /dev/null +++ b/platform/nvidia-bluefield/bluefield-platform-modules/debian/control @@ -0,0 +1,11 @@ +Source: bluefield-platform-modules +Section: main +Priority: extra +Maintainer: Vivek Reddy Karri +Build-Depends: debhelper (>= 8.0.0) +Standards-Version: 3.9.3 + +Package: bluefield-platform-modules +Version: 1.0 +Architecture: arm64 +Description: Kernel modules, udev rules, and system configuration files for the Nvidia Bluefield platform. diff --git a/platform/nvidia-bluefield/bluefield-platform-modules/debian/rules b/platform/nvidia-bluefield/bluefield-platform-modules/debian/rules new file mode 100755 index 00000000000..a48a0c1df61 --- /dev/null +++ b/platform/nvidia-bluefield/bluefield-platform-modules/debian/rules @@ -0,0 +1,19 @@ +#!/usr/bin/make -f + +export INSTALL_MOD_DIR:=extra + +KVERSION ?= $(shell uname -r) +KERNEL_SRC := /lib/modules/$(KVERSION) +MOD_SRC_DIR:= $(shell pwd)/drivers + +%: + dh $@ + +override_dh_auto_build: + +override_dh_auto_install: + dh_installdirs -pbluefield-platform-modules $(KERNEL_SRC)/$(INSTALL_MOD_DIR); + cp $(MOD_SRC_DIR)/*.ko debian/bluefield-platform-modules/$(KERNEL_SRC)/$(INSTALL_MOD_DIR); + +override_dh_clean: + dh_clean diff --git a/platform/nvidia-bluefield/bluefield-platform-modules/modprobe.d/mlx5_core.conf b/platform/nvidia-bluefield/bluefield-platform-modules/modprobe.d/mlx5_core.conf new file mode 100644 index 00000000000..0839ec46733 --- /dev/null +++ b/platform/nvidia-bluefield/bluefield-platform-modules/modprobe.d/mlx5_core.conf @@ -0,0 +1 @@ +blacklist mlx5_core diff --git a/platform/nvidia-bluefield/bluefield-platform-modules/systemd/dpu.service b/platform/nvidia-bluefield/bluefield-platform-modules/systemd/dpu.service new file mode 100644 index 00000000000..e713ca18e74 --- /dev/null +++ b/platform/nvidia-bluefield/bluefield-platform-modules/systemd/dpu.service @@ -0,0 +1,12 @@ +[Unit] +Description=DPU initialization routine +After=getty.target + +[Service] +Type=oneshot +ExecStartPre=/usr/bin/bfrshlog "Linux up" +ExecStart=/usr/bin/bfrshlog "DPU is ready" +StandardOutput=journal+console + +[Install] +WantedBy=multi-user.target diff --git a/platform/nvidia-bluefield/bluefield-platform-modules/templates/bluefield-modules.conf.j2 b/platform/nvidia-bluefield/bluefield-platform-modules/templates/bluefield-modules.conf.j2 new file mode 100644 index 00000000000..cf2c95c73be --- /dev/null +++ b/platform/nvidia-bluefield/bluefield-platform-modules/templates/bluefield-modules.conf.j2 @@ -0,0 +1,10 @@ +# /etc/modules: kernel modules to load at boot time. +# +# This file contains the names of kernel modules that should be loaded +# at boot time, one per line. Lines beginning with "#" are ignored. + +{% if driver_targets.strip() %} +{%- for k_module in driver_targets.strip().split() -%} +{{ k_module.split(".")[0] }} +{% endfor %} +{% endif -%} diff --git a/platform/nvidia-bluefield/bluefield-platform-modules/templates/bluefield-platform-modules.postinst.j2 b/platform/nvidia-bluefield/bluefield-platform-modules/templates/bluefield-platform-modules.postinst.j2 new file mode 100644 index 00000000000..a11a4449c68 --- /dev/null +++ b/platform/nvidia-bluefield/bluefield-platform-modules/templates/bluefield-platform-modules.postinst.j2 @@ -0,0 +1,18 @@ +# postinst script for sonic-platform-modules-bluefield2 + +set +e + +depmod -a +{% if driver_targets.strip() %} +{%- for k_module in driver_targets.strip().split() -%} +modprobe {{ k_module.split(".")[0] }} +{% endfor %} +{% endif -%} + +sync + +systemctl enable serial-getty@hvc0.service +systemctl enable serial-getty@ttyAMA0.service +systemctl enable serial-getty@ttyAMA1.service + +#DEBHELPER# diff --git a/platform/nvidia-bluefield/bluefield-platform-modules/udev/82-net-setup-link.rules b/platform/nvidia-bluefield/bluefield-platform-modules/udev/82-net-setup-link.rules new file mode 100644 index 00000000000..0a99b404476 --- /dev/null +++ b/platform/nvidia-bluefield/bluefield-platform-modules/udev/82-net-setup-link.rules @@ -0,0 +1,2 @@ +SUBSYSTEM=="net", ACTION=="add", DEVPATH=="/devices/pci0000:00/0000:00:00.0/0000:01:00.0/0000:02:00.0/0000:03:00.0/net/e*", ATTR{phys_port_name}=="p0", NAME="Ethernet0" +SUBSYSTEM=="net", ACTION=="add", DEVPATH=="/devices/pci0000:00/0000:00:00.0/0000:01:00.0/0000:02:00.0/0000:03:00.1/net/e*", ATTR{phys_port_name}=="p1", NAME="Ethernet4" diff --git a/platform/nvidia-bluefield/bluefield-platform-modules/udev/91-tmfifo_net.rules b/platform/nvidia-bluefield/bluefield-platform-modules/udev/91-tmfifo_net.rules new file mode 100644 index 00000000000..540908d6944 --- /dev/null +++ b/platform/nvidia-bluefield/bluefield-platform-modules/udev/91-tmfifo_net.rules @@ -0,0 +1 @@ +SUBSYSTEM=="net", ACTION=="add", DEVPATH=="/devices/platform/MLNXBF01:00/virtio1/net/eth*", NAME="tmfifo_net0" \ No newline at end of file diff --git a/platform/nvidia-bluefield/bluefield-platform-modules/udev/92-oob_net.rules b/platform/nvidia-bluefield/bluefield-platform-modules/udev/92-oob_net.rules new file mode 100644 index 00000000000..dd0c47a4fb6 --- /dev/null +++ b/platform/nvidia-bluefield/bluefield-platform-modules/udev/92-oob_net.rules @@ -0,0 +1 @@ +SUBSYSTEM=="net", ACTION=="add", DEVPATH=="/devices/platform/MLNXBF17:00/net/e*", NAME="eth0" diff --git a/platform/nvidia-bluefield/docker-syncd-bluefield/Dockerfile.j2 b/platform/nvidia-bluefield/docker-syncd-bluefield/Dockerfile.j2 new file mode 100644 index 00000000000..e11ea978c2c --- /dev/null +++ b/platform/nvidia-bluefield/docker-syncd-bluefield/Dockerfile.j2 @@ -0,0 +1,59 @@ +## +## Copyright (c) 2024 NVIDIA CORPORATION & AFFILIATES. +## Apache-2.0 +## +## Licensed under the Apache License, Version 2.0 (the "License"); +## you may not use this file except in compliance with the License. +## You may obtain a copy of the License at +## +## http://www.apache.org/licenses/LICENSE-2.0 +## +## Unless required by applicable law or agreed to in writing, software +## distributed under the License is distributed on an "AS IS" BASIS, +## WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied. +## See the License for the specific language governing permissions and +## limitations under the License. +## + +{% from "dockers/dockerfile-macros.j2" import install_debian_packages, install_python_wheels, copy_files %} +FROM docker-config-engine-bookworm-{{DOCKER_USERNAME}}:{{DOCKER_USERTAG}} + +ARG docker_container_name + +RUN [ -f /etc/rsyslog.conf ] && sed -ri "s/%syslogtag%/$docker_container_name#%syslogtag%/;" /etc/rsyslog.conf + +## Make apt-get non-interactive +ENV DEBIAN_FRONTEND=noninteractive + +RUN apt-get update && \ + apt-get install -y \ + udev \ + hwdata \ + pciutils \ + libpcap0.8 \ + libxml2 \ + python3-pip \ + python3-dev \ + python3-setuptools \ + binutils-dev \ + ethtool + +{% if docker_syncd_bluefield_debs.strip() -%} +# Copy locally-built Debian package dependencies +{{ copy_files("debs/", docker_syncd_bluefield_debs.split(' '), "/debs/") }} + +# Install locally-built Debian packages and implicitly install their dependencies +{{ install_debian_packages(docker_syncd_bluefield_debs.split(' ')) }} +{% endif %} + +## Clean up +RUN apt-get clean -y && \ + apt-get autoclean -y && \ + apt-get autoremove -y && \ + rm -rf /debs + +COPY ["supervisord.conf", "/etc/supervisor/conf.d/"] +COPY ["files/supervisor-proc-exit-listener", "/usr/bin"] +COPY ["critical_processes", "/etc/supervisor/"] + +ENTRYPOINT ["/usr/local/bin/supervisord"] diff --git a/platform/nvidia-bluefield/docker-syncd-bluefield/critical_processes b/platform/nvidia-bluefield/docker-syncd-bluefield/critical_processes new file mode 100644 index 00000000000..e69de29bb2d diff --git a/platform/nvidia-bluefield/docker-syncd-bluefield/supervisord.conf b/platform/nvidia-bluefield/docker-syncd-bluefield/supervisord.conf new file mode 100644 index 00000000000..6fd59606062 --- /dev/null +++ b/platform/nvidia-bluefield/docker-syncd-bluefield/supervisord.conf @@ -0,0 +1,39 @@ +[supervisord] +logfile_maxbytes=1MB +logfile_backups=2 +nodaemon=true + +[eventlistener:dependent-startup] +command=python3 -m supervisord_dependent_startup +autostart=true +autorestart=unexpected +startretries=0 +exitcodes=0,3 +events=PROCESS_STATE +buffer_size=1024 + +[eventlistener:supervisor-proc-exit-listener] +command=/usr/bin/supervisor-proc-exit-listener --container-name syncd +events=PROCESS_STATE_EXITED,PROCESS_STATE_RUNNING +autostart=true +autorestart=unexpected +buffer_size=1024 + +[program:rsyslogd] +command=/usr/sbin/rsyslogd -n -iNONE +priority=1 +autostart=false +autorestart=unexpected +stdout_logfile=syslog +stderr_logfile=syslog +dependent_startup=true + +[program:syncd] +command=/usr/bin/syncd_start.sh +priority=2 +autostart=false +autorestart=false +stdout_logfile=syslog +stderr_logfile=syslog +dependent_startup=true +dependent_startup_wait_for=rsyslogd:running diff --git a/platform/nvidia-bluefield/dpu-sai/.gitignore b/platform/nvidia-bluefield/dpu-sai/.gitignore new file mode 100644 index 00000000000..6dbdff4573b --- /dev/null +++ b/platform/nvidia-bluefield/dpu-sai/.gitignore @@ -0,0 +1,5 @@ +# Ignore everything in this directory +* +# Except these files +!.gitignore +!Makefile diff --git a/platform/nvidia-bluefield/dpu-sai/Makefile b/platform/nvidia-bluefield/dpu-sai/Makefile new file mode 100644 index 00000000000..c773bee1a6e --- /dev/null +++ b/platform/nvidia-bluefield/dpu-sai/Makefile @@ -0,0 +1,38 @@ +# +# Copyright (c) 2024 NVIDIA CORPORATION & AFFILIATES. +# Apache-2.0 +# +# Licensed under the Apache License, Version 2.0 (the "License"); +# you may not use this file except in compliance with the License. +# You may obtain a copy of the License at +# +# http://www.apache.org/licenses/LICENSE-2.0 +# +# Unless required by applicable law or agreed to in writing, software +# distributed under the License is distributed on an "AS IS" BASIS, +# WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied. +# See the License for the specific language governing permissions and +# limitations under the License. +# + +.ONESHELL: +SHELL = /bin/bash +.SHELLFLAGS += -ex + +MAIN_TARGET = $(DPU_SAI) +DERIVED_TARGETS = $(DPU_SAI_DBGSYM) + +$(addprefix $(DEST)/, $(MAIN_TARGET)): $(DEST)/% : + + rm -rf mlnx_sai_src + wget -c $(DPU_SAI_SOURCE_BASE_URL)/$(DPU_SAI_VERSION).tar.gz -O - | tar -xz --one-top-level=mlnx_sai_src + pushd mlnx_sai_src + pushd mlnx_sai + + # Build the package + debuild -e 'make_extra_flags="DEFS=-DACS_OS -DCONFIG_SYSLOG"' -us -uc -b -j$(SONIC_CONFIG_MAKE_JOBS) --admindir $(SONIC_DPKG_ADMINDIR) + + popd + + mv $* $(DERIVED_TARGETS) $(DEST)/ + popd diff --git a/platform/nvidia-bluefield/gpio-mlxbf3/.gitignore b/platform/nvidia-bluefield/gpio-mlxbf3/.gitignore new file mode 100644 index 00000000000..6dbdff4573b --- /dev/null +++ b/platform/nvidia-bluefield/gpio-mlxbf3/.gitignore @@ -0,0 +1,5 @@ +# Ignore everything in this directory +* +# Except these files +!.gitignore +!Makefile diff --git a/platform/nvidia-bluefield/gpio-mlxbf3/Makefile b/platform/nvidia-bluefield/gpio-mlxbf3/Makefile new file mode 100644 index 00000000000..1a8f580ca1e --- /dev/null +++ b/platform/nvidia-bluefield/gpio-mlxbf3/Makefile @@ -0,0 +1,39 @@ +# +# Copyright (c) 2024 NVIDIA CORPORATION & AFFILIATES. +# Apache-2.0 +# +# Licensed under the Apache License, Version 2.0 (the "License"); +# you may not use this file except in compliance with the License. +# You may obtain a copy of the License at +# +# http://www.apache.org/licenses/LICENSE-2.0 +# +# Unless required by applicable law or agreed to in writing, software +# distributed under the License is distributed on an "AS IS" BASIS, +# WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied. +# See the License for the specific language governing permissions and +# limitations under the License. +# + +.ONESHELL: +SHELL = /bin/bash +.SHELLFLAGS += -ex + +MLXBF3_GPIO = gpio-mlxbf3-${MLXBF3_GPIO_DRIVER_VERSION} +MODULE_DIR := $(shell pwd)/tmp/${MLXBF3_GPIO} +GET_PACKAGE := $(shell pwd)/../recipes/get-soc-package.sh + +$(addprefix $(DEST)/, $(MLXBF3_GPIO_DRIVER)): $(DEST)/% : + rm -rf ./tmp/ + mkdir ./tmp/ + pushd ./tmp/ + + ${GET_PACKAGE} ${BSD_BASE_SOURCE_URL} ${MLXBF3_GPIO} + + pushd ${MLXBF3_GPIO} + + # Build the package + make -C /lib/modules/$(KVERSION)/build M=$(MODULE_DIR) + + mv ${MLXBF3_GPIO_DRIVER} $(DEST)/ + popd diff --git a/platform/nvidia-bluefield/mft/.gitignore b/platform/nvidia-bluefield/mft/.gitignore new file mode 100644 index 00000000000..6dbdff4573b --- /dev/null +++ b/platform/nvidia-bluefield/mft/.gitignore @@ -0,0 +1,5 @@ +# Ignore everything in this directory +* +# Except these files +!.gitignore +!Makefile diff --git a/platform/nvidia-bluefield/mft/Makefile b/platform/nvidia-bluefield/mft/Makefile new file mode 100644 index 00000000000..649bb99b751 --- /dev/null +++ b/platform/nvidia-bluefield/mft/Makefile @@ -0,0 +1,80 @@ +# +# Copyright (c) 2024 NVIDIA CORPORATION & AFFILIATES. +# Apache-2.0 +# +# Licensed under the Apache License, Version 2.0 (the "License"); +# you may not use this file except in compliance with the License. +# You may obtain a copy of the License at +# +# http://www.apache.org/licenses/LICENSE-2.0 +# +# Unless required by applicable law or agreed to in writing, software +# distributed under the License is distributed on an "AS IS" BASIS, +# WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied. +# See the License for the specific language governing permissions and +# limitations under the License. +# +.ONESHELL: +SHELL = /bin/bash +.SHELLFLAGS += -e + +MFT_NAME = mft-$(MFT_VERSION)-$(MFT_REVISION)-arm64-deb +MFT_TGZ = $(MFT_NAME).tgz + +ifeq ($(MFT_FROM_INTERNAL),y) +MFT_TGZ_URL = $(MFT_INTERNAL_SOURCE_BASE_URL)/$(MFT_TGZ) +else +MFT_TGZ_URL = http://www.mellanox.com/downloads/MFT/$(MFT_TGZ) +endif + +BUILD_ARCH = $(shell dpkg-architecture -qDEB_BUILD_ARCH) +KERNEL_MFT_TARGET = kernel-mft-dkms-modules-$(KVERSION)_$(MFT_VERSION)_$(BUILD_ARCH).deb + +MAIN_TARGET = mft_$(MFT_VERSION)-$(MFT_REVISION)_arm64.deb +DERIVED_TARGETS = mft-oem_$(MFT_VERSION)-$(MFT_REVISION)_arm64.deb + +DKMS_CTRL = /var/lib/dkms/kernel-mft-dkms/ +DKMS_TMP := $(shell mktemp -u -d -t dkms.XXXXXXXXXX) + +MFT_TMP = /tmp/mft_build/ + +$(addprefix $(DEST)/, $(MAIN_TARGET)): $(DEST)/% : + mkdir -p $(MFT_TMP) + pushd $(MFT_TMP) + rm -rf $(MFT_NAME) + wget -O $(MFT_TGZ) $(MFT_TGZ_URL) + tar xzf $(MFT_TGZ) + + # fix timestamp because we do not actually build tools, only kernel + touch $(MFT_NAME)/DEBS/*.deb + touch $(MFT_NAME)/SDEBS/*.deb + mv $(MFT_NAME)/DEBS/*.deb $(DEST) + mv $(MFT_NAME)/SDEBS/*.deb $(DEST) + popd + rm -rf $(MFT_TMP) + +$(addprefix $(DEST)/, $(DERIVED_TARGETS)): $(DEST)/% : $(DEST)/$(MAIN_TARGET) + +$(addprefix $(DEST)/, $(KERNEL_MFT_TARGET)): $(DEST)/% : + # Prepare the directory to build kernel-mft-dkms-modules debian package + mkdir -p $(DKMS_TMP)/DEBIAN + mkdir -p $(DKMS_TMP)/lib/modules/$(KVERSION)/updates/dkms/ + export kversion="$(KVERSION)" + export mft_version="$(MFT_VERSION)" + j2 templates/control.j2 > $(DKMS_TMP)/DEBIAN/control + j2 templates/postinst.j2 > $(DKMS_TMP)/DEBIAN/postinst + j2 templates/postrm.j2 > $(DKMS_TMP)/DEBIAN/postrm + chmod +x $(DKMS_TMP)/DEBIAN/postinst + chmod +x $(DKMS_TMP)/DEBIAN/postrm + + sudo dkms build kernel-mft-dkms/$(MFT_VERSION) -k $(KVERSION) -a arm64 + + # copy the built modules + cp -r $(DKMS_CTRL)/kernel-$(KVERSION)*/module/*.ko \ + $(DKMS_TMP)/lib/modules/$(KVERSION)/updates/dkms/ + + dpkg -b $(DKMS_TMP) . + + rm -rf $(DKMS_TMP) + + mv $(KERNEL_MFT_TARGET) $(DEST) diff --git a/platform/nvidia-bluefield/mft/templates/control.j2 b/platform/nvidia-bluefield/mft/templates/control.j2 new file mode 100644 index 00000000000..91334bf5009 --- /dev/null +++ b/platform/nvidia-bluefield/mft/templates/control.j2 @@ -0,0 +1,9 @@ +Package: kernel-mft-dkms-modules-{{kversion}} +Source: kernel-mft-dkms-dkms-bin +Version: {{mft_version}} +Architecture: arm64 +Maintainer: Vivek Reddy +Provides: kernel-mft-dkms-modules +Section: misc +Priority: optional +Description: kernel-mft-dkms binary drivers for linux-image-{{kversion}} Kernel diff --git a/platform/nvidia-bluefield/mft/templates/postinst.j2 b/platform/nvidia-bluefield/mft/templates/postinst.j2 new file mode 100644 index 00000000000..b0dc5790936 --- /dev/null +++ b/platform/nvidia-bluefield/mft/templates/postinst.j2 @@ -0,0 +1,3 @@ +#!/bin/sh +set -e +depmod -a {{kversion}} diff --git a/platform/nvidia-bluefield/mft/templates/postrm.j2 b/platform/nvidia-bluefield/mft/templates/postrm.j2 new file mode 100644 index 00000000000..b0dc5790936 --- /dev/null +++ b/platform/nvidia-bluefield/mft/templates/postrm.j2 @@ -0,0 +1,3 @@ +#!/bin/sh +set -e +depmod -a {{kversion}} diff --git a/platform/nvidia-bluefield/mlx-bootctl/.gitignore b/platform/nvidia-bluefield/mlx-bootctl/.gitignore new file mode 100644 index 00000000000..6dbdff4573b --- /dev/null +++ b/platform/nvidia-bluefield/mlx-bootctl/.gitignore @@ -0,0 +1,5 @@ +# Ignore everything in this directory +* +# Except these files +!.gitignore +!Makefile diff --git a/platform/nvidia-bluefield/mlx-bootctl/Makefile b/platform/nvidia-bluefield/mlx-bootctl/Makefile new file mode 100644 index 00000000000..915d5cb3b33 --- /dev/null +++ b/platform/nvidia-bluefield/mlx-bootctl/Makefile @@ -0,0 +1,39 @@ +# +# Copyright (c) 2024 NVIDIA CORPORATION & AFFILIATES. +# Apache-2.0 +# +# Licensed under the Apache License, Version 2.0 (the "License"); +# you may not use this file except in compliance with the License. +# You may obtain a copy of the License at +# +# http://www.apache.org/licenses/LICENSE-2.0 +# +# Unless required by applicable law or agreed to in writing, software +# distributed under the License is distributed on an "AS IS" BASIS, +# WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied. +# See the License for the specific language governing permissions and +# limitations under the License. +# + +.ONESHELL: +SHELL = /bin/bash +.SHELLFLAGS += -ex + +MLX_BOOTCTL = mlx-bootctl-$(MLX_BOOTCTL_DRIVER_VERSION) +GET_PACKAGE := $(shell pwd)/../recipes/get-soc-package.sh + +$(addprefix $(DEST)/, $(MLX_BOOTCTL_DRIVER)): $(DEST)/% : + rm -rf ./tmp/ + mkdir ./tmp/ + pushd ./tmp/ + + ${GET_PACKAGE} ${BSD_BASE_SOURCE_URL} ${MLX_BOOTCTL} + + pushd ${MLX_BOOTCTL} + + # Build the package + KVER=$(KVERSION) WITH_DKMS=0 dpkg-buildpackage -rfakeroot -us -uc -b -j$(SONIC_CONFIG_MAKE_JOBS) --admindir $(SONIC_DPKG_ADMINDIR) + + mv mlxbf-bootctl.ko $(DEST)/mlx-bootctl.ko + + popd diff --git a/platform/nvidia-bluefield/mlxbf-bootctl/.gitignore b/platform/nvidia-bluefield/mlxbf-bootctl/.gitignore new file mode 100644 index 00000000000..6dbdff4573b --- /dev/null +++ b/platform/nvidia-bluefield/mlxbf-bootctl/.gitignore @@ -0,0 +1,5 @@ +# Ignore everything in this directory +* +# Except these files +!.gitignore +!Makefile diff --git a/platform/nvidia-bluefield/mlxbf-bootctl/Makefile b/platform/nvidia-bluefield/mlxbf-bootctl/Makefile new file mode 100644 index 00000000000..e967ffe1761 --- /dev/null +++ b/platform/nvidia-bluefield/mlxbf-bootctl/Makefile @@ -0,0 +1,39 @@ +# +# Copyright (c) 2024 NVIDIA CORPORATION & AFFILIATES. +# Apache-2.0 +# +# Licensed under the Apache License, Version 2.0 (the "License"); +# you may not use this file except in compliance with the License. +# You may obtain a copy of the License at +# +# http://www.apache.org/licenses/LICENSE-2.0 +# +# Unless required by applicable law or agreed to in writing, software +# distributed under the License is distributed on an "AS IS" BASIS, +# WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied. +# See the License for the specific language governing permissions and +# limitations under the License. +# + +.ONESHELL: +SHELL = /bin/bash +.SHELLFLAGS += -ex + +MLXBF_BOOTCTL = mlxbf-bootctl-${MLXBF_BOOTCTL_DEB_VERSION} +GET_PACKAGE := $(shell pwd)/../recipes/get-soc-package.sh + +$(addprefix $(DEST)/, $(MLXBF_BOOTCTL_DEB)): $(DEST)/% : + rm -rf ./tmp/ + mkdir ./tmp/ + pushd ./tmp/ + + ${GET_PACKAGE} ${BSD_BASE_SOURCE_URL} ${MLXBF_BOOTCTL} + + pushd ${MLXBF_BOOTCTL} + + # Build the package + DEB_BUILD_OPTIONS=nocheck dpkg-buildpackage -rfakeroot -us -uc -b -j$(SONIC_CONFIG_MAKE_JOBS) --admindir $(SONIC_DPKG_ADMINDIR) + + popd + + mv $* $(DEST)/ diff --git a/platform/nvidia-bluefield/mlxbf-gige/.gitignore b/platform/nvidia-bluefield/mlxbf-gige/.gitignore new file mode 100644 index 00000000000..6dbdff4573b --- /dev/null +++ b/platform/nvidia-bluefield/mlxbf-gige/.gitignore @@ -0,0 +1,5 @@ +# Ignore everything in this directory +* +# Except these files +!.gitignore +!Makefile diff --git a/platform/nvidia-bluefield/mlxbf-gige/Makefile b/platform/nvidia-bluefield/mlxbf-gige/Makefile new file mode 100644 index 00000000000..d9bddb1139f --- /dev/null +++ b/platform/nvidia-bluefield/mlxbf-gige/Makefile @@ -0,0 +1,39 @@ +# +# Copyright (c) 2024 NVIDIA CORPORATION & AFFILIATES. +# Apache-2.0 +# +# Licensed under the Apache License, Version 2.0 (the "License"); +# you may not use this file except in compliance with the License. +# You may obtain a copy of the License at +# +# http://www.apache.org/licenses/LICENSE-2.0 +# +# Unless required by applicable law or agreed to in writing, software +# distributed under the License is distributed on an "AS IS" BASIS, +# WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied. +# See the License for the specific language governing permissions and +# limitations under the License. +# + +.ONESHELL: +SHELL = /bin/bash +.SHELLFLAGS += -ex + +MLXBF_GIGE = mlxbf-gige-${MLXBF_GIGE_DRIVER_VERSION} +MODULE_DIR := $(shell pwd)/tmp/${MLXBF_GIGE} +GET_PACKAGE := $(shell pwd)/../recipes/get-soc-package.sh + +$(addprefix $(DEST)/, $(MLXBF_GIGE_DRIVER)): $(DEST)/% : + rm -rf ./tmp/ + mkdir ./tmp/ + pushd ./tmp/ + + ${GET_PACKAGE} ${BSD_BASE_SOURCE_URL} ${MLXBF_GIGE} + + pushd ${MLXBF_GIGE} + + # Build the package + make -C /lib/modules/$(KVERSION)/build M=$(MODULE_DIR) + + mv ${MLXBF_GIGE_DRIVER} $(DEST)/ + popd diff --git a/platform/nvidia-bluefield/mlxbf-pka/.gitignore b/platform/nvidia-bluefield/mlxbf-pka/.gitignore new file mode 100644 index 00000000000..6dbdff4573b --- /dev/null +++ b/platform/nvidia-bluefield/mlxbf-pka/.gitignore @@ -0,0 +1,5 @@ +# Ignore everything in this directory +* +# Except these files +!.gitignore +!Makefile diff --git a/platform/nvidia-bluefield/mlxbf-pka/Makefile b/platform/nvidia-bluefield/mlxbf-pka/Makefile new file mode 100644 index 00000000000..28a44c990dc --- /dev/null +++ b/platform/nvidia-bluefield/mlxbf-pka/Makefile @@ -0,0 +1,39 @@ +# +# Copyright (c) 2024 NVIDIA CORPORATION & AFFILIATES. +# Apache-2.0 +# +# Licensed under the Apache License, Version 2.0 (the "License"); +# you may not use this file except in compliance with the License. +# You may obtain a copy of the License at +# +# http://www.apache.org/licenses/LICENSE-2.0 +# +# Unless required by applicable law or agreed to in writing, software +# distributed under the License is distributed on an "AS IS" BASIS, +# WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied. +# See the License for the specific language governing permissions and +# limitations under the License. +# + +.ONESHELL: +SHELL = /bin/bash +.SHELLFLAGS += -ex + +MLXBF_PKA = mlxbf-pka-${MLXBF_PKA_DRIVER_VERSION} +MODULE_DIR := $(shell pwd)/tmp/${MLXBF_PKA} +GET_PACKAGE := $(shell pwd)/../recipes/get-soc-package.sh + +$(addprefix $(DEST)/, $(MLXBF_PKA_DRIVER)): $(DEST)/% : + rm -rf ./tmp/ + mkdir ./tmp/ + pushd ./tmp/ + + ${GET_PACKAGE} ${BSD_BASE_SOURCE_URL} ${MLXBF_PKA} + + pushd ${MLXBF_PKA} + + # Build the package + make -C /lib/modules/$(KVERSION)/build M=$(MODULE_DIR) + + mv ${MLXBF_PKA_DRIVER} $(DEST)/ + popd diff --git a/platform/nvidia-bluefield/mlxbf-ptm/Makefile b/platform/nvidia-bluefield/mlxbf-ptm/Makefile new file mode 100644 index 00000000000..d7c77951003 --- /dev/null +++ b/platform/nvidia-bluefield/mlxbf-ptm/Makefile @@ -0,0 +1,39 @@ +# +# Copyright (c) 2024 NVIDIA CORPORATION & AFFILIATES. +# Apache-2.0 +# +# Licensed under the Apache License, Version 2.0 (the "License"); +# you may not use this file except in compliance with the License. +# You may obtain a copy of the License at +# +# http://www.apache.org/licenses/LICENSE-2.0 +# +# Unless required by applicable law or agreed to in writing, software +# distributed under the License is distributed on an "AS IS" BASIS, +# WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied. +# See the License for the specific language governing permissions and +# limitations under the License. +# + +.ONESHELL: +SHELL = /bin/bash +.SHELLFLAGS += -ex + +MLXBF_PTM = mlxbf-ptm-${MLXBF_PTM_DRIVER_VERSION} +MODULE_DIR := $(shell pwd)/tmp/${MLXBF_PTM} +GET_PACKAGE := $(shell pwd)/../recipes/get-soc-package.sh + +$(addprefix $(DEST)/, $(MLXBF_PTM_DRIVER)): $(DEST)/% : + rm -rf ./tmp/ + mkdir ./tmp/ + pushd ./tmp/ + + ${GET_PACKAGE} ${BSD_BASE_SOURCE_URL} ${MLXBF_PTM} + + pushd ${MLXBF_PTM} + + # Build the package + make -C /lib/modules/$(KVERSION)/build M=$(MODULE_DIR) + + mv ${MLXBF_PTM_DRIVER} $(DEST)/ + popd diff --git a/platform/nvidia-bluefield/modules b/platform/nvidia-bluefield/modules new file mode 100644 index 00000000000..7166662dc8c --- /dev/null +++ b/platform/nvidia-bluefield/modules @@ -0,0 +1,6 @@ +crc16 +deflate +zlib_deflate +ubifs +squashfs +sdhci-of-dwcmshc diff --git a/platform/nvidia-bluefield/pinctrl-mlxbf3/.gitignore b/platform/nvidia-bluefield/pinctrl-mlxbf3/.gitignore new file mode 100644 index 00000000000..6dbdff4573b --- /dev/null +++ b/platform/nvidia-bluefield/pinctrl-mlxbf3/.gitignore @@ -0,0 +1,5 @@ +# Ignore everything in this directory +* +# Except these files +!.gitignore +!Makefile diff --git a/platform/nvidia-bluefield/pinctrl-mlxbf3/Makefile b/platform/nvidia-bluefield/pinctrl-mlxbf3/Makefile new file mode 100644 index 00000000000..ca56f30f832 --- /dev/null +++ b/platform/nvidia-bluefield/pinctrl-mlxbf3/Makefile @@ -0,0 +1,41 @@ +# +# Copyright (c) 2024 NVIDIA CORPORATION & AFFILIATES. +# Apache-2.0 +# +# Licensed under the Apache License, Version 2.0 (the "License"); +# you may not use this file except in compliance with the License. +# You may obtain a copy of the License at +# +# http://www.apache.org/licenses/LICENSE-2.0 +# +# Unless required by applicable law or agreed to in writing, software +# distributed under the License is distributed on an "AS IS" BASIS, +# WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied. +# See the License for the specific language governing permissions and +# limitations under the License. +# + +.ONESHELL: +SHELL = /bin/bash +.SHELLFLAGS += -ex + +MLXBF3_PINCTRL = pinctrl-mlxbf3-${MLXBF3_PINCTRL_DRIVER_VERSION} +MODULE_DIR := $(shell pwd)/tmp/${MLXBF3_PINCTRL} +GET_PACKAGE := $(shell pwd)/../recipes/get-soc-package.sh + +$(addprefix $(DEST)/, $(MLXBF3_PINCTRL_DRIVER)): $(DEST)/% : + rm -rf ./tmp/ + mkdir ./tmp/ + pushd ./tmp/ + + ${GET_PACKAGE} ${BSD_BASE_SOURCE_URL} ${MLXBF3_PINCTRL} + + pushd ${MLXBF3_PINCTRL} + + patch -p1 < ../../pinctrl-mlxbf3.c.patch + + # Build the package + make -C /lib/modules/$(KVERSION)/build M=$(MODULE_DIR) + + mv ${MLXBF3_PINCTRL_DRIVER} $(DEST)/ + popd diff --git a/platform/nvidia-bluefield/platform-api/.gitignore b/platform/nvidia-bluefield/platform-api/.gitignore new file mode 100644 index 00000000000..6dbdff4573b --- /dev/null +++ b/platform/nvidia-bluefield/platform-api/.gitignore @@ -0,0 +1,5 @@ +# Ignore everything in this directory +* +# Except these files +!.gitignore +!Makefile diff --git a/platform/nvidia-bluefield/platform-api/pytest.ini b/platform/nvidia-bluefield/platform-api/pytest.ini new file mode 100644 index 00000000000..778e2b10c43 --- /dev/null +++ b/platform/nvidia-bluefield/platform-api/pytest.ini @@ -0,0 +1,20 @@ +## +## Copyright (c) 2024 NVIDIA CORPORATION & AFFILIATES. +## Apache-2.0 +## +## Licensed under the Apache License, Version 2.0 (the "License"); +## you may not use this file except in compliance with the License. +## You may obtain a copy of the License at +## +## http://www.apache.org/licenses/LICENSE-2.0 +## +## Unless required by applicable law or agreed to in writing, software +## distributed under the License is distributed on an "AS IS" BASIS, +## WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied. +## See the License for the specific language governing permissions and +## limitations under the License. +## +[pytest] +addopts = --cov=sonic_platform --cov-report html --cov-report term --cov-report xml --junitxml=test-results.xml -vv +filterwarnings = + ignore::DeprecationWarning diff --git a/platform/nvidia-bluefield/platform-api/setup.cfg b/platform/nvidia-bluefield/platform-api/setup.cfg new file mode 100644 index 00000000000..b7e478982cc --- /dev/null +++ b/platform/nvidia-bluefield/platform-api/setup.cfg @@ -0,0 +1,2 @@ +[aliases] +test=pytest diff --git a/platform/nvidia-bluefield/platform-api/setup.py b/platform/nvidia-bluefield/platform-api/setup.py new file mode 100644 index 00000000000..7ef3bfd4790 --- /dev/null +++ b/platform/nvidia-bluefield/platform-api/setup.py @@ -0,0 +1,55 @@ +# +# Copyright (c) 2024 NVIDIA CORPORATION & AFFILIATES. +# Apache-2.0 +# +# Licensed under the Apache License, Version 2.0 (the "License"); +# you may not use this file except in compliance with the License. +# You may obtain a copy of the License at +# +# http://www.apache.org/licenses/LICENSE-2.0 +# +# Unless required by applicable law or agreed to in writing, software +# distributed under the License is distributed on an "AS IS" BASIS, +# WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied. +# See the License for the specific language governing permissions and +# limitations under the License. +# +from setuptools import setup + +setup( + name='platform-api', + version='1.0', + description='SONiC platform API implementation on NVIDIA BlueField platform', + license='Apache 2.0', + author='NVIDIA SONiC Team', + author_email='oivantsiv@nvidia.com', + url='https://github.com/Azure/sonic-buildimage', + maintainer='Oleksandr Ivantsiv', + maintainer_email='oivantsiv@nvidia.com', + packages=[ + 'sonic_platform', + 'sonic_platform/throttling_checks', + 'tests' + ], + setup_requires= [ + 'pytest-runner' + ], + tests_require = [ + 'pytest', + 'mock>=2.0.0' + ], + classifiers=[ + 'Development Status :: 3 - Alpha', + 'Environment :: Plugins', + 'Intended Audience :: Developers', + 'Intended Audience :: Information Technology', + 'Intended Audience :: System Administrators', + 'License :: OSI Approved :: Apache Software License', + 'Natural Language :: English', + 'Operating System :: POSIX :: Linux', + 'Programming Language :: Python :: 3.7', + 'Topic :: Utilities', + ], + keywords='sonic SONiC platform PLATFORM', + test_suite='setup.get_test_suite' +) diff --git a/platform/nvidia-bluefield/platform-api/sonic_platform/__init__.py b/platform/nvidia-bluefield/platform-api/sonic_platform/__init__.py new file mode 100644 index 00000000000..660a999a4af --- /dev/null +++ b/platform/nvidia-bluefield/platform-api/sonic_platform/__init__.py @@ -0,0 +1,18 @@ +# +# Copyright (c) 2024 NVIDIA CORPORATION & AFFILIATES. +# Apache-2.0 +# +# Licensed under the Apache License, Version 2.0 (the "License"); +# you may not use this file except in compliance with the License. +# You may obtain a copy of the License at +# +# http://www.apache.org/licenses/LICENSE-2.0 +# +# Unless required by applicable law or agreed to in writing, software +# distributed under the License is distributed on an "AS IS" BASIS, +# WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied. +# See the License for the specific language governing permissions and +# limitations under the License. +# +__all__ = ["platform", "chassis"] +from sonic_platform import * diff --git a/platform/nvidia-bluefield/platform-api/sonic_platform/chassis.py b/platform/nvidia-bluefield/platform-api/sonic_platform/chassis.py new file mode 100644 index 00000000000..0d92a16a04a --- /dev/null +++ b/platform/nvidia-bluefield/platform-api/sonic_platform/chassis.py @@ -0,0 +1,274 @@ +# +# Copyright (c) 2024 NVIDIA CORPORATION & AFFILIATES. +# Apache-2.0 +# +# Licensed under the Apache License, Version 2.0 (the "License"); +# you may not use this file except in compliance with the License. +# You may obtain a copy of the License at +# +# http://www.apache.org/licenses/LICENSE-2.0 +# +# Unless required by applicable law or agreed to in writing, software +# distributed under the License is distributed on an "AS IS" BASIS, +# WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied. +# See the License for the specific language governing permissions and +# limitations under the License. +# + +try: + from sonic_platform_base.chassis_base import ChassisBase + from sonic_platform_base.watchdog_base import WatchdogBase + from sonic_py_common.logger import Logger + import os + from functools import reduce + from time import sleep + + from . import utils + from .device_data import DeviceDataManager + from .sfp import Sfp + from .sfp_event import SfpEvent + from .eeprom import Eeprom + from .watchdog import Watchdog +except ImportError as e: + raise ImportError(str(e) + "- required module not found") + +MAX_SELECT_DELAY = 3600 + + +# Global logger class instance +logger = Logger() + + +class Chassis(ChassisBase): + """Platform-specific Chassis class""" + + def __init__(self): + super(Chassis, self).__init__() + + # Initialize DMI data + self.dmi_data = None + + self.device_data = DeviceDataManager() + self._initialize_sfp() + self.sfp_event = None + self._eeprom = Eeprom() + self._watchdog = Watchdog() + logger.log_info("Chassis loaded successfully") + + def _initialize_sfp(self): + self._sfp_list = [] + + sfp_count = self.get_num_sfps() + for index in range(sfp_count): + sfp_module = Sfp(index, self.device_data.get_sfp_data(index)) + self._sfp_list.append(sfp_module) + self._sfp_event = SfpEvent(self._sfp_list) + + def get_sfp(self, index): + return super(Chassis, self).get_sfp(index - 1) + + def get_num_sfps(self): + """ + Retrieves the number of sfps available on this chassis + + Returns: + An integer, the number of sfps available on this chassis + """ + return self.device_data.get_sfp_count() + + def get_change_event(self, timeout=0): + """ + Returns a nested dictionary containing all devices which have + experienced a change at chassis level + + Args: + timeout: Timeout in milliseconds (optional). If timeout == 0, + this method will block until a change is detected. + + Returns: + (bool, dict): + - True if call successful, False if not; + - A nested dictionary where key is a device type, + value is a dictionary with key:value pairs in the format of + {'device_id':'device_event'}, + where device_id is the device ID for this device and + device_event, + status='1' represents device inserted, + status='0' represents device removed. + Ex. {'fan':{'0':'0', '2':'1'}, 'sfp':{'11':'0'}} + indicates that fan 0 has been removed, fan 2 + has been inserted and sfp 11 has been removed. + """ + + return self._sfp_event.get_sfp_event(timeout) + + def get_eeprom(self): + """ + Retrieves eeprom device on this chassis + + Returns: + An object derived from WatchdogBase representing the hardware + eeprom device + """ + return self._eeprom + + def get_name(self): + """ + Retrieves the name of the device + + Returns: + string: The name of the device + """ + return self._eeprom.get_product_name() + + def get_model(self): + """ + Retrieves the model number (or part number) of the device + + Returns: + string: Model/part number of device + """ + return self._eeprom.get_part_number() + + def get_base_mac(self): + """ + Retrieves the base MAC address for the chassis + + Returns: + A string containing the MAC address in the format + 'XX:XX:XX:XX:XX:XX' + """ + return self._eeprom.get_base_mac() + + def get_serial(self): + """ + Retrieves the hardware serial number for the chassis + + Returns: + A string containing the hardware serial number for this chassis. + """ + return self._eeprom.get_serial_number() + + def get_system_eeprom_info(self): + """ + Retrieves the full content of system EEPROM information for the chassis + + Returns: + A dictionary where keys are the type code defined in + OCP ONIE TlvInfo EEPROM format and values are their corresponding + values. + """ + return self._eeprom.get_system_eeprom_info() + + def get_revision(self): + """ + Retrieves the hardware revision of the device + + Returns: + string: Revision value of device + """ + return self._eeprom.get_revision() + + def get_position_in_parent(self): + """ + Retrieves 1-based relative physical position in parent device. If the agent cannot determine the parent-relative position + for some reason, or if the associated value of entPhysicalContainedIn is '0', then the value '-1' is returned + Returns: + integer: The 1-based relative physical position in parent device or -1 if cannot determine the position + """ + return -1 + + def is_replaceable(self): + """ + Indicate whether this device is replaceable. + Returns: + bool: True if it is replaceable. + """ + return False + + ############################################## + # THERMAL methods + ############################################## + + def initialize_thermals(self): + if not self._thermal_list: + from .thermal import initialize_chassis_thermals + # Initialize thermals + self._thermal_list = initialize_chassis_thermals() + + def get_num_thermals(self): + """ + Retrieves the number of thermals available on this chassis + + Returns: + An integer, the number of thermals available on this chassis + """ + self.initialize_thermals() + return len(self._thermal_list) + + def get_all_thermals(self): + """ + Retrieves all thermals available on this chassis + + Returns: + A list of objects derived from ThermalBase representing all thermals + available on this chassis + """ + self.initialize_thermals() + return self._thermal_list + + def get_thermal(self, index): + """ + Retrieves thermal unit represented by (0-based) index + + Args: + index: An integer, the index (0-based) of the thermal to + retrieve + + Returns: + An object derived from ThermalBase representing the specified thermal + """ + self.initialize_thermals() + return super(Chassis, self).get_thermal(index) + + ############################################## + # System LED methods + ############################################## + + def initizalize_system_led(self): + pass + + def set_status_led(self, color): + """ + Sets the state of the system LED + + Args: + color: A string representing the color with which to set the + system LED + + Returns: + bool: True if system LED state is set successfully, False if not + """ + return False + + def get_status_led(self): + """ + Gets the state of the system LED + + Returns: + A string, one of the valid LED color strings which could be vendor + specified. + """ + return 'N/A' + + def get_reboot_cause(self): + """ + Retrieves the cause of the previous reboot + Returns: + A tuple (string, string) where the first element is a string + containing the cause of the previous reboot. This string must be + one of the predefined strings in this class. If the first string + is "REBOOT_CAUSE_HARDWARE_OTHER", the second string can be used + to pass a description of the reboot cause. + """ + return "N/A", "N/A" diff --git a/platform/nvidia-bluefield/platform-api/sonic_platform/device_data.py b/platform/nvidia-bluefield/platform-api/sonic_platform/device_data.py new file mode 100644 index 00000000000..c4d3e902f1e --- /dev/null +++ b/platform/nvidia-bluefield/platform-api/sonic_platform/device_data.py @@ -0,0 +1,72 @@ +# +# Copyright (c) 2024 NVIDIA CORPORATION & AFFILIATES. +# Apache-2.0 +# +# Licensed under the Apache License, Version 2.0 (the "License"); +# you may not use this file except in compliance with the License. +# You may obtain a copy of the License at +# +# http://www.apache.org/licenses/LICENSE-2.0 +# +# Unless required by applicable law or agreed to in writing, software +# distributed under the License is distributed on an "AS IS" BASIS, +# WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied. +# See the License for the specific language governing permissions and +# limitations under the License. +# + +import glob +import os +import json +from enum import Enum +from sonic_py_common import device_info + +from . import utils + + +class SfpData: + + def __init__(self, name, thermals=None): + self.name = name + self.thermals = thermals + + +class DeviceDataManager: + + def __init__(self): + self._platform = device_info.get_platform() + self._platform_dir = device_info.get_path_to_platform_dir() + + platform_json = os.path.join(self._platform_dir, device_info.PLATFORM_JSON_FILE) + if not os.path.isfile(platform_json): + raise RuntimeError("{} file does not exists".format(platform_json)) + + platform_data = json.loads(open(platform_json).read()) + self._chassis = platform_data.get('chassis') + if not self._chassis: + raise RuntimeError("Chassis data is not found in {} file".format(device_info.PLATFORM_JSON_FILE)) + + self._interfaces = platform_data.get('interfaces') + if not self._interfaces: + raise RuntimeError("Interfaces data is not found in {} file".format(device_info.PLATFORM_JSON_FILE)) + + def get_platform_name(self): + return self._chassis['name'] + + def get_fan_drawer_count(self): + return len(self._chassis['fan_drawers']) + + def get_fan_count(self): + return len(self._chassis['fans']) + + def get_psu_count(self): + return len(self._chassis['psus']) + + def get_sfp_count(self): + return len(self._chassis['sfps']) + + def get_sfp_data(self, sfp_index): + if sfp_index >= len(self._chassis['sfps']): + raise RuntimeError("Wrong SFP index: {}".format(sfp_index)) + sfp_data = self._chassis['sfps'][sfp_index] + return SfpData(**sfp_data) diff --git a/platform/nvidia-bluefield/platform-api/sonic_platform/eeprom.py b/platform/nvidia-bluefield/platform-api/sonic_platform/eeprom.py new file mode 100644 index 00000000000..1d924b9178c --- /dev/null +++ b/platform/nvidia-bluefield/platform-api/sonic_platform/eeprom.py @@ -0,0 +1,314 @@ +# +# Copyright (c) 2024 NVIDIA CORPORATION & AFFILIATES. +# Apache-2.0 +# +# Licensed under the Apache License, Version 2.0 (the "License"); +# you may not use this file except in compliance with the License. +# You may obtain a copy of the License at +# +# http://www.apache.org/licenses/LICENSE-2.0 +# +# Unless required by applicable law or agreed to in writing, software +# distributed under the License is distributed on an "AS IS" BASIS, +# WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied. +# See the License for the specific language governing permissions and +# limitations under the License. +# + +from functools import reduce +import re +import enum +import subprocess + +from sonic_py_common.logger import Logger +try: + from sonic_platform_base.sonic_eeprom.eeprom_tlvinfo import TlvInfoDecoder +except ImportError as e: + raise ImportError(str(e) + "- required module not found") + +from .utils import default_return + +logger = Logger() + + +class Vpd: + + class VpdAttrs(enum.Enum): + product_name_id = 0 + part_number_id = 1 + revision = 2 + serian_number = 3 + connectx_fw_ver = 4 + board_id = 5 + node_guid = 6 + sys_image_guid = 7 + + vpd_attrs_map = { + ('IDTAG', 'Board Id'): VpdAttrs.product_name_id, + ('PN', 'Part Number'): VpdAttrs.part_number_id, + ('EC', 'Revision'): VpdAttrs.revision, + ('SN', 'Serial Number'): VpdAttrs.serian_number, + } + + def __init__(self, fwmngr): + self.fwmngr = fwmngr + self.vpd_attrs = {} + + def _read_raw(self): + p = subprocess.Popen( + ["mlxvpd", "-d", self.fwmngr.get_pci_dev_name()], + stdout=subprocess.PIPE, stderr=subprocess.PIPE) + raw_data, err = p.communicate() + + if err: + raise RuntimeError(err.decode()) + + return raw_data.decode().split('\n') + + def _read(self): + vpd_attrs = {} + + for line in self._read_raw(): + line = line.strip() + if not line: + continue + + for (vpd, descr), idx in self.vpd_attrs_map.items(): + match = re.search(f'{vpd}\s+{descr}', line) + if not match: + continue + vpd_attrs[idx] = line.replace(match.group(), '').strip() + + return vpd_attrs + + def _get_vpd_attrs(self): + if not self.vpd_attrs: + self.vpd_attrs = self._read() + + return self.vpd_attrs + + def get_serial_number(self): + self._get_vpd_attrs() + return self.vpd_attrs[self.VpdAttrs.serian_number] + + def get_product_name(self): + self._get_vpd_attrs() + return self.vpd_attrs[self.VpdAttrs.product_name_id] + + def get_part_number(self): + self._get_vpd_attrs() + return self.vpd_attrs[self.VpdAttrs.part_number_id] + + def get_revision(self): + self._get_vpd_attrs() + return self.vpd_attrs[self.VpdAttrs.revision] + + +class FwManager: + + class FwInfo(enum.Enum): + base_mac = 0 + pci_dev_name = 1 + + fw_info_fields_map = { + 'Base MAC': FwInfo.base_mac, + 'PCI Device Name': FwInfo.pci_dev_name + } + + def __init__(self): + self._fw_info = {} + + def _read_fw_info_raw(self): + p = subprocess.Popen( + "mlxfwmanager", shell=True, stdout=subprocess.PIPE, stderr=subprocess.PIPE) + raw_data, err = p.communicate() + + if err: + raise RuntimeError(err.decode()) + + return raw_data.decode().split('\n') + + def _read_fw_info(self): + fw_info = {} + + for line in self._read_fw_info_raw(): + line = line.strip() + if not line: + continue + + line = line.split(': ') + if len(line) != 2 or line[0] not in self.fw_info_fields_map: + continue + + fw_info[self.fw_info_fields_map[line[0]]] = line[1].strip() + + return fw_info + + def _get_fw_info(self): + if not self._fw_info: + self._fw_info = self._read_fw_info() + + return self._fw_info + + def get_base_mac(self): + self._get_fw_info() + mac = self._fw_info[self.FwInfo.base_mac] + return ":".join([mac[i] + mac[i + 1] for i in range(0, len(mac), 2)]) + + def get_pci_dev_name(self): + self._get_fw_info() + return self._fw_info[self.FwInfo.pci_dev_name] + + +class Eeprom(TlvInfoDecoder): + + def __init__(self): + self._fwmngr = FwManager() + self._vpd = Vpd(self._fwmngr) + self._eeprom_info_dict = None + self._eeprom_raw = None + super(Eeprom, self).__init__('', 0, '', True) + + @default_return(return_value='Undefined.') + def get_base_mac(self): + """ + Retrieves the base MAC address for the chassis + + Returns: + A string containing the MAC address in the format + 'XX:XX:XX:XX:XX:XX' + """ + return self._get_eeprom_value(self._TLV_CODE_MAC_BASE) + + @default_return(return_value='Undefined.') + def get_serial_number(self): + """ + Retrieves the hardware serial number for the chassis + + Returns: + A string containing the hardware serial number for this chassis. + """ + return self._get_eeprom_value(self._TLV_CODE_SERIAL_NUMBER) + + @default_return(return_value='Undefined.') + def get_product_name(self): + """ + Retrieves the hardware product name for the chassis + + Returns: + A string containing the hardware product name for this chassis. + """ + return self._get_eeprom_value(self._TLV_CODE_PRODUCT_NAME) + + @default_return(return_value='Undefined.') + def get_part_number(self): + """ + Retrieves the hardware part number for the chassis + + Returns: + A string containing the hardware part number for this chassis. + """ + return self._get_eeprom_value(self._TLV_CODE_PART_NUMBER) + + @default_return(return_value='Undefined.') + def get_revision(self): + """ + Retrieves the hardware revision of the device + + Returns: + string: Revision value of device + """ + return self._get_eeprom_value(self._TLV_CODE_LABEL_REVISION) + + @default_return({}) + def get_system_eeprom_info(self): + """ + Retrieves the full content of system EEPROM information for the chassis + + Returns: + A dictionary where keys are the type code defined in + OCP ONIE TlvInfo EEPROM format and values are their corresponding + values. + """ + if not self._eeprom_info_dict: + self._eeprom_init() + return self._eeprom_info_dict + + def _get_eeprom_value(self, code): + """Helper function to help get EEPROM data by code + + Args: + code (int): EEPROM TLV code + + Returns: + str: value of EEPROM TLV + """ + eeprom_info_dict = self.get_system_eeprom_info() + return eeprom_info_dict[hex(code)] + + def _eeprom_init_raw(self, tlvs_info): + """Initializes the _eeprom_raw by encoding tlvs_info's values via TlvInfoDecoder.encoder + + Args: + tlvs_info (dict): EEPROM TLV types and values + + Returns: + int: EEPROM CRC + """ + encoded = [self.encoder((k,), tlvs_info[k]) for k in sorted(tlvs_info.keys())] + tlvs = reduce(lambda x,y: x+y, encoded) + + # adding TLV_CODE_CRC_32 [type, len] for checksum calculation + tlvs += bytearray([self._TLV_CODE_CRC_32]) + bytearray([4]) + + # 4 extra bytes for checksum value that is calculated and added later + tlvs_len = len(tlvs) + 4 + + tlvs_len_header = bytearray([(tlvs_len >> 8) & 0xFF]) + bytearray([tlvs_len & 0xFF]) + header = self._TLV_INFO_ID_STRING + bytearray([self._TLV_INFO_VERSION]) + tlvs_len_header + raw = header + tlvs + checksum = self.calculate_checksum(raw) + raw += self.encode_checksum(checksum) + self._eeprom_raw = raw + return checksum + + def _epprom_data_get(self): + data = {} + db_initialized = self._redis_hget('EEPROM_INFO|State', 'Initialized') + if db_initialized == '1': + tlvs = [self._TLV_CODE_PRODUCT_NAME, + self._TLV_CODE_PART_NUMBER, + self._TLV_CODE_SERIAL_NUMBER, + self._TLV_CODE_MAC_BASE, + self._TLV_CODE_LABEL_REVISION] + for code in tlvs: + value = self._redis_hget('EEPROM_INFO|{}'.format(hex(code)), 'Value') + if value: + data[code] = value + else: + data = { + self._TLV_CODE_PRODUCT_NAME: self._vpd.get_product_name(), + self._TLV_CODE_PART_NUMBER: self._vpd.get_part_number(), + self._TLV_CODE_SERIAL_NUMBER: self._vpd.get_serial_number(), + self._TLV_CODE_MAC_BASE: self._fwmngr.get_base_mac(), + self._TLV_CODE_LABEL_REVISION: self._vpd.get_revision(), + } + return data + + def _eeprom_init(self): + """Initializes the _eeprom_raw and _eeprom_info_dict via data retrieved from Vpd and FwManager + + """ + eeprom_data = self._epprom_data_get() + checksum = self._eeprom_init_raw(eeprom_data) + + self._eeprom_info_dict = dict([(hex(k), v) for k,v in eeprom_data.items()]) + self._eeprom_info_dict[hex(self._TLV_CODE_CRC_32)] = checksum + + def read_eeprom(self): + """Overrides the TlvInfoDecoder.read_eeprom so the EPPROM is read from _eeprom_raw instead of a file + + """ + if not self._eeprom_raw: + self._eeprom_init() + return self._eeprom_raw diff --git a/platform/nvidia-bluefield/platform-api/sonic_platform/pcie.py b/platform/nvidia-bluefield/platform-api/sonic_platform/pcie.py new file mode 100644 index 00000000000..f98ffa60eb3 --- /dev/null +++ b/platform/nvidia-bluefield/platform-api/sonic_platform/pcie.py @@ -0,0 +1,25 @@ +# +# Copyright (c) 2024 NVIDIA CORPORATION & AFFILIATES. +# Apache-2.0 +# +# Licensed under the Apache License, Version 2.0 (the "License"); +# you may not use this file except in compliance with the License. +# You may obtain a copy of the License at +# +# http://www.apache.org/licenses/LICENSE-2.0 +# +# Unless required by applicable law or agreed to in writing, software +# distributed under the License is distributed on an "AS IS" BASIS, +# WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied. +# See the License for the specific language governing permissions and +# limitations under the License. +# + +try: + from sonic_platform_base.sonic_pcie.pcie_common import PcieUtil +except ImportError as e: + raise ImportError(str(e) + "- required module not found") + +class Pcie(PcieUtil): + def __init__(self, path): + super().__init__(path) diff --git a/platform/nvidia-bluefield/platform-api/sonic_platform/platform.py b/platform/nvidia-bluefield/platform-api/sonic_platform/platform.py new file mode 100644 index 00000000000..bf38d6dd060 --- /dev/null +++ b/platform/nvidia-bluefield/platform-api/sonic_platform/platform.py @@ -0,0 +1,29 @@ +# +# Copyright (c) 2024 NVIDIA CORPORATION & AFFILIATES. +# Apache-2.0 +# +# Licensed under the Apache License, Version 2.0 (the "License"); +# you may not use this file except in compliance with the License. +# You may obtain a copy of the License at +# +# http://www.apache.org/licenses/LICENSE-2.0 +# +# Unless required by applicable law or agreed to in writing, software +# distributed under the License is distributed on an "AS IS" BASIS, +# WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied. +# See the License for the specific language governing permissions and +# limitations under the License. +# + +try: + from sonic_platform_base.platform_base import PlatformBase + from .chassis import Chassis +except ImportError as e: + raise ImportError(str(e) + "- required module not found") + + +class Platform(PlatformBase): + + def __init__(self): + PlatformBase.__init__(self) + self._chassis = Chassis() diff --git a/platform/nvidia-bluefield/platform-api/sonic_platform/sfp.py b/platform/nvidia-bluefield/platform-api/sonic_platform/sfp.py new file mode 100644 index 00000000000..c0e881db17f --- /dev/null +++ b/platform/nvidia-bluefield/platform-api/sonic_platform/sfp.py @@ -0,0 +1,217 @@ +# +# Copyright (c) 2024 NVIDIA CORPORATION & AFFILIATES. +# Apache-2.0 +# +# Licensed under the Apache License, Version 2.0 (the "License"); +# you may not use this file except in compliance with the License. +# You may obtain a copy of the License at +# +# http://www.apache.org/licenses/LICENSE-2.0 +# +# Unless required by applicable law or agreed to in writing, software +# distributed under the License is distributed on an "AS IS" BASIS, +# WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied. +# See the License for the specific language governing permissions and +# limitations under the License. +# + +try: + import os + import time + import subprocess + import mmap + from sonic_platform_base.sonic_xcvr.sfp_optoe_base import SfpOptoeBase + +except ImportError as err: + raise ImportError(str(err) + "- required module not found") + +SFP_TYPE_LIST = [ + '0x3' # SFP/SFP+/SFP28 and later +] +QSFP_TYPE_LIST = [ + '0xc', # QSFP + '0xd', # QSFP+ or later + '0x11' # QSFP28 or later +] +QSFP_DD_TYPE_LIST = [ + '0x18' # QSFP_DD Type +] + +EEPROM_ETHTOOL_READ_RETRIES = 5 + + +def check_ethtool_link_detected(name): + ethtool_cmd = ["ethtool", name] + + try: + output = subprocess.check_output(ethtool_cmd, + stderr=subprocess.DEVNULL, + universal_newlines=True) + output_lines = output.splitlines() + link_detected_info = next(filter(lambda x: x.strip().startswith('Link detected:'), output_lines), None) + if not link_detected_info: + return False + + link_detected_val = link_detected_info.strip().split(':')[1].strip() + return link_detected_val == 'yes' + + except subprocess.CalledProcessError as e: + return False + + +def read_eeprom_ethtool(name, offset, num_bytes): + eeprom_raw = [] + ethtool_cmd = ["ethtool", "-m", name, "hex", "on", "offset", str(offset), "length", str(num_bytes)] + try: + output = subprocess.check_output(ethtool_cmd, + stderr=subprocess.DEVNULL, + universal_newlines=True) + output_lines = output.splitlines() + first_line_raw = output_lines[0] + if "Offset" in first_line_raw: + for line in output_lines[2:]: + line_split = line.split() + eeprom_raw = eeprom_raw + line_split[1:] + except subprocess.CalledProcessError as e: + return None + eeprom_raw = map(lambda h: int(h, base=16), eeprom_raw) + return bytearray(eeprom_raw) + + +class Sfp(SfpOptoeBase): + + def __init__(self, index, sfp_data): + """ + SFP init + """ + SfpOptoeBase.__init__(self) + self.index = index + self.data = sfp_data + + def get_name(self): + """ + Returns native transceiver type + """ + raise NotImplementedError() + + def read_eeprom(self, offset, num_bytes): + """ + read eeprom specific bytes beginning from a random offset with size as num_bytes + + Args: + offset : + Integer, the offset from which the read transaction will start + num_bytes: + Integer, the number of bytes to be read + + Returns: + bytearray, if raw sequence of bytes are read correctly from the offset of size num_bytes + None, if the read_eeprom fails + """ + if not check_ethtool_link_detected(self.data.name): + return None + + # Temporary workaround to address instability + for _ in range(EEPROM_ETHTOOL_READ_RETRIES): + eeprom = read_eeprom_ethtool(self.data.name, offset, num_bytes) + if eeprom: + return eeprom + return None + + def write_eeprom(self, offset, num_bytes, write_buffer): + """ + write eeprom specific bytes beginning from a random offset with size as num_bytes + and write_buffer as the required bytes + + Args: + offset : + Integer, the offset from which the read transaction will start + num_bytes: + Integer, the number of bytes to be written + write_buffer: + bytearray, raw bytes buffer which is to be written beginning at the offset + + Returns: + a Boolean, true if the write succeeded and false if it did not succeed. + """ + raise NotImplementedError() + + def get_presence(self): + """ + Retrieves the presence of the sfp + + Returns: + True if sfp is present and false if it is absent + """ + eeprom_raw = self.read_eeprom(0, 1) + + return eeprom_raw is not None + + def get_reset_status(self): + """ + Retrieves the reset status of SFP + + Returns: + A Boolean, True if reset enabled, False if disabled + """ + raise NotImplementedError() + + def get_lpmode(self): + """ + Retrieves the lpmode (low power mode) status of this SFP + + Returns: + A Boolean, True if lpmode is enabled, False if disabled + """ + raise NotImplementedError() + + def reset(self): + """ + Reset SFP and return all user module settings to their default rate. + + Returns: + A boolean, True if successful, False if not + """ + raise NotImplementedError() + + def set_lpmode(self, lpmode): + """ + Sets the lpmode (low power mode) of SFP + + Args: + lpmode: A Boolean, True to enable lpmode, False to disable it + Note : lpmode can be overridden by set_power_override + + Returns: + A boolean, True if lpmode is set successfully, False if not + """ + raise NotImplementedError() + + def get_position_in_parent(self): + """ + Retrieves 1-based relative physical position in parent device. + Returns: + integer: The 1-based relative physical position in parent + device or -1 if cannot determine the position + """ + return self.index + + @staticmethod + def is_replaceable(): + """ + Indicate whether this device is replaceable. + Returns: + bool: True if it is replaceable. + """ + return True + + def get_error_description(self): + """ + Retrieves the error descriptions of the SFP module + + Returns: + String that represents the current error descriptions of vendor specific errors + In case there are multiple errors, they should be joined by '|', + like: "Bad EEPROM|Unsupported cable" + """ + raise NotImplementedError() diff --git a/platform/nvidia-bluefield/platform-api/sonic_platform/sfp_event.py b/platform/nvidia-bluefield/platform-api/sonic_platform/sfp_event.py new file mode 100644 index 00000000000..2fe97099151 --- /dev/null +++ b/platform/nvidia-bluefield/platform-api/sonic_platform/sfp_event.py @@ -0,0 +1,70 @@ +# +# Copyright (c) 2024 NVIDIA CORPORATION & AFFILIATES. +# Apache-2.0 +# +# Licensed under the Apache License, Version 2.0 (the "License"); +# you may not use this file except in compliance with the License. +# You may obtain a copy of the License at +# +# http://www.apache.org/licenses/LICENSE-2.0 +# +# Unless required by applicable law or agreed to in writing, software +# distributed under the License is distributed on an "AS IS" BASIS, +# WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied. +# See the License for the specific language governing permissions and +# limitations under the License. +# + +import time + + +POLL_INTERVAL_IN_SEC = 1 + + +class SfpEvent: + ''' Listen to insert/remove sfp events ''' + + def __init__(self, sfp_list): + self._sfp_list = sfp_list + self._present_ports = 0 + + def get_presence_bitmap(self): + bitmap = 0 + for sfp in self._sfp_list: + modpres = sfp.get_presence() + if modpres: + bitmap = bitmap | (1 << sfp.index) + return bitmap + + def get_sfp_event(self, timeout=2000): + port_dict = {} + change_dict = {'sfp': port_dict} + + if timeout < 1000: + cd_ms = 1000 + else: + cd_ms = timeout + + while cd_ms > 0: + bitmap = self.get_presence_bitmap() + changed_ports = self._present_ports ^ bitmap + if changed_ports != 0: + break + time.sleep(POLL_INTERVAL_IN_SEC) + # timeout=0 means wait for event forever + if timeout != 0: + cd_ms = cd_ms - POLL_INTERVAL_IN_SEC * 1000 + + if not changed_ports: + return True, change_dict + + for sfp in self._sfp_list: + if (changed_ports & (1 << sfp.index)): + if (bitmap & (1 << sfp.index)) == 0: + port_dict[sfp.index + 1] = '0' + else: + port_dict[sfp.index + 1] = '1' + + # Update the cache dict + self._present_ports = bitmap + return True, change_dict diff --git a/platform/nvidia-bluefield/platform-api/sonic_platform/thermal.py b/platform/nvidia-bluefield/platform-api/sonic_platform/thermal.py new file mode 100644 index 00000000000..8fdbfd38f0c --- /dev/null +++ b/platform/nvidia-bluefield/platform-api/sonic_platform/thermal.py @@ -0,0 +1,32 @@ +# +# Copyright (c) 2024 NVIDIA CORPORATION & AFFILIATES. +# Apache-2.0 +# +# Licensed under the Apache License, Version 2.0 (the "License"); +# you may not use this file except in compliance with the License. +# You may obtain a copy of the License at +# +# http://www.apache.org/licenses/LICENSE-2.0 +# +# Unless required by applicable law or agreed to in writing, software +# distributed under the License is distributed on an "AS IS" BASIS, +# WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied. +# See the License for the specific language governing permissions and +# limitations under the License. +# +############################################################################# +# Mellanox +# +# Module contains an implementation of SONiC Platform Base API and +# provides the thermals data which are available in the platform +# +############################################################################# + +try: + from .thermal_bf3 import initialize_chassis_thermals as bf3_init +except ImportError as e: + raise ImportError(str(e) + "- required module not found") + + +def initialize_chassis_thermals(): + return bf3_init() diff --git a/platform/nvidia-bluefield/platform-api/sonic_platform/thermal_bf3.py b/platform/nvidia-bluefield/platform-api/sonic_platform/thermal_bf3.py new file mode 100644 index 00000000000..c769a5e373f --- /dev/null +++ b/platform/nvidia-bluefield/platform-api/sonic_platform/thermal_bf3.py @@ -0,0 +1,146 @@ +# +# Copyright (c) 2024 NVIDIA CORPORATION & AFFILIATES. +# Apache-2.0 +# +# Licensed under the Apache License, Version 2.0 (the "License"); +# you may not use this file except in compliance with the License. +# You may obtain a copy of the License at +# +# http://www.apache.org/licenses/LICENSE-2.0 +# +# Unless required by applicable law or agreed to in writing, software +# distributed under the License is distributed on an "AS IS" BASIS, +# WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied. +# See the License for the specific language governing permissions and +# limitations under the License. +# + +try: + from sonic_platform_base.thermal_base import ThermalBase + from sonic_py_common.logger import Logger + import os +except ImportError as e: + raise ImportError (str(e) + "- required module not found") + +# Global logger class instance +logger = Logger() + +MLXBF_BASE_PATH = '/sys/kernel/debug/mlxbf-ptm/monitors/status' + +SENSORS = [ + {'name': 'CPU', 'mlxbf_sensor_name': 'core_temp', 'ht': 95, 'cht': 100}, + {'name': 'DDR', 'mlxbf_sensor_name': 'ddr_temp', 'ht': 95, 'cht': 100}, + {'name': 'SFP0', 'iface': 'Ethernet0', 'hwmon_path': None}, + {'name': 'SFP1', 'iface': 'Ethernet4', 'hwmon_path': None}, +] + +def set_hwmon_path(sensor): + base = f'/sys/class/net/{sensor["iface"]}/device/hwmon' + dirs = os.listdir(base) + if len(dirs) != 1 or not dirs[0].startswith('hwmon'): + logger.log_error(f'Failed to find hwmon path for {sensor["iface"]}') + return + sensor['hwmon_path'] = f'{base}/{dirs[0]}' + +def initialize_chassis_thermals(): + thermal_list = [] + for s in SENSORS: + if 'hwmon_path' in s: + set_hwmon_path(s) + thermal_list.append(Thermal(**s)) + return thermal_list + +def read_fs(path, name): + try: + with open(path) as f: + return float(f.readline().strip()) + except Exception as e: + logger.log_error(f'Failed to read {name} - {str(e)}') + return 'N/A' + +def read_temp_mlxbf(sensor_name): + path = f'{MLXBF_BASE_PATH}/{sensor_name}' + return read_fs(path, sensor_name) + +def read_temp_hwmon(hwmon_path, sensor): + if not hwmon_path: + return 'N/A' + path = f'{hwmon_path}/{sensor}' + v = read_fs(path, sensor) + if v == 'N/A': + return v + return v / 1000 + +class Thermal(ThermalBase): + def __init__(self, name, mlxbf_sensor_name=None, iface=None, hwmon_path=None, ht='N/A', cht='N/A'): + super(Thermal, self).__init__() + self.name = name + self.mlxbf_sensor_name = mlxbf_sensor_name + self.hwmon_path = hwmon_path + self.ht = ht + self.cht = cht + + def get_name(self): + """ + Retrieves the name of the device + + Returns: + string: The name of the device + """ + return self.name + + def get_temperature(self): + """ + Retrieves current temperature reading from thermal + + Returns: + A float number of current temperature in Celsius up to nearest thousandth + of one degree Celsius, e.g. 30.125 + """ + if self.mlxbf_sensor_name: + return read_temp_mlxbf(self.mlxbf_sensor_name) + else: + return read_temp_hwmon(self.hwmon_path, 'temp1_input') + + def get_high_threshold(self): + """ + Retrieves the high threshold temperature of thermal + + Returns: + A float number, the high threshold temperature of thermal in Celsius + up to nearest thousandth of one degree Celsius, e.g. 30.125 + """ + return self.ht + + def get_high_critical_threshold(self): + """ + Retrieves the high critical threshold temperature of thermal + + Returns: + A float number, the high critical threshold temperature of thermal in Celsius + up to nearest thousandth of one degree Celsius, e.g. 30.125 + """ + if self.hwmon_path: + return read_temp_hwmon(self.hwmon_path, 'temp1_crit') + else: + return self.cht + + def get_low_threshold(self): + """ + Retrieves the low threshold temperature of thermal + + Returns: + A float number, the low threshold temperature of thermal in Celsius + up to nearest thousandth of one degree Celsius, e.g. 30.125 + """ + return 'N/A' + + def get_low_critical_threshold(self): + """ + Retrieves the low critical threshold temperature of thermal + + Returns: + A float number, the low critical threshold temperature of thermal in Celsius + up to nearest thousandth of one degree Celsius, e.g. 30.125 + """ + return 'N/A' diff --git a/platform/nvidia-bluefield/platform-api/sonic_platform/throttling_checks/__init__.py b/platform/nvidia-bluefield/platform-api/sonic_platform/throttling_checks/__init__.py new file mode 100644 index 00000000000..3e5937ef91b --- /dev/null +++ b/platform/nvidia-bluefield/platform-api/sonic_platform/throttling_checks/__init__.py @@ -0,0 +1 @@ +__all__ = ['cpu_check', 'ddr_check'] diff --git a/platform/nvidia-bluefield/platform-api/sonic_platform/throttling_checks/cpu_check.py b/platform/nvidia-bluefield/platform-api/sonic_platform/throttling_checks/cpu_check.py new file mode 100644 index 00000000000..279b4e7e738 --- /dev/null +++ b/platform/nvidia-bluefield/platform-api/sonic_platform/throttling_checks/cpu_check.py @@ -0,0 +1,112 @@ +# +# Copyright (c) 2024 NVIDIA CORPORATION & AFFILIATES. +# Apache-2.0 +# +# Licensed under the Apache License, Version 2.0 (the "License"); +# you may not use this file except in compliance with the License. +# You may obtain a copy of the License at +# +# http://www.apache.org/licenses/LICENSE-2.0 +# +# Unless required by applicable law or agreed to in writing, software +# distributed under the License is distributed on an "AS IS" BASIS, +# WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied. +# See the License for the specific language governing permissions and +# limitations under the License. +# + +import os +from sonic_py_common.logger import Logger +from pathlib import Path +from enum import Enum, auto +from .utils import MLXBF_SENSOR_PATH, LAST_VALUES_STORAGE_PATH, read_sensor + +SYSLOG_IDENTIFIER = os.path.basename(__file__) +logger = Logger(SYSLOG_IDENTIFIER) + + +class CheckResult(Enum): + OK = auto() + THROTTLED_NOW = auto() + THROTTLED_BETWEEN_CHECKS = auto() + RECOVERED = auto() + + +class CPUThrottlingChecker: + fs_read_max_attempts = 3 + + def __init__(self, sensor_path = MLXBF_SENSOR_PATH, storage_path = LAST_VALUES_STORAGE_PATH): + self._sensor_path = sensor_path + self._storage_path = storage_path + + def _read_count_and_state_fs(self, path, ttype, ok_if_not_found = False): + count_path = f'{path}/{ttype}_throttling_event_count' + state_path = f'{path}/{ttype}_throttling_state' + + # read count/state/count to avoid race condition + for _ in range(CPUThrottlingChecker.fs_read_max_attempts): + count = read_sensor(count_path, ok_if_not_found) + state = read_sensor(state_path, ok_if_not_found) + count_again = read_sensor(count_path, ok_if_not_found) + if count == count_again: + return count, state + + raise Exception(f'Failed to read {ttype} state - inconsistent state during read attempt') + + def _read_count_and_state(self, ttype): + return self._read_count_and_state_fs(self._sensor_path, ttype) + + def _read_last_count_and_state(self, ttype): + return self._read_count_and_state_fs(self._storage_path, ttype, ok_if_not_found=True) + + def _save_count_and_state(self, ttype, count, state): + count_path = f'{self._storage_path}/{ttype}_throttling_event_count' + state_path = f'{self._storage_path}/{ttype}_throttling_state' + + Path(self._storage_path).mkdir(exist_ok=True) + + with open(count_path, 'w+') as f: + f.write(str(count)) + + with open(state_path, 'w+') as f: + f.write(str(state)) + + def _check_throttling_type(self, ttype) -> CheckResult: + count, state = self._read_count_and_state(ttype) + last_count, last_state = self._read_last_count_and_state(ttype) + self._save_count_and_state(ttype, count, state) + + if state > 1: + return CheckResult.THROTTLED_NOW + + # no previous state saved (first run) + if last_state is None: + return CheckResult.OK + + if last_state == 1: + if count != last_count: + logger.log_warning(f'CPU was {ttype} throttled') + return CheckResult.THROTTLED_BETWEEN_CHECKS + else: + logger.log_warning(f'CPU has recovered from {ttype} throttling') + return CheckResult.RECOVERED + + def check(self): + status = 'OK' + try: + thermal_check = self._check_throttling_type('thermal') + power_check = self._check_throttling_type('power') + if thermal_check == CheckResult.THROTTLED_NOW or power_check == CheckResult.THROTTLED_NOW: + status = 'Throttled' + except Exception as e: + logger.log_error(f'Failed to check CPU throttling: {e}') + return f'Throttling\nCPU:{status}' + + +def main(): + checker = CPUThrottlingChecker() + print(checker.check()) + + +if __name__ == '__main__': + main() diff --git a/platform/nvidia-bluefield/platform-api/sonic_platform/throttling_checks/ddr_check.py b/platform/nvidia-bluefield/platform-api/sonic_platform/throttling_checks/ddr_check.py new file mode 100644 index 00000000000..c3dd65c0ef6 --- /dev/null +++ b/platform/nvidia-bluefield/platform-api/sonic_platform/throttling_checks/ddr_check.py @@ -0,0 +1,49 @@ +# +# Copyright (c) 2024 NVIDIA CORPORATION & AFFILIATES. +# Apache-2.0 +# +# Licensed under the Apache License, Version 2.0 (the "License"); +# you may not use this file except in compliance with the License. +# You may obtain a copy of the License at +# +# http://www.apache.org/licenses/LICENSE-2.0 +# +# Unless required by applicable law or agreed to in writing, software +# distributed under the License is distributed on an "AS IS" BASIS, +# WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied. +# See the License for the specific language governing permissions and +# limitations under the License. +# + +import os +from sonic_py_common.logger import Logger +from .utils import MLXBF_SENSOR_PATH, DDR_THROTTLING_THRESHOLD, read_sensor + +SYSLOG_IDENTIFIER = os.path.basename(__file__) +logger = Logger(SYSLOG_IDENTIFIER) + + +class DDRThrottlingChecker: + + def __init__(self, sensor_path = MLXBF_SENSOR_PATH): + self._sensor_path = sensor_path + + def check(self): + status = 'OK' + try: + temp = read_sensor(f'{self._sensor_path}/ddr_temp') + if temp >= DDR_THROTTLING_THRESHOLD: + status = 'Throttled' + except Exception as e: + logger.log_error(f'Failed to check DDR throttling: {e}') + return f'Throttling\nDDR:{status}' + + +def main(): + checker = DDRThrottlingChecker() + print(checker.check()) + + +if __name__ == '__main__': + main() + diff --git a/platform/nvidia-bluefield/platform-api/sonic_platform/throttling_checks/utils.py b/platform/nvidia-bluefield/platform-api/sonic_platform/throttling_checks/utils.py new file mode 100644 index 00000000000..05025d61092 --- /dev/null +++ b/platform/nvidia-bluefield/platform-api/sonic_platform/throttling_checks/utils.py @@ -0,0 +1,29 @@ +# +# Copyright (c) 2024 NVIDIA CORPORATION & AFFILIATES. +# Apache-2.0 +# +# Licensed under the Apache License, Version 2.0 (the "License"); +# you may not use this file except in compliance with the License. +# You may obtain a copy of the License at +# +# http://www.apache.org/licenses/LICENSE-2.0 +# +# Unless required by applicable law or agreed to in writing, software +# distributed under the License is distributed on an "AS IS" BASIS, +# WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied. +# See the License for the specific language governing permissions and +# limitations under the License. +# + +MLXBF_SENSOR_PATH = '/sys/kernel/debug/mlxbf-ptm/monitors/status' +LAST_VALUES_STORAGE_PATH = '/var/run/mlxbf-last-read/' +DDR_THROTTLING_THRESHOLD = 95 + +def read_sensor(path, ok_if_not_found = False): + try: + with open(path) as f: + return int(f.readline().strip()) + except OSError: + if ok_if_not_found: + return None + raise Exception(f'Could not read the {path}') diff --git a/platform/nvidia-bluefield/platform-api/sonic_platform/utils.py b/platform/nvidia-bluefield/platform-api/sonic_platform/utils.py new file mode 100644 index 00000000000..d6bf6809f6d --- /dev/null +++ b/platform/nvidia-bluefield/platform-api/sonic_platform/utils.py @@ -0,0 +1,73 @@ +# +# Copyright (c) 2024 NVIDIA CORPORATION & AFFILIATES. +# Apache-2.0 +# +# Licensed under the Apache License, Version 2.0 (the "License"); +# you may not use this file except in compliance with the License. +# You may obtain a copy of the License at +# +# http://www.apache.org/licenses/LICENSE-2.0 +# +# Unless required by applicable law or agreed to in writing, software +# distributed under the License is distributed on an "AS IS" BASIS, +# WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied. +# See the License for the specific language governing permissions and +# limitations under the License. +# +import functools +import subprocess +from sonic_py_common.logger import Logger + +logger = Logger() + + +def read_only_cache(): + """Decorator to cache return value for a method/function once. + This decorator should be used for method/function when: + 1. Executing the method/function takes time. e.g. reading sysfs. + 2. The return value of this method/function never changes. + """ + def decorator(method): + method.return_value = None + + @functools.wraps(method) + def _impl(*args, **kwargs): + if not method.return_value: + method.return_value = method(*args, **kwargs) + return method.return_value + return _impl + return decorator + + +@read_only_cache() +def is_host(): + """ + Test whether current process is running on the host or an docker + return True for host and False for docker + """ + try: + proc = subprocess.Popen("docker --version 2>/dev/null", + stdout=subprocess.PIPE, + shell=True, + stderr=subprocess.STDOUT, + universal_newlines=True) + stdout = proc.communicate()[0] + proc.wait() + result = stdout.rstrip('\n') + return result != '' + except OSError as e: + return False + + +def default_return(return_value, log_func=logger.log_debug): + def wrapper(method): + @functools.wraps(method) + def _impl(*args, **kwargs): + try: + return method(*args, **kwargs) + except Exception as e: + if log_func: + log_func('Faield to execute method {} - {}'.format(method.__name__, repr(e))) + return return_value + return _impl + return wrapper diff --git a/platform/nvidia-bluefield/platform-api/sonic_platform/watchdog.py b/platform/nvidia-bluefield/platform-api/sonic_platform/watchdog.py new file mode 100644 index 00000000000..ca8b9574571 --- /dev/null +++ b/platform/nvidia-bluefield/platform-api/sonic_platform/watchdog.py @@ -0,0 +1,71 @@ +# +# Copyright (c) 2024 NVIDIA CORPORATION & AFFILIATES. +# Apache-2.0 +# +# Licensed under the Apache License, Version 2.0 (the "License"); +# you may not use this file except in compliance with the License. +# You may obtain a copy of the License at +# +# http://www.apache.org/licenses/LICENSE-2.0 +# +# Unless required by applicable law or agreed to in writing, software +# distributed under the License is distributed on an "AS IS" BASIS, +# WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied. +# See the License for the specific language governing permissions and +# limitations under the License. +# + + +try: + from sonic_platform_base.watchdog_base import WatchdogBase + from sonic_py_common.logger import Logger +except ImportError as e: + raise ImportError(str(e) + "- required module not found") + + +class Watchdog(WatchdogBase): + """Placeholder for watchdog implementation""" + + def arm(self, seconds): + """ + Arm the hardware watchdog with a timeout of seconds. + If the watchdog is currently armed, calling this function will + simply reset the timer to the provided value. If the underlying + hardware does not support the value provided in , this + method should arm the watchdog with the *next greater* available + value. + + Returns: + An integer specifying the *actual* number of seconds the watchdog + was armed with. On failure returns -1. + """ + return -1 + + def disarm(self): + """ + Disarm the hardware watchdog + + Returns: + A boolean, True if watchdog is disarmed successfully, False if not + """ + return False + + def is_armed(self): + """ + Retrieves the armed state of the hardware watchdog. + + Returns: + A boolean, True if watchdog is armed, False if not + """ + return False + + def get_remaining_time(self): + """ + If the watchdog is armed, retrieve the number of seconds remaining on + the watchdog timer + + Returns: + An integer specifying the number of seconds remaining on thei + watchdog timer. If the watchdog is not armed, returns -1. + """ + return -1 diff --git a/platform/nvidia-bluefield/platform-api/tests/__init__.py b/platform/nvidia-bluefield/platform-api/tests/__init__.py new file mode 100644 index 00000000000..b373cff146b --- /dev/null +++ b/platform/nvidia-bluefield/platform-api/tests/__init__.py @@ -0,0 +1,16 @@ +# +# Copyright (c) 2024 NVIDIA CORPORATION & AFFILIATES. +# Apache-2.0 +# +# Licensed under the Apache License, Version 2.0 (the "License"); +# you may not use this file except in compliance with the License. +# You may obtain a copy of the License at +# +# http://www.apache.org/licenses/LICENSE-2.0 +# +# Unless required by applicable law or agreed to in writing, software +# distributed under the License is distributed on an "AS IS" BASIS, +# WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied. +# See the License for the specific language governing permissions and +# limitations under the License. +# diff --git a/platform/nvidia-bluefield/platform-api/tests/test_chassis.py b/platform/nvidia-bluefield/platform-api/tests/test_chassis.py new file mode 100644 index 00000000000..e4a8826c449 --- /dev/null +++ b/platform/nvidia-bluefield/platform-api/tests/test_chassis.py @@ -0,0 +1,85 @@ +# +# Copyright (c) 2024 NVIDIA CORPORATION & AFFILIATES. +# Apache-2.0 +# +# Licensed under the Apache License, Version 2.0 (the "License"); +# you may not use this file except in compliance with the License. +# You may obtain a copy of the License at +# +# http://www.apache.org/licenses/LICENSE-2.0 +# +# Unless required by applicable law or agreed to in writing, software +# distributed under the License is distributed on an "AS IS" BASIS, +# WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied. +# See the License for the specific language governing permissions and +# limitations under the License. +# + +import os +import sys + +from unittest.mock import patch +from unittest.mock import mock_open +from unittest.mock import MagicMock + +test_path = os.path.dirname(os.path.abspath(__file__)) +modules_path = os.path.dirname(test_path) +sys.path.insert(0, modules_path) + +from sonic_platform.chassis import Chassis +from sonic_platform.device_data import DeviceDataManager +from .utils import platform_sample + +@patch('sonic_py_common.device_info.get_platform', MagicMock(return_value="")) +@patch('sonic_py_common.device_info.get_path_to_platform_dir', MagicMock(return_value="")) +@patch('builtins.open', new_callable=mock_open, read_data=platform_sample) +@patch('os.path.isfile', MagicMock(return_value=True)) +class TestChassis: + """ + Test class to test chassis.py. The test cases covers: + - SFP related API + """ + + def test_psu(self, *args): + chassis = Chassis() + + assert chassis.get_num_psus() == 0 + assert chassis.get_all_psus() == [] + + def test_fan(self, *args): + chassis = Chassis() + + assert chassis.get_num_fans() == 0 + assert chassis.get_all_fans() == [] + assert chassis.get_num_fan_drawers() == 0 + assert chassis.get_all_fan_drawers() == [] + + def test_sfp(self, *args): + # Test get_num_sfps, it should not create any SFP objects + DeviceDataManager.get_sfp_count = MagicMock(return_value=2) + + chassis = Chassis() + assert chassis.get_num_sfps() == 2 + assert len(chassis.get_all_sfps()) == 2 + + # Index out of bound, return None + sfp = chassis.get_sfp(4) + assert sfp is None + + # Get one SFP, other SFP list should be initialized to None + sfp = chassis.get_sfp(1) + assert sfp is not None + + # Get the SFP again, no new SFP created + sfp1 = chassis.get_sfp(1) + assert id(sfp) == id(sfp1) + + # Get another SFP, sfp_initialized_count increase + sfp2 = chassis.get_sfp(2) + assert sfp2 is not None + + # Get all SFPs, but there are SFP already created, only None SFP created + sfp_list = chassis.get_all_sfps() + assert len(sfp_list) == 2 + assert id(sfp1) == id(sfp_list[0]) + assert id(sfp2) == id(sfp_list[1]) diff --git a/platform/nvidia-bluefield/platform-api/tests/test_eeprom.py b/platform/nvidia-bluefield/platform-api/tests/test_eeprom.py new file mode 100644 index 00000000000..d4ab81fcef5 --- /dev/null +++ b/platform/nvidia-bluefield/platform-api/tests/test_eeprom.py @@ -0,0 +1,171 @@ +# +# Copyright (c) 2024 NVIDIA CORPORATION & AFFILIATES. +# Apache-2.0 +# +# Licensed under the Apache License, Version 2.0 (the "License"); +# you may not use this file except in compliance with the License. +# You may obtain a copy of the License at +# +# http://www.apache.org/licenses/LICENSE-2.0 +# +# Unless required by applicable law or agreed to in writing, software +# distributed under the License is distributed on an "AS IS" BASIS, +# WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied. +# See the License for the specific language governing permissions and +# limitations under the License. +# + +import os +import sys + +from unittest.mock import patch +from unittest.mock import mock_open +from unittest.mock import MagicMock + +test_path = os.path.dirname(os.path.abspath(__file__)) +modules_path = os.path.dirname(test_path) +sys.path.insert(0, modules_path) + +from sonic_platform.chassis import Chassis +from sonic_platform.eeprom import Eeprom + +from .utils import platform_sample + + +vpd_sample = """ + + VPD-KEYWORD DESCRIPTION VALUE + ----------- ----------- ----- +Read Only Section: + + PN Part Number MBF2H536C-CESOT + EC Revision A5 + V2 N/A MBF2H536C-CESOT + SN Serial Number MT2152X03653 + V3 N/A 144d28a86368ec11800008c0ebe14b94 + VA N/A MLX:MN=MLNX:CSKU=V2:UUID=V3:PCI=V0:MODL=BF2H536C + V0 Misc Info PCIeGen4 x16 + RV Checksum Complement 0x7a + IDTAG Board Id BlueField-2 DPU 100GbE Dual-Port QSFP56, integrated BMC, Secure Boot Enabled, Crypto Disabled, 32GB on-board DDR, 1GbE OOB management, FHHL +""" + + +fwinfo_sample = """ +Querying Mellanox devices firmware ... + +Device #1: +---------- + + Device Type: BlueField2 + Part Number: MBF2H536C-CESO_Ax + Description: BlueField-2 P-Series DPU 100GbE Dual-Port QSFP56; integrated BMC; PCIe Gen4 x16; Secure Boot Enabled; Crypto Disabled; 32GB on-board DDR; 1GbE OOB management; FHHL + PSID: MT_0000000767 + PCI Device Name: /dev/mst/mt41686_pciconf0 + Base GUID: 08c0eb0300e14b94 + Base MAC: 08c0ebe14b94 + Versions: Current Available + FW 24.99.0932 N/A + + Status: No matching image found + +""" + + +eeprom_info_dict = { + hex(Eeprom._TLV_CODE_SERIAL_NUMBER): 'MT2152X03653', + hex(Eeprom._TLV_CODE_PRODUCT_NAME): 'BlueField-2 DPU 100GbE Dual-Port QSFP56, integrated BMC, Secure Boot Enabled, Crypto Disabled, 32GB on-board DDR, 1GbE OOB management, FHHL', + hex(Eeprom._TLV_CODE_PART_NUMBER): 'MBF2H536C-CESOT', + hex(Eeprom._TLV_CODE_LABEL_REVISION): 'A5', + hex(Eeprom._TLV_CODE_MAC_BASE): '08:c0:eb:e1:4b:94', + hex(Eeprom._TLV_CODE_CRC_32): '0x64761f84' + } + +eeprom_redis_data = dict([((f'EEPROM_INFO|{k}', 'Value'), v) for k,v in eeprom_info_dict.items()]) +eeprom_redis_data[('EEPROM_INFO|State', 'Initialized')] = '1' + +redis_empty = {('EEPROM_INFO|State', 'Initialized'): '0'} + +mock_redis_uninitialized = MagicMock(side_effect = lambda k,v : redis_empty.get((k,v))) +mock_redis_initialized = MagicMock(side_effect = lambda k,v : eeprom_redis_data.get((k,v))) + + +@patch('sonic_py_common.device_info.get_platform', MagicMock(return_value="")) +@patch('sonic_py_common.device_info.get_path_to_platform_dir', MagicMock(return_value="")) +@patch('builtins.open', new_callable=mock_open, read_data=platform_sample) +@patch('os.path.isfile', MagicMock(return_value=True)) +class TestEeprom: + @patch('sonic_platform.eeprom.FwManager._read_fw_info_raw', MagicMock(return_value=fwinfo_sample.split('\n'))) + @patch('sonic_platform.eeprom.Vpd._read_raw', MagicMock(return_value=vpd_sample.split('\n'))) + def test_read_vdp_fw_raw(self, *args): + eeprom = Eeprom() + eeprom._redis_hget = mock_redis_uninitialized + assert eeprom.get_serial_number() == 'MT2152X03653' + assert eeprom.get_product_name() == 'BlueField-2 DPU 100GbE Dual-Port QSFP56, integrated BMC, Secure Boot Enabled, Crypto Disabled, 32GB on-board DDR, 1GbE OOB management, FHHL' + assert eeprom.get_part_number() == 'MBF2H536C-CESOT' + assert eeprom.get_revision() == 'A5' + assert eeprom.get_base_mac() == '08:c0:eb:e1:4b:94' + + chassis = Chassis() + chassis._eeprom = eeprom + assert chassis.get_serial() == 'MT2152X03653' + assert chassis.get_name() == 'BlueField-2 DPU 100GbE Dual-Port QSFP56, integrated BMC, Secure Boot Enabled, Crypto Disabled, 32GB on-board DDR, 1GbE OOB management, FHHL' + assert chassis.get_model() == 'MBF2H536C-CESOT' + assert chassis.get_revision() == 'A5' + assert chassis.get_base_mac() == '08:c0:eb:e1:4b:94' + + @patch('sonic_platform.eeprom.Eeprom.get_system_eeprom_info', MagicMock(return_value=eeprom_info_dict)) + def test_get_system_eeprom_info(self, *args): + chassis = Chassis() + assert chassis.get_serial() == 'MT2152X03653' + assert chassis.get_name() == 'BlueField-2 DPU 100GbE Dual-Port QSFP56, integrated BMC, Secure Boot Enabled, Crypto Disabled, 32GB on-board DDR, 1GbE OOB management, FHHL' + assert chassis.get_model() == 'MBF2H536C-CESOT' + assert chassis.get_revision() == 'A5' + assert chassis.get_base_mac() == '08:c0:eb:e1:4b:94' + assert chassis.get_system_eeprom_info() == eeprom_info_dict + + def test_get_system_eeprom_info_from_db(self, *args): + eeprom = Eeprom() + eeprom._redis_hget = mock_redis_initialized + assert eeprom.get_serial_number() == "MT2152X03653" + assert eeprom.get_product_name() == "BlueField-2 DPU 100GbE Dual-Port QSFP56, integrated BMC, Secure Boot Enabled, Crypto Disabled, 32GB on-board DDR, 1GbE OOB management, FHHL" + assert eeprom.get_part_number() == "MBF2H536C-CESOT" + assert eeprom.get_revision() == "A5" + assert eeprom.get_base_mac() == '08:c0:eb:e1:4b:94' + + + @patch('sonic_platform.eeprom.FwManager._read_fw_info_raw', MagicMock(return_value=fwinfo_sample.split('\n'))) + @patch('sonic_platform.eeprom.Vpd._read_raw', MagicMock(return_value=vpd_sample.split('\n'))) + def test_read_eeprom(self, *args): + types = [ + Eeprom._TLV_CODE_MAC_BASE, + Eeprom._TLV_CODE_SERIAL_NUMBER, + Eeprom._TLV_CODE_PRODUCT_NAME, + Eeprom._TLV_CODE_PART_NUMBER, + Eeprom._TLV_CODE_LABEL_REVISION, + Eeprom._TLV_CODE_LABEL_REVISION, + Eeprom._TLV_CODE_CRC_32 + ] + eeprom = Eeprom() + eeprom._redis_hget = mock_redis_uninitialized + + eeprom_data = eeprom.read_eeprom() + for t in types: + assert hex(t) in eeprom.get_system_eeprom_info() + exists, _ = eeprom.get_tlv_field(eeprom_data, t) + assert exists + + @patch('sonic_platform.eeprom.FwManager._read_fw_info_raw', MagicMock(return_value=fwinfo_sample.split('\n'))) + @patch('sonic_platform.eeprom.Vpd._read_raw', MagicMock(return_value=vpd_sample.split('\n'))) + def test_read_eeprom_crc(self, *args): + eeprom = Eeprom() + eeprom._redis_hget = mock_redis_uninitialized + + eeprom_data = eeprom.read_eeprom() + exists, crc = eeprom.get_tlv_field(eeprom_data, Eeprom._TLV_CODE_CRC_32) + + eeprom = Eeprom() + eeprom._redis_hget = mock_redis_initialized + eeprom_data = eeprom.read_eeprom() + exists, crc_redis = eeprom.get_tlv_field(eeprom_data, Eeprom._TLV_CODE_CRC_32) + assert exists + assert crc_redis == crc diff --git a/platform/nvidia-bluefield/platform-api/tests/test_sfp.py b/platform/nvidia-bluefield/platform-api/tests/test_sfp.py new file mode 100644 index 00000000000..d019911abb0 --- /dev/null +++ b/platform/nvidia-bluefield/platform-api/tests/test_sfp.py @@ -0,0 +1,55 @@ +# +# Copyright (c) 2024 NVIDIA CORPORATION & AFFILIATES. +# Apache-2.0 +# +# Licensed under the Apache License, Version 2.0 (the "License"); +# you may not use this file except in compliance with the License. +# You may obtain a copy of the License at +# +# http://www.apache.org/licenses/LICENSE-2.0 +# +# Unless required by applicable law or agreed to in writing, software +# distributed under the License is distributed on an "AS IS" BASIS, +# WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied. +# See the License for the specific language governing permissions and +# limitations under the License. +# +import os +import sys + +from unittest.mock import patch +from unittest.mock import mock_open +from unittest.mock import MagicMock + +test_path = os.path.dirname(os.path.abspath(__file__)) +modules_path = os.path.dirname(test_path) +sys.path.insert(0, modules_path) + +from sonic_platform.sfp import Sfp +from sonic_platform.chassis import Chassis + +from .utils import platform_sample + +@patch('sonic_py_common.device_info.get_platform', MagicMock(return_value="")) +@patch('sonic_py_common.device_info.get_path_to_platform_dir', MagicMock(return_value="")) +@patch('builtins.open', new_callable=mock_open, read_data=platform_sample) +@patch('os.path.isfile', MagicMock(return_value=True)) +class TestSfp: + + @patch('sonic_platform.sfp.Sfp.read_eeprom', MagicMock(return_value=bytearray([0x11]))) + @patch('sonic_platform.chassis.Chassis.get_num_sfps', MagicMock(return_value=2)) + def test_get_presence(self, *args): + chassis = Chassis() + + sfp = chassis.get_sfp(1) + + assert sfp.get_presence() == True + + @patch('sonic_platform.sfp.check_ethtool_link_detected', MagicMock(return_value=False)) + @patch('sonic_platform.chassis.Chassis.get_num_sfps', MagicMock(return_value=2)) + def test_sfp_unpluged(self, *args): + chassis = Chassis() + + sfp = chassis.get_sfp(1) + + assert sfp.get_presence() == False diff --git a/platform/nvidia-bluefield/platform-api/tests/test_sfp_event.py b/platform/nvidia-bluefield/platform-api/tests/test_sfp_event.py new file mode 100644 index 00000000000..ddec52bdbf9 --- /dev/null +++ b/platform/nvidia-bluefield/platform-api/tests/test_sfp_event.py @@ -0,0 +1,109 @@ +# +# Copyright (c) 2024 NVIDIA CORPORATION & AFFILIATES. +# Apache-2.0 +# +# Licensed under the Apache License, Version 2.0 (the "License"); +# you may not use this file except in compliance with the License. +# You may obtain a copy of the License at +# +# http://www.apache.org/licenses/LICENSE-2.0 +# +# Unless required by applicable law or agreed to in writing, software +# distributed under the License is distributed on an "AS IS" BASIS, +# WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied. +# See the License for the specific language governing permissions and +# limitations under the License. +# + +import os +import sys + +from unittest.mock import patch +from unittest.mock import mock_open +from unittest.mock import MagicMock + +test_path = os.path.dirname(os.path.abspath(__file__)) +modules_path = os.path.dirname(test_path) +sys.path.insert(0, modules_path) + +from sonic_platform.sfp import Sfp +from sonic_platform.chassis import Chassis + +from .utils import platform_sample + +@patch('sonic_py_common.device_info.get_platform', MagicMock(return_value="")) +@patch('sonic_py_common.device_info.get_path_to_platform_dir', MagicMock(return_value="")) +@patch('builtins.open', new_callable=mock_open, read_data=platform_sample) +@patch('os.path.isfile', MagicMock(return_value=True)) +@patch('sonic_platform.chassis.Chassis.get_num_sfps', MagicMock(return_value=2)) +class TestSfpEvent: + + def test_sfp_event_full_flow(self, *args): + chassis = Chassis() + + # Verify that no events are generated if SFPs are not present + with patch('sonic_platform.sfp.Sfp.read_eeprom', MagicMock(return_value=None)) as p: + rc, event = chassis.get_change_event(1000) + + assert rc == True + assert 'sfp' in event + assert event['sfp'] == {} + + # Verify that events for both ports are generated + with patch('sonic_platform.sfp.Sfp.read_eeprom', MagicMock(return_value=bytearray([0x11]))) as p: + rc, event = chassis.get_change_event(1000) + + assert rc == True + assert 'sfp' in event + assert event['sfp'] == {1: '1', 2: '1'} + + # Verify that events are not generated if port presence didn't change + with patch('sonic_platform.sfp.Sfp.read_eeprom', MagicMock(return_value=bytearray([0x11]))) as p: + rc, event = chassis.get_change_event(1000) + + assert rc == True + assert 'sfp' in event + assert event['sfp'] == {} + + # Verify that events are generated for both ports when SFPs are removed + with patch('sonic_platform.sfp.Sfp.read_eeprom', MagicMock(return_value=None)) as p: + rc, event = chassis.get_change_event(1000) + + assert rc == True + assert 'sfp' in event + assert event['sfp'] == {1: '0', 2: '0'} + + def test_sfp_event(self, *args): + chassis = Chassis() + + # Verify that no events are generated if SFPs are not present + with patch('sonic_platform.sfp_event.SfpEvent.get_presence_bitmap', MagicMock(return_value=0)) as p: + rc, event = chassis.get_change_event(1000) + + assert rc == True + assert 'sfp' in event + assert event['sfp'] == {} + + # Insert SFP for port 1. Verify that event for only port 1 is generated + with patch('sonic_platform.sfp_event.SfpEvent.get_presence_bitmap', MagicMock(return_value=0x1)) as p: + rc, event = chassis.get_change_event(1000) + + assert rc == True + assert 'sfp' in event + assert event['sfp'] == {1: '1'} + + # Insert SFP for port 2, remove SFP for port 1. Verify that correct events are generated + with patch('sonic_platform.sfp_event.SfpEvent.get_presence_bitmap', MagicMock(return_value=0x2)) as p: + rc, event = chassis.get_change_event(1000) + + assert rc == True + assert 'sfp' in event + assert event['sfp'] == {1: '0', 2: '1'} + + # Remove SFP for port 2. Verify that event only for port + with patch('sonic_platform.sfp_event.SfpEvent.get_presence_bitmap', MagicMock(return_value=0x0)) as p: + rc, event = chassis.get_change_event(1000) + + assert rc == True + assert 'sfp' in event + assert event['sfp'] == {2: '0'} diff --git a/platform/nvidia-bluefield/platform-api/tests/test_thermal_bf3.py b/platform/nvidia-bluefield/platform-api/tests/test_thermal_bf3.py new file mode 100644 index 00000000000..1ceac45d872 --- /dev/null +++ b/platform/nvidia-bluefield/platform-api/tests/test_thermal_bf3.py @@ -0,0 +1,91 @@ +# +# Copyright (c) 2024 NVIDIA CORPORATION & AFFILIATES. +# Apache-2.0 +# +# Licensed under the Apache License, Version 2.0 (the "License"); +# you may not use this file except in compliance with the License. +# You may obtain a copy of the License at +# +# http://www.apache.org/licenses/LICENSE-2.0 +# +# Unless required by applicable law or agreed to in writing, software +# distributed under the License is distributed on an "AS IS" BASIS, +# WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied. +# See the License for the specific language governing permissions and +# limitations under the License. +# + +import os +import sys + +from unittest.mock import patch +from unittest.mock import mock_open +from unittest.mock import MagicMock + +test_path = os.path.dirname(os.path.abspath(__file__)) +modules_path = os.path.dirname(test_path) +sys.path.insert(0, modules_path) + +from sonic_platform.chassis import Chassis +from .utils import platform_sample_bf3 + + +@patch('sonic_py_common.device_info.get_platform', MagicMock(return_value="")) +@patch('sonic_py_common.device_info.get_path_to_platform_dir', MagicMock(return_value="")) +@patch('builtins.open', new_callable=mock_open, read_data=platform_sample_bf3) +@patch('os.path.isfile', MagicMock(return_value=True)) +@patch('os.listdir', MagicMock(return_value=['mt41692_pciconf0.1'])) +class TestThermal: + + def test_chassis_thermal(self, *args): + from sonic_platform.thermal_bf3 import SENSORS + chassis = Chassis() + thermal_list = chassis.get_all_thermals() + assert thermal_list + + for s in SENSORS: + assert 'name' in s + assert 'mlxbf_sensor_name' in s or 'hwmon_path' in s + + sensor_names = list(map(lambda x: x.get('name'), SENSORS)) + thermal_names = list(map(lambda x: x.get_name(), thermal_list)) + for sn in sensor_names: + assert sn in thermal_names + + + def test_hwmon_read(self, *args): + from sonic_platform import thermal_bf3 as thermal + from sonic_platform.thermal_bf3 import Thermal + + thermal.read_fs = MagicMock(return_value=83123) + sensor = {'name': 'test', 'hwmon_path': '/tmp/', 'ht': 95, 'cht': 100} + t = Thermal(**sensor) + assert t.get_temperature() == 83.123 + assert t.get_high_critical_threshold() == 83.123 + + + def test_thermal_get(self, *args): + from sonic_platform import thermal_bf3 as thermal + from sonic_platform.thermal_bf3 import Thermal + + temp_test_mocked_vals = [123, 10.5, -1, None] + + for tv in temp_test_mocked_vals: + thermal.read_temp_mlxbf = MagicMock(return_value=tv) + sensor = {'name': 'test', 'mlxbf_sensor_name': 'test', 'ht': 95, 'cht': 100} + t = Thermal(**sensor) + assert t.get_temperature() == tv + assert t.get_high_threshold() == sensor['ht'] + assert t.get_high_critical_threshold() == sensor['cht'] + assert t.get_low_threshold() == 'N/A' + assert t.get_low_critical_threshold() == 'N/A' + + for tv in temp_test_mocked_vals: + thermal.read_temp_hwmon = MagicMock(return_value=tv) + sensor = {'name': 'test', 'hwmon_path': '/tmp/', 'ht': 95, 'cht': 100} + t = Thermal(**sensor) + assert t.get_temperature() == tv + assert t.get_high_threshold() == sensor['ht'] + assert t.get_high_critical_threshold() == tv + assert t.get_low_threshold() == 'N/A' + assert t.get_low_critical_threshold() == 'N/A' diff --git a/platform/nvidia-bluefield/platform-api/tests/test_throttling.py b/platform/nvidia-bluefield/platform-api/tests/test_throttling.py new file mode 100644 index 00000000000..fb0ef538dde --- /dev/null +++ b/platform/nvidia-bluefield/platform-api/tests/test_throttling.py @@ -0,0 +1,114 @@ +# +# Copyright (c) 2024 NVIDIA CORPORATION & AFFILIATES. +# Apache-2.0 +# +# Licensed under the Apache License, Version 2.0 (the "License"); +# you may not use this file except in compliance with the License. +# You may obtain a copy of the License at +# +# http://www.apache.org/licenses/LICENSE-2.0 +# +# Unless required by applicable law or agreed to in writing, software +# distributed under the License is distributed on an "AS IS" BASIS, +# WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied. +# See the License for the specific language governing permissions and +# limitations under the License. +# + +import os +import sys + +import tempfile +import pytest + +from .utils import TTestData, TTestFSState, LogRecorderMock +from sonic_platform.throttling_checks.cpu_check import CPUThrottlingChecker +from sonic_platform.throttling_checks.ddr_check import DDRThrottlingChecker + +test_path = os.path.dirname(os.path.abspath(__file__)) +modules_path = os.path.dirname(test_path) +sys.path.insert(0, modules_path) + +test_first_run_ok = TTestData('First Run all OK', TTestFSState([1, 0, 1, 0], []), 'OK', []) +test_first_run_powert = TTestData('First Run power throttled', TTestFSState([2, 0, 1, 0], []), 'Throttled', []) +test_first_run_thermalt = TTestData('First Run thermal throttled', TTestFSState([1, 0, 2, 0], []), 'Throttled', []) +test_recovered_powert = TTestData('Power throttled recovery', TTestFSState([1, 1, 1, 0], [2, 0, 1, 0]), 'OK', + [('warning', 'CPU has recovered from power throttling')]) +test_recovered_thermalt = TTestData('Thermal throttled recovery', TTestFSState([1, 0, 1, 1], [1, 0, 2, 0]), 'OK', + [('warning', 'CPU has recovered from thermal throttling')]) +test_in_between_powert = TTestData('Power throttled between checks', TTestFSState([1, 2, 1, 0], [1, 0, 1, 0]), 'OK', + [('warning', 'CPU was power throttled')]) +test_in_between_thermalt = TTestData('Power throttled between checks', TTestFSState([1, 0, 1, 2], [1, 0, 1, 0]), 'OK', + [('warning', 'CPU was thermal throttled')]) +test_no_sensors = TTestData('No sensors', TTestFSState([], []), 'OK', + [('error', 'Failed to check CPU throttling: Could not read the')]) + +test_ddr_ok = TTestData('DDR OK', TTestFSState([0, 0, 0, 0, 60], []), 'OK', []) +test_ddr_throttled = TTestData('DDR throttled', TTestFSState([0, 0, 0, 0, 100], []), 'Throttled', []) +test_ddr_no_sensors = TTestData('DDR no sensor', TTestFSState([], []), 'OK', + [('error', 'Failed to check DDR throttling: Could not read the')]) + +all_cpu_tests = [test_first_run_ok, + test_first_run_powert, + test_recovered_powert, + test_recovered_thermalt, + test_in_between_powert, + test_in_between_thermalt, + test_no_sensors] +first_run_tests = [test_first_run_ok, test_first_run_powert] +ddr_tests = [test_ddr_ok, test_ddr_throttled, test_ddr_no_sensors] + +class Test: + + def prepare_fs(self, sensors_path, storage_path, fs_state: TTestFSState): + sensors_data, storage_data = fs_state.get_dicts() + if sensors_data: + for sensor,value in sensors_data.items(): + with open(f'{sensors_path}/{sensor}', 'w') as f: + f.write(str(value)) + if storage_data: + for sensor,value in storage_data.items(): + with open(f'{storage_path}/{sensor}', 'w') as f: + f.write(str(value)) + + def verify_storage(self, storage_path, fs_state: TTestFSState): + expected, _ = fs_state.get_dicts() + for name, ev in expected.items(): + with open(f'{storage_path}/{name}') as f: + v = int(f.readline().strip()) + assert v == ev + + def setup_and_run(self, cpu_ddr, checker, test_data: TTestData, sensors_path, storage_path=None): + log_recorder = LogRecorderMock() + from sonic_platform.throttling_checks import cpu_check + from sonic_platform.throttling_checks import ddr_check + cpu_check.logger = log_recorder + ddr_check.logger = log_recorder + + self.prepare_fs(sensors_path, storage_path, test_data.fs_state) + + result = checker.check() + test_data.validate(result, log_recorder, cpu_ddr) + + if storage_path: + self.verify_storage(storage_path, test_data.fs_state) + + @pytest.mark.parametrize("test_data", all_cpu_tests, ids=list(map(lambda x: x.title, all_cpu_tests))) + def test_cpu(self, test_data: TTestData): + with tempfile.TemporaryDirectory() as sensors_path, tempfile.TemporaryDirectory() as storage_path: + checker = CPUThrottlingChecker(sensors_path, storage_path) + self.setup_and_run('CPU', checker, test_data, sensors_path, storage_path) + + @pytest.mark.parametrize("test_data", first_run_tests, ids=list(map(lambda x: x.title, first_run_tests))) + def test_cpu_storage_subdir(self, test_data: TTestData): + with tempfile.TemporaryDirectory() as sensors_path, tempfile.TemporaryDirectory() as storage_path: + # test that CPUThrottlingChecker will work correctly if subdirectory for storage should be created + storage_path = f'{storage_path}/storage' + checker = CPUThrottlingChecker(sensors_path, storage_path) + self.setup_and_run('CPU', checker, test_data, sensors_path, storage_path) + + @pytest.mark.parametrize("test_data", ddr_tests, ids=list(map(lambda x: x.title, ddr_tests))) + def test_ddr(self, test_data: TTestData): + with tempfile.TemporaryDirectory() as sensors_path: + checker = DDRThrottlingChecker(sensors_path) + self.setup_and_run('DDR', checker, test_data, sensors_path) diff --git a/platform/nvidia-bluefield/platform-api/tests/utils.py b/platform/nvidia-bluefield/platform-api/tests/utils.py new file mode 100644 index 00000000000..8c9878e0c0e --- /dev/null +++ b/platform/nvidia-bluefield/platform-api/tests/utils.py @@ -0,0 +1,133 @@ +# +# Copyright (c) 2024 NVIDIA CORPORATION & AFFILIATES. +# Apache-2.0 +# +# Licensed under the Apache License, Version 2.0 (the "License"); +# you may not use this file except in compliance with the License. +# You may obtain a copy of the License at +# +# http://www.apache.org/licenses/LICENSE-2.0 +# +# Unless required by applicable law or agreed to in writing, software +# distributed under the License is distributed on an "AS IS" BASIS, +# WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied. +# See the License for the specific language governing permissions and +# limitations under the License. +# + +from dataclasses import dataclass +from typing import List, ClassVar + +platform_sample = """ +{ + "chassis": { + "name": "Nvidia-MBF2H536C", + "components": [], + "fans": [], + "fan_drawers": [], + "psus": [], + "thermals": [], + "sfps": [ + { + "name": "p0" + }, + { + "name": "p1" + } + ] + }, + "interfaces": { + "Ethernet0": { + "index": "1,1,1,1", + "lanes": "0,1,2,3", + "breakout_modes": { + "1x100G": ["etp1"] + } + }, + "Ethernet4": { + "index": "2,2,2,2", + "lanes": "4,5,6,7", + "breakout_modes": { + "1x100G": ["etp2"] + } + } + } +} +""" + +platform_sample_bf3 = """ +{ + "chassis": { + "name": "arm64-nvda_bf-9009d3b600cvaa", + "components": [], + "fans": [], + "fan_drawers": [], + "psus": [], + "thermals": [], + "sfps": [ + { + "name": "p0" + }, + { + "name": "p1" + } + ] + }, + "interfaces": { + "Ethernet0": { + "index": "1,1,1,1", + "lanes": "0,1,2,3", + "breakout_modes": { + "1x100G": ["etp1"] + } + }, + "Ethernet4": { + "index": "2,2,2,2", + "lanes": "4,5,6,7", + "breakout_modes": { + "1x100G": ["etp2"] + } + } + } +} +""" + +# Utilities for throttling tests +class LogRecorderMock(object): + def __init__(self): + self.msgs = [] + + def log_warning(self, msg): + self.msgs.append(('warning', msg)) + + def log_error(self, msg): + self.msgs.append(('error', msg)) + + def get_messages(self): + return self.msgs + +@dataclass +class TTestFSState: + sensors: List[int] + storage: List[int] + sensor_names: ClassVar = ['power_throttling_state', 'power_throttling_event_count', + 'thermal_throttling_state', 'thermal_throttling_event_count', 'ddr_temp'] + def get_dicts(self): + return dict(zip(self.sensor_names, self.sensors)), dict(zip(self.sensor_names, self.storage)) + + +@dataclass +class TTestData: + title: str + fs_state: TTestFSState + result: str + log_msgs: List[str] + + def validate(self, result: str, log_recording: LogRecorderMock, t): + assert f'Throttling\n{t}:{self.result}' == result + assert len(self.log_msgs) == len(log_recording.get_messages()), log_recording.get_messages() + for expected, actual in zip(self.log_msgs, log_recording.get_messages()): + esev, emsg = expected + asev, amsg = actual + assert esev == asev + assert amsg.startswith(emsg), f'{amsg} != {emsg}' diff --git a/platform/nvidia-bluefield/pwr-mlxbf/.gitignore b/platform/nvidia-bluefield/pwr-mlxbf/.gitignore new file mode 100644 index 00000000000..6dbdff4573b --- /dev/null +++ b/platform/nvidia-bluefield/pwr-mlxbf/.gitignore @@ -0,0 +1,5 @@ +# Ignore everything in this directory +* +# Except these files +!.gitignore +!Makefile diff --git a/platform/nvidia-bluefield/pwr-mlxbf/Makefile b/platform/nvidia-bluefield/pwr-mlxbf/Makefile new file mode 100644 index 00000000000..856dc410d41 --- /dev/null +++ b/platform/nvidia-bluefield/pwr-mlxbf/Makefile @@ -0,0 +1,39 @@ +# +# Copyright (c) 2024 NVIDIA CORPORATION & AFFILIATES. +# Apache-2.0 +# +# Licensed under the Apache License, Version 2.0 (the "License"); +# you may not use this file except in compliance with the License. +# You may obtain a copy of the License at +# +# http://www.apache.org/licenses/LICENSE-2.0 +# +# Unless required by applicable law or agreed to in writing, software +# distributed under the License is distributed on an "AS IS" BASIS, +# WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied. +# See the License for the specific language governing permissions and +# limitations under the License. +# + +.ONESHELL: +SHELL = /bin/bash +.SHELLFLAGS += -ex + +PWR_MLXBF = pwr-mlxbf-$(PWR_MLXBF_DRIVER_VERSION) +MODULE_DIR := $(shell pwd)/tmp/${PWR_MLXBF} +GET_PACKAGE := $(shell pwd)/../recipes/get-soc-package.sh + +$(addprefix $(DEST)/, $(PWR_MLXBF_DRIVER)): $(DEST)/% : + rm -rf ./tmp/ + mkdir ./tmp/ + pushd ./tmp/ + + ${GET_PACKAGE} ${BSD_BASE_SOURCE_URL} ${PWR_MLXBF} + + pushd $(PWR_MLXBF) + + # Build the package + make -C /lib/modules/$(KVERSION)/build M=$(MODULE_DIR) + + mv $(PWR_MLXBF_DRIVER) $(DEST)/ + popd diff --git a/platform/nvidia-bluefield/recipes/bluefield-soc.dep b/platform/nvidia-bluefield/recipes/bluefield-soc.dep new file mode 100644 index 00000000000..d30ba91dc8b --- /dev/null +++ b/platform/nvidia-bluefield/recipes/bluefield-soc.dep @@ -0,0 +1,117 @@ +# +# Copyright (c) 2024 NVIDIA CORPORATION & AFFILIATES. +# Apache-2.0 +# +# Licensed under the Apache License, Version 2.0 (the "License"); +# you may not use this file except in compliance with the License. +# You may obtain a copy of the License at +# +# http://www.apache.org/licenses/LICENSE-2.0 +# +# Unless required by applicable law or agreed to in writing, software +# distributed under the License is distributed on an "AS IS" BASIS, +# WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied. +# See the License for the specific language governing permissions and +# limitations under the License. +# + +BSD_COMMON_FLAGS_LIST = $(SONIC_COMMON_FLAGS_LIST) $(BFSOC_VERSION) $(BFSOC_REVISION) $(BSD_BASE_SOURCE_URL) $(BOOTIMAGES_BASE_URL) $(KVERSION) +BSD_COMMON_FILES_LIST = $(SONIC_COMMON_BASE_FILES_LIST) \ + $(SONIC_COMMON_FILES_LIST) \ + $(PLATFORM_PATH)/recipes/bluefield-soc.mk \ + $(PLATFORM_PATH)/recipes/bluefield-soc.dep + +SPATH := $($(TMFIFO_DRIVER)_SRC_PATH) +DEP_FILES := $(BSD_COMMON_FILES_LIST) +DEP_FILES += $(shell git ls-files $(SPATH)) + +$(TMFIFO_DRIVER)_CACHE_MODE := GIT_CONTENT_SHA +$(TMFIFO_DRIVER)_DEP_FLAGS := $(BSD_COMMON_FLAGS_LIST) +$(TMFIFO_DRIVER)_DEP_FILES := $(DEP_FILES) + +SPATH := $($(MLXBF_GIGE_DRIVER)_SRC_PATH) +DEP_FILES := $(BSD_COMMON_FILES_LIST) +DEP_FILES += $(shell git ls-files $(SPATH)) + +$(MLXBF_GIGE_DRIVER)_CACHE_MODE := GIT_CONTENT_SHA +$(MLXBF_GIGE_DRIVER)_DEP_FLAGS := $(BSD_COMMON_FLAGS_LIST) +$(MLXBF_GIGE_DRIVER)_DEP_FILES := $(DEP_FILES) + +SPATH := $($(MLXBF3_GPIO_DRIVER)_SRC_PATH) +DEP_FILES := $(BSD_COMMON_FILES_LIST) +DEP_FILES += $(shell git ls-files $(SPATH)) + +$(MLXBF3_GPIO_DRIVER)_CACHE_MODE := GIT_CONTENT_SHA +$(MLXBF3_GPIO_DRIVER)_DEP_FLAGS := $(BSD_COMMON_FLAGS_LIST) +$(MLXBF3_GPIO_DRIVER)_DEP_FILES := $(DEP_FILES) + +SPATH := $($(MLXBF3_PINCTRL_DRIVER)_SRC_PATH) +DEP_FILES := $(BSD_COMMON_FILES_LIST) +DEP_FILES += $(shell git ls-files $(SPATH)) + +$(MLXBF3_PINCTRL_DRIVER)_CACHE_MODE := GIT_CONTENT_SHA +$(MLXBF3_PINCTRL_DRIVER)_DEP_FLAGS := $(BSD_COMMON_FLAGS_LIST) +$(MLXBF3_PINCTRL_DRIVER)_DEP_FILES := $(DEP_FILES) + +SPATH := $($(MLX_BOOTCTL_DRIVER)_SRC_PATH) +DEP_FILES := $(BSD_COMMON_FILES_LIST) +DEP_FILES += $(shell git ls-files $(SPATH)) + +$(MLX_BOOTCTL_DRIVER)_CACHE_MODE := GIT_CONTENT_SHA +$(MLX_BOOTCTL_DRIVER)_DEP_FLAGS := $(BSD_COMMON_FLAGS_LIST) +$(MLX_BOOTCTL_DRIVER)_DEP_FILES := $(DEP_FILES) + +SPATH := $($(MLXBF_BOOTCTL_DEB)_SRC_PATH) +DEP_FILES := $(BSD_COMMON_FILES_LIST) +DEP_FILES += $(shell git ls-files $(SPATH)) + +$(MLXBF_BOOTCTL_DEB)_CACHE_MODE := GIT_CONTENT_SHA +$(MLXBF_BOOTCTL_DEB)_DEP_FLAGS := $(BSD_COMMON_FLAGS_LIST) +$(MLXBF_BOOTCTL_DEB)_DEP_FILES := $(DEP_FILES) + +SPATH := $($(MLXBF_PKA_DRIVER)_SRC_PATH) +DEP_FILES := $(BSD_COMMON_FILES_LIST) +DEP_FILES += $(shell git ls-files $(SPATH)) + +$(MLXBF_PKA_DRIVER)_CACHE_MODE := GIT_CONTENT_SHA +$(MLXBF_PKA_DRIVER)_DEP_FLAGS := $(BSD_COMMON_FLAGS_LIST) +$(MLXBF_PKA_DRIVER)_DEP_FILES := $(DEP_FILES) + +SPATH := $($(PWR_MLXBF_DRIVER)_SRC_PATH) +DEP_FILES := $(BSD_COMMON_FILES_LIST) +DEP_FILES += $(shell git ls-files $(SPATH)) + +$(PWR_MLXBF_DRIVER)_CACHE_MODE := GIT_CONTENT_SHA +$(PWR_MLXBF_DRIVER)_DEP_FLAGS := $(BSD_COMMON_FLAGS_LIST) +$(PWR_MLXBF_DRIVER)_DEP_FILES := $(DEP_FILES) + +SPATH := $($(MLXBF_PTM_DRIVER)_SRC_PATH) +DEP_FILES := $(BSD_COMMON_FILES_LIST) +DEP_FILES += $(shell git ls-files $(SPATH)) + +$(MLXBF_PTM_DRIVER)_CACHE_MODE := GIT_CONTENT_SHA +$(MLXBF_PTM_DRIVER)_DEP_FLAGS := $(BSD_COMMON_FLAGS_LIST) +$(MLXBF_PTM_DRIVER)_DEP_FILES := $(DEP_FILES) + +DEP_FILES := $(BSD_COMMON_FILES_LIST) + +$(BOOTIMAGES)_CACHE_MODE := GIT_CONTENT_SHA +$(BOOTIMAGES)_DEP_FLAGS := $(BSD_COMMON_FLAGS_LIST) +$(BOOTIMAGES)_DEP_FILES := $(DEP_FILES) + +SPATH := $($(MLNX_BLUEFIELD_BUILD_SCRIPTS)_SRC_PATH) +DEP_FILES := $(BSD_COMMON_FILES_LIST) +DEP_FILES += $(shell git ls-files $(SPATH)) + +$(MLNX_BLUEFIELD_BUILD_SCRIPTS)_CACHE_MODE := GIT_CONTENT_SHA +$(MLNX_BLUEFIELD_BUILD_SCRIPTS)_DEP_FLAGS := $(BSD_COMMON_FLAGS_LIST) +$(MLNX_BLUEFIELD_BUILD_SCRIPTS)_DEP_FILES := $(DEP_FILES) + +SPATH := $($(BF_PLATFORM_MODULE)_SRC_PATH) +DEP_FILES := $(BSD_COMMON_FILES_LIST) +DEP_FILES += $(shell git ls-files $(SPATH)) + +$(BF_PLATFORM_MODULE)_CACHE_MODE := GIT_CONTENT_SHA +$(BF_PLATFORM_MODULE)_DEP_FLAGS := $(BSD_COMMON_FLAGS_LIST) +$(BF_PLATFORM_MODULE)_DEP_FILES := $(DEP_FILES) + diff --git a/platform/nvidia-bluefield/recipes/bluefield-soc.mk b/platform/nvidia-bluefield/recipes/bluefield-soc.mk new file mode 100644 index 00000000000..3ff25893625 --- /dev/null +++ b/platform/nvidia-bluefield/recipes/bluefield-soc.mk @@ -0,0 +1,174 @@ +# +# Copyright (c) 2024 NVIDIA CORPORATION & AFFILIATES. +# Apache-2.0 +# +# Licensed under the Apache License, Version 2.0 (the "License"); +# you may not use this file except in compliance with the License. +# You may obtain a copy of the License at +# +# http://www.apache.org/licenses/LICENSE-2.0 +# +# Unless required by applicable law or agreed to in writing, software +# distributed under the License is distributed on an "AS IS" BASIS, +# WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied. +# See the License for the specific language governing permissions and +# limitations under the License. +# + +# Bluefied Software Distribution Version +BFSOC_VERSION = 4.6.0 +BFSOC_REVISION = 13035 +BFB_IMG_TYPE = prod +BFSOC_BUILD_DATE = + +BSD_INTERNAL_BASE_URL = +BSD_BASE_URL = +BSD_BASE_SOURCE_URL = +BFSOC_FROM_INTERNAL = n + +ifneq ($(BSD_INTERNAL_BASE_URL), ) +BFSOC_FROM_INTERNAL = y +BSD_BASE_URL = $(BSD_INTERNAL_BASE_URL) +ifneq ($(BFSOC_BUILD_DATE), ) +BSD_BASE_URL = $(BSD_INTERNAL_BASE_URL)/$(BFSOC_BUILD_DATE) +endif + +BSD_BASE_SOURCE_URL = $(BSD_BASE_URL)/build/install/distro/SRPMS/ +DEV_BOOTIMAGES_BASE_URL = $(BSD_BASE_URL)/build/install/distro/dev-release/DEBS/ +PROD_BOOTIMAGES_BASE_URL = $(BSD_BASE_URL)/build/install/distro/ga-release/DEBS/ +endif + +export BFSOC_VERSION BFSOC_REVISION BSD_BASE_URL BSD_BASE_SOURCE_URL BFB_IMG_TYPE BFSOC_FROM_INTERNAL PLATFORM_PATH + +define make_url_bfsoc + $(1)_URL="https://github.com/Mellanox/sonic-bluefield-packages/releases/download/dpu-bfsoc-$(BFSOC_VERSION)-$(BFSOC_REVISION)-$(BLDENV)/$(1)" + +endef + +BF_PLATFORM_DRIVERS = +BFSOC_MAKE_DEBS = +BFSOC_MAKE_DEBS_DERIVED = +BFSOC_ONLINE_DEBS = + +MLXBF3_PINCTRL_DRIVER_VERSION = 1.0 +MLXBF3_PINCTRL_DRIVER = pinctrl-mlxbf3.ko +$(MLXBF3_PINCTRL_DRIVER)_SRC_PATH = $(PLATFORM_PATH)/pinctrl-mlxbf3 +$(MLXBF3_PINCTRL_DRIVER)_DEPENDS += $(LINUX_HEADERS) $(LINUX_HEADERS_COMMON) + +BF_PLATFORM_DRIVERS += $(MLXBF3_PINCTRL_DRIVER) +export MLXBF3_PINCTRL_DRIVER_VERSION MLXBF3_PINCTRL_DRIVER + +TMFIFO_DRIVER_VERSION = 1.7 +TMFIFO_DRIVER = mlxbf-tmfifo.ko +$(TMFIFO_DRIVER)_SRC_PATH = $(PLATFORM_PATH)/tmfifo +$(TMFIFO_DRIVER)_DEPENDS += $(LINUX_HEADERS) $(LINUX_HEADERS_COMMON) + +BF_PLATFORM_DRIVERS += $(TMFIFO_DRIVER) +export TMFIFO_DRIVER_VERSION TMFIFO_DRIVER + +MLXBF_GIGE_DRIVER_VERSION = 1.1 +MLXBF_GIGE_DRIVER = mlxbf-gige.ko +$(MLXBF_GIGE_DRIVER)_SRC_PATH = $(PLATFORM_PATH)/mlxbf-gige +$(MLXBF_GIGE_DRIVER)_DEPENDS += $(LINUX_HEADERS) $(LINUX_HEADERS_COMMON) + +BF_PLATFORM_DRIVERS += $(MLXBF_GIGE_DRIVER) +export MLXBF_GIGE_DRIVER_VERSION MLXBF_GIGE_DRIVER + +MLXBF3_GPIO_DRIVER_VERSION = 1.0 +MLXBF3_GPIO_DRIVER = gpio-mlxbf3.ko +$(MLXBF3_GPIO_DRIVER)_SRC_PATH = $(PLATFORM_PATH)/gpio-mlxbf3 +$(MLXBF3_GPIO_DRIVER)_DEPENDS += $(LINUX_HEADERS) $(LINUX_HEADERS_COMMON) + +BF_PLATFORM_DRIVERS += $(MLXBF3_GPIO_DRIVER) +export MLXBF3_GPIO_DRIVER_VERSION MLXBF3_GPIO_DRIVER + +ifeq ($(BFSOC_VERSION), 4.2.0) +MLX_BOOTCTL_DRIVER_VERSION = 1.6 +else +MLX_BOOTCTL_DRIVER_VERSION = 1.7 +endif +MLX_BOOTCTL_DRIVER = mlx-bootctl.ko +$(MLX_BOOTCTL_DRIVER)_SRC_PATH = $(PLATFORM_PATH)/mlx-bootctl +$(MLX_BOOTCTL_DRIVER)_DEPENDS += $(LINUX_HEADERS) $(LINUX_HEADERS_COMMON) + +BF_PLATFORM_DRIVERS += $(MLX_BOOTCTL_DRIVER) +export MLX_BOOTCTL_DRIVER_VERSION MLX_BOOTCTL_DRIVER + +SDHCI_OF_DWCMSHC_DRIVER_VERSION = 1.0 +SDHCI_OF_DWCMSHC_DRIVER = sdhci-of-dwcmshc.ko +$(SDHCI_OF_DWCMSHC_DRIVER)_SRC_PATH = $(PLATFORM_PATH)/sdhci-of-dwcmshc +$(SDHCI_OF_DWCMSHC_DRIVER)_DEPENDS += $(LINUX_HEADERS) $(LINUX_HEADERS_COMMON) + +BF_PLATFORM_DRIVERS += $(SDHCI_OF_DWCMSHC_DRIVER) +export SDHCI_OF_DWCMSHC_DRIVER_VERSION SDHCI_OF_DWCMSHC_DRIVER + +MLXBF_BOOTCTL_DEB_VERSION = 2.1 +MLXBF_BOOTCTL_DEB = mlxbf-bootctl_${MLXBF_BOOTCTL_DEB_VERSION}_${CONFIGURED_ARCH}.deb +$(MLXBF_BOOTCTL_DEB)_SRC_PATH = $(PLATFORM_PATH)/mlxbf-bootctl + +BFSOC_MAKE_DEBS += $(MLXBF_BOOTCTL_DEB) +export MLXBF_BOOTCTL_DEB_VERSION MLXBF_BOOTCTL_DEB + +MLXBF_PKA_DRIVER_VERSION = 1.0 +MLXBF_PKA_DRIVER = mlxbf-pka.ko +$(MLXBF_PKA_DRIVER)_SRC_PATH = $(PLATFORM_PATH)/mlxbf-pka +$(MLXBF_PKA_DRIVER)_DEPENDS += $(LINUX_HEADERS) $(LINUX_HEADERS_COMMON) + +BF_PLATFORM_DRIVERS += $(MLXBF_PKA_DRIVER) +export MLXBF_PKA_DRIVER_VERSION MLXBF_PKA_DRIVER + +PWR_MLXBF_DRIVER_VERSION = 1.0 +PWR_MLXBF_DRIVER = pwr-mlxbf.ko +$(PWR_MLXBF_DRIVER)_SRC_PATH = $(PLATFORM_PATH)/pwr-mlxbf +$(PWR_MLXBF_DRIVER)_DEPENDS += $(LINUX_HEADERS) $(LINUX_HEADERS_COMMON) + +BF_PLATFORM_DRIVERS += $(PWR_MLXBF_DRIVER) +export PWR_MLXBF_DRIVER_VERSION PWR_MLXBF_DRIVER + +MLXBF_PTM_DRIVER_VERSION = 1.1 +MLXBF_PTM_DRIVER = mlxbf-ptm.ko +$(MLXBF_PTM_DRIVER)_SRC_PATH = $(PLATFORM_PATH)/mlxbf-ptm +$(MLXBF_PTM_DRIVER)_DEPENDS += $(LINUX_HEADERS) $(LINUX_HEADERS_COMMON) + +BF_PLATFORM_DRIVERS += $(MLXBF_PTM_DRIVER) +export MLXBF_PTM_DRIVER_VERSION MLXBF_PTM_DRIVER + +ifeq ($(BFB_IMG_TYPE), prod) +BOOTIMAGES_BASE_URL = $(PROD_BOOTIMAGES_BASE_URL) +BOOTIMAGES = mlxbf-bootimages-signed_$(BFSOC_VERSION)-$(BFSOC_REVISION)_arm64.deb +else +BOOTIMAGES_BASE_URL = $(DEV_BOOTIMAGES_BASE_URL) +BOOTIMAGES = mlxbf-bootimages-devsigned_$(BFSOC_VERSION)-$(BFSOC_REVISION)_arm64.deb +endif + +$(BOOTIMAGES)_URL = $(BOOTIMAGES_BASE_URL)/$(BOOTIMAGES) + +BFSOC_ONLINE_DEBS += $(BOOTIMAGES) +export BOOTIMAGES BOOTIMAGES_BASE_URL + +MLNX_BLUEFIELD_BUILD_SCRIPTS = bfscripts_$(BFSOC_VERSION)-$(BFSOC_REVISION)_all.deb +$(MLNX_BLUEFIELD_BUILD_SCRIPTS)_SRC_PATH = $(PLATFORM_PATH)/bfscripts +$(MLNX_BLUEFIELD_BUILD_SCRIPTS)_DEPENDS += $(MLXBF_BOOTCTL_DEB) $(BOOTIMAGES) +$(MLNX_BLUEFIELD_BUILD_SCRIPTS)_RDEPENDS += $(MLXBF_BOOTCTL_DEB) $(BOOTIMAGES) + +BFSOC_MAKE_DEBS += $(MLNX_BLUEFIELD_BUILD_SCRIPTS) +export MLNX_BLUEFIELD_BUILD_SCRIPTS + +BF_PLATFORM_MODULE_VERSION = 1.0 +BF_PLATFORM_MODULE = bluefield-platform-modules_$(BF_PLATFORM_MODULE_VERSION)_arm64.deb +$(BF_PLATFORM_MODULE)_SRC_PATH = $(PLATFORM_PATH)/bluefield-platform-modules + +$(BF_PLATFORM_MODULE)_FILES = $(BF_PLATFORM_DRIVERS) + +SONIC_MAKE_DEBS += $(BF_PLATFORM_MODULE) +export BF_PLATFORM_MODULE_VERSION BF_PLATFORM_MODULE BF_PLATFORM_DRIVERS + +ifeq ($(BFSOC_FROM_INTERNAL), y) +SONIC_MAKE_FILES += $(BF_PLATFORM_DRIVERS) +SONIC_MAKE_DEBS += $(BFSOC_MAKE_DEBS) +SONIC_ONLINE_DEBS += $(BFSOC_ONLINE_DEBS) +else +$(eval $(foreach file,$(BF_PLATFORM_DRIVERS) $(BFSOC_MAKE_DEBS) $(BFSOC_MAKE_DEBS_DERIVED) $(BFSOC_ONLINE_DEBS), $(call make_url_bfsoc,$(file)))) +SONIC_ONLINE_FILES += $(BF_PLATFORM_DRIVERS) +SONIC_ONLINE_DEBS += $(BFSOC_MAKE_DEBS) $(BFSOC_MAKE_DEBS_DERIVED) $(BFSOC_ONLINE_DEBS) +endif diff --git a/platform/nvidia-bluefield/recipes/docker-syncd-bluefield.dep b/platform/nvidia-bluefield/recipes/docker-syncd-bluefield.dep new file mode 100644 index 00000000000..5cb508354f7 --- /dev/null +++ b/platform/nvidia-bluefield/recipes/docker-syncd-bluefield.dep @@ -0,0 +1,11 @@ + +DPATH := $($(DOCKER_SYNCD_BASE)_PATH) +DEP_FILES := $(SONIC_COMMON_FILES_LIST) $(PLATFORM_PATH)/$(RECIPE_DIR)/docker-syncd-bluefield.mk $(PLATFORM_PATH)/$(RECIPE_DIR)/docker-syncd-bluefield.dep +DEP_FILES += $(SONIC_COMMON_BASE_FILES_LIST) +DEP_FILES += $(shell git ls-files -- $(DPATH)) + +$(DOCKER_SYNCD_BASE)_CACHE_MODE := GIT_CONTENT_SHA +$(DOCKER_SYNCD_BASE)_DEP_FLAGS := $(SONIC_COMMON_FLAGS_LIST) +$(DOCKER_SYNCD_BASE)_DEP_FILES := $(DEP_FILES) + +$(eval $(call add_dbg_docker,$(DOCKER_SYNCD_BASE),$(DOCKER_SYNCD_BASE_DBG))) diff --git a/platform/nvidia-bluefield/recipes/docker-syncd-bluefield.mk b/platform/nvidia-bluefield/recipes/docker-syncd-bluefield.mk new file mode 100644 index 00000000000..dcc7244d4be --- /dev/null +++ b/platform/nvidia-bluefield/recipes/docker-syncd-bluefield.mk @@ -0,0 +1,36 @@ +# +# Copyright (c) 2024 NVIDIA CORPORATION & AFFILIATES. +# Apache-2.0 +# +# Licensed under the Apache License, Version 2.0 (the "License"); +# you may not use this file except in compliance with the License. +# You may obtain a copy of the License at +# +# http://www.apache.org/licenses/LICENSE-2.0 +# +# Unless required by applicable law or agreed to in writing, software +# distributed under the License is distributed on an "AS IS" BASIS, +# WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied. +# See the License for the specific language governing permissions and +# limitations under the License. +# + +DOCKER_SYNCD_PLATFORM_CODE = bluefield +include $(PLATFORM_PATH)/../template/docker-syncd-bookworm.mk + +$(DOCKER_SYNCD_BASE)_DEPENDS += $(SYNCD) $(MFT) $(SDN_APPL) $(DPU_SAI) $(MLNX_IPROUTE2) + +$(DOCKER_SYNCD_BASE)_DBG_DEPENDS += $(SYNCD_DBG) \ + $(LIBSWSSCOMMON_DBG) \ + $(LIBSAIMETADATA_DBG) \ + $(LIBSAIREDIS_DBG) + +ifeq ($(SDK_FROM_SRC), y) +$(DOCKER_SYNCD_BASE)_DBG_DEPENDS += $(DPU_SAI_DBGSYM) +endif + +$(DOCKER_SYNCD_BASE)_VERSION = 1.0.0 +$(DOCKER_SYNCD_BASE)_PACKAGE_NAME = syncd + +$(DOCKER_SYNCD_BASE)_RUN_OPT += -v /host/warmboot:/var/warmboot +$(DOCKER_SYNCD_BASE)_RUN_OPT += -v /var/log/bluefield/sdk-dumps:/var/log/bluefield/sdk-dumps diff --git a/platform/nvidia-bluefield/recipes/dpu-sai.dep b/platform/nvidia-bluefield/recipes/dpu-sai.dep new file mode 100644 index 00000000000..92cdae39900 --- /dev/null +++ b/platform/nvidia-bluefield/recipes/dpu-sai.dep @@ -0,0 +1,21 @@ +# DPKG FRK + +SPATH := $($(DPU_SAI)_SRC_PATH) +SLINKS := $(shell find $(SPATH) -type l -exec echo {} \; | grep -Ev ' ') +SMDEP_PATHS := $(shell git submodule status --recursive -- $(SPATH) | awk '{print $$2}' | grep -Ev ' ') +SMDEP_FILES := $(foreach path,$(SMDEP_PATHS),$(filter-out $(SMDEP_PATHS),$(addprefix $(path)/,$(shell cd $(path) && git ls-files | grep -Ev ' ')))) +DEP_FILES := $(SONIC_COMMON_FILES_LIST) $(PLATFORM_PATH)/$(RECIPE_DIR)/dpu-sai.mk $(PLATFORM_PATH)/$(RECIPE_DIR)/dpu-sai.dep +DEP_FILES += $(SONIC_COMMON_BASE_FILES_LIST) +DEP_FILES += $(filter-out $(SMDEP_PATHS),$(shell git ls-files -- $(SPATH) | grep -Ev ' ')) + +$(DPU_SAI)_CACHE_MODE := GIT_CONTENT_SHA +$(DPU_SAI)_DEP_FLAGS := $(SONIC_COMMON_FLAGS_LIST) +$(DPU_SAI)_DEP_FILES := $(filter-out $(SLINKS),$(DEP_FILES)) +$(DPU_SAI)_SMDEP_FILES := $(filter-out $(SLINKS),$(SMDEP_FILES)) +$(DPU_SAI)_SMDEP_PATHS := $(SMDEP_PATHS) + +$(DPU_SAI_DBGSYM)_CACHE_MODE := GIT_CONTENT_SHA +$(DPU_SAI_DBGSYM)_DEP_FLAGS := $(SONIC_COMMON_FLAGS_LIST) +$(DPU_SAI_DBGSYM)_DEP_FILES := $(filter-out $(SLINKS),$(DEP_FILES)) +$(DPU_SAI_DBGSYM)_SMDEP_FILES := $(filter-out $(SLINKS),$(SMDEP_FILES)) +$(DPU_SAI_DBGSYM)_SMDEP_PATHS := $(SMDEP_PATHS) diff --git a/platform/nvidia-bluefield/recipes/dpu-sai.mk b/platform/nvidia-bluefield/recipes/dpu-sai.mk new file mode 100644 index 00000000000..40b3f6e506f --- /dev/null +++ b/platform/nvidia-bluefield/recipes/dpu-sai.mk @@ -0,0 +1,47 @@ +# +# Copyright (c) 2024 NVIDIA CORPORATION & AFFILIATES. +# Apache-2.0 +# +# Licensed under the Apache License, Version 2.0 (the "License"); +# you may not use this file except in compliance with the License. +# You may obtain a copy of the License at +# +# http://www.apache.org/licenses/LICENSE-2.0 +# +# Unless required by applicable law or agreed to in writing, software +# distributed under the License is distributed on an "AS IS" BASIS, +# WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied. +# See the License for the specific language governing permissions and +# limitations under the License. +# + +DPU_SAI_VERSION = SAIBuild0.0.29.0 + +# Place here URL where SAI sources exist +DPU_SAI_SOURCE_BASE_URL= + +export DPU_SAI_VERSION DPU_SAI_SOURCE_BASE_URL + +define make_url_sai + $(1)_URL="https://github.com/Mellanox/sonic-bluefield-packages/releases/download/dpu-sai-$(DPU_SAI_VERSION)-$(BLDENV)/$(1)" + +endef + +DPU_SAI = mlnx-sai_1.mlnx.$(DPU_SAI_VERSION)_arm64.deb +$(DPU_SAI)_SRC_PATH = $(PLATFORM_PATH)/dpu-sai +$(DPU_SAI)_DEPENDS = $(SDN_APPL) +$(DPU_SAI)_RDEPENDS = $(SDN_APPL) +$(eval $(call add_conflict_package,$(DPU_SAI),$(LIBSAIVS_DEV))) +DPU_SAI_DBGSYM = mlnx-sai-dbgsym_1.mlnx.$(DPU_SAI_VERSION)_arm64.deb +$(eval $(call add_derived_package,$(DPU_SAI),$(DPU_SAI_DBGSYM))) + +ifneq ($(DPU_SAI_SOURCE_BASE_URL), ) +SONIC_MAKE_DEBS += $(DPU_SAI) +else +$(eval $(foreach deb,$(DPU_SAI) $(DPU_SAI_DBGSYM),$(call make_url_sai,$(deb)))) +SONIC_ONLINE_DEBS += $(DPU_SAI) +endif + + +export DPU_SAI +export DPU_SAI_DBGSYM diff --git a/platform/nvidia-bluefield/recipes/fw.dep b/platform/nvidia-bluefield/recipes/fw.dep new file mode 100644 index 00000000000..60cd2995efa --- /dev/null +++ b/platform/nvidia-bluefield/recipes/fw.dep @@ -0,0 +1,24 @@ +# +# Copyright (c) 2024 NVIDIA CORPORATION & AFFILIATES. +# Apache-2.0 +# +# Licensed under the Apache License, Version 2.0 (the "License"); +# you may not use this file except in compliance with the License. +# You may obtain a copy of the License at +# +# http://www.apache.org/licenses/LICENSE-2.0 +# +# Unless required by applicable law or agreed to in writing, software +# distributed under the License is distributed on an "AS IS" BASIS, +# WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied. +# See the License for the specific language governing permissions and +# limitations under the License. +# + +DEP_FILES := $(SONIC_COMMON_FILES_LIST) $(PLATFORM_PATH)/$(RECIPE_DIR)/fw.mk $(PLATFORM_PATH)/$(RECIPE_DIR)/fw.dep +DEP_FILES += $(SONIC_COMMON_BASE_FILES_LIST) + +$(BF_FW_FILES)_CACHE_MODE := GIT_CONTENT_SHA +$(BF_FW_FILES)_DEP_FLAGS := $(SONIC_COMMON_FLAGS_LIST) $(FW_BASE_PATH) $(BF3_FW_VERSION) +$(BF_FW_FILES)_DEP_FILES := $(DEP_FILES) + diff --git a/platform/nvidia-bluefield/recipes/fw.mk b/platform/nvidia-bluefield/recipes/fw.mk new file mode 100644 index 00000000000..94b0486e9e7 --- /dev/null +++ b/platform/nvidia-bluefield/recipes/fw.mk @@ -0,0 +1,42 @@ +# +# Copyright (c) 2024 NVIDIA CORPORATION & AFFILIATES. +# Apache-2.0 +# +# Licensed under the Apache License, Version 2.0 (the "License"); +# you may not use this file except in compliance with the License. +# You may obtain a copy of the License at +# +# http://www.apache.org/licenses/LICENSE-2.0 +# +# Unless required by applicable law or agreed to in writing, software +# distributed under the License is distributed on an "AS IS" BASIS, +# WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied. +# See the License for the specific language governing permissions and +# limitations under the License. +# + +BF3_FW_BASE_URL = + +BF3_FW_VERSION = 32.39.1002 + +BF3_FW_FILE = fw-BlueField-3-rel-$(subst .,_,$(BF3_FW_VERSION)).mfa + +define make_url_fw + $(1)_URL="https://github.com/Mellanox/sonic-bluefield-packages/releases/download/dpu-fw-$(BF3_FW_VERSION)/$(1)" + +endef + + +ifeq ($(BF3_FW_BASE_URL),) +$(eval $(foreach fw,$(BF3_FW_FILE),$(call make_url_fw,$(fw)))) +else +$(BF3_FW_FILE)_URL = $(BF3_FW_BASE_URL)/$(BF3_FW_FILE) +endif + +BF_FW_FILES = $(BF3_FW_FILE) + +export BF3_FW_FILE +export BF_FW_FILES + +SONIC_ONLINE_FILES += $(BF_FW_FILES) + diff --git a/platform/nvidia-bluefield/recipes/get-soc-package.sh b/platform/nvidia-bluefield/recipes/get-soc-package.sh new file mode 100755 index 00000000000..a3d5fc44185 --- /dev/null +++ b/platform/nvidia-bluefield/recipes/get-soc-package.sh @@ -0,0 +1,9 @@ +#!/bin/bash + +base_url=${1} +package_name=${2} + +full_url=$(lynx --listonly --nonumbers -dump ${base_url} | grep ${package_name}) +wget ${full_url} +rpm2cpio ${package_name}*.src.rpm | cpio -idmv +tar xf *.tar.gz diff --git a/platform/nvidia-bluefield/recipes/get_package_gh_asset_id.sh b/platform/nvidia-bluefield/recipes/get_package_gh_asset_id.sh new file mode 100755 index 00000000000..af0671233d6 --- /dev/null +++ b/platform/nvidia-bluefield/recipes/get_package_gh_asset_id.sh @@ -0,0 +1,32 @@ +#!/bin/bash +# +# Copyright (c) 2024 NVIDIA CORPORATION & AFFILIATES. +# Apache-2.0 +# +# Licensed under the Apache License, Version 2.0 (the "License"); +# you may not use this file except in compliance with the License. +# You may obtain a copy of the License at +# +# http://www.apache.org/licenses/LICENSE-2.0 +# +# Unless required by applicable law or agreed to in writing, software +# distributed under the License is distributed on an "AS IS" BASIS, +# WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied. +# See the License for the specific language governing permissions and +# limitations under the License. +# + +tag=$1 +package=$2 +gh_token=$3 + +repo=nvidia-sonic/sonic-bluefield-packages +assetsfile='/tmp/dpu-sdk-fw-assets-'$tag +lockfile='/tmp/dpu-sdk-fw-assets-lock-'$tag + +if [ ! -f $assetsfile ]; then + cmd="/usr/bin/curl -s -L -f -H 'Authorization: token $gh_token' 'https://api.github.com/repos/$repo/releases/tags/dpu-$tag' | jq -r '.assets[] | (.name) + \" \" + (.id | tostring)'" + eval "flock -w 5 $lockfile $cmd > $assetsfile" +fi + +echo $(grep $package $assetsfile | awk '{print $2}') diff --git a/platform/nvidia-bluefield/recipes/get_sdk_package_version.sh b/platform/nvidia-bluefield/recipes/get_sdk_package_version.sh new file mode 100755 index 00000000000..5711035979a --- /dev/null +++ b/platform/nvidia-bluefield/recipes/get_sdk_package_version.sh @@ -0,0 +1,45 @@ +#!/bin/bash +# +# Copyright (c) 2024 NVIDIA CORPORATION & AFFILIATES. +# Apache-2.0 +# +# Licensed under the Apache License, Version 2.0 (the "License"); +# you may not use this file except in compliance with the License. +# You may obtain a copy of the License at +# +# http://www.apache.org/licenses/LICENSE-2.0 +# +# Unless required by applicable law or agreed to in writing, software +# distributed under the License is distributed on an "AS IS" BASIS, +# WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied. +# See the License for the specific language governing permissions and +# limitations under the License. +# + +for i in "$@"; do + case $i in + -s) + short=true + shift + ;; + *) + ;; + esac +done + +path=$1 +package=$2 + +if [[ $path == "http"* ]]; then + cmd="curl -s" +else + cmd="cat" +fi + +version=$($cmd $path 2>/dev/null | grep ^$package | sed -e "s/$package -//g") + +if [[ $short == true ]]; then + echo $(echo $version | tr "-" " " | awk '{print $1}') +else + echo $version +fi diff --git a/platform/nvidia-bluefield/recipes/installer-image.dep b/platform/nvidia-bluefield/recipes/installer-image.dep new file mode 100644 index 00000000000..74214c6485a --- /dev/null +++ b/platform/nvidia-bluefield/recipes/installer-image.dep @@ -0,0 +1,5 @@ +# DPKG FRK + +(SONIC_BF_IMAGE_PXE)_CACHE_MODE := none +(SONIC_BF_IMAGE_BIN)_CACHE_MODE := none +(SONIC_BF_IMAGE_BFB)_CACHE_MODE := none diff --git a/platform/nvidia-bluefield/recipes/installer-image.mk b/platform/nvidia-bluefield/recipes/installer-image.mk new file mode 100644 index 00000000000..e3831a54d36 --- /dev/null +++ b/platform/nvidia-bluefield/recipes/installer-image.mk @@ -0,0 +1,92 @@ +# +# Copyright (c) 2024 NVIDIA CORPORATION & AFFILIATES. +# Apache-2.0 +# +# Licensed under the Apache License, Version 2.0 (the "License"); +# you may not use this file except in compliance with the License. +# You may obtain a copy of the License at +# +# http://www.apache.org/licenses/LICENSE-2.0 +# +# Unless required by applicable law or agreed to in writing, software +# distributed under the License is distributed on an "AS IS" BASIS, +# WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied. +# See the License for the specific language governing permissions and +# limitations under the License. +# + +# sonic nvidia-bluefield installer image + +SONIC_BF_IMAGE_BASE = sonic-nvidia-bluefield +$(SONIC_BF_IMAGE_BASE)_MACHINE = nvidia-bluefield + +$(SONIC_BF_IMAGE_BASE)_DEPENDS += $(MLXBF_BOOTCTL_DEB) \ + $(BOOTIMAGES) \ + $(MLNX_BLUEFIELD_BUILD_SCRIPTS) \ + $(MLNX_TOOLS) \ + $(OFED_KERNEL_UTILS) \ + $(KERNEL_MFT) \ + $(MLNX_IPROUTE2) + +# Install the packages during the build_debian phase +$(SONIC_BF_IMAGE_BASE)_INSTALLS += $(SYSTEMD_SONIC_GENERATOR) \ + $(KERNEL_MFT) \ + $(MFT_OEM) \ + $(MFT) \ + $(BOOTIMAGES) \ + $(MLXBF_BOOTCTL_DEB) \ + $(MLNX_BLUEFIELD_BUILD_SCRIPTS) \ + $(MLX_OPENIPMI_DEB) \ + $(MLX_OPENIPMI_SERVER_DEB) \ + $(BF_PLATFORM_MODULE) \ + $(OFED_KERNEL) \ + $(MLNX_TOOLS) \ + $(OFED_KERNEL_UTILS) \ + $(MLNX_IPROUTE2) + +DISABLED_DOCKERS = $(DOCKER_SFLOW) $(DOCKER_MGMT_FRAMEWORK) $(DOCKER_NAT) $(DOCKER_TEAMD) $(DOCKER_ROUTER_ADVERTISER) $(DOCKER_MUX) +DISABLED_PACKAGES_LOCAL = $(DOCKER_DHCP_RELAY) $(DOCKER_MACSEC) +DISABLED_FEATURE_FLAGS = INCLUDE_SFLOW INCLUDE_MGMT_FRAMEWORK INCLUDE_NAT INCLUDE_MACSEC INCLUDE_TEAMD INCLUDE_ROUTER_ADVERTISER INCLUDE_MUX +$(info Disabling the following docker images: $(DISABLED_DOCKERS)) +$(info Disabling the following packages: $(DISABLED_PACKAGES_LOCAL)) +$(info Disabling the following feauture flags: $(DISABLED_FEATURE_FLAGS)) + +SONIC_PACKAGES_LOCAL := $(filter-out $(DISABLED_PACKAGES_LOCAL), $(SONIC_PACKAGES_LOCAL)) + +$(foreach feature, $(DISABLED_FEATURE_FLAGS), $(eval override $(feature)=n )) + +$(SONIC_BF_IMAGE_BASE)_DOCKERS = $(filter-out $(DISABLED_DOCKERS), $(SONIC_INSTALL_DOCKER_IMAGES)) +$(SONIC_BF_IMAGE_BASE)_FILES = $(BF_FW_FILES) + +# A compressed archive which contains individual files required for PXE boot +# A BFB image is also generated as a by-product of PXE image generation +SONIC_BF_IMAGE_PXE = $(SONIC_BF_IMAGE_BASE).tar.gz +$(SONIC_BF_IMAGE_PXE)_IMAGE_TYPE = pxe +$(SONIC_BF_IMAGE_PXE)_MACHINE = $($(SONIC_BF_IMAGE_BASE)_MACHINE) +$(SONIC_BF_IMAGE_PXE)_INSTALLS += $($(SONIC_BF_IMAGE_BASE)_INSTALLS) +$(SONIC_BF_IMAGE_PXE)_DEPENDS += $($(SONIC_BF_IMAGE_BASE)_DEPENDS) +$(SONIC_BF_IMAGE_PXE)_DOCKERS += $($(SONIC_BF_IMAGE_BASE)_DOCKERS) +$(SONIC_BF_IMAGE_PXE)_LAZY_INSTALLS += $($(SONIC_BF_IMAGE_BASE)_LAZY_INSTALLS) +$(SONIC_BF_IMAGE_PXE)_FILES += $($(SONIC_BF_IMAGE_BASE)_FILES) $(MLX_BOOTCTL_DRIVER) + +# The traditional *.bin image. Works for sonic-sonic upgrade. +SONIC_BF_IMAGE_BIN = $(SONIC_BF_IMAGE_BASE).bin +$(SONIC_BF_IMAGE_BIN)_IMAGE_TYPE = onie +$(SONIC_BF_IMAGE_BIN)_MACHINE = $($(SONIC_BF_IMAGE_BASE)_MACHINE) +$(SONIC_BF_IMAGE_BIN)_INSTALLS += $($(SONIC_BF_IMAGE_BASE)_INSTALLS) +$(SONIC_BF_IMAGE_BIN)_DEPENDS += $($(SONIC_BF_IMAGE_BASE)_DEPENDS) +$(SONIC_BF_IMAGE_BIN)_DOCKERS += $($(SONIC_BF_IMAGE_BASE)_DOCKERS) +$(SONIC_BF_IMAGE_BIN)_LAZY_INSTALLS += $($(SONIC_BF_IMAGE_BASE)_LAZY_INSTALLS) +$(SONIC_BF_IMAGE_BIN)_FILES += $($(SONIC_BF_IMAGE_BASE)_FILES) + +# BFB (Bluefield BootStream) style image +SONIC_BF_IMAGE_BFB = $(SONIC_BF_IMAGE_BASE).bfb +$(SONIC_BF_IMAGE_BFB)_IMAGE_TYPE = bfb +$(SONIC_BF_IMAGE_BFB)_MACHINE = $($(SONIC_BF_IMAGE_BASE)_MACHINE) +$(SONIC_BF_IMAGE_BFB)_INSTALLS += $($(SONIC_BF_IMAGE_BASE)_INSTALLS) +$(SONIC_BF_IMAGE_BFB)_DEPENDS += $($(SONIC_BF_IMAGE_BASE)_DEPENDS) +$(SONIC_BF_IMAGE_BFB)_DOCKERS += $($(SONIC_BF_IMAGE_BASE)_DOCKERS) +$(SONIC_BF_IMAGE_BFB)_LAZY_INSTALLS += $($(SONIC_BF_IMAGE_BASE)_LAZY_INSTALLS) +$(SONIC_BF_IMAGE_BFB)_FILES += $($(SONIC_BF_IMAGE_BASE)_FILES) $(MLX_BOOTCTL_DRIVER) + +SONIC_INSTALLERS += $(SONIC_BF_IMAGE_PXE) $(SONIC_BF_IMAGE_BIN) $(SONIC_BF_IMAGE_BFB) diff --git a/platform/nvidia-bluefield/recipes/mft.dep b/platform/nvidia-bluefield/recipes/mft.dep new file mode 100644 index 00000000000..861adc49255 --- /dev/null +++ b/platform/nvidia-bluefield/recipes/mft.dep @@ -0,0 +1,18 @@ +# DPKG FRK + +SPATH := $($(MFT)_SRC_PATH) +DEP_FILES := $(SONIC_COMMON_FILES_LIST) $(PLATFORM_PATH)/$(RECIPE_DIR)/mft.mk $(PLATFORM_PATH)/$(RECIPE_DIR)/mft.dep +DEP_FILES += $(SONIC_COMMON_BASE_FILES_LIST) +DEP_FILES += $(shell git ls-files -- $(SPATH)) + +$(MFT)_CACHE_MODE := GIT_CONTENT_SHA +$(MFT)_DEP_FLAGS := $(SONIC_COMMON_FLAGS_LIST) +$(MFT)_DEP_FILES := $(DEP_FILES) + +$(KERNEL_MFT)_CACHE_MODE := GIT_CONTENT_SHA +$(KERNEL_MFT)_DEP_FLAGS := $(SONIC_COMMON_FLAGS_LIST) +$(KERNEL_MFT)_DEP_FILES := $(DEP_FILES) + +$(MFT_OEM)_CACHE_MODE := GIT_CONTENT_SHA +$(MFT_OEM)_DEP_FLAGS := $(SONIC_COMMON_FLAGS_LIST) +$(MFT_OEM)_DEP_FILES := $(DEP_FILES) diff --git a/platform/nvidia-bluefield/recipes/mft.mk b/platform/nvidia-bluefield/recipes/mft.mk new file mode 100644 index 00000000000..7f56158656c --- /dev/null +++ b/platform/nvidia-bluefield/recipes/mft.mk @@ -0,0 +1,44 @@ +# +# Copyright (c) 2024 NVIDIA CORPORATION & AFFILIATES. +# Apache-2.0 +# +# Licensed under the Apache License, Version 2.0 (the "License"); +# you may not use this file except in compliance with the License. +# You may obtain a copy of the License at +# +# http://www.apache.org/licenses/LICENSE-2.0 +# +# Unless required by applicable law or agreed to in writing, software +# distributed under the License is distributed on an "AS IS" BASIS, +# WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied. +# See the License for the specific language governing permissions and +# limitations under the License. + +MFT_VERSION = 4.26.1 +MFT_REVISION = 3 + +MFT_INTERNAL_SOURCE_BASE_URL = + +ifneq ($(MFT_INTERNAL_SOURCE_BASE_URL), ) +MFT_FROM_INTERNAL = y +else +MFT_FROM_INTERNAL = n +endif + +export MFT_VERSION MFT_REVISION MFT_FROM_INTERNAL MFT_INTERNAL_SOURCE_BASE_URL + +MFT = mft_$(MFT_VERSION)-$(MFT_REVISION)_arm64.deb +$(MFT)_SRC_PATH = $(PLATFORM_PATH)/mft + +MFT_OEM = mft-oem_$(MFT_VERSION)-$(MFT_REVISION)_arm64.deb +$(eval $(call add_derived_package,$(MFT),$(MFT_OEM))) + +KERNEL_MFT_DKMS = kernel-mft-dkms_$(MFT_VERSION)-$(MFT_REVISION)_all.deb +$(eval $(call add_derived_package,$(MFT),$(KERNEL_MFT_DKMS))) + +BUILD_ARCH = $(shell dpkg-architecture -qDEB_BUILD_ARCH) +KERNEL_MFT = kernel-mft-dkms-modules-$(KVERSION)_$(MFT_VERSION)_$(BUILD_ARCH).deb +$(KERNEL_MFT)_SRC_PATH = $(PLATFORM_PATH)/mft +$(KERNEL_MFT)_DEPENDS += $(LINUX_HEADERS) $(LINUX_HEADERS_COMMON) $(KERNEL_MFT_DKMS) + +SONIC_MAKE_DEBS += $(MFT) $(KERNEL_MFT) diff --git a/platform/nvidia-bluefield/recipes/platform-api.dep b/platform/nvidia-bluefield/recipes/platform-api.dep new file mode 100644 index 00000000000..c2f3b7acda5 --- /dev/null +++ b/platform/nvidia-bluefield/recipes/platform-api.dep @@ -0,0 +1,9 @@ +SPATH := $($(SONIC_PLATFORM_API_PY3)_SRC_PATH) +SLINKS := $(shell find $(SPATH) -type l -exec echo {} \; | grep -Ev ' ') +DEP_FILES := $(SONIC_COMMON_FILES_LIST) $(PLATFORM_PATH)/$(RECIPE_DIR)/platform-api.mk $(PLATFORM_PATH)/$(RECIPE_DIR)/platform-api.dep +DEP_FILES += $(SONIC_COMMON_BASE_FILES_LIST) +DEP_FILES += $(shell git ls-files -- $(SPATH) | grep -Ev ' ') + +$(SONIC_PLATFORM_API_PY3)_CACHE_MODE := GIT_CONTENT_SHA +$(SONIC_PLATFORM_API_PY3)_DEP_FLAGS := $(SONIC_COMMON_FLAGS_LIST) +$(SONIC_PLATFORM_API_PY3)_DEP_FILES := $(filter-out $(SLINKS),$(DEP_FILES)) diff --git a/platform/nvidia-bluefield/recipes/platform-api.mk b/platform/nvidia-bluefield/recipes/platform-api.mk new file mode 100644 index 00000000000..c9b670d9cee --- /dev/null +++ b/platform/nvidia-bluefield/recipes/platform-api.mk @@ -0,0 +1,27 @@ +# +# Copyright (c) 2024 NVIDIA CORPORATION & AFFILIATES. +# Apache-2.0 +# +# Licensed under the Apache License, Version 2.0 (the "License"); +# you may not use this file except in compliance with the License. +# You may obtain a copy of the License at +# +# http://www.apache.org/licenses/LICENSE-2.0 +# +# Unless required by applicable law or agreed to in writing, software +# distributed under the License is distributed on an "AS IS" BASIS, +# WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied. +# See the License for the specific language governing permissions and +# limitations under the License. +# + +# SONIC_PLATFORM_API_PY3 package + +SONIC_PLATFORM_API_PY3 = platform_api-1.0-py3-none-any.whl +$(SONIC_PLATFORM_API_PY3)_SRC_PATH = $(PLATFORM_PATH)/platform-api +$(SONIC_PLATFORM_API_PY3)_PYTHON_VERSION = 3 +$(SONIC_PLATFORM_API_PY3)_DEPENDS = $(SONIC_PY_COMMON_PY3) $(SONIC_PLATFORM_COMMON_PY3) $(SONIC_CONFIG_ENGINE_PY3) $(SONIC_PLATFORM_API_PY2) +$(SONIC_PLATFORM_API_PY3)_DEBS_DEPENDS = $(PYTHON3_SWSSCOMMON) +SONIC_PYTHON_WHEELS += $(SONIC_PLATFORM_API_PY3) + +export platform_api_py3_wheel_path="$(addprefix $(PYTHON_WHEELS_PATH)/,$(SONIC_PLATFORM_API_PY3))" diff --git a/platform/nvidia-bluefield/recipes/sdk.dep b/platform/nvidia-bluefield/recipes/sdk.dep new file mode 100644 index 00000000000..ced96a512e3 --- /dev/null +++ b/platform/nvidia-bluefield/recipes/sdk.dep @@ -0,0 +1,190 @@ +# +# Copyright (c) 2024 NVIDIA CORPORATION & AFFILIATES. +# Apache-2.0 +# +# Licensed under the Apache License, Version 2.0 (the "License"); +# you may not use this file except in compliance with the License. +# You may obtain a copy of the License at +# +# http://www.apache.org/licenses/LICENSE-2.0 +# +# Unless required by applicable law or agreed to in writing, software +# distributed under the License is distributed on an "AS IS" BASIS, +# WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied. +# See the License for the specific language governing permissions and +# limitations under the License. +# + +SDK_COMMON_FLAGS_LIST = $(SONIC_COMMON_FLAGS_LIST) $(SDK_VERSION) +SDK_COMMON_FILES_LIST = $(SONIC_COMMON_BASE_FILES_LIST) \ + $(SONIC_COMMON_FILES_LIST) \ + $(PLATFORM_PATH)/recipes/sdk.mk \ + $(PLATFORM_PATH)/recipes/sdk.dep \ + $(PLATFORM_PATH)/recipes/get_sdk_package_version.sh + +# OFED + +SPATH := $($(OFED_KERNEL)_SRC_PATH) +DEP_FILES := $(SDK_COMMON_FILES_LIST) +DEP_FILES += $(shell git ls-files -- $(SPATH)) + +$(OFED_KERNEL)_CACHE_MODE := GIT_CONTENT_SHA +$(OFED_KERNEL)_DEP_FLAGS := $(SDK_COMMON_FLAGS_LIST) +$(OFED_KERNEL)_DEP_FILES := $(DEP_FILES) + +$(MLNX_TOOLS)_CACHE_MODE := GIT_CONTENT_SHA +$(MLNX_TOOLS)_DEP_FLAGS := $(SDK_COMMON_FLAGS_LIST) +$(MLNX_TOOLS)_DEP_FILES := $(DEP_FILES) + +$(OFED_KERNEL_UTILS)_CACHE_MODE := GIT_CONTENT_SHA +$(OFED_KERNEL_UTILS)_DEP_FLAGS := $(SDK_COMMON_FLAGS_LIST) +$(OFED_KERNEL_UTILS)_DEP_FILES := $(DEP_FILES) + +# mlnx-iproute2 + +SPATH := $($(MLNX_IPROUTE2)_SRC_PATH) +DEP_FILES := $(SDK_COMMON_FILES_LIST) +DEP_FILES += $(shell git ls-files -- $(SPATH)) + +$(MLNX_IPROUTE2)_CACHE_MODE := GIT_CONTENT_SHA +$(MLNX_IPROUTE2)_DEP_FLAGS := $(SDK_COMMON_FLAGS_LIST) +$(MLNX_IPROUTE2)_DEP_FILES := $(DEP_FILES) + +# RDMA core and derived packages + +SPATH := $($(RDMA_CORE)_SRC_PATH) +DEP_FILES := $(SDK_COMMON_FILES_LIST) +DEP_FILES += $(shell git ls-files -- $(SPATH)) + +$(RDMA_CORE)_CACHE_MODE := GIT_CONTENT_SHA +$(RDMA_CORE)_DEP_FLAGS := $(SDK_COMMON_FLAGS_LIST) +$(RDMA_CORE)_DEP_FILES := $(DEP_FILES) + +$(IB_VERBS_PROV)_CACHE_MODE := GIT_CONTENT_SHA +$(IB_VERBS_PROV)_DEP_FLAGS := $(SDK_COMMON_FLAGS_LIST) +$(IB_VERBS_PROV)_DEP_FILES := $(DEP_FILES) + +$(IB_VERBS)_CACHE_MODE := GIT_CONTENT_SHA +$(IB_VERBS)_DEP_FLAGS := $(SDK_COMMON_FLAGS_LIST) +$(IB_VERBS)_DEP_FILES := $(DEP_FILES) + +$(IB_VERBS_DEV)_CACHE_MODE := GIT_CONTENT_SHA +$(IB_VERBS_DEV)_DEP_FLAGS := $(SDK_COMMON_FLAGS_LIST) +$(IB_VERBS_DEV)_DEP_FILES := $(DEP_FILES) + +$(IB_UMAD)_CACHE_MODE := GIT_CONTENT_SHA +$(IB_UMAD)_DEP_FLAGS := $(SDK_COMMON_FLAGS_LIST) +$(IB_UMAD)_DEP_FILES := $(DEP_FILES) + +$(IB_UMAD_DEV)_CACHE_MODE := GIT_CONTENT_SHA +$(IB_UMAD_DEV)_DEP_FLAGS := $(SDK_COMMON_FLAGS_LIST) +$(IB_UMAD_DEV)_DEP_FILES := $(DEP_FILES) + +ifeq ($(SDK_FROM_SRC),y) +$(RDMA_CORE_DBGSYM)_CACHE_MODE := GIT_CONTENT_SHA +$(RDMA_CORE_DBGSYM)_DEP_FLAGS := $(SDK_COMMON_FLAGS_LIST) +$(RDMA_CORE_DBGSYM)_DEP_FILES := $(DEP_FILES) + +$(IB_VERBS_PROV_DBGSYM)_CACHE_MODE := GIT_CONTENT_SHA +$(IB_VERBS_PROV_DBGSYM)_DEP_FLAGS := $(SDK_COMMON_FLAGS_LIST) +$(IB_VERBS_PROV_DBGSYM)_DEP_FILES := $(DEP_FILES) + +$(IB_VERBS_DBGSYM)_CACHE_MODE := GIT_CONTENT_SHA +$(IB_VERBS_DBGSYM)_DEP_FLAGS := $(SDK_COMMON_FLAGS_LIST) +$(IB_VERBS_DBGSYM)_DEP_FILES := $(DEP_FILES) + +$(IB_UMAD_DBGSYM)_CACHE_MODE := GIT_CONTENT_SHA +$(IB_UMAD_DBGSYM)_DEP_FLAGS := $(SDK_COMMON_FLAGS_LIST) +$(IB_UMAD_DBGSYM)_DEP_FILES := $(DEP_FILES) +endif + +# DPDK packages + +SPATH := $($(DPDK)_SRC_PATH) +DEP_FILES := $(SDK_COMMON_FILES_LIST) +DEP_FILES += $(shell git ls-files -- $(SPATH)) + +$(DPDK)_CACHE_MODE := GIT_CONTENT_SHA +$(DPDK)_DEP_FLAGS := $(SDK_COMMON_FLAGS_LIST) +$(DPDK)_DEP_FILES := $(DEP_FILES) + +$(DPDK_DEV)_CACHE_MODE := GIT_CONTENT_SHA +$(DPDK_DEV)_DEP_FLAGS := $(SDK_COMMON_FLAGS_LIST) +$(DPDK_DEV)_DEP_FILES := $(DEP_FILES) + +# Collectx CLXAPI + +FLAGS := $($(COLLECTX_CLXAPI)_URL) +DEP_FILES := $(SDK_COMMON_FILES_LIST) + +$(COLLECTX_CLXAPI)_CACHE_MODE := GIT_CONTENT_SHA +$(COLLECTX_CLXAPI)_DEP_FLAGS := $(SONIC_COMMON_FLAGS_LIST) $(FLAGS) +$(COLLECTX_CLXAPI)_DEP_FILES := $(DEP_FILES) + +# RXP compiler + +SPATH := $($(RXPCOMPILER)_SRC_PATH) +DEP_FILES := $(SDK_COMMON_FILES_LIST) +DEP_FILES += $(shell git ls-files -- $(SPATH)) + +$(RXPCOMPILER)_CACHE_MODE := GIT_CONTENT_SHA +$(RXPCOMPILER)_DEP_FLAGS := $(SDK_COMMON_FLAGS_LIST) +$(RXPCOMPILER)_DEP_FILES := $(DEP_FILES) + +$(LIBRXPCOMPILER_DEV)_CACHE_MODE := GIT_CONTENT_SHA +$(LIBRXPCOMPILER_DEV)_DEP_FLAGS := $(SDK_COMMON_FLAGS_LIST) +$(LIBRXPCOMPILER_DEV)_DEP_FILES := $(DEP_FILES) + +# UCX + +SPATH := $($(UCX)_SRC_PATH) +DEP_FILES := $(SDK_COMMON_FILES_LIST) +DEP_FILES += $(shell git ls-files -- $(SPATH)) + +$(UCX)_CACHE_MODE := GIT_CONTENT_SHA +$(UCX)_DEP_FLAGS := $(SDK_COMMON_FLAGS_LIST) +$(UCX)_DEP_FILES := $(DEP_FILES) + +# GRPC + +SPATH := $($(LIBGRPC_DEV)_SRC_PATH) +DEP_FILES := $(SDK_COMMON_FILES_LIST) +DEP_FILES += $(shell git ls-files -- $(SPATH)) + +$(LIBGRPC_DEV)_CACHE_MODE := GIT_CONTENT_SHA +$(LIBGRPC_DEV)_DEP_FLAGS := $(SDK_COMMON_FLAGS_LIST) +$(LIBGRPC_DEV)_DEP_FILES := $(DEP_FILES) + +$(LIBGRPC_DBG)_CACHE_MODE := GIT_CONTENT_SHA +$(LIBGRPC_DBG)_DEP_FLAGS := $(SDK_COMMON_FLAGS_LIST) +$(LIBGRPC_DBG)_DEP_FILES := $(DEP_FILES) + +# DOCA + +SPATH := $($(DOCA_LIBS)_SRC_PATH) +DEP_FILES := $(SDK_COMMON_FILES_LIST) +DEP_FILES += $(shell git ls-files -- $(SPATH)) + +$(DOCA_LIBS)_CACHE_MODE := GIT_CONTENT_SHA +$(DOCA_LIBS)_DEP_FLAGS := $(SDK_COMMON_FLAGS_LIST) +$(DOCA_LIBS)_DEP_FILES := $(DEP_FILES) + +$(DOCA_LIBS_DEV)_CACHE_MODE := GIT_CONTENT_SHA +$(DOCA_LIBS_DEV)_DEP_FLAGS := $(SDK_COMMON_FLAGS_LIST) +$(DOCA_LIBS_DEV)_DEP_FILES := $(DEP_FILES) + +ifeq ($(SDK_FROM_SRC),y) +$(DOCA_LIBS_DBG)_CACHE_MODE := GIT_CONTENT_SHA +$(DOCA_LIBS_DBG)_DEP_FLAGS := $(SDK_COMMON_FLAGS_LIST) +$(DOCA_LIBS_DBG)_DEP_FILES := $(DEP_FILES) +endif + +# SDN appliance + +SPATH := $($(SDN_APPL)_SRC_PATH) +DEP_FILES := $(SDK_COMMON_FILES_LIST) +DEP_FILES += $(shell git ls-files -- $(SPATH)) + +$(SDN_APPL)_CACHE_MODE := GIT_CONTENT_SHA +$(SDN_APPL)_DEP_FLAGS := $(SDK_COMMON_FLAGS_LIST) +$(SDN_APPL)_DEP_FILES := $(DEP_FILES) diff --git a/platform/nvidia-bluefield/recipes/sdk.mk b/platform/nvidia-bluefield/recipes/sdk.mk new file mode 100644 index 00000000000..d2a35a30feb --- /dev/null +++ b/platform/nvidia-bluefield/recipes/sdk.mk @@ -0,0 +1,331 @@ +# +# Copyright (c) 2024 NVIDIA CORPORATION & AFFILIATES. +# Apache-2.0 +# +# Licensed under the Apache License, Version 2.0 (the "License"); +# you may not use this file except in compliance with the License. +# You may obtain a copy of the License at +# +# http://www.apache.org/licenses/LICENSE-2.0 +# +# Unless required by applicable law or agreed to in writing, software +# distributed under the License is distributed on an "AS IS" BASIS, +# WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied. +# See the License for the specific language governing permissions and +# limitations under the License. +# + +SDK_BASE_PATH = $(PLATFORM_PATH)/sdk-src/sonic-bluefield-packages/bin + +# Place here URL where SDK sources exist +SDK_SOURCE_BASE_URL = +SDK_VERSION = 24.1-RC3 + +SDK_COLLECTX_URL = https://linux.mellanox.com/public/repo/doca/1.5.2/debian12/aarch64/ + +SDK_GH_BASE_URL = https://github.com/Mellanox/sonic-bluefield-packages/releases/download/dpu-sdk-$(SDK_VERSION)-$(BLDENV)/ + +define make_url_sdk + $(1)_URL="$(SDK_GH_BASE_URL)/$(1)" + +endef + +define get_sdk_version_file_gh + $(shell wget --quiet $(1) -O $(2)) + +endef + +ifneq ($(SDK_SOURCE_BASE_URL), ) +SDK_FROM_SRC = y +SDK_SOURCE_URL = $(SDK_SOURCE_BASE_URL)/$(subst -,/,$(SDK_VERSION)) +SDK_VERSIONS_FILE = $(PLATFORM_PATH)/sdk-src/VERSIONS +$(eval $(call get_sdk_version_file_gh, "$(SDK_SOURCE_URL)/VERSIONS_FOR_SONIC_BUILD", $(SDK_VERSIONS_FILE))) +else +SDK_FROM_SRC = n +SDK_VERSIONS_FILE = $(PLATFORM_PATH)/sdk-src/VERSIONS +$(eval $(call get_sdk_version_file_gh, "$(SDK_GH_BASE_URL)/VERSIONS_FOR_SONIC_BUILD", $(SDK_VERSIONS_FILE))) +endif + +export SDK_VERSION SDK_SOURCE_URL + +define get_sdk_package_version_short +$(shell $(PLATFORM_PATH)/recipes/get_sdk_package_version.sh -s $(SDK_VERSIONS_FILE) $(1)) +endef + +define get_sdk_package_version_full +$(shell $(PLATFORM_PATH)/recipes/get_sdk_package_version.sh $(SDK_VERSIONS_FILE) $(1)) +endef + +SDK_DEBS = +SDK_SRC_TARGETS = +SDK_ONLINE_TARGETS = + +# OFED and derived packages + +OFED_VER_SHORT = $(call get_sdk_package_version_short,"ofed") +OFED_VER_FULL = $(call get_sdk_package_version_full,"ofed") +OFED_KERNEL_VER_SHORT = $(call get_sdk_package_version_short,"mlnx-ofed-kernel") +OFED_KERNEL_VER_FULL = $(call get_sdk_package_version_full,"mlnx-ofed-kernel") +MLNX_TOOLS_VER = $(call get_sdk_package_version_full,"mlnx-tools") + +MLNX_TOOLS = mlnx-tools_$(MLNX_TOOLS_VER)_arm64.deb +$(MLNX_TOOLS)_SRC_PATH = $(PLATFORM_PATH)/sdk-src/ofed + +OFED_KERNEL_UTILS = mlnx-ofed-kernel-utils_$(OFED_KERNEL_VER_FULL)-1_arm64.deb + +$(eval $(call add_derived_package,$(MLNX_TOOLS),$(OFED_KERNEL_UTILS))) + +OFED_KERNEL_DKMS = mlnx-ofed-kernel-dkms_$(OFED_KERNEL_VER_SHORT)-1_all.deb +$(OFED_KERNEL_DKMS)_DEPENDS = $(OFED_KERNEL_UTILS) + +$(eval $(call add_derived_package,$(MLNX_TOOLS),$(OFED_KERNEL_DKMS))) + +OFED_KERNEL = mlnx-ofed-kernel-modules-$(KVERSION)_$(OFED_KERNEL_VER_SHORT)_$(BUILD_ARCH).deb +$(OFED_KERNEL)_SRC_PATH = $(PLATFORM_PATH)/sdk-src/ofed +$(OFED_KERNEL)_DEPENDS = $(LINUX_HEADERS) $(LINUX_HEADERS_COMMON) + +ifeq ($(SDK_FROM_SRC), y) +$(OFED_KERNEL)_DEPENDS += $(OFED_KERNEL_DKMS) +endif + +export OFED_VER_SHORT OFED_VER_FULL OFED_KERNEL OFED_KERNEL_UTILS OFED_KERNEL_VER_FULL MLNX_TOOLS OFED_KERNEL_DKMS + +SDK_DEBS += $(OFED_KERNEL) $(MLNX_TOOLS) $(OFED_KERNEL_UTILS) +SDK_SRC_TARGETS += $(OFED_KERNEL) $(MLNX_TOOLS) + +# MLNX iproute2 +MLNX_IPROUTE2_VER = $(call get_sdk_package_version_full,"mlnx-iproute2") + +MLNX_IPROUTE2 = mlnx-iproute2_$(MLNX_IPROUTE2_VER)_arm64.deb +$(MLNX_IPROUTE2)_SRC_PATH = $(PLATFORM_PATH)/sdk-src/mlnx-iproute2 + +export MLNX_IPROUTE2_VER MLNX_IPROUTE2 + +MLNX_IPROUTE2_DERIVED_DEBS = + +export MLNX_IPROUTE2_DERIVED_DEBS + +SDK_DEBS += $(MLNX_IPROUTE2) $(MLNX_IPROUTE2_DERIVED_DEBS) +SDK_SRC_TARGETS += $(MLNX_IPROUTE2) + +# RDMA and derived packages + +RDMA_CORE_VER = $(call get_sdk_package_version_full,"rdma-core") +RDMA_CORE = rdma-core_${RDMA_CORE_VER}_${CONFIGURED_ARCH}.deb +$(RDMA_CORE)_SRC_PATH = $(PLATFORM_PATH)/sdk-src/rdma +$(RDMA_CORE)_RDEPENDS = $(LIBNL3) +$(RDMA_CORE)_DEPENDS = $(LIBNL3_DEV) $(LIBNL_ROUTE3_DEV) +RDMA_CORE_DBGSYM = rdma-core-dbgsym_${RDMA_CORE_VER}_${CONFIGURED_ARCH}.deb + +IB_VERBS_PROV = ibverbs-providers_${RDMA_CORE_VER}_${CONFIGURED_ARCH}.deb +$(IB_VERBS_PROV)_DEPENDS = $(LIBNL3_DEV) $(LIBNL_ROUTE3_DEV) +IB_VERBS_PROV_DBGSYM = ibverbs-providers-dbgsym_${RDMA_CORE_VER}_${CONFIGURED_ARCH}.deb + +IB_VERBS = libibverbs1_${RDMA_CORE_VER}_${CONFIGURED_ARCH}.deb +$(IB_VERBS)_DEPENDS = $(LIBNL3_DEV) $(LIBNL_ROUTE3_DEV) +IB_VERBS_DEV = libibverbs-dev_${RDMA_CORE_VER}_${CONFIGURED_ARCH}.deb +$(IB_VERBS_DEV)_DEPENDS = $(IB_VERBS) $(IB_VERBS_PROV) +IB_VERBS_DBGSYM = libibverbs1-dbg_${RDMA_CORE_VER}_${CONFIGURED_ARCH}.deb + +IB_UMAD = libibumad3_${RDMA_CORE_VER}_${CONFIGURED_ARCH}.deb +IB_UMAD_DEV = libibumad-dev_${RDMA_CORE_VER}_${CONFIGURED_ARCH}.deb +IB_UMAD_DBGSYM = libibumad3-dbg_${RDMA_CORE_VER}_${CONFIGURED_ARCH}.deb + +RDMACM = librdmacm1_${RDMA_CORE_VER}_${CONFIGURED_ARCH}.deb +RDMACM_DEV = librdmacm-dev_${RDMA_CORE_VER}_${CONFIGURED_ARCH}.deb +$(RDMACM_DEV)_DEPENDS = $(RDMACM) $(IB_VERBS_DEV) +RDMACM_DBGSYM = librdmacm1-dbg_${RDMA_CORE_VER}_${CONFIGURED_ARCH}.deb + +$(eval $(call add_derived_package,$(RDMA_CORE),$(IB_VERBS_PROV))) +$(eval $(call add_derived_package,$(RDMA_CORE),$(IB_VERBS))) +$(eval $(call add_derived_package,$(RDMA_CORE),$(IB_VERBS_DEV))) +$(eval $(call add_derived_package,$(RDMA_CORE),$(IB_UMAD))) +$(eval $(call add_derived_package,$(RDMA_CORE),$(IB_UMAD_DEV))) +$(eval $(call add_derived_package,$(RDMA_CORE),$(RDMACM))) +$(eval $(call add_derived_package,$(RDMA_CORE),$(RDMACM_DEV))) + +ifeq ($(SDK_FROM_SRC),y) +$(eval $(call add_derived_package,$(RDMA_CORE),$(RDMA_CORE_DBGSYM))) +$(eval $(call add_derived_package,$(RDMA_CORE),$(IB_VERBS_PROV_DBGSYM))) +$(eval $(call add_derived_package,$(RDMA_CORE),$(IB_VERBS_DBGSYM))) +$(eval $(call add_derived_package,$(RDMA_CORE),$(IB_UMAD_DBGSYM))) +$(eval $(call add_derived_package,$(RDMA_CORE),$(RDMACM_DBGSYM))) +endif + +export RDMA_CORE RDMA_CORE_DBGSYM +export IB_VERBS IB_VERBS_DEV IB_VERBS_DBGSYM +export IB_VERBS_PROV IB_VERBS_PROV_DBGSYM +export IB_UMAD IB_UMAD_DEV IB_UMAD_DBGSYM +export RDMACM RDMACM_DEV RDMACM_DBGSYM + +RDMA_CORE_DERIVED_DEBS = $(RDMA_CORE_DBGSYM) \ + $(IB_VERBS) \ + $(IB_VERBS_DEV) \ + $(IB_VERBS_DBGSYM) \ + $(IB_VERBS_PROV) \ + $(IB_VERBS_PROV_DBGSYM) \ + $(IB_UMAD) \ + $(IB_UMAD_DEV) \ + $(IB_UMAD_DBGSYM) \ + $(RDMACM) \ + $(RDMACM_DEV) \ + $(RDMACM_DBGSYM) + +export RDMA_CORE_DERIVED_DEBS + +SDK_DEBS += $(RDMA_CORE) $(RDMA_CORE_DERIVED_DEBS) +SDK_SRC_TARGETS += $(RDMA_CORE) + +# FlexIO + +#FLEXIO_VER = $(call get_sdk_package_version_full,"flexio") +# +#FLEXIO = flexio_$(FLEXIO_VER)_arm64.deb +#$(FLEXIO)_SRC_PATH = $(PLATFORM_PATH)/sdk-src/flexio +#$(FLEXIO)_DEPENDS = $(IB_VERBS_PROV) $(IB_VERBS) $(IB_VERBS_DEV) +#$(FLEXIO)_RDEPENDS = $(IB_VERBS_PROV) $(IB_VERBS) $(IB_VERBS_DEV) +# +#export FLEXIO_VER FLEXIO + +SDK_DEBS += $(FLEXIO) +SDK_SRC_TARGETS += $(FLEXIO) + +# DPDK and derived packages + +DPDK_VER = $(call get_sdk_package_version_full,"dpdk") + +DPDK = mlnx-dpdk_${DPDK_VER}_${CONFIGURED_ARCH}.deb +$(DPDK)_SRC_PATH = $(PLATFORM_PATH)/sdk-src/dpdk +$(DPDK)_DEPENDS = $(FLEXIO) +$(DPDK)_RDEPENDS = $(FLEXIO) $(IB_VERBS_PROV) $(IB_VERBS) $(IB_VERBS_DEV) + +DPDK_DEV = mlnx-dpdk-dev_${DPDK_VER}_${CONFIGURED_ARCH}.deb +$(DPDK)_DEPENDS = $(RDMA_CORE) $(IB_VERBS_PROV) $(IB_VERBS) $(IB_VERBS_DEV) $(FLEXIO) +$(DPDK_DEV)_RDEPENDS = $(DPDK) $(FLEXIO) + +$(eval $(call add_derived_package,$(DPDK),$(DPDK_DEV))) + +export DPDK DPDK_DEV + +DPDK_DERIVED_DEBS = $(DPDK_DEV) +export DPDK_DERIVED_DEBS + +SDK_DEBS += $(DPDK) $(DPDK_DERIVED_DEBS) +SDK_SRC_TARGETS += $(DPDK) + +# Collectx + +COLLECTX_CLXAPI = collectx_1.14.3-9642347-debian12.1-aarch64-clxapi.deb +$(COLLECTX_CLXAPI)_URL = $(SDK_COLLECTX_URL)/collectx_1.14.3-9642347-debian12.1-aarch64-clxapi.deb +$(COLLECTX_CLXAPI)_RDEPENDS = $(IB_UMAD) + +COLLECTX_CLXAPI_DEV = collectx_1.14.3-9642347-debian12.1-aarch64-clxapidev.deb +$(COLLECTX_CLXAPI_DEV)_URL = $(SDK_COLLECTX_URL)/collectx_1.14.3-9642347-debian12.1-aarch64-clxapidev.deb +$(COLLECTX_CLXAPI_DEV)_DEPENDS = $(COLLECTX_CLXAPI) +$(COLLECTX_CLXAPI_DEV)_RDEPENDS = $(IB_UMAD) + +SDK_DEBS += $(COLLECTX_CLXAPI) $(COLLECTX_CLXAPI_DEV) +SDK_ONLINE_TARGETS += $(COLLECTX_CLXAPI) $(COLLECTX_CLXAPI_DEV) + +# RXP compiler and derived packages + +RXPCOMPILER_VER = $(call get_sdk_package_version_full,"rxp-tools") + +RXPCOMPILER = rxp-compiler_$(RXPCOMPILER_VER)_arm64.deb +$(RXPCOMPILER)_SRC_PATH = $(PLATFORM_PATH)/sdk-src/rxp-compiler +LIBRXPCOMPILER_DEV = librxpcompiler-dev_$(RXPCOMPILER_VER)_arm64.deb + +$(eval $(call add_derived_package,$(RXPCOMPILER),$(LIBRXPCOMPILER_DEV))) + +export RXPCOMPILER LIBRXPCOMPILER_DEV + +RXPCOMPILER_DERIVED_DEBS = $(LIBRXPCOMPILER_DEV) +export RXPCOMPILER_DERIVED_DEBS + +SDK_DEBS += $(RXPCOMPILER) $(RXPCOMPILER_DERIVED_DEBS) +SDK_SRC_TARGETS += $(RXPCOMPILER) + +# UCX and derived packages + +UCX_VER = $(call get_sdk_package_version_full,"ucx") + +UCX = ucx_$(UCX_VER)_arm64.deb +$(UCX)_DEPENDS = $(IB_VERBS_PROV) $(IB_VERBS) $(IB_VERBS_DEV) $(RDMACM) $(RDMACM_DEV) +$(UCX)_RDEPENDS = $(IB_VERBS_PROV) $(IB_VERBS) +$(UCX)_SRC_PATH = $(PLATFORM_PATH)/sdk-src/ucx + +export UCX_VER UCX + +SDK_DEBS += $(UCX) +SDK_SRC_TARGETS += $(UCX) + +# GRPC and derived packages + +LIBGRPC_VER = $(call get_sdk_package_version_full,"grpc") + +LIBGRPC_DEV = libgrpc-dev_$(LIBGRPC_VER)_arm64.deb +$(LIBGRPC_DEV)_SRC_PATH = $(PLATFORM_PATH)/sdk-src/grpc +LIBGRPC_DBG = libgrpc-dev-dbgsym_$(LIBGRPC_VER)_arm64.deb + +$(eval $(call add_derived_package,$(LIBGRPC_DEV),$(LIBGRPC_DBG))) + +export LIBGRPC_DEV LIBGRPC_DBG LIBGRPC_VER + +LIBGRPC_DERIVED_DEBS = $(LIBGRPC_DBG) +export LIBGRPC_DERIVED_DEBS + +SDK_DEBS += $(LIBGRPC_DEV) $(LIBGRPC_DERIVED_DEBS) +SDK_SRC_TARGETS += $(LIBGRPC_DEV) + +# DOCA and derived packages + +DOCA_VERSION = $(call get_sdk_package_version_full,"doca") +DOCA_DEB_VERSION = $(DOCA_VERSION)-1 + +DOCA_LIBS = doca-libs_${DOCA_DEB_VERSION}_${CONFIGURED_ARCH}.deb +$(DOCA_LIBS)_SRC_PATH = $(PLATFORM_PATH)/sdk-src/doca +$(DOCA_LIBS)_RDEPENDS = $(DPDK) $(COLLECTX_CLXAPI) $(RXPCOMPILER) $(LIBRXPCOMPILER_DEV) $(UCX) $(LIBGRPC_DEV) $(FLEXIO) +$(DOCA_LIBS)_DEPENDS = $(COLLECTX_CLXAPI) $(COLLECTX_CLXAPI_DEV) $(RXPCOMPILER) $(LIBRXPCOMPILER_DEV) $(UCX) $(DPDK_DEV) $(LIBGRPC_DEV) $(FLEXIO) +DOCA_LIBS_DEV = libdoca-libs-dev_${DOCA_DEB_VERSION}_${CONFIGURED_ARCH}.deb +DOCA_LIBS_DBG = doca-libs-dbgsym_${DOCA_DEB_VERSION}_${CONFIGURED_ARCH}.deb + +$(eval $(call add_derived_package,$(DOCA_LIBS),$(DOCA_LIBS_DEV))) +$(eval $(call add_derived_package,$(DOCA_LIBS),$(DOCA_LIBS_DBG))) + +export DOCA_LIBS DOCA_LIBS_DEV DOCA_LIBS_DBG + +DOCA_LIBS_DERIVED_DEBS = $(DOCA_LIBS_DEV) $(DOCA_LIBS_DBG) +export DOCA_LIBS_DERIVED_DEBS + +SDK_DEBS += $(DOCA_LIBS) $(DOCA_LIBS_DERIVED_DEBS) +SDK_SRC_TARGETS += $(DOCA_LIBS) + +# SDN Appliance + +SDN_APPL_VER=$(call get_sdk_package_version_full,"nasa") +SDN_APPL = sdn-appliance_${SDN_APPL_VER}_${CONFIGURED_ARCH}.deb +$(SDN_APPL)_SRC_PATH = $(PLATFORM_PATH)/sdk-src/sdn +$(SDN_APPL)_RDEPENDS = $(DOCA_LIBS) $(FLEXIO) $(MLNX_TOOLS) $(OFED_KERNEL_UTILS) $(MLNX_IPROUTE2) +$(SDN_APPL)_DEPENDS = $(DOCA_LIBS_DEV) $(DOCA_LIBS) $(DPDK_DEV) $(FLEXIO) $(MLNX_TOOLS) $(OFED_KERNEL_UTILS) + +export SDN_APPL + +SDN_APPL_DERIVED_DEBS = +export SDN_APPL_DERIVED_DEBS + +SDK_DEBS += $(SDN_APPL) $(SDN_APPL_DERIVED_DEBS) +SDK_SRC_TARGETS += $(SDN_APPL) + +ifeq ($(SDK_FROM_SRC), y) +SONIC_MAKE_DEBS += $(SDK_SRC_TARGETS) +SONIC_ONLINE_DEBS += $(SDK_ONLINE_TARGETS) +else +$(eval $(foreach deb,$(SDK_SRC_TARGETS) $(SDK_ONLINE_TARGETS) $(SDK_DEBS),$(call make_url_sdk,$(deb)))) +SONIC_ONLINE_DEBS += $(SDK_SRC_TARGETS) $(SDK_ONLINE_TARGETS) +endif + +SDK_PACKAGES = $(OFED_KERNEL) $(OFED_KERNEL_UTILS) $(MLNX_IPROUTE2) $(SDK_ONLINE_TARGETS) $(SDK_SRC_TARGETS) + +sdk-packages: $(addprefix $(DEBS_PATH)/, $(SDK_PACKAGES)) + +SONIC_PHONY_TARGETS += sdk-packages diff --git a/platform/nvidia-bluefield/rules.dep b/platform/nvidia-bluefield/rules.dep new file mode 100644 index 00000000000..d9238a576ec --- /dev/null +++ b/platform/nvidia-bluefield/rules.dep @@ -0,0 +1,28 @@ +# +# Copyright (c) 2024 NVIDIA CORPORATION & AFFILIATES. +# Apache-2.0 +# +# Licensed under the Apache License, Version 2.0 (the "License"); +# you may not use this file except in compliance with the License. +# You may obtain a copy of the License at +# +# http://www.apache.org/licenses/LICENSE-2.0 +# +# Unless required by applicable law or agreed to in writing, software +# distributed under the License is distributed on an "AS IS" BASIS, +# WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied. +# See the License for the specific language governing permissions and +# limitations under the License. +# + +RECIPE_DIR = recipes + +export RECIPE_DIR + +include $(PLATFORM_PATH)/$(RECIPE_DIR)/bluefield-soc.dep +include $(PLATFORM_PATH)/$(RECIPE_DIR)/mft.dep +include $(PLATFORM_PATH)/$(RECIPE_DIR)/fw.dep +include $(PLATFORM_PATH)/$(RECIPE_DIR)/dpu-sai.dep +include $(PLATFORM_PATH)/$(RECIPE_DIR)/platform-api.dep +include $(PLATFORM_PATH)/$(RECIPE_DIR)/installer-image.dep +include $(PLATFORM_PATH)/$(RECIPE_DIR)/sdk.dep diff --git a/platform/nvidia-bluefield/rules.mk b/platform/nvidia-bluefield/rules.mk new file mode 100644 index 00000000000..e4cedfa28fa --- /dev/null +++ b/platform/nvidia-bluefield/rules.mk @@ -0,0 +1,39 @@ +# +# Copyright (c) 2024 NVIDIA CORPORATION & AFFILIATES. +# Apache-2.0 +# +# Licensed under the Apache License, Version 2.0 (the "License"); +# you may not use this file except in compliance with the License. +# You may obtain a copy of the License at +# +# http://www.apache.org/licenses/LICENSE-2.0 +# +# Unless required by applicable law or agreed to in writing, software +# distributed under the License is distributed on an "AS IS" BASIS, +# WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied. +# See the License for the specific language governing permissions and +# limitations under the License. +# + +RECIPE_DIR = recipes + +override TARGET_BOOTLOADER=grub + +include $(PLATFORM_PATH)/$(RECIPE_DIR)/bluefield-soc.mk +include $(PLATFORM_PATH)/$(RECIPE_DIR)/mft.mk +include $(PLATFORM_PATH)/$(RECIPE_DIR)/fw.mk +include $(PLATFORM_PATH)/$(RECIPE_DIR)/dpu-sai.mk +include $(PLATFORM_PATH)/$(RECIPE_DIR)/sdk.mk +include $(PLATFORM_PATH)/$(RECIPE_DIR)/platform-api.mk +include $(PLATFORM_PATH)/$(RECIPE_DIR)/docker-syncd-bluefield.mk +include $(PLATFORM_PATH)/$(RECIPE_DIR)/installer-image.mk + +# Inject DPU sai into syncd +$(SYNCD)_DEPENDS += $(DPU_SAI) +$(SYNCD)_UNINSTALLS += $(DPU_SAI) + +# Runtime dependency on DPU sai is set only for syncd +$(SYNCD)_RDEPENDS += $(DPU_SAI) + +# Inject mft into platform monitor +$(DOCKER_PLATFORM_MONITOR)_DEPENDS += $(MFT) diff --git a/platform/nvidia-bluefield/sdhci-of-dwcmshc/.gitignore b/platform/nvidia-bluefield/sdhci-of-dwcmshc/.gitignore new file mode 100644 index 00000000000..6dbdff4573b --- /dev/null +++ b/platform/nvidia-bluefield/sdhci-of-dwcmshc/.gitignore @@ -0,0 +1,5 @@ +# Ignore everything in this directory +* +# Except these files +!.gitignore +!Makefile diff --git a/platform/nvidia-bluefield/sdhci-of-dwcmshc/Makefile b/platform/nvidia-bluefield/sdhci-of-dwcmshc/Makefile new file mode 100644 index 00000000000..f5fe67ffd64 --- /dev/null +++ b/platform/nvidia-bluefield/sdhci-of-dwcmshc/Makefile @@ -0,0 +1,44 @@ +# +# Copyright (c) 2024 NVIDIA CORPORATION & AFFILIATES. +# Apache-2.0 +# +# Licensed under the Apache License, Version 2.0 (the "License"); +# you may not use this file except in compliance with the License. +# You may obtain a copy of the License at +# +# http://www.apache.org/licenses/LICENSE-2.0 +# +# Unless required by applicable law or agreed to in writing, software +# distributed under the License is distributed on an "AS IS" BASIS, +# WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied. +# See the License for the specific language governing permissions and +# limitations under the License. +# + +.ONESHELL: +SHELL = /bin/bash +.SHELLFLAGS += -ex + +SDHCI_OF_DWCMSHC = sdhci-of-dwcmshc-${SDHCI_OF_DWCMSHC_DRIVER_VERSION} + +MAIN_TARGET = $(SDHCI_OF_DWCMSHC_DRIVER) +DERIVED_TARGETS = +GET_PACKAGE := $(shell pwd)/../recipes/get-soc-package.sh + +$(addprefix $(DEST)/, $(MAIN_TARGET)): $(DEST)/% : + rm -rf ./tmp/ + mkdir ./tmp/ + pushd ./tmp/ + + ${GET_PACKAGE} ${BSD_BASE_SOURCE_URL} ${SDHCI_OF_DWCMSHC} + + pushd ${SDHCI_OF_DWCMSHC} + find . -type f -exec touch {} + + + # Build the Debs + KVER=$(KVERSION) WITH_DKMS=0 dpkg-buildpackage -rfakeroot -us -uc -b -j$(SONIC_CONFIG_MAKE_JOBS) --admindir $(SONIC_DPKG_ADMINDIR) + + mv $(DERIVED_TARGETS) $* $(DEST)/ + popd + +$(addprefix $(DEST)/, $(DERIVED_TARGETS)): $(DEST)/% : $(DEST)/$(MAIN_TARGET) diff --git a/platform/nvidia-bluefield/sdk-src/doca/.gitignore b/platform/nvidia-bluefield/sdk-src/doca/.gitignore new file mode 100644 index 00000000000..6dbdff4573b --- /dev/null +++ b/platform/nvidia-bluefield/sdk-src/doca/.gitignore @@ -0,0 +1,5 @@ +# Ignore everything in this directory +* +# Except these files +!.gitignore +!Makefile diff --git a/platform/nvidia-bluefield/sdk-src/doca/0001-Allow-compilation-with-warnings.patch b/platform/nvidia-bluefield/sdk-src/doca/0001-Allow-compilation-with-warnings.patch new file mode 100644 index 00000000000..59893a07a01 --- /dev/null +++ b/platform/nvidia-bluefield/sdk-src/doca/0001-Allow-compilation-with-warnings.patch @@ -0,0 +1,13 @@ +diff --git a/meson.build b/meson.build +index 06e71ab..c674944 100644 +--- a/meson.build ++++ b/meson.build +@@ -16,7 +16,7 @@ project('DOCA', 'C', 'CPP', + version: run_command(find_program('cat', 'more'), files('VERSION'), check: true).stdout().strip(), + default_options: [ + 'buildtype=debug', +- 'werror=true', ++ 'werror=false', + 'warning_level=2', + 'b_staticpic=true', + 'prefix=/opt/mellanox/doca', diff --git a/platform/nvidia-bluefield/sdk-src/doca/Makefile b/platform/nvidia-bluefield/sdk-src/doca/Makefile new file mode 100644 index 00000000000..e3bc80c06e6 --- /dev/null +++ b/platform/nvidia-bluefield/sdk-src/doca/Makefile @@ -0,0 +1,49 @@ +# +# Copyright (c) 2024 NVIDIA CORPORATION & AFFILIATES. +# Apache-2.0 +# +# Licensed under the Apache License, Version 2.0 (the "License"); +# you may not use this file except in compliance with the License. +# You may obtain a copy of the License at +# +# http://www.apache.org/licenses/LICENSE-2.0 +# +# Unless required by applicable law or agreed to in writing, software +# distributed under the License is distributed on an "AS IS" BASIS, +# WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied. +# See the License for the specific language governing permissions and +# limitations under the License. +# + +.ONESHELL: +SHELL = /bin/bash + +MAIN_TARGET = $(DOCA_LIBS) +DERIVED_TARGETS = $(DOCA_LIBS_DEV) $(DOCA_LIBS_DBG) + +$(addprefix $(DEST)/, $(MAIN_TARGET)): $(DEST)/% : + # Make sure errors will be reported + set -e + + # get sources + rm -rf doca/ doca.zip + + # get sources + wget $(SDK_SOURCE_URL)/doca.zip + unzip doca.zip + + pushd doca/ + find . -type f -exec touch {} + + + patch -p1 < ../0001-Allow-compilation-with-warnings.patch + patch -p1 < ../0001-Remove-meson-from-dependencies.patch + source /etc/profile.d/libgrpc.sh + source /etc/profile.d/mlnx-dpdk-aarch64-linux-gnu.sh + + # Build the Debs + PATH=/opt/mellanox/grpc/bin:/usr/bin/:$(PATH) dpkg-buildpackage -us -uc -b -j$(SONIC_CONFIG_MAKE_JOBS) --admindir $(SONIC_DPKG_ADMINDIR) + + popd + mv $(DERIVED_TARGETS) $* $(DEST)/ + +$(addprefix $(DEST)/, $(DERIVED_TARGETS)): $(DEST)/% : $(DEST)/$(MAIN_TARGET) diff --git a/platform/nvidia-bluefield/sdk-src/dpdk/.gitignore b/platform/nvidia-bluefield/sdk-src/dpdk/.gitignore new file mode 100644 index 00000000000..6dbdff4573b --- /dev/null +++ b/platform/nvidia-bluefield/sdk-src/dpdk/.gitignore @@ -0,0 +1,5 @@ +# Ignore everything in this directory +* +# Except these files +!.gitignore +!Makefile diff --git a/platform/nvidia-bluefield/sdk-src/dpdk/Makefile b/platform/nvidia-bluefield/sdk-src/dpdk/Makefile new file mode 100644 index 00000000000..68a48b37f80 --- /dev/null +++ b/platform/nvidia-bluefield/sdk-src/dpdk/Makefile @@ -0,0 +1,45 @@ +# +# Copyright (c) 2024 NVIDIA CORPORATION & AFFILIATES. +# Apache-2.0 +# +# Licensed under the Apache License, Version 2.0 (the "License"); +# you may not use this file except in compliance with the License. +# You may obtain a copy of the License at +# +# http://www.apache.org/licenses/LICENSE-2.0 +# +# Unless required by applicable law or agreed to in writing, software +# distributed under the License is distributed on an "AS IS" BASIS, +# WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied. +# See the License for the specific language governing permissions and +# limitations under the License. +# + +.ONESHELL: +SHELL = /bin/bash + +MAIN_TARGET = $(DPDK) +DERIVED_TARGETS = $(DPDK_DEV) + +$(addprefix $(DEST)/, $(MAIN_TARGET)): $(DEST)/% : + # Make sure errors will be reported + set -e + + rm -rf dpdk.org/ dpdk.org.zip + + # get sources + wget $(SDK_SOURCE_URL)/dpdk.org.zip + unzip dpdk.org.zip + pushd dpdk.org/ + find . -type f -exec touch {} + + + patch -p1 < ../0001-Remove-meson-from-dependencies.patch + + # Build the package + # PATH variable is required for ninja to find the right version + DPDK_CONFIG_OPTIONS='--cross-file ../config/arm/arm64_bluefield_linux_gcc' DEB_BUILD_OPTIONS='dpdk_config_options=-Dmachine=0xd08' dpkg-buildpackage -us -uc -b -j$(SONIC_CONFIG_MAKE_JOBS) --admindir $(SONIC_DPKG_ADMINDIR) + + popd + mv $(DERIVED_TARGETS) $* $(DEST)/ + +$(addprefix $(DEST)/, $(DERIVED_TARGETS)): $(DEST)/% : $(DEST)/$(MAIN_TARGET) diff --git a/platform/nvidia-bluefield/sdk-src/flexio/.gitignore b/platform/nvidia-bluefield/sdk-src/flexio/.gitignore new file mode 100644 index 00000000000..6dbdff4573b --- /dev/null +++ b/platform/nvidia-bluefield/sdk-src/flexio/.gitignore @@ -0,0 +1,5 @@ +# Ignore everything in this directory +* +# Except these files +!.gitignore +!Makefile diff --git a/platform/nvidia-bluefield/sdk-src/flexio/Makefile b/platform/nvidia-bluefield/sdk-src/flexio/Makefile new file mode 100644 index 00000000000..019b1df8734 --- /dev/null +++ b/platform/nvidia-bluefield/sdk-src/flexio/Makefile @@ -0,0 +1,48 @@ +# +# Copyright (c) 2024 NVIDIA CORPORATION & AFFILIATES. +# Apache-2.0 +# +# Licensed under the Apache License, Version 2.0 (the "License"); +# you may not use this file except in compliance with the License. +# You may obtain a copy of the License at +# +# http://www.apache.org/licenses/LICENSE-2.0 +# +# Unless required by applicable law or agreed to in writing, software +# distributed under the License is distributed on an "AS IS" BASIS, +# WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied. +# See the License for the specific language governing permissions and +# limitations under the License. +# + +.ONESHELL: +SHELL = /bin/bash + +MAIN_TARGET = $(FLEXIO) +DERIVED_TARGETS = + +$(addprefix $(DEST)/, $(MAIN_TARGET)): $(DEST)/% : + # Make sure errors will be reported + set -e + + # get sources + rm -rf flexio-sdk/ flexio-sdk.zip + + # get sources + wget $(SDK_SOURCE_URL)/flexio-sdk.zip + unzip flexio-sdk.zip + + pushd flexio-sdk/ + find . -type f -exec touch {} + + + patch -p1 < ../0001-Allow-warning-during-package-compilation.patch + patch -p1 < ../0001-Install-LD-configuration.patch + patch -p1 < ../0001-Remove-meson-from-dependencies.patch + + # Build the Debs + dpkg-buildpackage -us -uc -b -j$(SONIC_CONFIG_MAKE_JOBS) --admindir $(SONIC_DPKG_ADMINDIR) + + popd + mv $(DERIVED_TARGETS) $* $(DEST)/ + +$(addprefix $(DEST)/, $(DERIVED_TARGETS)): $(DEST)/% : $(DEST)/$(MAIN_TARGET) diff --git a/platform/nvidia-bluefield/sdk-src/grpc/.gitignore b/platform/nvidia-bluefield/sdk-src/grpc/.gitignore new file mode 100644 index 00000000000..6dbdff4573b --- /dev/null +++ b/platform/nvidia-bluefield/sdk-src/grpc/.gitignore @@ -0,0 +1,5 @@ +# Ignore everything in this directory +* +# Except these files +!.gitignore +!Makefile diff --git a/platform/nvidia-bluefield/sdk-src/grpc/Makefile b/platform/nvidia-bluefield/sdk-src/grpc/Makefile new file mode 100644 index 00000000000..6fc434e3844 --- /dev/null +++ b/platform/nvidia-bluefield/sdk-src/grpc/Makefile @@ -0,0 +1,45 @@ +# +# Copyright (c) 2024 NVIDIA CORPORATION & AFFILIATES. +# Apache-2.0 +# +# Licensed under the Apache License, Version 2.0 (the "License"); +# you may not use this file except in compliance with the License. +# You may obtain a copy of the License at +# +# http://www.apache.org/licenses/LICENSE-2.0 +# +# Unless required by applicable law or agreed to in writing, software +# distributed under the License is distributed on an "AS IS" BASIS, +# WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied. +# See the License for the specific language governing permissions and +# limitations under the License. +# + +.ONESHELL: +SHELL = /bin/bash + +MAIN_TARGET = $(LIBGRPC_DEV) +DERIVED_TARGETS = $(LIBGRPC_DERIVED_DEBS) +LIBGRPC_TAR = libgrpc-dev_$(LIBGRPC_VER).tar.gz + +$(addprefix $(DEST)/, $(MAIN_TARGET)): $(DEST)/% : + # Make sure errors will be reported + set -e + + # get sources + rm -rf grpc/ $(LIBGRPC_TAR) + + # get sources + wget $(SDK_SOURCE_URL)/$(LIBGRPC_TAR) + tar xf $(LIBGRPC_TAR) + + pushd grpc/ + find . -type f -exec touch {} + + + # Build the Debs + dpkg-buildpackage -us -uc -b -j$(SONIC_CONFIG_MAKE_JOBS) --admindir $(SONIC_DPKG_ADMINDIR) + + popd + mv $(DERIVED_TARGETS) $* $(DEST)/ + +$(addprefix $(DEST)/, $(DERIVED_TARGETS)): $(DEST)/% : $(DEST)/$(MAIN_TARGET) diff --git a/platform/nvidia-bluefield/sdk-src/mlnx-iproute2/.gitignore b/platform/nvidia-bluefield/sdk-src/mlnx-iproute2/.gitignore new file mode 100644 index 00000000000..6dbdff4573b --- /dev/null +++ b/platform/nvidia-bluefield/sdk-src/mlnx-iproute2/.gitignore @@ -0,0 +1,5 @@ +# Ignore everything in this directory +* +# Except these files +!.gitignore +!Makefile diff --git a/platform/nvidia-bluefield/sdk-src/mlnx-iproute2/Makefile b/platform/nvidia-bluefield/sdk-src/mlnx-iproute2/Makefile new file mode 100644 index 00000000000..525e75b0924 --- /dev/null +++ b/platform/nvidia-bluefield/sdk-src/mlnx-iproute2/Makefile @@ -0,0 +1,46 @@ +# +# Copyright (c) 2024 NVIDIA CORPORATION & AFFILIATES. +# Apache-2.0 +# +# Licensed under the Apache License, Version 2.0 (the "License"); +# you may not use this file except in compliance with the License. +# You may obtain a copy of the License at +# +# http://www.apache.org/licenses/LICENSE-2.0 +# +# Unless required by applicable law or agreed to in writing, software +# distributed under the License is distributed on an "AS IS" BASIS, +# WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied. +# See the License for the specific language governing permissions and +# limitations under the License. +# + +.ONESHELL: +SHELL = /bin/bash + +MAIN_TARGET = $(MLNX_IPROUTE2) +DERIVED_TARGETS = $(MLNX_IPROUTE2_DERIVED_DEBS) + +OFED_TAR = MLNX_OFED_SRC-debian-$(OFED_VER_FULL).tgz +OFED_SRC = MLNX_OFED_SRC-$(OFED_VER_FULL) +MLNX_IPROUTE2_TAR = mlnx-iproute2_*.orig.tar.gz + +$(addprefix $(DEST)/, $(MAIN_TARGET)): $(DEST)/% : + # Make sure errors will be reported + set -e + + sudo rm -rf MLNX_OFED_SRC* + wget $(SDK_SOURCE_URL)/$(OFED_TAR) + tar xf $(OFED_TAR) + pushd $(OFED_SRC)/SOURCES + tar xf $(MLNX_IPROUTE2_TAR) + pushd mlnx-iproute2-*/ + find . -type f -exec touch {} + + + # Build the Debs + dpkg-buildpackage -us -uc -b -j$(SONIC_CONFIG_MAKE_JOBS) --admindir $(SONIC_DPKG_ADMINDIR) + + popd + mv $(DERIVED_TARGETS) $* $(DEST)/ + +$(addprefix $(DEST)/, $(DERIVED_TARGETS)): $(DEST)/% : $(DEST)/$(MAIN_TARGET) diff --git a/platform/nvidia-bluefield/sdk-src/ofed/.gitignore b/platform/nvidia-bluefield/sdk-src/ofed/.gitignore new file mode 100644 index 00000000000..6dbdff4573b --- /dev/null +++ b/platform/nvidia-bluefield/sdk-src/ofed/.gitignore @@ -0,0 +1,5 @@ +# Ignore everything in this directory +* +# Except these files +!.gitignore +!Makefile diff --git a/platform/nvidia-bluefield/sdk-src/ofed/Makefile b/platform/nvidia-bluefield/sdk-src/ofed/Makefile new file mode 100644 index 00000000000..b9485f4d426 --- /dev/null +++ b/platform/nvidia-bluefield/sdk-src/ofed/Makefile @@ -0,0 +1,87 @@ +# +# Copyright (c) 2024 NVIDIA CORPORATION & AFFILIATES. +# Apache-2.0 +# +# Licensed under the Apache License, Version 2.0 (the "License"); +# you may not use this file except in compliance with the License. +# You may obtain a copy of the License at +# +# http://www.apache.org/licenses/LICENSE-2.0 +# +# Unless required by applicable law or agreed to in writing, software +# distributed under the License is distributed on an "AS IS" BASIS, +# WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied. +# See the License for the specific language governing permissions and +# limitations under the License. +# + +.ONESHELL: +SHELL = /bin/bash +BUILD_ARCH = $(shell dpkg-architecture -qDEB_BUILD_ARCH) + +OFED_TAR = MLNX_OFED_SRC-debian-$(OFED_VER_FULL).tgz +OFED_SRC = MLNX_OFED_SRC-$(OFED_VER_FULL) + +DKMS_CTRL = /var/lib/dkms/mlnx-ofed-kernel/ +DKMS_TMP := $(shell mktemp -u -d -t dkms.XXXXXXXXXX) +UNAME_TMP := $(shell mktemp -u -d -t uname.XXXXXXXXXX) + +MLNX_TOOLS_TMP = /tmp/mlnx_tools_build/ + +$(addprefix $(DEST)/, $(MLNX_TOOLS)): $(DEST)/% : + # Make sure errors will be reported + set -e + mkdir -p $(MLNX_TOOLS_TMP) && pushd $(MLNX_TOOLS_TMP) + sudo rm -rf MLNX_OFED_SRC* + wget $(SDK_SOURCE_URL)/$(OFED_TAR) + tar xf $(OFED_TAR) + + pushd $(OFED_SRC)/ + find . -type f -exec touch {} + + + # Build the Debs + sudo ./install.pl --kernel-only --build-only --without-depcheck --force \ + --with-mlnx-tools --without-knem --without-knem-dkms \ + --without-kernel-mft-dkms + + sudo chown -R ${USER} ./* + + pushd DEBS/*/aarch64/ + chown ${USER} $(MLNX_TOOLS) $(OFED_KERNEL_UTILS) $(OFED_KERNEL_DKMS) + mv $(MLNX_TOOLS) $(OFED_KERNEL_UTILS) $(OFED_KERNEL_DKMS) $(DEST)/ + popd + + popd + popd + rm -rf $(MLNX_TOOLS_TMP) + +$(addprefix $(DEST)/, $(OFED_KERNEL_UTILS)): $(DEST)/% : $(DEST)/$(MLNX_TOOLS) +$(addprefix $(DEST)/, $(OFED_KERNEL_DKMS)): $(DEST)/% : $(DEST)/$(MLNX_TOOLS) + +$(addprefix $(DEST)/, $(OFED_KERNEL)): $(DEST)/% : + # Make sure errors will be reported + set -e + + # Prepare the directory to build mlnx-ofed-kernel-modules debian package + mkdir -p $(DKMS_TMP)/DEBIAN + mkdir -p $(DKMS_TMP)/lib/modules/$(KVERSION)/updates/dkms/ + export kversion="$(KVERSION)" + export mft_version="$(OFED_KERNEL_VER_FULL)" + j2 templates/control.j2 > $(DKMS_TMP)/DEBIAN/control + j2 templates/postinst.j2 > $(DKMS_TMP)/DEBIAN/postinst + j2 templates/postrm.j2 > $(DKMS_TMP)/DEBIAN/postrm + chmod +x $(DKMS_TMP)/DEBIAN/postinst + chmod +x $(DKMS_TMP)/DEBIAN/postrm + + sudo dkms build mlnx-ofed-kernel/$(OFED_KERNEL_VER_FULL) -k $(KVERSION) -a $(BUILD_ARCH) + + # copy the built modules + cp -r $(DKMS_CTRL)/kernel-$(KVERSION)-aarch64/module/*.ko \ + $(DKMS_TMP)/lib/modules/$(KVERSION)/updates/dkms/ + + dpkg -b $(DKMS_TMP) . + + chown ${USER} $(OFED_KERNEL) + mv $(OFED_KERNEL) $(DEST)/ + + rm -rf $(DKMS_TMP) diff --git a/platform/nvidia-bluefield/sdk-src/rdma/.gitignore b/platform/nvidia-bluefield/sdk-src/rdma/.gitignore new file mode 100644 index 00000000000..6dbdff4573b --- /dev/null +++ b/platform/nvidia-bluefield/sdk-src/rdma/.gitignore @@ -0,0 +1,5 @@ +# Ignore everything in this directory +* +# Except these files +!.gitignore +!Makefile diff --git a/platform/nvidia-bluefield/sdk-src/rdma/Makefile b/platform/nvidia-bluefield/sdk-src/rdma/Makefile new file mode 100644 index 00000000000..006c930b27d --- /dev/null +++ b/platform/nvidia-bluefield/sdk-src/rdma/Makefile @@ -0,0 +1,50 @@ +# +# Copyright (c) 2024 NVIDIA CORPORATION & AFFILIATES. +# Apache-2.0 +# +# Licensed under the Apache License, Version 2.0 (the "License"); +# you may not use this file except in compliance with the License. +# You may obtain a copy of the License at +# +# http://www.apache.org/licenses/LICENSE-2.0 +# +# Unless required by applicable law or agreed to in writing, software +# distributed under the License is distributed on an "AS IS" BASIS, +# WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied. +# See the License for the specific language governing permissions and +# limitations under the License. +# + +.ONESHELL: +SHELL = /bin/bash + +OFED_TAR = MLNX_OFED_SRC-debian-$(OFED_VER_FULL).tgz +OFED_SRC = MLNX_OFED_SRC-$(OFED_VER_FULL) +RDMA_TAR = rdma-core*.orig.tar.gz + +MAIN_TARGET = $(RDMA_CORE) +DERIVED_TARGETS = $(RDMA_CORE_DERIVED_DEBS) + +$(addprefix $(DEST)/, $(MAIN_TARGET)): $(DEST)/% : + # Make sure errors will be reported + set -e + + sudo rm -rf MLNX_OFED_SRC* + wget $(SDK_SOURCE_URL)/$(OFED_TAR) + tar xf $(OFED_TAR) + pushd $(OFED_SRC)/SOURCES + tar xf $(RDMA_TAR) + pushd rdma-core-*/ + find . -type f -exec touch {} + + + patch -p1 < ../../../disable-ibverb-dependencies.patch + + find . -type f -exec touch {} + + + # Build the Debs + dpkg-buildpackage -us -uc -b -j$(SONIC_CONFIG_MAKE_JOBS) --admindir $(SONIC_DPKG_ADMINDIR) + + popd + mv $(DERIVED_TARGETS) $* $(DEST)/ + +$(addprefix $(DEST)/, $(DERIVED_TARGETS)): $(DEST)/% : $(DEST)/$(MAIN_TARGET) diff --git a/platform/nvidia-bluefield/sdk-src/rxp-compiler/.gitignore b/platform/nvidia-bluefield/sdk-src/rxp-compiler/.gitignore new file mode 100644 index 00000000000..6dbdff4573b --- /dev/null +++ b/platform/nvidia-bluefield/sdk-src/rxp-compiler/.gitignore @@ -0,0 +1,5 @@ +# Ignore everything in this directory +* +# Except these files +!.gitignore +!Makefile diff --git a/platform/nvidia-bluefield/sdk-src/rxp-compiler/Makefile b/platform/nvidia-bluefield/sdk-src/rxp-compiler/Makefile new file mode 100644 index 00000000000..727f736d9aa --- /dev/null +++ b/platform/nvidia-bluefield/sdk-src/rxp-compiler/Makefile @@ -0,0 +1,44 @@ +# +# Copyright (c) 2024 NVIDIA CORPORATION & AFFILIATES. +# Apache-2.0 +# +# Licensed under the Apache License, Version 2.0 (the "License"); +# you may not use this file except in compliance with the License. +# You may obtain a copy of the License at +# +# http://www.apache.org/licenses/LICENSE-2.0 +# +# Unless required by applicable law or agreed to in writing, software +# distributed under the License is distributed on an "AS IS" BASIS, +# WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied. +# See the License for the specific language governing permissions and +# limitations under the License. +# + +.ONESHELL: +SHELL = /bin/bash + +MAIN_TARGET = $(RXPCOMPILER) +DERIVED_TARGETS = $(LIBRXPCOMPILER_DEV) + +$(addprefix $(DEST)/, $(MAIN_TARGET)): $(DEST)/% : + # Make sure errors will be reported + set -e + + # get sources + rm -rf rxp-tools/ rxp-tools.zip + + # get sources + wget $(SDK_SOURCE_URL)/rxp-tools.zip + unzip rxp-tools.zip + + pushd rxp-tools/ + find . -type f -exec touch {} + + + # Build the Debs + dpkg-buildpackage -us -uc -b -j$(SONIC_CONFIG_MAKE_JOBS) --admindir $(SONIC_DPKG_ADMINDIR) + + popd + mv $(DERIVED_TARGETS) $* $(DEST)/ + +$(addprefix $(DEST)/, $(DERIVED_TARGETS)): $(DEST)/% : $(DEST)/$(MAIN_TARGET) diff --git a/platform/nvidia-bluefield/sdk-src/sdn/.gitignore b/platform/nvidia-bluefield/sdk-src/sdn/.gitignore new file mode 100644 index 00000000000..6dbdff4573b --- /dev/null +++ b/platform/nvidia-bluefield/sdk-src/sdn/.gitignore @@ -0,0 +1,5 @@ +# Ignore everything in this directory +* +# Except these files +!.gitignore +!Makefile diff --git a/platform/nvidia-bluefield/sdk-src/sdn/Makefile b/platform/nvidia-bluefield/sdk-src/sdn/Makefile new file mode 100644 index 00000000000..f0852be15b3 --- /dev/null +++ b/platform/nvidia-bluefield/sdk-src/sdn/Makefile @@ -0,0 +1,48 @@ +# +# Copyright (c) 2024 NVIDIA CORPORATION & AFFILIATES. +# Apache-2.0 +# +# Licensed under the Apache License, Version 2.0 (the "License"); +# you may not use this file except in compliance with the License. +# You may obtain a copy of the License at +# +# http://www.apache.org/licenses/LICENSE-2.0 +# +# Unless required by applicable law or agreed to in writing, software +# distributed under the License is distributed on an "AS IS" BASIS, +# WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied. +# See the License for the specific language governing permissions and +# limitations under the License. +# + +.ONESHELL: +SHELL = /bin/bash + +MAIN_TARGET = $(SDN_APPL) +DERIVED_TARGETS = $(SDN_APPL_DERIVED_DEBS) + +$(addprefix $(DEST)/, $(MAIN_TARGET)): $(DEST)/% : + # Make sure errors will be reported + set -e + + # get sources + rm -rf SDN_appliance/ SDN_appliance.zip + + # get sources + wget $(SDK_SOURCE_URL)/SDN_appliance.zip + unzip SDN_appliance.zip + + pushd SDN_appliance/ + + find . -type f -exec touch {} + + + source /etc/profile.d/mlnx-dpdk-aarch64-linux-gnu.sh + source /etc/profile.d/doca-sdk-aarch64-linux-gnu.sh + + # Build the Debs + PATH=/usr/bin/:$(PATH) dpkg-buildpackage -us -uc -b -j1 --admindir $(SONIC_DPKG_ADMINDIR) + + popd + mv $(DERIVED_TARGETS) $* $(DEST)/ + +$(addprefix $(DEST)/, $(DERIVED_TARGETS)): $(DEST)/% : $(DEST)/$(MAIN_TARGET) diff --git a/platform/nvidia-bluefield/sdk-src/ucx/.gitignore b/platform/nvidia-bluefield/sdk-src/ucx/.gitignore new file mode 100644 index 00000000000..6dbdff4573b --- /dev/null +++ b/platform/nvidia-bluefield/sdk-src/ucx/.gitignore @@ -0,0 +1,5 @@ +# Ignore everything in this directory +* +# Except these files +!.gitignore +!Makefile diff --git a/platform/nvidia-bluefield/sdk-src/ucx/Makefile b/platform/nvidia-bluefield/sdk-src/ucx/Makefile new file mode 100644 index 00000000000..b3319c28b61 --- /dev/null +++ b/platform/nvidia-bluefield/sdk-src/ucx/Makefile @@ -0,0 +1,48 @@ +# +# Copyright (c) 2024 NVIDIA CORPORATION & AFFILIATES. +# Apache-2.0 +# +# Licensed under the Apache License, Version 2.0 (the "License"); +# you may not use this file except in compliance with the License. +# You may obtain a copy of the License at +# +# http://www.apache.org/licenses/LICENSE-2.0 +# +# Unless required by applicable law or agreed to in writing, software +# distributed under the License is distributed on an "AS IS" BASIS, +# WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied. +# See the License for the specific language governing permissions and +# limitations under the License. +# + +.ONESHELL: +SHELL = /bin/bash + +MAIN_TARGET = $(UCX) + +OFED_TAR = MLNX_OFED_SRC-debian-$(OFED_VER_FULL).tgz +OFED_SRC = MLNX_OFED_SRC-$(OFED_VER_FULL) +UCX_TAR = ucx_*.orig.tar.gz + +$(addprefix $(DEST)/, $(MAIN_TARGET)): $(DEST)/% : + # Make sure errors will be reported + set -e + + sudo rm -rf MLNX_OFED_SRC* + wget $(SDK_SOURCE_URL)/$(OFED_TAR) + tar xf $(OFED_TAR) + pushd $(OFED_SRC)/SOURCES + tar xf $(UCX_TAR) + pushd ucx-*/ + find . -type f -exec touch {} + + + patch -p0 < ../../../disable-libucx0-conflict.patch + patch -p1 < ../../../disable-go-bindings-generation.patch + + # Build the Debs + dpkg-buildpackage -us -uc -b -j$(SONIC_CONFIG_MAKE_JOBS) --admindir $(SONIC_DPKG_ADMINDIR) + + popd + mv $(DERIVED_TARGETS) $* $(DEST)/ + +$(addprefix $(DEST)/, $(DERIVED_TARGETS)): $(DEST)/% : $(DEST)/$(MAIN_TARGET) diff --git a/platform/nvidia-bluefield/sdk-src/ucx/disable-go-bindings-generation.patch b/platform/nvidia-bluefield/sdk-src/ucx/disable-go-bindings-generation.patch new file mode 100644 index 00000000000..04b9188a47a --- /dev/null +++ b/platform/nvidia-bluefield/sdk-src/ucx/disable-go-bindings-generation.patch @@ -0,0 +1,11 @@ +--- a/debian/rules ++++ b/debian/rules +@@ -19,7 +19,7 @@ XPMEM_OPT = $(shell echo ${DEB_BUILD_PROFILES} | grep -qw xpmem \ + dh $@ + + override_dh_auto_configure: +- ./contrib/configure-release-mt --prefix=/usr \ ++ ./contrib/configure-release-mt --prefix=/usr --with-go=no \ + --enable-examples --with-java=no \ + $(CUDA_OPT) $(XPMEM_OPT) + chmod +x debian/rules diff --git a/platform/nvidia-bluefield/tmfifo/.gitignore b/platform/nvidia-bluefield/tmfifo/.gitignore new file mode 100644 index 00000000000..6dbdff4573b --- /dev/null +++ b/platform/nvidia-bluefield/tmfifo/.gitignore @@ -0,0 +1,5 @@ +# Ignore everything in this directory +* +# Except these files +!.gitignore +!Makefile diff --git a/platform/nvidia-bluefield/tmfifo/Makefile b/platform/nvidia-bluefield/tmfifo/Makefile new file mode 100644 index 00000000000..0aaea9c33c4 --- /dev/null +++ b/platform/nvidia-bluefield/tmfifo/Makefile @@ -0,0 +1,39 @@ +# +# Copyright (c) 2024 NVIDIA CORPORATION & AFFILIATES. +# Apache-2.0 +# +# Licensed under the Apache License, Version 2.0 (the "License"); +# you may not use this file except in compliance with the License. +# You may obtain a copy of the License at +# +# http://www.apache.org/licenses/LICENSE-2.0 +# +# Unless required by applicable law or agreed to in writing, software +# distributed under the License is distributed on an "AS IS" BASIS, +# WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied. +# See the License for the specific language governing permissions and +# limitations under the License. +# + +.ONESHELL: +SHELL = /bin/bash +.SHELLFLAGS += -ex + +TMFIFO = tmfifo-${TMFIFO_DRIVER_VERSION} +MODULE_DIR := $(shell pwd)/tmp/${TMFIFO} +GET_PACKAGE := $(shell pwd)/../recipes/get-soc-package.sh + +$(addprefix $(DEST)/, $(TMFIFO_DRIVER)): $(DEST)/% : + rm -rf ./tmp/ + mkdir ./tmp/ + pushd ./tmp/ + + ${GET_PACKAGE} ${BSD_BASE_SOURCE_URL} ${TMFIFO} + + pushd ${TMFIFO} + + make -C /lib/modules/$(KVERSION)/build M=$(MODULE_DIR) + + mv ${TMFIFO_DRIVER} $(DEST)/ + popd + diff --git a/slave.mk b/slave.mk index 73088e945be..68ed31cd5e3 100644 --- a/slave.mk +++ b/slave.mk @@ -92,6 +92,8 @@ export BUILD_WORKDIR export GZ_COMPRESS_PROGRAM export MIRROR_SNAPSHOT export SONIC_OS_VERSION +export FILES_PATH +export PROJECT_ROOT ############################################################################### ## Utility rules @@ -726,6 +728,7 @@ SONIC_TARGET_LIST += $(addprefix $(FILES_PATH)/, $(SONIC_MAKE_FILES)) $(addprefix $(DEBS_PATH)/, $(SONIC_MAKE_DEBS)) : $(DEBS_PATH)/% : .platform $$(addsuffix -install,$$(addprefix $(DEBS_PATH)/,$$($$*_DEPENDS))) \ $$(addsuffix -install,$$(addprefix $(PYTHON_WHEELS_PATH)/,$$($$*_WHEEL_DEPENDS))) \ $$(addprefix $(DEBS_PATH)/,$$($$*_AFTER)) \ + $$(addprefix $(FILES_PATH)/,$$($$*_FILES)) \ $(call dpkg_depend,$(DEBS_PATH)/%.dep) $(HEADER)