App content protection failure

I have set kCGWindowSharingState to none for my app. Even though the sharing state is none, I am still able to record my app's content using the native screen recording app and third-party apps.

My App window detaills:

{
    kCGWindowAlpha = 1;
    kCGWindowBounds =     {
        Height = 700;
        Width = 1000;
        X = 1956;
        Y = 105;
    };
    kCGWindowIsOnscreen = 1;
    kCGWindowLayer = 0;
    kCGWindowMemoryUsage = 2176;
    kCGWindowName = "Create and Sell Online Training Programs - TrainerCentral";
    kCGWindowNumber = 13352;
    kCGWindowOwnerName = TrainerCentral;
    kCGWindowOwnerPID = 95409;
    kCGWindowSharingState = 0;
    kCGWindowStoreType = 1;
}
Answered by DTS Engineer in 796718022

I have set kCGWindowSharingState to none for my app. Even though the sharing state is none, I am still able to record my app's content using the native screen recording app and third-party apps.

Yes, that's correct. More specifically, what kCGWindowSharingState (and it's NSWindow equivalent, NSWindowSharingNone) actually change is how the window content is handled at the CGWindow level, not the broader system level. So, for example, "CGWindowListCreateImage" should either composite a black rectangle in place of the unshared content or fail entirely (when there isn't any content "left" to capture ). However, the key words there were "at the CGWindow level".

Virtually all screen recording/remote control app opperate below the window level, which means kCGWindowSharingState has no effect. The behavior here is basically deliberate- interpreting the underlying content from the "final" screen mix* is far more difficult than the window layer and a remote desktop app which couldn't interact with lots of applications wouldn't be very useful.

*In a typical remote desktop app, the controlling app doesn't actually "know" anything about the contents that are on screen. It simply presents an image of the current screen state and maps mouse motion/clicks on that image to the coordinate system of the machine it's controlling. The machine being controlled is still responsible for translating those events into the changes that actually happen on the target machine.

Anticipating your next question, no, I don't know of any (good) way that an app can prevent it's content from being captured. The only places I'm aware of the system doing this in the DVD Player application and when playing HLS protected content through AVFoundation. In both cases, the process involved is both private and not something that could easily be applied to more "general" content.

__
Kevin Elliott
DTS Engineer, CoreOS/Hardware

I have set kCGWindowSharingState to none for my app. Even though the sharing state is none, I am still able to record my app's content using the native screen recording app and third-party apps.

Yes, that's correct. More specifically, what kCGWindowSharingState (and it's NSWindow equivalent, NSWindowSharingNone) actually change is how the window content is handled at the CGWindow level, not the broader system level. So, for example, "CGWindowListCreateImage" should either composite a black rectangle in place of the unshared content or fail entirely (when there isn't any content "left" to capture ). However, the key words there were "at the CGWindow level".

Virtually all screen recording/remote control app opperate below the window level, which means kCGWindowSharingState has no effect. The behavior here is basically deliberate- interpreting the underlying content from the "final" screen mix* is far more difficult than the window layer and a remote desktop app which couldn't interact with lots of applications wouldn't be very useful.

*In a typical remote desktop app, the controlling app doesn't actually "know" anything about the contents that are on screen. It simply presents an image of the current screen state and maps mouse motion/clicks on that image to the coordinate system of the machine it's controlling. The machine being controlled is still responsible for translating those events into the changes that actually happen on the target machine.

Anticipating your next question, no, I don't know of any (good) way that an app can prevent it's content from being captured. The only places I'm aware of the system doing this in the DVD Player application and when playing HLS protected content through AVFoundation. In both cases, the process involved is both private and not something that could easily be applied to more "general" content.

__
Kevin Elliott
DTS Engineer, CoreOS/Hardware

Accepted Answer

In iOS, we receive a callback event when a user takes a screenshot. This is achieved by listening to the "UIApplicationUserDidTakeScreenshotNotification" event. Is there a similar event callback available for macOS?

[[NSNotificationCenter defaultCenter] addObserverForName:UIApplicationUserDidTakeScreenshotNotification
                                                  object:nil
                                                   queue:mainQueue
                                              usingBlock:^(NSNotification *note) {
                                                  // executes after screenshot
                                                  NSLog(@"Screenshot Detection : %@", note);
                                                  UIAlertView *screenshotAlert = [[UIAlertView alloc] initWithTitle:@"Screenshot Detected" message:@"Oh Oh no screenshot bruhh" delegate:nil cancelButtonTitle:@"OK" otherButtonTitles:nil];
                                                  [screenshotAlert show];
                                              }];

In iOS, we receive a callback event when a user takes a screenshot. This is achieved by listening to the "UIApplicationUserDidTakeScreenshotNotification" event. Is there a similar event callback available for macOS?

No, I don't think the system posts any notification for this.

__
Kevin Elliott
DTS Engineer, CoreOS/Hardware

App content protection failure
 
 
Q