(no commit message)
[libreriscv.git] / openpower / sv / cr_int_predication.mdwn
1 [[!tag standards]]
2
3 # New instructions for CR/INT predication
4
5 **DRAFT STATUS**
6
7 See:
8
9 * main bugreport for crweirds
10 <https://bugs.libre-soc.org/show_bug.cgi?id=533>
11 * <https://bugs.libre-soc.org/show_bug.cgi?id=527>
12 * <https://bugs.libre-soc.org/show_bug.cgi?id=569>
13 * <https://bugs.libre-soc.org/show_bug.cgi?id=558#c47>
14
15 Rationale:
16
17 Condition Registers are conceptually perfect for use as predicate masks, the only problem being that typical Vector ISAs have quite comprehensive mask-based instructions: set-before-first, popcount and much more. In fact many Vector ISAs can use Vectors *as* masks, consequently the entire Vector ISA is available for use in creating masks. This is not practical for SV given the strategy of leveraging pre-existing Scalar instructions in a minimalist way.
18
19 With the scalar OpenPOWER v3.0B ISA having already popcnt, cntlz and others normally seen in Vector Mask operations it makes sense to allow *both* scalar integers *and* CR-Vectors to be predicate masks. That in turn means that much more comprehensive interaction between CRs and scalar Integers is required, because with the CR Predication Modes designating CR *Fields*
20 (not CR bits) as Predicate Elements, fast transfers between CR *Fields* and
21 the Integer Register File is needed.
22
23 The opportunity is therefore taken to also augment CR logical arithmetic as well, using a mask-based paradigm that takes into consideration multiple bits of each CR Field (eq/lt/gt/ov). By contrast
24 v3.0B Scalar CR instructions (crand, crxor) only allow a single bit calculation.
25
26 Basic concept:
27
28 * CR-based instructions that perform simple AND/OR/XOR from any four bits
29 of a CR field to create a single bit value (0/1) in an integer register
30 * Inverse of the same, taking a single bit value (0/1) from an integer
31 register to selectively target any four bits of a given CR Field
32 * CR-to-CR version of the same, allowing multiple bits to be AND/OR/XORed
33 in one hit.
34 * Optional Vectorisation of the same when SVP64 is implemented
35
36 Purpose:
37
38 * To provide a merged version of what is currently a multi-sequence of
39 CR operations (crand, cror, crxor) with mfcr and mtcrf, reducing
40 instruction count.
41 * To provide a vectorised version of the same, suitable for advanced
42 predication
43
44 Side-effects:
45
46 * mtcrweird when RA=0 is a means to set or clear arbitrary CR bits
47 using immediates embedded within the instruction.
48
49 (Twin) Predication interactions:
50
51 * INT twin predication with zeroing is a way to copy an integer into CRs without necessarily needing the INT register (RA). if it is, it is effectively ANDed (or negate-and-ANDed) with the INT Predicate
52 * CR twin predication with zeroing is likewise a way to interact with the incoming integer
53
54 this gets particularly powerful if data-dependent predication is also enabled. further explanation is below.
55
56 # Bit ordering.
57
58 IBM chose MSB0 for the OpenPOWER v3.0B specification. This makes things slightly hair-raising and the relationship between the CR and the CR Field
59 numbers is not clearly defined. To make it clear we define a new
60 term, `CR{n}`.
61 `CR{n}` refers to `CR0` when `n=0` and consequently, for CR0-7, is defined, in v3.0B pseudocode, as:
62
63 CR{7-n} = CR[32+n*4:35+n*4]
64
65 Also note that for SVP64 the relationship for the sequential
66 numbering of elements is to the CR **fields** within
67 the CR Register, not to individual bits within the CR register.
68
69 # Instruction form and pseudocode
70
71 **DRAFT** Instruction format (use of MAJOR 19 not approved by
72 OPF ISA WG):
73
74 |0-5|6-10 |11|12-15|16-18|19-20|21-25 |26-30 |31|name |
75 |---|---- |--|-----|-----|-----|----- |----- |--|---- |
76 |19 |RT | |mask |BFA | |XO[0:4]|XO[5:9]|/ | |
77 |19 |RT |M |mask |BFA | 0 0 |XO[0:4]|0 mode |Rc|crrweird |
78 |19 |RA |M |mask |BF | 0 1 |XO[0:4]|0 mode |/ |mtcrweird |
79 |19 |BFT//|M |mask |BFA | 1 0 |XO[0:4]|0 mode |/ |crweirder |
80 |19 |BF |M |mask |BFA | 1 1 |XO[0:4]|0 mode |/ |crweird |
81
82 **crrweird**
83
84 mode is encoded in XO and is 4 bits
85
86 bit 19=0, bit 20=0
87
88 crrweird: RT, BFA, M, mask.mode
89
90 creg = CR{BFA}
91 n0 = mask[0] & (mode[0] == creg[0])
92 n1 = mask[1] & (mode[1] == creg[1])
93 n2 = mask[2] & (mode[2] == creg[2])
94 n3 = mask[3] & (mode[3] == creg[3])
95 result = n0|n1|n2|n3 if M else n0&n1&n2&n3
96 RT[63] = result # MSB0 numbering, 63 is LSB
97 If Rc:
98 CR0 = analyse(RT)
99
100 When used with SVP64 Prefixing this is a [[openpower/sv/normal]] SVP64 type operation and as
101 such can use Rc=1 and RC1 Data-dependent Mode capability
102
103 **mtcrweird**
104
105 bit 19=0, bit 20=1
106
107 mtcrweird: BF, RA, M, mask.mode
108
109 reg = (RA|0)
110 lsb = reg[63] # MSB0 numbering
111 n0 = mask[0] & (mode[0] == lsb)
112 n1 = mask[1] & (mode[1] == lsb)
113 n2 = mask[2] & (mode[2] == lsb)
114 n3 = mask[3] & (mode[3] == lsb)
115 result = n0 || n1 || n2 || n3
116 if M:
117 result |= CR{BF} & ~mask
118 CR{BF} = result
119
120 Note that when M=1 this operation is a Read-Modify-Write on the CR Field
121 BF. Masked-out bits of the 4-bit CR Field BF will not be changed when
122 M=1. Correspondingly when M=0 this operation is an overwrite: no read
123 of BF is required because the masked-out bits of the BF CR Field are
124 set to zero.
125
126 When used with SVP64 Prefixing this is a [[openpower/sv/cr_ops]] SVP64 type operation that has
127 3-bit Data-dependent and 3-bit Predicate-result capability
128 (BF is 3 bits)
129
130 **crweird**
131
132 bit 19=1, bit 20=0
133
134 crweird: BF, BFA, M, mask.mode
135
136 creg = CR{BFA}
137 n0 = mask[0] & (mode[0] == creg[0])
138 n1 = mask[1] & (mode[1] == creg[1])
139 n2 = mask[2] & (mode[2] == creg[2])
140 n3 = mask[3] & (mode[3] == creg[3])
141 result = n0 || n1 || n2 || n3
142 if M:
143 result |= CR{BF} & ~mask
144 CR{BF} = result
145
146 Note that when M=1 this operation is a Read-Modify-Write on the CR Field
147 BF. Masked-out bits of the 4-bit CR Field BF will not be changed when
148 M=1. Correspondingly when M=0 this operation is an overwrite: no read
149 of BF is required because the masked-out bits of the BF CR Field are
150 set to zero.
151
152 When used with SVP64 Prefixing this is a [[openpower/sv/cr_ops]] SVP64 type operation that has
153 3-bit Data-dependent and 3-bit Predicate-result capability
154 (BF is 3 bits)
155
156 **crweirder**
157
158 bit 19=1, bit 20=1
159
160 crweirder: BT, BFA, mask.mode
161
162 creg = CR{BFA}
163 n0 = mask[0] & (mode[0] == creg[0])
164 n1 = mask[1] & (mode[1] == creg[1])
165 n2 = mask[2] & (mode[2] == creg[2])
166 n3 = mask[3] & (mode[3] == creg[3])
167 BF = BT[2:4] # select CR
168 bit = BT[0:1] # select bit of CR
169 result = n0|n1|n2|n3 if M else n0&n1&n2&n3
170 CR{BF}[bit] = result
171
172 When used with SVP64 Prefixing this is a [[openpower/sv/cr_ops]] SVP64 type operation that has
173 5-bit Data-dependent and 5-bit Predicate-result capability
174 (BFT is 5 bits)
175
176 **Example Pseudo-ops:**
177
178 mtcri BF, mode mtcrweird BF, r0, 0, 0b1111.~mode
179 mtcrset BF, mask mtcrweird BF, r0, 1, mask.0b0000
180 mtcrclr BF, mask mtcrweird BF, r0, 1, mask.0b1111
181
182 # Vectorised versions
183
184 The name "weird" refers to a minor violation of SV rules when it comes to deriving the Vectorised versions of these instructions.
185
186 Normally the progression of the SV for-loop would move on to the next register.
187 Instead however in the scalar case these instructions **remain in the same register** and insert or transfer between **bits** of the scalar integer source or destination.
188
189 Further useful violation of the normal SV Elwidth override rules allows
190 for packing (or unpacking) of multiple CR test results into
191 (or out of) an Integer Element. Note
192 that the CR (source operand) elwidth field is utilised to determine the bit-
193 packing size (1/2/4/8 with remaining bits within the Integer element
194 set to zero) whilst the INT (dest operand) elwidth field still sets
195 the Integer element size as usual (8/16/32/default)
196
197 crrweird: RT, BB, mask.mode
198
199 for i in range(VL):
200 if BB.isvec:
201 creg = CR{BB+i}
202 else:
203 creg = CR{BB}
204 n0 = mask[0] & (mode[0] == creg[0])
205 n1 = mask[1] & (mode[1] == creg[1])
206 n2 = mask[2] & (mode[2] == creg[2])
207 n3 = mask[3] & (mode[3] == creg[3])
208 # OR or AND to a single bit
209 result = n0|n1|n2|n3 if M else n0&n1&n2&n3
210 if RT.isvec:
211 # TODO: RT.elwidth override to be also added here
212 # note, yes, really, the CR's elwidth field determines
213 # the bit-packing into the INT!
214 if BB.elwidth == 0b00:
215 # pack 1 result into 64-bit registers
216 iregs[RT+i][0..62] = 0
217 iregs[RT+i][63] = result # sets LSB to result
218 if BB.elwidth == 0b01:
219 # pack 2 results sequentially into INT registers
220 iregs[RT+i//2][0..61] = 0
221 iregs[RT+i//2][63-(i%2)] = result
222 if BB.elwidth == 0b10:
223 # pack 4 results sequentially into INT registers
224 iregs[RT+i//4][0..59] = 0
225 iregs[RT+i//4][63-(i%4)] = result
226 if BB.elwidth == 0b11:
227 # pack 8 results sequentially into INT registers
228 iregs[RT+i//8][0..55] = 0
229 iregs[RT+i//8][63-(i%8)] = result
230 else:
231 iregs[RT][63-i] = result # results also in scalar INT
232
233 Note that:
234
235 * in the scalar case the CR-Vector assessment
236 is stored bit-wise starting at the LSB of the
237 destination scalar INT
238 * in the INT-vector case the results are packed into LSBs
239 of the INT Elements, the packing arrangement depending on both
240 elwidth override settings.
241
242 # v3.1 setbc instructions
243
244 there are additional setb conditional instructions in v3.1 (p129)
245
246 RT = (CR[BI] == 1) ? 1 : 0
247
248 which also negate that, and also return -1 / 0. these are similar to crweird but not the same purpose. most notable is that crweird acts on CR fields rather than the entire 32 bit CR.
249
250 # Predication Examples
251
252 Take the following example:
253
254 r10 = 0b00010
255 sv.mtcrweird/dm=r10/dz cr8.v, 0, 0b0011.0000
256
257 Here, RA is zero, so the source input is zero. The destination
258 is CR Field 8, and the destination predicate mask indicates
259 to target the first two elements. Destination predicate zeroing is
260 enabled, and the destination predicate is only set in the 2nd bit.
261 mask is 0b0011, mode is all zeros.
262
263 Let us first consider what should go into element 0 (CR Field 8):
264
265 * The destination predicate bit is zero, and zeroing is enabled.
266 * Therefore, what is in the source is irrelevant: the result must
267 be zero.
268 * Therefore all four bits of CR Field 8 are therefore set to zero.
269
270 Now the second element, CR Field 9 (CR9):
271
272 * Bit 2 of the destination predicate, r10, is 1. Therefore the computation
273 of the result is relevant.
274 * RA is zero therefore bit 2 is zero. mask is 0b0011 and mode is 0b0000
275 * When calculating n0 thru n3 we get n0=1, n1=2, n2=0, n3=0
276 * Therefore, CR9 is set (using LSB0 ordering) to 0b0011, i.e. to mask.
277
278 It should be clear that this instruction uses bits of the integer
279 predicate to decide whether to set CR Fields to `(mask & ~mode)`
280 or to zero. Thus, in effect, it is the integer predicate that has
281 been copied into the CR Fields.
282
283 By using twin predication, zeroing, and inversion (sm=~r3, dm=r10) for example, it becomes possible to combine two Integers together in
284 order to set bits in CR Fields.
285 Likewise there are dozens of ways that CR Predicates can be used, on the
286 same sv.mtcrweird instruction.