Skip to content

Commit 6b0c34e

Browse files
committed
Reader API finished
1 parent c539c97 commit 6b0c34e

File tree

2 files changed

+39
-84
lines changed

2 files changed

+39
-84
lines changed

src/MemoryPack.Core/Formatters/BigIntegerFormatter.cs

Lines changed: 9 additions & 4 deletions
Original file line numberDiff line numberDiff line change
@@ -1,4 +1,6 @@
11
using System.Numerics;
2+
using System.Runtime.CompilerServices;
3+
using System.Runtime.InteropServices;
24
using System.Text;
35

46
namespace MemoryPack.Formatters;
@@ -22,12 +24,15 @@ public override void Serialize<TBufferWriter>(ref MemoryPackWriter<TBufferWriter
2224

2325
public override void Deserialize(ref MemoryPackReader reader, scoped ref BigInteger value)
2426
{
25-
if (reader.TryReadUnmanagedSpan<byte>(out var view, out var length))
27+
if (!reader.TryReadCollectionHeader(out var length))
2628
{
27-
value = new BigInteger(view);
28-
reader.Advance(length);
29+
value = default;
30+
return;
2931
}
3032

31-
MemoryPackSerializationException.ThrowInvalidCollection();
33+
ref var src = ref reader.GetSpanReference(length);
34+
value = new BigInteger(MemoryMarshal.CreateReadOnlySpan(ref src, length));
35+
36+
reader.Advance(length);
3237
}
3338
}

src/MemoryPack.Core/MemoryPackReader.cs

Lines changed: 30 additions & 80 deletions
Original file line numberDiff line numberDiff line change
@@ -172,18 +172,21 @@ public bool TryReadCollectionHeader(out int length)
172172
[MethodImpl(MethodImplOptions.AggressiveInlining)]
173173
public string? ReadString()
174174
{
175-
if (!TryReadUnmanagedSpan<char>(out var view, out var advanceLength))
175+
if (!TryReadCollectionHeader(out var length))
176176
{
177177
return null;
178178
}
179-
180-
if (view.Length == 0)
179+
if (length == 0)
181180
{
182181
return "";
183182
}
184183

185-
var str = new string(view);
186-
Advance(advanceLength);
184+
var byteCount = length * 2;
185+
ref var src = ref GetSpanReference(byteCount);
186+
187+
var str = new string(MemoryMarshal.CreateReadOnlySpan(ref Unsafe.As<byte, char>(ref src), length));
188+
189+
Advance(byteCount);
187190

188191
return str;
189192
}
@@ -219,7 +222,7 @@ public void ReadObject<T>(scoped ref T? value)
219222
return value;
220223
}
221224

222-
#region ReadArray/Span(view)
225+
#region ReadArray/Span
223226

224227
public T?[]? ReadArray<T>()
225228
{
@@ -293,42 +296,10 @@ public void ReadSpan<T>(scoped ref Span<T?> value)
293296
}
294297
}
295298

296-
//public void ReadSpan<T>(scoped ref Span<T?> value)
297-
//{
298-
// if (!RuntimeHelpers.IsReferenceOrContainsReferences<T>())
299-
// {
300-
// // DangerousReadUnmanaged(ref value);
301-
// // TODO:...?
302-
// throw new NotImplementedException();
303-
// }
304-
305-
// if (!TryReadLengthHeader(out var length))
306-
// {
307-
// value = null;
308-
// return;
309-
// }
310-
311-
// if (length == 0)
312-
// {
313-
// value = Array.Empty<T>();
314-
// return;
315-
// }
316-
317-
// // T[] support overwrite
318-
// if (value == null || value.Length != length)
319-
// {
320-
// value = new T[length];
321-
// }
322-
323-
// var formatter = MemoryPackFormatterProvider.GetFormatter<T>();
324-
// for (int i = 0; i < length; i++)
325-
// {
326-
// formatter.Deserialize(ref this, ref value[i]);
327-
// }
328-
//}
329-
330299
#endregion
331300

301+
#region UnmanagedArray/Span
302+
332303
public T[]? ReadUnmanagedArray<T>()
333304
where T : unmanaged
334305
{
@@ -341,6 +312,12 @@ public void ReadUnmanagedArray<T>(scoped ref T[]? value)
341312
DangerousReadUnmanagedArray<T>(ref value);
342313
}
343314

