-
Notifications
You must be signed in to change notification settings - Fork 231
/
Copy pathdynamic_match.cpp
120 lines (99 loc) · 3.03 KB
/
dynamic_match.cpp
1
2
3
4
5
6
7
8
9
10
11
12
13
14
15
16
17
18
19
20
21
22
23
24
25
26
27
28
29
30
31
32
33
34
35
36
37
38
39
40
41
42
43
44
45
46
47
48
49
50
51
52
53
54
55
56
57
58
59
60
61
62
63
64
65
66
67
68
69
70
71
72
73
74
75
76
77
78
79
80
81
82
83
84
85
86
87
88
89
90
91
92
93
94
95
96
97
98
99
100
101
102
103
104
105
106
107
108
109
110
111
112
113
114
115
116
117
118
119
120
// Copyright (c) 2014-2023 Dr. Colin Hirsch and Daniel Frey
// Distributed under the Boost Software License, Version 1.0.
// (See accompanying file LICENSE_1_0.txt or copy at https://www.boost.org/LICENSE_1_0.txt)
#include <cassert>
#include <cstring>
#include <iostream>
#include <string>
#include <tao/pegtl.hpp>
#include <tao/pegtl/contrib/analyze.hpp>
namespace pegtl = TAO_PEGTL_NAMESPACE;
namespace dynamic
{
struct long_literal_id
: pegtl::plus< pegtl::not_one< '[' > >
{};
struct long_literal_open
: pegtl::seq< pegtl::one< '[' >, long_literal_id, pegtl::one< '[' > >
{};
struct long_literal_mark
{
using rule_t = long_literal_mark;
template< pegtl::apply_mode,
pegtl::rewind_mode,
template< typename... >
class Action,
template< typename... >
class Control,
typename ParseInput,
typename... States >
static bool match( ParseInput& in, const std::string& id, const std::string& /*unused*/, States&&... /*unused*/ )
{
if( in.size( id.size() ) >= id.size() ) {
if( std::memcmp( in.current(), id.data(), id.size() ) == 0 ) {
in.bump( id.size() );
return true;
}
}
return false;
}
};
struct long_literal_close
: pegtl::seq< pegtl::one< ']' >, long_literal_mark, pegtl::one< ']' > >
{};
struct long_literal_body
: pegtl::any
{};
struct grammar
: pegtl::seq< long_literal_open, pegtl::until< long_literal_close, long_literal_body >, pegtl::eof >
{};
template< typename Rule >
struct action
{};
template<>
struct action< long_literal_id >
{
template< typename ActionInput >
static void apply( const ActionInput& in, std::string& id, const std::string& /*unused*/ )
{
id = in.string();
}
};
template<>
struct action< long_literal_body >
{
template< typename ActionInput >
static void apply( const ActionInput& in, const std::string& /*unused*/, std::string& body )
{
body += in.string();
}
};
} // namespace dynamic
namespace TAO_PEGTL_NAMESPACE
{
template< typename Name >
struct analyze_traits< Name, dynamic::long_literal_mark >
: analyze_any_traits<>
{};
} // namespace TAO_PEGTL_NAMESPACE
int main( int argc, char** argv ) // NOLINT(bugprone-exception-escape)
{
if( pegtl::analyze< dynamic::grammar >() != 0 ) {
std::cerr << "cycles without progress detected!" << std::endl;
return 1;
}
if( argc > 1 ) {
std::string id;
std::string body;
pegtl::argv_input in( argv, 1 );
if( pegtl::parse< dynamic::grammar, dynamic::action >( in, id, body ) ) {
std::cout << "long literal id was: " << id << std::endl;
std::cout << "long literal body was: " << body << std::endl;
}
else {
std::cerr << "parse error for: " << argv[ 1 ] << std::endl;
return 1;
}
}
return 0;
}