☰
Jetson Orin 上 RealSense 与 ROS2 环境搭建避坑指南
2026/9/25 4:24:48 网站建设 项目流程

1. 为什么要在 Jetson Orin 上折腾 RealSense 加 ROS2

如果你手上正好有一块 Jetson Orin 系列(不管是 Orin Nano、Orin NX 还是 AGX Orin),又碰巧拿到了一台 Intel RealSense D435i 或者 D455,打算跑机器人视觉、SLAM、机械臂抓取这类项目,那大概率绕不开 ROS2 这套中间件。问题在于,这三样东西凑在一起,坑比想象中多得多:Jetson 是 ARM64 架构,RealSense 官方 SDK 在 x86 上顺风顺水,到了 ARM 上就得自己编译内核模块;ROS2 的版本又和 Ubuntu 版本强绑定,装错一个版本,后面全是连锁反应。

我自己前前后后在 Orin Nano 和 Orin NX 上搭过好几套环境,从 JetPack 5.1 到 6.x,从 ROS2 Foxy 到 Humble,踩过的坑基本能写一本小册子。这篇就把整个流程从头到尾捋一遍,重点放在那些官方文档不会告诉你、但实际一定会卡住你的地方。目标很明确:让你在一块全新的 Orin 上,从刷机后的干净系统开始,一路走到能在 RViz2 里看到 RealSense 的点云和图像,中间不用反复重装系统。

适合谁看?如果你是完全没接触过 ROS2 的新手,这篇能当入门实操手册用;如果你已经会 ROS2 但第一次在 ARM 平台上搞 RealSense,那避坑部分对你价值最大。整篇内容基于 JetPack 6.x 加 Ubuntu 22.04 加 ROS2 Humble 这套目前最稳的组合来写,其他版本我会在对应位置标注差异。

先说结论性的判断:在 Jetson Orin 上搭 RealSense 加 ROS2,最大的三个坑分别是内核模块编译、ROS2 版本与 apt 源匹配、以及 USB 带宽与供电。这三个问题解决了,剩下的都是常规操作。下面按顺序拆。

2. 环境整体设计与版本选型思路

2.1 先定版本,别急着敲命令

很多人一拿到板子就急着apt install,结果装到一半发现版本对不上,只能重来。Jetson 平台的版本选择有一条硬约束链:JetPack 版本决定 Ubuntu 版本,Ubuntu 版本决定 ROS2 版本,ROS2 版本又影响 RealSense 的 ROS2 包兼容性。这条链上任何一环错位,后面都要返工。

目前主流的搭配是这样的:

JetPack 版本Ubuntu 版本推荐 ROS2 版本RealSense ROS2 包状态
JetPack 5.1.xUbuntu 20.04Foxy / Humble可用,Humble 需源码编译
JetPack 6.0/6.1Ubuntu 22.04Humble官方 apt 包直接可用
JetPack 6.2+Ubuntu 22.04Humble / JazzyHumble 最稳,Jazzy 生态尚在完善

我强烈建议新手直接上JetPack 6.x + Ubuntu 22.04 + ROS2 Humble。原因很简单:Humble 是 LTS 版本,官方维护到 2027 年,社区资料最全,ros-humble-realsense2-camera这个包在 ARM64 上有现成的 apt 源,不用自己编译 ROS 侧的代码。Foxy 虽然也能用,但已经停止维护,遇到问题搜到的答案越来越少。

至于 Jazzy,它在 x86 上已经很成熟了,但 ARM64 的预编译包覆盖度还不如 Humble,RealSense 相关的包有时候要自己编,对新手不友好。除非你有明确的理由必须用新版本,否则 Humble 是性价比最高的选择。

2.2 为什么 RealSense 在 ARM 上要单独编译内核模块

