linux/drivers/net/ethernet/freescale/fman/fman_keygen.c
<<
>>
Prefs
   1/*
   2 * Copyright 2017 NXP
   3 *
   4 * Redistribution and use in source and binary forms, with or without
   5 * modification, are permitted provided that the following conditions are met:
   6 *     * Redistributions of source code must retain the above copyright
   7 *       notice, this list of conditions and the following disclaimer.
   8 *     * Redistributions in binary form must reproduce the above copyright
   9 *       notice, this list of conditions and the following disclaimer in the
  10 *       documentation and/or other materials provided with the distribution.
  11 *     * Neither the name of NXP nor the
  12 *       names of its contributors may be used to endorse or promote products
  13 *       derived from this software without specific prior written permission.
  14 *
  15 *
  16 * ALTERNATIVELY, this software may be distributed under the terms of the
  17 * GNU General Public License ("GPL") as published by the Free Software
  18 * Foundation, either version 2 of that License or (at your option) any
  19 * later version.
  20 *
  21 * THIS SOFTWARE IS PROVIDED BY NXP ``AS IS'' AND ANY
  22 * EXPRESS OR IMPLIED WARRANTIES, INCLUDING, BUT NOT LIMITED TO, THE IMPLIED
  23 * WARRANTIES OF MERCHANTABILITY AND FITNESS FOR A PARTICULAR PURPOSE ARE
  24 * DISCLAIMED. IN NO EVENT SHALL NXP BE LIABLE FOR ANY
  25 * DIRECT, INDIRECT, INCIDENTAL, SPECIAL, EXEMPLARY, OR CONSEQUENTIAL DAMAGES
  26 * (INCLUDING, BUT NOT LIMITED TO, PROCUREMENT OF SUBSTITUTE GOODS OR SERVICES;
  27 * LOSS OF USE, DATA, OR PROFITS; OR BUSINESS INTERRUPTION) HOWEVER CAUSED AND
  28 * ON ANY THEORY OF LIABILITY, WHETHER IN CONTRACT, STRICT LIABILITY, OR TORT
  29 * (INCLUDING NEGLIGENCE OR OTHERWISE) ARISING IN ANY WAY OUT OF THE USE OF THIS
  30 * SOFTWARE, EVEN IF ADVISED OF THE POSSIBILITY OF SUCH DAMAGE.
  31 */
  32
  33#define pr_fmt(fmt) KBUILD_MODNAME ": " fmt
  34
  35#include <linux/slab.h>
  36
  37#include "fman_keygen.h"
  38
  39/* Maximum number of HW Ports */
  40#define FMAN_MAX_NUM_OF_HW_PORTS                64
  41
  42/* Maximum number of KeyGen Schemes */
  43#define FM_KG_MAX_NUM_OF_SCHEMES                32
  44
  45/* Number of generic KeyGen Generic Extract Command Registers */
  46#define FM_KG_NUM_OF_GENERIC_REGS               8
  47
  48/* Dummy port ID */
  49#define DUMMY_PORT_ID                           0
  50
  51/* Select Scheme Value Register */
  52#define KG_SCH_DEF_USE_KGSE_DV_0                2
  53#define KG_SCH_DEF_USE_KGSE_DV_1                3
  54
  55/* Registers Shifting values */
  56#define FM_KG_KGAR_NUM_SHIFT                    16
  57#define KG_SCH_DEF_L4_PORT_SHIFT                8
  58#define KG_SCH_DEF_IP_ADDR_SHIFT                18
  59#define KG_SCH_HASH_CONFIG_SHIFT_SHIFT          24
  60
  61/* KeyGen Registers bit field masks: */
  62
  63/* Enable bit field mask for KeyGen General Configuration Register */
  64#define FM_KG_KGGCR_EN                          0x80000000
  65
  66/* KeyGen Global Registers bit field masks */
  67#define FM_KG_KGAR_GO                           0x80000000
  68#define FM_KG_KGAR_READ                         0x40000000
  69#define FM_KG_KGAR_WRITE                        0x00000000
  70#define FM_KG_KGAR_SEL_SCHEME_ENTRY             0x00000000
  71#define FM_KG_KGAR_SCM_WSEL_UPDATE_CNT          0x00008000
  72
  73#define FM_KG_KGAR_ERR                          0x20000000
  74#define FM_KG_KGAR_SEL_CLS_PLAN_ENTRY           0x01000000
  75#define FM_KG_KGAR_SEL_PORT_ENTRY               0x02000000
  76#define FM_KG_KGAR_SEL_PORT_WSEL_SP             0x00008000
  77#define FM_KG_KGAR_SEL_PORT_WSEL_CPP            0x00004000
  78
  79/* Error events exceptions */
  80#define FM_EX_KG_DOUBLE_ECC                     0x80000000
  81#define FM_EX_KG_KEYSIZE_OVERFLOW               0x40000000
  82
  83/* Scheme Registers bit field masks */
  84#define KG_SCH_MODE_EN                          0x80000000
  85#define KG_SCH_VSP_NO_KSP_EN                    0x80000000
  86#define KG_SCH_HASH_CONFIG_SYM                  0x40000000
  87
  88/* Known Protocol field codes */
  89#define KG_SCH_KN_PORT_ID               0x80000000
  90#define KG_SCH_KN_MACDST                0x40000000
  91#define KG_SCH_KN_MACSRC                0x20000000
  92#define KG_SCH_KN_TCI1                  0x10000000
  93#define KG_SCH_KN_TCI2                  0x08000000
  94#define KG_SCH_KN_ETYPE                 0x04000000
  95#define KG_SCH_KN_PPPSID                0x02000000
  96#define KG_SCH_KN_PPPID                 0x01000000
  97#define KG_SCH_KN_MPLS1                 0x00800000
  98#define KG_SCH_KN_MPLS2                 0x00400000
  99#define KG_SCH_KN_MPLS_LAST             0x00200000
 100#define KG_SCH_KN_IPSRC1                0x00100000
 101#define KG_SCH_KN_IPDST1                0x00080000
 102#define KG_SCH_KN_PTYPE1                0x00040000
 103#define KG_SCH_KN_IPTOS_TC1             0x00020000
 104#define KG_SCH_KN_IPV6FL1               0x00010000
 105#define KG_SCH_KN_IPSRC2                0x00008000
 106#define KG_SCH_KN_IPDST2                0x00004000
 107#define KG_SCH_KN_PTYPE2                0x00002000
 108#define KG_SCH_KN_IPTOS_TC2             0x00001000
 109#define KG_SCH_KN_IPV6FL2               0x00000800
 110#define KG_SCH_KN_GREPTYPE              0x00000400
 111#define KG_SCH_KN_IPSEC_SPI             0x00000200
 112#define KG_SCH_KN_IPSEC_NH              0x00000100
 113#define KG_SCH_KN_IPPID                 0x00000080
 114#define KG_SCH_KN_L4PSRC                0x00000004
 115#define KG_SCH_KN_L4PDST                0x00000002
 116#define KG_SCH_KN_TFLG                  0x00000001
 117
 118/* NIA values */
 119#define NIA_ENG_BMI                     0x00500000
 120#define NIA_BMI_AC_ENQ_FRAME            0x00000002
 121#define ENQUEUE_KG_DFLT_NIA             (NIA_ENG_BMI | NIA_BMI_AC_ENQ_FRAME)
 122
 123/* Hard-coded configuration:
 124 * These values are used as hard-coded values for KeyGen configuration
 125 * and they replace user selections for this hard-coded version
 126 */
 127
 128/* Hash distribution shift */
 129#define DEFAULT_HASH_DIST_FQID_SHIFT            0
 130
 131/* Hash shift */
 132#define DEFAULT_HASH_SHIFT                      0
 133
 134/* Symmetric hash usage:
 135 * Warning:
 136 * - the value for symmetric hash usage must be in accordance with hash
 137 *      key defined below
 138 * - according to tests performed, spreading is not working if symmetric
 139 *      hash is set on true
 140 * So ultimately symmetric hash functionality should be always disabled:
 141 */
 142#define DEFAULT_SYMMETRIC_HASH                  false
 143
 144/* Hash Key extraction fields: */
 145#define DEFAULT_HASH_KEY_EXTRACT_FIELDS         \
 146        (KG_SCH_KN_IPSRC1 | KG_SCH_KN_IPDST1 | \
 147         KG_SCH_KN_L4PSRC | KG_SCH_KN_L4PDST | \
 148         KG_SCH_KN_IPSEC_SPI)
 149
 150/* Default values to be used as hash key in case IPv4 or L4 (TCP, UDP)
 151 * don't exist in the frame
 152 */
 153/* Default IPv4 address */
 154#define DEFAULT_HASH_KEY_IPv4_ADDR              0x0A0A0A0A
 155/* Default L4 port */
 156#define DEFAULT_HASH_KEY_L4_PORT                0x0B0B0B0B
 157
 158/* KeyGen Memory Mapped Registers: */
 159
 160/* Scheme Configuration RAM Registers */
 161struct fman_kg_scheme_regs {
 162        u32 kgse_mode;          /* 0x100: MODE */
 163        u32 kgse_ekfc;          /* 0x104: Extract Known Fields Command */
 164        u32 kgse_ekdv;          /* 0x108: Extract Known Default Value */
 165        u32 kgse_bmch;          /* 0x10C: Bit Mask Command High */
 166        u32 kgse_bmcl;          /* 0x110: Bit Mask Command Low */
 167        u32 kgse_fqb;           /* 0x114: Frame Queue Base */
 168        u32 kgse_hc;            /* 0x118: Hash Command */
 169        u32 kgse_ppc;           /* 0x11C: Policer Profile Command */
 170        u32 kgse_gec[FM_KG_NUM_OF_GENERIC_REGS];
 171                        /* 0x120: Generic Extract Command */
 172        u32 kgse_spc;
 173                /* 0x140: KeyGen Scheme Entry Statistic Packet Counter */
 174        u32 kgse_dv0;   /* 0x144: KeyGen Scheme Entry Default Value 0 */
 175        u32 kgse_dv1;   /* 0x148: KeyGen Scheme Entry Default Value 1 */
 176        u32 kgse_ccbs;
 177                /* 0x14C: KeyGen Scheme Entry Coarse Classification Bit*/
 178        u32 kgse_mv;    /* 0x150: KeyGen Scheme Entry Match vector */
 179        u32 kgse_om;    /* 0x154: KeyGen Scheme Entry Operation Mode bits */
 180        u32 kgse_vsp;
 181                /* 0x158: KeyGen Scheme Entry Virtual Storage Profile */
 182};
 183
 184/* Port Partition Configuration Registers */
 185struct fman_kg_pe_regs {
 186        u32 fmkg_pe_sp;         /* 0x100: KeyGen Port entry Scheme Partition */
 187        u32 fmkg_pe_cpp;
 188                /* 0x104: KeyGen Port Entry Classification Plan Partition */
 189};
 190
 191/* General Configuration and Status Registers
 192 * Global Statistic Counters
 193 * KeyGen Global Registers
 194 */
 195struct fman_kg_regs {
 196        u32 fmkg_gcr;   /* 0x000: KeyGen General Configuration Register */
 197        u32 res004;     /* 0x004: Reserved */
 198        u32 res008;     /* 0x008: Reserved */
 199        u32 fmkg_eer;   /* 0x00C: KeyGen Error Event Register */
 200        u32 fmkg_eeer;  /* 0x010: KeyGen Error Event Enable Register */
 201        u32 res014;     /* 0x014: Reserved */
 202        u32 res018;     /* 0x018: Reserved */
 203        u32 fmkg_seer;  /* 0x01C: KeyGen Scheme Error Event Register */
 204        u32 fmkg_seeer; /* 0x020: KeyGen Scheme Error Event Enable Register */
 205        u32 fmkg_gsr;   /* 0x024: KeyGen Global Status Register */
 206        u32 fmkg_tpc;   /* 0x028: Total Packet Counter Register */
 207        u32 fmkg_serc;  /* 0x02C: Soft Error Capture Register */
 208        u32 res030[4];  /* 0x030: Reserved */
 209        u32 fmkg_fdor;  /* 0x034: Frame Data Offset Register */
 210        u32 fmkg_gdv0r; /* 0x038: Global Default Value Register 0 */
 211        u32 fmkg_gdv1r; /* 0x03C: Global Default Value Register 1 */
 212        u32 res04c[6];  /* 0x040: Reserved */
 213        u32 fmkg_feer;  /* 0x044: Force Error Event Register */
 214        u32 res068[38]; /* 0x048: Reserved */
 215        union {
 216                u32 fmkg_indirect[63];  /* 0x100: Indirect Access Registers */
 217                struct fman_kg_scheme_regs fmkg_sch; /* Scheme Registers */
 218                struct fman_kg_pe_regs fmkg_pe; /* Port Partition Registers */
 219        };
 220        u32 fmkg_ar;    /* 0x1FC: KeyGen Action Register */
 221};
 222
 223/* KeyGen Scheme data */
 224struct keygen_scheme {
 225        bool used;      /* Specifies if this scheme is used */
 226        u8 hw_port_id;
 227                /* Hardware port ID
 228                 * schemes sharing between multiple ports is not
 229                 * currently supported
 230                 * so we have only one port id bound to a scheme
 231                 */
 232        u32 base_fqid;
 233                /* Base FQID:
 234                 * Must be between 1 and 2^24-1
 235                 * If hash is used and an even distribution is
 236                 * expected according to hash_fqid_count,
 237                 * base_fqid must be aligned to hash_fqid_count
 238                 */
 239        u32 hash_fqid_count;
 240                /* FQ range for hash distribution:
 241                 * Must be a power of 2
 242                 * Represents the range of queues for spreading
 243                 */
 244        bool use_hashing;       /* Usage of Hashing and spreading over FQ */
 245        bool symmetric_hash;    /* Symmetric Hash option usage */
 246        u8 hashShift;
 247                /* Hash result right shift.
 248                 * Select the 24 bits out of the 64 hash result.
 249                 * 0 means using the 24 LSB's, otherwise
 250                 * use the 24 LSB's after shifting right
 251                 */
 252        u32 match_vector;       /* Match Vector */
 253};
 254
 255/* KeyGen driver data */
 256struct fman_keygen {
 257        struct keygen_scheme schemes[FM_KG_MAX_NUM_OF_SCHEMES];
 258                                /* Array of schemes */
 259        struct fman_kg_regs __iomem *keygen_regs;       /* KeyGen registers */
 260};
 261
 262/* keygen_write_ar_wait
 263 *
 264 * Write Action Register with specified value, wait for GO bit field to be
 265 * idle and then read the error
 266 *
 267 * regs: KeyGen registers
 268 * fmkg_ar: Action Register value
 269 *
 270 * Return: Zero for success or error code in case of failure
 271 */
 272static int keygen_write_ar_wait(struct fman_kg_regs __iomem *regs, u32 fmkg_ar)
 273{
 274        iowrite32be(fmkg_ar, &regs->fmkg_ar);
 275
 276        /* Wait for GO bit field to be idle */
 277        while (fmkg_ar & FM_KG_KGAR_GO)
 278                fmkg_ar = ioread32be(&regs->fmkg_ar);
 279
 280        if (fmkg_ar & FM_KG_KGAR_ERR)
 281                return -EINVAL;
 282
 283        return 0;
 284}
 285
 286/* build_ar_scheme
 287 *
 288 * Build Action Register value for scheme settings
 289 *
 290 * scheme_id: Scheme ID
 291 * update_counter: update scheme counter
 292 * write: true for action to write the scheme or false for read action
 293 *
 294 * Return: AR value
 295 */
 296static u32 build_ar_scheme(u8 scheme_id, bool update_counter, bool write)
 297{
 298        u32 rw = (u32)(write ? FM_KG_KGAR_WRITE : FM_KG_KGAR_READ);
 299
 300        return (u32)(FM_KG_KGAR_GO |
 301                        rw |
 302                        FM_KG_KGAR_SEL_SCHEME_ENTRY |
 303                        DUMMY_PORT_ID |
 304                        ((u32)scheme_id << FM_KG_KGAR_NUM_SHIFT) |
 305                        (update_counter ? FM_KG_KGAR_SCM_WSEL_UPDATE_CNT : 0));
 306}
 307
 308/* build_ar_bind_scheme
 309 *
 310 * Build Action Register value for port binding to schemes
 311 *
 312 * hwport_id: HW Port ID
 313 * write: true for action to write the bind or false for read action
 314 *
 315 * Return: AR value
 316 */
 317static u32 build_ar_bind_scheme(u8 hwport_id, bool write)
 318{
 319        u32 rw = write ? (u32)FM_KG_KGAR_WRITE : (u32)FM_KG_KGAR_READ;
 320
 321        return (u32)(FM_KG_KGAR_GO |
 322                        rw |
 323                        FM_KG_KGAR_SEL_PORT_ENTRY |
 324                        hwport_id |
 325                        FM_KG_KGAR_SEL_PORT_WSEL_SP);
 326}
 327
 328/* keygen_write_sp
 329 *
 330 * Write Scheme Partition Register with specified value
 331 *
 332 * regs: KeyGen Registers
 333 * sp: Scheme Partition register value
 334 * add: true to add a scheme partition or false to clear
 335 *
 336 * Return: none
 337 */
 338static void keygen_write_sp(struct fman_kg_regs __iomem *regs, u32 sp, bool add)
 339{
 340        u32 tmp;
 341
 342        tmp = ioread32be(&regs->fmkg_pe.fmkg_pe_sp);
 343
 344        if (add)
 345                tmp |= sp;
 346        else
 347                tmp &= ~sp;
 348
 349        iowrite32be(tmp, &regs->fmkg_pe.fmkg_pe_sp);
 350}
 351
 352/* build_ar_bind_cls_plan
 353 *
 354 * Build Action Register value for Classification Plan
 355 *
 356 * hwport_id: HW Port ID
 357 * write: true for action to write the CP or false for read action
 358 *
 359 * Return: AR value
 360 */
 361static u32 build_ar_bind_cls_plan(u8 hwport_id, bool write)
 362{
 363        u32 rw = write ? (u32)FM_KG_KGAR_WRITE : (u32)FM_KG_KGAR_READ;
 364
 365        return (u32)(FM_KG_KGAR_GO |
 366                        rw |
 367                        FM_KG_KGAR_SEL_PORT_ENTRY |
 368                        hwport_id |
 369                        FM_KG_KGAR_SEL_PORT_WSEL_CPP);
 370}
 371
 372/* keygen_write_cpp
 373 *
 374 * Write Classification Plan Partition Register with specified value
 375 *
 376 * regs: KeyGen Registers
 377 * cpp: CPP register value
 378 *
 379 * Return: none
 380 */
 381static void keygen_write_cpp(struct fman_kg_regs __iomem *regs, u32 cpp)
 382{
 383        iowrite32be(cpp, &regs->fmkg_pe.fmkg_pe_cpp);
 384}
 385
 386/* keygen_write_scheme
 387 *
 388 * Write all Schemes Registers with specified values
 389 *
 390 * regs: KeyGen Registers
 391 * scheme_id: Scheme ID
 392 * scheme_regs: Scheme registers values desired to be written
 393 * update_counter: update scheme counter
 394 *
 395 * Return: Zero for success or error code in case of failure
 396 */
 397static int keygen_write_scheme(struct fman_kg_regs __iomem *regs, u8 scheme_id,
 398                               struct fman_kg_scheme_regs *scheme_regs,
 399                                bool update_counter)
 400{
 401        u32 ar_reg;
 402        int err, i;
 403
 404        /* Write indirect scheme registers */
 405        iowrite32be(scheme_regs->kgse_mode, &regs->fmkg_sch.kgse_mode);
 406        iowrite32be(scheme_regs->kgse_ekfc, &regs->fmkg_sch.kgse_ekfc);
 407        iowrite32be(scheme_regs->kgse_ekdv, &regs->fmkg_sch.kgse_ekdv);
 408        iowrite32be(scheme_regs->kgse_bmch, &regs->fmkg_sch.kgse_bmch);
 409        iowrite32be(scheme_regs->kgse_bmcl, &regs->fmkg_sch.kgse_bmcl);
 410        iowrite32be(scheme_regs->kgse_fqb, &regs->fmkg_sch.kgse_fqb);
 411        iowrite32be(scheme_regs->kgse_hc, &regs->fmkg_sch.kgse_hc);
 412        iowrite32be(scheme_regs->kgse_ppc, &regs->fmkg_sch.kgse_ppc);
 413        iowrite32be(scheme_regs->kgse_spc, &regs->fmkg_sch.kgse_spc);
 414        iowrite32be(scheme_regs->kgse_dv0, &regs->fmkg_sch.kgse_dv0);
 415        iowrite32be(scheme_regs->kgse_dv1, &regs->fmkg_sch.kgse_dv1);
 416        iowrite32be(scheme_regs->kgse_ccbs, &regs->fmkg_sch.kgse_ccbs);
 417        iowrite32be(scheme_regs->kgse_mv, &regs->fmkg_sch.kgse_mv);
 418        iowrite32be(scheme_regs->kgse_om, &regs->fmkg_sch.kgse_om);
 419        iowrite32be(scheme_regs->kgse_vsp, &regs->fmkg_sch.kgse_vsp);
 420
 421        for (i = 0 ; i < FM_KG_NUM_OF_GENERIC_REGS ; i++)
 422                iowrite32be(scheme_regs->kgse_gec[i],
 423                            &regs->fmkg_sch.kgse_gec[i]);
 424
 425        /* Write AR (Action register) */
 426        ar_reg = build_ar_scheme(scheme_id, update_counter, true);
 427        err = keygen_write_ar_wait(regs, ar_reg);
 428        if (err != 0) {
 429                pr_err("Writing Action Register failed\n");
 430                return err;
 431        }
 432
 433        return err;
 434}
 435
 436/* get_free_scheme_id
 437 *
 438 * Find the first free scheme available to be used
 439 *
 440 * keygen: KeyGen handle
 441 * scheme_id: pointer to scheme id
 442 *
 443 * Return: 0 on success, -EINVAL when the are no available free schemes
 444 */
 445static int get_free_scheme_id(struct fman_keygen *keygen, u8 *scheme_id)
 446{
 447        u8 i;
 448
 449        for (i = 0; i < FM_KG_MAX_NUM_OF_SCHEMES; i++)
 450                if (!keygen->schemes[i].used) {
 451                        *scheme_id = i;
 452                        return 0;
 453                }
 454
 455        return -EINVAL;
 456}
 457
 458/* get_scheme
 459 *
 460 * Provides the scheme for specified ID
 461 *
 462 * keygen: KeyGen handle
 463 * scheme_id: Scheme ID
 464 *
 465 * Return: handle to required scheme
 466 */
 467static struct keygen_scheme *get_scheme(struct fman_keygen *keygen,
 468                                        u8 scheme_id)
 469{
 470        if (scheme_id >= FM_KG_MAX_NUM_OF_SCHEMES)
 471                return NULL;
 472        return &keygen->schemes[scheme_id];
 473}
 474
 475/* keygen_bind_port_to_schemes
 476 *
 477 * Bind the port to schemes
 478 *
 479 * keygen: KeyGen handle
 480 * scheme_id: id of the scheme to bind to
 481 * bind: true to bind the port or false to unbind it
 482 *
 483 * Return: Zero for success or error code in case of failure
 484 */
 485static int keygen_bind_port_to_schemes(struct fman_keygen *keygen,
 486                                       u8 scheme_id,
 487                                        bool bind)
 488{
 489        struct fman_kg_regs __iomem *keygen_regs = keygen->keygen_regs;
 490        struct keygen_scheme *scheme;
 491        u32 ar_reg;
 492        u32 schemes_vector = 0;
 493        int err;
 494
 495        scheme = get_scheme(keygen, scheme_id);
 496        if (!scheme) {
 497                pr_err("Requested Scheme does not exist\n");
 498                return -EINVAL;
 499        }
 500        if (!scheme->used) {
 501                pr_err("Cannot bind port to an invalid scheme\n");
 502                return -EINVAL;
 503        }
 504
 505        schemes_vector |= 1 << (31 - scheme_id);
 506
 507        ar_reg = build_ar_bind_scheme(scheme->hw_port_id, false);
 508        err = keygen_write_ar_wait(keygen_regs, ar_reg);
 509        if (err != 0) {
 510                pr_err("Reading Action Register failed\n");
 511                return err;
 512        }
 513
 514        keygen_write_sp(keygen_regs, schemes_vector, bind);
 515
 516        ar_reg = build_ar_bind_scheme(scheme->hw_port_id, true);
 517        err = keygen_write_ar_wait(keygen_regs, ar_reg);
 518        if (err != 0) {
 519                pr_err("Writing Action Register failed\n");
 520                return err;
 521        }
 522
 523        return 0;
 524}
 525
 526/* keygen_scheme_setup
 527 *
 528 * Setup the scheme according to required configuration
 529 *
 530 * keygen: KeyGen handle
 531 * scheme_id: scheme ID
 532 * enable: true to enable scheme or false to disable it
 533 *
 534 * Return: Zero for success or error code in case of failure
 535 */
 536static int keygen_scheme_setup(struct fman_keygen *keygen, u8 scheme_id,
 537                               bool enable)
 538{
 539        struct fman_kg_regs __iomem *keygen_regs = keygen->keygen_regs;
 540        struct fman_kg_scheme_regs scheme_regs;
 541        struct keygen_scheme *scheme;
 542        u32 tmp_reg;
 543        int err;
 544
 545        scheme = get_scheme(keygen, scheme_id);
 546        if (!scheme) {
 547                pr_err("Requested Scheme does not exist\n");
 548                return -EINVAL;
 549        }
 550        if (enable && scheme->used) {
 551                pr_err("The requested Scheme is already used\n");
 552                return -EINVAL;
 553        }
 554
 555        /* Clear scheme registers */
 556        memset(&scheme_regs, 0, sizeof(struct fman_kg_scheme_regs));
 557
 558        /* Setup all scheme registers: */
 559        tmp_reg = 0;
 560
 561        if (enable) {
 562                /* Enable Scheme */
 563                tmp_reg |= KG_SCH_MODE_EN;
 564                /* Enqueue frame NIA */
 565                tmp_reg |= ENQUEUE_KG_DFLT_NIA;
 566        }
 567
 568        scheme_regs.kgse_mode = tmp_reg;
 569
 570        scheme_regs.kgse_mv = scheme->match_vector;
 571
 572        /* Scheme don't override StorageProfile:
 573         * valid only for DPAA_VERSION >= 11
 574         */
 575        scheme_regs.kgse_vsp = KG_SCH_VSP_NO_KSP_EN;
 576
 577        /* Configure Hard-Coded Rx Hashing: */
 578
 579        if (scheme->use_hashing) {
 580                /* configure kgse_ekfc */
 581                scheme_regs.kgse_ekfc = DEFAULT_HASH_KEY_EXTRACT_FIELDS;
 582
 583                /* configure kgse_ekdv */
 584                tmp_reg = 0;
 585                tmp_reg |= (KG_SCH_DEF_USE_KGSE_DV_0 <<
 586                                KG_SCH_DEF_IP_ADDR_SHIFT);
 587                tmp_reg |= (KG_SCH_DEF_USE_KGSE_DV_1 <<
 588                                KG_SCH_DEF_L4_PORT_SHIFT);
 589                scheme_regs.kgse_ekdv = tmp_reg;
 590
 591                /* configure kgse_dv0 */
 592                scheme_regs.kgse_dv0 = DEFAULT_HASH_KEY_IPv4_ADDR;
 593                /* configure kgse_dv1 */
 594                scheme_regs.kgse_dv1 = DEFAULT_HASH_KEY_L4_PORT;
 595
 596                /* configure kgse_hc  */
 597                tmp_reg = 0;
 598                tmp_reg |= ((scheme->hash_fqid_count - 1) <<
 599                                DEFAULT_HASH_DIST_FQID_SHIFT);
 600                tmp_reg |= scheme->hashShift << KG_SCH_HASH_CONFIG_SHIFT_SHIFT;
 601
 602                if (scheme->symmetric_hash) {
 603                        /* Normally extraction key should be verified if
 604                         * complies with symmetric hash
 605                         * But because extraction is hard-coded, we are sure
 606                         * the key is symmetric
 607                         */
 608                        tmp_reg |= KG_SCH_HASH_CONFIG_SYM;
 609                }
 610                scheme_regs.kgse_hc = tmp_reg;
 611        } else {
 612                scheme_regs.kgse_ekfc = 0;
 613                scheme_regs.kgse_hc = 0;
 614                scheme_regs.kgse_ekdv = 0;
 615                scheme_regs.kgse_dv0 = 0;
 616                scheme_regs.kgse_dv1 = 0;
 617        }
 618
 619        /* configure kgse_fqb: Scheme FQID base */
 620        tmp_reg = 0;
 621        tmp_reg |= scheme->base_fqid;
 622        scheme_regs.kgse_fqb = tmp_reg;
 623
 624        /* features not used by hard-coded configuration */
 625        scheme_regs.kgse_bmch = 0;
 626        scheme_regs.kgse_bmcl = 0;
 627        scheme_regs.kgse_spc = 0;
 628
 629        /* Write scheme registers */
 630        err = keygen_write_scheme(keygen_regs, scheme_id, &scheme_regs, true);
 631        if (err != 0) {
 632                pr_err("Writing scheme registers failed\n");
 633                return err;
 634        }
 635
 636        /* Update used field for Scheme */
 637        scheme->used = enable;
 638
 639        return 0;
 640}
 641
 642/* keygen_init
 643 *
 644 * KeyGen initialization:
 645 * Initializes and enables KeyGen, allocate driver memory, setup registers,
 646 * clear port bindings, invalidate all schemes
 647 *
 648 * keygen_regs: KeyGen registers base address
 649 *
 650 * Return: Handle to KeyGen driver
 651 */
 652struct fman_keygen *keygen_init(struct fman_kg_regs __iomem *keygen_regs)
 653{
 654        struct fman_keygen *keygen;
 655        u32 ar;
 656        int i;
 657
 658        /* Allocate memory for KeyGen driver */
 659        keygen = kzalloc(sizeof(*keygen), GFP_KERNEL);
 660        if (!keygen)
 661                return NULL;
 662
 663        keygen->keygen_regs = keygen_regs;
 664
 665        /* KeyGen initialization (for Master partition):
 666         * Setup KeyGen registers
 667         */
 668        iowrite32be(ENQUEUE_KG_DFLT_NIA, &keygen_regs->fmkg_gcr);
 669
 670        iowrite32be(FM_EX_KG_DOUBLE_ECC | FM_EX_KG_KEYSIZE_OVERFLOW,
 671                    &keygen_regs->fmkg_eer);
 672
 673        iowrite32be(0, &keygen_regs->fmkg_fdor);
 674        iowrite32be(0, &keygen_regs->fmkg_gdv0r);
 675        iowrite32be(0, &keygen_regs->fmkg_gdv1r);
 676
 677        /* Clear binding between ports to schemes and classification plans
 678         * so that all ports are not bound to any scheme/classification plan
 679         */
 680        for (i = 0; i < FMAN_MAX_NUM_OF_HW_PORTS; i++) {
 681                /* Clear all pe sp schemes registers */
 682                keygen_write_sp(keygen_regs, 0xffffffff, false);
 683                ar = build_ar_bind_scheme(i, true);
 684                keygen_write_ar_wait(keygen_regs, ar);
 685
 686                /* Clear all pe cpp classification plans registers */
 687                keygen_write_cpp(keygen_regs, 0);
 688                ar = build_ar_bind_cls_plan(i, true);
 689                keygen_write_ar_wait(keygen_regs, ar);
 690        }
 691
 692        /* Enable all scheme interrupts */
 693        iowrite32be(0xFFFFFFFF, &keygen_regs->fmkg_seer);
 694        iowrite32be(0xFFFFFFFF, &keygen_regs->fmkg_seeer);
 695
 696        /* Enable KyeGen */
 697        iowrite32be(ioread32be(&keygen_regs->fmkg_gcr) | FM_KG_KGGCR_EN,
 698                    &keygen_regs->fmkg_gcr);
 699
 700        return keygen;
 701}
 702EXPORT_SYMBOL(keygen_init);
 703
 704/* keygen_port_hashing_init
 705 *
 706 * Initializes a port for Rx Hashing with specified configuration parameters
 707 *
 708 * keygen: KeyGen handle
 709 * hw_port_id: HW Port ID
 710 * hash_base_fqid: Hashing Base FQID used for spreading
 711 * hash_size: Hashing size
 712 *
 713 * Return: Zero for success or error code in case of failure
 714 */
 715int keygen_port_hashing_init(struct fman_keygen *keygen, u8 hw_port_id,
 716                             u32 hash_base_fqid, u32 hash_size)
 717{
 718        struct keygen_scheme *scheme;
 719        u8 scheme_id;
 720        int err;
 721
 722        /* Validate Scheme configuration parameters */
 723        if (hash_base_fqid == 0 || (hash_base_fqid & ~0x00FFFFFF)) {
 724                pr_err("Base FQID must be between 1 and 2^24-1\n");
 725                return -EINVAL;
 726        }
 727        if (hash_size == 0 || (hash_size & (hash_size - 1)) != 0) {
 728                pr_err("Hash size must be power of two\n");
 729                return -EINVAL;
 730        }
 731
 732        /* Find a free scheme */
 733        err = get_free_scheme_id(keygen, &scheme_id);
 734        if (err) {
 735                pr_err("The maximum number of available Schemes has been exceeded\n");
 736                return -EINVAL;
 737        }
 738
 739        /* Create and configure Hard-Coded Scheme: */
 740
 741        scheme = get_scheme(keygen, scheme_id);
 742        if (!scheme) {
 743                pr_err("Requested Scheme does not exist\n");
 744                return -EINVAL;
 745        }
 746        if (scheme->used) {
 747                pr_err("The requested Scheme is already used\n");
 748                return -EINVAL;
 749        }
 750
 751        /* Clear all scheme fields because the scheme may have been
 752         * previously used
 753         */
 754        memset(scheme, 0, sizeof(struct keygen_scheme));
 755
 756        /* Setup scheme: */
 757        scheme->hw_port_id = hw_port_id;
 758        scheme->use_hashing = true;
 759        scheme->base_fqid = hash_base_fqid;
 760        scheme->hash_fqid_count = hash_size;
 761        scheme->symmetric_hash = DEFAULT_SYMMETRIC_HASH;
 762        scheme->hashShift = DEFAULT_HASH_SHIFT;
 763
 764        /* All Schemes in hard-coded configuration
 765         * are Indirect Schemes
 766         */
 767        scheme->match_vector = 0;
 768
 769        err = keygen_scheme_setup(keygen, scheme_id, true);
 770        if (err != 0) {
 771                pr_err("Scheme setup failed\n");
 772                return err;
 773        }
 774
 775        /* Bind Rx port to Scheme */
 776        err = keygen_bind_port_to_schemes(keygen, scheme_id, true);
 777        if (err != 0) {
 778                pr_err("Binding port to schemes failed\n");
 779                return err;
 780        }
 781
 782        return 0;
 783}
 784EXPORT_SYMBOL(keygen_port_hashing_init);
 785