All of lore.kernel.org
 help / color / mirror / Atom feed
From: Ryan Mallon <rmallon@gmail.com>
To: Frank Haverkamp <haver@linux.vnet.ibm.com>, linux-kernel@vger.kernel.org
Cc: arnd@arndb.de, gregkh@linuxfoundation.org,
	cody@linux.vnet.ibm.com, schwidefsky@de.ibm.com,
	utz.bacher@de.ibm.com, mmarek@suse.cz, jsvogt@de.ibm.com,
	MIJUNG@de.ibm.com, cascardo@linux.vnet.ibm.com, michael@ibmra.de,
	Frank Haverkamp <haver@vnet.ibm.com>
Subject: Re: [PATCH] Generic WorkQueue Engine (GenWQE) device driver (v4)
Date: Thu, 31 Oct 2013 14:49:20 +1100	[thread overview]
Message-ID: <5271D340.2090706@gmail.com> (raw)
In-Reply-To: <1383125578-26202-2-git-send-email-haver@linux.vnet.ibm.com>

On 30/10/13 20:32, Frank Haverkamp wrote:
> From: Frank Haverkamp <haver@vnet.ibm.com>

> Signed-off-by: Frank Haverkamp <haver@linux.vnet.ibm.com>
> Co-authors: Joerg-Stephan Vogt <jsvogt@de.ibm.com>,
>             Michael Jung <MIJUNG@de.ibm.com>,
>             Michael Ruettger <michael@ibmra.de>
> ---
>  Documentation/ABI/testing/debugfs-driver-genwqe |   57 +
>  Documentation/ABI/testing/sysfs-driver-genwqe   |   46 +
>  drivers/misc/Kconfig                            |    1 +
>  drivers/misc/Makefile                           |    1 +
>  drivers/misc/genwqe/Kconfig                     |   23 +
>  drivers/misc/genwqe/Makefile                    |    8 +
>  drivers/misc/genwqe/card_base.c                 | 1238 +++++++++++++++++++
>  drivers/misc/genwqe/card_base.h                 |  569 +++++++++
>  drivers/misc/genwqe/card_ddcb.c                 | 1380 +++++++++++++++++++++
>  drivers/misc/genwqe/card_ddcb.h                 |  188 +++
>  drivers/misc/genwqe/card_debugfs.c              |  566 +++++++++
>  drivers/misc/genwqe/card_dev.c                  | 1499 +++++++++++++++++++++++
>  drivers/misc/genwqe/card_sysfs.c                |  306 +++++
>  drivers/misc/genwqe/card_utils.c                |  983 +++++++++++++++
>  drivers/misc/genwqe/genwqe_driver.h             |   75 ++
>  include/linux/genwqe/genwqe_card.h              |  559 +++++++++
>  16 files changed, 7499 insertions(+), 0 deletions(-)


Please consider breaking this into multiple patches. One behemoth patch
is harder to review and less likely for people to read all of it. Since
this adds a new driver, you can add it in parts, e.g: core, sysfs,
documentation, etc, and add the Makefile/Kconfig bits in the final
patch. That way it won't break the build at any point.

Couple of comments on the sysfs bits below.

~Ryan

