[PATCH] D57337: [Targets] Adjust ARM data layout

2019-01-28 Thread Michael Platings via Phabricator via cfe-commits
michaelplatings updated this revision to Diff 183893.
michaelplatings added a comment.

Diff with -U9


Repository:
  rC Clang

CHANGES SINCE LAST ACTION
  https://reviews.llvm.org/D57337/new/

https://reviews.llvm.org/D57337

Files:
  clang/lib/Basic/Targets/ARM.cpp
  clang/test/CodeGen/armv7k-abi.c
  clang/test/CodeGen/target-data.c

Index: clang/test/CodeGen/target-data.c
===
--- clang/test/CodeGen/target-data.c
+++ clang/test/CodeGen/target-data.c
@@ -96,7 +96,7 @@
 
 // RUN: %clang_cc1 -triple arm-nacl -o - -emit-llvm %s | \
 // RUN: FileCheck %s -check-prefix=ARM-NACL
-// ARM-NACL: target datalayout = "e-m:e-p:32:32-i64:64-v128:64:128-a:0:32-n32-S128"
+// ARM-NACL: target datalayout = "e-m:e-p:32:32-F8-i64:64-v128:64:128-a:0:32-n32-S128"
 
 // RUN: %clang_cc1 -triple mipsel-nacl -o - -emit-llvm %s | \
 // RUN: FileCheck %s -check-prefix=MIPS-NACL
@@ -165,19 +165,19 @@
 
 // RUN: %clang_cc1 -triple thumb-unknown-gnueabi -o - -emit-llvm %s | \
 // RUN: FileCheck %s -check-prefix=THUMB
-// THUMB: target datalayout = "e-m:e-p:32:32-i64:64-v128:64:128-a:0:32-n32-S64"
+// THUMB: target datalayout = "e-m:e-p:32:32-F8-i64:64-v128:64:128-a:0:32-n32-S64"
 
 // RUN: %clang_cc1 -triple arm-unknown-gnueabi -o - -emit-llvm %s | \
 // RUN: FileCheck %s -check-prefix=ARM
-// ARM: target datalayout = "e-m:e-p:32:32-i64:64-v128:64:128-a:0:32-n32-S64"
+// ARM: target datalayout = "e-m:e-p:32:32-F8-i64:64-v128:64:128-a:0:32-n32-S64"
 
 // RUN: %clang_cc1 -triple thumb-unknown -o - -emit-llvm -target-abi apcs-gnu \
 // RUN: %s | FileCheck %s -check-prefix=THUMB-GNU
-// THUMB-GNU: target datalayout = "e-m:e-p:32:32-f64:32:64-v64:32:64-v128:32:128-a:0:32-n32-S32"
+// THUMB-GNU: target datalayout = "e-m:e-p:32:32-F8-f64:32:64-v64:32:64-v128:32:128-a:0:32-n32-S32"
 
 // RUN: %clang_cc1 -triple arm-unknown -o - -emit-llvm -target-abi apcs-gnu \
 // RUN: %s | FileCheck %s -check-prefix=ARM-GNU
-// ARM-GNU: target datalayout = "e-m:e-p:32:32-f64:32:64-v64:32:64-v128:32:128-a:0:32-n32-S32"
+// ARM-GNU: target datalayout = "e-m:e-p:32:32-F8-f64:32:64-v64:32:64-v128:32:128-a:0:32-n32-S32"
 
 // RUN: %clang_cc1 -triple arc-unknown-unknown -o - -emit-llvm %s | \
 // RUN: FileCheck %s -check-prefix=ARC
Index: clang/test/CodeGen/armv7k-abi.c
===
--- clang/test/CodeGen/armv7k-abi.c
+++ clang/test/CodeGen/armv7k-abi.c
@@ -4,7 +4,7 @@
 
 // Make sure 64 and 128 bit types are naturally aligned by the v7k ABI:
 
-// CHECK: target datalayout = "e-m:o-p:32:32-i64:64-a:0:32-n32-S128"
+// CHECK: target datalayout = "e-m:o-p:32:32-F8-i64:64-a:0:32-n32-S128"
 
 typedef struct {
   float arr[4];
Index: clang/lib/Basic/Targets/ARM.cpp
===
--- clang/lib/Basic/Targets/ARM.cpp
+++ clang/lib/Basic/Targets/ARM.cpp
@@ -40,13 +40,14 @@
   // so set preferred for small types to 32.
   if (T.isOSBinFormatMachO()) {
 resetDataLayout(BigEndian
-? "E-m:o-p:32:32-i64:64-v128:64:128-a:0:32-n32-S64"
-: "e-m:o-p:32:32-i64:64-v128:64:128-a:0:32-n32-S64");
+? "E-m:o-p:32:32-F8-i64:64-v128:64:128-a:0:32-n32-S64"
+: "e-m:o-p:32:32-F8-i64:64-v128:64:128-a:0:32-n32-S64");
   } else if (T.isOSWindows()) {
 assert(!BigEndian && "Windows on ARM does not support big endian");
 resetDataLayout("e"
 "-m:w"
 "-p:32:32"
+"-F8"
 "-i64:64"
 "-v128:64:128"
 "-a:0:32"
@@ -54,11 +55,11 @@
 "-S64");
   } else if (T.isOSNaCl()) {
 assert(!BigEndian && "NaCl on ARM does not support big endian");
-resetDataLayout("e-m:e-p:32:32-i64:64-v128:64:128-a:0:32-n32-S128");
+resetDataLayout("e-m:e-p:32:32-F8-i64:64-v128:64:128-a:0:32-n32-S128");
   } else {
 resetDataLayout(BigEndian
-? "E-m:e-p:32:32-i64:64-v128:64:128-a:0:32-n32-S64"
-: "e-m:e-p:32:32-i64:64-v128:64:128-a:0:32-n32-S64");
+? "E-m:e-p:32:32-F8-i64:64-v128:64:128-a:0:32-n32-S64"
+: "e-m:e-p:32:32-F8-i64:64-v128:64:128-a:0:32-n32-S64");
   }
 
   // FIXME: Enumerated types are variable width in straight AAPCS.
@@ -87,17 +88,17 @@
 
   if (T.isOSBinFormatMachO() && IsAAPCS16) {
 assert(!BigEndian && "AAPCS16 does not support big-endian");
-resetDataLayout("e-m:o-p:32:32-i64:64-a:0:32-n32-S128");
+resetDataLayout("e-m:o-p:32:32-F8-i64:64-a:0:32-n32-S128");
   } else if (T.isOSBinFormatMachO())
 resetDataLayout(
 BigEndian
-? "E-m:o-p:32:32-f64:32:64-v64:32:64-v128:32:128-a:0:32-n32-S32"
-: "e-m:o-p:32:32-f64:32:64-v64:32:64-v128:32:128-a:0:32-n32-S32");
+? "E-m:o-p:32:32-F8-f64:32:64-v64:32:64-v128:32:128-a:0:32-n32-S32"
+ 

[PATCH] D55121: Make several Python scripts portable across Python2 and Python 3

2018-11-30 Thread Michael Platings via Phabricator via cfe-commits
michaelplatings added a comment.

In general LGTM, as someone who's done a 2-3 conversion of similar scale before.

The only suggestion I'd make is to consider changing the `__future__` imports 
to `from __future__ import absolute_import, division, print_function`
I found this gave the best consistency between 2 & 3. Probably you don't need 
it at this point, but once the conversion is done there's less to go wrong in 
future.


Repository:
  rC Clang

CHANGES SINCE LAST ACTION
  https://reviews.llvm.org/D55121/new/

https://reviews.llvm.org/D55121



___
cfe-commits mailing list
cfe-commits@lists.llvm.org
http://lists.llvm.org/cgi-bin/mailman/listinfo/cfe-commits


[PATCH] D55121: Make several Python scripts portable across Python2 and Python 3

2018-12-03 Thread Michael Platings via Phabricator via cfe-commits
michaelplatings accepted this revision.
michaelplatings added a comment.
This revision is now accepted and ready to land.

LGTM


CHANGES SINCE LAST ACTION
  https://reviews.llvm.org/D55121/new/

https://reviews.llvm.org/D55121



___
cfe-commits mailing list
cfe-commits@lists.llvm.org
http://lists.llvm.org/cgi-bin/mailman/listinfo/cfe-commits


[PATCH] D57335: [IR] Don't assume all functions are 4 byte aligned

2019-02-26 Thread Michael Platings via Phabricator via cfe-commits
michaelplatings updated this revision to Diff 188324.

Repository:
  rG LLVM Github Monorepo

CHANGES SINCE LAST ACTION
  https://reviews.llvm.org/D57335/new/

https://reviews.llvm.org/D57335

Files:
  clang/lib/Basic/Targets/ARM.cpp
  clang/test/CodeGen/armv7k-abi.c
  clang/test/CodeGen/target-data.c
  llvm/docs/LangRef.rst
  llvm/include/llvm/IR/DataLayout.h
  llvm/lib/IR/ConstantFold.cpp
  llvm/lib/IR/DataLayout.cpp
  llvm/lib/IR/Value.cpp
  llvm/lib/Target/ARM/ARMTargetMachine.cpp
  llvm/unittests/IR/CMakeLists.txt
  llvm/unittests/IR/ConstantsTest.cpp
  llvm/unittests/IR/DataLayoutTest.cpp
  llvm/unittests/IR/FunctionTest.cpp

Index: llvm/unittests/IR/FunctionTest.cpp
===
--- llvm/unittests/IR/FunctionTest.cpp
+++ llvm/unittests/IR/FunctionTest.cpp
@@ -129,4 +129,29 @@
   EXPECT_TRUE(F->hasSection());
 }
 
+TEST(FunctionTest, GetPointerAlignment) {
+  LLVMContext Context;
+  Type *VoidType(Type::getVoidTy(Context));
+  FunctionType *FuncType(FunctionType::get(VoidType, false));
+  Function *Func = Function::Create(
+  FuncType, GlobalValue::ExternalLinkage);
+  EXPECT_EQ(0U, Func->getPointerAlignment(DataLayout("")));
+  EXPECT_EQ(1U, Func->getPointerAlignment(DataLayout("Fi8")));
+  EXPECT_EQ(1U, Func->getPointerAlignment(DataLayout("Fn8")));
+  EXPECT_EQ(2U, Func->getPointerAlignment(DataLayout("Fi16")));
+  EXPECT_EQ(2U, Func->getPointerAlignment(DataLayout("Fn16")));
+  EXPECT_EQ(4U, Func->getPointerAlignment(DataLayout("Fi32")));
+  EXPECT_EQ(4U, Func->getPointerAlignment(DataLayout("Fn32")));
+
+  Func->setAlignment(4U);
+
+  EXPECT_EQ(0U, Func->getPointerAlignment(DataLayout("")));
+  EXPECT_EQ(1U, Func->getPointerAlignment(DataLayout("Fi8")));
+  EXPECT_EQ(4U, Func->getPointerAlignment(DataLayout("Fn8")));
+  EXPECT_EQ(2U, Func->getPointerAlignment(DataLayout("Fi16")));
+  EXPECT_EQ(4U, Func->getPointerAlignment(DataLayout("Fn16")));
+  EXPECT_EQ(4U, Func->getPointerAlignment(DataLayout("Fi32")));
+  EXPECT_EQ(4U, Func->getPointerAlignment(DataLayout("Fn32")));
+}
+
 } // end namespace
Index: llvm/unittests/IR/DataLayoutTest.cpp
===
--- /dev/null
+++ llvm/unittests/IR/DataLayoutTest.cpp
@@ -0,0 +1,47 @@
+//===- ConstantRangeTest.cpp - ConstantRange tests ===//
+//
+// 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
+//
+//===--===//
+
+#include "llvm/IR/DataLayout.h"
+#include "gtest/gtest.h"
+
+using namespace llvm;
+
+namespace {
+
+TEST(DataLayoutTest, FunctionPtrAlign) {
+  EXPECT_EQ(0U, DataLayout("").getFunctionPtrAlign());
+  EXPECT_EQ(1U, DataLayout("Fi8").getFunctionPtrAlign());
+  EXPECT_EQ(2U, DataLayout("Fi16").getFunctionPtrAlign());
+  EXPECT_EQ(4U, DataLayout("Fi32").getFunctionPtrAlign());
+  EXPECT_EQ(8U, DataLayout("Fi64").getFunctionPtrAlign());
+  EXPECT_EQ(1U, DataLayout("Fn8").getFunctionPtrAlign());
+  EXPECT_EQ(2U, DataLayout("Fn16").getFunctionPtrAlign());
+  EXPECT_EQ(4U, DataLayout("Fn32").getFunctionPtrAlign());
+  EXPECT_EQ(8U, DataLayout("Fn64").getFunctionPtrAlign());
+  EXPECT_EQ(DataLayout::FunctionPtrAlignType::Independent, \
+  DataLayout("").getFunctionPtrAlignType());
+  EXPECT_EQ(DataLayout::FunctionPtrAlignType::Independent, \
+  DataLayout("Fi8").getFunctionPtrAlignType());
+  EXPECT_EQ(DataLayout::FunctionPtrAlignType::MultipleOfFunctionAlign, \
+  DataLayout("Fn8").getFunctionPtrAlignType());
+  EXPECT_EQ(DataLayout("Fi8"), DataLayout("Fi8"));
+  EXPECT_NE(DataLayout("Fi8"), DataLayout("Fi16"));
+  EXPECT_NE(DataLayout("Fi8"), DataLayout("Fn8"));
+
+  DataLayout a(""), b("Fi8"), c("Fn8");
+  EXPECT_NE(a, b);
+  EXPECT_NE(a, c);
+  EXPECT_NE(b, c);
+
+  a = b;
+  EXPECT_EQ(a, b);
+  a = c;
+  EXPECT_EQ(a, c);
+}
+
+}  // anonymous namespace
Index: llvm/unittests/IR/ConstantsTest.cpp
===
--- llvm/unittests/IR/ConstantsTest.cpp
+++ llvm/unittests/IR/ConstantsTest.cpp
@@ -475,5 +475,105 @@
   ASSERT_EQ(cast(C)->getOpcode(), Instruction::BitCast);
 }
 
+bool foldFuncPtrAndConstToNull(LLVMContext &Context, Module *TheModule,
+   uint64_t AndValue, unsigned FunctionAlign = 0) {
+  Type *VoidType(Type::getVoidTy(Context));
+  FunctionType *FuncType(FunctionType::get(VoidType, false));
+  Function *Func(Function::Create(
+  FuncType, GlobalValue::ExternalLinkage, "", TheModule));
+
+  if (FunctionAlign) Func->setAlignment(FunctionAlign);
+
+  IntegerType *ConstantIntType(Type::getInt32Ty(Context));
+  ConstantInt *TheConstant(ConstantInt::get(ConstantIntType, AndValue));
+
+  Constant *TheConstantExpr(
+  ConstantExpr::getPtrToInt(Func, ConstantIntType));
+
+  return ConstantExpr::g

[PATCH] D57335: [IR] Don't assume all functions are 4 byte aligned

2019-02-26 Thread Michael Platings via Phabricator via cfe-commits
michaelplatings updated this revision to Diff 188325.

Repository:
  rG LLVM Github Monorepo

CHANGES SINCE LAST ACTION
  https://reviews.llvm.org/D57335/new/

https://reviews.llvm.org/D57335

Files:
  clang/lib/Basic/Targets/ARM.cpp
  clang/test/CodeGen/armv7k-abi.c
  clang/test/CodeGen/target-data.c
  llvm/docs/LangRef.rst
  llvm/include/llvm/IR/DataLayout.h
  llvm/lib/IR/ConstantFold.cpp
  llvm/lib/IR/DataLayout.cpp
  llvm/lib/IR/Value.cpp
  llvm/lib/Target/ARM/ARMTargetMachine.cpp
  llvm/unittests/IR/CMakeLists.txt
  llvm/unittests/IR/ConstantsTest.cpp
  llvm/unittests/IR/DataLayoutTest.cpp
  llvm/unittests/IR/FunctionTest.cpp

Index: llvm/unittests/IR/FunctionTest.cpp
===
--- llvm/unittests/IR/FunctionTest.cpp
+++ llvm/unittests/IR/FunctionTest.cpp
@@ -129,4 +129,29 @@
   EXPECT_TRUE(F->hasSection());
 }
 
+TEST(FunctionTest, GetPointerAlignment) {
+  LLVMContext Context;
+  Type *VoidType(Type::getVoidTy(Context));
+  FunctionType *FuncType(FunctionType::get(VoidType, false));
+  Function *Func = Function::Create(
+  FuncType, GlobalValue::ExternalLinkage);
+  EXPECT_EQ(0U, Func->getPointerAlignment(DataLayout("")));
+  EXPECT_EQ(1U, Func->getPointerAlignment(DataLayout("Fi8")));
+  EXPECT_EQ(1U, Func->getPointerAlignment(DataLayout("Fn8")));
+  EXPECT_EQ(2U, Func->getPointerAlignment(DataLayout("Fi16")));
+  EXPECT_EQ(2U, Func->getPointerAlignment(DataLayout("Fn16")));
+  EXPECT_EQ(4U, Func->getPointerAlignment(DataLayout("Fi32")));
+  EXPECT_EQ(4U, Func->getPointerAlignment(DataLayout("Fn32")));
+
+  Func->setAlignment(4U);
+
+  EXPECT_EQ(0U, Func->getPointerAlignment(DataLayout("")));
+  EXPECT_EQ(1U, Func->getPointerAlignment(DataLayout("Fi8")));
+  EXPECT_EQ(4U, Func->getPointerAlignment(DataLayout("Fn8")));
+  EXPECT_EQ(2U, Func->getPointerAlignment(DataLayout("Fi16")));
+  EXPECT_EQ(4U, Func->getPointerAlignment(DataLayout("Fn16")));
+  EXPECT_EQ(4U, Func->getPointerAlignment(DataLayout("Fi32")));
+  EXPECT_EQ(4U, Func->getPointerAlignment(DataLayout("Fn32")));
+}
+
 } // end namespace
Index: llvm/unittests/IR/DataLayoutTest.cpp
===
--- /dev/null
+++ llvm/unittests/IR/DataLayoutTest.cpp
@@ -0,0 +1,47 @@
+//===- ConstantRangeTest.cpp - ConstantRange tests ===//
+//
+// 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
+//
+//===--===//
+
+#include "llvm/IR/DataLayout.h"
+#include "gtest/gtest.h"
+
+using namespace llvm;
+
+namespace {
+
+TEST(DataLayoutTest, FunctionPtrAlign) {
+  EXPECT_EQ(0U, DataLayout("").getFunctionPtrAlign());
+  EXPECT_EQ(1U, DataLayout("Fi8").getFunctionPtrAlign());
+  EXPECT_EQ(2U, DataLayout("Fi16").getFunctionPtrAlign());
+  EXPECT_EQ(4U, DataLayout("Fi32").getFunctionPtrAlign());
+  EXPECT_EQ(8U, DataLayout("Fi64").getFunctionPtrAlign());
+  EXPECT_EQ(1U, DataLayout("Fn8").getFunctionPtrAlign());
+  EXPECT_EQ(2U, DataLayout("Fn16").getFunctionPtrAlign());
+  EXPECT_EQ(4U, DataLayout("Fn32").getFunctionPtrAlign());
+  EXPECT_EQ(8U, DataLayout("Fn64").getFunctionPtrAlign());
+  EXPECT_EQ(DataLayout::FunctionPtrAlignType::Independent, \
+  DataLayout("").getFunctionPtrAlignType());
+  EXPECT_EQ(DataLayout::FunctionPtrAlignType::Independent, \
+  DataLayout("Fi8").getFunctionPtrAlignType());
+  EXPECT_EQ(DataLayout::FunctionPtrAlignType::MultipleOfFunctionAlign, \
+  DataLayout("Fn8").getFunctionPtrAlignType());
+  EXPECT_EQ(DataLayout("Fi8"), DataLayout("Fi8"));
+  EXPECT_NE(DataLayout("Fi8"), DataLayout("Fi16"));
+  EXPECT_NE(DataLayout("Fi8"), DataLayout("Fn8"));
+
+  DataLayout a(""), b("Fi8"), c("Fn8");
+  EXPECT_NE(a, b);
+  EXPECT_NE(a, c);
+  EXPECT_NE(b, c);
+
+  a = b;
+  EXPECT_EQ(a, b);
+  a = c;
+  EXPECT_EQ(a, c);
+}
+
+}  // anonymous namespace
Index: llvm/unittests/IR/ConstantsTest.cpp
===
--- llvm/unittests/IR/ConstantsTest.cpp
+++ llvm/unittests/IR/ConstantsTest.cpp
@@ -475,5 +475,105 @@
   ASSERT_EQ(cast(C)->getOpcode(), Instruction::BitCast);
 }
 
+bool foldFuncPtrAndConstToNull(LLVMContext &Context, Module *TheModule,
+   uint64_t AndValue, unsigned FunctionAlign = 0) {
+  Type *VoidType(Type::getVoidTy(Context));
+  FunctionType *FuncType(FunctionType::get(VoidType, false));
+  Function *Func(Function::Create(
+  FuncType, GlobalValue::ExternalLinkage, "", TheModule));
+
+  if (FunctionAlign) Func->setAlignment(FunctionAlign);
+
+  IntegerType *ConstantIntType(Type::getInt32Ty(Context));
+  ConstantInt *TheConstant(ConstantInt::get(ConstantIntType, AndValue));
+
+  Constant *TheConstantExpr(
+  ConstantExpr::getPtrToInt(Func, ConstantIntType));
+
+  return ConstantExpr::g

[PATCH] D57335: [IR] Don't assume all functions are 4 byte aligned

2019-03-06 Thread Michael Platings via Phabricator via cfe-commits
This revision was automatically updated to reflect the committed changes.
Closed by commit rL355522: [IR][ARM] Add function pointer alignment to 
datalayout (authored by michaelplatings, committed by ).

Changed prior to commit:
  https://reviews.llvm.org/D57335?vs=188325&id=189524#toc

Repository:
  rL LLVM

CHANGES SINCE LAST ACTION
  https://reviews.llvm.org/D57335/new/

https://reviews.llvm.org/D57335

Files:
  cfe/trunk/lib/Basic/Targets/ARM.cpp
  cfe/trunk/test/CodeGen/armv7k-abi.c
  cfe/trunk/test/CodeGen/target-data.c
  llvm/trunk/docs/LangRef.rst
  llvm/trunk/include/llvm/IR/DataLayout.h
  llvm/trunk/lib/IR/ConstantFold.cpp
  llvm/trunk/lib/IR/DataLayout.cpp
  llvm/trunk/lib/IR/Value.cpp
  llvm/trunk/lib/Target/ARM/ARMTargetMachine.cpp
  llvm/trunk/unittests/IR/CMakeLists.txt
  llvm/trunk/unittests/IR/ConstantsTest.cpp
  llvm/trunk/unittests/IR/DataLayoutTest.cpp
  llvm/trunk/unittests/IR/FunctionTest.cpp

Index: llvm/trunk/lib/Target/ARM/ARMTargetMachine.cpp
===
--- llvm/trunk/lib/Target/ARM/ARMTargetMachine.cpp
+++ llvm/trunk/lib/Target/ARM/ARMTargetMachine.cpp
@@ -141,6 +141,10 @@
   // Pointers are 32 bits and aligned to 32 bits.
   Ret += "-p:32:32";
 
+  // Function pointers are aligned to 8 bits (because the LSB stores the
+  // ARM/Thumb state).
+  Ret += "-Fi8";
+
   // ABIs other than APCS have 64 bit integers with natural alignment.
   if (ABI != ARMBaseTargetMachine::ARM_ABI_APCS)
 Ret += "-i64:64";
Index: llvm/trunk/lib/IR/DataLayout.cpp
===
--- llvm/trunk/lib/IR/DataLayout.cpp
+++ llvm/trunk/lib/IR/DataLayout.cpp
@@ -184,6 +184,8 @@
   AllocaAddrSpace = 0;
   StackNaturalAlign = 0;
   ProgramAddrSpace = 0;
+  FunctionPtrAlign = 0;
+  TheFunctionPtrAlignType = FunctionPtrAlignType::Independent;
   ManglingMode = MM_None;
   NonIntegralAddressSpaces.clear();
 
@@ -379,6 +381,22 @@
   StackNaturalAlign = inBytes(getInt(Tok));
   break;
 }
+case 'F': {
+  switch (Tok.front()) {
+  case 'i':
+TheFunctionPtrAlignType = FunctionPtrAlignType::Independent;
+break;
+  case 'n':
+TheFunctionPtrAlignType = FunctionPtrAlignType::MultipleOfFunctionAlign;
+break;
+  default:
+report_fatal_error("Unknown function pointer alignment type in "
+   "datalayout string");
+  }
+  Tok = Tok.substr(1);
+  FunctionPtrAlign = inBytes(getInt(Tok));
+  break;
+}
 case 'P': { // Function address space.
   ProgramAddrSpace = getAddrSpace(Tok);
   break;
@@ -432,6 +450,8 @@
  AllocaAddrSpace == Other.AllocaAddrSpace &&
  StackNaturalAlign == Other.StackNaturalAlign &&
  ProgramAddrSpace == Other.ProgramAddrSpace &&
+ FunctionPtrAlign == Other.FunctionPtrAlign &&
+ TheFunctionPtrAlignType == Other.TheFunctionPtrAlignType &&
  ManglingMode == Other.ManglingMode &&
  LegalIntWidths == Other.LegalIntWidths &&
  Alignments == Other.Alignments && Pointers == Other.Pointers;
Index: llvm/trunk/lib/IR/ConstantFold.cpp
===
--- llvm/trunk/lib/IR/ConstantFold.cpp
+++ llvm/trunk/lib/IR/ConstantFold.cpp
@@ -26,6 +26,7 @@
 #include "llvm/IR/GlobalAlias.h"
 #include "llvm/IR/GlobalVariable.h"
 #include "llvm/IR/Instructions.h"
+#include "llvm/IR/Module.h"
 #include "llvm/IR/Operator.h"
 #include "llvm/IR/PatternMatch.h"
 #include "llvm/Support/ErrorHandling.h"
@@ -1076,10 +1077,29 @@
 isa(CE1->getOperand(0))) {
   GlobalValue *GV = cast(CE1->getOperand(0));
 
-  // Functions are at least 4-byte aligned.
-  unsigned GVAlign = GV->getAlignment();
-  if (isa(GV))
-GVAlign = std::max(GVAlign, 4U);
+  unsigned GVAlign;
+
+  if (Module *TheModule = GV->getParent()) {
+GVAlign = GV->getPointerAlignment(TheModule->getDataLayout());
+
+// If the function alignment is not specified then assume that it
+// is 4.
+// This is dangerous; on x86, the alignment of the pointer
+// corresponds to the alignment of the function, but might be less
+// than 4 if it isn't explicitly specified.
+// However, a fix for this behaviour was reverted because it
+// increased code size (see https://reviews.llvm.org/D55115)
+// FIXME: This code should be deleted once existing targets have
+// appropriate defaults
+if (GVAlign == 0U && isa(GV))
+  GVAlign = 4U;
+  } else if (isa(GV)) {
+// Without a datalayout we have to assume the worst case: that the
+// function pointer isn't aligned at all.
+GVAlign = 0U;
+  } else {
+GVAlign = GV->getAlignment();
+  }
 
 

[PATCH] D57896: Variable names rule

2019-02-07 Thread Michael Platings via Phabricator via cfe-commits
michaelplatings created this revision.
Herald added a project: clang.
Herald added a subscriber: cfe-commits.

Following discussion 
 and 
general agreement that the current naming rule for variables is not ideal, this 
patch switches the naming rule to make `lowerCamelCase` the standard, 
consistent with a prior RFC 
.

Given that over 450,000 variables are currently named in `UpperCamelCase`, the 
rule also permits using that form for consistency with existing code. I can't 
see a way to express that in .clang-tidy files.


Repository:
  rG LLVM Github Monorepo

https://reviews.llvm.org/D57896

Files:
  .clang-tidy
  clang/.clang-tidy
  llvm/.clang-tidy
  llvm/docs/CodingStandards.rst

Index: llvm/docs/CodingStandards.rst
===
--- llvm/docs/CodingStandards.rst
+++ llvm/docs/CodingStandards.rst
@@ -1191,8 +1191,9 @@
   nouns and start with an upper-case letter (e.g. ``TextFileReader``).
 
 * **Variable names** should be nouns (as they represent state).  The name should
-  be camel case, and start with an upper case letter (e.g. ``Leader`` or
-  ``Boats``).
+  be camel case, and start with a lower case letter (e.g. ``leader`` or
+  ``boats``). It is also acceptable to use ``UpperCamelCase`` for consistency
+  with existing code.
   
 * **Function names** should be verb phrases (as they represent actions), and
   command-like function should be imperative.  The name should be camel case,
@@ -1232,16 +1233,22 @@
 
   class VehicleMaker {
 ...
-Factory F;// Bad -- abbreviation and non-descriptive.
-Factory Factory;  // Better.
-Factory TireFactory;  // Even better -- if VehicleMaker has more than one
-// kind of factories.
+Factory f;// Bad -- abbreviation and non-descriptive.
+Factory factory;  // Better.
+Factory tireFactory;  // Even better -- if VehicleMaker has more than
+// one kind of factory.
   };
 
-  Vehicle makeVehicle(VehicleType Type) {
-VehicleMaker M; // Might be OK if having a short life-span.
-Tire Tmp1 = M.makeTire();   // Bad -- 'Tmp1' provides no information.
-Light Headlight = M.makeLight("head");  // Good -- descriptive.
+  Vehicle makeVehicle(VehicleType type) {
+// Reusing the type name in lowerCamelCase form is often a good way to get
+// a suitable variable name.
+VehicleMaker vehicleMaker;
+
+// Bad -- 'tmp1' provides no information.
+Tire tmp1 = vehicleMaker.makeTire();
+
+// Good -- descriptive.
+Light headlight = vehicleMaker.makeLight("head");
 ...
   }
 
Index: llvm/.clang-tidy
===
--- llvm/.clang-tidy
+++ llvm/.clang-tidy
@@ -7,11 +7,11 @@
   - key: readability-identifier-naming.FunctionCase
 value:   camelBack
   - key: readability-identifier-naming.MemberCase
-value:   CamelCase
+value:   camelBack
   - key: readability-identifier-naming.ParameterCase
-value:   CamelCase
+value:   camelBack
   - key: readability-identifier-naming.UnionCase
 value:   CamelCase
   - key: readability-identifier-naming.VariableCase
-value:   CamelCase
+value:   camelBack
 
Index: clang/.clang-tidy
===
--- clang/.clang-tidy
+++ clang/.clang-tidy
@@ -12,11 +12,11 @@
   - key: readability-identifier-naming.FunctionCase
 value:   camelBack
   - key: readability-identifier-naming.MemberCase
-value:   CamelCase
+value:   camelBack
   - key: readability-identifier-naming.ParameterCase
-value:   CamelCase
+value:   camelBack
   - key: readability-identifier-naming.UnionCase
 value:   CamelCase
   - key: readability-identifier-naming.VariableCase
-value:   CamelCase
+value:   camelBack
 
Index: .clang-tidy
===
--- .clang-tidy
+++ .clang-tidy
@@ -7,11 +7,11 @@
   - key: readability-identifier-naming.FunctionCase
 value:   camelBack
   - key: readability-identifier-naming.MemberCase
-value:   CamelCase
+value:   camelBack
   - key: readability-identifier-naming.ParameterCase
-value:   CamelCase
+value:   camelBack
   - key: readability-identifier-naming.UnionCase
 value:   CamelCase
   - key: readability-identifier-naming.VariableCase
-value:   CamelCase
+value:  

[PATCH] D57896: Variable names rule

2019-02-07 Thread Michael Platings via Phabricator via cfe-commits
michaelplatings added a comment.

In D57896#1389042 , @lebedev.ri wrote:

> Pretty sure this patch should have gone to llvm-commits, not cfe-commits.


I just set the repository, Phabricator did the rest - apparently the magic 
isn't working so well.


Repository:
  rG LLVM Github Monorepo

CHANGES SINCE LAST ACTION
  https://reviews.llvm.org/D57896/new/

https://reviews.llvm.org/D57896



___
cfe-commits mailing list
cfe-commits@lists.llvm.org
https://lists.llvm.org/cgi-bin/mailman/listinfo/cfe-commits


[PATCH] D57896: Variable names rule

2019-02-08 Thread Michael Platings via Phabricator via cfe-commits
michaelplatings added a comment.

In D57896#1389067 , @lebedev.ri wrote:

> 1. Does clang-tidy warn on every single existing variable now?
> 2. It might be best to give this more visibility, by submitting a mail to 
> llvm-dev, with a **noticeable** subject, like "RFC: changing variable naming 
> rules in LLVM codebase"




1. Pretty much. Previously clang-tidy gave 56,787 unique warnings. After this 
patch it gives 361,382 unique warnings. I personally would be happy to change 
the settings from `camelBack` to `aNy_CasE`.

2. Done: http://lists.llvm.org/pipermail/llvm-dev/2019-February/130083.html


Repository:
  rG LLVM Github Monorepo

CHANGES SINCE LAST ACTION
  https://reviews.llvm.org/D57896/new/

https://reviews.llvm.org/D57896



___
cfe-commits mailing list
cfe-commits@lists.llvm.org
https://lists.llvm.org/cgi-bin/mailman/listinfo/cfe-commits


[PATCH] D57896: Variable names rule

2019-02-11 Thread Michael Platings via Phabricator via cfe-commits
michaelplatings added a comment.

In D57896#1390517 , @MyDeveloperDay 
wrote:

> Should we come up with a new style?  say `UpperOrLowerCamelCase`,   I don't 
> mind going and doing that in the readability-identifier-naming check, given 
> that I just wrote up all the Options for that check 
> https://clang.llvm.org/extra/clang-tidy/checks/readability-identifier-naming.html
>  in D56563: [clang-tidy]  add options documentation to 
> readability-identifier-naming checker 


Sounds good to me. I see that you've made D57966 
 a child of this issue, but we could swap the 
dependency around so that once your patch is applied I can update this patch to 
use `camelBackOrCase`.


Repository:
  rG LLVM Github Monorepo

CHANGES SINCE LAST ACTION
  https://reviews.llvm.org/D57896/new/

https://reviews.llvm.org/D57896



___
cfe-commits mailing list
cfe-commits@lists.llvm.org
https://lists.llvm.org/cgi-bin/mailman/listinfo/cfe-commits


[PATCH] D57896: Variable names rule

2019-02-18 Thread Michael Platings via Phabricator via cfe-commits
michaelplatings updated this revision to Diff 187252.
michaelplatings added a comment.

Update .clang-tidy files to use aNy_CasE until camelBackOrCase is available.
Add more guidance around acronyms.
Add more guidance around consistency with existing CamelCase variable names.
Change other code examples to camelBack.


Repository:
  rG LLVM Github Monorepo

CHANGES SINCE LAST ACTION
  https://reviews.llvm.org/D57896/new/

https://reviews.llvm.org/D57896

Files:
  .clang-tidy
  clang/.clang-tidy
  llvm/.clang-tidy
  llvm/docs/CodingStandards.rst

Index: llvm/docs/CodingStandards.rst
===
--- llvm/docs/CodingStandards.rst
+++ llvm/docs/CodingStandards.rst
@@ -311,13 +311,13 @@
 
.. code-block:: c++
 
- Object.emitName(nullptr);
+ object.emitName(nullptr);
 
An in-line C-style comment makes the intent obvious:
 
.. code-block:: c++
 
- Object.emitName(/*Prefix=*/nullptr);
+ object.emitName(/*prefix=*/nullptr);
 
 Commenting out large blocks of code is discouraged, but if you really have to do
 this (for documentation purposes or as a suggestion for debug printing), use
@@ -355,8 +355,8 @@
 
 .. code-block:: c++
 
-  /// Sets the xyzzy property to \p Baz.
-  void setXyzzy(bool Baz);
+  /// Sets the xyzzy property to \p baz.
+  void setXyzzy(bool baz);
 
 A documentation comment that uses all Doxygen features in a preferred way:
 
@@ -364,18 +364,18 @@
 
   /// Does foo and bar.
   ///
-  /// Does not do foo the usual way if \p Baz is true.
+  /// Does not do foo the usual way if \p baz is true.
   ///
   /// Typical usage:
   /// \code
-  ///   fooBar(false, "quux", Res);
+  ///   fooBar(false, "quux", res);
   /// \endcode
   ///
-  /// \param Quux kind of foo to do.
+  /// \param quux kind of foo to do.
   /// \param [out] Result filled with bar sequence on foo success.
   ///
   /// \returns true on success.
-  bool fooBar(bool Baz, StringRef Quux, std::vector &Result);
+  bool fooBar(bool baz, StringRef quux, std::vector &result);
 
 Don't duplicate the documentation comment in the header file and in the
 implementation file.  Put the documentation comments for public APIs into the
@@ -568,16 +568,16 @@
 .. code-block:: c++
 
   dyn_switch(V->stripPointerCasts(),
- [] (PHINode *PN) {
+ [] (PHINode *phiNode) {
// process phis...
  },
- [] (SelectInst *SI) {
+ [] (SelectInst *selectInst) {
// process selects...
  },
- [] (LoadInst *LI) {
+ [] (LoadInst *loadInst) {
// process loads...
  },
- [] (AllocaInst *AI) {
+ [] (AllocaInst *allocaInst) {
// process allocas...
  });
 
@@ -603,7 +603,7 @@
 
   foo({a, b, c}, {1, 2, 3});
 
-  llvm::Constant *Mask[] = {
+  llvm::Constant *mask[] = {
   llvm::ConstantInt::get(llvm::Type::getInt32Ty(getLLVMContext()), 0),
   llvm::ConstantInt::get(llvm::Type::getInt32Ty(getLLVMContext()), 1),
   llvm::ConstantInt::get(llvm::Type::getInt32Ty(getLLVMContext()), 2)};
@@ -633,7 +633,7 @@
 
 .. code-block:: c++
 
-  if (V = getValue()) {
+  if (v = getValue()) {
 ...
   }
 
@@ -644,7 +644,7 @@
 
 .. code-block:: c++
 
-  if ((V = getValue())) {
+  if ((v = getValue())) {
 ...
   }
 
@@ -736,7 +736,7 @@
   class Foo;
 
   // Breaks mangling in MSVC.
-  struct Foo { int Data; };
+  struct Foo { int data; };
 
 * As a rule of thumb, ``struct`` should be kept to structures where *all*
   members are declared public.
@@ -746,17 +746,17 @@
   // Foo feels like a class... this is strange.
   struct Foo {
   private:
-int Data;
+int data;
   public:
-Foo() : Data(0) { }
-int getData() const { return Data; }
-void setData(int D) { Data = D; }
+Foo() : data(0) { }
+int getData() const { return data; }
+void setData(int d) { data = d; }
   };
 
   // Bar isn't POD, but it does look like a struct.
   struct Bar {
-int Data;
-Bar() : Data(0) { }
+int data;
+Bar() : data(0) { }
   };
 
 Do not use Braced Initializer Lists to Call a Constructor
@@ -780,7 +780,7 @@
 Foo(std::string filename);
 
 // Construct a Foo by looking up the Nth element of some global data ...
-Foo(int N);
+Foo(int n);
 
 // ...
   };
@@ -789,7 +789,7 @@
   std::fill(foo.begin(), foo.end(), Foo("name"));
 
   // The pair is just being constructed like an aggregate, use braces.
-  bar_map.insert({my_key, my_value});
+  bar_map.insert({myKey, myValue});
 
 If you use a braced initializer list when initializing a variable, use an equals before the open curly brace:
 
@@ -821,15 +821,15 @@
 .. code-block:: c++
 
   // Typically there's no reason to copy.
-  for (const auto &Val : Container) { observe(Val); }
-  for (auto &Val : Container) { Val.change(); }
+  for (const auto &val : container) { observe(val); }
+  for (auto &val : container) { val

[PATCH] D57896: Variable names rule

2019-02-18 Thread Michael Platings via Phabricator via cfe-commits
michaelplatings marked an inline comment as done.
michaelplatings added inline comments.



Comment at: llvm/docs/CodingStandards.rst:1195
+  be camel case, and start with a lower case letter (e.g. ``leader`` or
+  ``boats``). It is also acceptable to use ``UpperCamelCase`` for consistency
+  with existing code.

rupprecht wrote:
> It would be nice for this section to be expanded a bit, just to avoid 
> inevitable code review churn, e.g. if I'm adding 50 lines to a 200 line file, 
> am I allowed to change the existing var names elsewhere in the file or 
> method, or is that outside the scope of my change? If I'm reviewing that 
> patch, do I tell the author they have to be consistent and revert other 
> changes? etc.
> 
> Is there any plan to use clang-tidy to do a global cleanup, or is this going 
> to be a totally ad-hoc migration -- variables use the new scheme only when 
> the code is updated?
I've had a go at expanding it. Please let me know if you have other suggestions.

> Is there any plan to use clang-tidy to do a global cleanup, or is this going 
> to be a totally ad-hoc migration -- variables use the new scheme only when 
> the code is updated?

The latter. Given that the code doesn't keep to the existing .clang-tidy rules 
I'm not optimistic that we could persuade code owners to start now. That's not 
to say it couldn't happen eventually, but my aim at this point in time is to 
make it easier to use good variable names and I don't want perfect to be the 
enemy of better.


Repository:
  rG LLVM Github Monorepo

CHANGES SINCE LAST ACTION
  https://reviews.llvm.org/D57896/new/

https://reviews.llvm.org/D57896



___
cfe-commits mailing list
cfe-commits@lists.llvm.org
https://lists.llvm.org/cgi-bin/mailman/listinfo/cfe-commits


[PATCH] D57896: Variable names rule

2019-02-19 Thread Michael Platings via Phabricator via cfe-commits
michaelplatings updated this revision to Diff 187339.
michaelplatings added a comment.

Changed recommendation for acronyms from lower case to upper case, as suggested 
by several responses to the RFC.


Repository:
  rG LLVM Github Monorepo

CHANGES SINCE LAST ACTION
  https://reviews.llvm.org/D57896/new/

https://reviews.llvm.org/D57896

Files:
  .clang-tidy
  clang/.clang-tidy
  llvm/.clang-tidy
  llvm/docs/CodingStandards.rst

Index: llvm/docs/CodingStandards.rst
===
--- llvm/docs/CodingStandards.rst
+++ llvm/docs/CodingStandards.rst
@@ -311,13 +311,13 @@
 
.. code-block:: c++
 
- Object.emitName(nullptr);
+ object.emitName(nullptr);
 
An in-line C-style comment makes the intent obvious:
 
.. code-block:: c++
 
- Object.emitName(/*Prefix=*/nullptr);
+ object.emitName(/*prefix=*/nullptr);
 
 Commenting out large blocks of code is discouraged, but if you really have to do
 this (for documentation purposes or as a suggestion for debug printing), use
@@ -355,8 +355,8 @@
 
 .. code-block:: c++
 
-  /// Sets the xyzzy property to \p Baz.
-  void setXyzzy(bool Baz);
+  /// Sets the xyzzy property to \p baz.
+  void setXyzzy(bool baz);
 
 A documentation comment that uses all Doxygen features in a preferred way:
 
@@ -364,18 +364,18 @@
 
   /// Does foo and bar.
   ///
-  /// Does not do foo the usual way if \p Baz is true.
+  /// Does not do foo the usual way if \p baz is true.
   ///
   /// Typical usage:
   /// \code
-  ///   fooBar(false, "quux", Res);
+  ///   fooBar(false, "quux", res);
   /// \endcode
   ///
-  /// \param Quux kind of foo to do.
+  /// \param quux kind of foo to do.
   /// \param [out] Result filled with bar sequence on foo success.
   ///
   /// \returns true on success.
-  bool fooBar(bool Baz, StringRef Quux, std::vector &Result);
+  bool fooBar(bool baz, StringRef quux, std::vector &result);
 
 Don't duplicate the documentation comment in the header file and in the
 implementation file.  Put the documentation comments for public APIs into the
@@ -603,7 +603,7 @@
 
   foo({a, b, c}, {1, 2, 3});
 
-  llvm::Constant *Mask[] = {
+  llvm::Constant *mask[] = {
   llvm::ConstantInt::get(llvm::Type::getInt32Ty(getLLVMContext()), 0),
   llvm::ConstantInt::get(llvm::Type::getInt32Ty(getLLVMContext()), 1),
   llvm::ConstantInt::get(llvm::Type::getInt32Ty(getLLVMContext()), 2)};
@@ -633,7 +633,7 @@
 
 .. code-block:: c++
 
-  if (V = getValue()) {
+  if (v = getValue()) {
 ...
   }
 
@@ -644,7 +644,7 @@
 
 .. code-block:: c++
 
-  if ((V = getValue())) {
+  if ((v = getValue())) {
 ...
   }
 
@@ -736,7 +736,7 @@
   class Foo;
 
   // Breaks mangling in MSVC.
-  struct Foo { int Data; };
+  struct Foo { int data; };
 
 * As a rule of thumb, ``struct`` should be kept to structures where *all*
   members are declared public.
@@ -746,17 +746,17 @@
   // Foo feels like a class... this is strange.
   struct Foo {
   private:
-int Data;
+int data;
   public:
-Foo() : Data(0) { }
-int getData() const { return Data; }
-void setData(int D) { Data = D; }
+Foo() : data(0) { }
+int getData() const { return data; }
+void setData(int d) { data = d; }
   };
 
   // Bar isn't POD, but it does look like a struct.
   struct Bar {
-int Data;
-Bar() : Data(0) { }
+int data;
+Bar() : data(0) { }
   };
 
 Do not use Braced Initializer Lists to Call a Constructor
@@ -780,7 +780,7 @@
 Foo(std::string filename);
 
 // Construct a Foo by looking up the Nth element of some global data ...
-Foo(int N);
+Foo(int n);
 
 // ...
   };
@@ -789,7 +789,7 @@
   std::fill(foo.begin(), foo.end(), Foo("name"));
 
   // The pair is just being constructed like an aggregate, use braces.
-  bar_map.insert({my_key, my_value});
+  bar_map.insert({myKey, myValue});
 
 If you use a braced initializer list when initializing a variable, use an equals before the open curly brace:
 
@@ -821,15 +821,15 @@
 .. code-block:: c++
 
   // Typically there's no reason to copy.
-  for (const auto &Val : Container) { observe(Val); }
-  for (auto &Val : Container) { Val.change(); }
+  for (const auto &val : container) { observe(val); }
+  for (auto &val : container) { val.change(); }
 
   // Remove the reference if you really want a new copy.
-  for (auto Val : Container) { Val.change(); saveSomewhere(Val); }
+  for (auto val : container) { val.change(); saveSomewhere(val); }
 
   // Copy pointers, but make it clear that they're pointers.
-  for (const auto *Ptr : Container) { observe(*Ptr); }
-  for (auto *Ptr : Container) { Ptr->change(); }
+  for (const auto *ptr : container) { observe(*ptr); }
+  for (auto *ptr : container) { ptr->change(); }
 
 Beware of non-determinism due to ordering of pointers
 ^
@@ -968,9 +968,9 @@
 
 .. code-block:: c++
 
-  Value *doSomething(Instruction *I) {
-if (!I->isTerminator() &&
-

[PATCH] D57896: Variable names rule

2019-02-19 Thread Michael Platings via Phabricator via cfe-commits
michaelplatings updated this revision to Diff 187344.

Repository:
  rG LLVM Github Monorepo

CHANGES SINCE LAST ACTION
  https://reviews.llvm.org/D57896/new/

https://reviews.llvm.org/D57896

Files:
  .clang-tidy
  clang/.clang-tidy
  llvm/.clang-tidy
  llvm/docs/CodingStandards.rst

Index: llvm/docs/CodingStandards.rst
===
--- llvm/docs/CodingStandards.rst
+++ llvm/docs/CodingStandards.rst
@@ -311,13 +311,13 @@
 
.. code-block:: c++
 
- Object.emitName(nullptr);
+ object.emitName(nullptr);
 
An in-line C-style comment makes the intent obvious:
 
.. code-block:: c++
 
- Object.emitName(/*Prefix=*/nullptr);
+ object.emitName(/*prefix=*/nullptr);
 
 Commenting out large blocks of code is discouraged, but if you really have to do
 this (for documentation purposes or as a suggestion for debug printing), use
@@ -355,8 +355,8 @@
 
 .. code-block:: c++
 
-  /// Sets the xyzzy property to \p Baz.
-  void setXyzzy(bool Baz);
+  /// Sets the xyzzy property to \p baz.
+  void setXyzzy(bool baz);
 
 A documentation comment that uses all Doxygen features in a preferred way:
 
@@ -364,18 +364,18 @@
 
   /// Does foo and bar.
   ///
-  /// Does not do foo the usual way if \p Baz is true.
+  /// Does not do foo the usual way if \p baz is true.
   ///
   /// Typical usage:
   /// \code
-  ///   fooBar(false, "quux", Res);
+  ///   fooBar(false, "quux", res);
   /// \endcode
   ///
-  /// \param Quux kind of foo to do.
+  /// \param quux kind of foo to do.
   /// \param [out] Result filled with bar sequence on foo success.
   ///
   /// \returns true on success.
-  bool fooBar(bool Baz, StringRef Quux, std::vector &Result);
+  bool fooBar(bool baz, StringRef quux, std::vector &result);
 
 Don't duplicate the documentation comment in the header file and in the
 implementation file.  Put the documentation comments for public APIs into the
@@ -603,7 +603,7 @@
 
   foo({a, b, c}, {1, 2, 3});
 
-  llvm::Constant *Mask[] = {
+  llvm::Constant *mask[] = {
   llvm::ConstantInt::get(llvm::Type::getInt32Ty(getLLVMContext()), 0),
   llvm::ConstantInt::get(llvm::Type::getInt32Ty(getLLVMContext()), 1),
   llvm::ConstantInt::get(llvm::Type::getInt32Ty(getLLVMContext()), 2)};
@@ -633,7 +633,7 @@
 
 .. code-block:: c++
 
-  if (V = getValue()) {
+  if (v = getValue()) {
 ...
   }
 
@@ -644,7 +644,7 @@
 
 .. code-block:: c++
 
-  if ((V = getValue())) {
+  if ((v = getValue())) {
 ...
   }
 
@@ -736,7 +736,7 @@
   class Foo;
 
   // Breaks mangling in MSVC.
-  struct Foo { int Data; };
+  struct Foo { int data; };
 
 * As a rule of thumb, ``struct`` should be kept to structures where *all*
   members are declared public.
@@ -746,17 +746,17 @@
   // Foo feels like a class... this is strange.
   struct Foo {
   private:
-int Data;
+int data;
   public:
-Foo() : Data(0) { }
-int getData() const { return Data; }
-void setData(int D) { Data = D; }
+Foo() : data(0) { }
+int getData() const { return data; }
+void setData(int d) { data = d; }
   };
 
   // Bar isn't POD, but it does look like a struct.
   struct Bar {
-int Data;
-Bar() : Data(0) { }
+int data;
+Bar() : data(0) { }
   };
 
 Do not use Braced Initializer Lists to Call a Constructor
@@ -780,7 +780,7 @@
 Foo(std::string filename);
 
 // Construct a Foo by looking up the Nth element of some global data ...
-Foo(int N);
+Foo(int n);
 
 // ...
   };
@@ -789,7 +789,7 @@
   std::fill(foo.begin(), foo.end(), Foo("name"));
 
   // The pair is just being constructed like an aggregate, use braces.
-  bar_map.insert({my_key, my_value});
+  bar_map.insert({myKey, myValue});
 
 If you use a braced initializer list when initializing a variable, use an equals before the open curly brace:
 
@@ -821,15 +821,15 @@
 .. code-block:: c++
 
   // Typically there's no reason to copy.
-  for (const auto &Val : Container) { observe(Val); }
-  for (auto &Val : Container) { Val.change(); }
+  for (const auto &val : container) { observe(val); }
+  for (auto &val : container) { val.change(); }
 
   // Remove the reference if you really want a new copy.
-  for (auto Val : Container) { Val.change(); saveSomewhere(Val); }
+  for (auto val : container) { val.change(); saveSomewhere(val); }
 
   // Copy pointers, but make it clear that they're pointers.
-  for (const auto *Ptr : Container) { observe(*Ptr); }
-  for (auto *Ptr : Container) { Ptr->change(); }
+  for (const auto *ptr : container) { observe(*ptr); }
+  for (auto *ptr : container) { ptr->change(); }
 
 Beware of non-determinism due to ordering of pointers
 ^
@@ -968,9 +968,9 @@
 
 .. code-block:: c++
 
-  Value *doSomething(Instruction *I) {
-if (!I->isTerminator() &&
-I->hasOneUse() && doOtherThing(I)) {
+  Value *doSomething(Instruction *instruction) {
+if (!instruction->isTerminator() &&
+instruction-

[PATCH] D57896: Variable names rule

2019-02-19 Thread Michael Platings via Phabricator via cfe-commits
michaelplatings added a comment.

In D57896#1402194 , @lattner wrote:

> > Changed recommendation for acronyms from lower case to upper case, as 
> > suggested by several responses to the RFC.
>
> I haven't been following the discussion closely - why is this the preferred 
> direction?  I don't think that things like "Basicblock *bb" or "MachineInstr 
> *mi" will be confusing, and going towards a consistently leading lower case 
> letter seems simple and preferable.


Maybe I misunderstood you 
(http://lists.llvm.org/pipermail/llvm-dev/2019-February/130223.html):

>> Maybe there should be an exception that variable names that start with an 
>> acronym still should start with an upper case letter?
>  That would also be fine with me - it could push such a debate down the road, 
> and is definitely important for a transition period anyway.

Also Chandler 
(http://lists.llvm.org/pipermail/llvm-dev/2019-February/130313.html):

> FWIW, I suspect separating the transition of our acronyms from the transition 
> of identifiers with non-acronym words may be an effective way to chip away at 
> the transition cost... Definitely an area that people who really care about 
> this should look at carefully.

And Sanjoy (kind of) 
(http://lists.llvm.org/pipermail/llvm-dev/2019-February/130304.html):

> maybe a gradual transition plan could be to allow these upper case acronyms 
> for specific classes?

I agree that lower case acronyms would ultimately be more consistent, but given 
where we are it seems more achievable to only change the rule for non-acronyms.


Repository:
  rG LLVM Github Monorepo

CHANGES SINCE LAST ACTION
  https://reviews.llvm.org/D57896/new/

https://reviews.llvm.org/D57896



___
cfe-commits mailing list
cfe-commits@lists.llvm.org
https://lists.llvm.org/cgi-bin/mailman/listinfo/cfe-commits


[PATCH] D57335: [IR] Don't assume all functions are 4 byte aligned

2019-02-25 Thread Michael Platings via Phabricator via cfe-commits
michaelplatings updated this revision to Diff 188184.
michaelplatings added a comment.
Herald added subscribers: cfe-commits, jdoerfert, mgorny, dschuff.
Herald added projects: clang, LLVM.

Hi @efriedma, sorry for the delayed response.
I've added the features you asked for to DataLayout.
It is intended that this patch preserves the existing behaviour if no function 
pointer alignment is specified.* Therefore I hope you'll agree that it isn't 
necessary for me to provide code to use the new feature on all platforms.
I did also look into using a target hook but doing so would require modifying a 
//lot// of functions to take a TargetTransformInfo argument. Given that we're 
in agreement that the DataLayout is an appropriate choice, it seemed like the 
best option.

- The exception to this is the case where the Function object doesn't have a 
parent - no alignment is assumed whereas previously 4-byte alignment was 
assumed. Hopefully this case is rare enough that code size won't be 
significantly impacted.


Repository:
  rG LLVM Github Monorepo

CHANGES SINCE LAST ACTION
  https://reviews.llvm.org/D57335/new/

https://reviews.llvm.org/D57335

Files:
  clang/lib/Basic/Targets/ARM.cpp
  clang/test/CodeGen/armv7k-abi.c
  clang/test/CodeGen/target-data.c
  llvm/docs/LangRef.rst
  llvm/include/llvm/IR/ConstantFold.h
  llvm/include/llvm/IR/DataLayout.h
  llvm/lib/IR/ConstantFold.cpp
  llvm/lib/IR/ConstantFold.h
  llvm/lib/IR/Constants.cpp
  llvm/lib/IR/DataLayout.cpp
  llvm/lib/IR/Value.cpp
  llvm/lib/Target/ARM/ARMTargetMachine.cpp
  llvm/unittests/IR/CMakeLists.txt
  llvm/unittests/IR/ConstantFoldTest.cpp
  llvm/unittests/IR/DataLayoutTest.cpp
  llvm/unittests/IR/FunctionTest.cpp

Index: llvm/unittests/IR/FunctionTest.cpp
===
--- llvm/unittests/IR/FunctionTest.cpp
+++ llvm/unittests/IR/FunctionTest.cpp
@@ -129,4 +129,29 @@
   EXPECT_TRUE(F->hasSection());
 }
 
+TEST(FunctionTest, GetPointerAlignment) {
+  LLVMContext Context;
+  Type *VoidType(Type::getVoidTy(Context));
+  FunctionType *FuncType(FunctionType::get(VoidType, false));
+  Function *Func = Function::Create(
+  FuncType, GlobalValue::ExternalLinkage);
+  EXPECT_EQ(0U, Func->getPointerAlignment(DataLayout("")));
+  EXPECT_EQ(1U, Func->getPointerAlignment(DataLayout("Fi8")));
+  EXPECT_EQ(1U, Func->getPointerAlignment(DataLayout("Fn8")));
+  EXPECT_EQ(2U, Func->getPointerAlignment(DataLayout("Fi16")));
+  EXPECT_EQ(2U, Func->getPointerAlignment(DataLayout("Fn16")));
+  EXPECT_EQ(4U, Func->getPointerAlignment(DataLayout("Fi32")));
+  EXPECT_EQ(4U, Func->getPointerAlignment(DataLayout("Fn32")));
+
+  Func->setAlignment(4U);
+
+  EXPECT_EQ(0U, Func->getPointerAlignment(DataLayout("")));
+  EXPECT_EQ(1U, Func->getPointerAlignment(DataLayout("Fi8")));
+  EXPECT_EQ(4U, Func->getPointerAlignment(DataLayout("Fn8")));
+  EXPECT_EQ(2U, Func->getPointerAlignment(DataLayout("Fi16")));
+  EXPECT_EQ(4U, Func->getPointerAlignment(DataLayout("Fn16")));
+  EXPECT_EQ(4U, Func->getPointerAlignment(DataLayout("Fi32")));
+  EXPECT_EQ(4U, Func->getPointerAlignment(DataLayout("Fn32")));
+}
+
 } // end namespace
Index: llvm/unittests/IR/DataLayoutTest.cpp
===
--- /dev/null
+++ llvm/unittests/IR/DataLayoutTest.cpp
@@ -0,0 +1,47 @@
+//===- ConstantRangeTest.cpp - ConstantRange tests ===//
+//
+// 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
+//
+//===--===//
+
+#include "llvm/IR/DataLayout.h"
+#include "gtest/gtest.h"
+
+using namespace llvm;
+
+namespace {
+
+TEST(DataLayoutTest, FunctionPtrAlign) {
+  EXPECT_EQ(0U, DataLayout("").getFunctionPtrAlign());
+  EXPECT_EQ(1U, DataLayout("Fi8").getFunctionPtrAlign());
+  EXPECT_EQ(2U, DataLayout("Fi16").getFunctionPtrAlign());
+  EXPECT_EQ(4U, DataLayout("Fi32").getFunctionPtrAlign());
+  EXPECT_EQ(8U, DataLayout("Fi64").getFunctionPtrAlign());
+  EXPECT_EQ(1U, DataLayout("Fn8").getFunctionPtrAlign());
+  EXPECT_EQ(2U, DataLayout("Fn16").getFunctionPtrAlign());
+  EXPECT_EQ(4U, DataLayout("Fn32").getFunctionPtrAlign());
+  EXPECT_EQ(8U, DataLayout("Fn64").getFunctionPtrAlign());
+  EXPECT_EQ(DataLayout::FunctionPtrAlignType::Independent, \
+  DataLayout("").getFunctionPtrAlignType());
+  EXPECT_EQ(DataLayout::FunctionPtrAlignType::Independent, \
+  DataLayout("Fi8").getFunctionPtrAlignType());
+  EXPECT_EQ(DataLayout::FunctionPtrAlignType::MultipleOfFunctionAlign, \
+  DataLayout("Fn8").getFunctionPtrAlignType());
+  EXPECT_EQ(DataLayout("Fi8"), DataLayout("Fi8"));
+  EXPECT_NE(DataLayout("Fi8"), DataLayout("Fi16"));
+  EXPECT_NE(DataLayout("Fi8"), DataLayout("Fn8"));
+
+  DataLayout a(""), b("Fi8"), c("Fn8");
+  EXPECT_NE(a, b);
+  EXPECT_NE(a, c);

[PATCH] D57335: [IR] Don't assume all functions are 4 byte aligned

2019-02-25 Thread Michael Platings via Phabricator via cfe-commits
michaelplatings marked 4 inline comments as done.
michaelplatings added inline comments.



Comment at: llvm/lib/IR/ConstantFold.cpp:1087
+  if (GVAlign == 0U && isa(GV))
+GVAlign = 4U;
 

efriedma wrote:
> Using "4" as a default is dangerous; on x86, the alignment of the pointer 
> corresponds to the alignment of the function, but might be less than 4 if it 
> isn't explicitly specified.
I've put in a comment to say as much. Sadly I'm not in a position to change 
this behaviour without causing a code size regression.


Repository:
  rG LLVM Github Monorepo

CHANGES SINCE LAST ACTION
  https://reviews.llvm.org/D57335/new/

https://reviews.llvm.org/D57335



___
cfe-commits mailing list
cfe-commits@lists.llvm.org
https://lists.llvm.org/cgi-bin/mailman/listinfo/cfe-commits


[PATCH] D64123: Add clang-llvm-rename tool.

2019-07-05 Thread Michael Platings via Phabricator via cfe-commits
michaelplatings added a comment.

Hi @ruiu,
Can you comment on how this compares to clang-tidy? I had assumed that the 
readability-identifier-naming clang-tidy rule would largely do the trick.


Repository:
  rG LLVM Github Monorepo

CHANGES SINCE LAST ACTION
  https://reviews.llvm.org/D64123/new/

https://reviews.llvm.org/D64123



___
cfe-commits mailing list
cfe-commits@lists.llvm.org
https://lists.llvm.org/cgi-bin/mailman/listinfo/cfe-commits


[PATCH] D71991: Fix external-names.c test when separator is \\

2019-12-30 Thread Michael Platings via Phabricator via cfe-commits
michaelplatings created this revision.
michaelplatings added reviewers: rnk, amccarth, dsanders, miyuki.
Herald added a project: clang.
Herald added a subscriber: cfe-commits.
michaelplatings edited the summary of this revision.

This fixes the following failure:

  C:\[...]\llvm\tools\clang\test\VFS\external-names.c:34:26: error: 
CHECK-DEBUG-EXTERNAL: expected string not found in input
  // CHECK-DEBUG-EXTERNAL: ![[Num]] = !DIFile(filename: 
"{{[^"]*}}Inputs{{.}}external-names.h"
   ^
  [...]
  :42:54: note: possible intended match here
  !10 = !DIFile(filename: 
"C:/[...]\\llvm\\tools\\clang\\test\\VFS\\Inputs\\external-names.h", directory: 
"")


Repository:
  rG LLVM Github Monorepo

https://reviews.llvm.org/D71991

Files:
  clang/test/VFS/external-names.c


Index: clang/test/VFS/external-names.c
===
--- clang/test/VFS/external-names.c
+++ clang/test/VFS/external-names.c
@@ -21,7 +21,7 @@
 // Diagnostics:
 
 // RUN: %clang_cc1 -I %t -ivfsoverlay %t.external.yaml -fsyntax-only %s 2>&1 | 
FileCheck -check-prefix=CHECK-DIAG-EXTERNAL %s
-// CHECK-DIAG-EXTERNAL: {{.*}}Inputs{{.}}external-names.h:{{[0-9]*:[0-9]*}}: 
warning: incompatible pointer
+// CHECK-DIAG-EXTERNAL: {{.*}}Inputs{{..?}}external-names.h:{{[0-9]*:[0-9]*}}: 
warning: incompatible pointer
 
 // RUN: %clang_cc1 -I %t -ivfsoverlay %t.yaml -fsyntax-only %s 2>&1 | 
FileCheck -check-prefix=CHECK-DIAG %s
 // CHECK-DIAG-NOT: Inputs
@@ -31,7 +31,7 @@
 
 // RUN: %clang_cc1 -I %t -ivfsoverlay %t.external.yaml -triple 
%itanium_abi_triple -debug-info-kind=limited -emit-llvm %s -o - | FileCheck 
-check-prefix=CHECK-DEBUG-EXTERNAL %s
 // CHECK-DEBUG-EXTERNAL: !DISubprogram({{.*}}file: ![[Num:[0-9]+]]
-// CHECK-DEBUG-EXTERNAL: ![[Num]] = !DIFile(filename: 
"{{[^"]*}}Inputs{{.}}external-names.h"
+// CHECK-DEBUG-EXTERNAL: ![[Num]] = !DIFile(filename: 
"{{[^"]*}}Inputs{{..?}}external-names.h"
 
 // RUN: %clang_cc1 -I %t -ivfsoverlay %t.yaml -triple %itanium_abi_triple 
-debug-info-kind=limited -emit-llvm %s -o - | FileCheck 
-check-prefix=CHECK-DEBUG %s
 // CHECK-DEBUG-NOT: Inputs
@@ -42,7 +42,7 @@
 // RUN: %clang_cc1 -D REINCLUDE -I %t -ivfsoverlay %t.external.yaml -Eonly %s 
-MTfoo -dependency-file %t.external.dep
 // RUN: echo "EOF" >> %t.external.dep
 // RUN: cat %t.external.dep | FileCheck --check-prefix=CHECK-DEP-EXTERNAL %s
-// CHECK-DEP-EXTERNAL: Inputs{{.}}external-names.h
+// CHECK-DEP-EXTERNAL: Inputs{{..?}}external-names.h
 // CHECK-DEP-EXTERNAL-NEXT: EOF
 
 // RUN: %clang_cc1 -D REINCLUDE -I %t -ivfsoverlay %t.yaml -Eonly %s -MTfoo 
-dependency-file %t.dep


Index: clang/test/VFS/external-names.c
===
--- clang/test/VFS/external-names.c
+++ clang/test/VFS/external-names.c
@@ -21,7 +21,7 @@
 // Diagnostics:
 
 // RUN: %clang_cc1 -I %t -ivfsoverlay %t.external.yaml -fsyntax-only %s 2>&1 | FileCheck -check-prefix=CHECK-DIAG-EXTERNAL %s
-// CHECK-DIAG-EXTERNAL: {{.*}}Inputs{{.}}external-names.h:{{[0-9]*:[0-9]*}}: warning: incompatible pointer
+// CHECK-DIAG-EXTERNAL: {{.*}}Inputs{{..?}}external-names.h:{{[0-9]*:[0-9]*}}: warning: incompatible pointer
 
 // RUN: %clang_cc1 -I %t -ivfsoverlay %t.yaml -fsyntax-only %s 2>&1 | FileCheck -check-prefix=CHECK-DIAG %s
 // CHECK-DIAG-NOT: Inputs
@@ -31,7 +31,7 @@
 
 // RUN: %clang_cc1 -I %t -ivfsoverlay %t.external.yaml -triple %itanium_abi_triple -debug-info-kind=limited -emit-llvm %s -o - | FileCheck -check-prefix=CHECK-DEBUG-EXTERNAL %s
 // CHECK-DEBUG-EXTERNAL: !DISubprogram({{.*}}file: ![[Num:[0-9]+]]
-// CHECK-DEBUG-EXTERNAL: ![[Num]] = !DIFile(filename: "{{[^"]*}}Inputs{{.}}external-names.h"
+// CHECK-DEBUG-EXTERNAL: ![[Num]] = !DIFile(filename: "{{[^"]*}}Inputs{{..?}}external-names.h"
 
 // RUN: %clang_cc1 -I %t -ivfsoverlay %t.yaml -triple %itanium_abi_triple -debug-info-kind=limited -emit-llvm %s -o - | FileCheck -check-prefix=CHECK-DEBUG %s
 // CHECK-DEBUG-NOT: Inputs
@@ -42,7 +42,7 @@
 // RUN: %clang_cc1 -D REINCLUDE -I %t -ivfsoverlay %t.external.yaml -Eonly %s -MTfoo -dependency-file %t.external.dep
 // RUN: echo "EOF" >> %t.external.dep
 // RUN: cat %t.external.dep | FileCheck --check-prefix=CHECK-DEP-EXTERNAL %s
-// CHECK-DEP-EXTERNAL: Inputs{{.}}external-names.h
+// CHECK-DEP-EXTERNAL: Inputs{{..?}}external-names.h
 // CHECK-DEP-EXTERNAL-NEXT: EOF
 
 // RUN: %clang_cc1 -D REINCLUDE -I %t -ivfsoverlay %t.yaml -Eonly %s -MTfoo -dependency-file %t.dep
___
cfe-commits mailing list
cfe-commits@lists.llvm.org
https://lists.llvm.org/cgi-bin/mailman/listinfo/cfe-commits


[PATCH] D71991: Fix external-names.c test when separator is \\

2019-12-31 Thread Michael Platings via Phabricator via cfe-commits
michaelplatings added a comment.

Thanks for accepting.
The repo is up to date. I guess the reason the failure hasn't happened with the 
build bots is that our downstream test setup differs somewhat from the norm - 
our test runner imports lit.discovery & lit.LitConfig directly rather than 
using the command line interface. I've had a hunt for what the exact difference 
might be but haven't been able to find it.


Repository:
  rG LLVM Github Monorepo

CHANGES SINCE LAST ACTION
  https://reviews.llvm.org/D71991/new/

https://reviews.llvm.org/D71991



___
cfe-commits mailing list
cfe-commits@lists.llvm.org
https://lists.llvm.org/cgi-bin/mailman/listinfo/cfe-commits


[PATCH] D71991: Fix external-names.c test when separator is \\

2019-12-31 Thread Michael Platings via Phabricator via cfe-commits
This revision was automatically updated to reflect the committed changes.
Closed by commit rG0c7ca82161b5: Fix external-names.c test when separator is \\ 
(authored by michaelplatings).

Repository:
  rG LLVM Github Monorepo

CHANGES SINCE LAST ACTION
  https://reviews.llvm.org/D71991/new/

https://reviews.llvm.org/D71991

Files:
  clang/test/VFS/external-names.c


Index: clang/test/VFS/external-names.c
===
--- clang/test/VFS/external-names.c
+++ clang/test/VFS/external-names.c
@@ -21,7 +21,7 @@
 // Diagnostics:
 
 // RUN: %clang_cc1 -I %t -ivfsoverlay %t.external.yaml -fsyntax-only %s 2>&1 | 
FileCheck -check-prefix=CHECK-DIAG-EXTERNAL %s
-// CHECK-DIAG-EXTERNAL: {{.*}}Inputs{{.}}external-names.h:{{[0-9]*:[0-9]*}}: 
warning: incompatible pointer
+// CHECK-DIAG-EXTERNAL: {{.*}}Inputs{{..?}}external-names.h:{{[0-9]*:[0-9]*}}: 
warning: incompatible pointer
 
 // RUN: %clang_cc1 -I %t -ivfsoverlay %t.yaml -fsyntax-only %s 2>&1 | 
FileCheck -check-prefix=CHECK-DIAG %s
 // CHECK-DIAG-NOT: Inputs
@@ -31,7 +31,7 @@
 
 // RUN: %clang_cc1 -I %t -ivfsoverlay %t.external.yaml -triple 
%itanium_abi_triple -debug-info-kind=limited -emit-llvm %s -o - | FileCheck 
-check-prefix=CHECK-DEBUG-EXTERNAL %s
 // CHECK-DEBUG-EXTERNAL: !DISubprogram({{.*}}file: ![[Num:[0-9]+]]
-// CHECK-DEBUG-EXTERNAL: ![[Num]] = !DIFile(filename: 
"{{[^"]*}}Inputs{{.}}external-names.h"
+// CHECK-DEBUG-EXTERNAL: ![[Num]] = !DIFile(filename: 
"{{[^"]*}}Inputs{{..?}}external-names.h"
 
 // RUN: %clang_cc1 -I %t -ivfsoverlay %t.yaml -triple %itanium_abi_triple 
-debug-info-kind=limited -emit-llvm %s -o - | FileCheck 
-check-prefix=CHECK-DEBUG %s
 // CHECK-DEBUG-NOT: Inputs
@@ -42,7 +42,7 @@
 // RUN: %clang_cc1 -D REINCLUDE -I %t -ivfsoverlay %t.external.yaml -Eonly %s 
-MTfoo -dependency-file %t.external.dep
 // RUN: echo "EOF" >> %t.external.dep
 // RUN: cat %t.external.dep | FileCheck --check-prefix=CHECK-DEP-EXTERNAL %s
-// CHECK-DEP-EXTERNAL: Inputs{{.}}external-names.h
+// CHECK-DEP-EXTERNAL: Inputs{{..?}}external-names.h
 // CHECK-DEP-EXTERNAL-NEXT: EOF
 
 // RUN: %clang_cc1 -D REINCLUDE -I %t -ivfsoverlay %t.yaml -Eonly %s -MTfoo 
-dependency-file %t.dep


Index: clang/test/VFS/external-names.c
===
--- clang/test/VFS/external-names.c
+++ clang/test/VFS/external-names.c
@@ -21,7 +21,7 @@
 // Diagnostics:
 
 // RUN: %clang_cc1 -I %t -ivfsoverlay %t.external.yaml -fsyntax-only %s 2>&1 | FileCheck -check-prefix=CHECK-DIAG-EXTERNAL %s
-// CHECK-DIAG-EXTERNAL: {{.*}}Inputs{{.}}external-names.h:{{[0-9]*:[0-9]*}}: warning: incompatible pointer
+// CHECK-DIAG-EXTERNAL: {{.*}}Inputs{{..?}}external-names.h:{{[0-9]*:[0-9]*}}: warning: incompatible pointer
 
 // RUN: %clang_cc1 -I %t -ivfsoverlay %t.yaml -fsyntax-only %s 2>&1 | FileCheck -check-prefix=CHECK-DIAG %s
 // CHECK-DIAG-NOT: Inputs
@@ -31,7 +31,7 @@
 
 // RUN: %clang_cc1 -I %t -ivfsoverlay %t.external.yaml -triple %itanium_abi_triple -debug-info-kind=limited -emit-llvm %s -o - | FileCheck -check-prefix=CHECK-DEBUG-EXTERNAL %s
 // CHECK-DEBUG-EXTERNAL: !DISubprogram({{.*}}file: ![[Num:[0-9]+]]
-// CHECK-DEBUG-EXTERNAL: ![[Num]] = !DIFile(filename: "{{[^"]*}}Inputs{{.}}external-names.h"
+// CHECK-DEBUG-EXTERNAL: ![[Num]] = !DIFile(filename: "{{[^"]*}}Inputs{{..?}}external-names.h"
 
 // RUN: %clang_cc1 -I %t -ivfsoverlay %t.yaml -triple %itanium_abi_triple -debug-info-kind=limited -emit-llvm %s -o - | FileCheck -check-prefix=CHECK-DEBUG %s
 // CHECK-DEBUG-NOT: Inputs
@@ -42,7 +42,7 @@
 // RUN: %clang_cc1 -D REINCLUDE -I %t -ivfsoverlay %t.external.yaml -Eonly %s -MTfoo -dependency-file %t.external.dep
 // RUN: echo "EOF" >> %t.external.dep
 // RUN: cat %t.external.dep | FileCheck --check-prefix=CHECK-DEP-EXTERNAL %s
-// CHECK-DEP-EXTERNAL: Inputs{{.}}external-names.h
+// CHECK-DEP-EXTERNAL: Inputs{{..?}}external-names.h
 // CHECK-DEP-EXTERNAL-NEXT: EOF
 
 // RUN: %clang_cc1 -D REINCLUDE -I %t -ivfsoverlay %t.yaml -Eonly %s -MTfoo -dependency-file %t.dep
___
cfe-commits mailing list
cfe-commits@lists.llvm.org
https://lists.llvm.org/cgi-bin/mailman/listinfo/cfe-commits


[PATCH] D134824: Fix frint ACLE intrinsic names

2022-09-28 Thread Michael Platings via Phabricator via cfe-commits
michaelplatings created this revision.
michaelplatings added a reviewer: jaykang10.
Herald added a project: All.
michaelplatings requested review of this revision.
Herald added a project: clang.
Herald added a subscriber: cfe-commits.

Although the instruction names begin "frint", the ACLE spec states that the 
intrinsic names begin "__rint", without the "f".


Repository:
  rG LLVM Github Monorepo

https://reviews.llvm.org/D134824

Files:
  clang/include/clang/Basic/BuiltinsAArch64.def
  clang/lib/CodeGen/CGBuiltin.cpp
  clang/lib/Headers/arm_acle.h
  clang/test/CodeGen/aarch64-v8.5a-scalar-frint3264-intrinsic.c

Index: clang/test/CodeGen/aarch64-v8.5a-scalar-frint3264-intrinsic.c
===
--- clang/test/CodeGen/aarch64-v8.5a-scalar-frint3264-intrinsic.c
+++ clang/test/CodeGen/aarch64-v8.5a-scalar-frint3264-intrinsic.c
@@ -7,58 +7,58 @@
 
 #include 
 
-// CHECK-LABEL: test_frint32zf
+// CHECK-LABEL: test_rint32zf
 // CHECK:  [[RND:%.*]] =  call float @llvm.aarch64.frint32z.f32(float %a)
 // CHECK:  ret float [[RND]]
-float test_frint32zf(float a) {
-  return __frint32zf(a);
+float test_rint32zf(float a) {
+  return __rint32zf(a);
 }
 
-// CHECK-LABEL: test_frint32z
+// CHECK-LABEL: test_rint32z
 // CHECK:  [[RND:%.*]] =  call double @llvm.aarch64.frint32z.f64(double %a)
 // CHECK:  ret double [[RND]]
-double test_frint32z(double a) {
-  return __frint32z(a);
+double test_rint32z(double a) {
+  return __rint32z(a);
 }
 
-// CHECK-LABEL: test_frint64zf
+// CHECK-LABEL: test_rint64zf
 // CHECK:  [[RND:%.*]] =  call float @llvm.aarch64.frint64z.f32(float %a)
 // CHECK:  ret float [[RND]]
-float test_frint64zf(float a) {
-  return __frint64zf(a);
+float test_rint64zf(float a) {
+  return __rint64zf(a);
 }
 
-// CHECK-LABEL: test_frint64z
+// CHECK-LABEL: test_rint64z
 // CHECK:  [[RND:%.*]] =  call double @llvm.aarch64.frint64z.f64(double %a)
 // CHECK:  ret double [[RND]]
-double test_frint64z(double a) {
-  return __frint64z(a);
+double test_rint64z(double a) {
+  return __rint64z(a);
 }
 
-// CHECK-LABEL: test_frint32xf
+// CHECK-LABEL: test_rint32xf
 // CHECK:  [[RND:%.*]] =  call float @llvm.aarch64.frint32x.f32(float %a)
 // CHECK:  ret float [[RND]]
-float test_frint32xf(float a) {
-  return __frint32xf(a);
+float test_rint32xf(float a) {
+  return __rint32xf(a);
 }
 
-// CHECK-LABEL: test_frint32x
+// CHECK-LABEL: test_rint32x
 // CHECK:  [[RND:%.*]] =  call double @llvm.aarch64.frint32x.f64(double %a)
 // CHECK:  ret double [[RND]]
-double test_frint32x(double a) {
-  return __frint32x(a);
+double test_rint32x(double a) {
+  return __rint32x(a);
 }
 
-// CHECK-LABEL: test_frint64xf
+// CHECK-LABEL: test_rint64xf
 // CHECK:  [[RND:%.*]] =  call float @llvm.aarch64.frint64x.f32(float %a)
 // CHECK:  ret float [[RND]]
-float test_frint64xf(float a) {
-  return __frint64xf(a);
+float test_rint64xf(float a) {
+  return __rint64xf(a);
 }
 
-// CHECK-LABEL: test_frint64x
+// CHECK-LABEL: test_rint64x
 // CHECK:  [[RND:%.*]] =  call double @llvm.aarch64.frint64x.f64(double %a)
 // CHECK:  ret double [[RND]]
-double test_frint64x(double a) {
-  return __frint64x(a);
+double test_rint64x(double a) {
+  return __rint64x(a);
 }
Index: clang/lib/Headers/arm_acle.h
===
--- clang/lib/Headers/arm_acle.h
+++ clang/lib/Headers/arm_acle.h
@@ -642,43 +642,43 @@
 /* Armv8.5-A FP rounding intrinsics */
 #if defined(__ARM_64BIT_STATE) && __ARM_64BIT_STATE && defined(__ARM_FEATURE_FRINT)
 static __inline__ float __attribute__((__always_inline__, __nodebug__))
-__frint32zf(float __a) {
-  return __builtin_arm_frint32zf(__a);
+__rint32zf(float __a) {
+  return __builtin_arm_rint32zf(__a);
 }
 
 static __inline__ double __attribute__((__always_inline__, __nodebug__))
-__frint32z(double __a) {
-  return __builtin_arm_frint32z(__a);
+__rint32z(double __a) {
+  return __builtin_arm_rint32z(__a);
 }
 
 static __inline__ float __attribute__((__always_inline__, __nodebug__))
-__frint64zf(float __a) {
-  return __builtin_arm_frint64zf(__a);
+__rint64zf(float __a) {
+  return __builtin_arm_rint64zf(__a);
 }
 
 static __inline__ double __attribute__((__always_inline__, __nodebug__))
-__frint64z(double __a) {
-  return __builtin_arm_frint64z(__a);
+__rint64z(double __a) {
+  return __builtin_arm_rint64z(__a);
 }
 
 static __inline__ float __attribute__((__always_inline__, __nodebug__))
-__frint32xf(float __a) {
-  return __builtin_arm_frint32xf(__a);
+__rint32xf(float __a) {
+  return __builtin_arm_rint32xf(__a);
 }
 
 static __inline__ double __attribute__((__always_inline__, __nodebug__))
-__frint32x(double __a) {
-  return __builtin_arm_frint32x(__a);
+__rint32x(double __a) {
+  return __builtin_arm_rint32x(__a);
 }
 
 static __inline__ float __attribute__((__always_inline__, __nodebug__))
-__frint64xf(float __a) {
-  return __builtin_arm_frint64xf(__a);
+__rint64xf(float __a) {
+  return __builtin_arm_rint64xf(__

[PATCH] D134824: Fix frint ACLE intrinsic names

2022-09-29 Thread Michael Platings via Phabricator via cfe-commits
This revision was landed with ongoing or failed builds.
This revision was automatically updated to reflect the committed changes.
Closed by commit rGdba8fced969e: Fix frint ACLE intrinsic names (authored by 
michaelplatings).

Repository:
  rG LLVM Github Monorepo

CHANGES SINCE LAST ACTION
  https://reviews.llvm.org/D134824/new/

https://reviews.llvm.org/D134824

Files:
  clang/include/clang/Basic/BuiltinsAArch64.def
  clang/lib/CodeGen/CGBuiltin.cpp
  clang/lib/Headers/arm_acle.h
  clang/test/CodeGen/aarch64-v8.5a-scalar-frint3264-intrinsic.c

Index: clang/test/CodeGen/aarch64-v8.5a-scalar-frint3264-intrinsic.c
===
--- clang/test/CodeGen/aarch64-v8.5a-scalar-frint3264-intrinsic.c
+++ clang/test/CodeGen/aarch64-v8.5a-scalar-frint3264-intrinsic.c
@@ -7,58 +7,58 @@
 
 #include 
 
-// CHECK-LABEL: test_frint32zf
+// CHECK-LABEL: test_rint32zf
 // CHECK:  [[RND:%.*]] =  call float @llvm.aarch64.frint32z.f32(float %a)
 // CHECK:  ret float [[RND]]
-float test_frint32zf(float a) {
-  return __frint32zf(a);
+float test_rint32zf(float a) {
+  return __rint32zf(a);
 }
 
-// CHECK-LABEL: test_frint32z
+// CHECK-LABEL: test_rint32z
 // CHECK:  [[RND:%.*]] =  call double @llvm.aarch64.frint32z.f64(double %a)
 // CHECK:  ret double [[RND]]
-double test_frint32z(double a) {
-  return __frint32z(a);
+double test_rint32z(double a) {
+  return __rint32z(a);
 }
 
-// CHECK-LABEL: test_frint64zf
+// CHECK-LABEL: test_rint64zf
 // CHECK:  [[RND:%.*]] =  call float @llvm.aarch64.frint64z.f32(float %a)
 // CHECK:  ret float [[RND]]
-float test_frint64zf(float a) {
-  return __frint64zf(a);
+float test_rint64zf(float a) {
+  return __rint64zf(a);
 }
 
-// CHECK-LABEL: test_frint64z
+// CHECK-LABEL: test_rint64z
 // CHECK:  [[RND:%.*]] =  call double @llvm.aarch64.frint64z.f64(double %a)
 // CHECK:  ret double [[RND]]
-double test_frint64z(double a) {
-  return __frint64z(a);
+double test_rint64z(double a) {
+  return __rint64z(a);
 }
 
-// CHECK-LABEL: test_frint32xf
+// CHECK-LABEL: test_rint32xf
 // CHECK:  [[RND:%.*]] =  call float @llvm.aarch64.frint32x.f32(float %a)
 // CHECK:  ret float [[RND]]
-float test_frint32xf(float a) {
-  return __frint32xf(a);
+float test_rint32xf(float a) {
+  return __rint32xf(a);
 }
 
-// CHECK-LABEL: test_frint32x
+// CHECK-LABEL: test_rint32x
 // CHECK:  [[RND:%.*]] =  call double @llvm.aarch64.frint32x.f64(double %a)
 // CHECK:  ret double [[RND]]
-double test_frint32x(double a) {
-  return __frint32x(a);
+double test_rint32x(double a) {
+  return __rint32x(a);
 }
 
-// CHECK-LABEL: test_frint64xf
+// CHECK-LABEL: test_rint64xf
 // CHECK:  [[RND:%.*]] =  call float @llvm.aarch64.frint64x.f32(float %a)
 // CHECK:  ret float [[RND]]
-float test_frint64xf(float a) {
-  return __frint64xf(a);
+float test_rint64xf(float a) {
+  return __rint64xf(a);
 }
 
-// CHECK-LABEL: test_frint64x
+// CHECK-LABEL: test_rint64x
 // CHECK:  [[RND:%.*]] =  call double @llvm.aarch64.frint64x.f64(double %a)
 // CHECK:  ret double [[RND]]
-double test_frint64x(double a) {
-  return __frint64x(a);
+double test_rint64x(double a) {
+  return __rint64x(a);
 }
Index: clang/lib/Headers/arm_acle.h
===
--- clang/lib/Headers/arm_acle.h
+++ clang/lib/Headers/arm_acle.h
@@ -642,43 +642,43 @@
 /* Armv8.5-A FP rounding intrinsics */
 #if defined(__ARM_64BIT_STATE) && __ARM_64BIT_STATE && defined(__ARM_FEATURE_FRINT)
 static __inline__ float __attribute__((__always_inline__, __nodebug__))
-__frint32zf(float __a) {
-  return __builtin_arm_frint32zf(__a);
+__rint32zf(float __a) {
+  return __builtin_arm_rint32zf(__a);
 }
 
 static __inline__ double __attribute__((__always_inline__, __nodebug__))
-__frint32z(double __a) {
-  return __builtin_arm_frint32z(__a);
+__rint32z(double __a) {
+  return __builtin_arm_rint32z(__a);
 }
 
 static __inline__ float __attribute__((__always_inline__, __nodebug__))
-__frint64zf(float __a) {
-  return __builtin_arm_frint64zf(__a);
+__rint64zf(float __a) {
+  return __builtin_arm_rint64zf(__a);
 }
 
 static __inline__ double __attribute__((__always_inline__, __nodebug__))
-__frint64z(double __a) {
-  return __builtin_arm_frint64z(__a);
+__rint64z(double __a) {
+  return __builtin_arm_rint64z(__a);
 }
 
 static __inline__ float __attribute__((__always_inline__, __nodebug__))
-__frint32xf(float __a) {
-  return __builtin_arm_frint32xf(__a);
+__rint32xf(float __a) {
+  return __builtin_arm_rint32xf(__a);
 }
 
 static __inline__ double __attribute__((__always_inline__, __nodebug__))
-__frint32x(double __a) {
-  return __builtin_arm_frint32x(__a);
+__rint32x(double __a) {
+  return __builtin_arm_rint32x(__a);
 }
 
 static __inline__ float __attribute__((__always_inline__, __nodebug__))
-__frint64xf(float __a) {
-  return __builtin_arm_frint64xf(__a);
+__rint64xf(float __a) {
+  return __builtin_arm_rint64xf(__a);
 }
 
 static __inline__ double __attribute__((__always_inline__, _

[PATCH] D140959: RFC: Multilib prototype

2023-01-04 Thread Michael Platings via Phabricator via cfe-commits
michaelplatings created this revision.
michaelplatings added a project: clang.
Herald added subscribers: s.egerton, ormris, abidh, mgrang, simoncook, 
kristof.beyls.
Herald added a project: All.
michaelplatings requested review of this revision.
Herald added subscribers: cfe-commits, MaskRay.

This is a prototype of a new approach to multilib.

The `multilib.yaml` file is a new interface that allows customising (a) which 
system library variants are available; and (b) how a library variant is 
identified as compatible with the clang arguments provided by the user.

The file 
clang/test/Driver/Inputs/baremetal_multilib/arm-none-eabi/multilib.yaml is an 
example that contains comments explaining how it is used.

The project I'm working on is LLVM Embedded Toolchain for Arm 
 so the design 
is made with that in mind, but it's intended to be flexible enough to work with 
other toolchains with many system library variants.


Repository:
  rG LLVM Github Monorepo

https://reviews.llvm.org/D140959

Files:
  clang/include/clang/Driver/Multilib2.h
  clang/lib/Driver/CMakeLists.txt
  clang/lib/Driver/Multilib2.cpp
  clang/lib/Driver/ToolChains/BareMetal.cpp
  clang/test/Driver/Inputs/baremetal_multilib/arm-none-eabi/multilib.yaml
  clang/test/Driver/arm-compiler-rt.c
  clang/test/Driver/baremetal-multilib.cpp
  clang/test/Driver/baremetal.cpp
  clang/test/Driver/print-libgcc-file-name-clangrt.c
  clang/unittests/Driver/CMakeLists.txt
  clang/unittests/Driver/Multilib2Test.cpp

Index: clang/unittests/Driver/Multilib2Test.cpp
===
--- /dev/null
+++ clang/unittests/Driver/Multilib2Test.cpp
@@ -0,0 +1,281 @@
+//===- unittests/Driver/Multilib2Test.cpp --- Multilib2 tests ---===//
+//
+// 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
+//
+//===--===//
+
+#include "clang/Driver/Multilib2.h"
+#include "llvm/ADT/ArrayRef.h"
+#include "gtest/gtest.h"
+
+using namespace clang::driver;
+using namespace clang;
+
+TEST(Multilib2Test, Parse) {
+  std::string O;
+  llvm::raw_string_ostream OS(O);
+
+  Multilib2 M;
+  EXPECT_FALSE(M.parse(R"(
+variants:
+- path: /abc
+)", OS));
+  EXPECT_TRUE(StringRef(O).contains("paths must be relative")) << O;
+
+  EXPECT_TRUE(M.parse(R"(
+variants:
+- path: .
+)", OS));
+  EXPECT_EQ(1U, M.size());
+  EXPECT_EQ("", std::get<0>(*M.begin()));
+
+  EXPECT_TRUE(M.parse(R"(
+variants:
+- path: abc
+)", OS));
+  EXPECT_EQ(1U, M.size());
+  EXPECT_EQ("/abc", std::get<0>(*M.begin()));
+
+  EXPECT_TRUE(M.parse(R"(
+variants:
+- path: pqr
+  args: [-mfloat-abi=soft]
+)", OS));
+  EXPECT_EQ(1U, M.size());
+  EXPECT_EQ("/pqr", std::get<0>(*M.begin()));
+  EXPECT_EQ(std::vector({"-mfloat-abi=soft"}), std::get<1>(*M.begin()));
+
+  EXPECT_TRUE(M.parse(R"(
+variants:
+- path: pqr
+  args: [-mfloat-abi=soft, -fno-exceptions]
+)", OS));
+  EXPECT_EQ(1U, M.size());
+  EXPECT_EQ(std::vector({"-mfloat-abi=soft", "-fno-exceptions"}), std::get<1>(*M.begin()));
+
+  EXPECT_TRUE(M.parse(R"(
+variants:
+- path: a
+- path: b
+)", OS));
+  EXPECT_EQ(2U, M.size());
+}
+
+TEST(Multilib2Test, SelectSoft) {
+  std::string O;
+  llvm::raw_string_ostream OS(O);
+  Multilib2 M;
+  ASSERT_TRUE(M.parse(R"(
+variants:
+- path: s
+  attrs: [softabi]
+arguments:
+- regex: -mfloat-abi soft
+  matchAttrs: [softabi]
+- regex: -mfloat-abi hard
+  matchAttrs: [hardabi]
+- regex: -msoft-float
+  noMatchAttrs: [hasfp]
+)", OS));
+  EXPECT_TRUE(M.select({"--target=arm-none-eabi"}).first);
+  EXPECT_TRUE(M.select({"--target=arm-none-eabi", "-mfloat-abi=soft"}).first);
+  EXPECT_TRUE(M.select({"--target=arm-none-eabi", "-mfloat-abi=softfp"}).first);
+  EXPECT_FALSE(M.select({"--target=arm-none-eabi", "-mfloat-abi=hard"}).first);
+  EXPECT_FALSE(M.select({"--target=arm-none-eabihf"}).first);
+}
+
+TEST(Multilib2Test, SelectSoftFP) {
+  std::string O;
+  llvm::raw_string_ostream OS(O);
+  Multilib2 M;
+  ASSERT_TRUE(M.parse(R"(
+variants:
+- path: f
+  attrs: [softabi, hasfp]
+arguments:
+- regex: -mfloat-abi soft
+  matchAttrs: [softabi]
+- regex: -mfloat-abi hard
+  matchAttrs: [hardabi]
+- regex: -msoft-float
+  noMatchAttrs: [hasfp]
+)", OS));
+  EXPECT_FALSE(M.select({"--target=arm-none-eabi", "-mfloat-abi=soft"}).first);
+  EXPECT_TRUE(M.select({"--target=arm-none-eabi", "-mfloat-abi=softfp"}).first);
+  EXPECT_FALSE(M.select({"--target=arm-none-eabi", "-mfloat-abi=hard"}).first);
+  EXPECT_FALSE(M.select({"--target=arm-none-eabihf"}).first);
+}
+
+TEST(Multilib2Test, SelectHard) {
+  // If hard float is all that's available then select that only if compiling with hard float.
+  std::string O;
+  llvm::raw_string_ostream OS(O);
+  Multilib2 M;
+  ASSERT_TRUE(M.parse(R"(
+variants:
+- p

[PATCH] D140959: RFC: Multilib prototype

2023-01-05 Thread Michael Platings via Phabricator via cfe-commits
michaelplatings added inline comments.



Comment at: clang/include/clang/Driver/Multilib2.h:33-34
+private:
+  std::vector, 
std::vector>> Multilibs;
+  std::vector, 
std::vector>> RegexAttributes;
+};

phosek wrote:
> I think it'd really help readability and comprehension if this was modeled 
> using types (that is `struct`s and `class`es). It's not at all clear what 
> these strings are supposed to represent, and seeing expressions like 
> `std::get<0>` doesn't help either.
I fully agree. Sorry if I wasn't clear in the RFC but this is the kind of thing 
I meant when I said the code is not intended to be production quality.



Comment at: 
clang/test/Driver/Inputs/baremetal_multilib/arm-none-eabi/multilib.yaml:24
+- path: thumb/v6-m/nofp
+  args: [--target=arm-none-eabi, -mfloat-abi=soft, -march=armv6m]
+  attrs: [thumb, soft, v6m]

phosek wrote:
> I understand how the second section is used to match arguments passed to 
> `clang -cc1` and turn those into attributes which are then used to find the 
> right variant, but I don't understand what this list of arguments is used for?
Having these here permits `clang -print-multi-lib` to work, which would print 
out something like this:
```
thumb/nofp;@mthumb@mfloat-abi=soft
thumb/v7/nofp;@mthumb@march=armv7@mfloat-abi=soft
...
```


Repository:
  rG LLVM Github Monorepo

CHANGES SINCE LAST ACTION
  https://reviews.llvm.org/D140959/new/

https://reviews.llvm.org/D140959

___
cfe-commits mailing list
cfe-commits@lists.llvm.org
https://lists.llvm.org/cgi-bin/mailman/listinfo/cfe-commits


[PATCH] D140959: RFC: Multilib prototype

2023-01-25 Thread Michael Platings via Phabricator via cfe-commits
michaelplatings added a comment.

How the multilib system matches user arguments is the main problem I've been 
struggling with.

These are the options I see:

1. Grant the multilib system full access to all cc1 arguments, as demonstrated 
by the current code. However declare the multilib system unstable - if you 
write a multilib specification, you are responsible for making sure it's 
updated when clang is updated. Clang plugins set the precedent for such an 
approach.

  Advantage: It's powerful.

  Disadvantages:
  - Experience with clang plugins suggests instability will be a source of 
frequent pain.
  - @lenary points out that the order of arguments can be significant.
  - Requires some major refactoring of how arguments are processed before this 
can be done in a robust way (how I implemented it in the prototype is far from 
robust).

2. Pass to the multilib system only the arguments as provided by the user.

  Advantage: Greatly reduced API surface.

  Disadvantage: whoever writes a multilib specification will have to reinvent a 
lot of logic to infer attributes from --target, -march, -mcpu etc. but with 
inadequate tools to do so.

3. Normalise user arguments before passing them to the multilib system.

  Advantages:
  - Uses the existing arguments API.
  - Powerful, if it can be done correctly.

Disadvantage:
  - The normalisation process effectively becomes a new API.
  - Normalisation appears hard to do correctly = likelihood of bugs.
  - Identifying attributes from arguments is fiddly e.g. extracting Arm 
architecture extensions from the march argument.
  - It's too easy to write a regex that could unintentionally match a newly 
introduced argument so the instability problem remains somewhat.

4. Hard-code the attributes and how they are detected in the same way they 
already are right now. For Arm this could be extended with Function Multi 
Versioning as @lenary pointed to, with namespacing to avoid potential clashes 
with other names. So you could have attributes like `[fsanitize=address, 
fno-exceptions, mfloat-abi=softfp, march=thumbv8.1m.main, arm:mve]`.

  Advantages:
  - This is similar to what we already do for multilib so it's well understood.
  - Limited yet extensible API.

Disadvantages:
  - Greatly limits the expressiveness of the multilib system.
  - Any time someone wants to base their multilib on a new attribute it 
requires a change to Clang.
  - Some regular expressions still required for forward compatibility e.g. with 
future versions of Armv8-M.

5. A combination of (1) and (4) as proposed by @lenary.

  Advantages:
  - Stability where predefined attributes are available.
  - The power to access unstable arguments if necessary.

Disadvantages:
  - Same as for (1) - requires some major refactoring of how arguments are 
processed before this can be done in a robust way (how I implemented it in the 
prototype is far from robust).
  - Greater maintenance burden.

None of these options are great but (4) is low risk and extensible so I'm 
currently investigating that.


Repository:
  rG LLVM Github Monorepo

CHANGES SINCE LAST ACTION
  https://reviews.llvm.org/D140959/new/

https://reviews.llvm.org/D140959

___
cfe-commits mailing list
cfe-commits@lists.llvm.org
https://lists.llvm.org/cgi-bin/mailman/listinfo/cfe-commits


[PATCH] D142878: Add testing for Fuchsia multilib

2023-01-30 Thread Michael Platings via Phabricator via cfe-commits
michaelplatings created this revision.
michaelplatings added a reviewer: phosek.
Herald added a subscriber: abrachet.
Herald added a project: All.
michaelplatings requested review of this revision.
Herald added subscribers: cfe-commits, MaskRay.
Herald added a project: clang.

The plan is to change how multilib works under the hood and this test gives 
confidence that the changes won't break user-visible behaviour.


Repository:
  rG LLVM Github Monorepo

https://reviews.llvm.org/D142878

Files:
  clang/lib/Driver/ToolChains/Fuchsia.cpp
  clang/lib/Driver/ToolChains/Fuchsia.h
  clang/unittests/Driver/CMakeLists.txt
  clang/unittests/Driver/FuchsiaTest.cpp

Index: clang/unittests/Driver/FuchsiaTest.cpp
===
--- /dev/null
+++ clang/unittests/Driver/FuchsiaTest.cpp
@@ -0,0 +1,80 @@
+//===- unittests/Driver/FuchsiaTest.cpp --- Fuchsia tests ---===//
+//
+// 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
+//
+//===--===//
+//
+// Unit tests for Fuchsia
+//
+//===--===//
+
+#include "../../lib/Driver/ToolChains/Fuchsia.h"
+#include "gtest/gtest.h"
+
+using namespace clang::driver;
+
+/*
+This test was added prior to changing the behaviour of Multilib.
+The way that Fuchsia used Multilib made it very likely that the change
+would cause it to break so by adding this exhaustive test we avoid that
+possibility.
+*/
+TEST(FuchsiaTest, MultilibVariant) {
+  MultilibSet Multilibs;
+  toolchains::Fuchsia::configureMultilibs(Multilibs);
+
+  std::string Actual;
+
+  for (bool Itanium : {false, true}) {
+for (bool RelativeVtables : {false, true}) {
+  for (bool Hwasan : {false, true}) {
+for (bool Asan : {false, true}) {
+  for (bool Exceptions : {false, true}) {
+Multilib::flags_list Flags;
+toolchains::Fuchsia::configureMultilibFlags(
+Flags, Exceptions, Asan, Hwasan, RelativeVtables, Itanium);
+Multilib Selected;
+EXPECT_TRUE(Multilibs.select(Flags, Selected));
+Actual += Selected.gccSuffix() + "\n";
+  }
+}
+  }
+}
+  }
+  std::string Expected = R"(/noexcept
+
+/asan+noexcept
+/asan
+/hwasan+noexcept
+/hwasan
+/hwasan+noexcept
+/hwasan
+/relative-vtables+noexcept
+/relative-vtables
+/relative-vtables+asan+noexcept
+/relative-vtables+asan
+/relative-vtables+hwasan+noexcept
+/relative-vtables+hwasan
+/relative-vtables+hwasan+noexcept
+/relative-vtables+hwasan
+/compat
+/compat
+/compat
+/compat
+/compat
+/compat
+/compat
+/compat
+/compat
+/compat
+/compat
+/compat
+/compat
+/compat
+/compat
+/compat
+)";
+  EXPECT_EQ(Expected, Actual);
+}
Index: clang/unittests/Driver/CMakeLists.txt
===
--- clang/unittests/Driver/CMakeLists.txt
+++ clang/unittests/Driver/CMakeLists.txt
@@ -9,6 +9,7 @@
 add_clang_unittest(ClangDriverTests
   DistroTest.cpp
   DXCModeTest.cpp
+  FuchsiaTest.cpp
   ToolChainTest.cpp
   ModuleCacheTest.cpp
   MultilibTest.cpp
Index: clang/lib/Driver/ToolChains/Fuchsia.h
===
--- clang/lib/Driver/ToolChains/Fuchsia.h
+++ clang/lib/Driver/ToolChains/Fuchsia.h
@@ -98,6 +98,11 @@
 
   const char *getDefaultLinker() const override { return "ld.lld"; }
 
+  static void configureMultilibs(MultilibSet &);
+  static void configureMultilibFlags(Multilib::flags_list &, bool Exceptions,
+ bool Asan, bool Hwasan,
+ bool RelativeVtables, bool Itanium);
+
 protected:
   Tool *buildLinker() const override;
 };
Index: clang/lib/Driver/ToolChains/Fuchsia.cpp
===
--- clang/lib/Driver/ToolChains/Fuchsia.cpp
+++ clang/lib/Driver/ToolChains/Fuchsia.cpp
@@ -215,6 +215,35 @@
 return FP;
   };
 
+  configureMultilibs(Multilibs);
+
+  Multilibs.FilterOut([&](const Multilib &M) {
+std::vector RD = FilePaths(M);
+return llvm::all_of(RD, [&](std::string P) { return !getVFS().exists(P); });
+  });
+
+  Multilib::flags_list Flags;
+  configureMultilibFlags(
+  Flags,
+  Args.hasFlag(options::OPT_fexceptions, options::OPT_fno_exceptions, true),
+  getSanitizerArgs(Args).needsAsanRt(),
+  getSanitizerArgs(Args).needsHwasanRt(),
+  Args.hasFlag(options::OPT_fexperimental_relative_cxx_abi_vtables,
+   options::OPT_fno_experimental_relative_cxx_abi_vtables,
+   false),
+  Args.getLastArgValue(options::OPT_fcxx_abi_EQ) == "itanium");
+
+  Multilibs.setFilePathsCallback(FilePaths);
+
+  if (Multilibs.select(Flags, SelectedMultilib))
+if

[PATCH] D142878: Add testing for Fuchsia multilib

2023-01-30 Thread Michael Platings via Phabricator via cfe-commits
michaelplatings updated this revision to Diff 493244.
michaelplatings added a comment.

Update commit message and run arc with clang-format on the PATH


Repository:
  rG LLVM Github Monorepo

CHANGES SINCE LAST ACTION
  https://reviews.llvm.org/D142878/new/

https://reviews.llvm.org/D142878

Files:
  clang/lib/Driver/ToolChains/Fuchsia.cpp
  clang/lib/Driver/ToolChains/Fuchsia.h
  clang/unittests/Driver/CMakeLists.txt
  clang/unittests/Driver/FuchsiaTest.cpp

Index: clang/unittests/Driver/FuchsiaTest.cpp
===
--- /dev/null
+++ clang/unittests/Driver/FuchsiaTest.cpp
@@ -0,0 +1,80 @@
+//===- unittests/Driver/FuchsiaTest.cpp --- Fuchsia tests ---===//
+//
+// 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
+//
+//===--===//
+//
+// Unit tests for Fuchsia
+//
+//===--===//
+
+#include "../../lib/Driver/ToolChains/Fuchsia.h"
+#include "gtest/gtest.h"
+
+using namespace clang::driver;
+
+/*
+This test was added prior to changing the behaviour of Multilib.
+The way that Fuchsia used Multilib made it very likely that the change
+would cause it to break so by adding this exhaustive test we avoid that
+possibility.
+*/
+TEST(FuchsiaTest, MultilibVariant) {
+  MultilibSet Multilibs;
+  toolchains::Fuchsia::configureMultilibs(Multilibs);
+
+  std::string Actual;
+
+  for (bool Itanium : {false, true}) {
+for (bool RelativeVtables : {false, true}) {
+  for (bool Hwasan : {false, true}) {
+for (bool Asan : {false, true}) {
+  for (bool Exceptions : {false, true}) {
+Multilib::flags_list Flags;
+toolchains::Fuchsia::configureMultilibFlags(
+Flags, Exceptions, Asan, Hwasan, RelativeVtables, Itanium);
+Multilib Selected;
+EXPECT_TRUE(Multilibs.select(Flags, Selected));
+Actual += Selected.gccSuffix() + "\n";
+  }
+}
+  }
+}
+  }
+  std::string Expected = R"(/noexcept
+
+/asan+noexcept
+/asan
+/hwasan+noexcept
+/hwasan
+/hwasan+noexcept
+/hwasan
+/relative-vtables+noexcept
+/relative-vtables
+/relative-vtables+asan+noexcept
+/relative-vtables+asan
+/relative-vtables+hwasan+noexcept
+/relative-vtables+hwasan
+/relative-vtables+hwasan+noexcept
+/relative-vtables+hwasan
+/compat
+/compat
+/compat
+/compat
+/compat
+/compat
+/compat
+/compat
+/compat
+/compat
+/compat
+/compat
+/compat
+/compat
+/compat
+/compat
+)";
+  EXPECT_EQ(Expected, Actual);
+}
Index: clang/unittests/Driver/CMakeLists.txt
===
--- clang/unittests/Driver/CMakeLists.txt
+++ clang/unittests/Driver/CMakeLists.txt
@@ -9,6 +9,7 @@
 add_clang_unittest(ClangDriverTests
   DistroTest.cpp
   DXCModeTest.cpp
+  FuchsiaTest.cpp
   ToolChainTest.cpp
   ModuleCacheTest.cpp
   MultilibTest.cpp
Index: clang/lib/Driver/ToolChains/Fuchsia.h
===
--- clang/lib/Driver/ToolChains/Fuchsia.h
+++ clang/lib/Driver/ToolChains/Fuchsia.h
@@ -98,6 +98,11 @@
 
   const char *getDefaultLinker() const override { return "ld.lld"; }
 
+  static void configureMultilibs(MultilibSet &);
+  static void configureMultilibFlags(Multilib::flags_list &, bool Exceptions,
+ bool Asan, bool Hwasan,
+ bool RelativeVtables, bool Itanium);
+
 protected:
   Tool *buildLinker() const override;
 };
Index: clang/lib/Driver/ToolChains/Fuchsia.cpp
===
--- clang/lib/Driver/ToolChains/Fuchsia.cpp
+++ clang/lib/Driver/ToolChains/Fuchsia.cpp
@@ -215,6 +215,35 @@
 return FP;
   };
 
+  configureMultilibs(Multilibs);
+
+  Multilibs.FilterOut([&](const Multilib &M) {
+std::vector RD = FilePaths(M);
+return llvm::all_of(RD, [&](std::string P) { return !getVFS().exists(P); });
+  });
+
+  Multilib::flags_list Flags;
+  configureMultilibFlags(
+  Flags,
+  Args.hasFlag(options::OPT_fexceptions, options::OPT_fno_exceptions, true),
+  getSanitizerArgs(Args).needsAsanRt(),
+  getSanitizerArgs(Args).needsHwasanRt(),
+  Args.hasFlag(options::OPT_fexperimental_relative_cxx_abi_vtables,
+   options::OPT_fno_experimental_relative_cxx_abi_vtables,
+   false),
+  Args.getLastArgValue(options::OPT_fcxx_abi_EQ) == "itanium");
+
+  Multilibs.setFilePathsCallback(FilePaths);
+
+  if (Multilibs.select(Flags, SelectedMultilib))
+if (!SelectedMultilib.isDefault())
+  if (const auto &PathsCallback = Multilibs.filePathsCallback())
+for (const auto &Path : PathsCallback(SelectedMultilib))
+  // Prepend the multi

[PATCH] D142893: Class for building MultilibSet

2023-01-30 Thread Michael Platings via Phabricator via cfe-commits
michaelplatings created this revision.
michaelplatings added a reviewer: phosek.
Herald added a subscriber: abrachet.
Herald added a project: All.
michaelplatings requested review of this revision.
Herald added subscribers: cfe-commits, MaskRay.
Herald added a project: clang.

The functionality in MultilibSet for creating it is tied to its current
implementation. Putting that code in a separate class is an enabler for
changing the MultilibSet implementation.


Repository:
  rG LLVM Github Monorepo

https://reviews.llvm.org/D142893

Files:
  clang/include/clang/Driver/Multilib.h
  clang/include/clang/Driver/MultilibBuilder.h
  clang/lib/Driver/CMakeLists.txt
  clang/lib/Driver/Multilib.cpp
  clang/lib/Driver/MultilibBuilder.cpp
  clang/lib/Driver/ToolChains/BareMetal.cpp
  clang/lib/Driver/ToolChains/Fuchsia.cpp
  clang/lib/Driver/ToolChains/Gnu.cpp
  clang/unittests/Driver/CMakeLists.txt
  clang/unittests/Driver/MultilibBuilderTest.cpp
  clang/unittests/Driver/MultilibTest.cpp

Index: clang/unittests/Driver/MultilibTest.cpp
===
--- clang/unittests/Driver/MultilibTest.cpp
+++ clang/unittests/Driver/MultilibTest.cpp
@@ -11,34 +11,17 @@
 //===--===//
 
 #include "clang/Driver/Multilib.h"
+#include "../../lib/Driver/ToolChains/CommonArgs.h"
 #include "clang/Basic/LLVM.h"
+#include "llvm/ADT/ArrayRef.h"
 #include "llvm/ADT/StringRef.h"
 #include "llvm/ADT/StringSwitch.h"
+#include "llvm/Support/SourceMgr.h"
 #include "gtest/gtest.h"
 
 using namespace clang::driver;
 using namespace clang;
 
-TEST(MultilibTest, MultilibValidity) {
-
-  ASSERT_TRUE(Multilib().isValid()) << "Empty multilib is not valid";
-
-  ASSERT_TRUE(Multilib().flag("+foo").isValid())
-  << "Single indicative flag is not valid";
-
-  ASSERT_TRUE(Multilib().flag("-foo").isValid())
-  << "Single contraindicative flag is not valid";
-
-  ASSERT_FALSE(Multilib().flag("+foo").flag("-foo").isValid())
-  << "Conflicting flags should invalidate the Multilib";
-
-  ASSERT_TRUE(Multilib().flag("+foo").flag("+foo").isValid())
-  << "Multilib should be valid even if it has the same flag twice";
-
-  ASSERT_TRUE(Multilib().flag("+foo").flag("-foobar").isValid())
-  << "Seemingly conflicting prefixes shouldn't actually conflict";
-}
-
 TEST(MultilibTest, OpEqReflexivity1) {
   Multilib M;
   ASSERT_TRUE(M == M) << "Multilib::operator==() is not reflexive";
@@ -50,40 +33,28 @@
 }
 
 TEST(MultilibTest, OpEqReflexivity3) {
-  Multilib M1, M2;
-  M1.flag("+foo");
-  M2.flag("+foo");
+  Multilib M1({}, {}, {}, 0, {"+foo"});
+  Multilib M2({}, {}, {}, 0, {"+foo"});
   ASSERT_TRUE(M1 == M2) << "Multilibs with the same flag should be the same";
 }
 
 TEST(MultilibTest, OpEqInequivalence1) {
-  Multilib M1, M2;
-  M1.flag("+foo");
-  M2.flag("-foo");
+  Multilib M1({}, {}, {}, 0, {"+foo"});
+  Multilib M2({}, {}, {}, 0, {"-foo"});
   ASSERT_FALSE(M1 == M2) << "Multilibs with conflicting flags are not the same";
   ASSERT_FALSE(M2 == M1)
   << "Multilibs with conflicting flags are not the same (commuted)";
 }
 
 TEST(MultilibTest, OpEqInequivalence2) {
-  Multilib M1, M2;
-  M2.flag("+foo");
+  Multilib M1;
+  Multilib M2({}, {}, {}, 0, {"+foo"});
   ASSERT_FALSE(M1 == M2) << "Flags make Multilibs different";
 }
 
-TEST(MultilibTest, OpEqEquivalence1) {
-  Multilib M1, M2;
-  M1.flag("+foo");
-  M2.flag("+foo").flag("+foo");
-  ASSERT_TRUE(M1 == M2) << "Flag duplication shouldn't affect equivalence";
-  ASSERT_TRUE(M2 == M1)
-  << "Flag duplication shouldn't affect equivalence (commuted)";
-}
-
 TEST(MultilibTest, OpEqEquivalence2) {
-  Multilib M1("64");
-  Multilib M2;
-  M2.gccSuffix("/64");
+  Multilib M1("/64");
+  Multilib M2("/64");
   ASSERT_TRUE(M1 == M2)
   << "Constructor argument must match Multilib::gccSuffix()";
   ASSERT_TRUE(M2 == M1)
@@ -91,9 +62,8 @@
 }
 
 TEST(MultilibTest, OpEqEquivalence3) {
-  Multilib M1("", "32");
-  Multilib M2;
-  M2.osSuffix("/32");
+  Multilib M1("", "/32");
+  Multilib M2("", "/32");
   ASSERT_TRUE(M1 == M2)
   << "Constructor argument must match Multilib::osSuffix()";
   ASSERT_TRUE(M2 == M1)
@@ -101,9 +71,8 @@
 }
 
 TEST(MultilibTest, OpEqEquivalence4) {
-  Multilib M1("", "", "16");
-  Multilib M2;
-  M2.includeSuffix("/16");
+  Multilib M1("", "", "/16");
+  Multilib M2("", "", "/16");
   ASSERT_TRUE(M1 == M2)
   << "Constructor argument must match Multilib::includeSuffix()";
   ASSERT_TRUE(M2 == M1)
@@ -111,31 +80,31 @@
 }
 
 TEST(MultilibTest, OpEqInequivalence3) {
-  Multilib M1("foo");
-  Multilib M2("bar");
+  Multilib M1("/foo");
+  Multilib M2("/bar");
   ASSERT_FALSE(M1 == M2) << "Differing gccSuffixes should be different";
   ASSERT_FALSE(M2 == M1)
   << "Differing gccSuffixes should be different (commuted)";
 }
 
 TEST(MultilibTest, OpEqInequivalence4) {
-  Multilib M1("", "foo");
-  Multilib M2("", "bar");
+  Multilib M1("", "/foo");

[PATCH] D142905: Change multilib selection algorithm

2023-01-30 Thread Michael Platings via Phabricator via cfe-commits
michaelplatings created this revision.
michaelplatings added a reviewer: phosek.
Herald added subscribers: abrachet, mgrang.
Herald added a project: All.
michaelplatings requested review of this revision.
Herald added subscribers: cfe-commits, MaskRay.
Herald added a project: clang.

The new algorithm is:

1. Find all multilibs with flags that are a subset of the requested flags.
2. If more than one multilib matches, choose the last.

In addition a new selection mechanism is permitted, for which multiple
multilibs are returned. This allows layering multilibs on top of each
other.

Since multilibs are now ordered within a list, they no longer need a
Priority field.

The new algorithm is different to the old algorithm, but in practise
the old algorithm was always used in such a way that the effect is the
same.
The old algorithm was to find the set intersection of the requested
flags (with the first character of each removed) with each multilib's
flags (ditto), and for that intersection check whether the first
character matched. However, ignoring the first characters, the
requested flags were always a superset of all the multilibs flags.
Therefore the new algorithm can be used as a drop-in replacement.


Repository:
  rG LLVM Github Monorepo

https://reviews.llvm.org/D142905

Files:
  clang/include/clang/Driver/Multilib.h
  clang/include/clang/Driver/MultilibBuilder.h
  clang/lib/Driver/Multilib.cpp
  clang/lib/Driver/MultilibBuilder.cpp
  clang/lib/Driver/ToolChains/CommonArgs.cpp
  clang/lib/Driver/ToolChains/Fuchsia.cpp
  clang/unittests/Driver/MultilibBuilderTest.cpp
  clang/unittests/Driver/MultilibTest.cpp

Index: clang/unittests/Driver/MultilibTest.cpp
===
--- clang/unittests/Driver/MultilibTest.cpp
+++ clang/unittests/Driver/MultilibTest.cpp
@@ -33,14 +33,14 @@
 }
 
 TEST(MultilibTest, OpEqReflexivity3) {
-  Multilib M1({}, {}, {}, 0, {"+foo"});
-  Multilib M2({}, {}, {}, 0, {"+foo"});
+  Multilib M1({}, {}, {}, {"+foo"});
+  Multilib M2({}, {}, {}, {"+foo"});
   ASSERT_TRUE(M1 == M2) << "Multilibs with the same flag should be the same";
 }
 
 TEST(MultilibTest, OpEqInequivalence1) {
-  Multilib M1({}, {}, {}, 0, {"+foo"});
-  Multilib M2({}, {}, {}, 0, {"-foo"});
+  Multilib M1({}, {}, {}, {"+foo"});
+  Multilib M2({}, {}, {}, {"-foo"});
   ASSERT_FALSE(M1 == M2) << "Multilibs with conflicting flags are not the same";
   ASSERT_FALSE(M2 == M1)
   << "Multilibs with conflicting flags are not the same (commuted)";
@@ -48,7 +48,7 @@
 
 TEST(MultilibTest, OpEqInequivalence2) {
   Multilib M1;
-  Multilib M2({}, {}, {}, 0, {"+foo"});
+  Multilib M2({}, {}, {}, {"+foo"});
   ASSERT_FALSE(M1 == M2) << "Flags make Multilibs different";
 }
 
@@ -124,7 +124,7 @@
 }
 
 TEST(MultilibTest, Construction3) {
-  Multilib M({}, {}, {}, 0, {"+f1", "+f2", "-f3"});
+  Multilib M({}, {}, {}, {"+f1", "+f2", "-f3"});
   for (Multilib::flags_list::const_iterator I = M.flags().begin(),
 E = M.flags().end();
I != E; ++I) {
@@ -149,8 +149,8 @@
 
 TEST(MultilibTest, SetPriority) {
   MultilibSet MS({
-  Multilib("/foo", {}, {}, 1, {"+foo"}),
-  Multilib("/bar", {}, {}, 2, {"+bar"}),
+  Multilib("/foo", {}, {}, {"+foo"}),
+  Multilib("/bar", {}, {}, {"+bar"}),
   });
   Multilib::flags_list Flags1 = {"+foo", "-bar"};
   Multilib Selection1;
@@ -166,3 +166,24 @@
   ASSERT_TRUE(Selection2.gccSuffix() == "/bar")
   << "Selection picked " << Selection2 << " which was not expected";
 }
+
+TEST(MultilibTest, SelectMultiple) {
+  MultilibSet MS({
+  Multilib("/a", {}, {}, {"x"}),
+  Multilib("/b", {}, {}, {"y"}),
+  });
+  std::vector Selection;
+
+  Selection = MS.select({"x"});
+  ASSERT_EQ(1u, Selection.size());
+  EXPECT_EQ("/a", Selection[0].gccSuffix());
+
+  Selection = MS.select({"y"});
+  ASSERT_EQ(1u, Selection.size());
+  EXPECT_EQ("/b", Selection[0].gccSuffix());
+
+  Selection = MS.select({"y", "x"});
+  ASSERT_EQ(2u, Selection.size());
+  EXPECT_EQ("/a", Selection[0].gccSuffix());
+  EXPECT_EQ("/b", Selection[1].gccSuffix());
+}
Index: clang/unittests/Driver/MultilibBuilderTest.cpp
===
--- clang/unittests/Driver/MultilibBuilderTest.cpp
+++ clang/unittests/Driver/MultilibBuilderTest.cpp
@@ -7,7 +7,7 @@
 //
 //===--===//
 //
-// Unit tests for Multilib and MultilibBuilder
+// Unit tests for MultilibBuilderVariant and MultilibBuilder
 //
 //===--===//
 
@@ -185,14 +185,14 @@
 bool IsSF = I & 0x2;
 Multilib::flags_list Flags;
 if (IsEL)
-  Flags.push_back("+EL");
+  Flags.insert("+EL");
 else
-  Flags.push_back("-EL");
+  Flags.insert("-EL");
 
 if (IsSF)
-  Flags.push_back("+SF");
+  Flags.insert("+SF");
 else
-  Flags.push_back("-S

[PATCH] D142932: Multilib YAML parsing

2023-01-30 Thread Michael Platings via Phabricator via cfe-commits
michaelplatings created this revision.
michaelplatings added a reviewer: phosek.
Herald added a project: All.
michaelplatings requested review of this revision.
Herald added subscribers: cfe-commits, MaskRay.
Herald added a project: clang.

Repository:
  rG LLVM Github Monorepo

https://reviews.llvm.org/D142932

Files:
  clang/include/clang/Driver/Multilib.h
  clang/lib/Driver/Multilib.cpp
  clang/unittests/Driver/MultilibTest.cpp

Index: clang/unittests/Driver/MultilibTest.cpp
===
--- clang/unittests/Driver/MultilibTest.cpp
+++ clang/unittests/Driver/MultilibTest.cpp
@@ -187,3 +187,347 @@
   EXPECT_EQ("/a", Selection[0].gccSuffix());
   EXPECT_EQ("/b", Selection[1].gccSuffix());
 }
+
+static void diagnosticCallback(const llvm::SMDiagnostic &D, void *Out) {
+  *reinterpret_cast(Out) = D.getMessage();
+}
+
+static bool parse(MultilibSet &MS, MultilibFlagMap &MFM,
+  std::string &Diagnostic, const char *Data) {
+  return MS.parse(llvm::MemoryBufferRef(Data, "TEST"), MFM, diagnosticCallback,
+  &Diagnostic);
+}
+
+static bool parse(MultilibSet &MS, MultilibFlagMap &MFM, const char *Data) {
+  return MS.parse(llvm::MemoryBufferRef(Data, "TEST"), MFM);
+}
+
+TEST(MultilibTest, ParseInvalid) {
+  std::string Diagnostic;
+
+  MultilibSet MS;
+  MultilibFlagMap MFM;
+  EXPECT_FALSE(parse(MS, MFM, Diagnostic, R"(
+variants:
+- dir: /abc
+  flags: []
+  printArgs: []
+)"));
+  EXPECT_TRUE(StringRef(Diagnostic).contains("paths must be relative"))
+  << Diagnostic;
+
+  EXPECT_FALSE(parse(MS, MFM, Diagnostic, R"(
+variants:
+- flags: []
+  printArgs: []
+)"));
+  EXPECT_TRUE(StringRef(Diagnostic).contains("missing required key 'dir'"))
+  << Diagnostic;
+
+  EXPECT_FALSE(parse(MS, MFM, Diagnostic, R"(
+variants:
+- dir: .
+  printArgs: []
+)"));
+  EXPECT_TRUE(StringRef(Diagnostic).contains("missing required key 'flags'"))
+  << Diagnostic;
+
+  EXPECT_FALSE(parse(MS, MFM, Diagnostic, R"(
+variants:
+- dir: .
+  flags: []
+)"));
+  EXPECT_TRUE(
+  StringRef(Diagnostic).contains("missing required key 'printArgs'"))
+  << Diagnostic;
+
+  EXPECT_FALSE(parse(MS, MFM, Diagnostic, R"(
+flagMap:
+- regex: abc
+)"));
+  EXPECT_TRUE(
+  StringRef(Diagnostic)
+  .contains("value required for 'matchFlags' or 'noMatchFlags'"))
+  << Diagnostic;
+}
+
+TEST(MultilibTest, Parse) {
+  MultilibSet MS;
+  MultilibFlagMap MFM;
+  EXPECT_TRUE(parse(MS, MFM, R"(
+variants:
+- dir: .
+  flags: []
+  printArgs: []
+)"));
+  EXPECT_EQ(1U, MS.size());
+  EXPECT_EQ("", MS.begin()->gccSuffix());
+
+  EXPECT_TRUE(parse(MS, MFM, R"(
+variants:
+- dir: abc
+  flags: []
+  printArgs: []
+)"));
+  EXPECT_EQ(1U, MS.size());
+  EXPECT_EQ("/abc", MS.begin()->gccSuffix());
+
+  EXPECT_TRUE(parse(MS, MFM, R"(
+variants:
+- dir: pqr
+  flags: []
+  printArgs: [-mfloat-abi=soft]
+)"));
+  EXPECT_EQ(1U, MS.size());
+  EXPECT_EQ("/pqr", MS.begin()->gccSuffix());
+  EXPECT_EQ(std::vector({"-mfloat-abi=soft"}),
+MS.begin()->getPrintArgs());
+
+  EXPECT_TRUE(parse(MS, MFM, R"(
+variants:
+- dir: pqr
+  flags: []
+  printArgs: [-mfloat-abi=soft, -fno-exceptions]
+)"));
+  EXPECT_EQ(1U, MS.size());
+  EXPECT_EQ(std::vector({"-mfloat-abi=soft", "-fno-exceptions"}),
+MS.begin()->getPrintArgs());
+
+  EXPECT_TRUE(parse(MS, MFM, R"(
+variants:
+- dir: a
+  flags: []
+  printArgs: []
+- dir: b
+  flags: []
+  printArgs: []
+)"));
+  EXPECT_EQ(2U, MS.size());
+}
+
+static bool select(const std::vector &InFlags,
+   const MultilibSet &MS, const MultilibFlagMap &MFM,
+   Multilib &Selected) {
+  Multilib::flags_list Flags(MFM.getFlags(InFlags));
+  Flags.insert(InFlags.begin(), InFlags.end());
+  return MS.select(Flags, Selected);
+}
+
+TEST(MultilibTest, SelectSoft) {
+  MultilibSet MS;
+  MultilibFlagMap MFM;
+  Multilib Selected;
+  ASSERT_TRUE(parse(MS, MFM, R"(
+variants:
+- dir: s
+  flags: [softabi]
+  printArgs: []
+flagMap:
+- regex: mfloat-abi=soft
+  matchFlags: [softabi]
+- regex: mfloat-abi=softfp
+  matchFlags: [softabi]
+)"));
+  EXPECT_TRUE(select({"mfloat-abi=soft"}, MS, MFM, Selected));
+  EXPECT_TRUE(select({"mfloat-abi=softfp"}, MS, MFM, Selected));
+  EXPECT_FALSE(select({"mfloat-abi=hard"}, MS, MFM, Selected));
+}
+
+TEST(MultilibTest, SelectSoftFP) {
+  MultilibSet MS;
+  MultilibFlagMap MFM;
+  Multilib Selected;
+  ASSERT_TRUE(parse(MS, MFM, R"(
+variants:
+- dir: f
+  flags: [mfloat-abi=softfp]
+  printArgs: []
+)"));
+  EXPECT_FALSE(select({"mfloat-abi=soft"}, MS, MFM, Selected));
+  EXPECT_TRUE(select({"mfloat-abi=softfp"}, MS, MFM, Selected));
+  EXPECT_FALSE(select({"mfloat-abi=hard"}, MS, MFM, Selected));
+}
+
+TEST(MultilibTest, SelectHard) {
+  // If hard float is all that's available then select that only if compiling
+  // with hard float.
+  MultilibSet MS;
+  MultilibFlagMap MFM;
+  Multilib Selected;
+  ASSERT_TRUE(parse(MS, MFM, R"(
+variants:
+- 

[PATCH] D142933: Add -print-multi-selection-flags argument

2023-01-30 Thread Michael Platings via Phabricator via cfe-commits
michaelplatings created this revision.
michaelplatings added reviewers: phosek, lenary, simon_tatham.
Herald added subscribers: abrachet, mgrang.
Herald added a project: All.
michaelplatings requested review of this revision.
Herald added subscribers: cfe-commits, MaskRay.
Herald added a project: clang.

Repository:
  rG LLVM Github Monorepo

https://reviews.llvm.org/D142933

Files:
  clang/include/clang/Driver/Options.td
  clang/include/clang/Driver/ToolChain.h
  clang/lib/Driver/Driver.cpp
  clang/lib/Driver/ToolChain.cpp
  clang/lib/Driver/ToolChains/Arch/ARM.cpp
  clang/lib/Driver/ToolChains/Arch/ARM.h
  clang/test/Driver/print-multi-selection-flags.c

Index: clang/test/Driver/print-multi-selection-flags.c
===
--- /dev/null
+++ clang/test/Driver/print-multi-selection-flags.c
@@ -0,0 +1,41 @@
+// RUN: %clang -print-multi-selection-flags --target=aarch64-linux -fc++-abi=itanium -fsanitize=address | FileCheck --check-prefix=CHECK-LINUX %s
+// CHECK-LINUX: fc++-abi=itanium
+// CHECK-LINUX-NEXT: fexceptions
+// CHECK-LINUX-NEXT: fno-experimental-relative-c++-abi-vtables
+// CHECK-LINUX-NEXT: frtti
+// CHECK-LINUX-NEXT: fsanitize=address
+// CHECK-LINUX-NEXT: target=aarch64-unknown-linux
+
+// RUN: %clang -print-multi-selection-flags --target=aarch64-fuchsia -fsanitize=hwaddress | FileCheck --check-prefix=CHECK-FUCHSIA %s
+// CHECK-FUCHSIA: fexperimental-relative-c++-abi-vtables
+// CHECK-FUCHSIA: fsanitize=hwaddress
+// CHECK-FUCHSIA: target=aarch64-unknown-fuchsia
+
+// RUN: %clang -print-multi-selection-flags --target=arm-none-eabi -mfloat-abi=soft -fno-exceptions -fno-rtti | FileCheck --check-prefix=CHECK-ARMV4T %s
+// CHECK-ARMV4T: fno-exceptions
+// CHECK-ARMV4T: fno-rtti
+// CHECK-ARMV4T: mfloat-abi=soft
+// CHECK-ARMV4T: mfpu=none
+// CHECK-ARMV4T: target=armv4t-none-unknown-eabi
+
+// RUN: %clang -print-multi-selection-flags --target=armv7em-none-eabi -mfloat-abi=softfp | FileCheck --check-prefix=CHECK-SOFTFP %s
+// CHECK-SOFTFP: mfloat-abi=softfp
+// CHECK-SOFTFP: mfpu=fpv4-sp-d16
+// CHECK-SOFTFP: target=thumbv7em-none-unknown-eabi
+
+// RUN: %clang -print-multi-selection-flags --target=arm-none-eabihf -march=armv7em -mfpu=fpv5-d16 | FileCheck --check-prefix=CHECK-HARD %s
+// CHECK-HARD: mfloat-abi=hard
+// CHECK-HARD: mfpu=fpv5-d16
+// CHECK-HARD: target=thumbv7em-none-unknown-eabihf
+
+// RUN: %clang -print-multi-selection-flags --target=arm-none-eabi -mfloat-abi=hard -march=armv8.1m.main+mve.fp | FileCheck --check-prefix=CHECK-MVE %s
+// CHECK-MVE: march=+mve
+// CHECK-MVE: march=+mve.fp
+// CHECK-MVE: mfloat-abi=hard
+// CHECK-MVE: mfpu=fp-armv8-fullfp16-sp-d16
+// CHECK-MVE: target=thumbv8.1m.main-none-unknown-eabihf
+
+// RUN: %clang -print-multi-selection-flags --target=arm-none-eabi -march=armv8.1m.main+mve+nofp | FileCheck --check-prefix=CHECK-MVENOFP %s
+// CHECK-MVENOFP: march=+mve
+// CHECK-MVENOFP-NOT: march=+mve.fp
+// CHECK-MVENOFP: mfpu=none
Index: clang/lib/Driver/ToolChains/Arch/ARM.h
===
--- clang/lib/Driver/ToolChains/Arch/ARM.h
+++ clang/lib/Driver/ToolChains/Arch/ARM.h
@@ -64,9 +64,11 @@
 void getARMArchCPUFromArgs(const llvm::opt::ArgList &Args,
llvm::StringRef &Arch, llvm::StringRef &CPU,
bool FromAs = false);
+// Optionally returns the FPUKind
 void getARMTargetFeatures(const Driver &D, const llvm::Triple &Triple,
   const llvm::opt::ArgList &Args,
-  std::vector &Features, bool ForAS);
+  std::vector &Features, bool ForAS,
+  unsigned *OutFPUKind = nullptr);
 int getARMSubArchVersionNumber(const llvm::Triple &Triple);
 bool isARMMProfile(const llvm::Triple &Triple);
 bool isARMAProfile(const llvm::Triple &Triple);
Index: clang/lib/Driver/ToolChains/Arch/ARM.cpp
===
--- clang/lib/Driver/ToolChains/Arch/ARM.cpp
+++ clang/lib/Driver/ToolChains/Arch/ARM.cpp
@@ -438,7 +438,8 @@
 
 void arm::getARMTargetFeatures(const Driver &D, const llvm::Triple &Triple,
const ArgList &Args,
-   std::vector &Features, bool ForAS) {
+   std::vector &Features, bool ForAS,
+   unsigned *OutFPUKind) {
   bool KernelOrKext =
   Args.hasArg(options::OPT_mkernel, options::OPT_fapple_kext);
   arm::FloatABI ABI = arm::getARMFloatABI(D, Triple, Args);
@@ -643,6 +644,7 @@
 {"-dotprod", "-fp16fml", "-bf16", "-mve.fp"});
 if (!hasIntegerMVE(Features))
   Features.emplace_back("-fpregs");
+FPUID = llvm::ARM::FK_NONE;
   }
 
   // En/disable crc code generation.
@@ -899,6 +901,10 @@
 
   if (Args.getLastArg(options::OPT_mno_bti_at_return_twice))
 Features.push_back("+no-bti-at-return-twice");
+
+  if (OutFPUKind) {

[PATCH] D142986: Enable multilib.yaml in the BareMetal ToolChain

2023-01-31 Thread Michael Platings via Phabricator via cfe-commits
michaelplatings created this revision.
michaelplatings added a reviewer: phosek.
Herald added subscribers: abidh, kristof.beyls.
Herald added a project: All.
michaelplatings requested review of this revision.
Herald added subscribers: cfe-commits, MaskRay.
Herald added a project: clang.

The default location for multilib.yaml is lib/clang-runtimes, without
any target-specific suffix. This will allow multilibs for different
architectures to share a common include directory.

To avoid breaking the arm-execute-only.c CHECK-NO-EXECUTE-ONLY-ASM
test, add a GetExecuteOnly argument to getARMTargetFeatures.

Since the presence of multilib.yaml can change the exact location of a
library, relax the baremetal.cpp test.


Repository:
  rG LLVM Github Monorepo

https://reviews.llvm.org/D142986

Files:
  clang/lib/Driver/ToolChain.cpp
  clang/lib/Driver/ToolChains/Arch/ARM.cpp
  clang/lib/Driver/ToolChains/Arch/ARM.h
  clang/lib/Driver/ToolChains/BareMetal.cpp
  clang/test/Driver/Inputs/baremetal_multilib/multilib.yaml
  clang/test/Driver/baremetal-multilib.cpp
  clang/test/Driver/baremetal.cpp

Index: clang/test/Driver/baremetal.cpp
===
--- clang/test/Driver/baremetal.cpp
+++ clang/test/Driver/baremetal.cpp
@@ -118,9 +118,9 @@
 // Verify that the bare metal driver does not include any host system paths:
 // CHECK-AARCH64-NO-HOST-INC: InstalledDir: [[INSTALLEDDIR:.+]]
 // CHECK-AARCH64-NO-HOST-INC: "-resource-dir" "[[RESOURCE:[^"]+]]"
-// CHECK-AARCH64-NO-HOST-INC-SAME: "-internal-isystem" "[[INSTALLEDDIR]]{{[/\\]+}}..{{[/\\]+}}lib{{[/\\]+}}clang-runtimes{{[/\\]+}}aarch64-none-elf{{[/\\]+}}include{{[/\\]+}}c++{{[/\\]+}}v1"
+// CHECK-AARCH64-NO-HOST-INC-SAME: "-internal-isystem" "[[INSTALLEDDIR]]{{[/\\]+}}..{{[/\\]+}}lib{{[/\\]+}}clang-runtimes{{[/\\]+[^"]*}}include{{[/\\]+}}c++{{[/\\]+}}v1"
 // CHECK-AARCH64-NO-HOST-INC-SAME: "-internal-isystem" "[[RESOURCE]]{{[/\\]+}}include"
-// CHECK-AARCH64-NO-HOST-INC-SAME: "-internal-isystem" "[[INSTALLEDDIR]]{{[/\\]+}}..{{[/\\]+}}lib{{[/\\]+}}clang-runtimes{{[/\\]+}}aarch64-none-elf{{[/\\]+}}include"
+// CHECK-AARCH64-NO-HOST-INC-SAME: "-internal-isystem" "[[INSTALLEDDIR]]{{[/\\]+}}..{{[/\\]+}}lib{{[/\\]+}}clang-runtimes{{[/\\]+[^"]*}}include"
 
 // RUN: %clang %s -### --target=riscv64-unknown-elf -o %t.out -L some/directory/user/asked/for \
 // RUN: --sysroot=%S/Inputs/basic_riscv64_tree/riscv64-unknown-elf 2>&1 \
Index: clang/test/Driver/baremetal-multilib.cpp
===
--- /dev/null
+++ clang/test/Driver/baremetal-multilib.cpp
@@ -0,0 +1,45 @@
+// REQUIRES: shell
+// UNSUPPORTED: system-windows
+
+// RUN: rm -rf %T/baremetal_multilib
+// RUN: mkdir -p %T/baremetal_multilib/bin
+// RUN: mkdir -p %T/baremetal_multilib/lib/clang-runtimes/arm-none-eabi/thumb/v8-m.main/fp/lib
+// RUN: touch %T/baremetal_multilib/lib/clang-runtimes/arm-none-eabi/thumb/v8-m.main/fp/lib/libclang_rt.builtins.a
+// RUN: ln -s %clang %T/baremetal_multilib/bin/clang
+// RUN: ln -s %S/Inputs/baremetal_multilib/multilib.yaml %T/baremetal_multilib/lib/clang-runtimes/multilib.yaml
+
+// RUN: %T/baremetal_multilib/bin/clang -no-canonical-prefixes %s -### -o %t.o 2>&1 \
+// RUN: --target=thumbv8m.main-none-eabihf --sysroot= \
+// RUN:   | FileCheck %s
+// CHECK: "{{.*}}clang{{.*}}" "-cc1" "-triple" "thumbv8m.main-none-unknown-eabihf"
+// CHECK-SAME: "-internal-isystem" "{{.*}}/baremetal_multilib/bin/../lib/clang-runtimes/arm-none-eabi/thumb/v8-m.main/fp/include/c++/v1"
+// CHECK-SAME: "-internal-isystem" "{{.*}}/baremetal_multilib/bin/../lib/clang-runtimes/arm-none-eabi/thumb/v8-m.main/fp/include"
+// CHECK-SAME: "-x" "c++" "{{.*}}/baremetal-multilib.cpp"
+// CHECK-NEXT: "{{[^"]*}}ld{{(\.(lld|bfd|gold))?}}{{(\.exe)?}}" "{{.*}}.o" "-Bstatic"
+// CHECK-SAME: "-L{{.*}}/baremetal_multilib/bin/../lib/clang-runtimes/arm-none-eabi/thumb/v8-m.main/fp/lib"
+// CHECK-SAME: "-lc" "-lm" "-lclang_rt.builtins"
+// CHECK-SAME: "-o" "{{.*}}.o"
+
+// RUN: %T/baremetal_multilib/bin/clang -no-canonical-prefixes -print-multi-directory 2>&1 \
+// RUN: --target=thumbv8m.main-none-eabihf --sysroot= \
+// RUN:   | FileCheck --check-prefix=CHECK-PRINT-MULTI-DIRECTORY %s
+// CHECK-PRINT-MULTI-DIRECTORY: arm-none-eabi/thumb/v8-m.main/fp
+
+// RUN: %T/baremetal_multilib/bin/clang -no-canonical-prefixes -print-multi-lib 2>&1 \
+// RUN: --target=arm-none-eabi --sysroot= \
+// RUN:   | FileCheck --check-prefix=CHECK-PRINT-MULTI-LIB %s
+// CHECK-PRINT-MULTI-LIB: arm-none-eabi/thumb/v6-m/nofp;@-target=thumbv6m-none-eabi@mfloat-abi=soft
+// CHECK-PRINT-MULTI-LIB: arm-none-eabi/thumb/v7-m/nofp;@-target=thumbv7m-none-eabi@mfloat-abi=soft
+// CHECK-PRINT-MULTI-LIB: arm-none-eabi/thumb/v7e-m/nofp;@-target=thumbv7em-none-eabi@mfloat-abi=soft@mfpu=none
+// CHECK-PRINT-MULTI-LIB: arm-none-eabi/thumb/v8-m.main/nofp;@-target=arm-none-eabi@mfloat-abi=soft@march=armv8m.main+nofp
+// CHECK-PRINT-MULTI-LIB: arm-none-eabi/

[PATCH] D140959: RFC: Multilib prototype

2023-02-01 Thread Michael Platings via Phabricator via cfe-commits
michaelplatings abandoned this revision.
michaelplatings added a comment.

I've created a new stack of changes taking into account the feedback. Unlike 
this change which was strictly a prototype, the new changes should be suitable 
for detailed review and hopefully approval.

- https://reviews.llvm.org/D142878 - Add testing for Fuchsia multilib
- https://reviews.llvm.org/D142893 - Class for building MultilibSet
- https://reviews.llvm.org/D142905 - Change multilib selection algorithm
- https://reviews.llvm.org/D142932 - Multilib YAML parsing
- https://reviews.llvm.org/D142933 - Add -print-multi-selection-flags argument
- https://reviews.llvm.org/D142986 - Enable multilib.yaml in the BareMetal 
ToolChain

I'm working on further patches to enable multilib layering, but that needn't 
block the above changes.

Thanks for giving it a try @Joe. The new changes are by design much more 
limited, in order to avoid creating an unstable API. I'd be interested to learn 
from you whether it's suitable for what you need, possibly by adding more 
functionality. In particular you'll see that https://reviews.llvm.org/D142933 
has functionality specific to Arm extensions so something similar may be 
required for other architectures.

In D140959#4028638 , @tschuett wrote:

> Did you look at Yaml I/O ?

Thanks for the tip, I've used it in https://reviews.llvm.org/D142932 and it's a 
great improvement.


Repository:
  rG LLVM Github Monorepo

CHANGES SINCE LAST ACTION
  https://reviews.llvm.org/D140959/new/

https://reviews.llvm.org/D140959

___
cfe-commits mailing list
cfe-commits@lists.llvm.org
https://lists.llvm.org/cgi-bin/mailman/listinfo/cfe-commits


[PATCH] D143059: [NFC] Enable selecting multiple multilibs

2023-02-01 Thread Michael Platings via Phabricator via cfe-commits
michaelplatings created this revision.
michaelplatings added a reviewer: phosek.
Herald added subscribers: luke, abrachet, frasercrmck, luismarques, apazos, 
sameer.abuasal, s.egerton, Jim, jocewei, PkmX, the_o, brucehoult, 
MartinMosbeck, rogfer01, atanasyan, edward-jones, zzheng, jrtc27, niosHD, 
sabuasal, simoncook, johnrusso, rbar, asb, sdardis.
Herald added a project: All.
michaelplatings requested review of this revision.
Herald added subscribers: cfe-commits, pcwang-thead, MaskRay.
Herald added a project: clang.

This will enable layering multilibs on top of each other.
For example a multilib containing only a no-exceptions libc++ could be
layered on top of a multilib containing C libs. This avoids the need
to duplicate the C library for every libc++ variant.

This change doesn't expose the functionality externally, it only opens
the functionality up to be potentially used by ToolChain classes.


Repository:
  rG LLVM Github Monorepo

https://reviews.llvm.org/D143059

Files:
  clang/include/clang/Driver/Multilib.h
  clang/include/clang/Driver/ToolChain.h
  clang/lib/Driver/Driver.cpp
  clang/lib/Driver/Multilib.cpp
  clang/lib/Driver/ToolChain.cpp
  clang/lib/Driver/ToolChains/BareMetal.cpp
  clang/lib/Driver/ToolChains/CSKYToolChain.cpp
  clang/lib/Driver/ToolChains/Fuchsia.cpp
  clang/lib/Driver/ToolChains/Gnu.cpp
  clang/lib/Driver/ToolChains/Gnu.h
  clang/lib/Driver/ToolChains/Hexagon.cpp
  clang/lib/Driver/ToolChains/Hurd.cpp
  clang/lib/Driver/ToolChains/Linux.cpp
  clang/lib/Driver/ToolChains/MipsLinux.cpp
  clang/lib/Driver/ToolChains/RISCVToolchain.cpp
  clang/test/Driver/fuchsia.cpp
  clang/unittests/Driver/FuchsiaTest.cpp
  clang/unittests/Driver/MultilibBuilderTest.cpp
  clang/unittests/Driver/MultilibTest.cpp

Index: clang/unittests/Driver/MultilibTest.cpp
===
--- clang/unittests/Driver/MultilibTest.cpp
+++ clang/unittests/Driver/MultilibTest.cpp
@@ -153,18 +153,18 @@
   Multilib("/bar", {}, {}, {"+bar"}),
   });
   Multilib::flags_list Flags1 = {"+foo", "-bar"};
-  Multilib Selection1;
+  llvm::SmallVector Selection1;
   ASSERT_TRUE(MS.select(Flags1, Selection1))
   << "Flag set was {\"+foo\"}, but selection not found";
-  ASSERT_TRUE(Selection1.gccSuffix() == "/foo")
-  << "Selection picked " << Selection1 << " which was not expected";
+  ASSERT_TRUE(Selection1.back().gccSuffix() == "/foo")
+  << "Selection picked " << Selection1.back() << " which was not expected";
 
   Multilib::flags_list Flags2 = {"+foo", "+bar"};
-  Multilib Selection2;
+  llvm::SmallVector Selection2;
   ASSERT_TRUE(MS.select(Flags2, Selection2))
   << "Flag set was {\"+bar\"}, but selection not found";
-  ASSERT_TRUE(Selection2.gccSuffix() == "/bar")
-  << "Selection picked " << Selection2 << " which was not expected";
+  ASSERT_TRUE(Selection2.back().gccSuffix() == "/bar")
+  << "Selection picked " << Selection2.back() << " which was not expected";
 }
 
 TEST(MultilibTest, SelectMultiple) {
@@ -172,17 +172,17 @@
   Multilib("/a", {}, {}, {"x"}),
   Multilib("/b", {}, {}, {"y"}),
   });
-  std::vector Selection;
+  llvm::SmallVector Selection;
 
-  Selection = MS.select({"x"});
+  ASSERT_TRUE(MS.select({"x"}, Selection));
   ASSERT_EQ(1u, Selection.size());
   EXPECT_EQ("/a", Selection[0].gccSuffix());
 
-  Selection = MS.select({"y"});
+  ASSERT_TRUE(MS.select({"y"}, Selection));
   ASSERT_EQ(1u, Selection.size());
   EXPECT_EQ("/b", Selection[0].gccSuffix());
 
-  Selection = MS.select({"y", "x"});
+  ASSERT_TRUE(MS.select({"y", "x"}, Selection));
   ASSERT_EQ(2u, Selection.size());
   EXPECT_EQ("/a", Selection[0].gccSuffix());
   EXPECT_EQ("/b", Selection[1].gccSuffix());
@@ -307,7 +307,7 @@
 
 static bool select(const std::vector &InFlags,
const MultilibSet &MS, const MultilibFlagMap &MFM,
-   Multilib &Selected) {
+   llvm::SmallVector &Selected) {
   Multilib::flags_list Flags(MFM.getFlags(InFlags));
   Flags.insert(InFlags.begin(), InFlags.end());
   return MS.select(Flags, Selected);
@@ -316,7 +316,7 @@
 TEST(MultilibTest, SelectSoft) {
   MultilibSet MS;
   MultilibFlagMap MFM;
-  Multilib Selected;
+  llvm::SmallVector Selected;
   ASSERT_TRUE(parse(MS, MFM, R"(
 variants:
 - dir: s
@@ -336,7 +336,7 @@
 TEST(MultilibTest, SelectSoftFP) {
   MultilibSet MS;
   MultilibFlagMap MFM;
-  Multilib Selected;
+  llvm::SmallVector Selected;
   ASSERT_TRUE(parse(MS, MFM, R"(
 variants:
 - dir: f
@@ -353,7 +353,7 @@
   // with hard float.
   MultilibSet MS;
   MultilibFlagMap MFM;
-  Multilib Selected;
+  llvm::SmallVector Selected;
   ASSERT_TRUE(parse(MS, MFM, R"(
 variants:
 - dir: h
@@ -368,7 +368,7 @@
 TEST(MultilibTest, SelectFloatABI) {
   MultilibSet MS;
   MultilibFlagMap MFM;
-  Multilib Selected;
+  llvm::SmallVector Selected;
   ASSERT_TRUE(parse(MS, MFM, R"(
 variants:
 - dir: s
@@ -389,11 +389,11 @@
   noMatchFlags: [hasfp]
 )"));
   select({"mfloat

[PATCH] D143075: BareMetal ToolChain multilib layering

2023-02-01 Thread Michael Platings via Phabricator via cfe-commits
michaelplatings created this revision.
michaelplatings added a reviewer: phosek.
Herald added a subscriber: abidh.
Herald added a project: All.
michaelplatings requested review of this revision.
Herald added subscribers: cfe-commits, MaskRay.
Herald added a project: clang.

This enables layering baremetal multilibs on top of each other.
For example a multilib containing only a no-exceptions libc++ could be
layered on top of a multilib containing C libs. This avoids the need
to duplicate the C library for every libc++ variant.


Repository:
  rG LLVM Github Monorepo

https://reviews.llvm.org/D143075

Files:
  clang/lib/Driver/ToolChains/BareMetal.cpp
  clang/lib/Driver/ToolChains/BareMetal.h
  clang/test/Driver/Inputs/baremetal_multilib/multilib.yaml
  clang/test/Driver/baremetal-multilib.cpp

Index: clang/test/Driver/baremetal-multilib.cpp
===
--- clang/test/Driver/baremetal-multilib.cpp
+++ clang/test/Driver/baremetal-multilib.cpp
@@ -25,6 +25,23 @@
 // RUN:   | FileCheck --check-prefix=CHECK-PRINT-MULTI-DIRECTORY %s
 // CHECK-PRINT-MULTI-DIRECTORY: arm-none-eabi/thumb/v8-m.main/fp
 
+// RUN: %T/baremetal_multilib/bin/clang -no-canonical-prefixes %s -### -o %t.o 2>&1 \
+// RUN: --target=thumbv8.1m.main-none-eabihf -fno-exceptions --sysroot= \
+// RUN:   | FileCheck --check-prefix=CHECK-LAYERED-MULTILIB %s
+// CHECK-LAYERED-MULTILIB: "{{.*}}clang{{.*}}" "-cc1" "-triple" "thumbv8.1m.main-none-unknown-eabihf"
+// CHECK-LAYERED-MULTILIB-SAME: "-internal-isystem" "{{.*}}/baremetal_multilib/bin/../lib/clang-runtimes/arm-none-eabi/thumb/v8.1-m.main/fp/noexcept/include/c++/v1"
+// CHECK-LAYERED-MULTILIB-SAME: "-internal-isystem" "{{.*}}/baremetal_multilib/bin/../lib/clang-runtimes/arm-none-eabi/thumb/v8.1-m.main/fp/include/c++/v1"
+// CHECK-LAYERED-MULTILIB-SAME: "-internal-isystem" "{{.*}}/baremetal_multilib/bin/../lib/clang-runtimes/arm-none-eabi/thumb/v8.1-m.main/fp/noexcept/include"
+// CHECK-LAYERED-MULTILIB-SAME: "-internal-isystem" "{{.*}}/baremetal_multilib/bin/../lib/clang-runtimes/arm-none-eabi/thumb/v8.1-m.main/fp/include"
+// CHECK-LAYERED-MULTILIB-NEXT: "-L{{.*}}/baremetal_multilib/bin/../lib/clang-runtimes/arm-none-eabi/thumb/v8.1-m.main/fp/noexcept/lib"
+// CHECK-LAYERED-MULTILIB-SAME: "-L{{.*}}/baremetal_multilib/bin/../lib/clang-runtimes/arm-none-eabi/thumb/v8.1-m.main/fp/lib"
+
+// RUN: %T/baremetal_multilib/bin/clang -no-canonical-prefixes -print-multi-directory 2>&1 \
+// RUN: --target=thumbv8.1m.main-none-eabihf -fno-exceptions --sysroot= \
+// RUN:   | FileCheck --check-prefix=CHECK-LAYERED-PRINT-MULTI-DIRECTORY %s
+// CHECK-LAYERED-PRINT-MULTI-DIRECTORY: arm-none-eabi/thumb/v8.1-m.main/fp
+// CHECK-LAYERED-PRINT-MULTI-DIRECTORY-NEXT: arm-none-eabi/thumb/v8.1-m.main/fp/noexcept
+
 // RUN: %T/baremetal_multilib/bin/clang -no-canonical-prefixes -print-multi-lib 2>&1 \
 // RUN: --target=arm-none-eabi --sysroot= \
 // RUN:   | FileCheck --check-prefix=CHECK-PRINT-MULTI-LIB %s
@@ -38,6 +55,7 @@
 // CHECK-PRINT-MULTI-LIB: arm-none-eabi/thumb/v8-m.main/fp;@-target=thumbv8m.main-none-eabihf
 // CHECK-PRINT-MULTI-LIB: arm-none-eabi/thumb/v8.1-m.main/fp;@-target=thumbv8.1m.main-none-eabihf
 // CHECK-PRINT-MULTI-LIB: arm-none-eabi/thumb/v8.1-m.main/nofp/mve;@-target=arm-none-eabihf@march=armv8.1m.main+nofp+mve
+// CHECK-PRINT-MULTI-LIB: arm-none-eabi/thumb/v8.1-m.main/fp/noexcept;@-target=thumbv8.1m.main-none-eabihf@fno-exceptions
 
 // RUN: %T/baremetal_multilib/bin/clang -no-canonical-prefixes -x assembler -mexecute-only \
 // RUN: --target=arm-none-eabi --sysroot= %s -c -### 2>&1 \
Index: clang/test/Driver/Inputs/baremetal_multilib/multilib.yaml
===
--- clang/test/Driver/Inputs/baremetal_multilib/multilib.yaml
+++ clang/test/Driver/Inputs/baremetal_multilib/multilib.yaml
@@ -65,6 +65,14 @@
   flags: [target=thumbv8.1m.main-none-unknown-eabihf, march=+mve]
   printArgs: [--target=arm-none-eabihf, -march=armv8.1m.main+nofp+mve]
 
+# A specialisation of v8.1-m.main/fp without exceptions.
+# This layers over the top of the regular v8.1-m.main/fp so it doesn't
+# need to have its own include directory or C library, thereby saving
+# disk space.
+- dir: arm-none-eabi/thumb/v8.1-m.main/fp/noexcept
+  flags: [target=thumbv8.1m.main-none-unknown-eabihf, hasfpu, fno-exceptions]
+  printArgs: [--target=thumbv8.1m.main-none-eabihf, -fno-exceptions]
+
 
 # The second section of the file is a map from auto-detected flags
 # to custom flags. The auto-detected flags can be printed out
Index: clang/lib/Driver/ToolChains/BareMetal.h
===
--- clang/lib/Driver/ToolChains/BareMetal.h
+++ clang/lib/Driver/ToolChains/BareMetal.h
@@ -70,6 +70,9 @@
   void AddLinkRuntimeLib(const llvm::opt::ArgList &Args,
  llvm::opt::ArgStringList &CmdArgs) const;
   std::string computeSysRoot() const override;
+

[PATCH] D142932: Multilib YAML parsing

2023-02-01 Thread Michael Platings via Phabricator via cfe-commits
michaelplatings updated this revision to Diff 493968.
michaelplatings added a comment.

Incorporated changes requested by @miyuki


Repository:
  rG LLVM Github Monorepo

CHANGES SINCE LAST ACTION
  https://reviews.llvm.org/D142932/new/

https://reviews.llvm.org/D142932

Files:
  clang/include/clang/Driver/Multilib.h
  clang/lib/Driver/Multilib.cpp
  clang/unittests/Driver/MultilibTest.cpp

Index: clang/unittests/Driver/MultilibTest.cpp
===
--- clang/unittests/Driver/MultilibTest.cpp
+++ clang/unittests/Driver/MultilibTest.cpp
@@ -187,3 +187,357 @@
   EXPECT_EQ("/a", Selection[0].gccSuffix());
   EXPECT_EQ("/b", Selection[1].gccSuffix());
 }
+
+static void diagnosticCallback(const llvm::SMDiagnostic &D, void *Out) {
+  *reinterpret_cast(Out) = D.getMessage();
+}
+
+static bool parse(MultilibSet &MS, MultilibFlagMap &MFM,
+  std::string &Diagnostic, const char *Data) {
+  return MS.parse(llvm::MemoryBufferRef(Data, "TEST"), MFM, diagnosticCallback,
+  &Diagnostic);
+}
+
+static bool parse(MultilibSet &MS, MultilibFlagMap &MFM, const char *Data) {
+  return MS.parse(llvm::MemoryBufferRef(Data, "TEST"), MFM);
+}
+
+TEST(MultilibTest, ParseInvalid) {
+  std::string Diagnostic;
+
+  MultilibSet MS;
+  MultilibFlagMap MFM;
+  EXPECT_FALSE(parse(MS, MFM, Diagnostic, R"(
+variants:
+- dir: /abc
+  flags: []
+  printArgs: []
+)"));
+  EXPECT_TRUE(StringRef(Diagnostic).contains("paths must be relative"))
+  << Diagnostic;
+
+  EXPECT_FALSE(parse(MS, MFM, Diagnostic, R"(
+variants:
+- flags: []
+  printArgs: []
+)"));
+  EXPECT_TRUE(StringRef(Diagnostic).contains("missing required key 'dir'"))
+  << Diagnostic;
+
+  EXPECT_FALSE(parse(MS, MFM, Diagnostic, R"(
+variants:
+- dir: .
+  printArgs: []
+)"));
+  EXPECT_TRUE(StringRef(Diagnostic).contains("missing required key 'flags'"))
+  << Diagnostic;
+
+  EXPECT_FALSE(parse(MS, MFM, Diagnostic, R"(
+variants:
+- dir: .
+  flags: []
+)"));
+  EXPECT_TRUE(
+  StringRef(Diagnostic).contains("missing required key 'printArgs'"))
+  << Diagnostic;
+
+  EXPECT_FALSE(parse(MS, MFM, Diagnostic, R"(
+flagMap:
+- regex: abc
+)"));
+  EXPECT_TRUE(
+  StringRef(Diagnostic)
+  .contains("value required for 'matchFlags' or 'noMatchFlags'"))
+  << Diagnostic;
+
+  EXPECT_FALSE(parse(MS, MFM, Diagnostic, R"(
+flagMap:
+- dir: .
+  regex: '('
+  printArgs: []
+
+)"));
+  EXPECT_TRUE(StringRef(Diagnostic).contains("parentheses not balanced"))
+  << Diagnostic;
+}
+
+TEST(MultilibTest, Parse) {
+  MultilibSet MS;
+  MultilibFlagMap MFM;
+  EXPECT_TRUE(parse(MS, MFM, R"(
+variants:
+- dir: .
+  flags: []
+  printArgs: []
+)"));
+  EXPECT_EQ(1U, MS.size());
+  EXPECT_EQ("", MS.begin()->gccSuffix());
+
+  EXPECT_TRUE(parse(MS, MFM, R"(
+variants:
+- dir: abc
+  flags: []
+  printArgs: []
+)"));
+  EXPECT_EQ(1U, MS.size());
+  EXPECT_EQ("/abc", MS.begin()->gccSuffix());
+
+  EXPECT_TRUE(parse(MS, MFM, R"(
+variants:
+- dir: pqr
+  flags: []
+  printArgs: [-mfloat-abi=soft]
+)"));
+  EXPECT_EQ(1U, MS.size());
+  EXPECT_EQ("/pqr", MS.begin()->gccSuffix());
+  EXPECT_EQ(std::vector({"-mfloat-abi=soft"}),
+MS.begin()->getPrintArgs());
+
+  EXPECT_TRUE(parse(MS, MFM, R"(
+variants:
+- dir: pqr
+  flags: []
+  printArgs: [-mfloat-abi=soft, -fno-exceptions]
+)"));
+  EXPECT_EQ(1U, MS.size());
+  EXPECT_EQ(std::vector({"-mfloat-abi=soft", "-fno-exceptions"}),
+MS.begin()->getPrintArgs());
+
+  EXPECT_TRUE(parse(MS, MFM, R"(
+variants:
+- dir: a
+  flags: []
+  printArgs: []
+- dir: b
+  flags: []
+  printArgs: []
+)"));
+  EXPECT_EQ(2U, MS.size());
+}
+
+static bool select(const std::vector &InFlags,
+   const MultilibSet &MS, const MultilibFlagMap &MFM,
+   Multilib &Selected) {
+  Multilib::flags_list Flags(MFM.getFlags(InFlags));
+  Flags.insert(InFlags.begin(), InFlags.end());
+  return MS.select(Flags, Selected);
+}
+
+TEST(MultilibTest, SelectSoft) {
+  MultilibSet MS;
+  MultilibFlagMap MFM;
+  Multilib Selected;
+  ASSERT_TRUE(parse(MS, MFM, R"(
+variants:
+- dir: s
+  flags: [softabi]
+  printArgs: []
+flagMap:
+- regex: mfloat-abi=soft
+  matchFlags: [softabi]
+- regex: mfloat-abi=softfp
+  matchFlags: [softabi]
+)"));
+  EXPECT_TRUE(select({"mfloat-abi=soft"}, MS, MFM, Selected));
+  EXPECT_TRUE(select({"mfloat-abi=softfp"}, MS, MFM, Selected));
+  EXPECT_FALSE(select({"mfloat-abi=hard"}, MS, MFM, Selected));
+}
+
+TEST(MultilibTest, SelectSoftFP) {
+  MultilibSet MS;
+  MultilibFlagMap MFM;
+  Multilib Selected;
+  ASSERT_TRUE(parse(MS, MFM, R"(
+variants:
+- dir: f
+  flags: [mfloat-abi=softfp]
+  printArgs: []
+)"));
+  EXPECT_FALSE(select({"mfloat-abi=soft"}, MS, MFM, Selected));
+  EXPECT_TRUE(select({"mfloat-abi=softfp"}, MS, MFM, Selected));
+  EXPECT_FALSE(select({"mfloat-abi=hard"}, MS, MFM, Selected));
+}
+
+TEST(MultilibTest, SelectHard) {
+  // If hard float is all that's available then se

[PATCH] D142933: Add -print-multi-selection-flags argument

2023-02-01 Thread Michael Platings via Phabricator via cfe-commits
michaelplatings added a comment.

> The main trouble I had was at that point we don't have a reference to the 
> ToolChain, so calling `getMultiSelectionFlags` was not possible. [...] I'm 
> not sure what the solution here is.

I see two options:

1. Split getMultiSelectionFlags into needs-ToolChain and doesn't-need-ToolChain 
parts, with the former calling the latter. From Gnu.cpp, call the latter, with 
the limitation that it can use fewer flags.
2. Pass a ToolChain to the Gnu.cpp functions.

> I added the arch extensions and abi to the Result in `getMultiSelectionFlags`

What was the syntax you used for that?
I'm not super keen on the `march=+ext` syntax I came up with so I'm open to 
alternatives.


Repository:
  rG LLVM Github Monorepo

CHANGES SINCE LAST ACTION
  https://reviews.llvm.org/D142933/new/

https://reviews.llvm.org/D142933

___
cfe-commits mailing list
cfe-commits@lists.llvm.org
https://lists.llvm.org/cgi-bin/mailman/listinfo/cfe-commits


[PATCH] D142933: Add -print-multi-selection-flags argument

2023-02-02 Thread Michael Platings via Phabricator via cfe-commits
michaelplatings added a comment.

In D142933#4099043 , @Joe wrote:

> I did briefly try to pass a ToolChain to Gnu.cpp functions, but it became 
> intrusive and had to add it in 5+ places, so unless I'm missing a trick to 
> get the ToolChain from the Driver, my vote would go to the former.

The Driver class does in fact have a private getToolChain method. So two new 
possibilities:

1. Make getToolChain public.
2. Make getMultiSelectionFlags a method of Driver.

> I dropped the `march=` and used the same format as target-features, so it was 
> simply `+m` or `+a`. I think this is intuitive enough without the `march=`

Thanks for explaining. I found that when I was writing a regex to match flags 
it was helpful to have a part of the string I could be sure would be there to 
avoid matching the wrong type of flag, and `march=` helped with that. I also 
worry that names from different types of flags could clash without some kind of 
namespacing.

> the form `x=y` is already broken when you add the flags from the flag list.

Can you give an example of what you mean by that? Sounds like something that 
might need fixing.


Repository:
  rG LLVM Github Monorepo

CHANGES SINCE LAST ACTION
  https://reviews.llvm.org/D142933/new/

https://reviews.llvm.org/D142933

___
cfe-commits mailing list
cfe-commits@lists.llvm.org
https://lists.llvm.org/cgi-bin/mailman/listinfo/cfe-commits


[PATCH] D142878: Add testing for Fuchsia multilib

2023-02-02 Thread Michael Platings via Phabricator via cfe-commits
michaelplatings updated this revision to Diff 494258.
michaelplatings added a comment.

Rebase


Repository:
  rG LLVM Github Monorepo

CHANGES SINCE LAST ACTION
  https://reviews.llvm.org/D142878/new/

https://reviews.llvm.org/D142878

Files:
  clang/lib/Driver/ToolChains/Fuchsia.cpp
  clang/lib/Driver/ToolChains/Fuchsia.h
  clang/unittests/Driver/CMakeLists.txt
  clang/unittests/Driver/FuchsiaTest.cpp

Index: clang/unittests/Driver/FuchsiaTest.cpp
===
--- /dev/null
+++ clang/unittests/Driver/FuchsiaTest.cpp
@@ -0,0 +1,62 @@
+//===- unittests/Driver/FuchsiaTest.cpp --- Fuchsia tests ---===//
+//
+// 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
+//
+//===--===//
+//
+// Unit tests for Fuchsia
+//
+//===--===//
+
+#include "../../lib/Driver/ToolChains/Fuchsia.h"
+#include "gtest/gtest.h"
+
+using namespace clang::driver;
+
+/*
+This test was added prior to changing the behaviour of Multilib.
+The way that Fuchsia used Multilib made it very likely that the change
+would cause it to break so by adding this exhaustive test we avoid that
+possibility.
+*/
+TEST(FuchsiaTest, MultilibVariant) {
+  MultilibSet Multilibs;
+  toolchains::Fuchsia::configureMultilibs(Multilibs);
+
+  std::string Actual;
+
+  for (bool Itanium : {false, true}) {
+for (bool Hwasan : {false, true}) {
+  for (bool Asan : {false, true}) {
+for (bool Exceptions : {false, true}) {
+  Multilib::flags_list Flags;
+  toolchains::Fuchsia::configureMultilibFlags(Flags, Exceptions, Asan,
+  Hwasan, Itanium);
+  Multilib Selected;
+  EXPECT_TRUE(Multilibs.select(Flags, Selected));
+  Actual += Selected.gccSuffix() + "\n";
+}
+  }
+}
+  }
+  std::string Expected = R"(/noexcept
+
+/asan+noexcept
+/asan
+/hwasan+noexcept
+/hwasan
+/hwasan+noexcept
+/hwasan
+/compat
+/compat
+/compat
+/compat
+/compat
+/compat
+/compat
+/compat
+)";
+  EXPECT_EQ(Expected, Actual);
+}
Index: clang/unittests/Driver/CMakeLists.txt
===
--- clang/unittests/Driver/CMakeLists.txt
+++ clang/unittests/Driver/CMakeLists.txt
@@ -9,6 +9,7 @@
 add_clang_unittest(ClangDriverTests
   DistroTest.cpp
   DXCModeTest.cpp
+  FuchsiaTest.cpp
   ToolChainTest.cpp
   ModuleCacheTest.cpp
   MultilibTest.cpp
Index: clang/lib/Driver/ToolChains/Fuchsia.h
===
--- clang/lib/Driver/ToolChains/Fuchsia.h
+++ clang/lib/Driver/ToolChains/Fuchsia.h
@@ -112,6 +112,10 @@
 
   const char *getDefaultLinker() const override { return "ld.lld"; }
 
+  static void configureMultilibs(MultilibSet &);
+  static void configureMultilibFlags(Multilib::flags_list &, bool Exceptions,
+ bool Asan, bool Hwasan, bool Itanium);
+
 protected:
   Tool *buildLinker() const override;
   Tool *buildStaticLibTool() const override;
Index: clang/lib/Driver/ToolChains/Fuchsia.cpp
===
--- clang/lib/Driver/ToolChains/Fuchsia.cpp
+++ clang/lib/Driver/ToolChains/Fuchsia.cpp
@@ -260,6 +260,32 @@
 return FP;
   };
 
+  configureMultilibs(Multilibs);
+
+  Multilibs.FilterOut([&](const Multilib &M) {
+std::vector RD = FilePaths(M);
+return llvm::all_of(RD, [&](std::string P) { return !getVFS().exists(P); });
+  });
+
+  Multilib::flags_list Flags;
+  configureMultilibFlags(
+  Flags,
+  Args.hasFlag(options::OPT_fexceptions, options::OPT_fno_exceptions, true),
+  getSanitizerArgs(Args).needsAsanRt(),
+  getSanitizerArgs(Args).needsHwasanRt(),
+  Args.getLastArgValue(options::OPT_fcxx_abi_EQ) == "itanium");
+
+  Multilibs.setFilePathsCallback(FilePaths);
+
+  if (Multilibs.select(Flags, SelectedMultilib))
+if (!SelectedMultilib.isDefault())
+  if (const auto &PathsCallback = Multilibs.filePathsCallback())
+for (const auto &Path : PathsCallback(SelectedMultilib))
+  // Prepend the multilib path to ensure it takes the precedence.
+  getFilePaths().insert(getFilePaths().begin(), Path);
+}
+
+void Fuchsia::configureMultilibs(MultilibSet &Multilibs) {
   Multilibs.push_back(Multilib());
   // Use the noexcept variant with -fno-exceptions to avoid the extra overhead.
   Multilibs.push_back(Multilib("noexcept", {}, {}, 1)
@@ -284,32 +310,16 @@
   .flag("+fno-exceptions"));
   // Use Itanium C++ ABI for the compat multilib.
   Multilibs.push_back(Multilib("compat", {}, {}, 6).flag("+fc++-abi=itanium"));
+}
 
-  Multilibs.FilterOut([&](const Multilib &M) {
-

[PATCH] D142893: Class for building MultilibSet

2023-02-02 Thread Michael Platings via Phabricator via cfe-commits
michaelplatings updated this revision to Diff 494259.
michaelplatings added a comment.

Rebase


Repository:
  rG LLVM Github Monorepo

CHANGES SINCE LAST ACTION
  https://reviews.llvm.org/D142893/new/

https://reviews.llvm.org/D142893

Files:
  clang/include/clang/Driver/Multilib.h
  clang/include/clang/Driver/MultilibBuilder.h
  clang/lib/Driver/CMakeLists.txt
  clang/lib/Driver/Multilib.cpp
  clang/lib/Driver/MultilibBuilder.cpp
  clang/lib/Driver/ToolChains/BareMetal.cpp
  clang/lib/Driver/ToolChains/Fuchsia.cpp
  clang/lib/Driver/ToolChains/Gnu.cpp
  clang/unittests/Driver/CMakeLists.txt
  clang/unittests/Driver/MultilibBuilderTest.cpp
  clang/unittests/Driver/MultilibTest.cpp

Index: clang/unittests/Driver/MultilibTest.cpp
===
--- clang/unittests/Driver/MultilibTest.cpp
+++ clang/unittests/Driver/MultilibTest.cpp
@@ -11,34 +11,17 @@
 //===--===//
 
 #include "clang/Driver/Multilib.h"
+#include "../../lib/Driver/ToolChains/CommonArgs.h"
 #include "clang/Basic/LLVM.h"
+#include "llvm/ADT/ArrayRef.h"
 #include "llvm/ADT/StringRef.h"
 #include "llvm/ADT/StringSwitch.h"
+#include "llvm/Support/SourceMgr.h"
 #include "gtest/gtest.h"
 
 using namespace clang::driver;
 using namespace clang;
 
-TEST(MultilibTest, MultilibValidity) {
-
-  ASSERT_TRUE(Multilib().isValid()) << "Empty multilib is not valid";
-
-  ASSERT_TRUE(Multilib().flag("+foo").isValid())
-  << "Single indicative flag is not valid";
-
-  ASSERT_TRUE(Multilib().flag("-foo").isValid())
-  << "Single contraindicative flag is not valid";
-
-  ASSERT_FALSE(Multilib().flag("+foo").flag("-foo").isValid())
-  << "Conflicting flags should invalidate the Multilib";
-
-  ASSERT_TRUE(Multilib().flag("+foo").flag("+foo").isValid())
-  << "Multilib should be valid even if it has the same flag twice";
-
-  ASSERT_TRUE(Multilib().flag("+foo").flag("-foobar").isValid())
-  << "Seemingly conflicting prefixes shouldn't actually conflict";
-}
-
 TEST(MultilibTest, OpEqReflexivity1) {
   Multilib M;
   ASSERT_TRUE(M == M) << "Multilib::operator==() is not reflexive";
@@ -50,40 +33,28 @@
 }
 
 TEST(MultilibTest, OpEqReflexivity3) {
-  Multilib M1, M2;
-  M1.flag("+foo");
-  M2.flag("+foo");
+  Multilib M1({}, {}, {}, 0, {"+foo"});
+  Multilib M2({}, {}, {}, 0, {"+foo"});
   ASSERT_TRUE(M1 == M2) << "Multilibs with the same flag should be the same";
 }
 
 TEST(MultilibTest, OpEqInequivalence1) {
-  Multilib M1, M2;
-  M1.flag("+foo");
-  M2.flag("-foo");
+  Multilib M1({}, {}, {}, 0, {"+foo"});
+  Multilib M2({}, {}, {}, 0, {"-foo"});
   ASSERT_FALSE(M1 == M2) << "Multilibs with conflicting flags are not the same";
   ASSERT_FALSE(M2 == M1)
   << "Multilibs with conflicting flags are not the same (commuted)";
 }
 
 TEST(MultilibTest, OpEqInequivalence2) {
-  Multilib M1, M2;
-  M2.flag("+foo");
+  Multilib M1;
+  Multilib M2({}, {}, {}, 0, {"+foo"});
   ASSERT_FALSE(M1 == M2) << "Flags make Multilibs different";
 }
 
-TEST(MultilibTest, OpEqEquivalence1) {
-  Multilib M1, M2;
-  M1.flag("+foo");
-  M2.flag("+foo").flag("+foo");
-  ASSERT_TRUE(M1 == M2) << "Flag duplication shouldn't affect equivalence";
-  ASSERT_TRUE(M2 == M1)
-  << "Flag duplication shouldn't affect equivalence (commuted)";
-}
-
 TEST(MultilibTest, OpEqEquivalence2) {
-  Multilib M1("64");
-  Multilib M2;
-  M2.gccSuffix("/64");
+  Multilib M1("/64");
+  Multilib M2("/64");
   ASSERT_TRUE(M1 == M2)
   << "Constructor argument must match Multilib::gccSuffix()";
   ASSERT_TRUE(M2 == M1)
@@ -91,9 +62,8 @@
 }
 
 TEST(MultilibTest, OpEqEquivalence3) {
-  Multilib M1("", "32");
-  Multilib M2;
-  M2.osSuffix("/32");
+  Multilib M1("", "/32");
+  Multilib M2("", "/32");
   ASSERT_TRUE(M1 == M2)
   << "Constructor argument must match Multilib::osSuffix()";
   ASSERT_TRUE(M2 == M1)
@@ -101,9 +71,8 @@
 }
 
 TEST(MultilibTest, OpEqEquivalence4) {
-  Multilib M1("", "", "16");
-  Multilib M2;
-  M2.includeSuffix("/16");
+  Multilib M1("", "", "/16");
+  Multilib M2("", "", "/16");
   ASSERT_TRUE(M1 == M2)
   << "Constructor argument must match Multilib::includeSuffix()";
   ASSERT_TRUE(M2 == M1)
@@ -111,31 +80,31 @@
 }
 
 TEST(MultilibTest, OpEqInequivalence3) {
-  Multilib M1("foo");
-  Multilib M2("bar");
+  Multilib M1("/foo");
+  Multilib M2("/bar");
   ASSERT_FALSE(M1 == M2) << "Differing gccSuffixes should be different";
   ASSERT_FALSE(M2 == M1)
   << "Differing gccSuffixes should be different (commuted)";
 }
 
 TEST(MultilibTest, OpEqInequivalence4) {
-  Multilib M1("", "foo");
-  Multilib M2("", "bar");
+  Multilib M1("", "/foo");
+  Multilib M2("", "/bar");
   ASSERT_FALSE(M1 == M2) << "Differing osSuffixes should be different";
   ASSERT_FALSE(M2 == M1)
   << "Differing osSuffixes should be different (commuted)";
 }
 
 TEST(MultilibTest, OpEqInequivalence5) {
-  Multilib M1("", "", "foo");
-  Multilib M2("", "", "bar");

[PATCH] D142905: Change multilib selection algorithm

2023-02-02 Thread Michael Platings via Phabricator via cfe-commits
michaelplatings updated this revision to Diff 494260.
michaelplatings added a comment.

Rebase


Repository:
  rG LLVM Github Monorepo

CHANGES SINCE LAST ACTION
  https://reviews.llvm.org/D142905/new/

https://reviews.llvm.org/D142905

Files:
  clang/include/clang/Driver/Multilib.h
  clang/include/clang/Driver/MultilibBuilder.h
  clang/lib/Driver/Multilib.cpp
  clang/lib/Driver/MultilibBuilder.cpp
  clang/lib/Driver/ToolChains/CommonArgs.cpp
  clang/lib/Driver/ToolChains/Fuchsia.cpp
  clang/unittests/Driver/MultilibBuilderTest.cpp
  clang/unittests/Driver/MultilibTest.cpp

Index: clang/unittests/Driver/MultilibTest.cpp
===
--- clang/unittests/Driver/MultilibTest.cpp
+++ clang/unittests/Driver/MultilibTest.cpp
@@ -33,14 +33,14 @@
 }
 
 TEST(MultilibTest, OpEqReflexivity3) {
-  Multilib M1({}, {}, {}, 0, {"+foo"});
-  Multilib M2({}, {}, {}, 0, {"+foo"});
+  Multilib M1({}, {}, {}, {"+foo"});
+  Multilib M2({}, {}, {}, {"+foo"});
   ASSERT_TRUE(M1 == M2) << "Multilibs with the same flag should be the same";
 }
 
 TEST(MultilibTest, OpEqInequivalence1) {
-  Multilib M1({}, {}, {}, 0, {"+foo"});
-  Multilib M2({}, {}, {}, 0, {"-foo"});
+  Multilib M1({}, {}, {}, {"+foo"});
+  Multilib M2({}, {}, {}, {"-foo"});
   ASSERT_FALSE(M1 == M2) << "Multilibs with conflicting flags are not the same";
   ASSERT_FALSE(M2 == M1)
   << "Multilibs with conflicting flags are not the same (commuted)";
@@ -48,7 +48,7 @@
 
 TEST(MultilibTest, OpEqInequivalence2) {
   Multilib M1;
-  Multilib M2({}, {}, {}, 0, {"+foo"});
+  Multilib M2({}, {}, {}, {"+foo"});
   ASSERT_FALSE(M1 == M2) << "Flags make Multilibs different";
 }
 
@@ -124,7 +124,7 @@
 }
 
 TEST(MultilibTest, Construction3) {
-  Multilib M({}, {}, {}, 0, {"+f1", "+f2", "-f3"});
+  Multilib M({}, {}, {}, {"+f1", "+f2", "-f3"});
   for (Multilib::flags_list::const_iterator I = M.flags().begin(),
 E = M.flags().end();
I != E; ++I) {
@@ -149,8 +149,8 @@
 
 TEST(MultilibTest, SetPriority) {
   MultilibSet MS({
-  Multilib("/foo", {}, {}, 1, {"+foo"}),
-  Multilib("/bar", {}, {}, 2, {"+bar"}),
+  Multilib("/foo", {}, {}, {"+foo"}),
+  Multilib("/bar", {}, {}, {"+bar"}),
   });
   Multilib::flags_list Flags1 = {"+foo", "-bar"};
   Multilib Selection1;
@@ -166,3 +166,24 @@
   ASSERT_TRUE(Selection2.gccSuffix() == "/bar")
   << "Selection picked " << Selection2 << " which was not expected";
 }
+
+TEST(MultilibTest, SelectMultiple) {
+  MultilibSet MS({
+  Multilib("/a", {}, {}, {"x"}),
+  Multilib("/b", {}, {}, {"y"}),
+  });
+  std::vector Selection;
+
+  Selection = MS.select({"x"});
+  ASSERT_EQ(1u, Selection.size());
+  EXPECT_EQ("/a", Selection[0].gccSuffix());
+
+  Selection = MS.select({"y"});
+  ASSERT_EQ(1u, Selection.size());
+  EXPECT_EQ("/b", Selection[0].gccSuffix());
+
+  Selection = MS.select({"y", "x"});
+  ASSERT_EQ(2u, Selection.size());
+  EXPECT_EQ("/a", Selection[0].gccSuffix());
+  EXPECT_EQ("/b", Selection[1].gccSuffix());
+}
Index: clang/unittests/Driver/MultilibBuilderTest.cpp
===
--- clang/unittests/Driver/MultilibBuilderTest.cpp
+++ clang/unittests/Driver/MultilibBuilderTest.cpp
@@ -7,7 +7,7 @@
 //
 //===--===//
 //
-// Unit tests for Multilib and MultilibBuilder
+// Unit tests for MultilibBuilderVariant and MultilibBuilder
 //
 //===--===//
 
@@ -185,14 +185,14 @@
 bool IsSF = I & 0x2;
 Multilib::flags_list Flags;
 if (IsEL)
-  Flags.push_back("+EL");
+  Flags.insert("+EL");
 else
-  Flags.push_back("-EL");
+  Flags.insert("-EL");
 
 if (IsSF)
-  Flags.push_back("+SF");
+  Flags.insert("+SF");
 else
-  Flags.push_back("-SF");
+  Flags.insert("-SF");
 
 Multilib Selection;
 ASSERT_TRUE(MS2.select(Flags, Selection))
@@ -209,3 +209,11 @@
 << "Selection picked " << Selection << " which was not expected ";
   }
 }
+
+TEST(MultilibBuilderTest, PrintArgs) {
+  MultilibBuilderVariant MBV =
+  MultilibBuilderVariant().flag("+x").flag("-y").flag("+a").flag("-b").flag(
+  "+c");
+  auto M = MBV.makeMultilib();
+  ASSERT_EQ(Multilib::arg_list({"-x", "-a", "-c"}), M.getPrintArgs());
+}
Index: clang/lib/Driver/ToolChains/Fuchsia.cpp
===
--- clang/lib/Driver/ToolChains/Fuchsia.cpp
+++ clang/lib/Driver/ToolChains/Fuchsia.cpp
@@ -289,33 +289,33 @@
 void Fuchsia::configureMultilibs(MultilibSet &Multilibs) {
   Multilibs.push_back(Multilib());
   // Use the noexcept variant with -fno-exceptions to avoid the extra overhead.
-  Multilibs.push_back(MultilibBuilderVariant("noexcept", {}, {}, 1)
+  Multilibs.push_back(MultilibBuilderVariant("noexcept", {}, {})
   

[PATCH] D143059: [NFC] Enable selecting multiple multilibs

2023-02-02 Thread Michael Platings via Phabricator via cfe-commits
michaelplatings updated this revision to Diff 494262.
michaelplatings added a comment.

Rebase and change llvm::SmallVector to simply 
llvm::SmallVector


Repository:
  rG LLVM Github Monorepo

CHANGES SINCE LAST ACTION
  https://reviews.llvm.org/D143059/new/

https://reviews.llvm.org/D143059

Files:
  clang/include/clang/Driver/Multilib.h
  clang/include/clang/Driver/ToolChain.h
  clang/lib/Driver/Driver.cpp
  clang/lib/Driver/Multilib.cpp
  clang/lib/Driver/ToolChain.cpp
  clang/lib/Driver/ToolChains/BareMetal.cpp
  clang/lib/Driver/ToolChains/CSKYToolChain.cpp
  clang/lib/Driver/ToolChains/Fuchsia.cpp
  clang/lib/Driver/ToolChains/Gnu.cpp
  clang/lib/Driver/ToolChains/Gnu.h
  clang/lib/Driver/ToolChains/Hexagon.cpp
  clang/lib/Driver/ToolChains/Hurd.cpp
  clang/lib/Driver/ToolChains/Linux.cpp
  clang/lib/Driver/ToolChains/MipsLinux.cpp
  clang/lib/Driver/ToolChains/RISCVToolchain.cpp
  clang/test/Driver/fuchsia.cpp
  clang/unittests/Driver/FuchsiaTest.cpp
  clang/unittests/Driver/MultilibBuilderTest.cpp
  clang/unittests/Driver/MultilibTest.cpp

Index: clang/unittests/Driver/MultilibTest.cpp
===
--- clang/unittests/Driver/MultilibTest.cpp
+++ clang/unittests/Driver/MultilibTest.cpp
@@ -153,18 +153,18 @@
   Multilib("/bar", {}, {}, {"+bar"}),
   });
   Multilib::flags_list Flags1 = {"+foo", "-bar"};
-  Multilib Selection1;
+  llvm::SmallVector Selection1;
   ASSERT_TRUE(MS.select(Flags1, Selection1))
   << "Flag set was {\"+foo\"}, but selection not found";
-  ASSERT_TRUE(Selection1.gccSuffix() == "/foo")
-  << "Selection picked " << Selection1 << " which was not expected";
+  ASSERT_TRUE(Selection1.back().gccSuffix() == "/foo")
+  << "Selection picked " << Selection1.back() << " which was not expected";
 
   Multilib::flags_list Flags2 = {"+foo", "+bar"};
-  Multilib Selection2;
+  llvm::SmallVector Selection2;
   ASSERT_TRUE(MS.select(Flags2, Selection2))
   << "Flag set was {\"+bar\"}, but selection not found";
-  ASSERT_TRUE(Selection2.gccSuffix() == "/bar")
-  << "Selection picked " << Selection2 << " which was not expected";
+  ASSERT_TRUE(Selection2.back().gccSuffix() == "/bar")
+  << "Selection picked " << Selection2.back() << " which was not expected";
 }
 
 TEST(MultilibTest, SelectMultiple) {
@@ -172,17 +172,17 @@
   Multilib("/a", {}, {}, {"x"}),
   Multilib("/b", {}, {}, {"y"}),
   });
-  std::vector Selection;
+  llvm::SmallVector Selection;
 
-  Selection = MS.select({"x"});
+  ASSERT_TRUE(MS.select({"x"}, Selection));
   ASSERT_EQ(1u, Selection.size());
   EXPECT_EQ("/a", Selection[0].gccSuffix());
 
-  Selection = MS.select({"y"});
+  ASSERT_TRUE(MS.select({"y"}, Selection));
   ASSERT_EQ(1u, Selection.size());
   EXPECT_EQ("/b", Selection[0].gccSuffix());
 
-  Selection = MS.select({"y", "x"});
+  ASSERT_TRUE(MS.select({"y", "x"}, Selection));
   ASSERT_EQ(2u, Selection.size());
   EXPECT_EQ("/a", Selection[0].gccSuffix());
   EXPECT_EQ("/b", Selection[1].gccSuffix());
@@ -317,7 +317,7 @@
 
 static bool select(const std::vector &InFlags,
const MultilibSet &MS, const MultilibFlagMap &MFM,
-   Multilib &Selected) {
+   llvm::SmallVector &Selected) {
   Multilib::flags_list Flags(MFM.getFlags(InFlags));
   Flags.insert(InFlags.begin(), InFlags.end());
   return MS.select(Flags, Selected);
@@ -326,7 +326,7 @@
 TEST(MultilibTest, SelectSoft) {
   MultilibSet MS;
   MultilibFlagMap MFM;
-  Multilib Selected;
+  llvm::SmallVector Selected;
   ASSERT_TRUE(parse(MS, MFM, R"(
 variants:
 - dir: s
@@ -346,7 +346,7 @@
 TEST(MultilibTest, SelectSoftFP) {
   MultilibSet MS;
   MultilibFlagMap MFM;
-  Multilib Selected;
+  llvm::SmallVector Selected;
   ASSERT_TRUE(parse(MS, MFM, R"(
 variants:
 - dir: f
@@ -363,7 +363,7 @@
   // with hard float.
   MultilibSet MS;
   MultilibFlagMap MFM;
-  Multilib Selected;
+  llvm::SmallVector Selected;
   ASSERT_TRUE(parse(MS, MFM, R"(
 variants:
 - dir: h
@@ -378,7 +378,7 @@
 TEST(MultilibTest, SelectFloatABI) {
   MultilibSet MS;
   MultilibFlagMap MFM;
-  Multilib Selected;
+  llvm::SmallVector Selected;
   ASSERT_TRUE(parse(MS, MFM, R"(
 variants:
 - dir: s
@@ -399,11 +399,11 @@
   noMatchFlags: [hasfp]
 )"));
   select({"mfloat-abi=soft"}, MS, MFM, Selected);
-  EXPECT_EQ("/s", Selected.gccSuffix());
+  EXPECT_EQ("/s", Selected.back().gccSuffix());
   select({"mfloat-abi=softfp"}, MS, MFM, Selected);
-  EXPECT_EQ("/f", Selected.gccSuffix());
+  EXPECT_EQ("/f", Selected.back().gccSuffix());
   select({"mfloat-abi=hard"}, MS, MFM, Selected);
-  EXPECT_EQ("/h", Selected.gccSuffix());
+  EXPECT_EQ("/h", Selected.back().gccSuffix());
 }
 
 TEST(MultilibTest, SelectFloatABIReversed) {
@@ -411,7 +411,7 @@
   // selected because soft is compatible with softfp and last wins.
   MultilibSet MS;
   MultilibFlagMap MFM;
-  Multilib Selected;
+  llvm::SmallVector Selected;
   ASSERT_TRUE(parse(MS, MFM, R"(
 variants:
 - d

[PATCH] D142933: Add -print-multi-selection-flags argument

2023-02-02 Thread Michael Platings via Phabricator via cfe-commits
michaelplatings marked an inline comment as done.
michaelplatings added a comment.

In D142933#4099587 , @Joe wrote:

> Would it be weird for one target to have the `march=` but anothers not?

Yes I think it would be weird. Potentially you could have a toolchain 
supporting Arm and other architectures so it would be unfortunate for that to 
be inconsistent. I'd very much like the API to work as well as possible across 
all architectures now, because it's going to be hard to change later. It's 
great getting your feedback on this.




Comment at: clang/lib/Driver/Driver.cpp:2213
+  if (C.getArgs().hasArg(options::OPT_print_multi_selection_flags)) {
+for (StringRef Attr : TC.getMultiSelectionFlags(C.getArgs()))
+  llvm::outs() << Attr << '\n';

Joe wrote:
> Do we want to parse the multilib.yaml here so we can print out custom flags 
> as well? It could help diagnose issues people have with them.
Yes, I think that would be an improvement. Might need to go in a later patch 
though.



Comment at: clang/lib/Driver/ToolChain.cpp:204
+Result.push_back(
+clang::driver::getDriverOptTable().getOptionName(Option).str());
+  }

Joe wrote:
> > 
> >> the form `x=y` is already broken when you add the flags from the flag list.
> > 
> > Can you give an example of what you mean by that? Sounds like something 
> > that might need fixing.
> For example the option name for OPT_fexceptions is just `fexceptions`, and 
> this is added directly to `Results`
OK, I was thrown by the word "broken".
The syntax for the multilib flags is derived from the command line arguments so 
I think this is fine.


Repository:
  rG LLVM Github Monorepo

CHANGES SINCE LAST ACTION
  https://reviews.llvm.org/D142933/new/

https://reviews.llvm.org/D142933

___
cfe-commits mailing list
cfe-commits@lists.llvm.org
https://lists.llvm.org/cgi-bin/mailman/listinfo/cfe-commits


[PATCH] D142933: Add -print-multi-selection-flags argument

2023-02-02 Thread Michael Platings via Phabricator via cfe-commits
michaelplatings added a comment.

In D142933#4099043 , @Joe wrote:

> I did briefly try to pass a ToolChain to Gnu.cpp functions, but it became 
> intrusive and had to add it in 5+ places, so unless I'm missing a trick to 
> get the ToolChain from the Driver, my vote would go to the former.

I looked into moving `getMultiSelectionFlags` into the `Driver` class but it 
felt wrong.

I think the place you need to call `getMultiSelectionFlags` is from 
`findRISCVBareMetalMultilibs` and `findRISCVMultilibs`. They will indeed need 
changing to take a `const ToolChain&`. They are called from 
`ScanGCCForMultilibs` which is a method of `GCCInstallationDetector`. 
`GCCInstallationDetector` could have a `const ToolChain&` member. 
`GCCInstallationDetector` is only instantiated from the `Generic_GCC` 
constructor - `Generic_GCC` is a subclass of `ToolChain` so it can pass `*this` 
to the `GCCInstallationDetector` constructor. I think that change would not be 
too intrusive.


Repository:
  rG LLVM Github Monorepo

CHANGES SINCE LAST ACTION
  https://reviews.llvm.org/D142933/new/

https://reviews.llvm.org/D142933

___
cfe-commits mailing list
cfe-commits@lists.llvm.org
https://lists.llvm.org/cgi-bin/mailman/listinfo/cfe-commits


[PATCH] D142933: Add -print-multi-selection-flags argument

2023-02-02 Thread Michael Platings via Phabricator via cfe-commits
michaelplatings updated this revision to Diff 494371.
michaelplatings added a comment.

Put "experimental" in the argument name. The intention is to include the new 
multilib as an experimental feature in LLVM 17 and stabilise it in LLVM 18.

Also remove support for -f(no-)experimental-relative-c++-abi-vtables from the 
new multilib since Fuchsia no longer needs it.


Repository:
  rG LLVM Github Monorepo

CHANGES SINCE LAST ACTION
  https://reviews.llvm.org/D142933/new/

https://reviews.llvm.org/D142933

Files:
  clang/include/clang/Driver/Options.td
  clang/include/clang/Driver/ToolChain.h
  clang/lib/Driver/Driver.cpp
  clang/lib/Driver/ToolChain.cpp
  clang/lib/Driver/ToolChains/Arch/ARM.cpp
  clang/lib/Driver/ToolChains/Arch/ARM.h
  clang/test/Driver/print-multi-selection-flags.c

Index: clang/test/Driver/print-multi-selection-flags.c
===
--- /dev/null
+++ clang/test/Driver/print-multi-selection-flags.c
@@ -0,0 +1,39 @@
+// RUN: %clang -print-multi-selection-flags-experimental --target=aarch64-linux -fc++-abi=itanium -fsanitize=address | FileCheck --check-prefix=CHECK-LINUX %s
+// CHECK-LINUX: fc++-abi=itanium
+// CHECK-LINUX-NEXT: fexceptions
+// CHECK-LINUX-NEXT: frtti
+// CHECK-LINUX-NEXT: fsanitize=address
+// CHECK-LINUX-NEXT: target=aarch64-unknown-linux
+
+// RUN: %clang -print-multi-selection-flags-experimental --target=aarch64-fuchsia -fsanitize=hwaddress | FileCheck --check-prefix=CHECK-FUCHSIA %s
+// CHECK-FUCHSIA: fsanitize=hwaddress
+// CHECK-FUCHSIA: target=aarch64-unknown-fuchsia
+
+// RUN: %clang -print-multi-selection-flags-experimental --target=arm-none-eabi -mfloat-abi=soft -fno-exceptions -fno-rtti | FileCheck --check-prefix=CHECK-ARMV4T %s
+// CHECK-ARMV4T: fno-exceptions
+// CHECK-ARMV4T: fno-rtti
+// CHECK-ARMV4T: mfloat-abi=soft
+// CHECK-ARMV4T: mfpu=none
+// CHECK-ARMV4T: target=armv4t-none-unknown-eabi
+
+// RUN: %clang -print-multi-selection-flags-experimental --target=armv7em-none-eabi -mfloat-abi=softfp | FileCheck --check-prefix=CHECK-SOFTFP %s
+// CHECK-SOFTFP: mfloat-abi=softfp
+// CHECK-SOFTFP: mfpu=fpv4-sp-d16
+// CHECK-SOFTFP: target=thumbv7em-none-unknown-eabi
+
+// RUN: %clang -print-multi-selection-flags-experimental --target=arm-none-eabihf -march=armv7em -mfpu=fpv5-d16 | FileCheck --check-prefix=CHECK-HARD %s
+// CHECK-HARD: mfloat-abi=hard
+// CHECK-HARD: mfpu=fpv5-d16
+// CHECK-HARD: target=thumbv7em-none-unknown-eabihf
+
+// RUN: %clang -print-multi-selection-flags-experimental --target=arm-none-eabi -mfloat-abi=hard -march=armv8.1m.main+mve.fp | FileCheck --check-prefix=CHECK-MVE %s
+// CHECK-MVE: march=+mve
+// CHECK-MVE: march=+mve.fp
+// CHECK-MVE: mfloat-abi=hard
+// CHECK-MVE: mfpu=fp-armv8-fullfp16-sp-d16
+// CHECK-MVE: target=thumbv8.1m.main-none-unknown-eabihf
+
+// RUN: %clang -print-multi-selection-flags-experimental --target=arm-none-eabi -march=armv8.1m.main+mve+nofp | FileCheck --check-prefix=CHECK-MVENOFP %s
+// CHECK-MVENOFP: march=+mve
+// CHECK-MVENOFP-NOT: march=+mve.fp
+// CHECK-MVENOFP: mfpu=none
Index: clang/lib/Driver/ToolChains/Arch/ARM.h
===
--- clang/lib/Driver/ToolChains/Arch/ARM.h
+++ clang/lib/Driver/ToolChains/Arch/ARM.h
@@ -64,9 +64,11 @@
 void getARMArchCPUFromArgs(const llvm::opt::ArgList &Args,
llvm::StringRef &Arch, llvm::StringRef &CPU,
bool FromAs = false);
+// Optionally returns the FPUKind
 void getARMTargetFeatures(const Driver &D, const llvm::Triple &Triple,
   const llvm::opt::ArgList &Args,
-  std::vector &Features, bool ForAS);
+  std::vector &Features, bool ForAS,
+  unsigned *OutFPUKind = nullptr);
 int getARMSubArchVersionNumber(const llvm::Triple &Triple);
 bool isARMMProfile(const llvm::Triple &Triple);
 bool isARMAProfile(const llvm::Triple &Triple);
Index: clang/lib/Driver/ToolChains/Arch/ARM.cpp
===
--- clang/lib/Driver/ToolChains/Arch/ARM.cpp
+++ clang/lib/Driver/ToolChains/Arch/ARM.cpp
@@ -438,7 +438,8 @@
 
 void arm::getARMTargetFeatures(const Driver &D, const llvm::Triple &Triple,
const ArgList &Args,
-   std::vector &Features, bool ForAS) {
+   std::vector &Features, bool ForAS,
+   unsigned *OutFPUKind) {
   bool KernelOrKext =
   Args.hasArg(options::OPT_mkernel, options::OPT_fapple_kext);
   arm::FloatABI ABI = arm::getARMFloatABI(D, Triple, Args);
@@ -643,6 +644,7 @@
 {"-dotprod", "-fp16fml", "-bf16", "-mve.fp"});
 if (!hasIntegerMVE(Features))
   Features.emplace_back("-fpregs");
+FPUID = llvm::ARM::FK_NONE;
   }
 
   // En/disable crc code generation.
@@ -899,6 +901,10 @@
 
   if (Args.getLastArg(options::OPT_

[PATCH] D142932: Multilib YAML parsing

2023-02-02 Thread Michael Platings via Phabricator via cfe-commits
michaelplatings updated this revision to Diff 494406.
michaelplatings added a comment.

Move the regular expression flag matching functionality into MutlilibSet. This 
(a) simplifies the code for loading from multilib.yaml; and (b) makes the flag 
matching functionality easier to access.


Repository:
  rG LLVM Github Monorepo

CHANGES SINCE LAST ACTION
  https://reviews.llvm.org/D142932/new/

https://reviews.llvm.org/D142932

Files:
  clang/include/clang/Driver/Multilib.h
  clang/lib/Driver/Multilib.cpp
  clang/unittests/Driver/MultilibTest.cpp

Index: clang/unittests/Driver/MultilibTest.cpp
===
--- clang/unittests/Driver/MultilibTest.cpp
+++ clang/unittests/Driver/MultilibTest.cpp
@@ -187,3 +187,340 @@
   EXPECT_EQ("/a", Selection[0].gccSuffix());
   EXPECT_EQ("/b", Selection[1].gccSuffix());
 }
+
+static void diagnosticCallback(const llvm::SMDiagnostic &D, void *Out) {
+  *reinterpret_cast(Out) = D.getMessage();
+}
+
+static bool parse(MultilibSet &MS, std::string &Diagnostic, const char *Data) {
+  return MS.parse(llvm::MemoryBufferRef(Data, "TEST"), diagnosticCallback,
+  &Diagnostic);
+}
+
+static bool parse(MultilibSet &MS, const char *Data) {
+  return MS.parse(llvm::MemoryBufferRef(Data, "TEST"));
+}
+
+TEST(MultilibTest, ParseInvalid) {
+  std::string Diagnostic;
+
+  MultilibSet MS;
+  EXPECT_FALSE(parse(MS, Diagnostic, R"(
+variants:
+- dir: /abc
+  flags: []
+  printArgs: []
+)"));
+  EXPECT_TRUE(StringRef(Diagnostic).contains("paths must be relative"))
+  << Diagnostic;
+
+  EXPECT_FALSE(parse(MS, Diagnostic, R"(
+variants:
+- flags: []
+  printArgs: []
+)"));
+  EXPECT_TRUE(StringRef(Diagnostic).contains("missing required key 'dir'"))
+  << Diagnostic;
+
+  EXPECT_FALSE(parse(MS, Diagnostic, R"(
+variants:
+- dir: .
+  printArgs: []
+)"));
+  EXPECT_TRUE(StringRef(Diagnostic).contains("missing required key 'flags'"))
+  << Diagnostic;
+
+  EXPECT_FALSE(parse(MS, Diagnostic, R"(
+variants:
+- dir: .
+  flags: []
+)"));
+  EXPECT_TRUE(
+  StringRef(Diagnostic).contains("missing required key 'printArgs'"))
+  << Diagnostic;
+
+  EXPECT_FALSE(parse(MS, Diagnostic, R"(
+flagMap:
+- regex: abc
+)"));
+  EXPECT_TRUE(
+  StringRef(Diagnostic)
+  .contains("value required for 'matchFlags' or 'noMatchFlags'"))
+  << Diagnostic;
+
+  EXPECT_FALSE(parse(MS, Diagnostic, R"(
+flagMap:
+- dir: .
+  regex: '('
+  printArgs: []
+
+)"));
+  EXPECT_TRUE(StringRef(Diagnostic).contains("parentheses not balanced"))
+  << Diagnostic;
+}
+
+TEST(MultilibTest, Parse) {
+  MultilibSet MS;
+  EXPECT_TRUE(parse(MS, R"(
+variants:
+- dir: .
+  flags: []
+  printArgs: []
+)"));
+  EXPECT_EQ(1U, MS.size());
+  EXPECT_EQ("", MS.begin()->gccSuffix());
+
+  EXPECT_TRUE(parse(MS, R"(
+variants:
+- dir: abc
+  flags: []
+  printArgs: []
+)"));
+  EXPECT_EQ(1U, MS.size());
+  EXPECT_EQ("/abc", MS.begin()->gccSuffix());
+
+  EXPECT_TRUE(parse(MS, R"(
+variants:
+- dir: pqr
+  flags: []
+  printArgs: [-mfloat-abi=soft]
+)"));
+  EXPECT_EQ(1U, MS.size());
+  EXPECT_EQ("/pqr", MS.begin()->gccSuffix());
+  EXPECT_EQ(std::vector({"-mfloat-abi=soft"}),
+MS.begin()->getPrintArgs());
+
+  EXPECT_TRUE(parse(MS, R"(
+variants:
+- dir: pqr
+  flags: []
+  printArgs: [-mfloat-abi=soft, -fno-exceptions]
+)"));
+  EXPECT_EQ(1U, MS.size());
+  EXPECT_EQ(std::vector({"-mfloat-abi=soft", "-fno-exceptions"}),
+MS.begin()->getPrintArgs());
+
+  EXPECT_TRUE(parse(MS, R"(
+variants:
+- dir: a
+  flags: []
+  printArgs: []
+- dir: b
+  flags: []
+  printArgs: []
+)"));
+  EXPECT_EQ(2U, MS.size());
+}
+
+TEST(MultilibTest, SelectSoft) {
+  MultilibSet MS;
+  Multilib Selected;
+  ASSERT_TRUE(parse(MS, R"(
+variants:
+- dir: s
+  flags: [softabi]
+  printArgs: []
+flagMap:
+- regex: mfloat-abi=soft
+  matchFlags: [softabi]
+- regex: mfloat-abi=softfp
+  matchFlags: [softabi]
+)"));
+  EXPECT_TRUE(MS.select({"mfloat-abi=soft"}, Selected));
+  EXPECT_TRUE(MS.select({"mfloat-abi=softfp"}, Selected));
+  EXPECT_FALSE(MS.select({"mfloat-abi=hard"}, Selected));
+}
+
+TEST(MultilibTest, SelectSoftFP) {
+  MultilibSet MS;
+  Multilib Selected;
+  ASSERT_TRUE(parse(MS, R"(
+variants:
+- dir: f
+  flags: [mfloat-abi=softfp]
+  printArgs: []
+)"));
+  EXPECT_FALSE(MS.select({"mfloat-abi=soft"}, Selected));
+  EXPECT_TRUE(MS.select({"mfloat-abi=softfp"}, Selected));
+  EXPECT_FALSE(MS.select({"mfloat-abi=hard"}, Selected));
+}
+
+TEST(MultilibTest, SelectHard) {
+  // If hard float is all that's available then select that only if compiling
+  // with hard float.
+  MultilibSet MS;
+  Multilib Selected;
+  ASSERT_TRUE(parse(MS, R"(
+variants:
+- dir: h
+  flags: [mfloat-abi=hard]
+  printArgs: []
+)"));
+  EXPECT_FALSE(MS.select({"mfloat-abi=soft"}, Selected));
+  EXPECT_FALSE(MS.select({"mfloat-abi=softfp"}, Selected));
+  EXPECT_TRUE(MS.select({"mfloat-abi=hard"}, Selected));
+}
+
+TEST(MultilibTest, SelectFloatABI) {
+  

[PATCH] D142986: Enable multilib.yaml in the BareMetal ToolChain

2023-02-02 Thread Michael Platings via Phabricator via cfe-commits
michaelplatings updated this revision to Diff 494414.
michaelplatings added a comment.

Rebase


Repository:
  rG LLVM Github Monorepo

CHANGES SINCE LAST ACTION
  https://reviews.llvm.org/D142986/new/

https://reviews.llvm.org/D142986

Files:
  clang/lib/Driver/ToolChain.cpp
  clang/lib/Driver/ToolChains/Arch/ARM.cpp
  clang/lib/Driver/ToolChains/Arch/ARM.h
  clang/lib/Driver/ToolChains/BareMetal.cpp
  clang/test/Driver/Inputs/baremetal_multilib/multilib.yaml
  clang/test/Driver/baremetal-multilib.cpp
  clang/test/Driver/baremetal.cpp

Index: clang/test/Driver/baremetal.cpp
===
--- clang/test/Driver/baremetal.cpp
+++ clang/test/Driver/baremetal.cpp
@@ -118,9 +118,9 @@
 // Verify that the bare metal driver does not include any host system paths:
 // CHECK-AARCH64-NO-HOST-INC: InstalledDir: [[INSTALLEDDIR:.+]]
 // CHECK-AARCH64-NO-HOST-INC: "-resource-dir" "[[RESOURCE:[^"]+]]"
-// CHECK-AARCH64-NO-HOST-INC-SAME: "-internal-isystem" "[[INSTALLEDDIR]]{{[/\\]+}}..{{[/\\]+}}lib{{[/\\]+}}clang-runtimes{{[/\\]+}}aarch64-none-elf{{[/\\]+}}include{{[/\\]+}}c++{{[/\\]+}}v1"
+// CHECK-AARCH64-NO-HOST-INC-SAME: "-internal-isystem" "[[INSTALLEDDIR]]{{[/\\]+}}..{{[/\\]+}}lib{{[/\\]+}}clang-runtimes{{[/\\]+[^"]*}}include{{[/\\]+}}c++{{[/\\]+}}v1"
 // CHECK-AARCH64-NO-HOST-INC-SAME: "-internal-isystem" "[[RESOURCE]]{{[/\\]+}}include"
-// CHECK-AARCH64-NO-HOST-INC-SAME: "-internal-isystem" "[[INSTALLEDDIR]]{{[/\\]+}}..{{[/\\]+}}lib{{[/\\]+}}clang-runtimes{{[/\\]+}}aarch64-none-elf{{[/\\]+}}include"
+// CHECK-AARCH64-NO-HOST-INC-SAME: "-internal-isystem" "[[INSTALLEDDIR]]{{[/\\]+}}..{{[/\\]+}}lib{{[/\\]+}}clang-runtimes{{[/\\]+[^"]*}}include"
 
 // RUN: %clang %s -### --target=riscv64-unknown-elf -o %t.out -L some/directory/user/asked/for \
 // RUN: --sysroot=%S/Inputs/basic_riscv64_tree/riscv64-unknown-elf 2>&1 \
Index: clang/test/Driver/baremetal-multilib.cpp
===
--- /dev/null
+++ clang/test/Driver/baremetal-multilib.cpp
@@ -0,0 +1,45 @@
+// REQUIRES: shell
+// UNSUPPORTED: system-windows
+
+// RUN: rm -rf %T/baremetal_multilib
+// RUN: mkdir -p %T/baremetal_multilib/bin
+// RUN: mkdir -p %T/baremetal_multilib/lib/clang-runtimes/arm-none-eabi/thumb/v8-m.main/fp/lib
+// RUN: touch %T/baremetal_multilib/lib/clang-runtimes/arm-none-eabi/thumb/v8-m.main/fp/lib/libclang_rt.builtins.a
+// RUN: ln -s %clang %T/baremetal_multilib/bin/clang
+// RUN: ln -s %S/Inputs/baremetal_multilib/multilib.yaml %T/baremetal_multilib/lib/clang-runtimes/multilib.yaml
+
+// RUN: %T/baremetal_multilib/bin/clang -no-canonical-prefixes %s -### -o %t.o 2>&1 \
+// RUN: --target=thumbv8m.main-none-eabihf --sysroot= \
+// RUN:   | FileCheck %s
+// CHECK: "{{.*}}clang{{.*}}" "-cc1" "-triple" "thumbv8m.main-none-unknown-eabihf"
+// CHECK-SAME: "-internal-isystem" "{{.*}}/baremetal_multilib/bin/../lib/clang-runtimes/arm-none-eabi/thumb/v8-m.main/fp/include/c++/v1"
+// CHECK-SAME: "-internal-isystem" "{{.*}}/baremetal_multilib/bin/../lib/clang-runtimes/arm-none-eabi/thumb/v8-m.main/fp/include"
+// CHECK-SAME: "-x" "c++" "{{.*}}/baremetal-multilib.cpp"
+// CHECK-NEXT: "{{[^"]*}}ld{{(\.(lld|bfd|gold))?}}{{(\.exe)?}}" "{{.*}}.o" "-Bstatic"
+// CHECK-SAME: "-L{{.*}}/baremetal_multilib/bin/../lib/clang-runtimes/arm-none-eabi/thumb/v8-m.main/fp/lib"
+// CHECK-SAME: "-lc" "-lm" "-lclang_rt.builtins"
+// CHECK-SAME: "-o" "{{.*}}.o"
+
+// RUN: %T/baremetal_multilib/bin/clang -no-canonical-prefixes -print-multi-directory 2>&1 \
+// RUN: --target=thumbv8m.main-none-eabihf --sysroot= \
+// RUN:   | FileCheck --check-prefix=CHECK-PRINT-MULTI-DIRECTORY %s
+// CHECK-PRINT-MULTI-DIRECTORY: arm-none-eabi/thumb/v8-m.main/fp
+
+// RUN: %T/baremetal_multilib/bin/clang -no-canonical-prefixes -print-multi-lib 2>&1 \
+// RUN: --target=arm-none-eabi --sysroot= \
+// RUN:   | FileCheck --check-prefix=CHECK-PRINT-MULTI-LIB %s
+// CHECK-PRINT-MULTI-LIB: arm-none-eabi/thumb/v6-m/nofp;@-target=thumbv6m-none-eabi@mfloat-abi=soft
+// CHECK-PRINT-MULTI-LIB: arm-none-eabi/thumb/v7-m/nofp;@-target=thumbv7m-none-eabi@mfloat-abi=soft
+// CHECK-PRINT-MULTI-LIB: arm-none-eabi/thumb/v7e-m/nofp;@-target=thumbv7em-none-eabi@mfloat-abi=soft@mfpu=none
+// CHECK-PRINT-MULTI-LIB: arm-none-eabi/thumb/v8-m.main/nofp;@-target=arm-none-eabi@mfloat-abi=soft@march=armv8m.main+nofp
+// CHECK-PRINT-MULTI-LIB: arm-none-eabi/thumb/v8.1-m.main/nofp/nomve;@-target=arm-none-eabi@mfloat-abi=soft@march=armv8.1m.main+nofp+nomve
+// CHECK-PRINT-MULTI-LIB: arm-none-eabi/thumb/v7e-m/fpv4_sp_d16;@-target=thumbv7em-none-eabihf@mfpu=fpv4-sp-d16
+// CHECK-PRINT-MULTI-LIB: arm-none-eabi/thumb/v7e-m/fpv5_d16;@-target=thumbv7em-none-eabihf@mfpu=fpv5-d16
+// CHECK-PRINT-MULTI-LIB: arm-none-eabi/thumb/v8-m.main/fp;@-target=thumbv8m.main-none-eabihf
+// CHECK-PRINT-MULTI-LIB: arm-none-eabi/thumb/v8.1-m.main/fp;@-target=thumbv8.1m.main-none-eabihf
+// CHECK-PRINT-MULTI-LIB: arm-none-eabi/th

[PATCH] D143059: [NFC] Enable selecting multiple multilibs

2023-02-02 Thread Michael Platings via Phabricator via cfe-commits
michaelplatings updated this revision to Diff 494416.
michaelplatings added a comment.

Rebase


Repository:
  rG LLVM Github Monorepo

CHANGES SINCE LAST ACTION
  https://reviews.llvm.org/D143059/new/

https://reviews.llvm.org/D143059

Files:
  clang/include/clang/Driver/Multilib.h
  clang/include/clang/Driver/ToolChain.h
  clang/lib/Driver/Driver.cpp
  clang/lib/Driver/Multilib.cpp
  clang/lib/Driver/ToolChain.cpp
  clang/lib/Driver/ToolChains/BareMetal.cpp
  clang/lib/Driver/ToolChains/CSKYToolChain.cpp
  clang/lib/Driver/ToolChains/Fuchsia.cpp
  clang/lib/Driver/ToolChains/Gnu.cpp
  clang/lib/Driver/ToolChains/Gnu.h
  clang/lib/Driver/ToolChains/Hexagon.cpp
  clang/lib/Driver/ToolChains/Hurd.cpp
  clang/lib/Driver/ToolChains/Linux.cpp
  clang/lib/Driver/ToolChains/MipsLinux.cpp
  clang/lib/Driver/ToolChains/RISCVToolchain.cpp
  clang/test/Driver/fuchsia.cpp
  clang/unittests/Driver/FuchsiaTest.cpp
  clang/unittests/Driver/MultilibBuilderTest.cpp
  clang/unittests/Driver/MultilibTest.cpp

Index: clang/unittests/Driver/MultilibTest.cpp
===
--- clang/unittests/Driver/MultilibTest.cpp
+++ clang/unittests/Driver/MultilibTest.cpp
@@ -153,18 +153,18 @@
   Multilib("/bar", {}, {}, {"+bar"}),
   });
   Multilib::flags_list Flags1 = {"+foo", "-bar"};
-  Multilib Selection1;
+  llvm::SmallVector Selection1;
   ASSERT_TRUE(MS.select(Flags1, Selection1))
   << "Flag set was {\"+foo\"}, but selection not found";
-  ASSERT_TRUE(Selection1.gccSuffix() == "/foo")
-  << "Selection picked " << Selection1 << " which was not expected";
+  ASSERT_TRUE(Selection1.back().gccSuffix() == "/foo")
+  << "Selection picked " << Selection1.back() << " which was not expected";
 
   Multilib::flags_list Flags2 = {"+foo", "+bar"};
-  Multilib Selection2;
+  llvm::SmallVector Selection2;
   ASSERT_TRUE(MS.select(Flags2, Selection2))
   << "Flag set was {\"+bar\"}, but selection not found";
-  ASSERT_TRUE(Selection2.gccSuffix() == "/bar")
-  << "Selection picked " << Selection2 << " which was not expected";
+  ASSERT_TRUE(Selection2.back().gccSuffix() == "/bar")
+  << "Selection picked " << Selection2.back() << " which was not expected";
 }
 
 TEST(MultilibTest, SelectMultiple) {
@@ -172,17 +172,17 @@
   Multilib("/a", {}, {}, {"x"}),
   Multilib("/b", {}, {}, {"y"}),
   });
-  std::vector Selection;
+  llvm::SmallVector Selection;
 
-  Selection = MS.select({"x"});
+  ASSERT_TRUE(MS.select({"x"}, Selection));
   ASSERT_EQ(1u, Selection.size());
   EXPECT_EQ("/a", Selection[0].gccSuffix());
 
-  Selection = MS.select({"y"});
+  ASSERT_TRUE(MS.select({"y"}, Selection));
   ASSERT_EQ(1u, Selection.size());
   EXPECT_EQ("/b", Selection[0].gccSuffix());
 
-  Selection = MS.select({"y", "x"});
+  ASSERT_TRUE(MS.select({"y", "x"}, Selection));
   ASSERT_EQ(2u, Selection.size());
   EXPECT_EQ("/a", Selection[0].gccSuffix());
   EXPECT_EQ("/b", Selection[1].gccSuffix());
@@ -314,7 +314,7 @@
 
 TEST(MultilibTest, SelectSoft) {
   MultilibSet MS;
-  Multilib Selected;
+  llvm::SmallVector Selected;
   ASSERT_TRUE(parse(MS, R"(
 variants:
 - dir: s
@@ -333,7 +333,7 @@
 
 TEST(MultilibTest, SelectSoftFP) {
   MultilibSet MS;
-  Multilib Selected;
+  llvm::SmallVector Selected;
   ASSERT_TRUE(parse(MS, R"(
 variants:
 - dir: f
@@ -349,7 +349,7 @@
   // If hard float is all that's available then select that only if compiling
   // with hard float.
   MultilibSet MS;
-  Multilib Selected;
+  llvm::SmallVector Selected;
   ASSERT_TRUE(parse(MS, R"(
 variants:
 - dir: h
@@ -363,7 +363,7 @@
 
 TEST(MultilibTest, SelectFloatABI) {
   MultilibSet MS;
-  Multilib Selected;
+  llvm::SmallVector Selected;
   ASSERT_TRUE(parse(MS, R"(
 variants:
 - dir: s
@@ -384,18 +384,18 @@
   noMatchFlags: [hasfp]
 )"));
   MS.select({"mfloat-abi=soft"}, Selected);
-  EXPECT_EQ("/s", Selected.gccSuffix());
+  EXPECT_EQ("/s", Selected.back().gccSuffix());
   MS.select({"mfloat-abi=softfp"}, Selected);
-  EXPECT_EQ("/f", Selected.gccSuffix());
+  EXPECT_EQ("/f", Selected.back().gccSuffix());
   MS.select({"mfloat-abi=hard"}, Selected);
-  EXPECT_EQ("/h", Selected.gccSuffix());
+  EXPECT_EQ("/h", Selected.back().gccSuffix());
 }
 
 TEST(MultilibTest, SelectFloatABIReversed) {
   // If soft is specified after softfp then softfp will never be
   // selected because soft is compatible with softfp and last wins.
   MultilibSet MS;
-  Multilib Selected;
+  llvm::SmallVector Selected;
   ASSERT_TRUE(parse(MS, R"(
 variants:
 - dir: h
@@ -416,11 +416,11 @@
   noMatchFlags: [hasfp]
 )"));
   MS.select({"mfloat-abi=soft"}, Selected);
-  EXPECT_EQ("/s", Selected.gccSuffix());
+  EXPECT_EQ("/s", Selected.back().gccSuffix());
   MS.select({"mfloat-abi=softfp"}, Selected);
-  EXPECT_EQ("/s", Selected.gccSuffix());
+  EXPECT_EQ("/s", Selected.back().gccSuffix());
   MS.select({"mfloat-abi=hard"}, Selected);
-  EXPECT_EQ("/h", Selected.gccSuffix());
+  EXPECT_EQ("/h", Selected.back().gccSuffix

[PATCH] D142933: Add -print-multi-selection-flags argument

2023-02-02 Thread Michael Platings via Phabricator via cfe-commits
michaelplatings updated this revision to Diff 494420.
michaelplatings added a comment.

Print flags expanded by any regular expression matchers in multilib.yaml


Repository:
  rG LLVM Github Monorepo

CHANGES SINCE LAST ACTION
  https://reviews.llvm.org/D142933/new/

https://reviews.llvm.org/D142933

Files:
  clang/include/clang/Driver/Options.td
  clang/include/clang/Driver/ToolChain.h
  clang/lib/Driver/Driver.cpp
  clang/lib/Driver/ToolChain.cpp
  clang/lib/Driver/ToolChains/Arch/ARM.cpp
  clang/lib/Driver/ToolChains/Arch/ARM.h
  clang/test/Driver/print-multi-selection-flags.c

Index: clang/test/Driver/print-multi-selection-flags.c
===
--- /dev/null
+++ clang/test/Driver/print-multi-selection-flags.c
@@ -0,0 +1,39 @@
+// RUN: %clang -print-multi-selection-flags-experimental --target=aarch64-linux -fc++-abi=itanium -fsanitize=address | FileCheck --check-prefix=CHECK-LINUX %s
+// CHECK-LINUX: fc++-abi=itanium
+// CHECK-LINUX-NEXT: fexceptions
+// CHECK-LINUX-NEXT: frtti
+// CHECK-LINUX-NEXT: fsanitize=address
+// CHECK-LINUX-NEXT: target=aarch64-unknown-linux
+
+// RUN: %clang -print-multi-selection-flags-experimental --target=aarch64-fuchsia -fsanitize=hwaddress | FileCheck --check-prefix=CHECK-FUCHSIA %s
+// CHECK-FUCHSIA: fsanitize=hwaddress
+// CHECK-FUCHSIA: target=aarch64-unknown-fuchsia
+
+// RUN: %clang -print-multi-selection-flags-experimental --target=arm-none-eabi -mfloat-abi=soft -fno-exceptions -fno-rtti | FileCheck --check-prefix=CHECK-ARMV4T %s
+// CHECK-ARMV4T: fno-exceptions
+// CHECK-ARMV4T: fno-rtti
+// CHECK-ARMV4T: mfloat-abi=soft
+// CHECK-ARMV4T: mfpu=none
+// CHECK-ARMV4T: target=armv4t-none-unknown-eabi
+
+// RUN: %clang -print-multi-selection-flags-experimental --target=armv7em-none-eabi -mfloat-abi=softfp | FileCheck --check-prefix=CHECK-SOFTFP %s
+// CHECK-SOFTFP: mfloat-abi=softfp
+// CHECK-SOFTFP: mfpu=fpv4-sp-d16
+// CHECK-SOFTFP: target=thumbv7em-none-unknown-eabi
+
+// RUN: %clang -print-multi-selection-flags-experimental --target=arm-none-eabihf -march=armv7em -mfpu=fpv5-d16 | FileCheck --check-prefix=CHECK-HARD %s
+// CHECK-HARD: mfloat-abi=hard
+// CHECK-HARD: mfpu=fpv5-d16
+// CHECK-HARD: target=thumbv7em-none-unknown-eabihf
+
+// RUN: %clang -print-multi-selection-flags-experimental --target=arm-none-eabi -mfloat-abi=hard -march=armv8.1m.main+mve.fp | FileCheck --check-prefix=CHECK-MVE %s
+// CHECK-MVE: march=+mve
+// CHECK-MVE: march=+mve.fp
+// CHECK-MVE: mfloat-abi=hard
+// CHECK-MVE: mfpu=fp-armv8-fullfp16-sp-d16
+// CHECK-MVE: target=thumbv8.1m.main-none-unknown-eabihf
+
+// RUN: %clang -print-multi-selection-flags-experimental --target=arm-none-eabi -march=armv8.1m.main+mve+nofp | FileCheck --check-prefix=CHECK-MVENOFP %s
+// CHECK-MVENOFP: march=+mve
+// CHECK-MVENOFP-NOT: march=+mve.fp
+// CHECK-MVENOFP: mfpu=none
Index: clang/lib/Driver/ToolChains/Arch/ARM.h
===
--- clang/lib/Driver/ToolChains/Arch/ARM.h
+++ clang/lib/Driver/ToolChains/Arch/ARM.h
@@ -64,9 +64,11 @@
 void getARMArchCPUFromArgs(const llvm::opt::ArgList &Args,
llvm::StringRef &Arch, llvm::StringRef &CPU,
bool FromAs = false);
+// Optionally returns the FPUKind
 void getARMTargetFeatures(const Driver &D, const llvm::Triple &Triple,
   const llvm::opt::ArgList &Args,
-  std::vector &Features, bool ForAS);
+  std::vector &Features, bool ForAS,
+  unsigned *OutFPUKind = nullptr);
 int getARMSubArchVersionNumber(const llvm::Triple &Triple);
 bool isARMMProfile(const llvm::Triple &Triple);
 bool isARMAProfile(const llvm::Triple &Triple);
Index: clang/lib/Driver/ToolChains/Arch/ARM.cpp
===
--- clang/lib/Driver/ToolChains/Arch/ARM.cpp
+++ clang/lib/Driver/ToolChains/Arch/ARM.cpp
@@ -438,7 +438,8 @@
 
 void arm::getARMTargetFeatures(const Driver &D, const llvm::Triple &Triple,
const ArgList &Args,
-   std::vector &Features, bool ForAS) {
+   std::vector &Features, bool ForAS,
+   unsigned *OutFPUKind) {
   bool KernelOrKext =
   Args.hasArg(options::OPT_mkernel, options::OPT_fapple_kext);
   arm::FloatABI ABI = arm::getARMFloatABI(D, Triple, Args);
@@ -643,6 +644,7 @@
 {"-dotprod", "-fp16fml", "-bf16", "-mve.fp"});
 if (!hasIntegerMVE(Features))
   Features.emplace_back("-fpregs");
+FPUID = llvm::ARM::FK_NONE;
   }
 
   // En/disable crc code generation.
@@ -899,6 +901,10 @@
 
   if (Args.getLastArg(options::OPT_mno_bti_at_return_twice))
 Features.push_back("+no-bti-at-return-twice");
+
+  if (OutFPUKind) {
+*OutFPUKind = FPUID;
+  }
 }
 
 std::string arm::getARMArch(StringRef Arch, const llvm::Triple &Triple

[PATCH] D142933: Add -print-multi-selection-flags argument

2023-02-02 Thread Michael Platings via Phabricator via cfe-commits
michaelplatings marked an inline comment as done.
michaelplatings added inline comments.



Comment at: clang/lib/Driver/Driver.cpp:2213
+  if (C.getArgs().hasArg(options::OPT_print_multi_selection_flags)) {
+for (StringRef Attr : TC.getMultiSelectionFlags(C.getArgs()))
+  llvm::outs() << Attr << '\n';

michaelplatings wrote:
> Joe wrote:
> > Do we want to parse the multilib.yaml here so we can print out custom flags 
> > as well? It could help diagnose issues people have with them.
> Yes, I think that would be an improvement. Might need to go in a later patch 
> though.
Should be working now.


Repository:
  rG LLVM Github Monorepo

CHANGES SINCE LAST ACTION
  https://reviews.llvm.org/D142933/new/

https://reviews.llvm.org/D142933

___
cfe-commits mailing list
cfe-commits@lists.llvm.org
https://lists.llvm.org/cgi-bin/mailman/listinfo/cfe-commits


[PATCH] D142933: Add -print-multi-selection-flags argument

2023-02-03 Thread Michael Platings via Phabricator via cfe-commits
michaelplatings updated this revision to Diff 494610.
michaelplatings added a comment.

Bugfix: if -msoft-float is set then -mfpu should be none.


Repository:
  rG LLVM Github Monorepo

CHANGES SINCE LAST ACTION
  https://reviews.llvm.org/D142933/new/

https://reviews.llvm.org/D142933

Files:
  clang/include/clang/Driver/Options.td
  clang/include/clang/Driver/ToolChain.h
  clang/lib/Driver/Driver.cpp
  clang/lib/Driver/ToolChain.cpp
  clang/lib/Driver/ToolChains/Arch/ARM.cpp
  clang/lib/Driver/ToolChains/Arch/ARM.h
  clang/test/Driver/print-multi-selection-flags.c

Index: clang/test/Driver/print-multi-selection-flags.c
===
--- /dev/null
+++ clang/test/Driver/print-multi-selection-flags.c
@@ -0,0 +1,44 @@
+// RUN: %clang -print-multi-selection-flags-experimental --target=aarch64-linux -fc++-abi=itanium -fsanitize=address | FileCheck --check-prefix=CHECK-LINUX %s
+// CHECK-LINUX: fc++-abi=itanium
+// CHECK-LINUX-NEXT: fexceptions
+// CHECK-LINUX-NEXT: frtti
+// CHECK-LINUX-NEXT: fsanitize=address
+// CHECK-LINUX-NEXT: target=aarch64-unknown-linux
+
+// RUN: %clang -print-multi-selection-flags-experimental --target=aarch64-fuchsia -fsanitize=hwaddress | FileCheck --check-prefix=CHECK-FUCHSIA %s
+// CHECK-FUCHSIA: fsanitize=hwaddress
+// CHECK-FUCHSIA: target=aarch64-unknown-fuchsia
+
+// RUN: %clang -print-multi-selection-flags-experimental --target=arm-none-eabi -mfloat-abi=soft -fno-exceptions -fno-rtti | FileCheck --check-prefix=CHECK-ARMV4T %s
+// CHECK-ARMV4T: fno-exceptions
+// CHECK-ARMV4T: fno-rtti
+// CHECK-ARMV4T: mfloat-abi=soft
+// CHECK-ARMV4T: mfpu=none
+// CHECK-ARMV4T: target=armv4t-none-unknown-eabi
+
+// RUN: %clang -print-multi-selection-flags-experimental --target=armv7em-none-eabi -mfloat-abi=softfp | FileCheck --check-prefix=CHECK-SOFTFP %s
+// CHECK-SOFTFP: mfloat-abi=softfp
+// CHECK-SOFTFP: mfpu=fpv4-sp-d16
+// CHECK-SOFTFP: target=thumbv7em-none-unknown-eabi
+
+// RUN: %clang -print-multi-selection-flags-experimental --target=arm-none-eabihf -march=armv7em -mfpu=fpv5-d16 | FileCheck --check-prefix=CHECK-HARD %s
+// CHECK-HARD: mfloat-abi=hard
+// CHECK-HARD: mfpu=fpv5-d16
+// CHECK-HARD: target=thumbv7em-none-unknown-eabihf
+
+// RUN: %clang -print-multi-selection-flags-experimental --target=arm-none-eabi -mfloat-abi=soft -march=armv8-m.main+nofp | FileCheck --check-prefix=CHECK-V8MMAIN-NOFP %s
+// CHECK-V8MMAIN-NOFP: mfloat-abi=soft
+// CHECK-V8MMAIN-NOFP: mfpu=none
+// CHECK-V8MMAIN-NOFP: target=thumbv8m.main-none-unknown-eabi
+
+// RUN: %clang -print-multi-selection-flags-experimental --target=arm-none-eabi -mfloat-abi=hard -march=armv8.1m.main+mve.fp | FileCheck --check-prefix=CHECK-MVE %s
+// CHECK-MVE: march=+mve
+// CHECK-MVE: march=+mve.fp
+// CHECK-MVE: mfloat-abi=hard
+// CHECK-MVE: mfpu=fp-armv8-fullfp16-sp-d16
+// CHECK-MVE: target=thumbv8.1m.main-none-unknown-eabihf
+
+// RUN: %clang -print-multi-selection-flags-experimental --target=arm-none-eabi -march=armv8.1m.main+mve+nofp | FileCheck --check-prefix=CHECK-MVENOFP %s
+// CHECK-MVENOFP: march=+mve
+// CHECK-MVENOFP-NOT: march=+mve.fp
+// CHECK-MVENOFP: mfpu=none
Index: clang/lib/Driver/ToolChains/Arch/ARM.h
===
--- clang/lib/Driver/ToolChains/Arch/ARM.h
+++ clang/lib/Driver/ToolChains/Arch/ARM.h
@@ -64,9 +64,11 @@
 void getARMArchCPUFromArgs(const llvm::opt::ArgList &Args,
llvm::StringRef &Arch, llvm::StringRef &CPU,
bool FromAs = false);
+// Optionally returns the FPUKind
 void getARMTargetFeatures(const Driver &D, const llvm::Triple &Triple,
   const llvm::opt::ArgList &Args,
-  std::vector &Features, bool ForAS);
+  std::vector &Features, bool ForAS,
+  unsigned *OutFPUKind = nullptr);
 int getARMSubArchVersionNumber(const llvm::Triple &Triple);
 bool isARMMProfile(const llvm::Triple &Triple);
 bool isARMAProfile(const llvm::Triple &Triple);
Index: clang/lib/Driver/ToolChains/Arch/ARM.cpp
===
--- clang/lib/Driver/ToolChains/Arch/ARM.cpp
+++ clang/lib/Driver/ToolChains/Arch/ARM.cpp
@@ -438,7 +438,8 @@
 
 void arm::getARMTargetFeatures(const Driver &D, const llvm::Triple &Triple,
const ArgList &Args,
-   std::vector &Features, bool ForAS) {
+   std::vector &Features, bool ForAS,
+   unsigned *OutFPUKind) {
   bool KernelOrKext =
   Args.hasArg(options::OPT_mkernel, options::OPT_fapple_kext);
   arm::FloatABI ABI = arm::getARMFloatABI(D, Triple, Args);
@@ -632,6 +633,7 @@
 // above call.
 Features.insert(Features.end(), {"-dotprod", "-fp16fml", "-bf16", "-mve",
  "-mve.fp", "-fpregs"});
+FPUID = llvm::ARM::FK_NONE;

[PATCH] D142878: Add testing for Fuchsia multilib

2023-02-06 Thread Michael Platings via Phabricator via cfe-commits
michaelplatings abandoned this revision.
michaelplatings added a comment.

> A more scalable approach would be to check only the minimal set of 
> combination necessary to achieve full coverage.

In that case the testing you've already got in place in 
`clang/test/Driver/fuchsia.cpp` is adequate. There was a potential bug here so 
I was being extra cautious, but in practice the test added in this change 
didn't pick up anything that wasn't also caught by the existing tests. I'll 
abandon this change and remove it from the stack. The change stack now begins 
at D142893 .


Repository:
  rG LLVM Github Monorepo

CHANGES SINCE LAST ACTION
  https://reviews.llvm.org/D142878/new/

https://reviews.llvm.org/D142878

___
cfe-commits mailing list
cfe-commits@lists.llvm.org
https://lists.llvm.org/cgi-bin/mailman/listinfo/cfe-commits


[PATCH] D142905: Change multilib selection algorithm

2023-02-06 Thread Michael Platings via Phabricator via cfe-commits
michaelplatings updated this revision to Diff 495070.
michaelplatings added a comment.

Set both fexceptions and fno-exceptions flags for Fuchsia multilib. Previously 
that tweak had slipped into D142878 , which 
is now abandoned.


Repository:
  rG LLVM Github Monorepo

CHANGES SINCE LAST ACTION
  https://reviews.llvm.org/D142905/new/

https://reviews.llvm.org/D142905

Files:
  clang/include/clang/Driver/Multilib.h
  clang/include/clang/Driver/MultilibBuilder.h
  clang/lib/Driver/Multilib.cpp
  clang/lib/Driver/MultilibBuilder.cpp
  clang/lib/Driver/ToolChains/CommonArgs.cpp
  clang/lib/Driver/ToolChains/Fuchsia.cpp
  clang/unittests/Driver/MultilibBuilderTest.cpp
  clang/unittests/Driver/MultilibTest.cpp

Index: clang/unittests/Driver/MultilibTest.cpp
===
--- clang/unittests/Driver/MultilibTest.cpp
+++ clang/unittests/Driver/MultilibTest.cpp
@@ -33,14 +33,14 @@
 }
 
 TEST(MultilibTest, OpEqReflexivity3) {
-  Multilib M1({}, {}, {}, 0, {"+foo"});
-  Multilib M2({}, {}, {}, 0, {"+foo"});
+  Multilib M1({}, {}, {}, {"+foo"});
+  Multilib M2({}, {}, {}, {"+foo"});
   ASSERT_TRUE(M1 == M2) << "Multilibs with the same flag should be the same";
 }
 
 TEST(MultilibTest, OpEqInequivalence1) {
-  Multilib M1({}, {}, {}, 0, {"+foo"});
-  Multilib M2({}, {}, {}, 0, {"-foo"});
+  Multilib M1({}, {}, {}, {"+foo"});
+  Multilib M2({}, {}, {}, {"-foo"});
   ASSERT_FALSE(M1 == M2) << "Multilibs with conflicting flags are not the same";
   ASSERT_FALSE(M2 == M1)
   << "Multilibs with conflicting flags are not the same (commuted)";
@@ -48,7 +48,7 @@
 
 TEST(MultilibTest, OpEqInequivalence2) {
   Multilib M1;
-  Multilib M2({}, {}, {}, 0, {"+foo"});
+  Multilib M2({}, {}, {}, {"+foo"});
   ASSERT_FALSE(M1 == M2) << "Flags make Multilibs different";
 }
 
@@ -124,7 +124,7 @@
 }
 
 TEST(MultilibTest, Construction3) {
-  Multilib M({}, {}, {}, 0, {"+f1", "+f2", "-f3"});
+  Multilib M({}, {}, {}, {"+f1", "+f2", "-f3"});
   for (Multilib::flags_list::const_iterator I = M.flags().begin(),
 E = M.flags().end();
I != E; ++I) {
@@ -149,8 +149,8 @@
 
 TEST(MultilibTest, SetPriority) {
   MultilibSet MS({
-  Multilib("/foo", {}, {}, 1, {"+foo"}),
-  Multilib("/bar", {}, {}, 2, {"+bar"}),
+  Multilib("/foo", {}, {}, {"+foo"}),
+  Multilib("/bar", {}, {}, {"+bar"}),
   });
   Multilib::flags_list Flags1 = {"+foo", "-bar"};
   Multilib Selection1;
@@ -166,3 +166,24 @@
   ASSERT_TRUE(Selection2.gccSuffix() == "/bar")
   << "Selection picked " << Selection2 << " which was not expected";
 }
+
+TEST(MultilibTest, SelectMultiple) {
+  MultilibSet MS({
+  Multilib("/a", {}, {}, {"x"}),
+  Multilib("/b", {}, {}, {"y"}),
+  });
+  std::vector Selection;
+
+  Selection = MS.select({"x"});
+  ASSERT_EQ(1u, Selection.size());
+  EXPECT_EQ("/a", Selection[0].gccSuffix());
+
+  Selection = MS.select({"y"});
+  ASSERT_EQ(1u, Selection.size());
+  EXPECT_EQ("/b", Selection[0].gccSuffix());
+
+  Selection = MS.select({"y", "x"});
+  ASSERT_EQ(2u, Selection.size());
+  EXPECT_EQ("/a", Selection[0].gccSuffix());
+  EXPECT_EQ("/b", Selection[1].gccSuffix());
+}
Index: clang/unittests/Driver/MultilibBuilderTest.cpp
===
--- clang/unittests/Driver/MultilibBuilderTest.cpp
+++ clang/unittests/Driver/MultilibBuilderTest.cpp
@@ -7,7 +7,7 @@
 //
 //===--===//
 //
-// Unit tests for Multilib and MultilibBuilder
+// Unit tests for MultilibBuilderVariant and MultilibBuilder
 //
 //===--===//
 
@@ -185,14 +185,14 @@
 bool IsSF = I & 0x2;
 Multilib::flags_list Flags;
 if (IsEL)
-  Flags.push_back("+EL");
+  Flags.insert("+EL");
 else
-  Flags.push_back("-EL");
+  Flags.insert("-EL");
 
 if (IsSF)
-  Flags.push_back("+SF");
+  Flags.insert("+SF");
 else
-  Flags.push_back("-SF");
+  Flags.insert("-SF");
 
 Multilib Selection;
 ASSERT_TRUE(MS2.select(Flags, Selection))
@@ -209,3 +209,11 @@
 << "Selection picked " << Selection << " which was not expected ";
   }
 }
+
+TEST(MultilibBuilderTest, PrintArgs) {
+  MultilibBuilderVariant MBV =
+  MultilibBuilderVariant().flag("+x").flag("-y").flag("+a").flag("-b").flag(
+  "+c");
+  auto M = MBV.makeMultilib();
+  ASSERT_EQ(Multilib::arg_list({"-x", "-a", "-c"}), M.getPrintArgs());
+}
Index: clang/lib/Driver/ToolChains/Fuchsia.cpp
===
--- clang/lib/Driver/ToolChains/Fuchsia.cpp
+++ clang/lib/Driver/ToolChains/Fuchsia.cpp
@@ -263,33 +263,33 @@
 
   Multilibs.push_back(Multilib());
   // Use the noexcept variant with -fno-exceptions to avoid the extra overhead.
-  Multilibs.push_back(MultilibBuilderVariant("noe

[PATCH] D143059: [NFC] Enable selecting multiple multilibs

2023-02-06 Thread Michael Platings via Phabricator via cfe-commits
michaelplatings updated this revision to Diff 495072.
michaelplatings added a comment.

Rebase


Repository:
  rG LLVM Github Monorepo

CHANGES SINCE LAST ACTION
  https://reviews.llvm.org/D143059/new/

https://reviews.llvm.org/D143059

Files:
  clang/include/clang/Driver/Multilib.h
  clang/include/clang/Driver/ToolChain.h
  clang/lib/Driver/Driver.cpp
  clang/lib/Driver/Multilib.cpp
  clang/lib/Driver/ToolChain.cpp
  clang/lib/Driver/ToolChains/BareMetal.cpp
  clang/lib/Driver/ToolChains/CSKYToolChain.cpp
  clang/lib/Driver/ToolChains/Fuchsia.cpp
  clang/lib/Driver/ToolChains/Gnu.cpp
  clang/lib/Driver/ToolChains/Gnu.h
  clang/lib/Driver/ToolChains/Hexagon.cpp
  clang/lib/Driver/ToolChains/Hurd.cpp
  clang/lib/Driver/ToolChains/Linux.cpp
  clang/lib/Driver/ToolChains/MipsLinux.cpp
  clang/lib/Driver/ToolChains/RISCVToolchain.cpp
  clang/test/Driver/fuchsia.cpp
  clang/unittests/Driver/MultilibBuilderTest.cpp
  clang/unittests/Driver/MultilibTest.cpp

Index: clang/unittests/Driver/MultilibTest.cpp
===
--- clang/unittests/Driver/MultilibTest.cpp
+++ clang/unittests/Driver/MultilibTest.cpp
@@ -153,18 +153,18 @@
   Multilib("/bar", {}, {}, {"+bar"}),
   });
   Multilib::flags_list Flags1 = {"+foo", "-bar"};
-  Multilib Selection1;
+  llvm::SmallVector Selection1;
   ASSERT_TRUE(MS.select(Flags1, Selection1))
   << "Flag set was {\"+foo\"}, but selection not found";
-  ASSERT_TRUE(Selection1.gccSuffix() == "/foo")
-  << "Selection picked " << Selection1 << " which was not expected";
+  ASSERT_TRUE(Selection1.back().gccSuffix() == "/foo")
+  << "Selection picked " << Selection1.back() << " which was not expected";
 
   Multilib::flags_list Flags2 = {"+foo", "+bar"};
-  Multilib Selection2;
+  llvm::SmallVector Selection2;
   ASSERT_TRUE(MS.select(Flags2, Selection2))
   << "Flag set was {\"+bar\"}, but selection not found";
-  ASSERT_TRUE(Selection2.gccSuffix() == "/bar")
-  << "Selection picked " << Selection2 << " which was not expected";
+  ASSERT_TRUE(Selection2.back().gccSuffix() == "/bar")
+  << "Selection picked " << Selection2.back() << " which was not expected";
 }
 
 TEST(MultilibTest, SelectMultiple) {
@@ -172,17 +172,17 @@
   Multilib("/a", {}, {}, {"x"}),
   Multilib("/b", {}, {}, {"y"}),
   });
-  std::vector Selection;
+  llvm::SmallVector Selection;
 
-  Selection = MS.select({"x"});
+  ASSERT_TRUE(MS.select({"x"}, Selection));
   ASSERT_EQ(1u, Selection.size());
   EXPECT_EQ("/a", Selection[0].gccSuffix());
 
-  Selection = MS.select({"y"});
+  ASSERT_TRUE(MS.select({"y"}, Selection));
   ASSERT_EQ(1u, Selection.size());
   EXPECT_EQ("/b", Selection[0].gccSuffix());
 
-  Selection = MS.select({"y", "x"});
+  ASSERT_TRUE(MS.select({"y", "x"}, Selection));
   ASSERT_EQ(2u, Selection.size());
   EXPECT_EQ("/a", Selection[0].gccSuffix());
   EXPECT_EQ("/b", Selection[1].gccSuffix());
@@ -314,7 +314,7 @@
 
 TEST(MultilibTest, SelectSoft) {
   MultilibSet MS;
-  Multilib Selected;
+  llvm::SmallVector Selected;
   ASSERT_TRUE(parse(MS, R"(
 variants:
 - dir: s
@@ -333,7 +333,7 @@
 
 TEST(MultilibTest, SelectSoftFP) {
   MultilibSet MS;
-  Multilib Selected;
+  llvm::SmallVector Selected;
   ASSERT_TRUE(parse(MS, R"(
 variants:
 - dir: f
@@ -349,7 +349,7 @@
   // If hard float is all that's available then select that only if compiling
   // with hard float.
   MultilibSet MS;
-  Multilib Selected;
+  llvm::SmallVector Selected;
   ASSERT_TRUE(parse(MS, R"(
 variants:
 - dir: h
@@ -363,7 +363,7 @@
 
 TEST(MultilibTest, SelectFloatABI) {
   MultilibSet MS;
-  Multilib Selected;
+  llvm::SmallVector Selected;
   ASSERT_TRUE(parse(MS, R"(
 variants:
 - dir: s
@@ -384,18 +384,18 @@
   noMatchFlags: [hasfp]
 )"));
   MS.select({"mfloat-abi=soft"}, Selected);
-  EXPECT_EQ("/s", Selected.gccSuffix());
+  EXPECT_EQ("/s", Selected.back().gccSuffix());
   MS.select({"mfloat-abi=softfp"}, Selected);
-  EXPECT_EQ("/f", Selected.gccSuffix());
+  EXPECT_EQ("/f", Selected.back().gccSuffix());
   MS.select({"mfloat-abi=hard"}, Selected);
-  EXPECT_EQ("/h", Selected.gccSuffix());
+  EXPECT_EQ("/h", Selected.back().gccSuffix());
 }
 
 TEST(MultilibTest, SelectFloatABIReversed) {
   // If soft is specified after softfp then softfp will never be
   // selected because soft is compatible with softfp and last wins.
   MultilibSet MS;
-  Multilib Selected;
+  llvm::SmallVector Selected;
   ASSERT_TRUE(parse(MS, R"(
 variants:
 - dir: h
@@ -416,11 +416,11 @@
   noMatchFlags: [hasfp]
 )"));
   MS.select({"mfloat-abi=soft"}, Selected);
-  EXPECT_EQ("/s", Selected.gccSuffix());
+  EXPECT_EQ("/s", Selected.back().gccSuffix());
   MS.select({"mfloat-abi=softfp"}, Selected);
-  EXPECT_EQ("/s", Selected.gccSuffix());
+  EXPECT_EQ("/s", Selected.back().gccSuffix());
   MS.select({"mfloat-abi=hard"}, Selected);
-  EXPECT_EQ("/h", Selected.gccSuffix());
+  EXPECT_EQ("/h", Selected.back().gccSuffix());
 }
 
 TEST(MultilibTest, SelectMClas

[PATCH] D140959: RFC: Multilib prototype

2023-01-20 Thread Michael Platings via Phabricator via cfe-commits
michaelplatings added a comment.

A constraint is that the user should be able to choose the library with a 
single list of arguments, as displayed with `-print-multi-lib`. Therefore I'm 
sceptical about making the selection mechanism too expressive, because 
`-print-multi-lib` can't explain that to the user. Already the presence of 
negation is stretching that.

Nevertheless let's pick an example of something that can't be directly 
expressed in the prototype: `NOT (a AND b)`. (I don't know why you'd want to do 
that, if you have a motivating example of something genuinely useful then that 
would be better)

The expression can be rearranged to `(a AND NOT b) OR (b AND NOT a) OR ((NOT a) 
AND NOT b)` which can be represented in an ugly way:

  variants:
  - path: p
args: [-a]
attrs: [a, not-b]
  - path: p
args: [-b]
attrs: [not-a, b]
  - path: p
args: []
attrs: [not-a, not-b]
  arguments:
  - regex: -a
matchAttrs: [a]
noMatchAttrs: [not-a]
  - regex: -b
matchAttrs: [b]
noMatchAttrs: [not-b]

I think this fits with the spirit of "Make the easy things easy, and the hard 
things possible."

> perhaps it's enough to just make sure there's extension room in the syntax so 
> that this can be added later

One of the many nice things about JSON & YAML is it gives you loads of room for 
extension, so yes. For example, currently `attrs` must be an array, but the 
option could be added later that it could be an object like `attrs: {not: [a, 
b]}`. But I hope it doesn't prove necessary ;)


Repository:
  rG LLVM Github Monorepo

CHANGES SINCE LAST ACTION
  https://reviews.llvm.org/D140959/new/

https://reviews.llvm.org/D140959

___
cfe-commits mailing list
cfe-commits@lists.llvm.org
https://lists.llvm.org/cgi-bin/mailman/listinfo/cfe-commits


[PATCH] D154786: [Clang][Driver] Pass through the --be8 endian flag to linker in BareMetal driver For Arm.

2023-07-18 Thread Michael Platings via Phabricator via cfe-commits
michaelplatings added inline comments.



Comment at: clang/lib/Driver/ToolChains/Arch/ARM.h:77
 bool isARMAProfile(const llvm::Triple &Triple);
+bool isArmBigEndian(const llvm::Triple &Triple, const llvm::opt::ArgList 
&Args);
 

Arm the company has rebranded but for consistency with other code use the 
all-caps name.


Repository:
  rG LLVM Github Monorepo

CHANGES SINCE LAST ACTION
  https://reviews.llvm.org/D154786/new/

https://reviews.llvm.org/D154786

___
cfe-commits mailing list
cfe-commits@lists.llvm.org
https://lists.llvm.org/cgi-bin/mailman/listinfo/cfe-commits


[PATCH] D154786: [Clang][Driver] Pass through the --be8 endian flag to linker in BareMetal driver For Arm.

2023-07-18 Thread Michael Platings via Phabricator via cfe-commits
michaelplatings accepted this revision.
michaelplatings added a comment.
This revision is now accepted and ready to land.

LGTM but please allow a day for others to comment.


Repository:
  rG LLVM Github Monorepo

CHANGES SINCE LAST ACTION
  https://reviews.llvm.org/D154786/new/

https://reviews.llvm.org/D154786

___
cfe-commits mailing list
cfe-commits@lists.llvm.org
https://lists.llvm.org/cgi-bin/mailman/listinfo/cfe-commits


[PATCH] D142702: [Clang][AArch64][SME] Generate target features from +(no)sme.* options

2023-07-20 Thread Michael Platings via Phabricator via cfe-commits
michaelplatings added inline comments.



Comment at: clang/test/Driver/aarch64-implied-sme-features.c:49
+// RUN: %clang -target aarch64-linux-gnu -march=armv8-a+nosme+sme-i16i64 %s 
-### 2>&1 | FileCheck %s --check-prefix=SME-SUBFEATURE-CONFLICT-REV
+// SME-SUBFEATURE-CONFLICT-REV: "-target-feature" "-sme-f64f64" 
"-target-feature" "+sme-i16i64" "-target-feature" "+sme" "-target-feature" 
"+bf16"

Hi Bryan, this test fails in our downstream toolchain because it has additional 
features that show up in between these features. Breaking the line up as shown 
would fix this. Another option could be to add `{{.*}}` between the features. 
Doing likewise for other checks in this file would make them less brittle as 
well.


Repository:
  rG LLVM Github Monorepo

CHANGES SINCE LAST ACTION
  https://reviews.llvm.org/D142702/new/

https://reviews.llvm.org/D142702

___
cfe-commits mailing list
cfe-commits@lists.llvm.org
https://lists.llvm.org/cgi-bin/mailman/listinfo/cfe-commits


[PATCH] D155776: [NFC] Add checks for self-assignment.

2023-07-24 Thread Michael Platings via Phabricator via cfe-commits
michaelplatings added a comment.

I reverted.


Repository:
  rG LLVM Github Monorepo

CHANGES SINCE LAST ACTION
  https://reviews.llvm.org/D155776/new/

https://reviews.llvm.org/D155776

___
cfe-commits mailing list
cfe-commits@lists.llvm.org
https://lists.llvm.org/cgi-bin/mailman/listinfo/cfe-commits


[PATCH] D155294: [Driver][RISCV] Find baremetal multilibs using YAML for GNU toolchain

2023-07-24 Thread Michael Platings via Phabricator via cfe-commits
michaelplatings added a comment.

> some nasty and repetitive regexes

Yes, it's the same for Arm architecture extensions. Petr & I went back and 
forth on this for a long time. See discussion here to understand Petr's 
concerns: https://discourse.llvm.org/t/rfc-multilib/67494/23


CHANGES SINCE LAST ACTION
  https://reviews.llvm.org/D155294/new/

https://reviews.llvm.org/D155294

___
cfe-commits mailing list
cfe-commits@lists.llvm.org
https://lists.llvm.org/cgi-bin/mailman/listinfo/cfe-commits


[PATCH] D142702: [Clang][AArch64][SME] Generate target features from +(no)sme.* options

2023-07-24 Thread Michael Platings via Phabricator via cfe-commits
michaelplatings added inline comments.



Comment at: clang/test/Driver/aarch64-implied-sme-features.c:49
+// RUN: %clang -target aarch64-linux-gnu -march=armv8-a+nosme+sme-i16i64 %s 
-### 2>&1 | FileCheck %s --check-prefix=SME-SUBFEATURE-CONFLICT-REV
+// SME-SUBFEATURE-CONFLICT-REV: "-target-feature" "-sme-f64f64" 
"-target-feature" "+sme-i16i64" "-target-feature" "+sme" "-target-feature" 
"+bf16"

bryanpkc wrote:
> MaskRay wrote:
> > michaelplatings wrote:
> > > Hi Bryan, this test fails in our downstream toolchain because it has 
> > > additional features that show up in between these features. Breaking the 
> > > line up as shown would fix this. Another option could be to add `{{.*}}` 
> > > between the features. Doing likewise for other checks in this file would 
> > > make them less brittle as well.
> > First: `-target ` has been deprecated since Clang 3.4, Use `--target=` for 
> > new tests.
> > 
> > Do you know why you have additional features? I think placing 
> > `"-target-feature"` on the same line is generally a good practice. It 
> > strengthens the test to ensure the feature set is compressive is not 
> > interleaved by other stuff.
> @michaelplatings @MaskRay  I can submit a patch quickly to fix `-target`. I 
> am curious what features show up between those ones in my test, because the 
> options to toggle dependent features should be added immediately after one 
> another. When I placed the `"-target-feature"` strings on the same line, I 
> was following the example in `aarch64-implied-sve-features.c`.
Thanks Bryan & MaskRay for explaining. I was unaware of the importance of 
feature dependencies for the ordering of target-feature flags so I retract my 
suggestion.


Repository:
  rG LLVM Github Monorepo

CHANGES SINCE LAST ACTION
  https://reviews.llvm.org/D142702/new/

https://reviews.llvm.org/D142702

___
cfe-commits mailing list
cfe-commits@lists.llvm.org
https://lists.llvm.org/cgi-bin/mailman/listinfo/cfe-commits


[PATCH] D156427: [clang] Improve hermeticity of clang header tests.

2023-07-27 Thread Michael Platings via Phabricator via cfe-commits
michaelplatings accepted this revision.
michaelplatings added a comment.
This revision is now accepted and ready to land.

LGTM


Repository:
  rG LLVM Github Monorepo

CHANGES SINCE LAST ACTION
  https://reviews.llvm.org/D156427/new/

https://reviews.llvm.org/D156427

___
cfe-commits mailing list
cfe-commits@lists.llvm.org
https://lists.llvm.org/cgi-bin/mailman/listinfo/cfe-commits


[PATCH] D57896: Variable names rule

2023-08-02 Thread Michael Platings via Phabricator via cfe-commits
michaelplatings added a comment.

Hi Sam, I won't be able to take this forward but you have my encouragement. To 
facilitate this change I got as far as changing Git [1], and GitHub has been 
updated accordingly [2], but I ran out of steam before getting to the change 
itself.
I'd be happy to let someone else (you?) take the lead and commandeer the change.

[1] https://moxio.com/blog/ignoring-bulk-change-commits-with-git-blame/
[2] 
https://github.blog/changelog/2022-03-24-ignore-commits-in-the-blame-view-beta/


Repository:
  rG LLVM Github Monorepo

CHANGES SINCE LAST ACTION
  https://reviews.llvm.org/D57896/new/

https://reviews.llvm.org/D57896

___
cfe-commits mailing list
cfe-commits@lists.llvm.org
https://lists.llvm.org/cgi-bin/mailman/listinfo/cfe-commits


[PATCH] D154578: [ARM][Driver] Change float-abi warning

2023-07-06 Thread Michael Platings via Phabricator via cfe-commits
michaelplatings created this revision.
michaelplatings added a reviewer: simon_tatham.
Herald added a subscriber: kristof.beyls.
Herald added a project: All.
michaelplatings requested review of this revision.
Herald added a project: clang.
Herald added a subscriber: cfe-commits.

Previously the warning stated "flag ignored" which is only partially
true - the invalid flag would prevent -feature +soft-float-abi from
being emitted which resulted in user-visible behaviour like
__ARM_PCS_VFP being defined.

Rather than attempt to coerce invalid flags into valid behaviour, don't
describe the expected behaviour.

Ideally the warning would be an error, as it is in GCC. However there
are tests in llvm-project that trigger the warning. Therefore one has to
assume that making the warning an error would break other code that
already exists in the wild.

Also apply test improvements suggested by @MaskRay on D150902 
.


Repository:
  rG LLVM Github Monorepo

https://reviews.llvm.org/D154578

Files:
  clang/include/clang/Basic/DiagnosticDriverKinds.td
  clang/test/Driver/arm-no-float-regs.c


Index: clang/test/Driver/arm-no-float-regs.c
===
--- clang/test/Driver/arm-no-float-regs.c
+++ clang/test/Driver/arm-no-float-regs.c
@@ -1,7 +1,6 @@
-// REQUIRES: arm-registered-target
-
 // Check that -mfloat-abi=hard gives a warning if FP registers aren't 
available.
-// RUN: %clang --target=arm-none-eabi -mcpu=cortex-m0 -mfloat-abi=hard -### -c 
%s 2>&1
+// RUN: %clang --target=arm-none-eabi -mcpu=cortex-m0 -mfloat-abi=hard -### -c 
%s 2>&1 \
+// RUN:   | FileCheck %s
 
 // RUN: %clang --target=arm-none-eabi -mcpu=cortex-m0 -mhard-float -### -c %s 
2>&1 \
 // RUN:   | FileCheck -check-prefix=HARDFLOAT %s
@@ -20,4 +19,4 @@
 
 // CHECK: warning: '-mfloat-abi=hard': selected processor lacks floating point 
registers
 // HARDFLOAT: warning: '-mhard-float': selected processor lacks floating point 
registers
-// NOWARN-NOT: selected processor lacks floating point registers
+// NOWARN-NOT: warning:
Index: clang/include/clang/Basic/DiagnosticDriverKinds.td
===
--- clang/include/clang/Basic/DiagnosticDriverKinds.td
+++ clang/include/clang/Basic/DiagnosticDriverKinds.td
@@ -418,8 +418,8 @@
   "float ABI '%0' is not supported by current library">,
   InGroup>;
 def warn_drv_no_floating_point_registers: Warning<
-  "'%0': selected processor lacks floating point registers; flag ignored">,
-  InGroup;
+  "'%0': selected processor lacks floating point registers">,
+  InGroup>;
 def warn_ignoring_ftabstop_value : Warning<
   "ignoring invalid -ftabstop value '%0', using default value %1">;
 def warn_drv_overriding_flag_option : Warning<


Index: clang/test/Driver/arm-no-float-regs.c
===
--- clang/test/Driver/arm-no-float-regs.c
+++ clang/test/Driver/arm-no-float-regs.c
@@ -1,7 +1,6 @@
-// REQUIRES: arm-registered-target
-
 // Check that -mfloat-abi=hard gives a warning if FP registers aren't available.
-// RUN: %clang --target=arm-none-eabi -mcpu=cortex-m0 -mfloat-abi=hard -### -c %s 2>&1
+// RUN: %clang --target=arm-none-eabi -mcpu=cortex-m0 -mfloat-abi=hard -### -c %s 2>&1 \
+// RUN:   | FileCheck %s
 
 // RUN: %clang --target=arm-none-eabi -mcpu=cortex-m0 -mhard-float -### -c %s 2>&1 \
 // RUN:   | FileCheck -check-prefix=HARDFLOAT %s
@@ -20,4 +19,4 @@
 
 // CHECK: warning: '-mfloat-abi=hard': selected processor lacks floating point registers
 // HARDFLOAT: warning: '-mhard-float': selected processor lacks floating point registers
-// NOWARN-NOT: selected processor lacks floating point registers
+// NOWARN-NOT: warning:
Index: clang/include/clang/Basic/DiagnosticDriverKinds.td
===
--- clang/include/clang/Basic/DiagnosticDriverKinds.td
+++ clang/include/clang/Basic/DiagnosticDriverKinds.td
@@ -418,8 +418,8 @@
   "float ABI '%0' is not supported by current library">,
   InGroup>;
 def warn_drv_no_floating_point_registers: Warning<
-  "'%0': selected processor lacks floating point registers; flag ignored">,
-  InGroup;
+  "'%0': selected processor lacks floating point registers">,
+  InGroup>;
 def warn_ignoring_ftabstop_value : Warning<
   "ignoring invalid -ftabstop value '%0', using default value %1">;
 def warn_drv_overriding_flag_option : Warning<
___
cfe-commits mailing list
cfe-commits@lists.llvm.org
https://lists.llvm.org/cgi-bin/mailman/listinfo/cfe-commits


[PATCH] D154578: [ARM][Driver] Change float-abi warning

2023-07-06 Thread Michael Platings via Phabricator via cfe-commits
michaelplatings updated this revision to Diff 537673.
michaelplatings added a comment.

Fix duplicate implicit group warning


Repository:
  rG LLVM Github Monorepo

CHANGES SINCE LAST ACTION
  https://reviews.llvm.org/D154578/new/

https://reviews.llvm.org/D154578

Files:
  clang/include/clang/Basic/DiagnosticDriverKinds.td
  clang/include/clang/Basic/DiagnosticGroups.td
  clang/test/Driver/arm-no-float-regs.c


Index: clang/test/Driver/arm-no-float-regs.c
===
--- clang/test/Driver/arm-no-float-regs.c
+++ clang/test/Driver/arm-no-float-regs.c
@@ -1,7 +1,6 @@
-// REQUIRES: arm-registered-target
-
 // Check that -mfloat-abi=hard gives a warning if FP registers aren't 
available.
-// RUN: %clang --target=arm-none-eabi -mcpu=cortex-m0 -mfloat-abi=hard -### -c 
%s 2>&1
+// RUN: %clang --target=arm-none-eabi -mcpu=cortex-m0 -mfloat-abi=hard -### -c 
%s 2>&1 \
+// RUN:   | FileCheck %s
 
 // RUN: %clang --target=arm-none-eabi -mcpu=cortex-m0 -mhard-float -### -c %s 
2>&1 \
 // RUN:   | FileCheck -check-prefix=HARDFLOAT %s
@@ -20,4 +19,4 @@
 
 // CHECK: warning: '-mfloat-abi=hard': selected processor lacks floating point 
registers
 // HARDFLOAT: warning: '-mhard-float': selected processor lacks floating point 
registers
-// NOWARN-NOT: selected processor lacks floating point registers
+// NOWARN-NOT: warning:
Index: clang/include/clang/Basic/DiagnosticGroups.td
===
--- clang/include/clang/Basic/DiagnosticGroups.td
+++ clang/include/clang/Basic/DiagnosticGroups.td
@@ -1349,6 +1349,8 @@
 
 def UnknownArgument : DiagGroup<"unknown-argument">;
 
+def UnsupportedABI : DiagGroup<"unsupported-abi">;
+
 // A warning group for warnings about code that clang accepts when
 // compiling OpenCL C/C++ but which is not compatible with the SPIR(-V) spec.
 def SpirCompat : DiagGroup<"spir-compat">;
Index: clang/include/clang/Basic/DiagnosticDriverKinds.td
===
--- clang/include/clang/Basic/DiagnosticDriverKinds.td
+++ clang/include/clang/Basic/DiagnosticDriverKinds.td
@@ -416,10 +416,10 @@
   "unknown platform, assuming -mfloat-abi=%0">;
 def warn_drv_unsupported_float_abi_by_lib : Warning<
   "float ABI '%0' is not supported by current library">,
-  InGroup>;
+  InGroup;
 def warn_drv_no_floating_point_registers: Warning<
-  "'%0': selected processor lacks floating point registers; flag ignored">,
-  InGroup;
+  "'%0': selected processor lacks floating point registers">,
+  InGroup;
 def warn_ignoring_ftabstop_value : Warning<
   "ignoring invalid -ftabstop value '%0', using default value %1">;
 def warn_drv_overriding_flag_option : Warning<


Index: clang/test/Driver/arm-no-float-regs.c
===
--- clang/test/Driver/arm-no-float-regs.c
+++ clang/test/Driver/arm-no-float-regs.c
@@ -1,7 +1,6 @@
-// REQUIRES: arm-registered-target
-
 // Check that -mfloat-abi=hard gives a warning if FP registers aren't available.
-// RUN: %clang --target=arm-none-eabi -mcpu=cortex-m0 -mfloat-abi=hard -### -c %s 2>&1
+// RUN: %clang --target=arm-none-eabi -mcpu=cortex-m0 -mfloat-abi=hard -### -c %s 2>&1 \
+// RUN:   | FileCheck %s
 
 // RUN: %clang --target=arm-none-eabi -mcpu=cortex-m0 -mhard-float -### -c %s 2>&1 \
 // RUN:   | FileCheck -check-prefix=HARDFLOAT %s
@@ -20,4 +19,4 @@
 
 // CHECK: warning: '-mfloat-abi=hard': selected processor lacks floating point registers
 // HARDFLOAT: warning: '-mhard-float': selected processor lacks floating point registers
-// NOWARN-NOT: selected processor lacks floating point registers
+// NOWARN-NOT: warning:
Index: clang/include/clang/Basic/DiagnosticGroups.td
===
--- clang/include/clang/Basic/DiagnosticGroups.td
+++ clang/include/clang/Basic/DiagnosticGroups.td
@@ -1349,6 +1349,8 @@
 
 def UnknownArgument : DiagGroup<"unknown-argument">;
 
+def UnsupportedABI : DiagGroup<"unsupported-abi">;
+
 // A warning group for warnings about code that clang accepts when
 // compiling OpenCL C/C++ but which is not compatible with the SPIR(-V) spec.
 def SpirCompat : DiagGroup<"spir-compat">;
Index: clang/include/clang/Basic/DiagnosticDriverKinds.td
===
--- clang/include/clang/Basic/DiagnosticDriverKinds.td
+++ clang/include/clang/Basic/DiagnosticDriverKinds.td
@@ -416,10 +416,10 @@
   "unknown platform, assuming -mfloat-abi=%0">;
 def warn_drv_unsupported_float_abi_by_lib : Warning<
   "float ABI '%0' is not supported by current library">,
-  InGroup>;
+  InGroup;
 def warn_drv_no_floating_point_registers: Warning<
-  "'%0': selected processor lacks floating point registers; flag ignored">,
-  InGroup;
+  "'%0': selected processor lacks floating point registers">,
+  InGroup;
 def warn_ignoring_ftabstop_value : Warning<
   "ignoring invalid -f

[PATCH] D154578: [ARM][Driver] Change float-abi warning

2023-07-07 Thread Michael Platings via Phabricator via cfe-commits
This revision was landed with ongoing or failed builds.
This revision was automatically updated to reflect the committed changes.
Closed by commit rG79165735e11e: [ARM][Driver] Change float-abi warning 
(authored by michaelplatings).

Repository:
  rG LLVM Github Monorepo

CHANGES SINCE LAST ACTION
  https://reviews.llvm.org/D154578/new/

https://reviews.llvm.org/D154578

Files:
  clang/include/clang/Basic/DiagnosticDriverKinds.td
  clang/include/clang/Basic/DiagnosticGroups.td
  clang/test/Driver/arm-no-float-regs.c


Index: clang/test/Driver/arm-no-float-regs.c
===
--- clang/test/Driver/arm-no-float-regs.c
+++ clang/test/Driver/arm-no-float-regs.c
@@ -1,7 +1,6 @@
-// REQUIRES: arm-registered-target
-
 // Check that -mfloat-abi=hard gives a warning if FP registers aren't 
available.
-// RUN: %clang --target=arm-none-eabi -mcpu=cortex-m0 -mfloat-abi=hard -### -c 
%s 2>&1
+// RUN: %clang --target=arm-none-eabi -mcpu=cortex-m0 -mfloat-abi=hard -### -c 
%s 2>&1 \
+// RUN:   | FileCheck %s
 
 // RUN: %clang --target=arm-none-eabi -mcpu=cortex-m0 -mhard-float -### -c %s 
2>&1 \
 // RUN:   | FileCheck -check-prefix=HARDFLOAT %s
@@ -20,4 +19,4 @@
 
 // CHECK: warning: '-mfloat-abi=hard': selected processor lacks floating point 
registers
 // HARDFLOAT: warning: '-mhard-float': selected processor lacks floating point 
registers
-// NOWARN-NOT: selected processor lacks floating point registers
+// NOWARN-NOT: warning:
Index: clang/include/clang/Basic/DiagnosticGroups.td
===
--- clang/include/clang/Basic/DiagnosticGroups.td
+++ clang/include/clang/Basic/DiagnosticGroups.td
@@ -1349,6 +1349,8 @@
 
 def UnknownArgument : DiagGroup<"unknown-argument">;
 
+def UnsupportedABI : DiagGroup<"unsupported-abi">;
+
 // A warning group for warnings about code that clang accepts when
 // compiling OpenCL C/C++ but which is not compatible with the SPIR(-V) spec.
 def SpirCompat : DiagGroup<"spir-compat">;
Index: clang/include/clang/Basic/DiagnosticDriverKinds.td
===
--- clang/include/clang/Basic/DiagnosticDriverKinds.td
+++ clang/include/clang/Basic/DiagnosticDriverKinds.td
@@ -416,10 +416,10 @@
   "unknown platform, assuming -mfloat-abi=%0">;
 def warn_drv_unsupported_float_abi_by_lib : Warning<
   "float ABI '%0' is not supported by current library">,
-  InGroup>;
+  InGroup;
 def warn_drv_no_floating_point_registers: Warning<
-  "'%0': selected processor lacks floating point registers; flag ignored">,
-  InGroup;
+  "'%0': selected processor lacks floating point registers">,
+  InGroup;
 def warn_ignoring_ftabstop_value : Warning<
   "ignoring invalid -ftabstop value '%0', using default value %1">;
 def warn_drv_overriding_flag_option : Warning<


Index: clang/test/Driver/arm-no-float-regs.c
===
--- clang/test/Driver/arm-no-float-regs.c
+++ clang/test/Driver/arm-no-float-regs.c
@@ -1,7 +1,6 @@
-// REQUIRES: arm-registered-target
-
 // Check that -mfloat-abi=hard gives a warning if FP registers aren't available.
-// RUN: %clang --target=arm-none-eabi -mcpu=cortex-m0 -mfloat-abi=hard -### -c %s 2>&1
+// RUN: %clang --target=arm-none-eabi -mcpu=cortex-m0 -mfloat-abi=hard -### -c %s 2>&1 \
+// RUN:   | FileCheck %s
 
 // RUN: %clang --target=arm-none-eabi -mcpu=cortex-m0 -mhard-float -### -c %s 2>&1 \
 // RUN:   | FileCheck -check-prefix=HARDFLOAT %s
@@ -20,4 +19,4 @@
 
 // CHECK: warning: '-mfloat-abi=hard': selected processor lacks floating point registers
 // HARDFLOAT: warning: '-mhard-float': selected processor lacks floating point registers
-// NOWARN-NOT: selected processor lacks floating point registers
+// NOWARN-NOT: warning:
Index: clang/include/clang/Basic/DiagnosticGroups.td
===
--- clang/include/clang/Basic/DiagnosticGroups.td
+++ clang/include/clang/Basic/DiagnosticGroups.td
@@ -1349,6 +1349,8 @@
 
 def UnknownArgument : DiagGroup<"unknown-argument">;
 
+def UnsupportedABI : DiagGroup<"unsupported-abi">;
+
 // A warning group for warnings about code that clang accepts when
 // compiling OpenCL C/C++ but which is not compatible with the SPIR(-V) spec.
 def SpirCompat : DiagGroup<"spir-compat">;
Index: clang/include/clang/Basic/DiagnosticDriverKinds.td
===
--- clang/include/clang/Basic/DiagnosticDriverKinds.td
+++ clang/include/clang/Basic/DiagnosticDriverKinds.td
@@ -416,10 +416,10 @@
   "unknown platform, assuming -mfloat-abi=%0">;
 def warn_drv_unsupported_float_abi_by_lib : Warning<
   "float ABI '%0' is not supported by current library">,
-  InGroup>;
+  InGroup;
 def warn_drv_no_floating_point_registers: Warning<
-  "'%0': selected processor lacks floating point registers; flag ignored">,
-  InGroup;
+  "'%0': selected processor lacks 

[PATCH] D154736: [Driver][ARM] Warn about -mabi= for assembler input with -fno-integrated-as

2023-07-10 Thread Michael Platings via Phabricator via cfe-commits
michaelplatings accepted this revision.
michaelplatings added a comment.
This revision is now accepted and ready to land.

LGTM


Repository:
  rG LLVM Github Monorepo

CHANGES SINCE LAST ACTION
  https://reviews.llvm.org/D154736/new/

https://reviews.llvm.org/D154736

___
cfe-commits mailing list
cfe-commits@lists.llvm.org
https://lists.llvm.org/cgi-bin/mailman/listinfo/cfe-commits


[PATCH] D154357: [Driver] Recognize powerpc-unknown-eabi as a bare-metal toolchain

2023-07-10 Thread Michael Platings via Phabricator via cfe-commits
michaelplatings accepted this revision.
michaelplatings added a comment.

Hi @MaskRay, thanks for the add. Yes, we've been deleting a lot of `eabi` 
recently, but that's specific to AArch64. I have no particular insight into 
PowerPC but from @jroelofs' link, I agree `eabi` seems correct here.

I've been touching `BareMetal.cpp` a lot recently, and from that point of view 
it seems reasonable to have another architecture join the party. LGTM but I 
agree with MaskRay it would be good to give folks from the PowerPC group a 
chance to comment.


Repository:
  rG LLVM Github Monorepo

CHANGES SINCE LAST ACTION
  https://reviews.llvm.org/D154357/new/

https://reviews.llvm.org/D154357

___
cfe-commits mailing list
cfe-commits@lists.llvm.org
https://lists.llvm.org/cgi-bin/mailman/listinfo/cfe-commits


[PATCH] D155294: [Driver][RISCV] Find baremetal multilibs using YAML for GNU toolchain

2023-07-14 Thread Michael Platings via Phabricator via cfe-commits
michaelplatings added a comment.

Hi Joe, it's nice to see multilib.yaml getting some adoption :)

> For the RISCVMultilibFlags, the mabi flag is used in combination with all the 
> march extension features (e.g +m). Notably, this doesn't align with the 
> current arm/aarch64 multilib flags, which all flags corresponding to the 
> command line flag. E.G -march=. Does this violate a particular design 
> decision, or can any target decide on whatever multilib flags they want?

Multilib flags must be valid command line options. So as `+a` is not a valid 
command line option, it should not be used as a multilib flag.

That said, I'm very aware that it would be desirable to specify attributes 
independently of command line options, so I think there's room for the design 
to grow.

> The location of multilib.yaml for a gnu toolchain is in the lib directory of 
> the sysroot. E.G riscv64-unknown-elf/lib/multilib.yaml. This differs from the 
> baremetal location of "lib/clang-runtimes".

The multilib.yaml design is agnostic to such decisions. If you can guarantee 
that all libraries will always use the exact same header files then it could 
make sense to have multilib apply only to libs. For the BareMetal toolchain I 
wanted to keep the flexibility of allowing different headers to be associated 
with each library.

> Does it make more sense to implement finding multilibs using yaml for riscv 
> in the baremetal toolchain first? I was planning on doing it after.

No strong opinion from me on this one. Doing BareMetal first might lend itself 
to a more consistent end result.


Repository:
  rG LLVM Github Monorepo

CHANGES SINCE LAST ACTION
  https://reviews.llvm.org/D155294/new/

https://reviews.llvm.org/D155294

___
cfe-commits mailing list
cfe-commits@lists.llvm.org
https://lists.llvm.org/cgi-bin/mailman/listinfo/cfe-commits


[PATCH] D142905: [Driver] Change multilib selection algorithm

2023-03-14 Thread Michael Platings via Phabricator via cfe-commits
michaelplatings updated this revision to Diff 505279.
michaelplatings marked an inline comment as done.
michaelplatings added a comment.

Calculate the output for -print-multi-lib lazily.
This necessitated returning to using std::vector to store flags to avoid 
reordering them.
In theory the big-O time to select a multilib is larger now but in practise the 
number of flags is small enough that in practice this is about 2 microseconds 
faster per clang invocation.


Repository:
  rG LLVM Github Monorepo

CHANGES SINCE LAST ACTION
  https://reviews.llvm.org/D142905/new/

https://reviews.llvm.org/D142905

Files:
  clang/include/clang/Driver/Multilib.h
  clang/include/clang/Driver/MultilibBuilder.h
  clang/lib/Driver/Multilib.cpp
  clang/lib/Driver/MultilibBuilder.cpp
  clang/lib/Driver/ToolChains/Fuchsia.cpp
  clang/unittests/Driver/MultilibBuilderTest.cpp
  clang/unittests/Driver/MultilibTest.cpp

Index: clang/unittests/Driver/MultilibTest.cpp
===
--- clang/unittests/Driver/MultilibTest.cpp
+++ clang/unittests/Driver/MultilibTest.cpp
@@ -33,14 +33,14 @@
 }
 
 TEST(MultilibTest, OpEqReflexivity3) {
-  Multilib M1({}, {}, {}, 0, {"+foo"});
-  Multilib M2({}, {}, {}, 0, {"+foo"});
+  Multilib M1({}, {}, {}, {"+foo"});
+  Multilib M2({}, {}, {}, {"+foo"});
   ASSERT_TRUE(M1 == M2) << "Multilibs with the same flag should be the same";
 }
 
 TEST(MultilibTest, OpEqInequivalence1) {
-  Multilib M1({}, {}, {}, 0, {"+foo"});
-  Multilib M2({}, {}, {}, 0, {"-foo"});
+  Multilib M1({}, {}, {}, {"+foo"});
+  Multilib M2({}, {}, {}, {"-foo"});
   ASSERT_FALSE(M1 == M2) << "Multilibs with conflicting flags are not the same";
   ASSERT_FALSE(M2 == M1)
   << "Multilibs with conflicting flags are not the same (commuted)";
@@ -48,7 +48,7 @@
 
 TEST(MultilibTest, OpEqInequivalence2) {
   Multilib M1;
-  Multilib M2({}, {}, {}, 0, {"+foo"});
+  Multilib M2({}, {}, {}, {"+foo"});
   ASSERT_FALSE(M1 == M2) << "Flags make Multilibs different";
 }
 
@@ -124,7 +124,7 @@
 }
 
 TEST(MultilibTest, Construction3) {
-  Multilib M({}, {}, {}, 0, {"+f1", "+f2", "-f3"});
+  Multilib M({}, {}, {}, {"+f1", "+f2", "-f3"});
   for (Multilib::flags_list::const_iterator I = M.flags().begin(),
 E = M.flags().end();
I != E; ++I) {
@@ -149,8 +149,8 @@
 
 TEST(MultilibTest, SetPriority) {
   MultilibSet MS({
-  Multilib("/foo", {}, {}, 1, {"+foo"}),
-  Multilib("/bar", {}, {}, 2, {"+bar"}),
+  Multilib("/foo", {}, {}, {"+foo"}),
+  Multilib("/bar", {}, {}, {"+bar"}),
   });
   Multilib::flags_list Flags1 = {"+foo", "-bar"};
   Multilib Selection1;
@@ -166,3 +166,24 @@
   ASSERT_TRUE(Selection2.gccSuffix() == "/bar")
   << "Selection picked " << Selection2 << " which was not expected";
 }
+
+TEST(MultilibTest, SelectMultiple) {
+  MultilibSet MS({
+  Multilib("/a", {}, {}, {"x"}),
+  Multilib("/b", {}, {}, {"y"}),
+  });
+  std::vector Selection;
+
+  Selection = MS.select({"x"});
+  ASSERT_EQ(1u, Selection.size());
+  EXPECT_EQ("/a", Selection[0].gccSuffix());
+
+  Selection = MS.select({"y"});
+  ASSERT_EQ(1u, Selection.size());
+  EXPECT_EQ("/b", Selection[0].gccSuffix());
+
+  Selection = MS.select({"y", "x"});
+  ASSERT_EQ(2u, Selection.size());
+  EXPECT_EQ("/a", Selection[0].gccSuffix());
+  EXPECT_EQ("/b", Selection[1].gccSuffix());
+}
Index: clang/unittests/Driver/MultilibBuilderTest.cpp
===
--- clang/unittests/Driver/MultilibBuilderTest.cpp
+++ clang/unittests/Driver/MultilibBuilderTest.cpp
@@ -207,3 +207,14 @@
 << "Selection picked " << Selection << " which was not expected ";
   }
 }
+
+TEST(MultilibBuilderTest, PrintOptions) {
+  Multilib M = MultilibBuilder()
+   .flag("+x")
+   .flag("-y")
+   .flag("+a")
+   .flag("-b")
+   .flag("+c")
+   .makeMultilib();
+  ASSERT_EQ(Multilib::flags_list({"-x", "-a", "-c"}), M.getPrintOptions());
+}
Index: clang/lib/Driver/ToolChains/Fuchsia.cpp
===
--- clang/lib/Driver/ToolChains/Fuchsia.cpp
+++ clang/lib/Driver/ToolChains/Fuchsia.cpp
@@ -263,33 +263,33 @@
 
   Multilibs.push_back(Multilib());
   // Use the noexcept variant with -fno-exceptions to avoid the extra overhead.
-  Multilibs.push_back(MultilibBuilder("noexcept", {}, {}, 1)
+  Multilibs.push_back(MultilibBuilder("noexcept", {}, {})
   .flag("-fexceptions")
   .flag("+fno-exceptions")
   .makeMultilib());
   // ASan has higher priority because we always want the instrumentated version.
-  Multilibs.push_back(MultilibBuilder("asan", {}, {}, 2)
+  Multilibs.push_back(MultilibBuilder("asan", {}, {})
   .flag("+fsanitize=address")
   .makeMultilib());
  

[PATCH] D142932: Multilib YAML parsing

2023-03-14 Thread Michael Platings via Phabricator via cfe-commits
michaelplatings updated this revision to Diff 505283.
michaelplatings marked 2 inline comments as done.
michaelplatings added a comment.

Decouple multilib versioning scheme from the Clang version


Repository:
  rG LLVM Github Monorepo

CHANGES SINCE LAST ACTION
  https://reviews.llvm.org/D142932/new/

https://reviews.llvm.org/D142932

Files:
  clang/include/clang/Driver/Multilib.h
  clang/lib/Driver/Multilib.cpp
  clang/unittests/Driver/MultilibTest.cpp

Index: clang/unittests/Driver/MultilibTest.cpp
===
--- clang/unittests/Driver/MultilibTest.cpp
+++ clang/unittests/Driver/MultilibTest.cpp
@@ -13,6 +13,7 @@
 #include "clang/Driver/Multilib.h"
 #include "../../lib/Driver/ToolChains/CommonArgs.h"
 #include "clang/Basic/LLVM.h"
+#include "clang/Basic/Version.h"
 #include "llvm/ADT/ArrayRef.h"
 #include "llvm/ADT/StringRef.h"
 #include "llvm/ADT/StringSwitch.h"
@@ -187,3 +188,392 @@
   EXPECT_EQ("/a", Selection[0].gccSuffix());
   EXPECT_EQ("/b", Selection[1].gccSuffix());
 }
+
+static void diagnosticCallback(const llvm::SMDiagnostic &D, void *Out) {
+  *reinterpret_cast(Out) = D.getMessage();
+}
+
+static bool parseYaml(MultilibSet &MS, std::string &Diagnostic,
+  const char *Data) {
+  return MS.parseYaml(llvm::MemoryBufferRef(Data, "TEST"), diagnosticCallback,
+  &Diagnostic);
+}
+
+static bool parseYaml(MultilibSet &MS, const char *Data) {
+  return MS.parseYaml(llvm::MemoryBufferRef(Data, "TEST"));
+}
+
+// When updating this version also update MultilibVersionCurrent in Multilib.cpp
+#define YAML_PREAMBLE "MultilibVersion: 1.0\n"
+
+TEST(MultilibTest, ParseInvalid) {
+  std::string Diagnostic;
+
+  MultilibSet MS;
+
+  EXPECT_FALSE(parseYaml(MS, Diagnostic, R"(
+Variants: []
+)"));
+  EXPECT_TRUE(
+  StringRef(Diagnostic).contains("missing required key 'MultilibVersion'"))
+  << Diagnostic;
+
+  // Reject files with a different major version
+  EXPECT_FALSE(parseYaml(MS, Diagnostic,
+ R"(
+MultilibVersion: 2.0
+Variants: []
+)"));
+  EXPECT_TRUE(
+  StringRef(Diagnostic).contains("Multilib version 2.0 is unsupported"))
+  << Diagnostic;
+  EXPECT_FALSE(parseYaml(MS, Diagnostic,
+ R"(
+MultilibVersion: 0.1
+Variants: []
+)"));
+  EXPECT_TRUE(
+  StringRef(Diagnostic).contains("Multilib version 0.1 is unsupported"))
+  << Diagnostic;
+
+  // Reject files with a later minor version
+  EXPECT_FALSE(parseYaml(MS, Diagnostic,
+ R"(
+MultilibVersion: 1.9
+Variants: []
+)"));
+  EXPECT_TRUE(
+  StringRef(Diagnostic).contains("Multilib version 1.9 is unsupported"))
+  << Diagnostic;
+
+  // Accept files with the same major version and the same or earlier minor
+  // version
+  EXPECT_TRUE(parseYaml(MS, Diagnostic, R"(
+MultilibVersion: 1.0
+Variants: []
+)")) << Diagnostic;
+
+  EXPECT_FALSE(parseYaml(MS, Diagnostic, YAML_PREAMBLE));
+  EXPECT_TRUE(StringRef(Diagnostic).contains("missing required key 'Variants'"))
+  << Diagnostic;
+
+  EXPECT_FALSE(parseYaml(MS, Diagnostic, YAML_PREAMBLE R"(
+Variants:
+- Dir: /abc
+  Flags: []
+  PrintOptions: []
+)"));
+  EXPECT_TRUE(StringRef(Diagnostic).contains("paths must be relative"))
+  << Diagnostic;
+
+  EXPECT_FALSE(parseYaml(MS, Diagnostic, YAML_PREAMBLE R"(
+Variants:
+- Flags: []
+  PrintOptions: []
+)"));
+  EXPECT_TRUE(StringRef(Diagnostic).contains("missing required key 'Dir'"))
+  << Diagnostic;
+
+  EXPECT_FALSE(parseYaml(MS, Diagnostic, YAML_PREAMBLE R"(
+Variants:
+- Dir: .
+  PrintOptions: []
+)"));
+  EXPECT_TRUE(StringRef(Diagnostic).contains("missing required key 'Flags'"))
+  << Diagnostic;
+
+  EXPECT_FALSE(parseYaml(MS, Diagnostic, YAML_PREAMBLE R"(
+Variants:
+- Dir: .
+  Flags: []
+)"));
+  EXPECT_TRUE(
+  StringRef(Diagnostic).contains("missing required key 'PrintOptions'"))
+  << Diagnostic;
+
+  EXPECT_FALSE(parseYaml(MS, Diagnostic, YAML_PREAMBLE R"(
+Variants: []
+FlagMap:
+- Regex: abc
+)"));
+  EXPECT_TRUE(
+  StringRef(Diagnostic)
+  .contains("value required for 'MatchFlags' or 'NoMatchFlags'"))
+  << Diagnostic;
+
+  EXPECT_FALSE(parseYaml(MS, Diagnostic, YAML_PREAMBLE R"(
+Variants: []
+FlagMap:
+- Dir: .
+  Regex: '('
+  PrintOptions: []
+)"));
+  EXPECT_TRUE(StringRef(Diagnostic).contains("parentheses not balanced"))
+  << Diagnostic;
+}
+
+TEST(MultilibTest, Parse) {
+  MultilibSet MS;
+  EXPECT_TRUE(parseYaml(MS, YAML_PREAMBLE R"(
+Variants:
+- Dir: .
+  Flags: []
+  PrintOptions: []
+)"));
+  EXPECT_EQ(1U, MS.size());
+  EXPECT_EQ("", MS.begin()->gccSuffix());
+
+  EXPECT_TRUE(parseYaml(MS, YAML_PREAMBLE R"(
+Variants:
+- Dir: abc
+  Flags: []
+  PrintOptions: []
+)"));
+  EXPECT_EQ(1U, MS.size());
+  EXPECT_EQ("/abc", MS.begin()->gccSuffix());
+
+  EXPECT_TRUE(parseYaml(MS, YAML_PREAMBLE R"(
+Variants:
+- Dir: pqr
+  Flags: []
+  PrintOptions: [-mfloat-abi=soft]
+)"));
+  EXPECT_EQ

[PATCH] D142933: Add -print-multi-selection-flags-experimental option

2023-03-14 Thread Michael Platings via Phabricator via cfe-commits
michaelplatings updated this revision to Diff 505284.
michaelplatings added a comment.

Rebase


Repository:
  rG LLVM Github Monorepo

CHANGES SINCE LAST ACTION
  https://reviews.llvm.org/D142933/new/

https://reviews.llvm.org/D142933

Files:
  clang/include/clang/Driver/Options.td
  clang/include/clang/Driver/ToolChain.h
  clang/lib/Driver/Driver.cpp
  clang/lib/Driver/ToolChain.cpp
  clang/lib/Driver/ToolChains/Arch/ARM.cpp
  clang/lib/Driver/ToolChains/Arch/ARM.h
  clang/test/Driver/print-multi-selection-flags.c

Index: clang/test/Driver/print-multi-selection-flags.c
===
--- /dev/null
+++ clang/test/Driver/print-multi-selection-flags.c
@@ -0,0 +1,54 @@
+// RUN: %clang -print-multi-selection-flags-experimental --target=aarch64-linux -fc++-abi=itanium -fsanitize=address | FileCheck --check-prefix=CHECK-LINUX %s
+// CHECK-LINUX: fc++-abi=itanium
+// CHECK-LINUX: fexceptions
+// CHECK-LINUX: frtti
+// CHECK-LINUX: fsanitize=address
+// CHECK-LINUX: target=aarch64-unknown-linux
+
+// RUN: %clang -print-multi-selection-flags-experimental --target=aarch64-fuchsia -fsanitize=hwaddress | FileCheck --check-prefix=CHECK-FUCHSIA %s
+// CHECK-FUCHSIA: fsanitize=hwaddress
+// CHECK-FUCHSIA: target=aarch64-unknown-fuchsia
+
+// RUN: %clang -print-multi-selection-flags-experimental --target=arm-none-eabi -mfloat-abi=soft -fno-exceptions -fno-rtti | FileCheck --check-prefix=CHECK-ARMV4T %s
+// CHECK-ARMV4T: fno-exceptions
+// CHECK-ARMV4T: fno-rtti
+// CHECK-ARMV4T: mfloat-abi=soft
+// CHECK-ARMV4T: mfpu=none
+// CHECK-ARMV4T: target=armv4t-none-unknown-eabi
+
+// RUN: %clang -print-multi-selection-flags-experimental --target=armv7em-none-eabi -mfloat-abi=softfp | FileCheck --check-prefix=CHECK-SOFTFP %s
+// CHECK-SOFTFP: mfloat-abi=softfp
+// CHECK-SOFTFP: mfpu=fpv4-sp-d16
+// CHECK-SOFTFP: target=thumbv7em-none-unknown-eabi
+
+// RUN: %clang -print-multi-selection-flags-experimental --target=arm-none-eabihf -march=armv7em -mfpu=fpv5-d16 | FileCheck --check-prefix=CHECK-HARD %s
+// CHECK-HARD: mfloat-abi=hard
+// CHECK-HARD: mfpu=fpv5-d16
+// CHECK-HARD: target=thumbv7em-none-unknown-eabihf
+
+// RUN: %clang -print-multi-selection-flags-experimental --target=arm-none-eabi -mfloat-abi=soft -march=armv8-m.main+nofp | FileCheck --check-prefix=CHECK-V8MMAIN-NOFP %s
+// CHECK-V8MMAIN-NOFP: mfloat-abi=soft
+// CHECK-V8MMAIN-NOFP: mfpu=none
+// CHECK-V8MMAIN-NOFP: target=thumbv8m.main-none-unknown-eabi
+
+// RUN: %clang -print-multi-selection-flags-experimental --target=arm-none-eabi -mfloat-abi=hard -march=armv8.1m.main+mve.fp | FileCheck --check-prefix=CHECK-MVE %s
+// CHECK-MVE: march=+mve
+// CHECK-MVE: march=+mve.fp
+// CHECK-MVE: mfloat-abi=hard
+// CHECK-MVE: mfpu=fp-armv8-fullfp16-sp-d16
+// CHECK-MVE: target=thumbv8.1m.main-none-unknown-eabihf
+
+// RUN: %clang -print-multi-selection-flags-experimental --target=arm-none-eabi -march=armv8.1m.main+mve+nofp | FileCheck --check-prefix=CHECK-MVENOFP %s
+// CHECK-MVENOFP: march=+mve
+// CHECK-MVENOFP-NOT: march=+mve.fp
+// CHECK-MVENOFP: mfpu=none
+
+// RUN: %clang -print-multi-selection-flags-experimental --target=aarch64-none-elf -march=armv8-a+lse | FileCheck --check-prefix=CHECK-LSE %s
+// CHECK-LSE: march=+lse
+
+// RUN: %clang -print-multi-selection-flags-experimental --target=aarch64-none-elf -march=armv8.5-a+sve+sve2 | FileCheck --check-prefix=CHECK-SVE2 %s
+// RUN: %clang -print-multi-selection-flags-experimental --target=aarch64-none-elf -march=armv9-a| FileCheck --check-prefix=CHECK-SVE2 %s
+// CHECK-SVE2: march=+simd
+// CHECK-SVE2: march=+sve
+// CHECK-SVE2: march=+sve2
+// CHECK-SVE2: target=aarch64-none-unknown-elf
Index: clang/lib/Driver/ToolChains/Arch/ARM.h
===
--- clang/lib/Driver/ToolChains/Arch/ARM.h
+++ clang/lib/Driver/ToolChains/Arch/ARM.h
@@ -63,9 +63,11 @@
 void getARMArchCPUFromArgs(const llvm::opt::ArgList &Args,
llvm::StringRef &Arch, llvm::StringRef &CPU,
bool FromAs = false);
+// Optionally returns the FPUKind
 void getARMTargetFeatures(const Driver &D, const llvm::Triple &Triple,
   const llvm::opt::ArgList &Args,
-  std::vector &Features, bool ForAS);
+  std::vector &Features, bool ForAS,
+  unsigned *OutFPUKind = nullptr);
 int getARMSubArchVersionNumber(const llvm::Triple &Triple);
 bool isARMMProfile(const llvm::Triple &Triple);
 bool isARMAProfile(const llvm::Triple &Triple);
Index: clang/lib/Driver/ToolChains/Arch/ARM.cpp
===
--- clang/lib/Driver/ToolChains/Arch/ARM.cpp
+++ clang/lib/Driver/ToolChains/Arch/ARM.cpp
@@ -437,7 +437,8 @@
 
 void arm::getARMTargetFeatures(const Driver &D, const llvm::Triple &Triple,
const ArgList &Args,
- 

[PATCH] D142986: Enable multilib.yaml in the BareMetal ToolChain

2023-03-14 Thread Michael Platings via Phabricator via cfe-commits
michaelplatings updated this revision to Diff 505286.
michaelplatings added a comment.

Rebase


Repository:
  rG LLVM Github Monorepo

CHANGES SINCE LAST ACTION
  https://reviews.llvm.org/D142986/new/

https://reviews.llvm.org/D142986

Files:
  clang/lib/Driver/ToolChain.cpp
  clang/lib/Driver/ToolChains/Arch/ARM.cpp
  clang/lib/Driver/ToolChains/Arch/ARM.h
  clang/lib/Driver/ToolChains/BareMetal.cpp
  clang/test/Driver/baremetal-multilib.yaml
  clang/test/Driver/baremetal.cpp
  clang/test/Driver/lit.local.cfg

Index: clang/test/Driver/lit.local.cfg
===
--- clang/test/Driver/lit.local.cfg
+++ clang/test/Driver/lit.local.cfg
@@ -1,7 +1,7 @@
 from lit.llvm import llvm_config
 
 config.suffixes = ['.c', '.cpp', '.cppm', '.h', '.m', '.mm', '.S', '.s', '.f90', '.F90', '.f95',
-   '.cu', '.rs', '.cl', '.clcpp', '.hip', '.hipi', '.hlsl']
+   '.cu', '.rs', '.cl', '.clcpp', '.hip', '.hipi', '.hlsl', '.yaml']
 config.substitutions = list(config.substitutions)
 config.substitutions.insert(0,
 ('%clang_cc1',
Index: clang/test/Driver/baremetal.cpp
===
--- clang/test/Driver/baremetal.cpp
+++ clang/test/Driver/baremetal.cpp
@@ -118,9 +118,9 @@
 // Verify that the bare metal driver does not include any host system paths:
 // CHECK-AARCH64-NO-HOST-INC: InstalledDir: [[INSTALLEDDIR:.+]]
 // CHECK-AARCH64-NO-HOST-INC: "-resource-dir" "[[RESOURCE:[^"]+]]"
-// CHECK-AARCH64-NO-HOST-INC-SAME: "-internal-isystem" "[[INSTALLEDDIR]]{{[/\\]+}}..{{[/\\]+}}lib{{[/\\]+}}clang-runtimes{{[/\\]+}}aarch64-none-elf{{[/\\]+}}include{{[/\\]+}}c++{{[/\\]+}}v1"
+// CHECK-AARCH64-NO-HOST-INC-SAME: "-internal-isystem" "[[INSTALLEDDIR]]{{[/\\]+}}..{{[/\\]+}}lib{{[/\\]+}}clang-runtimes{{[/\\]+[^"]*}}include{{[/\\]+}}c++{{[/\\]+}}v1"
 // CHECK-AARCH64-NO-HOST-INC-SAME: "-internal-isystem" "[[RESOURCE]]{{[/\\]+}}include"
-// CHECK-AARCH64-NO-HOST-INC-SAME: "-internal-isystem" "[[INSTALLEDDIR]]{{[/\\]+}}..{{[/\\]+}}lib{{[/\\]+}}clang-runtimes{{[/\\]+}}aarch64-none-elf{{[/\\]+}}include"
+// CHECK-AARCH64-NO-HOST-INC-SAME: "-internal-isystem" "[[INSTALLEDDIR]]{{[/\\]+}}..{{[/\\]+}}lib{{[/\\]+}}clang-runtimes{{[/\\]+[^"]*}}include"
 
 // RUN: %clang %s -### --target=riscv64-unknown-elf -o %t.out -L some/directory/user/asked/for \
 // RUN: --sysroot=%S/Inputs/basic_riscv64_tree/riscv64-unknown-elf 2>&1 \
Index: clang/test/Driver/baremetal-multilib.yaml
===
--- /dev/null
+++ clang/test/Driver/baremetal-multilib.yaml
@@ -0,0 +1,142 @@
+# REQUIRES: shell
+# UNSUPPORTED: system-windows
+
+# RUN: rm -rf %T/baremetal_multilib
+# RUN: mkdir -p %T/baremetal_multilib/bin
+# RUN: mkdir -p %T/baremetal_multilib/lib/clang-runtimes/arm-none-eabi/thumb/v8-m.main/fp/lib
+# RUN: touch %T/baremetal_multilib/lib/clang-runtimes/arm-none-eabi/thumb/v8-m.main/fp/lib/libclang_rt.builtins.a
+# RUN: ln -s %clang %T/baremetal_multilib/bin/clang
+# RUN: ln -s %s %T/baremetal_multilib/lib/clang-runtimes/multilib.yaml
+
+# RUN: %T/baremetal_multilib/bin/clang -no-canonical-prefixes -x c++ %s -### -o %t.out 2>&1 \
+# RUN: --target=thumbv8m.main-none-eabihf --sysroot= \
+# RUN:   | FileCheck -DSYSROOT=%T/baremetal_multilib %s
+# CHECK:  "-cc1" "-triple" "thumbv8m.main-none-unknown-eabihf"
+# CHECK-SAME: "-internal-isystem" "[[SYSROOT]]/bin/../lib/clang-runtimes/arm-none-eabi/thumb/v8-m.main/fp/include/c++/v1"
+# CHECK-SAME: "-internal-isystem" "[[SYSROOT]]/bin/../lib/clang-runtimes/arm-none-eabi/thumb/v8-m.main/fp/include"
+# CHECK-SAME: "-x" "c++" "{{.*}}baremetal-multilib.yaml"
+# CHECK-NEXT: ld{{(.exe)?}}" "{{.*}}.o" "-Bstatic"
+# CHECK-SAME: "-L[[SYSROOT]]/bin/../lib/clang-runtimes/arm-none-eabi/thumb/v8-m.main/fp/lib"
+# CHECK-SAME: "-lc" "-lm" "-lclang_rt.builtins"
+# CHECK-SAME: "-o" "{{.*}}.tmp.out"
+
+# RUN: %T/baremetal_multilib/bin/clang -no-canonical-prefixes -print-multi-directory 2>&1 \
+# RUN: --target=thumbv8m.main-none-eabihf --sysroot= \
+# RUN:   | FileCheck --check-prefix=CHECK-PRINT-MULTI-DIRECTORY %s
+# CHECK-PRINT-MULTI-DIRECTORY: arm-none-eabi/thumb/v8-m.main/fp
+
+# RUN: %T/baremetal_multilib/bin/clang -no-canonical-prefixes -print-multi-lib 2>&1 \
+# RUN: --target=arm-none-eabi --sysroot= \
+# RUN:   | FileCheck --check-prefix=CHECK-PRINT-MULTI-LIB %s
+# CHECK-PRINT-MULTI-LIB: arm-none-eabi/thumb/v6-m/nofp;@-target=thumbv6m-none-eabi@mfloat-abi=soft
+# CHECK-PRINT-MULTI-LIB: arm-none-eabi/thumb/v7-m/nofp;@-target=thumbv7m-none-eabi@mfloat-abi=soft
+# CHECK-PRINT-MULTI-LIB: arm-none-eabi/thumb/v7e-m/nofp;@-target=thumbv7em-none-eabi@mfloat-abi=soft@mfpu=none
+# CHECK-PRINT-MULTI-LIB: arm-none-eabi/thumb/v8-m.main/nofp;@-target=arm-none-eabi@mfloat-abi=soft@march=armv8m.main+nofp
+# CHECK-PRINT-MULTI-LIB: arm-none-eabi/thumb/v8.1-m.main/nofp/nomve;@-target=arm-none-eabi@mfloat-abi=soft@march=armv8.1m.main+nofp+nomve

[PATCH] D142986: Enable multilib.yaml in the BareMetal ToolChain

2023-03-14 Thread Michael Platings via Phabricator via cfe-commits
michaelplatings added inline comments.



Comment at: clang/lib/Driver/ToolChains/BareMetal.cpp:184
+  SmallString<128> MultilibPath(SysRootDir);
+  llvm::sys::path::append(MultilibPath, MULTILIB_YAML_FILENAME);
+

phosek wrote:
> Rather than hardcoding the filename and the location, which is inflexible, 
> could we instead provide a command line option to specify the file to use?
I'm not opposed to that in principle but I'd rather leave that as an option for 
a future change. At this point, for LLVM Embedded Toolchain for Arm our intent 
is that users will specify `--sysroot` if they want to use a separate set of 
multilibs.


Repository:
  rG LLVM Github Monorepo

CHANGES SINCE LAST ACTION
  https://reviews.llvm.org/D142986/new/

https://reviews.llvm.org/D142986

___
cfe-commits mailing list
cfe-commits@lists.llvm.org
https://lists.llvm.org/cgi-bin/mailman/listinfo/cfe-commits


[PATCH] D143059: [Driver] Enable selecting multiple multilibs

2023-03-14 Thread Michael Platings via Phabricator via cfe-commits
michaelplatings updated this revision to Diff 505288.
michaelplatings added a comment.

Rebase


Repository:
  rG LLVM Github Monorepo

CHANGES SINCE LAST ACTION
  https://reviews.llvm.org/D143059/new/

https://reviews.llvm.org/D143059

Files:
  clang/include/clang/Driver/Multilib.h
  clang/include/clang/Driver/ToolChain.h
  clang/lib/Driver/Driver.cpp
  clang/lib/Driver/Multilib.cpp
  clang/lib/Driver/ToolChain.cpp
  clang/lib/Driver/ToolChains/BareMetal.cpp
  clang/lib/Driver/ToolChains/CSKYToolChain.cpp
  clang/lib/Driver/ToolChains/Fuchsia.cpp
  clang/lib/Driver/ToolChains/Gnu.cpp
  clang/lib/Driver/ToolChains/Gnu.h
  clang/lib/Driver/ToolChains/Hexagon.cpp
  clang/lib/Driver/ToolChains/Hurd.cpp
  clang/lib/Driver/ToolChains/Linux.cpp
  clang/lib/Driver/ToolChains/MipsLinux.cpp
  clang/lib/Driver/ToolChains/RISCVToolchain.cpp
  clang/test/Driver/fuchsia.cpp
  clang/unittests/Driver/MultilibBuilderTest.cpp
  clang/unittests/Driver/MultilibTest.cpp

Index: clang/unittests/Driver/MultilibTest.cpp
===
--- clang/unittests/Driver/MultilibTest.cpp
+++ clang/unittests/Driver/MultilibTest.cpp
@@ -154,18 +154,18 @@
   Multilib("/bar", {}, {}, {"+bar"}),
   });
   Multilib::flags_list Flags1 = {"+foo", "-bar"};
-  Multilib Selection1;
+  llvm::SmallVector Selection1;
   ASSERT_TRUE(MS.select(Flags1, Selection1))
   << "Flag set was {\"+foo\"}, but selection not found";
-  ASSERT_TRUE(Selection1.gccSuffix() == "/foo")
-  << "Selection picked " << Selection1 << " which was not expected";
+  ASSERT_TRUE(Selection1.back().gccSuffix() == "/foo")
+  << "Selection picked " << Selection1.back() << " which was not expected";
 
   Multilib::flags_list Flags2 = {"+foo", "+bar"};
-  Multilib Selection2;
+  llvm::SmallVector Selection2;
   ASSERT_TRUE(MS.select(Flags2, Selection2))
   << "Flag set was {\"+bar\"}, but selection not found";
-  ASSERT_TRUE(Selection2.gccSuffix() == "/bar")
-  << "Selection picked " << Selection2 << " which was not expected";
+  ASSERT_TRUE(Selection2.back().gccSuffix() == "/bar")
+  << "Selection picked " << Selection2.back() << " which was not expected";
 }
 
 TEST(MultilibTest, SelectMultiple) {
@@ -173,17 +173,17 @@
   Multilib("/a", {}, {}, {"x"}),
   Multilib("/b", {}, {}, {"y"}),
   });
-  std::vector Selection;
+  llvm::SmallVector Selection;
 
-  Selection = MS.select({"x"});
+  ASSERT_TRUE(MS.select({"x"}, Selection));
   ASSERT_EQ(1u, Selection.size());
   EXPECT_EQ("/a", Selection[0].gccSuffix());
 
-  Selection = MS.select({"y"});
+  ASSERT_TRUE(MS.select({"y"}, Selection));
   ASSERT_EQ(1u, Selection.size());
   EXPECT_EQ("/b", Selection[0].gccSuffix());
 
-  Selection = MS.select({"y", "x"});
+  ASSERT_TRUE(MS.select({"y", "x"}, Selection));
   ASSERT_EQ(2u, Selection.size());
   EXPECT_EQ("/a", Selection[0].gccSuffix());
   EXPECT_EQ("/b", Selection[1].gccSuffix());
@@ -367,7 +367,7 @@
 
 TEST(MultilibTest, SelectSoft) {
   MultilibSet MS;
-  Multilib Selected;
+  llvm::SmallVector Selected;
   ASSERT_TRUE(parseYaml(MS, YAML_PREAMBLE R"(
 Variants:
 - Dir: s
@@ -386,7 +386,7 @@
 
 TEST(MultilibTest, SelectSoftFP) {
   MultilibSet MS;
-  Multilib Selected;
+  llvm::SmallVector Selected;
   ASSERT_TRUE(parseYaml(MS, YAML_PREAMBLE R"(
 Variants:
 - Dir: f
@@ -402,7 +402,7 @@
   // If hard float is all that's available then select that only if compiling
   // with hard float.
   MultilibSet MS;
-  Multilib Selected;
+  llvm::SmallVector Selected;
   ASSERT_TRUE(parseYaml(MS, YAML_PREAMBLE R"(
 Variants:
 - Dir: h
@@ -416,7 +416,7 @@
 
 TEST(MultilibTest, SelectFloatABI) {
   MultilibSet MS;
-  Multilib Selected;
+  llvm::SmallVector Selected;
   ASSERT_TRUE(parseYaml(MS, YAML_PREAMBLE R"(
 Variants:
 - Dir: s
@@ -437,18 +437,18 @@
   NoMatchFlags: [hasfp]
 )"));
   MS.select({"mfloat-abi=soft"}, Selected);
-  EXPECT_EQ("/s", Selected.gccSuffix());
+  EXPECT_EQ("/s", Selected.back().gccSuffix());
   MS.select({"mfloat-abi=softfp"}, Selected);
-  EXPECT_EQ("/f", Selected.gccSuffix());
+  EXPECT_EQ("/f", Selected.back().gccSuffix());
   MS.select({"mfloat-abi=hard"}, Selected);
-  EXPECT_EQ("/h", Selected.gccSuffix());
+  EXPECT_EQ("/h", Selected.back().gccSuffix());
 }
 
 TEST(MultilibTest, SelectFloatABIReversed) {
   // If soft is specified after softfp then softfp will never be
   // selected because soft is compatible with softfp and last wins.
   MultilibSet MS;
-  Multilib Selected;
+  llvm::SmallVector Selected;
   ASSERT_TRUE(parseYaml(MS, YAML_PREAMBLE R"(
 Variants:
 - Dir: h
@@ -469,11 +469,11 @@
   NoMatchFlags: [hasfp]
 )"));
   MS.select({"mfloat-abi=soft"}, Selected);
-  EXPECT_EQ("/s", Selected.gccSuffix());
+  EXPECT_EQ("/s", Selected.back().gccSuffix());
   MS.select({"mfloat-abi=softfp"}, Selected);
-  EXPECT_EQ("/s", Selected.gccSuffix());
+  EXPECT_EQ("/s", Selected.back().gccSuffix());
   MS.select({"mfloat-abi=hard"}, Selected);
-  EXPECT_EQ("/h", Selected.gccSuffix

[PATCH] D143075: BareMetal ToolChain multilib layering

2023-03-14 Thread Michael Platings via Phabricator via cfe-commits
michaelplatings updated this revision to Diff 505290.
michaelplatings added a comment.

Rebase


Repository:
  rG LLVM Github Monorepo

CHANGES SINCE LAST ACTION
  https://reviews.llvm.org/D143075/new/

https://reviews.llvm.org/D143075

Files:
  clang/lib/Driver/ToolChains/BareMetal.cpp
  clang/lib/Driver/ToolChains/BareMetal.h
  clang/test/Driver/baremetal-multilib.yaml

Index: clang/test/Driver/baremetal-multilib.yaml
===
--- clang/test/Driver/baremetal-multilib.yaml
+++ clang/test/Driver/baremetal-multilib.yaml
@@ -25,6 +25,23 @@
 # RUN:   | FileCheck --check-prefix=CHECK-PRINT-MULTI-DIRECTORY %s
 # CHECK-PRINT-MULTI-DIRECTORY: arm-none-eabi/thumb/v8-m.main/fp
 
+# RUN: %T/baremetal_multilib/bin/clang -no-canonical-prefixes -x c++ %s -### -o %t.out 2>&1 \
+# RUN: --target=thumbv8.1m.main-none-eabihf -fno-exceptions --sysroot= \
+# RUN:   | FileCheck -DSYSROOT=%T/baremetal_multilib --check-prefix=CHECK-LAYERED-MULTILIB %s
+# CHECK-LAYERED-MULTILIB:  "-cc1" "-triple" "thumbv8.1m.main-none-unknown-eabihf"
+# CHECK-LAYERED-MULTILIB-SAME: "-internal-isystem" "[[SYSROOT]]/bin/../lib/clang-runtimes/arm-none-eabi/thumb/v8.1-m.main/fp/noexcept/include/c++/v1"
+# CHECK-LAYERED-MULTILIB-SAME: "-internal-isystem" "[[SYSROOT]]/bin/../lib/clang-runtimes/arm-none-eabi/thumb/v8.1-m.main/fp/include/c++/v1"
+# CHECK-LAYERED-MULTILIB-SAME: "-internal-isystem" "[[SYSROOT]]/bin/../lib/clang-runtimes/arm-none-eabi/thumb/v8.1-m.main/fp/noexcept/include"
+# CHECK-LAYERED-MULTILIB-SAME: "-internal-isystem" "[[SYSROOT]]/bin/../lib/clang-runtimes/arm-none-eabi/thumb/v8.1-m.main/fp/include"
+# CHECK-LAYERED-MULTILIB-NEXT: "-L[[SYSROOT]]/bin/../lib/clang-runtimes/arm-none-eabi/thumb/v8.1-m.main/fp/noexcept/lib"
+# CHECK-LAYERED-MULTILIB-SAME: "-L[[SYSROOT]]/bin/../lib/clang-runtimes/arm-none-eabi/thumb/v8.1-m.main/fp/lib"
+
+# RUN: %T/baremetal_multilib/bin/clang -no-canonical-prefixes -print-multi-directory 2>&1 \
+# RUN: --target=thumbv8.1m.main-none-eabihf -fno-exceptions --sysroot= \
+# RUN:   | FileCheck --check-prefix=CHECK-LAYERED-PRINT-MULTI-DIRECTORY %s
+# CHECK-LAYERED-PRINT-MULTI-DIRECTORY:  arm-none-eabi/thumb/v8.1-m.main/fp
+# CHECK-LAYERED-PRINT-MULTI-DIRECTORY-NEXT: arm-none-eabi/thumb/v8.1-m.main/fp/noexcept
+
 # RUN: %T/baremetal_multilib/bin/clang -no-canonical-prefixes -print-multi-lib 2>&1 \
 # RUN: --target=arm-none-eabi --sysroot= \
 # RUN:   | FileCheck --check-prefix=CHECK-PRINT-MULTI-LIB %s
@@ -38,6 +55,7 @@
 # CHECK-PRINT-MULTI-LIB: arm-none-eabi/thumb/v8-m.main/fp;@-target=thumbv8m.main-none-eabihf
 # CHECK-PRINT-MULTI-LIB: arm-none-eabi/thumb/v8.1-m.main/fp;@-target=thumbv8.1m.main-none-eabihf
 # CHECK-PRINT-MULTI-LIB: arm-none-eabi/thumb/v8.1-m.main/nofp/mve;@-target=arm-none-eabihf@march=armv8.1m.main+nofp+mve
+# CHECK-PRINT-MULTI-LIB: arm-none-eabi/thumb/v8.1-m.main/fp/noexcept;@-target=thumbv8.1m.main-none-eabihf@fno-exceptions
 
 # RUN: %T/baremetal_multilib/bin/clang -no-canonical-prefixes -x assembler -mexecute-only \
 # RUN: --target=arm-none-eabi --sysroot= %s -c -### 2>&1 \
@@ -117,6 +135,14 @@
   Flags: [target=thumbv8.1m.main-none-unknown-eabihf, march=+mve]
   PrintOptions: [--target=arm-none-eabihf, -march=armv8.1m.main+nofp+mve]
 
+# A specialisation of v8.1-m.main/fp without exceptions.
+# This layers over the top of the regular v8.1-m.main/fp so it doesn't
+# need to have its own include directory or C library, thereby saving
+# disk space.
+- Dir: arm-none-eabi/thumb/v8.1-m.main/fp/noexcept
+  Flags: [target=thumbv8.1m.main-none-unknown-eabihf, hasfpu, fno-exceptions]
+  PrintOptions: [--target=thumbv8.1m.main-none-eabihf, -fno-exceptions]
+
 
 # The second section of the file is a map from auto-detected flags
 # to custom flags. The auto-detected flags can be printed out
Index: clang/lib/Driver/ToolChains/BareMetal.h
===
--- clang/lib/Driver/ToolChains/BareMetal.h
+++ clang/lib/Driver/ToolChains/BareMetal.h
@@ -71,6 +71,9 @@
   void AddLinkRuntimeLib(const llvm::opt::ArgList &Args,
  llvm::opt::ArgStringList &CmdArgs) const;
   std::string computeSysRoot() const override;
+
+private:
+  llvm::SmallVector getOrderedMultilibs() const;
 };
 
 } // namespace toolchains
Index: clang/lib/Driver/ToolChains/BareMetal.cpp
===
--- clang/lib/Driver/ToolChains/BareMetal.cpp
+++ clang/lib/Driver/ToolChains/BareMetal.cpp
@@ -103,9 +103,12 @@
   findMultilibs(D, Triple, Args);
   SmallString<128> SysRoot(computeSysRoot());
   if (!SysRoot.empty()) {
-llvm::sys::path::append(SysRoot, "lib");
-getFilePaths().push_back(std::string(SysRoot));
-getLibraryPaths().push_back(std::string(SysRoot));
+for (const Multilib &M : getOrderedMultilibs()) {
+  SmallString<128> Dir(SysRoot);
+  llvm::sys::path::append(Dir, M.osSuffix(), "lib");
+  getFileP

[PATCH] D143587: [Docs] Multilib design

2023-03-14 Thread Michael Platings via Phabricator via cfe-commits
michaelplatings updated this revision to Diff 505293.
michaelplatings added a comment.

Rebase


Repository:
  rG LLVM Github Monorepo

CHANGES SINCE LAST ACTION
  https://reviews.llvm.org/D143587/new/

https://reviews.llvm.org/D143587

Files:
  clang/docs/Multilib.rst
  clang/docs/index.rst
  clang/include/clang/Driver/Multilib.h

Index: clang/include/clang/Driver/Multilib.h
===
--- clang/include/clang/Driver/Multilib.h
+++ clang/include/clang/Driver/Multilib.h
@@ -72,6 +72,8 @@
   /// options and look similar to them, and others can be defined by a
   /// particular multilib.yaml. A multilib is considered compatible if its flags
   /// are a subset of the flags derived from the Clang command line options.
+  /// See clang/docs/Multilib.rst for further explanation of how flags may be
+  /// generated and used.
   const flags_list &flags() const { return Flags; }
 
   /// Returns the options that should be used for clang -print-multi-lib
Index: clang/docs/index.rst
===
--- clang/docs/index.rst
+++ clang/docs/index.rst
@@ -100,6 +100,7 @@
CodeOwners
InternalsManual
DriverInternals
+   Multilib
OffloadingDesign
PCHInternals
ItaniumMangleAbiTags
Index: clang/docs/Multilib.rst
===
--- /dev/null
+++ clang/docs/Multilib.rst
@@ -0,0 +1,327 @@
+
+Multilib
+
+
+Introduction
+
+
+This document describes how multilib is implemented in Clang.
+
+What is multilib and why might you care?
+If you're :doc:`cross compiling` then you can't use native
+system headers and libraries. To address this, you can use a combination of
+``--sysroot``, ``-isystem`` and ``-L`` options to point Clang at suitable
+directories for your target.
+However, when there are many possible directories to choose from, it's not
+necessarily obvious which one to pick.
+Multilib allows a toolchain designer to imbue the toolchain with the ability to
+pick a suitable directory automatically, based on the options the user provides
+to Clang. For example, if the user specifies
+``--target=arm-none-eabi -mcpu=cortex-m4`` the toolchain can choose a directory
+containing headers and libraries suitable for Armv7E-M, because it knows that's
+a suitable architecture for Arm Cortex-M4.
+Multilib can also choose between libraries for the same architecture based on
+other options. For example if the user specifies ``-fno-exceptions`` then a
+toolchain could select libraries built without exception support, thereby
+reducing the size of the resulting binary.
+
+Design
+==
+
+Clang supports GCC's ``-print-multi-lib`` and ``-print-multi-directory``
+options. These are described in
+`GCC Developer Options `_.
+
+There are two ways to configure multilib in Clang: hard-coded or via a
+configuration file.
+
+Hard-coded Multilib
+===
+
+The available libraries can be hard-coded in Clang. Typically this is done
+using the ``MultilibBuilder`` interface in
+``clang/include/clang/Driver/MultilibBuilder.h``.
+There are many examples of this in ``lib/Driver/ToolChains/Gnu.cpp``.
+The remainder of this document will not focus on this type of multilib.
+
+EXPERIMENTAL Multilib via configuration file
+
+
+Some Clang toolchains support loading multilib configuration from a
+``multilib.yaml`` configuration file.
+
+A ``multilib.yaml`` configuration file specifies which multilib variants are
+available, their relative location, what compilation options were used to build
+them, and the criteria by which they are selected.
+
+Multilib processing
+===
+
+Clang goes through the following steps to use multilib from a configuration
+file:
+#. Convert command line options to flags. Clang can accept the same
+   information via different options - for example,
+   ``--target=arm-none-eabi -march=armv7-m`` and
+   ``--target=armv7m-none-eabi`` are equivalent. Clang can also accept many
+   independent pieces of information within a single option - for example
+   ``-march=armv8.1m.main+fp+mve`` specifies the architecture and two
+   extensions in a single command line option.
+   To make it easier for the multilib system, Clang converts the command line
+   options into a standard set of simpler "flags". In many cases these flags
+   will look like a command line option with the leading ``-`` stripped off,
+   but where a suitable form for the flag doesn't exist in command line
+   options then its form will be different. For example, an Arm architecture
+   extension is represented like ``march=+mve`` since there's no way to specify
+   it in isolation in a command line option.
+   To see what flags are emitted for a given set of command line options, use
+   the ``-print-multi-selection-flags-experimen

[PATCH] D143587: [Docs] Multilib design

2023-03-15 Thread Michael Platings via Phabricator via cfe-commits
michaelplatings updated this revision to Diff 505451.
michaelplatings marked an inline comment as done.
michaelplatings added a comment.

Add quotes


Repository:
  rG LLVM Github Monorepo

CHANGES SINCE LAST ACTION
  https://reviews.llvm.org/D143587/new/

https://reviews.llvm.org/D143587

Files:
  clang/docs/Multilib.rst
  clang/docs/index.rst
  clang/include/clang/Driver/Multilib.h

Index: clang/include/clang/Driver/Multilib.h
===
--- clang/include/clang/Driver/Multilib.h
+++ clang/include/clang/Driver/Multilib.h
@@ -72,6 +72,8 @@
   /// options and look similar to them, and others can be defined by a
   /// particular multilib.yaml. A multilib is considered compatible if its flags
   /// are a subset of the flags derived from the Clang command line options.
+  /// See clang/docs/Multilib.rst for further explanation of how flags may be
+  /// generated and used.
   const flags_list &flags() const { return Flags; }
 
   /// Returns the options that should be used for clang -print-multi-lib
Index: clang/docs/index.rst
===
--- clang/docs/index.rst
+++ clang/docs/index.rst
@@ -100,6 +100,7 @@
CodeOwners
InternalsManual
DriverInternals
+   Multilib
OffloadingDesign
PCHInternals
ItaniumMangleAbiTags
Index: clang/docs/Multilib.rst
===
--- /dev/null
+++ clang/docs/Multilib.rst
@@ -0,0 +1,327 @@
+
+Multilib
+
+
+Introduction
+
+
+This document describes how multilib is implemented in Clang.
+
+What is multilib and why might you care?
+If you're :doc:`cross compiling` then you can't use native
+system headers and libraries. To address this, you can use a combination of
+``--sysroot``, ``-isystem`` and ``-L`` options to point Clang at suitable
+directories for your target.
+However, when there are many possible directories to choose from, it's not
+necessarily obvious which one to pick.
+Multilib allows a toolchain designer to imbue the toolchain with the ability to
+pick a suitable directory automatically, based on the options the user provides
+to Clang. For example, if the user specifies
+``--target=arm-none-eabi -mcpu=cortex-m4`` the toolchain can choose a directory
+containing headers and libraries suitable for Armv7E-M, because it knows that's
+a suitable architecture for Arm Cortex-M4.
+Multilib can also choose between libraries for the same architecture based on
+other options. For example if the user specifies ``-fno-exceptions`` then a
+toolchain could select libraries built without exception support, thereby
+reducing the size of the resulting binary.
+
+Design
+==
+
+Clang supports GCC's ``-print-multi-lib`` and ``-print-multi-directory``
+options. These are described in
+`GCC Developer Options `_.
+
+There are two ways to configure multilib in Clang: hard-coded or via a
+configuration file.
+
+Hard-coded Multilib
+===
+
+The available libraries can be hard-coded in Clang. Typically this is done
+using the ``MultilibBuilder`` interface in
+``clang/include/clang/Driver/MultilibBuilder.h``.
+There are many examples of this in ``lib/Driver/ToolChains/Gnu.cpp``.
+The remainder of this document will not focus on this type of multilib.
+
+EXPERIMENTAL Multilib via configuration file
+
+
+Some Clang toolchains support loading multilib configuration from a
+``multilib.yaml`` configuration file.
+
+A ``multilib.yaml`` configuration file specifies which multilib variants are
+available, their relative location, what compilation options were used to build
+them, and the criteria by which they are selected.
+
+Multilib processing
+===
+
+Clang goes through the following steps to use multilib from a configuration
+file:
+#. Convert command line options to flags. Clang can accept the same
+   information via different options - for example,
+   ``--target=arm-none-eabi -march=armv7-m`` and
+   ``--target=armv7m-none-eabi`` are equivalent. Clang can also accept many
+   independent pieces of information within a single option - for example
+   ``-march=armv8.1m.main+fp+mve`` specifies the architecture and two
+   extensions in a single command line option.
+   To make it easier for the multilib system, Clang converts the command line
+   options into a standard set of simpler "flags". In many cases these flags
+   will look like a command line option with the leading ``-`` stripped off,
+   but where a suitable form for the flag doesn't exist in command line
+   options then its form will be different. For example, an Arm architecture
+   extension is represented like ``march=+mve`` since there's no way to specify
+   it in isolation in a command line option.
+   To see what flags are emitted for a given set of command line options

[PATCH] D146141: [ARM] Use FPUKind enum instead of unsigned

2023-03-15 Thread Michael Platings via Phabricator via cfe-commits
michaelplatings created this revision.
michaelplatings added reviewers: simon_tatham, dcandler.
Herald added subscribers: hiraditya, kristof.beyls.
Herald added a project: All.
michaelplatings requested review of this revision.
Herald added subscribers: llvm-commits, cfe-commits, MaskRay.
Herald added projects: clang, LLVM.

Also rename some FPUID variables to FPUKind now it's clear that's what
they are.


Repository:
  rG LLVM Github Monorepo

https://reviews.llvm.org/D146141

Files:
  clang/lib/Basic/Targets/ARM.cpp
  clang/lib/Driver/ToolChains/Arch/ARM.cpp
  llvm/include/llvm/MC/MCStreamer.h
  llvm/include/llvm/TargetParser/ARMTargetParser.h
  llvm/lib/Target/ARM/AsmParser/ARMAsmParser.cpp
  llvm/lib/Target/ARM/MCTargetDesc/ARMELFStreamer.cpp
  llvm/lib/Target/ARM/MCTargetDesc/ARMTargetStreamer.cpp
  llvm/lib/TargetParser/ARMTargetParser.cpp
  llvm/unittests/TargetParser/TargetParserTest.cpp

Index: llvm/unittests/TargetParser/TargetParserTest.cpp
===
--- llvm/unittests/TargetParser/TargetParserTest.cpp
+++ llvm/unittests/TargetParser/TargetParserTest.cpp
@@ -120,7 +120,7 @@
   ARM::ArchKind AK = ARM::parseCPUArch(params.CPUName);
   EXPECT_EQ(params.ExpectedArch, ARM::getArchName(AK));
 
-  unsigned FPUKind = ARM::getDefaultFPU(params.CPUName, AK);
+  ARM::FPUKind FPUKind = ARM::getDefaultFPU(params.CPUName, AK);
   EXPECT_EQ(params.ExpectedFPU, ARM::getFPUName(FPUKind));
 
   uint64_t default_extensions = ARM::getDefaultExtensions(params.CPUName, AK);
@@ -765,10 +765,10 @@
 testArchExtDependency(const char *ArchExt,
   const std::initializer_list &Expected) {
   std::vector Features;
-  unsigned FPUID;
+  ARM::FPUKind FPUKind;
 
   if (!ARM::appendArchExtFeatures("", ARM::ArchKind::ARMV8_1MMainline, ArchExt,
-  Features, FPUID))
+  Features, FPUKind))
 return false;
 
   return llvm::all_of(Expected, [&](StringRef Ext) {
Index: llvm/lib/TargetParser/ARMTargetParser.cpp
===
--- llvm/lib/TargetParser/ARMTargetParser.cpp
+++ llvm/lib/TargetParser/ARMTargetParser.cpp
@@ -147,7 +147,8 @@
   return getProfileKind(parseArch(Arch));
 }
 
-bool ARM::getFPUFeatures(unsigned FPUKind, std::vector &Features) {
+bool ARM::getFPUFeatures(ARM::FPUKind FPUKind,
+ std::vector &Features) {
 
   if (FPUKind >= FK_LAST || FPUKind == FK_INVALID)
 return false;
@@ -211,7 +212,7 @@
   return true;
 }
 
-unsigned ARM::parseFPU(StringRef FPU) {
+ARM::FPUKind ARM::parseFPU(StringRef FPU) {
   StringRef Syn = getFPUSynonym(FPU);
   for (const auto &F : FPUNames) {
 if (Syn == F.Name)
@@ -220,7 +221,7 @@
   return FK_INVALID;
 }
 
-ARM::NeonSupportLevel ARM::getFPUNeonSupportLevel(unsigned FPUKind) {
+ARM::NeonSupportLevel ARM::getFPUNeonSupportLevel(ARM::FPUKind FPUKind) {
   if (FPUKind >= FK_LAST)
 return NeonSupportLevel::None;
   return FPUNames[FPUKind].NeonSupport;
@@ -243,33 +244,33 @@
   .Default(FPU);
 }
 
-StringRef ARM::getFPUName(unsigned FPUKind) {
+StringRef ARM::getFPUName(ARM::FPUKind FPUKind) {
   if (FPUKind >= FK_LAST)
 return StringRef();
   return FPUNames[FPUKind].Name;
 }
 
-ARM::FPUVersion ARM::getFPUVersion(unsigned FPUKind) {
+ARM::FPUVersion ARM::getFPUVersion(ARM::FPUKind FPUKind) {
   if (FPUKind >= FK_LAST)
 return FPUVersion::NONE;
   return FPUNames[FPUKind].FPUVer;
 }
 
-ARM::FPURestriction ARM::getFPURestriction(unsigned FPUKind) {
+ARM::FPURestriction ARM::getFPURestriction(ARM::FPUKind FPUKind) {
   if (FPUKind >= FK_LAST)
 return FPURestriction::None;
   return FPUNames[FPUKind].Restriction;
 }
 
-unsigned ARM::getDefaultFPU(StringRef CPU, ARM::ArchKind AK) {
+ARM::FPUKind ARM::getDefaultFPU(StringRef CPU, ARM::ArchKind AK) {
   if (CPU == "generic")
 return ARM::ARMArchNames[static_cast(AK)].DefaultFPU;
 
-  return StringSwitch(CPU)
+  return StringSwitch(CPU)
 #define ARM_CPU_NAME(NAME, ID, DEFAULT_FPU, IS_DEFAULT, DEFAULT_EXT)   \
   .Case(NAME, DEFAULT_FPU)
 #include "llvm/TargetParser/ARMTargetParser.def"
-   .Default(ARM::FK_INVALID);
+  .Default(ARM::FK_INVALID);
 }
 
 uint64_t ARM::getDefaultExtensions(StringRef CPU, ARM::ArchKind AK) {
@@ -362,7 +363,7 @@
   return StringRef();
 }
 
-static unsigned findDoublePrecisionFPU(unsigned InputFPUKind) {
+static ARM::FPUKind findDoublePrecisionFPU(ARM::FPUKind InputFPUKind) {
   const ARM::FPUName &InputFPU = ARM::FPUNames[InputFPUKind];
 
   // If the input FPU already supports double-precision, then there
@@ -394,7 +395,7 @@
 bool ARM::appendArchExtFeatures(StringRef CPU, ARM::ArchKind AK,
 StringRef ArchExt,
 std::vector &Features,
-unsigned &ArgFPUID) {
+ARM::FPUKind &ArgFPUKind) {
 
   size_t StartingNumFeatures = Features.size();

[PATCH] D142933: Add -print-multi-selection-flags-experimental option

2023-03-15 Thread Michael Platings via Phabricator via cfe-commits
michaelplatings updated this revision to Diff 505643.
michaelplatings marked 2 inline comments as done.
michaelplatings added a comment.

Rebase on D146141 


Repository:
  rG LLVM Github Monorepo

CHANGES SINCE LAST ACTION
  https://reviews.llvm.org/D142933/new/

https://reviews.llvm.org/D142933

Files:
  clang/include/clang/Driver/Options.td
  clang/include/clang/Driver/ToolChain.h
  clang/lib/Driver/Driver.cpp
  clang/lib/Driver/ToolChain.cpp
  clang/lib/Driver/ToolChains/Arch/ARM.cpp
  clang/lib/Driver/ToolChains/Arch/ARM.h
  clang/test/Driver/print-multi-selection-flags.c

Index: clang/test/Driver/print-multi-selection-flags.c
===
--- /dev/null
+++ clang/test/Driver/print-multi-selection-flags.c
@@ -0,0 +1,54 @@
+// RUN: %clang -print-multi-selection-flags-experimental --target=aarch64-linux -fc++-abi=itanium -fsanitize=address | FileCheck --check-prefix=CHECK-LINUX %s
+// CHECK-LINUX: fc++-abi=itanium
+// CHECK-LINUX: fexceptions
+// CHECK-LINUX: frtti
+// CHECK-LINUX: fsanitize=address
+// CHECK-LINUX: target=aarch64-unknown-linux
+
+// RUN: %clang -print-multi-selection-flags-experimental --target=aarch64-fuchsia -fsanitize=hwaddress | FileCheck --check-prefix=CHECK-FUCHSIA %s
+// CHECK-FUCHSIA: fsanitize=hwaddress
+// CHECK-FUCHSIA: target=aarch64-unknown-fuchsia
+
+// RUN: %clang -print-multi-selection-flags-experimental --target=arm-none-eabi -mfloat-abi=soft -fno-exceptions -fno-rtti | FileCheck --check-prefix=CHECK-ARMV4T %s
+// CHECK-ARMV4T: fno-exceptions
+// CHECK-ARMV4T: fno-rtti
+// CHECK-ARMV4T: mfloat-abi=soft
+// CHECK-ARMV4T: mfpu=none
+// CHECK-ARMV4T: target=armv4t-none-unknown-eabi
+
+// RUN: %clang -print-multi-selection-flags-experimental --target=armv7em-none-eabi -mfloat-abi=softfp | FileCheck --check-prefix=CHECK-SOFTFP %s
+// CHECK-SOFTFP: mfloat-abi=softfp
+// CHECK-SOFTFP: mfpu=fpv4-sp-d16
+// CHECK-SOFTFP: target=thumbv7em-none-unknown-eabi
+
+// RUN: %clang -print-multi-selection-flags-experimental --target=arm-none-eabihf -march=armv7em -mfpu=fpv5-d16 | FileCheck --check-prefix=CHECK-HARD %s
+// CHECK-HARD: mfloat-abi=hard
+// CHECK-HARD: mfpu=fpv5-d16
+// CHECK-HARD: target=thumbv7em-none-unknown-eabihf
+
+// RUN: %clang -print-multi-selection-flags-experimental --target=arm-none-eabi -mfloat-abi=soft -march=armv8-m.main+nofp | FileCheck --check-prefix=CHECK-V8MMAIN-NOFP %s
+// CHECK-V8MMAIN-NOFP: mfloat-abi=soft
+// CHECK-V8MMAIN-NOFP: mfpu=none
+// CHECK-V8MMAIN-NOFP: target=thumbv8m.main-none-unknown-eabi
+
+// RUN: %clang -print-multi-selection-flags-experimental --target=arm-none-eabi -mfloat-abi=hard -march=armv8.1m.main+mve.fp | FileCheck --check-prefix=CHECK-MVE %s
+// CHECK-MVE: march=+mve
+// CHECK-MVE: march=+mve.fp
+// CHECK-MVE: mfloat-abi=hard
+// CHECK-MVE: mfpu=fp-armv8-fullfp16-sp-d16
+// CHECK-MVE: target=thumbv8.1m.main-none-unknown-eabihf
+
+// RUN: %clang -print-multi-selection-flags-experimental --target=arm-none-eabi -march=armv8.1m.main+mve+nofp | FileCheck --check-prefix=CHECK-MVENOFP %s
+// CHECK-MVENOFP: march=+mve
+// CHECK-MVENOFP-NOT: march=+mve.fp
+// CHECK-MVENOFP: mfpu=none
+
+// RUN: %clang -print-multi-selection-flags-experimental --target=aarch64-none-elf -march=armv8-a+lse | FileCheck --check-prefix=CHECK-LSE %s
+// CHECK-LSE: march=+lse
+
+// RUN: %clang -print-multi-selection-flags-experimental --target=aarch64-none-elf -march=armv8.5-a+sve+sve2 | FileCheck --check-prefix=CHECK-SVE2 %s
+// RUN: %clang -print-multi-selection-flags-experimental --target=aarch64-none-elf -march=armv9-a| FileCheck --check-prefix=CHECK-SVE2 %s
+// CHECK-SVE2: march=+simd
+// CHECK-SVE2: march=+sve
+// CHECK-SVE2: march=+sve2
+// CHECK-SVE2: target=aarch64-none-unknown-elf
Index: clang/lib/Driver/ToolChains/Arch/ARM.h
===
--- clang/lib/Driver/ToolChains/Arch/ARM.h
+++ clang/lib/Driver/ToolChains/Arch/ARM.h
@@ -63,9 +63,11 @@
 void getARMArchCPUFromArgs(const llvm::opt::ArgList &Args,
llvm::StringRef &Arch, llvm::StringRef &CPU,
bool FromAs = false);
-void getARMTargetFeatures(const Driver &D, const llvm::Triple &Triple,
-  const llvm::opt::ArgList &Args,
-  std::vector &Features, bool ForAS);
+llvm::ARM::FPUKind getARMTargetFeatures(const Driver &D,
+const llvm::Triple &Triple,
+const llvm::opt::ArgList &Args,
+std::vector &Features,
+bool ForAS);
 int getARMSubArchVersionNumber(const llvm::Triple &Triple);
 bool isARMMProfile(const llvm::Triple &Triple);
 bool isARMAProfile(const llvm::Triple &Triple);
Index: clang/lib/Driver/ToolChains/Arch/ARM.cpp
===
--- cla

[PATCH] D142986: Enable multilib.yaml in the BareMetal ToolChain

2023-03-15 Thread Michael Platings via Phabricator via cfe-commits
michaelplatings updated this revision to Diff 505644.
michaelplatings added a comment.

Rebase on D146141 


Repository:
  rG LLVM Github Monorepo

CHANGES SINCE LAST ACTION
  https://reviews.llvm.org/D142986/new/

https://reviews.llvm.org/D142986

Files:
  clang/lib/Driver/ToolChain.cpp
  clang/lib/Driver/ToolChains/Arch/ARM.cpp
  clang/lib/Driver/ToolChains/Arch/ARM.h
  clang/lib/Driver/ToolChains/BareMetal.cpp
  clang/test/Driver/baremetal-multilib.yaml
  clang/test/Driver/baremetal.cpp
  clang/test/Driver/lit.local.cfg

Index: clang/test/Driver/lit.local.cfg
===
--- clang/test/Driver/lit.local.cfg
+++ clang/test/Driver/lit.local.cfg
@@ -1,7 +1,7 @@
 from lit.llvm import llvm_config
 
 config.suffixes = ['.c', '.cpp', '.cppm', '.h', '.m', '.mm', '.S', '.s', '.f90', '.F90', '.f95',
-   '.cu', '.rs', '.cl', '.clcpp', '.hip', '.hipi', '.hlsl']
+   '.cu', '.rs', '.cl', '.clcpp', '.hip', '.hipi', '.hlsl', '.yaml']
 config.substitutions = list(config.substitutions)
 config.substitutions.insert(0,
 ('%clang_cc1',
Index: clang/test/Driver/baremetal.cpp
===
--- clang/test/Driver/baremetal.cpp
+++ clang/test/Driver/baremetal.cpp
@@ -118,9 +118,9 @@
 // Verify that the bare metal driver does not include any host system paths:
 // CHECK-AARCH64-NO-HOST-INC: InstalledDir: [[INSTALLEDDIR:.+]]
 // CHECK-AARCH64-NO-HOST-INC: "-resource-dir" "[[RESOURCE:[^"]+]]"
-// CHECK-AARCH64-NO-HOST-INC-SAME: "-internal-isystem" "[[INSTALLEDDIR]]{{[/\\]+}}..{{[/\\]+}}lib{{[/\\]+}}clang-runtimes{{[/\\]+}}aarch64-none-elf{{[/\\]+}}include{{[/\\]+}}c++{{[/\\]+}}v1"
+// CHECK-AARCH64-NO-HOST-INC-SAME: "-internal-isystem" "[[INSTALLEDDIR]]{{[/\\]+}}..{{[/\\]+}}lib{{[/\\]+}}clang-runtimes{{[/\\]+[^"]*}}include{{[/\\]+}}c++{{[/\\]+}}v1"
 // CHECK-AARCH64-NO-HOST-INC-SAME: "-internal-isystem" "[[RESOURCE]]{{[/\\]+}}include"
-// CHECK-AARCH64-NO-HOST-INC-SAME: "-internal-isystem" "[[INSTALLEDDIR]]{{[/\\]+}}..{{[/\\]+}}lib{{[/\\]+}}clang-runtimes{{[/\\]+}}aarch64-none-elf{{[/\\]+}}include"
+// CHECK-AARCH64-NO-HOST-INC-SAME: "-internal-isystem" "[[INSTALLEDDIR]]{{[/\\]+}}..{{[/\\]+}}lib{{[/\\]+}}clang-runtimes{{[/\\]+[^"]*}}include"
 
 // RUN: %clang %s -### --target=riscv64-unknown-elf -o %t.out -L some/directory/user/asked/for \
 // RUN: --sysroot=%S/Inputs/basic_riscv64_tree/riscv64-unknown-elf 2>&1 \
Index: clang/test/Driver/baremetal-multilib.yaml
===
--- /dev/null
+++ clang/test/Driver/baremetal-multilib.yaml
@@ -0,0 +1,142 @@
+# REQUIRES: shell
+# UNSUPPORTED: system-windows
+
+# RUN: rm -rf %T/baremetal_multilib
+# RUN: mkdir -p %T/baremetal_multilib/bin
+# RUN: mkdir -p %T/baremetal_multilib/lib/clang-runtimes/arm-none-eabi/thumb/v8-m.main/fp/lib
+# RUN: touch %T/baremetal_multilib/lib/clang-runtimes/arm-none-eabi/thumb/v8-m.main/fp/lib/libclang_rt.builtins.a
+# RUN: ln -s %clang %T/baremetal_multilib/bin/clang
+# RUN: ln -s %s %T/baremetal_multilib/lib/clang-runtimes/multilib.yaml
+
+# RUN: %T/baremetal_multilib/bin/clang -no-canonical-prefixes -x c++ %s -### -o %t.out 2>&1 \
+# RUN: --target=thumbv8m.main-none-eabihf --sysroot= \
+# RUN:   | FileCheck -DSYSROOT=%T/baremetal_multilib %s
+# CHECK:  "-cc1" "-triple" "thumbv8m.main-none-unknown-eabihf"
+# CHECK-SAME: "-internal-isystem" "[[SYSROOT]]/bin/../lib/clang-runtimes/arm-none-eabi/thumb/v8-m.main/fp/include/c++/v1"
+# CHECK-SAME: "-internal-isystem" "[[SYSROOT]]/bin/../lib/clang-runtimes/arm-none-eabi/thumb/v8-m.main/fp/include"
+# CHECK-SAME: "-x" "c++" "{{.*}}baremetal-multilib.yaml"
+# CHECK-NEXT: ld{{(.exe)?}}" "{{.*}}.o" "-Bstatic"
+# CHECK-SAME: "-L[[SYSROOT]]/bin/../lib/clang-runtimes/arm-none-eabi/thumb/v8-m.main/fp/lib"
+# CHECK-SAME: "-lc" "-lm" "-lclang_rt.builtins"
+# CHECK-SAME: "-o" "{{.*}}.tmp.out"
+
+# RUN: %T/baremetal_multilib/bin/clang -no-canonical-prefixes -print-multi-directory 2>&1 \
+# RUN: --target=thumbv8m.main-none-eabihf --sysroot= \
+# RUN:   | FileCheck --check-prefix=CHECK-PRINT-MULTI-DIRECTORY %s
+# CHECK-PRINT-MULTI-DIRECTORY: arm-none-eabi/thumb/v8-m.main/fp
+
+# RUN: %T/baremetal_multilib/bin/clang -no-canonical-prefixes -print-multi-lib 2>&1 \
+# RUN: --target=arm-none-eabi --sysroot= \
+# RUN:   | FileCheck --check-prefix=CHECK-PRINT-MULTI-LIB %s
+# CHECK-PRINT-MULTI-LIB: arm-none-eabi/thumb/v6-m/nofp;@-target=thumbv6m-none-eabi@mfloat-abi=soft
+# CHECK-PRINT-MULTI-LIB: arm-none-eabi/thumb/v7-m/nofp;@-target=thumbv7m-none-eabi@mfloat-abi=soft
+# CHECK-PRINT-MULTI-LIB: arm-none-eabi/thumb/v7e-m/nofp;@-target=thumbv7em-none-eabi@mfloat-abi=soft@mfpu=none
+# CHECK-PRINT-MULTI-LIB: arm-none-eabi/thumb/v8-m.main/nofp;@-target=arm-none-eabi@mfloat-abi=soft@march=armv8m.main+nofp
+# CHECK-PRINT-MULTI-LIB: arm-none-eabi/thumb/v8.1-m.main/nofp/nomve;@-target=arm-none-eabi@

[PATCH] D142933: Add -print-multi-selection-flags-experimental option

2023-03-15 Thread Michael Platings via Phabricator via cfe-commits
michaelplatings added inline comments.



Comment at: clang/lib/Driver/ToolChain.cpp:237-245
+  // Enumerate boolean flags we care about for the purposes of multilib here.
+  // There must be a smarter way to do it but this gets us started.
+  const struct HasFlag {
+ID Pos, Neg;
+bool Default;
+  } HasFlagList[] = {
+  {OPT_fexceptions, OPT_fno_exceptions, true},

phosek wrote:
> Would it be possible to add this information to 
> https://github.com/llvm/llvm-project/blob/main/clang/include/clang/Driver/Options.td?
>  I think that would be more maintainable.
I thought about that, and it would be nice - it's a shame that this information 
gets copy-pasted across the Clang sources - there are already 5 or so places 
that do this. However for this change I think that would be too much scope 
creep so I've stuck with the status quo.



Comment at: clang/lib/Driver/ToolChains/Arch/ARM.cpp:441
+   std::vector &Features, bool ForAS,
+   unsigned *OutFPUKind) {
   bool KernelOrKext =

phosek wrote:
> Can we use `ARM::FPUKind` as a type here?
I made a new change, D146141, that makes this possible. I've rebased this patch 
on that change now so this is done.



Comment at: clang/lib/Driver/ToolChains/Arch/ARM.cpp:556
   // Honor -mfpu=. ClangAs gives preference to -Wa,-mfpu=.
   unsigned FPUID = llvm::ARM::FK_INVALID;
   const Arg *FPUArg = Args.getLastArg(options::OPT_mfpu_EQ);

phosek wrote:
> Is this variable used anywhere in this function?
Yes, although previously in this scope only for `FPUID == llvm::ARM::FK_NONE`. 
Now we're using it more since we're returning it.



Comment at: clang/lib/Driver/ToolChains/Arch/ARM.h:70
+  std::vector &Features, bool ForAS,
+  unsigned *OutFPUKind = nullptr);
 int getARMSubArchVersionNumber(const llvm::Triple &Triple);

phosek wrote:
> Using output argument isn't very common in LLVM and even in this particular 
> case seems a bit ad-hoc. I'm wondering if we could instead extract this logic 
> into a new function, for example `getARMFPUFeatures`?
It's not unusual in this area of the code. Usually the name is `ArgFPUKind` 
which I don't find descriptive so I went with `OutFPUKind` to make it clearer 
that it's an output of the function. However since the function had return type 
`void` I've now simply changed it to return `FPUKind` directly.

I spent a chunk of time looking into whether I could get a separate 
FPU-specific function. Finding the FPU is tightly coupled across a lot of code 
with finding the architecture and CPU. Although I'm sure the code could be 
better structured, the problem is also inherent because the floating point 
support is dependent on `-mfpu`, `-march`, `-mcpu`, `--target`, `-mfloat-abi` 
and possibly others so figuring everything out requires parsing many options. 
In short, I think returning FPUKind is the lesser evil here, even if it does 
seem a bit ad-hoc.


Repository:
  rG LLVM Github Monorepo

CHANGES SINCE LAST ACTION
  https://reviews.llvm.org/D142933/new/

https://reviews.llvm.org/D142933

___
cfe-commits mailing list
cfe-commits@lists.llvm.org
https://lists.llvm.org/cgi-bin/mailman/listinfo/cfe-commits


[PATCH] D146141: [ARM] Use FPUKind enum instead of unsigned

2023-03-16 Thread Michael Platings via Phabricator via cfe-commits
This revision was landed with ongoing or failed builds.
This revision was automatically updated to reflect the committed changes.
Closed by commit rG60bbf271b568: [ARM][NFC] Use FPUKind enum instead of 
unsigned (authored by michaelplatings).

Repository:
  rG LLVM Github Monorepo

CHANGES SINCE LAST ACTION
  https://reviews.llvm.org/D146141/new/

https://reviews.llvm.org/D146141

Files:
  clang/lib/Basic/Targets/ARM.cpp
  clang/lib/Driver/ToolChains/Arch/ARM.cpp
  llvm/include/llvm/MC/MCStreamer.h
  llvm/include/llvm/TargetParser/ARMTargetParser.h
  llvm/lib/Target/ARM/AsmParser/ARMAsmParser.cpp
  llvm/lib/Target/ARM/MCTargetDesc/ARMELFStreamer.cpp
  llvm/lib/Target/ARM/MCTargetDesc/ARMTargetStreamer.cpp
  llvm/lib/TargetParser/ARMTargetParser.cpp
  llvm/unittests/TargetParser/TargetParserTest.cpp

Index: llvm/unittests/TargetParser/TargetParserTest.cpp
===
--- llvm/unittests/TargetParser/TargetParserTest.cpp
+++ llvm/unittests/TargetParser/TargetParserTest.cpp
@@ -120,7 +120,7 @@
   ARM::ArchKind AK = ARM::parseCPUArch(params.CPUName);
   EXPECT_EQ(params.ExpectedArch, ARM::getArchName(AK));
 
-  unsigned FPUKind = ARM::getDefaultFPU(params.CPUName, AK);
+  ARM::FPUKind FPUKind = ARM::getDefaultFPU(params.CPUName, AK);
   EXPECT_EQ(params.ExpectedFPU, ARM::getFPUName(FPUKind));
 
   uint64_t default_extensions = ARM::getDefaultExtensions(params.CPUName, AK);
@@ -765,10 +765,10 @@
 testArchExtDependency(const char *ArchExt,
   const std::initializer_list &Expected) {
   std::vector Features;
-  unsigned FPUID;
+  ARM::FPUKind FPUKind;
 
   if (!ARM::appendArchExtFeatures("", ARM::ArchKind::ARMV8_1MMainline, ArchExt,
-  Features, FPUID))
+  Features, FPUKind))
 return false;
 
   return llvm::all_of(Expected, [&](StringRef Ext) {
Index: llvm/lib/TargetParser/ARMTargetParser.cpp
===
--- llvm/lib/TargetParser/ARMTargetParser.cpp
+++ llvm/lib/TargetParser/ARMTargetParser.cpp
@@ -147,7 +147,8 @@
   return getProfileKind(parseArch(Arch));
 }
 
-bool ARM::getFPUFeatures(unsigned FPUKind, std::vector &Features) {
+bool ARM::getFPUFeatures(ARM::FPUKind FPUKind,
+ std::vector &Features) {
 
   if (FPUKind >= FK_LAST || FPUKind == FK_INVALID)
 return false;
@@ -211,7 +212,7 @@
   return true;
 }
 
-unsigned ARM::parseFPU(StringRef FPU) {
+ARM::FPUKind ARM::parseFPU(StringRef FPU) {
   StringRef Syn = getFPUSynonym(FPU);
   for (const auto &F : FPUNames) {
 if (Syn == F.Name)
@@ -220,7 +221,7 @@
   return FK_INVALID;
 }
 
-ARM::NeonSupportLevel ARM::getFPUNeonSupportLevel(unsigned FPUKind) {
+ARM::NeonSupportLevel ARM::getFPUNeonSupportLevel(ARM::FPUKind FPUKind) {
   if (FPUKind >= FK_LAST)
 return NeonSupportLevel::None;
   return FPUNames[FPUKind].NeonSupport;
@@ -243,33 +244,33 @@
   .Default(FPU);
 }
 
-StringRef ARM::getFPUName(unsigned FPUKind) {
+StringRef ARM::getFPUName(ARM::FPUKind FPUKind) {
   if (FPUKind >= FK_LAST)
 return StringRef();
   return FPUNames[FPUKind].Name;
 }
 
-ARM::FPUVersion ARM::getFPUVersion(unsigned FPUKind) {
+ARM::FPUVersion ARM::getFPUVersion(ARM::FPUKind FPUKind) {
   if (FPUKind >= FK_LAST)
 return FPUVersion::NONE;
   return FPUNames[FPUKind].FPUVer;
 }
 
-ARM::FPURestriction ARM::getFPURestriction(unsigned FPUKind) {
+ARM::FPURestriction ARM::getFPURestriction(ARM::FPUKind FPUKind) {
   if (FPUKind >= FK_LAST)
 return FPURestriction::None;
   return FPUNames[FPUKind].Restriction;
 }
 
-unsigned ARM::getDefaultFPU(StringRef CPU, ARM::ArchKind AK) {
+ARM::FPUKind ARM::getDefaultFPU(StringRef CPU, ARM::ArchKind AK) {
   if (CPU == "generic")
 return ARM::ARMArchNames[static_cast(AK)].DefaultFPU;
 
-  return StringSwitch(CPU)
+  return StringSwitch(CPU)
 #define ARM_CPU_NAME(NAME, ID, DEFAULT_FPU, IS_DEFAULT, DEFAULT_EXT)   \
   .Case(NAME, DEFAULT_FPU)
 #include "llvm/TargetParser/ARMTargetParser.def"
-   .Default(ARM::FK_INVALID);
+  .Default(ARM::FK_INVALID);
 }
 
 uint64_t ARM::getDefaultExtensions(StringRef CPU, ARM::ArchKind AK) {
@@ -362,7 +363,7 @@
   return StringRef();
 }
 
-static unsigned findDoublePrecisionFPU(unsigned InputFPUKind) {
+static ARM::FPUKind findDoublePrecisionFPU(ARM::FPUKind InputFPUKind) {
   const ARM::FPUName &InputFPU = ARM::FPUNames[InputFPUKind];
 
   // If the input FPU already supports double-precision, then there
@@ -394,7 +395,7 @@
 bool ARM::appendArchExtFeatures(StringRef CPU, ARM::ArchKind AK,
 StringRef ArchExt,
 std::vector &Features,
-unsigned &ArgFPUID) {
+ARM::FPUKind &ArgFPUKind) {
 
   size_t StartingNumFeatures = Features.size();
   const bool Negated = stripNegationPrefix(ArchExt);
@@ -417,7 +418,7 @@
 CPU = "generic";
 
 

[PATCH] D142905: [Driver] Change multilib selection algorithm

2023-03-17 Thread Michael Platings via Phabricator via cfe-commits
michaelplatings updated this revision to Diff 506044.
michaelplatings added a comment.

fix typo in comment


Repository:
  rG LLVM Github Monorepo

CHANGES SINCE LAST ACTION
  https://reviews.llvm.org/D142905/new/

https://reviews.llvm.org/D142905

Files:
  clang/include/clang/Driver/Multilib.h
  clang/include/clang/Driver/MultilibBuilder.h
  clang/lib/Driver/Multilib.cpp
  clang/lib/Driver/MultilibBuilder.cpp
  clang/lib/Driver/ToolChains/Fuchsia.cpp
  clang/unittests/Driver/MultilibBuilderTest.cpp
  clang/unittests/Driver/MultilibTest.cpp

Index: clang/unittests/Driver/MultilibTest.cpp
===
--- clang/unittests/Driver/MultilibTest.cpp
+++ clang/unittests/Driver/MultilibTest.cpp
@@ -33,14 +33,14 @@
 }
 
 TEST(MultilibTest, OpEqReflexivity3) {
-  Multilib M1({}, {}, {}, 0, {"+foo"});
-  Multilib M2({}, {}, {}, 0, {"+foo"});
+  Multilib M1({}, {}, {}, {"+foo"});
+  Multilib M2({}, {}, {}, {"+foo"});
   ASSERT_TRUE(M1 == M2) << "Multilibs with the same flag should be the same";
 }
 
 TEST(MultilibTest, OpEqInequivalence1) {
-  Multilib M1({}, {}, {}, 0, {"+foo"});
-  Multilib M2({}, {}, {}, 0, {"-foo"});
+  Multilib M1({}, {}, {}, {"+foo"});
+  Multilib M2({}, {}, {}, {"-foo"});
   ASSERT_FALSE(M1 == M2) << "Multilibs with conflicting flags are not the same";
   ASSERT_FALSE(M2 == M1)
   << "Multilibs with conflicting flags are not the same (commuted)";
@@ -48,7 +48,7 @@
 
 TEST(MultilibTest, OpEqInequivalence2) {
   Multilib M1;
-  Multilib M2({}, {}, {}, 0, {"+foo"});
+  Multilib M2({}, {}, {}, {"+foo"});
   ASSERT_FALSE(M1 == M2) << "Flags make Multilibs different";
 }
 
@@ -124,7 +124,7 @@
 }
 
 TEST(MultilibTest, Construction3) {
-  Multilib M({}, {}, {}, 0, {"+f1", "+f2", "-f3"});
+  Multilib M({}, {}, {}, {"+f1", "+f2", "-f3"});
   for (Multilib::flags_list::const_iterator I = M.flags().begin(),
 E = M.flags().end();
I != E; ++I) {
@@ -149,8 +149,8 @@
 
 TEST(MultilibTest, SetPriority) {
   MultilibSet MS({
-  Multilib("/foo", {}, {}, 1, {"+foo"}),
-  Multilib("/bar", {}, {}, 2, {"+bar"}),
+  Multilib("/foo", {}, {}, {"+foo"}),
+  Multilib("/bar", {}, {}, {"+bar"}),
   });
   Multilib::flags_list Flags1 = {"+foo", "-bar"};
   Multilib Selection1;
@@ -166,3 +166,24 @@
   ASSERT_TRUE(Selection2.gccSuffix() == "/bar")
   << "Selection picked " << Selection2 << " which was not expected";
 }
+
+TEST(MultilibTest, SelectMultiple) {
+  MultilibSet MS({
+  Multilib("/a", {}, {}, {"x"}),
+  Multilib("/b", {}, {}, {"y"}),
+  });
+  std::vector Selection;
+
+  Selection = MS.select({"x"});
+  ASSERT_EQ(1u, Selection.size());
+  EXPECT_EQ("/a", Selection[0].gccSuffix());
+
+  Selection = MS.select({"y"});
+  ASSERT_EQ(1u, Selection.size());
+  EXPECT_EQ("/b", Selection[0].gccSuffix());
+
+  Selection = MS.select({"y", "x"});
+  ASSERT_EQ(2u, Selection.size());
+  EXPECT_EQ("/a", Selection[0].gccSuffix());
+  EXPECT_EQ("/b", Selection[1].gccSuffix());
+}
Index: clang/unittests/Driver/MultilibBuilderTest.cpp
===
--- clang/unittests/Driver/MultilibBuilderTest.cpp
+++ clang/unittests/Driver/MultilibBuilderTest.cpp
@@ -207,3 +207,14 @@
 << "Selection picked " << Selection << " which was not expected ";
   }
 }
+
+TEST(MultilibBuilderTest, PrintOptions) {
+  Multilib M = MultilibBuilder()
+   .flag("+x")
+   .flag("-y")
+   .flag("+a")
+   .flag("-b")
+   .flag("+c")
+   .makeMultilib();
+  ASSERT_EQ(Multilib::flags_list({"-x", "-a", "-c"}), M.getPrintOptions());
+}
Index: clang/lib/Driver/ToolChains/Fuchsia.cpp
===
--- clang/lib/Driver/ToolChains/Fuchsia.cpp
+++ clang/lib/Driver/ToolChains/Fuchsia.cpp
@@ -263,33 +263,33 @@
 
   Multilibs.push_back(Multilib());
   // Use the noexcept variant with -fno-exceptions to avoid the extra overhead.
-  Multilibs.push_back(MultilibBuilder("noexcept", {}, {}, 1)
+  Multilibs.push_back(MultilibBuilder("noexcept", {}, {})
   .flag("-fexceptions")
   .flag("+fno-exceptions")
   .makeMultilib());
   // ASan has higher priority because we always want the instrumentated version.
-  Multilibs.push_back(MultilibBuilder("asan", {}, {}, 2)
+  Multilibs.push_back(MultilibBuilder("asan", {}, {})
   .flag("+fsanitize=address")
   .makeMultilib());
   // Use the asan+noexcept variant with ASan and -fno-exceptions.
-  Multilibs.push_back(MultilibBuilder("asan+noexcept", {}, {}, 3)
+  Multilibs.push_back(MultilibBuilder("asan+noexcept", {}, {})
   .flag("+fsanitize=address")
   .flag("-fexceptions")
   .flag("+fno-exceptions")

[PATCH] D142905: [Driver] Change multilib selection algorithm

2023-03-21 Thread Michael Platings via Phabricator via cfe-commits
michaelplatings added a comment.

@phosek ping.


Repository:
  rG LLVM Github Monorepo

CHANGES SINCE LAST ACTION
  https://reviews.llvm.org/D142905/new/

https://reviews.llvm.org/D142905

___
cfe-commits mailing list
cfe-commits@lists.llvm.org
https://lists.llvm.org/cgi-bin/mailman/listinfo/cfe-commits


[PATCH] D142905: [Driver] Change multilib selection algorithm

2023-03-22 Thread Michael Platings via Phabricator via cfe-commits
michaelplatings updated this revision to Diff 507527.
michaelplatings marked an inline comment as done.
michaelplatings added a comment.

Add enum to Multilib class for how print options should be calculated.


Repository:
  rG LLVM Github Monorepo

CHANGES SINCE LAST ACTION
  https://reviews.llvm.org/D142905/new/

https://reviews.llvm.org/D142905

Files:
  clang/include/clang/Driver/Multilib.h
  clang/include/clang/Driver/MultilibBuilder.h
  clang/lib/Driver/Multilib.cpp
  clang/lib/Driver/MultilibBuilder.cpp
  clang/lib/Driver/ToolChains/Fuchsia.cpp
  clang/lib/Driver/ToolChains/OHOS.cpp
  clang/unittests/Driver/MultilibBuilderTest.cpp
  clang/unittests/Driver/MultilibTest.cpp

Index: clang/unittests/Driver/MultilibTest.cpp
===
--- clang/unittests/Driver/MultilibTest.cpp
+++ clang/unittests/Driver/MultilibTest.cpp
@@ -33,14 +33,14 @@
 }
 
 TEST(MultilibTest, OpEqReflexivity3) {
-  Multilib M1({}, {}, {}, 0, {"+foo"});
-  Multilib M2({}, {}, {}, 0, {"+foo"});
+  Multilib M1({}, {}, {}, {"+foo"});
+  Multilib M2({}, {}, {}, {"+foo"});
   ASSERT_TRUE(M1 == M2) << "Multilibs with the same flag should be the same";
 }
 
 TEST(MultilibTest, OpEqInequivalence1) {
-  Multilib M1({}, {}, {}, 0, {"+foo"});
-  Multilib M2({}, {}, {}, 0, {"-foo"});
+  Multilib M1({}, {}, {}, {"+foo"});
+  Multilib M2({}, {}, {}, {"-foo"});
   ASSERT_FALSE(M1 == M2) << "Multilibs with conflicting flags are not the same";
   ASSERT_FALSE(M2 == M1)
   << "Multilibs with conflicting flags are not the same (commuted)";
@@ -48,7 +48,7 @@
 
 TEST(MultilibTest, OpEqInequivalence2) {
   Multilib M1;
-  Multilib M2({}, {}, {}, 0, {"+foo"});
+  Multilib M2({}, {}, {}, {"+foo"});
   ASSERT_FALSE(M1 == M2) << "Flags make Multilibs different";
 }
 
@@ -124,7 +124,7 @@
 }
 
 TEST(MultilibTest, Construction3) {
-  Multilib M({}, {}, {}, 0, {"+f1", "+f2", "-f3"});
+  Multilib M({}, {}, {}, {"+f1", "+f2", "-f3"});
   for (Multilib::flags_list::const_iterator I = M.flags().begin(),
 E = M.flags().end();
I != E; ++I) {
@@ -149,8 +149,8 @@
 
 TEST(MultilibTest, SetPriority) {
   MultilibSet MS({
-  Multilib("/foo", {}, {}, 1, {"+foo"}),
-  Multilib("/bar", {}, {}, 2, {"+bar"}),
+  Multilib("/foo", {}, {}, {"+foo"}),
+  Multilib("/bar", {}, {}, {"+bar"}),
   });
   Multilib::flags_list Flags1 = {"+foo", "-bar"};
   Multilib Selection1;
@@ -166,3 +166,24 @@
   ASSERT_TRUE(Selection2.gccSuffix() == "/bar")
   << "Selection picked " << Selection2 << " which was not expected";
 }
+
+TEST(MultilibTest, SelectMultiple) {
+  MultilibSet MS({
+  Multilib("/a", {}, {}, {"x"}),
+  Multilib("/b", {}, {}, {"y"}),
+  });
+  std::vector Selection;
+
+  Selection = MS.select({"x"});
+  ASSERT_EQ(1u, Selection.size());
+  EXPECT_EQ("/a", Selection[0].gccSuffix());
+
+  Selection = MS.select({"y"});
+  ASSERT_EQ(1u, Selection.size());
+  EXPECT_EQ("/b", Selection[0].gccSuffix());
+
+  Selection = MS.select({"y", "x"});
+  ASSERT_EQ(2u, Selection.size());
+  EXPECT_EQ("/a", Selection[0].gccSuffix());
+  EXPECT_EQ("/b", Selection[1].gccSuffix());
+}
Index: clang/unittests/Driver/MultilibBuilderTest.cpp
===
--- clang/unittests/Driver/MultilibBuilderTest.cpp
+++ clang/unittests/Driver/MultilibBuilderTest.cpp
@@ -207,3 +207,14 @@
 << "Selection picked " << Selection << " which was not expected ";
   }
 }
+
+TEST(MultilibBuilderTest, PrintOptions) {
+  Multilib M = MultilibBuilder()
+   .flag("+x")
+   .flag("-y")
+   .flag("+a")
+   .flag("-b")
+   .flag("+c")
+   .makeMultilib();
+  ASSERT_EQ(Multilib::flags_list({"-x", "-a", "-c"}), M.getPrintOptions());
+}
Index: clang/lib/Driver/ToolChains/OHOS.cpp
===
--- clang/lib/Driver/ToolChains/OHOS.cpp
+++ clang/lib/Driver/ToolChains/OHOS.cpp
@@ -39,13 +39,13 @@
   // -mcpu=cortex-a7
   // -mfloat-abi=soft -mfloat-abi=softfp -mfloat-abi=hard
   // -mfpu=neon-vfpv4
-  Multilibs.push_back(Multilib("/a7_soft", {}, {}, 1,
+  Multilibs.push_back(Multilib("/a7_soft", {}, {},
   {"+mcpu=cortex-a7", "+mfloat-abi=soft"}));
 
-  Multilibs.push_back(Multilib("/a7_softfp_neon-vfpv4", {}, {}, 1,
+  Multilibs.push_back(Multilib("/a7_softfp_neon-vfpv4", {}, {},
   {"+mcpu=cortex-a7", "+mfloat-abi=softfp", "+mfpu=neon-vfpv4"}));
 
-  Multilibs.push_back(Multilib("/a7_hard_neon-vfpv4", {}, {}, 1,
+  Multilibs.push_back(Multilib("/a7_hard_neon-vfpv4", {}, {},
   {"+mcpu=cortex-a7", "+mfloat-abi=hard", "+mfpu=neon-vfpv4"}));
 
   if (Multilibs.select(Flags, Result.SelectedMultilib)) {
Index: clang/lib/Driver/ToolChains/Fuchsia.cpp
===
--- clang

[PATCH] D146757: [Driver] Enable defining multilib print options independently of flags

2023-03-23 Thread Michael Platings via Phabricator via cfe-commits
michaelplatings created this revision.
michaelplatings added a reviewer: phosek.
Herald added a project: All.
michaelplatings requested review of this revision.
Herald added subscribers: cfe-commits, MaskRay.
Herald added a project: clang.

Sometimes it's necessary to define a multilib in terms of attributes
that don't correspond directly to a valid command line option.
However to support -print-multi-lib we still need to specify a
representative set of command line options for the multilib.
Decoupling flags from print options enables this.

The default of deriving print options from flags beginning '+' remains.


Repository:
  rG LLVM Github Monorepo

https://reviews.llvm.org/D146757

Files:
  clang/include/clang/Driver/Multilib.h
  clang/lib/Driver/Multilib.cpp
  clang/unittests/Driver/MultilibBuilderTest.cpp
  clang/unittests/Driver/MultilibTest.cpp

Index: clang/unittests/Driver/MultilibTest.cpp
===
--- clang/unittests/Driver/MultilibTest.cpp
+++ clang/unittests/Driver/MultilibTest.cpp
@@ -187,3 +187,19 @@
   EXPECT_EQ("/a", Selection[0].gccSuffix());
   EXPECT_EQ("/b", Selection[1].gccSuffix());
 }
+
+TEST(MultilibBuilder, PrintOptions) {
+  ASSERT_EQ(Multilib::flags_list(), Multilib().getPrintOptions());
+  ASSERT_EQ(Multilib::flags_list({"-x"}),
+Multilib({}, {}, {}, {"+x"}).getPrintOptions());
+  ASSERT_EQ(Multilib::flags_list({"-x"}),
+Multilib({}, {}, {}, {"+x"}, Multilib::PrintOptionsType::PlusFlags)
+.getPrintOptions());
+  ASSERT_EQ(
+  Multilib::flags_list({"-x", "-a", "-c"}),
+  Multilib({}, {}, {}, {"+x", "-y", "+a", "-b", "+c"}).getPrintOptions());
+  ASSERT_EQ(
+  Multilib::flags_list({"-y"}),
+  Multilib({}, {}, {}, {"+x"}, Multilib::PrintOptionsType::List, {"-y"})
+  .getPrintOptions());
+}
Index: clang/unittests/Driver/MultilibBuilderTest.cpp
===
--- clang/unittests/Driver/MultilibBuilderTest.cpp
+++ clang/unittests/Driver/MultilibBuilderTest.cpp
@@ -207,3 +207,14 @@
 << "Selection picked " << Selection << " which was not expected ";
   }
 }
+
+TEST(MultilibBuilderTest, PrintOptions) {
+  Multilib M = MultilibBuilder()
+   .flag("+x")
+   .flag("-y")
+   .flag("+a")
+   .flag("-b")
+   .flag("+c")
+   .makeMultilib();
+  ASSERT_EQ(Multilib::flags_list({"-x", "-a", "-c"}), M.getPrintOptions());
+}
Index: clang/lib/Driver/Multilib.cpp
===
--- clang/lib/Driver/Multilib.cpp
+++ clang/lib/Driver/Multilib.cpp
@@ -26,15 +26,43 @@
 using namespace llvm::sys;
 
 Multilib::Multilib(StringRef GCCSuffix, StringRef OSSuffix,
-   StringRef IncludeSuffix, const flags_list &Flags)
+   StringRef IncludeSuffix, const flags_list &Flags,
+   PrintOptionsType PrintOptions,
+   const flags_list &PrintOptionsList)
 : GCCSuffix(GCCSuffix), OSSuffix(OSSuffix), IncludeSuffix(IncludeSuffix),
-  Flags(Flags) {
+  Flags(Flags), PrintOptionsList(PrintOptionsList),
+  PrintOptions(PrintOptions) {
   assert(GCCSuffix.empty() ||
  (StringRef(GCCSuffix).front() == '/' && GCCSuffix.size() > 1));
   assert(OSSuffix.empty() ||
  (StringRef(OSSuffix).front() == '/' && OSSuffix.size() > 1));
   assert(IncludeSuffix.empty() ||
  (StringRef(IncludeSuffix).front() == '/' && IncludeSuffix.size() > 1));
+  // If PrintOptions is something other than List then PrintOptionsList must be
+  // empty.
+  assert(PrintOptions == PrintOptionsType::List || PrintOptionsList.empty());
+}
+
+static Multilib::flags_list
+getPrintOptionsFromPlusFlags(const Multilib::flags_list &Flags) {
+  // Derive print options from flags beginning '+', replacing the first
+  // character with '-'.
+  Multilib::flags_list PrintOptions;
+  for (StringRef Flag : Flags) {
+if (Flag.front() == '+')
+  PrintOptions.push_back(("-" + Flag.substr(1)).str());
+  }
+  return PrintOptions;
+}
+
+Multilib::flags_list Multilib::getPrintOptions() const {
+  switch (PrintOptions) {
+  case PrintOptionsType::List:
+return PrintOptionsList;
+  case PrintOptionsType::PlusFlags:
+return getPrintOptionsFromPlusFlags(Flags);
+  }
+  llvm_unreachable("Unknown Multilib::PrintOptionsType");
 }
 
 LLVM_DUMP_METHOD void Multilib::dump() const {
@@ -44,14 +72,11 @@
 void Multilib::print(raw_ostream &OS) const {
   if (GCCSuffix.empty())
 OS << ".";
-  else {
+  else
 OS << StringRef(GCCSuffix).drop_front();
-  }
   OS << ";";
-  for (StringRef Flag : Flags) {
-if (Flag.front() == '+')
-  OS << "@" << Flag.substr(1);
-  }
+  for (StringRef Option : getPrintOptions())
+OS << "@" << Option.substr(1);
 }
 
 bool Multilib::operator==(const Multilib &Other) const {
Index: clang/include/clang/Driver/M

[PATCH] D142905: [Driver] Change multilib selection algorithm

2023-03-23 Thread Michael Platings via Phabricator via cfe-commits
michaelplatings updated this revision to Diff 507864.
michaelplatings added a comment.

Move change to print options into D146757 


Repository:
  rG LLVM Github Monorepo

CHANGES SINCE LAST ACTION
  https://reviews.llvm.org/D142905/new/

https://reviews.llvm.org/D142905

Files:
  clang/include/clang/Driver/Multilib.h
  clang/include/clang/Driver/MultilibBuilder.h
  clang/lib/Driver/Multilib.cpp
  clang/lib/Driver/MultilibBuilder.cpp
  clang/lib/Driver/ToolChains/Fuchsia.cpp
  clang/lib/Driver/ToolChains/OHOS.cpp
  clang/unittests/Driver/MultilibTest.cpp

Index: clang/unittests/Driver/MultilibTest.cpp
===
--- clang/unittests/Driver/MultilibTest.cpp
+++ clang/unittests/Driver/MultilibTest.cpp
@@ -33,14 +33,14 @@
 }
 
 TEST(MultilibTest, OpEqReflexivity3) {
-  Multilib M1({}, {}, {}, 0, {"+foo"});
-  Multilib M2({}, {}, {}, 0, {"+foo"});
+  Multilib M1({}, {}, {}, {"+foo"});
+  Multilib M2({}, {}, {}, {"+foo"});
   ASSERT_TRUE(M1 == M2) << "Multilibs with the same flag should be the same";
 }
 
 TEST(MultilibTest, OpEqInequivalence1) {
-  Multilib M1({}, {}, {}, 0, {"+foo"});
-  Multilib M2({}, {}, {}, 0, {"-foo"});
+  Multilib M1({}, {}, {}, {"+foo"});
+  Multilib M2({}, {}, {}, {"-foo"});
   ASSERT_FALSE(M1 == M2) << "Multilibs with conflicting flags are not the same";
   ASSERT_FALSE(M2 == M1)
   << "Multilibs with conflicting flags are not the same (commuted)";
@@ -48,7 +48,7 @@
 
 TEST(MultilibTest, OpEqInequivalence2) {
   Multilib M1;
-  Multilib M2({}, {}, {}, 0, {"+foo"});
+  Multilib M2({}, {}, {}, {"+foo"});
   ASSERT_FALSE(M1 == M2) << "Flags make Multilibs different";
 }
 
@@ -124,7 +124,7 @@
 }
 
 TEST(MultilibTest, Construction3) {
-  Multilib M({}, {}, {}, 0, {"+f1", "+f2", "-f3"});
+  Multilib M({}, {}, {}, {"+f1", "+f2", "-f3"});
   for (Multilib::flags_list::const_iterator I = M.flags().begin(),
 E = M.flags().end();
I != E; ++I) {
@@ -149,8 +149,8 @@
 
 TEST(MultilibTest, SetPriority) {
   MultilibSet MS({
-  Multilib("/foo", {}, {}, 1, {"+foo"}),
-  Multilib("/bar", {}, {}, 2, {"+bar"}),
+  Multilib("/foo", {}, {}, {"+foo"}),
+  Multilib("/bar", {}, {}, {"+bar"}),
   });
   Multilib::flags_list Flags1 = {"+foo", "-bar"};
   Multilib Selection1;
@@ -166,3 +166,24 @@
   ASSERT_TRUE(Selection2.gccSuffix() == "/bar")
   << "Selection picked " << Selection2 << " which was not expected";
 }
+
+TEST(MultilibTest, SelectMultiple) {
+  MultilibSet MS({
+  Multilib("/a", {}, {}, {"x"}),
+  Multilib("/b", {}, {}, {"y"}),
+  });
+  std::vector Selection;
+
+  Selection = MS.select({"x"});
+  ASSERT_EQ(1u, Selection.size());
+  EXPECT_EQ("/a", Selection[0].gccSuffix());
+
+  Selection = MS.select({"y"});
+  ASSERT_EQ(1u, Selection.size());
+  EXPECT_EQ("/b", Selection[0].gccSuffix());
+
+  Selection = MS.select({"y", "x"});
+  ASSERT_EQ(2u, Selection.size());
+  EXPECT_EQ("/a", Selection[0].gccSuffix());
+  EXPECT_EQ("/b", Selection[1].gccSuffix());
+}
Index: clang/lib/Driver/ToolChains/OHOS.cpp
===
--- clang/lib/Driver/ToolChains/OHOS.cpp
+++ clang/lib/Driver/ToolChains/OHOS.cpp
@@ -39,14 +39,16 @@
   // -mcpu=cortex-a7
   // -mfloat-abi=soft -mfloat-abi=softfp -mfloat-abi=hard
   // -mfpu=neon-vfpv4
-  Multilibs.push_back(Multilib("/a7_soft", {}, {}, 1,
-  {"+mcpu=cortex-a7", "+mfloat-abi=soft"}));
+  Multilibs.push_back(
+  Multilib("/a7_soft", {}, {}, {"+mcpu=cortex-a7", "+mfloat-abi=soft"}));
 
-  Multilibs.push_back(Multilib("/a7_softfp_neon-vfpv4", {}, {}, 1,
-  {"+mcpu=cortex-a7", "+mfloat-abi=softfp", "+mfpu=neon-vfpv4"}));
+  Multilibs.push_back(
+  Multilib("/a7_softfp_neon-vfpv4", {}, {},
+   {"+mcpu=cortex-a7", "+mfloat-abi=softfp", "+mfpu=neon-vfpv4"}));
 
-  Multilibs.push_back(Multilib("/a7_hard_neon-vfpv4", {}, {}, 1,
-  {"+mcpu=cortex-a7", "+mfloat-abi=hard", "+mfpu=neon-vfpv4"}));
+  Multilibs.push_back(
+  Multilib("/a7_hard_neon-vfpv4", {}, {},
+   {"+mcpu=cortex-a7", "+mfloat-abi=hard", "+mfpu=neon-vfpv4"}));
 
   if (Multilibs.select(Flags, Result.SelectedMultilib)) {
 Result.Multilibs = Multilibs;
Index: clang/lib/Driver/ToolChains/Fuchsia.cpp
===
--- clang/lib/Driver/ToolChains/Fuchsia.cpp
+++ clang/lib/Driver/ToolChains/Fuchsia.cpp
@@ -263,33 +263,33 @@
 
   Multilibs.push_back(Multilib());
   // Use the noexcept variant with -fno-exceptions to avoid the extra overhead.
-  Multilibs.push_back(MultilibBuilder("noexcept", {}, {}, 1)
+  Multilibs.push_back(MultilibBuilder("noexcept", {}, {})
   .flag("-fexceptions")
   .flag("+fno-exceptions")
   .makeMultilib());
   // ASan has higher priorit

[PATCH] D142905: [Driver] Change multilib selection algorithm

2023-03-23 Thread Michael Platings via Phabricator via cfe-commits
This revision was landed with ongoing or failed builds.
This revision was automatically updated to reflect the committed changes.
Closed by commit rGd30bc9e91241: [Driver] Change multilib selection algorithm 
(authored by michaelplatings).

Repository:
  rG LLVM Github Monorepo

CHANGES SINCE LAST ACTION
  https://reviews.llvm.org/D142905/new/

https://reviews.llvm.org/D142905

Files:
  clang/include/clang/Driver/Multilib.h
  clang/include/clang/Driver/MultilibBuilder.h
  clang/lib/Driver/Multilib.cpp
  clang/lib/Driver/MultilibBuilder.cpp
  clang/lib/Driver/ToolChains/Fuchsia.cpp
  clang/lib/Driver/ToolChains/OHOS.cpp
  clang/unittests/Driver/MultilibTest.cpp

Index: clang/unittests/Driver/MultilibTest.cpp
===
--- clang/unittests/Driver/MultilibTest.cpp
+++ clang/unittests/Driver/MultilibTest.cpp
@@ -33,14 +33,14 @@
 }
 
 TEST(MultilibTest, OpEqReflexivity3) {
-  Multilib M1({}, {}, {}, 0, {"+foo"});
-  Multilib M2({}, {}, {}, 0, {"+foo"});
+  Multilib M1({}, {}, {}, {"+foo"});
+  Multilib M2({}, {}, {}, {"+foo"});
   ASSERT_TRUE(M1 == M2) << "Multilibs with the same flag should be the same";
 }
 
 TEST(MultilibTest, OpEqInequivalence1) {
-  Multilib M1({}, {}, {}, 0, {"+foo"});
-  Multilib M2({}, {}, {}, 0, {"-foo"});
+  Multilib M1({}, {}, {}, {"+foo"});
+  Multilib M2({}, {}, {}, {"-foo"});
   ASSERT_FALSE(M1 == M2) << "Multilibs with conflicting flags are not the same";
   ASSERT_FALSE(M2 == M1)
   << "Multilibs with conflicting flags are not the same (commuted)";
@@ -48,7 +48,7 @@
 
 TEST(MultilibTest, OpEqInequivalence2) {
   Multilib M1;
-  Multilib M2({}, {}, {}, 0, {"+foo"});
+  Multilib M2({}, {}, {}, {"+foo"});
   ASSERT_FALSE(M1 == M2) << "Flags make Multilibs different";
 }
 
@@ -124,7 +124,7 @@
 }
 
 TEST(MultilibTest, Construction3) {
-  Multilib M({}, {}, {}, 0, {"+f1", "+f2", "-f3"});
+  Multilib M({}, {}, {}, {"+f1", "+f2", "-f3"});
   for (Multilib::flags_list::const_iterator I = M.flags().begin(),
 E = M.flags().end();
I != E; ++I) {
@@ -149,8 +149,8 @@
 
 TEST(MultilibTest, SetPriority) {
   MultilibSet MS({
-  Multilib("/foo", {}, {}, 1, {"+foo"}),
-  Multilib("/bar", {}, {}, 2, {"+bar"}),
+  Multilib("/foo", {}, {}, {"+foo"}),
+  Multilib("/bar", {}, {}, {"+bar"}),
   });
   Multilib::flags_list Flags1 = {"+foo", "-bar"};
   Multilib Selection1;
@@ -166,3 +166,24 @@
   ASSERT_TRUE(Selection2.gccSuffix() == "/bar")
   << "Selection picked " << Selection2 << " which was not expected";
 }
+
+TEST(MultilibTest, SelectMultiple) {
+  MultilibSet MS({
+  Multilib("/a", {}, {}, {"x"}),
+  Multilib("/b", {}, {}, {"y"}),
+  });
+  std::vector Selection;
+
+  Selection = MS.select({"x"});
+  ASSERT_EQ(1u, Selection.size());
+  EXPECT_EQ("/a", Selection[0].gccSuffix());
+
+  Selection = MS.select({"y"});
+  ASSERT_EQ(1u, Selection.size());
+  EXPECT_EQ("/b", Selection[0].gccSuffix());
+
+  Selection = MS.select({"y", "x"});
+  ASSERT_EQ(2u, Selection.size());
+  EXPECT_EQ("/a", Selection[0].gccSuffix());
+  EXPECT_EQ("/b", Selection[1].gccSuffix());
+}
Index: clang/lib/Driver/ToolChains/OHOS.cpp
===
--- clang/lib/Driver/ToolChains/OHOS.cpp
+++ clang/lib/Driver/ToolChains/OHOS.cpp
@@ -39,14 +39,16 @@
   // -mcpu=cortex-a7
   // -mfloat-abi=soft -mfloat-abi=softfp -mfloat-abi=hard
   // -mfpu=neon-vfpv4
-  Multilibs.push_back(Multilib("/a7_soft", {}, {}, 1,
-  {"+mcpu=cortex-a7", "+mfloat-abi=soft"}));
+  Multilibs.push_back(
+  Multilib("/a7_soft", {}, {}, {"+mcpu=cortex-a7", "+mfloat-abi=soft"}));
 
-  Multilibs.push_back(Multilib("/a7_softfp_neon-vfpv4", {}, {}, 1,
-  {"+mcpu=cortex-a7", "+mfloat-abi=softfp", "+mfpu=neon-vfpv4"}));
+  Multilibs.push_back(
+  Multilib("/a7_softfp_neon-vfpv4", {}, {},
+   {"+mcpu=cortex-a7", "+mfloat-abi=softfp", "+mfpu=neon-vfpv4"}));
 
-  Multilibs.push_back(Multilib("/a7_hard_neon-vfpv4", {}, {}, 1,
-  {"+mcpu=cortex-a7", "+mfloat-abi=hard", "+mfpu=neon-vfpv4"}));
+  Multilibs.push_back(
+  Multilib("/a7_hard_neon-vfpv4", {}, {},
+   {"+mcpu=cortex-a7", "+mfloat-abi=hard", "+mfpu=neon-vfpv4"}));
 
   if (Multilibs.select(Flags, Result.SelectedMultilib)) {
 Result.Multilibs = Multilibs;
Index: clang/lib/Driver/ToolChains/Fuchsia.cpp
===
--- clang/lib/Driver/ToolChains/Fuchsia.cpp
+++ clang/lib/Driver/ToolChains/Fuchsia.cpp
@@ -263,33 +263,33 @@
 
   Multilibs.push_back(Multilib());
   // Use the noexcept variant with -fno-exceptions to avoid the extra overhead.
-  Multilibs.push_back(MultilibBuilder("noexcept", {}, {}, 1)
+  Multilibs.push_back(MultilibBuilder("noexcept", {}, {})
   .flag("-fexceptions")
   .flag("+fno-exceptions")

[PATCH] D142932: Multilib YAML parsing

2023-03-24 Thread Michael Platings via Phabricator via cfe-commits
michaelplatings updated this revision to Diff 508036.
michaelplatings added a comment.

Rebase


Repository:
  rG LLVM Github Monorepo

CHANGES SINCE LAST ACTION
  https://reviews.llvm.org/D142932/new/

https://reviews.llvm.org/D142932

Files:
  clang/include/clang/Driver/Multilib.h
  clang/lib/Driver/Multilib.cpp
  clang/unittests/Driver/MultilibTest.cpp

Index: clang/unittests/Driver/MultilibTest.cpp
===
--- clang/unittests/Driver/MultilibTest.cpp
+++ clang/unittests/Driver/MultilibTest.cpp
@@ -13,6 +13,7 @@
 #include "clang/Driver/Multilib.h"
 #include "../../lib/Driver/ToolChains/CommonArgs.h"
 #include "clang/Basic/LLVM.h"
+#include "clang/Basic/Version.h"
 #include "llvm/ADT/ArrayRef.h"
 #include "llvm/ADT/StringRef.h"
 #include "llvm/ADT/StringSwitch.h"
@@ -203,3 +204,392 @@
   Multilib({}, {}, {}, {"+x"}, Multilib::PrintOptionsType::List, {"-y"})
   .getPrintOptions());
 }
+
+static void diagnosticCallback(const llvm::SMDiagnostic &D, void *Out) {
+  *reinterpret_cast(Out) = D.getMessage();
+}
+
+static bool parseYaml(MultilibSet &MS, std::string &Diagnostic,
+  const char *Data) {
+  return MS.parseYaml(llvm::MemoryBufferRef(Data, "TEST"), diagnosticCallback,
+  &Diagnostic);
+}
+
+static bool parseYaml(MultilibSet &MS, const char *Data) {
+  return MS.parseYaml(llvm::MemoryBufferRef(Data, "TEST"));
+}
+
+// When updating this version also update MultilibVersionCurrent in Multilib.cpp
+#define YAML_PREAMBLE "MultilibVersion: 1.0\n"
+
+TEST(MultilibTest, ParseInvalid) {
+  std::string Diagnostic;
+
+  MultilibSet MS;
+
+  EXPECT_FALSE(parseYaml(MS, Diagnostic, R"(
+Variants: []
+)"));
+  EXPECT_TRUE(
+  StringRef(Diagnostic).contains("missing required key 'MultilibVersion'"))
+  << Diagnostic;
+
+  // Reject files with a different major version
+  EXPECT_FALSE(parseYaml(MS, Diagnostic,
+ R"(
+MultilibVersion: 2.0
+Variants: []
+)"));
+  EXPECT_TRUE(
+  StringRef(Diagnostic).contains("Multilib version 2.0 is unsupported"))
+  << Diagnostic;
+  EXPECT_FALSE(parseYaml(MS, Diagnostic,
+ R"(
+MultilibVersion: 0.1
+Variants: []
+)"));
+  EXPECT_TRUE(
+  StringRef(Diagnostic).contains("Multilib version 0.1 is unsupported"))
+  << Diagnostic;
+
+  // Reject files with a later minor version
+  EXPECT_FALSE(parseYaml(MS, Diagnostic,
+ R"(
+MultilibVersion: 1.9
+Variants: []
+)"));
+  EXPECT_TRUE(
+  StringRef(Diagnostic).contains("Multilib version 1.9 is unsupported"))
+  << Diagnostic;
+
+  // Accept files with the same major version and the same or earlier minor
+  // version
+  EXPECT_TRUE(parseYaml(MS, Diagnostic, R"(
+MultilibVersion: 1.0
+Variants: []
+)")) << Diagnostic;
+
+  EXPECT_FALSE(parseYaml(MS, Diagnostic, YAML_PREAMBLE));
+  EXPECT_TRUE(StringRef(Diagnostic).contains("missing required key 'Variants'"))
+  << Diagnostic;
+
+  EXPECT_FALSE(parseYaml(MS, Diagnostic, YAML_PREAMBLE R"(
+Variants:
+- Dir: /abc
+  Flags: []
+  PrintOptions: []
+)"));
+  EXPECT_TRUE(StringRef(Diagnostic).contains("paths must be relative"))
+  << Diagnostic;
+
+  EXPECT_FALSE(parseYaml(MS, Diagnostic, YAML_PREAMBLE R"(
+Variants:
+- Flags: []
+  PrintOptions: []
+)"));
+  EXPECT_TRUE(StringRef(Diagnostic).contains("missing required key 'Dir'"))
+  << Diagnostic;
+
+  EXPECT_FALSE(parseYaml(MS, Diagnostic, YAML_PREAMBLE R"(
+Variants:
+- Dir: .
+  PrintOptions: []
+)"));
+  EXPECT_TRUE(StringRef(Diagnostic).contains("missing required key 'Flags'"))
+  << Diagnostic;
+
+  EXPECT_FALSE(parseYaml(MS, Diagnostic, YAML_PREAMBLE R"(
+Variants:
+- Dir: .
+  Flags: []
+)"));
+  EXPECT_TRUE(
+  StringRef(Diagnostic).contains("missing required key 'PrintOptions'"))
+  << Diagnostic;
+
+  EXPECT_FALSE(parseYaml(MS, Diagnostic, YAML_PREAMBLE R"(
+Variants: []
+FlagMap:
+- Regex: abc
+)"));
+  EXPECT_TRUE(
+  StringRef(Diagnostic)
+  .contains("value required for 'MatchFlags' or 'NoMatchFlags'"))
+  << Diagnostic;
+
+  EXPECT_FALSE(parseYaml(MS, Diagnostic, YAML_PREAMBLE R"(
+Variants: []
+FlagMap:
+- Dir: .
+  Regex: '('
+  PrintOptions: []
+)"));
+  EXPECT_TRUE(StringRef(Diagnostic).contains("parentheses not balanced"))
+  << Diagnostic;
+}
+
+TEST(MultilibTest, Parse) {
+  MultilibSet MS;
+  EXPECT_TRUE(parseYaml(MS, YAML_PREAMBLE R"(
+Variants:
+- Dir: .
+  Flags: []
+  PrintOptions: []
+)"));
+  EXPECT_EQ(1U, MS.size());
+  EXPECT_EQ("", MS.begin()->gccSuffix());
+
+  EXPECT_TRUE(parseYaml(MS, YAML_PREAMBLE R"(
+Variants:
+- Dir: abc
+  Flags: []
+  PrintOptions: []
+)"));
+  EXPECT_EQ(1U, MS.size());
+  EXPECT_EQ("/abc", MS.begin()->gccSuffix());
+
+  EXPECT_TRUE(parseYaml(MS, YAML_PREAMBLE R"(
+Variants:
+- Dir: pqr
+  Flags: []
+  PrintOptions: [-mfloat-abi=soft]
+)"));
+  EXPECT_EQ(1U, MS.size());
+  EXPECT_EQ("/pqr", MS.begin()->gccSuffix());
+  EXPECT_EQ(std::ve

[PATCH] D142933: Add -print-multi-selection-flags-experimental option

2023-03-24 Thread Michael Platings via Phabricator via cfe-commits
michaelplatings updated this revision to Diff 508037.
michaelplatings added a comment.

Rebase


Repository:
  rG LLVM Github Monorepo

CHANGES SINCE LAST ACTION
  https://reviews.llvm.org/D142933/new/

https://reviews.llvm.org/D142933

Files:
  clang/include/clang/Driver/Options.td
  clang/include/clang/Driver/ToolChain.h
  clang/lib/Driver/Driver.cpp
  clang/lib/Driver/ToolChain.cpp
  clang/lib/Driver/ToolChains/Arch/ARM.cpp
  clang/lib/Driver/ToolChains/Arch/ARM.h
  clang/test/Driver/print-multi-selection-flags.c

Index: clang/test/Driver/print-multi-selection-flags.c
===
--- /dev/null
+++ clang/test/Driver/print-multi-selection-flags.c
@@ -0,0 +1,54 @@
+// RUN: %clang -print-multi-selection-flags-experimental --target=aarch64-linux -fc++-abi=itanium -fsanitize=address | FileCheck --check-prefix=CHECK-LINUX %s
+// CHECK-LINUX: fc++-abi=itanium
+// CHECK-LINUX: fexceptions
+// CHECK-LINUX: frtti
+// CHECK-LINUX: fsanitize=address
+// CHECK-LINUX: target=aarch64-unknown-linux
+
+// RUN: %clang -print-multi-selection-flags-experimental --target=aarch64-fuchsia -fsanitize=hwaddress | FileCheck --check-prefix=CHECK-FUCHSIA %s
+// CHECK-FUCHSIA: fsanitize=hwaddress
+// CHECK-FUCHSIA: target=aarch64-unknown-fuchsia
+
+// RUN: %clang -print-multi-selection-flags-experimental --target=arm-none-eabi -mfloat-abi=soft -fno-exceptions -fno-rtti | FileCheck --check-prefix=CHECK-ARMV4T %s
+// CHECK-ARMV4T: fno-exceptions
+// CHECK-ARMV4T: fno-rtti
+// CHECK-ARMV4T: mfloat-abi=soft
+// CHECK-ARMV4T: mfpu=none
+// CHECK-ARMV4T: target=armv4t-none-unknown-eabi
+
+// RUN: %clang -print-multi-selection-flags-experimental --target=armv7em-none-eabi -mfloat-abi=softfp | FileCheck --check-prefix=CHECK-SOFTFP %s
+// CHECK-SOFTFP: mfloat-abi=softfp
+// CHECK-SOFTFP: mfpu=fpv4-sp-d16
+// CHECK-SOFTFP: target=thumbv7em-none-unknown-eabi
+
+// RUN: %clang -print-multi-selection-flags-experimental --target=arm-none-eabihf -march=armv7em -mfpu=fpv5-d16 | FileCheck --check-prefix=CHECK-HARD %s
+// CHECK-HARD: mfloat-abi=hard
+// CHECK-HARD: mfpu=fpv5-d16
+// CHECK-HARD: target=thumbv7em-none-unknown-eabihf
+
+// RUN: %clang -print-multi-selection-flags-experimental --target=arm-none-eabi -mfloat-abi=soft -march=armv8-m.main+nofp | FileCheck --check-prefix=CHECK-V8MMAIN-NOFP %s
+// CHECK-V8MMAIN-NOFP: mfloat-abi=soft
+// CHECK-V8MMAIN-NOFP: mfpu=none
+// CHECK-V8MMAIN-NOFP: target=thumbv8m.main-none-unknown-eabi
+
+// RUN: %clang -print-multi-selection-flags-experimental --target=arm-none-eabi -mfloat-abi=hard -march=armv8.1m.main+mve.fp | FileCheck --check-prefix=CHECK-MVE %s
+// CHECK-MVE: march=+mve
+// CHECK-MVE: march=+mve.fp
+// CHECK-MVE: mfloat-abi=hard
+// CHECK-MVE: mfpu=fp-armv8-fullfp16-sp-d16
+// CHECK-MVE: target=thumbv8.1m.main-none-unknown-eabihf
+
+// RUN: %clang -print-multi-selection-flags-experimental --target=arm-none-eabi -march=armv8.1m.main+mve+nofp | FileCheck --check-prefix=CHECK-MVENOFP %s
+// CHECK-MVENOFP: march=+mve
+// CHECK-MVENOFP-NOT: march=+mve.fp
+// CHECK-MVENOFP: mfpu=none
+
+// RUN: %clang -print-multi-selection-flags-experimental --target=aarch64-none-elf -march=armv8-a+lse | FileCheck --check-prefix=CHECK-LSE %s
+// CHECK-LSE: march=+lse
+
+// RUN: %clang -print-multi-selection-flags-experimental --target=aarch64-none-elf -march=armv8.5-a+sve+sve2 | FileCheck --check-prefix=CHECK-SVE2 %s
+// RUN: %clang -print-multi-selection-flags-experimental --target=aarch64-none-elf -march=armv9-a| FileCheck --check-prefix=CHECK-SVE2 %s
+// CHECK-SVE2: march=+simd
+// CHECK-SVE2: march=+sve
+// CHECK-SVE2: march=+sve2
+// CHECK-SVE2: target=aarch64-none-unknown-elf
Index: clang/lib/Driver/ToolChains/Arch/ARM.h
===
--- clang/lib/Driver/ToolChains/Arch/ARM.h
+++ clang/lib/Driver/ToolChains/Arch/ARM.h
@@ -63,9 +63,11 @@
 void getARMArchCPUFromArgs(const llvm::opt::ArgList &Args,
llvm::StringRef &Arch, llvm::StringRef &CPU,
bool FromAs = false);
-void getARMTargetFeatures(const Driver &D, const llvm::Triple &Triple,
-  const llvm::opt::ArgList &Args,
-  std::vector &Features, bool ForAS);
+llvm::ARM::FPUKind getARMTargetFeatures(const Driver &D,
+const llvm::Triple &Triple,
+const llvm::opt::ArgList &Args,
+std::vector &Features,
+bool ForAS);
 int getARMSubArchVersionNumber(const llvm::Triple &Triple);
 bool isARMMProfile(const llvm::Triple &Triple);
 bool isARMAProfile(const llvm::Triple &Triple);
Index: clang/lib/Driver/ToolChains/Arch/ARM.cpp
===
--- clang/lib/Driver/ToolChains/Arch/ARM.cpp
+++ clang/lib/Driver/ToolChains/Arch/ARM.cpp
@@ -447,9 +44

[PATCH] D142986: Enable multilib.yaml in the BareMetal ToolChain

2023-03-24 Thread Michael Platings via Phabricator via cfe-commits
michaelplatings updated this revision to Diff 508038.
michaelplatings added a comment.

Rebase


Repository:
  rG LLVM Github Monorepo

CHANGES SINCE LAST ACTION
  https://reviews.llvm.org/D142986/new/

https://reviews.llvm.org/D142986

Files:
  clang/lib/Driver/ToolChain.cpp
  clang/lib/Driver/ToolChains/Arch/ARM.cpp
  clang/lib/Driver/ToolChains/Arch/ARM.h
  clang/lib/Driver/ToolChains/BareMetal.cpp
  clang/test/Driver/baremetal-multilib.yaml
  clang/test/Driver/baremetal.cpp
  clang/test/Driver/lit.local.cfg

Index: clang/test/Driver/lit.local.cfg
===
--- clang/test/Driver/lit.local.cfg
+++ clang/test/Driver/lit.local.cfg
@@ -1,7 +1,7 @@
 from lit.llvm import llvm_config
 
 config.suffixes = ['.c', '.cpp', '.cppm', '.h', '.m', '.mm', '.S', '.s', '.f90', '.F90', '.f95',
-   '.cu', '.rs', '.cl', '.clcpp', '.hip', '.hipi', '.hlsl']
+   '.cu', '.rs', '.cl', '.clcpp', '.hip', '.hipi', '.hlsl', '.yaml']
 config.substitutions = list(config.substitutions)
 config.substitutions.insert(0,
 ('%clang_cc1',
Index: clang/test/Driver/baremetal.cpp
===
--- clang/test/Driver/baremetal.cpp
+++ clang/test/Driver/baremetal.cpp
@@ -118,9 +118,9 @@
 // Verify that the bare metal driver does not include any host system paths:
 // CHECK-AARCH64-NO-HOST-INC: InstalledDir: [[INSTALLEDDIR:.+]]
 // CHECK-AARCH64-NO-HOST-INC: "-resource-dir" "[[RESOURCE:[^"]+]]"
-// CHECK-AARCH64-NO-HOST-INC-SAME: "-internal-isystem" "[[INSTALLEDDIR]]{{[/\\]+}}..{{[/\\]+}}lib{{[/\\]+}}clang-runtimes{{[/\\]+}}aarch64-none-elf{{[/\\]+}}include{{[/\\]+}}c++{{[/\\]+}}v1"
+// CHECK-AARCH64-NO-HOST-INC-SAME: "-internal-isystem" "[[INSTALLEDDIR]]{{[/\\]+}}..{{[/\\]+}}lib{{[/\\]+}}clang-runtimes{{[/\\]+[^"]*}}include{{[/\\]+}}c++{{[/\\]+}}v1"
 // CHECK-AARCH64-NO-HOST-INC-SAME: "-internal-isystem" "[[RESOURCE]]{{[/\\]+}}include"
-// CHECK-AARCH64-NO-HOST-INC-SAME: "-internal-isystem" "[[INSTALLEDDIR]]{{[/\\]+}}..{{[/\\]+}}lib{{[/\\]+}}clang-runtimes{{[/\\]+}}aarch64-none-elf{{[/\\]+}}include"
+// CHECK-AARCH64-NO-HOST-INC-SAME: "-internal-isystem" "[[INSTALLEDDIR]]{{[/\\]+}}..{{[/\\]+}}lib{{[/\\]+}}clang-runtimes{{[/\\]+[^"]*}}include"
 
 // RUN: %clang %s -### --target=riscv64-unknown-elf -o %t.out -L some/directory/user/asked/for \
 // RUN: --sysroot=%S/Inputs/basic_riscv64_tree/riscv64-unknown-elf 2>&1 \
Index: clang/test/Driver/baremetal-multilib.yaml
===
--- /dev/null
+++ clang/test/Driver/baremetal-multilib.yaml
@@ -0,0 +1,142 @@
+# REQUIRES: shell
+# UNSUPPORTED: system-windows
+
+# RUN: rm -rf %T/baremetal_multilib
+# RUN: mkdir -p %T/baremetal_multilib/bin
+# RUN: mkdir -p %T/baremetal_multilib/lib/clang-runtimes/arm-none-eabi/thumb/v8-m.main/fp/lib
+# RUN: touch %T/baremetal_multilib/lib/clang-runtimes/arm-none-eabi/thumb/v8-m.main/fp/lib/libclang_rt.builtins.a
+# RUN: ln -s %clang %T/baremetal_multilib/bin/clang
+# RUN: ln -s %s %T/baremetal_multilib/lib/clang-runtimes/multilib.yaml
+
+# RUN: %T/baremetal_multilib/bin/clang -no-canonical-prefixes -x c++ %s -### -o %t.out 2>&1 \
+# RUN: --target=thumbv8m.main-none-eabihf --sysroot= \
+# RUN:   | FileCheck -DSYSROOT=%T/baremetal_multilib %s
+# CHECK:  "-cc1" "-triple" "thumbv8m.main-none-unknown-eabihf"
+# CHECK-SAME: "-internal-isystem" "[[SYSROOT]]/bin/../lib/clang-runtimes/arm-none-eabi/thumb/v8-m.main/fp/include/c++/v1"
+# CHECK-SAME: "-internal-isystem" "[[SYSROOT]]/bin/../lib/clang-runtimes/arm-none-eabi/thumb/v8-m.main/fp/include"
+# CHECK-SAME: "-x" "c++" "{{.*}}baremetal-multilib.yaml"
+# CHECK-NEXT: ld{{(.exe)?}}" "{{.*}}.o" "-Bstatic"
+# CHECK-SAME: "-L[[SYSROOT]]/bin/../lib/clang-runtimes/arm-none-eabi/thumb/v8-m.main/fp/lib"
+# CHECK-SAME: "-lc" "-lm" "-lclang_rt.builtins"
+# CHECK-SAME: "-o" "{{.*}}.tmp.out"
+
+# RUN: %T/baremetal_multilib/bin/clang -no-canonical-prefixes -print-multi-directory 2>&1 \
+# RUN: --target=thumbv8m.main-none-eabihf --sysroot= \
+# RUN:   | FileCheck --check-prefix=CHECK-PRINT-MULTI-DIRECTORY %s
+# CHECK-PRINT-MULTI-DIRECTORY: arm-none-eabi/thumb/v8-m.main/fp
+
+# RUN: %T/baremetal_multilib/bin/clang -no-canonical-prefixes -print-multi-lib 2>&1 \
+# RUN: --target=arm-none-eabi --sysroot= \
+# RUN:   | FileCheck --check-prefix=CHECK-PRINT-MULTI-LIB %s
+# CHECK-PRINT-MULTI-LIB: arm-none-eabi/thumb/v6-m/nofp;@-target=thumbv6m-none-eabi@mfloat-abi=soft
+# CHECK-PRINT-MULTI-LIB: arm-none-eabi/thumb/v7-m/nofp;@-target=thumbv7m-none-eabi@mfloat-abi=soft
+# CHECK-PRINT-MULTI-LIB: arm-none-eabi/thumb/v7e-m/nofp;@-target=thumbv7em-none-eabi@mfloat-abi=soft@mfpu=none
+# CHECK-PRINT-MULTI-LIB: arm-none-eabi/thumb/v8-m.main/nofp;@-target=arm-none-eabi@mfloat-abi=soft@march=armv8m.main+nofp
+# CHECK-PRINT-MULTI-LIB: arm-none-eabi/thumb/v8.1-m.main/nofp/nomve;@-target=arm-none-eabi@mfloat-abi=soft@march=armv8.1m.main+nofp+nomve

[PATCH] D143059: [Driver] Enable selecting multiple multilibs

2023-03-24 Thread Michael Platings via Phabricator via cfe-commits
michaelplatings updated this revision to Diff 508039.
michaelplatings added a comment.

Rebase


Repository:
  rG LLVM Github Monorepo

CHANGES SINCE LAST ACTION
  https://reviews.llvm.org/D143059/new/

https://reviews.llvm.org/D143059

Files:
  clang/include/clang/Driver/Multilib.h
  clang/include/clang/Driver/ToolChain.h
  clang/lib/Driver/Driver.cpp
  clang/lib/Driver/Multilib.cpp
  clang/lib/Driver/ToolChain.cpp
  clang/lib/Driver/ToolChains/BareMetal.cpp
  clang/lib/Driver/ToolChains/CSKYToolChain.cpp
  clang/lib/Driver/ToolChains/Fuchsia.cpp
  clang/lib/Driver/ToolChains/Gnu.cpp
  clang/lib/Driver/ToolChains/Gnu.h
  clang/lib/Driver/ToolChains/Hexagon.cpp
  clang/lib/Driver/ToolChains/Hurd.cpp
  clang/lib/Driver/ToolChains/Linux.cpp
  clang/lib/Driver/ToolChains/MipsLinux.cpp
  clang/lib/Driver/ToolChains/OHOS.cpp
  clang/lib/Driver/ToolChains/RISCVToolchain.cpp
  clang/test/Driver/fuchsia.cpp
  clang/unittests/Driver/MultilibBuilderTest.cpp
  clang/unittests/Driver/MultilibTest.cpp

Index: clang/unittests/Driver/MultilibTest.cpp
===
--- clang/unittests/Driver/MultilibTest.cpp
+++ clang/unittests/Driver/MultilibTest.cpp
@@ -154,18 +154,18 @@
   Multilib("/bar", {}, {}, {"+bar"}),
   });
   Multilib::flags_list Flags1 = {"+foo", "-bar"};
-  Multilib Selection1;
+  llvm::SmallVector Selection1;
   ASSERT_TRUE(MS.select(Flags1, Selection1))
   << "Flag set was {\"+foo\"}, but selection not found";
-  ASSERT_TRUE(Selection1.gccSuffix() == "/foo")
-  << "Selection picked " << Selection1 << " which was not expected";
+  ASSERT_TRUE(Selection1.back().gccSuffix() == "/foo")
+  << "Selection picked " << Selection1.back() << " which was not expected";
 
   Multilib::flags_list Flags2 = {"+foo", "+bar"};
-  Multilib Selection2;
+  llvm::SmallVector Selection2;
   ASSERT_TRUE(MS.select(Flags2, Selection2))
   << "Flag set was {\"+bar\"}, but selection not found";
-  ASSERT_TRUE(Selection2.gccSuffix() == "/bar")
-  << "Selection picked " << Selection2 << " which was not expected";
+  ASSERT_TRUE(Selection2.back().gccSuffix() == "/bar")
+  << "Selection picked " << Selection2.back() << " which was not expected";
 }
 
 TEST(MultilibTest, SelectMultiple) {
@@ -173,17 +173,17 @@
   Multilib("/a", {}, {}, {"x"}),
   Multilib("/b", {}, {}, {"y"}),
   });
-  std::vector Selection;
+  llvm::SmallVector Selection;
 
-  Selection = MS.select({"x"});
+  ASSERT_TRUE(MS.select({"x"}, Selection));
   ASSERT_EQ(1u, Selection.size());
   EXPECT_EQ("/a", Selection[0].gccSuffix());
 
-  Selection = MS.select({"y"});
+  ASSERT_TRUE(MS.select({"y"}, Selection));
   ASSERT_EQ(1u, Selection.size());
   EXPECT_EQ("/b", Selection[0].gccSuffix());
 
-  Selection = MS.select({"y", "x"});
+  ASSERT_TRUE(MS.select({"y", "x"}, Selection));
   ASSERT_EQ(2u, Selection.size());
   EXPECT_EQ("/a", Selection[0].gccSuffix());
   EXPECT_EQ("/b", Selection[1].gccSuffix());
@@ -383,7 +383,7 @@
 
 TEST(MultilibTest, SelectSoft) {
   MultilibSet MS;
-  Multilib Selected;
+  llvm::SmallVector Selected;
   ASSERT_TRUE(parseYaml(MS, YAML_PREAMBLE R"(
 Variants:
 - Dir: s
@@ -402,7 +402,7 @@
 
 TEST(MultilibTest, SelectSoftFP) {
   MultilibSet MS;
-  Multilib Selected;
+  llvm::SmallVector Selected;
   ASSERT_TRUE(parseYaml(MS, YAML_PREAMBLE R"(
 Variants:
 - Dir: f
@@ -418,7 +418,7 @@
   // If hard float is all that's available then select that only if compiling
   // with hard float.
   MultilibSet MS;
-  Multilib Selected;
+  llvm::SmallVector Selected;
   ASSERT_TRUE(parseYaml(MS, YAML_PREAMBLE R"(
 Variants:
 - Dir: h
@@ -432,7 +432,7 @@
 
 TEST(MultilibTest, SelectFloatABI) {
   MultilibSet MS;
-  Multilib Selected;
+  llvm::SmallVector Selected;
   ASSERT_TRUE(parseYaml(MS, YAML_PREAMBLE R"(
 Variants:
 - Dir: s
@@ -453,18 +453,18 @@
   NoMatchFlags: [hasfp]
 )"));
   MS.select({"mfloat-abi=soft"}, Selected);
-  EXPECT_EQ("/s", Selected.gccSuffix());
+  EXPECT_EQ("/s", Selected.back().gccSuffix());
   MS.select({"mfloat-abi=softfp"}, Selected);
-  EXPECT_EQ("/f", Selected.gccSuffix());
+  EXPECT_EQ("/f", Selected.back().gccSuffix());
   MS.select({"mfloat-abi=hard"}, Selected);
-  EXPECT_EQ("/h", Selected.gccSuffix());
+  EXPECT_EQ("/h", Selected.back().gccSuffix());
 }
 
 TEST(MultilibTest, SelectFloatABIReversed) {
   // If soft is specified after softfp then softfp will never be
   // selected because soft is compatible with softfp and last wins.
   MultilibSet MS;
-  Multilib Selected;
+  llvm::SmallVector Selected;
   ASSERT_TRUE(parseYaml(MS, YAML_PREAMBLE R"(
 Variants:
 - Dir: h
@@ -485,11 +485,11 @@
   NoMatchFlags: [hasfp]
 )"));
   MS.select({"mfloat-abi=soft"}, Selected);
-  EXPECT_EQ("/s", Selected.gccSuffix());
+  EXPECT_EQ("/s", Selected.back().gccSuffix());
   MS.select({"mfloat-abi=softfp"}, Selected);
-  EXPECT_EQ("/s", Selected.gccSuffix());
+  EXPECT_EQ("/s", Selected.back().gccSuffix());
   MS.select({"mfloat-abi=hard"}, Selected)

[PATCH] D143075: BareMetal ToolChain multilib layering

2023-03-24 Thread Michael Platings via Phabricator via cfe-commits
michaelplatings updated this revision to Diff 508040.
michaelplatings added a comment.

Rebase


Repository:
  rG LLVM Github Monorepo

CHANGES SINCE LAST ACTION
  https://reviews.llvm.org/D143075/new/

https://reviews.llvm.org/D143075

Files:
  clang/lib/Driver/ToolChains/BareMetal.cpp
  clang/lib/Driver/ToolChains/BareMetal.h
  clang/test/Driver/baremetal-multilib.yaml

Index: clang/test/Driver/baremetal-multilib.yaml
===
--- clang/test/Driver/baremetal-multilib.yaml
+++ clang/test/Driver/baremetal-multilib.yaml
@@ -25,6 +25,23 @@
 # RUN:   | FileCheck --check-prefix=CHECK-PRINT-MULTI-DIRECTORY %s
 # CHECK-PRINT-MULTI-DIRECTORY: arm-none-eabi/thumb/v8-m.main/fp
 
+# RUN: %T/baremetal_multilib/bin/clang -no-canonical-prefixes -x c++ %s -### -o %t.out 2>&1 \
+# RUN: --target=thumbv8.1m.main-none-eabihf -fno-exceptions --sysroot= \
+# RUN:   | FileCheck -DSYSROOT=%T/baremetal_multilib --check-prefix=CHECK-LAYERED-MULTILIB %s
+# CHECK-LAYERED-MULTILIB:  "-cc1" "-triple" "thumbv8.1m.main-none-unknown-eabihf"
+# CHECK-LAYERED-MULTILIB-SAME: "-internal-isystem" "[[SYSROOT]]/bin/../lib/clang-runtimes/arm-none-eabi/thumb/v8.1-m.main/fp/noexcept/include/c++/v1"
+# CHECK-LAYERED-MULTILIB-SAME: "-internal-isystem" "[[SYSROOT]]/bin/../lib/clang-runtimes/arm-none-eabi/thumb/v8.1-m.main/fp/include/c++/v1"
+# CHECK-LAYERED-MULTILIB-SAME: "-internal-isystem" "[[SYSROOT]]/bin/../lib/clang-runtimes/arm-none-eabi/thumb/v8.1-m.main/fp/noexcept/include"
+# CHECK-LAYERED-MULTILIB-SAME: "-internal-isystem" "[[SYSROOT]]/bin/../lib/clang-runtimes/arm-none-eabi/thumb/v8.1-m.main/fp/include"
+# CHECK-LAYERED-MULTILIB-NEXT: "-L[[SYSROOT]]/bin/../lib/clang-runtimes/arm-none-eabi/thumb/v8.1-m.main/fp/noexcept/lib"
+# CHECK-LAYERED-MULTILIB-SAME: "-L[[SYSROOT]]/bin/../lib/clang-runtimes/arm-none-eabi/thumb/v8.1-m.main/fp/lib"
+
+# RUN: %T/baremetal_multilib/bin/clang -no-canonical-prefixes -print-multi-directory 2>&1 \
+# RUN: --target=thumbv8.1m.main-none-eabihf -fno-exceptions --sysroot= \
+# RUN:   | FileCheck --check-prefix=CHECK-LAYERED-PRINT-MULTI-DIRECTORY %s
+# CHECK-LAYERED-PRINT-MULTI-DIRECTORY:  arm-none-eabi/thumb/v8.1-m.main/fp
+# CHECK-LAYERED-PRINT-MULTI-DIRECTORY-NEXT: arm-none-eabi/thumb/v8.1-m.main/fp/noexcept
+
 # RUN: %T/baremetal_multilib/bin/clang -no-canonical-prefixes -print-multi-lib 2>&1 \
 # RUN: --target=arm-none-eabi --sysroot= \
 # RUN:   | FileCheck --check-prefix=CHECK-PRINT-MULTI-LIB %s
@@ -38,6 +55,7 @@
 # CHECK-PRINT-MULTI-LIB: arm-none-eabi/thumb/v8-m.main/fp;@-target=thumbv8m.main-none-eabihf
 # CHECK-PRINT-MULTI-LIB: arm-none-eabi/thumb/v8.1-m.main/fp;@-target=thumbv8.1m.main-none-eabihf
 # CHECK-PRINT-MULTI-LIB: arm-none-eabi/thumb/v8.1-m.main/nofp/mve;@-target=arm-none-eabihf@march=armv8.1m.main+nofp+mve
+# CHECK-PRINT-MULTI-LIB: arm-none-eabi/thumb/v8.1-m.main/fp/noexcept;@-target=thumbv8.1m.main-none-eabihf@fno-exceptions
 
 # RUN: %T/baremetal_multilib/bin/clang -no-canonical-prefixes -x assembler -mexecute-only \
 # RUN: --target=arm-none-eabi --sysroot= %s -c -### 2>&1 \
@@ -117,6 +135,14 @@
   Flags: [target=thumbv8.1m.main-none-unknown-eabihf, march=+mve]
   PrintOptions: [--target=arm-none-eabihf, -march=armv8.1m.main+nofp+mve]
 
+# A specialisation of v8.1-m.main/fp without exceptions.
+# This layers over the top of the regular v8.1-m.main/fp so it doesn't
+# need to have its own include directory or C library, thereby saving
+# disk space.
+- Dir: arm-none-eabi/thumb/v8.1-m.main/fp/noexcept
+  Flags: [target=thumbv8.1m.main-none-unknown-eabihf, hasfpu, fno-exceptions]
+  PrintOptions: [--target=thumbv8.1m.main-none-eabihf, -fno-exceptions]
+
 
 # The second section of the file is a map from auto-detected flags
 # to custom flags. The auto-detected flags can be printed out
Index: clang/lib/Driver/ToolChains/BareMetal.h
===
--- clang/lib/Driver/ToolChains/BareMetal.h
+++ clang/lib/Driver/ToolChains/BareMetal.h
@@ -71,6 +71,9 @@
   void AddLinkRuntimeLib(const llvm::opt::ArgList &Args,
  llvm::opt::ArgStringList &CmdArgs) const;
   std::string computeSysRoot() const override;
+
+private:
+  llvm::SmallVector getOrderedMultilibs() const;
 };
 
 } // namespace toolchains
Index: clang/lib/Driver/ToolChains/BareMetal.cpp
===
--- clang/lib/Driver/ToolChains/BareMetal.cpp
+++ clang/lib/Driver/ToolChains/BareMetal.cpp
@@ -103,9 +103,12 @@
   findMultilibs(D, Triple, Args);
   SmallString<128> SysRoot(computeSysRoot());
   if (!SysRoot.empty()) {
-llvm::sys::path::append(SysRoot, "lib");
-getFilePaths().push_back(std::string(SysRoot));
-getLibraryPaths().push_back(std::string(SysRoot));
+for (const Multilib &M : getOrderedMultilibs()) {
+  SmallString<128> Dir(SysRoot);
+  llvm::sys::path::append(Dir, M.osSuffix(), "lib");
+  getFileP

[PATCH] D143587: [Docs] Multilib design

2023-03-24 Thread Michael Platings via Phabricator via cfe-commits
michaelplatings updated this revision to Diff 508041.
michaelplatings added a comment.

Rebase


Repository:
  rG LLVM Github Monorepo

CHANGES SINCE LAST ACTION
  https://reviews.llvm.org/D143587/new/

https://reviews.llvm.org/D143587

Files:
  clang/docs/Multilib.rst
  clang/docs/index.rst
  clang/include/clang/Driver/Multilib.h

Index: clang/include/clang/Driver/Multilib.h
===
--- clang/include/clang/Driver/Multilib.h
+++ clang/include/clang/Driver/Multilib.h
@@ -77,6 +77,8 @@
   /// options and look similar to them, and others can be defined by a
   /// particular multilib.yaml. A multilib is considered compatible if its flags
   /// are a subset of the flags derived from the Clang command line options.
+  /// See clang/docs/Multilib.rst for further explanation of how flags may be
+  /// generated and used.
   const flags_list &flags() const { return Flags; }
 
   /// Returns the options that should be used for clang -print-multi-lib
Index: clang/docs/index.rst
===
--- clang/docs/index.rst
+++ clang/docs/index.rst
@@ -100,6 +100,7 @@
CodeOwners
InternalsManual
DriverInternals
+   Multilib
OffloadingDesign
PCHInternals
ItaniumMangleAbiTags
Index: clang/docs/Multilib.rst
===
--- /dev/null
+++ clang/docs/Multilib.rst
@@ -0,0 +1,327 @@
+
+Multilib
+
+
+Introduction
+
+
+This document describes how multilib is implemented in Clang.
+
+What is multilib and why might you care?
+If you're :doc:`cross compiling` then you can't use native
+system headers and libraries. To address this, you can use a combination of
+``--sysroot``, ``-isystem`` and ``-L`` options to point Clang at suitable
+directories for your target.
+However, when there are many possible directories to choose from, it's not
+necessarily obvious which one to pick.
+Multilib allows a toolchain designer to imbue the toolchain with the ability to
+pick a suitable directory automatically, based on the options the user provides
+to Clang. For example, if the user specifies
+``--target=arm-none-eabi -mcpu=cortex-m4`` the toolchain can choose a directory
+containing headers and libraries suitable for Armv7E-M, because it knows that's
+a suitable architecture for Arm Cortex-M4.
+Multilib can also choose between libraries for the same architecture based on
+other options. For example if the user specifies ``-fno-exceptions`` then a
+toolchain could select libraries built without exception support, thereby
+reducing the size of the resulting binary.
+
+Design
+==
+
+Clang supports GCC's ``-print-multi-lib`` and ``-print-multi-directory``
+options. These are described in
+`GCC Developer Options `_.
+
+There are two ways to configure multilib in Clang: hard-coded or via a
+configuration file.
+
+Hard-coded Multilib
+===
+
+The available libraries can be hard-coded in Clang. Typically this is done
+using the ``MultilibBuilder`` interface in
+``clang/include/clang/Driver/MultilibBuilder.h``.
+There are many examples of this in ``lib/Driver/ToolChains/Gnu.cpp``.
+The remainder of this document will not focus on this type of multilib.
+
+EXPERIMENTAL Multilib via configuration file
+
+
+Some Clang toolchains support loading multilib configuration from a
+``multilib.yaml`` configuration file.
+
+A ``multilib.yaml`` configuration file specifies which multilib variants are
+available, their relative location, what compilation options were used to build
+them, and the criteria by which they are selected.
+
+Multilib processing
+===
+
+Clang goes through the following steps to use multilib from a configuration
+file:
+#. Convert command line options to flags. Clang can accept the same
+   information via different options - for example,
+   ``--target=arm-none-eabi -march=armv7-m`` and
+   ``--target=armv7m-none-eabi`` are equivalent. Clang can also accept many
+   independent pieces of information within a single option - for example
+   ``-march=armv8.1m.main+fp+mve`` specifies the architecture and two
+   extensions in a single command line option.
+   To make it easier for the multilib system, Clang converts the command line
+   options into a standard set of simpler "flags". In many cases these flags
+   will look like a command line option with the leading ``-`` stripped off,
+   but where a suitable form for the flag doesn't exist in command line
+   options then its form will be different. For example, an Arm architecture
+   extension is represented like ``march=+mve`` since there's no way to specify
+   it in isolation in a command line option.
+   To see what flags are emitted for a given set of command line options, use
+   the ``-print-multi-selection-flags-experimen

[PATCH] D144638: [lit] Detect Consistent File Access Times

2023-02-27 Thread Michael Platings via Phabricator via cfe-commits
michaelplatings added a comment.

Thanks very much for looking into this, the flakiness of these tests has been 
bugging me for ages.




Comment at: llvm/utils/lit/lit/llvm/config.py:171
+# in the tests that do the same thing.
+(_, try_touch_err) = self.get_process_output(["touch", "-a", "-t", 
"199505050555.55", f.name])
+if try_touch_err != "":

It looks like this command will be run on Windows. I think it will fail and 
cause False to be returned, which is the desired result, but this appears to be 
by accident rather than design. Therefore I'm inclined to agree with @int3 that 
a hard-coded check would be preferable.


Repository:
  rG LLVM Github Monorepo

CHANGES SINCE LAST ACTION
  https://reviews.llvm.org/D144638/new/

https://reviews.llvm.org/D144638

___
cfe-commits mailing list
cfe-commits@lists.llvm.org
https://lists.llvm.org/cgi-bin/mailman/listinfo/cfe-commits


[PATCH] D144638: [lit] Detect Consistent File Access Times

2023-02-27 Thread Michael Platings via Phabricator via cfe-commits
michaelplatings added inline comments.



Comment at: llvm/utils/lit/lit/llvm/config.py:171
+# in the tests that do the same thing.
+(_, try_touch_err) = self.get_process_output(["touch", "-a", "-t", 
"199505050555.55", f.name])
+if try_touch_err != "":

lenary wrote:
> michaelplatings wrote:
> > It looks like this command will be run on Windows. I think it will fail and 
> > cause False to be returned, which is the desired result, but this appears 
> > to be by accident rather than design. Therefore I'm inclined to agree with 
> > @int3 that a hard-coded check would be preferable.
> I am going to add the hardcoded checks, but I think `touch` is available in 
> windows, it should be in the same directory as all the git binaries.
This is definitely tangential to the change, but in case it's useful to know: 
conventionally only `C:\Program Files\Git\bin` is added to the path on Windows, 
not `C:\Program Files\Git\usr\bin`. `C:\Program Files\Git\bin` only contains 
`bash.exe`, `git.exe` and `sh.exe`.


Repository:
  rG LLVM Github Monorepo

CHANGES SINCE LAST ACTION
  https://reviews.llvm.org/D144638/new/

https://reviews.llvm.org/D144638

___
cfe-commits mailing list
cfe-commits@lists.llvm.org
https://lists.llvm.org/cgi-bin/mailman/listinfo/cfe-commits


[PATCH] D144638: [lit] Detect Inconsistent File Access Times

2023-02-27 Thread Michael Platings via Phabricator via cfe-commits
michaelplatings added a comment.

I see some of these tests previously had `UNSUPPORTED: system-netbsd` but not 
`UNSUPPORTED: system-windows` - do you know why?




Comment at: llvm/utils/lit/lit/llvm/config.py:190
+return False
+if "1995" not in touch_res_out:
+return False

This could end up matching the wrong part of the string, for example if the 
temporary file happened to have 1995 in its name. A regex match for '\b1995\b' 
would be more reliable.


Repository:
  rG LLVM Github Monorepo

CHANGES SINCE LAST ACTION
  https://reviews.llvm.org/D144638/new/

https://reviews.llvm.org/D144638

___
cfe-commits mailing list
cfe-commits@lists.llvm.org
https://lists.llvm.org/cgi-bin/mailman/listinfo/cfe-commits


[PATCH] D144638: [lit] Detect Inconsistent File Access Times

2023-03-02 Thread Michael Platings via Phabricator via cfe-commits
michaelplatings accepted this revision.
michaelplatings added a comment.
This revision is now accepted and ready to land.

LGTM


Repository:
  rG LLVM Github Monorepo

CHANGES SINCE LAST ACTION
  https://reviews.llvm.org/D144638/new/

https://reviews.llvm.org/D144638

___
cfe-commits mailing list
cfe-commits@lists.llvm.org
https://lists.llvm.org/cgi-bin/mailman/listinfo/cfe-commits


  1   2   3   >