2 * PROJECT: ReactOS API tests
3 * LICENSE: LGPLv2.1+ - See COPYING.LIB in the top level directory
4 * PURPOSE: Test for RtlFirstFreeAce
5 * PROGRAMMERS: Thomas Faber <thomas.faber@reactos.org>
13 _In_ SIZE_T SizeRequested
)
16 SIZE_T Size
= PAGE_ROUND_UP(SizeRequested
+ PAGE_SIZE
);
17 PVOID VirtualMemory
= NULL
;
20 Status
= NtAllocateVirtualMemory(NtCurrentProcess(), &VirtualMemory
, 0, &Size
, MEM_RESERVE
, PAGE_NOACCESS
);
22 if (!NT_SUCCESS(Status
))
28 Status
= NtAllocateVirtualMemory(NtCurrentProcess(), &VirtualMemory
, 0, &Size
, MEM_COMMIT
, PAGE_READWRITE
);
29 if (!NT_SUCCESS(Status
))
32 Status
= NtFreeVirtualMemory(NtCurrentProcess(), &VirtualMemory
, &Size
, MEM_RELEASE
);
33 ok(Status
== STATUS_SUCCESS
, "Status = %lx\n", Status
);
38 StartOfBuffer
= VirtualMemory
;
39 StartOfBuffer
+= Size
- SizeRequested
;
50 PVOID VirtualMemory
= (PVOID
)PAGE_ROUND_DOWN((SIZE_T
)Pointer
);
53 Status
= NtFreeVirtualMemory(NtCurrentProcess(), &VirtualMemory
, &Size
, MEM_RELEASE
);
54 ok(Status
== STATUS_SUCCESS
, "Status = %lx\n", Status
);
64 PACE_HEADER AceHeader
;
70 ASSERT(AceCount
<= RTL_NUMBER_OF(AceSizes
));
71 AclSize
= sizeof(ACL
);
72 va_start(Args
, AceCount
);
73 for (i
= 0; i
< AceCount
; i
++)
75 AceSizes
[i
] = va_arg(Args
, int);
76 AclSize
+= AceSizes
[i
];
80 Acl
= AllocateGuarded(AclSize
);
83 skip("Failed to allocate %lu bytes\n", AclSize
);
87 Acl
->AclRevision
= ACL_REVISION
;
89 Acl
->AclSize
= AclSize
;
90 Acl
->AceCount
= AceCount
;
93 AceHeader
= (PACE_HEADER
)(Acl
+ 1);
94 for (i
= 0; i
< AceCount
; i
++)
96 AceHeader
->AceType
= 0;
97 AceHeader
->AceFlags
= 0;
98 AceHeader
->AceSize
= AceSizes
[i
];
99 AceHeader
= (PACE_HEADER
)((PCHAR
)AceHeader
+ AceHeader
->AceSize
);
105 START_TEST(RtlFirstFreeAce
)
114 /* Simple empty ACL */
115 FirstAce
= InvalidPointer
;
116 Found
= RtlFirstFreeAce(Acl
, &FirstAce
);
117 ok(Found
== TRUE
, "Found = %u\n", Found
);
118 ok(FirstAce
== (PACE
)(Acl
+ 1), "FirstAce = %p (Acl was %p)\n", FirstAce
, Acl
);
120 /* Not enough space */
121 Acl
->AclSize
= sizeof(ACL
) - 1;
122 FirstAce
= InvalidPointer
;
123 Found
= RtlFirstFreeAce(Acl
, &FirstAce
);
124 ok(Found
== TRUE
, "Found = %u\n", Found
);
125 ok(FirstAce
== NULL
, "FirstAce = %p (Acl was %p)\n", FirstAce
, Acl
);
127 /* Invalid values for all the other fields */
128 Acl
->AclRevision
= 76;
130 Acl
->AclSize
= sizeof(ACL
);
132 FirstAce
= InvalidPointer
;
133 Found
= RtlFirstFreeAce(Acl
, &FirstAce
);
134 ok(Found
== TRUE
, "Found = %u\n", Found
);
135 ok(FirstAce
== (PACE
)(Acl
+ 1), "FirstAce = %p (Acl was %p)\n", FirstAce
, Acl
);
140 Acl
= MakeAcl(1, (int)sizeof(ACE_HEADER
));
143 /* ACL with one ACE */
144 FirstAce
= InvalidPointer
;
145 Found
= RtlFirstFreeAce(Acl
, &FirstAce
);
146 ok(Found
== TRUE
, "Found = %u\n", Found
);
147 ok(FirstAce
== (PACE
)((PACE_HEADER
)(Acl
+ 1) + 1), "FirstAce = %p (Acl was %p)\n", FirstAce
, Acl
);
149 /* The one ACE doesn't actually fit */
150 Acl
->AclSize
= sizeof(ACL
);
151 FirstAce
= InvalidPointer
;
152 Found
= RtlFirstFreeAce(Acl
, &FirstAce
);
153 ok(Found
== FALSE
, "Found = %u\n", Found
);
154 ok(FirstAce
== NULL
, "FirstAce = %p (Acl was %p)\n", FirstAce
, Acl
);
156 /* Only the first byte fits */
157 Acl
->AclSize
= sizeof(ACL
) + 1;
158 FirstAce
= InvalidPointer
;
159 Found
= RtlFirstFreeAce(Acl
, &FirstAce
);
160 ok(Found
== TRUE
, "Found = %u\n", Found
);
161 ok(FirstAce
== NULL
, "FirstAce = %p (Acl was %p)\n", FirstAce
, Acl
);
163 /* Until we cover the whole size we get NULL */
164 Acl
->AclSize
= sizeof(ACL
) + sizeof(ACE_HEADER
) - 1;
165 FirstAce
= InvalidPointer
;
166 Found
= RtlFirstFreeAce(Acl
, &FirstAce
);
167 ok(Found
== TRUE
, "Found = %u\n", Found
);
168 ok(FirstAce
== NULL
, "FirstAce = %p (Acl was %p)\n", FirstAce
, Acl
);
173 /* Same but bigger */
174 Acl
= MakeAcl(1, (int)sizeof(ACE_HEADER
) + 4);
177 /* ACL with one ACE */
178 FirstAce
= InvalidPointer
;
179 Found
= RtlFirstFreeAce(Acl
, &FirstAce
);
180 ok(Found
== TRUE
, "Found = %u\n", Found
);
181 ok(FirstAce
== (PACE
)((PCHAR
)(Acl
+ 1) + sizeof(ACE_HEADER
) + 4), "FirstAce = %p (Acl was %p)\n", FirstAce
, Acl
);
183 /* The one ACE doesn't actually fit */
184 Acl
->AclSize
= sizeof(ACL
);
185 FirstAce
= InvalidPointer
;
186 Found
= RtlFirstFreeAce(Acl
, &FirstAce
);
187 ok(Found
== FALSE
, "Found = %u\n", Found
);
188 ok(FirstAce
== NULL
, "FirstAce = %p (Acl was %p)\n", FirstAce
, Acl
);
190 /* Only the first byte fits */
191 Acl
->AclSize
= sizeof(ACL
) + 1;
192 FirstAce
= InvalidPointer
;
193 Found
= RtlFirstFreeAce(Acl
, &FirstAce
);
194 ok(Found
== TRUE
, "Found = %u\n", Found
);
195 ok(FirstAce
== NULL
, "FirstAce = %p (Acl was %p)\n", FirstAce
, Acl
);
197 /* Until we cover the whole size we get NULL */
198 Acl
->AclSize
= sizeof(ACL
) + sizeof(ACE_HEADER
) - 3;
199 FirstAce
= InvalidPointer
;
200 Found
= RtlFirstFreeAce(Acl
, &FirstAce
);
201 ok(Found
== TRUE
, "Found = %u\n", Found
);
202 ok(FirstAce
== NULL
, "FirstAce = %p (Acl was %p)\n", FirstAce
, Acl
);
207 Acl
= MakeAcl(4, (int)sizeof(ACE_HEADER
), (int)sizeof(ACE_HEADER
), (int)sizeof(ACCESS_ALLOWED_ACE
), (int)sizeof(ACCESS_ALLOWED_ACE
));
210 /* ACL with one ACE */
211 FirstAce
= InvalidPointer
;
212 Found
= RtlFirstFreeAce(Acl
, &FirstAce
);
213 ok(Found
== TRUE
, "Found = %u\n", Found
);
214 ok(FirstAce
== (PACE
)((PCHAR
)(Acl
+ 1) + 2 * sizeof(ACE_HEADER
) + 2 * sizeof(ACCESS_ALLOWED_ACE
)), "FirstAce = %p (Acl was %p)\n", FirstAce
, Acl
);
216 /* One less gives us NULL */
217 Acl
->AclSize
= sizeof(ACL
) + 2 * sizeof(ACE_HEADER
) + 2 * sizeof(ACCESS_ALLOWED_ACE
) - 1;
218 FirstAce
= InvalidPointer
;
219 Found
= RtlFirstFreeAce(Acl
, &FirstAce
);
220 ok(Found
== TRUE
, "Found = %u\n", Found
);
221 ok(FirstAce
== NULL
, "FirstAce = %p (Acl was %p)\n", FirstAce
, Acl
);
223 /* One ACE less also gives us FALSE */
224 Acl
->AclSize
= sizeof(ACL
) + 2 * sizeof(ACE_HEADER
) + sizeof(ACCESS_ALLOWED_ACE
);
225 FirstAce
= InvalidPointer
;
226 Found
= RtlFirstFreeAce(Acl
, &FirstAce
);
227 ok(Found
== FALSE
, "Found = %u\n", Found
);
228 ok(FirstAce
== NULL
, "FirstAce = %p (Acl was %p)\n", FirstAce
, Acl
);