• Home
  • Features
  • Pricing
  • Docs
  • Announcements
  • Sign In

moonbitlang / x / 939

21 Jul 2026 02:30AM UTC coverage: 84.504%. First build
939

Pull #280

github

web-flow
Merge 7553848b9 into 90bd61809
Pull Request #280: Optimize ChaCha with target-aware SIMD

72 of 171 new or added lines in 3 files covered. (42.11%)

2634 of 3117 relevant lines covered (84.5%)

269.81 hits per line

Source File
Press 'n' to go to next uncovered line, 'b' for previous

41.25
/crypto/simd.mbt
1
// Copyright 2025 International Digital Economy Academy
2
//
3
// Licensed under the Apache License, Version 2.0 (the "License");
4
// you may not use this file except in compliance with the License.
5
// You may obtain a copy of the License at
6
//
7
//     http://www.apache.org/licenses/LICENSE-2.0
8
//
9
// Unless required by applicable law or agreed to in writing, software
10
// distributed under the License is distributed on an "AS IS" BASIS,
11
// WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
12
// See the License for the specific language governing permissions and
13
// limitations under the License.
14

15
///|
16
#cfg(any(target="native", target="wasm"))
17
#inline
18
fn load_u32x16_be_into(
19
  bytes : FixedArray[Byte],
20
  byte_offset : Int,
21
  words : FixedArray[UInt],
22
) -> Unit {
23
  for group in 0..<4 {
×
24
    let value = @v128.v128_load(bytes, byte_offset + group * 16)
×
25
    let value = @v128.i8x16_shuffle(
×
26
      value, value, 3, 2, 1, 0, 7, 6, 5, 4, 11, 10, 9, 8, 15, 14, 13, 12,
27
    )
28
    let word_offset = group * 4
29
    words.unsafe_set(word_offset, @v128.i32x4_extract_lane(value, 0))
×
30
    words.unsafe_set(word_offset + 1, @v128.i32x4_extract_lane(value, 1))
×
31
    words.unsafe_set(word_offset + 2, @v128.i32x4_extract_lane(value, 2))
×
32
    words.unsafe_set(word_offset + 3, @v128.i32x4_extract_lane(value, 3))
×
33
  }
34
}
35

36
///|
37
#cfg(not(any(target="native", target="wasm")))
38
#inline
39
fn load_u32x16_be_into(
40
  bytes : FixedArray[Byte],
41
  byte_offset : Int,
42
  words : FixedArray[UInt],
43
) -> Unit {
44
  for word_offset in 0..<16 {
122✔
45
    let offset = byte_offset + word_offset * 4
1,952✔
46
    words.unsafe_set(
1,952✔
47
      word_offset,
48
      (bytes.unsafe_get(offset).to_uint() << 24) |
1,952✔
49
      (bytes.unsafe_get(offset + 1).to_uint() << 16) |
1,952✔
50
      (bytes.unsafe_get(offset + 2).to_uint() << 8) |
1,952✔
51
      bytes.unsafe_get(offset + 3).to_uint(),
1,952✔
52
    )
53
  }
54
}
55

56
///|
57
#cfg(any(target="native", target="wasm"))
58
#inline
59
fn load_i32x16_be_into(
60
  bytes : FixedArray[Byte],
61
  byte_offset : Int,
62
  words : FixedArray[Int],
63
) -> Unit {
64
  for group in 0..<4 {
×
65
    let value = @v128.v128_load(bytes, byte_offset + group * 16)
×
66
    let value = @v128.i8x16_shuffle(
×
67
      value, value, 3, 2, 1, 0, 7, 6, 5, 4, 11, 10, 9, 8, 15, 14, 13, 12,
68
    )
69
    let word_offset = group * 4
70
    words.unsafe_set(
×
71
      word_offset,
72
      @v128.i32x4_extract_lane(value, 0).reinterpret_as_int(),
×
73
    )
74
    words.unsafe_set(
×
75
      word_offset + 1,
76
      @v128.i32x4_extract_lane(value, 1).reinterpret_as_int(),
×
77
    )
78
    words.unsafe_set(
×
79
      word_offset + 2,
80
      @v128.i32x4_extract_lane(value, 2).reinterpret_as_int(),
×
81
    )
82
    words.unsafe_set(
×
83
      word_offset + 3,
84
      @v128.i32x4_extract_lane(value, 3).reinterpret_as_int(),
×
85
    )
86
  }
87
}
88

