@@ -465,6 +465,12 @@ IsLocalOrArg(Operand *op)
465
465
return op -> kind == REG_LOCAL || op -> kind == REG_ARG || op -> kind == REG_TEMP ;
466
466
}
467
467
468
+ static bool
469
+ IsDirectImmediate (Operand * op )
470
+ {
471
+ return op && op -> kind == IMM_INT ;
472
+ }
473
+
468
474
static bool
469
475
IsImmediate (Operand * op )
470
476
{
@@ -3832,6 +3838,50 @@ OptimizePeepholes(IRList *irl)
3832
3838
}
3833
3839
}
3834
3840
3841
+ // check for consecutive math opcodes
3842
+ if (ir_next && ir_next -> opc == opc
3843
+ && ir -> dst == ir_next -> dst
3844
+ && !InstrSetsAnyFlags (ir )
3845
+ && ir -> cond == ir_next -> cond
3846
+ && IsDirectImmediate (ir -> src )
3847
+ && IsDirectImmediate (ir_next -> src )
3848
+ && !IsHwReg (ir -> dst )
3849
+ )
3850
+ {
3851
+ int newval ;
3852
+ bool merge = true;
3853
+ // check for mergeable immediate math operands
3854
+ switch (opc ) {
3855
+ case OPC_ADD :
3856
+ case OPC_SUB :
3857
+ newval = ir_next -> src -> val + ir -> src -> val ;
3858
+ break ;
3859
+ case OPC_SHL :
3860
+ case OPC_SAR :
3861
+ case OPC_SHR :
3862
+ newval = ir_next -> src -> val + ir -> src -> val ;
3863
+ if (newval > 0x1f ) {
3864
+ merge = false;
3865
+ }
3866
+ break ;
3867
+ case OPC_OR :
3868
+ newval = ir_next -> src -> val | ir -> src -> val ;
3869
+ break ;
3870
+ case OPC_AND :
3871
+ newval = ir_next -> src -> val & ir -> src -> val ;
3872
+ break ;
3873
+ default :
3874
+ merge = false;
3875
+ break ;
3876
+ }
3877
+ if (merge ) {
3878
+ ir_next -> src = NewImmediate (newval );
3879
+ DeleteIR (irl , ir );
3880
+ changed = 1 ;
3881
+ goto done ;
3882
+ }
3883
+ }
3884
+
3835
3885
// check for add a,b ;; mov b,a ;; isdead a
3836
3886
// becomes add b, a
3837
3887
@@ -5705,6 +5755,7 @@ typedef struct PeepholePattern {
5705
5755
#define OPERAND_ANY -1
5706
5756
#define COND_ANY -1
5707
5757
#define OPC_ANY -1
5758
+
5708
5759
#define MAX_OPERANDS_IN_PATTERN 16
5709
5760
5710
5761
#define PEEP_OPNUM_MASK 0x00ffffff
@@ -6886,7 +6937,7 @@ static int FixupQMux(int arg, IRList *irl, IR *ir)
6886
6937
}
6887
6938
6888
6939
/*
6889
- * sign extend followed by AND is sometimes redundant
6940
+ * sign extend followed by AND, GETBYTE, or GETWORD is sometimes redundant
6890
6941
*/
6891
6942
static PeepholePattern pat_shl_shr_and [] = {
6892
6943
{ COND_ANY , OPC_SHL , PEEP_OP_SET |0 , PEEP_OP_SET_IMM |1 , PEEP_FLAGS_NONE },
0 commit comments