1// Set these requirements to ensure that we have an 8-byte binary ID.
2// REQUIRES: linux
3//
4// This will generate a 20-byte build ID, which requires 4-byte padding.
5// RUN: %clang_profgen -Wl,--build-id=sha1 -o %t %s
6// RUN: env LLVM_PROFILE_FILE=%t.profraw %run %t
7// RUN: %run %t %t.profraw
8
9#include <errno.h>
10#include <stdio.h>
11#include <stdint.h>
12#include <stdlib.h>
13#include <string.h>
14#include <sys/mman.h>
15#include <sys/stat.h>
16#include <sys/stat.h>
17#include <fcntl.h>
18#include <unistd.h>
19
20enum ValueKind {
21#define VALUE_PROF_KIND(Enumerator, Value, Descr) Enumerator = Value,
22#include "profile/InstrProfData.inc"
23};
24
25typedef struct __llvm_profile_header {
26#define INSTR_PROF_RAW_HEADER(Type, Name, Initializer) Type Name;
27#include "profile/InstrProfData.inc"
28} __llvm_profile_header;
29
30typedef void *IntPtrT;
31typedef struct __llvm_profile_data {
32#define INSTR_PROF_DATA(Type, LLVMType, Name, Initializer) Type Name;
33#include "profile/InstrProfData.inc"
34} __llvm_profile_data;
35
36void bail(const char* str) {
37 fprintf(stderr, format: "%s %s\n", str, strerror(errno));
38 exit(status: 1);
39}
40
41void func() {}
42
43int main(int argc, char** argv) {
44 if (argc == 2) {
45 int fd = open(file: argv[1], O_RDONLY);
46 if (fd == -1)
47 bail(str: "open");
48
49 struct stat st;
50 if (stat(file: argv[1], buf: &st))
51 bail(str: "stat");
52 uint64_t FileSize = st.st_size;
53
54 char* Buf = (char *)mmap(NULL, len: FileSize, PROT_READ, MAP_SHARED, fd: fd, offset: 0);
55 if (Buf == MAP_FAILED)
56 bail(str: "mmap");
57
58 __llvm_profile_header *Header = (__llvm_profile_header *)Buf;
59 if (Header->BinaryIdsSize != 32)
60 bail(str: "Invalid binary ID size");
61
62 char *BinaryIdsStart = Buf + sizeof(__llvm_profile_header);
63
64 uint64_t BinaryIdSize = *((uint64_t *)BinaryIdsStart);
65 if (BinaryIdSize != 20)
66 bail(str: "Expected a binary ID of size 20");
67
68 // Skip the size and the binary ID itself to check padding.
69 BinaryIdsStart += 8 + 20;
70 if (*((uint32_t *)BinaryIdsStart))
71 bail(str: "Found non-zero binary ID padding");
72
73 if (munmap(addr: Buf, len: FileSize))
74 bail(str: "munmap");
75
76 if (close(fd: fd))
77 bail(str: "close");
78 } else {
79 func();
80 }
81 return 0;
82}
83

source code of compiler-rt/test/profile/Linux/binary-id-padding.c