☰
DMTF协议解析:从SMBIOS到Redfish的服务器硬件管理标准
2026/10/3 16:05:34 网站建设 项目流程

一台服务器摆在机柜里,系统进不去、网络也不通,唯一的线索就是背板的BMC网口和机器外壳上已经磨花了的序列号贴纸。如果你有一点带外管理的经验,这时候多半会打开BMC网页,或者直接在终端里敲几行curl命令去调Redfish接口,从/redfish/v1/Systems/1里面把序列号取回来;如果手头什么工具都没有,那就只能拆开机箱看主板丝印,或者想办法进系统用dmidecode读SMBIOS表再对照分析。

这两个名字——Redfish和SMBIOS,日常运维中几乎每个干服务器的人都会碰到,但很少有人会去想它们背后其实是同一个组织定义的。这个组织叫DMTF,Distributed Management Task Force,分布式管理任务组。这一篇我想把它的家底翻一翻,说清楚SMBIOS和Redfish到底各自解决什么问题、怎么协作、实际用的时候有哪些坑。这类内容主机厂商的技术文档不会系统讲,网上的资料又太零散,所以我打算用系列文章的方式从最基础的概念开始,一篇一篇拆开讲。

1. 关于DMTF:硬件管理标准背后的“共同委员会”

1.1 DMTF的定位与历史

DMTF成立于1992年,原名Desktop Management Task Force,直译是“桌面管理任务组”。你会发现这个组织最初的目标其实很朴素:当年PC开始大规模进入企业,IT部门需要管理一堆不同品牌的PC,但戴尔、惠普、IBM各搞各的管理指令,互相之间不通用,管理一个机房等于同时维护好几套私有协议。

于是这些厂商坐下来,成立了一个中立组织,大家共同制定和推进管理标准。后来管理需求从桌面PC扩展到服务器、存储、网络设备,组织也更名为Distributed Management Task Force,名字里“Desktop”换成了“Distributed”,范围明显扩大。到今天,DMTF旗下有SMBIOS、Redfish、CIM、PMCI、DASH等多个标准家族,几乎覆盖了从PC到整座数据中心的硬件管理。

这里有个小知识值得留意:DMTF不是政府机构,也不像IEEE那样古板,它本质上是一个行业联盟,成员包括Dell、HPE、Lenovo、Intel、AMD、Microsoft、Broadcom、BMC Software等一大批软硬件厂商。正因为是厂商坐下来一起谈的产物,它的标准往往非常接地气,会充分考虑现实中既有的硬件生态和兼容性需求。

1.2 厂商为什么愿意把标准交给一个协会

做服务器的人应该有一个直觉:硬件厂商通常最不喜欢开放标准,因为它们要靠私有接口锁住客户。那DMTF凭什么能存活三十多年?

核心原因是管理接口和芯片级的私有技术不同。芯片可以靠指令集、微码、特殊硬件IP来形成壁垒,但管理接口如果完全私有,客户、系统软件、运维工具都无法统一对接,整个产业的运维成本会高得离谱。尤其是云时代,客户要求一套工具能同时管理多个品牌的服务器,如果每家厂商都用自己的API,云厂商就要写几十套适配代码,这是不可持续的。

DMTF做的事就是把这些接口标准前置化、模块化,让厂商在硬件出厂前就按照统一规范预留管理入口。厂商依然可以在规范之上增加私有扩展能力,但基础操作、数据格式、安全模型必须是通用的。这种做法既保住了厂商差异化的空间,又让下游客户和第三方软件有了稳定的依赖基础。

1.3 两条主线:SMBIOS描述数据,Redfish提供接口

DMTF体系内有很多标准,但对绝大多数服务器运维和开发人员来说,最重要的两条线就是SMBIOS和Redfish。可以这样理解:SMBIOS负责“描述”,它解决的是“硬件是什么、固件版本是多少、序列号是多少”这类静态信息的标准化;Redfish负责“操作”,它解决的是“状态查询、开关机、改启动顺序、收集日志、告警订阅”这类动态管理接口的标准化。

