macromem.cc (7646:a444dbee8c07) macromem.cc (7853:69aae4379062)
1/*
2 * Copyright (c) 2010 ARM Limited
3 * All rights reserved
4 *
5 * The license below extends only to copyright in the software and shall
6 * not be construed as granting a license to any other intellectual
7 * property including but not limited to intellectual property relating
8 * to a hardware implementation of the functionality of the software

--- 28 unchanged lines hidden (view full) ---

37 * (INCLUDING NEGLIGENCE OR OTHERWISE) ARISING IN ANY WAY OUT OF THE USE
38 * OF THIS SOFTWARE, EVEN IF ADVISED OF THE POSSIBILITY OF SUCH DAMAGE.
39 *
40 * Authors: Stephen Hines
41 */
42
43#include "arch/arm/insts/macromem.hh"
44#include "arch/arm/decoder.hh"
1/*
2 * Copyright (c) 2010 ARM Limited
3 * All rights reserved
4 *
5 * The license below extends only to copyright in the software and shall
6 * not be construed as granting a license to any other intellectual
7 * property including but not limited to intellectual property relating
8 * to a hardware implementation of the functionality of the software

--- 28 unchanged lines hidden (view full) ---

37 * (INCLUDING NEGLIGENCE OR OTHERWISE) ARISING IN ANY WAY OUT OF THE USE
38 * OF THIS SOFTWARE, EVEN IF ADVISED OF THE POSSIBILITY OF SUCH DAMAGE.
39 *
40 * Authors: Stephen Hines
41 */
42
43#include "arch/arm/insts/macromem.hh"
44#include "arch/arm/decoder.hh"
45#include <sstream>
45
46
47using namespace std;
46using namespace ArmISAInst;
47
48namespace ArmISA
49{
50
51MacroMemOp::MacroMemOp(const char *mnem, ExtMachInst machInst,
52 OpClass __opClass, IntRegIndex rn,
53 bool index, bool up, bool user, bool writeback,

--- 121 unchanged lines hidden (view full) ---

175 microOps[uopIdx++] = newNeonMemInst<MicroLdrNeon16Uop>(
176 size, machInst, rMid, rn, 0, align);
177 break;
178 case 1:
179 microOps[uopIdx++] = newNeonMemInst<MicroLdrNeon8Uop>(
180 size, machInst, rMid, rn, 0, align);
181 break;
182 default:
48using namespace ArmISAInst;
49
50namespace ArmISA
51{
52
53MacroMemOp::MacroMemOp(const char *mnem, ExtMachInst machInst,
54 OpClass __opClass, IntRegIndex rn,
55 bool index, bool up, bool user, bool writeback,

--- 121 unchanged lines hidden (view full) ---

177 microOps[uopIdx++] = newNeonMemInst<MicroLdrNeon16Uop>(
178 size, machInst, rMid, rn, 0, align);
179 break;
180 case 1:
181 microOps[uopIdx++] = newNeonMemInst<MicroLdrNeon8Uop>(
182 size, machInst, rMid, rn, 0, align);
183 break;
184 default:
183 panic("Unrecognized number of registers %d.\n", regs);
185 // Unknown number of registers
186 microOps[uopIdx++] = new Unknown(machInst);
184 }
185 if (wb) {
186 if (rm != 15 && rm != 13) {
187 microOps[uopIdx++] =
188 new MicroAddUop(machInst, rn, rn, rm, 0, ArmISA::LSL);
189 } else {
190 microOps[uopIdx++] =
191 new MicroAddiUop(machInst, rn, rn, regs * 8);

--- 19 unchanged lines hidden (view full) ---

211 microOps[uopIdx++] = newNeonMixInst<MicroDeintNeon4Uop>(
212 size, machInst, vd * 2 + 2, rMid + 4, inc * 2);
213 } else {
214 microOps[uopIdx++] = newNeonMixInst<MicroDeintNeon4Uop>(
215 size, machInst, vd * 2, rMid, inc * 2);
216 }
217 break;
218 default:
187 }
188 if (wb) {
189 if (rm != 15 && rm != 13) {
190 microOps[uopIdx++] =
191 new MicroAddUop(machInst, rn, rn, rm, 0, ArmISA::LSL);
192 } else {
193 microOps[uopIdx++] =
194 new MicroAddiUop(machInst, rn, rn, regs * 8);

--- 19 unchanged lines hidden (view full) ---

214 microOps[uopIdx++] = newNeonMixInst<MicroDeintNeon4Uop>(
215 size, machInst, vd * 2 + 2, rMid + 4, inc * 2);
216 } else {
217 microOps[uopIdx++] = newNeonMixInst<MicroDeintNeon4Uop>(
218 size, machInst, vd * 2, rMid, inc * 2);
219 }
220 break;
221 default:
219 panic("Bad number of elements to deinterleave %d.\n", elems);
222 // Bad number of elements to deinterleave
223 microOps[uopIdx++] = new Unknown(machInst);
220 }
221 }
222 assert(uopIdx == numMicroops);
223
224 for (unsigned i = 0; i < numMicroops - 1; i++) {
225 MicroOp * uopPtr = dynamic_cast<MicroOp *>(microOps[i].get());
226 assert(uopPtr);
227 uopPtr->setDelayedCommit();

--- 82 unchanged lines hidden (view full) ---

310 microOps[uopIdx++] = new MicroLdrNeon12Uop<uint32_t>(
311 machInst, ufp0, rn, 0, align);
312 break;
313 case 16:
314 microOps[uopIdx++] = new MicroLdrNeon16Uop<uint32_t>(
315 machInst, ufp0, rn, 0, align);
316 break;
317 default:
224 }
225 }
226 assert(uopIdx == numMicroops);
227
228 for (unsigned i = 0; i < numMicroops - 1; i++) {
229 MicroOp * uopPtr = dynamic_cast<MicroOp *>(microOps[i].get());
230 assert(uopPtr);
231 uopPtr->setDelayedCommit();

--- 82 unchanged lines hidden (view full) ---

314 microOps[uopIdx++] = new MicroLdrNeon12Uop<uint32_t>(
315 machInst, ufp0, rn, 0, align);
316 break;
317 case 16:
318 microOps[uopIdx++] = new MicroLdrNeon16Uop<uint32_t>(
319 machInst, ufp0, rn, 0, align);
320 break;
321 default:
318 panic("Unrecognized load size %d.\n", regs);
322 // Unrecognized load size
323 microOps[uopIdx++] = new Unknown(machInst);
319 }
320 if (wb) {
321 if (rm != 15 && rm != 13) {
322 microOps[uopIdx++] =
323 new MicroAddUop(machInst, rn, rn, rm, 0, ArmISA::LSL);
324 } else {
325 microOps[uopIdx++] =
326 new MicroAddiUop(machInst, rn, rn, loadSize);

--- 26 unchanged lines hidden (view full) ---

353 microOps[uopIdx++] = new MicroUnpackAllNeon4to8Uop<uint32_t>(
354 machInst, vd * 2, ufp0, inc * 2);
355 } else {
356 microOps[uopIdx++] = new MicroUnpackNeon4to8Uop<uint32_t>(
357 machInst, vd * 2, ufp0, inc * 2, lane);
358 }
359 break;
360 default:
324 }
325 if (wb) {
326 if (rm != 15 && rm != 13) {
327 microOps[uopIdx++] =
328 new MicroAddUop(machInst, rn, rn, rm, 0, ArmISA::LSL);
329 } else {
330 microOps[uopIdx++] =
331 new MicroAddiUop(machInst, rn, rn, loadSize);

--- 26 unchanged lines hidden (view full) ---

358 microOps[uopIdx++] = new MicroUnpackAllNeon4to8Uop<uint32_t>(
359 machInst, vd * 2, ufp0, inc * 2);
360 } else {
361 microOps[uopIdx++] = new MicroUnpackNeon4to8Uop<uint32_t>(
362 machInst, vd * 2, ufp0, inc * 2, lane);
363 }
364 break;
365 default:
361 panic("Bad size %d.\n", size);
366 // Bad size
367 microOps[uopIdx++] = new Unknown(machInst);
362 break;
363 }
364 break;
365 case 3:
366 assert(regs == 3);
367 switch (size) {
368 case 0:
369 if (all) {

--- 18 unchanged lines hidden (view full) ---

388 microOps[uopIdx++] = new MicroUnpackAllNeon4to6Uop<uint32_t>(
389 machInst, vd * 2, ufp0, inc * 2);
390 } else {
391 microOps[uopIdx++] = new MicroUnpackNeon4to6Uop<uint32_t>(
392 machInst, vd * 2, ufp0, inc * 2, lane);
393 }
394 break;
395 default:
368 break;
369 }
370 break;
371 case 3:
372 assert(regs == 3);
373 switch (size) {
374 case 0:
375 if (all) {

--- 18 unchanged lines hidden (view full) ---

394 microOps[uopIdx++] = new MicroUnpackAllNeon4to6Uop<uint32_t>(
395 machInst, vd * 2, ufp0, inc * 2);
396 } else {
397 microOps[uopIdx++] = new MicroUnpackNeon4to6Uop<uint32_t>(
398 machInst, vd * 2, ufp0, inc * 2, lane);
399 }
400 break;
401 default:
396 panic("Bad size %d.\n", size);
402 // Bad size
403 microOps[uopIdx++] = new Unknown(machInst);
397 break;
398 }
399 break;
400 case 2:
401 assert(regs == 2);
402 assert(loadRegs <= 2);
403 switch (size) {
404 case 0:

--- 19 unchanged lines hidden (view full) ---

424 microOps[uopIdx++] = new MicroUnpackAllNeon2to4Uop<uint32_t>(
425 machInst, vd * 2, ufp0, inc * 2);
426 } else {
427 microOps[uopIdx++] = new MicroUnpackNeon2to4Uop<uint32_t>(
428 machInst, vd * 2, ufp0, inc * 2, lane);
429 }
430 break;
431 default:
404 break;
405 }
406 break;
407 case 2:
408 assert(regs == 2);
409 assert(loadRegs <= 2);
410 switch (size) {
411 case 0:

--- 19 unchanged lines hidden (view full) ---

431 microOps[uopIdx++] = new MicroUnpackAllNeon2to4Uop<uint32_t>(
432 machInst, vd * 2, ufp0, inc * 2);
433 } else {
434 microOps[uopIdx++] = new MicroUnpackNeon2to4Uop<uint32_t>(
435 machInst, vd * 2, ufp0, inc * 2, lane);
436 }
437 break;
438 default:
432 panic("Bad size %d.\n", size);
439 // Bad size
440 microOps[uopIdx++] = new Unknown(machInst);
433 break;
434 }
435 break;
436 case 1:
437 assert(regs == 1 || (all && regs == 2));
438 assert(loadRegs <= 2);
439 for (unsigned offset = 0; offset < regs; offset++) {
440 switch (size) {

--- 26 unchanged lines hidden (view full) ---

467 machInst, (vd + offset) * 2, ufp0, inc * 2);
468 } else {
469 microOps[uopIdx++] =
470 new MicroUnpackNeon2to2Uop<uint32_t>(
471 machInst, (vd + offset) * 2, ufp0, inc * 2, lane);
472 }
473 break;
474 default:
441 break;
442 }
443 break;
444 case 1:
445 assert(regs == 1 || (all && regs == 2));
446 assert(loadRegs <= 2);
447 for (unsigned offset = 0; offset < regs; offset++) {
448 switch (size) {

--- 26 unchanged lines hidden (view full) ---

475 machInst, (vd + offset) * 2, ufp0, inc * 2);
476 } else {
477 microOps[uopIdx++] =
478 new MicroUnpackNeon2to2Uop<uint32_t>(
479 machInst, (vd + offset) * 2, ufp0, inc * 2, lane);
480 }
481 break;
482 default:
475 panic("Bad size %d.\n", size);
483 // Bad size
484 microOps[uopIdx++] = new Unknown(machInst);
476 break;
477 }
478 }
479 break;
480 default:
485 break;
486 }
487 }
488 break;
489 default:
481 panic("Bad number of elements to unpack %d.\n", elems);
490 // Bad number of elements to unpack
491 microOps[uopIdx++] = new Unknown(machInst);
482 }
483 assert(uopIdx == numMicroops);
484
485 for (unsigned i = 0; i < numMicroops - 1; i++) {
486 MicroOp * uopPtr = dynamic_cast<MicroOp *>(microOps[i].get());
487 assert(uopPtr);
488 uopPtr->setDelayedCommit();
489 }

