brintos

brintos / llvm-project-archived public Read only

0
0
Text · 13.1 KiB · 0dec565 Raw
301 lines · cpp
1//===-- lib/Parser/openacc-parsers.cpp ------------------------------------===//2//3// Part of the LLVM Project, under the Apache License v2.0 with LLVM Exceptions.4// See https://llvm.org/LICENSE.txt for license information.5// SPDX-License-Identifier: Apache-2.0 WITH LLVM-exception6//7//===----------------------------------------------------------------------===//8 9// Top-level grammar specification for OpenACC 3.3.10 11#include "basic-parsers.h"12#include "expr-parsers.h"13#include "misc-parsers.h"14#include "stmt-parser.h"15#include "token-parsers.h"16#include "type-parser-implementation.h"17#include "flang/Parser/parse-tree.h"18 19// OpenACC Directives and Clauses20namespace Fortran::parser {21 22// Only need to handle ! line comments because prescanning normalizes the23// other types of line comments from fixed form.24constexpr auto startAccLine{skipStuffBeforeStatement >>25    withMessage(26        "expected OpenACC directive sentinel: !$ACC, C$ACC, or *$ACC"_err_en_US,27        "!$ACC "_sptok)};28constexpr auto endAccLine{space >>29    recovery(30        withMessage("expected end of OpenACC directive"_err_en_US, endOfLine),31        SkipTo<'\n'>{} || ok)};32 33// Autogenerated clauses parser. Information is taken from ACC.td and the34// parser is generated by tablegen.35// Scalar value parsers are provided by Flang directly. Specific value parsers36// are provided below.37#define GEN_FLANG_CLAUSES_PARSER38#include "llvm/Frontend/OpenACC/ACC.inc"39 40TYPE_PARSER(41    construct<AccObject>(designator) || construct<AccObject>("/" >> name / "/"))42 43TYPE_PARSER(construct<AccObjectList>(nonemptyList(Parser<AccObject>{})))44 45TYPE_PARSER(construct<AccObjectListWithModifier>(46    maybe(Parser<AccDataModifier>{}), Parser<AccObjectList>{}))47 48TYPE_PARSER(construct<AccObjectListWithReduction>(49    Parser<ReductionOperator>{} / ":", Parser<AccObjectList>{}))50 51// 2.16 (3249) wait-argument is:52//   [devnum : int-expr :] [queues :] int-expr-list53TYPE_PARSER(construct<AccWaitArgument>(maybe("DEVNUM:" >> scalarIntExpr / ":"),54    "QUEUES:" >> nonemptyList(scalarIntExpr) || nonemptyList(scalarIntExpr)))55 56// 2.9 (1984-1986) size-expr is one of:57//   * (represented as an empty std::optional<ScalarIntExpr>)58//   int-expr59TYPE_PARSER(construct<AccSizeExpr>(scalarIntExpr) ||60    construct<AccSizeExpr>("*" >> construct<std::optional<ScalarIntExpr>>()))61TYPE_PARSER(construct<AccSizeExprList>(nonemptyList(Parser<AccSizeExpr>{})))62 63TYPE_PARSER(sourced(construct<AccDeviceTypeExpr>(64    first("*" >> pure(Fortran::common::OpenACCDeviceType::Star),65        "DEFAULT" >> pure(Fortran::common::OpenACCDeviceType::Default),66        "NVIDIA" >> pure(Fortran::common::OpenACCDeviceType::Nvidia),67        "ACC_DEVICE_NVIDIA" >> pure(Fortran::common::OpenACCDeviceType::Nvidia),68        "RADEON" >> pure(Fortran::common::OpenACCDeviceType::Radeon),69        "HOST" >> pure(Fortran::common::OpenACCDeviceType::Host),70        "MULTICORE" >> pure(Fortran::common::OpenACCDeviceType::Multicore)))))71 72TYPE_PARSER(73    construct<AccDeviceTypeExprList>(nonemptyList(Parser<AccDeviceTypeExpr>{})))74 75// tile size is one of:76//   * (represented as an empty std::optional<ScalarIntExpr>)77//   constant-int-expr78TYPE_PARSER(sourced(construct<AccTileExpr>(scalarIntConstantExpr) ||79    construct<AccTileExpr>(80        "*" >> construct<std::optional<ScalarIntConstantExpr>>())))81TYPE_PARSER(construct<AccTileExprList>(nonemptyList(Parser<AccTileExpr>{})))82 83// 2.9 (1979-1982) gang-arg is one of :84//   [num:]int-expr85//   dim:int-expr86//   static:size-expr87TYPE_PARSER(sourced(construct<AccGangArg>(construct<AccGangArg::Static>(88                        "STATIC: " >> Parser<AccSizeExpr>{})) ||89    construct<AccGangArg>(90        construct<AccGangArg::Dim>("DIM: " >> scalarIntExpr)) ||91    construct<AccGangArg>(92        construct<AccGangArg::Num>(maybe("NUM: "_tok) >> scalarIntExpr))))93 94// 2.9 gang-arg-list95TYPE_PARSER(96    construct<AccGangArgList>(many(maybe(","_tok) >> Parser<AccGangArg>{})))97 98// 2.9.1 collapse99TYPE_PARSER(construct<AccCollapseArg>(100    "FORCE:"_tok >> pure(true) || pure(false), scalarIntConstantExpr))101 102// 2.5.15 Reduction, F'2023 R1131, and CUF reduction-op103// Operator for reduction104TYPE_PARSER(construct<ReductionOperator>(105    first("+" >> pure(ReductionOperator::Operator::Plus),106        "*" >> pure(ReductionOperator::Operator::Multiply),107        "MAX" >> pure(ReductionOperator::Operator::Max),108        "MIN" >> pure(ReductionOperator::Operator::Min),109        "IAND" >> pure(ReductionOperator::Operator::Iand),110        "IOR" >> pure(ReductionOperator::Operator::Ior),111        "IEOR" >> pure(ReductionOperator::Operator::Ieor),112        ".AND." >> pure(ReductionOperator::Operator::And),113        ".OR." >> pure(ReductionOperator::Operator::Or),114        ".EQV." >> pure(ReductionOperator::Operator::Eqv),115        ".NEQV." >> pure(ReductionOperator::Operator::Neqv))))116 117// 2.15.1 Bind clause118TYPE_PARSER(sourced(construct<AccBindClause>(name) ||119    construct<AccBindClause>(scalarDefaultCharExpr)))120 121// 2.5.16 Default clause122TYPE_PARSER(sourced(construct<AccDefaultClause>(123    first("NONE" >> pure(llvm::acc::DefaultValue::ACC_Default_none),124        "PRESENT" >> pure(llvm::acc::DefaultValue::ACC_Default_present)))))125 126// SELF clause is either a simple optional condition for compute construct127// or a synonym of the HOST clause for the update directive 2.14.4 holding128// an object list.129TYPE_PARSER(sourced(130    construct<AccSelfClause>(Parser<AccObjectList>{}) / lookAhead(")"_tok) ||131    construct<AccSelfClause>(scalarLogicalExpr) / lookAhead(")"_tok) ||132    construct<AccSelfClause>(133        recovery(fail<std::optional<ScalarLogicalExpr>>(134                     "logical expression or object list expected"_err_en_US),135            SkipTo<')'>{} >> pure<std::optional<ScalarLogicalExpr>>()))))136 137// Modifier for copyin, copyout, cache and create138TYPE_PARSER(sourced(construct<AccDataModifier>(139    first("ZERO:" >> pure(AccDataModifier::Modifier::Zero),140        "READONLY:" >> pure(AccDataModifier::Modifier::ReadOnly)))))141 142// Combined directives143TYPE_PARSER(sourced(construct<AccCombinedDirective>(144    first("KERNELS LOOP" >> pure(llvm::acc::Directive::ACCD_kernels_loop),145        "PARALLEL LOOP" >> pure(llvm::acc::Directive::ACCD_parallel_loop),146        "SERIAL LOOP" >> pure(llvm::acc::Directive::ACCD_serial_loop)))))147 148// Block directives149TYPE_PARSER(sourced(construct<AccBlockDirective>(150    first("DATA" >> pure(llvm::acc::Directive::ACCD_data),151        "HOST_DATA" >> pure(llvm::acc::Directive::ACCD_host_data),152        "KERNELS" >> pure(llvm::acc::Directive::ACCD_kernels),153        "PARALLEL" >> pure(llvm::acc::Directive::ACCD_parallel),154        "SERIAL" >> pure(llvm::acc::Directive::ACCD_serial)))))155 156// Standalone directives157TYPE_PARSER(sourced(construct<AccStandaloneDirective>(158    first("ENTER DATA" >> pure(llvm::acc::Directive::ACCD_enter_data),159        "EXIT DATA" >> pure(llvm::acc::Directive::ACCD_exit_data),160        "INIT" >> pure(llvm::acc::Directive::ACCD_init),161        "SHUTDOWN" >> pure(llvm::acc::Directive::ACCD_shutdown),162        "SET" >> pure(llvm::acc::Directive::ACCD_set),163        "UPDATE" >> pure(llvm::acc::Directive::ACCD_update)))))164 165// Loop directives166TYPE_PARSER(sourced(construct<AccLoopDirective>(167    first("LOOP" >> pure(llvm::acc::Directive::ACCD_loop)))))168 169TYPE_PARSER(sourced(construct<AccBeginLoopDirective>(170    Parser<AccLoopDirective>{}, Parser<AccClauseList>{})))171 172TYPE_PARSER(construct<AccEndLoop>("END LOOP"_tok))173 174TYPE_PARSER(construct<OpenACCLoopConstruct>(175    Parser<AccBeginLoopDirective>{} / endAccLine, maybe(Parser<DoConstruct>{}),176    maybe(startAccLine >> Parser<AccEndLoop>{} / endAccLine)))177 178// 2.15.1 Routine directive179TYPE_PARSER(sourced(construct<OpenACCRoutineConstruct>(verbatim("ROUTINE"_tok),180    maybe(parenthesized(name)), Parser<AccClauseList>{})))181 182// 2.10 Cache directive183TYPE_PARSER(sourced(184    construct<OpenACCCacheConstruct>(sourced(construct<Verbatim>("CACHE"_tok)),185        parenthesized(Parser<AccObjectListWithModifier>{}))))186 187// 2.11 Combined constructs188TYPE_PARSER(sourced(construct<AccBeginCombinedDirective>(189    Parser<AccCombinedDirective>{}, Parser<AccClauseList>{})))190 191// 2.12 Atomic constructs192TYPE_PARSER(construct<AccEndAtomic>(startAccLine >> "END ATOMIC"_tok))193 194TYPE_PARSER("ATOMIC" >> construct<AccAtomicRead>(verbatim("READ"_tok),195                            Parser<AccClauseList>{} / endAccLine,196                            statement(assignmentStmt),197                            maybe(Parser<AccEndAtomic>{} / endAccLine)))198 199TYPE_PARSER("ATOMIC" >> construct<AccAtomicWrite>(verbatim("WRITE"_tok),200                            Parser<AccClauseList>{} / endAccLine,201                            statement(assignmentStmt),202                            maybe(Parser<AccEndAtomic>{} / endAccLine)))203 204TYPE_PARSER("ATOMIC" >>205    construct<AccAtomicUpdate>(maybe(verbatim("UPDATE"_tok)),206        Parser<AccClauseList>{} / endAccLine, statement(assignmentStmt),207        maybe(Parser<AccEndAtomic>{} / endAccLine)))208 209TYPE_PARSER("ATOMIC" >>210    construct<AccAtomicCapture>(verbatim("CAPTURE"_tok),211        Parser<AccClauseList>{} / endAccLine, statement(assignmentStmt),212        statement(assignmentStmt), Parser<AccEndAtomic>{} / endAccLine))213 214TYPE_PARSER(215    sourced(construct<OpenACCAtomicConstruct>(Parser<AccAtomicRead>{}) ||216        construct<OpenACCAtomicConstruct>(Parser<AccAtomicCapture>{}) ||217        construct<OpenACCAtomicConstruct>(Parser<AccAtomicWrite>{}) ||218        construct<OpenACCAtomicConstruct>(Parser<AccAtomicUpdate>{})))219 220// 2.13 Declare constructs221TYPE_PARSER(sourced(construct<AccDeclarativeDirective>(222    first("DECLARE" >> pure(llvm::acc::Directive::ACCD_declare)))))223 224// [Clause, [Clause], ...]225TYPE_PARSER(sourced(construct<AccClauseList>(226    many(maybe(","_tok) >> sourced(Parser<AccClause>{})))))227 228// 2.16.3 Wait directive229TYPE_PARSER(sourced(construct<OpenACCWaitConstruct>(230    sourced(construct<Verbatim>("WAIT"_tok)),231    maybe(parenthesized(Parser<AccWaitArgument>{})), Parser<AccClauseList>{})))232 233// Block Constructs234TYPE_PARSER(sourced(construct<AccBeginBlockDirective>(235    sourced(Parser<AccBlockDirective>{}), Parser<AccClauseList>{})))236 237TYPE_PARSER(startAccLine >> sourced(construct<AccEndBlockDirective>("END"_tok >>238                                recovery(sourced(Parser<AccBlockDirective>{}),239                                    construct<AccBlockDirective>(pure(240                                        llvm::acc::Directive::ACCD_data))))))241 242TYPE_PARSER(construct<OpenACCBlockConstruct>(243    Parser<AccBeginBlockDirective>{} / endAccLine, block,244    // NB, This allows mismatched directives, but semantics checks that they245    // match.246    recovery(withMessage("expected OpenACC end block directive"_err_en_US,247                 attempt(Parser<AccEndBlockDirective>{} / endAccLine)),248        construct<AccEndBlockDirective>(construct<AccBlockDirective>(249            pure(llvm::acc::Directive::ACCD_data))))))250 251// Standalone constructs252TYPE_PARSER(sourced(construct<OpenACCStandaloneConstruct>(253    Parser<AccStandaloneDirective>{}, Parser<AccClauseList>{})))254 255// Standalone declarative constructs256TYPE_PARSER(sourced(construct<OpenACCStandaloneDeclarativeConstruct>(257    Parser<AccDeclarativeDirective>{}, Parser<AccClauseList>{})))258 259TYPE_PARSER(startAccLine >>260    withMessage("expected OpenACC directive"_err_en_US,261        sourced(first(construct<OpenACCDeclarativeConstruct>(262                          Parser<OpenACCStandaloneDeclarativeConstruct>{}),263            construct<OpenACCDeclarativeConstruct>(264                Parser<OpenACCRoutineConstruct>{})))))265 266TYPE_PARSER(sourced(construct<OpenACCEndConstruct>(267    "END"_tok >> "LOOP"_tok >> pure(llvm::acc::Directive::ACCD_loop))))268 269// OpenACC constructs270TYPE_CONTEXT_PARSER("OpenACC construct"_en_US,271    startAccLine >>272        withMessage("expected OpenACC directive"_err_en_US,273            // Combined constructs before block constructs so we try to match274            // the longest possible match first.275            first(276                construct<OpenACCConstruct>(Parser<OpenACCCombinedConstruct>{}),277                construct<OpenACCConstruct>(Parser<OpenACCBlockConstruct>{}),278                construct<OpenACCConstruct>(Parser<OpenACCLoopConstruct>{}),279                construct<OpenACCConstruct>(280                    Parser<OpenACCStandaloneConstruct>{}),281                construct<OpenACCConstruct>(Parser<OpenACCCacheConstruct>{}),282                construct<OpenACCConstruct>(Parser<OpenACCWaitConstruct>{}),283                construct<OpenACCConstruct>(Parser<OpenACCAtomicConstruct>{}),284                construct<OpenACCConstruct>(Parser<OpenACCEndConstruct>{}))))285 286TYPE_PARSER(startAccLine >>287    sourced(construct<AccEndCombinedDirective>(sourced("END"_tok >>288        construct<AccCombinedDirective>("KERNELS"_tok >> maybe("LOOP"_tok) >>289                pure(llvm::acc::Directive::ACCD_kernels_loop) ||290            "PARALLEL"_tok >> maybe("LOOP"_tok) >>291                pure(llvm::acc::Directive::ACCD_parallel_loop) ||292            "SERIAL"_tok >> maybe("LOOP"_tok) >>293                pure(llvm::acc::Directive::ACCD_serial_loop))))))294 295TYPE_PARSER(sourced(construct<OpenACCCombinedConstruct>(296    Parser<AccBeginCombinedDirective>{} / endAccLine,297    maybe(Parser<DoConstruct>{}),298    maybe(Parser<AccEndCombinedDirective>{} / endAccLine))))299 300} // namespace Fortran::parser301