ReactOS Fundraising Campaign 2012
 
€ 4,410 / € 30,000

Information | Donate

Home | Info | Community | Development | myReactOS | Contact Us

  1. Home
  2. Community
  3. Development
  4. myReactOS
  5. Fundraiser 2012

  1. Main Page
  2. Alphabetical List
  3. Data Structures
  4. Directories
  5. File List
  6. Data Fields
  7. Globals
  8. Related Pages

ReactOS Development > Doxygen

lpc_x.h
Go to the documentation of this file.
00001 /*
00002 * PROJECT:         ReactOS Kernel
00003 * LICENSE:         GPL - See COPYING in the top level directory
00004 * FILE:            ntoskrnl/include/internal/lpc_x.h
00005 * PURPOSE:         Internal Inlined Functions for Local Procedure Call
00006 * PROGRAMMERS:     Alex Ionescu (alex.ionescu@reactos.org)
00007 */
00008 
00009 //
00010 // Gets the message type, removing the kernel-mode flag
00011 //
00012 #define LpcpGetMessageType(x)                               \
00013     ((x)->u2.s2.Type &~ LPC_KERNELMODE_MESSAGE)
00014 
00015 //
00016 // Waits on an LPC semaphore for a receive operation
00017 //
00018 #define LpcpReceiveWait(s, w)                               \
00019 {                                                           \
00020     LPCTRACE(LPC_REPLY_DEBUG, "Wait: %p\n", s);             \
00021     Status = KeWaitForSingleObject(s,                       \
00022                                    WrLpcReceive,            \
00023                                    w,                       \
00024                                    FALSE,                   \
00025                                    NULL);                   \
00026     LPCTRACE(LPC_REPLY_DEBUG, "Wait done: %lx\n", Status);  \
00027 }
00028 
00029 //
00030 // Waits on an LPC semaphore for a reply operation
00031 //
00032 #define LpcpReplyWait(s, w)                                 \
00033 {                                                           \
00034     LPCTRACE(LPC_SEND_DEBUG, "Wait: %p\n", s);              \
00035     Status = KeWaitForSingleObject(s,                       \
00036                                    WrLpcReply,              \
00037                                    w,                       \
00038                                    FALSE,                   \
00039                                    NULL);                   \
00040     LPCTRACE(LPC_SEND_DEBUG, "Wait done: %lx\n", Status);   \
00041     if (Status == STATUS_USER_APC)                          \
00042     {                                                       \
00043         /* We were preempted by an APC */                   \
00044         if (KeReadStateSemaphore(s))                        \
00045         {                                                   \
00046             /* It's still signaled, so wait on it */        \
00047             KeWaitForSingleObject(s,                        \
00048                                   WrExecutive,              \
00049                                   KernelMode,               \
00050                                   FALSE,                    \
00051                                   NULL);                    \
00052             Status = STATUS_SUCCESS;                        \
00053         }                                                   \
00054     }                                                       \
00055 }
00056 
00057 //
00058 // Waits on an LPC semaphore for a connect operation
00059 //
00060 #define LpcpConnectWait(s, w)                               \
00061 {                                                           \
00062     LPCTRACE(LPC_CONNECT_DEBUG, "Wait: %p\n", s);           \
00063     Status = KeWaitForSingleObject(s,                       \
00064                                    Executive,               \
00065                                    w,                       \
00066                                    FALSE,                   \
00067                                    NULL);                   \
00068     LPCTRACE(LPC_CONNECT_DEBUG, "Wait done: %lx\n", Status);\
00069     if (Status == STATUS_USER_APC)                          \
00070     {                                                       \
00071         /* We were preempted by an APC */                   \
00072         if (KeReadStateSemaphore(s))                        \
00073         {                                                   \
00074             /* It's still signaled, so wait on it */        \
00075             KeWaitForSingleObject(s,                        \
00076                                   WrExecutive,              \
00077                                   KernelMode,               \
00078                                   FALSE,                    \
00079                                   NULL);                    \
00080             Status = STATUS_SUCCESS;                        \
00081         }                                                   \
00082     }                                                       \
00083 }
00084 
00085 //
00086 // Releases an LPC Semaphore to complete a wait
00087 //
00088 #define LpcpCompleteWait(s)                                 \
00089 {                                                           \
00090     /* Release the semaphore */                             \
00091     LPCTRACE(LPC_SEND_DEBUG, "Release: %p\n", s);           \
00092     KeReleaseSemaphore(s, 1, 1, FALSE);                     \
00093 }
00094 
00095 //
00096 // Allocates a new message
00097 //
00098 static __inline
00099 PLPCP_MESSAGE
00100 LpcpAllocateFromPortZone(VOID)
00101 {
00102     PLPCP_MESSAGE Message;
00103 
00104     /* Allocate a message from the port zone while holding the lock */
00105     KeAcquireGuardedMutex(&LpcpLock);
00106     Message = (PLPCP_MESSAGE)ExAllocateFromPagedLookasideList(&LpcpMessagesLookaside);
00107     if (!Message)
00108     {
00109         /* Fail, and let caller cleanup */
00110         KeReleaseGuardedMutex(&LpcpLock);
00111         return NULL;
00112     }
00113 
00114     /* Initialize it */
00115     InitializeListHead(&Message->Entry);
00116     Message->RepliedToThread = NULL;
00117     Message->Request.u2.ZeroInit = 0;
00118 
00119     /* Release the lock */
00120     KeReleaseGuardedMutex(&LpcpLock);
00121     return Message;
00122 }
00123 
00124 //
00125 // Get the LPC Message associated to the Thread
00126 //
00127 FORCEINLINE
00128 PLPCP_MESSAGE
00129 LpcpGetMessageFromThread(IN PETHREAD Thread)
00130 {
00131     /* Check if the port flag is set */
00132     if (((ULONG_PTR)Thread->LpcReplyMessage) & LPCP_THREAD_FLAG_IS_PORT)
00133     {
00134         /* The pointer is actually a port, not a message, so return NULL */
00135         return NULL;
00136     }
00137 
00138     /* Otherwise, this is a message. Return the pointer */
00139     return (PLPCP_MESSAGE)((ULONG_PTR)Thread->LpcReplyMessage & ~LPCP_THREAD_FLAGS);
00140 }
00141 
00142 FORCEINLINE
00143 PLPCP_PORT_OBJECT
00144 LpcpGetPortFromThread(IN PETHREAD Thread)
00145 {
00146     /* Check if the port flag is set */
00147     if (((ULONG_PTR)Thread->LpcReplyMessage) & LPCP_THREAD_FLAG_IS_PORT)
00148     {
00149         /* The pointer is actually a port, return it */
00150         return (PLPCP_PORT_OBJECT)((ULONG_PTR)Thread->LpcWaitingOnPort &
00151                        ~LPCP_THREAD_FLAGS);
00152     }
00153 
00154     /* Otherwise, this is a message. There is nothing to return */
00155     return NULL;
00156 }
00157 
00158 FORCEINLINE
00159 VOID
00160 LpcpSetPortToThread(IN PETHREAD Thread,
00161                     IN PLPCP_PORT_OBJECT Port)
00162 {
00163     /* Set the port object */
00164     Thread->LpcWaitingOnPort = (PVOID)(((ULONG_PTR)Port) |
00165                                        LPCP_THREAD_FLAG_IS_PORT);
00166 }

Generated on Sat May 26 2012 04:36:07 for ReactOS by doxygen 1.7.6.1

ReactOS is a registered trademark or a trademark of ReactOS Foundation in the United States and other countries.