11. The -g option now causes optimisation of the output compiled C to be
turned off, and adds comments to the output file the same way -c does.
-12. Added new optimiser idioms [cxorand16] and [cxorand32] for situations
- where AND and XOR together are used to simulate AND and bitwise-not;
+
+12. Added more optimiser idioms: [cxorand16], [cxorand32], [cfoldintoorinand],
+ [or16and], [xor16and], [lshift32half], [rshiftoutofneg], [andoutofneg];
also generalised the idiom-matching code to compare 16-bit and 32-bit
constants as equal if they have the same value, and fixed some typos in
the current 16-bit complement idioms.
(#{1}1 == #{1}2)->(#{x1 == x2}0)
(#{1}1 != #{1}2)->(#{x1 != x2}0)
+; Reducing constants inside a C or operation can help to recognize idioms
+[cfoldintoorinand]
+(((_1) | #{1}2) & #{1}3)->(((_1) | #{x2 & x3}0) & _3)
; Binary bitwise optimizations
[cbinand]
((?32(_{!(c&1431655765LU)}2|_{!(c&2863311530LU)}1))&
#{!(x&2863311530LU)&&iselect(x,1431655765LU)==xselx(iselect(x,1431655765LU))}3
)->(((_2 >> #1) ^ _1) & _3)
-
+
; Bitwise complements. (The INTERCAL which ultimately leads to cases 3 and 4
; is not the most efficient way to do this, by the way.)
[cnot1]
((_1~#1431655765)$_2)->(((_1�)<<#1)|(#0$_2))
[selectmingle4]
(_1$(_2~#2863311530))->(((_2�)>>#1)|(_1$#0))
+[selectmingle5]
+((_{!(c&4294901760UL)}1$_{!(c&4294901760UL)}2)~#3579139412)
+->((_1耀)|(_2>>#1))
+
+; special cases of V16/?16; the top bit was 0, so becomes equal to the
+; bottom bit
+[or16and]
+((V16 _{!(c&4294934528UL)}1)耀)->((_1)<<#15)
+[xor16and]
+((?16 _{!(c&4294934528UL)}1)耀)->((_1)<<#15)
; Shifts
->((((_1>>#{r}0)~#{iselect(x3>>(r*2+1),1431655765LU)}0)
<<#{setbitcount(x3&((2LU<<(r*2))-1))}0)|#{iselect(mingle(x4,x2),x3)}0)
>
+
+
; 32-bit leftshift by 1; there are 8 ways to write this.
[lshift32by1]
(((_1�)<<#1)|((_1�)<<#1))->((_1�)<<#1)
(((_1�)<<#1)|((#1431655765&_1)<<#1))->((_1�)<<#1)
(((#715827882&_1)<<#1)|((_1�)<<#1))->((_1�)<<#1)
(((#715827882&_1)<<#1)|((#1431655765&_1)<<#1))->((_1�)<<#1)
+
+; a weird part of a leftshift
+[lshift32half]
+(#0$((:1�)~#715827883))->((:1�)<<#1)
+
+; Move rshift, AND out of neg
+[rshiftoutofneg]
+(~16 (.1 >> #{1}2))->(((~16 .1) >> _2) | #32768)
+(~32 (:1 >> #{1}2))->(((~32 :1) >> _2) | #2147483648)
+[andoutofneg]
+(~16 (.1 & #{1}2))->(((~16 .1) & _2) | #{(~x2)&65535}0)
+(~32 (:1 & #{1}2))->(((~32 :1) & _2) | #{~x2}0)
+
; Move AND inside shifts, and OR and XOR outside shifts
[andintoshift]
((_1 << #{1}2) & #{1}3)->((_1 & #{x3>>x2}0) << _2)
; Thanks to Joris Huizer for suggesting the idea behind the next one;
; this is a more general idiom than the suggested [triplenot].
[redundantdoublenot]
-(!(!(_{c==1}1)))->(_1)
\ No newline at end of file
+(!(!(_{c==1}1)))->(_1)