#ifndef _chip_h__
#define _chip_h__

/** chip **
 * 
 * Definitions of sensor chips found on Dracal devices.
 * 
 */

#include <stdint.h>

#include "unit.h"

#ifdef __cplusplus
extern "C" {
#endif


/**
 * Return a string description of the given chip.
 * 
 * In order to conserve memory, the implementation only provides a description for chips
 * that are enabled. To enable a chip "CHIPNAME", define the variable "ENABLE_CHIPNAME"
 * at compile-time.
 * 
 * For example, to enable the description for chip id "USBTENKI_CHIP_SHT31_T", define the
 * variable "ENABLE_CHIP_SHT31_T". This is easily achieved by adding the following argument
 * to your CFLAGS: -DENABLE_CHIP_SHT31_T
 */ 
const char *chip_description(uint16_t chip_id);


#ifdef ENABLE_ALL_CHIPS

/**
 * Return a string description of the given chip.
 * 
 * Since this function isn't required on firmware, it is only implemented when
 * ENABLE_ALL_CHIPS is defined.
 */ 
const char *chip_description_short(uint16_t chip_id);

/**
 * Constant array of units indexed by chip ID.
 *
 * Since this array isn't required on firmware, it is only defined when
 * ENABLE_ALL_CHIPS is defined.
 */
extern const unit_t CHIP_NATIVE_UNITS[];

/**
 * Return the native unit of a chip.
 * This macro is provided for backwards compatibility.
 *
 * Since this macro isn't required on firmware, it is only implemented when
 * ENABLE_ALL_CHIPS is defined.
 */
#define chip_native_unit(chip_id)  CHIP_NATIVE_UNITS[(chip_id)]

/**
 * Return a string description of an integer error code.
 *
 * Since this function isn't required on firmware, it is only implemented when
 * ENABLE_ALL_CHIPS is defined.
 */
const char *chip_error_to_string(int32_t error);

/**
 * Return a string description of an integer error code. This is functionally the
 * same as chip_error_to_string() but the resulting string does not contain spaces.
 *
 * Since this function isn't required on firmware, it is only implemented when
 * ENABLE_ALL_CHIPS is defined.
 */
const char *chip_error_to_string_no_spaces(int32_t error);

/**
 * Return a string description of an integer error code.
 *
 * Since this function isn't required on firmware, it is only implemented when
 * ENABLE_ALL_CHIPS is defined.
 */
const char *chip_thermocouple_type_to_string(int8_t type);

/**
 * Return the integer code corresponding to the given thermocouple type string.
 *
 * Since this function isn't required on firmware, it is only implemented when
 * ENABLE_ALL_CHIPS is defined.
 */
int8_t chip_thermocouple_string_to_type(const char *type);

#endif


//
// Error codes
//

#define CHIP_ERROR_UNKNOWN_CHIP  -1
#define CHIP_ERROR_TICKER_DEVICE -2

#define CHIP_ERROR_NO_DATA  1
#define CHIP_ERROR_SATURATED  2
#define CHIP_ERROR_SENSOR_ERROR  3
#define CHIP_ERROR_PROBE_DISCONNECTED  4
#define CHIP_ERROR_OUT_OF_RANGE  5
#define CHIP_ERROR_INVALID_DATA  6
#define CHIP_ERROR_SENSOR_SHORTED  7


//
// Thermocouple type constants
//

#define THERMOCOUPLE_TYPE_MIN  0
#define THERMOCOUPLE_TYPE_K  0
#define THERMOCOUPLE_TYPE_J  1
#define THERMOCOUPLE_TYPE_T  2
#define THERMOCOUPLE_TYPE_N  3
#define THERMOCOUPLE_TYPE_S  4
#define THERMOCOUPLE_TYPE_E  5
#define THERMOCOUPLE_TYPE_B  6
#define THERMOCOUPLE_TYPE_R  7
#define THERMOCOUPLE_TYPE_MAX  7

//
// Chip ID constants
//

#define USBTENKI_CHIP_MCP9800  0x00
#define USBTENKI_CHIP_LM75  0x01
#define USBTENKI_CHIP_LM92  0x02
#define USBTENKI_CHIP_SHT_TEMP  0x03
#define USBTENKI_CHIP_SHT_RH  0x04
#define USBTENKI_CHIP_TSL2561_IR_VISIBLE  0x05
#define USBTENKI_CHIP_TSL2561_IR  0x06

#define USBTENKI_CHIP_BS02_TEMP  0x07
#define USBTENKI_CHIP_BS02_RH  0x08

#define USBTENKI_CHIP_TSL2561_IR_VISIBLE_16X  0x09
#define USBTENKI_CHIP_TSL2561_IR_16X  0x0A

#define USBTENKI_CHIP_TSL2568_IR_VISIBLE  0x0B
#define USBTENKI_CHIP_TSL2568_IR_VISIBLE_16X  0x0C
#define USBTENKI_CHIP_TSL2568_IR  0x0D
#define USBTENKI_CHIP_TSL2568_IR_16X  0x0E

#define USBTENKI_CHIP_SE95  0x0F
#define USBTENKI_CHIP_D6F_V03A1  0x10
#define USBTENKI_CHIP_ADT7410  0x11

#define USBTENKI_CHIP_PT100_RTD  0x12
#define USBTENKI_CHIP_MLX90614_TA  0x13
#define USBTENKI_CHIP_MLX90614_TOBJ  0x14
#define USBTENKI_CHIP_MS5611_P  0x15
#define USBTENKI_CHIP_MS5611_T  0x16

#define USBTENKI_CHIP_CC2_RH  0x17
#define USBTENKI_CHIP_CC2_T  0x18
#define USBTENKI_CHIP_SHT31_RH  0x19
#define USBTENKI_CHIP_SHT35_RH  0x1A
#define USBTENKI_CHIP_SHT35_T  0x1B
#define USBTENKI_CHIP_THC_HOT  0x1C
#define USBTENKI_CHIP_THC_COLD  0x1D
#define USBTENKI_CHIP_SHT31_T  0x20

#define USBTENKI_CHIP_THC_TYPE_K  0x21
#define USBTENKI_CHIP_THC_TYPE_J  0x22
#define USBTENKI_CHIP_THC_TYPE_N  0x23
#define USBTENKI_CHIP_THC_TYPE_E  0x24
#define USBTENKI_CHIP_THC_TYPE_T  0x25
#define USBTENKI_CHIP_THC_TYPE_B  0x26
#define USBTENKI_CHIP_THC_TYPE_S  0x27
#define USBTENKI_CHIP_THC_TYPE_R  0x28

#define USBTENKI_CHIP_VEML6075_UVA  0x2A
#define USBTENKI_CHIP_VEML6075_UVB  0x2B
#define USBTENKI_CHIP_VEML6075_UVCOMP1  0x2C
#define USBTENKI_CHIP_VEML6075_UVCOMP2  0x2D
#define USBTENKI_CHIP_VEML6030_ALS  0x2E
#define USBTENKI_CHIP_VEML6030_WHITE  0x2F

#define USBTENKI_CHIP_DRACAL_EM1_BUS_VOLTAGE  0x30
#define USBTENKI_CHIP_DRACAL_EM1_SHUNT_VOLTAGE  0x31
#define USBTENKI_CHIP_DRACAL_EM1_POWER  0x32
#define USBTENKI_CHIP_DRACAL_EM1_CURRENT  0x33
#define USBTENKI_CHIP_RTD300_PT100_3W  0x34
#define USBTENKI_CHIP_RTD300_PT100_2W  0x35
#define USBTENKI_CHIP_RTD300_PT1000_3W  0x36

#define USBTENKI_CHIP_TMC200_COLD  0x37
#define USBTENKI_CHIP_TMC200_TYPE_K  0x38
#define USBTENKI_CHIP_TMC200_TYPE_J  0x39
#define USBTENKI_CHIP_TMC200_TYPE_N  0x3A
#define USBTENKI_CHIP_TMC200_TYPE_E  0x3B
#define USBTENKI_CHIP_TMC200_TYPE_T  0x3C
#define USBTENKI_CHIP_TMC200_TYPE_B  0x3D
#define USBTENKI_CHIP_TMC200_TYPE_S  0x3E
#define USBTENKI_CHIP_TMC200_TYPE_R  0x3F

#define USBTENKI_CHIP_CO2_PPM  0x40

#define USBTENKI_CHIP_CCS811_TVOC  0x41
#define USBTENKI_CHIP_CCS811_eCO2  0x42

#define USBTENKI_CHIP_RED  0x43
#define USBTENKI_CHIP_GREEN  0x44
#define USBTENKI_CHIP_BLUE  0x45
#define USBTENKI_CHIP_IR  0x46

#define USBTENKI_CHIP_SCD30_CO2  0x47
#define USBTENKI_CHIP_SCD30_T  0x48
#define USBTENKI_CHIP_SCD30_RH  0x49
#define USBTENKI_CHIP_SCD30_CO2_CAL 0x4A

#define USBTENKI_CHIP_SPS30_MC_PM1_0  0x50
#define USBTENKI_CHIP_SPS30_MC_PM2_5  0x51
#define USBTENKI_CHIP_SPS30_MC_PM4_0  0x52
#define USBTENKI_CHIP_SPS30_MC_PM10  0x53
#define USBTENKI_CHIP_SPS30_NC_PM0_5  0x54
#define USBTENKI_CHIP_SPS30_NC_PM1_0  0x55
#define USBTENKI_CHIP_SPS30_NC_PM2_5  0x56
#define USBTENKI_CHIP_SPS30_NC_PM4_0  0x57
#define USBTENKI_CHIP_SPS30_NC_PM10  0x58
#define USBTENKI_CHIP_SPS30_TYP_PART_SIZE  0x59

#define USBTENKI_CHIP_CO2_DXC200_FILTERED  0x5A
#define USBTENKI_CHIP_CO2_DXC200_INSTANT  0x5B

#define USBTENKI_CHIP_CO2_DXC300_COMPENSATED	0x6A
#define USBTENKI_CHIP_CO2_DXC300_RAW	        0x6B
#define USBTENKI_CHIP_CO2_DXC300_P_COMP	        0x6C
#define USBTENKI_CHIP_CO2_DXC300_T_COMP	        0x6D
#define USBTENKI_CHIP_CO2_DXC300_RH_COMP	    0x6E

#define USBTENKI_MCU_ADC0  0x80
#define USBTENKI_MCU_ADC1  0x81
#define USBTENKI_MCU_ADC2  0x82
#define USBTENKI_MCU_ADC3  0x83
#define USBTENKI_MCU_ADC4  0x84
#define USBTENKI_MCU_ADC5  0x85

#define USBTENKI_ACCEL_X  0x8A
#define USBTENKI_ACCEL_Y  0x8B
#define USBTENKI_ACCEL_Z  0x8C

#define USBTENKI_CHIP_MPX4115  0x90

#define USBTENKI_CHIP_VOLTS  0x91
#define USBTENKI_CHIP_VOLTS_REVERSE  0x92

#define USBTENKI_CHIP_MP3H6115A  0x93
#define USBTENKI_CHIP_MPXV7002  0x94

#define USBTENKI_CHIP_MLH_A  0x95

#define USBTENKI_CHIP_TACHOMETER  0xA0

// For cases where there are identical sensors in different locations that must be clearly
// labelled as such (eg: Internal, external...)
#define USBTENKI_CHIP_SHT31_T_INTERNAL  0xB0
#define USBTENKI_CHIP_SHT31_RH_INTERNAL  0xB1
#define USBTENKI_CHIP_SHT31_T_EXTERNAL  0xB2
#define USBTENKI_CHIP_SHT31_RH_EXTERNAL  0xB3

#define USBTENKI_CHIPX_PT100_TMP          0xB8

#define USBTENKI_CHIPX_SHT3X_RH		    0xBC
#define USBTENKI_CHIPX_SHT3X_T		    0xBD
#define USBTENKI_CHIPX_MS5611_P		0xBE
#define USBTENKI_CHIPX_MS5611_T		0xBF

#define USBTENKI_CHIP_TICKER  0xFD
#define USBTENKI_CHIP_MATH    0xFE
#define USBTENKI_CHIP_NONE    0xFF

#define USBTENKI_VIRTUAL_START  0x100
#define USBTENKI_VIRTUAL_DEW_POINT  0x100
#define USBTENKI_VIRTUAL_HUMIDEX  0x101
#define USBTENKI_VIRTUAL_HEAT_INDEX  0x102
#define USBTENKI_VIRTUAL_TSL2561_LUX  0x103
#define USBTENKI_VIRTUAL_TSL2568_LUX  0x104
#define USBTENKI_VIRTUAL_SHT75_COMPENSATED_RH  0x105
#define USBTENKI_VIRTUAL_ALTITUDE  0x106
#define USBTENKI_VIRTUAL_HEXCOLOR  0x107

#define USBTENKI_VIRTUAL_INTERNAL_DEW_POINT  0x108
#define USBTENKI_VIRTUAL_EXTERNAL_DEW_POINT  0x109


#ifdef ENABLE_ALL_CHIPS
    #define ENABLE_CHIP_ADT7410
    #define ENABLE_CHIP_SE95
    #define ENABLE_CHIP_MCP9800
    #define ENABLE_CHIP_LM75
    #define ENABLE_CHIP_LM92
    #define ENABLE_CHIP_SHT_TEMP
    #define ENABLE_CHIP_SHT_RH
    #define ENABLE_CHIP_BS02_TEMP
    #define ENABLE_CHIP_BS02_RH
    #define ENABLE_CHIP_CC2_RH
    #define ENABLE_CHIP_CC2_T
    #define ENABLE_CHIP_SHT31_T
    #define ENABLE_CHIP_SHT31_RH
    #define ENABLE_CHIP_SHT35_T
    #define ENABLE_CHIP_SHT35_RH
    #define ENABLE_CHIP_SCD30_T
    #define ENABLE_CHIP_SCD30_RH
    #define ENABLE_CHIP_SHT31_T_INTERNAL
    #define ENABLE_CHIP_SHT31_RH_INTERNAL
    #define ENABLE_CHIP_SHT31_T_EXTERNAL
    #define ENABLE_CHIP_SHT31_RH_EXTERNAL
    #define ENABLE_CHIP_CCS811_TVOC
    #define ENABLE_CHIP_CCS811_eCO2
    #define ENABLE_CHIP_SCD30_CO2
    #define ENABLE_CHIP_SCD30_CO2_CAL
    #define ENABLE_CHIP_CO2_PPM
    #define ENABLE_CHIP_CO2_DXC200_FILTERED
    #define ENABLE_CHIP_CO2_DXC200_INSTANT
    #define ENABLE_CHIP_CO2_DXC300_COMPENSATED
    #define ENABLE_CHIP_CO2_DXC300_RAW
    #define ENABLE_CHIP_CO2_DXC300_P_COMP
    #define ENABLE_CHIP_CO2_DXC300_T_COMP
    #define ENABLE_CHIP_CO2_DXC300_RH_COMP
    #define ENABLE_CHIP_SPS30_MC_PM1_0
    #define ENABLE_CHIP_SPS30_MC_PM2_5
    #define ENABLE_CHIP_SPS30_MC_PM4_0
    #define ENABLE_CHIP_SPS30_MC_PM10
    #define ENABLE_CHIP_SPS30_NC_PM0_5
    #define ENABLE_CHIP_SPS30_NC_PM1_0
    #define ENABLE_CHIP_SPS30_NC_PM2_5
    #define ENABLE_CHIP_SPS30_NC_PM4_0
    #define ENABLE_CHIP_SPS30_NC_PM10
    #define ENABLE_CHIP_SPS30_TYP_PART_SIZE
    #define ENABLE_CHIP_TSL2561_IR_VISIBLE
    #define ENABLE_CHIP_TSL2561_IR
    #define ENABLE_CHIP_TSL2561_IR_VISIBLE_16X
    #define ENABLE_CHIP_TSL2561_IR_16X
    #define ENABLE_CHIP_TSL2568_IR_VISIBLE
    #define ENABLE_CHIP_TSL2568_IR
    #define ENABLE_CHIP_TSL2568_IR_VISIBLE_16X
    #define ENABLE_CHIP_TSL2568_IR_16X
    #define ENABLE_MCU_ADC0
    #define ENABLE_MCU_ADC1
    #define ENABLE_MCU_ADC2
    #define ENABLE_MCU_ADC3
    #define ENABLE_MCU_ADC4
    #define ENABLE_MCU_ADC5
    #define ENABLE_CHIP_MPXV7002
    #define ENABLE_CHIP_MLH_A
    #define ENABLE_CHIP_MPX4115
    #define ENABLE_CHIP_MP3H6115A
    #define ENABLE_CHIP_VOLTS
    #define ENABLE_CHIP_VOLTS_REVERSE
    #define ENABLE_CHIP_DRACAL_EM1_BUS_VOLTAGE
    #define ENABLE_CHIP_DRACAL_EM1_SHUNT_VOLTAGE
    #define ENABLE_CHIP_DRACAL_EM1_POWER
    #define ENABLE_CHIP_DRACAL_EM1_CURRENT
    #define ENABLE_CHIP_TACHOMETER
    #define ENABLE_CHIP_RTD300_PT100_2W
    #define ENABLE_CHIP_RTD300_PT100_3W
    #define ENABLE_CHIP_RTD300_PT1000_3W
    #define ENABLE_CHIP_PT100_RTD
    #define ENABLE_CHIPX_PT100_TMP
    #define ENABLE_CHIP_TMC200_COLD
    #define ENABLE_CHIP_THC_COLD
    #define ENABLE_CHIP_THC_HOT
    #define ENABLE_CHIP_TMC200_TYPE_K
    #define ENABLE_CHIP_THC_TYPE_K
    #define ENABLE_CHIP_TMC200_TYPE_J
    #define ENABLE_CHIP_THC_TYPE_J
    #define ENABLE_CHIP_TMC200_TYPE_T
    #define ENABLE_CHIP_THC_TYPE_T
    #define ENABLE_CHIP_TMC200_TYPE_N
    #define ENABLE_CHIP_THC_TYPE_N
    #define ENABLE_CHIP_TMC200_TYPE_S
    #define ENABLE_CHIP_THC_TYPE_S
    #define ENABLE_CHIP_TMC200_TYPE_E
    #define ENABLE_CHIP_THC_TYPE_E
    #define ENABLE_CHIP_TMC200_TYPE_B
    #define ENABLE_CHIP_THC_TYPE_B
    #define ENABLE_CHIP_TMC200_TYPE_R
    #define ENABLE_CHIP_THC_TYPE_R
    #define ENABLE_CHIP_MLX90614_TA
    #define ENABLE_CHIP_MLX90614_TOBJ
    #define ENABLE_CHIP_MS5611_P
    #define ENABLE_CHIP_MS5611_T
    #define ENABLE_CHIP_VEML6075_UVA
    #define ENABLE_CHIP_VEML6075_UVB
    #define ENABLE_CHIP_VEML6030_ALS
    #define ENABLE_CHIP_VEML6030_WHITE
    #define ENABLE_CHIP_NONE
    #define ENABLE_CHIP_RED
    #define ENABLE_CHIP_GREEN
    #define ENABLE_CHIP_BLUE
    #define ENABLE_CHIP_IR
    #define ENABLE_CHIPX_SHT3X_RH
    #define ENABLE_CHIPX_SHT3X_T
    #define ENABLE_CHIPX_MS5611_P
    #define ENABLE_CHIPX_MS5611_T
    #define ENABLE_CHIP_TICKER
    #define ENABLE_CHIP_MATH
    #define ENABLE_VIRTUAL_ALTITUDE
    #define ENABLE_VIRTUAL_DEW_POINT
    #define ENABLE_VIRTUAL_EXTERNAL_DEW_POINT
    #define ENABLE_VIRTUAL_HEAT_INDEX
    #define ENABLE_VIRTUAL_HUMIDEX
    #define ENABLE_VIRTUAL_INTERNAL_DEW_POINT
    #define ENABLE_VIRTUAL_SHT75_COMPENSATED_RH
    #define ENABLE_VIRTUAL_TSL2561_LUX
    #define ENABLE_VIRTUAL_TSL2568_LUX
    #define ENABLE_VIRTUAL_HEXCOLOR
#endif


#ifdef __cplusplus
}
#endif

#endif