这是整个流程里最容易被低估的一环。RealSense 的深度相机依赖几个内核模块:uvcvideo、videodev、hid_sensor_*等。在 x86 的 Ubuntu 上,这些模块通常已经随内核打包好了,插上相机就能识别。但 Jetson 用的是 NVIDIA 定制的内核(基于 Tegra 平台),默认内核配置里没有开启 RealSense 需要的某些 UVC 元数据支持,尤其是CONFIG_VIDEO_UVC_METADATA这类选项。

结果就是:你插上 D435i,lsusb能看到设备,但rs-enumerate-devices报错,或者只能出彩色图出不了深度图。这不是驱动没装,而是内核模块的元数据通道没打通。解决办法有两个:一是用 RealSense 官方提供的patch-realsense-ubuntu-L4T.sh脚本给内核打补丁后重新编译模块,二是升级到较新的 JetPack 版本,NVIDIA 已经在新内核里默认开启了这些选项。

我实测下来,JetPack 6.x 的内核已经基本满足要求,但为了保险,还是建议跑一遍官方的内核补丁脚本,把该开的选项都确认一遍。这个脚本在librealsense仓库的scripts目录下,专门针对 L4T(Linux for Tegra)平台。

2.3 ROS2 与 DDS 的关系,为什么会影响 RealSense 使用

ROS2 底层用的是 DDS 做通信,Jetson 上默认的 DDS 实现(通常是 Fast DDS 或 Cyclone DDS)对网络配置比较敏感。RealSense 的 ROS2 节点会发布图像、深度、点云等多种话题,数据量很大,如果 DDS 的缓冲区配置不当,会出现话题能列出但收不到数据、或者 RViz2 里画面卡顿的情况。

这不是 RealSense 本身的问题,而是 DDS 在大数据量场景下的调优问题。后面在实操部分我会给出具体的环境变量配置,把 DDS 的共享内存和缓冲区调大,能明显改善点云传输的流畅度。这一点在官方教程里基本不会提,但实际做机械臂抓取或者 SLAM 时,点云卡顿会直接导致算法失效。

3. 系统准备与基础环境搭建

3.1 刷机后的第一件事:确认系统状态

假设你已经用 SDK Manager 刷好了 JetPack,系统第一次启动进入 Ubuntu 桌面。先别急着装东西,打开终端确认几个关键信息:

# 确认 L4T 版本 cat /etc/nv_tegra_release # 确认 Ubuntu 版本 lsb_release -a # 确认内核版本 uname -r # 确认架构 dpkg --print-architecture

dpkg --print-architecture应该输出arm64。如果输出amd64,说明你拿错机器了。/etc/nv_tegra_release会显示类似# R36 (release), REVISION: 3.0的信息,R36 对应 JetPack 6.x,R35 对应 JetPack 5.x。

注意:Jetson Orin Nano 出厂可能预装的是较老的 JetPack,如果你拿到的是二手板子或者别人刷过的,务必先确认版本,避免后面 apt 源对不上。

3.2 换源与基础依赖安装

Jetson 默认的 apt 源在国内访问速度一般,建议换成国内镜像源。但这里有个坑:Jetson 的源和普通 Ubuntu 的源不一样,它需要包含 NVIDIA 的 L4T 仓库。如果你直接把 x86 Ubuntu 的源贴进去,会破坏系统。

正确的做法是只替换 Ubuntu 的 ports 源部分,保留 NVIDIA 的源。具体操作:

# 备份原源 sudo cp /etc/apt/sources.list /etc/apt/sources.list.bak # 查看当前源内容,确认哪些是 ubuntu ports,哪些是 nvidia cat /etc/apt/sources.list

通常 Jetson 的源文件里会有ports.ubuntu.com这样的地址,把它替换成国内镜像即可。NVIDIA 的repo.download.nvidia.com那几行不要动。

换完源之后,安装基础依赖:

sudo apt update sudo apt upgrade -y sudo apt install -y \ build-essential \ cmake \ git \ wget \ curl \ libssl-dev \ libusb-1.0-0-dev \ libudev-dev \ pkg-config \ libgtk-3-dev \ libglfw3-dev \ libgl1-mesa-dev \ libglu1-mesa-dev \ python3-dev \ python3-pip

