import { IEmscriptenWrapper } from "../emscripten/i-emscripten-wrapper.js";
import type { IWorkerPoolBindings } from "./i-worker-pool-bindings.js";
import { type IManagedObject, type IManagedResourceNode, type IPointer } from "../../lifecycle/manged-resources.js";
/**
 * @public
 * How to handle jobs which don't "overflow", i.e. the workers cannot keep up with the work being sent.
 */
export declare enum EWorkerPoolOverflowMode {
    /**
     * Delete the job and then throw a {@link NestedError} with a cause of {@link WorkerPoolErrorCause.overflow}.
     * @remarks This is intended mainly for unit tests.
     * @remarks Ownership of the job is transferred to the job queue.
     */
    Throw = 1,
    /**
     * If no worker is able to accept the job, the job runs on the producer (caller) thread. This automatically
     * "fixes" backpressure by throttling the caller thread. This will result in degraded performance on the producer thread
     * (often the UI thread) which is not always desirable.
     * @remarks {@link IWorkerPool.addJob} will return false where the job ran synchronously.
     * @remarks Ownership of the job is transferred to the job queue.
     */
    Synchronous = 2,
    /**
     * Do nothing, it's up to you to choose an action.
     * @remarks {@link IWorkerPool.addJob} will return false where the job did not run.
     * @remarks Ownership of the job is NOT transferred to the job queue, the caller must clean up.
     */
    Noop = 3
}
/**
 * @public
 * The static members are the cause in {@link INestedError}.
 */
export declare class WorkerPoolErrorCause {
    static readonly overflow = "WorkerPoolErrorCause.overflow";
}
/**
 * @public
 * Configuration for a {@link IWorkerPool}.
 */
export interface IWorkerPoolConfig {
    /**
     * The number of threads in the pool.
     */
    readonly workerCount: number;
    /**
     * The number of jobs each thread can buffer.
     * Tune this in conjunction with the distribution strategy, # of workers and queue size to meet your needs.
     */
    readonly queueSize: number;
    readonly overflowMode?: EWorkerPoolOverflowMode;
}
/**
 * @public
 * A shared pool of web workers to run jobs off the main thread.
 * @remarks The pool should be stopped before being destroyed to avoid deadlocks.
 * @remarks Use the batching system to work out when a particular set of jobs has been completed.
 * @remarks If you know the number of threads you need, use `-sPTHREAD_POOL_SIZE=` to allocate them up front.
 */
export interface IWorkerPool extends IManagedObject, IPointer {
    /**
     * @returns The number of workers that started.
     */
    start(): Promise<number>;
    stop(): Promise<void>;
    isRunning(): boolean;
    /**
     * Transfer unique ownership of the job to the pool. If the pool is running, the job should eventually be run.
     * @remarks The job is deleted on completion.
     */
    addJob(jobPtr: number): boolean;
    /**
     * True if there is any job which has yet to be run. The answer is guaranteed correct on the producer thread.
     */
    hasPendingWork(): boolean;
    /**
     * After adding jobs, you can mark the last job on each worker to track when they have all be completed using {@link IWorkerPool.isBatchDone}.
     */
    setBatchEnd(): void;
    /**
     * This can be polled using {@link promisePoll}.;
     */
    isBatchDone(): boolean;
    /**
     * Cancel any outstanding jobs, does not kill the current job (which must complete first).
     */
    invalidateBatch(): void;
    /**
     * Becomes true once only "valid" jobs are running i.e. all the invalid jobs are gone - use in combination with
     * {@link IWorkerPool.invalidateBatch}.
     */
    areWorkersSynced(): boolean;
}
/**
 * @public
 * {@inheritDoc IWorkerPool}
 */
export declare class WorkerPool implements IWorkerPool {
    private readonly wrapper;
    static createRoundRobin(wrapper: IEmscriptenWrapper<IWorkerPoolBindings>, config: IWorkerPoolConfig, bindToReference: IManagedResourceNode | null, allocationFailThrows: boolean): WorkerPool | null;
    static createRoundRobin(wrapper: IEmscriptenWrapper<IWorkerPoolBindings>, config: IWorkerPoolConfig, bindToReference: IManagedResourceNode | null): IWorkerPool;
    readonly resourceHandle: IManagedResourceNode;
    readonly pointer: number;
    getWrapper(): IEmscriptenWrapper<IWorkerPoolBindings>;
    start(): Promise<number>;
    stop(): Promise<void>;
    isRunning(): boolean;
    isBatchDone(): boolean;
    setBatchEnd(): void;
    invalidateBatch(): void;
    areWorkersSynced(): boolean;
    hasPendingWork(): boolean;
    addJob(jobPtr: number): boolean;
    private readonly overflowMode;
    private readonly cleanup;
}
//# sourceMappingURL=worker-pool.d.ts.map