@@ -54,10 +54,27 @@ using namespace llvm;
54
54
55
55
extern cl::OptionCategory DisassemblerEmitterCat;
56
56
57
- cl::opt<bool > DecoderEmitterSuppressDuplicates (
57
+ enum SuppressLevel {
58
+ SUPPRESSION_DISABLE,
59
+ SUPPRESSION_LEVEL1,
60
+ SUPPRESSION_LEVEL2
61
+ };
62
+
63
+ cl::opt<SuppressLevel> DecoderEmitterSuppressDuplicates (
58
64
" suppress-per-hwmode-duplicates" ,
59
65
cl::desc (" Suppress duplication of instrs into per-HwMode decoder tables" ),
60
- cl::init(false ), cl::cat(DisassemblerEmitterCat));
66
+ cl::values(
67
+ clEnumValN (
68
+ SUPPRESSION_DISABLE, " O0" ,
69
+ " Do not prevent DecoderTable duplications caused by HwModes" ),
70
+ clEnumValN(
71
+ SUPPRESSION_LEVEL1, " O1" ,
72
+ " Remove duplicate DecoderTable entries generated due to HwModes" ),
73
+ clEnumValN(
74
+ SUPPRESSION_LEVEL2, " O2" ,
75
+ " Extract HwModes-specific instructions into new DecoderTables, "
76
+ " significantly reducing Table Duplications" )),
77
+ cl::init(SUPPRESSION_DISABLE), cl::cat(DisassemblerEmitterCat));
61
78
62
79
namespace {
63
80
@@ -128,6 +145,8 @@ struct EncodingIDAndOpcode {
128
145
};
129
146
130
147
using EncodingIDsVec = std::vector<EncodingIDAndOpcode>;
148
+ using NamespacesHwModesMap =
149
+ std::map<std::string, std::map<StringRef, unsigned >>;
131
150
132
151
raw_ostream &operator <<(raw_ostream &OS, const EncodingAndInst &Value) {
133
152
if (Value.EncodingDef != Value.Inst ->TheDef )
@@ -2417,21 +2436,65 @@ static bool Check(DecodeStatus &Out, DecodeStatus In) {
2417
2436
2418
2437
// Collect all HwModes referenced by the target for encoding purposes,
2419
2438
// returning a vector of corresponding names.
2420
- static void
2421
- collectHwModesReferencedForEncodings ( const CodeGenHwModes &HWM,
2422
- std::vector<StringRef> &Names ) {
2439
+ static void collectHwModesReferencedForEncodings (
2440
+ const CodeGenHwModes &HWM, std::vector<StringRef> &Names ,
2441
+ NamespacesHwModesMap &NamespacesWithHwModes ) {
2423
2442
SmallBitVector BV (HWM.getNumModeIds ());
2424
2443
for (const auto &MS : HWM.getHwModeSelects ()) {
2425
2444
for (const HwModeSelect::PairType &P : MS.second .Items ) {
2426
- if (P.second ->isSubClassOf (" InstructionEncoding" ))
2445
+ if (P.second ->isSubClassOf (" InstructionEncoding" )) {
2446
+ std::string DecoderNamespace =
2447
+ std::string (P.second ->getValueAsString (" DecoderNamespace" ));
2448
+ if (P.first == DefaultMode) {
2449
+ NamespacesWithHwModes[DecoderNamespace][" " ] = 1 ;
2450
+ } else {
2451
+ NamespacesWithHwModes[DecoderNamespace][HWM.getMode (P.first ).Name ] =
2452
+ 1 ;
2453
+ }
2427
2454
BV.set (P.first );
2455
+ }
2428
2456
}
2429
2457
}
2430
2458
transform (BV.set_bits (), std::back_inserter (Names), [&HWM](const int &M) {
2459
+ if (M == DefaultMode)
2460
+ return StringRef (" " );
2431
2461
return HWM.getModeName (M, /* IncludeDefault=*/ true );
2432
2462
});
2433
2463
}
2434
2464
2465
+ static void
2466
+ handleHwModesUnrelatedEncodings (const CodeGenInstruction *Instr,
2467
+ const std::vector<StringRef> &HwModeNames,
2468
+ NamespacesHwModesMap &NamespacesWithHwModes,
2469
+ std::vector<EncodingAndInst> &GlobalEncodings) {
2470
+ const Record *InstDef = Instr->TheDef ;
2471
+
2472
+ switch (DecoderEmitterSuppressDuplicates) {
2473
+ case SUPPRESSION_DISABLE: {
2474
+ for (StringRef HwModeName : HwModeNames)
2475
+ GlobalEncodings.emplace_back (InstDef, Instr, HwModeName);
2476
+ break ;
2477
+ }
2478
+ case SUPPRESSION_LEVEL1: {
2479
+ std::string DecoderNamespace =
2480
+ std::string (InstDef->getValueAsString (" DecoderNamespace" ));
2481
+ for (StringRef HwModeName : HwModeNames) {
2482
+ if (NamespacesWithHwModes.count (DecoderNamespace) > 0 &&
2483
+ NamespacesWithHwModes[DecoderNamespace].count (HwModeName) > 0 ) {
2484
+ GlobalEncodings.emplace_back (InstDef, Instr, HwModeName);
2485
+ } else {
2486
+ GlobalEncodings.emplace_back (InstDef, Instr, " " );
2487
+ break ;
2488
+ }
2489
+ }
2490
+ break ;
2491
+ }
2492
+ case SUPPRESSION_LEVEL2:
2493
+ GlobalEncodings.emplace_back (InstDef, Instr, " " );
2494
+ break ;
2495
+ }
2496
+ }
2497
+
2435
2498
// Emits disassembler code for instruction decoding.
2436
2499
void DecoderEmitter::run (raw_ostream &o) {
2437
2500
formatted_raw_ostream OS (o);
@@ -2457,10 +2520,12 @@ namespace llvm {
2457
2520
// Parameterize the decoders based on namespace and instruction width.
2458
2521
2459
2522
// First, collect all encoding-related HwModes referenced by the target.
2523
+ // And establish a mapping table between DecoderNamespace and HwMode.
2460
2524
// If HwModeNames is empty, add the empty string so we always have one HwMode.
2461
2525
const CodeGenHwModes &HWM = Target.getHwModes ();
2462
2526
std::vector<StringRef> HwModeNames;
2463
- collectHwModesReferencedForEncodings (HWM, HwModeNames);
2527
+ NamespacesHwModesMap NamespacesWithHwModes;
2528
+ collectHwModesReferencedForEncodings (HWM, HwModeNames, NamespacesWithHwModes);
2464
2529
if (HwModeNames.empty ())
2465
2530
HwModeNames.push_back (" " );
2466
2531
@@ -2471,22 +2536,22 @@ namespace llvm {
2471
2536
if (const RecordVal *RV = InstDef->getValue (" EncodingInfos" )) {
2472
2537
if (DefInit *DI = dyn_cast_or_null<DefInit>(RV->getValue ())) {
2473
2538
EncodingInfoByHwMode EBM (DI->getDef (), HWM);
2474
- for (auto &KV : EBM)
2475
- NumberedEncodings.emplace_back (
2476
- KV.second , NumberedInstruction,
2477
- HWM.getModeName (KV.first , /* IncludeDefault=*/ true ));
2539
+ for (auto &[ModeId, Encoding] : EBM) {
2540
+ // DecoderTables with DefaultMode should not have any suffix.
2541
+ if (ModeId == DefaultMode) {
2542
+ NumberedEncodings.emplace_back (Encoding, NumberedInstruction, " " );
2543
+ } else {
2544
+ NumberedEncodings.emplace_back (Encoding, NumberedInstruction,
2545
+ HWM.getMode (ModeId).Name );
2546
+ }
2547
+ }
2478
2548
continue ;
2479
2549
}
2480
2550
}
2481
- // This instruction is encoded the same on all HwModes. Emit it for all
2482
- // HwModes by default, otherwise leave it in a single common table.
2483
- if (DecoderEmitterSuppressDuplicates) {
2484
- NumberedEncodings.emplace_back (InstDef, NumberedInstruction, " AllModes" );
2485
- } else {
2486
- for (StringRef HwModeName : HwModeNames)
2487
- NumberedEncodings.emplace_back (InstDef, NumberedInstruction,
2488
- HwModeName);
2489
- }
2551
+ // This instruction is encoded the same on all HwModes.
2552
+ // According to user needs, provide varying degrees of suppression.
2553
+ handleHwModesUnrelatedEncodings (NumberedInstruction, HwModeNames,
2554
+ NamespacesWithHwModes, NumberedEncodings);
2490
2555
}
2491
2556
for (const auto &NumberedAlias :
2492
2557
RK.getAllDerivedDefinitions (" AdditionalEncoding" ))
0 commit comments