【92】实测:访问不存在的function导致UR

news2024/11/17 17:07:13


前言

协议规定访问不存在的function会导致UR,今天我们就来实测一下。

这篇文章主要设计下面几个方面:

1、X86上的memory config

2、config方式访问不存在的设备导致UR

3、UR和advisory  non fatal转换

4、header log解析

一、协议规定

    协议规定如果device 不支持收到的request type,那么request就unsupported request。如果request需要completion,那么completion的status就是UR。

    传统的PCI设备,device通过assert DEVSEL#来“claims” bus上的request(请求者通过把target devie的address放到address bus来初始化一个transaction,然后完成者通过assert DEVSEL#来response这个request(claim the transaction)。DEVSEL#就是用来表示该devcie已经被选中作为PCI request的target device。当device assert DEVSEL#,就表示该device已经decode了request的address,并且准备对这个request进行response)。如果在一段时间后,没有device来claim一个请求,请求者需要terminate这个request,这就是Master Abort。由于PCIe是一个点对点的互联协议,没有对应的机制来claim request,因此,request的receiver需要决定该request是否被claim。如果request不能被claim,那么该request被认为是Unsupported Request的,这就是PCIe协议中对等于传统的Master Abort termination机制

    对于Type0的device,如果是memory或者I/O request, function的地址范围决定了是否claim request,也就是常说的基于地址的路由机制。

    对于configuration request,request 中的format/type(type 0 request format)显示device是request的target,如果request的地址(completer ID(byte 8-9))是否一个没有实现的function,那么,device仍然不会claim 这个configuration request。

    Spec上说的极其拗口,其实非常简单,对于configuration request,如果request中的completer ID是device没有实现的function,那么devcie就认为该request是Unsupported Request

   协议读百遍不如上手一练,以知促行方能知行合一,我们来实际验证一下。

二、实际验证

1.X86 memory config介绍

    X86的config介绍见下面文章:

【14】PCIe架构下memory空间、IO空间、PCIe配置空间简介_linjiasen的博客-CSDN博客

 1.1 PCIe tree

2.验证过程

2.1 清零系统启动过程中的错误

     系统启动过程中会进行全function的枚举,这样会导致EP设备的出现错误,我们手动清零2:0.0和2:0.1的Device Status Register和Uncorrectable Error Status Register/Correctable Error Status Register

    清零后lspci -s 0:1.1 -vvvv、lspci -s 2:0.0 -vvvvv、lspci -s 2:0.1 -vvvvv的配置空间,方便后面操作后对比

root@mt-System-Product-Name:~# setpci -s 2:0.0 CAP_EXP+0xa.b
09
root@mt-System-Product-Name:~# setpci -s 2:0.0 CAP_EXP+0xa.b=0x9
root@mt-System-Product-Name:~# setpci -s 2:0.0 CAP_EXP+0xa.b
00
root@mt-System-Product-Name:~# setpci -s 2:0.1 CAP_EXP+0xa.b
09
root@mt-System-Product-Name:~# setpci -s 2:0.1 CAP_EXP+0xa.b=0x9
root@mt-System-Product-Name:~# setpci -s 2:0.1 CAP_EXP+0xa.b
00
root@mt-System-Product-Name:~#
root@mt-System-Product-Name:~# setpci -s 2:0.0 ECAP_AER+0x10.l
00002000
root@mt-System-Product-Name:~# setpci -s 2:0.0 ECAP_AER+0x10.l=0x2000
root@mt-System-Product-Name:~# setpci -s 2:0.0 ECAP_AER+0x10.l
00000000
root@mt-System-Product-Name:~# setpci -s 2:0.0 ECAP_AER+0x4.l
00000000
root@mt-System-Product-Name:~# setpci -s 2:0.1 ECAP_AER+0x4.l
00000000
root@mt-System-Product-Name:~# setpci -s 2:0.1 ECAP_AER+0x10.l
00002000
root@mt-System-Product-Name:~# setpci -s 2:0.1 ECAP_AER+0x10.l=0x2000
root@mt-System-Product-Name:~# setpci -s 2:0.1 ECAP_AER+0x10.l
00000000

2.2 configuration read 2:0.0的reg

