輔助處理器 (AP) 功能¶
簡介¶
輔助處理器 (AP) 功能是一種 IBM Z 加密功能,由三個 AP 指令和 1 到 256 個 PCIe 加密介面卡卡組成。 AP 裝置為分配給在 IBM Z 系統 LPAR 中執行的 Linux 系統中的所有 CPU 提供加密功能。
AP 介面卡卡透過 AP 匯流排公開。 vfio-ap 的動機是使用 VFIO 調解裝置框架使 AP 卡可用於 KVM 客戶機。 此實現很大程度上依賴於 s390 虛擬化功能,該功能完成了提供對 AP 裝置的直接訪問的大部分艱苦工作。
AP 架構概述¶
為了便於理解設計,讓我們從一些定義開始
AP 介面卡
AP 介面卡是一種 IBM Z 介面卡卡,可以執行加密功能。 可以將 0 到 256 個介面卡分配給 LPAR。 分配給執行 Linux 主機的 LPAR 的介面卡將可用於 Linux 主機。 每個介面卡都由一個從 0 到 255 的數字標識;但是,最大介面卡數量由機器型號和/或介面卡型別決定。 安裝後,任何 CPU 執行的 AP 指令都可以訪問 AP 介面卡。
AP 介面卡卡透過系統的啟用配置檔案分配給給定的 LPAR,該配置檔案可以透過 HMC 進行編輯。 當 Linux 主機系統在 LPAR 中進行 IPL 時,AP 匯流排會檢測分配給 LPAR 的 AP 介面卡卡,併為每個分配的介面卡建立一個 sysfs 裝置。 例如,如果 AP 介面卡 4 和 10 (0x0a) 分配給 LPAR,則 AP 匯流排將建立以下 sysfs 裝置條目
/sys/devices/ap/card04 /sys/devices/ap/card0a
指向這些裝置的符號連結也將在 AP 匯流排裝置子目錄中建立
/sys/bus/ap/devices/[card04] /sys/bus/ap/devices/[card04]
AP 域
介面卡被劃分為域。 根據介面卡型別和硬體配置,一個介面卡最多可以容納 256 個域。 域由一個從 0 到 255 的數字標識;但是,最大域數量由機器型號和/或介面卡型別決定。 域可以被認為是用於處理 AP 命令的一組硬體暫存器和記憶體。 可以使用用於明文金鑰加密的安全私鑰配置域。 域根據其訪問方式分為兩種方式之一
使用域是透過 AP 指令定位以處理 AP 命令的域。
控制域是透過傳送到使用域的 AP 命令更改的域;例如,設定控制域的安全私鑰。
AP 使用和控制域透過系統的啟用配置檔案分配給給定的 LPAR,該配置檔案可以透過 HMC 進行編輯。 當 Linux 主機系統在 LPAR 中進行 IPL 時,AP 匯流排模組會檢測分配給 LPAR 的 AP 使用和控制域。 每個使用域的域編號和每個 AP 介面卡的介面卡編號組合起來以建立 AP 佇列裝置(請參見下面的 AP 佇列部分)。 每個控制域的域編號將以位掩碼錶示並存儲在 sysfs 檔案 /sys/bus/ap/ap_control_domain_mask 中。 掩碼中的位(從最高有效位到最低有效位)對應於域 0-255。
AP 佇列
AP 佇列是將 AP 命令傳送到特定介面卡內的使用域的方式。 AP 佇列由 AP 介面卡 ID (APID) 和 AP 佇列索引 (APQI) 組成的元組標識。 APQI 對應於介面卡內的給定使用域編號。 此元組形成 AP 佇列編號 (APQN),唯一標識 AP 佇列。 AP 指令包括一個包含 APQN 的欄位,用於標識要將 AP 命令傳送到哪個 AP 佇列進行處理。
AP 匯流排將為每個 APQN 建立一個 sysfs 裝置,該裝置可以從載入 AP 匯流排模組時檢測到的 AP 介面卡和使用域編號的叉積中匯出。 例如,如果介面卡 4 和 10 (0x0a) 以及使用域 6 和 71 (0x47) 分配給 LPAR,則 AP 匯流排將建立以下 sysfs 條目
/sys/devices/ap/card04/04.0006 /sys/devices/ap/card04/04.0047 /sys/devices/ap/card0a/0a.0006 /sys/devices/ap/card0a/0a.0047
以下指向這些裝置的符號連結將在 AP 匯流排裝置子目錄中建立
/sys/bus/ap/devices/[04.0006] /sys/bus/ap/devices/[04.0047] /sys/bus/ap/devices/[0a.0006] /sys/bus/ap/devices/[0a.0047]
AP 指令
有三個 AP 指令
NQAP:將 AP 命令請求訊息排隊到佇列
DQAP:從佇列中取消 AP 命令回覆訊息的排隊
PQAP:管理佇列
AP 指令標識要定位以處理 AP 命令的域;這必須是使用域之一。 AP 命令可能會修改不是使用域之一的域,但修改的域必須是控制域之一。
AP 和 SIE¶
現在讓我們看一下硬體如何解釋在訪客上執行的 AP 指令。
一個稱為加密控制塊 (CRYCB) 的衛星控制塊附加到我們的主硬體虛擬化控制塊。 CRYCB 包含一個 AP 控制塊 (APCB),該控制塊具有三個欄位,用於標識分配給 KVM 訪客的介面卡、使用域和控制域
AP 掩碼 (APM) 欄位是一個位掩碼,用於標識分配給 KVM 訪客的 AP 介面卡。 掩碼中的每個位(從左到右)對應於一個從 0-255 的 APID。 如果設定了一個位,則相應的介面卡對於 KVM 訪客有效。
AP 佇列掩碼 (AQM) 欄位是一個位掩碼,用於標識分配給 KVM 訪客的 AP 使用域。 掩碼中的每個位(從左到右)對應於一個從 0-255 的 AP 佇列索引 (APQI)。 如果設定了一個位,則相應的佇列對於 KVM 訪客有效。
AP 域掩碼欄位是一個位掩碼,用於標識分配給 KVM 訪客的 AP 控制域。 ADM 位掩碼控制哪些域可以透過傳送到訪客使用域的 AP 命令請求訊息進行更改。 掩碼中的每個位(從左到右)對應於一個從 0-255 的域。 如果設定了一個位,則可以透過傳送到使用域的 AP 命令請求訊息來修改相應的域。
如果您還記得 AP 佇列的描述,AP 指令包括一個 APQN,用於標識要將 AP 命令請求訊息傳送到哪個 AP 佇列(NQAP 和 PQAP 指令),或者從中接收命令回覆訊息(DQAP 指令)。 APQN 的有效性由從 APM 和 AQM 計算的矩陣定義;它是所有分配的介面卡編號 (APM) 與所有分配的佇列索引 (AQM) 的笛卡爾積。 例如,如果將介面卡 1 和 2 以及使用域 5 和 6 分配給訪客,則 APQN (1,5)、(1,6)、(2,5) 和 (2,6) 對於訪客有效。
APQN 可以提供安全金鑰功能 - 即,每個域的私鑰都儲存在介面卡卡上 - 因此每個 APQN 最多必須分配給一個訪客或 Linux 主機
Example 1: Valid configuration:
------------------------------
Guest1: adapters 1,2 domains 5,6
Guest2: adapter 1,2 domain 7
This is valid because both guests have a unique set of APQNs:
Guest1 has APQNs (1,5), (1,6), (2,5), (2,6);
Guest2 has APQNs (1,7), (2,7)
Example 2: Valid configuration:
------------------------------
Guest1: adapters 1,2 domains 5,6
Guest2: adapters 3,4 domains 5,6
This is also valid because both guests have a unique set of APQNs:
Guest1 has APQNs (1,5), (1,6), (2,5), (2,6);
Guest2 has APQNs (3,5), (3,6), (4,5), (4,6)
Example 3: Invalid configuration:
--------------------------------
Guest1: adapters 1,2 domains 5,6
Guest2: adapter 1 domains 6,7
This is an invalid configuration because both guests have access to
APQN (1,6).
設計¶
該設計引入了三個新物件
AP 矩陣裝置
VFIO AP 裝置驅動程式 (vfio_ap.ko)
VFIO AP 調解直通裝置
VFIO AP 裝置驅動程式¶
VFIO AP (vfio_ap) 裝置驅動程式用於以下目的
提供介面以保護 APQN,以供 KVM 訪客獨佔使用。
設定 VFIO 調解裝置介面以管理 vfio_ap 調解裝置,並建立 sysfs 介面以分配介面卡、使用域和控制域,從而構成 KVM 訪客的矩陣。
配置 APCB 中 APM、AQM 和 ADM,APCB 包含在 KVM 訪客的 SIE 狀態描述引用的 CRYCB 中,以授予訪客訪問 AP 裝置矩陣的許可權
為 KVM 訪客獨佔使用保留 APQN¶
以下框圖說明了保留 APQN 的機制
+------------------+
7 remove | |
+--------------------> cex4queue driver |
| | |
| +------------------+
|
|
| +------------------+ +----------------+
| 5 register driver | | 3 create | |
| +----------------> Device core +----------> matrix device |
| | | | | |
| | +--------^---------+ +----------------+
| | |
| | +-------------------+
| | +-----------------------------------+ |
| | | 4 register AP driver | | 2 register device
| | | | |
+--------+---+-v---+ +--------+-------+-+
| | | |
| ap_bus +--------------------- > vfio_ap driver |
| | 8 probe | |
+--------^---------+ +--^--^------------+
6 edit | | |
apmask | +-----------------------------+ | 11 mdev create
aqmask | | 1 modprobe |
+--------+-----+---+ +----------------+-+ +----------------+
| | | |10 create| mediated |
| admin | | VFIO device core |---------> matrix |
| + | | | device |
+------+-+---------+ +--------^---------+ +--------^-------+
| | | |
| | 9 create vfio_ap-passthrough | |
| +------------------------------+ |
+-------------------------------------------------------------+
12 assign adapter/domain/control domain
為 KVM 訪客保留 AP 佇列的流程是
管理員載入 vfio_ap 裝置驅動程式
vfio-ap 驅動程式在其初始化期間將向裝置核心註冊一個“矩陣”裝置。 這將用作所有用於為訪客配置 AP 矩陣的 vfio_ap 調解裝置的父裝置。
/sys/devices/vfio_ap/matrix 裝置由裝置核心建立
vfio_ap 裝置驅動程式將在 AP 總線上註冊型別為 10 及更高版本(CEX4 及更高版本)的 AP 佇列裝置。 該驅動程式將提供 vfio_ap 驅動程式的探測和刪除回撥介面。 不支援早於 CEX4 佇列的裝置,這可以透過不支援將在相對較短的未來停止使用的較舊裝置來簡化實現,而不會不必要地使設計複雜化,並且很少有較舊的系統可用於測試。
AP 匯流排使用裝置核心註冊 vfio_ap 裝置驅動程式
管理員編輯 AP 介面卡和佇列掩碼以保留 AP 佇列供 vfio_ap 裝置驅動程式使用。
AP 匯流排從預設 zcrypt cex4queue 驅動程式中刪除為 vfio_ap 驅動程式保留的 AP 佇列。
AP 匯流排探測 vfio_ap 裝置驅動程式以繫結為其保留的佇列。
管理員建立一個要由訪客使用的直通型別 vfio_ap 調解裝置
管理員分配要由訪客獨佔使用的介面卡、使用域和控制域。
設定 VFIO 調解裝置介面¶
VFIO AP 裝置驅動程式利用 VFIO 調解裝置核心驅動程式的通用介面
註冊一個 AP 調解匯流排驅動程式,以將 vfio_ap 調解裝置新增到 VFIO 組並從中刪除它。
建立和銷燬 vfio_ap 調解裝置
將 vfio_ap 調解裝置新增到 AP 調解匯流排驅動程式並從中刪除它
將 vfio_ap 調解裝置新增到 IOMMU 組並從中刪除它
以下高階框圖顯示了 VFIO AP 調解裝置驅動程式的主要元件和介面
+-------------+
| |
| +---------+ | mdev_register_driver() +--------------+
| | Mdev | +<-----------------------+ |
| | bus | | | vfio_mdev.ko |
| | driver | +----------------------->+ |<-> VFIO user
| +---------+ | probe()/remove() +--------------+ APIs
| |
| MDEV CORE |
| MODULE |
| mdev.ko |
| +---------+ | mdev_register_parent() +--------------+
| |Physical | +<-----------------------+ |
| | device | | | vfio_ap.ko |<-> matrix
| |interface| +----------------------->+ | device
| +---------+ | callback +--------------+
+-------------+
在 vfio_ap 模組初始化期間,使用“mdev_parent_ops”結構註冊矩陣裝置,該結構提供 sysfs 屬性結構、mdev 函式和回撥介面以管理調解矩陣裝置。
sysfs 屬性結構
- supported_type_groups
VFIO 調解裝置框架支援建立使用者定義的調解裝置型別。 當裝置在調解裝置框架中註冊時,可以透過“supported_type_groups”結構指定這些調解裝置型別。 註冊過程為註冊裝置“mdev_supported_types”子目錄中指定的每種調解裝置型別建立 sysfs 結構。 除了裝置型別,還提供了調解裝置型別的 sysfs 屬性。
VFIO AP 裝置驅動程式將為直通設備註冊一種調解裝置型別
/sys/devices/vfio_ap/matrix/mdev_supported_types/vfio_ap-passthrough
將僅提供 VFIO mdev 框架所需的只讀屬性
... name ... device_api ... available_instances ... device_api
其中
- name
指定調解裝置型別的名稱
- device_api
調解裝置型別的 API
- available_instances
可以建立的 vfio_ap 調解直通裝置的數量
- device_api
指定 VFIO API
- mdev_attr_groups
此屬性組標識調解裝置的使用者定義 sysfs 屬性。 當裝置在 VFIO 調解裝置框架中註冊時,將在 vfio_ap 調解裝置的目錄中建立“mdev_attr_groups”結構中標識的 sysfs 屬性檔案。 vfio_ap 調解裝置的 sysfs 屬性為
- assign_adapter / unassign_adapter
用於將 AP 介面卡分配給/從 vfio_ap 調解裝置分配/取消分配的只寫屬性。 要分配/取消分配介面卡,介面卡的 APID 會回顯到相應的屬性檔案中。
- assign_domain / unassign_domain
用於將 AP 使用域分配給/從 vfio_ap 調解裝置分配/取消分配的只寫屬性。 要分配/取消分配域,使用域的域編號會回顯到相應的屬性檔案中。
- matrix
用於顯示從分配給 vfio_ap 調解裝置的介面卡和域編號的笛卡爾積匯出的 APQN 的只讀檔案。
- guest_matrix
用於顯示從 KVM 訪客 CRYCB 的 APM 和 AQM 欄位分別分配的介面卡和域編號的笛卡爾積匯出的 APQN 的只讀檔案。 如果任何 APQN 未引用繫結到 vfio_ap 裝置驅動程式的佇列裝置(即,佇列不在主機的 AP 配置中),則這可能與分配給 vfio_ap 調解裝置的 APQN 不同。
- assign_control_domain / unassign_control_domain
用於將 AP 控制域分配給/從 vfio_ap 調解裝置分配/取消分配的只寫屬性。 要分配/取消分配控制域,要分配/取消分配的域的 ID 會回顯到相應的屬性檔案中。
- control_domains
用於顯示分配給 vfio_ap 調解裝置的控制域編號的只讀檔案。
- ap_config
一個讀/寫檔案,寫入後,允許一次性替換 vfio_ap 調解裝置的所有三個 ap 矩陣掩碼。 給出三個掩碼,一個用於介面卡,一個用於域,一個用於控制域。 如果給定的狀態無法設定,則不會對 vfio-ap 調解裝置進行任何更改。
寫入 ap_config 的資料的格式如下:{amask},{dmask},{cmask}n
n 是一個換行符。
amask、dmask 和 cmask 是標識應分配給調解裝置的介面卡、域和控制域的掩碼。
掩碼的格式如下:0xNN..NN
其中 NN..NN 是表示 256 位值的 64 個十六進位制字元。 最左側(最高有效)的位表示介面卡/域 0。
對於表示您的 mdev 當前配置的掩碼示例集,只需 cat ap_config。
設定大於系統允許的最大值的介面卡或域編號將導致錯誤。
此屬性旨在供自動化使用。 終端使用者最好使用介面卡、域和控制域的相應分配/取消分配屬性。
函式
- create
分配 vfio_ap 驅動程式使用的 ap_matrix_mdev 結構
儲存對使用 mdev 的訪客的 KVM 結構的引用
儲存透過相應的 sysfs 屬性檔案分配的介面卡、域和控制域的 AP 矩陣配置
儲存訪客可用的介面卡、域和控制域的 AP 矩陣配置。 可能不會向訪客提供訪問引用不存在或未繫結到 vfio_ap 裝置驅動程式的佇列裝置的 APQN 的許可權。
- remove
取消分配 vfio_ap 調解裝置的 ap_matrix_mdev 結構。 僅當執行的訪客未使用 mdev 時,才允許這樣做。
回撥介面
- open_device
vfio_ap 驅動程式使用此回撥為矩陣 mdev 設備註冊 VFIO_GROUP_NOTIFY_SET_KVM 通知程式回撥函式。 使用者空間呼叫 open_device 回撥以將矩陣 mdev 裝置的 VFIO iommu 組連線到 MDEV 匯流排。 透過此回撥提供對用於配置 KVM 訪客的 KVM 結構的訪問。 KVM 結構用於配置訪客對透過 vfio_ap 調解裝置的 sysfs 屬性檔案定義的 AP 矩陣的訪問。
- close_device
取消註冊矩陣 mdev 裝置的 VFIO_GROUP_NOTIFY_SET_KVM 通知程式回撥函式,並取消配置訪客的 AP 矩陣。
- ioctl
此回撥處理 vfio 框架定義的 VFIO_DEVICE_GET_INFO 和 VFIO_DEVICE_RESET ioctl。
配置訪客的 AP 資源¶
當呼叫 VFIO_GROUP_NOTIFY_SET_KVM 通知程式回撥時,將執行 KVM 訪客的 AP 資源配置。 當用戶空間連線到 KVM 時,將呼叫通知程式函式。 訪客的 AP 資源透過其 APCB 進行配置
設定 APM 中與透過其“assign_adapter”介面分配給 vfio_ap 調解裝置的 APID 對應的位。
設定 AQM 中與透過其“assign_domain”介面分配給 vfio_ap 調解裝置的域對應的位。
設定 ADM 中與透過其“assign_control_domains”介面分配給 vfio_ap 調解裝置的域 dID 對應的位。
Linux 裝置模型排除了將未繫結到促進其直通的裝置驅動程式的裝置直通到 KVM 訪客。 因此,不會將不引用繫結到 vfio_ap 裝置驅動程式的佇列裝置的 APQN 分配給 KVM 訪客的矩陣。 但是,AP 架構不提供從訪客矩陣中過濾單個 APQN 的方法,因此將首先過濾透過其 sysfs“assign_adapter”、“assign_domain”和“assign_control_domain”介面分配給 vfio_ap 調解裝置的介面卡、域和控制域,然後再向訪客提供 AP 配置
將過濾未分配給主機 AP 配置的分配給矩陣 mdev 的介面卡的 APID、域的 APQI 和控制域的域編號。
將檢查從分配給 vfio_ap mdev 的 APID 和 APQI 的笛卡爾積匯出的每個 APQN,如果其中任何一個不引用繫結到 vfio_ap 裝置驅動程式的佇列裝置,則不會將介面卡插入到訪客中(即,與其 APID 對應的位不會設定在訪客的 APCB 中)。
AP 的 CPU 模型功能¶
AP 堆疊依賴於 AP 指令的存在以及三個功能:AP 功能測試 (APFT) 功能;AP 查詢配置資訊 (QCI) 功能;和 AP 佇列中斷控制功能。 這些特性/功能透過以下 CPU 模型功能提供給 KVM 訪客
ap:指示 AP 指令是否安裝在訪客上。 僅當 AP 指令安裝在主機上時,KVM 才會啟用此功能。
apft:指示 APFT 功能在訪客上可用。 僅當主機上可用時(即,設定了功能位 15),才能將此功能提供給訪客。
apqci:指示 AP QCI 功能在訪客上可用。 僅當主機上可用時(即,設定了功能位 12),才能將此功能提供給訪客。
apqi:指示 AP 佇列中斷控制功能在訪客上可用。 僅當主機上可用時(即,設定了功能位 65),才能將此功能提供給訪客。
注意:如果使用者選擇指定與 QEMU 的“主機”模型不同的 CPU 模型,則需要顯式啟用 CPU 模型功能和功能;例如
/usr/bin/qemu-system-s390x ... -cpu z13,ap=on,apqci=on,apft=on,apqi=on
可以透過顯式關閉 AP 特性/功能來阻止訪客使用它們;例如
/usr/bin/qemu-system-s390x ... -cpu host,ap=off,apqci=off,apft=off,apqi=off
注意:如果為訪客關閉了 APFT 功能 (apft=off),則訪客將看不到任何 AP 裝置。 在訪客上註冊型別 10 及更高版本 AP 裝置(即,cex4card 和 cex4queue 裝置驅動程式)的 zcrypt 裝置驅動程式需要 APFT 功能來確定安裝在給定 AP 裝置上的功能。 如果訪客上未安裝 APFT 功能,則在訪客上執行的 AP 匯流排將不會建立任何介面卡或域裝置,因為只能為訪客使用配置型別 10 及更高版本的裝置。
示例¶
現在讓我們提供一個示例來說明如何向 KVM 訪客授予對 AP 功能的訪問許可權。 對於此示例,我們將展示如何配置三個訪客,以便在訪客上執行 lszcrypt 命令將如下所示
訪客 1¶
CARD.DOMAIN |
TYPE |
MODE |
|---|---|---|
05 |
CEX5C |
CCA-Coproc |
05.0004 |
CEX5C |
CCA-Coproc |
05.00ab |
CEX5C |
CCA-Coproc |
06 |
CEX5A |
Accelerator |
06.0004 |
CEX5A |
Accelerator |
06.00ab |
CEX5A |
Accelerator |
訪客 2¶
CARD.DOMAIN |
TYPE |
MODE |
|---|---|---|
05 |
CEX5C |
CCA-Coproc |
05.0047 |
CEX5C |
CCA-Coproc |
05.00ff |
CEX5C |
CCA-Coproc |
訪客 3¶
CARD.DOMAIN |
TYPE |
MODE |
|---|---|---|
06 |
CEX5A |
Accelerator |
06.0047 |
CEX5A |
Accelerator |
06.00ff |
CEX5A |
Accelerator |
這些步驟是
在 Linux 主機上安裝 vfio_ap 模組。 vfio_ap 模組的依賴關係鏈是:* iommu * s390 * zcrypt * vfio * vfio_mdev * vfio_mdev_device * KVM
要構建 vfio_ap 模組,必須使用選定的以下 Kconfig 元素配置核心構建:* IOMMU_SUPPORT * S390 * AP * VFIO * KVM
如果使用 make menuconfig,請選擇以下選項來構建 vfio_ap 模組
-> Device Drivers -> IOMMU Hardware Support select S390 AP IOMMU Support -> VFIO Non-Privileged userspace driver framework -> Mediated device driver frramework -> VFIO driver for Mediated devices -> I/O subsystem -> VFIO support for AP devices保護將由三個訪客使用的 AP 佇列,以便主機無法訪問它們。 為了保護它們,有兩個 sysfs 檔案指定位掩碼,將 APQN 範圍的子集標記為僅可由預設 AP 佇列裝置驅動程式使用。 所有剩餘 APQN 可供任何其他裝置驅動程式使用。 vfio_ap 裝置驅動程式當前是唯一的非預設裝置驅動程式。 包含掩碼的 sysfs 檔案的位置是
/sys/bus/ap/apmask /sys/bus/ap/aqmask
“apmask”是一個 256 位掩碼,用於標識一組 AP 介面卡 ID (APID)。 掩碼中的每個位(從左到右)對應於一個從 0-255 的 APID。 如果設定了一個位,則 APID 屬於標記為僅可用於預設 AP 佇列裝置驅動程式的 APQN 子集。
“aqmask”是一個 256 位掩碼,用於標識一組 AP 佇列索引 (APQI)。 掩碼中的每個位(從左到右)對應於一個從 0-255 的 APQI。 如果設定了一個位,則 APQI 屬於標記為僅可用於預設 AP 佇列裝置驅動程式的 APQN 子集。
APID 的笛卡爾積(對應於 apmask 中設定的位)和 APQI 的笛卡爾積(對應於 aqmask 中設定的位)構成了僅可由主機預設裝置驅動程式使用的 APQN 子集。 所有其他 APQN 都可供非預設裝置驅動程式(如 vfio_ap 驅動程式)使用。
例如,以下掩碼
apmask: 0x7d00000000000000000000000000000000000000000000000000000000000000 aqmask: 0x8000000000000000000000000000000000000000000000000000000000000000
掩碼指示
介面卡 1、2、3、4、5 和 7 可供主機預設裝置驅動程式使用。
域 0 可供主機預設裝置驅動程式使用
僅可供預設主機裝置驅動程式使用的 APQN 子集是
(1,0)、(2,0)、(3,0)、(4.0)、(5,0) 和 (7,0)
所有其他 APQN 都可供非預設裝置驅動程式使用。
分配給 Linux 主機的每個 AP 佇列裝置的 APQN 都由 AP 匯流排根據從 APID 和 APQI 的笛卡爾積匯出的 APQN 集進行檢查,APID 和 APQI 標記為可用於預設 AP 佇列裝置驅動程式。 如果檢測到匹配項,將僅探測預設 AP 佇列裝置驅動程式;否則,將探測 vfio_ap 裝置驅動程式。
預設情況下,這兩個掩碼設定為保留所有 APQN 供預設 AP 佇列裝置驅動程式使用。 有兩種方法可以更改預設掩碼
可以透過在兩個格式之一中將字串回顯到相應的 sysfs 掩碼檔案中來編輯 sysfs 掩碼檔案
以 0x 開頭的絕對十六進位制字串(例如“0x12345678”)會設定掩碼。如果給定的字串短於掩碼,則會在右側填充 0;例如,指定掩碼值 0x41 與指定
0x4100000000000000000000000000000000000000000000000000000000000000
請記住,掩碼從左到右讀取,因此上面的掩碼標識裝置編號 1 和 7 (01000001)。
如果字串長於掩碼,則操作將以錯誤 (EINVAL) 終止。
掩碼中的各個位可以透過在逗號分隔的列表中指定要切換的每個位號來開啟和關閉。每個位號字串必須以(‘+’)或減號(‘-’)開頭,以指示要開啟(‘+’)或關閉(‘-’)相應的位。一些有效值是
“+0”開啟位 0
“-13”關閉位 13
“+0x41”開啟位 65
“-0xff”關閉位 255
以下示例
+0,-6,+0x47,-0xf0
開啟位 0 和 71 (0x47)
關閉位 6 和 240 (0xf0)
請注意,列表中未指定的位保持操作前的狀態。
也可以透過核心命令列上的引數在啟動時更改掩碼,如下所示
ap.apmask=0xffff ap.aqmask=0x40
這將建立以下掩碼
apmask: 0xffff000000000000000000000000000000000000000000000000000000000000 aqmask: 0x4000000000000000000000000000000000000000000000000000000000000000
從而產生以下兩個池
default drivers pool: adapter 0-15, domain 1 alternate drivers pool: adapter 16-255, domains 0, 2-255
注意: 更改掩碼,以便從 vfio_ap 介導的裝置(見下文)獲取一個或多個 APQN 將失敗並顯示錯誤 (EBUSY)。訊息會記錄到核心環形緩衝區,可以使用“dmesg”命令檢視。輸出標識每個標記為“在使用中”的 APQN,並標識分配給它的 vfio_ap 介導的裝置;例如
使用者空間可能無法重新分配已分配給 62177883-f1bb-47f0-914d-32a22e3a8804 的佇列 05.0054 使用者空間可能無法重新分配已分配給 cef03c3c-903d-4ecc-9a83-40694cb8aee4 的佇列 04.0054
保護我們示例的 APQN¶
為了保護 AP 佇列 05.0004、05.0047、05.00ab、05.00ff、06.0004、06.0047、06.00ab 和 06.00ff 以供 vfio_ap 裝置驅動程式使用,可以使用以下任一命令從預設掩碼中刪除相應的 APQN
echo -5,-6 > /sys/bus/ap/apmask echo -4,-0x47,-0xab,-0xff > /sys/bus/ap/aqmask或者可以如下設定掩碼
echo 0xf9ffffffffffffffffffffffffffffffffffffffffffffffffffffffffffffff \ > apmask echo 0xf7fffffffffffffffeffffffffffffffffffffffffeffffffffffffffffffffe \ > aqmask這將導致 AP 佇列 05.0004、05.0047、05.00ab、05.00ff、06.0004、06.0047、06.00ab 和 06.00ff 繫結到 vfio_ap 裝置驅動程式。vfio_ap 裝置驅動程式的 sysfs 目錄現在將包含指向繫結到它的 AP 佇列裝置的符號連結
/sys/bus/ap ... [drivers] ...... [vfio_ap] ......... [05.0004] ......... [05.0047] ......... [05.00ab] ......... [05.00ff] ......... [06.0004] ......... [06.0047] ......... [06.00ab] ......... [06.00ff]請記住,只有 10 型及更高版本的介面卡(即 CEX4 及更高版本)才能繫結到 vfio_ap 裝置驅動程式。這樣做的原因是透過不支援將在不久的將來停止使用的較舊裝置來簡化實現,從而不必要地使設計複雜化,並且用於測試的舊系統也很少。
因此,管理員必須注意僅保護可以繫結到 vfio_ap 裝置驅動程式的 AP 佇列。給定 AP 佇列裝置的裝置型別可以從父卡的 sysfs 目錄中讀取。例如,要檢視佇列 05.0004 的硬體型別
cat /sys/bus/ap/devices/card05/hwtype
hwtype 必須為 10 或更高(CEX4 或更新版本)才能繫結到 vfio_ap 裝置驅動程式。
建立配置三個客戶機的 AP 矩陣所需的介導裝置,並提供一個介面供客戶機使用 vfio_ap 驅動程式
/sys/devices/vfio_ap/matrix/ --- [mdev_supported_types] ------ [vfio_ap-passthrough] (passthrough vfio_ap mediated device type) --------- create --------- [devices]
要為三個客戶機建立介導裝置
uuidgen > create uuidgen > create uuidgen > create or echo $uuid1 > create echo $uuid2 > create echo $uuid3 > create
這將在 [devices] 子目錄中建立三個介導裝置,其名稱與寫入 create 屬性檔案的 UUID 相同。我們稱它們為 $uuid1、$uuid2 和 $uuid3,這是建立後的 sysfs 目錄結構
/sys/devices/vfio_ap/matrix/ --- [mdev_supported_types] ------ [vfio_ap-passthrough] --------- [devices] ------------ [$uuid1] --------------- assign_adapter --------------- assign_control_domain --------------- assign_domain --------------- matrix --------------- unassign_adapter --------------- unassign_control_domain --------------- unassign_domain ------------ [$uuid2] --------------- assign_adapter --------------- assign_control_domain --------------- assign_domain --------------- matrix --------------- unassign_adapter ----------------unassign_control_domain ----------------unassign_domain ------------ [$uuid3] --------------- assign_adapter --------------- assign_control_domain --------------- assign_domain --------------- matrix --------------- unassign_adapter ----------------unassign_control_domain ----------------unassign_domain
- 注意 *:除非使用
mdevctl 工具建立並持久化,否則 vfio_ap mdev 在重新啟動後不會持久存在。
管理員現在需要為介導裝置 $uuid1(對於 Guest1)、$uuid2(對於 Guest2)和 $uuid3(對於 Guest3)配置矩陣。
這是 Guest1 的矩陣配置方式
echo 5 > assign_adapter echo 6 > assign_adapter echo 4 > assign_domain echo 0xab > assign_domain
可以使用 assign_control_domain sysfs 檔案以類似的方式分配控制域。
如果在配置介面卡、域或控制域時出錯,可以使用 unassign_xxx 檔案取消分配介面卡、域或控制域。
要顯示 Guest1 的矩陣配置
cat matrix
要顯示分配給 Guest1 或將分配給 Guest1 的矩陣
cat guest_matrix
這是 Guest2 的矩陣配置方式
echo 5 > assign_adapter echo 0x47 > assign_domain echo 0xff > assign_domain
這是 Guest3 的矩陣配置方式
echo 6 > assign_adapter echo 0x47 > assign_domain echo 0xff > assign_domain
為了成功分配介面卡
指定的介面卡編號必須表示一個值,從 0 到為系統配置的最大介面卡編號。如果指定的介面卡編號高於最大值,則操作將以錯誤 (ENODEV) 終止。
- 注意:可以透過 sysfs
/sys/bus/ap/ap_max_adapter_id 屬性檔案獲取最大介面卡編號。
每個 APQN 都來自已分配介面卡的 APID 和先前分配域的 APQI 的笛卡爾積
必須僅對 vfio_ap 裝置驅動程式可用,如 sysfs /sys/bus/ap/apmask 和 /sys/bus/ap/aqmask 屬性檔案中所指定。如果甚至有一個 APQN 保留供主機裝置驅動程式使用,則操作將以錯誤 (EADDRNOTAVAIL) 終止。
不得分配給另一個 vfio_ap 介導的裝置。如果甚至有一個 APQN 分配給另一個 vfio_ap 介導的裝置,則操作將以錯誤 (EBUSY) 終止。
在編輯 sysfs /sys/bus/ap/apmask 和 sys/bus/ap/aqmask 屬性檔案時,不得進行分配,否則操作可能會以錯誤 (EBUSY) 終止。
為了成功分配域
指定的域編號必須表示一個值,從 0 到為系統配置的最大域編號。如果指定的域編號高於最大值,則操作將以錯誤 (ENODEV) 終止。
- 注意:可以透過 sysfs
/sys/bus/ap/ap_max_domain_id 屬性檔案獲取最大域編號。
每個 APQN 都來自已分配域的 APQI 和先前分配介面卡的 APID 的笛卡爾積
必須僅對 vfio_ap 裝置驅動程式可用,如 sysfs /sys/bus/ap/apmask 和 /sys/bus/ap/aqmask 屬性檔案中所指定。如果甚至有一個 APQN 保留供主機裝置驅動程式使用,則操作將以錯誤 (EADDRNOTAVAIL) 終止。
不得分配給另一個 vfio_ap 介導的裝置。如果甚至有一個 APQN 分配給另一個 vfio_ap 介導的裝置,則操作將以錯誤 (EBUSY) 終止。
在編輯 sysfs /sys/bus/ap/apmask 和 sys/bus/ap/aqmask 屬性檔案時,不得進行分配,否則操作可能會以錯誤 (EBUSY) 終止。
為了成功分配控制域
指定的域編號必須表示一個值,從 0 到為系統配置的最大域編號。如果指定的控制域編號高於最大值,則操作將以錯誤 (ENODEV) 終止。
啟動 Guest1
/usr/bin/qemu-system-s390x ... -cpu host,ap=on,apqci=on,apft=on,apqi=on \ -device vfio-ap,sysfsdev=/sys/devices/vfio_ap/matrix/$uuid1 ...
啟動 Guest2
/usr/bin/qemu-system-s390x ... -cpu host,ap=on,apqci=on,apft=on,apqi=on \ -device vfio-ap,sysfsdev=/sys/devices/vfio_ap/matrix/$uuid2 ...
啟動 Guest3
/usr/bin/qemu-system-s390x ... -cpu host,ap=on,apqci=on,apft=on,apqi=on \ -device vfio-ap,sysfsdev=/sys/devices/vfio_ap/matrix/$uuid3 ...
關閉客戶機時,可以刪除 vfio_ap 介導的裝置。
再次使用我們的示例,刪除 vfio_ap 介導的裝置 $uuid1
/sys/devices/vfio_ap/matrix/
--- [mdev_supported_types]
------ [vfio_ap-passthrough]
--------- [devices]
------------ [$uuid1]
--------------- remove
echo 1 > remove
這將刪除所有矩陣 mdev 裝置的 sysfs 結構,包括 mdev 裝置本身。要重新建立和重新配置矩陣 mdev 裝置,必須再次執行從步驟 3 開始的所有步驟。請注意,如果使用 vfio_ap mdev 的客戶機仍在執行,則刪除將失敗。
不必刪除 vfio_ap mdev,但如果 Linux 主機在剩餘的生命週期內沒有客戶機使用它,則可能需要刪除它。如果刪除了 vfio_ap mdev,則可能還需要重新配置為預設驅動程式保留的介面卡和佇列池。
熱插拔/拔出支援:¶
如果滿足以下條件,可以將介面卡、域或控制域熱插拔到正在執行的 KVM 客戶機中,方法是將其分配給客戶機正在使用的 vfio_ap 介導的裝置
介面卡、域或控制域也必須分配給主機的 AP 配置。
來自包括已分配介面卡的 APID 和已分配域的 APQI 的笛卡爾積的每個 APQN 必須引用繫結到 vfio_ap 裝置驅動程式的佇列裝置。
要熱插拔域,來自包括已分配域的 APQI 和已分配介面卡的 APID 的笛卡爾積的每個 APQN 必須引用繫結到 vfio_ap 裝置驅動程式的佇列裝置。
可以透過從客戶機正在使用的 vfio_ap 介導的裝置取消分配介面卡、域或控制域來從正在執行的 KVM 客戶機中熱拔出介面卡、域或控制域。
為 KVM 客戶機過度配置 AP 佇列:¶
本文中,過度配置定義為將不引用主機 AP 配置中的 AP 裝置的介面卡或域分配給 vfio_ap 介導的裝置。這裡的想法是,當介面卡或域可用時,它將使用已分配給它的 vfio_ap 介導的裝置自動熱插拔到 KVM 客戶機中,只要插入後產生的每個新 APQN 都引用繫結到 vfio_ap 裝置驅動程式的佇列裝置。
驅動程式功能¶
vfio_ap 驅動程式公開一個包含受支援功能的 sysfs 檔案。這樣做的目的是為了第三方工具(如 Libvirt 和 mdevctl)可以查詢特定功能的可用性。
可以在這裡找到功能列表:/sys/bus/matrix/devices/matrix/features
條目以空格分隔。每個條目由字母數字和下劃線字元的組合組成。
示例:cat /sys/bus/matrix/devices/matrix/features guest_matrix dyn ap_config
公告了以下功能
---------------+---------------------------------------------------------------+ | 標誌 | 描述 | +==============+===============================================================+ | guest_matrix | guest_matrix 屬性存在。它報告介面卡和域的矩陣, | | | 當 mdev 連線到客戶機時,介面卡和域的矩陣將被傳遞給客戶機。 | +--------------+---------------------------------------------------------------+ | dyn | 指示 AP 介面卡、域和控制的熱插拔/拔出 | | | 附加 mdev 的客戶機的域。 | +------------+-----------------------------------------------------------------+ | ap_config | 用於對 mdev 配置進行一次性修改的 ap_config 介面 | +--------------+---------------------------------------------------------------+
限制¶
對於使用 AP 裝置的客戶機,不支援即時客戶機遷移,除非系統管理員進行干預。在可以遷移 KVM 客戶機之前,必須刪除 vfio_ap 介導的裝置。不幸的是,在 KVM 客戶機正在使用 mdev 時,無法手動刪除它(即,echo 1 > /sys/devices/vfio_ap/matrix/$UUID/remove)。如果客戶機由 QEMU 模擬,則可以透過以下兩種方式之一從客戶機中熱拔出其 mdev
如果 KVM 客戶機是使用 libvirt 啟動的,則可以透過以下命令熱拔出 mdev
virsh detach-device <guestname> <path-to-device-xml>
例如,要從名為“my-guest”的客戶機中熱拔出 mdev 62177883-f1bb-47f0-914d-32a22e3a8804
virsh detach-device my-guest ~/config/my-guest-hostdev.xml
my-guest-hostdev.xml 的內容
<hostdev mode='subsystem' type='mdev' managed='no' model='vfio-ap'>
<source>
<address uuid='62177883-f1bb-47f0-914d-32a22e3a8804'/>
</source>
</hostdev>
virsh qemu-monitor-command <guest-name> --hmp "device-del <device-id>"
For example, to hot unplug the vfio_ap mediated device identified on the
qemu command line with 'id=hostdev0' from the guest named 'my-guest':
virsh qemu-monitor-command my-guest --hmp "device_del hostdev0"
可以透過將 qemu 監視器附加到客戶機並使用以下 qemu 監視器命令來熱拔出 vfio_ap 介導的裝置
(QEMU) device-del id=<device-id>
例如,要熱拔出在 qemu 命令列上以“id=hostdev0”指定的 vfio_ap 介導的裝置(在啟動客戶機時)
(QEMU) device-del id=hostdev0
在 KVM 客戶機完成即時遷移後,可以透過以下兩種方式之一將 AP 配置還原到目標系統上的 KVM 客戶機中,方法是將 vfio_ap 介導的裝置熱插拔到客戶機中
如果 KVM 客戶機是使用 libvirt 啟動的,則可以透過以下 virsh 命令將矩陣介導的裝置熱插拔到客戶機中
virsh attach-device <guestname> <path-to-device-xml>
例如,要將 mdev 62177883-f1bb-47f0-914d-32a22e3a8804 熱插拔到名為“my-guest”的客戶機中
virsh attach-device my-guest ~/config/my-guest-hostdev.xml
my-guest-hostdev.xml 的內容
<hostdev mode='subsystem' type='mdev' managed='no' model='vfio-ap'>
<source>
<address uuid='62177883-f1bb-47f0-914d-32a22e3a8804'/>
</source>
</hostdev>
virsh qemu-monitor-command <guest-name> --hmp \
"device_add vfio-ap,sysfsdev=<path-to-mdev>,id=<device-id>"
For example, to hot plug the vfio_ap mediated device
62177883-f1bb-47f0-914d-32a22e3a8804 into the guest named 'my-guest' with
device-id hostdev0:
virsh qemu-monitor-command my-guest --hmp \
"device_add vfio-ap,\
sysfsdev=/sys/devices/vfio_ap/matrix/62177883-f1bb-47f0-914d-32a22e3a8804,\
id=hostdev0"
可以透過將 qemu 監視器附加到客戶機並使用以下 qemu 監視器命令來熱插拔 vfio_ap 介導的裝置
(qemu) device_add “vfio-ap,sysfsdev=<path-to-mdev>,id=<device-id>”
例如,要將 vfio_ap 介導的裝置 62177883-f1bb-47f0-914d-32a22e3a8804 插入到裝置 ID hostdev0 的客戶機中
(QEMU) device-add “vfio-ap,sysfsdev=/sys/devices/vfio_ap/matrix/62177883-f1bb-47f0-914d-32a22e3a8804,id=hostdev0”