From d2fe0d263d9733c0561404b458491e1ccd601cf2 Mon Sep 17 00:00:00 2001 From: peter klausler Date: Tue, 30 Jan 2018 11:50:05 -0800 Subject: [PATCH] [flang] Add char-parsers.h. Original-commit: flang-compiler/f18@0f72c5cb400a9ff8acc1aa35433b03757700db7d --- flang/char-parsers.h | 114 +++++++++++++++++++++++++++++++++++++++++++ 1 file changed, 114 insertions(+) create mode 100644 flang/char-parsers.h diff --git a/flang/char-parsers.h b/flang/char-parsers.h new file mode 100644 index 000000000000..8a3b58d38780 --- /dev/null +++ b/flang/char-parsers.h @@ -0,0 +1,114 @@ +#ifndef FORTRAN_CHAR_PARSERS_H_ +#define FORTRAN_CHAR_PARSERS_H_ + +// Defines simple character-level parsers for use by the tokenizing +// parsers in cooked-chars.h. + +#include "basic-parsers.h" +#include "parse-state.h" +#include + +namespace Fortran { + +template +struct ExactRaw { + using resultType = char; + constexpr ExactRaw() {} + constexpr ExactRaw(const ExactRaw &) {} + static std::optional Parse(ParseState *state) { + if (std::optional ch{state->GetNextRawChar()}) { + if (*ch == goal) { + state->Advance(); + return ch; + } + } + return {}; + } +}; + +template +struct ExactRawRange { + using resultType = char; + constexpr ExactRawRange() {} + constexpr ExactRawRange(const ExactRawRange &) {}; + static std::optional Parse(ParseState *state) { + if (std::optional ch{state->GetNextRawChar()}) { + if (*ch >= a && *ch <= z) { + state->Advance(); + return ch; + } + } + return {}; + } +}; + +template +struct AnyCharExcept { + using resultType = char; + constexpr AnyCharExcept() {} + constexpr AnyCharExcept(const AnyCharExcept &) {} + static std::optional Parse(ParseState *state) { + if (std::optional ch{state->GetNextRawChar()}) { + if (*ch != unwanted) { + state->Advance(); + return ch; + } + } + return {}; + } +}; + +template +struct SkipPast { + using resultType = Success; + constexpr SkipPast() {} + constexpr SkipPast(const SkipPast &) {} + static std::optional Parse(ParseState *state) { + while (std::optional ch{state->GetNextRawChar()}) { + state->Advance(); + if (*ch == goal) { + return {Success{}}; + } + } + return {}; + } +}; + +// Line endings have been previously normalized to simple newlines. +constexpr auto eoln = ExactRaw<'\n'>{}; + +static inline bool InCharLiteral(const ParseState &state) { + return state.inCharLiteral(); +} + +constexpr StatePredicateGuardParser inCharLiteral{InCharLiteral}; + +class RawStringMatch { + public: + using resultType = Success; + constexpr RawStringMatch(const RawStringMatch &) = default; + constexpr RawStringMatch(const char *str, size_t n) : str_{str}, length_{n} {} + std::optional Parse(ParseState *state) const { + const char *p{str_}; + for (size_t j{0}; j < length_ && *p != '\0'; ++j, ++p) { + if (std::optional ch{state->GetNextRawChar()}) { + if (tolower(*ch) != *p) { + return {}; + } + state->Advance(); + } else { + return {}; + } + } + return {Success{}}; + } + private: + const char *const str_; + const size_t length_; +}; + +constexpr RawStringMatch operator""_raw(const char str[], size_t n) { + return RawStringMatch{str, n}; +} +} // namespace Fortran +#endif // FORTRAN_CHAR_PARSERS_H_