root@mt-System-Product-Name:~# cat /proc/iomem | grep mmcon -i
e0000000-efffffff : PCI MMCONFIG 0000 [bus 00-ff]
root@mt-System-Product-Name:~#
root@mt-System-Product-Name:~#
root@mt-System-Product-Name:~# busybox devmem 0xe0200000
0x01061ED5
root@mt-System-Product-Name:~# setpci -s 2:0.0 0x0.l
01061ed5
root@mt-System-Product-Name:~# busybox devmem 0xe0200030
0xA6000002
root@mt-System-Product-Name:~# setpci -s 2:0.0 0x30.l
a6000002
root@mt-System-Product-Name:~# lspci -s 2:0.0 -v
02:00.0 3D controller: Moore Threads Technology Co.,Ltd MTT S60
        Subsystem: Moore Threads Technology Co.,Ltd MTT S60
        Flags: bus master, fast devsel, latency 0, IRQ 255
        Memory at a4000000 (32-bit, non-prefetchable) [size=32M]
        Memory at 6000000000 (64-bit, prefetchable) [size=16G]
        Expansion ROM at a6000000 [disabled] [size=2M] 

在这里插入图片描述

我们看到PCI MMCONFIG的起始地址是0xe0000000,按照table 7-1的address map,可以算出2:0.0的配置空间起始地址是0xe0200000(0xe0000000+0x2<<20),busybox devmem 0xe0200000获取的值是0x01061ED5和setpci -s 2:0.0 0x0.l一致,是GPU的deviceid和vendor

busybox devmem 0xe0200030获取的值和setpci -s 2:0.0 0x30.l一致,是EXP ROM BAR reg。

configuration read后lspci -s 0:1.1 -vvvv、lspci -s 2:0.0 -vvvvv、lspci -s 2:0.1 -vvvvv的配置空间,方便后面操作后对比

我们对比2.1 清零系统启动过程中的错误2.2 configuration read 2:0.0的reg操作后lspci -s 0:1.1 -vvvv、lspci -s 2:0.0 -vvvvv、lspci -s 2:0.1 -vvvvv的结果,没有任何变化,说明2.2 configuration read 2:0.0的reg的操作没有引起错误。

2.3 configuration read 2:0.1的reg

root@mt-System-Product-Name:~# busybox devmem 0xe0201000
0x01FF1ED5
root@mt-System-Product-Name:~# setpci -s 2:0.1 0x0.l
01ff1ed5
root@mt-System-Product-Name:~#
root@mt-System-Product-Name:~# busybox devmem 0xe0201010
0xA2000000
root@mt-System-Product-Name:~# setpci -s 2:0.1 0x10.l
a2000000

configuration read后lspci -s 0:1.1 -vvvv、lspci -s 2:0.0 -vvvvv、lspci -s 2:0.1 -vvvvv的配置空间,方便后面操作后对比

 我们对比2.1 清零系统启动过程中的错误2.3 configuration read 2:0.1的reg操作后lspci -s 0:1.1 -vvvv、lspci -s 2:0.0 -vvvvv、lspci -s 2:0.1 -vvvvv的结果,没有任何变化,说明2.3 configuration read 2:0.0的reg的操作没有引起错误。

2.4 configuration read 2:0.2的reg导致UR转advisory non fatal错误

    现在外面要用configuration read一个没有实现的function的reg了。

root@mt-System-Product-Name:~# busybox devmem 0xe0202000
0xFFFFFFFF

我们看到返回一个全1的值

configuration read后lspci -s 0:1.1 -vvvv、lspci -s 2:0.0 -vvvvv、lspci -s 2:0.1 -vvvvv的配置空间,方便后面操作后对比

我们发现出现的UR的错误,这个UR的错误被转换成了advisory non fatal的correctable的错误

2.5 手动清零2.4中访问导致的错误,并设置severity为1

