@@ -192,6 +192,7 @@ enum ds5_mux_pad {
192192#define DS5_START_POLL_TIME 10
193193#define DS5_START_MAX_TIME 2000
194194#define DS5_START_MAX_COUNT (DS5_START_MAX_TIME / DS5_START_POLL_TIME)
195+ #define MAX_DS5_CONFIG_RETRIES 5
195196
196197/* I2C retry configuration */
197198#define DS5_I2C_RETRY_COUNT 5
@@ -1807,19 +1808,16 @@ static int ds5_configure(struct ds5 *state)
18071808
18081809 fmt = sensor -> streaming ? sensor -> config .format -> data_type : 0 ;
18091810
1810- /*
1811- * Set depth stream Z16 data type as 0x31
1812- * Set IR stream Y8I data type as 0x32
1811+ /* Determine desired data-type (special cases for depth/IR), then write
1812+ * it only when it differs from cached value. This avoids overwriting a
1813+ * correct DT with 0 (which caused INVALID_DT on subsequent attempts).
18131814 */
1815+ dt_value = fmt ;
18141816 if (state -> is_depth && fmt != 0 )
18151817 dt_value = 0x31 ;
18161818 else if (state -> is_y8 && fmt != 0 &&
18171819 sensor -> config .format -> data_type == GMSL_CSI_DT_YUV422_8 )
1818- ret = ds5_write (state , dt_addr , 0x32 );
1819- else
1820- ret = ds5_write (state , dt_addr , fmt );
1821- if (ret < 0 )
1822- return ret ;
1820+ dt_value = 0x32 ;
18231821
18241822 if (sensor -> cached_dt_value != dt_value ) {
18251823 ret = ds5_write (state , dt_addr , dt_value );
@@ -4455,14 +4453,14 @@ static int ds5_mux_s_stream(struct v4l2_subdev *sd, int on)
44554453 struct ds5 * state = container_of (sd , struct ds5 , mux .sd .subdev );
44564454 u16 streaming , status ;
44574455 int ret = 0 ;
4458- unsigned int i = 0 ;
4456+ unsigned int i = 0 , ds5_config_retries = MAX_DS5_CONFIG_RETRIES ;
44594457 unsigned long timeout , ts ;
44604458 int restore_val = 0 ;
44614459 u16 stream_cmd ;
44624460 u16 config_status_base , stream_status_base , stream_id , vc_id ;
44634461 struct ds5_sensor * sensor = state -> mux .last_set ;
44644462 u16 expected_streaming_state ;
4465- bool ds5_config_done = !on ;
4463+ bool ds5_config_done = !on ; /* for stop, skip config */
44664464
44674465 // spare duplicate calls
44684466 if (sensor -> streaming == on )
@@ -4580,8 +4578,15 @@ static int ds5_mux_s_stream(struct v4l2_subdev *sd, int on)
45804578 {
45814579 dev_warn (& state -> client -> dev ,
45824580 "stream %d config rejected, status 0x%04x, retry %u\n" , stream_id , status , i );
4583- ds5_config_done = false;
4584- ds5_config_cache_clear (sensor );
4581+ if (ds5_config_retries > 0 ) {
4582+ ds5_config_retries -- ;
4583+ ds5_config_done = false;
4584+ ds5_config_cache_clear (sensor );
4585+ } else {
4586+ dev_warn (& state -> client -> dev ,
4587+ "stream %d config failed after %d retries, aborting\n" , stream_id , i );
4588+ break ;
4589+ }
45854590 continue ;
45864591 }
45874592
@@ -4603,32 +4608,37 @@ static int ds5_mux_s_stream(struct v4l2_subdev *sd, int on)
46034608 ds5_write (state , DS5_START_STOP_STREAM ,
46044609 (on ? DS5_STREAM_STOP : DS5_STREAM_START ) | stream_id );
46054610 }
4606- ret = - EAGAIN ;
4607- #ifdef CONFIG_VIDEO_D4XX_SERDES
4611+ #ifdef CONFIG_VIDEO_D4XX_SERDES
46084612 if (on && sensor -> pipe_id >= 0 ) {
46094613 mutex_lock (& serdes_lock__ );
4610- if (state -> dser_ops -> release_pipe (state -> dser_dev , sensor -> pipe_id ) < 0 )
4611- dev_warn (& state -> client -> dev , "release pipe failed\n" );
4612- sensor -> pipe_id = PIPE_NOT_CONFIGURED ;
4614+ ret = state -> dser_ops -> release_pipe (state -> dser_dev , sensor -> pipe_id );
46134615 mutex_unlock (& serdes_lock__ );
4616+ if (ret < 0 ) {
4617+ dev_warn (& state -> client -> dev , "release pipe failed\n" );
4618+ } else {
4619+ sensor -> pipe_id = PIPE_NOT_CONFIGURED ;
4620+ }
46144621 }
4615- #endif
4622+ #endif
46164623 sensor -> streaming = restore_val ;
4624+ ret = - EAGAIN ;
46174625 }
46184626 else if (!on )
46194627 {
4628+ #ifdef CONFIG_VIDEO_D4XX_SERDES
46204629 mutex_lock (& serdes_lock__ );
46214630 if (state -> dser_ops -> release_pipe (state -> dser_dev , sensor -> pipe_id ) < 0 )
46224631 dev_warn (& state -> client -> dev , "release pipe failed\n" );
46234632 else
46244633 sensor -> pipe_id = PIPE_NOT_CONFIGURED ;
4625- if (state -> is_y8 &&
4626- state -> ir .sensor .config .format -> data_type ==
4627- GMSL_CSI_DT_RGB_888 ) {
4634+ if (state -> is_y8
4635+ && ( state -> ir .sensor .config .format -> data_type == GMSL_CSI_DT_RGB_888 ))
4636+ {
46284637 state -> dser_ops -> reset_oneshot (state -> dser_dev );
46294638 }
46304639 mutex_unlock (& serdes_lock__ );
46314640 msleep_range (100 );
4641+ #endif
46324642 }
46334643 return ret ;
46344644}
0 commit comments