@@ -39,13 +39,17 @@ enum RegisterKind {
39
39
ADDR64Reg,
40
40
FP32Reg,
41
41
FP64Reg,
42
- FP128Reg
42
+ FP128Reg,
43
+ VR32Reg,
44
+ VR64Reg,
45
+ VR128Reg
43
46
};
44
47
45
48
enum MemoryKind {
46
49
BDMem,
47
50
BDXMem,
48
- BDLMem
51
+ BDLMem,
52
+ BDVMem
49
53
};
50
54
51
55
class SystemZOperand : public MCParsedAsmOperand {
@@ -89,10 +93,10 @@ class SystemZOperand : public MCParsedAsmOperand {
89
93
// the base register has (ADDR32Reg or ADDR64Reg). Length is the operand
90
94
// length for D(L,B)-style operands, otherwise it is null.
91
95
struct MemOp {
92
- unsigned Base : 8 ;
93
- unsigned Index : 8 ;
94
- unsigned MemKind : 8 ;
95
- unsigned RegKind : 8 ;
96
+ unsigned Base : 12 ;
97
+ unsigned Index : 12 ;
98
+ unsigned MemKind : 4 ;
99
+ unsigned RegKind : 4 ;
96
100
const MCExpr *Disp;
97
101
const MCExpr *Length;
98
102
};
@@ -246,6 +250,13 @@ class SystemZOperand : public MCParsedAsmOperand {
246
250
bool isMemDisp12Len8 (RegisterKind RegKind) const {
247
251
return isMemDisp12 (BDLMem, RegKind) && inRange (Mem.Length , 1 , 0x100 );
248
252
}
253
+ void addBDVAddrOperands (MCInst &Inst, unsigned N) const {
254
+ assert (N == 3 && " Invalid number of operands" );
255
+ assert (isMem (BDVMem) && " Invalid operand type" );
256
+ Inst.addOperand (MCOperand::CreateReg (Mem.Base ));
257
+ addExpr (Inst, Mem.Disp );
258
+ Inst.addOperand (MCOperand::CreateReg (Mem.Index ));
259
+ }
249
260
250
261
// Override MCParsedAsmOperand.
251
262
SMLoc getStartLoc () const override { return StartLoc; }
@@ -307,17 +318,26 @@ class SystemZOperand : public MCParsedAsmOperand {
307
318
bool isFP32 () const { return isReg (FP32Reg); }
308
319
bool isFP64 () const { return isReg (FP64Reg); }
309
320
bool isFP128 () const { return isReg (FP128Reg); }
321
+ bool isVR32 () const { return isReg (VR32Reg); }
322
+ bool isVR64 () const { return isReg (VR64Reg); }
323
+ bool isVF128 () const { return false ; }
324
+ bool isVR128 () const { return isReg (VR128Reg); }
310
325
bool isBDAddr32Disp12 () const { return isMemDisp12 (BDMem, ADDR32Reg); }
311
326
bool isBDAddr32Disp20 () const { return isMemDisp20 (BDMem, ADDR32Reg); }
312
327
bool isBDAddr64Disp12 () const { return isMemDisp12 (BDMem, ADDR64Reg); }
313
328
bool isBDAddr64Disp20 () const { return isMemDisp20 (BDMem, ADDR64Reg); }
314
329
bool isBDXAddr64Disp12 () const { return isMemDisp12 (BDXMem, ADDR64Reg); }
315
330
bool isBDXAddr64Disp20 () const { return isMemDisp20 (BDXMem, ADDR64Reg); }
316
331
bool isBDLAddr64Disp12Len8 () const { return isMemDisp12Len8 (ADDR64Reg); }
332
+ bool isBDVAddr64Disp12 () const { return isMemDisp12 (BDVMem, ADDR64Reg); }
333
+ bool isU1Imm () const { return isImm (0 , 1 ); }
334
+ bool isU2Imm () const { return isImm (0 , 3 ); }
335
+ bool isU3Imm () const { return isImm (0 , 7 ); }
317
336
bool isU4Imm () const { return isImm (0 , 15 ); }
318
337
bool isU6Imm () const { return isImm (0 , 63 ); }
319
338
bool isU8Imm () const { return isImm (0 , 255 ); }
320
339
bool isS8Imm () const { return isImm (-128 , 127 ); }
340
+ bool isU12Imm () const { return isImm (0 , 4095 ); }
321
341
bool isU16Imm () const { return isImm (0 , 65535 ); }
322
342
bool isS16Imm () const { return isImm (-32768 , 32767 ); }
323
343
bool isU32Imm () const { return isImm (0 , (1LL << 32 ) - 1 ); }
@@ -334,6 +354,7 @@ class SystemZAsmParser : public MCTargetAsmParser {
334
354
enum RegisterGroup {
335
355
RegGR,
336
356
RegFP,
357
+ RegV,
337
358
RegAccess
338
359
};
339
360
struct Register {
@@ -352,7 +373,7 @@ class SystemZAsmParser : public MCTargetAsmParser {
352
373
RegisterKind Kind);
353
374
354
375
bool parseAddress (unsigned &Base, const MCExpr *&Disp,
355
- unsigned &Index, const MCExpr *&Length,
376
+ unsigned &Index, bool &IsVector, const MCExpr *&Length,
356
377
const unsigned *Regs, RegisterKind RegKind);
357
378
358
379
OperandMatchResultTy parseAddress (OperandVector &Operands,
@@ -419,6 +440,18 @@ class SystemZAsmParser : public MCTargetAsmParser {
419
440
OperandMatchResultTy parseFP128 (OperandVector &Operands) {
420
441
return parseRegister (Operands, RegFP, SystemZMC::FP128Regs, FP128Reg);
421
442
}
443
+ OperandMatchResultTy parseVR32 (OperandVector &Operands) {
444
+ return parseRegister (Operands, RegV, SystemZMC::VR32Regs, VR32Reg);
445
+ }
446
+ OperandMatchResultTy parseVR64 (OperandVector &Operands) {
447
+ return parseRegister (Operands, RegV, SystemZMC::VR64Regs, VR64Reg);
448
+ }
449
+ OperandMatchResultTy parseVF128 (OperandVector &Operands) {
450
+ llvm_unreachable (" Shouldn't be used as an operand" );
451
+ }
452
+ OperandMatchResultTy parseVR128 (OperandVector &Operands) {
453
+ return parseRegister (Operands, RegV, SystemZMC::VR128Regs, VR128Reg);
454
+ }
422
455
OperandMatchResultTy parseBDAddr32 (OperandVector &Operands) {
423
456
return parseAddress (Operands, BDMem, SystemZMC::GR32Regs, ADDR32Reg);
424
457
}
@@ -431,6 +464,9 @@ class SystemZAsmParser : public MCTargetAsmParser {
431
464
OperandMatchResultTy parseBDLAddr64 (OperandVector &Operands) {
432
465
return parseAddress (Operands, BDLMem, SystemZMC::GR64Regs, ADDR64Reg);
433
466
}
467
+ OperandMatchResultTy parseBDVAddr64 (OperandVector &Operands) {
468
+ return parseAddress (Operands, BDVMem, SystemZMC::GR64Regs, ADDR64Reg);
469
+ }
434
470
OperandMatchResultTy parseAccessReg (OperandVector &Operands);
435
471
OperandMatchResultTy parsePCRel16 (OperandVector &Operands) {
436
472
return parsePCRel (Operands, -(1LL << 16 ), (1LL << 16 ) - 1 , false );
@@ -484,6 +520,8 @@ bool SystemZAsmParser::parseRegister(Register &Reg) {
484
520
Reg.Group = RegGR;
485
521
else if (Prefix == ' f' && Reg.Num < 16 )
486
522
Reg.Group = RegFP;
523
+ else if (Prefix == ' v' && Reg.Num < 32 )
524
+ Reg.Group = RegV;
487
525
else if (Prefix == ' a' && Reg.Num < 16 )
488
526
Reg.Group = RegAccess;
489
527
else
@@ -534,8 +572,8 @@ SystemZAsmParser::parseRegister(OperandVector &Operands, RegisterGroup Group,
534
572
// Regs maps asm register numbers to LLVM register numbers and RegKind
535
573
// says what kind of address register we're using (ADDR32Reg or ADDR64Reg).
536
574
bool SystemZAsmParser::parseAddress (unsigned &Base, const MCExpr *&Disp,
537
- unsigned &Index, const MCExpr *&Length ,
538
- const unsigned *Regs,
575
+ unsigned &Index, bool &IsVector ,
576
+ const MCExpr *&Length, const unsigned *Regs,
539
577
RegisterKind RegKind) {
540
578
// Parse the displacement, which must always be present.
541
579
if (getParser ().parseExpression (Disp))
@@ -544,19 +582,31 @@ bool SystemZAsmParser::parseAddress(unsigned &Base, const MCExpr *&Disp,
544
582
// Parse the optional base and index.
545
583
Index = 0 ;
546
584
Base = 0 ;
585
+ IsVector = false ;
547
586
Length = nullptr ;
548
587
if (getLexer ().is (AsmToken::LParen)) {
549
588
Parser.Lex ();
550
589
551
590
if (getLexer ().is (AsmToken::Percent)) {
552
591
// Parse the first register and decide whether it's a base or an index.
553
592
Register Reg;
554
- if (parseRegister (Reg, RegGR, Regs, RegKind ))
593
+ if (parseRegister (Reg))
555
594
return true ;
556
- if (getLexer ().is (AsmToken::Comma))
557
- Index = Reg.Num ;
558
- else
559
- Base = Reg.Num ;
595
+ if (Reg.Group == RegV) {
596
+ // A vector index register. The base register is optional.
597
+ IsVector = true ;
598
+ Index = SystemZMC::VR128Regs[Reg.Num ];
599
+ } else if (Reg.Group == RegGR) {
600
+ if (Reg.Num == 0 )
601
+ return Error (Reg.StartLoc , " %r0 used in an address" );
602
+ // If the are two registers, the first one is the index and the
603
+ // second is the base.
604
+ if (getLexer ().is (AsmToken::Comma))
605
+ Index = Regs[Reg.Num ];
606
+ else
607
+ Base = Regs[Reg.Num ];
608
+ } else
609
+ return Error (Reg.StartLoc , " invalid address register" );
560
610
} else {
561
611
// Parse the length.
562
612
if (getParser ().parseExpression (Length))
@@ -587,28 +637,36 @@ SystemZAsmParser::parseAddress(OperandVector &Operands, MemoryKind MemKind,
587
637
const unsigned *Regs, RegisterKind RegKind) {
588
638
SMLoc StartLoc = Parser.getTok ().getLoc ();
589
639
unsigned Base, Index;
640
+ bool IsVector;
590
641
const MCExpr *Disp;
591
642
const MCExpr *Length;
592
- if (parseAddress (Base, Disp, Index, Length, Regs, RegKind))
643
+ if (parseAddress (Base, Disp, Index, IsVector, Length, Regs, RegKind))
593
644
return MatchOperand_ParseFail;
594
645
595
- if (Index && MemKind != BDXMem)
596
- {
597
- Error (StartLoc, " invalid use of indexed addressing" );
598
- return MatchOperand_ParseFail;
599
- }
646
+ if (IsVector && MemKind != BDVMem) {
647
+ Error (StartLoc, " invalid use of vector addressing" );
648
+ return MatchOperand_ParseFail;
649
+ }
600
650
601
- if (Length && MemKind != BDLMem)
602
- {
603
- Error (StartLoc, " invalid use of length addressing" );
604
- return MatchOperand_ParseFail;
605
- }
651
+ if (!IsVector && MemKind == BDVMem) {
652
+ Error (StartLoc, " vector index required in address" );
653
+ return MatchOperand_ParseFail;
654
+ }
606
655
607
- if (!Length && MemKind == BDLMem)
608
- {
609
- Error (StartLoc, " missing length in address" );
610
- return MatchOperand_ParseFail;
611
- }
656
+ if (Index && MemKind != BDXMem && MemKind != BDVMem) {
657
+ Error (StartLoc, " invalid use of indexed addressing" );
658
+ return MatchOperand_ParseFail;
659
+ }
660
+
661
+ if (Length && MemKind != BDLMem) {
662
+ Error (StartLoc, " invalid use of length addressing" );
663
+ return MatchOperand_ParseFail;
664
+ }
665
+
666
+ if (!Length && MemKind == BDLMem) {
667
+ Error (StartLoc, " missing length in address" );
668
+ return MatchOperand_ParseFail;
669
+ }
612
670
613
671
SMLoc EndLoc =
614
672
SMLoc::getFromPointer (Parser.getTok ().getLoc ().getPointer () - 1 );
@@ -631,6 +689,8 @@ bool SystemZAsmParser::ParseRegister(unsigned &RegNo, SMLoc &StartLoc,
631
689
RegNo = SystemZMC::GR64Regs[Reg.Num ];
632
690
else if (Reg.Group == RegFP)
633
691
RegNo = SystemZMC::FP64Regs[Reg.Num ];
692
+ else if (Reg.Group == RegV)
693
+ RegNo = SystemZMC::VR128Regs[Reg.Num ];
634
694
else
635
695
// FIXME: Access registers aren't modelled as LLVM registers yet.
636
696
return Error (Reg.StartLoc , " invalid operand for instruction" );
@@ -703,8 +763,10 @@ bool SystemZAsmParser::parseOperand(OperandVector &Operands,
703
763
// so we treat any plain expression as an immediate.
704
764
SMLoc StartLoc = Parser.getTok ().getLoc ();
705
765
unsigned Base, Index;
766
+ bool IsVector;
706
767
const MCExpr *Expr, *Length;
707
- if (parseAddress (Base, Expr, Index, Length, SystemZMC::GR64Regs, ADDR64Reg))
768
+ if (parseAddress (Base, Expr, Index, IsVector, Length, SystemZMC::GR64Regs,
769
+ ADDR64Reg))
708
770
return true ;
709
771
710
772
SMLoc EndLoc =
0 commit comments