1b687ad3c3491fffe22507cafc9347e10cbf6bd31Christopher Ferris/*
2b687ad3c3491fffe22507cafc9347e10cbf6bd31Christopher Ferris * Copyright (C) 2013 The Android Open Source Project
3b687ad3c3491fffe22507cafc9347e10cbf6bd31Christopher Ferris *
4b687ad3c3491fffe22507cafc9347e10cbf6bd31Christopher Ferris * Licensed under the Apache License, Version 2.0 (the "License");
5b687ad3c3491fffe22507cafc9347e10cbf6bd31Christopher Ferris * you may not use this file except in compliance with the License.
6b687ad3c3491fffe22507cafc9347e10cbf6bd31Christopher Ferris * You may obtain a copy of the License at
7b687ad3c3491fffe22507cafc9347e10cbf6bd31Christopher Ferris *
8b687ad3c3491fffe22507cafc9347e10cbf6bd31Christopher Ferris *      http://www.apache.org/licenses/LICENSE-2.0
9b687ad3c3491fffe22507cafc9347e10cbf6bd31Christopher Ferris *
10b687ad3c3491fffe22507cafc9347e10cbf6bd31Christopher Ferris * Unless required by applicable law or agreed to in writing, software
11b687ad3c3491fffe22507cafc9347e10cbf6bd31Christopher Ferris * distributed under the License is distributed on an "AS IS" BASIS,
12b687ad3c3491fffe22507cafc9347e10cbf6bd31Christopher Ferris * WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
13b687ad3c3491fffe22507cafc9347e10cbf6bd31Christopher Ferris * See the License for the specific language governing permissions and
14b687ad3c3491fffe22507cafc9347e10cbf6bd31Christopher Ferris * limitations under the License.
15b687ad3c3491fffe22507cafc9347e10cbf6bd31Christopher Ferris */
16b687ad3c3491fffe22507cafc9347e10cbf6bd31Christopher Ferris
17b687ad3c3491fffe22507cafc9347e10cbf6bd31Christopher Ferris#include <stdlib.h>
18b687ad3c3491fffe22507cafc9347e10cbf6bd31Christopher Ferris#include <string.h>
19b687ad3c3491fffe22507cafc9347e10cbf6bd31Christopher Ferris#include <sys/mman.h>
20b687ad3c3491fffe22507cafc9347e10cbf6bd31Christopher Ferris
21b687ad3c3491fffe22507cafc9347e10cbf6bd31Christopher Ferris#include <gtest/gtest.h>
22b687ad3c3491fffe22507cafc9347e10cbf6bd31Christopher Ferris#include "buffer_tests.h"
23b687ad3c3491fffe22507cafc9347e10cbf6bd31Christopher Ferris
24e5bbb6b6ab662503f06ceb20fa841d2e558d596dChristopher Ferris// For the comparison buffer tests, the maximum length to test for the
25e5bbb6b6ab662503f06ceb20fa841d2e558d596dChristopher Ferris// miscompare checks.
26e5bbb6b6ab662503f06ceb20fa841d2e558d596dChristopher Ferris#define MISCMP_MAX_LENGTH 512
27e5bbb6b6ab662503f06ceb20fa841d2e558d596dChristopher Ferris
28b687ad3c3491fffe22507cafc9347e10cbf6bd31Christopher Ferris#define FENCEPOST_LENGTH 8
29b687ad3c3491fffe22507cafc9347e10cbf6bd31Christopher Ferris
30b687ad3c3491fffe22507cafc9347e10cbf6bd31Christopher Ferrisstatic int g_single_aligns[][2] = {
31b687ad3c3491fffe22507cafc9347e10cbf6bd31Christopher Ferris  // Both buffers at same alignment.
32b687ad3c3491fffe22507cafc9347e10cbf6bd31Christopher Ferris  { 1, 0 },
33b687ad3c3491fffe22507cafc9347e10cbf6bd31Christopher Ferris  { 2, 0 },
34b687ad3c3491fffe22507cafc9347e10cbf6bd31Christopher Ferris  { 4, 0 },
35b687ad3c3491fffe22507cafc9347e10cbf6bd31Christopher Ferris  { 8, 0 },
36b687ad3c3491fffe22507cafc9347e10cbf6bd31Christopher Ferris  { 16, 0 },
37b687ad3c3491fffe22507cafc9347e10cbf6bd31Christopher Ferris  { 32, 0 },
38b687ad3c3491fffe22507cafc9347e10cbf6bd31Christopher Ferris  { 64, 0 },
39b687ad3c3491fffe22507cafc9347e10cbf6bd31Christopher Ferris  { 128, 0 },
40b687ad3c3491fffe22507cafc9347e10cbf6bd31Christopher Ferris
41b687ad3c3491fffe22507cafc9347e10cbf6bd31Christopher Ferris  // General unaligned cases.
42b687ad3c3491fffe22507cafc9347e10cbf6bd31Christopher Ferris  { 4, 1 },
43b687ad3c3491fffe22507cafc9347e10cbf6bd31Christopher Ferris  { 4, 2 },
44b687ad3c3491fffe22507cafc9347e10cbf6bd31Christopher Ferris  { 4, 3 },
45b687ad3c3491fffe22507cafc9347e10cbf6bd31Christopher Ferris
46b687ad3c3491fffe22507cafc9347e10cbf6bd31Christopher Ferris  { 8, 1 },
47b687ad3c3491fffe22507cafc9347e10cbf6bd31Christopher Ferris  { 8, 2 },
48b687ad3c3491fffe22507cafc9347e10cbf6bd31Christopher Ferris  { 8, 3 },
49b687ad3c3491fffe22507cafc9347e10cbf6bd31Christopher Ferris  { 8, 4 },
50b687ad3c3491fffe22507cafc9347e10cbf6bd31Christopher Ferris  { 8, 5 },
51b687ad3c3491fffe22507cafc9347e10cbf6bd31Christopher Ferris  { 8, 6 },
52b687ad3c3491fffe22507cafc9347e10cbf6bd31Christopher Ferris  { 8, 7 },
53b687ad3c3491fffe22507cafc9347e10cbf6bd31Christopher Ferris
54b687ad3c3491fffe22507cafc9347e10cbf6bd31Christopher Ferris  { 128, 1 },
55b687ad3c3491fffe22507cafc9347e10cbf6bd31Christopher Ferris  { 128, 4 },
56b687ad3c3491fffe22507cafc9347e10cbf6bd31Christopher Ferris  { 128, 8 },
57b687ad3c3491fffe22507cafc9347e10cbf6bd31Christopher Ferris  { 128, 12 },
58b687ad3c3491fffe22507cafc9347e10cbf6bd31Christopher Ferris  { 128, 16 },
59b687ad3c3491fffe22507cafc9347e10cbf6bd31Christopher Ferris};
60b687ad3c3491fffe22507cafc9347e10cbf6bd31Christopher Ferris
61b687ad3c3491fffe22507cafc9347e10cbf6bd31Christopher Ferrisstatic const size_t g_single_aligns_len = sizeof(g_single_aligns)/sizeof(int[2]);
62b687ad3c3491fffe22507cafc9347e10cbf6bd31Christopher Ferris
63b687ad3c3491fffe22507cafc9347e10cbf6bd31Christopher Ferris// Set of multiple buffer alignment combinations to be used for string/memory
64b687ad3c3491fffe22507cafc9347e10cbf6bd31Christopher Ferris// testing routines.
65b687ad3c3491fffe22507cafc9347e10cbf6bd31Christopher Ferrisstatic int g_double_aligns[][4] = {
66b687ad3c3491fffe22507cafc9347e10cbf6bd31Christopher Ferris  // Both buffers at same alignment.
67b687ad3c3491fffe22507cafc9347e10cbf6bd31Christopher Ferris  { 1, 0, 1, 0 },
68b687ad3c3491fffe22507cafc9347e10cbf6bd31Christopher Ferris  { 2, 0, 2, 0 },
69b687ad3c3491fffe22507cafc9347e10cbf6bd31Christopher Ferris  { 4, 0, 4, 0 },
70b687ad3c3491fffe22507cafc9347e10cbf6bd31Christopher Ferris  { 8, 0, 8, 0 },
71b687ad3c3491fffe22507cafc9347e10cbf6bd31Christopher Ferris  { 16, 0, 16, 0 },
72b687ad3c3491fffe22507cafc9347e10cbf6bd31Christopher Ferris  { 32, 0, 32, 0 },
73b687ad3c3491fffe22507cafc9347e10cbf6bd31Christopher Ferris  { 64, 0, 64, 0 },
74b687ad3c3491fffe22507cafc9347e10cbf6bd31Christopher Ferris  { 128, 0, 128, 0 },
75b687ad3c3491fffe22507cafc9347e10cbf6bd31Christopher Ferris
76b687ad3c3491fffe22507cafc9347e10cbf6bd31Christopher Ferris  // Different word alignments between buffers.
77b687ad3c3491fffe22507cafc9347e10cbf6bd31Christopher Ferris  { 8, 0, 4, 0 },
78b687ad3c3491fffe22507cafc9347e10cbf6bd31Christopher Ferris  { 4, 0, 8, 0 },
79b687ad3c3491fffe22507cafc9347e10cbf6bd31Christopher Ferris  { 16, 0, 4, 0 },
80b687ad3c3491fffe22507cafc9347e10cbf6bd31Christopher Ferris  { 4, 0, 16, 0 },
81b687ad3c3491fffe22507cafc9347e10cbf6bd31Christopher Ferris
82b687ad3c3491fffe22507cafc9347e10cbf6bd31Christopher Ferris  // General unaligned cases.
83b687ad3c3491fffe22507cafc9347e10cbf6bd31Christopher Ferris  { 4, 0, 4, 1 },
84b687ad3c3491fffe22507cafc9347e10cbf6bd31Christopher Ferris  { 4, 0, 4, 2 },
85b687ad3c3491fffe22507cafc9347e10cbf6bd31Christopher Ferris  { 4, 0, 4, 3 },
86b687ad3c3491fffe22507cafc9347e10cbf6bd31Christopher Ferris
87b687ad3c3491fffe22507cafc9347e10cbf6bd31Christopher Ferris  { 4, 1, 4, 0 },
88b687ad3c3491fffe22507cafc9347e10cbf6bd31Christopher Ferris  { 4, 1, 4, 1 },
89b687ad3c3491fffe22507cafc9347e10cbf6bd31Christopher Ferris  { 4, 1, 4, 2 },
90b687ad3c3491fffe22507cafc9347e10cbf6bd31Christopher Ferris  { 4, 1, 4, 3 },
91b687ad3c3491fffe22507cafc9347e10cbf6bd31Christopher Ferris
92b687ad3c3491fffe22507cafc9347e10cbf6bd31Christopher Ferris  { 4, 2, 4, 0 },
93b687ad3c3491fffe22507cafc9347e10cbf6bd31Christopher Ferris  { 4, 2, 4, 1 },
94b687ad3c3491fffe22507cafc9347e10cbf6bd31Christopher Ferris  { 4, 2, 4, 2 },
95b687ad3c3491fffe22507cafc9347e10cbf6bd31Christopher Ferris  { 4, 2, 4, 3 },
96b687ad3c3491fffe22507cafc9347e10cbf6bd31Christopher Ferris
97b687ad3c3491fffe22507cafc9347e10cbf6bd31Christopher Ferris  { 4, 3, 4, 0 },
98b687ad3c3491fffe22507cafc9347e10cbf6bd31Christopher Ferris  { 4, 3, 4, 1 },
99b687ad3c3491fffe22507cafc9347e10cbf6bd31Christopher Ferris  { 4, 3, 4, 2 },
100b687ad3c3491fffe22507cafc9347e10cbf6bd31Christopher Ferris  { 4, 3, 4, 3 },
101b687ad3c3491fffe22507cafc9347e10cbf6bd31Christopher Ferris
102b687ad3c3491fffe22507cafc9347e10cbf6bd31Christopher Ferris  { 8, 0, 8, 1 },
103b687ad3c3491fffe22507cafc9347e10cbf6bd31Christopher Ferris  { 8, 0, 8, 2 },
104b687ad3c3491fffe22507cafc9347e10cbf6bd31Christopher Ferris  { 8, 0, 8, 3 },
105b687ad3c3491fffe22507cafc9347e10cbf6bd31Christopher Ferris  { 8, 0, 8, 4 },
106b687ad3c3491fffe22507cafc9347e10cbf6bd31Christopher Ferris  { 8, 0, 8, 5 },
107b687ad3c3491fffe22507cafc9347e10cbf6bd31Christopher Ferris  { 8, 0, 8, 6 },
108b687ad3c3491fffe22507cafc9347e10cbf6bd31Christopher Ferris  { 8, 0, 8, 7 },
109b687ad3c3491fffe22507cafc9347e10cbf6bd31Christopher Ferris
110b687ad3c3491fffe22507cafc9347e10cbf6bd31Christopher Ferris  { 8, 1, 8, 0 },
111b687ad3c3491fffe22507cafc9347e10cbf6bd31Christopher Ferris  { 8, 1, 8, 1 },
112b687ad3c3491fffe22507cafc9347e10cbf6bd31Christopher Ferris  { 8, 1, 8, 2 },
113b687ad3c3491fffe22507cafc9347e10cbf6bd31Christopher Ferris  { 8, 1, 8, 3 },
114b687ad3c3491fffe22507cafc9347e10cbf6bd31Christopher Ferris  { 8, 1, 8, 4 },
115b687ad3c3491fffe22507cafc9347e10cbf6bd31Christopher Ferris  { 8, 1, 8, 5 },
116b687ad3c3491fffe22507cafc9347e10cbf6bd31Christopher Ferris  { 8, 1, 8, 6 },
117b687ad3c3491fffe22507cafc9347e10cbf6bd31Christopher Ferris  { 8, 1, 8, 7 },
118b687ad3c3491fffe22507cafc9347e10cbf6bd31Christopher Ferris
119b687ad3c3491fffe22507cafc9347e10cbf6bd31Christopher Ferris  { 8, 2, 8, 0 },
120b687ad3c3491fffe22507cafc9347e10cbf6bd31Christopher Ferris  { 8, 2, 8, 1 },
121b687ad3c3491fffe22507cafc9347e10cbf6bd31Christopher Ferris  { 8, 2, 8, 2 },
122b687ad3c3491fffe22507cafc9347e10cbf6bd31Christopher Ferris  { 8, 2, 8, 3 },
123b687ad3c3491fffe22507cafc9347e10cbf6bd31Christopher Ferris  { 8, 2, 8, 4 },
124b687ad3c3491fffe22507cafc9347e10cbf6bd31Christopher Ferris  { 8, 2, 8, 5 },
125b687ad3c3491fffe22507cafc9347e10cbf6bd31Christopher Ferris  { 8, 2, 8, 6 },
126b687ad3c3491fffe22507cafc9347e10cbf6bd31Christopher Ferris  { 8, 2, 8, 7 },
127b687ad3c3491fffe22507cafc9347e10cbf6bd31Christopher Ferris
128b687ad3c3491fffe22507cafc9347e10cbf6bd31Christopher Ferris  { 8, 3, 8, 0 },
129b687ad3c3491fffe22507cafc9347e10cbf6bd31Christopher Ferris  { 8, 3, 8, 1 },
130b687ad3c3491fffe22507cafc9347e10cbf6bd31Christopher Ferris  { 8, 3, 8, 2 },
131b687ad3c3491fffe22507cafc9347e10cbf6bd31Christopher Ferris  { 8, 3, 8, 3 },
132b687ad3c3491fffe22507cafc9347e10cbf6bd31Christopher Ferris  { 8, 3, 8, 4 },
133b687ad3c3491fffe22507cafc9347e10cbf6bd31Christopher Ferris  { 8, 3, 8, 5 },
134b687ad3c3491fffe22507cafc9347e10cbf6bd31Christopher Ferris  { 8, 3, 8, 6 },
135b687ad3c3491fffe22507cafc9347e10cbf6bd31Christopher Ferris  { 8, 3, 8, 7 },
136b687ad3c3491fffe22507cafc9347e10cbf6bd31Christopher Ferris
137b687ad3c3491fffe22507cafc9347e10cbf6bd31Christopher Ferris  { 8, 4, 8, 0 },
138b687ad3c3491fffe22507cafc9347e10cbf6bd31Christopher Ferris  { 8, 4, 8, 1 },
139b687ad3c3491fffe22507cafc9347e10cbf6bd31Christopher Ferris  { 8, 4, 8, 2 },
140b687ad3c3491fffe22507cafc9347e10cbf6bd31Christopher Ferris  { 8, 4, 8, 3 },
141b687ad3c3491fffe22507cafc9347e10cbf6bd31Christopher Ferris  { 8, 4, 8, 4 },
142b687ad3c3491fffe22507cafc9347e10cbf6bd31Christopher Ferris  { 8, 4, 8, 5 },
143b687ad3c3491fffe22507cafc9347e10cbf6bd31Christopher Ferris  { 8, 4, 8, 6 },
144b687ad3c3491fffe22507cafc9347e10cbf6bd31Christopher Ferris  { 8, 4, 8, 7 },
145b687ad3c3491fffe22507cafc9347e10cbf6bd31Christopher Ferris
146b687ad3c3491fffe22507cafc9347e10cbf6bd31Christopher Ferris  { 8, 5, 8, 0 },
147b687ad3c3491fffe22507cafc9347e10cbf6bd31Christopher Ferris  { 8, 5, 8, 1 },
148b687ad3c3491fffe22507cafc9347e10cbf6bd31Christopher Ferris  { 8, 5, 8, 2 },
149b687ad3c3491fffe22507cafc9347e10cbf6bd31Christopher Ferris  { 8, 5, 8, 3 },
150b687ad3c3491fffe22507cafc9347e10cbf6bd31Christopher Ferris  { 8, 5, 8, 4 },
151b687ad3c3491fffe22507cafc9347e10cbf6bd31Christopher Ferris  { 8, 5, 8, 5 },
152b687ad3c3491fffe22507cafc9347e10cbf6bd31Christopher Ferris  { 8, 5, 8, 6 },
153b687ad3c3491fffe22507cafc9347e10cbf6bd31Christopher Ferris  { 8, 5, 8, 7 },
154b687ad3c3491fffe22507cafc9347e10cbf6bd31Christopher Ferris
155b687ad3c3491fffe22507cafc9347e10cbf6bd31Christopher Ferris  { 8, 6, 8, 0 },
156b687ad3c3491fffe22507cafc9347e10cbf6bd31Christopher Ferris  { 8, 6, 8, 1 },
157b687ad3c3491fffe22507cafc9347e10cbf6bd31Christopher Ferris  { 8, 6, 8, 2 },
158b687ad3c3491fffe22507cafc9347e10cbf6bd31Christopher Ferris  { 8, 6, 8, 3 },
159b687ad3c3491fffe22507cafc9347e10cbf6bd31Christopher Ferris  { 8, 6, 8, 4 },
160b687ad3c3491fffe22507cafc9347e10cbf6bd31Christopher Ferris  { 8, 6, 8, 5 },
161b687ad3c3491fffe22507cafc9347e10cbf6bd31Christopher Ferris  { 8, 6, 8, 6 },
162b687ad3c3491fffe22507cafc9347e10cbf6bd31Christopher Ferris  { 8, 6, 8, 7 },
163b687ad3c3491fffe22507cafc9347e10cbf6bd31Christopher Ferris
164b687ad3c3491fffe22507cafc9347e10cbf6bd31Christopher Ferris  { 8, 7, 8, 0 },
165b687ad3c3491fffe22507cafc9347e10cbf6bd31Christopher Ferris  { 8, 7, 8, 1 },
166b687ad3c3491fffe22507cafc9347e10cbf6bd31Christopher Ferris  { 8, 7, 8, 2 },
167b687ad3c3491fffe22507cafc9347e10cbf6bd31Christopher Ferris  { 8, 7, 8, 3 },
168b687ad3c3491fffe22507cafc9347e10cbf6bd31Christopher Ferris  { 8, 7, 8, 4 },
169b687ad3c3491fffe22507cafc9347e10cbf6bd31Christopher Ferris  { 8, 7, 8, 5 },
170b687ad3c3491fffe22507cafc9347e10cbf6bd31Christopher Ferris  { 8, 7, 8, 6 },
171b687ad3c3491fffe22507cafc9347e10cbf6bd31Christopher Ferris  { 8, 7, 8, 7 },
172b687ad3c3491fffe22507cafc9347e10cbf6bd31Christopher Ferris
173b687ad3c3491fffe22507cafc9347e10cbf6bd31Christopher Ferris  { 128, 1, 128, 4 },
174b687ad3c3491fffe22507cafc9347e10cbf6bd31Christopher Ferris  { 128, 1, 128, 8 },
175b687ad3c3491fffe22507cafc9347e10cbf6bd31Christopher Ferris  { 128, 1, 128, 12 },
176b687ad3c3491fffe22507cafc9347e10cbf6bd31Christopher Ferris  { 128, 1, 128, 16 },
177b687ad3c3491fffe22507cafc9347e10cbf6bd31Christopher Ferris  { 128, 4, 128, 1 },
178b687ad3c3491fffe22507cafc9347e10cbf6bd31Christopher Ferris  { 128, 8, 128, 1 },
179b687ad3c3491fffe22507cafc9347e10cbf6bd31Christopher Ferris  { 128, 12, 128, 1 },
180b687ad3c3491fffe22507cafc9347e10cbf6bd31Christopher Ferris  { 128, 16, 128, 1 },
181b687ad3c3491fffe22507cafc9347e10cbf6bd31Christopher Ferris};
182b687ad3c3491fffe22507cafc9347e10cbf6bd31Christopher Ferris
183b687ad3c3491fffe22507cafc9347e10cbf6bd31Christopher Ferrisstatic const size_t g_double_aligns_len = sizeof(g_double_aligns)/sizeof(int[4]);
184b687ad3c3491fffe22507cafc9347e10cbf6bd31Christopher Ferris
185b687ad3c3491fffe22507cafc9347e10cbf6bd31Christopher Ferrisstatic size_t SetIncrement(size_t len) {
186b687ad3c3491fffe22507cafc9347e10cbf6bd31Christopher Ferris  if (len >= 4096) {
187b687ad3c3491fffe22507cafc9347e10cbf6bd31Christopher Ferris    return 1024;
188b687ad3c3491fffe22507cafc9347e10cbf6bd31Christopher Ferris  } else if (len >= 1024) {
189b687ad3c3491fffe22507cafc9347e10cbf6bd31Christopher Ferris    return 256;
190b687ad3c3491fffe22507cafc9347e10cbf6bd31Christopher Ferris  }
191b687ad3c3491fffe22507cafc9347e10cbf6bd31Christopher Ferris  return 1;
192b687ad3c3491fffe22507cafc9347e10cbf6bd31Christopher Ferris}
193b687ad3c3491fffe22507cafc9347e10cbf6bd31Christopher Ferris
194b687ad3c3491fffe22507cafc9347e10cbf6bd31Christopher Ferris// Return a pointer into the current buffer with the specified alignment.
195b687ad3c3491fffe22507cafc9347e10cbf6bd31Christopher Ferrisstatic void *GetAlignedPtr(void *orig_ptr, int alignment, int or_mask) {
196b687ad3c3491fffe22507cafc9347e10cbf6bd31Christopher Ferris  uint64_t ptr = reinterpret_cast<uint64_t>(orig_ptr);
197b687ad3c3491fffe22507cafc9347e10cbf6bd31Christopher Ferris  if (alignment > 0) {
198b687ad3c3491fffe22507cafc9347e10cbf6bd31Christopher Ferris      // When setting the alignment, set it to exactly the alignment chosen.
199b687ad3c3491fffe22507cafc9347e10cbf6bd31Christopher Ferris      // The pointer returned will be guaranteed not to be aligned to anything
200b687ad3c3491fffe22507cafc9347e10cbf6bd31Christopher Ferris      // more than that.
201b687ad3c3491fffe22507cafc9347e10cbf6bd31Christopher Ferris      ptr += alignment - (ptr & (alignment - 1));
202b687ad3c3491fffe22507cafc9347e10cbf6bd31Christopher Ferris      ptr |= alignment | or_mask;
203b687ad3c3491fffe22507cafc9347e10cbf6bd31Christopher Ferris  }
204b687ad3c3491fffe22507cafc9347e10cbf6bd31Christopher Ferris
205b687ad3c3491fffe22507cafc9347e10cbf6bd31Christopher Ferris  return reinterpret_cast<void*>(ptr);
206b687ad3c3491fffe22507cafc9347e10cbf6bd31Christopher Ferris}
207b687ad3c3491fffe22507cafc9347e10cbf6bd31Christopher Ferris
208b687ad3c3491fffe22507cafc9347e10cbf6bd31Christopher Ferrisstatic void SetFencepost(uint8_t *buffer) {
209b687ad3c3491fffe22507cafc9347e10cbf6bd31Christopher Ferris  for (int i = 0; i < FENCEPOST_LENGTH; i += 2) {
210b687ad3c3491fffe22507cafc9347e10cbf6bd31Christopher Ferris    buffer[i] = 0xde;
211b687ad3c3491fffe22507cafc9347e10cbf6bd31Christopher Ferris    buffer[i+1] = 0xad;
212b687ad3c3491fffe22507cafc9347e10cbf6bd31Christopher Ferris  }
213b687ad3c3491fffe22507cafc9347e10cbf6bd31Christopher Ferris}
214b687ad3c3491fffe22507cafc9347e10cbf6bd31Christopher Ferris
215b687ad3c3491fffe22507cafc9347e10cbf6bd31Christopher Ferrisstatic void VerifyFencepost(uint8_t *buffer) {
216b687ad3c3491fffe22507cafc9347e10cbf6bd31Christopher Ferris  for (int i = 0; i < FENCEPOST_LENGTH; i += 2) {
217b687ad3c3491fffe22507cafc9347e10cbf6bd31Christopher Ferris    if (buffer[i] != 0xde || buffer[i+1] != 0xad) {
218b687ad3c3491fffe22507cafc9347e10cbf6bd31Christopher Ferris      uint8_t expected_value;
219b687ad3c3491fffe22507cafc9347e10cbf6bd31Christopher Ferris      if (buffer[i] == 0xde) {
220b687ad3c3491fffe22507cafc9347e10cbf6bd31Christopher Ferris        i++;
221b687ad3c3491fffe22507cafc9347e10cbf6bd31Christopher Ferris        expected_value = 0xad;
222b687ad3c3491fffe22507cafc9347e10cbf6bd31Christopher Ferris      } else {
223b687ad3c3491fffe22507cafc9347e10cbf6bd31Christopher Ferris        expected_value = 0xde;
224b687ad3c3491fffe22507cafc9347e10cbf6bd31Christopher Ferris      }
225b687ad3c3491fffe22507cafc9347e10cbf6bd31Christopher Ferris      ASSERT_EQ(expected_value, buffer[i]);
226b687ad3c3491fffe22507cafc9347e10cbf6bd31Christopher Ferris    }
227b687ad3c3491fffe22507cafc9347e10cbf6bd31Christopher Ferris  }
228b687ad3c3491fffe22507cafc9347e10cbf6bd31Christopher Ferris}
229b687ad3c3491fffe22507cafc9347e10cbf6bd31Christopher Ferris
230b687ad3c3491fffe22507cafc9347e10cbf6bd31Christopher Ferrisvoid RunSingleBufferAlignTest(
231b687ad3c3491fffe22507cafc9347e10cbf6bd31Christopher Ferris    size_t max_test_size, void (*test_func)(uint8_t*, size_t),
232b687ad3c3491fffe22507cafc9347e10cbf6bd31Christopher Ferris    size_t (*set_incr)(size_t)) {
233b687ad3c3491fffe22507cafc9347e10cbf6bd31Christopher Ferris  if (!set_incr) {
234b687ad3c3491fffe22507cafc9347e10cbf6bd31Christopher Ferris    set_incr = SetIncrement;
235b687ad3c3491fffe22507cafc9347e10cbf6bd31Christopher Ferris  }
236b687ad3c3491fffe22507cafc9347e10cbf6bd31Christopher Ferris
237b687ad3c3491fffe22507cafc9347e10cbf6bd31Christopher Ferris  // Allocate one large buffer with lots of extra space so that we can
238b687ad3c3491fffe22507cafc9347e10cbf6bd31Christopher Ferris  // guarantee that the all possible alignments will fit.
239b687ad3c3491fffe22507cafc9347e10cbf6bd31Christopher Ferris  uint8_t *buf = new uint8_t[3*max_test_size];
240b687ad3c3491fffe22507cafc9347e10cbf6bd31Christopher Ferris
241b687ad3c3491fffe22507cafc9347e10cbf6bd31Christopher Ferris  uint8_t *buf_align;
242b687ad3c3491fffe22507cafc9347e10cbf6bd31Christopher Ferris  for (size_t i = 0; i < g_single_aligns_len; i++) {
243b687ad3c3491fffe22507cafc9347e10cbf6bd31Christopher Ferris    size_t incr = 1;
244b687ad3c3491fffe22507cafc9347e10cbf6bd31Christopher Ferris    for (size_t len = 0; len <= max_test_size; len += incr) {
245b687ad3c3491fffe22507cafc9347e10cbf6bd31Christopher Ferris      incr = set_incr(len);
246b687ad3c3491fffe22507cafc9347e10cbf6bd31Christopher Ferris
247b687ad3c3491fffe22507cafc9347e10cbf6bd31Christopher Ferris      buf_align = reinterpret_cast<uint8_t*>(GetAlignedPtr(
248b687ad3c3491fffe22507cafc9347e10cbf6bd31Christopher Ferris          buf+FENCEPOST_LENGTH, g_single_aligns[i][0], g_single_aligns[i][1]));
249b687ad3c3491fffe22507cafc9347e10cbf6bd31Christopher Ferris
250b687ad3c3491fffe22507cafc9347e10cbf6bd31Christopher Ferris      SetFencepost(&buf_align[-FENCEPOST_LENGTH]);
251b687ad3c3491fffe22507cafc9347e10cbf6bd31Christopher Ferris      SetFencepost(&buf_align[len]);
252b687ad3c3491fffe22507cafc9347e10cbf6bd31Christopher Ferris
253b687ad3c3491fffe22507cafc9347e10cbf6bd31Christopher Ferris      test_func(buf_align, len);
254b687ad3c3491fffe22507cafc9347e10cbf6bd31Christopher Ferris
255e5bbb6b6ab662503f06ceb20fa841d2e558d596dChristopher Ferris      VerifyFencepost(&buf_align[-FENCEPOST_LENGTH]);
256b687ad3c3491fffe22507cafc9347e10cbf6bd31Christopher Ferris      VerifyFencepost(&buf_align[len]);
257b687ad3c3491fffe22507cafc9347e10cbf6bd31Christopher Ferris    }
258b687ad3c3491fffe22507cafc9347e10cbf6bd31Christopher Ferris  }
2594d44675283e6c92d3294592be4fce7c9d89c19b6Pirama Arumuga Nainar  delete[] buf;
260b687ad3c3491fffe22507cafc9347e10cbf6bd31Christopher Ferris}
261b687ad3c3491fffe22507cafc9347e10cbf6bd31Christopher Ferris
262b687ad3c3491fffe22507cafc9347e10cbf6bd31Christopher Ferrisvoid RunSrcDstBufferAlignTest(
263b687ad3c3491fffe22507cafc9347e10cbf6bd31Christopher Ferris    size_t max_test_size, void (*test_func)(uint8_t*, uint8_t*, size_t),
264b687ad3c3491fffe22507cafc9347e10cbf6bd31Christopher Ferris    size_t (*set_incr)(size_t)) {
265b687ad3c3491fffe22507cafc9347e10cbf6bd31Christopher Ferris  if (!set_incr) {
266b687ad3c3491fffe22507cafc9347e10cbf6bd31Christopher Ferris    set_incr = SetIncrement;
267b687ad3c3491fffe22507cafc9347e10cbf6bd31Christopher Ferris  }
268b687ad3c3491fffe22507cafc9347e10cbf6bd31Christopher Ferris
269b687ad3c3491fffe22507cafc9347e10cbf6bd31Christopher Ferris  // Allocate two large buffers for all of the testing.
270b687ad3c3491fffe22507cafc9347e10cbf6bd31Christopher Ferris  uint8_t* src = new uint8_t[3*max_test_size];
271b687ad3c3491fffe22507cafc9347e10cbf6bd31Christopher Ferris  uint8_t* dst = new uint8_t[3*max_test_size];
272b687ad3c3491fffe22507cafc9347e10cbf6bd31Christopher Ferris
273b687ad3c3491fffe22507cafc9347e10cbf6bd31Christopher Ferris  uint8_t* src_align;
274b687ad3c3491fffe22507cafc9347e10cbf6bd31Christopher Ferris  uint8_t* dst_align;
275b687ad3c3491fffe22507cafc9347e10cbf6bd31Christopher Ferris  for (size_t i = 0; i < g_double_aligns_len; i++) {
276b687ad3c3491fffe22507cafc9347e10cbf6bd31Christopher Ferris    size_t incr = 1;
277b687ad3c3491fffe22507cafc9347e10cbf6bd31Christopher Ferris    for (size_t len = 0; len <= max_test_size; len += incr) {
278b687ad3c3491fffe22507cafc9347e10cbf6bd31Christopher Ferris      incr = set_incr(len);
279b687ad3c3491fffe22507cafc9347e10cbf6bd31Christopher Ferris
280b687ad3c3491fffe22507cafc9347e10cbf6bd31Christopher Ferris      src_align =
281b687ad3c3491fffe22507cafc9347e10cbf6bd31Christopher Ferris          reinterpret_cast<uint8_t*>(GetAlignedPtr(
282b687ad3c3491fffe22507cafc9347e10cbf6bd31Christopher Ferris              src+FENCEPOST_LENGTH, g_double_aligns[i][0], g_double_aligns[i][1]));
283b687ad3c3491fffe22507cafc9347e10cbf6bd31Christopher Ferris      dst_align =
284b687ad3c3491fffe22507cafc9347e10cbf6bd31Christopher Ferris          reinterpret_cast<uint8_t*>(GetAlignedPtr(
285b687ad3c3491fffe22507cafc9347e10cbf6bd31Christopher Ferris              dst+FENCEPOST_LENGTH, g_double_aligns[i][2], g_double_aligns[i][3]));
286b687ad3c3491fffe22507cafc9347e10cbf6bd31Christopher Ferris      SetFencepost(&dst_align[-FENCEPOST_LENGTH]);
287b687ad3c3491fffe22507cafc9347e10cbf6bd31Christopher Ferris      SetFencepost(&dst_align[len]);
288b687ad3c3491fffe22507cafc9347e10cbf6bd31Christopher Ferris
289b687ad3c3491fffe22507cafc9347e10cbf6bd31Christopher Ferris      test_func(src_align, dst_align, len);
290b687ad3c3491fffe22507cafc9347e10cbf6bd31Christopher Ferris
291e5bbb6b6ab662503f06ceb20fa841d2e558d596dChristopher Ferris      VerifyFencepost(&dst_align[-FENCEPOST_LENGTH]);
292b687ad3c3491fffe22507cafc9347e10cbf6bd31Christopher Ferris      VerifyFencepost(&dst_align[len]);
293b687ad3c3491fffe22507cafc9347e10cbf6bd31Christopher Ferris    }
294b687ad3c3491fffe22507cafc9347e10cbf6bd31Christopher Ferris  }
2954d44675283e6c92d3294592be4fce7c9d89c19b6Pirama Arumuga Nainar  delete[] src;
2964d44675283e6c92d3294592be4fce7c9d89c19b6Pirama Arumuga Nainar  delete[] dst;
297b687ad3c3491fffe22507cafc9347e10cbf6bd31Christopher Ferris}
298b687ad3c3491fffe22507cafc9347e10cbf6bd31Christopher Ferris
299e5bbb6b6ab662503f06ceb20fa841d2e558d596dChristopher Ferrisvoid RunCmpBufferAlignTest(
300e5bbb6b6ab662503f06ceb20fa841d2e558d596dChristopher Ferris    size_t max_test_size, void (*test_cmp_func)(uint8_t*, uint8_t*, size_t),
301e5bbb6b6ab662503f06ceb20fa841d2e558d596dChristopher Ferris    void (*test_miscmp_func)(uint8_t*, uint8_t*, size_t, size_t),
302e5bbb6b6ab662503f06ceb20fa841d2e558d596dChristopher Ferris    size_t (*set_incr)(size_t)) {
303e5bbb6b6ab662503f06ceb20fa841d2e558d596dChristopher Ferris  if (!set_incr) {
304e5bbb6b6ab662503f06ceb20fa841d2e558d596dChristopher Ferris    set_incr = SetIncrement;
305e5bbb6b6ab662503f06ceb20fa841d2e558d596dChristopher Ferris  }
306e5bbb6b6ab662503f06ceb20fa841d2e558d596dChristopher Ferris
307e5bbb6b6ab662503f06ceb20fa841d2e558d596dChristopher Ferris  // Allocate two large buffers for all of the testing.
308e5bbb6b6ab662503f06ceb20fa841d2e558d596dChristopher Ferris  uint8_t* buf1 = new uint8_t[3*max_test_size];
309e5bbb6b6ab662503f06ceb20fa841d2e558d596dChristopher Ferris  uint8_t* buf2 = new uint8_t[3*max_test_size];
310e5bbb6b6ab662503f06ceb20fa841d2e558d596dChristopher Ferris
311e5bbb6b6ab662503f06ceb20fa841d2e558d596dChristopher Ferris  uint8_t* buf1_align;
312e5bbb6b6ab662503f06ceb20fa841d2e558d596dChristopher Ferris  uint8_t* buf2_align;
313e5bbb6b6ab662503f06ceb20fa841d2e558d596dChristopher Ferris  for (size_t i = 0; i < g_double_aligns_len; i++) {
314e5bbb6b6ab662503f06ceb20fa841d2e558d596dChristopher Ferris    size_t incr = 1;
315e5bbb6b6ab662503f06ceb20fa841d2e558d596dChristopher Ferris    for (size_t len = 0; len <= max_test_size; len += incr) {
316e5bbb6b6ab662503f06ceb20fa841d2e558d596dChristopher Ferris      incr = set_incr(len);
317e5bbb6b6ab662503f06ceb20fa841d2e558d596dChristopher Ferris
318e5bbb6b6ab662503f06ceb20fa841d2e558d596dChristopher Ferris      buf1_align =
319e5bbb6b6ab662503f06ceb20fa841d2e558d596dChristopher Ferris          reinterpret_cast<uint8_t*>(GetAlignedPtr(
320e5bbb6b6ab662503f06ceb20fa841d2e558d596dChristopher Ferris              buf1, g_double_aligns[i][0], g_double_aligns[i][1]));
321e5bbb6b6ab662503f06ceb20fa841d2e558d596dChristopher Ferris      buf2_align =
322e5bbb6b6ab662503f06ceb20fa841d2e558d596dChristopher Ferris          reinterpret_cast<uint8_t*>(GetAlignedPtr(
323e5bbb6b6ab662503f06ceb20fa841d2e558d596dChristopher Ferris              buf2, g_double_aligns[i][2], g_double_aligns[i][3]));
324e5bbb6b6ab662503f06ceb20fa841d2e558d596dChristopher Ferris
325e5bbb6b6ab662503f06ceb20fa841d2e558d596dChristopher Ferris      // Check by putting all zeroes after both buffers.
326e5bbb6b6ab662503f06ceb20fa841d2e558d596dChristopher Ferris      memset(buf1_align+len, 0, 32);
327e5bbb6b6ab662503f06ceb20fa841d2e558d596dChristopher Ferris      memset(buf2_align+len, 0, 32);
328e5bbb6b6ab662503f06ceb20fa841d2e558d596dChristopher Ferris      test_cmp_func(buf1_align, buf2_align, len);
329e5bbb6b6ab662503f06ceb20fa841d2e558d596dChristopher Ferris
330e5bbb6b6ab662503f06ceb20fa841d2e558d596dChristopher Ferris      // Check by putting different values after both buffers.
331e5bbb6b6ab662503f06ceb20fa841d2e558d596dChristopher Ferris      for (size_t j = 0; j < 32; j++) {
332e5bbb6b6ab662503f06ceb20fa841d2e558d596dChristopher Ferris        buf1_align[len+j] = j;
333e5bbb6b6ab662503f06ceb20fa841d2e558d596dChristopher Ferris        buf2_align[len+j] = j+1;
334e5bbb6b6ab662503f06ceb20fa841d2e558d596dChristopher Ferris      }
335e5bbb6b6ab662503f06ceb20fa841d2e558d596dChristopher Ferris      test_cmp_func(buf1_align, buf2_align, len);
336e5bbb6b6ab662503f06ceb20fa841d2e558d596dChristopher Ferris
337e5bbb6b6ab662503f06ceb20fa841d2e558d596dChristopher Ferris      if (len > 0) {
338e5bbb6b6ab662503f06ceb20fa841d2e558d596dChristopher Ferris        // Change the lengths of the buffers and verify that there are
339e5bbb6b6ab662503f06ceb20fa841d2e558d596dChristopher Ferris        // miscompares.
340e5bbb6b6ab662503f06ceb20fa841d2e558d596dChristopher Ferris        for (size_t len2 = len+1; len2 < len+32; len2++) {
341e5bbb6b6ab662503f06ceb20fa841d2e558d596dChristopher Ferris          test_miscmp_func(buf1_align, buf2_align, len, len2);
342e5bbb6b6ab662503f06ceb20fa841d2e558d596dChristopher Ferris          test_miscmp_func(buf1_align, buf2_align, len2, len);
343e5bbb6b6ab662503f06ceb20fa841d2e558d596dChristopher Ferris        }
344e5bbb6b6ab662503f06ceb20fa841d2e558d596dChristopher Ferris      }
345e5bbb6b6ab662503f06ceb20fa841d2e558d596dChristopher Ferris    }
346e5bbb6b6ab662503f06ceb20fa841d2e558d596dChristopher Ferris  }
3474d44675283e6c92d3294592be4fce7c9d89c19b6Pirama Arumuga Nainar  delete[] buf1;
3484d44675283e6c92d3294592be4fce7c9d89c19b6Pirama Arumuga Nainar  delete[] buf2;
349e5bbb6b6ab662503f06ceb20fa841d2e558d596dChristopher Ferris}
350e5bbb6b6ab662503f06ceb20fa841d2e558d596dChristopher Ferris
351b687ad3c3491fffe22507cafc9347e10cbf6bd31Christopher Ferrisvoid RunSingleBufferOverreadTest(void (*test_func)(uint8_t*, size_t)) {
352b687ad3c3491fffe22507cafc9347e10cbf6bd31Christopher Ferris  // In order to verify that functions are not reading past the end of the
353b687ad3c3491fffe22507cafc9347e10cbf6bd31Christopher Ferris  // src, create data that ends exactly at an unreadable memory boundary.
354b687ad3c3491fffe22507cafc9347e10cbf6bd31Christopher Ferris  size_t pagesize = static_cast<size_t>(sysconf(_SC_PAGE_SIZE));
355b687ad3c3491fffe22507cafc9347e10cbf6bd31Christopher Ferris  uint8_t* memory;
356b687ad3c3491fffe22507cafc9347e10cbf6bd31Christopher Ferris  ASSERT_TRUE(posix_memalign(reinterpret_cast<void**>(&memory), pagesize,
357b687ad3c3491fffe22507cafc9347e10cbf6bd31Christopher Ferris                             2*pagesize) == 0);
358b687ad3c3491fffe22507cafc9347e10cbf6bd31Christopher Ferris  memset(memory, 0x23, 2*pagesize);
359b687ad3c3491fffe22507cafc9347e10cbf6bd31Christopher Ferris
360b687ad3c3491fffe22507cafc9347e10cbf6bd31Christopher Ferris  // Make the second page unreadable and unwritable.
361b687ad3c3491fffe22507cafc9347e10cbf6bd31Christopher Ferris  ASSERT_TRUE(mprotect(&memory[pagesize], pagesize, PROT_NONE) == 0);
362b687ad3c3491fffe22507cafc9347e10cbf6bd31Christopher Ferris
363b687ad3c3491fffe22507cafc9347e10cbf6bd31Christopher Ferris  for (size_t i = 0; i < pagesize; i++) {
364b687ad3c3491fffe22507cafc9347e10cbf6bd31Christopher Ferris    uint8_t* buf = &memory[pagesize-i];
365b687ad3c3491fffe22507cafc9347e10cbf6bd31Christopher Ferris
366b687ad3c3491fffe22507cafc9347e10cbf6bd31Christopher Ferris    test_func(buf, i);
367b687ad3c3491fffe22507cafc9347e10cbf6bd31Christopher Ferris  }
368b687ad3c3491fffe22507cafc9347e10cbf6bd31Christopher Ferris  ASSERT_TRUE(mprotect(&memory[pagesize], pagesize, PROT_READ | PROT_WRITE) == 0);
369b687ad3c3491fffe22507cafc9347e10cbf6bd31Christopher Ferris  free(memory);
370b687ad3c3491fffe22507cafc9347e10cbf6bd31Christopher Ferris}
371b687ad3c3491fffe22507cafc9347e10cbf6bd31Christopher Ferris
372b687ad3c3491fffe22507cafc9347e10cbf6bd31Christopher Ferrisvoid RunSrcDstBufferOverreadTest(void (*test_func)(uint8_t*, uint8_t*, size_t)) {
373b687ad3c3491fffe22507cafc9347e10cbf6bd31Christopher Ferris  // In order to verify that functions are not reading past the end of the
374b687ad3c3491fffe22507cafc9347e10cbf6bd31Christopher Ferris  // src, create data that ends exactly at an unreadable memory boundary.
375b687ad3c3491fffe22507cafc9347e10cbf6bd31Christopher Ferris  size_t pagesize = static_cast<size_t>(sysconf(_SC_PAGE_SIZE));
376b687ad3c3491fffe22507cafc9347e10cbf6bd31Christopher Ferris  uint8_t* memory;
377b687ad3c3491fffe22507cafc9347e10cbf6bd31Christopher Ferris  ASSERT_TRUE(posix_memalign(reinterpret_cast<void**>(&memory), pagesize,
378b687ad3c3491fffe22507cafc9347e10cbf6bd31Christopher Ferris                             2*pagesize) == 0);
379b687ad3c3491fffe22507cafc9347e10cbf6bd31Christopher Ferris  memset(memory, 0x23, 2*pagesize);
380b687ad3c3491fffe22507cafc9347e10cbf6bd31Christopher Ferris
381b687ad3c3491fffe22507cafc9347e10cbf6bd31Christopher Ferris  // Make the second page unreadable and unwritable.
382b687ad3c3491fffe22507cafc9347e10cbf6bd31Christopher Ferris  ASSERT_TRUE(mprotect(&memory[pagesize], pagesize, PROT_NONE) == 0);
383b687ad3c3491fffe22507cafc9347e10cbf6bd31Christopher Ferris
384fdfcfce7c6392d32f95a9f776ecd13da205b906cChristopher Ferris  uint8_t* dst_buffer = new uint8_t[2*pagesize];
385fdfcfce7c6392d32f95a9f776ecd13da205b906cChristopher Ferris  // Change the dst alignment as we change the source.
386fdfcfce7c6392d32f95a9f776ecd13da205b906cChristopher Ferris  for (size_t i = 0; i < 16; i++) {
387fdfcfce7c6392d32f95a9f776ecd13da205b906cChristopher Ferris    uint8_t* dst = &dst_buffer[i];
388fdfcfce7c6392d32f95a9f776ecd13da205b906cChristopher Ferris    for (size_t j = 0; j < pagesize; j++) {
389fdfcfce7c6392d32f95a9f776ecd13da205b906cChristopher Ferris      uint8_t* src = &memory[pagesize-j];
390fdfcfce7c6392d32f95a9f776ecd13da205b906cChristopher Ferris
391fdfcfce7c6392d32f95a9f776ecd13da205b906cChristopher Ferris      test_func(src, dst, j);
392fdfcfce7c6392d32f95a9f776ecd13da205b906cChristopher Ferris    }
393b687ad3c3491fffe22507cafc9347e10cbf6bd31Christopher Ferris  }
394b687ad3c3491fffe22507cafc9347e10cbf6bd31Christopher Ferris  ASSERT_TRUE(mprotect(&memory[pagesize], pagesize, PROT_READ | PROT_WRITE) == 0);
395b687ad3c3491fffe22507cafc9347e10cbf6bd31Christopher Ferris  free(memory);
396fdfcfce7c6392d32f95a9f776ecd13da205b906cChristopher Ferris  delete[] dst_buffer;
397b687ad3c3491fffe22507cafc9347e10cbf6bd31Christopher Ferris}
398e5bbb6b6ab662503f06ceb20fa841d2e558d596dChristopher Ferris
399e5bbb6b6ab662503f06ceb20fa841d2e558d596dChristopher Ferrisvoid RunCmpBufferOverreadTest(
400e5bbb6b6ab662503f06ceb20fa841d2e558d596dChristopher Ferris    void (*test_cmp_func)(uint8_t*, uint8_t*, size_t),
401e5bbb6b6ab662503f06ceb20fa841d2e558d596dChristopher Ferris    void (*test_miscmp_func)(uint8_t*, uint8_t*, size_t, size_t)) {
402e5bbb6b6ab662503f06ceb20fa841d2e558d596dChristopher Ferris  // In order to verify that functions are not reading past the end of either
403e5bbb6b6ab662503f06ceb20fa841d2e558d596dChristopher Ferris  // of the bufs, create both buffers that end exactly at an unreadable memory
404e5bbb6b6ab662503f06ceb20fa841d2e558d596dChristopher Ferris  // boundary.
405e5bbb6b6ab662503f06ceb20fa841d2e558d596dChristopher Ferris  size_t pagesize = static_cast<size_t>(sysconf(_SC_PAGE_SIZE));
406e5bbb6b6ab662503f06ceb20fa841d2e558d596dChristopher Ferris  uint8_t* memory1;
407e5bbb6b6ab662503f06ceb20fa841d2e558d596dChristopher Ferris  ASSERT_TRUE(posix_memalign(reinterpret_cast<void**>(&memory1), pagesize,
408e5bbb6b6ab662503f06ceb20fa841d2e558d596dChristopher Ferris                             2*pagesize) == 0);
409e5bbb6b6ab662503f06ceb20fa841d2e558d596dChristopher Ferris  memset(memory1, 0x23, 2*pagesize);
410e5bbb6b6ab662503f06ceb20fa841d2e558d596dChristopher Ferris
411e5bbb6b6ab662503f06ceb20fa841d2e558d596dChristopher Ferris  // Make the second page unreadable and unwritable.
412e5bbb6b6ab662503f06ceb20fa841d2e558d596dChristopher Ferris  ASSERT_TRUE(mprotect(&memory1[pagesize], pagesize, PROT_NONE) == 0);
413e5bbb6b6ab662503f06ceb20fa841d2e558d596dChristopher Ferris
414e5bbb6b6ab662503f06ceb20fa841d2e558d596dChristopher Ferris  uint8_t* memory2;
415e5bbb6b6ab662503f06ceb20fa841d2e558d596dChristopher Ferris  ASSERT_TRUE(posix_memalign(reinterpret_cast<void**>(&memory2), pagesize,
416e5bbb6b6ab662503f06ceb20fa841d2e558d596dChristopher Ferris                             2*pagesize) == 0);
417e5bbb6b6ab662503f06ceb20fa841d2e558d596dChristopher Ferris  memset(memory2, 0x23, 2*pagesize);
418e5bbb6b6ab662503f06ceb20fa841d2e558d596dChristopher Ferris
419e5bbb6b6ab662503f06ceb20fa841d2e558d596dChristopher Ferris  // Make the second page unreadable and unwritable.
420e5bbb6b6ab662503f06ceb20fa841d2e558d596dChristopher Ferris  ASSERT_TRUE(mprotect(&memory2[pagesize], pagesize, PROT_NONE) == 0);
421e5bbb6b6ab662503f06ceb20fa841d2e558d596dChristopher Ferris
422e5bbb6b6ab662503f06ceb20fa841d2e558d596dChristopher Ferris  for (size_t i = 0; i < pagesize; i++) {
423e5bbb6b6ab662503f06ceb20fa841d2e558d596dChristopher Ferris    uint8_t* buf1 = &memory1[pagesize-i];
424e5bbb6b6ab662503f06ceb20fa841d2e558d596dChristopher Ferris    uint8_t* buf2 = &memory2[pagesize-i];
425e5bbb6b6ab662503f06ceb20fa841d2e558d596dChristopher Ferris
426e5bbb6b6ab662503f06ceb20fa841d2e558d596dChristopher Ferris    test_cmp_func(buf1, buf2, i);
427e5bbb6b6ab662503f06ceb20fa841d2e558d596dChristopher Ferris  }
428e5bbb6b6ab662503f06ceb20fa841d2e558d596dChristopher Ferris
429e5bbb6b6ab662503f06ceb20fa841d2e558d596dChristopher Ferris  // Don't cycle through pagesize, MISCMP_MAX_LENGTH bytes should be good.
430e5bbb6b6ab662503f06ceb20fa841d2e558d596dChristopher Ferris  size_t miscmp_len;
431e5bbb6b6ab662503f06ceb20fa841d2e558d596dChristopher Ferris  if (pagesize > MISCMP_MAX_LENGTH) {
432e5bbb6b6ab662503f06ceb20fa841d2e558d596dChristopher Ferris    miscmp_len = MISCMP_MAX_LENGTH;
433e5bbb6b6ab662503f06ceb20fa841d2e558d596dChristopher Ferris  } else {
434e5bbb6b6ab662503f06ceb20fa841d2e558d596dChristopher Ferris    miscmp_len = pagesize;
435e5bbb6b6ab662503f06ceb20fa841d2e558d596dChristopher Ferris  }
436e5bbb6b6ab662503f06ceb20fa841d2e558d596dChristopher Ferris  for (size_t i = 1; i < miscmp_len; i++) {
437e5bbb6b6ab662503f06ceb20fa841d2e558d596dChristopher Ferris    uint8_t* buf1 = &memory1[pagesize-i];
438e5bbb6b6ab662503f06ceb20fa841d2e558d596dChristopher Ferris    for (size_t j = 1; j < miscmp_len; j++) {
439e5bbb6b6ab662503f06ceb20fa841d2e558d596dChristopher Ferris      if (j == i)
440e5bbb6b6ab662503f06ceb20fa841d2e558d596dChristopher Ferris        continue;
441e5bbb6b6ab662503f06ceb20fa841d2e558d596dChristopher Ferris
442e5bbb6b6ab662503f06ceb20fa841d2e558d596dChristopher Ferris      uint8_t* buf2 = &memory2[pagesize-j];
443e5bbb6b6ab662503f06ceb20fa841d2e558d596dChristopher Ferris
444e5bbb6b6ab662503f06ceb20fa841d2e558d596dChristopher Ferris      test_miscmp_func(buf1, buf2, i, j);
445e5bbb6b6ab662503f06ceb20fa841d2e558d596dChristopher Ferris    }
446e5bbb6b6ab662503f06ceb20fa841d2e558d596dChristopher Ferris  }
447e5bbb6b6ab662503f06ceb20fa841d2e558d596dChristopher Ferris
448e5bbb6b6ab662503f06ceb20fa841d2e558d596dChristopher Ferris  ASSERT_TRUE(mprotect(&memory1[pagesize], pagesize, PROT_READ | PROT_WRITE) == 0);
449e5bbb6b6ab662503f06ceb20fa841d2e558d596dChristopher Ferris  ASSERT_TRUE(mprotect(&memory2[pagesize], pagesize, PROT_READ | PROT_WRITE) == 0);
450e5bbb6b6ab662503f06ceb20fa841d2e558d596dChristopher Ferris  free(memory1);
451e5bbb6b6ab662503f06ceb20fa841d2e558d596dChristopher Ferris  free(memory2);
452e5bbb6b6ab662503f06ceb20fa841d2e558d596dChristopher Ferris}
453