<?xml version="1.0" encoding="UTF-8"?>
<feed xmlns="http://www.w3.org/2005/Atom" xml:lang="en">
    <title>Mark Rowe</title>
    <link rel="self" type="application/atom+xml" href="https://bdash.net.nz/atom.xml"/>
    <link rel="alternate" type="text/html" href="https://bdash.net.nz"/>
    <generator uri="https://www.getzola.org/">Zola</generator>
    <updated>2024-12-01T00:00:00+00:00</updated>
    <id>https://bdash.net.nz/atom.xml</id>
    <entry xml:lang="en">
        <title>TCC and the macOS Platform Sandbox Policy</title>
        <published>2024-12-01T00:00:00+00:00</published>
        <updated>2024-12-01T00:00:00+00:00</updated>
        
        <author>
          <name>
            
              Unknown
            
          </name>
        </author>
        
        <link rel="alternate" type="text/html" href="https://bdash.net.nz/posts/tcc-and-the-platform-sandbox-policy/"/>
        <id>https://bdash.net.nz/posts/tcc-and-the-platform-sandbox-policy/</id>
        
        <content type="html" xml:base="https://bdash.net.nz/posts/tcc-and-the-platform-sandbox-policy/">&lt;h1 id=&quot;background&quot;&gt;Background&lt;&#x2F;h1&gt;
