Guidant AI 資安檢視 · 模組報告

弱點檢測整合(jedi-detection)

客戶買了「弱點掃描」之後,這塊負責保管掃描工具的帳號密碼、收下客戶上傳的檢測規則包、把掃描任務派到客戶機房。這塊是全案最後收口的一塊,2026-09-20 查完——找到兩條高風險,其中一條是「客戶上傳的規則包會被我們的伺服器當成程式碼執行」。

🔴 這一頁查完了,但「查完」不等於「查得乾淨」

這塊是全案最後收口的一塊,2026-09-17 開始、2026-09-20 結束,總共分成 14 批查。

為什麼要分這麼多批:這塊的程式量大,而且一次交太多檔案給檢視工具,工具會中途把人砍掉、什麼都沒產出。所以一路往下切,切到每一批只剩幾個檔案為止。

這 14 批裡有 4 批是在跟工具搏鬥,不是在查程式——一批打了 17 小時、換 25 次人、零產出,一批的完成紀錄被誤刪,一批換了四次人,一批派三位只回來一位。這些不是要藏起來的難堪,是全站在 2026-09-20 決定止損的依據(見總報告首頁):工具不穩到這個程度,繼續往下掃拿不回相稱的東西,所以整輪改成「針對已經發現的修」。細節寫在下面的軌跡表底下。

所以這一頁該這樣讀:下面列的每一條都是查證過、可以拿去排工單的;但**「這 14 批裡沒再找到別的」不等於「這塊已經沒有問題」**——我們的方法能證明「找到了什麼」,不能證明「沒有別的」。

§1

這塊在產品裡做什麼

客戶買了「弱點掃描」功能之後,他可以在產品裡對自己機房的主機做資安檢測——掃有沒有沒修的漏洞、設定有沒有照規範設好。

要做到這件事,這塊要處理四件事,每一件都碰到高風險的東西:

它平常在做什麼

  1. 保管客戶的掃描工具帳號密碼(SonarQube、OpenVAS、ZAP 這些工具的存取權杖,還有連主機用的 SSH、Windows 遠端管理帳密)
  2. 收下客戶上傳的「檢測規則包」——一包壓縮檔,裡面是「要檢查哪些項目」的規則
  3. 把掃描任務派給裝在客戶機房的代理程式,並把帳密一起帶過去
  4. 把掃描報告收回來,存成稽核證據

為什麼它是敏感目標

這塊同時碰到四件高風險的事:

  • 手上有客戶主機的明文帳號密碼
  • 要解開客戶上傳的壓縮檔
  • 要代替客戶去抓外部網址
  • 要執行外部程式來解析規則包

前面提過的「不用登入就能取走客戶帳密」那條攻擊鏈,終點就在這裡——帳密解密之後放進派工單的那一行。


§2

檢視軌跡

檢視期間:2026-09-17 ~ 2026-09-23(已收口)|範圍:模組本體正式程式碼 160 個檔案,扣掉另一條線已查過的 11 個、以及 66 個沒有邏輯的檔案(空殼、純資料結構、離線小工具),實際檢視 83 個;另加我們主系統這一端的接線 12 個|共 15 批(模組本體 14 批+主系統接線 1 批)

⚠️ 模組本身那 83 個檔案、以及我們主系統這一端的 12 個接線檔都查完了。接線那一批的原始報告放在 FR-115 站(五支模組的接線放在同一個站)。

⚠️ 下表 13 列,但上面說 14 批——差的那一批是 D2-2:它打了 17 小時、一條都沒產出,後來整批重切重跑。它沒有結果可以列,所以不進表,只寫在表底下的誠實交代裡。

原始技術報告放在需求中心的 FR-108 站,檔名見下表最後一欄。那裡有每一批的完整技術細節、檔案清單與逐條推理,供需要深究或稽核抽查時查閱。

