mirror of
https://github.com/morluto/rea.git
synced 2026-11-14 18:52:48 +00:00
fix(firmware): treat empty DTB extents as non-overlapping
Refs #7315 Co-Authored-By: gensokyo-dev <342580529+gensokyo-dev@users.noreply.github.com>
This commit is contained in:
1 parent
056b78b636
commit
8d546bd028
3 files changed
+54
-18
No files matched your search
@@ -259,6 +259,34 @@ it.each([16, 17] as const)(
|
||||
expect(report.reservations).toEqual([]);
|
||||
},
|
||||
);
|
||||
it.each([
|
||||
[16, 0],
|
||||
[16, 44],
|
||||
[16, 60],
|
||||
[16, 72],
|
||||
[17, 0],
|
||||
[17, 44],
|
||||
[17, 60],
|
||||
[17, 72],
|
||||
] as const)(
|
||||
"accepts a v%s empty strings block at offset %s",
|
||||
(version, offset) => {
|
||||
const bytes = emptyStringsAtReservationBoundaryFixture(version);
|
||||
bytes.writeUInt32BE(offset, 12);
|
||||
expect(parse(bytes)).toMatchObject({
|
||||
nodes: [{ path: "/" }],
|
||||
reservations: [],
|
||||
});
|
||||
},
|
||||
);
|
||||
it.each([16, 17] as const)(
|
||||
"rejects an empty strings offset beyond totalsize in v%s",
|
||||
(version) => {
|
||||
const bytes = emptyStringsAtReservationBoundaryFixture(version);
|
||||
bytes.writeUInt32BE(bytes.length + 1, 12);
|
||||
expect(() => parse(bytes)).toThrow("FDT block outside totalsize");
|
||||
},
|
||||
);
|
||||
it("bounds expansion of repeated paths before allocation", () => {
|
||||
const longName = "a".repeat(4096);
|
||||
let node: FixtureNode = { name: longName };
|
||||
|
||||
@@ -76,8 +76,10 @@ export const parseDevicetree = (
|
||||
{ start: 0, end: headerBytes },
|
||||
];
|
||||
const range = (start: number, size: number) => {
|
||||
if (size < 0 || start < headerBytes || start > end - size)
|
||||
if (size < 0 || (size > 0 && start < headerBytes) || start > end - size)
|
||||
malformed("FDT block outside totalsize");
|
||||
// An empty extent occupies no bytes and cannot overlap another block.
|
||||
if (size === 0) return;
|
||||
const r = { start, end: start + size };
|
||||
if (ranges.some((other) => r.start < other.end && other.start < r.end))
|
||||
malformed("Overlapping FDT blocks");
|
||||
@@ -91,9 +93,10 @@ export const parseDevicetree = (
|
||||
header.size_dt_struct === null
|
||||
? Math.min(
|
||||
end,
|
||||
...[header.off_dt_strings, header.off_mem_rsvmap].filter(
|
||||
(n) => n > header.off_dt_struct,
|
||||
),
|
||||
...[
|
||||
...(header.size_dt_strings > 0 ? [header.off_dt_strings] : []),
|
||||
header.off_mem_rsvmap,
|
||||
].filter((n) => n > header.off_dt_struct),
|
||||
)
|
||||
: header.off_dt_struct + header.size_dt_struct;
|
||||
range(header.off_dt_struct, structEnd - header.off_dt_struct);
|
||||
|
||||
@@ -146,22 +146,27 @@ cliTest("inspects a relative DTB and preserves the source", async ({ cli }) => {
|
||||
});
|
||||
for (const version of [16, 17] as const) {
|
||||
cliTest(
|
||||
`inspects a v${version} DTB with empty strings at the reservation boundary`,
|
||||
`inspects a v${version} DTB with empty strings at arbitrary in-blob offsets`,
|
||||
async ({ cli }) => {
|
||||
const root = await createTestTempDirectory("rea-dtb-empty-strings-");
|
||||
const path = join(root, "board.dtb");
|
||||
await writeFile(path, emptyStringsAtReservationBoundaryFixture(version));
|
||||
const result = await cli.run({
|
||||
arguments: ["inspect-devicetree", path, "--json"],
|
||||
});
|
||||
expect(result.exitCode, result.stderr).toBe(0);
|
||||
const report = toolContract("inspect_devicetree").outputSchema.parse(
|
||||
result.json,
|
||||
).normalized_result;
|
||||
expect(report).toMatchObject({
|
||||
nodes: [{ path: "/" }],
|
||||
reservations: [],
|
||||
});
|
||||
for (const offset of [0, 44, 56, 60, 72]) {
|
||||
const path = join(root, `board-${String(offset)}.dtb`);
|
||||
const bytes = emptyStringsAtReservationBoundaryFixture(version);
|
||||
bytes.writeUInt32BE(offset, 12);
|
||||
await writeFile(path, bytes);
|
||||
const result = await cli.run({
|
||||
arguments: ["inspect-devicetree", path, "--json"],
|
||||
});
|
||||
expect(result.exitCode, result.stderr).toBe(0);
|
||||
const report = toolContract("inspect_devicetree").outputSchema.parse(
|
||||
result.json,
|
||||
).normalized_result;
|
||||
expect(report).toMatchObject({
|
||||
nodes: [{ path: "/" }],
|
||||
reservations: [],
|
||||
});
|
||||
expect(Buffer.compare(await readFile(path), bytes)).toBe(0);
|
||||
}
|
||||
},
|
||||
);
|
||||
}
|
||||
|
||||
Reference in new issue
Block a user