Skip to content

VXC 家族 (Viperfish)

地址适用于 libtpu-0.0.40-cp314 wheel 中的 libtpu.so(build-id 89edbbe81c5b328a958fe628a9f2207d)。其他版本会有所不同。

摘要

VXC 是四个 HAL 家族中覆盖面最广的一个。工厂类 tpu::TpuHalVxcHardwareFactory 独特地位于全局命名空间,而 JXC 和 PXC 位于匿名命名空间;它服务三个代号:Viperfish (TpuVersion::kViperfish = 3)、Ghostlite (kGhostlite = 4) 和 6acc60406 (k6acc60406 = 5)。Viperfish 是 VXC 的“本位”代号,家族也以它命名;Ghostlite 和 6acc60406 由 GXC 家族glc/gfc 初始化模块注册到同一个工厂中,在运行层面位于 VXC 内部。

VXC 继承了 PXC 引入的 fetch/load-core 拆分:asic_sw::driver::deepsea::vxc::vfc(vector fetch-core)和 vxc::vlc(vector load-core)。它的定义性新特征是 SparseCore,Viperfish 是第一代携带 SparseCore 的产品,而 SparseCore 的引入也对应着 BarnaCore 的退役。VXC HAL 实现也是四者中唯一一个大小为 216 字节而不是 208 字节的实现;额外的 8 字节是在偏移 +0xD0 处的一个标志字节。

本页遵循与 JXCPXCGXC 页面相同的组织方式。由于 GXC 注册到这个工厂中,代号分发的完整故事在这里讲述;GXC 页面涵盖 GXC 特有的内容(其编解码器和 sub-core ISA)。共享基类链见 HAL 家族

重新实现时,契约是:

  • 多版本注册表级分发:一个 global-ns 类、一个 vtable、三个按 TpuVersion keyed 的 16 字节实例,由三个独立的初始化模块注册。
  • 5 槽工厂 vtable(形状与 JXC/PXC 相同),以及带有 +0xD0 skip-slicebuilder 标志的 216 字节 TpuHalVxcHardwareImpl
  • 构造链 HardwareImpl → CommonHelper (48 B) → Chip (416 B) → Core (800 B),真正的按代号 switch 位于 InitializeDrivers
  • vxc::vfc / vxc::vlc fetch/load 拆分、vxc::isa 命名空间,以及统一的 TpuVxcDriver(V2 descriptor,无 DMA-issuer)。
工厂类tpu::TpuHalVxcHardwareFactoryglobal-ns,唯一例外)
服务的 TpuVersions3 — kViperfish (3), kGhostlite (4), k6acc60406 (5)
工厂 vtable / vptr_ZTV 0x21cabf70 / 已安装 vptr 0x21cabf80
工厂 typeinfo_ZTI 0x21cabfa8(__si base → TpuHalHardwareFactoryBase 0x21d343f8)
HAL 实现类 / 大小TpuHalVxcHardwareImpl, 216 B (0xD8), vtable 0x21cabfc0
初始化模块vxc 0x213eed20 (v3), glc 0x213eb9e0 (v4), gfc 0x213e9f60 (v5) — 每个 1× Register
Fetch/load 拆分vxc::vfc + vxc::vlc(继承自 PXC)
DMA 引擎统一的 tpu::TpuVxcDriver(无 issuer);DmaDescriptorV2

工厂绑定与注册

目的

VXC 将三个代号绑定到一个 HAL 实现。不同于 JXC(一个初始化模块,两次 Register 调用),VXC 使用三个独立的初始化模块,每个模块恰好调用一次 Register。原理相同:一个类、一个 vtable、N 个按 +8TpuVersion keyed 的注册表条目;但注册点分散在 GXC 家族模块中。

入口点

text
google_init_module_tpu_hal_vxc_hardware_impl (0x213eed20)  → Register(kHardware, 3, f)  // Viperfish
google_init_module_tpu_hal_glc_hardware_impl (0x213eb9e0)  → Register(kHardware, 4, f)  // Ghostlite
google_init_module_tpu_hal_gfc_hardware_impl (0x213e9f60)  → Register(kHardware, 5, f)  // 6acc60406
  (each: operator new(0x10); f[+8] = version; f[+0] = vptr 0x21cabf80; same vtable)