89
///|
90
#cfg(not(any(target="native", target="wasm")))
91
#inline
92
fn load_i32x16_be_into(
93
  bytes : FixedArray[Byte],
94
  byte_offset : Int,
95
  words : FixedArray[Int],
96
) -> Unit {
97
  for word_offset in 0..<16 {
534✔
98
    let offset = byte_offset + word_offset * 4
8,544✔
99
    words.unsafe_set(
8,544✔
100
      word_offset,
101
      (bytes.unsafe_get(offset).to_int() << 24) |
8,544✔
102
      (bytes.unsafe_get(offset + 1).to_int() << 16) |
8,544✔
103
      (bytes.unsafe_get(offset + 2).to_int() << 8) |
8,544✔
104
      bytes.unsafe_get(offset + 3).to_int(),
8,544✔
105
    )
106
  }
107
}
108

109
///|
110
#cfg(any(target="native", target="wasm"))
111
#inline
112
fn load_u32x16_le_into(
113
  bytes : FixedArray[Byte],
114
  byte_offset : Int,
115
  words : FixedArray[UInt],
116
) -> Unit {
117
  for group in 0..<4 {
×
118
    let value = @v128.v128_load(bytes, byte_offset + group * 16)
×
119
    let word_offset = group * 4
120
    words.unsafe_set(word_offset, @v128.i32x4_extract_lane(value, 0))
×
121
    words.unsafe_set(word_offset + 1, @v128.i32x4_extract_lane(value, 1))
×
122
    words.unsafe_set(word_offset + 2, @v128.i32x4_extract_lane(value, 2))
×
123
    words.unsafe_set(word_offset + 3, @v128.i32x4_extract_lane(value, 3))
×
124
  }
125
}
126

127
///|
128
#cfg(not(any(target="native", target="wasm")))
129
#inline
130
fn load_u32x16_le_into(
131
  bytes : FixedArray[Byte],
132
  byte_offset : Int,
133
  words : FixedArray[UInt],
134
) -> Unit {
135
  for word_offset in 0..<16 {
53✔
136
    let offset = byte_offset + word_offset * 4
848✔
137
    words.unsafe_set(
848✔
138
      word_offset,
139
      bytes.unsafe_get(offset).to_uint() |
848✔
140
      (bytes.unsafe_get(offset + 1).to_uint() << 8) |
848✔
141
      (bytes.unsafe_get(offset + 2).to_uint() << 16) |
848✔
142
      (bytes.unsafe_get(offset + 3).to_uint() << 24),
848✔
143
    )
144
  }
145
}
146

147
///|
148
#cfg(any(target="native", target="wasm"))
149
#inline
150
fn store_u32x4_le(
151
  words : FixedArray[UInt],
152
  word_offset : Int,
153
  bytes : FixedArray[Byte],
154
  byte_offset : Int,
155
) -> Unit {
156
  @v128.v128_store(
×
157
    bytes,
158
    byte_offset,
159
    @v128.i32x4_const(
×
160
      words.unsafe_get(word_offset),
×
161
      words.unsafe_get(word_offset + 1),
×
162
      words.unsafe_get(word_offset + 2),
×
163
      words.unsafe_get(word_offset + 3),
×
164
    ),
165
  )
166
}
167

