Simplify bitfields
| 10257 | |
| 10258 | // Simplify bitfields |
| 10259 | void Tokenizer::simplifyBitfields() |
| 10260 | { |
| 10261 | std::size_t anonymousBitfieldCounter = 0; |
| 10262 | for (Token *tok = list.front(); tok; tok = tok->next()) { |
| 10263 | Token *last = nullptr; |
| 10264 | |
| 10265 | if (Token::simpleMatch(tok, "for (")) |
| 10266 | tok = tok->linkAt(1); |
| 10267 | |
| 10268 | if (!Token::Match(tok, ";|{|}|public:|protected:|private:")) |
| 10269 | continue; |
| 10270 | |
| 10271 | const bool isEnum = tok->str() == "}" && isEnumStart(tok->link()); |
| 10272 | |
| 10273 | const auto tooLargeError = [this](const Token *tok) { |
| 10274 | const auto max = std::numeric_limits<short>::max(); |
| 10275 | reportError(tok, |
| 10276 | Severity::warning, |
| 10277 | "tooLargeBitField", |
| 10278 | "Bit-field size exceeds max number of bits " + std::to_string(max)); |
| 10279 | }; |
| 10280 | |
| 10281 | Token* typeTok = tok->next(); |
| 10282 | while (Token::Match(typeTok, "const|volatile")) |
| 10283 | typeTok = typeTok->next(); |
| 10284 | if (Token::Match(typeTok, ":: %name%")) |
| 10285 | typeTok = typeTok->next(); |
| 10286 | while (Token::Match(typeTok, "%name% :: %name%")) |
| 10287 | typeTok = typeTok->tokAt(2); |
| 10288 | if (Token::Match(typeTok, "%type% %name% :") && |
| 10289 | !Token::Match(tok->next(), "case|public|protected|private|class|struct") && |
| 10290 | !Token::simpleMatch(tok->tokAt(2), "default :")) { |
| 10291 | Token *tok1 = typeTok->next(); |
| 10292 | if (Token::Match(tok1, "%name% : %num% [;=,]")) |
| 10293 | if (!tok1->setBits(MathLib::toBigNumber(tok1->tokAt(2)))) |
| 10294 | tooLargeError(tok1->tokAt(2)); |
| 10295 | if (tok1 && tok1->tokAt(2) && |
| 10296 | (Token::Match(tok1->tokAt(2), "%bool%|%num%") || |
| 10297 | !Token::Match(tok1->tokAt(2), "public|protected|private| %type% ::|<|,|{|;"))) { |
| 10298 | while (tok1->next() && !Token::Match(tok1->next(), "[;,)]{}=]")) { |
| 10299 | if (Token::Match(tok1->next(), "[([]")) |
| 10300 | Token::eraseTokens(tok1, tok1->linkAt(1)); |
| 10301 | tok1->deleteNext(); |
| 10302 | } |
| 10303 | |
| 10304 | last = tok1->next(); |
| 10305 | } |
| 10306 | } else if (isEnum && Token::Match(tok, "} %name%| : %num% ;")) { |
| 10307 | if (tok->strAt(1) == ":") { |
| 10308 | tok->deleteNext(2); |
| 10309 | tok->insertToken("Anonymous"); |
| 10310 | } else { |
| 10311 | tok->next()->deleteNext(2); |
| 10312 | } |
| 10313 | } else if (Token::Match(typeTok, "%type% : %num%|%bool% ;") && |
| 10314 | typeTok->str() != "default") { |
| 10315 | const std::size_t id = anonymousBitfieldCounter++; |
| 10316 | const std::string name = "anonymous@" + std::to_string(id); |
nothing calls this directly
no test coverage detected