```text

### 算法

```c
function register_vxc_codename(version):    // one of three init modules
    f = operator_new(0x10)                  // 16-byte factory object
    f[+8] = version                         // 3, 4, or 5
    f[+0] = &VxcFactory_vtable + 0x10        // installed vptr 0x21cabf80 (SHARED)
    s = TpuHalFactory::Register(kHardware /*0*/, version, unique_ptr(f))
    CHECK(s == OK)
    // CHECK strings byte-confirm the codename → factory binding:
    //   0x94A3FA6 kViperfish, 0x94A4A6F kGhostlite, 0x94A3EF5 k6acc60406
    //   each: std::make_unique<tpu::TpuHalVxcHardwareFactory>(tpu::TpuVersion::kX)

怪异点 — VXC 工厂 ctor 确实接受一个 TpuVersion(CHECK 字符串会把 kViperfish/kGhostlite/k6acc60406 传给 make_unique),原因正是它必须服务三个版本;这点类似 JXC,不同于 PXC 的无参数 ctor。整个二进制中对工厂 vtable 0x21cabf70 恰好有三处引用,三处都是初始化模块的 lea 点。没有其他代码引用这个工厂类。

函数映射

函数地址作用
google_init_module_tpu_hal_vxc_hardware_impl0x213eed20注册 v3 (Viperfish)
google_init_module_tpu_hal_glc_hardware_impl0x213eb9e0注册 v4 (Ghostlite) — GXC 模块
google_init_module_tpu_hal_gfc_hardware_impl0x213e9f60注册 v5 (6acc60406) — GXC 模块
TpuHalFactory::Register0x1fbb16a0注册表插入(共享)

工厂 vtable

目的

VXC 的工厂 vtable 与 JXC 和 PXC 具有相同的 5 槽形状;只有命名空间位置(全局 vs 匿名)和两个覆写函数地址不同。

Vtable 布局

vaddr解析到基类/覆写
0x21cabf800 — ~TpuHalFactory() D20x0e723a80 (ret)继承
0x21cabf881 — ~TpuHalVxcHardwareFactory() D00x1d110e80覆写
0x21cabf902 — HardwareFactoryBase::Create(wq)0x1e80f560继承
0x21cabf983 — HardwareFactoryBase::CanCreate()0x1e80f520继承
0x21cabfa04 — TpuHalVxcHardwareFactory::CreateImpl(wq)0x1d110e00覆写

槽 1 编码 operator delete(this, 0x10),这个工厂是 16 字节,与所有四个家族一样。

算法 — CreateImpl

c
function TpuHalVxcHardwareFactory::CreateImpl(out, this, wq):   // 0x1d110e00
    obj     = operator_new(0xD8)              // 216 B = TpuHalVxcHardwareImpl
    version = *(u32*)(wq + 8)                 // TpuVersion from work-queue+8
    TpuHal::TpuHal(obj, version, wq)          // base ctor 0x1e811c00: wq→+0x68, version→+0x78
    *(void**)(obj + 0)    = &VxcImpl_vtable + 0x10   // plant 0x21cabfc0 → 0x21cabfd0
    *(void**)(obj + 0xC8) = nullptr            // CommonHelper slot
    *(byte*) (obj + 0xD0) = 0                  // skip-slicebuilder flag (VXC-ONLY; the extra 8 B)
    out.value = obj ; out.status = OK
    return out
