Skip to content

Commit 81192d8

Browse files
committed
use the function-ptr API exclusively
1 parent 5d33404 commit 81192d8

6 files changed

Lines changed: 147 additions & 64 deletions

File tree

src/RESPite/Messages/RespReader.cs

Lines changed: 3 additions & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -739,6 +739,9 @@ private readonly unsafe bool TryParseSlow<T>(
739739
#pragma warning disable RS0016, RS0027 // public API
740740
[Experimental(Experiments.Respite, UrlFormat = Experiments.UrlFormat)]
741741
[MethodImpl(MethodImplOptions.AggressiveInlining)]
742+
#if DEBUG
743+
[Obsolete("Please prefer the function-pointer API for library-internal use.")]
744+
#endif
742745
public readonly bool TryParseScalar<T>(ScalarParser<byte, T> parser, out T value)
743746
#pragma warning restore RS0016, RS0027 // public API
744747
{

src/StackExchange.Redis/HotKeys.ResultProcessor.cs

Lines changed: 6 additions & 2 deletions
Original file line numberDiff line numberDiff line change
@@ -43,9 +43,13 @@ private HotKeysResult(ref RespReader reader)
4343

4444
while (reader.TryMoveNext() && reader.IsScalar)
4545
{
46-
if (!reader.TryParseScalar(HotKeysFieldMetadata.TryParse, out HotKeysField field))
46+
HotKeysField field;
47+
unsafe
4748
{
48-
field = HotKeysField.Unknown;
49+
if (!reader.TryParseScalar(&HotKeysFieldMetadata.TryParse, out field))
50+
{
51+
field = HotKeysField.Unknown;
52+
}
4953
}
5054

5155
// Move to value

src/StackExchange.Redis/PhysicalConnection.Read.cs

Lines changed: 6 additions & 1 deletion
Original file line numberDiff line numberDiff line change
@@ -392,7 +392,12 @@ private bool OnOutOfBand(ReadOnlySpan<byte> payload, ref byte[]? lease)
392392
&& reader.AggregateLength() >= 2
393393
&& (reader.SafeTryMoveNext() & reader.IsInlineScalar & !reader.IsError))
394394
{
395-
if (!reader.TryParseScalar(PushKindMetadata.TryParse, out PushKind kind)) kind = PushKind.None;
395+
PushKind kind;
396+
unsafe
397+
{
398+
if (!reader.TryParseScalar(&PushKindMetadata.TryParse, out kind)) kind = PushKind.None;
399+
}
400+
396401
RedisChannel.RedisChannelOptions channelOptions = kind switch
397402
{
398403
PushKind.PMessage or PushKind.PSubscribe or PushKind.PUnsubscribe => RedisChannel.RedisChannelOptions.Pattern,

src/StackExchange.Redis/ResultProcessor.VectorSets.cs

Lines changed: 30 additions & 24 deletions
Original file line numberDiff line numberDiff line change
@@ -104,31 +104,37 @@ protected override bool SetResultCore(PhysicalConnection connection, Message mes
104104
continue;
105105
}
106106

107-
switch (field)
107+
unsafe
108108
{
109-
case VectorSetInfoField.Size when reader.TryReadInt64(out var i64):
110-
resultSize = i64;
111-
break;
112-
case VectorSetInfoField.VsetUid when reader.TryReadInt64(out var i64):
113-
vsetUid = i64;
114-
break;
115-
case VectorSetInfoField.MaxLevel when reader.TryReadInt64(out var i64):
116-
maxLevel = checked((int)i64);
117-
break;
118-
case VectorSetInfoField.VectorDim when reader.TryReadInt64(out var i64):
119-
vectorDim = checked((int)i64);
120-
break;
121-
case VectorSetInfoField.QuantType when reader.TryParseScalar<VectorSetQuantization>(VectorSetQuantizationMetadata.TryParse, out var quantTypeValue)
122-
&& quantTypeValue is not VectorSetQuantization.Unknown:
123-
quantType = quantTypeValue;
124-
break;
125-
case VectorSetInfoField.QuantType:
126-
quantTypeRaw = reader.ReadString();
127-
quantType = VectorSetQuantization.Unknown;
128-
break;
129-
case VectorSetInfoField.HnswMaxNodeUid when reader.TryReadInt64(out var i64):
130-
hnswMaxNodeUid = i64;
131-
break;
109+
switch (field)
110+
{
111+
case VectorSetInfoField.Size when reader.TryReadInt64(out var i64):
112+
resultSize = i64;
113+
break;
114+
case VectorSetInfoField.VsetUid when reader.TryReadInt64(out var i64):
115+
vsetUid = i64;
116+
break;
117+
case VectorSetInfoField.MaxLevel when reader.TryReadInt64(out var i64):
118+
maxLevel = checked((int)i64);
119+
break;
120+
case VectorSetInfoField.VectorDim when reader.TryReadInt64(out var i64):
121+
vectorDim = checked((int)i64);
122+
break;
123+
case VectorSetInfoField.QuantType
124+
when reader.TryParseScalar(
125+
&VectorSetQuantizationMetadata.TryParse,
126+
out VectorSetQuantization quantTypeValue)
127+
&& quantTypeValue is not VectorSetQuantization.Unknown:
128+
quantType = quantTypeValue;
129+
break;
130+
case VectorSetInfoField.QuantType:
131+
quantTypeRaw = reader.ReadString();
132+
quantType = VectorSetQuantization.Unknown;
133+
break;
134+
case VectorSetInfoField.HnswMaxNodeUid when reader.TryReadInt64(out var i64):
135+
hnswMaxNodeUid = i64;
136+
break;
137+
}
132138
}
133139
}
134140

src/StackExchange.Redis/ResultProcessor.cs

Lines changed: 93 additions & 33 deletions
Original file line numberDiff line numberDiff line change
@@ -966,9 +966,13 @@ protected override bool SetResultCore(PhysicalConnection connection, Message mes
966966
while (iter.MoveNext())
967967
{
968968
var key = iter.Value;
969-
if (!key.TryParseScalar(ConfigFieldMetadata.TryParse, out ConfigField field))
969+
ConfigField field;
970+
unsafe
970971
{
971-
field = ConfigField.Unknown;
972+
if (!key.TryParseScalar(&ConfigFieldMetadata.TryParse, out field))
973+
{
974+
field = ConfigField.Unknown;
975+
}
972976
}
973977

974978
if (!iter.MoveNext()) break;
@@ -1004,20 +1008,29 @@ protected override bool SetResultCore(PhysicalConnection connection, Message mes
10041008
break;
10051009
case ConfigField.SlaveReadOnly:
10061010
case ConfigField.ReplicaReadOnly:
1007-
if (val.TryParseScalar(YesNoMetadata.TryParse, out YesNo yesNo))
1011+
YesNo yesNo;
1012+
unsafe
10081013
{
1009-
switch (yesNo)
1014+
if (val.TryParseScalar(&YesNoMetadata.TryParse, out yesNo))
10101015
{
1011-
case YesNo.Yes:
1012-
server.ReplicaReadOnly = true;
1013-
Log?.LogInformationAutoConfiguredConfigReadOnlyReplica(new(server), true);
1014-
break;
1015-
case YesNo.No:
1016-
server.ReplicaReadOnly = false;
1017-
Log?.LogInformationAutoConfiguredConfigReadOnlyReplica(new(server), false);
1018-
break;
1016+
switch (yesNo)
1017+
{
1018+
case YesNo.Yes:
1019+
server.ReplicaReadOnly = true;
1020+
Log?.LogInformationAutoConfiguredConfigReadOnlyReplica(
1021+
new(server),
1022+
true);
1023+
break;
1024+
case YesNo.No:
1025+
server.ReplicaReadOnly = false;
1026+
Log?.LogInformationAutoConfiguredConfigReadOnlyReplica(
1027+
new(server),
1028+
false);
1029+
break;
1030+
}
10191031
}
10201032
}
1033+
10211034
break;
10221035
}
10231036
}
@@ -1032,9 +1045,13 @@ protected override bool SetResultCore(PhysicalConnection connection, Message mes
10321045
while (iter.MoveNext())
10331046
{
10341047
var key = iter.Value;
1035-
if (!key.TryParseScalar(HelloFieldMetadata.TryParse, out HelloField field))
1048+
HelloField field;
1049+
unsafe
10361050
{
1037-
field = HelloField.Unknown;
1051+
if (!key.TryParseScalar(&HelloFieldMetadata.TryParse, out field))
1052+
{
1053+
field = HelloField.Unknown;
1054+
}
10381055
}
10391056

10401057
if (!iter.MoveNext()) break;
@@ -1711,10 +1728,16 @@ protected override bool SetResultCore(PhysicalConnection connection, Message mes
17111728
{
17121729
if (reader.IsScalar)
17131730
{
1714-
if (!reader.TryParseScalar<RedisType>(RedisTypeMetadata.TryParse, out var redisType))
1731+
RedisType redisType;
1732+
unsafe
17151733
{
1716-
// RESP null values and empty strings should map to None rather than Unknown
1717-
redisType = (reader.IsNull || reader.ScalarLengthIs(0)) ? Redis.RedisType.None : Redis.RedisType.Unknown;
1734+
if (!reader.TryParseScalar(&RedisTypeMetadata.TryParse, out redisType))
1735+
{
1736+
// RESP null values and empty strings should map to None rather than Unknown
1737+
redisType = (reader.IsNull || reader.ScalarLengthIs(0))
1738+
? Redis.RedisType.None
1739+
: Redis.RedisType.Unknown;
1740+
}
17181741
}
17191742

17201743
SetResult(message, redisType);
@@ -1959,9 +1982,13 @@ protected override bool SetResultCore(PhysicalConnection connection, Message mes
19591982
var iter = reader.AggregateChildren();
19601983
while (iter.MoveNext() && iter.Value.IsScalar)
19611984
{
1962-
if (!iter.Value.TryParseScalar(LCSFieldMetadata.TryParse, out LCSField field))
1985+
LCSField field;
1986+
unsafe
19631987
{
1964-
field = LCSField.Unknown;
1988+
if (!iter.Value.TryParseScalar(&LCSFieldMetadata.TryParse, out field))
1989+
{
1990+
field = LCSField.Unknown;
1991+
}
19651992
}
19661993

19671994
if (!iter.MoveNext()) break; // out of data
@@ -2067,9 +2094,13 @@ protected override bool SetResultCore(PhysicalConnection connection, Message mes
20672094
return true;
20682095
}
20692096

2070-
if (!reader.TryParseScalar(RoleTypeMetadata.TryParse, out RoleType roleType))
2097+
RoleType roleType;
2098+
unsafe
20712099
{
2072-
roleType = RoleType.Unknown;
2100+
if (!reader.TryParseScalar(&RoleTypeMetadata.TryParse, out roleType))
2101+
{
2102+
roleType = RoleType.Unknown;
2103+
}
20732104
}
20742105

20752106
var role = roleType switch
@@ -2177,10 +2208,15 @@ private static bool TryParsePrimaryReplica(ref RespReader reader, out Role.Maste
21772208
}
21782209

21792210
// this is just a long-winded way of avoiding some string allocs!
2180-
if (!reader.TryParseScalar(ReplicationStateMetadata.TryParse, out ReplicationState state))
2211+
ReplicationState state;
2212+
unsafe
21812213
{
2182-
state = ReplicationState.Unknown;
2214+
if (!reader.TryParseScalar(&ReplicationStateMetadata.TryParse, out state))
2215+
{
2216+
state = ReplicationState.Unknown;
2217+
}
21832218
}
2219+
21842220
var replicationState = state switch
21852221
{
21862222
ReplicationState.Connect => "connect",
@@ -2595,9 +2631,13 @@ protected override StreamConsumerInfo ParseItem(ref RespReader reader)
25952631

25962632
while (reader.TryMoveNext() && reader.IsScalar)
25972633
{
2598-
if (!reader.TryParseScalar(StreamConsumerInfoFieldMetadata.TryParse, out StreamConsumerInfoField field))
2634+
StreamConsumerInfoField field;
2635+
unsafe
25992636
{
2600-
field = StreamConsumerInfoField.Unknown;
2637+
if (!reader.TryParseScalar(&StreamConsumerInfoFieldMetadata.TryParse, out field))
2638+
{
2639+
field = StreamConsumerInfoField.Unknown;
2640+
}
26012641
}
26022642

26032643
if (!reader.TryMoveNext()) break;
@@ -2664,9 +2704,13 @@ protected override StreamGroupInfo ParseItem(ref RespReader reader)
26642704

26652705
while (reader.TryMoveNext() && reader.IsScalar)
26662706
{
2667-
if (!reader.TryParseScalar(StreamGroupInfoFieldMetadata.TryParse, out StreamGroupInfoField field))
2707+
StreamGroupInfoField field;
2708+
unsafe
26682709
{
2669-
field = StreamGroupInfoField.Unknown;
2710+
if (!reader.TryParseScalar(&StreamGroupInfoFieldMetadata.TryParse, out field))
2711+
{
2712+
field = StreamGroupInfoField.Unknown;
2713+
}
26702714
}
26712715

26722716
if (!reader.TryMoveNext()) break;
@@ -2764,9 +2808,13 @@ protected override bool SetResultCore(PhysicalConnection connection, Message mes
27642808

27652809
while (reader.TryMoveNext() && reader.IsScalar)
27662810
{
2767-
if (!reader.TryParseScalar(StreamInfoFieldMetadata.TryParse, out StreamInfoField field))
2811+
StreamInfoField field;
2812+
unsafe
27682813
{
2769-
field = StreamInfoField.Unknown;
2814+
if (!reader.TryParseScalar(&StreamInfoFieldMetadata.TryParse, out field))
2815+
{
2816+
field = StreamInfoField.Unknown;
2817+
}
27702818
}
27712819

27722820
// Move to value
@@ -3301,9 +3349,15 @@ protected override bool SetResultCore(PhysicalConnection connection, Message mes
33013349

33023350
while (itemReader.TryMoveNext() && itemReader.IsScalar)
33033351
{
3304-
if (!itemReader.TryParseScalar(SentinelAddressFieldMetadata.TryParse, out SentinelAddressField field))
3352+
SentinelAddressField field;
3353+
unsafe
33053354
{
3306-
field = SentinelAddressField.Unknown;
3355+
if (!itemReader.TryParseScalar(
3356+
&SentinelAddressFieldMetadata.TryParse,
3357+
out field))
3358+
{
3359+
field = SentinelAddressField.Unknown;
3360+
}
33073361
}
33083362

33093363
// Check for second scalar value
@@ -3360,9 +3414,15 @@ protected override bool SetResultCore(PhysicalConnection connection, Message mes
33603414

33613415
while (r.TryMoveNext() && r.IsScalar)
33623416
{
3363-
if (!r.TryParseScalar(SentinelAddressFieldMetadata.TryParse, out SentinelAddressField field))
3417+
SentinelAddressField field;
3418+
unsafe
33643419
{
3365-
field = SentinelAddressField.Unknown;
3420+
if (!r.TryParseScalar(
3421+
&SentinelAddressFieldMetadata.TryParse,
3422+
out field))
3423+
{
3424+
field = SentinelAddressField.Unknown;
3425+
}
33663426
}
33673427

33683428
// Check for second scalar value

toys/StackExchange.Redis.Server/RedisServer.cs

Lines changed: 9 additions & 4 deletions
Original file line numberDiff line numberDiff line change
@@ -164,8 +164,9 @@ public override TypedRedisValue Execute(RedisClient client, in RedisRequest requ
164164
}
165165
return base.Execute(client, request);
166166

167-
static bool IsAuthCommand(in RedisRequest request) =>
168-
request.Count != 0 && request.GetReader(0).TryParseScalar(RedisCommandMetadata.TryParseCI, out RedisCommand cmd)
167+
static unsafe bool IsAuthCommand(in RedisRequest request) =>
168+
request.Count != 0 && request.GetReader(0).TryParseScalar(
169+
&RedisCommandMetadata.TryParseCI, out RedisCommand cmd)
169170
&& cmd is RedisCommand.AUTH or RedisCommand.HELLO;
170171
}
171172

@@ -206,9 +207,13 @@ protected virtual TypedRedisValue Hello(RedisClient client, in RedisRequest requ
206207
{
207208
int remaining = request.Count - (i + 1);
208209
var fieldReader = request.GetReader(i);
209-
if (!fieldReader.TryParseScalar(HelloSubFieldsMetadata.TryParseCI, out HelloSubFields field))
210+
HelloSubFields field;
211+
unsafe
210212
{
211-
return ArgFail(fieldReader);
213+
if (!fieldReader.TryParseScalar(&HelloSubFieldsMetadata.TryParseCI, out field))
214+
{
215+
return ArgFail(fieldReader);
216+
}
212217
}
213218

214219
switch (field)

0 commit comments

Comments
 (0)