&lt;h2 id=&quot;what-is-tcc&quot;&gt;What is TCC?&lt;&#x2F;h2&gt;
&lt;p&gt;TCC is a subsystem on macOS that is responsible for managing which applications
a user has permitted to access certain resources. Its full name is
&quot;Transparency, Consent and Control&quot;. If you&#x27;ve ever seen an &lt;em&gt;&quot;Application&quot; would
like to access the camera&lt;&#x2F;em&gt;  prompt… that&#x27;s TCC.&lt;&#x2F;p&gt;
&lt;p&gt;TCC is used to gate access to resources that Apple considers to be sensitive. Protected
resources include:&lt;&#x2F;p&gt;
&lt;ul&gt;
&lt;li&gt;Hardware devices such as the camera and microphone&lt;&#x2F;li&gt;
&lt;li&gt;Location services&lt;&#x2F;li&gt;
&lt;li&gt;A user&#x27;s photos, contacts, calendar, or reminders&lt;&#x2F;li&gt;
&lt;li&gt;Files in a user&#x27;s desktop, downloads or documents folders&lt;&#x2F;li&gt;
&lt;li&gt;Data managed by other third-party applications&lt;&#x2F;li&gt;
&lt;&#x2F;ul&gt;
&lt;p&gt;TCC permissions are mediated by the &lt;code&gt;tccd&lt;&#x2F;code&gt; process that runs as part of macOS.
System frameworks that access sensitive resources use private APIs, such as
&lt;code&gt;TCCAccessRequest&lt;&#x2F;code&gt; to determine whether they have permission to access the
resource. The API performs an interprocess call to &lt;code&gt;tccd&lt;&#x2F;code&gt;, which will trigger a
prompt if it is the first time the application has attempted to access that
class of resource. Otherwise, it will return the stored permission decision.&lt;&#x2F;p&gt;
&lt;h2 id=&quot;what-is-the-platform-sandbox-policy&quot;&gt;What is the Platform Sandbox Policy?&lt;&#x2F;h2&gt;
&lt;p&gt;For background about what sandboxing is on macOS and how it works, see
&lt;a href=&quot;https:&#x2F;&#x2F;bdash.net.nz&#x2F;posts&#x2F;sandboxing-on-macos&#x2F;&quot;&gt;Sandboxing on macOS&lt;&#x2F;a&gt;.&lt;&#x2F;p&gt;
&lt;p&gt;The Platform Sandbox Policy is a sandbox policy that is applied to all processes
running on macOS. It is applied transparently to all processes on the system,
irrespective of whether they are explicitly sandboxed.&lt;&#x2F;p&gt;
&lt;p&gt;The Platform Sandbox Policy implements one part of System Integrity Protection
on macOS. It defines and enforces the restrictions on access to the file system,
Mach bootstrap names, IOKit devices, and other resources. Amongst other
things, the platform sandbox policy uses process attributes (such as signing
identity, bundle identifier, and entitlements) to allow specific applications to
bypass restrictions that System Integrity Protection would typically apply to
them. This allows applications that are part of macOS to provide system
functionality, such as app installation and software updates, that would
otherwise be prohibited by System Integrity Protection.&lt;&#x2F;p&gt;
&lt;h1 id=&quot;with-user-approval&quot;&gt;&lt;code&gt;(with user-approval …)&lt;&#x2F;code&gt;&lt;&#x2F;h1&gt;
&lt;p&gt;One aspect of TCC that most existing analyses of it miss is that the Platform
Sandbox Policy also backstops TCC.  The sandbox kernel extension supports
triggering TCC prompts when a program accesses specific resources, rather than
being limited to merely allowing or denying the access, and the platform sandbox
policy makes use of this facility&lt;&#x2F;p&gt;
&lt;p&gt;Specifically, &lt;code&gt;allow&lt;&#x2F;code&gt; actions in the platform sandbox policy can have a &lt;code&gt;(with user-approval &quot;&amp;lt;type&amp;gt;&quot;)&lt;&#x2F;code&gt; modifier attached to them. This triggers an up-call
from the Sandbox kernel extension to the &lt;code&gt;sandboxd&lt;&#x2F;code&gt; user-space helper asking for
TCC approval of the specified type.  &lt;code&gt;sandboxd&lt;&#x2F;code&gt; translates this into a call to
&lt;code&gt;tccd&lt;&#x2F;code&gt;, much like a system framework using &lt;code&gt;TCCAccessRequest&lt;&#x2F;code&gt; to verify
that the calling application is permitted to access a given resource.&lt;&#x2F;p&gt;
&lt;h2 id=&quot;a-simple-example&quot;&gt;A &quot;simple&quot; example&lt;&#x2F;h2&gt;
&lt;p&gt;Access to the computer&#x27;s camera is gated behind the &lt;code&gt;kTCCServiceCamera&lt;&#x2F;code&gt; TCC
policy.  Frameworks that provide access to the camera, such as AVFoundation,
explicitly call &lt;code&gt;TCCAccessRequest(kTCCServiceCamera, …)&lt;&#x2F;code&gt; to ensure that the
application is permitted to access the camera. But as the camera is a hardware
device, a sufficiently motivated application could access it directly via the
IOKit framework. To safeguard against this, the Platform Sandbox Profile has a
policy in place for &lt;code&gt;iokit-open-user-client&lt;&#x2F;code&gt; operations that will trigger a TCC
prompt if a camera device is accessed directly via IOKit:&lt;&#x2F;p&gt;
&lt;pre data-lang=&quot;scm&quot; class=&quot;language-scm z-code&quot;&gt;&lt;code class=&quot;language-scm&quot; data-lang=&quot;scm&quot;&gt;&lt;span class=&quot;z-source z-lisp&quot;&gt;&lt;span class=&quot;z-meta z-group z-lisp&quot;&gt;&lt;span class=&quot;z-punctuation z-definition z-group z-begin z-lisp&quot;&gt;(&lt;&#x2F;span&gt;allow iokit&lt;span class=&quot;z-keyword z-operator z-arithmetic z-lisp&quot;&gt;-&lt;&#x2F;span&gt;&lt;span class=&quot;z-support z-function z-lisp&quot;&gt;open&lt;&#x2F;span&gt;&lt;span class=&quot;z-keyword z-operator z-arithmetic z-lisp&quot;&gt;-&lt;&#x2F;span&gt;user&lt;span class=&quot;z-keyword z-operator z-arithmetic z-lisp&quot;&gt;-&lt;&#x2F;span&gt;client
&lt;&#x2F;span&gt;&lt;&#x2F;span&gt;&lt;span class=&quot;z-source z-lisp&quot;&gt;&lt;span class=&quot;z-meta z-group z-lisp&quot;&gt;  &lt;span class=&quot;z-meta z-group z-lisp&quot;&gt;&lt;span class=&quot;z-punctuation z-definition z-group z-begin z-lisp&quot;&gt;(&lt;&#x2F;span&gt;&lt;span class=&quot;z-keyword z-control z-lisp&quot;&gt;with&lt;&#x2F;span&gt; user&lt;span class=&quot;z-keyword z-operator z-arithmetic z-lisp&quot;&gt;-&lt;&#x2F;span&gt;approval &lt;span class=&quot;z-string z-quoted z-double z-lisp&quot;&gt;&lt;span class=&quot;z-punctuation z-definition z-string z-begin z-lisp&quot;&gt;&amp;quot;&lt;&#x2F;span&gt;kTCCServiceCamera&lt;span class=&quot;z-punctuation z-definition z-string z-end z-lisp&quot;&gt;&amp;quot;&lt;&#x2F;span&gt;&lt;&#x2F;span&gt;&lt;span class=&quot;z-punctuation z-definition z-group z-end z-lisp&quot;&gt;)&lt;&#x2F;span&gt;&lt;&#x2F;span&gt;
&lt;&#x2F;span&gt;&lt;&#x2F;span&gt;&lt;span class=&quot;z-source z-lisp&quot;&gt;&lt;span class=&quot;z-meta z-group z-lisp&quot;&gt;  &lt;span class=&quot;z-meta z-group z-lisp&quot;&gt;&lt;span class=&quot;z-punctuation z-definition z-group z-begin z-lisp&quot;&gt;(&lt;&#x2F;span&gt;&lt;span class=&quot;z-support z-function z-lisp&quot;&gt;require&lt;&#x2F;span&gt;&lt;span class=&quot;z-keyword z-operator z-arithmetic z-lisp&quot;&gt;-&lt;&#x2F;span&gt;all
&lt;&#x2F;span&gt;&lt;&#x2F;span&gt;&lt;&#x2F;span&gt;&lt;span class=&quot;z-source z-lisp&quot;&gt;&lt;span class=&quot;z-meta z-group z-lisp&quot;&gt;&lt;span class=&quot;z-meta z-group z-lisp&quot;&gt;    &lt;span class=&quot;z-meta z-group z-lisp&quot;&gt;&lt;span class=&quot;z-punctuation z-definition z-group z-begin z-lisp&quot;&gt;(&lt;&#x2F;span&gt;process&lt;span class=&quot;z-keyword z-operator z-arithmetic z-lisp&quot;&gt;-&lt;&#x2F;span&gt;attribute is&lt;span class=&quot;z-keyword z-operator z-arithmetic z-lisp&quot;&gt;-&lt;&#x2F;span&gt;sandcastle&lt;span class=&quot;z-keyword z-operator z-arithmetic z-lisp&quot;&gt;-&lt;&#x2F;span&gt;constrained&lt;span class=&quot;z-punctuation z-definition z-group z-end z-lisp&quot;&gt;)&lt;&#x2F;span&gt;&lt;&#x2F;span&gt;
&lt;&#x2F;span&gt;&lt;&#x2F;span&gt;&lt;&#x2F;span&gt;&lt;span class=&quot;z-source z-lisp&quot;&gt;&lt;span class=&quot;z-meta z-group z-lisp&quot;&gt;&lt;span class=&quot;z-meta z-group z-lisp&quot;&gt;    &lt;span class=&quot;z-meta z-group z-lisp&quot;&gt;&lt;span class=&quot;z-punctuation z-definition z-group z-begin z-lisp&quot;&gt;(&lt;&#x2F;span&gt;&lt;span class=&quot;z-support z-function z-lisp&quot;&gt;require&lt;&#x2F;span&gt;&lt;span class=&quot;z-keyword z-operator z-arithmetic z-lisp&quot;&gt;-&lt;&#x2F;span&gt;any
&lt;&#x2F;span&gt;&lt;&#x2F;span&gt;&lt;&#x2F;span&gt;&lt;&#x2F;span&gt;&lt;span class=&quot;z-source z-lisp&quot;&gt;&lt;span class=&quot;z-meta z-group z-lisp&quot;&gt;&lt;span class=&quot;z-meta z-group z-lisp&quot;&gt;&lt;span class=&quot;z-meta z-group z-lisp&quot;&gt;      &lt;span class=&quot;z-meta z-group z-lisp&quot;&gt;&lt;span class=&quot;z-punctuation z-definition z-group z-begin z-lisp&quot;&gt;(&lt;&#x2F;span&gt;&lt;span class=&quot;z-support z-function z-lisp&quot;&gt;require&lt;&#x2F;span&gt;&lt;span class=&quot;z-keyword z-operator z-arithmetic z-lisp&quot;&gt;-&lt;&#x2F;span&gt;all
&lt;&#x2F;span&gt;&lt;&#x2F;span&gt;&lt;&#x2F;span&gt;&lt;&#x2F;span&gt;&lt;&#x2F;span&gt;&lt;span class=&quot;z-source z-lisp&quot;&gt;&lt;span class=&quot;z-meta z-group z-lisp&quot;&gt;&lt;span class=&quot;z-meta z-group z-lisp&quot;&gt;&lt;span class=&quot;z-meta z-group z-lisp&quot;&gt;&lt;span class=&quot;z-meta z-group z-lisp&quot;&gt;        &lt;span class=&quot;z-meta z-group z-lisp&quot;&gt;&lt;span class=&quot;z-punctuation z-definition z-group z-begin z-lisp&quot;&gt;(&lt;&#x2F;span&gt;iokit&lt;span class=&quot;z-keyword z-operator z-arithmetic z-lisp&quot;&gt;-&lt;&#x2F;span&gt;registry&lt;span class=&quot;z-keyword z-operator z-arithmetic z-lisp&quot;&gt;-&lt;&#x2F;span&gt;entry&lt;span class=&quot;z-keyword z-operator z-arithmetic z-lisp&quot;&gt;-&lt;&#x2F;span&gt;class &lt;span class=&quot;z-string z-quoted z-double z-lisp&quot;&gt;&lt;span class=&quot;z-punctuation z-definition z-string z-begin z-lisp&quot;&gt;&amp;quot;&lt;&#x2F;span&gt;IOFireWireAVCUserClient&lt;span class=&quot;z-punctuation z-definition z-string z-end z-lisp&quot;&gt;&amp;quot;&lt;&#x2F;span&gt;&lt;&#x2F;span&gt;&lt;span class=&quot;z-punctuation z-definition z-group z-end z-lisp&quot;&gt;)&lt;&#x2F;span&gt;&lt;&#x2F;span&gt;
&lt;&#x2F;span&gt;&lt;&#x2F;span&gt;&lt;&#x2F;span&gt;&lt;&#x2F;span&gt;&lt;&#x2F;span&gt;&lt;span class=&quot;z-source z-lisp&quot;&gt;&lt;span class=&quot;z-meta z-group z-lisp&quot;&gt;&lt;span class=&quot;z-meta z-group z-lisp&quot;&gt;&lt;span class=&quot;z-meta z-group z-lisp&quot;&gt;&lt;span class=&quot;z-meta z-group z-lisp&quot;&gt;        &lt;span class=&quot;z-meta z-group z-lisp&quot;&gt;&lt;span class=&quot;z-punctuation z-definition z-group z-begin z-lisp&quot;&gt;(&lt;&#x2F;span&gt;&lt;span class=&quot;z-support z-function z-lisp&quot;&gt;require&lt;&#x2F;span&gt;&lt;span class=&quot;z-keyword z-operator z-arithmetic z-lisp&quot;&gt;-&lt;&#x2F;span&gt;any
&lt;&#x2F;span&gt;&lt;&#x2F;span&gt;&lt;&#x2F;span&gt;&lt;&#x2F;span&gt;&lt;&#x2F;span&gt;&lt;&#x2F;span&gt;&lt;span class=&quot;z-source z-lisp&quot;&gt;&lt;span class=&quot;z-meta z-group z-lisp&quot;&gt;&lt;span class=&quot;z-meta z-group z-lisp&quot;&gt;&lt;span class=&quot;z-meta z-group z-lisp&quot;&gt;&lt;span class=&quot;z-meta z-group z-lisp&quot;&gt;&lt;span class=&quot;z-meta z-group z-lisp&quot;&gt;          &lt;span class=&quot;z-meta z-group z-lisp&quot;&gt;&lt;span class=&quot;z-punctuation z-definition z-group z-begin z-lisp&quot;&gt;(&lt;&#x2F;span&gt;&lt;span class=&quot;z-support z-function z-lisp&quot;&gt;require&lt;&#x2F;span&gt;&lt;span class=&quot;z-keyword z-operator z-arithmetic z-lisp&quot;&gt;-&lt;&#x2F;span&gt;&lt;span class=&quot;z-keyword z-operator z-logical z-lisp&quot;&gt;not&lt;&#x2F;span&gt;
&lt;&#x2F;span&gt;&lt;&#x2F;span&gt;&lt;&#x2F;span&gt;&lt;&#x2F;span&gt;&lt;&#x2F;span&gt;&lt;&#x2F;span&gt;&lt;&#x2F;span&gt;&lt;span class=&quot;z-source z-lisp&quot;&gt;&lt;span class=&quot;z-meta z-group z-lisp&quot;&gt;&lt;span class=&quot;z-meta z-group z-lisp&quot;&gt;&lt;span class=&quot;z-meta z-group z-lisp&quot;&gt;&lt;span class=&quot;z-meta z-group z-lisp&quot;&gt;&lt;span class=&quot;z-meta z-group z-lisp&quot;&gt;&lt;span class=&quot;z-meta z-group z-lisp&quot;&gt;            &lt;span class=&quot;z-meta z-group z-lisp&quot;&gt;&lt;span class=&quot;z-punctuation z-definition z-group z-begin z-lisp&quot;&gt;(&lt;&#x2F;span&gt;signing&lt;span class=&quot;z-keyword z-operator z-arithmetic z-lisp&quot;&gt;-&lt;&#x2F;span&gt;identifier &lt;span class=&quot;z-string z-quoted z-double z-lisp&quot;&gt;&lt;span class=&quot;z-punctuation z-definition z-string z-begin z-lisp&quot;&gt;&amp;quot;&lt;&#x2F;span&gt;com.apple.AVCAssistant&lt;span class=&quot;z-punctuation z-definition z-string z-end z-lisp&quot;&gt;&amp;quot;&lt;&#x2F;span&gt;&lt;&#x2F;span&gt;&lt;span class=&quot;z-punctuation z-definition z-group z-end z-lisp&quot;&gt;)&lt;&#x2F;span&gt;&lt;&#x2F;span&gt;&lt;span class=&quot;z-punctuation z-definition z-group z-end z-lisp&quot;&gt;)&lt;&#x2F;span&gt;&lt;&#x2F;span&gt;
&lt;&#x2F;span&gt;&lt;&#x2F;span&gt;&lt;&#x2F;span&gt;&lt;&#x2F;span&gt;&lt;&#x2F;span&gt;&lt;&#x2F;span&gt;&lt;span class=&quot;z-source z-lisp&quot;&gt;&lt;span class=&quot;z-meta z-group z-lisp&quot;&gt;&lt;span class=&quot;z-meta z-group z-lisp&quot;&gt;&lt;span class=&quot;z-meta z-group z-lisp&quot;&gt;&lt;span class=&quot;z-meta z-group z-lisp&quot;&gt;&lt;span class=&quot;z-meta z-group z-lisp&quot;&gt;          &lt;span class=&quot;z-meta z-group z-lisp&quot;&gt;&lt;span class=&quot;z-punctuation z-definition z-group z-begin z-lisp&quot;&gt;(&lt;&#x2F;span&gt;&lt;span class=&quot;z-support z-function z-lisp&quot;&gt;require&lt;&#x2F;span&gt;&lt;span class=&quot;z-keyword z-operator z-arithmetic z-lisp&quot;&gt;-&lt;&#x2F;span&gt;&lt;span class=&quot;z-keyword z-operator z-logical z-lisp&quot;&gt;not&lt;&#x2F;span&gt;
&lt;&#x2F;span&gt;&lt;&#x2F;span&gt;&lt;&#x2F;span&gt;&lt;&#x2F;span&gt;&lt;&#x2F;span&gt;&lt;&#x2F;span&gt;&lt;&#x2F;span&gt;&lt;span class=&quot;z-source z-lisp&quot;&gt;&lt;span class=&quot;z-meta z-group z-lisp&quot;&gt;&lt;span class=&quot;z-meta z-group z-lisp&quot;&gt;&lt;span class=&quot;z-meta z-group z-lisp&quot;&gt;&lt;span class=&quot;z-meta z-group z-lisp&quot;&gt;&lt;span class=&quot;z-meta z-group z-lisp&quot;&gt;&lt;span class=&quot;z-meta z-group z-lisp&quot;&gt;            &lt;span class=&quot;z-meta z-group z-lisp&quot;&gt;&lt;span class=&quot;z-punctuation z-definition z-group z-begin z-lisp&quot;&gt;(&lt;&#x2F;span&gt;process&lt;span class=&quot;z-keyword z-operator z-arithmetic z-lisp&quot;&gt;-&lt;&#x2F;span&gt;attribute is&lt;span class=&quot;z-keyword z-operator z-arithmetic z-lisp&quot;&gt;-&lt;&#x2F;span&gt;platform&lt;span class=&quot;z-keyword z-operator z-arithmetic z-lisp&quot;&gt;-&lt;&#x2F;span&gt;binary&lt;span class=&quot;z-punctuation z-definition z-group z-end z-lisp&quot;&gt;)&lt;&#x2F;span&gt;&lt;&#x2F;span&gt;&lt;span class=&quot;z-punctuation z-definition z-group z-end z-lisp&quot;&gt;)&lt;&#x2F;span&gt;&lt;&#x2F;span&gt;&lt;span class=&quot;z-punctuation z-definition z-group z-end z-lisp&quot;&gt;)&lt;&#x2F;span&gt;&lt;&#x2F;span&gt;&lt;span class=&quot;z-punctuation z-definition z-group z-end z-lisp&quot;&gt;)&lt;&#x2F;span&gt;&lt;&#x2F;span&gt;
&lt;&#x2F;span&gt;&lt;&#x2F;span&gt;&lt;&#x2F;span&gt;&lt;&#x2F;span&gt;&lt;span class=&quot;z-source z-lisp&quot;&gt;&lt;span class=&quot;z-meta z-group z-lisp&quot;&gt;&lt;span class=&quot;z-meta z-group z-lisp&quot;&gt;&lt;span class=&quot;z-meta z-group z-lisp&quot;&gt;      &lt;span class=&quot;z-meta z-group z-lisp&quot;&gt;&lt;span class=&quot;z-punctuation z-definition z-group z-begin z-lisp&quot;&gt;(&lt;&#x2F;span&gt;&lt;span class=&quot;z-support z-function z-lisp&quot;&gt;require&lt;&#x2F;span&gt;&lt;span class=&quot;z-keyword z-operator z-arithmetic z-lisp&quot;&gt;-&lt;&#x2F;span&gt;all
&lt;&#x2F;span&gt;&lt;&#x2F;span&gt;&lt;&#x2F;span&gt;&lt;&#x2F;span&gt;&lt;&#x2F;span&gt;&lt;span class=&quot;z-source z-lisp&quot;&gt;&lt;span class=&quot;z-meta z-group z-lisp&quot;&gt;&lt;span class=&quot;z-meta z-group z-lisp&quot;&gt;&lt;span class=&quot;z-meta z-group z-lisp&quot;&gt;&lt;span class=&quot;z-meta z-group z-lisp&quot;&gt;        &lt;span class=&quot;z-meta z-group z-lisp&quot;&gt;&lt;span class=&quot;z-punctuation z-definition z-group z-begin z-lisp&quot;&gt;(&lt;&#x2F;span&gt;iokit&lt;span class=&quot;z-keyword z-operator z-arithmetic z-lisp&quot;&gt;-&lt;&#x2F;span&gt;registry&lt;span class=&quot;z-keyword z-operator z-arithmetic z-lisp&quot;&gt;-&lt;&#x2F;span&gt;entry&lt;span class=&quot;z-keyword z-operator z-arithmetic z-lisp&quot;&gt;-&lt;&#x2F;span&gt;class &lt;span class=&quot;z-string z-quoted z-double z-lisp&quot;&gt;&lt;span class=&quot;z-punctuation z-definition z-string z-begin z-lisp&quot;&gt;&amp;quot;&lt;&#x2F;span&gt;IOUSBInterfaceUserClientV2&lt;span class=&quot;z-punctuation z-definition z-string z-end z-lisp&quot;&gt;&amp;quot;&lt;&#x2F;span&gt;&lt;&#x2F;span&gt;&lt;span class=&quot;z-punctuation z-definition z-group z-end z-lisp&quot;&gt;)&lt;&#x2F;span&gt;&lt;&#x2F;span&gt;
&lt;&#x2F;span&gt;&lt;&#x2F;span&gt;&lt;&#x2F;span&gt;&lt;&#x2F;span&gt;&lt;&#x2F;span&gt;&lt;span class=&quot;z-source z-lisp&quot;&gt;&lt;span class=&quot;z-meta z-group z-lisp&quot;&gt;&lt;span class=&quot;z-meta z-group z-lisp&quot;&gt;&lt;span class=&quot;z-meta z-group z-lisp&quot;&gt;&lt;span class=&quot;z-meta z-group z-lisp&quot;&gt;        &lt;span class=&quot;z-meta z-group z-lisp&quot;&gt;&lt;span class=&quot;z-punctuation z-definition z-group z-begin z-lisp&quot;&gt;(&lt;&#x2F;span&gt;iokit&lt;span class=&quot;z-keyword z-operator z-arithmetic z-lisp&quot;&gt;-&lt;&#x2F;span&gt;usb&lt;span class=&quot;z-keyword z-operator z-arithmetic z-lisp&quot;&gt;-&lt;&#x2F;span&gt;interface&lt;span class=&quot;z-keyword z-operator z-arithmetic z-lisp&quot;&gt;-&lt;&#x2F;span&gt;class kUSBVideoInterfaceClass&lt;span class=&quot;z-punctuation z-definition z-group z-end z-lisp&quot;&gt;)&lt;&#x2F;span&gt;&lt;&#x2F;span&gt;
&lt;&#x2F;span&gt;&lt;&#x2F;span&gt;&lt;&#x2F;span&gt;&lt;&#x2F;span&gt;&lt;&#x2F;span&gt;&lt;span class=&quot;z-source z-lisp&quot;&gt;&lt;span class=&quot;z-meta z-group z-lisp&quot;&gt;&lt;span class=&quot;z-meta z-group z-lisp&quot;&gt;&lt;span class=&quot;z-meta z-group z-lisp&quot;&gt;&lt;span class=&quot;z-meta z-group z-lisp&quot;&gt;        &lt;span class=&quot;z-meta z-group z-lisp&quot;&gt;&lt;span class=&quot;z-punctuation z-definition z-group z-begin z-lisp&quot;&gt;(&lt;&#x2F;span&gt;&lt;span class=&quot;z-support z-function z-lisp&quot;&gt;require&lt;&#x2F;span&gt;&lt;span class=&quot;z-keyword z-operator z-arithmetic z-lisp&quot;&gt;-&lt;&#x2F;span&gt;any
&lt;&#x2F;span&gt;&lt;&#x2F;span&gt;&lt;&#x2F;span&gt;&lt;&#x2F;span&gt;&lt;&#x2F;span&gt;&lt;&#x2F;span&gt;&lt;span class=&quot;z-source z-lisp&quot;&gt;&lt;span class=&quot;z-meta z-group z-lisp&quot;&gt;&lt;span class=&quot;z-meta z-group z-lisp&quot;&gt;&lt;span class=&quot;z-meta z-group z-lisp&quot;&gt;&lt;span class=&quot;z-meta z-group z-lisp&quot;&gt;&lt;span class=&quot;z-meta z-group z-lisp&quot;&gt;          &lt;span class=&quot;z-meta z-group z-lisp&quot;&gt;&lt;span class=&quot;z-punctuation z-definition z-group z-begin z-lisp&quot;&gt;(&lt;&#x2F;span&gt;&lt;span class=&quot;z-support z-function z-lisp&quot;&gt;require&lt;&#x2F;span&gt;&lt;span class=&quot;z-keyword z-operator z-arithmetic z-lisp&quot;&gt;-&lt;&#x2F;span&gt;&lt;span class=&quot;z-keyword z-operator z-logical z-lisp&quot;&gt;not&lt;&#x2F;span&gt;
&lt;&#x2F;span&gt;&lt;&#x2F;span&gt;&lt;&#x2F;span&gt;&lt;&#x2F;span&gt;&lt;&#x2F;span&gt;&lt;&#x2F;span&gt;&lt;&#x2F;span&gt;&lt;span class=&quot;z-source z-lisp&quot;&gt;&lt;span class=&quot;z-meta z-group z-lisp&quot;&gt;&lt;span class=&quot;z-meta z-group z-lisp&quot;&gt;&lt;span class=&quot;z-meta z-group z-lisp&quot;&gt;&lt;span class=&quot;z-meta z-group z-lisp&quot;&gt;&lt;span class=&quot;z-meta z-group z-lisp&quot;&gt;&lt;span class=&quot;z-meta z-group z-lisp&quot;&gt;            &lt;span class=&quot;z-meta z-group z-lisp&quot;&gt;&lt;span class=&quot;z-punctuation z-definition z-group z-begin z-lisp&quot;&gt;(&lt;&#x2F;span&gt;process&lt;span class=&quot;z-keyword z-operator z-arithmetic z-lisp&quot;&gt;-&lt;&#x2F;span&gt;attribute is&lt;span class=&quot;z-keyword z-operator z-arithmetic z-lisp&quot;&gt;-&lt;&#x2F;span&gt;platform&lt;span class=&quot;z-keyword z-operator z-arithmetic z-lisp&quot;&gt;-&lt;&#x2F;span&gt;binary&lt;span class=&quot;z-punctuation z-definition z-group z-end z-lisp&quot;&gt;)&lt;&#x2F;span&gt;&lt;&#x2F;span&gt;&lt;span class=&quot;z-punctuation z-definition z-group z-end z-lisp&quot;&gt;)&lt;&#x2F;span&gt;&lt;&#x2F;span&gt;
&lt;&#x2F;span&gt;&lt;&#x2F;span&gt;&lt;&#x2F;span&gt;&lt;&#x2F;span&gt;&lt;&#x2F;span&gt;&lt;&#x2F;span&gt;&lt;span class=&quot;z-source z-lisp&quot;&gt;&lt;span class=&quot;z-meta z-group z-lisp&quot;&gt;&lt;span class=&quot;z-meta z-group z-lisp&quot;&gt;&lt;span class=&quot;z-meta z-group z-lisp&quot;&gt;&lt;span class=&quot;z-meta z-group z-lisp&quot;&gt;&lt;span class=&quot;z-meta z-group z-lisp&quot;&gt;          &lt;span class=&quot;z-meta z-group z-lisp&quot;&gt;&lt;span class=&quot;z-punctuation z-definition z-group z-begin z-lisp&quot;&gt;(&lt;&#x2F;span&gt;&lt;span class=&quot;z-support z-function z-lisp&quot;&gt;require&lt;&#x2F;span&gt;&lt;span class=&quot;z-keyword z-operator z-arithmetic z-lisp&quot;&gt;-&lt;&#x2F;span&gt;&lt;span class=&quot;z-keyword z-operator z-logical z-lisp&quot;&gt;not&lt;&#x2F;span&gt;
&lt;&#x2F;span&gt;&lt;&#x2F;span&gt;&lt;&#x2F;span&gt;&lt;&#x2F;span&gt;&lt;&#x2F;span&gt;&lt;&#x2F;span&gt;&lt;&#x2F;span&gt;&lt;span class=&quot;z-source z-lisp&quot;&gt;&lt;span class=&quot;z-meta z-group z-lisp&quot;&gt;&lt;span class=&quot;z-meta z-group z-lisp&quot;&gt;&lt;span class=&quot;z-meta z-group z-lisp&quot;&gt;&lt;span class=&quot;z-meta z-group z-lisp&quot;&gt;&lt;span class=&quot;z-meta z-group z-lisp&quot;&gt;&lt;span class=&quot;z-meta z-group z-lisp&quot;&gt;            &lt;span class=&quot;z-meta z-group z-lisp&quot;&gt;&lt;span class=&quot;z-punctuation z-definition z-group z-begin z-lisp&quot;&gt;(&lt;&#x2F;span&gt;signing&lt;span class=&quot;z-keyword z-operator z-arithmetic z-lisp&quot;&gt;-&lt;&#x2F;span&gt;identifier &lt;span class=&quot;z-string z-quoted z-double z-lisp&quot;&gt;&lt;span class=&quot;z-punctuation z-definition z-string z-begin z-lisp&quot;&gt;&amp;quot;&lt;&#x2F;span&gt;com.apple.VDCAssistant&lt;span class=&quot;z-punctuation z-definition z-string z-end z-lisp&quot;&gt;&amp;quot;&lt;&#x2F;span&gt;&lt;&#x2F;span&gt;&lt;span class=&quot;z-punctuation z-definition z-group z-end z-lisp&quot;&gt;)&lt;&#x2F;span&gt;&lt;&#x2F;span&gt;&lt;span class=&quot;z-punctuation z-definition z-group z-end z-lisp&quot;&gt;)&lt;&#x2F;span&gt;&lt;&#x2F;span&gt;&lt;span class=&quot;z-punctuation z-definition z-group z-end z-lisp&quot;&gt;)&lt;&#x2F;span&gt;&lt;&#x2F;span&gt;&lt;span class=&quot;z-punctuation z-definition z-group z-end z-lisp&quot;&gt;)&lt;&#x2F;span&gt;&lt;&#x2F;span&gt;
&lt;&#x2F;span&gt;&lt;&#x2F;span&gt;&lt;&#x2F;span&gt;&lt;&#x2F;span&gt;&lt;span class=&quot;z-source z-lisp&quot;&gt;&lt;span class=&quot;z-meta z-group z-lisp&quot;&gt;&lt;span class=&quot;z-meta z-group z-lisp&quot;&gt;&lt;span class=&quot;z-meta z-group z-lisp&quot;&gt;      &lt;span class=&quot;z-meta z-group z-lisp&quot;&gt;&lt;span class=&quot;z-punctuation z-definition z-group z-begin z-lisp&quot;&gt;(&lt;&#x2F;span&gt;&lt;span class=&quot;z-support z-function z-lisp&quot;&gt;require&lt;&#x2F;span&gt;&lt;span class=&quot;z-keyword z-operator z-arithmetic z-lisp&quot;&gt;-&lt;&#x2F;span&gt;all
&lt;&#x2F;span&gt;&lt;&#x2F;span&gt;&lt;&#x2F;span&gt;&lt;&#x2F;span&gt;&lt;&#x2F;span&gt;&lt;span class=&quot;z-source z-lisp&quot;&gt;&lt;span class=&quot;z-meta z-group z-lisp&quot;&gt;&lt;span class=&quot;z-meta z-group z-lisp&quot;&gt;&lt;span class=&quot;z-meta z-group z-lisp&quot;&gt;&lt;span class=&quot;z-meta z-group z-lisp&quot;&gt;        &lt;span class=&quot;z-meta z-group z-lisp&quot;&gt;&lt;span class=&quot;z-punctuation z-definition z-group z-begin z-lisp&quot;&gt;(&lt;&#x2F;span&gt;&lt;span class=&quot;z-support z-function z-lisp&quot;&gt;require&lt;&#x2F;span&gt;&lt;span class=&quot;z-keyword z-operator z-arithmetic z-lisp&quot;&gt;-&lt;&#x2F;span&gt;&lt;span class=&quot;z-keyword z-operator z-logical z-lisp&quot;&gt;not&lt;&#x2F;span&gt;
&lt;&#x2F;span&gt;&lt;&#x2F;span&gt;&lt;&#x2F;span&gt;&lt;&#x2F;span&gt;&lt;&#x2F;span&gt;&lt;&#x2F;span&gt;&lt;span class=&quot;z-source z-lisp&quot;&gt;&lt;span class=&quot;z-meta z-group z-lisp&quot;&gt;&lt;span class=&quot;z-meta z-group z-lisp&quot;&gt;&lt;span class=&quot;z-meta z-group z-lisp&quot;&gt;&lt;span class=&quot;z-meta z-group z-lisp&quot;&gt;&lt;span class=&quot;z-meta z-group z-lisp&quot;&gt;          &lt;span class=&quot;z-meta z-group z-lisp&quot;&gt;&lt;span class=&quot;z-punctuation z-definition z-group z-begin z-lisp&quot;&gt;(&lt;&#x2F;span&gt;%entitlement&lt;span class=&quot;z-keyword z-operator z-arithmetic z-lisp&quot;&gt;-&lt;&#x2F;span&gt;is&lt;span class=&quot;z-keyword z-operator z-arithmetic z-lisp&quot;&gt;-&lt;&#x2F;span&gt;bool&lt;span class=&quot;z-keyword z-operator z-arithmetic z-lisp&quot;&gt;-&lt;&#x2F;span&gt;true &lt;span class=&quot;z-string z-quoted z-double z-lisp&quot;&gt;&lt;span class=&quot;z-punctuation z-definition z-string z-begin z-lisp&quot;&gt;&amp;quot;&lt;&#x2F;span&gt;com.apple.camera.iokit-user-access&lt;span class=&quot;z-punctuation z-definition z-string z-end z-lisp&quot;&gt;&amp;quot;&lt;&#x2F;span&gt;&lt;&#x2F;span&gt;&lt;span class=&quot;z-punctuation z-definition z-group z-end z-lisp&quot;&gt;)&lt;&#x2F;span&gt;&lt;&#x2F;span&gt;&lt;span class=&quot;z-punctuation z-definition z-group z-end z-lisp&quot;&gt;)&lt;&#x2F;span&gt;&lt;&#x2F;span&gt;
&lt;&#x2F;span&gt;&lt;&#x2F;span&gt;&lt;&#x2F;span&gt;&lt;&#x2F;span&gt;&lt;&#x2F;span&gt;&lt;span class=&quot;z-source z-lisp&quot;&gt;&lt;span class=&quot;z-meta z-group z-lisp&quot;&gt;&lt;span class=&quot;z-meta z-group z-lisp&quot;&gt;&lt;span class=&quot;z-meta z-group z-lisp&quot;&gt;&lt;span class=&quot;z-meta z-group z-lisp&quot;&gt;        &lt;span class=&quot;z-meta z-group z-lisp&quot;&gt;&lt;span class=&quot;z-punctuation z-definition z-group z-begin z-lisp&quot;&gt;(&lt;&#x2F;span&gt;iokit&lt;span class=&quot;z-keyword z-operator z-arithmetic z-lisp&quot;&gt;-&lt;&#x2F;span&gt;registry&lt;span class=&quot;z-keyword z-operator z-arithmetic z-lisp&quot;&gt;-&lt;&#x2F;span&gt;entry&lt;span class=&quot;z-keyword z-operator z-arithmetic z-lisp&quot;&gt;-&lt;&#x2F;span&gt;class &lt;span class=&quot;z-string z-quoted z-double z-lisp&quot;&gt;&lt;span class=&quot;z-punctuation z-definition z-string z-begin z-lisp&quot;&gt;&amp;quot;&lt;&#x2F;span&gt;AppleCamInUserClient&lt;span class=&quot;z-punctuation z-definition z-string z-end z-lisp&quot;&gt;&amp;quot;&lt;&#x2F;span&gt;&lt;&#x2F;span&gt;&lt;span class=&quot;z-punctuation z-definition z-group z-end z-lisp&quot;&gt;)&lt;&#x2F;span&gt;&lt;&#x2F;span&gt;&lt;span class=&quot;z-punctuation z-definition z-group z-end z-lisp&quot;&gt;)&lt;&#x2F;span&gt;&lt;&#x2F;span&gt;&lt;span class=&quot;z-punctuation z-definition z-group z-end z-lisp&quot;&gt;)&lt;&#x2F;span&gt;&lt;&#x2F;span&gt;&lt;span class=&quot;z-punctuation z-definition z-group z-end z-lisp&quot;&gt;)&lt;&#x2F;span&gt;&lt;&#x2F;span&gt;&lt;span class=&quot;z-punctuation z-definition z-group z-end z-lisp&quot;&gt;)&lt;&#x2F;span&gt;&lt;&#x2F;span&gt;
&lt;&#x2F;span&gt;&lt;&#x2F;code&gt;&lt;&#x2F;pre&gt;
&lt;p&gt;This triggers a &lt;code&gt;kTCCServiceCamera&lt;&#x2F;code&gt; prompt for any access to
&lt;code&gt;IOFireWireAVCUserClient&lt;&#x2F;code&gt;, &lt;code&gt;IOUSBInterfaceUserClientV2&lt;&#x2F;code&gt; with class
&lt;code&gt;kUSBVideoInterfaceClass&lt;&#x2F;code&gt;, and &lt;code&gt;AppleCamInUserClient&lt;&#x2F;code&gt;. Platform binaries and
binaries with certain entitlements or identifiers are excluded from the
prompting.&lt;&#x2F;p&gt;
&lt;h2 id=&quot;storage-classes&quot;&gt;Storage classes&lt;&#x2F;h2&gt;
&lt;p&gt;One of the key attributes used within the Platform Sandbox Policy is the concept
of the &lt;strong&gt;storage class&lt;&#x2F;strong&gt; of a file system object. This is a way of classifying a
given file system object as containing some type of data that may need special
attention.&lt;&#x2F;p&gt;
&lt;p&gt;File system objects are tracked in the sandbox kernel extension as kernel
&lt;code&gt;vnode&lt;&#x2F;code&gt; objects. A given &lt;code&gt;vnode&lt;&#x2F;code&gt; is assigned to exactly one storage class at a
time, though the storage class it is assigned to can change. The sandbox kernel
extension caches the mapping from &lt;code&gt;vnode&lt;&#x2F;code&gt; objects to storage class to avoid
recomputing them. The cache is invalidated in response to certain events
that could cause the mapping to change.&lt;&#x2F;p&gt;
&lt;p&gt;Storage classes are assigned by the Platform Sandbox Policy. The special
&lt;code&gt;storage-class-map&lt;&#x2F;code&gt; sandbox operation is used along with the &lt;code&gt;(with assign-storage-class &quot;&amp;lt;class&amp;gt;&quot;)&lt;&#x2F;code&gt; action modifier to determine which storage
class should be assigned to a given file system object. Within this portion of
the policy, the same filter operations that are applicable to file system
operations are available, along with predicates involving process or system
attributes.&lt;&#x2F;p&gt;
&lt;p&gt;There are around 130 storage classes defined by the Platform Sandbox Policy as
of macOS 15.1. Most of the storage classes describe data as belonging to a
specific application or framework (&lt;code&gt;CloudKit&lt;&#x2F;code&gt;, &lt;code&gt;FaceTime&lt;&#x2F;code&gt;, &lt;code&gt;Safari&lt;&#x2F;code&gt;, and many
others), while a handful correspond directly to TCC policies (for instance,
&lt;code&gt;kTCCServiceAddressBook&lt;&#x2F;code&gt;, &lt;code&gt;kTCCServiceSystemPolicyAppBundles&lt;&#x2F;code&gt;,
&lt;code&gt;kTCCServiceSsytemPolicySysAdminFiles&lt;&#x2F;code&gt;). You can see the &lt;a href=&quot;https:&#x2F;&#x2F;gist.github.com&#x2F;bdash&#x2F;9a73475ed0676b3a3fed88d21628e6ab#file-storage-classes-scm&quot;&gt;complete list of storage classes
here&lt;&#x2F;a&gt;.&lt;&#x2F;p&gt;
&lt;h3 id=&quot;tcc-prompting-based-on-storage-classes&quot;&gt;TCC prompting based on storage classes&lt;&#x2F;h3&gt;
&lt;p&gt;Much like the &lt;code&gt;iokit-open-user-client&lt;&#x2F;code&gt; &#x2F; &lt;code&gt;kTCCServiceCamera&lt;&#x2F;code&gt; case presented above, file system
operations consider a combination of path, storage class, and process attributes to determine
whether an operation should result in a TCC prompt.&lt;&#x2F;p&gt;
&lt;h3 id=&quot;a-sampling-of-storage-classes&quot;&gt;A sampling of storage classes&lt;&#x2F;h3&gt;
&lt;h4 id=&quot;ktccservicesystempolicynetworkvolumes&quot;&gt;&lt;code&gt;kTCCServiceSystemPolicyNetworkVolumes&lt;&#x2F;code&gt;&lt;&#x2F;h4&gt;
&lt;pre data-lang=&quot;scm&quot; class=&quot;language-scm z-code&quot;&gt;&lt;code class=&quot;language-scm&quot; data-lang=&quot;scm&quot;&gt;&lt;span class=&quot;z-source z-lisp&quot;&gt;&lt;span class=&quot;z-meta z-group z-lisp&quot;&gt;&lt;span class=&quot;z-punctuation z-definition z-group z-begin z-lisp&quot;&gt;(&lt;&#x2F;span&gt;file&lt;span class=&quot;z-keyword z-operator z-arithmetic z-lisp&quot;&gt;-&lt;&#x2F;span&gt;attribute local&lt;span class=&quot;z-keyword z-operator z-arithmetic z-lisp&quot;&gt;-&lt;&#x2F;span&gt;filesystem&lt;span class=&quot;z-punctuation z-definition z-group z-end z-lisp&quot;&gt;)&lt;&#x2F;span&gt;&lt;&#x2F;span&gt;
&lt;&#x2F;span&gt;&lt;&#x2F;code&gt;&lt;&#x2F;pre&gt;
&lt;h4 id=&quot;ktccservicesystempolicyappbundles&quot;&gt;&lt;code&gt;kTCCServiceSystemPolicyAppBundles&lt;&#x2F;code&gt;&lt;&#x2F;h4&gt;
&lt;pre data-lang=&quot;scm&quot; class=&quot;language-scm z-code&quot;&gt;&lt;code class=&quot;language-scm&quot; data-lang=&quot;scm&quot;&gt;&lt;span class=&quot;z-source z-lisp&quot;&gt;&lt;span class=&quot;z-meta z-group z-lisp&quot;&gt;&lt;span class=&quot;z-punctuation z-definition z-group z-begin z-lisp&quot;&gt;(&lt;&#x2F;span&gt;file&lt;span class=&quot;z-keyword z-operator z-arithmetic z-lisp&quot;&gt;-&lt;&#x2F;span&gt;attribute app&lt;span class=&quot;z-keyword z-operator z-arithmetic z-lisp&quot;&gt;-&lt;&#x2F;span&gt;bundle&lt;span class=&quot;z-punctuation z-definition z-group z-end z-lisp&quot;&gt;)&lt;&#x2F;span&gt;&lt;&#x2F;span&gt;
&lt;&#x2F;span&gt;&lt;&#x2F;code&gt;&lt;&#x2F;pre&gt;
&lt;h4 id=&quot;ktccservicesystempolicydownloadsfolder&quot;&gt;&lt;code&gt;kTCCServiceSystemPolicyDownloadsFolder&lt;&#x2F;code&gt;&lt;&#x2F;h4&gt;
&lt;pre data-lang=&quot;scm&quot; class=&quot;language-scm z-code&quot;&gt;&lt;code class=&quot;language-scm&quot; data-lang=&quot;scm&quot;&gt;&lt;span class=&quot;z-source z-lisp&quot;&gt;&lt;span class=&quot;z-meta z-group z-lisp&quot;&gt;&lt;span class=&quot;z-punctuation z-definition z-group z-begin z-lisp&quot;&gt;(&lt;&#x2F;span&gt;path &lt;span class=&quot;z-meta z-group z-lisp&quot;&gt;&lt;span class=&quot;z-punctuation z-definition z-group z-begin z-lisp&quot;&gt;(&lt;&#x2F;span&gt;subpath &lt;span class=&quot;z-string z-quoted z-double z-lisp&quot;&gt;&lt;span class=&quot;z-punctuation z-definition z-string z-begin z-lisp&quot;&gt;&amp;quot;&lt;&#x2F;span&gt;${any_user_home}&#x2F;downloads&lt;span class=&quot;z-punctuation z-definition z-string z-end z-lisp&quot;&gt;&amp;quot;&lt;&#x2F;span&gt;&lt;&#x2F;span&gt;&lt;span class=&quot;z-punctuation z-definition z-group z-end z-lisp&quot;&gt;)&lt;&#x2F;span&gt;&lt;&#x2F;span&gt;&lt;span class=&quot;z-punctuation z-definition z-group z-end z-lisp&quot;&gt;)&lt;&#x2F;span&gt;&lt;&#x2F;span&gt;
&lt;&#x2F;span&gt;&lt;&#x2F;code&gt;&lt;&#x2F;pre&gt;
&lt;h4 id=&quot;ktccservicesystempolicysysadminfiles&quot;&gt;&lt;code&gt;kTCCServiceSystemPolicySysAdminFiles&lt;&#x2F;code&gt;&lt;&#x2F;h4&gt;
&lt;pre data-lang=&quot;scm&quot; class=&quot;language-scm z-code&quot;&gt;&lt;code class=&quot;language-scm&quot; data-lang=&quot;scm&quot;&gt;&lt;span class=&quot;z-source z-lisp&quot;&gt;&lt;span class=&quot;z-meta z-group z-lisp&quot;&gt;&lt;span class=&quot;z-punctuation z-definition z-group z-begin z-lisp&quot;&gt;(&lt;&#x2F;span&gt;path
&lt;&#x2F;span&gt;&lt;&#x2F;span&gt;&lt;span class=&quot;z-source z-lisp&quot;&gt;&lt;span class=&quot;z-meta z-group z-lisp&quot;&gt;  &lt;span class=&quot;z-string z-quoted z-double z-lisp&quot;&gt;&lt;span class=&quot;z-punctuation z-definition z-string z-begin z-lisp&quot;&gt;&amp;quot;&lt;&#x2F;span&gt;&#x2F;library&#x2F;application support&#x2F;apple&#x2F;remote desktop&#x2F;remotemanagement.launchd&lt;span class=&quot;z-punctuation z-definition z-string z-end z-lisp&quot;&gt;&amp;quot;&lt;&#x2F;span&gt;&lt;&#x2F;span&gt;
&lt;&#x2F;span&gt;&lt;&#x2F;span&gt;&lt;span class=&quot;z-source z-lisp&quot;&gt;&lt;span class=&quot;z-meta z-group z-lisp&quot;&gt;  &lt;span class=&quot;z-string z-quoted z-double z-lisp&quot;&gt;&lt;span class=&quot;z-punctuation z-definition z-string z-begin z-lisp&quot;&gt;&amp;quot;&lt;&#x2F;span&gt;&#x2F;library&#x2F;preferences&#x2F;com.apple.security.smartcard.plist&lt;span class=&quot;z-punctuation z-definition z-string z-end z-lisp&quot;&gt;&amp;quot;&lt;&#x2F;span&gt;&lt;&#x2F;span&gt;
&lt;&#x2F;span&gt;&lt;&#x2F;span&gt;&lt;span class=&quot;z-source z-lisp&quot;&gt;&lt;span class=&quot;z-meta z-group z-lisp&quot;&gt;  &lt;span class=&quot;z-string z-quoted z-double z-lisp&quot;&gt;&lt;span class=&quot;z-punctuation z-definition z-string z-begin z-lisp&quot;&gt;&amp;quot;&lt;&#x2F;span&gt;&#x2F;library&#x2F;preferences&#x2F;directoryservice&#x2F;directoryservice.plist&lt;span class=&quot;z-punctuation z-definition z-string z-end z-lisp&quot;&gt;&amp;quot;&lt;&#x2F;span&gt;&lt;&#x2F;span&gt;
&lt;&#x2F;span&gt;&lt;&#x2F;span&gt;&lt;span class=&quot;z-source z-lisp&quot;&gt;&lt;span class=&quot;z-meta z-group z-lisp&quot;&gt;  &lt;span class=&quot;z-string z-quoted z-double z-lisp&quot;&gt;&lt;span class=&quot;z-punctuation z-definition z-string z-begin z-lisp&quot;&gt;&amp;quot;&lt;&#x2F;span&gt;&#x2F;library&#x2F;preferences&#x2F;systemconfiguration&#x2F;com.apple.smb.server.plist&lt;span class=&quot;z-punctuation z-definition z-string z-end z-lisp&quot;&gt;&amp;quot;&lt;&#x2F;span&gt;&lt;&#x2F;span&gt;
&lt;&#x2F;span&gt;&lt;&#x2F;span&gt;&lt;span class=&quot;z-source z-lisp&quot;&gt;&lt;span class=&quot;z-meta z-group z-lisp&quot;&gt;  &lt;span class=&quot;z-string z-quoted z-double z-lisp&quot;&gt;&lt;span class=&quot;z-punctuation z-definition z-string z-begin z-lisp&quot;&gt;&amp;quot;&lt;&#x2F;span&gt;&#x2F;private&#x2F;etc&#x2F;auto_home&lt;span class=&quot;z-punctuation z-definition z-string z-end z-lisp&quot;&gt;&amp;quot;&lt;&#x2F;span&gt;&lt;&#x2F;span&gt;
&lt;&#x2F;span&gt;&lt;&#x2F;span&gt;&lt;span class=&quot;z-source z-lisp&quot;&gt;&lt;span class=&quot;z-meta z-group z-lisp&quot;&gt;  &lt;span class=&quot;z-string z-quoted z-double z-lisp&quot;&gt;&lt;span class=&quot;z-punctuation z-definition z-string z-begin z-lisp&quot;&gt;&amp;quot;&lt;&#x2F;span&gt;&#x2F;private&#x2F;etc&#x2F;auto_master&lt;span class=&quot;z-punctuation z-definition z-string z-end z-lisp&quot;&gt;&amp;quot;&lt;&#x2F;span&gt;&lt;&#x2F;span&gt;
&lt;&#x2F;span&gt;&lt;&#x2F;span&gt;&lt;span class=&quot;z-source z-lisp&quot;&gt;&lt;span class=&quot;z-meta z-group z-lisp&quot;&gt;  &lt;span class=&quot;z-string z-quoted z-double z-lisp&quot;&gt;&lt;span class=&quot;z-punctuation z-definition z-string z-begin z-lisp&quot;&gt;&amp;quot;&lt;&#x2F;span&gt;&#x2F;private&#x2F;etc&#x2F;autofs.conf&lt;span class=&quot;z-punctuation z-definition z-string z-end z-lisp&quot;&gt;&amp;quot;&lt;&#x2F;span&gt;&lt;&#x2F;span&gt;
&lt;&#x2F;span&gt;&lt;&#x2F;span&gt;&lt;span class=&quot;z-source z-lisp&quot;&gt;&lt;span class=&quot;z-meta z-group z-lisp&quot;&gt;  &lt;span class=&quot;z-string z-quoted z-double z-lisp&quot;&gt;&lt;span class=&quot;z-punctuation z-definition z-string z-begin z-lisp&quot;&gt;&amp;quot;&lt;&#x2F;span&gt;&#x2F;private&#x2F;etc&#x2F;crontab&lt;span class=&quot;z-punctuation z-definition z-string z-end z-lisp&quot;&gt;&amp;quot;&lt;&#x2F;span&gt;&lt;&#x2F;span&gt;
&lt;&#x2F;span&gt;&lt;&#x2F;span&gt;&lt;span class=&quot;z-source z-lisp&quot;&gt;&lt;span class=&quot;z-meta z-group z-lisp&quot;&gt;  &lt;span class=&quot;z-string z-quoted z-double z-lisp&quot;&gt;&lt;span class=&quot;z-punctuation z-definition z-string z-begin z-lisp&quot;&gt;&amp;quot;&lt;&#x2F;span&gt;&#x2F;private&#x2F;etc&#x2F;exports&lt;span class=&quot;z-punctuation z-definition z-string z-end z-lisp&quot;&gt;&amp;quot;&lt;&#x2F;span&gt;&lt;&#x2F;span&gt;
&lt;&#x2F;span&gt;&lt;&#x2F;span&gt;&lt;span class=&quot;z-source z-lisp&quot;&gt;&lt;span class=&quot;z-meta z-group z-lisp&quot;&gt;  &lt;span class=&quot;z-string z-quoted z-double z-lisp&quot;&gt;&lt;span class=&quot;z-punctuation z-definition z-string z-begin z-lisp&quot;&gt;&amp;quot;&lt;&#x2F;span&gt;&#x2F;private&#x2F;etc&#x2F;master.passwd&lt;span class=&quot;z-punctuation z-definition z-string z-end z-lisp&quot;&gt;&amp;quot;&lt;&#x2F;span&gt;&lt;&#x2F;span&gt;
&lt;&#x2F;span&gt;&lt;&#x2F;span&gt;&lt;span class=&quot;z-source z-lisp&quot;&gt;&lt;span class=&quot;z-meta z-group z-lisp&quot;&gt;  &lt;span class=&quot;z-string z-quoted z-double z-lisp&quot;&gt;&lt;span class=&quot;z-punctuation z-definition z-string z-begin z-lisp&quot;&gt;&amp;quot;&lt;&#x2F;span&gt;&#x2F;private&#x2F;etc&#x2F;passwd&lt;span class=&quot;z-punctuation z-definition z-string z-end z-lisp&quot;&gt;&amp;quot;&lt;&#x2F;span&gt;&lt;&#x2F;span&gt;
&lt;&#x2F;span&gt;&lt;&#x2F;span&gt;&lt;span class=&quot;z-source z-lisp&quot;&gt;&lt;span class=&quot;z-meta z-group z-lisp&quot;&gt;  &lt;span class=&quot;z-string z-quoted z-double z-lisp&quot;&gt;&lt;span class=&quot;z-punctuation z-definition z-string z-begin z-lisp&quot;&gt;&amp;quot;&lt;&#x2F;span&gt;&#x2F;private&#x2F;etc&#x2F;sudo.conf&lt;span class=&quot;z-punctuation z-definition z-string z-end z-lisp&quot;&gt;&amp;quot;&lt;&#x2F;span&gt;&lt;&#x2F;span&gt;
&lt;&#x2F;span&gt;&lt;&#x2F;span&gt;&lt;span class=&quot;z-source z-lisp&quot;&gt;&lt;span class=&quot;z-meta z-group z-lisp&quot;&gt;  &lt;span class=&quot;z-string z-quoted z-double z-lisp&quot;&gt;&lt;span class=&quot;z-punctuation z-definition z-string z-begin z-lisp&quot;&gt;&amp;quot;&lt;&#x2F;span&gt;&#x2F;usr&#x2F;lib&#x2F;cron&lt;span class=&quot;z-punctuation z-definition z-string z-end z-lisp&quot;&gt;&amp;quot;&lt;&#x2F;span&gt;&lt;&#x2F;span&gt;
&lt;&#x2F;span&gt;&lt;&#x2F;span&gt;&lt;span class=&quot;z-source z-lisp&quot;&gt;&lt;span class=&quot;z-meta z-group z-lisp&quot;&gt;  &lt;span class=&quot;z-meta z-group z-lisp&quot;&gt;&lt;span class=&quot;z-punctuation z-definition z-group z-begin z-lisp&quot;&gt;(&lt;&#x2F;span&gt;prefix &lt;span class=&quot;z-string z-quoted z-double z-lisp&quot;&gt;&lt;span class=&quot;z-punctuation z-definition z-string z-begin z-lisp&quot;&gt;&amp;quot;&lt;&#x2F;span&gt;&#x2F;private&#x2F;etc&#x2F;rc.&lt;span class=&quot;z-punctuation z-definition z-string z-end z-lisp&quot;&gt;&amp;quot;&lt;&#x2F;span&gt;&lt;&#x2F;span&gt;&lt;span class=&quot;z-punctuation z-definition z-group z-end z-lisp&quot;&gt;)&lt;&#x2F;span&gt;&lt;&#x2F;span&gt;
&lt;&#x2F;span&gt;&lt;&#x2F;span&gt;&lt;span class=&quot;z-source z-lisp&quot;&gt;&lt;span class=&quot;z-meta z-group z-lisp&quot;&gt;  &lt;span class=&quot;z-meta z-group z-lisp&quot;&gt;&lt;span class=&quot;z-punctuation z-definition z-group z-begin z-lisp&quot;&gt;(&lt;&#x2F;span&gt;subpath &lt;span class=&quot;z-string z-quoted z-double z-lisp&quot;&gt;&lt;span class=&quot;z-punctuation z-definition z-string z-begin z-lisp&quot;&gt;&amp;quot;&lt;&#x2F;span&gt;&#x2F;library&#x2F;directoryservices&#x2F;plugins&lt;span class=&quot;z-punctuation z-definition z-string z-end z-lisp&quot;&gt;&amp;quot;&lt;&#x2F;span&gt;&lt;&#x2F;span&gt;&lt;span class=&quot;z-punctuation z-definition z-group z-end z-lisp&quot;&gt;)&lt;&#x2F;span&gt;&lt;&#x2F;span&gt;
&lt;&#x2F;span&gt;&lt;&#x2F;span&gt;&lt;span class=&quot;z-source z-lisp&quot;&gt;&lt;span class=&quot;z-meta z-group z-lisp&quot;&gt;  &lt;span class=&quot;z-meta z-group z-lisp&quot;&gt;&lt;span class=&quot;z-punctuation z-definition z-group z-begin z-lisp&quot;&gt;(&lt;&#x2F;span&gt;subpath &lt;span class=&quot;z-string z-quoted z-double z-lisp&quot;&gt;&lt;span class=&quot;z-punctuation z-definition z-string z-begin z-lisp&quot;&gt;&amp;quot;&lt;&#x2F;span&gt;&#x2F;library&#x2F;perl&lt;span class=&quot;z-punctuation z-definition z-string z-end z-lisp&quot;&gt;&amp;quot;&lt;&#x2F;span&gt;&lt;&#x2F;span&gt;&lt;span class=&quot;z-punctuation z-definition z-group z-end z-lisp&quot;&gt;)&lt;&#x2F;span&gt;&lt;&#x2F;span&gt;
&lt;&#x2F;span&gt;&lt;&#x2F;span&gt;&lt;span class=&quot;z-source z-lisp&quot;&gt;&lt;span class=&quot;z-meta z-group z-lisp&quot;&gt;  &lt;span class=&quot;z-meta z-group z-lisp&quot;&gt;&lt;span class=&quot;z-punctuation z-definition z-group z-begin z-lisp&quot;&gt;(&lt;&#x2F;span&gt;subpath &lt;span class=&quot;z-string z-quoted z-double z-lisp&quot;&gt;&lt;span class=&quot;z-punctuation z-definition z-string z-begin z-lisp&quot;&gt;&amp;quot;&lt;&#x2F;span&gt;&#x2F;library&#x2F;preferences&#x2F;logging&lt;span class=&quot;z-punctuation z-definition z-string z-end z-lisp&quot;&gt;&amp;quot;&lt;&#x2F;span&gt;&lt;&#x2F;span&gt;&lt;span class=&quot;z-punctuation z-definition z-group z-end z-lisp&quot;&gt;)&lt;&#x2F;span&gt;&lt;&#x2F;span&gt;
&lt;&#x2F;span&gt;&lt;&#x2F;span&gt;&lt;span class=&quot;z-source z-lisp&quot;&gt;&lt;span class=&quot;z-meta z-group z-lisp&quot;&gt;  &lt;span class=&quot;z-meta z-group z-lisp&quot;&gt;&lt;span class=&quot;z-punctuation z-definition z-group z-begin z-lisp&quot;&gt;(&lt;&#x2F;span&gt;subpath &lt;span class=&quot;z-string z-quoted z-double z-lisp&quot;&gt;&lt;span class=&quot;z-punctuation z-definition z-string z-begin z-lisp&quot;&gt;&amp;quot;&lt;&#x2F;span&gt;&#x2F;private&#x2F;etc&#x2F;pam.d&lt;span class=&quot;z-punctuation z-definition z-string z-end z-lisp&quot;&gt;&amp;quot;&lt;&#x2F;span&gt;&lt;&#x2F;span&gt;&lt;span class=&quot;z-punctuation z-definition z-group z-end z-lisp&quot;&gt;)&lt;&#x2F;span&gt;&lt;&#x2F;span&gt;
&lt;&#x2F;span&gt;&lt;&#x2F;span&gt;&lt;span class=&quot;z-source z-lisp&quot;&gt;&lt;span class=&quot;z-meta z-group z-lisp&quot;&gt;  &lt;span class=&quot;z-meta z-group z-lisp&quot;&gt;&lt;span class=&quot;z-punctuation z-definition z-group z-begin z-lisp&quot;&gt;(&lt;&#x2F;span&gt;subpath &lt;span class=&quot;z-string z-quoted z-double z-lisp&quot;&gt;&lt;span class=&quot;z-punctuation z-definition z-string z-begin z-lisp&quot;&gt;&amp;quot;&lt;&#x2F;span&gt;&#x2F;private&#x2F;etc&#x2F;postfix&lt;span class=&quot;z-punctuation z-definition z-string z-end z-lisp&quot;&gt;&amp;quot;&lt;&#x2F;span&gt;&lt;&#x2F;span&gt;&lt;span class=&quot;z-punctuation z-definition z-group z-end z-lisp&quot;&gt;)&lt;&#x2F;span&gt;&lt;&#x2F;span&gt;
&lt;&#x2F;span&gt;&lt;&#x2F;span&gt;&lt;span class=&quot;z-source z-lisp&quot;&gt;&lt;span class=&quot;z-meta z-group z-lisp&quot;&gt;  &lt;span class=&quot;z-meta z-group z-lisp&quot;&gt;&lt;span class=&quot;z-punctuation z-definition z-group z-begin z-lisp&quot;&gt;(&lt;&#x2F;span&gt;subpath &lt;span class=&quot;z-string z-quoted z-double z-lisp&quot;&gt;&lt;span class=&quot;z-punctuation z-definition z-string z-begin z-lisp&quot;&gt;&amp;quot;&lt;&#x2F;span&gt;&#x2F;private&#x2F;var&#x2F;at&lt;span class=&quot;z-punctuation z-definition z-string z-end z-lisp&quot;&gt;&amp;quot;&lt;&#x2F;span&gt;&lt;&#x2F;span&gt;&lt;span class=&quot;z-punctuation z-definition z-group z-end z-lisp&quot;&gt;)&lt;&#x2F;span&gt;&lt;&#x2F;span&gt;
&lt;&#x2F;span&gt;&lt;&#x2F;span&gt;&lt;span class=&quot;z-source z-lisp&quot;&gt;&lt;span class=&quot;z-meta z-group z-lisp&quot;&gt;  &lt;span class=&quot;z-meta z-group z-lisp&quot;&gt;&lt;span class=&quot;z-punctuation z-definition z-group z-begin z-lisp&quot;&gt;(&lt;&#x2F;span&gt;subpath &lt;span class=&quot;z-string z-quoted z-double z-lisp&quot;&gt;&lt;span class=&quot;z-punctuation z-definition z-string z-begin z-lisp&quot;&gt;&amp;quot;&lt;&#x2F;span&gt;&#x2F;private&#x2F;var&#x2F;db&#x2F;com.apple.xpc.launchd&lt;span class=&quot;z-punctuation z-definition z-string z-end z-lisp&quot;&gt;&amp;quot;&lt;&#x2F;span&gt;&lt;&#x2F;span&gt;&lt;span class=&quot;z-punctuation z-definition z-group z-end z-lisp&quot;&gt;)&lt;&#x2F;span&gt;&lt;&#x2F;span&gt;&lt;span class=&quot;z-punctuation z-definition z-group z-end z-lisp&quot;&gt;)&lt;&#x2F;span&gt;&lt;&#x2F;span&gt;
&lt;&#x2F;span&gt;&lt;&#x2F;code&gt;&lt;&#x2F;pre&gt;
&lt;h4 id=&quot;safari&quot;&gt;&lt;code&gt;Safari&lt;&#x2F;code&gt;&lt;&#x2F;h4&gt;
&lt;pre data-lang=&quot;scm&quot; class=&quot;language-scm z-code&quot;&gt;&lt;code class=&quot;language-scm&quot; data-lang=&quot;scm&quot;&gt;&lt;span class=&quot;z-source z-lisp&quot;&gt;&lt;span class=&quot;z-meta z-group z-lisp&quot;&gt;&lt;span class=&quot;z-punctuation z-definition z-group z-begin z-lisp&quot;&gt;(&lt;&#x2F;span&gt;path
&lt;&#x2F;span&gt;&lt;&#x2F;span&gt;&lt;span class=&quot;z-source z-lisp&quot;&gt;&lt;span class=&quot;z-meta z-group z-lisp&quot;&gt;  &lt;span class=&quot;z-meta z-group z-lisp&quot;&gt;&lt;span class=&quot;z-punctuation z-definition z-group z-begin z-lisp&quot;&gt;(&lt;&#x2F;span&gt;subpath &lt;span class=&quot;z-string z-quoted z-double z-lisp&quot;&gt;&lt;span class=&quot;z-punctuation z-definition z-string z-begin z-lisp&quot;&gt;&amp;quot;&lt;&#x2F;span&gt;${any_user_home}&#x2F;library&#x2F;caches&#x2F;com.apple.safari&lt;span class=&quot;z-punctuation z-definition z-string z-end z-lisp&quot;&gt;&amp;quot;&lt;&#x2F;span&gt;&lt;&#x2F;span&gt;&lt;span class=&quot;z-punctuation z-definition z-group z-end z-lisp&quot;&gt;)&lt;&#x2F;span&gt;&lt;&#x2F;span&gt;
&lt;&#x2F;span&gt;&lt;&#x2F;span&gt;&lt;span class=&quot;z-source z-lisp&quot;&gt;&lt;span class=&quot;z-meta z-group z-lisp&quot;&gt;  &lt;span class=&quot;z-meta z-group z-lisp&quot;&gt;&lt;span class=&quot;z-punctuation z-definition z-group z-begin z-lisp&quot;&gt;(&lt;&#x2F;span&gt;subpath &lt;span class=&quot;z-string z-quoted z-double z-lisp&quot;&gt;&lt;span class=&quot;z-punctuation z-definition z-string z-begin z-lisp&quot;&gt;&amp;quot;&lt;&#x2F;span&gt;${any_user_home}&#x2F;library&#x2F;caches&#x2F;com.apple.safari.safebrowsing&lt;span class=&quot;z-punctuation z-definition z-string z-end z-lisp&quot;&gt;&amp;quot;&lt;&#x2F;span&gt;&lt;&#x2F;span&gt;&lt;span class=&quot;z-punctuation z-definition z-group z-end z-lisp&quot;&gt;)&lt;&#x2F;span&gt;&lt;&#x2F;span&gt;
&lt;&#x2F;span&gt;&lt;&#x2F;span&gt;&lt;span class=&quot;z-source z-lisp&quot;&gt;&lt;span class=&quot;z-meta z-group z-lisp&quot;&gt;  &lt;span class=&quot;z-meta z-group z-lisp&quot;&gt;&lt;span class=&quot;z-punctuation z-definition z-group z-begin z-lisp&quot;&gt;(&lt;&#x2F;span&gt;subpath &lt;span class=&quot;z-string z-quoted z-double z-lisp&quot;&gt;&lt;span class=&quot;z-punctuation z-definition z-string z-begin z-lisp&quot;&gt;&amp;quot;&lt;&#x2F;span&gt;${any_user_home}&#x2F;library&#x2F;caches&#x2F;com.apple.safaridavclient&lt;span class=&quot;z-punctuation z-definition z-string z-end z-lisp&quot;&gt;&amp;quot;&lt;&#x2F;span&gt;&lt;&#x2F;span&gt;&lt;span class=&quot;z-punctuation z-definition z-group z-end z-lisp&quot;&gt;)&lt;&#x2F;span&gt;&lt;&#x2F;span&gt;
&lt;&#x2F;span&gt;&lt;&#x2F;span&gt;&lt;span class=&quot;z-source z-lisp&quot;&gt;&lt;span class=&quot;z-meta z-group z-lisp&quot;&gt;  &lt;span class=&quot;z-meta z-group z-lisp&quot;&gt;&lt;span class=&quot;z-punctuation z-definition z-group z-begin z-lisp&quot;&gt;(&lt;&#x2F;span&gt;subpath &lt;span class=&quot;z-string z-quoted z-double z-lisp&quot;&gt;&lt;span class=&quot;z-punctuation z-definition z-string z-begin z-lisp&quot;&gt;&amp;quot;&lt;&#x2F;span&gt;${any_user_home}&#x2F;library&#x2F;caches&#x2F;com.apple.safaritechnologypreview&lt;span class=&quot;z-punctuation z-definition z-string z-end z-lisp&quot;&gt;&amp;quot;&lt;&#x2F;span&gt;&lt;&#x2F;span&gt;&lt;span class=&quot;z-punctuation z-definition z-group z-end z-lisp&quot;&gt;)&lt;&#x2F;span&gt;&lt;&#x2F;span&gt;
&lt;&#x2F;span&gt;&lt;&#x2F;span&gt;&lt;span class=&quot;z-source z-lisp&quot;&gt;&lt;span class=&quot;z-meta z-group z-lisp&quot;&gt;  &lt;span class=&quot;z-meta z-group z-lisp&quot;&gt;&lt;span class=&quot;z-punctuation z-definition z-group z-begin z-lisp&quot;&gt;(&lt;&#x2F;span&gt;subpath &lt;span class=&quot;z-string z-quoted z-double z-lisp&quot;&gt;&lt;span class=&quot;z-punctuation z-definition z-string z-begin z-lisp&quot;&gt;&amp;quot;&lt;&#x2F;span&gt;${any_user_home}&#x2F;library&#x2F;containers&#x2F;com.apple.safari&lt;span class=&quot;z-punctuation z-definition z-string z-end z-lisp&quot;&gt;&amp;quot;&lt;&#x2F;span&gt;&lt;&#x2F;span&gt;&lt;span class=&quot;z-punctuation z-definition z-group z-end z-lisp&quot;&gt;)&lt;&#x2F;span&gt;&lt;&#x2F;span&gt;
&lt;&#x2F;span&gt;&lt;&#x2F;span&gt;&lt;span class=&quot;z-source z-lisp&quot;&gt;&lt;span class=&quot;z-meta z-group z-lisp&quot;&gt;  &lt;span class=&quot;z-meta z-group z-lisp&quot;&gt;&lt;span class=&quot;z-punctuation z-definition z-group z-begin z-lisp&quot;&gt;(&lt;&#x2F;span&gt;subpath &lt;span class=&quot;z-string z-quoted z-double z-lisp&quot;&gt;&lt;span class=&quot;z-punctuation z-definition z-string z-begin z-lisp&quot;&gt;&amp;quot;&lt;&#x2F;span&gt;${any_user_home}&#x2F;library&#x2F;containers&#x2F;com.apple.safari.webapp&lt;span class=&quot;z-punctuation z-definition z-string z-end z-lisp&quot;&gt;&amp;quot;&lt;&#x2F;span&gt;&lt;&#x2F;span&gt;&lt;span class=&quot;z-punctuation z-definition z-group z-end z-lisp&quot;&gt;)&lt;&#x2F;span&gt;&lt;&#x2F;span&gt;
&lt;&#x2F;span&gt;&lt;&#x2F;span&gt;&lt;span class=&quot;z-source z-lisp&quot;&gt;&lt;span class=&quot;z-meta z-group z-lisp&quot;&gt;  &lt;span class=&quot;z-meta z-group z-lisp&quot;&gt;&lt;span class=&quot;z-punctuation z-definition z-group z-begin z-lisp&quot;&gt;(&lt;&#x2F;span&gt;subpath
&lt;&#x2F;span&gt;&lt;&#x2F;span&gt;&lt;&#x2F;span&gt;&lt;span class=&quot;z-source z-lisp&quot;&gt;&lt;span class=&quot;z-meta z-group z-lisp&quot;&gt;&lt;span class=&quot;z-meta z-group z-lisp&quot;&gt;    &lt;span class=&quot;z-string z-quoted z-double z-lisp&quot;&gt;&lt;span class=&quot;z-punctuation z-definition z-string z-begin z-lisp&quot;&gt;&amp;quot;&lt;&#x2F;span&gt;${any_user_home}&#x2F;library&#x2F;containers&#x2F;com.apple.safaritechnologypreview&lt;span class=&quot;z-punctuation z-definition z-string z-end z-lisp&quot;&gt;&amp;quot;&lt;&#x2F;span&gt;&lt;&#x2F;span&gt;&lt;span class=&quot;z-punctuation z-definition z-group z-end z-lisp&quot;&gt;)&lt;&#x2F;span&gt;&lt;&#x2F;span&gt;
&lt;&#x2F;span&gt;&lt;&#x2F;span&gt;&lt;span class=&quot;z-source z-lisp&quot;&gt;&lt;span class=&quot;z-meta z-group z-lisp&quot;&gt;  &lt;span class=&quot;z-meta z-group z-lisp&quot;&gt;&lt;span class=&quot;z-punctuation z-definition z-group z-begin z-lisp&quot;&gt;(&lt;&#x2F;span&gt;subpath &lt;span class=&quot;z-string z-quoted z-double z-lisp&quot;&gt;&lt;span class=&quot;z-punctuation z-definition z-string z-begin z-lisp&quot;&gt;&amp;quot;&lt;&#x2F;span&gt;${any_user_home}&#x2F;library&#x2F;safari&lt;span class=&quot;z-punctuation z-definition z-string z-end z-lisp&quot;&gt;&amp;quot;&lt;&#x2F;span&gt;&lt;&#x2F;span&gt;&lt;span class=&quot;z-punctuation z-definition z-group z-end z-lisp&quot;&gt;)&lt;&#x2F;span&gt;&lt;&#x2F;span&gt;
&lt;&#x2F;span&gt;&lt;&#x2F;span&gt;&lt;span class=&quot;z-source z-lisp&quot;&gt;&lt;span class=&quot;z-meta z-group z-lisp&quot;&gt;  &lt;span class=&quot;z-meta z-group z-lisp&quot;&gt;&lt;span class=&quot;z-punctuation z-definition z-group z-begin z-lisp&quot;&gt;(&lt;&#x2F;span&gt;subpath &lt;span class=&quot;z-string z-quoted z-double z-lisp&quot;&gt;&lt;span class=&quot;z-punctuation z-definition z-string z-begin z-lisp&quot;&gt;&amp;quot;&lt;&#x2F;span&gt;${any_user_home}&#x2F;library&#x2F;safaritechnologypreview&lt;span class=&quot;z-punctuation z-definition z-string z-end z-lisp&quot;&gt;&amp;quot;&lt;&#x2F;span&gt;&lt;&#x2F;span&gt;&lt;span class=&quot;z-punctuation z-definition z-group z-end z-lisp&quot;&gt;)&lt;&#x2F;span&gt;&lt;&#x2F;span&gt;&lt;span class=&quot;z-punctuation z-definition z-group z-end z-lisp&quot;&gt;)&lt;&#x2F;span&gt;&lt;&#x2F;span&gt;
&lt;&#x2F;span&gt;&lt;&#x2F;code&gt;&lt;&#x2F;pre&gt;
</content>
        
    </entry>
    <entry xml:lang="en">
        <title>Sandboxing on macOS</title>
        <published>2024-11-27T00:00:00+00:00</published>
        <updated>2024-11-27T00:00:00+00:00</updated>
        
        <author>
          <name>
            
              Unknown
            
          </name>
        </author>
        
        <link rel="alternate" type="text/html" href="https://bdash.net.nz/posts/sandboxing-on-macos/"/>
        <id>https://bdash.net.nz/posts/sandboxing-on-macos/</id>
        
        <content type="html" xml:base="https://bdash.net.nz/posts/sandboxing-on-macos/">&lt;h1 id=&quot;background&quot;&gt;Background&lt;&#x2F;h1&gt;
&lt;p&gt;This is an overview of macOS&#x27;s built-in support for application sandboxing. It
covers how sandboxing behaves from an application&#x27;s perspective, how sandbox
policies are expressed, and how they&#x27;re enforced by the macOS kernel. The goal
is to help developers for non-Mac platforms understand what sandboxing entails
on the Mac, and to provide macOS developers with a deeper understanding of how
sandboxing works under the hood.&lt;&#x2F;p&gt;
&lt;p&gt;While I discuss sandboxing here in the context of macOS, much of the
implementation and resulting behavior are shared with Apple&#x27;s other platforms
(iOS, iPadOS, tvOS, etc). The most significant differences are that on those
other platforms, sandboxing is mandatory for third-party applications, and there
is no support for using custom sandbox policies in third-party applications.&lt;&#x2F;p&gt;
&lt;h2 id=&quot;what-is-sandboxing&quot;&gt;What is sandboxing?&lt;&#x2F;h2&gt;
&lt;p&gt;Sandboxing a process is a means of placing hard limits on the operations it can
perform. An application may be sandboxed for one of two reasons:&lt;&#x2F;p&gt;
&lt;ol&gt;
&lt;li&gt;
&lt;p&gt;&lt;strong&gt;Security hardening&lt;&#x2F;strong&gt;&lt;&#x2F;p&gt;
&lt;p&gt;In this context, the goal is to limit the impact of an attacker gaining code execution
within a sandboxed process. It places additional barriers between the initial
code execution and the ability for the attacker to execute other applications or
access resources such as user data on disk. This is the motiviation for sandboxing
processes like web browser rendering engines and other applications that process
complex data from from the internet.&lt;&#x2F;p&gt;
&lt;&#x2F;li&gt;
&lt;li&gt;
&lt;p&gt;&lt;strong&gt;User privacy&lt;&#x2F;strong&gt;&lt;&#x2F;p&gt;
&lt;p&gt;For many third-party applications, sandboxing is a demonstration that they
take user privacy seriously rather than a security mitigation. This is
particularly true of applications that use the App Sandbox policy as it
places strict limits on which parts of the filesystem an application can
access without the user explicitly granting them access via the system Open
dialog.&lt;&#x2F;p&gt;
&lt;&#x2F;li&gt;
&lt;&#x2F;ol&gt;
&lt;p&gt;Real-world sandbox policies block most operations by default and contain an
allow-list of permitted operations. In a perfect world, the sandbox for a
process is designed such that only the resources or operations needed during
normal execution of the process are available to it. In practice, the large
amount of code used in a typical process, both within the application itself and
provided by operating system libraries, make it difficult to tailor such a tight
sandbox. As a result most sandboxes evolve over time as the resources accessed
by an application change or the resource usage by system libraries becomes
better understood.&lt;&#x2F;p&gt;
&lt;h1 id=&quot;sandboxing-on-macos&quot;&gt;Sandboxing on macOS&lt;&#x2F;h1&gt;
&lt;p&gt;Sandboxing on macOS is implemented via the Sandbox kernel extension and controlled via the
&lt;a href=&quot;https:&#x2F;&#x2F;manp.gs&#x2F;mac&#x2F;7&#x2F;sandbox&quot;&gt;&lt;code&gt;sandbox(7)&lt;&#x2F;code&gt;&lt;&#x2F;a&gt; family of userspace APIs.&lt;&#x2F;p&gt;
&lt;h2 id=&quot;sandboxing-from-an-application-s-perspective&quot;&gt;Sandboxing from an application&#x27;s perspective&lt;&#x2F;h2&gt;
&lt;h3 id=&quot;types-of-application-sandbox&quot;&gt;Types of application sandbox&lt;&#x2F;h3&gt;
&lt;p&gt;There are two main ways that an application can run in a sandbox:&lt;&#x2F;p&gt;
&lt;ol&gt;
&lt;li&gt;
&lt;p&gt;It can explicitly apply a sandbox to itself using the &lt;code&gt;sandbox(7)&lt;&#x2F;code&gt; family of
APIs, most of which are undocumented. These APIs provide full control over the
policy that is applied.&lt;&#x2F;p&gt;
&lt;&#x2F;li&gt;
&lt;li&gt;
&lt;p&gt;It can opt into the App Sandbox via an entitlement. The App Sandbox is a predefined
sandbox policy provided by macOS that uses process attributes, such as the presence
of specific entitlements, to determine what resources should be accessible within the
sandbox. Use of the App Sandbox is required for third-party applications distributed
via the Mac App Store.&lt;&#x2F;p&gt;
&lt;&#x2F;li&gt;
&lt;&#x2F;ol&gt;
&lt;p&gt;The opaque and inflexible nature of the App Sandbox means that many large, third-party
applications that are distributed outside of the Mac App Store choose to use custom sandox
policies rather than the App Sandbox.&lt;&#x2F;p&gt;
&lt;h3 id=&quot;how-does-an-application-become-sandboxed&quot;&gt;How does an application become sandboxed?&lt;&#x2F;h3&gt;
&lt;p&gt;An application using the App Sandbox entitlement will be sandboxed automatically
by initializers in &lt;code&gt;libSystem&lt;&#x2F;code&gt; that run very early during an application&#x27;s launch.&lt;&#x2F;p&gt;
&lt;p&gt;An application not using the App Sandbox entitlement must explicitly apply a
sandbox policy to itself using an API such as &lt;code&gt;sandbox_init_with_parameters&lt;&#x2F;code&gt;.&lt;&#x2F;p&gt;
&lt;p&gt;It is not possible to sandbox an existing process from the outside. The process
must apply the sandbox to itself.&lt;&#x2F;p&gt;
&lt;p&gt;Once a process has a sandbox applied to it, it is not possible for it to disable
or remove the sandbox, nor is it possible for it to apply additional sandbox
policies. Sandboxes can be inherited when a subproces is spawned by a sandboxed
process.&lt;&#x2F;p&gt;
&lt;h3 id=&quot;what-happens-if-the-sandbox-policy-is-violated&quot;&gt;What happens if the sandbox policy is violated?&lt;&#x2F;h3&gt;
&lt;p&gt;By default, violating a sandbox policy results in the system call, or other operation that triggered
the violation, failing with &lt;code&gt;EPERM&lt;&#x2F;code&gt; (operation not permitted). It is up to the calling code to handle
this error gracefully.&lt;&#x2F;p&gt;
&lt;p&gt;The sandbox kernel extension also logs a message to the system console, and &lt;code&gt;sandboxd&lt;&#x2F;code&gt;
(a userspace helper) may generate a violation report that includes a backtrace of
the thread that triggered the violation. This can be used to track down what code was
responsible for the violation.&lt;&#x2F;p&gt;
&lt;p&gt;Sandbox policies can control this behavior via action modifiers. See &lt;a href=&quot;https:&#x2F;&#x2F;bdash.net.nz&#x2F;posts&#x2F;sandboxing-on-macos&#x2F;#sandbox-policy-evaluation&quot;&gt;Sandbox policy evaluation&lt;&#x2F;a&gt;
for more detail.&lt;&#x2F;p&gt;
&lt;h3 id=&quot;what-does-a-sandbox-policy-look-like&quot;&gt;What does a sandbox policy look like?&lt;&#x2F;h3&gt;
&lt;p&gt;Sandbox policies are written in a dialect of Scheme known as SBPL. The policies
are interpreted via an interpreter within &lt;code&gt;libsandbox&lt;&#x2F;code&gt;, based on
&lt;a href=&quot;https:&#x2F;&#x2F;tinyscheme.sourceforge.net&#x2F;home.html&quot;&gt;TinyScheme&lt;&#x2F;a&gt;, which generates a
compiled representation of the policy that it passes to the Sandbox kernel
extension.&lt;&#x2F;p&gt;
&lt;pre data-lang=&quot;scm&quot; class=&quot;language-scm z-code&quot;&gt;&lt;code class=&quot;language-scm&quot; data-lang=&quot;scm&quot;&gt;&lt;span class=&quot;z-source z-lisp&quot;&gt;&lt;span class=&quot;z-comment z-line z-semicolon z-lisp&quot;&gt;&lt;span class=&quot;z-punctuation z-definition z-comment z-lisp&quot;&gt;;&lt;&#x2F;span&gt;; All operations not explicitly allowed will be denied.
&lt;&#x2F;span&gt;&lt;&#x2F;span&gt;&lt;span class=&quot;z-source z-lisp&quot;&gt;&lt;span class=&quot;z-meta z-group z-lisp&quot;&gt;&lt;span class=&quot;z-punctuation z-definition z-group z-begin z-lisp&quot;&gt;(&lt;&#x2F;span&gt;default deny&lt;span class=&quot;z-punctuation z-definition z-group z-end z-lisp&quot;&gt;)&lt;&#x2F;span&gt;&lt;&#x2F;span&gt;
&lt;&#x2F;span&gt;&lt;span class=&quot;z-source z-lisp&quot;&gt;&lt;span class=&quot;z-comment z-line z-semicolon z-lisp&quot;&gt;&lt;span class=&quot;z-punctuation z-definition z-comment z-lisp&quot;&gt;;&lt;&#x2F;span&gt;; Allow reading from &#x2F;tmp&#x2F;foo and the directory &#x2F;tmp&#x2F;bar
&lt;&#x2F;span&gt;&lt;&#x2F;span&gt;&lt;span class=&quot;z-source z-lisp&quot;&gt;&lt;span class=&quot;z-comment z-line z-semicolon z-lisp&quot;&gt;&lt;span class=&quot;z-punctuation z-definition z-comment z-lisp&quot;&gt;;&lt;&#x2F;span&gt;; and any files below it.
&lt;&#x2F;span&gt;&lt;&#x2F;span&gt;&lt;span class=&quot;z-source z-lisp&quot;&gt;&lt;span class=&quot;z-meta z-group z-lisp&quot;&gt;&lt;span class=&quot;z-punctuation z-definition z-group z-begin z-lisp&quot;&gt;(&lt;&#x2F;span&gt;allow file&lt;span class=&quot;z-keyword z-operator z-arithmetic z-lisp&quot;&gt;-&lt;&#x2F;span&gt;&lt;span class=&quot;z-support z-function z-lisp&quot;&gt;read&lt;&#x2F;span&gt;&lt;span class=&quot;z-keyword z-operator z-arithmetic z-lisp&quot;&gt;*&lt;&#x2F;span&gt; &lt;span class=&quot;z-meta z-group z-lisp&quot;&gt;&lt;span class=&quot;z-punctuation z-definition z-group z-begin z-lisp&quot;&gt;(&lt;&#x2F;span&gt;path &lt;span class=&quot;z-string z-quoted z-double z-lisp&quot;&gt;&lt;span class=&quot;z-punctuation z-definition z-string z-begin z-lisp&quot;&gt;&amp;quot;&lt;&#x2F;span&gt;&#x2F;tmp&#x2F;foo&lt;span class=&quot;z-punctuation z-definition z-string z-end z-lisp&quot;&gt;&amp;quot;&lt;&#x2F;span&gt;&lt;&#x2F;span&gt;&lt;span class=&quot;z-punctuation z-definition z-group z-end z-lisp&quot;&gt;)&lt;&#x2F;span&gt;&lt;&#x2F;span&gt; &lt;span class=&quot;z-meta z-group z-lisp&quot;&gt;&lt;span class=&quot;z-punctuation z-definition z-group z-begin z-lisp&quot;&gt;(&lt;&#x2F;span&gt;subpath &lt;span class=&quot;z-string z-quoted z-double z-lisp&quot;&gt;&lt;span class=&quot;z-punctuation z-definition z-string z-begin z-lisp&quot;&gt;&amp;quot;&lt;&#x2F;span&gt;&#x2F;tmp&#x2F;bar&lt;span class=&quot;z-punctuation z-definition z-string z-end z-lisp&quot;&gt;&amp;quot;&lt;&#x2F;span&gt;&lt;&#x2F;span&gt;&lt;span class=&quot;z-punctuation z-definition z-group z-end z-lisp&quot;&gt;)&lt;&#x2F;span&gt;&lt;&#x2F;span&gt;&lt;span class=&quot;z-punctuation z-definition z-group z-end z-lisp&quot;&gt;)&lt;&#x2F;span&gt;&lt;&#x2F;span&gt;
&lt;&#x2F;span&gt;&lt;span class=&quot;z-source z-lisp&quot;&gt;&lt;span class=&quot;z-comment z-line z-semicolon z-lisp&quot;&gt;&lt;span class=&quot;z-punctuation z-definition z-comment z-lisp&quot;&gt;;&lt;&#x2F;span&gt;; Allow sysctl kern.hostname, but do it noisily.
&lt;&#x2F;span&gt;&lt;&#x2F;span&gt;&lt;span class=&quot;z-source z-lisp&quot;&gt;&lt;span class=&quot;z-meta z-group z-lisp&quot;&gt;&lt;span class=&quot;z-punctuation z-definition z-group z-begin z-lisp&quot;&gt;(&lt;&#x2F;span&gt;allow &lt;span class=&quot;z-meta z-group z-lisp&quot;&gt;&lt;span class=&quot;z-punctuation z-definition z-group z-begin z-lisp&quot;&gt;(&lt;&#x2F;span&gt;&lt;span class=&quot;z-keyword z-control z-lisp&quot;&gt;with&lt;&#x2F;span&gt; report&lt;span class=&quot;z-punctuation z-definition z-group z-end z-lisp&quot;&gt;)&lt;&#x2F;span&gt;&lt;&#x2F;span&gt; sysctl &lt;span class=&quot;z-meta z-group z-lisp&quot;&gt;&lt;span class=&quot;z-punctuation z-definition z-group z-begin z-lisp&quot;&gt;(&lt;&#x2F;span&gt;sysctl&lt;span class=&quot;z-keyword z-operator z-arithmetic z-lisp&quot;&gt;-&lt;&#x2F;span&gt;name &lt;span class=&quot;z-string z-quoted z-double z-lisp&quot;&gt;&lt;span class=&quot;z-punctuation z-definition z-string z-begin z-lisp&quot;&gt;&amp;quot;&lt;&#x2F;span&gt;kern.hostname&lt;span class=&quot;z-punctuation z-definition z-string z-end z-lisp&quot;&gt;&amp;quot;&lt;&#x2F;span&gt;&lt;&#x2F;span&gt;&lt;span class=&quot;z-punctuation z-definition z-group z-end z-lisp&quot;&gt;)&lt;&#x2F;span&gt;&lt;&#x2F;span&gt;&lt;span class=&quot;z-punctuation z-definition z-group z-end z-lisp&quot;&gt;)&lt;&#x2F;span&gt;&lt;&#x2F;span&gt;
&lt;&#x2F;span&gt;&lt;span class=&quot;z-source z-lisp&quot;&gt;&lt;span class=&quot;z-comment z-line z-semicolon z-lisp&quot;&gt;&lt;span class=&quot;z-punctuation z-definition z-comment z-lisp&quot;&gt;;&lt;&#x2F;span&gt;; Allow creating new files below &#x2F;tmp&#x2F;no-symlinks as long
&lt;&#x2F;span&gt;&lt;&#x2F;span&gt;&lt;span class=&quot;z-source z-lisp&quot;&gt;&lt;span class=&quot;z-comment z-line z-semicolon z-lisp&quot;&gt;&lt;span class=&quot;z-punctuation z-definition z-comment z-lisp&quot;&gt;;&lt;&#x2F;span&gt;; as they aren&amp;#39;t symlinks.
&lt;&#x2F;span&gt;&lt;&#x2F;span&gt;&lt;span class=&quot;z-source z-lisp&quot;&gt;&lt;span class=&quot;z-meta z-group z-lisp&quot;&gt;&lt;span class=&quot;z-punctuation z-definition z-group z-begin z-lisp&quot;&gt;(&lt;&#x2F;span&gt;allow file&lt;span class=&quot;z-keyword z-operator z-arithmetic z-lisp&quot;&gt;-&lt;&#x2F;span&gt;&lt;span class=&quot;z-support z-function z-lisp&quot;&gt;write&lt;&#x2F;span&gt;&lt;span class=&quot;z-keyword z-operator z-arithmetic z-lisp&quot;&gt;-&lt;&#x2F;span&gt;create&lt;span class=&quot;z-keyword z-operator z-arithmetic z-lisp&quot;&gt;*&lt;&#x2F;span&gt;
&lt;&#x2F;span&gt;&lt;&#x2F;span&gt;&lt;span class=&quot;z-source z-lisp&quot;&gt;&lt;span class=&quot;z-meta z-group z-lisp&quot;&gt;  &lt;span class=&quot;z-meta z-group z-lisp&quot;&gt;&lt;span class=&quot;z-punctuation z-definition z-group z-begin z-lisp&quot;&gt;(&lt;&#x2F;span&gt;&lt;span class=&quot;z-support z-function z-lisp&quot;&gt;require&lt;&#x2F;span&gt;&lt;span class=&quot;z-keyword z-operator z-arithmetic z-lisp&quot;&gt;-&lt;&#x2F;span&gt;all
&lt;&#x2F;span&gt;&lt;&#x2F;span&gt;&lt;&#x2F;span&gt;&lt;span class=&quot;z-source z-lisp&quot;&gt;&lt;span class=&quot;z-meta z-group z-lisp&quot;&gt;&lt;span class=&quot;z-meta z-group z-lisp&quot;&gt;  &lt;span class=&quot;z-meta z-group z-lisp&quot;&gt;&lt;span class=&quot;z-punctuation z-definition z-group z-begin z-lisp&quot;&gt;(&lt;&#x2F;span&gt;&lt;span class=&quot;z-support z-function z-lisp&quot;&gt;require&lt;&#x2F;span&gt;&lt;span class=&quot;z-keyword z-operator z-arithmetic z-lisp&quot;&gt;-&lt;&#x2F;span&gt;&lt;span class=&quot;z-keyword z-operator z-logical z-lisp&quot;&gt;not&lt;&#x2F;span&gt;
&lt;&#x2F;span&gt;&lt;&#x2F;span&gt;&lt;&#x2F;span&gt;&lt;&#x2F;span&gt;&lt;span class=&quot;z-source z-lisp&quot;&gt;&lt;span class=&quot;z-meta z-group z-lisp&quot;&gt;&lt;span class=&quot;z-meta z-group z-lisp&quot;&gt;&lt;span class=&quot;z-meta z-group z-lisp&quot;&gt;    &lt;span class=&quot;z-meta z-group z-lisp&quot;&gt;&lt;span class=&quot;z-punctuation z-definition z-group z-begin z-lisp&quot;&gt;(&lt;&#x2F;span&gt;vnode&lt;span class=&quot;z-keyword z-operator z-arithmetic z-lisp&quot;&gt;-&lt;&#x2F;span&gt;type SYMLINK&lt;span class=&quot;z-punctuation z-definition z-group z-end z-lisp&quot;&gt;)&lt;&#x2F;span&gt;&lt;&#x2F;span&gt;&lt;span class=&quot;z-punctuation z-definition z-group z-end z-lisp&quot;&gt;)&lt;&#x2F;span&gt;&lt;&#x2F;span&gt;
&lt;&#x2F;span&gt;&lt;&#x2F;span&gt;&lt;&#x2F;span&gt;&lt;span class=&quot;z-source z-lisp&quot;&gt;&lt;span class=&quot;z-meta z-group z-lisp&quot;&gt;&lt;span class=&quot;z-meta z-group z-lisp&quot;&gt;    &lt;span class=&quot;z-meta z-group z-lisp&quot;&gt;&lt;span class=&quot;z-punctuation z-definition z-group z-begin z-lisp&quot;&gt;(&lt;&#x2F;span&gt;subpath &lt;span class=&quot;z-string z-quoted z-double z-lisp&quot;&gt;&lt;span class=&quot;z-punctuation z-definition z-string z-begin z-lisp&quot;&gt;&amp;quot;&lt;&#x2F;span&gt;&#x2F;tmp&#x2F;no-symlinks&lt;span class=&quot;z-punctuation z-definition z-string z-end z-lisp&quot;&gt;&amp;quot;&lt;&#x2F;span&gt;&lt;&#x2F;span&gt;&lt;span class=&quot;z-punctuation z-definition z-group z-end z-lisp&quot;&gt;)&lt;&#x2F;span&gt;&lt;&#x2F;span&gt;&lt;span class=&quot;z-punctuation z-definition z-group z-end z-lisp&quot;&gt;)&lt;&#x2F;span&gt;&lt;&#x2F;span&gt;&lt;span class=&quot;z-punctuation z-definition z-group z-end z-lisp&quot;&gt;)&lt;&#x2F;span&gt;&lt;&#x2F;span&gt;
&lt;&#x2F;span&gt;&lt;&#x2F;code&gt;&lt;&#x2F;pre&gt;
&lt;p&gt;This simple policy shows the basics of how a sandbox policy is expressed. The
policy for individual operations is specified via an &lt;code&gt;allow&lt;&#x2F;code&gt; or &lt;code&gt;deny&lt;&#x2F;code&gt; function
call that takes the name of the operation and any predicates that must be
matched for the specified action (&lt;code&gt;allow&lt;&#x2F;code&gt; or &lt;code&gt;deny&lt;&#x2F;code&gt;) to be applied. A default
action is provided via the &lt;code&gt;default&lt;&#x2F;code&gt; function for cases not matched via explicit
&lt;code&gt;allow&lt;&#x2F;code&gt; or &lt;code&gt;deny&lt;&#x2F;code&gt; actions.&lt;&#x2F;p&gt;
&lt;p&gt;Being a Scheme dialect, the usual programming language constructs are available:
conditionals, loops, lambdas, and even macros!&lt;&#x2F;p&gt;
&lt;p&gt;Additionally, SBPL supports passing string values as parameters to the policy.
These parameters are available via the &lt;code&gt;param&lt;&#x2F;code&gt; function during policy
evaluation. This combination of features makes it possible to express a policy
that the application can configure:&lt;&#x2F;p&gt;
&lt;pre data-lang=&quot;scm&quot; class=&quot;language-scm z-code&quot;&gt;&lt;code class=&quot;language-scm&quot; data-lang=&quot;scm&quot;&gt;&lt;span class=&quot;z-source z-lisp&quot;&gt;&lt;span class=&quot;z-meta z-group z-lisp&quot;&gt;&lt;span class=&quot;z-punctuation z-definition z-group z-begin z-lisp&quot;&gt;(&lt;&#x2F;span&gt;define SHINY_NEW_DOWNLOADS_ENABLED &lt;span class=&quot;z-meta z-group z-lisp&quot;&gt;&lt;span class=&quot;z-punctuation z-definition z-group z-begin z-lisp&quot;&gt;(&lt;&#x2F;span&gt;param &lt;span class=&quot;z-string z-quoted z-double z-lisp&quot;&gt;&lt;span class=&quot;z-punctuation z-definition z-string z-begin z-lisp&quot;&gt;&amp;quot;&lt;&#x2F;span&gt;SHINY_NEW_DOWNLOADS_ENABLED&lt;span class=&quot;z-punctuation z-definition z-string z-end z-lisp&quot;&gt;&amp;quot;&lt;&#x2F;span&gt;&lt;&#x2F;span&gt;&lt;span class=&quot;z-punctuation z-definition z-group z-end z-lisp&quot;&gt;)&lt;&#x2F;span&gt;&lt;&#x2F;span&gt;&lt;span class=&quot;z-punctuation z-definition z-group z-end z-lisp&quot;&gt;)&lt;&#x2F;span&gt;&lt;&#x2F;span&gt;
&lt;&#x2F;span&gt;&lt;span class=&quot;z-source z-lisp&quot;&gt;&lt;span class=&quot;z-meta z-group z-lisp&quot;&gt;&lt;span class=&quot;z-punctuation z-definition z-group z-begin z-lisp&quot;&gt;(&lt;&#x2F;span&gt;&lt;span class=&quot;z-keyword z-control z-lisp&quot;&gt;if&lt;&#x2F;span&gt; &lt;span class=&quot;z-meta z-group z-lisp&quot;&gt;&lt;span class=&quot;z-punctuation z-definition z-group z-begin z-lisp&quot;&gt;(&lt;&#x2F;span&gt;&lt;span class=&quot;z-keyword z-operator z-comparison z-lisp&quot;&gt;equal&lt;&#x2F;span&gt;? SHINY_NEW_DOWNLOADS_ENABLED &lt;span class=&quot;z-string z-quoted z-double z-lisp&quot;&gt;&lt;span class=&quot;z-punctuation z-definition z-string z-begin z-lisp&quot;&gt;&amp;quot;&lt;&#x2F;span&gt;YES&lt;span class=&quot;z-punctuation z-definition z-string z-end z-lisp&quot;&gt;&amp;quot;&lt;&#x2F;span&gt;&lt;&#x2F;span&gt;&lt;span class=&quot;z-punctuation z-definition z-group z-end z-lisp&quot;&gt;)&lt;&#x2F;span&gt;&lt;&#x2F;span&gt;
&lt;&#x2F;span&gt;&lt;&#x2F;span&gt;&lt;span class=&quot;z-source z-lisp&quot;&gt;&lt;span class=&quot;z-meta z-group z-lisp&quot;&gt;  &lt;span class=&quot;z-meta z-group z-lisp&quot;&gt;&lt;span class=&quot;z-punctuation z-definition z-group z-begin z-lisp&quot;&gt;(&lt;&#x2F;span&gt;allow file&lt;span class=&quot;z-keyword z-operator z-arithmetic z-lisp&quot;&gt;-&lt;&#x2F;span&gt;&lt;span class=&quot;z-support z-function z-lisp&quot;&gt;read&lt;&#x2F;span&gt;&lt;span class=&quot;z-keyword z-operator z-arithmetic z-lisp&quot;&gt;*&lt;&#x2F;span&gt; file&lt;span class=&quot;z-keyword z-operator z-arithmetic z-lisp&quot;&gt;-&lt;&#x2F;span&gt;&lt;span class=&quot;z-support z-function z-lisp&quot;&gt;write&lt;&#x2F;span&gt;&lt;span class=&quot;z-keyword z-operator z-arithmetic z-lisp&quot;&gt;*&lt;&#x2F;span&gt; &lt;span class=&quot;z-meta z-group z-lisp&quot;&gt;&lt;span class=&quot;z-punctuation z-definition z-group z-begin z-lisp&quot;&gt;(&lt;&#x2F;span&gt;subpath &lt;span class=&quot;z-string z-quoted z-double z-lisp&quot;&gt;&lt;span class=&quot;z-punctuation z-definition z-string z-begin z-lisp&quot;&gt;&amp;quot;&lt;&#x2F;span&gt;${any_user_homedir}&#x2F;Downloads&lt;span class=&quot;z-punctuation z-definition z-string z-end z-lisp&quot;&gt;&amp;quot;&lt;&#x2F;span&gt;&lt;&#x2F;span&gt;&lt;span class=&quot;z-punctuation z-definition z-group z-end z-lisp&quot;&gt;)&lt;&#x2F;span&gt;&lt;&#x2F;span&gt;&lt;span class=&quot;z-punctuation z-definition z-group z-end z-lisp&quot;&gt;)&lt;&#x2F;span&gt;&lt;&#x2F;span&gt;&lt;span class=&quot;z-punctuation z-definition z-group z-end z-lisp&quot;&gt;)&lt;&#x2F;span&gt;&lt;&#x2F;span&gt;
&lt;&#x2F;span&gt;&lt;&#x2F;code&gt;&lt;&#x2F;pre&gt;
&lt;h4 id=&quot;sandbox-extensions&quot;&gt;Sandbox extensions&lt;&#x2F;h4&gt;
&lt;p&gt;The evaluation-time configurability that parameters and conditional logic
provides is applicable to policy decisions that affect the lifetime of the
process. However, they are not sufficient to handle cases where the possible
resources that may be accessed are not known in advance.  This requires the
ability to dynamically extend the sandbox after a policy has been applied.&lt;&#x2F;p&gt;
&lt;p&gt;For example, a service&#x27;s sandbox policy may be configured to allow it to access
data that it owns that lives in a fixed location. Clients of the service may
need it to perform work on data that they own that lives outside of that
location. Rather than having a broad sandbox policy that makes the client&#x27;s data
available, the sandbox policy can be limited to only the service&#x27;s data, and be
extended dynamically to access the client&#x27;s data via a &lt;em&gt;sandbox extension&lt;&#x2F;em&gt;.&lt;&#x2F;p&gt;
&lt;p&gt;Using a sandbox extension requires cooperation from both the sandbox policy, the
sandboxed process, and and the process interacting with the sandboxed process.&lt;&#x2F;p&gt;
&lt;p&gt;The process interacting with the sandboxed process issues an extension of a
given class (represented as a reverse-DNS style dotted string) to a given
resource that it has access to (typically a path or Mach bootstrap name). This
results in a sandbox token, represented as an opaque string.&lt;&#x2F;p&gt;
&lt;p&gt;The client sends this token to the sandboxed process which consumes the
extension token. The effect that the extension has on the sandboxed process is
controlled by logic within its sandbox policy. Once the work that requires the
extended sandbox is finished, the sandboxed process can release the extension.
This revokes access to the resources that the extension covered.&lt;&#x2F;p&gt;
&lt;p&gt;As an example of how the sandbox policy controls the effect an extension has on
it, consider the following:&lt;&#x2F;p&gt;
&lt;pre data-lang=&quot;scm&quot; class=&quot;language-scm z-code&quot;&gt;&lt;code class=&quot;language-scm&quot; data-lang=&quot;scm&quot;&gt;&lt;span class=&quot;z-source z-lisp&quot;&gt;&lt;span class=&quot;z-comment z-line z-semicolon z-lisp&quot;&gt;&lt;span class=&quot;z-punctuation z-definition z-comment z-lisp&quot;&gt;;&lt;&#x2F;span&gt;; Allow reading any file for which we have consumed an
&lt;&#x2F;span&gt;&lt;&#x2F;span&gt;&lt;span class=&quot;z-source z-lisp&quot;&gt;&lt;span class=&quot;z-comment z-line z-semicolon z-lisp&quot;&gt;&lt;span class=&quot;z-punctuation z-definition z-comment z-lisp&quot;&gt;;&lt;&#x2F;span&gt;; extension of class com.apple.app-sandbox.read
&lt;&#x2F;span&gt;&lt;&#x2F;span&gt;&lt;span class=&quot;z-source z-lisp&quot;&gt;&lt;span class=&quot;z-meta z-group z-lisp&quot;&gt;&lt;span class=&quot;z-punctuation z-definition z-group z-begin z-lisp&quot;&gt;(&lt;&#x2F;span&gt;allow file&lt;span class=&quot;z-keyword z-operator z-arithmetic z-lisp&quot;&gt;-&lt;&#x2F;span&gt;&lt;span class=&quot;z-support z-function z-lisp&quot;&gt;read&lt;&#x2F;span&gt;&lt;span class=&quot;z-keyword z-operator z-arithmetic z-lisp&quot;&gt;*&lt;&#x2F;span&gt; &lt;span class=&quot;z-meta z-group z-lisp&quot;&gt;&lt;span class=&quot;z-punctuation z-definition z-group z-begin z-lisp&quot;&gt;(&lt;&#x2F;span&gt;extension &lt;span class=&quot;z-string z-quoted z-double z-lisp&quot;&gt;&lt;span class=&quot;z-punctuation z-definition z-string z-begin z-lisp&quot;&gt;&amp;quot;&lt;&#x2F;span&gt;com.apple.app-sandbox.read&lt;span class=&quot;z-punctuation z-definition z-string z-end z-lisp&quot;&gt;&amp;quot;&lt;&#x2F;span&gt;&lt;&#x2F;span&gt;&lt;span class=&quot;z-punctuation z-definition z-group z-end z-lisp&quot;&gt;)&lt;&#x2F;span&gt;&lt;&#x2F;span&gt;&lt;span class=&quot;z-punctuation z-definition z-group z-end z-lisp&quot;&gt;)&lt;&#x2F;span&gt;&lt;&#x2F;span&gt;
&lt;&#x2F;span&gt;&lt;span class=&quot;z-source z-lisp&quot;&gt;&lt;span class=&quot;z-comment z-line z-semicolon z-lisp&quot;&gt;&lt;span class=&quot;z-punctuation z-definition z-comment z-lisp&quot;&gt;;&lt;&#x2F;span&gt;; In contrast, the com.example.sandbox.read-downloads
&lt;&#x2F;span&gt;&lt;&#x2F;span&gt;&lt;span class=&quot;z-source z-lisp&quot;&gt;&lt;span class=&quot;z-comment z-line z-semicolon z-lisp&quot;&gt;&lt;span class=&quot;z-punctuation z-definition z-comment z-lisp&quot;&gt;;&lt;&#x2F;span&gt;; extension will only permit reading a file if the extension
&lt;&#x2F;span&gt;&lt;&#x2F;span&gt;&lt;span class=&quot;z-source z-lisp&quot;&gt;&lt;span class=&quot;z-comment z-line z-semicolon z-lisp&quot;&gt;&lt;span class=&quot;z-punctuation z-definition z-comment z-lisp&quot;&gt;;&lt;&#x2F;span&gt;; was issued for a path under ~&#x2F;Downloads.
&lt;&#x2F;span&gt;&lt;&#x2F;span&gt;&lt;span class=&quot;z-source z-lisp&quot;&gt;&lt;span class=&quot;z-meta z-group z-lisp&quot;&gt;&lt;span class=&quot;z-punctuation z-definition z-group z-begin z-lisp&quot;&gt;(&lt;&#x2F;span&gt;allow file&lt;span class=&quot;z-keyword z-operator z-arithmetic z-lisp&quot;&gt;-&lt;&#x2F;span&gt;&lt;span class=&quot;z-support z-function z-lisp&quot;&gt;read&lt;&#x2F;span&gt;&lt;span class=&quot;z-keyword z-operator z-arithmetic z-lisp&quot;&gt;*&lt;&#x2F;span&gt;
&lt;&#x2F;span&gt;&lt;&#x2F;span&gt;&lt;span class=&quot;z-source z-lisp&quot;&gt;&lt;span class=&quot;z-meta z-group z-lisp&quot;&gt;  &lt;span class=&quot;z-meta z-group z-lisp&quot;&gt;&lt;span class=&quot;z-punctuation z-definition z-group z-begin z-lisp&quot;&gt;(&lt;&#x2F;span&gt;&lt;span class=&quot;z-support z-function z-lisp&quot;&gt;require&lt;&#x2F;span&gt;&lt;span class=&quot;z-keyword z-operator z-arithmetic z-lisp&quot;&gt;-&lt;&#x2F;span&gt;all
&lt;&#x2F;span&gt;&lt;&#x2F;span&gt;&lt;&#x2F;span&gt;&lt;span class=&quot;z-source z-lisp&quot;&gt;&lt;span class=&quot;z-meta z-group z-lisp&quot;&gt;&lt;span class=&quot;z-meta z-group z-lisp&quot;&gt;    &lt;span class=&quot;z-meta z-group z-lisp&quot;&gt;&lt;span class=&quot;z-punctuation z-definition z-group z-begin z-lisp&quot;&gt;(&lt;&#x2F;span&gt;extension &lt;span class=&quot;z-string z-quoted z-double z-lisp&quot;&gt;&lt;span class=&quot;z-punctuation z-definition z-string z-begin z-lisp&quot;&gt;&amp;quot;&lt;&#x2F;span&gt;com.example.sandbox.read-downloads&lt;span class=&quot;z-punctuation z-definition z-string z-end z-lisp&quot;&gt;&amp;quot;&lt;&#x2F;span&gt;&lt;&#x2F;span&gt;&lt;span class=&quot;z-punctuation z-definition z-group z-end z-lisp&quot;&gt;)&lt;&#x2F;span&gt;&lt;&#x2F;span&gt;
&lt;&#x2F;span&gt;&lt;&#x2F;span&gt;&lt;&#x2F;span&gt;&lt;span class=&quot;z-source z-lisp&quot;&gt;&lt;span class=&quot;z-meta z-group z-lisp&quot;&gt;&lt;span class=&quot;z-meta z-group z-lisp&quot;&gt;    &lt;span class=&quot;z-meta z-group z-lisp&quot;&gt;&lt;span class=&quot;z-punctuation z-definition z-group z-begin z-lisp&quot;&gt;(&lt;&#x2F;span&gt;subpath &lt;span class=&quot;z-string z-quoted z-double z-lisp&quot;&gt;&lt;span class=&quot;z-punctuation z-definition z-string z-begin z-lisp&quot;&gt;&amp;quot;&lt;&#x2F;span&gt;${any_user_homedir}&#x2F;Downloads&lt;span class=&quot;z-punctuation z-definition z-string z-end z-lisp&quot;&gt;&amp;quot;&lt;&#x2F;span&gt;&lt;&#x2F;span&gt;&lt;span class=&quot;z-punctuation z-definition z-group z-end z-lisp&quot;&gt;)&lt;&#x2F;span&gt;&lt;&#x2F;span&gt;&lt;span class=&quot;z-punctuation z-definition z-group z-end z-lisp&quot;&gt;)&lt;&#x2F;span&gt;&lt;&#x2F;span&gt;&lt;span class=&quot;z-punctuation z-definition z-group z-end z-lisp&quot;&gt;)&lt;&#x2F;span&gt;&lt;&#x2F;span&gt;
&lt;&#x2F;span&gt;&lt;&#x2F;code&gt;&lt;&#x2F;pre&gt;
&lt;p&gt;In the second example, the policy only permits the
&lt;code&gt;com.example.sandbox.read-downloads&lt;&#x2F;code&gt; sandbox extension class to be used to
extend access to a specific subdirectory.&lt;&#x2F;p&gt;
&lt;h1 id=&quot;sandbox-apis&quot;&gt;Sandbox APIs&lt;&#x2F;h1&gt;
&lt;p&gt;All of the sandbox APIs described here are private APIs. Apple considers
sandboxing at this level to be deprecated in favor of the App Sandbox. In
practice, the App Sandbox is not a usable replacement for many large
applications. Apple continues to make use of these lower-level APIs for
sandboxing its first-party applications and helper tools.&lt;&#x2F;p&gt;
&lt;p&gt;&lt;code&gt;sandbox_init_with_parameters&lt;&#x2F;code&gt; takes SBPL source as a string and an array of
parameters that the policy can access. It evaluates the SBPL and compiles the
resulting state to bytecode (described below). It then asks the Sandbox kernel
extension to apply the sandbox to the current process.&lt;&#x2F;p&gt;
&lt;p&gt;&lt;code&gt;sandbox_compile&lt;&#x2F;code&gt; and &lt;code&gt;sandbox_apply&lt;&#x2F;code&gt; split the work of compiling the policy to
bytecode and applying it to the process into two separate calls. This can avoid
the overhead of repeatedly evaluating the same SBPL source if you ever launch
more than one process with the same policy. Instead you can cache the compiled
bytecode and the process can then use the bytecode when applying its sandbox.&lt;&#x2F;p&gt;
&lt;p&gt;&lt;code&gt;sandbox_extension_issue_file&lt;&#x2F;code&gt;, &lt;code&gt;sandbox_extension_consume&lt;&#x2F;code&gt;,
&lt;code&gt;sandbox_extension_release&lt;&#x2F;code&gt; are used for issuing, consuming, and releasing
extensions respectively.&lt;&#x2F;p&gt;
&lt;h2 id=&quot;mac-in-the-macos-kernel&quot;&gt;MAC in the macOS kernel&lt;&#x2F;h2&gt;
&lt;p&gt;The macOS kernel (XNU) provides a Mandatory Access Control Framework (MACF) that
exposes around &lt;a href=&quot;https:&#x2F;&#x2F;github.com&#x2F;apple-oss-distributions&#x2F;xnu&#x2F;blob&#x2F;main&#x2F;security&#x2F;mac_policy.h&quot;&gt;300 policy
hooks&lt;&#x2F;a&gt;
that can be used to approve or deny specific operations at a fine-grained level.
Most of the policy hooks correspond to specific system calls or operations on
the kernel&#x27;s file system abstraction (VFS). As the name implies, these policy
hooks are mandatory and are applied to all clients that use the system calls or
perform file system operations.&lt;&#x2F;p&gt;
&lt;p&gt;The Sandbox kernel extension is a client of the MACF and implements many of the
policy hooks exposed by the kernel. When a system call is made that the Sandbox
kernel extension provides a policy hook for, XNU calls the corresponding policy
hook early in the handling of the system call. The policy hook is provided with
context about the operation being performed (i.e., arguments for the system call
being made). This gives the Sandbox kernel extension an opportunity to deny the
operation if its policies state that it should not be permitted.&lt;&#x2F;p&gt;
&lt;h2 id=&quot;sandbox-kernel-extension&quot;&gt;Sandbox kernel extension&lt;&#x2F;h2&gt;
&lt;p&gt;Sandbox policies can be applied to a process at two main levels&lt;sup class=&quot;footnote-reference&quot; id=&quot;fr-2-1&quot;&gt;&lt;a href=&quot;#fn-2&quot;&gt;1&lt;&#x2F;a&gt;&lt;&#x2F;sup&gt;:&lt;&#x2F;p&gt;
&lt;ol&gt;
&lt;li&gt;The platform sandbox policy is applied to all processes.&lt;&#x2F;li&gt;
&lt;li&gt;User-space applications can opt into being sandboxed.&lt;&#x2F;li&gt;
&lt;&#x2F;ol&gt;
&lt;p&gt;When a user-space application opts into being sandboxed, its sandbox policy is
passed to the Sandbox kernel extension via the &lt;code&gt;__mac_syscall&lt;&#x2F;code&gt; system call
(often via the &lt;code&gt;__sandbox_ms&lt;&#x2F;code&gt; wrapper function). The kernel routes this system
call to the appropriate MACF client based on its arguments. The Sandbox kernel
extension performs some basic validation and then associates the policy with the
kernel &lt;code&gt;proc&lt;&#x2F;code&gt; structure for the process using a MAC label.&lt;&#x2F;p&gt;
&lt;p&gt;When the kernel calls a MACF policy hook in the Sandbox kernel extension, the
policy hook is mapped to a sandbox operation type that describes the operation
being attempted. This provides a layer of indirection from the exact MACF hooks
exposed in the kernel. You can see the &lt;a href=&quot;https:&#x2F;&#x2F;gist.github.com&#x2F;bdash&#x2F;ccbfb773ad57484532a74a982fe4f571#file-sandbox-operations-scm&quot;&gt;complete list of sandbox operations
here&lt;&#x2F;a&gt;.&lt;&#x2F;p&gt;
&lt;p&gt;The operation is then evaluated against the platform sandbox policy. If the
system sandbox policy denies the operation, the denial is propagated back
through the MACF hook to the kernel and an error is returned via the system
call.&lt;&#x2F;p&gt;
&lt;p&gt;If the platform sandbox policy permits the operation, it will next be evaluated
against the process sandbox policy. The Sandbox kernel extension retrieves the
sandbox policy associated with the process performing the hooked operation. If a
sandbox policy is found, it is evaluated to determine whether the operation
should be permitted. If the process is not sandboxed, the operation is
permitted.&lt;&#x2F;p&gt;
&lt;h3 id=&quot;sandbox-policy-evaluation&quot;&gt;Sandbox policy evaluation&lt;&#x2F;h3&gt;
&lt;p&gt;The sandbox policy consists of a list of bytecode instructions, and a mapping from sandbox
operation to the initial bytecode instruction to be evaluated for that operation.
Bytecode instructions take two forms:&lt;&#x2F;p&gt;
&lt;ol&gt;
&lt;li&gt;
&lt;p&gt;&lt;strong&gt;Filter instructions&lt;&#x2F;strong&gt;&lt;&#x2F;p&gt;
&lt;p&gt;These consist of a predicate, an &lt;em&gt;if match&lt;&#x2F;em&gt; instruction index, and an &lt;em&gt;if not match&lt;&#x2F;em&gt;
instruction index. If the predicate evaluates to true, execution continues from the &lt;em&gt;if
match&lt;&#x2F;em&gt; instruction index. Otherwise it jumps to the &lt;em&gt;if not match&lt;&#x2F;em&gt; instruction index.&lt;&#x2F;p&gt;
&lt;&#x2F;li&gt;
&lt;li&gt;
&lt;p&gt;&lt;strong&gt;Action instructions&lt;&#x2F;strong&gt;&lt;&#x2F;p&gt;
&lt;p&gt;Actions may be either &lt;code&gt;allow&lt;&#x2F;code&gt; or &lt;code&gt;deny&lt;&#x2F;code&gt;, and they may have one or more modifiers
associated with them. When evaluation reaches an action, the modifiers are applied and
evaluation of the sandbox policy terminates with the action as the result.&lt;&#x2F;p&gt;
&lt;&#x2F;li&gt;
&lt;&#x2F;ol&gt;
&lt;p&gt;In the policies I have analyzed, all jumps are forward jumps. As a result the bytecode forms a
disconnected directed graph from entry points, through zero or more filters, to actions.&lt;&#x2F;p&gt;
&lt;h4 id=&quot;filters&quot;&gt;Filters&lt;&#x2F;h4&gt;
&lt;p&gt;There are around 90 different filter predicates supported as of macOS 15. You
can see the &lt;a href=&quot;https:&#x2F;&#x2F;gist.github.com&#x2F;bdash&#x2F;ccbfb773ad57484532a74a982fe4f571#file-filters-scm&quot;&gt;complete list of filter predicates
here&lt;&#x2F;a&gt;.&lt;&#x2F;p&gt;
&lt;p&gt;Most predicates match information about the operation being performed. For
instance, file system operations can be filtered via the &lt;code&gt;path&lt;&#x2F;code&gt; and &lt;code&gt;vnode-type&lt;&#x2F;code&gt;
filters. &lt;code&gt;sysctl&lt;&#x2F;code&gt; system calls can be filtered using the name of the operation via the
&lt;code&gt;sysctl-name&lt;&#x2F;code&gt; predicate. Mach bootstrap lookup operations can be matched via the
&lt;code&gt;global-name&lt;&#x2F;code&gt; or &lt;code&gt;local-name&lt;&#x2F;code&gt; filters.&lt;&#x2F;p&gt;
&lt;p&gt;The remainder of the predicates deal with attributes of the process performing
the operation, such as &lt;code&gt;signing-identifier&lt;&#x2F;code&gt; or &lt;code&gt;entitlement-is-present&lt;&#x2F;code&gt;, or the
state of the operating system system (&lt;code&gt;csr&lt;&#x2F;code&gt; for information about configurable
security restrictions such System Integrity Protection, or &lt;code&gt;system-attribute&lt;&#x2F;code&gt;
for other attributes).&lt;&#x2F;p&gt;
&lt;p&gt;These last two groups of predicates are mostly of use to policies that apply to
more than one application, such as the platform sandbox policy or the App
Sandbox, rather than application-specific policies.&lt;&#x2F;p&gt;
&lt;h4 id=&quot;action-modifiers&quot;&gt;Action modifiers&lt;&#x2F;h4&gt;
&lt;p&gt;Modifiers can be applied on both &lt;code&gt;allow&lt;&#x2F;code&gt; or &lt;code&gt;deny&lt;&#x2F;code&gt; actions in order to modify
&lt;a href=&quot;https:&#x2F;&#x2F;bdash.net.nz&#x2F;posts&#x2F;sandboxing-on-macos&#x2F;#what-happens-if-the-sandbox-policy-is-violated&quot;&gt;the default behavior&lt;&#x2F;a&gt;. The
permitted set of modifiers differs for &lt;code&gt;allow&lt;&#x2F;code&gt; and &lt;code&gt;deny&lt;&#x2F;code&gt; actions as some
modifiers only make sense in one context. You can see the &lt;a href=&quot;https:&#x2F;&#x2F;gist.github.com&#x2F;bdash&#x2F;ccbfb773ad57484532a74a982fe4f571#file-action-modifiers-scm&quot;&gt;complete list of
action modifiers
here&lt;&#x2F;a&gt;.&lt;&#x2F;p&gt;
&lt;p&gt;Examples of modifiers supported on deny actions include:&lt;&#x2F;p&gt;
&lt;ul&gt;
&lt;li&gt;overriding the errno value that is returned from the denied operation: &lt;code&gt;(with EBADEXEC)&lt;&#x2F;code&gt;&lt;&#x2F;li&gt;
&lt;li&gt;suppressing reporting of sandbox violations: &lt;code&gt;(with no-report)&lt;&#x2F;code&gt;&lt;&#x2F;li&gt;
&lt;li&gt;sending a signal to the user-space thread that performed the system call: &lt;code&gt;(with send-signal SIGUSR1)&lt;&#x2F;code&gt;&lt;&#x2F;li&gt;
&lt;li&gt;triggering Apple-internal telemetry related to the violation: &lt;code&gt;(with telemetry)&lt;&#x2F;code&gt;&lt;&#x2F;li&gt;
&lt;&#x2F;ul&gt;
&lt;p&gt;Modifiers supported on allow actions include:&lt;&#x2F;p&gt;
&lt;ul&gt;
&lt;li&gt;generating a violation report: &lt;code&gt;(with report)&lt;&#x2F;code&gt;&lt;&#x2F;li&gt;
&lt;li&gt;logging a message to the system console: &lt;code&gt;(with message &quot;…&quot;)&lt;&#x2F;code&gt;&lt;&#x2F;li&gt;
&lt;li&gt;triggering Apple-internal telemetry related to the operation: &lt;code&gt;(with telemetry)&lt;&#x2F;code&gt;&lt;&#x2F;li&gt;
&lt;&#x2F;ul&gt;
&lt;section class=&quot;footnotes&quot;&gt;
&lt;ol class=&quot;footnotes-list&quot;&gt;
&lt;li id=&quot;fn-2&quot;&gt;
&lt;p&gt;I have come across references to a few other types of policies (autobox,
bastion, and delegated policies), but I have not yet investigated what role they
play. &lt;a href=&quot;#fr-2-1&quot;&gt;↩&lt;&#x2F;a&gt;&lt;&#x2F;p&gt;
&lt;&#x2F;li&gt;
&lt;&#x2F;ol&gt;
&lt;&#x2F;section&gt;
</content>
        
    </entry>
</feed>
