/** * De-interleaving and sign extension. * * Layer 3. Sole owner of turning record bytes into sample values: the 2- and 3-byte two's * complement expressions exist here and nowhere else in edfcore. * * Bitwise operators appear in this file and are correct here — a sample is 16 or 24 bits, so * `|` and `<<` are exact on it. They are never applied to an OFFSET: a data offset in a * multi-gigabyte BDF routinely exceeds 2^31, where every bitwise operator silently wraps it * negative. Every offset below is plain arithmetic, exact to 2^53. */ import type { EdfHeader, RecordRange } from '../types.js'; /** * The allocation ceiling for a decode that has to allocate. * * A trailing optional argument on functions whose signature is otherwise fixed by the public * API, so passing nothing keeps the documented call shape and the 256 MiB default. */ export interface MaterializeOptions { readonly maxMaterializeBytes?: number; } /** * Samples, plus what was noticed about them on the way past. The out-of-range tally rides along * because the decode loop is already visiting every sample — counting it here costs nothing, * where asking for it afterwards would be a second pass over the whole array. */ export interface DecodedDigital { readonly digital: Int32Array; /** * Samples outside the DECLARED digital range, counted in the same pass that decodes them so * `EdfChunkSignal.outOfDigitalRangeCount` costs nothing. edfcore never clamps: a non-zero * count means the declared range is wrong, not that the samples are. */ readonly outOfDigitalRangeCount: number; } /** * `recordBytes` must be exactly the requested records and nothing else. * * Both halves matter. The range check catches a caller asking for records the file does not * have; the length check catches a buffer that does not start where `records.start` says it * does — which is unrecoverable rather than merely wrong, because nothing in the bytes * identifies which record they came from. */ /** * The header and the record buffer, before either is measured against the other. * * Both decoders answer a size mismatch by stating the file's own geometry — "1 records of 716 bytes * each are exactly 716" — which is the right message and the wrong one to compute from an argument * nobody checked. A recording where the header belongs made it read "of this file is exactly NaN * bytes (1 x undefined)", and an `ArrayBuffer` where the bytes belong made it "recordBytes is * undefined bytes — NaN whole records". Both are sentences about the FILE with arithmetic nonsense * in them, from a caller's wrong argument (fixed in 0.6.122). * * Shared by `decodeAnnotations`, which is the other function that measures a record buffer against a * header and must refuse the same pair in the same words. */ export declare function assertDecodable(header: EdfHeader, recordBytes: Uint8Array, call: string): void; /** * The destination for `sampleCount` samples: `out` when it is large enough, otherwise a fresh * array checked against the budget first. * * A longer `out` is narrowed with `subarray`, which shares its memory — the zero-allocation * path survives — while keeping `result.length` equal to the true sample count, so no caller * can mistake spare capacity for data. */ /** * The KIND of a reused `out` array, which none of the three resolvers that take one checked. * * Every one of them tested the LENGTH and then wrote through it, so an array of the wrong kind * passed. `toPhysical(signal, digital, new Int32Array(n))` is the one that costs data: the * physical values are written into an integer array, which truncates every one of them, and for a * bit value below 1 — which is most EEG channels in microvolts — the result is a buffer of zeros * returned as if it were the signal. Nothing said so. * * The other two return the array they were given, so the caller got back something other than the * `Int32Array` their signatures promise. * * `Object.prototype.toString`, not `instanceof`: a typed array from another realm is still the * right kind, and `a-clone-forgets-the-class.test.ts` is about exactly that distinction. */ export declare function assertOutKind(out: unknown, kind: string, call: string, because: string, subject?: string): void; /** * Decode one signal out of a record range, with the out-of-declared-range tally. * * The count compares against `min`/`max` of the DECLARED digital minimum and maximum rather * than against the pair as written: an inverted declaration (`digitalMinimum > digitalMaximum`) * would otherwise report every sample in the file as out of range, which tells the caller * nothing about the samples. */ export declare function decodeDigitalCounted(header: EdfHeader, recordBytes: Uint8Array, records: RecordRange, signalIndex: number, out?: Int32Array, options?: MaterializeOptions): DecodedDigital; /** * `recordBytes` must be exactly `records.count * header.recordByteLength` bytes and must begin * at record `records.start`; anything else throws `EdfRangeError`. `out` is reused when * supplied and long enough. * * The out-of-range tally reaches callers through `EdfChunkSignal.outOfDigitalRangeCount` — it is the same single * pass, so a caller never needs a second one to produce it. */ export declare function decodeDigital(header: EdfHeader, recordBytes: Uint8Array, records: RecordRange, signalIndex: number, out?: Int32Array, options?: MaterializeOptions): Int32Array; //# sourceMappingURL=digital.d.ts.map