• Home
  • Line#
  • Scopes#
  • Navigate#
  • Raw
  • Download
1 /*
2  * Copyright 2024 Valve Corporation
3  * Copyright 2022 Collabora Ltd
4  * SPDX-License-Identifier: MIT
5  */
6 
7 #include "util/macros.h"
8 #include <stdbool.h>
9 
10 #ifndef U_TRISTATE_H
11 #define U_TRISTATE_H
12 
13 /*
14  * Simple tri-state data structure.
15  *
16  * The tri-state can be set to a boolean or unset. The semantics of "unset"
17  * depend on the application, it could be either "don't care" or "maybe".
18  */
19 enum u_tristate {
20    U_TRISTATE_UNSET,
21    U_TRISTATE_NO,
22    U_TRISTATE_YES,
23 };
24 
25 /*
26  * Construct a tristate from an immediate value.
27  */
28 static inline enum u_tristate
u_tristate_make(bool value)29 u_tristate_make(bool value)
30 {
31    return value ? U_TRISTATE_YES : U_TRISTATE_NO;
32 }
33 
34 /*
35  * Try to set a tristate value to a specific boolean value, returning whether
36  * the operation is successful.
37  */
38 static inline bool
u_tristate_set(enum u_tristate * state,bool value)39 u_tristate_set(enum u_tristate *state, bool value)
40 {
41    switch (*state) {
42    case U_TRISTATE_UNSET:
43       *state = u_tristate_make(value);
44       return true;
45 
46    case U_TRISTATE_NO:
47       return (value == false);
48 
49    case U_TRISTATE_YES:
50       return (value == true);
51 
52    default:
53       unreachable("Invalid tristate value");
54    }
55 }
56 
57 /*
58  * Invert a tristate, returning the new value.
59  */
60 static inline enum u_tristate
u_tristate_invert(enum u_tristate tri)61 u_tristate_invert(enum u_tristate tri)
62 {
63    switch (tri) {
64    case U_TRISTATE_UNSET: return U_TRISTATE_UNSET;
65    case U_TRISTATE_YES: return U_TRISTATE_NO;
66    case U_TRISTATE_NO: return U_TRISTATE_YES;
67    }
68 
69    unreachable("invalid tristate");
70 }
71 
72 #endif
73