aboutsummaryrefslogtreecommitdiff
path: root/clang/lib/Basic/TargetInfo.cpp
diff options
context:
space:
mode:
Diffstat (limited to 'clang/lib/Basic/TargetInfo.cpp')
-rw-r--r--clang/lib/Basic/TargetInfo.cpp49
1 files changed, 49 insertions, 0 deletions
diff --git a/clang/lib/Basic/TargetInfo.cpp b/clang/lib/Basic/TargetInfo.cpp
index 72ee09d..f4d7c12 100644
--- a/clang/lib/Basic/TargetInfo.cpp
+++ b/clang/lib/Basic/TargetInfo.cpp
@@ -18,6 +18,7 @@
#include "clang/Basic/LangOptions.h"
#include "llvm/ADT/APFloat.h"
#include "llvm/ADT/STLExtras.h"
+#include "llvm/ADT/StringExtras.h"
#include "llvm/Support/ErrorHandling.h"
#include "llvm/TargetParser/TargetParser.h"
#include <cstdlib>
@@ -1042,3 +1043,51 @@ void TargetInfo::copyAuxTarget(const TargetInfo *Aux) {
auto *Src = static_cast<const TransferrableTargetInfo*>(Aux);
*Target = *Src;
}
+
+std::string
+TargetInfo::simplifyConstraint(StringRef Constraint,
+ SmallVectorImpl<ConstraintInfo> *OutCons) const {
+ std::string Result;
+
+ for (const char *I = Constraint.begin(), *E = Constraint.end(); I < E; I++) {
+ switch (*I) {
+ default:
+ Result += convertConstraint(I);
+ break;
+ // Ignore these
+ case '*':
+ case '?':
+ case '!':
+ case '=': // Will see this and the following in mult-alt constraints.
+ case '+':
+ break;
+ case '#': // Ignore the rest of the constraint alternative.
+ while (I + 1 != E && I[1] != ',')
+ I++;
+ break;
+ case '&':
+ case '%':
+ Result += *I;
+ while (I + 1 != E && I[1] == *I)
+ I++;
+ break;
+ case ',':
+ Result += "|";
+ break;
+ case 'g':
+ Result += "imr";
+ break;
+ case '[': {
+ assert(OutCons &&
+ "Must pass output names to constraints with a symbolic name");
+ unsigned Index;
+ bool ResolveResult = resolveSymbolicName(I, *OutCons, Index);
+ assert(ResolveResult && "Could not resolve symbolic name");
+ (void)ResolveResult;
+ Result += llvm::utostr(Index);
+ break;
+ }
+ }
+ }
+ return Result;
+}