NetworkStream.cs 5.4 KB

123456789101112131415161718192021222324252627282930313233343536373839404142434445464748495051525354555657585960616263646566676869707172737475767778798081828384858687888990919293949596979899100101102103104105106107108109110111112113114115116117118119120121122123124125126127128129130131132133134135136137138139140141142143144145146147148149150151152153154155156157158159160161162163164165166167168169170171172173174175176177178179180181182183184185186187188189190191192193194195196197198199200201202203204205206207208209210211212213214215216217218219220221222223224225226227228229230231232233234235236237238239240241242243244245246247248249250251252253254255256257258259260261262263264265266267268269270271272
  1. //
  2. // System.Net.Sockets.NetworkStream.cs
  3. //
  4. // Author:
  5. // Miguel de Icaza ([email protected])
  6. //
  7. // (C) 2002 Ximian, Inc. http://www.ximian.com
  8. //
  9. using System.IO;
  10. namespace System.Net.Sockets
  11. {
  12. public class NetworkStream : Stream, IDisposable {
  13. FileAccess access;
  14. Socket socket;
  15. bool owns_socket;
  16. bool readable, writeable;
  17. public NetworkStream (Socket socket)
  18. : this (socket, FileAccess.ReadWrite, false)
  19. {
  20. }
  21. public NetworkStream (Socket socket, bool owns_socket)
  22. : this (socket, FileAccess.ReadWrite, owns_socket)
  23. {
  24. }
  25. public NetworkStream (Socket socket, FileAccess access)
  26. : this (socket, access, false)
  27. {
  28. }
  29. public NetworkStream (Socket socket, FileAccess access, bool owns_socket)
  30. {
  31. if (socket == null)
  32. throw new ArgumentNullException ();
  33. if (!socket.Connected)
  34. throw new ArgumentException ("Not connected", "socket");
  35. if (socket.SocketType != SocketType.Stream)
  36. throw new ArgumentException ("Socket is not of type Stream", "socket");
  37. if (!socket.Blocking)
  38. throw new IOException ();
  39. this.socket = socket;
  40. this.owns_socket = owns_socket;
  41. this.access = access;
  42. readable = CanRead;
  43. writeable = CanWrite;
  44. }
  45. public override bool CanRead {
  46. get {
  47. return access == FileAccess.ReadWrite || access == FileAccess.Read;
  48. }
  49. }
  50. public override bool CanSeek {
  51. get {
  52. // network sockets cant seek.
  53. return false;
  54. }
  55. }
  56. public override bool CanWrite {
  57. get {
  58. return access == FileAccess.ReadWrite || access == FileAccess.Write;
  59. }
  60. }
  61. public virtual bool DataAvailable {
  62. get {
  63. return socket.Available > 0;
  64. }
  65. }
  66. public override long Length {
  67. get {
  68. // Network sockets always throw an exception
  69. throw new NotSupportedException ();
  70. }
  71. }
  72. public override long Position {
  73. get {
  74. // Network sockets always throw an exception
  75. throw new NotSupportedException ();
  76. }
  77. set {
  78. // Network sockets always throw an exception
  79. throw new NotSupportedException ();
  80. }
  81. }
  82. protected bool Readable {
  83. get {
  84. return readable;
  85. }
  86. set {
  87. readable = value;
  88. }
  89. }
  90. protected Socket Socket {
  91. get {
  92. return socket;
  93. }
  94. }
  95. protected bool Writeable {
  96. get {
  97. return writeable;
  98. }
  99. set {
  100. writeable = value;
  101. }
  102. }
  103. public override IAsyncResult BeginRead (byte [] buffer, int offset, int size,
  104. AsyncCallback callback, object state)
  105. {
  106. IAsyncResult retval;
  107. if (buffer == null)
  108. throw new ArgumentNullException ();
  109. if (socket == null)
  110. throw new ObjectDisposedException ("socket");
  111. int len = buffer.Length;
  112. if (offset >= len || size != len)
  113. throw new ArgumentOutOfRangeException ();
  114. try {
  115. retval = socket.BeginReceive (buffer, offset, size, 0, callback, state);
  116. } catch {
  117. throw new IOException ("BeginReceive failure");
  118. }
  119. return retval;
  120. }
  121. public override IAsyncResult BeginWrite (byte [] buffer, int offset, int size,
  122. AsyncCallback callback, object state)
  123. {
  124. IAsyncResult retval;
  125. if (buffer == null)
  126. throw new ArgumentNullException ();
  127. if (socket == null)
  128. throw new ObjectDisposedException ("socket");
  129. int len = buffer.Length;
  130. if (len < size)
  131. throw new ArgumentException ();
  132. try {
  133. retval = socket.BeginSend (buffer, offset, size, 0, callback, state);
  134. } catch {
  135. throw new IOException ("BeginWrite failure");
  136. }
  137. return retval;
  138. }
  139. ~NetworkStream ()
  140. {
  141. Dispose (false);
  142. }
  143. public override void Close ()
  144. {
  145. Dispose (true);
  146. }
  147. public virtual void Dispose (bool disposing)
  148. {
  149. if (owns_socket)
  150. if (socket != null)
  151. socket.Close ();
  152. socket = null;
  153. }
  154. public override int EndRead (IAsyncResult ar)
  155. {
  156. int res;
  157. if (ar == null)
  158. throw new ArgumentNullException ();
  159. if (socket == null)
  160. throw new ObjectDisposedException ("socket");
  161. try {
  162. res = socket.EndReceive (ar);
  163. } catch {
  164. throw new IOException ("EndRead failure");
  165. }
  166. return res;
  167. }
  168. public override void EndWrite (IAsyncResult ar)
  169. {
  170. if (ar == null)
  171. throw new ArgumentNullException ();
  172. if (socket == null)
  173. throw new ObjectDisposedException ("socket");
  174. try {
  175. socket.EndSend (ar);
  176. } catch {
  177. throw new IOException ("EndWrite failure");
  178. }
  179. }
  180. public override void Flush ()
  181. {
  182. // network streams are non-buffered, this is a no-op
  183. }
  184. void IDisposable.Dispose ()
  185. {
  186. Dispose (true);
  187. }
  188. public override int Read (byte [] buffer, int offset, int size)
  189. {
  190. int res;
  191. if (buffer == null)
  192. throw new ArgumentNullException ();
  193. if (buffer.Length < size)
  194. throw new ArgumentException ();
  195. try {
  196. res = socket.Receive (buffer, offset, size, 0);
  197. } catch {
  198. throw new IOException ("Read failure");
  199. }
  200. return res;
  201. }
  202. public override long Seek (long offset, SeekOrigin origin)
  203. {
  204. // NetworkStream objects do not support seeking.
  205. throw new NotSupportedException ();
  206. }
  207. public override void SetLength (long value)
  208. {
  209. // NetworkStream objects do not support SetLength
  210. throw new NotSupportedException ();
  211. }
  212. public override void Write (byte [] buffer, int offset, int size)
  213. {
  214. if (buffer == null)
  215. throw new ArgumentNullException ();
  216. if (buffer.Length < size)
  217. throw new ArgumentException ();
  218. try {
  219. socket.Send (buffer, offset, size, 0);
  220. } catch {
  221. throw new IOException ("Write failure");
  222. }
  223. }
  224. }
  225. }