static void setup_hal_devices (void) { DBusConnection *connection; DBusError error; LibHalContext *ctx; char **devices; int i, num = 0; dbus_error_init (&error); connection = dbus_bus_get (DBUS_BUS_SYSTEM, &error); if (connection == NULL) { /* cannot get a dbus connection */ if (dbus_error_is_set (&error)) { g_warning ("Getting a system dbus connection an error occured: %s", error.message); dbus_error_free (&error); } return; } dbus_connection_setup_with_g_main (connection, g_main_context_default ()); ctx = libhal_ctx_new (); g_return_if_fail (ctx != NULL); libhal_ctx_set_device_added (ctx, device_added_callback); libhal_ctx_set_device_removed (ctx, device_removed_callback); libhal_ctx_set_dbus_connection (ctx, connection); if (!libhal_ctx_init (ctx, &error)) { /* cannot connect to hald */ if (dbus_error_is_set (&error)) { g_warning ("Connecting to hald an error occured: %s", error.message); dbus_error_free (&error); } return; } devices = libhal_find_device_by_capability (ctx, "alsa", &num, &error); if (devices == NULL) { /* error in the libhal_find_device_by_capability function */ if (dbus_error_is_set (&error)) { g_warning ("Calling a hal function an error occured: %s", error.message); dbus_error_free (&error); } return; } for (i = 0; i < num; i++) { device_added_callback (ctx, devices[i]); } dbus_free_string_array (devices); }
void find_devices(void) { DBusError error; dbus_error_init(&error); if (ac_adapters) libhal_free_string_array(ac_adapters); ac_adapters = libhal_find_device_by_capability(hal_ctx, "ac_adapter", &num_ac_adapters, &error); if (dbus_error_is_set(&error)) { fprintf(stderr, "error: %s: %s\n", error.name, error.message); LIBHAL_FREE_DBUS_ERROR(&error); } if (batteries) libhal_free_string_array(batteries); batteries = libhal_find_device_by_capability(hal_ctx, "battery", &num_batteries, &error); if (dbus_error_is_set(&error)) { fprintf(stderr, "error: %s: %s\n", error.name, error.message); LIBHAL_FREE_DBUS_ERROR(&error); } }
/* * Mount all mountable volumes */ static void rmm_mount_all() { DBusError error; char **udis = NULL; int num_udis; int i; managed_volume_t *v; dbus_error_init(&error); /* get all volumes */ if ((udis = libhal_find_device_by_capability(hal_ctx, "volume", &num_udis, &error)) == NULL) { dprintf("mount_all: no volumes found\n"); goto out; } for (i = 0; i < num_udis; i++) { /* skip if already mounted */ if (libhal_device_get_property_bool(hal_ctx, udis[i], "volume.is_mounted", NULL)) { dprintf("mount_all: %s already mounted\n", udis[i]); continue; } if (!volume_should_mount(udis[i])) { continue; } if ((v = rmm_managed_alloc(hal_ctx, udis[i])) == NULL) { continue; } if (rmm_action(hal_ctx, udis[i], INSERT, &v->aa, 0, 0, 0)) { v->my = B_TRUE; managed_volumes = g_slist_prepend(managed_volumes, v); } else { rmm_managed_free(v); } } out: if (udis != NULL) { libhal_free_string_array(udis); } rmm_dbus_error_free(&error); }
static BOOL connect_and_register(DBusConnection *connection, struct config_hal_info *info) { DBusError error; char **devices; int num_devices, i; if (info->hal_ctx) return TRUE; /* already registered, pretend we did something */ info->system_bus = connection; dbus_error_init(&error); info->hal_ctx = libhal_ctx_new(); if (!info->hal_ctx) { LogMessage(X_ERROR, "config/hal: couldn't create HAL context\n"); goto out_err; } if (!libhal_ctx_set_dbus_connection(info->hal_ctx, info->system_bus)) { LogMessage(X_ERROR, "config/hal: couldn't associate HAL context with bus\n"); goto out_err; } if (!libhal_ctx_init(info->hal_ctx, &error)) { LogMessage(X_ERROR, "config/hal: couldn't initialise context: %s (%s)\n", error.name ? error.name : "unknown error", error.message ? error.message : "null"); goto out_err; } if (!libhal_device_property_watch_all(info->hal_ctx, &error)) { LogMessage(X_ERROR, "config/hal: couldn't watch all properties: %s (%s)\n", error.name ? error.name : "unknown error", error.message ? error.message : "null"); goto out_ctx; } libhal_ctx_set_device_added(info->hal_ctx, device_added); libhal_ctx_set_device_removed(info->hal_ctx, device_removed); devices = libhal_find_device_by_capability(info->hal_ctx, "input", &num_devices, &error); /* FIXME: Get default devices if error is set. */ if (dbus_error_is_set(&error)) { LogMessage(X_ERROR, "config/hal: couldn't find input device: %s (%s)\n", error.name ? error.name : "unknown error", error.message ? error.message : "null"); goto out_ctx; } for (i = 0; i < num_devices; i++) device_added(info->hal_ctx, devices[i]); libhal_free_string_array(devices); dbus_error_free(&error); return TRUE; out_ctx: dbus_error_free(&error); if (!libhal_ctx_shutdown(info->hal_ctx, &error)) { LogMessage(X_WARNING, "config/hal: couldn't shut down context: %s (%s)\n", error.name ? error.name : "unknown error", error.message ? error.message : "null"); dbus_error_free(&error); } out_err: dbus_error_free(&error); if (info->hal_ctx) { libhal_ctx_free(info->hal_ctx); } info->hal_ctx = NULL; info->system_bus = NULL; return FALSE; }
GSList* build_volume_list(LibHalContext* ctx, enum FormatVolumeType type, GHashTable* icon_cache, int icon_width, int icon_height) { const char* capability = ""; char** device_udis; int i, device_udi_count = 0; GSList* device_list = NULL; DBusError error; switch(type) { case FORMATVOLUMETYPE_VOLUME: capability = "volume"; break; case FORMATVOLUMETYPE_DRIVE: capability = "storage"; break; } /* Pull the storage (or volume) list from HAL */ dbus_error_init (&error); if ( (device_udis = libhal_find_device_by_capability (ctx, capability, &device_udi_count, &error) ) == NULL) { LIBHAL_FREE_DBUS_ERROR (&error); goto out; } /* if we use libhal_device_get-property() instead of * libhal_volume_get_mount_mount_point() we have to setup DBusError and * some other things, the problem is do we like to have (null) in the gui * when libhal-storage cannot discover where a partition is mounted? * if so we can remove the DBusError code and use the libhal-storage func * to retrive the mount point. * (or maybe we can check if is_partition == null and then don't strdup * it. * It returns null when a device is marked as swap or mounted via * cryptdisk or even if it's not listed in /etc/fstab */ /* Now we use libhal-storage to get the info */ FormatVolume* current; const char* icon_path; for(i=0; i < device_udi_count; i++) { current = g_new0(FormatVolume, 1); g_debug("udi: %s", device_udis[i]); current->udi = g_strdup(device_udis[i]); switch(type) { case FORMATVOLUMETYPE_VOLUME: current->volume = libhal_volume_from_udi(ctx, device_udis[i]); if(!current->volume) { g_free(current); continue; } /* FIXME: This tastes like wrong */ current->icon = NULL; current->friendly_name = get_friendly_volume_info(ctx, current->volume); current->drive_udi = g_strdup(libhal_volume_get_storage_device_udi(current->volume)); current->mountpoint = g_strdup(libhal_volume_get_mount_point(current->volume)); break; case FORMATVOLUMETYPE_DRIVE: current->drive = libhal_drive_from_udi(ctx, device_udis[i]); if(!current->drive) { g_free(current); continue; } g_debug("Icon drive: %s; Icon volume: %s", libhal_drive_get_dedicated_icon_drive(current->drive), libhal_drive_get_dedicated_icon_volume(current->drive)); icon_path = libhal_drive_get_dedicated_icon_drive(current->drive); current->icon = load_icon_from_cache(icon_path, icon_cache, icon_width, icon_height); current->friendly_name = get_friendly_drive_info(current->drive); break; } /* Do some last minute sanity checks */ if(!current->friendly_name) current->friendly_name = ""; device_list = g_slist_prepend(device_list, current); } if(device_udis) libhal_free_string_array(device_udis); out: return device_list; }
std::map<int, std::pair<std::string, std::string> > SerialPortEnumerator::getPorts() { std::map<int, std::pair<std::string, std::string> > ports; #ifdef MACOSX // use IOKit to enumerates devices // get a matching dictionary to specify which IOService class we're interested in CFMutableDictionaryRef classesToMatch = IOServiceMatching(kIOSerialBSDServiceValue); if (classesToMatch == NULL) throw DashelException(DashelException::EnumerationError, 0, "IOServiceMatching returned a NULL dictionary"); // specify all types of serial devices CFDictionarySetValue(classesToMatch, CFSTR(kIOSerialBSDTypeKey), CFSTR(kIOSerialBSDAllTypes)); // get an iterator to serial port services io_iterator_t matchingServices; kern_return_t kernResult = IOServiceGetMatchingServices(kIOMasterPortDefault, classesToMatch, &matchingServices); if (KERN_SUCCESS != kernResult) throw DashelException(DashelException::EnumerationError, kernResult, "IOServiceGetMatchingServices failed"); // iterate over services io_object_t modemService; int index = 0; while((modemService = IOIteratorNext(matchingServices))) { // get path for device CFTypeRef bsdPathAsCFString = IORegistryEntryCreateCFProperty(modemService, CFSTR(kIOCalloutDeviceKey), kCFAllocatorDefault, 0); if (bsdPathAsCFString) { std::string path; char cStr[255]; std::string name; bool res = CFStringGetCString((CFStringRef) bsdPathAsCFString, cStr, 255, kCFStringEncodingUTF8); if(res) path = cStr; else throw DashelException(DashelException::EnumerationError, 0, "CFStringGetCString failed"); CFRelease(bsdPathAsCFString); CFTypeRef fn = IORegistryEntrySearchCFProperty(modemService, kIOServicePlane, CFSTR("USB Product Name"), kCFAllocatorDefault, kIORegistryIterateRecursively | kIORegistryIterateParents); if(fn) { res = CFStringGetCString((CFStringRef) fn, cStr, 255, kCFStringEncodingUTF8); if(res) name = cStr; else throw DashelException(DashelException::EnumerationError, 0, "CFStringGetString failed"); CFRelease(fn); } else name = "Serial Port"; name = name + " (" + path + ")"; ports[index++] = std::make_pair<std::string, std::string>(path, name); } else throw DashelException(DashelException::EnumerationError, 0, "IORegistryEntryCreateCFProperty returned a NULL path"); // release service IOObjectRelease(modemService); } IOObjectRelease(matchingServices); #elif defined(USE_LIBUDEV) struct udev *udev; struct udev_enumerate *enumerate; struct udev_list_entry *devices, *dev_list_entry; struct udev_device *dev; int index = 0; udev = udev_new(); if(!udev) throw DashelException(DashelException::EnumerationError, 0, "Cannot create udev context"); enumerate = udev_enumerate_new(udev); udev_enumerate_add_match_subsystem(enumerate, "tty"); udev_enumerate_scan_devices(enumerate); devices = udev_enumerate_get_list_entry(enumerate); udev_list_entry_foreach(dev_list_entry, devices) { const char *sysfs_path; struct udev_device *usb_dev; const char * path; struct stat st; unsigned int maj,min; /* Get sysfs path and create the udev device */ sysfs_path = udev_list_entry_get_name(dev_list_entry); dev = udev_device_new_from_syspath(udev, sysfs_path); // Some sanity check path = udev_device_get_devnode(dev); if(stat(path, &st)) throw DashelException(DashelException::EnumerationError, 0, "Cannot stat serial port"); if(!S_ISCHR(st.st_mode)) throw DashelException(DashelException::EnumerationError, 0, "Serial port is not character device"); // Get the major/minor number maj = major(st.st_rdev); min = minor(st.st_rdev); // Ignore all the non physical ports if(!(maj == 2 || (maj == 4 && min < 64) || maj == 3 || maj == 5)) { ostringstream oss; // Check if usb, if yes get the device name usb_dev = udev_device_get_parent_with_subsystem_devtype(dev,"usb","usb_device"); if(usb_dev) oss << udev_device_get_sysattr_value(usb_dev,"product"); else oss << "Serial Port"; oss << " (" << path << ")"; ports[index++] = std::make_pair<std::string, std::string>(path,oss.str()); } udev_device_unref(dev); } udev_enumerate_unref(enumerate); udev_unref(udev); #elif defined(USE_HAL) // use HAL to enumerates devices DBusConnection* dbusConnection = dbus_bus_get(DBUS_BUS_SYSTEM, 0); if (!dbusConnection) throw DashelException(DashelException::EnumerationError, 0, "cannot connect to D-BUS."); LibHalContext* halContext = libhal_ctx_new(); if (!halContext) throw DashelException(DashelException::EnumerationError, 0, "cannot create HAL context: cannot create context"); if (!libhal_ctx_set_dbus_connection(halContext, dbusConnection)) throw DashelException(DashelException::EnumerationError, 0, "cannot create HAL context: cannot connect to D-BUS"); if (!libhal_ctx_init(halContext, 0)) throw DashelException(DashelException::EnumerationError, 0, "cannot create HAL context: cannot init context"); int devicesCount; char** devices = libhal_find_device_by_capability(halContext, "serial", &devicesCount, 0); for (int i = 0; i < devicesCount; i++) { char* devFileName = libhal_device_get_property_string(halContext, devices[i], "serial.device", 0); char* info = libhal_device_get_property_string(halContext, devices[i], "info.product", 0); int port = libhal_device_get_property_int(halContext, devices[i], "serial.port", 0); ostringstream oss; oss << info << " " << port; ports[devicesCount - i] = std::make_pair<std::string, std::string>(devFileName, oss.str()); libhal_free_string(info); libhal_free_string(devFileName); } libhal_free_string_array(devices); libhal_ctx_shutdown(halContext, 0); libhal_ctx_free(halContext); #endif return ports; };
int main (int argc, char *argv[]) { DBusConnection *dbconn; DBusError dberr; LibHalContext *hal_ctx; LibHalPropertyType property_type; char *property_key; dbus_bool_t bool_value; int int_value; char **udis; int num_udis; int i; dbus_error_init (&dberr); dbconn = dbus_bus_get (DBUS_BUS_SYSTEM, &dberr); if (dbus_error_is_set (&dberr)) { fprintf (stderr, "Can't get D-Bus system bus!"); return EXIT_FAILURE; } hal_ctx = libhal_ctx_new (); if (hal_ctx == NULL) { fprintf (stderr, "Can't create a LibHalContext!"); return EXIT_FAILURE; } /* Associate HAL with the D-Bus connection we established */ libhal_ctx_set_dbus_connection (hal_ctx, dbconn); dbus_error_init (&dberr); libhal_ctx_init (hal_ctx, &dberr); if (dbus_error_is_set (&dberr)) { fprintf (stderr, "libhal_ctx_init() failed: '%s'. Is hald running?", dberr.message); dbus_error_free (&dberr); libhal_ctx_free (hal_ctx); return EXIT_FAILURE; } /* Looking for optical drives: storage.cdrom is the capability */ udis = libhal_find_device_by_capability (hal_ctx, "storage.cdrom", &num_udis, &dberr); if (dbus_error_is_set (&dberr)) { fprintf (stderr, "libhal_find_device_by_capability error: '%s'\n", dberr.message); dbus_error_free (&dberr); libhal_ctx_free (hal_ctx); return EXIT_FAILURE; } printf ("Found %d Optical Device(s)\n", num_udis); for (i = 0; i < num_udis; i++) { /* Ensure our properties are the expected type */ property_type = libhal_device_get_property_type (hal_ctx, udis[i], "storage.cdrom.dvd", &dberr); if (dbus_error_is_set (&dberr) || property_type != LIBHAL_PROPERTY_TYPE_BOOLEAN) { fprintf (stderr, "error checking storage.cdrom.dvd type"); dbus_error_free (&dberr); libhal_ctx_free (hal_ctx); return EXIT_FAILURE; } property_type = libhal_device_get_property_type (hal_ctx, udis[i], "storage.cdrom.read_speed", &dberr); if (dbus_error_is_set (&dberr) || property_type != LIBHAL_PROPERTY_TYPE_INT32) { fprintf (stderr, "error checking storage.cdrom.read_speed type"); dbus_error_free (&dberr); libhal_ctx_free (hal_ctx); return EXIT_FAILURE; } /* Okay, now simply get property values */ bool_value = libhal_device_get_property_bool (hal_ctx, udis[i], "storage.cdrom.dvd", &dberr); if (dbus_error_is_set (&dberr)) { fprintf (stderr, "error getting storage.cdrom.dvd"); dbus_error_free (&dberr); libhal_ctx_free (hal_ctx); return EXIT_FAILURE; } int_value = libhal_device_get_property_int (hal_ctx, udis[i], "storage.cdrom.read_speed", &dberr); if (dbus_error_is_set (&dberr)) { fprintf (stderr, "error getting storage.cdrom.dvd"); dbus_error_free (&dberr); libhal_ctx_free (hal_ctx); return EXIT_FAILURE; } /* Display the info we just got */ printf ("Device %s has a maximum read spead of %d kb/s and %s read DVDs.\n", udis[i], int_value, bool_value ? "can" : "cannot"); } return EXIT_SUCCESS; }
char * battstat_hal_initialise (void (*callback) (void)) { DBusConnection *connection; LibHalContext *ctx; DBusError error; char *error_str; char **devices; int i, num; status_updated_callback = callback; if( battstat_hal_ctx != NULL ) return g_strdup( "Already initialised!" ); dbus_error_init( &error ); if( (connection = dbus_bus_get( DBUS_BUS_SYSTEM, &error )) == NULL ) goto error_out; dbus_connection_setup_with_g_main( connection, g_main_context_default() ); if( (ctx = libhal_ctx_new()) == NULL ) { dbus_set_error( &error, _("HAL error"), _("Could not create libhal_ctx") ); goto error_out; } libhal_ctx_set_device_property_modified( ctx, property_callback ); libhal_ctx_set_device_added( ctx, device_added_callback ); libhal_ctx_set_device_removed( ctx, device_removed_callback ); libhal_ctx_set_dbus_connection( ctx, connection ); if( libhal_ctx_init( ctx, &error ) == 0 ) goto error_freectx; devices = libhal_find_device_by_capability( ctx, "battery", &num, &error ); if( devices == NULL ) goto error_shutdownctx; /* FIXME: for now, if 0 battery devices are present on first scan, then fail. * This allows fallover to the legacy (ACPI, APM, etc) backends if the * installed version of HAL doesn't know about batteries. This check should * be removed at some point in the future (maybe circa MATE 2.13..). */ if( num == 0 ) { dbus_free_string_array( devices ); dbus_set_error( &error, _("HAL error"), _("No batteries found") ); goto error_shutdownctx; } for( i = 0; i < num; i++ ) { char *type = libhal_device_get_property_string( ctx, devices[i], "battery.type", &error ); if( type ) { /* We only track 'primary' batteries (ie: to avoid monitoring * batteries in cordless mice or UPSes etc.) */ if( !strcmp( type, "primary" ) ) add_to_list( ctx, &batteries, devices[i], sizeof (struct battery_info) ); libhal_free_string( type ); } } dbus_free_string_array( devices ); devices = libhal_find_device_by_capability( ctx, "ac_adapter", &num, &error ); if( devices == NULL ) { batteries = free_entire_list( batteries ); goto error_shutdownctx; } for( i = 0; i < num; i++ ) add_to_list( ctx, &adaptors, devices[i], sizeof (struct adaptor_info) ); dbus_free_string_array( devices ); dbus_error_free( &error ); battstat_hal_ctx = ctx; return NULL; error_shutdownctx: libhal_ctx_shutdown( ctx, NULL ); error_freectx: libhal_ctx_free( ctx ); error_out: error_str = g_strdup_printf( _("Unable to initialise HAL: %s: %s"), error.name, error.message ); dbus_error_free( &error ); return error_str; }
static void thunar_vfs_volume_manager_hal_init (ThunarVfsVolumeManagerHal *manager_hal) { LibHalDrive *hd; DBusError error; gchar **drive_udis; gchar **udis; gint n_drive_udis; gint n_udis; gint n, m; /* initialize the D-BUS error */ dbus_error_init (&error); /* allocate a HAL context */ manager_hal->context = libhal_ctx_new (); if (G_UNLIKELY (manager_hal->context == NULL)) return; /* try to connect to the system bus */ manager_hal->dbus_connection = dbus_bus_get (DBUS_BUS_SYSTEM, &error); if (G_UNLIKELY (manager_hal->dbus_connection == NULL)) goto failed; /* setup the D-BUS connection for the HAL context */ libhal_ctx_set_dbus_connection (manager_hal->context, manager_hal->dbus_connection); /* connect our manager object to the HAL context */ libhal_ctx_set_user_data (manager_hal->context, manager_hal); /* setup callbacks */ libhal_ctx_set_device_added (manager_hal->context, thunar_vfs_volume_manager_hal_device_added); libhal_ctx_set_device_removed (manager_hal->context, thunar_vfs_volume_manager_hal_device_removed); libhal_ctx_set_device_new_capability (manager_hal->context, thunar_vfs_volume_manager_hal_device_new_capability); libhal_ctx_set_device_lost_capability (manager_hal->context, thunar_vfs_volume_manager_hal_device_lost_capability); libhal_ctx_set_device_property_modified (manager_hal->context, thunar_vfs_volume_manager_hal_device_property_modified); libhal_ctx_set_device_condition (manager_hal->context, thunar_vfs_volume_manager_hal_device_condition); /* try to initialize the HAL context */ if (!libhal_ctx_init (manager_hal->context, &error)) goto failed; /* setup the D-BUS connection with the GLib main loop */ dbus_connection_setup_with_g_main (manager_hal->dbus_connection, NULL); /* lookup all drives currently known to HAL */ drive_udis = libhal_find_device_by_capability (manager_hal->context, "storage", &n_drive_udis, &error); if (G_LIKELY (drive_udis != NULL)) { /* process all drives UDIs */ for (m = 0; m < n_drive_udis; ++m) { /* determine the LibHalDrive for the drive UDI */ hd = libhal_drive_from_udi (manager_hal->context, drive_udis[m]); if (G_UNLIKELY (hd == NULL)) continue; /* check if we have a floppy disk here */ if (libhal_drive_get_type (hd) == LIBHAL_DRIVE_TYPE_FLOPPY) { /* add the drive based on the UDI */ thunar_vfs_volume_manager_hal_device_added (manager_hal->context, drive_udis[m]); } else { /* determine all volumes for the given drive */ udis = libhal_drive_find_all_volumes (manager_hal->context, hd, &n_udis); if (G_LIKELY (udis != NULL)) { /* add volumes for all given UDIs */ for (n = 0; n < n_udis; ++n) { /* add the volume based on the UDI */ thunar_vfs_volume_manager_hal_device_added (manager_hal->context, udis[n]); /* release the UDI (HAL bug #5279) */ free (udis[n]); } /* release the UDIs array (HAL bug #5279) */ free (udis); } } /* release the hal drive */ libhal_drive_free (hd); } /* release the drive UDIs */ libhal_free_string_array (drive_udis); } /* watch all devices for changes */ if (!libhal_device_property_watch_all (manager_hal->context, &error)) goto failed; return; failed: /* release the HAL context */ if (G_LIKELY (manager_hal->context != NULL)) { libhal_ctx_free (manager_hal->context); manager_hal->context = NULL; } /* print a warning message */ if (dbus_error_is_set (&error)) { g_warning (_("Failed to connect to the HAL daemon: %s"), error.message); dbus_error_free (&error); } }
static int init_hal(void) { LibHalContext *ctx; DBusError error; DBusConnection *dbus_connection; char **devices, **volumes; int i, num; if (!(ctx = libhal_ctx_new())) { fprintf(stderr, "can't initialize\n"); return -1; } dbus_error_init(&error); dbus_connection = dbus_bus_get(DBUS_BUS_SYSTEM, &error); if (dbus_error_is_set(&error)) { fprintf(stderr, "%s\n", error.message); dbus_error_free(&error); return -1; } dbus_connection_setup_with_g_main(dbus_connection, NULL); libhal_ctx_set_dbus_connection(ctx, dbus_connection); libhal_ctx_set_device_property_modified(ctx, hal_property_modified); if (!libhal_device_property_watch_all(ctx, &error)) { fprintf(stderr, "%s\n", error.message); dbus_error_free(&error); libhal_ctx_free(ctx); return -1; } if (!libhal_ctx_init(ctx, &error)) { fprintf(stderr, "%s\n", error.message); dbus_error_free(&error); libhal_ctx_free(ctx); return -1; } if (!(devices = libhal_get_all_devices(ctx, &num, &error))) { fprintf(stderr, "%s\n", error.message); dbus_error_free(&error); libhal_ctx_shutdown(ctx, NULL); libhal_ctx_free(ctx); return -1; } libhal_free_string_array(devices); volumes = libhal_find_device_by_capability(ctx, "volume", &num, &error); if (dbus_error_is_set(&error)) { printf("can't find volume devices: %s\n", error.message); dbus_error_free(&error); libhal_ctx_shutdown(ctx, NULL); libhal_ctx_free(ctx); return -1; } for (i = 0; i < num; i++) { char *udi = volumes[i]; if (libhal_device_property_exists(ctx, udi, "volume.is_mounted", NULL) && libhal_device_get_property_bool(ctx, udi, "volume.is_mounted", NULL)) { hal_property_modified(ctx, udi, "volume.is_mounted", FALSE, FALSE); hal_property_modified(ctx, udi, "volume.mount_point", FALSE, FALSE); } } libhal_free_string_array(volumes); return 0; }
static void connect_hook(DBusConnection *connection, void *data) { DBusError error; struct config_hal_info *info = data; char **devices; int num_devices, i; info->system_bus = connection; dbus_error_init(&error); if (!info->hal_ctx) info->hal_ctx = libhal_ctx_new(); if (!info->hal_ctx) { ErrorF("[config/hal] couldn't create HAL context\n"); goto out_err; } if (!libhal_ctx_set_dbus_connection(info->hal_ctx, info->system_bus)) { ErrorF("[config/hal] couldn't associate HAL context with bus\n"); goto out_ctx; } if (!libhal_ctx_init(info->hal_ctx, &error)) { ErrorF("[config/hal] couldn't initialise context: %s (%s)\n", error.name, error.message); goto out_ctx; } libhal_ctx_set_device_added(info->hal_ctx, device_added); libhal_ctx_set_device_removed(info->hal_ctx, device_removed); if (!libhal_device_property_watch_all(info->hal_ctx, &error)) { ErrorF("[config/hal] couldn't watch all properties: %s (%s)\n", error.name, error.message); goto out_ctx2; } devices = libhal_find_device_by_capability(info->hal_ctx, "input", &num_devices, &error); /* FIXME: Get default devices if error is set. */ for (i = 0; i < num_devices; i++) device_added(info->hal_ctx, devices[i]); libhal_free_string_array(devices); dbus_error_free(&error); return; out_ctx2: if (!libhal_ctx_shutdown(info->hal_ctx, &error)) DebugF("[config/hal] couldn't shut down context: %s (%s)\n", error.name, error.message); out_ctx: libhal_ctx_free(info->hal_ctx); out_err: dbus_error_free(&error); info->hal_ctx = NULL; info->system_bus = NULL; return; }
static void get_video_devices (ofGstCamData & cam_data) { int i, fd, ok; int num_udis = 0; char **udis; DBusError error; LibHalContext *hal_ctx; cam_data.num_webcam_devices = 0; g_print ("Probing devices with HAL...\n"); dbus_error_init (&error); hal_ctx = libhal_ctx_new (); if (hal_ctx == NULL) { g_warning ("Could not create libhal context"); dbus_error_free (&error); goto fallback; } if (!libhal_ctx_set_dbus_connection (hal_ctx, dbus_bus_get (DBUS_BUS_SYSTEM, &error))) { g_warning ("libhal_ctx_set_dbus_connection: %s: %s", error.name, error.message); dbus_error_free (&error); goto fallback; } if (!libhal_ctx_init (hal_ctx, &error)) { if (dbus_error_is_set (&error)) { g_warning ("libhal_ctx_init: %s: %s", error.name, error.message); dbus_error_free (&error); } g_warning ("Could not initialise connection to hald.\n" "Normally this means the HAL daemon (hald) is not running or not ready"); goto fallback; } udis = libhal_find_device_by_capability (hal_ctx, "video4linux", &num_udis, &error); if (dbus_error_is_set (&error)) { g_warning ("libhal_find_device_by_capability: %s: %s", error.name, error.message); dbus_error_free (&error); goto fallback; } /* Initialize webcam structures */ cam_data.webcam_devices = new ofGstDevice[num_udis]; for (i = 0; i < num_udis; i++) { char *device; char *parent_udi = NULL; char *subsystem = NULL; char *gstreamer_src, *product_name; struct v4l2_capability v2cap; struct video_capability v1cap; gint vendor_id = 0; gint product_id = 0; gchar *property_name = NULL; parent_udi = libhal_device_get_property_string (hal_ctx, udis[i], "info.parent", &error); if (dbus_error_is_set (&error)) { g_warning ("error getting parent for %s: %s: %s", udis[i], error.name, error.message); dbus_error_free (&error); } if (parent_udi != NULL) { subsystem = libhal_device_get_property_string (hal_ctx, parent_udi, "info.subsystem", NULL); if (subsystem == NULL) continue; property_name = g_strjoin (".", subsystem, "vendor_id", NULL); vendor_id = libhal_device_get_property_int (hal_ctx, parent_udi, property_name , &error); if (dbus_error_is_set (&error)) { g_warning ("error getting vendor id: %s: %s", error.name, error.message); dbus_error_free (&error); } g_free (property_name); property_name = g_strjoin (".", subsystem, "product_id", NULL); product_id = libhal_device_get_property_int (hal_ctx, parent_udi, property_name, &error); if (dbus_error_is_set (&error)) { g_warning ("error getting product id: %s: %s", error.name, error.message); dbus_error_free (&error); } g_free (property_name); libhal_free_string (subsystem); libhal_free_string (parent_udi); } g_print ("Found device %04x:%04x, getting capabilities...\n", vendor_id, product_id); device = libhal_device_get_property_string (hal_ctx, udis[i], "video4linux.device", &error); if (dbus_error_is_set (&error)) { g_warning ("error getting V4L device for %s: %s: %s", udis[i], error.name, error.message); dbus_error_free (&error); continue; } /* vbi devices support capture capability too, but cannot be used, * so detect them by device name */ if (strstr (device, "vbi")) { g_print ("Skipping vbi device: %s\n", device); libhal_free_string (device); continue; } if ((fd = open (device, O_RDONLY | O_NONBLOCK)) < 0) { g_warning ("Failed to open %s: %s", device, strerror (errno)); libhal_free_string (device); continue; } ok = ioctl (fd, VIDIOC_QUERYCAP, &v2cap); if (ok < 0) { ok = ioctl (fd, VIDIOCGCAP, &v1cap); if (ok < 0) { g_warning ("Error while probing v4l capabilities for %s: %s", device, strerror (errno)); libhal_free_string (device); close (fd); continue; } g_print ("Detected v4l device: %s\n", v1cap.name); g_print ("Device type: %d\n", v1cap.type); gstreamer_src = "v4lsrc"; product_name = v1cap.name; } else { guint cap = v2cap.capabilities; g_print ("Detected v4l2 device: %s\n", v2cap.card); g_print ("Driver: %s, version: %d\n", v2cap.driver, v2cap.version); /* g_print ("Bus info: %s\n", v2cap.bus_info); */ /* Doesn't seem anything useful */ g_print ("Capabilities: 0x%08X\n", v2cap.capabilities); if (!(cap & V4L2_CAP_VIDEO_CAPTURE)) { g_print ("Device %s seems to not have the capture capability, (radio tuner?)\n" "Removing it from device list.\n", device); libhal_free_string (device); close (fd); continue; } gstreamer_src = "v4l2src"; product_name = (char *) v2cap.card; } g_print ("\n"); cam_data.webcam_devices[cam_data.num_webcam_devices].hal_udi = g_strdup (udis[i]); cam_data.webcam_devices[cam_data.num_webcam_devices].video_device = g_strdup (device); cam_data.webcam_devices[cam_data.num_webcam_devices].gstreamer_src = g_strdup (gstreamer_src); cam_data.webcam_devices[cam_data.num_webcam_devices].product_name = g_strdup (product_name); cam_data.webcam_devices[cam_data.num_webcam_devices].num_video_formats = 0; cam_data.webcam_devices[cam_data.num_webcam_devices].supported_resolutions = g_hash_table_new_full (g_str_hash, g_str_equal, g_free, NULL); cam_data.num_webcam_devices++; libhal_free_string (device); close (fd); } libhal_free_string_array (udis); if (cam_data.num_webcam_devices == 0) { /* Create a fake device so that resolution changing stil works even if the * computer doesn't have a webcam. */ fallback: if (num_udis == 0) { cam_data.webcam_devices = new ofGstDevice; } cam_data.webcam_devices[0].num_video_formats = 0; cam_data.webcam_devices[0].hal_udi = g_strdup ("oF_fake_videodevice"); } cam_data.bInited=true; }