]> git.saurik.com Git - apple/xnu.git/blobdiff - osfmk/UserNotification/KUNCUserNotifications.c
xnu-7195.101.1.tar.gz
[apple/xnu.git] / osfmk / UserNotification / KUNCUserNotifications.c
index 21ef970a07e781fc4fd064a3ad365b400c88920d..59300b656456f5f3a016c6c63c48f6a6e45ddd60 100644 (file)
@@ -1,23 +1,29 @@
 /*
- * Copyright (c) 2000-2004 Apple Computer, Inc. All rights reserved.
+ * Copyright (c) 2000-2019 Apple Inc. All rights reserved.
  *
- * @APPLE_LICENSE_HEADER_START@
- * 
- * The contents of this file constitute Original Code as defined in and
- * are subject to the Apple Public Source License Version 1.1 (the
- * "License").  You may not use this file except in compliance with the
- * License.  Please obtain a copy of the License at
- * http://www.apple.com/publicsource and read it before using this file.
- * 
- * This Original Code and all software distributed under the License are
- * distributed on an "AS IS" basis, WITHOUT WARRANTY OF ANY KIND, EITHER
+ * @APPLE_OSREFERENCE_LICENSE_HEADER_START@
+ *
+ * This file contains Original Code and/or Modifications of Original Code
+ * as defined in and that are subject to the Apple Public Source License
+ * Version 2.0 (the 'License'). You may not use this file except in
+ * compliance with the License. The rights granted to you under the License
+ * may not be used to create, or enable the creation or redistribution of,
+ * unlawful or unlicensed copies of an Apple operating system, or to
+ * circumvent, violate, or enable the circumvention or violation of, any
+ * terms of an Apple operating system software license agreement.
+ *
+ * Please obtain a copy of the License at
+ * http://www.opensource.apple.com/apsl/ and read it before using this file.
+ *
+ * The Original Code and all software distributed under the License are
+ * distributed on an 'AS IS' basis, WITHOUT WARRANTY OF ANY KIND, EITHER
  * EXPRESS OR IMPLIED, AND APPLE HEREBY DISCLAIMS ALL SUCH WARRANTIES,
  * INCLUDING WITHOUT LIMITATION, ANY WARRANTIES OF MERCHANTABILITY,
- * FITNESS FOR A PARTICULAR PURPOSE OR NON-INFRINGEMENT.  Please see the
- * License for the specific language governing rights and limitations
- * under the License.
- * 
- * @APPLE_LICENSE_HEADER_END@
+ * FITNESS FOR A PARTICULAR PURPOSE, QUIET ENJOYMENT OR NON-INFRINGEMENT.
+ * Please see the License for the specific language governing rights and
+ * limitations under the License.
+ *
+ * @APPLE_OSREFERENCE_LICENSE_HEADER_END@
  */
 
 #include <mach/port.h>
 #include <IOKit/IOCFUnserialize.h>
 #endif
 
+#if CONFIG_USER_NOTIFICATION
 /*
  * DEFINES AND STRUCTURES
  */
 
 struct UNDReply {
-       decl_mutex_data(,lock)                          /* UNDReply lock */
-       int                             userLandNotificationKey;
-       KUNCUserNotificationCallBack    callback;
-       boolean_t                       inprogress;
-       ipc_port_t                      self_port;      /* Our port */
+       decl_lck_mtx_data(, lock);                               /* UNDReply lock */
+       int                             userLandNotificationKey;
+       KUNCUserNotificationCallBack    callback;
+       boolean_t                       inprogress;
+       ipc_port_t                      self_port;      /* Our port */
 };
 
-#define UNDReply_lock(reply)           mutex_lock(&reply->lock)
-#define UNDReply_lock_try(reply)       mutex_lock_try(&(reply)->lock)
-#define UNDReply_unlock(reply)         mutex_unlock(&(reply)->lock)
+#define UNDReply_lock(reply)            lck_mtx_lock(&reply->lock)
+#define UNDReply_unlock(reply)          lck_mtx_unlock(&reply->lock)
+
+extern lck_grp_t LockCompatGroup;
 
 /* forward declarations */
 void UNDReply_deallocate(
-       UNDReplyRef             reply);
+       UNDReplyRef             reply);
 
 
 void
 UNDReply_deallocate(
-       UNDReplyRef             reply)
+       UNDReplyRef             reply)
 {
        ipc_port_t port;
 
@@ -78,6 +86,7 @@ UNDReply_deallocate(
        UNDReply_unlock(reply);
 
        ipc_port_dealloc_kernel(port);
+       lck_mtx_destroy(&reply->lock, &LockCompatGroup);
        kfree(reply, sizeof(struct UNDReply));
        return;
 }
@@ -95,39 +104,45 @@ UNDServer_reference(void)
 
 static void
 UNDServer_deallocate(
-       UNDServerRef    UNDServer)
+       UNDServerRef    UNDServer)
 {
-       if (IP_VALID(UNDServer))
+       if (IP_VALID(UNDServer)) {
                ipc_port_release_send(UNDServer);
+       }
 }
 