这些依赖里,libusb-1.0-0-dev和libudev-dev是 RealSense 编译必需的,libgtk-3-dev和libglfw3-dev是 RealSense Viewer 需要的。少装一个,编译到一半就会报错。

3.3 安装 ROS2 Humble 的正确姿势

ROS2 Humble 在 Ubuntu 22.04 上的安装,官方文档写得很清楚,但 Jetson 上有个特殊点:ROS2 的 apt 源需要确认有 arm64 的包。Humble 的官方源是支持 arm64 的,所以直接按官方步骤走就行。

# 添加 ROS2 源 sudo apt install -y software-properties-common sudo add-apt-repository universe sudo apt update && sudo apt install -y curl sudo curl -sSL https://raw.githubusercontent.com/ros/rosdistro/master/ros.key \ -o /usr/share/keyrings/ros-archive-keyring.gpg echo "deb [arch=$(dpkg --print-architecture) signed-by=/usr/share/keyrings/ros-archive-keyring.gpg] \ http://packages.ros.org/ros2/ubuntu $(. /etc/os-release && echo $UBUNTU_CODENAME) main" | \ sudo tee /etc/apt/sources.list.d/ros2.list > /dev/null sudo apt update

这里有个网络问题:raw.githubusercontent.com在国内访问可能不稳定。如果卡住,可以手动下载 key 文件,或者用其他方式获取。key 文件的作用是验证包的签名,不能跳过。

安装 ROS2 基础包:

sudo apt install -y ros-humble-desktop

ros-humble-desktop包含了 RViz2、demo 节点、教程等,适合开发用。如果空间紧张,可以只装ros-humble-ros-base,但那样就没有 RViz2 了,后面看 RealSense 数据会不方便。

安装完成后,配置环境变量:

echo "source /opt/ros/humble/setup.bash" >> ~/.bashrc source ~/.bashrc

验证安装:

ros2 run demo_nodes_cpp talker

另开一个终端:

ros2 run demo_nodes_py listener

如果能看到 talker 发的消息被 listener 收到,说明 ROS2 基础环境没问题。这一步很重要,不要跳过验证直接装 RealSense,否则后面出问题分不清是 ROS2 的问题还是 RealSense 的问题。

实操心得:如果你用的是鱼香 ROS 的一键安装脚本,确实能省事,但脚本会修改一些系统配置。在 Jetson 上我建议还是手动装,因为一键脚本对 ARM 平台的支持不一定完善,出问题不好排查。

4. RealSense 驱动与 ROS2 包的完整部署

4.1 内核模块补丁:最关键的一步

前面说过,Jetson 的内核默认可能缺少 RealSense 需要的 UVC 元数据支持。RealSense 官方提供了一个针对 L4T 的补丁脚本,在librealsense仓库里。先克隆仓库:

cd ~ git clone https://github.com/IntelRealSense/librealsense.git cd librealsense

然后运行 L4T 补丁脚本:

./scripts/patch-realsense-ubuntu-L4T.sh

这个脚本会做几件事:检查当前内核版本、下载对应版本的内核源码、打上 RealSense 需要的补丁、重新编译uvcvideo等模块。整个过程比较长,在 Orin Nano 上大概要 20 到 40 分钟,取决于 SD 卡速度。

脚本执行过程中可能会遇到几个问题:

  • 内核源码下载失败:脚本会从 NVIDIA 的源下载内核源码,网络不好会卡住。可以手动下载后放到指定目录。
  • 编译报错缺少依赖:通常是libssl-dev或flex、bison没装,补上即可。
  • 脚本提示内核版本不匹配:如果你用的是 JetPack 6.2 这种很新的版本,脚本可能还没更新支持。这时候可以跳过补丁,直接测试相机是否能出深度图,如果能出就不用打补丁。

补丁打完,重启系统:

sudo reboot

重启后验证模块是否加载:

