* Re: [PATCH v2 07/13] powerpc/eeh: Clean up pci_ers_result handling
From: Michael Ellerman @ 2018-06-04 9:43 UTC (permalink / raw)
To: Sam Bobroff; +Cc: linuxppc-dev
In-Reply-To: <20180604012833.GA6139@tungsten.ozlabs.ibm.com>
Sam Bobroff <sbobroff@linux.ibm.com> writes:
> On Sat, Jun 02, 2018 at 01:40:46AM +1000, Michael Ellerman wrote:
>> Sam Bobroff <sbobroff@linux.ibm.com> writes:
>>
>> > As EEH event handling progresses, a cumulative result of type
>> > pci_ers_result is built up by (some of) the eeh_report_*() functions
>> > using either:
>> > if (rc == PCI_ERS_RESULT_NEED_RESET) *res = rc;
>> > if (*res == PCI_ERS_RESULT_NONE) *res = rc;
>> > or:
>> > if ((*res == PCI_ERS_RESULT_NONE) ||
>> > (*res == PCI_ERS_RESULT_RECOVERED)) *res = rc;
>> > if (*res == PCI_ERS_RESULT_DISCONNECT &&
>> > rc == PCI_ERS_RESULT_NEED_RESET) *res = rc;
>> > (Where *res is the accumulator.)
>> >
>> > However, the intent is not immediately clear and the result in some
>> > situations is order dependent.
>> >
>> > Address this by assigning a priority to each result value, and always
>> > merging to the highest priority. This renders the intent clear, and
>> > provides a stable value for all orderings.
>> >
>> > Signed-off-by: Sam Bobroff <sbobroff@linux.ibm.com>
>> > ---
>> > ====== v1 -> v2: ======
>> >
>> > * Added the value, and missing newline, to some WARN()s.
>> > * Improved name of merge_result() to pci_ers_merge_result().
>> > * Adjusted the result priorities so that unknown doesn't overlap with _NONE.
>>
>> These === markers seem to have confused patchwork, they ended up in the
>> patch, and then git put them in the changelog.
>>
>> http://patchwork.ozlabs.org/patch/920194/
>>
>> The usual format is just something like:
>>
>> v2 - Added the value, and missing newline, to some WARN()s.
>> - Improved name of merge_result() to pci_ers_merge_result().
>> - Adjusted the result priorities so that unknown doesn't overlap with _NONE.
>>
>> cheers
>
> Oh! I'll change it!
Thanks.
cheers
^ permalink raw reply
* Re: [RFC V2] virtio: Add platform specific DMA API translation for virito devices
From: David Gibson @ 2018-06-04 8:57 UTC (permalink / raw)
To: Benjamin Herrenschmidt
Cc: Michael S. Tsirkin, Anshuman Khandual, virtualization,
linux-kernel, linuxppc-dev, aik, robh, joe, elfring, jasowang,
mpe, hch
In-Reply-To: <f77638ddef3af52dd71341083707c9e3745dd505.camel@kernel.crashing.org>
[-- Attachment #1: Type: text/plain, Size: 1476 bytes --]
On Thu, May 24, 2018 at 08:27:04AM +1000, Benjamin Herrenschmidt wrote:
> On Wed, 2018-05-23 at 21:50 +0300, Michael S. Tsirkin wrote:
>
> > I re-read that discussion and I'm still unclear on the
> > original question, since I got several apparently
> > conflicting answers.
> >
> > I asked:
> >
> > Why isn't setting VIRTIO_F_IOMMU_PLATFORM on the
> > hypervisor side sufficient?
>
> I thought I had replied to this...
>
> There are a couple of reasons:
>
> - First qemu doesn't know that the guest will switch to "secure mode"
> in advance. There is no difference between a normal and a secure
> partition until the partition does the magic UV call to "enter secure
> mode" and qemu doesn't see any of it. So who can set the flag here ?
This seems weird to me. As a rule HV calls should go through qemu -
or be allowed to go directly to KVM *by* qemu. We generally reserve
the latter for hot path things. Since this isn't a hot path, having
the call handled directly by the kernel seems wrong.
Unless a "UV call" is something different I don't know about.
> - Second, when using VIRTIO_F_IOMMU_PLATFORM, we also make qemu (or
> vhost) go through the emulated MMIO for every access to the guest,
> which adds additional overhead.
>
--
David Gibson | I'll have my music baroque, and my code
david AT gibson.dropbear.id.au | minimalist, thank you. NOT _the_ _other_
| _way_ _around_!
http://www.ozlabs.org/~dgibson
[-- Attachment #2: signature.asc --]
[-- Type: application/pgp-signature, Size: 833 bytes --]
^ permalink raw reply
* Re: powerpc/powernv: copy/paste - Mask XERS0 bit in CR
From: Michael Ellerman @ 2018-06-04 9:11 UTC (permalink / raw)
To: Haren Myneni; +Cc: linuxppc-dev, sukadev
In-Reply-To: <5B14A0DB.9040704@linux.vnet.ibm.com>
Haren Myneni <haren@linux.vnet.ibm.com> writes:
> On 06/03/2018 03:48 AM, Michael Ellerman wrote:
>> Haren Myneni <haren@linux.vnet.ibm.com> writes:
>>> NX can set 3rd bit in CR register for XER[SO] (Summation overflow)
>>> which is not related to paste request. The current paste function
>>> returns failure for the successful request when this bit is set.
>>> So mask this bit and check the proper return status.
>>>
>>> Fixes: 2392c8c8c045 ("powerpc/powernv/vas: Define copy/paste interfaces")
>>> Cc: stable@vger.kernel.org # v4.14+
>>> Signed-off-by: Haren Myneni <haren@us.ibm.com>
>>>
>>> diff --git a/arch/powerpc/platforms/powernv/copy-paste.h b/arch/powerpc/platforms/powernv/copy-paste.h
>>> index c9a5036..82392e3 100644
>>> --- a/arch/powerpc/platforms/powernv/copy-paste.h
>>> +++ b/arch/powerpc/platforms/powernv/copy-paste.h
>>> @@ -9,7 +9,8 @@
>>> #include <asm/ppc-opcode.h>
>>>
>>> #define CR0_SHIFT 28
>>> -#define CR0_MASK 0xF
>>> +#define CR0_MASK 0xE /* 3rd bit undefined or set for XER[SO] */
>>> +
>>> /*
>>> * Copy/paste instructions:
>>> *
>>
>> Unfortunately this no longer applies to my next branch, because those
>> macros have been moved out of this header as part of an unrelated patch.
>>
>> The following patch should work instead, can you please confirm by
>> testing it?
>>
>> diff --git a/arch/powerpc/platforms/powernv/copy-paste.h b/arch/powerpc/platforms/powernv/copy-paste.h
>> index 3fa62de96d9c..c46a326776cf 100644
>> --- a/arch/powerpc/platforms/powernv/copy-paste.h
>> +++ b/arch/powerpc/platforms/powernv/copy-paste.h
>> @@ -41,5 +41,7 @@ static inline int vas_paste(void *paste_address, int offset)
>> : "b" (offset), "b" (paste_address)
>> : "memory", "cr0");
>>
>> - return (cr >> CR0_SHIFT) & CR0_MASK;
>> +
>> + /* We mask with 0xE to ignore SO */
>> + return (cr >> CR0_SHIFT) & 0xE;
>> }
>
> Tested with this patch and it works.
Thanks. I sent a new version to the list and will apply that.
cheers
^ permalink raw reply
* [PATCH] powerpc/powernv: copy/paste - Mask SO bit in CR
From: Michael Ellerman @ 2018-06-04 8:33 UTC (permalink / raw)
To: linuxppc-dev
NX can set the 3rd bit in CR register for XER[SO] (Summary overflow)
which is not related to paste request. The current paste function
returns failure for a successful request when this bit is set. So mask
this bit and check the proper return status.
Fixes: 2392c8c8c045 ("powerpc/powernv/vas: Define copy/paste interfaces")
Cc: stable@vger.kernel.org # v4.14+
Signed-off-by: Haren Myneni <haren@us.ibm.com>
Signed-off-by: Michael Ellerman <mpe@ellerman.id.au>
---
arch/powerpc/platforms/powernv/copy-paste.h | 3 ++-
1 file changed, 2 insertions(+), 1 deletion(-)
diff --git a/arch/powerpc/platforms/powernv/copy-paste.h b/arch/powerpc/platforms/powernv/copy-paste.h
index 3fa62de96d9c..cb36f9fbcef3 100644
--- a/arch/powerpc/platforms/powernv/copy-paste.h
+++ b/arch/powerpc/platforms/powernv/copy-paste.h
@@ -41,5 +41,6 @@ static inline int vas_paste(void *paste_address, int offset)
: "b" (offset), "b" (paste_address)
: "memory", "cr0");
- return (cr >> CR0_SHIFT) & CR0_MASK;
+ /* We mask with 0xE to ignore SO */
+ return (cr >> CR0_SHIFT) & 0xE;
}
--
2.14.1
^ permalink raw reply related
* Re: [PATCH v2] cpuidle/powernv : Add Description for cpuidle state
From: Benjamin Herrenschmidt @ 2018-06-04 9:04 UTC (permalink / raw)
To: Abhishek Goel, rjw, daniel.lezcano, paulus, mpe, linux-pm,
linuxppc-dev, linux-kernel
Cc: stewart
In-Reply-To: <20180604081758.104201-1-huntbag@linux.vnet.ibm.com>
On Mon, 2018-06-04 at 13:47 +0530, Abhishek Goel wrote:
> + if (of_property_read_string_array(power_mgt,
> + "ibm,cpu-idle-state-descs", descs, dt_idle_states) < 0) {
> + of_property_read_string_array(power_mgt,
> + "ibm,cpu-idle-state-names", descs, dt_idle_states);
> + pr_warn("cpuidle-powernv: missing ibm,cpu-idle-state-descs in DT\n"
> + "Name will be used for description\n");
> + }
>
> /*
Is this a new property ? I'm not fan of adding yet another of those
silly arrays.
I would say this is the right time now to switch over to a node per
state instead, as we discussed with Vaidy.
Additionally, while doing that, we can provide the versioning mechanism
I proposed so we can deal with state specific issues and erratas.
Cheers,
Ben.
^ permalink raw reply
* [PATCH v2] cpuidle/powernv : Add Description for cpuidle state
From: Abhishek Goel @ 2018-06-04 8:17 UTC (permalink / raw)
To: rjw, daniel.lezcano, benh, paulus, mpe, linux-pm, linuxppc-dev,
linux-kernel
Cc: stewart, Abhishek Goel
Names of cpuidle states were being used for description of states
in POWER as no descriptions were added in device tree. This patch
reads description for idle states which have been added in device
tree.
The description for idle states in case of POWER can be printed
using "cpupower monitor -l" or "cpupower idle-info".
Signed-off-by: Abhishek Goel <huntbag@linux.vnet.ibm.com>
---
The skiboot patch which adds description for idle states in device tree
can be found here: https://patchwork.ozlabs.org/patch/924879/
drivers/cpuidle/cpuidle-powernv.c | 19 +++++++++++++++----
include/linux/cpuidle.h | 2 +-
2 files changed, 16 insertions(+), 5 deletions(-)
diff --git a/drivers/cpuidle/cpuidle-powernv.c b/drivers/cpuidle/cpuidle-powernv.c
index 1a8234e706bc..08d8b0953a14 100644
--- a/drivers/cpuidle/cpuidle-powernv.c
+++ b/drivers/cpuidle/cpuidle-powernv.c
@@ -133,7 +133,7 @@ static int stop_loop(struct cpuidle_device *dev,
static struct cpuidle_state powernv_states[CPUIDLE_STATE_MAX] = {
{ /* Snooze */
.name = "snooze",
- .desc = "snooze",
+ .desc = "idle polling state",
.exit_latency = 0,
.target_residency = 0,
.enter = snooze_loop },
@@ -206,6 +206,7 @@ static int powernv_cpuidle_driver_init(void)
}
static inline void add_powernv_state(int index, const char *name,
+ const char *desc,
unsigned int flags,
int (*idle_fn)(struct cpuidle_device *,
struct cpuidle_driver *,
@@ -215,7 +216,7 @@ static inline void add_powernv_state(int index, const char *name,
u64 psscr_val, u64 psscr_mask)
{
strlcpy(powernv_states[index].name, name, CPUIDLE_NAME_LEN);
- strlcpy(powernv_states[index].desc, name, CPUIDLE_NAME_LEN);
+ strlcpy(powernv_states[index].desc, desc, CPUIDLE_DESC_LEN);
powernv_states[index].flags = flags;
powernv_states[index].target_residency = target_residency;
powernv_states[index].exit_latency = exit_latency;
@@ -250,6 +251,7 @@ static int powernv_add_idle_states(void)
u64 psscr_val[CPUIDLE_STATE_MAX];
u64 psscr_mask[CPUIDLE_STATE_MAX];
const char *names[CPUIDLE_STATE_MAX];
+ const char *descs[CPUIDLE_STATE_MAX];
u32 has_stop_states = 0;
int i, rc;
u32 supported_flags = pnv_get_supported_cpuidle_states();
@@ -311,6 +313,13 @@ static int powernv_add_idle_states(void)
pr_warn("cpuidle-powernv: missing ibm,cpu-idle-state-names in DT\n");
goto out;
}
+ if (of_property_read_string_array(power_mgt,
+ "ibm,cpu-idle-state-descs", descs, dt_idle_states) < 0) {
+ of_property_read_string_array(power_mgt,
+ "ibm,cpu-idle-state-names", descs, dt_idle_states);
+ pr_warn("cpuidle-powernv: missing ibm,cpu-idle-state-descs in DT\n"
+ "Name will be used for description\n");
+ }
/*
* If the idle states use stop instruction, probe for psscr values
@@ -414,10 +423,11 @@ static int powernv_add_idle_states(void)
target_residency = 100;
/* Add NAP state */
add_powernv_state(nr_idle_states, "Nap",
+ "stop processor execution",
CPUIDLE_FLAG_NONE, nap_loop,
target_residency, exit_latency, 0, 0);
} else if (has_stop_states && !stops_timebase) {
- add_powernv_state(nr_idle_states, names[i],
+ add_powernv_state(nr_idle_states, names[i], descs[i],
CPUIDLE_FLAG_NONE, stop_loop,
target_residency, exit_latency,
psscr_val[i], psscr_mask[i]);
@@ -434,11 +444,12 @@ static int powernv_add_idle_states(void)
target_residency = 300000;
/* Add FASTSLEEP state */
add_powernv_state(nr_idle_states, "FastSleep",
+ "Core and L2 clock gating",
CPUIDLE_FLAG_TIMER_STOP,
fastsleep_loop,
target_residency, exit_latency, 0, 0);
} else if (has_stop_states && stops_timebase) {
- add_powernv_state(nr_idle_states, names[i],
+ add_powernv_state(nr_idle_states, names[i], descs[i],
CPUIDLE_FLAG_TIMER_STOP, stop_loop,
target_residency, exit_latency,
psscr_val[i], psscr_mask[i]);
diff --git a/include/linux/cpuidle.h b/include/linux/cpuidle.h
index 1eefabf1621f..5094755cb132 100644
--- a/include/linux/cpuidle.h
+++ b/include/linux/cpuidle.h
@@ -17,7 +17,7 @@
#define CPUIDLE_STATE_MAX 10
#define CPUIDLE_NAME_LEN 16
-#define CPUIDLE_DESC_LEN 32
+#define CPUIDLE_DESC_LEN 60
struct module;
--
2.14.1
^ permalink raw reply related
* [PATCH 09/10] dpaa_eth: add support for hardware timestamping
From: Yangbo Lu @ 2018-06-04 7:08 UTC (permalink / raw)
To: netdev, madalin.bucur, Richard Cochran, Rob Herring, Shawn Guo,
David S . Miller
Cc: devicetree, linuxppc-dev, linux-arm-kernel, linux-kernel,
Yangbo Lu
In-Reply-To: <20180604070837.19265-1-yangbo.lu@nxp.com>
This patch is to add hardware timestamping support
for dpaa_eth. On Rx, timestamping is enabled for
all frames. On Tx, we only instruct the hardware
to timestamp the frames marked accordingly by the
stack.
Signed-off-by: Yangbo Lu <yangbo.lu@nxp.com>
---
drivers/net/ethernet/freescale/dpaa/Kconfig | 12 +++
drivers/net/ethernet/freescale/dpaa/dpaa_eth.c | 119 +++++++++++++++++++++++-
drivers/net/ethernet/freescale/dpaa/dpaa_eth.h | 5 +
3 files changed, 133 insertions(+), 3 deletions(-)
diff --git a/drivers/net/ethernet/freescale/dpaa/Kconfig b/drivers/net/ethernet/freescale/dpaa/Kconfig
index a654736..da34138 100644
--- a/drivers/net/ethernet/freescale/dpaa/Kconfig
+++ b/drivers/net/ethernet/freescale/dpaa/Kconfig
@@ -8,3 +8,15 @@ menuconfig FSL_DPAA_ETH
supporting the Freescale QorIQ chips.
Depends on Freescale Buffer Manager and Queue Manager
driver and Frame Manager Driver.
+
+if FSL_DPAA_ETH
+config FSL_DPAA_ETH_TS
+ bool "DPAA hardware timestamping support"
+ select PTP_1588_CLOCK_QORIQ
+ default n
+ help
+ Enable DPAA hardware timestamping support.
+ This option is useful for applications to get
+ hardware time stamps on the Ethernet packets
+ using the SO_TIMESTAMPING API.
+endif
diff --git a/drivers/net/ethernet/freescale/dpaa/dpaa_eth.c b/drivers/net/ethernet/freescale/dpaa/dpaa_eth.c
index fd43f98..864cfb0 100644
--- a/drivers/net/ethernet/freescale/dpaa/dpaa_eth.c
+++ b/drivers/net/ethernet/freescale/dpaa/dpaa_eth.c
@@ -1168,7 +1168,11 @@ static int dpaa_eth_init_tx_port(struct fman_port *port, struct dpaa_fq *errq,
buf_prefix_content.priv_data_size = buf_layout->priv_data_size;
buf_prefix_content.pass_prs_result = true;
buf_prefix_content.pass_hash_result = true;
+#ifdef CONFIG_FSL_DPAA_ETH_TS
+ buf_prefix_content.pass_time_stamp = true;
+#else
buf_prefix_content.pass_time_stamp = false;
+#endif
buf_prefix_content.data_align = DPAA_FD_DATA_ALIGNMENT;
params.specific_params.non_rx_params.err_fqid = errq->fqid;
@@ -1210,7 +1214,11 @@ static int dpaa_eth_init_rx_port(struct fman_port *port, struct dpaa_bp **bps,
buf_prefix_content.priv_data_size = buf_layout->priv_data_size;
buf_prefix_content.pass_prs_result = true;
buf_prefix_content.pass_hash_result = true;
+#ifdef CONFIG_FSL_DPAA_ETH_TS
+ buf_prefix_content.pass_time_stamp = true;
+#else
buf_prefix_content.pass_time_stamp = false;
+#endif
buf_prefix_content.data_align = DPAA_FD_DATA_ALIGNMENT;
rx_p = ¶ms.specific_params.rx_params;
@@ -1592,6 +1600,18 @@ static int dpaa_eth_refill_bpools(struct dpaa_priv *priv)
return 0;
}
+#ifdef CONFIG_FSL_DPAA_ETH_TS
+static int dpaa_get_tstamp_ns(struct net_device *net_dev, u64 *ns,
+ struct fman_port *port, const void *data)
+{
+ if (!fman_port_get_tstamp_field(port, data, ns)) {
+ be64_to_cpus(ns);
+ return 0;
+ }
+ return -EINVAL;
+}
+#endif
+
/* Cleanup function for outgoing frame descriptors that were built on Tx path,
* either contiguous frames or scatter/gather ones.
* Skb freeing is not handled here.
@@ -1615,6 +1635,24 @@ static int dpaa_eth_refill_bpools(struct dpaa_priv *priv)
skbh = (struct sk_buff **)phys_to_virt(addr);
skb = *skbh;
+#ifdef CONFIG_FSL_DPAA_ETH_TS
+ if (priv->tx_tstamp &&
+ skb_shinfo(skb)->tx_flags & SKBTX_HW_TSTAMP) {
+ struct skb_shared_hwtstamps shhwtstamps;
+ u64 ns;
+
+ memset(&shhwtstamps, 0, sizeof(shhwtstamps));
+
+ if (!dpaa_get_tstamp_ns(priv->net_dev, &ns,
+ priv->mac_dev->port[TX],
+ (void *)skbh)) {
+ shhwtstamps.hwtstamp = ns_to_ktime(ns);
+ skb_tstamp_tx(skb, &shhwtstamps);
+ } else {
+ dev_warn(dev, "dpaa_get_tstamp_ns failed!\n");
+ }
+ }
+#endif
if (unlikely(qm_fd_get_format(fd) == qm_fd_sg)) {
nr_frags = skb_shinfo(skb)->nr_frags;
dma_unmap_single(dev, addr, qm_fd_get_offset(fd) +
@@ -2086,6 +2124,14 @@ static int dpaa_start_xmit(struct sk_buff *skb, struct net_device *net_dev)
if (unlikely(err < 0))
goto skb_to_fd_failed;
+#ifdef CONFIG_FSL_DPAA_ETH_TS
+ if (priv->tx_tstamp &&
+ skb_shinfo(skb)->tx_flags & SKBTX_HW_TSTAMP) {
+ fd.cmd |= FM_FD_CMD_UPD;
+ skb_shinfo(skb)->tx_flags |= SKBTX_IN_PROGRESS;
+ }
+#endif
+
if (likely(dpaa_xmit(priv, percpu_stats, queue_mapping, &fd) == 0))
return NETDEV_TX_OK;
@@ -2304,6 +2350,23 @@ static enum qman_cb_dqrr_result rx_default_dqrr(struct qman_portal *portal,
if (!skb)
return qman_cb_dqrr_consume;
+#ifdef CONFIG_FSL_DPAA_ETH_TS
+ if (priv->rx_tstamp) {
+ struct skb_shared_hwtstamps *shhwtstamps;
+ u64 ns;
+
+ shhwtstamps = skb_hwtstamps(skb);
+ memset(shhwtstamps, 0, sizeof(*shhwtstamps));
+
+ if (!dpaa_get_tstamp_ns(priv->net_dev, &ns,
+ priv->mac_dev->port[RX],
+ vaddr))
+ shhwtstamps->hwtstamp = ns_to_ktime(ns);
+ else
+ dev_warn(net_dev->dev.parent, "dpaa_get_tstamp_ns failed!\n");
+ }
+#endif
+
skb->protocol = eth_type_trans(skb, net_dev);
if (net_dev->features & NETIF_F_RXHASH && priv->keygen_in_use &&
@@ -2523,11 +2586,61 @@ static int dpaa_eth_stop(struct net_device *net_dev)
return err;
}
+#ifdef CONFIG_FSL_DPAA_ETH_TS
+static int dpaa_ts_ioctl(struct net_device *dev, struct ifreq *rq, int cmd)
+{
+ struct dpaa_priv *priv = netdev_priv(dev);
+ struct hwtstamp_config config;
+
+ if (copy_from_user(&config, rq->ifr_data, sizeof(config)))
+ return -EFAULT;
+
+ switch (config.tx_type) {
+ case HWTSTAMP_TX_OFF:
+ /* Couldn't disable rx/tx timestamping separately.
+ * Do nothing here.
+ */
+ priv->tx_tstamp = false;
+ break;
+ case HWTSTAMP_TX_ON:
+ priv->mac_dev->set_tstamp(priv->mac_dev->fman_mac, true);
+ priv->tx_tstamp = true;
+ break;
+ default:
+ return -ERANGE;
+ }
+
+ if (config.rx_filter == HWTSTAMP_FILTER_NONE) {
+ /* Couldn't disable rx/tx timestamping separately.
+ * Do nothing here.
+ */
+ priv->rx_tstamp = false;
+ } else {
+ priv->mac_dev->set_tstamp(priv->mac_dev->fman_mac, true);
+ priv->rx_tstamp = true;
+ /* TS is set for all frame types, not only those requested */
+ config.rx_filter = HWTSTAMP_FILTER_ALL;
+ }
+
+ return copy_to_user(rq->ifr_data, &config, sizeof(config)) ?
+ -EFAULT : 0;
+}
+#endif /* CONFIG_FSL_DPAA_ETH_TS */
+
static int dpaa_ioctl(struct net_device *net_dev, struct ifreq *rq, int cmd)
{
- if (!net_dev->phydev)
- return -EINVAL;
- return phy_mii_ioctl(net_dev->phydev, rq, cmd);
+ int ret = -EINVAL;
+
+ if (cmd == SIOCGMIIREG) {
+ if (net_dev->phydev)
+ return phy_mii_ioctl(net_dev->phydev, rq, cmd);
+ }
+
+#ifdef CONFIG_FSL_DPAA_ETH_TS
+ if (cmd == SIOCSHWTSTAMP)
+ return dpaa_ts_ioctl(net_dev, rq, cmd);
+#endif
+ return ret;
}
static const struct net_device_ops dpaa_ops = {
diff --git a/drivers/net/ethernet/freescale/dpaa/dpaa_eth.h b/drivers/net/ethernet/freescale/dpaa/dpaa_eth.h
index bd94220..e8214fc 100644
--- a/drivers/net/ethernet/freescale/dpaa/dpaa_eth.h
+++ b/drivers/net/ethernet/freescale/dpaa/dpaa_eth.h
@@ -182,6 +182,11 @@ struct dpaa_priv {
struct dpaa_buffer_layout buf_layout[2];
u16 rx_headroom;
+
+#ifdef CONFIG_FSL_DPAA_ETH_TS
+ bool tx_tstamp; /* Tx timestamping enabled */
+ bool rx_tstamp; /* Rx timestamping enabled */
+#endif
};
/* from dpaa_ethtool.c */
--
1.7.1
^ permalink raw reply related
* [PATCH 05/10] arm64: dts: fsl: move ptp timer out of fman
From: Yangbo Lu @ 2018-06-04 7:08 UTC (permalink / raw)
To: netdev, madalin.bucur, Richard Cochran, Rob Herring, Shawn Guo,
David S . Miller
Cc: devicetree, linuxppc-dev, linux-arm-kernel, linux-kernel,
Yangbo Lu
In-Reply-To: <20180604070837.19265-1-yangbo.lu@nxp.com>
This patch is to move ptp timer node out of fman.
Because ptp timer will be probed by ptp_qoriq driver,
it should be an independent device in case of conflict
memory mapping.
Signed-off-by: Yangbo Lu <yangbo.lu@nxp.com>
---
arch/arm64/boot/dts/freescale/qoriq-fman3-0.dtsi | 14 ++++++++------
1 files changed, 8 insertions(+), 6 deletions(-)
diff --git a/arch/arm64/boot/dts/freescale/qoriq-fman3-0.dtsi b/arch/arm64/boot/dts/freescale/qoriq-fman3-0.dtsi
index 4dd0676..e745c0b 100644
--- a/arch/arm64/boot/dts/freescale/qoriq-fman3-0.dtsi
+++ b/arch/arm64/boot/dts/freescale/qoriq-fman3-0.dtsi
@@ -11,13 +11,14 @@ fman0: fman@1a00000 {
#size-cells = <1>;
cell-index = <0>;
compatible = "fsl,fman";
- ranges = <0x0 0x0 0x1a00000 0x100000>;
- reg = <0x0 0x1a00000 0x0 0x100000>;
+ ranges = <0x0 0x0 0x1a00000 0xfe000>;
+ reg = <0x0 0x1a00000 0x0 0xfe000>;
interrupts = <GIC_SPI 44 IRQ_TYPE_LEVEL_HIGH>,
<GIC_SPI 45 IRQ_TYPE_LEVEL_HIGH>;
clocks = <&clockgen 3 0>;
clock-names = "fmanclk";
fsl,qman-channel-range = <0x800 0x10>;
+ ptimer-handle = <&ptp_timer0>;
muram@0 {
compatible = "fsl,fman-muram";
@@ -73,9 +74,10 @@ fman0: fman@1a00000 {
compatible = "fsl,fman-memac-mdio", "fsl,fman-xmdio";
reg = <0xfd000 0x1000>;
};
+};
- ptp_timer0: ptp-timer@fe000 {
- compatible = "fsl,fman-ptp-timer";
- reg = <0xfe000 0x1000>;
- };
+ptp_timer0: ptp-timer@1afe000 {
+ compatible = "fsl,fman-ptp-timer";
+ reg = <0x1afe000 0x1000>;
+ interrupts = <GIC_SPI 44 IRQ_TYPE_LEVEL_HIGH>;
};
--
1.7.1
^ permalink raw reply related
* [PATCH 10/10] dpaa_eth: add the get_ts_info interface for ethtool
From: Yangbo Lu @ 2018-06-04 7:08 UTC (permalink / raw)
To: netdev, madalin.bucur, Richard Cochran, Rob Herring, Shawn Guo,
David S . Miller
Cc: devicetree, linuxppc-dev, linux-arm-kernel, linux-kernel,
Yangbo Lu
In-Reply-To: <20180604070837.19265-1-yangbo.lu@nxp.com>
Added the get_ts_info interface for ethtool to check
the timestamping capability.
Signed-off-by: Yangbo Lu <yangbo.lu@nxp.com>
---
drivers/net/ethernet/freescale/dpaa/dpaa_ethtool.c | 44 ++++++++++++++++++++
1 files changed, 44 insertions(+), 0 deletions(-)
diff --git a/drivers/net/ethernet/freescale/dpaa/dpaa_ethtool.c b/drivers/net/ethernet/freescale/dpaa/dpaa_ethtool.c
index 2f933b6..a20b434 100644
--- a/drivers/net/ethernet/freescale/dpaa/dpaa_ethtool.c
+++ b/drivers/net/ethernet/freescale/dpaa/dpaa_ethtool.c
@@ -32,6 +32,9 @@
#define pr_fmt(fmt) KBUILD_MODNAME ": " fmt
#include <linux/string.h>
+#include <linux/of_platform.h>
+#include <linux/net_tstamp.h>
+#include <linux/fsl/ptp_qoriq.h>
#include "dpaa_eth.h"
#include "mac.h"
@@ -515,6 +518,46 @@ static int dpaa_set_rxnfc(struct net_device *dev, struct ethtool_rxnfc *cmd)
return ret;
}
+static int dpaa_get_ts_info(struct net_device *net_dev,
+ struct ethtool_ts_info *info)
+{
+ struct device *dev = net_dev->dev.parent;
+ struct device_node *mac_node = dev->of_node;
+ struct device_node *fman_node = NULL, *ptp_node = NULL;
+ struct platform_device *ptp_dev = NULL;
+ struct qoriq_ptp *ptp = NULL;
+
+ fman_node = of_get_parent(mac_node);
+ if (fman_node)
+ ptp_node = of_parse_phandle(fman_node, "ptimer-handle", 0);
+
+ if (ptp_node)
+ ptp_dev = of_find_device_by_node(ptp_node);
+
+ if (ptp_dev)
+ ptp = platform_get_drvdata(ptp_dev);
+
+ if (ptp) {
+ info->phc_index = ptp->phc_index;
+#ifdef CONFIG_FSL_DPAA_ETH_TS
+ info->so_timestamping = SOF_TIMESTAMPING_TX_HARDWARE |
+ SOF_TIMESTAMPING_RX_HARDWARE |
+ SOF_TIMESTAMPING_RAW_HARDWARE;
+ info->tx_types = (1 << HWTSTAMP_TX_OFF) |
+ (1 << HWTSTAMP_TX_ON);
+ info->rx_filters = (1 << HWTSTAMP_FILTER_NONE) |
+ (1 << HWTSTAMP_FILTER_ALL);
+ return 0;
+#endif
+ } else {
+ info->phc_index = -1;
+ }
+
+ info->so_timestamping = SOF_TIMESTAMPING_RX_SOFTWARE |
+ SOF_TIMESTAMPING_SOFTWARE;
+ return 0;
+}
+
const struct ethtool_ops dpaa_ethtool_ops = {
.get_drvinfo = dpaa_get_drvinfo,
.get_msglevel = dpaa_get_msglevel,
@@ -530,4 +573,5 @@ static int dpaa_set_rxnfc(struct net_device *dev, struct ethtool_rxnfc *cmd)
.set_link_ksettings = dpaa_set_link_ksettings,
.get_rxnfc = dpaa_get_rxnfc,
.set_rxnfc = dpaa_set_rxnfc,
+ .get_ts_info = dpaa_get_ts_info,
};
--
1.7.1
^ permalink raw reply related
* [PATCH 02/10] ptp: support DPAA FMan 1588 timer in ptp_qoriq
From: Yangbo Lu @ 2018-06-04 7:08 UTC (permalink / raw)
To: netdev, madalin.bucur, Richard Cochran, Rob Herring, Shawn Guo,
David S . Miller
Cc: devicetree, linuxppc-dev, linux-arm-kernel, linux-kernel,
Yangbo Lu
In-Reply-To: <20180604070837.19265-1-yangbo.lu@nxp.com>
This patch is to support DPAA (Data Path Acceleration Architecture)
1588 timer by adding "fsl,fman-ptp-timer" compatible, sharing
interrupt with FMan, adding FSL_DPAA_ETH dependency, and fixing
up register offset.
Signed-off-by: Yangbo Lu <yangbo.lu@nxp.com>
---
drivers/ptp/Kconfig | 2 +-
drivers/ptp/ptp_qoriq.c | 104 ++++++++++++++++++++++++++---------------
include/linux/fsl/ptp_qoriq.h | 38 ++++++++++++---
3 files changed, 98 insertions(+), 46 deletions(-)
diff --git a/drivers/ptp/Kconfig b/drivers/ptp/Kconfig
index 474c988..d137c48 100644
--- a/drivers/ptp/Kconfig
+++ b/drivers/ptp/Kconfig
@@ -43,7 +43,7 @@ config PTP_1588_CLOCK_DTE
config PTP_1588_CLOCK_QORIQ
tristate "Freescale QorIQ 1588 timer as PTP clock"
- depends on GIANFAR
+ depends on GIANFAR || FSL_DPAA_ETH
depends on PTP_1588_CLOCK
default y
help
diff --git a/drivers/ptp/ptp_qoriq.c b/drivers/ptp/ptp_qoriq.c
index 1468a16..c4e3545 100644
--- a/drivers/ptp/ptp_qoriq.c
+++ b/drivers/ptp/ptp_qoriq.c
@@ -39,11 +39,12 @@
/* Caller must hold qoriq_ptp->lock. */
static u64 tmr_cnt_read(struct qoriq_ptp *qoriq_ptp)
{
+ struct qoriq_ptp_registers *regs = &qoriq_ptp->regs;
u64 ns;
u32 lo, hi;
- lo = qoriq_read(&qoriq_ptp->regs->tmr_cnt_l);
- hi = qoriq_read(&qoriq_ptp->regs->tmr_cnt_h);
+ lo = qoriq_read(®s->ctrl_regs->tmr_cnt_l);
+ hi = qoriq_read(®s->ctrl_regs->tmr_cnt_h);
ns = ((u64) hi) << 32;
ns |= lo;
return ns;
@@ -52,16 +53,18 @@ static u64 tmr_cnt_read(struct qoriq_ptp *qoriq_ptp)
/* Caller must hold qoriq_ptp->lock. */
static void tmr_cnt_write(struct qoriq_ptp *qoriq_ptp, u64 ns)
{
+ struct qoriq_ptp_registers *regs = &qoriq_ptp->regs;
u32 hi = ns >> 32;
u32 lo = ns & 0xffffffff;
- qoriq_write(&qoriq_ptp->regs->tmr_cnt_l, lo);
- qoriq_write(&qoriq_ptp->regs->tmr_cnt_h, hi);
+ qoriq_write(®s->ctrl_regs->tmr_cnt_l, lo);
+ qoriq_write(®s->ctrl_regs->tmr_cnt_h, hi);
}
/* Caller must hold qoriq_ptp->lock. */
static void set_alarm(struct qoriq_ptp *qoriq_ptp)
{
+ struct qoriq_ptp_registers *regs = &qoriq_ptp->regs;
u64 ns;
u32 lo, hi;
@@ -70,16 +73,18 @@ static void set_alarm(struct qoriq_ptp *qoriq_ptp)
ns -= qoriq_ptp->tclk_period;
hi = ns >> 32;
lo = ns & 0xffffffff;
- qoriq_write(&qoriq_ptp->regs->tmr_alarm1_l, lo);
- qoriq_write(&qoriq_ptp->regs->tmr_alarm1_h, hi);
+ qoriq_write(®s->alarm_regs->tmr_alarm1_l, lo);
+ qoriq_write(®s->alarm_regs->tmr_alarm1_h, hi);
}
/* Caller must hold qoriq_ptp->lock. */
static void set_fipers(struct qoriq_ptp *qoriq_ptp)
{
+ struct qoriq_ptp_registers *regs = &qoriq_ptp->regs;
+
set_alarm(qoriq_ptp);
- qoriq_write(&qoriq_ptp->regs->tmr_fiper1, qoriq_ptp->tmr_fiper1);
- qoriq_write(&qoriq_ptp->regs->tmr_fiper2, qoriq_ptp->tmr_fiper2);
+ qoriq_write(®s->fiper_regs->tmr_fiper1, qoriq_ptp->tmr_fiper1);
+ qoriq_write(®s->fiper_regs->tmr_fiper2, qoriq_ptp->tmr_fiper2);
}
/*
@@ -89,16 +94,17 @@ static void set_fipers(struct qoriq_ptp *qoriq_ptp)
static irqreturn_t isr(int irq, void *priv)
{
struct qoriq_ptp *qoriq_ptp = priv;
+ struct qoriq_ptp_registers *regs = &qoriq_ptp->regs;
struct ptp_clock_event event;
u64 ns;
u32 ack = 0, lo, hi, mask, val;
- val = qoriq_read(&qoriq_ptp->regs->tmr_tevent);
+ val = qoriq_read(®s->ctrl_regs->tmr_tevent);
if (val & ETS1) {
ack |= ETS1;
- hi = qoriq_read(&qoriq_ptp->regs->tmr_etts1_h);
- lo = qoriq_read(&qoriq_ptp->regs->tmr_etts1_l);
+ hi = qoriq_read(®s->etts_regs->tmr_etts1_h);
+ lo = qoriq_read(®s->etts_regs->tmr_etts1_l);
event.type = PTP_CLOCK_EXTTS;
event.index = 0;
event.timestamp = ((u64) hi) << 32;
@@ -108,8 +114,8 @@ static irqreturn_t isr(int irq, void *priv)
if (val & ETS2) {
ack |= ETS2;
- hi = qoriq_read(&qoriq_ptp->regs->tmr_etts2_h);
- lo = qoriq_read(&qoriq_ptp->regs->tmr_etts2_l);
+ hi = qoriq_read(®s->etts_regs->tmr_etts2_h);
+ lo = qoriq_read(®s->etts_regs->tmr_etts2_l);
event.type = PTP_CLOCK_EXTTS;
event.index = 1;
event.timestamp = ((u64) hi) << 32;
@@ -130,16 +136,16 @@ static irqreturn_t isr(int irq, void *priv)
hi = ns >> 32;
lo = ns & 0xffffffff;
spin_lock(&qoriq_ptp->lock);
- qoriq_write(&qoriq_ptp->regs->tmr_alarm2_l, lo);
- qoriq_write(&qoriq_ptp->regs->tmr_alarm2_h, hi);
+ qoriq_write(®s->alarm_regs->tmr_alarm2_l, lo);
+ qoriq_write(®s->alarm_regs->tmr_alarm2_h, hi);
spin_unlock(&qoriq_ptp->lock);
qoriq_ptp->alarm_value = ns;
} else {
- qoriq_write(&qoriq_ptp->regs->tmr_tevent, ALM2);
+ qoriq_write(®s->ctrl_regs->tmr_tevent, ALM2);
spin_lock(&qoriq_ptp->lock);
- mask = qoriq_read(&qoriq_ptp->regs->tmr_temask);
+ mask = qoriq_read(®s->ctrl_regs->tmr_temask);
mask &= ~ALM2EN;
- qoriq_write(&qoriq_ptp->regs->tmr_temask, mask);
+ qoriq_write(®s->ctrl_regs->tmr_temask, mask);
spin_unlock(&qoriq_ptp->lock);
qoriq_ptp->alarm_value = 0;
qoriq_ptp->alarm_interval = 0;
@@ -153,7 +159,7 @@ static irqreturn_t isr(int irq, void *priv)
}
if (ack) {
- qoriq_write(&qoriq_ptp->regs->tmr_tevent, ack);
+ qoriq_write(®s->ctrl_regs->tmr_tevent, ack);
return IRQ_HANDLED;
} else
return IRQ_NONE;
@@ -169,6 +175,7 @@ static int ptp_qoriq_adjfine(struct ptp_clock_info *ptp, long scaled_ppm)
u32 tmr_add;
int neg_adj = 0;
struct qoriq_ptp *qoriq_ptp = container_of(ptp, struct qoriq_ptp, caps);
+ struct qoriq_ptp_registers *regs = &qoriq_ptp->regs;
if (scaled_ppm < 0) {
neg_adj = 1;
@@ -186,7 +193,7 @@ static int ptp_qoriq_adjfine(struct ptp_clock_info *ptp, long scaled_ppm)
tmr_add = neg_adj ? tmr_add - diff : tmr_add + diff;
- qoriq_write(&qoriq_ptp->regs->tmr_add, tmr_add);
+ qoriq_write(®s->ctrl_regs->tmr_add, tmr_add);
return 0;
}
@@ -250,6 +257,7 @@ static int ptp_qoriq_enable(struct ptp_clock_info *ptp,
struct ptp_clock_request *rq, int on)
{
struct qoriq_ptp *qoriq_ptp = container_of(ptp, struct qoriq_ptp, caps);
+ struct qoriq_ptp_registers *regs = &qoriq_ptp->regs;
unsigned long flags;
u32 bit, mask;
@@ -266,23 +274,23 @@ static int ptp_qoriq_enable(struct ptp_clock_info *ptp,
return -EINVAL;
}
spin_lock_irqsave(&qoriq_ptp->lock, flags);
- mask = qoriq_read(&qoriq_ptp->regs->tmr_temask);
+ mask = qoriq_read(®s->ctrl_regs->tmr_temask);
if (on)
mask |= bit;
else
mask &= ~bit;
- qoriq_write(&qoriq_ptp->regs->tmr_temask, mask);
+ qoriq_write(®s->ctrl_regs->tmr_temask, mask);
spin_unlock_irqrestore(&qoriq_ptp->lock, flags);
return 0;
case PTP_CLK_REQ_PPS:
spin_lock_irqsave(&qoriq_ptp->lock, flags);
- mask = qoriq_read(&qoriq_ptp->regs->tmr_temask);
+ mask = qoriq_read(®s->ctrl_regs->tmr_temask);
if (on)
mask |= PP1EN;
else
mask &= ~PP1EN;
- qoriq_write(&qoriq_ptp->regs->tmr_temask, mask);
+ qoriq_write(®s->ctrl_regs->tmr_temask, mask);
spin_unlock_irqrestore(&qoriq_ptp->lock, flags);
return 0;
@@ -313,10 +321,12 @@ static int qoriq_ptp_probe(struct platform_device *dev)
{
struct device_node *node = dev->dev.of_node;
struct qoriq_ptp *qoriq_ptp;
+ struct qoriq_ptp_registers *regs;
struct timespec64 now;
int err = -ENOMEM;
u32 tmr_ctrl;
unsigned long flags;
+ void __iomem *base;
qoriq_ptp = kzalloc(sizeof(*qoriq_ptp), GFP_KERNEL);
if (!qoriq_ptp)
@@ -351,7 +361,7 @@ static int qoriq_ptp_probe(struct platform_device *dev)
pr_err("irq not in device tree\n");
goto no_node;
}
- if (request_irq(qoriq_ptp->irq, isr, 0, DRIVER, qoriq_ptp)) {
+ if (request_irq(qoriq_ptp->irq, isr, IRQF_SHARED, DRIVER, qoriq_ptp)) {
pr_err("request_irq failed\n");
goto no_node;
}
@@ -368,12 +378,27 @@ static int qoriq_ptp_probe(struct platform_device *dev)
spin_lock_init(&qoriq_ptp->lock);
- qoriq_ptp->regs = ioremap(qoriq_ptp->rsrc->start,
- resource_size(qoriq_ptp->rsrc));
- if (!qoriq_ptp->regs) {
+ base = ioremap(qoriq_ptp->rsrc->start,
+ resource_size(qoriq_ptp->rsrc));
+ if (!base) {
pr_err("ioremap ptp registers failed\n");
goto no_ioremap;
}
+
+ qoriq_ptp->base = base;
+
+ if (of_device_is_compatible(node, "fsl,fman-ptp-timer")) {
+ qoriq_ptp->regs.ctrl_regs = base + FMAN_CTRL_REGS_OFFSET;
+ qoriq_ptp->regs.alarm_regs = base + FMAN_ALARM_REGS_OFFSET;
+ qoriq_ptp->regs.fiper_regs = base + FMAN_FIPER_REGS_OFFSET;
+ qoriq_ptp->regs.etts_regs = base + FMAN_ETTS_REGS_OFFSET;
+ } else {
+ qoriq_ptp->regs.ctrl_regs = base + CTRL_REGS_OFFSET;
+ qoriq_ptp->regs.alarm_regs = base + ALARM_REGS_OFFSET;
+ qoriq_ptp->regs.fiper_regs = base + FIPER_REGS_OFFSET;
+ qoriq_ptp->regs.etts_regs = base + ETTS_REGS_OFFSET;
+ }
+
getnstimeofday64(&now);
ptp_qoriq_settime(&qoriq_ptp->caps, &now);
@@ -383,13 +408,14 @@ static int qoriq_ptp_probe(struct platform_device *dev)
spin_lock_irqsave(&qoriq_ptp->lock, flags);
- qoriq_write(&qoriq_ptp->regs->tmr_ctrl, tmr_ctrl);
- qoriq_write(&qoriq_ptp->regs->tmr_add, qoriq_ptp->tmr_add);
- qoriq_write(&qoriq_ptp->regs->tmr_prsc, qoriq_ptp->tmr_prsc);
- qoriq_write(&qoriq_ptp->regs->tmr_fiper1, qoriq_ptp->tmr_fiper1);
- qoriq_write(&qoriq_ptp->regs->tmr_fiper2, qoriq_ptp->tmr_fiper2);
+ regs = &qoriq_ptp->regs;
+ qoriq_write(®s->ctrl_regs->tmr_ctrl, tmr_ctrl);
+ qoriq_write(®s->ctrl_regs->tmr_add, qoriq_ptp->tmr_add);
+ qoriq_write(®s->ctrl_regs->tmr_prsc, qoriq_ptp->tmr_prsc);
+ qoriq_write(®s->fiper_regs->tmr_fiper1, qoriq_ptp->tmr_fiper1);
+ qoriq_write(®s->fiper_regs->tmr_fiper2, qoriq_ptp->tmr_fiper2);
set_alarm(qoriq_ptp);
- qoriq_write(&qoriq_ptp->regs->tmr_ctrl, tmr_ctrl|FIPERST|RTPE|TE|FRD);
+ qoriq_write(®s->ctrl_regs->tmr_ctrl, tmr_ctrl|FIPERST|RTPE|TE|FRD);
spin_unlock_irqrestore(&qoriq_ptp->lock, flags);
@@ -405,7 +431,7 @@ static int qoriq_ptp_probe(struct platform_device *dev)
return 0;
no_clock:
- iounmap(qoriq_ptp->regs);
+ iounmap(qoriq_ptp->base);
no_ioremap:
release_resource(qoriq_ptp->rsrc);
no_resource:
@@ -419,12 +445,13 @@ static int qoriq_ptp_probe(struct platform_device *dev)
static int qoriq_ptp_remove(struct platform_device *dev)
{
struct qoriq_ptp *qoriq_ptp = platform_get_drvdata(dev);
+ struct qoriq_ptp_registers *regs = &qoriq_ptp->regs;
- qoriq_write(&qoriq_ptp->regs->tmr_temask, 0);
- qoriq_write(&qoriq_ptp->regs->tmr_ctrl, 0);
+ qoriq_write(®s->ctrl_regs->tmr_temask, 0);
+ qoriq_write(®s->ctrl_regs->tmr_ctrl, 0);
ptp_clock_unregister(qoriq_ptp->clock);
- iounmap(qoriq_ptp->regs);
+ iounmap(qoriq_ptp->base);
release_resource(qoriq_ptp->rsrc);
free_irq(qoriq_ptp->irq, qoriq_ptp);
kfree(qoriq_ptp);
@@ -434,6 +461,7 @@ static int qoriq_ptp_remove(struct platform_device *dev)
static const struct of_device_id match_table[] = {
{ .compatible = "fsl,etsec-ptp" },
+ { .compatible = "fsl,fman-ptp-timer" },
{},
};
MODULE_DEVICE_TABLE(of, match_table);
diff --git a/include/linux/fsl/ptp_qoriq.h b/include/linux/fsl/ptp_qoriq.h
index b462d9e..dc3dac4 100644
--- a/include/linux/fsl/ptp_qoriq.h
+++ b/include/linux/fsl/ptp_qoriq.h
@@ -11,9 +11,8 @@
/*
* qoriq ptp registers
- * Generated by regen.tcl on Thu May 13 01:38:57 PM CEST 2010
*/
-struct qoriq_ptp_registers {
+struct ctrl_regs {
u32 tmr_ctrl; /* Timer control register */
u32 tmr_tevent; /* Timestamp event register */
u32 tmr_temask; /* Timer event mask register */
@@ -28,22 +27,47 @@ struct qoriq_ptp_registers {
u8 res1[4];
u32 tmroff_h; /* Timer offset high */
u32 tmroff_l; /* Timer offset low */
- u8 res2[8];
+};
+
+struct alarm_regs {
u32 tmr_alarm1_h; /* Timer alarm 1 high register */
u32 tmr_alarm1_l; /* Timer alarm 1 high register */
u32 tmr_alarm2_h; /* Timer alarm 2 high register */
u32 tmr_alarm2_l; /* Timer alarm 2 high register */
- u8 res3[48];
+};
+
+struct fiper_regs {
u32 tmr_fiper1; /* Timer fixed period interval */
u32 tmr_fiper2; /* Timer fixed period interval */
u32 tmr_fiper3; /* Timer fixed period interval */
- u8 res4[20];
+};
+
+struct etts_regs {
u32 tmr_etts1_h; /* Timestamp of general purpose external trigger */
u32 tmr_etts1_l; /* Timestamp of general purpose external trigger */
u32 tmr_etts2_h; /* Timestamp of general purpose external trigger */
u32 tmr_etts2_l; /* Timestamp of general purpose external trigger */
};
+struct qoriq_ptp_registers {
+ struct ctrl_regs __iomem *ctrl_regs;
+ struct alarm_regs __iomem *alarm_regs;
+ struct fiper_regs __iomem *fiper_regs;
+ struct etts_regs __iomem *etts_regs;
+};
+
+/* Offset definitions for the four register groups */
+#define CTRL_REGS_OFFSET 0x0
+#define ALARM_REGS_OFFSET 0x40
+#define FIPER_REGS_OFFSET 0x80
+#define ETTS_REGS_OFFSET 0xa0
+
+#define FMAN_CTRL_REGS_OFFSET 0x80
+#define FMAN_ALARM_REGS_OFFSET 0xb8
+#define FMAN_FIPER_REGS_OFFSET 0xd0
+#define FMAN_ETTS_REGS_OFFSET 0xe0
+
+
/* Bit definitions for the TMR_CTRL register */
#define ALM1P (1<<31) /* Alarm1 output polarity */
#define ALM2P (1<<30) /* Alarm2 output polarity */
@@ -105,10 +129,10 @@ struct qoriq_ptp_registers {
#define DRIVER "ptp_qoriq"
#define DEFAULT_CKSEL 1
#define N_EXT_TS 2
-#define REG_SIZE sizeof(struct qoriq_ptp_registers)
struct qoriq_ptp {
- struct qoriq_ptp_registers __iomem *regs;
+ void __iomem *base;
+ struct qoriq_ptp_registers regs;
spinlock_t lock; /* protects regs */
struct ptp_clock *clock;
struct ptp_clock_info caps;
--
1.7.1
^ permalink raw reply related
* [PATCH 07/10] fsl/fman_port: support getting timestamp field
From: Yangbo Lu @ 2018-06-04 7:08 UTC (permalink / raw)
To: netdev, madalin.bucur, Richard Cochran, Rob Herring, Shawn Guo,
David S . Miller
Cc: devicetree, linuxppc-dev, linux-arm-kernel, linux-kernel,
Yangbo Lu
In-Reply-To: <20180604070837.19265-1-yangbo.lu@nxp.com>
This patch is to add fman_port_get_tstamp_field() interface
to get timestamp field data.
Signed-off-by: Yangbo Lu <yangbo.lu@nxp.com>
---
drivers/net/ethernet/freescale/fman/fman_port.c | 12 ++++++++++++
drivers/net/ethernet/freescale/fman/fman_port.h | 3 +++
2 files changed, 15 insertions(+), 0 deletions(-)
diff --git a/drivers/net/ethernet/freescale/fman/fman_port.c b/drivers/net/ethernet/freescale/fman/fman_port.c
index ce6e24c..86f0094 100644
--- a/drivers/net/ethernet/freescale/fman/fman_port.c
+++ b/drivers/net/ethernet/freescale/fman/fman_port.c
@@ -1731,6 +1731,18 @@ int fman_port_get_hash_result_offset(struct fman_port *port, u32 *offset)
}
EXPORT_SYMBOL(fman_port_get_hash_result_offset);
+int fman_port_get_tstamp_field(struct fman_port *port, const void *data,
+ u64 *tstamp)
+{
+ if (port->buffer_offsets.time_stamp_offset == ILLEGAL_BASE)
+ return -EINVAL;
+
+ *tstamp = *(u64 *)(data + port->buffer_offsets.time_stamp_offset);
+
+ return 0;
+}
+EXPORT_SYMBOL(fman_port_get_tstamp_field);
+
static int fman_port_probe(struct platform_device *of_dev)
{
struct fman_port *port;
diff --git a/drivers/net/ethernet/freescale/fman/fman_port.h b/drivers/net/ethernet/freescale/fman/fman_port.h
index e86ca6a..d10e48d 100644
--- a/drivers/net/ethernet/freescale/fman/fman_port.h
+++ b/drivers/net/ethernet/freescale/fman/fman_port.h
@@ -153,6 +153,9 @@ int fman_port_cfg_buf_prefix_content(struct fman_port *port,
int fman_port_get_hash_result_offset(struct fman_port *port, u32 *offset);
+int fman_port_get_tstamp_field(struct fman_port *port, const void *data,
+ u64 *tstamp);
+
struct fman_port *fman_port_bind(struct device *dev);
#endif /* __FMAN_PORT_H */
--
1.7.1
^ permalink raw reply related
* [PATCH 08/10] fsl/fman: define frame description command UPD
From: Yangbo Lu @ 2018-06-04 7:08 UTC (permalink / raw)
To: netdev, madalin.bucur, Richard Cochran, Rob Herring, Shawn Guo,
David S . Miller
Cc: devicetree, linuxppc-dev, linux-arm-kernel, linux-kernel,
Yangbo Lu
In-Reply-To: <20180604070837.19265-1-yangbo.lu@nxp.com>
Defined frame description command FM_FD_CMD_UPD for
prepended data updating.
Signed-off-by: Yangbo Lu <yangbo.lu@nxp.com>
---
drivers/net/ethernet/freescale/fman/fman.h | 1 +
1 files changed, 1 insertions(+), 0 deletions(-)
diff --git a/drivers/net/ethernet/freescale/fman/fman.h b/drivers/net/ethernet/freescale/fman/fman.h
index bfa02e0..935c317 100644
--- a/drivers/net/ethernet/freescale/fman/fman.h
+++ b/drivers/net/ethernet/freescale/fman/fman.h
@@ -41,6 +41,7 @@
/* Frame queue Context Override */
#define FM_FD_CMD_FCO 0x80000000
#define FM_FD_CMD_RPD 0x40000000 /* Read Prepended Data */
+#define FM_FD_CMD_UPD 0x20000000 /* Update Prepended Data */
#define FM_FD_CMD_DTC 0x10000000 /* Do L4 Checksum */
/* TX-Port: Unsupported Format */
--
1.7.1
^ permalink raw reply related
* [PATCH 03/10] dt-binding: ptp_qoriq: add DPAA FMan support
From: Yangbo Lu @ 2018-06-04 7:08 UTC (permalink / raw)
To: netdev, madalin.bucur, Richard Cochran, Rob Herring, Shawn Guo,
David S . Miller
Cc: devicetree, linuxppc-dev, linux-arm-kernel, linux-kernel,
Yangbo Lu
In-Reply-To: <20180604070837.19265-1-yangbo.lu@nxp.com>
This patch is to add bindings description for DPAA
FMan 1588 timer, and also remove its description in
fsl-fman dt-bindings document.
Signed-off-by: Yangbo Lu <yangbo.lu@nxp.com>
---
Documentation/devicetree/bindings/net/fsl-fman.txt | 25 +-------------------
.../devicetree/bindings/ptp/ptp-qoriq.txt | 15 +++++++++--
2 files changed, 13 insertions(+), 27 deletions(-)
diff --git a/Documentation/devicetree/bindings/net/fsl-fman.txt b/Documentation/devicetree/bindings/net/fsl-fman.txt
index df873d1..74603dd 100644
--- a/Documentation/devicetree/bindings/net/fsl-fman.txt
+++ b/Documentation/devicetree/bindings/net/fsl-fman.txt
@@ -356,30 +356,7 @@ ethernet@e0000 {
============================================================================
FMan IEEE 1588 Node
-DESCRIPTION
-
-The FMan interface to support IEEE 1588
-
-
-PROPERTIES
-
-- compatible
- Usage: required
- Value type: <stringlist>
- Definition: A standard property.
- Must include "fsl,fman-ptp-timer".
-
-- reg
- Usage: required
- Value type: <prop-encoded-array>
- Definition: A standard property.
-
-EXAMPLE
-
-ptp-timer@fe000 {
- compatible = "fsl,fman-ptp-timer";
- reg = <0xfe000 0x1000>;
-};
+Refer to Documentation/devicetree/bindings/ptp/ptp-qoriq.txt
=============================================================================
FMan MDIO Node
diff --git a/Documentation/devicetree/bindings/ptp/ptp-qoriq.txt b/Documentation/devicetree/bindings/ptp/ptp-qoriq.txt
index 0f569d8..c5d0e79 100644
--- a/Documentation/devicetree/bindings/ptp/ptp-qoriq.txt
+++ b/Documentation/devicetree/bindings/ptp/ptp-qoriq.txt
@@ -2,7 +2,8 @@
General Properties:
- - compatible Should be "fsl,etsec-ptp"
+ - compatible Should be "fsl,etsec-ptp" for eTSEC
+ Should be "fsl,fman-ptp-timer" for DPAA FMan
- reg Offset and length of the register set for the device
- interrupts There should be at least two interrupts. Some devices
have as many as four PTP related interrupts.
@@ -43,14 +44,22 @@ Clock Properties:
value, which will be directly written in those bits, that is why,
according to reference manual, the next clock sources can be used:
+ For eTSEC,
<0> - external high precision timer reference clock (TSEC_TMR_CLK
input is used for this purpose);
<1> - eTSEC system clock;
<2> - eTSEC1 transmit clock;
<3> - RTC clock input.
- When this attribute is not used, eTSEC system clock will serve as
- IEEE 1588 timer reference clock.
+ For DPAA FMan,
+ <0> - external high precision timer reference clock (TMR_1588_CLK)
+ <1> - MAC system clock (1/2 FMan clock)
+ <2> - reserved
+ <3> - RTC clock oscillator
+
+ When this attribute is not used, the IEEE 1588 timer reference clock
+ will use the eTSEC system clock (for Gianfar) or the MAC system
+ clock (for DPAA).
Example:
--
1.7.1
^ permalink raw reply related
* [PATCH 06/10] fsl/fman: add set_tstamp interface
From: Yangbo Lu @ 2018-06-04 7:08 UTC (permalink / raw)
To: netdev, madalin.bucur, Richard Cochran, Rob Herring, Shawn Guo,
David S . Miller
Cc: devicetree, linuxppc-dev, linux-arm-kernel, linux-kernel,
Yangbo Lu
In-Reply-To: <20180604070837.19265-1-yangbo.lu@nxp.com>
This patch is to add set_tstamp interface for memac,
dtsec, and 10GEC controllers to configure HW timestamping.
Signed-off-by: Yangbo Lu <yangbo.lu@nxp.com>
---
drivers/net/ethernet/freescale/fman/fman_dtsec.c | 27 ++++++++++++++++++++++
drivers/net/ethernet/freescale/fman/fman_dtsec.h | 1 +
drivers/net/ethernet/freescale/fman/fman_memac.c | 5 ++++
drivers/net/ethernet/freescale/fman/fman_memac.h | 1 +
drivers/net/ethernet/freescale/fman/fman_tgec.c | 21 +++++++++++++++++
drivers/net/ethernet/freescale/fman/fman_tgec.h | 1 +
drivers/net/ethernet/freescale/fman/mac.c | 3 ++
drivers/net/ethernet/freescale/fman/mac.h | 1 +
8 files changed, 60 insertions(+), 0 deletions(-)
diff --git a/drivers/net/ethernet/freescale/fman/fman_dtsec.c b/drivers/net/ethernet/freescale/fman/fman_dtsec.c
index 57b1e2b..1ca543a 100644
--- a/drivers/net/ethernet/freescale/fman/fman_dtsec.c
+++ b/drivers/net/ethernet/freescale/fman/fman_dtsec.c
@@ -123,11 +123,13 @@
#define DTSEC_ECNTRL_R100M 0x00000008
#define DTSEC_ECNTRL_QSGMIIM 0x00000001
+#define TCTRL_TTSE 0x00000040
#define TCTRL_GTS 0x00000020
#define RCTRL_PAL_MASK 0x001f0000
#define RCTRL_PAL_SHIFT 16
#define RCTRL_GHTX 0x00000400
+#define RCTRL_RTSE 0x00000040
#define RCTRL_GRS 0x00000020
#define RCTRL_MPROM 0x00000008
#define RCTRL_RSF 0x00000004
@@ -1136,6 +1138,31 @@ int dtsec_set_allmulti(struct fman_mac *dtsec, bool enable)
return 0;
}
+int dtsec_set_tstamp(struct fman_mac *dtsec, bool enable)
+{
+ struct dtsec_regs __iomem *regs = dtsec->regs;
+ u32 rctrl, tctrl;
+
+ if (!is_init_done(dtsec->dtsec_drv_param))
+ return -EINVAL;
+
+ rctrl = ioread32be(®s->rctrl);
+ tctrl = ioread32be(®s->tctrl);
+
+ if (enable) {
+ rctrl |= RCTRL_RTSE;
+ tctrl |= TCTRL_TTSE;
+ } else {
+ rctrl &= ~RCTRL_RTSE;
+ tctrl &= ~TCTRL_TTSE;
+ }
+
+ iowrite32be(rctrl, ®s->rctrl);
+ iowrite32be(tctrl, ®s->tctrl);
+
+ return 0;
+}
+
int dtsec_del_hash_mac_address(struct fman_mac *dtsec, enet_addr_t *eth_addr)
{
struct dtsec_regs __iomem *regs = dtsec->regs;
diff --git a/drivers/net/ethernet/freescale/fman/fman_dtsec.h b/drivers/net/ethernet/freescale/fman/fman_dtsec.h
index 1a689ad..5149d96 100644
--- a/drivers/net/ethernet/freescale/fman/fman_dtsec.h
+++ b/drivers/net/ethernet/freescale/fman/fman_dtsec.h
@@ -56,5 +56,6 @@ int dtsec_set_exception(struct fman_mac *dtsec,
int dtsec_del_hash_mac_address(struct fman_mac *dtsec, enet_addr_t *eth_addr);
int dtsec_get_version(struct fman_mac *dtsec, u32 *mac_version);
int dtsec_set_allmulti(struct fman_mac *dtsec, bool enable);
+int dtsec_set_tstamp(struct fman_mac *dtsec, bool enable);
#endif /* __DTSEC_H */
diff --git a/drivers/net/ethernet/freescale/fman/fman_memac.c b/drivers/net/ethernet/freescale/fman/fman_memac.c
index 446a97b..bc6eb30 100644
--- a/drivers/net/ethernet/freescale/fman/fman_memac.c
+++ b/drivers/net/ethernet/freescale/fman/fman_memac.c
@@ -964,6 +964,11 @@ int memac_set_allmulti(struct fman_mac *memac, bool enable)
return 0;
}
+int memac_set_tstamp(struct fman_mac *memac, bool enable)
+{
+ return 0; /* Always enabled. */
+}
+
int memac_del_hash_mac_address(struct fman_mac *memac, enet_addr_t *eth_addr)
{
struct memac_regs __iomem *regs = memac->regs;
diff --git a/drivers/net/ethernet/freescale/fman/fman_memac.h b/drivers/net/ethernet/freescale/fman/fman_memac.h
index b5a5033..b2c671e 100644
--- a/drivers/net/ethernet/freescale/fman/fman_memac.h
+++ b/drivers/net/ethernet/freescale/fman/fman_memac.h
@@ -58,5 +58,6 @@ int memac_set_exception(struct fman_mac *memac,
int memac_add_hash_mac_address(struct fman_mac *memac, enet_addr_t *eth_addr);
int memac_del_hash_mac_address(struct fman_mac *memac, enet_addr_t *eth_addr);
int memac_set_allmulti(struct fman_mac *memac, bool enable);
+int memac_set_tstamp(struct fman_mac *memac, bool enable);
#endif /* __MEMAC_H */
diff --git a/drivers/net/ethernet/freescale/fman/fman_tgec.c b/drivers/net/ethernet/freescale/fman/fman_tgec.c
index 284735d..4070593 100644
--- a/drivers/net/ethernet/freescale/fman/fman_tgec.c
+++ b/drivers/net/ethernet/freescale/fman/fman_tgec.c
@@ -44,6 +44,7 @@
#define TGEC_TX_IPG_LENGTH_MASK 0x000003ff
/* Command and Configuration Register (COMMAND_CONFIG) */
+#define CMD_CFG_EN_TIMESTAMP 0x00100000
#define CMD_CFG_NO_LEN_CHK 0x00020000
#define CMD_CFG_PAUSE_IGNORE 0x00000100
#define CMF_CFG_CRC_FWD 0x00000040
@@ -588,6 +589,26 @@ int tgec_set_allmulti(struct fman_mac *tgec, bool enable)
return 0;
}
+int tgec_set_tstamp(struct fman_mac *tgec, bool enable)
+{
+ struct tgec_regs __iomem *regs = tgec->regs;
+ u32 tmp;
+
+ if (!is_init_done(tgec->cfg))
+ return -EINVAL;
+
+ tmp = ioread32be(®s->command_config);
+
+ if (enable)
+ tmp |= CMD_CFG_EN_TIMESTAMP;
+ else
+ tmp &= ~CMD_CFG_EN_TIMESTAMP;
+
+ iowrite32be(tmp, ®s->command_config);
+
+ return 0;
+}
+
int tgec_del_hash_mac_address(struct fman_mac *tgec, enet_addr_t *eth_addr)
{
struct tgec_regs __iomem *regs = tgec->regs;
diff --git a/drivers/net/ethernet/freescale/fman/fman_tgec.h b/drivers/net/ethernet/freescale/fman/fman_tgec.h
index cbbd3b4..3bfd106 100644
--- a/drivers/net/ethernet/freescale/fman/fman_tgec.h
+++ b/drivers/net/ethernet/freescale/fman/fman_tgec.h
@@ -52,5 +52,6 @@ int tgec_set_exception(struct fman_mac *tgec,
int tgec_del_hash_mac_address(struct fman_mac *tgec, enet_addr_t *eth_addr);
int tgec_get_version(struct fman_mac *tgec, u32 *mac_version);
int tgec_set_allmulti(struct fman_mac *tgec, bool enable);
+int tgec_set_tstamp(struct fman_mac *tgec, bool enable);
#endif /* __TGEC_H */
diff --git a/drivers/net/ethernet/freescale/fman/mac.c b/drivers/net/ethernet/freescale/fman/mac.c
index 7b5b95f..a847b9c 100644
--- a/drivers/net/ethernet/freescale/fman/mac.c
+++ b/drivers/net/ethernet/freescale/fman/mac.c
@@ -471,6 +471,7 @@ static void setup_dtsec(struct mac_device *mac_dev)
mac_dev->set_rx_pause = dtsec_accept_rx_pause_frames;
mac_dev->set_exception = dtsec_set_exception;
mac_dev->set_allmulti = dtsec_set_allmulti;
+ mac_dev->set_tstamp = dtsec_set_tstamp;
mac_dev->set_multi = set_multi;
mac_dev->start = start;
mac_dev->stop = stop;
@@ -490,6 +491,7 @@ static void setup_tgec(struct mac_device *mac_dev)
mac_dev->set_rx_pause = tgec_accept_rx_pause_frames;
mac_dev->set_exception = tgec_set_exception;
mac_dev->set_allmulti = tgec_set_allmulti;
+ mac_dev->set_tstamp = tgec_set_tstamp;
mac_dev->set_multi = set_multi;
mac_dev->start = start;
mac_dev->stop = stop;
@@ -509,6 +511,7 @@ static void setup_memac(struct mac_device *mac_dev)
mac_dev->set_rx_pause = memac_accept_rx_pause_frames;
mac_dev->set_exception = memac_set_exception;
mac_dev->set_allmulti = memac_set_allmulti;
+ mac_dev->set_tstamp = memac_set_tstamp;
mac_dev->set_multi = set_multi;
mac_dev->start = start;
mac_dev->stop = stop;
diff --git a/drivers/net/ethernet/freescale/fman/mac.h b/drivers/net/ethernet/freescale/fman/mac.h
index b520cec..824a81a 100644
--- a/drivers/net/ethernet/freescale/fman/mac.h
+++ b/drivers/net/ethernet/freescale/fman/mac.h
@@ -68,6 +68,7 @@ struct mac_device {
int (*set_promisc)(struct fman_mac *mac_dev, bool enable);
int (*change_addr)(struct fman_mac *mac_dev, enet_addr_t *enet_addr);
int (*set_allmulti)(struct fman_mac *mac_dev, bool enable);
+ int (*set_tstamp)(struct fman_mac *mac_dev, bool enable);
int (*set_multi)(struct net_device *net_dev,
struct mac_device *mac_dev);
int (*set_rx_pause)(struct fman_mac *mac_dev, bool en);
--
1.7.1
^ permalink raw reply related
* [PATCH 04/10] powerpc/mpc85xx: move ptp timer out of fman in dts
From: Yangbo Lu @ 2018-06-04 7:08 UTC (permalink / raw)
To: netdev, madalin.bucur, Richard Cochran, Rob Herring, Shawn Guo,
David S . Miller
Cc: devicetree, linuxppc-dev, linux-arm-kernel, linux-kernel,
Yangbo Lu
In-Reply-To: <20180604070837.19265-1-yangbo.lu@nxp.com>
This patch is to move ptp timer node out of fman.
Because ptp timer will be probed by ptp_qoriq driver,
it should be an independent device in case of conflict
memory mapping.
Signed-off-by: Yangbo Lu <yangbo.lu@nxp.com>
---
arch/powerpc/boot/dts/fsl/qoriq-fman-0.dtsi | 14 ++++++++------
arch/powerpc/boot/dts/fsl/qoriq-fman-1.dtsi | 14 ++++++++------
arch/powerpc/boot/dts/fsl/qoriq-fman3-0.dtsi | 14 ++++++++------
arch/powerpc/boot/dts/fsl/qoriq-fman3-1.dtsi | 14 ++++++++------
arch/powerpc/boot/dts/fsl/qoriq-fman3l-0.dtsi | 14 ++++++++------
5 files changed, 40 insertions(+), 30 deletions(-)
diff --git a/arch/powerpc/boot/dts/fsl/qoriq-fman-0.dtsi b/arch/powerpc/boot/dts/fsl/qoriq-fman-0.dtsi
index abd01d4..6b124f7 100644
--- a/arch/powerpc/boot/dts/fsl/qoriq-fman-0.dtsi
+++ b/arch/powerpc/boot/dts/fsl/qoriq-fman-0.dtsi
@@ -37,12 +37,13 @@ fman0: fman@400000 {
#size-cells = <1>;
cell-index = <0>;
compatible = "fsl,fman";
- ranges = <0 0x400000 0x100000>;
- reg = <0x400000 0x100000>;
+ ranges = <0 0x400000 0xfe000>;
+ reg = <0x400000 0xfe000>;
interrupts = <96 2 0 0>, <16 2 1 1>;
clocks = <&clockgen 3 0>;
clock-names = "fmanclk";
fsl,qman-channel-range = <0x40 0xc>;
+ ptimer-handle = <&ptp_timer0>;
muram@0 {
compatible = "fsl,fman-muram";
@@ -93,9 +94,10 @@ fman0: fman@400000 {
reg = <0x87000 0x1000>;
status = "disabled";
};
+};
- ptp_timer0: ptp-timer@fe000 {
- compatible = "fsl,fman-ptp-timer";
- reg = <0xfe000 0x1000>;
- };
+ptp_timer0: ptp-timer@4fe000 {
+ compatible = "fsl,fman-ptp-timer";
+ reg = <0x4fe000 0x1000>;
+ interrupts = <96 2 0 0>;
};
diff --git a/arch/powerpc/boot/dts/fsl/qoriq-fman-1.dtsi b/arch/powerpc/boot/dts/fsl/qoriq-fman-1.dtsi
index debea75..b80aaf5 100644
--- a/arch/powerpc/boot/dts/fsl/qoriq-fman-1.dtsi
+++ b/arch/powerpc/boot/dts/fsl/qoriq-fman-1.dtsi
@@ -37,12 +37,13 @@ fman1: fman@500000 {
#size-cells = <1>;
cell-index = <1>;
compatible = "fsl,fman";
- ranges = <0 0x500000 0x100000>;
- reg = <0x500000 0x100000>;
+ ranges = <0 0x500000 0xfe000>;
+ reg = <0x500000 0xfe000>;
interrupts = <97 2 0 0>, <16 2 1 0>;
clocks = <&clockgen 3 1>;
clock-names = "fmanclk";
fsl,qman-channel-range = <0x60 0xc>;
+ ptimer-handle = <&ptp_timer1>;
muram@0 {
compatible = "fsl,fman-muram";
@@ -93,9 +94,10 @@ fman1: fman@500000 {
reg = <0x87000 0x1000>;
status = "disabled";
};
+};
- ptp_timer1: ptp-timer@fe000 {
- compatible = "fsl,fman-ptp-timer";
- reg = <0xfe000 0x1000>;
- };
+ptp_timer1: ptp-timer@5fe000 {
+ compatible = "fsl,fman-ptp-timer";
+ reg = <0x5fe000 0x1000>;
+ interrupts = <97 2 0 0>;
};
diff --git a/arch/powerpc/boot/dts/fsl/qoriq-fman3-0.dtsi b/arch/powerpc/boot/dts/fsl/qoriq-fman3-0.dtsi
index 3a20e0d..d3720fd 100644
--- a/arch/powerpc/boot/dts/fsl/qoriq-fman3-0.dtsi
+++ b/arch/powerpc/boot/dts/fsl/qoriq-fman3-0.dtsi
@@ -37,12 +37,13 @@ fman0: fman@400000 {
#size-cells = <1>;
cell-index = <0>;
compatible = "fsl,fman";
- ranges = <0 0x400000 0x100000>;
- reg = <0x400000 0x100000>;
+ ranges = <0 0x400000 0xfe000>;
+ reg = <0x400000 0xfe000>;
interrupts = <96 2 0 0>, <16 2 1 1>;
clocks = <&clockgen 3 0>;
clock-names = "fmanclk";
fsl,qman-channel-range = <0x800 0x10>;
+ ptimer-handle = <&ptp_timer0>;
muram@0 {
compatible = "fsl,fman-muram";
@@ -98,9 +99,10 @@ fman0: fman@400000 {
compatible = "fsl,fman-memac-mdio", "fsl,fman-xmdio";
reg = <0xfd000 0x1000>;
};
+};
- ptp_timer0: ptp-timer@fe000 {
- compatible = "fsl,fman-ptp-timer";
- reg = <0xfe000 0x1000>;
- };
+ptp_timer0: ptp-timer@4fe000 {
+ compatible = "fsl,fman-ptp-timer";
+ reg = <0x4fe000 0x1000>;
+ interrupts = <96 2 0 0>;
};
diff --git a/arch/powerpc/boot/dts/fsl/qoriq-fman3-1.dtsi b/arch/powerpc/boot/dts/fsl/qoriq-fman3-1.dtsi
index 82750ac..ae34c20 100644
--- a/arch/powerpc/boot/dts/fsl/qoriq-fman3-1.dtsi
+++ b/arch/powerpc/boot/dts/fsl/qoriq-fman3-1.dtsi
@@ -37,12 +37,13 @@ fman1: fman@500000 {
#size-cells = <1>;
cell-index = <1>;
compatible = "fsl,fman";
- ranges = <0 0x500000 0x100000>;
- reg = <0x500000 0x100000>;
+ ranges = <0 0x500000 0xfe000>;
+ reg = <0x500000 0xfe000>;
interrupts = <97 2 0 0>, <16 2 1 0>;
clocks = <&clockgen 3 1>;
clock-names = "fmanclk";
fsl,qman-channel-range = <0x820 0x10>;
+ ptimer-handle = <&ptp_timer1>;
muram@0 {
compatible = "fsl,fman-muram";
@@ -98,9 +99,10 @@ fman1: fman@500000 {
compatible = "fsl,fman-memac-mdio", "fsl,fman-xmdio";
reg = <0xfd000 0x1000>;
};
+};
- ptp_timer1: ptp-timer@fe000 {
- compatible = "fsl,fman-ptp-timer";
- reg = <0xfe000 0x1000>;
- };
+ptp_timer1: ptp-timer@5fe000 {
+ compatible = "fsl,fman-ptp-timer";
+ reg = <0x5fe000 0x1000>;
+ interrupts = <97 2 0 0>;
};
diff --git a/arch/powerpc/boot/dts/fsl/qoriq-fman3l-0.dtsi b/arch/powerpc/boot/dts/fsl/qoriq-fman3l-0.dtsi
index 7f60b60..02f2755 100644
--- a/arch/powerpc/boot/dts/fsl/qoriq-fman3l-0.dtsi
+++ b/arch/powerpc/boot/dts/fsl/qoriq-fman3l-0.dtsi
@@ -37,12 +37,13 @@ fman0: fman@400000 {
#size-cells = <1>;
cell-index = <0>;
compatible = "fsl,fman";
- ranges = <0 0x400000 0x100000>;
- reg = <0x400000 0x100000>;
+ ranges = <0 0x400000 0xfe000>;
+ reg = <0x400000 0xfe000>;
interrupts = <96 2 0 0>, <16 2 1 1>;
clocks = <&clockgen 3 0>;
clock-names = "fmanclk";
fsl,qman-channel-range = <0x800 0x10>;
+ ptimer-handle = <&ptp_timer0>;
muram@0 {
compatible = "fsl,fman-muram";
@@ -86,9 +87,10 @@ fman0: fman@400000 {
compatible = "fsl,fman-memac-mdio", "fsl,fman-xmdio";
reg = <0xfd000 0x1000>;
};
+};
- ptp_timer0: ptp-timer@fe000 {
- compatible = "fsl,fman-ptp-timer";
- reg = <0xfe000 0x1000>;
- };
+ptp_timer0: ptp-timer@4fe000 {
+ compatible = "fsl,fman-ptp-timer";
+ reg = <0x4fe000 0x1000>;
+ interrupts = <96 2 0 0>;
};
--
1.7.1
^ permalink raw reply related
* [PATCH 00/10] Support DPAA PTP clock and timestamping
From: Yangbo Lu @ 2018-06-04 7:08 UTC (permalink / raw)
To: netdev, madalin.bucur, Richard Cochran, Rob Herring, Shawn Guo,
David S . Miller
Cc: devicetree, linuxppc-dev, linux-arm-kernel, linux-kernel,
Yangbo Lu
This patchset is to support DPAA FMAN PTP clock and HW timestamping.
- The patch #1 to patch #5 are to support DPAA FMAN 1588 timer in
ptp_qoriq driver.
- The patch #6 to patch #10 are to add HW timestamping support in
DPAA ethernet driver.
Yangbo Lu (10):
fsl/fman: share the event interrupt
ptp: support DPAA FMan 1588 timer in ptp_qoriq
dt-binding: ptp_qoriq: add DPAA FMan support
powerpc/mpc85xx: move ptp timer out of fman in dts
arm64: dts: fsl: move ptp timer out of fman
fsl/fman: add set_tstamp interface
fsl/fman_port: support getting timestamp field
fsl/fman: define frame description command UPD
dpaa_eth: add support for hardware timestamping
dpaa_eth: add the get_ts_info interface for ethtool
Documentation/devicetree/bindings/net/fsl-fman.txt | 25 +----
.../devicetree/bindings/ptp/ptp-qoriq.txt | 15 ++-
arch/arm64/boot/dts/freescale/qoriq-fman3-0.dtsi | 14 ++-
arch/powerpc/boot/dts/fsl/qoriq-fman-0.dtsi | 14 ++-
arch/powerpc/boot/dts/fsl/qoriq-fman-1.dtsi | 14 ++-
arch/powerpc/boot/dts/fsl/qoriq-fman3-0.dtsi | 14 ++-
arch/powerpc/boot/dts/fsl/qoriq-fman3-1.dtsi | 14 ++-
arch/powerpc/boot/dts/fsl/qoriq-fman3l-0.dtsi | 14 ++-
drivers/net/ethernet/freescale/dpaa/Kconfig | 12 ++
drivers/net/ethernet/freescale/dpaa/dpaa_eth.c | 119 +++++++++++++++++++-
drivers/net/ethernet/freescale/dpaa/dpaa_eth.h | 5 +
drivers/net/ethernet/freescale/dpaa/dpaa_ethtool.c | 44 +++++++
drivers/net/ethernet/freescale/fman/fman.c | 3 +-
drivers/net/ethernet/freescale/fman/fman.h | 1 +
drivers/net/ethernet/freescale/fman/fman_dtsec.c | 27 +++++
drivers/net/ethernet/freescale/fman/fman_dtsec.h | 1 +
drivers/net/ethernet/freescale/fman/fman_memac.c | 5 +
drivers/net/ethernet/freescale/fman/fman_memac.h | 1 +
drivers/net/ethernet/freescale/fman/fman_port.c | 12 ++
drivers/net/ethernet/freescale/fman/fman_port.h | 3 +
drivers/net/ethernet/freescale/fman/fman_tgec.c | 21 ++++
drivers/net/ethernet/freescale/fman/fman_tgec.h | 1 +
drivers/net/ethernet/freescale/fman/mac.c | 3 +
drivers/net/ethernet/freescale/fman/mac.h | 1 +
drivers/ptp/Kconfig | 2 +-
drivers/ptp/ptp_qoriq.c | 104 +++++++++++------
include/linux/fsl/ptp_qoriq.h | 38 +++++-
27 files changed, 414 insertions(+), 113 deletions(-)
^ permalink raw reply
* [PATCH 01/10] fsl/fman: share the event interrupt
From: Yangbo Lu @ 2018-06-04 7:08 UTC (permalink / raw)
To: netdev, madalin.bucur, Richard Cochran, Rob Herring, Shawn Guo,
David S . Miller
Cc: devicetree, linuxppc-dev, linux-arm-kernel, linux-kernel,
Yangbo Lu
In-Reply-To: <20180604070837.19265-1-yangbo.lu@nxp.com>
This patch is to share fman event interrupt because
the 1588 timer driver will also use this interrupt.
Signed-off-by: Yangbo Lu <yangbo.lu@nxp.com>
---
drivers/net/ethernet/freescale/fman/fman.c | 3 ++-
1 files changed, 2 insertions(+), 1 deletions(-)
diff --git a/drivers/net/ethernet/freescale/fman/fman.c b/drivers/net/ethernet/freescale/fman/fman.c
index 9530405..c415ac6 100644
--- a/drivers/net/ethernet/freescale/fman/fman.c
+++ b/drivers/net/ethernet/freescale/fman/fman.c
@@ -2801,7 +2801,8 @@ static irqreturn_t fman_irq(int irq, void *handle)
of_node_put(muram_node);
of_node_put(fm_node);
- err = devm_request_irq(&of_dev->dev, irq, fman_irq, 0, "fman", fman);
+ err = devm_request_irq(&of_dev->dev, irq, fman_irq, IRQF_SHARED,
+ "fman", fman);
if (err < 0) {
dev_err(&of_dev->dev, "%s: irq %d allocation failed (error = %d)\n",
__func__, irq, err);
--
1.7.1
^ permalink raw reply related
* Re: [PATCH] crypto/nx: Initialize 842 high and normal RxFIFO control registers
From: Oliver @ 2018-06-04 4:59 UTC (permalink / raw)
To: Haren Myneni; +Cc: Stewart Smith, linuxppc-dev, herbert, linux-crypto
In-Reply-To: <5B14A797.2050306@linux.vnet.ibm.com>
On Mon, Jun 4, 2018 at 12:44 PM, Haren Myneni <haren@linux.vnet.ibm.com> wr=
ote:
> On 06/03/2018 05:41 PM, Stewart Smith wrote:
>> Haren Myneni <haren@linux.vnet.ibm.com> writes:
>>> On 06/01/2018 12:41 AM, Stewart Smith wrote:
>>>> Haren Myneni <haren@linux.vnet.ibm.com> writes:
>>>>> NX increments readOffset by FIFO size in receive FIFO control registe=
r
>>>>> when CRB is read. But the index in RxFIFO has to match with the
>>>>> corresponding entry in FIFO maintained by VAS in kernel. Otherwise NX
>>>>> may be processing incorrect CRBs and can cause CRB timeout.
>>>>>
>>>>> VAS FIFO offset is 0 when the receive window is opened during
>>>>> initialization. When the module is reloaded or in kexec boot, readOff=
set
>>>>> in FIFO control register may not match with VAS entry. This patch add=
s
>>>>> nx_coproc_init OPAL call to reset readOffset and queued entries in FI=
FO
>>>>> control register for both high and normal FIFOs.
>>>>>
>>>>> Signed-off-by: Haren Myneni <haren@us.ibm.com>
>>>>>
>>>>> diff --git a/arch/powerpc/include/asm/opal-api.h b/arch/powerpc/inclu=
de/asm/opal-api.h
>>>>> index d886a5b..ff61e4b 100644
>>>>> --- a/arch/powerpc/include/asm/opal-api.h
>>>>> +++ b/arch/powerpc/include/asm/opal-api.h
>>>>> @@ -206,7 +206,8 @@
>>>>> #define OPAL_NPU_TL_SET 161
>>>>> #define OPAL_PCI_GET_PBCQ_TUNNEL_BAR 164
>>>>> #define OPAL_PCI_SET_PBCQ_TUNNEL_BAR 165
>>>>> -#define OPAL_LAST 165
>>>>> +#define OPAL_NX_COPROC_INIT 167
>>>>> +#define OPAL_LAST 167
>>>>>
>>>>> /* Device tree flags */
>>>>>
>>>>> diff --git a/arch/powerpc/include/asm/opal.h b/arch/powerpc/include/a=
sm/opal.h
>>>>> index 7159e1a..d79eb82 100644
>>>>> --- a/arch/powerpc/include/asm/opal.h
>>>>> +++ b/arch/powerpc/include/asm/opal.h
>>>>> @@ -288,6 +288,7 @@ int64_t opal_imc_counters_init(uint32_t type, uin=
t64_t address,
>>>>> int opal_get_power_shift_ratio(u32 handle, int token, u32 *psr);
>>>>> int opal_set_power_shift_ratio(u32 handle, int token, u32 psr);
>>>>> int opal_sensor_group_clear(u32 group_hndl, int token);
>>>>> +int opal_nx_coproc_init(uint32_t chip_id, uint32_t ct);
>>>>>
>>>>> s64 opal_signal_system_reset(s32 cpu);
>>>>>
>>>>> diff --git a/arch/powerpc/platforms/powernv/opal-wrappers.S b/arch/po=
werpc/platforms/powernv/opal-wrappers.S
>>>>> index 3da30c2..c7541a9 100644
>>>>> --- a/arch/powerpc/platforms/powernv/opal-wrappers.S
>>>>> +++ b/arch/powerpc/platforms/powernv/opal-wrappers.S
>>>>> @@ -325,3 +325,4 @@ OPAL_CALL(opal_npu_spa_clear_cache, OP=
AL_NPU_SPA_CLEAR_CACHE);
>>>>> OPAL_CALL(opal_npu_tl_set, OPAL_NPU_TL_SET);
>>>>> OPAL_CALL(opal_pci_get_pbcq_tunnel_bar, OPAL_PCI_GET_PBCQ_=
TUNNEL_BAR);
>>>>> OPAL_CALL(opal_pci_set_pbcq_tunnel_bar, OPAL_PCI_SET_PBCQ_=
TUNNEL_BAR);
>>>>> +OPAL_CALL(opal_nx_coproc_init, OPAL_NX_COPROC_INI=
T);
>>>>> diff --git a/arch/powerpc/platforms/powernv/opal.c b/arch/powerpc/pla=
tforms/powernv/opal.c
>>>>> index 48fbb41..5e13908 100644
>>>>> --- a/arch/powerpc/platforms/powernv/opal.c
>>>>> +++ b/arch/powerpc/platforms/powernv/opal.c
>>>>> @@ -1035,3 +1035,5 @@ void powernv_set_nmmu_ptcr(unsigned long ptcr)
>>>>> EXPORT_SYMBOL_GPL(opal_int_set_mfrr);
>>>>> EXPORT_SYMBOL_GPL(opal_int_eoi);
>>>>> EXPORT_SYMBOL_GPL(opal_error_code);
>>>>> +/* Export the below symbol for NX compression */
>>>>> +EXPORT_SYMBOL(opal_nx_coproc_init);
>>>>> diff --git a/drivers/crypto/nx/nx-842-powernv.c b/drivers/crypto/nx/n=
x-842-powernv.c
>>>>> index 1e87637..6c4784d 100644
>>>>> --- a/drivers/crypto/nx/nx-842-powernv.c
>>>>> +++ b/drivers/crypto/nx/nx-842-powernv.c
>>>>> @@ -24,6 +24,8 @@
>>>>> #include <asm/icswx.h>
>>>>> #include <asm/vas.h>
>>>>> #include <asm/reg.h>
>>>>> +#include <asm/opal-api.h>
>>>>> +#include <asm/opal.h>
>>>>>
>>>>> MODULE_LICENSE("GPL");
>>>>> MODULE_AUTHOR("Dan Streetman <ddstreet@ieee.org>");
>>>>> @@ -803,9 +805,26 @@ static int __init vas_cfg_coproc_info(struct dev=
ice_node *dn, int chip_id,
>>>>> if (!coproc)
>>>>> return -ENOMEM;
>>>>>
>>>>> - if (!strcmp(priority, "High"))
>>>>> + if (!strcmp(priority, "High")) {
>>>>> + /*
>>>>> + * (lpid, pid, tid) combination has to be unique for each
>>>>> + * coprocessor instance in the system. So to make it
>>>>> + * unique, skiboot uses coprocessor type such as 842 or
>>>>> + * GZIP for pid and provides this value to kernel in pid
>>>>> + * device-tree property.
>>>>> + *
>>>>> + * Initialize each NX instance for both high and normal
>>>>> + * priority FIFOs.
>>>>> + */
>>>>> + ret =3D opal_nx_coproc_init(chip_id, pid);
>>>>> + if (ret) {
>>>>> + pr_err("Failed to initialize NX coproc: %d\n", ret=
);
>>>>> + ret =3D opal_error_code(ret);
>>>>> + goto err_out;
>>>>> + }
>>>>> +
>>>>> coproc->ct =3D VAS_COP_TYPE_842_HIPRI;
>>>>
>>>> I think this should be called for all priority queues as it would be a=
t
>>>> least theoretically possible to only have Normal priority queues, in
>>>> which case this patch wouldn't fix the problem.
>>>
>>> device tree exports separate nodes for high and normal priority FIFOs
>>> per each NX instance. But NX init OPAL function is called once per
>>> each NX instance when high-FIFO device node is parsed to reset high
>>> and normal FIFO control registers. As you see in skiboot patch, resets
>>> both priority registers. Thought we should minimize the number of OPAL
>>> calla execution and also should have generic NX init OPAL call. We can
>>> extend this call to reset default values for any other registers if
>>> needed.
>>
>> This code does'nt do that though, it calls it for "high" priority, so if
>> for whatever reason there was a DT without a "High" priority node there,
>> it'd not call it.
>
> Skiboot exports high and normal FIFO nodes for each coprocessor type per =
NX instance. We will never see only normal FIFO node without high FIFO node=
. As we see in skiboot code, configure high FIFO and export this node first=
, and then normal FIFO. In case if xscom read/ write for high FIFO failed, =
we do not proceed for normal FIFO.
>
> Also, we use only high priority FIFOs in kernel (nx-842). Normal FIFOs ar=
e reserved only for user space use (NX GZIP in future).
>
> So we will not get in to the case that you described. Normal FIFO DT node=
will be available only with high FIFO node per each NX instance.
This is infuriating to read.
OPAL is an API that Skiboot happens to implement. It's like that so
that we can change the behaviour of skiboot (to work around bugs,
implement new features, or whatever) without breaking the existing
kernels that use that API. Trying to argue that this is OK because it
works with the *current* behaviour of skiboot misses the point
entirely.
>>> If you prefer calling separately based on priority, we can have
>>> opal_nx_coproc_FIFO_init(chip_id, pid, priority). Please let me know.
>>
>> I think the call is okay, it's just that if it needs to be called once
>> per accellerator, then we should ensure it does that.
>>
>
^ permalink raw reply
* Re: [PATCH] crypto/nx: Initialize 842 high and normal RxFIFO control registers
From: Haren Myneni @ 2018-06-04 4:52 UTC (permalink / raw)
To: Stewart Smith; +Cc: linuxppc-dev, herbert, linux-crypto
In-Reply-To: <878t7v2nxt.fsf@linux.vnet.ibm.com>
On 06/03/2018 09:08 PM, Stewart Smith wrote:
> Haren Myneni <haren@linux.vnet.ibm.com> writes:
>> On 06/03/2018 05:41 PM, Stewart Smith wrote:
>>> Haren Myneni <haren@linux.vnet.ibm.com> writes:
>>>> On 06/01/2018 12:41 AM, Stewart Smith wrote:
>>>>> Haren Myneni <haren@linux.vnet.ibm.com> writes:
>>>>>> NX increments readOffset by FIFO size in receive FIFO control register
>>>>>> when CRB is read. But the index in RxFIFO has to match with the
>>>>>> corresponding entry in FIFO maintained by VAS in kernel. Otherwise NX
>>>>>> may be processing incorrect CRBs and can cause CRB timeout.
>>>>>>
>>>>>> VAS FIFO offset is 0 when the receive window is opened during
>>>>>> initialization. When the module is reloaded or in kexec boot, readOffset
>>>>>> in FIFO control register may not match with VAS entry. This patch adds
>>>>>> nx_coproc_init OPAL call to reset readOffset and queued entries in FIFO
>>>>>> control register for both high and normal FIFOs.
>>>>>>
>>>>>> Signed-off-by: Haren Myneni <haren@us.ibm.com>
>>>>>>
>>>>>> diff --git a/arch/powerpc/include/asm/opal-api.h b/arch/powerpc/include/asm/opal-api.h
>>>>>> index d886a5b..ff61e4b 100644
>>>>>> --- a/arch/powerpc/include/asm/opal-api.h
>>>>>> +++ b/arch/powerpc/include/asm/opal-api.h
>>>>>> @@ -206,7 +206,8 @@
>>>>>> #define OPAL_NPU_TL_SET 161
>>>>>> #define OPAL_PCI_GET_PBCQ_TUNNEL_BAR 164
>>>>>> #define OPAL_PCI_SET_PBCQ_TUNNEL_BAR 165
>>>>>> -#define OPAL_LAST 165
>>>>>> +#define OPAL_NX_COPROC_INIT 167
>>>>>> +#define OPAL_LAST 167
>>>>>>
>>>>>> /* Device tree flags */
>>>>>>
>>>>>> diff --git a/arch/powerpc/include/asm/opal.h b/arch/powerpc/include/asm/opal.h
>>>>>> index 7159e1a..d79eb82 100644
>>>>>> --- a/arch/powerpc/include/asm/opal.h
>>>>>> +++ b/arch/powerpc/include/asm/opal.h
>>>>>> @@ -288,6 +288,7 @@ int64_t opal_imc_counters_init(uint32_t type, uint64_t address,
>>>>>> int opal_get_power_shift_ratio(u32 handle, int token, u32 *psr);
>>>>>> int opal_set_power_shift_ratio(u32 handle, int token, u32 psr);
>>>>>> int opal_sensor_group_clear(u32 group_hndl, int token);
>>>>>> +int opal_nx_coproc_init(uint32_t chip_id, uint32_t ct);
>>>>>>
>>>>>> s64 opal_signal_system_reset(s32 cpu);
>>>>>>
>>>>>> diff --git a/arch/powerpc/platforms/powernv/opal-wrappers.S b/arch/powerpc/platforms/powernv/opal-wrappers.S
>>>>>> index 3da30c2..c7541a9 100644
>>>>>> --- a/arch/powerpc/platforms/powernv/opal-wrappers.S
>>>>>> +++ b/arch/powerpc/platforms/powernv/opal-wrappers.S
>>>>>> @@ -325,3 +325,4 @@ OPAL_CALL(opal_npu_spa_clear_cache, OPAL_NPU_SPA_CLEAR_CACHE);
>>>>>> OPAL_CALL(opal_npu_tl_set, OPAL_NPU_TL_SET);
>>>>>> OPAL_CALL(opal_pci_get_pbcq_tunnel_bar, OPAL_PCI_GET_PBCQ_TUNNEL_BAR);
>>>>>> OPAL_CALL(opal_pci_set_pbcq_tunnel_bar, OPAL_PCI_SET_PBCQ_TUNNEL_BAR);
>>>>>> +OPAL_CALL(opal_nx_coproc_init, OPAL_NX_COPROC_INIT);
>>>>>> diff --git a/arch/powerpc/platforms/powernv/opal.c b/arch/powerpc/platforms/powernv/opal.c
>>>>>> index 48fbb41..5e13908 100644
>>>>>> --- a/arch/powerpc/platforms/powernv/opal.c
>>>>>> +++ b/arch/powerpc/platforms/powernv/opal.c
>>>>>> @@ -1035,3 +1035,5 @@ void powernv_set_nmmu_ptcr(unsigned long ptcr)
>>>>>> EXPORT_SYMBOL_GPL(opal_int_set_mfrr);
>>>>>> EXPORT_SYMBOL_GPL(opal_int_eoi);
>>>>>> EXPORT_SYMBOL_GPL(opal_error_code);
>>>>>> +/* Export the below symbol for NX compression */
>>>>>> +EXPORT_SYMBOL(opal_nx_coproc_init);
>>>>>> diff --git a/drivers/crypto/nx/nx-842-powernv.c b/drivers/crypto/nx/nx-842-powernv.c
>>>>>> index 1e87637..6c4784d 100644
>>>>>> --- a/drivers/crypto/nx/nx-842-powernv.c
>>>>>> +++ b/drivers/crypto/nx/nx-842-powernv.c
>>>>>> @@ -24,6 +24,8 @@
>>>>>> #include <asm/icswx.h>
>>>>>> #include <asm/vas.h>
>>>>>> #include <asm/reg.h>
>>>>>> +#include <asm/opal-api.h>
>>>>>> +#include <asm/opal.h>
>>>>>>
>>>>>> MODULE_LICENSE("GPL");
>>>>>> MODULE_AUTHOR("Dan Streetman <ddstreet@ieee.org>");
>>>>>> @@ -803,9 +805,26 @@ static int __init vas_cfg_coproc_info(struct device_node *dn, int chip_id,
>>>>>> if (!coproc)
>>>>>> return -ENOMEM;
>>>>>>
>>>>>> - if (!strcmp(priority, "High"))
>>>>>> + if (!strcmp(priority, "High")) {
>>>>>> + /*
>>>>>> + * (lpid, pid, tid) combination has to be unique for each
>>>>>> + * coprocessor instance in the system. So to make it
>>>>>> + * unique, skiboot uses coprocessor type such as 842 or
>>>>>> + * GZIP for pid and provides this value to kernel in pid
>>>>>> + * device-tree property.
>>>>>> + *
>>>>>> + * Initialize each NX instance for both high and normal
>>>>>> + * priority FIFOs.
>>>>>> + */
>>>>>> + ret = opal_nx_coproc_init(chip_id, pid);
>>>>>> + if (ret) {
>>>>>> + pr_err("Failed to initialize NX coproc: %d\n", ret);
>>>>>> + ret = opal_error_code(ret);
>>>>>> + goto err_out;
>>>>>> + }
>>>>>> +
>>>>>> coproc->ct = VAS_COP_TYPE_842_HIPRI;
>>>>>
>>>>> I think this should be called for all priority queues as it would be at
>>>>> least theoretically possible to only have Normal priority queues, in
>>>>> which case this patch wouldn't fix the problem.
>>>>
>>>> device tree exports separate nodes for high and normal priority FIFOs
>>>> per each NX instance. But NX init OPAL function is called once per
>>>> each NX instance when high-FIFO device node is parsed to reset high
>>>> and normal FIFO control registers. As you see in skiboot patch, resets
>>>> both priority registers. Thought we should minimize the number of OPAL
>>>> calla execution and also should have generic NX init OPAL call. We can
>>>> extend this call to reset default values for any other registers if
>>>> needed.
>>>
>>> This code does'nt do that though, it calls it for "high" priority, so if
>>> for whatever reason there was a DT without a "High" priority node there,
>>> it'd not call it.
>>
>> Skiboot exports high and normal FIFO nodes for each coprocessor type
>> per NX instance. We will never see only normal FIFO node without high
>> FIFO node. As we see in skiboot code, configure high FIFO and export
>> this node first, and then normal FIFO. In case if xscom read/ write
>> for high FIFO failed, we do not proceed for normal FIFO.
>
> Currently that's true, yes. But in the future it may not be. Imagine if
> we found a hardware bug that would mean disabling the 'High' priority
> one, or a future chip revision just had a single priority.
Correct, does not work for HW bug or NX does not support different priorities. But the current skiboot and kernel code has to be modified to support new chip revision anyway.
How about the following change - moved the OPAL caLL to nx842_powernv_probe_vas().
static int __init vas_cfg_coproc_info(struct device_node *dn, int chip_id,
- int vasid)
+ int vasid, int *ct)
{
struct vas_window *rxwin = NULL;
struct vas_rx_win_attr rxattr;
@@ -837,6 +839,15 @@ static int __init vas_cfg_coproc_info(struct device_node *dn, int chip_id,
coproc->vas.id = vasid;
nx842_add_coprocs_list(coproc, chip_id);
+ /*
+ * (lpid, pid, tid) combination has to be unique for each
+ * coprocessor instance in the system. So to make it
+ * unique, skiboot uses coprocessor type such as 842 or
+ * GZIP for pid and provides this value to kernel in pid
+ * device-tree property.
+ */
+ *ct = pid;
+
return 0;
err_out:
@@ -848,7 +859,7 @@ static int __init vas_cfg_coproc_info(struct device_node *dn, int chip_id,
static int __init nx842_powernv_probe_vas(struct device_node *pn)
{
struct device_node *dn;
- int chip_id, vasid, ret = 0;
+ int chip_id, vasid, ct, ret = 0;
int nx_fifo_found = 0;
chip_id = of_get_ibm_chip_id(pn);
@@ -865,7 +876,7 @@ static int __init nx842_powernv_probe_vas(struct device_node *pn)
for_each_child_of_node(pn, dn) {
if (of_device_is_compatible(dn, "ibm,p9-nx-842")) {
- ret = vas_cfg_coproc_info(dn, chip_id, vasid);
+ ret = vas_cfg_coproc_info(dn, chip_id, vasid, &ct);
if (ret) {
of_node_put(dn);
return ret;
@@ -879,6 +890,16 @@ static int __init nx842_powernv_probe_vas(struct device_node *pn)
ret = -EINVAL;
}
+ /*
+ * Initialize each NX instance for both high and normal
+ * priority FIFOs.
+ */
+ ret = opal_nx_coproc_init(chip_id, ct);
+ if (ret) {
+ pr_err("Failed to initialize NX coproc: %d\n", ret);
+ ret = opal_error_code(ret);
+ }
+
return ret;
}
^ permalink raw reply
* Re: [PATCH] crypto/nx: Initialize 842 high and normal RxFIFO control registers
From: Stewart Smith @ 2018-06-04 4:08 UTC (permalink / raw)
To: Haren Myneni; +Cc: mpe, linuxppc-dev, herbert, linux-crypto
In-Reply-To: <5B14A797.2050306@linux.vnet.ibm.com>
Haren Myneni <haren@linux.vnet.ibm.com> writes:
> On 06/03/2018 05:41 PM, Stewart Smith wrote:
>> Haren Myneni <haren@linux.vnet.ibm.com> writes:
>>> On 06/01/2018 12:41 AM, Stewart Smith wrote:
>>>> Haren Myneni <haren@linux.vnet.ibm.com> writes:
>>>>> NX increments readOffset by FIFO size in receive FIFO control register
>>>>> when CRB is read. But the index in RxFIFO has to match with the
>>>>> corresponding entry in FIFO maintained by VAS in kernel. Otherwise NX
>>>>> may be processing incorrect CRBs and can cause CRB timeout.
>>>>>
>>>>> VAS FIFO offset is 0 when the receive window is opened during
>>>>> initialization. When the module is reloaded or in kexec boot, readOffset
>>>>> in FIFO control register may not match with VAS entry. This patch adds
>>>>> nx_coproc_init OPAL call to reset readOffset and queued entries in FIFO
>>>>> control register for both high and normal FIFOs.
>>>>>
>>>>> Signed-off-by: Haren Myneni <haren@us.ibm.com>
>>>>>
>>>>> diff --git a/arch/powerpc/include/asm/opal-api.h b/arch/powerpc/include/asm/opal-api.h
>>>>> index d886a5b..ff61e4b 100644
>>>>> --- a/arch/powerpc/include/asm/opal-api.h
>>>>> +++ b/arch/powerpc/include/asm/opal-api.h
>>>>> @@ -206,7 +206,8 @@
>>>>> #define OPAL_NPU_TL_SET 161
>>>>> #define OPAL_PCI_GET_PBCQ_TUNNEL_BAR 164
>>>>> #define OPAL_PCI_SET_PBCQ_TUNNEL_BAR 165
>>>>> -#define OPAL_LAST 165
>>>>> +#define OPAL_NX_COPROC_INIT 167
>>>>> +#define OPAL_LAST 167
>>>>>
>>>>> /* Device tree flags */
>>>>>
>>>>> diff --git a/arch/powerpc/include/asm/opal.h b/arch/powerpc/include/asm/opal.h
>>>>> index 7159e1a..d79eb82 100644
>>>>> --- a/arch/powerpc/include/asm/opal.h
>>>>> +++ b/arch/powerpc/include/asm/opal.h
>>>>> @@ -288,6 +288,7 @@ int64_t opal_imc_counters_init(uint32_t type, uint64_t address,
>>>>> int opal_get_power_shift_ratio(u32 handle, int token, u32 *psr);
>>>>> int opal_set_power_shift_ratio(u32 handle, int token, u32 psr);
>>>>> int opal_sensor_group_clear(u32 group_hndl, int token);
>>>>> +int opal_nx_coproc_init(uint32_t chip_id, uint32_t ct);
>>>>>
>>>>> s64 opal_signal_system_reset(s32 cpu);
>>>>>
>>>>> diff --git a/arch/powerpc/platforms/powernv/opal-wrappers.S b/arch/powerpc/platforms/powernv/opal-wrappers.S
>>>>> index 3da30c2..c7541a9 100644
>>>>> --- a/arch/powerpc/platforms/powernv/opal-wrappers.S
>>>>> +++ b/arch/powerpc/platforms/powernv/opal-wrappers.S
>>>>> @@ -325,3 +325,4 @@ OPAL_CALL(opal_npu_spa_clear_cache, OPAL_NPU_SPA_CLEAR_CACHE);
>>>>> OPAL_CALL(opal_npu_tl_set, OPAL_NPU_TL_SET);
>>>>> OPAL_CALL(opal_pci_get_pbcq_tunnel_bar, OPAL_PCI_GET_PBCQ_TUNNEL_BAR);
>>>>> OPAL_CALL(opal_pci_set_pbcq_tunnel_bar, OPAL_PCI_SET_PBCQ_TUNNEL_BAR);
>>>>> +OPAL_CALL(opal_nx_coproc_init, OPAL_NX_COPROC_INIT);
>>>>> diff --git a/arch/powerpc/platforms/powernv/opal.c b/arch/powerpc/platforms/powernv/opal.c
>>>>> index 48fbb41..5e13908 100644
>>>>> --- a/arch/powerpc/platforms/powernv/opal.c
>>>>> +++ b/arch/powerpc/platforms/powernv/opal.c
>>>>> @@ -1035,3 +1035,5 @@ void powernv_set_nmmu_ptcr(unsigned long ptcr)
>>>>> EXPORT_SYMBOL_GPL(opal_int_set_mfrr);
>>>>> EXPORT_SYMBOL_GPL(opal_int_eoi);
>>>>> EXPORT_SYMBOL_GPL(opal_error_code);
>>>>> +/* Export the below symbol for NX compression */
>>>>> +EXPORT_SYMBOL(opal_nx_coproc_init);
>>>>> diff --git a/drivers/crypto/nx/nx-842-powernv.c b/drivers/crypto/nx/nx-842-powernv.c
>>>>> index 1e87637..6c4784d 100644
>>>>> --- a/drivers/crypto/nx/nx-842-powernv.c
>>>>> +++ b/drivers/crypto/nx/nx-842-powernv.c
>>>>> @@ -24,6 +24,8 @@
>>>>> #include <asm/icswx.h>
>>>>> #include <asm/vas.h>
>>>>> #include <asm/reg.h>
>>>>> +#include <asm/opal-api.h>
>>>>> +#include <asm/opal.h>
>>>>>
>>>>> MODULE_LICENSE("GPL");
>>>>> MODULE_AUTHOR("Dan Streetman <ddstreet@ieee.org>");
>>>>> @@ -803,9 +805,26 @@ static int __init vas_cfg_coproc_info(struct device_node *dn, int chip_id,
>>>>> if (!coproc)
>>>>> return -ENOMEM;
>>>>>
>>>>> - if (!strcmp(priority, "High"))
>>>>> + if (!strcmp(priority, "High")) {
>>>>> + /*
>>>>> + * (lpid, pid, tid) combination has to be unique for each
>>>>> + * coprocessor instance in the system. So to make it
>>>>> + * unique, skiboot uses coprocessor type such as 842 or
>>>>> + * GZIP for pid and provides this value to kernel in pid
>>>>> + * device-tree property.
>>>>> + *
>>>>> + * Initialize each NX instance for both high and normal
>>>>> + * priority FIFOs.
>>>>> + */
>>>>> + ret = opal_nx_coproc_init(chip_id, pid);
>>>>> + if (ret) {
>>>>> + pr_err("Failed to initialize NX coproc: %d\n", ret);
>>>>> + ret = opal_error_code(ret);
>>>>> + goto err_out;
>>>>> + }
>>>>> +
>>>>> coproc->ct = VAS_COP_TYPE_842_HIPRI;
>>>>
>>>> I think this should be called for all priority queues as it would be at
>>>> least theoretically possible to only have Normal priority queues, in
>>>> which case this patch wouldn't fix the problem.
>>>
>>> device tree exports separate nodes for high and normal priority FIFOs
>>> per each NX instance. But NX init OPAL function is called once per
>>> each NX instance when high-FIFO device node is parsed to reset high
>>> and normal FIFO control registers. As you see in skiboot patch, resets
>>> both priority registers. Thought we should minimize the number of OPAL
>>> calla execution and also should have generic NX init OPAL call. We can
>>> extend this call to reset default values for any other registers if
>>> needed.
>>
>> This code does'nt do that though, it calls it for "high" priority, so if
>> for whatever reason there was a DT without a "High" priority node there,
>> it'd not call it.
>
> Skiboot exports high and normal FIFO nodes for each coprocessor type
> per NX instance. We will never see only normal FIFO node without high
> FIFO node. As we see in skiboot code, configure high FIFO and export
> this node first, and then normal FIFO. In case if xscom read/ write
> for high FIFO failed, we do not proceed for normal FIFO.
Currently that's true, yes. But in the future it may not be. Imagine if
we found a hardware bug that would mean disabling the 'High' priority
one, or a future chip revision just had a single priority.
--
Stewart Smith
OPAL Architect, IBM.
^ permalink raw reply
* Re: [PATCH] crypto/nx: Initialize 842 high and normal RxFIFO control registers
From: Haren Myneni @ 2018-06-04 2:44 UTC (permalink / raw)
To: Stewart Smith; +Cc: mpe, linuxppc-dev, herbert, linux-crypto
In-Reply-To: <87bmcr2xj4.fsf@linux.vnet.ibm.com>
On 06/03/2018 05:41 PM, Stewart Smith wrote:
> Haren Myneni <haren@linux.vnet.ibm.com> writes:
>> On 06/01/2018 12:41 AM, Stewart Smith wrote:
>>> Haren Myneni <haren@linux.vnet.ibm.com> writes:
>>>> NX increments readOffset by FIFO size in receive FIFO control register
>>>> when CRB is read. But the index in RxFIFO has to match with the
>>>> corresponding entry in FIFO maintained by VAS in kernel. Otherwise NX
>>>> may be processing incorrect CRBs and can cause CRB timeout.
>>>>
>>>> VAS FIFO offset is 0 when the receive window is opened during
>>>> initialization. When the module is reloaded or in kexec boot, readOffset
>>>> in FIFO control register may not match with VAS entry. This patch adds
>>>> nx_coproc_init OPAL call to reset readOffset and queued entries in FIFO
>>>> control register for both high and normal FIFOs.
>>>>
>>>> Signed-off-by: Haren Myneni <haren@us.ibm.com>
>>>>
>>>> diff --git a/arch/powerpc/include/asm/opal-api.h b/arch/powerpc/include/asm/opal-api.h
>>>> index d886a5b..ff61e4b 100644
>>>> --- a/arch/powerpc/include/asm/opal-api.h
>>>> +++ b/arch/powerpc/include/asm/opal-api.h
>>>> @@ -206,7 +206,8 @@
>>>> #define OPAL_NPU_TL_SET 161
>>>> #define OPAL_PCI_GET_PBCQ_TUNNEL_BAR 164
>>>> #define OPAL_PCI_SET_PBCQ_TUNNEL_BAR 165
>>>> -#define OPAL_LAST 165
>>>> +#define OPAL_NX_COPROC_INIT 167
>>>> +#define OPAL_LAST 167
>>>>
>>>> /* Device tree flags */
>>>>
>>>> diff --git a/arch/powerpc/include/asm/opal.h b/arch/powerpc/include/asm/opal.h
>>>> index 7159e1a..d79eb82 100644
>>>> --- a/arch/powerpc/include/asm/opal.h
>>>> +++ b/arch/powerpc/include/asm/opal.h
>>>> @@ -288,6 +288,7 @@ int64_t opal_imc_counters_init(uint32_t type, uint64_t address,
>>>> int opal_get_power_shift_ratio(u32 handle, int token, u32 *psr);
>>>> int opal_set_power_shift_ratio(u32 handle, int token, u32 psr);
>>>> int opal_sensor_group_clear(u32 group_hndl, int token);
>>>> +int opal_nx_coproc_init(uint32_t chip_id, uint32_t ct);
>>>>
>>>> s64 opal_signal_system_reset(s32 cpu);
>>>>
>>>> diff --git a/arch/powerpc/platforms/powernv/opal-wrappers.S b/arch/powerpc/platforms/powernv/opal-wrappers.S
>>>> index 3da30c2..c7541a9 100644
>>>> --- a/arch/powerpc/platforms/powernv/opal-wrappers.S
>>>> +++ b/arch/powerpc/platforms/powernv/opal-wrappers.S
>>>> @@ -325,3 +325,4 @@ OPAL_CALL(opal_npu_spa_clear_cache, OPAL_NPU_SPA_CLEAR_CACHE);
>>>> OPAL_CALL(opal_npu_tl_set, OPAL_NPU_TL_SET);
>>>> OPAL_CALL(opal_pci_get_pbcq_tunnel_bar, OPAL_PCI_GET_PBCQ_TUNNEL_BAR);
>>>> OPAL_CALL(opal_pci_set_pbcq_tunnel_bar, OPAL_PCI_SET_PBCQ_TUNNEL_BAR);
>>>> +OPAL_CALL(opal_nx_coproc_init, OPAL_NX_COPROC_INIT);
>>>> diff --git a/arch/powerpc/platforms/powernv/opal.c b/arch/powerpc/platforms/powernv/opal.c
>>>> index 48fbb41..5e13908 100644
>>>> --- a/arch/powerpc/platforms/powernv/opal.c
>>>> +++ b/arch/powerpc/platforms/powernv/opal.c
>>>> @@ -1035,3 +1035,5 @@ void powernv_set_nmmu_ptcr(unsigned long ptcr)
>>>> EXPORT_SYMBOL_GPL(opal_int_set_mfrr);
>>>> EXPORT_SYMBOL_GPL(opal_int_eoi);
>>>> EXPORT_SYMBOL_GPL(opal_error_code);
>>>> +/* Export the below symbol for NX compression */
>>>> +EXPORT_SYMBOL(opal_nx_coproc_init);
>>>> diff --git a/drivers/crypto/nx/nx-842-powernv.c b/drivers/crypto/nx/nx-842-powernv.c
>>>> index 1e87637..6c4784d 100644
>>>> --- a/drivers/crypto/nx/nx-842-powernv.c
>>>> +++ b/drivers/crypto/nx/nx-842-powernv.c
>>>> @@ -24,6 +24,8 @@
>>>> #include <asm/icswx.h>
>>>> #include <asm/vas.h>
>>>> #include <asm/reg.h>
>>>> +#include <asm/opal-api.h>
>>>> +#include <asm/opal.h>
>>>>
>>>> MODULE_LICENSE("GPL");
>>>> MODULE_AUTHOR("Dan Streetman <ddstreet@ieee.org>");
>>>> @@ -803,9 +805,26 @@ static int __init vas_cfg_coproc_info(struct device_node *dn, int chip_id,
>>>> if (!coproc)
>>>> return -ENOMEM;
>>>>
>>>> - if (!strcmp(priority, "High"))
>>>> + if (!strcmp(priority, "High")) {
>>>> + /*
>>>> + * (lpid, pid, tid) combination has to be unique for each
>>>> + * coprocessor instance in the system. So to make it
>>>> + * unique, skiboot uses coprocessor type such as 842 or
>>>> + * GZIP for pid and provides this value to kernel in pid
>>>> + * device-tree property.
>>>> + *
>>>> + * Initialize each NX instance for both high and normal
>>>> + * priority FIFOs.
>>>> + */
>>>> + ret = opal_nx_coproc_init(chip_id, pid);
>>>> + if (ret) {
>>>> + pr_err("Failed to initialize NX coproc: %d\n", ret);
>>>> + ret = opal_error_code(ret);
>>>> + goto err_out;
>>>> + }
>>>> +
>>>> coproc->ct = VAS_COP_TYPE_842_HIPRI;
>>>
>>> I think this should be called for all priority queues as it would be at
>>> least theoretically possible to only have Normal priority queues, in
>>> which case this patch wouldn't fix the problem.
>>
>> device tree exports separate nodes for high and normal priority FIFOs
>> per each NX instance. But NX init OPAL function is called once per
>> each NX instance when high-FIFO device node is parsed to reset high
>> and normal FIFO control registers. As you see in skiboot patch, resets
>> both priority registers. Thought we should minimize the number of OPAL
>> calla execution and also should have generic NX init OPAL call. We can
>> extend this call to reset default values for any other registers if
>> needed.
>
> This code does'nt do that though, it calls it for "high" priority, so if
> for whatever reason there was a DT without a "High" priority node there,
> it'd not call it.
Skiboot exports high and normal FIFO nodes for each coprocessor type per NX instance. We will never see only normal FIFO node without high FIFO node. As we see in skiboot code, configure high FIFO and export this node first, and then normal FIFO. In case if xscom read/ write for high FIFO failed, we do not proceed for normal FIFO.
Also, we use only high priority FIFOs in kernel (nx-842). Normal FIFOs are reserved only for user space use (NX GZIP in future).
So we will not get in to the case that you described. Normal FIFO DT node will be available only with high FIFO node per each NX instance.
>
>> If you prefer calling separately based on priority, we can have
>> opal_nx_coproc_FIFO_init(chip_id, pid, priority). Please let me know.
>
> I think the call is okay, it's just that if it needs to be called once
> per accellerator, then we should ensure it does that.
>
^ permalink raw reply
* Re: powerpc/powernv: copy/paste - Mask XERS0 bit in CR
From: Haren Myneni @ 2018-06-04 2:15 UTC (permalink / raw)
To: Michael Ellerman; +Cc: linuxppc-dev, sukadev
In-Reply-To: <87r2lokuxb.fsf@concordia.ellerman.id.au>
On 06/03/2018 03:48 AM, Michael Ellerman wrote:
> Hi Haren,
>
> Haren Myneni <haren@linux.vnet.ibm.com> writes:
>>
>> NX can set 3rd bit in CR register for XER[SO] (Summation overflow)
>> which is not related to paste request. The current paste function
>> returns failure for the successful request when this bit is set.
>> So mask this bit and check the proper return status.
>>
>> Fixes: 2392c8c8c045 ("powerpc/powernv/vas: Define copy/paste interfaces")
>> Cc: stable@vger.kernel.org # v4.14+
>> Signed-off-by: Haren Myneni <haren@us.ibm.com>
>>
>> diff --git a/arch/powerpc/platforms/powernv/copy-paste.h b/arch/powerpc/platforms/powernv/copy-paste.h
>> index c9a5036..82392e3 100644
>> --- a/arch/powerpc/platforms/powernv/copy-paste.h
>> +++ b/arch/powerpc/platforms/powernv/copy-paste.h
>> @@ -9,7 +9,8 @@
>> #include <asm/ppc-opcode.h>
>>
>> #define CR0_SHIFT 28
>> -#define CR0_MASK 0xF
>> +#define CR0_MASK 0xE /* 3rd bit undefined or set for XER[SO] */
>> +
>> /*
>> * Copy/paste instructions:
>> *
>
> Unfortunately this no longer applies to my next branch, because those
> macros have been moved out of this header as part of an unrelated patch.
>
> The following patch should work instead, can you please confirm by
> testing it?
>
> diff --git a/arch/powerpc/platforms/powernv/copy-paste.h b/arch/powerpc/platforms/powernv/copy-paste.h
> index 3fa62de96d9c..c46a326776cf 100644
> --- a/arch/powerpc/platforms/powernv/copy-paste.h
> +++ b/arch/powerpc/platforms/powernv/copy-paste.h
> @@ -41,5 +41,7 @@ static inline int vas_paste(void *paste_address, int offset)
> : "b" (offset), "b" (paste_address)
> : "memory", "cr0");
>
> - return (cr >> CR0_SHIFT) & CR0_MASK;
> +
> + /* We mask with 0xE to ignore SO */
> + return (cr >> CR0_SHIFT) & 0xE;
> }
>
>
Tested with this patch and it works.
Thanks
Haren
> cheers
>
^ permalink raw reply
* Re: [PATCH v2 07/13] powerpc/eeh: Clean up pci_ers_result handling
From: Sam Bobroff @ 2018-06-04 1:28 UTC (permalink / raw)
To: Michael Ellerman; +Cc: linuxppc-dev
In-Reply-To: <87muwe3475.fsf@concordia.ellerman.id.au>
[-- Attachment #1: Type: text/plain, Size: 4454 bytes --]
On Sat, Jun 02, 2018 at 01:40:46AM +1000, Michael Ellerman wrote:
> Sam Bobroff <sbobroff@linux.ibm.com> writes:
>
> > As EEH event handling progresses, a cumulative result of type
> > pci_ers_result is built up by (some of) the eeh_report_*() functions
> > using either:
> > if (rc == PCI_ERS_RESULT_NEED_RESET) *res = rc;
> > if (*res == PCI_ERS_RESULT_NONE) *res = rc;
> > or:
> > if ((*res == PCI_ERS_RESULT_NONE) ||
> > (*res == PCI_ERS_RESULT_RECOVERED)) *res = rc;
> > if (*res == PCI_ERS_RESULT_DISCONNECT &&
> > rc == PCI_ERS_RESULT_NEED_RESET) *res = rc;
> > (Where *res is the accumulator.)
> >
> > However, the intent is not immediately clear and the result in some
> > situations is order dependent.
> >
> > Address this by assigning a priority to each result value, and always
> > merging to the highest priority. This renders the intent clear, and
> > provides a stable value for all orderings.
> >
> > Signed-off-by: Sam Bobroff <sbobroff@linux.ibm.com>
> > ---
> > ====== v1 -> v2: ======
> >
> > * Added the value, and missing newline, to some WARN()s.
> > * Improved name of merge_result() to pci_ers_merge_result().
> > * Adjusted the result priorities so that unknown doesn't overlap with _NONE.
>
> These === markers seem to have confused patchwork, they ended up in the
> patch, and then git put them in the changelog.
>
> http://patchwork.ozlabs.org/patch/920194/
>
> The usual format is just something like:
>
> v2 - Added the value, and missing newline, to some WARN()s.
> - Improved name of merge_result() to pci_ers_merge_result().
> - Adjusted the result priorities so that unknown doesn't overlap with _NONE.
>
> cheers
Oh! I'll change it!
Sam.
>
> > arch/powerpc/kernel/eeh_driver.c | 36 ++++++++++++++++++++++++++----------
> > 1 file changed, 26 insertions(+), 10 deletions(-)
> >
> > diff --git a/arch/powerpc/kernel/eeh_driver.c b/arch/powerpc/kernel/eeh_driver.c
> > index 188d15c4fe3a..2d3cac584899 100644
> > --- a/arch/powerpc/kernel/eeh_driver.c
> > +++ b/arch/powerpc/kernel/eeh_driver.c
> > @@ -39,6 +39,29 @@ struct eeh_rmv_data {
> > int removed;
> > };
> >
> > +static int eeh_result_priority(enum pci_ers_result result)
> > +{
> > + switch (result) {
> > + case PCI_ERS_RESULT_NONE: return 1;
> > + case PCI_ERS_RESULT_NO_AER_DRIVER: return 2;
> > + case PCI_ERS_RESULT_RECOVERED: return 3;
> > + case PCI_ERS_RESULT_CAN_RECOVER: return 4;
> > + case PCI_ERS_RESULT_DISCONNECT: return 5;
> > + case PCI_ERS_RESULT_NEED_RESET: return 6;
> > + default:
> > + WARN_ONCE(1, "Unknown pci_ers_result value: %d\n", (int)result);
> > + return 0;
> > + }
> > +};
> > +
> > +static enum pci_ers_result pci_ers_merge_result(enum pci_ers_result old,
> > + enum pci_ers_result new)
> > +{
> > + if (eeh_result_priority(new) > eeh_result_priority(old))
> > + return new;
> > + return old;
> > +}
> > +
> > /**
> > * eeh_pcid_get - Get the PCI device driver
> > * @pdev: PCI device
> > @@ -206,9 +229,7 @@ static void *eeh_report_error(struct eeh_dev *edev, void *userdata)
> >
> > rc = driver->err_handler->error_detected(dev, pci_channel_io_frozen);
> >
> > - /* A driver that needs a reset trumps all others */
> > - if (rc == PCI_ERS_RESULT_NEED_RESET) *res = rc;
> > - if (*res == PCI_ERS_RESULT_NONE) *res = rc;
> > + *res = pci_ers_merge_result(*res, rc);
> >
> > edev->in_error = true;
> > pci_uevent_ers(dev, PCI_ERS_RESULT_NONE);
> > @@ -249,9 +270,7 @@ static void *eeh_report_mmio_enabled(struct eeh_dev *edev, void *userdata)
> >
> > rc = driver->err_handler->mmio_enabled(dev);
> >
> > - /* A driver that needs a reset trumps all others */
> > - if (rc == PCI_ERS_RESULT_NEED_RESET) *res = rc;
> > - if (*res == PCI_ERS_RESULT_NONE) *res = rc;
> > + *res = pci_ers_merge_result(*res, rc);
> >
> > out:
> > eeh_pcid_put(dev);
> > @@ -294,10 +313,7 @@ static void *eeh_report_reset(struct eeh_dev *edev, void *userdata)
> > goto out;
> >
> > rc = driver->err_handler->slot_reset(dev);
> > - if ((*res == PCI_ERS_RESULT_NONE) ||
> > - (*res == PCI_ERS_RESULT_RECOVERED)) *res = rc;
> > - if (*res == PCI_ERS_RESULT_DISCONNECT &&
> > - rc == PCI_ERS_RESULT_NEED_RESET) *res = rc;
> > + *res = pci_ers_merge_result(*res, rc);
> >
> > out:
> > eeh_pcid_put(dev);
> > --
> > 2.16.1.74.g9b0b1f47b
>
[-- Attachment #2: signature.asc --]
[-- Type: application/pgp-signature, Size: 488 bytes --]
^ permalink raw reply
* Re: [PATCH] crypto/nx: Initialize 842 high and normal RxFIFO control registers
From: Stewart Smith @ 2018-06-04 0:41 UTC (permalink / raw)
To: Haren Myneni; +Cc: mpe, linuxppc-dev, herbert, linux-crypto
In-Reply-To: <5B117946.8010100@linux.vnet.ibm.com>
Haren Myneni <haren@linux.vnet.ibm.com> writes:
> On 06/01/2018 12:41 AM, Stewart Smith wrote:
>> Haren Myneni <haren@linux.vnet.ibm.com> writes:
>>> NX increments readOffset by FIFO size in receive FIFO control register
>>> when CRB is read. But the index in RxFIFO has to match with the
>>> corresponding entry in FIFO maintained by VAS in kernel. Otherwise NX
>>> may be processing incorrect CRBs and can cause CRB timeout.
>>>
>>> VAS FIFO offset is 0 when the receive window is opened during
>>> initialization. When the module is reloaded or in kexec boot, readOffset
>>> in FIFO control register may not match with VAS entry. This patch adds
>>> nx_coproc_init OPAL call to reset readOffset and queued entries in FIFO
>>> control register for both high and normal FIFOs.
>>>
>>> Signed-off-by: Haren Myneni <haren@us.ibm.com>
>>>
>>> diff --git a/arch/powerpc/include/asm/opal-api.h b/arch/powerpc/include/asm/opal-api.h
>>> index d886a5b..ff61e4b 100644
>>> --- a/arch/powerpc/include/asm/opal-api.h
>>> +++ b/arch/powerpc/include/asm/opal-api.h
>>> @@ -206,7 +206,8 @@
>>> #define OPAL_NPU_TL_SET 161
>>> #define OPAL_PCI_GET_PBCQ_TUNNEL_BAR 164
>>> #define OPAL_PCI_SET_PBCQ_TUNNEL_BAR 165
>>> -#define OPAL_LAST 165
>>> +#define OPAL_NX_COPROC_INIT 167
>>> +#define OPAL_LAST 167
>>>
>>> /* Device tree flags */
>>>
>>> diff --git a/arch/powerpc/include/asm/opal.h b/arch/powerpc/include/asm/opal.h
>>> index 7159e1a..d79eb82 100644
>>> --- a/arch/powerpc/include/asm/opal.h
>>> +++ b/arch/powerpc/include/asm/opal.h
>>> @@ -288,6 +288,7 @@ int64_t opal_imc_counters_init(uint32_t type, uint64_t address,
>>> int opal_get_power_shift_ratio(u32 handle, int token, u32 *psr);
>>> int opal_set_power_shift_ratio(u32 handle, int token, u32 psr);
>>> int opal_sensor_group_clear(u32 group_hndl, int token);
>>> +int opal_nx_coproc_init(uint32_t chip_id, uint32_t ct);
>>>
>>> s64 opal_signal_system_reset(s32 cpu);
>>>
>>> diff --git a/arch/powerpc/platforms/powernv/opal-wrappers.S b/arch/powerpc/platforms/powernv/opal-wrappers.S
>>> index 3da30c2..c7541a9 100644
>>> --- a/arch/powerpc/platforms/powernv/opal-wrappers.S
>>> +++ b/arch/powerpc/platforms/powernv/opal-wrappers.S
>>> @@ -325,3 +325,4 @@ OPAL_CALL(opal_npu_spa_clear_cache, OPAL_NPU_SPA_CLEAR_CACHE);
>>> OPAL_CALL(opal_npu_tl_set, OPAL_NPU_TL_SET);
>>> OPAL_CALL(opal_pci_get_pbcq_tunnel_bar, OPAL_PCI_GET_PBCQ_TUNNEL_BAR);
>>> OPAL_CALL(opal_pci_set_pbcq_tunnel_bar, OPAL_PCI_SET_PBCQ_TUNNEL_BAR);
>>> +OPAL_CALL(opal_nx_coproc_init, OPAL_NX_COPROC_INIT);
>>> diff --git a/arch/powerpc/platforms/powernv/opal.c b/arch/powerpc/platforms/powernv/opal.c
>>> index 48fbb41..5e13908 100644
>>> --- a/arch/powerpc/platforms/powernv/opal.c
>>> +++ b/arch/powerpc/platforms/powernv/opal.c
>>> @@ -1035,3 +1035,5 @@ void powernv_set_nmmu_ptcr(unsigned long ptcr)
>>> EXPORT_SYMBOL_GPL(opal_int_set_mfrr);
>>> EXPORT_SYMBOL_GPL(opal_int_eoi);
>>> EXPORT_SYMBOL_GPL(opal_error_code);
>>> +/* Export the below symbol for NX compression */
>>> +EXPORT_SYMBOL(opal_nx_coproc_init);
>>> diff --git a/drivers/crypto/nx/nx-842-powernv.c b/drivers/crypto/nx/nx-842-powernv.c
>>> index 1e87637..6c4784d 100644
>>> --- a/drivers/crypto/nx/nx-842-powernv.c
>>> +++ b/drivers/crypto/nx/nx-842-powernv.c
>>> @@ -24,6 +24,8 @@
>>> #include <asm/icswx.h>
>>> #include <asm/vas.h>
>>> #include <asm/reg.h>
>>> +#include <asm/opal-api.h>
>>> +#include <asm/opal.h>
>>>
>>> MODULE_LICENSE("GPL");
>>> MODULE_AUTHOR("Dan Streetman <ddstreet@ieee.org>");
>>> @@ -803,9 +805,26 @@ static int __init vas_cfg_coproc_info(struct device_node *dn, int chip_id,
>>> if (!coproc)
>>> return -ENOMEM;
>>>
>>> - if (!strcmp(priority, "High"))
>>> + if (!strcmp(priority, "High")) {
>>> + /*
>>> + * (lpid, pid, tid) combination has to be unique for each
>>> + * coprocessor instance in the system. So to make it
>>> + * unique, skiboot uses coprocessor type such as 842 or
>>> + * GZIP for pid and provides this value to kernel in pid
>>> + * device-tree property.
>>> + *
>>> + * Initialize each NX instance for both high and normal
>>> + * priority FIFOs.
>>> + */
>>> + ret = opal_nx_coproc_init(chip_id, pid);
>>> + if (ret) {
>>> + pr_err("Failed to initialize NX coproc: %d\n", ret);
>>> + ret = opal_error_code(ret);
>>> + goto err_out;
>>> + }
>>> +
>>> coproc->ct = VAS_COP_TYPE_842_HIPRI;
>>
>> I think this should be called for all priority queues as it would be at
>> least theoretically possible to only have Normal priority queues, in
>> which case this patch wouldn't fix the problem.
>
> device tree exports separate nodes for high and normal priority FIFOs
> per each NX instance. But NX init OPAL function is called once per
> each NX instance when high-FIFO device node is parsed to reset high
> and normal FIFO control registers. As you see in skiboot patch, resets
> both priority registers. Thought we should minimize the number of OPAL
> calla execution and also should have generic NX init OPAL call. We can
> extend this call to reset default values for any other registers if
> needed.
This code does'nt do that though, it calls it for "high" priority, so if
for whatever reason there was a DT without a "High" priority node there,
it'd not call it.
> If you prefer calling separately based on priority, we can have
> opal_nx_coproc_FIFO_init(chip_id, pid, priority). Please let me know.
I think the call is okay, it's just that if it needs to be called once
per accellerator, then we should ensure it does that.
--
Stewart Smith
OPAL Architect, IBM.
^ permalink raw reply
* Re: pkeys on POWER: Access rights not reset on execve
From: Ram Pai @ 2018-06-03 20:18 UTC (permalink / raw)
To: Florian Weimer; +Cc: Andy Lutomirski, Linux-MM, linuxppc-dev, Dave Hansen
In-Reply-To: <aae1952c-886b-cfc8-e98b-fa3be5fab0fa@redhat.com>
On Mon, May 21, 2018 at 01:29:11PM +0200, Florian Weimer wrote:
> On 05/20/2018 09:11 PM, Ram Pai wrote:
> >Florian,
> >
> > Does the following patch fix the problem for you? Just like x86
> > I am enabling all keys in the UAMOR register during
> > initialization itself. Hence any key created by any thread at
> > any time, will get activated on all threads. So any thread
> > can change the permission on that key. Smoke tested it
> > with your test program.
>
> I think this goes in the right direction, but the AMR value after
> fork is still strange:
>
> AMR (PID 34912): 0x0000000000000000
> AMR after fork (PID 34913): 0x0000000000000000
> AMR (PID 34913): 0x0000000000000000
> Allocated key in subprocess (PID 34913): 2
> Allocated key (PID 34912): 2
> Setting AMR: 0xffffffffffffffff
> New AMR value (PID 34912): 0x0fffffffffffffff
> About to call execl (PID 34912) ...
> AMR (PID 34912): 0x0fffffffffffffff
> AMR after fork (PID 34914): 0x0000000000000003
> AMR (PID 34914): 0x0000000000000003
> Allocated key in subprocess (PID 34914): 2
> Allocated key (PID 34912): 2
> Setting AMR: 0xffffffffffffffff
> New AMR value (PID 34912): 0x0fffffffffffffff
>
> I mean this line:
>
> AMR after fork (PID 34914): 0x0000000000000003
>
> Shouldn't it be the same as in the parent process?
Fixed it. Please try this patch. If it all works to your satisfaction, I
will clean it up further and send to Michael Ellermen(ppc maintainer).
commit 51f4208ed5baeab1edb9b0f8b68d7144449b3527
Author: Ram Pai <linuxram@us.ibm.com>
Date: Sun Jun 3 14:44:32 2018 -0500
Fix for the fork bug.
Signed-off-by: Ram Pai <linuxram@us.ibm.com>
diff --git a/arch/powerpc/kernel/process.c b/arch/powerpc/kernel/process.c
index 1237f13..999dd08 100644
--- a/arch/powerpc/kernel/process.c
+++ b/arch/powerpc/kernel/process.c
@@ -582,6 +582,7 @@ static void save_all(struct task_struct *tsk)
__giveup_spe(tsk);
msr_check_and_clear(msr_all_available);
+ thread_pkey_regs_save(&tsk->thread);
}
void flush_all_to_thread(struct task_struct *tsk)
diff --git a/arch/powerpc/mm/pkeys.c b/arch/powerpc/mm/pkeys.c
index ab4519a..af6aa4a 100644
--- a/arch/powerpc/mm/pkeys.c
+++ b/arch/powerpc/mm/pkeys.c
@@ -294,6 +294,7 @@ void thread_pkey_regs_save(struct thread_struct *thread)
*/
thread->amr = read_amr();
thread->iamr = read_iamr();
+ thread->uamor = read_uamor();
}
void thread_pkey_regs_restore(struct thread_struct *new_thread,
@@ -315,9 +316,13 @@ void thread_pkey_regs_init(struct thread_struct *thread)
if (static_branch_likely(&pkey_disabled))
return;
- thread->amr = read_amr() & pkey_amr_mask;
- thread->iamr = read_iamr() & pkey_iamr_mask;
+ thread->amr = pkey_amr_mask;
+ thread->iamr = pkey_iamr_mask;
thread->uamor = pkey_uamor_mask;
+
+ write_uamor(pkey_uamor_mask);
+ write_amr(pkey_amr_mask);
+ write_iamr(pkey_iamr_mask);
}
static inline bool pkey_allows_readwrite(int pkey)
>
> Thanks,
> Florian
--
Ram Pai
^ permalink raw reply related
page: next (older) | prev (newer) | latest
- recent:[subjects (threaded)|topics (new)|topics (active)]
This is a public inbox, see mirroring instructions
for how to clone and mirror all data and code used for this inbox