ma2tl:
macOS Forensic Timeline Generator
Using mac_apt Analysis Results
Japan Security Analyst Conference 2022
Internet Initiative Japan Inc.
Minoru Kobayashi

Who am I?

Minoru Kobayashi•••

Office of Emergency Response and Clearinghouse for Security Information,
Advanced Security Division, Internet Initiative Japan Inc.
Technical research, internal incident response
External Activities
Security Camp National Conference Speaker 2017-2019
Japan Security Analyst Conference Speaker 2018/2020
Black Hat USA 2018 Briefing Speaker
Twitter: @unkn0wnbit
2

Table of Contents

1. Motivation
2. How to create a timeline using theanalysis results of mac_apt
3. Implementation of ma2tl
4. Future work
5. Summary3

0Introduction

4

Introduction◦ The contents of this presentation are
all based on research and verification
conducted on Intel Macs.
◦ There may be some differences in
specifications on M1 Macs.
◦ However, in many respects, it could bediverted to investigate M1 Macs.
5

1

Motivation

6

The Need for Timelines in Forensics◦ What to do after collecting artifacts▪ Analyze OS and application artifacts with tools andcreate a timeline from the results.

◦ Purpose of creating a timeline▪ Understand the situation (suspicious points) of theaffected terminal.
▪ Organize the main activities of users, malware, andattackers based on timestamps.

▸Execute programs, download files, mount volumes, set
persistence, etc.

▪ Creating a timeline can reduce bias, leaps in thinking,and omissions in the research process.

7

Which tool to choose?

◦ Plaso▪ https://github.com/log2timeline/plaso▪ Automatic generation of super timelines▪ Capable of analyzing artifacts from various
operating systems, including macOS.
▪ Maintenance is active◦ Plaso can generate super timelines 🤩
% log2timeline.py --storage-file victim.plaso victim.E01% psort.py -o l2tcsv -w victime.csv victim.plaso
8Analyze with Plaso

It takes more than 4.5 days to process adisk image with a capacity of 30GB.
(For default settings)

9Super Timeline by Plaso

Mostly filesystem events

10

Problems with the super timeline generated by Plaso◦ All filesystem metadata is parsed by default.

▪ The number of unimportant files in the analysis is much higher.
▪ One file metadata is split into four events (MACB).

◦ The system log is recorded as a line by line event.

