mt9d111.c
1 /* Copyright 2018 Canaan Inc. 2 * 3 * Licensed under the Apache License, Version 2.0 (the "License"); 4 * you may not use this file except in compliance with the License. 5 * You may obtain a copy of the License at 6 * 7 * http://www.apache.org/licenses/LICENSE-2.0 8 * 9 * Unless required by applicable law or agreed to in writing, software 10 * distributed under the License is distributed on an "AS IS" BASIS}, 11 * WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied. 12 * See the License for the specific language governing permissions and 13 * limitations under the License. 14 */ 15 #include <stdio.h> 16 #include "mt9d111.h" 17 #include "dvp.h" 18 #include "plic.h" 19 #include "sleep.h" 20 #include "sensor.h" 21 #include "mphalport.h" 22 #include "cambus.h" 23 #include "printf.h" 24 25 static i2c_device_number_t i2c_dev_tmp = -2; // i2c_device_number_t components/micropython/port/src/omv/cambus.c 26 27 /** 28 * \brief Struct to store an register address and its value. 29 */ 30 struct Register 31 { 32 uint8_t address; /**< struct Register address. */ 33 uint16_t value; /**< struct Register value. */ 34 }; 35 36 /** 37 * \brief Default registers values (Values after boot). 38 */ 39 const struct Register reg_default_vals[] = 40 { 41 {MT9D111_REG_ROW_START, 0x001C}, 42 {MT9D111_REG_COLUMN_START, 0x003C}, 43 {MT9D111_REG_ROW_WIDTH, 0x04B0}, 44 {MT9D111_REG_COL_WIDTH, 0x0640}, 45 {MT9D111_REG_HORIZONTAL_BLANKING_B, 0x0204}, 46 {MT9D111_REG_VERTICAL_BLANKING_B, 0x002F}, 47 {MT9D111_REG_HORIZONTAL_BLANKING_A, 0x00FE}, 48 {MT9D111_REG_VERTICAL_BLANKING_A, 0x000C}, 49 {MT9D111_REG_SHUTTER_WIDTH, 0x04D0}, 50 {MT9D111_REG_ROW_SPEED, 0x0001}, 51 {MT9D111_REG_EXTRA_DELAY, 0x0000}, 52 {MT9D111_REG_SHUTTER_DELAY, 0x0000}, 53 {MT9D111_REG_RESET, 0x0000}, 54 {MT9D111_REG_FRAME_VALID_CONTROL, 0x0000}, 55 {MT9D111_REG_READ_MODE_B, 0x0300}, 56 {MT9D111_REG_READ_MODE_A, 0x8400}, 57 {MT9D111_REG_DARK_COL_ROWS, 0x010F}, 58 {MT9D111_REG_FLASH, 0x0608}, 59 {MT9D111_REG_EXTRA_RESET, 0x8000}, 60 {MT9D111_REG_LINE_VALID_CONTROL, 0x0000}, 61 {MT9D111_REG_BOTTOM_DARK_ROWS, 0x0007}, 62 {MT9D111_REG_GREEN_1_GAIN, 0x0020}, 63 {MT9D111_REG_BLUE_GAIN, 0x0020}, 64 {MT9D111_REG_RED_GAIN, 0x0020}, 65 {MT9D111_REG_GREEN_2_GAIN, 0x0020}, 66 {MT9D111_REG_GLOBAL_GAIN, 0x0020}, 67 {MT9D111_REG_ROW_NOISE, 0x042A}, 68 {MT9D111_REG_BLACK_ROWS, 0x00FF}, 69 {MT9D111_REG_DARK_G1_AVERAGE, 0x0000}, 70 {MT9D111_REG_DARK_B_AVERAGE, 0x0000}, 71 {MT9D111_REG_DARK_R_AVERAGE, 0x0000}, 72 {MT9D111_REG_DARK_G2_AVERAGE, 0x0000}, 73 {MT9D111_REG_CALIB_THRESHOLD, 0x231D}, 74 {MT9D111_REG_CALIB_CONTROL, 0x0080}, 75 {MT9D111_REG_CALIB_GREEN_1, 0x0000}, 76 {MT9D111_REG_CALIB_BLUE, 0x0000}, 77 {MT9D111_REG_CALIB_RED, 0x0000}, 78 {MT9D111_REG_CALIB_GREEN_2, 0x0000}, 79 {MT9D111_REG_CLOCK_CONTROL, 0xE000}, 80 {MT9D111_REG_PLL_CONTROL_1, 0x1000}, 81 {MT9D111_REG_PLL_CONTROL_2, 0x0500}, 82 {MT9D111_REG_GLOBAL_SHUTTER_CONTROL, 0x0000}, 83 {MT9D111_REG_START_INTEGRATION_T1, 0x0064}, 84 {MT9D111_REG_START_READOUT_T2, 0x0064}, 85 {MT9D111_REG_ASSERT_STROBE_T3, 0x0096}, 86 {MT9D111_REG_DEASSERT_STROBE_T4, 0x00C8}, 87 {MT9D111_REG_ASSERT_FLASH, 0x0064}, 88 {MT9D111_REG_DEASSERT_FLASH, 0x0078}, 89 {MT9D111_REG_EXTERNAL_SAMPLE_1, 0x0000}, 90 {MT9D111_REG_EXTERNAL_SAMPLE_2, 0x0000}, 91 {MT9D111_REG_EXTERNAL_SAMPLE_3, 0x0000}, 92 {MT9D111_REG_EXTERNAL_SAMPLING_CONTROL, 0x0000}, 93 {MT9D111_REG_PAGE_REGISTER, 0x0000}, 94 {MT9D111_REG_BYTEWISE_ADDRESS, 0x0000}, 95 {MT9D111_REG_CONTEXT_CONTROL, 0x0000} 96 }; 97 98 /** 99 * \brief QVGA (320x240) at 30 FPS. 100 * 101 * \see https://github.com/ArduCAM/Arduino/blob/master/ArduCAM/mt9d111_regs.h 102 */ 103 const struct Register reg_vals_qvga_30fps[] = 104 { 105 {MT9D111_REG_PAGE_REGISTER , MT9D111_REG_PAGE_0}, 106 {0x33 , 0x0343}, // RESERVED_CORE_33 107 108 {MT9D111_REG_PAGE_REGISTER , MT9D111_REG_PAGE_1}, 109 {MT9D111_REG_MICROCONTROLLER_VARIABLE_ADDRESS , 0xA115}, // SEQ_LLMODE 110 {MT9D111_REG_MICROCONTROLLER_VARIABLE_DATA , 0x0020}, // SEQ_LLMODE 111 112 {MT9D111_REG_PAGE_REGISTER , MT9D111_REG_PAGE_0}, 113 {0x38 , 0x0866}, // RESERVED_CORE_38 114 115 {MT9D111_REG_PAGE_REGISTER , MT9D111_REG_PAGE_2}, 116 {MT9D111_REG_LENS_CORRECTION_CONTROL , 0x0168}, // LENS_CORRECTION_CONTROL 117 {MT9D111_REG_ZONE_BOUNDARIES_X1_AND_X2 , 0x6432}, // ZONE_BOUNDS_X1_X2 118 {MT9D111_REG_ZONE_BOUNDARIES_X0_AND_X3 , 0x3296}, // ZONE_BOUNDS_X0_X3 119 {MT9D111_REG_ZONE_BOUNDARIES_X4_AND_X5 , 0x9664}, // ZONE_BOUNDS_X4_X5 120 {MT9D111_REG_ZONE_BOUNDARIES_Y1_AND_Y2 , 0x5028}, // ZONE_BOUNDS_Y1_Y2 121 {MT9D111_REG_ZONE_BOUNDARIES_Y0_AND_Y3 , 0x2878}, // ZONE_BOUNDS_Y0_Y3 122 {MT9D111_REG_ZONE_BOUNDARIES_Y4_AND_Y5 , 0x7850}, // ZONE_BOUNDS_Y4_Y5 123 {MT9D111_REG_CENTER_OFFSET , 0x0000}, // CENTER_OFFSET 124 {MT9D111_REG_FX_FOR_RED_COLOR_AT_THE_FIRST_PIXEL_OF_THE_ARRAY , 0x0152}, // FX_RED 125 {MT9D111_REG_FX_FOR_GREEN_COLOR_AT_THE_FIRST_PIXEL_OF_THE_ARRAY , 0x015C}, // FX_GREEN 126 {MT9D111_REG_FX_FOR_BLUE_COLOR_AT_THE_FIRST_PIXEL_OF_THE_ARRAY , 0x00F4}, // FX_BLUE 127 {MT9D111_REG_FY_FOR_RED_COLOR_AT_THE_FIRST_PIXEL_OF_THE_ARRAY , 0x0108}, // FY_RED 128 {MT9D111_REG_FY_FOR_GREEN_COLOR_AT_THE_FIRST_PIXEL_OF_THE_ARRAY , 0x00FA}, // FY_GREEN 129 {MT9D111_REG_FY_FOR_BLUE_COLOR_AT_THE_FIRST_PIXEL_OF_THE_ARRAY , 0x00CF}, // FY_BLUE 130 {MT9D111_REG_DF_DX_FOR_RED_COLOR_AT_THE_FIRST_PIXEL_OF_THE_ARRAY , 0x09AD}, // DF_DX_RED 131 {MT9D111_REG_DF_DX_FOR_GREEN_COLOR_AT_THE_FIRST_PIXEL_OF_THE_ARRAY , 0x091E}, // DF_DX_GREEN 132 {MT9D111_REG_DF_DX_FOR_BLUE_COLOR_AT_THE_FIRST_PIXEL_OF_THE_ARRAY , 0x0B3F}, // DF_DX_BLUE 133 {MT9D111_REG_DF_DY_FOR_RED_COLOR_AT_THE_FIRST_PIXEL_OF_THE_ARRAY , 0x0C85}, // DF_DY_RED 134 {MT9D111_REG_DF_DY_FOR_GREEN_COLOR_AT_THE_FIRST_PIXEL_OF_THE_ARRAY , 0x0CFF}, // DF_DY_GREEN 135 {MT9D111_REG_DF_DY_FOR_BLUE_COLOR_AT_THE_FIRST_PIXEL_OF_THE_ARRAY , 0x0D86}, // DF_DY_BLUE 136 {MT9D111_REG_SECOND_DERIVATIVE_FOR_ZONE_0_RED_COLOR , 0x163A}, // SECOND_DERIV_ZONE_0_RED 137 {MT9D111_REG_SECOND_DERIVATIVE_FOR_ZONE_0_GREEN_COLOR , 0x0E47}, // SECOND_DERIV_ZONE_0_GREEN 138 {MT9D111_REG_SECOND_DERIVATIVE_FOR_ZONE_0_BLUE_COLOR , 0x103C}, // SECOND_DERIV_ZONE_0_BLUE 139 {MT9D111_REG_SECOND_DERIVATIVE_FOR_ZONE_1_RED_COLOR , 0x1D35}, // SECOND_DERIV_ZONE_1_RED 140 {MT9D111_REG_SECOND_DERIVATIVE_FOR_ZONE_1_GREEN_COLOR , 0x173E}, // SECOND_DERIV_ZONE_1_GREEN 141 {MT9D111_REG_SECOND_DERIVATIVE_FOR_ZONE_1_BLUE_COLOR , 0x1119}, // SECOND_DERIV_ZONE_1_BLUE 142 {MT9D111_REG_SECOND_DERIVATIVE_FOR_ZONE_2_RED_COLOR , 0x1663}, // SECOND_DERIV_ZONE_2_RED 143 {MT9D111_REG_SECOND_DERIVATIVE_FOR_ZONE_2_GREEN_COLOR , 0x1569}, // SECOND_DERIV_ZONE_2_GREEN 144 {MT9D111_REG_SECOND_DERIVATIVE_FOR_ZONE_2_BLUE_COLOR , 0x104C}, // SECOND_DERIV_ZONE_2_BLUE 145 {MT9D111_REG_SECOND_DERIVATIVE_FOR_ZONE_3_RED_COLOR , 0x1015}, // SECOND_DERIV_ZONE_3_RED 146 {MT9D111_REG_SECOND_DERIVATIVE_FOR_ZONE_3_GREEN_COLOR , 0x1010}, // SECOND_DERIV_ZONE_3_GREEN 147 {MT9D111_REG_SECOND_DERIVATIVE_FOR_ZONE_3_BLUE_COLOR , 0x0B0A}, // SECOND_DERIV_ZONE_3_BLUE 148 {MT9D111_REG_SECOND_DERIVATIVE_FOR_ZONE_4_RED_COLOR , 0x0D53}, // SECOND_DERIV_ZONE_4_RED 149 {MT9D111_REG_SECOND_DERIVATIVE_FOR_ZONE_4_GREEN_COLOR , 0x0D51}, // SECOND_DERIV_ZONE_4_GREEN 150 {MT9D111_REG_SECOND_DERIVATIVE_FOR_ZONE_4_BLUE_COLOR , 0x0A44}, // SECOND_DERIV_ZONE_4_BLUE 151 {MT9D111_REG_SECOND_DERIVATIVE_FOR_ZONE_5_RED_COLOR , 0x1545}, // SECOND_DERIV_ZONE_5_RED 152 {MT9D111_REG_SECOND_DERIVATIVE_FOR_ZONE_5_GREEN_COLOR , 0x1643}, // SECOND_DERIV_ZONE_5_GREEN 153 {MT9D111_REG_SECOND_DERIVATIVE_FOR_ZONE_5_BLUE_COLOR , 0x1231}, // SECOND_DERIV_ZONE_5_BLUE 154 {MT9D111_REG_SECOND_DERIVATIVE_FOR_ZONE_6_RED_COLOR , 0x0047}, // SECOND_DERIV_ZONE_6_RED 155 {MT9D111_REG_SECOND_DERIVATIVE_FOR_ZONE_6_GREEN_COLOR , 0x035C}, // SECOND_DERIV_ZONE_6_GREEN 156 {MT9D111_REG_SECOND_DERIVATIVE_FOR_ZONE_6_BLUE_COLOR , 0xFE30}, // SECOND_DERIV_ZONE_6_BLUE 157 {MT9D111_REG_SECOND_DERIVATIVE_FOR_ZONE_7_RED_COLOR , 0x4625}, // SECOND_DERIV_ZONE_7_RED 158 {MT9D111_REG_SECOND_DERIVATIVE_FOR_ZONE_7_GREEN_COLOR , 0x47F3}, // SECOND_DERIV_ZONE_7_GREEN 159 {MT9D111_REG_SECOND_DERIVATIVE_FOR_ZONE_7_BLUE_COLOR , 0x5859}, // SECOND_DERIV_ZONE_7_BLUE 160 {MT9D111_REG_X2_FACTORS , 0x0000}, // X2_FACTORS 161 {MT9D111_REG_GLOBAL_OFFSET_OF_FXY_FUNCTION , 0x0000}, // GLOBAL_OFFSET_FXY_FUNCTION 162 {MT9D111_REG_K_FACTOR_IN_K_FX_FY , 0x0000}, // K_FACTOR_IN_K_FX_FY 163 164 {MT9D111_REG_PAGE_REGISTER , MT9D111_REG_PAGE_1}, 165 {MT9D111_REG_COLOR_PIPELINE_CONTROL , 0x01FC}, // COLOR_PIPELINE_CONTROL 166 167 {MT9D111_REG_PAGE_REGISTER , MT9D111_REG_PAGE_1}, 168 {MT9D111_REG_YUV_YCbCr_CONTROL , 0x0004}, // YUV_YCBCR_CONTROL 169 170 {MT9D111_REG_PAGE_REGISTER , MT9D111_REG_PAGE_0}, 171 {MT9D111_REG_CLOCK_CONTROL , 0xA000}, // CLOCK_ENABLING 172 173 {MT9D111_REG_PAGE_REGISTER , MT9D111_REG_PAGE_1}, 174 {MT9D111_REG_MICROCONTROLLER_VARIABLE_ADDRESS , 0xA102}, // SEQ_MODE 175 {MT9D111_REG_MICROCONTROLLER_VARIABLE_DATA , 0x001F}, // SEQ_MODE 176 {MT9D111_REG_COLOR_PIPELINE_CONTROL , 0x01FC}, // COLOR_PIPELINE_CONTROL 177 {MT9D111_REG_COLOR_PIPELINE_CONTROL , 0x01EC}, // COLOR_PIPELINE_CONTROL 178 {MT9D111_REG_COLOR_PIPELINE_CONTROL , 0x01FC}, // COLOR_PIPELINE_CONTROL 179 {MT9D111_REG_2D_APERTURE_CORRECTION_PARAMETERS , 0x0F08}, // APERTURE_PARAMETERS 180 {MT9D111_REG_MICROCONTROLLER_VARIABLE_ADDRESS , 0x270B}, // MODE_CONFIG 181 {MT9D111_REG_MICROCONTROLLER_VARIABLE_DATA , 0x0030}, // MODE_CONFIG, JPEG disabled for A and B 182 {MT9D111_REG_MICROCONTROLLER_VARIABLE_ADDRESS , 0xA121}, // SEQ_CAP_MODE 183 {MT9D111_REG_MICROCONTROLLER_VARIABLE_DATA , 0x007F}, // SEQ_CAP_MODE (127 frames before switching to Preview) 184 185 {MT9D111_REG_PAGE_REGISTER , MT9D111_REG_PAGE_0}, 186 {MT9D111_REG_HORIZONTAL_BLANKING_B , 0x00ED}, // HORZ_BLANK_B 187 {MT9D111_REG_VERTICAL_BLANKING_B , 0x000B}, // VERT_BLANK_B 188 {MT9D111_REG_HORIZONTAL_BLANKING_A , 0x0193}, // HORZ_BLANK_A 189 {MT9D111_REG_VERTICAL_BLANKING_A , 0x000B}, // VERT_BLANK_A 190 {MT9D111_REG_READ_MODE_B , 0x0700}, // READ_MODE_B (Image flip settings) 191 {MT9D111_REG_READ_MODE_A , 0x8400}, // READ_MODE_A (1ADC) 192 193 {MT9D111_REG_PAGE_REGISTER , MT9D111_REG_PAGE_1}, 194 {MT9D111_REG_MICROCONTROLLER_VARIABLE_ADDRESS , 0x2717}, // MODE_SENSOR_X_DELAY_A 195 {MT9D111_REG_MICROCONTROLLER_VARIABLE_DATA , 0x0187}, // MODE_SENSOR_X_DELAY_A 196 {MT9D111_REG_MICROCONTROLLER_VARIABLE_ADDRESS , 0x270F}, // MODE_SENSOR_ROW_START_A 197 {MT9D111_REG_MICROCONTROLLER_VARIABLE_DATA , 0x001C}, // MODE_SENSOR_ROW_START_A 198 {MT9D111_REG_MICROCONTROLLER_VARIABLE_ADDRESS , 0x2711}, // MODE_SENSOR_COL_START_A 199 {MT9D111_REG_MICROCONTROLLER_VARIABLE_DATA , 0x003C}, // MODE_SENSOR_COL_START_A 200 {MT9D111_REG_MICROCONTROLLER_VARIABLE_ADDRESS , 0x2713}, // MODE_SENSOR_ROW_HEIGHT_A 201 {MT9D111_REG_MICROCONTROLLER_VARIABLE_DATA , 0x04B0}, // MODE_SENSOR_ROW_HEIGHT_A 202 {MT9D111_REG_MICROCONTROLLER_VARIABLE_ADDRESS , 0x2715}, // MODE_SENSOR_COL_WIDTH_A 203 {MT9D111_REG_MICROCONTROLLER_VARIABLE_DATA , 0x0640}, // MODE_SENSOR_COL_WIDTH_A 204 {MT9D111_REG_MICROCONTROLLER_VARIABLE_ADDRESS , 0x2719}, // MODE_SENSOR_ROW_SPEED_A 205 {MT9D111_REG_MICROCONTROLLER_VARIABLE_DATA , 0x0011}, // MODE_SENSOR_ROW_SPEED_A 206 {MT9D111_REG_MICROCONTROLLER_VARIABLE_ADDRESS , 0x2707}, // MODE_OUTPUT_WIDTH_B 207 {MT9D111_REG_MICROCONTROLLER_VARIABLE_DATA , 0x0640}, // MODE_OUTPUT_WIDTH_B 208 {MT9D111_REG_MICROCONTROLLER_VARIABLE_ADDRESS , 0x2709}, // MODE_OUTPUT_HEIGHT_B 209 {MT9D111_REG_MICROCONTROLLER_VARIABLE_DATA , 0x04B0}, // MODE_OUTPUT_HEIGHT_B 210 {MT9D111_REG_MICROCONTROLLER_VARIABLE_ADDRESS , 0x271B}, // MODE_SENSOR_ROW_START_B 211 {MT9D111_REG_MICROCONTROLLER_VARIABLE_DATA , 0x001C}, // MODE_SENSOR_ROW_START_B 212 {MT9D111_REG_MICROCONTROLLER_VARIABLE_ADDRESS , 0x271D}, // MODE_SENSOR_COL_START_B 213 {MT9D111_REG_MICROCONTROLLER_VARIABLE_DATA , 0x003C}, // MODE_SENSOR_COL_START_B 214 {MT9D111_REG_MICROCONTROLLER_VARIABLE_ADDRESS , 0x271F}, // MODE_SENSOR_ROW_HEIGHT_B 215 {MT9D111_REG_MICROCONTROLLER_VARIABLE_DATA , 0x04B0}, // MODE_SENSOR_ROW_HEIGHT_B 216 {MT9D111_REG_MICROCONTROLLER_VARIABLE_ADDRESS , 0x2721}, // MODE_SENSOR_COL_WIDTH_B 217 {MT9D111_REG_MICROCONTROLLER_VARIABLE_DATA , 0x0640}, // MODE_SENSOR_COL_WIDTH_B 218 {MT9D111_REG_MICROCONTROLLER_VARIABLE_ADDRESS , 0x2723}, // MODE_SENSOR_X_DELAY_B 219 {MT9D111_REG_MICROCONTROLLER_VARIABLE_DATA , 0x03B1}, // MODE_SENSOR_X_DELAY_B 220 {MT9D111_REG_MICROCONTROLLER_VARIABLE_ADDRESS , 0x2725}, // MODE_SENSOR_ROW_SPEED_B 221 {MT9D111_REG_MICROCONTROLLER_VARIABLE_DATA , 0x0011}, // MODE_SENSOR_ROW_SPEED_B 222 223 // Maximum Slew-Rate on IO-Pads (for Mode A) 224 {MT9D111_REG_MICROCONTROLLER_VARIABLE_ADDRESS , 0x276B}, // MODE_FIFO_CONF0_A 225 {MT9D111_REG_MICROCONTROLLER_VARIABLE_DATA , 0x0027}, // MODE_FIFO_CONF0_A 226 {MT9D111_REG_MICROCONTROLLER_VARIABLE_ADDRESS , 0x276D}, // MODE_FIFO_CONF1_A 227 {MT9D111_REG_MICROCONTROLLER_VARIABLE_DATA , 0xE0E2}, // MODE_FIFO_CONF1_A 228 {MT9D111_REG_MICROCONTROLLER_VARIABLE_ADDRESS , 0xA76F}, // MODE_FIFO_CONF2_A 229 {MT9D111_REG_MICROCONTROLLER_VARIABLE_DATA , 0x00E1}, // MODE_FIFO_CONF2_A 230 231 // Maximum Slew-Rate on IO-Pads (for Mode B) 232 {MT9D111_REG_MICROCONTROLLER_VARIABLE_ADDRESS , 0x2772}, // MODE_FIFO_CONF0_B 233 {MT9D111_REG_MICROCONTROLLER_VARIABLE_DATA , 0x0027}, // MODE_FIFO_CONF0_B 234 {MT9D111_REG_MICROCONTROLLER_VARIABLE_ADDRESS , 0x2774}, // MODE_FIFO_CONF1_B 235 {MT9D111_REG_MICROCONTROLLER_VARIABLE_DATA , 0xE0E1}, // MODE_FIFO_CONF1_B 236 {MT9D111_REG_MICROCONTROLLER_VARIABLE_ADDRESS , 0xA776}, // MODE_FIFO_CONF2_B 237 {MT9D111_REG_MICROCONTROLLER_VARIABLE_DATA , 0x00E1}, // MODE_FIFO_CONF2_B 238 239 // Set maximum integration time to get a minimum of 15 fps at 45MHz 240 {MT9D111_REG_MICROCONTROLLER_VARIABLE_ADDRESS , 0xA20E}, // AE_MAX_INDEX 241 {MT9D111_REG_MICROCONTROLLER_VARIABLE_DATA , 0x0004}, // AE_MAX_INDEX 242 243 // Set minimum integration time to get a maximum of 15 fps at 45MHz 244 {MT9D111_REG_MICROCONTROLLER_VARIABLE_ADDRESS , 0xA20D}, // AE_MAX_INDEX 245 {MT9D111_REG_MICROCONTROLLER_VARIABLE_DATA , 0x0004}, // AE_MAX_INDEX 246 247 // Configue all GPIO for output and set low to save power 248 {MT9D111_REG_MICROCONTROLLER_VARIABLE_ADDRESS , 0x9078}, 249 {MT9D111_REG_MICROCONTROLLER_VARIABLE_DATA , 0x0000}, 250 {MT9D111_REG_MICROCONTROLLER_VARIABLE_ADDRESS , 0x9079}, 251 {MT9D111_REG_MICROCONTROLLER_VARIABLE_DATA , 0x0000}, 252 {MT9D111_REG_MICROCONTROLLER_VARIABLE_ADDRESS , 0x9070}, 253 {MT9D111_REG_MICROCONTROLLER_VARIABLE_DATA , 0x0000}, 254 {MT9D111_REG_MICROCONTROLLER_VARIABLE_ADDRESS , 0x9071}, 255 {MT9D111_REG_MICROCONTROLLER_VARIABLE_DATA , 0x0000}, 256 257 // Gamma and contrast 258 {MT9D111_REG_MICROCONTROLLER_VARIABLE_ADDRESS , 0xA743}, // MODE_GAM_CONT_A 259 {MT9D111_REG_MICROCONTROLLER_VARIABLE_DATA , 0x0003}, // MODE_GAM_CONT_A 260 {MT9D111_REG_MICROCONTROLLER_VARIABLE_ADDRESS , 0xA744}, // MODE_GAM_CONT_B 261 {MT9D111_REG_MICROCONTROLLER_VARIABLE_DATA , 0x0003}, // MODE_GAM_CONT_B 262 263 // Set PLL (MCLK = 19 MHz , PCLK = 79 MHz) 264 // Set PLL (MCLK = 45 MHz , PCLK = 45 MHz) -> From Wizard 265 {MT9D111_REG_PAGE_REGISTER , MT9D111_REG_PAGE_0}, 266 {MT9D111_REG_CONTEXT_CONTROL , 0x0000}, 267 268 {MT9D111_REG_PAGE_REGISTER , MT9D111_REG_PAGE_0}, 269 270 {MT9D111_REG_PAGE_REGISTER , MT9D111_REG_PAGE_1}, 271 {MT9D111_REG_MICROCONTROLLER_VARIABLE_ADDRESS , 0x2735}, // MODE_CROP_X0_A 272 {MT9D111_REG_MICROCONTROLLER_VARIABLE_DATA , 0x0000}, // MODE_CROP_X0_A 273 {MT9D111_REG_MICROCONTROLLER_VARIABLE_ADDRESS , 0x2737}, // MODE_CROP_X1_A 274 {MT9D111_REG_MICROCONTROLLER_VARIABLE_DATA , 1600}, // MODE_CROP_X1_A 275 {MT9D111_REG_MICROCONTROLLER_VARIABLE_ADDRESS , 0x2739}, // MODE_CROP_Y0_A 276 {MT9D111_REG_MICROCONTROLLER_VARIABLE_DATA , 0x0000}, // MODE_CROP_Y0_A 277 {MT9D111_REG_MICROCONTROLLER_VARIABLE_ADDRESS , 0x273B}, // MODE_CROP_Y1_A 278 {MT9D111_REG_MICROCONTROLLER_VARIABLE_DATA , 1200}, // MODE_CROP_Y1_A 279 {MT9D111_REG_MICROCONTROLLER_VARIABLE_ADDRESS , 0xA103}, // SEQ_CMD, Do capture 280 {MT9D111_REG_MICROCONTROLLER_VARIABLE_DATA , 0x0005}, 281 282 {MT9D111_REG_PAGE_REGISTER , MT9D111_REG_PAGE_0}, 283 }; 284 285 static int mt9d111_read_reg(sensor_t *sensor, uint8_t reg_addr) 286 { 287 printk("%s sensor %p\r\n", __func__, sensor); 288 return 0; 289 } 290 291 static int mt9d111_write_reg(sensor_t *sensor, uint8_t reg_addr, uint16_t reg_data) 292 { 293 printk("%s sensor %p\r\n", __func__, sensor); 294 return 0; 295 } 296 297 static int mt9d111_set_pixformat(sensor_t *sensor, pixformat_t pixformat) 298 { 299 printk("%s sensor %p\r\n", __func__, sensor); 300 return 0; 301 } 302 303 static int mt9d111_set_framesize(sensor_t *sensor, framesize_t framesize) 304 { 305 printk("%s sensor %p framesize %d\r\n", __func__, sensor, framesize); 306 uint16_t width = resolution[framesize][0]; 307 uint16_t height = resolution[framesize][1]; 308 309 // if (framesize == FRAMESIZE_QQVGA) 310 311 // this->SetResolution(MT9D111_MODE_CAPTURE, width, height); 312 313 /* delay n ms */ 314 mp_hal_delay_ms(100); 315 dvp_set_image_size(width, height); 316 return 0; 317 } 318 319 static int mt9d111_set_framerate(sensor_t *sensor, framerate_t framerate) 320 { 321 printk("%s %s %d\r\n", __func__, __FILE__, __LINE__); 322 return 0; 323 } 324 325 static int mt9d111_set_contrast(sensor_t *sensor, int level) 326 { 327 printk("%s %s %d\r\n", __func__, __FILE__, __LINE__); 328 return 0; 329 } 330 331 static int mt9d111_set_brightness(sensor_t *sensor, int level) 332 { 333 printk("%s %s %d\r\n", __func__, __FILE__, __LINE__); 334 return 0; 335 } 336 337 static int mt9d111_set_saturation(sensor_t *sensor, int level) 338 { 339 printk("%s %s %d\r\n", __func__, __FILE__, __LINE__); 340 return 0; 341 } 342 343 static int mt9d111_set_gainceiling(sensor_t *sensor, gainceiling_t gainceiling) 344 { 345 printk("%s %s %d\r\n", __func__, __FILE__, __LINE__); 346 return 0; 347 } 348 349 static int mt9d111_set_quality(sensor_t *sensor, int qs) 350 { 351 printk("%s %s %d\r\n", __func__, __FILE__, __LINE__); 352 return 0; 353 } 354 355 static int mt9d111_set_colorbar(sensor_t *sensor, int enable) 356 { 357 printk("%s %s %d\r\n", __func__, __FILE__, __LINE__); 358 return 0; 359 } 360 361 static int mt9d111_set_auto_gain(sensor_t *sensor, int enable, float gain_db, float gain_db_ceiling) 362 { 363 printk("%s %s %d\r\n", __func__, __FILE__, __LINE__); 364 return 0; 365 } 366 367 static int mt9d111_get_gain_db(sensor_t *sensor, float *gain_db) 368 { 369 printk("%s %s %d\r\n", __func__, __FILE__, __LINE__); 370 return 0; 371 } 372 373 static int mt9d111_set_auto_exposure(sensor_t *sensor, int enable, int exposure_us) 374 { 375 printk("%s %s %d\r\n", __func__, __FILE__, __LINE__); 376 return 0; 377 } 378 379 static int mt9d111_get_exposure_us(sensor_t *sensor, int *exposure_us) 380 { 381 printk("%s %s %d\r\n", __func__, __FILE__, __LINE__); 382 return 0; 383 } 384 385 static int mt9d111_set_auto_whitebal(sensor_t *sensor, int enable, float r_gain_db, float g_gain_db, float b_gain_db) 386 { 387 printk("%s %s %d\r\n", __func__, __FILE__, __LINE__); 388 return 0; 389 } 390 391 static int mt9d111_get_rgb_gain_db(sensor_t *sensor, float *r_gain_db, float *g_gain_db, float *b_gain_db) 392 { 393 printk("%s %s %d\r\n", __func__, __FILE__, __LINE__); 394 return 0; 395 } 396 397 static int mt9d111_set_hmirror(sensor_t *sensor, int enable) 398 { 399 printk("%s %s %d\r\n", __func__, __FILE__, __LINE__); 400 return 0; 401 } 402 403 static int mt9d111_set_vflip(sensor_t *sensor, int enable) 404 { 405 printk("%s %s %d\r\n", __func__, __FILE__, __LINE__); 406 return 0; 407 } 408 409 static int mt9d11_write(i2c_device_number_t i2c_dev_tmp, uint8_t reg, uint16_t val) 410 { 411 uint8_t tmp[3] = { 0 }; 412 tmp[0] = (uint8_t)(reg & 0xff); 413 tmp[1] = (uint8_t)((val >> 8) & 0xff); 414 tmp[2] = (uint8_t)(val & 0xff); 415 int ret = maix_i2c_send_data(i2c_dev_tmp, MT9D111_CONFIG_I2C_ID, tmp, 3, 20); 416 msleep(20); 417 return ret; 418 } 419 420 static uint16_t mt9d11_read(i2c_device_number_t i2c_dev_tmp, uint8_t reg) 421 { 422 uint8_t buf[2] = { 0 }; 423 maix_i2c_send_data(i2c_dev_tmp, MT9D111_CONFIG_I2C_ID, reg, 1, 20); 424 int ret = maix_i2c_recv_data(i2c_dev_tmp, MT9D111_CONFIG_I2C_ID, NULL, 0, buf, 2, 30); 425 msleep(20); 426 if (ret == 0) 427 { 428 return (buf[0] << 8) + buf[1]; 429 } 430 return -1; 431 } 432 433 uint16_t mt9d111_read_id(i2c_device_number_t extern_i2c_dev_tmp) 434 { 435 i2c_dev_tmp = extern_i2c_dev_tmp; // TODO remove after implementation cambus_readw and cambus_writew 436 // return 0x1519; 437 mt9d11_write(i2c_dev_tmp, MT9D111_REG_PAGE_REGISTER, MT9D111_REG_PAGE_0); 438 uint16_t id = mt9d11_read(i2c_dev_tmp, MT9D111_REG_RESERVED); 439 // printk("[mt9d11] Sensor ID:0x%x,req:0x1519\r\n", id); 440 return id; 441 } 442 443 static int mt9d111_reset(sensor_t *sensor) 444 { 445 for (uint8_t i = 0; i < (sizeof(reg_vals_qvga_30fps) / sizeof(struct Register)); i++) 446 { 447 mt9d11_write(i2c_dev_tmp, reg_vals_qvga_30fps[i].address, reg_vals_qvga_30fps[i].value); 448 } 449 return 0; 450 } 451 452 int mt9d111_init(sensor_t *sensor) 453 { 454 //Initialize sensor structure. 455 sensor->gs_bpp = 2; 456 sensor->reset = mt9d111_reset; 457 sensor->read_reg = mt9d111_read_reg; 458 sensor->write_reg = mt9d111_write_reg; 459 sensor->set_pixformat = mt9d111_set_pixformat; 460 sensor->set_framesize = mt9d111_set_framesize; 461 sensor->set_framerate = mt9d111_set_framerate; 462 sensor->set_contrast = mt9d111_set_contrast; 463 sensor->set_brightness = mt9d111_set_brightness; 464 sensor->set_saturation = mt9d111_set_saturation; 465 sensor->set_gainceiling = mt9d111_set_gainceiling; 466 sensor->set_quality = mt9d111_set_quality; 467 sensor->set_colorbar = mt9d111_set_colorbar; 468 sensor->set_auto_gain = mt9d111_set_auto_gain; 469 sensor->get_gain_db = mt9d111_get_gain_db; 470 sensor->set_auto_exposure = mt9d111_set_auto_exposure; 471 sensor->get_exposure_us = mt9d111_get_exposure_us; 472 sensor->set_auto_whitebal = mt9d111_set_auto_whitebal; 473 sensor->get_rgb_gain_db = mt9d111_get_rgb_gain_db; 474 sensor->set_hmirror = mt9d111_set_hmirror; 475 sensor->set_vflip = mt9d111_set_vflip; 476 477 // Set sensor flags 478 SENSOR_HW_FLAGS_SET(sensor, SENSOR_HW_FLAGS_VSYNC, 0); 479 SENSOR_HW_FLAGS_SET(sensor, SENSOR_HW_FLAGS_HSYNC, 0); 480 SENSOR_HW_FLAGS_SET(sensor, SENSOR_HW_FLAGS_PIXCK, 1); 481 SENSOR_HW_FLAGS_SET(sensor, SENSOR_HW_FLAGS_FSYNC, 0); 482 SENSOR_HW_FLAGS_SET(sensor, SENSOR_HW_FLAGS_JPEGE, 1); 483 484 return 0; 485 }