benshi001 created this revision.
benshi001 added reviewers: MaskRay, aykevl, dylanmckay.
Herald added a subscriber: Jim.
benshi001 requested review of this revision.
Herald added subscribers: cfe-commits, jacquesguan.
Herald added a project: clang.
Repository:
rG LLVM Github Monorepo
https://reviews.llvm.org/D118095
Files:
clang/include/clang/Basic/DiagnosticDriverKinds.td
clang/lib/Driver/ToolChains/AVR.cpp
clang/lib/Driver/ToolChains/AVR.h
clang/test/Driver/avr-mmcu.S
clang/test/Driver/avr-mmcu.c
Index: clang/test/Driver/avr-mmcu.c
===================================================================
--- clang/test/Driver/avr-mmcu.c
+++ clang/test/Driver/avr-mmcu.c
@@ -1,12 +1,15 @@
// A test for the propagation of the -mmcu option to -cc1 and -cc1as
-// RUN: %clang -### -target avr -no-canonical-prefixes -mmcu=attiny11 -save-temps %s 2>&1 | FileCheck -check-prefix=CHECK0 %s
-// CHECK0: clang{{.*}} "-cc1" {{.*}} "-target-cpu" "attiny11"
-// CHECK0: clang{{.*}} "-cc1as" {{.*}} "-target-cpu" "attiny11"
+// RUN: %clang -### -target avr -no-canonical-prefixes -mmcu=attiny11 %s -c 2>&1 | FileCheck -check-prefix=CHECKA %s
+// CHECKA: error: device 'attiny11' only supports assembly programming
+
+// RUN: %clang -### -target avr -no-canonical-prefixes -mmcu=attiny11 -x assembler-with-cpp %s -c 2>&1 | FileCheck -check-prefix=CHECKB %s
+// CHECKB-NOT: error: device 'attiny11' only supports assembly programming
// RUN: %clang -### -target avr -no-canonical-prefixes -mmcu=at90s2313 -save-temps %s 2>&1 | FileCheck -check-prefix=CHECK1 %s
// CHECK1: clang{{.*}} "-cc1" {{.*}} "-target-cpu" "at90s2313"
// CHECK1: clang{{.*}} "-cc1as" {{.*}} "-target-cpu" "at90s2313"
+// CHECK1-NOT: error: device 'at90s2313' only supports assembly programming
// RUN: %clang -### -target avr -no-canonical-prefixes -mmcu=at90s8515 -save-temps %s 2>&1 | FileCheck -check-prefix=CHECK2 %s
// CHECK2: clang{{.*}} "-cc1" {{.*}} "-target-cpu" "at90s8515"
Index: clang/test/Driver/avr-mmcu.S
===================================================================
--- /dev/null
+++ clang/test/Driver/avr-mmcu.S
@@ -0,0 +1,13 @@
+// A test for the supported language mode by different avr families.
+
+// RUN: %clang -### -target avr -no-canonical-prefixes -mmcu=attiny11 %s -c 2>&1 | FileCheck -check-prefix=CHECKA %s
+// CHECKA-NOT: error: device 'attiny11' only supports assembly programming
+
+// RUN: %clang -### -target avr -no-canonical-prefixes -mmcu=attiny11 -x c++ %s -c 2>&1 | FileCheck -check-prefix=CHECKB %s
+// CHECKB: error: device 'attiny11' only supports assembly programming
+
+// RUN: %clang -### -target avr -no-canonical-prefixes -mmcu=at90s8515 %s -c 2>&1 | FileCheck -check-prefix=CHECKC %s
+// CHECKC-NOT: error: device 'at90s8515' only supports assembly programming
+
+// RUN: %clang -### -target avr -no-canonical-prefixes -mmcu=at90s8515 %s -x c++ -c 2>&1 | FileCheck -check-prefix=CHECKD %s
+// CHECKD-NOT: error: device 'at90s8515' only supports assembly programming
Index: clang/lib/Driver/ToolChains/AVR.h
===================================================================
--- clang/lib/Driver/ToolChains/AVR.h
+++ clang/lib/Driver/ToolChains/AVR.h
@@ -19,6 +19,8 @@
namespace toolchains {
class LLVM_LIBRARY_VISIBILITY AVRToolChain : public Generic_ELF {
+ std::string AVRMcu;
+
public:
AVRToolChain(const Driver &D, const llvm::Triple &Triple,
const llvm::opt::ArgList &Args);
Index: clang/lib/Driver/ToolChains/AVR.cpp
===================================================================
--- clang/lib/Driver/ToolChains/AVR.cpp
+++ clang/lib/Driver/ToolChains/AVR.cpp
@@ -12,6 +12,7 @@
#include "clang/Driver/DriverDiagnostic.h"
#include "clang/Driver/InputInfo.h"
#include "clang/Driver/Options.h"
+#include "clang/Driver/Types.h"
#include "llvm/ADT/Optional.h"
#include "llvm/ADT/StringExtras.h"
#include "llvm/ADT/StringSwitch.h"
@@ -19,6 +20,7 @@
#include "llvm/MC/SubtargetFeature.h"
#include "llvm/Option/ArgList.h"
#include "llvm/Support/FileSystem.h"
+#include "llvm/Support/Path.h"
using namespace clang::driver;
using namespace clang::driver::toolchains;
@@ -311,24 +313,27 @@
: Generic_ELF(D, Triple, Args), LinkStdlib(false) {
GCCInstallation.init(Triple, Args);
+ // Save the CPU name for further checks.
+ AVRMcu = getCPUName(D, Args, Triple);
+
// Only add default libraries if the user hasn't explicitly opted out.
if (!Args.hasArg(options::OPT_nostdlib) &&
!Args.hasArg(options::OPT_nodefaultlibs) &&
+ !Args.hasArg(options::OPT_S /* does not apply when not linking */) &&
!Args.hasArg(options::OPT_c /* does not apply when not linking */)) {
- std::string CPU = getCPUName(D, Args, Triple);
- if (CPU.empty()) {
+ if (AVRMcu.empty()) {
// We cannot link any standard libraries without an MCU specified.
D.Diag(diag::warn_drv_avr_mcu_not_specified);
} else {
- Optional<StringRef> FamilyName = GetMCUFamilyName(CPU);
+ Optional<StringRef> FamilyName = GetMCUFamilyName(AVRMcu);
Optional<std::string> AVRLibcRoot = findAVRLibcInstallation();
if (!FamilyName.hasValue()) {
// We do not have an entry for this CPU in the family
// mapping table yet.
D.Diag(diag::warn_drv_avr_family_linking_stdlibs_not_implemented)
- << CPU;
+ << AVRMcu;
} else if (!GCCInstallation.isValid()) {
// No avr-gcc found and so no runtime linked.
D.Diag(diag::warn_drv_avr_gcc_not_found);
@@ -339,7 +344,7 @@
std::string GCCRoot(GCCInstallation.getInstallPath());
std::string GCCParentPath(GCCInstallation.getParentLibPath());
std::string LibcRoot = AVRLibcRoot.getValue();
- std::string SubPath = GetMCUSubPath(CPU);
+ std::string SubPath = GetMCUSubPath(AVRMcu);
getProgramPaths().push_back(GCCParentPath + "/../bin");
getFilePaths().push_back(LibcRoot + std::string("/lib/") + SubPath);
@@ -379,6 +384,45 @@
if (!DriverArgs.hasFlag(options::OPT_fuse_init_array,
options::OPT_fno_use_init_array, false))
CC1Args.push_back("-fno-use-init-array");
+
+ // Check if current main file is assembly when current MCU belongs to
+ // the avr1 family.
+ llvm::Optional<StringRef> FamilyName = GetMCUFamilyName(AVRMcu);
+ if (FamilyName.hasValue() && FamilyName->equals("avr1")) {
+ // Only '-x assembler-with-cpp' or '-x assembler' is allowed for avr1.
+ auto Langs = DriverArgs.getAllArgValues(options::OPT_x);
+ for (auto Lang : Langs)
+ if (Lang != "assembler-with-cpp" && Lang != "assembler")
+ getDriver().Diag(diag::err_drv_avr_assembly_only) << AVRMcu;
+
+ // Get the main file name.
+ const char *MainFileName = nullptr;
+ for (unsigned I = 0; I < CC1Args.size(); I++)
+ if (StringRef(CC1Args[I]).equals("-main-file-name")) {
+ MainFileName = CC1Args[I + 1];
+ break;
+ }
+ if (!MainFileName)
+ return;
+
+ // The main input file should be assembly only, it is OK that the main
+ // input file has either a '.S' or a '.s' suffix.
+ types::ID MainFileId = types::lookupTypeForExtension(
+ llvm::sys::path::extension(MainFileName).drop_front());
+ if (MainFileId == types::TY_Asm || MainFileId == types::TY_PP_Asm)
+ return;
+
+ // The main input file should be assembly only, it should be led by either
+ // '-x assembler-with-cpp' or '-x assembler', if it has neither a '.S' nor
+ // a '.s' suffix.
+ for (unsigned I = 0; I < DriverArgs.size(); I++) {
+ StringRef Arg(DriverArgs.getArgString(I));
+ if (Arg.equals("assembler-with-cpp") || Arg.equals("assembler"))
+ return;
+ if (Arg.contains(MainFileName))
+ getDriver().Diag(diag::err_drv_avr_assembly_only) << AVRMcu;
+ }
+ }
}
Tool *AVRToolChain::buildLinker() const {
Index: clang/include/clang/Basic/DiagnosticDriverKinds.td
===================================================================
--- clang/include/clang/Basic/DiagnosticDriverKinds.td
+++ clang/include/clang/Basic/DiagnosticDriverKinds.td
@@ -57,6 +57,8 @@
"standard library not linked and so no interrupt vector table or "
"compiler runtime routines will be linked">,
InGroup<AVRRtlibLinkingQuirks>;
+def err_drv_avr_assembly_only : Error<
+ "device '%0' only supports assembly programming">;
def err_drv_cuda_bad_gpu_arch : Error<"unsupported CUDA gpu architecture: %0">;
def err_drv_no_cuda_installation : Error<
"cannot find CUDA installation; provide its path via '--cuda-path', or pass "
_______________________________________________
cfe-commits mailing list
[email protected]
https://lists.llvm.org/cgi-bin/mailman/listinfo/cfe-commits