▪ We want meaningful information about what happened, not just line-byline events (we don't need just log messages).
▪ Unified Logs are not analyzed.

◦ As a result, most of the super timeline is filled with filesystem and system log events.
◦ It takes too long to complete the analysis in the first place.
◦ This is not the kind of information a forensic analyst wants tosee first.

11

The information the forensic analysts want and theinvestigation strategy◦ For malware infection investigation▪ Persistence setting status▪ Program execution history▪ Volume (USB thumb drives or disk images) mount▪ File Download◦ Make this kind of information the most basic timeline.
◦ Flesh out the timeline by expanding the scope of the investigationor conducting a deeper investigation as needed.

◦ We need a timeline to use as a basis for the investigation.
◦ Creating a timeline with only the necessary activities from theanalysis results of a tool focused on artifact analysis is more in linewith the requirements.
12

Tools focused on artifact analysis◦ There are two candidate analysis tools▪ AutoMacTC▸https://github.com/CrowdStrike/automactc▸Maintenance is stagnant.
▪ mac_apt▸https://github.com/ydkhatri/mac_apt▸Maintenance is active.

13

Which tool should we use?

◦ In view of the maintenance status andfunctionality, I recommend "mac_apt".
◦ Why is maintenance so important?

▪ macOS artifacts often change their file names andpaths with version upgrades.
▪ Using analysis tools that are not maintained will
increase the number of artifacts that cannot beanalyzed over time.

◦ Unified Logs parser is implemented.

▪ Unified Logs records a lot of useful information, but
only mac_apt has a parser implemented in OSS.

14

Motivation for creating the tool

◦ It is currently best to create a timeline that can be used as atemplate from the results of mac_apt analysis.
◦ To create a timeline from mac_apt analysis results, we needto refer to various tables.

▪ A table will be created for the number of plugins used in the analysis.
▪ Spotlight tables are cumbersome with many columns.

◦ Unified Logs contain useful information, but mac_apt does
not analyze them according to the message content.

▪ The message may change depending on the OS version upgrade.
▪ It is complicated to do a lot of filtering manually.
▪ Even with filtering, the output results may be large, and it may be difficult
to visually check.

◦ I need a tool that automatically generates a forensic
timeline!

15

Similar Tools◦ In terms of organizing, displaying, andchecking the results of mac_apt analysis, thefollowing tools also exist▪ mac_int▸https://burnhamforensics.com/projects/mac_int/▪ Building a Visualization Tool for mac_apt▸https://leahycenterblog.champlain.edu/2020/05/01/buildinga-visualization-tool-for-mac_apt/◦ Different in the following ways

▪ The main purpose of these tools is to check the resultsof mac_apt analysis in GUI, not to generate a timeline.
▪ No maintenance is being performed at this time.

16

2

How to create a timeline using theanalysis results of mac_apt

17Analysis results of mac_apt◦ DB where mac_apt stores the analysis
results▪ mac_apt.db : Results of artifact analysis▪ UnifiedLogs.db : Parsed Unified Logs
▪ APFS_Volumes_<GUID>.db : Parsed APFS
metadata▪ Export and SPOTLIGHT_DATA : Folder where
the artifact files exported from the disk image
will be saved
18mac_apt.db

There are as many tables as
plugins used in the analysis.

19

UnifiedLogs.db

You can apply filters equivalent to
the log command.

20

APFS_Volumes_<GUID>. db
You can check file timestamps, etc.,
but they are not formatted.

21

Timeline Creation Policy◦ Focus the investigation on analysis
results with time stamps.

▪ If timestamp is missing, refer to other tables or
APFS_Volumes_xxxx.db◦ Create a timeline for the following
activities▪ Persistence setting status▪ Program execution history▪ Volume mount▪ File Download
22

Persistence Analysis (1/3)◦ mac_apt.db : AutoStart▪ First, check the general user settings.
▪ No timestamp was recorded.

Autorun program

Autorun configuration file23

Persistence Analysis (2/3)◦ Check the timestamp of the auto-run
configuration file and the executablein APFS_Volumes_xxxx.db
SELECT * FROM Combined_Paths LEFT JOIN Combined_Inodes ON Combined_Paths.CNID = Combined_Inodes.CNID WHERE
Combined_Paths.Path = "/path/to/file" LIMIT 1;

File creation timestamp24Persistence Analysis (3/3)◦ Many autorun programs canbe found in the folders
listed on the right.
◦ Since macOS 10.15, thesystem volume and data
volume have been split.

Excerpt from the source code of ma2tl

Since macOS 10.15, it
is mounted as readonly, so there is little
risk of tampering.

System volume▪ The system volume is mounted

as read-only, so the risk oftampering is lower than before.
▪ Starting with macOS 11, thesystem volume is also signed.

◦ Therefore, programs on thesystem volume can be
excluded from theinvestigation at first

Data volume25

Program execution history analysis◦ mac_apt.db : SpotlightShortcuts
The string enteredin Spotlight▪ Applications executed via Spotlight will berecorded. (Only the date andTimestamp
time of the last execution.)
Application path

Application name26

Volume mount analysis◦ mac_apt.db : RecentItems

We can see thevolume name, but
not the timestamp.

◦ mac_apt.db : FsEvents

Modification date of the artifact file
(Not the timestamp)

Filtering conditions for volume mounts(create a folder under Volumes/)
27

File download analysis (1/5)◦ mac_apt.db : Quarantine▪ DB analysis results that store the same content as
the com.apple.quarantine extended attribute thatis assigned to files downloaded by web browsers,
etc.

Timestamp

Application name

Data download URL

Origin URL

28

File download analysis (2/5)◦ mac_apt.db : Safari▪ The destination of the file will be recorded.
▪ Since there is no timestamp, the timestamp is

inferred by linking the URL to the DataUrl in the
Quarantine table.
▪ Safari's download history is deleted after a day bydefault.
Data download URL

No timestamp

Local file path29

File download analysis (3/5)◦ mac_apt.db : Chrome

Data download URL

Origin URL

Download start timestamp

Local file path

Download completion timestamp30

File download analysis (4/5)◦ mac_apt.db : SpotlightDataView
Local file path

Data download URL

Download completion timestamp31

File download analysis (5/5)◦ No artifacts are left behind when files
are downloaded with the macOS
standard command "curl".

▪ It leaves traces of the curl execution itself, butdoes not tell us where it was accessed.

◦ In such cases, other investigations
such as malware analysis are also
necessary.

32

Information confirmed from mac_apt analysis results (1/2)◦ Persistence setting status▪ We know the autorun configuration file and the program to be autorun.
▪ We can also see the timestamps of the above files.

◦ Program execution history▪ We know which applications were executed via Spotlight.
▪ We know when it was last executed.
▪ There is no other execution history with timestamps.

◦ Volume mountNot enoughinformation.

▪ We know the name of the volume you mounted.
▪ The exact date and time of the mount is unknown.

◦ File Download▪ We know the date and time of the download, the URL from which it was
downloaded, and the file path to which it was saved.

33

Information confirmed from mac_apt analysis results (2/2)◦ The information in mac_apt.db alone
is clearly not enough to create atimeline◦ Any other data we should investigate?

34

"UnifiedLogs.db"
35

UnifiedLogs.db is a goldmine (1/5)◦ Unified Logs contains information necessary

to create a timeline, such as program
execution history and volume mount history,
which are not left in other artifacts.
◦ A veritable gold mine for macOS forensics◦ But for some reason, I almost never see
articles or blogs that explain this kind of
information.
36

UnifiedLogs.db is a goldmine (2/5)◦ Even commercial products parse
Unified Logs, but do not perform
analysis based on message content.
◦ Database load time, filtering time, etc.
are also slower than processing
UnifiedLogs.db.
37UnifiedLogs.db is a goldmine (3/5)

UnifiedLog will also be parsed.

Filtering is possible,
but the process is notvery fast.

38

UnifiedLogs.db is a goldmine (4/5)◦ log command% log show --predicate 'FILTERING CONDITION' --start 'YYYY-MM-DD hh:mm:ss' --end 'YYYY-MM-DD hh:mm:ss'◦ Filtering Keywords
eventTypeThe type of event: activityCreateEvent, activityTransitionEvent, logEvent, signpostEvent, stateEvent,timesyncEvent, traceEvent and userActionEvent.
eventMessage
The pattern within the message text, or activity name of a log/trace entry.
messageType
For logEvent and traceEvent, the type of the message itself: default, info, debug, error or fault.
process
The name of the process the originated the event.
processImagePath
The full path of the process that originated the event.
sender
The name of the library, framework, kernel extension, or mach-o image, that originated the event.
senderImagePath
The full path of the library, framework, kernel extension, or mach-o image, that originated the event.
subsystem
The subsystem used to log an event. Only works with log messages generated with os_log(3) APIs.
category
The category used to log an event. Only works with log messages generated with os_log(3) APIs. When
category is used, the subsystem filter should also be provided.

39

UnifiedLogs.db is a goldmine (5/5)◦ Unified Logs format
Timestamp

Thread ID

Activity ID
Log Type

TTL% log show --info --debug --predicate 'sender == "TimeMachine"'
Filtering the log data using "sender == "TimeMachine""
Timestamp
ThreadType
Activity
PID
2021-11-09 18:41:17.571449+0900 0x23fb85
Info
0x0
259
[com.apple.TimeMachine:General] Mountpoint '/Volumes/TimeMachine' is still valid

Subsystem

Category

Process Name

Process ID

Sender (Library)TTL
0backupd: (TimeMachine)

Event Message▪ In fact, it is displayed as a single line.
40

Investigating Unified Logs (1/13)◦ Program execution history (1)▪ Application Bundle (1)▪ macOS 10.15

Sender is "LaunchServices" and themessage starts with
"LAUNCHING:0x".

% log show --info --debug --predicate 'sender == "LaunchServices" AND eventMessage beginswith "LAUNCHING:0x"'
Filtering the log data using "sender == "LaunchServices" AND composedMessage BEGINSWITH "LAUNCHING:0x""
Startup source
Timestamp
ThreadType
Activity
PID
TTL
2021-07-26 12:56:05.393696+0900 0x77b0f8
Default
0x0
78164 0Evernote: (LaunchServices)[com.apple.processmanager:front-35286506] LAUNCHING:0x0-0x68c68c Safari foreground=1 bringForward=1 seed=7287 userActivityCount=02021-07-27 14:43:16.966842+0900 0x61b6f
Default0x0
4820Electron: (LaunchServices)[com.apple.processmanager:front-35286506] LAUNCHING:0x0-0xe50e5 Safari foreground=1 bringForward=1 seed=683 userActivityCount=02021-07-29 11:26:05.382074+0900 0x102e4d
Default
0x0
4980Dock: (LaunchServices)
Launched
application[com.apple.processmanager:front-35286506] LAUNCHING:0x0-0x189189 Safari foreground=1 bringForward=1 seed=1579 userActivityCount=02021-07-29 11:28:03.749083+0900 0x10362b
Default
0x029622 0open: (LaunchServices)[com.apple.processmanager:front-35286506] LAUNCHING:0x0-0x18e18e Safari foreground=1 bringForward=1 seed=1587 userActivityCount=041

Investigating Unified Logs (2/13)◦ Examples of startup source▪ Finder▪ Dock▪ Spotlight▪ loginwindow▸Applications that were executed when the "Reopen

windows when logging back in" checkbox was checkedin the logout dialog box and the user logged in again.
▸The application specified in "Login Items" under "Users& Groups".

▪ open▸If you run the application with the open command

42

Investigating Unified Logs (3/13)◦ Program Execution History (2)▪ Application Bundle (2)▪ macOS 11.0.1 - 12.0.1

The message changes to"LAUNCH: 0x".

% log show --info --debug --predicate 'sender == "LaunchServices" AND eventMessage beginswith "LAUNCH: 0x"'
Filtering the log data using "sender == "LaunchServices" AND composedMessage BEGINSWITH "LAUNCH: 0x""
Startup source
Timestamp
ThreadType
Activity
PID
TTL
2021-08-19 14:19:54.319840+0900 0x1676
Default
0x04270Dock: (LaunchServices)[com.apple.processmanager:front-35286506] LAUNCH: 0x0-0x3d03d com.apple.Maps starting stopped process.
2021-08-19 14:21:52.526205+0900 0x21fb
Default
0x04270Dock: (LaunchServices)[com.apple.processmanager:front-35286506] LAUNCH: 0x0-0x4d04d com.apple.Safari starting stopped process.
Launched
2021-08-19 14:48:38.978195+0900
0x186b application
Default
0x0
3880Dock: (LaunchServices)[com.apple.processmanager:front-35286506]
com.apple.MobileSMS starting stopped process.
(Application LAUNCH:
Bundle0x0-0x3e03e
ID)2021-08-19 14:57:09.230491+0900 0x246e
Default
0x0
3880Dock: (LaunchServices)[com.apple.processmanager:front-35286506] LAUNCH: 0x0-0x73073 com.apple.Safari starting stopped process.
2021-08-19 15:01:09.077054+0900 0x329
Info
0x0
153
0
loginwindow: (LaunchServices)[com.apple.launchservices:open] LAUNCH: 0x0-0x17017 com.apple.Terminal launched with launchInStoppedState=true, and not starting theapplication.
2021-08-19 15:01:09.228395+0900 0x329
Info
0x0
153
0
loginwindow: (LaunchServices)[com.apple.launchservices:open] LAUNCH: 0x0-0x18018 com.google.Chrome launched with launchInStoppedState=true, and not starting theapplication.

43

Investigating Unified Logs (4/13)◦ Behavior in macOS 11 and later (1)▪ Applications executed with the open command
will not be recorded.
▪ Bugs in macOS 11.6 (?)▸Logging does not occur unless the startup source is"loginwindow", "SystemUIServer", or"SoftwareUpdateNotificationManager".
▸macOS 11.6.1 and later are back to the same
specifications as 11.5.2 before.
▸Release notes for macOS 11.6.x have not been released,
so details are unknown.
● https://developer.apple.com/documentation/macosrelease-notes

44Investigating Unified Logs (5/13)◦ Behavior in macOS 11 and later (2)▪ When the startup source is "loginwindow".
▸Applications that are subject to "Reopen windows
when logging back in" will be logged as "Type =Info" and will only be logged in memory.

● The message contains "launchInStoppedState=true"▸Applications specified in the "Login Items" section of"Users & Groups" are logged as "Type = Default"
and will remain logged even after reboot.

Log of application executed with
"Reopen windows when logging back in".

% log show --info --debug --predicate 'sender == "LaunchServices" and eventMessage beginswith "LAUNCH: 0x"' --start '2022-01-14'
Filtering the log data using "sender == "LaunchServices" AND composedMessage BEGINSWITH "LAUNCH: 0x""
Timestamp
ThreadType
Activity
PID
TTL
2022-01-14 08:21:21.918761+0900 0x21efb
Info
0x0
4067
0
loginwindow: (LaunchServices) [com.apple.launchservices:open]
LAUNCH: 0x0-0x9ee9ee com.apple.Terminal launched with launchInStoppedState=true, and not starting the application.

45

Investigating Unified Logs (6/13)◦ Behavior in macOS 11 and later (3)▪ The first time you run an application downloaded fromthe Internet, Gakekeeper will be checked.
▪ The log will be recorded with "Type = Info" (recorded
in memory only).
▪ The message contains "launchInQuarantine == true".

% log show --info --debug --predicate 'sender == "LaunchServices" and eventMessage beginswith "LAUNCH: 0x"' --start '2022-01-14 13:00:00'
Filtering the log data using "sender == "LaunchServices" AND composedMessage BEGINSWITH "LAUNCH: 0x""
Timestamp
ThreadType
Activity
PID
TTL
2022-01-14 13:17:44.405335+0900 0x4786
Default
0x0
11240Dock: (LaunchServices) [com.apple.processmanager:front-35286506]
LAUNCH: 0x0-0xd80d8 com.apple.Safari starting stopped process.
2022-01-14 13:18:44.148002+0900 0x50ea
Info
0x0
1124
0
Dock: (LaunchServices) [com.apple.launchservices:open] LAUNCH:
0x0-0xeb0eb com.apple.DiskImageMounter launched with launchInQuarantine == true, so not starting the application.
2022-01-14 13:19:19.907199+0900 0x523c
Info
0x0
1127
0
Finder: (LaunchServices) [com.apple.launchservices:open] LAUNCH:
0x0-0xf10f1 com.ridiculousfish.HexFiend launched with launchInQuarantine == true, so not starting the application.
2022-01-14 13:21:21.389996+0900 0x5472
Default
0x0
1127
0Finder: (LaunchServices) [com.apple.processmanager:front35286506] LAUNCH: 0x0-0x100100 com.ridiculousfish.HexFiend starting stopped process.

Run the downloaded application(the first time).

Run the downloaded application(the second time).

46

Investigating Unified Logs (7/13)◦ Program Execution History (3)▪ If there is no application bundle ID (1)▸The application bundle ID is recorded as "(null)".
▸macOS 11 or later% log show --predicate 'eventMessage beginswith "LAUNCH: 0x"' --start '2022-01-12'
Filtering the log data using "composedMessage BEGINSWITH "LAUNCH: 0x""
Skipping info and debug messages, pass --info and/or --debug to include.
Timestamp
ThreadType
Activity
PID
TTL
2022-01-12 03:57:14.516187+0900 0x1693
Default
0x0
358
0Finder: (LaunchServices)[com.apple.processmanager:front-35286506] LAUNCH: 0x0-0x4d04d com.apple.DiskImageMounter starting stopped process.
2022-01-12 03:57:25.281130+0900 0x1d25
Default
0x0
358
0Finder: (LaunchServices)[com.apple.processmanager:front-35286506] LAUNCH: 0x0-0x50050 (null) starting stopped process.

47

Investigating Unified Logs (8/13)◦ Program Execution History (4) Filtered by process name "lsd",▪ No application bundle (2)▸Identify applications recorded as (null)message "Non-fatal error
enumerating", and time justbefore (null) was recorded% log show --predicate 'process == "lsd" and eventMessage beginswith "Non-fatal error enumerating"' --start '2022-01-12 03:57:24' -end '2022-01-12 03:57:26'
Filtering the log data using "process == "lsd" AND composedMessage BEGINSWITH "Non-fatal error enumerating""
Skipping info and debug messages, pass --info and/or --debug to include.
Timestamp
Type
PID
TTL
JustThread
before (null)is Activity
2022-01-12 03:57:25.245990+0900 0x18fd
Default
0x0
3572
lsd: (LaunchServices)
recorded(withinerror
about[com.apple.launchservices:default]
Non-fatalenumerating at <private>, continuing: Error Domain=NSCocoaErrorDomain Code=260"The file “PlugIns” couldn’t be 0.1
openedbecause there is no such file." UserInfo={NSURL=PlugIns/ -seconds?)
file:///Volumes/FakeTest/FakeApp.app/Contents/, NSFilePath=/Volumes/FakeTest/FakeApp.app/Contents/PlugIns,
NSUnderlyingError=0x7fc1edd290c0 {Error Domain=NSPOSIXErrorDomain Code=2 "No such file or directory"}}2022-01-12 03:57:25.255719+0900 0x18fd
Default
0x0
3572
lsd: (LaunchServices)[com.apple.launchservices:default] Non-fatal error enumerating at <private>, continuing: Error Domain=NSCocoaErrorDomain Code=260"The file “PlugIns” couldn’t be opened because there is no such file." UserInfo={NSURL=PlugIns/ -file:///Volumes/FakeTest/FakeApp.app/Contents/, NSFilePath=/Volumes/FakeTest/FakeApp.app/Contents/PlugIns,
NSUnderlyingError=0x7fc1edc2d550 {Error Domain=NSPOSIXErrorDomain Code=2 "No such file or directory"}}

application path48

Investigating Unified Logs (9/13)◦ Program Execution History (5)▪ Unsigned programs allowed to run by Gatekeeper▪ It also logs the mounting of unsigned DMGs.
▪ Logged only on first run.
▪ macOS 10.15 - 12.0.1% log show --info --debug --predicate 'category == "gk" and eventMessage BEGINSWITH "temporarySigning"'
Filtering the log data using "category == "gk" AND composedMessage BEGINSWITH "temporarySigning""
Timestamp
ThreadType
Activity
PID
TTL
2021-08-10 16:41:11.730226+0900 0x1dc9
Default
0x0
212
0
syspolicyd: (Security)[com.apple.securityd:gk] temporarySigning type=3 matchFlags=0x0 path=/Users/macforensics/Downloads/FakeTest2-bash.dmg
2021-08-10 16:41:26.286794+0900 0x206c
Default
0x0
212
0
syspolicyd: (Security)[com.apple.securityd:gk] temporarySigning type=1 matchFlags=0x0 path=/Volumes/FakeTest2-bash/FakeApp.app/Contents/MacOS/FakeApp

Programs with executepermission or mounted DMGs

49

Investigating Unified Logs (10/13)◦ Program Execution History (6)▪ adhoc signed program▪ macOS 10.15 - 12.0.1% log show --predicate '(process == "kernel" and eventMessage beginswith "AMFI: " and eventMessage contains " adhoc ") or (process =="amfid" and eventMessage contains "signature")'Filtering the log data using "(process == "kernel" AND composedMessage BEGINSWITH "AMFI: " AND composedMessage CONTAINS " adhoc ") OR(process == "amfid" AND composedMessage CONTAINS "signature")"Skipping info and debug messages, pass --info and/or --debug to include.
executed program has
Timestamp
ThreadType
Activity
PID TheTTL
2022-01-19 16:06:09.001258+0900 0x3753
Default
0x0
00an adhoc
kernel: (AppleMobileFileIntegrity)
AMFI:
signature.
'/Users/macforensics/Downloads/SysJoker/types-config.ts' is adhoc signed.
2022-01-19 16:06:09.002729+0900 0x1c8c
Default
0x0
215
0
amfid:/Users/macforensics/Downloads/SysJoker/types-config.ts signature not valid: -67050

The executed program has
an invalid signature.
50

Investigating Unified Logs (11/13)◦ Program Execution History (7)▪ Deny execution by security policy
Message contains "Security policy▪ macOS 10.15
would not allow process% log show --predicate 'eventMessage contains "Security policy would not allow process"'
Filtering the log data using "composedMessage CONTAINS "Security policy would not allow process""
Skipping info and debug messages, pass --info and/or --debug to include.
Timestamp
ThreadType
Activity
PID
TTL
2022-01-12 02:35:12.569186+0900 0xa980
Default
0x0
00kernel: (AppleSystemPolicy) Security policy
would not allow process: 822, /Users/macforensics/Downloads/floss

Program refused to run▪ macOS 11.0.1 - 12.0.1

You can search using the same criteria
as macOS 10.15, but the message
formatting will be slightly different.

% log show --info --debug --predicate 'eventMessage contains "Security policy would not allow process"'
Filtering the log data using "composedMessage CONTAINS "Security policy would not allow process""
Timestamp
ThreadType
Activity
PID
TTL
2021-08-20 17:26:24.667681+0900 0x1b6ba
Default
0x0
00kernel: (AppleSystemPolicy) ASP: Security
policy would not allow process: 2954, /Users/macforensics/Downloads/floss

Added since macOS 11.

51

Investigating Unified Logs (12/13)◦ Volume Mount (1)▪ macOS 10.15 - 12.0.1▪ HFS+The message contains "mounted"
or "unmount".

% log show --info -debug --predicate 'process == "kernel" AND (eventMessage CONTAINS[cd] "mounted" OR eventMessage CONTAINS[cd]"unmount")'
Filtering the log data using "process == "kernel" AND (composedMessage CONTAINS[cd] "mounted" OR composedMessage CONTAINS[cd]"unmount")"
mountedfile system
Timestamp
ThreadType
Activity
PID
TTL
2022-01-08 01:06:05.705926+0900 0x5d2a6
Default
0x0
00kernel: (HFS) hfs: mounted Script Debugger
8.0 on device disk4s2
2022-01-08 01:06:12.082076+0900 0x5d4e9
Default
0x0
00kernel: (HFS) hfs: unmount initiated on
Script Debugger 8.0 on device disk4s2

Volume nameunmount52

Investigating Unified Logs (13/13)◦ Volume Mount (2)▪ macOS 10.15 - 12.0.1▪ APFS (same filtering conditions as HFS+)% log show --info -debug --predicate 'process == "kernel" AND (eventMessage CONTAINS[cd] "mounted" OR eventMessage CONTAINS[cd]"unmount")'
Filtering the log data using "process == "kernel" AND (composedMessage
CONTAINS[cd]"mounted"Local
snapshots
can OR composedMessage CONTAINS[cd]"unmount")"
bePID
ignored.
Timestamp
ThreadType
ActivityTTL
2022-01-08 01:04:48.911752+0900 0x5cfc7
Default
0x0
00kernel: (apfs) apfs_vfsop_unmount:2441:
disk1: unmounting volume 'com.apple.TimeMachine.2022-01-08-000409.local'
2022-01-08 01:04:48.911778+0900 0x5cfc7
Default
0x0
00kernel: (apfs) apfs_vfsop_unmount:2733:
snapshot deletion completed on the livefs
2022-01-08 01:04:48.911782+0900 0x5cfc7
Default
0x0
00kernel: (apfs) apfs_vfsop_unmount:2798:
nx_num_vols_mounted is 5
Mount orunmount
Volume0x0
name2022-01-08
01:04:48.911788+0900
0x5cfc7
Default
00kernel: (apfs) apfs_vfsop_unmount:2807: all
done. going home. (numMountedAPFSVolumes 44)
file system2022-01-08 01:07:39.919784+0900 0x5d869
Default
0x0
00kernel: (apfs) apfs_vfsop_mount:2234:
disk5s1: mounted volume: FakeTest2-bash
2022-01-08 01:07:45.865955+0900 0x5d9f4
Default
0x0
00kernel: (apfs) apfs_vfsop_unmount:2441:
disk5: unmounting volume 'FakeTest2-bash'

