Skip to content

NSLog format string crash in PHPSchemeHandler when response contains % characters #94

@kaiserkiwi

Description

@kaiserkiwi

What were you trying to do?

Navigate between pages in a NativePHP iOS app running on the simulator. The app loads the initial page fine, but crashes as soon as any navigation occurs (e.g. clicking a link to a product page).

What happened?

The app crashes with EXC_BAD_ACCESS (SIGBUS) KERN_PROTECTION_FAILURE on Thread 11 (com.nativephp.persistent-php).

The crash originates in PHPSchemeHandler.swift:609 inside __CFStringAppendFormatCore, called from NSLog.

Root cause: Lines 595 and 609 in PHPSchemeHandler.swift use Swift string interpolation directly inside NSLog():

// Line 595
NSLog("[NativePHP] [\(mode)] --> \(request.method) \(request.uri)")

// Line 609
NSLog("[NativePHP] [\(mode)] <-- \(statusLine) (\(String(format: "%.1f", elapsed))ms)")

NSLog treats its first argument as a format string (like printf). If request.uri or statusLine contains % characters — which is extremely common in HTTP (URL-encoded paths like /path%20to, CSS in error pages containing width:100%, etc.) — NSLog interprets them as format specifiers (%s, %d, %2) and reads from invalid memory, causing the crash.

How to reproduce the bug

  1. Create a Laravel app with pages that contain % characters in URLs, HTML, or response bodies (virtually any real-world app)
  2. Run php artisan native:run ios
  3. Navigate to any page — the app crashes immediately

A minimal reproduction: any page that triggers a redirect to a URL containing %-encoded characters, or any HTML response where statusLine extraction fails and the body (containing %) leaks into the log.

Debug Output

Exception Type:  EXC_BAD_ACCESS (SIGBUS)
Exception Subtype: KERN_PROTECTION_FAILURE at 0x0000005800000050
Termination Reason: SIGNAL 10 Bus error: 10
Triggered by Thread:  11

Thread 11 Crashed:: Dispatch queue: com.nativephp.persistent-php
0   CoreFoundation    __CFStringAppendFormatCore + 7656
1   CoreFoundation    _CFStringCreateWithFormatAndArgumentsReturningMetadata + 180
2   CoreFoundation    _CFStringCreateWithFormatAndArgumentsAux2 + 40
3   libsystem_trace   _os_log_impl_dynamic + 172
4   libsystem_trace   _os_log_with_args_impl + 172
5   CoreFoundation    _CFLogvEx3 + 184
6   Foundation        _NSLogv + 120
7   Foundation        specialized withVaList<A>(_:_:) + 424
8   NativePHP-simulator.debug.dylib  closure #1 in PHPSchemeHandler.getResponse(request:completion:) + 2212 (PHPSchemeHandler.swift:609)

Which operating systems have you seen this occur on?

macOS

Which platforms were you trying to build for?

iOS (Simulator)

Notes

Potential Fix: Use NSLog("%@", message) instead of NSLog(message) to prevent format string interpretation:

// Line 595 — before:
NSLog("[NativePHP] [\(mode)] --> \(request.method) \(request.uri)")
// Line 595 — after:
NSLog("%@", "[NativePHP] [\(mode)] --> \(request.method) \(request.uri)")

// Line 609 — before:
NSLog("[NativePHP] [\(mode)] <-- \(statusLine) (\(String(format: "%.1f", elapsed))ms)")
// Line 609 — after:
NSLog("%@", "[NativePHP] [\(mode)] <-- \(statusLine) (\(String(format: "%.1f", elapsed))ms)")

It may be worth auditing all NSLog calls in the codebase for the same pattern. Any NSLog that interpolates user-controlled or response-derived content without using %@ as the format specifier is vulnerable to this crash.

I was able to fix this bug locally with this. But the next time I run native:install the bug reoccurs.

In my composer.json is "nativephp/mobile": "^3.2", and installe dis 3.2.3

Metadata

Metadata

Assignees

No one assigned

    Labels

    bugSomething isn't working

    Type

    No type

    Projects

    No projects

    Milestone

    No milestone

    Relationships

    None yet

    Development

    No branches or pull requests

    Issue actions