root@mt-System-Product-Name:~# setpci -s 2:0.0 ECAP_AER+0x10.l
00002000
root@mt-System-Product-Name:~# setpci -s 2:0.0 ECAP_AER+0x10.l=0x2000
root@mt-System-Product-Name:~# setpci -s 2:0.0 ECAP_AER+0x10.l
00000000
root@mt-System-Product-Name:~# setpci -s 2:0.1 ECAP_AER+0x10.l
00002000
root@mt-System-Product-Name:~# setpci -s 2:0.1 ECAP_AER+0x10.l=0x2000
root@mt-System-Product-Name:~# setpci -s 2:0.1 ECAP_AER+0x10.l
00000000
root@mt-System-Product-Name:~# setpci -s 2:0.0 ECAP_AER+0x4.l
00000000
root@mt-System-Product-Name:~# setpci -s 2:0.1 ECAP_AER+0x4.l
00000000
root@mt-System-Product-Name:~#
root@mt-System-Product-Name:~#
root@mt-System-Product-Name:~# setpci -s 2:0.0 CAP_EXP+0xa.b
09
root@mt-System-Product-Name:~# setpci -s 2:0.0 CAP_EXP+0xa.b=0x9
root@mt-System-Product-Name:~# setpci -s 2:0.0 CAP_EXP+0xa.b
00
root@mt-System-Product-Name:~# setpci -s 2:0.1 CAP_EXP+0xa.b
09
root@mt-System-Product-Name:~# setpci -s 2:0.1 CAP_EXP+0xa.b=0x9
root@mt-System-Product-Name:~# setpci -s 2:0.1 CAP_EXP+0xa.b
00
root@mt-System-Product-Name:~#
root@mt-System-Product-Name:~#
root@mt-System-Product-Name:~# setpci -s 2:0.0 ECAP_AER+0xc.l
00462030
root@mt-System-Product-Name:~# setpci -s 2:0.0 ECAP_AER+0xc.l=0xffffffff
root@mt-System-Product-Name:~# setpci -s 2:0.0 ECAP_AER+0xc.l
005ff031
root@mt-System-Product-Name:~#
root@mt-System-Product-Name:~# setpci -s 2:0.1 ECAP_AER+0xc.l
00462030
root@mt-System-Product-Name:~# setpci -s 2:0.1 ECAP_AER+0xc.l=0xffffffff
root@mt-System-Product-Name:~# setpci -s 2:0.1 ECAP_AER+0xc.l
005ff030

清零错误并设置severity后lspci -s 0:1.1 -vvvv、lspci -s 2:0.0 -vvvvv、lspci -s 2:0.1 -vvvvv的配置空间,方便后面操作后对比

我们发现2.4中访问导致的错误被清零了,并且UR错误的severity被置1了


2.6 configuration read 2:0.2的reg(offset:0x0)导致UR

 现在我们要用configuration read一个没有实现的function的reg(offset:0x0)了。

root@mt-System-Product-Name:~# busybox devmem 0xe0202000
0xFFFFFFFF

我们看到返回一个全1的值

configuration read后lspci -s 0:1.1 -vvvv、lspci -s 2:0.0 -vvvvv、lspci -s 2:0.1 -vvvvv的配置空间,方便后面操作后对比

我们发现出现的UR的错误

我们拿header log来解析一下,看看UR是不是我们刚才访问导致的,同时验证下X86的config read。

HeaderLog: 04000001 0000000f 02020000 00000000

04000001:对应的configuration read type0,说明请求是针对type的configuration read

 02020000: completer ID的bus是0x02,device是0x00,function是0x2

 2.7 configuration read 2:0.2的reg(offset:0x30)导致UR

为了验证到reg number对应的字段和head log reg更新,我们先手动清除上次访问导致的GPU的错误,清除错误后lspci -s 0:1.1 -vvvv、lspci -s 2:0.0 -vvvvv、lspci -s 2:0.1 -vvvvv的配置空间,方便后面操作后对比

root@mt-System-Product-Name:~# setpci -s 2:0.0 ECAP_AER+0x10.l
00000000
root@mt-System-Product-Name:~# setpci -s 2:0.1 ECAP_AER+0x10.l
00000000
root@mt-System-Product-Name:~# setpci -s 2:0.1 ECAP_AER+0x4.l
00100000
root@mt-System-Product-Name:~# setpci -s 2:0.1 ECAP_AER+0x4.l=0x00100000
root@mt-System-Product-Name:~# setpci -s 2:0.1 ECAP_AER+0x4.l
00000000
root@mt-System-Product-Name:~# setpci -s 2:0.0 ECAP_AER+0x4.l
00100000
root@mt-System-Product-Name:~# setpci -s 2:0.0 ECAP_AER+0x4.l=0x00100000
root@mt-System-Product-Name:~# setpci -s 2:0.0 ECAP_AER+0x4.l
00000000
root@mt-System-Product-Name:~# setpci -s 2:0.0 CAP_EXP+0xa.b
0c
root@mt-System-Product-Name:~# setpci -s 2:0.0 CAP_EXP+0xa.b=0xc
root@mt-System-Product-Name:~# setpci -s 2:0.0 CAP_EXP+0xa.b
00
root@mt-System-Product-Name:~# setpci -s 2:0.1 CAP_EXP+0xa.b
0c
root@mt-System-Product-Name:~# setpci -s 2:0.1 CAP_EXP+0xa.b=0xc
root@mt-System-Product-Name:~# setpci -s 2:0.1 CAP_EXP+0xa.b
00

 现在我们要用configuration read一个没有实现的function的reg(offset:0x30)了。