批次 查什麼 檔數 覆核投票 結果 原始報告檔名
D1 工具名錄、客戶帳密怎麼存、「測試連線」怎麼運作 36 18 票全投完(⚠️ 完成證明遺失,見下) 找到 4 條(1 高 3 中) scan-D1-tools-credentials
D3-1 代理程式回報結果、報告檔怎麼存成證據 4 9 票全投完 找到 1 條中 scan-D3-1-result-collection
D3-2 派工時「要掃哪些機器」怎麼被綁定 5 6 票全投完 找到 1 條中 scan-D3-2-job-binding
D3-3 執行狀態怎麼流轉、查詢入口 11 3 票全投完 這一批沒有新問題(工具唯一報的那條是已知舊帳) scan-D3-3-state-machine
D3-4a 派工/取消/刪除 1 9 票全投完 找到 1 條中 scan-D3-4a-orchestration-dispatch
D3-4b 回收/狀態/排程 1 9 票全投完 淨新增 0,三條全是舊帳;但把另一條舊問題的影響面擴大了 scan-D3-4b-orchestration-collect
D2-1b 上傳的壓縮檔怎麼驗 2 6 票全投完 找到 1 條中,並推翻了工作單的一項前提 scan-D2-1b-archive-validation
D2-1a 規則包上傳入口的守門 3 6 票全投完,零駁回 找到 2 條中(⚠️ 這一批跑得很不順,見下) scan-D2-1a-upload-route
D2-3 規則包怎麼解析、怎麼去外部抓 4 6 票全投完,零駁回 🔴 找到 2 條,其中一條是本塊第二條高風險 scan-D2-3-extraction-fetch
D2-2a 掃描基準的主要邏輯 1 3 票全投完,零駁回 找到 1 條中(另帶出兩條體質項) scan-D2-2a-profile-service
D2-4a 分類字典的完整路徑 8 一個疑點都沒提 範圍內沒有找到問題(另記一條體質項) scan-D2-4a-taxonomy-chain
D2-2b 掃描基準的資料存取層 4 一個疑點都沒提 範圍內沒有找到問題(另記一條體質項) scan-D2-2b-profile-domain-repo
D2-4b 版本存取層、規則清單表、掃描範圍的寫法 8 1 條提出、3 票全投完 淨新增 0——唯一提出的那條與第 11 條是同一條問題鏈(⚠️ 這一批跑得很不順,見下) scan-D2-4b-version-repo
W3(主系統接線) 我們主系統這一端怎麼把這塊接上來:設定、上傳入口、派工與權限檢查 12 一個疑點都沒提(完成證明齊全) 範圍內沒有新問題;執行者自己開檔另查出 1 條非資安的設定問題(見下方體質問題最後一列),並替第 7 條加了一個驗收項 scan-W3(在 FR-115 站)

四件跑不順的事——這就是我們決定止損的依據

下面四件不是「做得不順要老實承認」而已。它們是 2026-09-20 那個決定的證據:全站在這一天判斷「檢視工具本身不可靠,繼續投入不划算」,改成針對已經發現的修(見總報告首頁)。這一塊剛好把工具的不穩定度量得最清楚,所以細節列在這裡。

一、第一批(D1)的完成證明拿不出來。 產物資料夾被另一個被中斷的檢視程序誤刪了(不是同時跑太多造成的)。統籌者改從工作流程的結果檔獨立核完——6 個疑點、18 票全投、零漏投零中斷零降級。證據鏈補得起來,但那份完成紀錄確實沒了。

二、有一批(D2-2)打了 17 小時、換了 25 次人,一條都沒產出。 統籌者逐份看過那 25 份紀錄:22 份只寫了開頭一句就被中斷、3 份寫到一半。根因是工具自身的一個已知缺陷(上游還沒修),不是內容太難。後來把它拆成兩小批重跑,兩批都順利完成。

三、有一批(D2-1a)跑得很不順——換了四次人,前三次都被誤中斷,耗時 9 小時 22 分。那一批的完成紀錄只能證明「被提出的兩條投票完整」,不能證明「三個檔案被徹底讀過」。

四、最後一批(D2-4b)也不順——派了三位、只有一位跑完,前兩位被工具自身的一個自動壓縮機制誤砍(與第二點是同一個上游缺陷),整批耗時 4 小時 53 分。那位跑完的人交出的紀錄是完整的(提出 1 條、三票全投完、統籌者另把工作單列的三個重點逐項開檔查證),但另外兩位讀到哪裡,沒有紀錄可以還原。

把這四件擺在一起看:14 批裡有 4 批的成本花在「讓工具跑完」而不是「查程式」,其中最糟的一批投了 17 小時、拿回零條。這個比例就是繼續投入不划算的理由——不是我們怕麻煩,是同樣的時間放到修正那一側,拿得回的東西明確得多。

兩批「零發現」是有份量的零,不是空手而歸

其中兩批(D2-4a、D2-2b)一個疑點都沒提出來。這種情形要分兩種看:

  • 一種是「沒讀就被中斷」(像上面那 25 位)
  • 另一種是「讀完了、逐條交代每個懷疑過的地方為什麼不成立」

這兩批是後者。 而且統籌者把工作單列的重點逐項開檔查證、連開發環境核對資料庫規則與連線帳號權限,全部乾淨。最後一批(D2-4b)雖然提出了一條,但那條查下來與第 11 條是同一條問題鏈——由兩組不同的人、用不同的切法各自獨立撞到同一件事,反而讓第 11 條更站得住腳。

判準是看紀錄裡有沒有「結論」這個事件——「零條」有兩種,可信度天差地別。


§3

問題一覽

排序按風險,同風險的同一類排在一起。「出事會怎樣」那欄講的是業務影響——誰受影響、損失什麼,不是技術現象。

⚠️ 表裡有 14 列,但「這塊自己找到的」是前 13 條(2 條高風險、10 條中風險、1 條低風險)。

⚠️ 第 8 條重新定性後已從中風險調降為低風險(原因寫在那一列)。表格原則上按風險排序,但第 8 條保留在原位置沒有往下移,因為報告其他地方與工單都用「第 8 條」這個編號在指它,移動會對不上。

