#pragma once #include #include #include #include #include #include #include #include #include #define CRC8POLY (0x07) // Polynomial generator for CRC #define CRC8INITVAL (0xFF) enum class Beyond_Device_State { Disconnected, Application, Bootloader, EyetrackingDFU, CrashHandler }; enum class Beyond_Camera_State { Unknown, Valid, NotFound }; // Crash dump variables enum class Beyond_Crash_Reason { Hard_Fault = 0, Unknown_ISR = 1, Stack_Overflow = 2 }; enum class Crash_Dump_State { Begin, Got_SWVer, Got_Reason, Got_Proc1, Got_Proc2, Got_Proc3, Got_Proc4, Got_Name, Got_Num_Mem_Regions, Got_Mem_Region_Info, Done }; enum class Usage_Timer_State { Get_Total_Powered_Time, Get_Display_Time, Get_Longest_Continuous_Time, Done }; struct Crash_Info { std::string swver; Beyond_Crash_Reason crash_reason; uint32_t crash_irq_num; // IRQ number during crash uint32_t hfsr; // hard fault status register uint32_t cfsr; // configurable fault status register std::string crashed_task_name; // only valid if reason is Stack_Overflow // Crash dump processor state std::array regs; uint32_t psr; uint32_t msp; uint32_t psp; uint32_t exception_psr; std::array floats; uint32_t fpscr; // Memory dump information uint32_t num_mem_regions; using mem_region_info = std::tuple; std::vector mem_info; std::vector mem_dump; }; // Calculates a CRC8 checksum value over any length of data static uint8_t crc8(const uint8_t* input_data, uint32_t len) { uint32_t i; uint8_t j; uint8_t initcrc = CRC8INITVAL; const uint8_t* l_input; l_input = input_data; for (i = 0; i < len; i++) { initcrc ^= *l_input; l_input++; for (j = 0; j < 8; j++) { if (initcrc & 0x80u) { initcrc = (initcrc << 1) ^ CRC8POLY; } else { initcrc = (initcrc << 1); } } } return initcrc; } typedef std::tuple Config_T; namespace Config_Tags { enum Config_Tags { PCBA_Serial = 0x01, // Serial number of the HMD's main board RGB_Color = 0x02, // Startup RGB color Fan_Speed = 0x03, // Startup fan speed Prox_Disable = 0x04, // Disable the proximity sensor (displays always on) Linkbox_v1 = 0x05, // !DEPRECATED! changes the HPD signal level for compatibility with very old linkboxes Prox_Cal = 0x06, // Calibration value of proximity sensor, subtracted from raw reading FATP_Mode = 0x07, // Forces non-DSC "Final Assembly Test Plan" mode HMD_Serial = 0x08, // HMD's overall serial number Tracking_Serial = 0x09, // Tracking flex serial number Display_Brightness = 0x0A, // Default display brightness, 0->1023 Prox_Threshold = 0x0B, // Value at which proximity triggers the displays on / off Prox_Hysteresis = 0x0C, // Amount proximity needs to change for a switch in state, prevents unwanted frequent switching EDID_Switch = 0x0D, // Changes available video timings Prox_Offset = 0x0E, // Proximity trim offset VXR_Sleep_Enable = 0x0F, // Enabling VXR auto-shutoff; default is 0 (not loaded) which is no sleep. Invalid = 0xFF, }; const std::vector readableTags = { std::to_string(static_cast(Config_Tags::PCBA_Serial)), std::to_string(static_cast(Config_Tags::Tracking_Serial)), std::to_string(static_cast(Config_Tags::HMD_Serial)) }; }; // Special version for the bootloader. Initial value is zero. Otherwise identical to "crc8" static uint8_t crc8_bootloader(const uint8_t* input_data, uint32_t len) { uint32_t i; uint8_t j; uint8_t initcrc = 0; const uint8_t* l_input; l_input = input_data; for (i = 0; i < len; i++) { initcrc ^= *l_input; l_input++; for (j = 0; j < 8; j++) { if (initcrc & 0x80u) { initcrc = (initcrc << 1) ^ CRC8POLY; } else { initcrc = (initcrc << 1); } } } return initcrc; } /// struct HidHandler { // Main application HID commands void command_software_version(); void command_serial_number(); void command_hmd_serial_number(); void command_tracking_flex_serial_number(); void command_oled_serial_number(); void command_usage_timer(unsigned char usage_type); void command_mic_stereo(unsigned char stereo); void command_mic_integer_gain(unsigned short integer_gain); void command_mic_fractional_gain(unsigned short fractional_gain); void command_fan_speed_immediate(unsigned char fan_speed); void command_fan_speed_deferred(unsigned char fan_speed); void command_periodic_data_rate(unsigned short rate); void command_oled_vertical_flip(unsigned char flip); void command_oled_brightness(unsigned short brightness); void command_restart_in_bootloader(); void command_fpga_switch(); void command_rgb_led_color(unsigned char red, unsigned char green, unsigned char blue); void command_read_config(unsigned char block); void command_write_config(unsigned char block, unsigned char data[32]); void command_save_config(); void command_proximity_settings(unsigned char pwen, unsigned char prate, unsigned char pwlong, unsigned char pgain, unsigned char ppulse, unsigned char plen, unsigned char pldrive, unsigned char pwtime, unsigned char pdselect, unsigned char pmavg, unsigned char proxavg); void command_vxr_checksum(unsigned int start_address, unsigned int length); void command_vxr_query_tags(); void command_proximity_offset(uint16_t offset); void command_vxr_delete_block(unsigned char bank); void command_vxr_program(unsigned char length, unsigned int start_location, unsigned char data[32]); void command_vxr_reset(); void command_vxr_name(); void command_hardware_test(unsigned char test); void command_enter_fatp(); void command_edid_switch(unsigned char which_edid); void command_direct_oled(unsigned char which_oled, unsigned char length, unsigned char* data); bool verify_config(); void parse_config(); void save_config(std::vector new_entries); // Bootloader HID commands void blcommand_restart(); void blcommand_software_version(); void blcommand_write_data(uint32_t mem_address, unsigned char length, unsigned char* data); void blcommand_program_data(uint32_t mem_address); void blcommand_erase_app(); void blcommand_erase_flash(unsigned char erase_size_code, uint32_t mem_address); // Crashdump HID commands void cdcommand_get_crash_dump(); void cdcommand_software_version(); void cdcommand_get_reason(); void cdcommand_get_processor_state(uint32_t which_part); void cdcommand_get_task_name(); void cdcommand_get_num_mem_regions(); void cdcommand_get_mem_region_info(uint32_t which_region); void cdcommand_get_memory_dump(uint32_t startaddr, uint32_t length, uint32_t repeat_count); void cdcommand_restart(); void run(); void shutdown(); std::pair in_dfu(); std::string get_lighthouse_serial(); std::string get_device_rev(std::string targetVid, std::string targetPid); std::pair get_device(std::string targetVid, std::string targetPid, std::wstring targetName); bool uninstall_camera(std::string targetVid, std::string targetPid); const uint32_t CONFIG_DATA_LENGTH = 512; std::thread thread; std::atomic ready; std::atomic awaiting_device; std::atomic device_state; std::atomic et_camera_state; std::atomic bl_request_software_version; std::atomic bl_got_status; std::atomic pending_log; std::atomic entering_dfu; std::atomic leaving_dfu; std::atomic startup_camera_restart; std::atomic bl_status; std::atomic waiting_on_block; hid_device* device; std::mutex command_mutex; std::vector pending_commands; std::wofstream log; std::wstring error; uint64_t last_info_log; uint64_t last_usage_timer_request; uint64_t last_lhr_serial_request; uint64_t last_device_check_request; uint64_t last_camera_check_request; uint16_t et_camera_check_attempt; std::atomic usage_timer_status; std::atomic crashdump_status; Crash_Info cdinfo; std::atomic current_mem_region_number; std::atomic total_mem_dumped; std::atomic current_mem_addr; int64_t total_power_on = -1; int64_t displays_on = -1; int64_t longest_displays_on = -1; std::string firmware_version; std::string blfirmware_version; std::string et_cam_version; std::string hmd_serial; std::string tundra_serial; unsigned char raw_config[512]; std::vector> config; // Tag, data tuple std::vector rpm_samples; }; extern HidHandler hid_handler;