@@ -345,6 +345,9 @@ struct ov2740 {
345345
346346 /* NVM data inforamtion */
347347 struct nvm_data * nvm ;
348+
349+ /* True if the device has been identified */
350+ bool identified ;
348351};
349352
350353static inline struct ov2740 * to_ov2740 (struct v4l2_subdev * subdev )
@@ -440,6 +443,30 @@ static int ov2740_write_reg_list(struct ov2740 *ov2740,
440443 return 0 ;
441444}
442445
446+ static int ov2740_identify_module (struct ov2740 * ov2740 )
447+ {
448+ struct i2c_client * client = v4l2_get_subdevdata (& ov2740 -> sd );
449+ int ret ;
450+ u32 val ;
451+
452+ if (ov2740 -> identified )
453+ return 0 ;
454+
455+ ret = ov2740_read_reg (ov2740 , OV2740_REG_CHIP_ID , 3 , & val );
456+ if (ret )
457+ return ret ;
458+
459+ if (val != OV2740_CHIP_ID ) {
460+ dev_err (& client -> dev , "chip id mismatch: %x!=%x" ,
461+ OV2740_CHIP_ID , val );
462+ return - ENXIO ;
463+ }
464+
465+ ov2740 -> identified = true;
466+
467+ return 0 ;
468+ }
469+
443470static int ov2740_update_digital_gain (struct ov2740 * ov2740 , u32 d_gain )
444471{
445472 int ret = 0 ;
@@ -724,6 +751,10 @@ static int ov2740_start_streaming(struct ov2740 *ov2740)
724751 int link_freq_index ;
725752 int ret = 0 ;
726753
754+ ret = ov2740_identify_module (ov2740 );
755+ if (ret )
756+ return ret ;
757+
727758 ov2740_load_otp_data (nvm );
728759
729760 link_freq_index = ov2740 -> cur_mode -> link_freq_index ;
@@ -956,25 +987,6 @@ static const struct v4l2_subdev_internal_ops ov2740_internal_ops = {
956987 .open = ov2740_open ,
957988};
958989
959- static int ov2740_identify_module (struct ov2740 * ov2740 )
960- {
961- struct i2c_client * client = v4l2_get_subdevdata (& ov2740 -> sd );
962- int ret ;
963- u32 val ;
964-
965- ret = ov2740_read_reg (ov2740 , OV2740_REG_CHIP_ID , 3 , & val );
966- if (ret )
967- return ret ;
968-
969- if (val != OV2740_CHIP_ID ) {
970- dev_err (& client -> dev , "chip id mismatch: %x!=%x" ,
971- OV2740_CHIP_ID , val );
972- return - ENXIO ;
973- }
974-
975- return 0 ;
976- }
977-
978990static int ov2740_check_hwcfg (struct device * dev )
979991{
980992 struct fwnode_handle * ep ;
@@ -1137,6 +1149,7 @@ static int ov2740_probe(struct i2c_client *client)
11371149{
11381150 struct ov2740 * ov2740 ;
11391151 int ret = 0 ;
1152+ bool full_power ;
11401153
11411154 ret = ov2740_check_hwcfg (& client -> dev );
11421155 if (ret ) {
@@ -1149,6 +1162,15 @@ static int ov2740_probe(struct i2c_client *client)
11491162 if (!ov2740 )
11501163 return - ENOMEM ;
11511164
1165+ full_power = acpi_dev_state_d0 (& client -> dev );
1166+ if (full_power ) {
1167+ ret = ov2740_identify_module (ov2740 );
1168+ if (ret ) {
1169+ dev_err (& client -> dev , "failed to find sensor: %d" , ret );
1170+ return ret ;
1171+ }
1172+ }
1173+
11521174 v4l2_i2c_subdev_init (& ov2740 -> sd , client , & ov2740_subdev_ops );
11531175 ret = ov2740_identify_module (ov2740 );
11541176 if (ret ) {
@@ -1186,11 +1208,9 @@ static int ov2740_probe(struct i2c_client *client)
11861208 if (ret )
11871209 dev_warn (& client -> dev , "register nvmem failed, ret %d\n" , ret );
11881210
1189- /*
1190- * Device is already turned on by i2c-core with ACPI domain PM.
1191- * Enable runtime PM and turn off the device.
1192- */
1193- pm_runtime_set_active (& client -> dev );
1211+ /* Set the device's state to active if it's in D0 state. */
1212+ if (full_power )
1213+ pm_runtime_set_active (& client -> dev );
11941214 pm_runtime_enable (& client -> dev );
11951215 pm_runtime_idle (& client -> dev );
11961216
@@ -1225,6 +1245,7 @@ static struct i2c_driver ov2740_i2c_driver = {
12251245 },
12261246 .probe_new = ov2740_probe ,
12271247 .remove = ov2740_remove ,
1248+ .flags = I2C_DRV_ACPI_WAIVE_D0_PROBE ,
12281249};
12291250
12301251module_i2c_driver (ov2740_i2c_driver );
0 commit comments