[v1,01/24] drivers: crypto: meson: don't hardcode IRQ count

Message ID 20240110201216.18016-2-avromanov@salutedevices.com
State New
Headers
Series Support more Amlogic SoC families in crypto driver |

Commit Message

Alexey Romanov Jan. 10, 2024, 8:11 p.m. UTC
  IRQ count is no longer hardcoded, and make it part of
struct meson_flow. We need this for extend driver support for
other Amlogic SoC's.

Signed-off-by: Alexey Romanov <avromanov@salutedevices.com>
Signed-off-by: Jan Dakinevich <yvdakinevich@salutedevices.com>
---
 drivers/crypto/amlogic/amlogic-gxl-cipher.c |  2 +-
 drivers/crypto/amlogic/amlogic-gxl-core.c   | 47 ++++++++++++---------
 drivers/crypto/amlogic/amlogic-gxl.h        |  8 ++--
 3 files changed, 31 insertions(+), 26 deletions(-)
  

Comments

Neil Armstrong Jan. 11, 2024, 8:21 a.m. UTC | #1
On 10/01/2024 21:11, Alexey Romanov wrote:
> IRQ count is no longer hardcoded, and make it part of
> struct meson_flow. We need this for extend driver support for
> other Amlogic SoC's.

In this case you must make the interrupts maxItems lower for the new platforms in the bindings.

Neil