两条线发布时间相差二十年,但设计逻辑是一脉相承的。SMBIOS源自Intel在90年代提出的DMI标准,后来移交给DMTF维护,目前最新的规范是SMBIOS 3.6.0/3.7.0版本,定义了一套存放于内存中的数据结构表,操作系统和上层工具在启动时可以读取。Redfish则是2015年发布的,直接面向现代数据中心,采用HTTP/JSON/REST风格,让设备管理从“厂商命令行”升级为“可编程API”。

很多刚接触的人会误以为Redfish要取代SMBIOS,这是一个误区。实际上,两者考虑的是完全不同的层面,而且在不少场景下是互补关系。后面专门有一章展开讲它们的联动。

2. SMBIOS:藏在服务器“底板”上的硬件身份证

2.1 SMBIOS的数据结构与内存布局

SMBIOS的本质是一张存放在系统内存中的结构表,由BIOS/UEFI固件在开机时构建。这张表记录了主板、CPU、内存、BIOS版本、序列号、资产标签等信息。操作系统启动时,内核会去内存中查找SMBIOS入口点,然后把整个结构表解析出来,挂载到/sys/firmware/dmi/tables/下面,供用户态工具读取。

从规范层面看,SMBIOS规定了两类入口结构:32位入口点对应SMBIOS 2.x,标记是_SM_;64位入口点对应SMBIOS 3.x,标记是_SM3_。入口点里包含了结构表的物理地址和长度。传统的x86 BIOS会把这套表放在E0000h到EFFFFh之间的物理内存区域,也就是传统BIOS保留的那段空间;UEFI系统则通过EFI Configuration Table注册指向SMBIOS表,让加载UEFI的系统能直接访问。

这里的关键点是:SMBIOS不是一种“协议通信”,它更像是一个“信息仓库”。固件把结构化数据写好放在内存里,操作系统去取,中间没有握手、没有会话、没有动态交互。所以它的使用非常轻量,只要内存表没被破坏,读取基本零成本。

2.2 常见的Structure Type分别都在说什么

SMBIOS结构表由多个记录组成,每个记录都有一个类型号(Type)、长度和句柄(Handle)。我记得第一次看dmidecode输出时,满屏都是“Handle 0x0001, DMI type 1”,完全摸不着头脑。后来才发现,类型号才是理解SMBIOS的关键。这里把我工作中最常用的几个Type整理成了一张表:

Type名称关键信息
0BIOS InformationBIOS厂商、版本号、起始地址、BIOS特性
1System Information系统制造商、产品名、序列号、UUID
2Baseboard Information主板厂商、型号、序列号、资产标签
3Chassis Information机箱类型、厂商、版本号、序列号
4Processor InformationCPU厂商、系列、型号、频率、核心数、线程数
11OEM Strings厂商自定义的OEM字符串,常用作机架标签等
17Memory Device每根内存条的位置、容量、速率、制造商、序列号
41Onboard Devices Extended板载网卡、RAID卡等设备的类型和名称
42Redfish Host Interface用于发现Redfish带内接口的地址属性,后面会细说
127End of Table结构表结束标记

为什么需要这么细的分类?因为上层工具面对的是完全不同的消费方:资产管理系统只关心Type 1和Type 2,驱动安装脚本可能只关心Type 0和Type 4,固件更新工具要在Type 0里读BIOS版本,虚拟化平台则关心虚拟机的SMBIOS字符串。一个统一但分类清晰的结构表,让这些工具各取所需,不需要为不同厂商各写一份解析逻辑。

2.3 用dmidecode和sysfs读取SMBIOS

在Linux系统上读取SMBIOS,最经典的工具就是dmidecode。直接不带参数运行,它会列出所有Type的信息;也可以按类型过滤,比如只看系统型号和序列号:

dmidecode -t1 dmidecode -t2 dmidecode -t4 dmidecode -t17

需要说明的是,dmidecode通常需要root权限,因为它要访问物理内存映射或者/dev/mem。在较新的内核上,其实还可以直接从sysfs读取原始结构表,路径是/sys/firmware/dmi/tables/DMI,这是一份二进制数据。直接cat出来是乱码,但如果写脚本解析,倒是一个很不错的练习项目。

