Skip to content

Allow debugging of native addons on macOS #34340

Description

@ggreco
  • Version: v12.18 v14.5
  • Platform: macOS Catalina ( Darwin iMac-2.local 19.5.0 Darwin Kernel Version 19.5.0 )
  • Subsystem: main

What steps will reproduce the bug?

  • Open a terminal window

  • launch LLDB (the clang debugger) with the node executable (the official 14.3 and 12.x versions have the same problem

    lldb /usr/local/bin/node
    run -v

  • the result is:

    error: process exited with status -1 (Error 1)

How often does it reproduce? Is there a required condition?

It's 100% reproductable on catalina if the SIP (system integrity protection) is active.

What is the expected behavior?

The node binary should dump the version and quit, ie:

(lldb) r -v
Process 21451 launched: '/usr/local/bin/node' (x86_64)
v12.18.2
Process 21451 exited with status = 0 (0x00000000) 
(lldb)

What do you see instead?

The node binary cannot be debugged:

(lldb) r -v
error: process exited with status -1 (Error 1)
(lldb)

Additional information

The node binary miss the DEBUG entitlement, com.apple.security.get-task-allow , so lldb cannot attach to it nor launch it in debug mode.

The following command show the list of entitlements in the binary signature.

  codesign -d --entitlements :- /usr/local/bin/node

Here is the output of the command (in the pkg archive, or in the tar.gz, both for 12.x and 14.x):

Executable=/usr/local/bin/node
  <?xml version="1.0" encoding="UTF-8"?>
<!DOCTYPE plist PUBLIC "-//Apple//DTD PLIST 1.0//EN" "http://www.apple.com/DTDs/PropertyList-1.0.dtd">
<plist version="1.0">
<dict>
    <key>com.apple.security.cs.allow-jit</key>
    <true/>
    <key>com.apple.security.cs.allow-unsigned-executable-memory</key>
    <true/>
    <key>com.apple.security.cs.disable-executable-page-protection</key>
    <true/>
    <key>com.apple.security.cs.allow-dyld-environment-variables</key>
    <true/>
    <key>com.apple.security.cs.disable-library-validation</key>
    <true/>
</dict>
</plist>

Without debugging entitlements it's not possible to debug native modules with the official node binaries from nodejs.org. Entitlements can be added only when signing the binary.

Workarounds

  • Disable "hardened runtime" system-wide on osx (not suggested)

  • Use a self-built node executable (not suggested)

  • REPLACE node signature with your own (suggested):

    codesign --entitlements entitlements.txt -f -s "Developer ID Application: XXXXXXXX" /usr/local/bin/node
    

    Here is the contents of an entitlements.txt with the missing entitlement added:

  <?xml version="1.0" encoding="UTF-8"?>
<!DOCTYPE plist PUBLIC "-//Apple//DTD PLIST 1.0//EN" "http://www.apple.com/DTDs/PropertyList-1.0.dtd">
<plist version="1.0">
<dict>
    <key>com.apple.security.cs.allow-jit</key>
    <true/>
    <key>com.apple.security.cs.allow-unsigned-executable-memory</key>
    <true/>
    <key>com.apple.security.cs.disable-executable-page-protection</key>
    <true/>
    <key>com.apple.security.cs.allow-dyld-environment-variables</key>
    <true/>
    <key>com.apple.security.cs.disable-library-validation</key>
    <true/>
    <key>com.apple.security.get-task-allow</key>
    <true/>
</dict>
</plist>

Metadata

Metadata

Assignees

No one assigned

    Labels

    macosIssues and PRs related to the macOS platform.

    Type

    No type

    Projects

    No projects

      Milestone

      No milestone

      Relationships

      None yet

      Development

      No branches or pull requests

      Issue actions