1 // Copyright (c) 2012 The Chromium Authors. All rights reserved. 2 // Use of this source code is governed by a BSD-style license that can be 3 // found in the LICENSE file. 4 5 #include "sandbox/linux/seccomp-bpf/sandbox_bpf.h" 6 #include "sandbox/linux/seccomp-bpf/syscall_iterator.h" 7 #include "sandbox/linux/tests/unit_tests.h" 8 9 namespace sandbox { 10 11 namespace { 12 13 SANDBOX_TEST(SyscallIterator, Monotonous) { 14 for (int i = 0; i < 2; ++i) { 15 bool invalid_only = !i; // Testing both |invalid_only| cases. 16 SyscallIterator iter(invalid_only); 17 uint32_t next = iter.Next(); 18 19 if (!invalid_only) { 20 // The iterator should start at 0. 21 SANDBOX_ASSERT(next == 0); 22 } 23 for (uint32_t last = next; !iter.Done(); last = next) { 24 next = iter.Next(); 25 SANDBOX_ASSERT(last < next); 26 } 27 // The iterator should always return 0xFFFFFFFFu as the last value. 28 SANDBOX_ASSERT(next == 0xFFFFFFFFu); 29 } 30 } 31 32 SANDBOX_TEST(SyscallIterator, PublicSyscallRange) { 33 SyscallIterator iter(false); 34 uint32_t next = iter.Next(); 35 36 // The iterator should cover the public syscall range 37 // MIN_SYSCALL..MAX_PUBLIC_SYSCALL, without skipping syscalls. 38 // We're assuming MIN_SYSCALL == 0 for all architectures, 39 // this is currently valid for Intel and ARM EABI. 40 SANDBOX_ASSERT(MIN_SYSCALL == 0); 41 SANDBOX_ASSERT(next == MIN_SYSCALL); 42 for (uint32_t last = next; next < MAX_PUBLIC_SYSCALL + 1; last = next) { 43 SANDBOX_ASSERT((next = iter.Next()) == last + 1); 44 } 45 SANDBOX_ASSERT(next == MAX_PUBLIC_SYSCALL + 1); 46 } 47 48 #if defined(__arm__) 49 SANDBOX_TEST(SyscallIterator, ARMPrivateSyscallRange) { 50 SyscallIterator iter(false); 51 uint32_t next = iter.Next(); 52 while (next < MIN_PRIVATE_SYSCALL - 1) { 53 next = iter.Next(); 54 } 55 // The iterator should cover the ARM private syscall range 56 // without skipping syscalls. 57 SANDBOX_ASSERT(next == MIN_PRIVATE_SYSCALL - 1); 58 for (uint32_t last = next; next < MAX_PRIVATE_SYSCALL + 1; last = next) { 59 SANDBOX_ASSERT((next = iter.Next()) == last + 1); 60 } 61 SANDBOX_ASSERT(next == MAX_PRIVATE_SYSCALL + 1); 62 } 63 64 SANDBOX_TEST(SyscallIterator, ARMHiddenSyscallRange) { 65 SyscallIterator iter(false); 66 uint32_t next = iter.Next(); 67 while (next < MIN_GHOST_SYSCALL - 1) { 68 next = iter.Next(); 69 } 70 // The iterator should cover the ARM hidden syscall range 71 // without skipping syscalls. 72 SANDBOX_ASSERT(next == MIN_GHOST_SYSCALL - 1); 73 for (uint32_t last = next; next < MAX_SYSCALL + 1; last = next) { 74 SANDBOX_ASSERT((next = iter.Next()) == last + 1); 75 } 76 SANDBOX_ASSERT(next == MAX_SYSCALL + 1); 77 } 78 #endif 79 80 SANDBOX_TEST(SyscallIterator, Invalid) { 81 for (int i = 0; i < 2; ++i) { 82 bool invalid_only = !i; // Testing both |invalid_only| cases. 83 SyscallIterator iter(invalid_only); 84 uint32_t next = iter.Next(); 85 86 while (next < MAX_SYSCALL + 1) { 87 next = iter.Next(); 88 } 89 90 SANDBOX_ASSERT(next == MAX_SYSCALL + 1); 91 while (next < 0x7FFFFFFFu) { 92 next = iter.Next(); 93 } 94 95 // The iterator should return the signed/unsigned corner cases. 96 SANDBOX_ASSERT(next == 0x7FFFFFFFu); 97 next = iter.Next(); 98 SANDBOX_ASSERT(next == 0x80000000u); 99 SANDBOX_ASSERT(!iter.Done()); 100 next = iter.Next(); 101 SANDBOX_ASSERT(iter.Done()); 102 SANDBOX_ASSERT(next == 0xFFFFFFFFu); 103 } 104 } 105 106 SANDBOX_TEST(SyscallIterator, InvalidOnly) { 107 bool invalid_only = true; 108 SyscallIterator iter(invalid_only); 109 uint32_t next = iter.Next(); 110 // We're assuming MIN_SYSCALL == 0 for all architectures, 111 // this is currently valid for Intel and ARM EABI. 112 // First invalid syscall should then be |MAX_PUBLIC_SYSCALL + 1|. 113 SANDBOX_ASSERT(MIN_SYSCALL == 0); 114 SANDBOX_ASSERT(next == MAX_PUBLIC_SYSCALL + 1); 115 116 #if defined(__arm__) 117 next = iter.Next(); 118 // The iterator should skip until the last invalid syscall in this range. 119 SANDBOX_ASSERT(next == MIN_PRIVATE_SYSCALL - 1); 120 while (next <= MAX_PRIVATE_SYSCALL) { 121 next = iter.Next(); 122 } 123 124 next = iter.Next(); 125 // The iterator should skip until the last invalid syscall in this range. 126 SANDBOX_ASSERT(next == MIN_GHOST_SYSCALL - 1); 127 while (next <= MAX_SYSCALL) { 128 next = iter.Next(); 129 } 130 SANDBOX_ASSERT(next == MAX_SYSCALL + 1); 131 #endif 132 } 133 134 } // namespace 135 136 } // namespace sandbox 137