#include <mach/shared_region.h>
+#include <libkern/section_keywords.h>
+
unsigned long cs_procs_killed = 0;
unsigned long cs_procs_invalidated = 0;
int cs_enforcement_panic=0;
#if CONFIG_ENFORCE_SIGNED_CODE
-int cs_enforcement_enable = 1;
+#define DEFAULT_CS_ENFORCEMENT_ENABLE 1
#else
-int cs_enforcement_enable = 0;
+#define DEFAULT_CS_ENFORCEMENT_ENABLE 0
#endif
+SECURITY_READ_ONLY_LATE(int) cs_enforcement_enable = DEFAULT_CS_ENFORCEMENT_ENABLE;
#if CONFIG_ENFORCE_LIBRARY_VALIDATION
-int cs_library_val_enable = 1;
+#define DEFAULT_CS_LIBRARY_VA_ENABLE 1
#else
-int cs_library_val_enable = 0;
+#define DEFAULT_CS_LIBRARY_VA_ENABLE 0
#endif
+SECURITY_READ_ONLY_LATE(int) cs_library_val_enable = DEFAULT_CS_LIBRARY_VA_ENABLE;
#endif /* !SECURE_KERNEL */
int cs_all_vnodes = 0;
lck_grp_attr_t *attr = lck_grp_attr_alloc_init();
cs_lockgrp = lck_grp_alloc_init("KERNCS", attr);
+ lck_grp_attr_free(attr);
}
int
p->p_pid);
proc_lock(p);
p->p_csflags &= ~(CS_KILL | CS_HARD);
+ if (p->p_csflags & CS_VALID)
+ {
+ p->p_csflags |= CS_DEBUGGED;
+ }
proc_unlock(p);
vm_map_switch_protect(get_task_map(p->task), FALSE);
#endif
}
int
-cs_invalid_page(
- addr64_t vaddr)
+cs_invalid_page(addr64_t vaddr, boolean_t *cs_killed)
{
struct proc *p;
int send_kill = 0, retval = 0, verbose = cs_debug;
/* CS_KILL triggers a kill signal, and no you can't have the page. Nothing else. */
if (p->p_csflags & CS_KILL) {
- if (panic_on_cs_killed &&
- vaddr >= SHARED_REGION_BASE &&
- vaddr < SHARED_REGION_BASE + SHARED_REGION_SIZE) {
- panic("<rdar://14393620> cs_invalid_page(va=0x%llx): killing p=%p\n", (uint64_t) vaddr, p);
- }
p->p_csflags |= CS_KILLED;
cs_procs_killed++;
send_kill = 1;
retval = 1;
}
-#if __x86_64__
- if (panic_on_cs_killed &&
- vaddr >= SHARED_REGION_BASE &&
- vaddr < SHARED_REGION_BASE + SHARED_REGION_SIZE) {
- panic("<rdar://14393620> cs_invalid_page(va=0x%llx): cs error p=%p\n", (uint64_t) vaddr, p);
- }
-#endif /* __x86_64__ */
-
/* CS_HARD means fail the mapping operation so the process stays valid. */
if (p->p_csflags & CS_HARD) {
retval = 1;
retval ? "denying" : "allowing (remove VALID)",
send_kill ? " sending SIGKILL" : "");
- if (send_kill)
- threadsignal(current_thread(), SIGKILL, EXC_BAD_ACCESS);
+ if (send_kill) {
+ /* We will set the exit reason for the thread later */
+ threadsignal(current_thread(), SIGKILL, EXC_BAD_ACCESS, FALSE);
+ if (cs_killed) {
+ *cs_killed = TRUE;
+ }
+ } else if (cs_killed) {
+ *cs_killed = FALSE;
+ }
return retval;
return 0;
}
+/*
+ * Returns whether a given process is still valid.
+ */
+int
+cs_valid(struct proc *p)
+{
+
+ if (p == NULL)
+ p = current_proc();
+
+ if (p != NULL && (p->p_csflags & CS_VALID))
+ return 1;
+
+ return 0;
+}
+
/*
* Library validation functions
*/
return 0;
}
+/*
+ * <rdar://problem/24634089> added to allow system level library
+ * validation check at mac_cred_label_update_execve time
+ */
+int
+cs_system_require_lv(void)
+{
+ return cs_library_val_enable ? 1 : 0;
+}
+
+/*
+ * Function: csblob_get_base_offset
+ *
+ * Description: This function returns the base offset into the Mach-O binary
+ * for a given blob.
+*/
+
+off_t
+csblob_get_base_offset(struct cs_blob *blob)
+{
+ return blob->csb_base_offset;
+}
+
+/*
+ * Function: csblob_get_size
+ *
+ * Description: This function returns the size of a given blob.
+*/
+
+vm_size_t
+csblob_get_size(struct cs_blob *blob)
+{
+ return blob->csb_mem_size;
+}
+
+/*
+ * Function: csblob_get_addr
+ *
+ * Description: This function returns the address of a given blob.
+*/
+
+vm_address_t
+csblob_get_addr(struct cs_blob *blob)
+{
+ return blob->csb_mem_kaddr;
+}
+
/*
* Function: csblob_get_platform_binary
*
unsigned int
csblob_get_flags(struct cs_blob *blob)
{
- if (blob)
- return blob->csb_flags;
- return 0;
+ return blob->csb_flags;
}
/*
return csblob->csb_cdhash;
}
+void *
+csblob_entitlements_dictionary_copy(struct cs_blob *csblob)
+{
+ if (!csblob->csb_entitlements) return NULL;
+ osobject_retain(csblob->csb_entitlements);
+ return csblob->csb_entitlements;
+}
+
+void
+csblob_entitlements_dictionary_set(struct cs_blob *csblob, void * entitlements)
+{
+ assert(csblob->csb_entitlements == NULL);
+ if (entitlements) osobject_retain(entitlements);
+ csblob->csb_entitlements = entitlements;
+}
+
/*
* Function: csproc_get_teamid
*