Skip to content

Commit

Permalink
store processors in dedicated object
Browse files Browse the repository at this point in the history
  • Loading branch information
b-ma committed May 13, 2024
1 parent d528460 commit 931d059
Show file tree
Hide file tree
Showing 2 changed files with 14 additions and 11 deletions.
9 changes: 5 additions & 4 deletions js/AudioWorkletGlobalScope.js
Original file line number Diff line number Diff line change
Expand Up @@ -24,6 +24,7 @@ const kWorkletParamsCache = Symbol.for('node-web-audio-api:worklet-params-cache'
// const kWorkletOrderedParamNames = Symbol.for('node-web-audio-api:worklet-ordered-param-names');

const nameProcessorCtorMap = new Map();
const processors = {};
let pendingProcessorConstructionData = null;
let loopStarted = false;
let runLoopImmediateId = null;
Expand All @@ -48,7 +49,7 @@ function isConstructor(f) {

function runLoop() {
// block until we need to render a quantum
run_audio_worklet_global_scope(workletId);
run_audio_worklet_global_scope(workletId, processors);
// yield to the event loop, and then repeat
runLoopImmediateId = setImmediate(runLoop);
}
Expand Down Expand Up @@ -242,13 +243,13 @@ parentPort.on('message', event => {

switch (event.cmd) {
case 'node-web-audio-api:worklet:init': {
const { workletId, promiseId } = event;
const { workletId, processors, promiseId } = event;
break;
}
case 'node-web-audio-api:worklet:exit': {
clearImmediate(runLoopImmediateId);
// properly exit audio worklet on rust side
exit_audio_worklet_global_scope(workletId);
exit_audio_worklet_global_scope(workletId, processors);
// exit process
process.exit(0);
break;
Expand Down Expand Up @@ -288,7 +289,7 @@ parentPort.on('message', event => {
pendingProcessorConstructionData = null;
// store in global so that Rust can match the JS processor
// with its corresponding NapiAudioWorkletProcessor
globalThis[`${id}`] = instance;
processors[`${id}`] = instance;

if (!loopStarted) {
loopStarted = true;
Expand Down
16 changes: 9 additions & 7 deletions src/audio_worklet_node.rs
Original file line number Diff line number Diff line change
Expand Up @@ -137,7 +137,7 @@ struct WorkletAbruptCompletionResult {
}

/// Handle a AudioWorkletProcessor::process call in the Worker
fn process_audio_worklet(env: &Env, args: ProcessorArguments) -> Result<()> {
fn process_audio_worklet(env: &Env, processors: &JsObject, args: ProcessorArguments) -> Result<()> {
let ProcessorArguments {
id,
inputs,
Expand All @@ -148,8 +148,7 @@ fn process_audio_worklet(env: &Env, args: ProcessorArguments) -> Result<()> {
tail_time_sender,
} = args;

let mut global = env.get_global()?;
let processor = global.get_named_property::<JsUnknown>(&id.to_string())?;
let processor = processors.get_named_property::<JsUnknown>(&id.to_string())?;

// Make sure the processor exists, might run into race conditions
// between Rust Audio thread and JS Worker thread
Expand All @@ -159,6 +158,7 @@ fn process_audio_worklet(env: &Env, args: ProcessorArguments) -> Result<()> {
}

// fill AudioWorkletGlobalScope
let mut global = env.get_global()?;
global.set_named_property("currentTime", current_time)?;
global.set_named_property("currentFrame", current_frame)?;

Expand Down Expand Up @@ -290,7 +290,7 @@ fn process_audio_worklet(env: &Env, args: ProcessorArguments) -> Result<()> {
}

/// The entry point into Rust from the Worker
#[js_function(1)]
#[js_function(2)]
pub(crate) fn run_audio_worklet_global_scope(ctx: CallContext) -> Result<JsUndefined> {
// Set thread priority to highest, if not done already
if !HAS_THREAD_PRIO.replace(true) {
Expand All @@ -300,6 +300,8 @@ pub(crate) fn run_audio_worklet_global_scope(ctx: CallContext) -> Result<JsUndef

// Obtain the unique worker ID
let worklet_id = ctx.get::<JsNumber>(0)?.get_uint32()? as usize;
// List of registered processors
let processors = ctx.get::<JsObject>(1)?;

// Wait for an incoming command, the recv_timeout is required for OfflineAudioContext
// as we have no way to exit the worklet before the graph is dropped, so the worlet
Expand All @@ -311,11 +313,11 @@ pub(crate) fn run_audio_worklet_global_scope(ctx: CallContext) -> Result<JsUndef
{
match msg {
WorkletCommand::Drop(id) => {
let mut global = ctx.env.get_global()?;
global.delete_named_property(&id.to_string()).unwrap();
let mut processors = ctx.get::<JsObject>(1)?;
processors.delete_named_property(&id.to_string()).unwrap();
}
WorkletCommand::Process(args) => {
process_audio_worklet(ctx.env, args)?;
process_audio_worklet(ctx.env, &processors, args)?;
}
}
}
Expand Down

0 comments on commit 931d059

Please sign in to comment.