1/* 2 * Copyright (c) 2004,2011,2014 Apple Inc. All Rights Reserved. 3 * 4 * @APPLE_LICENSE_HEADER_START@ 5 * 6 * This file contains Original Code and/or Modifications of Original Code 7 * as defined in and that are subject to the Apple Public Source License 8 * Version 2.0 (the 'License'). You may not use this file except in 9 * compliance with the License. Please obtain a copy of the License at 10 * http://www.opensource.apple.com/apsl/ and read it before using this 11 * file. 12 * 13 * The Original Code and all software distributed under the License are 14 * distributed on an 'AS IS' basis, WITHOUT WARRANTY OF ANY KIND, EITHER 15 * EXPRESS OR IMPLIED, AND APPLE HEREBY DISCLAIMS ALL SUCH WARRANTIES, 16 * INCLUDING WITHOUT LIMITATION, ANY WARRANTIES OF MERCHANTABILITY, 17 * FITNESS FOR A PARTICULAR PURPOSE, QUIET ENJOYMENT OR NON-INFRINGEMENT. 18 * Please see the License for the specific language governing rights and 19 * limitations under the License. 20 * 21 * @APPLE_LICENSE_HEADER_END@ 22 */ 23 24 25// 26// iodevices - code for finding and tracking devices via IOKit 27// 28#ifndef _H_IODEVICES 29#define _H_IODEVICES 30 31#include <security_utilities/mach++.h> 32#include <security_utilities/machserver.h> 33#include <security_utilities/cfutilities.h> 34#include <IOKit/pwr_mgt/IOPMLib.h> 35 36 37namespace Security { 38namespace IOKit { 39 40 41// 42// An IOKit master port 43// 44class MasterPort : public MachPlusPlus::AutoPort { 45public: 46 MasterPort(); 47}; 48 49 50// 51// An IOKit device 52// 53class Device { 54public: 55 Device() : mService(MACH_PORT_NULL) { } 56 Device(io_service_t d) : mService(d) { } 57 ~Device(); 58 59 io_service_t ioObject() const { return mService; } 60 61 operator bool () const { return mService; } 62 bool operator ! () const { return !mService; } 63 64 std::string name() const; 65 std::string name(const char *plane) const; 66 std::string path(const char *plane = kIOServicePlane) const; 67 CFDictionaryRef properties() const; 68 CFTypeRef property(const char *name) const; 69 70 template <class T> 71 T property(const char *name) const 72 { return static_cast<T>(property(name)); } 73 74private: 75 io_service_t mService; 76}; 77 78 79// 80// A device iterator. 81// This isn't an STL iterator. It's not important enough. 82// 83class DeviceIterator { 84public: 85 DeviceIterator(io_iterator_t iter) : mIterator(iter), mAtEnd(false) { } 86 ~DeviceIterator(); 87 88 io_service_t operator () (); 89 90private: 91 io_iterator_t mIterator; // iterator port (handle) 92 bool mAtEnd; // already hit end 93}; 94 95 96// 97// An IOKit-style device matching dictionary, with convenient helper methods 98// 99class DeviceMatch : public CFRef<CFMutableDictionaryRef> { 100 NOCOPY(DeviceMatch) 101public: 102 DeviceMatch(CFMutableDictionaryRef dict) : CFRef<CFMutableDictionaryRef>(dict) { } // this dictionary 103 DeviceMatch(); // empty dictionary 104 DeviceMatch(const char *cls); // this class 105 DeviceMatch(const char *cls, const char *name, uint32_t value, ...); // class plus value pairs 106 107 CFRef<CFMutableDictionaryRef> &dict() { return static_cast<CFRef<CFMutableDictionaryRef> &>(*this); } 108 operator bool () const { return this->get() != NULL; } 109 bool operator ! () const { return this->get() == NULL; } 110 111 void add(const char *name, uint32_t value); // add one name/value pair 112}; 113 114 115// 116// An IOKit notification port object 117// 118class NotificationPort { 119public: 120 NotificationPort(); 121 NotificationPort(const MasterPort &master); 122 ~NotificationPort(); 123 124 mach_port_t port() const; 125 operator mach_port_t () const { return port(); } 126 127 CFRunLoopSourceRef source() const; 128 129 class Receiver { 130 public: 131 virtual ~Receiver(); 132 133 virtual void ioChange(DeviceIterator &iterator) = 0; 134 virtual void ioServiceChange(void *refCon, io_service_t service, //IOServiceInterestCallback 135 natural_t messageType, void *messageArgument) {} 136 }; 137 138 void add(const DeviceMatch &match, Receiver &receiver, const char *type = kIOFirstMatchNotification); 139 void addInterestNotification(Receiver &receiver, io_service_t service, 140 const io_name_t interestType = kIOGeneralInterest); 141 142private: 143 144 static void ioNotify(void *refCon, io_iterator_t iterator); 145 static void ioDeviceNotification(void *refCon, io_service_t service, 146 natural_t messageType, void *messageArgument); 147 148protected: 149 IONotificationPortRef mPortRef; 150}; 151 152 153class MachPortNotificationPort : public NotificationPort, public MachPlusPlus::MachServer::NoReplyHandler { 154public: 155 MachPortNotificationPort(); 156 virtual ~MachPortNotificationPort(); 157 158private: 159 boolean_t handle(mach_msg_header_t *in); 160}; 161 162 163} // end namespace MachPlusPlus 164} // end namespace Security 165 166#endif //_H_IODEVICES 167