1 // Copyright 2024 The Pigweed Authors
2 //
3 // Licensed under the Apache License, Version 2.0 (the "License"); you may not
4 // use this file except in compliance with the License. You may obtain a copy of
5 // the License at
6 //
7 // https://www.apache.org/licenses/LICENSE-2.0
8 //
9 // Unless required by applicable law or agreed to in writing, software
10 // distributed under the License is distributed on an "AS IS" BASIS, WITHOUT
11 // WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied. See the
12 // License for the specific language governing permissions and limitations under
13 // the License.
14
15 #include "pw_thread/attrs.h"
16
17 #include "pw_compilation_testing/negative_compilation.h"
18 #include "pw_thread/thread.h" // for PW_THREAD_GENERIC_CREATION_IS_SUPPORTED
19 #include "pw_unit_test/constexpr.h"
20 #include "pw_unit_test/framework.h"
21
22 namespace {
23
24 PW_CONSTEXPR_TEST(ThreadAttrs, Defaults, {
25 pw::ThreadAttrs attrs;
26 PW_TEST_EXPECT_STREQ(attrs.name(), "");
27 PW_TEST_EXPECT_EQ(attrs.priority(), pw::ThreadPriority::Default());
28 PW_TEST_EXPECT_EQ(attrs.stack_size_bytes(),
29 pw::thread::backend::kDefaultStackSizeBytes);
30 PW_TEST_EXPECT_EQ(attrs.native_stack_pointer(), nullptr);
31 PW_TEST_EXPECT_FALSE(attrs.has_external_stack());
32 });
33
34 PW_CONSTEXPR_TEST(ThreadAttrs, SetAttributes, {
35 pw::ThreadAttrs attrs = pw::ThreadAttrs()
36 .set_name("hello")
37 .set_priority(pw::ThreadPriority::High())
38 .set_stack_size_bytes(123);
39 PW_TEST_EXPECT_STREQ(attrs.name(), "hello");
40 PW_TEST_EXPECT_EQ(attrs.priority(), pw::ThreadPriority::High());
41 PW_TEST_EXPECT_EQ(attrs.stack_size_bytes(), 123u);
42 PW_TEST_EXPECT_EQ(attrs.native_stack_pointer(), nullptr);
43 PW_TEST_EXPECT_FALSE(attrs.has_external_stack());
44 });
45
46 // Declaring a ThreadStack requires generic thread creation.
47 #if PW_THREAD_GENERIC_CREATION_IS_SUPPORTED
48
49 PW_CONSTINIT pw::ThreadStack<0> stack;
50
51 PW_CONSTEXPR_TEST(ThreadAttrs, ExternalStack, {
52 pw::ThreadAttrs attrs = pw::ThreadAttrs().set_stack(stack);
53
54 PW_TEST_EXPECT_TRUE(attrs.has_external_stack());
55 PW_TEST_EXPECT_NE(attrs.native_stack_pointer(), nullptr);
56 });
57
TEST(ThreadAttrs,ExternalStackStackSize)58 TEST(ThreadAttrs, ExternalStackStackSize) {
59 pw::ThreadAttrs attrs = pw::ThreadAttrs().set_stack(stack);
60 EXPECT_EQ(attrs.native_stack_size(), attrs.native_stack().size());
61 }
62
63 #if PW_NC_TEST(CannotSetStackSizeWithExternalStack)
64 PW_NC_EXPECT("PW_ASSERT\(!has_external_stack\(\)\)");
65 [[maybe_unused]] constexpr pw::ThreadAttrs kTestAttrs =
66 pw::ThreadAttrs().set_stack(stack).set_stack_size_bytes(1);
67 #endif // PW_NC_TEST
68
69 #if PW_NC_TEST(CannotAccessNativeStackWithoutStackSet)
70 PW_NC_EXPECT("PW_ASSERT\(has_external_stack\(\)\)");
71 [[maybe_unused]] constexpr auto kTest = pw::ThreadAttrs().native_stack();
72 #endif // PW_NC_TEST
73
74 #endif // PW_THREAD_GENERIC_CREATION_IS_SUPPORTED
75
76 } // namespace
77