53

3

Implementation of ma2tl

54

ma2tl implementation policy (1/2)◦ mac_apt to timeline → ma2tl◦ Support for macOS 10.15 or later◦ Automate the verification procedure for each of theactivities mentioned above.

▪ If the analysis result has timestamps, create events from the main
data.
▸mac_apt.db : SpotlightShortcuts▪ If the analysis result does not have timestamps, create events byassociating it with a table of relevance.
▸mac_apt.db : AutoStart + APFS_Volumes_xxxx.db▸mac_apt.db : Safari + Quarantine▪ Filtering UnifiedLogs.db to extract necessary information frommessages55

ma2tl implementation policy (2/2)◦ Implement analysis plugins for each type of activity.

▪ Activities may be recorded across multiple analysis results, andinformation needs to be integrated to be output as a timeline.
▪ If you need a new activity, just add a new plugin◦ Replace Unified Logs event messages with content
whose meaning is easy to understand.
◦ Specify the timeline time range manually.

▪ I don't want a super timeline, but a minimum timeline that can beused as a starting point for investigation.
▪ Specify the range of dates and times that the forensic analysts
are interested in.

56

Configuration of ma2tl

📜Analysis resultsof mac_apt

mac_apt.db
UnifiedLogs.db
APFS_Volumes_xxxx.db

