1 //===--- OpenCLOptions.cpp---------------------------------------*- 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 #include "clang/Basic/OpenCLOptions.h"
10 
11 namespace clang {
12 
13 bool OpenCLOptions::isKnown(llvm::StringRef Ext) const {
14   return OptMap.find(Ext) != OptMap.end();
15 }
16 
17 bool OpenCLOptions::isEnabled(llvm::StringRef Ext) const {
18   auto E = OptMap.find(Ext);
19   return E != OptMap.end() && E->second.Enabled;
20 }
21 
22 bool OpenCLOptions::isWithPragma(llvm::StringRef Ext) const {
23   auto E = OptMap.find(Ext);
24   return E != OptMap.end() && E->second.WithPragma;
25 }
26 
27 bool OpenCLOptions::isSupported(llvm::StringRef Ext,
28                                 const LangOptions &LO) const {
29   auto E = OptMap.find(Ext);
30   if (E == OptMap.end()) {
31     return false;
32   }
33   auto I = OptMap.find(Ext)->getValue();
34   return I.Supported && I.isAvailableIn(LO);
35 }
36 
37 bool OpenCLOptions::isSupportedCore(llvm::StringRef Ext,
38                                     const LangOptions &LO) const {
39   auto E = OptMap.find(Ext);
40   if (E == OptMap.end()) {
41     return false;
42   }
43   auto I = OptMap.find(Ext)->getValue();
44   return I.Supported && I.isCoreIn(LO);
45 }
46 
47 bool OpenCLOptions::isSupportedOptionalCore(llvm::StringRef Ext,
48                                             const LangOptions &LO) const {
49   auto E = OptMap.find(Ext);
50   if (E == OptMap.end()) {
51     return false;
52   }
53   auto I = OptMap.find(Ext)->getValue();
54   return I.Supported && I.isOptionalCoreIn(LO);
55 }
56 
57 bool OpenCLOptions::isSupportedCoreOrOptionalCore(llvm::StringRef Ext,
58                                                   const LangOptions &LO) const {
59   return isSupportedCore(Ext, LO) || isSupportedOptionalCore(Ext, LO);
60 }
61 
62 bool OpenCLOptions::isSupportedExtension(llvm::StringRef Ext,
63                                          const LangOptions &LO) const {
64   auto E = OptMap.find(Ext);
65   if (E == OptMap.end()) {
66     return false;
67   }
68   auto I = OptMap.find(Ext)->getValue();
69   return I.Supported && I.isAvailableIn(LO) &&
70          !isSupportedCoreOrOptionalCore(Ext, LO);
71 }
72 
73 void OpenCLOptions::enable(llvm::StringRef Ext, bool V) {
74   OptMap[Ext].Enabled = V;
75 }
76 
77 void OpenCLOptions::acceptsPragma(llvm::StringRef Ext, bool V) {
78   OptMap[Ext].WithPragma = V;
79 }
80 
81 void OpenCLOptions::support(llvm::StringRef Ext, bool V) {
82   assert(!Ext.empty() && "Extension is empty.");
83   assert(Ext[0] != '+' && Ext[0] != '-');
84   OptMap[Ext].Supported = V;
85 }
86 
87 OpenCLOptions::OpenCLOptions() {
88 #define OPENCL_GENERIC_EXTENSION(Ext, WithPragma, AvailVer, CoreVer, OptVer)   \
89   OptMap.insert_or_assign(                                                     \
90       #Ext, OpenCLOptionInfo{WithPragma, AvailVer, CoreVer, OptVer});
91 #include "clang/Basic/OpenCLExtensions.def"
92 }
93 
94 void OpenCLOptions::addSupport(const llvm::StringMap<bool> &FeaturesMap,
95                                const LangOptions &Opts) {
96   for (const auto &F : FeaturesMap) {
97     const auto &Name = F.getKey();
98     if (F.getValue() && isKnown(Name) && OptMap[Name].isAvailableIn(Opts))
99       support(Name);
100   }
101 }
102 
103 void OpenCLOptions::disableAll() {
104   for (auto &Opt : OptMap)
105     Opt.getValue().Enabled = false;
106 }
107 
108 void OpenCLOptions::enableSupportedCore(const LangOptions &LO) {
109   for (auto &Opt : OptMap)
110     if (isSupportedCoreOrOptionalCore(Opt.getKey(), LO))
111       Opt.getValue().Enabled = true;
112 }
113 
114 } // end namespace clang
115