@@ -203,12 +203,18 @@ void CFB_CipherTemplate<BASE>::ProcessData(byte *outString, const byte *inString
203
203
//
204
204
// Also see https://github.com/weidai11/cryptopp/issues/683.
205
205
//
206
- #if !defined(__arm__)
207
- unsigned int alignment = policy.GetAlignment ();
208
- if (policy.CanIterate () && length >= bytesPerIteration && IsAlignedOn (outString, alignment))
206
+ // UPDATE: It appears the issue is related to alignment checks. When we made
207
+ // the alignment check result volatile GCC and Clang stopped
208
+ // short-circuiting the transform, which is what we wanted. I suspect
209
+ // there's a little more to the issue, but we can enable the block again.
210
+
211
+ const unsigned int alignment = policy.GetAlignment ();
212
+ volatile bool isAligned = IsAlignedOn (outString, alignment);
213
+ if (policy.CanIterate () && length >= bytesPerIteration && isAligned)
209
214
{
215
+ isAligned &= IsAlignedOn (inString, alignment);
210
216
const CipherDir cipherDir = GetCipherDir (*this );
211
- if (IsAlignedOn (inString, alignment) )
217
+ if (isAligned )
212
218
policy.Iterate (outString, inString, cipherDir, length / bytesPerIteration);
213
219
else
214
220
{
@@ -226,11 +232,6 @@ void CFB_CipherTemplate<BASE>::ProcessData(byte *outString, const byte *inString
226
232
// to use ptrdiff_t when subtracting pointers. We believe the relevant code paths
227
233
// are clean.
228
234
//
229
- // There are two remaining open questions. The first is aliasing rules. Char-types
230
- // are not bound by aliasing rules so we are OK. The second is array const-ness.
231
- // The arrays are created in datatest.cpp and they are non-const. Since the original
232
- // objects are non-const we are OK casting const-ness away as buffers are twiddled.
233
- //
234
235
// One workaround is a distinct and aligned temporary buffer. It [mostly] works
235
236
// as expected but requires an extra allocation (casts not shown):
236
237
//
@@ -241,11 +242,11 @@ void CFB_CipherTemplate<BASE>::ProcessData(byte *outString, const byte *inString
241
242
memcpy (outString, inString, length);
242
243
policy.Iterate (outString, outString, cipherDir, length / bytesPerIteration);
243
244
}
244
- inString = PtrAdd (inString, length - length % bytesPerIteration);
245
- outString = PtrAdd (outString, length - length % bytesPerIteration);
246
- length %= bytesPerIteration;
245
+ const size_t remainder = length % bytesPerIteration;
246
+ inString = PtrAdd (inString, length - remainder );
247
+ outString = PtrAdd (outString, length - remainder );
248
+ length = remainder ;
247
249
}
248
- #endif
249
250
250
251
while (length >= bytesPerIteration)
251
252
{
0 commit comments