Read⚙ma2tl
Invoke[🔌Plugins].
🚀Program Execution
🤿Persistence🔽File Download
🗻Volume Mount📰ma2tl result
OutputSQLite
XLSX
TSV

57

Plugin implementation example: File download

2) Extract the data.

1) Configure the information
required for the filedownload events from the
Safari and Quarantine tables
in mac_apt.db.

3) Determine the duplication.

4) Add to timeline.

58Plugin implementation example: Volume mount

1) Filter the logs ofvolume mounts.

Volume names to ignore
Regular expressions of
the message when thevolume is mounted

2) Extracting volume namefrom messages using
regular expressions

59

Execution example
The path where the results of
mac_apt analysis are stored.

Output destination
for ma2tl

Time range of the timeline
to be generated% python ./ma2tl.py -i ~/Documents/test -o ../ma2tl_output/test -s '2022-01-13 11:00:00' -e '202201-13 11:59:59' ALL
Output path: /Users/macforensics/Documents/GitHub/ma2tl_output/test
Plugins to use
MA2TL-INFO-Command line: ./ma2tl.py -i /Users/macforensics/Documents/test -o ../ma2tl_output/test -s
ALL: All plugins
2022-01-13 11:00:00 -e 2022-01-13 11:59:59 ALL
MA2TL-INFO-Input path : /Users/macforensics/Documents/GitHub/forked/mac_apt_out/test
MA2TL-INFO--------------------------------------------------MA2TL-INFO-Running plugin FILE_DOWNLOAD
Plugin output
MA2TL.PLUGINS.FILE_DOWNLOAD-INFO-Detected 1 events.
MA2TL-INFO--------------------------------------------------MA2TL-INFO-Running plugin PERSISTENCE
MA2TL.PLUGINS.PERSISTENCE-INFO-Detected 8 events.
MA2TL-INFO--------------------------------------------------MA2TL-INFO-Running plugin PROG_EXEC
MA2TL.PLUGINS.PROG_EXEC-INFO-Detected 2 events.
MA2TL-INFO--------------------------------------------------MA2TL-INFO-Running plugin VOLUME_MOUNTMA2TL.PLUGINS.VOLUME_MOUNT-INFO-Detected 2 events.
60

