llvm/flang/lib/evaluate/call.h
peter klausler be3b765e2a [flang] basic skeleton of assignment analyzer
remove needless template<> on some function overloads

dodge bogus compiler warning from gcc 8.1.0 only

stricter typing of expressions in symbols

adjust modfile12.f90 expected test results

add Unwrap, massage folding a bit

Use Unwrap to simplify folding

Move KindSelector analysis into expression semantics

fix crash

checkpoint

updates to TypeParamInquiry

support of %KIND type parameter inquiry

equality testing for expressions

checkpoint during PDT implementation

reformat

checkpoint derived type instantiation

checkpoint

resolve merge

debugging failed tests

fix failing resolve37.f90 test

all existing tests pass

clean up all build warnings

fix bug

update copyright dates

fix copyright dates

address review comments

review comment

merge with master after peeling off changes

bugfixing new feature

fix warning from old g++s

tweaks after merging with latest head

more bugfixing

making modfile17.f90 test work

Make kinds into expressions in symbol table types

big refactor for deferring kinds in intrinsic types

modfile17.f90 test passes

clean up TODOs

Simplify types as stored in scopes

Test KIND parameter default init expressions, debug them

Update copyright dates

address comments

remove dead line

address comments

Original-commit: flang-compiler/f18@1f43d0a048
Reviewed-on: https://github.com/flang-compiler/f18/pull/260
Tree-same-pre-rewrite: false
2019-01-17 10:41:08 -08:00

97 lines
3.5 KiB
C++

// Copyright (c) 2018-2019, NVIDIA CORPORATION. All rights reserved.
//
// Licensed under the Apache License, Version 2.0 (the "License");
// you may not use this file except in compliance with the License.
// You may obtain a copy of the License at
//
// http://www.apache.org/licenses/LICENSE-2.0
//
// Unless required by applicable law or agreed to in writing, software
// distributed under the License is distributed on an "AS IS" BASIS,
// WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
// See the License for the specific language governing permissions and
// limitations under the License.
#ifndef FORTRAN_EVALUATE_CALL_H_
#define FORTRAN_EVALUATE_CALL_H_
#include "common.h"
#include "type.h"
#include "../common/indirection.h"
#include "../parser/char-block.h"
#include "../semantics/attr.h"
#include <optional>
#include <ostream>
#include <vector>
namespace Fortran::semantics {
class Symbol;
}
namespace Fortran::evaluate {
struct ActualArgument {
explicit ActualArgument(Expr<SomeType> &&x) : value{std::move(x)} {}
explicit ActualArgument(CopyableIndirection<Expr<SomeType>> &&v)
: value{std::move(v)} {}
std::optional<DynamicType> GetType() const;
int Rank() const;
bool operator==(const ActualArgument &) const;
std::ostream &AsFortran(std::ostream &) const;
std::optional<int> VectorSize() const;
std::optional<parser::CharBlock> keyword;
bool isAlternateReturn{false}; // when true, "value" is a label number
// TODO: Mark legacy %VAL and %REF arguments
// Subtlety: There is a distinction that must be maintained here between an
// actual argument expression that is a variable and one that is not,
// e.g. between X and (X). The parser attempts to parse each argument
// first as a variable, then as an expression, and the distinction appears
// in the parse tree.
CopyableIndirection<Expr<SomeType>> value;
};
using ActualArguments = std::vector<std::optional<ActualArgument>>;
// Intrinsics are identified by their names and the characteristics
// of their arguments, at least for now.
using IntrinsicProcedure = std::string;
struct SpecificIntrinsic {
explicit SpecificIntrinsic(IntrinsicProcedure n) : name{n} {}
SpecificIntrinsic(IntrinsicProcedure n, std::optional<DynamicType> &&dt,
int r, semantics::Attrs a)
: name{n}, type{std::move(dt)}, rank{r}, attrs{a} {}
SpecificIntrinsic(const SpecificIntrinsic &) = default;
SpecificIntrinsic(SpecificIntrinsic &&) = default;
SpecificIntrinsic &operator=(const SpecificIntrinsic &) = default;
SpecificIntrinsic &operator=(SpecificIntrinsic &&) = default;
bool operator==(const SpecificIntrinsic &) const;
std::ostream &AsFortran(std::ostream &) const;
IntrinsicProcedure name;
bool isRestrictedSpecific{false}; // if true, can only call it
std::optional<DynamicType> type; // absent if and only if subroutine call
int rank{0};
semantics::Attrs attrs; // ELEMENTAL, POINTER
};
struct ProcedureDesignator {
EVALUATE_UNION_CLASS_BOILERPLATE(ProcedureDesignator)
explicit ProcedureDesignator(SpecificIntrinsic &&i) : u{std::move(i)} {}
explicit ProcedureDesignator(const semantics::Symbol &n) : u{&n} {}
std::optional<DynamicType> GetType() const;
int Rank() const;
bool IsElemental() const;
Expr<SubscriptInteger> LEN() const;
const semantics::Symbol *GetSymbol() const;
std::ostream &AsFortran(std::ostream &) const;
// TODO: When calling X%F, pass X as PASS argument unless NOPASS
std::variant<SpecificIntrinsic, const semantics::Symbol *> u;
};
}
#endif // FORTRAN_EVALUATE_CALL_H_