<?xml version="1.0" encoding="UTF-8"?><rss xmlns:dc="http://purl.org/dc/elements/1.1/" xmlns:content="http://purl.org/rss/1.0/modules/content/" xmlns:atom="http://www.w3.org/2005/Atom" version="2.0"><channel><title><![CDATA[3090 单卡跑 Qwen3.8-27B：NInfer 上机实测（180K 上下文 / C2 并发 / 4bit KV）]]></title><description><![CDATA[<h1>3090 单卡跑 Qwen3.8-27B：NInfer 上机实测（180K 上下文 / C2 并发 / 4bit KV）</h1>
<p dir="auto">NInfer 在论坛里火了一阵（<a href="https://lcz.me/topic/1644">原帖</a> 讲的是它把 NInfer 移植到 SM86），<br />
我机器上有一张 3090，原本跑的是调优过的 vLLM 栈，这次把服务换到 NInfer 上，看看到底能到什么程度、跟原来差多少。<br />
别人写过的背景不重复，这篇只写<strong>我这台机器的数字、能直接抄的配置，以及那几个不改就起不来的参数</strong>。</p>
<table class="table table-bordered table-striped">
<thead>
<tr>
<th></th>
<th></th>
</tr>
</thead>
<tbody>
<tr>
<td>显卡</td>
<td><strong>单张 RTX 3090 24G</strong>（SM86），功耗墙 <strong>300W</strong>（这卡默认 350W，影响见测评）</td>
</tr>
<tr>
<td>驱动</td>
<td>595.71.05</td>
</tr>
<tr>
<td>引擎</td>
<td>NInfer-3090 <strong>v0.6.1</strong>（官方 Linux x64 预编译包）</td>
</tr>
<tr>
<td>权重</td>
<td><code>neroued/Qwen3.8-27B-NInfer</code> @ revision <code>18dfc887</code>（container v2，18.2 GB）</td>
</tr>
<tr>
<td>部署</td>
<td>Docker（CUDA 12.8 runtime 底座 + 官方预编译二进制）</td>
</tr>
</tbody>
</table>
<hr />
<h2>一、部署：三步，全都能直接抄</h2>
<h3>1. 拿模型（<strong>必须钉 revision</strong>）</h3>
<p dir="auto">HF 仓库的 <code>qwen3_8_27b.ninfer</code> 在 2026-09-15 升级成 <strong>container v3</strong>，而 v0.6.1 的预编译二进制只认 <strong>v1/v2 容器</strong>，<br />
直接下 main 会报 <code>artifact magic is not NInfer v1 or v2</code>。钉到 v2 容器那个 revision：</p>
<pre><code class="language-bash">curl -L -C - --fail -o qwen3_8_27b.ninfer \
  "https://huggingface.co/neroued/Qwen3.8-27B-NInfer/resolve/18dfc887423fa5aabf3cb56fac41490e462b3fab/qwen3_8_27b.ninfer"
# 18,210,531,328 B   sha256 eec39564993d6e9c7d5e383382a760f093465c9d163ec9a1bd6b80199514bf3e
</code></pre>
<h3>2. 打镜像（10 秒，不编译）</h3>
<p dir="auto">上游只发 Dockerfile（源码 245 步 CUDA 编译）和预编译二进制，<strong>没有现成镜像</strong>（GHCR 上这个包匿名拉取是 DENIED）。<br />
最省事的路：拿官方 <strong>Linux x64 预编译包</strong>塞进官方 CUDA runtime 底座。</p>
<pre><code class="language-dockerfile">FROM nvidia/cuda:12.8.0-runtime-ubuntu24.04
# GeForce 卡不能用 forward-compat 的新 libcuda，不删会在启动时报 cudaErrorCompatNotSupportedOnDevice
RUN rm -rf /usr/local/cuda-12.8/compat /usr/local/cuda/compat
RUN apt-get update &amp;&amp; apt-get install -y --no-install-recommends ca-certificates curl \
    &amp;&amp; rm -rf /var/lib/apt/lists/*
COPY ninfer /usr/local/bin/ninfer
COPY ninfer-serve /usr/local/bin/ninfer-serve
ENTRYPOINT ["ninfer-serve"]
</code></pre>
<p dir="auto">预编译包：<code>ninfer-rtx3090-linux-x64-0.6.1-rtx3090.tar.gz</code><br />
（sha256 <code>eb6a6e5b4b318dcf5a8173ccdae8d98acbe730606a50d87eaf120353962965b5</code>），解包后两个二进制就是全部。</p>
<h3>3. 启动（<strong>四个参数是踩出来的，别改</strong>）</h3>
<pre><code class="language-bash">docker run -d --name ninfer --gpus '"device=0"' --ipc=host -p 18020:18020 \
  -v $PWD/models:/models:ro ninfer-3090:0.6.1 \
  /models/qwen3_8_27b.ninfer \
  --host 0.0.0.0 --port 18020 --model-id qwen3.8-27b --api-key "$KEY" \
  --max-context 184320 --kv-capacity 184320 \
  --max-concurrency 2 --max-pending-requests 16 --pending-timeout-ms 900000 \
  --prefill-chunk 1024 --kv-dtype rk8v4 --spec mtp --draft-tokens 3 --lm-head-draft
</code></pre>
<table class="table table-bordered table-striped">
<thead>
<tr>
<th>参数</th>
<th>为什么必须这么写</th>
</tr>
</thead>
<tbody>
<tr>
<td><code>--kv-capacity 184320</code>（<strong>显式</strong>）</td>
<td><code>auto</code> 在 C2 + MTP3 下直接拒绝启动：引擎最小运行时 6.68 GiB + 1 GiB 自动余量 &gt; 权重加载后剩下的 6.63 GiB</td>
</tr>
<tr>
<td><code>--pending-timeout-ms 900000</code></td>
<td>默认超时下，C2 的第二个长上下文请求会在排队时 <code>error inference request expired while waiting for admission</code></td>
</tr>
<tr>
<td><code>--kv-dtype rk8v4</code></td>
<td>int8 的 KV 在 C2 下最多只能开到 160K；rk8v4（K8/V4）能到 180K，<strong>实测两者速度没有差别</strong></td>
</tr>
<tr>
<td>不加 <code>--vision</code></td>
<td>开视觉要多占约 2.1 GiB，C2 下上下文从 180K 掉到 136K（余量只剩 48 MiB）</td>
</tr>
</tbody>
</table>
<p dir="auto">显存账（这张 24G 卡）：权重 16.67 GiB + KV 池（184320 token）5.61 GiB，模型加载 19 秒，<strong>启动后余量 1.02 GiB</strong>。</p>
<blockquote>
<p dir="auto"><strong>踩坑一句话版</strong>：v3 模型读不了（要钉 revision）、<code>kv-capacity auto</code> 起不来（要显式）、<code>fp8</code> KV 在 SM86 上被引擎拒绝（没有对应内核）、长上下文 C2 第二个请求会排队超时（要调大 pending timeout）、开 vision 只能 136K。</p>
</blockquote>
<p dir="auto"><strong>划重点：单张 3090 上，<code>180K 上下文 + 4bit KV(rk8v4) + C2 并发 + 关 vision</code> 是反复对比后的最佳组合。</strong><br />
再往上加要么牺牲并发（C1），要么牺牲上下文（开 vision 只到 136K），要么牺牲速度（int8 + 关投机解码换 180K，但 decode 掉到 35 tok/s）。</p>
<hr />
<h2>二、测评</h2>
<p dir="auto">测试条件：单个 Docker 实例、<code>--max-concurrency 2</code>、<code>--kv-dtype rk8v4</code>、MTP3 投机解码、默认采样、<br />
输入是真实长度的中英混合上下文（coding = 一整段代码 + 改代码要求；agent = 系统提示 + 工具定义 + 多轮工具返回 + 提问），<br />
每条请求最多生成 160 token。<strong>输入超过约 90K 时一个 180K 的 KV 池装不下两份，那两行是单请求</strong>（表里并发列写 1）。</p>
<p dir="auto"><strong>功耗墙 300W</strong>（这台的设置；卡默认 350W）。满载实测：</p>
<table class="table table-bordered table-striped">
<thead>
<tr>
<th></th>
<th>功耗</th>
<th>SM 频率</th>
<th>温度</th>
</tr>
</thead>
<tbody>
<tr>
<td>满载（util &gt; 60%，n=43 采样）</td>
<td>avg <strong>298 W</strong> / max 300 W（贴墙）</td>
<td>avg <strong>1538 MHz</strong>（1395–1665）</td>
<td>74 °C</td>
</tr>
</tbody>
</table>
<p dir="auto">放开到 350W 实测 decode <strong>+8%</strong>（54.6 → 59.0 tok/s，SM 1410 → 1545 MHz），我为了控温没放。</p>
<h3>coding 场景（长代码上下文 + 改代码）</h3>
<table class="table table-bordered table-striped">
<thead>
<tr>
<th>输入 token</th>
<th>并发</th>
<th>TTFT</th>
<th>prefill</th>
<th>decode/路</th>
<th>decode 合计</th>
<th>MTP 接受率</th>
<th>功耗 avg/max</th>
</tr>
</thead>
<tbody>
<tr>
<td>8,359</td>
<td>2</td>
<td>9.2s / 19.0s</td>
<td>903 tok/s</td>
<td>35.7 / 38.2 tok/s</td>
<td><strong>74 tok/s</strong></td>
<td>48.2%</td>
<td>292 / 300 W</td>
</tr>
<tr>
<td>32,305</td>
<td>2</td>
<td>39.1s / 80.1s</td>
<td>823 tok/s</td>
<td>43.3 / 46.6 tok/s</td>
<td><strong>90 tok/s</strong></td>
<td>58.3%</td>
<td>294 / 300 W</td>
</tr>
<tr>
<td>64,233</td>
<td>2</td>
<td>87.2s / 177.5s</td>
<td>736 tok/s</td>
<td>55.3 / 47.7 tok/s</td>
<td><strong>103 tok/s</strong></td>
<td>54.1%</td>
<td>297 / 300 W</td>
</tr>
<tr>
<td>128,089</td>
<td>1</td>
<td>209.8s</td>
<td>611 tok/s</td>
<td>51.5 tok/s</td>
<td><strong>52 tok/s</strong></td>
<td>66.7%</td>
<td>295 / 300 W</td>
</tr>
<tr>
<td>173,832</td>
<td>1</td>
<td>319.6s</td>
<td>544 tok/s</td>
<td>41.1 tok/s</td>
<td><strong>41 tok/s</strong></td>
<td>52.2%</td>
<td>296 / 300 W</td>
</tr>
</tbody>
</table>
<h3>agent 场景（system + 工具定义 + 多轮工具结果 + 提问）</h3>
<table class="table table-bordered table-striped">
<thead>
<tr>
<th>输入 token</th>
<th>并发</th>
<th>TTFT</th>
<th>prefill</th>
<th>decode/路</th>
<th>decode 合计</th>
<th>MTP 接受率</th>
<th>功耗 avg/max</th>
</tr>
</thead>
<tbody>
<tr>
<td>8,533</td>
<td>2</td>
<td>9.6s / 19.8s</td>
<td>884 tok/s</td>
<td>66.8 / 67.6 tok/s</td>
<td><strong>134 tok/s</strong></td>
<td>98.2%</td>
<td>290 / 300 W</td>
</tr>
<tr>
<td>33,057</td>
<td>2</td>
<td>40.5s / 82.0s</td>
<td>815 tok/s</td>
<td>79.5 / 77.9 tok/s</td>
<td><strong>157 tok/s</strong></td>
<td>98.2%</td>
<td>296 / 300 W</td>
</tr>
<tr>
<td>65,829</td>
<td>2</td>
<td>90.1s / 181.2s</td>
<td>730 tok/s</td>
<td>74.8 / 73.6 tok/s</td>
<td><strong>148 tok/s</strong></td>
<td>98.2%</td>
<td>296 / 300 W</td>
</tr>
<tr>
<td>131,419</td>
<td>1</td>
<td>217.5s</td>
<td>605 tok/s</td>
<td>63.2 tok/s</td>
<td><strong>63 tok/s</strong></td>
<td>96.3%</td>
<td>296 / 300 W</td>
</tr>
<tr>
<td>178,335</td>
<td>1</td>
<td>331.6s</td>
<td>538 tok/s</td>
<td>58.9 tok/s</td>
<td><strong>59 tok/s</strong></td>
<td>96.3%</td>
<td>296 / 300 W</td>
</tr>
</tbody>
</table>
<h3>四个观察</h3>
<ol>
<li><strong>prefill 是串行的</strong>，C2 的两个请求不是同时开始吃 prompt：第二个的 TTFT ≈ 排队（第一个的 prefill 时间）+ 自己的 prefill。<br />
32K 输入时 39s / 80s，64K 时 87s / 177s，都是这个规律。所以 C2 的并发收益主要体现在 decode 阶段，不是 TTFT。</li>
<li><strong>prefill 速度本身随输入变长而下降</strong>：8K 时 ~900 tok/s，64K 时 ~735，178K 时只有 ~545 tok/s。<br />
长上下文真正的代价是 TTFT（178K 输入要等 5.5 分钟），不是 decode。</li>
<li><strong>decode 几乎不随上下文衰减</strong>：coding 场景 36～55 tok/s、agent 场景 59～80 tok/s，178K 输入下反而还有 41～59。</li>
<li><strong>MTP 接受率完全看内容形态</strong>：agent 的工具调用轨迹是结构化 JSON，接受率 <strong>96～100%</strong>（每轮 3.9～4.0 个 token）；<br />
自由文本/代码只有 44～67%（每轮 2.4～3.0）。这也是 agent 场景 decode 比 coding 高一截的原因 —— 投机解码对结构化输出特别划算。</li>
</ol>
<h3>和 vLLM（我上一版用的栈）比：prefill 差一倍，原因是算力路径</h3>
<p dir="auto">同一张卡、同一个模型（Qwen3.8-27B W4A16），我上一版跑的是 <a href="https://github.com/syv-ai/HyperQwen" rel="nofollow ugc">syv-ai/HyperQwen</a> 系的 vLLM 栈<br />
（那套打了四十多个补丁 + 自定义 int8 预填注意力内核，不是原生 vLLM 开箱），本机实测：</p>
<table class="table table-bordered table-striped">
<thead>
<tr>
<th>输入长度</th>
<th>1K</th>
<th>4K</th>
<th>16K</th>
<th>64K</th>
<th>100K+</th>
</tr>
</thead>
<tbody>
<tr>
<td>vLLM（INT8 激活路径）</td>
<td>2,056</td>
<td><strong>2,170</strong></td>
<td>1,965</td>
<td><strong>1,412</strong></td>
<td>1,161@100K、<strong>934@178K</strong></td>
</tr>
<tr>
<td><strong>ninfer（这篇）</strong></td>
<td>~920</td>
<td>~920</td>
<td>892@20K</td>
<td>736</td>
<td>611@128K、544@178K</td>
</tr>
</tbody>
</table>
<p dir="auto">单流 decode 同理：vLLM 那套 <strong>110–118 tok/s</strong>，ninfer <strong>41–59 tok/s</strong>。两个方向都差大约一倍。</p>
<p dir="auto"><strong>原因不是 ninfer 写得烂，是两条算力路径的物理上限差 2 倍。</strong> 27B dense 每 prefill 一个 token 约 <strong>54 GFLOP</strong>：</p>
<table class="table table-bordered table-striped">
<thead>
<tr>
<th></th>
<th>用的单元</th>
<th>3090 上的算力</th>
<th>理论上限</th>
<th>实测达到</th>
</tr>
</thead>
<tbody>
<tr>
<td>ninfer</td>
<td>反量化 → <strong>FP16</strong> tensor core</td>
<td>71 TFLOPS</td>
<td>~1,315 tok/s</td>
<td>925（<strong>70%</strong>）</td>
</tr>
<tr>
<td>vLLM</td>
<td><strong>INT8</strong> tensor core（激活也量化）</td>
<td>142 TOPS</td>
<td>~2,630 tok/s</td>
<td>2,170（<strong>82%</strong>）</td>
</tr>
</tbody>
</table>
<p dir="auto">ninfer 已经把 FP16 这条路吃到七成。我把 <code>--prefill-chunk</code> 从 512 扫到 3584（911 / 925 / 927 / 925 tok/s），<br />
<strong>没有可调余量</strong>；它的权重是 4–6 bit 混合精度、激活是 FP16，所以只能走 FP16 MMA。<br />
想翻倍得让<strong>激活</strong>也走 int8，而 ninfer 现在没有这个开关（<code>--kv-dtype</code> 只管 KV cache）。<br />
也正因如此，<strong>给它换 int8 权重是负收益</strong> —— decode 是显存带宽瓶颈，权重从 4.6 bit 涨到 8 bit，每步要读的字节多 74%，decode 只会更慢。</p>
<p dir="auto">顺带对齐第三方数据，ninfer 在 dense 27B 这级别并不难看（llama.cpp CUDA 在 3090 上跑 Qwen3.5-27B Q4_K：<br />
4K <strong>1,104</strong> / 16K 977 / 32K 848 / 64K <strong>679</strong> tok/s）：浅上下文它低约 15%，<strong>64K 以上反而反超</strong>。<br />
网上那些 5,000+ tok/s 的 prefill 数字是 7B 小模型或 3–4B 激活的 MoE，跟 dense 27B 不是一个量级，别被带偏。</p>
<p dir="auto"><strong>所以怎么选</strong>：要吞吐、要短提示首字快（IDE agent、批量 API），vLLM 那套明显更强；<br />
要<strong>单卡 180K + 双并发 + Anthropic 原生协议 + 部署极简</strong>（一个预编译包，无补丁无编译），ninfer 更省事。<br />
我把它定位成"够用的长上下文单卡后端"，不拿它跟调优过的 vLLM 比跑分。</p>
<h3>和官方数字的差距（为什么不是 71 tok/s）</h3>
<p dir="auto">官方单用户 71 tok/s 那组数据是 <strong>Windows 版</strong>跑出来的，README 里写得很清楚：<br />
"A real-artifact Linux generation and <strong>Linux performance qualification remain open</strong>" —— Linux 二进制没做性能认证。<br />
除去平台差异，我这边的缺口主要在两处：<strong>MTP 接受率</strong>（2.4 vs 2.83 token/轮）和 <strong>功耗墙</strong>（300W 把 SM 压在 ~1.5 GHz）。<br />
参数上和官方 C1 示例逐字一致，没有漏开关。</p>
<hr />
<h2>三、一句话总结</h2>
<p dir="auto">NInfer 在 3090 上确实能用，<strong>单卡 180K 上下文 + 双并发</strong>当个人 agent 后端够了；<br />
但它的甜区是"上下文长、并发低、部署省事"，不是跑分 —— 同卡同模型上，调优过的 vLLM 栈在 prefill 和单流 decode 上都快约一倍，<br />
根因是算力路径（FP16 vs INT8 tensor core），不是实现质量。这点我不粉饰，选它买的是"一个预编译包跑起 180K + Anthropic 协议"。</p>
<p dir="auto">抄配置的话，把上面那四个参数照抄，尤其 <strong><code>--kv-capacity</code> 显式写</strong> 和 <strong><code>--pending-timeout-ms</code> 调大</strong> —— 这两个不改，C2 根本跑不起来。</p>
]]></description><link>https://lcz.me/topic/1904</link><generator>RSS for Node</generator><lastBuildDate>Fri, 25 Sep 2026 21:27:27 GMT</lastBuildDate><atom:link href="https://lcz.me/topic/1904.rss" rel="self" type="application/rss+xml"/><pubDate>Wed, 23 Sep 2026 02:01:57 GMT</pubDate><ttl>60</ttl><item><title><![CDATA[Reply to 3090 单卡跑 Qwen3.8-27B：NInfer 上机实测（180K 上下文 / C2 并发 / 4bit KV） on Thu, 24 Sep 2026 22:04:12 GMT]]></title><description><![CDATA[<p dir="auto">9–12 t/s 偏低。同卡同方案（单卡 3090、单流 C1、冷缓存、功耗墙 300W）实测 116K 上下文约 31 t/s、159K 约 19.9 t/s，所以先按下面几条定位，通常不用换方案。</p>
<ol>
<li>先分清瓶颈在显存带宽还是 KV 落 host。跑 decode 时看 <code>nvidia-smi dmon</code>：SM 高、mem 也高是正常带宽受限；如果 SM 不高、但 PCIe 有明显流量，基本是 KV/权重被 offload 到 CPU，长 ctx 下每 token 读 KV 全走 PCIe，就是这个掉到 10 t/s 的形态。</li>
<li>看 vLLM 启动日志里 <code>GPU KV cache size: N tokens</code> 是否覆盖你的实际上下文。<code>--max-model-len</code> 开太大（比如 256K）会按上限分配 block，24G 上更容易触发抢占/换页，按实际要用的长度设准。</li>
<li>确认 KV 精度真的走了 k4v2：KV 相关的开关要显式打开。退回 fp16 KV 时长 ctx 每 token 读取字节翻倍，decode 会直接掉一半。</li>
<li>查并发/抢占：vLLM 日志里搜 <code>Preemption</code>。多人同时请求会把单流压到几条，先按 C1 单流测基线。</li>
<li>关掉非必要开销：<code>--enforce-eager</code> 若开着（禁用 CUDA graph）会牺牲 decode 性能；采样用默认，别叠 grammar 或大 JSON 约束。</li>
</ol>
<p dir="auto">把启动命令、模型版本/commit、实际 max-model-len，以及一段 decode 时的 <code>nvidia-smi dmon</code>（含 SM%/mem%/power）贴出来，我对着数据判断是 offload、KV 精度还是调度问题。</p>
]]></description><link>https://lcz.me/post/20575</link><guid isPermaLink="true">https://lcz.me/post/20575</guid><dc:creator><![CDATA[Xiaote]]></dc:creator><pubDate>Thu, 24 Sep 2026 22:04:12 GMT</pubDate></item><item><title><![CDATA[Reply to 3090 单卡跑 Qwen3.8-27B：NInfer 上机实测（180K 上下文 / C2 并发 / 4bit KV） on Thu, 24 Sep 2026 18:49:12 GMT]]></title><description><![CDATA[<p dir="auto">版主您好，我现在单卡3090用的syv-ai/HyperQwen 的官方方案，这个方案长上下文的情况下decode输出特别慢，只有9-12token/s，想问下有什么好优化方案</p>
]]></description><link>https://lcz.me/post/20557</link><guid isPermaLink="true">https://lcz.me/post/20557</guid><dc:creator><![CDATA[Prio]]></dc:creator><pubDate>Thu, 24 Sep 2026 18:49:12 GMT</pubDate></item><item><title><![CDATA[Reply to 3090 单卡跑 Qwen3.8-27B：NInfer 上机实测（180K 上下文 / C2 并发 / 4bit KV） on Wed, 23 Sep 2026 07:02:04 GMT]]></title><description><![CDATA[<p dir="auto"><a class="plugin-mentions-user plugin-mentions-a" href="/user/davidwei0826" aria-label="Profile: davidwei0826">@<bdi>davidwei0826</bdi></a> 这组数据做得干净，功耗墙、冷缓存自证、pp/tg 分离都锁上了，结论我认可：单卡 3090 综合仍是 HyperQwen 更划算。补两点让 crossover 更硬：</p>
<ol>
<li>你标 † 的 29K/58K 是 C2 两路并发的单路值，而 1-4K 和 116K/159K 大概率是 C1。并发会同时压 KV 带宽和调度，两点不能和单流曲线直接连——crossover 的确切位置可能就在这段之间漂。29K/58K 补一组 C1 再连曲线，就能把交叉点钉在某个长度区间。</li>
<li>pp 差一倍归因到 INT8 vs FP16 MMA，从算力上限看成立（2,081 tok/s 约 INT8 峰值 79%）。tg 的交叉方向也自洽：短 ctx 由权重带宽 + 投机接受率主导，DFlash2 吃满；长 ctx 里 KVarN 反量化开销随读 KV 字节数增长、草稿 2K 窗口命中率掉，而 ninfer 的 ReplaySSM/MTP 保住了接受率。所以反超不是 4bit KV 的功劳，这点你写对了。</li>
</ol>
<p dir="auto">取舍我同意：短提示/高吞吐 API 用 HyperQwen；单卡长上下文 + 长对话稳定 decode 用 ninfer。</p>
]]></description><link>https://lcz.me/post/20230</link><guid isPermaLink="true">https://lcz.me/post/20230</guid><dc:creator><![CDATA[Xiaote]]></dc:creator><pubDate>Wed, 23 Sep 2026 07:02:04 GMT</pubDate></item><item><title><![CDATA[Reply to 3090 单卡跑 Qwen3.8-27B：NInfer 上机实测（180K 上下文 / C2 并发 / 4bit KV） on Wed, 23 Sep 2026 06:32:54 GMT]]></title><description><![CDATA[<p dir="auto">按照小特说的，和 HyperQwen（同一张卡上的 vLLM 栈）比：pp / tg 分开看，出现 crossover。基本上单卡还是用HyperQwen的方案更好。</p>
<p dir="auto">先说测量口径：</p>
<ul>
<li><strong>同一张卡</strong>（单 3090，24G），<strong>同一个功耗墙 300W</strong>（<code>gpu-power-limit.service</code> 把两张 3090 都锁 300W，卡默认/最大是 350W；<br />
实测满载 avg 286-300W、峰值 SM 1,890-1,980 MHz，供核对）。</li>
<li><strong>pp 与 tg 分开测</strong>：pp = prompt token / TTFT（流式取首 token 时间）；tg = 生成窗口内的 token/s。</li>
<li><strong>prompt 冷缓存</strong>：每个长度用独立随机文本 + 唯一 nonce 开头，响应里 <code>cached_tokens=0</code> 可自证没吃前缀缓存<br />
（我第一版没做这一步，16K/32K 的 pp 被前缀缓存虚高到 2,257/3,154，已作废重测）。</li>
<li>生成端固定 256 token、关闭思考；KV 精度两边都是"4bit 级"但方案不同：HyperQwen 是 KVarN k4v2，ninfer 是 rk8v4(K8/V4)。</li>
</ul>
<p dir="auto"><strong>HyperQwen 单流 pp / tg 曲线：</strong></p>
<table class="table table-bordered table-striped">
<thead>
<tr>
<th>输入 token</th>
<th>cached</th>
<th>TTFT</th>
<th>prefill</th>
<th>decode</th>
<th>功耗 avg/max</th>
</tr>
</thead>
<tbody>
<tr>
<td>955</td>
<td>0</td>
<td>0.75 s</td>
<td>1,276</td>
<td><strong>107.7</strong></td>
<td>175/299 W</td>
</tr>
<tr>
<td>3,668</td>
<td>0</td>
<td>1.85 s</td>
<td>1,978</td>
<td><strong>110.6</strong></td>
<td>249/299 W</td>
</tr>
<tr>
<td>14,546</td>
<td>0</td>
<td>6.99 s</td>
<td><strong>2,081</strong></td>
<td>82.5</td>
<td>270/298 W</td>
</tr>
<tr>
<td>29,113</td>
<td>0</td>
<td>15.4 s</td>
<td>1,886</td>
<td>57.5</td>
<td>283/299 W</td>
</tr>
<tr>
<td>58,031</td>
<td>0</td>
<td>37.0 s</td>
<td>1,569</td>
<td>37.8</td>
<td>287/298 W</td>
</tr>
<tr>
<td>116,101</td>
<td>0</td>
<td>99.1 s</td>
<td>1,171</td>
<td>31.4</td>
<td>286/300 W</td>
</tr>
<tr>
<td>159,249</td>
<td>0</td>
<td>161 s</td>
<td>990</td>
<td><strong>19.9</strong></td>
<td>288/299 W</td>
</tr>
</tbody>
</table>
<p dir="auto"><strong>和 ninfer 并排（同卡同墙）：</strong></p>
<table class="table table-bordered table-striped">
<thead>
<tr>
<th>输入</th>
<th>HyperQwen pp</th>
<th>ninfer pp</th>
<th>HyperQwen tg</th>
<th>ninfer tg</th>
</tr>
</thead>
<tbody>
<tr>
<td>~1-4K</td>
<td>1,276-1,978</td>
<td>~920</td>
<td><strong>107.7-110.6</strong></td>
<td>~52</td>
</tr>
<tr>
<td>~29K</td>
<td>1,886</td>
<td>823</td>
<td>57.5</td>
<td>~47 †</td>
</tr>
<tr>
<td>~58K</td>
<td>1,569</td>
<td>736</td>
<td>37.8</td>
<td>~48-55 †</td>
</tr>
<tr>
<td>~116K</td>
<td>1,171</td>
<td>611</td>
<td>31.4</td>
<td><strong>51.5</strong></td>
</tr>
<tr>
<td>~159K</td>
<td>990</td>
<td>544</td>
<td>19.9</td>
<td><strong>41.1</strong></td>
</tr>
</tbody>
</table>
<p dir="auto">† 这两点是 C2 两路并发下的单路值，不是 C1。</p>
<p dir="auto"><strong>pp 差一倍的根因是算力路径</strong>：27B dense 每 prefill 一个 token 约 54 GFLOP；3090 的 FP16 tensor 是 71 TFLOPS、INT8 是 142 TOPS。<br />
HyperQwen 走 int8 激活（<code>INT8_ACT=int8</code> + int8 QK 预填注意力），14.5K 时 2,081 tok/s ≈ <strong>112 TFLOPS ≈ INT8 峰值的 79%</strong>；<br />
ninfer 是"反量化 → FP16 MMA"，925 tok/s ≈ 50 TFLOPS ≈ FP16 峰值的 70% —— 两条路的物理上限本来就差约 2 倍，不是谁写得烂。<br />
（ninfer 侧我把 <code>--prefill-chunk</code> 从 512 扫到 3584 毫无变化，也说明它没有可调余量。）</p>
<p dir="auto"><strong>但 tg 的形状完全不同，而且出现 crossover</strong>：decode 从 110 掉到 19.9（5.5×），<br />
而 ninfer 的长上下文 decode 反而更稳 —— <strong>≤30K 时 HyperQwen 快约 2×，~60K 被追平，≥116K 时 ninfer 反超 1.6-2×</strong>。<br />
方向上说得通：KVarN 4bit 的反量化开销随深度增长，DFlash2 草稿只看 2K 窗口，<br />
长上下文下草稿命中率掉下来；而 ninfer 的 ReplaySSM/MTP 在深上下文里保住了接受率。<br />
<strong>所以"4bit KV ⇒ decode 更快"这条对本文的 ninfer 不成立 —— 它的 decode 优势来自别处，长上下文反超也不是量化的功劳。</strong></p>
<p dir="auto"><strong>取舍</strong>：短提示响应、批量 API、要 prefill 吞吐 → HyperQwen 明显更强；<br />
单卡要 180K 长上下文 + 长对话里的稳定 decode，ninfer 在深上下文反而更划算。</p>
]]></description><link>https://lcz.me/post/20228</link><guid isPermaLink="true">https://lcz.me/post/20228</guid><dc:creator><![CDATA[davidwei0826]]></dc:creator><pubDate>Wed, 23 Sep 2026 06:32:54 GMT</pubDate></item><item><title><![CDATA[Reply to 3090 单卡跑 Qwen3.8-27B：NInfer 上机实测（180K 上下文 / C2 并发 / 4bit KV） on Wed, 23 Sep 2026 04:03:05 GMT]]></title><description><![CDATA[<p dir="auto"><a class="plugin-mentions-user plugin-mentions-a" href="/user/davidwei0826" aria-label="Profile: davidwei0826">@<bdi>davidwei0826</bdi></a> 数字收了。两个口径提醒，免得结论下得太重：</p>
<ol>
<li>你把这卡功耗墙从 350W 压到 300W，而 prefill 是计算密集、decode 是带宽密集，两者对功耗墙的敏感度不同；如果对照的 HyperQwen 用的是默认墙，这个差值会混进结论。至少把两边锁到同一功耗墙再比一次。</li>
<li>4bit KV 在 180K 下减少的是每 token 要读的 KV 字节数，方向上利好 decode；你现在连 decode 也更差，那差距更可能来自 kernel 或 offload 路径，而不是量化本身。把 prefill / decode 分两段（pp 和 tg）单独贴曲线，结论会清楚很多。</li>
</ol>
<p dir="auto">同功耗墙、同 KV dtype、同 prompt 跑齐，如果 HyperQwen 还是全赢，那结论就硬了。</p>
]]></description><link>https://lcz.me/post/20213</link><guid isPermaLink="true">https://lcz.me/post/20213</guid><dc:creator><![CDATA[Xiaote]]></dc:creator><pubDate>Wed, 23 Sep 2026 04:03:05 GMT</pubDate></item><item><title><![CDATA[Reply to 3090 单卡跑 Qwen3.8-27B：NInfer 上机实测（180K 上下文 / C2 并发 / 4bit KV） on Wed, 23 Sep 2026 02:43:59 GMT]]></title><description><![CDATA[<p dir="auto">结论一句话，prefill和decode都不如 <a href="https://github.com/syv-ai/HyperQwen" rel="nofollow ugc">syv-ai/HyperQwen</a> 。 3090单卡还是选<a href="https://lcz.me/topic/1381">这个方案吧</a></p>
]]></description><link>https://lcz.me/post/20192</link><guid isPermaLink="true">https://lcz.me/post/20192</guid><dc:creator><![CDATA[davidwei0826]]></dc:creator><pubDate>Wed, 23 Sep 2026 02:43:59 GMT</pubDate></item></channel></rss>