Index: lib/Target/ARM64/ARM64.td =================================================================== --- lib/Target/ARM64/ARM64.td +++ lib/Target/ARM64/ARM64.td @@ -29,6 +29,9 @@ def FeatureCrypto : SubtargetFeature<"crypto", "HasCrypto", "true", "Enable cryptographic instructions">; +def FeatureCRC : SubtargetFeature<"crc", "HasCRC", "true", + "Enable ARMv8 CRC-32 checksum instructions">; + /// Cyclone has register move instructions which are "free". def FeatureZCRegMove : SubtargetFeature<"zcm", "HasZeroCycleRegMove", "true", "Has zereo-cycle register moves">; @@ -63,22 +66,27 @@ "Cortex-A53 ARM processors", [FeatureFPARMv8, FeatureNEON, - FeatureCrypto]>; + FeatureCrypto, + FeatureCRC]>; def ProcA57 : SubtargetFeature<"a57", "ARMProcFamily", "CortexA57", "Cortex-A57 ARM processors", [FeatureFPARMv8, FeatureNEON, - FeatureCrypto]>; + FeatureCrypto, + FeatureCRC]>; def ProcCyclone : SubtargetFeature<"cyclone", "ARMProcFamily", "Cyclone", "Cyclone", [FeatureFPARMv8, FeatureNEON, FeatureCrypto, + FeatureCRC, FeatureZCRegMove, FeatureZCZeroing]>; -def : ProcessorModel<"generic", NoSchedModel, [FeatureFPARMv8, FeatureNEON]>; +def : ProcessorModel<"generic", NoSchedModel, [FeatureFPARMv8, + FeatureNEON, + FeatureCRC]>; def : ProcessorModel<"cortex-a53", CortexA53Model, [ProcA53]>; def : ProcessorModel<"cortex-a57", NoSchedModel, [ProcA57]>; Index: lib/Target/ARM64/ARM64InstrFormats.td =================================================================== --- lib/Target/ARM64/ARM64InstrFormats.td +++ lib/Target/ARM64/ARM64InstrFormats.td @@ -1243,6 +1243,7 @@ let Inst{11-10} = sz; let Inst{9-5} = Rn; let Inst{4-0} = Rd; + let Predicates = [HasCRC]; } //--- Index: lib/Target/ARM64/ARM64InstrInfo.td =================================================================== --- lib/Target/ARM64/ARM64InstrInfo.td +++ lib/Target/ARM64/ARM64InstrInfo.td @@ -18,8 +18,10 @@ AssemblerPredicate<"FeatureFPARMv8", "fp-armv8">; def HasNEON : Predicate<"Subtarget->hasNEON()">, AssemblerPredicate<"FeatureNEON", "neon">; -def HasCrypto : Predicate<"Subtarget->hasCrypto()">, +def HasCrypto : Predicate<"Subtarget->hasCrypto()">, AssemblerPredicate<"FeatureCrypto", "crypto">; +def HasCRC : Predicate<"Subtarget->hasCRC()">, + AssemblerPredicate<"FeatureCRC", "crc">; //===----------------------------------------------------------------------===// // ARM64-specific DAG Nodes. Index: lib/Target/ARM64/ARM64Subtarget.h =================================================================== --- lib/Target/ARM64/ARM64Subtarget.h +++ lib/Target/ARM64/ARM64Subtarget.h @@ -35,6 +35,7 @@ bool HasFPARMv8; bool HasNEON; bool HasCrypto; + bool HasCRC; // HasZeroCycleRegMove - Has zero-cycle register mov instructions. bool HasZeroCycleRegMove; @@ -66,6 +67,7 @@ bool hasFPARMv8() const { return HasFPARMv8; } bool hasNEON() const { return HasNEON; } bool hasCrypto() const { return HasCrypto; } + bool hasCRC() const { return HasCRC; } bool isLittleEndian() const { return IsLittleEndian; } Index: lib/Target/ARM64/ARM64Subtarget.cpp =================================================================== --- lib/Target/ARM64/ARM64Subtarget.cpp +++ lib/Target/ARM64/ARM64Subtarget.cpp @@ -29,7 +29,7 @@ ARM64Subtarget::ARM64Subtarget(const std::string &TT, const std::string &CPU, const std::string &FS, bool LittleEndian) : ARM64GenSubtargetInfo(TT, CPU, FS), ARMProcFamily(Others), - HasFPARMv8(false), HasNEON(false), HasCrypto(false), + HasFPARMv8(false), HasNEON(false), HasCrypto(false), HasCRC(false), HasZeroCycleRegMove(false), HasZeroCycleZeroing(false), CPUString(CPU), TargetTriple(TT), IsLittleEndian(LittleEndian) { // Determine default and user-specified characteristics Index: test/CodeGen/ARM64/crc32.ll =================================================================== --- test/CodeGen/ARM64/crc32.ll +++ test/CodeGen/ARM64/crc32.ll @@ -1,4 +1,4 @@ -; RUN: llc -march=arm64 -o - %s | FileCheck %s +; RUN: llc -march=arm64 -mattr=+crc -o - %s | FileCheck %s define i32 @test_crc32b(i32 %cur, i8 %next) { ; CHECK-LABEL: test_crc32b: Index: test/MC/ARM64/basic-a64-instructions.s =================================================================== --- test/MC/ARM64/basic-a64-instructions.s +++ test/MC/ARM64/basic-a64-instructions.s @@ -1,4 +1,4 @@ -// RUN: llvm-mc -triple arm64 -show-encoding < %s | FileCheck %s +// RUN: llvm-mc -triple arm64 -mattr=+crc -show-encoding < %s | FileCheck %s crc32b w5, w7, w20 crc32h w28, wzr, w30 Index: test/MC/ARM64/diagno-predicate.s =================================================================== --- test/MC/ARM64/diagno-predicate.s +++ test/MC/ARM64/diagno-predicate.s @@ -1,4 +1,4 @@ -// RUN: not llvm-mc -triple arm64-linux-gnu -mattr=-fp-armv8 < %s 2> %t +// RUN: not llvm-mc -triple arm64-linux-gnu -mattr=-fp-armv8,-crc < %s 2> %t // RUN: FileCheck --check-prefix=CHECK-ERROR < %t %s @@ -17,3 +17,8 @@ // CHECK-ERROR-NEXT: pmull v0.1q, v1.1d, v2.1d // CHECK-ERROR-NEXT: ^ + crc32b w5, w7, w20 +// CHECK-ERROR: error: instruction requires: crc +// CHECK-ERROR-NEXT: crc32b w5, w7, w20 +// CHECK-ERROR-NEXT: ^ + Index: test/MC/Disassembler/ARM64/crc32.txt =================================================================== --- test/MC/Disassembler/ARM64/crc32.txt +++ test/MC/Disassembler/ARM64/crc32.txt @@ -1,4 +1,4 @@ -# RUN: llvm-mc -triple=arm64 -disassemble < %s | FileCheck %s +# RUN: llvm-mc -triple=arm64 -mattr=+crc -disassemble < %s | FileCheck %s # CHECK: crc32b w5, w7, w20 # CHECK: crc32h w28, wzr, w30