All of lore.kernel.org
 help / color / mirror / Atom feed
From: Lukas Wunner <lukas@wunner.de>
To: Linus Walleij <linus.walleij@linaro.org>,
	William Breathitt Gray <vilhelm.gray@gmail.com>,
	Geert Uytterhoeven <geert+renesas@glider.be>,
	Phil Reid <preid@electromag.com.au>,
	David Daney <david.daney@cavium.com>,
	Iban Rodriguez <irodriguez@cemitec.com>
Cc: Mathias Duckeck <m.duckeck@kunbus.de>,
	Phil Elwell <phil@raspberrypi.org>,
	linux-gpio@vger.kernel.org
Subject: Re: [PATCH v2 5/5] gpio: Add driver for Maxim MAX3191x industrial serializer
Date: Fri, 13 Oct 2017 13:11:24 +0200	[thread overview]
Message-ID: <20171013111124.GA12351@wunner.de> (raw)
In-Reply-To: <165c5061f7f309ecb7f1a3d32c8f7df5026f4a47.1507797496.git.lukas@wunner.de>

[cc += William Breathitt Gray, Geert Uytterhoeven, Phil Reid,
       David Daney, Iban Rodriguez]

The drivers

       gpio-104-dio-48e.c, gpio-74x164.c, gpio-gpio-mm.c,
       gpio-pca953x.c, gpio-thunderx.c, gpio-ws16c48.c,
       gpio-xilinx.c

currently use an inefficient algorithm for their ->set_multiple
callback:  They iterate over every chip (or bank or gpio pin),
check if any bits are set in the mask for this particular chip,
and if so, update the affected GPIOs.  If the mask is sparsely
populated, you'll waste CPU time checking chips even though
they're not affected by the operation at all.

Iterating over the chips is backwards, it is more efficient to
iterate over the bits set in the mask, identify the corresponding
chip and update its affected GPIOs.  The gpio-max3191x.c driver
I posted yesterday contains an example for such an algorithm and
you may want to improve your ->set_mutiple implementation accordingly:


> +static int max3191x_get_multiple(struct gpio_chip *gpio, unsigned long *mask,
> +				 unsigned long *bits)
> +{
> +	struct max3191x_chip *max3191x = gpiochip_get_data(gpio);
> +	int ret, bit = 0, wordlen = max3191x_wordlen(max3191x);
> +
> +	mutex_lock(&max3191x->lock);
> +	ret = max3191x_readout_locked(max3191x);
> +	if (ret)
> +		goto out_unlock;
> +
> +	while ((bit = find_next_bit(mask, gpio->ngpio, bit)) != gpio->ngpio) {
> +		unsigned int chipnum = bit / MAX3191X_NGPIO;
> +		unsigned long in, shift, index;
> +
> +		if (max3191x_chip_is_faulting(max3191x, chipnum)) {
> +			ret = -EIO;
> +			goto out_unlock;
> +		}
> +
> +		in = ((u8 *)max3191x->xfer.rx_buf)[chipnum * wordlen];
> +		shift = round_down(bit % BITS_PER_LONG, MAX3191X_NGPIO);
> +		index = bit / BITS_PER_LONG;
> +		bits[index] &= ~(mask[index] & (0xff << shift));
> +		bits[index] |= mask[index] & (in << shift); /* copy bits */
> +
> +		bit = (chipnum + 1) * MAX3191X_NGPIO; /* go to next chip */
> +	}
> +
> +out_unlock:
> +	mutex_unlock(&max3191x->lock);
> +	return ret;
> +}


I've used a while loop, obviously the same can be achieved with a
for loop but I found that harder to read and it didn't save any LoC.

This particular chip has 8 inputs (= MAX3191X_NGPIO) that can be read
concurrently.

The series containing this driver introduces a ->get_multiple callback.
Since you've implemented a ->set_multiple callback, you may want to
add a ->get_multiple callback to your driver as well.  (If supported
by the hardware, which is not the case for output-only chips such as
gpio-74x164.c.)

