wasm grow and fallback for sla
This commit is contained in:
parent
3255ce7bb7
commit
806c4fb70b
5 changed files with 71 additions and 7 deletions
|
|
@ -20,6 +20,27 @@ function init(worker) {
|
|||
// console.log({ INIT_SLA: worker });
|
||||
}
|
||||
|
||||
export function ensureSLAMemory(required) {
|
||||
let wasm = SLA.wasm;
|
||||
let available = wasm.memory.buffer.byteLength;
|
||||
|
||||
if (available >= required) {
|
||||
return;
|
||||
}
|
||||
|
||||
let page = 65536;
|
||||
let pages = Math.ceil((required - available) / page);
|
||||
try {
|
||||
wasm.memory.grow(pages);
|
||||
} catch (error) {
|
||||
let growError = new Error(`SLA WASM memory grow failed: need ${required} bytes, have ${available} bytes`);
|
||||
growError.code = "SLA_WASM_MEMORY";
|
||||
growError.cause = error;
|
||||
throw growError;
|
||||
}
|
||||
wasm.heap = new Uint8Array(wasm.memory.buffer);
|
||||
}
|
||||
|
||||
// runs in worker. would usually be in src/mode/sla/prepare.js
|
||||
// but the SLA driver skips the prepare step because there is no path routing
|
||||
async function sla_prepare(widgets, settings, update) {
|
||||
|
|
|
|||
|
|
@ -30,9 +30,10 @@ export function renderRasterLayers(print, renderer, onlayer, progress) {
|
|||
let { process, widgets, width, height, scaleX, scaleY, layermax } = ctx;
|
||||
let volume = 0;
|
||||
let count = 0;
|
||||
let useWasm = renderer.renderLayerWasm !== undefined;
|
||||
|
||||
for (let index=0; index<layermax; index++) {
|
||||
let rendered = renderer.renderLayerWasm({
|
||||
let params = {
|
||||
index,
|
||||
width,
|
||||
height,
|
||||
|
|
@ -40,7 +41,22 @@ export function renderRasterLayers(print, renderer, onlayer, progress) {
|
|||
scaleX,
|
||||
scaleY,
|
||||
masks: []
|
||||
});
|
||||
};
|
||||
let rendered;
|
||||
|
||||
if (useWasm) {
|
||||
try {
|
||||
rendered = renderer.renderLayerWasm(params);
|
||||
} catch (error) {
|
||||
if (error.code !== "SLA_WASM_MEMORY" || !renderer.renderLayer) {
|
||||
throw error;
|
||||
}
|
||||
useWasm = false;
|
||||
}
|
||||
}
|
||||
if (!useWasm) {
|
||||
rendered = renderer.renderLayer(params);
|
||||
}
|
||||
if (rendered.end) break;
|
||||
|
||||
volume += rendered.area * process.slaSlice;
|
||||
|
|
|
|||
|
|
@ -1,6 +1,6 @@
|
|||
/** Copyright Stewart Allen <sa@grid.space> -- All Rights Reserved */
|
||||
|
||||
import { SLA } from './init-work.js';
|
||||
import { SLA, ensureSLAMemory } from './init-work.js';
|
||||
|
||||
const default_values = {
|
||||
magic1: 'CXSW3DV2',
|
||||
|
|
@ -394,8 +394,11 @@ CXDLP.render = function(params) {
|
|||
}
|
||||
});
|
||||
|
||||
let wasm = SLA.wasm;
|
||||
let imagelen = width * height;
|
||||
let metadata = 6 + array.reduce((total, poly) => total + polyRecordBytes(poly), 0);
|
||||
ensureSLAMemory(imagelen + metadata + 1024);
|
||||
|
||||
let wasm = SLA.wasm;
|
||||
let writer = new self.DataWriter(new DataView(wasm.memory.buffer), imagelen);
|
||||
writer.writeU16(width, true);
|
||||
writer.writeU16(height, true);
|
||||
|
|
@ -431,3 +434,13 @@ CXDLP.render = function(params) {
|
|||
}
|
||||
return { lines, area };
|
||||
}
|
||||
|
||||
function polyRecordBytes(poly) {
|
||||
let bytes = 14 + poly.points.length * 8;
|
||||
if (poly.inner) {
|
||||
for (let i=0, il=poly.inner.length; i<il; i++) {
|
||||
bytes += polyRecordBytes(poly.inner[i]);
|
||||
}
|
||||
}
|
||||
return bytes;
|
||||
}
|
||||
|
|
|
|||
|
|
@ -1,6 +1,6 @@
|
|||
/** Copyright Stewart Allen <sa@grid.space> -- All Rights Reserved */
|
||||
|
||||
import { SLA } from './init-work.js';
|
||||
import { SLA, ensureSLAMemory } from './init-work.js';
|
||||
|
||||
function generatePhoton(print, conf, progress) {
|
||||
let printset = print.settings,
|
||||
|
|
@ -445,8 +445,12 @@ function renderLayerWasm(params) {
|
|||
}
|
||||
});
|
||||
|
||||
let wasm = SLA.wasm;
|
||||
let imagelen = width * height;
|
||||
let metadata = 6 + array.reduce((total, poly) => total + polyRecordBytes(poly), 0);
|
||||
let rleSpace = masks.length ? imagelen : 0;
|
||||
ensureSLAMemory(imagelen + Math.max(metadata, rleSpace) + 1024);
|
||||
|
||||
let wasm = SLA.wasm;
|
||||
let writer = new self.DataWriter(new DataView(wasm.memory.buffer), imagelen);
|
||||
writer.writeU16(width, true);
|
||||
writer.writeU16(height, true);
|
||||
|
|
@ -471,6 +475,16 @@ function renderLayerWasm(params) {
|
|||
return { image, layers, end: count === 0, area };
|
||||
}
|
||||
|
||||
function polyRecordBytes(poly) {
|
||||
let bytes = 14 + poly.points.length * 8;
|
||||
if (poly.inner) {
|
||||
for (let i=0, il=poly.inner.length; i<il; i++) {
|
||||
bytes += polyRecordBytes(poly.inner[i]);
|
||||
}
|
||||
}
|
||||
return bytes;
|
||||
}
|
||||
|
||||
// legacy JS-only rasterizer uses OffscreenCanvas
|
||||
function renderLayer(params) {
|
||||
let {width, height, index, widgets, scaleX, scaleY} = params;
|
||||
|
|
|
|||
|
|
@ -1,7 +1,7 @@
|
|||
all: kiri-sla.wasm kiri-geo.wasm kiri-ani.wasm
|
||||
|
||||
kiri-sla.wasm: kiri-sla.c
|
||||
emcc --no-entry -o kiri-sla.wasm kiri-sla.c -O3 -s ERROR_ON_UNDEFINED_SYMBOLS=0 -s TOTAL_MEMORY=40mb
|
||||
emcc --no-entry -o kiri-sla.wasm kiri-sla.c -O3 -s ERROR_ON_UNDEFINED_SYMBOLS=0 -s INITIAL_MEMORY=64mb -s ALLOW_MEMORY_GROWTH=1
|
||||
|
||||
kiri-geo.wasm: kiri-geo.cpp
|
||||
emcc --no-entry -o kiri-geo.wasm clipper.cpp kiri-geo.cpp -Oz -s ERROR_ON_UNDEFINED_SYMBOLS=0 -s TOTAL_MEMORY=40mb
|
||||
|
|
|
|||
Loading…
Reference in a new issue