aboutsummaryrefslogtreecommitdiffstats
diff options
context:
space:
mode:
-rw-r--r--drivers/gpu/drm/drm_dp_helper.c76
-rw-r--r--include/drm/drm_dp_helper.h5
2 files changed, 63 insertions, 18 deletions
diff --git a/drivers/gpu/drm/drm_dp_helper.c b/drivers/gpu/drm/drm_dp_helper.c
index f1283878ff6d..d5368ea56a0f 100644
--- a/drivers/gpu/drm/drm_dp_helper.c
+++ b/drivers/gpu/drm/drm_dp_helper.c
@@ -427,11 +427,13 @@ static u32 drm_dp_i2c_functionality(struct i2c_adapter *adapter)
427 * retrying the transaction as appropriate. It is assumed that the 427 * retrying the transaction as appropriate. It is assumed that the
428 * aux->transfer function does not modify anything in the msg other than the 428 * aux->transfer function does not modify anything in the msg other than the
429 * reply field. 429 * reply field.
430 *
431 * Returns bytes transferred on success, or a negative error code on failure.
430 */ 432 */
431static int drm_dp_i2c_do_msg(struct drm_dp_aux *aux, struct drm_dp_aux_msg *msg) 433static int drm_dp_i2c_do_msg(struct drm_dp_aux *aux, struct drm_dp_aux_msg *msg)
432{ 434{
433 unsigned int retry; 435 unsigned int retry;
434 int err; 436 int ret;
435 437
436 /* 438 /*
437 * DP1.2 sections 2.7.7.1.5.6.1 and 2.7.7.1.6.6.1: A DP Source device 439 * DP1.2 sections 2.7.7.1.5.6.1 and 2.7.7.1.6.6.1: A DP Source device
@@ -440,14 +442,14 @@ static int drm_dp_i2c_do_msg(struct drm_dp_aux *aux, struct drm_dp_aux_msg *msg)
440 */ 442 */
441 for (retry = 0; retry < 7; retry++) { 443 for (retry = 0; retry < 7; retry++) {
442 mutex_lock(&aux->hw_mutex); 444 mutex_lock(&aux->hw_mutex);
443 err = aux->transfer(aux, msg); 445 ret = aux->transfer(aux, msg);
444 mutex_unlock(&aux->hw_mutex); 446 mutex_unlock(&aux->hw_mutex);
445 if (err < 0) { 447 if (ret < 0) {
446 if (err == -EBUSY) 448 if (ret == -EBUSY)
447 continue; 449 continue;
448 450
449 DRM_DEBUG_KMS("transaction failed: %d\n", err); 451 DRM_DEBUG_KMS("transaction failed: %d\n", ret);
450 return err; 452 return ret;
451 } 453 }
452 454
453 455
@@ -488,9 +490,7 @@ static int drm_dp_i2c_do_msg(struct drm_dp_aux *aux, struct drm_dp_aux_msg *msg)
488 * Both native ACK and I2C ACK replies received. We 490 * Both native ACK and I2C ACK replies received. We
489 * can assume the transfer was successful. 491 * can assume the transfer was successful.
490 */ 492 */
491 if (err < msg->size) 493 return ret;
492 return -EPROTO;
493 return 0;
494 494
495 case DP_AUX_I2C_REPLY_NACK: 495 case DP_AUX_I2C_REPLY_NACK:
496 DRM_DEBUG_KMS("I2C nack\n"); 496 DRM_DEBUG_KMS("I2C nack\n");
@@ -513,14 +513,55 @@ static int drm_dp_i2c_do_msg(struct drm_dp_aux *aux, struct drm_dp_aux_msg *msg)
513 return -EREMOTEIO; 513 return -EREMOTEIO;
514} 514}
515 515
516/*
517 * Keep retrying drm_dp_i2c_do_msg until all data has been transferred.
518 *
519 * Returns an error code on failure, or a recommended transfer size on success.
520 */
521static int drm_dp_i2c_drain_msg(struct drm_dp_aux *aux, struct drm_dp_aux_msg *orig_msg)
522{
523 int err, ret = orig_msg->size;
524 struct drm_dp_aux_msg msg = *orig_msg;
525
526 while (msg.size > 0) {
527 err = drm_dp_i2c_do_msg(aux, &msg);
528 if (err <= 0)
529 return err == 0 ? -EPROTO : err;
530
531 if (err < msg.size && err < ret) {
532 DRM_DEBUG_KMS("Partial I2C reply: requested %zu bytes got %d bytes\n",
533 msg.size, err);
534 ret = err;
535 }
536
537 msg.size -= err;
538 msg.buffer += err;
539 }
540
541 return ret;
542}
543
544/*
545 * Bizlink designed DP->DVI-D Dual Link adapters require the I2C over AUX
546 * packets to be as large as possible. If not, the I2C transactions never
547 * succeed. Hence the default is maximum.
548 */
549static int dp_aux_i2c_transfer_size __read_mostly = DP_AUX_MAX_PAYLOAD_BYTES;
550module_param_unsafe(dp_aux_i2c_transfer_size, int, 0644);
551MODULE_PARM_DESC(dp_aux_i2c_transfer_size,
552 "Number of bytes to transfer in a single I2C over DP AUX CH message, (1-16, default 16)");
553
516static int drm_dp_i2c_xfer(struct i2c_adapter *adapter, struct i2c_msg *msgs, 554static int drm_dp_i2c_xfer(struct i2c_adapter *adapter, struct i2c_msg *msgs,
517 int num) 555 int num)
518{ 556{
519 struct drm_dp_aux *aux = adapter->algo_data; 557 struct drm_dp_aux *aux = adapter->algo_data;
520 unsigned int i, j; 558 unsigned int i, j;
559 unsigned transfer_size;
521 struct drm_dp_aux_msg msg; 560 struct drm_dp_aux_msg msg;
522 int err = 0; 561 int err = 0;
523 562
563 dp_aux_i2c_transfer_size = clamp(dp_aux_i2c_transfer_size, 1, DP_AUX_MAX_PAYLOAD_BYTES);
564
524 memset(&msg, 0, sizeof(msg)); 565 memset(&msg, 0, sizeof(msg));
525 566
526 for (i = 0; i < num; i++) { 567 for (i = 0; i < num; i++) {
@@ -538,20 +579,19 @@ static int drm_dp_i2c_xfer(struct i2c_adapter *adapter, struct i2c_msg *msgs,
538 err = drm_dp_i2c_do_msg(aux, &msg); 579 err = drm_dp_i2c_do_msg(aux, &msg);
539 if (err < 0) 580 if (err < 0)
540 break; 581 break;
541 /* 582 /* We want each transaction to be as large as possible, but
542 * Many hardware implementations support FIFOs larger than a 583 * we'll go to smaller sizes if the hardware gives us a
543 * single byte, but it has been empirically determined that 584 * short reply.
544 * transferring data in larger chunks can actually lead to
545 * decreased performance. Therefore each message is simply
546 * transferred byte-by-byte.
547 */ 585 */
548 for (j = 0; j < msgs[i].len; j++) { 586 transfer_size = dp_aux_i2c_transfer_size;
587 for (j = 0; j < msgs[i].len; j += msg.size) {
549 msg.buffer = msgs[i].buf + j; 588 msg.buffer = msgs[i].buf + j;
550 msg.size = 1; 589 msg.size = min(transfer_size, msgs[i].len - j);
551 590
552 err = drm_dp_i2c_do_msg(aux, &msg); 591 err = drm_dp_i2c_drain_msg(aux, &msg);
553 if (err < 0) 592 if (err < 0)
554 break; 593 break;
594 transfer_size = err;
555 } 595 }
556 if (err < 0) 596 if (err < 0)
557 break; 597 break;
diff --git a/include/drm/drm_dp_helper.h b/include/drm/drm_dp_helper.h
index c5fdc2d3ca97..523f04c90dea 100644
--- a/include/drm/drm_dp_helper.h
+++ b/include/drm/drm_dp_helper.h
@@ -42,6 +42,8 @@
42 * 1.2 formally includes both eDP and DPI definitions. 42 * 1.2 formally includes both eDP and DPI definitions.
43 */ 43 */
44 44
45#define DP_AUX_MAX_PAYLOAD_BYTES 16
46
45#define DP_AUX_I2C_WRITE 0x0 47#define DP_AUX_I2C_WRITE 0x0
46#define DP_AUX_I2C_READ 0x1 48#define DP_AUX_I2C_READ 0x1
47#define DP_AUX_I2C_STATUS 0x2 49#define DP_AUX_I2C_STATUS 0x2
@@ -680,6 +682,9 @@ struct drm_dp_aux_msg {
680 * transactions. The drm_dp_aux_register_i2c_bus() function registers an 682 * transactions. The drm_dp_aux_register_i2c_bus() function registers an
681 * I2C adapter that can be passed to drm_probe_ddc(). Upon removal, drivers 683 * I2C adapter that can be passed to drm_probe_ddc(). Upon removal, drivers
682 * should call drm_dp_aux_unregister_i2c_bus() to remove the I2C adapter. 684 * should call drm_dp_aux_unregister_i2c_bus() to remove the I2C adapter.
685 * The I2C adapter uses long transfers by default; if a partial response is
686 * received, the adapter will drop down to the size given by the partial
687 * response for this transaction only.
683 * 688 *
684 * Note that the aux helper code assumes that the .transfer() function 689 * Note that the aux helper code assumes that the .transfer() function
685 * only modifies the reply field of the drm_dp_aux_msg structure. The 690 * only modifies the reply field of the drm_dp_aux_msg structure. The