Source file src/pkg/math/big/arith.go
1
2
3
4
5
6
7
8
9
10
11 package big
12
13 import "math/bits"
14
15
16 type Word uint
17
18 const (
19 _S = _W / 8
20
21 _W = bits.UintSize
22 _B = 1 << _W
23 _M = _B - 1
24 )
25
26
27
28
29
30
31
32
33
34
35
36
37
38
39
40
41
42
43
44 func mulWW_g(x, y Word) (z1, z0 Word) {
45 hi, lo := bits.Mul(uint(x), uint(y))
46 return Word(hi), Word(lo)
47 }
48
49
50 func mulAddWWW_g(x, y, c Word) (z1, z0 Word) {
51 hi, lo := bits.Mul(uint(x), uint(y))
52 var cc uint
53 lo, cc = bits.Add(lo, uint(c), 0)
54 return Word(hi + cc), Word(lo)
55 }
56
57
58
59 func nlz(x Word) uint {
60 return uint(bits.LeadingZeros(uint(x)))
61 }
62
63
64 func divWW_g(u1, u0, v Word) (q, r Word) {
65 qq, rr := bits.Div(uint(u1), uint(u0), uint(v))
66 return Word(qq), Word(rr)
67 }
68
69
70 func addVV_g(z, x, y []Word) (c Word) {
71
72 for i := 0; i < len(z) && i < len(x) && i < len(y); i++ {
73 zi, cc := bits.Add(uint(x[i]), uint(y[i]), uint(c))
74 z[i] = Word(zi)
75 c = Word(cc)
76 }
77 return
78 }
79
80
81 func subVV_g(z, x, y []Word) (c Word) {
82
83 for i := 0; i < len(z) && i < len(x) && i < len(y); i++ {
84 zi, cc := bits.Sub(uint(x[i]), uint(y[i]), uint(c))
85 z[i] = Word(zi)
86 c = Word(cc)
87 }
88 return
89 }
90
91
92 func addVW_g(z, x []Word, y Word) (c Word) {
93 c = y
94
95 for i := 0; i < len(z) && i < len(x); i++ {
96 zi, cc := bits.Add(uint(x[i]), uint(c), 0)
97 z[i] = Word(zi)
98 c = Word(cc)
99 }
100 return
101 }
102
103
104
105
106
107
108
109
110 func addVWlarge(z, x []Word, y Word) (c Word) {
111 c = y
112
113 for i := 0; i < len(z) && i < len(x); i++ {
114 if c == 0 {
115 copy(z[i:], x[i:])
116 return
117 }
118 zi, cc := bits.Add(uint(x[i]), uint(c), 0)
119 z[i] = Word(zi)
120 c = Word(cc)
121 }
122 return
123 }
124
125 func subVW_g(z, x []Word, y Word) (c Word) {
126 c = y
127
128 for i := 0; i < len(z) && i < len(x); i++ {
129 zi, cc := bits.Sub(uint(x[i]), uint(c), 0)
130 z[i] = Word(zi)
131 c = Word(cc)
132 }
133 return
134 }
135
136
137 func subVWlarge(z, x []Word, y Word) (c Word) {
138 c = y
139
140 for i := 0; i < len(z) && i < len(x); i++ {
141 if c == 0 {
142 copy(z[i:], x[i:])
143 return
144 }
145 zi, cc := bits.Sub(uint(x[i]), uint(c), 0)
146 z[i] = Word(zi)
147 c = Word(cc)
148 }
149 return
150 }
151
152 func shlVU_g(z, x []Word, s uint) (c Word) {
153 if s == 0 {
154 copy(z, x)
155 return
156 }
157 if len(z) == 0 {
158 return
159 }
160 s &= _W - 1
161 ŝ := _W - s
162 ŝ &= _W - 1
163 c = x[len(z)-1] >> ŝ
164 for i := len(z) - 1; i > 0; i-- {
165 z[i] = x[i]<<s | x[i-1]>>ŝ
166 }
167 z[0] = x[0] << s
168 return
169 }
170
171 func shrVU_g(z, x []Word, s uint) (c Word) {
172 if s == 0 {
173 copy(z, x)
174 return
175 }
176 if len(z) == 0 {
177 return
178 }
179 s &= _W - 1
180 ŝ := _W - s
181 ŝ &= _W - 1
182 c = x[0] << ŝ
183 for i := 0; i < len(z)-1; i++ {
184 z[i] = x[i]>>s | x[i+1]<<ŝ
185 }
186 z[len(z)-1] = x[len(z)-1] >> s
187 return
188 }
189
190 func mulAddVWW_g(z, x []Word, y, r Word) (c Word) {
191 c = r
192
193 for i := 0; i < len(z) && i < len(x); i++ {
194 c, z[i] = mulAddWWW_g(x[i], y, c)
195 }
196 return
197 }
198
199 func addMulVVW_g(z, x []Word, y Word) (c Word) {
200
201 for i := 0; i < len(z) && i < len(x); i++ {
202 z1, z0 := mulAddWWW_g(x[i], y, z[i])
203 lo, cc := bits.Add(uint(z0), uint(c), 0)
204 c, z[i] = Word(cc), Word(lo)
205 c += z1
206 }
207 return
208 }
209
210 func divWVW_g(z []Word, xn Word, x []Word, y Word) (r Word) {
211 r = xn
212 for i := len(z) - 1; i >= 0; i-- {
213 z[i], r = divWW_g(r, x[i], y)
214 }
215 return
216 }
217
View as plain text