-
Notifications
You must be signed in to change notification settings - Fork 0
/
ArmControlPath.vhd
2772 lines (2575 loc) · 120 KB
/
ArmControlPath.vhd
1
2
3
4
5
6
7
8
9
10
11
12
13
14
15
16
17
18
19
20
21
22
23
24
25
26
27
28
29
30
31
32
33
34
35
36
37
38
39
40
41
42
43
44
45
46
47
48
49
50
51
52
53
54
55
56
57
58
59
60
61
62
63
64
65
66
67
68
69
70
71
72
73
74
75
76
77
78
79
80
81
82
83
84
85
86
87
88
89
90
91
92
93
94
95
96
97
98
99
100
101
102
103
104
105
106
107
108
109
110
111
112
113
114
115
116
117
118
119
120
121
122
123
124
125
126
127
128
129
130
131
132
133
134
135
136
137
138
139
140
141
142
143
144
145
146
147
148
149
150
151
152
153
154
155
156
157
158
159
160
161
162
163
164
165
166
167
168
169
170
171
172
173
174
175
176
177
178
179
180
181
182
183
184
185
186
187
188
189
190
191
192
193
194
195
196
197
198
199
200
201
202
203
204
205
206
207
208
209
210
211
212
213
214
215
216
217
218
219
220
221
222
223
224
225
226
227
228
229
230
231
232
233
234
235
236
237
238
239
240
241
242
243
244
245
246
247
248
249
250
251
252
253
254
255
256
257
258
259
260
261
262
263
264
265
266
267
268
269
270
271
272
273
274
275
276
277
278
279
280
281
282
283
284
285
286
287
288
289
290
291
292
293
294
295
296
297
298
299
300
301
302
303
304
305
306
307
308
309
310
311
312
313
314
315
316
317
318
319
320
321
322
323
324
325
326
327
328
329
330
331
332
333
334
335
336
337
338
339
340
341
342
343
344
345
346
347
348
349
350
351
352
353
354
355
356
357
358
359
360
361
362
363
364
365
366
367
368
369
370
371
372
373
374
375
376
377
378
379
380
381
382
383
384
385
386
387
388
389
390
391
392
393
394
395
396
397
398
399
400
401
402
403
404
405
406
407
408
409
410
411
412
413
414
415
416
417
418
419
420
421
422
423
424
425
426
427
428
429
430
431
432
433
434
435
436
437
438
439
440
441
442
443
444
445
446
447
448
449
450
451
452
453
454
455
456
457
458
459
460
461
462
463
464
465
466
467
468
469
470
471
472
473
474
475
476
477
478
479
480
481
482
483
484
485
486
487
488
489
490
491
492
493
494
495
496
497
498
499
500
501
502
503
504
505
506
507
508
509
510
511
512
513
514
515
516
517
518
519
520
521
522
523
524
525
526
527
528
529
530
531
532
533
534
535
536
537
538
539
540
541
542
543
544
545
546
547
548
549
550
551
552
553
554
555
556
557
558
559
560
561
562
563
564
565
566
567
568
569
570
571
572
573
574
575
576
577
578
579
580
581
582
583
584
585
586
587
588
589
590
591
592
593
594
595
596
597
598
599
600
601
602
603
604
605
606
607
608
609
610
611
612
613
614
615
616
617
618
619
620
621
622
623
624
625
626
627
628
629
630
631
632
633
634
635
636
637
638
639
640
641
642
643
644
645
646
647
648
649
650
651
652
653
654
655
656
657
658
659
660
661
662
663
664
665
666
667
668
669
670
671
672
673
674
675
676
677
678
679
680
681
682
683
684
685
686
687
688
689
690
691
692
693
694
695
696
697
698
699
700
701
702
703
704
705
706
707
708
709
710
711
712
713
714
715
716
717
718
719
720
721
722
723
724
725
726
727
728
729
730
731
732
733
734
735
736
737
738
739
740
741
742
743
744
745
746
747
748
749
750
751
752
753
754
755
756
757
758
759
760
761
762
763
764
765
766
767
768
769
770
771
772
773
774
775
776
777
778
779
780
781
782
783
784
785
786
787
788
789
790
791
792
793
794
795
796
797
798
799
800
801
802
803
804
805
806
807
808
809
810
811
812
813
814
815
816
817
818
819
820
821
822
823
824
825
826
827
828
829
830
831
832
833
834
835
836
837
838
839
840
841
842
843
844
845
846
847
848
849
850
851
852
853
854
855
856
857
858
859
860
861
862
863
864
865
866
867
868
869
870
871
872
873
874
875
876
877
878
879
880
881
882
883
884
885
886
887
888
889
890
891
892
893
894
895
896
897
898
899
900
901
902
903
904
905
906
907
908
909
910
911
912
913
914
915
916
917
918
919
920
921
922
923
924
925
926
927
928
929
930
931
932
933
934
935
936
937
938
939
940
941
942
943
944
945
946
947
948
949
950
951
952
953
954
955
956
957
958
959
960
961
962
963
964
965
966
967
968
969
970
971
972
973
974
975
976
977
978
979
980
981
982
983
984
985
986
987
988
989
990
991
992
993
994
995
996
997
998
999
1000
--------------------------------------------------------------------------------
-- Kontrollpfad des Arm Kerns
--------------------------------------------------------------------------------
-- Datum: 05.07.10
-- Version: 0.95
--------------------------------------------------------------------------------
library ieee;
use ieee.std_logic_1164.all;
use ieee.numeric_std.all;
library work;
use work.ArmTypes.all;
use work.ArmGlobalProbes.all;
use work.ArmConfiguration.all;
use work.ArmRegAddressTranslation.all;
--------------------------------------------------------------------------------
-- Simulationsmodelle fuer fehlerhaft implementierte Module
--------------------------------------------------------------------------------
--library ARM_SIM_LIB;
-- use ARM_SIM_LIB.ArmRegisterBitAdder;
-- use ARM_SIM_LIB.ArmLdmStmNextAddress;
-- use ARM_SIM_LIB.ArmCoarseInstructionDecoder;
-- use ARM_SIM_LIB.ArmBypassCtrl;
-- use ARM_SIM_LIB.ArmArithInstructionCtrl;
--------------------------------------------------------------------------------
entity ArmControlPath is
port(
CPA_CLK : in std_logic;
CPA_RST : in std_logic;
CPA_IRQ : in std_logic;
CPA_FIQ : in std_logic;
CPA_WAIT : in std_logic;
CPA_IF_ID : in std_logic_vector(31 downto 0);
CPA_IF_IABORT : in std_logic;
CPA_IF_IEN : out std_logic;
CPA_IF_IBE : in std_logic;
CPA_IF_FETCH : out std_logic;
CPA_IF_IMODE : out std_logic_vector(4 downto 0);
CPA_IF_IAR_INC : out std_logic;
CPA_IF_IAR_UPDATE_HB : out std_logic;
CPA_MEM_DnRW : out std_logic;
CPA_MEM_DEN : out std_logic;
CPA_MEM_DABORT : in std_logic;
CPA_MEM_DBE : in std_logic;
CPA_MEM_DMAS : out std_logic_vector(1 downto 0);
CPA_MEM_DMODE : out std_logic_vector(4 downto 0);
CPA_EX_CPSR : in std_logic_vector(31 downto 0);
CPA_DPA_ENABLE : out std_logic;
CPA_ID_IAR_REVOKE : out std_logic;
CPA_ID_IAR_HISTORY_ID : out std_logic_vector(INSTRUCTION_ID_WIDTH-1 downto 0);
CPA_ID_REF_R_PORTS_ADDR : out std_logic_vector(14 downto 0);
CPA_ID_IMMEDIATE : out std_logic_vector(31 downto 0);
CPA_ID_SHIFT_AMOUNT : out std_logic_vector(5 downto 0);
CPA_ID_OPB_MUX_CTRL : out std_logic;
CPA_ID_SHIFT_MUX_CTRL : out std_logic;
CPA_ID_CHS : in std_logic_vector(1 downto 0);
CPA_EX_OPA_PSR_MUX_CTRL : out std_logic;
CPA_EX_PSR_MUX_CTRL : out std_logic;
CPA_EX_OPX_MUX_CTRLS : out std_logic_vector(5 downto 0);
CPA_EX_CC_MUX_CTRL : out std_logic_vector(1 downto 0);
CPA_EX_SHIFT_MUX_CTRL : out std_logic_vector(1 downto 0);
CPA_EX_OPB_ALU_MUX_CTRL : out std_logic;
CPA_EX_PSR_CC_MUX_CTRL : out std_logic;
CPA_EX_DAR_MUX_CTRL : out std_logic;
CPA_EX_SHIFT_TYPE : out std_logic_vector(1 downto 0);
CPA_EX_SHIFT_RRX : out std_logic;
CPA_EX_ALU_CTRL : out std_logic_vector(3 downto 0);
CPA_EX_DRP_DMAS : out std_logic_vector(1 downto 0);
CPA_EX_DAR_EN : out std_logic;
CPA_EX_DAR_INC : out std_logic;
CPA_EX_PASS : out std_logic;
CPA_MEM_DATA_REG_EN : out std_logic;
CPA_MEM_RES_REG_EN : out std_logic;
CPA_MEM_CC_REG_EN : out std_logic;
CPA_MEM_BASE_MUX_CTRL : out std_logic;
CPA_MEM_BASE_REG_EN : out std_logic;
CPA_MEM_TRUNCATE_ADDR : out std_logic;
CPA_MEM_WMP_SIGNED : out std_logic;
CPA_MEM_CC_MUX_CTRL : out std_logic;
CPA_MEM_PASS : out std_logic;
CPA_WB_REF_W_PORT_A_EN : out std_logic;
CPA_WB_REF_W_PORT_B_EN : out std_logic;
CPA_WB_REF_W_PORTS_ADDR : out std_logic_vector(9 downto 0);
CPA_WB_LOAD_REG_EN : out std_logic;
CPA_WB_RES_REG_EN : out std_logic;
CPA_WB_CC_REG_EN : out std_logic;
CPA_WB_PSR_EN : out std_logic;
CPA_WB_PSR_CTRL : out PSR_CTRL_TYPE;
CPA_WB_IAR_MUX_CTRL : out std_logic;
CPA_WB_FBRANCH_MUX_CTRL : out std_logic;
CPA_WB_IAR_LOAD : out std_logic
);
end ArmControlPath;
architecture behave of ArmControlPath is
-- Komponentendeklaration
component ArmLdmStmNextAddress
port(
SYS_RST : in std_logic;
SYS_CLK : in std_logic;
LNA_LOAD_REGLIST : in std_logic;
LNA_HOLD_VALUE : in std_logic;
LNA_REGLIST : in std_logic_vector(15 downto 0);
LNA_ADDRESS : out std_logic_vector(3 downto 0);
LNA_CURRENT_REGLIST_REG : out std_logic_vector(15 downto 0)
);
end component ArmLdmStmNextAddress;
component ArmCoarseInstructionDecoder
port(
CID_INSTRUCTION : in std_logic_vector(31 downto 0);
CID_DECODED_VECTOR : out std_logic_vector(15 downto 0)
);
end component ArmCoarseInstructionDecoder;
component ArmCopDecoder
port(
ACD_INSTRUCTION_BITS : in std_logic_vector(8 downto 0);
ACD_INSTRUCTION_TYPE : out std_logic_vector(2 downto 0)
);
end component ArmCopDecoder;
component ArmConditionCheck
port(
CDC_CONDITION_FIELD : in std_logic_vector(3 downto 0);
CDC_CONDITION_CODE : in std_logic_vector(3 downto 0);
CDC_CONDITION_MET : out std_logic
);
end component ArmConditionCheck;
component ArmShiftRecoder
port(
SRC_OPERAND_2 : IN std_logic_vector(11 downto 5);
SRC_OPERAND_2_TYPE : IN std_logic_vector(1 downto 0);
SRC_SHIFT_AMOUNT : out std_logic_vector(5 downto 0);
SRC_SHIFT_TYPE : out std_logic_vector(1 downto 0);
SRC_SHIFT_RRX : out std_logic;
SRC_USE_OPC : out std_logic
);
end component ArmShiftRecoder;
component ArmRegisterBitAdder
port(
RBA_REGLIST : in std_logic_vector(15 downto 0);
RBA_NR_OF_REGS : out std_logic_vector(4 downto 0)
);
end component ArmRegisterBitAdder;
component ArmBypassCtrl
port(
--------------------------------------------------------------------------------
-- Sollten die Operanden in den Eingangsregistern gehalten werden, z.B.
-- fuer eine sinnvolle Loesung von Load-Use-Konflikten (besser als aktuell)
-- dann muessen die Steuersignale der EX-Eingangsregister ausgewertet
-- werden
--------------------------------------------------------------------------------
-- ABC_INST0_OPA_PSR_MUX_CTRL : in std_logic;
-- ABC_INST0_OPB_MUX_CTRL : in std_logic;
-- ABC_INST0_SHIFT_MUX_CTRL : in std_logic;
ABC_INST0_R_PORT_A_ADDR : in std_logic_vector(4 downto 0);
ABC_INST0_R_PORT_B_ADDR : in std_logic_vector(4 downto 0);
ABC_INST0_R_PORT_C_ADDR : in std_logic_vector(4 downto 0);
ABC_INST1_W_PORT_A_ADDR : in std_logic_vector(4 downto 0);
ABC_INST1_W_PORT_B_ADDR : in std_logic_vector(4 downto 0);
ABC_INST2_W_PORT_A_ADDR : in std_logic_vector(4 downto 0);
ABC_INST2_W_PORT_B_ADDR : in std_logic_vector(4 downto 0);
ABC_INST1_W_PORT_A_EN : in std_logic;
ABC_INST1_W_PORT_B_EN : in std_logic;
ABC_INST2_W_PORT_A_EN : in std_logic;
ABC_INST2_W_PORT_B_EN : in std_logic;
ABC_INST1_WB_PSR_EN : in std_logic;
ABC_INST1_WB_PSR_SET_CC : in std_logic;
ABC_INST2_WB_PSR_EN : in std_logic;
ABC_INST2_WB_PSR_SET_CC : in std_logic;
ABC_INST0_REGS_USED : in std_logic_vector(2 downto 0);
ABC_INST0_SHIFT_REG_USED : in std_logic;
ABC_INST0_OPA_BYPASS_MUX_CTRL : out std_logic_vector(1 downto 0);
ABC_INST0_OPB_BYPASS_MUX_CTRL : out std_logic_vector(1 downto 0);
ABC_INST0_OPC_BYPASS_MUX_CTRL : out std_logic_vector(1 downto 0);
ABC_INST0_SHIFT_BYPASS_MUX_CTRL : out std_logic_vector(1 downto 0);
ABC_INST0_CC_BYPASS_MUX_CTRL : out std_logic_vector(1 downto 0);
ABC_LOAD_USE_CONFLICT : out std_logic
);
end component ArmBypassCtrl;
component ArmArithInstructionCtrl
port(
AIC_DECODED_VECTOR : in std_logic_vector(15 downto 0);
AIC_INSTRUCTION : in std_logic_vector(31 downto 0);
AIC_IF_IAR_INC : out std_logic;
AIC_ID_R_PORT_A_ADDR : out std_logic_vector(3 downto 0);
AIC_ID_R_PORT_B_ADDR : out std_logic_vector(3 downto 0);
AIC_ID_R_PORT_C_ADDR : out std_logic_vector(3 downto 0);
AIC_ID_REGS_USED : out std_logic_vector(2 downto 0);
AIC_ID_IMMEDIATE : out std_logic_vector(31 downto 0);
AIC_ID_OPB_MUX_CTRL : out std_logic;
AIC_EX_ALU_CTRL : out std_logic_vector(3 downto 0);
AIC_MEM_RES_REG_EN : out std_logic;
AIC_MEM_CC_REG_EN : out std_logic;
AIC_WB_CC_REG_EN : out std_logic;
AIC_WB_W_PORT_A_ADDR : out std_logic_vector(3 downto 0);
AIC_WB_W_PORT_A_EN : out std_logic;
AIC_WB_RES_REG_EN : out std_logic;
AIC_WB_IAR_LOAD : out std_logic;
AIC_WB_PSR_EN : out std_logic;
AIC_WB_PSR_ER : out std_logic;
AIC_WB_PSR_SET_CC : out std_logic;
AIC_WB_IAR_MUX_CTRL : out std_logic;
AIC_DELAY : out std_logic_vector(1 downto 0);
AIC_ARM_NEXT_STATE : out ARM_STATE_TYPE
);
end component ArmArithInstructionCtrl;
--------------------------------------------------------------------------------
-- Urspruenglich konnten Signale fuer Exceptiontypen priorisiert
-- werden, die spezielle Art der Steuerung tut dies jedoch
-- fuer Data Abort, SWI und Undefined durch ihre Struktur bereits
-- selbststaendig. Die Entsprechenden Komponenten des Filters
-- sind daher auskommentiert
--------------------------------------------------------------------------------
-- COMPONENT ArmExceptionPrioritization
-- PORT(
-- EXP_FIQ_IN : in std_logic;
-- EXP_IRQ_IN : in std_logic;
-- EXP_PABORT_IN : in std_logic;
-- EXP_FIQ_OUT : out std_logic;
-- EXP_IRQ_OUT : out std_logic;
-- EXP_PABORT_OUT : out std_logic
-- );
-- END COMPONENT;
COMPONENT ArmDelayShiftRegister
generic(DSR_WIDTH : natural range 2 to 16 := 3);
PORT(
DSR_CLK : in std_logic;
DSR_RST : in std_logic;
DSR_WAIT : in std_logic;
DSR_SET : in std_logic;
DSR_OUT : out std_logic
);
end component ArmDelayShiftRegister;
-- Buffer zur Aufnahme der Registeradresse die auf die Basis
-- eines Speicherzugriffs verweist um diese bei einem DABORT
-- wiederherstellen zu koennen
component ArmRamBuffer
generic(
ARB_ADDR_WIDTH : natural range 1 to 4 := 3;
ARB_DATA_WIDTH : natural range 1 to 64 := 32
);
port(
ARB_CLK : in std_logic;
ARB_WRITE_EN : in std_logic;
ARB_ADDR : in std_logic_vector(ARB_ADDR_WIDTH-1 downto 0);
ARB_DATA_IN : in std_logic_vector(ARB_DATA_WIDTH-1 downto 0);
ARB_DATA_OUT : out std_logic_vector(ARB_DATA_WIDTH-1 downto 0)
);
end component ArmRamBuffer;
signal ID_REGS_USED : std_logic_vector(2 downto 0);
signal ID_MODE_MUX : MODE := USER;
signal IF_ARB_ADDR : std_logic_vector(INSTRUCTION_ID_WIDTH-1 downto 0) := (others => '0');
signal WB_ARB_DATA_OUT : std_logic_vector(4 downto 0) := (others => '0');
signal ID_BASE_REGADDRESS_MAPPED : std_logic_vector(4 downto 0) := (others => '0');
signal MEM_DABORT_FILTERED : std_logic := '0';
signal MEM_MEM_DEN : std_logic := '0';
signal ARM_STATE, ARM_NEXT_STATE : ARM_STATE_TYPE := STATE_FETCH;
signal IF_LDMSTM_MUX_CTRL : std_logic := '0';
signal IF_LDMSTM_MUX : std_logic_vector(15 downto 0) := (others => '0');
signal MAIN_DELAY, MAIN_DELAY_REG : natural range 0 to 3 := 0;
-- Steuersignale der FIQ/IRQ-Maskierung (registerbasiert)
SIGNAL ID_MASK_FIQ, ID_MASK_IRQ : std_logic := '0';
SIGNAL ID_FIQ_MASK, ID_IRQ_MASK : std_logic := '0';
-- weitere Exception-Steuersignale und Register
SIGNAL ID_INSTRUCTION_REG, ID_OLD_INSTRUCTION_REG : std_logic_vector(31 downto 0) := (others => '0');
signal ID_HOLD_OLD_INSTRUCTION_REG : std_logic := '0';
SIGNAL ID_IABORT_REG : std_logic := '0';
SIGNAL CID_DECODED_VECTOR : COARSE_DECODE_TYPE := CD_UNDEFINED;
-- IF_IAR_INC_REG wird aktuell nicht verwendet
SIGNAL IF_IAR_INC : std_logic := '0';
-- Interrupts werden erst registriert und dann verwendet um das Interruptsignal zu Beginn eines Taktes sicher zur Verfügung zu haben
-- Alle anderen externen Exceptionsignale sind ebenso registiert
SIGNAL ID_FIQ, ID_FIQ_REG, ID_IRQ, ID_IRQ_REG : std_logic := '0';
signal ID_DABORT_REG : std_logic := '0';
-- Steuersignale, die noch in der Decodestufe verwendet werden und neben
-- Ausgängen von ArmControlPath noch weitere Komponenten steuern
signal ID_REF_R_PORTS_ADDR : std_logic_vector(14 downto 0) := (others => '0');
-- signal ID_OPA_MUX_CTRL : std_logic := '0';
signal ID_OPB_MUX_CTRL : std_logic := '0';
signal ID_SHIFT_MUX_CTRL : std_logic := '0';
signal ID_LOAD_USE_CONFLICT : std_logic := '0';
-- Signal, durch das ein NOP in die Pipeline eingefuegt wird
-- signal ID_STOPP_DECODE : std_logic := '0';
signal ID_IMMEDIATE : std_logic_vector(31 downto 0) := (others => '0');
signal ID_DPA_ENABLE : std_logic := '0';
signal ID_SHIFT_AMOUNT : std_logic_vector(5 downto 0);
-- Pipelineregister der Speicherzugriffssteuerung
SIGNAL ID_MEM_DnRW, ID_MEM_DEN : std_logic := '0';
-- SIGNAL ID_MEM_DMAS : STD_LOGIC_VECTOR(1 downto 0);
SIGNAL EX_MEM_DnRW_REG, EX_MEM_DEN_REG, MEM_MEM_DnRW_REG, MEM_MEM_DEN_REG : std_logic;
-- SIGNAL EX_MEM_DMAS_REG, MEM_MEM_DMAS_REG : STD_LOGIC_VECTOR(1 downto 0) := (others => '0');
signal EX_OPX_MUX_CTRLS : EX_CTRL_SIG_6VEC_TYPE := (others => (others => '0'));
signal MEM_DMAS : MEM_CTRL_SIG_2VEC_TYPE := (others => DMAS_WORD);
-- Pipelineregister der Rückschreibadressen
signal WB_REF_W_PORTS_ADDR : WB_CTRL_SIG_10VEC_TYPE := (others => (others => '0'));
-- Pipelineregister der Rueckschreib-Enables
SIGNAL ID_REF_W_PORT_A_EN, ID_REF_W_PORT_B_EN : std_logic := '0';
SIGNAL EX_REF_W_PORT_A_EN_REG, EX_REF_W_PORT_B_EN_REG, MEM_REF_W_PORT_A_EN_REG, MEM_REF_W_PORT_B_EN_REG, WB_REF_W_PORT_A_EN_REG, WB_REF_W_PORT_B_EN_REG : STD_LOGIC := '0';
-- Pipelineregister für die Multiplexer der Executestufe
signal ID_EX_CC_MUX_CTRL,ID_EX_SHIFT_MUX_CTRL : std_logic_vector(1 downto 0) := "00";
signal EX_EX_SHIFT_MUX_CTRL_REG,EX_EX_CC_MUX_CTRL_REG : std_logic_vector(1 downto 0) := "00";
SIGNAL ID_EX_OPB_ALU_MUX_CTRL, ID_EX_PSR_CC_MUX_CTRL,
ID_EX_DAR_MUX_CTRL : std_logic := '0';
SIGNAL EX_EX_OPB_ALU_MUX_CTRL_REG, EX_EX_PSR_CC_MUX_CTRL_REG,
EX_EX_DAR_MUX_CTRL_REG : std_logic := '0';
signal EX_SHIFT_EX_CTRL : EX_SHIFT_EX_CTRL_TYPE := (others => (SH_LSL,'0'));
signal MEM_WMP_CTRL : MEM_CTRL_SIG_TYPE := (others => '0');
signal MEM_TRUNCATE_ADDR : MEM_CTRL_SIG_TYPE := (others => '0');
-- Pipelineregister für Steuersignale der verarbeitenden Komponenten der EX-STufe
-- SIGNAL ID_EX_SHIFT_TYPE, EX_EX_SHIFT_TYPE_REG : STD_LOGIC_VECTOR(1 downto 0) := "00";
-- SIGNAL ID_EX_SHIFT_RRX, EX_EX_SHIFT_RRX_REG : STD_LOGIC := '0';
SIGNAL ID_EX_ALU_CTRL, EX_EX_ALU_CTRL_REG : std_logic_vector(3 downto 0) := "0000";
-- Pipelineregister für die Steuersignale der MEM-Stufe
SIGNAL ID_MEM_DATA_REG_EN, EX_MEM_DATA_REG_EN_REG : std_logic := '0';
SIGNAL ID_MEM_RES_REG_EN, EX_MEM_RES_REG_EN_REG : std_logic := '0';
SIGNAL ID_MEM_CC_REG_EN, EX_MEM_CC_REG_EN_REG : std_logic := '0';
SIGNAL ID_MEM_DAR_EN, EX_MEM_DAR_EN_REG : std_logic := '0';
SIGNAL ID_MEM_DAR_INC, EX_MEM_DAR_INC_REG : std_logic := '0';
signal ID_MEM_BASE_REG_EN, EX_MEM_BASE_REG_EN_REG : std_logic := '0';
-- Pipelineregister für die Steuersignale der WB-Stufe
-- SIGNAL ID_WB_USER_REGS, EX_WB_USER_REGS_REG, MEM_WB_USER_REGS_REG, WB_WB_USER_REGS_REG : STD_LOGIC;
SIGNAL ID_WB_LOAD_REG_EN, EX_WB_LOAD_REG_EN_REG, MEM_WB_LOAD_REG_EN_REG : std_logic := '0';
SIGNAL ID_WB_RES_REG_EN, EX_WB_RES_REG_EN_REG, MEM_WB_RES_REG_EN_REG : std_logic := '0';
SIGNAL ID_WB_CC_REG_EN, EX_WB_CC_REG_EN_REG, MEM_WB_CC_REG_EN_REG : std_logic := '0';
SIGNAL ID_WB_PSR_EN, EX_WB_PSR_EN_REG, MEM_WB_PSR_EN_REG, WB_WB_PSR_EN_REG : std_logic := '0';
SIGNAL ID_WB_IAR_LOAD, EX_WB_IAR_LOAD_REG, MEM_WB_IAR_LOAD_REG, WB_WB_IAR_LOAD_REG : std_logic := '0';
SIGNAL ID_WB_IAR_MUX_CTRL, EX_WB_IAR_MUX_CTRL_REG, MEM_WB_IAR_MUX_CTRL_REG, WB_WB_IAR_MUX_CTRL_REG : std_logic := '0';
-- Vollstaendig priorisierte und maskierte Exceptionsignale
SIGNAL ID_FIQ_FILTERED : std_logic;
SIGNAL ID_IRQ_FILTERED, ID_PABORT_FILTERED : std_logic;
-- Neue Signale fuer die Verarbeitung von Coprozessorinstruktionen
signal ID_COP_INSTRUCTION_BITS : std_logic_vector(8 downto 0) := (others => '0');
signal ID_COP_INSTRUCTION_TYPE : COPROCESSOR_INSTRUCTION_TYPE;
-- Steuersignal und Pufferregister zum aktivieren des Instruktionsspeichers
-- Das Signal sollte aus Zeitgründen registriert sein.
SIGNAL IF_IEN, IF_IEN_REG : std_logic := '0';
-- Zweites Steuersignal zur Übernahme der gelesenen Instruktion in das Instruktionsregister
-- Sinnvollerweise sollte dieses Steuersignal nicht gepuffert sein und kann daher nicht
-- mit dem zum Aktivieren des Speicher identisch gewählt werden
SIGNAL IF_FETCH_INSTRUCTION : std_logic;
signal IF_UPDATE_HISTORY_BUFFERS : std_logic;
SIGNAL LNA_CURRENT_REGLIST_REG : std_logic_vector(15 downto 0) := (others => '0');
SIGNAL RBA_NR_OF_REGS : std_logic_vector(4 downto 0);
signal ID_FILTERED_EXCEPTIONS : std_logic_vector(2 downto 0);
-- SIGNAL SRC_SHIFT_AMOUNT : STD_LOGIC_VECTOR(5 downto 0);
-- SIGNAL SRC_SHIFT_TYPE : SHIFT_TYPE;
-- SIGNAL SRC_SHIFT_RRX : STD_LOGIC;
-- SIGNAL SRC_USE_OPC : STD_LOGIC;
signal SRC_SHIFT_CTRL : SHIFT_CTRL_TYPE;
SIGNAL SRC_OPERAND_2_TYPE : OPERAND_2_TYPE;
-- ID_CONDIGITION_FIELD entspricht den vier Bedingungsbits einer Instruktion
-- Für Einzyklenbefehle kann immer umittelbar das Bedingungsfeld auf das Signal gegeben werden, das dann mit der nächsten Taktflanke ein Bedingungsregister für die Executestufe setzt. Dort werden alle Schreib- und Speichersteuerleitungen für die Execute- und alle nachfolgenden Stufen invalidiert.
-- Bei mehrzyklenbefehlen entspricht ID_CONDITION_FIELD so lange dem Register EX_CONDITION_FIELD_REG (das seinen Wert also hält), bis der nächste Befehl dekodiert wird.
SIGNAL ID_CONDITION_FIELD, EX_CONDITION_FIELD_REG : std_logic_vector(3 downto 0) := "0000";
SIGNAL CDC_CONDITION_MET : std_logic := '0';
SIGNAL ID_LNA_LOAD_REGLIST, ID_LNA_HOLD_VALUE : std_logic := '0';
SIGNAL ID_LNA_ADDRESS : std_logic_vector(3 downto 0) := "0000";
-- Signale fuer den Einbau einer zusaetzlichen Komponente fuer die Reaktion auf Arithmetische Instruktionen, die Registeradressen
-- sind als Adressen vor der Abbildung auf 31 Register zu verstehen und daher nur 4 Bit breit
signal AIC_IF_IAR_INC : std_logic;
signal AIC_ID_R_PORT_A_ADDR : std_logic_vector(3 downto 0);
signal AIC_ID_R_PORT_B_ADDR : std_logic_vector(3 downto 0);
signal AIC_ID_R_PORT_C_ADDR : std_logic_vector(3 downto 0);
signal AIC_ID_IMMEDIATE : std_logic_vector(31 downto 0);
signal AIC_ID_REGS_USED : std_logic_vector(2 downto 0);
signal AIC_ID_OPB_MUX_CTRL : std_logic;
signal AIC_EX_ALU_CTRL : std_logic_vector(3 downto 0);
signal AIC_WB_W_PORT_A_ADDR : std_logic_vector(3 downto 0);
signal AIC_WB_W_PORT_A_EN : std_logic;
signal AIC_MEM_RES_REG_EN : std_logic;
signal AIC_MEM_CC_REG_EN : std_logic;
signal AIC_WB_CC_REG_EN : std_logic;
signal AIC_WB_RES_REG_EN : std_logic;
signal AIC_WB_PSR_EN : std_logic;
signal AIC_WB_PSR_ER : std_logic;
signal AIC_WB_PSR_SET_CC : std_logic;
signal AIC_WB_IAR_MUX_CTRL : std_logic;
signal AIC_WB_IAR_LOAD : std_logic;
signal AIC_DELAY : std_logic_vector(1 downto 0);
signal AIC_ARM_NEXT_STATE : ARM_STATE_TYPE;
-- Durch CDC_CONDITION_MET gefilterte Steuersignale
signal EX_REF_W_PORT_A_EN_REG_MET, EX_REF_W_PORT_B_EN_REG_MET, EX_MEM_DEN_REG_MET,
EX_MEM_DnRW_REG_MET, EX_WB_LOAD_REG_EN_REG_MET, --EX_WB_USER_REGS_REG_MET,
EX_WB_RES_REG_EN_REG_MET, EX_WB_CC_REG_EN_REG_MET, EX_WB_PSR_EN_REG_MET, EX_WB_IAR_LOAD_REG_MET : std_logic;
-- Neue Steuersignale fuer die Wartefunktion
signal ID_LNA_HOLD_VALUE_WAIT_MASKED : std_logic;
-- Register/Signale fuer die Erzeugung der Instruktions-ID
-- signal INSTRUCTION_ID_SRC_REG : std_logic_vector(INSTRUCTION_ID_WIDTH-1 downto 0);
signal IF_INST_ID_SRC_MUX, ID_INST_ID_PASS_MUX, WB_INST_ID_ABORT_MUX : std_logic_vector(INSTRUCTION_ID_WIDTH-1 downto 0);
signal IF_INSTRUCTION_ID_REGISTER_INC : std_logic_vector(INSTRUCTION_ID_WIDTH-1 downto 0);
signal IF_INST_ID_SRC_MUX_CTRL, ID_INST_ID_PASS_MUX_CTRL, WB_INST_ID_ABORT_MUX_CTRL : std_logic;
signal INSTRUCTION_ID_REGISTER : INSTRUCTION_ID_REGISTER_TYPE := (others => (others => '0'));
signal CPA_EX_PASS_REG : EX_CTRL_SIG_TYPE := "00";
-- Dieses Signal wird nur verwendet, wenn auch ein Coprozessor vorhanden ist
signal MEM_CC_MUX_CTRL_REG : MEM_CTRL_SIG_TYPE := "000";
signal EX_FBRANCH_MUX_CTRL : EX_CTRL_SIG_TYPE := "00";
signal WB_PSR_CTRL : WB_PSR_CTRL_TYPE := (others => (EXC_ENTRY => '0',EXC_RETURN => '0', SET_CC => '0', WRITE_SPSR => '0', MASK => "0000", MODE => SUPERVISOR));
signal EX_OPA_PSR_MUX_CTRL,EX_PSR_MUX_CTRL : EX_CTRL_SIG_TYPE := "00";
signal IRQ_FIQ_IABORT : std_logic;
-- Leseports C,B,A: die meisten Instruktionen verwenden nicht permanent
-- alle 3 Leseports. Damit keine sinnlosen Load-Use-Konflikte angezeigt
-- werden, muss eine Markierung existiern, welche gelesenen Registerinhalte
-- wirklich verwendet werden.
begin
--------------------------------------------------------------------------------
-- Instanzen von Hilfskomponenten
--------------------------------------------------------------------------------
ID_BASE_REGADDRESS_MAPPED <= GET_INTERNAL_ADDRESS(ID_INSTRUCTION_REG(19 downto 16),ID_MODE_MUX,'0');
CPA_BASE_ADDR_BUFFER : ArmRamBuffer
generic map(
ARB_ADDR_WIDTH => INSTRUCTION_ID_WIDTH,
ARB_DATA_WIDTH => 5 --Abgebildete Registeradresse
)
port map(
ARB_CLK => CPA_CLK,
ARB_WRITE_EN => IF_UPDATE_HISTORY_BUFFERS, --IF_FETCH_INSTRUCTION,
ARB_ADDR => IF_ARB_ADDR, -- kann nicht einfach das ID-Register sein weil beim ABORT umgeschaltet werden muss
-- mit dieser Zuweisung wird die Registeradresse des Basisregisters der Instruktion
-- in den Speicher verschoben, die bereits in der Decodestufe ist. Funktioniert weil mit dem
-- ersten Takt der aktuellen Instruktion bereits die naechste Instruktion gefetcht wird (immer), selbst
-- eine LDM-Instruktion die Pipeline lange blockiert ist ihre Basisregisteradresse daher bereits in den Puffer verschoben
ARB_DATA_IN => ID_BASE_REGADDRESS_MAPPED, --ID_INSTRUCTION_REG(19 downto 16),
ARB_DATA_OUT => WB_ARB_DATA_OUT
);
Inst_ArmArithInstructionCtrl: ArmArithInstructionCtrl port map(
AIC_DECODED_VECTOR => CID_DECODED_VECTOR,
AIC_INSTRUCTION => ID_INSTRUCTION_REG,
AIC_IF_IAR_INC => AIC_IF_IAR_INC ,
AIC_ID_R_PORT_A_ADDR => AIC_ID_R_PORT_A_ADDR ,
AIC_ID_R_PORT_B_ADDR => AIC_ID_R_PORT_B_ADDR ,
AIC_ID_R_PORT_C_ADDR => AIC_ID_R_PORT_C_ADDR ,
AIC_ID_REGS_USED => AIC_ID_REGS_USED ,
AIC_ID_IMMEDIATE => AIC_ID_IMMEDIATE ,
AIC_ID_OPB_MUX_CTRL => AIC_ID_OPB_MUX_CTRL ,
AIC_EX_ALU_CTRL => AIC_EX_ALU_CTRL ,
AIC_MEM_RES_REG_EN => AIC_MEM_RES_REG_EN ,
AIC_MEM_CC_REG_EN => AIC_MEM_CC_REG_EN ,
AIC_WB_W_PORT_A_ADDR => AIC_WB_W_PORT_A_ADDR ,
AIC_WB_W_PORT_A_EN => AIC_WB_W_PORT_A_EN ,
AIC_WB_RES_REG_EN => AIC_WB_RES_REG_EN ,
AIC_WB_CC_REG_EN => AIC_WB_CC_REG_EN ,
AIC_WB_IAR_LOAD => AIC_WB_IAR_LOAD ,
AIC_WB_PSR_EN => AIC_WB_PSR_EN ,
AIC_WB_PSR_ER => AIC_WB_PSR_ER ,
AIC_WB_PSR_SET_CC => AIC_WB_PSR_SET_CC ,
AIC_WB_IAR_MUX_CTRL => AIC_WB_IAR_MUX_CTRL ,
AIC_DELAY => AIC_DELAY ,
AIC_ARM_NEXT_STATE => AIC_ARM_NEXT_STATE
);
--------------------------------------------------------------------------------
-- Steuersignale für die Fetchstufe
--------------------------------------------------------------------------------
-- Beachte: Die Steuersignale für dem Instruktionsbus sind immer registriert,
-- werden also erst einen Takt nach dem setzen wirksam!
-- Etwas außer der Reihe wird hier auch ein Register für das PC-Inkrementsignal realisiert
-- CPA_IF_IEN <= IF_FETCH_INSTRUCTION_REG;
CPA_IF_IEN <= IF_IEN_REG;
CPA_IF_IAR_INC <= IF_IAR_INC;
CPA_IF_FETCH <= IF_FETCH_INSTRUCTION;
-- Am Instruktionsbus muss ein Betriebsmodus praesentiert werden. Sofern nach einem
-- Moduswechsel das naechste Fetch bis zur Aktualisierung des PSR verzoegert wird,
-- kann dazu der PSR-Modusausgang direkt verwendet werden. Zum Beschleunigen
-- der Ausnahmebehandlung wird der Modusausgang hier an den Multiplexer angeschlossen,
-- der den laufenden Moduswechsel in der Pipeline widerspiegelt.
CPA_IF_IMODE <= ID_MODE_MUX;
-- Das maskieren mit dem DABORT sorgt ggf. dafuer dass die History Buffer kleiner
-- sein koennen, erhoeht aber die Signallaufzeit der Buffer-Steuersignale signifikant.
-- Wenn diese Entscheidung zeitkritisch sein sollte kann MEM_DABORT_FILTERED aus
-- der Zuweisung wieder entfernt werden
IF_UPDATE_HISTORY_BUFFERS <= IF_FETCH_INSTRUCTION and not MEM_DABORT_FILTERED;
IF_INSTRUCTION_ID_REGISTER_INC <= std_logic_vector(unsigned(INSTRUCTION_ID_REGISTER(0)) + 1);
IF_INST_ID_SRC_MUX_CTRL <= IF_FETCH_INSTRUCTION;
IF_INST_ID_SRC_MUX <= IF_INSTRUCTION_ID_REGISTER_INC when IF_INST_ID_SRC_MUX_CTRL = '1' else INSTRUCTION_ID_REGISTER(0);
CPA_IF_IAR_UPDATE_HB <= IF_UPDATE_HISTORY_BUFFERS;--IF_FETCH_INSTRUCTION;
-- Im Takt nach der Abgebrochenen Instruktion wird die Basisadresse wiederhergestellt, dazu muss das entsprechende
-- ID-Register am Ende der MEM-Stufe als Adresse fuer das Auslesen des zugehörigen Eintrags im Basispuffer dienen
-- Waehrend dieses Takts beginnt die FSM, den Abort zu bearbeiten und Fetcht keine weitere Instruktion
IF_ARB_ADDR <= INSTRUCTION_ID_REGISTER(0) when ID_DABORT_REG = '0' else INSTRUCTION_ID_REGISTER(3);
-- Registerschreiben
SET_IF_ID_REGS : process(CPA_CLK)is
begin
if CPA_CLK'event and CPA_CLK = '1' then
if CPA_RST = '1' then
ID_INSTRUCTION_REG <= (others => '0');
ID_IABORT_REG <= '0';
-- Gleich im ersten Takt Instruktionsspeicher adressieren
IF_IEN_REG <= '1';
ID_FIQ_REG <= '0';
ID_IRQ_REG <= '0';
INSTRUCTION_ID_REGISTER(0)<= (others => '0');
else
ID_INSTRUCTION_REG <= ID_INSTRUCTION_REG;
ID_IABORT_REG <= ID_IABORT_REG;
IF_IEN_REG <= IF_IEN_REG;
ID_FIQ_REG <= ID_FIQ_REG;
ID_IRQ_REG <= ID_IRQ_REG;
INSTRUCTION_ID_REGISTER(0) <= INSTRUCTION_ID_REGISTER(0);
if CPA_WAIT = '0' then
INSTRUCTION_ID_REGISTER(0) <= IF_INST_ID_SRC_MUX;
-- In Wartezyklen wird der Speicher weiter aktiv angesteuert, wenn sich
-- der Inhalt des Instruktionsregisters nicht aendert bleibt dies genau so,
-- das Maskieren mit nWAIT ist also vermutlich ueberfluessig
IF_IEN_REG <= IF_IEN;
-- Das Inkrementieren wird bereits im Datenpfad direkt am IAR maskiert,
-- muss dies hier noch einmal sein?
-- Ich sehe keinen unmittelbaren Grund, die Interruptsignale
-- mit nWAIT zu maskieren, werde es aber dennoch vorlaeufig so handhaben
-- um den Prozessorkern _vollstaendig_ anzuhalten
ID_FIQ_REG <= CPA_FIQ;
ID_IRQ_REG <= CPA_IRQ;
end if;
if IF_FETCH_INSTRUCTION = '1' and CPA_IF_IBE = '1' and CPA_WAIT = '0' then
ID_INSTRUCTION_REG <= CPA_IF_ID;
ID_IABORT_REG <= CPA_IF_IABORT;
end if;
end if;
end if;
END PROCESS SET_IF_ID_REGS;
--------------------------------------------------------------------------------
-- Steuersignale für die Decodestufe
-- Beim Dekodieren erzeugte Steuersignale, die unmittelbar auf die
-- Executestufe wirken, werden hier nicht aufgeführt sondern stattdessen
-- direkt in der steuernden Statemachine zugewiesen
--------------------------------------------------------------------------------
-- Die Delayshiftregister muessen nWAIT nicht beruecksichtigen, sofern sichergestellt ist,
-- dass wahrend des Wartens permanent die gleichen Maskierungssteuersignale gesetzt werden
ArmDelayShiftRegister_FIQ: ArmDelayShiftRegister
generic map(DSR_WIDTH => 3)
port map(
DSR_CLK => CPA_CLK,
DSR_RST => CPA_RST,
DSR_WAIT=> CPA_WAIT,
DSR_SET => ID_MASK_FIQ, --evtl. zusaetzlich mit nWAIT maskieren
DSR_OUT => ID_FIQ_MASK
);
ArmDelayShiftRegister_IRQ: ArmDelayShiftRegister
generic map(DSR_WIDTH => 3)
port map(
DSR_CLK => CPA_CLK,
DSR_RST => CPA_RST,
DSR_WAIT=> CPA_WAIT,
DSR_SET => ID_MASK_IRQ, --evtl. zusaetzlich mit nWAIT maskieren
DSR_OUT => ID_IRQ_MASK
);
ID_COP_INSTRUCTION_BITS <= ID_INSTRUCTION_REG(27 downto 20) & ID_INSTRUCTION_REG(4);
COP_INSTRUCTION_DECODER : ArmCopDecoder
port map(
ACD_INSTRUCTION_BITS => ID_COP_INSTRUCTION_BITS,
ACD_INSTRUCTION_TYPE => ID_COP_INSTRUCTION_TYPE
);
ID_FIQ <= ID_FIQ_REG and not (CPA_EX_CPSR(6) or ID_FIQ_MASK);
ID_IRQ <= ID_IRQ_REG and not (CPA_EX_CPSR(7) or ID_IRQ_MASK);
IRQ_FIQ_IABORT <= ID_FIQ or ID_IRQ or ID_IABORT_REG;
-- Der Aufbau der Steuerung macht es nicht mehr notwendig, die
-- zahlreichen Unterbrechungssignale in einem eigenen Modul
-- zu priorisieren. Die verbliebene Priorisierung zwischen
-- FIQ,IRO und PABORT kann hier direkt im Quellcode erfolgen.
-- Pruefen: ist auch dies durch die Struktur der Steuerung bereits
-- ueberfluessig geworden?
ID_FIQ_FILTERED <= ID_FIQ;
ID_IRQ_FILTERED <= ID_IRQ and (not ID_FIQ);
ID_PABORT_FILTERED <= ID_IABORT_REG and (not ID_FIQ) and (not ID_IRQ);
ID_FILTERED_EXCEPTIONS <= ID_FIQ_FILTERED & ID_IRQ_FILTERED & ID_PABORT_FILTERED;
ArmCoarseInstructionDecoder_INSTANCE: ArmCoarseInstructionDecoder
port map(
CID_INSTRUCTION => ID_INSTRUCTION_REG,
CID_DECODED_VECTOR => CID_DECODED_VECTOR
);
-- Am beginn einer LDM/STM-Instruktion wird die darauf folgende Instruktion bereits
-- in das ID_INSTRUCTION_REG geschrieben, ID_LNA_LAOD_REGLIST aber nicht aktualisiert.
-- Es kann sich um eine weitere LDM-Instruktion handeln. Daher muss ArmLdmStmNextAddress einmalig
-- aus ID_INSTRUCTION_REG aktualisiert werden, wenn eine LDM/STM-Instruktion abeschlossen wird.
IF_LDMSTM_MUX <= CPA_IF_ID(15 downto 0) when IF_LDMSTM_MUX_CTRL = '0' else ID_INSTRUCTION_REG(15 downto 0);
-- Anpassung an Wartesignal: LOAD_REGLIST wird nicht maskiert, da das halten des alten Inhalts sinnlos ist
-- sofern das Ladesignal bereits gesetzt wurde.
-- HOLD_VALUE beruecksichtigt CPA_nWAIT um zu verhindern, dass der aktuelle Inhalt ueberschrieben wird
-- (ausser, und dann zurecht, durch ein LOAD)
ID_LNA_HOLD_VALUE_WAIT_MASKED <= CPA_WAIT or ID_LNA_HOLD_VALUE;
ArmLdmStmNextAddress_INSTANCE: ArmLdmStmNextAddress
port map(
SYS_RST => CPA_RST,
SYS_CLK => CPA_CLK,
LNA_LOAD_REGLIST => ID_LNA_LOAD_REGLIST,
LNA_HOLD_VALUE => ID_LNA_HOLD_VALUE_WAIT_MASKED,--ID_LNA_HOLD_VALUE,
--Es wird permanent ein Teil der Daten auf dem Bus gelesen,
-- nur bei Erkennen einer LDM/STM-Instruktion wird der Wert nicht
-- vom Bus aktualisiert
LNA_REGLIST => IF_LDMSTM_MUX,
LNA_ADDRESS => ID_LNA_ADDRESS,
--Ausgang mit den verbleibenden Zugriffsbits
-- zur Errechnung der ausbleibenden Zugriffszahl
LNA_CURRENT_REGLIST_REG => LNA_CURRENT_REGLIST_REG
);
ArmRegisterBitAdder_Instance: ArmRegisterBitAdder
PORT MAP(
RBA_REGLIST => LNA_CURRENT_REGLIST_REG,
RBA_NR_OF_REGS => RBA_NR_OF_REGS
);
-- Bypasssteuerung fuer die Verwendung des korrekten
-- neuen Modus unmittelbar nach dem ersten Takt des
-- Ausnahmebehandlung.
-- Der Bypass ermoeglicht nur die Verwendung
-- eines neuen Betriebsmodus der durch die Signale
-- PSR_EN und PSR_EXCEPTION_ENTRY verursacht wird, um die Wartezeit
-- nach dem ersten Takt zu verkurzen. Exception Return und
-- direkte Schreibzugriffe auf das Statusregister werden
-- nocht nicht beruecksichtigt
EXCEPTION_MODE_BYPASS : process(WB_PSR_CTRL(1).EXC_ENTRY, WB_PSR_CTRL(2).EXC_ENTRY, WB_PSR_CTRL(3).EXC_ENTRY,
WB_PSR_CTRL(1).MODE, WB_PSR_CTRL(2).MODE, WB_PSR_CTRL(3).MODE,
EX_WB_PSR_EN_REG_MET,MEM_WB_PSR_EN_REG,WB_WB_PSR_EN_REG, CPA_EX_CPSR(4 downto 0))is
-- variable ENTRY2,ENTRY3 : std_logic := '0';
begin
if (EX_WB_PSR_EN_REG_MET and WB_PSR_CTRL(1).EXC_ENTRY)= '1' then
ID_MODE_MUX <= WB_PSR_CTRL(1).MODE;
elsif (MEM_WB_PSR_EN_REG and WB_PSR_CTRL(2).EXC_ENTRY)= '1' then
ID_MODE_MUX <= WB_PSR_CTRL(2).MODE;
elsif (WB_WB_PSR_EN_REG and WB_PSR_CTRL(3).EXC_ENTRY)= '1' then
ID_MODE_MUX <= WB_PSR_CTRL(3).MODE;
else
ID_MODE_MUX <= CPA_EX_CPSR(4 downto 0);
end if;
end process EXCEPTION_MODE_BYPASS;
--------------------------------------------------------------------------------
-- Sicherstellen, dass keine Bypaessen geschaltet werden koennen
-- wenn der History Buffer verwendet wird
-- Wenn das nicht automatisch sicher ist, kann
-- IAR_REVOKE als zusaetzliches Steuersignal
-- verwendet werden
--------------------------------------------------------------------------------
Inst_ArmBypassCtrl: ArmBypassCtrl
port map(
-- ABC_INST0_OPA_PSR_MUX_CTRL => EX_OPA_PSR_MUX_CTRL(0),
-- ABC_INST0_OPB_MUX_CTRL => ID_OPB_MUX_CTRL,
-- ABC_INST0_SHIFT_MUX_CTRL => ID_SHIFT_MUX_CTRL,
ABC_INST0_R_PORT_A_ADDR => ID_REF_R_PORTS_ADDR(4 downto 0),
ABC_INST0_R_PORT_B_ADDR => ID_REF_R_PORTS_ADDR(9 downto 5),
ABC_INST0_R_PORT_C_ADDR => ID_REF_R_PORTS_ADDR(14 downto 10),
ABC_INST1_W_PORT_A_ADDR => WB_REF_W_PORTS_ADDR(1)(4 downto 0),
ABC_INST1_W_PORT_B_ADDR => WB_REF_W_PORTS_ADDR(1)(9 downto 5),
ABC_INST2_W_PORT_A_ADDR => WB_REF_W_PORTS_ADDR(2)(4 downto 0),
ABC_INST2_W_PORT_B_ADDR => WB_REF_W_PORTS_ADDR(2)(9 downto 5),
ABC_INST1_W_PORT_A_EN => EX_REF_W_PORT_A_EN_REG_MET,
ABC_INST1_W_PORT_B_EN => EX_REF_W_PORT_B_EN_REG_MET,
ABC_INST2_W_PORT_A_EN => MEM_REF_W_PORT_A_EN_REG,
ABC_INST2_W_PORT_B_EN => MEM_REF_W_PORT_B_EN_REG,
ABC_INST1_WB_PSR_EN => EX_WB_PSR_EN_REG_MET,
ABC_INST1_WB_PSR_SET_CC => WB_PSR_CTRL(1).SET_CC,
ABC_INST2_WB_PSR_EN => MEM_WB_PSR_EN_REG,
ABC_INST2_WB_PSR_SET_CC => WB_PSR_CTRL(2).SET_CC,
ABC_INST0_REGS_USED => ID_REGS_USED,
ABC_INST0_SHIFT_REG_USED => ID_SHIFT_MUX_CTRL,
ABC_INST0_OPA_BYPASS_MUX_CTRL => EX_OPX_MUX_CTRLS(0)(1 downto 0),--ID_EX_OPA_MUX_CTRL,
ABC_INST0_OPB_BYPASS_MUX_CTRL => EX_OPX_MUX_CTRLS(0)(3 downto 2),--ID_EX_OPB_MUX_CTRL,
ABC_INST0_OPC_BYPASS_MUX_CTRL => EX_OPX_MUX_CTRLS(0)(5 downto 4),--ID_EX_OPC_MUX_CTRL,
ABC_INST0_SHIFT_BYPASS_MUX_CTRL => ID_EX_SHIFT_MUX_CTRL,
ABC_INST0_CC_BYPASS_MUX_CTRL => ID_EX_CC_MUX_CTRL,
ABC_LOAD_USE_CONFLICT => ID_LOAD_USE_CONFLICT
);
CPA_ID_REF_R_PORTS_ADDR <= ID_REF_R_PORTS_ADDR;
CPA_ID_OPB_MUX_CTRL <= ID_OPB_MUX_CTRL;
CPA_ID_SHIFT_MUX_CTRL <= ID_SHIFT_MUX_CTRL;
CPA_ID_SHIFT_AMOUNT <= ID_SHIFT_AMOUNT;
CPA_ID_IMMEDIATE <= ID_IMMEDIATE;
CPA_DPA_ENABLE <= ID_DPA_ENABLE;
-- Bestimmung von SRC_OPERAND_2_TYPE
with CID_DECODED_VECTOR select
SRC_OPERAND_2_TYPE <= OP2_IMMEDIATE when CD_ARITH_IMMEDIATE,
OP2_IMMEDIATE when CD_MSR_IMMEDIATE,
OP2_REGISTER when CD_LOAD_STORE_UNSIGNED_REGISTER,
OP2_REGISTER when CD_ARITH_REGISTER,
OP2_REGISTER when CD_MSR_REGISTER, --kodiert wie ein LSL mit Weite 0
OP2_REGISTER_REGISTER when CD_ARITH_REGISTER_REGISTER,
OP2_NO_SHIFTER_OPERAND when others;
ArmShiftRecoder_Instance: ArmShiftRecoder
port map(
SRC_OPERAND_2 => ID_INSTRUCTION_REG(11 downto 5),
SRC_OPERAND_2_TYPE => SRC_OPERAND_2_TYPE,
SRC_SHIFT_AMOUNT => SRC_SHIFT_CTRL.SHIFT_CTRL_AMOUNT,--SRC_SHIFT_AMOUNT,
SRC_SHIFT_TYPE => SRC_SHIFT_CTRL.SHIFT_CTRL_TYPE,--SRC_SHIFT_TYPE,
SRC_SHIFT_RRX => SRC_SHIFT_CTRL.SHIFT_CTRL_RRX,--SRC_SHIFT_RRX,
-- Unmittelbares Setzen des Multiplexersteuersignales des EX-Stufe geht nicht
-- noch anzupassen:
SRC_USE_OPC => SRC_SHIFT_CTRL.SHIFT_CTRL_OPC--SRC_USE_OPC
);
-- Dieses Steuersignal ist relativ komplex zu erzeugen da es unmittelbar von der Prozessorsteuerung
-- abhaengt. Wenn immer eine neue, vorher gefetchte Instruktion neu bearbeitet wird, muss dieses
-- Signal einmal auf 1 gesetzt werden, in den folgenden Takten (so sie zur gleichen Instruktion gehoeren)
-- wird die gleiche ID verwendet. Derzeit wird das Signal immer genau dann gesetzt, wenn die
-- Steuerung im Zustand STATE_DECODE ist.
ID_INST_ID_PASS_MUX <= INSTRUCTION_ID_REGISTER(0) when ID_INST_ID_PASS_MUX_CTRL = '1' else INSTRUCTION_ID_REGISTER(1);
-- Registerschreiben
-- Ergeaenzung um CPA_nWAIT
SET_ID_EX_REGS : process(CPA_CLK)is
begin
if CPA_CLK'event and CPA_CLK = '1' then
--if CPA_RST = '1' then
-- Nach einem Reset befinden sich keine sinnvollen Werte in der Pipeline
-- Grundsaetzlich sollte NV im Bedingungsfeld aber alle
-- relevanten Steuersignale im naechsten Takt loeschen
-- EX_CONDITION_FIELD_REG <= NV;
-- EX_WB_PSR_EN_REG <= '0';
-- EX_WB_IAR_LOAD_REG <= '0';
-- INSTRUCTION_ID_REGISTER(1) <= (others => '0');
-- CPA_EX_PASS_REG(1) <= '0';
--else
INSTRUCTION_ID_REGISTER(1) <= INSTRUCTION_ID_REGISTER(1);
if CPA_WAIT = '0' then
INSTRUCTION_ID_REGISTER(1) <= ID_INST_ID_PASS_MUX;
MEM_CC_MUX_CTRL_REG(1) <= MEM_CC_MUX_CTRL_REG(0);
-- Evtl. den IF-Then-Else-Zweig umbauen, so dass alle davon eigentlich
-- nicht beruehrten Signale ausserhalb stehen statt implizit gespeichert
-- zu werden
if false then --ID_STOPP_DECODE = '1' then
-- Alle Steuersignale, die dauerhafte Wirkung entfalten auf 0 setzen
-- und so ein NOP in die Pipeline schreiben
-- Wenn das Bedingungsfeld erhalten bleibt, kann waehrend der Wartetakte
-- in WAIT_TO_FETCH und WAIT_TO_DECODE ueberprueft werden, ob das verbleiben in diesen
-- Zustaenden wirklich sinnvoll ist
EX_MEM_DnRW_REG <= '0';
EX_MEM_DEN_REG <= '0';
EX_REF_W_PORT_A_EN_REG <= '0';
EX_REF_W_PORT_B_EN_REG <= '0';
-- EX_WB_USER_REGS_REG <= '0';
EX_WB_LOAD_REG_EN_REG <= '0';
EX_WB_PSR_EN_REG <= '0';
EX_WB_IAR_LOAD_REG <= '0';
CPA_EX_PASS_REG(1) <= '0';
EX_FBRANCH_MUX_CTRL(1) <= '0';
EX_CONDITION_FIELD_REG <= EX_CONDITION_FIELD_REG;
else
EX_CONDITION_FIELD_REG <= ID_CONDITION_FIELD;
EX_OPX_MUX_CTRLS(1) <= EX_OPX_MUX_CTRLS(0);
EX_EX_SHIFT_MUX_CTRL_REG <= ID_EX_SHIFT_MUX_CTRL;
EX_EX_CC_MUX_CTRL_REG <= ID_EX_CC_MUX_CTRL;
EX_EX_OPB_ALU_MUX_CTRL_REG <= ID_EX_OPB_ALU_MUX_CTRL;
EX_EX_PSR_CC_MUX_CTRL_REG <= ID_EX_PSR_CC_MUX_CTRL;
EX_EX_DAR_MUX_CTRL_REG <= ID_EX_DAR_MUX_CTRL;
-- EX_EX_SHIFT_TYPE_REG <= ID_EX_SHIFT_TYPE;
-- EX_EX_SHIFT_RRX_REG <= ID_EX_SHIFT_RRX;
EX_SHIFT_EX_CTRL(1) <= EX_SHIFT_EX_CTRL(0);
EX_EX_ALU_CTRL_REG <= ID_EX_ALU_CTRL;
CPA_EX_PASS_REG(1) <= CPA_EX_PASS_REG(0);
EX_FBRANCH_MUX_CTRL(1) <= EX_FBRANCH_MUX_CTRL(0);
EX_MEM_DATA_REG_EN_REG <= ID_MEM_DATA_REG_EN;
EX_MEM_RES_REG_EN_REG <= ID_MEM_RES_REG_EN;
EX_MEM_CC_REG_EN_REG <= ID_MEM_CC_REG_EN;
EX_MEM_BASE_REG_EN_REG <= ID_MEM_BASE_REG_EN;
-- EX_MEM_DAR_EN_REG evtl. mit 0 setzen
EX_MEM_DAR_EN_REG <= ID_MEM_DAR_EN;
EX_MEM_DAR_INC_REG <= ID_MEM_DAR_INC;
MEM_WMP_CTRL(1) <= MEM_WMP_CTRL(0);
EX_MEM_DnRW_REG <= ID_MEM_DnRW;
EX_MEM_DEN_REG <= ID_MEM_DEN;
MEM_DMAS(1) <= MEM_DMAS(0);
MEM_TRUNCATE_ADDR(1) <= MEM_TRUNCATE_ADDR(0);
WB_REF_W_PORTS_ADDR(1) <= WB_REF_W_PORTS_ADDR(0);
EX_REF_W_PORT_A_EN_REG <= ID_REF_W_PORT_A_EN;
EX_REF_W_PORT_B_EN_REG <= ID_REF_W_PORT_B_EN;
EX_WB_LOAD_REG_EN_REG <= ID_WB_LOAD_REG_EN;
EX_WB_RES_REG_EN_REG <= ID_WB_RES_REG_EN;
EX_WB_CC_REG_EN_REG <= ID_WB_CC_REG_EN;
EX_WB_PSR_EN_REG <= ID_WB_PSR_EN;
WB_PSR_CTRL(1) <= WB_PSR_CTRL(0);
EX_WB_IAR_MUX_CTRL_REG <= ID_WB_IAR_MUX_CTRL;
EX_WB_IAR_LOAD_REG <= ID_WB_IAR_LOAD;
EX_OPA_PSR_MUX_CTRL(1) <= EX_OPA_PSR_MUX_CTRL(0);
EX_PSR_MUX_CTRL(1) <= EX_PSR_MUX_CTRL(0);
end if;
end if; -- if CPA_nWAIT = '1'
--end if;
if CPA_RST = '1' then
-- Nach einem Reset befinden sich keine sinnvollen Werte in der Pipeline
-- Grundsaetzlich sollte NV im Bedingungsfeld aber alle
-- relevanten Steuersignale im naechsten Takt loeschen
EX_CONDITION_FIELD_REG <= NV;
EX_WB_PSR_EN_REG <= '0';
EX_WB_IAR_LOAD_REG <= '0';
INSTRUCTION_ID_REGISTER(1) <= (others => '0');
CPA_EX_PASS_REG(1) <= '0';
end if;
end if;
end process SET_ID_EX_REGS;
--------------------------------------------------------------------------------
-- Steuersignale für die Executestufe
--------------------------------------------------------------------------------
-- Die Steuersignale in der EX-Stufe dürfen unabhängig von CDC_CONDITION_FIELD_REG
-- gesetzt werden, da sie ohne Ablegen der Ergebnisse in Pipelineregistern wirkungslos sind
CPA_EX_OPX_MUX_CTRLS <= EX_OPX_MUX_CTRLS(1);--EX_EX_OPC_MUX_CTRL_REG & EX_EX_OPB_MUX_CTRL_REG & EX_EX_OPA_MUX_CTRL_REG;
CPA_EX_SHIFT_MUX_CTRL <= EX_EX_SHIFT_MUX_CTRL_REG;
CPA_EX_CC_MUX_CTRL <= EX_EX_CC_MUX_CTRL_REG;
CPA_EX_OPB_ALU_MUX_CTRL <= EX_EX_OPB_ALU_MUX_CTRL_REG;
CPA_EX_PSR_CC_MUX_CTRL <= EX_EX_PSR_CC_MUX_CTRL_REG;
CPA_EX_DAR_MUX_CTRL <=EX_EX_DAR_MUX_CTRL_REG;
CPA_EX_SHIFT_TYPE <= EX_SHIFT_EX_CTRL(1).SHIFT_EX_CTRL_TYPE;--EX_EX_SHIFT_TYPE_REG;
CPA_EX_SHIFT_RRX <= EX_SHIFT_EX_CTRL(1).SHIFT_EX_CTRL_RRX;--EX_EX_SHIFT_RRX_REG;
CPA_EX_ALU_CTRL <= EX_EX_ALU_CTRL_REG;
CPA_EX_DRP_DMAS <= MEM_DMAS(1);
-- Der Instruktion in der EX-Stufe des Coprozessors signalisieren, dass sie
-- ausgefuehrt werden darf
CPA_EX_PASS <= CPA_EX_PASS_REG(1) and CDC_CONDITION_MET;
CPA_EX_OPA_PSR_MUX_CTRL <= EX_OPA_PSR_MUX_CTRL(1);
CPA_EX_PSR_MUX_CTRL <= EX_PSR_MUX_CTRL(1);
ArmConditionCheck_Instance: ArmConditionCheck
port map(
CDC_CONDITION_FIELD => EX_CONDITION_FIELD_REG,
CDC_CONDITION_CODE => CPA_EX_CPSR(31 downto 28),--CPA_EX_CC,
CDC_CONDITION_MET => CDC_CONDITION_MET
);
CPA_MEM_DATA_REG_EN <= EX_MEM_DATA_REG_EN_REG;
CPA_MEM_RES_REG_EN <= EX_MEM_RES_REG_EN_REG;
CPA_MEM_CC_REG_EN <= EX_MEM_CC_REG_EN_REG;
--Neu, steuert, ob eine Instruktion das Basisregister neu Beschreiben darf
-- In der aktuellen Loesung kopiert eine Instruktion den Inhalt des Registers im Takt mit einem Data Abort
-- nach WB_RES_REG, woraus er anschliessend in den Registerspeicher geschrieben wird, eine nachfolgende
-- Instruktion darf den Inhalt von MEM_BASE_REG daher unbedingt aendern, obwohl sie natuerlich keine Wirkung
-- auf den sichtbaren Prozessorzustand hat
CPA_MEM_BASE_REG_EN <= EX_MEM_BASE_REG_EN_REG;
-- CPA_MEM_BASE_REG_EN <= '0' when CDC_CONDITION_MET = '0' or (CPA_MEM_DABORT = '1' and MEM_MEM_DEN = '1' and ENABLE_DATA_ABORT) else EX_MEM_BASE_REG_EN_REG;
-- Neue durch CONDITION_MET beeinflusste Signale, die vorher im Prozess direkt gesetzt worden sind, ggf.
-- sind die Signale auch vom DABORT-Register abhaengig weil ein Data Abort auf nachfolgende Instruktionen
-- wirkt als ob diese nicht ausgefuehrt wuerde
EX_REF_W_PORT_A_EN_REG_MET <= EX_REF_W_PORT_A_EN_REG and CDC_CONDITION_MET and not ID_DABORT_REG;
EX_REF_W_PORT_B_EN_REG_MET <= EX_REF_W_PORT_B_EN_REG and CDC_CONDITION_MET and not ID_DABORT_REG;
-- Es koennte sinnvoll sein, das DEN-Signal bereits hier mit MEM_DABORT_FILTERED zu maskieren, das fuehrt
-- zu keiner weiteren Verzoegerung (weil in der MEM-Stufe gleichzeitig aehnliches stattfindet) und so
-- sicher verhindert wird, dass DEN auch nur kurz an ist, dafuer steht es freuher im naechsten Takt
-- zur Verfuegugn
EX_MEM_DEN_REG_MET <= EX_MEM_DEN_REG and CDC_CONDITION_MET and (not (ID_DABORT_REG or MEM_DABORT_FILTERED));
-- Das Signal ist im Prinzip von DEN abhaengig und muss daher nicht nochmal extra gefiltert werden
EX_MEM_DnRW_REG_MET <= EX_MEM_DnRW_REG;-- and CDC_CONDITION_MET and not ID_DABORT_REG;
-- EX_WB_USER_REGS_REG_MET <= EX_WB_USER_REGS_REG and CDC_CONDITION_MET and not ID_DABORT_REG;
EX_WB_LOAD_REG_EN_REG_MET <= EX_WB_LOAD_REG_EN_REG and CDC_CONDITION_MET and not ID_DABORT_REG;
-- Veraendern den sichtbaren Prozessorzustand nicht und muessen daher nicht maskiert werden
EX_WB_RES_REG_EN_REG_MET <= EX_WB_RES_REG_EN_REG; --and CDC_CONDITION_MET and not ID_DABORT_REG;
EX_WB_CC_REG_EN_REG_MET <= EX_WB_CC_REG_EN_REG; --and CDC_CONDITION_MET and not ID_DABORT_REG;
EX_WB_PSR_EN_REG_MET <= EX_WB_PSR_EN_REG and CDC_CONDITION_MET and not ID_DABORT_REG;
-- Wenn Fast Branch verwendet wird, darf das Load-Signal eines Sprungs nicht die WB-Stufe nicht erreichen, weil es bereits in der EX-Stufe wirkt
EX_WB_IAR_LOAD_REG_MET <= '1' when EX_WB_IAR_LOAD_REG = '1' and CDC_CONDITION_MET='1' and ID_DABORT_REG = '0' and (EX_FBRANCH_MUX_CTRL(1) = '0' or (not USE_FAST_BRANCH)) else '0';
CPA_EX_DAR_EN <= EX_MEM_DAR_EN_REG;
CPA_EX_DAR_INC <= EX_MEM_DAR_INC_REG;
-- Registerschreiben
SET_EX_MEM_REGS : process(CPA_CLK)IS
begin
if CPA_CLK'event AND CPA_CLK = '1' then
-- if CPA_RST = '1' then
-- MEM_REF_W_PORT_A_EN_REG <= '0';
-- MEM_REF_W_PORT_B_EN_REG <= '0';
-- MEM_MEM_DEN_REG <= '0';
-- -- MEM_WB_USER_REGS_REG <= '0';
-- MEM_WB_LOAD_REG_EN_REG <= '0';
-- MEM_WB_PSR_EN_REG <= '0';
-- MEM_WB_IAR_LOAD_REG <= '0';
-- else
INSTRUCTION_ID_REGISTER(2) <= INSTRUCTION_ID_REGISTER(2);
if CPA_WAIT = '0' then
INSTRUCTION_ID_REGISTER(2)<= INSTRUCTION_ID_REGISTER(1);
WB_REF_W_PORTS_ADDR(2) <= WB_REF_W_PORTS_ADDR(1);
MEM_DMAS(2) <= MEM_DMAS(1);
MEM_REF_W_PORT_A_EN_REG <= EX_REF_W_PORT_A_EN_REG_MET;
MEM_REF_W_PORT_B_EN_REG <= EX_REF_W_PORT_B_EN_REG_MET;
MEM_MEM_DEN_REG <= EX_MEM_DEN_REG_MET;
MEM_MEM_DnRW_REG <= EX_MEM_DnRW_REG_MET;
MEM_WMP_CTRL(2) <= MEM_WMP_CTRL(1);
MEM_CC_MUX_CTRL_REG(2) <= MEM_CC_MUX_CTRL_REG(1);
MEM_TRUNCATE_ADDR(2) <= MEM_TRUNCATE_ADDR(1);
MEM_WB_LOAD_REG_EN_REG <= EX_WB_LOAD_REG_EN_REG_MET;
MEM_WB_RES_REG_EN_REG <= EX_WB_RES_REG_EN_REG_MET;
MEM_WB_CC_REG_EN_REG <= EX_WB_CC_REG_EN_REG_MET;
MEM_WB_PSR_EN_REG <= EX_WB_PSR_EN_REG_MET;
MEM_WB_IAR_LOAD_REG <= EX_WB_IAR_LOAD_REG_MET;
WB_PSR_CTRL(2) <= WB_PSR_CTRL(1);
MEM_WB_IAR_MUX_CTRL_REG <= EX_WB_IAR_MUX_CTRL_REG;
end if;
-- end if;
if CPA_RST = '1' then
MEM_REF_W_PORT_A_EN_REG <= '0';
MEM_REF_W_PORT_B_EN_REG <= '0';
MEM_MEM_DEN_REG <= '0';
MEM_WB_LOAD_REG_EN_REG <= '0';
MEM_WB_PSR_EN_REG <= '0';
MEM_WB_IAR_LOAD_REG <= '0';
end if;
end if;
end process SET_EX_MEM_REGS;
--------------------------------------------------------------------------------
-- Steuersignale für die Memorystufe (Wirksam in der Memorystufe)
-- 10.09.09: Ergaenzung: MEM_DnRW_REG verundet mit MEM_DEN_REG, da sonst schreibzugriffe
-- bei nicht ausgefuehrten Speicherzugriffen autreten koennen. Alternativ kann auch
-- das DnRW-Signal beim Speichern in das EX/MEM-Register auf 0 gesetzt werden
-- 06.10.09: MEM_DEN und MEM_DnRW werden zusaetzlich durch ID_DABORT_REG maskiert,
-- da auf einen ABORT kein weiterer Speicherzugriff folgen darf, der Abort
-- aber erst behandelt wird wenn die verursachende Instruktion in der WB-Stufe ist
-- Hier noch zu ergaenzen: die Steuersignale zur WB-Stufe muessen geloescht werden
-- wenn ein Abort aufgetreten ist
--------------------------------------------------------------------------------
-- Im Prinzip ist diese Maskierung ueberfluessig da nur mit DEN wirklich auf Speicher zugegriffen wird (wird das aber im Speichersubsystem nicht kontrolliert
-- verhindert das Maskieren von DnRW versehentliche Schreibzugriffe)
CPA_MEM_DnRW <= MEM_MEM_DnRW_REG and MEM_MEM_DEN_REG and (not ID_DABORT_REG);-- when CPA_MEM_DBE = '1' else 'Z';
-- ID_DABORT_REG darf hier nur weggelassen werden wenn bereits in der EX-Stufe mit MEM_DABORT_FILTERED maskiert wurde
MEM_MEM_DEN <= MEM_MEM_DEN_REG;-- and (not ID_DABORT_REG);
CPA_MEM_DEN <= MEM_MEM_DEN;
CPA_MEM_DMAS <= MEM_DMAS(2);--MEM_MEM_DMAS_REG;-- when CPA_MEM_DBE = '1' else "ZZ";
-- Das angehaengte DABORT_FILTERED soll verhindern dass im extremfall Metawerte aus dem Speichersubsystem (in dem eine falsche
-- Adresse angesprochen wurde und evtl. kein Treiber aktiv ist) in den Prozessorkern gelangen