Windows下的对应工具就比较隐蔽了。很多人不知道,Windows自带的msinfo32里显示的“系统型号”和“BIOS版本/日期”大多来自SMBIOS。PowerShell下可以用Get-CimInstance Win32_BIOS和Get-CimInstance Win32_ComputerSystemProduct来读取,前者对应SMBIOS Type 0,后者对应Type 1。

我自己实际用得最多的是dmidecode -t1和dmidecode -t0。因为报修机器的时候,客服一定会问你序列号和BIOS版本;做资产盘点的时候,也要靠序列号来关联物理设备。除了dmidecode,DMTF官方还维护了一个libsmbios库和对应的命令行工具,感兴趣可以了解一下,它的字段解析比dmidecode更精细,适合做批量资产扫描的程序。

2.4 裸金属和虚拟化场景下的SMBIOS处理

这里有个很容易被忽略的坑:虚拟机的SMBIOS信息是虚拟化平台伪造出来的。在QEMU/KVM和VMware里,虚拟BIOS会生成一套SMBIOS表,但里面的厂商、序列号、UUID都是可以配置的。

云平台和虚拟化软件正是利用了这个特性来下发身份信息。比如OpenStack给虚拟机注入UUID时,就是通过nova配置里的smbios参数,把虚拟机实例的UUID写进SMBIOS Type 1。这样操作系统里读取到的序列号,就能和OpenStack实例的global UUID对应起来,排障时就能直接通过虚机里的序列号反查云平台记录。

做裸金属交付的时候,很多人会用一套预启动环境去扫描硬件配置,跑的就是dmidecode。但要注意,物理机上读取Type 17可以精确到每根内存条的位置和序列号,这对内存故障排查特别有用。你遇到过服务器报内存Cele,如果不确定是哪一根,dmidecode -t17就能把每个插槽的内存序列号列出来,再去内存标签上比对就行了。这在服务器售后里属于非常基础但实用的操作。

3. Redfish:用HTTP/JSON打造一个面向软件定义的带外管理API

3.1 Redfish出现的背景与技术选型逻辑

Redfish是DMTF在2015年发布的,它诞生的核心逻辑很清晰:旧时代的IPMI和WS-Man已经扛不住云时代的运维需求。

IPMI的问题在于它设计得太早了。IPMI依赖RMCP协议,走UDP 623端口,数据编码是IPMI命令格式,开发起来非常痛苦。用Python调IPMI,要么直接拼IPMI命令包,要么依赖ipmitool做进程调用,完全没有现代API那种“一切皆资源、资源皆可增删改查”的体验。而且IPMI的很多实现还是厂商自定义扩展,A厂商的fru信息字段和B厂商对不上是常态。

WS-Man是DMTF自己在标准管理接口领域的一次尝试,但它是基于SOAP/XML的,太重了,序列化和反序列化成本高,工具链不友好,生态一直没有做起来。

Redfish的选择非常聪明:直接拥抱互联网的主流API风格。传输层用HTTP/HTTPS,数据格式用JSON,资源模型借鉴OData v4规范,认证支持Session、Basic、TLS双向认证等。这个技术选型让任何一个会写REST API的开发者都能在一小时内上手,不需要学习任何私有格式,也不需要安装特殊的SDK。

3.2 资源模型与OData设计思路

Redfish的资源模型是全树状的。入口是/redfish/v1/,这个路径也叫ServiceRoot。从ServiceRoot出发,你可以发现所有其他的主要资源集合:Systems表示受管的主机系统,Chassis表示物理机箱/硬件框架,Managers表示管理控制器,也就是BMC自身,另外还有AccountService、SessionService、EventService、UpdateService等系统级服务。

这套模型借鉴了OData的资源概念,每种资源都有@odata.id作为唯一标识,有@odata.type声明类型,资源之间的关系通过Links字段链接。你可以把Redfish的BMC看作一台小型的Web服务,它上面挂着一张JSON组成的“关系图”,客户端只需要跟着链接往下走就能拿到所有信息。

