Files
chimera-Public/test/server/ps5debug-readonly-client.test.js
T

60 lines
3.1 KiB
JavaScript

'use strict';
const test = require('node:test');
const assert = require('node:assert/strict');
const net = require('net');
const { createPs5DebugReadonlyClient, bitPairSwap32, firmwareString, COMMANDS, PACKET_MAGIC, CMD_SUCCESS } = require('../../src/services/ps5debug-readonly-client');
test('ps5debug client sends only the five allowlisted read-only commands', async () => {
const seen = [];
const server = net.createServer(socket => {
let pending = Buffer.alloc(0);
socket.on('data', chunk => {
pending = Buffer.concat([pending, chunk]);
while (pending.length >= 12) {
const header = pending.subarray(0, 12); pending = pending.subarray(12);
assert.equal(header.readUInt32LE(0), PACKET_MAGIC >>> 0);
assert.equal(header.readUInt32LE(8), 0);
const command = header.readUInt32LE(4); seen.push(command);
if ([COMMANDS.VERSION, COMMANDS.BRANDING].includes(command)) {
const text = Buffer.from(command === COMMANDS.VERSION ? '1.3' : 'ps5debug-NG test');
const length = Buffer.alloc(4); length.writeUInt32LE(text.length, 0); socket.write(Buffer.concat([length, text]));
} else if (command === COMMANDS.FW_VERSION) {
const value = Buffer.alloc(2); value.writeUInt16LE(751, 0); socket.write(value);
} else if (command === COMMANDS.PLATFORM_ID) {
const value = Buffer.alloc(2); value.writeUInt16LE(5, 0); socket.write(value);
} else if (command === COMMANDS.FOREGROUND_APP) {
const status = Buffer.alloc(4); status.writeUInt32LE(bitPairSwap32(CMD_SUCCESS), 0); socket.write(status);
const value = Buffer.alloc(140); value.writeUInt32LE(4242, 0);
value.write('PPSA00001', 4); value.write('EP0000-PPSA00001_00-TEST', 20); value.write('eboot.bin', 84); value.write('01.23', 124); socket.write(value);
}
}
});
});
await new Promise(resolve => server.listen(0, '127.0.0.1', resolve));
try {
const port = server.address().port;
const client = createPs5DebugReadonlyClient({
settings: { get: key => key === 'ftp.host' ? '127.0.0.1' : '' }, port, timeoutMs: 1_000,
db: { getGame: id => id === 'PPSA00001' ? { title: 'Test Game', prospero_icon_url: '/icon.webp', version: '1.23' } : null },
});
const packet = await client.query();
assert.equal(packet.online, true);
assert.equal(packet.protocol, '1.3');
assert.equal(packet.firmware, '7.51');
assert.equal(packet.platform, 5);
assert.equal(packet.foreground.titleId, 'PPSA00001');
assert.equal(packet.foreground.game.title, 'Test Game');
assert.deepEqual(seen, [COMMANDS.VERSION, COMMANDS.BRANDING, COMMANDS.FW_VERSION, COMMANDS.PLATFORM_ID, COMMANDS.FOREGROUND_APP]);
assert.equal(packet.policy.memoryRead, false);
assert.equal(packet.policy.memoryWrite, false);
assert.equal(packet.policy.kernelAccess, false);
} finally { await new Promise(resolve => server.close(resolve)); }
});
test('firmware and status bit transforms are deterministic', () => {
assert.equal(firmwareString(505), '5.05');
assert.equal(firmwareString(960), '9.60');
assert.equal(bitPairSwap32(bitPairSwap32(CMD_SUCCESS)), CMD_SUCCESS);
});