@@ -55,8 +55,7 @@ void ucsi_notify_common(struct ucsi *ucsi, u32 cci)
5555}
5656EXPORT_SYMBOL_GPL (ucsi_notify_common );
5757
58- int ucsi_sync_control_common (struct ucsi * ucsi , u64 command , u32 * cci ,
59- void * data , size_t size )
58+ int ucsi_sync_control_common (struct ucsi * ucsi , u64 command , u32 * cci )
6059{
6160 bool ack = UCSI_COMMAND (command ) == UCSI_ACK_CC_CI ;
6261 int ret ;
@@ -84,9 +83,10 @@ int ucsi_sync_control_common(struct ucsi *ucsi, u64 command, u32 *cci,
8483 if (!ret && cci )
8584 ret = ucsi -> ops -> read_cci (ucsi , cci );
8685
87- if (!ret && data &&
86+ if (!ret && ucsi -> message_in_size > 0 &&
8887 (* cci & UCSI_CCI_COMMAND_COMPLETE ))
89- ret = ucsi -> ops -> read_message_in (ucsi , data , size );
88+ ret = ucsi -> ops -> read_message_in (ucsi , ucsi -> message_in ,
89+ ucsi -> message_in_size );
9090
9191 return ret ;
9292}
@@ -103,23 +103,25 @@ static int ucsi_acknowledge(struct ucsi *ucsi, bool conn_ack)
103103 ctrl |= UCSI_ACK_CONNECTOR_CHANGE ;
104104 }
105105
106- return ucsi -> ops -> sync_control (ucsi , ctrl , NULL , NULL , 0 );
106+ ucsi -> message_in_size = 0 ;
107+ return ucsi -> ops -> sync_control (ucsi , ctrl , NULL );
107108}
108109
109- static int ucsi_run_command (struct ucsi * ucsi , u64 command , u32 * cci ,
110- void * data , size_t size , bool conn_ack )
110+ static int ucsi_run_command (struct ucsi * ucsi , u64 command , u32 * cci , bool conn_ack )
111111{
112112 int ret , err ;
113113
114114 * cci = 0 ;
115115
116- if (size > UCSI_MAX_DATA_LENGTH (ucsi ))
116+ if (ucsi -> message_in_size > UCSI_MAX_DATA_LENGTH (ucsi ))
117117 return - EINVAL ;
118118
119- ret = ucsi -> ops -> sync_control (ucsi , command , cci , data , size );
119+ ret = ucsi -> ops -> sync_control (ucsi , command , cci );
120120
121- if (* cci & UCSI_CCI_BUSY )
122- return ucsi_run_command (ucsi , UCSI_CANCEL , cci , NULL , 0 , false) ?: - EBUSY ;
121+ if (* cci & UCSI_CCI_BUSY ) {
122+ ucsi -> message_in_size = 0 ;
123+ return ucsi_run_command (ucsi , UCSI_CANCEL , cci , false) ?: - EBUSY ;
124+ }
123125 if (ret )
124126 return ret ;
125127
@@ -151,10 +153,13 @@ static int ucsi_read_error(struct ucsi *ucsi, u8 connector_num)
151153 int ret ;
152154
153155 command = UCSI_GET_ERROR_STATUS | UCSI_CONNECTOR_NUMBER (connector_num );
154- ret = ucsi_run_command (ucsi , command , & cci , & error , sizeof (error ), false);
156+ ucsi -> message_in_size = sizeof (error );
157+ ret = ucsi_run_command (ucsi , command , & cci , false);
155158 if (ret < 0 )
156159 return ret ;
157160
161+ memcpy (& error , ucsi -> message_in , sizeof (error ));
162+
158163 switch (error ) {
159164 case UCSI_ERROR_INCOMPATIBLE_PARTNER :
160165 return - EOPNOTSUPP ;
@@ -200,8 +205,7 @@ static int ucsi_read_error(struct ucsi *ucsi, u8 connector_num)
200205 return - EIO ;
201206}
202207
203- static int ucsi_send_command_common (struct ucsi * ucsi , u64 cmd ,
204- void * data , size_t size , bool conn_ack )
208+ static int ucsi_send_command_common (struct ucsi * ucsi , u64 cmd , bool conn_ack )
205209{
206210 u8 connector_num ;
207211 u32 cci ;
@@ -229,7 +233,7 @@ static int ucsi_send_command_common(struct ucsi *ucsi, u64 cmd,
229233
230234 mutex_lock (& ucsi -> ppm_lock );
231235
232- ret = ucsi_run_command (ucsi , cmd , & cci , data , size , conn_ack );
236+ ret = ucsi_run_command (ucsi , cmd , & cci , conn_ack );
233237
234238 if (cci & UCSI_CCI_ERROR )
235239 ret = ucsi_read_error (ucsi , connector_num );
@@ -238,10 +242,9 @@ static int ucsi_send_command_common(struct ucsi *ucsi, u64 cmd,
238242 return ret ;
239243}
240244
241- int ucsi_send_command (struct ucsi * ucsi , u64 command ,
242- void * data , size_t size )
245+ int ucsi_send_command (struct ucsi * ucsi , u64 command )
243246{
244- return ucsi_send_command_common (ucsi , command , data , size , false);
247+ return ucsi_send_command_common (ucsi , command , false);
245248}
246249EXPORT_SYMBOL_GPL (ucsi_send_command );
247250
@@ -319,14 +322,17 @@ void ucsi_altmode_update_active(struct ucsi_connector *con)
319322 int i ;
320323
321324 command = UCSI_GET_CURRENT_CAM | UCSI_CONNECTOR_NUMBER (con -> num );
322- ret = ucsi_send_command (con -> ucsi , command , & cur , sizeof (cur ));
325+ con -> ucsi -> message_in_size = sizeof (cur );
326+ ret = ucsi_send_command (con -> ucsi , command );
323327 if (ret < 0 ) {
324328 if (con -> ucsi -> version > 0x0100 ) {
325329 dev_err (con -> ucsi -> dev ,
326330 "GET_CURRENT_CAM command failed\n" );
327331 return ;
328332 }
329333 cur = 0xff ;
334+ } else {
335+ memcpy (& cur , con -> ucsi -> message_in , sizeof (cur ));
330336 }
331337
332338 if (cur < UCSI_MAX_ALTMODES )
@@ -510,7 +516,8 @@ ucsi_register_altmodes_nvidia(struct ucsi_connector *con, u8 recipient)
510516 command |= UCSI_GET_ALTMODE_RECIPIENT (recipient );
511517 command |= UCSI_GET_ALTMODE_CONNECTOR_NUMBER (con -> num );
512518 command |= UCSI_GET_ALTMODE_OFFSET (i );
513- len = ucsi_send_command (con -> ucsi , command , & alt , sizeof (alt ));
519+ ucsi -> message_in_size = sizeof (alt );
520+ len = ucsi_send_command (con -> ucsi , command );
514521 /*
515522 * We are collecting all altmodes first and then registering.
516523 * Some type-C device will return zero length data beyond last
@@ -519,6 +526,8 @@ ucsi_register_altmodes_nvidia(struct ucsi_connector *con, u8 recipient)
519526 if (len < 0 )
520527 return len ;
521528
529+ memcpy (& alt , ucsi -> message_in , sizeof (alt ));
530+
522531 /* We got all altmodes, now break out and register them */
523532 if (!len || !alt .svid )
524533 break ;
@@ -586,12 +595,15 @@ static int ucsi_register_altmodes(struct ucsi_connector *con, u8 recipient)
586595 command |= UCSI_GET_ALTMODE_RECIPIENT (recipient );
587596 command |= UCSI_GET_ALTMODE_CONNECTOR_NUMBER (con -> num );
588597 command |= UCSI_GET_ALTMODE_OFFSET (i );
589- len = ucsi_send_command (con -> ucsi , command , alt , sizeof (alt ));
598+ con -> ucsi -> message_in_size = sizeof (alt );
599+ len = ucsi_send_command (con -> ucsi , command );
590600 if (len == - EBUSY )
591601 continue ;
592602 if (len <= 0 )
593603 return len ;
594604
605+ memcpy (& alt , con -> ucsi -> message_in , sizeof (alt ));
606+
595607 /*
596608 * This code is requesting one alt mode at a time, but some PPMs
597609 * may still return two. If that happens both alt modes need be
@@ -659,7 +671,9 @@ static int ucsi_get_connector_status(struct ucsi_connector *con, bool conn_ack)
659671 UCSI_MAX_DATA_LENGTH (con -> ucsi ));
660672 int ret ;
661673
662- ret = ucsi_send_command_common (con -> ucsi , command , & con -> status , size , conn_ack );
674+ con -> ucsi -> message_in_size = size ;
675+ ret = ucsi_send_command_common (con -> ucsi , command , conn_ack );
676+ memcpy (& con -> status , con -> ucsi -> message_in , size );
663677
664678 return ret < 0 ? ret : 0 ;
665679}
@@ -682,8 +696,9 @@ static int ucsi_read_pdos(struct ucsi_connector *con,
682696 command |= UCSI_GET_PDOS_PDO_OFFSET (offset );
683697 command |= UCSI_GET_PDOS_NUM_PDOS (num_pdos - 1 );
684698 command |= is_source (role ) ? UCSI_GET_PDOS_SRC_PDOS : 0 ;
685- ret = ucsi_send_command (ucsi , command , pdos + offset ,
686- num_pdos * sizeof (u32 ));
699+ ucsi -> message_in_size = num_pdos * sizeof (u32 );
700+ ret = ucsi_send_command (ucsi , command );
701+ memcpy (pdos + offset , ucsi -> message_in , num_pdos * sizeof (u32 ));
687702 if (ret < 0 && ret != - ETIMEDOUT )
688703 dev_err (ucsi -> dev , "UCSI_GET_PDOS failed (%d)\n" , ret );
689704
@@ -770,7 +785,9 @@ static int ucsi_get_pd_message(struct ucsi_connector *con, u8 recipient,
770785 command |= UCSI_GET_PD_MESSAGE_BYTES (len );
771786 command |= UCSI_GET_PD_MESSAGE_TYPE (type );
772787
773- ret = ucsi_send_command (con -> ucsi , command , data + offset , len );
788+ con -> ucsi -> message_in_size = len ;
789+ ret = ucsi_send_command (con -> ucsi , command );
790+ memcpy (data + offset , con -> ucsi -> message_in , len );
774791 if (ret < 0 )
775792 return ret ;
776793 }
@@ -935,7 +952,9 @@ static int ucsi_register_cable(struct ucsi_connector *con)
935952 int ret ;
936953
937954 command = UCSI_GET_CABLE_PROPERTY | UCSI_CONNECTOR_NUMBER (con -> num );
938- ret = ucsi_send_command (con -> ucsi , command , & cable_prop , sizeof (cable_prop ));
955+ con -> ucsi -> message_in_size = sizeof (cable_prop );
956+ ret = ucsi_send_command (con -> ucsi , command );
957+ memcpy (& cable_prop , con -> ucsi -> message_in , sizeof (cable_prop ));
939958 if (ret < 0 ) {
940959 dev_err (con -> ucsi -> dev , "GET_CABLE_PROPERTY failed (%d)\n" , ret );
941960 return ret ;
@@ -996,7 +1015,9 @@ static int ucsi_check_connector_capability(struct ucsi_connector *con)
9961015 return 0 ;
9971016
9981017 command = UCSI_GET_CONNECTOR_CAPABILITY | UCSI_CONNECTOR_NUMBER (con -> num );
999- ret = ucsi_send_command (con -> ucsi , command , & con -> cap , sizeof (con -> cap ));
1018+ con -> ucsi -> message_in_size = sizeof (con -> cap );
1019+ ret = ucsi_send_command (con -> ucsi , command );
1020+ memcpy (& con -> cap , con -> ucsi -> message_in , sizeof (con -> cap ));
10001021 if (ret < 0 ) {
10011022 dev_err (con -> ucsi -> dev , "GET_CONNECTOR_CAPABILITY failed (%d)\n" , ret );
10021023 return ret ;
@@ -1380,7 +1401,8 @@ static int ucsi_reset_connector(struct ucsi_connector *con, bool hard)
13801401 else if (con -> ucsi -> version >= UCSI_VERSION_2_0 )
13811402 command |= hard ? 0 : UCSI_CONNECTOR_RESET_DATA_VER_2_0 ;
13821403
1383- return ucsi_send_command (con -> ucsi , command , NULL , 0 );
1404+ con -> ucsi -> message_in_size = 0 ;
1405+ return ucsi_send_command (con -> ucsi , command );
13841406}
13851407
13861408static int ucsi_reset_ppm (struct ucsi * ucsi )
@@ -1461,15 +1483,17 @@ static int ucsi_role_cmd(struct ucsi_connector *con, u64 command)
14611483{
14621484 int ret ;
14631485
1464- ret = ucsi_send_command (con -> ucsi , command , NULL , 0 );
1486+ con -> ucsi -> message_in_size = 0 ;
1487+ ret = ucsi_send_command (con -> ucsi , command );
14651488 if (ret == - ETIMEDOUT ) {
14661489 u64 c ;
14671490
14681491 /* PPM most likely stopped responding. Resetting everything. */
14691492 ucsi_reset_ppm (con -> ucsi );
14701493
14711494 c = UCSI_SET_NOTIFICATION_ENABLE | con -> ucsi -> ntfy ;
1472- ucsi_send_command (con -> ucsi , c , NULL , 0 );
1495+ con -> ucsi -> message_in_size = 0 ;
1496+ ucsi_send_command (con -> ucsi , c );
14731497
14741498 ucsi_reset_connector (con , true);
14751499 }
@@ -1622,10 +1646,13 @@ static int ucsi_register_port(struct ucsi *ucsi, struct ucsi_connector *con)
16221646 /* Get connector capability */
16231647 command = UCSI_GET_CONNECTOR_CAPABILITY ;
16241648 command |= UCSI_CONNECTOR_NUMBER (con -> num );
1625- ret = ucsi_send_command (ucsi , command , & con -> cap , sizeof (con -> cap ));
1649+ ucsi -> message_in_size = sizeof (con -> cap );
1650+ ret = ucsi_send_command (ucsi , command );
16261651 if (ret < 0 )
16271652 goto out_unlock ;
16281653
1654+ memcpy (& con -> cap , ucsi -> message_in , sizeof (con -> cap ));
1655+
16291656 if (UCSI_CONCAP (con , OPMODE_DRP ))
16301657 cap -> data = TYPEC_PORT_DRD ;
16311658 else if (UCSI_CONCAP (con , OPMODE_DFP ))
@@ -1822,17 +1849,20 @@ static int ucsi_init(struct ucsi *ucsi)
18221849 /* Enable basic notifications */
18231850 ntfy = UCSI_ENABLE_NTFY_CMD_COMPLETE | UCSI_ENABLE_NTFY_ERROR ;
18241851 command = UCSI_SET_NOTIFICATION_ENABLE | ntfy ;
1825- ret = ucsi_send_command (ucsi , command , NULL , 0 );
1852+ ucsi -> message_in_size = 0 ;
1853+ ret = ucsi_send_command (ucsi , command );
18261854 if (ret < 0 )
18271855 goto err_reset ;
18281856
18291857 /* Get PPM capabilities */
18301858 command = UCSI_GET_CAPABILITY ;
1831- ret = ucsi_send_command ( ucsi , command , & ucsi -> cap ,
1832- BITS_TO_BYTES ( UCSI_GET_CAPABILITY_SIZE ) );
1859+ ucsi -> message_in_size = BITS_TO_BYTES ( UCSI_GET_CAPABILITY_SIZE );
1860+ ret = ucsi_send_command ( ucsi , command );
18331861 if (ret < 0 )
18341862 goto err_reset ;
18351863
1864+ memcpy (& ucsi -> cap , ucsi -> message_in , BITS_TO_BYTES (UCSI_GET_CAPABILITY_SIZE ));
1865+
18361866 if (!ucsi -> cap .num_connectors ) {
18371867 ret = - ENODEV ;
18381868 goto err_reset ;
@@ -1862,7 +1892,8 @@ static int ucsi_init(struct ucsi *ucsi)
18621892 /* Enable all supported notifications */
18631893 ntfy = ucsi_get_supported_notifications (ucsi );
18641894 command = UCSI_SET_NOTIFICATION_ENABLE | ntfy ;
1865- ret = ucsi_send_command (ucsi , command , NULL , 0 );
1895+ ucsi -> message_in_size = 0 ;
1896+ ret = ucsi_send_command (ucsi , command );
18661897 if (ret < 0 )
18671898 goto err_unregister ;
18681899
@@ -1913,7 +1944,8 @@ static void ucsi_resume_work(struct work_struct *work)
19131944
19141945 /* Restore UCSI notification enable mask after system resume */
19151946 command = UCSI_SET_NOTIFICATION_ENABLE | ucsi -> ntfy ;
1916- ret = ucsi_send_command (ucsi , command , NULL , 0 );
1947+ ucsi -> message_in_size = 0 ;
1948+ ret = ucsi_send_command (ucsi , command );
19171949 if (ret < 0 ) {
19181950 dev_err (ucsi -> dev , "failed to re-enable notifications (%d)\n" , ret );
19191951 return ;
0 commit comments