[PATCH v3 7/8] irqchip/gic-v3-its: Handle its nodes as kernel devices
Manage its nodes as kernel devices. We can then use the kernel's device resource management for memory allocation. Freeing memory becomes much easier now. This also allows us to use CMA for the allocation of large its tables. Signed-off-by: Robert Richter--- drivers/irqchip/irq-gic-v3-its.c | 118 --- 1 file changed, 60 insertions(+), 58 deletions(-) diff --git a/drivers/irqchip/irq-gic-v3-its.c b/drivers/irqchip/irq-gic-v3-its.c index 488f811d5978..b7d853dd6b75 100644 --- a/drivers/irqchip/irq-gic-v3-its.c +++ b/drivers/irqchip/irq-gic-v3-its.c @@ -20,6 +20,7 @@ #include #include #include +#include #include #include #include @@ -75,6 +76,7 @@ struct its_baser { * list of devices writing to it. */ struct its_node { + struct device dev; struct fwnode_handle*fwnode; raw_spinlock_t lock; struct list_headentry; @@ -400,7 +402,7 @@ static struct its_cmd_block *its_allocate_entry(struct its_node *its) while (its_queue_full(its)) { count--; if (!count) { - pr_err_ratelimited("ITS queue not draining\n"); + dev_err_ratelimited(>dev, "ITS queue not draining\n"); return NULL; } cpu_relax(); @@ -460,7 +462,7 @@ static void its_wait_for_range_completion(struct its_node *its, count--; if (!count) { - pr_err_ratelimited("ITS queue timeout\n"); + dev_err_ratelimited(>dev, "ITS queue timeout\n"); return; } cpu_relax(); @@ -480,7 +482,7 @@ static void its_send_single_command(struct its_node *its, cmd = its_allocate_entry(its); if (!cmd) { /* We're soo screewed... */ - pr_err_ratelimited("ITS can't allocate, dropping command\n"); + dev_err_ratelimited(>dev, "ITS can't allocate, dropping command\n"); raw_spin_unlock_irqrestore(>lock, flags); return; } @@ -490,7 +492,7 @@ static void its_send_single_command(struct its_node *its, if (sync_col) { sync_cmd = its_allocate_entry(its); if (!sync_cmd) { - pr_err_ratelimited("ITS can't SYNC, skipping\n"); + dev_err_ratelimited(>dev, "ITS can't SYNC, skipping\n"); goto post; } its_encode_cmd(sync_cmd, GITS_CMD_SYNC); @@ -869,14 +871,15 @@ static int its_setup_baser(struct its_node *its, struct its_baser *baser, retry_alloc_baser: alloc_pages = (PAGE_ORDER_TO_SIZE(order) / psz); if (alloc_pages > GITS_BASER_PAGES_MAX) { - pr_warn("ITS@%pa: %s too large, reduce ITS pages %u->%u\n", - >phys_base, its_base_type_string[type], - alloc_pages, GITS_BASER_PAGES_MAX); + dev_warn(>dev, "%s too large, reduce ITS pages %u->%u\n", + its_base_type_string[type], alloc_pages, + GITS_BASER_PAGES_MAX); alloc_pages = GITS_BASER_PAGES_MAX; order = get_order(GITS_BASER_PAGES_MAX * psz); } - base = (void *)__get_free_pages(GFP_KERNEL | __GFP_ZERO, order); + base = (void *)devm_get_free_pages(>dev, GFP_KERNEL | __GFP_ZERO, + order); if (!base) return -ENOMEM; @@ -928,7 +931,7 @@ static int its_setup_baser(struct its_node *its, struct its_baser *baser, * size and retry. If we reach 4K, then * something is horribly wrong... */ - free_pages((unsigned long)base, order); + devm_free_pages(>dev, (unsigned long)base); baser->base = NULL; switch (psz) { @@ -942,10 +945,9 @@ static int its_setup_baser(struct its_node *its, struct its_baser *baser, } if (val != tmp) { - pr_err("ITS@%pa: %s doesn't stick: %llx %llx\n", - >phys_base, its_base_type_string[type], - val, tmp); - free_pages((unsigned long)base, order); + dev_err(>dev, "%s doesn't stick: %llx %llx\n", + its_base_type_string[type], val, tmp); + devm_free_pages(>dev, (unsigned long)base); return -ENXIO; } @@ -954,8 +956,8 @@ static int its_setup_baser(struct its_node *its, struct its_baser *baser, baser->psz = psz; tmp = indirect ? GITS_LVL1_ENTRY_SIZE : esz; - pr_info("ITS@%pa: allocated %d %s @%lx (%s, esz %d, psz %dK, shr %d)\n", - >phys_base, (int)(PAGE_ORDER_TO_SIZE(order) / (int)tmp), + dev_info(>dev, "allocated %d %s @%lx (%s, esz %d,
[PATCH v3 7/8] irqchip/gic-v3-its: Handle its nodes as kernel devices
Manage its nodes as kernel devices. We can then use the kernel's device resource management for memory allocation. Freeing memory becomes much easier now. This also allows us to use CMA for the allocation of large its tables. Signed-off-by: Robert Richter --- drivers/irqchip/irq-gic-v3-its.c | 118 --- 1 file changed, 60 insertions(+), 58 deletions(-) diff --git a/drivers/irqchip/irq-gic-v3-its.c b/drivers/irqchip/irq-gic-v3-its.c index 488f811d5978..b7d853dd6b75 100644 --- a/drivers/irqchip/irq-gic-v3-its.c +++ b/drivers/irqchip/irq-gic-v3-its.c @@ -20,6 +20,7 @@ #include #include #include +#include #include #include #include @@ -75,6 +76,7 @@ struct its_baser { * list of devices writing to it. */ struct its_node { + struct device dev; struct fwnode_handle*fwnode; raw_spinlock_t lock; struct list_headentry; @@ -400,7 +402,7 @@ static struct its_cmd_block *its_allocate_entry(struct its_node *its) while (its_queue_full(its)) { count--; if (!count) { - pr_err_ratelimited("ITS queue not draining\n"); + dev_err_ratelimited(>dev, "ITS queue not draining\n"); return NULL; } cpu_relax(); @@ -460,7 +462,7 @@ static void its_wait_for_range_completion(struct its_node *its, count--; if (!count) { - pr_err_ratelimited("ITS queue timeout\n"); + dev_err_ratelimited(>dev, "ITS queue timeout\n"); return; } cpu_relax(); @@ -480,7 +482,7 @@ static void its_send_single_command(struct its_node *its, cmd = its_allocate_entry(its); if (!cmd) { /* We're soo screewed... */ - pr_err_ratelimited("ITS can't allocate, dropping command\n"); + dev_err_ratelimited(>dev, "ITS can't allocate, dropping command\n"); raw_spin_unlock_irqrestore(>lock, flags); return; } @@ -490,7 +492,7 @@ static void its_send_single_command(struct its_node *its, if (sync_col) { sync_cmd = its_allocate_entry(its); if (!sync_cmd) { - pr_err_ratelimited("ITS can't SYNC, skipping\n"); + dev_err_ratelimited(>dev, "ITS can't SYNC, skipping\n"); goto post; } its_encode_cmd(sync_cmd, GITS_CMD_SYNC); @@ -869,14 +871,15 @@ static int its_setup_baser(struct its_node *its, struct its_baser *baser, retry_alloc_baser: alloc_pages = (PAGE_ORDER_TO_SIZE(order) / psz); if (alloc_pages > GITS_BASER_PAGES_MAX) { - pr_warn("ITS@%pa: %s too large, reduce ITS pages %u->%u\n", - >phys_base, its_base_type_string[type], - alloc_pages, GITS_BASER_PAGES_MAX); + dev_warn(>dev, "%s too large, reduce ITS pages %u->%u\n", + its_base_type_string[type], alloc_pages, + GITS_BASER_PAGES_MAX); alloc_pages = GITS_BASER_PAGES_MAX; order = get_order(GITS_BASER_PAGES_MAX * psz); } - base = (void *)__get_free_pages(GFP_KERNEL | __GFP_ZERO, order); + base = (void *)devm_get_free_pages(>dev, GFP_KERNEL | __GFP_ZERO, + order); if (!base) return -ENOMEM; @@ -928,7 +931,7 @@ static int its_setup_baser(struct its_node *its, struct its_baser *baser, * size and retry. If we reach 4K, then * something is horribly wrong... */ - free_pages((unsigned long)base, order); + devm_free_pages(>dev, (unsigned long)base); baser->base = NULL; switch (psz) { @@ -942,10 +945,9 @@ static int its_setup_baser(struct its_node *its, struct its_baser *baser, } if (val != tmp) { - pr_err("ITS@%pa: %s doesn't stick: %llx %llx\n", - >phys_base, its_base_type_string[type], - val, tmp); - free_pages((unsigned long)base, order); + dev_err(>dev, "%s doesn't stick: %llx %llx\n", + its_base_type_string[type], val, tmp); + devm_free_pages(>dev, (unsigned long)base); return -ENXIO; } @@ -954,8 +956,8 @@ static int its_setup_baser(struct its_node *its, struct its_baser *baser, baser->psz = psz; tmp = indirect ? GITS_LVL1_ENTRY_SIZE : esz; - pr_info("ITS@%pa: allocated %d %s @%lx (%s, esz %d, psz %dK, shr %d)\n", - >phys_base, (int)(PAGE_ORDER_TO_SIZE(order) / (int)tmp), + dev_info(>dev, "allocated %d %s @%lx (%s, esz %d, psz %dK, shr %d)\n", +