⚠️ 第 14 條不是這塊的新發現,是別的模組早就登記過的一個問題,這次查出它的波及範圍也涵蓋到這塊——條數不重複計算,但修的時候不能漏掉這塊。詳見該列與下方結論第 7 點。

# 問題 風險 分類 出事會怎樣(誰受影響) 怎麼修 狀態
1 🔴 客戶上傳的檢測規則包會被外部工具當成程式碼直接執行 🟠 高 外部送什麼就收什麼 拿到的是我們後端主機的全部權限——一整批系統密鑰(含用來簽發登入憑證的那一把,拿到就能冒充任何人登入,另有代理程式的憑證私鑰、檢測工具的加密金鑰與一整排外部服務的通行證)、一個能自行把自己提權成超級管理員的資料庫身分(提權之後讀寫全部客戶的資料)、檔案儲存與代理程式的憑證,以及跳進內網的能力。一個客戶的管理員就能打下整台主機與全平台資料 重新打包之前先讀一次規則包裡的設定檔,看到程式樣板標記就拒收;要放在打包那一步本身,只補上傳那條路會漏掉網址那條。實際做法:解析前先讀 inspec.yml,含 <% 樣板記號直接拒收(只擋這一個檔,見打折說明) ✅ 已修(CM-2057)
2 🔴 「測試連線」按鈕沒有檢查權限,只要能登入就能按——按下去系統會把掃描工具的帳密解密,送到按的人自己指定的那台主機 🟠 高 只驗登入、不檢查歸屬 一次拿走整家公司的維運帳密——送出去的是連主機用的 SSH/Windows 遠端管理密碼,以及三套掃描工具的存取權杖。這是漏掉不是刻意:同一支檔案裡的新增、修改、重置每一支都有檢查權限,真正的缺口只有「測試連線」這一支(同樣沒掛的「查引用次數」是純查詢、不解密、不對外連線,沒掛是合理的)。⚠️ 既然第 6 條裁定不限制連到哪裡,這道權限檢查就是唯一的防線 補一行權限宣告,同一支檔案裡有三處現成寫法可以照抄 ✅ 已修(CM-2042)
3 網址型規則來源完全繞過壓縮檔的檢查 🟡 中 外部送什麼就收什麼 防壓縮檔炸彈的三道上限(檔案數/大小/膨脹倍數)只接在「上傳檔案」那條路上;改填一個網址,下載回來直接解開,三道上限一道都不會碰到。45MB 的檔案解開成數十 GB 完全做得到,伺服器記憶體被吃爆、所有客戶一起停擺 把檢查改放到解析那一層,讓現有與未來的第三種來源天然都涵蓋。實際做法:三道上限下沉到上傳與網址共用的 _read_entries(),不在網址分支補第二套 ✅ 已修(CM-2057)
4 上傳規則包的「最多一萬個檔」上限,對 .zip 格式形同虛設 🟡 中 資源耗盡 上限要等檔案清單全部展開進記憶體之後才開始數——數到第一萬零一個才喊停時,記憶體早就吃掉了。實測:一個 49.7MB、裝 59.5 萬個空檔的壓縮檔,光打開就多吃 360MB 記憶體,連送幾次就能把伺服器打到停擺。最難察覺的是日誌看起來一切正常(照樣回報「壓縮檔不安全」),但代價已經付掉了 打開之前先讀壓縮檔檔尾的目錄筆數、超量直接擋;並且改掉那段寫反的說明文字。實際做法:打開 zip 前先讀檔尾 EOCD 筆數欄位擋量,並改掉寫反的註解 ✅ 已修(CM-2057)
5 填網址建立掃描基準時系統放行沒加密的連線,而且網址型來源完全不記指紋 🟡 中 外部送什麼就收什麼 代理程式住在客戶內網、手上有主機帳密,它拿到網址後直接下載並執行裡面的規則。路徑上任何能動手腳的人換掉那包檔案,就等於在代理程式裡跑自己的程式碼,掃描報告也跟著造假。沒有加密要破解,因為根本沒有加密——而我們後端自己的下載器只准加密連線,同一個系統兩套標準 只收加密連線;第一次解析成功時記下檔案指紋並讓代理程式對帳(上傳那條路本來就這樣做,網址這條只是沒補上)。實際做法:新登記只收 https、既有 http 留警告日誌、網址型落 sha256 並下發給代理程式對帳 ✅ 已修(CM-2057)
6 「測試連線」要連到哪台主機,是呼叫者在請求裡直接指定的 🟡 中 外部送什麼就收什麼 客戶內網裡的代理程式因此變成「只要登入就能用的任意連線跳板」——回應訊息的差異(連得上/連不上/逾時)還能拿來一台一台探測客戶內網有哪些機器開著哪些服務。⚠️ 與第 2 條是同一個入口上的兩個獨立問題:第 2 條是「誰可以按」,這條是「按下去可以打到哪」 不限制可以連到哪裡(已裁定不做目標白名單——掃描目標是客戶自己的主機、帳號也是客戶提供的,哪台算合法目標該由客戶自己管)。改做三件:① 限制單次可帶的主機數量,擋的是「一個請求帶一萬台就變成內網掃描器」;② 回應收斂成單純的成功/失敗,擋的是「用連得上/連不上/逾時的差異一台一台探測」;③ 日誌要記誰按的、連到哪一台、用了哪一組設定——只記「有人按了測試連線」追不到事。實際做法:主機數上限+回應收斂+稽核 log ✅ 已修(CM-2058)
7 資料庫的客戶隔離規則方向寫反了 🟡 中 客戶資料沒隔開 子單位的人看得到母單位的資料(還能改、能刪),母單位反而看不到自己底下子單位的資料——隔離該擋的沒擋、不該擋的擋了,資安與功能兩面同時出錯。同樣的寫法在出貨基線裡共有 11 條(本塊五張表、遠端代理程式一張、授權三張,再加合規文件匯入那塊的兩張),只改這五張等於沒修。⚠️ 合規文件匯入那兩張是第三種寫法、比另外九條更寬鬆——它用的是純文字包含比對,單位編號 1 會命中任何含有 1 的路徑;而且它拿單位編號去跟使用者編號比對,這兩者根本不是同一種東西。用同一個關鍵字搜尋找不到它們,要單獨處理。跟第 2 條疊起來更糟:子單位成員可以對母單位登記的工具按「測試連線」,把母單位的帳密送到自己的主機 🔴 11 條要分兩組改,不是全部照同一套:8 張改用同一個檔案裡已經在用的正確寫法;授權那 3 張(授權檔、授權異動紀錄、停權紀錄)「看」要保持現狀、只擋「改」和「刪」——那三張絕對不可以照另外八張的做法改,改了每個子單位都會查不到頭上那張授權,被判成「沒買」,打任何功能都會被擋掉(原因見授權管理那塊)。應用層也要補上客戶條件。已裁定集中處理:與其他修正工單一起做,不為此單獨重新產生出貨基線(產品還沒出貨,「新裝客戶拿到錯的」目前不存在;11 條分批改等於改兩次驗兩次,漏一張就白做)。🔴 但出貨前必須完成——第一個客戶裝機那一刻,代價就從零變成實質。🔴 施工時逐條比對、不要批次取代:這些跟基線裡上百條正確的混在同一個檔案,批次取代會把對的一起改壞 ⬜ 未修,歸 1.21.1 hotfix(CM-2289)
8 權限矩陣騙了管理員——取消勾選後前端選單藏起來了,後端八支讀取功能照樣回全部 ⚪ 低 只驗登入、不檢查歸屬 ⚠️ 這條原本評中風險,重新定性後調降為低。 原本的寫法會讓人以為「任何登入者都拿得到」,但這個功能本來就只開給租戶管理員使用,拿得到的人本來就拿得到。真正的問題是管理員被騙了:他在權限矩陣裡取消勾選,前端選單確實藏起來,但該帳號直接對系統送請求,後端八支讀取功能(基準清單、下拉選單、單筆詳情、版本歷史、主檔使用狀況、版本使用狀況、規則清單、抽取狀態)一支都沒檢查,照樣回全部。也就是說那一格勾選其實不生效 八支讀取功能補掛權限檢查,並保留那顆權限點以維持未來細分的彈性(例如日後讓稽核人員「看得到但改不了」)。🔴 補的時候要一併把程式裡那句「讀取端刻意不掛」的說明文字改掉,否則下一個人看到又會當成設計、把它拿掉。🔴 這個功能有公版機制,不要改壞——看得到哪些資料是三種用「或」連起來(公版人人看得到+自己建的+上游分享下來的),補權限是加在「能不能進這個功能」那一層,不動「看得到哪些」那一層;補完要驗四件事:管理員看得到公版、看得到自己的、下游看得到上游分享的、沒勾權限的被擋掉。「改壞」的長相是「有些本來看得到的人突然看不到了」 ✅ 已修(CM-2042)
9 按下「開始掃描」時,解密後的客戶主機帳密會多存一份明文進派工資料表 🟡 中 密碼外流 那份存下來的從頭到尾沒有任何程式讀過——代理程式拿到的是另一份當場重新解密的。等於產品刻意做的加密保護被這一行繞過:拿到資料庫備份或唯讀帳號的人,一句查詢就得到客戶正式機房的可用主機密碼與掃描器管理員權杖。而且這張表沒有任何清理機制,每掃一次就多留一份、無限累積 刪掉那一行寫入,再補一支清掉存量的腳本(已確認刪掉不影響代理程式)——已刪除 _dispatch_one() 裡寫入明文的那一行,正常派工與「立即重新指派/重跑」兩條路徑共用同一函式,一次刪除兩條路都修好;DEV 查過既有殘留資料筆數為 0,無需補清理 ✅ 已修(FR-114.4-3)
10 手動重新解析功能無條件開一條背景工作,可以把主機打掛 🟡 中 資源耗盡 每收一次請求就開一條背景工作、把最大 50MB 的檔整包讀進記憶體、再開一支最長 15 分鐘的外部程式,沒有同時執行上限、也不檢查這一版是不是已經在跑——連打幾百次就是幾百條同時存在,同一台機器上所有客戶一起變慢 加「同一版已在跑就拒絕」的判斷+總量上限。⚠️ 不只是「加一個判斷」而已——手動重新解析目前會主動把狀態壓回「等待中」再排(當初這樣寫是怕前端看到舊的失敗狀態、以為按了沒反應)。這個壓回的動作要一起處理,否則新加的判斷永遠看到「等待中」、擋不到任何東西。修改範圍比表面上大。實際做法:同版去重+同時上限 4+排隊上限 ✅ 已修(CM-2058)
11 換掃描工具時,「要掃哪些機器」不會拿實際生效的值重新檢查台數上限 🟡 中 外部送什麼就收什麼 先綁一支不設台數上限的工具、把範圍填成一個超大網段;再送第二次只換工具不帶範圍——舊的超大範圍就原封不動留著跟到新工具底下。按下執行時系統會把網段逐台展開,一個大網段展開是 1,677 萬台,記憶體瞬間吃爆、服務當掉。統籌者驗收時另外查到同一個洞的第二個發生點 用「這次更新完成後實際會生效的值」重新檢查;展開網段前先加一道很寬鬆的總數上限當保險。實際做法:用生效值重驗+展開端絕對上限 65536 ✅ 已修(CM-2058)
12 查掃描執行紀錄少了「你是不是這個專案的人」這道檢查 🟡 中 只驗登入、不檢查歸屬 同一家客戶裡任何成員知道任務編號,就讀得到別人專案的掃描歷史。同一個服務裡另外八個吃任務編號的功能每一個都先做了這道檢查,只有這一支漏掉 補上同一個服務裡其他八處已經在用的那行檢查;任務不存在時回報找不到,不要回空清單 ✅ 已修(CM-2040)
13 **代理程式回報報告時「檔名叫什麼就存什麼」 🟡 中 外部送什麼就收什麼 不去掉路徑、也不驗副檔名。稽核人員在畫面上點開預覽時,網頁格式的檔案會被瀏覽器當成網頁執行——那段程式是用稽核人員本人的身分在跑,可以冒用他做任何事。而網頁格式正是掃描報告的正式格式,這是日常路徑不是罕見情境。⚠️ 要走到危險的那個動作得多轉一手:在「執行歷史」那一區點掃描報告是下載**(強制存檔、不會在頁面裡開,那條是安全的);危險的預覽要從證據清單那邊點。掃描報告收回來時會同時寫一筆證據,所以這條路是通的 存檔前先去掉路徑、再比對副檔名白名單;更保險的做法是一律自己命名。實際做法:報告檔名一律去路徑+查副檔名白名單,不合規退回系統自產名,中文檔名保留 ✅ 已修(CM-2062)
14
⚠️ 不計入本塊條數
只能看、沒有待辦任務的「唯讀角色」,其實可以對客戶的正式機器發動帶帳密的掃描
**(這條是「稽核流程」那塊已登記問題的波及範圍,不是本塊的新發現)
🟡 中 只驗登入、不檢查歸屬 這一塊有八支會改狀態的功能(開始掃描、取消、重跑、刪紀錄等)吃的是同一道「任一角色都放行」的守門**。決策者已裁定唯讀角色不該能動別人的任務——已修:八支全數改接嚴格守門,只有該任務的被指派人或專案 manager 能操作 補「呼叫者是不是這個任務的負責人、或這個專案的管理者」這道檢查,範圍涵蓋這八支——流程那邊的嚴格守門已做好(FR-114.1-1,common/authz/ 的 assert_workflow_job_operator);套件側八處呼叫點已改接 WorkflowExecutionService.assert_job_operator(workflow_execution_id, template_job_id)(FR-114.1-2),背景自動完成路徑(無 request context)維持原樣不掛守門 ✅ 已修(FR-114.1-2)

