1193326Sed//===--- TokenConcatenation.h - Token Concatenation Avoidance ---*- C++ -*-===// 2193326Sed// 3193326Sed// The LLVM Compiler Infrastructure 4193326Sed// 5193326Sed// This file is distributed under the University of Illinois Open Source 6193326Sed// License. See LICENSE.TXT for details. 7193326Sed// 8193326Sed//===----------------------------------------------------------------------===// 9193326Sed// 10193326Sed// This file defines the TokenConcatenation class. 11193326Sed// 12193326Sed//===----------------------------------------------------------------------===// 13193326Sed 14193326Sed#ifndef CLANG_LEX_TOKEN_CONCATENATION_H 15193326Sed#define CLANG_LEX_TOKEN_CONCATENATION_H 16193326Sed 17193326Sed#include "clang/Basic/TokenKinds.h" 18193326Sed 19193326Sednamespace clang { 20193326Sed class Preprocessor; 21193326Sed class Token; 22198092Srdivacky 23193326Sed /// TokenConcatenation class, which answers the question of 24193326Sed /// "Is it safe to emit two tokens without a whitespace between them, or 25193326Sed /// would that cause implicit concatenation of the tokens?" 26193326Sed /// 27193326Sed /// For example, it emitting two identifiers "foo" and "bar" next to each 28193326Sed /// other would cause the lexer to produce one "foobar" token. Emitting "1" 29193326Sed /// and ")" next to each other is safe. 30193326Sed /// 31193326Sed class TokenConcatenation { 32193326Sed Preprocessor &PP; 33198092Srdivacky 34193326Sed enum AvoidConcatInfo { 35193326Sed /// By default, a token never needs to avoid concatenation. Most tokens 36193326Sed /// (e.g. ',', ')', etc) don't cause a problem when concatenated. 37193326Sed aci_never_avoid_concat = 0, 38198092Srdivacky 39193326Sed /// aci_custom_firstchar - AvoidConcat contains custom code to handle this 40193326Sed /// token's requirements, and it needs to know the first character of the 41193326Sed /// token. 42193326Sed aci_custom_firstchar = 1, 43198092Srdivacky 44193326Sed /// aci_custom - AvoidConcat contains custom code to handle this token's 45193326Sed /// requirements, but it doesn't need to know the first character of the 46193326Sed /// token. 47193326Sed aci_custom = 2, 48198092Srdivacky 49193326Sed /// aci_avoid_equal - Many tokens cannot be safely followed by an '=' 50193326Sed /// character. For example, "<<" turns into "<<=" when followed by an =. 51193326Sed aci_avoid_equal = 4 52193326Sed }; 53198092Srdivacky 54193326Sed /// TokenInfo - This array contains information for each token on what 55193326Sed /// action to take when avoiding concatenation of tokens in the AvoidConcat 56193326Sed /// method. 57193326Sed char TokenInfo[tok::NUM_TOKENS]; 58193326Sed public: 59193326Sed TokenConcatenation(Preprocessor &PP); 60198092Srdivacky 61207619Srdivacky bool AvoidConcat(const Token &PrevPrevTok, 62207619Srdivacky const Token &PrevTok, 63207619Srdivacky const Token &Tok) const; 64193326Sed 65193326Sed private: 66226633Sdim /// IsIdentifierStringPrefix - Return true if the spelling of the token 67226633Sdim /// is literally 'L', 'u', 'U', or 'u8'. 68226633Sdim bool IsIdentifierStringPrefix(const Token &Tok) const; 69193326Sed }; 70193326Sed } // end clang namespace 71193326Sed 72193326Sed#endif 73