举个例子,查询某个系统的状态,通常的路径是:

GET /redfish/v1/Systems/1

响应里会包含Status对象的State和Health字段,分别表示电源状态和健康状态。不同于传统CLI输出,JSON结构让这些数据可以直接被监控系统、自动化平台消费,不需要人去解析表格文本。

Redfish的另一个特点是“行为通过Action表达”。例如重启操作,请求/redfish/v1/Systems/1/Actions/ComputerSystem.Reset,方法为POST,body里指定ResetType,可选值包括GracefulRestart、ForceRestart、On、Off等。这种设计比IPMI那种魔法数字要直观得多。

3.3 一次真实场景的Redfish调用

纸上谈兵没有意义,我把自己在一台测试服务器上验证Redfish API的常用命令组合贴出来。假设BMC的IP是192.168.1.100,管理员账号是admin。

先用curl直接请求ServiceRoot,看看BMC支持哪些资源:

curl -k https://192.168.1.100/redfish/v1/ -u admin:password | jq .

-k是因为BMC通常使用自签名证书,生产环境建议把BMC证书换成企业CA签发,这样就不需要跳过校验了。

接下来获取系统信息:

curl -k https://192.168.1.100/redfish/v1/Systems/1 -u admin:password | jq '{Id, PowerState, Status, Model, SerialNumber, BiosVersion}'

这一步拿到的东西,很多其实就是SMBIOS提供的数据被BMC从系统侧拉回来后转成JSON暴露出来的。能看到SerialNumber字段,说明Redfish和SMBIOS在物理设备数据上是同源的。

再往后就是操作。比如把服务器开机:

curl -k -X POST https://192.168.1.100/redfish/v1/Systems/1/Actions/ComputerSystem.Reset \ -u admin:password \ -H "Content-Type: application/json" \ -d '{"ResetType": "On"}'

有些模块支持PowerCycle、GracefulRestart等数值,具体看资源的Actions链接里允许哪些。这就体现出了Redfish的另一个好处:它是一个能自我描述的API。你不必翻手册,只要GET当前资源,看Actions段里暴露了哪些可用操作和参数枚举,就能完成真正的“按需调用”。

3.4 事件订阅、固件刷新与自动化集成

除了查询和重启这种基础功能,Redfish还有三个非常能提效的能力:事件订阅、固件更新和带外网络配置。

事件订阅,英文叫Event Subscription。传统做法是运维脚本定时轮询BMC的报警状态,比如每5分钟检查一次/redfish/v1/Systems/1的Health字段。这样时效性差,而且产生大量无效请求。Redfish的事件订阅机制允许客户端在/redfish/v1/EventService/Subscriptions上创建一个订阅,指定回调地址和感兴趣的事件类型,比如StatusChange、Alert。当BMC产生对应事件时,会主动向订阅地址推送JSON事件消息。这就把“轮询”变成了“推送”,监控系统只需要处理推送过来的事件就行。

固件更新也是核心场景。Redfish通过UpdateService暴露固件升级功能,接口语义很简洁:POST一个多部分表单,把固件文件传上去,BMC负责后续的刷写和校验,客户端再通过TaskService监控任务进度。用这种方式做跨品牌服务器的固件批量升级,比自己找每家厂商的专属升级工具要省事得多。

带外网络配置也很重要。BMC网卡的IP地址、子网、VLAN等参数,现代Redfish实现通常都可以通过/redfish/v1/Managers/1/EthernetInterfaces/1来PATCH修改。这让自动化装机系统能在服务器第一次上电时就通过网络把BMC接口拉入正确的管理网络,而不是用串口线一台台去连。

4. Redfish与SMBIOS的联动关系:一个管内容,一个管传输

4.1 Redfish资源模型里为什么到处都是SMBIOS的影子

看到这里你可能已经发现了:Redfish返回的Model、SerialNumber、BiosVersion这些字段,和SMBIOS里Type 1、Type 0的内容几乎一一对应。这不是巧合,而是BMC固件在实现Redfish接口时,直接调用了固件侧的SMBIOS数据。