root@mt-System-Product-Name:~# busybox devmem 0xe0202030
0xFFFFFFFF

我们看到返回一个全1的值

 我们发现出现的UR的错误

 ​​​​​​

 我们拿header log来解析一下。

02020030中的0x30就是访问的reg number

总结

    configuration read访问没有实现的function会导致UR的错误 

本文来自互联网用户投稿,该文观点仅代表作者本人,不代表本站立场。本站仅提供信息存储空间服务,不拥有所有权,不承担相关法律责任。如若转载,请注明出处:http://www.coloradmin.cn/o/545551.html

如若内容造成侵权/违法违规/事实不符,请联系多彩编程网进行投诉反馈,一经查实,立即删除!

相关文章

SPI总线通讯协议学习

目录 什么是SPI 信号线 理解通讯原理 采样 SPI的推广 什么是SPI SPI是芯片与芯片之间的通讯,准确得说是串行同步通讯。既然都说了同步&#xff0c;那发送数据当然要和时钟线SCK配合才能发数据. 采用一主多从的模式&#xff0c;主机只有一个,而从机可以有若干个。 信号线 …

Java面试知识点(全)-Java并发-多线程JUC三- JUC集合/线程池

Java面试知识点(全) 导航&#xff1a; https://nanxiang.blog.csdn.net/article/details/130640392 注&#xff1a;随时更新 JUC集合类 为什么HashTable慢? 它的并发度是什么? 那么ConcurrentHashMap并发度是什么? Hashtable之所以效率低下主要是因为其实现使用了synchro…

学习开源项目消息推送平台需要什么基础?

有很多人问过我&#xff0c;学习开源项目消息推送平台austin需要有什么基础&#xff0c;我往往会回答&#xff1a;有SpringBoot基础就够了。 我在几年前总结过从零学习Java的路线&#xff0c;现在看来也没有很过时&#xff1a; Java基础&#xff1a;流程控制–>面向对象(包…

文件上传,解析漏洞编译器安全(23)

apache低版本解析漏洞 这个网站目录里有两个文件&#xff0c;一个是正常的php文件&#xff0c;另一个xx.php.xxx&#xff0c;源码是php源码&#xff0c;命名的文件&#xff0c;而访问中xxx的文件依旧可以执行出php代码的结果&#xff0c;而xxx就能当php文件解析&#xff0c;这…

【Linux】shell脚本编程

C/C与shell的区别 C/C是编译型 编译链接xx.c->xx 二进制机器指令 shell编程解释型 xx.sh 需要解释器&#xff08;如&#xff1a;bash&#xff09; Java 解释器编译 xx.java->xx.class 配置环境 输出一个hello my.sh #!/usr/bin/bash/echo"hello"ex…

php中Ajax的简单使用,登录表单调用Ajax判断是否正确登录利用layer.msg进行提示

php中Ajax的简单使用 jQuery中如何使用Ajax&#xff1f; jQuery 中封装了两个方法 get() 和 post() 方法用于通过 HTTP GET 或 POST 请求从服务器请求数据。 两种在客户端和服务器端进行请求-响应的常用方法是&#xff1a;GET 和 POST。 GET - 从指定的资源请求数据POST - …

Postman集合/文件夹/请求中脚本的执行顺序

Postman的Collection(集合)/Folder(集合的子文件夹)/Request(请求)中都有Pre-request Script(请求前脚本)和Tests(请求后脚本) 这个功能类似于不同范围的Test Fixture功能, 我们来探索3个问题: 脚本的执行顺序?保存在集合/子文件夹中的请求单独发送时是否会执行 集合以及子文…

css自定义变量

文章目录 学习链接1.什么是CSS变量?2.如何定义CSS变量?定义CSS变量示例 3.如何使用CSS变量?使用示例 4.CSS变量可以干什么用?1. 提取相同的属性值风格切换简单案例index.htmlindex.css 2. 简化相似的代码案例实现1案例实现2index.html index.css 5.作用域问题案例index.htm…

【数据结构】--单链表力扣面试题③找链表的中间节点

目录 法一&#xff1a;遍历链表法 法二、快慢指针法 题述&#xff1a;给定一个头结点为head的非空单链表&#xff0c;返回链表的中间节点。如果有两个中间节点&#xff0c;则返回第二个中间节点。 示例1&#xff1a; 输入&#xff1a;【1,2,3,4,5】 输出&#xff1a;此链表…

〖Web全栈开发④〗— HTML基础详讲(超详细)

