1 /* SPDX-License-Identifier: LGPL-2.1-or-later */
2
3 #include <ctype.h>
4 #include <dirent.h>
5 #include <errno.h>
6 #include <fcntl.h>
7 #include <linux/sockios.h>
8 #include <net/if.h>
9 #include <stdbool.h>
10 #include <stddef.h>
11 #include <stdio.h>
12 #include <stdlib.h>
13 #include <string.h>
14 #include <sys/ioctl.h>
15 #include <sys/socket.h>
16 #include <sys/stat.h>
17 #include <unistd.h>
18
19 #include "libudev.h"
20 #include "sd-device.h"
21
22 #include "alloc-util.h"
23 #include "device-private.h"
24 #include "device-util.h"
25 #include "libudev-device-internal.h"
26 #include "libudev-list-internal.h"
27 #include "parse-util.h"
28 #include "time-util.h"
29
30 /**
31 * SECTION:libudev-device
32 * @short_description: kernel sys devices
33 *
34 * Representation of kernel sys devices. Devices are uniquely identified
35 * by their syspath, every device has exactly one path in the kernel sys
36 * filesystem. Devices usually belong to a kernel subsystem, and have
37 * a unique name inside that subsystem.
38 */
39
40 /**
41 * udev_device:
42 *
43 * Opaque object representing one kernel sys device.
44 */
45 struct udev_device {
46 struct udev *udev;
47
48 /* real device object */
49 sd_device *device;
50
51 /* legacy */
52 unsigned n_ref;
53
54 struct udev_device *parent;
55 bool parent_set;
56
57 struct udev_list *properties;
58 uint64_t properties_generation;
59 struct udev_list *all_tags, *current_tags;
60 uint64_t all_tags_generation, current_tags_generation;
61 struct udev_list *devlinks;
62 uint64_t devlinks_generation;
63 bool properties_read:1;
64 bool all_tags_read:1;
65 bool current_tags_read:1;
66 bool devlinks_read:1;
67 struct udev_list *sysattrs;
68 bool sysattrs_read;
69 };
70
71 /**
72 * udev_device_get_seqnum:
73 * @udev_device: udev device
74 *
75 * This is only valid if the device was received through a monitor. Devices read from
76 * sys do not have a sequence number.
77 *
78 * Returns: the kernel event sequence number, or 0 if there is no sequence number available.
79 **/
udev_device_get_seqnum(struct udev_device * udev_device)80 _public_ unsigned long long udev_device_get_seqnum(struct udev_device *udev_device) {
81 uint64_t seqnum;
82
83 assert_return_errno(udev_device, 0, EINVAL);
84
85 if (sd_device_get_seqnum(udev_device->device, &seqnum) < 0)
86 return 0;
87
88 return seqnum;
89 }
90
91 /**
92 * udev_device_get_devnum:
93 * @udev_device: udev device
94 *
95 * Get the device major/minor number.
96 *
97 * Returns: the dev_t number.
98 **/
udev_device_get_devnum(struct udev_device * udev_device)99 _public_ dev_t udev_device_get_devnum(struct udev_device *udev_device) {
100 dev_t devnum;
101 int r;
102
103 assert_return_errno(udev_device, makedev(0, 0), EINVAL);
104
105 r = sd_device_get_devnum(udev_device->device, &devnum);
106 if (r == -ENOENT)
107 return makedev(0, 0);
108 if (r < 0)
109 return_with_errno(makedev(0, 0), r);
110
111 return devnum;
112 }
113
114 /**
115 * udev_device_get_driver:
116 * @udev_device: udev device
117 *
118 * Get the kernel driver name.
119 *
120 * Returns: the driver name string, or #NULL if there is no driver attached.
121 **/
udev_device_get_driver(struct udev_device * udev_device)122 _public_ const char *udev_device_get_driver(struct udev_device *udev_device) {
123 const char *driver;
124 int r;
125
126 assert_return_errno(udev_device, NULL, EINVAL);
127
128 r = sd_device_get_driver(udev_device->device, &driver);
129 if (r < 0)
130 return_with_errno(NULL, r);
131
132 return driver;
133 }
134
135 /**
136 * udev_device_get_devtype:
137 * @udev_device: udev device
138 *
139 * Retrieve the devtype string of the udev device.
140 *
141 * Returns: the devtype name of the udev device, or #NULL if it cannot be determined
142 **/
udev_device_get_devtype(struct udev_device * udev_device)143 _public_ const char *udev_device_get_devtype(struct udev_device *udev_device) {
144 const char *devtype;
145 int r;
146
147 assert_return_errno(udev_device, NULL, EINVAL);
148
149 r = sd_device_get_devtype(udev_device->device, &devtype);
150 if (r == -ENOENT)
151 return NULL;
152 if (r < 0)
153 return_with_errno(NULL, r);
154
155 return devtype;
156 }
157
158 /**
159 * udev_device_get_subsystem:
160 * @udev_device: udev device
161 *
162 * Retrieve the subsystem string of the udev device. The string does not
163 * contain any "/".
164 *
165 * Returns: the subsystem name of the udev device, or #NULL if it cannot be determined
166 **/
udev_device_get_subsystem(struct udev_device * udev_device)167 _public_ const char *udev_device_get_subsystem(struct udev_device *udev_device) {
168 const char *subsystem;
169 int r;
170
171 assert_return_errno(udev_device, NULL, EINVAL);
172
173 r = sd_device_get_subsystem(udev_device->device, &subsystem);
174 if (r < 0)
175 return_with_errno(NULL, r);
176
177 return subsystem;
178 }
179
180 /**
181 * udev_device_get_property_value:
182 * @udev_device: udev device
183 * @key: property name
184 *
185 * Get the value of a given property.
186 *
187 * Returns: the property string, or #NULL if there is no such property.
188 **/
udev_device_get_property_value(struct udev_device * udev_device,const char * key)189 _public_ const char *udev_device_get_property_value(struct udev_device *udev_device, const char *key) {
190 const char *value;
191 int r;
192
193 assert_return_errno(udev_device && key, NULL, EINVAL);
194
195 r = sd_device_get_property_value(udev_device->device, key, &value);
196 if (r < 0)
197 return_with_errno(NULL, r);
198
199 return value;
200 }
201
udev_device_new(struct udev * udev,sd_device * device)202 struct udev_device *udev_device_new(struct udev *udev, sd_device *device) {
203 _cleanup_(udev_list_freep) struct udev_list *properties = NULL, *all_tags = NULL, *current_tags = NULL, *sysattrs = NULL, *devlinks = NULL;
204 struct udev_device *udev_device;
205
206 assert(device);
207
208 properties = udev_list_new(true);
209 if (!properties)
210 return_with_errno(NULL, ENOMEM);
211 all_tags = udev_list_new(true);
212 if (!all_tags)
213 return_with_errno(NULL, ENOMEM);
214 current_tags = udev_list_new(true);
215 if (!current_tags)
216 return_with_errno(NULL, ENOMEM);
217 sysattrs = udev_list_new(true);
218 if (!sysattrs)
219 return_with_errno(NULL, ENOMEM);
220 devlinks = udev_list_new(true);
221 if (!devlinks)
222 return_with_errno(NULL, ENOMEM);
223
224 udev_device = new(struct udev_device, 1);
225 if (!udev_device)
226 return_with_errno(NULL, ENOMEM);
227
228 *udev_device = (struct udev_device) {
229 .n_ref = 1,
230 .udev = udev,
231 .device = sd_device_ref(device),
232 .properties = TAKE_PTR(properties),
233 .all_tags = TAKE_PTR(all_tags),
234 .current_tags = TAKE_PTR(current_tags),
235 .sysattrs = TAKE_PTR(sysattrs),
236 .devlinks = TAKE_PTR(devlinks),
237 };
238
239 return udev_device;
240 }
241
242 /**
243 * udev_device_new_from_syspath:
244 * @udev: udev library context
245 * @syspath: sys device path including sys directory
246 *
247 * Create new udev device, and fill in information from the sys
248 * device and the udev database entry. The syspath is the absolute
249 * path to the device, including the sys mount point.
250 *
251 * The initial refcount is 1, and needs to be decremented to
252 * release the resources of the udev device.
253 *
254 * Returns: a new udev device, or #NULL, if it does not exist
255 **/
udev_device_new_from_syspath(struct udev * udev,const char * syspath)256 _public_ struct udev_device *udev_device_new_from_syspath(struct udev *udev, const char *syspath) {
257 _cleanup_(sd_device_unrefp) sd_device *device = NULL;
258 int r;
259
260 r = sd_device_new_from_syspath(&device, syspath);
261 if (r < 0)
262 return_with_errno(NULL, r);
263
264 return udev_device_new(udev, device);
265 }
266
267 /**
268 * udev_device_new_from_devnum:
269 * @udev: udev library context
270 * @type: char or block device
271 * @devnum: device major/minor number
272 *
273 * Create new udev device, and fill in information from the sys
274 * device and the udev database entry. The device is looked-up
275 * by its major/minor number and type. Character and block device
276 * numbers are not unique across the two types.
277 *
278 * The initial refcount is 1, and needs to be decremented to
279 * release the resources of the udev device.
280 *
281 * Returns: a new udev device, or #NULL, if it does not exist
282 **/
udev_device_new_from_devnum(struct udev * udev,char type,dev_t devnum)283 _public_ struct udev_device *udev_device_new_from_devnum(struct udev *udev, char type, dev_t devnum) {
284 _cleanup_(sd_device_unrefp) sd_device *device = NULL;
285 int r;
286
287 r = sd_device_new_from_devnum(&device, type, devnum);
288 if (r < 0)
289 return_with_errno(NULL, r);
290
291 return udev_device_new(udev, device);
292 }
293
294 /**
295 * udev_device_new_from_device_id:
296 * @udev: udev library context
297 * @id: text string identifying a kernel device
298 *
299 * Create new udev device, and fill in information from the sys
300 * device and the udev database entry. The device is looked-up
301 * by a special string:
302 * b8:2 - block device major:minor
303 * c128:1 - char device major:minor
304 * n3 - network device ifindex
305 * +sound:card29 - kernel driver core subsystem:device name
306 *
307 * The initial refcount is 1, and needs to be decremented to
308 * release the resources of the udev device.
309 *
310 * Returns: a new udev device, or #NULL, if it does not exist
311 **/
udev_device_new_from_device_id(struct udev * udev,const char * id)312 _public_ struct udev_device *udev_device_new_from_device_id(struct udev *udev, const char *id) {
313 _cleanup_(sd_device_unrefp) sd_device *device = NULL;
314 int r;
315
316 r = sd_device_new_from_device_id(&device, id);
317 if (r < 0)
318 return_with_errno(NULL, r);
319
320 return udev_device_new(udev, device);
321 }
322
323 /**
324 * udev_device_new_from_subsystem_sysname:
325 * @udev: udev library context
326 * @subsystem: the subsystem of the device
327 * @sysname: the name of the device
328 *
329 * Create new udev device, and fill in information from the sys device
330 * and the udev database entry. The device is looked up by the subsystem
331 * and name string of the device, like "mem" / "zero", or "block" / "sda".
332 *
333 * The initial refcount is 1, and needs to be decremented to
334 * release the resources of the udev device.
335 *
336 * Returns: a new udev device, or #NULL, if it does not exist
337 **/
udev_device_new_from_subsystem_sysname(struct udev * udev,const char * subsystem,const char * sysname)338 _public_ struct udev_device *udev_device_new_from_subsystem_sysname(struct udev *udev, const char *subsystem, const char *sysname) {
339 _cleanup_(sd_device_unrefp) sd_device *device = NULL;
340 int r;
341
342 r = sd_device_new_from_subsystem_sysname(&device, subsystem, sysname);
343 if (r < 0)
344 return_with_errno(NULL, r);
345
346 return udev_device_new(udev, device);
347 }
348
349 /**
350 * udev_device_new_from_environment
351 * @udev: udev library context
352 *
353 * Create new udev device, and fill in information from the
354 * current process environment. This only works reliably if
355 * the process is called from a udev rule. It is usually used
356 * for tools executed from IMPORT= rules.
357 *
358 * The initial refcount is 1, and needs to be decremented to
359 * release the resources of the udev device.
360 *
361 * Returns: a new udev device, or #NULL, if it does not exist
362 **/
udev_device_new_from_environment(struct udev * udev)363 _public_ struct udev_device *udev_device_new_from_environment(struct udev *udev) {
364 _cleanup_(sd_device_unrefp) sd_device *device = NULL;
365 int r;
366
367 r = device_new_from_strv(&device, environ);
368 if (r < 0)
369 return_with_errno(NULL, r);
370
371 return udev_device_new(udev, device);
372 }
373
device_new_from_parent(struct udev_device * child)374 static struct udev_device *device_new_from_parent(struct udev_device *child) {
375 sd_device *parent;
376 int r;
377
378 assert_return_errno(child, NULL, EINVAL);
379
380 r = sd_device_get_parent(child->device, &parent);
381 if (r < 0)
382 return_with_errno(NULL, r);
383
384 return udev_device_new(child->udev, parent);
385 }
386
387 /**
388 * udev_device_get_parent:
389 * @udev_device: the device to start searching from
390 *
391 * Find the next parent device, and fill in information from the sys
392 * device and the udev database entry.
393 *
394 * Returned device is not referenced. It is attached to the child
395 * device, and will be cleaned up when the child device is cleaned up.
396 *
397 * It is not necessarily just the upper level directory, empty or not
398 * recognized sys directories are ignored.
399 *
400 * It can be called as many times as needed, without caring about
401 * references.
402 *
403 * Returns: a new udev device, or #NULL, if it no parent exist.
404 **/
udev_device_get_parent(struct udev_device * udev_device)405 _public_ struct udev_device *udev_device_get_parent(struct udev_device *udev_device) {
406 assert_return_errno(udev_device, NULL, EINVAL);
407
408 if (!udev_device->parent_set) {
409 udev_device->parent_set = true;
410 udev_device->parent = device_new_from_parent(udev_device);
411 }
412
413 /* TODO: errno will differ here in case parent == NULL */
414 return udev_device->parent;
415 }
416
417 /**
418 * udev_device_get_parent_with_subsystem_devtype:
419 * @udev_device: udev device to start searching from
420 * @subsystem: the subsystem of the device
421 * @devtype: the type (DEVTYPE) of the device
422 *
423 * Find the next parent device, with a matching subsystem and devtype
424 * value, and fill in information from the sys device and the udev
425 * database entry.
426 *
427 * If devtype is #NULL, only subsystem is checked, and any devtype will
428 * match.
429 *
430 * Returned device is not referenced. It is attached to the child
431 * device, and will be cleaned up when the child device is cleaned up.
432 *
433 * It can be called as many times as needed, without caring about
434 * references.
435 *
436 * Returns: a new udev device, or #NULL if no matching parent exists.
437 **/
udev_device_get_parent_with_subsystem_devtype(struct udev_device * udev_device,const char * subsystem,const char * devtype)438 _public_ struct udev_device *udev_device_get_parent_with_subsystem_devtype(struct udev_device *udev_device, const char *subsystem, const char *devtype) {
439 sd_device *parent;
440 int r;
441
442 assert_return_errno(udev_device, NULL, EINVAL);
443
444 /* this relies on the fact that finding the subdevice of a parent or the
445 parent of a subdevice commute */
446
447 /* first find the correct sd_device */
448 r = sd_device_get_parent_with_subsystem_devtype(udev_device->device, subsystem, devtype, &parent);
449 if (r < 0)
450 return_with_errno(NULL, r);
451
452 /* then walk the chain of udev_device parents until the corresponding
453 one is found */
454 while ((udev_device = udev_device_get_parent(udev_device)))
455 if (udev_device->device == parent)
456 return udev_device;
457
458 return_with_errno(NULL, ENOENT);
459 }
460
461 /**
462 * udev_device_get_udev:
463 * @udev_device: udev device
464 *
465 * Retrieve the udev library context the device was created with.
466 *
467 * Returns: the udev library context
468 **/
udev_device_get_udev(struct udev_device * udev_device)469 _public_ struct udev *udev_device_get_udev(struct udev_device *udev_device) {
470 assert_return_errno(udev_device, NULL, EINVAL);
471
472 return udev_device->udev;
473 }
474
udev_device_free(struct udev_device * udev_device)475 static struct udev_device *udev_device_free(struct udev_device *udev_device) {
476 assert(udev_device);
477
478 sd_device_unref(udev_device->device);
479 udev_device_unref(udev_device->parent);
480
481 udev_list_free(udev_device->properties);
482 udev_list_free(udev_device->sysattrs);
483 udev_list_free(udev_device->all_tags);
484 udev_list_free(udev_device->current_tags);
485 udev_list_free(udev_device->devlinks);
486
487 return mfree(udev_device);
488 }
489
490 /**
491 * udev_device_ref:
492 * @udev_device: udev device
493 *
494 * Take a reference of a udev device.
495 *
496 * Returns: the passed udev device
497 **/
498
499 /**
500 * udev_device_unref:
501 * @udev_device: udev device
502 *
503 * Drop a reference of a udev device. If the refcount reaches zero,
504 * the resources of the device will be released.
505 *
506 * Returns: #NULL
507 **/
508 DEFINE_PUBLIC_TRIVIAL_REF_UNREF_FUNC(struct udev_device, udev_device, udev_device_free);
509
510 /**
511 * udev_device_get_devpath:
512 * @udev_device: udev device
513 *
514 * Retrieve the kernel devpath value of the udev device. The path
515 * does not contain the sys mount point, and starts with a '/'.
516 *
517 * Returns: the devpath of the udev device
518 **/
udev_device_get_devpath(struct udev_device * udev_device)519 _public_ const char *udev_device_get_devpath(struct udev_device *udev_device) {
520 const char *devpath;
521 int r;
522
523 assert_return_errno(udev_device, NULL, EINVAL);
524
525 r = sd_device_get_devpath(udev_device->device, &devpath);
526 if (r < 0)
527 return_with_errno(NULL, r);
528
529 return devpath;
530 }
531
532 /**
533 * udev_device_get_syspath:
534 * @udev_device: udev device
535 *
536 * Retrieve the sys path of the udev device. The path is an
537 * absolute path and starts with the sys mount point.
538 *
539 * Returns: the sys path of the udev device
540 **/
udev_device_get_syspath(struct udev_device * udev_device)541 _public_ const char *udev_device_get_syspath(struct udev_device *udev_device) {
542 const char *syspath;
543 int r;
544
545 assert_return_errno(udev_device, NULL, EINVAL);
546
547 r = sd_device_get_syspath(udev_device->device, &syspath);
548 if (r < 0)
549 return_with_errno(NULL, r);
550
551 return syspath;
552 }
553
554 /**
555 * udev_device_get_sysname:
556 * @udev_device: udev device
557 *
558 * Get the kernel device name in /sys.
559 *
560 * Returns: the name string of the device
561 **/
udev_device_get_sysname(struct udev_device * udev_device)562 _public_ const char *udev_device_get_sysname(struct udev_device *udev_device) {
563 const char *sysname;
564 int r;
565
566 assert_return_errno(udev_device, NULL, EINVAL);
567
568 r = sd_device_get_sysname(udev_device->device, &sysname);
569 if (r < 0)
570 return_with_errno(NULL, r);
571
572 return sysname;
573 }
574
575 /**
576 * udev_device_get_sysnum:
577 * @udev_device: udev device
578 *
579 * Get the instance number of the device.
580 *
581 * Returns: the trailing number string of the device name
582 **/
udev_device_get_sysnum(struct udev_device * udev_device)583 _public_ const char *udev_device_get_sysnum(struct udev_device *udev_device) {
584 const char *sysnum;
585 int r;
586
587 assert_return_errno(udev_device, NULL, EINVAL);
588
589 r = sd_device_get_sysnum(udev_device->device, &sysnum);
590 if (r == -ENOENT)
591 return NULL;
592 if (r < 0)
593 return_with_errno(NULL, r);
594
595 return sysnum;
596 }
597
598 /**
599 * udev_device_get_devnode:
600 * @udev_device: udev device
601 *
602 * Retrieve the device node file name belonging to the udev device.
603 * The path is an absolute path, and starts with the device directory.
604 *
605 * Returns: the device node file name of the udev device, or #NULL if no device node exists
606 **/
udev_device_get_devnode(struct udev_device * udev_device)607 _public_ const char *udev_device_get_devnode(struct udev_device *udev_device) {
608 const char *devnode;
609 int r;
610
611 assert_return_errno(udev_device, NULL, EINVAL);
612
613 r = sd_device_get_devname(udev_device->device, &devnode);
614 if (r < 0)
615 return_with_errno(NULL, r);
616
617 return devnode;
618 }
619
620 /**
621 * udev_device_get_devlinks_list_entry:
622 * @udev_device: udev device
623 *
624 * Retrieve the list of device links pointing to the device file of
625 * the udev device. The next list entry can be retrieved with
626 * udev_list_entry_get_next(), which returns #NULL if no more entries exist.
627 * The devlink path can be retrieved from the list entry by
628 * udev_list_entry_get_name(). The path is an absolute path, and starts with
629 * the device directory.
630 *
631 * Returns: the first entry of the device node link list
632 **/
udev_device_get_devlinks_list_entry(struct udev_device * udev_device)633 _public_ struct udev_list_entry *udev_device_get_devlinks_list_entry(struct udev_device *udev_device) {
634 assert_return_errno(udev_device, NULL, EINVAL);
635
636 if (device_get_devlinks_generation(udev_device->device) != udev_device->devlinks_generation ||
637 !udev_device->devlinks_read) {
638 const char *devlink;
639
640 udev_list_cleanup(udev_device->devlinks);
641
642 FOREACH_DEVICE_DEVLINK(udev_device->device, devlink)
643 if (!udev_list_entry_add(udev_device->devlinks, devlink, NULL))
644 return_with_errno(NULL, ENOMEM);
645
646 udev_device->devlinks_read = true;
647 udev_device->devlinks_generation = device_get_devlinks_generation(udev_device->device);
648 }
649
650 return udev_list_get_entry(udev_device->devlinks);
651 }
652
653 /**
654 * udev_device_get_event_properties_entry:
655 * @udev_device: udev device
656 *
657 * Retrieve the list of key/value device properties of the udev
658 * device. The next list entry can be retrieved with udev_list_entry_get_next(),
659 * which returns #NULL if no more entries exist. The property name
660 * can be retrieved from the list entry by udev_list_entry_get_name(),
661 * the property value by udev_list_entry_get_value().
662 *
663 * Returns: the first entry of the property list
664 **/
udev_device_get_properties_list_entry(struct udev_device * udev_device)665 _public_ struct udev_list_entry *udev_device_get_properties_list_entry(struct udev_device *udev_device) {
666 assert_return_errno(udev_device, NULL, EINVAL);
667
668 if (device_get_properties_generation(udev_device->device) != udev_device->properties_generation ||
669 !udev_device->properties_read) {
670 const char *key, *value;
671
672 udev_list_cleanup(udev_device->properties);
673
674 FOREACH_DEVICE_PROPERTY(udev_device->device, key, value)
675 if (!udev_list_entry_add(udev_device->properties, key, value))
676 return_with_errno(NULL, ENOMEM);
677
678 udev_device->properties_read = true;
679 udev_device->properties_generation = device_get_properties_generation(udev_device->device);
680 }
681
682 return udev_list_get_entry(udev_device->properties);
683 }
684
685 /**
686 * udev_device_get_action:
687 * @udev_device: udev device
688 *
689 * This is only valid if the device was received through a monitor. Devices read from
690 * sys do not have an action string. Usual actions are: add, remove, change, move,
691 * online, offline.
692 *
693 * Returns: the kernel action value, or #NULL if there is no action value available.
694 **/
udev_device_get_action(struct udev_device * udev_device)695 _public_ const char *udev_device_get_action(struct udev_device *udev_device) {
696 sd_device_action_t action;
697
698 assert_return_errno(udev_device, NULL, EINVAL);
699
700 if (sd_device_get_action(udev_device->device, &action) < 0)
701 return NULL;
702
703 return device_action_to_string(action);
704 }
705
706 /**
707 * udev_device_get_usec_since_initialized:
708 * @udev_device: udev device
709 *
710 * Return the number of microseconds passed since udev set up the
711 * device for the first time.
712 *
713 * This is only implemented for devices with need to store properties
714 * in the udev database. All other devices return 0 here.
715 *
716 * Returns: the number of microseconds since the device was first seen.
717 **/
udev_device_get_usec_since_initialized(struct udev_device * udev_device)718 _public_ unsigned long long int udev_device_get_usec_since_initialized(struct udev_device *udev_device) {
719 usec_t ts;
720 int r;
721
722 assert_return(udev_device, -EINVAL);
723
724 r = sd_device_get_usec_since_initialized(udev_device->device, &ts);
725 if (r < 0)
726 return_with_errno(0, r);
727
728 return ts;
729 }
730
731 /**
732 * udev_device_get_sysattr_value:
733 * @udev_device: udev device
734 * @sysattr: attribute name
735 *
736 * The retrieved value is cached in the device. Repeated calls will return the same
737 * value and not open the attribute again.
738 *
739 * Returns: the content of a sys attribute file, or #NULL if there is no sys attribute value.
740 **/
udev_device_get_sysattr_value(struct udev_device * udev_device,const char * sysattr)741 _public_ const char *udev_device_get_sysattr_value(struct udev_device *udev_device, const char *sysattr) {
742 const char *value;
743 int r;
744
745 assert_return_errno(udev_device, NULL, EINVAL);
746
747 r = sd_device_get_sysattr_value(udev_device->device, sysattr, &value);
748 if (r < 0)
749 return_with_errno(NULL, r);
750
751 return value;
752 }
753
754 /**
755 * udev_device_set_sysattr_value:
756 * @udev_device: udev device
757 * @sysattr: attribute name
758 * @value: new value to be set
759 *
760 * Update the contents of the sys attribute and the cached value of the device.
761 *
762 * Returns: Negative error code on failure or 0 on success.
763 **/
udev_device_set_sysattr_value(struct udev_device * udev_device,const char * sysattr,const char * value)764 _public_ int udev_device_set_sysattr_value(struct udev_device *udev_device, const char *sysattr, const char *value) {
765 int r;
766
767 assert_return(udev_device, -EINVAL);
768
769 r = sd_device_set_sysattr_value(udev_device->device, sysattr, value);
770 if (r < 0)
771 return r;
772
773 return 0;
774 }
775
776 /**
777 * udev_device_get_sysattr_list_entry:
778 * @udev_device: udev device
779 *
780 * Retrieve the list of available sysattrs, with value being empty;
781 * This just return all available sysfs attributes for a particular
782 * device without reading their values.
783 *
784 * Returns: the first entry of the property list
785 **/
udev_device_get_sysattr_list_entry(struct udev_device * udev_device)786 _public_ struct udev_list_entry *udev_device_get_sysattr_list_entry(struct udev_device *udev_device) {
787 assert_return_errno(udev_device, NULL, EINVAL);
788
789 if (!udev_device->sysattrs_read) {
790 const char *sysattr;
791
792 udev_list_cleanup(udev_device->sysattrs);
793
794 FOREACH_DEVICE_SYSATTR(udev_device->device, sysattr)
795 if (!udev_list_entry_add(udev_device->sysattrs, sysattr, NULL))
796 return_with_errno(NULL, ENOMEM);
797
798 udev_device->sysattrs_read = true;
799 }
800
801 return udev_list_get_entry(udev_device->sysattrs);
802 }
803
804 /**
805 * udev_device_get_is_initialized:
806 * @udev_device: udev device
807 *
808 * Check if udev has already handled the device and has set up
809 * device node permissions and context, or has renamed a network
810 * device.
811 *
812 * This is only implemented for devices with a device node
813 * or network interfaces. All other devices return 1 here.
814 *
815 * Returns: 1 if the device is set up. 0 otherwise.
816 **/
udev_device_get_is_initialized(struct udev_device * udev_device)817 _public_ int udev_device_get_is_initialized(struct udev_device *udev_device) {
818 int r;
819
820 assert_return(udev_device, -EINVAL);
821
822 r = sd_device_get_is_initialized(udev_device->device);
823 if (r < 0)
824 return_with_errno(0, r);
825
826 return r;
827 }
828
829 /**
830 * udev_device_get_tags_list_entry:
831 * @udev_device: udev device
832 *
833 * Retrieve the list of tags attached to the udev device. The next
834 * list entry can be retrieved with udev_list_entry_get_next(),
835 * which returns #NULL if no more entries exist. The tag string
836 * can be retrieved from the list entry by udev_list_entry_get_name().
837 *
838 * Returns: the first entry of the tag list
839 **/
udev_device_get_tags_list_entry(struct udev_device * udev_device)840 _public_ struct udev_list_entry *udev_device_get_tags_list_entry(struct udev_device *udev_device) {
841 assert_return_errno(udev_device, NULL, EINVAL);
842
843 if (device_get_tags_generation(udev_device->device) != udev_device->all_tags_generation ||
844 !udev_device->all_tags_read) {
845 const char *tag;
846
847 udev_list_cleanup(udev_device->all_tags);
848
849 FOREACH_DEVICE_TAG(udev_device->device, tag)
850 if (!udev_list_entry_add(udev_device->all_tags, tag, NULL))
851 return_with_errno(NULL, ENOMEM);
852
853 udev_device->all_tags_read = true;
854 udev_device->all_tags_generation = device_get_tags_generation(udev_device->device);
855 }
856
857 return udev_list_get_entry(udev_device->all_tags);
858 }
859
udev_device_get_current_tags_list_entry(struct udev_device * udev_device)860 _public_ struct udev_list_entry *udev_device_get_current_tags_list_entry(struct udev_device *udev_device) {
861 assert_return_errno(udev_device, NULL, EINVAL);
862
863 if (device_get_tags_generation(udev_device->device) != udev_device->current_tags_generation ||
864 !udev_device->current_tags_read) {
865 const char *tag;
866
867 udev_list_cleanup(udev_device->current_tags);
868
869 FOREACH_DEVICE_CURRENT_TAG(udev_device->device, tag)
870 if (!udev_list_entry_add(udev_device->current_tags, tag, NULL))
871 return_with_errno(NULL, ENOMEM);
872
873 udev_device->current_tags_read = true;
874 udev_device->current_tags_generation = device_get_tags_generation(udev_device->device);
875 }
876
877 return udev_list_get_entry(udev_device->current_tags);
878 }
879
880 /**
881 * udev_device_has_tag:
882 * @udev_device: udev device
883 * @tag: tag name
884 *
885 * Check if a given device has a certain tag associated.
886 *
887 * Returns: 1 if the tag is found. 0 otherwise.
888 **/
udev_device_has_tag(struct udev_device * udev_device,const char * tag)889 _public_ int udev_device_has_tag(struct udev_device *udev_device, const char *tag) {
890 assert_return(udev_device, 0);
891
892 return sd_device_has_tag(udev_device->device, tag) > 0;
893 }
894
udev_device_has_current_tag(struct udev_device * udev_device,const char * tag)895 _public_ int udev_device_has_current_tag(struct udev_device *udev_device, const char *tag) {
896 assert_return(udev_device, 0);
897
898 return sd_device_has_current_tag(udev_device->device, tag) > 0;
899 }
900
udev_device_get_sd_device(struct udev_device * udev_device)901 sd_device *udev_device_get_sd_device(struct udev_device *udev_device) {
902 assert(udev_device);
903
904 return udev_device->device;
905 }
906