Thesis Friday #6: Acquiring the Apple Unified Log – Terminal

Why use the terminal?


I write this guide based on years of experience as a digital forensic specialist. What you’re reading is not just a general how-to. It’s the exact approach I use in my own investigations, including when working with reference datasets.

Apple’s Unified Logging system records events in a binary format from various sources — system processes, user applications, background daemons, and kernel extensions. It’s structured and indexed, but also extremely verbose. The log-command provides direct, scriptable access to this data, allowing for precise filtering without relying on a GUI or dealing with limited export capabilities.

There are excellent tools available that can help you extract and interpret this data. But in this case, I want to focus on understanding what those tools actually do under the hood. How they acquire the data, step by step.

What do you need?

Terminal commands

In this command we will acquire the AUL from a device that is connected to the macOS device:

$ sudo log collect --device --output /path/to/filename.logarchive

Let’s break this down:

  • sudo Required for elevated privileges. Without it, the system won’t allow access to protected log data.
  • log collect This tells macOS to initiate a collection of the Unified Log.
  • –device This flag specifies that you’re collecting logs from a connected device (e.g. an iPhone or another Mac in target disk mode). ⚠️ Without this flag, the command collects logs from the local system by default.
  • –output /path/to/filename.logarchive This defines the destination and filename for the log archive. Example: ~/Desktop/target_logs.logarchive

To maintain a clean audit trail and support chain-of-custody documentation, Apple provides additional parameters:

  • –device-name Use this to specify the name of the connected device. This is the human-readable device name shown in Finder or Apple Configurator.
  • udid This is the universally unique identifier assigned to the device by Apple. Unlike the name, the UUID cannot be modified by the end user and is ideal for forensic tracking. 

We now have an evidence file: a .logarchive bundle acquired directly from the target device. This file is considered our original.

From this point forward, we do not touch the original file.

Instead, we work exclusively with forensic copies to preserve integrity and avoid accidental modification. This is a standard practice in digital forensics, always protect your source, always document your workflow. You can hash the file for chain of custody integrity.

Preparing the logarchive for analysis

Now that we’re working from a forensic copy of the original .logarchive, we can start slicing the data. This is ideal for timeline reconstruction, correlation with other sources, or import into forensic tools. It also dramatically reduces file size compared to dumping the entire .logarchive.

Extracting a timeline

Let’s say you want to narrow your focus to a specific timeframe. You can extract only the log entries between two timestamps using the –start and –end flags:

$ log show --archive /path/to/working_copy.logarchive --start "2025-05-27 12:00:00" --end "2025-05-27 13:00:00" > filename.log

Let’s break it down:

  • log show This is the base command used to read and display log data from either the live system or an archive.
  • –archive /Path/to/working_copy.logarchive Specifies the path to the .logarchive file we’re analyzing. In this case, it’s the forensic working copy.
  • –start “2025-05-27 12:00:00” Sets the beginning of the time window you want to extract. This means: only show log entries after this timestamp.
  • –end “2025-05-27 13:00:00” Sets the end of the time window. Together with –start, this extracts exactly one hour of log activity.
  • > filename.log Redirects the output of the command to a file named scoped.log. This keeps your Terminal clean and saves the result for further analysis or archiving.

Convert the .logarchive to json

If you need to work with the log data in a structured format, for example to import it into a forensic timeline tool or parse it with Python. You can convert the .logarchive to JSON. The –style json flag outputs each log entry as a structured JSON object, and adding –info includes metadata about the archive.

Keep in mind: JSON exports grow fast. Always define a narrow time window to avoid creating massive files.

$ log show --archive /path/to/working_copy.logarchive --start "2025-05-27 12:00:00" --end "2025-05-27 13:00:00" --style json --info > filename.json

Let’s break it down:

  • log show The base command for reading logs.
  • –archive /path/to/working_copy.logarchive Points to the .logarchive copy you’re analyzing.
  • –start “2025-05-27 12:00:00” and –end “2025-05-27 13:00:00” Limits the output to a 1 hour time window. Always use these to reduce volume and keep your dataset relevant.
  • –style json Converts the log entries into structured JSON format — ideal for automation, searching, or parsing in other tools.
  • –info Includes additional metadata (e.g. timezone info, archive context, system information). This can be valuable in forensic scenarios where context matters.
  • > filename.json Redirects the output to a .json file on disk.

⚠️ Warning: File Size Can Explode

JSON exports are not compressed and contain verbose field names. Even a short time window can result in unexpectedly large files.

I will cover soon how to do your analysis on the AUL with tools and without.