Chris Paquin

AI, Virtualization, Containers, Infrastructure, Linux

Tag: redhat

  • RHEL 10 – Enable Health Monitoring for NVIDIA GPUs Using DCGM Exporter

    RHEL 10 – Enable Health Monitoring for NVIDIA GPUs Using DCGM Exporter

    Nvidia Datacenter GPU Manager (DCGM) is a suite of tools that provides health monitoring, performance telemetry, and proactive diagnostics for NVIDIA GPUs deployed on bare-metal servers. It is mainly installed for managing a fleet of GPUs across a large number of GPU enabled nodes.

    DCGM does not have a WebUI, and is often seen “exporting” metrics into Grafana or other enterprise observability tools (like Zabbix) via Prometheus Scrape. I have both Grafana and Zabbix in my lab environment so I have a couple of options to where I want to visualize the data.

    In this post, we are going to …

    • Validate GPU Host Setup
    • Install Nvidia DCGM
    • Enable Health Watches via DCGM
    • Setup dcgm-exporter for exporting of GPU metrics

    Nvidia Drivers Install on RHEL 10.1

    A lot has changed in RHEL 10.1 regarding the installation of NVIDIA drivers on RHEL 10. You can now install them via rhel-drivers.

    The post below is pretty throughout on the topic
    https://www.redhat.com/en/blog/introducing-new-and-simplified-ai-accelerator-driver-experience-rhel

    Since I already have the NVIDIA drivers installed on my two GPU enabled nodes, I will just confirm they are both running the same driver version (for consistency) and will ensure the driver is loading properly with nvidia-smi. I will also install CUDA and the nvidia-container-toolkit.


    Host Validation

    In my lab I have 2x Dell R730s with Nvidia Tesla T4s installed (Turing-class GPUs). They are not the most modern GPUs but they are Data center class, can be purchased pretty cheaply used, and only draw ~70w of power and therefore do not require any additional power connections from a riser card or the system board.

    So on each host we will first start off by insuring we have the proper NVIDIA drivers installed.

    [root@columbia ~]# rhel-drivers list
    Available drivers:
    amdgpu:latest
    > nvidia:590.48.01

    Now we run “nvidia-smi” to confirm the driver is loaded and the GPU is recognized.

    nvidia-smi
    Tue Feb 24 10:49:29 2026
    +-----------------------------------------------------------------------------------------+
    | NVIDIA-SMI 580.105.08 Driver Version: 580.105.08 CUDA Version: 13.0 |
    +-----------------------------------------+------------------------+----------------------+
    | GPU Name Persistence-M | Bus-Id Disp.A | Volatile Uncorr. ECC |
    | Fan Temp Perf Pwr:Usage/Cap | Memory-Usage | GPU-Util Compute M. |
    | | | MIG M. |
    |=========================================+========================+======================|
    | 0 Tesla T4 Off | 00000000:04:00.0 Off | 0 |
    | N/A 34C P8 13W / 70W | 0MiB / 15360MiB | 0% Default |
    | | | N/A |
    +-----------------------------------------+------------------------+----------------------+

    Moving on 2 our second host and verify the installed driver.

    [root@prometheus ~]$ rhel-drivers list
    Available drivers:
    amdgpu:latest
    *> nvidia:590.48.01

    And nvidia-smi output, we can see that there are two Telsa T4s in this machine. Nice!

    [root@prometheus ~]$ nvidia-smi
    Tue Feb 24 10:52:55 2026
    +-----------------------------------------------------------------------------------------+
    | NVIDIA-SMI 590.48.01 Driver Version: 590.48.01 CUDA Version: 13.1 |
    +-----------------------------------------+------------------------+----------------------+
    | GPU Name Persistence-M | Bus-Id Disp.A | Volatile Uncorr. ECC |
    | Fan Temp Perf Pwr:Usage/Cap | Memory-Usage | GPU-Util Compute M. |
    | | | MIG M. |
    |=========================================+========================+======================|
    | 0 Tesla T4 Off | 00000000:04:00.0 Off | 0 |
    | N/A 30C P8 9W / 70W | 0MiB / 15360MiB | 0% Default |
    | | | N/A |
    +-----------------------------------------+------------------------+----------------------+
    | 1 Tesla T4 Off | 00000000:06:00.0 Off | 0 |
    | N/A 32C P8 9W / 70W | 0MiB / 15360MiB | 0% Default |
    | | | N/A |
    +-----------------------------------------+------------------------+----------------------+

    Lets also make sure that we have the same CUDA version installed across hosts.

    [root@prometheus ~]$ rpm -qa | grep cuda-toolkit
    cuda-toolkit-config-common-13.1.80-1.noarch
    cuda-toolkit-13-config-common-13.1.80-1.noarch
    cuda-toolkit-13-1-config-common-13.1.80-1.noarch
    cuda-toolkit-13-1-13.1.1-1.x86_64
    cuda-toolkit-13.1.1-1.x86_64

    We also need to update $PATH for nvcc if we have not done so already.

    cat << 'EOF' | sudo tee /etc/profile.d/cuda.sh
    export PATH=/usr/local/cuda/bin:$PATH
    export LD_LIBRARY_PATH=/usr/local/cuda/lib64:$LD_LIBRARY_PATH
    EOF

    Then source the path.

    # source /etc/profile.d/cuda.sh

    And now run nvcc.

    nvcc --version
    nvcc: NVIDIA (R) Cuda compiler driver
    Copyright (c) 2005-2025 NVIDIA Corporation
    Built on Tue_Dec_16_07:23:41_PM_PST_2025
    Cuda compilation tools, release 13.1, V13.1.115
    Build cuda_13.1.r13.1/compiler.37061995_0

    We also will need to install the Nvidia Container Toolkit on both GPU hosts, using the RHEL 9 version below.

    sudo dnf config-manager \
    --add-repo=https://nvidia.github.io/libnvidia-container/stable/rpm/nvidia-container-toolkit.repo

    Once again we are going to skip the gpgcheck. Again this is a homelab.

    sudo dnf install -y --nogpgcheck nvidia-container-toolkit

    And now we validate install on both hosts.

    # nvidia-ctk --version
    NVIDIA Container Toolkit CLI version 1.18.2
    commit: 9e88ed39710fd94c7e49fbb26d96492c45e574fb

    Now we need to generate the CDI specification, as Podman does not use Docker-style run-times, and instead using Container Device Interface (CDI).

    sudo nvidia-ctk cdi generate --output=/etc/cdi/nvidia.yaml

    The command above creates /etc/cdi/nvidia.yaml which describes installed GPUs and NVML libraries.
    We now need to restart podman and confirm podman sees our CDI devices.

    cat <<'EOF' | sudo tee /etc/containers/containers.conf.d/99-cdi.conf
    [engine]
    cdi_enabled=true
    cdi_spec_dirs=["/etc/cdi","/var/run/cdi"]
    EOF

    Now we need to verify podman can utilize our GPUs. Again we are running these commands on both our GPU enabled servers.

        podman run --rm --device nvidia.com/gpu=all docker.io/nvidia/cuda:12.0.0-base-ubuntu22.04 nvidia-smi -L
    GPU 0: Tesla T4 (UUID: GPU-9491a3e6-ea29-ba4e-4403-083244d5575c)
    GPU 1: Tesla T4 (UUID: GPU-1d877ac8-5df1-34b0-4f86-59945e37d2ba)
    
    

    DCGM install on RHEL 10

    The install is pretty straight forward, for this post I am performing these steps on both my GPU enabled hosts.

    Add Nvidia Repo

    Note that I could not find DCGM in the RHEL10 repos, so going with RHEL9 repos. Seems to work without issue thus far.

    # dnf config-manager --add-repo \
    https://developer.download.nvidia.com/compute/cuda/repos/rhel9/x86_64/cuda-rhel9.repo

    Now install as shown below.

    Note we are skipping the gpgcheck due to RHEL10 newer OpenGPG verification stack. Since this is a lab, and not production, this is acceptable for testing.

    # dnf install -y --nogpgcheck datacenter-gpu-manager-4-core datacenter-gpu-manager-4-proprietary

    Now we can start the service.

    # systemctl enable --now nvidia-dcgm

    And we check that the service is running.

    systemctl status nvidia-dcgm
    ● nvidia-dcgm.service - NVIDIA DCGM service
    Loaded: loaded (/usr/lib/systemd/system/nvidia-dcgm.service; enabled; preset: disabled)
    Active: active (running) since Tue 2026-02-24 10:37:35 EST; 36min ago
    Invocation: da9cd3a2c8a5463a95a3605b68adf253
    Main PID: 2263 (nv-hostengine)
    Tasks: 17 (limit: 1646190)
    Memory: 91.7M (peak: 93.1M)
    CPU: 23.253s
    CGroup: /system.slice/nvidia-dcgm.service
    └─2263 /usr/bin/nv-hostengine -n --service-account nvidia-dcgm
    Feb 24 10:37:35 prometheus.lab systemd[1]: Started nvidia-dcgm.service - NVIDIA DCGM service.
    Feb 24 10:37:37 prometheus.lab nv-hostengine[2263]: DCGM initialized
    Feb 24 10:37:37 prometheus.lab nv-hostengine[2263]: Started host engine version 4.5.2 using port number:>

    dcgmi discovery -l

    Now that dcgmi is installed lets confirm it can see our GPUs.

    This command lists all discovered GPUs. Shows GPU id, PCI BUS ID and Model Name. Should be comparable to the output of nvidia-smi. This command confirms that dcgmi can talk to the host engine.

    dcgmi discovery -l
    2 GPUs found (Active).
    +--------+----------------------------------------------------------------------+
    | GPU ID | Device Information |
    +--------+----------------------------------------------------------------------+
    | 0 | Name: Tesla T4 |
    | | PCI Bus ID: 00000000:04:00.0 |
    | | Device UUID: GPU-9491a3e6-ea29-ba4e-4403-083244d5575c |
    +--------+----------------------------------------------------------------------+
    | 1 | Name: Tesla T4 |
    | | PCI Bus ID: 00000000:06:00.0 |
    | | Device UUID: GPU-1d877ac8-5df1-34b0-4f86-59945e37d2ba |
    +--------+----------------------------------------------------------------------+

    Enable Health Watches

    Health Watches are background checks that DCGM performs on the GPU subsystems. While they are not required for metrics export they do provide additional metrics related to GPU health, so lets enable them.

    dcgmi health -s a
    Health monitor systems set successfully.

    dcgm-exporter

    NVIDIA DCGM Exporter is an open-source tool (container) that collects real-time telemetry data from NVIDIA GPUs—such as utilization, memory usage, temperature, and power consumption—and exposes them in a Prometheus-compatible format.

    We are going to run it via Quadlet ( /etc/containers/systemd/dcgm-exporter.container)

    [Unit]
    Description=NVIDIA DCGM Exporter
    After=network-online.target nvidia-dcgm.service
    Wants=network-online.target
    [Container]
    Image=docker.io/nvidia/dcgm-exporter:latest
    Network=host
    SecurityLabelDisable=true
    AddCapability=SYS_ADMIN
    PodmanArgs=–device nvidia.com/gpu=all
    PodmanArgs=–pid=host
    [Service]
    Restart=always
    [Install]
    WantedBy=multi-user.target
    view raw gistfile1.txt hosted with ❤ by GitHub

    Now lets start the container

     sudo systemctl daemon-reload
    [root@columbia ~]# sudo systemctl start dcgm-exporter.service
    [root@columbia ~]# podman ps
    CONTAINER ID  IMAGE                                  COMMAND     CREATED         STATUS         PORTS       NAMES
    8804d788f7f5  docker.io/nvidia/dcgm-exporter:latest              10 seconds ago  Up 10 seconds              systemd-dcgm-exporter
    
    

    Lets verify it is listening on port 9400.

    ss -tnlp | grep 9400
    LISTEN 0 4096 *:9400 *:* users:(("dcgm-exporter",pid=135704,fd=24))

    Now lets poke a hole in our firewall to allow the traffic.

    firewall-cmd --add-port=9400/tcp --permanent
    success
    [root@prometheus ~]$ sudo firewall-cmd --reload

    And test locally with curl.

    curl -s -o /dev/null -w "%{http_code}" http://10.1.10.23:9400/metrics

    We can also view the metrics in our browser

    Screenshot of a command-line output displaying NVIDIA GPU statistics including clock frequency, temperature, power usage, and memory utilization.

    Next steps will be to scrape and import.
    Which I will do after lunch.

    Resources

    Learn more from NVIDIA’s official resources:

  • Fix GPG Check Failed Error on RHEL 10.1

    Overview

    On some RHEL 10.1 installs users are running into this error, post-install, when attempting to install packages via dnf.

    Unsure if the issue is isolated to users attempting to install RHEL via the full DVD ISO, from the minimal boot ISO, and users deploying RHEL 10.1 via kickstart.

     GPG Keys are configured as: file:///etc/pki/rpm-gpg/RPM-GPG-KEY-redhat-release
    The GPG keys listed for the "Red Hat Enterprise Linux 10 for x86_64 - AppStream (RPMs)" repository are already installed but they are not correct for this package.
    Check that the correct key URLs are configured for this repository.. Failing package is: gnupg2-smime-2.4.5-3.el10_1.x86_64
     GPG Keys are configured as: file:///etc/pki/rpm-gpg/RPM-GPG-KEY-redhat-release
    The downloaded packages were saved in cache until the next successful transaction.
    You can remove cached packages by executing 'yum clean packages'.
    Error: GPG check FAILED

    More Details

    The issue is caused by GPG keys installed in /etc/pki/rpm-gpg, specifically RPM-GPG-KEY-redhat-release

    This issue is being tracked via BUG RHEL-144980


    Workaround

    I am currently aware of two workaround, one manual, one much more simple. Details below


    Workaround #1 (Simple)

    Use dnf to install new GPG keys used via dnf

    $ sudo dnf update redhat-release

    After doing so you should run the following

    $ sudo dnf clean all

    You should now be able to update RHEL and install additional RPMs.


    Workaround #2 (manual)

    You can delete the current key in “/etc/pki/rpm-gpg”

    Delete the following

    • RPM-GPG-KEY-redhat-release
    • RPM-GPG-KEY-redhat-beta (if applicable)

    Then SCP known working copies of the keys that you just deleted from a RHEL 10.1 host that is not experiencing this issue. I would suspect an earlier build of RHEL 10.1 or possibly a later build or RHEL 10.1 once available will not experience this issue.

    Once you replace the keys, clean up dnf cache

    $ sudo dnf clean-all
  • Setting up Chrony/NTP Server with GPS on Ubuntu 22.04

    Setting up Chrony/NTP Server with GPS on Ubuntu 22.04

    Introduction

    In this post I will cover setting up a ntp/chrony server on Ubuntu 22.04 using a Satellite GPS Receiver. I have also recently published another post on Chrony, which goes a bit more into basic commands. That post can be found here.


    Hardware

    Note: the GlobalSat BU-353-W11 does not support 1pps. It’s designed primarily for positioning and navigation, not precision timing. We can use it as our timesource for chrony, with a typical accuracy: ±50–150 ms. Good enough for a lab.


    Hardware Detection

    After plugging in the USB cable on the GNSS module, check for a new USB device.

    # lsusb
    Bus 001 Device 004: ID 1546:01a7 U-Blox AG [u-blox 7]

    Output from dmegs also shows the device was detected properly

    [347055.572498] usb 1-2.4: new full-speed USB device number 4 using tegra-xusb
    [347055.768706] cdc_acm 1-2.4:1.0: ttyACM0: USB ACM device
    [347055.768784] usbcore: registered new interface driver cdc_acm
    [347055.768788] cdc_acm: USB Abstract Control Model driver for USB modems and ISDN adapters

    In the output above you can see the device was detected ttyACM0. Now we need to confirm how the device was enumerated. As you can see the device is owned by root and the group is dialout

    # ls -l /dev/ttyACM*
    crw-rw---- 1 root dialout 166, 0 Dec 29 13:40 /dev/ttyACM0
    
    

    You can run a quick check to confirm that the device is functioning as shown below

    # cat /dev/ttyACM0
    $GPTXT,01,01,02,u-blox ag - www.u-blox.com*50
    
    $GPTXT,01,01,02,HW  UBX-G70xx   00070000 FF7FFFFFo*69
    
    $GPTXT,01,01,02,ROM CORE 1.00 (59842) Jun 27 2012 17:43:52*59
    
    $GPGGA,201055.00,3356.15827,N,08345.15611,W,2,12,0.80,280.0,M,-31.5,M,,0000*67
    
    -----------truncated----------------

    GPSD

    To use a GPS/GNSS antenna with chronyd on Linux for time synchronization and location sharing, we will use the gpsd service to manage the GPS hardware and make its data accessible to other applications, including chronyd

    Package Installation

    # sudo apt update
    # sudo apt install gpsd gpsd-clients chrony pps-tools 

    GPSD Configuration

    Identify the GPS device: The device will likely be /dev/ttyUSB0/dev/ttyACM0, or similar. You can verify this by running cat /dev/ttyUSB0 (replace ttyUSB0 with your suspected device) and looking for NMEA strings (lines starting with $GPGGA$GNRMC, etc.).

    Edit the gpsd configuration file: Open /etc/default/gpsd and set the DEVICESGPSD_OPTIONS, and USBAUTO variables.

    START_DAEMON="true"
    GPSD_OPTIONS="-n -b"
    DEVICES="/dev/ttyACM0"
    USBAUTO="false"
    GPSD_SOCKET="/var/run/gpsd.sock"
    

    For reference here are configuration params for GPSD_OPTIONS

    FlagArgumentMeaningNotes
    -nnoneStart reading GPS immediatelyRequired for chrony/NTP
    -bnoneRead-only mode (no device writes)Recommended for USB pucks
    -NnoneRun in foregroundDebug only
    -D<level>Debug verbosityUse -D 2 or -D 3
    -F<path>Control socket pathNeeded for manual runs
    -s<baud>Force serial baud rateUART devices only
    -S<port>TCP listening portRare; usually disabled
    -GnoneAllow remote TCP clientsAvoid on servers
    -lnoneList drivers and exitDiagnostic
    -VnoneShow version and exitInformational
    -hnoneHelp outputReference

    Enable and start gpsd

    # sudo systemctl enable gpsd
    # sudo systemctl restart gpsd

    Verify gpsd is receiving data

    # cgps -s
    

    Output below

    Screen output from a GPSD client showing real-time GPS data, including time, latitude, longitude, altitude, speed, and satellite information.

    Interpreting the output from cgps

    High-Level Status (The Big Picture)

    • (Satellites) Seen / Used: 13 / 11
    • Fix: 3D DGPS FIX – means the receiver has solved all three spatial dimensions: (Latitude, Longitude, Altitude)
    • Time is valid
    • Position accuracy: ~5–10 feet horizontal

    Satellite Section (Right Pane)

    Seen 13 / Used 11
    

    This means:

    • The receiver can currently see 13 satellites
    • 11 of those are strong enough to be used in the solution

    This is quite a healthy signal for a device sitting inside up against a window.

    Anything above:

    • 4 used → valid 3D fix
    • 8+ used → very solid geometry
    • 10–12 used → excellent (we are here)

    Constellations

    • GP = GPS
      • U.S. GPS constellation
      • Medium Earth Orbit (≈20,200 km)
      • ~30 active satellites worldwide
    • SB = SBAS (WAAS corrections)
      • Satellite-Based Augmentation System
      • Broadcast correction data
      • Improve accuracy of GPS measurements
      • Do not provide independent position fixes

    The presence of SBAS satellites indicates differential reminder data is available, improving accuracy.

    Fix & Timing (Left Pane)

    Fix State

    Status: 3D DGPS FIX (1 secs)
    
    • 3D = Latitude, longitude, altitude solved
    • DGPS = WAAS corrections applied
    • (1 secs) = Fix age (very fresh)

    Time Quality

    Time: 2025-12-29T20:32:22.000Z
    Time offset: 0.078609772 s
    


    Chrony

    Install Chrony via apt

    # apt install chrony -y

    Configure Chrony

    Edit /etc/chrony/chrony.conf. This config has been tested on Ubuntu 22.04, YMMV on other Linux versions.

    ###############################################################################
    # Chrony configuration
    #
    # Purpose:
    # – Discipline system time using a USB GPS receiver via gpsd (NMEA-only)
    # – No PPS available, so accuracy is milliseconds (not microseconds)
    # – Act as a low-priority NTP server for the local network
    #
    # Notes:
    # – Chrony always operates internally in UTC
    # – GPS time is provided by gpsd over a UNIX socket
    ###############################################################################
    #——————————————————————————
    # Include additional configuration snippets
    #——————————————————————————
    # Allows drop-in configuration files (not required, but standard on Ubuntu)
    confdir /etc/chrony/conf.d
    ###############################################################################
    # Debug / observability
    ###############################################################################
    # Where chrony writes its own detailed log streams
    logdir /var/log/chrony
    # Enable detailed logs:
    # – tracking: disciplined clock state (offset/freq/skew, etc.)
    # – measurements: raw samples from sources (very useful for refclocks)
    # – statistics: aggregate stats per source
    log tracking measurements statistics
    # Log when chrony makes a clock correction bigger than the thresholds
    # (units: seconds). Helps correlate “why did time jump?” events.
    logchange 0.5
    #——————————————————————————
    # GPS reference clock (via gpsd)
    #——————————————————————————
    # Use gpsd's UNIX socket as a reference clock.
    #
    # SOCK /var/run/gpsd.sock
    # – Chrony does NOT talk to the GPS device directly
    # – gpsd parses NMEA and provides time samples
    #
    # refid GPS
    # – Human-readable label shown in chronyc output
    #
    # poll 4
    # – Poll interval = 2^4 seconds = 16 seconds
    #
    # precision 1e-1
    # – Declare expected precision (~100 ms)
    # – REQUIRED for NMEA-only GPS to avoid sample rejection
    #
    # delay 0.2
    # – Account for USB + NMEA sentence latency
    #
    # trust
    # – Explicitly allow chrony to accept this low-precision refclock
    #
    #refclock SOCK /run/gpsd.sock refid GPS poll 4 precision 1e-1 delay 0.2 trust prefer
    refclock SHM 0 refid GPS poll 4 precision 1e-1 delay 0.2 trust prefer
    #——————————————————————————
    # Standalone operation policy
    #——————————————————————————
    # Allow chrony to discipline the system clock even if:
    # – No network NTP servers are configured
    # – GPS is the only available reference
    #
    # Advertise this host as stratum 10 to NTP clients:
    # – Prevents it from being treated as an authoritative time source
    # – Avoids NTP loops
    # – Appropriate for NMEA-only GPS (no PPS)
    #
    local stratum 2
    #——————————————————————————
    # Clock stepping behavior
    #——————————————————————————
    # Allow the system clock to be stepped (jumped) instead of slewed
    # if the offset is larger than 1 second, but ONLY during startup
    # and only for the first 3 updates.
    #
    # This prevents long convergence times on boot while avoiding
    # disruptive time jumps during normal operation.
    #
    makestep 1.0 3
    #——————————————————————————
    # Frequency drift handling
    #——————————————————————————
    # Persist the measured frequency error of the system clock.
    #
    # This allows chrony to:
    # – Start with a good frequency estimate after reboot
    # – Converge faster
    # – Free-run more accurately if all time sources disappear
    #
    driftfile /var/lib/chrony/chrony.drift
    #——————————————————————————
    # NTP server behavior (serving time to clients)
    #——————————————————————————
    # Allow NTP clients from the local subnet to query this server
    #
    allow 10.1.10.0/24
    # Bind NTP service explicitly to this interface/address
    # (prevents listening on unintended interfaces)
    #
    bindaddress 10.1.10.11
    #——————————————————————————
    # Optional dynamic source handling
    #——————————————————————————
    # Allow chrony to use NTP servers provided via DHCP (if present)
    #
    sourcedir /run/chrony-dhcp
    # Allow additional NTP source files to be added modularly
    #
    sourcedir /etc/chrony/sources.d
    #——————————————————————————
    # Security and key material
    #——————————————————————————
    # File containing NTP authentication keys (if used)
    #
    keyfile /etc/chrony/chrony.keys
    # Directory used to store NTS (Network Time Security) cookies and keys
    #
    ntsdumpdir /var/lib/chrony
    #——————————————————————————
    # Logging
    #——————————————————————————
    # Directory where chrony logs are written
    #
    logdir /var/log/chrony
    # Uncomment the following line to enable detailed logging:
    # log tracking measurements statistics
    #——————————————————————————
    # Stability and safety controls
    #——————————————————————————
    # Prevent chrony from applying updates if clock estimates become unstable
    #
    maxupdateskew 100.0
    # Periodically sync the system time back to the hardware RTC
    # (every ~11 minutes)
    #
    rtcsync
    #——————————————————————————
    # Leap second handling
    #——————————————————————————
    # Obtain leap second and TAI-UTC offset information from the system
    # timezone database, operating in strict UTC mode.
    #
    leapsectz right/UTC
    view raw gistfile1.txt hosted with ❤ by GitHub

    Explanation of Chrony Config for GPSD

    OptionPurpose
    SOCK /var/run/gpsd.sockRead time from gpsd
    refid GPSLabel in chrony output
    poll 4Poll every 16 seconds
    precision 1e-1~100 ms accuracy (realistic for NMEA)
    delay 0.2USB + NMEA latency
    makestep 1.0 3Allow initial step corrections

    Start and Enable

    # systemctl enable chrony.service
    # systemctl start chrony.service

    After a few minutes, we should start to see pre-configured clients appear in the output of the command below

     # chronyc clients
    Hostname                      NTP   Drop Int IntL Last     Cmd   Drop Int  Last
    =============================================================================
    scar.lab                        5      0   6   -    30       0      0   -     -
    

    Chrony Client-side Setup

    Ubuntu Client

    $ sudo apt install chrony -y

    Configure the to listen to the chrony server address 10.1.10.10. Comment out any other server or pool directives in /etc/chrony/chrony.conf.

    server 10.1.10.11

    Start and enable the service.

    $ sudo systemctl enable chrony --now
    

    Check configured time source for chrony

    $ chronyc -n sources -v

    What the above output tells you

    • All NTP servers/pools configured for this client
    • Which source is currently selected
    • Reachability and time quality

    Key indicators

    SymbolMeaning
    ^*Current sync source
    ^+Candidate source
    ^-Reachable, not selected
    ^?Unusable / not trusted yet

    Cisco Catalyst Client Config

    Use the commands below to configure your Cisco switch to use the new timesource

    # Enter global configuration mode
    configure terminal
    
    # Define the NTP server
    ntp server 10.1.10.11
    
    # (Optional) Set the switch to use its own hardware clock if it loses sync
    ntp master 10
    
    # Exit and save
    end
    write memory
  • Step-by-Step Nvidia Driver, CUDA Toolkit, & Container Toolkit Install for RHEL9

    Step-by-Step Nvidia Driver, CUDA Toolkit, & Container Toolkit Install for RHEL9

    Introduction

    In this step-by-steps guide we will replace the out of the box nouveau drivers on RHEL9 with Nvidia Drivers. We will also install the the Nvidia CUDA Toolkit and the Nvidia Container Toolkit.


    GPU and Driver Inspection

    First we need to make sure that our Nvdia GPU is recognized by Red Hat Enterprise Linux 9 (RHEL9).

    lspci -nn | grep -i nvidia
    b6:00.0 3D controller [0302]: NVIDIA Corporation GA102GL [A40] [10de:2235] (rev a1)
    

    Using the command below we can see that we are currently using the non-propietary nouveau driver.

    # lspci | grep ' NVIDIA ' | cut -d" " -f 1 | xargs -i lspci -v -s {}
    b6:00.0 3D controller: NVIDIA Corporation GA102GL [A40] (rev a1)
    	Subsystem: NVIDIA Corporation Device 145a
    	Flags: bus master, fast devsel, latency 0, IRQ 32, NUMA node 0
    	Memory at fa000000 (32-bit, non-prefetchable) [size=16M]
    	Memory at 38d000000000 (64-bit, prefetchable) [size=64G]
    	Memory at 38f040000000 (64-bit, prefetchable) [size=32M]
    	Capabilities: [60] Power Management version 3
    	Capabilities: [68] Null
    	Capabilities: [78] Express Legacy Endpoint, MSI 00
    	Capabilities: [b4] Vendor Specific Information: Len=14 <?>
    	Capabilities: [c8] MSI-X: Enable- Count=6 Masked-
    	Capabilities: [100] Virtual Channel
    	Capabilities: [258] L1 PM Substates
    	Capabilities: [128] Power Budgeting <?>
    	Capabilities: [420] Advanced Error Reporting
    	Capabilities: [600] Vendor Specific Information: ID=0001 Rev=1 Len=024 <?>
    	Capabilities: [900] Secondary PCI Express
    	Capabilities: [bb0] Physical Resizable BAR
    	Capabilities: [bcc] Single Root I/O Virtualization (SR-IOV)
    	Capabilities: [c14] Alternative Routing-ID Interpretation (ARI)
    	Capabilities: [c1c] Physical Layer 16.0 GT/s <?>
    	Capabilities: [d00] Lane Margining at the Receiver <?>
    	Capabilities: [e00] Data Link Feature <?>
    	Kernel driver in use: nouveau
    	Kernel modules: nouveau
    

    Configuring Repositories for the Nvidia Driver Install

    First we need to enable the RHEL9 CodeReady Builder repo. Note we are running these commands as root.

    # subscription-manager repos --enable codeready-builder-for-rhel-9-$(uname -i)-rpms
    

    Next we will need to install and configure the EPEL repo.

    # dnf install -y https://dl.fedoraproject.org/pub/epel/epel-release-latest-9.noarch.rpm
    

    Now we install the ELRepo project repo – this will provide nvidia-detect which we can utilize later

    # dnf -y  install https://www.elrepo.org/elrepo-release-9.el9.elrepo.noarch.rpm

    Prerequisites for Nvidia Driver Install

    Now we need to install dependencies and build tools.

    # dnf install -y kernel-devel-$(uname -r) kernel-headers-$(uname -r) gcc make dkms acpid libglvnd-glx libglvnd-opengl libglvnd-devel pkgconfig
    

    Install Nvidia Drivers

    Install nvidia-detect from the ELRepo project repo.

    # dnf -y install nvidia-detect

    Now install the Nvidia Drivers.

    # dnf -y install $(nvidia-detect)

    Now reboot.


    Confirming Nvidia Driver Installation

    Now lets run the command below one more time.

    [root@gpu ~]# lspci | grep ' NVIDIA ' | cut -d" " -f 1 | xargs -i lspci -v -s {}
    b6:00.0 3D controller: NVIDIA Corporation GA102GL [A40] (rev a1)
    	Subsystem: NVIDIA Corporation Device 145a
    	Flags: bus master, fast devsel, latency 0, IRQ 32, NUMA node 0
    	Memory at fa000000 (32-bit, non-prefetchable) [size=16M]
    	Memory at 38d000000000 (64-bit, prefetchable) [size=64G]
    	Memory at 38f040000000 (64-bit, prefetchable) [size=32M]
    	Capabilities: [60] Power Management version 3
    	Capabilities: [68] Null
    	Capabilities: [78] Express Legacy Endpoint, MSI 00
    	Capabilities: [b4] Vendor Specific Information: Len=14 <?>
    	Capabilities: [c8] MSI-X: Enable- Count=6 Masked-
    	Capabilities: [100] Virtual Channel
    	Capabilities: [250] Latency Tolerance Reporting
    	Capabilities: [258] L1 PM Substates
    	Capabilities: [128] Power Budgeting <?>
    	Capabilities: [420] Advanced Error Reporting
    	Capabilities: [600] Vendor Specific Information: ID=0001 Rev=1 Len=024 <?>
    	Capabilities: [900] Secondary PCI Express
    	Capabilities: [bb0] Physical Resizable BAR
    	Capabilities: [bcc] Single Root I/O Virtualization (SR-IOV)
    	Capabilities: [c14] Alternative Routing-ID Interpretation (ARI)
    	Capabilities: [c1c] Physical Layer 16.0 GT/s <?>
    	Capabilities: [d00] Lane Margining at the Receiver <?>
    	Capabilities: [e00] Data Link Feature <?>
    	Kernel driver in use: nvidia
    	Kernel modules: nouveau, nvidia_drm, nvidia
    

    As you can see in the output below, the kernel is loading the Nvidia driver. We can still see nouveau kernel modules listed, but that is fine, as they are not loaded. We can confirm this with the command below.

    # lsmod | grep nouveau

    The above command should not output anything, while the opposite should be true for the command below.

    # lsmod | grep nvidia

    Configure Nvidia Persistenced

    Start and enable nvidia-persistenced.service. This will enable persistence-mode which will keep the nvidia device state from going “stale”

    # systemctl enable nvidia-persistenced.service
    # systemctl start nvidia-persistenced.service
    

    Installing the Nvidia CUDA Toolkit

    We will now follow the official guide and install the Nvidia CUDA toolkit. Per that guide, we need to enable a few repos, however two of those repos should be enabled by default, and the other one we enabled above, however I will list them here for the sake of documentation.

    # subscription-manager repos --enable=rhel-9-for-x86_64-appstream-rpms
    # subscription-manager repos --enable=rhel-9-for-x86_64-baseos-rpms
    # subscription-manager repos --enable=codeready-builder-for-rhel-9-x86_64-rpms

    Now we install the Nvidia repo for the CUDA toolkit.

    dnf config-manager --add-repo https://developer.download.nvidia.com/compute/cuda/repos/rhel9/x86_64/cuda-rhel9.repo
    

    Now install the CUDA toolkit as shown below

    # sudo dnf -y install cuda-toolkit

    Confirm that the toolkit is installed and note the version.

    # rpm -qa cuda-toolkit
    cuda-toolkit-12.8.1-1.x86_64
    

    Add the following to your .bashrc. And if you intend to run/install anything as root, you may want to add it to root’s .bashrc as well. Note that the cuda version should match the one that you installed above.

    export PATH=/usr/local/cuda-12.8/bin:$PATH

    Now test nvcc as shown below.

    # nvcc --version
    nvcc: NVIDIA (R) Cuda compiler driver
    Copyright (c) 2005-2025 NVIDIA Corporation
    Built on Fri_Feb_21_20:23:50_PST_2025
    Cuda compilation tools, release 12.8, V12.8.93
    Build cuda_12.8.r12.8/compiler.35583870_0
    

    Installing the Nvidia Container Toolkit

    Next we will install the Nvidia Container Toolkit, which allows users to run GPU-accelerated containerized applications.

    A bit about Container Management in RHEL 9

    The default container packages in RHEL 9 are as follows.

    1. Podman – daemonless container image
    2. Buildah – tool for building OCI (Open Container Initiative) container images
    3. Skopeo – tool for managing container images and repos
    4. CRIU – tool to create and save running container checkpoints to disk
    5. Udica – tool for managing SELinux policies for containers

    Installation of the toolkit

    We will follow the instructions as documented here.

    First we configure the repo

    # curl -s -L https://nvidia.github.io/libnvidia-container/stable/rpm/nvidia-container-toolkit.repo | \
      sudo tee /etc/yum.repos.d/nvidia-container-toolkit.repo

    Then install via dnf

    # dnf install -y nvidia-container-toolkit

    Configuring the Container Toolkit for Podman

    Generate the CDI specification file using the command below.

    # nvidia-ctk cdi generate --output=/etc/cdi/nvidia.yaml

    Now lets check the names of the generated device(s).

    # nvidia-ctk cdi list
    INFO[0000] Found 3 CDI devices                          
    nvidia.com/gpu=0
    nvidia.com/gpu=GPU-7e880be2-891c-72e3-9515-0fd51240e7f4
    nvidia.com/gpu=all
    

    References

    1. https://medium.com/@blackhorseya/step-by-step-guide-to-installing-nvidia-drivers-on-rhel-9-1107e0cd641d
    2. https://access.redhat.com/discussions/227d2101-b4e3-490a-aa1c-601c407ec038
    3. https://darryldias.me/2022/install-nvidia-drivers-on-rhel-9/
    4. https://docs.nvidia.com/datacenter/cloud-native/container-toolkit/latest/install-guide.html
    5. https://docs.nvidia.com/cuda/cuda-installation-guide-linux/index.html#network-repo-installation-for-rhel-rocky
    6. https://docs.nvidia.com/datacenter/cloud-native/container-toolkit/latest/cdi-support.html
  • How to Install and Configure Dnsmasq with Web Frontend on RHEL 9

    How to Install and Configure Dnsmasq with Web Frontend on RHEL 9

    In this post we are going to install and configure dnsmasq with a simple webUI acting as a front end for our less technical users. Our goal is to simplify dns in our lab sandboxes, and keep users from directly modifying our dnsmasq config files.

    Installation

    First we need to install dnsmasq.

    # dnf -y install dnsmasq

    Now lets enable and start the service. We will also check the status of the service to ensure that we do not have any issues with the default config.

    # systemctl start dnsmasq
    # systemctl enable dnsmasq
    # systemctl status dnsmasq

    Configuration

    Next let’s make a backup of the default configuration file before we start making modification.

    cp /etc/dnsmasq.conf /etc/dnsmasq.conf.orig

    I made the following modifications.

    1. listen-address is the loopback and our routable ip address
    2. expand-hosts, we uncomment this in order to allow dnsmasq to automatically expand the hostnames to fully qualified domain names
    3. domain – this is the local domain that we will serve via dnsmasq
    4. dhcp-range – this is the range of IP addresses that dnsmasq is allowed to hand out
    interface=enp1s0
    listen-address=127.0.0.1,192.168.65.7
    expand-hosts
    domain=sandbox3.localdomain
    dhcp-range=192.168.65.20,192.168.65.40,255.255.255.128,12h
    

    Next we check our config file for any errors

    # dnsmasq --test
    dnsmasq: syntax check OK.

    Now lets restart dnsmasq

    # systemctl restart dnsmasq

    Firewall Config

    Now we need to modify firewalld

    [root@dns ~]#  firewall-cmd --add-service=dns --permanent
    success
    [root@dns ~]# firewall-cmd --add-service=dhcp --permanent
    success
    [root@dns ~]# firewall-cmd --reload
    success

    Testing

    I prefer to use nslookup for testing, so lets install it

    # dnf -y install bind-utils

    Now let’s make sure we are able to resolve addresses, using our local instance of dnsmasq.

    # nslookup
    > server localhost
    Default server: localhost
    Address: ::1#53
    Default server: localhost
    Address: 127.0.0.1#53
    > google.com
    Server:		localhost
    Address:	::1#53
    
    Non-authoritative answer:
    Name:	google.com
    Address: 142.251.40.174
    Name:	google.com
    Address: 2607:f8b0:4006:821::200e
    

    Install and Configure the Webui

    For the webui – we are going to use a simple one that I found via the link below. https://github.com/akivajp/dnsmasq-webconf

    First, we need to install git and pip

    # dnf -y install git
    # dnf -y install pip

    Then we follow the directions which I will repeat here.

    # mkdir -p ~/git && cd ~/git
    # git clone https://github.com/akivajp/dnsmasq-webconf.git

    Then we use pip to install jinja2

    # pip install --user bottle jinja2

    Now change directory

    # cd dnsmasq-webconf/

    We now need to poke a hole for http traffic in our local firewall

    # firewall-cmd --add-service=http --permanent
    # firewall-cmd --reload

    Now start the front end

    #  python ~/git/dnsmasq-webconf/app/index.py 80 --leases /var/lib/dnsmasq/dnsmasq.leases --hosts /etc/hosts --config /etc/dnsmasq.conf

    Creating a Service

    So far we have dnsmasq configured and running, and we have installed a web front end and have been able to start it on the command line. Now we need to configure the front end to start as a service when the OS boots. So we now need to turn the webUI into a systemd service.

    First we create the following service file

    # vi /etc/systemd/system/dnsmasq-webconf.service

    The contents of which are below. Note that we have modified relative paths to be absolute paths.

    [Unit]
    Description=DNSMasq WebConf
    After=network.target
    
    [Service]
    ExecStart=/usr/bin/python3 /root/git/dnsmasq-webconf/app/index.py 80 --leases /var/lib/dnsmasq/dnsmasq.leases --hosts /etc/hosts --config /etc/dnsmasq.conf
    Restart=always
    User=root
    WorkingDirectory=/root/git/dnsmasq-webconf/app
    StandardOutput=journal
    StandardError=journal
    
    [Install]
    WantedBy=multi-user.target

    Now we need to reload systemd

    # systemctl daemon-reload

    Now we can start the service

    # systemctl start dnsmasq-webconf.service

  • Getting Started with RamaLama with Nvidia Cuda Support On Ubuntu 24.04

    Getting Started with RamaLama with Nvidia Cuda Support On Ubuntu 24.04

    Introduction to RamaLama

    Streamlining AI Deployment with OCI Containers

    RamaLama is an open-source project developed to simplify AI model deployment and management using OCI (Open Container Initiative) containers. Ramalama enables seamless execution of AI workloads across different hardware configurations, supporting both GPU-accelerated and CPU-based environments.

    By leveraging container engines like Podman and Docker, RamaLama includes all necessary dependencies, eliminating complex installation and dependency nightmares.

    Ramalama integrates with AI model registries such as Hugging Face and Ollama, providing flexibility in model selection. Key features include automatic GPU detection, CPU fallback, and optional direct execution on the host system.

    Prerequisites

    Updating Ubuntu

    First let’s confirm our Ubuntu version

    $ sudo lsb_release -a
    No LSB modules are available.
    Distributor ID:	Ubuntu
    Description:	Ubuntu 22.04.5 LTS
    Release:	22.04
    Codename:	jammy
    

    Run the two commands below to update your package cache and install any updates. Reboot if required.

    $ sudo apt-get update
    $ sudo apt-get upgrade -y

    Installing podman

    $ sudo apt -y install podman
    # sudo podman --version
    podman version 5.0.3

    Installing Nvidia Drivers

    Assuming you added third-party repos at build time, we should be able to check the suggested NVIDIA driver version. Do so with the command below

    $ nvidia-detector
    nvidia-driver-545

    The command below confirms that we do not have an NVIDIA driver loaded.

    $ cat /proc/driver/nvidia/version
    cat: /proc/driver/nvidia/version: No such file or directory

    Now let’s install the NVIDIA driver.

    $ sudo ubuntu-drivers --gpgpu install

    And we need to install the nvidia-utils package. Make sure the package version matches your installed driver.

    $ sudo apt install nvidia-utils-535-server

    Now reboot.

    Once your system is back up. Run the command below to verify that the drivers installed correctly. At the top of the output you should see your driver version and CUDA API version

    $ sudo nvidia-smi

    You must configure the persistence daemon (nvidia-persistenced) to start at boot and run continuously. Otherwise, the driver may unload, causing the Tesla GPUs to deinitialize, requiring a full reinitialization when nvidia-smi is executed. Additionally, failing to keep nvidia-persistenced running could lead to more severe issues, such as GPU crashes, depending on the workload.

    Enable and start the service below

    $ sudo systemctl start nvidia-persistenced
    $ sudo systemctl status nvidia-persistenced
    

    Installing Nvidia Cuda Toolkit

    Run the command below to install the nvidia-cuda-toolkit from the default Ubuntu repos.

    $ sudo apt install nvidia-cuda-toolkit -y

    Now test to ensure proper install and that new binary files are in your path.

    ~# nvcc --version
    nvcc: NVIDIA (R) Cuda compiler driver
    Copyright (c) 2005-2021 NVIDIA Corporation
    Built on Thu_Nov_18_09:45:30_PST_2021
    Cuda compilation tools, release 11.5, V11.5.119
    Build cuda_11.5.r11.5/compiler.30672275_0
    

    Configuring Podman with Nvidia Cuda Support

    Following along with this document from the RamaLama github page, we first need to install the nvidia-container-toolkit.

    First configure the repo. Note that this is one command. See here for more info.

    $ sudo curl -fsSL https://nvidia.github.io/libnvidia-container/gpgkey | sudo gpg --dearmor -o /usr/share/keyrings/nvidia-container-toolkit-keyring.gpg \
      && curl -s -L https://nvidia.github.io/libnvidia-container/stable/deb/nvidia-container-toolkit.list | \
        sed 's#deb https://#deb [signed-by=/usr/share/keyrings/nvidia-container-toolkit-keyring.gpg] https://#g' | \
        sudo tee /etc/apt/sources.list.d/nvidia-container-toolkit.list

    Refresh the repos

    # sudo apt-get update

    Then install the toolkit

    $ sudo apt install nvidia-container-toolkit -y

    Then run the command below to create the CDI spec file

    $ sudo nvidia-ctk cdi generate --output=/etc/cdi/nvidia.yaml

    Now lets check the detected devices

    $ nvidia-ctk cdi list

    My two Telsa T4s have been detected

    INFO[0000] Found 5 CDI devices                          
    nvidia.com/gpu=0
    nvidia.com/gpu=1
    nvidia.com/gpu=GPU-1d877ac8-5df1-34b0-4f86-59945e37d2ba
    nvidia.com/gpu=GPU-9491a3e6-ea29-ba4e-4403-083244d5575c
    nvidia.com/gpu=all
    

    Test the install/config

    $ sudo podman run --rm --device=nvidia.com/gpu=all fedora nvidia-smi

    Installing Python pip

    Lets first make sure that python 3 is installed

    $ python3 --version
    Python 3.12.7

    Now we need to install the virtual-env module for python

    $ sudo apt install python3.10-venv

    Installing RamaLama via Pip in a Python Virt Env

    Create a directory for ramalama, and cd to that directory

    $ mkdir ramalama && cd ramalama

    Create virtual env and source to activate

    $ python3 -m venv --upgrade-deps venv
    $ source venv/bin/activate

    Now pip install

    $ pip install ramalama

    Now run a model as a test

    $ ramalama run instructlab/merlinite-7b-lab

    In another window, run the commands shown below to view the ramalama container running in your python virtual env. Note that the output of podman ps will be empty unless your “activate” your virtual env.

    $ source venv/bin/activate
    $ podman ps

    Screenshot below


    Example CLI Commands

    Pull a model.

    $ ramalama pull ollama://mistral

    List downloaded models.

    $ ramalama list
    NAME                             MODIFIED       SIZE   
    ollama://mistral:latest          42 seconds ago 3.83 GB
    ollama://merlinite-7b-lab:latest 10 hours ago   4.07 GB
    

    Run a model

    $ ramalama run mistral:latest

    Info on ramalama itself. Output will tell you detected GPUs and what driver is being used.

    $ ramalama info

    –dryrun flag provides the podman command used to serve/run a model

    $  ramalama --dryrun run instructlab/merlinite-7b-lab 
    podman run --rm -i --label ai.ramalama --name ramalama_6buqEjuCUm --env=HOME=/tmp --init --security-opt=label=disable --cap-drop=all --security-opt=no-new-privileges --label ai.ramalama.model=instructlab/merlinite-7b-lab --label ai.ramalama.engine=podman --label ai.ramalama.runtime=llama.cpp --label ai.ramalama.command=run --pull=newer -t --device /dev/dri --device nvidia.com/gpu=all -e CUDA_VISIBLE_DEVICES=0 --network none --mount=type=bind,src=/home/cpaquin/.local/share/ramalama/models/ollama/merlinite-7b-lab:latest,destination=/mnt/models/model.file,ro quay.io/ramalama/cuda:latest llama-run -c 2048 --temp 0.8 --ngl 999 /mnt/models/model.file 
    
    

    There are a whole load of other topics that I will eventually get into with ramalama

    1. GPU Support/Enablement
    2. RAG
    3. Whisper

    More to come at a later date. In the meantime, take a look at the “Resources” section below.

    Additional Video

    Resources

    1. https://github.com/containers/ramalama
    2. https://github.com/containers/ramalama/blob/main/docs/ramalama.1.md
    3. https://developers.redhat.com/articles/2024/11/22/how-ramalama-makes-working-ai-models-boring
    4. https://developers.redhat.com/blog/2024/12/17/simplifying-ai-ramalama-and-llama-run
    5. https://www.linkedin.com/pulse/ollama-much-try-ramalama-surya-rekha-tw5kf/
  • Running RHEL 8 on Dell R710/610 via Raid Controller Retrofit

    Running RHEL 8 on Dell R710/610 via Raid Controller Retrofit

    A while back, I wrote a blog post that outlined a process of injecting deprecated storage controller drivers into RHEL 8 via a Driver Update Disk.

    In a nutshell, this process allows you to install RHEL 8 on the R710/R610 (11th Gen)

    This process worked fine, unless you wanted to yum update your server. Rather than attempt to find a repeatable process of injecting drivers prior to updating, I decided to upgrade my RAID controller to one that was supported.

    My 11th generation, R710, came with a Perc H700. Identified below.

    # lspci -knn | grep 'RAID bus controller'
    03:00.0 RAID bus controller [0104]: Broadcom / LSI MegaRAID SAS 2108 [Liberator] [1000:0079] (rev 05)
    

    Based on feedback from friends and co-workers. I purchased a PERC H330, which I believe ships with the 13th Gen Dell rackmount servers.

    These cards can be found for pretty cheap on Ebay. Make sure that you order one with the correct bracket based on your needs (full-height/half-height).

    Plus you will need 2 new cables. You are looking for SFF8643 to SFF8087 (mini SAS HD to mini SAS). They are also cheap and can be found on Ebay/Amazon

    Output from one of my Dell R710s. Note I did not remove the original card.

    # lspci -knn | grep 'RAID bus controller'
    03:00.0 RAID bus controller [0104]: Broadcom / LSI MegaRAID SAS 2108 [Liberator] [1000:0079] (rev 05)
    05:00.0 RAID bus controller [0104]: Broadcom / LSI MegaRAID SAS-3 3108 [Invader] [1000:005d] (rev 02)
    

    Afterthoughts

    I’ve only performed this swap on one of my R710s, I have 2 more as well as 2 R610s. Below are are few things to consider if you are looking to perform a similar upgrade

    1. Take a hard look at your existing server. Do you need to purchase a full sized pci card or a mini card? This may likely be the case on the 1u servers and may be a blocker for you
    2. Remove the old card. The server does not quite like having a raid controller installed without cables.
    3. If you buy a full-sized pci card, make sure you get one with the bracket that you need (full height vs. half height vs. no bracket)
    4. You might want to find a cable with 90 degree connectors for the backplane. Mine fit fine on the 710, but I have heard that the 90 degree connector is best for 1U servers.
    5. You may want to consider upgrading your 11th generation server to an 12th generation Dell, R720/R620s can be purchased relatively cheaply and the RAM and disks in your 11th gen will work in a newer 12th generation. (note that the 11th gen Dell CPUs are socket LGA1366, while the 12th gen Dells utilize socket LGA2011)

    Additional Resources

    https://docs.redhat.com/en/documentation/red_hat_enterprise_linux/8/html/considerations_in_adopting_rhel_8/hardware-enablement_considerations-in-adopting-rhel-8#removed-adapters_hardware-enablement