C++ GPT 运行时#

TensorRT-LLM 包含一个 C++ 组件,用于执行使用 Python API 构建的 TensorRT 引擎,如TensorRT-LLM 架构部分所述。该组件称为 C++ 运行时。

C++ 运行时的 API 由cpp/include/tensorrt_llm/runtime中声明的类和cpp/tensorrt_llm/runtime中实现的类组成。

即使该文档中描述的不同组件名称中包含 GPT,它们也并非仅限于此特定模型。例如,这些类可用于实现 BLOOM、GPT-J、GPT-NeoX 或 LLaMA 等自回归模型。

对 T5 等编码器-解码器模型的完整支持将在未来的 TensorRT-LLM 版本中添加。目前仅提供 Python 版本的实验性支持,位于examples/enc_dec文件夹中。

概述#

运行时模型由ModelConfig类的实例和必须执行的 TensorRT 引擎指针描述以执行推理。环境通过WorldConfig进行配置(该名称来源于MPI及其“著名”的MPI_COMM_WORLD默认通信器)。SamplingConfig类封装了控制新令牌生成的参数。

模型配置#

模型配置是ModelConfig类的一个实例。该类封装了以下参数(它们被声明为私有成员变量,并通过 getter 和 setter 暴露):

  • vocabSize,词汇表大小,

  • numLayers,模型中的层数,

  • numHeads,注意力块中的头数,

  • numKvHeads,注意力组件中 K 和 V 的头数。当 K/V 头数与 (Q) 头数相同时,模型使用多头注意力。当 K/V 头数为 1 时,使用多查询注意力。否则,使用分组查询注意力。有关更多信息,请参阅多头、多查询和分组查询注意力

  • hiddenSize,隐藏维度的大小,

  • dataType,用于构建 TensorRT 引擎并在推理期间运行模型的数据类型,

  • useGptAttentionPlugin,指示多头、多查询和分组查询注意力运算符是否使用GPT Attention 插件编译,

  • inputPacked,指示输入必须打包(或设置为false时进行填充)。出于性能原因,建议始终使用打包,即使其默认值设置为false(将在未来版本中更改)。有关更多信息,请参阅多头、多查询和分组查询注意力

  • pagedKvCache,指示 K/V 缓存是否使用分页。有关更多信息,请参阅多头、多查询和分组查询注意力

  • tokensPerBlock,是 K/V 缓存每个块中的令牌数。当启用分页 K/V 缓存时,该参数相关。默认值为 64。有关更多信息,请参阅多头、多查询和分组查询注意力

  • quantMode,控制量化方法。有关更多信息,请参阅数值精度

  • maxBatchSize,指示 TensorRT 引擎构建时支持的最大批处理大小,

  • maxInputLen,输入序列的最大大小,

  • maxSequenceLen,序列的最大总大小(输入+输出)。

World 配置#

使用 TensorRT-LLM C++ 运行时无需熟悉MPI。您需要了解以下两点主要内容:

  • TensorRT-LLM 中的 C++ 运行时使用进程在不同的 GPU 上执行 TensorRT 引擎。这些 GPU 可以位于单个节点上,也可以位于集群中的不同节点上。每个进程在 MPI 中称为一个 rank

  • rank 被分组到通信组中。TensorRT-LLM C++ 运行时将该组称为 world

World 配置是WorldConfig类的一个实例,它封装了以下参数:

  • tensorParallelism,协作实现张量并行性(TP)的 rank 数。使用 TP 时,每个 GPU 执行模型所有层的计算。其中一些计算在 GPU 之间分布。在大多数情况下,TP 比流水线并行性(PP)更均衡,但需要在 GPU 之间更高的带宽。在 GPU 之间存在 NVLINK 时,建议使用此设置,

  • pipelineParallelism,协作实现流水线并行性(PP)的 rank 数。使用 PP 时,每个 GPU 处理连续层的一个子集。GPU 之间的通信仅发生在层子集的边界处。使用 PP 更难保证 GPU 的充分利用,但所需的内存带宽更少。在 GPU 之间不存在 NVLINK 时,建议使用此设置,

  • rank,rank 的唯一标识符,

  • gpusPerNode,指示每个节点上的 GPU 数量。拥有此信息使 C++ 运行时能够优化节点内 GPU 之间的通信(例如利用 A100 DGX 节点中 GPU 之间的NVLINK互连)。

