static void __init sun5i_timer_init(struct device_node *node) { struct reset_control *rstc; void __iomem *timer_base; struct clk *clk; int irq; timer_base = of_io_request_and_map(node, 0, of_node_full_name(node)); if (!timer_base) panic("Can't map registers"); irq = irq_of_parse_and_map(node, 0); if (irq <= 0) panic("Can't parse IRQ"); clk = of_clk_get(node, 0); if (IS_ERR(clk)) panic("Can't get timer clock"); rstc = of_reset_control_get(node, NULL); if (!IS_ERR(rstc)) reset_control_deassert(rstc); sun5i_setup_clocksource(node, timer_base, clk, irq); sun5i_setup_clockevent(node, timer_base, clk, irq); }
static int __init sun5i_timer_init(struct device_node *node) { struct reset_control *rstc; void __iomem *timer_base; struct clk *clk; int irq, ret; timer_base = of_io_request_and_map(node, 0, of_node_full_name(node)); if (IS_ERR(timer_base)) { pr_err("Can't map registers\n"); return PTR_ERR(timer_base); } irq = irq_of_parse_and_map(node, 0); if (irq <= 0) { pr_err("Can't parse IRQ\n"); return -EINVAL; } clk = of_clk_get(node, 0); if (IS_ERR(clk)) { pr_err("Can't get timer clock\n"); return PTR_ERR(clk); } rstc = of_reset_control_get(node, NULL); if (!IS_ERR(rstc)) reset_control_deassert(rstc); ret = sun5i_setup_clocksource(node, timer_base, clk, irq); if (ret) return ret; return sun5i_setup_clockevent(node, timer_base, clk, irq); }
static void __init sun5i_ccu_init(struct device_node *node, const struct sunxi_ccu_desc *desc) { void __iomem *reg; u32 val; reg = of_io_request_and_map(node, 0, of_node_full_name(node)); if (IS_ERR(reg)) { pr_err("%s: Could not map the clock registers\n", of_node_full_name(node)); return; } /* Force the PLL-Audio-1x divider to 4 */ val = readl(reg + SUN5I_PLL_AUDIO_REG); val &= ~GENMASK(19, 16); writel(val | (3 << 16), reg + SUN5I_PLL_AUDIO_REG); /* * Use the peripheral PLL as the AHB parent, instead of CPU / * AXI which have rate changes due to cpufreq. * * This is especially a big deal for the HS timer whose parent * clock is AHB. */ val = readl(reg + SUN5I_AHB_REG); val &= ~GENMASK(7, 6); writel(val | (2 << 6), reg + SUN5I_AHB_REG); sunxi_ccu_probe(node, reg, desc); }
static void sun8i_a23_apb0_setup(struct device_node *node) { void __iomem *reg; struct resource res; struct clk *clk; reg = of_io_request_and_map(node, 0, of_node_full_name(node)); if (IS_ERR(reg)) { /* * This happens with clk nodes instantiated through mfd, * as those do not have their resources assigned in the * device tree. Do not print an error in this case. */ if (PTR_ERR(reg) != -EINVAL) pr_err("Could not get registers for a23-apb0-clk\n"); return; } clk = sun8i_a23_apb0_register(node, reg); if (IS_ERR(clk)) goto err_unmap; return; err_unmap: iounmap(reg); of_address_to_resource(node, 0, &res); release_mem_region(res.start, resource_size(&res)); }
static void __init sun8i_a33_ccu_setup(struct device_node *node) { void __iomem *reg; u32 val; reg = of_io_request_and_map(node, 0, of_node_full_name(node)); if (IS_ERR(reg)) { pr_err("%s: Could not map the clock registers\n", of_node_full_name(node)); return; } /* Force the PLL-Audio-1x divider to 4 */ val = readl(reg + SUN8I_A33_PLL_AUDIO_REG); val &= ~GENMASK(19, 16); writel(val | (3 << 16), reg + SUN8I_A33_PLL_AUDIO_REG); /* Force PLL-MIPI to MIPI mode */ val = readl(reg + SUN8I_A33_PLL_MIPI_REG); val &= ~BIT(16); writel(val, reg + SUN8I_A33_PLL_MIPI_REG); sunxi_ccu_probe(node, reg, &sun8i_a33_ccu_desc); ccu_mux_notifier_register(pll_cpux_clk.common.hw.clk, &sun8i_a33_cpu_nb); }
static int __init integrator_ap_timer_init_of(struct device_node *node) { const char *path; void __iomem *base; int err; int irq; struct clk *clk; unsigned long rate; struct device_node *pri_node; struct device_node *sec_node; base = of_io_request_and_map(node, 0, "integrator-timer"); if (IS_ERR(base)) return PTR_ERR(base); clk = of_clk_get(node, 0); if (IS_ERR(clk)) { pr_err("No clock for %pOFn\n", node); return PTR_ERR(clk); } clk_prepare_enable(clk); rate = clk_get_rate(clk); writel(0, base + TIMER_CTRL); err = of_property_read_string(of_aliases, "arm,timer-primary", &path); if (err) { pr_warn("Failed to read property\n"); return err; } pri_node = of_find_node_by_path(path); err = of_property_read_string(of_aliases, "arm,timer-secondary", &path); if (err) { pr_warn("Failed to read property\n"); return err; } sec_node = of_find_node_by_path(path); if (node == pri_node) /* The primary timer lacks IRQ, use as clocksource */ return integrator_clocksource_init(rate, base); if (node == sec_node) { /* The secondary timer will drive the clock event */ irq = irq_of_parse_and_map(node, 0); return integrator_clockevent_init(rate, base, irq); } pr_info("Timer @%p unused\n", base); clk_disable_unprepare(clk); return 0; }
static void __iomem * __init icoll_init_iobase(struct device_node *np) { void __iomem *icoll_base; icoll_base = of_io_request_and_map(np, 0, np->name); if (IS_ERR(icoll_base)) panic("%s: unable to map resource", np->full_name); return icoll_base; }
static int __init vf610_mscm_ir_of_init(struct device_node *node, struct device_node *parent) { struct irq_domain *domain, *domain_parent; struct regmap *mscm_cp_regmap; int ret, cpuid; domain_parent = irq_find_host(parent); if (!domain_parent) { pr_err("vf610_mscm_ir: interrupt-parent not found\n"); return -EINVAL; } mscm_ir_data = kzalloc(sizeof(*mscm_ir_data), GFP_KERNEL); if (!mscm_ir_data) return -ENOMEM; mscm_ir_data->mscm_ir_base = of_io_request_and_map(node, 0, "mscm-ir"); if (!mscm_ir_data->mscm_ir_base) { pr_err("vf610_mscm_ir: unable to map mscm register\n"); ret = -ENOMEM; goto out_free; } mscm_cp_regmap = syscon_regmap_lookup_by_phandle(node, "fsl,cpucfg"); if (IS_ERR(mscm_cp_regmap)) { ret = PTR_ERR(mscm_cp_regmap); pr_err("vf610_mscm_ir: regmap lookup for cpucfg failed\n"); goto out_unmap; } regmap_read(mscm_cp_regmap, MSCM_CPxNUM, &cpuid); mscm_ir_data->cpu_mask = 0x1 << cpuid; domain = irq_domain_add_hierarchy(domain_parent, 0, MSCM_IRSPRC_NUM, node, &mscm_irq_domain_ops, mscm_ir_data); if (!domain) { ret = -ENOMEM; goto out_unmap; } cpu_pm_register_notifier(&mscm_ir_notifier_block); return 0; out_unmap: iounmap(mscm_ir_data->mscm_ir_base); out_free: kfree(mscm_ir_data); return ret; }
static __init int timer_of_base_init(struct device_node *np, struct of_timer_base *of_base) { of_base->base = of_base->name ? of_io_request_and_map(np, of_base->index, of_base->name) : of_iomap(np, of_base->index); if (IS_ERR(of_base->base)) { pr_err("Failed to iomap (%s)\n", of_base->name); return PTR_ERR(of_base->base); } return 0; }
static int owl_sps_probe(struct platform_device *pdev) { const struct of_device_id *match; const struct owl_sps_info *sps_info; struct owl_sps *sps; int i, ret; if (!pdev->dev.of_node) { dev_err(&pdev->dev, "no device node\n"); return -ENODEV; } match = of_match_device(pdev->dev.driver->of_match_table, &pdev->dev); if (!match || !match->data) { dev_err(&pdev->dev, "unknown compatible or missing data\n"); return -EINVAL; } sps_info = match->data; sps = devm_kzalloc(&pdev->dev, sizeof(*sps) + sps_info->num_domains * sizeof(sps->domains[0]), GFP_KERNEL); if (!sps) return -ENOMEM; sps->base = of_io_request_and_map(pdev->dev.of_node, 0, "owl-sps"); if (IS_ERR(sps->base)) { dev_err(&pdev->dev, "failed to map sps registers\n"); return PTR_ERR(sps->base); } sps->dev = &pdev->dev; sps->info = sps_info; sps->genpd_data.domains = sps->domains; sps->genpd_data.num_domains = sps_info->num_domains; for (i = 0; i < sps_info->num_domains; i++) { ret = owl_sps_init_domain(sps, i); if (ret) return ret; } ret = of_genpd_add_provider_onecell(pdev->dev.of_node, &sps->genpd_data); if (ret) { dev_err(&pdev->dev, "failed to add provider (%d)", ret); return ret; } return 0; }
static void __init sun4i_mod1_clk_setup(struct device_node *node) { struct clk *clk; struct clk_mux *mux; struct clk_gate *gate; const char *parents[4]; const char *clk_name = node->name; void __iomem *reg; int i; reg = of_io_request_and_map(node, 0, of_node_full_name(node)); if (IS_ERR(reg)) return; mux = kzalloc(sizeof(*mux), GFP_KERNEL); if (!mux) goto err_unmap; gate = kzalloc(sizeof(*gate), GFP_KERNEL); if (!gate) goto err_free_mux; of_property_read_string(node, "clock-output-names", &clk_name); i = of_clk_parent_fill(node, parents, SUN4I_MOD1_MAX_PARENTS); gate->reg = reg; gate->bit_idx = SUN4I_MOD1_ENABLE; gate->lock = &mod1_lock; mux->reg = reg; mux->shift = SUN4I_MOD1_MUX; mux->mask = BIT(SUN4I_MOD1_MUX_WIDTH) - 1; mux->lock = &mod1_lock; clk = clk_register_composite(NULL, clk_name, parents, i, &mux->hw, &clk_mux_ops, NULL, NULL, &gate->hw, &clk_gate_ops, CLK_SET_RATE_PARENT); if (IS_ERR(clk)) goto err_free_gate; of_clk_add_provider(node, of_clk_src_simple_get, clk); return; err_free_gate: kfree(gate); err_free_mux: kfree(mux); err_unmap: iounmap(reg); }
static void __init sun9i_a80_pll4_setup(struct device_node *node) { void __iomem *reg; reg = of_io_request_and_map(node, 0, of_node_full_name(node)); if (IS_ERR(reg)) { pr_err("Could not get registers for a80-pll4-clk: %s\n", node->name); return; } sunxi_factors_register(node, &sun9i_a80_pll4_data, &sun9i_a80_pll4_lock, reg); }
static int __init meson6_timer_init(struct device_node *node) { u32 val; int ret, irq; timer_base = of_io_request_and_map(node, 0, "meson6-timer"); if (IS_ERR(timer_base)) { pr_err("Can't map registers\n"); return -ENXIO; } irq = irq_of_parse_and_map(node, 0); if (irq <= 0) { pr_err("Can't parse IRQ\n"); return -EINVAL; } /* Set 1us for timer E */ val = readl(timer_base + TIMER_ISA_MUX); val &= ~TIMER_CSD_INPUT_MASK; val |= TIMER_CSD_UNIT_1US << TIMER_INPUT_BIT(CSD_ID); writel(val, timer_base + TIMER_ISA_MUX); sched_clock_register(meson6_timer_sched_read, 32, USEC_PER_SEC); clocksource_mmio_init(timer_base + TIMER_ISA_VAL(CSD_ID), node->name, 1000 * 1000, 300, 32, clocksource_mmio_readl_up); /* Timer A base 1us */ val &= ~TIMER_CED_INPUT_MASK; val |= TIMER_CED_UNIT_1US << TIMER_INPUT_BIT(CED_ID); writel(val, timer_base + TIMER_ISA_MUX); /* Stop the timer A */ meson6_clkevt_time_stop(CED_ID); ret = setup_irq(irq, &meson6_timer_irq); if (ret) { pr_warn("failed to setup irq %d\n", irq); return ret; } meson6_clockevent.cpumask = cpu_possible_mask; meson6_clockevent.irq = irq; clockevents_config_and_register(&meson6_clockevent, USEC_PER_SEC, 1, 0xfffe); return 0; }
static void __init sun8i_v3s_ccu_setup(struct device_node *node) { void __iomem *reg; u32 val; reg = of_io_request_and_map(node, 0, of_node_full_name(node)); if (IS_ERR(reg)) { pr_err("%pOF: Could not map the clock registers\n", node); return; } /* Force the PLL-Audio-1x divider to 4 */ val = readl(reg + SUN8I_V3S_PLL_AUDIO_REG); val &= ~GENMASK(19, 16); writel(val | (3 << 16), reg + SUN8I_V3S_PLL_AUDIO_REG); sunxi_ccu_probe(node, reg, &sun8i_v3s_ccu_desc); }
static void __init sun9i_a80_gt_setup(struct device_node *node) { void __iomem *reg; struct clk *gt; reg = of_io_request_and_map(node, 0, of_node_full_name(node)); if (IS_ERR(reg)) { pr_err("Could not get registers for a80-gt-clk: %s\n", node->name); return; } gt = sunxi_factors_register(node, &sun9i_a80_gt_data, &sun9i_a80_gt_lock, reg); /* The GT bus clock needs to be always enabled */ __clk_get(gt); clk_prepare_enable(gt); }
static void __init sun8i_r40_ccu_setup(struct device_node *node) { void __iomem *reg; u32 val; reg = of_io_request_and_map(node, 0, of_node_full_name(node)); if (IS_ERR(reg)) { pr_err("%s: Could not map the clock registers\n", of_node_full_name(node)); return; } /* Force the PLL-Audio-1x divider to 4 */ val = readl(reg + SUN8I_R40_PLL_AUDIO_REG); val &= ~GENMASK(19, 16); writel(val | (3 << 16), reg + SUN8I_R40_PLL_AUDIO_REG); /* Force PLL-MIPI to MIPI mode */ val = readl(reg + SUN8I_R40_PLL_MIPI_REG); val &= ~BIT(16); writel(val, reg + SUN8I_R40_PLL_MIPI_REG); /* Force OHCI 12M parent to 12M divided from 48M */ val = readl(reg + SUN8I_R40_USB_CLK_REG); val &= ~GENMASK(25, 20); writel(val, reg + SUN8I_R40_USB_CLK_REG); sunxi_ccu_probe(node, reg, &sun8i_r40_ccu_desc); /* Gate then ungate PLL CPU after any rate changes */ ccu_pll_notifier_register(&sun8i_r40_pll_cpu_nb); /* Reparent CPU during PLL CPU rate changes */ ccu_mux_notifier_register(pll_cpu_clk.common.hw.clk, &sun8i_r40_cpu_nb); }
!(~cntacr & (CNTACR_RWVT | CNTACR_RVCT))) { of_node_put(best_frame); best_frame = frame; arch_timer_mem_use_virtual = true; break; } if (~cntacr & (CNTACR_RWPT | CNTACR_RPCT)) continue; of_node_put(best_frame); best_frame = of_node_get(frame); } ret= -ENXIO; base = arch_counter_base = of_io_request_and_map(best_frame, 0, "arch_mem_timer"); if (IS_ERR(base)) { pr_err("arch_timer: Can't map frame's registers\n"); goto out; } if (arch_timer_mem_use_virtual) irq = irq_of_parse_and_map(best_frame, 1); else irq = irq_of_parse_and_map(best_frame, 0); ret = -EINVAL; if (!irq) { pr_err("arch_timer: Frame missing %s irq", arch_timer_mem_use_virtual ? "virt" : "phys"); goto out;
static void __init sun8i_a23_mbus_setup(struct device_node *node) { int num_parents = of_clk_get_parent_count(node); const char **parents; const char *clk_name = node->name; struct resource res; struct clk_divider *div; struct clk_gate *gate; struct clk_mux *mux; struct clk *clk; void __iomem *reg; int err; parents = kcalloc(num_parents, sizeof(*parents), GFP_KERNEL); if (!parents) return; reg = of_io_request_and_map(node, 0, of_node_full_name(node)); if (IS_ERR(reg)) { pr_err("Could not get registers for sun8i-mbus-clk\n"); goto err_free_parents; } div = kzalloc(sizeof(*div), GFP_KERNEL); if (!div) goto err_unmap; mux = kzalloc(sizeof(*mux), GFP_KERNEL); if (!mux) goto err_free_div; gate = kzalloc(sizeof(*gate), GFP_KERNEL); if (!gate) goto err_free_mux; of_property_read_string(node, "clock-output-names", &clk_name); of_clk_parent_fill(node, parents, num_parents); gate->reg = reg; gate->bit_idx = SUN8I_MBUS_ENABLE; gate->lock = &sun8i_a23_mbus_lock; div->reg = reg; div->shift = SUN8I_MBUS_DIV_SHIFT; div->width = SUN8I_MBUS_DIV_WIDTH; div->lock = &sun8i_a23_mbus_lock; mux->reg = reg; mux->shift = SUN8I_MBUS_MUX_SHIFT; mux->mask = SUN8I_MBUS_MUX_MASK; mux->lock = &sun8i_a23_mbus_lock; clk = clk_register_composite(NULL, clk_name, parents, num_parents, &mux->hw, &clk_mux_ops, &div->hw, &clk_divider_ops, &gate->hw, &clk_gate_ops, 0); if (IS_ERR(clk)) goto err_free_gate; err = of_clk_add_provider(node, of_clk_src_simple_get, clk); if (err) goto err_unregister_clk; kfree(parents); /* parents is deep copied */ /* The MBUS clocks needs to be always enabled */ __clk_get(clk); clk_prepare_enable(clk); return; err_unregister_clk: /* TODO: The composite clock stuff will leak a bit here. */ clk_unregister(clk); err_free_gate: kfree(gate); err_free_mux: kfree(mux); err_free_div: kfree(div); err_unmap: iounmap(reg); of_address_to_resource(node, 0, &res); release_mem_region(res.start, resource_size(&res)); err_free_parents: kfree(parents); }
static void __init sun4i_pll2_setup(struct device_node *node, int post_div_offset) { const char *clk_name = node->name, *parent; struct clk **clks, *base_clk, *prediv_clk; struct clk_onecell_data *clk_data; struct clk_multiplier *mult; struct clk_gate *gate; void __iomem *reg; u32 val; reg = of_io_request_and_map(node, 0, of_node_full_name(node)); if (IS_ERR(reg)) return; clk_data = kzalloc(sizeof(*clk_data), GFP_KERNEL); if (!clk_data) goto err_unmap; clks = kcalloc(SUN4I_PLL2_OUTPUTS, sizeof(struct clk *), GFP_KERNEL); if (!clks) goto err_free_data; parent = of_clk_get_parent_name(node, 0); prediv_clk = clk_register_divider(NULL, "pll2-prediv", parent, 0, reg, SUN4I_PLL2_PRE_DIV_SHIFT, SUN4I_PLL2_PRE_DIV_WIDTH, CLK_DIVIDER_ONE_BASED | CLK_DIVIDER_ALLOW_ZERO, &sun4i_a10_pll2_lock); if (IS_ERR(prediv_clk)) { pr_err("Couldn't register the prediv clock\n"); goto err_free_array; } /* Setup the gate part of the PLL2 */ gate = kzalloc(sizeof(struct clk_gate), GFP_KERNEL); if (!gate) goto err_unregister_prediv; gate->reg = reg; gate->bit_idx = SUN4I_PLL2_ENABLE; gate->lock = &sun4i_a10_pll2_lock; /* Setup the multiplier part of the PLL2 */ mult = kzalloc(sizeof(struct clk_multiplier), GFP_KERNEL); if (!mult) goto err_free_gate; mult->reg = reg; mult->shift = SUN4I_PLL2_N_SHIFT; mult->width = 7; mult->flags = CLK_MULTIPLIER_ZERO_BYPASS | CLK_MULTIPLIER_ROUND_CLOSEST; mult->lock = &sun4i_a10_pll2_lock; parent = __clk_get_name(prediv_clk); base_clk = clk_register_composite(NULL, "pll2-base", &parent, 1, NULL, NULL, &mult->hw, &clk_multiplier_ops, &gate->hw, &clk_gate_ops, CLK_SET_RATE_PARENT); if (IS_ERR(base_clk)) { pr_err("Couldn't register the base multiplier clock\n"); goto err_free_multiplier; } parent = __clk_get_name(base_clk); /* * PLL2-1x * * This is supposed to have a post divider, but we won't need * to use it, we just need to initialise it to 4, and use a * fixed divider. */ val = readl(reg); val &= ~(SUN4I_PLL2_POST_DIV_MASK << SUN4I_PLL2_POST_DIV_SHIFT); val |= (SUN4I_PLL2_POST_DIV_VALUE - post_div_offset) << SUN4I_PLL2_POST_DIV_SHIFT; writel(val, reg); of_property_read_string_index(node, "clock-output-names", SUN4I_A10_PLL2_1X, &clk_name); clks[SUN4I_A10_PLL2_1X] = clk_register_fixed_factor(NULL, clk_name, parent, CLK_SET_RATE_PARENT, 1, SUN4I_PLL2_POST_DIV_VALUE); WARN_ON(IS_ERR(clks[SUN4I_A10_PLL2_1X])); /* * PLL2-2x * * This clock doesn't use the post divider, and really is just * a fixed divider from the PLL2 base clock. */ of_property_read_string_index(node, "clock-output-names", SUN4I_A10_PLL2_2X, &clk_name); clks[SUN4I_A10_PLL2_2X] = clk_register_fixed_factor(NULL, clk_name, parent, CLK_SET_RATE_PARENT, 1, 2); WARN_ON(IS_ERR(clks[SUN4I_A10_PLL2_2X])); /* PLL2-4x */ of_property_read_string_index(node, "clock-output-names", SUN4I_A10_PLL2_4X, &clk_name); clks[SUN4I_A10_PLL2_4X] = clk_register_fixed_factor(NULL, clk_name, parent, CLK_SET_RATE_PARENT, 1, 1); WARN_ON(IS_ERR(clks[SUN4I_A10_PLL2_4X])); /* PLL2-8x */ of_property_read_string_index(node, "clock-output-names", SUN4I_A10_PLL2_8X, &clk_name); clks[SUN4I_A10_PLL2_8X] = clk_register_fixed_factor(NULL, clk_name, parent, CLK_SET_RATE_PARENT, 2, 1); WARN_ON(IS_ERR(clks[SUN4I_A10_PLL2_8X])); clk_data->clks = clks; clk_data->clk_num = SUN4I_PLL2_OUTPUTS; of_clk_add_provider(node, of_clk_src_onecell_get, clk_data); return; err_free_multiplier: kfree(mult); err_free_gate: kfree(gate); err_unregister_prediv: clk_unregister_divider(prediv_clk); err_free_array: kfree(clks); err_free_data: kfree(clk_data); err_unmap: iounmap(reg); }