从协议层次上看,SMBIOS更像一个“内容仓库”,负责存放硬件和固件的描述信息;Redfish更像一个“服务接口”,负责把这些信息按标准格式对外开放。BMC通过后台通道读取到SMBIOS信息后,将其映射到Redfish资源模型的对应字段。可以类比成一个图书馆:SMBIOS是书架上的实体图书,Redfish是图书馆的检索服务,你通过Redfish搜到的书目信息,源头始终是书架上的书。

所以在排查“为什么Redfish里查不到序列号”时,不要只盯着Redfish服务本身,有时候问题出在SMBIOS信息缺失或损坏。BMC能拿到错误的SMBIOS数据,照样会把错误信息原封不动地抛给Redfish客户端。这在实际排障里是个容易走弯路的点。

4.2 SMBIOS Type 42:Redfish的带内入口由SMBIOS来定义

这里有一个非常丝滑的联动细节:Redfish的带内(In-band)Host Interface,是通过SMBIOS Type 42来定义的。

非带外场景下,我们通常通过BMC的独立网口访问Redfish。但在某些环境里,主机操作系统需要直接通过本机硬件与BMC通信,不需要额外的管理网线。这种“带内Redfish”的发现机制,就是SMBIOS Type 42。它记录了Host Interface Type、协议类型以及访问入口地址信息。操作系统里的Redfish客户端在启动后,可以从SMBIOS表中找到Type 42结构,拿到访问BMC服务所需的网络地址或设备标识,接着就像远程访问一样,直接通过本机回环或者专门的设备路径发起Redfish调用。

也就是说,SMBIOS对Redfish的价值不止是提供数据,它还能帮助Redfish服务被系统“发现”。设计得相当巧妙。以前有人问,“Redfish会不会取代SMBIOS?”答案是取代不了,因为Redfish的带内发现机制恰恰依赖SMBIOS来定位。

4.3 跨协议排查案例:Redfish拿不到SN的例子

我之前遇到一个很典型的案例。现场反馈一台服务器的Redfish接口能查询到CPU型号和内存容量,但SerialNumber字段是空的。第一反应是Redfish服务出了问题,结果反复验证BMC服务完全正常,其他字段都返回正常。

最后我把视角切到SMBIOS,进主机系统里跑了一遍dmidecode -t1,发现Type 1里的Serial Number确实为空。BMC在构建Redfish资源时读到的就是空值,自然不会有内容。问题的根源其实是主板上的SMBIOS数据在生产流程中没被正确刷写,属于硬件信息写入环节的问题,和Redfish本身一点关系都没有。

这个案例说明,如果你做的是带外管理系统,掌握SMBIOS的读取方式和数据结构,能显著加快这类跨层问题的定位速度。只会用Redfish的API是入门,能结合SMBIOS底层数据做判断,才算真正掌握这套协议栈。

4.4 选型边界:什么时候看SMBIOS,什么时候调Redfish

简单总结一下两个协议的适用场景。

想快速确认一台物理机的硬件配置和资产信息,尤其是不想依赖网络和BMC的时候,SMBIOS是最可靠的路径。因为它就在内存里,只要机器能开机、系统能起来,就能读取。资产管理、驱动匹配、固件版本核对、维修序列号获取,这些场景用SMBIOS足够了。

但如果你想做远程批量管理、自动化巡检、告警接收、固件升级、电源控制,那就必须走Redfish。它提供的是真正意义上的“控制面”能力,而不是只读信息。而且Redfish的安全性设计比SMBIOS完善得多,支持TLS、Session、RBAC权限控制,适合在数据中心里大规模使用。

选型没什么好纠结的,数据型需求找SMBIOS,操作型需求找Redfish,两者在实际产品中也是默认协同的。

5. 学习路径与避坑指南:从零开始上手DMTF协议

5.1 最小可用的学习环境搭建