采样参数#

SamplingConfig类封装了控制新令牌生成的参数。下表列出了选择解码方法的比较(X表示尚不支持)。除了beamWidth参数外,所有字段都是可选的,如果用户未提供值,运行时将使用默认值。对于向量字段,TensorRT-LLM 运行时支持每个序列一个值(即向量包含batchSize个值)。如果所有序列对给定参数使用相同的值,则向量可以限制为单个元素(即size() == 1)。

HF 中的方法名称

HF 中的条件

TRT-LLM 中的方法名称

TRT-LLM 中的条件

辅助解码

assistant_modelprompt_lookup_num_tokens!=None

X

集束搜索解码

num_beams>1do_sample=False

集束搜索

beamWidth > 1

集束搜索多项式采样

num_beams>1do_sample=True

X

受约束集束搜索解码

constraints!=Noneforce_words_ids!=None

X

对比搜索

penalty_alpha>0top_k>1

X

多样化集束搜索解码

num_beams>1num_beam_groups>1

X

贪婪解码

num_beams=1do_sample=False

采样

beamWidth == 1topK=0topP=0.0f

多项式采样

num_beams=1do_sample=True

采样

beamWidth == 1 且 (topK>0topP>0.0f)

常规

TRT-LLM 中的名称

描述

数据类型

值范围

默认值

HF 中的名称

temperature

采样工作流程中 logits 的调制

List[Float]

[0.0f, $+\infty$)

1.0f (无调制)

temperature

minLength

生成令牌数量的下界

List[Int]

[0, $+\infty$)

0 (无效果(生成的第一个令牌可以是 EOS))

min_length

repetitionPenalty

惩罚重复令牌
乘法,与出现次数无关

List[Float]

[0.0f, $+\infty$)
< 1.0f 鼓励重复
> 1.0f 抑制重复

1.0f (无效果)

repetition_penalty

presencePenalty

惩罚已存在的令牌
加法,与出现次数无关

List[Float]

($-\infty$, $+\infty$)
< 0.0f 鼓励重复
> 0.0f 抑制重复

0.0f (无效果)

no

frequencyPenalty

惩罚已存在的令牌
加法,与出现次数有关

List[Float]

($-\infty$, $+\infty$)
< 0.0f 鼓励重复
> 0.0f 抑制重复

0.0f (无效果)

no

noRepeatNgramSize

List[Int]

[0, $+\infty$)
> 0 该大小的所有 ngrams 只能出现一次

0 (无效果)

no_repeat_ngram_size

  • 在将repetitionPenaltypresencePenaltyfrequencyPenalty应用到 logits 时,输入提示的令牌会被包含在内。

  • 参数repetitionPenaltypresencePenaltyfrequencyPenalty不是互斥的。

采样

TRT-LLM 中的名称

描述

数据类型

值范围

默认值

HF 中的名称

randomSeed

随机数生成器的随机种子

Int64

[0, 2^64-1]

0

no

topK

用于采样的 logits 数量

List[Int]

[0, 1024]

0

top_k

topP

用于采样的 top-P 概率

List[Float]

[0.0f, 1.0f]

0.0f

top_p

topPDecay

topP 算法中的衰减

List[Float]

(0.0f, 1.0f]

1.0f

no

topPMin

topP 算法中的衰减

List[Float]

(0.0f, 1.0f]

1.0e-6f

no

topPResetIds

topP 算法中的衰减

List[Int]

[-1, $+\infty$)