另外記下的七條體質問題

這七條都不是現在打得到的漏洞。多數是「目前沒事是巧合、不是設計」的地方,列出來是因為它們會長成漏洞;其中兩條查下來另有結論——一條的危害情境根本不成立、一條是產品刻意的行為決定,兩條都在下表標明了。

最右欄是各自的處置——它們不是同一種待辦,有的跟著這塊的修正一起做,有的只改註解不動程式,有的只是記錄。

問題 為什麼現在沒事 為什麼還是要記 怎麼處置
「分享」這個範圍值,三層各認一套 建立掃描基準時填不出「分享」(被擋),但改基準時卻改得成——資料庫認、存取層認、業務邏輯那層不認 一個欄位三個地方各認一套值域,目前沒壞是巧合 ✅ 跟著這塊的修正一起做——既然要動這塊,順手把三個地方對齊
模組自帶的兩支資料庫腳本都落後主線(建表的那支、設定隔離規則的那支) 安裝程式會先跑出貨基線(已經是新的),之後才跑模組自帶那一輪,而那些腳本都是「已存在就跳過」——表已經是新的,那一輪等於空轉。所以「新裝客戶會出事」這個情境不會發生 真正的問題不是資安,是這個模組宣稱自己可以獨立安裝,而這個宣稱是假的。會受害的是「不走我們安裝程式、只拿這個模組自己裝」的人——今天沒有這種人 📝 只記錄,不處理(情境不成立)
一段說明文字寫的跟資料庫實際規則相反 說「刻意不受隔離、要看到全站」,實際上受隔離管;能走到這一步的人本來就是平台管理員,殊途同歸 那段文字前半句說「不受隔離」、後半句自己又承認「仍受規則擋」,前後矛盾,而事實是後半句對——結論碰巧正確、推理是錯的。下一個人只讀前半句就會放心開放刪除功能,而那會把數量誤判成 0、把還在用的標籤刪掉 📝 跟著一起改掉那段文字,程式不動
掃描基準那四個檔裡,一行客戶隔離的程式碼都沒有——安全完全外包給資料庫 三個前提目前逐項查過都成立:資料庫隔離規則正確、連線帳號沒有繞過權限的特權、上層一定會先經過受保護的資料表 三件事任何一件被改動,這四個檔不會有任何反應——不報錯、測試不會變紅,只會安靜地開始回傳別的客戶的資料 📝 把這三個前提寫進那幾個檔的開頭說明,程式不動。⚠️ 在這層自己再算一次不是正解——那會變成「兩套規則各自維護」,更壞。要留的是那句前提提醒
**規則清單那張表的保護「靠約定、沒有機制強制」 這張表沒掛資料庫隔離,靠的是「要查它一定得先拿到版本編號,而版本編號只能從受保護的表取得」;現有三個入口逐條追過,確實都先經過那一關 取資料那支方法是公開的,自己不檢查手上的版本編號是不是這家客戶的**——日後第四個入口只要手上有編號就能直接繞過,不會有任何錯誤訊息,只會悄悄拿到別家客戶的規則清單 📝 把這個前提寫進該檔開頭說明,程式不動(理由同上一列)
共用的分頁查詢工具,把跨欄位的條件用「或」而不是「且」連起來 不構成跨客戶外洩(客戶隔離靠資料庫那層擋,不靠這層條件) ⚠️ 這是刻意設計、不是小 bug——那支共用工具的說明文字明寫「多個文字條件以『或』連接」,實作也對得上。所以不能當小 bug 順手修:改它等於改全產品共用底層的對外約定,至少五支模組在用,沒特別動它的一律默默吃這個預設行為。影響不是外洩,是正確性——同時填兩個文字條件,拿回來的是「符合其中一個」,而使用者以為自己篩過了 🗂️ 另開獨立工單處理,本塊只記錄、不列為待修。這是產品行為決定,不是資安問題
規則包解壓上限有三套數字,其中一套根本沒接上(主系統接線那批查出) 三套數字現在剛好一致,所以行為正常;沒接上的那套只是擺著,不會被讀 哪天有人以為改那套就能調上限,改了卻完全沒效果——而且三套各自演化,下次數字就不一致了 🗂️ 非資安,另開一般修正工單:收成一套、刪掉沒接上的那套

