2020-02-25 23:11:52 +08:00
|
|
|
//===-- lib/Parser/unparse.cpp --------------------------------------------===//
|
2018-05-02 03:50:34 +08:00
|
|
|
//
|
2019-12-21 04:52:07 +08:00
|
|
|
// Part of the LLVM Project, under the Apache License v2.0 with LLVM Exceptions.
|
|
|
|
// See https://llvm.org/LICENSE.txt for license information.
|
|
|
|
// SPDX-License-Identifier: Apache-2.0 WITH LLVM-exception
|
2018-05-02 03:50:34 +08:00
|
|
|
//
|
2020-01-11 04:12:03 +08:00
|
|
|
//===----------------------------------------------------------------------===//
|
2018-05-02 03:50:34 +08:00
|
|
|
|
2018-03-01 08:56:10 +08:00
|
|
|
// Generates Fortran from the content of a parse tree, using the
|
|
|
|
// traversal templates in parse-tree-visitor.h.
|
|
|
|
|
2020-02-25 23:11:52 +08:00
|
|
|
#include "flang/Parser/unparse.h"
|
|
|
|
#include "flang/Common/Fortran.h"
|
|
|
|
#include "flang/Common/idioms.h"
|
|
|
|
#include "flang/Common/indirection.h"
|
|
|
|
#include "flang/Parser/characters.h"
|
|
|
|
#include "flang/Parser/parse-tree-visitor.h"
|
|
|
|
#include "flang/Parser/parse-tree.h"
|
2020-02-28 23:11:03 +08:00
|
|
|
#include "llvm/Support/raw_ostream.h"
|
2018-03-01 08:56:10 +08:00
|
|
|
#include <algorithm>
|
2018-03-21 01:59:07 +08:00
|
|
|
#include <cinttypes>
|
|
|
|
#include <cstddef>
|
2018-03-31 06:23:37 +08:00
|
|
|
#include <set>
|
2018-02-27 06:28:32 +08:00
|
|
|
|
2018-05-03 04:48:12 +08:00
|
|
|
namespace Fortran::parser {
|
2018-02-27 06:28:32 +08:00
|
|
|
|
|
|
|
class UnparseVisitor {
|
|
|
|
public:
|
2020-02-28 23:11:03 +08:00
|
|
|
UnparseVisitor(llvm::raw_ostream &out, int indentationAmount,
|
|
|
|
Encoding encoding, bool capitalize, bool backslashEscapes,
|
|
|
|
preStatementType *preStatement, AnalyzedObjectsAsFortran *asFortran)
|
2020-03-29 12:00:16 +08:00
|
|
|
: out_{out}, indentationAmount_{indentationAmount}, encoding_{encoding},
|
|
|
|
capitalizeKeywords_{capitalize}, backslashEscapes_{backslashEscapes},
|
|
|
|
preStatement_{preStatement}, asFortran_{asFortran} {}
|
2018-02-27 06:28:32 +08:00
|
|
|
|
2018-04-07 04:13:20 +08:00
|
|
|
// In nearly all cases, this code avoids defining Boolean-valued Pre()
|
|
|
|
// callbacks for the parse tree walking framework in favor of two void
|
|
|
|
// functions, Before() and Unparse(), which imply true and false return
|
|
|
|
// values for Pre() respectively.
|
2020-03-29 12:00:16 +08:00
|
|
|
template <typename T> void Before(const T &) {}
|
|
|
|
template <typename T> double Unparse(const T &); // not void, never used
|
2018-04-07 04:13:20 +08:00
|
|
|
|
2020-03-29 12:00:16 +08:00
|
|
|
template <typename T> bool Pre(const T &x) {
|
2018-04-27 06:44:29 +08:00
|
|
|
if constexpr (std::is_void_v<decltype(Unparse(x))>) {
|
|
|
|
// There is a local definition of Unparse() for this type. It
|
|
|
|
// overrides the parse tree walker's default Walk() over the descendents.
|
|
|
|
Before(x);
|
|
|
|
Unparse(x);
|
|
|
|
Post(x);
|
2020-03-29 12:00:16 +08:00
|
|
|
return false; // Walk() does not visit descendents
|
2018-04-27 06:44:29 +08:00
|
|
|
} else {
|
|
|
|
Before(x);
|
2020-03-29 12:00:16 +08:00
|
|
|
return true; // there's no Unparse() defined here, Walk() the descendents
|
2018-04-27 06:44:29 +08:00
|
|
|
}
|
2018-04-07 04:13:20 +08:00
|
|
|
}
|
2020-03-29 12:00:16 +08:00
|
|
|
template <typename T> void Post(const T &) {}
|
2018-02-27 06:28:32 +08:00
|
|
|
|
|
|
|
// Emit simple types as-is.
|
2018-04-07 04:13:20 +08:00
|
|
|
void Unparse(const std::string &x) { Put(x); }
|
|
|
|
void Unparse(int x) { Put(std::to_string(x)); }
|
2018-10-10 22:24:27 +08:00
|
|
|
void Unparse(unsigned int x) { Put(std::to_string(x)); }
|
|
|
|
void Unparse(long x) { Put(std::to_string(x)); }
|
|
|
|
void Unparse(unsigned long x) { Put(std::to_string(x)); }
|
|
|
|
void Unparse(long long x) { Put(std::to_string(x)); }
|
|
|
|
void Unparse(unsigned long long x) { Put(std::to_string(x)); }
|
2018-04-07 04:13:20 +08:00
|
|
|
void Unparse(char x) { Put(x); }
|
2018-03-01 08:56:10 +08:00
|
|
|
|
|
|
|
// Statement labels and ends of lines
|
2020-03-29 12:00:16 +08:00
|
|
|
template <typename T> void Before(const Statement<T> &x) {
|
2018-06-27 06:01:42 +08:00
|
|
|
if (preStatement_) {
|
|
|
|
(*preStatement_)(x.source, out_, indent_);
|
|
|
|
}
|
2018-03-01 08:56:10 +08:00
|
|
|
Walk(x.label, " ");
|
|
|
|
}
|
2020-03-29 12:00:16 +08:00
|
|
|
template <typename T> void Post(const Statement<T> &) { Put('\n'); }
|
2018-03-01 08:56:10 +08:00
|
|
|
|
|
|
|
// The special-case formatting functions for these productions are
|
|
|
|
// ordered to correspond roughly to their order of appearance in
|
|
|
|
// the Fortran 2018 standard (and parse-tree.h).
|
|
|
|
|
2020-03-29 12:00:16 +08:00
|
|
|
void Unparse(const Program &x) { // R501
|
|
|
|
Walk("", x.v, "\n"); // put blank lines between ProgramUnits
|
2018-03-01 08:56:10 +08:00
|
|
|
}
|
2018-03-21 01:59:07 +08:00
|
|
|
|
2020-03-29 12:00:16 +08:00
|
|
|
void Unparse(const Name &x) { // R603
|
2018-03-24 05:18:59 +08:00
|
|
|
Put(x.ToString());
|
2018-03-21 01:59:07 +08:00
|
|
|
}
|
2020-03-29 12:00:16 +08:00
|
|
|
void Unparse(const DefinedOperator::IntrinsicOperator &x) { // R608
|
2018-03-01 08:56:10 +08:00
|
|
|
switch (x) {
|
2020-03-29 12:00:16 +08:00
|
|
|
case DefinedOperator::IntrinsicOperator::Power:
|
|
|
|
Put("**");
|
|
|
|
break;
|
|
|
|
case DefinedOperator::IntrinsicOperator::Multiply:
|
|
|
|
Put('*');
|
|
|
|
break;
|
|
|
|
case DefinedOperator::IntrinsicOperator::Divide:
|
|
|
|
Put('/');
|
|
|
|
break;
|
|
|
|
case DefinedOperator::IntrinsicOperator::Add:
|
|
|
|
Put('+');
|
|
|
|
break;
|
|
|
|
case DefinedOperator::IntrinsicOperator::Subtract:
|
|
|
|
Put('-');
|
|
|
|
break;
|
|
|
|
case DefinedOperator::IntrinsicOperator::Concat:
|
|
|
|
Put("//");
|
|
|
|
break;
|
|
|
|
case DefinedOperator::IntrinsicOperator::LT:
|
|
|
|
Put('<');
|
|
|
|
break;
|
|
|
|
case DefinedOperator::IntrinsicOperator::LE:
|
|
|
|
Put("<=");
|
|
|
|
break;
|
|
|
|
case DefinedOperator::IntrinsicOperator::EQ:
|
|
|
|
Put("==");
|
|
|
|
break;
|
|
|
|
case DefinedOperator::IntrinsicOperator::NE:
|
|
|
|
Put("/=");
|
|
|
|
break;
|
|
|
|
case DefinedOperator::IntrinsicOperator::GE:
|
|
|
|
Put(">=");
|
|
|
|
break;
|
|
|
|
case DefinedOperator::IntrinsicOperator::GT:
|
|
|
|
Put('>');
|
|
|
|
break;
|
|
|
|
default:
|
|
|
|
Put('.'), Word(DefinedOperator::EnumToString(x)), Put('.');
|
2018-03-01 08:56:10 +08:00
|
|
|
}
|
|
|
|
}
|
2020-03-29 12:00:16 +08:00
|
|
|
void Post(const Star &) { Put('*'); } // R701 &c.
|
|
|
|
void Post(const TypeParamValue::Deferred &) { Put(':'); } // R701
|
|
|
|
void Unparse(const DeclarationTypeSpec::Type &x) { // R703
|
2018-03-15 06:31:16 +08:00
|
|
|
Word("TYPE("), Walk(x.derived), Put(')');
|
2018-03-01 08:56:10 +08:00
|
|
|
}
|
2018-04-07 04:13:20 +08:00
|
|
|
void Unparse(const DeclarationTypeSpec::Class &x) {
|
2018-03-15 06:31:16 +08:00
|
|
|
Word("CLASS("), Walk(x.derived), Put(')');
|
2018-03-01 08:56:10 +08:00
|
|
|
}
|
2018-03-15 06:31:16 +08:00
|
|
|
void Post(const DeclarationTypeSpec::ClassStar &) { Word("CLASS(*)"); }
|
|
|
|
void Post(const DeclarationTypeSpec::TypeStar &) { Word("TYPE(*)"); }
|
2018-04-07 04:13:20 +08:00
|
|
|
void Unparse(const DeclarationTypeSpec::Record &x) {
|
2018-03-15 06:31:16 +08:00
|
|
|
Word("RECORD/"), Walk(x.v), Put('/');
|
2018-03-01 08:56:10 +08:00
|
|
|
}
|
2020-03-29 12:00:16 +08:00
|
|
|
void Before(const IntrinsicTypeSpec::Real &) { // R704
|
2018-03-15 06:31:16 +08:00
|
|
|
Word("REAL");
|
2018-03-01 08:56:10 +08:00
|
|
|
}
|
2019-08-16 04:50:27 +08:00
|
|
|
void Before(const IntrinsicTypeSpec::Complex &) { Word("COMPLEX"); }
|
2018-03-01 08:56:10 +08:00
|
|
|
void Post(const IntrinsicTypeSpec::DoublePrecision &) {
|
2018-03-15 06:31:16 +08:00
|
|
|
Word("DOUBLE PRECISION");
|
2018-03-01 08:56:10 +08:00
|
|
|
}
|
2019-08-16 04:50:27 +08:00
|
|
|
void Before(const IntrinsicTypeSpec::Character &) { Word("CHARACTER"); }
|
|
|
|
void Before(const IntrinsicTypeSpec::Logical &) { Word("LOGICAL"); }
|
2018-03-15 06:31:16 +08:00
|
|
|
void Post(const IntrinsicTypeSpec::DoubleComplex &) {
|
|
|
|
Word("DOUBLE COMPLEX");
|
|
|
|
}
|
2020-03-29 12:00:16 +08:00
|
|
|
void Before(const IntegerTypeSpec &) { // R705
|
2018-03-15 06:31:16 +08:00
|
|
|
Word("INTEGER");
|
2018-03-01 08:56:10 +08:00
|
|
|
}
|
2020-03-29 12:00:16 +08:00
|
|
|
void Unparse(const KindSelector &x) { // R706
|
2018-03-01 08:56:10 +08:00
|
|
|
std::visit(
|
2018-11-30 01:27:34 +08:00
|
|
|
common::visitors{
|
|
|
|
[&](const ScalarIntConstantExpr &y) {
|
|
|
|
Put('('), Word("KIND="), Walk(y), Put(')');
|
|
|
|
},
|
|
|
|
[&](const KindSelector::StarSize &y) { Put('*'), Walk(y.v); },
|
|
|
|
},
|
2018-03-01 08:56:10 +08:00
|
|
|
x.u);
|
|
|
|
}
|
2020-03-29 12:00:16 +08:00
|
|
|
void Unparse(const SignedIntLiteralConstant &x) { // R707
|
2019-03-23 05:27:18 +08:00
|
|
|
Put(std::get<CharBlock>(x.t).ToString());
|
2018-03-01 08:56:10 +08:00
|
|
|
Walk("_", std::get<std::optional<KindParam>>(x.t));
|
|
|
|
}
|
2020-03-29 12:00:16 +08:00
|
|
|
void Unparse(const IntLiteralConstant &x) { // R708
|
2019-03-23 05:27:18 +08:00
|
|
|
Put(std::get<CharBlock>(x.t).ToString());
|
2018-03-01 08:56:10 +08:00
|
|
|
Walk("_", std::get<std::optional<KindParam>>(x.t));
|
|
|
|
}
|
2020-03-29 12:00:16 +08:00
|
|
|
void Unparse(const Sign &x) { // R712
|
2018-03-01 08:56:10 +08:00
|
|
|
Put(x == Sign::Negative ? '-' : '+');
|
|
|
|
}
|
2020-03-29 12:00:16 +08:00
|
|
|
void Unparse(const RealLiteralConstant &x) { // R714, R715
|
2018-03-21 01:59:07 +08:00
|
|
|
Put(x.real.source.ToString()), Walk("_", x.kind);
|
2018-03-01 08:56:10 +08:00
|
|
|
}
|
2020-03-29 12:00:16 +08:00
|
|
|
void Unparse(const ComplexLiteralConstant &x) { // R718 - R720
|
2018-03-01 08:56:10 +08:00
|
|
|
Put('('), Walk(x.t, ","), Put(')');
|
|
|
|
}
|
2020-03-29 12:00:16 +08:00
|
|
|
void Unparse(const CharSelector::LengthAndKind &x) { // R721
|
2018-03-15 06:31:16 +08:00
|
|
|
Put('('), Word("KIND="), Walk(x.kind);
|
|
|
|
Walk(", LEN=", x.length), Put(')');
|
2018-03-01 08:56:10 +08:00
|
|
|
}
|
2020-03-29 12:00:16 +08:00
|
|
|
void Unparse(const LengthSelector &x) { // R722
|
|
|
|
std::visit(common::visitors{
|
|
|
|
[&](const TypeParamValue &y) {
|
|
|
|
Put('('), Word("LEN="), Walk(y), Put(')');
|
|
|
|
},
|
|
|
|
[&](const CharLength &y) { Put('*'), Walk(y); },
|
|
|
|
},
|
2018-03-01 08:56:10 +08:00
|
|
|
x.u);
|
|
|
|
}
|
2020-03-29 12:00:16 +08:00
|
|
|
void Unparse(const CharLength &x) { // R723
|
2018-11-30 01:27:34 +08:00
|
|
|
std::visit(
|
|
|
|
common::visitors{
|
|
|
|
[&](const TypeParamValue &y) { Put('('), Walk(y), Put(')'); },
|
|
|
|
[&](const std::int64_t &y) { Walk(y); },
|
|
|
|
},
|
2018-03-01 08:56:10 +08:00
|
|
|
x.u);
|
|
|
|
}
|
2020-03-29 12:00:16 +08:00
|
|
|
void Unparse(const CharLiteralConstant &x) { // R724
|
2019-06-19 03:34:23 +08:00
|
|
|
const auto &str{std::get<std::string>(x.t)};
|
2018-07-11 08:09:07 +08:00
|
|
|
if (const auto &k{std::get<std::optional<KindParam>>(x.t)}) {
|
2019-06-29 02:16:37 +08:00
|
|
|
Walk(*k), Put('_');
|
2018-03-01 08:56:10 +08:00
|
|
|
}
|
2019-06-29 02:16:37 +08:00
|
|
|
PutNormalized(str);
|
2018-03-01 08:56:10 +08:00
|
|
|
}
|
2019-06-15 06:44:32 +08:00
|
|
|
void Unparse(const HollerithLiteralConstant &x) {
|
2019-06-29 02:16:37 +08:00
|
|
|
auto ucs{DecodeString<std::u32string, Encoding::UTF_8>(x.v, false)};
|
2019-06-15 06:44:32 +08:00
|
|
|
Unparse(ucs.size());
|
2018-03-01 08:56:10 +08:00
|
|
|
Put('H');
|
2019-06-19 03:34:23 +08:00
|
|
|
for (char32_t ch : ucs) {
|
2019-06-15 06:44:32 +08:00
|
|
|
EncodedCharacter encoded{EncodeCharacter(encoding_, ch)};
|
|
|
|
for (int j{0}; j < encoded.bytes; ++j) {
|
|
|
|
Put(encoded.buffer[j]);
|
|
|
|
}
|
|
|
|
}
|
2018-03-01 08:56:10 +08:00
|
|
|
}
|
2020-03-29 12:00:16 +08:00
|
|
|
void Unparse(const LogicalLiteralConstant &x) { // R725
|
2018-03-16 01:59:46 +08:00
|
|
|
Put(std::get<bool>(x.t) ? ".TRUE." : ".FALSE.");
|
|
|
|
Walk("_", std::get<std::optional<KindParam>>(x.t));
|
2018-03-01 08:56:10 +08:00
|
|
|
}
|
2020-03-29 12:00:16 +08:00
|
|
|
void Unparse(const DerivedTypeStmt &x) { // R727
|
2018-03-15 06:31:16 +08:00
|
|
|
Word("TYPE"), Walk(", ", std::get<std::list<TypeAttrSpec>>(x.t), ", ");
|
2018-03-21 01:59:07 +08:00
|
|
|
Put(" :: "), Walk(std::get<Name>(x.t));
|
2018-03-01 08:56:10 +08:00
|
|
|
Walk("(", std::get<std::list<Name>>(x.t), ", ", ")");
|
|
|
|
Indent();
|
|
|
|
}
|
2020-03-29 12:00:16 +08:00
|
|
|
void Unparse(const Abstract &) { // R728, &c.
|
2018-03-15 06:31:16 +08:00
|
|
|
Word("ABSTRACT");
|
2018-03-01 08:56:10 +08:00
|
|
|
}
|
2018-03-15 07:31:41 +08:00
|
|
|
void Post(const TypeAttrSpec::BindC &) { Word("BIND(C)"); }
|
2018-04-07 04:13:20 +08:00
|
|
|
void Unparse(const TypeAttrSpec::Extends &x) {
|
2018-03-15 06:31:16 +08:00
|
|
|
Word("EXTENDS("), Walk(x.v), Put(')');
|
2018-03-01 08:56:10 +08:00
|
|
|
}
|
2020-03-29 12:00:16 +08:00
|
|
|
void Unparse(const EndTypeStmt &x) { // R730
|
2018-03-15 06:31:16 +08:00
|
|
|
Outdent(), Word("END TYPE"), Walk(" ", x.v);
|
2018-03-01 08:56:10 +08:00
|
|
|
}
|
2020-03-29 12:00:16 +08:00
|
|
|
void Unparse(const SequenceStmt &) { // R731
|
2018-03-15 06:31:16 +08:00
|
|
|
Word("SEQUENCE");
|
2018-03-01 08:56:10 +08:00
|
|
|
}
|
2020-03-29 12:00:16 +08:00
|
|
|
void Unparse(const TypeParamDefStmt &x) { // R732
|
2018-03-01 08:56:10 +08:00
|
|
|
Walk(std::get<IntegerTypeSpec>(x.t));
|
2018-09-06 07:02:41 +08:00
|
|
|
Put(", "), Walk(std::get<common::TypeParamAttr>(x.t));
|
2018-03-01 08:56:10 +08:00
|
|
|
Put(" :: "), Walk(std::get<std::list<TypeParamDecl>>(x.t), ", ");
|
|
|
|
}
|
2020-03-29 12:00:16 +08:00
|
|
|
void Unparse(const TypeParamDecl &x) { // R733
|
2018-03-21 01:59:07 +08:00
|
|
|
Walk(std::get<Name>(x.t));
|
2018-03-01 08:56:10 +08:00
|
|
|
Walk("=", std::get<std::optional<ScalarIntConstantExpr>>(x.t));
|
|
|
|
}
|
2020-03-29 12:00:16 +08:00
|
|
|
void Unparse(const DataComponentDefStmt &x) { // R737
|
2018-07-11 08:09:07 +08:00
|
|
|
const auto &dts{std::get<DeclarationTypeSpec>(x.t)};
|
|
|
|
const auto &attrs{std::get<std::list<ComponentAttrSpec>>(x.t)};
|
|
|
|
const auto &decls{std::get<std::list<ComponentDecl>>(x.t)};
|
2018-03-01 08:56:10 +08:00
|
|
|
Walk(dts), Walk(", ", attrs, ", ");
|
|
|
|
if (!attrs.empty() ||
|
|
|
|
(!std::holds_alternative<DeclarationTypeSpec::Record>(dts.u) &&
|
|
|
|
std::none_of(
|
|
|
|
decls.begin(), decls.end(), [](const ComponentDecl &d) {
|
2018-07-11 08:09:07 +08:00
|
|
|
const auto &init{
|
|
|
|
std::get<std::optional<Initialization>>(d.t)};
|
2019-11-10 01:29:31 +08:00
|
|
|
return init &&
|
2018-03-01 08:56:10 +08:00
|
|
|
std::holds_alternative<
|
2018-06-19 02:03:43 +08:00
|
|
|
std::list<common::Indirection<DataStmtValue>>>(
|
|
|
|
init->u);
|
2018-03-01 08:56:10 +08:00
|
|
|
}))) {
|
|
|
|
Put(" ::");
|
|
|
|
}
|
|
|
|
Put(' '), Walk(decls, ", ");
|
|
|
|
}
|
2020-03-29 12:00:16 +08:00
|
|
|
void Unparse(const Allocatable &) { // R738
|
2018-03-15 06:31:16 +08:00
|
|
|
Word("ALLOCATABLE");
|
2018-03-01 08:56:10 +08:00
|
|
|
}
|
2019-08-16 04:50:27 +08:00
|
|
|
void Unparse(const Pointer &) { Word("POINTER"); }
|
|
|
|
void Unparse(const Contiguous &) { Word("CONTIGUOUS"); }
|
2018-04-07 04:13:20 +08:00
|
|
|
void Before(const ComponentAttrSpec &x) {
|
2020-03-29 12:00:16 +08:00
|
|
|
std::visit(common::visitors{
|
|
|
|
[&](const CoarraySpec &) { Word("CODIMENSION["); },
|
|
|
|
[&](const ComponentArraySpec &) { Word("DIMENSION("); },
|
|
|
|
[](const auto &) {},
|
|
|
|
},
|
2018-03-01 08:56:10 +08:00
|
|
|
x.u);
|
|
|
|
}
|
|
|
|
void Post(const ComponentAttrSpec &x) {
|
2020-03-29 12:00:16 +08:00
|
|
|
std::visit(common::visitors{
|
|
|
|
[&](const CoarraySpec &) { Put(']'); },
|
|
|
|
[&](const ComponentArraySpec &) { Put(')'); },
|
|
|
|
[](const auto &) {},
|
|
|
|
},
|
2018-03-01 08:56:10 +08:00
|
|
|
x.u);
|
|
|
|
}
|
2020-03-29 12:00:16 +08:00
|
|
|
void Unparse(const ComponentDecl &x) { // R739
|
2018-03-01 08:56:10 +08:00
|
|
|
Walk(std::get<ObjectName>(x.t));
|
|
|
|
Walk("(", std::get<std::optional<ComponentArraySpec>>(x.t), ")");
|
|
|
|
Walk("[", std::get<std::optional<CoarraySpec>>(x.t), "]");
|
|
|
|
Walk("*", std::get<std::optional<CharLength>>(x.t));
|
|
|
|
Walk(std::get<std::optional<Initialization>>(x.t));
|
|
|
|
}
|
2020-03-29 12:00:16 +08:00
|
|
|
void Unparse(const ComponentArraySpec &x) { // R740
|
|
|
|
std::visit(common::visitors{
|
|
|
|
[&](const std::list<ExplicitShapeSpec> &y) { Walk(y, ","); },
|
|
|
|
[&](const DeferredShapeSpecList &y) { Walk(y); },
|
|
|
|
},
|
2018-03-01 08:56:10 +08:00
|
|
|
x.u);
|
|
|
|
}
|
2020-03-29 12:00:16 +08:00
|
|
|
void Unparse(const ProcComponentDefStmt &x) { // R741
|
2018-03-15 06:31:16 +08:00
|
|
|
Word("PROCEDURE(");
|
2018-03-01 08:56:10 +08:00
|
|
|
Walk(std::get<std::optional<ProcInterface>>(x.t)), Put(')');
|
|
|
|
Walk(", ", std::get<std::list<ProcComponentAttrSpec>>(x.t), ", ");
|
|
|
|
Put(" :: "), Walk(std::get<std::list<ProcDecl>>(x.t), ", ");
|
|
|
|
}
|
2020-03-29 12:00:16 +08:00
|
|
|
void Unparse(const NoPass &) { // R742
|
2018-03-15 06:31:16 +08:00
|
|
|
Word("NOPASS");
|
2018-03-01 08:56:10 +08:00
|
|
|
}
|
2018-04-07 04:13:20 +08:00
|
|
|
void Unparse(const Pass &x) { Word("PASS"), Walk("(", x.v, ")"); }
|
2020-03-29 12:00:16 +08:00
|
|
|
void Unparse(const Initialization &x) { // R743 & R805
|
|
|
|
std::visit(common::visitors{
|
|
|
|
[&](const ConstantExpr &y) { Put(" = "), Walk(y); },
|
|
|
|
[&](const NullInit &y) { Put(" => "), Walk(y); },
|
|
|
|
[&](const InitialDataTarget &y) { Put(" => "), Walk(y); },
|
|
|
|
[&](const std::list<common::Indirection<DataStmtValue>> &y) {
|
|
|
|
Walk("/", y, ", ", "/");
|
|
|
|
},
|
|
|
|
},
|
2018-03-01 08:56:10 +08:00
|
|
|
x.u);
|
|
|
|
}
|
2020-03-29 12:00:16 +08:00
|
|
|
void Unparse(const PrivateStmt &) { // R745
|
2018-03-15 06:31:16 +08:00
|
|
|
Word("PRIVATE");
|
2018-03-01 08:56:10 +08:00
|
|
|
}
|
2020-03-29 12:00:16 +08:00
|
|
|
void Unparse(const TypeBoundProcedureStmt::WithoutInterface &x) { // R749
|
2018-03-15 06:31:16 +08:00
|
|
|
Word("PROCEDURE"), Walk(", ", x.attributes, ", ");
|
2018-03-16 07:03:28 +08:00
|
|
|
Put(" :: "), Walk(x.declarations, ", ");
|
2018-03-01 08:56:10 +08:00
|
|
|
}
|
2018-04-07 04:13:20 +08:00
|
|
|
void Unparse(const TypeBoundProcedureStmt::WithInterface &x) {
|
2018-03-15 06:31:16 +08:00
|
|
|
Word("PROCEDURE("), Walk(x.interfaceName), Put("), ");
|
2018-03-01 08:56:10 +08:00
|
|
|
Walk(x.attributes);
|
2018-03-16 07:03:28 +08:00
|
|
|
Put(" :: "), Walk(x.bindingNames, ", ");
|
2018-03-01 08:56:10 +08:00
|
|
|
}
|
2020-03-29 12:00:16 +08:00
|
|
|
void Unparse(const TypeBoundProcDecl &x) { // R750
|
2018-03-01 08:56:10 +08:00
|
|
|
Walk(std::get<Name>(x.t));
|
|
|
|
Walk(" => ", std::get<std::optional<Name>>(x.t));
|
|
|
|
}
|
2020-03-29 12:00:16 +08:00
|
|
|
void Unparse(const TypeBoundGenericStmt &x) { // R751
|
2018-03-15 06:31:16 +08:00
|
|
|
Word("GENERIC"), Walk(", ", std::get<std::optional<AccessSpec>>(x.t));
|
2018-06-19 02:03:43 +08:00
|
|
|
Put(" :: "), Walk(std::get<common::Indirection<GenericSpec>>(x.t));
|
2018-03-01 08:56:10 +08:00
|
|
|
Put(" => "), Walk(std::get<std::list<Name>>(x.t), ", ");
|
|
|
|
}
|
2020-03-29 12:00:16 +08:00
|
|
|
void Post(const BindAttr::Deferred &) { Word("DEFERRED"); } // R752
|
2018-03-15 06:31:16 +08:00
|
|
|
void Post(const BindAttr::Non_Overridable &) { Word("NON_OVERRIDABLE"); }
|
2020-03-29 12:00:16 +08:00
|
|
|
void Unparse(const FinalProcedureStmt &x) { // R753
|
2018-03-15 08:02:21 +08:00
|
|
|
Word("FINAL :: "), Walk(x.v, ", ");
|
2018-03-15 06:31:16 +08:00
|
|
|
}
|
2020-03-29 12:00:16 +08:00
|
|
|
void Unparse(const DerivedTypeSpec &x) { // R754
|
2018-03-01 08:56:10 +08:00
|
|
|
Walk(std::get<Name>(x.t));
|
|
|
|
Walk("(", std::get<std::list<TypeParamSpec>>(x.t), ",", ")");
|
|
|
|
}
|
2020-03-29 12:00:16 +08:00
|
|
|
void Unparse(const TypeParamSpec &x) { // R755
|
2018-03-01 08:56:10 +08:00
|
|
|
Walk(std::get<std::optional<Keyword>>(x.t), "=");
|
|
|
|
Walk(std::get<TypeParamValue>(x.t));
|
|
|
|
}
|
2020-03-29 12:00:16 +08:00
|
|
|
void Unparse(const StructureConstructor &x) { // R756
|
2018-03-01 08:56:10 +08:00
|
|
|
Walk(std::get<DerivedTypeSpec>(x.t));
|
|
|
|
Put('('), Walk(std::get<std::list<ComponentSpec>>(x.t), ", "), Put(')');
|
|
|
|
}
|
2020-03-29 12:00:16 +08:00
|
|
|
void Unparse(const ComponentSpec &x) { // R757
|
2018-03-01 08:56:10 +08:00
|
|
|
Walk(std::get<std::optional<Keyword>>(x.t), "=");
|
|
|
|
Walk(std::get<ComponentDataSource>(x.t));
|
|
|
|
}
|
2020-03-29 12:00:16 +08:00
|
|
|
void Unparse(const EnumDefStmt &) { // R760
|
2018-03-15 08:02:21 +08:00
|
|
|
Word("ENUM, BIND(C)"), Indent();
|
2018-03-01 08:56:10 +08:00
|
|
|
}
|
2020-03-29 12:00:16 +08:00
|
|
|
void Unparse(const EnumeratorDefStmt &x) { // R761
|
2018-03-15 08:02:21 +08:00
|
|
|
Word("ENUMERATOR :: "), Walk(x.v, ", ");
|
2018-03-01 08:56:10 +08:00
|
|
|
}
|
2020-03-29 12:00:16 +08:00
|
|
|
void Unparse(const Enumerator &x) { // R762
|
2018-03-01 08:56:10 +08:00
|
|
|
Walk(std::get<NamedConstant>(x.t));
|
|
|
|
Walk(" = ", std::get<std::optional<ScalarIntConstantExpr>>(x.t));
|
|
|
|
}
|
2020-03-29 12:00:16 +08:00
|
|
|
void Post(const EndEnumStmt &) { // R763
|
2018-03-15 08:02:21 +08:00
|
|
|
Outdent(), Word("END ENUM");
|
2018-03-01 08:56:10 +08:00
|
|
|
}
|
2020-03-29 12:00:16 +08:00
|
|
|
void Unparse(const BOZLiteralConstant &x) { // R764 - R767
|
2018-08-09 07:30:58 +08:00
|
|
|
Put(x.v);
|
2018-03-01 08:56:10 +08:00
|
|
|
}
|
2020-03-29 12:00:16 +08:00
|
|
|
void Unparse(const AcValue::Triplet &x) { // R773
|
2018-03-01 08:56:10 +08:00
|
|
|
Walk(std::get<0>(x.t)), Put(':'), Walk(std::get<1>(x.t));
|
|
|
|
Walk(":", std::get<std::optional<ScalarIntExpr>>(x.t));
|
|
|
|
}
|
2020-03-29 12:00:16 +08:00
|
|
|
void Unparse(const ArrayConstructor &x) { // R769
|
2018-03-01 08:56:10 +08:00
|
|
|
Put('['), Walk(x.v), Put(']');
|
|
|
|
}
|
2020-03-29 12:00:16 +08:00
|
|
|
void Unparse(const AcSpec &x) { // R770
|
2018-03-01 08:56:10 +08:00
|
|
|
Walk(x.type, "::"), Walk(x.values, ", ");
|
|
|
|
}
|
2020-03-29 12:00:16 +08:00
|
|
|
template <typename A, typename B> void Unparse(const LoopBounds<A, B> &x) {
|
2018-03-01 08:56:10 +08:00
|
|
|
Walk(x.name), Put('='), Walk(x.lower), Put(','), Walk(x.upper);
|
|
|
|
Walk(",", x.step);
|
|
|
|
}
|
2020-03-29 12:00:16 +08:00
|
|
|
void Unparse(const AcImpliedDo &x) { // R774
|
2018-03-14 08:11:26 +08:00
|
|
|
Put('('), Walk(std::get<std::list<AcValue>>(x.t), ", ");
|
|
|
|
Put(", "), Walk(std::get<AcImpliedDoControl>(x.t)), Put(')');
|
|
|
|
}
|
2020-03-29 12:00:16 +08:00
|
|
|
void Unparse(const AcImpliedDoControl &x) { // R775
|
2018-03-01 08:56:10 +08:00
|
|
|
Walk(std::get<std::optional<IntegerTypeSpec>>(x.t), "::");
|
2019-05-09 23:32:27 +08:00
|
|
|
Walk(std::get<AcImpliedDoControl::Bounds>(x.t));
|
2018-03-01 08:56:10 +08:00
|
|
|
}
|
|
|
|
|
2020-03-29 12:00:16 +08:00
|
|
|
void Unparse(const TypeDeclarationStmt &x) { // R801
|
2018-07-11 08:09:07 +08:00
|
|
|
const auto &dts{std::get<DeclarationTypeSpec>(x.t)};
|
|
|
|
const auto &attrs{std::get<std::list<AttrSpec>>(x.t)};
|
|
|
|
const auto &decls{std::get<std::list<EntityDecl>>(x.t)};
|
2018-03-01 08:56:10 +08:00
|
|
|
Walk(dts), Walk(", ", attrs, ", ");
|
2018-03-20 07:17:23 +08:00
|
|
|
|
2018-07-11 08:09:07 +08:00
|
|
|
static const auto isInitializerOldStyle{[](const Initialization &i) {
|
2018-06-19 02:03:43 +08:00
|
|
|
return std::holds_alternative<
|
|
|
|
std::list<common::Indirection<DataStmtValue>>>(i.u);
|
2018-07-11 08:09:07 +08:00
|
|
|
}};
|
|
|
|
static const auto hasAssignmentInitializer{[](const EntityDecl &d) {
|
2018-03-20 07:17:23 +08:00
|
|
|
// Does a declaration have a new-style =x initializer?
|
2018-07-11 08:09:07 +08:00
|
|
|
const auto &init{std::get<std::optional<Initialization>>(d.t)};
|
2019-11-10 01:29:31 +08:00
|
|
|
return init && !isInitializerOldStyle(*init);
|
2018-07-11 08:09:07 +08:00
|
|
|
}};
|
|
|
|
static const auto hasSlashDelimitedInitializer{[](const EntityDecl &d) {
|
2018-03-20 07:17:23 +08:00
|
|
|
// Does a declaration have an old-style /x/ initializer?
|
2018-07-11 08:09:07 +08:00
|
|
|
const auto &init{std::get<std::optional<Initialization>>(d.t)};
|
2019-11-10 01:29:31 +08:00
|
|
|
return init && isInitializerOldStyle(*init);
|
2018-07-11 08:09:07 +08:00
|
|
|
}};
|
|
|
|
const auto useDoubledColons{[&]() {
|
2018-03-20 07:17:23 +08:00
|
|
|
bool isRecord{std::holds_alternative<DeclarationTypeSpec::Record>(dts.u)};
|
|
|
|
if (!attrs.empty()) {
|
|
|
|
// Attributes after the type require :: before the entities.
|
|
|
|
CHECK(!isRecord);
|
|
|
|
return true;
|
|
|
|
}
|
|
|
|
if (std::any_of(decls.begin(), decls.end(), hasAssignmentInitializer)) {
|
|
|
|
// Always use :: with new style standard initializers (=x),
|
|
|
|
// since the standard requires them to appear (even in free form,
|
|
|
|
// where mandatory spaces already disambiguate INTEGER J=666).
|
|
|
|
CHECK(!isRecord);
|
|
|
|
return true;
|
|
|
|
}
|
|
|
|
if (isRecord) {
|
|
|
|
// Never put :: in a legacy extension RECORD// statement.
|
|
|
|
return false;
|
|
|
|
}
|
|
|
|
// The :: is optional for this declaration. Avoid usage that can
|
|
|
|
// crash the pgf90 compiler.
|
|
|
|
if (std::any_of(
|
|
|
|
decls.begin(), decls.end(), hasSlashDelimitedInitializer)) {
|
|
|
|
// Don't use :: when a declaration uses legacy DATA-statement-like
|
|
|
|
// /x/ initialization.
|
|
|
|
return false;
|
|
|
|
}
|
|
|
|
// Don't use :: with intrinsic types. Otherwise, use it.
|
|
|
|
return !std::holds_alternative<IntrinsicTypeSpec>(dts.u);
|
2018-07-11 08:09:07 +08:00
|
|
|
}};
|
2018-03-20 07:17:23 +08:00
|
|
|
|
|
|
|
if (useDoubledColons()) {
|
|
|
|
Put(" ::");
|
2018-03-01 08:56:10 +08:00
|
|
|
}
|
|
|
|
Put(' '), Walk(std::get<std::list<EntityDecl>>(x.t), ", ");
|
|
|
|
}
|
2020-03-29 12:00:16 +08:00
|
|
|
void Before(const AttrSpec &x) { // R802
|
|
|
|
std::visit(common::visitors{
|
|
|
|
[&](const CoarraySpec &) { Word("CODIMENSION["); },
|
|
|
|
[&](const ArraySpec &) { Word("DIMENSION("); },
|
|
|
|
[](const auto &) {},
|
|
|
|
},
|
2018-03-14 07:59:30 +08:00
|
|
|
x.u);
|
|
|
|
}
|
|
|
|
void Post(const AttrSpec &x) {
|
2020-03-29 12:00:16 +08:00
|
|
|
std::visit(common::visitors{
|
|
|
|
[&](const CoarraySpec &) { Put(']'); },
|
|
|
|
[&](const ArraySpec &) { Put(')'); },
|
|
|
|
[](const auto &) {},
|
|
|
|
},
|
2018-03-14 07:59:30 +08:00
|
|
|
x.u);
|
|
|
|
}
|
2020-03-29 12:00:16 +08:00
|
|
|
void Unparse(const EntityDecl &x) { // R803
|
2018-03-01 08:56:10 +08:00
|
|
|
Walk(std::get<ObjectName>(x.t));
|
|
|
|
Walk("(", std::get<std::optional<ArraySpec>>(x.t), ")");
|
|
|
|
Walk("[", std::get<std::optional<CoarraySpec>>(x.t), "]");
|
|
|
|
Walk("*", std::get<std::optional<CharLength>>(x.t));
|
|
|
|
Walk(std::get<std::optional<Initialization>>(x.t));
|
|
|
|
}
|
2020-03-29 12:00:16 +08:00
|
|
|
void Unparse(const NullInit &) { // R806
|
2018-03-15 06:31:16 +08:00
|
|
|
Word("NULL()");
|
2018-03-01 08:56:10 +08:00
|
|
|
}
|
2020-03-29 12:00:16 +08:00
|
|
|
void Unparse(const LanguageBindingSpec &x) { // R808 & R1528
|
2018-03-15 06:31:16 +08:00
|
|
|
Word("BIND(C"), Walk(", NAME=", x.v), Put(')');
|
2018-03-01 08:56:10 +08:00
|
|
|
}
|
2020-03-29 12:00:16 +08:00
|
|
|
void Unparse(const CoarraySpec &x) { // R809
|
|
|
|
std::visit(common::visitors{
|
|
|
|
[&](const DeferredCoshapeSpecList &y) { Walk(y); },
|
|
|
|
[&](const ExplicitCoshapeSpec &y) { Walk(y); },
|
|
|
|
},
|
2018-03-01 08:56:10 +08:00
|
|
|
x.u);
|
|
|
|
}
|
2020-03-29 12:00:16 +08:00
|
|
|
void Unparse(const DeferredCoshapeSpecList &x) { // R810
|
2018-07-11 08:09:07 +08:00
|
|
|
for (auto j{x.v}; j > 0; --j) {
|
2018-03-01 08:56:10 +08:00
|
|
|
Put(':');
|
|
|
|
if (j > 1) {
|
|
|
|
Put(',');
|
|
|
|
}
|
|
|
|
}
|
|
|
|
}
|
2020-03-29 12:00:16 +08:00
|
|
|
void Unparse(const ExplicitCoshapeSpec &x) { // R811
|
2018-03-01 08:56:10 +08:00
|
|
|
Walk(std::get<std::list<ExplicitShapeSpec>>(x.t), ",", ",");
|
|
|
|
Walk(std::get<std::optional<SpecificationExpr>>(x.t), ":"), Put('*');
|
|
|
|
}
|
2020-03-29 12:00:16 +08:00
|
|
|
void Unparse(const ExplicitShapeSpec &x) { // R812 - R813 & R816 - R818
|
2018-03-01 08:56:10 +08:00
|
|
|
Walk(std::get<std::optional<SpecificationExpr>>(x.t), ":");
|
|
|
|
Walk(std::get<SpecificationExpr>(x.t));
|
|
|
|
}
|
2020-03-29 12:00:16 +08:00
|
|
|
void Unparse(const ArraySpec &x) { // R815
|
|
|
|
std::visit(common::visitors{
|
|
|
|
[&](const std::list<ExplicitShapeSpec> &y) { Walk(y, ","); },
|
|
|
|
[&](const std::list<AssumedShapeSpec> &y) { Walk(y, ","); },
|
|
|
|
[&](const DeferredShapeSpecList &y) { Walk(y); },
|
|
|
|
[&](const AssumedSizeSpec &y) { Walk(y); },
|
|
|
|
[&](const ImpliedShapeSpec &y) { Walk(y); },
|
|
|
|
[&](const AssumedRankSpec &y) { Walk(y); },
|
|
|
|
},
|
2018-03-01 08:56:10 +08:00
|
|
|
x.u);
|
|
|
|
}
|
2020-03-29 12:00:16 +08:00
|
|
|
void Post(const AssumedShapeSpec &) { Put(':'); } // R819
|
|
|
|
void Unparse(const DeferredShapeSpecList &x) { // R820
|
2018-07-11 08:09:07 +08:00
|
|
|
for (auto j{x.v}; j > 0; --j) {
|
2018-03-01 08:56:10 +08:00
|
|
|
Put(':');
|
|
|
|
if (j > 1) {
|
|
|
|
Put(',');
|
|
|
|
}
|
|
|
|
}
|
|
|
|
}
|
2020-03-29 12:00:16 +08:00
|
|
|
void Unparse(const AssumedImpliedSpec &x) { // R821
|
2018-03-01 08:56:10 +08:00
|
|
|
Walk(x.v, ":");
|
|
|
|
Put('*');
|
|
|
|
}
|
2020-03-29 12:00:16 +08:00
|
|
|
void Unparse(const AssumedSizeSpec &x) { // R822
|
2018-03-01 08:56:10 +08:00
|
|
|
Walk(std::get<std::list<ExplicitShapeSpec>>(x.t), ",", ",");
|
|
|
|
Walk(std::get<AssumedImpliedSpec>(x.t));
|
|
|
|
}
|
2020-03-29 12:00:16 +08:00
|
|
|
void Unparse(const ImpliedShapeSpec &x) { // R823
|
2018-03-01 08:56:10 +08:00
|
|
|
Walk(x.v, ",");
|
|
|
|
}
|
2020-03-29 12:00:16 +08:00
|
|
|
void Post(const AssumedRankSpec &) { Put(".."); } // R825
|
2018-03-15 06:31:16 +08:00
|
|
|
void Post(const Asynchronous &) { Word("ASYNCHRONOUS"); }
|
|
|
|
void Post(const External &) { Word("EXTERNAL"); }
|
|
|
|
void Post(const Intrinsic &) { Word("INTRINSIC"); }
|
|
|
|
void Post(const Optional &) { Word("OPTIONAL"); }
|
|
|
|
void Post(const Parameter &) { Word("PARAMETER"); }
|
|
|
|
void Post(const Protected &) { Word("PROTECTED"); }
|
|
|
|
void Post(const Save &) { Word("SAVE"); }
|
|
|
|
void Post(const Target &) { Word("TARGET"); }
|
|
|
|
void Post(const Value &) { Word("VALUE"); }
|
|
|
|
void Post(const Volatile &) { Word("VOLATILE"); }
|
2020-03-29 12:00:16 +08:00
|
|
|
void Unparse(const IntentSpec &x) { // R826
|
2018-03-15 06:31:16 +08:00
|
|
|
Word("INTENT("), Walk(x.v), Put(")");
|
2018-03-01 08:56:10 +08:00
|
|
|
}
|
2020-03-29 12:00:16 +08:00
|
|
|
void Unparse(const AccessStmt &x) { // R827
|
2018-03-01 08:56:10 +08:00
|
|
|
Walk(std::get<AccessSpec>(x.t));
|
|
|
|
Walk(" :: ", std::get<std::list<AccessId>>(x.t), ", ");
|
|
|
|
}
|
2020-03-29 12:00:16 +08:00
|
|
|
void Unparse(const AllocatableStmt &x) { // R829
|
2018-03-15 06:31:16 +08:00
|
|
|
Word("ALLOCATABLE :: "), Walk(x.v, ", ");
|
2018-03-01 08:56:10 +08:00
|
|
|
}
|
2020-03-29 12:00:16 +08:00
|
|
|
void Unparse(const ObjectDecl &x) { // R830 & R860
|
2018-03-01 08:56:10 +08:00
|
|
|
Walk(std::get<ObjectName>(x.t));
|
|
|
|
Walk("(", std::get<std::optional<ArraySpec>>(x.t), ")");
|
|
|
|
Walk("[", std::get<std::optional<CoarraySpec>>(x.t), "]");
|
|
|
|
}
|
2020-03-29 12:00:16 +08:00
|
|
|
void Unparse(const AsynchronousStmt &x) { // R831
|
2018-03-15 06:31:16 +08:00
|
|
|
Word("ASYNCHRONOUS :: "), Walk(x.v, ", ");
|
2018-03-01 08:56:10 +08:00
|
|
|
}
|
2020-03-29 12:00:16 +08:00
|
|
|
void Unparse(const BindStmt &x) { // R832
|
2018-03-01 08:56:10 +08:00
|
|
|
Walk(x.t, " :: ");
|
|
|
|
}
|
2020-03-29 12:00:16 +08:00
|
|
|
void Unparse(const BindEntity &x) { // R833
|
2018-03-01 08:56:10 +08:00
|
|
|
bool isCommon{std::get<BindEntity::Kind>(x.t) == BindEntity::Kind::Common};
|
|
|
|
const char *slash{isCommon ? "/" : ""};
|
|
|
|
Put(slash), Walk(std::get<Name>(x.t)), Put(slash);
|
|
|
|
}
|
2020-03-29 12:00:16 +08:00
|
|
|
void Unparse(const CodimensionStmt &x) { // R834
|
2018-03-15 06:31:16 +08:00
|
|
|
Word("CODIMENSION :: "), Walk(x.v, ", ");
|
2018-03-01 08:56:10 +08:00
|
|
|
}
|
2020-03-29 12:00:16 +08:00
|
|
|
void Unparse(const CodimensionDecl &x) { // R835
|
2018-03-01 08:56:10 +08:00
|
|
|
Walk(std::get<Name>(x.t));
|
|
|
|
Put('['), Walk(std::get<CoarraySpec>(x.t)), Put(']');
|
|
|
|
}
|
2020-03-29 12:00:16 +08:00
|
|
|
void Unparse(const ContiguousStmt &x) { // R836
|
2018-03-15 06:31:16 +08:00
|
|
|
Word("CONTIGUOUS :: "), Walk(x.v, ", ");
|
2018-03-01 08:56:10 +08:00
|
|
|
}
|
2020-03-29 12:00:16 +08:00
|
|
|
void Unparse(const DataStmt &x) { // R837
|
2018-03-15 06:31:16 +08:00
|
|
|
Word("DATA "), Walk(x.v, ", ");
|
2018-03-01 08:56:10 +08:00
|
|
|
}
|
2020-03-29 12:00:16 +08:00
|
|
|
void Unparse(const DataStmtSet &x) { // R838
|
2018-03-01 08:56:10 +08:00
|
|
|
Walk(std::get<std::list<DataStmtObject>>(x.t), ", ");
|
|
|
|
Put('/'), Walk(std::get<std::list<DataStmtValue>>(x.t), ", "), Put('/');
|
|
|
|
}
|
2020-03-29 12:00:16 +08:00
|
|
|
void Unparse(const DataImpliedDo &x) { // R840, R842
|
2018-03-15 06:31:16 +08:00
|
|
|
Put('('), Walk(std::get<std::list<DataIDoObject>>(x.t), ", "), Put(',');
|
2018-03-01 08:56:10 +08:00
|
|
|
Walk(std::get<std::optional<IntegerTypeSpec>>(x.t), "::");
|
2019-05-09 23:32:27 +08:00
|
|
|
Walk(std::get<DataImpliedDo::Bounds>(x.t)), Put(')');
|
2018-03-01 08:56:10 +08:00
|
|
|
}
|
2020-03-29 12:00:16 +08:00
|
|
|
void Unparse(const DataStmtValue &x) { // R843
|
2018-03-01 08:56:10 +08:00
|
|
|
Walk(std::get<std::optional<DataStmtRepeat>>(x.t), "*");
|
|
|
|
Walk(std::get<DataStmtConstant>(x.t));
|
|
|
|
}
|
2020-03-29 12:00:16 +08:00
|
|
|
void Unparse(const DimensionStmt &x) { // R848
|
2018-03-15 06:31:16 +08:00
|
|
|
Word("DIMENSION :: "), Walk(x.v, ", ");
|
2018-03-01 08:56:10 +08:00
|
|
|
}
|
2018-04-07 04:13:20 +08:00
|
|
|
void Unparse(const DimensionStmt::Declaration &x) {
|
2018-03-01 08:56:10 +08:00
|
|
|
Walk(std::get<Name>(x.t));
|
|
|
|
Put('('), Walk(std::get<ArraySpec>(x.t)), Put(')');
|
|
|
|
}
|
2020-03-29 12:00:16 +08:00
|
|
|
void Unparse(const IntentStmt &x) { // R849
|
2018-03-01 08:56:10 +08:00
|
|
|
Walk(x.t, " :: ");
|
|
|
|
}
|
2020-03-29 12:00:16 +08:00
|
|
|
void Unparse(const OptionalStmt &x) { // R850
|
2018-03-15 06:31:16 +08:00
|
|
|
Word("OPTIONAL :: "), Walk(x.v, ", ");
|
2018-03-01 08:56:10 +08:00
|
|
|
}
|
2020-03-29 12:00:16 +08:00
|
|
|
void Unparse(const ParameterStmt &x) { // R851
|
2018-03-15 06:31:16 +08:00
|
|
|
Word("PARAMETER("), Walk(x.v, ", "), Put(')');
|
2018-03-01 08:56:10 +08:00
|
|
|
}
|
2020-03-29 12:00:16 +08:00
|
|
|
void Unparse(const NamedConstantDef &x) { // R852
|
2018-03-01 08:56:10 +08:00
|
|
|
Walk(x.t, "=");
|
|
|
|
}
|
2020-03-29 12:00:16 +08:00
|
|
|
void Unparse(const PointerStmt &x) { // R853
|
2018-04-10 04:40:20 +08:00
|
|
|
Word("POINTER :: "), Walk(x.v, ", ");
|
|
|
|
}
|
2020-03-29 12:00:16 +08:00
|
|
|
void Unparse(const PointerDecl &x) { // R854
|
2018-04-10 04:40:20 +08:00
|
|
|
Walk(std::get<Name>(x.t));
|
|
|
|
Walk("(", std::get<std::optional<DeferredShapeSpecList>>(x.t), ")");
|
2018-03-01 08:56:10 +08:00
|
|
|
}
|
2020-03-29 12:00:16 +08:00
|
|
|
void Unparse(const ProtectedStmt &x) { // R855
|
2018-03-15 06:31:16 +08:00
|
|
|
Word("PROTECTED :: "), Walk(x.v, ", ");
|
2018-03-01 08:56:10 +08:00
|
|
|
}
|
2020-03-29 12:00:16 +08:00
|
|
|
void Unparse(const SaveStmt &x) { // R856
|
2018-03-15 06:31:16 +08:00
|
|
|
Word("SAVE"), Walk(" :: ", x.v, ", ");
|
2018-03-01 08:56:10 +08:00
|
|
|
}
|
2020-03-29 12:00:16 +08:00
|
|
|
void Unparse(const SavedEntity &x) { // R857, R858
|
2018-03-01 08:56:10 +08:00
|
|
|
bool isCommon{
|
|
|
|
std::get<SavedEntity::Kind>(x.t) == SavedEntity::Kind::Common};
|
|
|
|
const char *slash{isCommon ? "/" : ""};
|
|
|
|
Put(slash), Walk(std::get<Name>(x.t)), Put(slash);
|
|
|
|
}
|
2020-03-29 12:00:16 +08:00
|
|
|
void Unparse(const TargetStmt &x) { // R859
|
2018-03-15 06:31:16 +08:00
|
|
|
Word("TARGET :: "), Walk(x.v, ", ");
|
2018-03-01 08:56:10 +08:00
|
|
|
}
|
2020-03-29 12:00:16 +08:00
|
|
|
void Unparse(const ValueStmt &x) { // R861
|
2018-03-15 06:31:16 +08:00
|
|
|
Word("VALUE :: "), Walk(x.v, ", ");
|
2018-03-01 08:56:10 +08:00
|
|
|
}
|
2020-03-29 12:00:16 +08:00
|
|
|
void Unparse(const VolatileStmt &x) { // R862
|
2018-03-15 06:31:16 +08:00
|
|
|
Word("VOLATILE :: "), Walk(x.v, ", ");
|
2018-03-01 08:56:10 +08:00
|
|
|
}
|
2020-03-29 12:00:16 +08:00
|
|
|
void Unparse(const ImplicitStmt &x) { // R863
|
2018-03-15 06:31:16 +08:00
|
|
|
Word("IMPLICIT ");
|
2020-03-29 12:00:16 +08:00
|
|
|
std::visit(common::visitors{
|
|
|
|
[&](const std::list<ImplicitSpec> &y) { Walk(y, ", "); },
|
|
|
|
[&](const std::list<ImplicitStmt::ImplicitNoneNameSpec> &y) {
|
|
|
|
Word("NONE"), Walk(" (", y, ", ", ")");
|
|
|
|
},
|
|
|
|
},
|
2018-03-01 08:56:10 +08:00
|
|
|
x.u);
|
|
|
|
}
|
2020-03-29 12:00:16 +08:00
|
|
|
void Unparse(const ImplicitSpec &x) { // R864
|
2018-03-01 08:56:10 +08:00
|
|
|
Walk(std::get<DeclarationTypeSpec>(x.t));
|
|
|
|
Put('('), Walk(std::get<std::list<LetterSpec>>(x.t), ", "), Put(')');
|
|
|
|
}
|
2020-03-29 12:00:16 +08:00
|
|
|
void Unparse(const LetterSpec &x) { // R865
|
2018-03-21 01:59:07 +08:00
|
|
|
Put(*std::get<const char *>(x.t));
|
2018-07-11 08:09:07 +08:00
|
|
|
auto second{std::get<std::optional<const char *>>(x.t)};
|
2019-11-10 01:29:31 +08:00
|
|
|
if (second) {
|
2018-03-21 01:59:07 +08:00
|
|
|
Put('-'), Put(**second);
|
|
|
|
}
|
2018-03-01 08:56:10 +08:00
|
|
|
}
|
2020-03-29 12:00:16 +08:00
|
|
|
void Unparse(const ImportStmt &x) { // R867
|
2018-03-15 06:31:16 +08:00
|
|
|
Word("IMPORT");
|
2018-03-01 08:56:10 +08:00
|
|
|
switch (x.kind) {
|
2020-03-29 12:00:16 +08:00
|
|
|
case common::ImportKind::Default:
|
|
|
|
Walk(" :: ", x.names, ", ");
|
|
|
|
break;
|
2018-08-24 02:45:49 +08:00
|
|
|
case common::ImportKind::Only:
|
2018-03-15 06:31:16 +08:00
|
|
|
Put(", "), Word("ONLY: ");
|
2018-03-16 07:03:28 +08:00
|
|
|
Walk(x.names, ", ");
|
2018-03-01 08:56:10 +08:00
|
|
|
break;
|
2020-03-29 12:00:16 +08:00
|
|
|
case common::ImportKind::None:
|
|
|
|
Word(", NONE");
|
|
|
|
break;
|
|
|
|
case common::ImportKind::All:
|
|
|
|
Word(", ALL");
|
|
|
|
break;
|
2018-03-01 08:56:10 +08:00
|
|
|
}
|
|
|
|
}
|
2020-03-29 12:00:16 +08:00
|
|
|
void Unparse(const NamelistStmt &x) { // R868
|
2018-03-15 06:31:16 +08:00
|
|
|
Word("NAMELIST"), Walk(x.v, ", ");
|
2018-03-01 08:56:10 +08:00
|
|
|
}
|
2018-04-07 04:13:20 +08:00
|
|
|
void Unparse(const NamelistStmt::Group &x) {
|
2018-03-21 01:59:07 +08:00
|
|
|
Put('/'), Walk(std::get<Name>(x.t)), Put('/');
|
2018-03-01 08:56:10 +08:00
|
|
|
Walk(std::get<std::list<Name>>(x.t), ", ");
|
|
|
|
}
|
2020-03-29 12:00:16 +08:00
|
|
|
void Unparse(const EquivalenceStmt &x) { // R870, R871
|
2018-03-15 06:31:16 +08:00
|
|
|
Word("EQUIVALENCE");
|
2018-03-01 08:56:10 +08:00
|
|
|
const char *separator{" "};
|
|
|
|
for (const std::list<EquivalenceObject> &y : x.v) {
|
|
|
|
Put(separator), Put('('), Walk(y), Put(')');
|
|
|
|
separator = ", ";
|
|
|
|
}
|
|
|
|
}
|
2020-03-29 12:00:16 +08:00
|
|
|
void Unparse(const CommonStmt &x) { // R873
|
2018-03-15 06:31:16 +08:00
|
|
|
Word("COMMON ");
|
2019-02-13 08:13:58 +08:00
|
|
|
Walk(x.blocks);
|
2018-03-01 08:56:10 +08:00
|
|
|
}
|
2020-03-29 12:00:16 +08:00
|
|
|
void Unparse(const CommonBlockObject &x) { // R874
|
2018-03-01 08:56:10 +08:00
|
|
|
Walk(std::get<Name>(x.t));
|
|
|
|
Walk("(", std::get<std::optional<ArraySpec>>(x.t), ")");
|
|
|
|
}
|
2018-04-07 04:13:20 +08:00
|
|
|
void Unparse(const CommonStmt::Block &x) {
|
2019-09-28 05:08:09 +08:00
|
|
|
Word("/"), Walk(std::get<std::optional<Name>>(x.t)), Word("/");
|
2018-03-01 08:56:10 +08:00
|
|
|
Walk(std::get<std::list<CommonBlockObject>>(x.t));
|
|
|
|
}
|
|
|
|
|
2020-03-29 12:00:16 +08:00
|
|
|
void Unparse(const Substring &x) { // R908, R909
|
2018-04-14 05:21:13 +08:00
|
|
|
Walk(std::get<DataRef>(x.t));
|
2018-03-01 08:56:10 +08:00
|
|
|
Put('('), Walk(std::get<SubstringRange>(x.t)), Put(')');
|
|
|
|
}
|
2018-04-07 04:13:20 +08:00
|
|
|
void Unparse(const CharLiteralConstantSubstring &x) {
|
2018-03-01 08:56:10 +08:00
|
|
|
Walk(std::get<CharLiteralConstant>(x.t));
|
|
|
|
Put('('), Walk(std::get<SubstringRange>(x.t)), Put(')');
|
|
|
|
}
|
2020-03-29 12:00:16 +08:00
|
|
|
void Unparse(const SubstringRange &x) { // R910
|
2018-03-01 08:56:10 +08:00
|
|
|
Walk(x.t, ":");
|
|
|
|
}
|
2020-03-29 12:00:16 +08:00
|
|
|
void Unparse(const PartRef &x) { // R912
|
2018-03-01 08:56:10 +08:00
|
|
|
Walk(x.name);
|
|
|
|
Walk("(", x.subscripts, ",", ")");
|
|
|
|
Walk(x.imageSelector);
|
|
|
|
}
|
2020-03-29 12:00:16 +08:00
|
|
|
void Unparse(const StructureComponent &x) { // R913
|
2018-03-31 06:23:37 +08:00
|
|
|
Walk(x.base);
|
|
|
|
if (structureComponents_.find(x.component.source) !=
|
|
|
|
structureComponents_.end()) {
|
|
|
|
Put('.');
|
|
|
|
} else {
|
|
|
|
Put('%');
|
|
|
|
}
|
|
|
|
Walk(x.component);
|
2018-03-01 08:56:10 +08:00
|
|
|
}
|
2020-03-29 12:00:16 +08:00
|
|
|
void Unparse(const ArrayElement &x) { // R917
|
2018-03-01 08:56:10 +08:00
|
|
|
Walk(x.base);
|
|
|
|
Put('('), Walk(x.subscripts, ","), Put(')');
|
|
|
|
}
|
2020-03-29 12:00:16 +08:00
|
|
|
void Unparse(const SubscriptTriplet &x) { // R921
|
2018-03-01 08:56:10 +08:00
|
|
|
Walk(std::get<0>(x.t)), Put(':'), Walk(std::get<1>(x.t));
|
|
|
|
Walk(":", std::get<2>(x.t));
|
|
|
|
}
|
2020-03-29 12:00:16 +08:00
|
|
|
void Unparse(const ImageSelector &x) { // R924
|
2018-03-01 08:56:10 +08:00
|
|
|
Put('['), Walk(std::get<std::list<Cosubscript>>(x.t), ",");
|
|
|
|
Walk(",", std::get<std::list<ImageSelectorSpec>>(x.t), ","), Put(']');
|
|
|
|
}
|
2020-03-29 12:00:16 +08:00
|
|
|
void Before(const ImageSelectorSpec::Stat &) { // R926
|
2018-03-15 06:31:16 +08:00
|
|
|
Word("STAT=");
|
2018-03-01 08:56:10 +08:00
|
|
|
}
|
2018-04-07 04:13:20 +08:00
|
|
|
void Before(const ImageSelectorSpec::Team_Number &) { Word("TEAM_NUMBER="); }
|
2019-04-16 06:53:18 +08:00
|
|
|
void Before(const ImageSelectorSpec &x) {
|
|
|
|
if (std::holds_alternative<TeamValue>(x.u)) {
|
|
|
|
Word("TEAM=");
|
|
|
|
}
|
|
|
|
}
|
2020-03-29 12:00:16 +08:00
|
|
|
void Unparse(const AllocateStmt &x) { // R927
|
2018-03-15 06:31:16 +08:00
|
|
|
Word("ALLOCATE(");
|
|
|
|
Walk(std::get<std::optional<TypeSpec>>(x.t), "::");
|
2018-03-01 08:56:10 +08:00
|
|
|
Walk(std::get<std::list<Allocation>>(x.t), ", ");
|
|
|
|
Walk(", ", std::get<std::list<AllocOpt>>(x.t), ", "), Put(')');
|
|
|
|
}
|
2020-03-29 12:00:16 +08:00
|
|
|
void Before(const AllocOpt &x) { // R928, R931
|
|
|
|
std::visit(common::visitors{
|
|
|
|
[&](const AllocOpt::Mold &) { Word("MOLD="); },
|
|
|
|
[&](const AllocOpt::Source &) { Word("SOURCE="); },
|
|
|
|
[](const StatOrErrmsg &) {},
|
|
|
|
},
|
2018-03-01 08:56:10 +08:00
|
|
|
x.u);
|
|
|
|
}
|
2020-03-29 12:00:16 +08:00
|
|
|
void Unparse(const Allocation &x) { // R932
|
2018-03-01 08:56:10 +08:00
|
|
|
Walk(std::get<AllocateObject>(x.t));
|
|
|
|
Walk("(", std::get<std::list<AllocateShapeSpec>>(x.t), ",", ")");
|
|
|
|
Walk("[", std::get<std::optional<AllocateCoarraySpec>>(x.t), "]");
|
|
|
|
}
|
2020-03-29 12:00:16 +08:00
|
|
|
void Unparse(const AllocateShapeSpec &x) { // R934 & R938
|
2018-03-01 08:56:10 +08:00
|
|
|
Walk(std::get<std::optional<BoundExpr>>(x.t), ":");
|
|
|
|
Walk(std::get<BoundExpr>(x.t));
|
|
|
|
}
|
2020-03-29 12:00:16 +08:00
|
|
|
void Unparse(const AllocateCoarraySpec &x) { // R937
|
2018-03-01 08:56:10 +08:00
|
|
|
Walk(std::get<std::list<AllocateCoshapeSpec>>(x.t), ",", ",");
|
|
|
|
Walk(std::get<std::optional<BoundExpr>>(x.t), ":"), Put('*');
|
|
|
|
}
|
2020-03-29 12:00:16 +08:00
|
|
|
void Unparse(const NullifyStmt &x) { // R939
|
2018-03-15 06:31:16 +08:00
|
|
|
Word("NULLIFY("), Walk(x.v, ", "), Put(')');
|
2018-03-01 08:56:10 +08:00
|
|
|
}
|
2020-03-29 12:00:16 +08:00
|
|
|
void Unparse(const DeallocateStmt &x) { // R941
|
2018-03-15 06:31:16 +08:00
|
|
|
Word("DEALLOCATE(");
|
|
|
|
Walk(std::get<std::list<AllocateObject>>(x.t), ", ");
|
2018-03-01 08:56:10 +08:00
|
|
|
Walk(", ", std::get<std::list<StatOrErrmsg>>(x.t), ", "), Put(')');
|
|
|
|
}
|
2020-03-29 12:00:16 +08:00
|
|
|
void Before(const StatOrErrmsg &x) { // R942 & R1165
|
|
|
|
std::visit(common::visitors{
|
|
|
|
[&](const StatVariable &) { Word("STAT="); },
|
|
|
|
[&](const MsgVariable &) { Word("ERRMSG="); },
|
|
|
|
},
|
2018-03-01 08:56:10 +08:00
|
|
|
x.u);
|
|
|
|
}
|
|
|
|
|
|
|
|
// R1001 - R1022
|
2019-06-05 07:25:06 +08:00
|
|
|
bool Pre(const Expr &x) {
|
2019-12-18 04:32:16 +08:00
|
|
|
if (asFortran_ && x.typedExpr) {
|
2019-06-05 07:25:06 +08:00
|
|
|
// Format the expression representation from semantics
|
2019-12-18 02:53:20 +08:00
|
|
|
asFortran_->expr(out_, *x.typedExpr);
|
2019-06-05 07:25:06 +08:00
|
|
|
return false;
|
|
|
|
} else {
|
|
|
|
return true;
|
|
|
|
}
|
|
|
|
}
|
2018-04-07 04:13:20 +08:00
|
|
|
void Unparse(const Expr::Parentheses &x) { Put('('), Walk(x.v), Put(')'); }
|
2019-08-16 04:50:27 +08:00
|
|
|
void Before(const Expr::UnaryPlus &) { Put("+"); }
|
|
|
|
void Before(const Expr::Negate &) { Put("-"); }
|
|
|
|
void Before(const Expr::NOT &) { Word(".NOT."); }
|
2018-04-07 04:13:20 +08:00
|
|
|
void Unparse(const Expr::PercentLoc &x) {
|
2018-03-15 06:31:16 +08:00
|
|
|
Word("%LOC("), Walk(x.v), Put(')');
|
2018-03-01 08:56:10 +08:00
|
|
|
}
|
2018-04-07 04:13:20 +08:00
|
|
|
void Unparse(const Expr::Power &x) { Walk(x.t, "**"); }
|
|
|
|
void Unparse(const Expr::Multiply &x) { Walk(x.t, "*"); }
|
|
|
|
void Unparse(const Expr::Divide &x) { Walk(x.t, "/"); }
|
|
|
|
void Unparse(const Expr::Add &x) { Walk(x.t, "+"); }
|
|
|
|
void Unparse(const Expr::Subtract &x) { Walk(x.t, "-"); }
|
|
|
|
void Unparse(const Expr::Concat &x) { Walk(x.t, "//"); }
|
|
|
|
void Unparse(const Expr::LT &x) { Walk(x.t, "<"); }
|
|
|
|
void Unparse(const Expr::LE &x) { Walk(x.t, "<="); }
|
|
|
|
void Unparse(const Expr::EQ &x) { Walk(x.t, "=="); }
|
|
|
|
void Unparse(const Expr::NE &x) { Walk(x.t, "/="); }
|
|
|
|
void Unparse(const Expr::GE &x) { Walk(x.t, ">="); }
|
|
|
|
void Unparse(const Expr::GT &x) { Walk(x.t, ">"); }
|
|
|
|
void Unparse(const Expr::AND &x) { Walk(x.t, ".AND."); }
|
|
|
|
void Unparse(const Expr::OR &x) { Walk(x.t, ".OR."); }
|
|
|
|
void Unparse(const Expr::EQV &x) { Walk(x.t, ".EQV."); }
|
|
|
|
void Unparse(const Expr::NEQV &x) { Walk(x.t, ".NEQV."); }
|
|
|
|
void Unparse(const Expr::ComplexConstructor &x) {
|
2018-03-01 08:56:10 +08:00
|
|
|
Put('('), Walk(x.t, ","), Put(')');
|
|
|
|
}
|
2018-04-07 04:13:20 +08:00
|
|
|
void Unparse(const Expr::DefinedBinary &x) {
|
2020-03-29 12:00:16 +08:00
|
|
|
Walk(std::get<1>(x.t)); // left
|
2018-03-01 08:56:10 +08:00
|
|
|
Walk(std::get<DefinedOpName>(x.t));
|
2020-03-29 12:00:16 +08:00
|
|
|
Walk(std::get<2>(x.t)); // right
|
2018-03-01 08:56:10 +08:00
|
|
|
}
|
2020-03-29 12:00:16 +08:00
|
|
|
void Unparse(const DefinedOpName &x) { // R1003, R1023, R1414, & R1415
|
2019-03-21 05:17:12 +08:00
|
|
|
Walk(x.v);
|
2018-03-01 08:56:10 +08:00
|
|
|
}
|
2020-03-29 12:00:16 +08:00
|
|
|
void Unparse(const AssignmentStmt &x) { // R1032
|
2019-12-18 02:53:20 +08:00
|
|
|
if (asFortran_ && x.typedAssignment.get()) {
|
2019-12-18 07:59:25 +08:00
|
|
|
Put(' ');
|
2019-12-18 02:53:20 +08:00
|
|
|
asFortran_->assignment(out_, *x.typedAssignment);
|
2019-12-18 07:59:25 +08:00
|
|
|
Put('\n');
|
2019-12-18 02:53:20 +08:00
|
|
|
} else {
|
|
|
|
Walk(x.t, " = ");
|
|
|
|
}
|
2018-03-01 08:56:10 +08:00
|
|
|
}
|
2020-03-29 12:00:16 +08:00
|
|
|
void Unparse(const PointerAssignmentStmt &x) { // R1033, R1034, R1038
|
2020-01-04 02:38:51 +08:00
|
|
|
if (asFortran_ && x.typedAssignment.get()) {
|
|
|
|
Put(' ');
|
|
|
|
asFortran_->assignment(out_, *x.typedAssignment);
|
|
|
|
Put('\n');
|
|
|
|
} else {
|
|
|
|
Walk(std::get<DataRef>(x.t));
|
|
|
|
std::visit(
|
|
|
|
common::visitors{
|
|
|
|
[&](const std::list<BoundsRemapping> &y) {
|
|
|
|
Put('('), Walk(y), Put(')');
|
|
|
|
},
|
|
|
|
[&](const std::list<BoundsSpec> &y) { Walk("(", y, ", ", ")"); },
|
|
|
|
},
|
|
|
|
std::get<PointerAssignmentStmt::Bounds>(x.t).u);
|
|
|
|
Put(" => "), Walk(std::get<Expr>(x.t));
|
|
|
|
}
|
2018-03-01 08:56:10 +08:00
|
|
|
}
|
2020-03-29 12:00:16 +08:00
|
|
|
void Post(const BoundsSpec &) { // R1035
|
2018-03-01 08:56:10 +08:00
|
|
|
Put(':');
|
|
|
|
}
|
2020-03-29 12:00:16 +08:00
|
|
|
void Unparse(const BoundsRemapping &x) { // R1036
|
2018-03-01 08:56:10 +08:00
|
|
|
Walk(x.t, ":");
|
|
|
|
}
|
2020-03-29 12:00:16 +08:00
|
|
|
void Unparse(const WhereStmt &x) { // R1041, R1045, R1046
|
2018-03-15 06:31:16 +08:00
|
|
|
Word("WHERE ("), Walk(x.t, ") ");
|
2018-03-01 08:56:10 +08:00
|
|
|
}
|
2020-03-29 12:00:16 +08:00
|
|
|
void Unparse(const WhereConstructStmt &x) { // R1043
|
2018-03-01 08:56:10 +08:00
|
|
|
Walk(std::get<std::optional<Name>>(x.t), ": ");
|
2018-03-15 06:31:16 +08:00
|
|
|
Word("WHERE ("), Walk(std::get<LogicalExpr>(x.t)), Put(')');
|
2018-03-01 08:56:10 +08:00
|
|
|
Indent();
|
|
|
|
}
|
2020-03-29 12:00:16 +08:00
|
|
|
void Unparse(const MaskedElsewhereStmt &x) { // R1047
|
2018-03-01 08:56:10 +08:00
|
|
|
Outdent();
|
2018-03-15 06:31:16 +08:00
|
|
|
Word("ELSEWHERE ("), Walk(std::get<LogicalExpr>(x.t)), Put(')');
|
2018-03-01 08:56:10 +08:00
|
|
|
Walk(" ", std::get<std::optional<Name>>(x.t));
|
|
|
|
Indent();
|
|
|
|
}
|
2020-03-29 12:00:16 +08:00
|
|
|
void Unparse(const ElsewhereStmt &x) { // R1048
|
2018-03-15 06:31:16 +08:00
|
|
|
Outdent(), Word("ELSEWHERE"), Walk(" ", x.v), Indent();
|
2018-03-01 08:56:10 +08:00
|
|
|
}
|
2020-03-29 12:00:16 +08:00
|
|
|
void Unparse(const EndWhereStmt &x) { // R1049
|
2018-03-15 06:31:16 +08:00
|
|
|
Outdent(), Word("END WHERE"), Walk(" ", x.v);
|
2018-03-01 08:56:10 +08:00
|
|
|
}
|
2020-03-29 12:00:16 +08:00
|
|
|
void Unparse(const ForallConstructStmt &x) { // R1051
|
2018-03-01 08:56:10 +08:00
|
|
|
Walk(std::get<std::optional<Name>>(x.t), ": ");
|
2018-06-19 02:03:43 +08:00
|
|
|
Word("FORALL"), Walk(std::get<common::Indirection<ConcurrentHeader>>(x.t));
|
2018-03-01 08:56:10 +08:00
|
|
|
Indent();
|
|
|
|
}
|
2020-03-29 12:00:16 +08:00
|
|
|
void Unparse(const EndForallStmt &x) { // R1054
|
2018-03-15 06:31:16 +08:00
|
|
|
Outdent(), Word("END FORALL"), Walk(" ", x.v);
|
2018-03-01 08:56:10 +08:00
|
|
|
}
|
2020-03-29 12:00:16 +08:00
|
|
|
void Before(const ForallStmt &) { // R1055
|
2018-03-15 06:31:16 +08:00
|
|
|
Word("FORALL");
|
2018-03-01 08:56:10 +08:00
|
|
|
}
|
|
|
|
|
2020-03-29 12:00:16 +08:00
|
|
|
void Unparse(const AssociateStmt &x) { // R1103
|
2018-03-01 08:56:10 +08:00
|
|
|
Walk(std::get<std::optional<Name>>(x.t), ": ");
|
2018-03-15 06:31:16 +08:00
|
|
|
Word("ASSOCIATE (");
|
|
|
|
Walk(std::get<std::list<Association>>(x.t), ", "), Put(')'), Indent();
|
2018-03-01 08:56:10 +08:00
|
|
|
}
|
2020-03-29 12:00:16 +08:00
|
|
|
void Unparse(const Association &x) { // R1104
|
2018-03-01 08:56:10 +08:00
|
|
|
Walk(x.t, " => ");
|
|
|
|
}
|
2020-03-29 12:00:16 +08:00
|
|
|
void Unparse(const EndAssociateStmt &x) { // R1106
|
2018-03-15 06:31:16 +08:00
|
|
|
Outdent(), Word("END ASSOCIATE"), Walk(" ", x.v);
|
2018-03-01 08:56:10 +08:00
|
|
|
}
|
2020-03-29 12:00:16 +08:00
|
|
|
void Unparse(const BlockStmt &x) { // R1108
|
2018-03-15 06:31:16 +08:00
|
|
|
Walk(x.v, ": "), Word("BLOCK"), Indent();
|
2018-03-01 08:56:10 +08:00
|
|
|
}
|
2020-03-29 12:00:16 +08:00
|
|
|
void Unparse(const EndBlockStmt &x) { // R1110
|
2018-03-15 06:31:16 +08:00
|
|
|
Outdent(), Word("END BLOCK"), Walk(" ", x.v);
|
2018-03-01 08:56:10 +08:00
|
|
|
}
|
2020-03-29 12:00:16 +08:00
|
|
|
void Unparse(const ChangeTeamStmt &x) { // R1112
|
2018-03-01 08:56:10 +08:00
|
|
|
Walk(std::get<std::optional<Name>>(x.t), ": ");
|
2019-04-07 02:17:07 +08:00
|
|
|
Word("CHANGE TEAM ("), Walk(std::get<TeamValue>(x.t));
|
2018-03-01 08:56:10 +08:00
|
|
|
Walk(", ", std::get<std::list<CoarrayAssociation>>(x.t), ", ");
|
|
|
|
Walk(", ", std::get<std::list<StatOrErrmsg>>(x.t), ", "), Put(')');
|
|
|
|
Indent();
|
|
|
|
}
|
2020-03-29 12:00:16 +08:00
|
|
|
void Unparse(const CoarrayAssociation &x) { // R1113
|
2018-03-01 08:56:10 +08:00
|
|
|
Walk(x.t, " => ");
|
|
|
|
}
|
2020-03-29 12:00:16 +08:00
|
|
|
void Unparse(const EndChangeTeamStmt &x) { // R1114
|
2018-03-15 06:31:16 +08:00
|
|
|
Outdent(), Word("END TEAM (");
|
2018-03-01 08:56:10 +08:00
|
|
|
Walk(std::get<std::list<StatOrErrmsg>>(x.t), ", ");
|
|
|
|
Put(')'), Walk(" ", std::get<std::optional<Name>>(x.t));
|
|
|
|
}
|
2020-03-29 12:00:16 +08:00
|
|
|
void Unparse(const CriticalStmt &x) { // R1117
|
2018-03-01 08:56:10 +08:00
|
|
|
Walk(std::get<std::optional<Name>>(x.t), ": ");
|
2018-03-15 06:31:16 +08:00
|
|
|
Word("CRITICAL ("), Walk(std::get<std::list<StatOrErrmsg>>(x.t), ", ");
|
2018-03-01 08:56:10 +08:00
|
|
|
Put(')'), Indent();
|
|
|
|
}
|
2020-03-29 12:00:16 +08:00
|
|
|
void Unparse(const EndCriticalStmt &x) { // R1118
|
2018-03-15 06:31:16 +08:00
|
|
|
Outdent(), Word("END CRITICAL"), Walk(" ", x.v);
|
2018-03-01 08:56:10 +08:00
|
|
|
}
|
2020-03-29 12:00:16 +08:00
|
|
|
void Unparse(const DoConstruct &x) { // R1119, R1120
|
2018-03-01 08:56:10 +08:00
|
|
|
Walk(std::get<Statement<NonLabelDoStmt>>(x.t));
|
|
|
|
Indent(), Walk(std::get<Block>(x.t), ""), Outdent();
|
|
|
|
Walk(std::get<Statement<EndDoStmt>>(x.t));
|
|
|
|
}
|
2020-03-29 12:00:16 +08:00
|
|
|
void Unparse(const LabelDoStmt &x) { // R1121
|
2018-03-01 08:56:10 +08:00
|
|
|
Walk(std::get<std::optional<Name>>(x.t), ": ");
|
2018-03-15 06:31:16 +08:00
|
|
|
Word("DO "), Walk(std::get<Label>(x.t));
|
2018-03-01 08:56:10 +08:00
|
|
|
Walk(" ", std::get<std::optional<LoopControl>>(x.t));
|
|
|
|
}
|
2020-03-29 12:00:16 +08:00
|
|
|
void Unparse(const NonLabelDoStmt &x) { // R1122
|
2018-03-01 08:56:10 +08:00
|
|
|
Walk(std::get<std::optional<Name>>(x.t), ": ");
|
2018-03-15 06:31:16 +08:00
|
|
|
Word("DO "), Walk(std::get<std::optional<LoopControl>>(x.t));
|
2018-03-01 08:56:10 +08:00
|
|
|
}
|
2020-03-29 12:00:16 +08:00
|
|
|
void Unparse(const LoopControl &x) { // R1123
|
|
|
|
std::visit(common::visitors{
|
|
|
|
[&](const ScalarLogicalExpr &y) {
|
|
|
|
Word("WHILE ("), Walk(y), Put(')');
|
|
|
|
},
|
|
|
|
[&](const auto &y) { Walk(y); },
|
|
|
|
},
|
2018-03-01 08:56:10 +08:00
|
|
|
x.u);
|
|
|
|
}
|
2020-03-29 12:00:16 +08:00
|
|
|
void Unparse(const ConcurrentHeader &x) { // R1125
|
2018-03-01 08:56:10 +08:00
|
|
|
Put('('), Walk(std::get<std::optional<IntegerTypeSpec>>(x.t), "::");
|
|
|
|
Walk(std::get<std::list<ConcurrentControl>>(x.t), ", ");
|
|
|
|
Walk(", ", std::get<std::optional<ScalarLogicalExpr>>(x.t)), Put(')');
|
|
|
|
}
|
2020-03-29 12:00:16 +08:00
|
|
|
void Unparse(const ConcurrentControl &x) { // R1126 - R1128
|
2018-03-01 08:56:10 +08:00
|
|
|
Walk(std::get<Name>(x.t)), Put('='), Walk(std::get<1>(x.t));
|
|
|
|
Put(':'), Walk(std::get<2>(x.t));
|
|
|
|
Walk(":", std::get<std::optional<ScalarIntExpr>>(x.t));
|
|
|
|
}
|
2020-03-29 12:00:16 +08:00
|
|
|
void Before(const LoopControl::Concurrent &) { // R1129
|
2018-03-15 06:31:16 +08:00
|
|
|
Word("CONCURRENT");
|
2018-03-01 08:56:10 +08:00
|
|
|
}
|
2018-04-07 04:13:20 +08:00
|
|
|
void Unparse(const LocalitySpec::Local &x) {
|
2018-03-15 06:31:16 +08:00
|
|
|
Word("LOCAL("), Walk(x.v, ", "), Put(')');
|
2018-03-01 08:56:10 +08:00
|
|
|
}
|
2018-04-07 04:13:20 +08:00
|
|
|
void Unparse(const LocalitySpec::LocalInit &x) {
|
2018-10-02 06:00:09 +08:00
|
|
|
Word("LOCAL_INIT("), Walk(x.v, ", "), Put(')');
|
2018-03-01 08:56:10 +08:00
|
|
|
}
|
2018-04-07 04:13:20 +08:00
|
|
|
void Unparse(const LocalitySpec::Shared &x) {
|
2018-03-15 06:31:16 +08:00
|
|
|
Word("SHARED("), Walk(x.v, ", "), Put(')');
|
2018-03-01 08:56:10 +08:00
|
|
|
}
|
2019-08-16 04:50:27 +08:00
|
|
|
void Post(const LocalitySpec::DefaultNone &) { Word("DEFAULT(NONE)"); }
|
2020-03-29 12:00:16 +08:00
|
|
|
void Unparse(const EndDoStmt &x) { // R1132
|
2018-03-15 06:31:16 +08:00
|
|
|
Word("END DO"), Walk(" ", x.v);
|
2018-03-01 08:56:10 +08:00
|
|
|
}
|
2020-03-29 12:00:16 +08:00
|
|
|
void Unparse(const CycleStmt &x) { // R1133
|
2018-03-15 06:31:16 +08:00
|
|
|
Word("CYCLE"), Walk(" ", x.v);
|
2018-03-01 08:56:10 +08:00
|
|
|
}
|
2020-03-29 12:00:16 +08:00
|
|
|
void Unparse(const IfThenStmt &x) { // R1135
|
2018-03-01 08:56:10 +08:00
|
|
|
Walk(std::get<std::optional<Name>>(x.t), ": ");
|
2018-03-15 06:31:16 +08:00
|
|
|
Word("IF ("), Walk(std::get<ScalarLogicalExpr>(x.t));
|
|
|
|
Put(") "), Word("THEN"), Indent();
|
2018-03-01 08:56:10 +08:00
|
|
|
}
|
2020-03-29 12:00:16 +08:00
|
|
|
void Unparse(const ElseIfStmt &x) { // R1136
|
2018-03-15 06:31:16 +08:00
|
|
|
Outdent(), Word("ELSE IF (");
|
|
|
|
Walk(std::get<ScalarLogicalExpr>(x.t)), Put(") "), Word("THEN");
|
|
|
|
Walk(" ", std::get<std::optional<Name>>(x.t)), Indent();
|
2018-03-01 08:56:10 +08:00
|
|
|
}
|
2020-03-29 12:00:16 +08:00
|
|
|
void Unparse(const ElseStmt &x) { // R1137
|
2018-03-15 06:31:16 +08:00
|
|
|
Outdent(), Word("ELSE"), Walk(" ", x.v), Indent();
|
2018-03-01 08:56:10 +08:00
|
|
|
}
|
2020-03-29 12:00:16 +08:00
|
|
|
void Unparse(const EndIfStmt &x) { // R1138
|
2018-03-15 06:31:16 +08:00
|
|
|
Outdent(), Word("END IF"), Walk(" ", x.v);
|
2018-03-01 08:56:10 +08:00
|
|
|
}
|
2020-03-29 12:00:16 +08:00
|
|
|
void Unparse(const IfStmt &x) { // R1139
|
2018-03-15 06:31:16 +08:00
|
|
|
Word("IF ("), Walk(x.t, ") ");
|
2018-03-01 08:56:10 +08:00
|
|
|
}
|
2020-03-29 12:00:16 +08:00
|
|
|
void Unparse(const SelectCaseStmt &x) { // R1141, R1144
|
2018-03-01 08:56:10 +08:00
|
|
|
Walk(std::get<std::optional<Name>>(x.t), ": ");
|
2018-03-15 06:31:16 +08:00
|
|
|
Word("SELECT CASE (");
|
|
|
|
Walk(std::get<Scalar<Expr>>(x.t)), Put(')'), Indent();
|
2018-03-01 08:56:10 +08:00
|
|
|
}
|
2020-03-29 12:00:16 +08:00
|
|
|
void Unparse(const CaseStmt &x) { // R1142
|
2018-03-15 06:31:16 +08:00
|
|
|
Outdent(), Word("CASE "), Walk(std::get<CaseSelector>(x.t));
|
2018-03-01 08:56:10 +08:00
|
|
|
Walk(" ", std::get<std::optional<Name>>(x.t)), Indent();
|
|
|
|
}
|
2020-03-29 12:00:16 +08:00
|
|
|
void Unparse(const EndSelectStmt &x) { // R1143 & R1151 & R1155
|
2018-03-15 06:31:16 +08:00
|
|
|
Outdent(), Word("END SELECT"), Walk(" ", x.v);
|
2018-02-27 06:28:32 +08:00
|
|
|
}
|
2020-03-29 12:00:16 +08:00
|
|
|
void Unparse(const CaseSelector &x) { // R1145
|
|
|
|
std::visit(common::visitors{
|
|
|
|
[&](const std::list<CaseValueRange> &y) {
|
|
|
|
Put('('), Walk(y), Put(')');
|
|
|
|
},
|
|
|
|
[&](const Default &) { Word("DEFAULT"); },
|
|
|
|
},
|
2018-03-01 08:56:10 +08:00
|
|
|
x.u);
|
2018-02-27 06:28:32 +08:00
|
|
|
}
|
2020-03-29 12:00:16 +08:00
|
|
|
void Unparse(const CaseValueRange::Range &x) { // R1146
|
2018-03-01 08:56:10 +08:00
|
|
|
Walk(x.lower), Put(':'), Walk(x.upper);
|
2018-02-27 06:28:32 +08:00
|
|
|
}
|
2020-03-29 12:00:16 +08:00
|
|
|
void Unparse(const SelectRankStmt &x) { // R1149
|
2018-03-01 08:56:10 +08:00
|
|
|
Walk(std::get<0>(x.t), ": ");
|
2018-03-15 06:31:16 +08:00
|
|
|
Word("SELECT RANK ("), Walk(std::get<1>(x.t), " => ");
|
2018-03-01 08:56:10 +08:00
|
|
|
Walk(std::get<Selector>(x.t)), Put(')'), Indent();
|
2018-02-27 06:28:32 +08:00
|
|
|
}
|
2020-03-29 12:00:16 +08:00
|
|
|
void Unparse(const SelectRankCaseStmt &x) { // R1150
|
2018-03-15 06:31:16 +08:00
|
|
|
Outdent(), Word("RANK ");
|
2020-03-29 12:00:16 +08:00
|
|
|
std::visit(common::visitors{
|
|
|
|
[&](const ScalarIntConstantExpr &y) {
|
|
|
|
Put('('), Walk(y), Put(')');
|
|
|
|
},
|
|
|
|
[&](const Star &) { Put("(*)"); },
|
|
|
|
[&](const Default &) { Word("DEFAULT"); },
|
|
|
|
},
|
2018-03-01 08:56:10 +08:00
|
|
|
std::get<SelectRankCaseStmt::Rank>(x.t).u);
|
|
|
|
Walk(" ", std::get<std::optional<Name>>(x.t)), Indent();
|
2018-02-27 06:28:32 +08:00
|
|
|
}
|
2020-03-29 12:00:16 +08:00
|
|
|
void Unparse(const SelectTypeStmt &x) { // R1153
|
2018-03-01 08:56:10 +08:00
|
|
|
Walk(std::get<0>(x.t), ": ");
|
2018-03-15 06:31:16 +08:00
|
|
|
Word("SELECT TYPE ("), Walk(std::get<1>(x.t), " => ");
|
2018-03-01 08:56:10 +08:00
|
|
|
Walk(std::get<Selector>(x.t)), Put(')'), Indent();
|
2018-02-27 06:28:32 +08:00
|
|
|
}
|
2020-03-29 12:00:16 +08:00
|
|
|
void Unparse(const TypeGuardStmt &x) { // R1154
|
2018-03-01 08:56:10 +08:00
|
|
|
Outdent(), Walk(std::get<TypeGuardStmt::Guard>(x.t));
|
|
|
|
Walk(" ", std::get<std::optional<Name>>(x.t)), Indent();
|
2018-02-27 06:28:32 +08:00
|
|
|
}
|
2018-04-07 04:13:20 +08:00
|
|
|
void Unparse(const TypeGuardStmt::Guard &x) {
|
2018-11-30 01:27:34 +08:00
|
|
|
std::visit(
|
|
|
|
common::visitors{
|
|
|
|
[&](const TypeSpec &y) { Word("TYPE IS ("), Walk(y), Put(')'); },
|
|
|
|
[&](const DerivedTypeSpec &y) {
|
|
|
|
Word("CLASS IS ("), Walk(y), Put(')');
|
|
|
|
},
|
|
|
|
[&](const Default &) { Word("CLASS DEFAULT"); },
|
|
|
|
},
|
2018-03-01 08:56:10 +08:00
|
|
|
x.u);
|
2018-02-27 06:28:32 +08:00
|
|
|
}
|
2020-03-29 12:00:16 +08:00
|
|
|
void Unparse(const ExitStmt &x) { // R1156
|
2018-03-15 06:31:16 +08:00
|
|
|
Word("EXIT"), Walk(" ", x.v);
|
2018-02-27 06:28:32 +08:00
|
|
|
}
|
2020-03-29 12:00:16 +08:00
|
|
|
void Before(const GotoStmt &) { // R1157
|
2018-03-15 06:31:16 +08:00
|
|
|
Word("GO TO ");
|
2018-03-01 08:56:10 +08:00
|
|
|
}
|
2020-03-29 12:00:16 +08:00
|
|
|
void Unparse(const ComputedGotoStmt &x) { // R1158
|
2018-03-15 06:31:16 +08:00
|
|
|
Word("GO TO ("), Walk(x.t, "), ");
|
2018-03-01 08:56:10 +08:00
|
|
|
}
|
2020-03-29 12:00:16 +08:00
|
|
|
void Unparse(const ContinueStmt &) { // R1159
|
2018-03-15 06:31:16 +08:00
|
|
|
Word("CONTINUE");
|
2018-03-01 08:56:10 +08:00
|
|
|
}
|
2020-03-29 12:00:16 +08:00
|
|
|
void Unparse(const StopStmt &x) { // R1160, R1161
|
2018-03-01 08:56:10 +08:00
|
|
|
if (std::get<StopStmt::Kind>(x.t) == StopStmt::Kind::ErrorStop) {
|
2018-03-15 06:31:16 +08:00
|
|
|
Word("ERROR ");
|
2018-02-27 06:28:32 +08:00
|
|
|
}
|
2018-03-15 06:31:16 +08:00
|
|
|
Word("STOP"), Walk(" ", std::get<std::optional<StopCode>>(x.t));
|
2018-03-01 08:56:10 +08:00
|
|
|
Walk(", QUIET=", std::get<std::optional<ScalarLogicalExpr>>(x.t));
|
2018-02-27 06:28:32 +08:00
|
|
|
}
|
2020-03-29 12:00:16 +08:00
|
|
|
void Unparse(const FailImageStmt &) { // R1163
|
2018-03-15 06:31:16 +08:00
|
|
|
Word("FAIL IMAGE");
|
2018-02-27 06:28:32 +08:00
|
|
|
}
|
2020-03-29 12:00:16 +08:00
|
|
|
void Unparse(const SyncAllStmt &x) { // R1164
|
2018-03-15 06:31:16 +08:00
|
|
|
Word("SYNC ALL ("), Walk(x.v, ", "), Put(')');
|
2018-02-27 06:28:32 +08:00
|
|
|
}
|
2020-03-29 12:00:16 +08:00
|
|
|
void Unparse(const SyncImagesStmt &x) { // R1166
|
2018-03-15 06:31:16 +08:00
|
|
|
Word("SYNC IMAGES (");
|
|
|
|
Walk(std::get<SyncImagesStmt::ImageSet>(x.t));
|
2018-03-01 08:56:10 +08:00
|
|
|
Walk(", ", std::get<std::list<StatOrErrmsg>>(x.t), ", "), Put(')');
|
2018-02-27 06:28:32 +08:00
|
|
|
}
|
2020-03-29 12:00:16 +08:00
|
|
|
void Unparse(const SyncMemoryStmt &x) { // R1168
|
2018-03-15 06:31:16 +08:00
|
|
|
Word("SYNC MEMORY ("), Walk(x.v, ", "), Put(')');
|
2018-02-27 06:28:32 +08:00
|
|
|
}
|
2020-03-29 12:00:16 +08:00
|
|
|
void Unparse(const SyncTeamStmt &x) { // R1169
|
2019-04-07 02:17:07 +08:00
|
|
|
Word("SYNC TEAM ("), Walk(std::get<TeamValue>(x.t));
|
2018-03-01 08:56:10 +08:00
|
|
|
Walk(", ", std::get<std::list<StatOrErrmsg>>(x.t), ", "), Put(')');
|
2018-02-27 06:28:32 +08:00
|
|
|
}
|
2020-03-29 12:00:16 +08:00
|
|
|
void Unparse(const EventPostStmt &x) { // R1170
|
2018-03-15 06:31:16 +08:00
|
|
|
Word("EVENT POST ("), Walk(std::get<EventVariable>(x.t));
|
2018-03-01 08:56:10 +08:00
|
|
|
Walk(", ", std::get<std::list<StatOrErrmsg>>(x.t), ", "), Put(')');
|
2018-02-27 06:28:32 +08:00
|
|
|
}
|
2020-03-29 12:00:16 +08:00
|
|
|
void Before(const EventWaitStmt::EventWaitSpec &x) { // R1173, R1174
|
|
|
|
std::visit(common::visitors{
|
|
|
|
[&](const ScalarIntExpr &) { Word("UNTIL_COUNT="); },
|
|
|
|
[](const StatOrErrmsg &) {},
|
|
|
|
},
|
2018-02-27 06:28:32 +08:00
|
|
|
x.u);
|
2018-03-01 08:56:10 +08:00
|
|
|
}
|
2020-03-29 12:00:16 +08:00
|
|
|
void Unparse(const EventWaitStmt &x) { // R1170
|
2018-03-15 06:31:16 +08:00
|
|
|
Word("EVENT WAIT ("), Walk(std::get<EventVariable>(x.t));
|
2018-03-01 08:56:10 +08:00
|
|
|
Walk(", ", std::get<std::list<EventWaitStmt::EventWaitSpec>>(x.t), ", ");
|
|
|
|
Put(')');
|
|
|
|
}
|
2020-03-29 12:00:16 +08:00
|
|
|
void Unparse(const FormTeamStmt &x) { // R1175, R1177
|
2018-03-15 06:31:16 +08:00
|
|
|
Word("FORM TEAM ("), Walk(std::get<ScalarIntExpr>(x.t));
|
2018-03-01 08:56:10 +08:00
|
|
|
Put(','), Walk(std::get<TeamVariable>(x.t));
|
|
|
|
Walk(", ", std::get<std::list<FormTeamStmt::FormTeamSpec>>(x.t), ", ");
|
|
|
|
Put(')');
|
2018-02-27 06:28:32 +08:00
|
|
|
}
|
2020-03-29 12:00:16 +08:00
|
|
|
void Before(const FormTeamStmt::FormTeamSpec &x) { // R1176, R1178
|
|
|
|
std::visit(common::visitors{
|
|
|
|
[&](const ScalarIntExpr &) { Word("NEW_INDEX="); },
|
|
|
|
[](const StatOrErrmsg &) {},
|
|
|
|
},
|
2018-02-27 06:28:32 +08:00
|
|
|
x.u);
|
2018-03-01 08:56:10 +08:00
|
|
|
}
|
2020-03-29 12:00:16 +08:00
|
|
|
void Unparse(const LockStmt &x) { // R1179
|
2018-03-15 06:31:16 +08:00
|
|
|
Word("LOCK ("), Walk(std::get<LockVariable>(x.t));
|
2018-03-01 08:56:10 +08:00
|
|
|
Walk(", ", std::get<std::list<LockStmt::LockStat>>(x.t), ", ");
|
|
|
|
Put(')');
|
2018-02-27 06:28:32 +08:00
|
|
|
}
|
2020-03-29 12:00:16 +08:00
|
|
|
void Before(const LockStmt::LockStat &x) { // R1180
|
2018-11-30 01:27:34 +08:00
|
|
|
std::visit(
|
|
|
|
common::visitors{
|
|
|
|
[&](const ScalarLogicalVariable &) { Word("ACQUIRED_LOCK="); },
|
2019-08-16 04:50:27 +08:00
|
|
|
[](const StatOrErrmsg &) {},
|
2018-11-30 01:27:34 +08:00
|
|
|
},
|
2018-03-01 08:56:10 +08:00
|
|
|
x.u);
|
|
|
|
}
|
2020-03-29 12:00:16 +08:00
|
|
|
void Unparse(const UnlockStmt &x) { // R1181
|
2018-03-15 06:31:16 +08:00
|
|
|
Word("UNLOCK ("), Walk(std::get<LockVariable>(x.t));
|
2018-03-01 08:56:10 +08:00
|
|
|
Walk(", ", std::get<std::list<StatOrErrmsg>>(x.t), ", ");
|
2018-02-27 06:28:32 +08:00
|
|
|
Put(')');
|
|
|
|
}
|
|
|
|
|
2020-03-29 12:00:16 +08:00
|
|
|
void Unparse(const OpenStmt &x) { // R1204
|
2018-03-15 06:31:16 +08:00
|
|
|
Word("OPEN ("), Walk(x.v, ", "), Put(')');
|
2018-02-27 06:28:32 +08:00
|
|
|
}
|
2020-03-29 12:00:16 +08:00
|
|
|
bool Pre(const ConnectSpec &x) { // R1205
|
|
|
|
return std::visit(common::visitors{
|
|
|
|
[&](const FileUnitNumber &) {
|
|
|
|
Word("UNIT=");
|
|
|
|
return true;
|
|
|
|
},
|
|
|
|
[&](const FileNameExpr &) {
|
|
|
|
Word("FILE=");
|
|
|
|
return true;
|
|
|
|
},
|
|
|
|
[&](const ConnectSpec::CharExpr &y) {
|
|
|
|
Walk(y.t, "=");
|
|
|
|
return false;
|
|
|
|
},
|
|
|
|
[&](const MsgVariable &) {
|
|
|
|
Word("IOMSG=");
|
|
|
|
return true;
|
|
|
|
},
|
|
|
|
[&](const StatVariable &) {
|
|
|
|
Word("IOSTAT=");
|
|
|
|
return true;
|
|
|
|
},
|
|
|
|
[&](const ConnectSpec::Recl &) {
|
|
|
|
Word("RECL=");
|
|
|
|
return true;
|
|
|
|
},
|
|
|
|
[&](const ConnectSpec::Newunit &) {
|
|
|
|
Word("NEWUNIT=");
|
|
|
|
return true;
|
|
|
|
},
|
|
|
|
[&](const ErrLabel &) {
|
|
|
|
Word("ERR=");
|
|
|
|
return true;
|
|
|
|
},
|
|
|
|
[&](const StatusExpr &) {
|
|
|
|
Word("STATUS=");
|
|
|
|
return true;
|
|
|
|
},
|
|
|
|
},
|
2018-03-01 08:56:10 +08:00
|
|
|
x.u);
|
2018-02-27 06:28:32 +08:00
|
|
|
}
|
2020-03-29 12:00:16 +08:00
|
|
|
void Unparse(const CloseStmt &x) { // R1208
|
2018-03-15 06:31:16 +08:00
|
|
|
Word("CLOSE ("), Walk(x.v, ", "), Put(')');
|
2018-03-01 08:56:10 +08:00
|
|
|
}
|
2020-03-29 12:00:16 +08:00
|
|
|
void Before(const CloseStmt::CloseSpec &x) { // R1209
|
|
|
|
std::visit(common::visitors{
|
|
|
|
[&](const FileUnitNumber &) { Word("UNIT="); },
|
|
|
|
[&](const StatVariable &) { Word("IOSTAT="); },
|
|
|
|
[&](const MsgVariable &) { Word("IOMSG="); },
|
|
|
|
[&](const ErrLabel &) { Word("ERR="); },
|
|
|
|
[&](const StatusExpr &) { Word("STATUS="); },
|
|
|
|
},
|
2018-03-01 08:56:10 +08:00
|
|
|
x.u);
|
2018-02-27 06:28:32 +08:00
|
|
|
}
|
2020-03-29 12:00:16 +08:00
|
|
|
void Unparse(const ReadStmt &x) { // R1210
|
2018-03-15 06:31:16 +08:00
|
|
|
Word("READ ");
|
2018-03-01 08:56:10 +08:00
|
|
|
if (x.iounit) {
|
|
|
|
Put('('), Walk(x.iounit);
|
|
|
|
if (x.format) {
|
|
|
|
Put(", "), Walk(x.format);
|
|
|
|
}
|
2018-03-16 07:03:28 +08:00
|
|
|
Walk(", ", x.controls, ", ");
|
2018-03-01 08:56:10 +08:00
|
|
|
Put(')');
|
|
|
|
} else if (x.format) {
|
|
|
|
Walk(x.format);
|
|
|
|
if (!x.items.empty()) {
|
|
|
|
Put(", ");
|
|
|
|
}
|
|
|
|
} else {
|
2018-03-16 07:03:28 +08:00
|
|
|
Put('('), Walk(x.controls, ", "), Put(')');
|
2018-03-01 08:56:10 +08:00
|
|
|
}
|
|
|
|
Walk(" ", x.items, ", ");
|
2018-02-27 06:28:32 +08:00
|
|
|
}
|
2020-03-29 12:00:16 +08:00
|
|
|
void Unparse(const WriteStmt &x) { // R1211
|
2018-03-15 06:31:16 +08:00
|
|
|
Word("WRITE (");
|
2018-03-01 08:56:10 +08:00
|
|
|
if (x.iounit) {
|
|
|
|
Walk(x.iounit);
|
|
|
|
if (x.format) {
|
|
|
|
Put(", "), Walk(x.format);
|
|
|
|
}
|
2018-03-16 07:03:28 +08:00
|
|
|
Walk(", ", x.controls, ", ");
|
2018-03-01 08:56:10 +08:00
|
|
|
} else {
|
2018-03-16 07:03:28 +08:00
|
|
|
Walk(x.controls, ", ");
|
2018-03-01 08:56:10 +08:00
|
|
|
}
|
|
|
|
Put(')'), Walk(" ", x.items, ", ");
|
2018-02-27 06:28:32 +08:00
|
|
|
}
|
2020-03-29 12:00:16 +08:00
|
|
|
void Unparse(const PrintStmt &x) { // R1212
|
2018-03-15 06:31:16 +08:00
|
|
|
Word("PRINT "), Walk(std::get<Format>(x.t));
|
2018-03-01 08:56:10 +08:00
|
|
|
Walk(", ", std::get<std::list<OutputItem>>(x.t), ", ");
|
2018-02-27 06:28:32 +08:00
|
|
|
}
|
2020-03-29 12:00:16 +08:00
|
|
|
bool Pre(const IoControlSpec &x) { // R1213
|
|
|
|
return std::visit(common::visitors{
|
|
|
|
[&](const IoUnit &) {
|
|
|
|
Word("UNIT=");
|
|
|
|
return true;
|
|
|
|
},
|
|
|
|
[&](const Format &) {
|
|
|
|
Word("FMT=");
|
|
|
|
return true;
|
|
|
|
},
|
|
|
|
[&](const Name &) {
|
|
|
|
Word("NML=");
|
|
|
|
return true;
|
|
|
|
},
|
|
|
|
[&](const IoControlSpec::CharExpr &y) {
|
|
|
|
Walk(y.t, "=");
|
|
|
|
return false;
|
|
|
|
},
|
|
|
|
[&](const IoControlSpec::Asynchronous &) {
|
|
|
|
Word("ASYNCHRONOUS=");
|
|
|
|
return true;
|
|
|
|
},
|
|
|
|
[&](const EndLabel &) {
|
|
|
|
Word("END=");
|
|
|
|
return true;
|
|
|
|
},
|
|
|
|
[&](const EorLabel &) {
|
|
|
|
Word("EOR=");
|
|
|
|
return true;
|
|
|
|
},
|
|
|
|
[&](const ErrLabel &) {
|
|
|
|
Word("ERR=");
|
|
|
|
return true;
|
|
|
|
},
|
|
|
|
[&](const IdVariable &) {
|
|
|
|
Word("ID=");
|
|
|
|
return true;
|
|
|
|
},
|
|
|
|
[&](const MsgVariable &) {
|
|
|
|
Word("IOMSG=");
|
|
|
|
return true;
|
|
|
|
},
|
|
|
|
[&](const StatVariable &) {
|
|
|
|
Word("IOSTAT=");
|
|
|
|
return true;
|
|
|
|
},
|
|
|
|
[&](const IoControlSpec::Pos &) {
|
|
|
|
Word("POS=");
|
|
|
|
return true;
|
|
|
|
},
|
|
|
|
[&](const IoControlSpec::Rec &) {
|
|
|
|
Word("REC=");
|
|
|
|
return true;
|
|
|
|
},
|
|
|
|
[&](const IoControlSpec::Size &) {
|
|
|
|
Word("SIZE=");
|
|
|
|
return true;
|
|
|
|
},
|
|
|
|
},
|
2018-03-01 08:56:10 +08:00
|
|
|
x.u);
|
|
|
|
}
|
2020-03-29 12:00:16 +08:00
|
|
|
void Unparse(const InputImpliedDo &x) { // R1218
|
2018-03-01 08:56:10 +08:00
|
|
|
Put('('), Walk(std::get<std::list<InputItem>>(x.t), ", "), Put(", ");
|
|
|
|
Walk(std::get<IoImpliedDoControl>(x.t)), Put(')');
|
2018-02-27 06:28:32 +08:00
|
|
|
}
|
2020-03-29 12:00:16 +08:00
|
|
|
void Unparse(const OutputImpliedDo &x) { // R1219
|
2018-03-01 08:56:10 +08:00
|
|
|
Put('('), Walk(std::get<std::list<OutputItem>>(x.t), ", "), Put(", ");
|
|
|
|
Walk(std::get<IoImpliedDoControl>(x.t)), Put(')');
|
2018-02-27 06:28:32 +08:00
|
|
|
}
|
2020-03-29 12:00:16 +08:00
|
|
|
void Unparse(const WaitStmt &x) { // R1222
|
2018-03-15 06:31:16 +08:00
|
|
|
Word("WAIT ("), Walk(x.v, ", "), Put(')');
|
2018-02-27 06:28:32 +08:00
|
|
|
}
|
2020-03-29 12:00:16 +08:00
|
|
|
void Before(const WaitSpec &x) { // R1223
|
|
|
|
std::visit(common::visitors{
|
|
|
|
[&](const FileUnitNumber &) { Word("UNIT="); },
|
|
|
|
[&](const EndLabel &) { Word("END="); },
|
|
|
|
[&](const EorLabel &) { Word("EOR="); },
|
|
|
|
[&](const ErrLabel &) { Word("ERR="); },
|
|
|
|
[&](const IdExpr &) { Word("ID="); },
|
|
|
|
[&](const MsgVariable &) { Word("IOMSG="); },
|
|
|
|
[&](const StatVariable &) { Word("IOSTAT="); },
|
|
|
|
},
|
2018-03-01 08:56:10 +08:00
|
|
|
x.u);
|
|
|
|
}
|
2020-03-29 12:00:16 +08:00
|
|
|
void Unparse(const BackspaceStmt &x) { // R1224
|
2018-03-15 06:31:16 +08:00
|
|
|
Word("BACKSPACE ("), Walk(x.v, ", "), Put(')');
|
2018-02-27 06:28:32 +08:00
|
|
|
}
|
2020-03-29 12:00:16 +08:00
|
|
|
void Unparse(const EndfileStmt &x) { // R1225
|
2018-03-15 06:31:16 +08:00
|
|
|
Word("ENDFILE ("), Walk(x.v, ", "), Put(')');
|
2018-02-27 06:28:32 +08:00
|
|
|
}
|
2020-03-29 12:00:16 +08:00
|
|
|
void Unparse(const RewindStmt &x) { // R1226
|
2018-03-15 06:31:16 +08:00
|
|
|
Word("REWIND ("), Walk(x.v, ", "), Put(')');
|
2018-02-27 06:28:32 +08:00
|
|
|
}
|
2020-03-29 12:00:16 +08:00
|
|
|
void Before(const PositionOrFlushSpec &x) { // R1227 & R1229
|
|
|
|
std::visit(common::visitors{
|
|
|
|
[&](const FileUnitNumber &) { Word("UNIT="); },
|
|
|
|
[&](const MsgVariable &) { Word("IOMSG="); },
|
|
|
|
[&](const StatVariable &) { Word("IOSTAT="); },
|
|
|
|
[&](const ErrLabel &) { Word("ERR="); },
|
|
|
|
},
|
2018-03-16 08:09:27 +08:00
|
|
|
x.u);
|
|
|
|
}
|
2020-03-29 12:00:16 +08:00
|
|
|
void Unparse(const FlushStmt &x) { // R1228
|
2018-03-15 06:31:16 +08:00
|
|
|
Word("FLUSH ("), Walk(x.v, ", "), Put(')');
|
2018-02-27 06:28:32 +08:00
|
|
|
}
|
2020-03-29 12:00:16 +08:00
|
|
|
void Unparse(const InquireStmt &x) { // R1230
|
2018-03-15 06:31:16 +08:00
|
|
|
Word("INQUIRE (");
|
2018-03-01 08:56:10 +08:00
|
|
|
std::visit(
|
2018-11-30 01:27:34 +08:00
|
|
|
common::visitors{
|
|
|
|
[&](const InquireStmt::Iolength &y) {
|
|
|
|
Word("IOLENGTH="), Walk(y.t, ") ");
|
|
|
|
},
|
|
|
|
[&](const std::list<InquireSpec> &y) { Walk(y, ", "), Put(')'); },
|
|
|
|
},
|
2018-03-01 08:56:10 +08:00
|
|
|
x.u);
|
2018-02-27 06:28:32 +08:00
|
|
|
}
|
2020-03-29 12:00:16 +08:00
|
|
|
bool Pre(const InquireSpec &x) { // R1231
|
|
|
|
return std::visit(common::visitors{
|
|
|
|
[&](const FileUnitNumber &) {
|
|
|
|
Word("UNIT=");
|
|
|
|
return true;
|
|
|
|
},
|
|
|
|
[&](const FileNameExpr &) {
|
|
|
|
Word("FILE=");
|
|
|
|
return true;
|
|
|
|
},
|
|
|
|
[&](const InquireSpec::CharVar &y) {
|
|
|
|
Walk(y.t, "=");
|
|
|
|
return false;
|
|
|
|
},
|
|
|
|
[&](const InquireSpec::IntVar &y) {
|
|
|
|
Walk(y.t, "=");
|
|
|
|
return false;
|
|
|
|
},
|
|
|
|
[&](const InquireSpec::LogVar &y) {
|
|
|
|
Walk(y.t, "=");
|
|
|
|
return false;
|
|
|
|
},
|
|
|
|
[&](const IdExpr &) {
|
|
|
|
Word("ID=");
|
|
|
|
return true;
|
|
|
|
},
|
|
|
|
[&](const ErrLabel &) {
|
|
|
|
Word("ERR=");
|
|
|
|
return true;
|
|
|
|
},
|
|
|
|
},
|
2018-03-01 08:56:10 +08:00
|
|
|
x.u);
|
2018-02-27 06:28:32 +08:00
|
|
|
}
|
2018-03-01 08:56:10 +08:00
|
|
|
|
2020-03-29 12:00:16 +08:00
|
|
|
void Before(const FormatStmt &) { // R1301
|
2018-03-15 06:31:16 +08:00
|
|
|
Word("FORMAT");
|
2018-02-27 06:28:32 +08:00
|
|
|
}
|
2020-03-29 12:00:16 +08:00
|
|
|
void Unparse(const format::FormatSpecification &x) { // R1302, R1303, R1305
|
2018-03-01 08:56:10 +08:00
|
|
|
Put('('), Walk("", x.items, ",", x.unlimitedItems.empty() ? "" : ",");
|
|
|
|
Walk("*(", x.unlimitedItems, ",", ")"), Put(')');
|
|
|
|
}
|
2020-03-29 12:00:16 +08:00
|
|
|
void Unparse(const format::FormatItem &x) { // R1304, R1306, R1321
|
2019-11-10 01:29:31 +08:00
|
|
|
if (x.repeatCount) {
|
2018-03-01 08:56:10 +08:00
|
|
|
Walk(*x.repeatCount);
|
|
|
|
}
|
2020-03-29 12:00:16 +08:00
|
|
|
std::visit(common::visitors{
|
|
|
|
[&](const std::string &y) { PutNormalized(y); },
|
|
|
|
[&](const std::list<format::FormatItem> &y) {
|
|
|
|
Walk("(", y, ",", ")");
|
|
|
|
},
|
|
|
|
[&](const auto &y) { Walk(y); },
|
|
|
|
},
|
2018-02-27 06:28:32 +08:00
|
|
|
x.u);
|
|
|
|
}
|
2018-04-07 04:13:20 +08:00
|
|
|
void Unparse(
|
2020-03-29 12:00:16 +08:00
|
|
|
const format::IntrinsicTypeDataEditDesc &x) { // R1307(1/2) - R1311
|
2018-03-01 08:56:10 +08:00
|
|
|
switch (x.kind) {
|
|
|
|
#define FMT(x) \
|
2020-03-29 12:00:16 +08:00
|
|
|
case format::IntrinsicTypeDataEditDesc::Kind::x: \
|
|
|
|
Put(#x); \
|
|
|
|
break
|
2018-03-01 08:56:10 +08:00
|
|
|
FMT(I);
|
|
|
|
FMT(B);
|
|
|
|
FMT(O);
|
|
|
|
FMT(Z);
|
|
|
|
FMT(F);
|
|
|
|
FMT(E);
|
|
|
|
FMT(EN);
|
|
|
|
FMT(ES);
|
|
|
|
FMT(EX);
|
|
|
|
FMT(G);
|
|
|
|
FMT(L);
|
|
|
|
FMT(A);
|
|
|
|
FMT(D);
|
|
|
|
#undef FMT
|
|
|
|
}
|
|
|
|
Walk(x.width), Walk(".", x.digits), Walk("E", x.exponentWidth);
|
2018-02-27 06:28:32 +08:00
|
|
|
}
|
2020-03-29 12:00:16 +08:00
|
|
|
void Unparse(const format::DerivedTypeDataEditDesc &x) { // R1307(2/2), R1312
|
2018-03-15 06:31:16 +08:00
|
|
|
Word("DT");
|
2018-03-01 08:56:10 +08:00
|
|
|
if (!x.type.empty()) {
|
|
|
|
Put('"'), Put(x.type), Put('"');
|
|
|
|
}
|
|
|
|
Walk("(", x.parameters, ",", ")");
|
|
|
|
}
|
2020-03-29 12:00:16 +08:00
|
|
|
void Unparse(const format::ControlEditDesc &x) { // R1313, R1315-R1320
|
2018-03-01 08:56:10 +08:00
|
|
|
switch (x.kind) {
|
|
|
|
case format::ControlEditDesc::Kind::T:
|
2018-03-15 06:31:16 +08:00
|
|
|
Word("T");
|
2018-03-01 08:56:10 +08:00
|
|
|
Walk(x.count);
|
|
|
|
break;
|
|
|
|
case format::ControlEditDesc::Kind::TL:
|
2018-03-15 06:31:16 +08:00
|
|
|
Word("TL");
|
2018-03-01 08:56:10 +08:00
|
|
|
Walk(x.count);
|
|
|
|
break;
|
|
|
|
case format::ControlEditDesc::Kind::TR:
|
2018-03-15 06:31:16 +08:00
|
|
|
Word("TR");
|
2018-03-01 08:56:10 +08:00
|
|
|
Walk(x.count);
|
|
|
|
break;
|
|
|
|
case format::ControlEditDesc::Kind::X:
|
|
|
|
if (x.count != 1) {
|
|
|
|
Walk(x.count);
|
|
|
|
}
|
2018-03-15 06:31:16 +08:00
|
|
|
Word("X");
|
2018-03-01 08:56:10 +08:00
|
|
|
break;
|
|
|
|
case format::ControlEditDesc::Kind::Slash:
|
|
|
|
if (x.count != 1) {
|
|
|
|
Walk(x.count);
|
|
|
|
}
|
|
|
|
Put('/');
|
|
|
|
break;
|
2020-03-29 12:00:16 +08:00
|
|
|
case format::ControlEditDesc::Kind::Colon:
|
|
|
|
Put(':');
|
|
|
|
break;
|
2018-03-01 08:56:10 +08:00
|
|
|
case format::ControlEditDesc::Kind::P:
|
|
|
|
Walk(x.count);
|
2018-03-15 06:31:16 +08:00
|
|
|
Word("P");
|
2018-03-01 08:56:10 +08:00
|
|
|
break;
|
|
|
|
#define FMT(x) \
|
2020-03-29 12:00:16 +08:00
|
|
|
case format::ControlEditDesc::Kind::x: \
|
|
|
|
Put(#x); \
|
|
|
|
break
|
2018-03-01 08:56:10 +08:00
|
|
|
FMT(SS);
|
|
|
|
FMT(SP);
|
|
|
|
FMT(S);
|
|
|
|
FMT(BN);
|
|
|
|
FMT(BZ);
|
|
|
|
FMT(RU);
|
|
|
|
FMT(RD);
|
|
|
|
FMT(RZ);
|
|
|
|
FMT(RN);
|
|
|
|
FMT(RC);
|
|
|
|
FMT(RP);
|
|
|
|
FMT(DC);
|
|
|
|
FMT(DP);
|
|
|
|
#undef FMT
|
2020-03-29 12:00:16 +08:00
|
|
|
case format::ControlEditDesc::Kind::Dollar:
|
|
|
|
Put('$');
|
|
|
|
break;
|
|
|
|
case format::ControlEditDesc::Kind::Backslash:
|
|
|
|
Put('\\');
|
|
|
|
break;
|
2018-03-01 08:56:10 +08:00
|
|
|
}
|
|
|
|
}
|
|
|
|
|
2020-03-29 12:00:16 +08:00
|
|
|
void Before(const MainProgram &x) { // R1401
|
2018-03-01 08:56:10 +08:00
|
|
|
if (!std::get<std::optional<Statement<ProgramStmt>>>(x.t)) {
|
|
|
|
Indent();
|
|
|
|
}
|
2018-02-27 06:28:32 +08:00
|
|
|
}
|
2020-03-29 12:00:16 +08:00
|
|
|
void Before(const ProgramStmt &) { // R1402
|
2018-03-15 06:31:16 +08:00
|
|
|
Word("PROGRAM "), Indent();
|
2018-02-27 06:28:32 +08:00
|
|
|
}
|
2020-03-29 12:00:16 +08:00
|
|
|
void Unparse(const EndProgramStmt &x) { // R1403
|
2018-04-04 01:29:04 +08:00
|
|
|
EndSubprogram("PROGRAM", x.v);
|
2018-02-27 06:28:32 +08:00
|
|
|
}
|
2020-03-29 12:00:16 +08:00
|
|
|
void Before(const ModuleStmt &) { // R1405
|
2018-03-15 06:31:16 +08:00
|
|
|
Word("MODULE "), Indent();
|
2018-02-27 06:28:32 +08:00
|
|
|
}
|
2020-03-29 12:00:16 +08:00
|
|
|
void Unparse(const EndModuleStmt &x) { // R1406
|
2018-04-04 01:29:04 +08:00
|
|
|
EndSubprogram("MODULE", x.v);
|
2018-02-27 06:28:32 +08:00
|
|
|
}
|
2020-03-29 12:00:16 +08:00
|
|
|
void Unparse(const UseStmt &x) { // R1409
|
2018-03-15 06:31:16 +08:00
|
|
|
Word("USE"), Walk(", ", x.nature), Put(" :: "), Walk(x.moduleName);
|
2020-03-29 12:00:16 +08:00
|
|
|
std::visit(common::visitors{
|
|
|
|
[&](const std::list<Rename> &y) { Walk(", ", y, ", "); },
|
|
|
|
[&](const std::list<Only> &y) { Walk(", ONLY: ", y, ", "); },
|
|
|
|
},
|
2018-03-01 08:56:10 +08:00
|
|
|
x.u);
|
|
|
|
}
|
2020-03-29 12:00:16 +08:00
|
|
|
void Unparse(const Rename &x) { // R1411
|
|
|
|
std::visit(common::visitors{
|
|
|
|
[&](const Rename::Names &y) { Walk(y.t, " => "); },
|
|
|
|
[&](const Rename::Operators &y) {
|
|
|
|
Word("OPERATOR("), Walk(y.t, ") => OPERATOR("), Put(")");
|
|
|
|
},
|
|
|
|
},
|
2018-03-01 08:56:10 +08:00
|
|
|
x.u);
|
|
|
|
}
|
2020-03-29 12:00:16 +08:00
|
|
|
void Unparse(const SubmoduleStmt &x) { // R1417
|
2018-07-18 03:51:54 +08:00
|
|
|
Word("SUBMODULE ("), WalkTupleElements(x.t, ")"), Indent();
|
2018-02-27 06:28:32 +08:00
|
|
|
}
|
2020-03-29 12:00:16 +08:00
|
|
|
void Unparse(const ParentIdentifier &x) { // R1418
|
2018-03-01 08:56:10 +08:00
|
|
|
Walk(std::get<Name>(x.t)), Walk(":", std::get<std::optional<Name>>(x.t));
|
|
|
|
}
|
2020-03-29 12:00:16 +08:00
|
|
|
void Unparse(const EndSubmoduleStmt &x) { // R1419
|
2018-04-04 01:29:04 +08:00
|
|
|
EndSubprogram("SUBMODULE", x.v);
|
2018-02-27 06:28:32 +08:00
|
|
|
}
|
2020-03-29 12:00:16 +08:00
|
|
|
void Unparse(const BlockDataStmt &x) { // R1421
|
2018-03-15 06:31:16 +08:00
|
|
|
Word("BLOCK DATA"), Walk(" ", x.v), Indent();
|
2018-02-27 06:28:32 +08:00
|
|
|
}
|
2020-03-29 12:00:16 +08:00
|
|
|
void Unparse(const EndBlockDataStmt &x) { // R1422
|
2018-04-04 01:29:04 +08:00
|
|
|
EndSubprogram("BLOCK DATA", x.v);
|
2018-02-27 06:28:32 +08:00
|
|
|
}
|
|
|
|
|
2020-03-29 12:00:16 +08:00
|
|
|
void Unparse(const InterfaceStmt &x) { // R1503
|
|
|
|
std::visit(common::visitors{
|
|
|
|
[&](const std::optional<GenericSpec> &y) {
|
|
|
|
Word("INTERFACE"), Walk(" ", y);
|
|
|
|
},
|
|
|
|
[&](const Abstract &) { Word("ABSTRACT INTERFACE"); },
|
|
|
|
},
|
2018-03-01 08:56:10 +08:00
|
|
|
x.u);
|
2018-02-27 06:28:32 +08:00
|
|
|
Indent();
|
|
|
|
}
|
2020-03-29 12:00:16 +08:00
|
|
|
void Unparse(const EndInterfaceStmt &x) { // R1504
|
2018-03-15 06:31:16 +08:00
|
|
|
Outdent(), Word("END INTERFACE"), Walk(" ", x.v);
|
2018-02-27 06:28:32 +08:00
|
|
|
}
|
2020-03-29 12:00:16 +08:00
|
|
|
void Unparse(const ProcedureStmt &x) { // R1506
|
2018-03-01 08:56:10 +08:00
|
|
|
if (std::get<ProcedureStmt::Kind>(x.t) ==
|
|
|
|
ProcedureStmt::Kind::ModuleProcedure) {
|
2018-03-15 06:31:16 +08:00
|
|
|
Word("MODULE ");
|
2018-03-01 08:56:10 +08:00
|
|
|
}
|
2018-03-15 06:31:16 +08:00
|
|
|
Word("PROCEDURE :: ");
|
2018-03-01 08:56:10 +08:00
|
|
|
Walk(std::get<std::list<Name>>(x.t), ", ");
|
2018-02-27 06:28:32 +08:00
|
|
|
}
|
2020-03-29 12:00:16 +08:00
|
|
|
void Before(const GenericSpec &x) { // R1508, R1509
|
2018-03-15 07:31:41 +08:00
|
|
|
std::visit(
|
2018-11-30 01:27:34 +08:00
|
|
|
common::visitors{
|
2019-08-16 04:50:27 +08:00
|
|
|
[&](const DefinedOperator &) { Word("OPERATOR("); },
|
2018-03-15 07:31:41 +08:00
|
|
|
[&](const GenericSpec::Assignment &) { Word("ASSIGNMENT(=)"); },
|
|
|
|
[&](const GenericSpec::ReadFormatted &) {
|
|
|
|
Word("READ(FORMATTED)");
|
|
|
|
},
|
|
|
|
[&](const GenericSpec::ReadUnformatted &) {
|
|
|
|
Word("READ(UNFORMATTED)");
|
|
|
|
},
|
|
|
|
[&](const GenericSpec::WriteFormatted &) {
|
|
|
|
Word("WRITE(FORMATTED)");
|
|
|
|
},
|
|
|
|
[&](const GenericSpec::WriteUnformatted &) {
|
|
|
|
Word("WRITE(UNFORMATTED)");
|
|
|
|
},
|
2018-11-30 01:27:34 +08:00
|
|
|
[](const auto &) {},
|
|
|
|
},
|
2018-03-01 08:56:10 +08:00
|
|
|
x.u);
|
|
|
|
}
|
2018-03-15 07:31:41 +08:00
|
|
|
void Post(const GenericSpec &x) {
|
2020-03-29 12:00:16 +08:00
|
|
|
std::visit(common::visitors{
|
|
|
|
[&](const DefinedOperator &) { Put(')'); },
|
|
|
|
[](const auto &) {},
|
|
|
|
},
|
2018-03-15 07:31:41 +08:00
|
|
|
x.u);
|
|
|
|
}
|
2020-03-29 12:00:16 +08:00
|
|
|
void Unparse(const GenericStmt &x) { // R1510
|
2018-03-15 06:31:16 +08:00
|
|
|
Word("GENERIC"), Walk(", ", std::get<std::optional<AccessSpec>>(x.t));
|
2018-03-01 08:56:10 +08:00
|
|
|
Put(" :: "), Walk(std::get<GenericSpec>(x.t)), Put(" => ");
|
|
|
|
Walk(std::get<std::list<Name>>(x.t), ", ");
|
|
|
|
}
|
2020-03-29 12:00:16 +08:00
|
|
|
void Unparse(const ExternalStmt &x) { // R1511
|
2018-03-15 06:31:16 +08:00
|
|
|
Word("EXTERNAL :: "), Walk(x.v, ", ");
|
2018-03-01 08:56:10 +08:00
|
|
|
}
|
2020-03-29 12:00:16 +08:00
|
|
|
void Unparse(const ProcedureDeclarationStmt &x) { // R1512
|
2019-08-08 05:45:44 +08:00
|
|
|
Word("PROCEDURE("), Walk(std::get<std::optional<ProcInterface>>(x.t));
|
2018-03-01 08:56:10 +08:00
|
|
|
Put(')'), Walk(", ", std::get<std::list<ProcAttrSpec>>(x.t), ", ");
|
|
|
|
Put(" :: "), Walk(std::get<std::list<ProcDecl>>(x.t), ", ");
|
|
|
|
}
|
2020-03-29 12:00:16 +08:00
|
|
|
void Unparse(const ProcDecl &x) { // R1515
|
2018-03-01 08:56:10 +08:00
|
|
|
Walk(std::get<Name>(x.t));
|
|
|
|
Walk(" => ", std::get<std::optional<ProcPointerInit>>(x.t));
|
|
|
|
}
|
2020-03-29 12:00:16 +08:00
|
|
|
void Unparse(const IntrinsicStmt &x) { // R1519
|
2018-03-15 06:31:16 +08:00
|
|
|
Word("INTRINSIC :: "), Walk(x.v, ", ");
|
2018-03-01 08:56:10 +08:00
|
|
|
}
|
2020-03-29 12:00:16 +08:00
|
|
|
void Unparse(const FunctionReference &x) { // R1520
|
2018-03-01 08:56:10 +08:00
|
|
|
Walk(std::get<ProcedureDesignator>(x.v.t));
|
|
|
|
Put('('), Walk(std::get<std::list<ActualArgSpec>>(x.v.t), ", "), Put(')');
|
|
|
|
}
|
2020-03-29 12:00:16 +08:00
|
|
|
void Unparse(const CallStmt &x) { // R1521
|
2019-12-18 02:53:20 +08:00
|
|
|
if (asFortran_ && x.typedCall.get()) {
|
2019-12-20 11:13:16 +08:00
|
|
|
Put(' ');
|
2019-12-18 02:53:20 +08:00
|
|
|
asFortran_->call(out_, *x.typedCall);
|
2019-12-20 11:13:16 +08:00
|
|
|
Put('\n');
|
2018-03-16 08:09:27 +08:00
|
|
|
} else {
|
2019-12-18 02:53:20 +08:00
|
|
|
const auto &pd{std::get<ProcedureDesignator>(x.v.t)};
|
|
|
|
const auto &args{std::get<std::list<ActualArgSpec>>(x.v.t)};
|
|
|
|
Word("CALL "), Walk(pd);
|
|
|
|
if (args.empty()) {
|
|
|
|
if (std::holds_alternative<ProcComponentRef>(pd.u)) {
|
2020-03-29 12:00:16 +08:00
|
|
|
Put("()"); // pgf90 crashes on CALL to tbp without parentheses
|
2019-12-18 02:53:20 +08:00
|
|
|
}
|
|
|
|
} else {
|
|
|
|
Walk("(", args, ", ", ")");
|
|
|
|
}
|
2018-03-16 08:09:27 +08:00
|
|
|
}
|
2018-03-01 08:56:10 +08:00
|
|
|
}
|
2020-03-29 12:00:16 +08:00
|
|
|
void Unparse(const ActualArgSpec &x) { // R1523
|
2018-03-01 08:56:10 +08:00
|
|
|
Walk(std::get<std::optional<Keyword>>(x.t), "=");
|
|
|
|
Walk(std::get<ActualArg>(x.t));
|
|
|
|
}
|
2020-03-29 12:00:16 +08:00
|
|
|
void Unparse(const ActualArg::PercentRef &x) { // R1524
|
2018-03-15 06:31:16 +08:00
|
|
|
Word("%REF("), Walk(x.v), Put(')');
|
2018-03-01 08:56:10 +08:00
|
|
|
}
|
2018-04-07 04:13:20 +08:00
|
|
|
void Unparse(const ActualArg::PercentVal &x) {
|
2018-03-15 06:31:16 +08:00
|
|
|
Word("%VAL("), Walk(x.v), Put(')');
|
2018-03-01 08:56:10 +08:00
|
|
|
}
|
2020-03-29 12:00:16 +08:00
|
|
|
void Before(const AltReturnSpec &) { // R1525
|
2018-03-15 06:31:16 +08:00
|
|
|
Put('*');
|
2018-02-27 06:28:32 +08:00
|
|
|
}
|
2020-03-29 12:00:16 +08:00
|
|
|
void Post(const PrefixSpec::Elemental) { Word("ELEMENTAL"); } // R1527
|
2018-03-15 07:31:41 +08:00
|
|
|
void Post(const PrefixSpec::Impure) { Word("IMPURE"); }
|
|
|
|
void Post(const PrefixSpec::Module) { Word("MODULE"); }
|
|
|
|
void Post(const PrefixSpec::Non_Recursive) { Word("NON_RECURSIVE"); }
|
|
|
|
void Post(const PrefixSpec::Pure) { Word("PURE"); }
|
|
|
|
void Post(const PrefixSpec::Recursive) { Word("RECURSIVE"); }
|
2020-03-29 12:00:16 +08:00
|
|
|
void Unparse(const FunctionStmt &x) { // R1530
|
2018-03-01 08:56:10 +08:00
|
|
|
Walk("", std::get<std::list<PrefixSpec>>(x.t), " ", " ");
|
2018-03-15 08:02:21 +08:00
|
|
|
Word("FUNCTION "), Walk(std::get<Name>(x.t)), Put("(");
|
2018-03-01 08:56:10 +08:00
|
|
|
Walk(std::get<std::list<Name>>(x.t), ", "), Put(')');
|
|
|
|
Walk(" ", std::get<std::optional<Suffix>>(x.t)), Indent();
|
|
|
|
}
|
2020-03-29 12:00:16 +08:00
|
|
|
void Unparse(const Suffix &x) { // R1532
|
2018-03-01 08:56:10 +08:00
|
|
|
if (x.resultName) {
|
2018-03-15 06:31:16 +08:00
|
|
|
Word("RESULT("), Walk(x.resultName), Put(')');
|
2018-03-01 08:56:10 +08:00
|
|
|
Walk(" ", x.binding);
|
2018-02-27 06:28:32 +08:00
|
|
|
} else {
|
2018-03-01 08:56:10 +08:00
|
|
|
Walk(x.binding);
|
2018-02-27 06:28:32 +08:00
|
|
|
}
|
|
|
|
}
|
2020-03-29 12:00:16 +08:00
|
|
|
void Unparse(const EndFunctionStmt &x) { // R1533
|
2018-04-04 01:29:04 +08:00
|
|
|
EndSubprogram("FUNCTION", x.v);
|
2018-02-27 06:28:32 +08:00
|
|
|
}
|
2020-03-29 12:00:16 +08:00
|
|
|
void Unparse(const SubroutineStmt &x) { // R1535
|
2018-03-01 08:56:10 +08:00
|
|
|
Walk("", std::get<std::list<PrefixSpec>>(x.t), " ", " ");
|
2018-03-15 06:31:16 +08:00
|
|
|
Word("SUBROUTINE "), Walk(std::get<Name>(x.t));
|
2018-07-11 08:09:07 +08:00
|
|
|
const auto &args{std::get<std::list<DummyArg>>(x.t)};
|
|
|
|
const auto &bind{std::get<std::optional<LanguageBindingSpec>>(x.t)};
|
2018-03-15 07:31:41 +08:00
|
|
|
if (args.empty()) {
|
|
|
|
Walk(" () ", bind);
|
|
|
|
} else {
|
|
|
|
Walk(" (", args, ", ", ")");
|
|
|
|
Walk(" ", bind);
|
|
|
|
}
|
2018-03-01 08:56:10 +08:00
|
|
|
Indent();
|
2018-02-27 06:28:32 +08:00
|
|
|
}
|
2020-03-29 12:00:16 +08:00
|
|
|
void Unparse(const EndSubroutineStmt &x) { // R1537
|
2018-04-04 01:29:04 +08:00
|
|
|
EndSubprogram("SUBROUTINE", x.v);
|
2018-02-27 06:28:32 +08:00
|
|
|
}
|
2020-03-29 12:00:16 +08:00
|
|
|
void Before(const MpSubprogramStmt &) { // R1539
|
2018-03-15 06:31:16 +08:00
|
|
|
Word("MODULE PROCEDURE "), Indent();
|
2018-03-01 08:56:10 +08:00
|
|
|
}
|
2020-03-29 12:00:16 +08:00
|
|
|
void Unparse(const EndMpSubprogramStmt &x) { // R1540
|
2018-04-04 01:29:04 +08:00
|
|
|
EndSubprogram("PROCEDURE", x.v);
|
2018-02-27 06:28:32 +08:00
|
|
|
}
|
2020-03-29 12:00:16 +08:00
|
|
|
void Unparse(const EntryStmt &x) { // R1541
|
2018-04-10 04:45:30 +08:00
|
|
|
Word("ENTRY "), Walk(std::get<Name>(x.t)), Put("(");
|
|
|
|
Walk(std::get<std::list<DummyArg>>(x.t), ", "), Put(")");
|
2018-03-01 08:56:10 +08:00
|
|
|
Walk(" ", std::get<std::optional<Suffix>>(x.t));
|
2018-02-27 06:28:32 +08:00
|
|
|
}
|
2020-03-29 12:00:16 +08:00
|
|
|
void Unparse(const ReturnStmt &x) { // R1542
|
2018-03-15 06:31:16 +08:00
|
|
|
Word("RETURN"), Walk(" ", x.v);
|
2018-02-27 06:28:32 +08:00
|
|
|
}
|
2020-03-29 12:00:16 +08:00
|
|
|
void Unparse(const ContainsStmt &) { // R1543
|
2018-03-01 08:56:10 +08:00
|
|
|
Outdent();
|
2018-03-15 06:31:16 +08:00
|
|
|
Word("CONTAINS");
|
2018-03-01 08:56:10 +08:00
|
|
|
Indent();
|
2018-02-27 06:28:32 +08:00
|
|
|
}
|
2020-03-29 12:00:16 +08:00
|
|
|
void Unparse(const StmtFunctionStmt &x) { // R1544
|
2018-03-01 08:56:10 +08:00
|
|
|
Walk(std::get<Name>(x.t)), Put('(');
|
|
|
|
Walk(std::get<std::list<Name>>(x.t), ", "), Put(") = ");
|
|
|
|
Walk(std::get<Scalar<Expr>>(x.t));
|
2018-02-27 06:28:32 +08:00
|
|
|
}
|
2018-03-01 08:56:10 +08:00
|
|
|
|
2018-03-24 06:14:52 +08:00
|
|
|
// Directives, extensions, and deprecated constructs
|
2018-04-07 04:13:20 +08:00
|
|
|
void Unparse(const CompilerDirective &x) {
|
2018-03-24 06:14:52 +08:00
|
|
|
std::visit(
|
2018-06-19 02:03:43 +08:00
|
|
|
common::visitors{
|
|
|
|
[&](const std::list<CompilerDirective::IgnoreTKR> &tkr) {
|
2020-03-29 12:00:16 +08:00
|
|
|
Word("!DIR$ IGNORE_TKR"); // emitted even if tkr list is empty
|
2018-06-19 02:03:43 +08:00
|
|
|
Walk(" ", tkr, ", ");
|
|
|
|
},
|
2020-07-18 07:36:59 +08:00
|
|
|
[&](const std::list<CompilerDirective::NameValue> &names) {
|
|
|
|
Walk("!DIR$ ", names, " ");
|
|
|
|
},
|
2018-11-30 01:27:34 +08:00
|
|
|
},
|
2018-03-24 06:14:52 +08:00
|
|
|
x.u);
|
|
|
|
Put('\n');
|
|
|
|
}
|
2018-04-07 04:13:20 +08:00
|
|
|
void Unparse(const CompilerDirective::IgnoreTKR &x) {
|
2018-07-11 08:09:07 +08:00
|
|
|
const auto &list{std::get<std::list<const char *>>(x.t)};
|
2018-03-24 06:14:52 +08:00
|
|
|
if (!list.empty()) {
|
|
|
|
Put("(");
|
|
|
|
for (const char *tkr : list) {
|
|
|
|
Put(*tkr);
|
|
|
|
}
|
|
|
|
Put(") ");
|
|
|
|
}
|
|
|
|
Walk(std::get<Name>(x.t));
|
|
|
|
}
|
2020-07-18 07:36:59 +08:00
|
|
|
void Unparse(const CompilerDirective::NameValue &x) {
|
|
|
|
Walk(std::get<Name>(x.t));
|
|
|
|
Walk("=", std::get<std::optional<std::uint64_t>>(x.t));
|
|
|
|
}
|
[flang][openacc] OpenACC 3.0 parser
Summary:
This patch introduce the parser for OpenACC 3.0 in Flang. It uses the same TableGen mechanism
than OpenMP.
Reviewers: nvdatian, sscalpone, tskeith, klausler, ichoyjx, jdoerfert, DavidTruby
Reviewed By: klausler
Subscribers: MaskRay, SouraVX, mgorny, hiraditya, jfb, sstefan1, llvm-commits
Tags: #llvm, #flang
Differential Revision: https://reviews.llvm.org/D83649
2020-07-15 02:28:34 +08:00
|
|
|
|
|
|
|
// OpenACC Directives & Clauses
|
|
|
|
void Unparse(const AccAtomicCapture &x) {
|
|
|
|
BeginOpenACC();
|
|
|
|
Word("!$ACC CAPTURE");
|
|
|
|
Put("\n");
|
|
|
|
EndOpenACC();
|
|
|
|
Walk(std::get<AccAtomicCapture::Stmt1>(x.t));
|
|
|
|
Put("\n");
|
|
|
|
Walk(std::get<AccAtomicCapture::Stmt2>(x.t));
|
|
|
|
BeginOpenACC();
|
|
|
|
Word("!$ACC END ATOMIC\n");
|
|
|
|
EndOpenACC();
|
|
|
|
}
|
|
|
|
void Unparse(const AccAtomicRead &x) {
|
|
|
|
BeginOpenACC();
|
|
|
|
Word("!$ACC ATOMIC READ");
|
|
|
|
Put("\n");
|
|
|
|
EndOpenACC();
|
|
|
|
Walk(std::get<Statement<AssignmentStmt>>(x.t));
|
|
|
|
BeginOpenACC();
|
|
|
|
Walk(std::get<std::optional<AccEndAtomic>>(x.t), "!$ACC END ATOMIC\n");
|
|
|
|
EndOpenACC();
|
|
|
|
}
|
|
|
|
void Unparse(const AccAtomicWrite &x) {
|
|
|
|
BeginOpenACC();
|
|
|
|
Word("!$ACC ATOMIC WRITE");
|
|
|
|
Put("\n");
|
|
|
|
EndOpenACC();
|
|
|
|
Walk(std::get<Statement<AssignmentStmt>>(x.t));
|
|
|
|
BeginOpenACC();
|
|
|
|
Walk(std::get<std::optional<AccEndAtomic>>(x.t), "!$ACC END ATOMIC\n");
|
|
|
|
EndOpenACC();
|
|
|
|
}
|
|
|
|
void Unparse(const AccAtomicUpdate &x) {
|
|
|
|
BeginOpenACC();
|
|
|
|
Word("!$ACC ATOMIC UPDATE");
|
|
|
|
Put("\n");
|
|
|
|
EndOpenACC();
|
|
|
|
Walk(std::get<Statement<AssignmentStmt>>(x.t));
|
|
|
|
BeginOpenACC();
|
|
|
|
Walk(std::get<std::optional<AccEndAtomic>>(x.t), "!$ACC END ATOMIC\n");
|
|
|
|
EndOpenACC();
|
|
|
|
}
|
|
|
|
void Unparse(const llvm::acc::Directive &x) {
|
|
|
|
Word(llvm::acc::getOpenACCDirectiveName(x).str());
|
|
|
|
}
|
2020-08-18 02:22:01 +08:00
|
|
|
#define GEN_FLANG_CLAUSE_UNPARSE
|
|
|
|
#include "llvm/Frontend/OpenACC/ACC.cpp.inc"
|
[flang][openacc] OpenACC 3.0 parser
Summary:
This patch introduce the parser for OpenACC 3.0 in Flang. It uses the same TableGen mechanism
than OpenMP.
Reviewers: nvdatian, sscalpone, tskeith, klausler, ichoyjx, jdoerfert, DavidTruby
Reviewed By: klausler
Subscribers: MaskRay, SouraVX, mgorny, hiraditya, jfb, sstefan1, llvm-commits
Tags: #llvm, #flang
Differential Revision: https://reviews.llvm.org/D83649
2020-07-15 02:28:34 +08:00
|
|
|
void Unparse(const AccObjectListWithModifier &x) {
|
|
|
|
Walk(std::get<std::optional<AccDataModifier>>(x.t), ":");
|
|
|
|
Walk(std::get<AccObjectList>(x.t));
|
|
|
|
}
|
|
|
|
void Unparse(const AccDataModifier::Modifier &x) {
|
|
|
|
Word(AccDataModifier::EnumToString(x));
|
|
|
|
}
|
2020-12-18 00:32:52 +08:00
|
|
|
void Unparse(const AccBindClause &x) {
|
|
|
|
std::visit(common::visitors{
|
|
|
|
[&](const Name &y) { Put('('), Walk(y), Put(')'); },
|
|
|
|
[&](const ScalarDefaultCharExpr &y) {
|
|
|
|
Put('('), Walk(y), Put(')');
|
|
|
|
},
|
|
|
|
},
|
|
|
|
x.u);
|
|
|
|
}
|
[flang][openacc] OpenACC 3.0 parser
Summary:
This patch introduce the parser for OpenACC 3.0 in Flang. It uses the same TableGen mechanism
than OpenMP.
Reviewers: nvdatian, sscalpone, tskeith, klausler, ichoyjx, jdoerfert, DavidTruby
Reviewed By: klausler
Subscribers: MaskRay, SouraVX, mgorny, hiraditya, jfb, sstefan1, llvm-commits
Tags: #llvm, #flang
Differential Revision: https://reviews.llvm.org/D83649
2020-07-15 02:28:34 +08:00
|
|
|
void Unparse(const AccDefaultClause &x) {
|
|
|
|
switch (x.v) {
|
|
|
|
case AccDefaultClause::Arg::None:
|
|
|
|
Put("NONE");
|
|
|
|
break;
|
|
|
|
case AccDefaultClause::Arg::Present:
|
|
|
|
Put("PRESENT");
|
|
|
|
break;
|
|
|
|
}
|
|
|
|
}
|
|
|
|
void Unparse(const AccClauseList &x) { Walk(" ", x.v, " "); }
|
|
|
|
void Unparse(const AccGangArgument &x) {
|
|
|
|
Walk("NUM:", std::get<std::optional<ScalarIntExpr>>(x.t));
|
|
|
|
Walk(", STATIC:", std::get<std::optional<AccSizeExpr>>(x.t));
|
|
|
|
}
|
|
|
|
void Unparse(const OpenACCBlockConstruct &x) {
|
|
|
|
BeginOpenACC();
|
|
|
|
Word("!$ACC ");
|
|
|
|
Walk(std::get<AccBeginBlockDirective>(x.t));
|
|
|
|
Put("\n");
|
|
|
|
EndOpenACC();
|
|
|
|
Walk(std::get<Block>(x.t), "");
|
|
|
|
BeginOpenACC();
|
|
|
|
Word("!$ACC END ");
|
|
|
|
Walk(std::get<AccEndBlockDirective>(x.t));
|
|
|
|
Put("\n");
|
|
|
|
EndOpenACC();
|
|
|
|
}
|
|
|
|
void Unparse(const OpenACCLoopConstruct &x) {
|
|
|
|
BeginOpenACC();
|
|
|
|
Word("!$ACC ");
|
|
|
|
Walk(std::get<AccBeginLoopDirective>(x.t));
|
|
|
|
Put("\n");
|
|
|
|
EndOpenACC();
|
|
|
|
Walk(std::get<std::optional<DoConstruct>>(x.t));
|
|
|
|
}
|
|
|
|
void Unparse(const AccBeginLoopDirective &x) {
|
|
|
|
Walk(std::get<AccLoopDirective>(x.t));
|
|
|
|
Walk(std::get<AccClauseList>(x.t));
|
|
|
|
}
|
|
|
|
void Unparse(const OpenACCStandaloneConstruct &x) {
|
|
|
|
BeginOpenACC();
|
|
|
|
Word("!$ACC ");
|
|
|
|
Walk(std::get<AccStandaloneDirective>(x.t));
|
|
|
|
Walk(std::get<AccClauseList>(x.t));
|
|
|
|
Put("\n");
|
|
|
|
EndOpenACC();
|
|
|
|
}
|
|
|
|
void Unparse(const OpenACCStandaloneDeclarativeConstruct &x) {
|
|
|
|
BeginOpenACC();
|
|
|
|
Word("!$ACC ");
|
|
|
|
Walk(std::get<AccDeclarativeDirective>(x.t));
|
|
|
|
Walk(std::get<AccClauseList>(x.t));
|
|
|
|
Put("\n");
|
|
|
|
EndOpenACC();
|
|
|
|
}
|
|
|
|
void Unparse(const OpenACCCombinedConstruct &x) {
|
|
|
|
BeginOpenACC();
|
|
|
|
Word("!$ACC ");
|
|
|
|
Walk(std::get<AccBeginCombinedDirective>(x.t));
|
|
|
|
Put("\n");
|
|
|
|
EndOpenACC();
|
2020-08-14 02:04:43 +08:00
|
|
|
Walk(std::get<std::optional<DoConstruct>>(x.t));
|
[flang][openacc] OpenACC 3.0 parser
Summary:
This patch introduce the parser for OpenACC 3.0 in Flang. It uses the same TableGen mechanism
than OpenMP.
Reviewers: nvdatian, sscalpone, tskeith, klausler, ichoyjx, jdoerfert, DavidTruby
Reviewed By: klausler
Subscribers: MaskRay, SouraVX, mgorny, hiraditya, jfb, sstefan1, llvm-commits
Tags: #llvm, #flang
Differential Revision: https://reviews.llvm.org/D83649
2020-07-15 02:28:34 +08:00
|
|
|
BeginOpenACC();
|
2020-10-01 22:34:50 +08:00
|
|
|
Walk("!$ACC END ", std::get<std::optional<AccEndCombinedDirective>>(x.t),
|
|
|
|
"\n");
|
[flang][openacc] OpenACC 3.0 parser
Summary:
This patch introduce the parser for OpenACC 3.0 in Flang. It uses the same TableGen mechanism
than OpenMP.
Reviewers: nvdatian, sscalpone, tskeith, klausler, ichoyjx, jdoerfert, DavidTruby
Reviewed By: klausler
Subscribers: MaskRay, SouraVX, mgorny, hiraditya, jfb, sstefan1, llvm-commits
Tags: #llvm, #flang
Differential Revision: https://reviews.llvm.org/D83649
2020-07-15 02:28:34 +08:00
|
|
|
EndOpenACC();
|
|
|
|
}
|
|
|
|
void Unparse(const OpenACCRoutineConstruct &x) {
|
|
|
|
BeginOpenACC();
|
|
|
|
Word("!$ACC ROUTINE");
|
|
|
|
Walk("(", std::get<std::optional<Name>>(x.t), ")");
|
|
|
|
Walk(std::get<AccClauseList>(x.t));
|
|
|
|
Put("\n");
|
|
|
|
EndOpenACC();
|
|
|
|
}
|
|
|
|
void Unparse(const AccObject &x) {
|
|
|
|
std::visit(common::visitors{
|
|
|
|
[&](const Designator &y) { Walk(y); },
|
|
|
|
[&](const Name &y) { Put("/"), Walk(y), Put("/"); },
|
|
|
|
},
|
|
|
|
x.u);
|
|
|
|
}
|
|
|
|
void Unparse(const AccObjectList &x) { Walk(x.v, ","); }
|
2020-08-25 02:22:34 +08:00
|
|
|
void Unparse(const AccReductionOperator::Operator &x) {
|
|
|
|
Word(AccReductionOperator::EnumToString(x));
|
|
|
|
}
|
[flang][openacc] OpenACC 3.0 parser
Summary:
This patch introduce the parser for OpenACC 3.0 in Flang. It uses the same TableGen mechanism
than OpenMP.
Reviewers: nvdatian, sscalpone, tskeith, klausler, ichoyjx, jdoerfert, DavidTruby
Reviewed By: klausler
Subscribers: MaskRay, SouraVX, mgorny, hiraditya, jfb, sstefan1, llvm-commits
Tags: #llvm, #flang
Differential Revision: https://reviews.llvm.org/D83649
2020-07-15 02:28:34 +08:00
|
|
|
void Unparse(const AccObjectListWithReduction &x) {
|
|
|
|
Walk(std::get<AccReductionOperator>(x.t));
|
|
|
|
Put(":");
|
|
|
|
Walk(std::get<AccObjectList>(x.t));
|
|
|
|
}
|
|
|
|
void Unparse(const OpenACCCacheConstruct &x) {
|
|
|
|
BeginOpenACC();
|
|
|
|
Word("!$ACC ");
|
|
|
|
Word("CACHE(");
|
|
|
|
Walk(std::get<AccObjectListWithModifier>(x.t));
|
|
|
|
Put(")");
|
|
|
|
Put("\n");
|
|
|
|
EndOpenACC();
|
|
|
|
}
|
2020-08-24 08:01:10 +08:00
|
|
|
void Unparse(const AccWaitArgument &x) {
|
|
|
|
Walk("DEVNUM:", std::get<std::optional<ScalarIntExpr>>(x.t), ":");
|
|
|
|
Walk(std::get<std::list<ScalarIntExpr>>(x.t), ",");
|
|
|
|
}
|
[flang][openacc] OpenACC 3.0 parser
Summary:
This patch introduce the parser for OpenACC 3.0 in Flang. It uses the same TableGen mechanism
than OpenMP.
Reviewers: nvdatian, sscalpone, tskeith, klausler, ichoyjx, jdoerfert, DavidTruby
Reviewed By: klausler
Subscribers: MaskRay, SouraVX, mgorny, hiraditya, jfb, sstefan1, llvm-commits
Tags: #llvm, #flang
Differential Revision: https://reviews.llvm.org/D83649
2020-07-15 02:28:34 +08:00
|
|
|
void Unparse(const OpenACCWaitConstruct &x) {
|
|
|
|
BeginOpenACC();
|
|
|
|
Word("!$ACC ");
|
|
|
|
Word("WAIT(");
|
|
|
|
Walk(std::get<std::optional<AccWaitArgument>>(x.t));
|
|
|
|
Walk(std::get<AccClauseList>(x.t));
|
|
|
|
Put(")");
|
|
|
|
Put("\n");
|
|
|
|
EndOpenACC();
|
|
|
|
}
|
|
|
|
|
2018-06-02 01:40:13 +08:00
|
|
|
// OpenMP Clauses & Directives
|
2018-07-21 06:49:19 +08:00
|
|
|
void Unparse(const OmpObject &x) {
|
2020-03-29 12:00:16 +08:00
|
|
|
std::visit(common::visitors{
|
|
|
|
[&](const Designator &y) { Walk(y); },
|
|
|
|
[&](const Name &y) { Put("/"), Walk(y), Put("/"); },
|
|
|
|
},
|
2019-09-19 00:43:31 +08:00
|
|
|
x.u);
|
2018-06-02 01:40:13 +08:00
|
|
|
}
|
2019-08-16 04:50:27 +08:00
|
|
|
void Unparse(const OmpMapType::Always &) { Word("ALWAYS,"); }
|
2018-06-02 01:40:13 +08:00
|
|
|
void Unparse(const OmpMapClause &x) {
|
2018-07-21 06:49:19 +08:00
|
|
|
Word("MAP(");
|
|
|
|
Walk(std::get<std::optional<OmpMapType>>(x.t), ":");
|
|
|
|
Walk(std::get<OmpObjectList>(x.t));
|
2018-06-02 01:40:13 +08:00
|
|
|
Put(") ");
|
|
|
|
}
|
|
|
|
void Unparse(const OmpScheduleModifier &x) {
|
|
|
|
Walk(std::get<OmpScheduleModifier::Modifier1>(x.t));
|
|
|
|
Walk(",", std::get<std::optional<OmpScheduleModifier::Modifier2>>(x.t));
|
|
|
|
}
|
|
|
|
void Unparse(const OmpScheduleClause &x) {
|
2018-07-21 06:49:19 +08:00
|
|
|
Word("SCHEDULE(");
|
2019-05-09 05:05:44 +08:00
|
|
|
Walk(std::get<std::optional<OmpScheduleModifier>>(x.t), ":");
|
2018-06-02 01:40:13 +08:00
|
|
|
Walk(std::get<OmpScheduleClause::ScheduleType>(x.t));
|
2018-06-02 05:36:51 +08:00
|
|
|
Walk(",", std::get<std::optional<ScalarIntExpr>>(x.t));
|
2018-06-02 01:40:13 +08:00
|
|
|
Put(")");
|
|
|
|
}
|
|
|
|
void Unparse(const OmpAlignedClause &x) {
|
2018-07-21 06:49:19 +08:00
|
|
|
Word("ALIGNED("), Walk(std::get<std::list<Name>>(x.t), ",");
|
2018-06-02 01:40:13 +08:00
|
|
|
Walk(std::get<std::optional<ScalarIntConstantExpr>>(x.t));
|
|
|
|
Put(") ");
|
|
|
|
}
|
|
|
|
void Unparse(const OmpIfClause &x) {
|
2018-07-21 06:49:19 +08:00
|
|
|
Word("IF("),
|
2018-06-02 02:15:32 +08:00
|
|
|
Walk(std::get<std::optional<OmpIfClause::DirectiveNameModifier>>(x.t),
|
|
|
|
":");
|
2018-06-02 01:40:13 +08:00
|
|
|
Walk(std::get<ScalarLogicalExpr>(x.t));
|
|
|
|
Put(") ");
|
|
|
|
}
|
|
|
|
void Unparse(const OmpLinearClause::WithoutModifier &x) {
|
2018-07-21 06:49:19 +08:00
|
|
|
Word("LINEAR("), Walk(x.names, ", ");
|
2018-06-02 01:40:13 +08:00
|
|
|
Walk(":", x.step);
|
|
|
|
Put(")");
|
|
|
|
}
|
|
|
|
void Unparse(const OmpLinearClause::WithModifier &x) {
|
2018-07-21 06:49:19 +08:00
|
|
|
Word("LINEAR("), Walk(x.modifier), Put("("), Walk(x.names, ","), Put(")");
|
2018-06-02 01:40:13 +08:00
|
|
|
Walk(":", x.step);
|
|
|
|
Put(")");
|
|
|
|
}
|
|
|
|
void Unparse(const OmpReductionClause &x) {
|
2018-07-21 06:49:19 +08:00
|
|
|
Word("REDUCTION(");
|
2018-06-02 01:40:13 +08:00
|
|
|
Walk(std::get<OmpReductionOperator>(x.t));
|
|
|
|
Put(":");
|
|
|
|
Walk(std::get<std::list<Designator>>(x.t), ",");
|
|
|
|
Put(")");
|
|
|
|
}
|
2020-08-05 22:58:13 +08:00
|
|
|
void Unparse(const OmpAllocateClause &x) {
|
|
|
|
Word("ALLOCATE(");
|
|
|
|
Walk(std::get<std::optional<OmpAllocateClause::Allocator>>(x.t), ":");
|
|
|
|
Walk(std::get<OmpObjectList>(x.t));
|
|
|
|
Put(")");
|
|
|
|
}
|
2018-06-02 01:40:13 +08:00
|
|
|
void Unparse(const OmpDependSinkVecLength &x) {
|
2019-07-13 02:12:34 +08:00
|
|
|
Walk(std::get<DefinedOperator>(x.t));
|
2018-06-02 01:40:13 +08:00
|
|
|
Walk(std::get<ScalarIntConstantExpr>(x.t));
|
|
|
|
}
|
|
|
|
void Unparse(const OmpDependSinkVec &x) {
|
|
|
|
Walk(std::get<Name>(x.t));
|
|
|
|
Walk(std::get<std::optional<OmpDependSinkVecLength>>(x.t));
|
|
|
|
}
|
|
|
|
void Unparse(const OmpDependClause::InOut &x) {
|
2018-07-21 06:49:19 +08:00
|
|
|
Put("(");
|
2018-06-02 01:40:13 +08:00
|
|
|
Walk(std::get<OmpDependenceType>(x.t));
|
|
|
|
Put(":");
|
|
|
|
Walk(std::get<std::list<Designator>>(x.t), ",");
|
2018-07-21 06:49:19 +08:00
|
|
|
Put(")");
|
2018-06-02 01:40:13 +08:00
|
|
|
}
|
2018-07-21 06:49:19 +08:00
|
|
|
bool Pre(const OmpDependClause &x) {
|
2020-03-29 12:00:16 +08:00
|
|
|
return std::visit(common::visitors{
|
|
|
|
[&](const OmpDependClause::Source &) {
|
|
|
|
Word("DEPEND(SOURCE)");
|
|
|
|
return false;
|
|
|
|
},
|
|
|
|
[&](const OmpDependClause::Sink &y) {
|
|
|
|
Word("DEPEND(SINK:");
|
|
|
|
Walk(y.v);
|
|
|
|
Put(")");
|
|
|
|
return false;
|
|
|
|
},
|
|
|
|
[&](const OmpDependClause::InOut &) {
|
|
|
|
Word("DEPEND");
|
|
|
|
return true;
|
|
|
|
},
|
|
|
|
},
|
2018-06-02 01:40:13 +08:00
|
|
|
x.u);
|
|
|
|
}
|
2019-08-16 04:50:27 +08:00
|
|
|
bool Pre(const OmpDefaultClause &) {
|
2018-07-21 06:49:19 +08:00
|
|
|
Word("DEFAULT(");
|
|
|
|
return true;
|
|
|
|
}
|
2019-08-16 04:50:27 +08:00
|
|
|
void Post(const OmpDefaultClause &) { Put(")"); }
|
|
|
|
bool Pre(const OmpProcBindClause &) {
|
2018-07-21 06:49:19 +08:00
|
|
|
Word("PROC_BIND(");
|
|
|
|
return true;
|
|
|
|
}
|
2019-08-16 04:50:27 +08:00
|
|
|
void Post(const OmpProcBindClause &) { Put(")"); }
|
2019-09-09 05:52:43 +08:00
|
|
|
void Unparse(const OmpDefaultmapClause &x) {
|
|
|
|
Word("DEFAULTMAP(");
|
|
|
|
Walk(std::get<OmpDefaultmapClause::ImplicitBehavior>(x.t));
|
|
|
|
Walk(":",
|
|
|
|
std::get<std::optional<OmpDefaultmapClause::VariableCategory>>(x.t));
|
|
|
|
Word(")");
|
2018-06-02 02:15:32 +08:00
|
|
|
}
|
2018-07-21 06:49:19 +08:00
|
|
|
void Unparse(const OmpNowait &) { Word("NOWAIT"); }
|
2020-08-18 02:22:01 +08:00
|
|
|
void Unparse(const OmpDistScheduleClause &x) {
|
2019-10-03 17:37:05 +08:00
|
|
|
Word("DIST_SCHEDULE(STATIC");
|
|
|
|
Walk(", ", x.v);
|
2018-06-02 02:15:32 +08:00
|
|
|
Put(")");
|
2018-06-02 01:40:13 +08:00
|
|
|
}
|
2020-08-18 02:22:01 +08:00
|
|
|
#define GEN_FLANG_CLAUSE_UNPARSE
|
2020-12-18 03:07:29 +08:00
|
|
|
#include "llvm/Frontend/OpenMP/OMP.inc"
|
2018-06-02 01:40:13 +08:00
|
|
|
void Unparse(const OmpLoopDirective &x) {
|
2019-07-13 04:35:22 +08:00
|
|
|
switch (x.v) {
|
[flang][openmp] Use common Directive and Clause enum from llvm/Frontend
Summary:
This patch is removing the custom enumeration for OpenMP Directives and Clauses and replace them
with the newly tablegen generated one from llvm/Frontend. This is a first patch and some will follow to share the same
infrastructure where possible. The next patch should use the clauses allowance defined in the tablegen file.
Reviewers: jdoerfert, DavidTruby, sscalpone, kiranchandramohan, ichoyjx
Reviewed By: DavidTruby, ichoyjx
Subscribers: jholewinski, cfe-commits, dblaikie, MaskRay, ymandel, ichoyjx, mgorny, yaxunl, guansong, jfb, sstefan1, aaron.ballman, llvm-commits
Tags: #llvm, #flang, #clang
Differential Revision: https://reviews.llvm.org/D82906
2020-07-02 08:57:11 +08:00
|
|
|
case llvm::omp::Directive::OMPD_distribute:
|
2020-03-29 12:00:16 +08:00
|
|
|
Word("DISTRIBUTE ");
|
|
|
|
break;
|
[flang][openmp] Use common Directive and Clause enum from llvm/Frontend
Summary:
This patch is removing the custom enumeration for OpenMP Directives and Clauses and replace them
with the newly tablegen generated one from llvm/Frontend. This is a first patch and some will follow to share the same
infrastructure where possible. The next patch should use the clauses allowance defined in the tablegen file.
Reviewers: jdoerfert, DavidTruby, sscalpone, kiranchandramohan, ichoyjx
Reviewed By: DavidTruby, ichoyjx
Subscribers: jholewinski, cfe-commits, dblaikie, MaskRay, ymandel, ichoyjx, mgorny, yaxunl, guansong, jfb, sstefan1, aaron.ballman, llvm-commits
Tags: #llvm, #flang, #clang
Differential Revision: https://reviews.llvm.org/D82906
2020-07-02 08:57:11 +08:00
|
|
|
case llvm::omp::Directive::OMPD_distribute_parallel_do:
|
2019-07-13 04:35:22 +08:00
|
|
|
Word("DISTRIBUTE PARALLEL DO ");
|
|
|
|
break;
|
[flang][openmp] Use common Directive and Clause enum from llvm/Frontend
Summary:
This patch is removing the custom enumeration for OpenMP Directives and Clauses and replace them
with the newly tablegen generated one from llvm/Frontend. This is a first patch and some will follow to share the same
infrastructure where possible. The next patch should use the clauses allowance defined in the tablegen file.
Reviewers: jdoerfert, DavidTruby, sscalpone, kiranchandramohan, ichoyjx
Reviewed By: DavidTruby, ichoyjx
Subscribers: jholewinski, cfe-commits, dblaikie, MaskRay, ymandel, ichoyjx, mgorny, yaxunl, guansong, jfb, sstefan1, aaron.ballman, llvm-commits
Tags: #llvm, #flang, #clang
Differential Revision: https://reviews.llvm.org/D82906
2020-07-02 08:57:11 +08:00
|
|
|
case llvm::omp::Directive::OMPD_distribute_parallel_do_simd:
|
2019-07-13 04:35:22 +08:00
|
|
|
Word("DISTRIBUTE PARALLEL DO SIMD ");
|
|
|
|
break;
|
[flang][openmp] Use common Directive and Clause enum from llvm/Frontend
Summary:
This patch is removing the custom enumeration for OpenMP Directives and Clauses and replace them
with the newly tablegen generated one from llvm/Frontend. This is a first patch and some will follow to share the same
infrastructure where possible. The next patch should use the clauses allowance defined in the tablegen file.
Reviewers: jdoerfert, DavidTruby, sscalpone, kiranchandramohan, ichoyjx
Reviewed By: DavidTruby, ichoyjx
Subscribers: jholewinski, cfe-commits, dblaikie, MaskRay, ymandel, ichoyjx, mgorny, yaxunl, guansong, jfb, sstefan1, aaron.ballman, llvm-commits
Tags: #llvm, #flang, #clang
Differential Revision: https://reviews.llvm.org/D82906
2020-07-02 08:57:11 +08:00
|
|
|
case llvm::omp::Directive::OMPD_distribute_simd:
|
2019-07-13 04:35:22 +08:00
|
|
|
Word("DISTRIBUTE SIMD ");
|
|
|
|
break;
|
[flang][openmp] Use common Directive and Clause enum from llvm/Frontend
Summary:
This patch is removing the custom enumeration for OpenMP Directives and Clauses and replace them
with the newly tablegen generated one from llvm/Frontend. This is a first patch and some will follow to share the same
infrastructure where possible. The next patch should use the clauses allowance defined in the tablegen file.
Reviewers: jdoerfert, DavidTruby, sscalpone, kiranchandramohan, ichoyjx
Reviewed By: DavidTruby, ichoyjx
Subscribers: jholewinski, cfe-commits, dblaikie, MaskRay, ymandel, ichoyjx, mgorny, yaxunl, guansong, jfb, sstefan1, aaron.ballman, llvm-commits
Tags: #llvm, #flang, #clang
Differential Revision: https://reviews.llvm.org/D82906
2020-07-02 08:57:11 +08:00
|
|
|
case llvm::omp::Directive::OMPD_do:
|
2020-03-29 12:00:16 +08:00
|
|
|
Word("DO ");
|
|
|
|
break;
|
[flang][openmp] Use common Directive and Clause enum from llvm/Frontend
Summary:
This patch is removing the custom enumeration for OpenMP Directives and Clauses and replace them
with the newly tablegen generated one from llvm/Frontend. This is a first patch and some will follow to share the same
infrastructure where possible. The next patch should use the clauses allowance defined in the tablegen file.
Reviewers: jdoerfert, DavidTruby, sscalpone, kiranchandramohan, ichoyjx
Reviewed By: DavidTruby, ichoyjx
Subscribers: jholewinski, cfe-commits, dblaikie, MaskRay, ymandel, ichoyjx, mgorny, yaxunl, guansong, jfb, sstefan1, aaron.ballman, llvm-commits
Tags: #llvm, #flang, #clang
Differential Revision: https://reviews.llvm.org/D82906
2020-07-02 08:57:11 +08:00
|
|
|
case llvm::omp::Directive::OMPD_do_simd:
|
|
|
|
Word("DO SIMD ");
|
2020-03-29 12:00:16 +08:00
|
|
|
break;
|
[flang][openmp] Use common Directive and Clause enum from llvm/Frontend
Summary:
This patch is removing the custom enumeration for OpenMP Directives and Clauses and replace them
with the newly tablegen generated one from llvm/Frontend. This is a first patch and some will follow to share the same
infrastructure where possible. The next patch should use the clauses allowance defined in the tablegen file.
Reviewers: jdoerfert, DavidTruby, sscalpone, kiranchandramohan, ichoyjx
Reviewed By: DavidTruby, ichoyjx
Subscribers: jholewinski, cfe-commits, dblaikie, MaskRay, ymandel, ichoyjx, mgorny, yaxunl, guansong, jfb, sstefan1, aaron.ballman, llvm-commits
Tags: #llvm, #flang, #clang
Differential Revision: https://reviews.llvm.org/D82906
2020-07-02 08:57:11 +08:00
|
|
|
case llvm::omp::Directive::OMPD_parallel_do:
|
2020-03-29 12:00:16 +08:00
|
|
|
Word("PARALLEL DO ");
|
|
|
|
break;
|
[flang][openmp] Use common Directive and Clause enum from llvm/Frontend
Summary:
This patch is removing the custom enumeration for OpenMP Directives and Clauses and replace them
with the newly tablegen generated one from llvm/Frontend. This is a first patch and some will follow to share the same
infrastructure where possible. The next patch should use the clauses allowance defined in the tablegen file.
Reviewers: jdoerfert, DavidTruby, sscalpone, kiranchandramohan, ichoyjx
Reviewed By: DavidTruby, ichoyjx
Subscribers: jholewinski, cfe-commits, dblaikie, MaskRay, ymandel, ichoyjx, mgorny, yaxunl, guansong, jfb, sstefan1, aaron.ballman, llvm-commits
Tags: #llvm, #flang, #clang
Differential Revision: https://reviews.llvm.org/D82906
2020-07-02 08:57:11 +08:00
|
|
|
case llvm::omp::Directive::OMPD_parallel_do_simd:
|
2019-07-13 04:35:22 +08:00
|
|
|
Word("PARALLEL DO SIMD ");
|
|
|
|
break;
|
[flang][openmp] Use common Directive and Clause enum from llvm/Frontend
Summary:
This patch is removing the custom enumeration for OpenMP Directives and Clauses and replace them
with the newly tablegen generated one from llvm/Frontend. This is a first patch and some will follow to share the same
infrastructure where possible. The next patch should use the clauses allowance defined in the tablegen file.
Reviewers: jdoerfert, DavidTruby, sscalpone, kiranchandramohan, ichoyjx
Reviewed By: DavidTruby, ichoyjx
Subscribers: jholewinski, cfe-commits, dblaikie, MaskRay, ymandel, ichoyjx, mgorny, yaxunl, guansong, jfb, sstefan1, aaron.ballman, llvm-commits
Tags: #llvm, #flang, #clang
Differential Revision: https://reviews.llvm.org/D82906
2020-07-02 08:57:11 +08:00
|
|
|
case llvm::omp::Directive::OMPD_simd:
|
2020-03-29 12:00:16 +08:00
|
|
|
Word("SIMD ");
|
|
|
|
break;
|
[flang][openmp] Use common Directive and Clause enum from llvm/Frontend
Summary:
This patch is removing the custom enumeration for OpenMP Directives and Clauses and replace them
with the newly tablegen generated one from llvm/Frontend. This is a first patch and some will follow to share the same
infrastructure where possible. The next patch should use the clauses allowance defined in the tablegen file.
Reviewers: jdoerfert, DavidTruby, sscalpone, kiranchandramohan, ichoyjx
Reviewed By: DavidTruby, ichoyjx
Subscribers: jholewinski, cfe-commits, dblaikie, MaskRay, ymandel, ichoyjx, mgorny, yaxunl, guansong, jfb, sstefan1, aaron.ballman, llvm-commits
Tags: #llvm, #flang, #clang
Differential Revision: https://reviews.llvm.org/D82906
2020-07-02 08:57:11 +08:00
|
|
|
case llvm::omp::Directive::OMPD_target_parallel_do:
|
2019-07-13 04:35:22 +08:00
|
|
|
Word("TARGET PARALLEL DO ");
|
|
|
|
break;
|
[flang][openmp] Use common Directive and Clause enum from llvm/Frontend
Summary:
This patch is removing the custom enumeration for OpenMP Directives and Clauses and replace them
with the newly tablegen generated one from llvm/Frontend. This is a first patch and some will follow to share the same
infrastructure where possible. The next patch should use the clauses allowance defined in the tablegen file.
Reviewers: jdoerfert, DavidTruby, sscalpone, kiranchandramohan, ichoyjx
Reviewed By: DavidTruby, ichoyjx
Subscribers: jholewinski, cfe-commits, dblaikie, MaskRay, ymandel, ichoyjx, mgorny, yaxunl, guansong, jfb, sstefan1, aaron.ballman, llvm-commits
Tags: #llvm, #flang, #clang
Differential Revision: https://reviews.llvm.org/D82906
2020-07-02 08:57:11 +08:00
|
|
|
case llvm::omp::Directive::OMPD_target_parallel_do_simd:
|
2019-07-13 04:35:22 +08:00
|
|
|
Word("TARGET PARALLEL DO SIMD ");
|
|
|
|
break;
|
[flang][openmp] Use common Directive and Clause enum from llvm/Frontend
Summary:
This patch is removing the custom enumeration for OpenMP Directives and Clauses and replace them
with the newly tablegen generated one from llvm/Frontend. This is a first patch and some will follow to share the same
infrastructure where possible. The next patch should use the clauses allowance defined in the tablegen file.
Reviewers: jdoerfert, DavidTruby, sscalpone, kiranchandramohan, ichoyjx
Reviewed By: DavidTruby, ichoyjx
Subscribers: jholewinski, cfe-commits, dblaikie, MaskRay, ymandel, ichoyjx, mgorny, yaxunl, guansong, jfb, sstefan1, aaron.ballman, llvm-commits
Tags: #llvm, #flang, #clang
Differential Revision: https://reviews.llvm.org/D82906
2020-07-02 08:57:11 +08:00
|
|
|
case llvm::omp::Directive::OMPD_target_teams_distribute:
|
2019-07-13 04:35:22 +08:00
|
|
|
Word("TARGET TEAMS DISTRIBUTE ");
|
|
|
|
break;
|
[flang][openmp] Use common Directive and Clause enum from llvm/Frontend
Summary:
This patch is removing the custom enumeration for OpenMP Directives and Clauses and replace them
with the newly tablegen generated one from llvm/Frontend. This is a first patch and some will follow to share the same
infrastructure where possible. The next patch should use the clauses allowance defined in the tablegen file.
Reviewers: jdoerfert, DavidTruby, sscalpone, kiranchandramohan, ichoyjx
Reviewed By: DavidTruby, ichoyjx
Subscribers: jholewinski, cfe-commits, dblaikie, MaskRay, ymandel, ichoyjx, mgorny, yaxunl, guansong, jfb, sstefan1, aaron.ballman, llvm-commits
Tags: #llvm, #flang, #clang
Differential Revision: https://reviews.llvm.org/D82906
2020-07-02 08:57:11 +08:00
|
|
|
case llvm::omp::Directive::OMPD_target_teams_distribute_parallel_do:
|
2019-07-13 04:35:22 +08:00
|
|
|
Word("TARGET TEAMS DISTRIBUTE PARALLEL DO ");
|
|
|
|
break;
|
[flang][openmp] Use common Directive and Clause enum from llvm/Frontend
Summary:
This patch is removing the custom enumeration for OpenMP Directives and Clauses and replace them
with the newly tablegen generated one from llvm/Frontend. This is a first patch and some will follow to share the same
infrastructure where possible. The next patch should use the clauses allowance defined in the tablegen file.
Reviewers: jdoerfert, DavidTruby, sscalpone, kiranchandramohan, ichoyjx
Reviewed By: DavidTruby, ichoyjx
Subscribers: jholewinski, cfe-commits, dblaikie, MaskRay, ymandel, ichoyjx, mgorny, yaxunl, guansong, jfb, sstefan1, aaron.ballman, llvm-commits
Tags: #llvm, #flang, #clang
Differential Revision: https://reviews.llvm.org/D82906
2020-07-02 08:57:11 +08:00
|
|
|
case llvm::omp::Directive::OMPD_target_teams_distribute_parallel_do_simd:
|
2019-07-13 04:35:22 +08:00
|
|
|
Word("TARGET TEAMS DISTRIBUTE PARALLEL DO SIMD ");
|
|
|
|
break;
|
[flang][openmp] Use common Directive and Clause enum from llvm/Frontend
Summary:
This patch is removing the custom enumeration for OpenMP Directives and Clauses and replace them
with the newly tablegen generated one from llvm/Frontend. This is a first patch and some will follow to share the same
infrastructure where possible. The next patch should use the clauses allowance defined in the tablegen file.
Reviewers: jdoerfert, DavidTruby, sscalpone, kiranchandramohan, ichoyjx
Reviewed By: DavidTruby, ichoyjx
Subscribers: jholewinski, cfe-commits, dblaikie, MaskRay, ymandel, ichoyjx, mgorny, yaxunl, guansong, jfb, sstefan1, aaron.ballman, llvm-commits
Tags: #llvm, #flang, #clang
Differential Revision: https://reviews.llvm.org/D82906
2020-07-02 08:57:11 +08:00
|
|
|
case llvm::omp::Directive::OMPD_target_teams_distribute_simd:
|
2019-07-13 04:35:22 +08:00
|
|
|
Word("TARGET TEAMS DISTRIBUTE SIMD ");
|
|
|
|
break;
|
[flang][openmp] Use common Directive and Clause enum from llvm/Frontend
Summary:
This patch is removing the custom enumeration for OpenMP Directives and Clauses and replace them
with the newly tablegen generated one from llvm/Frontend. This is a first patch and some will follow to share the same
infrastructure where possible. The next patch should use the clauses allowance defined in the tablegen file.
Reviewers: jdoerfert, DavidTruby, sscalpone, kiranchandramohan, ichoyjx
Reviewed By: DavidTruby, ichoyjx
Subscribers: jholewinski, cfe-commits, dblaikie, MaskRay, ymandel, ichoyjx, mgorny, yaxunl, guansong, jfb, sstefan1, aaron.ballman, llvm-commits
Tags: #llvm, #flang, #clang
Differential Revision: https://reviews.llvm.org/D82906
2020-07-02 08:57:11 +08:00
|
|
|
case llvm::omp::Directive::OMPD_target_simd:
|
2020-03-29 12:00:16 +08:00
|
|
|
Word("TARGET SIMD ");
|
|
|
|
break;
|
[flang][openmp] Use common Directive and Clause enum from llvm/Frontend
Summary:
This patch is removing the custom enumeration for OpenMP Directives and Clauses and replace them
with the newly tablegen generated one from llvm/Frontend. This is a first patch and some will follow to share the same
infrastructure where possible. The next patch should use the clauses allowance defined in the tablegen file.
Reviewers: jdoerfert, DavidTruby, sscalpone, kiranchandramohan, ichoyjx
Reviewed By: DavidTruby, ichoyjx
Subscribers: jholewinski, cfe-commits, dblaikie, MaskRay, ymandel, ichoyjx, mgorny, yaxunl, guansong, jfb, sstefan1, aaron.ballman, llvm-commits
Tags: #llvm, #flang, #clang
Differential Revision: https://reviews.llvm.org/D82906
2020-07-02 08:57:11 +08:00
|
|
|
case llvm::omp::Directive::OMPD_taskloop:
|
2020-03-29 12:00:16 +08:00
|
|
|
Word("TASKLOOP ");
|
|
|
|
break;
|
[flang][openmp] Use common Directive and Clause enum from llvm/Frontend
Summary:
This patch is removing the custom enumeration for OpenMP Directives and Clauses and replace them
with the newly tablegen generated one from llvm/Frontend. This is a first patch and some will follow to share the same
infrastructure where possible. The next patch should use the clauses allowance defined in the tablegen file.
Reviewers: jdoerfert, DavidTruby, sscalpone, kiranchandramohan, ichoyjx
Reviewed By: DavidTruby, ichoyjx
Subscribers: jholewinski, cfe-commits, dblaikie, MaskRay, ymandel, ichoyjx, mgorny, yaxunl, guansong, jfb, sstefan1, aaron.ballman, llvm-commits
Tags: #llvm, #flang, #clang
Differential Revision: https://reviews.llvm.org/D82906
2020-07-02 08:57:11 +08:00
|
|
|
case llvm::omp::Directive::OMPD_taskloop_simd:
|
2019-07-13 04:35:22 +08:00
|
|
|
Word("TASKLOOP SIMD ");
|
|
|
|
break;
|
[flang][openmp] Use common Directive and Clause enum from llvm/Frontend
Summary:
This patch is removing the custom enumeration for OpenMP Directives and Clauses and replace them
with the newly tablegen generated one from llvm/Frontend. This is a first patch and some will follow to share the same
infrastructure where possible. The next patch should use the clauses allowance defined in the tablegen file.
Reviewers: jdoerfert, DavidTruby, sscalpone, kiranchandramohan, ichoyjx
Reviewed By: DavidTruby, ichoyjx
Subscribers: jholewinski, cfe-commits, dblaikie, MaskRay, ymandel, ichoyjx, mgorny, yaxunl, guansong, jfb, sstefan1, aaron.ballman, llvm-commits
Tags: #llvm, #flang, #clang
Differential Revision: https://reviews.llvm.org/D82906
2020-07-02 08:57:11 +08:00
|
|
|
case llvm::omp::Directive::OMPD_teams_distribute:
|
2019-07-13 04:35:22 +08:00
|
|
|
Word("TEAMS DISTRIBUTE ");
|
|
|
|
break;
|
[flang][openmp] Use common Directive and Clause enum from llvm/Frontend
Summary:
This patch is removing the custom enumeration for OpenMP Directives and Clauses and replace them
with the newly tablegen generated one from llvm/Frontend. This is a first patch and some will follow to share the same
infrastructure where possible. The next patch should use the clauses allowance defined in the tablegen file.
Reviewers: jdoerfert, DavidTruby, sscalpone, kiranchandramohan, ichoyjx
Reviewed By: DavidTruby, ichoyjx
Subscribers: jholewinski, cfe-commits, dblaikie, MaskRay, ymandel, ichoyjx, mgorny, yaxunl, guansong, jfb, sstefan1, aaron.ballman, llvm-commits
Tags: #llvm, #flang, #clang
Differential Revision: https://reviews.llvm.org/D82906
2020-07-02 08:57:11 +08:00
|
|
|
case llvm::omp::Directive::OMPD_teams_distribute_parallel_do:
|
2019-07-13 04:35:22 +08:00
|
|
|
Word("TEAMS DISTRIBUTE PARALLEL DO ");
|
|
|
|
break;
|
[flang][openmp] Use common Directive and Clause enum from llvm/Frontend
Summary:
This patch is removing the custom enumeration for OpenMP Directives and Clauses and replace them
with the newly tablegen generated one from llvm/Frontend. This is a first patch and some will follow to share the same
infrastructure where possible. The next patch should use the clauses allowance defined in the tablegen file.
Reviewers: jdoerfert, DavidTruby, sscalpone, kiranchandramohan, ichoyjx
Reviewed By: DavidTruby, ichoyjx
Subscribers: jholewinski, cfe-commits, dblaikie, MaskRay, ymandel, ichoyjx, mgorny, yaxunl, guansong, jfb, sstefan1, aaron.ballman, llvm-commits
Tags: #llvm, #flang, #clang
Differential Revision: https://reviews.llvm.org/D82906
2020-07-02 08:57:11 +08:00
|
|
|
case llvm::omp::Directive::OMPD_teams_distribute_parallel_do_simd:
|
2019-07-13 04:35:22 +08:00
|
|
|
Word("TEAMS DISTRIBUTE PARALLEL DO SIMD ");
|
|
|
|
break;
|
[flang][openmp] Use common Directive and Clause enum from llvm/Frontend
Summary:
This patch is removing the custom enumeration for OpenMP Directives and Clauses and replace them
with the newly tablegen generated one from llvm/Frontend. This is a first patch and some will follow to share the same
infrastructure where possible. The next patch should use the clauses allowance defined in the tablegen file.
Reviewers: jdoerfert, DavidTruby, sscalpone, kiranchandramohan, ichoyjx
Reviewed By: DavidTruby, ichoyjx
Subscribers: jholewinski, cfe-commits, dblaikie, MaskRay, ymandel, ichoyjx, mgorny, yaxunl, guansong, jfb, sstefan1, aaron.ballman, llvm-commits
Tags: #llvm, #flang, #clang
Differential Revision: https://reviews.llvm.org/D82906
2020-07-02 08:57:11 +08:00
|
|
|
case llvm::omp::Directive::OMPD_teams_distribute_simd:
|
2019-07-13 04:35:22 +08:00
|
|
|
Word("TEAMS DISTRIBUTE SIMD ");
|
|
|
|
break;
|
[flang][openmp] Use common Directive and Clause enum from llvm/Frontend
Summary:
This patch is removing the custom enumeration for OpenMP Directives and Clauses and replace them
with the newly tablegen generated one from llvm/Frontend. This is a first patch and some will follow to share the same
infrastructure where possible. The next patch should use the clauses allowance defined in the tablegen file.
Reviewers: jdoerfert, DavidTruby, sscalpone, kiranchandramohan, ichoyjx
Reviewed By: DavidTruby, ichoyjx
Subscribers: jholewinski, cfe-commits, dblaikie, MaskRay, ymandel, ichoyjx, mgorny, yaxunl, guansong, jfb, sstefan1, aaron.ballman, llvm-commits
Tags: #llvm, #flang, #clang
Differential Revision: https://reviews.llvm.org/D82906
2020-07-02 08:57:11 +08:00
|
|
|
default:
|
|
|
|
break;
|
2019-07-13 04:35:22 +08:00
|
|
|
}
|
2018-06-02 01:40:13 +08:00
|
|
|
}
|
2018-07-21 06:49:19 +08:00
|
|
|
void Unparse(const OmpObjectList &x) { Walk(x.v, ","); }
|
2019-08-07 02:59:40 +08:00
|
|
|
void Unparse(const OmpSimpleStandaloneDirective &x) {
|
2019-07-13 04:57:58 +08:00
|
|
|
switch (x.v) {
|
[flang][openmp] Use common Directive and Clause enum from llvm/Frontend
Summary:
This patch is removing the custom enumeration for OpenMP Directives and Clauses and replace them
with the newly tablegen generated one from llvm/Frontend. This is a first patch and some will follow to share the same
infrastructure where possible. The next patch should use the clauses allowance defined in the tablegen file.
Reviewers: jdoerfert, DavidTruby, sscalpone, kiranchandramohan, ichoyjx
Reviewed By: DavidTruby, ichoyjx
Subscribers: jholewinski, cfe-commits, dblaikie, MaskRay, ymandel, ichoyjx, mgorny, yaxunl, guansong, jfb, sstefan1, aaron.ballman, llvm-commits
Tags: #llvm, #flang, #clang
Differential Revision: https://reviews.llvm.org/D82906
2020-07-02 08:57:11 +08:00
|
|
|
case llvm::omp::Directive::OMPD_barrier:
|
2019-08-07 02:59:40 +08:00
|
|
|
Word("BARRIER ");
|
|
|
|
break;
|
[flang][openmp] Use common Directive and Clause enum from llvm/Frontend
Summary:
This patch is removing the custom enumeration for OpenMP Directives and Clauses and replace them
with the newly tablegen generated one from llvm/Frontend. This is a first patch and some will follow to share the same
infrastructure where possible. The next patch should use the clauses allowance defined in the tablegen file.
Reviewers: jdoerfert, DavidTruby, sscalpone, kiranchandramohan, ichoyjx
Reviewed By: DavidTruby, ichoyjx
Subscribers: jholewinski, cfe-commits, dblaikie, MaskRay, ymandel, ichoyjx, mgorny, yaxunl, guansong, jfb, sstefan1, aaron.ballman, llvm-commits
Tags: #llvm, #flang, #clang
Differential Revision: https://reviews.llvm.org/D82906
2020-07-02 08:57:11 +08:00
|
|
|
case llvm::omp::Directive::OMPD_taskwait:
|
2019-08-07 02:59:40 +08:00
|
|
|
Word("TASKWAIT ");
|
|
|
|
break;
|
[flang][openmp] Use common Directive and Clause enum from llvm/Frontend
Summary:
This patch is removing the custom enumeration for OpenMP Directives and Clauses and replace them
with the newly tablegen generated one from llvm/Frontend. This is a first patch and some will follow to share the same
infrastructure where possible. The next patch should use the clauses allowance defined in the tablegen file.
Reviewers: jdoerfert, DavidTruby, sscalpone, kiranchandramohan, ichoyjx
Reviewed By: DavidTruby, ichoyjx
Subscribers: jholewinski, cfe-commits, dblaikie, MaskRay, ymandel, ichoyjx, mgorny, yaxunl, guansong, jfb, sstefan1, aaron.ballman, llvm-commits
Tags: #llvm, #flang, #clang
Differential Revision: https://reviews.llvm.org/D82906
2020-07-02 08:57:11 +08:00
|
|
|
case llvm::omp::Directive::OMPD_taskyield:
|
2019-08-07 02:59:40 +08:00
|
|
|
Word("TASKYIELD ");
|
|
|
|
break;
|
[flang][openmp] Use common Directive and Clause enum from llvm/Frontend
Summary:
This patch is removing the custom enumeration for OpenMP Directives and Clauses and replace them
with the newly tablegen generated one from llvm/Frontend. This is a first patch and some will follow to share the same
infrastructure where possible. The next patch should use the clauses allowance defined in the tablegen file.
Reviewers: jdoerfert, DavidTruby, sscalpone, kiranchandramohan, ichoyjx
Reviewed By: DavidTruby, ichoyjx
Subscribers: jholewinski, cfe-commits, dblaikie, MaskRay, ymandel, ichoyjx, mgorny, yaxunl, guansong, jfb, sstefan1, aaron.ballman, llvm-commits
Tags: #llvm, #flang, #clang
Differential Revision: https://reviews.llvm.org/D82906
2020-07-02 08:57:11 +08:00
|
|
|
case llvm::omp::Directive::OMPD_target_enter_data:
|
2019-07-13 04:57:58 +08:00
|
|
|
Word("TARGET ENTER DATA ");
|
|
|
|
break;
|
[flang][openmp] Use common Directive and Clause enum from llvm/Frontend
Summary:
This patch is removing the custom enumeration for OpenMP Directives and Clauses and replace them
with the newly tablegen generated one from llvm/Frontend. This is a first patch and some will follow to share the same
infrastructure where possible. The next patch should use the clauses allowance defined in the tablegen file.
Reviewers: jdoerfert, DavidTruby, sscalpone, kiranchandramohan, ichoyjx
Reviewed By: DavidTruby, ichoyjx
Subscribers: jholewinski, cfe-commits, dblaikie, MaskRay, ymandel, ichoyjx, mgorny, yaxunl, guansong, jfb, sstefan1, aaron.ballman, llvm-commits
Tags: #llvm, #flang, #clang
Differential Revision: https://reviews.llvm.org/D82906
2020-07-02 08:57:11 +08:00
|
|
|
case llvm::omp::Directive::OMPD_target_exit_data:
|
2019-07-13 04:57:58 +08:00
|
|
|
Word("TARGET EXIT DATA ");
|
|
|
|
break;
|
[flang][openmp] Use common Directive and Clause enum from llvm/Frontend
Summary:
This patch is removing the custom enumeration for OpenMP Directives and Clauses and replace them
with the newly tablegen generated one from llvm/Frontend. This is a first patch and some will follow to share the same
infrastructure where possible. The next patch should use the clauses allowance defined in the tablegen file.
Reviewers: jdoerfert, DavidTruby, sscalpone, kiranchandramohan, ichoyjx
Reviewed By: DavidTruby, ichoyjx
Subscribers: jholewinski, cfe-commits, dblaikie, MaskRay, ymandel, ichoyjx, mgorny, yaxunl, guansong, jfb, sstefan1, aaron.ballman, llvm-commits
Tags: #llvm, #flang, #clang
Differential Revision: https://reviews.llvm.org/D82906
2020-07-02 08:57:11 +08:00
|
|
|
case llvm::omp::Directive::OMPD_target_update:
|
2019-07-13 04:57:58 +08:00
|
|
|
Word("TARGET UPDATE ");
|
|
|
|
break;
|
[flang][openmp] Use common Directive and Clause enum from llvm/Frontend
Summary:
This patch is removing the custom enumeration for OpenMP Directives and Clauses and replace them
with the newly tablegen generated one from llvm/Frontend. This is a first patch and some will follow to share the same
infrastructure where possible. The next patch should use the clauses allowance defined in the tablegen file.
Reviewers: jdoerfert, DavidTruby, sscalpone, kiranchandramohan, ichoyjx
Reviewed By: DavidTruby, ichoyjx
Subscribers: jholewinski, cfe-commits, dblaikie, MaskRay, ymandel, ichoyjx, mgorny, yaxunl, guansong, jfb, sstefan1, aaron.ballman, llvm-commits
Tags: #llvm, #flang, #clang
Differential Revision: https://reviews.llvm.org/D82906
2020-07-02 08:57:11 +08:00
|
|
|
case llvm::omp::Directive::OMPD_ordered:
|
2019-08-07 02:59:40 +08:00
|
|
|
Word("ORDERED ");
|
|
|
|
break;
|
[flang][openmp] Use common Directive and Clause enum from llvm/Frontend
Summary:
This patch is removing the custom enumeration for OpenMP Directives and Clauses and replace them
with the newly tablegen generated one from llvm/Frontend. This is a first patch and some will follow to share the same
infrastructure where possible. The next patch should use the clauses allowance defined in the tablegen file.
Reviewers: jdoerfert, DavidTruby, sscalpone, kiranchandramohan, ichoyjx
Reviewed By: DavidTruby, ichoyjx
Subscribers: jholewinski, cfe-commits, dblaikie, MaskRay, ymandel, ichoyjx, mgorny, yaxunl, guansong, jfb, sstefan1, aaron.ballman, llvm-commits
Tags: #llvm, #flang, #clang
Differential Revision: https://reviews.llvm.org/D82906
2020-07-02 08:57:11 +08:00
|
|
|
default:
|
|
|
|
// Nothing to be done
|
|
|
|
break;
|
2019-07-13 04:57:58 +08:00
|
|
|
}
|
2018-07-21 06:49:19 +08:00
|
|
|
}
|
|
|
|
void Unparse(const OmpBlockDirective &x) {
|
2019-07-13 05:23:16 +08:00
|
|
|
switch (x.v) {
|
[flang][openmp] Use common Directive and Clause enum from llvm/Frontend
Summary:
This patch is removing the custom enumeration for OpenMP Directives and Clauses and replace them
with the newly tablegen generated one from llvm/Frontend. This is a first patch and some will follow to share the same
infrastructure where possible. The next patch should use the clauses allowance defined in the tablegen file.
Reviewers: jdoerfert, DavidTruby, sscalpone, kiranchandramohan, ichoyjx
Reviewed By: DavidTruby, ichoyjx
Subscribers: jholewinski, cfe-commits, dblaikie, MaskRay, ymandel, ichoyjx, mgorny, yaxunl, guansong, jfb, sstefan1, aaron.ballman, llvm-commits
Tags: #llvm, #flang, #clang
Differential Revision: https://reviews.llvm.org/D82906
2020-07-02 08:57:11 +08:00
|
|
|
case llvm::omp::Directive::OMPD_master:
|
2020-03-29 12:00:16 +08:00
|
|
|
Word("MASTER");
|
|
|
|
break;
|
[flang][openmp] Use common Directive and Clause enum from llvm/Frontend
Summary:
This patch is removing the custom enumeration for OpenMP Directives and Clauses and replace them
with the newly tablegen generated one from llvm/Frontend. This is a first patch and some will follow to share the same
infrastructure where possible. The next patch should use the clauses allowance defined in the tablegen file.
Reviewers: jdoerfert, DavidTruby, sscalpone, kiranchandramohan, ichoyjx
Reviewed By: DavidTruby, ichoyjx
Subscribers: jholewinski, cfe-commits, dblaikie, MaskRay, ymandel, ichoyjx, mgorny, yaxunl, guansong, jfb, sstefan1, aaron.ballman, llvm-commits
Tags: #llvm, #flang, #clang
Differential Revision: https://reviews.llvm.org/D82906
2020-07-02 08:57:11 +08:00
|
|
|
case llvm::omp::Directive::OMPD_ordered:
|
2020-03-29 12:00:16 +08:00
|
|
|
Word("ORDERED ");
|
|
|
|
break;
|
[flang][openmp] Use common Directive and Clause enum from llvm/Frontend
Summary:
This patch is removing the custom enumeration for OpenMP Directives and Clauses and replace them
with the newly tablegen generated one from llvm/Frontend. This is a first patch and some will follow to share the same
infrastructure where possible. The next patch should use the clauses allowance defined in the tablegen file.
Reviewers: jdoerfert, DavidTruby, sscalpone, kiranchandramohan, ichoyjx
Reviewed By: DavidTruby, ichoyjx
Subscribers: jholewinski, cfe-commits, dblaikie, MaskRay, ymandel, ichoyjx, mgorny, yaxunl, guansong, jfb, sstefan1, aaron.ballman, llvm-commits
Tags: #llvm, #flang, #clang
Differential Revision: https://reviews.llvm.org/D82906
2020-07-02 08:57:11 +08:00
|
|
|
case llvm::omp::Directive::OMPD_parallel_workshare:
|
2019-07-13 05:23:16 +08:00
|
|
|
Word("PARALLEL WORKSHARE ");
|
|
|
|
break;
|
[flang][openmp] Use common Directive and Clause enum from llvm/Frontend
Summary:
This patch is removing the custom enumeration for OpenMP Directives and Clauses and replace them
with the newly tablegen generated one from llvm/Frontend. This is a first patch and some will follow to share the same
infrastructure where possible. The next patch should use the clauses allowance defined in the tablegen file.
Reviewers: jdoerfert, DavidTruby, sscalpone, kiranchandramohan, ichoyjx
Reviewed By: DavidTruby, ichoyjx
Subscribers: jholewinski, cfe-commits, dblaikie, MaskRay, ymandel, ichoyjx, mgorny, yaxunl, guansong, jfb, sstefan1, aaron.ballman, llvm-commits
Tags: #llvm, #flang, #clang
Differential Revision: https://reviews.llvm.org/D82906
2020-07-02 08:57:11 +08:00
|
|
|
case llvm::omp::Directive::OMPD_parallel:
|
2020-03-29 12:00:16 +08:00
|
|
|
Word("PARALLEL ");
|
|
|
|
break;
|
[flang][openmp] Use common Directive and Clause enum from llvm/Frontend
Summary:
This patch is removing the custom enumeration for OpenMP Directives and Clauses and replace them
with the newly tablegen generated one from llvm/Frontend. This is a first patch and some will follow to share the same
infrastructure where possible. The next patch should use the clauses allowance defined in the tablegen file.
Reviewers: jdoerfert, DavidTruby, sscalpone, kiranchandramohan, ichoyjx
Reviewed By: DavidTruby, ichoyjx
Subscribers: jholewinski, cfe-commits, dblaikie, MaskRay, ymandel, ichoyjx, mgorny, yaxunl, guansong, jfb, sstefan1, aaron.ballman, llvm-commits
Tags: #llvm, #flang, #clang
Differential Revision: https://reviews.llvm.org/D82906
2020-07-02 08:57:11 +08:00
|
|
|
case llvm::omp::Directive::OMPD_single:
|
2020-03-29 12:00:16 +08:00
|
|
|
Word("SINGLE ");
|
|
|
|
break;
|
[flang][openmp] Use common Directive and Clause enum from llvm/Frontend
Summary:
This patch is removing the custom enumeration for OpenMP Directives and Clauses and replace them
with the newly tablegen generated one from llvm/Frontend. This is a first patch and some will follow to share the same
infrastructure where possible. The next patch should use the clauses allowance defined in the tablegen file.
Reviewers: jdoerfert, DavidTruby, sscalpone, kiranchandramohan, ichoyjx
Reviewed By: DavidTruby, ichoyjx
Subscribers: jholewinski, cfe-commits, dblaikie, MaskRay, ymandel, ichoyjx, mgorny, yaxunl, guansong, jfb, sstefan1, aaron.ballman, llvm-commits
Tags: #llvm, #flang, #clang
Differential Revision: https://reviews.llvm.org/D82906
2020-07-02 08:57:11 +08:00
|
|
|
case llvm::omp::Directive::OMPD_target_data:
|
2020-03-29 12:00:16 +08:00
|
|
|
Word("TARGET DATA ");
|
|
|
|
break;
|
[flang][openmp] Use common Directive and Clause enum from llvm/Frontend
Summary:
This patch is removing the custom enumeration for OpenMP Directives and Clauses and replace them
with the newly tablegen generated one from llvm/Frontend. This is a first patch and some will follow to share the same
infrastructure where possible. The next patch should use the clauses allowance defined in the tablegen file.
Reviewers: jdoerfert, DavidTruby, sscalpone, kiranchandramohan, ichoyjx
Reviewed By: DavidTruby, ichoyjx
Subscribers: jholewinski, cfe-commits, dblaikie, MaskRay, ymandel, ichoyjx, mgorny, yaxunl, guansong, jfb, sstefan1, aaron.ballman, llvm-commits
Tags: #llvm, #flang, #clang
Differential Revision: https://reviews.llvm.org/D82906
2020-07-02 08:57:11 +08:00
|
|
|
case llvm::omp::Directive::OMPD_target_parallel:
|
2019-07-13 05:23:16 +08:00
|
|
|
Word("TARGET PARALLEL ");
|
|
|
|
break;
|
[flang][openmp] Use common Directive and Clause enum from llvm/Frontend
Summary:
This patch is removing the custom enumeration for OpenMP Directives and Clauses and replace them
with the newly tablegen generated one from llvm/Frontend. This is a first patch and some will follow to share the same
infrastructure where possible. The next patch should use the clauses allowance defined in the tablegen file.
Reviewers: jdoerfert, DavidTruby, sscalpone, kiranchandramohan, ichoyjx
Reviewed By: DavidTruby, ichoyjx
Subscribers: jholewinski, cfe-commits, dblaikie, MaskRay, ymandel, ichoyjx, mgorny, yaxunl, guansong, jfb, sstefan1, aaron.ballman, llvm-commits
Tags: #llvm, #flang, #clang
Differential Revision: https://reviews.llvm.org/D82906
2020-07-02 08:57:11 +08:00
|
|
|
case llvm::omp::Directive::OMPD_target_teams:
|
2019-07-13 05:23:16 +08:00
|
|
|
Word("TARGET TEAMS ");
|
|
|
|
break;
|
[flang][openmp] Use common Directive and Clause enum from llvm/Frontend
Summary:
This patch is removing the custom enumeration for OpenMP Directives and Clauses and replace them
with the newly tablegen generated one from llvm/Frontend. This is a first patch and some will follow to share the same
infrastructure where possible. The next patch should use the clauses allowance defined in the tablegen file.
Reviewers: jdoerfert, DavidTruby, sscalpone, kiranchandramohan, ichoyjx
Reviewed By: DavidTruby, ichoyjx
Subscribers: jholewinski, cfe-commits, dblaikie, MaskRay, ymandel, ichoyjx, mgorny, yaxunl, guansong, jfb, sstefan1, aaron.ballman, llvm-commits
Tags: #llvm, #flang, #clang
Differential Revision: https://reviews.llvm.org/D82906
2020-07-02 08:57:11 +08:00
|
|
|
case llvm::omp::Directive::OMPD_target:
|
2020-03-29 12:00:16 +08:00
|
|
|
Word("TARGET ");
|
|
|
|
break;
|
[flang][openmp] Use common Directive and Clause enum from llvm/Frontend
Summary:
This patch is removing the custom enumeration for OpenMP Directives and Clauses and replace them
with the newly tablegen generated one from llvm/Frontend. This is a first patch and some will follow to share the same
infrastructure where possible. The next patch should use the clauses allowance defined in the tablegen file.
Reviewers: jdoerfert, DavidTruby, sscalpone, kiranchandramohan, ichoyjx
Reviewed By: DavidTruby, ichoyjx
Subscribers: jholewinski, cfe-commits, dblaikie, MaskRay, ymandel, ichoyjx, mgorny, yaxunl, guansong, jfb, sstefan1, aaron.ballman, llvm-commits
Tags: #llvm, #flang, #clang
Differential Revision: https://reviews.llvm.org/D82906
2020-07-02 08:57:11 +08:00
|
|
|
case llvm::omp::Directive::OMPD_taskgroup:
|
2020-03-29 12:00:16 +08:00
|
|
|
Word("TASKGROUP ");
|
|
|
|
break;
|
[flang][openmp] Use common Directive and Clause enum from llvm/Frontend
Summary:
This patch is removing the custom enumeration for OpenMP Directives and Clauses and replace them
with the newly tablegen generated one from llvm/Frontend. This is a first patch and some will follow to share the same
infrastructure where possible. The next patch should use the clauses allowance defined in the tablegen file.
Reviewers: jdoerfert, DavidTruby, sscalpone, kiranchandramohan, ichoyjx
Reviewed By: DavidTruby, ichoyjx
Subscribers: jholewinski, cfe-commits, dblaikie, MaskRay, ymandel, ichoyjx, mgorny, yaxunl, guansong, jfb, sstefan1, aaron.ballman, llvm-commits
Tags: #llvm, #flang, #clang
Differential Revision: https://reviews.llvm.org/D82906
2020-07-02 08:57:11 +08:00
|
|
|
case llvm::omp::Directive::OMPD_task:
|
2020-03-29 12:00:16 +08:00
|
|
|
Word("TASK ");
|
|
|
|
break;
|
[flang][openmp] Use common Directive and Clause enum from llvm/Frontend
Summary:
This patch is removing the custom enumeration for OpenMP Directives and Clauses and replace them
with the newly tablegen generated one from llvm/Frontend. This is a first patch and some will follow to share the same
infrastructure where possible. The next patch should use the clauses allowance defined in the tablegen file.
Reviewers: jdoerfert, DavidTruby, sscalpone, kiranchandramohan, ichoyjx
Reviewed By: DavidTruby, ichoyjx
Subscribers: jholewinski, cfe-commits, dblaikie, MaskRay, ymandel, ichoyjx, mgorny, yaxunl, guansong, jfb, sstefan1, aaron.ballman, llvm-commits
Tags: #llvm, #flang, #clang
Differential Revision: https://reviews.llvm.org/D82906
2020-07-02 08:57:11 +08:00
|
|
|
case llvm::omp::Directive::OMPD_teams:
|
2020-03-29 12:00:16 +08:00
|
|
|
Word("TEAMS ");
|
|
|
|
break;
|
[flang][openmp] Use common Directive and Clause enum from llvm/Frontend
Summary:
This patch is removing the custom enumeration for OpenMP Directives and Clauses and replace them
with the newly tablegen generated one from llvm/Frontend. This is a first patch and some will follow to share the same
infrastructure where possible. The next patch should use the clauses allowance defined in the tablegen file.
Reviewers: jdoerfert, DavidTruby, sscalpone, kiranchandramohan, ichoyjx
Reviewed By: DavidTruby, ichoyjx
Subscribers: jholewinski, cfe-commits, dblaikie, MaskRay, ymandel, ichoyjx, mgorny, yaxunl, guansong, jfb, sstefan1, aaron.ballman, llvm-commits
Tags: #llvm, #flang, #clang
Differential Revision: https://reviews.llvm.org/D82906
2020-07-02 08:57:11 +08:00
|
|
|
case llvm::omp::Directive::OMPD_workshare:
|
2020-03-29 12:00:16 +08:00
|
|
|
Word("WORKSHARE ");
|
|
|
|
break;
|
[flang][openmp] Use common Directive and Clause enum from llvm/Frontend
Summary:
This patch is removing the custom enumeration for OpenMP Directives and Clauses and replace them
with the newly tablegen generated one from llvm/Frontend. This is a first patch and some will follow to share the same
infrastructure where possible. The next patch should use the clauses allowance defined in the tablegen file.
Reviewers: jdoerfert, DavidTruby, sscalpone, kiranchandramohan, ichoyjx
Reviewed By: DavidTruby, ichoyjx
Subscribers: jholewinski, cfe-commits, dblaikie, MaskRay, ymandel, ichoyjx, mgorny, yaxunl, guansong, jfb, sstefan1, aaron.ballman, llvm-commits
Tags: #llvm, #flang, #clang
Differential Revision: https://reviews.llvm.org/D82906
2020-07-02 08:57:11 +08:00
|
|
|
default:
|
|
|
|
// Nothing to be done
|
|
|
|
break;
|
2019-07-13 05:23:16 +08:00
|
|
|
}
|
2018-07-21 06:49:19 +08:00
|
|
|
}
|
2020-12-14 15:11:39 +08:00
|
|
|
void Unparse(const OmpAtomicClauseList &x) { Walk(" ", x.v, " "); }
|
|
|
|
|
2018-07-21 06:49:19 +08:00
|
|
|
void Unparse(const OmpAtomic &x) {
|
|
|
|
BeginOpenMP();
|
|
|
|
Word("!$OMP ATOMIC");
|
2020-12-14 15:11:39 +08:00
|
|
|
Walk(std::get<OmpAtomicClauseList>(x.t));
|
2018-06-02 01:40:13 +08:00
|
|
|
Put("\n");
|
2018-07-21 06:49:19 +08:00
|
|
|
EndOpenMP();
|
|
|
|
Walk(std::get<Statement<AssignmentStmt>>(x.t));
|
|
|
|
BeginOpenMP();
|
|
|
|
Walk(std::get<std::optional<OmpEndAtomic>>(x.t), "!$OMP END ATOMIC\n");
|
|
|
|
EndOpenMP();
|
|
|
|
}
|
|
|
|
void Unparse(const OmpAtomicCapture &x) {
|
|
|
|
BeginOpenMP();
|
|
|
|
Word("!$OMP ATOMIC");
|
2020-10-07 02:18:08 +08:00
|
|
|
Walk(std::get<0>(x.t));
|
2018-07-21 06:49:19 +08:00
|
|
|
Word(" CAPTURE");
|
2020-10-07 02:18:08 +08:00
|
|
|
Walk(std::get<2>(x.t));
|
2018-07-21 06:49:19 +08:00
|
|
|
Put("\n");
|
|
|
|
EndOpenMP();
|
|
|
|
Walk(std::get<OmpAtomicCapture::Stmt1>(x.t));
|
|
|
|
Put("\n");
|
|
|
|
Walk(std::get<OmpAtomicCapture::Stmt2>(x.t));
|
|
|
|
BeginOpenMP();
|
|
|
|
Word("!$OMP END ATOMIC\n");
|
|
|
|
EndOpenMP();
|
|
|
|
}
|
|
|
|
void Unparse(const OmpAtomicRead &x) {
|
|
|
|
BeginOpenMP();
|
|
|
|
Word("!$OMP ATOMIC");
|
2020-10-07 02:18:08 +08:00
|
|
|
Walk(std::get<0>(x.t));
|
2018-07-21 06:49:19 +08:00
|
|
|
Word(" READ");
|
2020-10-07 02:18:08 +08:00
|
|
|
Walk(std::get<2>(x.t));
|
2018-07-21 06:49:19 +08:00
|
|
|
Put("\n");
|
|
|
|
EndOpenMP();
|
|
|
|
Walk(std::get<Statement<AssignmentStmt>>(x.t));
|
|
|
|
BeginOpenMP();
|
|
|
|
Walk(std::get<std::optional<OmpEndAtomic>>(x.t), "!$OMP END ATOMIC\n");
|
|
|
|
EndOpenMP();
|
|
|
|
}
|
|
|
|
void Unparse(const OmpAtomicUpdate &x) {
|
|
|
|
BeginOpenMP();
|
|
|
|
Word("!$OMP ATOMIC");
|
2020-10-07 02:18:08 +08:00
|
|
|
Walk(std::get<0>(x.t));
|
2018-07-21 06:49:19 +08:00
|
|
|
Word(" UPDATE");
|
2020-10-07 02:18:08 +08:00
|
|
|
Walk(std::get<2>(x.t));
|
2018-07-21 06:49:19 +08:00
|
|
|
Put("\n");
|
|
|
|
EndOpenMP();
|
|
|
|
Walk(std::get<Statement<AssignmentStmt>>(x.t));
|
|
|
|
BeginOpenMP();
|
|
|
|
Walk(std::get<std::optional<OmpEndAtomic>>(x.t), "!$OMP END ATOMIC\n");
|
|
|
|
EndOpenMP();
|
|
|
|
}
|
|
|
|
void Unparse(const OmpAtomicWrite &x) {
|
|
|
|
BeginOpenMP();
|
|
|
|
Word("!$OMP ATOMIC");
|
2020-10-07 02:18:08 +08:00
|
|
|
Walk(std::get<0>(x.t));
|
2018-07-21 06:49:19 +08:00
|
|
|
Word(" WRITE");
|
2020-10-07 02:18:08 +08:00
|
|
|
Walk(std::get<2>(x.t));
|
2018-07-21 06:49:19 +08:00
|
|
|
Put("\n");
|
|
|
|
EndOpenMP();
|
|
|
|
Walk(std::get<Statement<AssignmentStmt>>(x.t));
|
|
|
|
BeginOpenMP();
|
|
|
|
Walk(std::get<std::optional<OmpEndAtomic>>(x.t), "!$OMP END ATOMIC\n");
|
|
|
|
EndOpenMP();
|
|
|
|
}
|
2020-10-17 00:36:12 +08:00
|
|
|
void Unparse(const OpenMPExecutableAllocate &x) {
|
|
|
|
BeginOpenMP();
|
|
|
|
Word("!$OMP ALLOCATE");
|
|
|
|
Walk(" (", std::get<std::optional<OmpObjectList>>(x.t), ")");
|
|
|
|
Walk(std::get<OmpClauseList>(x.t));
|
|
|
|
Put("\n");
|
|
|
|
EndOpenMP();
|
|
|
|
Walk(std::get<Statement<AllocateStmt>>(x.t));
|
|
|
|
}
|
|
|
|
void Unparse(const OpenMPDeclarativeAllocate &x) {
|
|
|
|
BeginOpenMP();
|
|
|
|
Word("!$OMP ALLOCATE");
|
|
|
|
Put(" (");
|
|
|
|
Walk(std::get<OmpObjectList>(x.t));
|
|
|
|
Put(")");
|
|
|
|
Walk(std::get<OmpClauseList>(x.t));
|
|
|
|
Put("\n");
|
|
|
|
EndOpenMP();
|
|
|
|
}
|
2019-08-13 07:08:10 +08:00
|
|
|
void Unparse(const OmpCriticalDirective &x) {
|
2018-07-21 06:49:19 +08:00
|
|
|
BeginOpenMP();
|
|
|
|
Word("!$OMP CRITICAL");
|
|
|
|
Walk(" (", std::get<std::optional<Name>>(x.t), ")");
|
2020-10-07 02:18:08 +08:00
|
|
|
Walk(std::get<std::optional<OmpClause>>(x.t));
|
2018-07-21 06:49:19 +08:00
|
|
|
Put("\n");
|
|
|
|
EndOpenMP();
|
2019-07-13 03:46:39 +08:00
|
|
|
}
|
2019-08-13 07:08:10 +08:00
|
|
|
void Unparse(const OmpEndCriticalDirective &x) {
|
2018-07-21 06:49:19 +08:00
|
|
|
BeginOpenMP();
|
|
|
|
Word("!$OMP END CRITICAL");
|
2019-08-13 07:08:10 +08:00
|
|
|
Walk(" (", std::get<std::optional<Name>>(x.t), ")");
|
2018-07-21 06:49:19 +08:00
|
|
|
Put("\n");
|
|
|
|
EndOpenMP();
|
2018-06-02 01:40:13 +08:00
|
|
|
}
|
2019-08-13 07:08:10 +08:00
|
|
|
void Unparse(const OpenMPCriticalConstruct &x) {
|
|
|
|
Walk(std::get<OmpCriticalDirective>(x.t));
|
|
|
|
Walk(std::get<Block>(x.t), "");
|
|
|
|
Walk(std::get<OmpEndCriticalDirective>(x.t));
|
|
|
|
}
|
2019-08-21 01:23:56 +08:00
|
|
|
void Unparse(const OmpDeclareTargetWithList &x) {
|
|
|
|
Put("("), Walk(x.v), Put(")");
|
2018-07-21 06:49:19 +08:00
|
|
|
}
|
|
|
|
void Unparse(const OmpReductionInitializerClause &x) {
|
|
|
|
Word(" INITIALIZER(OMP_PRIV = ");
|
|
|
|
Walk(x.v);
|
|
|
|
Put(")");
|
|
|
|
}
|
|
|
|
void Unparse(const OmpReductionCombiner::FunctionCombiner &x) {
|
|
|
|
const auto &pd = std::get<ProcedureDesignator>(x.v.t);
|
|
|
|
const auto &args = std::get<std::list<ActualArgSpec>>(x.v.t);
|
|
|
|
Walk(pd);
|
|
|
|
if (args.empty()) {
|
|
|
|
if (std::holds_alternative<ProcComponentRef>(pd.u)) {
|
|
|
|
Put("()");
|
|
|
|
}
|
|
|
|
} else {
|
|
|
|
Walk("(", args, ", ", ")");
|
|
|
|
}
|
|
|
|
}
|
|
|
|
void Unparse(const OpenMPDeclareReductionConstruct &x) {
|
|
|
|
Put("(");
|
|
|
|
Walk(std::get<OmpReductionOperator>(x.t)), Put(" : ");
|
|
|
|
Walk(std::get<std::list<DeclarationTypeSpec>>(x.t), ","), Put(" : ");
|
|
|
|
Walk(std::get<OmpReductionCombiner>(x.t));
|
|
|
|
Put(")");
|
|
|
|
Walk(std::get<std::optional<OmpReductionInitializerClause>>(x.t));
|
|
|
|
}
|
|
|
|
bool Pre(const OpenMPDeclarativeConstruct &x) {
|
|
|
|
BeginOpenMP();
|
|
|
|
Word("!$OMP ");
|
2020-03-29 12:00:16 +08:00
|
|
|
return std::visit(common::visitors{
|
2020-10-17 00:36:12 +08:00
|
|
|
[&](const OpenMPDeclarativeAllocate &z) {
|
|
|
|
Word("ALLOCATE (");
|
|
|
|
Walk(std::get<OmpObjectList>(z.t));
|
|
|
|
Put(")");
|
|
|
|
Walk(std::get<OmpClauseList>(z.t));
|
|
|
|
Put("\n");
|
|
|
|
EndOpenMP();
|
|
|
|
return false;
|
|
|
|
},
|
2020-03-29 12:00:16 +08:00
|
|
|
[&](const OpenMPDeclareReductionConstruct &) {
|
|
|
|
Word("DECLARE REDUCTION ");
|
|
|
|
return true;
|
|
|
|
},
|
|
|
|
[&](const OpenMPDeclareSimdConstruct &y) {
|
|
|
|
Word("DECLARE SIMD ");
|
|
|
|
Walk("(", std::get<std::optional<Name>>(y.t), ")");
|
|
|
|
Walk(std::get<OmpClauseList>(y.t));
|
|
|
|
Put("\n");
|
|
|
|
EndOpenMP();
|
|
|
|
return false;
|
|
|
|
},
|
|
|
|
[&](const OpenMPDeclareTargetConstruct &) {
|
|
|
|
Word("DECLARE TARGET ");
|
|
|
|
return true;
|
|
|
|
},
|
|
|
|
[&](const OpenMPThreadprivate &) {
|
|
|
|
Word("THREADPRIVATE (");
|
|
|
|
return true;
|
|
|
|
},
|
|
|
|
},
|
2018-06-02 01:40:13 +08:00
|
|
|
x.u);
|
|
|
|
}
|
2019-08-16 04:50:27 +08:00
|
|
|
void Post(const OpenMPDeclarativeConstruct &) {
|
2018-07-21 06:49:19 +08:00
|
|
|
Put("\n");
|
|
|
|
EndOpenMP();
|
|
|
|
}
|
2019-08-16 04:50:27 +08:00
|
|
|
void Post(const OpenMPThreadprivate &) {
|
2018-07-21 06:49:19 +08:00
|
|
|
Put(")\n");
|
|
|
|
EndOpenMP();
|
|
|
|
}
|
2019-08-14 23:42:28 +08:00
|
|
|
void Unparse(const OmpSectionsDirective &x) {
|
|
|
|
switch (x.v) {
|
[flang][openmp] Use common Directive and Clause enum from llvm/Frontend
Summary:
This patch is removing the custom enumeration for OpenMP Directives and Clauses and replace them
with the newly tablegen generated one from llvm/Frontend. This is a first patch and some will follow to share the same
infrastructure where possible. The next patch should use the clauses allowance defined in the tablegen file.
Reviewers: jdoerfert, DavidTruby, sscalpone, kiranchandramohan, ichoyjx
Reviewed By: DavidTruby, ichoyjx
Subscribers: jholewinski, cfe-commits, dblaikie, MaskRay, ymandel, ichoyjx, mgorny, yaxunl, guansong, jfb, sstefan1, aaron.ballman, llvm-commits
Tags: #llvm, #flang, #clang
Differential Revision: https://reviews.llvm.org/D82906
2020-07-02 08:57:11 +08:00
|
|
|
case llvm::omp::Directive::OMPD_sections:
|
2020-03-29 12:00:16 +08:00
|
|
|
Word("SECTIONS ");
|
|
|
|
break;
|
[flang][openmp] Use common Directive and Clause enum from llvm/Frontend
Summary:
This patch is removing the custom enumeration for OpenMP Directives and Clauses and replace them
with the newly tablegen generated one from llvm/Frontend. This is a first patch and some will follow to share the same
infrastructure where possible. The next patch should use the clauses allowance defined in the tablegen file.
Reviewers: jdoerfert, DavidTruby, sscalpone, kiranchandramohan, ichoyjx
Reviewed By: DavidTruby, ichoyjx
Subscribers: jholewinski, cfe-commits, dblaikie, MaskRay, ymandel, ichoyjx, mgorny, yaxunl, guansong, jfb, sstefan1, aaron.ballman, llvm-commits
Tags: #llvm, #flang, #clang
Differential Revision: https://reviews.llvm.org/D82906
2020-07-02 08:57:11 +08:00
|
|
|
case llvm::omp::Directive::OMPD_parallel_sections:
|
2019-08-14 23:42:28 +08:00
|
|
|
Word("PARALLEL SECTIONS ");
|
|
|
|
break;
|
[flang][openmp] Use common Directive and Clause enum from llvm/Frontend
Summary:
This patch is removing the custom enumeration for OpenMP Directives and Clauses and replace them
with the newly tablegen generated one from llvm/Frontend. This is a first patch and some will follow to share the same
infrastructure where possible. The next patch should use the clauses allowance defined in the tablegen file.
Reviewers: jdoerfert, DavidTruby, sscalpone, kiranchandramohan, ichoyjx
Reviewed By: DavidTruby, ichoyjx
Subscribers: jholewinski, cfe-commits, dblaikie, MaskRay, ymandel, ichoyjx, mgorny, yaxunl, guansong, jfb, sstefan1, aaron.ballman, llvm-commits
Tags: #llvm, #flang, #clang
Differential Revision: https://reviews.llvm.org/D82906
2020-07-02 08:57:11 +08:00
|
|
|
default:
|
|
|
|
break;
|
2019-08-14 23:42:28 +08:00
|
|
|
}
|
2018-07-21 06:49:19 +08:00
|
|
|
}
|
2019-08-14 23:42:28 +08:00
|
|
|
void Unparse(const OmpSectionBlocks &x) {
|
|
|
|
for (const auto &y : x.v) {
|
|
|
|
BeginOpenMP();
|
|
|
|
Word("!$OMP SECTION");
|
|
|
|
Put("\n");
|
|
|
|
EndOpenMP();
|
2020-03-29 12:00:16 +08:00
|
|
|
Walk(y, ""); // y is Block
|
2019-08-14 23:42:28 +08:00
|
|
|
}
|
2018-07-21 06:49:19 +08:00
|
|
|
}
|
2019-08-14 23:42:28 +08:00
|
|
|
void Unparse(const OpenMPSectionsConstruct &x) {
|
2018-07-21 06:49:19 +08:00
|
|
|
BeginOpenMP();
|
2019-08-14 23:42:28 +08:00
|
|
|
Word("!$OMP ");
|
|
|
|
Walk(std::get<OmpBeginSectionsDirective>(x.t));
|
2018-07-21 06:49:19 +08:00
|
|
|
Put("\n");
|
|
|
|
EndOpenMP();
|
2019-08-14 23:42:28 +08:00
|
|
|
Walk(std::get<OmpSectionBlocks>(x.t));
|
2018-07-21 06:49:19 +08:00
|
|
|
BeginOpenMP();
|
2019-08-14 23:42:28 +08:00
|
|
|
Word("!$OMP END ");
|
|
|
|
Walk(std::get<OmpEndSectionsDirective>(x.t));
|
2018-07-21 06:49:19 +08:00
|
|
|
Put("\n");
|
|
|
|
EndOpenMP();
|
|
|
|
}
|
|
|
|
void Unparse(const OpenMPCancellationPointConstruct &x) {
|
|
|
|
BeginOpenMP();
|
|
|
|
Word("!$OMP CANCELLATION POINT ");
|
2019-08-07 02:59:40 +08:00
|
|
|
Walk(std::get<OmpCancelType>(x.t));
|
2018-07-21 06:49:19 +08:00
|
|
|
Put("\n");
|
|
|
|
EndOpenMP();
|
|
|
|
}
|
|
|
|
void Unparse(const OpenMPCancelConstruct &x) {
|
|
|
|
BeginOpenMP();
|
|
|
|
Word("!$OMP CANCEL ");
|
|
|
|
Walk(std::get<OmpCancelType>(x.t));
|
|
|
|
Walk(std::get<std::optional<OpenMPCancelConstruct::If>>(x.t));
|
|
|
|
Put("\n");
|
|
|
|
EndOpenMP();
|
|
|
|
}
|
2020-11-22 03:31:17 +08:00
|
|
|
void Unparse(const OmpMemoryOrderClause &x) { Walk(x.v); }
|
2020-12-14 15:11:39 +08:00
|
|
|
void Unparse(const OmpAtomicClause &x) {
|
|
|
|
std::visit(common::visitors{
|
|
|
|
[&](const OmpMemoryOrderClause &y) { Walk(y); },
|
|
|
|
[&](const OmpClause &z) { Walk(z); },
|
|
|
|
},
|
|
|
|
x.u);
|
|
|
|
}
|
2018-07-21 06:49:19 +08:00
|
|
|
void Unparse(const OpenMPFlushConstruct &x) {
|
|
|
|
BeginOpenMP();
|
2020-07-07 16:56:22 +08:00
|
|
|
Word("!$OMP FLUSH ");
|
2020-12-14 16:00:26 +08:00
|
|
|
Walk(std::get<std::optional<std::list<OmpMemoryOrderClause>>>(x.t));
|
2020-07-07 16:56:22 +08:00
|
|
|
Walk(" (", std::get<std::optional<OmpObjectList>>(x.t), ")");
|
2018-07-21 06:49:19 +08:00
|
|
|
Put("\n");
|
|
|
|
EndOpenMP();
|
|
|
|
}
|
[flang] [OpenMP] parse tree changes for `OpenMPLoopConstruct` (flang-compiler/f18#656)
1. Following Block and Sections constructs, re-structure loop related
constructs into `{Begin, Loop, End}`. Being part of the work in
PR flang-compiler/f18#599, the `Loop` and `End` nodes are optional during parser. They
should be filled in during the phase of `CanonicalizationOfOmp`. This
commit is solely for the parse tree change. So, after this commit,
PR flang-compiler/f18#599 needs to be changed accordingly.
2. Removed parse tree nodes for `END DO` and `END DO SIMD`. Similar to
Block and Sections constructs, `End` node now accepts clauses too,
the validity checks are deferred into Semantics. This is more genernal
and error message could be better.
3. With this commit alone, assertion error would occur when `End` directive
is present, for example `!$OMP END DO` because the `End` node is not
moved into `OpenMPLoopConstruct` yet. Again, PR flang-compiler/f18#599 will handle that.
More tests will be added in PR flang-compiler/f18#599 and during the future Semantics work.
Original-commit: flang-compiler/f18@8cd1932fd61fa67f8ad5abfd337cf7a223ea89f4
Reviewed-on: https://github.com/flang-compiler/f18/pull/656
2019-08-15 06:16:27 +08:00
|
|
|
void Unparse(const OmpEndLoopDirective &x) {
|
2018-07-21 06:49:19 +08:00
|
|
|
BeginOpenMP();
|
|
|
|
Word("!$OMP END ");
|
[flang] [OpenMP] parse tree changes for `OpenMPLoopConstruct` (flang-compiler/f18#656)
1. Following Block and Sections constructs, re-structure loop related
constructs into `{Begin, Loop, End}`. Being part of the work in
PR flang-compiler/f18#599, the `Loop` and `End` nodes are optional during parser. They
should be filled in during the phase of `CanonicalizationOfOmp`. This
commit is solely for the parse tree change. So, after this commit,
PR flang-compiler/f18#599 needs to be changed accordingly.
2. Removed parse tree nodes for `END DO` and `END DO SIMD`. Similar to
Block and Sections constructs, `End` node now accepts clauses too,
the validity checks are deferred into Semantics. This is more genernal
and error message could be better.
3. With this commit alone, assertion error would occur when `End` directive
is present, for example `!$OMP END DO` because the `End` node is not
moved into `OpenMPLoopConstruct` yet. Again, PR flang-compiler/f18#599 will handle that.
More tests will be added in PR flang-compiler/f18#599 and during the future Semantics work.
Original-commit: flang-compiler/f18@8cd1932fd61fa67f8ad5abfd337cf7a223ea89f4
Reviewed-on: https://github.com/flang-compiler/f18/pull/656
2019-08-15 06:16:27 +08:00
|
|
|
Walk(std::get<OmpLoopDirective>(x.t));
|
|
|
|
Walk(std::get<OmpClauseList>(x.t));
|
2018-07-21 06:49:19 +08:00
|
|
|
Put("\n");
|
|
|
|
EndOpenMP();
|
|
|
|
}
|
|
|
|
void Unparse(const OmpClauseList &x) { Walk(" ", x.v, " "); }
|
2019-08-07 02:59:40 +08:00
|
|
|
void Unparse(const OpenMPSimpleStandaloneConstruct &x) {
|
2018-07-21 06:49:19 +08:00
|
|
|
BeginOpenMP();
|
2018-06-02 01:40:13 +08:00
|
|
|
Word("!$OMP ");
|
2019-08-07 02:59:40 +08:00
|
|
|
Walk(std::get<OmpSimpleStandaloneDirective>(x.t));
|
2018-07-21 06:49:19 +08:00
|
|
|
Walk(std::get<OmpClauseList>(x.t));
|
|
|
|
Put("\n");
|
|
|
|
EndOpenMP();
|
2018-06-02 01:40:13 +08:00
|
|
|
}
|
2018-07-21 06:49:19 +08:00
|
|
|
void Unparse(const OpenMPBlockConstruct &x) {
|
|
|
|
BeginOpenMP();
|
2018-06-02 01:40:13 +08:00
|
|
|
Word("!$OMP ");
|
[flang] [OpenMP] parse tree changes for `OpenMPBlockConstruct` (flang-compiler/f18#632)
* [OpenMP] parse tree changes for `OpenMPBlockConstruct`
1. merge `Workshare` and `Single` into `OpenMPBlockConstruct` because
they both accept structured-block and syntax is similar to other block
directives.
2. `OpenMPBlockConstruct` changes to structure like `{Begin, Block, End}`,
where `Begin` and `End` are tuple of `{Directive, ClauseList}`.
3. Updated the check-omp-structure.* for necessary parts. Added all the END
directive enumeration types that may have clauses.
More tests will be added during Semantics.
* [OpenMP] Update on Tim's suggestion
1. Fix unspecified enumeration for `OmpDirective` in the `OmpContext`.
This is through getting rid of `PushContext(source)` function to
make sure whenever it is about to push a NEW context, directive
source location and enumeration are available. To do that, I moved
around all the switches for directive into high level `Construct`'s
`Enter` node. Besides fixing the issue, the side benefit is that
whenever we call `GetContext().directive`, we are sure that the
`directive` here was set already.
2. When `Enter` the `OmpEndBlockDirective` node, partial context
information, such as directive source location or legal clause lists,
needs to be reset. The new directive source location should be
`OmpEndBlockDirective`'s `source`. The enumeration `directive`
should not be reset for the END directives that do not accept
clauses because nothing needs to be checked (for example any clause
that is on `END PARALLEL` is illegal).
Original-commit: flang-compiler/f18@e5bd6b7ba0fbe9006f3e431260428b194f2d2616
Reviewed-on: https://github.com/flang-compiler/f18/pull/632
2019-08-10 06:11:20 +08:00
|
|
|
Walk(std::get<OmpBeginBlockDirective>(x.t));
|
2018-07-21 06:49:19 +08:00
|
|
|
Put("\n");
|
|
|
|
EndOpenMP();
|
|
|
|
Walk(std::get<Block>(x.t), "");
|
|
|
|
BeginOpenMP();
|
|
|
|
Word("!$OMP END ");
|
|
|
|
Walk(std::get<OmpEndBlockDirective>(x.t));
|
|
|
|
Put("\n");
|
|
|
|
EndOpenMP();
|
|
|
|
}
|
|
|
|
void Unparse(const OpenMPLoopConstruct &x) {
|
|
|
|
BeginOpenMP();
|
|
|
|
Word("!$OMP ");
|
[flang] [OpenMP] parse tree changes for `OpenMPLoopConstruct` (flang-compiler/f18#656)
1. Following Block and Sections constructs, re-structure loop related
constructs into `{Begin, Loop, End}`. Being part of the work in
PR flang-compiler/f18#599, the `Loop` and `End` nodes are optional during parser. They
should be filled in during the phase of `CanonicalizationOfOmp`. This
commit is solely for the parse tree change. So, after this commit,
PR flang-compiler/f18#599 needs to be changed accordingly.
2. Removed parse tree nodes for `END DO` and `END DO SIMD`. Similar to
Block and Sections constructs, `End` node now accepts clauses too,
the validity checks are deferred into Semantics. This is more genernal
and error message could be better.
3. With this commit alone, assertion error would occur when `End` directive
is present, for example `!$OMP END DO` because the `End` node is not
moved into `OpenMPLoopConstruct` yet. Again, PR flang-compiler/f18#599 will handle that.
More tests will be added in PR flang-compiler/f18#599 and during the future Semantics work.
Original-commit: flang-compiler/f18@8cd1932fd61fa67f8ad5abfd337cf7a223ea89f4
Reviewed-on: https://github.com/flang-compiler/f18/pull/656
2019-08-15 06:16:27 +08:00
|
|
|
Walk(std::get<OmpBeginLoopDirective>(x.t));
|
2018-07-21 06:49:19 +08:00
|
|
|
Put("\n");
|
|
|
|
EndOpenMP();
|
2019-08-23 01:34:15 +08:00
|
|
|
Walk(std::get<std::optional<DoConstruct>>(x.t));
|
|
|
|
Walk(std::get<std::optional<OmpEndLoopDirective>>(x.t));
|
2018-06-02 01:40:13 +08:00
|
|
|
}
|
2019-03-22 07:29:50 +08:00
|
|
|
void Unparse(const BasedPointer &x) {
|
|
|
|
Put('('), Walk(std::get<0>(x.t)), Put(","), Walk(std::get<1>(x.t));
|
2018-03-01 08:56:10 +08:00
|
|
|
Walk("(", std::get<std::optional<ArraySpec>>(x.t), ")"), Put(')');
|
|
|
|
}
|
2019-03-22 07:29:50 +08:00
|
|
|
void Unparse(const BasedPointerStmt &x) { Walk("POINTER ", x.v, ","); }
|
2018-03-31 06:23:37 +08:00
|
|
|
void Post(const StructureField &x) {
|
2018-07-11 08:09:07 +08:00
|
|
|
if (const auto *def{std::get_if<Statement<DataComponentDefStmt>>(&x.u)}) {
|
2018-03-31 06:23:37 +08:00
|
|
|
for (const auto &decl :
|
|
|
|
std::get<std::list<ComponentDecl>>(def->statement.t)) {
|
|
|
|
structureComponents_.insert(std::get<Name>(decl.t).source);
|
|
|
|
}
|
|
|
|
}
|
|
|
|
}
|
2018-04-07 04:13:20 +08:00
|
|
|
void Unparse(const StructureStmt &x) {
|
2018-03-15 06:31:16 +08:00
|
|
|
Word("STRUCTURE ");
|
2020-03-29 12:00:16 +08:00
|
|
|
if (std::get<bool>(x.t)) { // slashes around name
|
2018-03-01 08:56:10 +08:00
|
|
|
Put('/'), Walk(std::get<Name>(x.t)), Put('/');
|
|
|
|
Walk(" ", std::get<std::list<EntityDecl>>(x.t), ", ");
|
|
|
|
} else {
|
|
|
|
CHECK(std::get<std::list<EntityDecl>>(x.t).empty());
|
|
|
|
Walk(std::get<Name>(x.t));
|
|
|
|
}
|
|
|
|
Indent();
|
|
|
|
}
|
2018-03-15 06:31:16 +08:00
|
|
|
void Post(const Union::UnionStmt &) { Word("UNION"), Indent(); }
|
|
|
|
void Post(const Union::EndUnionStmt &) { Outdent(), Word("END UNION"); }
|
|
|
|
void Post(const Map::MapStmt &) { Word("MAP"), Indent(); }
|
|
|
|
void Post(const Map::EndMapStmt &) { Outdent(), Word("END MAP"); }
|
2018-03-01 08:56:10 +08:00
|
|
|
void Post(const StructureDef::EndStructureStmt &) {
|
2018-03-15 06:31:16 +08:00
|
|
|
Outdent(), Word("END STRUCTURE");
|
2018-03-01 08:56:10 +08:00
|
|
|
}
|
2018-04-07 04:13:20 +08:00
|
|
|
void Unparse(const OldParameterStmt &x) {
|
2018-03-15 06:31:16 +08:00
|
|
|
Word("PARAMETER "), Walk(x.v, ", ");
|
2018-03-01 08:56:10 +08:00
|
|
|
}
|
2018-04-07 04:13:20 +08:00
|
|
|
void Unparse(const ArithmeticIfStmt &x) {
|
2018-03-15 06:31:16 +08:00
|
|
|
Word("IF ("), Walk(std::get<Expr>(x.t)), Put(") ");
|
2018-03-01 08:56:10 +08:00
|
|
|
Walk(std::get<1>(x.t)), Put(", ");
|
|
|
|
Walk(std::get<2>(x.t)), Put(", ");
|
|
|
|
Walk(std::get<3>(x.t));
|
|
|
|
}
|
2018-04-07 04:13:20 +08:00
|
|
|
void Unparse(const AssignStmt &x) {
|
2018-03-15 06:31:16 +08:00
|
|
|
Word("ASSIGN "), Walk(std::get<Label>(x.t));
|
|
|
|
Word(" TO "), Walk(std::get<Name>(x.t));
|
2018-03-01 08:56:10 +08:00
|
|
|
}
|
2018-04-07 04:13:20 +08:00
|
|
|
void Unparse(const AssignedGotoStmt &x) {
|
2018-03-15 06:31:16 +08:00
|
|
|
Word("GO TO "), Walk(std::get<Name>(x.t));
|
2018-03-01 08:56:10 +08:00
|
|
|
Walk(", (", std::get<std::list<Label>>(x.t), ", ", ")");
|
2018-02-27 06:28:32 +08:00
|
|
|
}
|
2018-04-07 04:13:20 +08:00
|
|
|
void Unparse(const PauseStmt &x) { Word("PAUSE"), Walk(" ", x.v); }
|
2018-02-27 06:28:32 +08:00
|
|
|
|
2018-03-24 05:31:14 +08:00
|
|
|
#define WALK_NESTED_ENUM(CLASS, ENUM) \
|
2018-04-07 04:13:20 +08:00
|
|
|
void Unparse(const CLASS::ENUM &x) { Word(CLASS::EnumToString(x)); }
|
2020-03-29 12:00:16 +08:00
|
|
|
WALK_NESTED_ENUM(AccessSpec, Kind) // R807
|
|
|
|
WALK_NESTED_ENUM(common, TypeParamAttr) // R734
|
|
|
|
WALK_NESTED_ENUM(IntentSpec, Intent) // R826
|
|
|
|
WALK_NESTED_ENUM(ImplicitStmt, ImplicitNoneNameSpec) // R866
|
|
|
|
WALK_NESTED_ENUM(ConnectSpec::CharExpr, Kind) // R1205
|
2018-03-24 05:31:14 +08:00
|
|
|
WALK_NESTED_ENUM(IoControlSpec::CharExpr, Kind)
|
|
|
|
WALK_NESTED_ENUM(InquireSpec::CharVar, Kind)
|
|
|
|
WALK_NESTED_ENUM(InquireSpec::IntVar, Kind)
|
|
|
|
WALK_NESTED_ENUM(InquireSpec::LogVar, Kind)
|
2020-03-29 12:00:16 +08:00
|
|
|
WALK_NESTED_ENUM(ProcedureStmt, Kind) // R1506
|
|
|
|
WALK_NESTED_ENUM(UseStmt, ModuleNature) // R1410
|
|
|
|
WALK_NESTED_ENUM(OmpProcBindClause, Type) // OMP PROC_BIND
|
|
|
|
WALK_NESTED_ENUM(OmpDefaultClause, Type) // OMP DEFAULT
|
|
|
|
WALK_NESTED_ENUM(OmpDefaultmapClause, ImplicitBehavior) // OMP DEFAULTMAP
|
|
|
|
WALK_NESTED_ENUM(OmpDefaultmapClause, VariableCategory) // OMP DEFAULTMAP
|
|
|
|
WALK_NESTED_ENUM(OmpScheduleModifierType, ModType) // OMP schedule-modifier
|
|
|
|
WALK_NESTED_ENUM(OmpLinearModifier, Type) // OMP linear-modifier
|
|
|
|
WALK_NESTED_ENUM(OmpDependenceType, Type) // OMP dependence-type
|
|
|
|
WALK_NESTED_ENUM(OmpMapType, Type) // OMP map-type
|
|
|
|
WALK_NESTED_ENUM(OmpScheduleClause, ScheduleType) // OMP schedule-type
|
|
|
|
WALK_NESTED_ENUM(OmpIfClause, DirectiveNameModifier) // OMP directive-modifier
|
|
|
|
WALK_NESTED_ENUM(OmpCancelType, Type) // OMP cancel-type
|
2018-03-01 08:56:10 +08:00
|
|
|
#undef WALK_NESTED_ENUM
|
|
|
|
|
|
|
|
void Done() const { CHECK(indent_ == 0); }
|
|
|
|
|
2018-02-27 06:28:32 +08:00
|
|
|
private:
|
2018-03-01 08:56:10 +08:00
|
|
|
void Put(char);
|
|
|
|
void Put(const char *);
|
|
|
|
void Put(const std::string &);
|
2019-06-19 04:46:54 +08:00
|
|
|
void PutNormalized(const std::string &);
|
2018-03-15 06:31:16 +08:00
|
|
|
void PutKeywordLetter(char);
|
|
|
|
void Word(const char *);
|
2018-03-24 05:31:14 +08:00
|
|
|
void Word(const std::string &);
|
2018-03-01 08:56:10 +08:00
|
|
|
void Indent() { indent_ += indentationAmount_; }
|
|
|
|
void Outdent() {
|
|
|
|
CHECK(indent_ >= indentationAmount_);
|
|
|
|
indent_ -= indentationAmount_;
|
|
|
|
}
|
2018-07-21 06:49:19 +08:00
|
|
|
void BeginOpenMP() { openmpDirective_ = true; }
|
|
|
|
void EndOpenMP() { openmpDirective_ = false; }
|
[flang][openacc] OpenACC 3.0 parser
Summary:
This patch introduce the parser for OpenACC 3.0 in Flang. It uses the same TableGen mechanism
than OpenMP.
Reviewers: nvdatian, sscalpone, tskeith, klausler, ichoyjx, jdoerfert, DavidTruby
Reviewed By: klausler
Subscribers: MaskRay, SouraVX, mgorny, hiraditya, jfb, sstefan1, llvm-commits
Tags: #llvm, #flang
Differential Revision: https://reviews.llvm.org/D83649
2020-07-15 02:28:34 +08:00
|
|
|
void BeginOpenACC() { openaccDirective_ = true; }
|
|
|
|
void EndOpenACC() { openaccDirective_ = false; }
|
2018-02-27 06:28:32 +08:00
|
|
|
|
2018-03-01 08:56:10 +08:00
|
|
|
// Call back to the traversal framework.
|
2020-03-29 12:00:16 +08:00
|
|
|
template <typename T> void Walk(const T &x) {
|
2018-03-01 08:56:10 +08:00
|
|
|
Fortran::parser::Walk(x, *this);
|
|
|
|
}
|
2018-02-27 06:28:32 +08:00
|
|
|
|
2018-03-01 08:56:10 +08:00
|
|
|
// Traverse a std::optional<> value. Emit a prefix and/or a suffix string
|
|
|
|
// only when it contains a value.
|
2020-03-29 12:00:16 +08:00
|
|
|
template <typename A>
|
2018-03-01 08:56:10 +08:00
|
|
|
void Walk(
|
|
|
|
const char *prefix, const std::optional<A> &x, const char *suffix = "") {
|
2019-11-10 01:29:31 +08:00
|
|
|
if (x) {
|
2018-03-15 06:31:16 +08:00
|
|
|
Word(prefix), Walk(*x), Word(suffix);
|
2018-02-27 06:28:32 +08:00
|
|
|
}
|
2018-03-01 08:56:10 +08:00
|
|
|
}
|
2020-03-29 12:00:16 +08:00
|
|
|
template <typename A>
|
2018-03-01 08:56:10 +08:00
|
|
|
void Walk(const std::optional<A> &x, const char *suffix = "") {
|
|
|
|
return Walk("", x, suffix);
|
|
|
|
}
|
|
|
|
|
|
|
|
// Traverse a std::list<>. Separate the elements with an optional string.
|
|
|
|
// Emit a prefix and/or a suffix string only when the list is not empty.
|
2020-03-29 12:00:16 +08:00
|
|
|
template <typename A>
|
2018-03-01 08:56:10 +08:00
|
|
|
void Walk(const char *prefix, const std::list<A> &list,
|
|
|
|
const char *comma = ", ", const char *suffix = "") {
|
|
|
|
if (!list.empty()) {
|
|
|
|
const char *str{prefix};
|
|
|
|
for (const auto &x : list) {
|
2018-03-15 06:31:16 +08:00
|
|
|
Word(str), Walk(x);
|
2018-03-01 08:56:10 +08:00
|
|
|
str = comma;
|
2018-02-27 06:28:32 +08:00
|
|
|
}
|
2018-03-15 06:31:16 +08:00
|
|
|
Word(suffix);
|
2018-02-27 06:28:32 +08:00
|
|
|
}
|
2018-03-01 08:56:10 +08:00
|
|
|
}
|
2020-03-29 12:00:16 +08:00
|
|
|
template <typename A>
|
2018-03-01 08:56:10 +08:00
|
|
|
void Walk(const std::list<A> &list, const char *comma = ", ",
|
|
|
|
const char *suffix = "") {
|
|
|
|
return Walk("", list, comma, suffix);
|
|
|
|
}
|
|
|
|
|
|
|
|
// Traverse a std::tuple<>, with an optional separator.
|
2020-03-29 12:00:16 +08:00
|
|
|
template <std::size_t J = 0, typename T>
|
2018-03-01 08:56:10 +08:00
|
|
|
void WalkTupleElements(const T &tuple, const char *separator) {
|
2019-08-16 01:17:31 +08:00
|
|
|
if (J > 0 && J < std::tuple_size_v<T>) {
|
2020-03-29 12:00:16 +08:00
|
|
|
Word(separator); // this usage dodges "unused parameter" warning
|
2019-08-16 01:17:31 +08:00
|
|
|
}
|
2018-03-01 08:56:10 +08:00
|
|
|
if constexpr (J < std::tuple_size_v<T>) {
|
|
|
|
Walk(std::get<J>(tuple));
|
|
|
|
WalkTupleElements<J + 1>(tuple, separator);
|
2018-02-27 06:28:32 +08:00
|
|
|
}
|
|
|
|
}
|
2020-03-29 12:00:16 +08:00
|
|
|
template <typename... A>
|
2018-03-01 08:56:10 +08:00
|
|
|
void Walk(const std::tuple<A...> &tuple, const char *separator = "") {
|
|
|
|
WalkTupleElements(tuple, separator);
|
|
|
|
}
|
|
|
|
|
2018-04-04 01:29:04 +08:00
|
|
|
void EndSubprogram(const char *kind, const std::optional<Name> &name) {
|
|
|
|
Outdent(), Word("END "), Word(kind), Walk(" ", name);
|
|
|
|
structureComponents_.clear();
|
|
|
|
}
|
2018-03-31 06:23:37 +08:00
|
|
|
|
2020-02-28 23:11:03 +08:00
|
|
|
llvm::raw_ostream &out_;
|
2018-03-01 08:56:10 +08:00
|
|
|
int indent_{0};
|
|
|
|
const int indentationAmount_{1};
|
|
|
|
int column_{1};
|
|
|
|
const int maxColumns_{80};
|
2018-03-31 06:23:37 +08:00
|
|
|
std::set<CharBlock> structureComponents_;
|
2019-06-12 01:34:58 +08:00
|
|
|
Encoding encoding_{Encoding::UTF_8};
|
2018-03-15 06:31:16 +08:00
|
|
|
bool capitalizeKeywords_{true};
|
[flang][openacc] OpenACC 3.0 parser
Summary:
This patch introduce the parser for OpenACC 3.0 in Flang. It uses the same TableGen mechanism
than OpenMP.
Reviewers: nvdatian, sscalpone, tskeith, klausler, ichoyjx, jdoerfert, DavidTruby
Reviewed By: klausler
Subscribers: MaskRay, SouraVX, mgorny, hiraditya, jfb, sstefan1, llvm-commits
Tags: #llvm, #flang
Differential Revision: https://reviews.llvm.org/D83649
2020-07-15 02:28:34 +08:00
|
|
|
bool openaccDirective_{false};
|
2018-07-21 06:49:19 +08:00
|
|
|
bool openmpDirective_{false};
|
2018-07-20 06:35:55 +08:00
|
|
|
bool backslashEscapes_{false};
|
2018-06-27 06:01:42 +08:00
|
|
|
preStatementType *preStatement_{nullptr};
|
2019-12-18 02:53:20 +08:00
|
|
|
AnalyzedObjectsAsFortran *asFortran_{nullptr};
|
2018-03-01 08:56:10 +08:00
|
|
|
};
|
|
|
|
|
|
|
|
void UnparseVisitor::Put(char ch) {
|
2018-07-21 06:49:19 +08:00
|
|
|
int sav = indent_;
|
[flang][openacc] OpenACC 3.0 parser
Summary:
This patch introduce the parser for OpenACC 3.0 in Flang. It uses the same TableGen mechanism
than OpenMP.
Reviewers: nvdatian, sscalpone, tskeith, klausler, ichoyjx, jdoerfert, DavidTruby
Reviewed By: klausler
Subscribers: MaskRay, SouraVX, mgorny, hiraditya, jfb, sstefan1, llvm-commits
Tags: #llvm, #flang
Differential Revision: https://reviews.llvm.org/D83649
2020-07-15 02:28:34 +08:00
|
|
|
if (openmpDirective_ || openaccDirective_) {
|
2018-07-21 06:49:19 +08:00
|
|
|
indent_ = 0;
|
|
|
|
}
|
2018-03-01 08:56:10 +08:00
|
|
|
if (column_ <= 1) {
|
|
|
|
if (ch == '\n') {
|
|
|
|
return;
|
2018-02-27 06:28:32 +08:00
|
|
|
}
|
2018-03-01 08:56:10 +08:00
|
|
|
for (int j{0}; j < indent_; ++j) {
|
|
|
|
out_ << ' ';
|
|
|
|
}
|
|
|
|
column_ = indent_ + 2;
|
|
|
|
} else if (ch == '\n') {
|
|
|
|
column_ = 1;
|
|
|
|
} else if (++column_ >= maxColumns_) {
|
|
|
|
out_ << "&\n";
|
|
|
|
for (int j{0}; j < indent_; ++j) {
|
|
|
|
out_ << ' ';
|
|
|
|
}
|
2018-07-21 06:49:19 +08:00
|
|
|
if (openmpDirective_) {
|
|
|
|
out_ << "!$OMP&";
|
|
|
|
column_ = 8;
|
[flang][openacc] OpenACC 3.0 parser
Summary:
This patch introduce the parser for OpenACC 3.0 in Flang. It uses the same TableGen mechanism
than OpenMP.
Reviewers: nvdatian, sscalpone, tskeith, klausler, ichoyjx, jdoerfert, DavidTruby
Reviewed By: klausler
Subscribers: MaskRay, SouraVX, mgorny, hiraditya, jfb, sstefan1, llvm-commits
Tags: #llvm, #flang
Differential Revision: https://reviews.llvm.org/D83649
2020-07-15 02:28:34 +08:00
|
|
|
} else if (openaccDirective_) {
|
|
|
|
out_ << "!$ACC&";
|
|
|
|
column_ = 8;
|
2018-07-21 06:49:19 +08:00
|
|
|
} else {
|
|
|
|
out_ << '&';
|
|
|
|
column_ = indent_ + 3;
|
|
|
|
}
|
2018-02-27 06:28:32 +08:00
|
|
|
}
|
2018-03-01 08:56:10 +08:00
|
|
|
out_ << ch;
|
[flang][openacc] OpenACC 3.0 parser
Summary:
This patch introduce the parser for OpenACC 3.0 in Flang. It uses the same TableGen mechanism
than OpenMP.
Reviewers: nvdatian, sscalpone, tskeith, klausler, ichoyjx, jdoerfert, DavidTruby
Reviewed By: klausler
Subscribers: MaskRay, SouraVX, mgorny, hiraditya, jfb, sstefan1, llvm-commits
Tags: #llvm, #flang
Differential Revision: https://reviews.llvm.org/D83649
2020-07-15 02:28:34 +08:00
|
|
|
if (openmpDirective_ || openaccDirective_) {
|
2018-07-21 06:49:19 +08:00
|
|
|
indent_ = sav;
|
|
|
|
}
|
2018-03-01 08:56:10 +08:00
|
|
|
}
|
2018-02-27 06:28:32 +08:00
|
|
|
|
2018-03-01 08:56:10 +08:00
|
|
|
void UnparseVisitor::Put(const char *str) {
|
|
|
|
for (; *str != '\0'; ++str) {
|
|
|
|
Put(*str);
|
|
|
|
}
|
|
|
|
}
|
|
|
|
|
|
|
|
void UnparseVisitor::Put(const std::string &str) {
|
|
|
|
for (char ch : str) {
|
|
|
|
Put(ch);
|
2018-02-27 06:28:32 +08:00
|
|
|
}
|
2018-03-01 08:56:10 +08:00
|
|
|
}
|
2018-02-27 06:28:32 +08:00
|
|
|
|
2019-06-19 04:46:54 +08:00
|
|
|
void UnparseVisitor::PutNormalized(const std::string &str) {
|
2019-06-29 02:16:37 +08:00
|
|
|
auto decoded{DecodeString<std::string, Encoding::LATIN_1>(str, true)};
|
2019-06-19 04:46:54 +08:00
|
|
|
std::string encoded{EncodeString<Encoding::LATIN_1>(decoded)};
|
|
|
|
Put(QuoteCharacterLiteral(encoded, backslashEscapes_));
|
|
|
|
}
|
|
|
|
|
2018-03-15 06:31:16 +08:00
|
|
|
void UnparseVisitor::PutKeywordLetter(char ch) {
|
|
|
|
if (capitalizeKeywords_) {
|
2018-03-01 08:56:10 +08:00
|
|
|
Put(ToUpperCaseLetter(ch));
|
2018-03-15 06:31:16 +08:00
|
|
|
} else {
|
|
|
|
Put(ToLowerCaseLetter(ch));
|
2018-02-27 06:28:32 +08:00
|
|
|
}
|
2018-03-01 08:56:10 +08:00
|
|
|
}
|
2018-02-27 06:28:32 +08:00
|
|
|
|
2018-03-15 06:31:16 +08:00
|
|
|
void UnparseVisitor::Word(const char *str) {
|
|
|
|
for (; *str != '\0'; ++str) {
|
|
|
|
PutKeywordLetter(*str);
|
2018-03-01 08:56:10 +08:00
|
|
|
}
|
|
|
|
}
|
2018-02-27 06:28:32 +08:00
|
|
|
|
2018-03-24 06:14:52 +08:00
|
|
|
void UnparseVisitor::Word(const std::string &str) { Word(str.c_str()); }
|
2018-03-24 05:31:14 +08:00
|
|
|
|
2020-02-28 23:11:03 +08:00
|
|
|
void Unparse(llvm::raw_ostream &out, const Program &program, Encoding encoding,
|
2018-07-20 06:35:55 +08:00
|
|
|
bool capitalizeKeywords, bool backslashEscapes,
|
2019-12-18 02:53:20 +08:00
|
|
|
preStatementType *preStatement, AnalyzedObjectsAsFortran *asFortran) {
|
2019-06-05 07:25:06 +08:00
|
|
|
UnparseVisitor visitor{out, 1, encoding, capitalizeKeywords, backslashEscapes,
|
2019-12-18 02:53:20 +08:00
|
|
|
preStatement, asFortran};
|
2018-02-27 06:28:32 +08:00
|
|
|
Walk(program, visitor);
|
2018-03-01 08:56:10 +08:00
|
|
|
visitor.Done();
|
2018-02-27 06:28:32 +08:00
|
|
|
}
|
2020-03-29 12:00:16 +08:00
|
|
|
} // namespace Fortran::parser
|