this repo has no description
1
fork

Configure Feed

Select the types of activity you want to include in your feed.

IOKit: more property support

+242 -46
+1
src/IOKit/CMakeLists.txt
··· 25 25 io_device_iterator.cpp 26 26 io_device.cpp 27 27 io_device_usb.cpp 28 + io_device_net.cpp 28 29 ) 29 30 30 31 add_library(IOKit SHARED ${IOKit_SRCS})
+7
src/IOKit/cfutil.h
··· 1 1 #ifndef IOKIT_CFUTIL_H 2 2 #define IOKIT_CFUTIL_H 3 + #include <CoreFoundation/CFString.h> 4 + #include <CoreFoundation/CFNumber.h> 3 5 4 6 #define strCFEqual(cfs, cstr) (CFStringCompare(cfs, CFSTR(cstr), CFStringCompareFlags(0)) == 0) 5 7 ··· 8 10 if (!val) 9 11 return nullptr; 10 12 return CFStringCreateWithCString(kCFAllocatorDefault, val, kCFStringEncodingUTF8); 13 + } 14 + 15 + inline CFNumberRef intToCF(int val, CFAllocatorRef all = kCFAllocatorDefault) 16 + { 17 + return CFNumberCreate(all, kCFNumberIntType, &val); 11 18 } 12 19 13 20 #endif
+55 -25
src/IOKit/io_device.cpp
··· 2 2 #include <cstdlib> 3 3 #include "cfutil.h" 4 4 5 + static const property_mapping generic_properties[] = { 6 + property_mapping{ CFSTR("IOVendor"), [](io_device* d, CFAllocatorRef a) -> CFTypeRef { if (const char* name = d->property("ID_VENDOR")) return strToCF(name, a); else return strToCF(d->property("ID_VENDOR_FROM_DATABASE"), a); } }, 7 + property_mapping{ CFSTR("IOModel"), [](io_device* d, CFAllocatorRef a) -> CFTypeRef { if (const char* name = d->property("ID_MODEL")) return strToCF(name, a); else return strToCF(d->property("ID_MODEL_FROM_DATABASE"), a); } }, 8 + property_mapping{ CFSTR("BSD Name"), [](io_device* d, CFAllocatorRef a) -> CFTypeRef { if (const char* name = d->sysname()) return strToCF(name, a); else return strToCF(d->property("INTERFACE"), a); } }, // name or property INTERFACE 9 + }; 10 + 5 11 io_device::io_device(struct udev_device* dev) 6 12 : m_device(dev) 7 13 { ··· 54 60 55 61 CFTypeRef io_device::retrieve(const property_mapping* mapping, CFAllocatorRef allocator) 56 62 { 57 - const char* value = nullptr; 58 - if (mapping->linuxProperty) 59 - value = property(mapping->linuxProperty); 60 - else if (mapping->linuxSysAttr) 61 - value = sysattr(mapping->linuxSysAttr); 62 - if (!value) 63 - return nullptr; 64 - 65 - if (mapping->dataType == property_mapping::String) 66 - return strToCF(value, allocator); 63 + if (mapping->evaluator) 64 + return mapping->evaluator(this, allocator); 67 65 else 68 66 { 69 - int base = (mapping->dataType == property_mapping::Number10) ? 10 : 16; 70 - char* end; 71 - long lvalue = strtol(value, &end, base); 72 - 73 - if (end == value) 67 + const char* value = nullptr; 68 + if (mapping->linuxProperty) 69 + value = property(mapping->linuxProperty); 70 + else if (mapping->linuxSysAttr) 71 + value = sysattr(mapping->linuxSysAttr); 72 + if (!value) 74 73 return nullptr; 74 + 75 + if (mapping->dataType == property_mapping::String) 76 + return strToCF(value, allocator); 77 + else 78 + { 79 + int base = (mapping->dataType == property_mapping::Number10) ? 10 : 16; 80 + char* end; 81 + long lvalue = strtol(value, &end, base); 75 82 76 - return CFNumberCreate(allocator, kCFNumberLongType, &lvalue); 77 - } 78 - } 83 + if (end == value) 84 + return nullptr; 79 85 80 - void io_device::properties(CFMutableDictionaryRef dict, CFAllocatorRef allocator) 81 - { 86 + return CFNumberCreate(allocator, kCFNumberLongType, &lvalue); 87 + } 88 + } 82 89 } 83 90 84 - CFTypeRef io_device::property(CFStringRef name, CFAllocatorRef allocator) 91 + void io_device::retrieveAll(CFMutableDictionaryRef dict, const property_mapping* mapping, size_t count, CFAllocatorRef allocator) 85 92 { 86 - return nullptr; 93 + for (size_t i = 0; i < count; i++) 94 + { 95 + CFTypeRef val = retrieve(mapping + i, allocator); 96 + CFDictionarySetValue(dict, mapping[i].appleName, val); 97 + } 87 98 } 88 99 89 - const property_mapping* property_mapping::find(const property_mapping* map, size_t count, CFStringRef what) 100 + CFTypeRef io_device::retrieve(const property_mapping* mapping, size_t count, CFStringRef name, CFAllocatorRef allocator) 90 101 { 91 102 for (size_t i = 0; i < count; i++) 92 103 { 93 - if (CFStringCompare(map[i].appleName, what, CFStringCompareFlags(0)) == 0) 94 - return map + i; 104 + if (CFStringCompare(name, mapping[i].appleName, CFStringCompareFlags(0)) == 0) 105 + return retrieve(mapping + i, allocator); 95 106 } 96 107 return nullptr; 97 108 } 98 109 110 + io_device* io_device::parent() 111 + { 112 + return nullptr; // not implemented yet 113 + } 114 + 115 + const char* io_device::sysname() 116 + { 117 + return udev_device_get_sysname(m_device); 118 + } 119 + 120 + void io_device::properties(CFMutableDictionaryRef dict, CFAllocatorRef allocator) 121 + { 122 + retrieveAll(dict, generic_properties, sizeof(generic_properties) / sizeof(generic_properties[0]), allocator); 123 + } 124 + 125 + CFTypeRef io_device::property(CFStringRef name, CFAllocatorRef allocator) 126 + { 127 + return retrieve(generic_properties, sizeof(generic_properties) / sizeof(generic_properties[0]), name, allocator); 128 + }
+20 -5
src/IOKit/io_device.h
··· 14 14 virtual ~io_device(); 15 15 virtual void properties(CFMutableDictionaryRef dict, CFAllocatorRef allocator); 16 16 virtual CFTypeRef property(CFStringRef name, CFAllocatorRef allocator); 17 - protected: 17 + virtual io_device* parent(); 18 + 19 + const char* sysname(); 18 20 const char* property(const char* name); 19 21 const char* sysattr(const char* name); 20 22 CFStringRef sysattrStr(const char* name, CFAllocatorRef allocator); 21 23 CFNumberRef sysattrNum(const char* name, CFAllocatorRef allocator); 24 + protected: 22 25 CFTypeRef retrieve(const property_mapping* mapping, CFAllocatorRef allocator); 26 + CFTypeRef retrieve(const property_mapping* mapping, size_t count, CFStringRef name, CFAllocatorRef allocator); 27 + void retrieveAll(CFMutableDictionaryRef dict, const property_mapping* mapping, size_t count, CFAllocatorRef allocator); 23 28 protected: 24 29 struct udev_device* m_device; 25 30 struct udev_list_entry *m_properties, *m_sysattrs; ··· 27 32 28 33 struct property_mapping 29 34 { 35 + enum DataType { String, Number10, Number16 }; 36 + typedef CFTypeRef (*EvaluatorType)(io_device*,CFAllocatorRef); 37 + 38 + property_mapping(CFStringRef appleName, const char* linuxProperty, const char* linuxSysAttr, DataType dataType) 39 + : appleName(appleName), linuxProperty(linuxProperty), linuxSysAttr(linuxSysAttr), dataType(dataType), evaluator(0) 40 + { 41 + } 42 + 43 + property_mapping(CFStringRef appleName, EvaluatorType ev) 44 + : appleName(appleName), evaluator(ev) 45 + { 46 + } 47 + 30 48 CFStringRef appleName; 31 49 const char* linuxProperty; 32 50 const char* linuxSysAttr; 33 51 34 - enum DataType { String, Number10, Number16 }; 35 52 DataType dataType; 36 - 37 - static const property_mapping* find(const property_mapping* map, size_t count, CFStringRef what); 53 + EvaluatorType evaluator; 38 54 }; 39 55 40 56 #endif 41 -
+117
src/IOKit/io_device_net.cpp
··· 1 + #include "io_device_net.h" 2 + #include "cfutil.h" 3 + #include <cstring> 4 + #include <cstdlib> 5 + #include <sys/types.h> 6 + #include <sys/socket.h> 7 + #include <linux/if_arp.h> 8 + 9 + /* 10 + #define kIOInterfaceUnit "IOInterfaceUnit" 11 + #define kIOInterfaceType "IOInterfaceType" 12 + #define kIOMACAddress "IOMACAddress" 13 + #define kIOPrimaryInterface "IOPrimaryInterface" 14 + */ 15 + 16 + static CFTypeRef ConvertInterfaceType(io_device* d, CFAllocatorRef allocator); 17 + static CFTypeRef ConvertMACAddress(io_device* d, CFAllocatorRef allocator); 18 + 19 + static const property_mapping iface_properties[] = { 20 + property_mapping{ CFSTR("IOMediaAddressLength"), nullptr, "addr_len", property_mapping::Number10 }, 21 + property_mapping{ CFSTR("IOInterfaceType"), ConvertInterfaceType }, 22 + property_mapping{ CFSTR("IOMaxTransferUnit"), nullptr, "mtu", property_mapping::Number10 }, 23 + property_mapping{ CFSTR("IOBuiltin"), [](io_device* d, CFAllocatorRef) -> CFTypeRef { return kCFBooleanFalse; } }, 24 + property_mapping{ CFSTR("IOPrimaryInterface"), [](io_device* d, CFAllocatorRef) -> CFTypeRef { return (strcmp(d->property("INTERFACE"), "eth0") == 0) ? kCFBooleanTrue : kCFBooleanFalse; } }, 25 + }; 26 + 27 + CFTypeRef io_device_net::property(CFStringRef name, CFAllocatorRef allocator) 28 + { 29 + CFTypeRef v = retrieve(iface_properties, sizeof(iface_properties) / sizeof(iface_properties[0]), name, allocator); 30 + if (v) 31 + return v; 32 + else 33 + return io_device::property(name, allocator); 34 + } 35 + 36 + void io_device_net::properties(CFMutableDictionaryRef dict, CFAllocatorRef allocator) 37 + { 38 + io_device::properties(dict, allocator); 39 + retrieveAll(dict, iface_properties, sizeof(iface_properties) / sizeof(iface_properties[0]), allocator); 40 + } 41 + 42 + static CFTypeRef ConvertInterfaceType(io_device* d, CFAllocatorRef allocator) 43 + { 44 + int type = atoi(d->sysattr("type")); 45 + int mtype = 0; 46 + 47 + // This is not complete, but could suffice 48 + switch (type) 49 + { 50 + case ARPHRD_ETHER: 51 + case ARPHRD_IEEE80211: // linux/include/linux/if_arp.h 52 + mtype = 6; // xnu-792/bsd/net/if_types.h 53 + break; 54 + case ARPHRD_LOOPBACK: 55 + mtype = 0x18; 56 + break; 57 + case ARPHRD_PPP: 58 + mtype = 0x17; 59 + break; 60 + case ARPHRD_ATM: 61 + mtype = 0x25; 62 + break; 63 + case ARPHRD_IEEE1394: 64 + mtype = 0x90; 65 + break; 66 + case ARPHRD_SLIP: 67 + mtype = 0x1c; 68 + break; 69 + } 70 + 71 + return intToCF(mtype, allocator); 72 + } 73 + 74 + io_device* io_device_net::parent() 75 + { 76 + return new io_device_net_ctrl(udev_device_ref(m_device)); 77 + } 78 + 79 + static const property_mapping ctrl_properties[] = { 80 + property_mapping{ CFSTR("IOLinkSpeed"), nullptr, "speed", property_mapping::Number10 }, 81 + property_mapping{ CFSTR("IOLinkStatus"), [](io_device* d, CFAllocatorRef a) -> CFTypeRef { int act = atoi(d->sysattr("carrier")); return intToCF(act ? 3 : 1, a); } }, // if_media.h 82 + property_mapping{ CFSTR("IOMACAddress"), ConvertMACAddress }, 83 + }; 84 + 85 + CFTypeRef io_device_net_ctrl::property(CFStringRef name, CFAllocatorRef allocator) 86 + { 87 + return io_device::property(name, allocator); 88 + } 89 + 90 + void io_device_net_ctrl::properties(CFMutableDictionaryRef dict, CFAllocatorRef allocator) 91 + { 92 + io_device::properties(dict, allocator); 93 + } 94 + 95 + CFTypeRef ConvertMACAddress(io_device* d, CFAllocatorRef allocator) 96 + { 97 + int len = atoi(d->sysattr("addr_len")); 98 + const char* addr = d->sysattr("address"); 99 + 100 + if (!addr) 101 + return nullptr; 102 + 103 + UInt8* bytes = new UInt8[len]; 104 + CFTypeRef rv; 105 + 106 + for (int i = 0; i < len; i++) 107 + { 108 + long byte = strtol(addr + i*3, nullptr, 16); 109 + bytes[i] = UInt8(byte); 110 + } 111 + 112 + rv = CFDataCreate(allocator, bytes, len); 113 + 114 + delete [] bytes; 115 + return rv; 116 + } 117 +
+27
src/IOKit/io_device_net.h
··· 1 + #ifndef IOKIT_IODEVICENET_H 2 + #define IOKIT_IODEVICENET_H 3 + #include "io_device.h" 4 + 5 + // IONetworkInterface 6 + class io_device_net : public io_device 7 + { 8 + public: 9 + // error: inheriting constructors are not supported 10 + // using io_device::io_device; 11 + 12 + io_device_net(struct udev_device* device) : io_device(device) {} 13 + virtual CFTypeRef property(CFStringRef name, CFAllocatorRef allocator) override; 14 + virtual void properties(CFMutableDictionaryRef dict, CFAllocatorRef allocator) override; 15 + virtual io_device* parent() override; 16 + }; 17 + 18 + // IONetworkController 19 + class io_device_net_ctrl : public io_device 20 + { 21 + public: 22 + io_device_net_ctrl(struct udev_device* device) : io_device(device) {} 23 + virtual CFTypeRef property(CFStringRef name, CFAllocatorRef allocator) override; 24 + virtual void properties(CFMutableDictionaryRef dict, CFAllocatorRef allocator) override; 25 + }; 26 + 27 + #endif
+13 -14
src/IOKit/io_device_usb.cpp
··· 2 2 3 3 // https://developer.apple.com/library/mac/#documentation/IOKit/Reference/USBSpec_header_reference/Reference/reference.html 4 4 static const property_mapping usb_properties[] = { 5 - { CFSTR("Serial Number"), nullptr, "serial", property_mapping::String }, 6 - { CFSTR("USB Product Name"), nullptr, "product", property_mapping::String }, 7 - { CFSTR("USB Vendor Name"), nullptr, "manufacturer", property_mapping::String }, 8 - { CFSTR("VendorID"), nullptr, "idVendor", property_mapping::Number16 }, 9 - { CFSTR("ProductID"), nullptr, "idProduct", property_mapping::Number16 }, 10 - { CFSTR("bInterfaceClass"), nullptr, "bInterfaceClass", property_mapping::Number16 }, 11 - { CFSTR("bDeviceClass"), nullptr, "bDeviceClass", property_mapping::Number16 }, 5 + property_mapping{ CFSTR("Serial Number"), nullptr, "serial", property_mapping::String }, 6 + property_mapping{ CFSTR("USB Product Name"), nullptr, "product", property_mapping::String }, 7 + property_mapping{ CFSTR("USB Vendor Name"), nullptr, "manufacturer", property_mapping::String }, 8 + property_mapping{ CFSTR("VendorID"), nullptr, "idVendor", property_mapping::Number16 }, 9 + property_mapping{ CFSTR("ProductID"), nullptr, "idProduct", property_mapping::Number16 }, 10 + property_mapping{ CFSTR("bInterfaceClass"), nullptr, "bInterfaceClass", property_mapping::Number16 }, 11 + property_mapping{ CFSTR("bDeviceClass"), nullptr, "bDeviceClass", property_mapping::Number16 }, 12 12 }; 13 13 14 14 15 15 CFTypeRef io_device_usb::property(CFStringRef name, CFAllocatorRef allocator) 16 16 { 17 - const property_mapping* prop = property_mapping::find(usb_properties, sizeof(usb_properties)/sizeof(usb_properties[0]), name); 18 - 19 - if (!prop) 20 - return nullptr; 17 + CFTypeRef v = retrieve(usb_properties, sizeof(usb_properties) / sizeof(usb_properties[0]), name, allocator); 18 + if (v) 19 + return v; 21 20 else 22 - return retrieve(prop, allocator); 21 + return io_device::property(name, allocator); 23 22 } 24 23 25 24 void io_device_usb::properties(CFMutableDictionaryRef dict, CFAllocatorRef allocator) 26 25 { 27 - // walk dict, call retrieve() 28 - 26 + io_device::properties(dict, allocator); 27 + retrieveAll(dict, usb_properties, sizeof(usb_properties) / sizeof(usb_properties[0]), allocator); 29 28 }
+2 -2
src/IOKit/service.mm
··· 151 151 void filterByProperties(struct udev_enumerate* uenum, CFDictionaryRef dict) 152 152 { 153 153 size_t size = CFDictionaryGetCount(dict); 154 - CFStringRef* keys = new CFStringRef[size]; 155 - CFDictionaryGetKeysAndValues(dict, (const void **) keys, nullptr); 154 + CFStringRef* keys = new CFStringRef[size]; 155 + CFDictionaryGetKeysAndValues(dict, (const void **) keys, nullptr); 156 156 157 157 for (size_t i = 0; i < size; i++) 158 158 {