Received: by 2002:a05:6358:795:b0:dc:4c66:fc3e with SMTP id n21csp2230385rwj; Sun, 30 Oct 2022 13:43:15 -0700 (PDT) X-Google-Smtp-Source: AMsMyM76EXdrdU9blEL/pMtWh/gfU9/wVgSnwEJ1BUXLMbFt4qmcFHDMifZ28AP7kmG6+PbofKNb X-Received: by 2002:a05:6a00:999:b0:56c:3d0d:96fe with SMTP id u25-20020a056a00099900b0056c3d0d96femr10893267pfg.12.1667162595628; Sun, 30 Oct 2022 13:43:15 -0700 (PDT) ARC-Seal: i=1; a=rsa-sha256; t=1667162595; cv=none; d=google.com; s=arc-20160816; b=QhbKo96udrGrVmdSWWIBwhWyHbT+SDjWMMJbMthArsVnDlxKTkUvVYfj+/zHD7xxzt H78D3rQT5Kriez9x3JRDvX/XPMRDmeVYz598rIxkaAVJQ7R0zYowCiwp2+rCC4ZG+ycJ SjMUKJtxaKqCwcR8HYICu05GpfMiw9G9kM39pFzSL6VTOoeQ+tzTJzbWhXiCqBghflul s4YUpf9w4H2oL1B5It5Wp9upBBJx4kJp5N8AKiG5ndbpQAFZp1s9M9DOJ6hjGfzPKOxM Z1XzzjvsFy3O7uiC1zfsSlfifgJemO75h1XmfmbHmv2B4unYMQIXIAd292PlweByg6k5 JdFg== ARC-Message-Signature: i=1; a=rsa-sha256; c=relaxed/relaxed; d=google.com; s=arc-20160816; h=list-id:precedence:content-transfer-encoding:mime-version :references:in-reply-to:message-id:date:subject:cc:to:from :dkim-signature; bh=/70yde/ER3LkJXc+fZGhAb/0UY1KoaXhbuLb7z7ORbE=; b=a6HrT2W/BdqAuz8uEYBR9PJRGZeKujyKUoN5M4wL6r788o6V+5Z7a/Fbs/5ME8qgcy rCWmAhch1dOtG1n7ez1fgfBp7+iOYtcACtCyytas1gGesqy+lgAbn6k0zo12ERWMBPj5 i/m9LOKMqqYhk8sxeVPegtAF9zI/yIuGhFD2h9oZ6gjqaGdgyOLMCHx3ttq9T7RlJ2nk jDskzldtG8CzVsdYYVxI4W9Qox0P/kJcbMH+fs3oVgl4Ms/4+Y1f8AdLVxpZ63qIwha4 5j57Rh4sxwPfR0qt6o15knW6ES8nrQyXFiyNcQVVTOs2dT6sWOJ1CRFTE64Z6yTt801C RSSw== ARC-Authentication-Results: i=1; mx.google.com; dkim=pass header.i=@gmail.com header.s=20210112 header.b=RNgslzFL; spf=pass (google.com: domain of linux-kernel-owner@vger.kernel.org designates 2620:137:e000::1:20 as permitted sender) smtp.mailfrom=linux-kernel-owner@vger.kernel.org; dmarc=pass (p=NONE sp=QUARANTINE dis=NONE) header.from=gmail.com Return-Path: Received: from out1.vger.email (out1.vger.email. [2620:137:e000::1:20]) by mx.google.com with ESMTP id a17-20020a656051000000b0046174e5ceaasi6751435pgp.656.2022.10.30.13.43.03; Sun, 30 Oct 2022 13:43:15 -0700 (PDT) Received-SPF: pass (google.com: domain of linux-kernel-owner@vger.kernel.org designates 2620:137:e000::1:20 as permitted sender) client-ip=2620:137:e000::1:20; Authentication-Results: mx.google.com; dkim=pass header.i=@gmail.com header.s=20210112 header.b=RNgslzFL; spf=pass (google.com: domain of linux-kernel-owner@vger.kernel.org designates 2620:137:e000::1:20 as permitted sender) smtp.mailfrom=linux-kernel-owner@vger.kernel.org; dmarc=pass (p=NONE sp=QUARANTINE dis=NONE) header.from=gmail.com Received: (majordomo@vger.kernel.org) by vger.kernel.org via listexpand id S229949AbiJ3UfW (ORCPT + 99 others); Sun, 30 Oct 2022 16:35:22 -0400 Received: from lindbergh.monkeyblade.net ([23.128.96.19]:45792 "EHLO lindbergh.monkeyblade.net" rhost-flags-OK-OK-OK-OK) by vger.kernel.org with ESMTP id S229781AbiJ3UfJ (ORCPT ); Sun, 30 Oct 2022 16:35:09 -0400 Received: from mail-wm1-x32a.google.com (mail-wm1-x32a.google.com [IPv6:2a00:1450:4864:20::32a]) by lindbergh.monkeyblade.net (Postfix) with ESMTPS id 5FFE7B7D1; Sun, 30 Oct 2022 13:34:44 -0700 (PDT) Received: by mail-wm1-x32a.google.com with SMTP id m29-20020a05600c3b1d00b003c6bf423c71so9723798wms.0; Sun, 30 Oct 2022 13:34:44 -0700 (PDT) DKIM-Signature: v=1; a=rsa-sha256; c=relaxed/relaxed; d=gmail.com; s=20210112; h=content-transfer-encoding:mime-version:references:in-reply-to :message-id:date:subject:cc:to:from:from:to:cc:subject:date :message-id:reply-to; bh=/70yde/ER3LkJXc+fZGhAb/0UY1KoaXhbuLb7z7ORbE=; b=RNgslzFLXcYc/7qkNDCxsyGq6dFUmnXok01RYIzUOiVlZFkGHXhuoYC9umrs8QLFDe tf9jXn1lXQD4tOIqOxBm1aNFzBDHKLf48HO0khZHJ1q3dI2WqW8QDXNEIsheehVuYbGM yiLiNnxtOYDg1HeM+mz0iq15zgCOpDsr1sQzuD09u0n+2vOWFabwZgYnT2UchWKGTXSY HQYR2eTHx9Z4UtxUKhcni2+4rSG3M937Wo3KER5/qNf+ZVImtopt8SLsMz0ciU4nh8mp 7Ja4+FkXEVOqrQBOh6kByn7eU4eCsgp8ZXGkRfOG0xmt00Zl5obPsXWTpCzVE/VeDGIA ZPWg== X-Google-DKIM-Signature: v=1; a=rsa-sha256; c=relaxed/relaxed; d=1e100.net; s=20210112; h=content-transfer-encoding:mime-version:references:in-reply-to :message-id:date:subject:cc:to:from:x-gm-message-state:from:to:cc :subject:date:message-id:reply-to; bh=/70yde/ER3LkJXc+fZGhAb/0UY1KoaXhbuLb7z7ORbE=; b=dnrWsmV0+7YTUfolftMf9IjkHFkEn1XO7iqWdypv2PNC8gBPbXKJ1t7u7CviarvxDN k/uZkll2RGqNR+A3dDYFHjJsGbd0YFrgnxzDzO+oAE1tfcKjzrC7tB0RE5/G8yYyy+bD GDQHWyxmYle1HxDEnlp/uoyPmhG7lkSxb2HGfsY+S++/6nq7rgIs9gaDRBKhuEPI7Zw3 ybRlCglM3T+QNVVOk5tUKxDlAaEMJkg3fhXJnyC3zCuo1McAK7oRIzfMj8ykobuslkBU svT/Lp8SH+WPOWjhq4+fAwo8GznyQVoYYoRxqgG/Bq+3iC/x4p0zFDDnkIZSeCB5Ho+e p5eg== X-Gm-Message-State: ACrzQf1/CuGbqY77SgIkeTiB41m8sBWgbxW8U3ccCkHyfYBitXV+07vH apNgytJ+qaLkDU8z6b45RCs= X-Received: by 2002:a1c:f008:0:b0:3b4:fd2e:3ede with SMTP id a8-20020a1cf008000000b003b4fd2e3edemr16281717wmb.133.1667162083882; Sun, 30 Oct 2022 13:34:43 -0700 (PDT) Received: from michael-VirtualBox.. (89-139-44-91.bb.netvision.net.il. [89.139.44.91]) by smtp.googlemail.com with ESMTPSA id n25-20020a05600c181900b003b95ed78275sm4939385wmp.20.2022.10.30.13.34.42 (version=TLS1_3 cipher=TLS_AES_256_GCM_SHA384 bits=256/256); Sun, 30 Oct 2022 13:34:43 -0700 (PDT) From: Michael Zaidman To: jikos@kernel.org Cc: linux-kernel@vger.kernel.org, linux-input@vger.kernel.org, linux-i2c@vger.kernel.org, germain.hebert@ca.abb.com, Enrik.Berkhan@inka.de, Michael Zaidman Subject: [PATCH v3 12/12] HID: ft260: missed NACK from busy device Date: Sun, 30 Oct 2022 22:34:03 +0200 Message-Id: <20221030203403.4637-13-michael.zaidman@gmail.com> X-Mailer: git-send-email 2.34.1 In-Reply-To: <20221030203403.4637-1-michael.zaidman@gmail.com> References: <20221030203403.4637-1-michael.zaidman@gmail.com> MIME-Version: 1.0 Content-Transfer-Encoding: 8bit X-Spam-Status: No, score=-2.1 required=5.0 tests=BAYES_00,DKIM_SIGNED, DKIM_VALID,DKIM_VALID_AU,DKIM_VALID_EF,FREEMAIL_FROM, RCVD_IN_DNSWL_NONE,SPF_HELO_NONE,SPF_PASS autolearn=ham autolearn_force=no version=3.4.6 X-Spam-Checker-Version: SpamAssassin 3.4.6 (2021-04-09) on lindbergh.monkeyblade.net Precedence: bulk List-ID: X-Mailing-List: linux-kernel@vger.kernel.org When writing into a slow device like an EEPROM chip, the controller may exit the busy state before the device releases the bus. In this case, the ft260_xfer_status returns success before the data transfer completion. The patch fixes it by returning from the ft260_xfer_status() with the "-EAGAIN" on both controller and bus busy status when appropriate. It does not apply to the i2c combined transactions when after the write IO, the controller keeps the bus busy until the read IO and then between reading IOs to ensure an atomic operation. Co-developed-by: Germain Hebert Signed-off-by: Germain Hebert Signed-off-by: Michael Zaidman --- drivers/hid/hid-ft260.c | 31 ++++++++++++++++++++++++------- 1 file changed, 24 insertions(+), 7 deletions(-) diff --git a/drivers/hid/hid-ft260.c b/drivers/hid/hid-ft260.c index b3f715f6ea86..da8ea0d16059 100644 --- a/drivers/hid/hid-ft260.c +++ b/drivers/hid/hid-ft260.c @@ -303,7 +303,7 @@ static int ft260_i2c_reset(struct hid_device *hdev) return ret; } -static int ft260_xfer_status(struct ft260_device *dev) +static int ft260_xfer_status(struct ft260_device *dev, u8 bus_busy) { struct hid_device *hdev = dev->hdev; struct ft260_get_i2c_status_report report; @@ -320,7 +320,7 @@ static int ft260_xfer_status(struct ft260_device *dev) ft260_dbg("bus_status %#02x, clock %u\n", report.bus_status, dev->clock); - if (report.bus_status & FT260_I2C_STATUS_CTRL_BUSY) + if (report.bus_status & (FT260_I2C_STATUS_CTRL_BUSY | bus_busy)) return -EAGAIN; /* @@ -355,8 +355,11 @@ static int ft260_hid_output_report(struct hid_device *hdev, u8 *data, static int ft260_hid_output_report_check_status(struct ft260_device *dev, u8 *data, int len) { + u8 bus_busy; int ret, usec, try = 100; struct hid_device *hdev = dev->hdev; + struct ft260_i2c_write_request_report *rep = + (struct ft260_i2c_write_request_report *)data; ret = ft260_hid_output_report(hdev, data, len); if (ret < 0) { @@ -374,8 +377,18 @@ static int ft260_hid_output_report_check_status(struct ft260_device *dev, ft260_dbg("wait %d usec, len %d\n", usec, len); } + /* + * Do not check the busy bit for combined transactions + * since the controller keeps the bus busy between writing + * and reading IOs to ensure an atomic operation. + */ + if (rep->flag == FT260_FLAG_START) + bus_busy = 0; + else + bus_busy = FT260_I2C_STATUS_BUS_BUSY; + do { - ret = ft260_xfer_status(dev); + ret = ft260_xfer_status(dev, bus_busy); if (ret != -EAGAIN) break; } while (--try); @@ -399,7 +412,7 @@ static int ft260_i2c_write(struct ft260_device *dev, u8 addr, u8 *data, return -EINVAL; if (time_is_before_jiffies(dev->need_wakeup_at)) { - (void)ft260_xfer_status(dev); + (void)ft260_xfer_status(dev, 0); ft260_dbg("device wakeup"); } @@ -453,7 +466,7 @@ static int ft260_smbus_write(struct ft260_device *dev, u8 addr, u8 cmd, return -EINVAL; if (time_is_before_jiffies(dev->need_wakeup_at)) { - (void)ft260_xfer_status(dev); + (void)ft260_xfer_status(dev, 0); ft260_dbg("device wakeup"); } @@ -484,6 +497,7 @@ static int ft260_i2c_read(struct ft260_device *dev, u8 addr, u8 *data, int timeout, ret = 0; struct ft260_i2c_read_request_report rep; struct hid_device *hdev = dev->hdev; + u8 bus_busy = 0; if ((flag & FT260_FLAG_START_REPEATED) == FT260_FLAG_START_REPEATED) flag = FT260_FLAG_START_REPEATED; @@ -527,7 +541,10 @@ static int ft260_i2c_read(struct ft260_device *dev, u8 addr, u8 *data, dev->read_buf = NULL; - ret = ft260_xfer_status(dev); + if (flag & FT260_FLAG_STOP) + bus_busy = FT260_I2C_STATUS_BUS_BUSY; + + ret = ft260_xfer_status(dev, bus_busy); if (ret < 0) { ret = -EIO; ft260_i2c_reset(hdev); @@ -1003,7 +1020,7 @@ static int ft260_probe(struct hid_device *hdev, const struct hid_device_id *id) mutex_init(&dev->lock); init_completion(&dev->wait); - ret = ft260_xfer_status(dev); + ret = ft260_xfer_status(dev, FT260_I2C_STATUS_BUS_BUSY); if (ret) ft260_i2c_reset(hdev); -- 2.34.1