dependencies = [
gobject_dependency,
- libudev_dependency,
utils_dependencies,
]
#include <utils.h>
-#include <string.h>
-#include <errno.h>
-#include <stdio.h>
-#include <stdbool.h>
-
-#include <libudev.h>
-
/**
* SECTION: query
* @Title: Global functions in ALSACtl
#define generate_file_error(exception, errno, msg) \
g_set_error_literal(exception, G_FILE_ERROR, g_file_error_from_errno(errno), msg)
-static void prepare_udev_enum(struct udev_enumerate **enumerator,
- GError **error)
-{
- struct udev *ctx;
- int err;
-
- ctx = udev_new();
- if (ctx == NULL) {
- generate_file_error(error, errno, "udev_new()");
- return;
- }
-
- *enumerator = udev_enumerate_new(ctx);
- if (*enumerator == NULL) {
- generate_file_error(error, errno, "udev_enumerate_new()");
- udev_unref(ctx);
- return;
- }
-
- err = udev_enumerate_add_match_subsystem(*enumerator, "sound");
- if (err < 0) {
- generate_file_error(error, -err, "udev_enumerate_add_match_subsystem()");
- udev_enumerate_unref(*enumerator);
- udev_unref(ctx);
- return;
- }
-
- err = udev_enumerate_scan_devices(*enumerator);
- if (err < 0) {
- generate_file_error(error, -err, "udev_enumerate_scan_devices()");
- udev_enumerate_unref(*enumerator);
- udev_unref(ctx);
- }
-}
-
-static struct udev_device *detect_dev(struct udev_enumerate *enumerator,
- struct udev_list_entry *entry,
- const char *prefix)
-{
- struct udev *ctx = udev_enumerate_get_udev(enumerator);
- const char *syspath;
- struct udev_device *dev;
- const char *sysname;
-
- syspath = udev_list_entry_get_name(entry);
- if (syspath == NULL)
- return NULL;
-
- dev = udev_device_new_from_syspath(ctx, syspath);
- if (dev == NULL)
- return NULL;
-
- sysname = udev_device_get_sysname(dev);
- if (sysname == NULL) {
- udev_device_unref(dev);
- return NULL;
- }
-
- if (strstr(sysname, prefix) != sysname) {
- udev_device_unref(dev);
- return NULL;
- }
-
- return dev;
-}
-
-static void release_udev_enum(struct udev_enumerate *enumerator)
-{
- struct udev *ctx = udev_enumerate_get_udev(enumerator);
-
- udev_enumerate_unref(enumerator);
- udev_unref(ctx);
-}
-
-static int compare_guint(const void *l, const void *r)
-{
- const guint *x = l;
- const guint *y = r;
-
- return *x > *y;
-}
-
/**
* alsactl_get_card_id_list:
* @entries: (array length=entry_count)(out): The list of numerical ID for sound
void alsactl_get_card_id_list(guint **entries, gsize *entry_count,
GError **error)
{
- struct udev_enumerate *enumerator = NULL;
- struct udev_list_entry *entry, *entry_list;
- unsigned int count;
- unsigned int index;
+ int err;
g_return_if_fail(entries != NULL);
g_return_if_fail(entry_count != NULL);
g_return_if_fail(error == NULL || *error == NULL);
- prepare_udev_enum(&enumerator, error);
- if (*error != NULL)
- return;
-
- entry_list = udev_enumerate_get_list_entry(enumerator);
-
- count = 0;
- udev_list_entry_foreach(entry, entry_list) {
- struct udev_device *dev = detect_dev(enumerator, entry, "card");
- if (dev != NULL) {
- ++count;
- udev_device_unref(dev);
- }
- }
-
- // Nothing available.
- if (count == 0)
- goto end;
-
- *entries = g_malloc0_n(count, sizeof(**entries));
-
- index = 0;
- udev_list_entry_foreach(entry, entry_list) {
- struct udev_device *dev = detect_dev(enumerator, entry, "card");
- if (dev != NULL) {
- const char *sysnum = udev_device_get_sysnum(dev);
- long val;
-
- if (!long_from_string(sysnum, &val)) {
- (*entries)[index] = val;
- ++index;
- }
- udev_device_unref(dev);
- }
- }
-
- g_warn_if_fail(index == count);
-
- *entry_count = count;
-
- qsort(*entries, count, sizeof(guint), compare_guint);
-end:
- release_udev_enum(enumerator);
+ err = generate_card_sysnum_list(entries, entry_count);
+ if (err < 0)
+ generate_file_error(error, -err, "Fail to generate list of card sysnum");
}
/**
dependencies = [
gobject_dependency,
- libudev_dependency,
utils_dependencies,
]
#include <utils.h>
-#include <stdio.h>
-#include <errno.h>
-#include <stdbool.h>
#include <sys/types.h>
#include <sys/stat.h>
#include <fcntl.h>
#include <sys/ioctl.h>
#include <unistd.h>
-#include <libudev.h>
-
/**
* SECTION: query
* @Title: Global functions in ALSAHwdep
* descriptor
*/
-// 'C' is required apart from emulation of Open Sound System.
-#define PREFIX_SYSNAME_TEMPLATE "hwC%u"
-
#define generate_file_error(error, errno, msg) \
g_set_error_literal(error, G_FILE_ERROR, g_file_error_from_errno(errno), msg)
#define generate_file_error_fmt(error, errno, fmt, msg) \
g_set_error(error, G_FILE_ERROR, g_file_error_from_errno(errno), fmt, msg)
-static void prepare_udev_enum(struct udev_enumerate **enumerator, GError **error)
-{
- struct udev *ctx;
- int err;
-
- ctx = udev_new();
- if (ctx == NULL) {
- generate_file_error(error, errno, "udev_new()");
- return;
- }
-
- *enumerator = udev_enumerate_new(ctx);
- if (*enumerator == NULL) {
- generate_file_error(error, errno, "udev_enumerate_new()");
- udev_unref(ctx);
- return;
- }
-
- err = udev_enumerate_add_match_subsystem(*enumerator, "sound");
- if (err < 0) {
- generate_file_error(error, -err, "udev_enumerate_add_match_subsystem()");
- udev_enumerate_unref(*enumerator);
- udev_unref(ctx);
- return;
- }
-
- err = udev_enumerate_scan_devices(*enumerator);
- if (err < 0) {
- generate_file_error(error, -err, "udev_enumerate_scan_devices()");
- udev_enumerate_unref(*enumerator);
- udev_unref(ctx);
- }
-}
-
-static struct udev_device *detect_dev(struct udev_enumerate *enumerator,
- struct udev_list_entry *entry,
- const char *prefix)
-{
- struct udev *ctx = udev_enumerate_get_udev(enumerator);
- const char *syspath;
- struct udev_device *dev;
- const char *sysname;
-
- syspath = udev_list_entry_get_name(entry);
- if (syspath == NULL)
- return NULL;
-
- dev = udev_device_new_from_syspath(ctx, syspath);
- if (dev == NULL)
- return NULL;
-
- sysname = udev_device_get_sysname(dev);
- if (sysname == NULL) {
- udev_device_unref(dev);
- return NULL;
- }
-
- if (strstr(sysname, prefix) != sysname) {
- udev_device_unref(dev);
- return NULL;
- }
-
- return dev;
-}
-
-static void release_udev_enum(struct udev_enumerate *enumerator)
-{
- struct udev *ctx = udev_enumerate_get_udev(enumerator);
-
- udev_enumerate_unref(enumerator);
- udev_unref(ctx);
-}
-
-static int compare_guint(const void *l, const void *r)
-{
- const guint *x = l;
- const guint *y = r;
-
- return *x > *y;
-}
-
-static unsigned int calculate_digits(unsigned int number)
-{
- unsigned int digits = 0;
-
- while (true) {
- number /= 10;
- ++digits;
- if (number == 0)
- break;
- }
-
- return digits;
-}
-
/**
* alsahwdep_get_device_id_list:
* @card_id: The numerical ID of sound card.
void alsahwdep_get_device_id_list(guint card_id, guint **entries,
gsize *entry_count, GError **error)
{
- struct udev_enumerate *enumerator = NULL;
- unsigned int length;
- char *prefix = NULL;
- struct udev_list_entry *entry, *entry_list;
- unsigned int count;
- unsigned int index;
+ int err;
g_return_if_fail(entries != NULL);
g_return_if_fail(entry_count != NULL);
g_return_if_fail(error == NULL || *error == NULL);
- prepare_udev_enum(&enumerator, error);
- if (*error != NULL)
- return;
-
- length = strlen(PREFIX_SYSNAME_TEMPLATE) + calculate_digits(card_id) + 1;
- prefix = g_malloc0(length);
-
- snprintf(prefix, length, PREFIX_SYSNAME_TEMPLATE, card_id);
-
- entry_list = udev_enumerate_get_list_entry(enumerator);
-
- count = 0;
- udev_list_entry_foreach(entry, entry_list) {
- struct udev_device *dev = detect_dev(enumerator, entry, prefix);
- if (dev != NULL) {
- ++count;
- udev_device_unref(dev);
- }
- }
-
- // Nothing available.
- if (count == 0)
- goto end;
-
- *entries = g_malloc0_n(count, sizeof(**entries));
-
- index = 0;
- udev_list_entry_foreach(entry, entry_list) {
- struct udev_device *dev = detect_dev(enumerator, entry, prefix);
- if (dev != NULL) {
- const char *sysnum = udev_device_get_sysnum(dev);
- long val;
-
- if (!long_from_string(sysnum, &val)) {
- (*entries)[index] = (guint)val;
- ++index;
- }
- udev_device_unref(dev);
- }
- }
-
- g_warn_if_fail(index == count);
-
- *entry_count = count;
-
- qsort(*entries, count, sizeof(guint), compare_guint);
-end:
- g_free(prefix);
- release_udev_enum(enumerator);
+ err = generate_hwdep_sysnum_list(entries, entry_count, card_id);
+ if (err < 0)
+ generate_file_error(error, -err, "Fail to generate list of hwdep sysnum");
}
/**
dependencies = [
gobject_dependency,
- libudev_dependency,
utils_dependencies,
]
#include <utils.h>
-#include <stdio.h>
-#include <errno.h>
-#include <stdbool.h>
#include <sys/types.h>
#include <sys/stat.h>
#include <fcntl.h>
#include <sys/ioctl.h>
#include <unistd.h>
-#include <libudev.h>
-
/**
* SECTION: query
* @Title: Global functions in ALSARawmidi
* descriptor
*/
-// 'C' is required apart from emulation of Open Sound System.
-#define PREFIX_SYSNAME_TEMPLATE "midiC%u"
-
#define generate_file_error(error, errno, msg) \
g_set_error_literal(error, G_FILE_ERROR, g_file_error_from_errno(errno), msg)
#define generate_file_error_fmt(error, errno, fmt, msg) \
g_set_error(error, G_FILE_ERROR, g_file_error_from_errno(errno), fmt, msg)
-static void prepare_udev_enum(struct udev_enumerate **enumerator, GError **error)
-{
- struct udev *ctx;
- int err;
-
- ctx = udev_new();
- if (ctx == NULL) {
- generate_file_error(error, errno, "udev_new()");
- return;
- }
-
- *enumerator = udev_enumerate_new(ctx);
- if (*enumerator == NULL) {
- generate_file_error(error, errno, "udev_enumerate_new()");
- udev_unref(ctx);
- return;
- }
-
- err = udev_enumerate_add_match_subsystem(*enumerator, "sound");
- if (err < 0) {
- generate_file_error(error, -err, "udev_enumerate_add_match_subsystem()");
- udev_enumerate_unref(*enumerator);
- udev_unref(ctx);
- return;
- }
-
- err = udev_enumerate_scan_devices(*enumerator);
- if (err < 0) {
- generate_file_error(error, -err, "udev_enumerate_scan_devices()");
- udev_enumerate_unref(*enumerator);
- udev_unref(ctx);
- }
-}
-
-static struct udev_device *detect_dev(struct udev_enumerate *enumerator,
- struct udev_list_entry *entry,
- const char *prefix)
-{
- struct udev *ctx = udev_enumerate_get_udev(enumerator);
- const char *syspath;
- struct udev_device *dev;
- const char *sysname;
-
- syspath = udev_list_entry_get_name(entry);
- if (syspath == NULL)
- return NULL;
-
- dev = udev_device_new_from_syspath(ctx, syspath);
- if (dev == NULL)
- return NULL;
-
- sysname = udev_device_get_sysname(dev);
- if (sysname == NULL) {
- udev_device_unref(dev);
- return NULL;
- }
-
- if (strstr(sysname, prefix) != sysname) {
- udev_device_unref(dev);
- return NULL;
- }
-
- return dev;
-}
-
-static void release_udev_enum(struct udev_enumerate *enumerator)
-{
- struct udev *ctx = udev_enumerate_get_udev(enumerator);
-
- udev_enumerate_unref(enumerator);
- udev_unref(ctx);
-}
-
-static int compare_guint(const void *l, const void *r)
-{
- const guint *x = l;
- const guint *y = r;
-
- return *x > *y;
-}
-
-static unsigned int calculate_digits(unsigned int number)
-{
- unsigned int digits = 0;
-
- while (true) {
- number /= 10;
- ++digits;
- if (number == 0)
- break;
- }
-
- return digits;
-}
-
/**
* alsarawmidi_get_device_id_list:
* @card_id: The numerical ID of sound card.
void alsarawmidi_get_device_id_list(guint card_id, guint **entries,
gsize *entry_count, GError **error)
{
- struct udev_enumerate *enumerator = NULL;
- unsigned int length;
- char *prefix = NULL;
- struct udev_list_entry *entry, *entry_list;
- unsigned int count;
- unsigned int index;
+ int err;
g_return_if_fail(entries != NULL);
g_return_if_fail(entry_count != NULL);
g_return_if_fail(error == NULL || *error == NULL);
- prepare_udev_enum(&enumerator, error);
- if (*error != NULL)
- return;
-
- length = strlen(PREFIX_SYSNAME_TEMPLATE) + calculate_digits(card_id) + 1;
- prefix = g_malloc0(length);
-
- snprintf(prefix, length, PREFIX_SYSNAME_TEMPLATE, card_id);
-
- entry_list = udev_enumerate_get_list_entry(enumerator);
-
- count = 0;
- udev_list_entry_foreach(entry, entry_list) {
- struct udev_device *dev = detect_dev(enumerator, entry, prefix);
- if (dev != NULL) {
- ++count;
- udev_device_unref(dev);
- }
- }
-
- // Nothing available.
- if (count == 0)
- goto end;
-
- *entries = g_malloc0_n(count, sizeof(**entries));
-
- index = 0;
- udev_list_entry_foreach(entry, entry_list) {
- struct udev_device *dev = detect_dev(enumerator, entry, prefix);
- if (dev != NULL) {
- const char *sysnum = udev_device_get_sysnum(dev);
- long val;
-
- if (!long_from_string(sysnum, &val)) {
- (*entries)[index] = (guint)val;
- ++index;
- }
- udev_device_unref(dev);
- }
- }
-
- g_warn_if_fail(index == count);
-
- *entry_count = count;
-
- qsort(*entries, count, sizeof(guint), compare_guint);
-end:
- g_free(prefix);
- release_udev_enum(enumerator);
+ err = generate_rawmidi_sysnum_list(entries, entry_count, card_id);
+ if (err < 0)
+ generate_file_error(error, -err, "Fail to generate list of rawmidi sysnum");
}
/**
dependencies = [
gobject_dependency,
- libudev_dependency,
utils_dependencies,
alsatimer_dependency,
]
// SPDX-License-Identifier: LGPL-3.0-or-later
#include "privates.h"
-#include "utils.h"
-#include <errno.h>
+#include <utils.h>
+
#include <sys/types.h>
#include <sys/stat.h>
#include <fcntl.h>
-#include <unistd.h>
#include <sys/ioctl.h>
-#include <stdbool.h>
-
-#include <libudev.h>
+#include <unistd.h>
/**
* SECTION: query
dependencies = [
gobject_dependency,
- libudev_dependency,
utils_dependencies,
]
#include <utils.h>
-#include <stdio.h>
-#include <stdbool.h>
-#include <errno.h>
#include <sys/types.h>
#include <sys/stat.h>
#include <fcntl.h>
-#include <unistd.h>
#include <sys/ioctl.h>
+#include <unistd.h>
+#include <stdio.h>
#include <stdbool.h>
#include <time.h>
-#include <libudev.h>
-
/**
* SECTION: query
* @Title: Global functions in ALSATimer
#include <stdio.h>
#include <errno.h>
#include <string.h>
+#include <stdlib.h>
#define SOUND_SUBSYSTEM "sound"
udev_unref(ctx);
return err;
}
+
+static int detect_device(struct udev_device **device, struct udev *ctx,
+ struct udev_list_entry *entry, const char *prefix)
+{
+ const char *syspath;
+ struct udev_device *dev;
+ const char *sysname;
+
+ syspath = udev_list_entry_get_name(entry);
+ if (syspath == NULL)
+ return -errno;
+
+ dev = udev_device_new_from_syspath(ctx, syspath);
+ if (dev == NULL)
+ return -errno;
+
+ sysname = udev_device_get_sysname(dev);
+ if (sysname == NULL) {
+ udev_device_unref(dev);
+ return -errno;
+ }
+
+ if (strstr(sysname, prefix) != sysname) {
+ udev_device_unref(dev);
+ return -ENODEV;
+ }
+
+ *device = dev;
+
+ return 0;
+}
+
+static int compare_u32(const void *l, const void *r)
+{
+ const unsigned int *x = l;
+ const unsigned int *y = r;
+
+ return *x > *y;
+}
+
+int generate_sysnum_list_by_sysname_prefix(unsigned int **entries, unsigned long *entry_count,
+ const char *prefix)
+{
+ struct udev *ctx;
+ struct udev_enumerate *enumerator;
+ unsigned int count;
+ struct udev_list_entry *entry, *entry_list;
+ unsigned int index;
+ int err;
+
+ ctx = udev_new();
+ if (ctx == NULL)
+ return -errno;
+
+ enumerator = udev_enumerate_new(ctx);
+ if (enumerator == NULL) {
+ err = -errno;
+ goto err_ctx;
+ }
+
+ err = udev_enumerate_add_match_subsystem(enumerator, SOUND_SUBSYSTEM);
+ if (err < 0) {
+ goto err_enum;
+ }
+
+ err = udev_enumerate_scan_devices(enumerator);
+ if (err < 0)
+ goto err_enum;
+
+ count = 0;
+ entry_list = udev_enumerate_get_list_entry(enumerator);
+ udev_list_entry_foreach(entry, entry_list) {
+ struct udev_device *dev;
+ int err;
+
+ err = detect_device(&dev, ctx, entry, prefix);
+ if (err < 0)
+ continue;
+
+ ++count;
+ udev_device_unref(dev);
+ }
+
+ // Nothing available.
+ if (count == 0)
+ goto err_enum;
+
+ *entries = calloc(count, sizeof(**entries));
+ if (*entries == NULL) {
+ err = -ENOMEM;
+ goto err_enum;
+ }
+
+ index = 0;
+ udev_list_entry_foreach(entry, entry_list) {
+ struct udev_device *dev;
+ const char *sysnum;
+ long val;
+ int err;
+
+ err = detect_device(&dev, ctx, entry, prefix);
+ if (err < 0)
+ continue;
+
+ sysnum = udev_device_get_sysnum(dev);
+ if (sysnum != NULL && !long_from_string(sysnum, &val)) {
+ (*entries)[index] = (unsigned int)val;
+ ++index;
+ }
+
+ udev_device_unref(dev);
+ }
+
+ if (index != count) {
+ err = -ENODATA;
+ goto err_enum;
+ }
+
+ *entry_count = count;
+
+ qsort(*entries, count, sizeof(unsigned int), compare_u32);
+err_enum:
+ udev_enumerate_unref(enumerator);
+err_ctx:
+ udev_unref(ctx);
+
+ return err;
+}
#include <stdarg.h>
#include <libudev.h>
-#define CARD_SYSNAME_TEMPLATE "card%u"
+#define CARD_SYSNAME_PREFIX "card"
+#define CARD_SYSNAME_TEMPLATE CARD_SYSNAME_PREFIX "%u"
#define CONTROL_SYSNAME_TEMPLATE "controlC%u"
-#define RAWMIDI_SYSNAME_TEMPLATE "midiC%uD%u"
-#define HWDEP_SYSNAME_TEMPLATE "hwC%uD%u"
+// 'C' is required apart from emulation of Open Sound System.
+#define RAWMIDI_SYSNAME_PREFIX_TEMPLATE "midiC%u"
+#define RAWMIDI_SYSNAME_TEMPLATE RAWMIDI_SYSNAME_PREFIX_TEMPLATE "D%u"
+// 'C' is required apart from emulation of Open Sound System.
+#define HWDEP_SYSNAME_PREFIX_TEMPLATE "hwC%u"
+#define HWDEP_SYSNAME_TEMPLATE HWDEP_SYSNAME_PREFIX_TEMPLATE "D%u"
#define TIMER_SYSNAME "timer"
#define SEQ_SYSNAME "seq"
int lookup_and_allocate_string_by_sysname(char **name, const char *sysname,
const char *(*func)(struct udev_device *));
+int generate_sysnum_list_by_sysname_prefix(unsigned int **entries, unsigned long *entry_count,
+ const char *prefix);
+
static inline int lookup_and_allocate_name_by_sysname(char **name,
const char *(*func)(struct udev_device *),
const char *fmt, va_list ap)
return lookup_and_allocate_devname_by_sysname(devname, SEQ_SYSNAME);
}
+static inline int generate_sysnum_list(unsigned int **entries, unsigned long *entry_count,
+ const char *fmt, ...)
+{
+ char *prefix;
+ va_list ap;
+ int err;
+
+ va_start(ap, fmt);
+ err = allocate_string(&prefix, fmt, ap);
+ va_end(ap);
+
+ if (err >= 0)
+ err = generate_sysnum_list_by_sysname_prefix(entries, entry_count, prefix);
+ free(prefix);
+
+ return err;
+}
+
+static inline int generate_card_sysnum_list(unsigned int **entries, unsigned long *entry_count)
+{
+ return generate_sysnum_list(entries, entry_count, CARD_SYSNAME_PREFIX);
+}
+
+static inline int generate_hwdep_sysnum_list(unsigned int **entries, unsigned long *entry_count,
+ unsigned int card_id)
+{
+ return generate_sysnum_list(entries, entry_count, HWDEP_SYSNAME_PREFIX_TEMPLATE, card_id);
+}
+
+static inline int generate_rawmidi_sysnum_list(unsigned int **entries, unsigned long *entry_count,
+ unsigned int card_id)
+{
+ return generate_sysnum_list(entries, entry_count, RAWMIDI_SYSNAME_PREFIX_TEMPLATE, card_id);
+}
+
#endif