```text

> **怪异点 —** VXC 实现的**额外 8 字节**是在偏移 `+0xD0` 处的单个 bool(填充到 8 字节)。它是 *skip-slicebuilder / use-default-configured-properties* 开关:`CreateAndInitializeChips` 从 `FLAGS_deepsea_hal_test_skip_slicebuilder` (0x22398628) 设置它;`GetConfiguredProperties`(槽 8)读取它以在 `GetDefaultConfiguredProperties(topology)` 与 helper 的缓存状态之间选择;`PreTearDownChips`(槽 21)读取它以跳过 mesh teardown。这个标志只存在于 VXC 上,因为只有 VXC 有一个*可以*跳过的多芯片 slice-builder mesh。JXC/PXC 没有 slice-builder,因此没有标志,也因此是 208 字节。它**不是**稀疏状态指针。

### 注意事项

216 字节实现大小有双重证明:`CreateImpl` 中的 `operator new(0xD8)`,以及实现 D0 dtor 中的 `operator delete(this, 0xD8)`。在三个家族中,VXC 唯一覆写实现槽 18(`WaitForCoreDumpComplete`, 0x1d110f00);它的实现覆写数量是 8(槽 012818192021)。见 [HAL 工厂覆写矩阵](hal-factory-override-matrix.md)。

---

## 工厂之下的构造链

### 目的

`TpuHalVxcHardwareImpl::CreateAndInitializeChips`(实现 vtable 槽 20,@ 0x1d110f20)驱动产品图,也是四个家族中唯一设置 `+0xD0` 标志并初始化 slice-builder mesh 的一个。

### 入口点

```text
TpuHalVxcHardwareImpl::CreateAndInitializeChips (0x1d110f20)
  ├─ TpuChipParts::CoreCount / SharedMemoryCount   ── data-driven constraints
  ├─ this[+0xD0] = FLAGS_deepsea_hal_test_skip_slicebuilder & 1
  ├─ TpuHalVxcCommonHelper (48 B, 0x1d111a60)        ── stored at impl+0xC8
  ├─ helper->InitializeDrivers(options, skip)        ── per-codename switch (0x1d111a80)
  ├─ helper->MaybeInitializeSliceBuilder (0x1d113120)
  └─ helper->CreateChips (0x1d113440)
       └─ TpuChipVxcDriverImpl (416 B, 0x1d114120)    ── + SyncFlagResources (296 B)
            └─ core-factory lambda
                 └─ TpuCoreVxcDriverImpl (800 B, 0x1d118340)  ── takes a TpuVxcDriver*

算法 — 按代号 switch

c
function TpuHalVxcCommonHelper::InitializeDrivers(options, skip):   // 0x1d111a80
    chip_parts = *(options + 8)               // chip-parts proto pointer
    version    = *(u32*)chip_parts            // first u32 of chip-parts proto
    variant    = TpuChipParts::variant_name() // 0x20b1eb40 (sv: ptr in rax, len in rdx)
    switch (version):                          // inline cmp $5 / $4 / $3
        case 5 (6acc60406): if variant non-empty: InvalidArgument "6acc60406 unsupported variant " (0xa1d990c)
                            else if platform==0: scanner = sub_1FBA82A0 / CreateMultiVfScannerAdapter
        case 4 (Ghostlite): if variant non-empty: InvalidArgument "ghostlite unsupported variant " (0xa1d992b)
                            else if platform==0: scanner = asic_sw::deepsea::DeepseaDeviceScanner (0x1fba7a20)
        case 3 (Viperfish): scanner = vxc::vfc::VfDeviceScanner (0x1d1b0e20)
                            /* or vxc::vlc::VfDeviceScanner (0x1d1b0be0) when variant=="lite"
                               and FLAGS_vxc_virtual_function / qword_22398620 is set */
        default:            LogMessageFatal "TpuVersion <N> not supported." (line 501)
    // a nonzero platform type in any case → MakeError "TPU Platform Type `%s` is not supported."
