From 670265a2caafbe72da1dbf397be05caf55141661 Mon Sep 17 00:00:00 2001 From: Thomas Makin Date: Mon, 5 Oct 2026 12:40:55 -0500 Subject: [PATCH] bm92t: gork assisted minor rework --- drivers/usb/typec/bm92txx.c | 69 ++++++++++++++++++++++++------------- 1 file changed, 46 insertions(+), 23 deletions(-) diff --git a/drivers/usb/typec/bm92txx.c b/drivers/usb/typec/bm92txx.c index 24489316fd5f..d4a09535c0a3 100644 --- a/drivers/usb/typec/bm92txx.c +++ b/drivers/usb/typec/bm92txx.c @@ -585,6 +585,11 @@ static inline bool bm92t_received_vdm(const short alert_data) return (alert_data & ALERT_VDM_RECEIVED); } +static inline bool bm92t_received_dp_event(const short alert_data) +{ + return (alert_data & ALERT_DP_EVENT); +} + static inline bool bm92t_is_plugged(const short status1_data) { return (status1_data & STATUS1_INSERT); @@ -937,7 +942,6 @@ static void bm92t_port_set_init_state(struct work_struct *work) struct bm92t_info *info = container_of(to_delayed_work(work), struct bm92t_info, oneshot_work); - disable_irq(info->i2c_client->irq); bm92t_set_vbus_enable(info, false); @@ -1005,6 +1009,9 @@ static bool bm92t_check_pdo(struct bm92t_info *info) dev_info(dev, "Device in Nintendo mode\n"); info->cable.pdo_no = 2; info->cable.pdo = pdo[1]; + info->cable.is_nintendo_dock = true; + info->cable.pdo_no = 2; + info->cable.pdo = pdo[1]; return 1; } @@ -1465,28 +1472,28 @@ init_contract_out: break; case PS_RDY_SENT: - if (bm92t_is_success(alert_data)) { - schedule_delayed_work(&info->power_work, - msecs_to_jiffies(2000)); + if (!bm92t_is_success(alert_data)) + break; - if (bm92t_is_ufp(status1_data)) { - /* Check if Dual-Role Data is supported */ - if (!info->cable.drd_support) { - dev_err(dev, "Device in UFP and DRD not supported!\n"); - break; - } + schedule_delayed_work(&info->power_work, msecs_to_jiffies(2000)); - cmd = DR_SWAP_CMD; - err = bm92t_send_cmd(info, &cmd); - bm92t_state_machine(info, DR_SWAP_SENT); - } else if (bm92t_is_dfp(status1_data)) { - dev_dbg(dev, "Already in DFP mode\n"); - bm92t_send_vdm(info, vdm_discover_id_msg, - sizeof(vdm_discover_id_msg)); - bm92t_state_machine(info, VDM_DISC_ID_SENT); - } - } - break; + if (info->cable.is_nintendo_dock || + (bm92t_is_ufp(status1_data) && info->cable.drd_support && false)) { + unsigned short cmd = DR_SWAP_CMD; + + bm92t_send_cmd(info, &cmd); + bm92t_state_machine(info, DR_SWAP_SENT); + } else if (bm92t_is_dfp(status1_data)) { + bm92t_set_data_role(info, TYPEC_HOST, true); + bm92t_send_vdm(info, vdm_discover_id_msg, + sizeof(vdm_discover_id_msg)); + bm92t_state_machine(info, VDM_DISC_ID_SENT); + } else { + /* UFP + not dock: give the port to xudc */ + bm92t_set_data_role(info, TYPEC_DEVICE, true); + bm92t_state_machine(info, DOCK_CONFIG_HANDLED); + } + break; case DR_SWAP_SENT: if (bm92t_is_success(alert_data) && @@ -1859,7 +1866,23 @@ init_contract_out: } ret: - enable_irq(info->i2c_client->irq); + // drain + if (bm92t_received_vdm(alert_data)) { + unsigned char vdm[29]; + + cmd = ACCEPT_VDM_CMD; + bm92t_send_cmd(info, &cmd); + bm92t_read_reg(info, INCOMING_VDM_REG, vdm, sizeof(vdm)); + } + + if (bm92t_received_dp_event(alert_data)) { + unsigned short dp; + + bm92t_read_reg(info, DP_STATUS_REG, (void *)&dp, sizeof(dp)); + /* HOS also reads 0x1C / 0x1D */ + bm92t_read_reg(info, UNKOWN_1C_REG, (void *)&dp, sizeof(dp)); + bm92t_read_reg(info, UNKOWN_1D_REG, (void *)&dp, sizeof(dp)); + } } static irqreturn_t bm92t_interrupt_handler(int irq, void *handle) @@ -2502,7 +2525,7 @@ static int bm92t_probe(struct i2c_client *client) */ if (request_threaded_irq(client->irq, NULL, bm92t_interrupt_handler, - IRQF_TRIGGER_LOW | IRQF_ONESHOT, "bm92t", + IRQF_ONESHOT, "bm92t", info)) { dev_err(&client->dev, "Request irq failed\n"); err = -EBUSY;