315+
public void ReadUnmanagedSpan<T>(scoped ref Span<T> value)
316+
where T : unmanaged
317+
{
318+
DangerousReadUnmanagedSpan<T>(ref value);
319+
}
320+
344321
// T: should be unamanged type
345322
public unsafe T[]? DangerousReadUnmanagedArray<T>()
346323
{
@@ -374,18 +351,18 @@ public unsafe void DangerousReadUnmanagedArray<T>(scoped ref T[]? value)
374351
return;
375352
}
376353

377-
var size = length * Unsafe.SizeOf<T>();
378-
ref var src = ref GetSpanReference(size);
354+
var byteCount = length * Unsafe.SizeOf<T>();
355+
ref var src = ref GetSpanReference(byteCount);
379356

380357
if (value == null || value.Length != length)
381358
{
382359
value = GC.AllocateUninitializedArray<T>(length);
383360
}
384361

385362
ref var dest = ref Unsafe.As<T, byte>(ref MemoryMarshal.GetArrayDataReference(value));
386-
Unsafe.CopyBlockUnaligned(ref dest, ref src, (uint)size);
363+
Unsafe.CopyBlockUnaligned(ref dest, ref src, (uint)byteCount);
387364

388-
Advance(size);
365+
Advance(byteCount);
389366
}
390367

391368
public unsafe void DangerousReadUnmanagedSpan<T>(scoped ref Span<T> value)
@@ -402,48 +379,21 @@ public unsafe void DangerousReadUnmanagedSpan<T>(scoped ref Span<T> value)
402379
return;
403380
}
404381

405-
var size = length * Unsafe.SizeOf<T>();
406-
ref var src = ref GetSpanReference(size);
382+
var byteCount = length * Unsafe.SizeOf<T>();
383+
ref var src = ref GetSpanReference(byteCount);
407384

408385
if (value == null || value.Length != length)
409386
{
410387
value = GC.AllocateUninitializedArray<T>(length);
411388
}
412389

413390
ref var dest = ref Unsafe.As<T, byte>(ref MemoryMarshal.GetReference(value));
414-
Unsafe.CopyBlockUnaligned(ref dest, ref src, (uint)size);
415-
416-
Advance(size);
417-
}
391+
Unsafe.CopyBlockUnaligned(ref dest, ref src, (uint)byteCount);
418392

419-
420-
421-
// TODO:this?
422-
423-
public bool TryReadUnmanagedSpan<T>(out ReadOnlySpan<T> view, out int advanceLength)
424-
where T : unmanaged
425-
{
426-
return DangerousTryReadUnmanagedSpan(out view, out advanceLength);
427-
}
428-
429-
// T: should be unamanged type
430-
public bool DangerousTryReadUnmanagedSpan<T>(out ReadOnlySpan<T> view, out int advanceLength)
431-
{
432-
if (!TryReadCollectionHeader(out var length))
433-
{
434-
view = default;
435-
advanceLength = 0;
436-
return false;
437-
}
438-
439-
view = MemoryMarshal.CreateReadOnlySpan(ref Unsafe.As<byte, T>(ref GetSpanReference(length)), length);
440-
advanceLength = view.Length * Unsafe.SizeOf<T>();
441-
return true;
393+
Advance(byteCount);
442394
}
443395

444-
445-
446-
396+
#endregion
447397

448398
public void ReadSpanWithoutReadLengthHeader<T>(int length, scoped ref Span<T?> value)
449399
{
@@ -460,12 +410,12 @@ public void ReadSpanWithoutReadLengthHeader<T>(int length, scoped ref Span<T?> v
460410
value = GC.AllocateUninitializedArray<T>(length);
461411
}
462412

463-
var size = length * Unsafe.SizeOf<T>();
464-
ref var src = ref GetSpanReference(size);
413+
var byteCount = length * Unsafe.SizeOf<T>();
414+
ref var src = ref GetSpanReference(byteCount);
465415
ref var dest = ref Unsafe.As<T, byte>(ref MemoryMarshal.GetReference(value)!);
466-
Unsafe.CopyBlockUnaligned(ref dest, ref src, (uint)size);
416+
Unsafe.CopyBlockUnaligned(ref dest, ref src, (uint)byteCount);
467417

468-
Advance(size);
418+
Advance(byteCount);
469419
}
470420
else
471421
{

0 commit comments

Comments
 (0)