[Skiboot] [PATCH 3/5] NX: Add P9 NX support for 842 compression engine

Sukadev Bhattiprolu sukadev at linux.vnet.ibm.com
Wed Feb 22 07:07:09 AEDT 2017


Haren Myneni [haren at linux.vnet.ibm.com] wrote:
> 
> This patch adds changes needed for 842 compression engine on power 9.
> Virtual Accelerator Switch (VAS) is used to access NX 842 engine on P9
> and the chasnnel setup be will done with receive FIFO. So RxFIFO
> address, logical partition ID (lpid), process ID (pid) and thread ID
> (tid) are used for this setup. p9 NX supports high and normal priority
> FIFOs. skiboot is not involved to process data with 842 engine, but
> configures User Mode Access Control (UMAC) registers with these values
> and provide them to kernel.
> 
> Also configures registers to setup and enable / disable the engine with

nit: /configures/configure the/

> the appropriate registers. Creates the following device-tree entries to
> provide RxFIFO address, lpid, pid and tid values so that kernel can
> drive P9 NX 842 engine.
> 
>    /ibm,nx-842-high	: High priority 842 RxFIFO
>    /ibm,nx-842-normal	: Normal priority 842 RxFIFO

These nodes are in the xscom* directory? Would be useful to mention that.
> 
> Each RxFIFO node contains:
>    rx-fifo-address	: Address represents for RxFIFO buffer

nit: s/represents for/of/

Maybe a note to say that we want to allocate a large contiguous buffer
so we allocate in skiboot and pass address to kernel?

>    lpid			: Chip ID
>    pid			: 842 coprocessor type
>    tid 			: Priority (either high or normal)

Does the hardware require these mapping or is it just a simple way of
finding unique values for LPID/PID/TID? If so, see also the GCID2LPID()
suggestion below.

