Skip to content

Instantly share code, notes, and snippets.

@mdippery
Last active March 14, 2025 23:34
Show Gist options
  • Save mdippery/87c2b8557c830e335673e89a58525d40 to your computer and use it in GitHub Desktop.
Save mdippery/87c2b8557c830e335673e89a58525d40 to your computer and use it in GitHub Desktop.
Get window information using Core Graphics
#import <stdio.h>
#import <sys/sysctl.h>
#import <unistd.h>
#import <Foundation/Foundation.h>
#import <CoreGraphics/CoreGraphics.h>
/* Returns the parent of any arbitrary process, more flexible than
* getpid() and getppid().
*/
pid_t get_parent_pid(pid_t pid)
{
struct kinfo_proc proc;
size_t proc_size = sizeof(proc);
int mib[4] = { CTL_KERN, KERN_PROC, KERN_PROC_PID, pid };
if (sysctl(mib, 4, &proc, &proc_size, NULL, 0) == -1) {
perror("sysctl");
return -1;
}
return proc.kp_eproc.e_ppid;
}
void follow_pid(pid_t pid)
{
fprintf(stderr, "Following pid chain\n");
while (pid > 0) {
pid = get_parent_pid(pid);
fprintf(stderr, " - %u\n", pid);
}
}
int main(int argc, char **argv)
{
NSAutoreleasePool *pool = [[NSAutoreleasePool alloc] init];
pid_t myPID = getpid();
fprintf(stderr, "my pid = %u\n", myPID);
follow_pid(myPID);
CFArrayRef windowInfo = CGWindowListCopyWindowInfo(kCGWindowListOptionOnScreenOnly, kCGNullWindowID);
/* fprintf(stderr, "windowInfo at %p\n", windowInfo); */
CFIndex windowCount = CFArrayGetCount(windowInfo);
/* fprintf(stderr, "Found %ld windows\n", windowCount); */
for (long i = 0; i < windowCount; ++i) {
NSDictionary *windowDict = (__bridge NSDictionary *) CFArrayGetValueAtIndex(windowInfo, i);
NSLog(@"%@", windowDict);
}
[pool release];
return 0;
}
Sign up for free to join this conversation on GitHub. Already have an account? Sign in to comment