lsmod | grep uvcvideo

应该能看到uvcvideo模块。如果没看到,说明补丁没生效,需要回头检查。

4.2 编译安装 librealsense SDK

内核模块搞定后,编译 RealSense 的 SDK。这一步在 ARM 上比 x86 慢很多,Orin Nano 上大概要 30 到 60 分钟。

cd ~/librealsense mkdir build && cd build cmake .. -DBUILD_EXAMPLES=true \ -DFORCE_RSUSB_BACKEND=false \ -DBUILD_WITH_CUDA=true \ -DCMAKE_BUILD_TYPE=Release make -j$(nproc) sudo make install

几个关键参数解释一下:

  • -DBUILD_EXAMPLES=true:编译示例程序,包括rs-enumerate-devices和realsense-viewer,方便测试。
  • -DFORCE_RSUSB_BACKEND=false:这个参数很关键。RSUSB 后端是不依赖内核模块的纯用户态驱动,但性能不如内核态。既然我们已经打了内核补丁,就用内核态,性能更好。如果补丁没成功,可以改成true作为备选方案。
  • -DBUILD_WITH_CUDA=true:Jetson 有 CUDA,开启后某些处理可以用 GPU 加速。但注意,这个选项有时候会导致编译报错,如果报错就改成false。
  • -DCMAKE_BUILD_TYPE=Release:Release 模式编译,性能更好,编译时间也更短。

编译完成后,配置 udev 规则,让普通用户也能访问相机:

sudo cp config/99-realsense-libusb.rules /etc/udev/rules.d/ sudo udevadm control --reload-rules && sudo udevadm trigger

然后重新插拔相机,测试:

rs-enumerate-devices

如果能看到 D435i 的详细信息,包括序列号、固件版本、支持的分辨率,说明 SDK 安装成功。

注意:如果rs-enumerate-devices报No device connected,先检查 USB 连接。Jetson Orin Nano 的 USB 口供电能力有限,D435i 最好用带供电的 USB Hub,或者插在供电充足的 USB 3.0 口上。我遇到过好几次因为供电不足导致设备时认时不认的情况。

4.3 安装 RealSense 的 ROS2 包

SDK 装好后,ROS2 包就简单了。Humble 有现成的 apt 包:

sudo apt install -y ros-humble-realsense2-camera ros-humble-realsense2-description

realsense2-camera是驱动节点,realsense2-description是 URDF 描述文件,后面在 RViz2 里显示相机模型会用到。

如果你用的 ROS2 版本没有现成的 apt 包,或者想用最新版,可以从源码编译:

cd ~/ros2_ws/src git clone https://github.com/IntelRealSense/realsense-ros.git -b ros2-development cd ~/ros2_ws rosdep install -i --from-path src --rosdistro humble -y colcon build --symlink-install

源码编译的好处是可以用最新的功能和修复,坏处是每次更新都要重新编译。新手建议先用 apt 包,稳定优先。

4.4 启动相机节点并验证数据

启动 RealSense 的 ROS2 节点:

ros2 launch realsense2_camera rs_launch.py

默认会启动彩色、深度、红外等多个流。如果只想启动深度和彩色:

ros2 launch realsense2_camera rs_launch.py \ enable_color:=true \ enable_depth:=true \ enable_infra1:=false \ enable_infra2:=false \ enable_gyro:=false \ enable_accel:=false

D435i 带 IMU,如果不用 IMU 可以关掉,减少数据量和 CPU 占用。

另开终端查看话题:

ros2 topic list

应该能看到/camera/color/image_raw、/camera/depth/image_rect_raw、/camera/color/camera_info等话题。查看帧率:

ros2 topic hz /camera/color/image_raw

正常应该在 30Hz 左右。如果帧率很低或者话题没有数据,参考后面的排查部分。

在 RViz2 里查看点云:

rviz2

在 RViz2 里添加 PointCloud2 显示,话题选/camera/depth/color/points,Fixed Frame 设为camera_link。如果能看到彩色的点云,恭喜你,环境搭好了。

