Environment setup
Use Xcode 27. New SwiftUI app, iOS 27 or macOS 27. Add Foundation Models. If you later add an XPC service, that is a second target on macOS.
xcodebuild -version
# New App, SwiftUI, iOS 27 or macOS 27. Add FoundationModels.
# macOS only: File > New > Target > XPC Service if you need a second process.
When the on-device model calls a tool, your call(arguments:) function runs. Unless you move that work, it runs in the app process. It can see whatever the app can see. The model does not get a smaller sandbox for free.
That is still useful. The iOS sandbox and the macOS App Sandbox already block a lot of the system. They do not block a tool from reading every file your app already has, or from starting a long loop that burns battery, or from opening a network path you enabled for the app.
An Edge FDE treats every tool as untrusted input plus privileged code. The arguments come from the model. The privileges come from your process. You insert an executor so the tool cannot touch more than a list you wrote.
Read Talk to tools with MCP, Stop prompt attacks and leaks, and Make several agents agree first for how tools arrive, how to check the arguments, and when a tool should wait for a vote.
Next, look at the isolation options Apple actually gives you.
Key concepts
Tool.call(arguments:)runs in the app process unless you move it.- Tools inherit app rights: files, network, sensors, battery.
- The iOS sandbox limits system access, not in-app abuse.
- Model arguments are untrusted. Your Swift is privileged.
Takeaways
- Treat every tool as untrusted input plus privileged code.
- A tool can touch everything the app already can.
- Plan an executor so tools cannot exceed your allow-list.