1 #include <ot/timer/test.hpp>
2 #include <ot/timer/arc.hpp>
3 #include <ot/timer/pin.hpp>
4
5 namespace ot {
6
7 // ------------------------------------------------------------------------------------------------
8
9 // Constructor
Test(Arc & arc)10 Test::Test(Arc& arc) : _arc {arc} {
11 }
12
13 // Function: rat
rat(Split el,Tran rf) const14 std::optional<float> Test::rat(Split el, Tran rf) const {
15 return _rat[el][rf];
16 }
17
18 // Function: constraint
constraint(Split el,Tran rf) const19 std::optional<float> Test::constraint(Split el, Tran rf) const {
20 return _constraint[el][rf];
21 }
22
23 // Function: cppr_credit
cppr_credit(Split el,Tran rf) const24 std::optional<float> Test::cppr_credit(Split el, Tran rf) const {
25 return _cppr_credit[el][rf];
26 }
27
28 // Function: slack
slack(Split el,Tran rf) const29 std::optional<float> Test::slack(Split el, Tran rf) const {
30 if(_arc._to._at[el][rf] && _rat[el][rf]) {
31 return (
32 el == MIN ? *_arc._to._at[el][rf] - *_rat[el][rf] :
33 *_rat[el][rf] - *_arc._to._at[el][rf]
34 ) + (
35 _cppr_credit[el][rf] ? *_cppr_credit[el][rf] : 0.0f
36 );
37 }
38 else return std::nullopt;
39 }
40
41 // Function: raw_slack
raw_slack(Split el,Tran rf) const42 std::optional<float> Test::raw_slack(Split el, Tran rf) const {
43 if(_arc._to._at[el][rf] && _rat[el][rf]) {
44 return (
45 el == MIN ? *_arc._to._at[el][rf] - *_rat[el][rf] :
46 *_rat[el][rf] - *_arc._to._at[el][rf]
47 );
48 }
49 else return std::nullopt;
50 }
51
52 // Function: arc
arc() const53 const Arc& Test::arc() const {
54 return _arc;
55 }
56
57 // Function: constrained_pin
constrained_pin() const58 const Pin& Test::constrained_pin() const {
59 return _arc._to;
60 }
61
62 // Function: related_pin
related_pin() const63 const Pin& Test::related_pin() const {
64 return _arc._from;
65 }
66
67 // Function: _constrained_pin
_constrained_pin()68 Pin& Test::_constrained_pin() {
69 return _arc._to;
70 }
71
72 // Function: _related_pin
_related_pin()73 Pin& Test::_related_pin() {
74 return _arc._from;
75 }
76
77 // Procedure: _reset
_reset()78 void Test::_reset() {
79 FOR_EACH_EL_RF(el, rf) {
80 _rat[el][rf].reset();
81 _cppr_credit[el][rf].reset();
82 _constraint[el][rf].reset();
83 _related_at[el][rf].reset();
84 }
85 }
86
87 // Procedure: _fprop_rat
_fprop_rat(float period)88 void Test::_fprop_rat(float period) {
89
90 auto tv = _arc.timing_view();
91
92 FOR_EACH_EL_RF_IF(el, rf, tv[el]) {
93
94 // SLEW not defined at the constrained pin.
95 if(!(_arc._to._slew[el][rf])) {
96 continue;
97 }
98
99 auto fel = (el == MIN ? MAX : MIN);
100 auto frf = tv[el]->is_rising_edge_triggered() ? RISE : FALL;
101
102 if(frf == FALL && !tv[el]->is_falling_edge_triggered()) {
103 OT_LOGE("clock transition not found for test ", _arc.name());
104 continue;
105 }
106
107 // AT/SLEW not defined at the arc._from
108 if(!(_arc._from._at[fel][frf]) || !(_arc._from._slew[fel][frf])) {
109 continue;
110 }
111
112 if(el == MIN) {
113 _related_at[el][rf] = *_arc._from._at[fel][frf];
114 }
115 else {
116 _related_at[el][rf] = *_arc._from._at[fel][frf] + period;
117 }
118
119 _constraint[el][rf] = tv[el]->constraint(
120 frf,
121 rf,
122 *_arc._from._slew[fel][frf],
123 *_arc._to._slew[el][rf]
124 );
125
126 if(_constraint[el][rf] && _related_at[el][rf]) {
127 if(el == MIN) {
128 _rat[el][rf] = *_constraint[el][rf] + *_related_at[el][rf];
129 }
130 else {
131 _rat[el][rf] = *_related_at[el][rf] - *_constraint[el][rf];
132 }
133 }
134 }
135 }
136
137 }; // end of namespace ot. -----------------------------------------------------------------------
138
139
140
141
142
143
144
145
146
147
148