下面只展開需要你自己判斷、或容易被誤解的幾條。 其餘的修法明確,看上面表格的「怎麼修」那一欄就夠了——沒有展開不代表沒查,也不代表不重要。

§4

第 1 條:上傳一包規則,就在我們的伺服器上執行

這是本塊影響面最大的一條。

不是「多看到一些資料」,是整台後端主機交出去。

問題是什麼

客戶要做檢測,得先給系統一包「檢測規則」——一個壓縮檔,裡面有一支設定檔說明這包規則是什麼。

系統把這個壓縮檔原封不動交給一支外部工具去解析。問題在這支外部工具身上:它讀那支設定檔的時候,會先把檔案內容當成程式樣板跑一遍,再拿結果去解析。

這是那支工具自己的行為(統籌者打開本機安裝的那份原始碼逐行核對,確認一字不差),不是我們寫錯——但我們把使用者的檔案直接餵了進去。

而且不只這一條路。 同一支工具還有第二種讀法:如果設定檔用的是「程式檔」那種形式,它會直接把整個檔案當程式碼執行——比樣板那條更直白,連包裝都不用。兩條路的結局一樣,防法也一樣(在交給它之前先看內容),列出來是為了讓修的人知道不能只擋樣板那一種。

我們的驗證器為什麼擋不住