如果你刚接触Redfish,不一定非要买一台真机。DMTF官方在GitHub上维护了redfish-mockup-server,它是一个模拟BMC的Python服务,打开之后会提供全套Redfish资源树,响应结构和真实BMC非常接近,非常适合拿来做API练习和客户端开发调试。

我自己常用的练习路径是这样:先用mockup server熟悉Redfish资源树和OData的响应格式,再在上面验证Session登录流程,然后是查询资源、修改Boot配置、调用Reset Action。跑通这一圈之后,再在真实BMC上操作,会顺利很多。

SMBIOS的学习环境更简单,任何一台Linux机器都能满足。跑一遍dmidecode,把Type 0到Type 17的类型都过一遍,对照DMTF的SMBIOS规范文档理解字段含义。动手能力强的话,可以写一个小的Python解析器,直接读/sys/firmware/dmi/tables/DMI,尝试解析出Type 1的制造商和序列号。这个过程对理解SMBIOS二进制布局特别有帮助。

5.2 我在实践中总结的三条实用经验

第一,做自动化脚本之前,先确认目标机器的Redfish实现版本和规范版本。不同厂商的BMC在实现Redfish时,API路径和返回字段会有差异。比如有的BMC的/redfish/v1/Systems下只有1,有的有多个实例;有的BMC在Links字段里扩展了私有属性。所以写通用自动化框架时,一定要做“能力探测”,先GET ServiceRoot和Resource,看看实际暴露的资源有哪些,再决定后续请求。

第二,操作类API一定要看Actions的描述。你可能会想当然地认为重启接口就是ComputerSystem.Reset + ResetType=On,但部分设备实现里ResetType的枚举值并不相同。有些支持PowerOn,有些用On,有些还提供Nmi(非屏蔽中断)这类高级类型。最稳妥的方式是请求资源后,从Actions的@Redfish.ActionInfo里读取参数的AllowableValues,再生成下拉选项,而不是硬编码。

第三,安全基线一定要认真。很多BMC出厂默认开着admin/admin并且允许明文HTTP访问,这在内部管理网络都极度危险。Redfish部署上线前,至少要关闭HTTP,启用TLS,修改默认账号密码,限制来源IP。如果BMC支持多用户权限模型,就按最小权限分配账号。这块做得稳,Redfish会成为运维利器;做得差,它就是你的安全突破口。

5.3 常见问题清单与技术选型参考

最后列一个我在社区答疑时反复遇到的高频问题清单,你可以直接拿来排查:

现象可能原因
curl -k访问Redfish报SSL错误自签名证书过期或时间不对,检查BMC系统时间和证书有效期
请求出现401 Unauthorized账号密码错误或Session Token过期,重新登录后再请求
PATCH修改Boot设置不生效Payload中字段名与规范不一致,或缺少必要的Content-Type头
事件订阅后收不到推送订阅时未设置正确EventTypes,或BMC无法访问订阅回调地址
Redfish返回的SerialNumber为空底层SMBIOS Type 1里的序列号就是空的,问题在BIOS侧
不同BMC的System ID路径不一致用/redfish/v1/Systems先遍历集合,不要硬编码资源ID

如果你想给自己的监控系统做带外管理集成,我建议考虑用DMTF官方维护的python-redfish-library,它封装了Session登录、请求重试、数组遍历等常见逻辑,比自己写curl包装要省力得多。命令行快速验证的话,redfishtool也是一个不错的选择,语法接近curl但更适合做资源遍历。

另外,Redfish规范本身的更新也很快,从1.0到1.14+版本,新增了电源管理、散热、固件更新、认证能力等不少内容。看规范的时候不建议一页页从头啃,先看DMTF的“Resource Guide”,找到你关心的资源类型,按需查对应章节就够了。这类规范文档的核心目的是查询,不是通读,这个心态非常重要。

这一篇先把DMTF、SMBIOS、Redfish的关系和入门路径讲完。下一篇我打算往实操方向深挖,重点拆解Redfish的会话管理机制、事件推送的完整实现流程,以及如何通过SMBIOS实现带内在带外故障场景下的兜底排查。这块我自己前期踩了不少坑,值得展开写清楚。

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

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

立即咨询