2 // System.Net.FtpDataStream.cs
5 // Carlos Alberto Cortez (calberto.cortez@gmail.com)
7 // (c) Copyright 2006 Novell, Inc. (http://www.novell.com)
12 using System.Net.Sockets;
13 using System.Runtime.Remoting.Messaging;
14 using System.Threading;
19 class FtpDataStream : Stream, IDisposable
21 FtpWebRequest request;
27 internal FtpDataStream (FtpWebRequest request, Stream stream, bool isRead)
30 throw new ArgumentNullException ("request");
32 this.request = request;
33 this.networkStream = stream;
37 public override bool CanRead {
43 public override bool CanWrite {
49 public override bool CanSeek {
55 public override long Length {
57 throw new NotSupportedException ();
61 public override long Position {
63 throw new NotSupportedException ();
66 throw new NotSupportedException ();
70 internal Stream NetworkStream {
77 public override void Close ()
82 public override void Flush ()
87 public override long Seek (long offset, SeekOrigin origin)
89 throw new NotSupportedException ();
92 public override void SetLength (long value)
94 throw new NotSupportedException ();
97 int ReadInternal (byte [] buffer, int offset, int size)
100 request.CheckIfAborted ();
103 // Probably it would be better to have the socket here
104 nbytes = networkStream.Read (buffer, offset, size);
105 } catch (IOException) {
106 throw new ProtocolViolationException ("Server commited a protocol violation");
111 networkStream = null;
112 request.CloseDataConnection ();
113 request.SetTransferCompleted ();
119 public override IAsyncResult BeginRead (byte [] buffer, int offset, int size, AsyncCallback cb, object state)
124 throw new NotSupportedException ();
126 throw new ArgumentNullException ("buffer");
127 if (offset < 0 || offset > buffer.Length)
128 throw new ArgumentOutOfRangeException ("offset");
129 if (size < 0 || size > buffer.Length - offset)
130 throw new ArgumentOutOfRangeException ("offset+size");
132 ReadDelegate del = ReadInternal;
133 return del.BeginInvoke (buffer, offset, size, cb, state);
136 public override int EndRead (IAsyncResult asyncResult)
138 if (asyncResult == null)
139 throw new ArgumentNullException ("asyncResult");
141 AsyncResult ar = asyncResult as AsyncResult;
143 throw new ArgumentException ("Invalid asyncResult", "asyncResult");
145 ReadDelegate del = ar.AsyncDelegate as ReadDelegate;
147 throw new ArgumentException ("Invalid asyncResult", "asyncResult");
149 return del.EndInvoke (asyncResult);
152 public override int Read (byte [] buffer, int offset, int size)
154 request.CheckIfAborted ();
155 IAsyncResult ar = BeginRead (buffer, offset, size, null, null);
156 if (!ar.IsCompleted && !ar.AsyncWaitHandle.WaitOne (request.ReadWriteTimeout, false))
157 throw new WebException ("Read timed out.", WebExceptionStatus.Timeout);
162 delegate void WriteDelegate (byte [] buffer, int offset, int size);
164 void WriteInternal (byte [] buffer, int offset, int size)
166 request.CheckIfAborted ();
169 networkStream.Write (buffer, offset, size);
170 } catch (IOException) {
171 throw new ProtocolViolationException ();
175 public override IAsyncResult BeginWrite (byte [] buffer, int offset, int size, AsyncCallback cb, object state)
179 throw new NotSupportedException ();
181 throw new ArgumentNullException ("buffer");
182 if (offset < 0 || offset > buffer.Length)
183 throw new ArgumentOutOfRangeException ("offset");
184 if (size < 0 || size > buffer.Length - offset)
185 throw new ArgumentOutOfRangeException ("offset+size");
187 WriteDelegate del = WriteInternal;
188 return del.BeginInvoke (buffer, offset, size, cb, state);
191 public override void EndWrite (IAsyncResult asyncResult)
193 if (asyncResult == null)
194 throw new ArgumentNullException ("asyncResult");
196 AsyncResult ar = asyncResult as AsyncResult;
198 throw new ArgumentException ("Invalid asyncResult.", "asyncResult");
200 WriteDelegate del = ar.AsyncDelegate as WriteDelegate;
202 throw new ArgumentException ("Invalid asyncResult.", "asyncResult");
204 del.EndInvoke (asyncResult);
207 public override void Write (byte [] buffer, int offset, int size)
209 request.CheckIfAborted ();
210 IAsyncResult ar = BeginWrite (buffer, offset, size, null, null);
211 if (!ar.IsCompleted && !ar.AsyncWaitHandle.WaitOne (request.ReadWriteTimeout, false))
212 throw new WebException ("Read timed out.", WebExceptionStatus.Timeout);
222 void IDisposable.Dispose ()
225 GC.SuppressFinalize (this);
228 protected override void Dispose (bool disposing)
234 if (networkStream != null) {
235 request.CloseDataConnection ();
236 request.SetTransferCompleted ();
238 networkStream = null;
242 void CheckDisposed ()
245 throw new ObjectDisposedException (GetType ().FullName);
248 delegate int ReadDelegate (byte [] buffer, int offset, int size);