From 57650165d94765878166240f79ab90ade2ca8612 Mon Sep 17 00:00:00 2001 From: msilvadi Date: Wed, 8 Oct 2025 19:36:25 -0400 Subject: [PATCH 1/3] sync --- .../parameter_expectations.param | 1079 +++++++++++++++++ .../parameter_testing_logic.py | 107 ++ 2 files changed, 1186 insertions(+) create mode 100644 pixhawk_param_testing/parameter_expectations.param create mode 100644 pixhawk_param_testing/parameter_testing_logic.py diff --git a/pixhawk_param_testing/parameter_expectations.param b/pixhawk_param_testing/parameter_expectations.param new file mode 100644 index 0000000..e64170e --- /dev/null +++ b/pixhawk_param_testing/parameter_expectations.param @@ -0,0 +1,1079 @@ +ACRO_BAL_PITCH,1 +ACRO_BAL_ROLL,1 +ACRO_OPTIONS,0 +ACRO_RP_EXPO,0.3 +ACRO_RP_RATE,360 +ACRO_RP_RATE_TC,0 +ACRO_THR_MID,0 +ACRO_TRAINER,2 +ACRO_Y_EXPO,0 +ACRO_Y_RATE,202.5 +ACRO_Y_RATE_TC,0 +ADSB_TYPE,0 +AHRS_COMP_BETA,0.1 +AHRS_EKF_TYPE,3 +AHRS_GPS_GAIN,1 +AHRS_GPS_MINSATS,6 +AHRS_GPS_USE,1 +AHRS_OPTIONS,0 +AHRS_ORIENTATION,0 +AHRS_RP_P,0.2 +AHRS_TRIM_X,0.0080835 +AHRS_TRIM_Y,-0.004619 +AHRS_TRIM_Z,0 +AHRS_WIND_MAX,0 +AHRS_YAW_P,0.2 +ANGLE_MAX,3000 +ARMING_ACCTHRESH,0.75 +ARMING_CHECK,11438 +ARMING_CRSDP_IGN,0 +ARMING_MAGTHRESH,100 +ARMING_MIS_ITEMS,0 +ARMING_OPTIONS,0 +ARMING_RUDDER,2 +ARSPD_ENABLE,0 +ATC_ACCEL_P_MAX,110000 +ATC_ACCEL_R_MAX,110000 +ATC_ACCEL_Y_MAX,27000 +ATC_ANG_LIM_TC,1 +ATC_ANG_PIT_P,4.5 +ATC_ANG_RLL_P,4.5 +ATC_ANG_YAW_P,4.5 +ATC_ANGLE_BOOST,1 +ATC_INPUT_TC,0.15 +ATC_RAT_PIT_D,0.0036 +ATC_RAT_PIT_D_FF,0 +ATC_RAT_PIT_FF,0 +ATC_RAT_PIT_FLTD,20 +ATC_RAT_PIT_FLTE,0 +ATC_RAT_PIT_FLTT,20 +ATC_RAT_PIT_I,0.135 +ATC_RAT_PIT_IMAX,0.5 +ATC_RAT_PIT_NEF,0 +ATC_RAT_PIT_NTF,0 +ATC_RAT_PIT_P,0.135 +ATC_RAT_PIT_PDMX,0 +ATC_RAT_PIT_SMAX,0 +ATC_RAT_RLL_D,0.0036 +ATC_RAT_RLL_D_FF,0 +ATC_RAT_RLL_FF,0 +ATC_RAT_RLL_FLTD,20 +ATC_RAT_RLL_FLTE,0 +ATC_RAT_RLL_FLTT,20 +ATC_RAT_RLL_I,0.135 +ATC_RAT_RLL_IMAX,0.5 +ATC_RAT_RLL_NEF,0 +ATC_RAT_RLL_NTF,0 +ATC_RAT_RLL_P,0.135 +ATC_RAT_RLL_PDMX,0 +ATC_RAT_RLL_SMAX,0 +ATC_RAT_YAW_D,0 +ATC_RAT_YAW_D_FF,0 +ATC_RAT_YAW_FF,0 +ATC_RAT_YAW_FLTD,20 +ATC_RAT_YAW_FLTE,2.5 +ATC_RAT_YAW_FLTT,20 +ATC_RAT_YAW_I,0.018 +ATC_RAT_YAW_IMAX,0.5 +ATC_RAT_YAW_NEF,0 +ATC_RAT_YAW_NTF,0 +ATC_RAT_YAW_P,0.18 +ATC_RAT_YAW_PDMX,0 +ATC_RAT_YAW_SMAX,0 +ATC_RATE_FF_ENAB,1 +ATC_RATE_P_MAX,0 +ATC_RATE_R_MAX,0 +ATC_RATE_Y_MAX,0 +ATC_SLEW_YAW,6000 +ATC_THR_G_BOOST,0 +ATC_THR_MIX_MAN,0.1 +ATC_THR_MIX_MAX,0.5 +ATC_THR_MIX_MIN,0.1 +AUTO_OPTIONS,0 +AUTOTUNE_AGGR,0.1 +AUTOTUNE_AXES,7 +AUTOTUNE_MIN_D,0.001 +AVD_ENABLE,0 +AVOID_ACCEL_MAX,3 +AVOID_ALT_MIN,0 +AVOID_ANGLE_MAX,1000 +AVOID_BACKUP_DZ,0.1 +AVOID_BACKUP_SPD,0.75 +AVOID_BACKZ_SPD,0.75 +AVOID_BEHAVE,0 +AVOID_DIST_MAX,5 +AVOID_ENABLE,3 +AVOID_MARGIN,2 +BARO_ALT_OFFSET,0 +BARO_ALTERR_MAX,2000 +BARO_EXT_BUS,-1 +BARO_FIELD_ELV,0 +BARO_FLTR_RNG,0 +BARO_GND_TEMP,0 +BARO_OPTIONS,0 +BARO_PRIMARY,0 +BARO_PROBE_EXT,0 +BARO1_DEVID,292369 +BARO1_GND_PRESS,97013.19 +BARO1_WCF_ENABLE,0 +BARO2_DEVID,1074177 +BARO2_GND_PRESS,96828.48 +BARO2_WCF_ENABLE,0 +BARO3_DEVID,0 +BARO3_GND_PRESS,0 +BARO3_WCF_ENABLE,0 +BATT_ARM_MAH,0 +BATT_ARM_VOLT,0 +BATT_CAPACITY,3300 +BATT_CRT_MAH,0 +BATT_CRT_VOLT,0 +BATT_FS_CRT_ACT,0 +BATT_FS_LOW_ACT,0 +BATT_FS_VOLTSRC,0 +BATT_I2C_ADDR,0 +BATT_I2C_BUS,1 +BATT_LOW_MAH,0 +BATT_LOW_TIMER,10 +BATT_LOW_VOLT,10.5 +BATT_MAX_AMPS,90 +BATT_MONITOR,21 +BATT_OPTIONS,0 +BATT_SERIAL_NUM,-1 +BATT_SHUNT,0.0005 +BATT2_MONITOR,0 +BATT3_MONITOR,0 +BATT4_MONITOR,0 +BATT5_MONITOR,0 +BATT6_MONITOR,0 +BATT7_MONITOR,0 +BATT8_MONITOR,0 +BATT9_MONITOR,0 +BCN_TYPE,0 +BRD_BOOT_DELAY,0 +BRD_HEAT_I,0.07 +BRD_HEAT_IMAX,70 +BRD_HEAT_LOWMGN,0 +BRD_HEAT_P,50 +BRD_HEAT_TARG,45 +BRD_IO_DSHOT,0 +BRD_IO_ENABLE,1 +BRD_OPTIONS,1 +BRD_RTC_TYPES,1 +BRD_RTC_TZ_MIN,0 +BRD_SAFETY_DEFLT,1 +BRD_SAFETY_MASK,16368 +BRD_SAFETYOPTION,3 +BRD_SBUS_OUT,0 +BRD_SD_FENCE,0 +BRD_SD_MISSION,0 +BRD_SD_SLOWDOWN,0 +BRD_SER1_RTSCTS,2 +BRD_SER2_RTSCTS,2 +BRD_SER5_RTSCTS,2 +BRD_SERIAL_NUM,0 +BRD_TYPE,43 +BRD_VBUS_MIN,4.3 +BRD_VSERVO_MIN,0 +BTN_ENABLE,0 +CAM_AUTO_ONLY,0 +CAM_MAX_ROLL,0 +CAM_RC_TYPE,0 +CAM1_TYPE,0 +CAM2_TYPE,0 +CAN_D1_PROTOCOL,1 +CAN_D1_PROTOCOL2,10 +CAN_D1_UC_ESC_BM,0 +CAN_D1_UC_ESC_OF,0 +CAN_D1_UC_ESC_RV,0 +CAN_D1_UC_NODE,10 +CAN_D1_UC_NTF_RT,20 +CAN_D1_UC_OPTION,0 +CAN_D1_UC_POOL,16384 +CAN_D1_UC_RLY_RT,0 +CAN_D1_UC_SER_EN,0 +CAN_D1_UC_SRV_BM,0 +CAN_D1_UC_SRV_RT,50 +CAN_D2_PROTOCOL,0 +CAN_D2_PROTOCOL2,0 +CAN_LOGLEVEL,3 +CAN_P1_BITRATE,1000000 +CAN_P1_DRIVER,1 +CAN_P1_FDBITRATE,4 +CAN_P2_DRIVER,0 +CAN_SLCAN_CPORT,0 +CAN_SLCAN_SDELAY,1 +CAN_SLCAN_SERNUM,-1 +CAN_SLCAN_TIMOUT,0 +CHUTE_ENABLED,0 +CIRCLE_OPTIONS,1 +CIRCLE_RADIUS,1000 +CIRCLE_RATE,20 +COMPASS_AUTO_ROT,2 +COMPASS_AUTODEC,1 +COMPASS_CAL_FIT,16 +COMPASS_DEC,0 +COMPASS_DEV_ID,331777 +COMPASS_DEV_ID2,0 +COMPASS_DEV_ID3,0 +COMPASS_DEV_ID4,0 +COMPASS_DEV_ID5,0 +COMPASS_DEV_ID6,0 +COMPASS_DEV_ID7,0 +COMPASS_DEV_ID8,0 +COMPASS_DIA_X,1 +COMPASS_DIA_Y,1 +COMPASS_DIA_Z,1 +COMPASS_DIA2_X,1 +COMPASS_DIA2_Y,1 +COMPASS_DIA2_Z,1 +COMPASS_DIA3_X,1 +COMPASS_DIA3_Y,1 +COMPASS_DIA3_Z,1 +COMPASS_DISBLMSK,0 +COMPASS_ENABLE,0 +COMPASS_EXTERN2,0 +COMPASS_EXTERN3,0 +COMPASS_EXTERNAL,0 +COMPASS_FLTR_RNG,0 +COMPASS_LEARN,0 +COMPASS_MOT_X,0 +COMPASS_MOT_Y,0 +COMPASS_MOT_Z,0 +COMPASS_MOT2_X,0 +COMPASS_MOT2_Y,0 +COMPASS_MOT2_Z,0 +COMPASS_MOT3_X,0 +COMPASS_MOT3_Y,0 +COMPASS_MOT3_Z,0 +COMPASS_MOTCT,0 +COMPASS_ODI_X,0 +COMPASS_ODI_Y,0 +COMPASS_ODI_Z,0 +COMPASS_ODI2_X,0 +COMPASS_ODI2_Y,0 +COMPASS_ODI2_Z,0 +COMPASS_ODI3_X,0 +COMPASS_ODI3_Y,0 +COMPASS_ODI3_Z,0 +COMPASS_OFFS_MAX,1800 +COMPASS_OFS_X,30.32092 +COMPASS_OFS_Y,52.11601 +COMPASS_OFS_Z,-136.6821 +COMPASS_OFS2_X,0 +COMPASS_OFS2_Y,0 +COMPASS_OFS2_Z,0 +COMPASS_OFS3_X,0 +COMPASS_OFS3_Y,0 +COMPASS_OFS3_Z,0 +COMPASS_OPTIONS,0 +COMPASS_ORIENT,0 +COMPASS_ORIENT2,0 +COMPASS_ORIENT3,0 +COMPASS_PMOT_EN,0 +COMPASS_PRIO1_ID,331777 +COMPASS_PRIO2_ID,0 +COMPASS_PRIO3_ID,0 +COMPASS_SCALE,0 +COMPASS_SCALE2,0 +COMPASS_SCALE3,0 +COMPASS_USE,1 +COMPASS_USE2,1 +COMPASS_USE3,1 +CUST_ROT_ENABLE,0 +DEV_OPTIONS,0 +DISARM_DELAY,10 +EAHRS_TYPE,0 +EFI_TYPE,0 +EK3_ABIAS_P_NSE,0.02 +EK3_ACC_BIAS_LIM,1 +EK3_ACC_P_NSE,0.35 +EK3_AFFINITY,0 +EK3_ALT_M_NSE,2 +EK3_BCN_DELAY,50 +EK3_BCN_I_GTE,500 +EK3_BCN_M_NSE,1 +EK3_BETA_MASK,0 +EK3_CHECK_SCALE,100 +EK3_DRAG_BCOEF_X,0 +EK3_DRAG_BCOEF_Y,0 +EK3_DRAG_M_NSE,0.5 +EK3_DRAG_MCOEF,0 +EK3_EAS_I_GATE,400 +EK3_EAS_M_NSE,1.4 +EK3_ENABLE,1 +EK3_ERR_THRESH,0.2 +EK3_FLOW_DELAY,10 +EK3_FLOW_I_GATE,300 +EK3_FLOW_M_NSE,0.25 +EK3_FLOW_USE,1 +EK3_GBIAS_P_NSE,0.001 +EK3_GLITCH_RAD,25 +EK3_GND_EFF_DZ,4 +EK3_GPS_CHECK,31 +EK3_GPS_VACC_MAX,0 +EK3_GSF_RST_MAX,2 +EK3_GSF_RUN_MASK,3 +EK3_GSF_USE_MASK,3 +EK3_GYRO_P_NSE,0.015 +EK3_HGT_DELAY,60 +EK3_HGT_I_GATE,500 +EK3_HRT_FILT,2 +EK3_IMU_MASK,3 +EK3_LOG_LEVEL,0 +EK3_MAG_CAL,3 +EK3_MAG_EF_LIM,50 +EK3_MAG_I_GATE,300 +EK3_MAG_M_NSE,0.05 +EK3_MAG_MASK,0 +EK3_MAGB_P_NSE,0.0001 +EK3_MAGE_P_NSE,0.001 +EK3_MAX_FLOW,2.5 +EK3_NOAID_M_NSE,10 +EK3_OGN_HGT_MASK,0 +EK3_OGNM_TEST_SF,2 +EK3_POS_I_GATE,500 +EK3_POSNE_M_NSE,0.5 +EK3_PRIMARY,0 +EK3_RNG_I_GATE,500 +EK3_RNG_M_NSE,0.5 +EK3_RNG_USE_HGT,-1 +EK3_RNG_USE_SPD,2 +EK3_SRC_OPTIONS,1 +EK3_SRC1_POSXY,3 +EK3_SRC1_POSZ,3 +EK3_SRC1_VELXY,3 +EK3_SRC1_VELZ,3 +EK3_SRC1_YAW,1 +EK3_SRC2_POSXY,0 +EK3_SRC2_POSZ,1 +EK3_SRC2_VELXY,0 +EK3_SRC2_VELZ,0 +EK3_SRC2_YAW,0 +EK3_SRC3_POSXY,0 +EK3_SRC3_POSZ,1 +EK3_SRC3_VELXY,0 +EK3_SRC3_VELZ,0 +EK3_SRC3_YAW,0 +EK3_TAU_OUTPUT,25 +EK3_TERR_GRAD,0.1 +EK3_VEL_I_GATE,500 +EK3_VELD_M_NSE,0.5 +EK3_VELNE_M_NSE,0.3 +EK3_VIS_VERR_MAX,0.9 +EK3_VIS_VERR_MIN,0.1 +EK3_WENC_VERR,0.1 +EK3_WIND_P_NSE,0.2 +EK3_WIND_PSCALE,1 +EK3_YAW_I_GATE,300 +EK3_YAW_M_NSE,0.5 +ESC_CALIBRATION,0 +ESC_TLM_MAV_OFS,0 +FENCE_ACTION,1 +FENCE_ALT_MAX,100 +FENCE_ALT_MIN,-10 +FENCE_ENABLE,0 +FENCE_MARGIN,2 +FENCE_RADIUS,300 +FENCE_TOTAL,0 +FENCE_TYPE,7 +FFT_ENABLE,0 +FHLD_BRAKE_RATE,8 +FHLD_FILT_HZ,5 +FHLD_FLOW_MAX,0.6 +FHLD_QUAL_MIN,10 +FHLD_XY_FILT_HZ,5 +FHLD_XY_I,0.3 +FHLD_XY_IMAX,3000 +FHLD_XY_P,0.2 +FILT1_TYPE,0 +FILT2_TYPE,0 +FILT3_TYPE,0 +FILT4_TYPE,0 +FILT5_TYPE,0 +FILT6_TYPE,0 +FILT7_TYPE,0 +FILT8_TYPE,0 +FLIGHT_OPTIONS,0 +FLOW_TYPE,0 +FLTMODE_CH,5 +FLTMODE_GCSBLOCK,0 +FLTMODE1,0 +FLTMODE2,0 +FLTMODE3,0 +FLTMODE4,0 +FLTMODE5,0 +FLTMODE6,0 +FOLL_ENABLE,0 +FORMAT_VERSION,120 +FRAME_CLASS,1 +FRAME_TYPE,1 +FRSKY_DNLINK_ID,27 +FRSKY_DNLINK1_ID,20 +FRSKY_DNLINK2_ID,7 +FRSKY_OPTIONS,0 +FRSKY_UPLINK_ID,13 +FS_CRASH_CHECK,1 +FS_DR_ENABLE,2 +FS_DR_TIMEOUT,30 +FS_EKF_ACTION,1 +FS_EKF_FILT,5 +FS_EKF_THRESH,0.8 +FS_GCS_ENABLE,0 +FS_GCS_TIMEOUT,5 +FS_OPTIONS,16 +FS_THR_ENABLE,0 +FS_THR_VALUE,975 +FS_VIBE_ENABLE,1 +GCS_PID_MASK,0 +GEN_TYPE,0 +GND_EFFECT_COMP,1 +GPS_AUTO_CONFIG,1 +GPS_AUTO_SWITCH,0 +GPS_BLEND_MASK,5 +GPS_CAN_NODEID1,0 +GPS_CAN_NODEID2,0 +GPS_COM_PORT,1 +GPS_COM_PORT2,1 +GPS_DELAY_MS,0 +GPS_DELAY_MS2,0 +GPS_DRV_OPTIONS,0 +GPS_GNSS_MODE,0 +GPS_GNSS_MODE2,0 +GPS_HDOP_GOOD,140 +GPS_INJECT_TO,127 +GPS_MB1_TYPE,0 +GPS_MB2_TYPE,0 +GPS_MIN_DGPS,100 +GPS_MIN_ELEV,-100 +GPS_NAVFILTER,8 +GPS_POS1_X,0 +GPS_POS1_Y,0 +GPS_POS1_Z,0 +GPS_POS2_X,0 +GPS_POS2_Y,0 +GPS_POS2_Z,0 +GPS_PRIMARY,0 +GPS_RATE_MS,200 +GPS_RATE_MS2,200 +GPS_RAW_DATA,0 +GPS_SAVE_CFG,2 +GPS_SBAS_MODE,2 +GPS_SBP_LOGMASK,-256 +GPS_TYPE,14 +GPS_TYPE2,0 +GPS1_CAN_OVRIDE,0 +GPS2_CAN_OVRIDE,0 +GRIP_ENABLE,0 +GUID_OPTIONS,0 +GUID_TIMEOUT,3 +INITIAL_MODE,0 +INS_ACC_BODYFIX,2 +INS_ACC_ID,3866898 +INS_ACC1_CALTEMP,40.125 +INS_ACC2_CALTEMP,41 +INS_ACC2_ID,3866906 +INS_ACC2OFFS_X,-0.0139966 +INS_ACC2OFFS_Y,-0.0023239 +INS_ACC2OFFS_Z,-0.1075951 +INS_ACC2SCAL_X,0.99915 +INS_ACC2SCAL_Y,0.9987492 +INS_ACC2SCAL_Z,0.996999 +INS_ACC3_CALTEMP,31.4375 +INS_ACC3_ID,3866890 +INS_ACC3OFFS_X,-0.0053368 +INS_ACC3OFFS_Y,-0.0188114 +INS_ACC3OFFS_Z,0.0970504 +INS_ACC3SCAL_X,0.998634 +INS_ACC3SCAL_Y,0.9993203 +INS_ACC3SCAL_Z,0.9976228 +INS_ACCEL_FILTER,20 +INS_ACCOFFS_X,-0.0298293 +INS_ACCOFFS_Y,0.0050121 +INS_ACCOFFS_Z,-0.0304518 +INS_ACCSCAL_X,0.9988758 +INS_ACCSCAL_Y,0.9987569 +INS_ACCSCAL_Z,0.9971477 +INS_ENABLE_MASK,0 +INS_FAST_SAMPLE,7 +INS_GYR_CAL,1 +INS_GYR_ID,3866898 +INS_GYR1_CALTEMP,22.71875 +INS_GYR2_CALTEMP,23.3125 +INS_GYR2_ID,3866906 +INS_GYR2OFFS_X,-0.0149512 +INS_GYR2OFFS_Y,0.0040659 +INS_GYR2OFFS_Z,-0.0003938 +INS_GYR3_CALTEMP,24 +INS_GYR3_ID,3866890 +INS_GYR3OFFS_X,-0.0001496 +INS_GYR3OFFS_Y,0.0006235 +INS_GYR3OFFS_Z,-0.0002471 +INS_GYRO_FILTER,20 +INS_GYRO_RATE,1 +INS_GYROFFS_X,0.0002499 +INS_GYROFFS_Y,0.0023659 +INS_GYROFFS_Z,-0.0004639 +INS_HNTC2_ENABLE,0 +INS_HNTCH_ENABLE,0 +INS_LOG_BAT_CNT,1024 +INS_LOG_BAT_LGCT,32 +INS_LOG_BAT_LGIN,20 +INS_LOG_BAT_MASK,0 +INS_LOG_BAT_OPT,0 +INS_POS1_X,0 +INS_POS1_Y,0 +INS_POS1_Z,0 +INS_POS2_X,0 +INS_POS2_Y,0 +INS_POS2_Z,0 +INS_POS3_X,0 +INS_POS3_Y,0 +INS_POS3_Z,0 +INS_RAW_LOG_OPT,0 +INS_STILL_THRESH,2.5 +INS_TCAL_OPTIONS,0 +INS_TCAL1_ENABLE,0 +INS_TCAL2_ENABLE,0 +INS_TCAL3_ENABLE,0 +INS_TRIM_OPTION,1 +INS_USE,1 +INS_USE2,1 +INS_USE3,1 +KDE_NPOLE,14 +LAND_ALT_LOW,1000 +LAND_REPOSITION,1 +LAND_SPEED,50 +LAND_SPEED_HIGH,0 +LGR_ENABLE,0 +LOG_BACKEND_TYPE,1 +LOG_BITMASK,176126 +LOG_DARM_RATEMAX,0 +LOG_DISARMED,0 +LOG_FILE_BUFSIZE,200 +LOG_FILE_DSRMROT,0 +LOG_FILE_MB_FREE,500 +LOG_FILE_RATEMAX,0 +LOG_FILE_TIMEOUT,5 +LOG_MAV_BUFSIZE,8 +LOG_MAV_RATEMAX,0 +LOG_MAX_FILES,500 +LOG_REPLAY,0 +LOIT_ACC_MAX,500 +LOIT_ANG_MAX,0 +LOIT_BRK_ACCEL,250 +LOIT_BRK_DELAY,1 +LOIT_BRK_JERK,500 +LOIT_SPEED,1250 +MIS_OPTIONS,0 +MIS_RESTART,0 +MIS_TOTAL,0 +MNT1_TYPE,0 +MNT2_TYPE,0 +MOT_BAT_CURR_MAX,0 +MOT_BAT_CURR_TC,5 +MOT_BAT_IDX,0 +MOT_BAT_VOLT_MAX,0 +MOT_BAT_VOLT_MIN,0 +MOT_BOOST_SCALE,0 +MOT_HOVER_LEARN,2 +MOT_OPTIONS,0 +MOT_PWM_MAX,2000 +MOT_PWM_MIN,1000 +MOT_PWM_TYPE,0 +MOT_SAFE_DISARM,0 +MOT_SAFE_TIME,1 +MOT_SLEW_DN_TIME,0 +MOT_SLEW_UP_TIME,0 +MOT_SPIN_ARM,0.1 +MOT_SPIN_MAX,0.95 +MOT_SPIN_MIN,0.15 +MOT_SPOOL_TIM_DN,0 +MOT_SPOOL_TIME,0.5 +MOT_THST_EXPO,0.65 +MOT_THST_HOVER,0.35 +MOT_YAW_HEADROOM,200 +MSP_OPTIONS,0 +MSP_OSD_NCELLS,0 +NET_ENABLE,0 +NET_P1_TYPE,0 +NET_P2_TYPE,0 +NET_P3_TYPE,0 +NET_P4_TYPE,0 +NMEA_MSG_EN,3 +NMEA_RATE_MS,100 +NTF_BUZZ_ON_LVL,1 +NTF_BUZZ_PIN,-1 +NTF_BUZZ_TYPES,5 +NTF_BUZZ_VOLUME,100 +NTF_DISPLAY_TYPE,0 +NTF_LED_BRIGHT,3 +NTF_LED_LEN,1 +NTF_LED_OVERRIDE,0 +NTF_LED_TYPES,123079 +OA_TYPE,0 +OSD_TYPE,0 +PHLD_BRAKE_ANGLE,3000 +PHLD_BRAKE_RATE,8 +PILOT_ACCEL_Z,250 +PILOT_SPEED_DN,0 +PILOT_SPEED_UP,250 +PILOT_THR_BHV,0 +PILOT_THR_FILT,0 +PILOT_TKOFF_ALT,0 +PILOT_Y_EXPO,0 +PILOT_Y_RATE,202.5 +PILOT_Y_RATE_TC,0 +PLDP_DELAY,0 +PLDP_RNG_MIN,0 +PLDP_SPEED_DN,0 +PLDP_THRESH,0.9 +PLND_ENABLED,0 +PRX_ALT_MIN,1 +PRX_FILT,0.25 +PRX_IGN_GND,0 +PRX_LOG_RAW,0 +PRX1_TYPE,0 +PRX2_TYPE,0 +PRX3_TYPE,0 +PSC_ACCZ_D,0 +PSC_ACCZ_D_FF,0 +PSC_ACCZ_FF,0 +PSC_ACCZ_FLTD,0 +PSC_ACCZ_FLTE,20 +PSC_ACCZ_FLTT,0 +PSC_ACCZ_I,1 +PSC_ACCZ_IMAX,800 +PSC_ACCZ_NEF,0 +PSC_ACCZ_NTF,0 +PSC_ACCZ_P,0.5 +PSC_ACCZ_PDMX,0 +PSC_ACCZ_SMAX,0 +PSC_ANGLE_MAX,0 +PSC_JERK_XY,5 +PSC_JERK_Z,5 +PSC_POSXY_P,1 +PSC_POSZ_P,1 +PSC_VELXY_D,0.5 +PSC_VELXY_FF,0 +PSC_VELXY_FLTD,5 +PSC_VELXY_FLTE,5 +PSC_VELXY_I,1 +PSC_VELXY_IMAX,1000 +PSC_VELXY_P,2 +PSC_VELZ_D,0 +PSC_VELZ_FF,0 +PSC_VELZ_FLTD,5 +PSC_VELZ_FLTE,5 +PSC_VELZ_I,0 +PSC_VELZ_IMAX,1000 +PSC_VELZ_P,5 +RALLY_INCL_HOME,1 +RALLY_LIMIT_KM,0.3 +RALLY_TOTAL,0 +RC_FS_TIMEOUT,1 +RC_OPTIONS,32 +RC_OVERRIDE_TIME,3 +RC_PROTOCOLS,1 +RC_SPEED,490 +RC1_DZ,20 +RC1_MAX,1900 +RC1_MIN,1100 +RC1_OPTION,0 +RC1_REVERSED,0 +RC1_TRIM,1500 +RC10_DZ,0 +RC10_MAX,1900 +RC10_MIN,1100 +RC10_OPTION,0 +RC10_REVERSED,0 +RC10_TRIM,1500 +RC11_DZ,0 +RC11_MAX,1900 +RC11_MIN,1100 +RC11_OPTION,0 +RC11_REVERSED,0 +RC11_TRIM,1500 +RC12_DZ,0 +RC12_MAX,1900 +RC12_MIN,1100 +RC12_OPTION,0 +RC12_REVERSED,0 +RC12_TRIM,1500 +RC13_DZ,0 +RC13_MAX,1900 +RC13_MIN,1100 +RC13_OPTION,0 +RC13_REVERSED,0 +RC13_TRIM,1500 +RC14_DZ,0 +RC14_MAX,1900 +RC14_MIN,1100 +RC14_OPTION,0 +RC14_REVERSED,0 +RC14_TRIM,1500 +RC15_DZ,0 +RC15_MAX,1900 +RC15_MIN,1100 +RC15_OPTION,0 +RC15_REVERSED,0 +RC15_TRIM,1500 +RC16_DZ,0 +RC16_MAX,1900 +RC16_MIN,1100 +RC16_OPTION,0 +RC16_REVERSED,0 +RC16_TRIM,1500 +RC2_DZ,20 +RC2_MAX,1900 +RC2_MIN,1100 +RC2_OPTION,0 +RC2_REVERSED,0 +RC2_TRIM,1500 +RC3_DZ,30 +RC3_MAX,1900 +RC3_MIN,1100 +RC3_OPTION,0 +RC3_REVERSED,0 +RC3_TRIM,1500 +RC4_DZ,20 +RC4_MAX,1900 +RC4_MIN,1100 +RC4_OPTION,0 +RC4_REVERSED,0 +RC4_TRIM,1500 +RC5_DZ,0 +RC5_MAX,1900 +RC5_MIN,1100 +RC5_OPTION,0 +RC5_REVERSED,0 +RC5_TRIM,1500 +RC6_DZ,0 +RC6_MAX,1900 +RC6_MIN,1100 +RC6_OPTION,0 +RC6_REVERSED,0 +RC6_TRIM,1500 +RC7_DZ,0 +RC7_MAX,1900 +RC7_MIN,1100 +RC7_OPTION,0 +RC7_REVERSED,0 +RC7_TRIM,1500 +RC8_DZ,0 +RC8_MAX,1900 +RC8_MIN,1100 +RC8_OPTION,0 +RC8_REVERSED,0 +RC8_TRIM,1500 +RC9_DZ,0 +RC9_MAX,1900 +RC9_MIN,1100 +RC9_OPTION,0 +RC9_REVERSED,0 +RC9_TRIM,1500 +RCMAP_PITCH,2 +RCMAP_ROLL,1 +RCMAP_THROTTLE,3 +RCMAP_YAW,4 +RELAY1_FUNCTION,0 +RELAY2_FUNCTION,0 +RELAY3_FUNCTION,0 +RELAY4_FUNCTION,0 +RELAY5_FUNCTION,0 +RELAY6_FUNCTION,0 +RNGFND_FILT,0.5 +RNGFND1_TYPE,0 +RNGFND2_TYPE,0 +RNGFND3_TYPE,0 +RNGFND4_TYPE,0 +RNGFND5_TYPE,0 +RNGFND6_TYPE,0 +RNGFND7_TYPE,0 +RNGFND8_TYPE,0 +RNGFND9_TYPE,0 +RNGFNDA_TYPE,0 +RPM1_TYPE,0 +RPM2_TYPE,0 +RSSI_TYPE,0 +RTL_ALT,1500 +RTL_ALT_FINAL,0 +RTL_ALT_TYPE,0 +RTL_CLIMB_MIN,0 +RTL_CONE_SLOPE,3 +RTL_LOIT_TIME,5000 +RTL_OPTIONS,0 +RTL_SPEED,0 +SCHED_DEBUG,0 +SCHED_LOOP_RATE,400 +SCHED_OPTIONS,0 +SCR_DEBUG_OPTS,0 +SCR_DIR_DISABLE,0 +SCR_ENABLE,1 +SCR_HEAP_SIZE,204800 +SCR_LD_CHECKSUM,-1 +SCR_RUN_CHECKSUM,-1 +SCR_THD_PRIORITY,0 +SCR_USER1,0 +SCR_USER2,0 +SCR_USER3,0 +SCR_USER4,0 +SCR_USER5,0 +SCR_USER6,0 +SCR_VM_I_COUNT,10000 +SERIAL_PASS1,0 +SERIAL_PASS2,-1 +SERIAL_PASSTIMO,15 +SERIAL0_BAUD,115 +SERIAL0_PROTOCOL,2 +SERIAL1_BAUD,57 +SERIAL1_OPTIONS,0 +SERIAL1_PROTOCOL,2 +SERIAL2_BAUD,57 +SERIAL2_OPTIONS,0 +SERIAL2_PROTOCOL,2 +SERIAL3_BAUD,230 +SERIAL3_OPTIONS,0 +SERIAL3_PROTOCOL,5 +SERIAL4_BAUD,230 +SERIAL4_OPTIONS,0 +SERIAL4_PROTOCOL,5 +SERIAL5_BAUD,57 +SERIAL5_OPTIONS,0 +SERIAL5_PROTOCOL,-1 +SERIAL6_BAUD,57 +SERIAL6_OPTIONS,0 +SERIAL6_PROTOCOL,-1 +SERIAL7_BAUD,57 +SERIAL7_OPTIONS,0 +SERIAL7_PROTOCOL,-1 +SERIAL8_BAUD,115200 +SERIAL8_OPTIONS,0 +SERIAL8_PROTOCOL,2 +SERVO_32_ENABLE,0 +SERVO_BLH_3DMASK,0 +SERVO_BLH_AUTO,0 +SERVO_BLH_BDMASK,0 +SERVO_BLH_DEBUG,0 +SERVO_BLH_MASK,0 +SERVO_BLH_OTYPE,0 +SERVO_BLH_POLES,14 +SERVO_BLH_PORT,0 +SERVO_BLH_RVMASK,0 +SERVO_BLH_TEST,0 +SERVO_BLH_TMOUT,0 +SERVO_BLH_TRATE,10 +SERVO_DSHOT_ESC,0 +SERVO_DSHOT_RATE,0 +SERVO_FTW_MASK,0 +SERVO_FTW_POLES,14 +SERVO_FTW_RVMASK,0 +SERVO_GPIO_MASK,0 +SERVO_RATE,50 +SERVO_RC_FS_MSK,0 +SERVO_ROB_POSMAX,4095 +SERVO_ROB_POSMIN,0 +SERVO_SBUS_RATE,50 +SERVO_VOLZ_MASK,0 +SERVO1_FUNCTION,33 +SERVO1_MAX,1900 +SERVO1_MIN,1100 +SERVO1_REVERSED,0 +SERVO1_TRIM,1500 +SERVO10_FUNCTION,0 +SERVO10_MAX,1900 +SERVO10_MIN,1100 +SERVO10_REVERSED,0 +SERVO10_TRIM,1500 +SERVO11_FUNCTION,0 +SERVO11_MAX,1900 +SERVO11_MIN,1100 +SERVO11_REVERSED,0 +SERVO11_TRIM,1500 +SERVO12_FUNCTION,0 +SERVO12_MAX,1900 +SERVO12_MIN,1100 +SERVO12_REVERSED,0 +SERVO12_TRIM,1500 +SERVO13_FUNCTION,0 +SERVO13_MAX,1900 +SERVO13_MIN,1100 +SERVO13_REVERSED,0 +SERVO13_TRIM,1500 +SERVO14_FUNCTION,0 +SERVO14_MAX,1900 +SERVO14_MIN,1100 +SERVO14_REVERSED,0 +SERVO14_TRIM,1500 +SERVO15_FUNCTION,0 +SERVO15_MAX,1900 +SERVO15_MIN,1100 +SERVO15_REVERSED,0 +SERVO15_TRIM,1500 +SERVO16_FUNCTION,0 +SERVO16_MAX,1900 +SERVO16_MIN,1100 +SERVO16_REVERSED,0 +SERVO16_TRIM,1500 +SERVO2_FUNCTION,34 +SERVO2_MAX,1900 +SERVO2_MIN,1100 +SERVO2_REVERSED,0 +SERVO2_TRIM,1500 +SERVO3_FUNCTION,35 +SERVO3_MAX,1900 +SERVO3_MIN,1100 +SERVO3_REVERSED,0 +SERVO3_TRIM,1500 +SERVO4_FUNCTION,36 +SERVO4_MAX,1900 +SERVO4_MIN,1100 +SERVO4_REVERSED,0 +SERVO4_TRIM,1500 +SERVO5_FUNCTION,0 +SERVO5_MAX,1900 +SERVO5_MIN,1100 +SERVO5_REVERSED,0 +SERVO5_TRIM,1500 +SERVO6_FUNCTION,0 +SERVO6_MAX,1900 +SERVO6_MIN,1100 +SERVO6_REVERSED,0 +SERVO6_TRIM,1500 +SERVO7_FUNCTION,0 +SERVO7_MAX,1900 +SERVO7_MIN,1100 +SERVO7_REVERSED,0 +SERVO7_TRIM,1500 +SERVO8_FUNCTION,0 +SERVO8_MAX,1900 +SERVO8_MIN,1100 +SERVO8_REVERSED,0 +SERVO8_TRIM,1500 +SERVO9_FUNCTION,0 +SERVO9_MAX,1900 +SERVO9_MIN,1100 +SERVO9_REVERSED,0 +SERVO9_TRIM,1500 +SID_AXIS,0 +SIMPLE,0 +SPRAY_ENABLE,0 +SR0_ADSB,0 +SR0_EXT_STAT,0 +SR0_EXTRA1,0 +SR0_EXTRA2,0 +SR0_EXTRA3,0 +SR0_PARAMS,0 +SR0_POSITION,0 +SR0_RAW_CTRL,0 +SR0_RAW_SENS,0 +SR0_RC_CHAN,0 +SR1_ADSB,0 +SR1_EXT_STAT,0 +SR1_EXTRA1,0 +SR1_EXTRA2,0 +SR1_EXTRA3,0 +SR1_PARAMS,0 +SR1_POSITION,0 +SR1_RAW_CTRL,0 +SR1_RAW_SENS,0 +SR1_RC_CHAN,0 +SR2_ADSB,0 +SR2_EXT_STAT,0 +SR2_EXTRA1,0 +SR2_EXTRA2,0 +SR2_EXTRA3,0 +SR2_PARAMS,0 +SR2_POSITION,0 +SR2_RAW_CTRL,0 +SR2_RAW_SENS,0 +SR2_RC_CHAN,0 +SR3_ADSB,0 +SR3_EXT_STAT,0 +SR3_EXTRA1,0 +SR3_EXTRA2,0 +SR3_EXTRA3,0 +SR3_PARAMS,0 +SR3_POSITION,0 +SR3_RAW_CTRL,0 +SR3_RAW_SENS,0 +SR3_RC_CHAN,0 +SR4_ADSB,0 +SR4_EXT_STAT,0 +SR4_EXTRA1,0 +SR4_EXTRA2,0 +SR4_EXTRA3,0 +SR4_PARAMS,0 +SR4_POSITION,0 +SR4_RAW_CTRL,0 +SR4_RAW_SENS,0 +SR4_RC_CHAN,0 +SR5_ADSB,0 +SR5_EXT_STAT,0 +SR5_EXTRA1,0 +SR5_EXTRA2,0 +SR5_EXTRA3,0 +SR5_PARAMS,0 +SR5_POSITION,0 +SR5_RAW_CTRL,0 +SR5_RAW_SENS,0 +SR5_RC_CHAN,0 +SR6_ADSB,0 +SR6_EXT_STAT,0 +SR6_EXTRA1,0 +SR6_EXTRA2,0 +SR6_EXTRA3,0 +SR6_PARAMS,0 +SR6_POSITION,0 +SR6_RAW_CTRL,0 +SR6_RAW_SENS,0 +SR6_RC_CHAN,0 +SRTL_ACCURACY,2 +SRTL_OPTIONS,0 +SRTL_POINTS,300 +STAT_BOOTCNT,71 +STAT_FLTTIME,0 +STAT_RESET,1 +STAT_RUNTIME,25951 +SUPER_SIMPLE,0 +SURFTRAK_MODE,1 +SURFTRAK_TC,1 +SYSID_ENFORCE,0 +SYSID_MYGCS,255 +SYSID_THISMAV,1 +TCAL_ENABLED,0 +TELEM_DELAY,0 +TERRAIN_ENABLE,1 +TERRAIN_MARGIN,0.05 +TERRAIN_OFS_MAX,30 +TERRAIN_OPTIONS,0 +TERRAIN_SPACING,100 +THR_DZ,100 +THROW_ALT_MAX,0 +THROW_ALT_MIN,0 +THROW_MOT_START,0 +THROW_NEXTMODE,18 +THROW_TYPE,0 +TKOFF_RPM_MAX,0 +TKOFF_RPM_MIN,0 +TKOFF_SLEW_TIME,2 +TKOFF_THR_MAX,0.9 +TUNE,0 +TUNE_MAX,0 +TUNE_MIN,0 +VISO_TYPE,0 +VTX_ENABLE,0 +WINCH_TYPE,0 +WP_NAVALT_MIN,0 +WP_YAW_BEHAVIOR,2 +WPNAV_ACCEL,250 +WPNAV_ACCEL_C,0 +WPNAV_ACCEL_Z,100 +WPNAV_JERK,1 +WPNAV_RADIUS,200 +WPNAV_RFND_USE,1 +WPNAV_SPEED,1000 +WPNAV_SPEED_DN,150 +WPNAV_SPEED_UP,250 +WPNAV_TER_MARGIN,10 +WVANE_ENABLE,0 +ZIGZ_AUTO_ENABLE,0 diff --git a/pixhawk_param_testing/parameter_testing_logic.py b/pixhawk_param_testing/parameter_testing_logic.py new file mode 100644 index 0000000..4f30e39 --- /dev/null +++ b/pixhawk_param_testing/parameter_testing_logic.py @@ -0,0 +1,107 @@ +from __future__ import annotations +from pathlib import Path +import re +from typing import Dict, List, Tuple, Union +from pymavlink import matliv + +#python parameter_check_logic.py drone_actual.param +ParamValue = Union[int, float, str] +Pathish = Union[str, Path] + +__all__ = [ + "parse_params_file", + "diff_params", + "check_file_against_baseline", + "ParamValue", +] + +#Compile once for speed +_LINE_RE = re.compile(r"^([^,]+)\s*,\s*(.+)$") + +def parse_params_file(path: Pathish) -> Dict[str, ParamValue]: + p = Path(path) + params: Dict[str, ParamValue] = {} + + with p.open("r", encoding="utf-8", errors="replace") as f: + for ln in f: + ln = ln.strip() + if not ln or ln.startswith("#"): + continue + m = _LINE_RE.match(ln) + if not m: + continue + k, v = m.group(1).strip(), m.group(2).strip() + try: + fv = float(v) + params[k] = int(fv) if fv.is_integer() else fv + except ValueError: + params[k] = v + return params + +def diff_params( + actual: Dict[str, ParamValue], + expected: Dict[str, ParamValue], +) -> Tuple[List[str], List[Tuple[str, ParamValue, ParamValue]], List[str]]: + + missing: List[str] = [] + mismatches: List[Tuple[str, ParamValue, ParamValue]] = [] + extras: List[str] = [] + + for k, exp in expected.items(): + if k not in actual: + missing.append(k) + elif actual[k] != exp: + mismatches.append((k, exp, actual[k])) + + for k in actual: + if k not in expected: + extras.append(k) + + missing.sort() + mismatches.sort(key=lambda t: t[0]) + extras.sort() + + return missing, mismatches, extras + +def check_file_against_baseline( + actual_file: Pathish, + baseline_file: Pathish, +) -> Tuple[List[str], List[Tuple[str, ParamValue, ParamValue]], List[str]]: + actual = parse_params_file(actual_file) + expected = parse_params_file(baseline_file) + return diff_params(actual, expected) + +if __name__ == "__main__": + import sys + from pathlib import Path + + BASELINE_FILE = Path("parameter_expectations.param") + + if len(sys.argv) != 2: + print("Usage: python parameter_check_logic.py ") + sys.exit(2) + + actual_path = Path(sys.argv[1]) + baseline_path = BASELINE_FILE + + if not baseline_path.exists(): + print(f"Baseline file not found: {baseline_path}") + sys.exit(2) + if not actual_path.exists(): + print(f"Actual file not found: {actual_path}") + sys.exit(2) + + missing, mismatches, extras = check_file_against_baseline(actual_path, baseline_path) + + if not missing and not mismatches and not extras: + print("Files match baseline") + sys.exit(0) + else: + print("Differences found:") + if missing: + print(f"Missing: {missing}") + if mismatches: + print(f"Mismatches: {mismatches}") + if extras: + print(f"Extras: {extras}") + sys.exit(1) From 63cfd13302f9d2073ca6e900aba25a4ed9a3f1f0 Mon Sep 17 00:00:00 2001 From: msilvadi Date: Sun, 16 Nov 2025 22:51:21 -0500 Subject: [PATCH 2/3] sync --- .../message_encoding_decoding.py | 2 +- .../metadata_encoding_decoding.py | 2 +- .../parameter_testing_logic.py | 107 -------- .../camera_emulator/test_camera_emulator.py | 2 +- .../parameter_expectations.param | 0 .../parameter_testing_logic.py | 247 ++++++++++++++++++ 6 files changed, 250 insertions(+), 110 deletions(-) delete mode 100644 pixhawk_param_testing/parameter_testing_logic.py rename {pixhawk_param_testing => tests/integration/hitl/pixhawk_param_testing}/parameter_expectations.param (100%) create mode 100644 tests/integration/hitl/pixhawk_param_testing/parameter_testing_logic.py diff --git a/modules/data_encoding/message_encoding_decoding.py b/modules/data_encoding/message_encoding_decoding.py index 180703b..5548a27 100644 --- a/modules/data_encoding/message_encoding_decoding.py +++ b/modules/data_encoding/message_encoding_decoding.py @@ -1,6 +1,6 @@ """ Encoding and Decoding Global Positions -Save first byte as char to represent which worker sent the message +Save first byte as char to represent which worker sent the message """ import base64 diff --git a/modules/data_encoding/metadata_encoding_decoding.py b/modules/data_encoding/metadata_encoding_decoding.py index 1025b17..b38cfac 100644 --- a/modules/data_encoding/metadata_encoding_decoding.py +++ b/modules/data_encoding/metadata_encoding_decoding.py @@ -1,6 +1,6 @@ """ Encoding and Decoding Metadata -Save first byte as char to represent which worker sent the message +Save first byte as char to represent which worker sent the message """ import base64 diff --git a/pixhawk_param_testing/parameter_testing_logic.py b/pixhawk_param_testing/parameter_testing_logic.py deleted file mode 100644 index 4f30e39..0000000 --- a/pixhawk_param_testing/parameter_testing_logic.py +++ /dev/null @@ -1,107 +0,0 @@ -from __future__ import annotations -from pathlib import Path -import re -from typing import Dict, List, Tuple, Union -from pymavlink import matliv - -#python parameter_check_logic.py drone_actual.param -ParamValue = Union[int, float, str] -Pathish = Union[str, Path] - -__all__ = [ - "parse_params_file", - "diff_params", - "check_file_against_baseline", - "ParamValue", -] - -#Compile once for speed -_LINE_RE = re.compile(r"^([^,]+)\s*,\s*(.+)$") - -def parse_params_file(path: Pathish) -> Dict[str, ParamValue]: - p = Path(path) - params: Dict[str, ParamValue] = {} - - with p.open("r", encoding="utf-8", errors="replace") as f: - for ln in f: - ln = ln.strip() - if not ln or ln.startswith("#"): - continue - m = _LINE_RE.match(ln) - if not m: - continue - k, v = m.group(1).strip(), m.group(2).strip() - try: - fv = float(v) - params[k] = int(fv) if fv.is_integer() else fv - except ValueError: - params[k] = v - return params - -def diff_params( - actual: Dict[str, ParamValue], - expected: Dict[str, ParamValue], -) -> Tuple[List[str], List[Tuple[str, ParamValue, ParamValue]], List[str]]: - - missing: List[str] = [] - mismatches: List[Tuple[str, ParamValue, ParamValue]] = [] - extras: List[str] = [] - - for k, exp in expected.items(): - if k not in actual: - missing.append(k) - elif actual[k] != exp: - mismatches.append((k, exp, actual[k])) - - for k in actual: - if k not in expected: - extras.append(k) - - missing.sort() - mismatches.sort(key=lambda t: t[0]) - extras.sort() - - return missing, mismatches, extras - -def check_file_against_baseline( - actual_file: Pathish, - baseline_file: Pathish, -) -> Tuple[List[str], List[Tuple[str, ParamValue, ParamValue]], List[str]]: - actual = parse_params_file(actual_file) - expected = parse_params_file(baseline_file) - return diff_params(actual, expected) - -if __name__ == "__main__": - import sys - from pathlib import Path - - BASELINE_FILE = Path("parameter_expectations.param") - - if len(sys.argv) != 2: - print("Usage: python parameter_check_logic.py ") - sys.exit(2) - - actual_path = Path(sys.argv[1]) - baseline_path = BASELINE_FILE - - if not baseline_path.exists(): - print(f"Baseline file not found: {baseline_path}") - sys.exit(2) - if not actual_path.exists(): - print(f"Actual file not found: {actual_path}") - sys.exit(2) - - missing, mismatches, extras = check_file_against_baseline(actual_path, baseline_path) - - if not missing and not mismatches and not extras: - print("Files match baseline") - sys.exit(0) - else: - print("Differences found:") - if missing: - print(f"Missing: {missing}") - if mismatches: - print(f"Mismatches: {mismatches}") - if extras: - print(f"Extras: {extras}") - sys.exit(1) diff --git a/tests/integration/camera_emulator/test_camera_emulator.py b/tests/integration/camera_emulator/test_camera_emulator.py index 9d63a54..4b4ee1c 100644 --- a/tests/integration/camera_emulator/test_camera_emulator.py +++ b/tests/integration/camera_emulator/test_camera_emulator.py @@ -6,7 +6,7 @@ run this script (this will create a virtual camera and start streaming images to it) - Run test_camera_read (will open the virtual camera using opencv and display the images) -Note: may need to mess around with camera index +Note: may need to mess around with camera index (usually will be # of cameras connected to computer + 1) """ diff --git a/pixhawk_param_testing/parameter_expectations.param b/tests/integration/hitl/pixhawk_param_testing/parameter_expectations.param similarity index 100% rename from pixhawk_param_testing/parameter_expectations.param rename to tests/integration/hitl/pixhawk_param_testing/parameter_expectations.param diff --git a/tests/integration/hitl/pixhawk_param_testing/parameter_testing_logic.py b/tests/integration/hitl/pixhawk_param_testing/parameter_testing_logic.py new file mode 100644 index 0000000..2d69c29 --- /dev/null +++ b/tests/integration/hitl/pixhawk_param_testing/parameter_testing_logic.py @@ -0,0 +1,247 @@ +"""This following code ensures assertion of expected parameters with Mavlink data. +It reads a baseline file of expected Pixhawk parameters and compares them +against values retrieved over MAVLink. +""" + +from __future__ import annotations + +import os +import re +import sys +import time +from pathlib import Path +from typing import Dict, List, Tuple, Union + +# Default connection settings used if environment variables are not set. +DEFAULT_PIXHAWK_ADDRESS = "/dev/ttyAMA0" +DEFAULT_PIXHAWK_BAUD = 57600 + +ParamValue = Union[int, float, str] +Pathish = Union[str, Path] + +# parses expectations file by spliting each expected parameter into parameter +# name (before comma) and value +_LINE_RE = re.compile(r"^([^,]+)\s*,\s*(.+)$") + + +def _coerce_value(value_str: str) -> ParamValue: + """ + This function allows for value interpretation as a number. + + It tries to convert a string into a float, and if that float is an integer + value, it converts it to an int. Otherwise, it leaves the string as-is. + """ + try: + float_value = float(value_str) + return int(float_value) if float_value.is_integer() else float_value + except ValueError: + return value_str + + +def parse_params_file(path: Pathish) -> Dict[str, ParamValue]: + """ + reads param_expectations line by line and builds a dictionary + + Each non-empty, non-comment line is expected to look like: + PARAM_NAME, VALUE # optional inline comment + + Returns: + dict mapping parameter name -> coerced value. + """ + param_path = Path(path) + params: Dict[str, ParamValue] = {} + + with param_path.open("r", encoding="utf-8", errors="replace") as file: + for line in file: + line = line.strip() + if not line or line.startswith("#"): + continue + + match = _LINE_RE.match(line) + if not match: + continue + + key, raw_value = match.group(1).strip(), match.group(2).strip() + + # allow inline comments after value + if "#" in raw_value: + raw_value = raw_value.split("#", 1)[0].strip() + + params[key] = _coerce_value(raw_value) + + return params + + +def _float_equal(a: float, b: float, eps: float = 1e-6) -> bool: + """Helper that checks if two floats are equal within a small epsilon.""" + return abs(a - b) <= eps + + +def _values_equal(a: ParamValue, b: ParamValue) -> bool: + """ + Ensures values are approprialtley cmpared via rounding / tolerance. + + If both values are numeric, they are compared using a float tolerance. + Otherwise, a normal equality comparison is used. + """ + if isinstance(a, (int, float)) and isinstance(b, (int, float)): + return _float_equal(float(a), float(b)) + return a == b + + +def diff_params( + actual: Dict[str, ParamValue], + expected: Dict[str, ParamValue], +) -> Tuple[List[str], List[Tuple[str, ParamValue, ParamValue]], List[str]]: + """ + Takes actual and expected values as parameters to build three lists of + missing, mismatched and extras. + + Returns: + missing: parameters that are in expected but not found in actual. + mismatches: (name, expected_value, actual_value) for value differences. + extras: parameters that are found on dron but not in file. + """ + missing: List[str] = [] + mismatches: List[Tuple[str, ParamValue, ParamValue]] = [] + extras: List[str] = [] + + # builds missing and mismatches lists in case + for name, expected_value in expected.items(): + if name not in actual: + missing.append(name) + elif not _values_equal(actual[name], expected_value): + mismatches.append((name, expected_value, actual[name])) + + # checks for parameters that are fouund on dron but not in file + for name in actual: + if name not in expected: + extras.append(name) + + missing.sort() + mismatches.sort(key=lambda item: item[0]) + extras.sort() + + return missing, mismatches, extras + + +def fetch_all_params_mavlink( + address: str, + baud: int = DEFAULT_PIXHAWK_BAUD, + timeout_s: int = 25, +) -> Dict[str, ParamValue]: + """ + Opens MAVLink connection directly and builds a dictionary by listening in + for PARAM_VALUE messages. + + It: + - checks if vehicle is alive using a heartbeat + - requests params + - decrypts and strips messages into values + """ + # imported here so other modules can import this file without pymavlink + from pymavlink import mavutil # pylint: disable=import-outside-toplevel + + # checks if vehicle is alive + connection = mavutil.mavlink_connection(address, baud=baud) + heartbeat = connection.wait_heartbeat(timeout=timeout_s) + if not heartbeat: + raise RuntimeError("Drone is not operating") + + # requests params + connection.mav.param_request_list_send( + connection.target_system, + connection.target_component, + ) + + params: Dict[str, ParamValue] = {} + seen_names: set[str] = set() + total_count: int | None = None + end_time = time.time() + timeout_s + + try: + while time.time() < end_time: + msg = connection.recv_match( + type="PARAM_VALUE", + blocking=True, + timeout=2.0, + ) + if not msg: + continue + + # decrypt and strip message into values + raw_id = msg.param_id + if isinstance(raw_id, bytes): + name = raw_id.decode("ascii", errors="ignore").strip("\x00") + else: + name = str(raw_id).strip("\x00") + + params[name] = float(msg.param_value) + seen_names.add(name) # keeps track of how many parameters collected + + try: + total_count = int(msg.param_count) + except (TypeError, ValueError): + total_count = None + + # break early if all have been collected + if total_count and len(seen_names) >= total_count: + break + finally: + # best-effort close, failure here is non-fatal + try: + connection.close() + except Exception: # pylint: disable=broad-except + pass + + return params + + +def main() -> int: + """ + Main function which calls all others and compares expected parameters to + actual parameters. + """ + address = os.environ.get("PIXHAWK_ADDRESS", DEFAULT_PIXHAWK_ADDRESS) + baud_str = os.environ.get("PIXHAWK_BAUD", str(DEFAULT_PIXHAWK_BAUD)) + baud = int(baud_str) + + baseline = Path(__file__).with_name("parameter_expectations.param") + + if not baseline.exists(): + print(f"Baseline not found: {baseline}") + return 2 # checks for expectations file + + try: + actual = fetch_all_params_mavlink(address, baud=baud, timeout_s=25) + except Exception as exc: # pylint: disable=broad-exception-caught + # attempts to connect to mavlink and returns 2 if failiyre + print(f"Failed to fetch params via MAVLink: {exc}") + return 2 + + expected = parse_params_file(baseline) + missing, mismatches, extras = diff_params(actual, expected) + + if not missing and not mismatches and not extras: + print("All Pixhawk parameters match baseline.") + return 0 # success + + # prints exactly which parameters were not found or are not right + print("Differences found:") + if missing: + print(f"- Missing ({len(missing)}): {missing}") + if mismatches: + lines = [ + f"{name}: expected={exp} actual={act}" + for name, exp, act in mismatches + ] + print(f"- Mismatches ({len(mismatches)}):") + print(" " + "\n ".join(lines)) + if extras: + print(f"- Extras ({len(extras)}): {extras}") + + return 1 # returns 1 if differences are found + + +if __name__ == "__main__": + sys.exit(main()) From a1f7d3a232e435188365a16dec8cb411a06ae0be Mon Sep 17 00:00:00 2001 From: msilvadi Date: Sat, 22 Nov 2025 11:50:06 -0500 Subject: [PATCH 3/3] ensured fcode passed "black" linter --- .../hitl/pixhawk_param_testing/parameter_testing_logic.py | 7 ++----- 1 file changed, 2 insertions(+), 5 deletions(-) diff --git a/tests/integration/hitl/pixhawk_param_testing/parameter_testing_logic.py b/tests/integration/hitl/pixhawk_param_testing/parameter_testing_logic.py index 2d69c29..270e9e1 100644 --- a/tests/integration/hitl/pixhawk_param_testing/parameter_testing_logic.py +++ b/tests/integration/hitl/pixhawk_param_testing/parameter_testing_logic.py @@ -140,7 +140,7 @@ def fetch_all_params_mavlink( - decrypts and strips messages into values """ # imported here so other modules can import this file without pymavlink - from pymavlink import mavutil # pylint: disable=import-outside-toplevel + from pymavlink import mavutil # pylint: disable=import-outside-toplevel # checks if vehicle is alive connection = mavutil.mavlink_connection(address, baud=baud) @@ -231,10 +231,7 @@ def main() -> int: if missing: print(f"- Missing ({len(missing)}): {missing}") if mismatches: - lines = [ - f"{name}: expected={exp} actual={act}" - for name, exp, act in mismatches - ] + lines = [f"{name}: expected={exp} actual={act}" for name, exp, act in mismatches] print(f"- Mismatches ({len(mismatches)}):") print(" " + "\n ".join(lines)) if extras: