ReactOS 0.4.15-dev-8119-g4fb2fdb
NpfsConnect.c
Go to the documentation of this file.
1/*
2 * PROJECT: ReactOS kernel-mode tests
3 * LICENSE: LGPLv2+ - See COPYING.LIB in the top level directory
4 * PURPOSE: Kernel-Mode Test Suite NPFS Connect test
5 * PROGRAMMER: Thomas Faber <thomas.faber@reactos.org>
6 */
7
8#include <kmt_test.h>
9#include "npfs.h"
10
11#define MAX_INSTANCES 5
12#define IN_QUOTA 4096
13#define OUT_QUOTA 4096
14
15#define CheckServer(ServerHandle, State) \
16 NpCheckServerPipe(ServerHandle, \
17 BYTE_STREAM, QUEUE, BYTE_STREAM, DUPLEX, \
18 MAX_INSTANCES, 1, \
19 IN_QUOTA, 0, \
20 OUT_QUOTA, OUT_QUOTA, \
21 State)
22
23#define CheckClient(ClientHandle, State) \
24 NpCheckClientPipe(ClientHandle, \
25 BYTE_STREAM, QUEUE, BYTE_STREAM, DUPLEX, \
26 MAX_INSTANCES, 1, \
27 IN_QUOTA, 0, \
28 OUT_QUOTA, OUT_QUOTA, \
29 State)
30
31static
32VOID
35{
36 HANDLE ClientHandle;
37
38 ClientHandle = NULL;
39 Context->Connect.Status = NpOpenPipe(&ClientHandle,
40 Context->Connect.PipePath,
42 Context->Connect.ClientHandle = ClientHandle;
43}
44
45static
46VOID
49{
50 Context->Listen.Status = NpListenPipe(Context->Listen.ServerHandle);
51}
52
53static
57 IN PCWSTR PipePath,
58 IN ULONG MilliSeconds)
59{
60 Context->Work = ConnectPipe;
61 Context->Connect.PipePath = PipePath;
62 return TriggerWork(Context, MilliSeconds);
63}
64
65static
69 IN HANDLE ServerHandle,
70 IN ULONG MilliSeconds)
71{
72 Context->Work = ListenPipe;
73 Context->Listen.ServerHandle = ServerHandle;
74 return TriggerWork(Context, MilliSeconds);
75}
76
77static
78VOID
80 IN HANDLE ServerHandle,
81 IN PCWSTR PipePath)
82{
84 THREAD_CONTEXT ConnectContext;
85 THREAD_CONTEXT ListenContext;
86 BOOLEAN Okay;
87 HANDLE ClientHandle;
88
89 StartWorkerThread(&ConnectContext);
90 StartWorkerThread(&ListenContext);
91
92 /* Server should start out listening */
94
95 /* Connect a client */
96 ClientHandle = NULL;
97 Okay = CheckConnectPipe(&ConnectContext, PipePath, 100);
98 ok_bool_true(Okay, "CheckConnectPipe returned");
99 ok_eq_hex(ConnectContext.Connect.Status, STATUS_SUCCESS);
100 if (NT_SUCCESS(ConnectContext.Connect.Status))
101 {
102 ClientHandle = ConnectContext.Connect.ClientHandle;
104 }
106
107 /* Connect another client */
108 Okay = CheckConnectPipe(&ConnectContext, PipePath, 100);
109 ok_bool_true(Okay, "CheckConnectPipe returned");
110 ok_eq_hex(ConnectContext.Connect.Status, STATUS_PIPE_NOT_AVAILABLE);
111 if (NT_SUCCESS(ConnectContext.Connect.Status))
112 ObCloseHandle(ConnectContext.Connect.ClientHandle, KernelMode);
115
116 /* Disconnecting the client should fail */
117 Status = NpDisconnectPipe(ClientHandle);
121
122 /* Listening on the client should fail */
123 Status = NpListenPipe(ClientHandle);
127
128 /* Close client */
129 if (ClientHandle)
130 ObCloseHandle(ClientHandle, KernelMode);
132
133 /* Connecting a client now should fail */
134 Okay = CheckConnectPipe(&ConnectContext, PipePath, 100);
135 ok_bool_true(Okay, "CheckConnectPipe returned");
136 ok_eq_hex(ConnectContext.Connect.Status, STATUS_PIPE_NOT_AVAILABLE);
137 if (NT_SUCCESS(ConnectContext.Connect.Status))
138 ObCloseHandle(ConnectContext.Connect.ClientHandle, KernelMode);
140
141 /* Listening should fail */
142 Okay = CheckListenPipe(&ListenContext, ServerHandle, 100);
143 ok_bool_true(Okay, "CheckListenPipe returned");
144 if (!skip(Okay, "Listen succeeded unexpectedly\n"))
146
147 /* Disconnect server */
148 Status = NpDisconnectPipe(ServerHandle);
151
152 /* Disconnecting again should fail */
153 Status = NpDisconnectPipe(ServerHandle);
156
157 /* Connecting a client now should fail */
158 Okay = CheckConnectPipe(&ConnectContext, PipePath, 100);
159 ok_bool_true(Okay, "CheckConnectPipe returned");
160 ok_eq_hex(ConnectContext.Connect.Status, STATUS_PIPE_NOT_AVAILABLE);
161 if (NT_SUCCESS(ConnectContext.Connect.Status))
162 ObCloseHandle(ConnectContext.Connect.ClientHandle, KernelMode);
164
165 /**************************************************************************/
166 /* Now listen again */
167 Okay = CheckListenPipe(&ListenContext, ServerHandle, 100);
168 ok_bool_false(Okay, "CheckListenPipe returned");
169 //blocks: CheckServer(ServerHandle, FILE_PIPE_LISTENING_STATE);
170
171 /* Connect client */
172 ClientHandle = NULL;
173 Okay = CheckConnectPipe(&ConnectContext, PipePath, 100);
174 ok_bool_true(Okay, "CheckConnectPipe returned");
175 ok_eq_hex(ConnectContext.Connect.Status, STATUS_SUCCESS);
176 if (NT_SUCCESS(ConnectContext.Connect.Status))
177 {
178 ClientHandle = ConnectContext.Connect.ClientHandle;
180 }
181 Okay = WaitForWork(&ListenContext, 100);
182 ok_bool_true(Okay, "WaitForWork returned");
183 ok_eq_hex(ListenContext.Listen.Status, STATUS_SUCCESS);
185
186 /* Listening again should fail */
187 Okay = CheckListenPipe(&ListenContext, ServerHandle, 100);
188 ok_bool_true(Okay, "CheckListenPipe returned");
189 ok_eq_hex(ListenContext.Listen.Status, STATUS_PIPE_CONNECTED);
192
193 /* Disconnect server */
194 Status = NpDisconnectPipe(ServerHandle);
198
199 /* Close client */
200 if (ClientHandle)
201 ObCloseHandle(ClientHandle, KernelMode);
203
204 /**************************************************************************/
205 /* Listen once more */
206 Okay = CheckListenPipe(&ListenContext, ServerHandle, 100);
207 ok_bool_false(Okay, "CheckListenPipe returned");
208 //blocks: CheckServer(ServerHandle, FILE_PIPE_LISTENING_STATE);
209
210 /* Connect client */
211 ClientHandle = NULL;
212 Okay = CheckConnectPipe(&ConnectContext, PipePath, 100);
213 ok_bool_true(Okay, "CheckConnectPipe returned");
214 ok_eq_hex(ConnectContext.Connect.Status, STATUS_SUCCESS);
215 if (NT_SUCCESS(ConnectContext.Connect.Status))
216 {
217 ClientHandle = ConnectContext.Connect.ClientHandle;
219 }
220 Okay = WaitForWork(&ListenContext, 100);
221 ok_bool_true(Okay, "WaitForWork returned");
222 ok_eq_hex(ListenContext.Listen.Status, STATUS_SUCCESS);
224
225 /* Close server */
226 Status = ObCloseHandle(ServerHandle, KernelMode);
229
230 /* Close client */
231 if (ClientHandle)
232 ObCloseHandle(ClientHandle, KernelMode);
233
234 FinishWorkerThread(&ListenContext);
235 FinishWorkerThread(&ConnectContext);
236}
237
238static KSTART_ROUTINE RunTest;
239static
240VOID
241NTAPI
244{
246 HANDLE ServerHandle;
247
249
250 ServerHandle = INVALID_HANDLE_VALUE;
251 Status = NpCreatePipe(&ServerHandle,
252 DEVICE_NAMED_PIPE L"\\KmtestNpfsConnectTestPipe",
255 IN_QUOTA,
256 OUT_QUOTA);
258 ok(ServerHandle != NULL && ServerHandle != INVALID_HANDLE_VALUE, "ServerHandle = %p\n", ServerHandle);
259 if (!skip(NT_SUCCESS(Status) && ServerHandle != NULL && ServerHandle != INVALID_HANDLE_VALUE, "No pipe\n"))
260 {
262 TestConnect(ServerHandle, DEVICE_NAMED_PIPE L"\\KmtestNpfsConnectTestPipe");
263 }
264}
265
266START_TEST(NpfsConnect)
267{
269
272}
#define OUT_QUOTA
Definition: NpfsConnect.c:13
static BOOLEAN CheckListenPipe(IN PTHREAD_CONTEXT Context, IN HANDLE ServerHandle, IN ULONG MilliSeconds)
Definition: NpfsConnect.c:67
#define CheckClient(ClientHandle, State)
Definition: NpfsConnect.c:23
static VOID ListenPipe(IN OUT PTHREAD_CONTEXT Context)
Definition: NpfsConnect.c:47
#define CheckServer(ServerHandle, State)
Definition: NpfsConnect.c:15
static KSTART_ROUTINE RunTest
Definition: NpfsConnect.c:238
#define IN_QUOTA
Definition: NpfsConnect.c:12
#define MAX_INSTANCES
Definition: NpfsConnect.c:11
static VOID ConnectPipe(IN OUT PTHREAD_CONTEXT Context)
Definition: NpfsConnect.c:33
static BOOLEAN CheckConnectPipe(IN PTHREAD_CONTEXT Context, IN PCWSTR PipePath, IN ULONG MilliSeconds)
Definition: NpfsConnect.c:55
unsigned char BOOLEAN
#define ok_eq_hex(value, expected)
Definition: apitest.h:77
#define ok_bool_false(value, desc)
Definition: apitest.h:79
#define ok_bool_true(value, desc)
Definition: apitest.h:78
#define ok(value,...)
Definition: atltest.h:57
#define skip(...)
Definition: atltest.h:64
#define START_TEST(x)
Definition: atltest.h:75
LONG NTSTATUS
Definition: precomp.h:26
#define NULL
Definition: types.h:112
#define NT_SUCCESS(StatCode)
Definition: apphelp.c:32
#define INVALID_HANDLE_VALUE
Definition: compat.h:731
_In_opt_ PFILE_OBJECT _In_opt_ PETHREAD Thread
Definition: fltkernel.h:2653
Status
Definition: gdiplustypes.h:25
#define FILE_PIPE_DISCONNECTED_STATE
Definition: winternl.h:790
#define FILE_PIPE_LISTENING_STATE
Definition: winternl.h:791
#define FILE_PIPE_CONNECTED_STATE
Definition: winternl.h:792
#define FILE_PIPE_CLOSING_STATE
Definition: winternl.h:793
PKTHREAD KmtStartThread(IN PKSTART_ROUTINE StartRoutine, IN PVOID StartContext OPTIONAL)
VOID KmtFinishThread(IN PKTHREAD Thread OPTIONAL, IN PKEVENT Event OPTIONAL)
#define NpDisconnectPipe(ServerHandle)
Definition: npfs.h:74
BOOLEAN WaitForWork(IN PTHREAD_CONTEXT Context, IN ULONG MilliSeconds)
Definition: NpfsHelpers.c:692
#define BYTE_STREAM
Definition: npfs.h:13
NTSTATUS NpOpenPipe(OUT PHANDLE ClientHandle, IN PCWSTR PipePath, IN ULONG NamedPipeConfiguration)
Definition: NpfsHelpers.c:180
VOID FinishWorkerThread(IN PTHREAD_CONTEXT Context)
Definition: NpfsHelpers.c:685
#define DUPLEX
Definition: npfs.h:21
BOOLEAN TriggerWork(IN PTHREAD_CONTEXT Context, IN ULONG MilliSeconds)
Definition: NpfsHelpers.c:710
#define DEVICE_NAMED_PIPE
Definition: npfs.h:11
NTSTATUS NpCreatePipe(OUT PHANDLE ServerHandle, IN PCWSTR PipePath, IN ULONG ReadMode, IN ULONG CompletionMode, IN ULONG NamedPipeType, IN ULONG NamedPipeConfiguration, IN ULONG MaximumInstances, IN ULONG InboundQuota, IN ULONG OutboundQuota)
VOID StartWorkerThread(OUT PTHREAD_CONTEXT Context)
Definition: NpfsHelpers.c:674
#define NpListenPipe(ServerHandle)
Definition: npfs.h:73
#define QUEUE
Definition: npfs.h:17
#define NpQueryPipe(h, es)
Definition: npfs.h:147
KMT_MESSAGE_HANDLER TestConnect
Definition: connect.c:257
#define KernelMode
Definition: asm.h:34
#define FILE_PIPE_FULL_DUPLEX
Definition: iotypes.h:83
#define UNREFERENCED_PARAMETER(P)
Definition: ntbasedef.h:317
#define STATUS_PIPE_DISCONNECTED
Definition: ntstatus.h:412
#define STATUS_PIPE_NOT_AVAILABLE
Definition: ntstatus.h:408
#define STATUS_PIPE_CONNECTED
Definition: ntstatus.h:414
#define STATUS_ILLEGAL_FUNCTION
Definition: ntstatus.h:411
#define L(x)
Definition: ntvdm.h:50
NTSTATUS NTAPI ObCloseHandle(IN HANDLE Handle, IN KPROCESSOR_MODE AccessMode)
Definition: obhandle.c:3379
#define STATUS_SUCCESS
Definition: shellext.h:65
struct _THREAD_CONTEXT::@1620::@1623 Listen
struct _THREAD_CONTEXT::@1620::@1622 Connect
const uint16_t * PCWSTR
Definition: typedefs.h:57
#define NTAPI
Definition: typedefs.h:36
#define IN
Definition: typedefs.h:39
uint32_t ULONG
Definition: typedefs.h:59
#define OUT
Definition: typedefs.h:40