HTML基础详讲 &#xff08;一&#xff09;HTML基础1.1浏览器发展史1.2浏览器的诞生和发展 &#xff08;二&#xff09; 什么是网页2.1 网站是什么&#xff1f;2.2 什么是网站2.3 网站服务器2.4 总结 &#xff08;三&#xff09;HTML基础3.1 什么是HTML3.2 HTML标签3.3 实例3.4 …

为什么每个C程序都需要一个叫做 main 的函数?

文章目录 1、为什么每个C程序都需要一个叫做main的函数&#xff1f;2、为什么 C 的 main 函数可以通过调用 exit 或者执行一条 return 语句来结束&#xff0c;或者两者都不做&#xff0c;而程序依然可以正确终止&#xff1f; 1、为什么每个C程序都需要一个叫做main的函数&#…

论文阅读记录(1)

这一周读了2021cvpr的《Learning to Filter: Siamese Relation Network for Robust Tracking》。这篇文章的创新点&#xff1a; Relation Detector。关系检测器。关系检测器在本文中以元学习的方式执行&#xff0c;以获得从背景中过滤干扰物的能力。Refinement Module。x细化模…

canal学习-运行canal-adapter源码并记录解决报错问题(包含缺失的jar文件)(一)

运行canal-adapter 1. 下载canal源码1.1 下载源码并安装好环境1.2 查看目录结构 2.项目运行2.1 项目打包2.2 项目打包可能遇到的问题&#xff1a;1.Failure to find com.alibaba.otter:connector.tcp:jar:jar-with-dependencies:1.1.52.com.alibaba.druid.pool.DruidDataSource…

数字信号处理基础(三):FIR滤波器的设计

目录 1. 滤波器1.1 低通滤波器1.2 高通滤波器1.3 带通滤波器1.4 带阻滤波器 2. 完整代码3. 结果图 1. 滤波器 1.1 低通滤波器 低通滤波器需要知道低通截止频率&#xff0c;然后采用以下代码实现 % 低通滤波器设计 fp2*10000; % 低通滤波器截止频率&#x…

安全测试之使用Docker搭建SQL注入安全测试平台sqli-labs

1 搜索镜像 docker search sqli-labs 2 拉取镜像 docker pull acgpiano/sqli-labs 3 创建docker容器 docker run -d --name sqli-labs -p 10012:80 acgpiano/sqli-labs 4 访问测试平台网站 若直接使用虚拟机&#xff0c;则直接通过ip端口号访问若通过配置域名&#xff0…

2023-5-20-各种编译器的全面学习

&#x1f37f;*★,*:.☆(&#xffe3;▽&#xffe3;)/$:*.★* &#x1f37f; &#x1f4a5;&#x1f4a5;&#x1f4a5;欢迎来到&#x1f91e;汤姆&#x1f91e;的csdn博文&#x1f4a5;&#x1f4a5;&#x1f4a5; &#x1f49f;&#x1f49f;喜欢的朋友可以关注一下&#xf…

网站投票软件投票链接制作软件投票链接小程序投票程序

近些年来&#xff0c;第三方的微信投票制作平台如雨后春笋般络绎不绝。随着手机的互联网的发展及微信开放平台各项基于手机能力的开放&#xff0c;更多人选择微信投票小程序平台&#xff0c;因为它有非常大的优势。 1.它比起微信公众号自带的投票系统、传统的H5投票系统有可以图…

LLVM-Clang交叉编译详细教程

文章目录 前言对比GCC与ClangClang交叉编译参数选项安装交叉编译器交叉编译生成二进制文件Target Arch列表Target Triple列表参考文档后话 前言 最近自己写了个C的小项目&#xff0c;想在Windows编译出其他平台的二进制文件的话&#xff0c;只能交叉编译了&#xff0c;于是就选…

性能测试-JMeter分布式测试及其详细步骤

性能测试概要 性能测试是软件测试中的一种&#xff0c;它可以衡量系统的稳定性、扩展性、可靠性、速度和资源使用。它可以发现性能瓶颈&#xff0c;确保能满足业务需求。很多系统都需要做性能测试&#xff0c;如Web应用、数据库和操作系统等。 性能测试种类非常多&#xff0c;…

深入学习《c语言函数》

&#x1f4d5;博主介绍&#xff1a;目前大一正在学习c语言&#xff0c;数据结构&#xff0c;计算机网络。 c语言学习&#xff0c;是为了更好的学习其他的编程语言&#xff0c;C语言是母体语言&#xff0c;是人机交互接近底层的桥梁。 本章学习函数。 让我们开启c语言学习之旅吧…