/// <summary> /// 创建短路径 /// </summary> /// <param name="node"></param> /// <param name="parser"></param> internal void CreateShortPath(Cache.Value.Node node, ref OperationParameter.NodeParser parser) { byte[] packet = parser.CreateReadPacket(OperationParameter.Serializer.HeaderSize); ulong identity = shortPaths[shortPathIndex].Set(node, packet); parser.ReturnParameter.ReturnParameterSetBinary(new ShortPathIdentity { Index = shortPathIndex, Identity = identity, Ticks = startTicks, PacketSize = packet.Length }); if (++shortPathIndex == shortPaths.Length) { shortPathIndex = 0; } }
/// <summary> /// 操作数据 /// </summary> /// <param name="parameter">短路径操作参数</param> /// <returns>返回参数</returns> internal ValueData.Data Operation(ref OperationParameter.ShortPathOperationNode parameter) { if (CanWrite) { if (parameter.Buffer != null) { if (parameter.Identity.Ticks == startTicks) { byte[] packet; Cache.Value.Node node = shortPaths[parameter.Identity.Index].Get(parameter.Identity.Identity, out packet); if (packet.Length == parameter.Identity.PacketSize) { if (node.IsNode) { byte[] bufferData = parameter.Buffer.Array.Array; System.Buffer.BlockCopy(packet, 0, bufferData, parameter.Buffer.Array.Start + OperationParameter.Serializer.HeaderSize, parameter.Identity.PacketSize); fixed(byte *bufferFixed = bufferData) { OperationParameter.NodeParser parser = new OperationParameter.NodeParser(this, parameter.Buffer, bufferFixed); parser.Read += parameter.Identity.PacketSize; node.Operation(ref parser); if (parser.IsOperation) { onOperation(parameter.Buffer); } else { parameter.Buffer.FreeReference(); } return(parser.ReturnParameter); } } return(new ValueData.Data(ReturnType.NotFoundShortPathNode)); } } return(new ValueData.Data(ReturnType.NotFoundShortPath)); } return(new ValueData.Data(ReturnType.ServerDeSerializeError)); } return(new ValueData.Data(ReturnType.CanNotWrite)); }
internal ulong Set(Cache.Value.Node node, byte[] packet) { this.node = node; this.packet = packet; return(++identity); }
/// <summary> /// 查询数据 /// </summary> /// <param name="queryData">查询数据</param> /// <returns>返回参数</returns> internal ValueData.Data ShortPathQuery(ref SubArray <byte> queryData) { byte[] data = queryData.Array; ReturnType returnType = ReturnType.NotFoundShortPath; fixed(byte *dataFixed = queryData.Array) { byte * start = dataFixed + queryData.Start; ShortPathIdentity identity = new ShortPathIdentity(start + OperationParameter.Serializer.HeaderSize); if (identity.Ticks == startTicks) { byte[] packet; Cache.Value.Node node = shortPaths[identity.Index].Get(identity.Identity, out packet); if (packet.Length == identity.PacketSize) { if (node.IsNode) { returnType = ReturnType.Unknown; if ((*(int *)start = queryData.Length + identity.PacketSize - ShortPathIdentity.SerializeSize) <= queryData.Length) { System.Buffer.BlockCopy(packet, 0, data, queryData.Start + OperationParameter.Serializer.HeaderSize, identity.PacketSize); System.Buffer.BlockCopy(data, queryData.Start + (OperationParameter.Serializer.HeaderSize + ShortPathIdentity.SerializeSize), data, queryData.Start + (OperationParameter.Serializer.HeaderSize + identity.PacketSize), queryData.Length - (OperationParameter.Serializer.HeaderSize + ShortPathIdentity.SerializeSize)); queryData.Length = *(int *)start; queryBuffer.Set(ref queryData); OperationParameter.NodeParser parser = new OperationParameter.NodeParser(this, queryBuffer, dataFixed); parser.Read += identity.PacketSize; node.Query(ref parser); return(parser.ReturnParameter); } else { Buffer buffer = BufferCount.GetBuffer(*(int *)start); try { SubArray <byte> bufferSubArray = buffer.Array; byte[] bufferData = bufferSubArray.Array; fixed(byte *bufferFixed = bufferData) { *(ulong *)(bufferFixed + bufferSubArray.Start) = *(ulong *)start; System.Buffer.BlockCopy(packet, 0, bufferData, bufferSubArray.Start + OperationParameter.Serializer.HeaderSize, identity.PacketSize); System.Buffer.BlockCopy(data, queryData.Start + (OperationParameter.Serializer.HeaderSize + ShortPathIdentity.SerializeSize), bufferData, bufferSubArray.Start + (OperationParameter.Serializer.HeaderSize + identity.PacketSize), queryData.Length - (OperationParameter.Serializer.HeaderSize + ShortPathIdentity.SerializeSize)); OperationParameter.NodeParser parser = new OperationParameter.NodeParser(this, buffer, bufferFixed); parser.Read += identity.PacketSize; node.Query(ref parser); return(parser.ReturnParameter); } } finally { buffer.Dispose(); } } } else { returnType = ReturnType.NotFoundShortPathNode; } } } } return(new ValueData.Data(returnType)); }
/// <summary> /// 操作数据 /// </summary> /// <param name="parameter">短路径操作参数</param> /// <param name="onOperation"></param> internal void Operation(ref OperationParameter.ShortPathOperationNode parameter, Func <AutoCSer.Net.TcpServer.ReturnValue <ReturnParameter>, bool> onOperation) { ReturnType returnType = ReturnType.CanNotWrite; try { if (CanWrite) { if (parameter.Buffer != null) { returnType = ReturnType.NotFoundShortPath; if (parameter.Identity.Ticks == startTicks) { byte[] packet; Cache.Value.Node node = shortPaths[parameter.Identity.Index].Get(parameter.Identity.Identity, out packet); if (packet.Length == parameter.Identity.PacketSize) { if (node.IsNode) { returnType = ReturnType.Unknown; byte[] bufferData = parameter.Buffer.Array.Array; System.Buffer.BlockCopy(packet, 0, bufferData, parameter.Buffer.Array.Start + OperationParameter.Serializer.HeaderSize, parameter.Identity.PacketSize); fixed(byte *bufferFixed = bufferData) { OperationParameter.NodeParser parser = new OperationParameter.NodeParser(this, parameter.Buffer, bufferFixed); parser.Read += parameter.Identity.PacketSize; parser.OnReturn = onOperation; try { node.Operation(ref parser); } finally { if (parser.OnReturn == null) { returnType = ReturnType.Success; } } if (parser.IsOperation) { this.onOperation(parameter.Buffer); } else { parameter.Buffer.FreeReference(); } return; } } else { returnType = ReturnType.NotFoundShortPathNode; } } } } else { returnType = ReturnType.ServerDeSerializeError; } } parameter.Buffer.FreeReference(); } finally { if (returnType != ReturnType.Success) { onOperation(new ReturnParameter(returnType)); } } }
/// <summary> /// 查询数据 /// </summary> /// <param name="queryData">查询数据</param> /// <param name="onQuery"></param> /// <param name="isDeSerializeStream">是否反序列化网络流,否则需要 Copy 数据</param> internal void ShortPathQuery(ref SubArray <byte> queryData, AutoCSer.Net.TcpServer.ServerCallback <ReturnParameter> onQuery, bool isDeSerializeStream) { byte[] data = queryData.Array; ReturnType returnType = ReturnType.ServerDeSerializeError; try { fixed(byte *dataFixed = queryData.GetFixedBuffer()) { byte * start = dataFixed + queryData.Start; ShortPathIdentity identity = new ShortPathIdentity(start + OperationParameter.Serializer.HeaderSize); returnType = ReturnType.NotFoundShortPath; if (identity.Ticks == startTicks) { byte[] packet; Cache.Value.Node node = shortPaths[identity.Index].Get(identity.Identity, out packet); if (packet.Length == identity.PacketSize) { if (node.IsNode) { returnType = ReturnType.Unknown; if ((*(int *)start = queryData.Length + identity.PacketSize - ShortPathIdentity.SerializeSize) <= queryData.Length) { System.Buffer.BlockCopy(packet, 0, data, queryData.Start + OperationParameter.Serializer.HeaderSize, identity.PacketSize); System.Buffer.BlockCopy(data, queryData.Start + (OperationParameter.Serializer.HeaderSize + ShortPathIdentity.SerializeSize), data, queryData.Start + (OperationParameter.Serializer.HeaderSize + identity.PacketSize), queryData.Length - (OperationParameter.Serializer.HeaderSize + ShortPathIdentity.SerializeSize)); queryData.Length = *(int *)start; queryBuffer.Set(ref queryData); OperationParameter.NodeParser parser = new OperationParameter.NodeParser(this, queryBuffer, dataFixed); parser.Read += identity.PacketSize; parser.SetOnReturn(onQuery, isDeSerializeStream); onQuery = null; try { node.Query(ref parser); } finally { parser.CallOnReturn(); } } else { Buffer buffer = BufferCount.GetBuffer(*(int *)start); try { SubArray <byte> bufferSubArray = buffer.Array; byte[] bufferData = bufferSubArray.Array; fixed(byte *bufferFixed = bufferData) { *(ulong *)(bufferFixed + bufferSubArray.Start) = *(ulong *)start; System.Buffer.BlockCopy(packet, 0, bufferData, bufferSubArray.Start + OperationParameter.Serializer.HeaderSize, identity.PacketSize); System.Buffer.BlockCopy(data, queryData.Start + (OperationParameter.Serializer.HeaderSize + ShortPathIdentity.SerializeSize), bufferData, bufferSubArray.Start + (OperationParameter.Serializer.HeaderSize + identity.PacketSize), queryData.Length - (OperationParameter.Serializer.HeaderSize + ShortPathIdentity.SerializeSize)); OperationParameter.NodeParser parser = new OperationParameter.NodeParser(this, buffer, bufferFixed); parser.Read += identity.PacketSize; parser.SetOnReturn(onQuery, isDeSerializeStream); onQuery = null; try { node.Query(ref parser); } finally { parser.CallOnReturn(); } } } finally { buffer.Dispose(); } } } else { returnType = ReturnType.NotFoundShortPathNode; } } } } } finally { if (onQuery != null) { onQuery.Callback(new ReturnParameter(returnType)); } } }