linux/include/linux/extcon.h
<<
>>
Prefs
   1/*
   2 *  External connector (extcon) class driver
   3 *
   4 * Copyright (C) 2012 Samsung Electronics
   5 * Author: Donggeun Kim <dg77.kim@samsung.com>
   6 * Author: MyungJoo Ham <myungjoo.ham@samsung.com>
   7 *
   8 * based on switch class driver
   9 * Copyright (C) 2008 Google, Inc.
  10 * Author: Mike Lockwood <lockwood@android.com>
  11 *
  12 * This software is licensed under the terms of the GNU General Public
  13 * License version 2, as published by the Free Software Foundation, and
  14 * may be copied, distributed, and modified under those terms.
  15 *
  16 * This program is distributed in the hope that it will be useful,
  17 * but WITHOUT ANY WARRANTY; without even the implied warranty of
  18 * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE.  See the
  19 * GNU General Public License for more details.
  20 *
  21*/
  22
  23#ifndef __LINUX_EXTCON_H__
  24#define __LINUX_EXTCON_H__
  25
  26#include <linux/notifier.h>
  27
  28#define SUPPORTED_CABLE_MAX     32
  29#define CABLE_NAME_MAX          30
  30
  31/*
  32 * The standard cable name is to help support general notifier
  33 * and notifee device drivers to share the common names.
  34 * Please use standard cable names unless your notifier device has
  35 * a very unique and abnormal cable or
  36 * the cable type is supposed to be used with only one unique
  37 * pair of notifier/notifee devices.
  38 *
  39 * Please add any other "standard" cables used with extcon dev.
  40 *
  41 * You may add a dot and number to specify version or specification
  42 * of the specific cable if it is required. (e.g., "Fast-charger.18"
  43 * and "Fast-charger.10" for 1.8A and 1.0A chargers)
  44 * However, the notifee and notifier should be able to handle such
  45 * string and if the notifee can negotiate the protocol or idenify,
  46 * you don't need such convention. This convention is helpful when
  47 * notifier can distinguish but notifiee cannot.
  48 */
  49enum extcon_cable_name {
  50        EXTCON_USB = 0,
  51        EXTCON_USB_HOST,
  52        EXTCON_TA, /* Travel Adaptor */
  53        EXTCON_FAST_CHARGER,
  54        EXTCON_SLOW_CHARGER,
  55        EXTCON_CHARGE_DOWNSTREAM, /* Charging an external device */
  56        EXTCON_HDMI,
  57        EXTCON_MHL,
  58        EXTCON_DVI,
  59        EXTCON_VGA,
  60        EXTCON_DOCK,
  61        EXTCON_LINE_IN,
  62        EXTCON_LINE_OUT,
  63        EXTCON_MIC_IN,
  64        EXTCON_HEADPHONE_OUT,
  65        EXTCON_SPDIF_IN,
  66        EXTCON_SPDIF_OUT,
  67        EXTCON_VIDEO_IN,
  68        EXTCON_VIDEO_OUT,
  69        EXTCON_MECHANICAL,
  70};
  71extern const char *extcon_cable_name[];
  72
  73struct extcon_cable;
  74
  75/**
  76 * struct extcon_dev - An extcon device represents one external connector.
  77 * @name        The name of this extcon device. Parent device name is used
  78 *              if NULL.
  79 * @supported_cable     Array of supported cable name ending with NULL.
  80 *                      If supported_cable is NULL, cable name related APIs
  81 *                      are disabled.
  82 * @mutually_exclusive  Array of mutually exclusive set of cables that cannot
  83 *                      be attached simultaneously. The array should be
  84 *                      ending with NULL or be NULL (no mutually exclusive
  85 *                      cables). For example, if it is { 0x7, 0x30, 0}, then,
  86 *                      {0, 1}, {0, 1, 2}, {0, 2}, {1, 2}, or {4, 5} cannot
  87 *                      be attached simulataneously. {0x7, 0} is equivalent to
  88 *                      {0x3, 0x6, 0x5, 0}. If it is {0xFFFFFFFF, 0}, there
  89 *                      can be no simultaneous connections.
  90 * @print_name  An optional callback to override the method to print the
  91 *              name of the extcon device.
  92 * @print_state An optional callback to override the method to print the
  93 *              status of the extcon device.
  94 * @dev         Device of this extcon. Do not provide at register-time.
  95 * @state       Attach/detach state of this extcon. Do not provide at
  96 *              register-time
  97 * @nh  Notifier for the state change events from this extcon
  98 * @entry       To support list of extcon devices so that uses can search
  99 *              for extcon devices based on the extcon name.
 100 * @lock
 101 * @max_supported       Internal value to store the number of cables.
 102 * @extcon_dev_type     Device_type struct to provide attribute_groups
 103 *                      customized for each extcon device.
 104 * @cables      Sysfs subdirectories. Each represents one cable.
 105 *
 106 * In most cases, users only need to provide "User initializing data" of
 107 * this struct when registering an extcon. In some exceptional cases,
 108 * optional callbacks may be needed. However, the values in "internal data"
 109 * are overwritten by register function.
 110 */
 111struct extcon_dev {
 112        /* --- Optional user initializing data --- */
 113        const char      *name;
 114        const char **supported_cable;
 115        const u32       *mutually_exclusive;
 116
 117        /* --- Optional callbacks to override class functions --- */
 118        ssize_t (*print_name)(struct extcon_dev *edev, char *buf);
 119        ssize_t (*print_state)(struct extcon_dev *edev, char *buf);
 120
 121        /* --- Internal data. Please do not set. --- */
 122        struct device   *dev;
 123        u32             state;
 124        struct raw_notifier_head nh;
 125        struct list_head entry;
 126        spinlock_t lock; /* could be called by irq handler */
 127        int max_supported;
 128
 129        /* /sys/class/extcon/.../cable.n/... */
 130        struct device_type extcon_dev_type;
 131        struct extcon_cable *cables;
 132        /* /sys/class/extcon/.../mutually_exclusive/... */
 133        struct attribute_group attr_g_muex;
 134        struct attribute **attrs_muex;
 135        struct device_attribute *d_attrs_muex;
 136};
 137
 138/**
 139 * struct extcon_cable  - An internal data for each cable of extcon device.
 140 * @edev        The extcon device
 141 * @cable_index Index of this cable in the edev
 142 * @attr_g      Attribute group for the cable
 143 * @attr_name   "name" sysfs entry
 144 * @attr_state  "state" sysfs entry
 145 * @attrs       Array pointing to attr_name and attr_state for attr_g
 146 */
 147struct extcon_cable {
 148        struct extcon_dev *edev;
 149        int cable_index;
 150
 151        struct attribute_group attr_g;
 152        struct device_attribute attr_name;
 153        struct device_attribute attr_state;
 154
 155        struct attribute *attrs[3]; /* to be fed to attr_g.attrs */
 156};
 157
 158/**
 159 * struct extcon_specific_cable_nb - An internal data for
 160 *                              extcon_register_interest().
 161 * @internal_nb a notifier block bridging extcon notifier and cable notifier.
 162 * @user_nb     user provided notifier block for events from a specific cable.
 163 * @cable_index the target cable.
 164 * @edev        the target extcon device.
 165 * @previous_value      the saved previous event value.
 166 */
 167struct extcon_specific_cable_nb {
 168        struct notifier_block internal_nb;
 169        struct notifier_block *user_nb;
 170        int cable_index;
 171        struct extcon_dev *edev;
 172        unsigned long previous_value;
 173};
 174
 175#if IS_ENABLED(CONFIG_EXTCON)
 176
 177/*
 178 * Following APIs are for notifiers or configurations.
 179 * Notifiers are the external port and connection devices.
 180 */
 181extern int extcon_dev_register(struct extcon_dev *edev, struct device *dev);
 182extern void extcon_dev_unregister(struct extcon_dev *edev);
 183extern struct extcon_dev *extcon_get_extcon_dev(const char *extcon_name);
 184
 185/*
 186 * get/set/update_state access the 32b encoded state value, which represents
 187 * states of all possible cables of the multistate port. For example, if one
 188 * calls extcon_set_state(edev, 0x7), it may mean that all the three cables
 189 * are attached to the port.
 190 */
 191static inline u32 extcon_get_state(struct extcon_dev *edev)
 192{
 193        return edev->state;
 194}
 195
 196extern int extcon_set_state(struct extcon_dev *edev, u32 state);
 197extern int extcon_update_state(struct extcon_dev *edev, u32 mask, u32 state);
 198
 199/*
 200 * get/set_cable_state access each bit of the 32b encoded state value.
 201 * They are used to access the status of each cable based on the cable_name
 202 * or cable_index, which is retrived by extcon_find_cable_index
 203 */
 204extern int extcon_find_cable_index(struct extcon_dev *sdev,
 205                                   const char *cable_name);
 206extern int extcon_get_cable_state_(struct extcon_dev *edev, int cable_index);
 207extern int extcon_set_cable_state_(struct extcon_dev *edev, int cable_index,
 208                                   bool cable_state);
 209
 210extern int extcon_get_cable_state(struct extcon_dev *edev,
 211                                  const char *cable_name);
 212extern int extcon_set_cable_state(struct extcon_dev *edev,
 213                                  const char *cable_name, bool cable_state);
 214
 215/*
 216 * Following APIs are for notifiees (those who want to be notified)
 217 * to register a callback for events from a specific cable of the extcon.
 218 * Notifiees are the connected device drivers wanting to get notified by
 219 * a specific external port of a connection device.
 220 */
 221extern int extcon_register_interest(struct extcon_specific_cable_nb *obj,
 222                                    const char *extcon_name,
 223                                    const char *cable_name,
 224                                    struct notifier_block *nb);
 225extern int extcon_unregister_interest(struct extcon_specific_cable_nb *nb);
 226
 227/*
 228 * Following APIs are to monitor every action of a notifier.
 229 * Registerer gets notified for every external port of a connection device.
 230 * Probably this could be used to debug an action of notifier; however,
 231 * we do not recommend to use this at normal 'notifiee' device drivers who
 232 * want to be notified by a specific external port of the notifier.
 233 */
 234extern int extcon_register_notifier(struct extcon_dev *edev,
 235                                    struct notifier_block *nb);
 236extern int extcon_unregister_notifier(struct extcon_dev *edev,
 237                                      struct notifier_block *nb);
 238#else /* CONFIG_EXTCON */
 239static inline int extcon_dev_register(struct extcon_dev *edev,
 240                                      struct device *dev)
 241{
 242        return 0;
 243}
 244
 245static inline void extcon_dev_unregister(struct extcon_dev *edev) { }
 246
 247static inline u32 extcon_get_state(struct extcon_dev *edev)
 248{
 249        return 0;
 250}
 251
 252static inline int extcon_set_state(struct extcon_dev *edev, u32 state)
 253{
 254        return 0;
 255}
 256
 257static inline int extcon_update_state(struct extcon_dev *edev, u32 mask,
 258                                       u32 state)
 259{
 260        return 0;
 261}
 262
 263static inline int extcon_find_cable_index(struct extcon_dev *edev,
 264                                          const char *cable_name)
 265{
 266        return 0;
 267}
 268
 269static inline int extcon_get_cable_state_(struct extcon_dev *edev,
 270                                          int cable_index)
 271{
 272        return 0;
 273}
 274
 275static inline int extcon_set_cable_state_(struct extcon_dev *edev,
 276                                          int cable_index, bool cable_state)
 277{
 278        return 0;
 279}
 280
 281static inline int extcon_get_cable_state(struct extcon_dev *edev,
 282                        const char *cable_name)
 283{
 284        return 0;
 285}
 286
 287static inline int extcon_set_cable_state(struct extcon_dev *edev,
 288                        const char *cable_name, int state)
 289{
 290        return 0;
 291}
 292
 293static inline struct extcon_dev *extcon_get_extcon_dev(const char *extcon_name)
 294{
 295        return NULL;
 296}
 297
 298static inline int extcon_register_notifier(struct extcon_dev *edev,
 299                                           struct notifier_block *nb)
 300{
 301        return 0;
 302}
 303
 304static inline int extcon_unregister_notifier(struct extcon_dev *edev,
 305                                             struct notifier_block *nb)
 306{
 307        return 0;
 308}
 309
 310static inline int extcon_register_interest(struct extcon_specific_cable_nb *obj,
 311                                           const char *extcon_name,
 312                                           const char *cable_name,
 313                                           struct notifier_block *nb)
 314{
 315        return 0;
 316}
 317
 318static inline int extcon_unregister_interest(struct extcon_specific_cable_nb
 319                                                    *obj)
 320{
 321        return 0;
 322}
 323#endif /* CONFIG_EXTCON */
 324#endif /* __LINUX_EXTCON_H__ */
 325
lxr.linux.no kindly hosted by Redpill Linpro AS, provider of Linux consulting and operations services since 1995.