加拿大魁北克疫苗護照的缺陷:分析
魁北克政府允許存儲和驗證疫苗接種護照的移動應用程序(VaxiCode 和 VaxiCode Verif)的推出在上周引起了大量墨水流動。這是有充分理由的;自 2021 年 9 月 1 日起,所有非必要服務商戶都將使用 VaxiCode Verif 應用程序。
和許多其他專家一樣,我在去年 5 月第一次接種疫苗時收到二維碼后立即對其內容進行了分析。上周,我還分析了魁北克政府建立并由Akinox開發的兩個應用程序。
這篇博文從技術角度解釋了魁北克政府建立的疫苗護照系統的工作原理,以及我們在 VaxiCode Verif 中發現的漏洞的詳細信息,該漏洞允許應用程序被迫將非政府頒發的二維碼識別為有效的。目前,無法確認這與加拿大廣播電臺上周五報道的“路易斯”發現的漏洞相同,因為尚未發布任何技術細節。
我們將周日發現的漏洞告知了 Akinox,并確認最近幾天發布的 iOS 版 VaxiCode Verif 1.0.2 更新修復了該漏洞。尚未分析 Android 版本的應用程序,但 VaxiCode 和 VaxiCode Verif 使用Expo框架,該框架允許使用相同的源代碼生成 iOS 和 Android 應用程序。因此,兩個平臺上的應用程序可能是等效的。
讓我們深入了解魁北克疫苗護照的內容
首先,讓我們看看二維碼包含什么。一般來說,二維碼只包含文字。它通常是一個 URL。

但讓我們回到魁北克疫苗護照申請。我們注意到此二維碼中包含的 URL 以 開頭shc:/。“shc”實際上是SMART Health Cards的首字母縮寫,該規范定義了用于交換有關個人疫苗接種狀態信息的格式。該規范誕生于 2021 年,目的是能夠簽發這本著名的疫苗護照,并能夠驗證其真實性。這與美國幾個州(包括加利福尼亞州、紐約州和路易斯安那州)選擇的標準相同。該規范的制定由疫苗接種證書倡議牽頭,一個由公共和私人組織組成的聯盟,致力于在全球范圍內安全部署護照。為魁北克政府開發 VaxiCode 和 VaxiCode Verif 的公司 Akinox 是該組織的成員。
該規范描述了如何將 URL 中的數字解碼為可讀內容。

