blob: 8b90df460f51dd04e7b19b4a62cfa290614188df [file] [log] [blame]
George Burgess IV9a274102019-06-04 15:39:52 -07001/*
2 * Copyright (C) 2019 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#ifndef __clang__
18#error "Non-clang isn't supported"
19#endif
20
21// Clang compile-time and run-time tests for Bionic's FORTIFY.
22//
23// This file is compiled in two configurations ways to give us a sane set of tests for clang's
24// FORTIFY implementation.
25//
26// One configuration uses clang's diagnostic consumer
27// (https://clang.llvm.org/doxygen/classclang_1_1VerifyDiagnosticConsumer.html#details)
28// to check diagnostics (e.g. the expected-* comments everywhere).
29//
30// Please note that this test does things like leaking memory. That's WAI.
31
32// Silence all "from 'diagnose_if'" `note`s from anywhere, including headers; they're uninteresting
33// for this test case, and their line numbers may change over time.
34// expected-note@* 0+{{from 'diagnose_if'}}
35//
36// Similarly, there are a few overload tricks we have to emit errors. Ignore any notes from those.
37// expected-note@* 0+{{candidate function}}
38
39#ifndef _FORTIFY_SOURCE
40#error "_FORTIFY_SOURCE must be defined"
41#endif
42
43#include <sys/cdefs.h>
44
45// This is a test specifically of bionic's FORTIFY machinery. Other stdlibs need not apply.
46#ifndef __BIONIC__
47// expected-no-diagnostics
48#else
49
50// As alluded to above, we're going to be doing some obviously very broken things in this file.
51// FORTIFY helpfully flags a lot of it at compile-time, but we want it to *actually* crash, too. So
52// let's wipe out any build-time errors.
53#ifndef COMPILATION_TESTS
54#undef __clang_error_if
55#define __clang_error_if(...)
56#undef __clang_warning_if
57#define __clang_warning_if(...)
58#endif
59
60#include <err.h>
61#include <fcntl.h>
62#include <limits.h>
63#include <poll.h>
64#include <signal.h>
65#include <stdio.h>
66#include <stdlib.h>
67#include <string.h>
68#include <sys/socket.h>
69#include <sys/stat.h>
70#include <sys/wait.h>
71#include <syslog.h>
72#include <unistd.h>
73#include <wchar.h>
74
75#ifndef COMPILATION_TESTS
76#include <gtest/gtest.h>
77#include "BionicDeathTest.h"
78
79#define CONCAT2(x, y) x##y
80#define CONCAT(x, y) CONCAT2(x, y)
81#define FORTIFY_TEST_NAME CONCAT(clang_fortify_test_, _FORTIFY_SOURCE)
82
83namespace {
84struct FORTIFY_TEST_NAME : BionicDeathTest {
85 protected:
86 void SetUp() override {
87 stdin_saved = dup(STDIN_FILENO);
88 if (stdin_saved < 0) err(1, "failed to dup stdin");
89
90 int devnull = open("/dev/null", O_RDONLY);
91 if (devnull < 0) err(1, "failed to open /dev/null");
92
93 if (!dup2(devnull, STDIN_FILENO)) err(1, "failed to overwrite stdin");
94 static_cast<void>(close(devnull));
95
96 BionicDeathTest::SetUp();
97 }
98
99 void TearDown() override {
100 if (stdin_saved == -1) return;
101 if (!dup2(stdin_saved, STDIN_FILENO)) warn("failed to restore stdin");
102
103 static_cast<void>(close(stdin_saved));
104
105 BionicDeathTest::TearDown();
106 }
107
108 private:
109 int stdin_saved = -1;
110};
111} // namespace
112
113template <typename Fn>
114__attribute__((noreturn)) static void ExitAfter(Fn&& f) {
115 f();
116 // No need to tear things down; our parent process should handle that.
117 _exit(0);
118}
119
120// In any case (including failing tests), we always want to die after this.
121#define DIE_WITH(expr, cond, regex) EXPECT_EXIT(ExitAfter([&] { (expr); }), cond, regex)
122
123// EXPECT_NO_DEATH forks so that the test remains alive on a bug, and so that the environment
124// doesn't get modified on no bug. (Environment modification is especially tricky to deal with given
125// the *_STRUCT variants below.)
126#define EXPECT_NO_DEATH(expr) DIE_WITH(expr, testing::ExitedWithCode(0), "")
127#define EXPECT_FORTIFY_DEATH(expr) DIE_WITH(expr, testing::KilledBySignal(SIGABRT), "FORTIFY")
128// Expecting death, but only if we're doing a "strict" struct-checking mode.
129#if _FORTIFY_SOURCE > 1
130#define EXPECT_FORTIFY_DEATH_STRUCT EXPECT_FORTIFY_DEATH
131#else
132#define EXPECT_FORTIFY_DEATH_STRUCT EXPECT_NO_DEATH
133#endif
134
135#define FORTIFY_TEST(test_name) TEST(FORTIFY_TEST_NAME, test_name)
136
137#else // defined(COMPILATION_TESTS)
138
139#define EXPECT_NO_DEATH(expr) expr
140#define EXPECT_FORTIFY_DEATH(expr) expr
141#define EXPECT_FORTIFY_DEATH_STRUCT EXPECT_FORTIFY_DEATH
142#define FORTIFY_TEST(test_name) void test_name()
143#endif
144
145const static int kBogusFD = -1;
146
147FORTIFY_TEST(string) {
148 char small_buffer[8] = {};
149
150 {
151 char large_buffer[sizeof(small_buffer) + 1] = {};
152 // expected-error@+1{{size bigger than buffer}}
153 EXPECT_FORTIFY_DEATH(memcpy(small_buffer, large_buffer, sizeof(large_buffer)));
154 // expected-error@+1{{size bigger than buffer}}
155 EXPECT_FORTIFY_DEATH(memmove(small_buffer, large_buffer, sizeof(large_buffer)));
156 // FIXME: this should be EXPECT_FORTIFY_DEATH
157#if 0
158 // expected-error@+1{{called with bigger length than the destination}}
159#endif
160 EXPECT_NO_DEATH(mempcpy(small_buffer, large_buffer, sizeof(large_buffer)));
161 // expected-error@+1{{size bigger than buffer}}
162 EXPECT_FORTIFY_DEATH(memset(small_buffer, 0, sizeof(large_buffer)));
163 // expected-warning@+1{{arguments got flipped?}}
164 EXPECT_NO_DEATH(memset(small_buffer, sizeof(small_buffer), 0));
165 // FIXME: Should these be warnings?
166 // expected-warning@+1{{will always overflow}}
167 EXPECT_FORTIFY_DEATH(bcopy(large_buffer, small_buffer, sizeof(large_buffer)));
168 // expected-warning@+1{{will always overflow}}
169 EXPECT_FORTIFY_DEATH(bzero(small_buffer, sizeof(large_buffer)));
170 }
171
172 {
173 const char large_string[] = "Hello!!!";
174 static_assert(sizeof(large_string) > sizeof(small_buffer), "");
175
176 // expected-error@+1{{string bigger than buffer}}
177 EXPECT_FORTIFY_DEATH(strcpy(small_buffer, large_string));
178 // expected-error@+1{{string bigger than buffer}}
179 EXPECT_FORTIFY_DEATH(stpcpy(small_buffer, large_string));
George Burgess IV77f99aa2019-06-06 14:14:52 -0700180 // expected-error@+1{{size bigger than buffer}}
George Burgess IV9a274102019-06-04 15:39:52 -0700181 EXPECT_FORTIFY_DEATH(strncpy(small_buffer, large_string, sizeof(large_string)));
George Burgess IV77f99aa2019-06-06 14:14:52 -0700182 // expected-error@+1{{size bigger than buffer}}
George Burgess IV9a274102019-06-04 15:39:52 -0700183 EXPECT_FORTIFY_DEATH(stpncpy(small_buffer, large_string, sizeof(large_string)));
George Burgess IV77f99aa2019-06-06 14:14:52 -0700184 // expected-error@+1{{string bigger than buffer}}
George Burgess IV9a274102019-06-04 15:39:52 -0700185 EXPECT_FORTIFY_DEATH(strcat(small_buffer, large_string));
George Burgess IV77f99aa2019-06-06 14:14:52 -0700186 // expected-error@+1{{size bigger than buffer}}
George Burgess IV9a274102019-06-04 15:39:52 -0700187 EXPECT_FORTIFY_DEATH(strncat(small_buffer, large_string, sizeof(large_string)));
George Burgess IV77f99aa2019-06-06 14:14:52 -0700188 // expected-error@+1{{size bigger than buffer}}
189 EXPECT_FORTIFY_DEATH(strlcpy(small_buffer, large_string, sizeof(large_string)));
190 // expected-error@+1{{size bigger than buffer}}
191 EXPECT_FORTIFY_DEATH(strlcat(small_buffer, large_string, sizeof(large_string)));
George Burgess IV9a274102019-06-04 15:39:52 -0700192 }
193
194 {
195 struct {
196 char tiny_buffer[4];
197 char tiny_buffer2[4];
198 } split = {};
199
200 EXPECT_NO_DEATH(memcpy(split.tiny_buffer, &split, sizeof(split)));
201 EXPECT_NO_DEATH(memcpy(split.tiny_buffer, &split, sizeof(split)));
202 EXPECT_NO_DEATH(memmove(split.tiny_buffer, &split, sizeof(split)));
203 EXPECT_NO_DEATH(mempcpy(split.tiny_buffer, &split, sizeof(split)));
204 EXPECT_NO_DEATH(memset(split.tiny_buffer, 0, sizeof(split)));
205
206 EXPECT_NO_DEATH(bcopy(&split, split.tiny_buffer, sizeof(split)));
207 EXPECT_NO_DEATH(bzero(split.tiny_buffer, sizeof(split)));
208
209 const char small_string[] = "Hi!!";
210 static_assert(sizeof(small_string) > sizeof(split.tiny_buffer), "");
211
212#if _FORTIFY_SOURCE > 1
213 // expected-error@+2{{string bigger than buffer}}
214#endif
215 EXPECT_FORTIFY_DEATH_STRUCT(strcpy(split.tiny_buffer, small_string));
216
217#if _FORTIFY_SOURCE > 1
218 // expected-error@+2{{string bigger than buffer}}
219#endif
220 EXPECT_FORTIFY_DEATH_STRUCT(stpcpy(split.tiny_buffer, small_string));
221
222#if _FORTIFY_SOURCE > 1
George Burgess IV77f99aa2019-06-06 14:14:52 -0700223 // expected-error@+2{{size bigger than buffer}}
George Burgess IV9a274102019-06-04 15:39:52 -0700224#endif
225 EXPECT_FORTIFY_DEATH_STRUCT(strncpy(split.tiny_buffer, small_string, sizeof(small_string)));
226
227#if _FORTIFY_SOURCE > 1
George Burgess IV77f99aa2019-06-06 14:14:52 -0700228 // expected-error@+2{{size bigger than buffer}}
George Burgess IV9a274102019-06-04 15:39:52 -0700229#endif
230 EXPECT_FORTIFY_DEATH_STRUCT(stpncpy(split.tiny_buffer, small_string, sizeof(small_string)));
231
232#if _FORTIFY_SOURCE > 1
George Burgess IV77f99aa2019-06-06 14:14:52 -0700233 // expected-error@+2{{string bigger than buffer}}
George Burgess IV9a274102019-06-04 15:39:52 -0700234#endif
235 EXPECT_FORTIFY_DEATH_STRUCT(strcat(split.tiny_buffer, small_string));
236
237#if _FORTIFY_SOURCE > 1
George Burgess IV77f99aa2019-06-06 14:14:52 -0700238 // expected-error@+2{{size bigger than buffer}}
George Burgess IV9a274102019-06-04 15:39:52 -0700239#endif
240 EXPECT_FORTIFY_DEATH_STRUCT(strncat(split.tiny_buffer, small_string, sizeof(small_string)));
George Burgess IV77f99aa2019-06-06 14:14:52 -0700241
242#if _FORTIFY_SOURCE > 1
243 // expected-error@+2{{size bigger than buffer}}
244#endif
245 EXPECT_FORTIFY_DEATH_STRUCT(strlcat(split.tiny_buffer, small_string, sizeof(small_string)));
246
247#if _FORTIFY_SOURCE > 1
248 // expected-error@+2{{size bigger than buffer}}
249#endif
250 EXPECT_FORTIFY_DEATH_STRUCT(strlcpy(split.tiny_buffer, small_string, sizeof(small_string)));
George Burgess IV9a274102019-06-04 15:39:52 -0700251 }
252}
253
George Burgess IV2356c932019-06-06 17:18:13 -0700254FORTIFY_TEST(fcntl) {
255 const char target[] = "/dev/null";
256 int dirfd = 0;
257
258 // These all emit hard errors without diagnose_if, so running them is a bit
259 // more involved.
260#ifdef COMPILATION_TESTS
261 // expected-error@+1{{too many arguments}}
262 open("/", 0, 0, 0);
263 // expected-error@+1{{too many arguments}}
264 open64("/", 0, 0, 0);
265 // expected-error@+1{{too many arguments}}
266 openat(0, "/", 0, 0, 0);
267 // expected-error@+1{{too many arguments}}
268 openat64(0, "/", 0, 0, 0);
269#endif
270
271 // expected-error@+1{{missing mode}}
272 EXPECT_FORTIFY_DEATH(open(target, O_CREAT));
273 // expected-error@+1{{missing mode}}
274 EXPECT_FORTIFY_DEATH(open(target, O_TMPFILE));
275 // expected-error@+1{{missing mode}}
276 EXPECT_FORTIFY_DEATH(open64(target, O_CREAT));
277 // expected-error@+1{{missing mode}}
278 EXPECT_FORTIFY_DEATH(open64(target, O_TMPFILE));
279 // expected-error@+1{{missing mode}}
280 EXPECT_FORTIFY_DEATH(openat(dirfd, target, O_CREAT));
281 // expected-error@+1{{missing mode}}
282 EXPECT_FORTIFY_DEATH(openat(dirfd, target, O_TMPFILE));
283 // expected-error@+1{{missing mode}}
284 EXPECT_FORTIFY_DEATH(openat64(dirfd, target, O_CREAT));
285 // expected-error@+1{{missing mode}}
286 EXPECT_FORTIFY_DEATH(openat64(dirfd, target, O_TMPFILE));
287
288 // expected-warning@+1{{superfluous mode bits}}
289 EXPECT_NO_DEATH(open(target, O_RDONLY, 0777));
290 // expected-warning@+1{{superfluous mode bits}}
291 EXPECT_NO_DEATH(open64(target, O_RDONLY, 0777));
292 // expected-warning@+1{{superfluous mode bits}}
293 EXPECT_NO_DEATH(openat(dirfd, target, O_RDONLY, 0777));
294 // expected-warning@+1{{superfluous mode bits}}
295 EXPECT_NO_DEATH(openat64(dirfd, target, O_RDONLY, 0777));
296}
297
George Burgess IV9a274102019-06-04 15:39:52 -0700298// Since these emit hard errors, it's sort of hard to run them...
299#ifdef COMPILATION_TESTS
300namespace compilation_tests {
301template <typename T>
302static T declval() {
303 __builtin_unreachable();
304}
305
George Burgess IV9a274102019-06-04 15:39:52 -0700306static void testFormatStrings() {
307 const auto unsigned_value = declval<unsigned long long>();
308 const auto* unknown_string = declval<const char*>();
George Burgess IV06bb4ce2019-06-13 15:13:02 -0700309 const auto va = *declval<va_list*>();
George Burgess IV9a274102019-06-04 15:39:52 -0700310
311 {
312 auto some_fd = declval<int>();
313 // expected-warning@+1{{format specifies type 'int'}}
314 dprintf(some_fd, "%d", unsigned_value);
315 // expected-warning@+1{{format string is not a string literal}}
316 dprintf(some_fd, unknown_string, unsigned_value);
317 // expected-warning@+1{{format string is not a string literal}}
318 vdprintf(1, unknown_string, va);
319 }
320
321 {
322 auto* retval = declval<char*>();
323#if 0
324 // expected-error@+2{{ignoring return value}}
325#endif
326 // expected-warning@+1{{format specifies type 'int'}}
327 asprintf(&retval, "%d", unsigned_value);
328#if 0
329 // expected-error@+2{{ignoring return value}}
330#endif
331 // expected-warning@+1{{format string is not a string literal}}
332 asprintf(&retval, unknown_string, unsigned_value);
333#if 0
334 // expected-error@+2{{ignoring return value}}
335#endif
336 // expected-warning@+1{{format string is not a string literal}}
337 vasprintf(&retval, unknown_string, va);
338 }
339
340 // expected-warning@+1{{format specifies type 'int'}}
341 syslog(0, "%d", unsigned_value);
342 // expected-warning@+1{{format string is not a string literal}}
343 syslog(0, unknown_string, unsigned_value);
344 // expected-warning@+1{{format string is not a string literal}}
345 vsyslog(0, unknown_string, va);
346
347 {
348 auto* file = declval<FILE*>();
349 // expected-warning@+1{{format specifies type 'int'}}
350 fprintf(file, "%d", unsigned_value);
351 // expected-warning@+1{{format string is not a string literal}}
352 fprintf(file, unknown_string, unsigned_value);
353 // expected-warning@+1{{format string is not a string literal}}
354 vfprintf(file, unknown_string, va);
355 }
356
357 // expected-warning@+1{{format specifies type 'int'}}
358 printf("%d", unsigned_value);
359 // expected-warning@+1{{format string is not a string literal}}
360 printf(unknown_string, unsigned_value);
361 // expected-warning@+1{{format string is not a string literal}}
362 vprintf(unknown_string, va);
363
364 {
365 char buf[128];
366 // expected-warning@+1{{format specifies type 'int'}}
367 sprintf(buf, "%d", unsigned_value);
368 // expected-warning@+1{{format string is not a string literal}}
369 sprintf(buf, unknown_string, unsigned_value);
370 // expected-warning@+1{{format string is not a string literal}}
371 sprintf(buf, unknown_string, va);
372
373 // expected-warning@+1{{format specifies type 'int'}}
374 snprintf(buf, sizeof(buf), "%d", unsigned_value);
375 // expected-warning@+1{{format string is not a string literal}}
376 snprintf(buf, sizeof(buf), unknown_string, unsigned_value);
377 // expected-warning@+1{{format string is not a string literal}}
378 vsnprintf(buf, sizeof(buf), unknown_string, va);
379 }
380
381 // FIXME: below are general format string cases where clang should probably try to warn.
382 {
383 char buf[4];
384 sprintf(buf, "%s", "1234");
385 sprintf(buf, "1%s4", "23");
386 sprintf(buf, "%d", 1234);
387
388 // Similar thoughts for strncpy, etc.
389 }
390}
391
392static void testStdlib() {
393 char path_buffer[PATH_MAX - 1];
George Burgess IV8c0ec112019-06-06 17:23:32 -0700394 // expected-warning@+2{{ignoring return value of function}}
George Burgess IV9a274102019-06-04 15:39:52 -0700395 // expected-error@+1{{must be NULL or a pointer to a buffer with >= PATH_MAX bytes}}
396 realpath("/", path_buffer);
George Burgess IV8c0ec112019-06-06 17:23:32 -0700397 // expected-warning@+1{{ignoring return value of function}}
George Burgess IV9a274102019-06-04 15:39:52 -0700398 realpath("/", nullptr);
399
George Burgess IV8c0ec112019-06-06 17:23:32 -0700400 // expected-warning@+2{{ignoring return value of function}}
401 // expected-error@+1{{flipped arguments?}}
George Burgess IV9a274102019-06-04 15:39:52 -0700402 realpath(nullptr, path_buffer);
403
George Burgess IV8c0ec112019-06-06 17:23:32 -0700404 // expected-warning@+2{{ignoring return value of function}}
George Burgess IV9a274102019-06-04 15:39:52 -0700405 // expected-error@+1{{flipped arguments?}}
406 realpath(nullptr, nullptr);
407}
408} // namespace compilation_tests
409#endif
410
411FORTIFY_TEST(poll) {
412 int pipe_fds[2];
413 if (pipe(pipe_fds)) err(1, "pipe failed");
414
415 // after this, pipe_fds[0] should always report RDHUP
416 if (close(pipe_fds[1])) err(1, "close failed");
417
418 struct pollfd poll_fd = { pipe_fds[0], POLLRDHUP, 0 };
419 {
420 struct pollfd few_fds[] = { poll_fd, poll_fd };
421 // expected-error@+1{{fd_count is larger than the given buffer}}
422 EXPECT_FORTIFY_DEATH(poll(few_fds, 3, 0));
423 // expected-error@+1{{fd_count is larger than the given buffer}}
424 EXPECT_FORTIFY_DEATH(ppoll(few_fds, 3, 0, 0));
425 // expected-error@+1{{fd_count is larger than the given buffer}}
426 EXPECT_FORTIFY_DEATH(ppoll64(few_fds, 3, 0, nullptr));
427 }
428
429 {
430 struct {
431 struct pollfd few[2];
432 struct pollfd extra[1];
433 } fds = { { poll_fd, poll_fd }, { poll_fd } };
434 static_assert(sizeof(fds) >= sizeof(struct pollfd) * 3, "");
435
436#if _FORTIFY_SOURCE > 1
437 // expected-error@+2{{fd_count is larger than the given buffer}}
438#endif
439 EXPECT_FORTIFY_DEATH_STRUCT(poll(fds.few, 3, 0));
440
441 struct timespec timeout = {};
442#if _FORTIFY_SOURCE > 1
443 // expected-error@+2{{fd_count is larger than the given buffer}}
444#endif
445 EXPECT_FORTIFY_DEATH_STRUCT(ppoll(fds.few, 3, &timeout, 0));
446
447#if _FORTIFY_SOURCE > 1
448 // expected-error@+2{{fd_count is larger than the given buffer}}
449#endif
450 EXPECT_FORTIFY_DEATH_STRUCT(ppoll64(fds.few, 3, 0, nullptr));
451 }
452}
453
454FORTIFY_TEST(socket) {
455 {
456 char small_buffer[8];
457 // expected-error@+1{{size bigger than buffer}}
458 EXPECT_FORTIFY_DEATH(recv(kBogusFD, small_buffer, sizeof(small_buffer) + 1, 0));
459 // expected-error@+1{{size bigger than buffer}}
460 EXPECT_FORTIFY_DEATH(recvfrom(kBogusFD, small_buffer, sizeof(small_buffer) + 1, 0, 0, 0));
461
462 // expected-error@+1{{size bigger than buffer}}
463 EXPECT_FORTIFY_DEATH(send(kBogusFD, small_buffer, sizeof(small_buffer) + 1, 0));
464 // expected-error@+1{{size bigger than buffer}}
465 EXPECT_FORTIFY_DEATH(sendto(kBogusFD, small_buffer, sizeof(small_buffer) + 1, 0, 0, 0));
466 }
467
468 {
469 struct {
470 char tiny_buffer[4];
471 char tiny_buffer2;
472 } split = {};
473
474 EXPECT_NO_DEATH(recv(kBogusFD, split.tiny_buffer, sizeof(split), 0));
475 EXPECT_NO_DEATH(recvfrom(kBogusFD, split.tiny_buffer, sizeof(split), 0, 0, 0));
476 }
477}
478
479FORTIFY_TEST(sys_stat) {
480 // expected-error@+1{{'umask' called with invalid mode}}
481 EXPECT_FORTIFY_DEATH(umask(01777));
482}
483
484FORTIFY_TEST(stdio) {
485 char small_buffer[8] = {};
486 {
487#if 0
488 // expected-error@+1{{may overflow the destination buffer}}
489#endif
490 EXPECT_FORTIFY_DEATH(snprintf(small_buffer, sizeof(small_buffer) + 1, ""));
491
492 va_list va;
493#if 0
494 // expected-error@+1{{may overflow the destination buffer}}
495#endif
496 // expected-warning@+1{{format string is empty}}
497 EXPECT_FORTIFY_DEATH(vsnprintf(small_buffer, sizeof(small_buffer) + 1, "", va));
498 }
499
500 // expected-error@+1{{size should not be negative}}
501 EXPECT_FORTIFY_DEATH(fgets(small_buffer, -1, stdin));
502 // expected-error@+1{{size is larger than the destination buffer}}
503 EXPECT_FORTIFY_DEATH(fgets(small_buffer, sizeof(small_buffer) + 1, stdin));
504
505 // expected-error@+1{{size * count overflows}}
506 EXPECT_NO_DEATH(fread(small_buffer, 2, (size_t)-1, stdin));
507 // expected-error@+1{{size * count is too large for the given buffer}}
508 EXPECT_FORTIFY_DEATH(fread(small_buffer, 1, sizeof(small_buffer) + 1, stdin));
509
510 // expected-error@+1{{size * count overflows}}
511 EXPECT_NO_DEATH(fwrite(small_buffer, 2, (size_t)-1, stdout));
512 // expected-error@+1{{size * count is too large for the given buffer}}
513 EXPECT_FORTIFY_DEATH(fwrite(small_buffer, 1, sizeof(small_buffer) + 1, stdout));
514}
515
516FORTIFY_TEST(unistd) {
517 char small_buffer[8];
518
519 // Return value warnings are (sort of) a part of FORTIFY, so we don't ignore them.
520#if 0
521 // expected-error@+2{{ignoring return value of function}}
522#endif
523 // expected-error@+1{{bytes overflows the given object}}
524 EXPECT_FORTIFY_DEATH(read(kBogusFD, small_buffer, sizeof(small_buffer) + 1));
525#if 0
526 // expected-error@+2{{ignoring return value of function}}
527#endif
528 // expected-error@+1{{bytes overflows the given object}}
529 EXPECT_FORTIFY_DEATH(pread(kBogusFD, small_buffer, sizeof(small_buffer) + 1, 0));
530#if 0
531 // expected-error@+2{{ignoring return value of function}}
532#endif
533 // expected-error@+1{{bytes overflows the given object}}
534 EXPECT_FORTIFY_DEATH(pread64(kBogusFD, small_buffer, sizeof(small_buffer) + 1, 0));
535#if 0
536 // expected-error@+2{{ignoring return value of function}}
537#endif
538 // expected-error@+1{{bytes overflows the given object}}
539 EXPECT_FORTIFY_DEATH(write(kBogusFD, small_buffer, sizeof(small_buffer) + 1));
540#if 0
541 // expected-error@+2{{ignoring return value of function}}
542#endif
543 // expected-error@+1{{bytes overflows the given object}}
544 EXPECT_FORTIFY_DEATH(pwrite(kBogusFD, small_buffer, sizeof(small_buffer) + 1, 0));
545#if 0
546 // expected-error@+2{{ignoring return value of function}}
547#endif
548 // expected-error@+1{{bytes overflows the given object}}
549 EXPECT_FORTIFY_DEATH(pwrite64(kBogusFD, small_buffer, sizeof(small_buffer) + 1, 0));
550#if 0
551 // expected-error@+2{{ignoring return value of function}}
552#endif
553 // expected-error@+1{{bytes overflows the given object}}
554 EXPECT_FORTIFY_DEATH(readlink("/", small_buffer, sizeof(small_buffer) + 1));
555#if 0
556 // expected-error@+2{{ignoring return value of function}}
557#endif
558 // expected-error@+1{{bytes overflows the given object}}
559 EXPECT_FORTIFY_DEATH(getcwd(small_buffer, sizeof(small_buffer) + 1));
560
561 // getcwd allocates and returns a buffer if you pass null to getcwd
562 EXPECT_NO_DEATH(getcwd(nullptr, 0));
563 EXPECT_NO_DEATH(getcwd(nullptr, 4096));
564
565 struct {
566 char tiny_buffer[4];
567 char tiny_buffer2[4];
568 } split;
569
570 EXPECT_NO_DEATH(read(kBogusFD, split.tiny_buffer, sizeof(split)));
571 EXPECT_NO_DEATH(pread(kBogusFD, split.tiny_buffer, sizeof(split), 0));
572 EXPECT_NO_DEATH(pread64(kBogusFD, split.tiny_buffer, sizeof(split), 0));
573 EXPECT_NO_DEATH(write(kBogusFD, split.tiny_buffer, sizeof(split)));
574 EXPECT_NO_DEATH(pwrite(kBogusFD, split.tiny_buffer, sizeof(split), 0));
575 EXPECT_NO_DEATH(pwrite64(kBogusFD, split.tiny_buffer, sizeof(split), 0));
576
577#if _FORTIFY_SOURCE > 1
578 // expected-error@+2{{bytes overflows the given object}}
579#endif
580 EXPECT_FORTIFY_DEATH_STRUCT(readlink("/", split.tiny_buffer, sizeof(split)));
581#if _FORTIFY_SOURCE > 1
582 // expected-error@+2{{bytes overflows the given object}}
583#endif
584 EXPECT_FORTIFY_DEATH_STRUCT(getcwd(split.tiny_buffer, sizeof(split)));
585
586 {
587 // FIXME: These should all die in FORTIFY. Headers are bugged.
588#ifdef COMPILATION_TESTS
589 char* volatile unknown = small_buffer;
590 const size_t count = static_cast<size_t>(SSIZE_MAX) + 1;
591 // expected-error@+1{{'count' must be <= SSIZE_MAX}}
592 EXPECT_FORTIFY_DEATH(read(kBogusFD, unknown, count));
593 // expected-error@+1{{'count' must be <= SSIZE_MAX}}
594 EXPECT_FORTIFY_DEATH(pread(kBogusFD, unknown, count, 0));
595 // expected-error@+1{{'count' must be <= SSIZE_MAX}}
596 EXPECT_FORTIFY_DEATH(pread64(kBogusFD, unknown, count, 0));
597 // expected-error@+1{{'count' must be <= SSIZE_MAX}}
598 EXPECT_FORTIFY_DEATH(write(kBogusFD, unknown, count));
599 // expected-error@+1{{'count' must be <= SSIZE_MAX}}
600 EXPECT_FORTIFY_DEATH(pwrite(kBogusFD, unknown, count, 0));
601 // expected-error@+1{{'count' must be <= SSIZE_MAX}}
602 EXPECT_FORTIFY_DEATH(pwrite64(kBogusFD, unknown, count, 0));
603#endif
604 }
605}
606
607#endif // defined(__BIONIC__)