Skip to content

Commit

Permalink
fix(cli-repl): patch WASM wrapper for pac-proxy-agent on s390x MONGOS…
Browse files Browse the repository at this point in the history
  • Loading branch information
addaleax authored Aug 14, 2024
1 parent 50de961 commit ea12bee
Show file tree
Hide file tree
Showing 4 changed files with 77 additions and 7 deletions.
2 changes: 2 additions & 0 deletions packages/cli-repl/.depcheckrc
Original file line number Diff line number Diff line change
Expand Up @@ -18,5 +18,7 @@ ignores:
- ipv6-normalize
- bindings
- system-ca
# used for monkey-patching our s390x fix in
- '@tootallnate/quickjs-emscripten'
ignore-patterns:
- .eslintrc.js
53 changes: 53 additions & 0 deletions packages/cli-repl/src/pac-proxy-s390x-patch.ts
Original file line number Diff line number Diff line change
@@ -0,0 +1,53 @@
import assert from 'assert';

const isBigEndian =
new Int32Array(new Uint8Array([1, 0, 0, 0]).buffer)[0] !== 1;

// The pac-proxy-agent module uses a WebAssembly agent under the hood for
// safely evaluating JS. The interface for this doesn't properly account for
// little-endian vs. big-endian host platform distinctions.

// Official support for s390x may not be planned: https://github.com/justjake/quickjs-emscripten/issues/123

export let applyPacProxyS390XPatch: () => void;
if (isBigEndian) {
applyPacProxyS390XPatch = () => {
// eslint-disable-next-line @typescript-eslint/no-var-requires
const {
ModuleMemory,
} = require('@tootallnate/quickjs-emscripten/dist/memory');

const { toPointerArray } = ModuleMemory.prototype;
{
// Consistency check: The version we are currently using is actually broken
const HEAPU8 = new Uint8Array(4);
toPointerArray.call(
new ModuleMemory({
_malloc: () => 0,
HEAPU8,
}),
[{ value: 0x01020304 }]
);
assert.deepStrictEqual([...HEAPU8], [1, 2, 3, 4]); // should be 4, 3, 2, 1
}

ModuleMemory.prototype.toPointerArray = function (
handleArray: { value: number }[]
) {
return toPointerArray.call(
this,
handleArray.map(({ value }) => ({
value:
((value & 0x000000ff) << 24) |
((value & 0x0000ff00) << 8) |
((value & 0x00ff0000) >> 8) |
((value & 0xff000000) >> 24),
}))
);
};
};
} else {
applyPacProxyS390XPatch = () => {
// no-op
};
}
3 changes: 3 additions & 0 deletions packages/cli-repl/src/run.ts
Original file line number Diff line number Diff line change
Expand Up @@ -22,6 +22,7 @@ import { baseBuildInfo, buildInfo } from './build-info';
import { getStoragePaths, getGlobalConfigPaths } from './config-directory';
import { getCryptLibraryPaths } from './crypt-library-paths';
import { getTlsCertificateSelector } from './tls-certificate-selector';
import { applyPacProxyS390XPatch } from './pac-proxy-s390x-patch';
import { redactURICredentials } from '@mongosh/history';
import { generateConnectionInfoFromCliArgs } from '@mongosh/arg-parser';
import askcharacter from 'askcharacter';
Expand Down Expand Up @@ -170,6 +171,8 @@ async function main() {
process.removeAllListeners('SIGINT');
}

applyPacProxyS390XPatch();

// If we are spawned via Windows doubleclick, ask the user for an URI to
// connect to. Allow an environment variable to override this for testing.
isSingleConsoleProcess =
Expand Down
26 changes: 19 additions & 7 deletions packages/e2e-tests/test/e2e-snapshot.spec.ts
Original file line number Diff line number Diff line change
Expand Up @@ -15,7 +15,7 @@ const commonPrefix = (a: string, b: string): string =>
? a
: b && commonPrefix(a, b.slice(0, -1));

describe('e2e startup banners', function () {
describe('e2e snapshot support', function () {
skipIfApiStrict();
afterEach(TestShell.cleanup);

Expand Down Expand Up @@ -103,14 +103,22 @@ describe('e2e startup banners', function () {
// console.table(categorized.map(([m, c]) => [m.replace(prefix, ''), c]));
const verifyAllInCategoryMatch = (
category: (typeof categorized)[number][1],
re: RegExp
re: RegExp,
negative = false
) => {
for (const [module, cat] of categorized) {
if (cat === category) {
expect(module).to.match(
re,
`Found unexpected '${module}' in category '${cat}'`
);
if (negative) {
expect(module).not.to.match(
re,
`Found unexpected '${module}' in category '${cat}'`
);
} else {
expect(module).to.match(
re,
`Found unexpected '${module}' in category '${cat}'`
);
}
}
}
};
Expand Down Expand Up @@ -138,8 +146,12 @@ describe('e2e startup banners', function () {
);
verifyAllInCategoryMatch(
'nodb-eval',
/^node_modules\/(kerberos|mongodb-client-encryption|glibc-version|@mongodb-js\/devtools-proxy-support|@mongodb-js\/socksv5|agent-base|(win|macos)-export-certificate-and-key)\//
/^node_modules\/(kerberos|mongodb-client-encryption|glibc-version|@mongodb-js\/devtools-proxy-support|@mongodb-js\/socksv5|agent-base|(win|macos)-export-certificate-and-key|@tootallnate\/quickjs-emscripten)\//
);
if (process.arch !== 's390x') {
// quickjs is in the list above but should be exlucded anywhere but on s390x
verifyAllInCategoryMatch('nodb-eval', /quickjs-emscripten/, true);
}
verifyAllThatMatchAreInCategory(
'not-loaded',
/^node_modules\/(express|openid-client|qs|send|jose|execa|body-parser|@babel\/highlight|@babel\/code-frame)\//
Expand Down

0 comments on commit ea12bee

Please sign in to comment.