File Index
Files and directories
Sign in
FILE

pd.c

File preview with syntax highlighting.

linux-6.19.14/drivers/usb/typec/pd.c C
  1// SPDX-License-Identifier: GPL-2.0
  2/*
  3 * USB Power Delivery sysfs entries
  4 *
  5 * Copyright (C) 2022, Intel Corporation
  6 * Author: Heikki Krogerus <heikki.krogerus@linux.intel.com>
  7 */
  8
  9#include <linux/slab.h>
 10#include <linux/usb/pd.h>
 11
 12#include "pd.h"
 13
 14static DEFINE_IDA(pd_ida);
 15
 16static struct class pd_class = {
 17	.name = "usb_power_delivery",
 18};
 19
 20#define to_pdo(o) container_of(o, struct pdo, dev)
 21
 22struct pdo {
 23	struct device dev;
 24	int object_position;
 25	u32 pdo;
 26};
 27
 28static void pdo_release(struct device *dev)
 29{
 30	kfree(to_pdo(dev));
 31}
 32
 33/* -------------------------------------------------------------------------- */
 34/* Fixed Supply */
 35
 36static ssize_t
 37dual_role_power_show(struct device *dev, struct device_attribute *attr, char *buf)
 38{
 39	return sysfs_emit(buf, "%u\n", !!(to_pdo(dev)->pdo & PDO_FIXED_DUAL_ROLE));
 40}
 41static DEVICE_ATTR_RO(dual_role_power);
 42
 43static ssize_t
 44usb_suspend_supported_show(struct device *dev, struct device_attribute *attr, char *buf)
 45{
 46	return sysfs_emit(buf, "%u\n", !!(to_pdo(dev)->pdo & PDO_FIXED_SUSPEND));
 47}
 48static DEVICE_ATTR_RO(usb_suspend_supported);
 49
 50static ssize_t
 51higher_capability_show(struct device *dev, struct device_attribute *attr, char *buf)
 52{
 53	return sysfs_emit(buf, "%u\n", !!(to_pdo(dev)->pdo & PDO_FIXED_HIGHER_CAP));
 54}
 55static DEVICE_ATTR_RO(higher_capability);
 56
 57static ssize_t
 58unconstrained_power_show(struct device *dev, struct device_attribute *attr, char *buf)
 59{
 60	return sysfs_emit(buf, "%u\n", !!(to_pdo(dev)->pdo & PDO_FIXED_EXTPOWER));
 61}
 62static DEVICE_ATTR_RO(unconstrained_power);
 63
 64static ssize_t
 65usb_communication_capable_show(struct device *dev, struct device_attribute *attr, char *buf)
 66{
 67	return sysfs_emit(buf, "%u\n", !!(to_pdo(dev)->pdo & PDO_FIXED_USB_COMM));
 68}
 69static DEVICE_ATTR_RO(usb_communication_capable);
 70
 71static ssize_t
 72dual_role_data_show(struct device *dev, struct device_attribute *attr, char *buf)
 73{
 74	return sysfs_emit(buf, "%u\n", !!(to_pdo(dev)->pdo & PDO_FIXED_DATA_SWAP));
 75}
 76static DEVICE_ATTR_RO(dual_role_data);
 77
 78static ssize_t
 79unchunked_extended_messages_supported_show(struct device *dev,
 80					   struct device_attribute *attr, char *buf)
 81{
 82	return sysfs_emit(buf, "%u\n", !!(to_pdo(dev)->pdo & PDO_FIXED_UNCHUNK_EXT));
 83}
 84static DEVICE_ATTR_RO(unchunked_extended_messages_supported);
 85
 86static ssize_t
 87peak_current_show(struct device *dev, struct device_attribute *attr, char *buf)
 88{
 89	return sysfs_emit(buf, "%u\n", (to_pdo(dev)->pdo >> PDO_FIXED_PEAK_CURR_SHIFT) & 3);
 90}
 91static DEVICE_ATTR_RO(peak_current);
 92
 93static ssize_t
 94fast_role_swap_current_show(struct device *dev, struct device_attribute *attr, char *buf)
 95{
 96	return sysfs_emit(buf, "%u\n", (to_pdo(dev)->pdo >> PDO_FIXED_FRS_CURR_SHIFT) & 3);
 97}
 98static DEVICE_ATTR_RO(fast_role_swap_current);
 99
