第七章:CUDA 豪賭與遊戲玩家的「R&D 稅」
2026 年春天,一個剛拿到碩士學位的機器學習工程師,正在為他的第一份工作做技術選型。任務很簡單:訓練一個中等規模的語言模型。他打開 PyTorch,寫了幾行程式碼,呼叫了 torch.cuda.is_available(),確認 GPU 在線,然後開始訓練。
他沒有想過那行程式碼底下發生了什麼。
PyTorch 呼叫了 cuDNN——NVIDIA 的深度神 經網路加速函式庫。cuDNN 呼叫了 cuBLAS——NVIDIA 的線性代數函式庫。cuBLAS 編譯成 PTX 中間碼,再被 NVIDIA 驅動程式即時翻譯成 SASS——那張 GPU 的原生機器指令。整條管線從第一行 Python 到最後一個電晶體的開關,每一層都印著同一個商標。
他的主管說:「公司預算吃緊,AMD 的 GPU 便宜四成。能不能換?」
他試了。把 torch.cuda 改成 torch.hip。第一個錯誤出現在 cuDNN 的某個卷積核心——AMD 的對應物 MIOpen 不支援那個特定的資料排列格式。他繞過去了。第二個錯誤出現在多 GPU 通訊——NVIDIA 的 NCCL 函式庫在 AMD 上沒有對等品,AMD 自己的 RCCL 效能差一截,某些拓撲下直接掛掉。他花了三天追蹤問題,發現是驅動程式層的一個 race condition,AMD 的 ROCm 團隊在 GitHub 上標記為「已知問題,預計下一版修復」。
兩週後,他跟主管說:「換不了。」
他把這件事當成一個工程問題——AMD 的軟體還不夠成熟,再等兩年或許就好了。
不是。
AMD 的 ROCm 不是「還不夠成熟」。它已經追了十年,依然追不上。不是因為 AMD 的工程師比 NVIDIA 的差,是因為他們面對的不是一道鎖,是一座四層深的監獄。而你——每一個用 PyTorch 訓練過模型的人——從讀碩士的第一天起,就住在裡面。
上一章講了一道鎖怎麼被撬開。DirectX 鎖了 PC 遊戲三十年,Valve 用 Proton 把它繞過去了。讀完那一章,你可能覺得:鎖都能撬開,只要有人夠執著。
這一章要打碎那個幻覺。
I. 作案動機
2003 年,一個叫 Ian Buck 的史丹佛大學博士生,發表了一樣 東西。不是一張顯示卡,不是一款遊戲——是一個程式語言。
它叫 Brook。
Buck 在史丹佛圖形實驗室裡觀察到一個事實:GPU 裡面有幾百個小核心,每一個都能做浮點運算,合起來的算力遠超當時最快的 CPU。但這些核心只認得繪圖 API——它們被硬體設計綁死在「畫像素」這一件事上。如果能把它們拿來算別的東西——矩陣乘法、物理模擬、蛋白質摺疊——那會怎樣?
Brook 就是他給出的答案:一個讓程式設計師用類似 C 的語法,把通用運算任務丟到 GPU 上面跑的語言。概念很漂亮,但有一個致命問題:Brook 必須把所有運算任務偽裝成圖形渲染指令——因為當時的 GPU 硬體只認得繪圖 API。你想算一個矩陣乘法?你得先假裝它是一塊三角形的紋理,然後用 OpenGL 的 shader 去「渲染」它。效率低,限制多,能做的事少。
Buck 靠 Brook 拿了學位。然後黃仁勳親自邀請他加入 NVIDIA。
2004 年,Buck 進了 NVIDIA。黃仁勳看了 Buck 的研究,看到的不是一篇學術報告——他看到的是一條縫。GPU 裡面有幾百個小核心,每一個都能做浮點運算,但硬體設計強迫它們只能畫圖。如果把這個限制拿掉——讓那些核心可以做任何運算——GPU 就會從一張繪圖卡變成一台超級電腦。
但拿掉限制的代價很大。它意味著重新設計 GPU 的整個架構:指令集要改、記憶體模型要改、執行緒排程器要改。而這些改動不會讓遊戲跑得更快——遊戲只需要畫圖,不需要通用運算。換句話說,改了之後,遊戲玩家拿不到任何好處,但 NVIDIA 要為這些改動付出巨額的研發成本。
黃仁勳讓 Buck 帶一支團隊,把 Brook 的概念直接燒進下一代 GPU 的硬體裡。不是用軟體模擬,不是用 shader hack——是在矽晶片上刻出真正的通用運算單元,讓每一個 核心都能執行任意的 C 語言程式碼。
2006 年 11 月 8 日,GeForce 8800 GTX 上市。代號 G80。599 美元。128 個串流處理器,6.81 億個電晶體,90 奈米製程。
遊戲玩家看到的是:史上第一張支援 DirectX 10 的顯示卡,畫質的跳躍讓人目瞪口呆。
遊戲玩家沒看到的是:那 128 個串流處理器裡面,每一個都被重新設計過——它們不只能算像素,還能算任何東西。矩陣乘法、傅立葉轉換、流體力學模擬、分子動力學——只要你能寫成並行程式碼的問題,都可以丟上去。
七個月後,2007 年 6 月 26 日,NVIDIA 發佈 CUDA Toolkit 1.0——一套讓程式設計師直接用 C 語言在 GPU 上寫通用運算程式的開發工具。
沒有玩家注意到。沒有遊戲媒體報導。對 99% 的 GeForce 8800 GTX 用戶來說,CUDA 是一個不存在的東西。他們花 599 美元買了一張顯示卡,為的是玩遊戲,不是跑科學計算。
但他們的 599 美元裡面,有一部分被拿去分攤了通用運算核心的研發成本。
每一張賣出去的 GeForce,都內建了玩家用不到但科研界日後會用到的硬體。NVIDIA 沒有跟任何人解釋這件事。它不需要。它只需要繼續賣遊戲顯示卡——賣得越多,通用運算的研發成本被攤得越薄,風險就越低。
間章定義過一種人——看得穿硬體指令集、軟體 API、以及上層應用三個層次之間接縫的人。黃仁勳就是這種人的原型。他看得見 GPU 繪圖核心跟通用運算之間的那條縫。他下的賭注是:先讓遊戲玩家幫我養這條縫,等有一天,有人會來認領。
但這裡要停下來問一個問題:NVIDIA 不是 Valve。
上一章特別指出,Valve 能扛住 Steam Machine 失敗後繼續投資 Linux,是因為它是私人公司——沒有股東、沒有華爾街分析師每季度問你 ROI 在哪裡。但 NVIDIA 在 1999 年 1 月 就已經上市了。它是一家 NASDAQ 掛牌的公眾公司。CUDA 的研發成本讓 NVIDIA 的市值從大約 80 億美元跌到不足 15 億美元。華爾街的反應不是質疑,是沉默——那是比質疑更可怕的東西。
黃仁勳憑什麼扛得住?
答案,要從第四章埋下的一條線說起。
第四章的結尾講過:NVIDIA 在 2001 年為初代 Xbox 供應了 GPU——代號 NV2A,基於 GeForce 3 架構。那是 NVIDIA 第一次嘗到主機市場的味道。味道很苦。微軟在合約裡鎖死了晶片價格,要求 NVIDIA 逐年降價。黃仁勳拒絕。雙方的關係從冷淡到仲裁,最終在 2003 年 2 月和解。但和解不是和好。2003 年 8 月,微軟宣佈 Xbox 360 的 GPU 改用 ATI。
NVIDIA 被踢出了客廳。
從商業教科書的角度看,這是一場失敗。主機 GPU 是一條長達七到十年的穩定訂單管線——第八章會展開這一點。失去微軟這個客戶,等於失去一條幾千萬台出貨量的長期飯票。
但事後看,被踢出去,是黃仁勳職業生涯裡發生過的最好的事。
原因有三。
第一,主機 GPU 是一份吃力不討好的差事。 主機廠要求你把晶片做成半客製化的 SoC,塞進它們設計的機殼裡,按照它們的散熱預算跑,然後年年降價。你的頂級工程師不是在追求下一代架構的突破——他們在替微軟省成本。如果 NVIDIA 還在做 Xbox 360 的 GPU,2004 到 2006 年那些本該設計 CUDA 核心的工程師,很可能被鎖在為微軟壓縮成本的苦差事上。
第二,PC 顯示卡的利潤結構,比主機 GPU 好得不是一個等級。 微軟嫌一顆主機晶片幾十美元太貴。但 PC 玩家願意花 599 美元買一張 GeForce 8800 GTX——那是主機 GPU 單價的十幾倍。微軟不肯給的利潤,遊戲玩家雙手奉上。這些利潤,就是 CUDA 燒了十年而 NVIDIA 不會倒閉的真正原因。黃仁勳把 CUDA 的研發成本藏在每一張 GeForce 的毛利裡——玩家看不見,華爾街也不夠懂硬體設計,不知道那些「通用運算核心」是遊戲玩家用不到的東西。「R&D 稅」不只是一個比喻。它是黃仁勳瞞天過海的財務手段。
第三,失去客廳,迫使黃仁勳去想一個他本來不需要問的問題:GPU 除了畫遊戲,還能做什麼? 如果 NVIDIA 還有微軟的長期飯票,這個問題可能永遠不會被認真對待。但飯票沒了。黃仁勳必須為 GPU 找到遊戲以外的第二條命。Ian Buck 的 Brook,就是那條命的起點。
這裡有一個諷刺到令人窒息的迴旋。
2002 年,微軟為了在每顆 Xbox 晶片上省幾美元的成本,跟 NVIDIA 鬧翻。那幾美元乘以幾千萬台 Xbox,大約是幾億美元的爭議。微軟覺得自己贏了——用更便宜的 ATI 晶片做了 Xbox 360,賣得比初代好。
二十年後,2023 年,微軟向 NVIDIA 下了一筆訂單。不是幾億美元——是幾十億美元。幾萬張 H100 和後續的 B200,用來訓練它投資了一百三十億美元的 OpenAI 的大型語言模型。每一張卡的售價,是當年那顆 Xbox GPU 成本的幾百倍。
當年微軟嫌貴踢走 NVIDIA 省下的那筆錢,如今連本帶利,全部嘔了回來。而且是跪著嘔的——因為 CUDA 的四層鎖意味著,微軟就算想換供應商,也換不了。
微軟是 CUDA 壟斷的間接催生者。 它踢走了 NVIDIA,逼黃仁勳退回 PC,退回 PC 讓 NVIDIA 賺到養 CUDA 的利潤,CUDA 長成了四層深的監獄,而微軟自己,成了這座監獄裡最大的一個囚犯。
這個「有一天」,他等了六年。