1 //===-- include/flang/Common/Fortran-features.h -----------------*- C++ -*-===// 2 // 3 // Part of the LLVM Project, under the Apache License v2.0 with LLVM Exceptions. 4 // See https://llvm.org/LICENSE.txt for license information. 5 // SPDX-License-Identifier: Apache-2.0 WITH LLVM-exception 6 // 7 //===----------------------------------------------------------------------===// 8 9 #ifndef FORTRAN_COMMON_FORTRAN_FEATURES_H_ 10 #define FORTRAN_COMMON_FORTRAN_FEATURES_H_ 11 12 #include "flang/Common/Fortran.h" 13 #include "flang/Common/enum-set.h" 14 #include "flang/Common/idioms.h" 15 #include <optional> 16 #include <vector> 17 18 namespace Fortran::common { 19 20 // Non-conforming extensions & legacies 21 ENUM_CLASS(LanguageFeature, BackslashEscapes, OldDebugLines, 22 FixedFormContinuationWithColumn1Ampersand, LogicalAbbreviations, 23 XOROperator, PunctuationInNames, OptionalFreeFormSpace, BOZExtensions, 24 EmptyStatement, AlternativeNE, ExecutionPartNamelist, DECStructures, 25 DoubleComplex, Byte, StarKind, ExponentMatchingKindParam, QuadPrecision, 26 SlashInitialization, TripletInArrayConstructor, MissingColons, 27 SignedComplexLiteral, OldStyleParameter, ComplexConstructor, PercentLOC, 28 SignedMultOperand, FileName, Carriagecontrol, Convert, Dispose, 29 IOListLeadingComma, AbbreviatedEditDescriptor, ProgramParentheses, 30 PercentRefAndVal, OmitFunctionDummies, CrayPointer, Hollerith, ArithmeticIF, 31 Assign, AssignedGOTO, Pause, OpenACC, OpenMP, CUDA, CruftAfterAmpersand, 32 ClassicCComments, AdditionalFormats, BigIntLiterals, RealDoControls, 33 EquivalenceNumericWithCharacter, EquivalenceNonDefaultNumeric, 34 EquivalenceSameNonSequence, AdditionalIntrinsics, AnonymousParents, 35 OldLabelDoEndStatements, LogicalIntegerAssignment, EmptySourceFile, 36 ProgramReturn, ImplicitNoneTypeNever, ImplicitNoneTypeAlways, 37 ForwardRefImplicitNone, OpenAccessAppend, BOZAsDefaultInteger, 38 DistinguishableSpecifics, DefaultSave, PointerInSeqType, NonCharacterFormat, 39 SaveMainProgram, SaveBigMainProgramVariables, 40 DistinctArrayConstructorLengths, PPCVector, RelaxedIntentInChecking, 41 ForwardRefImplicitNoneData, NullActualForAllocatable, 42 ActualIntegerConvertedToSmallerKind, HollerithOrCharacterAsBOZ, 43 BindingAsProcedure, StatementFunctionExtensions, 44 UseGenericIntrinsicWhenSpecificDoesntMatch, DataStmtExtensions, 45 RedundantContiguous, RedundantAttribute, InitBlankCommon, 46 EmptyBindCDerivedType, MiscSourceExtensions, AllocateToOtherLength, 47 LongNames, IntrinsicAsSpecific, BenignNameClash, BenignRedundancy, 48 NullMoldAllocatableComponentValue, NopassScalarBase, MiscUseExtensions, 49 ImpliedDoIndexScope, DistinctCommonSizes, OddIndexVariableRestrictions, 50 IndistinguishableSpecifics, SubroutineAndFunctionSpecifics, 51 EmptySequenceType, NonSequenceCrayPointee, BranchIntoConstruct, 52 BadBranchTarget, HollerithPolymorphic, ListDirectedSize, 53 NonBindCInteroperability, CudaManaged, CudaUnified, 54 PolymorphicActualAllocatableOrPointerToMonomorphicDummy, RelaxedPureDummy, 55 UndefinableAsynchronousOrVolatileActual, AutomaticInMainProgram, PrintCptr, 56 SavedLocalInSpecExpr, PrintNamelist, AssumedRankPassedToNonAssumedRank, 57 IgnoreIrrelevantAttributes, Unsigned) 58 59 // Portability and suspicious usage warnings 60 ENUM_CLASS(UsageWarning, Portability, PointerToUndefinable, 61 NonTargetPassedToTarget, PointerToPossibleNoncontiguous, 62 ShortCharacterActual, ShortArrayActual, ImplicitInterfaceActual, 63 PolymorphicTransferArg, PointerComponentTransferArg, TransferSizePresence, 64 F202XAllocatableBreakingChange, OptionalMustBePresent, CommonBlockPadding, 65 LogicalVsCBool, BindCCharLength, ProcDummyArgShapes, ExternalNameConflict, 66 FoldingException, FoldingAvoidsRuntimeCrash, FoldingValueChecks, 67 FoldingFailure, FoldingLimit, Interoperability, CharacterInteroperability, 68 Bounds, Preprocessing, Scanning, OpenAccUsage, ProcPointerCompatibility, 69 VoidMold, KnownBadImplicitInterface, EmptyCase, CaseOverflow, CUDAUsage, 70 IgnoreTKRUsage, ExternalInterfaceMismatch, DefinedOperatorArgs, Final, 71 ZeroDoStep, UnusedForallIndex, OpenMPUsage, DataLength, IgnoredDirective, 72 HomonymousSpecific, HomonymousResult, IgnoredIntrinsicFunctionType, 73 PreviousScalarUse, RedeclaredInaccessibleComponent, ImplicitShared, 74 IndexVarRedefinition, IncompatibleImplicitInterfaces, BadTypeForTarget, 75 VectorSubscriptFinalization, UndefinedFunctionResult, UselessIomsg, 76 MismatchingDummyProcedure, SubscriptedEmptyArray, UnsignedLiteralTruncation, 77 CompatibleDeclarationsFromDistinctModules) 78 79 using LanguageFeatures = EnumSet<LanguageFeature, LanguageFeature_enumSize>; 80 using UsageWarnings = EnumSet<UsageWarning, UsageWarning_enumSize>; 81 82 std::optional<LanguageFeature> FindLanguageFeature(const char *); 83 std::optional<UsageWarning> FindUsageWarning(const char *); 84 85 class LanguageFeatureControl { 86 public: 87 LanguageFeatureControl(); 88 LanguageFeatureControl(const LanguageFeatureControl &) = default; 89 90 void Enable(LanguageFeature f, bool yes = true) { disable_.set(f, !yes); } 91 void EnableWarning(LanguageFeature f, bool yes = true) { 92 warnLanguage_.set(f, yes); 93 } 94 void EnableWarning(UsageWarning w, bool yes = true) { 95 warnUsage_.set(w, yes); 96 } 97 void WarnOnAllNonstandard(bool yes = true) { warnAllLanguage_ = yes; } 98 void WarnOnAllUsage(bool yes = true) { warnAllUsage_ = yes; } 99 void DisableAllNonstandardWarnings() { 100 warnAllLanguage_ = false; 101 warnLanguage_.clear(); 102 } 103 void DisableAllUsageWarnings() { 104 warnAllUsage_ = false; 105 warnUsage_.clear(); 106 } 107 108 bool IsEnabled(LanguageFeature f) const { return !disable_.test(f); } 109 bool ShouldWarn(LanguageFeature f) const { 110 return (warnAllLanguage_ && f != LanguageFeature::OpenMP && 111 f != LanguageFeature::OpenACC && f != LanguageFeature::CUDA) || 112 warnLanguage_.test(f); 113 } 114 bool ShouldWarn(UsageWarning w) const { 115 return warnAllUsage_ || warnUsage_.test(w); 116 } 117 // Return all spellings of operators names, depending on features enabled 118 std::vector<const char *> GetNames(LogicalOperator) const; 119 std::vector<const char *> GetNames(RelationalOperator) const; 120 121 private: 122 LanguageFeatures disable_; 123 LanguageFeatures warnLanguage_; 124 bool warnAllLanguage_{false}; 125 UsageWarnings warnUsage_; 126 bool warnAllUsage_{false}; 127 }; 128 } // namespace Fortran::common 129 #endif // FORTRAN_COMMON_FORTRAN_FEATURES_H_ 130