300 lines
12 KiB
Markdown
Executable File
300 lines
12 KiB
Markdown
Executable File
---
|
||
title: Mapping Apple OS builds to WebKit source releases
|
||
tags: [webkit, safari, macos, ios, crash, ravel, reference]
|
||
created: 2026-10-06
|
||
updated: 2026-10-06
|
||
---
|
||
|
||
# Mapping Apple OS builds to WebKit source releases
|
||
|
||
## Purpose
|
||
|
||
This document explains how to map a WebKit crash on macOS or iOS to:
|
||
|
||
1. the exact Apple OS build;
|
||
2. the exact system WebKit binary by Mach-O UUID;
|
||
3. its `CFBundleVersion` and WebKit `FULL_VERSION`;
|
||
4. the closest public WebKit source tag;
|
||
5. the presence or absence of a source change.
|
||
|
||
The DuckDuckGo Apple browsers currently support macOS **12.3+** and iOS **15.0+**. The deployment targets are defined in `macOS/Configuration/Common.xcconfig` and `iOS/DuckDuckGo-iOS.xcodeproj/project.pbxproj` in the Apple browsers repository.
|
||
|
||
## Short answer
|
||
|
||
Use this chain for an exact mapping:
|
||
|
||
```text
|
||
OS version + OS build
|
||
-> WebKit Mach-O UUID from the crash report
|
||
-> matching binary and UUID in Ravel
|
||
-> WebKit CFBundleVersion from the OS or app telemetry
|
||
-> remove the platform SYSTEM_VERSION_PREFIX
|
||
-> WebKit FULL_VERSION
|
||
-> public source tag or release branch
|
||
-> inspect the released code for the fix
|
||
```
|
||
|
||
An OS major version identifies only a **WebKit release train**. It does not identify the exact WebKit revision because Apple updates WebKit in OS point and security releases.
|
||
|
||
## Version fields
|
||
|
||
| Field | Example | Meaning |
|
||
|---|---:|---|
|
||
| OS version | `macOS 27.0.1` | Marketing version |
|
||
| OS build | `26A434` | Exact Apple OS build; use this in Ravel |
|
||
| Mach-O UUID | `70BEE322-...` | Exact WebKit binary identity for one architecture |
|
||
| `CFBundleVersion` | `22625.1.29.11.28` | System framework build version |
|
||
| `SYSTEM_VERSION_PREFIX` | `22` | Platform/OS prefix added by Apple's production build |
|
||
| WebKit `FULL_VERSION` | `625.1.29.11.28` | Release version without the system prefix |
|
||
| Source tag | `WebKit-7625.1.29.11.28` | Candidate public source release |
|
||
| HTTP User-Agent | `AppleWebKit/605.1.15` | Frozen compatibility token; not usable for this mapping |
|
||
|
||
## Supported OS release trains
|
||
|
||
These tables map each supported OS major to its initial Safari/WebKit release train. Always use the exact-build workflow for a crash or API-availability decision.
|
||
|
||
### macOS 12.3+
|
||
|
||
| macOS | DDG support | Safari release | WebKit base `FULL_VERSION` | macOS prefix | Production bundle base | Public source-tag family |
|
||
|---|---:|---:|---:|---:|---:|---|
|
||
| 12 Monterey | 12.3+ | 15 | `612.1.27` | `17` | `17612.1.27` | `Safari-612.1.27.*` |
|
||
| 13 Ventura | Yes | 16 | `614.1.25` | `18` | `18614.1.25` | `WebKit-7614.1.25.*` |
|
||
| 14 Sonoma | Yes | 17 | `616.1.27` | `19` | `19616.1.27` | `WebKit-7616.1.27.*` |
|
||
| 15 Sequoia | Yes | 18 | `619.1.26` | `20` | `20619.1.26` | `WebKit-7619.1.26.*` |
|
||
| 26 Tahoe | Yes | 26 | `622.1.22` | `21` | `21622.1.22` | `WebKit-7622.1.22.*` |
|
||
| 27 Golden Gate | Yes | 27 | `625.1.29` | `22` | `22625.1.29` | `WebKit-7625.1.29.*` |
|
||
|
||
### iOS 15.0+
|
||
|
||
WebKit uses `SYSTEM_VERSION_PREFIX = 8` for iPhone-family SDKs. Therefore the iOS production bundle version is `8` concatenated with `FULL_VERSION`.
|
||
|
||
| iOS | DDG support | Safari release | WebKit base `FULL_VERSION` | iOS prefix | Production bundle base | Public source-tag family |
|
||
|---|---:|---:|---:|---:|---:|---|
|
||
| 15 | 15.0+ | 15 | `612.1.27` | `8` | `8612.1.27` | `Safari-612.1.27.*` |
|
||
| 16 | Yes | 16 | `614.1.25` | `8` | `8614.1.25` | `WebKit-7614.1.25.*` |
|
||
| 17 | Yes | 17 | `616.1.27` | `8` | `8616.1.27` | `WebKit-7616.1.27.*` |
|
||
| 18 | Yes | 18 | `619.1.26` | `8` | `8619.1.26` | `WebKit-7619.1.26.*` |
|
||
| 26 | Yes | 26 | `622.1.22` | `8` | `8622.1.22` | `WebKit-7622.1.22.*` |
|
||
| 27 | Yes | 27 | `625.1.29` | `8` | `8625.1.29` | `WebKit-7625.1.29.*` |
|
||
|
||
iOS versions 19–25 do not exist; Apple changed the public version number from 18 to 26.
|
||
|
||
## Exact builds verified in Ravel
|
||
|
||
Ravel is currently incomplete. A missing build means that Ravel does not index it, not that the OS lacks WebKit.
|
||
|
||
### macOS examples
|
||
|
||
| macOS | Build | WebKit UUID | `CFBundleVersion` | `FULL_VERSION` |
|
||
|---|---|---|---:|---:|
|
||
| 26.5.2 | `25F84` | `49B21D99-8716-31B8-8686-71B287325F1D` | `21624.2.5.11.8` | `624.2.5.11.8` |
|
||
| 26.6 | `25G72` | `B090AABF-9A3B-3110-9DA9-F0F40FCEC972` | `21624.4.5.11.5` | `624.4.5.11.5` |
|
||
| 26.6.1 | `25G76` | `B090AABF-9A3B-3110-9DA9-F0F40FCEC972` | `21624.4.5.11.5` | `624.4.5.11.5` |
|
||
| 26.6.2 | `25G83` | `844AF253-CAF6-3623-9DAD-A055C5274E62` | `21624.5.1.11.3` | `624.5.1.11.3` |
|
||
| 27.0.1 | `26A434` | `70BEE322-37EE-3B22-8012-4F76BA105C29` | `22625.1.29.11.28` | `625.1.29.11.28` |
|
||
| 27.2 beta | `26B5086k` | `6F6AB57E-1492-3950-9962-85B6AFD430A3` | `22625.2.4.1` | `625.2.4.1` |
|
||
| 27.2 beta 2 | `26B5091g` | `56B4AA44-CB66-3641-8B22-723C39B5BC6E` | `22625.2.5.11.1` | `625.2.5.11.1` |
|
||
| 27.2 beta 3 | `26B5101f` | `B32D7081-AE42-3A2E-ACBB-CF4D4BE4F296` | `22625.2.7.1` | `625.2.7.1` |
|
||
|
||
macOS 26.6 and 26.6.1 contain the same WebKit binary: both UUID and `CFBundleVersion` match.
|
||
|
||
### iOS examples
|
||
|
||
Ravel identifies iOS WebKit binaries and UUIDs, but its dyld-cache page does not expose the framework `Info.plist` value. Read `CFBundleVersion` at runtime or from an extracted IPSW before claiming an exact source release.
|
||
|
||
| iOS | Build | WebKit UUID |
|
||
|---|---|---|
|
||
| 26.6 | `23G71` | `7627FDAB-129E-32BB-A2AC-F0DC02853D4E` |
|
||
| 26.6.1 | `23G83` | `C39BD22C-3475-38AF-91BD-0B7574081011` |
|
||
| 26.6.2 | `23G90` | `C39BD22C-3475-38AF-91BD-0B7574081011` |
|
||
| 27.0.1 | `24A446` | `D12A79A6-98CB-323C-8F72-613AD0983BBC` |
|
||
| 27.2 beta | `24B5084k` | `1FD67A57-D91B-3B26-9F4F-91AB8299B6E7` |
|
||
| 27.2 beta 2 | `24B5089g` | `509D51AD-2CF9-3982-BFD5-81221D1B903D` |
|
||
| 27.2 beta 3 | `24B5099f` | `0566BF55-2DC4-34F6-B211-96FFAA0A37A4` |
|
||
|
||
iOS 26.6.1 and 26.6.2 contain the same WebKit binary UUID.
|
||
|
||
## Exact mapping procedure
|
||
|
||
### 1. Read the OS build and WebKit UUID
|
||
|
||
From an Apple crash report, record the OS version/build and the WebKit image UUID. Compare UUIDs without case or dashes, and match the architecture.
|
||
|
||
```bash
|
||
rg 'OS Version:|WebKit.*<' crash-report.crash
|
||
```
|
||
|
||
### 2. Find the binary in Ravel
|
||
|
||
Use the OS build and the correct binary path:
|
||
|
||
```text
|
||
macOS: /System/Library/Frameworks/WebKit.framework/Versions/A/WebKit
|
||
iOS: /System/Library/Frameworks/WebKit.framework/WebKit
|
||
```
|
||
|
||
Ravel URL pattern:
|
||
|
||
```text
|
||
https://ravel.dbg.re/binary?build=<OS_BUILD>&domain=dyld_cache&path=<URL_ENCODED_BINARY_PATH>
|
||
```
|
||
|
||
The Ravel UUID must equal the crash-report UUID. A matching version string without a matching UUID is weaker evidence.
|
||
|
||
### 3. Read `CFBundleVersion`
|
||
|
||
From app code on either platform:
|
||
|
||
```swift
|
||
import WebKit
|
||
|
||
let webKitBundleVersion = Bundle(for: WKWebView.self)
|
||
.object(forInfoDictionaryKey: "CFBundleVersion") as? String
|
||
```
|
||
|
||
On macOS, it can also be read without app changes:
|
||
|
||
```bash
|
||
defaults read /System/Library/Frameworks/WebKit.framework/Resources/Info CFBundleVersion
|
||
```
|
||
|
||
For iOS, log the runtime value on a test device or include it in crash/pixel metadata. Do not infer an exact iOS value from the same-numbered macOS release.
|
||
|
||
### 4. Remove `SYSTEM_VERSION_PREFIX`
|
||
|
||
Apple production builds concatenate the prefix and the WebKit version:
|
||
|
||
```text
|
||
CFBundleVersion = SYSTEM_VERSION_PREFIX + FULL_VERSION
|
||
```
|
||
|
||
| Platform | OS | Prefix |
|
||
|---|---|---:|
|
||
| iOS | All supported versions | `8` |
|
||
| macOS | 12 | `17` |
|
||
| macOS | 13 | `18` |
|
||
| macOS | 14 | `19` |
|
||
| macOS | 15 | `20` |
|
||
| macOS | 26 | `21` |
|
||
| macOS | 27 | `22` |
|
||
|
||
Example:
|
||
|
||
```text
|
||
22625.1.29.11.28 - prefix 22 -> 625.1.29.11.28
|
||
```
|
||
|
||
### 5. Resolve the public source release
|
||
|
||
For modern release trains, candidate tags use:
|
||
|
||
```text
|
||
WebKit-7<FULL_VERSION>
|
||
```
|
||
|
||
Example:
|
||
|
||
```text
|
||
625.1.29.11.28 -> WebKit-7625.1.29.11.28
|
||
```
|
||
|
||
The 612 train is an older naming exception:
|
||
|
||
```text
|
||
612.1.27.* -> Safari-612.1.27.*
|
||
```
|
||
|
||
Check exact public tags and release branches:
|
||
|
||
```bash
|
||
git ls-remote --tags https://github.com/WebKit/WebKit.git 'WebKit-7625.1.29*'
|
||
git ls-remote --heads https://github.com/WebKit/WebKit.git 'safari-7625*'
|
||
```
|
||
|
||
An adjacent tag is only a bound, not an exact match. Apple may publish a binary before publishing the corresponding source tag.
|
||
|
||
### 6. Verify the fix in released source
|
||
|
||
Inspect the changed code in the candidate tag. This is stronger than checking one commit SHA because Apple may cherry-pick the change under a different SHA.
|
||
|
||
For the certificate-info crash discussed below:
|
||
|
||
```bash
|
||
git show <TAG>:Source/WebKit/UIProcess/WebFrameProxy.h \
|
||
| rg 'commitCertificateInfo'
|
||
```
|
||
|
||
Old signature:
|
||
|
||
```cpp
|
||
void commitCertificateInfo(const URL&);
|
||
```
|
||
|
||
Fixed signature from `318982@main`:
|
||
|
||
```cpp
|
||
void commitCertificateInfo(const URL&, bool hasCertificateInfo);
|
||
```
|
||
|
||
### 7. When the exact source tag is unavailable
|
||
|
||
Record the evidence level explicitly:
|
||
|
||
1. UUID + `CFBundleVersion`: exact binary and release version are known.
|
||
2. Symbols or disassembly: a specific ABI or behavior can be proven in the binary.
|
||
3. Reproduction on the exact OS build: the bug can be proven present or absent.
|
||
|
||
Safari Technology Preview is a separate build. Its version does not prove the version of system WebKit.
|
||
|
||
## Current certificate-info crash
|
||
|
||
The crash on macOS 27.0.1 maps as follows:
|
||
|
||
```text
|
||
macOS: 27.0.1 (26A434)
|
||
Crash UUID: 70BEE322-37EE-3B22-8012-4F76BA105C29
|
||
Ravel UUID: 70BEE322-37EE-3B22-8012-4F76BA105C29
|
||
CFBundleVersion: 22625.1.29.11.28
|
||
Prefix: 22
|
||
FULL_VERSION: 625.1.29.11.28
|
||
Candidate tag: WebKit-7625.1.29.11.28
|
||
```
|
||
|
||
The exact `.11.28` source tag is not public as of 2026-10-06; `.11.27` is public. The crash symbol and the `WebKit-7625.1.29` source family both show the old one-argument signature. Therefore the fix is absent from macOS 27.0.1.
|
||
|
||
Ravel identifies macOS 27.2 beta binaries as `625.2.4.1`, `625.2.5.11.1`, and `625.2.7.1`. Public `WebKit-7625.2.*` tags are not available as of 2026-10-06. The fix landed in `318982@main` and Safari Technology Preview 251, so macOS 27.2 is a candidate for the first fixed system release, but source inclusion is not yet proven.
|
||
|
||
## DuckDuckGo telemetry gap
|
||
|
||
Current pixels do not include the exact system WebKit `CFBundleVersion`. The HTTP User-Agent cannot fill this gap because Apple returns the frozen `AppleWebKit/605.1.15` compatibility token.
|
||
|
||
Add one field to relevant crash and WebKit failure telemetry:
|
||
|
||
```text
|
||
webkit_build=22625.1.29.11.28
|
||
```
|
||
|
||
Populate it from `Bundle(for: WKWebView.self).CFBundleVersion`. This makes OS-build-to-WebKit correlation deterministic on both macOS and iOS.
|
||
|
||
## Sources
|
||
|
||
- [WebKit source repository](https://github.com/WebKit/WebKit)
|
||
- [Current WebKit version configuration](https://github.com/WebKit/WebKit/blob/main/Configurations/Version.xcconfig)
|
||
- [Safari 15 / WebKit 612 version configuration](https://chromium.googlesource.com/external/github.com/WebKit/webkit/+/refs/tags/Safari-612.1.27/Source/WebKit/Configurations/Version.xcconfig)
|
||
- [Safari 16 / WebKit 614 version configuration](https://chromium.googlesource.com/external/github.com/WebKit/webkit/+/refs/tags/WebKit-7614.1.25/Source/WebKit/Configurations/Version.xcconfig)
|
||
- [Safari 17 / WebKit 616 version configuration](https://github.com/WebKit/WebKit/blob/WebKit-7616.1.27/Configurations/Version.xcconfig)
|
||
- [Safari 27 / WebKit 625 version configuration](https://github.com/WebKit/WebKit/blob/WebKit-7625.1.29/Configurations/Version.xcconfig)
|
||
- [Ravel binary catalogue](https://ravel.dbg.re/browse)
|
||
- [MDN Safari release metadata](https://github.com/mdn/browser-compat-data/blob/main/browsers/safari.json)
|
||
- [Safari release notes](https://developer.apple.com/documentation/safari-release-notes)
|
||
- [WebKit commit 318982@main](https://commits.webkit.org/318982@main)
|
||
- [Safari Technology Preview 251](https://webkit.org/blog/18194/release-notes-for-safari-technology-preview-251/)
|
||
|
||
## Limits
|
||
|
||
- One OS major contains multiple WebKit updates; use the exact OS build for conclusions.
|
||
- Ravel is in beta and does not index every historical Apple build.
|
||
- Intel and Apple Silicon binaries may have different UUIDs.
|
||
- An exact public tag may appear after Apple ships the binary.
|
||
- Verify released code, not only commit ancestry, because fixes can be cherry-picked.
|