-1 (无效果)

no

minP

缩放最可能的令牌以确定最小令牌概率。

List[Float]

[0.0f, 1.0f]

0.0 (无效果)

min_p

  • 如果设置topK = 0topP = 0.0f,则执行贪婪搜索。

  • 如果设置topK > 0topP = 0.0f,则概率最高的topK个令牌将成为采样的候选(在 TRT-LLM 中称为TopK sampling)。

  • 如果设置topK = 0topP > 0.0f,令牌将按概率降序排序,然后累积概率大于topP的概率最高的令牌将成为采样的候选(在 TRT-LLM 中称为TopP sampling)。

  • 如果设置topK > 0topP > 0.0f,则将选择概率最高的topK个令牌,然后将这些选定的令牌按概率降序排序并将其概率归一化,然后累积概率大于topP的归一化概率最高的令牌将成为采样的候选(在 TRT-LLM 中称为TopKTopP sampling)。

  • 如果批处理中不同序列提供了不同的topK值,则实现的性能将取决于最大值。出于效率原因,建议将具有相似topK值的请求一起进行批处理。

  • topPDecaytopPMintopPResetIds用于开放式文本生成的真实性增强语言模型中进行了解释。topPDecay是衰减,topPMin是下界,topPResetIds指示重置衰减的位置。

  • minP升温:Min-p 采样用于创意和连贯的 LLM 输出中进行了解释。

集束搜索

TRT-LLM 中的名称

描述

数据类型

值范围

默认值

HF 中的名称

beamWidth

集束搜索算法的宽度

Int

[0, 1024]

0 (禁用集束搜索)

beam_width

beamSearchDiversityRate

生成令牌的多样性

List[Float]

[0, $+\infty$)

0.0f

diversity_penalty

lengthPenalty

惩罚更长的序列

List[Float]

[0, $+\infty$)

0.0f

length_penalty

earlyStopping

参见下方描述

List[Int]

($-\infty$, $+\infty$)

0

early_stopping

  • 集束搜索算法:集束搜索

  • HF 中的参数diversity_penalty仅用于多样化集束搜索解码(或称为Group-Beam-Search),TRT-LLM 尚未支持该功能。

  • 如果设置earlyStopping = 1,则一旦生成了beamWidth个完成句子,解码将停止。

  • 如果设置earlyStopping = 0,则解码将继续进行,直到无法生成更好的句子(得分更高)。

  • 如果将earlyStopping设置为其他值,则解码将仅取决于lengthlengthPenalty

  • beamWidth参数是一个标量值。这意味着在 TensorRT-LLM 的当前版本中,无法为每个输入序列指定不同的宽度。此限制可能会在未来版本中解除。

会话#

运行时会话已被弃用,推荐使用执行器 API。它将在 TensorRT-LLM 的未来版本中移除。

GptSession 用于运行 GPT 类自回归模型的示例可在cpp/tests/runtime/gptSessionTest.cpp中找到。

内部组件#

GptSession类封装了两个主要组件。TllmRuntime负责执行 TensorRT 引擎。GptDecoder从 logits 生成令牌。TllmRuntime类是一个内部组件,不建议直接使用该类。GptDecoder可以直接用于实现自定义生成循环,以及用于GptSession实现无法满足的用例。

In-flight Batching 支持#

In-flight batching 通过为每个请求使用单独的解码器来支持。与使用单个解码器相比,最大的区别在于如何管理从 logits 生成令牌。一个批处理被拆分成batchSize个单独的请求,并使用分开的 CUDA 流发出内核。此行为可能会在未来版本中重新考虑,以维护批处理的结构并提高效率。

已知问题和未来变更#

  • 在当前版本的 TensorRT-LLM 中,C++ 和 Python 运行时是两个独立的软件组件,并且 C++ 运行时正在更积极地开发(包括 in-flight batching 等功能)。未来版本的目标可能是基于 C++ 运行时重建 Python 运行时。