test: preserve method-free IL2CPP overflow verification

This commit is contained in:
morluto committed 2026-11-10 16:48:48 -05:00
1 parent d5e2d59eb6
commit 86b1b1431a
2 files changed
+39 -11

No files matched your search

+15 -6
View File
@@ -6,6 +6,7 @@ import { Client } from "@modelcontextprotocol/client";
import { StdioClientTransport } from "@modelcontextprotocol/client/stdio";
import { absoluteCallerPath } from "../dist/filesystem/callerPath.js";
import { toolContract } from "../dist/contracts/toolContracts.js";
import { il2cppMetadataViewRequestSchema } from "../dist/domain/analysisView/il2cppMetadataView.js";
import { ArtifactResourceScope } from "../dist/artifacts/ArtifactResourceScope.js";
import {
requireMcpOutput,
@@ -79,24 +80,32 @@ await withVerifierCleanup(async () => {
assert.equal(error.code, "resource_constraint");
assert.equal(error.details.reported_limits.boundary, "mcp-response");
assert.match(error.details.reported_limits.evidence_id, /^ev_/u);
const collections = il2cppMetadataViewRequestSchema.options.map(
(option) => option.shape.collection.value,
);
const collection =
["methods", ...collections].find(
(name) => Array.isArray(report[name]) && report[name].length > 0,
) ?? "methods";
const expectedRows = report[collection].slice(0, 16);
const retained = (
await call("inspect_analysis_view", {
source: {
kind: "retained-evidence",
evidence_id: error.details.reported_limits.evidence_id,
},
view: { kind: "il2cpp-metadata", collection: "methods", limit: 16 },
view: { kind: "il2cpp-metadata", collection, limit: 16 },
})
).normalized_result;
assert.ok(
report.methods.length > 0,
"Overflow retention needs a nonempty method oracle",
);
assert.deepEqual(
retained.items,
report.methods.slice(0, 16).map((row, index) => ({ ...row, index })),
expectedRows.map((row, index) => ({ ...row, index })),
"Failed complete delivery must retain its exact Evidence before reanalysis",
);
if (expectedRows.length === 0)
console.log(
"[unverified] Retention lookup succeeded, but empty queryable tables provide no nonempty row-content witness",
);
console.log(
`[ok] MCP complete delivery refused at the stdio budget (${error.details.reported_limits.response_bytes_at_least} bytes) with retained Evidence`,
);
@@ -8,9 +8,18 @@ import { expect, it } from "vitest";
const execute = promisify(execFile);
it.each([true, false])(
"requires overflow Evidence to be retained before another analysis (retained=%s)",
async (retained) => {
it.each([
["methods", true],
["methods", false],
["types", true],
["types", false],
["sections", true],
["sections", false],
["empty", true],
["empty", false],
] as const)(
"requires overflow Evidence before reanalysis (%s, retained=%s)",
async (collection, retained) => {
const directory = await mkdtemp(
join(tmpdir(), "rea-il2cpp-retention-oracle-"),
);
@@ -24,7 +33,10 @@ import {promisify} from 'node:util';
const path=process.env.INPUT;
const identity={sha256:'a'.repeat(64),bytes:1};
const report={artifact:{path,...identity},magic:0xfab11baf,sections:[],images:[{type_count:1}],types:[{declaring_type:-1,method_start:0,method_count:1}],methods:[{declaring_type:0,name:'AuthoredMethod'}],fields:[],properties:[],events:[],parameters:[],string_literals:[]};
const counts={sections:0,images:1,types:1,methods:1,nested_types:0,fields:0,properties:0,events:0,parameters:0,string_literals:0,...Object.fromEntries(['code_gen_modules','method_addresses','method_address_states','return_types','field_types','parameter_types','generic_method_instances','generic_method_instance_states','generic_method_issues'].map(k=>[k,null]))};
if(process.env.COLLECTION!=='methods'){report.methods=[];report.types[0].method_count=0;}
if(['sections','empty'].includes(process.env.COLLECTION)){report.images=[];report.types=[];}
if(process.env.COLLECTION==='sections')report.sections=[{name:'authored-nonmethod-table',offset:64,size:4096}];
const counts={sections:report.sections.length,images:report.images.length,types:report.types.length,methods:report.methods.length,nested_types:0,fields:0,properties:0,events:0,parameters:0,string_literals:0,...Object.fromEntries(['code_gen_modules','method_addresses','method_address_states','return_types','field_types','parameter_types','generic_method_instances','generic_method_instance_states','generic_method_issues'].map(k=>[k,null]))};
let reanalyzed=false;
export class Client {
async connect(){} async close(){} async listTools(){return {tools:[{name:'inspect_il2cpp_metadata'}]};}
@@ -76,13 +88,20 @@ registerHooks({resolve(specifier,context,next){
RECORDING: join(directory, "recording.mjs"),
INPUT: join(directory, "metadata.dat"),
RETAINED: String(retained),
COLLECTION: collection,
},
},
);
if (retained) {
expect((await result).stdout).toContain(
const { stdout } = await result;
expect(stdout).toContain(
"All asserted IL2CPP metadata CLI/MCP checks passed",
);
expect(
stdout.includes(
"empty queryable tables provide no nonempty row-content witness",
),
).toBe(collection === "empty");
} else {
await expect(result).rejects.toMatchObject({
stderr: expect.stringContaining(