Last active
March 24, 2020 22:20
-
-
Save knightsc/4678757164b2c63a58856a1acb3dd17e to your computer and use it in GitHub Desktop.
An example of using the libEndpointSecurity.dylib in Catalina
This file contains bidirectional Unicode text that may be interpreted or compiled differently than what appears below. To review, open the file in an editor that reveals hidden Unicode characters.
Learn more about bidirectional Unicode characters
#import <Foundation/Foundation.h> | |
#import <EndpointSecurity/EndpointSecurity.h> | |
#import <os/log.h> | |
#import <bsm/libbsm.h> | |
/* | |
In the beta 1 seed it's not straight forward to create an EndpointSecurity extension. | |
You can use libEndpointSecurity.dylib directly as long as you set the following things: | |
1. Disable SIP | |
2. Give your app the com.apple.developer.endpoint-security.client entitlement | |
3. Run the application as root | |
This code works with Catalina beta 5 | |
*/ | |
void log_message(const es_message_t *message) { | |
pid_t pid = audit_token_to_pid(message->process->audit_token); | |
pid_t target_pid; | |
NSMutableString *log = [[NSMutableString alloc] init]; | |
switch (message->event_type) { | |
case ES_EVENT_TYPE_AUTH_EXEC: | |
[log appendString:@"auth_exec: "]; | |
break; | |
case ES_EVENT_TYPE_AUTH_OPEN: | |
[log appendString:@"auth_open: "]; | |
break; | |
case ES_EVENT_TYPE_AUTH_KEXTLOAD: | |
[log appendString:@"auth_kextload: "]; | |
break; | |
case ES_EVENT_TYPE_AUTH_MMAP: | |
[log appendString:@"auth_mmap: "]; | |
break; | |
case ES_EVENT_TYPE_AUTH_MPROTECT: | |
[log appendString:@"auth_mprotect: "]; | |
break; | |
case ES_EVENT_TYPE_AUTH_MOUNT: | |
[log appendString:@"auth_mount: "]; | |
break; | |
case ES_EVENT_TYPE_AUTH_RENAME: | |
[log appendString:@"auth_rename: "]; | |
break; | |
case ES_EVENT_TYPE_AUTH_SIGNAL: | |
[log appendString:[NSString stringWithFormat:@"%8d auth_signal: %d", pid, message->event.signal.sig]]; | |
break; | |
case ES_EVENT_TYPE_AUTH_UNLINK: | |
[log appendString:@"auth_unlink: "]; | |
break; | |
case ES_EVENT_TYPE_NOTIFY_EXEC: | |
[log appendString:[NSString stringWithFormat:@"%8d exec: %s", message->process->ppid, message->event.exec.target->executable->path.data]]; | |
break; | |
case ES_EVENT_TYPE_NOTIFY_OPEN: | |
[log appendString:[NSString stringWithFormat:@"%8d open: %s", pid, message->event.open.file->path.data]]; | |
break; | |
case ES_EVENT_TYPE_NOTIFY_FORK: | |
[log appendString:@"fork: "]; | |
break; | |
case ES_EVENT_TYPE_NOTIFY_CLOSE: | |
[log appendString:[NSString stringWithFormat:@"%8d close: %s", pid, message->event.close.target->path.data]]; | |
break; | |
case ES_EVENT_TYPE_NOTIFY_CREATE: | |
[log appendString:@"create: "]; | |
break; | |
case ES_EVENT_TYPE_NOTIFY_EXCHANGEDATA: | |
[log appendString:@"exchangedata: "]; | |
break; | |
case ES_EVENT_TYPE_NOTIFY_EXIT: | |
[log appendString:@"exit: "]; | |
break; | |
case ES_EVENT_TYPE_NOTIFY_GET_TASK: | |
target_pid = audit_token_to_pid(message->event.get_task.target->audit_token); | |
[log appendString:[NSString stringWithFormat:@"%8d get_task: %d", pid, target_pid]]; | |
break; | |
case ES_EVENT_TYPE_NOTIFY_KEXTLOAD: | |
[log appendString:@"kextload: "]; | |
break; | |
case ES_EVENT_TYPE_NOTIFY_KEXTUNLOAD: | |
[log appendString:@"kextunload: "]; | |
break; | |
case ES_EVENT_TYPE_NOTIFY_LINK: | |
[log appendString:@"link: "]; | |
break; | |
case ES_EVENT_TYPE_NOTIFY_MMAP: | |
[log appendString:@"mmap: "]; | |
break; | |
case ES_EVENT_TYPE_NOTIFY_MPROTECT: | |
[log appendString:@"mprotect: "]; | |
break; | |
case ES_EVENT_TYPE_NOTIFY_MOUNT: | |
[log appendString:@"mount: "]; | |
break; | |
case ES_EVENT_TYPE_NOTIFY_UNMOUNT: | |
[log appendString:@"unmount: "]; | |
break; | |
case ES_EVENT_TYPE_NOTIFY_IOKIT_OPEN: | |
[log appendString:@"iokit_open: "]; | |
break; | |
case ES_EVENT_TYPE_NOTIFY_RENAME: | |
[log appendString:@"rename: "]; | |
break; | |
case ES_EVENT_TYPE_NOTIFY_SETATTRLIST: | |
[log appendString:@"setattrlist: "]; | |
break; | |
case ES_EVENT_TYPE_NOTIFY_SETEXTATTR: | |
[log appendString:@"setextattr: "]; | |
break; | |
case ES_EVENT_TYPE_NOTIFY_SETFLAGS: | |
[log appendString:@"setflags: "]; | |
break; | |
case ES_EVENT_TYPE_NOTIFY_SETMODE: | |
[log appendString:@"setmode: "]; | |
break; | |
case ES_EVENT_TYPE_NOTIFY_SETOWNER: | |
[log appendString:@"setowner: "]; | |
break; | |
case ES_EVENT_TYPE_NOTIFY_SIGNAL: | |
[log appendString:@"signal: "]; | |
break; | |
case ES_EVENT_TYPE_NOTIFY_UNLINK: | |
[log appendString:@"unlink: "]; | |
break; | |
case ES_EVENT_TYPE_NOTIFY_WRITE: | |
[log appendString:@"write: "]; | |
break; | |
case ES_EVENT_TYPE_AUTH_FILE_PROVIDER_MATERIALIZE: | |
[log appendString:@"auth_file_provider_materialize: "]; | |
break; | |
case ES_EVENT_TYPE_NOTIFY_FILE_PROVIDER_MATERIALIZE: | |
[log appendString:@"file_provider_materialize: "]; | |
break; | |
case ES_EVENT_TYPE_AUTH_FILE_PROVIDER_UPDATE: | |
[log appendString:@"auth_file_provider_update: "]; | |
break; | |
case ES_EVENT_TYPE_NOTIFY_FILE_PROVIDER_UPDATE: | |
[log appendString:@"file_provider_update: "]; | |
break; | |
case ES_EVENT_TYPE_AUTH_READLINK: | |
[log appendString:@"auth_readlink: "]; | |
break; | |
case ES_EVENT_TYPE_NOTIFY_READLINK: | |
[log appendString:@"readlink: "]; | |
break; | |
case ES_EVENT_TYPE_AUTH_TRUNCATE: | |
[log appendString:@"auth_truncate: "]; | |
break; | |
case ES_EVENT_TYPE_NOTIFY_TRUNCATE: | |
[log appendString:@"truncate: "]; | |
break; | |
case ES_EVENT_TYPE_AUTH_LINK: | |
[log appendString:@"auth_link: "]; | |
break; | |
case ES_EVENT_TYPE_NOTIFY_LOOKUP: | |
[log appendString:@"lookup: "]; | |
break; | |
case ES_EVENT_TYPE_LAST: | |
os_log_error(OS_LOG_DEFAULT, "impossible"); | |
break; | |
} | |
const char *s = [log UTF8String]; | |
os_log(OS_LOG_DEFAULT, "%s", s); | |
} | |
int main(int argc, const char * argv[]) { | |
@autoreleasepool { | |
os_log(OS_LOG_DEFAULT, "Starting endpoint security..."); | |
es_client_t *client; | |
es_new_client_result_t res = es_new_client(&client, ^(es_client_t *client, const es_message_t *message) { | |
pid_t ppid = message->process->ppid; | |
// pid_t pid = audit_token_to_pid(message->proc.audit_token); | |
if (ppid != 1) { | |
// Ignore everything other than the process we're monitoring | |
// es_mute_process(client, message->proc.audit_token); | |
// return; | |
} | |
log_message(message); | |
// For now just auth everything | |
if (message->action_type == ES_ACTION_TYPE_AUTH) { | |
es_respond_result_t res = es_respond_auth_result(client, message, ES_AUTH_RESULT_ALLOW, false); | |
if (res != ES_RESPOND_RESULT_SUCCESS) { | |
os_log_error(OS_LOG_DEFAULT, "es_respond_auth_result failed: %d", res); | |
} | |
} | |
}); | |
// es_new_client_result_t res = es_new_client(&client, ^(es_client_t *client, const es_message_t *message) { | |
// }); | |
if (res != ES_NEW_CLIENT_RESULT_SUCCESS) { | |
os_log_error(OS_LOG_DEFAULT, "es_new_client failed: %d", res); | |
exit(1); | |
} | |
es_clear_cache_result_t cres = es_clear_cache(client); | |
if (cres != ES_CLEAR_CACHE_RESULT_SUCCESS) { | |
os_log_error(OS_LOG_DEFAULT, "es_clear_cache failed: %d", cres); | |
exit(1); | |
} | |
// 16 is the max? why?????!!!??!? | |
// Maybe if we split the request into two groups then it will work? | |
// es_event_type_t events[] = { | |
// ES_EVENT_TYPE_NOTIFY_EXEC, | |
// ES_EVENT_TYPE_NOTIFY_OPEN, | |
// ES_EVENT_TYPE_NOTIFY_FORK, | |
// ES_EVENT_TYPE_NOTIFY_CLOSE, | |
// ES_EVENT_TYPE_NOTIFY_CREATE, | |
// ES_EVENT_TYPE_NOTIFY_EXCHANGEDATA, | |
// ES_EVENT_TYPE_NOTIFY_EXIT, | |
// ES_EVENT_TYPE_NOTIFY_GET_TASK, | |
// ES_EVENT_TYPE_NOTIFY_KEXTLOAD, | |
// ES_EVENT_TYPE_NOTIFY_KEXTUNLOAD, | |
// ES_EVENT_TYPE_NOTIFY_LINK, | |
// ES_EVENT_TYPE_NOTIFY_MMAP, | |
// ES_EVENT_TYPE_NOTIFY_MPROTECT, | |
// ES_EVENT_TYPE_NOTIFY_MOUNT, | |
// ES_EVENT_TYPE_NOTIFY_UNMOUNT, | |
// ES_EVENT_TYPE_NOTIFY_IOKIT_OPEN, | |
// ES_EVENT_TYPE_NOTIFY_RENAME, | |
// ES_EVENT_TYPE_NOTIFY_SETATTRLIST, | |
// ES_EVENT_TYPE_NOTIFY_SETEXTATTR, | |
// ES_EVENT_TYPE_NOTIFY_SETFLAGS, | |
// ES_EVENT_TYPE_NOTIFY_SETMODE, | |
// ES_EVENT_TYPE_NOTIFY_SETOWNER, | |
// ES_EVENT_TYPE_NOTIFY_SIGNAL, | |
// ES_EVENT_TYPE_NOTIFY_UNLINK, | |
// ES_EVENT_TYPE_NOTIFY_WRITE, | |
// ES_EVENT_TYPE_NOTIFY_FILE_PROVIDER_MATERIALIZATION, | |
// ES_EVENT_TYPE_NOTIFY_FILE_PROVIDER_UPDATE | |
// }; | |
es_event_type_t events[] = { | |
ES_EVENT_TYPE_NOTIFY_EXEC | |
}; | |
es_return_t ret = es_subscribe(client, events, sizeof(events) / sizeof(events[0])); | |
if (ret != ES_RETURN_SUCCESS) { | |
os_log(OS_LOG_DEFAULT, "es_subscribe failed"); | |
exit(1); | |
} | |
os_log(OS_LOG_DEFAULT, "Initialized"); | |
NSRunLoop *runLoop = [NSRunLoop currentRunLoop]; | |
[runLoop run]; | |
// Calling this will kernel panic! in b1 and b2 not sure about b3 | |
// if (!es_delete_client(client)) { | |
// os_log_error(OS_LOG_DEFAULT, "es_delete_client failed"); | |
// exit(1); | |
// } | |
} | |
return 0; | |
} |
Sign up for free
to join this conversation on GitHub.
Already have an account?
Sign in to comment
Hi,
Can we check event path is File_type or Folder_type ?
Thanks in advance.