驗證器自己在檔頭寫明:「只驗結構不驗內容」。它檢查——

檢查了什麼 有沒有看設定檔的內容
副檔名、檔案大小 ❌
檔案格式的識別碼 ❌
檔名會不會解壓到別的目錄 ❌
有沒有捷徑檔 ❌
檔案數量、膨脹倍數 ❌

沒有一項在看那支設定檔裡面寫了什麼。

所以一份檔名正常、結構正常的惡意規則包,一道防線都不會碰到。建好基準之後系統自動排解析,程式就執行了。

打進去能拿到什麼

拿到的東西 能做什麼
一整批系統密鑰 除了簽發登入憑證那一把(拿到就能冒充任何人登入,包含平台管理員),還有代理程式的憑證私鑰、檢測工具的加密金鑰,以及一整排外部服務的通行證
能自行提權的資料庫身分 這個帳號本身沒有繞過客戶隔離的特權,但它可以自己把「我是超級管理員」那個開關打開,而全庫的隔離規則都認那個開關。結果一樣是讀寫全部客戶的資料——但要講清楚是「能自行提權」,不是「本來就是管理員」
檔案儲存與代理程式的憑證 取走所有客戶上傳的檔案;接管客戶機房的代理程式
那台主機本身 當成跳板往內網走

