static int create_sysfs_entry_channel(struct hidma_mgmt_dev *mdev, char *name, int mode, int index, struct kobject *parent) { struct hidma_chan_attr *chattr; char *name_copy; chattr = devm_kmalloc(&mdev->pdev->dev, sizeof(*chattr), GFP_KERNEL); if (!chattr) return -ENOMEM; name_copy = devm_kstrdup(&mdev->pdev->dev, name, GFP_KERNEL); if (!name_copy) return -ENOMEM; chattr->mdev = mdev; chattr->index = index; chattr->attr.attr.name = name_copy; chattr->attr.attr.mode = mode; chattr->attr.show = show_values_channel; chattr->attr.store = set_values_channel; sysfs_attr_init(&chattr->attr.attr); return sysfs_create_file(parent, &chattr->attr.attr); }
static int __ufs_qcom_phy_init_vreg(struct device *dev, struct ufs_qcom_phy_vreg *vreg, const char *name, bool optional) { int err = 0; char prop_name[MAX_PROP_NAME]; vreg->name = devm_kstrdup(dev, name, GFP_KERNEL); if (!vreg->name) { err = -ENOMEM; goto out; } vreg->reg = devm_regulator_get(dev, name); if (IS_ERR(vreg->reg)) { err = PTR_ERR(vreg->reg); vreg->reg = NULL; if (!optional) dev_err(dev, "failed to get %s, %d\n", name, err); goto out; } if (dev->of_node) { snprintf(prop_name, MAX_PROP_NAME, "%s-max-microamp", name); err = of_property_read_u32(dev->of_node, prop_name, &vreg->max_uA); if (err && err != -EINVAL) { dev_err(dev, "%s: failed to read %s\n", __func__, prop_name); goto out; } else if (err == -EINVAL || !vreg->max_uA) { if (regulator_count_voltages(vreg->reg) > 0) { dev_err(dev, "%s: %s is mandatory\n", __func__, prop_name); goto out; } err = 0; } snprintf(prop_name, MAX_PROP_NAME, "%s-always-on", name); vreg->is_always_on = of_property_read_bool(dev->of_node, prop_name); } if (!strcmp(name, "vdda-pll")) { vreg->max_uV = VDDA_PLL_MAX_UV; vreg->min_uV = VDDA_PLL_MIN_UV; } else if (!strcmp(name, "vdda-phy")) { vreg->max_uV = VDDA_PHY_MAX_UV; vreg->min_uV = VDDA_PHY_MIN_UV; } else if (!strcmp(name, "vddp-ref-clk")) { vreg->max_uV = VDDP_REF_CLK_MAX_UV; vreg->min_uV = VDDP_REF_CLK_MIN_UV; } out: if (err) kfree(vreg->name); return err; }
static int __init gef_gpio_probe(struct platform_device *pdev) { const struct of_device_id *of_id = of_match_device(gef_gpio_ids, &pdev->dev); struct gpio_chip *gc; void __iomem *regs; int ret; gc = devm_kzalloc(&pdev->dev, sizeof(*gc), GFP_KERNEL); if (!gc) return -ENOMEM; regs = of_iomap(pdev->dev.of_node, 0); if (!regs) return -ENOMEM; ret = bgpio_init(gc, &pdev->dev, 4, regs + GEF_GPIO_IN, regs + GEF_GPIO_OUT, NULL, NULL, regs + GEF_GPIO_DIRECT, BGPIOF_BIG_ENDIAN_BYTE_ORDER); if (ret) { dev_err(&pdev->dev, "bgpio_init failed\n"); goto err0; } /* Setup pointers to chip functions */ gc->label = devm_kstrdup(&pdev->dev, pdev->dev.of_node->full_name, GFP_KERNEL); if (!gc->label) { ret = -ENOMEM; goto err0; } gc->base = -1; gc->ngpio = (u16)(uintptr_t)of_id->data; gc->of_gpio_n_cells = 2; gc->of_node = pdev->dev.of_node; /* This function adds a memory mapped GPIO chip */ ret = devm_gpiochip_add_data(&pdev->dev, gc, NULL); if (ret) goto err0; return 0; err0: iounmap(regs); pr_err("%s: GPIO chip registration failed\n", pdev->dev.of_node->full_name); return ret; };
/* * of_coresight_parse_endpoint : Parse the given output endpoint @ep * and fill the connection information in @conn * * Parses the local port, remote device name and the remote port. * * Returns : * 1 - If the parsing is successful and a connection record * was created for an output connection. * 0 - If the parsing completed without any fatal errors. * -Errno - Fatal error, abort the scanning. */ static int of_coresight_parse_endpoint(struct device *dev, struct device_node *ep, struct coresight_connection *conn) { int ret = 0; struct of_endpoint endpoint, rendpoint; struct device_node *rparent = NULL; struct device_node *rep = NULL; struct device *rdev = NULL; do { /* Parse the local port details */ if (of_graph_parse_endpoint(ep, &endpoint)) break; /* * Get a handle on the remote endpoint and the device it is * attached to. */ rep = of_graph_get_remote_endpoint(ep); if (!rep) break; rparent = of_coresight_get_port_parent(rep); if (!rparent) break; if (of_graph_parse_endpoint(rep, &rendpoint)) break; /* If the remote device is not available, defer probing */ rdev = of_coresight_get_endpoint_device(rparent); if (!rdev) { ret = -EPROBE_DEFER; break; } conn->outport = endpoint.port; conn->child_name = devm_kstrdup(dev, dev_name(rdev), GFP_KERNEL); conn->child_port = rendpoint.port; /* Connection record updated */ ret = 1; } while (0); of_node_put(rparent); of_node_put(rep); put_device(rdev); return ret; }
static int create_sysfs_entry(struct hidma_mgmt_dev *dev, char *name, int mode) { struct device_attribute *attrs; char *name_copy; attrs = devm_kmalloc(&dev->pdev->dev, sizeof(struct device_attribute), GFP_KERNEL); if (!attrs) return -ENOMEM; name_copy = devm_kstrdup(&dev->pdev->dev, name, GFP_KERNEL); if (!name_copy) return -ENOMEM; attrs->attr.name = name_copy; attrs->attr.mode = mode; attrs->show = show_values; attrs->store = set_values; sysfs_attr_init(&attrs->attr); return device_create_file(&dev->pdev->dev, attrs); }
static int reg_fixed_voltage_probe(struct platform_device *pdev) { struct fixed_voltage_config *config; struct fixed_voltage_data *drvdata; struct regulator_config cfg = { }; int ret; if (pdev->dev.of_node) { config = of_get_fixed_voltage_config(&pdev->dev); if (IS_ERR(config)) return PTR_ERR(config); } else { config = dev_get_platdata(&pdev->dev); } if (!config) return -ENOMEM; drvdata = devm_kzalloc(&pdev->dev, sizeof(struct fixed_voltage_data), GFP_KERNEL); if (!drvdata) return -ENOMEM; drvdata->desc.name = devm_kstrdup(&pdev->dev, config->supply_name, GFP_KERNEL); if (drvdata->desc.name == NULL) { dev_err(&pdev->dev, "Failed to allocate supply name\n"); return -ENOMEM; } drvdata->desc.type = REGULATOR_VOLTAGE; drvdata->desc.owner = THIS_MODULE; drvdata->desc.ops = &fixed_voltage_ops; drvdata->desc.enable_time = config->startup_delay; if (config->input_supply) { drvdata->desc.supply_name = devm_kstrdup(&pdev->dev, config->input_supply, GFP_KERNEL); if (!drvdata->desc.supply_name) { dev_err(&pdev->dev, "Failed to allocate input supply\n"); return -ENOMEM; } } if (config->microvolts) drvdata->desc.n_voltages = 1; drvdata->desc.fixed_uV = config->microvolts; if (config->gpio >= 0) cfg.ena_gpio = config->gpio; cfg.ena_gpio_invert = !config->enable_high; if (config->enabled_at_boot) { if (config->enable_high) cfg.ena_gpio_flags |= GPIOF_OUT_INIT_HIGH; else cfg.ena_gpio_flags |= GPIOF_OUT_INIT_LOW; } else { if (config->enable_high) cfg.ena_gpio_flags |= GPIOF_OUT_INIT_LOW; else cfg.ena_gpio_flags |= GPIOF_OUT_INIT_HIGH; } if (config->gpio_is_open_drain) cfg.ena_gpio_flags |= GPIOF_OPEN_DRAIN; cfg.dev = &pdev->dev; cfg.init_data = config->init_data; cfg.driver_data = drvdata; cfg.of_node = pdev->dev.of_node; drvdata->dev = devm_regulator_register(&pdev->dev, &drvdata->desc, &cfg); if (IS_ERR(drvdata->dev)) { ret = PTR_ERR(drvdata->dev); dev_err(&pdev->dev, "Failed to register regulator: %d\n", ret); return ret; } platform_set_drvdata(pdev, drvdata); dev_dbg(&pdev->dev, "%s supplying %duV\n", drvdata->desc.name, drvdata->desc.fixed_uV); return 0; }
/* * The SD/eMMC IP block has an internal mux and divider used for * generating the MMC clock. Use the clock framework to create and * manage these clocks. */ static int meson_mmc_clk_init(struct meson_host *host) { struct clk_init_data init; char clk_name[32]; int i, ret = 0; const char *mux_parent_names[MUX_CLK_NUM_PARENTS]; unsigned int mux_parent_count = 0; const char *clk_div_parents[1]; u32 clk_reg, cfg; /* get the mux parents */ for (i = 0; i < MUX_CLK_NUM_PARENTS; i++) { char name[16]; snprintf(name, sizeof(name), "clkin%d", i); host->mux_parent[i] = devm_clk_get(host->dev, name); if (IS_ERR(host->mux_parent[i])) { ret = PTR_ERR(host->mux_parent[i]); if (PTR_ERR(host->mux_parent[i]) != -EPROBE_DEFER) dev_err(host->dev, "Missing clock %s\n", name); host->mux_parent[i] = NULL; return ret; } mux_parent_names[i] = __clk_get_name(host->mux_parent[i]); mux_parent_count++; } /* create the mux */ snprintf(clk_name, sizeof(clk_name), "%s#mux", dev_name(host->dev)); init.name = clk_name; init.ops = &clk_mux_ops; init.flags = 0; init.parent_names = mux_parent_names; init.num_parents = mux_parent_count; host->mux.reg = host->regs + SD_EMMC_CLOCK; host->mux.shift = CLK_SRC_SHIFT; host->mux.mask = CLK_SRC_MASK; host->mux.flags = 0; host->mux.table = NULL; host->mux.hw.init = &init; host->mux_clk = devm_clk_register(host->dev, &host->mux.hw); if (WARN_ON(IS_ERR(host->mux_clk))) return PTR_ERR(host->mux_clk); /* create the divider */ snprintf(clk_name, sizeof(clk_name), "%s#div", dev_name(host->dev)); init.name = devm_kstrdup(host->dev, clk_name, GFP_KERNEL); init.ops = &clk_divider_ops; init.flags = CLK_SET_RATE_PARENT; clk_div_parents[0] = __clk_get_name(host->mux_clk); init.parent_names = clk_div_parents; init.num_parents = ARRAY_SIZE(clk_div_parents); host->cfg_div.reg = host->regs + SD_EMMC_CLOCK; host->cfg_div.shift = CLK_DIV_SHIFT; host->cfg_div.width = CLK_DIV_WIDTH; host->cfg_div.hw.init = &init; host->cfg_div.flags = CLK_DIVIDER_ONE_BASED | CLK_DIVIDER_ROUND_CLOSEST | CLK_DIVIDER_ALLOW_ZERO; host->cfg_div_clk = devm_clk_register(host->dev, &host->cfg_div.hw); if (WARN_ON(PTR_ERR_OR_ZERO(host->cfg_div_clk))) return PTR_ERR(host->cfg_div_clk); /* init SD_EMMC_CLOCK to sane defaults w/min clock rate */ clk_reg = 0; clk_reg |= CLK_PHASE_180 << CLK_PHASE_SHIFT; clk_reg |= CLK_SRC_XTAL << CLK_SRC_SHIFT; clk_reg |= CLK_DIV_MAX << CLK_DIV_SHIFT; clk_reg &= ~CLK_ALWAYS_ON; writel(clk_reg, host->regs + SD_EMMC_CLOCK); /* Ensure clock starts in "auto" mode, not "always on" */ cfg = readl(host->regs + SD_EMMC_CFG); cfg &= ~CFG_CLK_ALWAYS_ON; cfg |= CFG_AUTO_CLK; writel(cfg, host->regs + SD_EMMC_CFG); ret = clk_prepare_enable(host->cfg_div_clk); if (ret) return ret; /* Get the nearest minimum clock to 400KHz */ host->mmc->f_min = clk_round_rate(host->cfg_div_clk, 400000); ret = meson_mmc_clk_set(host, host->mmc->f_min); if (!ret) clk_disable_unprepare(host->cfg_div_clk); return ret; }
static int iio_hwmon_probe(struct platform_device *pdev) { struct device *dev = &pdev->dev; struct iio_hwmon_state *st; struct sensor_device_attribute *a; int ret, i; int in_i = 1, temp_i = 1, curr_i = 1, humidity_i = 1; enum iio_chan_type type; struct iio_channel *channels; const char *name = "iio_hwmon"; char *sname; if (dev->of_node && dev->of_node->name) name = dev->of_node->name; channels = iio_channel_get_all(dev); if (IS_ERR(channels)) return PTR_ERR(channels); st = devm_kzalloc(dev, sizeof(*st), GFP_KERNEL); if (st == NULL) { ret = -ENOMEM; goto error_release_channels; } st->channels = channels; /* count how many attributes we have */ while (st->channels[st->num_channels].indio_dev) st->num_channels++; st->attrs = devm_kzalloc(dev, sizeof(*st->attrs) * (st->num_channels + 1), GFP_KERNEL); if (st->attrs == NULL) { ret = -ENOMEM; goto error_release_channels; } for (i = 0; i < st->num_channels; i++) { a = devm_kzalloc(dev, sizeof(*a), GFP_KERNEL); if (a == NULL) { ret = -ENOMEM; goto error_release_channels; } sysfs_attr_init(&a->dev_attr.attr); ret = iio_get_channel_type(&st->channels[i], &type); if (ret < 0) goto error_release_channels; switch (type) { case IIO_VOLTAGE: a->dev_attr.attr.name = kasprintf(GFP_KERNEL, "in%d_input", in_i++); break; case IIO_TEMP: a->dev_attr.attr.name = kasprintf(GFP_KERNEL, "temp%d_input", temp_i++); break; case IIO_CURRENT: a->dev_attr.attr.name = kasprintf(GFP_KERNEL, "curr%d_input", curr_i++); break; case IIO_HUMIDITYRELATIVE: a->dev_attr.attr.name = kasprintf(GFP_KERNEL, "humidity%d_input", humidity_i++); break; default: ret = -EINVAL; goto error_release_channels; } if (a->dev_attr.attr.name == NULL) { ret = -ENOMEM; goto error_release_channels; } a->dev_attr.show = iio_hwmon_read_val; a->dev_attr.attr.mode = S_IRUGO; a->index = i; st->attrs[i] = &a->dev_attr.attr; } st->attr_group.attrs = st->attrs; st->groups[0] = &st->attr_group; sname = devm_kstrdup(dev, name, GFP_KERNEL); if (!sname) { ret = -ENOMEM; goto error_release_channels; } strreplace(sname, '-', '_'); st->hwmon_dev = hwmon_device_register_with_groups(dev, sname, st, st->groups); if (IS_ERR(st->hwmon_dev)) { ret = PTR_ERR(st->hwmon_dev); goto error_release_channels; } platform_set_drvdata(pdev, st); return 0; error_release_channels: iio_channel_release_all(channels); return ret; }
static int meson8b_init_rgmii_tx_clk(struct meson8b_dwmac *dwmac) { struct clk_init_data init; int i, ret; struct device *dev = &dwmac->pdev->dev; char clk_name[32]; const char *clk_div_parents[1]; const char *mux_parent_names[MUX_CLK_NUM_PARENTS]; /* get the mux parents from DT */ for (i = 0; i < MUX_CLK_NUM_PARENTS; i++) { char name[16]; snprintf(name, sizeof(name), "clkin%d", i); dwmac->m250_mux_parent[i] = devm_clk_get(dev, name); if (IS_ERR(dwmac->m250_mux_parent[i])) { ret = PTR_ERR(dwmac->m250_mux_parent[i]); if (ret != -EPROBE_DEFER) dev_err(dev, "Missing clock %s\n", name); return ret; } mux_parent_names[i] = __clk_get_name(dwmac->m250_mux_parent[i]); } /* create the m250_mux */ snprintf(clk_name, sizeof(clk_name), "%s#m250_sel", dev_name(dev)); init.name = clk_name; init.ops = &clk_mux_ops; init.flags = CLK_SET_RATE_PARENT; init.parent_names = mux_parent_names; init.num_parents = MUX_CLK_NUM_PARENTS; dwmac->m250_mux.reg = dwmac->regs + PRG_ETH0; dwmac->m250_mux.shift = PRG_ETH0_CLK_M250_SEL_SHIFT; dwmac->m250_mux.mask = PRG_ETH0_CLK_M250_SEL_MASK; dwmac->m250_mux.flags = 0; dwmac->m250_mux.table = NULL; dwmac->m250_mux.hw.init = &init; dwmac->m250_mux_clk = devm_clk_register(dev, &dwmac->m250_mux.hw); if (WARN_ON(IS_ERR(dwmac->m250_mux_clk))) return PTR_ERR(dwmac->m250_mux_clk); /* create the m250_div */ snprintf(clk_name, sizeof(clk_name), "%s#m250_div", dev_name(dev)); init.name = devm_kstrdup(dev, clk_name, GFP_KERNEL); init.ops = &clk_divider_ops; init.flags = CLK_SET_RATE_PARENT; clk_div_parents[0] = __clk_get_name(dwmac->m250_mux_clk); init.parent_names = clk_div_parents; init.num_parents = ARRAY_SIZE(clk_div_parents); dwmac->m250_div.reg = dwmac->regs + PRG_ETH0; dwmac->m250_div.shift = PRG_ETH0_CLK_M250_DIV_SHIFT; dwmac->m250_div.width = PRG_ETH0_CLK_M250_DIV_WIDTH; dwmac->m250_div.hw.init = &init; dwmac->m250_div.flags = CLK_DIVIDER_ONE_BASED | CLK_DIVIDER_ALLOW_ZERO | CLK_DIVIDER_ROUND_CLOSEST; dwmac->m250_div_clk = devm_clk_register(dev, &dwmac->m250_div.hw); if (WARN_ON(IS_ERR(dwmac->m250_div_clk))) return PTR_ERR(dwmac->m250_div_clk); /* create the fixed_div2 */ snprintf(clk_name, sizeof(clk_name), "%s#fixed_div2", dev_name(dev)); init.name = devm_kstrdup(dev, clk_name, GFP_KERNEL); init.ops = &clk_fixed_factor_ops; init.flags = CLK_SET_RATE_PARENT; clk_div_parents[0] = __clk_get_name(dwmac->m250_div_clk); init.parent_names = clk_div_parents; init.num_parents = ARRAY_SIZE(clk_div_parents); dwmac->fixed_div2.mult = 1; dwmac->fixed_div2.div = 2; dwmac->fixed_div2.hw.init = &init; dwmac->fixed_div2_clk = devm_clk_register(dev, &dwmac->fixed_div2.hw); if (WARN_ON(IS_ERR(dwmac->fixed_div2_clk))) return PTR_ERR(dwmac->fixed_div2_clk); /* create the rgmii_tx_en */ init.name = devm_kasprintf(dev, GFP_KERNEL, "%s#rgmii_tx_en", dev_name(dev)); init.ops = &clk_gate_ops; init.flags = CLK_SET_RATE_PARENT; clk_div_parents[0] = __clk_get_name(dwmac->fixed_div2_clk); init.parent_names = clk_div_parents; init.num_parents = ARRAY_SIZE(clk_div_parents); dwmac->rgmii_tx_en.reg = dwmac->regs + PRG_ETH0; dwmac->rgmii_tx_en.bit_idx = PRG_ETH0_RGMII_TX_CLK_EN; dwmac->rgmii_tx_en.hw.init = &init; dwmac->rgmii_tx_en_clk = devm_clk_register(dev, &dwmac->rgmii_tx_en.hw); if (WARN_ON(IS_ERR(dwmac->rgmii_tx_en_clk))) return PTR_ERR(dwmac->rgmii_tx_en_clk); return 0; }