The Small Company in Europe Caught in the Big Trade War Between the U.S. and China
© Peter Dejong/Associated Press
© Peter Dejong/Associated Press
Sometimes apps that should run fine seem to find problems where there shouldn’t be any, becoming slow to launch, unable to update, erratic, and easily crashed. One reason that can account for these is that the app has become stuck in translocation. This article explains how you can check that, and what you can do to solve it and restore the app’s normal function.
App translocation, or Gatekeeper Path Randomisation (GPR), is a security mechanism intended to disrupt malicious code that’s dependent on its immediate location, perhaps to access other code in plugins. When a new quarantined app is run from the same folder it came in, it’s copied to a random path that appears as a volume, typically hidden at something like /private/var/folders/x4/[random chars]/T/AppTranslocation/[UUID]/d/, and run from there. However, it’s only present there while it’s running, and the moment you quit the app that location is unmounted, and vanishes.
In theory, translocation shouldn’t affect an app, but when it occurs repeatedly, it’s likely to prevent it from updating itself, and have other adverse effects. When an app has been translocated once, unless something is done to prevent further translocation, it’s likely to suffer the same fate every time it’s run, so becoming stuck in translocation.
To determine whether an app is being run from translocation, you need to discover the path of its executable when it’s running. That’s simple to do using Activity Monitor:
If the path starts with anything like /private/var/folders/x4/[random chars]/T/AppTranslocation/[UUID]/d/, then the app is being run in translocation.
If you’d prefer to perform this in Terminal instead, run the app, then enter the commandps xw | grep AppName
to see its executable path. This was suggested by Quinn “The Eskimo!” of Apple’s Developer Technical Support.
App translocation occurs when all the following apply:
One common error that falls foul of those rules is when two or more apps are moved together from the Downloads folder into Applications, and another is to move an app inside the same folder it came in, into Applications.
Although you can strip the com.apple.quarantine extended attribute from the app, it’s simpler and better practice to:
Future updates should then work fine, and the app should be spared any further translocation.
Apple has just released its weekly update to XProtect, bringing it to version 5319. As usual, it doesn’t release information about what security issues this update might add or change.
This version adds three new Yara rules. MACOS.SOMA.OCENA is yet another for the vast Soma/Amos family, and there are two for the far newer MACOS.ODYSSEY group, MACOS.ODYSSEY.SOCGO and MACOS.ODYSSEY.SEENA.
You can check whether this update has been installed by opening System Information via About This Mac, and selecting the Installations item under Software.
A full listing of security data file versions is given by SilentKnight and SystHist for El Capitan to Tahoe available from their product page. If your Mac hasn’t yet installed this update, you can force it using SilentKnight or at the command line.
If you want to install this as a named update in SilentKnight, its label is XProtectPlistConfigData_10_15-5319
This update has already been released for Sequoia and Tahoe via iCloud. If you want to check it manually, use the Terminal commandsudo xprotect check
then enter your admin password. If that returns version 5319 but your Mac still reports an older version is installed, you should be able to force the update usingsudo xprotect update
Some who use SilentKnight for the first time discover that their Mac has been running for months with one of its security systems disabled. As macOS doesn’t have a dashboard to warn you of such dangerous settings, you may not notice until it’s too late. This article explains how to check those essential security settings on Macs with T2 or Apple silicon chips, and how to put them right. Intel Macs without T2 chips are different, and are covered in a previous version.
Running your Mac in Full Security ensures it gets full protection from its Secure Boot technology. In an Apple silicon Mac this prevents it from loading third-party kernel extensions, and requires recent approved versions of macOS. Check this in System Information by selecting the Controller item in its Hardware section, or in SilentKnight.
This is controlled in Startup Security Utility, accessed from Recovery. Note that it only works with the paired Recovery system, the one you normally use; Apple silicon fallback Recovery doesn’t have this ability.
If you need to run kernel extensions or other software that can’t be loaded in Full Security, use Startup Security Utility to set the Mac to Reduced Security, and enable kexts. Avoid doing this if at all possible.
Settings are different for Intel Macs with T2 chips, where there are three levels of boot security, and the most common reason for reduction from Full Security is to enable that Mac to boot from external drives, something that Apple silicon Macs can do in Full Security.
Since El Capitan, macOS has protected all its system files, even down to bundled apps, using System Integrity Protection. This should make it impossible for malware or other software to change those protected files. SIP is also required for a wide range of other security protection, and should be fully enabled unless you have a compelling reason for disabling it partially or completely. In Apple silicon Macs, its status is reported in System Information’s Controller item, but Intel Macs instead give it in the Software section. It’s also checked by SilentKnight and Skint.
You can turn SIP off, something very occasionally needed to perform certain essential tasks. Doing so requires you to start up in Recovery mode, enter a command in Terminal there, and restart; Apple silicon Macs also need to have their boot security reduced in Startup Security Utility before SIP can be disabled.
To enable SIP, start up in Recovery mode, open Terminal, and type the following command:csrutil enable; reboot
Once that’s done your Mac will restart in normal mode, and you should confirm that SIP is reported as enabled.
If you ever do need to disable SIP, do yourself a favour and put a sticky note on your Mac’s display to remind you to turn it back on.
Gatekeeper runs checks on apps when they’re opened, and those can include scans for known malicious software using XProtect. As part of your Mac’s frontline protection against malware, you should leave those enabled unless there’s a compelling reason to temporarily disable them. However, I don’t know of anywhere in the macOS GUI that informs you whether these checks are being performed, although they are reported by SilentKnight and Skint.
If it has been disabled, you may be able to enable it using the commandspctl --enable
but chances are that you will instead need to invokesudo spctl --global-enable
requiring you to authenticate using your admin password. Be careful with those commands: the hyphens before enable and global-enable aren’t long dashes, but two separate hyphens.
When you install Big Sur or later, the vast majority of its system files are saved in its System volume. For your Mac to boot from this, it has to be turned into a snapshot, sealed using a tree of cryptographic hashes, and the master seal ‘signed’ by a hash, which is compared against that set by Apple. This signed system volume is extremely secure and thoroughly reliable. On Intel Macs, this is only reported in Disk Utility, but Apple silicon Macs list it in System Information as well. It’s also reported by SilentKnight and Skint.
The SSV should always be enabled. If it isn’t, you’ll need to re-install macOS.
Intel Macs with T2 chips and Apple silicon Macs encrypt the whole of the Data volume on their internal SSD. By default, that uses an internally-generated key that’s used automatically when any user logs in. Although it provides good security in most situations, you’re far better off enabling FileVault, as that protects the encryption key with your password as well. This imposes no overhead on accessing encrypted data, and provides valuable protection for your data at no cost.
Check whether FileVault is enabled in Privacy & Security settings, where you can enable it if it’s not already turned on. SilentKnight checks it as well.
To ensure your Mac and its apps are best protected from malware, keep its firmware and macOS up to date. As those are updated together, Macs with T2 or Apple silicon chips that are running the most recent release of their major version of macOS will also be running the current firmware, which no longer needs to be checked separately. Check the version of macOS in the About This Mac command at the top of the Apple menu.
Apple lists current supported versions of macOS on its Security Releases page. Those, and versions of security data software, are also listed and detailed here on this page.
If your Mac is running an older release of macOS and its firmware, update them together using Software Update in General settings.
This anti-malware scanner performs automatic background scans to detect and remove a wide range of malicious software. It’s normally scheduled to run at least once a day, when your Mac is awake but not busy, and supplied with mains power. You’re wise to check that its scans are being run correctly, and will probably want to know if it has detected and remediated any malware. SilentKnight and Skint run a quick check of its activity over the previous 36 hours, and XProCheck provides detailed reporting and analysis.
Over the last year or so, XProtect Remediator has been using a timer during its scans, and automatically cancelling them if a scan takes longer than allowed. On many Macs, most scans are terminated early, and that results in warnings from SilentKnight and Skint. If you’re concerned, check the reports in XProCheck, where you’ll see that plugin was cancelled with a status_code of 30, as is typical with the timer.
SilentKnight does all of those and more.
The greatest challenge in using the Unified log is how to navigate its many thousands of entries, to find those you want to read. Success depends on the combination of two aids: time and waypoints (or landmarks).
No matter how you obtain log extracts, you need to know when to look for those entries. The more precisely you can work out the time of interest, the quicker and easier it will be to locate the entries you’re interested in. While the log
command offers alternatives, LogUI works throughout using the local time applicable when you access the log, allowing for your current time zone and any seasonal adjustment to it, when accessing the live log in that Mac.
However, the underlying times given in log extracts are those recorded by the Mac or device whose log you’re accessing. If its system clock was five minutes slow when those entries were written to its log, then you need to allow for that. For example, when I first started my Mac yesterday its clock might have been 1 minute slow. An event that occurred at 10:56 yesterday by the room clock would therefore appear in the log entries for 10:55.
One important time you can discover is the boot time of the Mac. Mints offers a Boot button to retrieve boot times over the last 24 hours. If the logs were written by a different Mac or device, then you’ll need to search for the time of that last boot. Fortunately the first two log entries are easily recognised:11:41:37.562774+0100 === system boot: D3CEA9B4-F045-434D-8D12-C6E794A02F14
11:41:42.758780+0100 kprintf initialized
The long gap between the first two entries is accounted for by the firmware phase of the boot process. If necessary you can search for a message containing ===
(three equals signs). Mints provides the time of the first of those for each boot, and its UUID.
There are two occasions when time can become confusing, when clock corrections are applied, and when clocks are moved forward or back to add or remove summer or seasonal time changes. Fortunately the latter only change twice each year, although when they do, you really don’t want to see what happened in the log, and those changes aren’t even applied at a predictable time.
Clock corrections, like kernel boot, are readily found by the ===
text in their message. They normally happen in pairs, with the first correction the larger, and the second often far smaller. Here’s an example seen in consecutive log entries:08:26:16.140474+0100 /usr/libexec/sandboxd[80] ==> com.apple.sandboxd
08:26:10.043353+0100 === system wallclock time adjusted
08:26:10.044335+0100 Sandbox: distnoted(72) deny(1) file-read-metadata /private
08:26:10.044601+0100 2 duplicate reports for Sandbox: distnoted(72) deny(1) file-read-metadata /private
08:26:10.044606+0100 Sandbox: distnoted(72) deny(1) file-read-metadata /Library
08:26:10.089204+0100 === system wallclock time adjusted
08:26:10.091850+0100 started normally
The first adjustment dropped the clock back by 6.1 seconds, from 08:26:16.140474 to 08:26:10.043353. This means that you’ll see times of 08:26:12 both before the correction and afterwards. The second adjustment, from 08:26:10.044606 to 08:26:10.089204, was far smaller at 0.045 seconds, and at least went in the right direction.
The most substantial clock corrections are made shortly after booting. Although macOS does make them later, the size of those should be smaller.
Even working with times resolved to the second, those can still leave you browsing thousands of log entries. To locate more precisely you need details of one or more entries that will be sufficiently distinctive to focus in on a few dozen. These are waypoints for navigation.
LogUI provides three methods for locating these waypoints:
These are best used when the time period of your extract needs to be relatively long, so would return a large number of entries. For example, if you can only narrow the time down to several minutes, and are looking for the time that a specific app was launched, you can look for that app’s job description when it’s created and written to the log by RunningBoard.*
Over a period of two minutes, RunningBoard might write thousands of entries in the log, so looking for your app’s job description among them would be time-consuming. Set the start time and period to cover the whole of the time you want to search, then set a predicate for the subsystem com.apple.runningboard
.
When LogUI fetches that log extract, there might still be over 2,000 entries, so now is the time to apply search text to filter those further.
To filter those 2,000 entries and show only those containing job descriptions created by RunningBoard, enter the text constructed job
in LogUI’s search box, with its menu set to Messages, and press Return. You’ll now see that list reduced to just a handful, and looking through them you can discover exactly when your waypoint occurred.
My example for this article starts with a period of just 2 minutes, in which there were more than 100,000 log entries.
Using the com.apple.runningboard
predicate whittled those down to 13,443 entries.
Searching within those for constructed job
left me with just 8 entries to look through.
Sometimes you can’t devise the right combination of predicate and search filter to discover what you’re looking for, which might be an error reported in a subsystem or a process that you can’t identify. One good way forward is to narrow your log extract as much as you can, then save the extract as Rich Text, open that in a suitable editor, and search through it for the word error
. That will discover every log entry containing the word error
anywhere, rather than confining it to the message text.
Armed with your waypoint and the exact time of its entry in the log, you can now set that as the start time, set a period of a couple of seconds, and get a full log extract containing all the detail you might need. This should give you further clues to allow you to move through time using predicates and search filters to discover what happened. This is much quicker and less frustrating than trying to scan through thousands of log entries in search of vague clues.
* Sadly, the days of being able to access freely RunningBoard’s informative job descriptions in the log are over. As of macOS Tahoe, all you’ll see is the dreaded <private> of censorship. If you want to examine these now, you’ll have to remove log privacy protection first. Thanks, Apple, for providing such useful tools then rendering them next to useless.
I hope that you enjoyed Saturday’s Mac Riddles, episode 329. Here are my solutions to them.
Two credentials (two-factor authentication uses two secrets, such as a password and a PIN code sent separately) or 762 (0x2FA in decimal) should be superseded by passkeys (a modern and more secure replacement).
Notably from Autodesk (vendors of AutoCAD and other computer-aided design software) but once by Claris (ClarisCAD, 1989-1991), it’s 3,245 (0xCAD in decimal).
From the Mac II (Apple Desktop Bus, introduced as the peripheral interface for Mac II and SE) until replaced by USB (it was, with the iMac), 2,779 (0xADB in decimal) was quite enough (it didn’t support hot-swapping, which could result in electrical damage).
They are all hexadecimal numbers as well as abbreviations.
I look forward to your putting alternative cases.
One of the longstanding oddities in macOS security has been scanning of a notarized app by XProtect before it can be launched. When apps are submitted to Apple for notarization, they’re scanned for malicious content using methods at least as effective as XProtect, and should any notarized software subsequently be identified as malicious, its notarization and signature are revoked immediately. That should make it impossible for any app with a valid notarization ticket to contain malware known to Apple.
One of the improvements believed to be incorporated into macOS 26 Tahoe is that validly notarized apps are no longer scanned by XProtect. When I examined this recently, I confirmed that was correct, although in practice this did little if anything to improve the launch times of apps. This article extends those observations to include app first run, when detection of malware is most critical.
When an app is run for the first time in a recent version of macOS, there are three options:
This article considers the second and third of those.
In Sequoia 15.7 these apps undergo a “direct malware and dylib scan” using the XProtect data stored in its new location, in /var/protected/xprotect/XProtect.bundle. Because this is the first run, once Gatekeeper assessment is complete and confirms the app is safe to run, the user is presented with a dialog asking for their consent. Because of the inevitable delay in responding to that, two times can provide meaningful estimates of performance:
In Tahoe 26.0 no XProtect scan was attempted, as com.apple.xprotect entered in the log “Xprotect is skipping executable assessment”, and com.apple.syspolicy.exec confirmed “Skipping XProtect scan on seen software”. Despite that, the first of those times was nearly twice that required in Sequoia, at 10.29 seconds. The reason for this is unknown, but over that period the log contained about 13,000 entries reporting “SecKeyVerifySignature”.
As a result, a smaller and simpler app was used to test app translocation and its effects.
Instead of using Calibre as my test app here, I chose my own app Podofyllin, with its 442 KB executable and no dylibs or other complications. This was downloaded from here, unarchived automatically in the ~/Downloads folder and there run from the folder it came in, to ensure that it would be translocated.
Early in the launch sequence, com.apple.securityd writes a log entry indicating it has created the translocation directory “SecTranslocateCreateSecureDirectoryForURL”, following which diskarbitrationd
replicates the app bundle to what appears as a different volume in the translocation path. Then a first run Gatekeeper assessment is performed, including an XProtect scan, checking the notarization ticket using CloudKit, a user approval dialogue, and setting up the app’s provenance tracking.
In Sequoia 15.7, the XProtect scan took 0.15 seconds, and the total period required for the Gatekeeper scan was 0.19 seconds.
In Tahoe 26.0, com.apple.syspolicy.exec logged “Skipping up front XProtect scan” and com.apple.syspolicy went straight on to perform the CloudKit lookup. This was confirmed later by com.apple.syspolicy.exec in “Skipping XProtect scan on seen software” just before reporting the Gatekeeper scan was complete. With no time required for the XProtect scan, the total used for the Gatekeeper scan was 0.16 seconds, 88% of that for Sequoia.
Over the last couple of years it has become clear that some apps, even though they have been moved from their original download location, continue to undergo translocation whenever they’re run, and that can cause ongoing problems.
An app will be translocated if all the following apply:
Tests in recent macOS show that apps won’t be translocated if:
The following will normally result in the app being run in translocation:
You can readily check whether an app is being run in translocation by starting the app and either:
ps xw | grep AppName
in Terminal.If the path shown for the app is something absurdly long like /private/var/folders/x4/[random chars]/T/AppTranslocation/[UUID]/d/, then it has been translocated.
If an app that appears to have been correctly installed is still being translocated, move it individually (one app at a time) from the folder it’s currently in to a different folder, run it from there, close the app, and move it back to where you want to keep it.
Among the foundations of visual design are two essential insights, into understanding human vision, and the experience gained from our long history of visual communication. Common to both is the importance of tone (brightness, lightness, etc.) and its contrasts. Not only do around one in twenty males struggle to distinguish some or most colours, but all of us rely on tone to interpret what we see in the absence of information from colours.
This has been illustrated throughout the history of visual art, where those who have excelled in visual communication have placed particular emphasis on tone. Consider Lucas Cranach the Elder (1472–1553) as an example of proven classical methods.
We know a lot about the tonal modelling that Cranach used in his Martyrdom of Saint Catherine painted in 1504-5, through the infra-red reflectogram below, which effectively looks through the paint layer at the underdrawing beneath.
Cranach’s assistants first laid a thin layer of light reddish imprimatura on the white ground of this panel. Once that had dried thoroughly, Cranach himself would have laid down the underdrawing using a pointed brush with carbon black ink. This extended to the tonal modelling shown clearly in the reflectogram.
Following that came undermodelling using grey tones of carbon black and lead white. Some of the darker garments were preceded by a local underpainting of black, a technique popular at the time for dark red fabrics in particular. Much of this seems to have been completed quickly, probably within a single day.
A common practice among masters discards colour altogether and builds the image using tone alone, known as grisaille.
Three centuries after Cranach, the great French illustrator and painter Gustave Doré (1832–1883) painted a group of three works about the Franco-Prussian War entirely in grisaille. Best known among those is The Enigma (souvenirs de 1870), from 1871.
Even a few minutes exposure to a screenful of macOS Tahoe’s windows demonstrates how its new design goes out of its way to ignore those essential insights, and present us with controls that are either bleached- or blacked-out depending on our choice of appearance mode.
In light mode, with default transparency, tool icons and text are clearly distinguished tonally, as are some controls including buttons and checkboxes. However, text entry fields are indistinguishable from the background, and there’s a general lack of demarcation, particularly between the controls and the list view below.
Oddly, dark mode outlines some controls better than light mode, but text entry fields and the list view below still lack demarcation.
One popular mitigation to this lack of tonal contrast is to resort to an Accessibility control that purports to reduce transparency rather than increasing contrast, although in fact its main advantage in Tahoe is to improve tonal contrast, at least in the toolbar.
This still has no effect on controls below the toolbar, and fails to demarcate text entry fields or the list view below.
The elephant in macOS Tahoe is its ignorance of human vision and our long experience of visual communication. It’s an elephant that comes in two appearance modes, bleached-out white or blacked-out black. It has little if any impact on the interface of Apple’s other OS 26es, but it makes macOS a pain to look at and harder to use. I feel sure that Lucas Cranach the Elder, Gustave Doré and every other self-respecting visual artist would be equally offended.
Here are this weekend’s Mac riddles to entertain you through family time, shopping and recreation.
1: Two credentials or 762 should be superseded by passkeys.
2: Notably from Autodesk but once by Claris, it’s 3,245.
3: From the Mac II until replaced by USB, 2,779 was quite enough.
To help you cross-check your solutions, or confuse you further, there’s a common factor between them.
I’ll post my solutions first thing on Monday morning.
Please don’t post your solutions as comments here: it spoils it for others.
If there’s one topic that needs explanation currently, it’s how macOS updates XProtect’s data. Let me try.
Until this changed in Sequoia, updating XProtect has been straightforward: its data is stored in a bundle named XProtect.bundle, in the path /Library/Apple/System/Library/CoreServices, on the Data volume so it can readily be updated. When you or macOS downloads and installs an XProtect update, it simply replaces that bundle with the new one. This is shown in the diagram below.
The source of those updates is Apple’s Software Update Service, through the Software Update pane in System Preferences or System Settings, the softwareupdate
command tool, or an app like SilentKnight. Left to its own devices, macOS normally checks for updates soon after starting up, and once every 24 hours running after that.
XProtect in macOS 15 prefers not to use the XProtect.bundle in its old location of /Library/Apple/System/Library/CoreServices, instead looking for XProtect.bundle in its new location, /var/protected/xprotect.
However, when you or your Mac use the old update system, including Software Update, softwareupdate
or SilentKnight, that still installs the update in the old location, where it won’t normally be used by XProtect when making its checks. What was supposed to happen in early versions of Sequoia was that at least once a day, macOS checked whether there was a newer update in the old location. If there was, then it should have automatically prepared and moved that to the new location in /var/protected/xprotect for XProtect to use.
If you wanted that to happen immediately, then you could run the following command in Terminal:sudo xprotect update
then enter your admin user’s password. The xprotect
command tool would then complete the installation of that update from its old location into its new one.
There’s also a second way that XProtect in early Sequoia could be updated, and that’s over a connection to iCloud. If that was used, then the update was installed straight into its new location, and didn’t change the XProtect bundle in the old location at all. Although Apple had used that earlier, all XProtect updates since the release of Sequoia came using the old Software Update system, so needed to be completed using the xprotect
command in Terminal.
This is shown in the diagram below. The blue boxes show the old Software Update system, and the pink boxes are the new parts that ensure the update is installed in the new location.
Later, that changed and Apple started releasing updates via iCloud. By about macOS 15.3, xprotect update
was no longer able to install XProtect in the new location, and that was only possible once that update had been released to iCloud, from where xprotect update
could download and install it to the new location.
With the release of macOS 26.0 Tahoe, this changed again. Macs running the latest versions of Sequoia and any version of Tahoe (after 26.0 release) continue to update the old location in /Library/Apple/System/Library/CoreServices as before.
Updating the new location in /var/protected/xprotect can occur by two methods. A background service XProtectUpdateService can:
That service is scheduled to run once every 24 hours.
The end result can appear confusing, but is summarised in the diagram below.
There are two routes for XProtect data to be updated in the new location:
softwareupdate
, then XProtectUpdateService runs later and installs a copy of that update to the new location.Both of those updates run silently, and the only ways to check that the new location has been updated are to:
xprotect version
,As far as the user is concerned:
xprotect update
in Terminal is only worthwhile if the new location hasn’t yet been updated, but that update has been released via iCloud, as confirmed using xprotect check
.Virtual Machines running macOS on Apple silicon Macs are more versatile than the host they run on. When you want to create a new VM, or modify an existing one, there are some powerful options available.
One of the most useful is to duplicate an existing VM: as APFS will do that using clone files, and the virtual disk in a VM is stored as a sparse file, that will use much less disk space than making a completely new VM. If you’re likely to need a supply of VMs running the same version of macOS, why not create a base VM using the IPSW for that version, duplicate it, then set up each clone as you require?
For even more flexibility, you can increase the size of the VM as I have already explained. The only remaining problem is how you can migrate the contents of one VM to another. Although my previous attempts to do this had been unsuccessful, Michael was kind enough to provide the solution, and this article explains how to use Migration Assistant in two VMs running concurrently to copy the contents of one VM to another, on the same host Mac. This should also enable you to migrate between a VM and a Mac.
To perform a successful migration, Migration Assistant needs to connect to a mounted Data volume on local storage, or over a network. It can’t use a VM shared folder on the host as the source (server). If your virtualiser supports root level access to USB storage, enabling it to mount an external disk in the VM, then you should be able to migrate from a Time Machine or other backup on that disk. Migration can be performed during initial setup and customisation of macOS, or by running Migration Assistant later. In this walkthrough, I’ll use the former.
To do this, the virtualiser has two fundamental requirements:
Apple enforces a limit of two macOS VMs running concurrently on the same Mac, a rule written into the macOS license. Although that might seem stingy, macOS isn’t like Linux and you can’t run Tahoe on a single core with a mere 3-4 GB of memory. However, if you can spare at least 3 P cores and around 12 GB of memory for each, there should be ample to perform a migration. In practice, that means the host Mac should have a total of eight or more P cores, and at least 32 GB of memory.
MAC addresses are supposed to be unique. As the connection between these two VMs is over your local network, your DHCP server must allocate them two different IP addresses, or they won’t be able to migrate. The way to ensure that works is to assign each VM its own and different MAC address.
My own free Viable satisfies both requirements. Here I’ll use that to set up a new VM as the migration client, using an existing VM as the server. For the sake of simplicity, I’ll assume the MAC address of the server is the default, and won’t change that.
This uses two macOS VMs running at the same time:
Start by installing the IPSW to create your new VM. Rather than going straight on to its first run, at this stage open the server VM with the default MAC set, log into it, and locate Migration Assistant in /Applications/Utilities ready to run.
Now change the MAC address in Viable’s window to something different. I used d6:a7:58:8e:79:d4 instead of d6:a7:58:8e:78:d4. Then open the new VM, the migration client, and take it through its configuration, opting to migrate to it from another Mac.
When you reach the screen that sets that up, open Migration Assistant on the server VM, and set it to transfer data To another Mac. Then switch back to the client VM, and you should see that server offered as the source for your migration. Select it and perform the PIN authorisation so they can connect.
On the client, select the items you want to migrate to that VM, and proceed.
After a few minutes, the migration should complete, allowing the client to finish setting up with its new user account. You can then shut down the server and reset the MAC address and other settings in Viable.
Viable’s narrative documents the sequence:
Apple’s instructions on migration are here.
If your Mac starts to boot but doesn’t get as far as displaying the login window, one of four things should happen:
The second of those is the most urgent, as it’s in a boot loop, and you need to force it to shut down by pressing and holding the Power button. Although macOS should limit the number of boot loops, don’t leave it to continue looping. If your Mac appears to have frozen, wait for up to an hour before forcing it to shut down, as it could be in the middle of checking and repairing disks, which you shouldn’t interrupt in case it proves successful.
This is a new feature in Tahoe, and uses latest data from Apple to try to recover your Mac automatically. For it to do that it requires an internet connection, preferably over Wi-Fi.
Distinctive to its opening window is its first aid symbol ⊕. Click on the Continue button to move on, and follow its instructions. At the end of that, you should see one of three outcomes:
When your Mac restarts, it may show a notification that you need to recover iCloud data. If so, open System Settings and you should see a new item in its sidebar to Recover iCloud Data.
If that doesn’t fix your Mac, you’ll almost certainly need to start up in Recovery and try to fix it there.
Boot loops happen when a kernel panic occurs during the boot process, before the login window is displayed. When the Mac tries to restart as a result, it hits the same kernel panic, and starts the cycle again. Boot freezes are the opposite: instead of repeatedly cycling through reboot-panic, the boot process comes to a complete halt, normally showing a stuck progress bar on the display. Thankfully neither is in the least common, and should have become even rarer with the introduction of the Signed System Volume (SSV) in Big Sur and later, and the deprecation of third-party kernel extensions.
What you do next on an Apple silicon Mac depends on whether it’s trying to load third-party kernel extensions. As Intel Macs don’t enjoy the same secure boot process, dealing with them is more difficult.
When an Apple silicon Mac is running at Full Security, the only kernel extensions that it loads are those provided in macOS, whose integrity is checked during the boot process. Any third-party kernel extensions included in the Auxiliary Kernel Collection in /Library/KernelCollections remain untouched. Likely causes of kernel panics during booting in Full Security mode include failure of validation of the on-disk root hash of the SSV, and hardware faults or errors, either internal or external.
An Apple silicon Mac running at Reduced Security can load third-party kernel extensions from the Auxiliary Kernel Collection in /Library/KernelCollections when that is explicitly enabled in Startup Security Utility. In the absence of any more probable reason for a kernel panic occurring during booting, it should be assumed that the cause is a third-party kernel extension, and that should be disabled in Recovery mode. This can only be done in paired Recovery, following a single long press of the Power button, not in fallback Recovery.
Restarting in Full Security should then complete normally, and allow the third-party kernel extension to be updated or uninstalled as needed.
In most cases, boot loops and freezes are best assessed by disconnecting all suspect peripherals, running Diagnostics and Disk Utility’s First Aid in paired Recovery mode. If that isn’t available, then Fallback Recovery can be used instead. Unfortunately, the most valuable diagnostic tool for kernel panics, the panic log, usually isn’t accessible when a panic has occurred during boot, although it may be shown when you get the Mac to start up normally again.
Before starting up in Diagnostics, disconnect all peripherals, except those that are essential such as keyboard, mouse/trackpad and any primary external display. Ensure a good Wi-Fi network connection can be made. If the problem occurred when trying to boot from an external disk, or if that Mac had previously been booting from one, it may be better to leave that connected; historically, some older combinations of firmware and macOS panic when an external boot disk has been disconnected but is still expected for the next boot.
On Apple silicon Macs, Diagnostics is unique in relying on a hidden key combination: at the initial Recovery screen, hold Command-D until the Diagnostics Loader starts. This may require download of the disk image from Apple’s servers before testing can proceed. Once loaded, there’s a hidden option for extended diagnostics that can be triggered by holding the Command-E key combination.
Disk Utility is accessed as usual from the main Recovery window.
Previous tools for the management of kernel extensions included kextload
, kextunload
and others. In Big Sur and later, these have been replaced by a single command tool kmutil
, which is inevitably complex to use. Full details are given in its man page, which is extensive and an excellent source of additional information.
There are at least four kmutil
commands that could prove useful:
kmutil trigger-panic-medic
, only available in recoveryOS, clears the AKC at /Library/KernelCollections and forces it to be rebuilt, requiring each kernel extension to be re-approved before it can be loaded. This is intended to be used to recover a system following a kernel panic generated by one of the kernel extensions in the AKC.kmutil inspect
lists all currently installed kernel extensions according to their collection.kmutil clear-staging
clears the contents of the staging directory /Library/StagedExtensions.kmutil unload -p /path/kextname.kext
unloads the kernel extension specified by /path/kextname.kext. This terminates and unloads it, but doesn’t remove the original kernel extension or any staged copy. Unless you also remove the kernel extension and remove it from its collection, it’s likely to load again at the next boot.In theory, removing the original kernel extension by removing the app which contains it, or deleting it from /Library/Extensions, should trigger kernelmanagerd
to remove it from the Auxiliary Kernel Collection and the staging directory /Library/StagedExtensions. However, that won’t take effect until after the next reboot. If the kernel extension isn’t then removed, it may be worth using kmutil clear-staging
, and if necessary kmutil trigger-panic-medic
in Recovery mode. Remember that kernel extensions may be left unused in staging, and are protected there by SIP, making manual removal tedious at best, and possibly pointless.
While system extensions shouldn’t cause kernel panics or freezes during the boot process, the command tool available to manage them is systemextensionsctl
. You can usesystemextensionsctl list
to list all known system extensions and their status.
To remove an orphaned system extension, with SIP already disabled, first list those known usingsystemextensionsctl list
to provide the teamID and bundleID. Then use those in the commandsystemextensionsctl uninstall teamID bundleID
and don’t forget to re-enable SIP immediately afterwards.
Historically, reinstalling macOS has often been advocated as a means of addressing boot loops and freezes. In Macs that perform full checking of the integrity of the SSV, Intel Macs with a T2 chip and Apple silicon models, that’s generally unwarranted.
Another option worth considering might be starting up in Safe mode, as that blocks the loading of most third-party components that could cause conflicts before the login window is loaded.
One well-known if rare cause of boot looping is a problem with firmware. For Intel Macs with T2 chips and Apple silicon Macs, the preferred solution to that is to boot the Mac in DFU mode, connect another Mac running a recent version of macOS, and perform a Revive from there. This is non-destructive of the SSV and Data volume, unlike a full Restore. Apple provides detailed instructions for you to do this yourself, provided you have the necessary second Mac and cable.
The cable used mustn’t be Thunderbolt, but plain USB-C. That’s because DFU mode doesn’t support Thunderbolt or its cable. Connect that to the designated DFU port on the Mac you’re going to Revive. That can be found in Apple’s note, or in Mactracker.
kmutil trigger-panic-medic
in Recovery.Apple has released its weekly update to XProtect, bringing it to version 5318. As usual, it doesn’t release information about what security issues this update might add or change.
This version makes several changes to the Yara definition for MACOS.COMPLIANTPIRATE.DEFU, but doesn’t add any new detection rules.
You can check whether this update has been installed by opening System Information via About This Mac, and selecting the Installations item under Software.
A full listing of security data file versions is given by SilentKnight and SystHist for El Capitan to Tahoe available from their product page. If your Mac hasn’t yet installed this update, you can force it using SilentKnight or at the command line.
If you want to install this as a named update in SilentKnight, its label is XProtectPlistConfigData_10_15-5318
This update has now been released for Sequoia and Tahoe via iCloud. If you want to check it manually, use the Terminal commandsudo xprotect check
then enter your admin password. If that returns version 5318 but your Mac still reports an older version is installed, you should be able to force the update usingsudo xprotect update
However, if the regular update has been installed in the old location, XProtect is likely to update its new location from that. There’s nothing you can do to force that, but it may well explain why your Mac seems to have updated itself.
Updated 0450GMT 9 October 2025.
If you ever encounter an error when checking an APFS volume using First Aid in Disk Utility or fsck_apfs
, you won’t be informed of the path and name of the item responsible, but given its inode number, in an entry likewarning: inode (id 402194151): Resource Fork xattr is missing for compressed file
The inode number given can only be resolved to a path and file/folder name if you also have a second number giving the volume for that item. As that will be for the volume being checked at the time, you should be able to identify that immediately. The only time that you might struggle to do that is with items in a snapshot; those should, I think, be the same as the volume they are taken from. However, as snapshots are read-only, there’s probably little point in pursuing errors in them.
To resolve these in my free utility Mints, open its inode Resolver using the Window / Data… / Inode menu command. Drag and drop another file from the same volume onto that window.
The Resolver will then display that file’s volfs path, such as/.vol/16777242/1241014
All you need do now is paste the inode number given in the warning or error message in Disk Utility or fsck_apfs
, into the Inode Number box at the top of the Resolver window, and click the Resolve button. Mints then looks up information for that inode number on the same volume, using GetFileInfo
, and displays it below.
One drag and drop, a paste, and a click to discover what APFS is complaining about.
You’ll sometimes see Terminal’s find
command with the option -inum
recommended as a way to convert from an inode number to a regular path. Although you can do that, it’s easier to use the command GetFileInfo
instead. For that you’ll need the full volfs path, including the volume number.
To find the volume number, use my free utility Precize, and open another file on the same volume. The second line in its window gives the full volfs path for that file. Copy the start of that, leaving the second number, the inode, such as/.vol/16777238/
Alternatively, you can use the stat
command as given below.
In Terminal, typeGetFileInfo
with a space at the end, and paste the text you copied from Precize. Then copy and paste the inode number given in the First Aid warning, to assemble the whole command, such asGetFileInfo /.vol/16777238/402194151
Press Return, and after a few seconds, you should see something likefile: "/Users/hoakley/Library/Mobile Documents/com~apple~CloudDocs/backup1/0MintsSpotlightTest4syzFiles/SpotTestA.rtf"
type: "\0\0\0\0"
creator: "\0\0\0\0"
attributes: avbstclinmedz
created: 05/17/2023 08:45:00
modified: 05/17/2023 08:45:00
giving the full path and filename that you want.
GetFileInfo
is one of the oldest commands in macOS, and has been deprecated as long as anyone can remember. I suspect that Apple is still trying to work out what can substitute for it.
Use Precize to run this the other way around: open the file and read the path in that second line. To copy the whole of it, press Command-2.
The simplest ways of obtaining inode numbers and so building volfs paths in Terminal are using the -i
option to the ls
command, and for individual items using stat
:ls -i
lists each item in the current directory, giving its inode number first, e.g.22084095 00swift
13679656 Microsoft User Data
22075835 Wolfram Mathematica
and so on;stat myfile.text
returns16777220 36849933 -rw-r--r-- 1 hoakley staff […] myfile.text
where the first number is the volume number, and the second is the inode number of that item, or /.vol/16777220/36849933
.
You’ve just run First Aid in Disk Utility, or fsck_apfs
, and that reports warnings or errors. What should you do next?
By far the most frequent error encountered in Disk Utility’s checks results from its inability to unmount a volume before it can start testing. While this is reported as an error, and it prevents the checks from running, it can sometimes be solved by manually unmounting the volume in question. It normally doesn’t indicate anything sinister, and is simply frustrating.
If the warnings or errors were reported on your current boot Data volume and you ran that check in normal user mode, consider starting your Mac up in Recovery mode to repeat the check there.
Although macOS does an impressive job of performing checks on a live volume, it’s more reliable and more likely to be able to perform any repairs needed in Recovery mode, when the Data volume isn’t mounted and live. When there, if you prefer, you can still use fsck_apfs
in Terminal.
The other case where checks may be best made in Recovery are those on an active Time Machine backup volume. That’s because those can be difficult to unmount before running the checks, although that is possible as long as a backup isn’t being made at the time, or Spotlight indexing taking place. The sure way to avoid those is to do so in Recovery mode.
Any remarks about problems or irregularities encountered during checks should make explicit whether they are warnings or errors, and it’s essential to make a clear distinction between them.
Warnings are observations that could have significance, or might be perfectly normal in the circumstances. Only an APFS engineer is likely to be able to tell the difference. Among the commonest are those reporting missing xattrs for compressed files:warning: inode (id 113812826): Resource Fork xattr is missing for compressed file
Experience is that those aren’t related to any consequent errors, and you should be able to leave those alone.
Errors are abnormalities that do have more significance, and might have the potential to cause further problems. Where possible, First Aid or fsck_apfs
should attempt to repair those, most probably by performing “deferred repairs”. Those are normally minor errors that it already has plans to attend to when that volume is next mounted, the time that APFS normally performs its routine maintenance.
These are read-only copies of the file system metadata at a previous instant in time, and are associated with retained storage blocks. They aren’t part of the active volume, and their metadata are separate. As they’re read-only, any warnings or errors are most unlikely to be fixed, so you have a choice of leaving that snapshot to be deleted routinely by age, or deleting it early yourself.
Snapshots are made by backup utilities including Time Machine, which are required by Apple to have a mechanism that will delete them automatically after a set period. In the case of Time Machine, that’s when the snapshot is over 24 hours old. Snapshots aren’t backups, but augment regular backups, and stand in for them when backup storage isn’t available. In general, there seems little point in deleting a snapshot early just because there’s a reported warning or error for it, as that won’t affect the health of the active volume.
Warnings and errors related to specific files or directories are normally given with an item id, which should be their inode number. To go any further, you’ll need to convert that to a path and file/directory name. You should therefore copy and paste all reports into a separate file as reference. Resolving an inode to a path and item name is detailed in this article.
In many cases involving items that can be resolved to an existing path, the faulty item is in one of the hidden folders such as .Spotlight-V100
for Spotlight indexes, or .DocumentRevisions-V100
for the document version database. In the former, rebuilding Spotlight’s indexes may resolve the problem, but you’re unlikely to be able to do anything about the latter.
If the inode resolves to a regular file, deleting that can remove the problem, but when you try restoring that file from a backup you may discover the backup has the same problem. Getting to the bottom of a recurrent file system error might require the knowledge and skills of an Apple engineer. Consider reporting this using Feedback, as it should then help iron out any remaining bugs in APFS.
You should also consider whether your Mac might be running old third-party software that is causing recurrent errors. Normally, products should work at a higher level that isolates them from the file system itself, but there are some surprising exceptions. If you can identify a cause, please inform the developers of that software so that it can be fixed.
One potentially dangerous practice occurs when an older version of APFS changes a newer file system. APFS back in High Sierra and Mojave knew nothing of boot volume groups, firmlinks, or many of the features of more modern versions of APFS. If you really must run different versions of macOS on the same Mac, or shared external storage, avoid such version conflicts, and never run an older version of Disk Utility or fsck_apfs
on a newer APFS container or volume.
I hope that you enjoyed Saturday’s Mac Riddles, episode 328. Here are my solutions to them.
Schwabe’s painting shows a chain of angels emerging from a belfry.
Doré’s engraving shows The Demons Threaten Virgil, from his illustrations to Dante’s Inferno.
They are each (secret) agents: James Bond from Ian Fleming, Jason Bourne from Robert Ludlum, George Smiley from John le Carré, and Modesty Blaise from Peter O’Donnell.
They are each run by launchd
from property lists in folders titled LaunchAngels (new in Tahoe), LaunchDaemons and LaunchAgents.
I look forward to your putting alternative cases.
For many years, I believed what the log
command told me, that log entries could contain any of the 26 or more fields available, although they didn’t. It was only as I was developing utilities like LogUI that I discovered that log entries come in (at least) four types, each with its own format and set of fields. This article is a guide to those, and how they are displayed in LogUI.
Those available in the OSLog API are fewer in number than appear in log
command output, and include some of limited interest. Those not exposed in LogUI include:
LogUI displays each entry using the same order of fields and colour-coding. Although they can’t all be seen together in any single log entry, the overall sequence is:
Standard levels are given as text, and chosen from one of the following: fault, error, notice, info, debug, undefined. These are only used with Regular log entries, not other types. LogUI always includes debug level entries when they’re available.
The four types of entry are:
These are normally by far the most common, and are seen throughout the processes and subsystems writing log entries. They normally contain up to the following fields:
datestamp, [1], activity ID, category, level, sender, process, process ID, subsystem, thread ID, message
These examples include:
datestamp, 1, activity ID, category, level, sender, process, process ID, subsystem, thread ID, message
which is fairly normal.
These mark specific activities, and vary according to the process and subsystem. Some are valuable waypoints, and all are recognisably shorter than most regular entries, containing only the following fields:
datestamp, [2], activity ID, parent activity ID, sender, process, process ID, thread ID, message
These are examples of one of the most valuable activities reported, indicating a mouse-click or tap. They’re also complete, as they consist of:
datestamp, 2, activity ID, parent activity ID, sender, process, process ID, thread ID, message
These are rare but instantly recognisable because of their brevity. They consist of just three fields:
datestamp,[3], message
Two of the most important are the announcement of the start of kernel boot:
and adjustment of the internal clock:
These are also easy to search for, as their message contains the distinctive ===
string.
By default, LogUI extracts omit Signposts, but if you tick the Show Signposts box before loading log entries, they will also be displayed. In parts, they can outnumber regular entries, and are unlikely to provide you with meaningful information unless you know internal details of their process. Each Signpost adds three type-specific fields, shown after the process ID:
datestamp, [4], activity ID, category, sender, process, process ID, signpost ID, signpost name, signpost type, subsystem, thread ID
These examples come from the most prolific user of Signposts, SkyLight for WindowServer, and contain
datestamp, 4, activity ID, category, sender, process, process ID, signpost ID, signpost name, signpost type, subsystem, thread ID
Note there’s no message field, as their meaning is determined by the signpost fields.
The OSLog API doesn’t currently give access to Mach times, only to opaque Date
variables. From those, LogUI’s datestamps give:
year–month–day hour:minute:second.microsecond+timezone
All times and time zones given are those current when LogUI obtains that extract, not when that entry was written. This can become extremely confusing when clocks change to and from {summer time, daylight time, daylight saving time, daylight savings time, DST}, and when passing through time zones, and great care is required when reading logs containing such corrections. LogUI tries to make this easier, but care is still required.
If you have used the log
command, you may be aware that can return Mach times as ticks, offering precision down to the nanosecond. This currently isn’t possible when using the OSLog API, but given the relatively slow clock of Apple silicon Macs, it’s no longer as useful as it used to be with Intel’s nanosecond Mach ticks.
By default, all data in message fields is censored to protect the privacy of the user. This replaces chunks of text with the dreaded <private>, and can render many entries devoid of any useful information. In recent versions of macOS log privacy can be removed by installing a profile. However, that doesn’t apply retrospectively, only to log entries collected after the profile has been installed.
Removing privacy also increases the size in storage of log entries, and may reveal sensitive information. As soon as you have completed acquisition of the logs you need with privacy removed, you should therefore remove the profile, to allow normal censorship to resume.
A suitably signed profile is here: enablelogprivatedata
To install the profile, unzip the archive into a convenient folder and double-click it. You’ll be informed by a notification that you need to review the profile to install it. Open System Settings and select Device Management in its View menu, or search for it. Follow the instructions given there to install and activate it.
Sadly, this doesn’t cover all censorship. Some systems require additional configuration changes, for example CFNetwork diagnostic logging. Jeff Johnson explained how to enable that, but Apple has since blocked that, and I don’t know of a practical alternative. In some cases, additional detail can be obtained by adjusting log settings.
A short practical summary of LogUI’s log entries is provided in its Help book.
Before macOS Tahoe, the biggest sticking point in virtualising macOS on Apple silicon Macs has been their lack of support for the App Store. From the outset this has been an ironic limitation. Here’s some of Apple’s most advanced technology running on its latest hardware, and it can’t even run the apps that Apple sells, only those supplied direct by their developers.
VMs can now have iCloud and iCloud Drive support, Messages, FaceTime, FileVault, and plentiful shared folders, but the one thing they have lacked that renders them useless for many users and many purposes is that can’t sign into Apple services, particularly the App Store. Some apps, including those in Apple’s iWork suite, will run in a VM despite it being unable to sign into your account, but you can only window-shop in the App Store, and most of its apps will simply refuse to run, even free ones.
I’ve long suspected that this is an example of Apple Commercial constraining Apple Engineering. To be useful, macOS VMs would have to be exempted limits on the number of Macs authorised to access services, and that could open up the possibility of third-parties bypassing FairPlay and the digital rights controls embedded in macOS. It must be deeply frustrating to those working on virtualisation, knowing that it could be done but won’t be.
So the only substantial new feature for macOS virtualisation in Tahoe is the introduction of ASIF disk images. For the time being, I’m not sure they’re going to change much for most of us who host our VMs on local APFS storage. As they still don’t enjoy proper API support, I don’t see any compelling reason to rush into their use, unless you want to host your VMs in the cloud.
Upgrading to Tahoe has, though, drawn attention to problems lurking for those who created VMs of 50 GB or smaller, who now want to enlarge them for this purpose.
Don’t skimp when creating a new VM. Give it a useful size, as its Disk.img is stored as a sparse file, so won’t take all that disk space unless you fill it to capacity. I now make my default VMs 100 GB to ensure there’s ample free for updates and anything else that might arise.
If you do have a treasured VM that’s too small, you may well be able to increase its size, either using Disk Utility or the hdiutil resize
command tool if you prefer. To do this, start by duplicating your VM in the Finder. That creates a clone, and lets you fall back to the unaltered original if the resizing goes horribly wrong.
To resize the disk image using Disk Utility, you first have to move it out from inside its VM bundle, easily done in the Finder. Then in Disk Utility’s Images menu use the Resize… command, select that Disk.img and enter its new size. Add a little, around 8%, to allow for overheads, and let Disk Utility get on with the work.
Here’s Disk Utility inside this Tahoe VM, showing its 50 GB virtual disk.
I then resized it to just over 100 GB.
Here it is afterwards, now showing a full 100 GB.
I gather from others that resizing doesn’t always work. If you can’t get it to, then the only way forward is to create a new VM with the larger capacity and copy across the contents of your old VM. One obvious way to make that simpler and more thorough would be to use Migration, either during configuration of the new VM, or shortly afterwards.
I’m very grateful to Michael for telling us of his success in migrating from a small to a larger VM in Tahoe. I’m also more than a little jealous, as I’ve so far been unable to get it to work for me.
I’m also mystified as to how two macOS VMs running concurrently on the same Mac could establish a connection to support the file transfers required in migration. Neither can expose its virtual folders as shared folders for the other, and in any case shared folders are strictly circumscribed. Sharing them over AFP runs into a quirk of their bridged networking, that both of the VMs will default to using the same network IP address. In my failed tests, the destination Migration Assistant was able to recognise the source, but failed to connect to it successfully.
For the moment macOS virtualisation hasn’t made any substantial improvements in Tahoe. It still can’t sign into Apple services, and AI remains unavailable. Let’s hope the next year brings more and better, and realises more of its potential.
Here are this weekend’s Mac riddles to entertain you through family time, shopping and recreation.
3: James Bond, Jason Bourne, George Smiley, Modesty Blaise.
To help you cross-check your solutions, or confuse you further, there’s a common factor between them.
I’ll post my solutions first thing on Monday morning.
Please don’t post your solutions as comments here: it spoils it for others.
Every self-respecting file system identifies files and directories using numbered data structures. In most modern file systems, those data structures are known as inodes, and their numbers are inode numbers, sometimes shortened to inodes. The term is thought to be a contraction of index node, which certainly makes sense, but is lost in the mists of time.
In any file system, for example an individual APFS volume, the inode numbers uniquely identify each inode, and each object within that file system has its own inode. Whatever else the file system might do, the inode number identifies one and only one object within it. Thus one invariant way of identifying any file is by referencing the file system containing it, and its inode number.
The Mac’s original native file systems, ending most recently in Mac OS Extended File System, or HFS+ from its origins in the Hierarchical File System, don’t use inodes as such, and don’t strictly speaking have inode numbers. Instead, the data structures for their files and folders are kept in Catalogue Nodes, and their numbers are Catalogue Node IDs, CNIDs.
With Mac OS X came Unix APIs, and their requirement to use inodes and inode numbers. As CNIDs are unique to each file and folder within an HFS+ volume, for HFS+ they are used as inode numbers, although in some ways they differ. CNIDs are unsigned 32-bit integers, with the numbers 0-15 reserved for system use. For example, CNID 7 is normally used as the Startup file’s ID.
Although not necessarily related to CNIDs, it’s worth noting that the Mac’s original file system MFS allowed a maximum of 4,094 files, its successor HFS was limited to 65,535, and HFS+ to 4,294,967,295. Those are in effect the maximum number of inode numbers or their equivalents allowed in that file system.
Unlike HFS+, APFS was designed from the outset to support standard Posix features, so has inodes numbered using unsigned 64-bit integers.
Strictly, the APFS inode number is the object identifier in the header of the file-system key. Not all unsigned 64-bit integers can be used as inode numbers, though, as a bit mask is used, and the number includes an encoded object type. APFS also makes special allowance for volume groups consisting of firmlinked System and Data volumes, to allow for their inode numbers to remain unique across both volumes. Officially, those allow for a maximum number of inode numbers of 9,223,372,036,854,775,808, either in single APFS file systems, or shared across two in a volume group.
Every file in APFS is required to have, at an absolute minimum, an inode and its associated attributes, shown above in blue, including a set of timestamps, permissions, and other essential information about that file.
There are also three optional types of component:
When looking at inode numbers in volume groups, they can be used to determine which of the firmlinked file systems contains any given file. Both volumes share the same volume ID, and files in the System volume have very high inode numbers, while those in the Data volume are relatively low. I have given further details here.
Inode numbers are more generally useful in distinguishing files whose data appears identical, and the behaviour of various methods of linking files.
Copying a file within the same file system (volume) creates a new file with its own inode number, of course. However, duplicating a file within the same file system results in an APFS clone file, with a distinct inode, although it shares common data, so their inode numbers are also different.
Instead of duplicating everything, only the inode and its attributes (blue and pink) are duplicated, together with their file extent information. There’s a flag in each clone file’s attributes to indicate that cloning has taken place.
A symbolic link or symlink is merely a pointer to the linked file’s path, and doesn’t involve inode numbers at all. Because of that, changing the linked file’s name or path breaks its link. Finder aliases and their kindred bookmarks do contain inode numbers, so should be able to cope with changes to the linked file’s name or path, provided it remains in the same file system and doesn’t change inode number.
Hard links are more complex, and depend on the way in which the file system implements them, although the fundamental rule is that each object that’s hardlinked to the same file has the same inode number. According to Apple’s reference to APFS, this is how it handles hard links.
When you create a hard link to a file (blue), APFS creates two siblings (purple) with their own IDs and links, including different paths and names as appropriate. Those don’t replace the original inode, and there remains a single file object for the whole of that hardlinked file.
Inode attributes keep a count of the number of links they have to siblings in their link (or reference) count. Normally, when a file has no hard links that’s one, and there are no sibling files. When a file is to be deleted, if its link count is only 1, the file and all its associated components can be removed, subject to the requirements of any clones and applicable snapshots. If the link count is greater than 1, then only the sibling being removed is deleted.
Inode numbers are readily accessed using command tools in Terminal. For example, ls -i
lists items with their inode numbers shown. One free utility that displays full information about inode numbers and much more is Precize.
The volume ID is given as the first number in the volfs path, and the second is the inode number of that file within that. Note that the File Reference URL (FileRefURL) uses a different numbering system, and the Ref count of 1 indicates this file has no hard links.
Browsing through the /System/Library folder in macOS Tahoe you’ll no doubt be surprised to see a new folder, between LaunchAgents and LaunchDaemons, named LaunchAngels. This article takes a preliminary look at what’s in there, and what these new additions to Apple’s bestiary do.
These have been used in macOS for a great many years, probably since the introduction of launchd
in Mac OS X 10.4 Tiger in 2005. These folders contain property lists for:
launchd
, running as root before the user logs in, and communicating indirectly with user processes, normally by XPC. They’re not allowed to connect to WindowServer.launchd
, but normally run on the user’s behalf, communicating with other processes and daemons. Although they can have GUI interfaces, they’re normally minimal.Before you have logged in, launchd
runs services and other components specified in property list files in the LaunchAgents and LaunchDaemons folders in /System/Library, and in /Library. Those in /System/Library are all part of macOS, owned by Apple, and locked away on the SSV, but those in /Library can include those installed by third party products, although these days more are being enclosed in app bundles. As they’re run before the user logs in, those work for all users, so are global services.
These property list files contain keyed settings to determine what launchd
does with what. Although they can contain many other key-value pairs, two most important ones are ProgramArguments (or Program), which tells launchd
what to run, and RunAtLoad, which determines whether launchd
should run the service or app whenever your Mac starts up and it loads those agents and services. Other keys determine whether the agent/service should be kept running at all times; if that is set, if it crashes or is otherwise terminated, launchd
will automatically start it up again. That’s important for background services that apps rely on to function.
As of macOS 26.0.1 there are three Launch Angels, each with a property list in /System/Library/LaunchAngels. Those relate to three apps now in /System/Library/CoreServices,
AccessibilityUIServer is an addition to the Accessibility process group, and is listed in the processes in Activity Monitor as Accessibility. It thus runs in the background, supporting Accessibility features in Tahoe. These might perhaps extend the Accessibility enhancements for UIKit provided in UIAccessibility to macOS.
The other two apps aren’t run at load, so must be run on demand. GameOverlayUI appears to be responsible for providing the new Game Overlay features, and I suspect that PosterBoard is responsible for Lock Screen customisation. A key set for each of these in their property list is _ExperimentalNonLaunching, suggesting that these are still in test.
Apple describes Game Overlay as allowing “players to stay in the game when it matters most. Players can easily adjust settings, connect with friends, and check out the latest In-App Events and supported Game Center features, all without leaving their game.”
What’s most unusual, and may be new with Tahoe, is that all three property lists include settings for RunningBoard and its life cycle management. These are the keys
I’m not aware of any similar RunningBoard settings for property lists in the LaunchAgents or LaunchDaemons folders, though.
launchd
using property lists in /System/Library/LaunchAngels.If you bought an M1 Mac with just a 256 GB internal SSD and have kept up with macOS upgrades and updates, should you be worried that it’s running out of space by the time it makes it to Tahoe? Dare you look at Storage settings to see how much of the SSD is now swallowed up by System Data? This article explains why macOS 26 shouldn’t devour the last of your SSD, and how you can ensure that it doesn’t.
Internal boot disk layout is most complex in Apple silicon Macs, as theirs is divided into three partitions (or APFS containers). Two are hidden and contain pre-boot and other low-level support files, and amount to around 6 GB. The Macintosh HD partition then takes the lion’s share, the whole of the remainder. Even on a 256 GB SSD, that’s about 250 GB.
Volumes within Macintosh HD include:
The system your Mac actually boots into isn’t the System volume itself, but a snapshot made of it, occupying the same space, plus a little extra for the snapshot’s metadata including its tree of hashes to form its seal and signature. Because this is a snapshot it uses the same data stored for the System volume, and doesn’t double that up.
This should allow your Data volume a maximum of 228 GB, less any space required by the VM volume. Although installation of a macOS upgrade or update will require substantial additional space, once that’s complete the space taken by the System volume and its snapshot should fall to little more than 12 GB.
In traditional macOS upgrades, the Installer app was downloaded first, and itself required around 13-15 GB. That was run, and expanded its contents to be installed onto the System volume, replacing much or all of it.
Updates work more economically, as they contain only the files that have changed, so far less than the Installer app. When they’re installed, they replace only those files changed in the System volume, ready for a new snapshot to be made from that, to be used to boot that Mac. So an update-style upgrade, as you should get when going from macOS 15.7 to 26.0, should require a much smaller download, a faster install, and less space to install the new version of macOS. However, the end result should be identical, with exactly the same files installed in the System volume, and exactly the same in the snapshot used when running.
Whichever is used, the installation process is similar. First, the files to be installed are expanded, then they’re written to the mounted System volume, with some going onto the Data volume as well. Once the System volume is complete, a snapshot is made of it, and that’s sealed using a tree hierarchy of hashes, culminating at the top of the tree in the seal.
Storage settings scans the contents of the boot volume group, Macintosh HD, and divides the storage used into different categories like Applications and Podcasts. It appears to total those up and account for the remainder of storage used in the category System Data. That doesn’t include the size of the System volume, or its snapshot, but can include temporary files like caches, snapshots, and anything else it can’t account for in other categories.
If there are substantial amounts of space that aren’t accounted for on your Mac’s internal SSD, and you want to reduce that, you need to account for it before deciding what to do about it.
First check for large snapshots. I hear repeatedly of Macs that turn out to have hundreds of GB being used by snapshots unnecessarily, and the current record is over 400 GB. The easiest place to check for those is in Disk Utility. In the sidebar on the left select the Data volume, then Show APFS Snapshots in the View menu for them to be displayed at the foot of the main view.
Backup utilities including Time Machine normally make a snapshot with each backup, and retain them for 24 hours, following which they’re automatically deleted. As snapshots can’t exclude folders in the way that Time Machine can in its backups, if you’ve been working with a couple of 100 GB VMs then they will be retained in snapshots even though you probably exclude them from being backed up.
Once you’re happy that free space isn’t being retained in snapshots, use a disk mapping utility like DaisyDisk or GrandPerspective to hunt down other large files and folders that you may not need. One reader here recently discovered that their iOS and iPadOS backups had taken over more than half the space on their Mac’s SSD.
Installing a macOS upgrade also changes files on your Data volume, and may retain temporary support files. These are normally cleaned up in the next 24 hours, and you may be able to encourage that by starting your Mac up in Safe mode, leaving it a couple of minutes, then restarting it in normal user mode.
By a couple of days after the upgrade, your Mac should have returned to normal use of storage. If it hasn’t, check snapshots and go hunt that missing space.
Apple has released its weekly update to XProtect, bringing it to version 5317. As usual, it doesn’t release information about what security issues this update might add or change.
This version adds five new detection signatures to its Yara file. These include another newcomer with four signatures, MACOS.DAILYDUMPLING, and MACOS.SOMA.SEEND to add to the large Amos/Soma family.
You can check whether this update has been installed by opening System Information via About This Mac, and selecting the Installations item under Software.
A full listing of security data file versions is given by SilentKnight and SystHist for El Capitan to Tahoe available from their product page. If your Mac hasn’t yet installed this update, you can force it using SilentKnight or at the command line.
If you want to install this as a named update in SilentKnight, its label is XProtectPlistConfigData_10_15-5317
I apologise for the late announcement of this update, which seems to have been released after 22:00 GMT on 30 September, but was still incomplete here through the whole of today, 1 October.
This update has already been released for Sequoia and Tahoe via iCloud. If you want to check it manually, use the Terminal commandsudo xprotect check
then enter your admin password. If that returns version 5317 but your Mac still reports an older version is installed, you should be able to force the update usingsudo xprotect update
As promised earlier this week, I’m delighted to offer a new version of my log browser LogUI that provides a Diagnostics Tool to help you understand log folders and discover any problems with them.
Open its window using the Diagnostics Tool command in the Window menu, and you’re offered four tools at the top.
The first, Get Info, performs a simple analysis on the files in the selected diagnostics folder. By default, that’s your current live log, in the path /private/var/db/diagnostics, in your Data volume. After telling you how many log files there are in each of its three main folders, and the number of timesync files, it reports the date and time of the oldest Persist log file, marking the start of the continuous log record, in this case nearly 4 days ago.
You can use these tools on any diagnostics folder you can access through its dialog. This includes Time Machine backups, external boot disks, and other bootable systems. Don’t click on the Open button, though, until you’ve selected the diagnostics folder in the view above.
Locating the diagnostics folder in a Time Machine backup can be interesting, but once you’ve found it, LogUI will happily check it for you.
The Catalogue tool lists all the tracev3 log files in the folders inside diagnostics, starting with those in Persist. It gives each file’s creation and modification timestamps, indicating the range for log entries within them, their size in bytes, and an estimate of the period that file covers.
The Analyse tool extracts information from each of logd
‘s statistics files, with the number of log entries broken down in frequency order. If you tick the CSV checkbox, they will be delivered in CSV format, ready to import into other software such as a spreadsheet.
The last of the tools, Save Text, saves the contents of the window to a text file for your records.
Further information about locations used for log files is in this article.
LogUI 1.0 build 74 is now available from here: logui174
from Downloads above, and from its Product Page.
Enjoy!
One seemingly widespread complaint about recent versions of macOS has been slow launch times of notarized apps even after they have cleared quarantine in their first run. Debate on the cause of this was vigorous in April and May, but was overtaken by Apple’s announcement of macOS 26 Tahoe. I therefore postponed further work on app launch and Gatekeeper until after Tahoe’s release.
This proved worthwhile, as soon after the first beta-release, it was suggested that Tahoe would accelerate the first launch of notarized apps by exempting them from a malware scan, although I have been unable to confirm that from Apple’s published information. That would make good sense: if an app’s CDHashes verify and match those of its notarization ticket, and no known malware was found when it was notarized, then it’s not plausible for it to contain malicious content since notarization was performed. This article considers what has changed in Gatekeeper in macOS 26.0.
Although Apple hasn’t yet updated it for macOS 26, its Platform Security Guide explains what Gatekeeper does in macOS Sequoia. For an app, plug-in or an installer package downloaded from outside the App Store and opened on a Mac, Gatekeeper verifies the software:
To assess this, I have used Calibre version 8.11.0 installed in a macOS virtual machine running on a Mac mini M4 Pro. Calibre is a large app at just over 1 GB with many components to be checked. This version has 82 items in its Frameworks folder, 20 executables in its MacOS folder, and 25 dylibs in its Plugins folder, totalling 113 dylibs and others that need to be checked.
Two VMs were prepared, one with macOS 15.7 Sequoia installed, the other with macOS 26.0 Tahoe. Both were run with 5 CPU cores, 16 GB memory, 100 GB disk, and bridged networking.
Calibre was launched three times in Tahoe, first when freshly installed and still in quarantine. Following that, the VM was shut down, started up 4 hours later and Calibre was run a second time. The VM was shut down again, and started up two days later for a third run. Log extracts were collected within a minute using LogUI.
This proceeded similarly to first run in Sequoia, with the exception of XProtect malware scanning. Soon after com.apple.syspolicy.exec reported that a GK (Gatekeeper) process assessment was starting, it wrote the log entrySkipping up front XProtect scan on: PST: (path: f0970f7f0ab1ff9f), (team: NTY7FVCEKP), (id: (null)), (bundle_id: (null))
That was reiterated later, shortly before the outcome of the GK evaluationSkipping XProtect scan on seen software: PST: (path: f0970f7f0ab1ff9f), (team: NTY7FVCEKP), (id: (null)), (bundle_id: (null))
There were no other log entries that suggested an XProtect malware scan had been attempted.
As is normal in the first run, notarization was checked using CloudKit, there was abundant evidence of CDHash verification, the user was prompted for their approval, and once that was complete the code was allowed to proceed.
Despite the lack of an XProtect scan, launch was as long as previous first runs in recent versions of macOS, taking 10.4 seconds from the second click to launch the app, to display of the prompt for user approval. During that period, a standard progress dialog was displayed. Entries in the log consisted of about 13,000 messages of SecKeyVerifySignature
from syspolicyd
and trustd
, with repeated errors ofSecError com.apple.securityd Malformed anchor records, not an array
The second and third runs, out of quarantine, were almost identical in the log, and similar to those in macOS 15.7 (below). com.apple.syspolicy.exec announced early that the code had already been evaluated, and those previous results would be used. Provenance data was found, and the evaluation completed without any CloudKit check of notarization. Times from the second click to launch the app, to loading of the app’s preferences were 0.64 and 0.66 seconds.
At various times, the kernel reported that it was considering a malware scan on one of the executables being checked, for exampleASP: considering malware scan (activeRulesVersion: 11716915239283693719 lastScanVersion: 0 chgtime: 1758884893 lastFileScanTime: 1758884893 threshold: 1758884893 pid: 949 info_path: /Applications/calibre.app/Contents/MacOS/calibre proc_path: /Applications/calibre.app/Contents/MacOS/calibre isNewerThanScan: 0 needsVersionScan: 0 is_time_eval_exempt: 0 is_scan_version_exempt: 1
Those appear new to macOS 26, and haven’t been seen in any log records from macOS 15.7 or earlier. Executables cited in those messages extended beyond components of Calibre to others that happened to be running at the time, but none was followed by any report of whether a scan was performed as a result.
Although they didn’t delay app launch, at the same time amfid
entered the path of the main executable and 112 dylibs and others to check each individually. For the dylibs and others, each was accompanied by a report from the kernel ofAMFI: constraint violation [dylib path] has entitlements but is not a main binary
Those took a period of approximately 3 seconds in each of the two runs.
These were remarkably similar, and in many parts identical, to those in Tahoe, except that there were no messages reporting consideration of malware scans. Times from the second click to launch the app, to loading of the app’s preferences were slightly quicker than Tahoe, at 0.59 and 0.59 seconds. Concurrent time to iterate through all the executable components was also shorter at 2.6 seconds, with identical reports of constraint violations.
From this evidence, I’m not convinced of any significant improvement in launch times. Please let me know whether you think that Tahoe has improved the speed of your app launches.
Previous articles:
Why some apps launch very slowly
Gone to launch
Apple has just released macOS 26.0.1 Tahoe, which fixes the problem upgrading to 26.0 on Mac Studio M3 Ultra models, and apparently fixes other urgent bugs.
For Apple silicon, the update is a 1.76 GB download.
Tahoe 26.0.1 fixes a single vulnerability, although Apple doesn’t report that it’s already being exploited. The same is also fixed in Sequoia 15.7.1, and in Sonoma 14.8.1.
macOS 26.0.1 has build number of 25A362, Safari version 26.0.1 (21622.1.22.11.15), and a Darwin Kernel version of 25.0.0. There has been no change in iBoot firmware, which remains at 13822.1.2.
As Apple hasn’t been forthcoming about what else has changed, here’s my list:
Otherwise, remarkably little has changed.
Updated 1910 29 September 2025.