195639269Sstephan/** 295639269Sstephan BEGIN FILE: api/pre-js.js 395639269Sstephan 495639269Sstephan This file is intended to be prepended to the sqlite3.js build using 595639269Sstephan Emscripten's --pre-js=THIS_FILE flag (or equivalent). 695639269Sstephan*/ 7cd0df83cSstephan 8cd0df83cSstephan// See notes in extern-post-js.js 9cd0df83cSstephanconst sqlite3InitModuleState = self.sqlite3InitModuleState || Object.create(null); 10cd0df83cSstephandelete self.sqlite3InitModuleState; 11*1fc6ffccSstephansqlite3InitModuleState.debugModule('self.location =',self.location); 12cd0df83cSstephan 13cd0df83cSstephan/** 14cd0df83cSstephan This custom locateFile() tries to figure out where to load `path` 15cd0df83cSstephan from. The intent is to provide a way for foo/bar/X.js loaded from a 16cd0df83cSstephan Worker constructor or importScripts() to be able to resolve 17cd0df83cSstephan foo/bar/X.wasm (in the latter case, with some help): 18cd0df83cSstephan 19cd0df83cSstephan 1) If URL param named the same as `path` is set, it is returned. 20cd0df83cSstephan 21cd0df83cSstephan 2) If sqlite3InitModuleState.sqlite3Dir is set, then (thatName + path) 22cd0df83cSstephan is returned (note that it's assumed to end with '/'). 23cd0df83cSstephan 24cd0df83cSstephan 3) If this code is running in the main UI thread AND it was loaded 25cd0df83cSstephan from a SCRIPT tag, the directory part of that URL is used 26cd0df83cSstephan as the prefix. (This form of resolution unfortunately does not 27cd0df83cSstephan function for scripts loaded via importScripts().) 28cd0df83cSstephan 29cd0df83cSstephan 4) If none of the above apply, (prefix+path) is returned. 30cd0df83cSstephan*/ 31f71c954cSstephanModule['locateFile'] = function(path, prefix) { 32cd0df83cSstephan let theFile; 33cd0df83cSstephan const up = this.urlParams; 34cd0df83cSstephan if(up.has(path)){ 35cd0df83cSstephan theFile = up.get(path); 36cd0df83cSstephan }else if(this.sqlite3Dir){ 37cd0df83cSstephan theFile = this.sqlite3Dir + path; 38cd0df83cSstephan }else if(this.scriptDir){ 39cd0df83cSstephan theFile = this.scriptDir + path; 40cd0df83cSstephan }else{ 41cd0df83cSstephan theFile = prefix + path; 42cd0df83cSstephan } 43*1fc6ffccSstephan sqlite3InitModuleState.debugModule( 44*1fc6ffccSstephan "locateFile(",arguments[0], ',', arguments[1],")", 45*1fc6ffccSstephan 'sqlite3InitModuleState.scriptDir =',this.scriptDir, 46*1fc6ffccSstephan 'up.entries() =',Array.from(up.entries()), 47*1fc6ffccSstephan "result =", theFile 48*1fc6ffccSstephan ); 49cd0df83cSstephan return theFile; 50cd0df83cSstephan}.bind(sqlite3InitModuleState); 51f71c954cSstephan 52f71c954cSstephan/** 53*1fc6ffccSstephan Bug warning: a custom Module.instantiateWasm() does not work 54*1fc6ffccSstephan in WASMFS builds: 55f71c954cSstephan 56f71c954cSstephan https://github.com/emscripten-core/emscripten/issues/17951 57*1fc6ffccSstephan 58*1fc6ffccSstephan In such builds we must disable this. 59f71c954cSstephan*/ 60*1fc6ffccSstephanconst xNameOfInstantiateWasm = true 61*1fc6ffccSstephan ? 'instantiateWasm' 62*1fc6ffccSstephan : 'emscripten-bug-17951'; 63*1fc6ffccSstephanModule[xNameOfInstantiateWasm] = function callee(imports,onSuccess){ 64f6c686c9Sstephan imports.env.foo = function(){}; 65*1fc6ffccSstephan const uri = Module.locateFile( 66*1fc6ffccSstephan callee.uri, ( 67*1fc6ffccSstephan ('undefined'===typeof scriptDirectory/*var defined by Emscripten glue*/) 68*1fc6ffccSstephan ? '' : scriptDirectory) 69*1fc6ffccSstephan ); 70*1fc6ffccSstephan sqlite3InitModuleState.debugModule( 71*1fc6ffccSstephan "instantiateWasm() uri =", uri 72*1fc6ffccSstephan ); 73*1fc6ffccSstephan const wfetch = ()=>fetch(uri, {credentials: 'same-origin'}); 74f71c954cSstephan const loadWasm = WebAssembly.instantiateStreaming 75f6c686c9Sstephan ? async ()=>{ 76f71c954cSstephan return WebAssembly.instantiateStreaming(wfetch(), imports) 77f71c954cSstephan .then((arg)=>onSuccess(arg.instance, arg.module)); 78f71c954cSstephan } 79f6c686c9Sstephan : async ()=>{ // Safari < v15 80f71c954cSstephan return wfetch() 81f71c954cSstephan .then(response => response.arrayBuffer()) 82f71c954cSstephan .then(bytes => WebAssembly.instantiate(bytes, imports)) 83f71c954cSstephan .then((arg)=>onSuccess(arg.instance, arg.module)); 84f71c954cSstephan }; 85f71c954cSstephan loadWasm(); 86f71c954cSstephan return {}; 87f71c954cSstephan}; 88f71c954cSstephan/* 89f6c686c9Sstephan It is literally impossible to reliably get the name of _this_ script 90f6c686c9Sstephan at runtime, so impossible to derive X.wasm from script name 91f6c686c9Sstephan X.js. Thus we need, at build-time, to redefine 92*1fc6ffccSstephan Module[xNameOfInstantiateWasm].uri by appending it to a build-specific 93f6c686c9Sstephan copy of this file with the name of the wasm file. This is apparently 94f6c686c9Sstephan why Emscripten hard-codes the name of the wasm file into their glue 95f6c686c9Sstephan scripts. 96f71c954cSstephan*/ 97*1fc6ffccSstephanModule[xNameOfInstantiateWasm].uri = 'sqlite3.wasm'; 98*1fc6ffccSstephan/* END FILE: api/pre-js.js, noting that the build process may add a 99*1fc6ffccSstephan line after this one to change the above .uri to a build-specific 100*1fc6ffccSstephan one. */ 101