]> git.saurik.com Git - apple/xnu.git/blobdiff - bsd/sys/kpi_socket.h
xnu-4570.31.3.tar.gz
[apple/xnu.git] / bsd / sys / kpi_socket.h
index 1e63945cf7bdde85e4abaecc0931a67756ef28d0..837611b5c84b7b0ae98985abd5aeb39cdd9ec29d 100644 (file)
@@ -1,8 +1,8 @@
 /*
- * Copyright (c) 2004 Apple Computer, Inc. All rights reserved.
+ * Copyright (c) 2008-2017 Apple Inc. All rights reserved.
  *
  * @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
  * 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,
@@ -22,7 +22,7 @@
  * 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@
  */
 /*!
@@ -56,13 +56,33 @@ struct timeval;
                Calls to your upcall function are not serialized and may be
                called concurrently from multiple threads in the kernel.
 
-               Your upcall function will be called when:
+               Your upcall function will be called:
+                   when there is data more than the low water mark for reading,
+                   or when there is space for a write,
+                   or when there is a connection to accept,
+                   or when a socket is connected,
+                   or when a socket is closed or disconnected
 
        @param so A reference to the socket that's ready.
        @param cookie The cookie passed in when the socket was created.
        @param waitf Indicates whether or not it's safe to block.
 */
-typedef void (*sock_upcall)(socket_t so, void* cookie, int waitf);
+typedef void (*sock_upcall)(socket_t so, void *cookie, int waitf);
+
+#ifdef KERNEL_PRIVATE
+/*!
+       @typedef sock_evupcall
+
+       @discussion sock_evupcall is used by a socket to notify an in kernel
+               client when an event occurs. Instead of making blocking calls in
+               the kernel, a client can specify an upcall which will be called
+               when an event status is available.
+       @param so A reference to the socket that's ready.
+       @param cookie The cookie passed in when the socket was created.
+       @param event Indicates the event as defined by SO_FILT_HINT_*
+*/
+typedef void (*sock_evupcall)(socket_t so, void *cookie, u_int32_t event);
+#endif /* KERNEL_PRIVATE */
 
 /*!
        @function sock_accept
@@ -85,8 +105,17 @@ typedef void (*sock_upcall)(socket_t so, void* cookie, int waitf);
                socket for tracking the connection.
        @result 0 on success otherwise the errno error.
  */
-errno_t sock_accept(socket_t so, struct sockaddr *from, int fromlen,
-    int flags, sock_upcall callback, void* cookie, socket_t *new_so);
+#ifdef KERNEL_PRIVATE
+extern errno_t sock_accept_internal(socket_t so, struct sockaddr *from, int fromlen,
+    int flags, sock_upcall callback, void *cookie, socket_t *new_so);
+
+#define        sock_accept(so, from, fromlen, flags, callback, cookie, new_so) \
+       sock_accept_internal((so), (from), (fromlen), (flags), (callback), \
+       (cookie), (new_so))
+#else
+extern errno_t sock_accept(socket_t so, struct sockaddr *from, int fromlen,
+    int flags, sock_upcall callback, void *cookie, socket_t *new_so);
+#endif /* KERNEL_PRIVATE */
 
 /*!
        @function sock_bind
@@ -96,7 +125,7 @@ errno_t sock_accept(socket_t so, struct sockaddr *from, int fromlen,
        @param to The local address the socket should be bound to.
        @result 0 on success otherwise the errno error.
  */
-errno_t sock_bind(socket_t so, const struct sockaddr *to);
+extern errno_t sock_bind(socket_t so, const struct sockaddr *to);
 
 /*!
        @function sock_connect
@@ -112,7 +141,7 @@ errno_t sock_bind(socket_t so, const struct sockaddr *to);
        @result 0 on success, EINPROGRESS for a non-blocking connect that
                has not completed, otherwise the errno error.
  */
