linux/drivers/pinctrl/mvebu/pinctrl-mvebu.c
<<
>>
Prefs
   1// SPDX-License-Identifier: GPL-2.0-or-later
   2/*
   3 * Marvell MVEBU pinctrl core driver
   4 *
   5 * Authors: Sebastian Hesselbarth <sebastian.hesselbarth@gmail.com>
   6 *          Thomas Petazzoni <thomas.petazzoni@free-electrons.com>
   7 */
   8
   9#include <linux/platform_device.h>
  10#include <linux/slab.h>
  11#include <linux/io.h>
  12#include <linux/of.h>
  13#include <linux/of_address.h>
  14#include <linux/of_platform.h>
  15#include <linux/err.h>
  16#include <linux/gpio/driver.h>
  17#include <linux/pinctrl/machine.h>
  18#include <linux/pinctrl/pinconf.h>
  19#include <linux/pinctrl/pinctrl.h>
  20#include <linux/pinctrl/pinmux.h>
  21#include <linux/mfd/syscon.h>
  22#include <linux/regmap.h>
  23
  24#include "pinctrl-mvebu.h"
  25
  26#define MPPS_PER_REG    8
  27#define MPP_BITS        4
  28#define MPP_MASK        0xf
  29
  30struct mvebu_pinctrl_function {
  31        const char *name;
  32        const char **groups;
  33        unsigned num_groups;
  34};
  35
  36struct mvebu_pinctrl_group {
  37        const char *name;
  38        const struct mvebu_mpp_ctrl *ctrl;
  39        struct mvebu_mpp_ctrl_data *data;
  40        struct mvebu_mpp_ctrl_setting *settings;
  41        unsigned num_settings;
  42        unsigned gid;
  43        unsigned *pins;
  44        unsigned npins;
  45};
  46
  47struct mvebu_pinctrl {
  48        struct device *dev;
  49        struct pinctrl_dev *pctldev;
  50        struct pinctrl_desc desc;
  51        struct mvebu_pinctrl_group *groups;
  52        unsigned num_groups;
  53        struct mvebu_pinctrl_function *functions;
  54        unsigned num_functions;
  55        u8 variant;
  56};
  57
  58int mvebu_mmio_mpp_ctrl_get(struct mvebu_mpp_ctrl_data *data,
  59                             unsigned int pid, unsigned long *config)
  60{
  61        unsigned off = (pid / MVEBU_MPPS_PER_REG) * MVEBU_MPP_BITS;
  62        unsigned shift = (pid % MVEBU_MPPS_PER_REG) * MVEBU_MPP_BITS;
  63
  64        *config = (readl(data->base + off) >> shift) & MVEBU_MPP_MASK;
  65
  66        return 0;
  67}
  68
  69int mvebu_mmio_mpp_ctrl_set(struct mvebu_mpp_ctrl_data *data,
  70                             unsigned int pid, unsigned long config)
  71{
  72        unsigned off = (pid / MVEBU_MPPS_PER_REG) * MVEBU_MPP_BITS;
  73        unsigned shift = (pid % MVEBU_MPPS_PER_REG) * MVEBU_MPP_BITS;
  74        unsigned long reg;
  75
  76        reg = readl(data->base + off) & ~(MVEBU_MPP_MASK << shift);
  77        writel(reg | (config << shift), data->base + off);
  78
  79        return 0;
  80}
  81
  82static struct mvebu_pinctrl_group *mvebu_pinctrl_find_group_by_pid(
  83        struct mvebu_pinctrl *pctl, unsigned pid)
  84{
  85        unsigned n;
  86        for (n = 0; n < pctl->num_groups; n++) {
  87                if (pid >= pctl->groups[n].pins[0] &&
  88                    pid < pctl->groups[n].pins[0] +
  89                        pctl->groups[n].npins)
  90                        return &pctl->groups[n];
  91        }
  92        return NULL;
  93}
  94
  95static struct mvebu_pinctrl_group *mvebu_pinctrl_find_group_by_name(
  96        struct mvebu_pinctrl *pctl, const char *name)
  97{
  98        unsigned n;
  99        for (n = 0; n < pctl->num_groups; n++) {
 100                if (strcmp(name, pctl->groups[n].name) == 0)
 101                        return &pctl->groups[n];
 102        }
 103        return NULL;
 104}
 105
 106static struct mvebu_mpp_ctrl_setting *mvebu_pinctrl_find_setting_by_val(
 107        struct mvebu_pinctrl *pctl, struct mvebu_pinctrl_group *grp,
 108        unsigned long config)
 109{
 110        unsigned n;
 111        for (n = 0; n < grp->num_settings; n++) {
 112                if (config == grp->settings[n].val) {
 113                        if (!pctl->variant || (pctl->variant &
 114                                               grp->settings[n].variant))
 115                                return &grp->settings[n];
 116                }
 117        }
 118        return NULL;
 119}
 120
 121static struct mvebu_mpp_ctrl_setting *mvebu_pinctrl_find_setting_by_name(
 122        struct mvebu_pinctrl *pctl, struct mvebu_pinctrl_group *grp,
 123        const char *name)
 124{
 125        unsigned n;
 126        for (n = 0; n < grp->num_settings; n++) {
 127                if (strcmp(name, grp->settings[n].name) == 0) {
 128                        if (!pctl->variant || (pctl->variant &
 129                                               grp->settings[n].variant))
 130                                return &grp->settings[n];
 131                }
 132        }
 133        return NULL;
 134}
 135
 136static struct mvebu_mpp_ctrl_setting *mvebu_pinctrl_find_gpio_setting(
 137        struct mvebu_pinctrl *pctl, struct mvebu_pinctrl_group *grp)
 138{
 139        unsigned n;
 140        for (n = 0; n < grp->num_settings; n++) {
 141                if (grp->settings[n].flags &
 142                        (MVEBU_SETTING_GPO | MVEBU_SETTING_GPI)) {
 143                        if (!pctl->variant || (pctl->variant &
 144                                                grp->settings[n].variant))
 145                                return &grp->settings[n];
 146                }
 147        }
 148        return NULL;
 149}
 150
 151static struct mvebu_pinctrl_function *mvebu_pinctrl_find_function_by_name(
 152        struct mvebu_pinctrl *pctl, const char *name)
 153{
 154        unsigned n;
 155        for (n = 0; n < pctl->num_functions; n++) {
 156                if (strcmp(name, pctl->functions[n].name) == 0)
 157                        return &pctl->functions[n];
 158        }
 159        return NULL;
 160}
 161
 162static int mvebu_pinconf_group_get(struct pinctrl_dev *pctldev,
 163                                unsigned gid, unsigned long *config)
 164{
 165        struct mvebu_pinctrl *pctl = pinctrl_dev_get_drvdata(pctldev);
 166        struct mvebu_pinctrl_group *grp = &pctl->groups[gid];
 167
 168        if (!grp->ctrl)
 169                return -EINVAL;
 170
 171        return grp->ctrl->mpp_get(grp->data, grp->pins[0], config);
 172}
 173
 174static int mvebu_pinconf_group_set(struct pinctrl_dev *pctldev,
 175                                unsigned gid, unsigned long *configs,
 176                                unsigned num_configs)
 177{
 178        struct mvebu_pinctrl *pctl = pinctrl_dev_get_drvdata(pctldev);
 179        struct mvebu_pinctrl_group *grp = &pctl->groups[gid];
 180        int i, ret;
 181
 182        if (!grp->ctrl)
 183                return -EINVAL;
 184
 185        for (i = 0; i < num_configs; i++) {
 186                ret = grp->ctrl->mpp_set(grp->data, grp->pins[0], configs[i]);
 187                if (ret)
 188                        return ret;
 189        } /* for each config */
 190
 191        return 0;
 192}
 193
 194static void mvebu_pinconf_group_dbg_show(struct pinctrl_dev *pctldev,
 195                                        struct seq_file *s, unsigned gid)
 196{
 197        struct mvebu_pinctrl *pctl = pinctrl_dev_get_drvdata(pctldev);
 198        struct mvebu_pinctrl_group *grp = &pctl->groups[gid];
 199        struct mvebu_mpp_ctrl_setting *curr;
 200        unsigned long config;
 201        unsigned n;
 202
 203        if (mvebu_pinconf_group_get(pctldev, gid, &config))
 204                return;
 205
 206        curr = mvebu_pinctrl_find_setting_by_val(pctl, grp, config);
 207
 208        if (curr) {
 209                seq_printf(s, "current: %s", curr->name);
 210                if (curr->subname)
 211                        seq_printf(s, "(%s)", curr->subname);
 212                if (curr->flags & (MVEBU_SETTING_GPO | MVEBU_SETTING_GPI)) {
 213                        seq_putc(s, '(');
 214                        if (curr->flags & MVEBU_SETTING_GPI)
 215                                seq_putc(s, 'i');
 216                        if (curr->flags & MVEBU_SETTING_GPO)
 217                                seq_putc(s, 'o');
 218                        seq_putc(s, ')');
 219                }
 220        } else {
 221                seq_puts(s, "current: UNKNOWN");
 222        }
 223
 224        if (grp->num_settings > 1) {
 225                seq_puts(s, ", available = [");
 226                for (n = 0; n < grp->num_settings; n++) {
 227                        if (curr == &grp->settings[n])
 228                                continue;
 229
 230                        /* skip unsupported settings for this variant */
 231                        if (pctl->variant &&
 232                            !(pctl->variant & grp->settings[n].variant))
 233                                continue;
 234
 235                        seq_printf(s, " %s", grp->settings[n].name);
 236                        if (grp->settings[n].subname)
 237                                seq_printf(s, "(%s)", grp->settings[n].subname);
 238                        if (grp->settings[n].flags &
 239                                (MVEBU_SETTING_GPO | MVEBU_SETTING_GPI)) {
 240                                seq_putc(s, '(');
 241                                if (grp->settings[n].flags & MVEBU_SETTING_GPI)
 242                                        seq_putc(s, 'i');
 243                                if (grp->settings[n].flags & MVEBU_SETTING_GPO)
 244                                        seq_putc(s, 'o');
 245                                seq_putc(s, ')');
 246                        }
 247                }
 248                seq_puts(s, " ]");
 249        }
 250}
 251
 252static const struct pinconf_ops mvebu_pinconf_ops = {
 253        .pin_config_group_get = mvebu_pinconf_group_get,
 254        .pin_config_group_set = mvebu_pinconf_group_set,
 255        .pin_config_group_dbg_show = mvebu_pinconf_group_dbg_show,
 256};
 257
 258static int mvebu_pinmux_get_funcs_count(struct pinctrl_dev *pctldev)
 259{
 260        struct mvebu_pinctrl *pctl = pinctrl_dev_get_drvdata(pctldev);
 261
 262        return pctl->num_functions;
 263}
 264
 265static const char *mvebu_pinmux_get_func_name(struct pinctrl_dev *pctldev,
 266                                        unsigned fid)
 267{
 268        struct mvebu_pinctrl *pctl = pinctrl_dev_get_drvdata(pctldev);
 269
 270        return pctl->functions[fid].name;
 271}
 272
 273static int mvebu_pinmux_get_groups(struct pinctrl_dev *pctldev, unsigned fid,
 274                                const char * const **groups,
 275                                unsigned * const num_groups)
 276{
 277        struct mvebu_pinctrl *pctl = pinctrl_dev_get_drvdata(pctldev);
 278
 279        *groups = pctl->functions[fid].groups;
 280        *num_groups = pctl->functions[fid].num_groups;
 281        return 0;
 282}
 283
 284static int mvebu_pinmux_set(struct pinctrl_dev *pctldev, unsigned fid,
 285                            unsigned gid)
 286{
 287        struct mvebu_pinctrl *pctl = pinctrl_dev_get_drvdata(pctldev);
 288        struct mvebu_pinctrl_function *func = &pctl->functions[fid];
 289        struct mvebu_pinctrl_group *grp = &pctl->groups[gid];
 290        struct mvebu_mpp_ctrl_setting *setting;
 291        int ret;
 292        unsigned long config;
 293
 294        setting = mvebu_pinctrl_find_setting_by_name(pctl, grp,
 295                                                     func->name);
 296        if (!setting) {
 297                dev_err(pctl->dev,
 298                        "unable to find setting %s in group %s\n",
 299                        func->name, func->groups[gid]);
 300                return -EINVAL;
 301        }
 302
 303        config = setting->val;
 304        ret = mvebu_pinconf_group_set(pctldev, grp->gid, &config, 1);
 305        if (ret) {
 306                dev_err(pctl->dev, "cannot set group %s to %s\n",
 307                        func->groups[gid], func->name);
 308                return ret;
 309        }
 310
 311        return 0;
 312}
 313
 314static int mvebu_pinmux_gpio_request_enable(struct pinctrl_dev *pctldev,
 315                        struct pinctrl_gpio_range *range, unsigned offset)
 316{
 317        struct mvebu_pinctrl *pctl = pinctrl_dev_get_drvdata(pctldev);
 318        struct mvebu_pinctrl_group *grp;
 319        struct mvebu_mpp_ctrl_setting *setting;
 320        unsigned long config;
 321
 322        grp = mvebu_pinctrl_find_group_by_pid(pctl, offset);
 323        if (!grp)
 324                return -EINVAL;
 325
 326        if (grp->ctrl->mpp_gpio_req)
 327                return grp->ctrl->mpp_gpio_req(grp->data, offset);
 328
 329        setting = mvebu_pinctrl_find_gpio_setting(pctl, grp);
 330        if (!setting)
 331                return -ENOTSUPP;
 332
 333        config = setting->val;
 334
 335        return mvebu_pinconf_group_set(pctldev, grp->gid, &config, 1);
 336}
 337
 338static int mvebu_pinmux_gpio_set_direction(struct pinctrl_dev *pctldev,
 339           struct pinctrl_gpio_range *range, unsigned offset, bool input)
 340{
 341        struct mvebu_pinctrl *pctl = pinctrl_dev_get_drvdata(pctldev);
 342        struct mvebu_pinctrl_group *grp;
 343        struct mvebu_mpp_ctrl_setting *setting;
 344
 345        grp = mvebu_pinctrl_find_group_by_pid(pctl, offset);
 346        if (!grp)
 347                return -EINVAL;
 348
 349        if (grp->ctrl->mpp_gpio_dir)
 350                return grp->ctrl->mpp_gpio_dir(grp->data, offset, input);
 351
 352        setting = mvebu_pinctrl_find_gpio_setting(pctl, grp);
 353        if (!setting)
 354                return -ENOTSUPP;
 355
 356        if ((input && (setting->flags & MVEBU_SETTING_GPI)) ||
 357            (!input && (setting->flags & MVEBU_SETTING_GPO)))
 358                return 0;
 359
 360        return -ENOTSUPP;
 361}
 362
 363static const struct pinmux_ops mvebu_pinmux_ops = {
 364        .get_functions_count = mvebu_pinmux_get_funcs_count,
 365        .get_function_name = mvebu_pinmux_get_func_name,
 366        .get_function_groups = mvebu_pinmux_get_groups,
 367        .gpio_request_enable = mvebu_pinmux_gpio_request_enable,
 368        .gpio_set_direction = mvebu_pinmux_gpio_set_direction,
 369        .set_mux = mvebu_pinmux_set,
 370};
 371
 372static int mvebu_pinctrl_get_groups_count(struct pinctrl_dev *pctldev)
 373{
 374        struct mvebu_pinctrl *pctl = pinctrl_dev_get_drvdata(pctldev);
 375        return pctl->num_groups;
 376}
 377
 378static const char *mvebu_pinctrl_get_group_name(struct pinctrl_dev *pctldev,
 379                                                unsigned gid)
 380{
 381        struct mvebu_pinctrl *pctl = pinctrl_dev_get_drvdata(pctldev);
 382        return pctl->groups[gid].name;
 383}
 384
 385static int mvebu_pinctrl_get_group_pins(struct pinctrl_dev *pctldev,
 386                                        unsigned gid, const unsigned **pins,
 387                                        unsigned *num_pins)
 388{
 389        struct mvebu_pinctrl *pctl = pinctrl_dev_get_drvdata(pctldev);
 390        *pins = pctl->groups[gid].pins;
 391        *num_pins = pctl->groups[gid].npins;
 392        return 0;
 393}
 394
 395static int mvebu_pinctrl_dt_node_to_map(struct pinctrl_dev *pctldev,
 396                                        struct device_node *np,
 397                                        struct pinctrl_map **map,
 398                                        unsigned *num_maps)
 399{
 400        struct mvebu_pinctrl *pctl = pinctrl_dev_get_drvdata(pctldev);
 401        struct property *prop;
 402        const char *function;
 403        const char *group;
 404        int ret, nmaps, n;
 405
 406        *map = NULL;
 407        *num_maps = 0;
 408
 409        ret = of_property_read_string(np, "marvell,function", &function);
 410        if (ret) {
 411                dev_err(pctl->dev,
 412                        "missing marvell,function in node %pOFn\n", np);
 413                return 0;
 414        }
 415
 416        nmaps = of_property_count_strings(np, "marvell,pins");
 417        if (nmaps < 0) {
 418                dev_err(pctl->dev,
 419                        "missing marvell,pins in node %pOFn\n", np);
 420                return 0;
 421        }
 422
 423        *map = kmalloc_array(nmaps, sizeof(**map), GFP_KERNEL);
 424        if (!*map)
 425                return -ENOMEM;
 426
 427        n = 0;
 428        of_property_for_each_string(np, "marvell,pins", prop, group) {
 429                struct mvebu_pinctrl_group *grp =
 430                        mvebu_pinctrl_find_group_by_name(pctl, group);
 431
 432                if (!grp) {
 433                        dev_err(pctl->dev, "unknown pin %s", group);
 434                        continue;
 435                }
 436
 437                if (!mvebu_pinctrl_find_setting_by_name(pctl, grp, function)) {
 438                        dev_err(pctl->dev, "unsupported function %s on pin %s",
 439                                function, group);
 440                        continue;
 441                }
 442
 443                (*map)[n].type = PIN_MAP_TYPE_MUX_GROUP;
 444                (*map)[n].data.mux.group = group;
 445                (*map)[n].data.mux.function = function;
 446                n++;
 447        }
 448
 449        *num_maps = nmaps;
 450
 451        return 0;
 452}
 453
 454static void mvebu_pinctrl_dt_free_map(struct pinctrl_dev *pctldev,
 455                                struct pinctrl_map *map, unsigned num_maps)
 456{
 457        kfree(map);
 458}
 459
 460static const struct pinctrl_ops mvebu_pinctrl_ops = {
 461        .get_groups_count = mvebu_pinctrl_get_groups_count,
 462        .get_group_name = mvebu_pinctrl_get_group_name,
 463        .get_group_pins = mvebu_pinctrl_get_group_pins,
 464        .dt_node_to_map = mvebu_pinctrl_dt_node_to_map,
 465        .dt_free_map = mvebu_pinctrl_dt_free_map,
 466};
 467
 468static int _add_function(struct mvebu_pinctrl_function *funcs, int *funcsize,
 469                        const char *name)
 470{
 471        if (*funcsize <= 0)
 472                return -EOVERFLOW;
 473
 474        while (funcs->num_groups) {
 475                /* function already there */
 476                if (strcmp(funcs->name, name) == 0) {
 477                        funcs->num_groups++;
 478                        return -EEXIST;
 479                }
 480                funcs++;
 481        }
 482
 483        /* append new unique function */
 484        funcs->name = name;
 485        funcs->num_groups = 1;
 486        (*funcsize)--;
 487
 488        return 0;
 489}
 490
 491static int mvebu_pinctrl_build_functions(struct platform_device *pdev,
 492                                         struct mvebu_pinctrl *pctl)
 493{
 494        struct mvebu_pinctrl_function *funcs;
 495        int num = 0, funcsize = pctl->desc.npins;
 496        int n, s;
 497
 498        /* we allocate functions for number of pins and hope
 499         * there are fewer unique functions than pins available */
 500        funcs = devm_kcalloc(&pdev->dev,
 501                             funcsize, sizeof(struct mvebu_pinctrl_function),
 502                             GFP_KERNEL);
 503        if (!funcs)
 504                return -ENOMEM;
 505
 506        for (n = 0; n < pctl->num_groups; n++) {
 507                struct mvebu_pinctrl_group *grp = &pctl->groups[n];
 508                for (s = 0; s < grp->num_settings; s++) {
 509                        int ret;
 510
 511                        /* skip unsupported settings on this variant */
 512                        if (pctl->variant &&
 513                            !(pctl->variant & grp->settings[s].variant))
 514                                continue;
 515
 516                        /* check for unique functions and count groups */
 517                        ret = _add_function(funcs, &funcsize,
 518                                            grp->settings[s].name);
 519                        if (ret == -EOVERFLOW)
 520                                dev_err(&pdev->dev,
 521                                        "More functions than pins(%d)\n",
 522                                        pctl->desc.npins);
 523                        if (ret < 0)
 524                                continue;
 525
 526                        num++;
 527                }
 528        }
 529
 530        pctl->num_functions = num;
 531        pctl->functions = funcs;
 532
 533        for (n = 0; n < pctl->num_groups; n++) {
 534                struct mvebu_pinctrl_group *grp = &pctl->groups[n];
 535                for (s = 0; s < grp->num_settings; s++) {
 536                        struct mvebu_pinctrl_function *f;
 537                        const char **groups;
 538
 539                        /* skip unsupported settings on this variant */
 540                        if (pctl->variant &&
 541                            !(pctl->variant & grp->settings[s].variant))
 542                                continue;
 543
 544                        f = mvebu_pinctrl_find_function_by_name(pctl,
 545                                                        grp->settings[s].name);
 546
 547                        /* allocate group name array if not done already */
 548                        if (!f->groups) {
 549                                f->groups = devm_kcalloc(&pdev->dev,
 550                                                 f->num_groups,
 551                                                 sizeof(char *),
 552                                                 GFP_KERNEL);
 553                                if (!f->groups)
 554                                        return -ENOMEM;
 555                        }
 556
 557                        /* find next free group name and assign current name */
 558                        groups = f->groups;
 559                        while (*groups)
 560                                groups++;
 561                        *groups = grp->name;
 562                }
 563        }
 564
 565        return 0;
 566}
 567
 568int mvebu_pinctrl_probe(struct platform_device *pdev)
 569{
 570        struct mvebu_pinctrl_soc_info *soc = dev_get_platdata(&pdev->dev);
 571        struct mvebu_pinctrl *pctl;
 572        struct pinctrl_pin_desc *pdesc;
 573        unsigned gid, n, k;
 574        unsigned size, noname = 0;
 575        char *noname_buf;
 576        void *p;
 577        int ret;
 578
 579        if (!soc || !soc->controls || !soc->modes) {
 580                dev_err(&pdev->dev, "wrong pinctrl soc info\n");
 581                return -EINVAL;
 582        }
 583
 584        pctl = devm_kzalloc(&pdev->dev, sizeof(struct mvebu_pinctrl),
 585                        GFP_KERNEL);
 586        if (!pctl)
 587                return -ENOMEM;
 588
 589        pctl->desc.name = dev_name(&pdev->dev);
 590        pctl->desc.owner = THIS_MODULE;
 591        pctl->desc.pctlops = &mvebu_pinctrl_ops;
 592        pctl->desc.pmxops = &mvebu_pinmux_ops;
 593        pctl->desc.confops = &mvebu_pinconf_ops;
 594        pctl->variant = soc->variant;
 595        pctl->dev = &pdev->dev;
 596        platform_set_drvdata(pdev, pctl);
 597
 598        /* count controls and create names for mvebu generic
 599           register controls; also does sanity checks */
 600        pctl->num_groups = 0;
 601        pctl->desc.npins = 0;
 602        for (n = 0; n < soc->ncontrols; n++) {
 603                const struct mvebu_mpp_ctrl *ctrl = &soc->controls[n];
 604
 605                pctl->desc.npins += ctrl->npins;
 606                /* initialize control's pins[] array */
 607                for (k = 0; k < ctrl->npins; k++)
 608                        ctrl->pins[k] = ctrl->pid + k;
 609
 610                /*
 611                 * We allow to pass controls with NULL name that we treat
 612                 * as a range of one-pin groups with generic mvebu register
 613                 * controls.
 614                 */
 615                if (!ctrl->name) {
 616                        pctl->num_groups += ctrl->npins;
 617                        noname += ctrl->npins;
 618                } else {
 619                        pctl->num_groups += 1;
 620                }
 621        }
 622
 623        pdesc = devm_kcalloc(&pdev->dev,
 624                             pctl->desc.npins,
 625                             sizeof(struct pinctrl_pin_desc),
 626                             GFP_KERNEL);
 627        if (!pdesc)
 628                return -ENOMEM;
 629
 630        for (n = 0; n < pctl->desc.npins; n++)
 631                pdesc[n].number = n;
 632        pctl->desc.pins = pdesc;
 633
 634        /*
 635         * allocate groups and name buffers for unnamed groups.
 636         */
 637        size = pctl->num_groups * sizeof(*pctl->groups) + noname * 8;
 638        p = devm_kzalloc(&pdev->dev, size, GFP_KERNEL);
 639        if (!p)
 640                return -ENOMEM;
 641
 642        pctl->groups = p;
 643        noname_buf = p + pctl->num_groups * sizeof(*pctl->groups);
 644
 645        /* assign mpp controls to groups */
 646        gid = 0;
 647        for (n = 0; n < soc->ncontrols; n++) {
 648                const struct mvebu_mpp_ctrl *ctrl = &soc->controls[n];
 649                struct mvebu_mpp_ctrl_data *data = soc->control_data ?
 650                                                   &soc->control_data[n] : NULL;
 651
 652                pctl->groups[gid].gid = gid;
 653                pctl->groups[gid].ctrl = ctrl;
 654                pctl->groups[gid].data = data;
 655                pctl->groups[gid].name = ctrl->name;
 656                pctl->groups[gid].pins = ctrl->pins;
 657                pctl->groups[gid].npins = ctrl->npins;
 658
 659                /*
 660                 * We treat unnamed controls as a range of one-pin groups
 661                 * with generic mvebu register controls. Use one group for
 662                 * each in this range and assign a default group name.
 663                 */
 664                if (!ctrl->name) {
 665                        pctl->groups[gid].name = noname_buf;
 666                        pctl->groups[gid].npins = 1;
 667                        sprintf(noname_buf, "mpp%d", ctrl->pid+0);
 668                        noname_buf += 8;
 669
 670                        for (k = 1; k < ctrl->npins; k++) {
 671                                gid++;
 672                                pctl->groups[gid].gid = gid;
 673                                pctl->groups[gid].ctrl = ctrl;
 674                                pctl->groups[gid].data = data;
 675                                pctl->groups[gid].name = noname_buf;
 676                                pctl->groups[gid].pins = &ctrl->pins[k];
 677                                pctl->groups[gid].npins = 1;
 678                                sprintf(noname_buf, "mpp%d", ctrl->pid+k);
 679                                noname_buf += 8;
 680                        }
 681                }
 682                gid++;
 683        }
 684
 685        /* assign mpp modes to groups */
 686        for (n = 0; n < soc->nmodes; n++) {
 687                struct mvebu_mpp_mode *mode = &soc->modes[n];
 688                struct mvebu_mpp_ctrl_setting *set = &mode->settings[0];
 689                struct mvebu_pinctrl_group *grp;
 690                unsigned num_settings;
 691                unsigned supp_settings;
 692
 693                for (num_settings = 0, supp_settings = 0; ; set++) {
 694                        if (!set->name)
 695                                break;
 696
 697                        num_settings++;
 698
 699                        /* skip unsupported settings for this variant */
 700                        if (pctl->variant && !(pctl->variant & set->variant))
 701                                continue;
 702
 703                        supp_settings++;
 704
 705                        /* find gpio/gpo/gpi settings */
 706                        if (strcmp(set->name, "gpio") == 0)
 707                                set->flags = MVEBU_SETTING_GPI |
 708                                        MVEBU_SETTING_GPO;
 709                        else if (strcmp(set->name, "gpo") == 0)
 710                                set->flags = MVEBU_SETTING_GPO;
 711                        else if (strcmp(set->name, "gpi") == 0)
 712                                set->flags = MVEBU_SETTING_GPI;
 713                }
 714
 715                /* skip modes with no settings for this variant */
 716                if (!supp_settings)
 717                        continue;
 718
 719                grp = mvebu_pinctrl_find_group_by_pid(pctl, mode->pid);
 720                if (!grp) {
 721                        dev_warn(&pdev->dev, "unknown pinctrl group %d\n",
 722                                mode->pid);
 723                        continue;
 724                }
 725
 726                grp->settings = mode->settings;
 727                grp->num_settings = num_settings;
 728        }
 729
 730        ret = mvebu_pinctrl_build_functions(pdev, pctl);
 731        if (ret) {
 732                dev_err(&pdev->dev, "unable to build functions\n");
 733                return ret;
 734        }
 735
 736        pctl->pctldev = devm_pinctrl_register(&pdev->dev, &pctl->desc, pctl);
 737        if (IS_ERR(pctl->pctldev)) {
 738                dev_err(&pdev->dev, "unable to register pinctrl driver\n");
 739                return PTR_ERR(pctl->pctldev);
 740        }
 741
 742        dev_info(&pdev->dev, "registered pinctrl driver\n");
 743
 744        /* register gpio ranges */
 745        for (n = 0; n < soc->ngpioranges; n++)
 746                pinctrl_add_gpio_range(pctl->pctldev, &soc->gpioranges[n]);
 747
 748        return 0;
 749}
 750
 751/*
 752 * mvebu_pinctrl_simple_mmio_probe - probe a simple mmio pinctrl
 753 * @pdev: platform device (with platform data already attached)
 754 *
 755 * Initialise a simple (single base address) mmio pinctrl driver,
 756 * assigning the MMIO base address to all mvebu mpp ctrl instances.
 757 */
 758int mvebu_pinctrl_simple_mmio_probe(struct platform_device *pdev)
 759{
 760        struct mvebu_pinctrl_soc_info *soc = dev_get_platdata(&pdev->dev);
 761        struct mvebu_mpp_ctrl_data *mpp_data;
 762        struct resource *res;
 763        void __iomem *base;
 764        int i;
 765
 766        res = platform_get_resource(pdev, IORESOURCE_MEM, 0);
 767        base = devm_ioremap_resource(&pdev->dev, res);
 768        if (IS_ERR(base))
 769                return PTR_ERR(base);
 770
 771        mpp_data = devm_kcalloc(&pdev->dev, soc->ncontrols, sizeof(*mpp_data),
 772                                GFP_KERNEL);
 773        if (!mpp_data)
 774                return -ENOMEM;
 775
 776        for (i = 0; i < soc->ncontrols; i++)
 777                mpp_data[i].base = base;
 778
 779        soc->control_data = mpp_data;
 780
 781        return mvebu_pinctrl_probe(pdev);
 782}
 783
 784int mvebu_regmap_mpp_ctrl_get(struct mvebu_mpp_ctrl_data *data,
 785                              unsigned int pid, unsigned long *config)
 786{
 787        unsigned off = (pid / MVEBU_MPPS_PER_REG) * MVEBU_MPP_BITS;
 788        unsigned shift = (pid % MVEBU_MPPS_PER_REG) * MVEBU_MPP_BITS;
 789        unsigned int val;
 790        int err;
 791
 792        err = regmap_read(data->regmap.map, data->regmap.offset + off, &val);
 793        if (err)
 794                return err;
 795
 796        *config = (val >> shift) & MVEBU_MPP_MASK;
 797
 798        return 0;
 799}
 800
 801int mvebu_regmap_mpp_ctrl_set(struct mvebu_mpp_ctrl_data *data,
 802                              unsigned int pid, unsigned long config)
 803{
 804        unsigned off = (pid / MVEBU_MPPS_PER_REG) * MVEBU_MPP_BITS;
 805        unsigned shift = (pid % MVEBU_MPPS_PER_REG) * MVEBU_MPP_BITS;
 806
 807        return regmap_update_bits(data->regmap.map, data->regmap.offset + off,
 808                                  MVEBU_MPP_MASK << shift, config << shift);
 809}
 810
 811int mvebu_pinctrl_simple_regmap_probe(struct platform_device *pdev,
 812                                      struct device *syscon_dev, u32 offset)
 813{
 814        struct mvebu_pinctrl_soc_info *soc = dev_get_platdata(&pdev->dev);
 815        struct mvebu_mpp_ctrl_data *mpp_data;
 816        struct regmap *regmap;
 817        int i;
 818
 819        regmap = syscon_node_to_regmap(syscon_dev->of_node);
 820        if (IS_ERR(regmap))
 821                return PTR_ERR(regmap);
 822
 823        mpp_data = devm_kcalloc(&pdev->dev, soc->ncontrols, sizeof(*mpp_data),
 824                                GFP_KERNEL);
 825        if (!mpp_data)
 826                return -ENOMEM;
 827
 828        for (i = 0; i < soc->ncontrols; i++) {
 829                mpp_data[i].regmap.map = regmap;
 830                mpp_data[i].regmap.offset = offset;
 831        }
 832
 833        soc->control_data = mpp_data;
 834
 835        return mvebu_pinctrl_probe(pdev);
 836}
 837