Documentation
¶
Index ¶
- Constants
- Variables
- func IsSystemFiltered(err error) bool
- type AmbiguityResolutionProcessor
- type CodePriorityProvider
- type CorrectionApplicationProcessor
- type EKFProcessor
- type EKFState
- type ElevationMaskProcessor
- type EphemerisProcessor
- type GeometryFreeProcessor
- type GeometryProcessor
- type IonosphereFreeProcessor
- type MelbourneWubbenaProcessor
- type NarrowLaneProcessor
- type NiellModel
- type PhaseWindupProcessor
- type PositionProcessor
- type PreciseProductProcessor
- type PreciseProductProvider
- type SaastamoinenModel
- type SagnacProcessor
- type StanagModel
- type SystemFilterProcessor
- type TroposphereModel
- type TroposphereProcessor
- type WideLaneProcessor
Constants ¶
const (
// AngularVelocity is the angular velocity of the Earth in rad/s
AngularVelocity = 7.2921151467e-5
)
Variables ¶
var ErrSystemFiltered = errors.New("system filtered")
ErrSystemFiltered is returned when a satellite is filtered out by system. This is an expected condition, not an error, so it should be logged at DEBUG level.
Functions ¶
func IsSystemFiltered ¶ added in v0.33.0
IsSystemFiltered checks if an error is from system filtering.
Types ¶
type AmbiguityResolutionProcessor ¶
type AmbiguityResolutionProcessor struct {
// contains filtered or unexported fields
}
AmbiguityResolutionProcessor handles integer ambiguity resolution for PPP-AR
func NewAmbiguityResolutionProcessor ¶
func NewAmbiguityResolutionProcessor(enabled bool, minRatio float64, minSatellites int, validationMethod string) *AmbiguityResolutionProcessor
NewAmbiguityResolutionProcessor creates a new ambiguity resolution processor
func (*AmbiguityResolutionProcessor) IsEnabled ¶
func (a *AmbiguityResolutionProcessor) IsEnabled() bool
IsEnabled returns whether ambiguity resolution is enabled
func (*AmbiguityResolutionProcessor) Name ¶
func (a *AmbiguityResolutionProcessor) Name() string
Name returns the processor name
func (*AmbiguityResolutionProcessor) Process ¶
func (a *AmbiguityResolutionProcessor) Process(ctx context.Context, state *pipeline.SatelliteState) error
Process performs ambiguity resolution on the satellite state
func (*AmbiguityResolutionProcessor) SetEnabled ¶
func (a *AmbiguityResolutionProcessor) SetEnabled(enabled bool)
SetEnabled enables or disables ambiguity resolution
type CodePriorityProvider ¶ added in v0.33.0
type CodePriorityProvider interface {
GetSignalTypePriorities(system gnss.System, satelliteID observation.SatelliteID) map[observation.SignalType]int
}
CodePriorityProvider is an interface for getting signal type priorities for a satellite. This avoids import cycles by not directly importing the config package.
type CorrectionApplicationProcessor ¶ added in v0.33.0
type CorrectionApplicationProcessor struct {
// contains filtered or unexported fields
}
CorrectionApplicationProcessor applies calculated corrections to pseudorange observations.
Purpose ¶
In GNSS positioning, measured pseudoranges contain several systematic errors that must be removed before computing position. This processor applies corrections for:
- Satellite clock bias (removes satellite clock offset from GPS time)
- Tropospheric delay (removes atmospheric path delay)
- Sagnac effect (corrects for Earth rotation during signal travel)
Pipeline Position ¶
This processor MUST be placed in the pipeline:
- AFTER correction calculation processors (TroposphereProcessor, SagnacProcessor, etc.)
- BEFORE linear combination processors (IonosphereFreeProcessor, WideLaneProcessor, etc.)
This ensures that:
- Raw observations are corrected once in a centralized location
- All downstream processors (combinations, positioning algorithms) use corrected pseudoranges
- The correction logic doesn't need to be duplicated in multiple places
GNSS Observation Equation ¶
The measured pseudorange contains:
Measured_Range = True_Range + c*dt_receiver - c*dt_satellite + Troposphere_Delay - Sagnac + Noise
To recover the geometric range for positioning:
Corrected_Range = Measured_Range + c*dt_satellite - Troposphere_Delay + Sagnac
Where:
- dt_satellite = satellite clock bias + relativistic correction (seconds)
- Troposphere_Delay = atmospheric path delay (always positive, meters)
- Sagnac = Earth rotation effect (can be ±, meters)
- c = speed of light (299,792,458 m/s)
Sign Conventions ¶
Satellite clock (dt_sat): If satellite clock is FAST (positive bias), the timestamp is early, making measured range too SHORT. Therefore ADD c*dt_sat to correct.
Troposphere: Always LENGTHENS the apparent range. SUBTRACT to get geometric range.
Sagnac: Can be positive or negative depending on geometry. ADD to correct.
Important Notes ¶
- This processor modifies observations IN-PLACE. Original raw values are not preserved.
- Only pseudorange (Range field) is corrected. Phase observations are not modified.
- Phase corrections would require different handling (opposite ionosphere sign, phase windup, etc.)
- Receiver clock offset remains in the corrected pseudoranges (solved for in positioning)
Example Usage ¶
In config/builder.go:
// After correction processors procs = append(procs, troposphereProcessor, sagnacProcessor) // Apply corrections (this processor) procs = append(procs, NewCorrectionApplicationProcessor(true)) // Before combination processors procs = append(procs, ionosphereFreeProcessor)
func NewCorrectionApplicationProcessor ¶ added in v0.33.0
func NewCorrectionApplicationProcessor(enabled bool) *CorrectionApplicationProcessor
NewCorrectionApplicationProcessor creates a new correction application processor.
func (*CorrectionApplicationProcessor) IsEnabled ¶ added in v0.33.0
func (p *CorrectionApplicationProcessor) IsEnabled() bool
IsEnabled returns whether the processor is currently enabled.
func (*CorrectionApplicationProcessor) Name ¶ added in v0.33.0
func (p *CorrectionApplicationProcessor) Name() string
Name returns the processor name.
func (*CorrectionApplicationProcessor) Process ¶ added in v0.33.0
func (p *CorrectionApplicationProcessor) Process(ctx context.Context, state *pipeline.SatelliteState) error
Process applies all available corrections to the observations.
func (*CorrectionApplicationProcessor) SetEnabled ¶ added in v0.33.0
func (p *CorrectionApplicationProcessor) SetEnabled(enabled bool)
SetEnabled allows toggling the processor on/off at runtime.
type EKFProcessor ¶
type EKFProcessor struct {
// contains filtered or unexported fields
}
EKFProcessor implements Extended Kalman Filter for PPP-AR positioning
func NewEKFProcessor ¶
func NewEKFProcessor(initialPosition coordinates.Vector3D) *EKFProcessor
NewEKFProcessor creates a new EKF processor
func (*EKFProcessor) GetState ¶
func (e *EKFProcessor) GetState() *EKFState
GetState returns the current EKF state
func (*EKFProcessor) Process ¶
func (e *EKFProcessor) Process(ctx context.Context, state *pipeline.SatelliteState) error
Process performs EKF prediction and update steps
func (*EKFProcessor) SetState ¶
func (e *EKFProcessor) SetState(state *EKFState)
SetState sets the EKF state
type EKFState ¶
type EKFState struct {
// Position and velocity states
Position coordinates.Vector3D
Velocity coordinates.Vector3D
// Clock states (per system)
Clocks map[gnss.System]float64
// Troposphere states
TroposphereZWD float64
TroposphereGrad [2]float64 // North, East gradients
// Ambiguity states (per satellite-signal pair)
Ambiguities map[string]float64 // Key: "system_satID_signal"
// Covariance matrix (simplified for now)
Covariance map[string]map[string]float64
}
EKFState represents the state of the Extended Kalman Filter
type ElevationMaskProcessor ¶
type ElevationMaskProcessor struct {
// contains filtered or unexported fields
}
ElevationMaskProcessor checks if satellites are above the elevation mask. Satellites below the mask are marked in the quality indicators.
func NewElevationMaskProcessor ¶
func NewElevationMaskProcessor(masks map[gnss.System]float64) *ElevationMaskProcessor
NewElevationMaskProcessor creates a new elevation mask processor. The masks map specifies the minimum elevation angle for each GNSS system.
func (*ElevationMaskProcessor) Name ¶
func (p *ElevationMaskProcessor) Name() string
Name returns the processor name.
func (*ElevationMaskProcessor) Process ¶
func (p *ElevationMaskProcessor) Process(ctx context.Context, state *pipeline.SatelliteState) error
Process checks if the satellite is above the elevation mask for its system. If geometry is not available (e.g., when a priori coordinates are zero), the elevation mask check is skipped and the satellite is not marked as masked. This allows initial position solutions to proceed without elevation filtering.
type EphemerisProcessor ¶
type EphemerisProcessor struct {
// contains filtered or unexported fields
}
EphemerisProcessor attaches ephemeris data to satellite state. It looks up the closest ephemeris message in time from the provided store.
func NewEphemerisProcessor ¶
func NewEphemerisProcessor(store *ephemeris.EphemerisStore) *EphemerisProcessor
NewEphemerisProcessor creates a new ephemeris processor with the given store.
func (*EphemerisProcessor) Name ¶
func (p *EphemerisProcessor) Name() string
Name returns the processor name for logging and error messages.
func (*EphemerisProcessor) Process ¶
func (p *EphemerisProcessor) Process(ctx context.Context, state *pipeline.SatelliteState) error
Process looks up and attaches ephemeris to the satellite state.
type GeometryFreeProcessor ¶
type GeometryFreeProcessor struct {
// contains filtered or unexported fields
}
GeometryFreeProcessor calculates the geometry-free linear combination. This combination removes geometric range, leaving only dispersive effects.
func NewGeometryFreeProcessor ¶
func NewGeometryFreeProcessor(enabled bool) *GeometryFreeProcessor
NewGeometryFreeProcessor creates a new geometry-free combination processor.
func (*GeometryFreeProcessor) Name ¶
func (p *GeometryFreeProcessor) Name() string
Name returns the processor name.
func (*GeometryFreeProcessor) Process ¶
func (p *GeometryFreeProcessor) Process(ctx context.Context, state *pipeline.SatelliteState) error
Process calculates the geometry-free combination.
type GeometryProcessor ¶
type GeometryProcessor struct {
// contains filtered or unexported fields
}
GeometryProcessor calculates azimuth, elevation, and geometric range from receiver to satellite.
func NewGeometryProcessor ¶
func NewGeometryProcessor(receiverPos coordinates.Vector3D) *GeometryProcessor
NewGeometryProcessor creates a new geometry processor. The receiver position should be in ECEF coordinates (meters).
func (*GeometryProcessor) Name ¶
func (p *GeometryProcessor) Name() string
Name returns the processor name.
func (*GeometryProcessor) Process ¶
func (p *GeometryProcessor) Process(ctx context.Context, state *pipeline.SatelliteState) error
Process calculates the geometric relationship between receiver and satellite.
func (*GeometryProcessor) SetReceiverPosition ¶
func (p *GeometryProcessor) SetReceiverPosition(pos coordinates.Vector3D)
SetReceiverPosition updates the receiver position. This is useful when the receiver position is refined during processing.
type IonosphereFreeProcessor ¶
type IonosphereFreeProcessor struct {
// contains filtered or unexported fields
}
IonosphereFreeProcessor calculates the ionosphere-free linear combination. This requires dual-frequency observations.
func NewIonosphereFreeProcessor ¶
func NewIonosphereFreeProcessor(enabled bool) *IonosphereFreeProcessor
NewIonosphereFreeProcessor creates a new ionosphere-free combination processor.
func NewIonosphereFreeProcessorWithPriorities ¶ added in v0.33.0
func NewIonosphereFreeProcessorWithPriorities(enabled bool, priorityProvider CodePriorityProvider) *IonosphereFreeProcessor
NewIonosphereFreeProcessorWithPriorities creates a new ionosphere-free combination processor with code priorities.
func (*IonosphereFreeProcessor) Name ¶
func (p *IonosphereFreeProcessor) Name() string
Name returns the processor name.
func (*IonosphereFreeProcessor) Process ¶
func (p *IonosphereFreeProcessor) Process(ctx context.Context, state *pipeline.SatelliteState) error
Process calculates the ionosphere-free combination.
type MelbourneWubbenaProcessor ¶
type MelbourneWubbenaProcessor struct {
// contains filtered or unexported fields
}
MelbourneWubbenaProcessor calculates the Melbourne-Wübbena combination. This is useful for cycle slip detection.
func NewMelbourneWubbenaProcessor ¶
func NewMelbourneWubbenaProcessor(enabled bool) *MelbourneWubbenaProcessor
NewMelbourneWubbenaProcessor creates a new Melbourne-Wübbena processor.
func (*MelbourneWubbenaProcessor) Name ¶
func (p *MelbourneWubbenaProcessor) Name() string
Name returns the processor name.
func (*MelbourneWubbenaProcessor) Process ¶
func (p *MelbourneWubbenaProcessor) Process(ctx context.Context, state *pipeline.SatelliteState) error
Process calculates the Melbourne-Wübbena combination. Uses the same frequency band selection as IonosphereFreeProcessor for consistency.
type NarrowLaneProcessor ¶
type NarrowLaneProcessor struct {
// contains filtered or unexported fields
}
NarrowLaneProcessor calculates the narrow-lane linear combination.
func NewNarrowLaneProcessor ¶
func NewNarrowLaneProcessor(enabled bool) *NarrowLaneProcessor
NewNarrowLaneProcessor creates a new narrow-lane combination processor.
func (*NarrowLaneProcessor) Name ¶
func (p *NarrowLaneProcessor) Name() string
Name returns the processor name.
func (*NarrowLaneProcessor) Process ¶
func (p *NarrowLaneProcessor) Process(ctx context.Context, state *pipeline.SatelliteState) error
Process calculates the narrow-lane combination.
type NiellModel ¶
type NiellModel struct{}
NiellModel implements the Niell tropospheric model.
func (*NiellModel) Compute ¶
func (m *NiellModel) Compute(elevation, latitude, altitude, doy float64) float64
type PhaseWindupProcessor ¶
type PhaseWindupProcessor struct {
// contains filtered or unexported fields
}
PhaseWindupProcessor calculates carrier phase windup correction. Phase windup occurs due to the relative orientation of satellite and receiver antennas. This is a placeholder implementation - full implementation requires tracking previous state.
func NewPhaseWindupProcessor ¶
func NewPhaseWindupProcessor(enabled bool) *PhaseWindupProcessor
NewPhaseWindupProcessor creates a new phase windup processor.
func (*PhaseWindupProcessor) IsEnabled ¶
func (p *PhaseWindupProcessor) IsEnabled() bool
IsEnabled returns whether the processor is currently enabled.
func (*PhaseWindupProcessor) Name ¶
func (p *PhaseWindupProcessor) Name() string
Name returns the processor name.
func (*PhaseWindupProcessor) Process ¶
func (p *PhaseWindupProcessor) Process(ctx context.Context, state *pipeline.SatelliteState) error
Process calculates the phase windup correction.
func (*PhaseWindupProcessor) SetEnabled ¶
func (p *PhaseWindupProcessor) SetEnabled(enabled bool)
SetEnabled allows toggling the processor on/off at runtime.
type PositionProcessor ¶
type PositionProcessor struct {
// contains filtered or unexported fields
}
PositionProcessor calculates satellite position and clock from ephemeris. It requires ephemeris to be already attached to the satellite state.
func NewPositionProcessor ¶
func NewPositionProcessor(useTransmissionTime bool) *PositionProcessor
NewPositionProcessor creates a new position processor. If useTransmissionTime is true, it will compute position at signal transmission time. Otherwise, it uses the signal reception time (epoch time).
func (*PositionProcessor) Name ¶
func (p *PositionProcessor) Name() string
Name returns the processor name.
func (*PositionProcessor) Process ¶
func (p *PositionProcessor) Process(ctx context.Context, state *pipeline.SatelliteState) error
Process computes the satellite position and clock offset.
type PreciseProductProcessor ¶
type PreciseProductProcessor struct {
// contains filtered or unexported fields
}
PreciseProductProcessor attaches precise orbit and clock corrections to satellite states
func NewPreciseProductProcessor ¶
func NewPreciseProductProcessor(provider PreciseProductProvider) *PreciseProductProcessor
NewPreciseProductProcessor creates a new precise product processor
func (*PreciseProductProcessor) Name ¶
func (p *PreciseProductProcessor) Name() string
Name returns the processor name
func (*PreciseProductProcessor) Process ¶
func (p *PreciseProductProcessor) Process(ctx context.Context, state *pipeline.SatelliteState) error
Process attaches precise orbit and clock corrections to the satellite state
type PreciseProductProvider ¶
type PreciseProductProvider interface {
GetOrbitRecord(system gnss.System, satID observation.SatelliteID, t time.Time) (*precise.OrbitRecord, error)
GetClockRecord(system gnss.System, satID observation.SatelliteID, t time.Time) (*precise.ClockRecord, error)
GetTimeRange() (time.Time, time.Time)
}
PreciseProductProvider interface for accessing precise products
type SaastamoinenModel ¶
type SaastamoinenModel struct{}
SaastamoinenModel implements the Saastamoinen tropospheric model.
func (*SaastamoinenModel) Compute ¶
func (m *SaastamoinenModel) Compute(elevation, latitude, altitude, doy float64) float64
type SagnacProcessor ¶
type SagnacProcessor struct {
// contains filtered or unexported fields
}
SagnacProcessor calculates the Sagnac effect correction. This accounts for Earth's rotation during signal propagation.
func NewSagnacProcessor ¶
func NewSagnacProcessor(receiverPos coordinates.Vector3D, enabled bool) *SagnacProcessor
NewSagnacProcessor creates a new Sagnac correction processor.
func (*SagnacProcessor) IsEnabled ¶
func (p *SagnacProcessor) IsEnabled() bool
IsEnabled returns whether the processor is currently enabled.
func (*SagnacProcessor) Name ¶
func (p *SagnacProcessor) Name() string
Name returns the processor name.
func (*SagnacProcessor) Process ¶
func (p *SagnacProcessor) Process(ctx context.Context, state *pipeline.SatelliteState) error
Process calculates the Sagnac correction.
func (*SagnacProcessor) SetEnabled ¶
func (p *SagnacProcessor) SetEnabled(enabled bool)
SetEnabled allows toggling the processor on/off at runtime.
type StanagModel ¶
type StanagModel struct{}
StanagModel implements the STANAG tropospheric model.
func (*StanagModel) Compute ¶
func (m *StanagModel) Compute(elevation, latitude, altitude, doy float64) float64
type SystemFilterProcessor ¶ added in v0.33.0
type SystemFilterProcessor struct {
// contains filtered or unexported fields
}
SystemFilterProcessor filters satellites by GNSS system. Satellites from systems not in the allowed list will be rejected. This processor should be placed early in the pipeline to avoid unnecessary processing of unwanted systems.
func NewSystemFilterProcessor ¶ added in v0.33.0
func NewSystemFilterProcessor(systems []gnss.System) *SystemFilterProcessor
NewSystemFilterProcessor creates a new system filter processor. If systems is empty or nil, all systems are allowed (no filtering).
func (*SystemFilterProcessor) Name ¶ added in v0.33.0
func (p *SystemFilterProcessor) Name() string
Name returns the processor name.
func (*SystemFilterProcessor) Process ¶ added in v0.33.0
func (p *SystemFilterProcessor) Process(ctx context.Context, state *pipeline.SatelliteState) error
Process checks if the satellite's system is in the allowed list. Returns ErrSystemFiltered if the system is not allowed, causing the satellite to be skipped. This is an expected condition and should be logged at DEBUG level, not WARN.
type TroposphereModel ¶
type TroposphereModel interface {
// Compute calculates the tropospheric delay in meters.
// Parameters: elevation (degrees), latitude (radians), altitude (meters), day of year
Compute(elevation, latitude, altitude, doy float64) float64
}
TroposphereModel defines the interface for tropospheric delay models.
type TroposphereProcessor ¶
type TroposphereProcessor struct {
// contains filtered or unexported fields
}
TroposphereProcessor calculates tropospheric delay correction.
func NewTroposphereProcessor ¶
func NewTroposphereProcessor(modelType string, receiverPos coordinates.Vector3D, enabled bool) *TroposphereProcessor
NewTroposphereProcessor creates a new troposphere correction processor. modelType can be "niell", "sasstamoinen", or "stanag". If enabled is false, the processor will skip computation.
func (*TroposphereProcessor) IsEnabled ¶
func (p *TroposphereProcessor) IsEnabled() bool
IsEnabled returns whether the processor is currently enabled.
func (*TroposphereProcessor) Name ¶
func (p *TroposphereProcessor) Name() string
Name returns the processor name.
func (*TroposphereProcessor) Process ¶
func (p *TroposphereProcessor) Process(ctx context.Context, state *pipeline.SatelliteState) error
Process calculates the tropospheric delay.
func (*TroposphereProcessor) SetEnabled ¶
func (p *TroposphereProcessor) SetEnabled(enabled bool)
SetEnabled allows toggling the processor on/off at runtime.
type WideLaneProcessor ¶
type WideLaneProcessor struct {
// contains filtered or unexported fields
}
WideLaneProcessor calculates the wide-lane linear combination.
func NewWideLaneProcessor ¶
func NewWideLaneProcessor(enabled bool) *WideLaneProcessor
NewWideLaneProcessor creates a new wide-lane combination processor.
func (*WideLaneProcessor) Name ¶
func (p *WideLaneProcessor) Name() string
Name returns the processor name.
func (*WideLaneProcessor) Process ¶
func (p *WideLaneProcessor) Process(ctx context.Context, state *pipeline.SatelliteState) error
Process calculates the wide-lane combination.