168
///|
169
#cfg(not(any(target="native", target="wasm")))
170
#inline
171
fn store_u32x4_le(
172
  words : FixedArray[UInt],
173
  word_offset : Int,
174
  bytes : FixedArray[Byte],
175
  byte_offset : Int,
176
) -> Unit {
177
  for lane in 0..<4 {
16✔
178
    let word = words.unsafe_get(word_offset + lane)
64✔
179
    let offset = byte_offset + lane * 4
180
    bytes.unsafe_set(offset, word.to_byte())
64✔
181
    bytes.unsafe_set(offset + 1, (word >> 8).to_byte())
64✔
182
    bytes.unsafe_set(offset + 2, (word >> 16).to_byte())
64✔
183
    bytes.unsafe_set(offset + 3, (word >> 24).to_byte())
64✔
184
  }
185
}
186

187
///|
188
#cfg(any(target="native", target="wasm"))
189
fn xor_bytes_with_splat_in_place(
190
  bytes : FixedArray[Byte],
191
  length : Int,
192
  mask : Byte,
193
) -> Unit {
194
  let simd_end = length / 16 * 16
×
195
  let vector_mask = @v128.i8x16_splat(mask)
×
196
  for offset = 0; offset < simd_end; offset = offset + 16 {
×
197
    @v128.v128_load(bytes, offset)
×
198
    |> @v128.v128_xor(vector_mask)
×
199
    |> value => { @v128.v128_store(bytes, offset, value) }
×
200
  }
201
  for offset in simd_end..<length {
202
    bytes.unsafe_set(offset, bytes.unsafe_get(offset) ^ mask)
×
203
  }
204
}
205

206
///|
207
#cfg(any(target="native", target="wasm"))
208
#inline
209
fn xor_byte_ranges_in_place(
210
  bytes : FixedArray[Byte],
211
  byte_offset : Int,
212
  mask : FixedArray[Byte],
213
  mask_offset : Int,
214
  length : Int,
215
) -> Unit {
NEW
216
  let simd_end = length / 16 * 16
×
NEW
217
  for offset = 0; offset < simd_end; offset = offset + 16 {
×
NEW
218
    @v128.v128_store(
×
219
      bytes,
220
      byte_offset + offset,
NEW
221
      @v128.v128_xor(
×
NEW
222
        @v128.v128_load(bytes, byte_offset + offset),
×
NEW
223
        @v128.v128_load(mask, mask_offset + offset),
×
224
      ),
225
    )
226
  }
NEW
227
  for offset = simd_end; offset < length; offset = offset + 1 {
×
NEW
228
    bytes.unsafe_set(
×
229
      byte_offset + offset,
NEW
230
      bytes.unsafe_get(byte_offset + offset) ^
×
NEW
231
      mask.unsafe_get(mask_offset + offset),
×
232
    )
233
  }
234
}
235

236
///|
237
#cfg(not(any(target="native", target="wasm", target="js")))
238
#inline
239
fn xor_byte_ranges_in_place(
240
  bytes : FixedArray[Byte],
241
  byte_offset : Int,
242
  mask : FixedArray[Byte],
243
  mask_offset : Int,
244
  length : Int,
245
) -> Unit {
246
  for offset in 0..<length {
19✔
247
    bytes.unsafe_set(
1,216✔
248
      byte_offset + offset,
249
      bytes.unsafe_get(byte_offset + offset) ^
1,216✔
250
      mask.unsafe_get(mask_offset + offset),
1,216✔
251
    )
252
  }
253
}
254

255
///|
256
#cfg(not(any(target="native", target="wasm")))
257
fn xor_bytes_with_splat_in_place(
258
  bytes : FixedArray[Byte],
259
  length : Int,
260
  mask : Byte,
261
) -> Unit {
262
  for offset in 0..<length {
10✔
263
    bytes.unsafe_set(offset, bytes.unsafe_get(offset) ^ mask)
640✔
264
  }
265
}
STATUS · Troubleshooting · Open an Issue · Sales · Support · CAREERS · ENTERPRISE · START FREE TRIAL · SCHEDULE DEMO
ANNOUNCEMENTS · TWITTER · TOS & SLA · Supported CI Services · What's a CI service? · Automated Testing

© 2026 Coveralls, Inc