> 
> Signed-off-by: Haren Myneni <haren at us.ibm.com>
> ---
>  hw/nx-842.c      |   68 ++++++++++++++++++--
>  hw/nx-compress.c |  178 +++++++++++++++++++++++++++++++++++++++++++++++++++++-
>  include/nx.h     |    4 +
>  3 files changed, 242 insertions(+), 8 deletions(-)
> 
> diff --git a/hw/nx-842.c b/hw/nx-842.c
> index 3ccb549..a284803 100644
> --- a/hw/nx-842.c
> +++ b/hw/nx-842.c
> @@ -20,12 +20,13 @@
>  #include <io.h>
>  #include <cpu.h>
>  #include <nx.h>
> +#include <vas.h>
> 
>  /* Configuration settings */
>  #define CFG_842_FC_ENABLE	(0x1f) /* enable all 842 functions */
>  #define CFG_842_ENABLE		(1) /* enable 842 engines */
> -#define DMA_COMPRESS_PREFETCH	(1) /* enable prefetching (on P8) */
> -#define DMA_DECOMPRESS_PREFETCH	(1) /* enable prefetching (on P8) */
> +#define DMA_COMPRESS_PREFETCH	(1) /* enable prefetching (on P8 or P9) */
> +#define DMA_DECOMPRESS_PREFETCH	(1) /* enable prefetching (on P8 or P9) */
>  #define DMA_COMPRESS_MAX_RR	(15) /* range 1-15 */
>  #define DMA_DECOMPRESS_MAX_RR	(15) /* range 1-15 */
>  #define DMA_SPBC		(1) /* write SPBC in CPB */
> @@ -90,6 +91,32 @@ static int nx_cfg_842(u32 gcid, u64 xcfg)
>  	return rc;
>  }
> 
> +static int nx_cfg_842_umac(struct dt_node *node, u32 gcid, u32 pb_base)
> +{	
> +	int rc;
> +	u64 umac_bar, umac_ctrl, umac_notify;
> +	struct dt_node *nx_node;
> +	
> +	nx_node = dt_new(node, "ibm,nx-842-high");
> +	umac_bar = pb_base + NX_P9_842_HIGH_PRI_RX_FIFO_BAR;
> +	umac_ctrl = pb_base + NX_P9_842_HIGH_PRI_RX_FIFO_CTRL;
> +	umac_notify = pb_base + NX_P9_842_HIGH_PRI_RX_FIFO_NOTIFY_MATCH;
> +	rc = nx_set_rx_fifo(nx_node, gcid, umac_bar, umac_notify, umac_ctrl,
> +				NX_CT_842, RX_FIFO_HIGH_PRIORITY);
> +	if (rc)
> +		return rc;
> +
> +	nx_node= dt_new(node, "ibm,nx-842-normal");
> +	umac_bar = pb_base + NX_P9_842_NORMAL_PRI_RX_FIFO_BAR;
> +	umac_ctrl = pb_base + NX_P9_842_NORMAL_PRI_RX_FIFO_CTRL;
> +	umac_notify = pb_base + NX_P9_842_NORMAL_PRI_RX_FIFO_NOTIFY_MATCH;
> +	rc = nx_set_rx_fifo(nx_node, gcid, umac_bar, umac_notify, umac_ctrl,
> +				NX_CT_842, RX_FIFO_NORMAL_PRIORITY);
> +
nit: extra new line.
> +	
> +	return rc;
> +}
> +
>  static int nx_cfg_842_dma(u32 gcid, u64 xcfg)
>  {
>  	u64 cfg;
> @@ -99,7 +126,7 @@ static int nx_cfg_842_dma(u32 gcid, u64 xcfg)
>  	if (rc)
>  		return rc;
> 
> -	if (proc_gen == proc_gen_p8) {
> +	if (proc_gen >= proc_gen_p8) {
>  		cfg = SETFIELD(NX_DMA_CFG_842_COMPRESS_PREFETCH, cfg,
>  			       DMA_COMPRESS_PREFETCH);
>  		cfg = SETFIELD(NX_DMA_CFG_842_DECOMPRESS_PREFETCH, cfg,
> @@ -112,14 +139,16 @@ static int nx_cfg_842_dma(u32 gcid, u64 xcfg)
>  		       DMA_DECOMPRESS_MAX_RR);
>  	cfg = SETFIELD(NX_DMA_CFG_842_SPBC, cfg,
>  		       DMA_SPBC);
> -	cfg = SETFIELD(NX_DMA_CFG_842_CSB_WR, cfg,
> +	if (proc_gen < proc_gen_p9) {
> +		cfg = SETFIELD(NX_DMA_CFG_842_CSB_WR, cfg,
>  		       DMA_CSB_WR);
> -	cfg = SETFIELD(NX_DMA_CFG_842_COMPLETION_MODE, cfg,
> +		cfg = SETFIELD(NX_DMA_CFG_842_COMPLETION_MODE, cfg,
>  		       DMA_COMPLETION_MODE);
> -	cfg = SETFIELD(NX_DMA_CFG_842_CPB_WR, cfg,
> +		cfg = SETFIELD(NX_DMA_CFG_842_CPB_WR, cfg,
>  		       DMA_CPB_WR);
> -	cfg = SETFIELD(NX_DMA_CFG_842_OUTPUT_DATA_WR, cfg,
> +		cfg = SETFIELD(NX_DMA_CFG_842_OUTPUT_DATA_WR, cfg,
>  		       DMA_OUTPUT_DATA_WR);
> +	}
> 
>  	rc = xscom_write(gcid, xcfg, cfg);
>  	if (rc)
> @@ -188,3 +217,28 @@ void nx_enable_842(struct dt_node *node, u32 gcid, u32 pb_base)
>  	dt_add_property_cells(node, "ibm,842-coprocessor-type", NX_CT_842);
>  	dt_add_property_cells(node, "ibm,842-coprocessor-instance", gcid + 1);
>  }
> +
> +void p9_nx_enable_842(struct dt_node *node, u32 gcid, u32 pb_base)
> +{
> +	u64 cfg_dma, cfg_ee;
> +	int rc;
> +
> +	cfg_dma = pb_base + NX_P9_DMA_CFG;
> +	cfg_ee = pb_base + NX_P9_EE_CFG;
> +
> +	rc = nx_cfg_842_dma(gcid, cfg_dma);
> +	if (rc) 
> +		return;
> +
> +	rc = nx_cfg_842_umac(node, gcid, pb_base);
> +	if (rc)
> +		return;
> +
> +	rc = nx_cfg_842_ee(gcid, cfg_ee);
> +	if (rc)
> +		return;
> +
> +	prlog(PR_INFO, "NX%d: 842 Coprocessor Enabled\n", gcid);
> +
> +}
> +
> diff --git a/hw/nx-compress.c b/hw/nx-compress.c
> index 2ea2734..b4abe9e 100644
> --- a/hw/nx-compress.c
> +++ b/hw/nx-compress.c
> @@ -20,15 +20,191 @@
>  #include <io.h>
>  #include <cpu.h>
>  #include <nx.h>
> +#include <vas.h>
> +
> +static int nx_cfg_umac_tx_wc(u32 gcid, u64 xcfg)
> +{
> +	int rc = 0;
> +	u64 cfg;
> +
> +	cfg = vas_get_wcbs_bar(gcid);
> +	if (!cfg) {
> +		prerror("NX%d: ERROR finding WC Backing store BAR\n", gcid);
> +		return -ENOMEM;
> +	}
> +
> +	/*
> +	 * NOTE: Write the entire bar address to SCOM. VAS/NX will extract
> +	 *       the relevant (NX_P9_UMAC_TX_WINDOW_CONTEXT_ADDR) bits.
> +	 *       IOW, _don't_:

s/:/just write the bit field like:/

> +	 *
> +	 *       cfg = SETFIELD(NX_P9_UMAC_TX_WINDOW_CONTEXT_ADDR, 0ULL, cfg);
> +	 */
> +	rc = xscom_write (gcid, xcfg, cfg);
> +
> +	if (rc)
> +		prerror("NX%d: ERROR: UMAC SEND WC BAR, %d\n", gcid, rc);
> +	else
> +		prlog(PR_DEBUG,"NX%d: UMAC SEND WC BAR, 0x%016lx, " 
> +				"xcfg 0x%llx\n",
> +			gcid, (unsigned long)cfg, xcfg);
> +
> +	return rc;
> +}
> +
> +static int nx_cfg_umac_vas_mmio(u32 gcid, u64 xcfg)
> +{
> +	int rc = 0;
> +	u64 cfg;
> +
> +	cfg = vas_get_hvwc_mmio_bar(gcid);
> +	/*
> +	 * NOTE: Write the entire bar address to SCOM. VAS/NX will extract
> +	 *       the relevant (NX_P9_UMAC_VAS_MMIO_ADDR) bits. IOW, _don't_:
s/:/just write the bit field like:/
> +	 *
> +	 *       cfg = SETFIELD(NX_P9_UMAC_VAS_MMIO_ADDR, 0ULL, cfg);
> +	 */
> +	rc = xscom_write (gcid, xcfg, cfg);
> +
> +	if (rc)
> +		prerror("NX%d: ERROR: UMAC VAS MMIO BAR, %d\n", gcid, rc);
> +	else
> +		prlog(PR_DEBUG, "NX%d: UMAC VAS MMIO BAR, 0x%016lx, "
> +				"xcfg 0x%llx\n",
> +			gcid, (unsigned long)cfg, xcfg);
> +	
> +	return rc;
> +}
> +
> +static int nx_cfg_umac_status_ctrl(u32 gcid, u64 xcfg)
> +{
> +	u64 uctrl;
> +	int rc;
> +#define CRB_ENABLE	1
> +
> +	rc = xscom_read(gcid, xcfg, &uctrl);
> +	if (rc)
> +		return rc;
> +	
> +	uctrl = SETFIELD(NX_P9_UMAC_STATUS_CTRL_CRB_ENABLE, uctrl, CRB_ENABLE);
> +	rc = xscom_write(gcid, xcfg, uctrl);
> +	if (rc) 
> +		prerror("NX%d: ERROR: Setting UMAC Status Control failure %d\n",
> +			gcid, rc);
> +	else 
> +		prlog(PR_DEBUG, "NX%d: Setting UMAC FIFO bar 0x%016lx\n",
> +			gcid, (unsigned long)uctrl);
> +
> +	return rc;
> +}
> +
> +int nx_set_rx_fifo(struct dt_node *node, u32 gcid, u64 umac_bar,

s/nx_set_rx_fifo/nx_cfg_rx_fifo/ for consistency?

> +			u64 umac_notify, u64 umac_ctrl,
> +			u32 ct_type, u32 priority)

s/ct_type/ct/?

> +{
> +	u64 cfg;
> +	int rc;
> +	uint64_t fifo;
> +#define MATCH_ENABLE    1
> +#define MAX_QUEUED      256
> +#define HPRI_MAX_READ   256
> +
> +	fifo = (uint64_t) local_alloc(gcid, RX_FIFO_SIZE, RX_FIFO_SIZE);
> +	assert(fifo);
> +
> +	rc = xscom_read(gcid, umac_bar, &cfg);
> +	if (rc)
> +		return rc;
> +
> +	cfg = SETFIELD(NX_P9_RX_FIFO_BAR_ADDR, cfg, fifo);
> +	cfg = SETFIELD(NX_P9_RX_FIFO_BAR_SIZE, cfg, RX_FIFO_MAX_CRB);

According to the spec, I think we need to replace RX_FIFO_MAX_CRB with 0x5.
Basically, the

	log(RX_FIFO_MAX_CRB/1024)

> +
> +	rc = xscom_write(gcid, umac_bar, cfg);
> +	if (rc) {
> +		prerror("NX%d: ERROR: Setting UMAC FIFO bar failure %d\n",
> +			gcid, rc);
> +		return rc;
> +	} else 
> +		prlog(PR_DEBUG, "NX%d: Setting UMAC FIFO bar 0x%016lx\n",
> +			gcid, (unsigned long)cfg);
> +
> +	rc = xscom_read(gcid, umac_notify, &cfg);
> +	if (rc) 
> +		return rc;
> +
> +	prerror(" Skiboot1 RX fifo address 0x%Lx lpid %d pid %d tid %d\n",
> +			fifo, gcid + 1, ct_type, priority);
> +
> +	cfg = SETFIELD(NX_P9_RX_FIFO_NOTIFY_MATCH_LPID, cfg, gcid + 1);
> +	cfg = SETFIELD(NX_P9_RX_FIFO_NOTIFY_MATCH_PID, cfg, ct_type);
> +	cfg = SETFIELD(NX_P9_RX_FIFO_NOTIFY_MATCH_TID, cfg, priority);

We are using gcid, ct_type and priority as LPID/PID/TID in multiple
places. Maybe good to add a comment or use simple wrappers like

	GCID2LPID(gcid), CT2PID(ct), PRI2TID(priority)


> +	cfg = SETFIELD(NX_P9_RX_FIFO_NOTIFY_MATCH_MATCH_ENABLE, cfg,
> +			MATCH_ENABLE);
> +
> +	rc = xscom_write(gcid, umac_notify, cfg);
> +	if (rc) {
> +		prerror("NX%d: ERROR: Setting UMAC notify match failure %d\n",
> +			gcid, rc);
> +		return rc;
> +	} else 
> +		prlog(PR_DEBUG, "NX%d: Setting UMAC notify match 0x%016lx\n",
> +				gcid, (unsigned long)cfg);
> +	
> +	rc = xscom_read(gcid, umac_ctrl, &cfg);
> +	if (rc)
> +		return rc;
> +
> +	cfg = SETFIELD(NX_P9_RX_FIFO_CTRL_QUEUED, cfg, MAX_QUEUED);
> +	cfg = SETFIELD(NX_P9_RX_FIFO_CTRL_HPRI_MAX_READ, cfg, HPRI_MAX_READ);
> +
> +	rc = xscom_write(gcid, umac_ctrl, cfg);
> +	if (rc) {
> +		prerror("NX%d: ERROR: Setting UMAC control failure %d\n",
> +				gcid, rc);
> +		return rc;
> +	} else
> +		prlog(PR_DEBUG, "NX%d: Setting UMAC control 0x%016lx\n",
> +				gcid, (unsigned long)cfg);
> +	
> +	dt_add_property_u64(node, "rx-fifo-address", fifo);
> +	dt_add_property_cells(node, "lpid", gcid + 1);
> +	dt_add_property_cells(node, "pid", ct_type);
> +	dt_add_property_cells(node, "tid", priority);
> +
> +	return 0;
> +}
> 
>  void nx_create_compress_node(struct dt_node *node)
>  {
>  	u32 gcid, pb_base;
> +	int rc;
> 
>  	gcid = dt_get_chip_id(node);
>  	pb_base = dt_get_address(node, 0, NULL);
> 
>  	prlog(PR_INFO, "NX%d: 842 at 0x%x\n", gcid, pb_base);
> 
> -	nx_enable_842(node, gcid, pb_base);
> +	if (dt_node_is_compatible(node, "ibm,power9-nx")) {
> +		u64 cfg_mmio, cfg_txwc, cfg_uctrl;
> +
> +		printf("Found ibm,power9-nx\n");
> +		cfg_mmio = pb_base + NX_P9_UMAC_VAS_MMIO_BAR;
> +		cfg_txwc = pb_base + NX_P9_UMAC_TX_WINDOW_CONTEXT_BAR;
> +		cfg_uctrl = pb_base + NX_P9_UMAC_STATUS_CTRL;
> +
> +		rc = nx_cfg_umac_vas_mmio(gcid, cfg_mmio);
> +		if (rc)
> +			return;
> +
> +		rc = nx_cfg_umac_tx_wc(gcid, cfg_txwc);
> +		if (rc)
> +			return;
> +		
> +		rc = nx_cfg_umac_status_ctrl(gcid, cfg_uctrl);
> +		if (rc)
> +			return;
> +
> +		p9_nx_enable_842(node, gcid, pb_base);
> +	} else 
> +		nx_enable_842(node, gcid, pb_base);
>  }
> diff --git a/include/nx.h b/include/nx.h
> index 0a7b1b0..18fa91f 100644
> --- a/include/nx.h
> +++ b/include/nx.h
> @@ -381,7 +381,11 @@ extern void nx_create_crypto_node(struct dt_node *);
>  extern void nx_create_compress_node(struct dt_node *);
> 
>  extern void nx_enable_842(struct dt_node *, u32 gcid, u32 pb_base);
> +extern void p9_nx_enable_842(struct dt_node *, u32 gcid, u32 pb_base);
> 
> +extern int nx_set_rx_fifo(struct dt_node *node, u32 gcid, u64 umac_bar,
> +			u64 umac_notify, u64 umac_ctrl, u32 ct_type,
> +			u32 priority);
>  extern void nx_init(void);
> 
>  #endif /* __NX_H */
> -- 
> 1.7.1
> 
> 



More information about the Skiboot mailing list