From patchwork Mon Apr 16 02:51:49 2018 Content-Type: text/plain; charset="utf-8" MIME-Version: 1.0 Content-Transfer-Encoding: 7bit X-Patchwork-Submitter: Akinobu Mita X-Patchwork-Id: 10342073 Return-Path: Received: from mail.wl.linuxfoundation.org (pdx-wl-mail.web.codeaurora.org [172.30.200.125]) by pdx-korg-patchwork.web.codeaurora.org (Postfix) with ESMTP id 2AE95601C2 for ; Mon, 16 Apr 2018 02:52:41 +0000 (UTC) Received: from mail.wl.linuxfoundation.org (localhost [127.0.0.1]) by mail.wl.linuxfoundation.org (Postfix) with ESMTP id 1D67C201CB for ; Mon, 16 Apr 2018 02:52:41 +0000 (UTC) Received: by mail.wl.linuxfoundation.org (Postfix, from userid 486) id 1200F2228E; Mon, 16 Apr 2018 02:52:41 +0000 (UTC) X-Spam-Checker-Version: SpamAssassin 3.3.1 (2010-03-16) on pdx-wl-mail.web.codeaurora.org X-Spam-Level: X-Spam-Status: No, score=-8.0 required=2.0 tests=BAYES_00,DKIM_SIGNED, DKIM_VALID, DKIM_VALID_AU, FREEMAIL_FROM, MAILING_LIST_MULTI, RCVD_IN_DNSWL_HI autolearn=ham version=3.3.1 Received: from vger.kernel.org (vger.kernel.org [209.132.180.67]) by mail.wl.linuxfoundation.org (Postfix) with ESMTP id 99C0A201CB for ; Mon, 16 Apr 2018 02:52:40 +0000 (UTC) Received: (majordomo@vger.kernel.org) by vger.kernel.org via listexpand id S1752900AbeDPCwi (ORCPT ); Sun, 15 Apr 2018 22:52:38 -0400 Received: from mail-pl0-f67.google.com ([209.85.160.67]:42498 "EHLO mail-pl0-f67.google.com" rhost-flags-OK-OK-OK-OK) by vger.kernel.org with ESMTP id S1752854AbeDPCwg (ORCPT ); Sun, 15 Apr 2018 22:52:36 -0400 Received: by mail-pl0-f67.google.com with SMTP id t20-v6so9194418ply.9; Sun, 15 Apr 2018 19:52:35 -0700 (PDT) DKIM-Signature: v=1; a=rsa-sha256; c=relaxed/relaxed; d=gmail.com; s=20161025; h=from:to:cc:subject:date:message-id:in-reply-to:references; bh=kR225tMiYwbmcJwVTI6UmROQzKpIqZ4CBwYerYD6360=; b=T/1rE7zx21c2gt9Rv4zxvIs2PlmHsvgCdYNnDpcjZ4toG/7L4GEQM9CWSbjtMwp/AO fSi7nIrVa5dEHAPFwfe0kWbi3a0rZUnslz/Z0lnmyihlCgneGHyk5XLemarwjuOzMtVl +wo5Ep3ShmiZABslaXGbMbSv0RLf0QzHMkWvXmgCfPZ7YIU93vlsIb085Q/48SlWvU4h jzvhZV+9loMCGkL7dDYIzCtX3eUWvTj6Uqpr+4+CUd0F4SCcgOlxe+Okt0L1ei5zVLkD o/b/pbTXHLffN9Qj3bPtb7/jenFyAu1Xq/9BJwQjNX8CjRpyg9x5/oWwZ+Fz0GjCLMzd X1Nw== X-Google-DKIM-Signature: v=1; a=rsa-sha256; c=relaxed/relaxed; d=1e100.net; s=20161025; h=x-gm-message-state:from:to:cc:subject:date:message-id:in-reply-to :references; bh=kR225tMiYwbmcJwVTI6UmROQzKpIqZ4CBwYerYD6360=; b=c+UNlipURu+yBMadXSS7C4k2eiRMvKRBIXaxx+vV3NL4cnmTa6yjAPVPupAWOZ6iim qrUfLPZgHLhQHauLvtrBzAIdIJm/i1fkwDXOF3egupnPSw0qG+9sSZ7fNw7I2kuDKpKR icy5vs3oqGKd2VUlri4vvaI30dT4yQytD3PWM3xWHdobiPpt080FLDdyRRuMmCVvrsZY 19EZb2gnWm+P5nz2kRHFBP7eEz3J4/yvDlc3AddGX1QR2RAArOs1tQEaZ1JcUCuzIN9r /Mrc3xH0Wv15h1rfnz9zjFEgE5Tq1b0bspefNLnXZEOm/w9zWX21VA5E//AfzXGbUr03 6F3g== X-Gm-Message-State: ALQs6tDyU2oqFtau2/lHD39TTielnpj6cfVxl2ehmlIMDJbKpQ420Z2F DeYlAodurJX0EPgTCX1pysZSnw== X-Google-Smtp-Source: AIpwx4+pR7pLMDOa8tDbLdPihhsRRRZTVOvVFF+x+YPOsmNFZdxoLLVBdfQwOwgXY8r0a9wWkPvN5w== X-Received: by 2002:a17:902:7611:: with SMTP id k17-v6mr13826909pll.244.1523847155420; Sun, 15 Apr 2018 19:52:35 -0700 (PDT) Received: from localhost.localdomain ([240f:4:c2bc:1:3df1:9c88:51ad:c027]) by smtp.gmail.com with ESMTPSA id e1sm3694274pgt.49.2018.04.15.19.52.32 (version=TLS1_2 cipher=ECDHE-RSA-AES128-SHA bits=128/128); Sun, 15 Apr 2018 19:52:34 -0700 (PDT) From: Akinobu Mita To: linux-media@vger.kernel.org, devicetree@vger.kernel.org Cc: Akinobu Mita , Jacopo Mondi , Laurent Pinchart , Hans Verkuil , Sakari Ailus , Mauro Carvalho Chehab Subject: [PATCH v2 08/10] media: ov772x: handle nested s_power() calls Date: Mon, 16 Apr 2018 11:51:49 +0900 Message-Id: <1523847111-12986-9-git-send-email-akinobu.mita@gmail.com> X-Mailer: git-send-email 2.7.4 In-Reply-To: <1523847111-12986-1-git-send-email-akinobu.mita@gmail.com> References: <1523847111-12986-1-git-send-email-akinobu.mita@gmail.com> Sender: linux-media-owner@vger.kernel.org Precedence: bulk List-ID: X-Mailing-List: linux-media@vger.kernel.org X-Virus-Scanned: ClamAV using ClamSMTP Depending on the v4l2 driver, calling s_power() could be nested. So the actual transitions between power saving mode and normal operation mode should only happen at the first power on and the last power off. This adds an s_power() nesting counter and updates the power state if the counter is modified from 0 to != 0 or from != 0 to 0. Cc: Jacopo Mondi Cc: Laurent Pinchart Cc: Hans Verkuil Cc: Sakari Ailus Cc: Mauro Carvalho Chehab Signed-off-by: Akinobu Mita --- * v2 - New patch drivers/media/i2c/ov772x.c | 33 +++++++++++++++++++++++++++++---- 1 file changed, 29 insertions(+), 4 deletions(-) diff --git a/drivers/media/i2c/ov772x.c b/drivers/media/i2c/ov772x.c index 4245a46..2cd6e85 100644 --- a/drivers/media/i2c/ov772x.c +++ b/drivers/media/i2c/ov772x.c @@ -424,6 +424,9 @@ struct ov772x_priv { /* band_filter = COM8[5] ? 256 - BDBASE : 0 */ unsigned short band_filter; unsigned int fps; + /* lock to protect power_count */ + struct mutex power_lock; + int power_count; #ifdef CONFIG_MEDIA_CONTROLLER struct media_pad pad; #endif @@ -871,9 +874,25 @@ static int ov772x_power_off(struct ov772x_priv *priv) static int ov772x_s_power(struct v4l2_subdev *sd, int on) { struct ov772x_priv *priv = to_ov772x(sd); + int ret = 0; + + mutex_lock(&priv->power_lock); - return on ? ov772x_power_on(priv) : - ov772x_power_off(priv); + /* If the power count is modified from 0 to != 0 or from != 0 to 0, + * update the power state. + */ + if (priv->power_count == !on) + ret = on ? ov772x_power_on(priv) : ov772x_power_off(priv); + + if (!ret) { + /* Update the power count. */ + priv->power_count += on ? 1 : -1; + WARN_ON(priv->power_count < 0); + } + + mutex_unlock(&priv->power_lock); + + return ret; } static const struct ov772x_win_size *ov772x_select_win(u32 width, u32 height) @@ -1303,6 +1322,7 @@ static int ov772x_probe(struct i2c_client *client, return -ENOMEM; priv->info = client->dev.platform_data; + mutex_init(&priv->power_lock); v4l2_i2c_subdev_init(&priv->subdev, client, &ov772x_subdev_ops); priv->subdev.flags |= V4L2_SUBDEV_FL_HAS_DEVNODE; @@ -1314,8 +1334,10 @@ static int ov772x_probe(struct i2c_client *client, v4l2_ctrl_new_std(&priv->hdl, &ov772x_ctrl_ops, V4L2_CID_BAND_STOP_FILTER, 0, 256, 1, 0); priv->subdev.ctrl_handler = &priv->hdl; - if (priv->hdl.error) - return priv->hdl.error; + if (priv->hdl.error) { + ret = priv->hdl.error; + goto error_mutex_destroy; + } priv->clk = clk_get(&client->dev, "xclk"); if (IS_ERR(priv->clk)) { @@ -1363,6 +1385,8 @@ static int ov772x_probe(struct i2c_client *client, clk_put(priv->clk); error_ctrl_free: v4l2_ctrl_handler_free(&priv->hdl); +error_mutex_destroy: + mutex_destroy(&priv->power_lock); return ret; } @@ -1377,6 +1401,7 @@ static int ov772x_remove(struct i2c_client *client) gpiod_put(priv->pwdn_gpio); v4l2_async_unregister_subdev(&priv->subdev); v4l2_ctrl_handler_free(&priv->hdl); + mutex_destroy(&priv->power_lock); return 0; }