-/* 
+/*
  * UND Mig Callbacks
-*/
+ */
 
 kern_return_t
-UNDAlertCompletedWithResult_rpc (
-        UNDReplyRef            reply,
-        int                    result,
-        xmlData_t              keyRef,         /* raw XML bytes */
-        mach_msg_type_number_t keyLen)
+UNDAlertCompletedWithResult_rpc(
+       UNDReplyRef             reply,
+       int                     result,
+       xmlData_t               keyRef,         /* raw XML bytes */
+#ifdef KERNEL_CF
+       mach_msg_type_number_t  keyLen)
+#else
+       __unused mach_msg_type_number_t keyLen)
+#endif
 {
 #ifdef KERNEL_CF
-       CFStringRef             xmlError = NULL;
-       CFDictionaryRef         dict = NULL;
+       CFStringRef             xmlError = NULL;
+       CFDictionaryRef         dict = NULL;
 #else
        const void *dict = (const void *)keyRef;
 #endif
 
-       if (reply == UND_REPLY_NULL || !reply->inprogress)
+       if (reply == UND_REPLY_NULL || !reply->inprogress) {
                return KERN_INVALID_ARGUMENT;
+       }
 
        /*
         * JMM - No C vesion of the Unserialize code in-kernel
         * and no C type for a CFDictionary either.  For now,
         * just pass the raw keyRef through.
         */
-#ifdef KERNEL_CF 
+#ifdef KERNEL_CF
        if (keyRef && keyLen) {
                dict = IOCFUnserialize(keyRef, NULL, NULL, &xmlError);
        }
@@ -139,7 +154,7 @@ UNDAlertCompletedWithResult_rpc (
 #endif /* KERNEL_CF */
 
        if (reply->callback) {
-               (reply->callback)((KUNCUserNotificationID) reply, result, dict);
+               (reply->callback)((int)(KUNCUserNotificationID)reply, result, dict);
        }
 
        UNDReply_lock(reply);
@@ -159,12 +174,13 @@ UNDAlertCompletedWithResult_rpc (
  *             to identify that request.
  */
 kern_return_t
-UNDNotificationCreated_rpc (
-        UNDReplyRef    reply,
-        int            userLandNotificationKey)
+UNDNotificationCreated_rpc(
+       UNDReplyRef     reply,
+       int             userLandNotificationKey)
 {
-       if (reply == UND_REPLY_NULL)
+       if (reply == UND_REPLY_NULL) {
                return KERN_INVALID_ARGUMENT;
+       }
 
        UNDReply_lock(reply);
        if (reply->inprogress || reply->userLandNotificationKey != -1) {
@@ -178,36 +194,29 @@ UNDNotificationCreated_rpc (
 
 /*
  * KUNC Functions
-*/
+ */
 
 
 KUNCUserNotificationID
-KUNCGetNotificationID()
+KUNCGetNotificationID(void)
 {
        UNDReplyRef reply;
 
        reply = (UNDReplyRef) kalloc(sizeof(struct UNDReply));
        if (reply != UND_REPLY_NULL) {
-               reply->self_port = ipc_port_alloc_kernel();
-               if (reply->self_port == IP_NULL) {
-                       kfree(reply, sizeof(struct UNDReply));
-                       reply = UND_REPLY_NULL;
-               } else {
-                       mutex_init(&reply->lock, 0);
-                       reply->userLandNotificationKey = -1;
-                       reply->inprogress = FALSE;
-                       ipc_kobject_set(reply->self_port,
-                                       (ipc_kobject_t)reply,
-                                       IKOT_UND_REPLY);
-               }
+               reply->self_port = ipc_kobject_alloc_port((ipc_kobject_t)reply,
+                   IKOT_UND_REPLY, IPC_KOBJECT_ALLOC_NONE);
+               lck_mtx_init(&reply->lock, &LockCompatGroup, LCK_ATTR_NULL);
+               reply->userLandNotificationKey = -1;
+               reply->inprogress = FALSE;
        }
        return (KUNCUserNotificationID) reply;
 }
 
 
-kern_return_t KUNCExecute(char executionPath[1024], int uid, int gid)
+kern_return_t
+KUNCExecute(char executionPath[1024], int uid, int gid)
 {
-
        UNDServerRef UNDServer;
 
        UNDServer = UNDServer_reference();
@@ -220,15 +229,17 @@ kern_return_t KUNCExecute(char executionPath[1024], int uid, int gid)
        return MACH_SEND_INVALID_DEST;
 }
 
-kern_return_t KUNCUserNotificationCancel(
+kern_return_t
+KUNCUserNotificationCancel(
        KUNCUserNotificationID id)
 {
        UNDReplyRef reply = (UNDReplyRef)id;
        kern_return_t kr;
        int ulkey;
 
-       if (reply == UND_REPLY_NULL)
+       if (reply == UND_REPLY_NULL) {
                return KERN_INVALID_ARGUMENT;
+       }
 
        UNDReply_lock(reply);
        if (!reply->inprogress) {
@@ -245,10 +256,11 @@ kern_return_t KUNCUserNotificationCancel(
 
                UNDServer = UNDServer_reference();
                if (IP_VALID(UNDServer)) {
-                       kr = UNDCancelNotification_rpc(UNDServer,ulkey);
+                       kr = UNDCancelNotification_rpc(UNDServer, ulkey);
                        UNDServer_deallocate(UNDServer);
-               } else
+               } else {
                        kr = MACH_SEND_INVALID_DEST;
+               }
        } else {
                UNDReply_unlock(reply);
                kr = KERN_SUCCESS;
@@ -259,14 +271,14 @@ kern_return_t KUNCUserNotificationCancel(
 
 kern_return_t
 KUNCUserNotificationDisplayNotice(
-       int             noticeTimeout,
-       unsigned        flags,
-       char            *iconPath,
-       char            *soundPath,
-       char            *localizationPath,
-       char            *alertHeader,
-       char            *alertMessage,
-       char            *defaultButtonTitle)
+       int             noticeTimeout,
+       unsigned        flags,
+       char            *iconPath,
+       char            *soundPath,
+       char            *localizationPath,
+       char            *alertHeader,
+       char            *alertMessage,
+       char            *defaultButtonTitle)
 {
        UNDServerRef UNDServer;
 
@@ -274,14 +286,14 @@ KUNCUserNotificationDisplayNotice(
        if (IP_VALID(UNDServer)) {
                kern_return_t kr;
                kr = UNDDisplayNoticeSimple_rpc(UNDServer,
-                                       noticeTimeout,
-                                       flags,
-                                       iconPath,
-                                       soundPath,
-                                       localizationPath,
-                                       alertHeader,
-                                       alertMessage,
-                                       defaultButtonTitle);
+                   noticeTimeout,
+                   flags,
+                   iconPath,
+                   soundPath,
+                   localizationPath,
+                   alertHeader,
+                   alertMessage,
+                   defaultButtonTitle);
                UNDServer_deallocate(UNDServer);
                return kr;
        }
@@ -290,35 +302,35 @@ KUNCUserNotificationDisplayNotice(
 
 kern_return_t
 KUNCUserNotificationDisplayAlert(
-       int             alertTimeout,
-       unsigned        flags,
-       char            *iconPath,
-       char            *soundPath,
-       char            *localizationPath,
-       char            *alertHeader,
-       char            *alertMessage,
-       char            *defaultButtonTitle,
-       char            *alternateButtonTitle,
-       char            *otherButtonTitle,
-       unsigned        *responseFlags)
+       int             alertTimeout,
+       unsigned        flags,
+       char            *iconPath,
+       char            *soundPath,
+       char            *localizationPath,
+       char            *alertHeader,
+       char            *alertMessage,
+       char            *defaultButtonTitle,
+       char            *alternateButtonTitle,
+       char            *otherButtonTitle,
+       unsigned        *responseFlags)
 {
-       UNDServerRef    UNDServer;
-       
+       UNDServerRef    UNDServer;
+
        UNDServer = UNDServer_reference();
        if (IP_VALID(UNDServer)) {
-               kern_return_t   kr;
+               kern_return_t   kr;
                kr = UNDDisplayAlertSimple_rpc(UNDServer,
-                                      alertTimeout,
-                                      flags,
-                                      iconPath,
-                                      soundPath,
-                                      localizationPath,
-                                      alertHeader,
-                                      alertMessage,
-                                      defaultButtonTitle,
-                                      alternateButtonTitle,
-                                      otherButtonTitle,
-                                      responseFlags);
+                   alertTimeout,
+                   flags,
+                   iconPath,
+                   soundPath,
+                   localizationPath,
+                   alertHeader,
+                   alertMessage,
+                   defaultButtonTitle,
+                   alternateButtonTitle,
+                   otherButtonTitle,
+                   responseFlags);
                UNDServer_deallocate(UNDServer);
                return kr;
        }
@@ -327,21 +339,22 @@ KUNCUserNotificationDisplayAlert(
 
 kern_return_t
 KUNCUserNotificationDisplayFromBundle(
-       KUNCUserNotificationID       id,
-       char                         *bundlePath,
-       char                         *fileName,
-       char                         *fileExtension,
-       char                         *messageKey,
-       char                         *tokenString,
+       KUNCUserNotificationID       id,
+       char                         *bundlePath,
+       char                         *fileName,
+       char                         *fileExtension,
+       char                         *messageKey,
+       char                         *tokenString,
        KUNCUserNotificationCallBack callback,
-       __unused int                    contextKey)
+       __unused int                    contextKey)
 {
        UNDReplyRef reply = (UNDReplyRef)id;
        UNDServerRef UNDServer;
        ipc_port_t reply_port;
 
-       if (reply == UND_REPLY_NULL)
+       if (reply == UND_REPLY_NULL) {
                return KERN_INVALID_ARGUMENT;
+       }
        UNDReply_lock(reply);
        if (reply->inprogress == TRUE || reply->userLandNotificationKey != -1) {
                UNDReply_unlock(reply);
@@ -357,12 +370,12 @@ KUNCUserNotificationDisplayFromBundle(
                kern_return_t kr;
 
                kr = UNDDisplayCustomFromBundle_rpc(UNDServer,
-                                           reply_port,
-                                           bundlePath,
-                                           fileName,
-                                           fileExtension,
-                                           messageKey,
-                                           tokenString);
+                   reply_port,
+                   bundlePath,
+                   fileName,
+                   fileExtension,
+                   messageKey,
+                   tokenString);
                UNDServer_deallocate(UNDServer);
                return kr;
        }
@@ -390,13 +403,14 @@ convert_port_to_UNDReply(
                        ip_unlock(port);
                        return UND_REPLY_NULL;
                }
-               reply = (UNDReplyRef) port->ip_kobject;
+               reply = (UNDReplyRef) ip_get_kobject(port);
                assert(reply != UND_REPLY_NULL);
                ip_unlock(port);
                return reply;
        }
        return UND_REPLY_NULL;
 }
+#endif
 
 /*
  *      User interface for setting the host UserNotification Daemon port.
@@ -404,10 +418,15 @@ convert_port_to_UNDReply(
 
 kern_return_t
 host_set_UNDServer(
-        host_priv_t     host_priv,
-        UNDServerRef    server)
+       host_priv_t     host_priv,
+       UNDServerRef    server)
 {
-       return (host_set_user_notification_port(host_priv, server));
+#if CONFIG_USER_NOTIFICATION
+       return host_set_user_notification_port(host_priv, server);
+#else
+#pragma unused(host_priv, server)
+       return KERN_NOT_SUPPORTED;
+#endif
 }
 
 /*
@@ -417,7 +436,12 @@ host_set_UNDServer(
 kern_return_t
 host_get_UNDServer(
        host_priv_t     host_priv,
-       UNDServerRef    *serverp)
+       UNDServerRef    *serverp)
 {
-       return (host_get_user_notification_port(host_priv, serverp));
+#if CONFIG_USER_NOTIFICATION
+       return host_get_user_notification_port(host_priv, serverp);
+#else
+#pragma unused(host_priv, serverp)
+       return KERN_NOT_SUPPORTED;
+#endif
 }