annotate DEPENDENCIES/generic/include/boost/wave/cpplexer/detect_include_guards.hpp @ 133:4acb5d8d80b6 tip

Don't fail environmental check if README.md exists (but .txt and no-suffix don't)
author Chris Cannam
date Tue, 30 Jul 2019 12:25:44 +0100
parents 2665513ce2d3
children
rev   line source
Chris@16 1 /*=============================================================================
Chris@16 2 Boost.Wave: A Standard compliant C++ preprocessor library
Chris@16 3
Chris@16 4 http://www.boost.org/
Chris@16 5
Chris@16 6 State machine detecting include guards in an included file.
Chris@16 7 This detects two forms of include guards:
Chris@16 8
Chris@16 9 #ifndef INCLUDE_GUARD_MACRO
Chris@16 10 #define INCLUDE_GUARD_MACRO
Chris@16 11 ...
Chris@16 12 #endif
Chris@16 13
Chris@16 14 or
Chris@16 15
Chris@16 16 if !defined(INCLUDE_GUARD_MACRO)
Chris@16 17 #define INCLUDE_GUARD_MACRO
Chris@16 18 ...
Chris@16 19 #endif
Chris@16 20
Chris@16 21 note, that the parenthesis are optional (i.e. !defined INCLUDE_GUARD_MACRO
Chris@16 22 will work as well). The code allows for any whitespace, newline and single
Chris@16 23 '#' tokens before the #if/#ifndef and after the final #endif.
Chris@16 24
Chris@16 25 Copyright (c) 2001-2012 Hartmut Kaiser. Distributed under the Boost
Chris@16 26 Software License, Version 1.0. (See accompanying file
Chris@16 27 LICENSE_1_0.txt or copy at http://www.boost.org/LICENSE_1_0.txt)
Chris@16 28 =============================================================================*/
Chris@16 29 #if !defined(DETECT_INCLUDE_GUARDS_HK060304_INCLUDED)
Chris@16 30 #define DETECT_INCLUDE_GUARDS_HK060304_INCLUDED
Chris@16 31
Chris@16 32 #include <boost/wave/wave_config.hpp>
Chris@16 33 #include <boost/wave/token_ids.hpp>
Chris@16 34
Chris@16 35 // this must occur after all of the includes and before any code appears
Chris@16 36 #ifdef BOOST_HAS_ABI_HEADERS
Chris@16 37 #include BOOST_ABI_PREFIX
Chris@16 38 #endif
Chris@16 39
Chris@16 40 ///////////////////////////////////////////////////////////////////////////////
Chris@16 41 namespace boost {
Chris@16 42 namespace wave {
Chris@16 43 namespace cpplexer {
Chris@16 44
Chris@16 45 template <typename Token>
Chris@16 46 class include_guards
Chris@16 47 {
Chris@16 48 public:
Chris@16 49 include_guards()
Chris@16 50 : state(&include_guards::state_0), detected_guards(false),
Chris@16 51 current_state(true), if_depth(0)
Chris@16 52 {}
Chris@16 53
Chris@16 54 Token& detect_guard(Token& t)
Chris@16 55 { return current_state ? (this->*state)(t) : t; }
Chris@16 56 bool detected(std::string& guard_name_) const
Chris@16 57 {
Chris@16 58 if (detected_guards) {
Chris@16 59 guard_name_ = guard_name.c_str();
Chris@16 60 return true;
Chris@16 61 }
Chris@16 62 return false;
Chris@16 63 }
Chris@16 64
Chris@16 65 private:
Chris@16 66 typedef Token& state_type(Token& t);
Chris@16 67 state_type include_guards::* state;
Chris@16 68
Chris@16 69 bool detected_guards;
Chris@16 70 bool current_state;
Chris@16 71 typename Token::string_type guard_name;
Chris@16 72 int if_depth;
Chris@16 73
Chris@16 74 state_type state_0, state_1, state_2, state_3, state_4, state_5;
Chris@16 75 state_type state_1a, state_1b, state_1c, state_1d, state_1e;
Chris@16 76
Chris@16 77 bool is_skippable(token_id id) const
Chris@16 78 {
Chris@16 79 return (T_POUND == BASE_TOKEN(id) ||
Chris@16 80 IS_CATEGORY(id, WhiteSpaceTokenType) ||
Chris@16 81 IS_CATEGORY(id, EOLTokenType));
Chris@16 82 }
Chris@16 83 };
Chris@16 84
Chris@16 85 ///////////////////////////////////////////////////////////////////////////////
Chris@16 86 // state 0: beginning of a file, tries to recognize #ifndef or #if tokens
Chris@16 87 template <typename Token>
Chris@16 88 inline Token&
Chris@16 89 include_guards<Token>::state_0(Token& t)
Chris@16 90 {
Chris@16 91 token_id id = token_id(t);
Chris@16 92 if (T_PP_IFNDEF == id)
Chris@16 93 state = &include_guards::state_1;
Chris@16 94 else if (T_PP_IF == id)
Chris@16 95 state = &include_guards::state_1a;
Chris@16 96 else if (!is_skippable(id))
Chris@16 97 current_state = false;
Chris@16 98 return t;
Chris@16 99 }
Chris@16 100
Chris@16 101 ///////////////////////////////////////////////////////////////////////////////
Chris@16 102 // state 1: found #ifndef, looking for T_IDENTIFIER
Chris@16 103 template <typename Token>
Chris@16 104 inline Token&
Chris@16 105 include_guards<Token>::state_1(Token& t)
Chris@16 106 {
Chris@16 107 token_id id = token_id(t);
Chris@16 108 if (T_IDENTIFIER == id) {
Chris@16 109 guard_name = t.get_value();
Chris@16 110 state = &include_guards::state_2;
Chris@16 111 }
Chris@16 112 else if (!is_skippable(id))
Chris@16 113 current_state = false;
Chris@16 114 return t;
Chris@16 115 }
Chris@16 116
Chris@16 117 ///////////////////////////////////////////////////////////////////////////////
Chris@16 118 // state 1a: found T_PP_IF, looking for T_NOT ("!")
Chris@16 119 template <typename Token>
Chris@16 120 inline Token&
Chris@16 121 include_guards<Token>::state_1a(Token& t)
Chris@16 122 {
Chris@16 123 token_id id = token_id(t);
Chris@16 124 if (T_NOT == BASE_TOKEN(id))
Chris@16 125 state = &include_guards::state_1b;
Chris@16 126 else if (!is_skippable(id))
Chris@16 127 current_state = false;
Chris@16 128 return t;
Chris@16 129 }
Chris@16 130
Chris@16 131 ///////////////////////////////////////////////////////////////////////////////
Chris@16 132 // state 1b: found T_NOT, looking for 'defined'
Chris@16 133 template <typename Token>
Chris@16 134 inline Token&
Chris@16 135 include_guards<Token>::state_1b(Token& t)
Chris@16 136 {
Chris@16 137 token_id id = token_id(t);
Chris@16 138 if (T_IDENTIFIER == id && t.get_value() == "defined")
Chris@16 139 state = &include_guards::state_1c;
Chris@16 140 else if (!is_skippable(id))
Chris@16 141 current_state = false;
Chris@16 142 return t;
Chris@16 143 }
Chris@16 144
Chris@16 145 ///////////////////////////////////////////////////////////////////////////////
Chris@16 146 // state 1c: found 'defined', looking for (optional) T_LEFTPAREN
Chris@16 147 template <typename Token>
Chris@16 148 inline Token&
Chris@16 149 include_guards<Token>::state_1c(Token& t)
Chris@16 150 {
Chris@16 151 token_id id = token_id(t);
Chris@16 152 if (T_LEFTPAREN == id)
Chris@16 153 state = &include_guards::state_1d;
Chris@16 154 else if (T_IDENTIFIER == id) {
Chris@16 155 guard_name = t.get_value();
Chris@16 156 state = &include_guards::state_2;
Chris@16 157 }
Chris@16 158 else if (!is_skippable(id))
Chris@16 159 current_state = false;
Chris@16 160 return t;
Chris@16 161 }
Chris@16 162
Chris@16 163 ///////////////////////////////////////////////////////////////////////////////
Chris@16 164 // state 1d: found T_LEFTPAREN, looking for T_IDENTIFIER guard
Chris@16 165 template <typename Token>
Chris@16 166 inline Token&
Chris@16 167 include_guards<Token>::state_1d(Token& t)
Chris@16 168 {
Chris@16 169 token_id id = token_id(t);
Chris@16 170 if (T_IDENTIFIER == id) {
Chris@16 171 guard_name = t.get_value();
Chris@16 172 state = &include_guards::state_1e;
Chris@16 173 }
Chris@16 174 else if (!is_skippable(id))
Chris@16 175 current_state = false;
Chris@16 176 return t;
Chris@16 177 }
Chris@16 178
Chris@16 179 ///////////////////////////////////////////////////////////////////////////////
Chris@16 180 // state 1e: found T_IDENTIFIER guard, looking for T_RIGHTPAREN
Chris@16 181 template <typename Token>
Chris@16 182 inline Token&
Chris@16 183 include_guards<Token>::state_1e(Token& t)
Chris@16 184 {
Chris@16 185 token_id id = token_id(t);
Chris@16 186 if (T_RIGHTPAREN == id)
Chris@16 187 state = &include_guards::state_2;
Chris@16 188 else if (!is_skippable(id))
Chris@16 189 current_state = false;
Chris@16 190 return t;
Chris@16 191 }
Chris@16 192
Chris@16 193 ///////////////////////////////////////////////////////////////////////////////
Chris@16 194 // state 2: found T_IDENTIFIER, looking for #define
Chris@16 195 template <typename Token>
Chris@16 196 inline Token&
Chris@16 197 include_guards<Token>::state_2(Token& t)
Chris@16 198 {
Chris@16 199 token_id id = token_id(t);
Chris@16 200 if (T_PP_DEFINE == id)
Chris@16 201 state = &include_guards::state_3;
Chris@16 202 else if (!is_skippable(id))
Chris@16 203 current_state = false;
Chris@16 204 return t;
Chris@16 205 }
Chris@16 206
Chris@16 207 ///////////////////////////////////////////////////////////////////////////////
Chris@16 208 // state 3: found #define, looking for T_IDENTIFIER as recognized by state 1
Chris@16 209 template <typename Token>
Chris@16 210 inline Token&
Chris@16 211 include_guards<Token>::state_3(Token& t)
Chris@16 212 {
Chris@16 213 token_id id = token_id(t);
Chris@16 214 if (T_IDENTIFIER == id && t.get_value() == guard_name)
Chris@16 215 state = &include_guards::state_4;
Chris@16 216 else if (!is_skippable(id))
Chris@16 217 current_state = false;
Chris@16 218 return t;
Chris@16 219 }
Chris@16 220
Chris@16 221 ///////////////////////////////////////////////////////////////////////////////
Chris@16 222 // state 4: found guard T_IDENTIFIER, looking for #endif
Chris@16 223 template <typename Token>
Chris@16 224 inline Token&
Chris@16 225 include_guards<Token>::state_4(Token& t)
Chris@16 226 {
Chris@16 227 token_id id = token_id(t);
Chris@16 228 if (T_PP_IF == id || T_PP_IFDEF == id || T_PP_IFNDEF == id)
Chris@16 229 ++if_depth;
Chris@16 230 else if (T_PP_ENDIF == id) {
Chris@16 231 if (if_depth > 0)
Chris@16 232 --if_depth;
Chris@16 233 else
Chris@16 234 state = &include_guards::state_5;
Chris@16 235 }
Chris@16 236 return t;
Chris@16 237 }
Chris@16 238
Chris@16 239 ///////////////////////////////////////////////////////////////////////////////
Chris@16 240 // state 5: found final #endif, looking for T_EOF
Chris@16 241 template <typename Token>
Chris@16 242 inline Token&
Chris@16 243 include_guards<Token>::state_5(Token& t)
Chris@16 244 {
Chris@16 245 token_id id = token_id(t);
Chris@16 246 if (T_EOF == id)
Chris@16 247 detected_guards = current_state;
Chris@16 248 else if (!is_skippable(id))
Chris@16 249 current_state = false;
Chris@16 250 return t;
Chris@16 251 }
Chris@16 252
Chris@16 253 ///////////////////////////////////////////////////////////////////////////////
Chris@16 254 } // namespace cpplexer
Chris@16 255 } // namespace wave
Chris@16 256 } // namespace boost
Chris@16 257
Chris@16 258 // the suffix header occurs after all of the code
Chris@16 259 #ifdef BOOST_HAS_ABI_HEADERS
Chris@16 260 #include BOOST_ABI_SUFFIX
Chris@16 261 #endif
Chris@16 262
Chris@16 263 #endif // !DETECT_INCLUDE_GUARDS_HK060304_INCLUDED