@@ -18,6 +18,7 @@ import (
18
18
"cmd/compile/internal/types"
19
19
"cmd/internal/obj"
20
20
"cmd/internal/obj/arm"
21
+ "internal/abi"
21
22
)
22
23
23
24
// loadByType returns the load instruction of the given type.
@@ -712,18 +713,167 @@ func ssaGenValue(s *ssagen.State, v *ssa.Value) {
712
713
p .To .Name = obj .NAME_EXTERN
713
714
// AuxInt encodes how many buffer entries we need.
714
715
p .To .Sym = ir .Syms .GCWriteBarrier [v .AuxInt - 1 ]
715
- case ssa .OpARMLoweredPanicBoundsA , ssa .OpARMLoweredPanicBoundsB , ssa .OpARMLoweredPanicBoundsC :
716
- p := s .Prog (obj .ACALL )
717
- p .To .Type = obj .TYPE_MEM
718
- p .To .Name = obj .NAME_EXTERN
719
- p .To .Sym = ssagen .BoundsCheckFunc [v .AuxInt ]
720
- s .UseArgs (8 ) // space used in callee args area by assembly stubs
721
- case ssa .OpARMLoweredPanicExtendA , ssa .OpARMLoweredPanicExtendB , ssa .OpARMLoweredPanicExtendC :
722
- p := s .Prog (obj .ACALL )
716
+
717
+ case ssa .OpARMLoweredPanicBoundsRR , ssa .OpARMLoweredPanicBoundsRC , ssa .OpARMLoweredPanicBoundsCR , ssa .OpARMLoweredPanicBoundsCC ,
718
+ ssa .OpARMLoweredPanicExtendRR , ssa .OpARMLoweredPanicExtendRC :
719
+ // Compute the constant we put in the PCData entry for this call.
720
+ code , signed := ssa .BoundsKind (v .AuxInt ).Code ()
721
+ xIsReg := false
722
+ yIsReg := false
723
+ xVal := 0
724
+ yVal := 0
725
+ extend := false
726
+ switch v .Op {
727
+ case ssa .OpARMLoweredPanicBoundsRR :
728
+ xIsReg = true
729
+ xVal = int (v .Args [0 ].Reg () - arm .REG_R0 )
730
+ yIsReg = true
731
+ yVal = int (v .Args [1 ].Reg () - arm .REG_R0 )
732
+ case ssa .OpARMLoweredPanicExtendRR :
733
+ extend = true
734
+ xIsReg = true
735
+ hi := int (v .Args [0 ].Reg () - arm .REG_R0 )
736
+ lo := int (v .Args [1 ].Reg () - arm .REG_R0 )
737
+ xVal = hi << 2 + lo // encode 2 register numbers
738
+ yIsReg = true
739
+ yVal = int (v .Args [2 ].Reg () - arm .REG_R0 )
740
+ case ssa .OpARMLoweredPanicBoundsRC :
741
+ xIsReg = true
742
+ xVal = int (v .Args [0 ].Reg () - arm .REG_R0 )
743
+ c := v .Aux .(ssa.PanicBoundsC ).C
744
+ if c >= 0 && c <= abi .BoundsMaxConst {
745
+ yVal = int (c )
746
+ } else {
747
+ // Move constant to a register
748
+ yIsReg = true
749
+ if yVal == xVal {
750
+ yVal = 1
751
+ }
752
+ p := s .Prog (arm .AMOVW )
753
+ p .From .Type = obj .TYPE_CONST
754
+ p .From .Offset = c
755
+ p .To .Type = obj .TYPE_REG
756
+ p .To .Reg = arm .REG_R0 + int16 (yVal )
757
+ }
758
+ case ssa .OpARMLoweredPanicExtendRC :
759
+ extend = true
760
+ xIsReg = true
761
+ hi := int (v .Args [0 ].Reg () - arm .REG_R0 )
762
+ lo := int (v .Args [1 ].Reg () - arm .REG_R0 )
763
+ xVal = hi << 2 + lo // encode 2 register numbers
764
+ c := v .Aux .(ssa.PanicBoundsC ).C
765
+ if c >= 0 && c <= abi .BoundsMaxConst {
766
+ yVal = int (c )
767
+ } else {
768
+ // Move constant to a register
769
+ for yVal == hi || yVal == lo {
770
+ yVal ++
771
+ }
772
+ p := s .Prog (arm .AMOVW )
773
+ p .From .Type = obj .TYPE_CONST
774
+ p .From .Offset = c
775
+ p .To .Type = obj .TYPE_REG
776
+ p .To .Reg = arm .REG_R0 + int16 (yVal )
777
+ }
778
+ case ssa .OpARMLoweredPanicBoundsCR :
779
+ yIsReg = true
780
+ yVal := int (v .Args [0 ].Reg () - arm .REG_R0 )
781
+ c := v .Aux .(ssa.PanicBoundsC ).C
782
+ if c >= 0 && c <= abi .BoundsMaxConst {
783
+ xVal = int (c )
784
+ } else if signed && int64 (int32 (c )) == c || ! signed && int64 (uint32 (c )) == c {
785
+ // Move constant to a register
786
+ xIsReg = true
787
+ if xVal == yVal {
788
+ xVal = 1
789
+ }
790
+ p := s .Prog (arm .AMOVW )
791
+ p .From .Type = obj .TYPE_CONST
792
+ p .From .Offset = c
793
+ p .To .Type = obj .TYPE_REG
794
+ p .To .Reg = arm .REG_R0 + int16 (xVal )
795
+ } else {
796
+ // Move constant to two registers
797
+ extend = true
798
+ xIsReg = true
799
+ hi := 0
800
+ lo := 1
801
+ if hi == yVal {
802
+ hi = 2
803
+ }
804
+ if lo == yVal {
805
+ lo = 2
806
+ }
807
+ xVal = hi << 2 + lo
808
+ p := s .Prog (arm .AMOVW )
809
+ p .From .Type = obj .TYPE_CONST
810
+ p .From .Offset = c >> 32
811
+ p .To .Type = obj .TYPE_REG
812
+ p .To .Reg = arm .REG_R0 + int16 (hi )
813
+ p = s .Prog (arm .AMOVW )
814
+ p .From .Type = obj .TYPE_CONST
815
+ p .From .Offset = int64 (int32 (c ))
816
+ p .To .Type = obj .TYPE_REG
817
+ p .To .Reg = arm .REG_R0 + int16 (lo )
818
+ }
819
+ case ssa .OpARMLoweredPanicBoundsCC :
820
+ c := v .Aux .(ssa.PanicBoundsCC ).Cx
821
+ if c >= 0 && c <= abi .BoundsMaxConst {
822
+ xVal = int (c )
823
+ } else if signed && int64 (int32 (c )) == c || ! signed && int64 (uint32 (c )) == c {
824
+ // Move constant to a register
825
+ xIsReg = true
826
+ p := s .Prog (arm .AMOVW )
827
+ p .From .Type = obj .TYPE_CONST
828
+ p .From .Offset = c
829
+ p .To .Type = obj .TYPE_REG
830
+ p .To .Reg = arm .REG_R0 + int16 (xVal )
831
+ } else {
832
+ // Move constant to two registers
833
+ extend = true
834
+ xIsReg = true
835
+ hi := 0
836
+ lo := 1
837
+ xVal = hi << 2 + lo
838
+ p := s .Prog (arm .AMOVW )
839
+ p .From .Type = obj .TYPE_CONST
840
+ p .From .Offset = c >> 32
841
+ p .To .Type = obj .TYPE_REG
842
+ p .To .Reg = arm .REG_R0 + int16 (hi )
843
+ p = s .Prog (arm .AMOVW )
844
+ p .From .Type = obj .TYPE_CONST
845
+ p .From .Offset = int64 (int32 (c ))
846
+ p .To .Type = obj .TYPE_REG
847
+ p .To .Reg = arm .REG_R0 + int16 (lo )
848
+ }
849
+ c = v .Aux .(ssa.PanicBoundsCC ).Cy
850
+ if c >= 0 && c <= abi .BoundsMaxConst {
851
+ yVal = int (c )
852
+ } else {
853
+ // Move constant to a register
854
+ yIsReg = true
855
+ yVal = 2
856
+ p := s .Prog (arm .AMOVW )
857
+ p .From .Type = obj .TYPE_CONST
858
+ p .From .Offset = c
859
+ p .To .Type = obj .TYPE_REG
860
+ p .To .Reg = arm .REG_R0 + int16 (yVal )
861
+ }
862
+ }
863
+ c := abi .BoundsEncode (code , signed , xIsReg , yIsReg , xVal , yVal )
864
+
865
+ p := s .Prog (obj .APCDATA )
866
+ p .From .SetConst (abi .PCDATA_PanicBounds )
867
+ p .To .SetConst (int64 (c ))
868
+ p = s .Prog (obj .ACALL )
723
869
p .To .Type = obj .TYPE_MEM
724
870
p .To .Name = obj .NAME_EXTERN
725
- p .To .Sym = ssagen .ExtendCheckFunc [v .AuxInt ]
726
- s .UseArgs (12 ) // space used in callee args area by assembly stubs
871
+ if extend {
872
+ p .To .Sym = ir .Syms .PanicExtend
873
+ } else {
874
+ p .To .Sym = ir .Syms .PanicBounds
875
+ }
876
+
727
877
case ssa .OpARMDUFFZERO :
728
878
p := s .Prog (obj .ADUFFZERO )
729
879
p .To .Type = obj .TYPE_MEM
0 commit comments