> +++ b/drivers/misc/genwqe/card_sysfs.c
> @@ -0,0 +1,306 @@
> +/**
> + * IBM Accelerator Family 'GenWQE'
> + *
> + * (C) Copyright IBM Corp. 2013
> + *
> + * Author: Frank Haverkamp <haver@linux.vnet.ibm.com>
> + * Author: Joerg-Stephan Vogt <jsvogt@de.ibm.com>
> + * Author: Michael Jung <mijung@de.ibm.com>
> + * Author: Michael Ruettger <michael@ibmra.de>
> + *
> + * This program is free software; you can redistribute it and/or modify
> + * it under the terms of the GNU General Public License (version 2 only)
> + * as published by the Free Software Foundation.
> + *
> + * This program is distributed in the hope that it will be useful,
> + * but WITHOUT ANY WARRANTY; without even the implied warranty of
> + * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the
> + * GNU General Public License for more details.
> + */
> +
> +/*
> + * Sysfs interfaces for the GenWQE card. There are attributes to query
> + * the version of the bitstream as well as some for the
> + * driver. Additionally there are some attributes which help to debug
> + * potential problems.
> + */
> +
> +#include <linux/version.h>
> +#include <linux/kernel.h>
> +#include <linux/types.h>
> +#include <linux/module.h>
> +#include <linux/pci.h>
> +#include <linux/string.h>
> +#include <linux/fs.h>
> +#include <linux/sysfs.h>
> +#include <linux/ctype.h>
> +
> +#include "card_base.h"
> +#include "card_ddcb.h"
> +
> +static const char * const genwqe_types[] = {
> +	[GENWQE_TYPE_ALTERA_230] = "GenWQE4-230",
> +	[GENWQE_TYPE_ALTERA_530] = "GenWQE4-530",
> +	[GENWQE_TYPE_ALTERA_A4]  = "GenWQE5-A4",
> +	[GENWQE_TYPE_ALTERA_A7]  = "GenWQE5-A7",
> +};
> +
> +static ssize_t show_card_status(struct device *dev,
> +				struct device_attribute *attr,
> +				char *buf)
> +{
> +	ssize_t len = 0;
> +	struct genwqe_dev *cd = dev_get_drvdata(dev);
> +	const char *cs[GENWQE_CARD_STATE_MAX] = { "unused", "used", "error" };
> +
> +	len += scnprintf(&buf[len], PAGE_SIZE - len,
> +			 "%s\n", cs[cd->card_state]);
> +	return len;

This is a bit confusingly written. Why do:

	scnprintf(&buf[len], ...

When len is always zero at that point? Since you are printing from an
array of statically sized strings that are guaranteed to be smaller than
PAGE_SIZE, you can safely do:

	sprintf(buf, "%s\n", cs[cd->card_state]);

You might want to add some checking for cd->card_state being out of
bounds, and printing "unknown" or something in that case.

Same issue exists in other sysfs handlers.

> +}
> +
> +static ssize_t show_card_appid(struct device *dev,
> +			       struct device_attribute *attr,
> +			       char *buf)
> +{
> +	ssize_t len = 0;
> +	char app_name[5];
> +	struct genwqe_dev *cd = dev_get_drvdata(dev);
> +
> +	genwqe_read_app_id(cd, app_name, sizeof(app_name));
> +	len += scnprintf(&buf[len], PAGE_SIZE - len,
> +			 "%s\n", app_name);
> +	return len;
> +}
> +
> +static ssize_t show_card_version(struct device *dev,
> +				 struct device_attribute *attr,
> +				 char *buf)
> +{
> +	ssize_t len = 0;
> +	u64 slu_id, app_id;
> +	struct genwqe_dev *cd = dev_get_drvdata(dev);
> +
> +	slu_id = __genwqe_readq(cd, IO_SLU_UNITCFG);
> +	app_id = __genwqe_readq(cd, IO_APP_UNITCFG);
> +
> +	len += scnprintf(&buf[len], PAGE_SIZE - len,
> +			 "%016llx.%016llx\n", slu_id, app_id);
> +	return len;
> +}
> +
> +/**
> + * FIXME Implement me!
> + */
> +static ssize_t show_cpld_version(struct device *dev,
> +				 struct device_attribute *attr,
> +				 char *buf)
> +{
> +	ssize_t len = 0;
> +	len += scnprintf(&buf[len], PAGE_SIZE - len,
> +			 "unknown (FIXME)\n");
> +	return len;
> +}
> +
> +static ssize_t show_card_type(struct device *dev,
> +			      struct device_attribute *attr,
> +			      char *buf)
> +{
> +	ssize_t len = 0;
> +	u8 card_type;
> +	struct genwqe_dev *cd = dev_get_drvdata(dev);
> +
> +	card_type = genwqe_card_type(cd);
> +	len += scnprintf(&buf[len], PAGE_SIZE - len,
> +			 "%s\n", (card_type >= ARRAY_SIZE(genwqe_types)) ?
> +			 "invalid" : genwqe_types[card_type]);
> +	return len;
> +}
> +
> +static ssize_t show_card_driver(struct device *dev,
> +				struct device_attribute *attr,
> +				char *buf)
> +{
> +	ssize_t len = 0;
> +	len += scnprintf(&buf[len], PAGE_SIZE - len,
> +			 "%s\n", DRV_VERS_STRING);
> +	return len;
> +}
> +
> +static ssize_t show_card_tempsens(struct device *dev,
> +				  struct device_attribute *attr,
> +				  char *buf)
> +{
> +	ssize_t len = 0;
> +	u64 tempsens;
> +	struct genwqe_dev *cd = dev_get_drvdata(dev);
> +
> +	tempsens = __genwqe_readq(cd, IO_SLU_TEMPERATURE_SENSOR);
> +	len += scnprintf(&buf[len], PAGE_SIZE - len,
> +			 "%016llx\n", tempsens);
> +	return len;
> +}
> +
> +static ssize_t show_card_base_clock(struct device *dev,
> +				    struct device_attribute *attr,
> +				    char *buf)
> +{
> +	ssize_t len = 0;
> +	u64 base_clock;
> +	struct genwqe_dev *cd = dev_get_drvdata(dev);
> +
> +	base_clock = genwqe_base_clock_frequency(cd);
> +	len += scnprintf(&buf[len], PAGE_SIZE - len,
> +			 "%lld\n", base_clock);
> +	return len;
> +}
> +
> +/**
> + * show_card_curr_bitstream() - Show the current bitstream id
> + *
> + * There is a bug in some old versions of the CPLD which selects the
> + * bitstream, which causes the IO_SLU_BITSTREAM register to report
> + * unreliable data in very rare cases. This makes this sysfs
> + * unreliable up to the point were a new CPLD version is being used.
> + *
> + * Unfortunately there is no automatic way yet to query the CPLD
> + * version (See show_cpld_version() ;-)), such that you need to
> + * manually ensure via programming tools that you have a recent
> + * version of the CPLD software.
> + *
> + * The proposed circumvention is to use a special recovery bitstream
> + * on the backup partition (0) to identify problems while loading the
> + * image.
> + */
> +static ssize_t show_card_curr_bitstream(struct device *dev,
> +					struct device_attribute *attr,
> +					char *buf)
> +{
> +	ssize_t len = 0;
> +	int curr_bitstream;
> +	struct genwqe_dev *cd = dev_get_drvdata(dev);
> +
> +	curr_bitstream = __genwqe_readq(cd, IO_SLU_BITSTREAM) & 0x1;
> +	len += scnprintf(&buf[len], PAGE_SIZE - len,
> +			 "%d\n", curr_bitstream);
> +	return len;
> +}
> +
> +/**
> + * show_card_next_bitstream() - Show the next activated bitstream
> + *
> + * IO_SLC_CFGREG_SOFTRESET: This register can only be accessed by the PF.
> + */
> +static ssize_t show_card_next_bitstream(struct device *dev,
> +					struct device_attribute *attr,
> +					char *buf)
> +{
> +	ssize_t len = 0;
> +	int next_bitstream;
> +	struct genwqe_dev *cd = dev_get_drvdata(dev);
> +
> +	switch ((cd->softreset & 0xCull) >> 2) {
> +	case 0x2:
> +		next_bitstream =  0;
> +		break;
> +	case 0x3:
> +		next_bitstream =  1;
> +		break;
> +	default:
> +		next_bitstream = -1;
> +		break;		/* error */
> +	}
> +	len += scnprintf(&buf[len], PAGE_SIZE - len,
> +			 "%d\n", next_bitstream);
> +	return len;
> +}
> +
> +static ssize_t store_card_next_bitstream(struct device *dev,
> +					 struct device_attribute *attr,
> +					 const char *buf, size_t count)
> +{
> +	u64 partition;
> +	struct genwqe_dev *cd = dev_get_drvdata(dev);
> +
> +	if (kstrtoull(buf, 0, &partition) < 0)
> +		return -EINVAL;

Does this give a type error? partition should be unsigned long long,
which is _at least_ 64 bits.

> +
> +	switch (partition) {
> +	case 0x0:
> +		cd->softreset = 0x78ull;
> +		break;
> +	case 0x1:
> +		cd->softreset = 0x7cull;
> +		break;
> +	default:
> +		return -EINVAL;
> +	}
> +
> +	__genwqe_writeq(cd, IO_SLC_CFGREG_SOFTRESET, cd->softreset);
> +	return count;
> +}
> +
> +/*
> + * Create device_attribute structures / params: name, mode, show, store
> + * additional flag if valid in VF
> + */
> +struct genwqe_dev_attrib {
> +	struct device_attribute att;	/* sysfs entry attributes */
> +	int vf;				/* may exist in VF or not */
> +};
> +
> +static struct genwqe_dev_attrib dev_attr_tab[] = {
> +	{__ATTR(tempsens,       S_IRUGO, show_card_tempsens, NULL), 0},
> +	{__ATTR(next_bitstream, (S_IRUGO | S_IWUSR),
> +		show_card_next_bitstream, store_card_next_bitstream), 0},
> +	{__ATTR(curr_bitstream, S_IRUGO, show_card_curr_bitstream, NULL), 0},
> +	{__ATTR(cpld_version,   S_IRUGO, show_cpld_version, NULL), 0},
> +	{__ATTR(base_clock,	S_IRUGO, show_card_base_clock, NULL), 0},
> +
> +	{__ATTR(driver,		S_IRUGO, show_card_driver, NULL), 1},
> +	{__ATTR(type,		S_IRUGO, show_card_type, NULL), 1},
> +	{__ATTR(version,	S_IRUGO, show_card_version, NULL), 1},
> +	{__ATTR(appid,		S_IRUGO, show_card_appid, NULL), 1},
> +	{__ATTR(status,		S_IRUGO, show_card_status, NULL), 1},
> +};
> +
> +/**
> + * create_card_sysfs() - Setup sysfs entries of the card device
> + *
> + * VFs have restricted mmio capabilities, so not all sysfs entries
> + * are allowed in VFs.
> + */
> +int create_card_sysfs(struct genwqe_dev *cd)

This is extern, and has a very generic name. Prefix it with genwqe or
something. Same for the function below, and for any other extern symbols
you have.



  parent reply	other threads:[~2013-10-31  3:49 UTC|newest]

Thread overview: 21+ messages / expand[flat|nested]  mbox.gz  Atom feed  top
2013-10-30  9:32 [PATCH] Generic WorkQueue Engine (GenWQE) device driver (v4) Frank Haverkamp
2013-10-30  9:32 ` Frank Haverkamp
2013-10-30 17:35   ` Greg KH
2013-10-30 20:38     ` Ryan Mallon
2013-11-04 16:19       ` Frank Haverkamp
2013-11-04 16:18     ` Frank Haverkamp
2013-10-30 17:36   ` Greg KH
2013-11-04 16:20     ` Frank Haverkamp
2013-10-30 17:37   ` Greg KH
2013-11-04 16:30     ` Frank Haverkamp
2013-10-30 17:39   ` Greg KH
2013-10-30 17:44   ` Greg KH
2013-11-04 16:41     ` Frank Haverkamp
2013-11-04 22:15       ` Greg KH
2013-11-05  7:16         ` Frank Haverkamp
2013-11-05 12:50           ` Greg KH
2013-10-31  3:49   ` Ryan Mallon [this message]
2013-11-04 16:44     ` Frank Haverkamp
2013-11-04 16:45     ` Frank Haverkamp
2013-11-12 13:50 ` Pavel Machek
2013-11-13 12:36   ` Frank Haverkamp

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=5271D340.2090706@gmail.com \
    --to=rmallon@gmail.com \
    --cc=MIJUNG@de.ibm.com \
    --cc=arnd@arndb.de \
    --cc=cascardo@linux.vnet.ibm.com \
    --cc=cody@linux.vnet.ibm.com \
    --cc=gregkh@linuxfoundation.org \
    --cc=haver@linux.vnet.ibm.com \
    --cc=haver@vnet.ibm.com \
    --cc=jsvogt@de.ibm.com \
    --cc=linux-kernel@vger.kernel.org \
    --cc=michael@ibmra.de \
    --cc=mmarek@suse.cz \
    --cc=schwidefsky@de.ibm.com \
    --cc=utz.bacher@de.ibm.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.