blob: b5fcf267fe637100f869c14977abc49ab0fb05d4 [file] [log] [blame]
Elliott Hughesa55f6302013-01-02 14:23:43 -08001/*
2 * Copyright (C) 2012 The Android Open Source Project
3 *
4 * Licensed under the Apache License, Version 2.0 (the "License");
5 * you may not use this file except in compliance with the License.
6 * You may obtain a copy of the License at
7 *
8 * http://www.apache.org/licenses/LICENSE-2.0
9 *
10 * Unless required by applicable law or agreed to in writing, software
11 * distributed under the License is distributed on an "AS IS" BASIS,
12 * WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
13 * See the License for the specific language governing permissions and
14 * limitations under the License.
15 */
16
17#include <gtest/gtest.h>
Yabin Cui9df70402014-11-05 18:01:01 -080018#include "BionicDeathTest.h"
Christopher Ferris13613132013-10-28 15:24:04 -070019#include "ScopedSignalHandler.h"
Elliott Hughesb4f76162013-09-19 16:27:24 -070020#include "TemporaryFile.h"
Elliott Hughesa55f6302013-01-02 14:23:43 -080021
Elliott Hughes915fefb2014-02-18 12:34:51 -080022#include <errno.h>
Colin Cross3d19a832014-02-14 18:56:23 -080023#include <fcntl.h>
Elliott Hughes21972b62014-07-28 12:24:22 -070024#include <limits.h>
Elliott Hughes428f5562013-02-05 16:10:59 -080025#include <stdint.h>
Yabin Cuib5e581a2014-11-08 14:58:12 -080026#include <sys/param.h>
Elliott Hughes7086ad62014-06-19 16:39:01 -070027#include <sys/syscall.h>
Elliott Hughes764a9932014-04-08 19:44:36 -070028#include <sys/types.h>
Derek Xued94e7f02014-09-25 11:12:01 +010029#include <sys/utsname.h>
Elliott Hughes764a9932014-04-08 19:44:36 -070030#include <sys/wait.h>
Yabin Cui9df70402014-11-05 18:01:01 -080031#include <unistd.h>
32
Elliott Hughesa55f6302013-01-02 14:23:43 -080033TEST(unistd, sysconf_SC_MONOTONIC_CLOCK) {
34 ASSERT_GT(sysconf(_SC_MONOTONIC_CLOCK), 0);
35}
Elliott Hughes428f5562013-02-05 16:10:59 -080036
Elliott Hughes533dde42014-04-25 18:27:38 -070037static void* get_brk() {
38 return sbrk(0);
39}
Elliott Hughes428f5562013-02-05 16:10:59 -080040
Elliott Hughes533dde42014-04-25 18:27:38 -070041static void* page_align(uintptr_t addr) {
42 uintptr_t mask = sysconf(_SC_PAGE_SIZE) - 1;
43 return reinterpret_cast<void*>((addr + mask) & ~mask);
44}
45
46TEST(unistd, brk) {
47 void* initial_break = get_brk();
48
49 // The kernel aligns the break to a page.
50 void* new_break = reinterpret_cast<void*>(reinterpret_cast<uintptr_t>(initial_break) + 1);
Elliott Hughes428f5562013-02-05 16:10:59 -080051 ASSERT_EQ(0, brk(new_break));
Elliott Hughes533dde42014-04-25 18:27:38 -070052 ASSERT_GE(get_brk(), new_break);
Elliott Hughes428f5562013-02-05 16:10:59 -080053
Elliott Hughes533dde42014-04-25 18:27:38 -070054 new_break = page_align(reinterpret_cast<uintptr_t>(initial_break) + sysconf(_SC_PAGE_SIZE));
55 ASSERT_EQ(0, brk(new_break));
56 ASSERT_EQ(get_brk(), new_break);
57}
58
59TEST(unistd, brk_ENOMEM) {
60 ASSERT_EQ(-1, brk(reinterpret_cast<void*>(-1)));
61 ASSERT_EQ(ENOMEM, errno);
62}
63
Christopher Ferris738b0cc2014-05-21 19:03:34 -070064#if defined(__GLIBC__)
65#define SBRK_MIN INTPTR_MIN
66#define SBRK_MAX INTPTR_MAX
67#else
68#define SBRK_MIN PTRDIFF_MIN
69#define SBRK_MAX PTRDIFF_MAX
70#endif
71
Elliott Hughes533dde42014-04-25 18:27:38 -070072TEST(unistd, sbrk_ENOMEM) {
Christopher Ferris738b0cc2014-05-21 19:03:34 -070073#if defined(__BIONIC__) && !defined(__LP64__)
74 // There is no way to guarantee that all overflow conditions can be tested
75 // without manipulating the underlying values of the current break.
76 extern void* __bionic_brk;
77
78 class ScopedBrk {
79 public:
80 ScopedBrk() : saved_brk_(__bionic_brk) {}
81 virtual ~ScopedBrk() { __bionic_brk = saved_brk_; }
82
83 private:
84 void* saved_brk_;
85 };
86
87 ScopedBrk scope_brk;
88
89 // Set the current break to a point that will cause an overflow.
90 __bionic_brk = reinterpret_cast<void*>(static_cast<uintptr_t>(PTRDIFF_MAX) + 2);
Elliott Hughes533dde42014-04-25 18:27:38 -070091
92 // Can't increase by so much that we'd overflow.
93 ASSERT_EQ(reinterpret_cast<void*>(-1), sbrk(PTRDIFF_MAX));
94 ASSERT_EQ(ENOMEM, errno);
95
Christopher Ferris738b0cc2014-05-21 19:03:34 -070096 // Set the current break to a point that will cause an overflow.
97 __bionic_brk = reinterpret_cast<void*>(static_cast<uintptr_t>(PTRDIFF_MAX));
Elliott Hughes533dde42014-04-25 18:27:38 -070098
Elliott Hughes533dde42014-04-25 18:27:38 -070099 ASSERT_EQ(reinterpret_cast<void*>(-1), sbrk(PTRDIFF_MIN));
100 ASSERT_EQ(ENOMEM, errno);
Christopher Ferris738b0cc2014-05-21 19:03:34 -0700101
102 __bionic_brk = reinterpret_cast<void*>(static_cast<uintptr_t>(PTRDIFF_MAX) - 1);
103
104 ASSERT_EQ(reinterpret_cast<void*>(-1), sbrk(PTRDIFF_MIN + 1));
105 ASSERT_EQ(ENOMEM, errno);
106#else
107 class ScopedBrk {
108 public:
109 ScopedBrk() : saved_brk_(get_brk()) {}
110 virtual ~ScopedBrk() { brk(saved_brk_); }
111
112 private:
113 void* saved_brk_;
114 };
115
116 ScopedBrk scope_brk;
117
118 uintptr_t cur_brk = reinterpret_cast<uintptr_t>(get_brk());
119 if (cur_brk < static_cast<uintptr_t>(-(SBRK_MIN+1))) {
120 // Do the overflow test for a max negative increment.
121 ASSERT_EQ(reinterpret_cast<void*>(-1), sbrk(SBRK_MIN));
122#if defined(__BIONIC__)
123 // GLIBC does not set errno in overflow case.
124 ASSERT_EQ(ENOMEM, errno);
125#endif
126 }
127
128 uintptr_t overflow_brk = static_cast<uintptr_t>(SBRK_MAX) + 2;
129 if (cur_brk < overflow_brk) {
130 // Try and move the value to PTRDIFF_MAX + 2.
131 cur_brk = reinterpret_cast<uintptr_t>(sbrk(overflow_brk));
132 }
133 if (cur_brk >= overflow_brk) {
134 ASSERT_EQ(reinterpret_cast<void*>(-1), sbrk(SBRK_MAX));
135#if defined(__BIONIC__)
136 // GLIBC does not set errno in overflow case.
137 ASSERT_EQ(ENOMEM, errno);
138#endif
139 }
Elliott Hughes533dde42014-04-25 18:27:38 -0700140#endif
Elliott Hughes428f5562013-02-05 16:10:59 -0800141}
Elliott Hughesb4f76162013-09-19 16:27:24 -0700142
143TEST(unistd, truncate) {
144 TemporaryFile tf;
145 ASSERT_EQ(0, close(tf.fd));
146 ASSERT_EQ(0, truncate(tf.filename, 123));
147
148 struct stat sb;
149 ASSERT_EQ(0, stat(tf.filename, &sb));
150 ASSERT_EQ(123, sb.st_size);
151}
152
153TEST(unistd, truncate64) {
154 TemporaryFile tf;
155 ASSERT_EQ(0, close(tf.fd));
156 ASSERT_EQ(0, truncate64(tf.filename, 123));
157
158 struct stat sb;
159 ASSERT_EQ(0, stat(tf.filename, &sb));
160 ASSERT_EQ(123, sb.st_size);
161}
162
163TEST(unistd, ftruncate) {
164 TemporaryFile tf;
165 ASSERT_EQ(0, ftruncate(tf.fd, 123));
166 ASSERT_EQ(0, close(tf.fd));
167
168 struct stat sb;
169 ASSERT_EQ(0, stat(tf.filename, &sb));
170 ASSERT_EQ(123, sb.st_size);
171}
172
173TEST(unistd, ftruncate64) {
174 TemporaryFile tf;
175 ASSERT_EQ(0, ftruncate64(tf.fd, 123));
176 ASSERT_EQ(0, close(tf.fd));
177
178 struct stat sb;
179 ASSERT_EQ(0, stat(tf.filename, &sb));
180 ASSERT_EQ(123, sb.st_size);
181}
Elliott Hughes11952072013-10-24 15:15:14 -0700182
Elliott Hughes1728b232014-05-14 10:02:03 -0700183static bool g_pause_test_flag = false;
Elliott Hughes11952072013-10-24 15:15:14 -0700184static void PauseTestSignalHandler(int) {
Elliott Hughes1728b232014-05-14 10:02:03 -0700185 g_pause_test_flag = true;
Elliott Hughes11952072013-10-24 15:15:14 -0700186}
187
188TEST(unistd, pause) {
Christopher Ferris13613132013-10-28 15:24:04 -0700189 ScopedSignalHandler handler(SIGALRM, PauseTestSignalHandler);
190
Elliott Hughes11952072013-10-24 15:15:14 -0700191 alarm(1);
Elliott Hughes1728b232014-05-14 10:02:03 -0700192 ASSERT_FALSE(g_pause_test_flag);
Elliott Hughes11952072013-10-24 15:15:14 -0700193 ASSERT_EQ(-1, pause());
Elliott Hughes1728b232014-05-14 10:02:03 -0700194 ASSERT_TRUE(g_pause_test_flag);
Elliott Hughes11952072013-10-24 15:15:14 -0700195}
Colin Cross3d19a832014-02-14 18:56:23 -0800196
197TEST(unistd, read) {
198 int fd = open("/proc/version", O_RDONLY);
199 ASSERT_TRUE(fd != -1);
200
201 char buf[5];
202 ASSERT_EQ(5, read(fd, buf, 5));
203 ASSERT_EQ(buf[0], 'L');
204 ASSERT_EQ(buf[1], 'i');
205 ASSERT_EQ(buf[2], 'n');
206 ASSERT_EQ(buf[3], 'u');
207 ASSERT_EQ(buf[4], 'x');
208 close(fd);
209}
210
211TEST(unistd, read_EBADF) {
212 // read returns ssize_t which is 64-bits on LP64, so it's worth explicitly checking that
213 // our syscall stubs correctly return a 64-bit -1.
214 char buf[1];
215 ASSERT_EQ(-1, read(-1, buf, sizeof(buf)));
216 ASSERT_EQ(EBADF, errno);
217}
Elliott Hughesaedb00d2014-03-03 14:38:20 -0800218
Elliott Hughes21972b62014-07-28 12:24:22 -0700219TEST(unistd, syscall_long) {
220 // Check that syscall(3) correctly returns long results.
221 // https://code.google.com/p/android/issues/detail?id=73952
222 // We assume that the break is > 4GiB, but this is potentially flaky.
223 uintptr_t p = reinterpret_cast<uintptr_t>(sbrk(0));
224 ASSERT_EQ(p, static_cast<uintptr_t>(syscall(__NR_brk, 0)));
225}
226
Elliott Hughesaedb00d2014-03-03 14:38:20 -0800227TEST(unistd, alarm) {
228 ASSERT_EQ(0U, alarm(0));
229}
Elliott Hughes9f525642014-04-08 17:14:01 -0700230
231TEST(unistd, _exit) {
232 int pid = fork();
233 ASSERT_NE(-1, pid) << strerror(errno);
234
235 if (pid == 0) {
236 _exit(99);
237 }
238
239 int status;
240 ASSERT_EQ(pid, waitpid(pid, &status, 0));
241 ASSERT_TRUE(WIFEXITED(status));
242 ASSERT_EQ(99, WEXITSTATUS(status));
243}
Grigoriy Kraynovcbf6df02013-09-17 15:44:22 +0400244
245TEST(unistd, getenv_unsetenv) {
246 ASSERT_EQ(0, setenv("test-variable", "hello", 1));
247 ASSERT_STREQ("hello", getenv("test-variable"));
248 ASSERT_EQ(0, unsetenv("test-variable"));
249 ASSERT_TRUE(getenv("test-variable") == NULL);
250}
251
252TEST(unistd, unsetenv_EINVAL) {
Grigoriy Kraynovcbf6df02013-09-17 15:44:22 +0400253 EXPECT_EQ(-1, unsetenv(""));
254 EXPECT_EQ(EINVAL, errno);
255 EXPECT_EQ(-1, unsetenv("a=b"));
256 EXPECT_EQ(EINVAL, errno);
257}
258
259TEST(unistd, setenv_EINVAL) {
260 EXPECT_EQ(-1, setenv(NULL, "value", 0));
261 EXPECT_EQ(EINVAL, errno);
262 EXPECT_EQ(-1, setenv(NULL, "value", 1));
263 EXPECT_EQ(EINVAL, errno);
264 EXPECT_EQ(-1, setenv("", "value", 0));
265 EXPECT_EQ(EINVAL, errno);
266 EXPECT_EQ(-1, setenv("", "value", 1));
267 EXPECT_EQ(EINVAL, errno);
268 EXPECT_EQ(-1, setenv("a=b", "value", 0));
269 EXPECT_EQ(EINVAL, errno);
270 EXPECT_EQ(-1, setenv("a=b", "value", 1));
271 EXPECT_EQ(EINVAL, errno);
272}
273
274TEST(unistd, setenv) {
275 ASSERT_EQ(0, unsetenv("test-variable"));
276
277 char a[] = "a";
278 char b[] = "b";
279 char c[] = "c";
280
281 // New value.
282 EXPECT_EQ(0, setenv("test-variable", a, 0));
283 EXPECT_STREQ(a, getenv("test-variable"));
284
285 // Existing value, no overwrite.
286 EXPECT_EQ(0, setenv("test-variable", b, 0));
287 EXPECT_STREQ(a, getenv("test-variable"));
288
289 // Existing value, overwrite.
290 EXPECT_EQ(0, setenv("test-variable", c, 1));
291 EXPECT_STREQ(c, getenv("test-variable"));
292 // But the arrays backing the values are unchanged.
293 EXPECT_EQ('a', a[0]);
294 EXPECT_EQ('b', b[0]);
295 EXPECT_EQ('c', c[0]);
296
297 ASSERT_EQ(0, unsetenv("test-variable"));
298}
299
300TEST(unistd, putenv) {
301 ASSERT_EQ(0, unsetenv("a"));
302
303 char* s1 = strdup("a=b");
304 ASSERT_EQ(0, putenv(s1));
305
306 ASSERT_STREQ("b", getenv("a"));
307 s1[2] = 'c';
308 ASSERT_STREQ("c", getenv("a"));
309
310 char* s2 = strdup("a=b");
311 ASSERT_EQ(0, putenv(s2));
312
313 ASSERT_STREQ("b", getenv("a"));
314 ASSERT_EQ('c', s1[2]);
315
316 ASSERT_EQ(0, unsetenv("a"));
317 free(s1);
318 free(s2);
319}
320
321TEST(unistd, clearenv) {
322 extern char** environ;
323
324 // Guarantee that environ is not initially empty...
325 ASSERT_EQ(0, setenv("test-variable", "a", 1));
326
327 // Stash a copy.
328 std::vector<char*> old_environ;
329 for (size_t i = 0; environ[i] != NULL; ++i) {
330 old_environ.push_back(strdup(environ[i]));
331 }
332
333 ASSERT_EQ(0, clearenv());
334
335 EXPECT_TRUE(environ == NULL || environ[0] == NULL);
336 EXPECT_EQ(NULL, getenv("test-variable"));
337 EXPECT_EQ(0, setenv("test-variable", "post-clear", 1));
338 EXPECT_STREQ("post-clear", getenv("test-variable"));
339
340 // Put the old environment back.
341 for (size_t i = 0; i < old_environ.size(); ++i) {
342 EXPECT_EQ(0, putenv(old_environ[i]));
343 }
344
345 // Check it wasn't overwritten.
346 EXPECT_STREQ("a", getenv("test-variable"));
347
348 EXPECT_EQ(0, unsetenv("test-variable"));
349}
Elliott Hughesa62a28d2014-05-07 14:30:33 -0700350
351static void TestFsyncFunction(int (*fn)(int)) {
352 int fd;
353
354 // Can't sync an invalid fd.
355 errno = 0;
356 EXPECT_EQ(-1, fn(-1));
357 EXPECT_EQ(EBADF, errno);
358
359 // It doesn't matter whether you've opened a file for write or not.
360 TemporaryFile tf;
361 ASSERT_NE(-1, tf.fd);
362
363 EXPECT_EQ(0, fn(tf.fd));
364
365 ASSERT_NE(-1, fd = open(tf.filename, O_RDONLY));
366 EXPECT_EQ(0, fn(fd));
367 close(fd);
368
369 ASSERT_NE(-1, fd = open(tf.filename, O_RDWR));
370 EXPECT_EQ(0, fn(fd));
371 close(fd);
372
373 // The fd can even be a directory.
374 ASSERT_NE(-1, fd = open("/", O_RDONLY));
375 EXPECT_EQ(0, fn(fd));
376 close(fd);
377
378 // But some file systems may choose to be fussy...
379 errno = 0;
380 ASSERT_NE(-1, fd = open("/proc/version", O_RDONLY));
381 EXPECT_EQ(-1, fn(fd));
382 EXPECT_EQ(EINVAL, errno);
383 close(fd);
384}
385
386TEST(unistd, fdatasync) {
387 TestFsyncFunction(fdatasync);
388}
389
390TEST(unistd, fsync) {
391 TestFsyncFunction(fsync);
392}
Elliott Hughes7086ad62014-06-19 16:39:01 -0700393
Elliott Hughesfa9e16e2014-06-23 17:49:45 -0700394static void AssertGetPidCorrect() {
395 // The loop is just to make manual testing/debugging with strace easier.
396 pid_t getpid_syscall_result = syscall(__NR_getpid);
397 for (size_t i = 0; i < 128; ++i) {
398 ASSERT_EQ(getpid_syscall_result, getpid());
399 }
400}
401
Elliott Hughes7086ad62014-06-19 16:39:01 -0700402TEST(unistd, getpid_caching_and_fork) {
403 pid_t parent_pid = getpid();
404 ASSERT_EQ(syscall(__NR_getpid), parent_pid);
405
406 pid_t fork_result = fork();
407 ASSERT_NE(fork_result, -1);
408 if (fork_result == 0) {
409 // We're the child.
Elliott Hughesfa9e16e2014-06-23 17:49:45 -0700410 AssertGetPidCorrect();
Elliott Hughes7086ad62014-06-19 16:39:01 -0700411 ASSERT_EQ(parent_pid, getppid());
412 _exit(123);
413 } else {
414 // We're the parent.
415 ASSERT_EQ(parent_pid, getpid());
416
417 int status;
418 ASSERT_EQ(fork_result, waitpid(fork_result, &status, 0));
419 ASSERT_TRUE(WIFEXITED(status));
420 ASSERT_EQ(123, WEXITSTATUS(status));
421 }
422}
423
Elliott Hughesfa9e16e2014-06-23 17:49:45 -0700424static int GetPidCachingCloneStartRoutine(void*) {
425 AssertGetPidCorrect();
426 return 123;
Elliott Hughes7086ad62014-06-19 16:39:01 -0700427}
428
Elliott Hughesfa9e16e2014-06-23 17:49:45 -0700429TEST(unistd, getpid_caching_and_clone) {
430 pid_t parent_pid = getpid();
431 ASSERT_EQ(syscall(__NR_getpid), parent_pid);
432
433 void* child_stack[1024];
434 int clone_result = clone(GetPidCachingCloneStartRoutine, &child_stack[1024], CLONE_NEWNS | SIGCHLD, NULL);
Elliott Hughes2b3b2ec2014-08-21 19:23:53 -0700435 if (clone_result == -1 && errno == EPERM && getuid() != 0) {
436 GTEST_LOG_(INFO) << "This test only works if you have permission to CLONE_NEWNS; try running as root.\n";
437 return;
438 }
Elliott Hughesfa9e16e2014-06-23 17:49:45 -0700439 ASSERT_NE(clone_result, -1);
440
441 ASSERT_EQ(parent_pid, getpid());
442
443 int status;
444 ASSERT_EQ(clone_result, waitpid(clone_result, &status, 0));
445 ASSERT_TRUE(WIFEXITED(status));
446 ASSERT_EQ(123, WEXITSTATUS(status));
447}
448
449static void* GetPidCachingPthreadStartRoutine(void*) {
450 AssertGetPidCorrect();
Elliott Hughes7086ad62014-06-19 16:39:01 -0700451 return NULL;
452}
453
454TEST(unistd, getpid_caching_and_pthread_create) {
455 pid_t parent_pid = getpid();
456
457 pthread_t t;
Elliott Hughesfa9e16e2014-06-23 17:49:45 -0700458 ASSERT_EQ(0, pthread_create(&t, NULL, GetPidCachingPthreadStartRoutine, NULL));
Elliott Hughes7086ad62014-06-19 16:39:01 -0700459
460 ASSERT_EQ(parent_pid, getpid());
461
462 void* result;
463 ASSERT_EQ(0, pthread_join(t, &result));
464 ASSERT_EQ(NULL, result);
465}
Elliott Hughes60452a22014-09-22 14:41:30 -0700466
Yabin Cui9df70402014-11-05 18:01:01 -0800467class unistd_DeathTest : public BionicDeathTest {};
468
469TEST_F(unistd_DeathTest, abort) {
Elliott Hughes60452a22014-09-22 14:41:30 -0700470 ASSERT_EXIT(abort(), testing::KilledBySignal(SIGABRT), "");
471}
Elliott Hughesb86a4c72014-11-07 16:07:13 -0800472
473TEST(unistd, sethostname) {
474 // The permissions check happens before the argument check, so this will
475 // fail for a different reason if you're running as root than if you're
476 // not, but it'll fail either way. Checking that we have the symbol is about
477 // all we can do for sethostname(2).
478 ASSERT_EQ(-1, sethostname("", -1));
479}
Derek Xued94e7f02014-09-25 11:12:01 +0100480
481TEST(unistd, gethostname) {
482 char hostname[HOST_NAME_MAX + 1];
Derek Xued94e7f02014-09-25 11:12:01 +0100483 memset(hostname, 0, sizeof(hostname));
484
Yongqin Liu2f954ba2014-10-30 16:34:55 +0800485 // Can we get the hostname with a big buffer?
Derek Xued94e7f02014-09-25 11:12:01 +0100486 ASSERT_EQ(0, gethostname(hostname, HOST_NAME_MAX));
Yongqin Liu2f954ba2014-10-30 16:34:55 +0800487
488 // Can we get the hostname with a right-sized buffer?
489 errno = 0;
490 ASSERT_EQ(0, gethostname(hostname, strlen(hostname) + 1));
491
492 // Does uname(2) agree?
Derek Xued94e7f02014-09-25 11:12:01 +0100493 utsname buf;
494 ASSERT_EQ(0, uname(&buf));
495 ASSERT_EQ(0, strncmp(hostname, buf.nodename, SYS_NMLN));
496 ASSERT_GT(strlen(hostname), 0U);
497
Yongqin Liu2f954ba2014-10-30 16:34:55 +0800498 // Do we correctly detect truncation?
Derek Xued94e7f02014-09-25 11:12:01 +0100499 errno = 0;
500 ASSERT_EQ(-1, gethostname(hostname, strlen(hostname)));
501 ASSERT_EQ(ENAMETOOLONG, errno);
Derek Xued94e7f02014-09-25 11:12:01 +0100502}
Yabin Cuib5e581a2014-11-08 14:58:12 -0800503
504TEST(unistd, pathconf_fpathconf) {
505 TemporaryFile tf;
506 long rc = 0L;
507 // As a file system's block size is always power of 2, the configure values
508 // for ALLOC and XFER should be power of 2 as well.
509 rc = pathconf(tf.filename, _PC_ALLOC_SIZE_MIN);
510 ASSERT_TRUE(rc > 0 && powerof2(rc));
511 rc = pathconf(tf.filename, _PC_REC_MIN_XFER_SIZE);
512 ASSERT_TRUE(rc > 0 && powerof2(rc));
513 rc = pathconf(tf.filename, _PC_REC_XFER_ALIGN);
514 ASSERT_TRUE(rc > 0 && powerof2(rc));
515
516 rc = fpathconf(tf.fd, _PC_ALLOC_SIZE_MIN);
517 ASSERT_TRUE(rc > 0 && powerof2(rc));
518 rc = fpathconf(tf.fd, _PC_REC_MIN_XFER_SIZE);
519 ASSERT_TRUE(rc > 0 && powerof2(rc));
520 rc = fpathconf(tf.fd, _PC_REC_XFER_ALIGN);
521 ASSERT_TRUE(rc > 0 && powerof2(rc));
522}