Skip to content

Commit 69741a8

Browse files
add caching to CborReader.PeekState()
1 parent 37cf2bd commit 69741a8

File tree

1 file changed

+20
-0
lines changed
  • src/libraries/System.Security.Cryptography.Encoding/tests/Cbor

1 file changed

+20
-0
lines changed

src/libraries/System.Security.Cryptography.Encoding/tests/Cbor/CborReader.cs

Lines changed: 20 additions & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -49,6 +49,7 @@ internal partial class CborReader
4949
private bool _isEvenNumberOfDataItemsRead = true; // required for indefinite-length map writes
5050
private Stack<(CborMajorType type, int bytesRead, bool isEvenNumberOfDataItemsWritten, ulong? remainingDataItems)>? _nestedDataItems;
5151
private bool _isTagContext = false; // true if reader is expecting a tagged value
52+
private CborReaderState _cachedState = CborReaderState.Unknown; // caches the current reader state
5253

5354
// stores a reusable List allocation for keeping ranges in the buffer
5455
private List<(int offset, int length)>? _rangeListAllocation = null;
@@ -62,6 +63,16 @@ internal CborReader(ReadOnlyMemory<byte> buffer)
6263
public int BytesRemaining => _buffer.Length;
6364

6465
public CborReaderState PeekState()
66+
{
67+
if (_cachedState == CborReaderState.Unknown)
68+
{
69+
_cachedState = PeekStateCore();
70+
}
71+
72+
return _cachedState;
73+
}
74+
75+
private CborReaderState PeekStateCore()
6576
{
6677
if (_remainingDataItems == 0)
6778
{
@@ -289,6 +300,11 @@ private void PopDataItem(CborMajorType expectedType)
289300
_nestedDataItems.Pop();
290301
_remainingDataItems = remainingItems;
291302
_isEvenNumberOfDataItemsRead = isEvenNumberOfDataItemsWritten;
303+
// Popping items from the stack can change the reader state
304+
// without necessarily needing to advance the buffer
305+
// (e.g. we're at the end of a definite-length collection).
306+
// We therefore need to invalidate the cache here.
307+
_cachedState = CborReaderState.Unknown;
292308
}
293309

294310
private void AdvanceDataItemCounters()
@@ -302,6 +318,8 @@ private void AdvanceBuffer(int length)
302318
{
303319
_buffer = _buffer.Slice(length);
304320
_bytesRead += length;
321+
// invalidate the state cache
322+
_cachedState = CborReaderState.Unknown;
305323
}
306324

307325
private void EnsureBuffer(int length)
@@ -373,6 +391,8 @@ private void RestoreCheckpoint(CborReaderCheckpoint checkpoint)
373391
_remainingDataItems = checkpoint.RemainingDataItems;
374392
_isEvenNumberOfDataItemsRead = checkpoint.IsEvenNumberOfDataItemsRead;
375393
_isTagContext = checkpoint.IsTagContext;
394+
// invalidate the state cache
395+
_cachedState = CborReaderState.Unknown;
376396
}
377397
}
378398

0 commit comments

Comments
 (0)