RPCServerPipeTransport.cs 3.2 KB

123456789101112131415161718192021222324252627282930313233343536373839404142434445464748495051525354555657585960616263646566676869707172737475767778798081828384858687888990919293949596
  1. using System.IO.Pipes;
  2. using System.Security.Principal;
  3. using H.Formatters;
  4. using H.Pipes;
  5. using H.Pipes.AccessControl;
  6. namespace InABox.Rpc
  7. {
  8. public class RpcServerPipeTransport : RpcServerTransport<PipeConnection<RpcMessage?>>, IDisposable
  9. {
  10. private PipeServer<RpcMessage?> _transport;
  11. public override bool IsSecure() => false;
  12. private void SetPipeSecurity()
  13. {
  14. #pragma warning disable CA1416
  15. var pipeSecurity = new PipeSecurity();
  16. pipeSecurity.AddAccessRule(new PipeAccessRule(new SecurityIdentifier(WellKnownSidType.LocalSid, null), PipeAccessRights.ReadWrite, System.Security.AccessControl.AccessControlType.Allow));
  17. pipeSecurity.AddAccessRule(new PipeAccessRule(new SecurityIdentifier(WellKnownSidType.LocalServiceSid, null), PipeAccessRights.ReadWrite, System.Security.AccessControl.AccessControlType.Allow));
  18. pipeSecurity.AddAccessRule(new PipeAccessRule(new SecurityIdentifier(WellKnownSidType.LocalSystemSid, null), PipeAccessRights.ReadWrite, System.Security.AccessControl.AccessControlType.Allow));
  19. _transport.SetPipeSecurity(pipeSecurity);
  20. #pragma warning restore CA1416
  21. }
  22. public RpcServerPipeTransport(string name)
  23. {
  24. _transport = new PipeServer<RpcMessage?>(name, formatter:new MessagePackFormatter());
  25. #if WINDOWS
  26. SetPipeSecurity();
  27. #endif
  28. _transport.ClientConnected += Transport_OnConnected;
  29. _transport.ClientDisconnected += Transport_OnDisconnected;
  30. _transport.MessageReceived += Transport_OnMessage;
  31. _transport.ExceptionOccurred += Transport_OnException;
  32. }
  33. public override void Start()
  34. {
  35. _transport.StartAsync().Wait();
  36. }
  37. public override void Stop()
  38. {
  39. _transport.StopAsync().Wait();
  40. }
  41. private void Transport_OnConnected(object? sender, H.Pipes.Args.ConnectionEventArgs<RpcMessage?> e)
  42. {
  43. DoOpen(e.Connection);
  44. }
  45. private void Transport_OnMessage(object? sender, H.Pipes.Args.ConnectionMessageEventArgs<RpcMessage?> e)
  46. {
  47. Task.Run(() =>
  48. {
  49. var response = DoMessage(e.Connection, e.Message);
  50. e.Connection.WriteAsync(response);
  51. });
  52. }
  53. public override void Send(PipeConnection<RpcMessage?> connection, RpcMessage message)
  54. {
  55. connection.WriteAsync(message);
  56. }
  57. private void Transport_OnDisconnected(object? sender, H.Pipes.Args.ConnectionEventArgs<RpcMessage?> e)
  58. {
  59. DoClose(e.Connection, RpcTransportCloseEventType.Closed);
  60. e.Connection.DisposeAsync();
  61. }
  62. private void Transport_OnException(object? sender, H.Pipes.Args.ExceptionEventArgs e)
  63. {
  64. DoException(null, e.Exception);
  65. }
  66. public void Dispose()
  67. {
  68. _transport.DisposeAsync().AsTask().Wait();
  69. }
  70. ~RpcServerPipeTransport()
  71. {
  72. Dispose();
  73. }
  74. }
  75. }