乐于分享
好东西不私藏

TensorRT-LLM 0.5.0 源码之三十三

TensorRT-LLM 0.5.0 源码之三十三

baseLayer

class BaseLayer{public:    BaseLayer(cudaStream_t stream, tensorrt_llm::common::IAllocator* allocator, bool is_free_buffer_after_forward,        cudaDeviceProp* cuda_device_prop = nullptr)        : stream_(stream)        , allocator_(allocator)        , cuda_device_prop_(cuda_device_prop)        , is_free_buffer_after_forward_(is_free_buffer_after_forward){};    virtual ~BaseLayer() = default;virtual cudaStream_t getStream(){        return stream_;    }virtual void setStream(cudaStream_t stream){        stream_ = stream;    }protected:    // device environments    cudaStream_t stream_;    tensorrt_llm::common::IAllocator* allocator_;    cudaDeviceProp* cuda_device_prop_ = nullptr;    bool is_free_buffer_after_forward_;    bool is_allocate_buffer_ = false; // TODO to be deprecated};

DecodingSetupParams

namespace tc = tensorrt_llm::common;class DecodingSetupParams{public:    std::optional<std::vector<float>> temperature;       // [1] or [batch_size] on cpu    std::optional<std::vector<std::int32_t>> min_length; // [1] or [batch_size] on cpu    // repetition_penalty and presence_penalty are mutually exclusive.    std::optional<std::vector<float>> repetition_penalty; // [1] or [batch_size] on cpu    std::optional<std::vector<float>> presence_penalty;   // [1] or [batch_size] on cpu};

DecodingParams

class DecodingParams{public:    DecodingParams(int step, int ite, tc::Tensor logits, tc::Tensor end_ids)        : step{step}        , ite{ite}        , logits{std::move(logits)}        , end_ids{std::move(end_ids)}    {    }    // mandatory parameters    int step;    int ite; // iteration. ite 用于标识当前正在处理的是这个子批次中的第几个独立序列或实例。    tc::Tensor logits;  // [local_batch_size, beam_width, vocab_size_padded]    tc::Tensor end_ids; // [local_batch_size]};

DecodingOutputParams

class DecodingOutputParams{public:explicit DecodingOutputParams(tc::Tensor outputIds)        : output_ids{std::move(outputIds)}    {    }    // mandatory parameters    tc::Tensor output_ids; // [max_seq_len, batch_size]    // optional parameters    std::optional<tc::Tensor> finished;        // [batch_size * beam_width], optional    std::optional<tc::Tensor> sequence_length; // [batch_size * beam_width], optional    std::optional<tc::Tensor> cum_log_probs;   // [batch_size * beam_width], necessary in beam search    std::optional<tc::Tensor>        output_log_probs;                 // [request_ouptut_length, batch_size * beam_width], must be float*, optional    std::optional<tc::Tensor> parent_ids; // [max_seq_len, batch_size * beam_width], necessary in beam search    tc::Tensor output_ids_ptr;            // [batch_size] int* (2-d array), each int* has [beam_width, max_seq_len]};

BaseSamplingLayer

template <typename T>class BaseSamplingLayer : public BaseLayer{public:    BaseSamplingLayer(size_t vocab_size, size_t vocab_size_padded, cudaStream_t stream,        tensorrt_llm::common::IAllocator* allocator, bool is_free_buffer_after_forward,        cudaDeviceProp* cuda_device_prop);    BaseSamplingLayer(BaseSamplingLayer const& sampling_layer);    ~BaseSamplingLayer() override;    class SetupParams : public DecodingSetupParams    {    public:        std::optional<std::vector<std::uint32_t>> runtime_top_k;    // [1] or [batch_size] on cpu        std::optional<std::vector<float>> runtime_top_p;            // [1] or [batch_size] on cpu        std::optional<std::vector<unsigned long long>> random_seed; // [1] or [batch_size] on cpu    };    class ForwardParams : public DecodingParams    {    public:        ForwardParams(int step, int ite, tc::Tensor logits, tc::Tensor end_ids, int max_seq_len)            : DecodingParams{step, ite, std::move(logits), std::move(end_ids)}            , max_seq_len{max_seq_len}        {        }        // mandatory parameters        int max_seq_len;        // optional parameters        std::optional<tc::Tensor> embedding_bias; // [vocab_size_padded]        std::optional<tc::Tensor> input_lengths;  // [local_batch_size * beam_width]    };void forward(DecodingOutputParams& outputs, ForwardParams const& params);protected:    size_t vocab_size_;    size_t vocab_size_padded_;    size_t sampling_workspace_size_;    void* sampling_workspace_ = nullptr;    // device    curandState_t* curandstate_buf_ = nullptr; // [B,]    unsigned long long* random_seeds_buf_ = nullptr; // [B,]    float* temperature_buf_ = nullptr; // [B,]    float* repetition_penalty_buf_ = nullptr; // [B,]    int32_t* min_lengths_buf_ = nullptr; // [B,]    bool* skip_decode_buf_ = nullptr; // [B,]    T* runtime_logits_buf_ = nullptr;  // [B,V]      // host    std::vector<float> mTemperature;    std::vector<float> mRepetitionPenalty;    std::vector<int32_t> mMinLengths;    bool* skip_decode_ = nullptr;  // [B,], host    bool skip_any_ = false;    tensorrt_llm::kernels::RepetitionPenaltyType repetition_penalty_type_        = tensorrt_llm::kernels::RepetitionPenaltyType::None;virtual void runSampling(DecodingOutputParams& outputs, DecodingParams const& params)= 0;virtual void freeBuffer();void setupBase(size_t batch_size, SetupParams const& setupParams);private:void allocateBuffer(size_t batch_size);bool isValidBatchSize(size_t batch_size);};
template <typename T>BaseSamplingLayer<T>::BaseSamplingLayer(size_t vocab_size, size_t vocab_size_padded, cudaStream_t stream,    IAllocator* allocator, bool is_free_buffer_after_forward, cudaDeviceProp* cuda_device_prop)    : BaseLayer(stream, allocator, is_free_buffer_after_forward, cuda_device_prop)    , vocab_size_(vocab_size)    , vocab_size_padded_(vocab_size_padded){}template <typename T>BaseSamplingLayer<T>::BaseSamplingLayer(BaseSamplingLayer const& sampling_layer)    : BaseLayer(sampling_layer)    , vocab_size_(sampling_layer.vocab_size_)    , vocab_size_padded_(sampling_layer.vocab_size_padded_)    , sampling_workspace_size_(sampling_layer.sampling_workspace_size_){}template <typename T>BaseSamplingLayer<T>::~BaseSamplingLayer(){}

allocateBuffer

template <typename T>void BaseSamplingLayer<T>::allocateBuffer(size_t batch_size){    TLLM_LOG_DEBUG(__PRETTY_FUNCTION__);    curandstate_buf_ = allocator_->reMalloc(curandstate_buf_, sizeof(curandState_t) * batch_size, false); // [B,]    random_seeds_buf_ = allocator_->reMalloc(random_seeds_buf_, sizeof(unsigned long long) * batch_size, false); // [B,]    temperature_buf_ = allocator_->reMalloc(temperature_buf_, sizeof(float) * batch_size, false); // [B,]    repetition_penalty_buf_ = allocator_->reMalloc(repetition_penalty_buf_, sizeof(float) * batch_size, false); // [B,]    min_lengths_buf_ = allocator_->reMalloc(min_lengths_buf_, sizeof(int) * batch_size, false); // [B,]    runtime_logits_buf_ = allocator_->reMalloc(runtime_logits_buf_, sizeof(T) * batch_size * vocab_size_padded_, false); // [B,V]    skip_decode_buf_ = allocator_->reMalloc(skip_decode_buf_, sizeof(bool) * batch_size, false); // [B,]    // host buffers.    skip_decode_ = (bool*) std::realloc(skip_decode_, sizeof(bool) * batch_size);  // [B,]    TLLM_CHECK(skip_decode_ != nullptr);    is_allocate_buffer_ = true;}
template <typename T>void BaseSamplingLayer<T>::freeBuffer(){    TLLM_LOG_DEBUG(__PRETTY_FUNCTION__);    if (is_allocate_buffer_)    {        allocator_->free((void**) (&curandstate_buf_));        allocator_->free((void**) (&random_seeds_buf_));        allocator_->free((void**) (&temperature_buf_));        allocator_->free((void**) (&repetition_penalty_buf_));        allocator_->free((void**) (&min_lengths_buf_));        allocator_->free((void**) (&runtime_logits_buf_));        allocator_->free((void**) (&skip_decode_buf_));        std::free(skip_decode_);        is_allocate_buffer_ = false;    }}

setupBase

default random_seed = 0

template <typename T>void BaseSamplingLayer<T>::setupBase(const size_t batch_size, SetupParams const& setupParams){    TLLM_LOG_DEBUG(__PRETTY_FUNCTION__);    allocateBuffer(batch_size);    // If runtime argument has single random seed, using this random seed to    // initialize the random table of all sentences. If the argument has    // [batch_size] random seeds, initializing the random table by different    // random seeds respectively. If no random seed, initialize the random table    // of all sentences by 0 directly.    // default seed 0.    if (setupParams.random_seed)    {        if (setupParams.random_seed->size() == 1)        {            invokeCurandInitialize(curandstate_buf_, batch_size, setupParams.random_seed->front(), stream_);            sync_check_cuda_error();        }        else        {            TLLM_CHECK_WITH_INFO(setupParams.random_seed->size() == batch_size, "Random seed vector size mismatch.");            cudaAutoCpy(random_seeds_buf_, setupParams.random_seed->data(), batch_size, stream_);            invokeCurandBatchInitialize(curandstate_buf_, batch_size, random_seeds_buf_, stream_);            sync_check_cuda_error();        }    }    else    {        // Initialize curand states using the default seed 0.        invokeCurandInitialize(curandstate_buf_, batch_size, 0, stream_);    }    // Setup penalties.    auto fillBuffers        = [this, &batch_size](auto const& optParam, auto const defaultValue, auto& hostBuffer, auto& deviceBuffer)    {        hostBuffer.resize(batch_size);        if (!optParam)        {            std::fill(std::begin(hostBuffer), std::end(hostBuffer), defaultValue);        }        else if (optParam->size() == 1)        {            std::fill(std::begin(hostBuffer), std::end(hostBuffer), optParam->front());        }        else        {            TLLM_CHECK_WITH_INFO(optParam->size() == batch_size, "Argument vector size mismatch.");            std::copy(optParam->begin(), optParam->end(), std::begin(hostBuffer));        }        cudaAutoCpy(deviceBuffer, hostBuffer.data(), batch_size, stream_);    };      // default temperature 1.0      // defualt min_length 1    fillBuffers(setupParams.temperature, 1.0f, mTemperature, temperature_buf_);    fillBuffers(setupParams.min_length, 1, mMinLengths, min_lengths_buf_);    // default repetition_penalty 0.0    if ((setupParams.repetition_penalty) || (setupParams.presence_penalty))    {        TLLM_CHECK_WITH_INFO(!((setupParams.repetition_penalty) && (setupParams.presence_penalty)),            "Found ambiguous parameters repetition_penalty and presence_penalty "            "which are mutually exclusive. "            "Please provide one of repetition_penalty or presence_penalty.");        repetition_penalty_type_ = (setupParams.repetition_penalty) ? RepetitionPenaltyType::Multiplicative                                                                    : RepetitionPenaltyType::Additive;        auto const& repetition_penalty = (repetition_penalty_type_ == RepetitionPenaltyType::Multiplicative)            ? setupParams.repetition_penalty            : setupParams.presence_penalty;        // repetition_penalty is not empty, so default value 0.0f has no effect        fillBuffers(repetition_penalty, 0.0f, mRepetitionPenalty, repetition_penalty_buf_);    }    else    {        repetition_penalty_type_ = RepetitionPenaltyType::None;    }}

penaltyTypes

enum class RepetitionPenaltyType{    Additive,       // the presence penalty    Multiplicative, // the repetition penalty    None            // No repetition penalty.};inline float getDefaultPenaltyValue(RepetitionPenaltyType penalty_type){    switch (penalty_type)    {    case RepetitionPenaltyType::Additive: return 0.0f;    case RepetitionPenaltyType::Multiplicative: return 1.0f;    default: break;    }    return 0.0f;}

forward

template class BaseSamplingLayer<float>; // fp32template class BaseSamplingLayer<half>;  // fp16, no bf16
template <typename T>void BaseSamplingLayer<T>::forward(DecodingOutputParams& outputs, ForwardParams const& params){    TLLM_LOG_DEBUG("%s start", __PRETTY_FUNCTION__);    auto const batch_size = outputs.output_ids_ptr.shape[0];    auto const local_batch_size = params.logits.shape[0];    auto const ite = params.ite;    auto const step = params.step;    auto* const input_lengths = params.input_lengths ? params.input_lengths->template getPtr<const int>() : nullptr;    auto* logits = params.logits.template getPtr<T>();#define ALL_OF(p_, sz_, dt_, v_) (std::all_of(p_, p_ + sz_, [&](dt_ b) { return b == v_; }))    bool* skip_decode = skip_decode_ + ite * local_batch_size;    if (ALL_OF(skip_decode, local_batch_size, bool, true))    {        // No sample in the current batch to do TopX sampling.        return;    }    skip_any_ = std::any_of(skip_decode, skip_decode + local_batch_size, [](bool b) { return b; });    if (skip_any_)    {        // A TopX Sampling layer directly changes the logit values. In case of        // skip_any==true, meaning topk and topp layers will run simultaneously for        // a batch in the same step. We copy the logits to an internal buffer, not        // affecting the other sampling layers.        TLLM_CHECK(params.logits.size() == local_batch_size * vocab_size_padded_);        cudaD2Dcpy(runtime_logits_buf_, logits, params.logits.size());        logits = runtime_logits_buf_;    }    // 1. logits embedding bias or temperature    auto* embedding_bias = params.embedding_bias ? params.embedding_bias->template getPtr<T const>() : nullptr;    if (embedding_bias != nullptr        || !ALL_OF(std::begin(mTemperature) + ite * local_batch_size, local_batch_size, float, 1.0f))    {        invokeBatchApplyTemperaturePenalty(logits, embedding_bias, temperature_buf_ + ite * local_batch_size,            local_batch_size, vocab_size_, vocab_size_padded_, stream_);    }    sync_check_cuda_error();        // 2. repeation_penalty    if (step > 1 && repetition_penalty_type_ != RepetitionPenaltyType::None)    {        float default_value = getDefaultPenaltyValue(repetition_penalty_type_);        if (!ALL_OF(std::begin(mRepetitionPenalty) + ite * local_batch_size, local_batch_size, float, default_value))        {            auto* const input_lengths                = params.input_lengths ? params.input_lengths->template getPtr<const int>() : nullptr;            invokeBatchApplyRepetitionPenalty(logits, repetition_penalty_buf_ + ite * local_batch_size,                outputs.output_ids_ptr.template getPtr<const int*>(), outputs.sequence_length->getPtr<const int>(),                batch_size, local_batch_size, vocab_size_padded_, input_lengths, repetition_penalty_type_,                params.max_seq_len, stream_);            sync_check_cuda_error();        }    }     // 3. minLengthPenalty    auto* end_ids = params.end_ids.template getPtr<const int>();    invokeMinLengthPenalty(logits, min_lengths_buf_ + ite * local_batch_size, end_ids,        outputs.sequence_length->getPtr<const int>(), input_lengths, local_batch_size, vocab_size_padded_, stream_);    sync_check_cuda_error();#undef ALL_OF     // 4. TopX sampling    runSampling(outputs, params);    if (is_free_buffer_after_forward_)    {        freeBuffer();    }    sync_check_cuda_error();    TLLM_LOG_DEBUG("%s stop", __PRETTY_FUNCTION__);}

参考文献

  • • https://github.com/NVIDIA/TensorRT-LLM/blob/release/0.5.0/cpp/tensorrt_llm/layers/CMakeLists.txt
  • • https://github.com/NVIDIA/TensorRT-LLM/blob/release/0.5.0/cpp/tensorrt_llm/layers/baseSamplingLayer.h
点个「赞」+「在看」❤️
让我们知道这份文字有温暖到你,也是我们持续创作的最大动力!
推荐
TensorRT-LLM 0.5.0 源码之三十二
TensorRT-LLM 0.5.0 源码之三十一
信息差的消失
Agent 数据生产与训练
基准测试设计:选择开放模型测试与封闭模型测试
gRPC 使用建议
flashinfer.sampling 实现四
AI 时代的组织变更
TensorRT-LLM 0.5.0 源码之二十七
flashinfer.sampling 实现三
什么是循环工程?AI 编码智能体的新范式
Trae IDE 实战指南:核心AI功能、Skill运用与项目开发全流程
Small matrix multiplication - Triton
从空文件夹到生成图表:Claude Code 实战教程
Claude Code 入门:研究者配置指南
Claude Code 究竟擅长什么?一次实测验证
GLM-5.2:面向长时序任务打造
Anthropic Fable 5
循环工程(Loop Engineering)
Agent SFT 标准数据格式 + Loss Mask 完整实现
4D Parallelism
TileLang与OpenAI Triton的核心区别
TensorRT-LLM 0.5.0 源码之二十六
Agent SFT 数据
Claude Code 的上限,就是你的上限
如何用Claude Code提升软件工程工作效率、改善生活
LLM推理优化的核心技术:深入理解KV缓存与分页注意力机制
MiMo-V2-Flash技术报告
AI原生开发中的MCP与CLI对比
Qwen3-TTS 技术报告
PagedAttention
如何让AI听懂你的“话外音”?GOAT-SLM模型实现更懂情感的语言交互
FlashAttention与PagedAttention详解:拯救GPU显存,让大模型飞起来的核心技术
LM-as-a-judge:LLM评估指南
LLM Sequence Packing
深入了解SmoothQuant:大模型高效量化背后的数学原理
语音合成(TTS)分句生成拼接时的响度一致性问题:现状、成因与对策
当扩散模型遇上流匹配:原来是一回事儿
语音合成中的“一对多”问题主流模型解决方案分析
使用LoRA对LLM进行微调的实用技巧
语音合成(TTS)中文自然度:问题、成因、解决方案
语音合成(TTS)跳跃与重复问题的解析:成因、机制及解决方案
最新!SpeechLLM 综述:架构、能力、挑战与未来全揭秘

相关学习资料