一個客戶的管理員,就能打下整台主機與全平台資料。

而且網址型來源更省事——把同一份檔案放自己的伺服器上填進去即可,連上傳都不用。

為什麼評「高」而不是「最嚴重」

判斷依據 這件事
要先有帳號嗎 要,必須是登入的客戶管理員
過了那一道之後呢 沒有第二道防線

門檻只有這一道。(對照:全案唯一那條「最嚴重」是連帳號都不用的。)

建議怎麼修

步驟 做什麼 為什麼不能省
一 重新打包之前先讀一次那支設定檔,看到程式樣板標記就拒收 這是唯一在所有來源之前的共同關卡
二 這道檢查要放進打包那一步本身 放在上傳那條路的服務層會漏掉網址那條路——兩條路共用同一支打包程式
三(長期) 把那支外部工具關進沙箱跑 就算哪天又冒出第三條路,被執行的程式也出不來

§5

第 2 條:一個按鈕,送走整家公司的維運帳密

問題是什麼

掃描工具設定頁上有個「測試連線」按鈕,本來是給管理員確認「我填的帳密對不對、連得上嗎」。

按下去之後,系統會把存好的帳密解密,交給裝在客戶機房的代理程式,送到指定的那台主機去試連。

問題是這個按鈕沒有檢查權限——任何一個能登入的帳號都按得動。

這是漏掉,不是刻意

同一支檔案裡的功能 有沒有檢查權限
新增工具設定 ✅
修改工具設定 ✅
重置工具設定 ✅
測試連線 ❌ ← 真正的缺口
查引用次數 ❌(但這支沒掛是合理的,見下)

本報告撰寫時開檔核對,三支寫入功能的權限檢查都在,那兩支仍然只有「客戶有沒有買這個功能」這一道。

但這兩支的性質差很多,要修的只有一支:「查引用次數」是純查詢——不解密任何東西、也不對外連線,沒掛權限是合理的。「測試連線」雖然名字像查詢,實際是寫入性質:它會實際把憑證送出去,還會回寫測試結果。只有這一支是缺口。

送出去的是什麼

連主機用的 SSH 密碼、Windows 遠端管理帳密,以及 SonarQube、OpenVAS、ZAP 這些掃描工具的存取權杖——等於一次拿走整家公司的維運帳密。

這條跟「設備清冊讀取不守」那條長得像,但不能比照放行

那一條是純讀取,這一條會解密憑證並主動對外連線。性質完全不同。

而且「連到哪裡」也是呼叫者說了算(第 6 條)

要連到哪台主機,是呼叫者在請求裡直接指定的——系統既不比對白名單,也不管這台主機跟存好的設定有沒有關係。

結果是客戶內網裡那支代理程式變成**「只要登入就能用的任意連線跳板」**,而且回應訊息的差異(連得上/連不上/逾時)還能拿來一台一台探測客戶內網。

已裁定:不做目標白名單

原本的建議是「只准連到該客戶已經登記的掃描目標」。這個建議已經撤掉。

理由:掃描目標是客戶自己的主機、連線帳號也是客戶提供的,我們無從判斷哪一台算合法目標——這件事該由客戶自己管。硬做白名單只會擋掉正常使用:測連線本來就常常是在「還沒登記的主機」上測。

改做三件:

  1. 限制單次可以帶幾台主機——擋的是「一個請求帶一萬台,測試連線就變成內網掃描器」
  2. 回應收斂成單純的成功/失敗——擋的是「用連得上/連不上/逾時的差異,一台一台探測客戶內網」
  3. 日誌要記三樣才追得到:誰按的、連到哪一台、用了哪一組設定。只記「有人按了測試連線」沒有用

前兩件都不會擋到正常使用——真的在測連線的人一次就測一台,也只需要知道「這組帳密能不能用」。

🔴 既然不限制連到哪裡,第 2 條那道權限檢查就是唯一的防線。 第 2 條原本被歸在「跟第 6 條一起修才有意義」,現在它自己就是那個意義——第 2 條要往前排。


§6

這塊的結論

