1 // Copyright (c) 2013-2014 Sandstorm Development Group, Inc. and contributors
2 // Licensed under the MIT License:
3 //
4 // Permission is hereby granted, free of charge, to any person obtaining a copy
5 // of this software and associated documentation files (the "Software"), to deal
6 // in the Software without restriction, including without limitation the rights
7 // to use, copy, modify, merge, publish, distribute, sublicense, and/or sell
8 // copies of the Software, and to permit persons to whom the Software is
9 // furnished to do so, subject to the following conditions:
10 //
11 // The above copyright notice and this permission notice shall be included in
12 // all copies or substantial portions of the Software.
13 //
14 // THE SOFTWARE IS PROVIDED "AS IS", WITHOUT WARRANTY OF ANY KIND, EXPRESS OR
15 // IMPLIED, INCLUDING BUT NOT LIMITED TO THE WARRANTIES OF MERCHANTABILITY,
16 // FITNESS FOR A PARTICULAR PURPOSE AND NONINFRINGEMENT. IN NO EVENT SHALL THE
17 // AUTHORS OR COPYRIGHT HOLDERS BE LIABLE FOR ANY CLAIM, DAMAGES OR OTHER
18 // LIABILITY, WHETHER IN AN ACTION OF CONTRACT, TORT OR OTHERWISE, ARISING FROM,
19 // OUT OF OR IN CONNECTION WITH THE SOFTWARE OR THE USE OR OTHER DEALINGS IN
20 // THE SOFTWARE.
21 
22 // Parser combinator framework!
23 //
24 // This file declares several functions which construct parsers, usually taking other parsers as
25 // input, thus making them parser combinators.
26 //
27 // A valid parser is any functor which takes a reference to an input cursor (defined below) as its
28 // input and returns a Maybe.  The parser returns null on parse failure, or returns the parsed
29 // result on success.
30 //
31 // An "input cursor" is any type which implements the same interface as IteratorInput, below.  Such
32 // a type acts as a pointer to the current input location.  When a parser returns successfully, it
33 // will have updated the input cursor to point to the position just past the end of what was parsed.
34 // On failure, the cursor position is unspecified.
35 
36 #pragma once
37 
38 #include "../common.h"
39 #include "../memory.h"
40 #include "../array.h"
41 #include "../tuple.h"
42 #include "../vector.h"
43 
44 #if _MSC_VER && _MSC_VER < 1920 && !__clang__
45 #define KJ_MSVC_BROKEN_DECLTYPE 1
46 #endif
47 
48 #if KJ_MSVC_BROKEN_DECLTYPE
49 #include <type_traits>  // result_of_t
50 #endif
51 
52 KJ_BEGIN_HEADER
53 
54 namespace kj {
55 namespace parse {
56 
57 template <typename Element, typename Iterator>
58 class IteratorInput {
59   // A parser input implementation based on an iterator range.
60 
61 public:
IteratorInput(Iterator begin,Iterator end)62   IteratorInput(Iterator begin, Iterator end)
63       : parent(nullptr), pos(begin), end(end), best(begin) {}
IteratorInput(IteratorInput & parent)64   explicit IteratorInput(IteratorInput& parent)
65       : parent(&parent), pos(parent.pos), end(parent.end), best(parent.pos) {}
~IteratorInput()66   ~IteratorInput() {
67     if (parent != nullptr) {
68       parent->best = kj::max(kj::max(pos, best), parent->best);
69     }
70   }
71   KJ_DISALLOW_COPY(IteratorInput);
72 
advanceParent()73   void advanceParent() {
74     parent->pos = pos;
75   }
forgetParent()76   void forgetParent() {
77     parent = nullptr;
78   }
79 
atEnd()80   bool atEnd() { return pos == end; }
81   auto current() -> decltype(*instance<Iterator>()) {
82     KJ_IREQUIRE(!atEnd());
83     return *pos;
84   }
85   auto consume() -> decltype(*instance<Iterator>()) {
86     KJ_IREQUIRE(!atEnd());
87     return *pos++;
88   }
next()89   void next() {
90     KJ_IREQUIRE(!atEnd());
91     ++pos;
92   }
93 
getBest()94   Iterator getBest() { return kj::max(pos, best); }
95 
getPosition()96   Iterator getPosition() { return pos; }
97 
98 private:
99   IteratorInput* parent;
100   Iterator pos;
101   Iterator end;
102   Iterator best;  // furthest we got with any sub-input
103 };
104 
105 template <typename T> struct OutputType_;
106 template <typename T> struct OutputType_<Maybe<T>> { typedef T Type; };
107 template <typename Parser, typename Input>
108 using OutputType = typename OutputType_<
109 #if KJ_MSVC_BROKEN_DECLTYPE
110     std::result_of_t<Parser(Input)>
111     // The instance<T&>() based version below results in many compiler errors on MSVC2017.
112 #else
113     decltype(instance<Parser&>()(instance<Input&>()))
114 #endif
115     >::Type;
116 // Synonym for the output type of a parser, given the parser type and the input type.
117 
118 // =======================================================================================
119 
120 template <typename Input, typename Output>
121 class ParserRef {
122   // Acts as a reference to some other parser, with simplified type.  The referenced parser
123   // is polymorphic by virtual call rather than templates.  For grammars of non-trivial size,
124   // it is important to inject refs into the grammar here and there to prevent the parser types
125   // from becoming ridiculous.  Using too many of them can hurt performance, though.
126 
127 public:
128   ParserRef(): parser(nullptr), wrapper(nullptr) {}
129   ParserRef(const ParserRef&) = default;
130   ParserRef(ParserRef&&) = default;
131   ParserRef& operator=(const ParserRef& other) = default;
132   ParserRef& operator=(ParserRef&& other) = default;
133 
134   template <typename Other>
135   constexpr ParserRef(Other&& other)
136       : parser(&other), wrapper(&WrapperImplInstance<Decay<Other>>::instance) {
137     static_assert(kj::isReference<Other>(), "ParserRef should not be assigned to a temporary.");
138   }
139 
140   template <typename Other>
141   inline ParserRef& operator=(Other&& other) {
142     static_assert(kj::isReference<Other>(), "ParserRef should not be assigned to a temporary.");
143     parser = &other;
144     wrapper = &WrapperImplInstance<Decay<Other>>::instance;
145     return *this;
146   }
147 
148   KJ_ALWAYS_INLINE(Maybe<Output> operator()(Input& input) const) {
149     // Always inline in the hopes that this allows branch prediction to kick in so the virtual call
150     // doesn't hurt so much.
151     return wrapper->parse(parser, input);
152   }
153 
154 private:
155   struct Wrapper {
156     virtual Maybe<Output> parse(const void* parser, Input& input) const = 0;
157   };
158   template <typename ParserImpl>
159   struct WrapperImpl: public Wrapper {
160     Maybe<Output> parse(const void* parser, Input& input) const override {
161       return (*reinterpret_cast<const ParserImpl*>(parser))(input);
162     }
163   };
164   template <typename ParserImpl>
165   struct WrapperImplInstance {
166 #if _MSC_VER && !__clang__
167     // TODO(msvc): MSVC currently fails to initialize vtable pointers for constexpr values so
168     //   we have to make this just const instead.
169     static const WrapperImpl<ParserImpl> instance;
170 #else
171     static constexpr WrapperImpl<ParserImpl> instance = WrapperImpl<ParserImpl>();
172 #endif
173   };
174 
175   const void* parser;
176   const Wrapper* wrapper;
177 };
178 
179 template <typename Input, typename Output>
180 template <typename ParserImpl>
181 #if _MSC_VER && !__clang__
182 const typename ParserRef<Input, Output>::template WrapperImpl<ParserImpl>
183 ParserRef<Input, Output>::WrapperImplInstance<ParserImpl>::instance = WrapperImpl<ParserImpl>();
184 #else
185 constexpr typename ParserRef<Input, Output>::template WrapperImpl<ParserImpl>
186 ParserRef<Input, Output>::WrapperImplInstance<ParserImpl>::instance;
187 #endif
188 
189 template <typename Input, typename ParserImpl>
190 constexpr ParserRef<Input, OutputType<ParserImpl, Input>> ref(ParserImpl& impl) {
191   // Constructs a ParserRef.  You must specify the input type explicitly, e.g.
192   // `ref<MyInput>(myParser)`.
193 
194   return ParserRef<Input, OutputType<ParserImpl, Input>>(impl);
195 }
196 
197 // -------------------------------------------------------------------
198 // any
199 // Output = one token
200 
201 class Any_ {
202 public:
203   template <typename Input>
204   Maybe<Decay<decltype(instance<Input>().consume())>> operator()(Input& input) const {
205     if (input.atEnd()) {
206       return nullptr;
207     } else {
208       return input.consume();
209     }
210   }
211 };
212 
213 constexpr Any_ any = Any_();
214 // A parser which matches any token and simply returns it.
215 
216 // -------------------------------------------------------------------
217 // exactly()
218 // Output = Tuple<>
219 
220 template <typename T>
221 class Exactly_ {
222 public:
223   explicit constexpr Exactly_(T&& expected): expected(expected) {}
224 
225   template <typename Input>
226   Maybe<Tuple<>> operator()(Input& input) const {
227     if (input.atEnd() || input.current() != expected) {
228       return nullptr;
229     } else {
230       input.next();
231       return Tuple<>();
232     }
233   }
234 
235 private:
236   T expected;
237 };
238 
239 template <typename T>
240 constexpr Exactly_<T> exactly(T&& expected) {
241   // Constructs a parser which succeeds when the input is exactly the token specified.  The
242   // result is always the empty tuple.
243 
244   return Exactly_<T>(kj::fwd<T>(expected));
245 }
246 
247 // -------------------------------------------------------------------
248 // exactlyConst()
249 // Output = Tuple<>
250 
251 template <typename T, T expected>
252 class ExactlyConst_ {
253 public:
254   explicit constexpr ExactlyConst_() {}
255 
256   template <typename Input>
257   Maybe<Tuple<>> operator()(Input& input) const {
258     if (input.atEnd() || input.current() != expected) {
259       return nullptr;
260     } else {
261       input.next();
262       return Tuple<>();
263     }
264   }
265 };
266 
267 template <typename T, T expected>
268 constexpr ExactlyConst_<T, expected> exactlyConst() {
269   // Constructs a parser which succeeds when the input is exactly the token specified.  The
270   // result is always the empty tuple.  This parser is templated on the token value which may cause
271   // it to perform better -- or worse.  Be sure to measure.
272 
273   return ExactlyConst_<T, expected>();
274 }
275 
276 // -------------------------------------------------------------------
277 // constResult()
278 
279 template <typename SubParser, typename Result>
280 class ConstResult_ {
281 public:
282   explicit constexpr ConstResult_(SubParser&& subParser, Result&& result)
283       : subParser(kj::fwd<SubParser>(subParser)), result(kj::fwd<Result>(result)) {}
284 
285   template <typename Input>
286   Maybe<Result> operator()(Input& input) const {
287     if (subParser(input) == nullptr) {
288       return nullptr;
289     } else {
290       return result;
291     }
292   }
293 
294 private:
295   SubParser subParser;
296   Result result;
297 };
298 
299 template <typename SubParser, typename Result>
300 constexpr ConstResult_<SubParser, Result> constResult(SubParser&& subParser, Result&& result) {
301   // Constructs a parser which returns exactly `result` if `subParser` is successful.
302   return ConstResult_<SubParser, Result>(kj::fwd<SubParser>(subParser), kj::fwd<Result>(result));
303 }
304 
305 template <typename SubParser>
306 constexpr ConstResult_<SubParser, Tuple<>> discard(SubParser&& subParser) {
307   // Constructs a parser which wraps `subParser` but discards the result.
308   return constResult(kj::fwd<SubParser>(subParser), Tuple<>());
309 }
310 
311 // -------------------------------------------------------------------
312 // sequence()
313 // Output = Flattened Tuple of outputs of sub-parsers.
314 
315 template <typename... SubParsers> class Sequence_;
316 
317 template <typename FirstSubParser, typename... SubParsers>
318 class Sequence_<FirstSubParser, SubParsers...> {
319 public:
320   template <typename T, typename... U>
321   explicit constexpr Sequence_(T&& firstSubParser, U&&... rest)
322       : first(kj::fwd<T>(firstSubParser)), rest(kj::fwd<U>(rest)...) {}
323 
324   // TODO(msvc): The trailing return types on `operator()` and `parseNext()` expose at least two
325   //   bugs in MSVC:
326   //
327   //     1. An ICE.
328   //     2. 'error C2672: 'operator __surrogate_func': no matching overloaded function found)',
329   //        which crops up in numerous places when trying to build the capnp command line tools.
330   //
331   //   The only workaround I found for both bugs is to omit the trailing return types and instead
332   //   rely on C++14's return type deduction.
333 
334   template <typename Input>
335   auto operator()(Input& input) const
336 #if !_MSC_VER || __clang__
337       -> Maybe<decltype(tuple(
338           instance<OutputType<FirstSubParser, Input>>(),
339           instance<OutputType<SubParsers, Input>>()...))>
340 #endif
341   {
342     return parseNext(input);
343   }
344 
345   template <typename Input, typename... InitialParams>
346   auto parseNext(Input& input, InitialParams&&... initialParams) const
347 #if !_MSC_VER || __clang__
348       -> Maybe<decltype(tuple(
349           kj::fwd<InitialParams>(initialParams)...,
350           instance<OutputType<FirstSubParser, Input>>(),
351           instance<OutputType<SubParsers, Input>>()...))>
352 #endif
353   {
354     KJ_IF_MAYBE(firstResult, first(input)) {
355       return rest.parseNext(input, kj::fwd<InitialParams>(initialParams)...,
356                             kj::mv(*firstResult));
357     } else {
358       // TODO(msvc): MSVC depends on return type deduction to compile this function, so we need to
359       //   help it deduce the right type on this code path.
360       return Maybe<decltype(tuple(
361           kj::fwd<InitialParams>(initialParams)...,
362           instance<OutputType<FirstSubParser, Input>>(),
363           instance<OutputType<SubParsers, Input>>()...))>{nullptr};
364     }
365   }
366 
367 private:
368   FirstSubParser first;
369   Sequence_<SubParsers...> rest;
370 };
371 
372 template <>
373 class Sequence_<> {
374 public:
375   template <typename Input>
376   Maybe<Tuple<>> operator()(Input& input) const {
377     return parseNext(input);
378   }
379 
380   template <typename Input, typename... Params>
381   auto parseNext(Input& input, Params&&... params) const ->
382       Maybe<decltype(tuple(kj::fwd<Params>(params)...))> {
383     return tuple(kj::fwd<Params>(params)...);
384   }
385 };
386 
387 template <typename... SubParsers>
388 constexpr Sequence_<SubParsers...> sequence(SubParsers&&... subParsers) {
389   // Constructs a parser that executes each of the parameter parsers in sequence and returns a
390   // tuple of their results.
391 
392   return Sequence_<SubParsers...>(kj::fwd<SubParsers>(subParsers)...);
393 }
394 
395 // -------------------------------------------------------------------
396 // many()
397 // Output = Array of output of sub-parser, or just a uint count if the sub-parser returns Tuple<>.
398 
399 template <typename SubParser, bool atLeastOne>
400 class Many_ {
401   template <typename Input, typename Output = OutputType<SubParser, Input>>
402   struct Impl;
403 public:
404   explicit constexpr Many_(SubParser&& subParser)
405       : subParser(kj::fwd<SubParser>(subParser)) {}
406 
407   template <typename Input>
408   auto operator()(Input& input) const
409       -> decltype(Impl<Input>::apply(instance<const SubParser&>(), input));
410 
411 private:
412   SubParser subParser;
413 };
414 
415 template <typename SubParser, bool atLeastOne>
416 template <typename Input, typename Output>
417 struct Many_<SubParser, atLeastOne>::Impl {
418   static Maybe<Array<Output>> apply(const SubParser& subParser, Input& input) {
419     typedef Vector<OutputType<SubParser, Input>> Results;
420     Results results;
421 
422     while (!input.atEnd()) {
423       Input subInput(input);
424 
425       KJ_IF_MAYBE(subResult, subParser(subInput)) {
426         subInput.advanceParent();
427         results.add(kj::mv(*subResult));
428       } else {
429         break;
430       }
431     }
432 
433     if (atLeastOne && results.empty()) {
434       return nullptr;
435     }
436 
437     return results.releaseAsArray();
438   }
439 };
440 
441 template <typename SubParser, bool atLeastOne>
442 template <typename Input>
443 struct Many_<SubParser, atLeastOne>::Impl<Input, Tuple<>> {
444   // If the sub-parser output is Tuple<>, just return a count.
445 
446   static Maybe<uint> apply(const SubParser& subParser, Input& input) {
447     uint count = 0;
448 
449     while (!input.atEnd()) {
450       Input subInput(input);
451 
452       KJ_IF_MAYBE(subResult, subParser(subInput)) {
453         subInput.advanceParent();
454         ++count;
455       } else {
456         break;
457       }
458     }
459 
460     if (atLeastOne && count == 0) {
461       return nullptr;
462     }
463 
464     return count;
465   }
466 };
467 
468 template <typename SubParser, bool atLeastOne>
469 template <typename Input>
470 auto Many_<SubParser, atLeastOne>::operator()(Input& input) const
471     -> decltype(Impl<Input>::apply(instance<const SubParser&>(), input)) {
472   return Impl<Input, OutputType<SubParser, Input>>::apply(subParser, input);
473 }
474 
475 template <typename SubParser>
476 constexpr Many_<SubParser, false> many(SubParser&& subParser) {
477   // Constructs a parser that repeatedly executes the given parser until it fails, returning an
478   // Array of the results (or a uint count if `subParser` returns an empty tuple).
479   return Many_<SubParser, false>(kj::fwd<SubParser>(subParser));
480 }
481 
482 template <typename SubParser>
483 constexpr Many_<SubParser, true> oneOrMore(SubParser&& subParser) {
484   // Like `many()` but the parser must parse at least one item to be successful.
485   return Many_<SubParser, true>(kj::fwd<SubParser>(subParser));
486 }
487 
488 // -------------------------------------------------------------------
489 // times()
490 // Output = Array of output of sub-parser, or Tuple<> if sub-parser returns Tuple<>.
491 
492 template <typename SubParser>
493 class Times_ {
494   template <typename Input, typename Output = OutputType<SubParser, Input>>
495   struct Impl;
496 public:
497   explicit constexpr Times_(SubParser&& subParser, uint count)
498       : subParser(kj::fwd<SubParser>(subParser)), count(count) {}
499 
500   template <typename Input>
501   auto operator()(Input& input) const
502       -> decltype(Impl<Input>::apply(instance<const SubParser&>(), instance<uint>(), input));
503 
504 private:
505   SubParser subParser;
506   uint count;
507 };
508 
509 template <typename SubParser>
510 template <typename Input, typename Output>
511 struct Times_<SubParser>::Impl {
512   static Maybe<Array<Output>> apply(const SubParser& subParser, uint count, Input& input) {
513     auto results = heapArrayBuilder<OutputType<SubParser, Input>>(count);
514 
515     while (results.size() < count) {
516       if (input.atEnd()) {
517         return nullptr;
518       } else KJ_IF_MAYBE(subResult, subParser(input)) {
519         results.add(kj::mv(*subResult));
520       } else {
521         return nullptr;
522       }
523     }
524 
525     return results.finish();
526   }
527 };
528 
529 template <typename SubParser>
530 template <typename Input>
531 struct Times_<SubParser>::Impl<Input, Tuple<>> {
532   // If the sub-parser output is Tuple<>, just return a count.
533 
534   static Maybe<Tuple<>> apply(const SubParser& subParser, uint count, Input& input) {
535     uint actualCount = 0;
536 
537     while (actualCount < count) {
538       if (input.atEnd()) {
539         return nullptr;
540       } else KJ_IF_MAYBE(subResult, subParser(input)) {
541         ++actualCount;
542       } else {
543         return nullptr;
544       }
545     }
546 
547     return tuple();
548   }
549 };
550 
551 template <typename SubParser>
552 template <typename Input>
553 auto Times_<SubParser>::operator()(Input& input) const
554     -> decltype(Impl<Input>::apply(instance<const SubParser&>(), instance<uint>(), input)) {
555   return Impl<Input, OutputType<SubParser, Input>>::apply(subParser, count, input);
556 }
557 
558 template <typename SubParser>
559 constexpr Times_<SubParser> times(SubParser&& subParser, uint count) {
560   // Constructs a parser that repeats the subParser exactly `count` times.
561   return Times_<SubParser>(kj::fwd<SubParser>(subParser), count);
562 }
563 
564 // -------------------------------------------------------------------
565 // optional()
566 // Output = Maybe<output of sub-parser>
567 
568 template <typename SubParser>
569 class Optional_ {
570 public:
571   explicit constexpr Optional_(SubParser&& subParser)
572       : subParser(kj::fwd<SubParser>(subParser)) {}
573 
574   template <typename Input>
575   Maybe<Maybe<OutputType<SubParser, Input>>> operator()(Input& input) const {
576     typedef Maybe<OutputType<SubParser, Input>> Result;
577 
578     Input subInput(input);
579     KJ_IF_MAYBE(subResult, subParser(subInput)) {
580       subInput.advanceParent();
581       return Result(kj::mv(*subResult));
582     } else {
583       return Result(nullptr);
584     }
585   }
586 
587 private:
588   SubParser subParser;
589 };
590 
591 template <typename SubParser>
592 constexpr Optional_<SubParser> optional(SubParser&& subParser) {
593   // Constructs a parser that accepts zero or one of the given sub-parser, returning a Maybe
594   // of the sub-parser's result.
595   return Optional_<SubParser>(kj::fwd<SubParser>(subParser));
596 }
597 
598 // -------------------------------------------------------------------
599 // oneOf()
600 // All SubParsers must have same output type, which becomes the output type of the
601 // OneOfParser.
602 
603 template <typename... SubParsers>
604 class OneOf_;
605 
606 template <typename FirstSubParser, typename... SubParsers>
607 class OneOf_<FirstSubParser, SubParsers...> {
608 public:
609   explicit constexpr OneOf_(FirstSubParser&& firstSubParser, SubParsers&&... rest)
610       : first(kj::fwd<FirstSubParser>(firstSubParser)), rest(kj::fwd<SubParsers>(rest)...) {}
611 
612   template <typename Input>
613   Maybe<OutputType<FirstSubParser, Input>> operator()(Input& input) const {
614     {
615       Input subInput(input);
616       Maybe<OutputType<FirstSubParser, Input>> firstResult = first(subInput);
617 
618       if (firstResult != nullptr) {
619         subInput.advanceParent();
620         return kj::mv(firstResult);
621       }
622     }
623 
624     // Hoping for some tail recursion here...
625     return rest(input);
626   }
627 
628 private:
629   FirstSubParser first;
630   OneOf_<SubParsers...> rest;
631 };
632 
633 template <>
634 class OneOf_<> {
635 public:
636   template <typename Input>
637   decltype(nullptr) operator()(Input& input) const {
638     return nullptr;
639   }
640 };
641 
642 template <typename... SubParsers>
643 constexpr OneOf_<SubParsers...> oneOf(SubParsers&&... parsers) {
644   // Constructs a parser that accepts one of a set of options.  The parser behaves as the first
645   // sub-parser in the list which returns successfully.  All of the sub-parsers must return the
646   // same type.
647   return OneOf_<SubParsers...>(kj::fwd<SubParsers>(parsers)...);
648 }
649 
650 // -------------------------------------------------------------------
651 // transform()
652 // Output = Result of applying transform functor to input value.  If input is a tuple, it is
653 // unpacked to form the transformation parameters.
654 
655 template <typename Position>
656 struct Span {
657 public:
658   inline const Position& begin() const { return begin_; }
659   inline const Position& end() const { return end_; }
660 
661   Span() = default;
662   inline constexpr Span(Position&& begin, Position&& end): begin_(mv(begin)), end_(mv(end)) {}
663 
664 private:
665   Position begin_;
666   Position end_;
667 };
668 
669 template <typename Position>
670 constexpr Span<Decay<Position>> span(Position&& start, Position&& end) {
671   return Span<Decay<Position>>(kj::fwd<Position>(start), kj::fwd<Position>(end));
672 }
673 
674 template <typename SubParser, typename TransformFunc>
675 class Transform_ {
676 public:
677   explicit constexpr Transform_(SubParser&& subParser, TransformFunc&& transform)
678       : subParser(kj::fwd<SubParser>(subParser)), transform(kj::fwd<TransformFunc>(transform)) {}
679 
680   template <typename Input>
681   Maybe<decltype(kj::apply(instance<TransformFunc&>(),
682                            instance<OutputType<SubParser, Input>&&>()))>
683       operator()(Input& input) const {
684     KJ_IF_MAYBE(subResult, subParser(input)) {
685       return kj::apply(transform, kj::mv(*subResult));
686     } else {
687       return nullptr;
688     }
689   }
690 
691 private:
692   SubParser subParser;
693   TransformFunc transform;
694 };
695 
696 template <typename SubParser, typename TransformFunc>
697 class TransformOrReject_ {
698 public:
699   explicit constexpr TransformOrReject_(SubParser&& subParser, TransformFunc&& transform)
700       : subParser(kj::fwd<SubParser>(subParser)), transform(kj::fwd<TransformFunc>(transform)) {}
701 
702   template <typename Input>
703   decltype(kj::apply(instance<TransformFunc&>(), instance<OutputType<SubParser, Input>&&>()))
704       operator()(Input& input) const {
705     KJ_IF_MAYBE(subResult, subParser(input)) {
706       return kj::apply(transform, kj::mv(*subResult));
707     } else {
708       return nullptr;
709     }
710   }
711 
712 private:
713   SubParser subParser;
714   TransformFunc transform;
715 };
716 
717 template <typename SubParser, typename TransformFunc>
718 class TransformWithLocation_ {
719 public:
720   explicit constexpr TransformWithLocation_(SubParser&& subParser, TransformFunc&& transform)
721       : subParser(kj::fwd<SubParser>(subParser)), transform(kj::fwd<TransformFunc>(transform)) {}
722 
723   template <typename Input>
724   Maybe<decltype(kj::apply(instance<TransformFunc&>(),
725                            instance<Span<Decay<decltype(instance<Input&>().getPosition())>>>(),
726                            instance<OutputType<SubParser, Input>&&>()))>
727       operator()(Input& input) const {
728     auto start = input.getPosition();
729     KJ_IF_MAYBE(subResult, subParser(input)) {
730       return kj::apply(transform, Span<decltype(start)>(kj::mv(start), input.getPosition()),
731                        kj::mv(*subResult));
732     } else {
733       return nullptr;
734     }
735   }
736 
737 private:
738   SubParser subParser;
739   TransformFunc transform;
740 };
741 
742 template <typename SubParser, typename TransformFunc>
743 constexpr Transform_<SubParser, TransformFunc> transform(
744     SubParser&& subParser, TransformFunc&& functor) {
745   // Constructs a parser which executes some other parser and then transforms the result by invoking
746   // `functor` on it.  Typically `functor` is a lambda.  It is invoked using `kj::apply`,
747   // meaning tuples will be unpacked as arguments.
748   return Transform_<SubParser, TransformFunc>(
749       kj::fwd<SubParser>(subParser), kj::fwd<TransformFunc>(functor));
750 }
751 
752 template <typename SubParser, typename TransformFunc>
753 constexpr TransformOrReject_<SubParser, TransformFunc> transformOrReject(
754     SubParser&& subParser, TransformFunc&& functor) {
755   // Like `transform()` except that `functor` returns a `Maybe`.  If it returns null, parsing fails,
756   // otherwise the parser's result is the content of the `Maybe`.
757   return TransformOrReject_<SubParser, TransformFunc>(
758       kj::fwd<SubParser>(subParser), kj::fwd<TransformFunc>(functor));
759 }
760 
761 template <typename SubParser, typename TransformFunc>
762 constexpr TransformWithLocation_<SubParser, TransformFunc> transformWithLocation(
763     SubParser&& subParser, TransformFunc&& functor) {
764   // Like `transform` except that `functor` also takes a `Span` as its first parameter specifying
765   // the location of the parsed content.  The span's position type is whatever the parser input's
766   // getPosition() returns.
767   return TransformWithLocation_<SubParser, TransformFunc>(
768       kj::fwd<SubParser>(subParser), kj::fwd<TransformFunc>(functor));
769 }
770 
771 // -------------------------------------------------------------------
772 // notLookingAt()
773 // Fails if the given parser succeeds at the current location.
774 
775 template <typename SubParser>
776 class NotLookingAt_ {
777 public:
778   explicit constexpr NotLookingAt_(SubParser&& subParser)
779       : subParser(kj::fwd<SubParser>(subParser)) {}
780 
781   template <typename Input>
782   Maybe<Tuple<>> operator()(Input& input) const {
783     Input subInput(input);
784     subInput.forgetParent();
785     if (subParser(subInput) == nullptr) {
786       return Tuple<>();
787     } else {
788       return nullptr;
789     }
790   }
791 
792 private:
793   SubParser subParser;
794 };
795 
796 template <typename SubParser>
797 constexpr NotLookingAt_<SubParser> notLookingAt(SubParser&& subParser) {
798   // Constructs a parser which fails at any position where the given parser succeeds.  Otherwise,
799   // it succeeds without consuming any input and returns an empty tuple.
800   return NotLookingAt_<SubParser>(kj::fwd<SubParser>(subParser));
801 }
802 
803 // -------------------------------------------------------------------
804 // endOfInput()
805 // Output = Tuple<>, only succeeds if at end-of-input
806 
807 class EndOfInput_ {
808 public:
809   template <typename Input>
810   Maybe<Tuple<>> operator()(Input& input) const {
811     if (input.atEnd()) {
812       return Tuple<>();
813     } else {
814       return nullptr;
815     }
816   }
817 };
818 
819 constexpr EndOfInput_ endOfInput = EndOfInput_();
820 // A parser that succeeds only if it is called with no input.
821 
822 }  // namespace parse
823 }  // namespace kj
824 
825 KJ_END_HEADER
826