1 // SPDX-License-Identifier: GPL-2.0 2 /* 3 * USB Type-C Connector Class 4 * 5 * Copyright (C) 2017, Intel Corporation 6 * Author: Heikki Krogerus <[email protected]> 7 */ 8 9 #include <linux/device.h> 10 #include <linux/module.h> 11 #include <linux/mutex.h> 12 #include <linux/slab.h> 13 #include <linux/usb/typec.h> 14 #include <linux/usb/typec_mux.h> 15 16 struct typec_mode { 17 int index; 18 u32 vdo; 19 char *desc; 20 enum typec_port_type roles; 21 22 struct typec_altmode *alt_mode; 23 24 unsigned int active:1; 25 26 char group_name[6]; 27 struct attribute_group group; 28 struct attribute *attrs[5]; 29 struct device_attribute vdo_attr; 30 struct device_attribute desc_attr; 31 struct device_attribute active_attr; 32 struct device_attribute roles_attr; 33 }; 34 35 struct typec_altmode { 36 struct device dev; 37 u16 svid; 38 int n_modes; 39 struct typec_mode modes[ALTMODE_MAX_MODES]; 40 const struct attribute_group *mode_groups[ALTMODE_MAX_MODES]; 41 }; 42 43 struct typec_plug { 44 struct device dev; 45 enum typec_plug_index index; 46 }; 47 48 struct typec_cable { 49 struct device dev; 50 enum typec_plug_type type; 51 struct usb_pd_identity *identity; 52 unsigned int active:1; 53 }; 54 55 struct typec_partner { 56 struct device dev; 57 unsigned int usb_pd:1; 58 struct usb_pd_identity *identity; 59 enum typec_accessory accessory; 60 }; 61 62 struct typec_port { 63 unsigned int id; 64 struct device dev; 65 66 int prefer_role; 67 enum typec_data_role data_role; 68 enum typec_role pwr_role; 69 enum typec_role vconn_role; 70 enum typec_pwr_opmode pwr_opmode; 71 enum typec_port_type port_type; 72 struct mutex port_type_lock; 73 74 enum typec_orientation orientation; 75 struct typec_switch *sw; 76 struct typec_mux *mux; 77 78 const struct typec_capability *cap; 79 }; 80 81 #define to_typec_port(_dev_) container_of(_dev_, struct typec_port, dev) 82 #define to_typec_plug(_dev_) container_of(_dev_, struct typec_plug, dev) 83 #define to_typec_cable(_dev_) container_of(_dev_, struct typec_cable, dev) 84 #define to_typec_partner(_dev_) container_of(_dev_, struct typec_partner, dev) 85 #define to_altmode(_dev_) container_of(_dev_, struct typec_altmode, dev) 86 87 static const struct device_type typec_partner_dev_type; 88 static const struct device_type typec_cable_dev_type; 89 static const struct device_type typec_plug_dev_type; 90 static const struct device_type typec_port_dev_type; 91 92 #define is_typec_partner(_dev_) (_dev_->type == &typec_partner_dev_type) 93 #define is_typec_cable(_dev_) (_dev_->type == &typec_cable_dev_type) 94 #define is_typec_plug(_dev_) (_dev_->type == &typec_plug_dev_type) 95 #define is_typec_port(_dev_) (_dev_->type == &typec_port_dev_type) 96 97 static DEFINE_IDA(typec_index_ida); 98 static struct class *typec_class; 99 100 /* ------------------------------------------------------------------------- */ 101 /* Common attributes */ 102 103 static const char * const typec_accessory_modes[] = { 104 [TYPEC_ACCESSORY_NONE] = "none", 105 [TYPEC_ACCESSORY_AUDIO] = "analog_audio", 106 [TYPEC_ACCESSORY_DEBUG] = "debug", 107 }; 108 109 static struct usb_pd_identity *get_pd_identity(struct device *dev) 110 { 111 if (is_typec_partner(dev)) { 112 struct typec_partner *partner = to_typec_partner(dev); 113 114 return partner->identity; 115 } else if (is_typec_cable(dev)) { 116 struct typec_cable *cable = to_typec_cable(dev); 117 118 return cable->identity; 119 } 120 return NULL; 121 } 122 123 static ssize_t id_header_show(struct device *dev, struct device_attribute *attr, 124 char *buf) 125 { 126 struct usb_pd_identity *id = get_pd_identity(dev); 127 128 return sprintf(buf, "0x%08x\n", id->id_header); 129 } 130 static DEVICE_ATTR_RO(id_header); 131 132 static ssize_t cert_stat_show(struct device *dev, struct device_attribute *attr, 133 char *buf) 134 { 135 struct usb_pd_identity *id = get_pd_identity(dev); 136 137 return sprintf(buf, "0x%08x\n", id->cert_stat); 138 } 139 static DEVICE_ATTR_RO(cert_stat); 140 141 static ssize_t product_show(struct device *dev, struct device_attribute *attr, 142 char *buf) 143 { 144 struct usb_pd_identity *id = get_pd_identity(dev); 145 146 return sprintf(buf, "0x%08x\n", id->product); 147 } 148 static DEVICE_ATTR_RO(product); 149 150 static struct attribute *usb_pd_id_attrs[] = { 151 &dev_attr_id_header.attr, 152 &dev_attr_cert_stat.attr, 153 &dev_attr_product.attr, 154 NULL 155 }; 156 157 static const struct attribute_group usb_pd_id_group = { 158 .name = "identity", 159 .attrs = usb_pd_id_attrs, 160 }; 161 162 static const struct attribute_group *usb_pd_id_groups[] = { 163 &usb_pd_id_group, 164 NULL, 165 }; 166 167 static void typec_report_identity(struct device *dev) 168 { 169 sysfs_notify(&dev->kobj, "identity", "id_header"); 170 sysfs_notify(&dev->kobj, "identity", "cert_stat"); 171 sysfs_notify(&dev->kobj, "identity", "product"); 172 } 173 174 /* ------------------------------------------------------------------------- */ 175 /* Alternate Modes */ 176 177 /** 178 * typec_altmode_update_active - Report Enter/Exit mode 179 * @alt: Handle to the alternate mode 180 * @mode: Mode index 181 * @active: True when the mode has been entered 182 * 183 * If a partner or cable plug executes Enter/Exit Mode command successfully, the 184 * drivers use this routine to report the updated state of the mode. 185 */ 186 void typec_altmode_update_active(struct typec_altmode *alt, int mode, 187 bool active) 188 { 189 struct typec_mode *m = &alt->modes[mode]; 190 char dir[6]; 191 192 if (m->active == active) 193 return; 194 195 m->active = active; 196 snprintf(dir, sizeof(dir), "mode%d", mode); 197 sysfs_notify(&alt->dev.kobj, dir, "active"); 198 kobject_uevent(&alt->dev.kobj, KOBJ_CHANGE); 199 } 200 EXPORT_SYMBOL_GPL(typec_altmode_update_active); 201 202 /** 203 * typec_altmode2port - Alternate Mode to USB Type-C port 204 * @alt: The Alternate Mode 205 * 206 * Returns handle to the port that a cable plug or partner with @alt is 207 * connected to. 208 */ 209 struct typec_port *typec_altmode2port(struct typec_altmode *alt) 210 { 211 if (is_typec_plug(alt->dev.parent)) 212 return to_typec_port(alt->dev.parent->parent->parent); 213 if (is_typec_partner(alt->dev.parent)) 214 return to_typec_port(alt->dev.parent->parent); 215 if (is_typec_port(alt->dev.parent)) 216 return to_typec_port(alt->dev.parent); 217 218 return NULL; 219 } 220 EXPORT_SYMBOL_GPL(typec_altmode2port); 221 222 static ssize_t 223 typec_altmode_vdo_show(struct device *dev, struct device_attribute *attr, 224 char *buf) 225 { 226 struct typec_mode *mode = container_of(attr, struct typec_mode, 227 vdo_attr); 228 229 return sprintf(buf, "0x%08x\n", mode->vdo); 230 } 231 232 static ssize_t 233 typec_altmode_desc_show(struct device *dev, struct device_attribute *attr, 234 char *buf) 235 { 236 struct typec_mode *mode = container_of(attr, struct typec_mode, 237 desc_attr); 238 239 return sprintf(buf, "%s\n", mode->desc ? mode->desc : ""); 240 } 241 242 static ssize_t 243 typec_altmode_active_show(struct device *dev, struct device_attribute *attr, 244 char *buf) 245 { 246 struct typec_mode *mode = container_of(attr, struct typec_mode, 247 active_attr); 248 249 return sprintf(buf, "%s\n", mode->active ? "yes" : "no"); 250 } 251 252 static ssize_t 253 typec_altmode_active_store(struct device *dev, struct device_attribute *attr, 254 const char *buf, size_t size) 255 { 256 struct typec_mode *mode = container_of(attr, struct typec_mode, 257 active_attr); 258 struct typec_port *port = typec_altmode2port(mode->alt_mode); 259 bool activate; 260 int ret; 261 262 if (!port->cap->activate_mode) 263 return -EOPNOTSUPP; 264 265 ret = kstrtobool(buf, &activate); 266 if (ret) 267 return ret; 268 269 ret = port->cap->activate_mode(port->cap, mode->index, activate); 270 if (ret) 271 return ret; 272 273 return size; 274 } 275 276 static ssize_t 277 typec_altmode_roles_show(struct device *dev, struct device_attribute *attr, 278 char *buf) 279 { 280 struct typec_mode *mode = container_of(attr, struct typec_mode, 281 roles_attr); 282 ssize_t ret; 283 284 switch (mode->roles) { 285 case TYPEC_PORT_SRC: 286 ret = sprintf(buf, "source\n"); 287 break; 288 case TYPEC_PORT_SNK: 289 ret = sprintf(buf, "sink\n"); 290 break; 291 case TYPEC_PORT_DRP: 292 default: 293 ret = sprintf(buf, "source sink\n"); 294 break; 295 } 296 return ret; 297 } 298 299 static void typec_init_modes(struct typec_altmode *alt, 300 const struct typec_mode_desc *desc, bool is_port) 301 { 302 int i; 303 304 for (i = 0; i < alt->n_modes; i++, desc++) { 305 struct typec_mode *mode = &alt->modes[i]; 306 307 /* Not considering the human readable description critical */ 308 mode->desc = kstrdup(desc->desc, GFP_KERNEL); 309 if (desc->desc && !mode->desc) 310 dev_err(&alt->dev, "failed to copy mode%d desc\n", i); 311 312 mode->alt_mode = alt; 313 mode->vdo = desc->vdo; 314 mode->roles = desc->roles; 315 mode->index = desc->index; 316 sprintf(mode->group_name, "mode%d", desc->index); 317 318 sysfs_attr_init(&mode->vdo_attr.attr); 319 mode->vdo_attr.attr.name = "vdo"; 320 mode->vdo_attr.attr.mode = 0444; 321 mode->vdo_attr.show = typec_altmode_vdo_show; 322 323 sysfs_attr_init(&mode->desc_attr.attr); 324 mode->desc_attr.attr.name = "description"; 325 mode->desc_attr.attr.mode = 0444; 326 mode->desc_attr.show = typec_altmode_desc_show; 327 328 sysfs_attr_init(&mode->active_attr.attr); 329 mode->active_attr.attr.name = "active"; 330 mode->active_attr.attr.mode = 0644; 331 mode->active_attr.show = typec_altmode_active_show; 332 mode->active_attr.store = typec_altmode_active_store; 333 334 mode->attrs[0] = &mode->vdo_attr.attr; 335 mode->attrs[1] = &mode->desc_attr.attr; 336 mode->attrs[2] = &mode->active_attr.attr; 337 338 /* With ports, list the roles that the mode is supported with */ 339 if (is_port) { 340 sysfs_attr_init(&mode->roles_attr.attr); 341 mode->roles_attr.attr.name = "supported_roles"; 342 mode->roles_attr.attr.mode = 0444; 343 mode->roles_attr.show = typec_altmode_roles_show; 344 345 mode->attrs[3] = &mode->roles_attr.attr; 346 } 347 348 mode->group.attrs = mode->attrs; 349 mode->group.name = mode->group_name; 350 351 alt->mode_groups[i] = &mode->group; 352 } 353 } 354 355 static ssize_t svid_show(struct device *dev, struct device_attribute *attr, 356 char *buf) 357 { 358 struct typec_altmode *alt = to_altmode(dev); 359 360 return sprintf(buf, "%04x\n", alt->svid); 361 } 362 static DEVICE_ATTR_RO(svid); 363 364 static struct attribute *typec_altmode_attrs[] = { 365 &dev_attr_svid.attr, 366 NULL 367 }; 368 ATTRIBUTE_GROUPS(typec_altmode); 369 370 static void typec_altmode_release(struct device *dev) 371 { 372 struct typec_altmode *alt = to_altmode(dev); 373 int i; 374 375 for (i = 0; i < alt->n_modes; i++) 376 kfree(alt->modes[i].desc); 377 kfree(alt); 378 } 379 380 static const struct device_type typec_altmode_dev_type = { 381 .name = "typec_alternate_mode", 382 .groups = typec_altmode_groups, 383 .release = typec_altmode_release, 384 }; 385 386 static struct typec_altmode * 387 typec_register_altmode(struct device *parent, 388 const struct typec_altmode_desc *desc) 389 { 390 struct typec_altmode *alt; 391 int ret; 392 393 alt = kzalloc(sizeof(*alt), GFP_KERNEL); 394 if (!alt) 395 return ERR_PTR(-ENOMEM); 396 397 alt->svid = desc->svid; 398 alt->n_modes = desc->n_modes; 399 typec_init_modes(alt, desc->modes, is_typec_port(parent)); 400 401 alt->dev.parent = parent; 402 alt->dev.groups = alt->mode_groups; 403 alt->dev.type = &typec_altmode_dev_type; 404 dev_set_name(&alt->dev, "svid-%04x", alt->svid); 405 406 ret = device_register(&alt->dev); 407 if (ret) { 408 dev_err(parent, "failed to register alternate mode (%d)\n", 409 ret); 410 put_device(&alt->dev); 411 return ERR_PTR(ret); 412 } 413 414 return alt; 415 } 416 417 /** 418 * typec_unregister_altmode - Unregister Alternate Mode 419 * @alt: The alternate mode to be unregistered 420 * 421 * Unregister device created with typec_partner_register_altmode(), 422 * typec_plug_register_altmode() or typec_port_register_altmode(). 423 */ 424 void typec_unregister_altmode(struct typec_altmode *alt) 425 { 426 if (!IS_ERR_OR_NULL(alt)) 427 device_unregister(&alt->dev); 428 } 429 EXPORT_SYMBOL_GPL(typec_unregister_altmode); 430 431 /* ------------------------------------------------------------------------- */ 432 /* Type-C Partners */ 433 434 static ssize_t accessory_mode_show(struct device *dev, 435 struct device_attribute *attr, 436 char *buf) 437 { 438 struct typec_partner *p = to_typec_partner(dev); 439 440 return sprintf(buf, "%s\n", typec_accessory_modes[p->accessory]); 441 } 442 static DEVICE_ATTR_RO(accessory_mode); 443 444 static ssize_t supports_usb_power_delivery_show(struct device *dev, 445 struct device_attribute *attr, 446 char *buf) 447 { 448 struct typec_partner *p = to_typec_partner(dev); 449 450 return sprintf(buf, "%s\n", p->usb_pd ? "yes" : "no"); 451 } 452 static DEVICE_ATTR_RO(supports_usb_power_delivery); 453 454 static struct attribute *typec_partner_attrs[] = { 455 &dev_attr_accessory_mode.attr, 456 &dev_attr_supports_usb_power_delivery.attr, 457 NULL 458 }; 459 ATTRIBUTE_GROUPS(typec_partner); 460 461 static void typec_partner_release(struct device *dev) 462 { 463 struct typec_partner *partner = to_typec_partner(dev); 464 465 kfree(partner); 466 } 467 468 static const struct device_type typec_partner_dev_type = { 469 .name = "typec_partner", 470 .groups = typec_partner_groups, 471 .release = typec_partner_release, 472 }; 473 474 /** 475 * typec_partner_set_identity - Report result from Discover Identity command 476 * @partner: The partner updated identity values 477 * 478 * This routine is used to report that the result of Discover Identity USB power 479 * delivery command has become available. 480 */ 481 int typec_partner_set_identity(struct typec_partner *partner) 482 { 483 if (!partner->identity) 484 return -EINVAL; 485 486 typec_report_identity(&partner->dev); 487 return 0; 488 } 489 EXPORT_SYMBOL_GPL(typec_partner_set_identity); 490 491 /** 492 * typec_partner_register_altmode - Register USB Type-C Partner Alternate Mode 493 * @partner: USB Type-C Partner that supports the alternate mode 494 * @desc: Description of the alternate mode 495 * 496 * This routine is used to register each alternate mode individually that 497 * @partner has listed in response to Discover SVIDs command. The modes for a 498 * SVID listed in response to Discover Modes command need to be listed in an 499 * array in @desc. 500 * 501 * Returns handle to the alternate mode on success or NULL on failure. 502 */ 503 struct typec_altmode * 504 typec_partner_register_altmode(struct typec_partner *partner, 505 const struct typec_altmode_desc *desc) 506 { 507 return typec_register_altmode(&partner->dev, desc); 508 } 509 EXPORT_SYMBOL_GPL(typec_partner_register_altmode); 510 511 /** 512 * typec_register_partner - Register a USB Type-C Partner 513 * @port: The USB Type-C Port the partner is connected to 514 * @desc: Description of the partner 515 * 516 * Registers a device for USB Type-C Partner described in @desc. 517 * 518 * Returns handle to the partner on success or ERR_PTR on failure. 519 */ 520 struct typec_partner *typec_register_partner(struct typec_port *port, 521 struct typec_partner_desc *desc) 522 { 523 struct typec_partner *partner; 524 int ret; 525 526 partner = kzalloc(sizeof(*partner), GFP_KERNEL); 527 if (!partner) 528 return ERR_PTR(-ENOMEM); 529 530 partner->usb_pd = desc->usb_pd; 531 partner->accessory = desc->accessory; 532 533 if (desc->identity) { 534 /* 535 * Creating directory for the identity only if the driver is 536 * able to provide data to it. 537 */ 538 partner->dev.groups = usb_pd_id_groups; 539 partner->identity = desc->identity; 540 } 541 542 partner->dev.class = typec_class; 543 partner->dev.parent = &port->dev; 544 partner->dev.type = &typec_partner_dev_type; 545 dev_set_name(&partner->dev, "%s-partner", dev_name(&port->dev)); 546 547 ret = device_register(&partner->dev); 548 if (ret) { 549 dev_err(&port->dev, "failed to register partner (%d)\n", ret); 550 put_device(&partner->dev); 551 return ERR_PTR(ret); 552 } 553 554 return partner; 555 } 556 EXPORT_SYMBOL_GPL(typec_register_partner); 557 558 /** 559 * typec_unregister_partner - Unregister a USB Type-C Partner 560 * @partner: The partner to be unregistered 561 * 562 * Unregister device created with typec_register_partner(). 563 */ 564 void typec_unregister_partner(struct typec_partner *partner) 565 { 566 if (!IS_ERR_OR_NULL(partner)) 567 device_unregister(&partner->dev); 568 } 569 EXPORT_SYMBOL_GPL(typec_unregister_partner); 570 571 /* ------------------------------------------------------------------------- */ 572 /* Type-C Cable Plugs */ 573 574 static void typec_plug_release(struct device *dev) 575 { 576 struct typec_plug *plug = to_typec_plug(dev); 577 578 kfree(plug); 579 } 580 581 static const struct device_type typec_plug_dev_type = { 582 .name = "typec_plug", 583 .release = typec_plug_release, 584 }; 585 586 /** 587 * typec_plug_register_altmode - Register USB Type-C Cable Plug Alternate Mode 588 * @plug: USB Type-C Cable Plug that supports the alternate mode 589 * @desc: Description of the alternate mode 590 * 591 * This routine is used to register each alternate mode individually that @plug 592 * has listed in response to Discover SVIDs command. The modes for a SVID that 593 * the plug lists in response to Discover Modes command need to be listed in an 594 * array in @desc. 595 * 596 * Returns handle to the alternate mode on success or ERR_PTR on failure. 597 */ 598 struct typec_altmode * 599 typec_plug_register_altmode(struct typec_plug *plug, 600 const struct typec_altmode_desc *desc) 601 { 602 return typec_register_altmode(&plug->dev, desc); 603 } 604 EXPORT_SYMBOL_GPL(typec_plug_register_altmode); 605 606 /** 607 * typec_register_plug - Register a USB Type-C Cable Plug 608 * @cable: USB Type-C Cable with the plug 609 * @desc: Description of the cable plug 610 * 611 * Registers a device for USB Type-C Cable Plug described in @desc. A USB Type-C 612 * Cable Plug represents a plug with electronics in it that can response to USB 613 * Power Delivery SOP Prime or SOP Double Prime packages. 614 * 615 * Returns handle to the cable plug on success or ERR_PTR on failure. 616 */ 617 struct typec_plug *typec_register_plug(struct typec_cable *cable, 618 struct typec_plug_desc *desc) 619 { 620 struct typec_plug *plug; 621 char name[8]; 622 int ret; 623 624 plug = kzalloc(sizeof(*plug), GFP_KERNEL); 625 if (!plug) 626 return ERR_PTR(-ENOMEM); 627 628 sprintf(name, "plug%d", desc->index); 629 630 plug->index = desc->index; 631 plug->dev.class = typec_class; 632 plug->dev.parent = &cable->dev; 633 plug->dev.type = &typec_plug_dev_type; 634 dev_set_name(&plug->dev, "%s-%s", dev_name(cable->dev.parent), name); 635 636 ret = device_register(&plug->dev); 637 if (ret) { 638 dev_err(&cable->dev, "failed to register plug (%d)\n", ret); 639 put_device(&plug->dev); 640 return ERR_PTR(ret); 641 } 642 643 return plug; 644 } 645 EXPORT_SYMBOL_GPL(typec_register_plug); 646 647 /** 648 * typec_unregister_plug - Unregister a USB Type-C Cable Plug 649 * @plug: The cable plug to be unregistered 650 * 651 * Unregister device created with typec_register_plug(). 652 */ 653 void typec_unregister_plug(struct typec_plug *plug) 654 { 655 if (!IS_ERR_OR_NULL(plug)) 656 device_unregister(&plug->dev); 657 } 658 EXPORT_SYMBOL_GPL(typec_unregister_plug); 659 660 /* Type-C Cables */ 661 662 static ssize_t 663 type_show(struct device *dev, struct device_attribute *attr, char *buf) 664 { 665 struct typec_cable *cable = to_typec_cable(dev); 666 667 return sprintf(buf, "%s\n", cable->active ? "active" : "passive"); 668 } 669 static DEVICE_ATTR_RO(type); 670 671 static const char * const typec_plug_types[] = { 672 [USB_PLUG_NONE] = "unknown", 673 [USB_PLUG_TYPE_A] = "type-a", 674 [USB_PLUG_TYPE_B] = "type-b", 675 [USB_PLUG_TYPE_C] = "type-c", 676 [USB_PLUG_CAPTIVE] = "captive", 677 }; 678 679 static ssize_t plug_type_show(struct device *dev, 680 struct device_attribute *attr, char *buf) 681 { 682 struct typec_cable *cable = to_typec_cable(dev); 683 684 return sprintf(buf, "%s\n", typec_plug_types[cable->type]); 685 } 686 static DEVICE_ATTR_RO(plug_type); 687 688 static struct attribute *typec_cable_attrs[] = { 689 &dev_attr_type.attr, 690 &dev_attr_plug_type.attr, 691 NULL 692 }; 693 ATTRIBUTE_GROUPS(typec_cable); 694 695 static void typec_cable_release(struct device *dev) 696 { 697 struct typec_cable *cable = to_typec_cable(dev); 698 699 kfree(cable); 700 } 701 702 static const struct device_type typec_cable_dev_type = { 703 .name = "typec_cable", 704 .groups = typec_cable_groups, 705 .release = typec_cable_release, 706 }; 707 708 /** 709 * typec_cable_set_identity - Report result from Discover Identity command 710 * @cable: The cable updated identity values 711 * 712 * This routine is used to report that the result of Discover Identity USB power 713 * delivery command has become available. 714 */ 715 int typec_cable_set_identity(struct typec_cable *cable) 716 { 717 if (!cable->identity) 718 return -EINVAL; 719 720 typec_report_identity(&cable->dev); 721 return 0; 722 } 723 EXPORT_SYMBOL_GPL(typec_cable_set_identity); 724 725 /** 726 * typec_register_cable - Register a USB Type-C Cable 727 * @port: The USB Type-C Port the cable is connected to 728 * @desc: Description of the cable 729 * 730 * Registers a device for USB Type-C Cable described in @desc. The cable will be 731 * parent for the optional cable plug devises. 732 * 733 * Returns handle to the cable on success or ERR_PTR on failure. 734 */ 735 struct typec_cable *typec_register_cable(struct typec_port *port, 736 struct typec_cable_desc *desc) 737 { 738 struct typec_cable *cable; 739 int ret; 740 741 cable = kzalloc(sizeof(*cable), GFP_KERNEL); 742 if (!cable) 743 return ERR_PTR(-ENOMEM); 744 745 cable->type = desc->type; 746 cable->active = desc->active; 747 748 if (desc->identity) { 749 /* 750 * Creating directory for the identity only if the driver is 751 * able to provide data to it. 752 */ 753 cable->dev.groups = usb_pd_id_groups; 754 cable->identity = desc->identity; 755 } 756 757 cable->dev.class = typec_class; 758 cable->dev.parent = &port->dev; 759 cable->dev.type = &typec_cable_dev_type; 760 dev_set_name(&cable->dev, "%s-cable", dev_name(&port->dev)); 761 762 ret = device_register(&cable->dev); 763 if (ret) { 764 dev_err(&port->dev, "failed to register cable (%d)\n", ret); 765 put_device(&cable->dev); 766 return ERR_PTR(ret); 767 } 768 769 return cable; 770 } 771 EXPORT_SYMBOL_GPL(typec_register_cable); 772 773 /** 774 * typec_unregister_cable - Unregister a USB Type-C Cable 775 * @cable: The cable to be unregistered 776 * 777 * Unregister device created with typec_register_cable(). 778 */ 779 void typec_unregister_cable(struct typec_cable *cable) 780 { 781 if (!IS_ERR_OR_NULL(cable)) 782 device_unregister(&cable->dev); 783 } 784 EXPORT_SYMBOL_GPL(typec_unregister_cable); 785 786 /* ------------------------------------------------------------------------- */ 787 /* USB Type-C ports */ 788 789 static const char * const typec_roles[] = { 790 [TYPEC_SINK] = "sink", 791 [TYPEC_SOURCE] = "source", 792 }; 793 794 static const char * const typec_data_roles[] = { 795 [TYPEC_DEVICE] = "device", 796 [TYPEC_HOST] = "host", 797 }; 798 799 static const char * const typec_port_types[] = { 800 [TYPEC_PORT_SRC] = "source", 801 [TYPEC_PORT_SNK] = "sink", 802 [TYPEC_PORT_DRP] = "dual", 803 }; 804 805 static const char * const typec_port_types_drp[] = { 806 [TYPEC_PORT_SRC] = "dual [source] sink", 807 [TYPEC_PORT_SNK] = "dual source [sink]", 808 [TYPEC_PORT_DRP] = "[dual] source sink", 809 }; 810 811 static ssize_t 812 preferred_role_store(struct device *dev, struct device_attribute *attr, 813 const char *buf, size_t size) 814 { 815 struct typec_port *port = to_typec_port(dev); 816 int role; 817 int ret; 818 819 if (port->cap->type != TYPEC_PORT_DRP) { 820 dev_dbg(dev, "Preferred role only supported with DRP ports\n"); 821 return -EOPNOTSUPP; 822 } 823 824 if (!port->cap->try_role) { 825 dev_dbg(dev, "Setting preferred role not supported\n"); 826 return -EOPNOTSUPP; 827 } 828 829 role = sysfs_match_string(typec_roles, buf); 830 if (role < 0) { 831 if (sysfs_streq(buf, "none")) 832 role = TYPEC_NO_PREFERRED_ROLE; 833 else 834 return -EINVAL; 835 } 836 837 ret = port->cap->try_role(port->cap, role); 838 if (ret) 839 return ret; 840 841 port->prefer_role = role; 842 return size; 843 } 844 845 static ssize_t 846 preferred_role_show(struct device *dev, struct device_attribute *attr, 847 char *buf) 848 { 849 struct typec_port *port = to_typec_port(dev); 850 851 if (port->cap->type != TYPEC_PORT_DRP) 852 return 0; 853 854 if (port->prefer_role < 0) 855 return 0; 856 857 return sprintf(buf, "%s\n", typec_roles[port->prefer_role]); 858 } 859 static DEVICE_ATTR_RW(preferred_role); 860 861 static ssize_t data_role_store(struct device *dev, 862 struct device_attribute *attr, 863 const char *buf, size_t size) 864 { 865 struct typec_port *port = to_typec_port(dev); 866 int ret; 867 868 if (!port->cap->dr_set) { 869 dev_dbg(dev, "data role swapping not supported\n"); 870 return -EOPNOTSUPP; 871 } 872 873 ret = sysfs_match_string(typec_data_roles, buf); 874 if (ret < 0) 875 return ret; 876 877 mutex_lock(&port->port_type_lock); 878 if (port->cap->data != TYPEC_PORT_DRD) { 879 ret = -EOPNOTSUPP; 880 goto unlock_and_ret; 881 } 882 883 ret = port->cap->dr_set(port->cap, ret); 884 if (ret) 885 goto unlock_and_ret; 886 887 ret = size; 888 unlock_and_ret: 889 mutex_unlock(&port->port_type_lock); 890 return ret; 891 } 892 893 static ssize_t data_role_show(struct device *dev, 894 struct device_attribute *attr, char *buf) 895 { 896 struct typec_port *port = to_typec_port(dev); 897 898 if (port->cap->data == TYPEC_PORT_DRD) 899 return sprintf(buf, "%s\n", port->data_role == TYPEC_HOST ? 900 "[host] device" : "host [device]"); 901 902 return sprintf(buf, "[%s]\n", typec_data_roles[port->data_role]); 903 } 904 static DEVICE_ATTR_RW(data_role); 905 906 static ssize_t power_role_store(struct device *dev, 907 struct device_attribute *attr, 908 const char *buf, size_t size) 909 { 910 struct typec_port *port = to_typec_port(dev); 911 int ret; 912 913 if (!port->cap->pd_revision) { 914 dev_dbg(dev, "USB Power Delivery not supported\n"); 915 return -EOPNOTSUPP; 916 } 917 918 if (!port->cap->pr_set) { 919 dev_dbg(dev, "power role swapping not supported\n"); 920 return -EOPNOTSUPP; 921 } 922 923 if (port->pwr_opmode != TYPEC_PWR_MODE_PD) { 924 dev_dbg(dev, "partner unable to swap power role\n"); 925 return -EIO; 926 } 927 928 ret = sysfs_match_string(typec_roles, buf); 929 if (ret < 0) 930 return ret; 931 932 mutex_lock(&port->port_type_lock); 933 if (port->port_type != TYPEC_PORT_DRP) { 934 dev_dbg(dev, "port type fixed at \"%s\"", 935 typec_port_types[port->port_type]); 936 ret = -EOPNOTSUPP; 937 goto unlock_and_ret; 938 } 939 940 ret = port->cap->pr_set(port->cap, ret); 941 if (ret) 942 goto unlock_and_ret; 943 944 ret = size; 945 unlock_and_ret: 946 mutex_unlock(&port->port_type_lock); 947 return ret; 948 } 949 950 static ssize_t power_role_show(struct device *dev, 951 struct device_attribute *attr, char *buf) 952 { 953 struct typec_port *port = to_typec_port(dev); 954 955 if (port->cap->type == TYPEC_PORT_DRP) 956 return sprintf(buf, "%s\n", port->pwr_role == TYPEC_SOURCE ? 957 "[source] sink" : "source [sink]"); 958 959 return sprintf(buf, "[%s]\n", typec_roles[port->pwr_role]); 960 } 961 static DEVICE_ATTR_RW(power_role); 962 963 static ssize_t 964 port_type_store(struct device *dev, struct device_attribute *attr, 965 const char *buf, size_t size) 966 { 967 struct typec_port *port = to_typec_port(dev); 968 int ret; 969 enum typec_port_type type; 970 971 if (!port->cap->port_type_set || port->cap->type != TYPEC_PORT_DRP) { 972 dev_dbg(dev, "changing port type not supported\n"); 973 return -EOPNOTSUPP; 974 } 975 976 ret = sysfs_match_string(typec_port_types, buf); 977 if (ret < 0) 978 return ret; 979 980 type = ret; 981 mutex_lock(&port->port_type_lock); 982 983 if (port->port_type == type) { 984 ret = size; 985 goto unlock_and_ret; 986 } 987 988 ret = port->cap->port_type_set(port->cap, type); 989 if (ret) 990 goto unlock_and_ret; 991 992 port->port_type = type; 993 ret = size; 994 995 unlock_and_ret: 996 mutex_unlock(&port->port_type_lock); 997 return ret; 998 } 999 1000 static ssize_t 1001 port_type_show(struct device *dev, struct device_attribute *attr, 1002 char *buf) 1003 { 1004 struct typec_port *port = to_typec_port(dev); 1005 1006 if (port->cap->type == TYPEC_PORT_DRP) 1007 return sprintf(buf, "%s\n", 1008 typec_port_types_drp[port->port_type]); 1009 1010 return sprintf(buf, "[%s]\n", typec_port_types[port->cap->type]); 1011 } 1012 static DEVICE_ATTR_RW(port_type); 1013 1014 static const char * const typec_pwr_opmodes[] = { 1015 [TYPEC_PWR_MODE_USB] = "default", 1016 [TYPEC_PWR_MODE_1_5A] = "1.5A", 1017 [TYPEC_PWR_MODE_3_0A] = "3.0A", 1018 [TYPEC_PWR_MODE_PD] = "usb_power_delivery", 1019 }; 1020 1021 static ssize_t power_operation_mode_show(struct device *dev, 1022 struct device_attribute *attr, 1023 char *buf) 1024 { 1025 struct typec_port *port = to_typec_port(dev); 1026 1027 return sprintf(buf, "%s\n", typec_pwr_opmodes[port->pwr_opmode]); 1028 } 1029 static DEVICE_ATTR_RO(power_operation_mode); 1030 1031 static ssize_t vconn_source_store(struct device *dev, 1032 struct device_attribute *attr, 1033 const char *buf, size_t size) 1034 { 1035 struct typec_port *port = to_typec_port(dev); 1036 bool source; 1037 int ret; 1038 1039 if (!port->cap->pd_revision) { 1040 dev_dbg(dev, "VCONN swap depends on USB Power Delivery\n"); 1041 return -EOPNOTSUPP; 1042 } 1043 1044 if (!port->cap->vconn_set) { 1045 dev_dbg(dev, "VCONN swapping not supported\n"); 1046 return -EOPNOTSUPP; 1047 } 1048 1049 ret = kstrtobool(buf, &source); 1050 if (ret) 1051 return ret; 1052 1053 ret = port->cap->vconn_set(port->cap, (enum typec_role)source); 1054 if (ret) 1055 return ret; 1056 1057 return size; 1058 } 1059 1060 static ssize_t vconn_source_show(struct device *dev, 1061 struct device_attribute *attr, char *buf) 1062 { 1063 struct typec_port *port = to_typec_port(dev); 1064 1065 return sprintf(buf, "%s\n", 1066 port->vconn_role == TYPEC_SOURCE ? "yes" : "no"); 1067 } 1068 static DEVICE_ATTR_RW(vconn_source); 1069 1070 static ssize_t supported_accessory_modes_show(struct device *dev, 1071 struct device_attribute *attr, 1072 char *buf) 1073 { 1074 struct typec_port *port = to_typec_port(dev); 1075 ssize_t ret = 0; 1076 int i; 1077 1078 for (i = 0; i < ARRAY_SIZE(port->cap->accessory); i++) { 1079 if (port->cap->accessory[i]) 1080 ret += sprintf(buf + ret, "%s ", 1081 typec_accessory_modes[port->cap->accessory[i]]); 1082 } 1083 1084 if (!ret) 1085 return sprintf(buf, "none\n"); 1086 1087 buf[ret - 1] = '\n'; 1088 1089 return ret; 1090 } 1091 static DEVICE_ATTR_RO(supported_accessory_modes); 1092 1093 static ssize_t usb_typec_revision_show(struct device *dev, 1094 struct device_attribute *attr, 1095 char *buf) 1096 { 1097 struct typec_port *port = to_typec_port(dev); 1098 u16 rev = port->cap->revision; 1099 1100 return sprintf(buf, "%d.%d\n", (rev >> 8) & 0xff, (rev >> 4) & 0xf); 1101 } 1102 static DEVICE_ATTR_RO(usb_typec_revision); 1103 1104 static ssize_t usb_power_delivery_revision_show(struct device *dev, 1105 struct device_attribute *attr, 1106 char *buf) 1107 { 1108 struct typec_port *p = to_typec_port(dev); 1109 1110 return sprintf(buf, "%d\n", (p->cap->pd_revision >> 8) & 0xff); 1111 } 1112 static DEVICE_ATTR_RO(usb_power_delivery_revision); 1113 1114 static struct attribute *typec_attrs[] = { 1115 &dev_attr_data_role.attr, 1116 &dev_attr_power_operation_mode.attr, 1117 &dev_attr_power_role.attr, 1118 &dev_attr_preferred_role.attr, 1119 &dev_attr_supported_accessory_modes.attr, 1120 &dev_attr_usb_power_delivery_revision.attr, 1121 &dev_attr_usb_typec_revision.attr, 1122 &dev_attr_vconn_source.attr, 1123 &dev_attr_port_type.attr, 1124 NULL, 1125 }; 1126 ATTRIBUTE_GROUPS(typec); 1127 1128 static int typec_uevent(struct device *dev, struct kobj_uevent_env *env) 1129 { 1130 int ret; 1131 1132 ret = add_uevent_var(env, "TYPEC_PORT=%s", dev_name(dev)); 1133 if (ret) 1134 dev_err(dev, "failed to add uevent TYPEC_PORT\n"); 1135 1136 return ret; 1137 } 1138 1139 static void typec_release(struct device *dev) 1140 { 1141 struct typec_port *port = to_typec_port(dev); 1142 1143 ida_simple_remove(&typec_index_ida, port->id); 1144 typec_switch_put(port->sw); 1145 typec_mux_put(port->mux); 1146 kfree(port); 1147 } 1148 1149 static const struct device_type typec_port_dev_type = { 1150 .name = "typec_port", 1151 .groups = typec_groups, 1152 .uevent = typec_uevent, 1153 .release = typec_release, 1154 }; 1155 1156 /* --------------------------------------- */ 1157 /* Driver callbacks to report role updates */ 1158 1159 /** 1160 * typec_set_data_role - Report data role change 1161 * @port: The USB Type-C Port where the role was changed 1162 * @role: The new data role 1163 * 1164 * This routine is used by the port drivers to report data role changes. 1165 */ 1166 void typec_set_data_role(struct typec_port *port, enum typec_data_role role) 1167 { 1168 if (port->data_role == role) 1169 return; 1170 1171 port->data_role = role; 1172 sysfs_notify(&port->dev.kobj, NULL, "data_role"); 1173 kobject_uevent(&port->dev.kobj, KOBJ_CHANGE); 1174 } 1175 EXPORT_SYMBOL_GPL(typec_set_data_role); 1176 1177 /** 1178 * typec_set_pwr_role - Report power role change 1179 * @port: The USB Type-C Port where the role was changed 1180 * @role: The new data role 1181 * 1182 * This routine is used by the port drivers to report power role changes. 1183 */ 1184 void typec_set_pwr_role(struct typec_port *port, enum typec_role role) 1185 { 1186 if (port->pwr_role == role) 1187 return; 1188 1189 port->pwr_role = role; 1190 sysfs_notify(&port->dev.kobj, NULL, "power_role"); 1191 kobject_uevent(&port->dev.kobj, KOBJ_CHANGE); 1192 } 1193 EXPORT_SYMBOL_GPL(typec_set_pwr_role); 1194 1195 /** 1196 * typec_set_pwr_role - Report VCONN source change 1197 * @port: The USB Type-C Port which VCONN role changed 1198 * @role: Source when @port is sourcing VCONN, or Sink when it's not 1199 * 1200 * This routine is used by the port drivers to report if the VCONN source is 1201 * changes. 1202 */ 1203 void typec_set_vconn_role(struct typec_port *port, enum typec_role role) 1204 { 1205 if (port->vconn_role == role) 1206 return; 1207 1208 port->vconn_role = role; 1209 sysfs_notify(&port->dev.kobj, NULL, "vconn_source"); 1210 kobject_uevent(&port->dev.kobj, KOBJ_CHANGE); 1211 } 1212 EXPORT_SYMBOL_GPL(typec_set_vconn_role); 1213 1214 static int partner_match(struct device *dev, void *data) 1215 { 1216 return is_typec_partner(dev); 1217 } 1218 1219 /** 1220 * typec_set_pwr_opmode - Report changed power operation mode 1221 * @port: The USB Type-C Port where the mode was changed 1222 * @opmode: New power operation mode 1223 * 1224 * This routine is used by the port drivers to report changed power operation 1225 * mode in @port. The modes are USB (default), 1.5A, 3.0A as defined in USB 1226 * Type-C specification, and "USB Power Delivery" when the power levels are 1227 * negotiated with methods defined in USB Power Delivery specification. 1228 */ 1229 void typec_set_pwr_opmode(struct typec_port *port, 1230 enum typec_pwr_opmode opmode) 1231 { 1232 struct device *partner_dev; 1233 1234 if (port->pwr_opmode == opmode) 1235 return; 1236 1237 port->pwr_opmode = opmode; 1238 sysfs_notify(&port->dev.kobj, NULL, "power_operation_mode"); 1239 kobject_uevent(&port->dev.kobj, KOBJ_CHANGE); 1240 1241 partner_dev = device_find_child(&port->dev, NULL, partner_match); 1242 if (partner_dev) { 1243 struct typec_partner *partner = to_typec_partner(partner_dev); 1244 1245 if (opmode == TYPEC_PWR_MODE_PD && !partner->usb_pd) { 1246 partner->usb_pd = 1; 1247 sysfs_notify(&partner_dev->kobj, NULL, 1248 "supports_usb_power_delivery"); 1249 } 1250 put_device(partner_dev); 1251 } 1252 } 1253 EXPORT_SYMBOL_GPL(typec_set_pwr_opmode); 1254 1255 /* ------------------------------------------ */ 1256 /* API for Multiplexer/DeMultiplexer Switches */ 1257 1258 /** 1259 * typec_set_orientation - Set USB Type-C cable plug orientation 1260 * @port: USB Type-C Port 1261 * @orientation: USB Type-C cable plug orientation 1262 * 1263 * Set cable plug orientation for @port. 1264 */ 1265 int typec_set_orientation(struct typec_port *port, 1266 enum typec_orientation orientation) 1267 { 1268 int ret; 1269 1270 if (port->sw) { 1271 ret = port->sw->set(port->sw, orientation); 1272 if (ret) 1273 return ret; 1274 } 1275 1276 port->orientation = orientation; 1277 1278 return 0; 1279 } 1280 EXPORT_SYMBOL_GPL(typec_set_orientation); 1281 1282 /** 1283 * typec_set_mode - Set mode of operation for USB Type-C connector 1284 * @port: USB Type-C port for the connector 1285 * @mode: Operation mode for the connector 1286 * 1287 * Set mode @mode for @port. This function will configure the muxes needed to 1288 * enter @mode. 1289 */ 1290 int typec_set_mode(struct typec_port *port, int mode) 1291 { 1292 return port->mux ? port->mux->set(port->mux, mode) : 0; 1293 } 1294 EXPORT_SYMBOL_GPL(typec_set_mode); 1295 1296 /* --------------------------------------- */ 1297 1298 /** 1299 * typec_port_register_altmode - Register USB Type-C Port Alternate Mode 1300 * @port: USB Type-C Port that supports the alternate mode 1301 * @desc: Description of the alternate mode 1302 * 1303 * This routine is used to register an alternate mode that @port is capable of 1304 * supporting. 1305 * 1306 * Returns handle to the alternate mode on success or ERR_PTR on failure. 1307 */ 1308 struct typec_altmode * 1309 typec_port_register_altmode(struct typec_port *port, 1310 const struct typec_altmode_desc *desc) 1311 { 1312 return typec_register_altmode(&port->dev, desc); 1313 } 1314 EXPORT_SYMBOL_GPL(typec_port_register_altmode); 1315 1316 /** 1317 * typec_register_port - Register a USB Type-C Port 1318 * @parent: Parent device 1319 * @cap: Description of the port 1320 * 1321 * Registers a device for USB Type-C Port described in @cap. 1322 * 1323 * Returns handle to the port on success or ERR_PTR on failure. 1324 */ 1325 struct typec_port *typec_register_port(struct device *parent, 1326 const struct typec_capability *cap) 1327 { 1328 struct typec_port *port; 1329 int ret; 1330 int id; 1331 1332 port = kzalloc(sizeof(*port), GFP_KERNEL); 1333 if (!port) 1334 return ERR_PTR(-ENOMEM); 1335 1336 id = ida_simple_get(&typec_index_ida, 0, 0, GFP_KERNEL); 1337 if (id < 0) { 1338 kfree(port); 1339 return ERR_PTR(id); 1340 } 1341 1342 port->sw = typec_switch_get(cap->fwnode ? &port->dev : parent); 1343 if (IS_ERR(port->sw)) { 1344 ret = PTR_ERR(port->sw); 1345 goto err_switch; 1346 } 1347 1348 port->mux = typec_mux_get(cap->fwnode ? &port->dev : parent); 1349 if (IS_ERR(port->mux)) { 1350 ret = PTR_ERR(port->mux); 1351 goto err_mux; 1352 } 1353 1354 switch (cap->type) { 1355 case TYPEC_PORT_SRC: 1356 port->pwr_role = TYPEC_SOURCE; 1357 port->vconn_role = TYPEC_SOURCE; 1358 break; 1359 case TYPEC_PORT_SNK: 1360 port->pwr_role = TYPEC_SINK; 1361 port->vconn_role = TYPEC_SINK; 1362 break; 1363 case TYPEC_PORT_DRP: 1364 if (cap->prefer_role != TYPEC_NO_PREFERRED_ROLE) 1365 port->pwr_role = cap->prefer_role; 1366 else 1367 port->pwr_role = TYPEC_SINK; 1368 break; 1369 } 1370 1371 switch (cap->data) { 1372 case TYPEC_PORT_DFP: 1373 port->data_role = TYPEC_HOST; 1374 break; 1375 case TYPEC_PORT_UFP: 1376 port->data_role = TYPEC_DEVICE; 1377 break; 1378 case TYPEC_PORT_DRD: 1379 if (cap->prefer_role == TYPEC_SOURCE) 1380 port->data_role = TYPEC_HOST; 1381 else 1382 port->data_role = TYPEC_DEVICE; 1383 break; 1384 } 1385 1386 port->id = id; 1387 port->cap = cap; 1388 port->port_type = cap->type; 1389 mutex_init(&port->port_type_lock); 1390 port->prefer_role = cap->prefer_role; 1391 1392 port->dev.class = typec_class; 1393 port->dev.parent = parent; 1394 port->dev.fwnode = cap->fwnode; 1395 port->dev.type = &typec_port_dev_type; 1396 dev_set_name(&port->dev, "port%d", id); 1397 1398 ret = device_register(&port->dev); 1399 if (ret) { 1400 dev_err(parent, "failed to register port (%d)\n", ret); 1401 put_device(&port->dev); 1402 return ERR_PTR(ret); 1403 } 1404 1405 return port; 1406 1407 err_mux: 1408 typec_switch_put(port->sw); 1409 1410 err_switch: 1411 ida_simple_remove(&typec_index_ida, port->id); 1412 kfree(port); 1413 1414 return ERR_PTR(ret); 1415 } 1416 EXPORT_SYMBOL_GPL(typec_register_port); 1417 1418 /** 1419 * typec_unregister_port - Unregister a USB Type-C Port 1420 * @port: The port to be unregistered 1421 * 1422 * Unregister device created with typec_register_port(). 1423 */ 1424 void typec_unregister_port(struct typec_port *port) 1425 { 1426 if (!IS_ERR_OR_NULL(port)) 1427 device_unregister(&port->dev); 1428 } 1429 EXPORT_SYMBOL_GPL(typec_unregister_port); 1430 1431 static int __init typec_init(void) 1432 { 1433 typec_class = class_create(THIS_MODULE, "typec"); 1434 return PTR_ERR_OR_ZERO(typec_class); 1435 } 1436 subsys_initcall(typec_init); 1437 1438 static void __exit typec_exit(void) 1439 { 1440 class_destroy(typec_class); 1441 ida_destroy(&typec_index_ida); 1442 } 1443 module_exit(typec_exit); 1444 1445 MODULE_AUTHOR("Heikki Krogerus <[email protected]>"); 1446 MODULE_LICENSE("GPL v2"); 1447 MODULE_DESCRIPTION("USB Type-C Connector Class"); 1448