1
0
Fork 0
alistair23-linux/drivers/usb/typec/ucsi/ucsi.h

457 lines
13 KiB
C
Raw Normal View History

License cleanup: add SPDX GPL-2.0 license identifier to files with no license Many source files in the tree are missing licensing information, which makes it harder for compliance tools to determine the correct license. By default all files without license information are under the default license of the kernel, which is GPL version 2. Update the files which contain no license information with the 'GPL-2.0' SPDX license identifier. The SPDX identifier is a legally binding shorthand, which can be used instead of the full boiler plate text. This patch is based on work done by Thomas Gleixner and Kate Stewart and Philippe Ombredanne. How this work was done: Patches were generated and checked against linux-4.14-rc6 for a subset of the use cases: - file had no licensing information it it. - file was a */uapi/* one with no licensing information in it, - file was a */uapi/* one with existing licensing information, Further patches will be generated in subsequent months to fix up cases where non-standard license headers were used, and references to license had to be inferred by heuristics based on keywords. The analysis to determine which SPDX License Identifier to be applied to a file was done in a spreadsheet of side by side results from of the output of two independent scanners (ScanCode & Windriver) producing SPDX tag:value files created by Philippe Ombredanne. Philippe prepared the base worksheet, and did an initial spot review of a few 1000 files. The 4.13 kernel was the starting point of the analysis with 60,537 files assessed. Kate Stewart did a file by file comparison of the scanner results in the spreadsheet to determine which SPDX license identifier(s) to be applied to the file. She confirmed any determination that was not immediately clear with lawyers working with the Linux Foundation. Criteria used to select files for SPDX license identifier tagging was: - Files considered eligible had to be source code files. - Make and config files were included as candidates if they contained >5 lines of source - File already had some variant of a license header in it (even if <5 lines). All documentation files were explicitly excluded. The following heuristics were used to determine which SPDX license identifiers to apply. - when both scanners couldn't find any license traces, file was considered to have no license information in it, and the top level COPYING file license applied. For non */uapi/* files that summary was: SPDX license identifier # files ---------------------------------------------------|------- GPL-2.0 11139 and resulted in the first patch in this series. If that file was a */uapi/* path one, it was "GPL-2.0 WITH Linux-syscall-note" otherwise it was "GPL-2.0". Results of that was: SPDX license identifier # files ---------------------------------------------------|------- GPL-2.0 WITH Linux-syscall-note 930 and resulted in the second patch in this series. - if a file had some form of licensing information in it, and was one of the */uapi/* ones, it was denoted with the Linux-syscall-note if any GPL family license was found in the file or had no licensing in it (per prior point). Results summary: SPDX license identifier # files ---------------------------------------------------|------ GPL-2.0 WITH Linux-syscall-note 270 GPL-2.0+ WITH Linux-syscall-note 169 ((GPL-2.0 WITH Linux-syscall-note) OR BSD-2-Clause) 21 ((GPL-2.0 WITH Linux-syscall-note) OR BSD-3-Clause) 17 LGPL-2.1+ WITH Linux-syscall-note 15 GPL-1.0+ WITH Linux-syscall-note 14 ((GPL-2.0+ WITH Linux-syscall-note) OR BSD-3-Clause) 5 LGPL-2.0+ WITH Linux-syscall-note 4 LGPL-2.1 WITH Linux-syscall-note 3 ((GPL-2.0 WITH Linux-syscall-note) OR MIT) 3 ((GPL-2.0 WITH Linux-syscall-note) AND MIT) 1 and that resulted in the third patch in this series. - when the two scanners agreed on the detected license(s), that became the concluded license(s). - when there was disagreement between the two scanners (one detected a license but the other didn't, or they both detected different licenses) a manual inspection of the file occurred. - In most cases a manual inspection of the information in the file resulted in a clear resolution of the license that should apply (and which scanner probably needed to revisit its heuristics). - When it was not immediately clear, the license identifier was confirmed with lawyers working with the Linux Foundation. - If there was any question as to the appropriate license identifier, the file was flagged for further research and to be revisited later in time. In total, over 70 hours of logged manual review was done on the spreadsheet to determine the SPDX license identifiers to apply to the source files by Kate, Philippe, Thomas and, in some cases, confirmation by lawyers working with the Linux Foundation. Kate also obtained a third independent scan of the 4.13 code base from FOSSology, and compared selected files where the other two scanners disagreed against that SPDX file, to see if there was new insights. The Windriver scanner is based on an older version of FOSSology in part, so they are related. Thomas did random spot checks in about 500 files from the spreadsheets for the uapi headers and agreed with SPDX license identifier in the files he inspected. For the non-uapi files Thomas did random spot checks in about 15000 files. In initial set of patches against 4.14-rc6, 3 files were found to have copy/paste license identifier errors, and have been fixed to reflect the correct identifier. Additionally Philippe spent 10 hours this week doing a detailed manual inspection and review of the 12,461 patched files from the initial patch version early this week with: - a full scancode scan run, collecting the matched texts, detected license ids and scores - reviewing anything where there was a license detected (about 500+ files) to ensure that the applied SPDX license was correct - reviewing anything where there was no detection but the patch license was not GPL-2.0 WITH Linux-syscall-note to ensure that the applied SPDX license was correct This produced a worksheet with 20 files needing minor correction. This worksheet was then exported into 3 different .csv files for the different types of files to be modified. These .csv files were then reviewed by Greg. Thomas wrote a script to parse the csv files and add the proper SPDX tag to the file, in the format that the file expected. This script was further refined by Greg based on the output to detect more types of files automatically and to distinguish between header and source .c files (which need different comment types.) Finally Greg ran the script using the .csv files to generate the patches. Reviewed-by: Kate Stewart <kstewart@linuxfoundation.org> Reviewed-by: Philippe Ombredanne <pombredanne@nexb.com> Reviewed-by: Thomas Gleixner <tglx@linutronix.de> Signed-off-by: Greg Kroah-Hartman <gregkh@linuxfoundation.org>
2017-11-01 08:07:57 -06:00
/* SPDX-License-Identifier: GPL-2.0 */
usb: typec: Add support for UCSI interface UCSI - USB Type-C Connector System Software Interface - is a specification that defines set of registers and data structures for controlling the USB Type-C ports. It's designed for systems where an embedded controller (EC) is in charge of the USB Type-C PHY or USB Power Delivery controller. It is designed for systems with EC, but it is not limited to them, and for example some USB Power Delivery controllers will use it as their direct control interface. With UCSI the EC (or USB PD controller) acts as the port manager, implementing all USB Type-C and Power Delivery state machines. The OS can use the interfaces for reading the status of the ports and controlling basic operations like role swapping. The UCSI specification highlights the fact that it does not define the interface method (PCI/I2C/ACPI/etc.). Therefore the driver is implemented as library and every supported interface method needs its own driver. Driver for ACPI is provided in separate patch following this one. The initial driver includes support for all required features from UCSI specification version 1.0 (getting connector capabilities and status, and support for power and data role swapping), but none of the optional UCSI features (alternate modes, power source capabilities, and cable capabilities). Signed-off-by: Heikki Krogerus <heikki.krogerus@linux.intel.com> Reviewed-by: Guenter Roeck <linux@roeck-us.net> Signed-off-by: Greg Kroah-Hartman <gregkh@linuxfoundation.org>
2017-06-16 02:21:24 -06:00
#ifndef __DRIVER_USB_TYPEC_UCSI_H
#define __DRIVER_USB_TYPEC_UCSI_H
#include <linux/bitops.h>
#include <linux/device.h>
usb: typec: Add support for UCSI interface UCSI - USB Type-C Connector System Software Interface - is a specification that defines set of registers and data structures for controlling the USB Type-C ports. It's designed for systems where an embedded controller (EC) is in charge of the USB Type-C PHY or USB Power Delivery controller. It is designed for systems with EC, but it is not limited to them, and for example some USB Power Delivery controllers will use it as their direct control interface. With UCSI the EC (or USB PD controller) acts as the port manager, implementing all USB Type-C and Power Delivery state machines. The OS can use the interfaces for reading the status of the ports and controlling basic operations like role swapping. The UCSI specification highlights the fact that it does not define the interface method (PCI/I2C/ACPI/etc.). Therefore the driver is implemented as library and every supported interface method needs its own driver. Driver for ACPI is provided in separate patch following this one. The initial driver includes support for all required features from UCSI specification version 1.0 (getting connector capabilities and status, and support for power and data role swapping), but none of the optional UCSI features (alternate modes, power source capabilities, and cable capabilities). Signed-off-by: Heikki Krogerus <heikki.krogerus@linux.intel.com> Reviewed-by: Guenter Roeck <linux@roeck-us.net> Signed-off-by: Greg Kroah-Hartman <gregkh@linuxfoundation.org>
2017-06-16 02:21:24 -06:00
#include <linux/types.h>
#include <linux/usb/typec.h>
usb: typec: Add support for UCSI interface UCSI - USB Type-C Connector System Software Interface - is a specification that defines set of registers and data structures for controlling the USB Type-C ports. It's designed for systems where an embedded controller (EC) is in charge of the USB Type-C PHY or USB Power Delivery controller. It is designed for systems with EC, but it is not limited to them, and for example some USB Power Delivery controllers will use it as their direct control interface. With UCSI the EC (or USB PD controller) acts as the port manager, implementing all USB Type-C and Power Delivery state machines. The OS can use the interfaces for reading the status of the ports and controlling basic operations like role swapping. The UCSI specification highlights the fact that it does not define the interface method (PCI/I2C/ACPI/etc.). Therefore the driver is implemented as library and every supported interface method needs its own driver. Driver for ACPI is provided in separate patch following this one. The initial driver includes support for all required features from UCSI specification version 1.0 (getting connector capabilities and status, and support for power and data role swapping), but none of the optional UCSI features (alternate modes, power source capabilities, and cable capabilities). Signed-off-by: Heikki Krogerus <heikki.krogerus@linux.intel.com> Reviewed-by: Guenter Roeck <linux@roeck-us.net> Signed-off-by: Greg Kroah-Hartman <gregkh@linuxfoundation.org>
2017-06-16 02:21:24 -06:00
/* -------------------------------------------------------------------------- */
/* Command Status and Connector Change Indication (CCI) data structure */
struct ucsi_cci {
u8:1; /* reserved */
u8 connector_change:7;
u8 data_length;
u16:9; /* reserved */
u16 not_supported:1;
u16 cancel_complete:1;
u16 reset_complete:1;
u16 busy:1;
u16 ack_complete:1;
u16 error:1;
u16 cmd_complete:1;
} __packed;
/* Default fields in CONTROL data structure */
struct ucsi_command {
u8 cmd;
u8 length;
u64 data:48;
} __packed;
/* ACK Command structure */
struct ucsi_ack_cmd {
u8 cmd;
u8 length;
u8 cci_ack:1;
u8 cmd_ack:1;
u8:6; /* reserved */
} __packed;
/* Connector Reset Command structure */
struct ucsi_con_rst {
u8 cmd;
u8 length;
u8 con_num:7;
u8 hard_reset:1;
} __packed;
/* Set USB Operation Mode Command structure */
struct ucsi_uor_cmd {
u8 cmd;
u8 length;
u16 con_num:7;
u16 role:3;
#define UCSI_UOR_ROLE_DFP BIT(0)
#define UCSI_UOR_ROLE_UFP BIT(1)
#define UCSI_UOR_ROLE_DRP BIT(2)
u16:6; /* reserved */
} __packed;
/* Get Alternate Modes Command structure */
struct ucsi_altmode_cmd {
u8 cmd;
u8 length;
u8 recipient;
#define UCSI_RECIPIENT_CON 0
#define UCSI_RECIPIENT_SOP 1
#define UCSI_RECIPIENT_SOP_P 2
#define UCSI_RECIPIENT_SOP_PP 3
u8 con_num;
u8 offset;
u8 num_altmodes;
} __packed;
usb: typec: Add support for UCSI interface UCSI - USB Type-C Connector System Software Interface - is a specification that defines set of registers and data structures for controlling the USB Type-C ports. It's designed for systems where an embedded controller (EC) is in charge of the USB Type-C PHY or USB Power Delivery controller. It is designed for systems with EC, but it is not limited to them, and for example some USB Power Delivery controllers will use it as their direct control interface. With UCSI the EC (or USB PD controller) acts as the port manager, implementing all USB Type-C and Power Delivery state machines. The OS can use the interfaces for reading the status of the ports and controlling basic operations like role swapping. The UCSI specification highlights the fact that it does not define the interface method (PCI/I2C/ACPI/etc.). Therefore the driver is implemented as library and every supported interface method needs its own driver. Driver for ACPI is provided in separate patch following this one. The initial driver includes support for all required features from UCSI specification version 1.0 (getting connector capabilities and status, and support for power and data role swapping), but none of the optional UCSI features (alternate modes, power source capabilities, and cable capabilities). Signed-off-by: Heikki Krogerus <heikki.krogerus@linux.intel.com> Reviewed-by: Guenter Roeck <linux@roeck-us.net> Signed-off-by: Greg Kroah-Hartman <gregkh@linuxfoundation.org>
2017-06-16 02:21:24 -06:00
struct ucsi_control {
union {
u64 raw_cmd;
struct ucsi_command cmd;
struct ucsi_uor_cmd uor;
struct ucsi_ack_cmd ack;
struct ucsi_con_rst con_rst;
struct ucsi_altmode_cmd alt;
usb: typec: Add support for UCSI interface UCSI - USB Type-C Connector System Software Interface - is a specification that defines set of registers and data structures for controlling the USB Type-C ports. It's designed for systems where an embedded controller (EC) is in charge of the USB Type-C PHY or USB Power Delivery controller. It is designed for systems with EC, but it is not limited to them, and for example some USB Power Delivery controllers will use it as their direct control interface. With UCSI the EC (or USB PD controller) acts as the port manager, implementing all USB Type-C and Power Delivery state machines. The OS can use the interfaces for reading the status of the ports and controlling basic operations like role swapping. The UCSI specification highlights the fact that it does not define the interface method (PCI/I2C/ACPI/etc.). Therefore the driver is implemented as library and every supported interface method needs its own driver. Driver for ACPI is provided in separate patch following this one. The initial driver includes support for all required features from UCSI specification version 1.0 (getting connector capabilities and status, and support for power and data role swapping), but none of the optional UCSI features (alternate modes, power source capabilities, and cable capabilities). Signed-off-by: Heikki Krogerus <heikki.krogerus@linux.intel.com> Reviewed-by: Guenter Roeck <linux@roeck-us.net> Signed-off-by: Greg Kroah-Hartman <gregkh@linuxfoundation.org>
2017-06-16 02:21:24 -06:00
};
};
#define __UCSI_CMD(_ctrl_, _cmd_) \
{ \
(_ctrl_).raw_cmd = 0; \
(_ctrl_).cmd.cmd = _cmd_; \
}
/* Helper for preparing ucsi_control for CONNECTOR_RESET command. */
#define UCSI_CMD_CONNECTOR_RESET(_ctrl_, _con_, _hard_) \
{ \
__UCSI_CMD(_ctrl_, UCSI_CONNECTOR_RESET) \
(_ctrl_).con_rst.con_num = (_con_)->num; \
(_ctrl_).con_rst.hard_reset = _hard_; \
}
/* Helper for preparing ucsi_control for ACK_CC_CI command. */
#define UCSI_CMD_ACK(_ctrl_, _ack_) \
{ \
__UCSI_CMD(_ctrl_, UCSI_ACK_CC_CI) \
(_ctrl_).ack.cci_ack = ((_ack_) == UCSI_ACK_EVENT); \
(_ctrl_).ack.cmd_ack = ((_ack_) == UCSI_ACK_CMD); \
}
/* Helper for preparing ucsi_control for SET_NOTIFY_ENABLE command. */
#define UCSI_CMD_SET_NTFY_ENABLE(_ctrl_, _ntfys_) \
{ \
__UCSI_CMD(_ctrl_, UCSI_SET_NOTIFICATION_ENABLE) \
(_ctrl_).cmd.data = _ntfys_; \
}
/* Helper for preparing ucsi_control for GET_CAPABILITY command. */
#define UCSI_CMD_GET_CAPABILITY(_ctrl_) \
{ \
__UCSI_CMD(_ctrl_, UCSI_GET_CAPABILITY) \
}
/* Helper for preparing ucsi_control for GET_CONNECTOR_CAPABILITY command. */
#define UCSI_CMD_GET_CONNECTOR_CAPABILITY(_ctrl_, _con_) \
{ \
__UCSI_CMD(_ctrl_, UCSI_GET_CONNECTOR_CAPABILITY) \
(_ctrl_).cmd.data = _con_; \
}
/* Helper for preparing ucsi_control for GET_ALTERNATE_MODES command. */
#define UCSI_CMD_GET_ALTERNATE_MODES(_ctrl_, _r_, _con_num_, _o_, _num_)\
{ \
__UCSI_CMD((_ctrl_), UCSI_GET_ALTERNATE_MODES) \
_ctrl_.alt.recipient = (_r_); \
_ctrl_.alt.con_num = (_con_num_); \
_ctrl_.alt.offset = (_o_); \
_ctrl_.alt.num_altmodes = (_num_) - 1; \
}
/* Helper for preparing ucsi_control for GET_CAM_SUPPORTED command. */
#define UCSI_CMD_GET_CAM_SUPPORTED(_ctrl_, _con_) \
{ \
__UCSI_CMD((_ctrl_), UCSI_GET_CAM_SUPPORTED) \
_ctrl_.cmd.data = (_con_); \
}
/* Helper for preparing ucsi_control for GET_CAM_SUPPORTED command. */
#define UCSI_CMD_GET_CURRENT_CAM(_ctrl_, _con_) \
{ \
__UCSI_CMD((_ctrl_), UCSI_GET_CURRENT_CAM) \
_ctrl_.cmd.data = (_con_); \
}
usb: typec: Add support for UCSI interface UCSI - USB Type-C Connector System Software Interface - is a specification that defines set of registers and data structures for controlling the USB Type-C ports. It's designed for systems where an embedded controller (EC) is in charge of the USB Type-C PHY or USB Power Delivery controller. It is designed for systems with EC, but it is not limited to them, and for example some USB Power Delivery controllers will use it as their direct control interface. With UCSI the EC (or USB PD controller) acts as the port manager, implementing all USB Type-C and Power Delivery state machines. The OS can use the interfaces for reading the status of the ports and controlling basic operations like role swapping. The UCSI specification highlights the fact that it does not define the interface method (PCI/I2C/ACPI/etc.). Therefore the driver is implemented as library and every supported interface method needs its own driver. Driver for ACPI is provided in separate patch following this one. The initial driver includes support for all required features from UCSI specification version 1.0 (getting connector capabilities and status, and support for power and data role swapping), but none of the optional UCSI features (alternate modes, power source capabilities, and cable capabilities). Signed-off-by: Heikki Krogerus <heikki.krogerus@linux.intel.com> Reviewed-by: Guenter Roeck <linux@roeck-us.net> Signed-off-by: Greg Kroah-Hartman <gregkh@linuxfoundation.org>
2017-06-16 02:21:24 -06:00
/* Helper for preparing ucsi_control for GET_CONNECTOR_STATUS command. */
#define UCSI_CMD_GET_CONNECTOR_STATUS(_ctrl_, _con_) \
{ \
__UCSI_CMD(_ctrl_, UCSI_GET_CONNECTOR_STATUS) \
(_ctrl_).cmd.data = _con_; \
}
#define __UCSI_ROLE(_ctrl_, _cmd_, _con_num_) \
{ \
__UCSI_CMD(_ctrl_, _cmd_) \
(_ctrl_).uor.con_num = _con_num_; \
(_ctrl_).uor.role = UCSI_UOR_ROLE_DRP; \
}
/* Helper for preparing ucsi_control for SET_UOR command. */
#define UCSI_CMD_SET_UOR(_ctrl_, _con_, _role_) \
{ \
__UCSI_ROLE(_ctrl_, UCSI_SET_UOR, (_con_)->num) \
(_ctrl_).uor.role |= (_role_) == TYPEC_HOST ? UCSI_UOR_ROLE_DFP : \
UCSI_UOR_ROLE_UFP; \
}
/* Helper for preparing ucsi_control for SET_PDR command. */
#define UCSI_CMD_SET_PDR(_ctrl_, _con_, _role_) \
{ \
__UCSI_ROLE(_ctrl_, UCSI_SET_PDR, (_con_)->num) \
(_ctrl_).uor.role |= (_role_) == TYPEC_SOURCE ? UCSI_UOR_ROLE_DFP : \
UCSI_UOR_ROLE_UFP; \
}
/* Commands */
#define UCSI_PPM_RESET 0x01
#define UCSI_CANCEL 0x02
#define UCSI_CONNECTOR_RESET 0x03
#define UCSI_ACK_CC_CI 0x04
#define UCSI_SET_NOTIFICATION_ENABLE 0x05
#define UCSI_GET_CAPABILITY 0x06
#define UCSI_GET_CONNECTOR_CAPABILITY 0x07
#define UCSI_SET_UOM 0x08
#define UCSI_SET_UOR 0x09
#define UCSI_SET_PDM 0x0a
#define UCSI_SET_PDR 0x0b
#define UCSI_GET_ALTERNATE_MODES 0x0c
#define UCSI_GET_CAM_SUPPORTED 0x0d
#define UCSI_GET_CURRENT_CAM 0x0e
#define UCSI_SET_NEW_CAM 0x0f
#define UCSI_GET_PDOS 0x10
#define UCSI_GET_CABLE_PROPERTY 0x11
#define UCSI_GET_CONNECTOR_STATUS 0x12
#define UCSI_GET_ERROR_STATUS 0x13
/* ACK_CC_CI commands */
#define UCSI_ACK_EVENT 1
#define UCSI_ACK_CMD 2
/* Bits for SET_NOTIFICATION_ENABLE command */
#define UCSI_ENABLE_NTFY_CMD_COMPLETE BIT(0)
#define UCSI_ENABLE_NTFY_EXT_PWR_SRC_CHANGE BIT(1)
#define UCSI_ENABLE_NTFY_PWR_OPMODE_CHANGE BIT(2)
#define UCSI_ENABLE_NTFY_CAP_CHANGE BIT(5)
#define UCSI_ENABLE_NTFY_PWR_LEVEL_CHANGE BIT(6)
#define UCSI_ENABLE_NTFY_PD_RESET_COMPLETE BIT(7)
#define UCSI_ENABLE_NTFY_CAM_CHANGE BIT(8)
#define UCSI_ENABLE_NTFY_BAT_STATUS_CHANGE BIT(9)
#define UCSI_ENABLE_NTFY_PARTNER_CHANGE BIT(11)
#define UCSI_ENABLE_NTFY_PWR_DIR_CHANGE BIT(12)
#define UCSI_ENABLE_NTFY_CONNECTOR_CHANGE BIT(14)
#define UCSI_ENABLE_NTFY_ERROR BIT(15)
#define UCSI_ENABLE_NTFY_ALL 0xdbe7
/* Error information returned by PPM in response to GET_ERROR_STATUS command. */
#define UCSI_ERROR_UNREGONIZED_CMD BIT(0)
#define UCSI_ERROR_INVALID_CON_NUM BIT(1)
#define UCSI_ERROR_INVALID_CMD_ARGUMENT BIT(2)
#define UCSI_ERROR_INCOMPATIBLE_PARTNER BIT(3)
#define UCSI_ERROR_CC_COMMUNICATION_ERR BIT(4)
#define UCSI_ERROR_DEAD_BATTERY BIT(5)
#define UCSI_ERROR_CONTRACT_NEGOTIATION_FAIL BIT(6)
/* Data structure filled by PPM in response to GET_CAPABILITY command. */
struct ucsi_capability {
u32 attributes;
#define UCSI_CAP_ATTR_DISABLE_STATE BIT(0)
#define UCSI_CAP_ATTR_BATTERY_CHARGING BIT(1)
#define UCSI_CAP_ATTR_USB_PD BIT(2)
#define UCSI_CAP_ATTR_TYPEC_CURRENT BIT(6)
#define UCSI_CAP_ATTR_POWER_AC_SUPPLY BIT(8)
#define UCSI_CAP_ATTR_POWER_OTHER BIT(10)
#define UCSI_CAP_ATTR_POWER_VBUS BIT(14)
u32 num_connectors:8;
u32 features:24;
#define UCSI_CAP_SET_UOM BIT(0)
#define UCSI_CAP_SET_PDM BIT(1)
#define UCSI_CAP_ALT_MODE_DETAILS BIT(2)
#define UCSI_CAP_ALT_MODE_OVERRIDE BIT(3)
#define UCSI_CAP_PDO_DETAILS BIT(4)
#define UCSI_CAP_CABLE_DETAILS BIT(5)
#define UCSI_CAP_EXT_SUPPLY_NOTIFICATIONS BIT(6)
#define UCSI_CAP_PD_RESET BIT(7)
u8 num_alt_modes;
u8 reserved;
u16 bc_version;
u16 pd_version;
u16 typec_version;
} __packed;
/* Data structure filled by PPM in response to GET_CONNECTOR_CAPABILITY cmd. */
struct ucsi_connector_capability {
u8 op_mode;
#define UCSI_CONCAP_OPMODE_DFP BIT(0)
#define UCSI_CONCAP_OPMODE_UFP BIT(1)
#define UCSI_CONCAP_OPMODE_DRP BIT(2)
#define UCSI_CONCAP_OPMODE_AUDIO_ACCESSORY BIT(3)
#define UCSI_CONCAP_OPMODE_DEBUG_ACCESSORY BIT(4)
#define UCSI_CONCAP_OPMODE_USB2 BIT(5)
#define UCSI_CONCAP_OPMODE_USB3 BIT(6)
#define UCSI_CONCAP_OPMODE_ALT_MODE BIT(7)
u8 provider:1;
u8 consumer:1;
u8:6; /* reserved */
} __packed;
struct ucsi_altmode {
u16 svid;
u32 mid;
} __packed;
/* Data structure filled by PPM in response to GET_CABLE_PROPERTY command. */
struct ucsi_cable_property {
u16 speed_supported;
u8 current_capability;
u8 vbus_in_cable:1;
u8 active_cable:1;
u8 directionality:1;
u8 plug_type:2;
#define UCSI_CABLE_PROPERTY_PLUG_TYPE_A 0
#define UCSI_CABLE_PROPERTY_PLUG_TYPE_B 1
#define UCSI_CABLE_PROPERTY_PLUG_TYPE_C 2
#define UCSI_CABLE_PROPERTY_PLUG_OTHER 3
u8 mode_support:1;
u8:2; /* reserved */
u8 latency:4;
u8:4; /* reserved */
} __packed;
/* Data structure filled by PPM in response to GET_CONNECTOR_STATUS command. */
struct ucsi_connector_status {
u16 change;
#define UCSI_CONSTAT_EXT_SUPPLY_CHANGE BIT(1)
#define UCSI_CONSTAT_POWER_OPMODE_CHANGE BIT(2)
#define UCSI_CONSTAT_PDOS_CHANGE BIT(5)
#define UCSI_CONSTAT_POWER_LEVEL_CHANGE BIT(6)
#define UCSI_CONSTAT_PD_RESET_COMPLETE BIT(7)
#define UCSI_CONSTAT_CAM_CHANGE BIT(8)
#define UCSI_CONSTAT_BC_CHANGE BIT(9)
#define UCSI_CONSTAT_PARTNER_CHANGE BIT(11)
#define UCSI_CONSTAT_POWER_DIR_CHANGE BIT(12)
#define UCSI_CONSTAT_CONNECT_CHANGE BIT(14)
#define UCSI_CONSTAT_ERROR BIT(15)
u16 pwr_op_mode:3;
#define UCSI_CONSTAT_PWR_OPMODE_NONE 0
#define UCSI_CONSTAT_PWR_OPMODE_DEFAULT 1
#define UCSI_CONSTAT_PWR_OPMODE_BC 2
#define UCSI_CONSTAT_PWR_OPMODE_PD 3
#define UCSI_CONSTAT_PWR_OPMODE_TYPEC1_5 4
#define UCSI_CONSTAT_PWR_OPMODE_TYPEC3_0 5
u16 connected:1;
u16 pwr_dir:1;
u16 partner_flags:8;
#define UCSI_CONSTAT_PARTNER_FLAG_USB BIT(0)
#define UCSI_CONSTAT_PARTNER_FLAG_ALT_MODE BIT(1)
u16 partner_type:3;
#define UCSI_CONSTAT_PARTNER_TYPE_DFP 1
#define UCSI_CONSTAT_PARTNER_TYPE_UFP 2
#define UCSI_CONSTAT_PARTNER_TYPE_CABLE 3 /* Powered Cable */
#define UCSI_CONSTAT_PARTNER_TYPE_CABLE_AND_UFP 4 /* Powered Cable */
#define UCSI_CONSTAT_PARTNER_TYPE_DEBUG 5
#define UCSI_CONSTAT_PARTNER_TYPE_AUDIO 6
u32 request_data_obj;
u8 bc_status:2;
#define UCSI_CONSTAT_BC_NOT_CHARGING 0
#define UCSI_CONSTAT_BC_NOMINAL_CHARGING 1
#define UCSI_CONSTAT_BC_SLOW_CHARGING 2
#define UCSI_CONSTAT_BC_TRICKLE_CHARGING 3
u8 provider_cap_limit_reason:4;
#define UCSI_CONSTAT_CAP_PWR_LOWERED 0
#define UCSI_CONSTAT_CAP_PWR_BUDGET_LIMIT 1
u8:2; /* reserved */
} __packed;
/* -------------------------------------------------------------------------- */
struct ucsi;
struct ucsi_data {
u16 version;
u16 reserved;
union {
u32 raw_cci;
struct ucsi_cci cci;
};
struct ucsi_control ctrl;
u32 message_in[4];
u32 message_out[4];
} __packed;
/*
* struct ucsi_ppm - Interface to UCSI Platform Policy Manager
* @data: memory location to the UCSI data structures
* @cmd: UCSI command execution routine
* @sync: Refresh UCSI mailbox (the data structures)
*/
struct ucsi_ppm {
struct ucsi_data *data;
int (*cmd)(struct ucsi_ppm *, struct ucsi_control *);
int (*sync)(struct ucsi_ppm *);
};
struct ucsi *ucsi_register_ppm(struct device *dev, struct ucsi_ppm *ppm);
void ucsi_unregister_ppm(struct ucsi *ucsi);
void ucsi_notify(struct ucsi *ucsi);
/* -------------------------------------------------------------------------- */
enum ucsi_status {
UCSI_IDLE = 0,
UCSI_BUSY,
UCSI_ERROR,
};
struct ucsi {
struct device *dev;
struct ucsi_ppm *ppm;
enum ucsi_status status;
struct completion complete;
struct ucsi_capability cap;
struct ucsi_connector *connector;
struct work_struct work;
/* PPM Communication lock */
struct mutex ppm_lock;
/* PPM communication flags */
unsigned long flags;
#define EVENT_PENDING 0
#define COMMAND_PENDING 1
#define ACK_PENDING 2
};
#define UCSI_MAX_SVID 5
#define UCSI_MAX_ALTMODES (UCSI_MAX_SVID * 6)
struct ucsi_connector {
int num;
struct ucsi *ucsi;
struct mutex lock; /* port lock */
struct work_struct work;
struct completion complete;
struct typec_port *port;
struct typec_partner *partner;
struct typec_altmode *port_altmode[UCSI_MAX_ALTMODES];
struct typec_altmode *partner_altmode[UCSI_MAX_ALTMODES];
struct typec_capability typec_cap;
struct ucsi_connector_status status;
struct ucsi_connector_capability cap;
};
int ucsi_send_command(struct ucsi *ucsi, struct ucsi_control *ctrl,
void *retval, size_t size);
void ucsi_altmode_update_active(struct ucsi_connector *con);
int ucsi_resume(struct ucsi *ucsi);
#if IS_ENABLED(CONFIG_TYPEC_DP_ALTMODE)
struct typec_altmode *
ucsi_register_displayport(struct ucsi_connector *con,
bool override, int offset,
struct typec_altmode_desc *desc);
void ucsi_displayport_remove_partner(struct typec_altmode *adev);
#else
static inline struct typec_altmode *
ucsi_register_displayport(struct ucsi_connector *con,
bool override, int offset,
struct typec_altmode_desc *desc)
{
return NULL;
}
static inline void
ucsi_displayport_remove_partner(struct typec_altmode *adev) { }
#endif /* CONFIG_TYPEC_DP_ALTMODE */
usb: typec: Add support for UCSI interface UCSI - USB Type-C Connector System Software Interface - is a specification that defines set of registers and data structures for controlling the USB Type-C ports. It's designed for systems where an embedded controller (EC) is in charge of the USB Type-C PHY or USB Power Delivery controller. It is designed for systems with EC, but it is not limited to them, and for example some USB Power Delivery controllers will use it as their direct control interface. With UCSI the EC (or USB PD controller) acts as the port manager, implementing all USB Type-C and Power Delivery state machines. The OS can use the interfaces for reading the status of the ports and controlling basic operations like role swapping. The UCSI specification highlights the fact that it does not define the interface method (PCI/I2C/ACPI/etc.). Therefore the driver is implemented as library and every supported interface method needs its own driver. Driver for ACPI is provided in separate patch following this one. The initial driver includes support for all required features from UCSI specification version 1.0 (getting connector capabilities and status, and support for power and data role swapping), but none of the optional UCSI features (alternate modes, power source capabilities, and cable capabilities). Signed-off-by: Heikki Krogerus <heikki.krogerus@linux.intel.com> Reviewed-by: Guenter Roeck <linux@roeck-us.net> Signed-off-by: Greg Kroah-Hartman <gregkh@linuxfoundation.org>
2017-06-16 02:21:24 -06:00
#endif /* __DRIVER_USB_TYPEC_UCSI_H */