--- 41 unchanged lines hidden (view full) ---

531 microOps[uopIdx++] = newNeonMixInst<MicroInterNeon4Uop>(
532 size, machInst, rMid + 4, vd * 2 + 2, inc * 2);
533 } else {
534 microOps[uopIdx++] = newNeonMixInst<MicroInterNeon4Uop>(
535 size, machInst, rMid, vd * 2, inc * 2);
536 }
537 break;
538 default:
492 }
493 assert(uopIdx == numMicroops);
494
495 for (unsigned i = 0; i < numMicroops - 1; i++) {
496 MicroOp * uopPtr = dynamic_cast<MicroOp *>(microOps[i].get());
497 assert(uopPtr);
498 uopPtr->setDelayedCommit();
499 }

--- 41 unchanged lines hidden (view full) ---

541 microOps[uopIdx++] = newNeonMixInst<MicroInterNeon4Uop>(
542 size, machInst, rMid + 4, vd * 2 + 2, inc * 2);
543 } else {
544 microOps[uopIdx++] = newNeonMixInst<MicroInterNeon4Uop>(
545 size, machInst, rMid, vd * 2, inc * 2);
546 }
547 break;
548 default:
539 panic("Bad number of elements to interleave %d.\n", elems);
549 // Bad number of elements to interleave
550 microOps[uopIdx++] = new Unknown(machInst);
540 }
541 }
542 switch (regs) {
543 case 4:
544 microOps[uopIdx++] = newNeonMemInst<MicroStrNeon16Uop>(
545 size, machInst, rMid, rn, 0, align);
546 microOps[uopIdx++] = newNeonMemInst<MicroStrNeon16Uop>(
547 size, machInst, rMid + 4, rn, 16, noAlign);

--- 8 unchanged lines hidden (view full) ---

556 microOps[uopIdx++] = newNeonMemInst<MicroStrNeon16Uop>(
557 size, machInst, rMid, rn, 0, align);
558 break;
559 case 1:
560 microOps[uopIdx++] = newNeonMemInst<MicroStrNeon8Uop>(
561 size, machInst, rMid, rn, 0, align);
562 break;
563 default:
551 }
552 }
553 switch (regs) {
554 case 4:
555 microOps[uopIdx++] = newNeonMemInst<MicroStrNeon16Uop>(
556 size, machInst, rMid, rn, 0, align);
557 microOps[uopIdx++] = newNeonMemInst<MicroStrNeon16Uop>(
558 size, machInst, rMid + 4, rn, 16, noAlign);

--- 8 unchanged lines hidden (view full) ---

567 microOps[uopIdx++] = newNeonMemInst<MicroStrNeon16Uop>(
568 size, machInst, rMid, rn, 0, align);
569 break;
570 case 1:
571 microOps[uopIdx++] = newNeonMemInst<MicroStrNeon8Uop>(
572 size, machInst, rMid, rn, 0, align);
573 break;
574 default:
564 panic("Unrecognized number of registers %d.\n", regs);
575 // Unknown number of registers
576 microOps[uopIdx++] = new Unknown(machInst);
565 }
566 if (wb) {
567 if (rm != 15 && rm != 13) {
568 microOps[uopIdx++] =
569 new MicroAddUop(machInst, rn, rn, rm, 0, ArmISA::LSL);
570 } else {
571 microOps[uopIdx++] =
572 new MicroAddiUop(machInst, rn, rn, regs * 8);

--- 49 unchanged lines hidden (view full) ---

622 microOps[uopIdx++] = new MicroPackNeon8to2Uop<uint16_t>(
623 machInst, ufp0, vd * 2, inc * 2, lane);
624 break;
625 case 2:
626 microOps[uopIdx++] = new MicroPackNeon8to4Uop<uint32_t>(
627 machInst, ufp0, vd * 2, inc * 2, lane);
628 break;
629 default:
577 }
578 if (wb) {
579 if (rm != 15 && rm != 13) {
580 microOps[uopIdx++] =
581 new MicroAddUop(machInst, rn, rn, rm, 0, ArmISA::LSL);
582 } else {
583 microOps[uopIdx++] =
584 new MicroAddiUop(machInst, rn, rn, regs * 8);

--- 49 unchanged lines hidden (view full) ---

634 microOps[uopIdx++] = new MicroPackNeon8to2Uop<uint16_t>(
635 machInst, ufp0, vd * 2, inc * 2, lane);
636 break;
637 case 2:
638 microOps[uopIdx++] = new MicroPackNeon8to4Uop<uint32_t>(
639 machInst, ufp0, vd * 2, inc * 2, lane);
640 break;
641 default:
630 panic("Bad size %d.\n", size);
642 // Bad size
643 microOps[uopIdx++] = new Unknown(machInst);
631 break;
632 }
633 break;
634 case 3:
635 assert(regs == 3);
636 switch (size) {
637 case 0:
638 microOps[uopIdx++] = new MicroPackNeon6to2Uop<uint8_t>(
639 machInst, ufp0, vd * 2, inc * 2, lane);
640 break;
641 case 1:
642 microOps[uopIdx++] = new MicroPackNeon6to2Uop<uint16_t>(
643 machInst, ufp0, vd * 2, inc * 2, lane);
644 break;
645 case 2:
646 microOps[uopIdx++] = new MicroPackNeon6to4Uop<uint32_t>(
647 machInst, ufp0, vd * 2, inc * 2, lane);
648 break;
649 default:
644 break;
645 }
646 break;
647 case 3:
648 assert(regs == 3);
649 switch (size) {
650 case 0:
651 microOps[uopIdx++] = new MicroPackNeon6to2Uop<uint8_t>(
652 machInst, ufp0, vd * 2, inc * 2, lane);
653 break;
654 case 1:
655 microOps[uopIdx++] = new MicroPackNeon6to2Uop<uint16_t>(
656 machInst, ufp0, vd * 2, inc * 2, lane);
657 break;
658 case 2:
659 microOps[uopIdx++] = new MicroPackNeon6to4Uop<uint32_t>(
660 machInst, ufp0, vd * 2, inc * 2, lane);
661 break;
662 default:
650 panic("Bad size %d.\n", size);
663 // Bad size
664 microOps[uopIdx++] = new Unknown(machInst);
651 break;
652 }
653 break;
654 case 2:
655 assert(regs == 2);
656 assert(storeRegs <= 2);
657 switch (size) {
658 case 0:

--- 4 unchanged lines hidden (view full) ---

663 microOps[uopIdx++] = new MicroPackNeon4to2Uop<uint16_t>(
664 machInst, ufp0, vd * 2, inc * 2, lane);
665 break;
666 case 2:
667 microOps[uopIdx++] = new MicroPackNeon4to2Uop<uint32_t>(
668 machInst, ufp0, vd * 2, inc * 2, lane);
669 break;
670 default:
665 break;
666 }
667 break;
668 case 2:
669 assert(regs == 2);
670 assert(storeRegs <= 2);
671 switch (size) {
672 case 0:

--- 4 unchanged lines hidden (view full) ---

677 microOps[uopIdx++] = new MicroPackNeon4to2Uop<uint16_t>(
678 machInst, ufp0, vd * 2, inc * 2, lane);
679 break;
680 case 2:
681 microOps[uopIdx++] = new MicroPackNeon4to2Uop<uint32_t>(
682 machInst, ufp0, vd * 2, inc * 2, lane);
683 break;
684 default:
671 panic("Bad size %d.\n", size);
685 // Bad size
686 microOps[uopIdx++] = new Unknown(machInst);
672 break;
673 }
674 break;
675 case 1:
676 assert(regs == 1 || (all && regs == 2));
677 assert(storeRegs <= 2);
678 for (unsigned offset = 0; offset < regs; offset++) {
679 switch (size) {

--- 5 unchanged lines hidden (view full) ---

685 microOps[uopIdx++] = new MicroPackNeon2to2Uop<uint16_t>(
686 machInst, ufp0, (vd + offset) * 2, inc * 2, lane);
687 break;
688 case 2:
689 microOps[uopIdx++] = new MicroPackNeon2to2Uop<uint32_t>(
690 machInst, ufp0, (vd + offset) * 2, inc * 2, lane);
691 break;
692 default:
687 break;
688 }
689 break;
690 case 1:
691 assert(regs == 1 || (all && regs == 2));
692 assert(storeRegs <= 2);
693 for (unsigned offset = 0; offset < regs; offset++) {
694 switch (size) {

--- 5 unchanged lines hidden (view full) ---

700 microOps[uopIdx++] = new MicroPackNeon2to2Uop<uint16_t>(
701 machInst, ufp0, (vd + offset) * 2, inc * 2, lane);
702 break;
703 case 2:
704 microOps[uopIdx++] = new MicroPackNeon2to2Uop<uint32_t>(
705 machInst, ufp0, (vd + offset) * 2, inc * 2, lane);
706 break;
707 default:
693 panic("Bad size %d.\n", size);
708 // Bad size
709 microOps[uopIdx++] = new Unknown(machInst);
694 break;
695 }
696 }
697 break;
698 default:
710 break;
711 }
712 }
713 break;
714 default:
699 panic("Bad number of elements to pack %d.\n", elems);
715 // Bad number of elements to unpack
716 microOps[uopIdx++] = new Unknown(machInst);
700 }
701 switch (storeSize) {
702 case 1:
703 microOps[uopIdx++] = new MicroStrNeon1Uop<uint8_t>(
704 machInst, ufp0, rn, 0, align);
705 break;
706 case 2:
707 if (eBytes == 2) {

--- 44 unchanged lines hidden (view full) ---

752 microOps[uopIdx++] = new MicroStrNeon12Uop<uint32_t>(
753 machInst, ufp0, rn, 0, align);
754 break;
755 case 16:
756 microOps[uopIdx++] = new MicroStrNeon16Uop<uint32_t>(
757 machInst, ufp0, rn, 0, align);
758 break;
759 default:
717 }
718 switch (storeSize) {
719 case 1:
720 microOps[uopIdx++] = new MicroStrNeon1Uop<uint8_t>(
721 machInst, ufp0, rn, 0, align);
722 break;
723 case 2:
724 if (eBytes == 2) {

--- 44 unchanged lines hidden (view full) ---

769 microOps[uopIdx++] = new MicroStrNeon12Uop<uint32_t>(
770 machInst, ufp0, rn, 0, align);
771 break;
772 case 16:
773 microOps[uopIdx++] = new MicroStrNeon16Uop<uint32_t>(
774 machInst, ufp0, rn, 0, align);
775 break;
776 default:
760 panic("Unrecognized store size %d.\n", regs);
777 // Bad store size
778 microOps[uopIdx++] = new Unknown(machInst);
761 }
762 if (wb) {
763 if (rm != 15 && rm != 13) {
764 microOps[uopIdx++] =
765 new MicroAddUop(machInst, rn, rn, rm, 0, ArmISA::LSL);
766 } else {
767 microOps[uopIdx++] =
768 new MicroAddiUop(machInst, rn, rn, storeSize);

--- 150 unchanged lines hidden ---
779 }
780 if (wb) {
781 if (rm != 15 && rm != 13) {
782 microOps[uopIdx++] =
783 new MicroAddUop(machInst, rn, rn, rm, 0, ArmISA::LSL);
784 } else {
785 microOps[uopIdx++] =
786 new MicroAddiUop(machInst, rn, rn, storeSize);

--- 150 unchanged lines hidden ---