一句話:這塊查完了,找到十三條,其中兩條高風險(另有一條是別處問題波及到這裡)。這兩條高風險的共同特徵是——這塊手上握著的東西,本來就是全案最敏感的(客戶主機的明文帳密、可執行的規則包、對客戶內網的連線能力)。

建議的處理順序:

  1. 第 1 條最優先。 它是目前本塊唯一一條「一次得手就拿到整台主機與全平台資料」的,而且修法很小(在打包前多讀一次設定檔)。⚠️ 修的位置要對——放在上傳那條路會漏掉網址那條;而且要同時擋掉兩種讀法(當成程式樣板跑,以及直接當程式碼執行)。
  2. 第 2 條緊接著——它現在是唯一的防線。 因為第 6 條已裁定不限制可以連到哪裡(目標是客戶自己的主機,該由客戶自己管),所以「誰可以按這顆按鈕」變成唯一擋得住的地方。真正要補的只有「測試連線」這一支(同樣沒掛的「查引用次數」是純查詢、不解密、不對外連線,不必動)。
  3. 第 6 條同一個入口一起做,但方向改了:不做目標白名單,改成限制單次台數、回應只給成功/失敗、日誌記到「誰按的、連到哪一台、用了哪一組設定」。
  4. 第 3、4、5 條建議一起修——都在「規則包怎麼進來、怎麼被檢查」這一段,而且第 3 條與第 4 條是同一支驗證器的兩種病(一個是「上限太晚生效」,一個是「上限根本沒接進這條路」)。修的時候把檢查放進解析那一層,未來的第三種來源天然涵蓋。
  5. 第 7 條要跨出這一塊看——同樣寫反的隔離規則在出貨基線裡共有 11 條,橫跨四塊功能,只改本塊的五張等於沒修。已裁定集中一次改完、不為此單獨重產基線,🔴 但出貨前必須完成;施工時逐條比對、不要批次取代(會把基線裡上百條正確的一起改壞)。⚠️ 動出貨基線屬決策者裁示範圍。 🔴 而且這 11 條要分兩組改:8 張改成正確方向,授權那 3 張只擋「改」和「刪」、「看」保持原樣——授權的設計就是「照綁在最頂層、底下子單位共用」,把那三張改成跟其他表一樣會讓每個子單位查不到授權、功能當場掛掉。詳見授權管理那塊。
  6. 第 10 條的修改範圍比表面上大——除了加上限,還要一併處理「手動重抽會主動把狀態壓回等待中」這個既有動作,否則新加的判斷擋不到任何東西。
  7. 第 14 條不是這塊的新問題,但修的時候不能漏掉這塊——那條原本記在「稽核流程」那塊,決策方向已經裁定,但原本記的範圍只有流程那塊的兩支功能;這次查出來,這塊還有八支吃同一道守門。修那條的時候要把範圍一起擴大到這八支。
  8. 第 8 條順位最後。 重新定性後已調降為低風險——那個功能本來就只開給租戶管理員,不是「任何登入者都拿得到」。真正的問題是權限矩陣騙了管理員(取消勾選只讓前端選單消失,後端照回)。補的時候保留那顆權限點、一併改掉那句「讀取端刻意不掛」的說明文字,並驗證公版與分享的可見範圍沒有被改壞。這個形狀與設備清冊那塊相同,建議兩處一次裁。

最後要說清楚兩件事:

  • 「查完」不等於「查乾淨」。 這 14 批查過的範圍裡沒再找到別的,但我們的方法能證明的是「找到了什麼」,不是「沒有別的」。
  • 有 4 批的成本花在跟工具搏鬥、不是查程式(一批 17 小時零產出、一批紀錄被誤刪、一批換四次人、一批派三位回一位)。這幾批涵蓋的檔案,可信度要打一點折;而這也正是全站在 2026-09-20 決定止損、改成「針對已經發現的修」的依據(見總報告首頁)。
統計(2026-09-23 收口)
檢視批數 15 批(模組本體 14 批+主系統接線 1 批,已全部完成;其中 4 批的成本花在跟工具搏鬥)
檢視的檔案 83 個(正式程式碼 160 個,扣掉另一條線已查過的 11 個、與 66 個沒有邏輯的檔案)
這塊找到的問題 13 條
↳ 高風險 2 條
↳ 中風險 10 條
↳ 低風險 1 條(第 8 條,重新定性後由中調降)
另有別處問題波及到這塊 1 條(表中第 14 條,不計入上面的 13 條)
已修 0 條
未修 13 條(+波及的那 1 條)
另記的體質問題 7 條——跟著這塊修正一起做 1 條、只改說明文字不動程式 3 條、另開獨立工單 2 條、只記錄不處理 1 條
已開工單 0 張(決策者裁定先登記,修正工單另批統一開)
主系統接線 已補查(2026-09-23,12 個檔、一批)——範圍內沒有新的資安問題

你想知道 看哪裡
我們用什麼方法查、結果有多可信 檢視方法與工具
為什麼有些批次要拆得很小 檢視方法與工具 → 為什麼要分批進行
其他模組的檢視結果 回總報告首頁