File RateConverter_core.h¶
FileList > inc > RateConverter > RateConverter_core.h
Go to the source code of this file
Optimal-speed rate conversion cascade. More...
#include "clib_common.h"#include "dp_state.h"#include <complex.h>#include <stddef.h>#include "resamp/resamp_core.h"#include "fir/fir_core.h"
Classes¶
| Type | Name |
|---|---|
| struct | RateConverter_state_t Cascade state owns all sub-stage C objects. |
Public Types¶
| Type | Name |
|---|---|
| enum | rc_stage_t |
Public Functions¶
| Type | Name |
|---|---|
| size_t | RateConverter_convert (double rate, int compensate, const float _Complex * in, size_t n_in, float _Complex * out, size_t max_out) One-shot rate conversion — no persistent state required. |
| RateConverter_state_t * | RateConverter_create (double rate, int compensate) Create a rate converter for the given output/input rate ratio. Selects the cheapest cascade of CIC, HalfbandDecimator, and/or polyphase Resampler stages at construction time (see file header for the selection table). Setting compensate=1 appends a closed-form Molnar-Vucic CIC droop-compensating FIR after any CIC stage, which improves passband flatness at the cost of one extra FIR stage. |
| void | RateConverter_destroy (RateConverter_state_t * s) Free all resources. NULL is a no-op. |
| size_t | RateConverter_execute (RateConverter_state_t * s, const float _Complex * in, size_t n_in, float _Complex * out, size_t max_out) Convert a block of CF32 samples through the cascade. Passes input through each stage in order, ping-ponging between two intermediate buffers. State persists between calls, so contiguous calls on sequential blocks give the same result as one large call. Output length is approximately n_in * rate. |
| size_t | RateConverter_execute_max_out (RateConverter_state_t * s) Upper bound on execute output for a standard 65536-sample block. |
| double | RateConverter_get_rate (const RateConverter_state_t * s) Get / set the output-to-input sample rate ratio. The setter rebuilds the entire cascade (new stage selection, new sub-objects) and resets all filter memories — equivalent to destroying and recreating with the new rate. Setting rate <= 0 is silently ignored. |
| void | RateConverter_get_state (const RateConverter_state_t * s, void * blob) Serialize s's active-stage state intoblob . |
| void | RateConverter_reset (RateConverter_state_t * s) Zero all sub-stage filter memories. Rate, stage count, and stage types are preserved. Processing from a reset state produces the same output as a freshly created converter fed the same input. Use between signal bursts to suppress transient artefacts from prior filter memory. |
| void | RateConverter_set_rate (RateConverter_state_t * s, double rate) Change the rate; rebuilds the cascade and resets all filter state. Silently ignores rate <= 0. |
| int | RateConverter_set_state (RateConverter_state_t * s, const void * blob) Restore active-stage state from blob (same rate). |
| int | RateConverter_stage_label (RateConverter_state_t * s, int i, char * buf, size_t len) Write a human-readable label for stage i into buf. |
| size_t | RateConverter_state_bytes (const RateConverter_state_t * s) Bytes RateConverter_get_state() writes for s (envelope + stages). |
Macros¶
| Type | Name |
|---|---|
| define | RC_MAX_STAGES 3 |
| define | RC_STATE_MAGIC [**DP\_FOURCC**](dp__state_8h.md#define-dp_fourcc) ('R', 'C', 'V', 'T') |
| define | RC_STATE_VERSION 1u |
Detailed Description¶
Selects the cheapest cascade of CIC, HalfbandDecimator, and/or polyphase Resampler stages for a given output/input sample rate ratio at creation time. All sub-stage C objects are owned by the state struct.
Stage selection (D = 1/rate):
rate >= 1.0 or D < 2 [Resampler(rate)] D ~= 2^1 [HalfbandDecimator] D ~= 2^2 [HalfbandDecimator, HalfbandDecimator] D ~= 2^n, n>=3, D<=4096 [CIC(D)] D >= 8, non-power-of-2 [CIC(R*), Resampler correction] R* = nearest power-of-2 to D otherwise (2 <= D < 8, non-int) [Resampler(rate)]
Lifecycle:
RateConverter_state_t *rc = RateConverter_create(0.1, 0);
// rc->n_stages == 2: CIC(8) then Resampler(0.8)
float _Complex out[512];
size_t n = RateConverter_execute(rc, in, 4096, out, 512);
RateConverter_destroy(rc);
Public Types Documentation¶
enum rc_stage_t¶
Stage type tags.
Public Functions Documentation¶
function RateConverter_convert¶
One-shot rate conversion — no persistent state required.
size_t RateConverter_convert (
double rate,
int compensate,
const float _Complex * in,
size_t n_in,
float _Complex * out,
size_t max_out
)
Creates a temporary converter, converts n_in samples, destroys it. Equivalent to:
RateConverter_state_t *rc = RateConverter_create(rate, compensate);
size_t n = RateConverter_execute(rc, in, n_in, out, max_out);
RateConverter_destroy(rc);
Use RateConverter_create() directly when processing multiple blocks at the same rate — the one-shot form resets filter memory on every call.
Parameters:
rateOutput-to-input sample rate ratio.compensateNon-zero to enable CIC droop compensation.inCF32 input samples.n_inNumber of input samples.outOutput buffer.max_outOutput buffer capacity in samples.
Returns:
Number of output samples written; 0 only if OOM or n_in == 0.
function RateConverter_create¶
Create a rate converter for the given output/input rate ratio. Selects the cheapest cascade of CIC, HalfbandDecimator, and/or polyphase Resampler stages at construction time (see file header for the selection table). Setting compensate=1 appends a closed-form Molnar-Vucic CIC droop-compensating FIR after any CIC stage, which improves passband flatness at the cost of one extra FIR stage.
Parameters:
rateOutput-to-input sample rate ratio. Any positive float.compensateNon-zero to append a CIC passband-droop compensating FIR after any CIC stage.
Returns:
Non-NULL on success; NULL if rate <= 0 or OOM.
>>> from doppler.resample import RateConverter
>>> rc = RateConverter(rate=0.5, compensate=0)
>>> rc.rate
0.5
function RateConverter_destroy¶
Free all resources. NULL is a no-op.
function RateConverter_execute¶
Convert a block of CF32 samples through the cascade. Passes input through each stage in order, ping-ponging between two intermediate buffers. State persists between calls, so contiguous calls on sequential blocks give the same result as one large call. Output length is approximately n_in * rate.
size_t RateConverter_execute (
RateConverter_state_t * s,
const float _Complex * in,
size_t n_in,
float _Complex * out,
size_t max_out
)
Parameters:
sPointer to a valid RateConverter_state_t.inCF32 input block.n_inNumber of input samples.outOutput buffer; must hold at least max_out samples.max_outCapacity of out in samples.
Returns:
CF32 output array; length is approximately n_in * rate.
>>> from doppler.resample import RateConverter
>>> import numpy as np
>>> rc = RateConverter(rate=0.5, compensate=0)
>>> y = rc.execute(np.zeros(1024, dtype=np.complex64))
>>> y.shape, y.dtype
((512,), dtype('complex64'))
function RateConverter_execute_max_out¶
Upper bound on execute output for a standard 65536-sample block.
Returns (size_t)(65536 * max(rate, 1.0)) + 2. The Python extension uses this to pre-allocate the output buffer on the first execute call.
function RateConverter_get_rate¶
Get / set the output-to-input sample rate ratio. The setter rebuilds the entire cascade (new stage selection, new sub-objects) and resets all filter memories — equivalent to destroying and recreating with the new rate. Setting rate <= 0 is silently ignored.
>>> from doppler.resample import RateConverter
>>> rc = RateConverter(rate=0.5, compensate=0)
>>> rc.rate
0.5
>>> rc.rate = 2.0
>>> rc.rate
2.0
function RateConverter_get_state¶
Serialize s's active-stage state intoblob .
function RateConverter_reset¶
Zero all sub-stage filter memories. Rate, stage count, and stage types are preserved. Processing from a reset state produces the same output as a freshly created converter fed the same input. Use between signal bursts to suppress transient artefacts from prior filter memory.
>>> from doppler.resample import RateConverter
>>> rc = RateConverter(rate=0.5, compensate=0)
>>> rc.reset()
>>> rc.rate
0.5
function RateConverter_set_rate¶
Change the rate; rebuilds the cascade and resets all filter state. Silently ignores rate <= 0.
Parameters:
sPointer to a valid RateConverter_state_t.rateNew output/input rate ratio.
function RateConverter_set_state¶
Restore active-stage state from blob (same rate).
Returns:
DP_OK, or DP_ERR_INVALID if the blob's envelope rejects.
function RateConverter_stage_label¶
Write a human-readable label for stage i into buf.
Examples: "HalfbandDecimator", "CIC(8)", "CIC(8)+FIR", "Resampler(0.8)".
Parameters:
sMust be non-NULL.iStage index in[0, s->n_stages).bufOutput buffer.lenCapacity of buf in bytes.
Returns:
1 on success, 0 if i is out of range.
function RateConverter_state_bytes¶
Bytes RateConverter_get_state() writes fors (envelope + stages).
Macro Definition Documentation¶
define RC_MAX_STAGES¶
Maximum number of visible cascade stages.
define RC_STATE_MAGIC¶
define RC_STATE_VERSION¶
The documentation for this class was generated from the following file native/inc/RateConverter/RateConverter_core.h