Mercurial > minori
comparison dep/animia/src/util/osx.cc @ 169:e44b7c428d7c
dep/animia: add libkvm method (UNTESTED)
author | Paper <mrpapersonic@gmail.com> |
---|---|
date | Sun, 19 Nov 2023 17:30:38 -0500 |
parents | 8937fb7f2d66 |
children | c413e475f496 |
comparison
equal
deleted
inserted
replaced
168:79a2a24453fa | 169:e44b7c428d7c |
---|---|
1 #include "animia/util/osx.h" | 1 #include "animia/util/osx.h" |
2 | |
3 #include <string> | |
4 #include <memory> | |
2 | 5 |
3 #ifdef HAVE_COREFOUNDATION | 6 #ifdef HAVE_COREFOUNDATION |
4 #include <CoreFoundation/CoreFoundation.h> | 7 #include <CoreFoundation/CoreFoundation.h> |
5 #endif | 8 #endif |
6 | 9 |
7 namespace animia::internal::osx::util { | 10 namespace animia::internal::osx::util { |
8 | 11 |
9 #ifdef HAVE_COREFOUNDATION | 12 #ifdef HAVE_COREFOUNDATION |
10 /* All of these LaunchServices things use *internal functions* that are subject | 13 /* I don't want to have to call CFRelease */ |
11 ** to change. Granted, it's not very likely that these will change very much | 14 template<typename T> |
12 ** because I'm fairly sure Apple uses them lots in their own internal code. | 15 struct CFDeleter { |
16 using pointer = T; | |
17 void operator()(pointer p) { CFRelease(p); } | |
18 } | |
19 | |
20 template<typename T> | |
21 typedef CFReference = std::unique_ptr<T, CFDeleter>; | |
22 | |
23 /* all of these LaunchServices things use *internal functions* that are subject | |
24 * to change. Granted, it's not very likely that these will change very much | |
25 * because I'm fairly sure Apple uses them lots in their own internal code. | |
13 */ | 26 */ |
14 | |
15 /* from RDProcess */ | |
16 typedef CFTypeRef (*LSASNCreateWithPidSpec)(CFAllocatorRef, pid_t); | 27 typedef CFTypeRef (*LSASNCreateWithPidSpec)(CFAllocatorRef, pid_t); |
17 typedef CFDictionaryRef (*LSCopyApplicationInformationSpec)(int, CFTypeRef, CFArrayRef); | 28 typedef CFDictionaryRef (*LSCopyApplicationInformationSpec)(int, CFTypeRef, CFArrayRef); |
18 | 29 |
19 static LSCopyApplicationInformationSpec LSCopyApplicationInformation = nullptr; | 30 static LSCopyApplicationInformationSpec LSCopyApplicationInformation = nullptr; |
20 static LSASNCreateWithPidSpec LSASNCreateWithPid = nullptr; | 31 static LSASNCreateWithPidSpec LSASNCreateWithPid = nullptr; |
21 | 32 |
22 /* retrieved from LaunchServicesSPI.h in WebKit */ | 33 /* retrieved from LaunchServicesSPI.h in WebKit */ |
23 static constexpr int kLSDefaultSessionID = -2; | 34 static constexpr int kLSDefaultSessionID = -2; |
35 | |
24 static const CFStringRef kLaunchServicesBundleID = CFSTR("com.apple.LaunchServices"); | 36 static const CFStringRef kLaunchServicesBundleID = CFSTR("com.apple.LaunchServices"); |
25 | 37 |
26 /* retrieved dynamically */ | 38 /* retrieved dynamically */ |
27 static CFStringRef kLSDisplayNameKey = nullptr; | 39 static CFStringRef kLSDisplayNameKey = nullptr; |
28 static CFStringRef kLSPIDKey = nullptr; | 40 static CFStringRef kLSPIDKey = nullptr; |
54 static bool LaunchServicesGetProcessName(pid_t pid, std::string& result) { | 66 static bool LaunchServicesGetProcessName(pid_t pid, std::string& result) { |
55 if (!LSCopyApplicationInformation || !LSASNCreateWithPid) | 67 if (!LSCopyApplicationInformation || !LSASNCreateWithPid) |
56 if (!GetLaunchServicesPrivateSymbols()) | 68 if (!GetLaunchServicesPrivateSymbols()) |
57 return false; | 69 return false; |
58 | 70 |
59 CFTypeRef asn = LSASNCreateWithPid(kCFAllocatorDefault, pid); | 71 CFReference<CFTypeRef> asn = LSASNCreateWithPid(kCFAllocatorDefault, pid); |
60 | 72 |
61 CFArrayRef request_array = CFArrayCreate(NULL, (const void **)kLSDisplayNameKey, 1, NULL); | 73 CFReference<CFArrayRef> request_array = CFArrayCreate(NULL, (const void **)kLSDisplayNameKey, 1, NULL); |
62 | 74 |
63 CFDictionaryRef dictionary = LSCopyApplicationInformation(kLaunchServicesMagicConstant, asn, request_array); | 75 CFReference<CFDictionaryRef> dictionary = LSCopyApplicationInformation(kLaunchServicesMagicConstant, asn, request_array.get()); |
64 | 76 if (!dictionary.get()) |
65 CFRelease(request_array); | |
66 if (!dictionary) | |
67 return false; | 77 return false; |
68 | 78 |
69 CFStringRef str; | 79 CFReference<CFStringRef> str; |
70 if (!CFDictionaryGetValueIfPresent(dictionary, kLSDisplayNameKey, (CFTypeRef*)&str) || !str) { | 80 { |
71 CFRelease(dictionary); | 81 CFStringRef rstr; |
72 return false; | 82 if (!CFDictionaryGetValueIfPresent(dictionary, kLSDisplayNameKey, (CFTypeRef*)&rstr) || !rstr) |
73 } | 83 return false; |
74 CFRetain(str); | 84 str.reset(rstr); |
75 | |
76 CFRelease(dictionary); | |
77 | |
78 result.reserve(CFStringGetMaximumSizeForEncoding(CFStringGetLength(str), kCFStringEncodingUTF8) + 1); | |
79 | |
80 if (!CFStringGetCString(str, &result.front(), result.length(), result.length())) { | |
81 CFRelease(str); | |
82 return false; | |
83 } | 85 } |
84 | 86 |
85 CFRelease(str); | 87 result.reserve(CFStringGetMaximumSizeForEncoding(CFStringGetLength(str.get()), kCFStringEncodingUTF8) + 1); |
88 | |
89 if (!CFStringGetCString(str.get(), &result.front(), result.length(), result.length())) | |
90 return false; | |
86 | 91 |
87 return true; | 92 return true; |
88 } | 93 } |
89 #endif // HAVE_COREFOUNDATION | 94 #endif // HAVE_COREFOUNDATION |
90 | 95 |