Mac OS X开发对我来说是一个相当新的动物,我正在移植一些软件.对于软件许可和注册,我需要能够生成某种硬件ID.它不一定是任何花哨的东西; 以太网MAC地址,硬盘串口,CPU串口等等.
我已经在Windows上覆盖了它,但我对Mac没有任何线索.知道我需要做什么,或者我可以在哪里获取有关此信息的信息会很棒!
编辑:
对于任何对此感兴趣的人,这是我最终使用Qt的QProcess类的代码:
QProcess proc; QStringList args; args << "-c" << "ioreg -rd1 -c IOPlatformExpertDevice | awk '/IOPlatformUUID/ { print $3; }'"; proc.start( "/bin/bash", args ); proc.waitForFinished(); QString uID = proc.readAll();
注意:我正在使用C++.
对于C/C++:
void get_platform_uuid(char * buf, int bufSize) { io_registry_entry_t ioRegistryRoot = IORegistryEntryFromPath(kIOMasterPortDefault, "IOService:/"); CFStringRef uuidCf = (CFStringRef) IORegistryEntryCreateCFProperty(ioRegistryRoot, CFSTR(kIOPlatformUUIDKey), kCFAllocatorDefault, 0); IOObjectRelease(ioRegistryRoot); CFStringGetCString(uuidCf, buf, bufSize, kCFStringEncodingMacRoman); CFRelease(uuidCf); }
试试这个终端命令:
ioreg -rd1 -c IOPlatformExpertDevice | awk '/IOPlatformUUID/ { split($0, line, "\""); printf("%s\n", line[4]); }'
从这里开始
这是用Cocoa包装的命令(可能会变得更干净):
NSArray * args = [NSArray arrayWithObjects:@"-rd1", @"-c", @"IOPlatformExpertDevice", @"|", @"grep", @"model", nil]; NSTask * task = [NSTask new]; [task setLaunchPath:@"/usr/sbin/ioreg"]; [task setArguments:args]; NSPipe * pipe = [NSPipe new]; [task setStandardOutput:pipe]; [task launch]; NSArray * args2 = [NSArray arrayWithObjects:@"/IOPlatformUUID/ { split($0, line, \"\\\"\"); printf(\"%s\\n\", line[4]); }", nil]; NSTask * task2 = [NSTask new]; [task2 setLaunchPath:@"/usr/bin/awk"]; [task2 setArguments:args2]; NSPipe * pipe2 = [NSPipe new]; [task2 setStandardInput:pipe]; [task2 setStandardOutput:pipe2]; NSFileHandle * fileHandle2 = [pipe2 fileHandleForReading]; [task2 launch]; NSData * data = [fileHandle2 readDataToEndOfFile]; NSString * uuid = [[NSString alloc] initWithData:data encoding:NSUTF8StringEncoding];
如果您告诉我们您使用的语言,这将更容易回答.通过SystemConfiguration框架可以在没有任何shell命令的情况下获取信息,如果您想让自己的手真的变脏,也可以通过IOKit获取.
- (NSString*) getMACAddress: (BOOL)stripColons { NSMutableString *macAddress = nil; NSArray *allInterfaces = (NSArray*)SCNetworkInterfaceCopyAll(); NSEnumerator *interfaceWalker = [allInterfaces objectEnumerator]; SCNetworkInterfaceRef curInterface = nil; while ( curInterface = (SCNetworkInterfaceRef)[interfaceWalker nextObject] ) { if ( [(NSString*)SCNetworkInterfaceGetBSDName(curInterface) isEqualToString:@"en0"] ) { macAddress = [[(NSString*)SCNetworkInterfaceGetHardwareAddressString(curInterface) mutableCopy] autorelease]; if ( stripColons == YES ) { [macAddress replaceOccurrencesOfString: @":" withString: @"" options: NSLiteralSearch range: NSMakeRange(0, [macAddress length])]; } break; } } return [[macAddress copy] autorelease]; }
为什么不试试gethostuuid()
?以下是Mac OS X系统调用手册中的文档:
名称:
gethostuuid -- return a unique identifier for the current machine
概要:
#includeint gethostuuid(uuid_t id, const struct timespec *wait);
描述:
gethostuuid()函数返回由id指定的16字节uuid_t,它唯一地标识当前计算机.请注意,gethostuuid()用于生成UUID的硬件标识符本身可以进行修改.
wait参数是指向struct timespec的指针,指定等待结果的最长时间.将tv_sec和tv_nsec字段设置为零意味着无限期地等待直到完成.
返回值:
gethostuuid()函数在成功时返回零,或在出错时返回-1.
错误
如果出现以下情况,gethostuuid()函数将失败:
[EFAULT] wait points to memory that is not a valid part of the process address space. [EWOULDBLOCK] The wait timeout expired before the UUID could be obtained.
/* g++ mac_uuid.cpp -framework CoreFoundation -lIOKit */ #include#include using namespace std; void get_platform_uuid(char * buf, int bufSize) { io_registry_entry_t ioRegistryRoot = IORegistryEntryFromPath(kIOMasterPortDefault, "IOService:/"); CFStringRef uuidCf = (CFStringRef) IORegistryEntryCreateCFProperty(ioRegistryRoot, CFSTR(kIOPlatformUUIDKey), kCFAllocatorDefault, 0); IOObjectRelease(ioRegistryRoot); CFStringGetCString(uuidCf, buf, bufSize, kCFStringEncodingMacRoman); CFRelease(uuidCf); } int main() { char buf[512] = ""; get_platform_uuid(buf, sizeof(buf)); cout << buf << endl; }