Skip to content
New issue

Have a question about this project? Sign up for a free GitHub account to open an issue and contact its maintainers and the community.

By clicking “Sign up for GitHub”, you agree to our terms of service and privacy statement. We’ll occasionally send you account related emails.

Already on GitHub? Sign in to your account

Improve performance of re-used symmetric one shots #93124

Closed
wants to merge 4 commits into from

Conversation

vcsjones
Copy link
Member

@vcsjones vcsjones commented Oct 6, 2023

Today, when you use the symmetric one-shots to decrypt or decrypt, it creates a new lite cipher, uses it, then clean it up every time.

(Context: "lite cipher" is the internal facade over the platform's native encryption components)

Creating a lite cipher is expensive from various things like creating handles, validating keys and inputs, and simply the natural of the algorithm itself from activities like key expansion.

This change allows caching the lite cipher for the duration of the key, so long as the key doesn't change. If the key changes, then the lite cipher is invalidated.

The scenario this improves is this:

using Aes aes = aes.Create();
aes.Key = GetTheKey();
byte[] iv1 = RandomNumberGenerator.GetBytes(16);
byte[] iv2 = RandomNumberGenerator.GetBytes(16);
byte[] ciphertext1 = aes.EncryptCbc(plaintext1, iv1);
byte[] ciphertext2 = aes.EncryptCbc(plaintext2, iv2);
// N or more calls to EncryptCbc / DecryptCbc, etc.

Because the one-shots were previously more-or-less fully contained, they were thread safe - such that calling the one shots from a single instance of SymmetricAlgorithm would work and produce correct results. This is trait I would like to keep and I am not comfortable breaking. Because of this then, the caching uses interlocked exchanges of handles. Since we are only caching one instance at a given time, using an instance from multiple threads may not benefit from the cache. I think this is reasonable to keep the caching mechanism simple, and there is an easy developer workaround: pool an instance of the SymmetricAlgorithm.

This does mean though that there is a performance penalty, albeit a small one, for when the one-shot is used exactly once. The extra bookkeeping for the caching is wasted. However, it is far outweighed if you use it more than once.

Full data is below, but some examples:

Aes.EncryptCbc with a single call when from 579.0ns to 606.2ns.
Aes.EncryptCbc with three calls when from 1,395.5ns to 757.2ns.

TripleDES.EncryptCbc with a single call when from 11,311.6ns to 11,294.2ns (this "improvement" is within error)
TripleDES.EncryptCbc with three calls when from 33,826.3ns to 13,004.6ns.

The performance improvements can be substantial when it's used multiple times. For single uses, the performance loss is two Interlocked.Exchange calls.

This pull request addresses ECB and CBC only. Absent is CFB. CFB, because of feedback size, could be addressed differently, which is why I am leaving it out of this pull request. ECB and CBC are the far more common modes as well.

Benchmarks are in this Gist so they don't wrap funny in this comment. https://gist.github.com/vcsjones/b79889c4c6196bec50d783ff6e9aba0d

CBC benchmark source
ECB benchmark source

@vcsjones vcsjones added area-System.Security tenet-performance Performance related issue labels Oct 6, 2023
@ghost
Copy link

ghost commented Oct 6, 2023

Tagging subscribers to this area: @dotnet/area-system-security, @bartonjs, @vcsjones
See info in area-owners.md if you want to be subscribed.

Issue Details

Today, when you use the symmetric one-shots to decrypt or decrypt, it creates a new lite cipher, uses it, then clean it up every time.

(Context: "lite cipher" is the internal facade over the platform's native encryption components)

Creating a lite cipher is expensive from various things like creating handles, validating keys and inputs, and simply the natural of the algorithm itself from activities like key expansion.

This change allows caching the lite cipher for the duration of the key, so long as the key doesn't change. If the key changes, then the lite cipher is invalidated.

The scenario this improves is this:

using Aes aes = aes.Create();
aes.Key = GetTheKey();
byte[] iv1 = RandomNumberGenerator.GetBytes(16);
byte[] iv2 = RandomNumberGenerator.GetBytes(16);
byte[] ciphertext1 = aes.EncryptCbc(plaintext1, iv1);
byte[] ciphertext2 = aes.EncryptCbc(plaintext2, iv1);
// N or more calls to EncryptCbc / DecryptCbc, etc.

Because the one-shots were previously more-or-less fully contained, they were thread safe - such that calling the one shots from a single instance of SymmetricAlgorithm would work and produce correct results. This is trait I would like to keep and I am not comfortable breaking. Because of this then, the caching uses interlocked exchanges of handles. Since we are only caching one instance at a given time, using an instance from multiple threads may not benefit from the cache. I think this is reasonable to keep the caching mechanism simple, and there is an easy developer workaround: pool an instance of the SymmetricAlgorithm.

This does mean though that there is a performance penalty, albeit a small one, for when the one-shot is used exactly once. The extra bookkeeping for the caching is wasted. However, it is far outweighed if you use it more than once.

Full data is below, but some examples:

Aes.EncryptCbc with a single call when from 579.0ns to 606.2ns.
Aes.EncryptCbc with three calls when from 1,395.5ns to 757.2ns.

TripleDES.EncryptCbc with a single call when from 11,311.6ns to 11,294.2ns (this "improvement" is within error)
TripleDES.EncryptCbc with three calls when from 33,826.3ns to 13,004.6ns.

The performance improvements can be substantial when it's used multiple times. For single uses, the performance loss is two Interlocked.Exchange calls.

This pull request addresses ECB and CBC only. Absent is CFB. CFB, because of feedback size, could be addressed differently, which is why I am leaving it out of this pull request. ECB and CBC are the far more common modes as well.

CBC Benchmarks
Method Job Toolchain DataSize NumberOfOperations Mode Algorithm Mean Error StdDev Ratio Gen0 Allocated Alloc Ratio
Encrypt_Cbc_ToSpan Job-VPVYBA branch 16 1 PKCS7 Aes 606.2 ns 4.99 ns 4.67 ns 1.05 0.0658 416 B 1.08
Encrypt_Cbc_ToSpan Job-QKOWKL main 16 1 PKCS7 Aes 579.0 ns 2.76 ns 2.58 ns 1.00 0.0610 384 B 1.00
Decrypt_Cbc_ToSpan Job-VPVYBA branch 16 1 PKCS7 Aes 605.5 ns 3.22 ns 3.01 ns 1.01 0.0658 416 B 1.08
Decrypt_Cbc_ToSpan Job-QKOWKL main 16 1 PKCS7 Aes 596.8 ns 2.64 ns 2.47 ns 1.00 0.0610 384 B 1.00
Encrypt_Cbc_ToSpan Job-VPVYBA branch 16 1 PKCS7 DES 4,121.0 ns 6.31 ns 5.27 ns 1.01 0.0763 496 B 1.07
Encrypt_Cbc_ToSpan Job-QKOWKL main 16 1 PKCS7 DES 4,086.9 ns 4.03 ns 3.57 ns 1.00 0.0687 464 B 1.00
Decrypt_Cbc_ToSpan Job-VPVYBA branch 16 1 PKCS7 DES 3,960.6 ns 18.83 ns 17.62 ns 0.97 0.0763 496 B 1.07
Decrypt_Cbc_ToSpan Job-QKOWKL main 16 1 PKCS7 DES 4,094.3 ns 5.70 ns 5.33 ns 1.00 0.0687 464 B 1.00
Encrypt_Cbc_ToSpan Job-VPVYBA branch 16 1 PKCS7 RC2 1,992.9 ns 4.16 ns 3.69 ns 1.02 0.0725 456 B 1.08
Encrypt_Cbc_ToSpan Job-QKOWKL main 16 1 PKCS7 RC2 1,956.9 ns 5.76 ns 5.39 ns 1.00 0.0648 424 B 1.00
Decrypt_Cbc_ToSpan Job-VPVYBA branch 16 1 PKCS7 RC2 1,827.2 ns 3.67 ns 3.25 ns 1.01 0.0725 456 B 1.08
Decrypt_Cbc_ToSpan Job-QKOWKL main 16 1 PKCS7 RC2 1,813.8 ns 3.15 ns 2.80 ns 1.00 0.0668 424 B 1.00
Encrypt_Cbc_ToSpan Job-VPVYBA branch 16 1 PKCS7 TripleDES 11,294.2 ns 33.64 ns 31.46 ns 1.00 0.0763 496 B 1.07
Encrypt_Cbc_ToSpan Job-QKOWKL main 16 1 PKCS7 TripleDES 11,311.6 ns 23.85 ns 21.15 ns 1.00 0.0610 464 B 1.00
Decrypt_Cbc_ToSpan Job-VPVYBA branch 16 1 PKCS7 TripleDES 11,463.8 ns 48.48 ns 45.35 ns 1.03 0.0763 496 B 1.07
Decrypt_Cbc_ToSpan Job-QKOWKL main 16 1 PKCS7 TripleDES 11,145.7 ns 27.60 ns 25.82 ns 1.00 0.0610 464 B 1.00
Encrypt_Cbc_ToSpan Job-VPVYBA branch 16 2 PKCS7 Aes 678.0 ns 2.62 ns 2.45 ns 0.68 0.0658 416 B 0.81
Encrypt_Cbc_ToSpan Job-QKOWKL main 16 2 PKCS7 Aes 999.1 ns 4.37 ns 4.09 ns 1.00 0.0801 512 B 1.00
Decrypt_Cbc_ToSpan Job-VPVYBA branch 16 2 PKCS7 Aes 683.3 ns 3.93 ns 3.67 ns 0.67 0.0658 416 B 0.81
Decrypt_Cbc_ToSpan Job-QKOWKL main 16 2 PKCS7 Aes 1,026.2 ns 5.32 ns 4.97 ns 1.00 0.0801 512 B 1.00
Encrypt_Cbc_ToSpan Job-VPVYBA branch 16 2 PKCS7 DES 4,504.2 ns 5.09 ns 4.25 ns 0.57 0.0763 496 B 0.78
Encrypt_Cbc_ToSpan Job-QKOWKL main 16 2 PKCS7 DES 7,907.5 ns 14.60 ns 12.19 ns 1.00 0.0916 632 B 1.00
Decrypt_Cbc_ToSpan Job-VPVYBA branch 16 2 PKCS7 DES 4,317.5 ns 11.72 ns 10.39 ns 0.54 0.0763 496 B 0.78
Decrypt_Cbc_ToSpan Job-QKOWKL main 16 2 PKCS7 DES 8,013.6 ns 14.96 ns 12.49 ns 1.00 0.0916 632 B 1.00
Encrypt_Cbc_ToSpan Job-VPVYBA branch 16 2 PKCS7 RC2 2,484.2 ns 5.44 ns 5.09 ns 0.66 0.0839 528 B 0.87
Encrypt_Cbc_ToSpan Job-QKOWKL main 16 2 PKCS7 RC2 3,753.9 ns 3.20 ns 2.84 ns 1.00 0.0954 608 B 1.00
Decrypt_Cbc_ToSpan Job-VPVYBA branch 16 2 PKCS7 RC2 2,173.9 ns 6.72 ns 6.28 ns 0.63 0.0839 528 B 0.87
Decrypt_Cbc_ToSpan Job-QKOWKL main 16 2 PKCS7 RC2 3,461.0 ns 8.15 ns 7.22 ns 1.00 0.0954 608 B 1.00
Encrypt_Cbc_ToSpan Job-VPVYBA branch 16 2 PKCS7 TripleDES 12,109.4 ns 35.04 ns 32.78 ns 0.54 0.0763 496 B 0.78
Encrypt_Cbc_ToSpan Job-QKOWKL main 16 2 PKCS7 TripleDES 22,458.3 ns 84.69 ns 79.22 ns 1.00 0.0916 632 B 1.00
Decrypt_Cbc_ToSpan Job-VPVYBA branch 16 2 PKCS7 TripleDES 11,931.6 ns 43.27 ns 38.36 ns 0.54 0.0763 496 B 0.78
Decrypt_Cbc_ToSpan Job-QKOWKL main 16 2 PKCS7 TripleDES 22,154.8 ns 114.97 ns 101.92 ns 1.00 0.0916 632 B 1.00
Encrypt_Cbc_ToSpan Job-VPVYBA branch 16 3 PKCS7 Aes 757.2 ns 2.76 ns 2.58 ns 0.54 0.0658 416 B 0.65
Encrypt_Cbc_ToSpan Job-QKOWKL main 16 3 PKCS7 Aes 1,395.5 ns 12.07 ns 11.29 ns 1.00 0.1011 640 B 1.00
Decrypt_Cbc_ToSpan Job-VPVYBA branch 16 3 PKCS7 Aes 752.4 ns 4.49 ns 3.98 ns 0.51 0.0658 416 B 0.65
Decrypt_Cbc_ToSpan Job-QKOWKL main 16 3 PKCS7 Aes 1,471.2 ns 3.67 ns 3.43 ns 1.00 0.1011 640 B 1.00
Encrypt_Cbc_ToSpan Job-VPVYBA branch 16 3 PKCS7 DES 4,788.3 ns 13.78 ns 12.89 ns 0.40 0.0763 496 B 0.62
Encrypt_Cbc_ToSpan Job-QKOWKL main 16 3 PKCS7 DES 11,966.2 ns 11.29 ns 9.43 ns 1.00 0.1221 800 B 1.00
Decrypt_Cbc_ToSpan Job-VPVYBA branch 16 3 PKCS7 DES 4,657.8 ns 6.53 ns 5.78 ns 0.40 0.0763 496 B 0.62
Decrypt_Cbc_ToSpan Job-QKOWKL main 16 3 PKCS7 DES 11,743.8 ns 30.78 ns 27.28 ns 1.00 0.1221 800 B 1.00
Encrypt_Cbc_ToSpan Job-VPVYBA branch 16 3 PKCS7 RC2 2,953.6 ns 7.39 ns 6.91 ns 0.53 0.0954 600 B 0.76
Encrypt_Cbc_ToSpan Job-QKOWKL main 16 3 PKCS7 RC2 5,536.0 ns 12.08 ns 11.30 ns 1.00 0.1221 792 B 1.00
Decrypt_Cbc_ToSpan Job-VPVYBA branch 16 3 PKCS7 RC2 2,496.5 ns 3.43 ns 3.04 ns 0.49 0.0954 600 B 0.76
Decrypt_Cbc_ToSpan Job-QKOWKL main 16 3 PKCS7 RC2 5,096.1 ns 19.47 ns 18.21 ns 1.00 0.1221 792 B 1.00
Encrypt_Cbc_ToSpan Job-VPVYBA branch 16 3 PKCS7 TripleDES 13,004.6 ns 50.16 ns 39.16 ns 0.38 0.0763 496 B 0.62
Encrypt_Cbc_ToSpan Job-QKOWKL main 16 3 PKCS7 TripleDES 33,826.3 ns 100.39 ns 88.99 ns 1.00 0.1221 800 B 1.00
Decrypt_Cbc_ToSpan Job-VPVYBA branch 16 3 PKCS7 TripleDES 12,696.4 ns 61.61 ns 54.62 ns 0.38 0.0763 496 B 0.62
Decrypt_Cbc_ToSpan Job-QKOWKL main 16 3 PKCS7 TripleDES 33,138.3 ns 115.95 ns 108.46 ns 1.00 0.1221 800 B 1.00
ECB Benchmarks
Method Job Toolchain DataSize NumberOfOperations Mode Algorithm Mean Error StdDev Ratio Gen0 Allocated Alloc Ratio
Encrypt_Ecb_ToSpan Job-VPVYBA branch 16 1 PKCS7 Aes 572.5 ns 2.21 ns 1.96 ns 1.02 0.0658 416 B 1.08
Encrypt_Ecb_ToSpan Job-QKOWKL main 16 1 PKCS7 Aes 561.4 ns 2.82 ns 2.64 ns 1.00 0.0610 384 B 1.00
DecryptEcb_ToSpan Job-VPVYBA branch 16 1 PKCS7 Aes 586.5 ns 4.27 ns 4.00 ns 1.02 0.0658 416 B 1.08
DecryptEcb_ToSpan Job-QKOWKL main 16 1 PKCS7 Aes 572.4 ns 3.30 ns 3.08 ns 1.00 0.0610 384 B 1.00
Encrypt_Ecb_ToSpan Job-VPVYBA branch 16 1 PKCS7 DES 3,987.4 ns 4.04 ns 3.78 ns 1.03 0.0763 496 B 1.07
Encrypt_Ecb_ToSpan Job-QKOWKL main 16 1 PKCS7 DES 3,858.4 ns 5.13 ns 4.55 ns 1.00 0.0687 464 B 1.00
DecryptEcb_ToSpan Job-VPVYBA branch 16 1 PKCS7 DES 3,936.6 ns 9.21 ns 8.17 ns 1.01 0.0763 496 B 1.07
DecryptEcb_ToSpan Job-QKOWKL main 16 1 PKCS7 DES 3,886.0 ns 9.01 ns 7.52 ns 1.00 0.0687 464 B 1.00
Encrypt_Ecb_ToSpan Job-VPVYBA branch 16 1 PKCS7 RC2 1,831.0 ns 3.45 ns 2.88 ns 1.01 0.0725 456 B 1.08
Encrypt_Ecb_ToSpan Job-QKOWKL main 16 1 PKCS7 RC2 1,813.0 ns 3.39 ns 2.83 ns 1.00 0.0668 424 B 1.00
DecryptEcb_ToSpan Job-VPVYBA branch 16 1 PKCS7 RC2 1,708.4 ns 3.00 ns 2.81 ns 1.01 0.0725 456 B 1.08
DecryptEcb_ToSpan Job-QKOWKL main 16 1 PKCS7 RC2 1,693.1 ns 5.26 ns 4.92 ns 1.00 0.0668 424 B 1.00
Encrypt_Ecb_ToSpan Job-VPVYBA branch 16 1 PKCS7 TripleDES 11,218.4 ns 34.75 ns 32.51 ns 1.02 0.0763 496 B 1.07
Encrypt_Ecb_ToSpan Job-QKOWKL main 16 1 PKCS7 TripleDES 11,007.1 ns 44.17 ns 41.31 ns 1.00 0.0610 464 B 1.00
DecryptEcb_ToSpan Job-VPVYBA branch 16 1 PKCS7 TripleDES 10,853.4 ns 50.29 ns 47.04 ns 0.96 0.0763 496 B 1.07
DecryptEcb_ToSpan Job-QKOWKL main 16 1 PKCS7 TripleDES 11,289.6 ns 23.50 ns 19.62 ns 1.00 0.0610 464 B 1.00
Encrypt_Ecb_ToSpan Job-VPVYBA branch 16 2 PKCS7 Aes 660.3 ns 5.69 ns 5.32 ns 0.69 0.0658 416 B 0.81
Encrypt_Ecb_ToSpan Job-QKOWKL main 16 2 PKCS7 Aes 960.1 ns 6.02 ns 5.64 ns 1.00 0.0811 512 B 1.00
DecryptEcb_ToSpan Job-VPVYBA branch 16 2 PKCS7 Aes 665.8 ns 3.13 ns 2.45 ns 0.67 0.0658 416 B 0.81
DecryptEcb_ToSpan Job-QKOWKL main 16 2 PKCS7 Aes 986.4 ns 4.80 ns 4.49 ns 1.00 0.0801 512 B 1.00
Encrypt_Ecb_ToSpan Job-VPVYBA branch 16 2 PKCS7 DES 4,334.5 ns 6.67 ns 5.91 ns 0.56 0.0763 496 B 0.78
Encrypt_Ecb_ToSpan Job-QKOWKL main 16 2 PKCS7 DES 7,709.4 ns 5.02 ns 3.92 ns 1.00 0.0916 632 B 1.00
DecryptEcb_ToSpan Job-VPVYBA branch 16 2 PKCS7 DES 4,196.8 ns 3.90 ns 3.26 ns 0.54 0.0763 496 B 0.78
DecryptEcb_ToSpan Job-QKOWKL main 16 2 PKCS7 DES 7,776.3 ns 13.75 ns 12.19 ns 1.00 0.0916 632 B 1.00
Encrypt_Ecb_ToSpan Job-VPVYBA branch 16 2 PKCS7 RC2 2,273.5 ns 3.72 ns 3.48 ns 0.66 0.0839 528 B 0.87
Encrypt_Ecb_ToSpan Job-QKOWKL main 16 2 PKCS7 RC2 3,461.7 ns 7.17 ns 6.71 ns 1.00 0.0954 608 B 1.00
DecryptEcb_ToSpan Job-VPVYBA branch 16 2 PKCS7 RC2 2,037.3 ns 3.80 ns 3.37 ns 0.63 0.0839 528 B 0.87
DecryptEcb_ToSpan Job-QKOWKL main 16 2 PKCS7 RC2 3,236.9 ns 5.67 ns 5.31 ns 1.00 0.0954 608 B 1.00
Encrypt_Ecb_ToSpan Job-VPVYBA branch 16 2 PKCS7 TripleDES 12,035.6 ns 56.44 ns 52.80 ns 0.54 0.0763 496 B 0.78
Encrypt_Ecb_ToSpan Job-QKOWKL main 16 2 PKCS7 TripleDES 22,137.7 ns 72.31 ns 67.64 ns 1.00 0.0916 632 B 1.00
DecryptEcb_ToSpan Job-VPVYBA branch 16 2 PKCS7 TripleDES 11,652.6 ns 29.61 ns 26.25 ns 0.53 0.0763 496 B 0.78
DecryptEcb_ToSpan Job-QKOWKL main 16 2 PKCS7 TripleDES 22,164.3 ns 57.66 ns 53.93 ns 1.00 0.0916 632 B 1.00
Encrypt_Ecb_ToSpan Job-VPVYBA branch 16 3 PKCS7 Aes 708.8 ns 2.30 ns 2.15 ns 0.53 0.0658 416 B 0.65
Encrypt_Ecb_ToSpan Job-QKOWKL main 16 3 PKCS7 Aes 1,344.8 ns 16.80 ns 15.72 ns 1.00 0.1011 640 B 1.00
DecryptEcb_ToSpan Job-VPVYBA branch 16 3 PKCS7 Aes 725.8 ns 4.55 ns 4.26 ns 0.52 0.0658 416 B 0.65
DecryptEcb_ToSpan Job-QKOWKL main 16 3 PKCS7 Aes 1,387.8 ns 13.76 ns 12.87 ns 1.00 0.1011 640 B 1.00
Encrypt_Ecb_ToSpan Job-VPVYBA branch 16 3 PKCS7 DES 4,443.4 ns 5.53 ns 4.31 ns 0.39 0.0763 496 B 0.62
Encrypt_Ecb_ToSpan Job-QKOWKL main 16 3 PKCS7 DES 11,420.1 ns 16.38 ns 15.32 ns 1.00 0.1221 800 B 1.00
DecryptEcb_ToSpan Job-VPVYBA branch 16 3 PKCS7 DES 4,508.5 ns 3.28 ns 2.91 ns 0.41 0.0763 496 B 0.62
DecryptEcb_ToSpan Job-QKOWKL main 16 3 PKCS7 DES 11,072.3 ns 16.52 ns 15.45 ns 1.00 0.1221 800 B 1.00
Encrypt_Ecb_ToSpan Job-VPVYBA branch 16 3 PKCS7 RC2 2,687.7 ns 6.07 ns 5.68 ns 0.53 0.0954 600 B 0.76
Encrypt_Ecb_ToSpan Job-QKOWKL main 16 3 PKCS7 RC2 5,088.6 ns 10.13 ns 8.98 ns 1.00 0.1221 792 B 1.00
DecryptEcb_ToSpan Job-VPVYBA branch 16 3 PKCS7 RC2 2,330.7 ns 4.45 ns 3.95 ns 0.49 0.0954 600 B 0.76
DecryptEcb_ToSpan Job-QKOWKL main 16 3 PKCS7 RC2 4,758.3 ns 12.44 ns 11.03 ns 1.00 0.1221 792 B 1.00
Encrypt_Ecb_ToSpan Job-VPVYBA branch 16 3 PKCS7 TripleDES 12,663.7 ns 35.35 ns 33.06 ns 0.38 0.0763 496 B 0.62
Encrypt_Ecb_ToSpan Job-QKOWKL main 16 3 PKCS7 TripleDES 33,229.1 ns 215.92 ns 191.41 ns 1.00 0.1221 800 B 1.00
DecryptEcb_ToSpan Job-VPVYBA branch 16 3 PKCS7 TripleDES 12,796.3 ns 70.03 ns 65.50 ns 0.39 0.0763 496 B 0.62
DecryptEcb_ToSpan Job-QKOWKL main 16 3 PKCS7 TripleDES 32,748.0 ns 93.27 ns 87.24 ns 1.00 0.1221 800 B 1.00

CBC benchmark source
ECB benchmark source

Author: vcsjones
Assignees: -
Labels:

area-System.Security, tenet-performance

Milestone: -

@ghost ghost assigned vcsjones Oct 6, 2023
@vcsjones vcsjones marked this pull request as ready for review October 6, 2023 19:19
@vcsjones vcsjones marked this pull request as draft October 6, 2023 20:51
Comment on lines +54 to +55
base.Key = value;
InvalidateOneShotAlgorithms();
Copy link
Member

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

  • This instance has been used, so there's a cached lite-cipher for the mode we care about.
  • Thread A calls into set_Key, hasn't yet made it to updating the field
  • Thread B starts encrypting (or decrypting, whatever), something long. Gigabyteish. Still has k0
  • Thread A makes it out to InvalidateOneShotAlgorithms. get_Key will now return k1
  • Thread B finishes. The field is null, so it puts back the instance it used at k0.
  • As long as parallel ops never happen again, the cache stays at k0 from one-borrow one-return.

Right?

Copy link
Member Author

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

Ah, right, yep.

@vcsjones
Copy link
Member Author

vcsjones commented Oct 6, 2023

Okay, going to close this for now, as the threading part needs a bit of work. Will re-open when that's in better shape, with new benchmarks.

@vcsjones vcsjones closed this Oct 6, 2023
@ghost ghost locked as resolved and limited conversation to collaborators Nov 6, 2023
Sign up for free to subscribe to this conversation on GitHub. Already have an account? Sign in.
Labels
Projects
None yet
Development

Successfully merging this pull request may close these issues.

2 participants