-errno_t sock_connect(socket_t so, const struct sockaddr *to, int flags);
+extern errno_t sock_connect(socket_t so, const struct sockaddr *to, int flags);
 
 #ifdef KERNEL_PRIVATE
 /*
@@ -132,7 +161,7 @@ errno_t sock_connect(socket_t so, const struct sockaddr *to, int flags);
                returned if the connection did not complete in the timeout
                specified.
  */
-errno_t sock_connectwait(socket_t so, const struct timeval *tv);
+extern errno_t sock_connectwait(socket_t so, const struct timeval *tv);
 #endif /* KERNEL_PRIVATE */
 
 /*!
@@ -144,7 +173,7 @@ errno_t sock_connectwait(socket_t so, const struct timeval *tv);
        @param peernamelen Length of storage for the peer name.
        @result 0 on success otherwise the errno error.
  */
-errno_t sock_getpeername(socket_t so, struct sockaddr *peername,
+extern errno_t sock_getpeername(socket_t so, struct sockaddr *peername,
     int peernamelen);
 
 /*!
@@ -156,7 +185,7 @@ errno_t sock_getpeername(socket_t so, struct sockaddr *peername,
        @param socknamelen Length of storage for the socket name.
        @result 0 on success otherwise the errno error.
  */
-errno_t sock_getsockname(socket_t so, struct sockaddr *sockname,
+extern errno_t sock_getsockname(socket_t so, struct sockaddr *sockname,
     int socknamelen);
 
 /*!
@@ -169,8 +198,8 @@ errno_t sock_getsockname(socket_t so, struct sockaddr *sockname,
        @param optlen The length of optval, returns the actual length.
        @result 0 on success otherwise the errno error.
  */
-errno_t sock_getsockopt(socket_t so, int level, int optname, void *optval,
-    int *optlen);
+extern errno_t sock_getsockopt(socket_t so, int level, int optname,
+    void *optval, int *optlen);
 
 /*!
        @function sock_ioctl
@@ -180,7 +209,7 @@ errno_t sock_getsockopt(socket_t so, int level, int optname, void *optval,
        @param argp The argument.
        @result 0 on success otherwise the errno error.
  */
-errno_t sock_ioctl(socket_t so, unsigned long request, void *argp);
+extern errno_t sock_ioctl(socket_t so, unsigned long request, void *argp);
 
 /*!
        @function sock_setsockopt
@@ -192,8 +221,53 @@ errno_t sock_ioctl(socket_t so, unsigned long request, void *argp);
        @param optlen The length of optval.
        @result 0 on success otherwise the errno error.
  */
-errno_t sock_setsockopt(socket_t so, int level, int optname, const void *optval,
-    int optlen);
+extern errno_t sock_setsockopt(socket_t so, int level, int optname,
+    const void *optval, int optlen);
+
+#ifdef KERNEL_PRIVATE
+/*
+       This function was added to support AFP setting the traffic class
+       for a backup stream within a wireless LAN or over link-local address.
+
+       If you feel you need to use this function, please contact us to
+       explain why.
+
+       @function sock_settclassopt
+       @discussion Allows a caller to set the traffic class.
+       @param so The socket.
+       @param optval The option value.
+       @param optlen The length of optval.
+       @result 0 on success otherwise the errno error.
+ */
+extern errno_t sock_settclassopt(socket_t so, const void* optval, size_t optlen);
+
+/*
+       This function was added to support AFP getting the traffic class
+       set on a stream.
+
+       This is also a private API, please contact us if you need to use it.
+
+       @function sockgettclassopt
+       @discussion Allows a caller to get the traffic class.
+       @param so The socket.
+       @param optval The option value.
+       @param optlen The length of optval, returns the actual length.
+       @result 0 on success otherwise the errno error.
+*/
+extern errno_t sock_gettclassopt(socket_t so, void* optval, size_t* optlen);
+
+#ifdef XNU_KERNEL_PRIVATE
+extern void socket_set_traffic_mgt_flags_locked(socket_t so, u_int8_t flags);
+extern void socket_clear_traffic_mgt_flags_locked(socket_t so, u_int8_t flags);
+#endif /* XNU_KERNEL_PRIVATE */
+#ifdef BSD_KERNEL_PRIVATE
+extern void socket_set_traffic_mgt_flags(socket_t so, u_int8_t flags);
+extern void socket_clear_traffic_mgt_flags(socket_t so, u_int8_t flags);
+extern errno_t socket_defunct(struct proc *, socket_t so, int);
+extern errno_t sock_receive_internal(socket_t, struct msghdr *, mbuf_t *,
+    int, size_t *);
+#endif /* BSD_KERNEL_PRIVATE */
+#endif /* KERNEL_PRIVATE */
 
 /*!
        @function sock_listen
@@ -203,7 +277,7 @@ errno_t sock_setsockopt(socket_t so, int level, int optname, const void *optval,
        @param backlog The maximum length of the queue of pending connections.
        @result 0 on success otherwise the errno error.
  */
-errno_t sock_listen(socket_t so, int backlog);
+extern errno_t sock_listen(socket_t so, int backlog);
 
 /*!
        @function sock_receive
@@ -217,7 +291,7 @@ errno_t sock_listen(socket_t so, int backlog);
        @result 0 on success, EWOULDBLOCK if non-blocking and operation
                would cause the thread to block, otherwise the errno error.
  */
-errno_t sock_receive(socket_t so, struct msghdr *msg, int flags,
+extern errno_t sock_receive(socket_t so, struct msghdr *msg, int flags,
     size_t *recvdlen);
 
 /*!
@@ -238,7 +312,7 @@ errno_t sock_receive(socket_t so, struct msghdr *msg, int flags,
        @result 0 on success, EWOULDBLOCK if non-blocking and operation
                would cause the thread to block, otherwise the errno error.
  */
-errno_t sock_receivembuf(socket_t so, struct msghdr *msg, mbuf_t *data,
+extern errno_t sock_receivembuf(socket_t so, struct msghdr *msg, mbuf_t *data,
     int flags, size_t *recvlen);
 
 /*!
@@ -253,7 +327,7 @@ errno_t sock_receivembuf(socket_t so, struct msghdr *msg, mbuf_t *data,
        @result 0 on success, EWOULDBLOCK if non-blocking and operation
                would cause the thread to block, otherwise the errno error.
  */
-errno_t sock_send(socket_t so, const struct msghdr *msg, int flags,
+extern errno_t sock_send(socket_t so, const struct msghdr *msg, int flags,
     size_t *sentlen);
 
 /*!
@@ -270,7 +344,7 @@ errno_t sock_send(socket_t so, const struct msghdr *msg, int flags,
                would cause the thread to block, otherwise the errno error.
                Regardless of return value, the mbuf chain 'data' will be freed.
  */
-errno_t sock_sendmbuf(socket_t so, const struct msghdr *msg, mbuf_t data,
+extern errno_t sock_sendmbuf(socket_t so, const struct msghdr *msg, mbuf_t data,
     int flags, size_t *sentlen);
 
 /*!
@@ -278,10 +352,12 @@ errno_t sock_sendmbuf(socket_t so, const struct msghdr *msg, mbuf_t data,
        @discussion Shutdown one or both directions of a connection. See
                'man 2 shutdown' for more information.
        @param so The socket.
-       @param how SHUT_RD - shutdown receive. SHUT_WR - shutdown send. SHUT_RDWR - shutdown both.
+       @param how SHUT_RD - shutdown receive.
+               SHUT_WR - shutdown send.
+               SHUT_RDWR - shutdown both.
        @result 0 on success otherwise the errno error.
  */
-errno_t sock_shutdown(socket_t so, int how);
+extern errno_t sock_shutdown(socket_t so, int how);
 
 /*!
        @function sock_socket
@@ -297,18 +373,27 @@ errno_t sock_shutdown(socket_t so, int how);
        @param new_so Upon success, a reference to the new socket.
        @result 0 on success otherwise the errno error.
  */
-errno_t sock_socket(int domain, int type, int protocol, sock_upcall callback,
-    void* cookie, socket_t *new_so);
+#ifdef KERNEL_PRIVATE
+extern errno_t sock_socket_internal(int domain, int type, int protocol,
+    sock_upcall callback, void *cookie, socket_t *new_so);
+    
+#define        sock_socket(domain, type, protocol, callback, cookie, new_so) \
+       sock_socket_internal((domain), (type), (protocol), \
+       (callback), (cookie), (new_so))
+#else
+extern errno_t sock_socket(int domain, int type, int protocol,
+    sock_upcall callback, void *cookie, socket_t *new_so);
+#endif /* KERNEL_PRIVATE */
 
 /*!
        @function sock_close
        @discussion Close the socket.
        @param so The socket to close. This should only ever be a socket
                created with sock_socket. Closing a socket created in user space
-               using sock_close may leave a file descriptor pointing to the closed
-               socket, resulting in undefined behavior.
+               using sock_close may leave a file descriptor pointing to the
+               closed socket, resulting in undefined behavior.
  */
-void   sock_close(socket_t so);
+extern void sock_close(socket_t so);
 
 #ifdef KERNEL_PRIVATE
 /*
@@ -321,7 +406,7 @@ void        sock_close(socket_t so);
                that socket. It is used in conjunction with
                sock_release(socket_t so).
  */
-void   sock_retain(socket_t so);
+extern void sock_retain(socket_t so);
 
 /*
        @function sock_release
@@ -331,7 +416,7 @@ void        sock_retain(socket_t so);
                on a socket acquired with sock_retain. When the last retain
                count is reached, this will call sock_close to close the socket.
  */
-void   sock_release(socket_t so);
+extern void sock_release(socket_t so);
 #endif /* KERNEL_PRIVATE */
 
 /*!
@@ -342,7 +427,7 @@ void        sock_release(socket_t so);
        @param on Indicate whether or not the SS_PRIV flag should be set.
        @result 0 on success otherwise the errno error.
  */
-errno_t sock_setpriv(socket_t so, int on);
+extern errno_t sock_setpriv(socket_t so, int on);
 
 /*!
        @function sock_isconnected
@@ -350,7 +435,7 @@ errno_t sock_setpriv(socket_t so, int on);
        @param so The socket to check.
        @result 0 - socket is not connected. 1 - socket is connected.
  */
-int sock_isconnected(socket_t so);
+extern int sock_isconnected(socket_t so);
 
 /*!
        @function sock_isnonblocking
@@ -363,7 +448,7 @@ int sock_isconnected(socket_t so);
                If the parameter is non-zero, the socket will not block.
        @result 0 - socket will block. 1 - socket will not block.
  */
-int sock_isnonblocking(socket_t so);
+extern int sock_isnonblocking(socket_t so);
 
 /*!
        @function sock_gettype
@@ -372,12 +457,12 @@ int sock_isnonblocking(socket_t so);
                parameters following so are NULL, that information is not
                retrieved.
        @param so The socket to check.
-       @param domain The domain of the socket (PF_INET, etc...). May be NULL.
-       @param type The socket type (SOCK_STREAM, SOCK_DGRAM, etc...). May be NULL.
+       @param domain The domain of the socket (PF_INET, ...). May be NULL.
+       @param type The socket type (SOCK_STREAM, SOCK_DGRAM, ...). May be NULL.
        @param protocol The socket protocol. May be NULL.
        @result 0 on success otherwise the errno error.
  */
-errno_t sock_gettype(socket_t so, int *domain, int *type, int *protocol);
+extern errno_t sock_gettype(socket_t so, int *domain, int *type, int *protocol);
 
 #ifdef KERNEL_PRIVATE
 /*
@@ -388,7 +473,7 @@ errno_t sock_gettype(socket_t so, int *domain, int *type, int *protocol);
        @param on Indicate whether or not the SB_NOINTR flag should be set.
        @result 0 on success otherwise the errno error.
  */
-errno_t sock_nointerrupt(socket_t so, int on);
+extern errno_t sock_nointerrupt(socket_t so, int on);
 
 /*
        @function sock_getlistener
@@ -410,7 +495,7 @@ errno_t sock_nointerrupt(socket_t so, int on);
                NULL if the socket is not in the incomplete/completed list
                of a listener.
  */
-socket_t sock_getlistener(socket_t so);
+extern socket_t sock_getlistener(socket_t so);
 
 /*
        @function sock_getaddr
@@ -424,14 +509,90 @@ socket_t sock_getlistener(socket_t so);
        @param peername 0 for local address, and non-zero for peer address.
        @result 0 on success otherwise the errno error.
  */
-errno_t sock_getaddr(socket_t so, struct sockaddr **psockname, int peername);
+extern errno_t sock_getaddr(socket_t so, struct sockaddr **psockname,
+    int peername);
 
 /*
        @function sock_freeaddr
        @discussion Frees the socket address allocated by sock_getaddr.
        @param sockname The socket name to be freed.
  */
-void sock_freeaddr(struct sockaddr *sockname);
+extern void sock_freeaddr(struct sockaddr *sockname);
+
+/*
+       @function sock_setupcall
+       @discussion Set the notifier function to be called when an event
+               occurs on the socket. This may be set to NULL to disable
+               further notifications. Setting the function does not
+               affect currently notifications about to be sent or being sent.
+               Note: When this function is used on a socket passed from
+               userspace it is crucial to call sock_retain() on the socket
+               otherwise a callback could be dispatched on a closed socket
+               and cause a crash.
+       @param sock The socket.
+       @param callback The notifier function
+       @param context A cookie passed directly to the callback
+*/
+extern errno_t sock_setupcall(socket_t sock, sock_upcall callback,
+    void *context);
+
+/*
+       @function sock_setupcalls
+       @discussion Set the notifier function to be called when an event
+               occurs on the socket. This may be set to NULL to disable
+               further notifications. Setting the function does not
+               affect currently notifications about to be sent or being sent.
+               Note: When this function is used on a socket passed from
+               userspace it is crucial to call sock_retain() on the socket
+               otherwise a callback could be dispatched on a closed socket
+               and cause a crash.
+       @param sock The socket.
+       @param read_callback The read notifier function
+       @param read_context A cookie passed directly to the read callback
+       @param write_callback The write notifier function
+       @param write_context A cookie passed directly to the write callback
+*/
+extern errno_t sock_setupcalls(socket_t sock, sock_upcall read_callback,
+    void *read_context, sock_upcall write_callback, void *write_context);
+
+/*
+       @function sock_setupcalls_locked
+       @discussion The locked version of sock_setupcalls
+       @param locked: When sets, indicates that the callbacks expect to be
+                      on a locked socket. Thus, no unlock is done prior to
+                      calling the callback.
+ */
+extern void sock_setupcalls_locked(socket_t sock,
+    sock_upcall rcallback, void *rcontext,
+    sock_upcall wcallback, void *wcontext, int locked);
+
+/*
+       @function sock_catchevents
+       @discussion Set the notifier function to be called when an event
+               occurs on the socket. This may be set to NULL to disable
+               further notifications. Setting the function does not
+               affect currently notifications about to be sent or being sent.
+       @param sock The socket.
+       @param event_callback The event notifier function
+       @param event_context A cookie passed directly to the event callback
+       @param event_mask One or more SO_FILT_HINT_* values OR'ed together,
+               indicating the registered event(s).
+*/
+extern errno_t sock_catchevents(socket_t sock, sock_evupcall event_callback,
+    void *event_context, u_int32_t event_mask);
+
+extern void sock_catchevents_locked(socket_t sock, sock_evupcall ecallback,
+    void *econtext, u_int32_t emask);
+
+
+/*
+       @function sock_iskernel
+       @discussion Returns true if the socket was created by the kernel or
+               is owned by the kernel.
+       @param sock The socket.
+       @result True if the kernel owns the socket.
+*/
+extern int sock_iskernel(socket_t);
 #endif /* KERNEL_PRIVATE */
 
 __END_DECLS