信息被解碼為 JSON 網絡令牌 (JWT),或者更具體地說是 JSON 網絡簽名 (JWS),因為它是一個簽名令牌。SHC 規范并沒有重新發明輪子:JWT 是一種用于交換加密或數字簽名信息的現有技術。
如果您想了解有關疫苗護照內容的更多信息,您可以使用Fran?ois Proulx 開發的在線工具從移動設備輕松檢查。
這些信息應該加密嗎?
許多人建議對二維碼中的信息進行加密。這似乎是保護它的好方法;然而,破譯這些信息太容易了。該信息必須被 VeriCode Verif 理解,因此應用程序應包含解密密鑰。提取密鑰后,任何人都可以解密二維碼。這會給人一種安全的錯誤印象,并引起公眾的更多批評。
由于這些原因,SHC 協議不提供加密方法。但是,它確實需要數字簽名。
數字簽名如何工作?
數字簽名基于非對稱加密,這意味著使用密鑰對。這對由一個私鑰組成,只有發行人(這里是魁北克政府)才能對數據進行簽名,還有一個所謂的公鑰,用于驗證是否使用私鑰進行了簽名。
除其他外,非對稱加密用于加密 Internet 上的通信。在沒有私鑰或從公鑰猜測私鑰的情況下,沒有已知的攻擊可以簽名。
這也意味著優先考慮的是不惜一切代價保護這個私鑰。破壞此密鑰將允許生成加密有效的二維碼。我們發現的缺陷并非如此:我們不需要私鑰來偽造 VaxiCode Verif 認為有效的疫苗證明。相反,問題在于 VaxiCode Verif 中驗證算法的實現。
VaxiCode Verif 的缺陷究竟是什么?
SMART Health Cards 規范旨在允許多個疫苗證據發布者的可能性。這反映了每個國家或地區都有責任出具自己的證據的現實。因此,每個政府都有自己的一對密鑰來簽署和驗證護照。
SHC 規范要求發行實體在 Internet 上提供其公鑰。疫苗證明在“iss”(issuer 的縮寫)字段中包含指向發行人網站的 URL 。驗證應用程序應通過連接.well-known/jwks.json到此 URL 來找到發行者的公鑰。
該規范沒有定義(至少目前)確定發行人是否值得信賴的方法。
Akinox 選擇在 VaxiCode 和 VaxiCode Verif 中包含魁北克政府的公鑰。當發行人是魁北克政府時(特別iss是如果是https://covid19.quebec.ca/PreuveVaccinaleApi/issuer),應用程序將使用此密鑰。然而,下載第三方發行者密鑰的代碼仍在應用程序中,即使它不是必需的。
該漏洞在于,一旦下載了公鑰,就可以使用它來驗證任何其他通行證,而無需檢查它是否與頒發者字段 ( iss)的內容匹配。
這是顯示偽造疫苗證明有效的攻擊場景:
- 攻擊者生成密鑰對并在以下位置提供公鑰
https://example.org/.well-known/jwks.json - 他以二維碼的形式生成了兩張智能健康卡:
- 第一個是使用任意內容創建的,前提是
iss是https://example.org。 - 第二個是使用想要冒充接種疫苗的人的個人信息以及
iss指向合法政府域的字段創建的,并使用步驟 1 中生成的密鑰對其進行簽名。 - 在驗證疫苗護照期間,攻擊者首先出示第一個二維碼。此驗證將被 VaxiCode Verif 拒絕,但會強制應用程序下載攻擊者的公鑰并將其添加到其受信任的鑰匙串中。
- 攻擊者隨后將展示第二個二維碼,該二維碼將被 VaxiCode Verif 驗證為合法。
自周日起在 Apple App Store 上可用的 1.0.2 版修復了該問題。此更新完全刪除了從發行者的 URL 下載公鑰的功能。
什么可以做得更好?
負責部署疫苗證明的當局和開發人員受到難以緩解的限制:時間。魁北克疫苗接種證明的整個開發和部署是在幾個月內完成的。盡管存在一些缺陷,但該系統正在運行。
為了透明起見,魁北克政府可能錯過了發布其制作的應用程序源代碼的好機會。畢竟,這些應用程序沒有什么可隱藏的,也沒有什么秘密。缺陷的快速發現表明,大量專家的分析提高了此類應用程序的安全性。源代碼的發布和專家的分析可能避免了可能影響公眾信心的丑聞,因為所有人都可以自行檢查安全性。
也有人覺得魁北克疫苗護照所載的個人資料過多。在這方面,本來可以制作包含較少信息的較輕版本的護照。也就是說,這種較輕的版本可能在魁北克以外地區無法使用,因為確定一個人是否受到保護的規則可能因地區而異(哪些疫苗被認為是有效的,劑量多少等)。
這就是瑞士選擇的“COVID light證書”。還應該指出的是,瑞士應用程序的源代碼也已經發布了幾個月。
我們沒有測試允許發放疫苗護照的服務器,因為我們既沒有魁北克政府或 Akinox 的授權,也沒有獲得這樣做的許可。與魁北克提供的應用程序分析不同,這將構成對遠程系統的攻擊,可能導致服務中斷的風險。
結論
我們的分析首先考察了 CHS 規范的發展歷史,該規范是在國際上專門為發布 COVID-19 疫苗接種確認而制定的。然后我們解釋了使用非對稱加密技術對數據進行簽名的重要性,在這種情況下,確保所提供的疫苗接種證明的有效性。但是,我們發現驗證算法的實現存在缺陷,該缺陷允許偽造 VaxiCode Verif 顯示為合法的疫苗證明。我們將這個缺陷通知了 Akinox,并且在應用程序更新后即在幾天內修復了它。最后,我們指出了提高這些應用程序源代碼透明度的潛在好處。
通過這個分析,我認為,雖然 VaxiCode Verif 在發布時存在一些問題,但該系統所基于的技術是可靠的。在我看來,使用現有標準和技術的想法是一個很好的決定。它使用 SMART Health Cards 協議確保區域之間的簽名安全性和互操作性。在我看來,拒絕有效疫苗護照的系統缺陷會產生比相反更嚴重的影響,而這里并非如此。
問題在短短幾天內得到解決表明各方都想要一個安全的系統。總有需要改進的地方,但 SHC 提出的數字簽名的使用迄今為止是安全的。