1 /* 2 * Marvell 88E6xxx Switch Port Registers support 3 * 4 * Copyright (c) 2008 Marvell Semiconductor 5 * 6 * Copyright (c) 2016-2017 Savoir-faire Linux Inc. 7 * Vivien Didelot <vivien.didelot@savoirfairelinux.com> 8 * 9 * This program is free software; you can redistribute it and/or modify 10 * it under the terms of the GNU General Public License as published by 11 * the Free Software Foundation; either version 2 of the License, or 12 * (at your option) any later version. 13 */ 14 15 #include <linux/bitfield.h> 16 #include <linux/if_bridge.h> 17 #include <linux/phy.h> 18 #include <linux/phylink.h> 19 20 #include "chip.h" 21 #include "port.h" 22 #include "serdes.h" 23 24 int mv88e6xxx_port_read(struct mv88e6xxx_chip *chip, int port, int reg, 25 u16 *val) 26 { 27 int addr = chip->info->port_base_addr + port; 28 29 return mv88e6xxx_read(chip, addr, reg, val); 30 } 31 32 int mv88e6xxx_port_write(struct mv88e6xxx_chip *chip, int port, int reg, 33 u16 val) 34 { 35 int addr = chip->info->port_base_addr + port; 36 37 return mv88e6xxx_write(chip, addr, reg, val); 38 } 39 40 /* Offset 0x00: MAC (or PCS or Physical) Status Register 41 * 42 * For most devices, this is read only. However the 6185 has the MyPause 43 * bit read/write. 44 */ 45 int mv88e6185_port_set_pause(struct mv88e6xxx_chip *chip, int port, 46 int pause) 47 { 48 u16 reg; 49 int err; 50 51 err = mv88e6xxx_port_read(chip, port, MV88E6XXX_PORT_STS, ®); 52 if (err) 53 return err; 54 55 if (pause) 56 reg |= MV88E6XXX_PORT_STS_MY_PAUSE; 57 else 58 reg &= ~MV88E6XXX_PORT_STS_MY_PAUSE; 59 60 return mv88e6xxx_port_write(chip, port, MV88E6XXX_PORT_STS, reg); 61 } 62 63 /* Offset 0x01: MAC (or PCS or Physical) Control Register 64 * 65 * Link, Duplex and Flow Control have one force bit, one value bit. 66 * 67 * For port's MAC speed, ForceSpd (or SpdValue) bits 1:0 program the value. 68 * Alternative values require the 200BASE (or AltSpeed) bit 12 set. 69 * Newer chips need a ForcedSpd bit 13 set to consider the value. 70 */ 71 72 static int mv88e6xxx_port_set_rgmii_delay(struct mv88e6xxx_chip *chip, int port, 73 phy_interface_t mode) 74 { 75 u16 reg; 76 int err; 77 78 err = mv88e6xxx_port_read(chip, port, MV88E6XXX_PORT_MAC_CTL, ®); 79 if (err) 80 return err; 81 82 reg &= ~(MV88E6XXX_PORT_MAC_CTL_RGMII_DELAY_RXCLK | 83 MV88E6XXX_PORT_MAC_CTL_RGMII_DELAY_TXCLK); 84 85 switch (mode) { 86 case PHY_INTERFACE_MODE_RGMII_RXID: 87 reg |= MV88E6XXX_PORT_MAC_CTL_RGMII_DELAY_RXCLK; 88 break; 89 case PHY_INTERFACE_MODE_RGMII_TXID: 90 reg |= MV88E6XXX_PORT_MAC_CTL_RGMII_DELAY_TXCLK; 91 break; 92 case PHY_INTERFACE_MODE_RGMII_ID: 93 reg |= MV88E6XXX_PORT_MAC_CTL_RGMII_DELAY_RXCLK | 94 MV88E6XXX_PORT_MAC_CTL_RGMII_DELAY_TXCLK; 95 break; 96 case PHY_INTERFACE_MODE_RGMII: 97 break; 98 default: 99 return 0; 100 } 101 102 err = mv88e6xxx_port_write(chip, port, MV88E6XXX_PORT_MAC_CTL, reg); 103 if (err) 104 return err; 105 106 dev_dbg(chip->dev, "p%d: delay RXCLK %s, TXCLK %s\n", port, 107 reg & MV88E6XXX_PORT_MAC_CTL_RGMII_DELAY_RXCLK ? "yes" : "no", 108 reg & MV88E6XXX_PORT_MAC_CTL_RGMII_DELAY_TXCLK ? "yes" : "no"); 109 110 return 0; 111 } 112 113 int mv88e6352_port_set_rgmii_delay(struct mv88e6xxx_chip *chip, int port, 114 phy_interface_t mode) 115 { 116 if (port < 5) 117 return -EOPNOTSUPP; 118 119 return mv88e6xxx_port_set_rgmii_delay(chip, port, mode); 120 } 121 122 int mv88e6390_port_set_rgmii_delay(struct mv88e6xxx_chip *chip, int port, 123 phy_interface_t mode) 124 { 125 if (port != 0) 126 return -EOPNOTSUPP; 127 128 return mv88e6xxx_port_set_rgmii_delay(chip, port, mode); 129 } 130 131 int mv88e6xxx_port_set_link(struct mv88e6xxx_chip *chip, int port, int link) 132 { 133 u16 reg; 134 int err; 135 136 err = mv88e6xxx_port_read(chip, port, MV88E6XXX_PORT_MAC_CTL, ®); 137 if (err) 138 return err; 139 140 reg &= ~(MV88E6XXX_PORT_MAC_CTL_FORCE_LINK | 141 MV88E6XXX_PORT_MAC_CTL_LINK_UP); 142 143 switch (link) { 144 case LINK_FORCED_DOWN: 145 reg |= MV88E6XXX_PORT_MAC_CTL_FORCE_LINK; 146 break; 147 case LINK_FORCED_UP: 148 reg |= MV88E6XXX_PORT_MAC_CTL_FORCE_LINK | 149 MV88E6XXX_PORT_MAC_CTL_LINK_UP; 150 break; 151 case LINK_UNFORCED: 152 /* normal link detection */ 153 break; 154 default: 155 return -EINVAL; 156 } 157 158 err = mv88e6xxx_port_write(chip, port, MV88E6XXX_PORT_MAC_CTL, reg); 159 if (err) 160 return err; 161 162 dev_dbg(chip->dev, "p%d: %s link %s\n", port, 163 reg & MV88E6XXX_PORT_MAC_CTL_FORCE_LINK ? "Force" : "Unforce", 164 reg & MV88E6XXX_PORT_MAC_CTL_LINK_UP ? "up" : "down"); 165 166 return 0; 167 } 168 169 int mv88e6xxx_port_set_duplex(struct mv88e6xxx_chip *chip, int port, int dup) 170 { 171 u16 reg; 172 int err; 173 174 err = mv88e6xxx_port_read(chip, port, MV88E6XXX_PORT_MAC_CTL, ®); 175 if (err) 176 return err; 177 178 reg &= ~(MV88E6XXX_PORT_MAC_CTL_FORCE_DUPLEX | 179 MV88E6XXX_PORT_MAC_CTL_DUPLEX_FULL); 180 181 switch (dup) { 182 case DUPLEX_HALF: 183 reg |= MV88E6XXX_PORT_MAC_CTL_FORCE_DUPLEX; 184 break; 185 case DUPLEX_FULL: 186 reg |= MV88E6XXX_PORT_MAC_CTL_FORCE_DUPLEX | 187 MV88E6XXX_PORT_MAC_CTL_DUPLEX_FULL; 188 break; 189 case DUPLEX_UNFORCED: 190 /* normal duplex detection */ 191 break; 192 default: 193 return -EINVAL; 194 } 195 196 err = mv88e6xxx_port_write(chip, port, MV88E6XXX_PORT_MAC_CTL, reg); 197 if (err) 198 return err; 199 200 dev_dbg(chip->dev, "p%d: %s %s duplex\n", port, 201 reg & MV88E6XXX_PORT_MAC_CTL_FORCE_DUPLEX ? "Force" : "Unforce", 202 reg & MV88E6XXX_PORT_MAC_CTL_DUPLEX_FULL ? "full" : "half"); 203 204 return 0; 205 } 206 207 static int mv88e6xxx_port_set_speed(struct mv88e6xxx_chip *chip, int port, 208 int speed, bool alt_bit, bool force_bit) 209 { 210 u16 reg, ctrl; 211 int err; 212 213 switch (speed) { 214 case 10: 215 ctrl = MV88E6XXX_PORT_MAC_CTL_SPEED_10; 216 break; 217 case 100: 218 ctrl = MV88E6XXX_PORT_MAC_CTL_SPEED_100; 219 break; 220 case 200: 221 if (alt_bit) 222 ctrl = MV88E6XXX_PORT_MAC_CTL_SPEED_100 | 223 MV88E6390_PORT_MAC_CTL_ALTSPEED; 224 else 225 ctrl = MV88E6065_PORT_MAC_CTL_SPEED_200; 226 break; 227 case 1000: 228 ctrl = MV88E6XXX_PORT_MAC_CTL_SPEED_1000; 229 break; 230 case 2500: 231 if (alt_bit) 232 ctrl = MV88E6390_PORT_MAC_CTL_SPEED_10000 | 233 MV88E6390_PORT_MAC_CTL_ALTSPEED; 234 else 235 ctrl = MV88E6390_PORT_MAC_CTL_SPEED_10000; 236 break; 237 case 10000: 238 /* all bits set, fall through... */ 239 case SPEED_UNFORCED: 240 ctrl = MV88E6XXX_PORT_MAC_CTL_SPEED_UNFORCED; 241 break; 242 default: 243 return -EOPNOTSUPP; 244 } 245 246 err = mv88e6xxx_port_read(chip, port, MV88E6XXX_PORT_MAC_CTL, ®); 247 if (err) 248 return err; 249 250 reg &= ~MV88E6XXX_PORT_MAC_CTL_SPEED_MASK; 251 if (alt_bit) 252 reg &= ~MV88E6390_PORT_MAC_CTL_ALTSPEED; 253 if (force_bit) { 254 reg &= ~MV88E6390_PORT_MAC_CTL_FORCE_SPEED; 255 if (speed != SPEED_UNFORCED) 256 ctrl |= MV88E6390_PORT_MAC_CTL_FORCE_SPEED; 257 } 258 reg |= ctrl; 259 260 err = mv88e6xxx_port_write(chip, port, MV88E6XXX_PORT_MAC_CTL, reg); 261 if (err) 262 return err; 263 264 if (speed) 265 dev_dbg(chip->dev, "p%d: Speed set to %d Mbps\n", port, speed); 266 else 267 dev_dbg(chip->dev, "p%d: Speed unforced\n", port); 268 269 return 0; 270 } 271 272 /* Support 10, 100, 200 Mbps (e.g. 88E6065 family) */ 273 int mv88e6065_port_set_speed(struct mv88e6xxx_chip *chip, int port, int speed) 274 { 275 if (speed == SPEED_MAX) 276 speed = 200; 277 278 if (speed > 200) 279 return -EOPNOTSUPP; 280 281 /* Setting 200 Mbps on port 0 to 3 selects 100 Mbps */ 282 return mv88e6xxx_port_set_speed(chip, port, speed, false, false); 283 } 284 285 /* Support 10, 100, 1000 Mbps (e.g. 88E6185 family) */ 286 int mv88e6185_port_set_speed(struct mv88e6xxx_chip *chip, int port, int speed) 287 { 288 if (speed == SPEED_MAX) 289 speed = 1000; 290 291 if (speed == 200 || speed > 1000) 292 return -EOPNOTSUPP; 293 294 return mv88e6xxx_port_set_speed(chip, port, speed, false, false); 295 } 296 297 /* Support 10, 100, 200, 1000, 2500 Mbps (e.g. 88E6341) */ 298 int mv88e6341_port_set_speed(struct mv88e6xxx_chip *chip, int port, int speed) 299 { 300 if (speed == SPEED_MAX) 301 speed = port < 5 ? 1000 : 2500; 302 303 if (speed > 2500) 304 return -EOPNOTSUPP; 305 306 if (speed == 200 && port != 0) 307 return -EOPNOTSUPP; 308 309 if (speed == 2500 && port < 5) 310 return -EOPNOTSUPP; 311 312 return mv88e6xxx_port_set_speed(chip, port, speed, !port, true); 313 } 314 315 /* Support 10, 100, 200, 1000 Mbps (e.g. 88E6352 family) */ 316 int mv88e6352_port_set_speed(struct mv88e6xxx_chip *chip, int port, int speed) 317 { 318 if (speed == SPEED_MAX) 319 speed = 1000; 320 321 if (speed > 1000) 322 return -EOPNOTSUPP; 323 324 if (speed == 200 && port < 5) 325 return -EOPNOTSUPP; 326 327 return mv88e6xxx_port_set_speed(chip, port, speed, true, false); 328 } 329 330 /* Support 10, 100, 200, 1000, 2500 Mbps (e.g. 88E6390) */ 331 int mv88e6390_port_set_speed(struct mv88e6xxx_chip *chip, int port, int speed) 332 { 333 if (speed == SPEED_MAX) 334 speed = port < 9 ? 1000 : 2500; 335 336 if (speed > 2500) 337 return -EOPNOTSUPP; 338 339 if (speed == 200 && port != 0) 340 return -EOPNOTSUPP; 341 342 if (speed == 2500 && port < 9) 343 return -EOPNOTSUPP; 344 345 return mv88e6xxx_port_set_speed(chip, port, speed, true, true); 346 } 347 348 /* Support 10, 100, 200, 1000, 2500, 10000 Mbps (e.g. 88E6190X) */ 349 int mv88e6390x_port_set_speed(struct mv88e6xxx_chip *chip, int port, int speed) 350 { 351 if (speed == SPEED_MAX) 352 speed = port < 9 ? 1000 : 10000; 353 354 if (speed == 200 && port != 0) 355 return -EOPNOTSUPP; 356 357 if (speed >= 2500 && port < 9) 358 return -EOPNOTSUPP; 359 360 return mv88e6xxx_port_set_speed(chip, port, speed, true, true); 361 } 362 363 int mv88e6390x_port_set_cmode(struct mv88e6xxx_chip *chip, int port, 364 phy_interface_t mode) 365 { 366 int lane; 367 u16 cmode; 368 u16 reg; 369 int err; 370 371 if (mode == PHY_INTERFACE_MODE_NA) 372 return 0; 373 374 if (port != 9 && port != 10) 375 return -EOPNOTSUPP; 376 377 switch (mode) { 378 case PHY_INTERFACE_MODE_1000BASEX: 379 cmode = MV88E6XXX_PORT_STS_CMODE_1000BASE_X; 380 break; 381 case PHY_INTERFACE_MODE_SGMII: 382 cmode = MV88E6XXX_PORT_STS_CMODE_SGMII; 383 break; 384 case PHY_INTERFACE_MODE_2500BASEX: 385 cmode = MV88E6XXX_PORT_STS_CMODE_2500BASEX; 386 break; 387 case PHY_INTERFACE_MODE_XGMII: 388 case PHY_INTERFACE_MODE_XAUI: 389 cmode = MV88E6XXX_PORT_STS_CMODE_XAUI; 390 break; 391 case PHY_INTERFACE_MODE_RXAUI: 392 cmode = MV88E6XXX_PORT_STS_CMODE_RXAUI; 393 break; 394 default: 395 cmode = 0; 396 } 397 398 lane = mv88e6390x_serdes_get_lane(chip, port); 399 if (lane < 0) 400 return lane; 401 402 if (chip->ports[port].serdes_irq) { 403 err = mv88e6390_serdes_irq_disable(chip, port, lane); 404 if (err) 405 return err; 406 } 407 408 err = mv88e6390_serdes_power(chip, port, false); 409 if (err) 410 return err; 411 412 if (cmode) { 413 err = mv88e6xxx_port_read(chip, port, MV88E6XXX_PORT_STS, ®); 414 if (err) 415 return err; 416 417 reg &= ~MV88E6XXX_PORT_STS_CMODE_MASK; 418 reg |= cmode; 419 420 err = mv88e6xxx_port_write(chip, port, MV88E6XXX_PORT_STS, reg); 421 if (err) 422 return err; 423 424 err = mv88e6390_serdes_power(chip, port, true); 425 if (err) 426 return err; 427 428 if (chip->ports[port].serdes_irq) { 429 err = mv88e6390_serdes_irq_enable(chip, port, lane); 430 if (err) 431 return err; 432 } 433 } 434 435 chip->ports[port].cmode = cmode; 436 437 return 0; 438 } 439 440 int mv88e6185_port_get_cmode(struct mv88e6xxx_chip *chip, int port, u8 *cmode) 441 { 442 int err; 443 u16 reg; 444 445 err = mv88e6xxx_port_read(chip, port, MV88E6XXX_PORT_STS, ®); 446 if (err) 447 return err; 448 449 *cmode = reg & MV88E6185_PORT_STS_CMODE_MASK; 450 451 return 0; 452 } 453 454 int mv88e6352_port_get_cmode(struct mv88e6xxx_chip *chip, int port, u8 *cmode) 455 { 456 int err; 457 u16 reg; 458 459 err = mv88e6xxx_port_read(chip, port, MV88E6XXX_PORT_STS, ®); 460 if (err) 461 return err; 462 463 *cmode = reg & MV88E6XXX_PORT_STS_CMODE_MASK; 464 465 return 0; 466 } 467 468 int mv88e6352_port_link_state(struct mv88e6xxx_chip *chip, int port, 469 struct phylink_link_state *state) 470 { 471 int err; 472 u16 reg; 473 474 err = mv88e6xxx_port_read(chip, port, MV88E6XXX_PORT_STS, ®); 475 if (err) 476 return err; 477 478 switch (reg & MV88E6XXX_PORT_STS_SPEED_MASK) { 479 case MV88E6XXX_PORT_STS_SPEED_10: 480 state->speed = SPEED_10; 481 break; 482 case MV88E6XXX_PORT_STS_SPEED_100: 483 state->speed = SPEED_100; 484 break; 485 case MV88E6XXX_PORT_STS_SPEED_1000: 486 state->speed = SPEED_1000; 487 break; 488 case MV88E6XXX_PORT_STS_SPEED_10000: 489 if ((reg & MV88E6XXX_PORT_STS_CMODE_MASK) == 490 MV88E6XXX_PORT_STS_CMODE_2500BASEX) 491 state->speed = SPEED_2500; 492 else 493 state->speed = SPEED_10000; 494 break; 495 } 496 497 state->duplex = reg & MV88E6XXX_PORT_STS_DUPLEX ? 498 DUPLEX_FULL : DUPLEX_HALF; 499 state->link = !!(reg & MV88E6XXX_PORT_STS_LINK); 500 state->an_enabled = 1; 501 state->an_complete = state->link; 502 503 return 0; 504 } 505 506 int mv88e6185_port_link_state(struct mv88e6xxx_chip *chip, int port, 507 struct phylink_link_state *state) 508 { 509 if (state->interface == PHY_INTERFACE_MODE_1000BASEX) { 510 u8 cmode = chip->ports[port].cmode; 511 512 /* When a port is in "Cross-chip serdes" mode, it uses 513 * 1000Base-X full duplex mode, but there is no automatic 514 * link detection. Use the sync OK status for link (as it 515 * would do for 1000Base-X mode.) 516 */ 517 if (cmode == MV88E6185_PORT_STS_CMODE_SERDES) { 518 u16 mac; 519 int err; 520 521 err = mv88e6xxx_port_read(chip, port, 522 MV88E6XXX_PORT_MAC_CTL, &mac); 523 if (err) 524 return err; 525 526 state->link = !!(mac & MV88E6185_PORT_MAC_CTL_SYNC_OK); 527 state->an_enabled = 1; 528 state->an_complete = 529 !!(mac & MV88E6185_PORT_MAC_CTL_AN_DONE); 530 state->duplex = 531 state->link ? DUPLEX_FULL : DUPLEX_UNKNOWN; 532 state->speed = 533 state->link ? SPEED_1000 : SPEED_UNKNOWN; 534 535 return 0; 536 } 537 } 538 539 return mv88e6352_port_link_state(chip, port, state); 540 } 541 542 /* Offset 0x02: Jamming Control 543 * 544 * Do not limit the period of time that this port can be paused for by 545 * the remote end or the period of time that this port can pause the 546 * remote end. 547 */ 548 int mv88e6097_port_pause_limit(struct mv88e6xxx_chip *chip, int port, u8 in, 549 u8 out) 550 { 551 return mv88e6xxx_port_write(chip, port, MV88E6097_PORT_JAM_CTL, 552 out << 8 | in); 553 } 554 555 int mv88e6390_port_pause_limit(struct mv88e6xxx_chip *chip, int port, u8 in, 556 u8 out) 557 { 558 int err; 559 560 err = mv88e6xxx_port_write(chip, port, MV88E6390_PORT_FLOW_CTL, 561 MV88E6390_PORT_FLOW_CTL_UPDATE | 562 MV88E6390_PORT_FLOW_CTL_LIMIT_IN | in); 563 if (err) 564 return err; 565 566 return mv88e6xxx_port_write(chip, port, MV88E6390_PORT_FLOW_CTL, 567 MV88E6390_PORT_FLOW_CTL_UPDATE | 568 MV88E6390_PORT_FLOW_CTL_LIMIT_OUT | out); 569 } 570 571 /* Offset 0x04: Port Control Register */ 572 573 static const char * const mv88e6xxx_port_state_names[] = { 574 [MV88E6XXX_PORT_CTL0_STATE_DISABLED] = "Disabled", 575 [MV88E6XXX_PORT_CTL0_STATE_BLOCKING] = "Blocking/Listening", 576 [MV88E6XXX_PORT_CTL0_STATE_LEARNING] = "Learning", 577 [MV88E6XXX_PORT_CTL0_STATE_FORWARDING] = "Forwarding", 578 }; 579 580 int mv88e6xxx_port_set_state(struct mv88e6xxx_chip *chip, int port, u8 state) 581 { 582 u16 reg; 583 int err; 584 585 err = mv88e6xxx_port_read(chip, port, MV88E6XXX_PORT_CTL0, ®); 586 if (err) 587 return err; 588 589 reg &= ~MV88E6XXX_PORT_CTL0_STATE_MASK; 590 591 switch (state) { 592 case BR_STATE_DISABLED: 593 state = MV88E6XXX_PORT_CTL0_STATE_DISABLED; 594 break; 595 case BR_STATE_BLOCKING: 596 case BR_STATE_LISTENING: 597 state = MV88E6XXX_PORT_CTL0_STATE_BLOCKING; 598 break; 599 case BR_STATE_LEARNING: 600 state = MV88E6XXX_PORT_CTL0_STATE_LEARNING; 601 break; 602 case BR_STATE_FORWARDING: 603 state = MV88E6XXX_PORT_CTL0_STATE_FORWARDING; 604 break; 605 default: 606 return -EINVAL; 607 } 608 609 reg |= state; 610 611 err = mv88e6xxx_port_write(chip, port, MV88E6XXX_PORT_CTL0, reg); 612 if (err) 613 return err; 614 615 dev_dbg(chip->dev, "p%d: PortState set to %s\n", port, 616 mv88e6xxx_port_state_names[state]); 617 618 return 0; 619 } 620 621 int mv88e6xxx_port_set_egress_mode(struct mv88e6xxx_chip *chip, int port, 622 enum mv88e6xxx_egress_mode mode) 623 { 624 int err; 625 u16 reg; 626 627 err = mv88e6xxx_port_read(chip, port, MV88E6XXX_PORT_CTL0, ®); 628 if (err) 629 return err; 630 631 reg &= ~MV88E6XXX_PORT_CTL0_EGRESS_MODE_MASK; 632 633 switch (mode) { 634 case MV88E6XXX_EGRESS_MODE_UNMODIFIED: 635 reg |= MV88E6XXX_PORT_CTL0_EGRESS_MODE_UNMODIFIED; 636 break; 637 case MV88E6XXX_EGRESS_MODE_UNTAGGED: 638 reg |= MV88E6XXX_PORT_CTL0_EGRESS_MODE_UNTAGGED; 639 break; 640 case MV88E6XXX_EGRESS_MODE_TAGGED: 641 reg |= MV88E6XXX_PORT_CTL0_EGRESS_MODE_TAGGED; 642 break; 643 case MV88E6XXX_EGRESS_MODE_ETHERTYPE: 644 reg |= MV88E6XXX_PORT_CTL0_EGRESS_MODE_ETHER_TYPE_DSA; 645 break; 646 default: 647 return -EINVAL; 648 } 649 650 return mv88e6xxx_port_write(chip, port, MV88E6XXX_PORT_CTL0, reg); 651 } 652 653 int mv88e6085_port_set_frame_mode(struct mv88e6xxx_chip *chip, int port, 654 enum mv88e6xxx_frame_mode mode) 655 { 656 int err; 657 u16 reg; 658 659 err = mv88e6xxx_port_read(chip, port, MV88E6XXX_PORT_CTL0, ®); 660 if (err) 661 return err; 662 663 reg &= ~MV88E6XXX_PORT_CTL0_FRAME_MODE_MASK; 664 665 switch (mode) { 666 case MV88E6XXX_FRAME_MODE_NORMAL: 667 reg |= MV88E6XXX_PORT_CTL0_FRAME_MODE_NORMAL; 668 break; 669 case MV88E6XXX_FRAME_MODE_DSA: 670 reg |= MV88E6XXX_PORT_CTL0_FRAME_MODE_DSA; 671 break; 672 default: 673 return -EINVAL; 674 } 675 676 return mv88e6xxx_port_write(chip, port, MV88E6XXX_PORT_CTL0, reg); 677 } 678 679 int mv88e6351_port_set_frame_mode(struct mv88e6xxx_chip *chip, int port, 680 enum mv88e6xxx_frame_mode mode) 681 { 682 int err; 683 u16 reg; 684 685 err = mv88e6xxx_port_read(chip, port, MV88E6XXX_PORT_CTL0, ®); 686 if (err) 687 return err; 688 689 reg &= ~MV88E6XXX_PORT_CTL0_FRAME_MODE_MASK; 690 691 switch (mode) { 692 case MV88E6XXX_FRAME_MODE_NORMAL: 693 reg |= MV88E6XXX_PORT_CTL0_FRAME_MODE_NORMAL; 694 break; 695 case MV88E6XXX_FRAME_MODE_DSA: 696 reg |= MV88E6XXX_PORT_CTL0_FRAME_MODE_DSA; 697 break; 698 case MV88E6XXX_FRAME_MODE_PROVIDER: 699 reg |= MV88E6XXX_PORT_CTL0_FRAME_MODE_PROVIDER; 700 break; 701 case MV88E6XXX_FRAME_MODE_ETHERTYPE: 702 reg |= MV88E6XXX_PORT_CTL0_FRAME_MODE_ETHER_TYPE_DSA; 703 break; 704 default: 705 return -EINVAL; 706 } 707 708 return mv88e6xxx_port_write(chip, port, MV88E6XXX_PORT_CTL0, reg); 709 } 710 711 static int mv88e6185_port_set_forward_unknown(struct mv88e6xxx_chip *chip, 712 int port, bool unicast) 713 { 714 int err; 715 u16 reg; 716 717 err = mv88e6xxx_port_read(chip, port, MV88E6XXX_PORT_CTL0, ®); 718 if (err) 719 return err; 720 721 if (unicast) 722 reg |= MV88E6185_PORT_CTL0_FORWARD_UNKNOWN; 723 else 724 reg &= ~MV88E6185_PORT_CTL0_FORWARD_UNKNOWN; 725 726 return mv88e6xxx_port_write(chip, port, MV88E6XXX_PORT_CTL0, reg); 727 } 728 729 int mv88e6352_port_set_egress_floods(struct mv88e6xxx_chip *chip, int port, 730 bool unicast, bool multicast) 731 { 732 int err; 733 u16 reg; 734 735 err = mv88e6xxx_port_read(chip, port, MV88E6XXX_PORT_CTL0, ®); 736 if (err) 737 return err; 738 739 reg &= ~MV88E6352_PORT_CTL0_EGRESS_FLOODS_MASK; 740 741 if (unicast && multicast) 742 reg |= MV88E6352_PORT_CTL0_EGRESS_FLOODS_ALL_UNKNOWN_DA; 743 else if (unicast) 744 reg |= MV88E6352_PORT_CTL0_EGRESS_FLOODS_NO_UNKNOWN_MC_DA; 745 else if (multicast) 746 reg |= MV88E6352_PORT_CTL0_EGRESS_FLOODS_NO_UNKNOWN_UC_DA; 747 else 748 reg |= MV88E6352_PORT_CTL0_EGRESS_FLOODS_NO_UNKNOWN_DA; 749 750 return mv88e6xxx_port_write(chip, port, MV88E6XXX_PORT_CTL0, reg); 751 } 752 753 /* Offset 0x05: Port Control 1 */ 754 755 int mv88e6xxx_port_set_message_port(struct mv88e6xxx_chip *chip, int port, 756 bool message_port) 757 { 758 u16 val; 759 int err; 760 761 err = mv88e6xxx_port_read(chip, port, MV88E6XXX_PORT_CTL1, &val); 762 if (err) 763 return err; 764 765 if (message_port) 766 val |= MV88E6XXX_PORT_CTL1_MESSAGE_PORT; 767 else 768 val &= ~MV88E6XXX_PORT_CTL1_MESSAGE_PORT; 769 770 return mv88e6xxx_port_write(chip, port, MV88E6XXX_PORT_CTL1, val); 771 } 772 773 /* Offset 0x06: Port Based VLAN Map */ 774 775 int mv88e6xxx_port_set_vlan_map(struct mv88e6xxx_chip *chip, int port, u16 map) 776 { 777 const u16 mask = mv88e6xxx_port_mask(chip); 778 u16 reg; 779 int err; 780 781 err = mv88e6xxx_port_read(chip, port, MV88E6XXX_PORT_BASE_VLAN, ®); 782 if (err) 783 return err; 784 785 reg &= ~mask; 786 reg |= map & mask; 787 788 err = mv88e6xxx_port_write(chip, port, MV88E6XXX_PORT_BASE_VLAN, reg); 789 if (err) 790 return err; 791 792 dev_dbg(chip->dev, "p%d: VLANTable set to %.3x\n", port, map); 793 794 return 0; 795 } 796 797 int mv88e6xxx_port_get_fid(struct mv88e6xxx_chip *chip, int port, u16 *fid) 798 { 799 const u16 upper_mask = (mv88e6xxx_num_databases(chip) - 1) >> 4; 800 u16 reg; 801 int err; 802 803 /* Port's default FID lower 4 bits are located in reg 0x06, offset 12 */ 804 err = mv88e6xxx_port_read(chip, port, MV88E6XXX_PORT_BASE_VLAN, ®); 805 if (err) 806 return err; 807 808 *fid = (reg & 0xf000) >> 12; 809 810 /* Port's default FID upper bits are located in reg 0x05, offset 0 */ 811 if (upper_mask) { 812 err = mv88e6xxx_port_read(chip, port, MV88E6XXX_PORT_CTL1, 813 ®); 814 if (err) 815 return err; 816 817 *fid |= (reg & upper_mask) << 4; 818 } 819 820 return 0; 821 } 822 823 int mv88e6xxx_port_set_fid(struct mv88e6xxx_chip *chip, int port, u16 fid) 824 { 825 const u16 upper_mask = (mv88e6xxx_num_databases(chip) - 1) >> 4; 826 u16 reg; 827 int err; 828 829 if (fid >= mv88e6xxx_num_databases(chip)) 830 return -EINVAL; 831 832 /* Port's default FID lower 4 bits are located in reg 0x06, offset 12 */ 833 err = mv88e6xxx_port_read(chip, port, MV88E6XXX_PORT_BASE_VLAN, ®); 834 if (err) 835 return err; 836 837 reg &= 0x0fff; 838 reg |= (fid & 0x000f) << 12; 839 840 err = mv88e6xxx_port_write(chip, port, MV88E6XXX_PORT_BASE_VLAN, reg); 841 if (err) 842 return err; 843 844 /* Port's default FID upper bits are located in reg 0x05, offset 0 */ 845 if (upper_mask) { 846 err = mv88e6xxx_port_read(chip, port, MV88E6XXX_PORT_CTL1, 847 ®); 848 if (err) 849 return err; 850 851 reg &= ~upper_mask; 852 reg |= (fid >> 4) & upper_mask; 853 854 err = mv88e6xxx_port_write(chip, port, MV88E6XXX_PORT_CTL1, 855 reg); 856 if (err) 857 return err; 858 } 859 860 dev_dbg(chip->dev, "p%d: FID set to %u\n", port, fid); 861 862 return 0; 863 } 864 865 /* Offset 0x07: Default Port VLAN ID & Priority */ 866 867 int mv88e6xxx_port_get_pvid(struct mv88e6xxx_chip *chip, int port, u16 *pvid) 868 { 869 u16 reg; 870 int err; 871 872 err = mv88e6xxx_port_read(chip, port, MV88E6XXX_PORT_DEFAULT_VLAN, 873 ®); 874 if (err) 875 return err; 876 877 *pvid = reg & MV88E6XXX_PORT_DEFAULT_VLAN_MASK; 878 879 return 0; 880 } 881 882 int mv88e6xxx_port_set_pvid(struct mv88e6xxx_chip *chip, int port, u16 pvid) 883 { 884 u16 reg; 885 int err; 886 887 err = mv88e6xxx_port_read(chip, port, MV88E6XXX_PORT_DEFAULT_VLAN, 888 ®); 889 if (err) 890 return err; 891 892 reg &= ~MV88E6XXX_PORT_DEFAULT_VLAN_MASK; 893 reg |= pvid & MV88E6XXX_PORT_DEFAULT_VLAN_MASK; 894 895 err = mv88e6xxx_port_write(chip, port, MV88E6XXX_PORT_DEFAULT_VLAN, 896 reg); 897 if (err) 898 return err; 899 900 dev_dbg(chip->dev, "p%d: DefaultVID set to %u\n", port, pvid); 901 902 return 0; 903 } 904 905 /* Offset 0x08: Port Control 2 Register */ 906 907 static const char * const mv88e6xxx_port_8021q_mode_names[] = { 908 [MV88E6XXX_PORT_CTL2_8021Q_MODE_DISABLED] = "Disabled", 909 [MV88E6XXX_PORT_CTL2_8021Q_MODE_FALLBACK] = "Fallback", 910 [MV88E6XXX_PORT_CTL2_8021Q_MODE_CHECK] = "Check", 911 [MV88E6XXX_PORT_CTL2_8021Q_MODE_SECURE] = "Secure", 912 }; 913 914 static int mv88e6185_port_set_default_forward(struct mv88e6xxx_chip *chip, 915 int port, bool multicast) 916 { 917 int err; 918 u16 reg; 919 920 err = mv88e6xxx_port_read(chip, port, MV88E6XXX_PORT_CTL2, ®); 921 if (err) 922 return err; 923 924 if (multicast) 925 reg |= MV88E6XXX_PORT_CTL2_DEFAULT_FORWARD; 926 else 927 reg &= ~MV88E6XXX_PORT_CTL2_DEFAULT_FORWARD; 928 929 return mv88e6xxx_port_write(chip, port, MV88E6XXX_PORT_CTL2, reg); 930 } 931 932 int mv88e6185_port_set_egress_floods(struct mv88e6xxx_chip *chip, int port, 933 bool unicast, bool multicast) 934 { 935 int err; 936 937 err = mv88e6185_port_set_forward_unknown(chip, port, unicast); 938 if (err) 939 return err; 940 941 return mv88e6185_port_set_default_forward(chip, port, multicast); 942 } 943 944 int mv88e6095_port_set_upstream_port(struct mv88e6xxx_chip *chip, int port, 945 int upstream_port) 946 { 947 int err; 948 u16 reg; 949 950 err = mv88e6xxx_port_read(chip, port, MV88E6XXX_PORT_CTL2, ®); 951 if (err) 952 return err; 953 954 reg &= ~MV88E6095_PORT_CTL2_CPU_PORT_MASK; 955 reg |= upstream_port; 956 957 return mv88e6xxx_port_write(chip, port, MV88E6XXX_PORT_CTL2, reg); 958 } 959 960 int mv88e6xxx_port_set_8021q_mode(struct mv88e6xxx_chip *chip, int port, 961 u16 mode) 962 { 963 u16 reg; 964 int err; 965 966 err = mv88e6xxx_port_read(chip, port, MV88E6XXX_PORT_CTL2, ®); 967 if (err) 968 return err; 969 970 reg &= ~MV88E6XXX_PORT_CTL2_8021Q_MODE_MASK; 971 reg |= mode & MV88E6XXX_PORT_CTL2_8021Q_MODE_MASK; 972 973 err = mv88e6xxx_port_write(chip, port, MV88E6XXX_PORT_CTL2, reg); 974 if (err) 975 return err; 976 977 dev_dbg(chip->dev, "p%d: 802.1QMode set to %s\n", port, 978 mv88e6xxx_port_8021q_mode_names[mode]); 979 980 return 0; 981 } 982 983 int mv88e6xxx_port_set_map_da(struct mv88e6xxx_chip *chip, int port) 984 { 985 u16 reg; 986 int err; 987 988 err = mv88e6xxx_port_read(chip, port, MV88E6XXX_PORT_CTL2, ®); 989 if (err) 990 return err; 991 992 reg |= MV88E6XXX_PORT_CTL2_MAP_DA; 993 994 return mv88e6xxx_port_write(chip, port, MV88E6XXX_PORT_CTL2, reg); 995 } 996 997 int mv88e6165_port_set_jumbo_size(struct mv88e6xxx_chip *chip, int port, 998 size_t size) 999 { 1000 u16 reg; 1001 int err; 1002 1003 err = mv88e6xxx_port_read(chip, port, MV88E6XXX_PORT_CTL2, ®); 1004 if (err) 1005 return err; 1006 1007 reg &= ~MV88E6XXX_PORT_CTL2_JUMBO_MODE_MASK; 1008 1009 if (size <= 1522) 1010 reg |= MV88E6XXX_PORT_CTL2_JUMBO_MODE_1522; 1011 else if (size <= 2048) 1012 reg |= MV88E6XXX_PORT_CTL2_JUMBO_MODE_2048; 1013 else if (size <= 10240) 1014 reg |= MV88E6XXX_PORT_CTL2_JUMBO_MODE_10240; 1015 else 1016 return -ERANGE; 1017 1018 return mv88e6xxx_port_write(chip, port, MV88E6XXX_PORT_CTL2, reg); 1019 } 1020 1021 /* Offset 0x09: Port Rate Control */ 1022 1023 int mv88e6095_port_egress_rate_limiting(struct mv88e6xxx_chip *chip, int port) 1024 { 1025 return mv88e6xxx_port_write(chip, port, MV88E6XXX_PORT_EGRESS_RATE_CTL1, 1026 0x0000); 1027 } 1028 1029 int mv88e6097_port_egress_rate_limiting(struct mv88e6xxx_chip *chip, int port) 1030 { 1031 return mv88e6xxx_port_write(chip, port, MV88E6XXX_PORT_EGRESS_RATE_CTL1, 1032 0x0001); 1033 } 1034 1035 /* Offset 0x0C: Port ATU Control */ 1036 1037 int mv88e6xxx_port_disable_learn_limit(struct mv88e6xxx_chip *chip, int port) 1038 { 1039 return mv88e6xxx_port_write(chip, port, MV88E6XXX_PORT_ATU_CTL, 0); 1040 } 1041 1042 /* Offset 0x0D: (Priority) Override Register */ 1043 1044 int mv88e6xxx_port_disable_pri_override(struct mv88e6xxx_chip *chip, int port) 1045 { 1046 return mv88e6xxx_port_write(chip, port, MV88E6XXX_PORT_PRI_OVERRIDE, 0); 1047 } 1048 1049 /* Offset 0x0f: Port Ether type */ 1050 1051 int mv88e6351_port_set_ether_type(struct mv88e6xxx_chip *chip, int port, 1052 u16 etype) 1053 { 1054 return mv88e6xxx_port_write(chip, port, MV88E6XXX_PORT_ETH_TYPE, etype); 1055 } 1056 1057 /* Offset 0x18: Port IEEE Priority Remapping Registers [0-3] 1058 * Offset 0x19: Port IEEE Priority Remapping Registers [4-7] 1059 */ 1060 1061 int mv88e6095_port_tag_remap(struct mv88e6xxx_chip *chip, int port) 1062 { 1063 int err; 1064 1065 /* Use a direct priority mapping for all IEEE tagged frames */ 1066 err = mv88e6xxx_port_write(chip, port, 1067 MV88E6095_PORT_IEEE_PRIO_REMAP_0123, 1068 0x3210); 1069 if (err) 1070 return err; 1071 1072 return mv88e6xxx_port_write(chip, port, 1073 MV88E6095_PORT_IEEE_PRIO_REMAP_4567, 1074 0x7654); 1075 } 1076 1077 static int mv88e6xxx_port_ieeepmt_write(struct mv88e6xxx_chip *chip, 1078 int port, u16 table, u8 ptr, u16 data) 1079 { 1080 u16 reg; 1081 1082 reg = MV88E6390_PORT_IEEE_PRIO_MAP_TABLE_UPDATE | table | 1083 (ptr << __bf_shf(MV88E6390_PORT_IEEE_PRIO_MAP_TABLE_PTR_MASK)) | 1084 (data & MV88E6390_PORT_IEEE_PRIO_MAP_TABLE_DATA_MASK); 1085 1086 return mv88e6xxx_port_write(chip, port, 1087 MV88E6390_PORT_IEEE_PRIO_MAP_TABLE, reg); 1088 } 1089 1090 int mv88e6390_port_tag_remap(struct mv88e6xxx_chip *chip, int port) 1091 { 1092 int err, i; 1093 u16 table; 1094 1095 for (i = 0; i <= 7; i++) { 1096 table = MV88E6390_PORT_IEEE_PRIO_MAP_TABLE_INGRESS_PCP; 1097 err = mv88e6xxx_port_ieeepmt_write(chip, port, table, i, 1098 (i | i << 4)); 1099 if (err) 1100 return err; 1101 1102 table = MV88E6390_PORT_IEEE_PRIO_MAP_TABLE_EGRESS_GREEN_PCP; 1103 err = mv88e6xxx_port_ieeepmt_write(chip, port, table, i, i); 1104 if (err) 1105 return err; 1106 1107 table = MV88E6390_PORT_IEEE_PRIO_MAP_TABLE_EGRESS_YELLOW_PCP; 1108 err = mv88e6xxx_port_ieeepmt_write(chip, port, table, i, i); 1109 if (err) 1110 return err; 1111 1112 table = MV88E6390_PORT_IEEE_PRIO_MAP_TABLE_EGRESS_AVB_PCP; 1113 err = mv88e6xxx_port_ieeepmt_write(chip, port, table, i, i); 1114 if (err) 1115 return err; 1116 } 1117 1118 return 0; 1119 } 1120