Skip to content

Commit a69c7d7

Browse files
committed
src,permission: add --allow-addon flag
PR-URL: #51183 Reviewed-By: Marco Ippolito <[email protected]> Reviewed-By: Paolo Insogna <[email protected]>
1 parent 8ff6bc4 commit a69c7d7

File tree

10 files changed

+94
-1
lines changed

10 files changed

+94
-1
lines changed

doc/api/cli.md

Lines changed: 42 additions & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -103,6 +103,47 @@ If this flag is passed, the behavior can still be set to not abort through
103103
[`process.setUncaughtExceptionCaptureCallback()`][] (and through usage of the
104104
`node:domain` module that uses it).
105105

106+
### `--allow-addons`
107+
108+
<!-- YAML
109+
added: REPLACEME
110+
-->
111+
112+
> Stability: 1.1 - Active development
113+
114+
When using the [Permission Model][], the process will not be able to use
115+
native addons by default.
116+
Attempts to do so will throw an `ERR_DLOPEN_DISABLED` unless the
117+
user explicitly passes the `--allow-addons` flag when starting Node.js.
118+
119+
Example:
120+
121+
```cjs
122+
// Attempt to require an native addon
123+
require('nodejs-addon-example');
124+
```
125+
126+
```console
127+
$ node --experimental-permission --allow-fs-read=* index.js
128+
node:internal/modules/cjs/loader:1319
129+
return process.dlopen(module, path.toNamespacedPath(filename));
130+
^
131+
132+
Error: Cannot load native addon because loading addons is disabled.
133+
at Module._extensions..node (node:internal/modules/cjs/loader:1319:18)
134+
at Module.load (node:internal/modules/cjs/loader:1091:32)
135+
at Module._load (node:internal/modules/cjs/loader:938:12)
136+
at Module.require (node:internal/modules/cjs/loader:1115:19)
137+
at require (node:internal/modules/helpers:130:18)
138+
at Object.<anonymous> (/home/index.js:1:15)
139+
at Module._compile (node:internal/modules/cjs/loader:1233:14)
140+
at Module._extensions..js (node:internal/modules/cjs/loader:1287:10)
141+
at Module.load (node:internal/modules/cjs/loader:1091:32)
142+
at Module._load (node:internal/modules/cjs/loader:938:12) {
143+
code: 'ERR_DLOPEN_DISABLED'
144+
}
145+
```
146+
106147
### `--allow-child-process`
107148

108149
<!-- YAML
@@ -2407,6 +2448,7 @@ Node.js options that are allowed are:
24072448

24082449
<!-- node-options-node start -->
24092450

2451+
* `--allow-addons`
24102452
* `--allow-child-process`
24112453
* `--allow-fs-read`
24122454
* `--allow-fs-write`

doc/api/permissions.md

Lines changed: 4 additions & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -506,6 +506,9 @@ Error: Access to this API has been restricted
506506
Allowing access to spawning a process and creating worker threads can be done
507507
using the [`--allow-child-process`][] and [`--allow-worker`][] respectively.
508508

509+
To allow native addons when using permission model, use the [`--allow-addons`][]
510+
flag.
511+
509512
#### Runtime API
510513

511514
When enabling the Permission Model through the [`--experimental-permission`][]
@@ -588,6 +591,7 @@ There are constraints you need to know before using this system:
588591

589592
[Import maps]: https://url.spec.whatwg.org/#relative-url-with-fragment-string
590593
[Security Policy]: https://github.com/nodejs/node/blob/main/SECURITY.md
594+
[`--allow-addons`]: cli.md#--allow-addons
591595
[`--allow-child-process`]: cli.md#--allow-child-process
592596
[`--allow-fs-read`]: cli.md#--allow-fs-read
593597
[`--allow-fs-write`]: cli.md#--allow-fs-write

doc/node.1

Lines changed: 3 additions & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -82,6 +82,9 @@ Allow file system read access when using the permission model.
8282
.It Fl -allow-fs-write
8383
Allow file system write access when using the permission model.
8484
.
85+
.It Fl -allow-addons
86+
Allow using native addons when using the permission model.
87+
.
8588
.It Fl -allow-child-process
8689
Allow spawning process when using the permission model.
8790
.