> 
> Signed-off-by: Alexey Romanov <avromanov@salutedevices.com>
> Signed-off-by: Jan Dakinevich <yvdakinevich@salutedevices.com>
> ---
>   drivers/crypto/amlogic/amlogic-gxl-cipher.c |  2 +-
>   drivers/crypto/amlogic/amlogic-gxl-core.c   | 47 ++++++++++++---------
>   drivers/crypto/amlogic/amlogic-gxl.h        |  8 ++--
>   3 files changed, 31 insertions(+), 26 deletions(-)
> 
> diff --git a/drivers/crypto/amlogic/amlogic-gxl-cipher.c b/drivers/crypto/amlogic/amlogic-gxl-cipher.c
> index af017a087ebf..e01ed6347c3d 100644
> --- a/drivers/crypto/amlogic/amlogic-gxl-cipher.c
> +++ b/drivers/crypto/amlogic/amlogic-gxl-cipher.c
> @@ -19,7 +19,7 @@
>   
>   static int get_engine_number(struct meson_dev *mc)
>   {
> -	return atomic_inc_return(&mc->flow) % MAXFLOW;
> +	return atomic_inc_return(&mc->flow) % mc->flow_cnt;
>   }
>   
>   static bool meson_cipher_need_fallback(struct skcipher_request *areq)
> diff --git a/drivers/crypto/amlogic/amlogic-gxl-core.c b/drivers/crypto/amlogic/amlogic-gxl-core.c
> index 937187027ad5..a5df061f9890 100644
> --- a/drivers/crypto/amlogic/amlogic-gxl-core.c
> +++ b/drivers/crypto/amlogic/amlogic-gxl-core.c
> @@ -26,8 +26,8 @@ static irqreturn_t meson_irq_handler(int irq, void *data)
>   	int flow;
>   	u32 p;
>   
> -	for (flow = 0; flow < MAXFLOW; flow++) {
> -		if (mc->irqs[flow] == irq) {
> +	for (flow = 0; flow < mc->flow_cnt; flow++) {
> +		if (mc->chanlist[flow].irq == irq) {
>   			p = readl(mc->base + ((0x04 + flow) << 2));
>   			if (p) {
>   				writel_relaxed(0xF, mc->base + ((0x4 + flow) << 2));
> @@ -103,7 +103,7 @@ static int meson_debugfs_show(struct seq_file *seq, void *v)
>   	struct meson_dev *mc = seq->private;
>   	int i;
>   
> -	for (i = 0; i < MAXFLOW; i++)
> +	for (i = 0; i < mc->flow_cnt; i++)
>   		seq_printf(seq, "Channel %d: nreq %lu\n", i, mc->chanlist[i].stat_req);
>   
>   	for (i = 0; i < ARRAY_SIZE(mc_algs); i++) {
> @@ -138,14 +138,32 @@ static void meson_free_chanlist(struct meson_dev *mc, int i)
>    */
>   static int meson_allocate_chanlist(struct meson_dev *mc)
>   {
> +	struct platform_device *pdev = to_platform_device(mc->dev);
>   	int i, err;
>   
> -	mc->chanlist = devm_kcalloc(mc->dev, MAXFLOW,
> +	mc->flow_cnt = platform_irq_count(pdev);
> +	if (mc->flow_cnt <= 0) {
> +		dev_err(mc->dev, "No IRQs defined\n");
> +		return -ENODEV;
> +	}
> +
> +	mc->chanlist = devm_kcalloc(mc->dev, mc->flow_cnt,
>   				    sizeof(struct meson_flow), GFP_KERNEL);
>   	if (!mc->chanlist)
>   		return -ENOMEM;
>   
> -	for (i = 0; i < MAXFLOW; i++) {
> +	for (i = 0; i < mc->flow_cnt; i++) {
> +		mc->chanlist[i].irq = platform_get_irq(pdev, i);
> +		if (mc->chanlist[i].irq < 0)
> +			return mc->chanlist[i].irq;
> +
> +		err = devm_request_irq(mc->dev, mc->chanlist[i].irq,
> +				       meson_irq_handler, 0, "aml-crypto", mc);
> +		if (err < 0) {
> +			dev_err(mc->dev, "Cannot request IRQ for flow %d\n", i);
> +			return err;
> +		}
> +
>   		init_completion(&mc->chanlist[i].complete);
>   
>   		mc->chanlist[i].engine = crypto_engine_alloc_init(mc->dev, true);
> @@ -215,7 +233,7 @@ static void meson_unregister_algs(struct meson_dev *mc)
>   static int meson_crypto_probe(struct platform_device *pdev)
>   {
>   	struct meson_dev *mc;
> -	int err, i;
> +	int err;
>   
>   	mc = devm_kzalloc(&pdev->dev, sizeof(*mc), GFP_KERNEL);
>   	if (!mc)
> @@ -237,19 +255,6 @@ static int meson_crypto_probe(struct platform_device *pdev)
>   		return err;
>   	}
>   
> -	for (i = 0; i < MAXFLOW; i++) {
> -		mc->irqs[i] = platform_get_irq(pdev, i);
> -		if (mc->irqs[i] < 0)
> -			return mc->irqs[i];
> -
> -		err = devm_request_irq(&pdev->dev, mc->irqs[i], meson_irq_handler, 0,
> -				       "gxl-crypto", mc);
> -		if (err < 0) {
> -			dev_err(mc->dev, "Cannot request IRQ for flow %d\n", i);
> -			return err;
> -		}
> -	}
> -
>   	err = clk_prepare_enable(mc->busclk);
>   	if (err != 0) {
>   		dev_err(&pdev->dev, "Cannot prepare_enable busclk\n");
> @@ -273,7 +278,7 @@ static int meson_crypto_probe(struct platform_device *pdev)
>   error_alg:
>   	meson_unregister_algs(mc);
>   error_flow:
> -	meson_free_chanlist(mc, MAXFLOW - 1);
> +	meson_free_chanlist(mc, mc->flow_cnt - 1);
>   	clk_disable_unprepare(mc->busclk);
>   	return err;
>   }
> @@ -288,7 +293,7 @@ static int meson_crypto_remove(struct platform_device *pdev)
>   
>   	meson_unregister_algs(mc);
>   
> -	meson_free_chanlist(mc, MAXFLOW - 1);
> +	meson_free_chanlist(mc, mc->flow_cnt - 1);
>   
>   	clk_disable_unprepare(mc->busclk);
>   	return 0;
> diff --git a/drivers/crypto/amlogic/amlogic-gxl.h b/drivers/crypto/amlogic/amlogic-gxl.h
> index 8c0746a1d6d4..e5cc6e028fa8 100644
> --- a/drivers/crypto/amlogic/amlogic-gxl.h
> +++ b/drivers/crypto/amlogic/amlogic-gxl.h
> @@ -22,8 +22,6 @@
>   #define MESON_OPMODE_ECB 0
>   #define MESON_OPMODE_CBC 1
>   
> -#define MAXFLOW 2
> -
>   #define MAXDESC 64
>   
>   #define DESC_LAST BIT(18)
> @@ -62,6 +60,7 @@ struct meson_desc {
>    * @keylen:	keylen for this flow operation
>    * @complete:	completion for the current task on this flow
>    * @status:	set to 1 by interrupt if task is done
> + * @irq:	IRQ number for amlogic-crypto
>    * @t_phy:	Physical address of task
>    * @tl:		pointer to the current ce_task for this flow
>    * @stat_req:	number of request done by this flow
> @@ -70,6 +69,7 @@ struct meson_flow {
>   	struct crypto_engine *engine;
>   	struct completion complete;
>   	int status;
> +	int irq;
>   	unsigned int keylen;
>   	dma_addr_t t_phy;
>   	struct meson_desc *tl;
> @@ -85,7 +85,7 @@ struct meson_flow {
>    * @dev:	the platform device
>    * @chanlist:	array of all flow
>    * @flow:	flow to use in next request
> - * @irqs:	IRQ numbers for amlogic-crypto
> + * @flow_cnt:	flow count for amlogic-crypto
>    * @dbgfs_dir:	Debugfs dentry for statistic directory
>    * @dbgfs_stats: Debugfs dentry for statistic counters
>    */
> @@ -95,7 +95,7 @@ struct meson_dev {
>   	struct device *dev;
>   	struct meson_flow *chanlist;
>   	atomic_t flow;
> -	int irqs[MAXFLOW];
> +	int flow_cnt;
>   #ifdef CONFIG_CRYPTO_DEV_AMLOGIC_GXL_DEBUG
>   	struct dentry *dbgfs_dir;
>   #endif
  

Patch

diff --git a/drivers/crypto/amlogic/amlogic-gxl-cipher.c b/drivers/crypto/amlogic/amlogic-gxl-cipher.c
index af017a087ebf..e01ed6347c3d 100644
--- a/drivers/crypto/amlogic/amlogic-gxl-cipher.c
+++ b/drivers/crypto/amlogic/amlogic-gxl-cipher.c
@@ -19,7 +19,7 @@ 
 
 static int get_engine_number(struct meson_dev *mc)
 {
-	return atomic_inc_return(&mc->flow) % MAXFLOW;
+	return atomic_inc_return(&mc->flow) % mc->flow_cnt;
 }
 
 static bool meson_cipher_need_fallback(struct skcipher_request *areq)
diff --git a/drivers/crypto/amlogic/amlogic-gxl-core.c b/drivers/crypto/amlogic/amlogic-gxl-core.c
index 937187027ad5..a5df061f9890 100644
--- a/drivers/crypto/amlogic/amlogic-gxl-core.c
+++ b/drivers/crypto/amlogic/amlogic-gxl-core.c
@@ -26,8 +26,8 @@  static irqreturn_t meson_irq_handler(int irq, void *data)
 	int flow;
 	u32 p;
 
-	for (flow = 0; flow < MAXFLOW; flow++) {
-		if (mc->irqs[flow] == irq) {
+	for (flow = 0; flow < mc->flow_cnt; flow++) {
+		if (mc->chanlist[flow].irq == irq) {
 			p = readl(mc->base + ((0x04 + flow) << 2));
 			if (p) {
 				writel_relaxed(0xF, mc->base + ((0x4 + flow) << 2));
@@ -103,7 +103,7 @@  static int meson_debugfs_show(struct seq_file *seq, void *v)
 	struct meson_dev *mc = seq->private;
 	int i;
 
-	for (i = 0; i < MAXFLOW; i++)
+	for (i = 0; i < mc->flow_cnt; i++)
 		seq_printf(seq, "Channel %d: nreq %lu\n", i, mc->chanlist[i].stat_req);
 
 	for (i = 0; i < ARRAY_SIZE(mc_algs); i++) {
@@ -138,14 +138,32 @@  static void meson_free_chanlist(struct meson_dev *mc, int i)
  */
 static int meson_allocate_chanlist(struct meson_dev *mc)
 {
+	struct platform_device *pdev = to_platform_device(mc->dev);
 	int i, err;
 
-	mc->chanlist = devm_kcalloc(mc->dev, MAXFLOW,
+	mc->flow_cnt = platform_irq_count(pdev);
+	if (mc->flow_cnt <= 0) {
+		dev_err(mc->dev, "No IRQs defined\n");
+		return -ENODEV;
+	}
+
+	mc->chanlist = devm_kcalloc(mc->dev, mc->flow_cnt,
 				    sizeof(struct meson_flow), GFP_KERNEL);
 	if (!mc->chanlist)
 		return -ENOMEM;
 
-	for (i = 0; i < MAXFLOW; i++) {
+	for (i = 0; i < mc->flow_cnt; i++) {
+		mc->chanlist[i].irq = platform_get_irq(pdev, i);
+		if (mc->chanlist[i].irq < 0)
+			return mc->chanlist[i].irq;
+
+		err = devm_request_irq(mc->dev, mc->chanlist[i].irq,
+				       meson_irq_handler, 0, "aml-crypto", mc);
+		if (err < 0) {
+			dev_err(mc->dev, "Cannot request IRQ for flow %d\n", i);
+			return err;
+		}
+
 		init_completion(&mc->chanlist[i].complete);
 
 		mc->chanlist[i].engine = crypto_engine_alloc_init(mc->dev, true);
@@ -215,7 +233,7 @@  static void meson_unregister_algs(struct meson_dev *mc)
 static int meson_crypto_probe(struct platform_device *pdev)
 {
 	struct meson_dev *mc;
-	int err, i;
+	int err;
 
 	mc = devm_kzalloc(&pdev->dev, sizeof(*mc), GFP_KERNEL);
 	if (!mc)
@@ -237,19 +255,6 @@  static int meson_crypto_probe(struct platform_device *pdev)
 		return err;
 	}
 
-	for (i = 0; i < MAXFLOW; i++) {
-		mc->irqs[i] = platform_get_irq(pdev, i);
-		if (mc->irqs[i] < 0)
-			return mc->irqs[i];
-
-		err = devm_request_irq(&pdev->dev, mc->irqs[i], meson_irq_handler, 0,
-				       "gxl-crypto", mc);
-		if (err < 0) {
-			dev_err(mc->dev, "Cannot request IRQ for flow %d\n", i);
-			return err;
-		}
-	}
-
 	err = clk_prepare_enable(mc->busclk);
 	if (err != 0) {
 		dev_err(&pdev->dev, "Cannot prepare_enable busclk\n");
@@ -273,7 +278,7 @@  static int meson_crypto_probe(struct platform_device *pdev)
 error_alg:
 	meson_unregister_algs(mc);
 error_flow:
-	meson_free_chanlist(mc, MAXFLOW - 1);
+	meson_free_chanlist(mc, mc->flow_cnt - 1);
 	clk_disable_unprepare(mc->busclk);
 	return err;
 }
@@ -288,7 +293,7 @@  static int meson_crypto_remove(struct platform_device *pdev)
 
 	meson_unregister_algs(mc);
 
-	meson_free_chanlist(mc, MAXFLOW - 1);
+	meson_free_chanlist(mc, mc->flow_cnt - 1);
 
 	clk_disable_unprepare(mc->busclk);
 	return 0;
diff --git a/drivers/crypto/amlogic/amlogic-gxl.h b/drivers/crypto/amlogic/amlogic-gxl.h
index 8c0746a1d6d4..e5cc6e028fa8 100644
--- a/drivers/crypto/amlogic/amlogic-gxl.h
+++ b/drivers/crypto/amlogic/amlogic-gxl.h
@@ -22,8 +22,6 @@ 
 #define MESON_OPMODE_ECB 0
 #define MESON_OPMODE_CBC 1
 
-#define MAXFLOW 2
-
 #define MAXDESC 64
 
 #define DESC_LAST BIT(18)
@@ -62,6 +60,7 @@  struct meson_desc {
  * @keylen:	keylen for this flow operation
  * @complete:	completion for the current task on this flow
  * @status:	set to 1 by interrupt if task is done
+ * @irq:	IRQ number for amlogic-crypto
  * @t_phy:	Physical address of task
  * @tl:		pointer to the current ce_task for this flow
  * @stat_req:	number of request done by this flow
@@ -70,6 +69,7 @@  struct meson_flow {
 	struct crypto_engine *engine;
 	struct completion complete;
 	int status;
+	int irq;
 	unsigned int keylen;
 	dma_addr_t t_phy;
 	struct meson_desc *tl;
@@ -85,7 +85,7 @@  struct meson_flow {
  * @dev:	the platform device
  * @chanlist:	array of all flow
  * @flow:	flow to use in next request
- * @irqs:	IRQ numbers for amlogic-crypto
+ * @flow_cnt:	flow count for amlogic-crypto
  * @dbgfs_dir:	Debugfs dentry for statistic directory
  * @dbgfs_stats: Debugfs dentry for statistic counters
  */
@@ -95,7 +95,7 @@  struct meson_dev {
 	struct device *dev;
 	struct meson_flow *chanlist;
 	atomic_t flow;
-	int irqs[MAXFLOW];
+	int flow_cnt;
 #ifdef CONFIG_CRYPTO_DEV_AMLOGIC_GXL_DEBUG
 	struct dentry *dbgfs_dir;
 #endif