boolean_t ipc_kobject_notify( mach_msg_header_t *request_header, mach_msg_header_t *reply_header) { mach_msg_max_trailer_t * trailer; ipc_port_t port = (ipc_port_t) request_header->msgh_remote_port; ((mig_reply_error_t *) reply_header)->RetCode = MIG_NO_REPLY; trailer = (mach_msg_max_trailer_t *) ((vm_offset_t)request_header + request_header->msgh_size); /* * The kobject notification is privileged and can change the * refcount on kernel-internal objects - make sure * that the message wasn't faked! */ if (0 != bcmp(&trailer->msgh_audit, &KERNEL_AUDIT_TOKEN, sizeof(trailer->msgh_audit))) { return FALSE; } if (0 != bcmp(&trailer->msgh_sender, &KERNEL_SECURITY_TOKEN, sizeof(trailer->msgh_sender))) { return FALSE; } switch (request_header->msgh_id) { case MACH_NOTIFY_NO_SENDERS: switch (ip_kotype(port)) { case IKOT_VOUCHER: ipc_voucher_notify(request_header); return TRUE; case IKOT_VOUCHER_ATTR_CONTROL: ipc_voucher_attr_control_notify(request_header); return TRUE; case IKOT_SEMAPHORE: semaphore_notify(request_header); return TRUE; case IKOT_TASK: task_port_notify(request_header); return TRUE; case IKOT_NAMED_ENTRY: ip_lock(port); /* * Bring the sequence number and mscount in * line with ipc_port_destroy assertion. */ port->ip_mscount = 0; port->ip_messages.imq_seqno = 0; ipc_port_destroy(port); /* releases lock */ return TRUE; case IKOT_UPL: upl_no_senders( request_header->msgh_remote_port, (mach_port_mscount_t) ((mach_no_senders_notification_t *) request_header)->not_count); reply_header->msgh_remote_port = MACH_PORT_NULL; return TRUE; #if CONFIG_AUDIT case IKOT_AU_SESSIONPORT: audit_session_nosenders(request_header); return TRUE; #endif case IKOT_FILEPORT: fileport_notify(request_header); return TRUE; case IKOT_WORK_INTERVAL: work_interval_port_notify(request_header); return TRUE; } break; case MACH_NOTIFY_PORT_DELETED: case MACH_NOTIFY_PORT_DESTROYED: case MACH_NOTIFY_SEND_ONCE: case MACH_NOTIFY_DEAD_NAME: break; default: return FALSE; } switch (ip_kotype(port)) { #ifdef IOKIT case IKOT_IOKIT_OBJECT: case IKOT_IOKIT_CONNECT: case IKOT_IOKIT_SPARE: { return iokit_notify(request_header); } #endif case IKOT_TASK_RESUME: { return task_suspension_notify(request_header); } default: return FALSE; } }
boolean_t ipc_kobject_notify( mach_msg_header_t *request_header, mach_msg_header_t *reply_header) { ipc_port_t port = (ipc_port_t) request_header->msgh_remote_port; ((mig_reply_error_t *) reply_header)->RetCode = MIG_NO_REPLY; switch (request_header->msgh_id) { case MACH_NOTIFY_NO_SENDERS: switch (ip_kotype(port)) { case IKOT_VOUCHER: ipc_voucher_notify(request_header); return TRUE; case IKOT_VOUCHER_ATTR_CONTROL: ipc_voucher_attr_control_notify(request_header); return TRUE; case IKOT_SEMAPHORE: semaphore_notify(request_header); return TRUE; case IKOT_NAMED_ENTRY: ip_lock(port); /* * Bring the sequence number and mscount in * line with ipc_port_destroy assertion. */ port->ip_mscount = 0; port->ip_messages.imq_seqno = 0; ipc_port_destroy(port); /* releases lock */ return TRUE; case IKOT_UPL: upl_no_senders( request_header->msgh_remote_port, (mach_port_mscount_t) ((mach_no_senders_notification_t *) request_header)->not_count); reply_header->msgh_remote_port = MACH_PORT_NULL; return TRUE; #if CONFIG_AUDIT case IKOT_AU_SESSIONPORT: audit_session_nosenders(request_header); return TRUE; #endif case IKOT_FILEPORT: fileport_notify(request_header); return TRUE; } break; case MACH_NOTIFY_PORT_DELETED: case MACH_NOTIFY_PORT_DESTROYED: case MACH_NOTIFY_SEND_ONCE: case MACH_NOTIFY_DEAD_NAME: break; default: return FALSE; } switch (ip_kotype(port)) { #ifdef IOKIT case IKOT_IOKIT_OBJECT: case IKOT_IOKIT_CONNECT: case IKOT_IOKIT_SPARE: { return iokit_notify(request_header); } #endif case IKOT_TASK_RESUME: { return task_suspension_notify(request_header); } default: return FALSE; } }