5. 常见问题与排查技巧实录

5.1 相机识别不到或时认时不认

这是最高频的问题。表现是lsusb能看到 Intel 的设备,但rs-enumerate-devices报错,或者 ROS2 节点启动后话题没有数据。

排查顺序:

  1. 检查 USB 连接:D435i 必须用 USB 3.0 线,且线材质量要好。劣质线材会导致带宽不足,深度流无法启动。换一根官方线或者确认支持 3.0 的线试试。
  2. 检查供电:Orin Nano 的 USB 口供电有限,如果同时接了其他外设,相机可能供电不足。用带外部供电的 USB Hub。
  3. 检查 udev 规则:确认99-realsense-libusb.rules已经复制到/etc/udev/rules.d/,并且执行了udevadm trigger。
  4. 检查内核模块:lsmod | grep uvcvideo确认模块加载。如果没加载,重新跑补丁脚本。

我遇到过一次特别诡异的情况:相机在 Orin NX 上正常,换到 Orin Nano 上就不认。最后发现是 Orin Nano 的某个 USB 口和相机的 USB 控制器兼容性问题,换一个口就好了。所以换口测试是排查硬件问题的第一步。

5.2 深度图能出但点云卡顿

点云卡顿通常不是相机的问题,而是 DDS 传输的问题。ROS2 默认的 DDS 配置对大数据量话题不够友好。解决办法是调整 DDS 参数。

如果用 Fast DDS,可以设置环境变量:

export RMW_IMPLEMENTATION=rmw_fastrtps_cpp export FASTRTPS_DEFAULT_PROFILES_FILE=~/fastdds_profile.xml

然后创建一个配置文件fastdds_profile.xml:

<?xml version="1.0" encoding="UTF-8"?> <profiles xmlns="http://www.eprosima.com/XMLSchemas/fastRTPS_Profiles"> <transport_descriptors> <transport_descriptor> <transport_id>UdpTransport</transport_id> <type>UDPv4</type> <sendBufferSize>1048576</sendBufferSize> <receiveBufferSize>1048576</receiveBufferSize> </transport_descriptor> </transport_descriptors> <participant profile_name="participant_profile" is_default_profile="true"> <rtps> <userTransports> <transport_id>UdpTransport</transport_id> </userTransports> <useBuiltinTransports>false</useBuiltinTransports> </rtps> </participant> </profiles>

把发送和接收缓冲区调到 1MB,能明显改善点云传输。另外,如果不需要跨机器通信,可以用共享内存传输,速度更快。

5.3 ROS2 命令找不到或环境变量失效

ros2: command not found这个问题,九成是环境变量没 source。检查~/.bashrc里有没有source /opt/ros/humble/setup.bash。如果有但还是不行,可能是 ROS2 没装成功,重新执行安装步骤。

另一个常见情况是:装了 ROS2 之后又装了其他软件,把~/.bashrc覆盖了。所以建议把 source 命令放在~/.bashrc的最后,或者单独写一个~/.ros2_env文件,在~/.bashrc里 source 它。

5.4 常见问题速查表

现象可能原因解决方法
rs-enumerate-devices无设备USB 供电/线材/udev换线、换口、检查 udev 规则
只有彩色无深度内核模块缺元数据支持跑 L4T 补丁脚本,重启
点云卡顿DDS 缓冲区不足调大 Fast DDS 缓冲区
ROS2 节点启动报错版本不匹配确认 ROS2 版本与包版本一致
RViz2 无点云Fixed Frame 错误设为 camera_link
编译 librealsense 报错缺依赖补装 libssl-dev、libusb 等
帧率低USB 带宽不足降低分辨率或关闭部分流

5.5 几个独家避坑技巧

技巧一:先测试再编译。在编译 librealsense 之前,先用realsense-viewer(如果 JetPack 里有预装的)或者简单的 Python 脚本测试相机是否能出图。如果相机本身有问题,编译再久也没用。

