Merge pull request #446 from dpaulat/feature/rda-rpg-build-23.0

Update to RDA/RPG Build 23.0
This commit is contained in:
Dan Paulat 2025-05-17 18:03:02 -05:00 committed by GitHub
commit f08a7d9a8d
No known key found for this signature in database
GPG key ID: B5690EEEBB952194
24 changed files with 2502 additions and 2319 deletions

View file

@ -1460,7 +1460,7 @@ RadarProductManagerImpl::StoreRadarProductRecord(
if (storedRecord != nullptr) if (storedRecord != nullptr)
{ {
logger_->error( logger_->debug(
"Level 2 product previously loaded, loading from cache"); "Level 2 product previously loaded, loading from cache");
} }
} }

View file

@ -1,6 +1,7 @@
#pragma once #pragma once
#include <array> #include <array>
#include <bit>
#include <cstring> #include <cstring>
#include <execution> #include <execution>
#include <istream> #include <istream>
@ -13,12 +14,8 @@
# include <arpa/inet.h> # include <arpa/inet.h>
#endif #endif
namespace scwx namespace scwx::awips
{ {
namespace awips
{
class MessageImpl;
class Message class Message
{ {
@ -56,16 +53,55 @@ public:
static float SwapFloat(float f) static float SwapFloat(float f)
{ {
if constexpr (std::endian::native == std::endian::little)
{
// Variable is initialized by memcpy
// NOLINTNEXTLINE(cppcoreguidelines-init-variables)
std::uint32_t temp; std::uint32_t temp;
std::memcpy(&temp, &f, sizeof(std::uint32_t)); std::memcpy(&temp, &f, sizeof(std::uint32_t));
temp = ntohl(temp); temp = ntohl(temp);
std::memcpy(&f, &temp, sizeof(float)); std::memcpy(&f, &temp, sizeof(float));
}
return f; return f;
} }
template<std::size_t _Size> static double SwapDouble(double d)
static void SwapArray(std::array<float, _Size>& arr, {
std::size_t size = _Size) if constexpr (std::endian::native == std::endian::little)
{
// Variable is initialized by memcpy
// NOLINTNEXTLINE(cppcoreguidelines-init-variables)
std::uint64_t temp;
std::memcpy(&temp, &d, sizeof(std::uint64_t));
temp = Swap64(temp);
std::memcpy(&d, &temp, sizeof(float));
}
return d;
}
static std::uint64_t Swap64(std::uint64_t value)
{
if constexpr (std::endian::native == std::endian::little)
{
// NOLINTBEGIN(cppcoreguidelines-avoid-magic-numbers)
const std::uint32_t high =
ntohl(static_cast<std::uint32_t>(value >> 32));
const std::uint32_t low =
ntohl(static_cast<std::uint32_t>(value & 0xFFFFFFFFULL));
return (static_cast<std::uint64_t>(low) << 32) | high;
// NOLINTEND(cppcoreguidelines-avoid-magic-numbers)
}
else
{
return value;
}
}
template<std::size_t kSize>
static void SwapArray(std::array<float, kSize>& arr,
std::size_t size = kSize)
{
if constexpr (std::endian::native == std::endian::little)
{ {
std::transform(std::execution::par_unseq, std::transform(std::execution::par_unseq,
arr.begin(), arr.begin(),
@ -73,10 +109,13 @@ public:
arr.begin(), arr.begin(),
[](float f) { return SwapFloat(f); }); [](float f) { return SwapFloat(f); });
} }
}
template<std::size_t _Size> template<std::size_t kSize>
static void SwapArray(std::array<std::int16_t, _Size>& arr, static void SwapArray(std::array<std::int16_t, kSize>& arr,
std::size_t size = _Size) std::size_t size = kSize)
{
if constexpr (std::endian::native == std::endian::little)
{ {
std::transform(std::execution::par_unseq, std::transform(std::execution::par_unseq,
arr.begin(), arr.begin(),
@ -84,10 +123,13 @@ public:
arr.begin(), arr.begin(),
[](std::int16_t u) { return ntohs(u); }); [](std::int16_t u) { return ntohs(u); });
} }
}
template<std::size_t _Size> template<std::size_t kSize>
static void SwapArray(std::array<std::uint16_t, _Size>& arr, static void SwapArray(std::array<std::uint16_t, kSize>& arr,
std::size_t size = _Size) std::size_t size = kSize)
{
if constexpr (std::endian::native == std::endian::little)
{ {
std::transform(std::execution::par_unseq, std::transform(std::execution::par_unseq,
arr.begin(), arr.begin(),
@ -95,10 +137,13 @@ public:
arr.begin(), arr.begin(),
[](std::uint16_t u) { return ntohs(u); }); [](std::uint16_t u) { return ntohs(u); });
} }
}
template<std::size_t _Size> template<std::size_t kSize>
static void SwapArray(std::array<std::uint32_t, _Size>& arr, static void SwapArray(std::array<std::uint32_t, kSize>& arr,
std::size_t size = _Size) std::size_t size = kSize)
{
if constexpr (std::endian::native == std::endian::little)
{ {
std::transform(std::execution::par_unseq, std::transform(std::execution::par_unseq,
arr.begin(), arr.begin(),
@ -106,28 +151,67 @@ public:
arr.begin(), arr.begin(),
[](std::uint32_t u) { return ntohl(u); }); [](std::uint32_t u) { return ntohl(u); });
} }
}
template<typename T> template<typename T>
static void SwapMap(std::map<T, float>& m) static void SwapMap(std::map<T, float>& m)
{
if constexpr (std::endian::native == std::endian::little)
{ {
std::for_each(std::execution::par_unseq, std::for_each(std::execution::par_unseq,
m.begin(), m.begin(),
m.end(), m.end(),
[](auto& p) { p.second = SwapFloat(p.second); }); [](auto& p) { p.second = SwapFloat(p.second); });
} }
}
static void SwapVector(std::vector<std::uint16_t>& v) template<typename T>
static void SwapVector(std::vector<T>& v)
{ {
std::transform(std::execution::par_unseq, if constexpr (std::endian::native == std::endian::little)
{
std::transform(
std::execution::par_unseq,
v.begin(), v.begin(),
v.end(), v.end(),
v.begin(), v.begin(),
[](std::uint16_t u) { return ntohs(u); }); [](T u)
{
if constexpr (std::is_same_v<T, std::uint16_t> ||
std::is_same_v<T, std::int16_t>)
{
return static_cast<T>(ntohs(u));
}
else if constexpr (std::is_same_v<T, std::uint32_t> ||
std::is_same_v<T, std::int32_t>)
{
return static_cast<T>(ntohl(u));
}
else if constexpr (std::is_same_v<T, std::uint64_t> ||
std::is_same_v<T, std::int64_t>)
{
return static_cast<T>(Swap64(u));
}
else if constexpr (std::is_same_v<T, float>)
{
return SwapFloat(u);
}
else if constexpr (std::is_same_v<T, double>)
{
return SwapDouble(u);
}
else
{
static_assert(std::is_same_v<T, void>,
"Unsupported type for SwapVector");
}
});
}
} }
private: private:
std::unique_ptr<MessageImpl> p; class Impl;
std::unique_ptr<Impl> p;
}; };
} // namespace awips } // namespace scwx::awips
} // namespace scwx

View file

@ -2,11 +2,7 @@
#include <scwx/wsr88d/rda/generic_radar_data.hpp> #include <scwx/wsr88d/rda/generic_radar_data.hpp>
namespace scwx namespace scwx::wsr88d::rda
{
namespace wsr88d
{
namespace rda
{ {
class DigitalRadarDataGeneric : public GenericRadarData class DigitalRadarDataGeneric : public GenericRadarData
@ -27,30 +23,31 @@ public:
DigitalRadarDataGeneric(DigitalRadarDataGeneric&&) noexcept; DigitalRadarDataGeneric(DigitalRadarDataGeneric&&) noexcept;
DigitalRadarDataGeneric& operator=(DigitalRadarDataGeneric&&) noexcept; DigitalRadarDataGeneric& operator=(DigitalRadarDataGeneric&&) noexcept;
std::string radar_identifier() const; [[nodiscard]] std::string radar_identifier() const;
std::uint32_t collection_time() const; [[nodiscard]] std::uint32_t collection_time() const override;
std::uint16_t modified_julian_date() const; [[nodiscard]] std::uint16_t modified_julian_date() const override;
std::uint16_t azimuth_number() const; [[nodiscard]] std::uint16_t azimuth_number() const override;
units::degrees<float> azimuth_angle() const; [[nodiscard]] units::degrees<float> azimuth_angle() const override;
std::uint8_t compression_indicator() const; [[nodiscard]] std::uint8_t compression_indicator() const;
std::uint16_t radial_length() const; [[nodiscard]] std::uint16_t radial_length() const;
std::uint8_t azimuth_resolution_spacing() const; [[nodiscard]] std::uint8_t azimuth_resolution_spacing() const;
std::uint8_t radial_status() const; [[nodiscard]] std::uint8_t radial_status() const;
std::uint16_t elevation_number() const; [[nodiscard]] std::uint16_t elevation_number() const override;
std::uint8_t cut_sector_number() const; [[nodiscard]] std::uint8_t cut_sector_number() const;
units::degrees<float> elevation_angle() const; [[nodiscard]] units::degrees<float> elevation_angle() const;
std::uint8_t radial_spot_blanking_status() const; [[nodiscard]] std::uint8_t radial_spot_blanking_status() const;
std::uint8_t azimuth_indexing_mode() const; [[nodiscard]] std::uint8_t azimuth_indexing_mode() const;
std::uint16_t data_block_count() const; [[nodiscard]] std::uint16_t data_block_count() const;
std::uint16_t volume_coverage_pattern_number() const; [[nodiscard]] std::uint16_t volume_coverage_pattern_number() const override;
std::shared_ptr<ElevationDataBlock> elevation_data_block() const; [[nodiscard]] std::shared_ptr<ElevationDataBlock>
std::shared_ptr<RadialDataBlock> radial_data_block() const; elevation_data_block() const;
std::shared_ptr<VolumeDataBlock> volume_data_block() const; [[nodiscard]] std::shared_ptr<RadialDataBlock> radial_data_block() const;
std::shared_ptr<GenericRadarData::MomentDataBlock> [[nodiscard]] std::shared_ptr<VolumeDataBlock> volume_data_block() const;
moment_data_block(DataBlockType type) const; [[nodiscard]] std::shared_ptr<GenericRadarData::MomentDataBlock>
moment_data_block(DataBlockType type) const override;
bool Parse(std::istream& is); bool Parse(std::istream& is) override;
static std::shared_ptr<DigitalRadarDataGeneric> static std::shared_ptr<DigitalRadarDataGeneric>
Create(Level2MessageHeader&& header, std::istream& is); Create(Level2MessageHeader&& header, std::istream& is);
@ -65,11 +62,14 @@ class DigitalRadarDataGeneric::DataBlock
protected: protected:
explicit DataBlock(const std::string& dataBlockType, explicit DataBlock(const std::string& dataBlockType,
const std::string& dataName); const std::string& dataName);
public:
virtual ~DataBlock(); virtual ~DataBlock();
DataBlock(const DataBlock&) = delete; DataBlock(const DataBlock&) = delete;
DataBlock& operator=(const DataBlock&) = delete; DataBlock& operator=(const DataBlock&) = delete;
protected:
DataBlock(DataBlock&&) noexcept; DataBlock(DataBlock&&) noexcept;
DataBlock& operator=(DataBlock&&) noexcept; DataBlock& operator=(DataBlock&&) noexcept;
@ -118,17 +118,19 @@ public:
MomentDataBlock(MomentDataBlock&&) noexcept; MomentDataBlock(MomentDataBlock&&) noexcept;
MomentDataBlock& operator=(MomentDataBlock&&) noexcept; MomentDataBlock& operator=(MomentDataBlock&&) noexcept;
std::uint16_t number_of_data_moment_gates() const; [[nodiscard]] std::uint16_t number_of_data_moment_gates() const override;
units::kilometers<float> data_moment_range() const; [[nodiscard]] units::kilometers<float> data_moment_range() const override;
std::int16_t data_moment_range_raw() const; [[nodiscard]] std::int16_t data_moment_range_raw() const override;
units::kilometers<float> data_moment_range_sample_interval() const; [[nodiscard]] units::kilometers<float>
std::uint16_t data_moment_range_sample_interval_raw() const; data_moment_range_sample_interval() const override;
float snr_threshold() const; [[nodiscard]] std::uint16_t
std::int16_t snr_threshold_raw() const; data_moment_range_sample_interval_raw() const override;
std::uint8_t data_word_size() const; [[nodiscard]] float snr_threshold() const;
float scale() const; [[nodiscard]] std::int16_t snr_threshold_raw() const override;
float offset() const; [[nodiscard]] std::uint8_t data_word_size() const override;
const void* data_moments() const; [[nodiscard]] float scale() const override;
[[nodiscard]] float offset() const override;
[[nodiscard]] const void* data_moments() const override;
static std::shared_ptr<MomentDataBlock> static std::shared_ptr<MomentDataBlock>
Create(const std::string& dataBlockType, Create(const std::string& dataBlockType,
@ -155,7 +157,7 @@ public:
RadialDataBlock(RadialDataBlock&&) noexcept; RadialDataBlock(RadialDataBlock&&) noexcept;
RadialDataBlock& operator=(RadialDataBlock&&) noexcept; RadialDataBlock& operator=(RadialDataBlock&&) noexcept;
float unambiguous_range() const; [[nodiscard]] float unambiguous_range() const;
static std::shared_ptr<RadialDataBlock> static std::shared_ptr<RadialDataBlock>
Create(const std::string& dataBlockType, Create(const std::string& dataBlockType,
@ -182,9 +184,9 @@ public:
VolumeDataBlock(VolumeDataBlock&&) noexcept; VolumeDataBlock(VolumeDataBlock&&) noexcept;
VolumeDataBlock& operator=(VolumeDataBlock&&) noexcept; VolumeDataBlock& operator=(VolumeDataBlock&&) noexcept;
float latitude() const; [[nodiscard]] float latitude() const;
float longitude() const; [[nodiscard]] float longitude() const;
std::uint16_t volume_coverage_pattern_number() const; [[nodiscard]] std::uint16_t volume_coverage_pattern_number() const;
static std::shared_ptr<VolumeDataBlock> static std::shared_ptr<VolumeDataBlock>
Create(const std::string& dataBlockType, Create(const std::string& dataBlockType,
@ -198,6 +200,4 @@ private:
bool Parse(std::istream& is); bool Parse(std::istream& is);
}; };
} // namespace rda } // namespace scwx::wsr88d::rda
} // namespace wsr88d
} // namespace scwx

View file

@ -2,28 +2,19 @@
#include <scwx/wsr88d/rda/level2_message.hpp> #include <scwx/wsr88d/rda/level2_message.hpp>
namespace scwx namespace scwx::wsr88d::rda
{
namespace wsr88d
{
namespace rda
{ {
struct Level2MessageInfo struct Level2MessageInfo
{ {
std::shared_ptr<Level2Message> message; std::shared_ptr<Level2Message> message {nullptr};
bool headerValid; bool headerValid {false};
bool messageValid; bool messageValid {false};
Level2MessageInfo() :
message(nullptr), headerValid(false), messageValid(false)
{
}
}; };
class Level2MessageFactory class Level2MessageFactory
{ {
private: public:
explicit Level2MessageFactory() = delete; explicit Level2MessageFactory() = delete;
~Level2MessageFactory() = delete; ~Level2MessageFactory() = delete;
@ -33,7 +24,6 @@ private:
Level2MessageFactory(Level2MessageFactory&&) noexcept = delete; Level2MessageFactory(Level2MessageFactory&&) noexcept = delete;
Level2MessageFactory& operator=(Level2MessageFactory&&) noexcept = delete; Level2MessageFactory& operator=(Level2MessageFactory&&) noexcept = delete;
public:
struct Context; struct Context;
static std::shared_ptr<Context> CreateContext(); static std::shared_ptr<Context> CreateContext();
@ -41,6 +31,4 @@ public:
std::shared_ptr<Context>& ctx); std::shared_ptr<Context>& ctx);
}; };
} // namespace rda } // namespace scwx::wsr88d::rda
} // namespace wsr88d
} // namespace scwx

View file

@ -2,14 +2,8 @@
#include <scwx/wsr88d/rda/level2_message.hpp> #include <scwx/wsr88d/rda/level2_message.hpp>
namespace scwx namespace scwx::wsr88d::rda
{ {
namespace wsr88d
{
namespace rda
{
class PerformanceMaintenanceDataImpl;
class PerformanceMaintenanceData : public Level2Message class PerformanceMaintenanceData : public Level2Message
{ {
@ -24,267 +18,261 @@ public:
PerformanceMaintenanceData(PerformanceMaintenanceData&&) noexcept; PerformanceMaintenanceData(PerformanceMaintenanceData&&) noexcept;
PerformanceMaintenanceData& operator=(PerformanceMaintenanceData&&) noexcept; PerformanceMaintenanceData& operator=(PerformanceMaintenanceData&&) noexcept;
uint16_t loop_back_set_status() const; [[nodiscard]] std::uint16_t loop_back_set_status() const;
uint32_t t1_output_frames() const; [[nodiscard]] std::uint32_t t1_output_frames() const;
uint32_t t1_input_frames() const; [[nodiscard]] std::uint32_t t1_input_frames() const;
uint32_t router_memory_used() const; [[nodiscard]] std::uint32_t router_memory_used() const;
uint32_t router_memory_free() const; [[nodiscard]] std::uint32_t router_memory_free() const;
uint16_t router_memory_utilization() const; [[nodiscard]] std::uint16_t router_memory_utilization() const;
uint16_t route_to_rpg() const; [[nodiscard]] std::uint16_t route_to_rpg() const;
uint32_t csu_loss_of_signal() const; [[nodiscard]] std::uint16_t t1_port_status() const;
uint32_t csu_loss_of_frames() const; [[nodiscard]] std::uint16_t router_dedicated_ethernet_port_status() const;
uint32_t csu_yellow_alarms() const; [[nodiscard]] std::uint16_t router_commercial_ethernet_port_status() const;
uint32_t csu_blue_alarms() const; [[nodiscard]] std::uint32_t csu_24hr_errored_seconds() const;
uint32_t csu_24hr_errored_seconds() const; [[nodiscard]] std::uint32_t csu_24hr_severely_errored_seconds() const;
uint32_t csu_24hr_severely_errored_seconds() const; [[nodiscard]] std::uint32_t
uint32_t csu_24hr_severely_errored_framing_seconds() const; csu_24hr_severely_errored_framing_seconds() const;
uint32_t csu_24hr_unavailable_seconds() const; [[nodiscard]] std::uint32_t csu_24hr_unavailable_seconds() const;
uint32_t csu_24hr_controlled_slip_seconds() const; [[nodiscard]] std::uint32_t csu_24hr_controlled_slip_seconds() const;
uint32_t csu_24hr_path_coding_violations() const; [[nodiscard]] std::uint32_t csu_24hr_path_coding_violations() const;
uint32_t csu_24hr_line_errored_seconds() const; [[nodiscard]] std::uint32_t csu_24hr_line_errored_seconds() const;
uint32_t csu_24hr_bursty_errored_seconds() const; [[nodiscard]] std::uint32_t csu_24hr_bursty_errored_seconds() const;
uint32_t csu_24hr_degraded_minutes() const; [[nodiscard]] std::uint32_t csu_24hr_degraded_minutes() const;
uint32_t lan_switch_cpu_utilization() const; [[nodiscard]] std::uint32_t lan_switch_cpu_utilization() const;
uint16_t lan_switch_memory_utilization() const; [[nodiscard]] std::uint16_t lan_switch_memory_utilization() const;
uint16_t ifdr_chasis_temperature() const; [[nodiscard]] std::uint16_t ifdr_chasis_temperature() const;
uint16_t ifdr_fpga_temperature() const; [[nodiscard]] std::uint16_t ifdr_fpga_temperature() const;
int32_t gps_satellites() const; [[nodiscard]] std::uint16_t ntp_status() const;
uint16_t ipc_status() const; [[nodiscard]] std::uint16_t ipc_status() const;
uint16_t commanded_channel_control() const; [[nodiscard]] std::uint16_t commanded_channel_control() const;
uint16_t polarization() const; [[nodiscard]] std::uint16_t polarization() const;
float ame_internal_temperature() const; [[nodiscard]] float ame_internal_temperature() const;
float ame_receiver_module_temperature() const; [[nodiscard]] float ame_receiver_module_temperature() const;
float ame_bite_cal_module_temperature() const; [[nodiscard]] float ame_bite_cal_module_temperature() const;
uint16_t ame_peltier_pulse_width_modulation() const; [[nodiscard]] std::uint16_t ame_peltier_pulse_width_modulation() const;
uint16_t ame_peltier_status() const; [[nodiscard]] std::uint16_t ame_peltier_status() const;
uint16_t ame_a_d_converter_status() const; [[nodiscard]] std::uint16_t ame_a_d_converter_status() const;
uint16_t ame_state() const; [[nodiscard]] std::uint16_t ame_state() const;
float ame_3_3v_ps_voltage() const; [[nodiscard]] float ame_3_3v_ps_voltage() const;
float ame_5v_ps_voltage() const; [[nodiscard]] float ame_5v_ps_voltage() const;
float ame_6_5v_ps_voltage() const; [[nodiscard]] float ame_6_5v_ps_voltage() const;
float ame_15v_ps_voltage() const; [[nodiscard]] float ame_15v_ps_voltage() const;
float ame_48v_ps_voltage() const; [[nodiscard]] float ame_48v_ps_voltage() const;
float ame_stalo_power() const; [[nodiscard]] float ame_stalo_power() const;
float peltier_current() const; [[nodiscard]] float peltier_current() const;
float adc_calibration_reference_voltage() const; [[nodiscard]] float adc_calibration_reference_voltage() const;
uint16_t ame_mode() const; [[nodiscard]] std::uint16_t ame_mode() const;
uint16_t ame_peltier_mode() const; [[nodiscard]] std::uint16_t ame_peltier_mode() const;
float ame_peltier_inside_fan_current() const; [[nodiscard]] float ame_peltier_inside_fan_current() const;
float ame_peltier_outside_fan_current() const; [[nodiscard]] float ame_peltier_outside_fan_current() const;
float horizontal_tr_limiter_voltage() const; [[nodiscard]] float horizontal_tr_limiter_voltage() const;
float vertical_tr_limiter_voltage() const; [[nodiscard]] float vertical_tr_limiter_voltage() const;
float adc_calibration_offset_voltage() const; [[nodiscard]] float adc_calibration_offset_voltage() const;
float adc_calibration_gain_correction() const; [[nodiscard]] float adc_calibration_gain_correction() const;
uint16_t rcp_status() const; [[nodiscard]] std::uint16_t rcp_status() const;
std::string rcp_string() const; [[nodiscard]] std::string rcp_string() const;
uint16_t spip_power_buttons() const; [[nodiscard]] std::uint16_t spip_power_buttons() const;
float master_power_administrator_load() const; [[nodiscard]] float master_power_administrator_load() const;
float expansion_power_administrator_load() const; [[nodiscard]] float expansion_power_administrator_load() const;
uint16_t _5vdc_ps() const; [[nodiscard]] std::uint16_t _5vdc_ps() const;
uint16_t _15vdc_ps() const; [[nodiscard]] std::uint16_t _15vdc_ps() const;
uint16_t _28vdc_ps() const; [[nodiscard]] std::uint16_t _28vdc_ps() const;
uint16_t neg_15vdc_ps() const; [[nodiscard]] std::uint16_t neg_15vdc_ps() const;
uint16_t _45vdc_ps() const; [[nodiscard]] std::uint16_t _45vdc_ps() const;
uint16_t filament_ps_voltage() const; [[nodiscard]] std::uint16_t filament_ps_voltage() const;
uint16_t vacuum_pump_ps_voltage() const; [[nodiscard]] std::uint16_t vacuum_pump_ps_voltage() const;
uint16_t focus_coil_ps_voltage() const; [[nodiscard]] std::uint16_t focus_coil_ps_voltage() const;
uint16_t filament_ps() const; [[nodiscard]] std::uint16_t filament_ps() const;
uint16_t klystron_warmup() const; [[nodiscard]] std::uint16_t klystron_warmup() const;
uint16_t transmitter_available() const; [[nodiscard]] std::uint16_t transmitter_available() const;
uint16_t wg_switch_position() const; [[nodiscard]] std::uint16_t wg_switch_position() const;
uint16_t wg_pfn_transfer_interlock() const; [[nodiscard]] std::uint16_t wg_pfn_transfer_interlock() const;
uint16_t maintenance_mode() const; [[nodiscard]] std::uint16_t maintenance_mode() const;
uint16_t maintenance_required() const; [[nodiscard]] std::uint16_t maintenance_required() const;
uint16_t pfn_switch_position() const; [[nodiscard]] std::uint16_t pfn_switch_position() const;
uint16_t modulator_overload() const; [[nodiscard]] std::uint16_t modulator_overload() const;
uint16_t modulator_inv_current() const; [[nodiscard]] std::uint16_t modulator_inv_current() const;
uint16_t modulator_switch_fail() const; [[nodiscard]] std::uint16_t modulator_switch_fail() const;
uint16_t main_power_voltage() const; [[nodiscard]] std::uint16_t main_power_voltage() const;
uint16_t charging_system_fail() const; [[nodiscard]] std::uint16_t charging_system_fail() const;
uint16_t inverse_diode_current() const; [[nodiscard]] std::uint16_t inverse_diode_current() const;
uint16_t trigger_amplifier() const; [[nodiscard]] std::uint16_t trigger_amplifier() const;
uint16_t circulator_temperature() const; [[nodiscard]] std::uint16_t circulator_temperature() const;
uint16_t spectrum_filter_pressure() const; [[nodiscard]] std::uint16_t spectrum_filter_pressure() const;
uint16_t wg_arc_vswr() const; [[nodiscard]] std::uint16_t wg_arc_vswr() const;
uint16_t cabinet_interlock() const; [[nodiscard]] std::uint16_t cabinet_interlock() const;
uint16_t cabinet_air_temperature() const; [[nodiscard]] std::uint16_t cabinet_air_temperature() const;
uint16_t cabinet_airflow() const; [[nodiscard]] std::uint16_t cabinet_airflow() const;
uint16_t klystron_current() const; [[nodiscard]] std::uint16_t klystron_current() const;
uint16_t klystron_filament_current() const; [[nodiscard]] std::uint16_t klystron_filament_current() const;
uint16_t klystron_vacion_current() const; [[nodiscard]] std::uint16_t klystron_vacion_current() const;
uint16_t klystron_air_temperature() const; [[nodiscard]] std::uint16_t klystron_air_temperature() const;
uint16_t klystron_airflow() const; [[nodiscard]] std::uint16_t klystron_airflow() const;
uint16_t modulator_switch_maintenance() const; [[nodiscard]] std::uint16_t modulator_switch_maintenance() const;
uint16_t post_charge_regulator_maintenance() const; [[nodiscard]] std::uint16_t post_charge_regulator_maintenance() const;
uint16_t wg_pressure_humidity() const; [[nodiscard]] std::uint16_t wg_pressure_humidity() const;
uint16_t transmitter_overvoltage() const; [[nodiscard]] std::uint16_t transmitter_overvoltage() const;
uint16_t transmitter_overcurrent() const; [[nodiscard]] std::uint16_t transmitter_overcurrent() const;
uint16_t focus_coil_current() const; [[nodiscard]] std::uint16_t focus_coil_current() const;
uint16_t focus_coil_airflow() const; [[nodiscard]] std::uint16_t focus_coil_airflow() const;
uint16_t oil_temperature() const; [[nodiscard]] std::uint16_t oil_temperature() const;
uint16_t prf_limit() const; [[nodiscard]] std::uint16_t prf_limit() const;
uint16_t transmitter_oil_level() const; [[nodiscard]] std::uint16_t transmitter_oil_level() const;
uint16_t transmitter_battery_charging() const; [[nodiscard]] std::uint16_t transmitter_battery_charging() const;
uint16_t high_voltage_status() const; [[nodiscard]] std::uint16_t high_voltage_status() const;
uint16_t transmitter_recycling_summary() const; [[nodiscard]] std::uint16_t transmitter_recycling_summary() const;
uint16_t transmitter_inoperable() const; [[nodiscard]] std::uint16_t transmitter_inoperable() const;
uint16_t transmitter_air_filter() const; [[nodiscard]] std::uint16_t transmitter_air_filter() const;
uint16_t zero_test_bit(unsigned i) const; [[nodiscard]] std::uint16_t zero_test_bit(unsigned i) const;
uint16_t one_test_bit(unsigned i) const; [[nodiscard]] std::uint16_t one_test_bit(unsigned i) const;
uint16_t xmtr_spip_interface() const; [[nodiscard]] std::uint16_t xmtr_spip_interface() const;
uint16_t transmitter_summary_status() const; [[nodiscard]] std::uint16_t transmitter_summary_status() const;
float transmitter_rf_power() const; [[nodiscard]] float transmitter_rf_power() const;
float horizontal_xmtr_peak_power() const; [[nodiscard]] float horizontal_xmtr_peak_power() const;
float xmtr_peak_power() const; [[nodiscard]] float xmtr_peak_power() const;
float vertical_xmtr_peak_power() const; [[nodiscard]] float vertical_xmtr_peak_power() const;
float xmtr_rf_avg_power() const; [[nodiscard]] float xmtr_rf_avg_power() const;
uint32_t xmtr_recycle_count() const; [[nodiscard]] std::uint32_t xmtr_recycle_count() const;
float receiver_bias() const; [[nodiscard]] float receiver_bias() const;
float transmit_imbalance() const; [[nodiscard]] float transmit_imbalance() const;
float xmtr_power_meter_zero() const; [[nodiscard]] float xmtr_power_meter_zero() const;
uint16_t ac_unit1_compressor_shut_off() const; [[nodiscard]] std::uint16_t ac_unit1_compressor_shut_off() const;
uint16_t ac_unit2_compressor_shut_off() const; [[nodiscard]] std::uint16_t ac_unit2_compressor_shut_off() const;
uint16_t generator_maintenance_required() const; [[nodiscard]] std::uint16_t generator_maintenance_required() const;
uint16_t generator_battery_voltage() const; [[nodiscard]] std::uint16_t generator_battery_voltage() const;
uint16_t generator_engine() const; [[nodiscard]] std::uint16_t generator_engine() const;
uint16_t generator_volt_frequency() const; [[nodiscard]] std::uint16_t generator_volt_frequency() const;
uint16_t power_source() const; [[nodiscard]] std::uint16_t power_source() const;
uint16_t transitional_power_source() const; [[nodiscard]] std::uint16_t transitional_power_source() const;
uint16_t generator_auto_run_off_switch() const; [[nodiscard]] std::uint16_t generator_auto_run_off_switch() const;
uint16_t aircraft_hazard_lighting() const; [[nodiscard]] std::uint16_t aircraft_hazard_lighting() const;
uint16_t equipment_shelter_fire_detection_system() const; [[nodiscard]] std::uint16_t equipment_shelter_fire_detection_system() const;
uint16_t equipment_shelter_fire_smoke() const; [[nodiscard]] std::uint16_t equipment_shelter_fire_smoke() const;
uint16_t generator_shelter_fire_smoke() const; [[nodiscard]] std::uint16_t generator_shelter_fire_smoke() const;
uint16_t utility_voltage_frequency() const; [[nodiscard]] std::uint16_t utility_voltage_frequency() const;
uint16_t site_security_alarm() const; [[nodiscard]] std::uint16_t site_security_alarm() const;
uint16_t security_equipment() const; [[nodiscard]] std::uint16_t security_equipment() const;
uint16_t security_system() const; [[nodiscard]] std::uint16_t security_system() const;
uint16_t receiver_connected_to_antenna() const; [[nodiscard]] std::uint16_t receiver_connected_to_antenna() const;
uint16_t radome_hatch() const; [[nodiscard]] std::uint16_t radome_hatch() const;
uint16_t ac_unit1_filter_dirty() const; [[nodiscard]] std::uint16_t ac_unit1_filter_dirty() const;
uint16_t ac_unit2_filter_dirty() const; [[nodiscard]] std::uint16_t ac_unit2_filter_dirty() const;
float equipment_shelter_temperature() const; [[nodiscard]] float equipment_shelter_temperature() const;
float outside_ambient_temperature() const; [[nodiscard]] float outside_ambient_temperature() const;
float transmitter_leaving_air_temp() const; [[nodiscard]] float transmitter_leaving_air_temp() const;
float ac_unit1_discharge_air_temp() const; [[nodiscard]] float ac_unit1_discharge_air_temp() const;
float generator_shelter_temperature() const; [[nodiscard]] float generator_shelter_temperature() const;
float radome_air_temperature() const; [[nodiscard]] float radome_air_temperature() const;
float ac_unit2_discharge_air_temp() const; [[nodiscard]] float ac_unit2_discharge_air_temp() const;
float spip_15v_ps() const; [[nodiscard]] float spip_15v_ps() const;
float spip_neg_15v_ps() const; [[nodiscard]] float spip_neg_15v_ps() const;
uint16_t spip_28v_ps_status() const; [[nodiscard]] std::uint16_t spip_28v_ps_status() const;
float spip_5v_ps() const; [[nodiscard]] float spip_5v_ps() const;
uint16_t converted_generator_fuel_level() const; [[nodiscard]] std::uint16_t converted_generator_fuel_level() const;
uint16_t elevation_pos_dead_limit() const; [[nodiscard]] std::uint16_t elevation_pos_dead_limit() const;
uint16_t _150v_overvoltage() const; [[nodiscard]] std::uint16_t _150v_overvoltage() const;
uint16_t _150v_undervoltage() const; [[nodiscard]] std::uint16_t _150v_undervoltage() const;
uint16_t elevation_servo_amp_inhibit() const; [[nodiscard]] std::uint16_t elevation_servo_amp_inhibit() const;
uint16_t elevation_servo_amp_short_circuit() const; [[nodiscard]] std::uint16_t elevation_servo_amp_short_circuit() const;
uint16_t elevation_servo_amp_overtemp() const; [[nodiscard]] std::uint16_t elevation_servo_amp_overtemp() const;
uint16_t elevation_motor_overtemp() const; [[nodiscard]] std::uint16_t elevation_motor_overtemp() const;
uint16_t elevation_stow_pin() const; [[nodiscard]] std::uint16_t elevation_stow_pin() const;
uint16_t elevation_housing_5v_ps() const; [[nodiscard]] std::uint16_t elevation_housing_5v_ps() const;
uint16_t elevation_neg_dead_limit() const; [[nodiscard]] std::uint16_t elevation_neg_dead_limit() const;
uint16_t elevation_pos_normal_limit() const; [[nodiscard]] std::uint16_t elevation_pos_normal_limit() const;
uint16_t elevation_neg_normal_limit() const; [[nodiscard]] std::uint16_t elevation_neg_normal_limit() const;
uint16_t elevation_encoder_light() const; [[nodiscard]] std::uint16_t elevation_encoder_light() const;
uint16_t elevation_gearbox_oil() const; [[nodiscard]] std::uint16_t elevation_gearbox_oil() const;
uint16_t elevation_handwheel() const; [[nodiscard]] std::uint16_t elevation_handwheel() const;
uint16_t elevation_amp_ps() const; [[nodiscard]] std::uint16_t elevation_amp_ps() const;
uint16_t azimuth_servo_amp_inhibit() const; [[nodiscard]] std::uint16_t azimuth_servo_amp_inhibit() const;
uint16_t azimuth_servo_amp_short_circuit() const; [[nodiscard]] std::uint16_t azimuth_servo_amp_short_circuit() const;
uint16_t azimuth_servo_amp_overtemp() const; [[nodiscard]] std::uint16_t azimuth_servo_amp_overtemp() const;
uint16_t azimuth_motor_overtemp() const; [[nodiscard]] std::uint16_t azimuth_motor_overtemp() const;
uint16_t azimuth_stow_pin() const; [[nodiscard]] std::uint16_t azimuth_stow_pin() const;
uint16_t azimuth_housing_5v_ps() const; [[nodiscard]] std::uint16_t azimuth_housing_5v_ps() const;
uint16_t azimuth_encoder_light() const; [[nodiscard]] std::uint16_t azimuth_encoder_light() const;
uint16_t azimuth_gearbox_oil() const; [[nodiscard]] std::uint16_t azimuth_gearbox_oil() const;
uint16_t azimuth_bull_gear_oil() const; [[nodiscard]] std::uint16_t azimuth_bull_gear_oil() const;
uint16_t azimuth_handwheel() const; [[nodiscard]] std::uint16_t azimuth_handwheel() const;
uint16_t azimuth_servo_amp_ps() const; [[nodiscard]] std::uint16_t azimuth_servo_amp_ps() const;
uint16_t servo() const; [[nodiscard]] std::uint16_t servo() const;
uint16_t pedestal_interlock_switch() const; [[nodiscard]] std::uint16_t pedestal_interlock_switch() const;
uint16_t coho_clock() const; [[nodiscard]] std::uint16_t coho_clock() const;
uint16_t rf_generator_frequency_select_oscillator() const; [[nodiscard]] std::uint16_t rf_generator_frequency_select_oscillator() const;
uint16_t rf_generator_rf_stalo() const; [[nodiscard]] std::uint16_t rf_generator_rf_stalo() const;
uint16_t rf_generator_phase_shifted_coho() const; [[nodiscard]] std::uint16_t rf_generator_phase_shifted_coho() const;
uint16_t _9v_receiver_ps() const; [[nodiscard]] std::uint16_t _9v_receiver_ps() const;
uint16_t _5v_receiver_ps() const; [[nodiscard]] std::uint16_t _5v_receiver_ps() const;
uint16_t _18v_receiver_ps() const; [[nodiscard]] std::uint16_t _18v_receiver_ps() const;
uint16_t neg_9v_receiver_ps() const; [[nodiscard]] std::uint16_t neg_9v_receiver_ps() const;
uint16_t _5v_single_channel_rdaiu_ps() const; [[nodiscard]] std::uint16_t _5v_single_channel_rdaiu_ps() const;
float horizontal_short_pulse_noise() const; [[nodiscard]] float horizontal_short_pulse_noise() const;
float horizontal_long_pulse_noise() const; [[nodiscard]] float horizontal_long_pulse_noise() const;
float horizontal_noise_temperature() const; [[nodiscard]] float horizontal_noise_temperature() const;
float vertical_short_pulse_noise() const; [[nodiscard]] float vertical_short_pulse_noise() const;
float vertical_long_pulse_noise() const; [[nodiscard]] float vertical_long_pulse_noise() const;
float vertical_noise_temperature() const; [[nodiscard]] float vertical_noise_temperature() const;
float horizontal_linearity() const; [[nodiscard]] float horizontal_linearity() const;
float horizontal_dynamic_range() const; [[nodiscard]] float horizontal_dynamic_range() const;
float horizontal_delta_dbz0() const; [[nodiscard]] float horizontal_delta_dbz0() const;
float vertical_delta_dbz0() const; [[nodiscard]] float vertical_delta_dbz0() const;
float kd_peak_measured() const; [[nodiscard]] float kd_peak_measured() const;
float short_pulse_horizontal_dbz0() const; [[nodiscard]] float short_pulse_horizontal_dbz0() const;
float long_pulse_horizontal_dbz0() const; [[nodiscard]] float long_pulse_horizontal_dbz0() const;
uint16_t velocity_processed() const; [[nodiscard]] std::uint16_t velocity_processed() const;
uint16_t width_processed() const; [[nodiscard]] std::uint16_t width_processed() const;
uint16_t velocity_rf_gen() const; [[nodiscard]] std::uint16_t velocity_rf_gen() const;
uint16_t width_rf_gen() const; [[nodiscard]] std::uint16_t width_rf_gen() const;
float horizontal_i0() const; [[nodiscard]] float horizontal_i0() const;
float vertical_i0() const; [[nodiscard]] float vertical_i0() const;
float vertical_dynamic_range() const; [[nodiscard]] float vertical_dynamic_range() const;
float short_pulse_vertical_dbz0() const; [[nodiscard]] float short_pulse_vertical_dbz0() const;
float long_pulse_vertical_dbz0() const; [[nodiscard]] float long_pulse_vertical_dbz0() const;
float horizontal_power_sense() const; [[nodiscard]] float horizontal_power_sense() const;
float vertical_power_sense() const; [[nodiscard]] float vertical_power_sense() const;
float zdr_bias() const; [[nodiscard]] float zdr_offset() const;
float clutter_suppression_delta() const; [[nodiscard]] float clutter_suppression_delta() const;
float clutter_suppression_unfiltered_power() const; [[nodiscard]] float clutter_suppression_unfiltered_power() const;
float clutter_suppression_filtered_power() const; [[nodiscard]] float clutter_suppression_filtered_power() const;
float vertical_linearity() const; [[nodiscard]] float vertical_linearity() const;
uint16_t state_file_read_status() const; [[nodiscard]] std::uint16_t state_file_read_status() const;
uint16_t state_file_write_status() const; [[nodiscard]] std::uint16_t state_file_write_status() const;
uint16_t bypass_map_file_read_status() const; [[nodiscard]] std::uint16_t bypass_map_file_read_status() const;
uint16_t bypass_map_file_write_status() const; [[nodiscard]] std::uint16_t bypass_map_file_write_status() const;
uint16_t current_adaptation_file_read_status() const; [[nodiscard]] std::uint16_t current_adaptation_file_read_status() const;
uint16_t current_adaptation_file_write_status() const; [[nodiscard]] std::uint16_t current_adaptation_file_write_status() const;
uint16_t censor_zone_file_read_status() const; [[nodiscard]] std::uint16_t censor_zone_file_read_status() const;
uint16_t censor_zone_file_write_status() const; [[nodiscard]] std::uint16_t censor_zone_file_write_status() const;
uint16_t remote_vcp_file_read_status() const; [[nodiscard]] std::uint16_t remote_vcp_file_read_status() const;
uint16_t remote_vcp_file_write_status() const; [[nodiscard]] std::uint16_t remote_vcp_file_write_status() const;
uint16_t baseline_adaptation_file_read_status() const; [[nodiscard]] std::uint16_t baseline_adaptation_file_read_status() const;
uint16_t read_status_of_prf_sets() const; [[nodiscard]] std::uint16_t read_status_of_prf_sets() const;
uint16_t clutter_filter_map_file_read_status() const; [[nodiscard]] std::uint16_t clutter_filter_map_file_read_status() const;
uint16_t clutter_filter_map_file_write_status() const; [[nodiscard]] std::uint16_t clutter_filter_map_file_write_status() const;
uint16_t generatl_disk_io_error() const; [[nodiscard]] std::uint16_t general_disk_io_error() const;
uint8_t rsp_status() const; [[nodiscard]] std::uint8_t rsp_status() const;
uint8_t motherboard_temperature() const; [[nodiscard]] std::uint8_t cpu1_temperature() const;
uint8_t cpu1_temperature() const; [[nodiscard]] std::uint8_t cpu2_temperature() const;
uint8_t cpu2_temperature() const; [[nodiscard]] std::uint16_t rsp_motherboard_power() const;
uint16_t cpu1_fan_speed() const; [[nodiscard]] std::uint16_t spip_comm_status() const;
uint16_t cpu2_fan_speed() const; [[nodiscard]] std::uint16_t hci_comm_status() const;
uint16_t rsp_fan1_speed() const; [[nodiscard]] std::uint16_t signal_processor_command_status() const;
uint16_t rsp_fan2_speed() const; [[nodiscard]] std::uint16_t ame_communication_status() const;
uint16_t rsp_fan3_speed() const; [[nodiscard]] std::uint16_t rms_link_status() const;
uint16_t spip_comm_status() const; [[nodiscard]] std::uint16_t rpg_link_status() const;
uint16_t hci_comm_status() const; [[nodiscard]] std::uint16_t interpanel_link_status() const;
uint16_t signal_processor_command_status() const; [[nodiscard]] std::uint32_t performance_check_time() const;
uint16_t ame_communication_status() const; [[nodiscard]] std::uint16_t version() const;
uint16_t rms_link_status() const;
uint16_t rpg_link_status() const;
uint16_t interpanel_link_status() const;
uint32_t performance_check_time() const;
uint16_t version() const;
bool Parse(std::istream& is); bool Parse(std::istream& is) override;
static std::shared_ptr<PerformanceMaintenanceData> static std::shared_ptr<PerformanceMaintenanceData>
Create(Level2MessageHeader&& header, std::istream& is); Create(Level2MessageHeader&& header, std::istream& is);
private: private:
std::unique_ptr<PerformanceMaintenanceDataImpl> p; class Impl;
std::unique_ptr<Impl> p;
}; };
} // namespace rda } // namespace scwx::wsr88d::rda
} // namespace wsr88d
} // namespace scwx

View file

@ -2,14 +2,8 @@
#include <scwx/wsr88d/rda/level2_message.hpp> #include <scwx/wsr88d/rda/level2_message.hpp>
namespace scwx namespace scwx::wsr88d::rda
{ {
namespace wsr88d
{
namespace rda
{
class RdaAdaptationDataImpl;
class RdaAdaptationData : public Level2Message class RdaAdaptationData : public Level2Message
{ {
@ -23,193 +17,199 @@ public:
RdaAdaptationData(RdaAdaptationData&&) noexcept; RdaAdaptationData(RdaAdaptationData&&) noexcept;
RdaAdaptationData& operator=(RdaAdaptationData&&) noexcept; RdaAdaptationData& operator=(RdaAdaptationData&&) noexcept;
std::string adap_file_name() const; [[nodiscard]] std::string adap_file_name() const;
std::string adap_format() const; [[nodiscard]] std::string adap_format() const;
std::string adap_revision() const; [[nodiscard]] std::string adap_revision() const;
std::string adap_date() const; [[nodiscard]] std::string adap_date() const;
std::string adap_time() const; [[nodiscard]] std::string adap_time() const;
float lower_pre_limit() const; [[nodiscard]] float lower_pre_limit() const;
float az_lat() const; [[nodiscard]] float az_lat() const;
float upper_pre_limit() const; [[nodiscard]] float upper_pre_limit() const;
float el_lat() const; [[nodiscard]] float el_lat() const;
float parkaz() const; [[nodiscard]] float parkaz() const;
float parkel() const; [[nodiscard]] float parkel() const;
float a_fuel_conv(unsigned i) const; [[nodiscard]] float a_fuel_conv(unsigned i) const;
float a_min_shelter_temp() const; [[nodiscard]] float a_min_shelter_temp() const;
float a_max_shelter_temp() const; [[nodiscard]] float a_max_shelter_temp() const;
float a_min_shelter_ac_temp_diff() const; [[nodiscard]] float a_min_shelter_ac_temp_diff() const;
float a_max_xmtr_air_temp() const; [[nodiscard]] float a_max_xmtr_air_temp() const;
float a_max_rad_temp() const; [[nodiscard]] float a_max_rad_temp() const;
float a_max_rad_temp_rise() const; [[nodiscard]] float a_max_rad_temp_rise() const;
float lower_dead_limit() const; [[nodiscard]] float lower_dead_limit() const;
float upper_dead_limit() const; [[nodiscard]] float upper_dead_limit() const;
float a_min_gen_room_temp() const; [[nodiscard]] float a_min_gen_room_temp() const;
float a_max_gen_room_temp() const; [[nodiscard]] float a_max_gen_room_temp() const;
float spip_5v_reg_lim() const; [[nodiscard]] float spip_5v_reg_lim() const;
float spip_15v_reg_lim() const; [[nodiscard]] float spip_15v_reg_lim() const;
bool rpg_co_located() const; [[nodiscard]] bool rpg_co_located() const;
bool spec_filter_installed() const; [[nodiscard]] bool spec_filter_installed() const;
bool tps_installed() const; [[nodiscard]] bool tps_installed() const;
bool rms_installed() const; [[nodiscard]] bool rms_installed() const;
uint32_t a_hvdl_tst_int() const; [[nodiscard]] std::uint32_t a_hvdl_tst_int() const;
uint32_t a_rpg_lt_int() const; [[nodiscard]] std::uint32_t a_rpg_lt_int() const;
uint32_t a_min_stab_util_pwr_time() const; [[nodiscard]] std::uint32_t a_min_stab_util_pwr_time() const;
uint32_t a_gen_auto_exer_interval() const; [[nodiscard]] std::uint32_t a_gen_auto_exer_interval() const;
uint32_t a_util_pwr_sw_req_interval() const; [[nodiscard]] std::uint32_t a_util_pwr_sw_req_interval() const;
float a_low_fuel_level() const; [[nodiscard]] float a_low_fuel_level() const;
uint32_t config_chan_number() const; [[nodiscard]] std::uint32_t config_chan_number() const;
uint32_t redundant_chan_config() const; [[nodiscard]] std::uint32_t redundant_chan_config() const;
float atten_table(unsigned i) const; [[nodiscard]] float atten_table(unsigned i) const;
float path_losses(unsigned i) const; [[nodiscard]] float path_losses(unsigned i) const;
float h_coupler_xmt_loss() const; [[nodiscard]] float h_coupler_xmt_loss() const;
float h_coupler_cw_loss() const; [[nodiscard]] float h_coupler_cw_loss() const;
float v_coupler_xmt_loss() const; [[nodiscard]] float v_coupler_xmt_loss() const;
float ame_ts_bias() const; [[nodiscard]] float ame_ts_bias() const;
float v_coupler_cw_loss() const; [[nodiscard]] float v_coupler_cw_loss() const;
float pwr_sense_bias() const; [[nodiscard]] float pwr_sense_bias() const;
float ame_v_noise_enr() const; [[nodiscard]] float ame_v_noise_enr() const;
float chan_cal_diff() const; [[nodiscard]] float chan_cal_diff() const;
float v_ts_cw() const; [[nodiscard]] float v_ts_cw() const;
float h_rnscale(unsigned i) const; [[nodiscard]] float h_rnscale(unsigned i) const;
float atmos(unsigned i) const; [[nodiscard]] float atmos(unsigned i) const;
float el_index(unsigned i) const; [[nodiscard]] float el_index(unsigned i) const;
uint32_t tfreq_mhz() const; [[nodiscard]] std::uint32_t tfreq_mhz() const;
float base_data_tcn() const; [[nodiscard]] float base_data_tcn() const;
float refl_data_tover() const; [[nodiscard]] float refl_data_tover() const;
float tar_h_dbz0_lp() const; [[nodiscard]] float tar_h_dbz0_lp() const;
float tar_v_dbz0_lp() const; [[nodiscard]] float tar_v_dbz0_lp() const;
uint32_t init_phi_dp() const; [[nodiscard]] std::uint32_t init_phi_dp() const;
uint32_t norm_init_phi_dp() const; [[nodiscard]] std::uint32_t norm_init_phi_dp() const;
float lx_lp() const; [[nodiscard]] float lx_lp() const;
float lx_sp() const; [[nodiscard]] float lx_sp() const;
float meteor_param() const; [[nodiscard]] float meteor_param() const;
float antenna_gain() const; [[nodiscard]] float antenna_gain() const;
float vel_degrad_limit() const; [[nodiscard]] float vel_degrad_limit() const;
float wth_degrad_limit() const; [[nodiscard]] float wth_degrad_limit() const;
float h_noisetemp_dgrad_limit() const; [[nodiscard]] float h_noisetemp_dgrad_limit() const;
uint32_t h_min_noisetemp() const; [[nodiscard]] std::uint32_t h_min_noisetemp() const;
float v_noisetemp_dgrad_limit() const; [[nodiscard]] float v_noisetemp_dgrad_limit() const;
uint32_t v_min_noisetemp() const; [[nodiscard]] std::uint32_t v_min_noisetemp() const;
float kly_degrade_limit() const; [[nodiscard]] float kly_degrade_limit() const;
float ts_coho() const; [[nodiscard]] float ts_coho() const;
float h_ts_cw() const; [[nodiscard]] float h_ts_cw() const;
float ts_stalo() const; [[nodiscard]] float ts_stalo() const;
float ame_h_noise_enr() const; [[nodiscard]] float ame_h_noise_enr() const;
float xmtr_peak_pwr_high_limit() const; [[nodiscard]] float xmtr_peak_pwr_high_limit() const;
float xmtr_peak_pwr_low_limit() const; [[nodiscard]] float xmtr_peak_pwr_low_limit() const;
float h_dbz0_delta_limit() const; [[nodiscard]] float h_dbz0_delta_limit() const;
float threshold1() const; [[nodiscard]] float threshold1() const;
float threshold2() const; [[nodiscard]] float threshold2() const;
float clut_supp_dgrad_lim() const; [[nodiscard]] float clut_supp_dgrad_lim() const;
float range0_value() const; [[nodiscard]] float range0_value() const;
float xmtr_pwr_mtr_scale() const; [[nodiscard]] float xmtr_pwr_mtr_scale() const;
float v_dbz0_delta_limit() const; [[nodiscard]] float v_dbz0_delta_limit() const;
float tar_h_dbz0_sp() const; [[nodiscard]] float tar_h_dbz0_sp() const;
float tar_v_dbz0_sp() const; [[nodiscard]] float tar_v_dbz0_sp() const;
uint32_t deltaprf() const; [[nodiscard]] std::uint32_t deltaprf() const;
uint32_t tau_sp() const; [[nodiscard]] std::uint32_t tau_sp() const;
uint32_t tau_lp() const; [[nodiscard]] std::uint32_t tau_lp() const;
uint32_t nc_dead_value() const; [[nodiscard]] std::uint32_t nc_dead_value() const;
uint32_t tau_rf_sp() const; [[nodiscard]] std::uint32_t tau_rf_sp() const;
uint32_t tau_rf_lp() const; [[nodiscard]] std::uint32_t tau_rf_lp() const;
float seg1_lim() const; [[nodiscard]] float seg1_lim() const;
float slatsec() const; [[nodiscard]] float slatsec() const;
float slonsec() const; [[nodiscard]] float slonsec() const;
uint32_t slatdeg() const; [[nodiscard]] std::uint32_t slatdeg() const;
uint32_t slatmin() const; [[nodiscard]] std::uint32_t slatmin() const;
uint32_t slondeg() const; [[nodiscard]] std::uint32_t slondeg() const;
uint32_t slonmin() const; [[nodiscard]] std::uint32_t slonmin() const;
char slatdir() const; [[nodiscard]] char slatdir() const;
char slondir() const; [[nodiscard]] char slondir() const;
float az_correction_factor() const; [[nodiscard]] double dig_rcvr_clock_freq() const;
float el_correction_factor() const; [[nodiscard]] double coho_freq() const;
std::string site_name() const; [[nodiscard]] float az_correction_factor() const;
float ant_manual_setup_ielmin() const; [[nodiscard]] float el_correction_factor() const;
float ant_manual_setup_ielmax() const; [[nodiscard]] std::string site_name() const;
uint32_t ant_manual_setup_fazvelmax() const; [[nodiscard]] float ant_manual_setup_ielmin() const;
uint32_t ant_manual_setup_felvelmax() const; [[nodiscard]] float ant_manual_setup_ielmax() const;
int32_t ant_manual_setup_ignd_hgt() const; [[nodiscard]] std::uint32_t ant_manual_setup_fazvelmax() const;
uint32_t ant_manual_setup_irad_hgt() const; [[nodiscard]] std::uint32_t ant_manual_setup_felvelmax() const;
float az_pos_sustain_drive() const; [[nodiscard]] std::int32_t ant_manual_setup_ignd_hgt() const;
float az_neg_sustain_drive() const; [[nodiscard]] std::uint32_t ant_manual_setup_irad_hgt() const;
float az_nom_pos_drive_slope() const; [[nodiscard]] float az_pos_sustain_drive() const;
float az_nom_neg_drive_slope() const; [[nodiscard]] float az_neg_sustain_drive() const;
float az_feedback_slope() const; [[nodiscard]] float az_nom_pos_drive_slope() const;
float el_pos_sustain_drive() const; [[nodiscard]] float az_nom_neg_drive_slope() const;
float el_neg_sustain_drive() const; [[nodiscard]] float az_feedback_slope() const;
float el_nom_pos_drive_slope() const; [[nodiscard]] float el_pos_sustain_drive() const;
float el_nom_neg_drive_slope() const; [[nodiscard]] float el_neg_sustain_drive() const;
float el_feedback_slope() const; [[nodiscard]] float el_nom_pos_drive_slope() const;
float el_first_slope() const; [[nodiscard]] float el_nom_neg_drive_slope() const;
float el_second_slope() const; [[nodiscard]] float el_feedback_slope() const;
float el_third_slope() const; [[nodiscard]] float el_first_slope() const;
float el_droop_pos() const; [[nodiscard]] float el_second_slope() const;
float el_off_neutral_drive() const; [[nodiscard]] float el_third_slope() const;
float az_intertia() const; [[nodiscard]] float el_droop_pos() const;
float el_inertia() const; [[nodiscard]] float el_off_neutral_drive() const;
uint32_t rvp8nv_iwaveguide_length() const; [[nodiscard]] float az_intertia() const;
float v_rnscale(unsigned i) const; [[nodiscard]] float el_inertia() const;
float vel_data_tover() const; [[nodiscard]] float az_stow_angle() const;
float width_data_tover() const; [[nodiscard]] float el_stow_angle() const;
float doppler_range_start() const; [[nodiscard]] float az_encoder_alignment() const;
uint32_t max_el_index() const; [[nodiscard]] float el_encoder_alignment() const;
float seg2_lim() const; [[nodiscard]] std::string refined_park() const;
float seg3_lim() const; [[nodiscard]] std::uint32_t rvp8nv_iwaveguide_length() const;
float seg4_lim() const; [[nodiscard]] float v_rnscale(unsigned i) const;
uint32_t nbr_el_segments() const; [[nodiscard]] float vel_data_tover() const;
float h_noise_long() const; [[nodiscard]] float width_data_tover() const;
float ant_noise_temp() const; [[nodiscard]] float doppler_range_start() const;
float h_noise_short() const; [[nodiscard]] std::uint32_t max_el_index() const;
float h_noise_tolerance() const; [[nodiscard]] float seg2_lim() const;
float min_h_dyn_range() const; [[nodiscard]] float seg3_lim() const;
bool gen_installed() const; [[nodiscard]] float seg4_lim() const;
bool gen_exercise() const; [[nodiscard]] std::uint32_t nbr_el_segments() const;
float v_noise_tolerance() const; [[nodiscard]] float h_noise_long() const;
float min_v_dyn_range() const; [[nodiscard]] float ant_noise_temp() const;
float zdr_bias_dgrad_lim() const; [[nodiscard]] float h_noise_short() const;
float baseline_zdr_bias() const; [[nodiscard]] float h_noise_tolerance() const;
float v_noise_long() const; [[nodiscard]] float min_h_dyn_range() const;
float v_noise_short() const; [[nodiscard]] bool gen_installed() const;
float zdr_data_tover() const; [[nodiscard]] bool gen_exercise() const;
float phi_data_tover() const; [[nodiscard]] float v_noise_tolerance() const;
float rho_data_tover() const; [[nodiscard]] float min_v_dyn_range() const;
float stalo_power_dgrad_limit() const; [[nodiscard]] float zdr_offset_dgrad_lim() const;
float stalo_power_maint_limit() const; [[nodiscard]] float baseline_zdr_offset() const;
float min_h_pwr_sense() const; [[nodiscard]] float v_noise_long() const;
float min_v_pwr_sense() const; [[nodiscard]] float v_noise_short() const;
float h_pwr_sense_offset() const; [[nodiscard]] float zdr_data_tover() const;
float v_pwr_sense_offset() const; [[nodiscard]] float phi_data_tover() const;
float ps_gain_ref() const; [[nodiscard]] float rho_data_tover() const;
float rf_pallet_broad_loss() const; [[nodiscard]] float stalo_power_dgrad_limit() const;
float ame_ps_tolerance() const; [[nodiscard]] float stalo_power_maint_limit() const;
float ame_max_temp() const; [[nodiscard]] float min_h_pwr_sense() const;
float ame_min_temp() const; [[nodiscard]] float min_v_pwr_sense() const;
float rcvr_mod_max_temp() const; [[nodiscard]] float h_pwr_sense_offset() const;
float rcvr_mod_min_temp() const; [[nodiscard]] float v_pwr_sense_offset() const;
float bite_mod_max_temp() const; [[nodiscard]] float ps_gain_ref() const;
float bite_mod_min_temp() const; [[nodiscard]] float rf_pallet_broad_loss() const;
uint32_t default_polarization() const; [[nodiscard]] float ame_ps_tolerance() const;
float tr_limit_dgrad_limit() const; [[nodiscard]] float ame_max_temp() const;
float tr_limit_fail_limit() const; [[nodiscard]] float ame_min_temp() const;
bool rfp_stepper_enabled() const; [[nodiscard]] float rcvr_mod_max_temp() const;
float ame_current_tolerance() const; [[nodiscard]] float rcvr_mod_min_temp() const;
uint32_t h_only_polarization() const; [[nodiscard]] float bite_mod_max_temp() const;
uint32_t v_only_polarization() const; [[nodiscard]] float bite_mod_min_temp() const;
float sun_bias() const; [[nodiscard]] std::uint32_t default_polarization() const;
float a_min_shelter_temp_warn() const; [[nodiscard]] float tr_limit_dgrad_limit() const;
float power_meter_zero() const; [[nodiscard]] float tr_limit_fail_limit() const;
float txb_baseline() const; [[nodiscard]] bool rfp_stepper_enabled() const;
float txb_alarm_thresh() const; [[nodiscard]] float ame_current_tolerance() const;
[[nodiscard]] std::uint32_t h_only_polarization() const;
[[nodiscard]] std::uint32_t v_only_polarization() const;
[[nodiscard]] float sun_bias() const;
[[nodiscard]] float a_min_shelter_temp_warn() const;
[[nodiscard]] float power_meter_zero() const;
[[nodiscard]] float txb_baseline() const;
[[nodiscard]] float txb_alarm_thresh() const;
bool Parse(std::istream& is); bool Parse(std::istream& is) override;
static std::shared_ptr<RdaAdaptationData> static std::shared_ptr<RdaAdaptationData>
Create(Level2MessageHeader&& header, std::istream& is); Create(Level2MessageHeader&& header, std::istream& is);
private: private:
std::unique_ptr<RdaAdaptationDataImpl> p; class Impl;
std::unique_ptr<Impl> p;
}; };
} // namespace rda } // namespace scwx::wsr88d::rda
} // namespace wsr88d
} // namespace scwx

View file

@ -0,0 +1,30 @@
#pragma once
#include <scwx/wsr88d/rda/level2_message.hpp>
namespace scwx::wsr88d::rda
{
class RdaPrfData : public Level2Message
{
public:
explicit RdaPrfData();
~RdaPrfData() override;
RdaPrfData(const RdaPrfData&) = delete;
RdaPrfData& operator=(const RdaPrfData&) = delete;
RdaPrfData(RdaPrfData&&) noexcept;
RdaPrfData& operator=(RdaPrfData&&) noexcept;
bool Parse(std::istream& is) override;
static std::shared_ptr<RdaPrfData> Create(Level2MessageHeader&& header,
std::istream& is);
private:
class Impl;
std::unique_ptr<Impl> p;
};
} // namespace scwx::wsr88d::rda

View file

@ -2,14 +2,8 @@
#include <scwx/wsr88d/rda/level2_message.hpp> #include <scwx/wsr88d/rda/level2_message.hpp>
namespace scwx namespace scwx::wsr88d::rda
{ {
namespace wsr88d
{
namespace rda
{
class RdaStatusDataImpl;
class RdaStatusData : public Level2Message class RdaStatusData : public Level2Message
{ {
@ -23,45 +17,45 @@ public:
RdaStatusData(RdaStatusData&&) noexcept; RdaStatusData(RdaStatusData&&) noexcept;
RdaStatusData& operator=(RdaStatusData&&) noexcept; RdaStatusData& operator=(RdaStatusData&&) noexcept;
uint16_t rda_status() const; [[nodiscard]] std::uint16_t rda_status() const;
uint16_t operability_status() const; [[nodiscard]] std::uint16_t operability_status() const;
uint16_t control_status() const; [[nodiscard]] std::uint16_t control_status() const;
uint16_t auxiliary_power_generator_state() const; [[nodiscard]] std::uint16_t auxiliary_power_generator_state() const;
uint16_t average_transmitter_power() const; [[nodiscard]] std::uint16_t average_transmitter_power() const;
float horizontal_reflectivity_calibration_correction() const; [[nodiscard]] float horizontal_reflectivity_calibration_correction() const;
uint16_t data_transmission_enabled() const; [[nodiscard]] std::uint16_t data_transmission_enabled() const;
uint16_t volume_coverage_pattern_number() const; [[nodiscard]] std::uint16_t volume_coverage_pattern_number() const;
uint16_t rda_control_authorization() const; [[nodiscard]] std::uint16_t rda_control_authorization() const;
uint16_t rda_build_number() const; [[nodiscard]] std::uint16_t rda_build_number() const;
uint16_t operational_mode() const; [[nodiscard]] std::uint16_t operational_mode() const;
uint16_t super_resolution_status() const; [[nodiscard]] std::uint16_t super_resolution_status() const;
uint16_t clutter_mitigation_decision_status() const; [[nodiscard]] std::uint16_t clutter_mitigation_decision_status() const;
uint16_t avset_ebc_rda_log_data_status() const; [[nodiscard]] std::uint16_t rda_scan_and_data_flags() const;
uint16_t rda_alarm_summary() const; [[nodiscard]] std::uint16_t rda_alarm_summary() const;
uint16_t command_acknowledgement() const; [[nodiscard]] std::uint16_t command_acknowledgement() const;
uint16_t channel_control_status() const; [[nodiscard]] std::uint16_t channel_control_status() const;
uint16_t spot_blanking_status() const; [[nodiscard]] std::uint16_t spot_blanking_status() const;
uint16_t bypass_map_generation_date() const; [[nodiscard]] std::uint16_t bypass_map_generation_date() const;
uint16_t bypass_map_generation_time() const; [[nodiscard]] std::uint16_t bypass_map_generation_time() const;
uint16_t clutter_filter_map_generation_date() const; [[nodiscard]] std::uint16_t clutter_filter_map_generation_date() const;
uint16_t clutter_filter_map_generation_time() const; [[nodiscard]] std::uint16_t clutter_filter_map_generation_time() const;
float vertical_reflectivity_calibration_correction() const; [[nodiscard]] float vertical_reflectivity_calibration_correction() const;
uint16_t transition_power_source_status() const; [[nodiscard]] std::uint16_t transition_power_source_status() const;
uint16_t rms_control_status() const; [[nodiscard]] std::uint16_t rms_control_status() const;
uint16_t performance_check_status() const; [[nodiscard]] std::uint16_t performance_check_status() const;
uint16_t alarm_codes(unsigned i) const; [[nodiscard]] std::uint16_t alarm_codes(unsigned i) const;
uint16_t signal_processing_options() const; [[nodiscard]] std::uint16_t signal_processing_options() const;
uint16_t status_version() const; [[nodiscard]] std::uint16_t downloaded_pattern_number() const;
[[nodiscard]] std::uint16_t status_version() const;
bool Parse(std::istream& is); bool Parse(std::istream& is) override;
static std::shared_ptr<RdaStatusData> Create(Level2MessageHeader&& header, static std::shared_ptr<RdaStatusData> Create(Level2MessageHeader&& header,
std::istream& is); std::istream& is);
private: private:
std::unique_ptr<RdaStatusDataImpl> p; class Impl;
std::unique_ptr<Impl> p;
}; };
} // namespace rda } // namespace scwx::wsr88d::rda
} // namespace wsr88d
} // namespace scwx

View file

@ -0,0 +1,48 @@
#pragma once
#include <scwx/wsr88d/rpg/packet.hpp>
#include <cstdint>
#include <memory>
namespace scwx::wsr88d::rpg
{
class DigitalRasterDataArrayPacket : public Packet
{
public:
explicit DigitalRasterDataArrayPacket();
~DigitalRasterDataArrayPacket() override;
DigitalRasterDataArrayPacket(const DigitalRasterDataArrayPacket&) = delete;
DigitalRasterDataArrayPacket&
operator=(const DigitalRasterDataArrayPacket&) = delete;
DigitalRasterDataArrayPacket(DigitalRasterDataArrayPacket&&) noexcept;
DigitalRasterDataArrayPacket&
operator=(DigitalRasterDataArrayPacket&&) noexcept;
[[nodiscard]] std::uint16_t packet_code() const override;
[[nodiscard]] std::uint16_t i_coordinate_start() const;
[[nodiscard]] std::uint16_t j_coordinate_start() const;
[[nodiscard]] std::uint16_t i_scale_factor() const;
[[nodiscard]] std::uint16_t j_scale_factor() const;
[[nodiscard]] std::uint16_t number_of_cells() const;
[[nodiscard]] std::uint16_t number_of_rows() const;
[[nodiscard]] std::uint16_t number_of_bytes_in_row(std::uint16_t r) const;
[[nodiscard]] const std::vector<std::uint8_t>& level(std::uint16_t r) const;
[[nodiscard]] std::size_t data_size() const override;
bool Parse(std::istream& is) override;
static std::shared_ptr<DigitalRasterDataArrayPacket>
Create(std::istream& is);
private:
class Impl;
std::unique_ptr<Impl> p;
};
} // namespace scwx::wsr88d::rpg

View file

@ -2,16 +2,12 @@
#include <scwx/wsr88d/rpg/level3_message.hpp> #include <scwx/wsr88d/rpg/level3_message.hpp>
namespace scwx namespace scwx::wsr88d::rpg
{
namespace wsr88d
{
namespace rpg
{ {
class Level3MessageFactory class Level3MessageFactory
{ {
private: public:
explicit Level3MessageFactory() = delete; explicit Level3MessageFactory() = delete;
~Level3MessageFactory() = delete; ~Level3MessageFactory() = delete;
@ -21,10 +17,7 @@ private:
Level3MessageFactory(Level3MessageFactory&&) noexcept = delete; Level3MessageFactory(Level3MessageFactory&&) noexcept = delete;
Level3MessageFactory& operator=(Level3MessageFactory&&) noexcept = delete; Level3MessageFactory& operator=(Level3MessageFactory&&) noexcept = delete;
public:
static std::shared_ptr<Level3Message> Create(std::istream& is); static std::shared_ptr<Level3Message> Create(std::istream& is);
}; };
} // namespace rpg } // namespace scwx::wsr88d::rpg
} // namespace wsr88d
} // namespace scwx

View file

@ -2,16 +2,12 @@
#include <scwx/wsr88d/rpg/packet.hpp> #include <scwx/wsr88d/rpg/packet.hpp>
namespace scwx namespace scwx::wsr88d::rpg
{
namespace wsr88d
{
namespace rpg
{ {
class PacketFactory class PacketFactory
{ {
private: public:
explicit PacketFactory() = delete; explicit PacketFactory() = delete;
~PacketFactory() = delete; ~PacketFactory() = delete;
@ -21,10 +17,7 @@ private:
PacketFactory(PacketFactory&&) noexcept = delete; PacketFactory(PacketFactory&&) noexcept = delete;
PacketFactory& operator=(PacketFactory&&) noexcept = delete; PacketFactory& operator=(PacketFactory&&) noexcept = delete;
public:
static std::shared_ptr<Packet> Create(std::istream& is); static std::shared_ptr<Packet> Create(std::istream& is);
}; };
} // namespace rpg } // namespace scwx::wsr88d::rpg
} // namespace wsr88d
} // namespace scwx

View file

@ -12,8 +12,6 @@
namespace scwx::wsr88d::rpg namespace scwx::wsr88d::rpg
{ {
class ProductDescriptionBlockImpl;
class ProductDescriptionBlock : public awips::Message class ProductDescriptionBlock : public awips::Message
{ {
public: public:
@ -26,38 +24,38 @@ public:
ProductDescriptionBlock(ProductDescriptionBlock&&) noexcept; ProductDescriptionBlock(ProductDescriptionBlock&&) noexcept;
ProductDescriptionBlock& operator=(ProductDescriptionBlock&&) noexcept; ProductDescriptionBlock& operator=(ProductDescriptionBlock&&) noexcept;
[[nodiscard]] int16_t block_divider() const; [[nodiscard]] std::int16_t block_divider() const;
[[nodiscard]] float latitude_of_radar() const; [[nodiscard]] float latitude_of_radar() const;
[[nodiscard]] float longitude_of_radar() const; [[nodiscard]] float longitude_of_radar() const;
[[nodiscard]] int16_t height_of_radar() const; [[nodiscard]] std::int16_t height_of_radar() const;
[[nodiscard]] int16_t product_code() const; [[nodiscard]] std::int16_t product_code() const;
[[nodiscard]] uint16_t operational_mode() const; [[nodiscard]] std::uint16_t operational_mode() const;
[[nodiscard]] uint16_t volume_coverage_pattern() const; [[nodiscard]] std::uint16_t volume_coverage_pattern() const;
[[nodiscard]] int16_t sequence_number() const; [[nodiscard]] std::int16_t sequence_number() const;
[[nodiscard]] uint16_t volume_scan_number() const; [[nodiscard]] std::uint16_t volume_scan_number() const;
[[nodiscard]] uint16_t volume_scan_date() const; [[nodiscard]] std::uint16_t volume_scan_date() const;
[[nodiscard]] uint32_t volume_scan_start_time() const; [[nodiscard]] std::uint32_t volume_scan_start_time() const;
[[nodiscard]] uint16_t generation_date_of_product() const; [[nodiscard]] std::uint16_t generation_date_of_product() const;
[[nodiscard]] uint32_t generation_time_of_product() const; [[nodiscard]] std::uint32_t generation_time_of_product() const;
[[nodiscard]] uint16_t elevation_number() const; [[nodiscard]] std::uint16_t elevation_number() const;
[[nodiscard]] uint16_t data_level_threshold(size_t i) const; [[nodiscard]] std::uint16_t data_level_threshold(size_t i) const;
[[nodiscard]] uint8_t version() const; [[nodiscard]] std::uint8_t version() const;
[[nodiscard]] uint8_t spot_blank() const; [[nodiscard]] std::uint8_t spot_blank() const;
[[nodiscard]] uint32_t offset_to_symbology() const; [[nodiscard]] std::uint32_t offset_to_symbology() const;
[[nodiscard]] uint32_t offset_to_graphic() const; [[nodiscard]] std::uint32_t offset_to_graphic() const;
[[nodiscard]] uint32_t offset_to_tabular() const; [[nodiscard]] std::uint32_t offset_to_tabular() const;
[[nodiscard]] float range() const; [[nodiscard]] float range() const;
[[nodiscard]] uint16_t range_raw() const; [[nodiscard]] std::uint16_t range_raw() const;
[[nodiscard]] float x_resolution() const; [[nodiscard]] float x_resolution() const;
[[nodiscard]] uint16_t x_resolution_raw() const; [[nodiscard]] std::uint16_t x_resolution_raw() const;
[[nodiscard]] float y_resolution() const; [[nodiscard]] float y_resolution() const;
[[nodiscard]] uint16_t y_resolution_raw() const; [[nodiscard]] std::uint16_t y_resolution_raw() const;
[[nodiscard]] uint16_t threshold() const; [[nodiscard]] std::uint16_t threshold() const;
[[nodiscard]] float offset() const; [[nodiscard]] float offset() const;
[[nodiscard]] float scale() const; [[nodiscard]] float scale() const;
[[nodiscard]] uint16_t number_of_levels() const; [[nodiscard]] std::uint16_t number_of_levels() const;
[[nodiscard]] std::optional<DataLevelCode> [[nodiscard]] std::optional<DataLevelCode>
data_level_code(std::uint8_t level) const; data_level_code(std::uint8_t level) const;
@ -78,14 +76,15 @@ public:
[[nodiscard]] bool IsCompressionEnabled() const; [[nodiscard]] bool IsCompressionEnabled() const;
[[nodiscard]] bool IsDataLevelCoded() const; [[nodiscard]] bool IsDataLevelCoded() const;
[[nodiscard]] size_t data_size() const override; [[nodiscard]] std::size_t data_size() const override;
bool Parse(std::istream& is) override; bool Parse(std::istream& is) override;
static constexpr size_t SIZE = 102u; static constexpr std::size_t SIZE = 102u;
private: private:
std::unique_ptr<ProductDescriptionBlockImpl> p; class Impl;
std::unique_ptr<Impl> p;
}; };
} // namespace scwx::wsr88d::rpg } // namespace scwx::wsr88d::rpg

View file

@ -9,14 +9,19 @@ namespace awips
static const std::string logPrefix_ = "scwx::awips::message"; static const std::string logPrefix_ = "scwx::awips::message";
static const auto logger_ = util::Logger::Create(logPrefix_); static const auto logger_ = util::Logger::Create(logPrefix_);
class MessageImpl class Message::Impl
{ {
public: public:
explicit MessageImpl() {}; explicit Impl() = default;
~MessageImpl() = default; ~Impl() = default;
Impl(const Impl&) = delete;
Impl& operator=(const Impl&) = delete;
Impl(const Impl&&) = delete;
Impl& operator=(const Impl&&) = delete;
}; };
Message::Message() : p(std::make_unique<MessageImpl>()) {} Message::Message() : p(std::make_unique<Impl>()) {}
Message::~Message() = default; Message::~Message() = default;
Message::Message(Message&&) noexcept = default; Message::Message(Message&&) noexcept = default;

View file

@ -1,11 +1,7 @@
#include <scwx/wsr88d/rda/digital_radar_data_generic.hpp> #include <scwx/wsr88d/rda/digital_radar_data_generic.hpp>
#include <scwx/util/logger.hpp> #include <scwx/util/logger.hpp>
namespace scwx namespace scwx::wsr88d::rda
{
namespace wsr88d
{
namespace rda
{ {
static const std::string logPrefix_ = static const std::string logPrefix_ =
@ -27,9 +23,9 @@ static const std::unordered_map<std::string, DataBlockType> strToDataBlock_ {
class DigitalRadarDataGeneric::DataBlock::Impl class DigitalRadarDataGeneric::DataBlock::Impl
{ {
public: public:
explicit Impl(const std::string& dataBlockType, explicit Impl(std::string dataBlockType, std::string dataName) :
const std::string& dataName) : dataBlockType_ {std::move(dataBlockType)},
dataBlockType_ {dataBlockType}, dataName_ {dataName} dataName_ {std::move(dataName)}
{ {
} }
@ -51,7 +47,13 @@ DigitalRadarDataGeneric::DataBlock::operator=(DataBlock&&) noexcept = default;
class DigitalRadarDataGeneric::MomentDataBlock::Impl class DigitalRadarDataGeneric::MomentDataBlock::Impl
{ {
public: public:
explicit Impl() {} explicit Impl() = default;
~Impl() = default;
Impl(const Impl&) = delete;
Impl& operator=(const Impl&) = delete;
Impl(const Impl&&) = delete;
Impl& operator=(const Impl&&) = delete;
std::uint16_t numberOfDataMomentGates_ {0}; std::uint16_t numberOfDataMomentGates_ {0};
std::int16_t dataMomentRange_ {0}; std::int16_t dataMomentRange_ {0};
@ -89,7 +91,9 @@ DigitalRadarDataGeneric::MomentDataBlock::number_of_data_moment_gates() const
units::kilometers<float> units::kilometers<float>
DigitalRadarDataGeneric::MomentDataBlock::data_moment_range() const DigitalRadarDataGeneric::MomentDataBlock::data_moment_range() const
{ {
return units::kilometers<float> {p->dataMomentRange_ * 0.001f}; static constexpr float kScale_ = 0.001f;
return units::kilometers<float> {static_cast<float>(p->dataMomentRange_) *
kScale_};
} }
std::int16_t std::int16_t
@ -102,7 +106,9 @@ units::kilometers<float>
DigitalRadarDataGeneric::MomentDataBlock::data_moment_range_sample_interval() DigitalRadarDataGeneric::MomentDataBlock::data_moment_range_sample_interval()
const const
{ {
return units::kilometers<float> {p->dataMomentRangeSampleInterval_ * 0.001f}; static constexpr float kScale_ = 0.001f;
return units::kilometers<float> {
static_cast<float>(p->dataMomentRangeSampleInterval_) * kScale_};
} }
std::uint16_t DigitalRadarDataGeneric::MomentDataBlock:: std::uint16_t DigitalRadarDataGeneric::MomentDataBlock::
@ -113,7 +119,8 @@ std::uint16_t DigitalRadarDataGeneric::MomentDataBlock::
float DigitalRadarDataGeneric::MomentDataBlock::snr_threshold() const float DigitalRadarDataGeneric::MomentDataBlock::snr_threshold() const
{ {
return p->snrThreshold_ * 0.1f; static constexpr float kScale_ = 0.1f;
return static_cast<float>(p->snrThreshold_) * kScale_;
} }
std::int16_t DigitalRadarDataGeneric::MomentDataBlock::snr_threshold_raw() const std::int16_t DigitalRadarDataGeneric::MomentDataBlock::snr_threshold_raw() const
@ -138,14 +145,14 @@ float DigitalRadarDataGeneric::MomentDataBlock::offset() const
const void* DigitalRadarDataGeneric::MomentDataBlock::data_moments() const const void* DigitalRadarDataGeneric::MomentDataBlock::data_moments() const
{ {
const void* dataMoments; const void* dataMoments = nullptr;
switch (p->dataWordSize_) switch (p->dataWordSize_)
{ {
case 8: case 8: // NOLINT(cppcoreguidelines-avoid-magic-numbers)
dataMoments = p->momentGates8_.data(); dataMoments = p->momentGates8_.data();
break; break;
case 16: case 16: // NOLINT(cppcoreguidelines-avoid-magic-numbers)
dataMoments = p->momentGates16_.data(); dataMoments = p->momentGates16_.data();
break; break;
default: default:
@ -190,13 +197,15 @@ bool DigitalRadarDataGeneric::MomentDataBlock::Parse(std::istream& is)
is.read(reinterpret_cast<char*>(&p->offset_), 4); // 24-27 is.read(reinterpret_cast<char*>(&p->offset_), 4); // 24-27
p->numberOfDataMomentGates_ = ntohs(p->numberOfDataMomentGates_); p->numberOfDataMomentGates_ = ntohs(p->numberOfDataMomentGates_);
p->dataMomentRange_ = ntohs(p->dataMomentRange_); p->dataMomentRange_ = static_cast<std::int16_t>(ntohs(p->dataMomentRange_));
p->dataMomentRangeSampleInterval_ = ntohs(p->dataMomentRangeSampleInterval_); p->dataMomentRangeSampleInterval_ = ntohs(p->dataMomentRangeSampleInterval_);
p->tover_ = ntohs(p->tover_); p->tover_ = ntohs(p->tover_);
p->snrThreshold_ = ntohs(p->snrThreshold_); p->snrThreshold_ = static_cast<std::int16_t>(ntohs(p->snrThreshold_));
p->scale_ = awips::Message::SwapFloat(p->scale_); p->scale_ = awips::Message::SwapFloat(p->scale_);
p->offset_ = awips::Message::SwapFloat(p->offset_); p->offset_ = awips::Message::SwapFloat(p->offset_);
// NOLINTBEGIN(cppcoreguidelines-avoid-magic-numbers)
if (p->numberOfDataMomentGates_ <= 1840) if (p->numberOfDataMomentGates_ <= 1840)
{ {
if (p->dataWordSize_ == 8) if (p->dataWordSize_ == 8)
@ -209,7 +218,7 @@ bool DigitalRadarDataGeneric::MomentDataBlock::Parse(std::istream& is)
{ {
p->momentGates16_.resize(p->numberOfDataMomentGates_); p->momentGates16_.resize(p->numberOfDataMomentGates_);
is.read(reinterpret_cast<char*>(p->momentGates16_.data()), is.read(reinterpret_cast<char*>(p->momentGates16_.data()),
p->numberOfDataMomentGates_ * 2); static_cast<std::streamsize>(p->numberOfDataMomentGates_) * 2);
awips::Message::SwapVector(p->momentGates16_); awips::Message::SwapVector(p->momentGates16_);
} }
else else
@ -225,13 +234,21 @@ bool DigitalRadarDataGeneric::MomentDataBlock::Parse(std::istream& is)
dataBlockValid = false; dataBlockValid = false;
} }
// NOLINTEND(cppcoreguidelines-avoid-magic-numbers)
return dataBlockValid; return dataBlockValid;
} }
class DigitalRadarDataGeneric::VolumeDataBlock::Impl class DigitalRadarDataGeneric::VolumeDataBlock::Impl
{ {
public: public:
explicit Impl() {} explicit Impl() = default;
~Impl() = default;
Impl(const Impl&) = delete;
Impl& operator=(const Impl&) = delete;
Impl(const Impl&&) = delete;
Impl& operator=(const Impl&&) = delete;
std::uint16_t lrtup_ {0}; std::uint16_t lrtup_ {0};
std::uint8_t versionNumberMajor_ {0}; std::uint8_t versionNumberMajor_ {0};
@ -247,6 +264,7 @@ public:
float initialSystemDifferentialPhase_ {0.0f}; float initialSystemDifferentialPhase_ {0.0f};
std::uint16_t volumeCoveragePatternNumber_ {0}; std::uint16_t volumeCoveragePatternNumber_ {0};
std::uint16_t processingStatus_ {0}; std::uint16_t processingStatus_ {0};
std::uint16_t zdrBiasEstimateWeightedMean_ {0};
}; };
DigitalRadarDataGeneric::VolumeDataBlock::VolumeDataBlock( DigitalRadarDataGeneric::VolumeDataBlock::VolumeDataBlock(
@ -320,7 +338,7 @@ bool DigitalRadarDataGeneric::VolumeDataBlock::Parse(std::istream& is)
p->lrtup_ = ntohs(p->lrtup_); p->lrtup_ = ntohs(p->lrtup_);
p->latitude_ = awips::Message::SwapFloat(p->latitude_); p->latitude_ = awips::Message::SwapFloat(p->latitude_);
p->longitude_ = awips::Message::SwapFloat(p->longitude_); p->longitude_ = awips::Message::SwapFloat(p->longitude_);
p->siteHeight_ = ntohs(p->siteHeight_); p->siteHeight_ = static_cast<std::int16_t>(ntohs(p->siteHeight_));
p->feedhornHeight_ = ntohs(p->feedhornHeight_); p->feedhornHeight_ = ntohs(p->feedhornHeight_);
p->calibrationConstant_ = awips::Message::SwapFloat(p->calibrationConstant_); p->calibrationConstant_ = awips::Message::SwapFloat(p->calibrationConstant_);
p->horizontaShvTxPower_ = awips::Message::SwapFloat(p->horizontaShvTxPower_); p->horizontaShvTxPower_ = awips::Message::SwapFloat(p->horizontaShvTxPower_);
@ -332,13 +350,35 @@ bool DigitalRadarDataGeneric::VolumeDataBlock::Parse(std::istream& is)
p->volumeCoveragePatternNumber_ = ntohs(p->volumeCoveragePatternNumber_); p->volumeCoveragePatternNumber_ = ntohs(p->volumeCoveragePatternNumber_);
p->processingStatus_ = ntohs(p->processingStatus_); p->processingStatus_ = ntohs(p->processingStatus_);
// NOLINTBEGIN(cppcoreguidelines-avoid-magic-numbers)
if (p->lrtup_ >= 46)
{
is.read(reinterpret_cast<char*>(&p->zdrBiasEstimateWeightedMean_),
2); // 44-45
p->zdrBiasEstimateWeightedMean_ = ntohs(p->zdrBiasEstimateWeightedMean_);
}
if (p->lrtup_ >= 52)
{
is.seekg(6, std::ios_base::cur); // 46-51
}
// NOLINTEND(cppcoreguidelines-avoid-magic-numbers)
return dataBlockValid; return dataBlockValid;
} }
class DigitalRadarDataGeneric::ElevationDataBlock::Impl class DigitalRadarDataGeneric::ElevationDataBlock::Impl
{ {
public: public:
explicit Impl() {} explicit Impl() = default;
~Impl() = default;
Impl(const Impl&) = delete;
Impl& operator=(const Impl&) = delete;
Impl(const Impl&&) = delete;
Impl& operator=(const Impl&&) = delete;
std::uint16_t lrtup_ {0}; std::uint16_t lrtup_ {0};
std::int16_t atmos_ {0}; std::int16_t atmos_ {0};
@ -384,7 +424,7 @@ bool DigitalRadarDataGeneric::ElevationDataBlock::Parse(std::istream& is)
is.read(reinterpret_cast<char*>(&p->calibrationConstant_), 4); // 8-11 is.read(reinterpret_cast<char*>(&p->calibrationConstant_), 4); // 8-11
p->lrtup_ = ntohs(p->lrtup_); p->lrtup_ = ntohs(p->lrtup_);
p->atmos_ = ntohs(p->atmos_); p->atmos_ = static_cast<std::int16_t>(ntohs(p->atmos_));
p->calibrationConstant_ = awips::Message::SwapFloat(p->calibrationConstant_); p->calibrationConstant_ = awips::Message::SwapFloat(p->calibrationConstant_);
return dataBlockValid; return dataBlockValid;
@ -393,7 +433,13 @@ bool DigitalRadarDataGeneric::ElevationDataBlock::Parse(std::istream& is)
class DigitalRadarDataGeneric::RadialDataBlock::Impl class DigitalRadarDataGeneric::RadialDataBlock::Impl
{ {
public: public:
explicit Impl() {} explicit Impl() = default;
~Impl() = default;
Impl(const Impl&) = delete;
Impl& operator=(const Impl&) = delete;
Impl(const Impl&&) = delete;
Impl& operator=(const Impl&&) = delete;
std::uint16_t lrtup_ {0}; std::uint16_t lrtup_ {0};
std::uint16_t unambigiousRange_ {0}; std::uint16_t unambigiousRange_ {0};
@ -420,7 +466,8 @@ DigitalRadarDataGeneric::RadialDataBlock::operator=(
float DigitalRadarDataGeneric::RadialDataBlock::unambiguous_range() const float DigitalRadarDataGeneric::RadialDataBlock::unambiguous_range() const
{ {
return p->unambigiousRange_ / 10.0f; static constexpr float kScale_ = 0.1f;
return static_cast<float>(p->unambigiousRange_) * kScale_;
} }
std::shared_ptr<DigitalRadarDataGeneric::RadialDataBlock> std::shared_ptr<DigitalRadarDataGeneric::RadialDataBlock>
@ -473,9 +520,14 @@ bool DigitalRadarDataGeneric::RadialDataBlock::Parse(std::istream& is)
class DigitalRadarDataGeneric::Impl class DigitalRadarDataGeneric::Impl
{ {
public: public:
explicit Impl() {}; explicit Impl() = default;
~Impl() = default; ~Impl() = default;
Impl(const Impl&) = delete;
Impl& operator=(const Impl&) = delete;
Impl(const Impl&&) = delete;
Impl& operator=(const Impl&&) = delete;
std::string radarIdentifier_ {}; std::string radarIdentifier_ {};
std::uint32_t collectionTime_ {0}; std::uint32_t collectionTime_ {0};
std::uint16_t modifiedJulianDate_ {0}; std::uint16_t modifiedJulianDate_ {0};
@ -491,6 +543,8 @@ public:
std::uint8_t radialSpotBlankingStatus_ {0}; std::uint8_t radialSpotBlankingStatus_ {0};
std::uint8_t azimuthIndexingMode_ {0}; std::uint8_t azimuthIndexingMode_ {0};
std::uint16_t dataBlockCount_ {0}; std::uint16_t dataBlockCount_ {0};
// NOLINTNEXTLINE(cppcoreguidelines-avoid-magic-numbers)
std::array<std::uint32_t, 10> dataBlockPointer_ {0}; std::array<std::uint32_t, 10> dataBlockPointer_ {0};
std::shared_ptr<VolumeDataBlock> volumeDataBlock_ {nullptr}; std::shared_ptr<VolumeDataBlock> volumeDataBlock_ {nullptr};
@ -666,6 +720,8 @@ bool DigitalRadarDataGeneric::Parse(std::istream& is)
p->elevationAngle_ = SwapFloat(p->elevationAngle_); p->elevationAngle_ = SwapFloat(p->elevationAngle_);
p->dataBlockCount_ = ntohs(p->dataBlockCount_); p->dataBlockCount_ = ntohs(p->dataBlockCount_);
// NOLINTBEGIN(cppcoreguidelines-avoid-magic-numbers)
if (p->azimuthNumber_ < 1 || p->azimuthNumber_ > 720) if (p->azimuthNumber_ < 1 || p->azimuthNumber_ > 720)
{ {
logger_->warn("Invalid azimuth number: {}", p->azimuthNumber_); logger_->warn("Invalid azimuth number: {}", p->azimuthNumber_);
@ -687,18 +743,22 @@ bool DigitalRadarDataGeneric::Parse(std::istream& is)
messageValid = false; messageValid = false;
} }
// NOLINTEND(cppcoreguidelines-avoid-magic-numbers)
if (!messageValid) if (!messageValid)
{ {
p->dataBlockCount_ = 0; p->dataBlockCount_ = 0;
} }
is.read(reinterpret_cast<char*>(&p->dataBlockPointer_), is.read(reinterpret_cast<char*>(&p->dataBlockPointer_),
p->dataBlockCount_ * 4); static_cast<std::streamsize>(p->dataBlockCount_) * 4);
SwapArray(p->dataBlockPointer_, p->dataBlockCount_); SwapArray(p->dataBlockPointer_, p->dataBlockCount_);
for (uint16_t b = 0; b < p->dataBlockCount_; ++b) for (uint16_t b = 0; b < p->dataBlockCount_; ++b)
{ {
// Index already has bounds check
// NOLINTNEXTLINE(cppcoreguidelines-pro-bounds-constant-array-index)
is.seekg(isBegin + std::streamoff(p->dataBlockPointer_[b]), is.seekg(isBegin + std::streamoff(p->dataBlockPointer_[b]),
std::ios_base::beg); std::ios_base::beg);
@ -771,6 +831,4 @@ DigitalRadarDataGeneric::Create(Level2MessageHeader&& header, std::istream& is)
return message; return message;
} }
} // namespace rda } // namespace scwx::wsr88d::rda
} // namespace wsr88d
} // namespace scwx

View file

@ -8,26 +8,23 @@
#include <scwx/wsr88d/rda/digital_radar_data_generic.hpp> #include <scwx/wsr88d/rda/digital_radar_data_generic.hpp>
#include <scwx/wsr88d/rda/performance_maintenance_data.hpp> #include <scwx/wsr88d/rda/performance_maintenance_data.hpp>
#include <scwx/wsr88d/rda/rda_adaptation_data.hpp> #include <scwx/wsr88d/rda/rda_adaptation_data.hpp>
#include <scwx/wsr88d/rda/rda_prf_data.hpp>
#include <scwx/wsr88d/rda/rda_status_data.hpp> #include <scwx/wsr88d/rda/rda_status_data.hpp>
#include <scwx/wsr88d/rda/volume_coverage_pattern_data.hpp> #include <scwx/wsr88d/rda/volume_coverage_pattern_data.hpp>
#include <unordered_map> #include <unordered_map>
#include <vector> #include <vector>
namespace scwx namespace scwx::wsr88d::rda
{
namespace wsr88d
{
namespace rda
{ {
static const std::string logPrefix_ = static const std::string logPrefix_ =
"scwx::wsr88d::rda::level2_message_factory"; "scwx::wsr88d::rda::level2_message_factory";
static const auto logger_ = util::Logger::Create(logPrefix_); static const auto logger_ = util::Logger::Create(logPrefix_);
typedef std::function<std::shared_ptr<Level2Message>(Level2MessageHeader&&, using CreateLevel2MessageFunction =
std::istream&)> std::function<std::shared_ptr<Level2Message>(Level2MessageHeader&&,
CreateLevel2MessageFunction; std::istream&)>;
static const std::unordered_map<unsigned int, CreateLevel2MessageFunction> static const std::unordered_map<unsigned int, CreateLevel2MessageFunction>
create_ {{1, DigitalRadarData::Create}, create_ {{1, DigitalRadarData::Create},
@ -37,20 +34,18 @@ static const std::unordered_map<unsigned int, CreateLevel2MessageFunction>
{13, ClutterFilterBypassMap::Create}, {13, ClutterFilterBypassMap::Create},
{15, ClutterFilterMap::Create}, {15, ClutterFilterMap::Create},
{18, RdaAdaptationData::Create}, {18, RdaAdaptationData::Create},
{31, DigitalRadarDataGeneric::Create}}; {31, DigitalRadarDataGeneric::Create},
{32, RdaPrfData::Create}};
struct Level2MessageFactory::Context struct Level2MessageFactory::Context
{ {
Context() : Context() :
messageData_ {}, messageBuffer_ {messageData_}, messageBufferStream_ {&messageBuffer_}
bufferedSize_ {},
messageBuffer_ {messageData_},
messageBufferStream_ {&messageBuffer_}
{ {
} }
std::vector<char> messageData_; std::vector<char> messageData_ {};
size_t bufferedSize_; std::size_t bufferedSize_ {};
util::vectorbuf messageBuffer_; util::vectorbuf messageBuffer_;
std::istream messageBufferStream_; std::istream messageBufferStream_;
bool bufferingData_ {false}; bool bufferingData_ {false};
@ -76,13 +71,16 @@ Level2MessageInfo Level2MessageFactory::Create(std::istream& is,
if (info.headerValid) if (info.headerValid)
{ {
if (header.message_size() == 65535) if (header.message_size() == std::numeric_limits<std::uint16_t>::max())
{ {
// A message size of 65535 indicates a message with a single segment.
// The size is specified in the bytes normally reserved for the segment
// number and total number of segments.
segment = 1; segment = 1;
totalSegments = 1; totalSegments = 1;
dataSize = dataSize =
(static_cast<std::size_t>(header.number_of_message_segments()) (static_cast<std::size_t>(header.number_of_message_segments())
<< 16) + << 16) + // NOLINT(cppcoreguidelines-avoid-magic-numbers)
header.message_segment_number(); header.message_segment_number();
} }
else else
@ -143,14 +141,16 @@ Level2MessageInfo Level2MessageFactory::Create(std::istream& is,
logger_->debug("Bad size estimate, increasing size"); logger_->debug("Bad size estimate, increasing size");
// Estimate remaining size // Estimate remaining size
uint16_t remainingSegments = static const std::uint16_t kMinRemainingSegments_ = 100u;
std::max<uint16_t>(totalSegments - segment + 1, 100u); const std::uint16_t remainingSegments = std::max<std::uint16_t>(
size_t remainingSize = remainingSegments * dataSize; totalSegments - segment + 1, kMinRemainingSegments_);
const std::size_t remainingSize = remainingSegments * dataSize;
ctx->messageData_.resize(ctx->bufferedSize_ + remainingSize); ctx->messageData_.resize(ctx->bufferedSize_ + remainingSize);
} }
is.read(ctx->messageData_.data() + ctx->bufferedSize_, dataSize); is.read(&ctx->messageData_[ctx->bufferedSize_],
static_cast<std::streamsize>(dataSize));
ctx->bufferedSize_ += dataSize; ctx->bufferedSize_ += dataSize;
if (is.eof()) if (is.eof())
@ -164,7 +164,7 @@ Level2MessageInfo Level2MessageFactory::Create(std::istream& is,
else if (segment == totalSegments) else if (segment == totalSegments)
{ {
ctx->messageBuffer_.update_read_pointers(ctx->bufferedSize_); ctx->messageBuffer_.update_read_pointers(ctx->bufferedSize_);
header.set_message_size(static_cast<uint16_t>( header.set_message_size(static_cast<std::uint16_t>(
ctx->bufferedSize_ / 2 + Level2MessageHeader::SIZE)); ctx->bufferedSize_ / 2 + Level2MessageHeader::SIZE));
messageStream = &ctx->messageBufferStream_; messageStream = &ctx->messageBufferStream_;
@ -186,7 +186,7 @@ Level2MessageInfo Level2MessageFactory::Create(std::istream& is,
else if (info.headerValid) else if (info.headerValid)
{ {
// Seek to the end of the current message // Seek to the end of the current message
is.seekg(dataSize, std::ios_base::cur); is.seekg(static_cast<std::streamoff>(dataSize), std::ios_base::cur);
} }
if (info.message == nullptr) if (info.message == nullptr)
@ -197,6 +197,4 @@ Level2MessageInfo Level2MessageFactory::Create(std::istream& is,
return info; return info;
} }
} // namespace rda } // namespace scwx::wsr88d::rda
} // namespace wsr88d
} // namespace scwx

File diff suppressed because it is too large Load diff

File diff suppressed because it is too large Load diff

View file

@ -0,0 +1,120 @@
#include <scwx/wsr88d/rda/rda_prf_data.hpp>
#include <scwx/util/logger.hpp>
namespace scwx::wsr88d::rda
{
static const std::string logPrefix_ = "scwx::wsr88d::rda::rda_prf_data";
static const auto logger_ = scwx::util::Logger::Create(logPrefix_);
struct RdaPrfWaveformData
{
std::uint16_t waveformType_ {0};
std::uint16_t prfCount_ {0};
std::vector<std::uint32_t> prfValues_ {};
};
class RdaPrfData::Impl
{
public:
explicit Impl() = default;
~Impl() = default;
Impl(const Impl&) = delete;
Impl& operator=(const Impl&) = delete;
Impl(const Impl&&) = delete;
Impl& operator=(const Impl&&) = delete;
std::uint16_t numberOfWaveforms_ {0};
std::vector<RdaPrfWaveformData> waveformData_ {};
};
RdaPrfData::RdaPrfData() : p(std::make_unique<Impl>()) {}
RdaPrfData::~RdaPrfData() = default;
RdaPrfData::RdaPrfData(RdaPrfData&&) noexcept = default;
RdaPrfData& RdaPrfData::operator=(RdaPrfData&&) noexcept = default;
bool RdaPrfData::Parse(std::istream& is)
{
logger_->trace("Parsing RDA PRF Data (Message Type 32)");
bool messageValid = true;
std::size_t bytesRead = 0;
const std::streampos isBegin = is.tellg();
is.read(reinterpret_cast<char*>(&p->numberOfWaveforms_), 2); // 1
is.seekg(2, std::ios_base::cur); // 2
bytesRead += 4;
p->numberOfWaveforms_ = ntohs(p->numberOfWaveforms_);
// NOLINTNEXTLINE(cppcoreguidelines-avoid-magic-numbers): Readability
if (p->numberOfWaveforms_ < 1 || p->numberOfWaveforms_ > 5)
{
logger_->warn("Invalid number of waveforms: {}", p->numberOfWaveforms_);
p->numberOfWaveforms_ = 0;
messageValid = false;
}
p->waveformData_.resize(p->numberOfWaveforms_);
for (std::uint16_t i = 0; i < p->numberOfWaveforms_; ++i)
{
auto& w = p->waveformData_[i];
is.read(reinterpret_cast<char*>(&w.waveformType_), 2); // P1
is.read(reinterpret_cast<char*>(&w.prfCount_), 2); // P2
w.waveformType_ = ntohs(w.waveformType_);
w.prfCount_ = ntohs(w.prfCount_);
bytesRead += 4;
// NOLINTNEXTLINE(cppcoreguidelines-avoid-magic-numbers): Readability
if (w.prfCount_ > 255)
{
logger_->warn("Invalid PRF count: {} (waveform {})", w.prfCount_, i);
w.prfCount_ = 0;
messageValid = false;
break;
}
w.prfValues_.resize(w.prfCount_);
for (std::uint16_t j = 0; j < w.prfCount_; ++j)
{
is.read(reinterpret_cast<char*>(&w.prfValues_[j]), 4);
}
bytesRead += static_cast<std::size_t>(w.prfCount_) * 4;
SwapVector(w.prfValues_);
}
is.seekg(isBegin, std::ios_base::beg);
if (!ValidateMessage(is, bytesRead))
{
messageValid = false;
}
return messageValid;
}
std::shared_ptr<RdaPrfData> RdaPrfData::Create(Level2MessageHeader&& header,
std::istream& is)
{
std::shared_ptr<RdaPrfData> message = std::make_shared<RdaPrfData>();
message->set_header(std::move(header));
if (!message->Parse(is))
{
message.reset();
}
return message;
}
} // namespace scwx::wsr88d::rda

View file

@ -1,232 +1,214 @@
#include <scwx/wsr88d/rda/rda_status_data.hpp> #include <scwx/wsr88d/rda/rda_status_data.hpp>
#include <scwx/util/logger.hpp> #include <scwx/util/logger.hpp>
namespace scwx namespace scwx::wsr88d::rda
{
namespace wsr88d
{
namespace rda
{ {
static const std::string logPrefix_ = "scwx::wsr88d::rda::rda_status_data"; static const std::string logPrefix_ = "scwx::wsr88d::rda::rda_status_data";
static const auto logger_ = util::Logger::Create(logPrefix_); static const auto logger_ = util::Logger::Create(logPrefix_);
class RdaStatusDataImpl class RdaStatusData::Impl
{ {
public: public:
explicit RdaStatusDataImpl() : explicit Impl() = default;
rdaStatus_ {0}, ~Impl() = default;
operabilityStatus_ {0},
controlStatus_ {0},
auxiliaryPowerGeneratorState_ {0},
averageTransmitterPower_ {0},
horizontalReflectivityCalibrationCorrection_ {0},
dataTransmissionEnabled_ {0},
volumeCoveragePatternNumber_ {0},
rdaControlAuthorization_ {0},
rdaBuildNumber_ {0},
operationalMode_ {0},
superResolutionStatus_ {0},
clutterMitigationDecisionStatus_ {0},
avsetEbcRdaLogDataStatus_ {0},
rdaAlarmSummary_ {0},
commandAcknowledgement_ {0},
channelControlStatus_ {0},
spotBlankingStatus_ {0},
bypassMapGenerationDate_ {0},
bypassMapGenerationTime_ {0},
clutterFilterMapGenerationDate_ {0},
clutterFilterMapGenerationTime_ {0},
verticalReflectivityCalibrationCorrection_ {0},
transitionPowerSourceStatus_ {0},
rmsControlStatus_ {0},
performanceCheckStatus_ {0},
alarmCodes_ {0},
signalProcessingOptions_ {0},
statusVersion_ {0} {};
~RdaStatusDataImpl() = default;
uint16_t rdaStatus_; Impl(const Impl&) = delete;
uint16_t operabilityStatus_; Impl& operator=(const Impl&) = delete;
uint16_t controlStatus_; Impl(const Impl&&) = delete;
uint16_t auxiliaryPowerGeneratorState_; Impl& operator=(const Impl&&) = delete;
uint16_t averageTransmitterPower_;
int16_t horizontalReflectivityCalibrationCorrection_; std::uint16_t rdaStatus_ {0};
uint16_t dataTransmissionEnabled_; std::uint16_t operabilityStatus_ {0};
uint16_t volumeCoveragePatternNumber_; std::uint16_t controlStatus_ {0};
uint16_t rdaControlAuthorization_; std::uint16_t auxiliaryPowerGeneratorState_ {0};
uint16_t rdaBuildNumber_; std::uint16_t averageTransmitterPower_ {0};
uint16_t operationalMode_; std::int16_t horizontalReflectivityCalibrationCorrection_ {0};
uint16_t superResolutionStatus_; std::uint16_t dataTransmissionEnabled_ {0};
uint16_t clutterMitigationDecisionStatus_; std::uint16_t volumeCoveragePatternNumber_ {0};
uint16_t avsetEbcRdaLogDataStatus_; std::uint16_t rdaControlAuthorization_ {0};
uint16_t rdaAlarmSummary_; std::uint16_t rdaBuildNumber_ {0};
uint16_t commandAcknowledgement_; std::uint16_t operationalMode_ {0};
uint16_t channelControlStatus_; std::uint16_t superResolutionStatus_ {0};
uint16_t spotBlankingStatus_; std::uint16_t clutterMitigationDecisionStatus_ {0};
uint16_t bypassMapGenerationDate_; std::uint16_t rdaScanAndDataFlags_ {0};
uint16_t bypassMapGenerationTime_; std::uint16_t rdaAlarmSummary_ {0};
uint16_t clutterFilterMapGenerationDate_; std::uint16_t commandAcknowledgement_ {0};
uint16_t clutterFilterMapGenerationTime_; std::uint16_t channelControlStatus_ {0};
int16_t verticalReflectivityCalibrationCorrection_; std::uint16_t spotBlankingStatus_ {0};
uint16_t transitionPowerSourceStatus_; std::uint16_t bypassMapGenerationDate_ {0};
uint16_t rmsControlStatus_; std::uint16_t bypassMapGenerationTime_ {0};
uint16_t performanceCheckStatus_; std::uint16_t clutterFilterMapGenerationDate_ {0};
std::array<uint16_t, 14> alarmCodes_; std::uint16_t clutterFilterMapGenerationTime_ {0};
uint16_t signalProcessingOptions_; std::int16_t verticalReflectivityCalibrationCorrection_ {0};
uint16_t statusVersion_; std::uint16_t transitionPowerSourceStatus_ {0};
std::uint16_t rmsControlStatus_ {0};
std::uint16_t performanceCheckStatus_ {0};
// NOLINTNEXTLINE(cppcoreguidelines-avoid-magic-numbers)
std::array<std::uint16_t, 14> alarmCodes_ {0};
std::uint16_t signalProcessingOptions_ {0};
std::uint16_t downloadedPatternNumber_ {0};
std::uint16_t statusVersion_ {0};
}; };
RdaStatusData::RdaStatusData() : RdaStatusData::RdaStatusData() : Level2Message(), p(std::make_unique<Impl>()) {}
Level2Message(), p(std::make_unique<RdaStatusDataImpl>())
{
}
RdaStatusData::~RdaStatusData() = default; RdaStatusData::~RdaStatusData() = default;
RdaStatusData::RdaStatusData(RdaStatusData&&) noexcept = default; RdaStatusData::RdaStatusData(RdaStatusData&&) noexcept = default;
RdaStatusData& RdaStatusData::operator=(RdaStatusData&&) noexcept = default; RdaStatusData& RdaStatusData::operator=(RdaStatusData&&) noexcept = default;
uint16_t RdaStatusData::rda_status() const std::uint16_t RdaStatusData::rda_status() const
{ {
return p->rdaStatus_; return p->rdaStatus_;
} }
uint16_t RdaStatusData::operability_status() const std::uint16_t RdaStatusData::operability_status() const
{ {
return p->operabilityStatus_; return p->operabilityStatus_;
} }
uint16_t RdaStatusData::control_status() const std::uint16_t RdaStatusData::control_status() const
{ {
return p->controlStatus_; return p->controlStatus_;
} }
uint16_t RdaStatusData::auxiliary_power_generator_state() const std::uint16_t RdaStatusData::auxiliary_power_generator_state() const
{ {
return p->auxiliaryPowerGeneratorState_; return p->auxiliaryPowerGeneratorState_;
} }
uint16_t RdaStatusData::average_transmitter_power() const std::uint16_t RdaStatusData::average_transmitter_power() const
{ {
return p->averageTransmitterPower_; return p->averageTransmitterPower_;
} }
float RdaStatusData::horizontal_reflectivity_calibration_correction() const float RdaStatusData::horizontal_reflectivity_calibration_correction() const
{ {
return p->horizontalReflectivityCalibrationCorrection_ * 0.01f; constexpr float kScale_ = 0.01f;
return static_cast<float>(p->horizontalReflectivityCalibrationCorrection_) *
kScale_;
} }
uint16_t RdaStatusData::data_transmission_enabled() const std::uint16_t RdaStatusData::data_transmission_enabled() const
{ {
return p->dataTransmissionEnabled_; return p->dataTransmissionEnabled_;
} }
uint16_t RdaStatusData::volume_coverage_pattern_number() const std::uint16_t RdaStatusData::volume_coverage_pattern_number() const
{ {
return p->volumeCoveragePatternNumber_; return p->volumeCoveragePatternNumber_;
} }
uint16_t RdaStatusData::rda_control_authorization() const std::uint16_t RdaStatusData::rda_control_authorization() const
{ {
return p->rdaControlAuthorization_; return p->rdaControlAuthorization_;
} }
uint16_t RdaStatusData::rda_build_number() const std::uint16_t RdaStatusData::rda_build_number() const
{ {
return p->rdaBuildNumber_; return p->rdaBuildNumber_;
} }
uint16_t RdaStatusData::operational_mode() const std::uint16_t RdaStatusData::operational_mode() const
{ {
return p->operationalMode_; return p->operationalMode_;
} }
uint16_t RdaStatusData::super_resolution_status() const std::uint16_t RdaStatusData::super_resolution_status() const
{ {
return p->superResolutionStatus_; return p->superResolutionStatus_;
} }
uint16_t RdaStatusData::clutter_mitigation_decision_status() const std::uint16_t RdaStatusData::clutter_mitigation_decision_status() const
{ {
return p->clutterMitigationDecisionStatus_; return p->clutterMitigationDecisionStatus_;
} }
uint16_t RdaStatusData::avset_ebc_rda_log_data_status() const std::uint16_t RdaStatusData::rda_scan_and_data_flags() const
{ {
return p->avsetEbcRdaLogDataStatus_; return p->rdaScanAndDataFlags_;
} }
uint16_t RdaStatusData::rda_alarm_summary() const std::uint16_t RdaStatusData::rda_alarm_summary() const
{ {
return p->rdaAlarmSummary_; return p->rdaAlarmSummary_;
} }
uint16_t RdaStatusData::command_acknowledgement() const std::uint16_t RdaStatusData::command_acknowledgement() const
{ {
return p->commandAcknowledgement_; return p->commandAcknowledgement_;
} }
uint16_t RdaStatusData::channel_control_status() const std::uint16_t RdaStatusData::channel_control_status() const
{ {
return p->channelControlStatus_; return p->channelControlStatus_;
} }
uint16_t RdaStatusData::spot_blanking_status() const std::uint16_t RdaStatusData::spot_blanking_status() const
{ {
return p->spotBlankingStatus_; return p->spotBlankingStatus_;
} }
uint16_t RdaStatusData::bypass_map_generation_date() const std::uint16_t RdaStatusData::bypass_map_generation_date() const
{ {
return p->bypassMapGenerationDate_; return p->bypassMapGenerationDate_;
} }
uint16_t RdaStatusData::bypass_map_generation_time() const std::uint16_t RdaStatusData::bypass_map_generation_time() const
{ {
return p->bypassMapGenerationTime_; return p->bypassMapGenerationTime_;
} }
uint16_t RdaStatusData::clutter_filter_map_generation_date() const std::uint16_t RdaStatusData::clutter_filter_map_generation_date() const
{ {
return p->clutterFilterMapGenerationDate_; return p->clutterFilterMapGenerationDate_;
} }
uint16_t RdaStatusData::clutter_filter_map_generation_time() const std::uint16_t RdaStatusData::clutter_filter_map_generation_time() const
{ {
return p->clutterFilterMapGenerationTime_; return p->clutterFilterMapGenerationTime_;
} }
float RdaStatusData::vertical_reflectivity_calibration_correction() const float RdaStatusData::vertical_reflectivity_calibration_correction() const
{ {
return p->verticalReflectivityCalibrationCorrection_ * 0.01f; constexpr float kScale_ = 0.01f;
return static_cast<float>(p->verticalReflectivityCalibrationCorrection_) *
kScale_;
} }
uint16_t RdaStatusData::transition_power_source_status() const std::uint16_t RdaStatusData::transition_power_source_status() const
{ {
return p->transitionPowerSourceStatus_; return p->transitionPowerSourceStatus_;
} }
uint16_t RdaStatusData::rms_control_status() const std::uint16_t RdaStatusData::rms_control_status() const
{ {
return p->rmsControlStatus_; return p->rmsControlStatus_;
} }
uint16_t RdaStatusData::performance_check_status() const std::uint16_t RdaStatusData::performance_check_status() const
{ {
return p->performanceCheckStatus_; return p->performanceCheckStatus_;
} }
uint16_t RdaStatusData::alarm_codes(unsigned i) const std::uint16_t RdaStatusData::alarm_codes(unsigned i) const
{ {
return p->alarmCodes_[i]; return p->alarmCodes_.at(i);
} }
uint16_t RdaStatusData::signal_processing_options() const std::uint16_t RdaStatusData::signal_processing_options() const
{ {
return p->signalProcessingOptions_; return p->signalProcessingOptions_;
} }
uint16_t RdaStatusData::status_version() const std::uint16_t RdaStatusData::downloaded_pattern_number() const
{
return p->downloadedPatternNumber_;
}
std::uint16_t RdaStatusData::status_version() const
{ {
return p->statusVersion_; return p->statusVersion_;
} }
@ -238,6 +220,7 @@ bool RdaStatusData::Parse(std::istream& is)
bool messageValid = true; bool messageValid = true;
size_t bytesRead = 0; size_t bytesRead = 0;
// NOLINTBEGIN(cppcoreguidelines-avoid-magic-numbers): Readability
is.read(reinterpret_cast<char*>(&p->rdaStatus_), 2); // 1 is.read(reinterpret_cast<char*>(&p->rdaStatus_), 2); // 1
is.read(reinterpret_cast<char*>(&p->operabilityStatus_), 2); // 2 is.read(reinterpret_cast<char*>(&p->operabilityStatus_), 2); // 2
is.read(reinterpret_cast<char*>(&p->controlStatus_), 2); // 3 is.read(reinterpret_cast<char*>(&p->controlStatus_), 2); // 3
@ -254,7 +237,7 @@ bool RdaStatusData::Parse(std::istream& is)
is.read(reinterpret_cast<char*>(&p->superResolutionStatus_), 2); // 12 is.read(reinterpret_cast<char*>(&p->superResolutionStatus_), 2); // 12
is.read(reinterpret_cast<char*>(&p->clutterMitigationDecisionStatus_), is.read(reinterpret_cast<char*>(&p->clutterMitigationDecisionStatus_),
2); // 13 2); // 13
is.read(reinterpret_cast<char*>(&p->avsetEbcRdaLogDataStatus_), 2); // 14 is.read(reinterpret_cast<char*>(&p->rdaScanAndDataFlags_), 2); // 14
is.read(reinterpret_cast<char*>(&p->rdaAlarmSummary_), 2); // 15 is.read(reinterpret_cast<char*>(&p->rdaAlarmSummary_), 2); // 15
is.read(reinterpret_cast<char*>(&p->commandAcknowledgement_), 2); // 16 is.read(reinterpret_cast<char*>(&p->commandAcknowledgement_), 2); // 16
is.read(reinterpret_cast<char*>(&p->channelControlStatus_), 2); // 17 is.read(reinterpret_cast<char*>(&p->channelControlStatus_), 2); // 17
@ -272,7 +255,7 @@ bool RdaStatusData::Parse(std::istream& is)
is.read(reinterpret_cast<char*>(&p->rmsControlStatus_), 2); // 25 is.read(reinterpret_cast<char*>(&p->rmsControlStatus_), 2); // 25
is.read(reinterpret_cast<char*>(&p->performanceCheckStatus_), 2); // 26 is.read(reinterpret_cast<char*>(&p->performanceCheckStatus_), 2); // 26
is.read(reinterpret_cast<char*>(&p->alarmCodes_), is.read(reinterpret_cast<char*>(&p->alarmCodes_),
p->alarmCodes_.size() * 2); // 27-40 static_cast<std::streamsize>(p->alarmCodes_.size() * 2)); // 27-40
bytesRead += 80; bytesRead += 80;
p->rdaStatus_ = ntohs(p->rdaStatus_); p->rdaStatus_ = ntohs(p->rdaStatus_);
@ -280,8 +263,8 @@ bool RdaStatusData::Parse(std::istream& is)
p->controlStatus_ = ntohs(p->controlStatus_); p->controlStatus_ = ntohs(p->controlStatus_);
p->auxiliaryPowerGeneratorState_ = ntohs(p->auxiliaryPowerGeneratorState_); p->auxiliaryPowerGeneratorState_ = ntohs(p->auxiliaryPowerGeneratorState_);
p->averageTransmitterPower_ = ntohs(p->averageTransmitterPower_); p->averageTransmitterPower_ = ntohs(p->averageTransmitterPower_);
p->horizontalReflectivityCalibrationCorrection_ = p->horizontalReflectivityCalibrationCorrection_ = static_cast<std::int16_t>(
ntohs(p->horizontalReflectivityCalibrationCorrection_); ntohs(p->horizontalReflectivityCalibrationCorrection_));
p->dataTransmissionEnabled_ = ntohs(p->dataTransmissionEnabled_); p->dataTransmissionEnabled_ = ntohs(p->dataTransmissionEnabled_);
p->volumeCoveragePatternNumber_ = ntohs(p->volumeCoveragePatternNumber_); p->volumeCoveragePatternNumber_ = ntohs(p->volumeCoveragePatternNumber_);
p->rdaControlAuthorization_ = ntohs(p->rdaControlAuthorization_); p->rdaControlAuthorization_ = ntohs(p->rdaControlAuthorization_);
@ -290,7 +273,7 @@ bool RdaStatusData::Parse(std::istream& is)
p->superResolutionStatus_ = ntohs(p->superResolutionStatus_); p->superResolutionStatus_ = ntohs(p->superResolutionStatus_);
p->clutterMitigationDecisionStatus_ = p->clutterMitigationDecisionStatus_ =
ntohs(p->clutterMitigationDecisionStatus_); ntohs(p->clutterMitigationDecisionStatus_);
p->avsetEbcRdaLogDataStatus_ = ntohs(p->avsetEbcRdaLogDataStatus_); p->rdaScanAndDataFlags_ = ntohs(p->rdaScanAndDataFlags_);
p->rdaAlarmSummary_ = ntohs(p->rdaAlarmSummary_); p->rdaAlarmSummary_ = ntohs(p->rdaAlarmSummary_);
p->commandAcknowledgement_ = ntohs(p->commandAcknowledgement_); p->commandAcknowledgement_ = ntohs(p->commandAcknowledgement_);
p->channelControlStatus_ = ntohs(p->channelControlStatus_); p->channelControlStatus_ = ntohs(p->channelControlStatus_);
@ -301,18 +284,20 @@ bool RdaStatusData::Parse(std::istream& is)
ntohs(p->clutterFilterMapGenerationDate_); ntohs(p->clutterFilterMapGenerationDate_);
p->clutterFilterMapGenerationTime_ = p->clutterFilterMapGenerationTime_ =
ntohs(p->clutterFilterMapGenerationTime_); ntohs(p->clutterFilterMapGenerationTime_);
p->verticalReflectivityCalibrationCorrection_ = p->verticalReflectivityCalibrationCorrection_ = static_cast<std::int16_t>(
ntohs(p->verticalReflectivityCalibrationCorrection_); ntohs(p->verticalReflectivityCalibrationCorrection_));
p->transitionPowerSourceStatus_ = ntohs(p->transitionPowerSourceStatus_); p->transitionPowerSourceStatus_ = ntohs(p->transitionPowerSourceStatus_);
p->rmsControlStatus_ = ntohs(p->rmsControlStatus_); p->rmsControlStatus_ = ntohs(p->rmsControlStatus_);
p->performanceCheckStatus_ = ntohs(p->performanceCheckStatus_); p->performanceCheckStatus_ = ntohs(p->performanceCheckStatus_);
SwapArray(p->alarmCodes_); SwapArray(p->alarmCodes_);
// RDA Build 18.0 increased the size of the message from 80 to 120 bytes // RDA Build 18.0 increased the size of the message from 80 to 120 bytes
if (header().message_size() * 2 > Level2MessageHeader::SIZE + 80) if (static_cast<std::size_t>(header().message_size()) * 2 >
Level2MessageHeader::SIZE + 80)
{ {
is.read(reinterpret_cast<char*>(&p->signalProcessingOptions_), 2); // 41 is.read(reinterpret_cast<char*>(&p->signalProcessingOptions_), 2); // 41
is.seekg(36, std::ios_base::cur); // 42-59 is.seekg(34, std::ios_base::cur); // 42-58
is.read(reinterpret_cast<char*>(&p->downloadedPatternNumber_), 2); // 59
is.read(reinterpret_cast<char*>(&p->statusVersion_), 2); // 60 is.read(reinterpret_cast<char*>(&p->statusVersion_), 2); // 60
bytesRead += 40; bytesRead += 40;
@ -320,6 +305,8 @@ bool RdaStatusData::Parse(std::istream& is)
p->statusVersion_ = ntohs(p->statusVersion_); p->statusVersion_ = ntohs(p->statusVersion_);
} }
// NOLINTEND(cppcoreguidelines-avoid-magic-numbers)
if (!ValidateMessage(is, bytesRead)) if (!ValidateMessage(is, bytesRead))
{ {
messageValid = false; messageValid = false;
@ -342,6 +329,4 @@ RdaStatusData::Create(Level2MessageHeader&& header, std::istream& is)
return message; return message;
} }
} // namespace rda } // namespace scwx::wsr88d::rda
} // namespace wsr88d
} // namespace scwx

View file

@ -0,0 +1,225 @@
#include <scwx/wsr88d/rpg/digital_raster_data_array_packet.hpp>
#include <scwx/util/logger.hpp>
#include <istream>
#include <string>
namespace scwx::wsr88d::rpg
{
static const std::string logPrefix_ =
"scwx::wsr88d::rpg::digital_raster_data_array_packet";
static const auto logger_ = util::Logger::Create(logPrefix_);
class DigitalRasterDataArrayPacket::Impl
{
public:
struct Row
{
std::uint16_t numberOfBytes_ {0};
std::vector<std::uint8_t> level_ {};
};
explicit Impl() = default;
~Impl() = default;
Impl(const Impl&) = delete;
Impl& operator=(const Impl&) = delete;
Impl(const Impl&&) = delete;
Impl& operator=(const Impl&&) = delete;
std::uint16_t packetCode_ {0};
std::uint16_t iCoordinateStart_ {0};
std::uint16_t jCoordinateStart_ {0};
std::uint16_t iScaleFactor_ {0};
std::uint16_t jScaleFactor_ {0};
std::uint16_t numberOfCells_ {0};
std::uint16_t numberOfRows_ {0};
std::uint16_t numberOfBytesInRow_ {0};
// Repeat for each row
std::vector<Row> row_ {};
std::size_t dataSize_ {0};
};
DigitalRasterDataArrayPacket::DigitalRasterDataArrayPacket() :
p(std::make_unique<Impl>())
{
}
DigitalRasterDataArrayPacket::~DigitalRasterDataArrayPacket() = default;
DigitalRasterDataArrayPacket::DigitalRasterDataArrayPacket(
DigitalRasterDataArrayPacket&&) noexcept = default;
DigitalRasterDataArrayPacket& DigitalRasterDataArrayPacket::operator=(
DigitalRasterDataArrayPacket&&) noexcept = default;
std::uint16_t DigitalRasterDataArrayPacket::packet_code() const
{
return p->packetCode_;
}
std::uint16_t DigitalRasterDataArrayPacket::i_coordinate_start() const
{
return p->iCoordinateStart_;
}
std::uint16_t DigitalRasterDataArrayPacket::j_coordinate_start() const
{
return p->jCoordinateStart_;
}
std::uint16_t DigitalRasterDataArrayPacket::i_scale_factor() const
{
return p->iScaleFactor_;
}
std::uint16_t DigitalRasterDataArrayPacket::j_scale_factor() const
{
return p->jScaleFactor_;
}
std::uint16_t DigitalRasterDataArrayPacket::number_of_cells() const
{
return p->numberOfCells_;
}
std::uint16_t DigitalRasterDataArrayPacket::number_of_rows() const
{
return p->numberOfRows_;
}
std::uint16_t
DigitalRasterDataArrayPacket::number_of_bytes_in_row(std::uint16_t r) const
{
return p->row_[r].numberOfBytes_;
}
const std::vector<std::uint8_t>&
DigitalRasterDataArrayPacket::level(std::uint16_t r) const
{
return p->row_[r].level_;
}
size_t DigitalRasterDataArrayPacket::data_size() const
{
return p->dataSize_;
}
bool DigitalRasterDataArrayPacket::Parse(std::istream& is)
{
bool blockValid = true;
std::size_t bytesRead = 0;
// NOLINTBEGIN(cppcoreguidelines-avoid-magic-numbers)
is.read(reinterpret_cast<char*>(&p->packetCode_), 2);
is.read(reinterpret_cast<char*>(&p->iCoordinateStart_), 2);
is.read(reinterpret_cast<char*>(&p->jCoordinateStart_), 2);
is.read(reinterpret_cast<char*>(&p->iScaleFactor_), 2);
is.read(reinterpret_cast<char*>(&p->jScaleFactor_), 2);
is.read(reinterpret_cast<char*>(&p->numberOfCells_), 2);
is.read(reinterpret_cast<char*>(&p->numberOfRows_), 2);
bytesRead += 14;
p->packetCode_ = ntohs(p->packetCode_);
p->iCoordinateStart_ = ntohs(p->iCoordinateStart_);
p->jCoordinateStart_ = ntohs(p->jCoordinateStart_);
p->iScaleFactor_ = ntohs(p->iScaleFactor_);
p->jScaleFactor_ = ntohs(p->jScaleFactor_);
p->numberOfCells_ = ntohs(p->numberOfCells_);
p->numberOfRows_ = ntohs(p->numberOfRows_);
if (is.eof())
{
logger_->debug("Reached end of file");
blockValid = false;
}
else
{
if (p->packetCode_ != 33)
{
logger_->warn("Invalid packet code: {}", p->packetCode_);
blockValid = false;
}
if (p->numberOfCells_ < 1 || p->numberOfCells_ > 1840)
{
logger_->warn("Invalid number of cells: {}", p->numberOfCells_);
blockValid = false;
}
if (p->numberOfRows_ < 1 || p->numberOfRows_ > 464)
{
logger_->warn("Invalid number of rows: {}", p->numberOfRows_);
blockValid = false;
}
}
if (blockValid)
{
p->row_.resize(p->numberOfRows_);
for (std::uint16_t r = 0; r < p->numberOfRows_; r++)
{
auto& row = p->row_[r];
is.read(reinterpret_cast<char*>(&row.numberOfBytes_), 2);
bytesRead += 2;
row.numberOfBytes_ = ntohs(row.numberOfBytes_);
if (row.numberOfBytes_ < 1 || row.numberOfBytes_ > 1840)
{
logger_->warn(
"Invalid number of bytes: {} (Row {})", row.numberOfBytes_, r);
blockValid = false;
break;
}
else if (row.numberOfBytes_ < p->numberOfCells_)
{
logger_->warn("Number of bytes < number of cells: {} < {} (Row {})",
row.numberOfBytes_,
p->numberOfCells_,
r);
blockValid = false;
break;
}
// Read raster bins
const std::size_t dataSize = p->numberOfCells_;
row.level_.resize(dataSize);
is.read(reinterpret_cast<char*>(row.level_.data()),
static_cast<std::streamsize>(dataSize));
is.seekg(static_cast<std::streamoff>(row.numberOfBytes_ - dataSize),
std::ios_base::cur);
bytesRead += row.numberOfBytes_;
}
}
// NOLINTEND(cppcoreguidelines-avoid-magic-numbers)
p->dataSize_ = bytesRead;
if (!ValidateMessage(is, bytesRead))
{
blockValid = false;
}
return blockValid;
}
std::shared_ptr<DigitalRasterDataArrayPacket>
DigitalRasterDataArrayPacket::Create(std::istream& is)
{
std::shared_ptr<DigitalRasterDataArrayPacket> packet =
std::make_shared<DigitalRasterDataArrayPacket>();
if (!packet->Parse(is))
{
packet.reset();
}
return packet;
}
} // namespace scwx::wsr88d::rpg

View file

@ -9,22 +9,17 @@
#include <scwx/wsr88d/rpg/tabular_product_message.hpp> #include <scwx/wsr88d/rpg/tabular_product_message.hpp>
#include <unordered_map> #include <unordered_map>
#include <vector>
namespace scwx namespace scwx::wsr88d::rpg
{
namespace wsr88d
{
namespace rpg
{ {
static const std::string logPrefix_ = static const std::string logPrefix_ =
"scwx::wsr88d::rpg::level3_message_factory"; "scwx::wsr88d::rpg::level3_message_factory";
static const auto logger_ = util::Logger::Create(logPrefix_); static const auto logger_ = util::Logger::Create(logPrefix_);
typedef std::function<std::shared_ptr<Level3Message>(Level3MessageHeader&&, using CreateLevel3MessageFunction =
std::istream&)> std::function<std::shared_ptr<Level3Message>(Level3MessageHeader&&,
CreateLevel3MessageFunction; std::istream&)>;
static const std::unordered_map<int, CreateLevel3MessageFunction> // static const std::unordered_map<int, CreateLevel3MessageFunction> //
create_ {{2, GeneralStatusMessage::Create}, create_ {{2, GeneralStatusMessage::Create},
@ -119,9 +114,14 @@ static const std::unordered_map<int, CreateLevel3MessageFunction> //
{182, GraphicProductMessage::Create}, {182, GraphicProductMessage::Create},
{184, GraphicProductMessage::Create}, {184, GraphicProductMessage::Create},
{186, GraphicProductMessage::Create}, {186, GraphicProductMessage::Create},
{189, GraphicProductMessage::Create},
{190, GraphicProductMessage::Create},
{191, GraphicProductMessage::Create},
{192, GraphicProductMessage::Create},
{193, GraphicProductMessage::Create}, {193, GraphicProductMessage::Create},
{195, GraphicProductMessage::Create}, {195, GraphicProductMessage::Create},
{196, GraphicProductMessage::Create}, {196, GraphicProductMessage::Create},
{197, GraphicProductMessage::Create},
{202, GraphicProductMessage::Create}}; {202, GraphicProductMessage::Create}};
std::shared_ptr<Level3Message> Level3MessageFactory::Create(std::istream& is) std::shared_ptr<Level3Message> Level3MessageFactory::Create(std::istream& is)
@ -149,13 +149,12 @@ std::shared_ptr<Level3Message> Level3MessageFactory::Create(std::istream& is)
else if (headerValid) else if (headerValid)
{ {
// Seek to the end of the current message // Seek to the end of the current message
is.seekg(header.length_of_message() - Level3MessageHeader::SIZE, is.seekg(static_cast<std::streamoff>(header.length_of_message()) -
static_cast<std::streamoff>(Level3MessageHeader::SIZE),
std::ios_base::cur); std::ios_base::cur);
} }
return message; return message;
} }
} // namespace rpg } // namespace scwx::wsr88d::rpg
} // namespace wsr88d
} // namespace scwx

View file

@ -5,6 +5,7 @@
#include <scwx/wsr88d/rpg/cell_trend_volume_scan_times.hpp> #include <scwx/wsr88d/rpg/cell_trend_volume_scan_times.hpp>
#include <scwx/wsr88d/rpg/digital_precipitation_data_array_packet.hpp> #include <scwx/wsr88d/rpg/digital_precipitation_data_array_packet.hpp>
#include <scwx/wsr88d/rpg/digital_radial_data_array_packet.hpp> #include <scwx/wsr88d/rpg/digital_radial_data_array_packet.hpp>
#include <scwx/wsr88d/rpg/digital_raster_data_array_packet.hpp>
#include <scwx/wsr88d/rpg/generic_data_packet.hpp> #include <scwx/wsr88d/rpg/generic_data_packet.hpp>
#include <scwx/wsr88d/rpg/hda_hail_symbol_packet.hpp> #include <scwx/wsr88d/rpg/hda_hail_symbol_packet.hpp>
#include <scwx/wsr88d/rpg/linked_contour_vector_packet.hpp> #include <scwx/wsr88d/rpg/linked_contour_vector_packet.hpp>
@ -27,18 +28,14 @@
#include <unordered_map> #include <unordered_map>
namespace scwx namespace scwx::wsr88d::rpg
{
namespace wsr88d
{
namespace rpg
{ {
static const std::string logPrefix_ = "scwx::wsr88d::rpg::packet_factory"; static const std::string logPrefix_ = "scwx::wsr88d::rpg::packet_factory";
static const auto logger_ = util::Logger::Create(logPrefix_); static const auto logger_ = util::Logger::Create(logPrefix_);
typedef std::function<std::shared_ptr<Packet>(std::istream&)> using CreateMessageFunction =
CreateMessageFunction; std::function<std::shared_ptr<Packet>(std::istream&)>;
static const std::unordered_map<unsigned int, CreateMessageFunction> create_ { static const std::unordered_map<unsigned int, CreateMessageFunction> create_ {
{1, TextAndSpecialSymbolPacket::Create}, {1, TextAndSpecialSymbolPacket::Create},
@ -69,6 +66,7 @@ static const std::unordered_map<unsigned int, CreateMessageFunction> create_ {
{26, PointGraphicSymbolPacket::Create}, {26, PointGraphicSymbolPacket::Create},
{28, GenericDataPacket::Create}, {28, GenericDataPacket::Create},
{29, GenericDataPacket::Create}, {29, GenericDataPacket::Create},
{33, DigitalRasterDataArrayPacket::Create},
{0x0802, SetColorLevelPacket::Create}, {0x0802, SetColorLevelPacket::Create},
{0x0E03, LinkedContourVectorPacket::Create}, {0x0E03, LinkedContourVectorPacket::Create},
{0x3501, UnlinkedContourVectorPacket::Create}, {0x3501, UnlinkedContourVectorPacket::Create},
@ -81,7 +79,7 @@ std::shared_ptr<Packet> PacketFactory::Create(std::istream& is)
std::shared_ptr<Packet> packet = nullptr; std::shared_ptr<Packet> packet = nullptr;
bool packetValid = true; bool packetValid = true;
uint16_t packetCode; std::uint16_t packetCode {0};
is.read(reinterpret_cast<char*>(&packetCode), 2); is.read(reinterpret_cast<char*>(&packetCode), 2);
packetCode = ntohs(packetCode); packetCode = ntohs(packetCode);
@ -108,6 +106,4 @@ std::shared_ptr<Packet> PacketFactory::Create(std::istream& is)
return packet; return packet;
} }
} // namespace rpg } // namespace scwx::wsr88d::rpg
} // namespace wsr88d
} // namespace scwx

View file

@ -1,3 +1,4 @@
#include <cstddef>
#include <scwx/wsr88d/rpg/product_description_block.hpp> #include <scwx/wsr88d/rpg/product_description_block.hpp>
#include <scwx/util/float.hpp> #include <scwx/util/float.hpp>
#include <scwx/util/logger.hpp> #include <scwx/util/logger.hpp>
@ -21,28 +22,13 @@ static const std::string logPrefix_ =
static const auto logger_ = util::Logger::Create(logPrefix_); static const auto logger_ = util::Logger::Create(logPrefix_);
static const std::set<int> compressedProducts_ = { static const std::set<int> compressedProducts_ = {
32, 94, 99, 134, 135, 138, 149, 152, 153, 154, 155, 32, 94, 99, 113, 134, 135, 138, 149, 152, 153, 154, 155, 159,
159, 161, 163, 165, 167, 168, 170, 172, 173, 174, 175, 161, 163, 165, 167, 168, 170, 172, 173, 174, 175, 176, 177, 178,
176, 177, 178, 179, 180, 182, 186, 193, 195, 202}; 179, 180, 182, 186, 189, 190, 191, 192, 193, 195, 197, 202};
static const std::set<int> uncodedDataLevelProducts_ = {32, static const std::set<int> uncodedDataLevelProducts_ = {
34, 32, 34, 81, 93, 94, 99, 134, 135, 138, 153, 154, 155,
81, 159, 161, 163, 177, 189, 190, 191, 192, 193, 195, 197};
93,
94,
99,
134,
135,
138,
153,
154,
155,
159,
161,
163,
177,
193,
195};
static const std::unordered_map<int, unsigned int> rangeMap_ { static const std::unordered_map<int, unsigned int> rangeMap_ {
{19, 230}, {20, 460}, {27, 230}, {30, 230}, {31, 230}, {32, 230}, {19, 230}, {20, 460}, {27, 230}, {30, 230}, {31, 230}, {32, 230},
@ -57,7 +43,8 @@ static const std::unordered_map<int, unsigned int> rangeMap_ {
{163, 300}, {165, 300}, {166, 230}, {167, 300}, {168, 300}, {169, 230}, {163, 300}, {165, 300}, {166, 230}, {167, 300}, {168, 300}, {169, 230},
{170, 230}, {171, 230}, {172, 230}, {173, 230}, {174, 230}, {175, 230}, {170, 230}, {171, 230}, {172, 230}, {173, 230}, {174, 230}, {175, 230},
{176, 230}, {177, 230}, {178, 300}, {179, 300}, {180, 89}, {181, 89}, {176, 230}, {177, 230}, {178, 300}, {179, 300}, {180, 89}, {181, 89},
{182, 89}, {184, 89}, {186, 417}, {193, 460}, {195, 460}, {196, 50}}; {182, 89}, {184, 89}, {186, 417}, {193, 460}, {195, 460}, {196, 50},
{197, 230}};
static const std::unordered_map<int, unsigned int> xResolutionMap_ { static const std::unordered_map<int, unsigned int> xResolutionMap_ {
{19, 1000}, {20, 2000}, {27, 1000}, {30, 1000}, {31, 2000}, {32, 1000}, {19, 1000}, {20, 2000}, {27, 1000}, {30, 1000}, {31, 2000}, {32, 1000},
@ -71,7 +58,7 @@ static const std::unordered_map<int, unsigned int> xResolutionMap_ {
{166, 250}, {167, 250}, {168, 250}, {169, 2000}, {170, 250}, {171, 2000}, {166, 250}, {167, 250}, {168, 250}, {169, 2000}, {170, 250}, {171, 2000},
{172, 250}, {173, 250}, {174, 250}, {175, 250}, {176, 250}, {177, 250}, {172, 250}, {173, 250}, {174, 250}, {175, 250}, {176, 250}, {177, 250},
{178, 1000}, {179, 1000}, {180, 150}, {181, 150}, {182, 150}, {184, 150}, {178, 1000}, {179, 1000}, {180, 150}, {181, 150}, {182, 150}, {184, 150},
{186, 300}, {193, 250}, {195, 1000}}; {186, 300}, {193, 250}, {195, 1000}, {197, 250}};
static const std::unordered_map<int, unsigned int> yResolutionMap_ {{37, 1000}, static const std::unordered_map<int, unsigned int> yResolutionMap_ {{37, 1000},
{38, 4000}, {38, 4000},
@ -86,7 +73,11 @@ static const std::unordered_map<int, unsigned int> yResolutionMap_ {{37, 1000},
{90, 4000}, {90, 4000},
{97, 1000}, {97, 1000},
{98, 4000}, {98, 4000},
{166, 250}}; {166, 250},
{189, 20},
{190, 20},
{191, 20},
{192, 20}};
// GR uses different internal units than defined units in level 3 products // GR uses different internal units than defined units in level 3 products
static const std::unordered_map<std::int16_t, float> grScale_ { static const std::unordered_map<std::int16_t, float> grScale_ {
@ -105,73 +96,57 @@ static const std::unordered_map<std::int16_t, float> grScale_ {
{174, ((units::inches<float> {1} * 0.01f) / units::millimeters<float> {1})}, {174, ((units::inches<float> {1} * 0.01f) / units::millimeters<float> {1})},
{175, ((units::inches<float> {1} * 0.01f) / units::millimeters<float> {1})}}; {175, ((units::inches<float> {1} * 0.01f) / units::millimeters<float> {1})}};
class ProductDescriptionBlockImpl class ProductDescriptionBlock::Impl
{ {
public: public:
explicit ProductDescriptionBlockImpl() : explicit Impl() = default;
blockDivider_ {0}, ~Impl() = default;
latitudeOfRadar_ {0},
longitudeOfRadar_ {0},
heightOfRadar_ {0},
productCode_ {0},
operationalMode_ {0},
volumeCoveragePattern_ {0},
sequenceNumber_ {0},
volumeScanNumber_ {0},
volumeScanDate_ {0},
volumeScanStartTime_ {0},
generationDateOfProduct_ {0},
generationTimeOfProduct_ {0},
elevationNumber_ {0},
version_ {0},
spotBlank_ {0},
offsetToSymbology_ {0},
offsetToGraphic_ {0},
offsetToTabular_ {0},
parameters_ {0},
halfwords_ {0}
{
}
~ProductDescriptionBlockImpl() = default;
uint16_t halfword(size_t i); Impl(const Impl&) = delete;
Impl& operator=(const Impl&) = delete;
Impl(const Impl&&) = delete;
Impl& operator=(const Impl&&) = delete;
int16_t blockDivider_; std::uint16_t halfword(std::size_t i);
int32_t latitudeOfRadar_;
int32_t longitudeOfRadar_; std::int16_t blockDivider_ {0};
int16_t heightOfRadar_; std::int32_t latitudeOfRadar_ {0};
int16_t productCode_; std::int32_t longitudeOfRadar_ {0};
uint16_t operationalMode_; std::int16_t heightOfRadar_ {0};
uint16_t volumeCoveragePattern_; std::int16_t productCode_ {0};
int16_t sequenceNumber_; std::uint16_t operationalMode_ {0};
uint16_t volumeScanNumber_; std::uint16_t volumeCoveragePattern_ {0};
uint16_t volumeScanDate_; std::int16_t sequenceNumber_ {0};
uint32_t volumeScanStartTime_; std::uint16_t volumeScanNumber_ {0};
uint16_t generationDateOfProduct_; std::uint16_t volumeScanDate_ {0};
uint32_t generationTimeOfProduct_; std::uint32_t volumeScanStartTime_ {0};
std::uint16_t generationDateOfProduct_ {0};
std::uint32_t generationTimeOfProduct_ {0};
// 27-28: Product dependent parameters 1 and 2 (Table V) // 27-28: Product dependent parameters 1 and 2 (Table V)
uint16_t elevationNumber_; std::uint16_t elevationNumber_ {0};
// 30: Product dependent parameter 3 (Table V) // 30: Product dependent parameter 3 (Table V)
// 31-46: Product dependent (Note 1) // 31-46: Product dependent (Note 1)
// 47-53: Product dependent parameters 4-10 (Table V, Note 3) // 47-53: Product dependent parameters 4-10 (Table V, Note 3)
uint8_t version_; std::uint8_t version_ {0};
uint8_t spotBlank_; std::uint8_t spotBlank_ {0};
uint32_t offsetToSymbology_; std::uint32_t offsetToSymbology_ {0};
uint32_t offsetToGraphic_; std::uint32_t offsetToGraphic_ {0};
uint32_t offsetToTabular_; std::uint32_t offsetToTabular_ {0};
std::array<uint16_t, 10> parameters_; // NOLINTBEGIN(cppcoreguidelines-avoid-magic-numbers)
std::array<uint16_t, 16> halfwords_; std::array<std::uint16_t, 10> parameters_ {0};
std::array<std::uint16_t, 16> halfwords_ {0};
// NOLINTEND(cppcoreguidelines-avoid-magic-numbers)
}; };
uint16_t ProductDescriptionBlockImpl::halfword(size_t i) std::uint16_t ProductDescriptionBlock::Impl::halfword(std::size_t i)
{ {
// Halfwords start at halfword 31 // Halfwords start at halfword 31
return halfwords_[i - 31]; // NOLINTNEXTLINE(cppcoreguidelines-avoid-magic-numbers)
return halfwords_.at(i - 31);
} }
ProductDescriptionBlock::ProductDescriptionBlock() : ProductDescriptionBlock::ProductDescriptionBlock() : p(std::make_unique<Impl>())
p(std::make_unique<ProductDescriptionBlockImpl>())
{ {
} }
ProductDescriptionBlock::~ProductDescriptionBlock() = default; ProductDescriptionBlock::~ProductDescriptionBlock() = default;
@ -181,102 +156,104 @@ ProductDescriptionBlock::ProductDescriptionBlock(
ProductDescriptionBlock& ProductDescriptionBlock::operator=( ProductDescriptionBlock& ProductDescriptionBlock::operator=(
ProductDescriptionBlock&&) noexcept = default; ProductDescriptionBlock&&) noexcept = default;
int16_t ProductDescriptionBlock::block_divider() const std::int16_t ProductDescriptionBlock::block_divider() const
{ {
return p->blockDivider_; return p->blockDivider_;
} }
float ProductDescriptionBlock::latitude_of_radar() const float ProductDescriptionBlock::latitude_of_radar() const
{ {
return p->latitudeOfRadar_ * 0.001f; static constexpr float kScale = 0.001f;
return static_cast<float>(p->latitudeOfRadar_) * kScale;
} }
float ProductDescriptionBlock::longitude_of_radar() const float ProductDescriptionBlock::longitude_of_radar() const
{ {
return p->longitudeOfRadar_ * 0.001f; static constexpr float kScale = 0.001f;
return static_cast<float>(p->longitudeOfRadar_) * kScale;
} }
int16_t ProductDescriptionBlock::height_of_radar() const std::int16_t ProductDescriptionBlock::height_of_radar() const
{ {
return p->heightOfRadar_; return p->heightOfRadar_;
} }
int16_t ProductDescriptionBlock::product_code() const std::int16_t ProductDescriptionBlock::product_code() const
{ {
return p->productCode_; return p->productCode_;
} }
uint16_t ProductDescriptionBlock::operational_mode() const std::uint16_t ProductDescriptionBlock::operational_mode() const
{ {
return p->operationalMode_; return p->operationalMode_;
} }
uint16_t ProductDescriptionBlock::volume_coverage_pattern() const std::uint16_t ProductDescriptionBlock::volume_coverage_pattern() const
{ {
return p->volumeCoveragePattern_; return p->volumeCoveragePattern_;
} }
int16_t ProductDescriptionBlock::sequence_number() const std::int16_t ProductDescriptionBlock::sequence_number() const
{ {
return p->sequenceNumber_; return p->sequenceNumber_;
} }
uint16_t ProductDescriptionBlock::volume_scan_number() const std::uint16_t ProductDescriptionBlock::volume_scan_number() const
{ {
return p->volumeScanNumber_; return p->volumeScanNumber_;
} }
uint16_t ProductDescriptionBlock::volume_scan_date() const std::uint16_t ProductDescriptionBlock::volume_scan_date() const
{ {
return p->volumeScanDate_; return p->volumeScanDate_;
} }
uint32_t ProductDescriptionBlock::volume_scan_start_time() const std::uint32_t ProductDescriptionBlock::volume_scan_start_time() const
{ {
return p->volumeScanStartTime_; return p->volumeScanStartTime_;
} }
uint16_t ProductDescriptionBlock::generation_date_of_product() const std::uint16_t ProductDescriptionBlock::generation_date_of_product() const
{ {
return p->generationDateOfProduct_; return p->generationDateOfProduct_;
} }
uint32_t ProductDescriptionBlock::generation_time_of_product() const std::uint32_t ProductDescriptionBlock::generation_time_of_product() const
{ {
return p->generationTimeOfProduct_; return p->generationTimeOfProduct_;
} }
uint16_t ProductDescriptionBlock::elevation_number() const std::uint16_t ProductDescriptionBlock::elevation_number() const
{ {
return p->elevationNumber_; return p->elevationNumber_;
} }
uint16_t ProductDescriptionBlock::data_level_threshold(size_t i) const std::uint16_t ProductDescriptionBlock::data_level_threshold(std::size_t i) const
{ {
return p->halfwords_[i]; return p->halfwords_.at(i);
} }
uint8_t ProductDescriptionBlock::version() const std::uint8_t ProductDescriptionBlock::version() const
{ {
return p->version_; return p->version_;
} }
uint8_t ProductDescriptionBlock::spot_blank() const std::uint8_t ProductDescriptionBlock::spot_blank() const
{ {
return p->spotBlank_; return p->spotBlank_;
} }
uint32_t ProductDescriptionBlock::offset_to_symbology() const std::uint32_t ProductDescriptionBlock::offset_to_symbology() const
{ {
return p->offsetToSymbology_; return p->offsetToSymbology_;
} }
uint32_t ProductDescriptionBlock::offset_to_graphic() const std::uint32_t ProductDescriptionBlock::offset_to_graphic() const
{ {
return p->offsetToGraphic_; return p->offsetToGraphic_;
} }
uint32_t ProductDescriptionBlock::offset_to_tabular() const std::uint32_t ProductDescriptionBlock::offset_to_tabular() const
{ {
return p->offsetToTabular_; return p->offsetToTabular_;
} }
@ -286,14 +263,14 @@ float ProductDescriptionBlock::range() const
return range_raw(); return range_raw();
} }
uint16_t ProductDescriptionBlock::range_raw() const std::uint16_t ProductDescriptionBlock::range_raw() const
{ {
uint16_t range = 0; std::uint16_t range = 0;
auto it = rangeMap_.find(p->productCode_); auto it = rangeMap_.find(p->productCode_);
if (it != rangeMap_.cend()) if (it != rangeMap_.cend())
{ {
range = static_cast<uint16_t>(it->second); range = static_cast<std::uint16_t>(it->second);
} }
return range; return range;
@ -301,17 +278,18 @@ uint16_t ProductDescriptionBlock::range_raw() const
float ProductDescriptionBlock::x_resolution() const float ProductDescriptionBlock::x_resolution() const
{ {
return x_resolution_raw() * 0.001f; static constexpr float kScale = 0.001f;
return static_cast<float>(x_resolution_raw()) * kScale;
} }
uint16_t ProductDescriptionBlock::x_resolution_raw() const std::uint16_t ProductDescriptionBlock::x_resolution_raw() const
{ {
uint16_t xResolution = 0; std::uint16_t xResolution = 0;
auto it = xResolutionMap_.find(p->productCode_); auto it = xResolutionMap_.find(p->productCode_);
if (it != xResolutionMap_.cend()) if (it != xResolutionMap_.cend())
{ {
xResolution = static_cast<uint16_t>(it->second); xResolution = static_cast<std::uint16_t>(it->second);
} }
return xResolution; return xResolution;
@ -319,25 +297,28 @@ uint16_t ProductDescriptionBlock::x_resolution_raw() const
float ProductDescriptionBlock::y_resolution() const float ProductDescriptionBlock::y_resolution() const
{ {
return y_resolution_raw() * 0.001f; static constexpr float kScale = 0.001f;
return static_cast<float>(y_resolution_raw()) * kScale;
} }
uint16_t ProductDescriptionBlock::y_resolution_raw() const std::uint16_t ProductDescriptionBlock::y_resolution_raw() const
{ {
uint16_t yResolution = 0; std::uint16_t yResolution = 0;
auto it = yResolutionMap_.find(p->productCode_); auto it = yResolutionMap_.find(p->productCode_);
if (it != yResolutionMap_.cend()) if (it != yResolutionMap_.cend())
{ {
yResolution = static_cast<uint16_t>(it->second); yResolution = static_cast<std::uint16_t>(it->second);
} }
return yResolution; return yResolution;
} }
uint16_t ProductDescriptionBlock::threshold() const std::uint16_t ProductDescriptionBlock::threshold() const
{ {
uint16_t threshold = 1; std::uint16_t threshold = 1;
// NOLINTBEGIN(cppcoreguidelines-avoid-magic-numbers)
switch (p->productCode_) switch (p->productCode_)
{ {
@ -394,6 +375,8 @@ uint16_t ProductDescriptionBlock::threshold() const
break; break;
} }
// NOLINTEND(cppcoreguidelines-avoid-magic-numbers)
return threshold; return threshold;
} }
@ -401,6 +384,8 @@ float ProductDescriptionBlock::offset() const
{ {
float offset = 0.0f; float offset = 0.0f;
// NOLINTBEGIN(cppcoreguidelines-avoid-magic-numbers)
switch (p->productCode_) switch (p->productCode_)
{ {
case 32: case 32:
@ -416,7 +401,8 @@ float ProductDescriptionBlock::offset() const
case 186: case 186:
case 193: case 193:
case 195: case 195:
offset = static_cast<int16_t>(p->halfword(31)) * 0.1f; offset =
static_cast<float>(static_cast<std::int16_t>(p->halfword(31))) * 0.1f;
break; break;
case 134: case 134:
@ -424,7 +410,7 @@ float ProductDescriptionBlock::offset() const
break; break;
case 135: case 135:
offset = static_cast<int16_t>(p->halfword(33)); offset = static_cast<std::int16_t>(p->halfword(33));
break; break;
case 159: case 159:
@ -445,6 +431,8 @@ float ProductDescriptionBlock::offset() const
break; break;
} }
// NOLINTEND(cppcoreguidelines-avoid-magic-numbers)
return offset; return offset;
} }
@ -452,6 +440,8 @@ float ProductDescriptionBlock::scale() const
{ {
float scale = 1.0f; float scale = 1.0f;
// NOLINTBEGIN(cppcoreguidelines-avoid-magic-numbers)
switch (p->productCode_) switch (p->productCode_)
{ {
case 32: case 32:
@ -466,11 +456,11 @@ float ProductDescriptionBlock::scale() const
case 186: case 186:
case 193: case 193:
case 195: case 195:
scale = p->halfword(32) * 0.1f; scale = static_cast<float>(p->halfword(32)) * 0.1f;
break; break;
case 81: case 81:
scale = p->halfword(32) * 0.001f; scale = static_cast<float>(p->halfword(32)) * 0.001f;
break; break;
case 134: case 134:
@ -482,7 +472,7 @@ float ProductDescriptionBlock::scale() const
break; break;
case 138: case 138:
scale = p->halfword(32) * 0.01f; scale = static_cast<float>(p->halfword(32)) * 0.01f;
break; break;
case 159: case 159:
@ -503,12 +493,16 @@ float ProductDescriptionBlock::scale() const
break; break;
} }
// NOLINTEND(cppcoreguidelines-avoid-magic-numbers)
return scale; return scale;
} }
uint16_t ProductDescriptionBlock::number_of_levels() const std::uint16_t ProductDescriptionBlock::number_of_levels() const
{ {
uint16_t numberOfLevels = 16u; // NOLINTBEGIN(cppcoreguidelines-avoid-magic-numbers)
std::uint16_t numberOfLevels = 16u;
switch (p->productCode_) switch (p->productCode_)
{ {
@ -580,6 +574,10 @@ uint16_t ProductDescriptionBlock::number_of_levels() const
break; break;
case 134: case 134:
case 189:
case 190:
case 191:
case 192:
numberOfLevels = 256; numberOfLevels = 256;
break; break;
@ -619,6 +617,8 @@ uint16_t ProductDescriptionBlock::number_of_levels() const
break; break;
} }
// NOLINTEND(cppcoreguidelines-avoid-magic-numbers)
return numberOfLevels; return numberOfLevels;
} }
@ -626,6 +626,8 @@ std::uint16_t ProductDescriptionBlock::log_start() const
{ {
std::uint16_t logStart = std::numeric_limits<std::uint16_t>::max(); std::uint16_t logStart = std::numeric_limits<std::uint16_t>::max();
// NOLINTBEGIN(cppcoreguidelines-avoid-magic-numbers)
switch (p->productCode_) switch (p->productCode_)
{ {
case 134: case 134:
@ -636,6 +638,8 @@ std::uint16_t ProductDescriptionBlock::log_start() const
break; break;
} }
// NOLINTEND(cppcoreguidelines-avoid-magic-numbers)
return logStart; return logStart;
} }
@ -643,6 +647,8 @@ float ProductDescriptionBlock::log_offset() const
{ {
float logOffset = 0.0f; float logOffset = 0.0f;
// NOLINTBEGIN(cppcoreguidelines-avoid-magic-numbers)
switch (p->productCode_) switch (p->productCode_)
{ {
case 134: case 134:
@ -653,6 +659,8 @@ float ProductDescriptionBlock::log_offset() const
break; break;
} }
// NOLINTEND(cppcoreguidelines-avoid-magic-numbers)
return logOffset; return logOffset;
} }
@ -660,6 +668,8 @@ float ProductDescriptionBlock::log_scale() const
{ {
float logScale = 1.0f; float logScale = 1.0f;
// NOLINTBEGIN(cppcoreguidelines-avoid-magic-numbers)
switch (p->productCode_) switch (p->productCode_)
{ {
case 134: case 134:
@ -670,6 +680,8 @@ float ProductDescriptionBlock::log_scale() const
break; break;
} }
// NOLINTEND(cppcoreguidelines-avoid-magic-numbers)
return logScale; return logScale;
} }
@ -688,6 +700,8 @@ float ProductDescriptionBlock::gr_scale() const
std::uint8_t ProductDescriptionBlock::data_mask() const std::uint8_t ProductDescriptionBlock::data_mask() const
{ {
// NOLINTBEGIN(cppcoreguidelines-avoid-magic-numbers)
std::uint8_t dataMask = 0xff; std::uint8_t dataMask = 0xff;
switch (p->productCode_) switch (p->productCode_)
@ -700,6 +714,8 @@ std::uint8_t ProductDescriptionBlock::data_mask() const
break; break;
} }
// NOLINTEND(cppcoreguidelines-avoid-magic-numbers)
return dataMask; return dataMask;
} }
@ -707,6 +723,8 @@ std::uint8_t ProductDescriptionBlock::topped_mask() const
{ {
std::uint8_t toppedMask = 0x00; std::uint8_t toppedMask = 0x00;
// NOLINTBEGIN(cppcoreguidelines-avoid-magic-numbers)
switch (p->productCode_) switch (p->productCode_)
{ {
case 135: case 135:
@ -717,6 +735,8 @@ std::uint8_t ProductDescriptionBlock::topped_mask() const
break; break;
} }
// NOLINTEND(cppcoreguidelines-avoid-magic-numbers)
return toppedMask; return toppedMask;
} }
@ -728,7 +748,7 @@ units::angle::degrees<double> ProductDescriptionBlock::elevation() const
{ {
// Elevation is given in tenths of a degree // Elevation is given in tenths of a degree
// NOLINTNEXTLINE(cppcoreguidelines-avoid-magic-numbers) // NOLINTNEXTLINE(cppcoreguidelines-avoid-magic-numbers)
elevation = static_cast<int16_t>(p->parameters_[2]) * 0.1; elevation = static_cast<std::int16_t>(p->parameters_[2]) * 0.1;
} }
return units::angle::degrees<double> {elevation}; return units::angle::degrees<double> {elevation};
@ -743,11 +763,15 @@ bool ProductDescriptionBlock::IsCompressionEnabled() const
{ {
bool isCompressed = false; bool isCompressed = false;
// NOLINTBEGIN(cppcoreguidelines-avoid-magic-numbers)
if (compressedProducts_.contains(p->productCode_)) if (compressedProducts_.contains(p->productCode_))
{ {
isCompressed = (p->parameters_[7] == 1u); isCompressed = (p->parameters_[7] == 1u);
} }
// NOLINTEND(cppcoreguidelines-avoid-magic-numbers)
return isCompressed; return isCompressed;
} }
@ -756,7 +780,7 @@ bool ProductDescriptionBlock::IsDataLevelCoded() const
return !uncodedDataLevelProducts_.contains(p->productCode_); return !uncodedDataLevelProducts_.contains(p->productCode_);
} }
size_t ProductDescriptionBlock::data_size() const std::size_t ProductDescriptionBlock::data_size() const
{ {
return SIZE; return SIZE;
} }
@ -767,6 +791,8 @@ bool ProductDescriptionBlock::Parse(std::istream& is)
const std::streampos blockStart = is.tellg(); const std::streampos blockStart = is.tellg();
// NOLINTBEGIN(cppcoreguidelines-avoid-magic-numbers)
is.read(reinterpret_cast<char*>(&p->blockDivider_), 2); // 10 is.read(reinterpret_cast<char*>(&p->blockDivider_), 2); // 10
is.read(reinterpret_cast<char*>(&p->latitudeOfRadar_), 4); // 11-12 is.read(reinterpret_cast<char*>(&p->latitudeOfRadar_), 4); // 11-12
is.read(reinterpret_cast<char*>(&p->longitudeOfRadar_), 4); // 13-14 is.read(reinterpret_cast<char*>(&p->longitudeOfRadar_), 4); // 13-14
@ -780,25 +806,29 @@ bool ProductDescriptionBlock::Parse(std::istream& is)
is.read(reinterpret_cast<char*>(&p->volumeScanStartTime_), 4); // 22-23 is.read(reinterpret_cast<char*>(&p->volumeScanStartTime_), 4); // 22-23
is.read(reinterpret_cast<char*>(&p->generationDateOfProduct_), 2); // 24 is.read(reinterpret_cast<char*>(&p->generationDateOfProduct_), 2); // 24
is.read(reinterpret_cast<char*>(&p->generationTimeOfProduct_), 4); // 25-26 is.read(reinterpret_cast<char*>(&p->generationTimeOfProduct_), 4); // 25-26
is.read(reinterpret_cast<char*>(&p->parameters_[0]), 2 * 2); // 27-28 is.read(reinterpret_cast<char*>(&p->parameters_[0]),
static_cast<std::streamsize>(2 * 2)); // 27-28
is.read(reinterpret_cast<char*>(&p->elevationNumber_), 2); // 29 is.read(reinterpret_cast<char*>(&p->elevationNumber_), 2); // 29
is.read(reinterpret_cast<char*>(&p->parameters_[2]), 2); // 30 is.read(reinterpret_cast<char*>(&p->parameters_[2]), 2); // 30
is.read(reinterpret_cast<char*>(&p->halfwords_[0]), 16 * 2); // 31-46 is.read(reinterpret_cast<char*>(&p->halfwords_[0]),
is.read(reinterpret_cast<char*>(&p->parameters_[3]), 7 * 2); // 47-53 static_cast<std::streamsize>(16 * 2)); // 31-46
is.read(reinterpret_cast<char*>(&p->parameters_[3]),
static_cast<std::streamsize>(7 * 2)); // 47-53
is.read(reinterpret_cast<char*>(&p->version_), 1); // 54 is.read(reinterpret_cast<char*>(&p->version_), 1); // 54
is.read(reinterpret_cast<char*>(&p->spotBlank_), 1); // 54 is.read(reinterpret_cast<char*>(&p->spotBlank_), 1); // 54
is.read(reinterpret_cast<char*>(&p->offsetToSymbology_), 4); // 55-56 is.read(reinterpret_cast<char*>(&p->offsetToSymbology_), 4); // 55-56
is.read(reinterpret_cast<char*>(&p->offsetToGraphic_), 4); // 57-58 is.read(reinterpret_cast<char*>(&p->offsetToGraphic_), 4); // 57-58
is.read(reinterpret_cast<char*>(&p->offsetToTabular_), 4); // 59-60 is.read(reinterpret_cast<char*>(&p->offsetToTabular_), 4); // 59-60
p->blockDivider_ = ntohs(p->blockDivider_); p->blockDivider_ = static_cast<std::int16_t>(ntohs(p->blockDivider_));
p->latitudeOfRadar_ = ntohl(p->latitudeOfRadar_); p->latitudeOfRadar_ = static_cast<std::int32_t>(ntohl(p->latitudeOfRadar_));
p->longitudeOfRadar_ = ntohl(p->longitudeOfRadar_); p->longitudeOfRadar_ =
p->heightOfRadar_ = ntohs(p->heightOfRadar_); static_cast<std::int32_t>(ntohl(p->longitudeOfRadar_));
p->productCode_ = ntohs(p->productCode_); p->heightOfRadar_ = static_cast<std::int16_t>(ntohs(p->heightOfRadar_));
p->productCode_ = static_cast<std::int16_t>(ntohs(p->productCode_));
p->operationalMode_ = ntohs(p->operationalMode_); p->operationalMode_ = ntohs(p->operationalMode_);
p->volumeCoveragePattern_ = ntohs(p->volumeCoveragePattern_); p->volumeCoveragePattern_ = ntohs(p->volumeCoveragePattern_);
p->sequenceNumber_ = ntohs(p->sequenceNumber_); p->sequenceNumber_ = static_cast<std::int16_t>(ntohs(p->sequenceNumber_));
p->volumeScanNumber_ = ntohs(p->volumeScanNumber_); p->volumeScanNumber_ = ntohs(p->volumeScanNumber_);
p->volumeScanDate_ = ntohs(p->volumeScanDate_); p->volumeScanDate_ = ntohs(p->volumeScanDate_);
p->volumeScanStartTime_ = ntohl(p->volumeScanStartTime_); p->volumeScanStartTime_ = ntohl(p->volumeScanStartTime_);
@ -833,6 +863,8 @@ bool ProductDescriptionBlock::Parse(std::istream& is)
} }
} }
// NOLINTEND(cppcoreguidelines-avoid-magic-numbers)
if (blockValid) if (blockValid)
{ {
logger_->trace("Product code: {}", p->productCode_); logger_->trace("Product code: {}", p->productCode_);
@ -850,6 +882,8 @@ bool ProductDescriptionBlock::Parse(std::istream& is)
std::optional<DataLevelCode> std::optional<DataLevelCode>
ProductDescriptionBlock::data_level_code(std::uint8_t level) const ProductDescriptionBlock::data_level_code(std::uint8_t level) const
{ {
// NOLINTBEGIN(cppcoreguidelines-avoid-magic-numbers)
switch (p->productCode_) switch (p->productCode_)
{ {
case 32: case 32:
@ -864,6 +898,10 @@ ProductDescriptionBlock::data_level_code(std::uint8_t level) const
case 163: case 163:
case 167: case 167:
case 168: case 168:
case 189:
case 190:
case 191:
case 192:
case 195: case 195:
switch (level) switch (level)
{ {
@ -1035,11 +1073,11 @@ ProductDescriptionBlock::data_level_code(std::uint8_t level) const
if (number_of_levels() <= 16 && level < 16 && if (number_of_levels() <= 16 && level < 16 &&
!uncodedDataLevelProducts_.contains(p->productCode_)) !uncodedDataLevelProducts_.contains(p->productCode_))
{ {
uint16_t th = data_level_threshold(level); const std::uint16_t th = data_level_threshold(level);
if ((th & 0x8000u)) if ((th & 0x8000u))
{ {
// If bit 0 is one, then the LSB is coded // If bit 0 is one, then the LSB is coded
uint16_t lsb = th & 0x00ffu; const std::uint16_t lsb = th & 0x00ffu;
switch (lsb) switch (lsb)
{ {
@ -1083,6 +1121,8 @@ ProductDescriptionBlock::data_level_code(std::uint8_t level) const
} }
} }
// NOLINTEND(cppcoreguidelines-avoid-magic-numbers)
return std::nullopt; return std::nullopt;
} }
@ -1101,6 +1141,8 @@ ProductDescriptionBlock::data_value(std::uint8_t level) const
std::optional<float> f = std::nullopt; std::optional<float> f = std::nullopt;
// NOLINTBEGIN(cppcoreguidelines-avoid-magic-numbers)
// Different products use different scale/offset formulas // Different products use different scale/offset formulas
if (numberOfLevels > 16 || if (numberOfLevels > 16 ||
uncodedDataLevelProducts_.contains(p->productCode_)) uncodedDataLevelProducts_.contains(p->productCode_))
@ -1118,17 +1160,17 @@ ProductDescriptionBlock::data_value(std::uint8_t level) const
case 174: case 174:
case 175: case 175:
case 176: case 176:
f = (level - dataOffset) / dataScale; f = (static_cast<float>(level) - dataOffset) / dataScale;
break; break;
case 134: case 134:
if (level < log_start()) if (level < log_start())
{ {
f = (level - dataOffset) / dataScale; f = (static_cast<float>(level) - dataOffset) / dataScale;
} }
else else
{ {
f = expf((level - log_offset()) / log_scale()); f = expf((static_cast<float>(level) - log_offset()) / log_scale());
} }
break; break;
@ -1137,7 +1179,7 @@ ProductDescriptionBlock::data_value(std::uint8_t level) const
[[fallthrough]]; [[fallthrough]];
default: default:
f = level * dataScale + dataOffset; f = static_cast<float>(level) * dataScale + dataOffset;
break; break;
} }
} }
@ -1177,6 +1219,8 @@ ProductDescriptionBlock::data_value(std::uint8_t level) const
} }
} }
// NOLINTEND(cppcoreguidelines-avoid-magic-numbers)
// Scale for GR compatibility // Scale for GR compatibility
if (f.has_value()) if (f.has_value())
{ {

View file

@ -125,6 +125,7 @@ set(HDR_WSR88D_RDA include/scwx/wsr88d/rda/clutter_filter_bypass_map.hpp
include/scwx/wsr88d/rda/level2_message_header.hpp include/scwx/wsr88d/rda/level2_message_header.hpp
include/scwx/wsr88d/rda/performance_maintenance_data.hpp include/scwx/wsr88d/rda/performance_maintenance_data.hpp
include/scwx/wsr88d/rda/rda_adaptation_data.hpp include/scwx/wsr88d/rda/rda_adaptation_data.hpp
include/scwx/wsr88d/rda/rda_prf_data.hpp
include/scwx/wsr88d/rda/rda_status_data.hpp include/scwx/wsr88d/rda/rda_status_data.hpp
include/scwx/wsr88d/rda/rda_types.hpp include/scwx/wsr88d/rda/rda_types.hpp
include/scwx/wsr88d/rda/volume_coverage_pattern_data.hpp) include/scwx/wsr88d/rda/volume_coverage_pattern_data.hpp)
@ -138,6 +139,7 @@ set(SRC_WSR88D_RDA source/scwx/wsr88d/rda/clutter_filter_bypass_map.cpp
source/scwx/wsr88d/rda/level2_message_header.cpp source/scwx/wsr88d/rda/level2_message_header.cpp
source/scwx/wsr88d/rda/performance_maintenance_data.cpp source/scwx/wsr88d/rda/performance_maintenance_data.cpp
source/scwx/wsr88d/rda/rda_adaptation_data.cpp source/scwx/wsr88d/rda/rda_adaptation_data.cpp
source/scwx/wsr88d/rda/rda_prf_data.cpp
source/scwx/wsr88d/rda/rda_status_data.cpp source/scwx/wsr88d/rda/rda_status_data.cpp
source/scwx/wsr88d/rda/volume_coverage_pattern_data.cpp) source/scwx/wsr88d/rda/volume_coverage_pattern_data.cpp)
set(HDR_WSR88D_RPG include/scwx/wsr88d/rpg/ccb_header.hpp set(HDR_WSR88D_RPG include/scwx/wsr88d/rpg/ccb_header.hpp
@ -145,6 +147,7 @@ set(HDR_WSR88D_RPG include/scwx/wsr88d/rpg/ccb_header.hpp
include/scwx/wsr88d/rpg/cell_trend_volume_scan_times.hpp include/scwx/wsr88d/rpg/cell_trend_volume_scan_times.hpp
include/scwx/wsr88d/rpg/digital_precipitation_data_array_packet.hpp include/scwx/wsr88d/rpg/digital_precipitation_data_array_packet.hpp
include/scwx/wsr88d/rpg/digital_radial_data_array_packet.hpp include/scwx/wsr88d/rpg/digital_radial_data_array_packet.hpp
include/scwx/wsr88d/rpg/digital_raster_data_array_packet.hpp
include/scwx/wsr88d/rpg/general_status_message.hpp include/scwx/wsr88d/rpg/general_status_message.hpp
include/scwx/wsr88d/rpg/generic_data_packet.hpp include/scwx/wsr88d/rpg/generic_data_packet.hpp
include/scwx/wsr88d/rpg/generic_radial_data_packet.hpp include/scwx/wsr88d/rpg/generic_radial_data_packet.hpp
@ -186,6 +189,7 @@ set(SRC_WSR88D_RPG source/scwx/wsr88d/rpg/ccb_header.cpp
source/scwx/wsr88d/rpg/cell_trend_volume_scan_times.cpp source/scwx/wsr88d/rpg/cell_trend_volume_scan_times.cpp
source/scwx/wsr88d/rpg/digital_precipitation_data_array_packet.cpp source/scwx/wsr88d/rpg/digital_precipitation_data_array_packet.cpp
source/scwx/wsr88d/rpg/digital_radial_data_array_packet.cpp source/scwx/wsr88d/rpg/digital_radial_data_array_packet.cpp
source/scwx/wsr88d/rpg/digital_raster_data_array_packet.cpp
source/scwx/wsr88d/rpg/general_status_message.cpp source/scwx/wsr88d/rpg/general_status_message.cpp
source/scwx/wsr88d/rpg/generic_data_packet.cpp source/scwx/wsr88d/rpg/generic_data_packet.cpp
source/scwx/wsr88d/rpg/generic_radial_data_packet.cpp source/scwx/wsr88d/rpg/generic_radial_data_packet.cpp