aboutsummaryrefslogtreecommitdiff
path: root/modules/devices/usb.c
diff options
context:
space:
mode:
Diffstat (limited to 'modules/devices/usb.c')
-rw-r--r--modules/devices/usb.c224
1 files changed, 224 insertions, 0 deletions
diff --git a/modules/devices/usb.c b/modules/devices/usb.c
new file mode 100644
index 00000000..c6a5ab39
--- /dev/null
+++ b/modules/devices/usb.c
@@ -0,0 +1,224 @@
+/*
+ * HardInfo - Displays System Information
+ * Copyright (C) 2003-2008 L. A. F. Pereira <l@tia.mat.br>
+ *
+ * This program is free software; you can redistribute it and/or modify
+ * it under the terms of the GNU General Public License as published by
+ * the Free Software Foundation, version 2 or later.
+ *
+ * This program is distributed in the hope that it will be useful,
+ * but WITHOUT ANY WARRANTY; without even the implied warranty of
+ * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the
+ * GNU General Public License for more details.
+ *
+ * You should have received a copy of the GNU General Public License
+ * along with this program; if not, write to the Free Software
+ * Foundation, Inc., 51 Franklin St, Fifth Floor, Boston, MA 02110-1301 USA
+ */
+
+#include <string.h>
+
+#include "cpu_util.h"
+#include "hardinfo.h"
+#include "devices.h"
+#include "usb_util.h"
+
+gchar *usb_list = NULL;
+gchar *usb_icons = NULL;
+
+#define UNKIFNULL_AC(f) (f != NULL) ? f : _("(Unknown)")
+#define IARR_END -2
+#define IARR_ANY -1
+
+static struct {
+ int class;
+ char *icon;
+} usb_class_icons[] = {
+ { 0x1, "audio"}, /* Audio */
+ { 0x2, "modem"}, /* Communications and CDC Control */
+ { 0x3, "inputdevices"}, /* HID (Human Interface Device) */
+ { 0x6, "camera-photo"}, /* Still Imaging */
+ { 0x7, "printer"}, /* Printer */
+ { 0x8, "media-removable"}, /* Mass storage */
+ { 0x9, "usb"}, /* Hub */
+ { 0xe, "camera-web"}, /* Video */
+ {IARR_END, NULL}
+};
+
+static struct {
+ int class, subclass, protocol;
+ char *icon;
+} usb_type_icons[] = {
+ { 0x2, 0x6, IARR_ANY, "network-interface"}, /* Ethernet Networking Control Model */
+ { 0x3, 0x1, 0x1, "keyboard"}, /* Keyboard */
+ { 0x3, 0x1, 0x2, "mouse"}, /* Mouse */
+ {0xe0, 0x1, 0x1, "bluetooth"}, /* Bluetooth Programming Interface */
+ {IARR_END, IARR_END, IARR_END, NULL},
+};
+
+static const char* get_class_icon(int class){
+ int i = 0;
+ while (usb_class_icons[i].class != IARR_END) {
+ if (usb_class_icons[i].class == class) {
+ return usb_class_icons[i].icon;
+ }
+ i++;
+ }
+ return NULL;
+}
+
+static const char* get_usbif_icon(const usbi *usbif) {
+ int i = 0;
+ while (usb_type_icons[i].class != IARR_END) {
+ if (usb_type_icons[i].class == usbif->if_class && usb_type_icons[i].subclass == usbif->if_subclass &&
+ (usb_type_icons[i].protocol == IARR_ANY || usb_type_icons[i].protocol == usbif->if_protocol)) {
+
+ return usb_type_icons[i].icon;
+ }
+ i++;
+ }
+
+ return get_class_icon(usbif->if_class);
+}
+
+static const char* get_usbdev_icon(const usbd *u) {
+ const char * icon = NULL;
+ usbi *curr_if;
+
+ curr_if = u->if_list;
+ while (icon == NULL && curr_if != NULL){
+ icon = get_usbif_icon(curr_if);
+ curr_if = curr_if->next;
+ }
+
+ if (icon == NULL){
+ icon = get_class_icon(u->dev_class);
+ }
+
+ return icon;
+}
+
+static void _usb_dev(const usbd *u) {
+ gchar *name, *key, *label, *str, *speed;
+ gchar *product, *vendor, *manufacturer, *device; /* don't free */
+ gchar *interfaces = strdup("");
+ usbi *i;
+ const char* icon;
+
+ vendor = UNKIFNULL_AC(u->vendor);
+ product = UNKIFNULL_AC(u->product);
+ manufacturer = UNKIFNULL_AC(u->manufacturer);
+ device = UNKIFNULL_AC(u->device);
+
+ if (u->vendors) {
+ gchar *ribbon = vendor_list_ribbon(u->vendors, params.fmt_opts);
+ name = g_strdup_printf("%s %s", ribbon, u->product? product: device);
+ } else {
+ name = g_strdup_printf("%s %s", u->vendor? vendor: manufacturer, u->product? product: device);
+ }
+ key = g_strdup_printf("USB%03d:%03d:%03d", u->bus, u->dev, 0);
+ label = g_strdup_printf("%03d:%03d", u->bus, u->dev);
+ icon = get_usbdev_icon(u);
+
+ usb_list = h_strdup_cprintf("$%s$%s=%s\n", usb_list, key, label, name);
+ usb_icons = h_strdup_cprintf("Icon$%s$%s=%s.png\n", usb_icons, key, label, icon ? icon: "usb");
+
+ if (u->if_list != NULL) {
+ i = u->if_list;
+ while (i != NULL){
+ interfaces = h_strdup_cprintf("[%s %d %s]\n"
+ /* Class */ "%s=[%d] %s\n"
+ /* Sub-class */ "%s=[%d] %s\n"
+ /* Protocol */ "%s=[%d] %s\n"
+ /* Driver */ "%s=%s\n",
+ interfaces,
+ _("Interface"), i->if_number, i->if_label? i->if_label: "",
+ _("Class"), i->if_class, UNKIFNULL_AC(i->if_class_str),
+ _("Sub-class"), i->if_subclass, UNKIFNULL_AC(i->if_subclass_str),
+ _("Protocol"), i->if_protocol, UNKIFNULL_AC(i->if_protocol_str),
+ _("Driver"), UNKIFNULL_AC(i->driver)
+ );
+ i = i->next;
+ }
+ }
+
+ if (u->speed_mbs > 0){
+ speed = g_strdup_printf("%d %s", u->speed_mbs, _("Mb/s"));
+ }
+ else{
+ speed = g_strdup(_("Unknown"));
+ }
+
+ str = g_strdup_printf("[%s]\n"
+ /* Product */ "%s=[0x%04x] %s\n"
+ /* Vendor */ "$^$%s=[0x%04x] %s\n"
+ /* Device */ "%s=%s\n"
+ /* Manufacturer */ "$^$%s=%s\n"
+ /* Max Current */ "%s=%d %s\n"
+ /* USB Version */ "%s=%s\n"
+ /* Speed */ "%s=%s\n"
+ /* Class */ "%s=[%d] %s\n"
+ /* Sub-class */ "%s=[%d] %s\n"
+ /* Protocol */ "%s=[%d] %s\n"
+ /* Dev Version */ "%s=%s\n"
+ /* Serial */ "%s=%s\n"
+ "[%s]\n"
+ /* Bus */ "%s=%03d\n"
+ /* Device */ "%s=%03d\n"
+ /* Interfaces */ "%s",
+ _("Device Information"),
+ _("Product"), u->product_id, product,
+ _("Vendor"), u->vendor_id, vendor,
+ _("Device"), device,
+ _("Manufacturer"), manufacturer,
+ _("Max Current"), u->max_curr_ma, _("mA"),
+ _("USB Version"), u->usb_version,
+ _("Speed"), speed,
+ _("Class"), u->dev_class, UNKIFNULL_AC(u->dev_class_str),
+ _("Sub-class"), u->dev_subclass, UNKIFNULL_AC(u->dev_subclass_str),
+ _("Protocol"), u->dev_protocol, UNKIFNULL_AC(u->dev_protocol_str),
+ _("Device Version"), UNKIFNULL_AC(u->device_version),
+ _("Serial Number"), UNKIFNULL_AC(u->serial),
+ _("Connection"),
+ _("Bus"), u->bus,
+ _("Device"), u->dev,
+ interfaces
+ );
+
+ moreinfo_add_with_prefix("DEV", key, str); /* str now owned by morinfo */
+
+ g_free(speed);
+ g_free(name);
+ g_free(key);
+ g_free(label);
+ g_free(interfaces);
+}
+
+void __scan_usb(void) {
+ usbd *list = usb_get_device_list();
+ usbd *curr = list;
+
+ int c = usbd_list_count(list);
+
+ if (usb_list) {
+ moreinfo_del_with_prefix("DEV:USB");
+ g_free(usb_list);
+ }
+ if (usb_icons){
+ g_free(usb_icons);
+ usb_icons = NULL;
+ }
+ usb_list = g_strdup_printf("[%s]\n", _("USB Devices"));
+
+ if (c > 0) {
+ while(curr) {
+ _usb_dev(curr);
+ curr=curr->next;
+ }
+
+ usbd_list_free(list);
+ } else {
+ /* No USB? */
+ usb_list = g_strconcat(usb_list, _("No USB devices found."), "=\n", NULL);
+ }
+}