1//===-- c_api_test.cpp ----------------------------------------------------===//
2//
3// Part of the LLVM Project, under the Apache License v2.0 with LLVM Exceptions.
4// See https://llvm.org/LICENSE.txt for license information.
5// SPDX-License-Identifier: Apache-2.0 WITH LLVM-exception
6//
7//===----------------------------------------------------------------------===//
8//
9// This file is a part of the ORC runtime.
10//
11//===----------------------------------------------------------------------===//
12
13#include "orc_rt/c_api.h"
14#include "gtest/gtest.h"
15
16TEST(CAPITest, WrapperFunctionResultInit) {
17 orc_rt_WrapperFunctionResult R;
18 orc_rt_WrapperFunctionResultInit(&R);
19
20 EXPECT_EQ(R.Size, 0U);
21 EXPECT_EQ(R.Data.ValuePtr, nullptr);
22
23 // Check that this value isn't treated as an out-of-band error.
24 EXPECT_EQ(orc_rt_WrapperFunctionResultGetOutOfBandError(&R), nullptr);
25
26 // Check that we can dispose of the value.
27 orc_rt_DisposeWrapperFunctionResult(&R);
28}
29
30TEST(CAPITest, WrapperFunctionResultAllocSmall) {
31 constexpr size_t SmallAllocSize = sizeof(const char *);
32
33 auto R = orc_rt_WrapperFunctionResultAllocate(Size: SmallAllocSize);
34 char *DataPtr = orc_rt_WrapperFunctionResultData(R: &R);
35
36 for (size_t I = 0; I != SmallAllocSize; ++I)
37 DataPtr[I] = 0x55 + I;
38
39 // Check that the inline storage in R.Data.Value contains the expected
40 // sequence.
41 EXPECT_EQ(R.Size, SmallAllocSize);
42 for (size_t I = 0; I != SmallAllocSize; ++I)
43 EXPECT_EQ(R.Data.Value[I], (char)(0x55 + I))
44 << "Unexpected value at index " << I;
45
46 // Check that this value isn't treated as an out-of-band error.
47 EXPECT_EQ(orc_rt_WrapperFunctionResultGetOutOfBandError(R: &R), nullptr);
48
49 // Check that orc_rt_WrapperFunctionResult(Data|Result|Size) and
50 // orc_rt_WrapperFunctionResultGetOutOfBandError behave as expected.
51 EXPECT_EQ(orc_rt_WrapperFunctionResultData(R: &R), R.Data.Value);
52 EXPECT_EQ(orc_rt_WrapperFunctionResultSize(R: &R), SmallAllocSize);
53 EXPECT_FALSE(orc_rt_WrapperFunctionResultEmpty(R: &R));
54 EXPECT_EQ(orc_rt_WrapperFunctionResultGetOutOfBandError(R: &R), nullptr);
55
56 // Check that we can dispose of the value.
57 orc_rt_DisposeWrapperFunctionResult(R: &R);
58}
59
60TEST(CAPITest, WrapperFunctionResultAllocLarge) {
61 constexpr size_t LargeAllocSize = sizeof(const char *) + 1;
62
63 auto R = orc_rt_WrapperFunctionResultAllocate(LargeAllocSize);
64 char *DataPtr = orc_rt_WrapperFunctionResultData(&R);
65
66 for (size_t I = 0; I != LargeAllocSize; ++I)
67 DataPtr[I] = 0x55 + I;
68
69 // Check that the inline storage in R.Data.Value contains the expected
70 // sequence.
71 EXPECT_EQ(R.Size, LargeAllocSize);
72 EXPECT_EQ(R.Data.ValuePtr, DataPtr);
73 for (size_t I = 0; I != LargeAllocSize; ++I)
74 EXPECT_EQ(R.Data.ValuePtr[I], (char)(0x55 + I))
75 << "Unexpected value at index " << I;
76
77 // Check that this value isn't treated as an out-of-band error.
78 EXPECT_EQ(orc_rt_WrapperFunctionResultGetOutOfBandError(&R), nullptr);
79
80 // Check that orc_rt_WrapperFunctionResult(Data|Result|Size) and
81 // orc_rt_WrapperFunctionResultGetOutOfBandError behave as expected.
82 EXPECT_EQ(orc_rt_WrapperFunctionResultData(&R), R.Data.ValuePtr);
83 EXPECT_EQ(orc_rt_WrapperFunctionResultSize(&R), LargeAllocSize);
84 EXPECT_FALSE(orc_rt_WrapperFunctionResultEmpty(&R));
85 EXPECT_EQ(orc_rt_WrapperFunctionResultGetOutOfBandError(&R), nullptr);
86
87 // Check that we can dispose of the value.
88 orc_rt_DisposeWrapperFunctionResult(&R);
89}
90
91TEST(CAPITest, WrapperFunctionResultFromRangeSmall) {
92 constexpr size_t SmallAllocSize = sizeof(const char *);
93
94 char Source[SmallAllocSize];
95 for (size_t I = 0; I != SmallAllocSize; ++I)
96 Source[I] = 0x55 + I;
97
98 orc_rt_WrapperFunctionResult R =
99 orc_rt_CreateWrapperFunctionResultFromRange(Data: Source, Size: SmallAllocSize);
100
101 // Check that the inline storage in R.Data.Value contains the expected
102 // sequence.
103 EXPECT_EQ(R.Size, SmallAllocSize);
104 for (size_t I = 0; I != SmallAllocSize; ++I)
105 EXPECT_EQ(R.Data.Value[I], (char)(0x55 + I))
106 << "Unexpected value at index " << I;
107
108 // Check that we can dispose of the value.
109 orc_rt_DisposeWrapperFunctionResult(R: &R);
110}
111
112TEST(CAPITest, WrapperFunctionResultFromRangeLarge) {
113 constexpr size_t LargeAllocSize = sizeof(const char *) + 1;
114
115 char Source[LargeAllocSize];
116 for (size_t I = 0; I != LargeAllocSize; ++I)
117 Source[I] = 0x55 + I;
118
119 orc_rt_WrapperFunctionResult R =
120 orc_rt_CreateWrapperFunctionResultFromRange(Data: Source, Size: LargeAllocSize);
121
122 // Check that the inline storage in R.Data.Value contains the expected
123 // sequence.
124 EXPECT_EQ(R.Size, LargeAllocSize);
125 for (size_t I = 0; I != LargeAllocSize; ++I)
126 EXPECT_EQ(R.Data.ValuePtr[I], (char)(0x55 + I))
127 << "Unexpected value at index " << I;
128
129 // Check that we can dispose of the value.
130 orc_rt_DisposeWrapperFunctionResult(R: &R);
131}
132
133TEST(CAPITest, WrapperFunctionResultFromStringSmall) {
134 constexpr size_t SmallAllocSize = sizeof(const char *);
135
136 char Source[SmallAllocSize];
137 for (size_t I = 0; I != SmallAllocSize - 1; ++I)
138 Source[I] = 'a' + I;
139 Source[SmallAllocSize - 1] = '\0';
140
141 orc_rt_WrapperFunctionResult R =
142 orc_rt_CreateWrapperFunctionResultFromString(Source);
143
144 // Check that the inline storage in R.Data.Value contains the expected
145 // sequence.
146 EXPECT_EQ(R.Size, SmallAllocSize);
147 for (size_t I = 0; I != SmallAllocSize - 1; ++I)
148 EXPECT_EQ(R.Data.Value[I], (char)('a' + I))
149 << "Unexpected value at index " << I;
150 EXPECT_EQ(R.Data.Value[SmallAllocSize - 1], '\0')
151 << "Unexpected value at index " << (SmallAllocSize - 1);
152
153 // Check that we can dispose of the value.
154 orc_rt_DisposeWrapperFunctionResult(R: &R);
155}
156
157TEST(CAPITest, WrapperFunctionResultFromStringLarge) {
158 constexpr size_t LargeAllocSize = sizeof(const char *) + 1;
159
160 char Source[LargeAllocSize];
161 for (size_t I = 0; I != LargeAllocSize - 1; ++I)
162 Source[I] = 'a' + I;
163 Source[LargeAllocSize - 1] = '\0';
164
165 orc_rt_WrapperFunctionResult R =
166 orc_rt_CreateWrapperFunctionResultFromString(Source);
167
168 // Check that the inline storage in R.Data.Value contains the expected
169 // sequence.
170 EXPECT_EQ(R.Size, LargeAllocSize);
171 for (size_t I = 0; I != LargeAllocSize - 1; ++I)
172 EXPECT_EQ(R.Data.ValuePtr[I], (char)('a' + I))
173 << "Unexpected value at index " << I;
174 EXPECT_EQ(R.Data.ValuePtr[LargeAllocSize - 1], '\0')
175 << "Unexpected value at index " << (LargeAllocSize - 1);
176
177 // Check that we can dispose of the value.
178 orc_rt_DisposeWrapperFunctionResult(R: &R);
179}
180
181TEST(CAPITest, WrapperFunctionResultFromOutOfBandError) {
182 constexpr const char *ErrMsg = "test error message";
183 orc_rt_WrapperFunctionResult R =
184 orc_rt_CreateWrapperFunctionResultFromOutOfBandError(ErrMsg);
185
186#ifndef NDEBUG
187 EXPECT_DEATH(
188 { orc_rt_WrapperFunctionResultData(&R); },
189 "Cannot get data for out-of-band error value");
190 EXPECT_DEATH(
191 { orc_rt_WrapperFunctionResultSize(&R); },
192 "Cannot get size for out-of-band error value");
193#endif
194
195 EXPECT_FALSE(orc_rt_WrapperFunctionResultEmpty(&R));
196 const char *OOBErrMsg = orc_rt_WrapperFunctionResultGetOutOfBandError(&R);
197 EXPECT_NE(OOBErrMsg, nullptr);
198 EXPECT_NE(OOBErrMsg, ErrMsg);
199 EXPECT_TRUE(strcmp(OOBErrMsg, ErrMsg) == 0);
200
201 orc_rt_DisposeWrapperFunctionResult(&R);
202}
203

source code of compiler-rt/lib/orc/tests/unit/c_api_test.cpp