技巧二:保留一份可用的系统镜像。Jetson 上折腾环境,很容易把系统搞乱。建议在环境搭好后,用dd或者 SDK Manager 备份一份镜像。下次出问题直接恢复,比重新搭快得多。

技巧三:注意散热。Orin Nano 在编译 librealsense 时 CPU 满载,如果散热不好会降频,编译时间翻倍。加个风扇或者确保散热片接触良好。

技巧四:ROS2 的 QoS 设置。RealSense 的图像话题默认用SENSOR_DATAQoS,这种 QoS 不保证可靠传输,但延迟低。如果你在 RViz2 里看不到图像,检查 QoS 设置是否匹配。RViz2 里可以手动设置 QoS 策略。

6. 从环境搭建到实际项目的延伸

6.1 用 RealSense 做机械臂抓取的前置准备

环境搭好后,下一步通常是做视觉抓取。D435i 在机械臂场景里很常见,因为它有 IMU,可以做手眼标定。在 ROS2 里,你需要额外安装ros-humble-realsense2-description来获取相机的 URDF,然后配合robot_state_publisher和tf2做坐标变换。

手眼标定的核心是确定相机坐标系和机械臂末端坐标系的关系。常用工具是easy_handeye2或者moveit的标定功能。这部分内容展开又是一大篇,这里只提一个关键点:标定前确保 RealSense 的内参已经正确读取。可以用rs-enumerate-devices -c查看相机内参,或者在 ROS2 里订阅/camera/color/camera_info话题。

6.2 点云与八叉树地图导航

如果你打算用 RealSense 做导航,点云转八叉树地图是常见流程。ROS2 里有octomap_server2或者octomap的 ROS2 移植版。RealSense 的点云话题可以直接喂给 octomap 节点,生成三维占据栅格地图。

这里有个性能问题:D435i 的点云数据量很大,直接喂给 octomap 会占用大量 CPU。建议先做降采样,用pcl_ros的 VoxelGrid 滤波器把点云稀疏化,再送给 octomap。在 Orin 上,还可以用 CUDA 加速点云处理,但需要自己写节点或者用现成的 GPU 版本 PCL。

6.3 在 Orin 上跑视觉模型的注意事项

很多人搭 RealSense 环境是为了跑视觉模型,比如 YOLO 或者分割网络。Orin 有 GPU,跑推理没问题,但要注意:RealSense 的 ROS2 节点和推理节点会抢 CPU 和内存。建议把相机节点的分辨率调低,或者用硬件编码的流。

另外,ROS2 的图像传输如果走 DDS,会有序列化和反序列化的开销。如果推理节点和相机节点在同一台机器上,可以用image_transport的compressed或者raw模式,减少开销。更激进的做法是直接用共享内存传图像,但这需要自己写节点。

6.4 后续可以扩展的方向

环境搭好只是起点。基于这套环境,你可以做很多事情:SLAM 建图(用slam_toolbox或rtabmap)、目标检测与跟踪、三维重建、机械臂视觉伺服等。每个方向都有对应的 ROS2 包,大部分在 Humble 上都有支持。

我个人建议先从rtabmap入手,它集成了 RealSense 的驱动,能直接出三维地图和定位结果,适合快速验证环境是否真的可用。跑通rtabmap之后,再根据自己的项目需求深入。

最后分享一个我在实际使用中的体会:Jetson Orin 加 RealSense 这套组合,硬件本身很强大,但软件生态的成熟度还比不上 x86 加 Ubuntu 的组合。遇到问题的时候,多去 GitHub 的 issue 区搜,很多坑别人已经踩过并且给出了解决方案。另外,保持系统干净,不要装太多无关的包,能减少很多依赖冲突。环境搭好后,第一时间做备份,这个习惯能帮你省下大量重装的时间。

需要专业的网站建设服务?

联系我们获取免费的网站建设咨询和方案报价,让我们帮助您实现业务目标

立即咨询