100static ssize_t voltage_show(struct device *dev, struct device_attribute *attr, char *buf)
101{
102	return sysfs_emit(buf, "%umV\n", pdo_fixed_voltage(to_pdo(dev)->pdo));
103}
104static DEVICE_ATTR_RO(voltage);
105
106/* Shared with Variable supplies, both source and sink */
107static ssize_t current_show(struct device *dev, struct device_attribute *attr, char *buf)
108{
109	return sysfs_emit(buf, "%umA\n", pdo_max_current(to_pdo(dev)->pdo));
110}
111
112/* Shared with Variable type supplies */
113static struct device_attribute maximum_current_attr = {
114	.attr = {
115		.name = "maximum_current",
116		.mode = 0444,
117	},
118	.show = current_show,
119};
120
121static struct device_attribute operational_current_attr = {
122	.attr = {
123		.name = "operational_current",
124		.mode = 0444,
125	},
126	.show = current_show,
127};
128
129static struct attribute *source_fixed_supply_attrs[] = {
130	&dev_attr_dual_role_power.attr,
131	&dev_attr_usb_suspend_supported.attr,
132	&dev_attr_unconstrained_power.attr,
133	&dev_attr_usb_communication_capable.attr,
134	&dev_attr_dual_role_data.attr,
135	&dev_attr_unchunked_extended_messages_supported.attr,
136	&dev_attr_peak_current.attr,
137	&dev_attr_voltage.attr,
138	&maximum_current_attr.attr,
139	NULL
140};
141
142static umode_t fixed_attr_is_visible(struct kobject *kobj, struct attribute *attr, int n)
143{
144	if (to_pdo(kobj_to_dev(kobj))->object_position &&
145	    attr != &dev_attr_peak_current.attr &&
146	    attr != &dev_attr_voltage.attr &&
147	    attr != &maximum_current_attr.attr &&
148	    attr != &operational_current_attr.attr)
149		return 0;
150
151	return attr->mode;
152}
153
154static const struct attribute_group source_fixed_supply_group = {
155	.is_visible = fixed_attr_is_visible,
156	.attrs = source_fixed_supply_attrs,
157};
158__ATTRIBUTE_GROUPS(source_fixed_supply);
159
160static const struct device_type source_fixed_supply_type = {
161	.name = "pdo",
162	.release = pdo_release,
163	.groups = source_fixed_supply_groups,
164};
165
166static struct attribute *sink_fixed_supply_attrs[] = {
167	&dev_attr_dual_role_power.attr,
168	&dev_attr_higher_capability.attr,
169	&dev_attr_unconstrained_power.attr,
170	&dev_attr_usb_communication_capable.attr,
171	&dev_attr_dual_role_data.attr,
172	&dev_attr_unchunked_extended_messages_supported.attr,
173	&dev_attr_fast_role_swap_current.attr,
174	&dev_attr_voltage.attr,
175	&operational_current_attr.attr,
176	NULL
177};
178
179static const struct attribute_group sink_fixed_supply_group = {
180	.is_visible = fixed_attr_is_visible,
181	.attrs = sink_fixed_supply_attrs,
182};
183__ATTRIBUTE_GROUPS(sink_fixed_supply);
184
185static const struct device_type sink_fixed_supply_type = {
186	.name = "pdo",
187	.release = pdo_release,
188	.groups = sink_fixed_supply_groups,
189};
190
191/* -------------------------------------------------------------------------- */
192/* Variable Supply */
193
194static ssize_t
195maximum_voltage_show(struct device *dev, struct device_attribute *attr, char *buf)
196{
197	return sysfs_emit(buf, "%umV\n", pdo_max_voltage(to_pdo(dev)->pdo));
198}
199static DEVICE_ATTR_RO(maximum_voltage);
200
201static ssize_t
202minimum_voltage_show(struct device *dev, struct device_attribute *attr, char *buf)
203{
204	return sysfs_emit(buf, "%umV\n", pdo_min_voltage(to_pdo(dev)->pdo));
205}
206static DEVICE_ATTR_RO(minimum_voltage);
207
208static struct attribute *source_variable_supply_attrs[] = {
209	&dev_attr_maximum_voltage.attr,
210	&dev_attr_minimum_voltage.attr,
211	&maximum_current_attr.attr,
212	NULL
213};
214ATTRIBUTE_GROUPS(source_variable_supply);
215
216static const struct device_type source_variable_supply_type = {
217	.name = "pdo",
218	.release = pdo_release,
219	.groups = source_variable_supply_groups,
220};
221
222static struct attribute *sink_variable_supply_attrs[] = {
223	&dev_attr_maximum_voltage.attr,
224	&dev_attr_minimum_voltage.attr,
225	&operational_current_attr.attr,
226	NULL
227};
228ATTRIBUTE_GROUPS(sink_variable_supply);
229
230static const struct device_type sink_variable_supply_type = {
231	.name = "pdo",
232	.release = pdo_release,
233	.groups = sink_variable_supply_groups,
234};
235
236/* -------------------------------------------------------------------------- */
237/* Battery */
238
239static ssize_t
240maximum_power_show(struct device *dev, struct device_attribute *attr, char *buf)
241{
242	return sysfs_emit(buf, "%umW\n", pdo_max_power(to_pdo(dev)->pdo));
243}
244static DEVICE_ATTR_RO(maximum_power);
245
246static ssize_t
247operational_power_show(struct device *dev, struct device_attribute *attr, char *buf)
248{
249	return sysfs_emit(buf, "%umW\n", pdo_max_power(to_pdo(dev)->pdo));
250}
251static DEVICE_ATTR_RO(operational_power);
252
253static struct attribute *source_battery_attrs[] = {
254	&dev_attr_maximum_voltage.attr,
255	&dev_attr_minimum_voltage.attr,
256	&dev_attr_maximum_power.attr,
257	NULL
258};
259ATTRIBUTE_GROUPS(source_battery);
260
261static const struct device_type source_battery_type = {
262	.name = "pdo",
263	.release = pdo_release,
264	.groups = source_battery_groups,
265};
266
267static struct attribute *sink_battery_attrs[] = {
268	&dev_attr_maximum_voltage.attr,
269	&dev_attr_minimum_voltage.attr,
270	&dev_attr_operational_power.attr,
271	NULL
272};
273ATTRIBUTE_GROUPS(sink_battery);
274
275static const struct device_type sink_battery_type = {
276	.name = "pdo",
277	.release = pdo_release,
278	.groups = sink_battery_groups,
279};
280
281/* -------------------------------------------------------------------------- */
282/* Standard Power Range (SPR) Programmable Power Supply (PPS) */
283
284static ssize_t
285pps_power_limited_show(struct device *dev, struct device_attribute *attr, char *buf)
286{
287	return sysfs_emit(buf, "%u\n", !!(to_pdo(dev)->pdo & BIT(27)));
288}
289static DEVICE_ATTR_RO(pps_power_limited);
290
291static ssize_t
292pps_max_voltage_show(struct device *dev, struct device_attribute *attr, char *buf)
293{
294	return sysfs_emit(buf, "%umV\n", pdo_pps_apdo_max_voltage(to_pdo(dev)->pdo));
295}
296
297static ssize_t
298pps_min_voltage_show(struct device *dev, struct device_attribute *attr, char *buf)
299{
300	return sysfs_emit(buf, "%umV\n", pdo_pps_apdo_min_voltage(to_pdo(dev)->pdo));
301}
302
303static ssize_t
304pps_max_current_show(struct device *dev, struct device_attribute *attr, char *buf)
305{
306	return sysfs_emit(buf, "%umA\n", pdo_pps_apdo_max_current(to_pdo(dev)->pdo));
307}
308
309static struct device_attribute pps_max_voltage_attr = {
310	.attr = {
311		.name = "maximum_voltage",
312		.mode = 0444,
313	},
314	.show = pps_max_voltage_show,
315};
316
317static struct device_attribute pps_min_voltage_attr = {
318	.attr = {
319		.name = "minimum_voltage",
320		.mode = 0444,
321	},
322	.show = pps_min_voltage_show,
323};
324
325static struct device_attribute pps_max_current_attr = {
326	.attr = {
327		.name = "maximum_current",
328		.mode = 0444,
329	},
330	.show = pps_max_current_show,
331};
332
333static struct attribute *source_pps_attrs[] = {
334	&dev_attr_pps_power_limited.attr,
335	&pps_max_voltage_attr.attr,
336	&pps_min_voltage_attr.attr,
337	&pps_max_current_attr.attr,
338	NULL
339};
340ATTRIBUTE_GROUPS(source_pps);
341
342static const struct device_type source_pps_type = {
343	.name = "pdo",
344	.release = pdo_release,
345	.groups = source_pps_groups,
346};
347
348static struct attribute *sink_pps_attrs[] = {
349	&pps_max_voltage_attr.attr,
350	&pps_min_voltage_attr.attr,
351	&pps_max_current_attr.attr,
352	NULL
353};
354ATTRIBUTE_GROUPS(sink_pps);
355
356static const struct device_type sink_pps_type = {
357	.name = "pdo",
358	.release = pdo_release,
359	.groups = sink_pps_groups,
360};
361
362/* -------------------------------------------------------------------------- */
363/* Standard Power Range (SPR) Adjustable Voltage Supply (AVS) */
364
365static ssize_t
366spr_avs_9v_to_15v_max_current_show(struct device *dev,
367				   struct device_attribute *attr, char *buf)
368{
369	return sysfs_emit(buf, "%umA\n",
370			  pdo_spr_avs_apdo_9v_to_15v_max_current_ma(to_pdo(dev)->pdo));
371}
372
373static ssize_t
374spr_avs_15v_to_20v_max_current_show(struct device *dev,
375				    struct device_attribute *attr, char *buf)
376{
377	return sysfs_emit(buf, "%umA\n",
378			  pdo_spr_avs_apdo_15v_to_20v_max_current_ma(to_pdo(dev)->pdo));
379}
380
381static ssize_t
382spr_avs_src_peak_current_show(struct device *dev,
383			      struct device_attribute *attr, char *buf)
384{
385	return sysfs_emit(buf, "%u\n",
386			  pdo_spr_avs_apdo_src_peak_current(to_pdo(dev)->pdo));
387}
388
389static struct device_attribute spr_avs_9v_to_15v_max_current_attr = {
390	.attr = {
391		.name = "maximum_current_9V_to_15V",
392		.mode = 0444,
393	},
394	.show = spr_avs_9v_to_15v_max_current_show,
395};
396
397static struct device_attribute spr_avs_15v_to_20v_max_current_attr = {
398	.attr = {
399		.name = "maximum_current_15V_to_20V",
400		.mode = 0444,
401	},
402	.show = spr_avs_15v_to_20v_max_current_show,
403};
404
405static struct device_attribute spr_avs_src_peak_current_attr = {
406	.attr = {
407		.name = "peak_current",
408		.mode = 0444,
409	},
410	.show = spr_avs_src_peak_current_show,
411};
412
413static struct attribute *source_spr_avs_attrs[] = {
414	&spr_avs_9v_to_15v_max_current_attr.attr,
415	&spr_avs_15v_to_20v_max_current_attr.attr,
416	&spr_avs_src_peak_current_attr.attr,
417	NULL
418};
419ATTRIBUTE_GROUPS(source_spr_avs);
420
421static const struct device_type source_spr_avs_type = {
422	.name = "pdo",
423	.release = pdo_release,
424	.groups = source_spr_avs_groups,
425};
426
427static struct attribute *sink_spr_avs_attrs[] = {
428	&spr_avs_9v_to_15v_max_current_attr.attr,
429	&spr_avs_15v_to_20v_max_current_attr.attr,
430	NULL
431};
432ATTRIBUTE_GROUPS(sink_spr_avs);
433
434static const struct device_type sink_spr_avs_type = {
435	.name = "pdo",
436	.release = pdo_release,
437	.groups = sink_spr_avs_groups,
438};
439
440/* -------------------------------------------------------------------------- */
441
442static const char * const supply_name[] = {
443	[PDO_TYPE_FIXED] = "fixed_supply",
444	[PDO_TYPE_BATT]  = "battery",
445	[PDO_TYPE_VAR]	 = "variable_supply",
446};
447
448static const char * const apdo_supply_name[] = {
449	[APDO_TYPE_PPS]      = "programmable_supply",
450	[APDO_TYPE_SPR_AVS]  = "spr_adjustable_voltage_supply",
451};
452
453static const struct device_type *source_type[] = {
454	[PDO_TYPE_FIXED] = &source_fixed_supply_type,
455	[PDO_TYPE_BATT]  = &source_battery_type,
456	[PDO_TYPE_VAR]   = &source_variable_supply_type,
457};
458
459static const struct device_type *source_apdo_type[] = {
460	[APDO_TYPE_PPS]     = &source_pps_type,
461	[APDO_TYPE_SPR_AVS] = &source_spr_avs_type,
462};
463
464static const struct device_type *sink_type[] = {
465	[PDO_TYPE_FIXED] = &sink_fixed_supply_type,
466	[PDO_TYPE_BATT]  = &sink_battery_type,
467	[PDO_TYPE_VAR]   = &sink_variable_supply_type,
468};
469
470static const struct device_type *sink_apdo_type[] = {
471	[APDO_TYPE_PPS]     = &sink_pps_type,
472	[APDO_TYPE_SPR_AVS] = &sink_spr_avs_type,
473};
474
475/* REVISIT: Export when EPR_*_Capabilities need to be supported. */
476static int add_pdo(struct usb_power_delivery_capabilities *cap, u32 pdo, int position)
477{
478	const struct device_type *type;
479	const char *name;
480	struct pdo *p;
481	int ret;
482
483	p = kzalloc(sizeof(*p), GFP_KERNEL);
484	if (!p)
485		return -ENOMEM;
486
487	p->pdo = pdo;
488	p->object_position = position;
489
490	if (pdo_type(pdo) == PDO_TYPE_APDO) {
491		/*
492		 * FIXME: Only PPS, SPR_AVS supported for now!
493		 * Skipping others.
494		 */
495		if (pdo_apdo_type(pdo) != APDO_TYPE_PPS &&
496		    pdo_apdo_type(pdo) != APDO_TYPE_SPR_AVS) {
497			dev_warn(&cap->dev, "Unknown APDO type. PDO 0x%08x\n", pdo);
498			kfree(p);
499			return 0;
500		}
501
502		if (is_source(cap->role))
503			type = source_apdo_type[pdo_apdo_type(pdo)];
504		else
505			type = sink_apdo_type[pdo_apdo_type(pdo)];
506
507		name = apdo_supply_name[pdo_apdo_type(pdo)];
508	} else {
509		if (is_source(cap->role))
510			type = source_type[pdo_type(pdo)];
511		else
512			type = sink_type[pdo_type(pdo)];
513
514		name = supply_name[pdo_type(pdo)];
515	}
516
517	p->dev.parent = &cap->dev;
518	p->dev.type = type;
519	dev_set_name(&p->dev, "%u:%s", position + 1, name);
520
521	ret = device_register(&p->dev);
522	if (ret) {
523		put_device(&p->dev);
524		return ret;
525	}
526
527	return 0;
528}
529
530static int remove_pdo(struct device *dev, void *data)
531{
532	device_unregister(dev);
533	return 0;
534}
535
536/* -------------------------------------------------------------------------- */
537
538static const char * const cap_name[] = {
539	[TYPEC_SINK]    = "sink-capabilities",
540	[TYPEC_SOURCE]  = "source-capabilities",
541};
542
543static void pd_capabilities_release(struct device *dev)
544{
545	kfree(to_usb_power_delivery_capabilities(dev));
546}
547
548static const struct device_type pd_capabilities_type = {
549	.name = "capabilities",
550	.release = pd_capabilities_release,
551};
552
553/**
554 * usb_power_delivery_register_capabilities - Register a set of capabilities.
555 * @pd: The USB PD instance that the capabilities belong to.
556 * @desc: Description of the Capabilities Message.
557 *
558 * This function registers a Capabilities Message described in @desc. The
559 * capabilities will have their own sub-directory under @pd in sysfs.
560 *
561 * The function returns pointer to struct usb_power_delivery_capabilities, or
562 * ERR_PRT(errno).
563 */
564struct usb_power_delivery_capabilities *
565usb_power_delivery_register_capabilities(struct usb_power_delivery *pd,
566					 struct usb_power_delivery_capabilities_desc *desc)
567{
568	struct usb_power_delivery_capabilities *cap;
569	int ret;
570	int i;
571
572	cap = kzalloc(sizeof(*cap), GFP_KERNEL);
573	if (!cap)
574		return ERR_PTR(-ENOMEM);
575
576	cap->pd = pd;
577	cap->role = desc->role;
578
579	cap->dev.parent = &pd->dev;
580	cap->dev.type = &pd_capabilities_type;
581	dev_set_name(&cap->dev, "%s", cap_name[cap->role]);
582
583	ret = device_register(&cap->dev);
584	if (ret) {
585		put_device(&cap->dev);
586		return ERR_PTR(ret);
587	}
588
589	for (i = 0; i < PDO_MAX_OBJECTS && desc->pdo[i]; i++) {
590		ret = add_pdo(cap, desc->pdo[i], i);
591		if (ret) {
592			usb_power_delivery_unregister_capabilities(cap);
593			return ERR_PTR(ret);
594		}
595	}
596
597	return cap;
598}
599EXPORT_SYMBOL_GPL(usb_power_delivery_register_capabilities);
600
601/**
602 * usb_power_delivery_unregister_capabilities - Unregister a set of capabilities
603 * @cap: The capabilities
604 */
605void usb_power_delivery_unregister_capabilities(struct usb_power_delivery_capabilities *cap)
606{
607	if (!cap)
608		return;
609
610	device_for_each_child(&cap->dev, NULL, remove_pdo);
611	device_unregister(&cap->dev);
612}
613EXPORT_SYMBOL_GPL(usb_power_delivery_unregister_capabilities);
614
615/* -------------------------------------------------------------------------- */
616
617static ssize_t revision_show(struct device *dev, struct device_attribute *attr, char *buf)
618{
619	struct usb_power_delivery *pd = to_usb_power_delivery(dev);
620
621	return sysfs_emit(buf, "%u.%u\n", (pd->revision >> 8) & 0xff, (pd->revision >> 4) & 0xf);
622}
623static DEVICE_ATTR_RO(revision);
624
625static ssize_t version_show(struct device *dev, struct device_attribute *attr, char *buf)
626{
627	struct usb_power_delivery *pd = to_usb_power_delivery(dev);
628
629	return sysfs_emit(buf, "%u.%u\n", (pd->version >> 8) & 0xff, (pd->version >> 4) & 0xf);
630}
631static DEVICE_ATTR_RO(version);
632
633static struct attribute *pd_attrs[] = {
634	&dev_attr_revision.attr,
635	&dev_attr_version.attr,
636	NULL
637};
638
639static umode_t pd_attr_is_visible(struct kobject *kobj, struct attribute *attr, int n)
640{
641	struct usb_power_delivery *pd = to_usb_power_delivery(kobj_to_dev(kobj));
642
643	if (attr == &dev_attr_version.attr && !pd->version)
644		return 0;
645
646	return attr->mode;
647}
648
649static const struct attribute_group pd_group = {
650	.is_visible = pd_attr_is_visible,
651	.attrs = pd_attrs,
652};
653__ATTRIBUTE_GROUPS(pd);
654
655static void pd_release(struct device *dev)
656{
657	struct usb_power_delivery *pd = to_usb_power_delivery(dev);
658
659	ida_free(&pd_ida, pd->id);
660	kfree(pd);
661}
662
663static const struct device_type pd_type = {
664	.name = "usb_power_delivery",
665	.release = pd_release,
666	.groups = pd_groups,
667};
668
669struct usb_power_delivery *usb_power_delivery_find(const char *name)
670{
671	struct device *dev;
672
673	dev = class_find_device_by_name(&pd_class, name);
674
675	return dev ? to_usb_power_delivery(dev) : NULL;
676}
677
678/**
679 * usb_power_delivery_register - Register USB Power Delivery Support.
680 * @parent: Parent device.
681 * @desc: Description of the USB PD contract.
682 *
683 * This routine can be used to register USB Power Delivery capabilities that a
684 * device or devices can support. These capabilities represent all the
685 * capabilities that can be negotiated with a partner, so not only the Power
686 * Capabilities that are negotiated using the USB PD Capabilities Message.
687 *
688 * The USB Power Delivery Support object that this routine generates can be used
689 * as the parent object for all the actual USB Power Delivery Messages and
690 * objects that can be negotiated with the partner.
691 *
692 * Returns handle to struct usb_power_delivery or ERR_PTR.
693 */
694struct usb_power_delivery *
695usb_power_delivery_register(struct device *parent, struct usb_power_delivery_desc *desc)
696{
697	struct usb_power_delivery *pd;
698	int ret;
699
700	pd = kzalloc(sizeof(*pd), GFP_KERNEL);
701	if (!pd)
702		return ERR_PTR(-ENOMEM);
703
704	ret = ida_alloc(&pd_ida, GFP_KERNEL);
705	if (ret < 0) {
706		kfree(pd);
707		return ERR_PTR(ret);
708	}
709
710	pd->id = ret;
711	pd->revision = desc->revision;
712	pd->version = desc->version;
713
714	pd->dev.parent = parent;
715	pd->dev.type = &pd_type;
716	pd->dev.class = &pd_class;
717	dev_set_name(&pd->dev, "pd%d", pd->id);
718
719	ret = device_register(&pd->dev);
720	if (ret) {
721		put_device(&pd->dev);
722		return ERR_PTR(ret);
723	}
724
725	return pd;
726}
727EXPORT_SYMBOL_GPL(usb_power_delivery_register);
728
729/**
730 * usb_power_delivery_unregister - Unregister USB Power Delivery Support.
731 * @pd: The USB PD contract.
732 */
733void usb_power_delivery_unregister(struct usb_power_delivery *pd)
734{
735	if (IS_ERR_OR_NULL(pd))
736		return;
737
738	device_unregister(&pd->dev);
739}
740EXPORT_SYMBOL_GPL(usb_power_delivery_unregister);
741
742/**
743 * usb_power_delivery_link_device - Link device to its USB PD object.
744 * @pd: The USB PD instance.
745 * @dev: The device.
746 *
747 * This function can be used to create a symlink named "usb_power_delivery" for
748 * @dev that points to @pd.
749 */
750int usb_power_delivery_link_device(struct usb_power_delivery *pd, struct device *dev)
751{
752	int ret;
753
754	if (IS_ERR_OR_NULL(pd) || !dev)
755		return 0;
756
757	ret = sysfs_create_link(&dev->kobj, &pd->dev.kobj, "usb_power_delivery");
758	if (ret)
759		return ret;
760
761	get_device(&pd->dev);
762	get_device(dev);
763
764	return 0;
765}
766EXPORT_SYMBOL_GPL(usb_power_delivery_link_device);
767
768/**
769 * usb_power_delivery_unlink_device - Unlink device from its USB PD object.
770 * @pd: The USB PD instance.
771 * @dev: The device.
772 *
773 * Remove the symlink that was previously created with pd_link_device().
774 */
775void usb_power_delivery_unlink_device(struct usb_power_delivery *pd, struct device *dev)
776{
777	if (IS_ERR_OR_NULL(pd) || !dev)
778		return;
779
780	sysfs_remove_link(&dev->kobj, "usb_power_delivery");
781	put_device(&pd->dev);
782	put_device(dev);
783}
784EXPORT_SYMBOL_GPL(usb_power_delivery_unlink_device);
785
786/* -------------------------------------------------------------------------- */
787
788int __init usb_power_delivery_init(void)
789{
790	return class_register(&pd_class);
791}
792
793void __exit usb_power_delivery_exit(void)
794{
795	ida_destroy(&pd_ida);
796	class_unregister(&pd_class);
797}
~/ Read-only file preview.