You can find the full series here:
https://www.spinics.net/lists/linux-gpio/msg25997.html

If you want to fetch the series from a git repo, use this branch:
https://github.com/RevolutionPi/linux/commits/revpi-4.9

Thanks,

Lukas

  reply	other threads:[~2017-10-13 11:11 UTC|newest]

Thread overview: 22+ messages / expand[flat|nested]  mbox.gz  Atom feed  top
2017-10-12 10:40 [PATCH v2 0/5] GPIO driver for Maxim MAX3191x Lukas Wunner
2017-10-12 10:40 ` [PATCH v2 3/5] dt-bindings: Document common property for daisy-chained devices Lukas Wunner
     [not found]   ` <f0c3b0c5514f74717c5783360b60062dfe9b8c0f.1507797496.git.lukas-JFq808J9C/izQB+pC5nmwQ@public.gmane.org>
2017-10-15 11:30     ` Jonathan Cameron
2017-10-17 20:32     ` Rob Herring
2017-10-19 20:35     ` Linus Walleij
2017-10-12 10:40 ` [PATCH v2 2/5] gpio: Introduce ->get_multiple callback Lukas Wunner
2017-10-13 12:46   ` Linus Walleij
     [not found] ` <cover.1507797496.git.lukas-JFq808J9C/izQB+pC5nmwQ@public.gmane.org>
2017-10-12 10:40   ` [PATCH v2 4/5] dt-bindings: gpio: max3191x: Document new driver Lukas Wunner
2017-10-17 20:30     ` Rob Herring
     [not found]     ` <57660f421f2080914940806394a9365ac959f5a8.1507797496.git.lukas-JFq808J9C/izQB+pC5nmwQ@public.gmane.org>
2017-10-19 20:36       ` Linus Walleij
2017-10-12 10:40   ` [PATCH v2 5/5] gpio: Add driver for Maxim MAX3191x industrial serializer Lukas Wunner
2017-10-13 11:11     ` Lukas Wunner [this message]
2017-10-13 16:53       ` David Daney
2017-10-13 21:29         ` Lukas Wunner
2017-10-13 22:12           ` David Daney
2017-10-14 11:24             ` Lukas Wunner
2017-10-19 20:41     ` Linus Walleij
2017-10-12 10:40 ` [PATCH v2 1/5] bitops: Introduce assign_bit() Lukas Wunner
2017-10-12 18:30   ` Andrew Morton
2017-10-13 12:44   ` Linus Walleij
2017-10-13 12:48 ` [PATCH v2 0/5] GPIO driver for Maxim MAX3191x Linus Walleij
2017-10-13 12:48   ` Linus Walleij

Reply instructions:

You may reply publicly to this message via plain-text email
using any one of the following methods:

* Save the following mbox file, import it into your mail client,
  and reply-to-all from there: mbox

  Avoid top-posting and favor interleaved quoting:
  https://en.wikipedia.org/wiki/Posting_style#Interleaved_style

* Reply using the --to, --cc, and --in-reply-to
  switches of git-send-email(1):

  git send-email \
    --in-reply-to=20171013111124.GA12351@wunner.de \
    --to=lukas@wunner.de \
    --cc=david.daney@cavium.com \
    --cc=geert+renesas@glider.be \
    --cc=irodriguez@cemitec.com \
    --cc=linus.walleij@linaro.org \
    --cc=linux-gpio@vger.kernel.org \
    --cc=m.duckeck@kunbus.de \
    --cc=phil@raspberrypi.org \
    --cc=preid@electromag.com.au \
    --cc=vilhelm.gray@gmail.com \
    /path/to/YOUR_REPLY

  https://kernel.org/pub/software/scm/git/docs/git-send-email.html

* If your mail client supports setting the In-Reply-To header
  via mailto: links, try the mailto: link
Be sure your reply has a Subject: header at the top and a blank line before the message body.
This is an external index of several public inboxes,
see mirroring instructions on how to clone and mirror
all data and code used by this external index.