├── .gitignore ├── main ├── CMakeLists.txt ├── component.mk ├── redar_i2c_driver.h ├── redar.c ├── MLX90640_API.h ├── redar_i2c_driver.c └── MLX90640_API.c ├── Makefile ├── CMakeLists.txt ├── README.md ├── LICENSE └── sdkconfig /.gitignore: -------------------------------------------------------------------------------- 1 | build 2 | -------------------------------------------------------------------------------- /main/CMakeLists.txt: -------------------------------------------------------------------------------- 1 | idf_component_register(SRCS "redar.c" 2 | INCLUDE_DIRS "") -------------------------------------------------------------------------------- /main/component.mk: -------------------------------------------------------------------------------- 1 | # 2 | # "main" pseudo-component makefile. 3 | # 4 | # (Uses default behaviour of compiling all source files in directory, adding 'include' to include path.) 5 | 6 | -------------------------------------------------------------------------------- /Makefile: -------------------------------------------------------------------------------- 1 | # 2 | # This is a project Makefile. It is assumed the directory this Makefile resides in is a 3 | # project subdirectory. 4 | # 5 | 6 | PROJECT_NAME := hello-world 7 | 8 | include $(IDF_PATH)/make/project.mk 9 | 10 | -------------------------------------------------------------------------------- /CMakeLists.txt: -------------------------------------------------------------------------------- 1 | # The following lines of boilerplate have to be in your project's 2 | # CMakeLists in this exact order for cmake to work correctly 3 | cmake_minimum_required(VERSION 3.5) 4 | 5 | include($ENV{IDF_PATH}/tools/cmake/project.cmake) 6 | project(hello-world) -------------------------------------------------------------------------------- /main/redar_i2c_driver.h: -------------------------------------------------------------------------------- 1 | #ifndef _REDAR_I2C_DRIVER_ 2 | #define _REDAR_I2C_DRIVER_ 3 | 4 | 5 | #define SDA_PIN 21 6 | #define SCL_PIN 22 7 | #define I2C_BUS_FREQUENCY_HZ 1000000 8 | #define ACK_CHECK_EN 0x1 9 | #define ACK_CHECK_DIS 0x0 10 | #define ACK_VAL 0x0 11 | #define NACK_VAL 0x1 12 | #define I2C_MASTER_TIMEOUT_MS 1000 13 | 14 | #include 15 | 16 | 17 | void REDAR_I2CInit(void); 18 | int REDAR_I2CRead(uint8_t slaveAddr,uint16_t startAddress, uint16_t nMemAddressRead, uint16_t *data); 19 | int REDAR_I2CWrite(uint8_t slaveAddr,uint16_t writeAddress, uint16_t data); 20 | #endif -------------------------------------------------------------------------------- /README.md: -------------------------------------------------------------------------------- 1 | # REDar - infraRed Radar 2 | 3 | Using MLX90640 and ESP32, read an IR image of 32x24 pixels 4 | 5 | ## Hardware Requirements 6 | - ESP32 7 | - MLX90640 8 | - Mac, Linux or Windows for programming 9 | 10 | ## Software Requirements 11 | - [ESP-IDF](https://github.com/espressif/esp-idf) v4.0 (Probably works with other versions too) 12 | 13 | ## How-To 14 | This assumes command-line and ESP-IDF knowledge. 15 | - Install ESP-IDF on your system and set it up properly (source the environment & provide path to your USB device) 16 | - Wire the MLX sensor to ESP32 power and ESP32 I2C bus 17 | - SDA_PIN 21 & SCL_PIN 22 are defaults in this code 18 | 19 | - Clone this repo 20 | - Within this repo: make flash & make monitor 21 | 22 | ## Program entry point 23 | - redar.c in main folder 24 | 25 | ## What it does 26 | Right now it only reads out cyclically the temperature array properly 27 | 28 | ## References 29 | - [MLX90640 generic C driver](https://github.com/melexis/mlx90640-library) 30 | - [MLX90640 Datasheet](https://www.melexis.com/-/media/files/documents/datasheets/mlx90640-datasheet-melexis.pdf) -------------------------------------------------------------------------------- /LICENSE: -------------------------------------------------------------------------------- 1 | MIT License 2 | 3 | Copyright (c) 2020 Patrick Wieder 4 | 5 | Permission is hereby granted, free of charge, to any person obtaining a copy 6 | of this software and associated documentation files (the "Software"), to deal 7 | in the Software without restriction, including without limitation the rights 8 | to use, copy, modify, merge, publish, distribute, sublicense, and/or sell 9 | copies of the Software, and to permit persons to whom the Software is 10 | furnished to do so, subject to the following conditions: 11 | 12 | The above copyright notice and this permission notice shall be included in all 13 | copies or substantial portions of the Software. 14 | 15 | THE SOFTWARE IS PROVIDED "AS IS", WITHOUT WARRANTY OF ANY KIND, EXPRESS OR 16 | IMPLIED, INCLUDING BUT NOT LIMITED TO THE WARRANTIES OF MERCHANTABILITY, 17 | FITNESS FOR A PARTICULAR PURPOSE AND NONINFRINGEMENT. IN NO EVENT SHALL THE 18 | AUTHORS OR COPYRIGHT HOLDERS BE LIABLE FOR ANY CLAIM, DAMAGES OR OTHER 19 | LIABILITY, WHETHER IN AN ACTION OF CONTRACT, TORT OR OTHERWISE, ARISING FROM, 20 | OUT OF OR IN CONNECTION WITH THE SOFTWARE OR THE USE OR OTHER DEALINGS IN THE 21 | SOFTWARE. 22 | -------------------------------------------------------------------------------- /main/redar.c: -------------------------------------------------------------------------------- 1 | #include 2 | #include "sdkconfig.h" 3 | #include "freertos/FreeRTOS.h" 4 | #include "freertos/task.h" 5 | #include "esp_system.h" 6 | #include "esp_spi_flash.h" 7 | #include "esp_log.h" 8 | 9 | #include "MLX90640_API.h" 10 | 11 | #define TA_SHIFT 8 12 | float emissivity = 0.95; 13 | float tr; 14 | unsigned char slaveAddress = 0x33; 15 | static uint16_t eeMLX90640[832]; 16 | static uint16_t mlx90640Frame[834]; 17 | paramsMLX90640 mlx90640; 18 | static float mlx90640To[768]; 19 | int status; 20 | const TickType_t xDelay = 2000 / portTICK_PERIOD_MS; 21 | 22 | 23 | void app_main(void) 24 | { 25 | printf("Starting IR Cam...\n"); 26 | REDAR_I2CInit(); 27 | status = MLX90640_DumpEE (slaveAddress, eeMLX90640); 28 | status = MLX90640_ExtractParameters(eeMLX90640, &mlx90640); 29 | 30 | 31 | 32 | while(1) 33 | { 34 | // default mode is chess mode, only every second pixel will be updated 35 | //2 subframes needed for full image update 36 | //default sampling on sensor is 2Hz. 37 | 38 | MLX90640_GetSubFrameData (slaveAddress, mlx90640Frame); 39 | tr = MLX90640_GetTa(mlx90640Frame, &mlx90640) - TA_SHIFT; 40 | MLX90640_CalculateTo(mlx90640Frame, &mlx90640, emissivity, tr, mlx90640To); 41 | 42 | MLX90640_GetSubFrameData (slaveAddress, mlx90640Frame); 43 | tr = MLX90640_GetTa(mlx90640Frame, &mlx90640) - TA_SHIFT; 44 | MLX90640_CalculateTo(mlx90640Frame, &mlx90640, emissivity, tr, mlx90640To); 45 | 46 | for(int p=0;p< 768; p++) 47 | { 48 | ESP_LOGI("REDAR","T[%i]=%.2f", p, mlx90640To[p]); 49 | } 50 | 51 | vTaskDelay( xDelay ); 52 | } 53 | 54 | } 55 | -------------------------------------------------------------------------------- /main/MLX90640_API.h: -------------------------------------------------------------------------------- 1 | /** 2 | * @copyright (C) 2017 Melexis N.V. 3 | * 4 | * Licensed under the Apache License, Version 2.0 (the "License"); 5 | * you may not use this file except in compliance with the License. 6 | * You may obtain a copy of the License at 7 | * 8 | * http://www.apache.org/licenses/LICENSE-2.0 9 | * 10 | * Unless required by applicable law or agreed to in writing, software 11 | * distributed under the License is distributed on an "AS IS" BASIS, 12 | * WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied. 13 | * See the License for the specific language governing permissions and 14 | * limitations under the License. 15 | * 16 | */ 17 | 18 | #include 19 | #include "redar_i2c_driver.h" 20 | 21 | #ifndef _MLX640_API_H_ 22 | #define _MLX640_API_H_ 23 | 24 | #define SCALEALPHA 0.000001 25 | 26 | typedef struct 27 | { 28 | int16_t kVdd; 29 | int16_t vdd25; 30 | float KvPTAT; 31 | float KtPTAT; 32 | uint16_t vPTAT25; 33 | float alphaPTAT; 34 | int16_t gainEE; 35 | float tgc; 36 | float cpKv; 37 | float cpKta; 38 | uint8_t resolutionEE; 39 | uint8_t calibrationModeEE; 40 | float KsTa; 41 | float ksTo[5]; 42 | int16_t ct[5]; 43 | uint16_t alpha[768]; 44 | uint8_t alphaScale; 45 | int16_t offset[768]; 46 | int8_t kta[768]; 47 | uint8_t ktaScale; 48 | int8_t kv[768]; 49 | uint8_t kvScale; 50 | float cpAlpha[2]; 51 | int16_t cpOffset[2]; 52 | float ilChessC[3]; 53 | uint16_t brokenPixels[5]; 54 | uint16_t outlierPixels[5]; 55 | } paramsMLX90640; 56 | 57 | int MLX90640_DumpEE(uint8_t slaveAddr, uint16_t *eeData); 58 | int MLX90640_GetSubFrameData(uint8_t slaveAddr, uint16_t *frameData); 59 | int MLX90640_GetFrameData(uint8_t slaveAddr, uint16_t *frameData); 60 | int MLX90640_ExtractParameters(uint16_t *eeData, paramsMLX90640 *mlx90640); 61 | float MLX90640_GetVdd(uint16_t *frameData, const paramsMLX90640 *params); 62 | float MLX90640_GetTa(uint16_t *frameData, const paramsMLX90640 *params); 63 | void MLX90640_GetImage(uint16_t *frameData, const paramsMLX90640 *params, float *result); 64 | void MLX90640_CalculateTo(uint16_t *frameData, const paramsMLX90640 *params, float emissivity, float tr, float *result); 65 | int MLX90640_SetResolution(uint8_t slaveAddr, uint8_t resolution); 66 | int MLX90640_GetCurResolution(uint8_t slaveAddr); 67 | int MLX90640_SetRefreshRate(uint8_t slaveAddr, uint8_t refreshRate); 68 | int MLX90640_GetRefreshRate(uint8_t slaveAddr); 69 | int MLX90640_GetSubPageNumber(uint16_t *frameData); 70 | int MLX90640_GetCurMode(uint8_t slaveAddr); 71 | int MLX90640_SetInterleavedMode(uint8_t slaveAddr); 72 | int MLX90640_SetChessMode(uint8_t slaveAddr); 73 | void MLX90640_BadPixelsCorrection(uint16_t *pixels, float *to, int mode, paramsMLX90640 *params); 74 | 75 | #endif 76 | -------------------------------------------------------------------------------- /main/redar_i2c_driver.c: -------------------------------------------------------------------------------- 1 | #include "redar_i2c_driver.h" 2 | #include "driver/i2c.h" 3 | #include "freertos/FreeRTOS.h" 4 | #include "freertos/task.h" 5 | #include "esp_system.h" 6 | #include "esp_log.h" 7 | 8 | void REDAR_I2CInit() 9 | { 10 | i2c_config_t conf = { 11 | .mode = I2C_MODE_MASTER, 12 | .sda_io_num = SDA_PIN, 13 | .sda_pullup_en = GPIO_PULLUP_ENABLE, 14 | .scl_io_num = SCL_PIN, 15 | .scl_pullup_en = GPIO_PULLUP_ENABLE, 16 | .master.clk_speed = I2C_BUS_FREQUENCY_HZ 17 | }; 18 | 19 | esp_err_t cret = i2c_param_config(I2C_NUM_0,&conf); 20 | esp_err_t iret = i2c_driver_install(I2C_NUM_0, I2C_MODE_MASTER, 0, 0, 0); 21 | if(cret != ESP_OK || iret != ESP_OK) 22 | { 23 | ESP_LOGE("REDAR", "I2C INSTALL ERROR %i %i", cret, iret); 24 | } 25 | } 26 | 27 | int REDAR_I2CRead(uint8_t slaveAddr, uint16_t startAddress, uint16_t nMemAddressRead, uint16_t *data) 28 | { 29 | uint8_t sa; 30 | int cnt = 0; 31 | int i = 0; 32 | uint8_t command[2] = {0,0}; 33 | uint8_t * i2cData; 34 | int i2cData_len = 1664; 35 | i2cData = malloc(i2cData_len); 36 | uint16_t *p; 37 | 38 | p = data; 39 | sa = (slaveAddr << 1); 40 | command[0] = startAddress >> 8; 41 | command[1] = startAddress & 0x00FF; 42 | 43 | i2c_cmd_handle_t cmd = i2c_cmd_link_create(); 44 | i2c_master_start(cmd); 45 | //slave address 46 | i2c_master_write_byte(cmd,sa | I2C_MASTER_WRITE, ACK_CHECK_EN); 47 | //device registers to be read 48 | i2c_master_write(cmd,command,2,ACK_CHECK_EN); 49 | 50 | i2c_master_start(cmd); 51 | //slave address before streaming 52 | i2c_master_write_byte(cmd,sa | I2C_MASTER_READ, ACK_CHECK_EN); 53 | //read all bytes -1 terminated with ACK 54 | i2c_master_read(cmd,i2cData,2*nMemAddressRead-1,ACK_VAL); 55 | //read final byte termated with NACK 56 | i2c_master_read_byte(cmd,i2cData+(2*nMemAddressRead-1),NACK_VAL); 57 | i2c_master_stop(cmd); 58 | 59 | esp_err_t ret = i2c_master_cmd_begin(I2C_NUM_0, cmd, I2C_MASTER_TIMEOUT_MS / portTICK_RATE_MS); 60 | i2c_cmd_link_delete(cmd); 61 | 62 | 63 | for(cnt=0; cnt < nMemAddressRead; cnt++) 64 | { 65 | i = cnt << 1; 66 | *p++ = (uint16_t)i2cData[i]*256 + (uint16_t)i2cData[i+1]; 67 | } 68 | 69 | free(i2cData); 70 | 71 | if(ret != ESP_OK) 72 | { 73 | ESP_LOGE("REDAR", "I2C READ ERROR %i", ret); 74 | } 75 | return ret; 76 | } 77 | 78 | int REDAR_I2CWrite(uint8_t slaveAddr, uint16_t writeAddress, uint16_t data) 79 | { 80 | 81 | uint8_t sa; 82 | uint8_t command[4] = {0,0,0,0}; 83 | static uint16_t dataCheck; 84 | 85 | 86 | sa = (slaveAddr << 1); 87 | command[0] = writeAddress >> 8; 88 | command[1] = writeAddress & 0x00FF; 89 | command[2] = data >> 8; 90 | command[3] = data & 0x00FF; 91 | 92 | i2c_cmd_handle_t cmd = i2c_cmd_link_create(); 93 | i2c_master_start(cmd); 94 | i2c_master_write_byte(cmd,sa | I2C_MASTER_WRITE, ACK_CHECK_EN); 95 | i2c_master_write(cmd,command,4,ACK_CHECK_EN); 96 | i2c_master_stop(cmd); 97 | 98 | esp_err_t ret = i2c_master_cmd_begin(I2C_NUM_0, cmd, I2C_MASTER_TIMEOUT_MS / portTICK_RATE_MS); 99 | i2c_cmd_link_delete(cmd); 100 | 101 | if(ret != ESP_OK) 102 | { 103 | ESP_LOGE("REDAR", "I2C WRITE ERROR"); 104 | } 105 | 106 | REDAR_I2CRead(slaveAddr,writeAddress,1, &dataCheck); 107 | if ( dataCheck != data) 108 | { 109 | return -2; 110 | } 111 | 112 | return 0; 113 | } 114 | 115 | -------------------------------------------------------------------------------- /sdkconfig: -------------------------------------------------------------------------------- 1 | # 2 | # Automatically generated file. DO NOT EDIT. 3 | # Espressif IoT Development Framework (ESP-IDF) Project Configuration 4 | # 5 | CONFIG_IDF_TARGET_ESP32=y 6 | CONFIG_IDF_TARGET="esp32" 7 | CONFIG_IDF_FIRMWARE_CHIP_ID=0x0000 8 | 9 | # 10 | # SDK tool configuration 11 | # 12 | CONFIG_SDK_TOOLPREFIX="xtensa-esp32-elf-" 13 | CONFIG_SDK_PYTHON="python" 14 | CONFIG_SDK_MAKE_WARN_UNDEFINED_VARIABLES=y 15 | CONFIG_APP_COMPILE_TIME_DATE=y 16 | # CONFIG_APP_EXCLUDE_PROJECT_VER_VAR is not set 17 | # CONFIG_APP_EXCLUDE_PROJECT_NAME_VAR is not set 18 | # CONFIG_BOOTLOADER_LOG_LEVEL_NONE is not set 19 | # CONFIG_BOOTLOADER_LOG_LEVEL_ERROR is not set 20 | # CONFIG_BOOTLOADER_LOG_LEVEL_WARN is not set 21 | CONFIG_BOOTLOADER_LOG_LEVEL_INFO=y 22 | # CONFIG_BOOTLOADER_LOG_LEVEL_DEBUG is not set 23 | # CONFIG_BOOTLOADER_LOG_LEVEL_VERBOSE is not set 24 | CONFIG_BOOTLOADER_LOG_LEVEL=3 25 | # CONFIG_BOOTLOADER_VDDSDIO_BOOST_1_8V is not set 26 | CONFIG_BOOTLOADER_VDDSDIO_BOOST_1_9V=y 27 | # CONFIG_BOOTLOADER_FACTORY_RESET is not set 28 | # CONFIG_BOOTLOADER_APP_TEST is not set 29 | CONFIG_BOOTLOADER_WDT_ENABLE=y 30 | # CONFIG_BOOTLOADER_WDT_DISABLE_IN_USER_CODE is not set 31 | CONFIG_BOOTLOADER_WDT_TIME_MS=9000 32 | # CONFIG_BOOTLOADER_APP_ROLLBACK_ENABLE is not set 33 | # CONFIG_SECURE_SIGNED_APPS_NO_SECURE_BOOT is not set 34 | # CONFIG_SECURE_BOOT_ENABLED is not set 35 | # CONFIG_SECURE_FLASH_ENC_ENABLED is not set 36 | CONFIG_ESPTOOLPY_PORT="/dev/ttyUSB0" 37 | CONFIG_ESPTOOLPY_BAUD_115200B=y 38 | # CONFIG_ESPTOOLPY_BAUD_230400B is not set 39 | # CONFIG_ESPTOOLPY_BAUD_921600B is not set 40 | # CONFIG_ESPTOOLPY_BAUD_2MB is not set 41 | # CONFIG_ESPTOOLPY_BAUD_OTHER is not set 42 | CONFIG_ESPTOOLPY_BAUD_OTHER_VAL=115200 43 | CONFIG_ESPTOOLPY_BAUD=115200 44 | CONFIG_ESPTOOLPY_COMPRESSED=y 45 | # CONFIG_ESPTOOLPY_FLASHMODE_QIO is not set 46 | # CONFIG_ESPTOOLPY_FLASHMODE_QOUT is not set 47 | CONFIG_ESPTOOLPY_FLASHMODE_DIO=y 48 | # CONFIG_ESPTOOLPY_FLASHMODE_DOUT is not set 49 | CONFIG_ESPTOOLPY_FLASHMODE="dio" 50 | # CONFIG_ESPTOOLPY_FLASHFREQ_80M is not set 51 | CONFIG_ESPTOOLPY_FLASHFREQ_40M=y 52 | # CONFIG_ESPTOOLPY_FLASHFREQ_26M is not set 53 | # CONFIG_ESPTOOLPY_FLASHFREQ_20M is not set 54 | CONFIG_ESPTOOLPY_FLASHFREQ="40m" 55 | # CONFIG_ESPTOOLPY_FLASHSIZE_1MB is not set 56 | CONFIG_ESPTOOLPY_FLASHSIZE_2MB=y 57 | # CONFIG_ESPTOOLPY_FLASHSIZE_4MB is not set 58 | # CONFIG_ESPTOOLPY_FLASHSIZE_8MB is not set 59 | # CONFIG_ESPTOOLPY_FLASHSIZE_16MB is not set 60 | CONFIG_ESPTOOLPY_FLASHSIZE="2MB" 61 | CONFIG_ESPTOOLPY_FLASHSIZE_DETECT=y 62 | CONFIG_ESPTOOLPY_BEFORE_RESET=y 63 | # CONFIG_ESPTOOLPY_BEFORE_NORESET is not set 64 | CONFIG_ESPTOOLPY_BEFORE="default_reset" 65 | CONFIG_ESPTOOLPY_AFTER_RESET=y 66 | # CONFIG_ESPTOOLPY_AFTER_NORESET is not set 67 | CONFIG_ESPTOOLPY_AFTER="hard_reset" 68 | # CONFIG_ESPTOOLPY_MONITOR_BAUD_9600B is not set 69 | # CONFIG_ESPTOOLPY_MONITOR_BAUD_57600B is not set 70 | CONFIG_ESPTOOLPY_MONITOR_BAUD_115200B=y 71 | # CONFIG_ESPTOOLPY_MONITOR_BAUD_230400B is not set 72 | # CONFIG_ESPTOOLPY_MONITOR_BAUD_921600B is not set 73 | # CONFIG_ESPTOOLPY_MONITOR_BAUD_2MB is not set 74 | # CONFIG_ESPTOOLPY_MONITOR_BAUD_OTHER is not set 75 | CONFIG_ESPTOOLPY_MONITOR_BAUD_OTHER_VAL=115200 76 | CONFIG_ESPTOOLPY_MONITOR_BAUD=115200 77 | CONFIG_PARTITION_TABLE_SINGLE_APP=y 78 | # CONFIG_PARTITION_TABLE_TWO_OTA is not set 79 | # CONFIG_PARTITION_TABLE_CUSTOM is not set 80 | CONFIG_PARTITION_TABLE_CUSTOM_FILENAME="partitions.csv" 81 | CONFIG_PARTITION_TABLE_FILENAME="partitions_singleapp.csv" 82 | CONFIG_PARTITION_TABLE_OFFSET=0x8000 83 | CONFIG_PARTITION_TABLE_MD5=y 84 | CONFIG_COMPILER_OPTIMIZATION_LEVEL_DEBUG=y 85 | # CONFIG_COMPILER_OPTIMIZATION_LEVEL_RELEASE is not set 86 | CONFIG_COMPILER_OPTIMIZATION_ASSERTIONS_ENABLE=y 87 | # CONFIG_COMPILER_OPTIMIZATION_ASSERTIONS_SILENT is not set 88 | # CONFIG_COMPILER_OPTIMIZATION_ASSERTIONS_DISABLE is not set 89 | # CONFIG_COMPILER_CXX_EXCEPTIONS is not set 90 | CONFIG_COMPILER_STACK_CHECK_MODE_NONE=y 91 | # CONFIG_COMPILER_STACK_CHECK_MODE_NORM is not set 92 | # CONFIG_COMPILER_STACK_CHECK_MODE_STRONG is not set 93 | # CONFIG_COMPILER_STACK_CHECK_MODE_ALL is not set 94 | # CONFIG_COMPILER_STACK_CHECK is not set 95 | # CONFIG_COMPILER_WARN_WRITE_STRINGS is not set 96 | # CONFIG_COMPILER_DISABLE_GCC8_WARNINGS is not set 97 | # CONFIG_ESP32_APPTRACE_DEST_TRAX is not set 98 | CONFIG_ESP32_APPTRACE_DEST_NONE=y 99 | # CONFIG_ESP32_APPTRACE_ENABLE is not set 100 | CONFIG_ESP32_APPTRACE_LOCK_ENABLE=y 101 | # CONFIG_BT_ENABLED is not set 102 | CONFIG_BTDM_CTRL_BR_EDR_SCO_DATA_PATH_EFF=0 103 | # CONFIG_BTDM_CTRL_AUTO_LATENCY_EFF is not set 104 | CONFIG_BTDM_CTRL_BLE_MAX_CONN_EFF=0 105 | CONFIG_BTDM_CTRL_BR_EDR_MAX_ACL_CONN_EFF=0 106 | CONFIG_BTDM_CTRL_BR_EDR_MAX_SYNC_CONN_EFF=0 107 | CONFIG_BTDM_CTRL_PINNED_TO_CORE=0 108 | CONFIG_BTDM_BLE_SLEEP_CLOCK_ACCURACY_INDEX_EFF=1 109 | CONFIG_BT_RESERVE_DRAM=0 110 | # CONFIG_BLE_MESH is not set 111 | # CONFIG_ADC_FORCE_XPD_FSM is not set 112 | CONFIG_ADC_DISABLE_DAC=y 113 | # CONFIG_SPI_MASTER_IN_IRAM is not set 114 | CONFIG_SPI_MASTER_ISR_IN_IRAM=y 115 | # CONFIG_SPI_SLAVE_IN_IRAM is not set 116 | CONFIG_SPI_SLAVE_ISR_IN_IRAM=y 117 | # CONFIG_EFUSE_CUSTOM_TABLE is not set 118 | # CONFIG_EFUSE_VIRTUAL is not set 119 | # CONFIG_EFUSE_CODE_SCHEME_COMPAT_NONE is not set 120 | CONFIG_EFUSE_CODE_SCHEME_COMPAT_3_4=y 121 | # CONFIG_EFUSE_CODE_SCHEME_COMPAT_REPEAT is not set 122 | CONFIG_EFUSE_MAX_BLK_LEN=192 123 | # CONFIG_ESP_TLS_SERVER is not set 124 | CONFIG_ESP32_REV_MIN_0=y 125 | # CONFIG_ESP32_REV_MIN_1 is not set 126 | # CONFIG_ESP32_REV_MIN_2 is not set 127 | # CONFIG_ESP32_REV_MIN_3 is not set 128 | CONFIG_ESP32_REV_MIN=0 129 | CONFIG_ESP32_DPORT_WORKAROUND=y 130 | # CONFIG_ESP32_DEFAULT_CPU_FREQ_80 is not set 131 | CONFIG_ESP32_DEFAULT_CPU_FREQ_160=y 132 | # CONFIG_ESP32_DEFAULT_CPU_FREQ_240 is not set 133 | CONFIG_ESP32_DEFAULT_CPU_FREQ_MHZ=160 134 | # CONFIG_ESP32_SPIRAM_SUPPORT is not set 135 | # CONFIG_ESP32_MEMMAP_TRACEMEM is not set 136 | # CONFIG_ESP32_MEMMAP_TRACEMEM_TWOBANKS is not set 137 | # CONFIG_ESP32_TRAX is not set 138 | CONFIG_ESP32_TRACEMEM_RESERVE_DRAM=0x0 139 | # CONFIG_ESP32_UNIVERSAL_MAC_ADDRESSES_TWO is not set 140 | CONFIG_ESP32_UNIVERSAL_MAC_ADDRESSES_FOUR=y 141 | CONFIG_ESP32_UNIVERSAL_MAC_ADDRESSES=4 142 | # CONFIG_ESP32_ULP_COPROC_ENABLED is not set 143 | CONFIG_ESP32_ULP_COPROC_RESERVE_MEM=0 144 | # CONFIG_ESP32_PANIC_PRINT_HALT is not set 145 | CONFIG_ESP32_PANIC_PRINT_REBOOT=y 146 | # CONFIG_ESP32_PANIC_SILENT_REBOOT is not set 147 | # CONFIG_ESP32_PANIC_GDBSTUB is not set 148 | CONFIG_ESP32_DEBUG_OCDAWARE=y 149 | CONFIG_ESP32_DEBUG_STUBS_ENABLE=y 150 | CONFIG_ESP32_BROWNOUT_DET=y 151 | CONFIG_ESP32_BROWNOUT_DET_LVL_SEL_0=y 152 | # CONFIG_ESP32_BROWNOUT_DET_LVL_SEL_1 is not set 153 | # CONFIG_ESP32_BROWNOUT_DET_LVL_SEL_2 is not set 154 | # CONFIG_ESP32_BROWNOUT_DET_LVL_SEL_3 is not set 155 | # CONFIG_ESP32_BROWNOUT_DET_LVL_SEL_4 is not set 156 | # CONFIG_ESP32_BROWNOUT_DET_LVL_SEL_5 is not set 157 | # CONFIG_ESP32_BROWNOUT_DET_LVL_SEL_6 is not set 158 | # CONFIG_ESP32_BROWNOUT_DET_LVL_SEL_7 is not set 159 | CONFIG_ESP32_BROWNOUT_DET_LVL=0 160 | CONFIG_ESP32_REDUCE_PHY_TX_POWER=y 161 | CONFIG_ESP32_TIME_SYSCALL_USE_RTC_FRC1=y 162 | # CONFIG_ESP32_TIME_SYSCALL_USE_RTC is not set 163 | # CONFIG_ESP32_TIME_SYSCALL_USE_FRC1 is not set 164 | # CONFIG_ESP32_TIME_SYSCALL_USE_NONE is not set 165 | CONFIG_ESP32_RTC_CLK_SRC_INT_RC=y 166 | # CONFIG_ESP32_RTC_CLK_SRC_EXT_CRYS is not set 167 | # CONFIG_ESP32_RTC_CLK_SRC_EXT_OSC is not set 168 | # CONFIG_ESP32_RTC_CLK_SRC_INT_8MD256 is not set 169 | CONFIG_ESP32_RTC_CLK_CAL_CYCLES=1024 170 | CONFIG_ESP32_DEEP_SLEEP_WAKEUP_DELAY=2000 171 | CONFIG_ESP32_XTAL_FREQ_40=y 172 | # CONFIG_ESP32_XTAL_FREQ_26 is not set 173 | # CONFIG_ESP32_XTAL_FREQ_AUTO is not set 174 | CONFIG_ESP32_XTAL_FREQ=40 175 | # CONFIG_ESP32_DISABLE_BASIC_ROM_CONSOLE is not set 176 | # CONFIG_ESP32_NO_BLOBS is not set 177 | # CONFIG_ESP32_COMPATIBLE_PRE_V2_1_BOOTLOADERS is not set 178 | # CONFIG_ESP32_USE_FIXED_STATIC_RAM_SIZE is not set 179 | CONFIG_ESP32_DPORT_DIS_INTERRUPT_LVL=5 180 | # CONFIG_PM_ENABLE is not set 181 | CONFIG_ADC_CAL_EFUSE_TP_ENABLE=y 182 | CONFIG_ADC_CAL_EFUSE_VREF_ENABLE=y 183 | CONFIG_ADC_CAL_LUT_ENABLE=y 184 | # CONFIG_ESP_TIMER_PROFILING is not set 185 | CONFIG_ESP_ERR_TO_NAME_LOOKUP=y 186 | CONFIG_ESP_SYSTEM_EVENT_QUEUE_SIZE=32 187 | CONFIG_ESP_SYSTEM_EVENT_TASK_STACK_SIZE=2304 188 | CONFIG_ESP_MAIN_TASK_STACK_SIZE=3584 189 | CONFIG_ESP_IPC_TASK_STACK_SIZE=1024 190 | CONFIG_ESP_TIMER_TASK_STACK_SIZE=3584 191 | CONFIG_ESP_CONSOLE_UART_DEFAULT=y 192 | # CONFIG_ESP_CONSOLE_UART_CUSTOM is not set 193 | # CONFIG_ESP_CONSOLE_UART_NONE is not set 194 | CONFIG_ESP_CONSOLE_UART_NUM=0 195 | CONFIG_ESP_CONSOLE_UART_BAUDRATE=115200 196 | CONFIG_ESP_INT_WDT=y 197 | CONFIG_ESP_INT_WDT_TIMEOUT_MS=300 198 | CONFIG_ESP_INT_WDT_CHECK_CPU1=y 199 | CONFIG_ESP_TASK_WDT=y 200 | # CONFIG_ESP_TASK_WDT_PANIC is not set 201 | CONFIG_ESP_TASK_WDT_TIMEOUT_S=5 202 | CONFIG_ESP_TASK_WDT_CHECK_IDLE_TASK_CPU0=y 203 | CONFIG_ESP_TASK_WDT_CHECK_IDLE_TASK_CPU1=y 204 | CONFIG_ETH_USE_ESP32_EMAC=y 205 | CONFIG_ETH_PHY_INTERFACE_RMII=y 206 | # CONFIG_ETH_PHY_INTERFACE_MII is not set 207 | CONFIG_ETH_RMII_CLK_INPUT=y 208 | # CONFIG_ETH_RMII_CLK_OUTPUT is not set 209 | CONFIG_ETH_RMII_CLK_IN_GPIO=0 210 | CONFIG_ETH_DMA_BUFFER_SIZE=512 211 | CONFIG_ETH_DMA_RX_BUFFER_NUM=10 212 | CONFIG_ETH_DMA_TX_BUFFER_NUM=10 213 | CONFIG_ETH_USE_SPI_ETHERNET=y 214 | CONFIG_ETH_SPI_ETHERNET_DM9051=y 215 | # CONFIG_ESP_EVENT_LOOP_PROFILING is not set 216 | CONFIG_ESP_EVENT_POST_FROM_ISR=y 217 | CONFIG_ESP_EVENT_POST_FROM_IRAM_ISR=y 218 | CONFIG_ESP_HTTP_CLIENT_ENABLE_HTTPS=y 219 | # CONFIG_ESP_HTTP_CLIENT_ENABLE_BASIC_AUTH is not set 220 | CONFIG_HTTPD_MAX_REQ_HDR_LEN=512 221 | CONFIG_HTTPD_MAX_URI_LEN=512 222 | CONFIG_HTTPD_ERR_RESP_NO_DELAY=y 223 | CONFIG_HTTPD_PURGE_BUF_LEN=32 224 | # CONFIG_HTTPD_LOG_PURGE_DATA is not set 225 | # CONFIG_OTA_ALLOW_HTTP is not set 226 | # CONFIG_ESP_HTTPS_SERVER_ENABLE is not set 227 | CONFIG_ESP32_WIFI_STATIC_RX_BUFFER_NUM=10 228 | CONFIG_ESP32_WIFI_DYNAMIC_RX_BUFFER_NUM=32 229 | # CONFIG_ESP32_WIFI_STATIC_TX_BUFFER is not set 230 | CONFIG_ESP32_WIFI_DYNAMIC_TX_BUFFER=y 231 | CONFIG_ESP32_WIFI_TX_BUFFER_TYPE=1 232 | CONFIG_ESP32_WIFI_DYNAMIC_TX_BUFFER_NUM=32 233 | # CONFIG_ESP32_WIFI_CSI_ENABLED is not set 234 | CONFIG_ESP32_WIFI_AMPDU_TX_ENABLED=y 235 | CONFIG_ESP32_WIFI_TX_BA_WIN=6 236 | CONFIG_ESP32_WIFI_AMPDU_RX_ENABLED=y 237 | CONFIG_ESP32_WIFI_RX_BA_WIN=6 238 | CONFIG_ESP32_WIFI_NVS_ENABLED=y 239 | CONFIG_ESP32_WIFI_TASK_PINNED_TO_CORE_0=y 240 | # CONFIG_ESP32_WIFI_TASK_PINNED_TO_CORE_1 is not set 241 | CONFIG_ESP32_WIFI_SOFTAP_BEACON_MAX_LEN=752 242 | CONFIG_ESP32_WIFI_MGMT_SBUF_NUM=32 243 | # CONFIG_ESP32_WIFI_DEBUG_LOG_ENABLE is not set 244 | CONFIG_ESP32_WIFI_IRAM_OPT=y 245 | CONFIG_ESP32_WIFI_RX_IRAM_OPT=y 246 | CONFIG_ESP32_PHY_CALIBRATION_AND_DATA_STORAGE=y 247 | # CONFIG_ESP32_PHY_INIT_DATA_IN_PARTITION is not set 248 | CONFIG_ESP32_PHY_MAX_WIFI_TX_POWER=20 249 | CONFIG_ESP32_PHY_MAX_TX_POWER=20 250 | # CONFIG_ESP32_ENABLE_COREDUMP_TO_FLASH is not set 251 | # CONFIG_ESP32_ENABLE_COREDUMP_TO_UART is not set 252 | CONFIG_ESP32_ENABLE_COREDUMP_TO_NONE=y 253 | # CONFIG_ESP32_ENABLE_COREDUMP is not set 254 | # CONFIG_FATFS_CODEPAGE_DYNAMIC is not set 255 | CONFIG_FATFS_CODEPAGE_437=y 256 | # CONFIG_FATFS_CODEPAGE_720 is not set 257 | # CONFIG_FATFS_CODEPAGE_737 is not set 258 | # CONFIG_FATFS_CODEPAGE_771 is not set 259 | # CONFIG_FATFS_CODEPAGE_775 is not set 260 | # CONFIG_FATFS_CODEPAGE_850 is not set 261 | # CONFIG_FATFS_CODEPAGE_852 is not set 262 | # CONFIG_FATFS_CODEPAGE_855 is not set 263 | # CONFIG_FATFS_CODEPAGE_857 is not set 264 | # CONFIG_FATFS_CODEPAGE_860 is not set 265 | # CONFIG_FATFS_CODEPAGE_861 is not set 266 | # CONFIG_FATFS_CODEPAGE_862 is not set 267 | # CONFIG_FATFS_CODEPAGE_863 is not set 268 | # CONFIG_FATFS_CODEPAGE_864 is not set 269 | # CONFIG_FATFS_CODEPAGE_865 is not set 270 | # CONFIG_FATFS_CODEPAGE_866 is not set 271 | # CONFIG_FATFS_CODEPAGE_869 is not set 272 | # CONFIG_FATFS_CODEPAGE_932 is not set 273 | # CONFIG_FATFS_CODEPAGE_936 is not set 274 | # CONFIG_FATFS_CODEPAGE_949 is not set 275 | # CONFIG_FATFS_CODEPAGE_950 is not set 276 | CONFIG_FATFS_CODEPAGE=437 277 | CONFIG_FATFS_LFN_NONE=y 278 | # CONFIG_FATFS_LFN_HEAP is not set 279 | # CONFIG_FATFS_LFN_STACK is not set 280 | CONFIG_FATFS_FS_LOCK=0 281 | CONFIG_FATFS_TIMEOUT_MS=10000 282 | CONFIG_FATFS_PER_FILE_CACHE=y 283 | CONFIG_FMB_MASTER_TIMEOUT_MS_RESPOND=150 284 | CONFIG_FMB_MASTER_DELAY_MS_CONVERT=200 285 | CONFIG_FMB_QUEUE_LENGTH=20 286 | CONFIG_FMB_SERIAL_TASK_STACK_SIZE=2048 287 | CONFIG_FMB_SERIAL_BUF_SIZE=256 288 | CONFIG_FMB_SERIAL_TASK_PRIO=10 289 | # CONFIG_FMB_CONTROLLER_SLAVE_ID_SUPPORT is not set 290 | CONFIG_FMB_CONTROLLER_NOTIFY_TIMEOUT=20 291 | CONFIG_FMB_CONTROLLER_NOTIFY_QUEUE_SIZE=20 292 | CONFIG_FMB_CONTROLLER_STACK_SIZE=4096 293 | CONFIG_FMB_EVENT_QUEUE_TIMEOUT=20 294 | CONFIG_FMB_TIMER_PORT_ENABLED=y 295 | CONFIG_FMB_TIMER_GROUP=0 296 | CONFIG_FMB_TIMER_INDEX=0 297 | # CONFIG_FREERTOS_UNICORE is not set 298 | CONFIG_FREERTOS_NO_AFFINITY=0x7FFFFFFF 299 | CONFIG_FREERTOS_CORETIMER_0=y 300 | # CONFIG_FREERTOS_CORETIMER_1 is not set 301 | CONFIG_FREERTOS_HZ=100 302 | CONFIG_FREERTOS_ASSERT_ON_UNTESTED_FUNCTION=y 303 | # CONFIG_FREERTOS_CHECK_STACKOVERFLOW_NONE is not set 304 | # CONFIG_FREERTOS_CHECK_STACKOVERFLOW_PTRVAL is not set 305 | CONFIG_FREERTOS_CHECK_STACKOVERFLOW_CANARY=y 306 | # CONFIG_FREERTOS_WATCHPOINT_END_OF_STACK is not set 307 | CONFIG_FREERTOS_INTERRUPT_BACKTRACE=y 308 | CONFIG_FREERTOS_THREAD_LOCAL_STORAGE_POINTERS=1 309 | CONFIG_FREERTOS_ASSERT_FAIL_ABORT=y 310 | # CONFIG_FREERTOS_ASSERT_FAIL_PRINT_CONTINUE is not set 311 | # CONFIG_FREERTOS_ASSERT_DISABLE is not set 312 | CONFIG_FREERTOS_IDLE_TASK_STACKSIZE=1536 313 | CONFIG_FREERTOS_ISR_STACKSIZE=1536 314 | # CONFIG_FREERTOS_LEGACY_HOOKS is not set 315 | CONFIG_FREERTOS_MAX_TASK_NAME_LEN=16 316 | # CONFIG_FREERTOS_SUPPORT_STATIC_ALLOCATION is not set 317 | CONFIG_FREERTOS_TIMER_TASK_PRIORITY=1 318 | CONFIG_FREERTOS_TIMER_TASK_STACK_DEPTH=2048 319 | CONFIG_FREERTOS_TIMER_QUEUE_LENGTH=10 320 | CONFIG_FREERTOS_QUEUE_REGISTRY_SIZE=0 321 | # CONFIG_FREERTOS_USE_TRACE_FACILITY is not set 322 | # CONFIG_FREERTOS_GENERATE_RUN_TIME_STATS is not set 323 | # CONFIG_FREERTOS_DEBUG_INTERNALS is not set 324 | CONFIG_FREERTOS_TASK_FUNCTION_WRAPPER=y 325 | CONFIG_FREERTOS_CHECK_MUTEX_GIVEN_BY_OWNER=y 326 | # CONFIG_FREERTOS_CHECK_PORT_CRITICAL_COMPLIANCE is not set 327 | CONFIG_HEAP_POISONING_DISABLED=y 328 | # CONFIG_HEAP_POISONING_LIGHT is not set 329 | # CONFIG_HEAP_POISONING_COMPREHENSIVE is not set 330 | CONFIG_HEAP_TRACING_OFF=y 331 | # CONFIG_HEAP_TRACING_STANDALONE is not set 332 | # CONFIG_HEAP_TRACING_TOHOST is not set 333 | # CONFIG_HEAP_TRACING is not set 334 | # CONFIG_LOG_DEFAULT_LEVEL_NONE is not set 335 | # CONFIG_LOG_DEFAULT_LEVEL_ERROR is not set 336 | # CONFIG_LOG_DEFAULT_LEVEL_WARN is not set 337 | CONFIG_LOG_DEFAULT_LEVEL_INFO=y 338 | # CONFIG_LOG_DEFAULT_LEVEL_DEBUG is not set 339 | # CONFIG_LOG_DEFAULT_LEVEL_VERBOSE is not set 340 | CONFIG_LOG_DEFAULT_LEVEL=3 341 | CONFIG_LOG_COLORS=y 342 | CONFIG_LWIP_LOCAL_HOSTNAME="espressif" 343 | # CONFIG_LWIP_L2_TO_L3_COPY is not set 344 | # CONFIG_LWIP_IRAM_OPTIMIZATION is not set 345 | CONFIG_LWIP_TIMERS_ONDEMAND=y 346 | CONFIG_LWIP_MAX_SOCKETS=10 347 | # CONFIG_LWIP_USE_ONLY_LWIP_SELECT is not set 348 | CONFIG_LWIP_SO_REUSE=y 349 | CONFIG_LWIP_SO_REUSE_RXTOALL=y 350 | # CONFIG_LWIP_SO_RCVBUF is not set 351 | CONFIG_LWIP_IP_FRAG=y 352 | # CONFIG_LWIP_IP_REASSEMBLY is not set 353 | # CONFIG_LWIP_STATS is not set 354 | # CONFIG_LWIP_ETHARP_TRUST_IP_MAC is not set 355 | CONFIG_LWIP_ESP_GRATUITOUS_ARP=y 356 | CONFIG_LWIP_GARP_TMR_INTERVAL=60 357 | CONFIG_LWIP_TCPIP_RECVMBOX_SIZE=32 358 | CONFIG_LWIP_DHCP_DOES_ARP_CHECK=y 359 | # CONFIG_LWIP_DHCP_RESTORE_LAST_IP is not set 360 | CONFIG_LWIP_DHCPS_LEASE_UNIT=60 361 | CONFIG_LWIP_DHCPS_MAX_STATION_NUM=8 362 | # CONFIG_LWIP_AUTOIP is not set 363 | # CONFIG_LWIP_IPV6_AUTOCONFIG is not set 364 | CONFIG_LWIP_NETIF_LOOPBACK=y 365 | CONFIG_LWIP_LOOPBACK_MAX_PBUFS=8 366 | CONFIG_LWIP_MAX_ACTIVE_TCP=16 367 | CONFIG_LWIP_MAX_LISTENING_TCP=16 368 | CONFIG_LWIP_TCP_MAXRTX=12 369 | CONFIG_LWIP_TCP_SYNMAXRTX=6 370 | CONFIG_LWIP_TCP_MSS=1440 371 | CONFIG_LWIP_TCP_MSL=60000 372 | CONFIG_LWIP_TCP_SND_BUF_DEFAULT=5744 373 | CONFIG_LWIP_TCP_WND_DEFAULT=5744 374 | CONFIG_LWIP_TCP_RECVMBOX_SIZE=6 375 | CONFIG_LWIP_TCP_QUEUE_OOSEQ=y 376 | # CONFIG_LWIP_TCP_KEEP_CONNECTION_WHEN_IP_CHANGES is not set 377 | CONFIG_LWIP_TCP_OVERSIZE_MSS=y 378 | # CONFIG_LWIP_TCP_OVERSIZE_QUARTER_MSS is not set 379 | # CONFIG_LWIP_TCP_OVERSIZE_DISABLE is not set 380 | CONFIG_LWIP_MAX_UDP_PCBS=16 381 | CONFIG_LWIP_UDP_RECVMBOX_SIZE=6 382 | CONFIG_LWIP_TCPIP_TASK_STACK_SIZE=3072 383 | CONFIG_LWIP_TCPIP_TASK_AFFINITY_NO_AFFINITY=y 384 | # CONFIG_LWIP_TCPIP_TASK_AFFINITY_CPU0 is not set 385 | # CONFIG_LWIP_TCPIP_TASK_AFFINITY_CPU1 is not set 386 | CONFIG_LWIP_TCPIP_TASK_AFFINITY=0x7FFFFFFF 387 | # CONFIG_LWIP_PPP_SUPPORT is not set 388 | # CONFIG_LWIP_MULTICAST_PING is not set 389 | # CONFIG_LWIP_BROADCAST_PING is not set 390 | CONFIG_LWIP_MAX_RAW_PCBS=16 391 | CONFIG_LWIP_DHCP_MAX_NTP_SERVERS=1 392 | CONFIG_LWIP_SNTP_UPDATE_DELAY=3600000 393 | CONFIG_MBEDTLS_INTERNAL_MEM_ALLOC=y 394 | # CONFIG_MBEDTLS_DEFAULT_MEM_ALLOC is not set 395 | # CONFIG_MBEDTLS_CUSTOM_MEM_ALLOC is not set 396 | CONFIG_MBEDTLS_ASYMMETRIC_CONTENT_LEN=y 397 | CONFIG_MBEDTLS_SSL_IN_CONTENT_LEN=16384 398 | CONFIG_MBEDTLS_SSL_OUT_CONTENT_LEN=4096 399 | # CONFIG_MBEDTLS_DEBUG is not set 400 | # CONFIG_MBEDTLS_ECP_RESTARTABLE is not set 401 | # CONFIG_MBEDTLS_CMAC_C is not set 402 | CONFIG_MBEDTLS_HARDWARE_AES=y 403 | CONFIG_MBEDTLS_HARDWARE_MPI=y 404 | # CONFIG_MBEDTLS_MPI_USE_INTERRUPT is not set 405 | CONFIG_MBEDTLS_HARDWARE_SHA=y 406 | CONFIG_MBEDTLS_HAVE_TIME=y 407 | # CONFIG_MBEDTLS_HAVE_TIME_DATE is not set 408 | CONFIG_MBEDTLS_TLS_SERVER_AND_CLIENT=y 409 | # CONFIG_MBEDTLS_TLS_SERVER_ONLY is not set 410 | # CONFIG_MBEDTLS_TLS_CLIENT_ONLY is not set 411 | # CONFIG_MBEDTLS_TLS_DISABLED is not set 412 | CONFIG_MBEDTLS_TLS_SERVER=y 413 | CONFIG_MBEDTLS_TLS_CLIENT=y 414 | CONFIG_MBEDTLS_TLS_ENABLED=y 415 | CONFIG_MBEDTLS_PSK_MODES=y 416 | CONFIG_MBEDTLS_KEY_EXCHANGE_PSK=y 417 | CONFIG_MBEDTLS_KEY_EXCHANGE_DHE_PSK=y 418 | CONFIG_MBEDTLS_KEY_EXCHANGE_ECDHE_PSK=y 419 | CONFIG_MBEDTLS_KEY_EXCHANGE_RSA_PSK=y 420 | CONFIG_MBEDTLS_KEY_EXCHANGE_RSA=y 421 | CONFIG_MBEDTLS_KEY_EXCHANGE_DHE_RSA=y 422 | CONFIG_MBEDTLS_KEY_EXCHANGE_ELLIPTIC_CURVE=y 423 | CONFIG_MBEDTLS_KEY_EXCHANGE_ECDHE_RSA=y 424 | CONFIG_MBEDTLS_KEY_EXCHANGE_ECDHE_ECDSA=y 425 | CONFIG_MBEDTLS_KEY_EXCHANGE_ECDH_ECDSA=y 426 | CONFIG_MBEDTLS_KEY_EXCHANGE_ECDH_RSA=y 427 | CONFIG_MBEDTLS_SSL_RENEGOTIATION=y 428 | # CONFIG_MBEDTLS_SSL_PROTO_SSL3 is not set 429 | CONFIG_MBEDTLS_SSL_PROTO_TLS1=y 430 | CONFIG_MBEDTLS_SSL_PROTO_TLS1_1=y 431 | CONFIG_MBEDTLS_SSL_PROTO_TLS1_2=y 432 | CONFIG_MBEDTLS_SSL_PROTO_DTLS=y 433 | CONFIG_MBEDTLS_SSL_ALPN=y 434 | CONFIG_MBEDTLS_CLIENT_SSL_SESSION_TICKETS=y 435 | CONFIG_MBEDTLS_SERVER_SSL_SESSION_TICKETS=y 436 | CONFIG_MBEDTLS_AES_C=y 437 | # CONFIG_MBEDTLS_CAMELLIA_C is not set 438 | # CONFIG_MBEDTLS_DES_C is not set 439 | CONFIG_MBEDTLS_RC4_DISABLED=y 440 | # CONFIG_MBEDTLS_RC4_ENABLED_NO_DEFAULT is not set 441 | # CONFIG_MBEDTLS_RC4_ENABLED is not set 442 | # CONFIG_MBEDTLS_BLOWFISH_C is not set 443 | # CONFIG_MBEDTLS_XTEA_C is not set 444 | CONFIG_MBEDTLS_CCM_C=y 445 | CONFIG_MBEDTLS_GCM_C=y 446 | # CONFIG_MBEDTLS_RIPEMD160_C is not set 447 | CONFIG_MBEDTLS_PEM_PARSE_C=y 448 | CONFIG_MBEDTLS_PEM_WRITE_C=y 449 | CONFIG_MBEDTLS_X509_CRL_PARSE_C=y 450 | CONFIG_MBEDTLS_X509_CSR_PARSE_C=y 451 | CONFIG_MBEDTLS_ECP_C=y 452 | CONFIG_MBEDTLS_ECDH_C=y 453 | CONFIG_MBEDTLS_ECDSA_C=y 454 | CONFIG_MBEDTLS_ECP_DP_SECP192R1_ENABLED=y 455 | CONFIG_MBEDTLS_ECP_DP_SECP224R1_ENABLED=y 456 | CONFIG_MBEDTLS_ECP_DP_SECP256R1_ENABLED=y 457 | CONFIG_MBEDTLS_ECP_DP_SECP384R1_ENABLED=y 458 | CONFIG_MBEDTLS_ECP_DP_SECP521R1_ENABLED=y 459 | CONFIG_MBEDTLS_ECP_DP_SECP192K1_ENABLED=y 460 | CONFIG_MBEDTLS_ECP_DP_SECP224K1_ENABLED=y 461 | CONFIG_MBEDTLS_ECP_DP_SECP256K1_ENABLED=y 462 | CONFIG_MBEDTLS_ECP_DP_BP256R1_ENABLED=y 463 | CONFIG_MBEDTLS_ECP_DP_BP384R1_ENABLED=y 464 | CONFIG_MBEDTLS_ECP_DP_BP512R1_ENABLED=y 465 | CONFIG_MBEDTLS_ECP_DP_CURVE25519_ENABLED=y 466 | CONFIG_MBEDTLS_ECP_NIST_OPTIM=y 467 | CONFIG_MDNS_MAX_SERVICES=10 468 | CONFIG_MQTT_PROTOCOL_311=y 469 | CONFIG_MQTT_TRANSPORT_SSL=y 470 | CONFIG_MQTT_TRANSPORT_WEBSOCKET=y 471 | CONFIG_MQTT_TRANSPORT_WEBSOCKET_SECURE=y 472 | # CONFIG_MQTT_USE_CUSTOM_CONFIG is not set 473 | # CONFIG_MQTT_TASK_CORE_SELECTION_ENABLED is not set 474 | # CONFIG_MQTT_CUSTOM_OUTBOX is not set 475 | CONFIG_NEWLIB_STDOUT_LINE_ENDING_CRLF=y 476 | # CONFIG_NEWLIB_STDOUT_LINE_ENDING_LF is not set 477 | # CONFIG_NEWLIB_STDOUT_LINE_ENDING_CR is not set 478 | # CONFIG_NEWLIB_STDIN_LINE_ENDING_CRLF is not set 479 | # CONFIG_NEWLIB_STDIN_LINE_ENDING_LF is not set 480 | CONFIG_NEWLIB_STDIN_LINE_ENDING_CR=y 481 | # CONFIG_NEWLIB_NANO_FORMAT is not set 482 | # CONFIG_OPENSSL_DEBUG is not set 483 | # CONFIG_OPENSSL_ASSERT_DO_NOTHING is not set 484 | CONFIG_OPENSSL_ASSERT_EXIT=y 485 | CONFIG_PTHREAD_TASK_PRIO_DEFAULT=5 486 | CONFIG_PTHREAD_TASK_STACK_SIZE_DEFAULT=3072 487 | CONFIG_PTHREAD_STACK_MIN=768 488 | CONFIG_PTHREAD_DEFAULT_CORE_NO_AFFINITY=y 489 | # CONFIG_PTHREAD_DEFAULT_CORE_0 is not set 490 | # CONFIG_PTHREAD_DEFAULT_CORE_1 is not set 491 | CONFIG_PTHREAD_TASK_CORE_DEFAULT=-1 492 | CONFIG_PTHREAD_TASK_NAME_DEFAULT="pthread" 493 | # CONFIG_SPI_FLASH_VERIFY_WRITE is not set 494 | # CONFIG_SPI_FLASH_ENABLE_COUNTERS is not set 495 | CONFIG_SPI_FLASH_ROM_DRIVER_PATCH=y 496 | CONFIG_SPI_FLASH_DANGEROUS_WRITE_ABORTS=y 497 | # CONFIG_SPI_FLASH_DANGEROUS_WRITE_FAILS is not set 498 | # CONFIG_SPI_FLASH_DANGEROUS_WRITE_ALLOWED is not set 499 | # CONFIG_SPI_FLASH_USE_LEGACY_IMPL is not set 500 | CONFIG_SPI_FLASH_SUPPORT_ISSI_CHIP=y 501 | CONFIG_SPI_FLASH_SUPPORT_GD_CHIP=y 502 | CONFIG_SPIFFS_MAX_PARTITIONS=3 503 | CONFIG_SPIFFS_CACHE=y 504 | CONFIG_SPIFFS_CACHE_WR=y 505 | # CONFIG_SPIFFS_CACHE_STATS is not set 506 | CONFIG_SPIFFS_PAGE_CHECK=y 507 | CONFIG_SPIFFS_GC_MAX_RUNS=10 508 | # CONFIG_SPIFFS_GC_STATS is not set 509 | CONFIG_SPIFFS_PAGE_SIZE=256 510 | CONFIG_SPIFFS_OBJ_NAME_LEN=32 511 | CONFIG_SPIFFS_USE_MAGIC=y 512 | CONFIG_SPIFFS_USE_MAGIC_LENGTH=y 513 | CONFIG_SPIFFS_META_LENGTH=4 514 | CONFIG_SPIFFS_USE_MTIME=y 515 | # CONFIG_SPIFFS_DBG is not set 516 | # CONFIG_SPIFFS_API_DBG is not set 517 | # CONFIG_SPIFFS_GC_DBG is not set 518 | # CONFIG_SPIFFS_CACHE_DBG is not set 519 | # CONFIG_SPIFFS_CHECK_DBG is not set 520 | # CONFIG_SPIFFS_TEST_VISUALISATION is not set 521 | CONFIG_NETIF_IP_LOST_TIMER_INTERVAL=120 522 | CONFIG_TCPIP_LWIP=y 523 | CONFIG_UNITY_ENABLE_FLOAT=y 524 | CONFIG_UNITY_ENABLE_DOUBLE=y 525 | # CONFIG_UNITY_ENABLE_COLOR is not set 526 | CONFIG_UNITY_ENABLE_IDF_TEST_RUNNER=y 527 | # CONFIG_UNITY_ENABLE_FIXTURE is not set 528 | # CONFIG_UNITY_ENABLE_BACKTRACE_ON_FAIL is not set 529 | CONFIG_VFS_SUPPRESS_SELECT_DEBUG_OUTPUT=y 530 | CONFIG_VFS_SUPPORT_TERMIOS=y 531 | CONFIG_SEMIHOSTFS_MAX_MOUNT_POINTS=1 532 | CONFIG_SEMIHOSTFS_HOST_PATH_MAX_LEN=128 533 | # CONFIG_WL_SECTOR_SIZE_512 is not set 534 | CONFIG_WL_SECTOR_SIZE_4096=y 535 | CONFIG_WL_SECTOR_SIZE=4096 536 | CONFIG_WIFI_PROV_SCAN_MAX_ENTRIES=16 537 | CONFIG_WIFI_PROV_AUTOSTOP_TIMEOUT=30 538 | CONFIG_WPA_MBEDTLS_CRYPTO=y 539 | # CONFIG_LEGACY_INCLUDE_COMMON_HEADERS is not set 540 | 541 | # Deprecated options for backward compatibility 542 | CONFIG_TOOLPREFIX="xtensa-esp32-elf-" 543 | CONFIG_PYTHON="python" 544 | CONFIG_MAKE_WARN_UNDEFINED_VARIABLES=y 545 | # CONFIG_LOG_BOOTLOADER_LEVEL_NONE is not set 546 | # CONFIG_LOG_BOOTLOADER_LEVEL_ERROR is not set 547 | # CONFIG_LOG_BOOTLOADER_LEVEL_WARN is not set 548 | CONFIG_LOG_BOOTLOADER_LEVEL_INFO=y 549 | # CONFIG_LOG_BOOTLOADER_LEVEL_DEBUG is not set 550 | # CONFIG_LOG_BOOTLOADER_LEVEL_VERBOSE is not set 551 | CONFIG_LOG_BOOTLOADER_LEVEL=3 552 | # CONFIG_APP_ROLLBACK_ENABLE is not set 553 | # CONFIG_FLASH_ENCRYPTION_ENABLED is not set 554 | # CONFIG_FLASHMODE_QIO is not set 555 | # CONFIG_FLASHMODE_QOUT is not set 556 | CONFIG_FLASHMODE_DIO=y 557 | # CONFIG_FLASHMODE_DOUT is not set 558 | # CONFIG_MONITOR_BAUD_9600B is not set 559 | # CONFIG_MONITOR_BAUD_57600B is not set 560 | CONFIG_MONITOR_BAUD_115200B=y 561 | # CONFIG_MONITOR_BAUD_230400B is not set 562 | # CONFIG_MONITOR_BAUD_921600B is not set 563 | # CONFIG_MONITOR_BAUD_2MB is not set 564 | # CONFIG_MONITOR_BAUD_OTHER is not set 565 | CONFIG_MONITOR_BAUD_OTHER_VAL=115200 566 | CONFIG_MONITOR_BAUD=115200 567 | CONFIG_OPTIMIZATION_LEVEL_DEBUG=y 568 | # CONFIG_OPTIMIZATION_LEVEL_RELEASE is not set 569 | CONFIG_OPTIMIZATION_ASSERTIONS_ENABLED=y 570 | # CONFIG_OPTIMIZATION_ASSERTIONS_SILENT is not set 571 | # CONFIG_OPTIMIZATION_ASSERTIONS_DISABLED is not set 572 | # CONFIG_CXX_EXCEPTIONS is not set 573 | CONFIG_STACK_CHECK_NONE=y 574 | # CONFIG_STACK_CHECK_NORM is not set 575 | # CONFIG_STACK_CHECK_STRONG is not set 576 | # CONFIG_STACK_CHECK_ALL is not set 577 | # CONFIG_STACK_CHECK is not set 578 | # CONFIG_WARN_WRITE_STRINGS is not set 579 | # CONFIG_DISABLE_GCC8_WARNINGS is not set 580 | CONFIG_BTDM_CONTROLLER_BLE_MAX_CONN_EFF=0 581 | CONFIG_BTDM_CONTROLLER_BR_EDR_MAX_ACL_CONN_EFF=0 582 | CONFIG_BTDM_CONTROLLER_BR_EDR_MAX_SYNC_CONN_EFF=0 583 | CONFIG_BTDM_CONTROLLER_PINNED_TO_CORE=0 584 | CONFIG_ADC2_DISABLE_DAC=y 585 | # CONFIG_SPIRAM_SUPPORT is not set 586 | # CONFIG_MEMMAP_TRACEMEM is not set 587 | # CONFIG_MEMMAP_TRACEMEM_TWOBANKS is not set 588 | CONFIG_TRACEMEM_RESERVE_DRAM=0x0 589 | # CONFIG_TWO_UNIVERSAL_MAC_ADDRESS is not set 590 | CONFIG_FOUR_UNIVERSAL_MAC_ADDRESS=y 591 | CONFIG_NUMBER_OF_UNIVERSAL_MAC_ADDRESS=4 592 | # CONFIG_ULP_COPROC_ENABLED is not set 593 | CONFIG_ULP_COPROC_RESERVE_MEM=0 594 | CONFIG_BROWNOUT_DET=y 595 | CONFIG_BROWNOUT_DET_LVL_SEL_0=y 596 | # CONFIG_BROWNOUT_DET_LVL_SEL_1 is not set 597 | # CONFIG_BROWNOUT_DET_LVL_SEL_2 is not set 598 | # CONFIG_BROWNOUT_DET_LVL_SEL_3 is not set 599 | # CONFIG_BROWNOUT_DET_LVL_SEL_4 is not set 600 | # CONFIG_BROWNOUT_DET_LVL_SEL_5 is not set 601 | # CONFIG_BROWNOUT_DET_LVL_SEL_6 is not set 602 | # CONFIG_BROWNOUT_DET_LVL_SEL_7 is not set 603 | CONFIG_BROWNOUT_DET_LVL=0 604 | CONFIG_REDUCE_PHY_TX_POWER=y 605 | CONFIG_ESP32_RTC_CLOCK_SOURCE_INTERNAL_RC=y 606 | # CONFIG_ESP32_RTC_CLOCK_SOURCE_EXTERNAL_CRYSTAL is not set 607 | # CONFIG_ESP32_RTC_CLOCK_SOURCE_EXTERNAL_OSC is not set 608 | # CONFIG_ESP32_RTC_CLOCK_SOURCE_INTERNAL_8MD256 is not set 609 | # CONFIG_DISABLE_BASIC_ROM_CONSOLE is not set 610 | # CONFIG_NO_BLOBS is not set 611 | # CONFIG_COMPATIBLE_PRE_V2_1_BOOTLOADERS is not set 612 | CONFIG_SYSTEM_EVENT_QUEUE_SIZE=32 613 | CONFIG_SYSTEM_EVENT_TASK_STACK_SIZE=2304 614 | CONFIG_MAIN_TASK_STACK_SIZE=3584 615 | CONFIG_IPC_TASK_STACK_SIZE=1024 616 | CONFIG_TIMER_TASK_STACK_SIZE=3584 617 | CONFIG_CONSOLE_UART_DEFAULT=y 618 | # CONFIG_CONSOLE_UART_CUSTOM is not set 619 | # CONFIG_CONSOLE_UART_NONE is not set 620 | CONFIG_CONSOLE_UART_NUM=0 621 | CONFIG_CONSOLE_UART_BAUDRATE=115200 622 | CONFIG_INT_WDT=y 623 | CONFIG_INT_WDT_TIMEOUT_MS=300 624 | CONFIG_INT_WDT_CHECK_CPU1=y 625 | CONFIG_TASK_WDT=y 626 | # CONFIG_TASK_WDT_PANIC is not set 627 | CONFIG_TASK_WDT_TIMEOUT_S=5 628 | CONFIG_TASK_WDT_CHECK_IDLE_TASK_CPU0=y 629 | CONFIG_TASK_WDT_CHECK_IDLE_TASK_CPU1=y 630 | # CONFIG_EVENT_LOOP_PROFILING is not set 631 | CONFIG_POST_EVENTS_FROM_ISR=y 632 | CONFIG_POST_EVENTS_FROM_IRAM_ISR=y 633 | CONFIG_MB_MASTER_TIMEOUT_MS_RESPOND=150 634 | CONFIG_MB_MASTER_DELAY_MS_CONVERT=200 635 | CONFIG_MB_QUEUE_LENGTH=20 636 | CONFIG_MB_SERIAL_TASK_STACK_SIZE=2048 637 | CONFIG_MB_SERIAL_BUF_SIZE=256 638 | CONFIG_MB_SERIAL_TASK_PRIO=10 639 | # CONFIG_MB_CONTROLLER_SLAVE_ID_SUPPORT is not set 640 | CONFIG_MB_CONTROLLER_NOTIFY_TIMEOUT=20 641 | CONFIG_MB_CONTROLLER_NOTIFY_QUEUE_SIZE=20 642 | CONFIG_MB_CONTROLLER_STACK_SIZE=4096 643 | CONFIG_MB_EVENT_QUEUE_TIMEOUT=20 644 | CONFIG_MB_TIMER_PORT_ENABLED=y 645 | CONFIG_MB_TIMER_GROUP=0 646 | CONFIG_MB_TIMER_INDEX=0 647 | # CONFIG_SUPPORT_STATIC_ALLOCATION is not set 648 | CONFIG_TIMER_TASK_PRIORITY=1 649 | CONFIG_TIMER_TASK_STACK_DEPTH=2048 650 | CONFIG_TIMER_QUEUE_LENGTH=10 651 | # CONFIG_L2_TO_L3_COPY is not set 652 | # CONFIG_USE_ONLY_LWIP_SELECT is not set 653 | CONFIG_ESP_GRATUITOUS_ARP=y 654 | CONFIG_GARP_TMR_INTERVAL=60 655 | CONFIG_TCPIP_RECVMBOX_SIZE=32 656 | CONFIG_TCP_MAXRTX=12 657 | CONFIG_TCP_SYNMAXRTX=6 658 | CONFIG_TCP_MSS=1440 659 | CONFIG_TCP_MSL=60000 660 | CONFIG_TCP_SND_BUF_DEFAULT=5744 661 | CONFIG_TCP_WND_DEFAULT=5744 662 | CONFIG_TCP_RECVMBOX_SIZE=6 663 | CONFIG_TCP_QUEUE_OOSEQ=y 664 | # CONFIG_ESP_TCP_KEEP_CONNECTION_WHEN_IP_CHANGES is not set 665 | CONFIG_TCP_OVERSIZE_MSS=y 666 | # CONFIG_TCP_OVERSIZE_QUARTER_MSS is not set 667 | # CONFIG_TCP_OVERSIZE_DISABLE is not set 668 | CONFIG_UDP_RECVMBOX_SIZE=6 669 | CONFIG_TCPIP_TASK_STACK_SIZE=3072 670 | CONFIG_TCPIP_TASK_AFFINITY_NO_AFFINITY=y 671 | # CONFIG_TCPIP_TASK_AFFINITY_CPU0 is not set 672 | # CONFIG_TCPIP_TASK_AFFINITY_CPU1 is not set 673 | CONFIG_TCPIP_TASK_AFFINITY=0x7FFFFFFF 674 | # CONFIG_PPP_SUPPORT is not set 675 | CONFIG_ESP32_PTHREAD_TASK_PRIO_DEFAULT=5 676 | CONFIG_ESP32_PTHREAD_TASK_STACK_SIZE_DEFAULT=3072 677 | CONFIG_ESP32_PTHREAD_STACK_MIN=768 678 | CONFIG_ESP32_DEFAULT_PTHREAD_CORE_NO_AFFINITY=y 679 | # CONFIG_ESP32_DEFAULT_PTHREAD_CORE_0 is not set 680 | # CONFIG_ESP32_DEFAULT_PTHREAD_CORE_1 is not set 681 | CONFIG_ESP32_PTHREAD_TASK_CORE_DEFAULT=-1 682 | CONFIG_ESP32_PTHREAD_TASK_NAME_DEFAULT="pthread" 683 | CONFIG_SPI_FLASH_WRITING_DANGEROUS_REGIONS_ABORTS=y 684 | # CONFIG_SPI_FLASH_WRITING_DANGEROUS_REGIONS_FAILS is not set 685 | # CONFIG_SPI_FLASH_WRITING_DANGEROUS_REGIONS_ALLOWED is not set 686 | CONFIG_IP_LOST_TIMER_INTERVAL=120 687 | CONFIG_SUPPRESS_SELECT_DEBUG_OUTPUT=y 688 | CONFIG_SUPPORT_TERMIOS=y 689 | # End of deprecated options 690 | -------------------------------------------------------------------------------- /main/MLX90640_API.c: -------------------------------------------------------------------------------- 1 | /** 2 | * @copyright (C) 2017 Melexis N.V. 3 | * 4 | * Licensed under the Apache License, Version 2.0 (the "License"); 5 | * you may not use this file except in compliance with the License. 6 | * You may obtain a copy of the License at 7 | * 8 | * http://www.apache.org/licenses/LICENSE-2.0 9 | * 10 | * Unless required by applicable law or agreed to in writing, software 11 | * distributed under the License is distributed on an "AS IS" BASIS, 12 | * WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied. 13 | * See the License for the specific language governing permissions and 14 | * limitations under the License. 15 | * 16 | */ 17 | 18 | #include "MLX90640_API.h" 19 | #include "esp_log.h" 20 | #include 21 | 22 | void ExtractVDDParameters(uint16_t *eeData, paramsMLX90640 *mlx90640); 23 | void ExtractPTATParameters(uint16_t *eeData, paramsMLX90640 *mlx90640); 24 | void ExtractGainParameters(uint16_t *eeData, paramsMLX90640 *mlx90640); 25 | void ExtractTgcParameters(uint16_t *eeData, paramsMLX90640 *mlx90640); 26 | void ExtractResolutionParameters(uint16_t *eeData, paramsMLX90640 *mlx90640); 27 | void ExtractKsTaParameters(uint16_t *eeData, paramsMLX90640 *mlx90640); 28 | void ExtractKsToParameters(uint16_t *eeData, paramsMLX90640 *mlx90640); 29 | void ExtractAlphaParameters(uint16_t *eeData, paramsMLX90640 *mlx90640); 30 | void ExtractOffsetParameters(uint16_t *eeData, paramsMLX90640 *mlx90640); 31 | void ExtractKtaPixelParameters(uint16_t *eeData, paramsMLX90640 *mlx90640); 32 | void ExtractKvPixelParameters(uint16_t *eeData, paramsMLX90640 *mlx90640); 33 | void ExtractCPParameters(uint16_t *eeData, paramsMLX90640 *mlx90640); 34 | void ExtractCILCParameters(uint16_t *eeData, paramsMLX90640 *mlx90640); 35 | int ExtractDeviatingPixels(uint16_t *eeData, paramsMLX90640 *mlx90640); 36 | int CheckAdjacentPixels(uint16_t pix1, uint16_t pix2); 37 | float GetMedian(float *values, int n); 38 | int IsPixelBad(uint16_t pixel,paramsMLX90640 *params); 39 | 40 | int MLX90640_DumpEE(uint8_t slaveAddr, uint16_t *eeData) 41 | { 42 | return REDAR_I2CRead(slaveAddr, 0x2400, 832, eeData); 43 | } 44 | 45 | int MLX90640_GetSubFrameData(uint8_t slaveAddr, uint16_t *frameData) 46 | { 47 | uint16_t dataReady = 0; 48 | uint16_t controlRegister1; 49 | uint16_t statusRegister; 50 | int error = 1; 51 | uint8_t cnt = 0; 52 | 53 | //is dara ready for readout 54 | while(dataReady == 0) 55 | { 56 | error = REDAR_I2CRead(slaveAddr, 0x8000, 1, &statusRegister); 57 | if(error != 0) 58 | { 59 | return error; 60 | } 61 | dataReady = statusRegister & 0x0008; 62 | } 63 | 64 | 65 | //resetting dataRead flag and enabling next measurement cycle 66 | error = REDAR_I2CWrite(slaveAddr, 0x8000, 0x0030); 67 | if(error == -1) 68 | { 69 | return error; 70 | } 71 | 72 | //reading frame 73 | error = REDAR_I2CRead(slaveAddr, 0x0400, 832, frameData); 74 | if(error != 0) 75 | { 76 | return error; 77 | } 78 | 79 | error = REDAR_I2CRead(slaveAddr, 0x800D, 1, &controlRegister1); 80 | frameData[832] = controlRegister1; 81 | frameData[833] = statusRegister & 0x0001; 82 | 83 | if(error != 0) 84 | { 85 | return error; 86 | } 87 | 88 | return frameData[833]; 89 | } 90 | 91 | int MLX90640_GetFrameData(uint8_t slaveAddr, uint16_t *frameData) 92 | { 93 | uint16_t dataReady = 1; 94 | uint16_t controlRegister1; 95 | uint16_t statusRegister; 96 | int error = 1; 97 | uint8_t cnt = 0; 98 | 99 | dataReady = 0; 100 | while(dataReady == 0) 101 | { 102 | error = REDAR_I2CRead(slaveAddr, 0x8000, 1, &statusRegister); 103 | if(error != 0) 104 | { 105 | return error; 106 | } 107 | dataReady = statusRegister & 0x0008; 108 | } 109 | 110 | while(dataReady != 0 && cnt < 5) 111 | { 112 | error = REDAR_I2CWrite(slaveAddr, 0x8000, 0x0030); 113 | if(error == -1) 114 | { 115 | return error; 116 | } 117 | 118 | error = REDAR_I2CRead(slaveAddr, 0x0400, 832, frameData); 119 | if(error != 0) 120 | { 121 | return error; 122 | } 123 | 124 | error = REDAR_I2CRead(slaveAddr, 0x8000, 1, &statusRegister); 125 | if(error != 0) 126 | { 127 | return error; 128 | } 129 | dataReady = statusRegister & 0x0008; 130 | cnt = cnt + 1; 131 | } 132 | 133 | if(cnt > 4) 134 | { 135 | ESP_LOGI("redar","timeout in reading second page"); 136 | return -8; 137 | } 138 | 139 | error = REDAR_I2CRead(slaveAddr, 0x800D, 1, &controlRegister1); 140 | frameData[832] = controlRegister1; 141 | frameData[833] = statusRegister & 0x0001; 142 | 143 | if(error != 0) 144 | { 145 | return error; 146 | } 147 | 148 | return frameData[833]; 149 | } 150 | 151 | int MLX90640_ExtractParameters(uint16_t *eeData, paramsMLX90640 *mlx90640) 152 | { 153 | int error = 0; 154 | 155 | ExtractVDDParameters(eeData, mlx90640); 156 | ExtractPTATParameters(eeData, mlx90640); 157 | ExtractGainParameters(eeData, mlx90640); 158 | ExtractTgcParameters(eeData, mlx90640); 159 | ExtractResolutionParameters(eeData, mlx90640); 160 | ExtractKsTaParameters(eeData, mlx90640); 161 | ExtractKsToParameters(eeData, mlx90640); 162 | ExtractCPParameters(eeData, mlx90640); 163 | ExtractAlphaParameters(eeData, mlx90640); 164 | ExtractOffsetParameters(eeData, mlx90640); 165 | ExtractKtaPixelParameters(eeData, mlx90640); 166 | ExtractKvPixelParameters(eeData, mlx90640); 167 | ExtractCILCParameters(eeData, mlx90640); 168 | error = ExtractDeviatingPixels(eeData, mlx90640); 169 | 170 | return error; 171 | 172 | } 173 | 174 | //------------------------------------------------------------------------------ 175 | 176 | int MLX90640_SetResolution(uint8_t slaveAddr, uint8_t resolution) 177 | { 178 | uint16_t controlRegister1; 179 | int value; 180 | int error; 181 | 182 | value = (resolution & 0x03) << 10; 183 | 184 | error = REDAR_I2CRead(slaveAddr, 0x800D, 1, &controlRegister1); 185 | 186 | if(error == 0) 187 | { 188 | value = (controlRegister1 & 0xF3FF) | value; 189 | error = REDAR_I2CWrite(slaveAddr, 0x800D, value); 190 | } 191 | 192 | return error; 193 | } 194 | 195 | //------------------------------------------------------------------------------ 196 | 197 | int MLX90640_GetCurResolution(uint8_t slaveAddr) 198 | { 199 | uint16_t controlRegister1; 200 | int resolutionRAM; 201 | int error; 202 | 203 | error = REDAR_I2CRead(slaveAddr, 0x800D, 1, &controlRegister1); 204 | if(error != 0) 205 | { 206 | return error; 207 | } 208 | resolutionRAM = (controlRegister1 & 0x0C00) >> 10; 209 | 210 | return resolutionRAM; 211 | } 212 | 213 | //------------------------------------------------------------------------------ 214 | 215 | int MLX90640_SetRefreshRate(uint8_t slaveAddr, uint8_t refreshRate) 216 | { 217 | uint16_t controlRegister1; 218 | int value; 219 | int error; 220 | 221 | value = (refreshRate & 0x07)<<7; 222 | 223 | error = REDAR_I2CRead(slaveAddr, 0x800D, 1, &controlRegister1); 224 | if(error == 0) 225 | { 226 | value = (controlRegister1 & 0xFC7F) | value; 227 | error = REDAR_I2CWrite(slaveAddr, 0x800D, value); 228 | } 229 | 230 | return error; 231 | } 232 | 233 | //------------------------------------------------------------------------------ 234 | 235 | int MLX90640_GetRefreshRate(uint8_t slaveAddr) 236 | { 237 | uint16_t controlRegister1; 238 | int refreshRate; 239 | int error; 240 | 241 | error = REDAR_I2CRead(slaveAddr, 0x800D, 1, &controlRegister1); 242 | if(error != 0) 243 | { 244 | return error; 245 | } 246 | refreshRate = (controlRegister1 & 0x0380) >> 7; 247 | 248 | return refreshRate; 249 | } 250 | 251 | //------------------------------------------------------------------------------ 252 | 253 | int MLX90640_SetInterleavedMode(uint8_t slaveAddr) 254 | { 255 | uint16_t controlRegister1; 256 | int value; 257 | int error; 258 | 259 | error = REDAR_I2CRead(slaveAddr, 0x800D, 1, &controlRegister1); 260 | 261 | if(error == 0) 262 | { 263 | value = (controlRegister1 & 0xEFFF); 264 | error = REDAR_I2CWrite(slaveAddr, 0x800D, value); 265 | } 266 | 267 | return error; 268 | } 269 | 270 | //------------------------------------------------------------------------------ 271 | 272 | int MLX90640_SetChessMode(uint8_t slaveAddr) 273 | { 274 | uint16_t controlRegister1; 275 | int value; 276 | int error; 277 | 278 | error = REDAR_I2CRead(slaveAddr, 0x800D, 1, &controlRegister1); 279 | 280 | if(error == 0) 281 | { 282 | value = (controlRegister1 | 0x1000); 283 | error = REDAR_I2CWrite(slaveAddr, 0x800D, value); 284 | } 285 | 286 | return error; 287 | } 288 | 289 | //------------------------------------------------------------------------------ 290 | 291 | int MLX90640_GetCurMode(uint8_t slaveAddr) 292 | { 293 | uint16_t controlRegister1; 294 | int modeRAM; 295 | int error; 296 | 297 | error = REDAR_I2CRead(slaveAddr, 0x800D, 1, &controlRegister1); 298 | if(error != 0) 299 | { 300 | return error; 301 | } 302 | modeRAM = (controlRegister1 & 0x1000) >> 12; 303 | 304 | return modeRAM; 305 | } 306 | 307 | //------------------------------------------------------------------------------ 308 | 309 | void MLX90640_CalculateTo(uint16_t *frameData, const paramsMLX90640 *params, float emissivity, float tr, float *result) 310 | { 311 | float vdd; 312 | float ta; 313 | float ta4; 314 | float tr4; 315 | float taTr; 316 | float gain; 317 | float irDataCP[2]; 318 | float irData; 319 | float alphaCompensated; 320 | uint8_t mode; 321 | int8_t ilPattern; 322 | int8_t chessPattern; 323 | int8_t pattern; 324 | int8_t conversionPattern; 325 | float Sx; 326 | float To; 327 | float alphaCorrR[4]; 328 | int8_t range; 329 | uint16_t subPage; 330 | float ktaScale; 331 | float kvScale; 332 | float alphaScale; 333 | float kta; 334 | float kv; 335 | 336 | subPage = frameData[833]; 337 | vdd = MLX90640_GetVdd(frameData, params); 338 | ta = MLX90640_GetTa(frameData, params); 339 | 340 | ta4 = (ta + 273.15); 341 | ta4 = ta4 * ta4; 342 | ta4 = ta4 * ta4; 343 | tr4 = (tr + 273.15); 344 | tr4 = tr4 * tr4; 345 | tr4 = tr4 * tr4; 346 | taTr = tr4 - (tr4-ta4)/emissivity; 347 | 348 | ktaScale = pow(2,(double)params->ktaScale); 349 | kvScale = pow(2,(double)params->kvScale); 350 | alphaScale = pow(2,(double)params->alphaScale); 351 | 352 | alphaCorrR[0] = 1 / (1 + params->ksTo[0] * 40); 353 | alphaCorrR[1] = 1 ; 354 | alphaCorrR[2] = (1 + params->ksTo[1] * params->ct[2]); 355 | alphaCorrR[3] = alphaCorrR[2] * (1 + params->ksTo[2] * (params->ct[3] - params->ct[2])); 356 | 357 | //------------------------- Gain calculation ----------------------------------- 358 | gain = frameData[778]; 359 | if(gain > 32767) 360 | { 361 | gain = gain - 65536; 362 | } 363 | 364 | gain = params->gainEE / gain; 365 | 366 | //------------------------- To calculation ------------------------------------- 367 | mode = (frameData[832] & 0x1000) >> 5; 368 | 369 | irDataCP[0] = frameData[776]; 370 | irDataCP[1] = frameData[808]; 371 | for( int i = 0; i < 2; i++) 372 | { 373 | if(irDataCP[i] > 32767) 374 | { 375 | irDataCP[i] = irDataCP[i] - 65536; 376 | } 377 | irDataCP[i] = irDataCP[i] * gain; 378 | } 379 | irDataCP[0] = irDataCP[0] - params->cpOffset[0] * (1 + params->cpKta * (ta - 25)) * (1 + params->cpKv * (vdd - 3.3)); 380 | if( mode == params->calibrationModeEE) 381 | { 382 | irDataCP[1] = irDataCP[1] - params->cpOffset[1] * (1 + params->cpKta * (ta - 25)) * (1 + params->cpKv * (vdd - 3.3)); 383 | } 384 | else 385 | { 386 | irDataCP[1] = irDataCP[1] - (params->cpOffset[1] + params->ilChessC[0]) * (1 + params->cpKta * (ta - 25)) * (1 + params->cpKv * (vdd - 3.3)); 387 | } 388 | 389 | for( int pixelNumber = 0; pixelNumber < 768; pixelNumber++) 390 | { 391 | ilPattern = pixelNumber / 32 - (pixelNumber / 64) * 2; 392 | chessPattern = ilPattern ^ (pixelNumber - (pixelNumber/2)*2); 393 | conversionPattern = ((pixelNumber + 2) / 4 - (pixelNumber + 3) / 4 + (pixelNumber + 1) / 4 - pixelNumber / 4) * (1 - 2 * ilPattern); 394 | 395 | if(mode == 0) 396 | { 397 | pattern = ilPattern; 398 | } 399 | else 400 | { 401 | pattern = chessPattern; 402 | } 403 | 404 | if(pattern == frameData[833]) 405 | { 406 | irData = frameData[pixelNumber]; 407 | if(irData > 32767) 408 | { 409 | irData = irData - 65536; 410 | } 411 | irData = irData * gain; 412 | 413 | kta = params->kta[pixelNumber]/ktaScale; 414 | kv = params->kv[pixelNumber]/kvScale; 415 | irData = irData - params->offset[pixelNumber]*(1 + kta*(ta - 25))*(1 + kv*(vdd - 3.3)); 416 | 417 | if(mode != params->calibrationModeEE) 418 | { 419 | irData = irData + params->ilChessC[2] * (2 * ilPattern - 1) - params->ilChessC[1] * conversionPattern; 420 | } 421 | 422 | irData = irData - params->tgc * irDataCP[subPage]; 423 | irData = irData / emissivity; 424 | 425 | alphaCompensated = SCALEALPHA*alphaScale/params->alpha[pixelNumber]; 426 | alphaCompensated = alphaCompensated*(1 + params->KsTa * (ta - 25)); 427 | 428 | Sx = alphaCompensated * alphaCompensated * alphaCompensated * (irData + alphaCompensated * taTr); 429 | Sx = sqrt(sqrt(Sx)) * params->ksTo[1]; 430 | 431 | To = sqrt(sqrt(irData/(alphaCompensated * (1 - params->ksTo[1] * 273.15) + Sx) + taTr)) - 273.15; 432 | 433 | if(To < params->ct[1]) 434 | { 435 | range = 0; 436 | } 437 | else if(To < params->ct[2]) 438 | { 439 | range = 1; 440 | } 441 | else if(To < params->ct[3]) 442 | { 443 | range = 2; 444 | } 445 | else 446 | { 447 | range = 3; 448 | } 449 | 450 | To = sqrt(sqrt(irData / (alphaCompensated * alphaCorrR[range] * (1 + params->ksTo[range] * (To - params->ct[range]))) + taTr)) - 273.15; 451 | 452 | result[pixelNumber] = To; 453 | } 454 | } 455 | } 456 | 457 | //------------------------------------------------------------------------------ 458 | 459 | void MLX90640_GetImage(uint16_t *frameData, const paramsMLX90640 *params, float *result) 460 | { 461 | float vdd; 462 | float ta; 463 | float gain; 464 | float irDataCP[2]; 465 | float irData; 466 | float alphaCompensated; 467 | uint8_t mode; 468 | int8_t ilPattern; 469 | int8_t chessPattern; 470 | int8_t pattern; 471 | int8_t conversionPattern; 472 | float image; 473 | uint16_t subPage; 474 | float ktaScale; 475 | float kvScale; 476 | float kta; 477 | float kv; 478 | 479 | subPage = frameData[833]; 480 | vdd = MLX90640_GetVdd(frameData, params); 481 | ta = MLX90640_GetTa(frameData, params); 482 | 483 | ktaScale = pow(2,(double)params->ktaScale); 484 | kvScale = pow(2,(double)params->kvScale); 485 | 486 | //------------------------- Gain calculation ----------------------------------- 487 | gain = frameData[778]; 488 | if(gain > 32767) 489 | { 490 | gain = gain - 65536; 491 | } 492 | 493 | gain = params->gainEE / gain; 494 | 495 | //------------------------- Image calculation ------------------------------------- 496 | mode = (frameData[832] & 0x1000) >> 5; 497 | 498 | irDataCP[0] = frameData[776]; 499 | irDataCP[1] = frameData[808]; 500 | for( int i = 0; i < 2; i++) 501 | { 502 | if(irDataCP[i] > 32767) 503 | { 504 | irDataCP[i] = irDataCP[i] - 65536; 505 | } 506 | irDataCP[i] = irDataCP[i] * gain; 507 | } 508 | irDataCP[0] = irDataCP[0] - params->cpOffset[0] * (1 + params->cpKta * (ta - 25)) * (1 + params->cpKv * (vdd - 3.3)); 509 | if( mode == params->calibrationModeEE) 510 | { 511 | irDataCP[1] = irDataCP[1] - params->cpOffset[1] * (1 + params->cpKta * (ta - 25)) * (1 + params->cpKv * (vdd - 3.3)); 512 | } 513 | else 514 | { 515 | irDataCP[1] = irDataCP[1] - (params->cpOffset[1] + params->ilChessC[0]) * (1 + params->cpKta * (ta - 25)) * (1 + params->cpKv * (vdd - 3.3)); 516 | } 517 | 518 | for( int pixelNumber = 0; pixelNumber < 768; pixelNumber++) 519 | { 520 | ilPattern = pixelNumber / 32 - (pixelNumber / 64) * 2; 521 | chessPattern = ilPattern ^ (pixelNumber - (pixelNumber/2)*2); 522 | conversionPattern = ((pixelNumber + 2) / 4 - (pixelNumber + 3) / 4 + (pixelNumber + 1) / 4 - pixelNumber / 4) * (1 - 2 * ilPattern); 523 | 524 | if(mode == 0) 525 | { 526 | pattern = ilPattern; 527 | } 528 | else 529 | { 530 | pattern = chessPattern; 531 | } 532 | 533 | if(pattern == frameData[833]) 534 | { 535 | irData = frameData[pixelNumber]; 536 | if(irData > 32767) 537 | { 538 | irData = irData - 65536; 539 | } 540 | irData = irData * gain; 541 | 542 | kta = params->kta[pixelNumber]/ktaScale; 543 | kv = params->kv[pixelNumber]/kvScale; 544 | irData = irData - params->offset[pixelNumber]*(1 + kta*(ta - 25))*(1 + kv*(vdd - 3.3)); 545 | 546 | if(mode != params->calibrationModeEE) 547 | { 548 | irData = irData + params->ilChessC[2] * (2 * ilPattern - 1) - params->ilChessC[1] * conversionPattern; 549 | } 550 | 551 | irData = irData - params->tgc * irDataCP[subPage]; 552 | 553 | alphaCompensated = params->alpha[pixelNumber]; 554 | 555 | image = irData*alphaCompensated; 556 | 557 | result[pixelNumber] = image; 558 | } 559 | } 560 | } 561 | 562 | //------------------------------------------------------------------------------ 563 | 564 | float MLX90640_GetVdd(uint16_t *frameData, const paramsMLX90640 *params) 565 | { 566 | float vdd; 567 | float resolutionCorrection; 568 | 569 | int resolutionRAM; 570 | 571 | vdd = frameData[810]; 572 | if(vdd > 32767) 573 | { 574 | vdd = vdd - 65536; 575 | } 576 | resolutionRAM = (frameData[832] & 0x0C00) >> 10; 577 | resolutionCorrection = pow(2, (double)params->resolutionEE) / pow(2, (double)resolutionRAM); 578 | vdd = (resolutionCorrection * vdd - params->vdd25) / params->kVdd + 3.3; 579 | 580 | return vdd; 581 | } 582 | 583 | //------------------------------------------------------------------------------ 584 | 585 | float MLX90640_GetTa(uint16_t *frameData, const paramsMLX90640 *params) 586 | { 587 | float ptat; 588 | float ptatArt; 589 | float vdd; 590 | float ta; 591 | 592 | vdd = MLX90640_GetVdd(frameData, params); 593 | 594 | ptat = frameData[800]; 595 | if(ptat > 32767) 596 | { 597 | ptat = ptat - 65536; 598 | } 599 | 600 | ptatArt = frameData[768]; 601 | if(ptatArt > 32767) 602 | { 603 | ptatArt = ptatArt - 65536; 604 | } 605 | ptatArt = (ptat / (ptat * params->alphaPTAT + ptatArt)) * pow(2, (double)18); 606 | 607 | ta = (ptatArt / (1 + params->KvPTAT * (vdd - 3.3)) - params->vPTAT25); 608 | ta = ta / params->KtPTAT + 25; 609 | 610 | return ta; 611 | } 612 | 613 | //------------------------------------------------------------------------------ 614 | 615 | int MLX90640_GetSubPageNumber(uint16_t *frameData) 616 | { 617 | return frameData[833]; 618 | 619 | } 620 | 621 | //------------------------------------------------------------------------------ 622 | void MLX90640_BadPixelsCorrection(uint16_t *pixels, float *to, int mode, paramsMLX90640 *params) 623 | { 624 | float ap[4]; 625 | uint8_t pix; 626 | uint8_t line; 627 | uint8_t column; 628 | 629 | pix = 0; 630 | while(pixels[pix] != 0xFFFF) 631 | { 632 | line = pixels[pix]>>5; 633 | column = pixels[pix] - (line<<5); 634 | 635 | if(mode == 1) 636 | { 637 | if(line == 0) 638 | { 639 | if(column == 0) 640 | { 641 | to[pixels[pix]] = to[33]; 642 | } 643 | else if(column == 31) 644 | { 645 | to[pixels[pix]] = to[62]; 646 | } 647 | else 648 | { 649 | to[pixels[pix]] = (to[pixels[pix]+31] + to[pixels[pix]+33])/2.0; 650 | } 651 | } 652 | else if(line == 23) 653 | { 654 | if(column == 0) 655 | { 656 | to[pixels[pix]] = to[705]; 657 | } 658 | else if(column == 31) 659 | { 660 | to[pixels[pix]] = to[734]; 661 | } 662 | else 663 | { 664 | to[pixels[pix]] = (to[pixels[pix]-33] + to[pixels[pix]-31])/2.0; 665 | } 666 | } 667 | else if(column == 0) 668 | { 669 | to[pixels[pix]] = (to[pixels[pix]-31] + to[pixels[pix]+33])/2.0; 670 | } 671 | else if(column == 31) 672 | { 673 | to[pixels[pix]] = (to[pixels[pix]-33] + to[pixels[pix]+31])/2.0; 674 | } 675 | else 676 | { 677 | ap[0] = to[pixels[pix]-33]; 678 | ap[1] = to[pixels[pix]-31]; 679 | ap[2] = to[pixels[pix]+31]; 680 | ap[3] = to[pixels[pix]+33]; 681 | to[pixels[pix]] = GetMedian(ap,4); 682 | } 683 | } 684 | else 685 | { 686 | if(column == 0) 687 | { 688 | to[pixels[pix]] = to[pixels[pix]+1]; 689 | } 690 | else if(column == 1 || column == 30) 691 | { 692 | to[pixels[pix]] = (to[pixels[pix]-1]+to[pixels[pix]+1])/2.0; 693 | } 694 | else if(column == 31) 695 | { 696 | to[pixels[pix]] = to[pixels[pix]-1]; 697 | } 698 | else 699 | { 700 | if(IsPixelBad(pixels[pix]-2,params) == 0 && IsPixelBad(pixels[pix]+2,params) == 0) 701 | { 702 | ap[0] = to[pixels[pix]+1] - to[pixels[pix]+2]; 703 | ap[1] = to[pixels[pix]-1] - to[pixels[pix]-2]; 704 | if(fabs(ap[0]) > fabs(ap[1])) 705 | { 706 | to[pixels[pix]] = to[pixels[pix]-1] + ap[1]; 707 | } 708 | else 709 | { 710 | to[pixels[pix]] = to[pixels[pix]+1] + ap[0]; 711 | } 712 | } 713 | else 714 | { 715 | to[pixels[pix]] = (to[pixels[pix]-1]+to[pixels[pix]+1])/2.0; 716 | } 717 | } 718 | } 719 | pix = pix + 1; 720 | } 721 | } 722 | 723 | //------------------------------------------------------------------------------ 724 | 725 | void ExtractVDDParameters(uint16_t *eeData, paramsMLX90640 *mlx90640) 726 | { 727 | int16_t kVdd; 728 | int16_t vdd25; 729 | 730 | kVdd = eeData[51]; 731 | 732 | kVdd = (eeData[51] & 0xFF00) >> 8; 733 | if(kVdd > 127) 734 | { 735 | kVdd = kVdd - 256; 736 | } 737 | kVdd = 32 * kVdd; 738 | vdd25 = eeData[51] & 0x00FF; 739 | vdd25 = ((vdd25 - 256) << 5) - 8192; 740 | 741 | mlx90640->kVdd = kVdd; 742 | mlx90640->vdd25 = vdd25; 743 | } 744 | 745 | //------------------------------------------------------------------------------ 746 | 747 | void ExtractPTATParameters(uint16_t *eeData, paramsMLX90640 *mlx90640) 748 | { 749 | float KvPTAT; 750 | float KtPTAT; 751 | int16_t vPTAT25; 752 | float alphaPTAT; 753 | 754 | KvPTAT = (eeData[50] & 0xFC00) >> 10; 755 | if(KvPTAT > 31) 756 | { 757 | KvPTAT = KvPTAT - 64; 758 | } 759 | KvPTAT = KvPTAT/4096; 760 | 761 | KtPTAT = eeData[50] & 0x03FF; 762 | if(KtPTAT > 511) 763 | { 764 | KtPTAT = KtPTAT - 1024; 765 | } 766 | KtPTAT = KtPTAT/8; 767 | 768 | vPTAT25 = eeData[49]; 769 | 770 | alphaPTAT = (eeData[16] & 0xF000) / pow(2, (double)14) + 8.0f; 771 | 772 | mlx90640->KvPTAT = KvPTAT; 773 | mlx90640->KtPTAT = KtPTAT; 774 | mlx90640->vPTAT25 = vPTAT25; 775 | mlx90640->alphaPTAT = alphaPTAT; 776 | } 777 | 778 | //------------------------------------------------------------------------------ 779 | 780 | void ExtractGainParameters(uint16_t *eeData, paramsMLX90640 *mlx90640) 781 | { 782 | int16_t gainEE; 783 | 784 | gainEE = eeData[48]; 785 | if(gainEE > 32767) 786 | { 787 | gainEE = gainEE -65536; 788 | } 789 | 790 | mlx90640->gainEE = gainEE; 791 | } 792 | 793 | //------------------------------------------------------------------------------ 794 | 795 | void ExtractTgcParameters(uint16_t *eeData, paramsMLX90640 *mlx90640) 796 | { 797 | float tgc; 798 | tgc = eeData[60] & 0x00FF; 799 | if(tgc > 127) 800 | { 801 | tgc = tgc - 256; 802 | } 803 | tgc = tgc / 32.0f; 804 | 805 | mlx90640->tgc = tgc; 806 | } 807 | 808 | //------------------------------------------------------------------------------ 809 | 810 | void ExtractResolutionParameters(uint16_t *eeData, paramsMLX90640 *mlx90640) 811 | { 812 | uint8_t resolutionEE; 813 | resolutionEE = (eeData[56] & 0x3000) >> 12; 814 | 815 | mlx90640->resolutionEE = resolutionEE; 816 | } 817 | 818 | //------------------------------------------------------------------------------ 819 | 820 | void ExtractKsTaParameters(uint16_t *eeData, paramsMLX90640 *mlx90640) 821 | { 822 | float KsTa; 823 | KsTa = (eeData[60] & 0xFF00) >> 8; 824 | if(KsTa > 127) 825 | { 826 | KsTa = KsTa -256; 827 | } 828 | KsTa = KsTa / 8192.0f; 829 | 830 | mlx90640->KsTa = KsTa; 831 | } 832 | 833 | //------------------------------------------------------------------------------ 834 | 835 | void ExtractKsToParameters(uint16_t *eeData, paramsMLX90640 *mlx90640) 836 | { 837 | int KsToScale; 838 | int8_t step; 839 | 840 | step = ((eeData[63] & 0x3000) >> 12) * 10; 841 | 842 | mlx90640->ct[0] = -40; 843 | mlx90640->ct[1] = 0; 844 | mlx90640->ct[2] = (eeData[63] & 0x00F0) >> 4; 845 | mlx90640->ct[3] = (eeData[63] & 0x0F00) >> 8; 846 | 847 | mlx90640->ct[2] = mlx90640->ct[2]*step; 848 | mlx90640->ct[3] = mlx90640->ct[2] + mlx90640->ct[3]*step; 849 | mlx90640->ct[4] = 400; 850 | 851 | KsToScale = (eeData[63] & 0x000F) + 8; 852 | KsToScale = 1 << KsToScale; 853 | 854 | mlx90640->ksTo[0] = eeData[61] & 0x00FF; 855 | mlx90640->ksTo[1] = (eeData[61] & 0xFF00) >> 8; 856 | mlx90640->ksTo[2] = eeData[62] & 0x00FF; 857 | mlx90640->ksTo[3] = (eeData[62] & 0xFF00) >> 8; 858 | 859 | for(int i = 0; i < 4; i++) 860 | { 861 | if(mlx90640->ksTo[i] > 127) 862 | { 863 | mlx90640->ksTo[i] = mlx90640->ksTo[i] - 256; 864 | } 865 | mlx90640->ksTo[i] = mlx90640->ksTo[i] / KsToScale; 866 | } 867 | 868 | mlx90640->ksTo[4] = -0.0002; 869 | } 870 | 871 | //------------------------------------------------------------------------------ 872 | 873 | void ExtractAlphaParameters(uint16_t *eeData, paramsMLX90640 *mlx90640) 874 | { 875 | int accRow[24]; 876 | int accColumn[32]; 877 | int p = 0; 878 | int alphaRef; 879 | uint8_t alphaScale; 880 | uint8_t accRowScale; 881 | uint8_t accColumnScale; 882 | uint8_t accRemScale; 883 | float alphaTemp[768]; 884 | float temp; 885 | 886 | 887 | accRemScale = eeData[32] & 0x000F; 888 | accColumnScale = (eeData[32] & 0x00F0) >> 4; 889 | accRowScale = (eeData[32] & 0x0F00) >> 8; 890 | alphaScale = ((eeData[32] & 0xF000) >> 12) + 30; 891 | alphaRef = eeData[33]; 892 | 893 | for(int i = 0; i < 6; i++) 894 | { 895 | p = i * 4; 896 | accRow[p + 0] = (eeData[34 + i] & 0x000F); 897 | accRow[p + 1] = (eeData[34 + i] & 0x00F0) >> 4; 898 | accRow[p + 2] = (eeData[34 + i] & 0x0F00) >> 8; 899 | accRow[p + 3] = (eeData[34 + i] & 0xF000) >> 12; 900 | } 901 | 902 | for(int i = 0; i < 24; i++) 903 | { 904 | if (accRow[i] > 7) 905 | { 906 | accRow[i] = accRow[i] - 16; 907 | } 908 | } 909 | 910 | for(int i = 0; i < 8; i++) 911 | { 912 | p = i * 4; 913 | accColumn[p + 0] = (eeData[40 + i] & 0x000F); 914 | accColumn[p + 1] = (eeData[40 + i] & 0x00F0) >> 4; 915 | accColumn[p + 2] = (eeData[40 + i] & 0x0F00) >> 8; 916 | accColumn[p + 3] = (eeData[40 + i] & 0xF000) >> 12; 917 | } 918 | 919 | for(int i = 0; i < 32; i ++) 920 | { 921 | if (accColumn[i] > 7) 922 | { 923 | accColumn[i] = accColumn[i] - 16; 924 | } 925 | } 926 | 927 | for(int i = 0; i < 24; i++) 928 | { 929 | for(int j = 0; j < 32; j ++) 930 | { 931 | p = 32 * i +j; 932 | alphaTemp[p] = (eeData[64 + p] & 0x03F0) >> 4; 933 | if (alphaTemp[p] > 31) 934 | { 935 | alphaTemp[p] = alphaTemp[p] - 64; 936 | } 937 | alphaTemp[p] = alphaTemp[p]*(1 << accRemScale); 938 | alphaTemp[p] = (alphaRef + (accRow[i] << accRowScale) + (accColumn[j] << accColumnScale) + alphaTemp[p]); 939 | alphaTemp[p] = alphaTemp[p] / pow(2,(double)alphaScale); 940 | alphaTemp[p] = alphaTemp[p] - mlx90640->tgc * (mlx90640->cpAlpha[0] + mlx90640->cpAlpha[1])/2; 941 | alphaTemp[p] = SCALEALPHA/alphaTemp[p]; 942 | } 943 | } 944 | 945 | temp = alphaTemp[0]; 946 | for(int i = 1; i < 768; i++) 947 | { 948 | if (alphaTemp[i] > temp) 949 | { 950 | temp = alphaTemp[i]; 951 | } 952 | } 953 | 954 | alphaScale = 0; 955 | while(temp < 32768) 956 | { 957 | temp = temp*2; 958 | alphaScale = alphaScale + 1; 959 | } 960 | 961 | for(int i = 0; i < 768; i++) 962 | { 963 | temp = alphaTemp[i] * pow(2,(double)alphaScale); 964 | mlx90640->alpha[i] = (temp + 0.5); 965 | 966 | } 967 | 968 | mlx90640->alphaScale = alphaScale; 969 | 970 | } 971 | 972 | //------------------------------------------------------------------------------ 973 | 974 | void ExtractOffsetParameters(uint16_t *eeData, paramsMLX90640 *mlx90640) 975 | { 976 | int occRow[24]; 977 | int occColumn[32]; 978 | int p = 0; 979 | int16_t offsetRef; 980 | uint8_t occRowScale; 981 | uint8_t occColumnScale; 982 | uint8_t occRemScale; 983 | 984 | 985 | occRemScale = (eeData[16] & 0x000F); 986 | occColumnScale = (eeData[16] & 0x00F0) >> 4; 987 | occRowScale = (eeData[16] & 0x0F00) >> 8; 988 | offsetRef = eeData[17]; 989 | if (offsetRef > 32767) 990 | { 991 | offsetRef = offsetRef - 65536; 992 | } 993 | 994 | for(int i = 0; i < 6; i++) 995 | { 996 | p = i * 4; 997 | occRow[p + 0] = (eeData[18 + i] & 0x000F); 998 | occRow[p + 1] = (eeData[18 + i] & 0x00F0) >> 4; 999 | occRow[p + 2] = (eeData[18 + i] & 0x0F00) >> 8; 1000 | occRow[p + 3] = (eeData[18 + i] & 0xF000) >> 12; 1001 | } 1002 | 1003 | for(int i = 0; i < 24; i++) 1004 | { 1005 | if (occRow[i] > 7) 1006 | { 1007 | occRow[i] = occRow[i] - 16; 1008 | } 1009 | } 1010 | 1011 | for(int i = 0; i < 8; i++) 1012 | { 1013 | p = i * 4; 1014 | occColumn[p + 0] = (eeData[24 + i] & 0x000F); 1015 | occColumn[p + 1] = (eeData[24 + i] & 0x00F0) >> 4; 1016 | occColumn[p + 2] = (eeData[24 + i] & 0x0F00) >> 8; 1017 | occColumn[p + 3] = (eeData[24 + i] & 0xF000) >> 12; 1018 | } 1019 | 1020 | for(int i = 0; i < 32; i ++) 1021 | { 1022 | if (occColumn[i] > 7) 1023 | { 1024 | occColumn[i] = occColumn[i] - 16; 1025 | } 1026 | } 1027 | 1028 | for(int i = 0; i < 24; i++) 1029 | { 1030 | for(int j = 0; j < 32; j ++) 1031 | { 1032 | p = 32 * i +j; 1033 | mlx90640->offset[p] = (eeData[64 + p] & 0xFC00) >> 10; 1034 | if (mlx90640->offset[p] > 31) 1035 | { 1036 | mlx90640->offset[p] = mlx90640->offset[p] - 64; 1037 | } 1038 | mlx90640->offset[p] = mlx90640->offset[p]*(1 << occRemScale); 1039 | mlx90640->offset[p] = (offsetRef + (occRow[i] << occRowScale) + (occColumn[j] << occColumnScale) + mlx90640->offset[p]); 1040 | } 1041 | } 1042 | } 1043 | 1044 | //------------------------------------------------------------------------------ 1045 | 1046 | void ExtractKtaPixelParameters(uint16_t *eeData, paramsMLX90640 *mlx90640) 1047 | { 1048 | int p = 0; 1049 | int8_t KtaRC[4]; 1050 | int8_t KtaRoCo; 1051 | int8_t KtaRoCe; 1052 | int8_t KtaReCo; 1053 | int8_t KtaReCe; 1054 | uint8_t ktaScale1; 1055 | uint8_t ktaScale2; 1056 | uint8_t split; 1057 | float ktaTemp[768]; 1058 | float temp; 1059 | 1060 | KtaRoCo = (eeData[54] & 0xFF00) >> 8; 1061 | if (KtaRoCo > 127) 1062 | { 1063 | KtaRoCo = KtaRoCo - 256; 1064 | } 1065 | KtaRC[0] = KtaRoCo; 1066 | 1067 | KtaReCo = (eeData[54] & 0x00FF); 1068 | if (KtaReCo > 127) 1069 | { 1070 | KtaReCo = KtaReCo - 256; 1071 | } 1072 | KtaRC[2] = KtaReCo; 1073 | 1074 | KtaRoCe = (eeData[55] & 0xFF00) >> 8; 1075 | if (KtaRoCe > 127) 1076 | { 1077 | KtaRoCe = KtaRoCe - 256; 1078 | } 1079 | KtaRC[1] = KtaRoCe; 1080 | 1081 | KtaReCe = (eeData[55] & 0x00FF); 1082 | if (KtaReCe > 127) 1083 | { 1084 | KtaReCe = KtaReCe - 256; 1085 | } 1086 | KtaRC[3] = KtaReCe; 1087 | 1088 | ktaScale1 = ((eeData[56] & 0x00F0) >> 4) + 8; 1089 | ktaScale2 = (eeData[56] & 0x000F); 1090 | 1091 | for(int i = 0; i < 24; i++) 1092 | { 1093 | for(int j = 0; j < 32; j ++) 1094 | { 1095 | p = 32 * i +j; 1096 | split = 2*(p/32 - (p/64)*2) + p%2; 1097 | ktaTemp[p] = (eeData[64 + p] & 0x000E) >> 1; 1098 | if (ktaTemp[p] > 3) 1099 | { 1100 | ktaTemp[p] = ktaTemp[p] - 8; 1101 | } 1102 | ktaTemp[p] = ktaTemp[p] * (1 << ktaScale2); 1103 | ktaTemp[p] = KtaRC[split] + ktaTemp[p]; 1104 | ktaTemp[p] = ktaTemp[p] / pow(2,(double)ktaScale1); 1105 | //ktaTemp[p] = ktaTemp[p] * mlx90640->offset[p]; 1106 | } 1107 | } 1108 | 1109 | temp = fabs(ktaTemp[0]); 1110 | for(int i = 1; i < 768; i++) 1111 | { 1112 | if (fabs(ktaTemp[i]) > temp) 1113 | { 1114 | temp = fabs(ktaTemp[i]); 1115 | } 1116 | } 1117 | 1118 | ktaScale1 = 0; 1119 | while(temp < 64) 1120 | { 1121 | temp = temp*2; 1122 | ktaScale1 = ktaScale1 + 1; 1123 | } 1124 | 1125 | for(int i = 0; i < 768; i++) 1126 | { 1127 | temp = ktaTemp[i] * pow(2,(double)ktaScale1); 1128 | if (temp < 0) 1129 | { 1130 | mlx90640->kta[i] = (temp - 0.5); 1131 | } 1132 | else 1133 | { 1134 | mlx90640->kta[i] = (temp + 0.5); 1135 | } 1136 | 1137 | } 1138 | 1139 | mlx90640->ktaScale = ktaScale1; 1140 | } 1141 | 1142 | 1143 | //------------------------------------------------------------------------------ 1144 | 1145 | void ExtractKvPixelParameters(uint16_t *eeData, paramsMLX90640 *mlx90640) 1146 | { 1147 | int p = 0; 1148 | int8_t KvT[4]; 1149 | int8_t KvRoCo; 1150 | int8_t KvRoCe; 1151 | int8_t KvReCo; 1152 | int8_t KvReCe; 1153 | uint8_t kvScale; 1154 | uint8_t split; 1155 | float kvTemp[768]; 1156 | float temp; 1157 | 1158 | KvRoCo = (eeData[52] & 0xF000) >> 12; 1159 | if (KvRoCo > 7) 1160 | { 1161 | KvRoCo = KvRoCo - 16; 1162 | } 1163 | KvT[0] = KvRoCo; 1164 | 1165 | KvReCo = (eeData[52] & 0x0F00) >> 8; 1166 | if (KvReCo > 7) 1167 | { 1168 | KvReCo = KvReCo - 16; 1169 | } 1170 | KvT[2] = KvReCo; 1171 | 1172 | KvRoCe = (eeData[52] & 0x00F0) >> 4; 1173 | if (KvRoCe > 7) 1174 | { 1175 | KvRoCe = KvRoCe - 16; 1176 | } 1177 | KvT[1] = KvRoCe; 1178 | 1179 | KvReCe = (eeData[52] & 0x000F); 1180 | if (KvReCe > 7) 1181 | { 1182 | KvReCe = KvReCe - 16; 1183 | } 1184 | KvT[3] = KvReCe; 1185 | 1186 | kvScale = (eeData[56] & 0x0F00) >> 8; 1187 | 1188 | 1189 | for(int i = 0; i < 24; i++) 1190 | { 1191 | for(int j = 0; j < 32; j ++) 1192 | { 1193 | p = 32 * i +j; 1194 | split = 2*(p/32 - (p/64)*2) + p%2; 1195 | kvTemp[p] = KvT[split]; 1196 | kvTemp[p] = kvTemp[p] / pow(2,(double)kvScale); 1197 | //kvTemp[p] = kvTemp[p] * mlx90640->offset[p]; 1198 | } 1199 | } 1200 | 1201 | temp = fabs(kvTemp[0]); 1202 | for(int i = 1; i < 768; i++) 1203 | { 1204 | if (fabs(kvTemp[i]) > temp) 1205 | { 1206 | temp = fabs(kvTemp[i]); 1207 | } 1208 | } 1209 | 1210 | kvScale = 0; 1211 | while(temp < 64) 1212 | { 1213 | temp = temp*2; 1214 | kvScale = kvScale + 1; 1215 | } 1216 | 1217 | for(int i = 0; i < 768; i++) 1218 | { 1219 | temp = kvTemp[i] * pow(2,(double)kvScale); 1220 | if (temp < 0) 1221 | { 1222 | mlx90640->kv[i] = (temp - 0.5); 1223 | } 1224 | else 1225 | { 1226 | mlx90640->kv[i] = (temp + 0.5); 1227 | } 1228 | 1229 | } 1230 | 1231 | mlx90640->kvScale = kvScale; 1232 | } 1233 | 1234 | //------------------------------------------------------------------------------ 1235 | 1236 | void ExtractCPParameters(uint16_t *eeData, paramsMLX90640 *mlx90640) 1237 | { 1238 | float alphaSP[2]; 1239 | int16_t offsetSP[2]; 1240 | float cpKv; 1241 | float cpKta; 1242 | uint8_t alphaScale; 1243 | uint8_t ktaScale1; 1244 | uint8_t kvScale; 1245 | 1246 | alphaScale = ((eeData[32] & 0xF000) >> 12) + 27; 1247 | 1248 | offsetSP[0] = (eeData[58] & 0x03FF); 1249 | if (offsetSP[0] > 511) 1250 | { 1251 | offsetSP[0] = offsetSP[0] - 1024; 1252 | } 1253 | 1254 | offsetSP[1] = (eeData[58] & 0xFC00) >> 10; 1255 | if (offsetSP[1] > 31) 1256 | { 1257 | offsetSP[1] = offsetSP[1] - 64; 1258 | } 1259 | offsetSP[1] = offsetSP[1] + offsetSP[0]; 1260 | 1261 | alphaSP[0] = (eeData[57] & 0x03FF); 1262 | if (alphaSP[0] > 511) 1263 | { 1264 | alphaSP[0] = alphaSP[0] - 1024; 1265 | } 1266 | alphaSP[0] = alphaSP[0] / pow(2,(double)alphaScale); 1267 | 1268 | alphaSP[1] = (eeData[57] & 0xFC00) >> 10; 1269 | if (alphaSP[1] > 31) 1270 | { 1271 | alphaSP[1] = alphaSP[1] - 64; 1272 | } 1273 | alphaSP[1] = (1 + alphaSP[1]/128) * alphaSP[0]; 1274 | 1275 | cpKta = (eeData[59] & 0x00FF); 1276 | if (cpKta > 127) 1277 | { 1278 | cpKta = cpKta - 256; 1279 | } 1280 | ktaScale1 = ((eeData[56] & 0x00F0) >> 4) + 8; 1281 | mlx90640->cpKta = cpKta / pow(2,(double)ktaScale1); 1282 | 1283 | cpKv = (eeData[59] & 0xFF00) >> 8; 1284 | if (cpKv > 127) 1285 | { 1286 | cpKv = cpKv - 256; 1287 | } 1288 | kvScale = (eeData[56] & 0x0F00) >> 8; 1289 | mlx90640->cpKv = cpKv / pow(2,(double)kvScale); 1290 | 1291 | mlx90640->cpAlpha[0] = alphaSP[0]; 1292 | mlx90640->cpAlpha[1] = alphaSP[1]; 1293 | mlx90640->cpOffset[0] = offsetSP[0]; 1294 | mlx90640->cpOffset[1] = offsetSP[1]; 1295 | } 1296 | 1297 | //------------------------------------------------------------------------------ 1298 | 1299 | void ExtractCILCParameters(uint16_t *eeData, paramsMLX90640 *mlx90640) 1300 | { 1301 | float ilChessC[3]; 1302 | uint8_t calibrationModeEE; 1303 | 1304 | calibrationModeEE = (eeData[10] & 0x0800) >> 4; 1305 | calibrationModeEE = calibrationModeEE ^ 0x80; 1306 | 1307 | ilChessC[0] = (eeData[53] & 0x003F); 1308 | if (ilChessC[0] > 31) 1309 | { 1310 | ilChessC[0] = ilChessC[0] - 64; 1311 | } 1312 | ilChessC[0] = ilChessC[0] / 16.0f; 1313 | 1314 | ilChessC[1] = (eeData[53] & 0x07C0) >> 6; 1315 | if (ilChessC[1] > 15) 1316 | { 1317 | ilChessC[1] = ilChessC[1] - 32; 1318 | } 1319 | ilChessC[1] = ilChessC[1] / 2.0f; 1320 | 1321 | ilChessC[2] = (eeData[53] & 0xF800) >> 11; 1322 | if (ilChessC[2] > 15) 1323 | { 1324 | ilChessC[2] = ilChessC[2] - 32; 1325 | } 1326 | ilChessC[2] = ilChessC[2] / 8.0f; 1327 | 1328 | mlx90640->calibrationModeEE = calibrationModeEE; 1329 | mlx90640->ilChessC[0] = ilChessC[0]; 1330 | mlx90640->ilChessC[1] = ilChessC[1]; 1331 | mlx90640->ilChessC[2] = ilChessC[2]; 1332 | } 1333 | 1334 | //------------------------------------------------------------------------------ 1335 | 1336 | int ExtractDeviatingPixels(uint16_t *eeData, paramsMLX90640 *mlx90640) 1337 | { 1338 | uint16_t pixCnt = 0; 1339 | uint16_t brokenPixCnt = 0; 1340 | uint16_t outlierPixCnt = 0; 1341 | int warn = 0; 1342 | int i; 1343 | 1344 | for(pixCnt = 0; pixCnt<5; pixCnt++) 1345 | { 1346 | mlx90640->brokenPixels[pixCnt] = 0xFFFF; 1347 | mlx90640->outlierPixels[pixCnt] = 0xFFFF; 1348 | } 1349 | 1350 | pixCnt = 0; 1351 | while (pixCnt < 768 && brokenPixCnt < 5 && outlierPixCnt < 5) 1352 | { 1353 | if(eeData[pixCnt+64] == 0) 1354 | { 1355 | mlx90640->brokenPixels[brokenPixCnt] = pixCnt; 1356 | brokenPixCnt = brokenPixCnt + 1; 1357 | } 1358 | else if((eeData[pixCnt+64] & 0x0001) != 0) 1359 | { 1360 | mlx90640->outlierPixels[outlierPixCnt] = pixCnt; 1361 | outlierPixCnt = outlierPixCnt + 1; 1362 | } 1363 | 1364 | pixCnt = pixCnt + 1; 1365 | 1366 | } 1367 | 1368 | if(brokenPixCnt > 4) 1369 | { 1370 | warn = -3; 1371 | } 1372 | else if(outlierPixCnt > 4) 1373 | { 1374 | warn = -4; 1375 | } 1376 | else if((brokenPixCnt + outlierPixCnt) > 4) 1377 | { 1378 | warn = -5; 1379 | } 1380 | else 1381 | { 1382 | for(pixCnt=0; pixCntbrokenPixels[pixCnt],mlx90640->brokenPixels[i]); 1387 | if(warn != 0) 1388 | { 1389 | return warn; 1390 | } 1391 | } 1392 | } 1393 | 1394 | for(pixCnt=0; pixCntoutlierPixels[pixCnt],mlx90640->outlierPixels[i]); 1399 | if(warn != 0) 1400 | { 1401 | return warn; 1402 | } 1403 | } 1404 | } 1405 | 1406 | for(pixCnt=0; pixCntbrokenPixels[pixCnt],mlx90640->outlierPixels[i]); 1411 | if(warn != 0) 1412 | { 1413 | return warn; 1414 | } 1415 | } 1416 | } 1417 | 1418 | } 1419 | 1420 | 1421 | return warn; 1422 | 1423 | } 1424 | 1425 | //------------------------------------------------------------------------------ 1426 | 1427 | int CheckAdjacentPixels(uint16_t pix1, uint16_t pix2) 1428 | { 1429 | int pixPosDif; 1430 | 1431 | pixPosDif = pix1 - pix2; 1432 | if(pixPosDif > -34 && pixPosDif < -30) 1433 | { 1434 | return -6; 1435 | } 1436 | if(pixPosDif > -2 && pixPosDif < 2) 1437 | { 1438 | return -6; 1439 | } 1440 | if(pixPosDif > 30 && pixPosDif < 34) 1441 | { 1442 | return -6; 1443 | } 1444 | 1445 | return 0; 1446 | } 1447 | 1448 | //------------------------------------------------------------------------------ 1449 | 1450 | float GetMedian(float *values, int n) 1451 | { 1452 | float temp; 1453 | 1454 | for(int i=0; ioutlierPixels[i] || pixel == params->brokenPixels[i]) 1486 | { 1487 | return 1; 1488 | } 1489 | } 1490 | 1491 | return 0; 1492 | } 1493 | 1494 | //------------------------------------------------------------------------------ 1495 | --------------------------------------------------------------------------------