Example of analysis results◦ Timeline of Script Debugger downloaded,installed, and run on macOS 11.5.2.

Timestamp (user-specified time zone)
Default: system local
Timestamp (UTC)

Launch Safari

Activity Type

Activity Description

Plugin name

Since it is macOS 11, theScript Debugger firsttime startup artifacts are
not left behind.

Download a DMG
Volume mount
Launch System Preferencesfrom Script Debugger
61

ma2tl demo
62

ma2tl demo scenario

1) Download a malware
downloader disguised as a tool.
2) Run the downloader.

⚙ 💻 Victim

👾
😈 Attacker's server

macOS 10.15.5

🚀4) Execute the malware
and set persistence.

👹
3) Download a malware.

63

ma2tl demo timeline3) 👹The malware was downloaded using curl, so it
is not included in the timeline generated by ma2tl.

1) 👾

2) ⚙
adhoc signed4) 🚀The path of the autorun program
is not a standard folder.
64

4

Future work

65

Future work

◦ Support for more mac_apt analysis results▪ Analysis results with timestamp▪ Analysis results showing timestamps in combination with
APFS_Volumes_xxxx.db◦ Ongoing investigation of Unified Logs

▪ Application Execution▪ Program refused to be executed by the system▪ exFAT, NTFS, SMB volume mount◦ Optimize the timeline to be generated▪ Eliminate duplicate events▪ Expand the scope of events to include cautionary messages.

◦ Maintenance▪ Will newer versions of macOS still record log messages that ma2tl canrecognize?

66

5

Summary67

Summary◦ Shared how to create a timeline from

mac_apt analysis results and Unified Logs.
◦ Introduced the implementation andfunction of ma2tl.
▪ Automatic generation of timeline from mac_apt
analysis results and Unified Logs
▪ More activities can be supported by plugins.

◦ ma2tl GitHub repository▪ https://github.com/mnrkbys/ma2tl
68

Thank you for listening!

Any questions?
69

CREDITS for this presentation template and Icons

Special thanks to all the people who made andreleased these awesome resources for free:◦ Presentation template by SlidesCarnival70