← All issues

[2] Attachment-element arbitrary file read via unvalidated IPC path

Severity: High | Component: WebKit UIProcess attachment handling | c6cd4e0

diff가 추가한 provenance check는 이전까지 누락된 상태였으며, 이로 인해 침해된 renderer가 UI process 수준에서 읽을 수 있는 임의의 파일을 지목하고 그 내용을 attachment에 바인딩하는 것이 가능했습니다. sandbox 파일시스템 탈출로 이어지는 information leak으로 확장되려면 사전 renderer 침해만 전제되면 충분하며, /etc/passwd regression test가 해당 경로의 실제 도달 가능성을 뒷받침합니다.

WebProcessProxy에는 pasteboard 및 drag-drop 작업을 통해 web process에 정당하게 제공된 경로를 추적하는 파일 경로 allowlist(m_allowedAttachmentFilePaths)가 추가되었습니다. RegisterAttachmentIdentifierFromFilePath에서는 MESSAGE_CHECK를 통해 수신된 경로를 이 allowlist와 대조하며, 허가되지 않은 경로에 대해서는 web process를 종료합니다.

Source/WebKit/UIProcess/WebPageProxy.cpp

void WebPageProxy::registerAttachmentIdentifierFromFilePath(IPC::Connection& con...
{
MESSAGE_CHECK_BASE(protect(preferences())->attachmentElementEnabled(), connection);
MESSAGE_CHECK_BASE(IdentifierToAttachmentMap::isValidKey(identifier), connection);
+ MESSAGE_CHECK_BASE(WebProcessProxy::fromConnection(connection)->isAllowedAttachmentFilePath(filePath), connection);
...
+#if ENABLE(ATTACHMENT_ELEMENT)
+ for (auto& filename : dragData.fileNames())
+ protect(protectedThis->legacyMainFrameProcess())->addAllowedAttachmentFilePath(filename);
+#endif

Source/WebKit/UIProcess/WebProcessProxy.cpp

+void WebProcessProxy::addAllowedAttachmentFilePath(const String& filePath)
+{
+ if (!filePath.isEmpty())
+ m_allowedAttachmentFilePaths.add(filePath);
+}
+bool WebProcessProxy::isAllowedAttachmentFilePath(const String& filePath) const
+{
+ return m_allowedAttachmentFilePaths.contains(filePath);
+}

Tools/TestWebKitAPI/Tests/WebKit/WKWebView/WKAttachmentTests.mm

+ [webView evaluateJavaScript:
+ @"IPC.sendMessage('UI', IPC.webPageProxyID, IPC.messages.WebPageProxy_RegisterAttachmentIdentifierFromFilePath.name, ["
+ " {type: 'String', value: 'fake-identifier'},"
+ " {type: 'String', value: 'application/octet-stream'},"
+ " {type: 'String', value: '/etc/passwd'}"
+ "])"
+ completionHandler:nil];
+ [navigationDelegate waitForWebContentProcessDidTerminate];

이번 patch는 WebProcessProxyHashSet<String> m_allowedAttachmentFilePaths를 추가했습니다. 이 집합은 UI process가 web process에 실제 파일시스템 경로를 전달하는 모든 정당한 지점에서 채워집니다. drag-drop 시에는 performDragOperationdragData.fileNames()를 순회하며 경로를 추가하고, pasteboard 읽기 시에는 WebPasteboardProxyCocoa.mm에서 새로 도입된 addAllowedAttachmentFilePaths helper를 통해 추가됩니다. registerAttachmentIdentifierFromFilePath에는 MESSAGE_CHECK_BASE(... isAllowedAttachmentFilePath(filePath), connection)가 추가되어, 정당하게 허용된 적 없는 경로에 대해 web process를 종료합니다. 보조적인 강화 조치로 registerAttachmentsFromSerializedData에도 isValidKey 검사가 추가되었습니다.

WebContent → UIProcess IPC 경계를 넘는 파일시스템 경로에 대한 provenance 검증 누락 — sandbox 내 송신자가 허가받지 않은 파일을 지목할 수 있었던 패턴.

WebProcessProxy는 하나의 web content process를 대표하는 UI process 측 객체로, WebContent sandbox 밖에서 사용자의 전체 권한으로 실행됩니다. <attachment> element의 backing data는 디스크 상의 파일이 될 수 있으며, 해당 파일은 식별자를 통해 등록됩니다. registerAttachmentIdentifierFromFilePath는 web process가 제공한 경로를 받아 attachment를 생성하는 UI process 측 IPC handler입니다. UI process가 renderer에 실제 파일시스템 경로를 노출하는 정당한 경우는 사용자가 파일을 drag-drop하거나 파일 URL을 붙여넣을 때뿐입니다. 이때 UI process는 sandbox extension을 통해 해당 경로들만 한정적으로 공유합니다. MESSAGE_CHECK_BASE는 assertion이 실패할 경우 송신 process를 종료합니다.

전형적인 confused-deputy / IPC 검증 누락 유형의 버그입니다. 패치 이전에는 registerAttachmentIdentifierFromFilePath가 renderer로부터 임의의 filePath 문자열을 받아 해당 경로를 backing으로 하는 attachment를 등록했습니다. UI process가 해당 경로를 정당하게 노출한 적이 있는지는 전혀 확인하지 않았습니다. 누락된 불변 조건은 다음과 같습니다. attachment 생성에 사용되는 파일 경로는 반드시 실제 사용자 행위(drag-drop 또는 pasteboard 읽기)를 통한 허가로 소급되어야 합니다.

🔒

How a single unvalidated IPC argument turns a privileged-process file operation into a renderer-visible disclosure is traced end to end.

더 확인하려면 구독해 주세요

🔒

Three reusable audit patterns for confused-deputy IPC bugs are identified, with concrete UIProcess starting points for variant discovery.

더 확인하려면 구독해 주세요