```text

> **注意 —** 这是整个 HAL 树中*唯一*真正按 `TpuVersion` 分支的 switch,并且它位于 `CommonHelper` 中,而不是工厂或实现中。工厂层在类上是统一的;实现方法不携带版本 switch。该分发位于 driver-init 层级,数据来自 chip-parts proto 的第一个 u32;它选择按代号的 device scanner,而不是分支 HAL 对象构造。

### 注意事项

每个 core 的 ctor 接受一个 `TpuVxcDriver*`,即统一的 VXC driver,而不是单独的 DMA-issuer(对比 JXC 的 `JfDmaIssuer*`)。`TpuVxcDriver` 构建 V2 DMA descriptor(`asic_sw::deepsea::dma::Descriptor`,14-bit sync flag),并通过 `EnableNHopRouting` / `SetRoutingStrategy` 配置 ICI routing。chip 对象还额外分配一个 296 字节的 `SyncFlagResources` 块。

---

## Driver 子命名空间清单

`asic_sw::driver::deepsea::vxc::` 承载 fetch/load 拆分和家族级 ISA。符号表确认的直接子命名空间:

| 子命名空间 | 作用 |
|---|---|
| `vxc::vfc` | **vector fetch-core** — fetch 侧指令流 |
| `vxc::vlc` | **vector load-core** — load 侧指令流 |
| `vxc::isa` | 家族级 ISA(170K 符号) |

fetch-core 之下是 `vxc::vfc::isa`(67K 符号)、`vxc::vfc::profiler`(40K 符号,含具名 `TraceEntry` 类,4015 符号),load 侧则是 `vxc::vlc::profiler`(12K 符号,`TraceEntry`,3001 符号)。SparseCore ISA bundles(`SparseCoreScsBundle`、`SparseCoreTacBundle`)位于 `vxc::vfc::isa` 之下,即 ISA/codec 层,而不是 216 字节 HAL 实现。每个 `vxc::vfc` / `vxc::vlc` 都携带自己的 `profiler::TraceEntry` 类,因此在[分类](sub-core-taxonomy.md)中二者都是 trace-entry sub-cores。

---

## 按代号差异

VXC 背后的三个代号在数据(chip-parts)和它们的 *codec* 类上不同,但共享一个 HAL 实现、一个 `TpuVxcDriver`、一个 V2 descriptor。Viperfish 在 `viperfish::isa` 下有自己的具名 worker(`EncoderVfTensorCore`、`DecoderVfTensorCore`);Ghostlite 和 6acc60406 详见 [GXC 页面](gxc-family.md)。

|| Viperfish (v3) | Ghostlite (v4) | 6acc60406 (v5) | 来源 |
|---|---|---|---|---|
| TpuVersion 枚举 | kViperfish = 3 | kGhostlite = 4 | k6acc60406 = 5 | `TpuVersionToString` 0x20b3a480 |
| ToString | "viperfish" | "ghostlite" | "6acc60406" | rel.ro 表 0x22011bf0 |
| 外部名称 | "TPU v5" (v5p / v5e) | "TPU v6 lite" (v6e) | "TPU7x" (tpu7x) | `TpuVersionToExternalName` 0x20b3a500 |
| 初始化模块 | vxc 0x213eed20 | glc 0x213eb9e0 | gfc 0x213e9f60 | symtab |
| Codec(`TpuCodec::Create` 0x1e835fa0 中的 case) | `CreateTpuCodecViperfish` (case 3) | `CreateTpuCodecGhostlite` (case 4) | anonymous `sub_1E838380` (case 5) | symtab |
| TensorCore / BarnaCore |/|/|/| TpuChipParts |
| SparseCore | 是(第一代) ||| TpuChipParts |
| Driver sub-core ISA | `vxc::vfc/vlc::isa` | `gxc::glc::isa` | `gxc::gfc::isa` | symtab |
| Flag 前缀 | `xla_vf_` (50), `xla_sc_` (164) | `xla_gf_` (44), `xla_sc_` | `xla_gf_`, `xla_sc_` | flag scan |

> **易错点 —** Ghostlite 和 6acc60406 注册到*这个*(VXC)工厂中,但它们的 driver 层 ISA 位于 **`gxc`** 命名空间(`gxc::glc::isa`、`gxc::gfc::isa`)下,而不是 `vxc` 下。只有 Viperfish 的 ISA 位于 `vxc` 下。对 v4/v5 而言,HAL 家族和 driver 子命名空间是解耦的,这也是两个页面互相交叉链接的原因。见 [GXC 家族](gxc-family.md)。

---

## 交叉引用

- [JXC 家族](jxc-family.md) — fused-dataflow 祖先,带有单独的 `JfDmaIssuer`
- [PXC 家族](pxc-family.md) — 引入了 VXC 继承的 fetch/load 拆分;V2 descriptor 的首个使用者
- [GXC 家族](gxc-family.md) — Ghostlite + 6acc60406,通过 glc/gfc 初始化模块注册到这个 VXC 工厂
- [Sub-Core 分类](sub-core-taxonomy.md) — fetch/load 拆分演化中的 `vfc`/`vlc`;SparseCore 引入
- [HAL 家族](hal-families.md) — 共享的 `TpuHalFactory` 基类链和 template-method `Create`
- [代号矩阵](tpu-version-codename-matrix.md) — 6 值 `TpuVersion` enum 和 HAL routing
- [HAL 工厂覆写矩阵](hal-factory-override-matrix.md) — 每个实现的 23 槽覆写表