Skip to content

Commit e278cb5

Browse files
authored
Remove code duplication between library_wasmfs.js and library_fs.js (#19279)
1 parent 9d03621 commit e278cb5

File tree

5 files changed

+112
-143
lines changed

5 files changed

+112
-143
lines changed

src/library_fs.js

Lines changed: 9 additions & 71 deletions
Original file line numberDiff line numberDiff line change
@@ -5,7 +5,10 @@
55
*/
66

77
mergeInto(LibraryManager.library, {
8-
$FS__deps: ['$randomFill', '$PATH', '$PATH_FS', '$TTY', '$MEMFS', '$asyncLoad',
8+
$FS__deps: ['$randomFill', '$PATH', '$PATH_FS', '$TTY', '$MEMFS',
9+
'$FS_createPreloadedFile',
10+
'$FS_modeStringToFlags',
11+
'$FS_getMode',
912
'$intArrayFromString',
1013
'$stringToUTF8Array',
1114
'$lengthBytesUTF8',
@@ -88,6 +91,7 @@ Object.defineProperties(FSNode.prototype, {
8891
}
8992
});
9093
FS.FSNode = FSNode;
94+
FS.createPreloadedFile = FS_createPreloadedFile;
9195
FS.staticInit();` +
9296
#if USE_CLOSURE_COMPILER
9397
// Declare variable for Closure, FS.createPreloadedFile() below calls Browser.handledByPreloadPlugin()
@@ -293,25 +297,6 @@ FS.staticInit();` +
293297
//
294298
// permissions
295299
//
296-
flagModes: {
297-
// Extra quotes used here on the keys to this object otherwise jsifier will
298-
// erase them in the process of reading and then writing the JS library
299-
// code.
300-
'"r"': {{{ cDefs.O_RDONLY }}},
301-
'"r+"': {{{ cDefs.O_RDWR }}},
302-
'"w"': {{{ cDefs.O_TRUNC }}} | {{{ cDefs.O_CREAT }}} | {{{ cDefs.O_WRONLY }}},
303-
'"w+"': {{{ cDefs.O_TRUNC }}} | {{{ cDefs.O_CREAT }}} | {{{ cDefs.O_RDWR }}},
304-
'"a"': {{{ cDefs.O_APPEND }}} | {{{ cDefs.O_CREAT }}} | {{{ cDefs.O_WRONLY }}},
305-
'"a+"': {{{ cDefs.O_APPEND }}} | {{{ cDefs.O_CREAT }}} | {{{ cDefs.O_RDWR }}},
306-
},
307-
// convert the 'r', 'r+', etc. to it's corresponding set of O_* flags
308-
modeStringToFlags: (str) => {
309-
var flags = FS.flagModes[str];
310-
if (typeof flags == 'undefined') {
311-
throw new Error('Unknown file open mode: ' + str);
312-
}
313-
return flags;
314-
},
315300
// convert O_* bitmask to a string for nodePermissions
316301
flagsToPermissionString: (flag) => {
317302
var perms = ['r', 'w', 'rw'][flag & 3];
@@ -1010,7 +995,7 @@ FS.staticInit();` +
1010995
if (path === "") {
1011996
throw new FS.ErrnoError({{{ cDefs.ENOENT }}});
1012997
}
1013-
flags = typeof flags == 'string' ? FS.modeStringToFlags(flags) : flags;
998+
flags = typeof flags == 'string' ? FS_modeStringToFlags(flags) : flags;
1014999
mode = typeof mode == 'undefined' ? 438 /* 0666 */ : mode;
10151000
if ((flags & {{{ cDefs.O_CREAT }}})) {
10161001
mode = (mode & {{{ cDefs.S_IALLUGO }}}) | {{{ cDefs.S_IFREG }}};
@@ -1536,12 +1521,6 @@ FS.staticInit();` +
15361521
//
15371522
// old v1 compatibility functions
15381523
//
1539-
getMode: (canRead, canWrite) => {
1540-
var mode = 0;
1541-
if (canRead) mode |= {{{ cDefs.S_IRUGO }}} | {{{ cDefs.S_IXUGO }}};
1542-
if (canWrite) mode |= {{{ cDefs.S_IWUGO }}};
1543-
return mode;
1544-
},
15451524
findObject: (path, dontResolveLastLink) => {
15461525
var ret = FS.analyzePath(path, dontResolveLastLink);
15471526
if (!ret.exists) {
@@ -1595,7 +1574,7 @@ FS.staticInit();` +
15951574
},
15961575
createFile: (parent, name, properties, canRead, canWrite) => {
15971576
var path = PATH.join2(typeof parent == 'string' ? parent : FS.getPath(parent), name);
1598-
var mode = FS.getMode(canRead, canWrite);
1577+
var mode = FS_getMode(canRead, canWrite);
15991578
return FS.create(path, mode);
16001579
},
16011580
createDataFile: (parent, name, data, canRead, canWrite, canOwn) => {
@@ -1604,7 +1583,7 @@ FS.staticInit();` +
16041583
parent = typeof parent == 'string' ? parent : FS.getPath(parent);
16051584
path = name ? PATH.join2(parent, name) : parent;
16061585
}
1607-
var mode = FS.getMode(canRead, canWrite);
1586+
var mode = FS_getMode(canRead, canWrite);
16081587
var node = FS.create(path, mode);
16091588
if (data) {
16101589
if (typeof data == 'string') {
@@ -1623,7 +1602,7 @@ FS.staticInit();` +
16231602
},
16241603
createDevice: (parent, name, input, output) => {
16251604
var path = PATH.join2(typeof parent == 'string' ? parent : FS.getPath(parent), name);
1626-
var mode = FS.getMode(!!input, !!output);
1605+
var mode = FS_getMode(!!input, !!output);
16271606
if (!FS.createDevice.major) FS.createDevice.major = 64;
16281607
var dev = FS.makedev(FS.createDevice.major++, 0);
16291608
// Create a fake device that a set of stream ops to emulate
@@ -1872,47 +1851,6 @@ FS.staticInit();` +
18721851
node.stream_ops = stream_ops;
18731852
return node;
18741853
},
1875-
// Preloads a file asynchronously. You can call this before run, for example in
1876-
// preRun. run will be delayed until this file arrives and is set up.
1877-
// If you call it after run(), you may want to pause the main loop until it
1878-
// completes, if so, you can use the onload parameter to be notified when
1879-
// that happens.
1880-
// In addition to normally creating the file, we also asynchronously preload
1881-
// the browser-friendly versions of it: For an image, we preload an Image
1882-
// element and for an audio, and Audio. These are necessary for SDL_Image
1883-
// and _Mixer to find the files in preloadedImages/Audios.
1884-
// You can also call this with a typed array instead of a url. It will then
1885-
// do preloading for the Image/Audio part, as if the typed array were the
1886-
// result of an XHR that you did manually.
1887-
createPreloadedFile: (parent, name, url, canRead, canWrite, onload, onerror, dontCreateFile, canOwn, preFinish) => {
1888-
// TODO we should allow people to just pass in a complete filename instead
1889-
// of parent and name being that we just join them anyways
1890-
var fullname = name ? PATH_FS.resolve(PATH.join2(parent, name)) : parent;
1891-
var dep = getUniqueRunDependency('cp ' + fullname); // might have several active requests for the same fullname
1892-
function processData(byteArray) {
1893-
function finish(byteArray) {
1894-
if (preFinish) preFinish();
1895-
if (!dontCreateFile) {
1896-
FS.createDataFile(parent, name, byteArray, canRead, canWrite, canOwn);
1897-
}
1898-
if (onload) onload();
1899-
removeRunDependency(dep);
1900-
}
1901-
if (Browser.handledByPreloadPlugin(byteArray, fullname, finish, () => {
1902-
if (onerror) onerror();
1903-
removeRunDependency(dep);
1904-
})) {
1905-
return;
1906-
}
1907-
finish(byteArray);
1908-
}
1909-
addRunDependency(dep);
1910-
if (typeof url == 'string') {
1911-
asyncLoad(url, (byteArray) => processData(byteArray), onerror);
1912-
} else {
1913-
processData(url);
1914-
}
1915-
},
19161854

19171855
// Removed v1 functions
19181856
#if ASSERTIONS

src/library_fs_shared.js

Lines changed: 79 additions & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -0,0 +1,79 @@
1+
/**
2+
* @license
3+
* Copyright 2032 The Emscripten Authors
4+
* SPDX-License-Identifier: MIT
5+
*/
6+
7+
mergeInto(LibraryManager.library, {
8+
// Preloads a file asynchronously. You can call this before run, for example in
9+
// preRun. run will be delayed until this file arrives and is set up.
10+
// If you call it after run(), you may want to pause the main loop until it
11+
// completes, if so, you can use the onload parameter to be notified when
12+
// that happens.
13+
// In addition to normally creating the file, we also asynchronously preload
14+
// the browser-friendly versions of it: For an image, we preload an Image
15+
// element and for an audio, and Audio. These are necessary for SDL_Image
16+
// and _Mixer to find the files in preloadedImages/Audios.
17+
// You can also call this with a typed array instead of a url. It will then
18+
// do preloading for the Image/Audio part, as if the typed array were the
19+
// result of an XHR that you did manually.
20+
$FS_createPreloadedFile__deps: ['$asyncLoad'],
21+
$FS_createPreloadedFile: function(parent, name, url, canRead, canWrite, onload, onerror, dontCreateFile, canOwn, preFinish) {
22+
#if WASMFS
23+
// TODO: use WasmFS code to resolve and join the path here?
24+
var fullname = name ? parent + '/' + name : parent;
25+
#else
26+
// TODO we should allow people to just pass in a complete filename instead
27+
// of parent and name being that we just join them anyways
28+
var fullname = name ? PATH_FS.resolve(PATH.join2(parent, name)) : parent;
29+
#endif
30+
var dep = getUniqueRunDependency('cp ' + fullname); // might have several active requests for the same fullname
31+
function processData(byteArray) {
32+
function finish(byteArray) {
33+
if (preFinish) preFinish();
34+
if (!dontCreateFile) {
35+
FS.createDataFile(parent, name, byteArray, canRead, canWrite, canOwn);
36+
}
37+
if (onload) onload();
38+
removeRunDependency(dep);
39+
}
40+
#if !MINIMAL_RUNTIME
41+
if (Browser.handledByPreloadPlugin(byteArray, fullname, finish, () => {
42+
if (onerror) onerror();
43+
removeRunDependency(dep);
44+
})) {
45+
return;
46+
}
47+
#endif
48+
finish(byteArray);
49+
}
50+
addRunDependency(dep);
51+
if (typeof url == 'string') {
52+
asyncLoad(url, (byteArray) => processData(byteArray), onerror);
53+
} else {
54+
processData(url);
55+
}
56+
},
57+
// convert the 'r', 'r+', etc. to it's corresponding set of O_* flags
58+
$FS_modeStringToFlags: function(str) {
59+
var flagModes = {
60+
'r': {{{ cDefs.O_RDONLY }}},
61+
'r+': {{{ cDefs.O_RDWR }}},
62+
'w': {{{ cDefs.O_TRUNC }}} | {{{ cDefs.O_CREAT }}} | {{{ cDefs.O_WRONLY }}},
63+
'w+': {{{ cDefs.O_TRUNC }}} | {{{ cDefs.O_CREAT }}} | {{{ cDefs.O_RDWR }}},
64+
'a': {{{ cDefs.O_APPEND }}} | {{{ cDefs.O_CREAT }}} | {{{ cDefs.O_WRONLY }}},
65+
'a+': {{{ cDefs.O_APPEND }}} | {{{ cDefs.O_CREAT }}} | {{{ cDefs.O_RDWR }}},
66+
};
67+
var flags = flagModes[str];
68+
if (typeof flags == 'undefined') {
69+
throw new Error('Unknown file open mode: ' + str);
70+
}
71+
return flags;
72+
},
73+
$FS_getMode: function(canRead, canWrite) {
74+
var mode = 0;
75+
if (canRead) mode |= {{{ cDefs.S_IRUGO }}} | {{{ cDefs.S_IXUGO }}};
76+
if (canWrite) mode |= {{{ cDefs.S_IWUGO }}};
77+
return mode;
78+
},
79+
});

src/library_noderawfs.js

Lines changed: 2 additions & 2 deletions
Original file line numberDiff line numberDiff line change
@@ -5,7 +5,7 @@
55
*/
66

77
mergeInto(LibraryManager.library, {
8-
$NODERAWFS__deps: ['$ERRNO_CODES', '$FS', '$NODEFS', '$mmapAlloc'],
8+
$NODERAWFS__deps: ['$ERRNO_CODES', '$FS', '$NODEFS', '$mmapAlloc', '$FS_modeStringToFlags'],
99
$NODERAWFS__postset: `
1010
if (ENVIRONMENT_IS_NODE) {
1111
var _wrapNodeError = function(func) {
@@ -83,7 +83,7 @@ mergeInto(LibraryManager.library, {
8383
utime: function(path, atime, mtime) { fs.utimesSync(path, atime/1000, mtime/1000); },
8484
open: function(path, flags, mode, suggestFD) {
8585
if (typeof flags == "string") {
86-
flags = VFS.modeStringToFlags(flags)
86+
flags = FS_modeStringToFlags(flags)
8787
}
8888
var pathTruncated = path.split('/').map(function(s) { return s.substr(0, 255); }).join('/');
8989
var nfd = fs.openSync(pathTruncated, NODEFS.flagsForNode(flags), mode);

src/library_wasmfs.js

Lines changed: 12 additions & 63 deletions
Original file line numberDiff line numberDiff line change
@@ -7,82 +7,31 @@
77
mergeInto(LibraryManager.library, {
88
$wasmFSPreloadedFiles: [],
99
$wasmFSPreloadedDirs: [],
10-
#if USE_CLOSURE_COMPILER
1110
// Declare variable for Closure, FS.createPreloadedFile() below calls Browser.handledByPreloadPlugin()
12-
$FS__postset: '/**@suppress {duplicate, undefinedVars}*/var Browser;',
11+
$FS__postset: `
12+
#if USE_CLOSURE_COMPILER
13+
/**@suppress {duplicate, undefinedVars}*/var Browser;
1314
#endif
15+
FS.createPreloadedFile = FS_createPreloadedFile;
16+
`,
1417
$FS__deps: [
1518
'$wasmFSPreloadedFiles',
1619
'$wasmFSPreloadedDirs',
17-
'$asyncLoad',
1820
'$PATH',
1921
'$stringToNewUTF8',
2022
'$stringToUTF8OnStack',
2123
'$withStackSave',
2224
'$readI53FromI64',
25+
'$FS_createPreloadedFile',
26+
'$FS_getMode',
27+
#if FORCE_FILESYSTEM
28+
'$FS_modeStringToFlags',
29+
#endif
2330
],
2431
$FS : {
25-
// TODO: Clean up the following functions - currently copied from library_fs.js directly.
26-
createPreloadedFile: (parent, name, url, canRead, canWrite, onload, onerror, dontCreateFile, canOwn, preFinish) => {
27-
// TODO: use WasmFS code to resolve and join the path here?
28-
var fullname = name ? parent + '/' + name : parent;
29-
var dep = getUniqueRunDependency('cp ' + fullname); // might have several active requests for the same fullname
30-
function processData(byteArray) {
31-
function finish(byteArray) {
32-
if (preFinish) preFinish();
33-
if (!dontCreateFile) {
34-
FS.createDataFile(parent, name, byteArray, canRead, canWrite, canOwn);
35-
}
36-
if (onload) onload();
37-
removeRunDependency(dep);
38-
}
39-
#if !MINIMAL_RUNTIME
40-
if (Browser.handledByPreloadPlugin(byteArray, fullname, finish, () => {
41-
if (onerror) onerror();
42-
removeRunDependency(dep);
43-
})) {
44-
return;
45-
}
46-
#endif
47-
finish(byteArray);
48-
}
49-
addRunDependency(dep);
50-
if (typeof url == 'string') {
51-
asyncLoad(url, (byteArray) => {
52-
processData(byteArray);
53-
}, onerror);
54-
} else {
55-
processData(url);
56-
}
57-
},
58-
getMode: (canRead, canWrite) => {
59-
var mode = 0;
60-
if (canRead) mode |= {{{ cDefs.S_IRUGO }}} | {{{ cDefs.S_IXUGO }}};
61-
if (canWrite) mode |= {{{ cDefs.S_IWUGO }}};
62-
return mode;
63-
},
64-
modeStringToFlags: (str) => {
65-
var flags = FS.flagModes[str];
66-
if (typeof flags == 'undefined') {
67-
throw new Error('Unknown file open mode: ' + str);
68-
}
69-
return flags;
70-
},
71-
flagModes: {
72-
// copied directly from library_fs.js
73-
// Extra quotes used here on the keys to this object otherwise jsifier will
74-
// erase them in the process of reading and then writing the JS library
75-
// code.
76-
'"r"': {{{ cDefs.O_RDONLY }}},
77-
'"r+"': {{{ cDefs.O_RDWR }}},
78-
'"w"': {{{ cDefs.O_TRUNC }}} | {{{ cDefs.O_CREAT }}} | {{{ cDefs.O_WRONLY }}},
79-
'"w+"': {{{ cDefs.O_TRUNC }}} | {{{ cDefs.O_CREAT }}} | {{{ cDefs.O_RDWR }}},
80-
'"a"': {{{ cDefs.O_APPEND }}} | {{{ cDefs.O_CREAT }}} | {{{ cDefs.O_WRONLY }}},
81-
'"a+"': {{{ cDefs.O_APPEND }}} | {{{ cDefs.O_CREAT }}} | {{{ cDefs.O_RDWR }}},
82-
},
8332
createDataFile: (parent, name, data, canRead, canWrite, canOwn) => {
8433
// Data files must be cached until the file system itself has been initialized.
85-
var mode = FS.getMode(canRead, canWrite);
34+
var mode = FS_getMode(canRead, canWrite);
8635
var pathName = name ? parent + '/' + name : parent;
8736
wasmFSPreloadedFiles.push({pathName: pathName, fileData: data, mode: mode});
8837
},
@@ -148,7 +97,7 @@ mergeInto(LibraryManager.library, {
14897
},
14998
// TODO: open
15099
open: (path, flags, mode) => {
151-
flags = typeof flags == 'string' ? FS.modeStringToFlags(flags) : flags;
100+
flags = typeof flags == 'string' ? FS_modeStringToFlags(flags) : flags;
152101
mode = typeof mode == 'undefined' ? 438 /* 0666 */ : mode;
153102
return withStackSave(() => {
154103
var buffer = stringToUTF8OnStack(path);

src/modules.js

Lines changed: 10 additions & 7 deletions
Original file line numberDiff line numberDiff line change
@@ -80,6 +80,7 @@ global.LibraryManager = {
8080
if (FILESYSTEM) {
8181
// Core filesystem libraries (always linked against, unless -sFILESYSTEM=0 is specified)
8282
libraries = libraries.concat([
83+
'library_fs_shared.js',
8384
'library_fs.js',
8485
'library_memfs.js',
8586
'library_tty.js',
@@ -97,12 +98,15 @@ global.LibraryManager = {
9798
libraries.push('library_nodepath.js');
9899
}
99100
} else if (WASMFS) {
100-
libraries.push('library_wasmfs.js');
101-
libraries.push('library_wasmfs_js_file.js');
102-
libraries.push('library_wasmfs_jsimpl.js');
103-
libraries.push('library_wasmfs_fetch.js');
104-
libraries.push('library_wasmfs_node.js');
105-
libraries.push('library_wasmfs_opfs.js');
101+
libraries = libraries.concat([
102+
'library_fs_shared.js',
103+
'library_wasmfs.js',
104+
'library_wasmfs_js_file.js',
105+
'library_wasmfs_jsimpl.js',
106+
'library_wasmfs_fetch.js',
107+
'library_wasmfs_node.js',
108+
'library_wasmfs_opfs.js',
109+
]);
106110
}
107111

108112
// Additional JS libraries (without AUTO_JS_LIBRARIES, link to these explicitly via -lxxx.js)
@@ -361,7 +365,6 @@ function exportRuntime() {
361365
'FS_createFolder',
362366
'FS_createPath',
363367
'FS_createDataFile',
364-
'FS_createPreloadedFile',
365368
'FS_createLazyFile',
366369
'FS_createLink',
367370
'FS_createDevice',

0 commit comments

Comments
 (0)