lib/internal/process/pre_execution.js

Lines changed: 2 additions & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -615,6 +615,7 @@ function initializePermission() {
615615
'ExperimentalWarning');
616616
const { has, deny } = require('internal/process/permission');
617617
const warnFlags = [
618+
'--allow-addons',
618619
'--allow-child-process',
619620
'--allow-worker',
620621
];
@@ -655,6 +656,7 @@ function initializePermission() {
655656
const availablePermissionFlags = [
656657
'--allow-fs-read',
657658
'--allow-fs-write',
659+
'--allow-addons',
658660
'--allow-child-process',
659661
'--allow-worker',
660662
];

src/env.cc

Lines changed: 3 additions & 1 deletion
Original file line numberDiff line numberDiff line change
@@ -894,7 +894,9 @@ Environment::Environment(IsolateData* isolate_data,
894894
// The process shouldn't be able to neither
895895
// spawn/worker nor use addons or enable inspector
896896
// unless explicitly allowed by the user
897-
options_->allow_native_addons = false;
897+
if (!options_->allow_addons) {
898+
options_->allow_native_addons = false;
899+
}
898900
flags_ = flags_ | EnvironmentFlags::kNoCreateInspector;
899901
permission()->Apply({"*"}, permission::PermissionScope::kInspector);
900902
if (!options_->allow_child_process) {

src/node_options.cc

Lines changed: 4 additions & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -447,6 +447,10 @@ EnvironmentOptionsParser::EnvironmentOptionsParser() {
447447
"allow permissions to write in the filesystem",
448448
&EnvironmentOptions::allow_fs_write,
449449
kAllowedInEnvvar);
450+
AddOption("--allow-addons",
451+
"allow use of addons when any permissions are set",
452+
&EnvironmentOptions::allow_addons,
453+
kAllowedInEnvvar);
450454
AddOption("--allow-child-process",
451455
"allow use of child process when any permissions are set",
452456
&EnvironmentOptions::allow_child_process,

src/node_options.h

Lines changed: 1 addition & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -123,6 +123,7 @@ class EnvironmentOptions : public Options {
123123
bool experimental_permission = false;
124124
std::vector<std::string> allow_fs_read;
125125
std::vector<std::string> allow_fs_write;
126+
bool allow_addons = false;
126127
bool allow_child_process = false;
127128
bool allow_worker_threads = false;
128129
bool experimental_repl_await = true;
Lines changed: 17 additions & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -0,0 +1,17 @@
1+
// Flags: --experimental-permission --allow-addons --allow-fs-read=*
2+
'use strict';
3+
4+
const common = require('../common');
5+
common.skipIfWorker();
6+
7+
const { createRequire } = require('node:module');
8+
const assert = require('node:assert');
9+
const fixtures = require('../common/fixtures');
10+
const loadFixture = createRequire(fixtures.path('node_modules'));
11+
// When a permission is set by cli, the process shouldn't be able
12+
// to require native addons unless --allow-addons is sent
13+
{
14+
// doesNotThrow
15+
const msg = loadFixture('pkgexports/no-addons');
16+
assert.strictEqual(msg, 'using native addons');
17+
}
Lines changed: 17 additions & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -0,0 +1,17 @@
1+
// Flags: --experimental-permission --allow-fs-read=*
2+
'use strict';
3+
4+
const common = require('../common');
5+
common.skipIfWorker();
6+
7+
const { createRequire } = require('node:module');
8+
const assert = require('node:assert');
9+
const fixtures = require('../common/fixtures');
10+
const loadFixture = createRequire(fixtures.path('node_modules'));
11+
// When a permission is set by cli, the process shouldn't be able
12+
// to require native addons unless --allow-addons is sent
13+
{
14+
// doesNotThrow
15+
const msg = loadFixture('pkgexports/no-addons');
16+
assert.strictEqual(msg, 'not using native addons');
17+
}

test/parallel/test-permission-warning-flags.js

Lines changed: 1 addition & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -5,6 +5,7 @@ const { spawnSync } = require('child_process');
55
const assert = require('assert');
66

77
const warnFlags = [
8+
'--allow-addons',
89
'--allow-child-process',
910
'--allow-worker',
1011
];

0 commit comments

Comments
 (0)