2009-04-11 Sebastien Pouliot <sebastien@ximian.com>
[mono.git] / mcs / class / System.Net / System.Net / WebClient_2_1.cs
1 //
2 // System.Net.WebClient
3 //
4 // Authors:
5 //      Lawrence Pit (loz@cable.a2000.nl)
6 //      Gonzalo Paniagua Javier (gonzalo@ximian.com)
7 //      Atsushi Enomoto (atsushi@ximian.com)
8 //      Miguel de Icaza (miguel@ximian.com)
9 //      Stephane Delcroix (sdelcroix@novell.com)
10 //
11 // Copyright 2003 Ximian, Inc. (http://www.ximian.com)
12 // Copyright 2006, 2008 Novell, Inc. (http://www.novell.com)
13 //
14 //
15 // Permission is hereby granted, free of charge, to any person obtaining
16 // a copy of this software and associated documentation files (the
17 // "Software"), to deal in the Software without restriction, including
18 // without limitation the rights to use, copy, modify, merge, publish,
19 // distribute, sublicense, and/or sell copies of the Software, and to
20 // permit persons to whom the Software is furnished to do so, subject to
21 // the following conditions:
22 // 
23 // The above copyright notice and this permission notice shall be
24 // included in all copies or substantial portions of the Software.
25 // 
26 // THE SOFTWARE IS PROVIDED "AS IS", WITHOUT WARRANTY OF ANY KIND,
27 // EXPRESS OR IMPLIED, INCLUDING BUT NOT LIMITED TO THE WARRANTIES OF
28 // MERCHANTABILITY, FITNESS FOR A PARTICULAR PURPOSE AND
29 // NONINFRINGEMENT. IN NO EVENT SHALL THE AUTHORS OR COPYRIGHT HOLDERS BE
30 // LIABLE FOR ANY CLAIM, DAMAGES OR OTHER LIABILITY, WHETHER IN AN ACTION
31 // OF CONTRACT, TORT OR OTHERWISE, ARISING FROM, OUT OF OR IN CONNECTION
32 // WITH THE SOFTWARE OR THE USE OR OTHER DEALINGS IN THE SOFTWARE.
33 //
34 //
35 // Notes on CancelAsync and Async methods:
36 //
37 //    WebClient.CancelAsync is implemented by calling Thread.Interrupt
38 //    in our helper thread.   The various async methods have to cancel
39 //    any ongoing requests by calling request.Abort () at that point.
40 //    In a few places (UploadDataCore, UploadValuesCore,
41 //    UploadFileCore) we catch the ThreadInterruptedException and
42 //    abort the request there.
43 //
44 //    Higher level routines (the async callbacks) also need to catch
45 //    the exception and raise the OnXXXXCompleted events there with
46 //    the "canceled" flag set to true. 
47 //
48 //    In a few other places where these helper routines are not used
49 //    (OpenReadAsync for example) catching the ThreadAbortException
50 //    also must abort the request.
51 //
52 //    The Async methods currently differ in their implementation from
53 //    the .NET implementation in that we manually catch any other
54 //    exceptions and correctly raise the OnXXXXCompleted passing the
55 //    Exception that caused the problem.   The .NET implementation
56 //    does not seem to have a mechanism to flag errors that happen
57 //    during downloads though.    We do this because we still need to
58 //    catch the exception on these helper threads, or we would
59 //    otherwise kill the application (on the 2.x profile, uncaught
60 //    exceptions in threads terminate the application).
61 //
62 using System;
63 using System.Security;
64 using System.Collections.Specialized;
65 using System.ComponentModel;
66 using System.IO;
67 using System.Runtime.InteropServices;
68 using System.Runtime.Serialization;
69 using System.Text;
70 using System.Threading;
71 using System.Net.Cache;
72
73 namespace System.Net 
74 {
75 #if NET_2_1
76         public class WebClient
77         {
78                 private delegate void ProgressChangedDelegate (long read, long length, object state);
79
80 //              static readonly string urlEncodedCType = "application/x-www-form-urlencoded";
81 //              static byte [] hexBytes;
82 //              ICredentials credentials;
83                 WebHeaderCollection headers;
84 //              WebHeaderCollection responseHeaders;
85                 Uri baseAddress;
86                 string baseString;
87 //              NameValueCollection queryString;
88                 bool is_busy, async;
89                 Thread async_thread;
90                 Encoding encoding = Encoding.UTF8;
91                 bool allow_read_buffering = true;
92 //              IWebProxy proxy;
93 //
94 //              // Constructors
95 //              static WebClient ()
96 //              {
97 //                      hexBytes = new byte [16];
98 //                      int index = 0;
99 //                      for (int i = '0'; i <= '9'; i++, index++)
100 //                              hexBytes [index] = (byte) i;
101 //
102 //                      for (int i = 'A'; i <= 'F'; i++, index++)
103 //                              hexBytes [index] = (byte) i;
104 //              }
105 //              
106 //              public WebClient ()
107 //              {
108 //              }
109 //              
110 //              // Properties
111 //              
112                 public string BaseAddress {
113                         get {
114                                 if (baseString == null) {
115                                         if (baseAddress == null)
116                                                 return "";
117                                 }
118
119                                 baseString = baseAddress.ToString ();
120                                 return baseString;
121                         }
122                         
123                         set {
124                                 if (value == null || value == "") {
125                                         baseAddress = null;
126                                 } else {
127                                         baseAddress = new Uri (value);
128                                 }
129                         }
130                 }
131 //
132 //#if NET_2_0
133 //              static Exception GetMustImplement ()
134 //              {
135 //                      return new NotImplementedException ();
136 //              }
137 //              
138 //              [MonoTODO]
139 //              public RequestCachePolicy CachePolicy
140 //              {
141 //                      get {
142 //                              throw GetMustImplement ();
143 //                      }
144 //                      set {
145 //                              throw GetMustImplement ();
146 //                      }
147 //              }
148 //
149 //              [MonoTODO]
150 //              public bool UseDefaultCredentials
151 //              {
152 //                      get {
153 //                              throw GetMustImplement ();
154 //                      }
155 //                      set {
156 //                              throw GetMustImplement ();
157 //                      }
158 //              }
159 //#endif
160 //              
161 //              public ICredentials Credentials {
162 //                      get { return credentials; }
163 //                      set { credentials = value; }
164 //              }
165 //
166                 public WebHeaderCollection Headers {
167                         get {
168                                 if (headers == null)
169                                         headers = new WebHeaderCollection ();
170
171                                 return headers;
172                         }
173                         set { headers = value; }
174                 }
175 //              
176 //              public NameValueCollection QueryString {
177 //                      get {
178 //                              if (queryString == null)
179 //                                      queryString = new NameValueCollection ();
180 //
181 //                              return queryString;
182 //                      }
183 //                      set { queryString = value; }
184 //              }
185 //              
186 //              public WebHeaderCollection ResponseHeaders {
187 //                      get { return responseHeaders; }
188 //              }
189 //
190 //#if NET_2_0
191                 public Encoding Encoding {
192                         get { return encoding; }
193                         set {
194                                 if (value == null)
195                                         throw new ArgumentNullException ("value");
196                                 encoding = value;
197                         }
198                 }
199 //
200 //              public IWebProxy Proxy {
201 //                      get { return proxy; }
202 //                      set { proxy = value; }
203 //              }
204 //#endif
205 //
206                 public bool IsBusy {
207                         get { return is_busy; }
208                 }
209
210                 [MonoTODO ("value is unused")]
211                 public bool AllowReadStreamBuffering {
212                         get { return allow_read_buffering; }
213                         set { allow_read_buffering = value; }
214                 }
215
216                 // Methods
217
218                 void CheckBusy ()
219                 {
220                         if (IsBusy)
221                                 throw new NotSupportedException ("WebClient does not support conccurent I/O operations.");
222                 }
223
224                 void SetBusy ()
225                 {
226                         lock (this) {
227                                 CheckBusy ();
228                                 is_busy = true;
229                         }
230                 }
231
232 //              //   DownloadData
233 //
234 //              public byte [] DownloadData (string address)
235 //              {
236 //#if NET_2_0
237 //                      if (address == null)
238 //                              throw new ArgumentNullException ("address");
239 //#endif
240 //
241 //                      return DownloadData (CreateUri (address));
242 //              }
243 //
244 //#if NET_2_0
245 //              public
246 //#endif
247 //              byte [] DownloadData (Uri address)
248 //              {
249 //#if NET_2_0
250 //                      if (address == null)
251 //                              throw new ArgumentNullException ("address");
252 //#endif
253 //
254 //                      try {
255 //                              SetBusy ();
256 //                              async = false;
257 //                              return DownloadDataCore (address, null);
258 //                      } finally {
259 //                              is_busy = false;
260 //                      }
261 //              }
262 //
263                 Stream DownloadDataCore (Uri address, object userToken)
264                 {
265                         WebRequest request = null;
266
267                         try {
268                                 request = SetupRequest (address, "GET");
269                                 //WebResponse response = request.GetResponse ();
270                                 IAsyncResult asyncresult = request.BeginGetResponse (null, userToken);
271                                 asyncresult.AsyncWaitHandle.WaitOne ();
272                                 WebResponse response = request.EndGetResponse (asyncresult);
273                                 Stream st = ProcessResponse (response);
274                                 return ReadAll (st, (int) st.Length, userToken);
275                         } catch (ThreadInterruptedException){
276                                 if (request != null)
277                                         request.Abort ();
278                                 throw;
279                         } catch (Exception ex) {
280                                 throw new WebException ("An error occurred " +
281                                         "performing a WebClient request.", ex);
282                         }
283                 }
284
285 //              //   DownloadFile
286 //
287 //              public void DownloadFile (string address, string fileName)
288 //              {
289 //#if NET_2_0
290 //                      if (address == null)
291 //                              throw new ArgumentNullException ("address");
292 //#endif
293 //
294 //                      DownloadFile (CreateUri (address), fileName);
295 //              }
296 //
297 //#if NET_2_0
298 //              public
299 //#endif
300 //              void DownloadFile (Uri address, string fileName)
301 //              {
302 //#if NET_2_0
303 //                      if (address == null)
304 //                              throw new ArgumentNullException ("address");
305 //                      if (fileName == null)
306 //                              throw new ArgumentNullException ("fileName");
307 //#endif
308 //
309 //                      try {
310 //                              SetBusy ();
311 //                              async = false;
312 //                              DownloadFileCore (address, fileName, null);
313 //                      } catch (Exception ex) {
314 //                              throw new WebException ("An error occurred " +
315 //                                      "performing a WebClient request.", ex);
316 //                      } finally {
317 //                              is_busy = false;
318 //                      }
319 //              }
320 //
321 //              void DownloadFileCore (Uri address, string fileName, object userToken)
322 //              {
323 //                      WebRequest request = null;
324 //                      
325 //                      using (FileStream f = new FileStream (fileName, FileMode.Create)) {
326 //                              try {
327 //                                      request = SetupRequest (address);
328 //                                      WebResponse response = request.GetResponse ();
329 //                                      Stream st = ProcessResponse (response);
330 //                                      
331 //                                      int cLength = (int) response.ContentLength;
332 //                                      int length = (cLength <= -1 || cLength > 32*1024) ? 32*1024 : cLength;
333 //                                      byte [] buffer = new byte [length];
334 //                                      
335 //                                      int nread = 0;
336 //#if NET_2_0
337 //                                      long notify_total = 0;
338 //#endif                                        
339 //                                      while ((nread = st.Read (buffer, 0, length)) != 0){
340 //#if NET_2_0
341 //                                              if (async){
342 //                                                      notify_total += nread;
343 //                                                      OnDownloadProgressChanged (
344 //                                                              new DownloadProgressChangedEventArgs (notify_total, response.ContentLength, userToken));
345 //                                                                                                    
346 //                                              }
347 //#endif
348 //                                              f.Write (buffer, 0, nread);
349 //                                      }
350 //                              } catch (ThreadInterruptedException){
351 //                                      if (request != null)
352 //                                              request.Abort ();
353 //                                      throw;
354 //                              }
355 //                      }
356 //              }
357 //
358 //              //   OpenRead
359 //
360 //              public Stream OpenRead (string address)
361 //              {
362 //#if NET_2_0
363 //                      if (address == null)
364 //                              throw new ArgumentNullException ("address");
365 //#endif
366 //
367 //                      return OpenRead (CreateUri (address));
368 //              }
369 //
370 //#if NET_2_0
371 //              public
372 //#endif
373 //              Stream OpenRead (Uri address)
374 //              {
375 //#if NET_2_0
376 //                      if (address == null)
377 //                              throw new ArgumentNullException ("address");
378 //#endif
379 //
380 //                      WebRequest request = null;
381 //                      try {
382 //                              SetBusy ();
383 //                              async = false;
384 //                              request = SetupRequest (address);
385 //                              WebResponse response = request.GetResponse ();
386 //                              return ProcessResponse (response);
387 //                      } catch (Exception ex) {
388 //                              throw new WebException ("An error occurred " +
389 //                                      "performing a WebClient request.", ex);
390 //                      } finally {
391 //                              is_busy = false;
392 //                      }
393 //              }
394 //
395 //              //   OpenWrite
396 //
397 //              public Stream OpenWrite (string address)
398 //              {
399 //#if NET_2_0
400 //                      if (address == null)
401 //                              throw new ArgumentNullException ("address");
402 //#endif
403 //
404 //                      return OpenWrite (CreateUri (address));
405 //              }
406 //              
407 //              public Stream OpenWrite (string address, string method)
408 //              {
409 //#if NET_2_0
410 //                      if (address == null)
411 //                              throw new ArgumentNullException ("address");
412 //#endif
413 //
414 //                      return OpenWrite (CreateUri (address), method);
415 //              }
416 //
417 //#if NET_2_0
418 //              public
419 //#endif
420 //              Stream OpenWrite (Uri address)
421 //              {
422 //                      return OpenWrite (address, (string) null);
423 //              }
424 //
425 //#if NET_2_0
426 //              public
427 //#endif
428 //              Stream OpenWrite (Uri address, string method)
429 //              {
430 //#if NET_2_0
431 //                      if (address == null)
432 //                              throw new ArgumentNullException ("address");
433 //#endif
434 //
435 //                      try {
436 //                              SetBusy ();
437 //                              async = false;
438 //                              WebRequest request = SetupRequest (address, method);
439 //                              return request.GetRequestStream ();
440 //                      } catch (Exception ex) {
441 //                              throw new WebException ("An error occurred " +
442 //                                      "performing a WebClient request.", ex);
443 //                      } finally {
444 //                              is_busy = false;
445 //                      }
446 //              }
447 //
448                 private string DetermineMethod (Uri address, string method)
449                 {
450                         if (method != null)
451                                 return method;
452
453                         if (address.Scheme == Uri.UriSchemeFtp)
454                                 return "RETR";
455                         return "POST";
456                 }
457
458 //              //   UploadData
459 //
460 //              public byte [] UploadData (string address, byte [] data)
461 //              {
462 //#if NET_2_0
463 //                      if (address == null)
464 //                              throw new ArgumentNullException ("address");
465 //#endif
466 //
467 //                      return UploadData (CreateUri (address), data);
468 //              }
469 //              
470 //              public byte [] UploadData (string address, string method, byte [] data)
471 //              {
472 //#if NET_2_0
473 //                      if (address == null)
474 //                              throw new ArgumentNullException ("address");
475 //#endif
476 //
477 //                      return UploadData (CreateUri (address), method, data);
478 //              }
479 //
480 //#if NET_2_0
481 //              public
482 //#endif
483 //              byte [] UploadData (Uri address, byte [] data)
484 //              {
485 //                      return UploadData (address, (string) null, data);
486 //              }
487 //
488 //#if NET_2_0
489 //              public
490 //#endif
491 //              byte [] UploadData (Uri address, string method, byte [] data)
492 //              {
493 //#if NET_2_0
494 //                      if (address == null)
495 //                              throw new ArgumentNullException ("address");
496 //                      if (data == null)
497 //                              throw new ArgumentNullException ("data");
498 //#endif
499 //
500 //                      try {
501 //                              SetBusy ();
502 //                              async = false;
503 //                              return UploadDataCore (address, method, data, null);
504 //                      } catch (Exception ex) {
505 //                              throw new WebException ("An error occurred " +
506 //                                      "performing a WebClient request.", ex);
507 //                      } finally {
508 //                              is_busy = false;
509 //                      }
510 //              }
511 //
512 //              byte [] UploadDataCore (Uri address, string method, byte [] data, object userToken)
513 //              {
514 //#if ONLY_1_1
515 //                      if (address == null)
516 //                              throw new ArgumentNullException ("address");
517 //                      if (data == null)
518 //                              throw new ArgumentNullException ("data");
519 //#endif
520 //
521 //                      WebRequest request = SetupRequest (address, method);
522 //                      try {
523 //                              int contentLength = data.Length;
524 //                              request.ContentLength = contentLength;
525 //                              using (Stream stream = request.GetRequestStream ()) {
526 //                                      stream.Write (data, 0, contentLength);
527 //                              }
528 //                              
529 //                              WebResponse response = request.GetResponse ();
530 //                              Stream st = ProcessResponse (response);
531 //                              return ReadAll (st, (int) response.ContentLength, userToken);
532 //                      } catch (ThreadInterruptedException){
533 //                              if (request != null)
534 //                                      request.Abort ();
535 //                              throw;
536 //                      }
537 //              }
538 //
539 //              //   UploadFile
540 //
541 //              public byte [] UploadFile (string address, string fileName)
542 //              {
543 //#if NET_2_0
544 //                      if (address == null)
545 //                              throw new ArgumentNullException ("address");
546 //#endif
547 //
548 //                      return UploadFile (CreateUri (address), fileName);
549 //              }
550 //
551 //#if NET_2_0
552 //              public
553 //#endif
554 //              byte [] UploadFile (Uri address, string fileName)
555 //              {
556 //                      return UploadFile (address, (string) null, fileName);
557 //              }
558 //              
559 //              public byte [] UploadFile (string address, string method, string fileName)
560 //              {
561 //                      return UploadFile (CreateUri (address), method, fileName);
562 //              }
563 //
564 //#if NET_2_0
565 //              public
566 //#endif
567 //              byte [] UploadFile (Uri address, string method, string fileName)
568 //              {
569 //#if NET_2_0
570 //                      if (address == null)
571 //                              throw new ArgumentNullException ("address");
572 //                      if (fileName == null)
573 //                              throw new ArgumentNullException ("fileName");
574 //#endif
575 //
576 //                      try {
577 //                              SetBusy ();
578 //                              async = false;
579 //                              return UploadFileCore (address, method, fileName, null);
580 //                      } catch (Exception ex) {
581 //                              throw new WebException ("An error occurred " +
582 //                                      "performing a WebClient request.", ex);
583 //                      } finally {
584 //                              is_busy = false;
585 //                      }
586 //              }
587 //
588 //              byte [] UploadFileCore (Uri address, string method, string fileName, object userToken)
589 //              {
590 //#if ONLY_1_1
591 //                      if (address == null)
592 //                              throw new ArgumentNullException ("address");
593 //#endif
594 //
595 //                      string fileCType = Headers ["Content-Type"];
596 //                      if (fileCType != null) {
597 //                              string lower = fileCType.ToLower ();
598 //                              if (lower.StartsWith ("multipart/"))
599 //                                      throw new WebException ("Content-Type cannot be set to a multipart" +
600 //                                                              " type for this request.");
601 //                      } else {
602 //                              fileCType = "application/octet-stream";
603 //                      }
604 //
605 //                      string boundary = "------------" + DateTime.Now.Ticks.ToString ("x");
606 //                      Headers ["Content-Type"] = String.Format ("multipart/form-data; boundary={0}", boundary);
607 //                      Stream reqStream = null;
608 //                      Stream fStream = null;
609 //                      byte [] resultBytes = null;
610 //
611 //                      fileName = Path.GetFullPath (fileName);
612 //
613 //                      WebRequest request = null;
614 //                      try {
615 //                              fStream = File.OpenRead (fileName);
616 //                              request = SetupRequest (address, method);
617 //                              reqStream = request.GetRequestStream ();
618 //                              byte [] realBoundary = Encoding.ASCII.GetBytes ("--" + boundary + "\r\n");
619 //                              reqStream.Write (realBoundary, 0, realBoundary.Length);
620 //                              string partHeaders = String.Format ("Content-Disposition: form-data; " +
621 //                                                                  "name=\"file\"; filename=\"{0}\"\r\n" +
622 //                                                                  "Content-Type: {1}\r\n\r\n",
623 //                                                                  Path.GetFileName (fileName), fileCType);
624 //
625 //                              byte [] partHeadersBytes = Encoding.UTF8.GetBytes (partHeaders);
626 //                              reqStream.Write (partHeadersBytes, 0, partHeadersBytes.Length);
627 //                              int nread;
628 //                              byte [] buffer = new byte [4096];
629 //                              while ((nread = fStream.Read (buffer, 0, 4096)) != 0)
630 //                                      reqStream.Write (buffer, 0, nread);
631 //
632 //                              reqStream.WriteByte ((byte) '\r');
633 //                              reqStream.WriteByte ((byte) '\n');
634 //                              reqStream.Write (realBoundary, 0, realBoundary.Length);
635 //                              reqStream.Close ();
636 //                              reqStream = null;
637 //                              WebResponse response = request.GetResponse ();
638 //                              Stream st = ProcessResponse (response);
639 //                              resultBytes = ReadAll (st, (int) response.ContentLength, userToken);
640 //                      } catch (ThreadInterruptedException){
641 //                              if (request != null)
642 //                                      request.Abort ();
643 //                              throw;
644 //                      } finally {
645 //                              if (fStream != null)
646 //                                      fStream.Close ();
647 //
648 //                              if (reqStream != null)
649 //                                      reqStream.Close ();
650 //                      }
651 //                      
652 //                      return resultBytes;
653 //              }
654 //              
655 //              public byte[] UploadValues (string address, NameValueCollection data)
656 //              {
657 //#if NET_2_0
658 //                      if (address == null)
659 //                              throw new ArgumentNullException ("address");
660 //#endif
661 //
662 //                      return UploadValues (CreateUri (address), data);
663 //              }
664 //              
665 //              public byte[] UploadValues (string address, string method, NameValueCollection data)
666 //              {
667 //#if NET_2_0
668 //                      if (address == null)
669 //                              throw new ArgumentNullException ("address");
670 //#endif
671 //
672 //                      return UploadValues (CreateUri (address), method, data);
673 //              }
674 //
675 //#if NET_2_0
676 //              public
677 //#endif
678 //              byte[] UploadValues (Uri address, NameValueCollection data)
679 //              {
680 //                      return UploadValues (address, (string) null, data);
681 //              }
682 //
683 //#if NET_2_0
684 //              public
685 //#endif
686 //              byte[] UploadValues (Uri address, string method, NameValueCollection data)
687 //              {
688 //#if NET_2_0
689 //                      if (address == null)
690 //                              throw new ArgumentNullException ("address");
691 //                      if (data == null)
692 //                              throw new ArgumentNullException ("data");
693 //#endif
694 //
695 //                      try {
696 //                              SetBusy ();
697 //                              async = false;
698 //                              return UploadValuesCore (address, method, data, null);
699 //                      } catch (Exception ex) {
700 //                              throw new WebException ("An error occurred " +
701 //                                      "performing a WebClient request.", ex);
702 //                      } finally {
703 //                              is_busy = false;
704 //                      }
705 //              }
706 //
707 //              byte[] UploadValuesCore (Uri uri, string method, NameValueCollection data, object userToken)
708 //              {
709 //#if ONLY_1_1
710 //                      if (data == null)
711 //                              throw new ArgumentNullException ("data");
712 //#endif
713 //
714 //                      string cType = Headers ["Content-Type"];
715 //                      if (cType != null && String.Compare (cType, urlEncodedCType, true) != 0)
716 //                              throw new WebException ("Content-Type header cannot be changed from its default " +
717 //                                                      "value for this request.");
718 //
719 //                      Headers ["Content-Type"] = urlEncodedCType;
720 //                      WebRequest request = SetupRequest (uri, method);
721 //                      try {
722 //                              Stream rqStream = request.GetRequestStream ();
723 //                              MemoryStream tmpStream = new MemoryStream ();
724 //                              foreach (string key in data) {
725 //                                      byte [] bytes = Encoding.ASCII.GetBytes (key);
726 //                                      UrlEncodeAndWrite (tmpStream, bytes);
727 //                                      tmpStream.WriteByte ((byte) '=');
728 //                                      bytes = Encoding.ASCII.GetBytes (data [key]);
729 //                                      UrlEncodeAndWrite (tmpStream, bytes);
730 //                                      tmpStream.WriteByte ((byte) '&');
731 //                              }
732 //                              
733 //                              int length = (int) tmpStream.Length;
734 //                              if (length > 0)
735 //                                      tmpStream.SetLength (--length); // remove trailing '&'
736 //                              
737 //                              byte [] buf = tmpStream.GetBuffer ();
738 //                              rqStream.Write (buf, 0, length);
739 //                              rqStream.Close ();
740 //                              tmpStream.Close ();
741 //                              
742 //                              WebResponse response = request.GetResponse ();
743 //                              Stream st = ProcessResponse (response);
744 //                              return ReadAll (st, (int) response.ContentLength, userToken);
745 //                      } catch (ThreadInterruptedException) {
746 //                              request.Abort ();
747 //                              throw;
748 //                      }
749 //              }
750 //
751 //#if NET_2_0
752 //              public string DownloadString (string address)
753 //              {
754 //                      return encoding.GetString (DownloadData (address));
755 //              }
756 //
757 //              public string DownloadString (Uri address)
758 //              {
759 //                      return encoding.GetString (DownloadData (address));
760 //              }
761 //
762 //              public string UploadString (string address, string data)
763 //              {
764 //                      if (address == null)
765 //                              throw new ArgumentNullException ("address");
766 //                      if (data == null)
767 //                              throw new ArgumentNullException ("data");
768 //
769 //                      byte [] resp = UploadData (address, encoding.GetBytes (data));
770 //                      return encoding.GetString (resp);
771 //              }
772 //
773 //              public string UploadString (string address, string method, string data)
774 //              {
775 //                      if (address == null)
776 //                              throw new ArgumentNullException ("address");
777 //                      if (data == null)
778 //                              throw new ArgumentNullException ("data");
779 //
780 //                      byte [] resp = UploadData (address, method, encoding.GetBytes (data));
781 //                      return encoding.GetString (resp);
782 //              }
783 //
784 //              public string UploadString (Uri address, string data)
785 //              {
786 //                      if (address == null)
787 //                              throw new ArgumentNullException ("address");
788 //                      if (data == null)
789 //                              throw new ArgumentNullException ("data");
790 //
791 //                      byte [] resp = UploadData (address, encoding.GetBytes (data));
792 //                      return encoding.GetString (resp);
793 //              }
794 //
795 //              public string UploadString (Uri address, string method, string data)
796 //              {
797 //                      if (address == null)
798 //                              throw new ArgumentNullException ("address");
799 //                      if (data == null)
800 //                              throw new ArgumentNullException ("data");
801 //
802 //                      byte [] resp = UploadData (address, method, encoding.GetBytes (data));
803 //                      return encoding.GetString (resp);
804 //              }
805 //
806 //              public event DownloadDataCompletedEventHandler DownloadDataCompleted;
807 //              public event AsyncCompletedEventHandler DownloadFileCompleted;
808                 public event DownloadProgressChangedEventHandler DownloadProgressChanged;
809                 public event DownloadStringCompletedEventHandler DownloadStringCompleted;
810                 public event OpenReadCompletedEventHandler OpenReadCompleted;
811                 public event OpenWriteCompletedEventHandler OpenWriteCompleted;
812 //              public event UploadDataCompletedEventHandler UploadDataCompleted;
813 //              public event UploadFileCompletedEventHandler UploadFileCompleted;
814                 public event UploadProgressChangedEventHandler UploadProgressChanged;
815                 public event UploadStringCompletedEventHandler UploadStringCompleted;
816 //              public event UploadValuesCompletedEventHandler UploadValuesCompleted;
817                 public event WriteStreamClosedEventHandler WriteStreamClosed;
818 //#endif
819 //
820 //              Uri CreateUri (string address)
821 //              {
822 //#if ONLY_1_1
823 //                      try {
824 //                              return MakeUri (address);
825 //                      } catch (Exception ex) {
826 //                              throw new WebException ("An error occurred " +
827 //                                      "performing a WebClient request.", ex);
828 //                      }
829 //#else
830 //                      return MakeUri (address);
831 //#endif
832 //              }
833 //
834 //              Uri MakeUri (string path)
835 //              {
836 //                      string query = null;
837 //                      if (queryString != null && queryString.Count != 0) {
838 //                              // This is not the same as UploadValues, because these 'keys' are not
839 //                              // urlencoded here.
840 //                              StringBuilder sb = new StringBuilder ();
841 //                              sb.Append ('?');
842 //                              foreach (string key in queryString)
843 //                                      sb.AppendFormat ("{0}={1}&", key, UrlEncode (queryString [key]));
844 //
845 //                              if (sb.Length != 0) {
846 //                                      sb.Length--; // remove trailing '&'
847 //                                      query = sb.ToString ();
848 //                              }
849 //                      }
850 //
851 //                      if (baseAddress == null && query == null) {
852 //                              try {
853 //                                      return new Uri (path);
854 //#if NET_2_0
855 //                              } catch (ArgumentNullException) {
856 //                                      path = Path.GetFullPath (path);
857 //                                      return new Uri ("file://" + path);
858 //#endif
859 //                              } catch (UriFormatException) {
860 //                                      path = Path.GetFullPath (path);
861 //                                      return new Uri ("file://" + path);
862 //                              }
863 //                      }
864 //
865 //                      if (baseAddress == null)
866 //                              return new Uri (path + query, (query != null));
867 //
868 //                      if (query == null)
869 //                              return new Uri (baseAddress, path);
870 //
871 //                      return new Uri (baseAddress, path + query, (query != null));
872 //              }
873 //              
874                 WebRequest SetupRequest (Uri uri)
875                 {
876                         WebRequest request = WebRequest.Create (baseAddress != null ? new Uri (baseAddress, uri) : uri);
877 //                      if (Proxy != null)
878 //                              request.Proxy = Proxy;
879 //                      request.Credentials = credentials;
880
881                         // Special headers. These are properties of HttpWebRequest.
882                         // What do we do with other requests differnt from HttpWebRequest?
883 //                      if (headers != null && headers.Count != 0 && (request is HttpWebRequest)) {
884 //                              HttpWebRequest req = (HttpWebRequest) request;
885 //                              string expect = headers ["Expect"];
886 //                              string contentType = headers ["Content-Type"];
887 //                              string accept = headers ["Accept"];
888 //                              string connection = headers ["Connection"];
889 //                              string userAgent = headers ["User-Agent"];
890 //                              string referer = headers ["Referer"];
891 //                              headers.RemoveInternal ("Expect");
892 //                              headers.RemoveInternal ("Content-Type");
893 //                              headers.RemoveInternal ("Accept");
894 //                              headers.RemoveInternal ("Connection");
895 //                              headers.RemoveInternal ("Referer");
896 //                              headers.RemoveInternal ("User-Agent");
897 //                              request.Headers = headers;
898 //
899 //                              if (expect != null && expect.Length > 0)
900 //                                      req.Expect = expect;
901 //
902 //                              if (accept != null && accept.Length > 0)
903 //                                      req.Accept = accept;
904 //
905 //                              if (contentType != null && contentType.Length > 0)
906 //                                      req.ContentType = contentType;
907 //
908 //                              if (connection != null && connection.Length > 0)
909 //                                      req.Connection = connection;
910 //
911 //                              if (userAgent != null && userAgent.Length > 0)
912 //                                      req.UserAgent = userAgent;
913 //
914 //                              if (referer != null && referer.Length > 0)
915 //                                      req.Referer = referer;
916 //                      }
917 //
918 //                      responseHeaders = null;
919                         request.SetupProgressDelegate ((ProgressChangedDelegate) delegate (long read, long length, object state) {
920                                 OnDownloadProgressChanged (new DownloadProgressChangedEventArgs (read, length, state));
921                         });
922                         return request;
923                 }
924
925                 WebRequest SetupRequest (Uri uri, string method)
926                 {
927                         WebRequest request = SetupRequest (uri);
928                         request.Method = DetermineMethod (uri, method);
929                         return request;
930                 }
931
932                 Stream ProcessResponse (WebResponse response)
933                 {
934 //                      responseHeaders = response.Headers;
935                         return response.GetResponseStream ();
936                 }
937
938                 Stream ReadAll (Stream stream, int length, object userToken)
939                 {
940                         MemoryStream ms = null;
941
942                         bool nolength = (length == -1);
943                         int size = ((nolength) ? 8192 : length);
944                         ms = new MemoryStream (size);
945
946                         int nread;
947                         byte [] buffer = new byte [size];
948                         while ((nread = stream.Read (buffer, 0, buffer.Length)) != 0) {
949                                 ms.Write (buffer, 0, nread);
950                                 if (async){
951                                         OnDownloadProgressChanged (new DownloadProgressChangedEventArgs (nread, length, userToken));
952                                 }
953                                 if (!nolength && ms.Length == length) {
954                                         break;
955                                 }
956                         }
957
958                         ms.Position = 0;
959                         return ms;
960                 }
961
962 //              string UrlEncode (string str)
963 //              {
964 //                      StringBuilder result = new StringBuilder ();
965 //
966 //                      int len = str.Length;
967 //                      for (int i = 0; i < len; i++) {
968 //                              char c = str [i];
969 //                              if (c == ' ')
970 //                                      result.Append ('+');
971 //                              else if ((c < '0' && c != '-' && c != '.') ||
972 //                                       (c < 'A' && c > '9') ||
973 //                                       (c > 'Z' && c < 'a' && c != '_') ||
974 //                                       (c > 'z')) {
975 //                                      result.Append ('%');
976 //                                      int idx = ((int) c) >> 4;
977 //                                      result.Append ((char) hexBytes [idx]);
978 //                                      idx = ((int) c) & 0x0F;
979 //                                      result.Append ((char) hexBytes [idx]);
980 //                              } else {
981 //                                      result.Append (c);
982 //                              }
983 //                      }
984 //
985 //                      return result.ToString ();
986 //              }
987 //
988 //              static void UrlEncodeAndWrite (Stream stream, byte [] bytes)
989 //              {
990 //                      if (bytes == null)
991 //                              return;
992 //
993 //                      int len = bytes.Length;
994 //                      if (len == 0)
995 //                              return;
996 //
997 //                      for (int i = 0; i < len; i++) {
998 //                              char c = (char) bytes [i];
999 //                              if (c == ' ')
1000 //                                      stream.WriteByte ((byte) '+');
1001 //                              else if ((c < '0' && c != '-' && c != '.') ||
1002 //                                       (c < 'A' && c > '9') ||
1003 //                                       (c > 'Z' && c < 'a' && c != '_') ||
1004 //                                       (c > 'z')) {
1005 //                                      stream.WriteByte ((byte) '%');
1006 //                                      int idx = ((int) c) >> 4;
1007 //                                      stream.WriteByte (hexBytes [idx]);
1008 //                                      idx = ((int) c) & 0x0F;
1009 //                                      stream.WriteByte (hexBytes [idx]);
1010 //                              } else {
1011 //                                      stream.WriteByte ((byte) c);
1012 //                              }
1013 //                      }
1014 //              }
1015 //
1016 //#if NET_2_0
1017                 [SecuritySafeCritical]
1018                 public void CancelAsync ()
1019                 {
1020                         lock (this){
1021                                 if (async_thread == null)
1022                                         return;
1023
1024                                 //
1025                                 // We first flag things as done, in case the Interrupt hangs
1026                                 // or the thread decides to hang in some other way inside the
1027                                 // event handlers, or if we are stuck somewhere else.  This
1028                                 // ensures that the WebClient object is reusable immediately
1029                                 //
1030                                 Thread t = async_thread;
1031                                 CompleteAsync ();
1032                                 t.Interrupt ();
1033                         }
1034                 }
1035
1036                 void CompleteAsync ()
1037                 {
1038                         lock (this){
1039                                 is_busy = false;
1040                                 async_thread = null;
1041                         }
1042                 }
1043
1044 //              //    DownloadDataAsync
1045 //
1046 //              public void DownloadDataAsync (Uri address)
1047 //              {
1048 //                      DownloadDataAsync (address, null);
1049 //              }
1050 //
1051 //              public void DownloadDataAsync (Uri address, object userToken)
1052 //              {
1053 //                      if (address == null)
1054 //                              throw new ArgumentNullException ("address");
1055 //                      
1056 //                      lock (this) {
1057 //                              SetBusy ();
1058 //                              async = true;
1059 //                              
1060 //                              async_thread = new Thread (delegate (object state) {
1061 //                                      object [] args = (object []) state;
1062 //                                      try {
1063 //                                              byte [] data = DownloadDataCore ((Uri) args [0], args [1]);
1064 //                                              OnDownloadDataCompleted (
1065 //                                                      new DownloadDataCompletedEventArgs (data, null, false, args [1]));
1066 //                                      } catch (ThreadInterruptedException){
1067 //                                              OnDownloadDataCompleted (
1068 //                                                      new DownloadDataCompletedEventArgs (null, null, true, args [1]));
1069 //                                              throw;
1070 //                                      } catch (Exception e){
1071 //                                              OnDownloadDataCompleted (
1072 //                                                      new DownloadDataCompletedEventArgs (null, e, false, args [1]));
1073 //                                      }
1074 //                              });
1075 //                              object [] cb_args = new object [] {address, userToken};
1076 //                              async_thread.Start (cb_args);
1077 //                      }
1078 //              }
1079 //
1080 //              //    DownloadFileAsync
1081 //
1082 //              public void DownloadFileAsync (Uri address, string fileName)
1083 //              {
1084 //                      DownloadFileAsync (address, fileName, null);
1085 //              }
1086 //
1087 //              public void DownloadFileAsync (Uri address, string fileName, object userToken)
1088 //              {
1089 //                      if (address == null)
1090 //                              throw new ArgumentNullException ("address");
1091 //                      if (fileName == null)
1092 //                              throw new ArgumentNullException ("fileName");
1093 //                      
1094 //                      lock (this) {
1095 //                              SetBusy ();
1096 //                              async = true;
1097 //
1098 //                              async_thread = new Thread (delegate (object state) {
1099 //                                      object [] args = (object []) state;
1100 //                                      try {
1101 //                                              DownloadFileCore ((Uri) args [0], (string) args [1], args [2]);
1102 //                                              OnDownloadFileCompleted (
1103 //                                                      new AsyncCompletedEventArgs (null, false, args [2]));
1104 //                                      } catch (ThreadInterruptedException){
1105 //                                              OnDownloadFileCompleted (
1106 //                                                      new AsyncCompletedEventArgs (null, true, args [2]));
1107 //                                      } catch (Exception e){
1108 //                                              OnDownloadFileCompleted (
1109 //                                                      new AsyncCompletedEventArgs (e, false, args [2]));
1110 //                                      }});
1111 //                              object [] cb_args = new object [] {address, fileName, userToken};
1112 //                              async_thread.Start (cb_args);
1113 //                      }
1114 //              }
1115 //
1116 //              //    DownloadStringAsync
1117 //
1118                 public void DownloadStringAsync (Uri address)
1119                 {
1120                         DownloadStringAsync (address, null);
1121                 }
1122
1123                 public void DownloadStringAsync (Uri address, object userToken)
1124                 {
1125                         if (address == null)
1126                                 throw new ArgumentNullException ("address");
1127
1128                         lock (this) {
1129                                 SetBusy ();
1130                                 async = true;
1131
1132                                 async_thread = new Thread (delegate (object state) {
1133                                         object [] args = (object []) state;
1134                                         try {
1135                                                 Stream bdata = DownloadDataCore ((Uri) args [0], args [1]);
1136                                                 string data;
1137                                                 using (StreamReader stream = new StreamReader (bdata, encoding, true))
1138                                                         data = stream.ReadToEnd ();
1139
1140                                                 OnDownloadStringCompleted (
1141                                                         new DownloadStringCompletedEventArgs (data, null, false, args [1]));
1142                                         } catch (ThreadInterruptedException){
1143                                                 OnDownloadStringCompleted (
1144                                                         new DownloadStringCompletedEventArgs (null, null, true, args [1]));
1145                                         } catch (Exception e){
1146                                                 OnDownloadStringCompleted (
1147                                                         new DownloadStringCompletedEventArgs (null, e, false, args [1]));
1148                                         }});
1149                                 object [] cb_args = new object [] {address, userToken};
1150                                 async_thread.Start (cb_args);
1151                         }
1152                 }
1153
1154                 //    OpenReadAsync
1155
1156                 public void OpenReadAsync (Uri address)
1157                 {
1158                         OpenReadAsync (address, null);
1159                 }
1160
1161                 public void OpenReadAsync (Uri address, object userToken)
1162                 {
1163                         if (address == null)
1164                                 throw new ArgumentNullException ("address");
1165
1166                         lock (this) {
1167                                 SetBusy ();
1168                                 async = true;
1169
1170                                 async_thread = new Thread (delegate (object state) {
1171                                         object [] args = (object []) state;
1172                                         WebRequest request = null;
1173                                         try {
1174                                                 request = SetupRequest ((Uri) args [0]);
1175                                                 //WebResponse response = request.GetResponse ();
1176                                                 IAsyncResult asyncresult = request.BeginGetResponse (null, userToken);
1177                                                 asyncresult.AsyncWaitHandle.WaitOne ();
1178                                                 WebResponse response = request.EndGetResponse (asyncresult);
1179                                                 Stream stream = ProcessResponse (response);
1180                                                 OnOpenReadCompleted (
1181                                                         new OpenReadCompletedEventArgs (stream, address, null, false, args [1]));
1182                                         } catch (ThreadInterruptedException){
1183                                                 if (request != null)
1184                                                         request.Abort ();
1185
1186                                                 OnOpenReadCompleted (new OpenReadCompletedEventArgs (null, null, null, true, args [1]));
1187                                         } catch (Exception e){
1188                                                 OnOpenReadCompleted (new OpenReadCompletedEventArgs (null, null, e, false, args [1]));
1189                                         } });
1190                                 object [] cb_args = new object [] {address, userToken};
1191                                 async_thread.Start (cb_args);
1192                         }
1193                 }
1194
1195 //              //    OpenWriteAsync
1196 //
1197                 public void OpenWriteAsync (Uri address)
1198                 {
1199                         OpenWriteAsync (address, null);
1200                 }
1201
1202                 public void OpenWriteAsync (Uri address, string method)
1203                 {
1204                         OpenWriteAsync (address, method, null);
1205                 }
1206
1207                 public void OpenWriteAsync (Uri address, string method, object userToken)
1208                 {
1209                         throw new NotImplementedException ();
1210 //                      if (address == null)
1211 //                              throw new ArgumentNullException ("address");
1212 //
1213 //                      lock (this) {
1214 //                              SetBusy ();
1215 //                              async = true;
1216 //
1217 //                              async_thread = new Thread (delegate (object state) {
1218 //                                      object [] args = (object []) state;
1219 //                                      WebRequest request = null;
1220 //                                      try {
1221 //                                              request = SetupRequest ((Uri) args [0], (string) args [1]);
1222 //                                              Stream stream = request.GetRequestStream ();
1223 //                                              OnOpenWriteCompleted (
1224 //                                                      new OpenWriteCompletedEventArgs (stream, null, false, args [2]));
1225 //                                      } catch (ThreadInterruptedException){
1226 //                                              if (request != null)
1227 //                                                      request.Abort ();
1228 //                                              OnOpenWriteCompleted (
1229 //                                                      new OpenWriteCompletedEventArgs (null, null, true, args [2]));
1230 //                                      } catch (Exception e){
1231 //                                              OnOpenWriteCompleted (
1232 //                                                      new OpenWriteCompletedEventArgs (null, e, false, args [2]));
1233 //                                      }});
1234 //                              object [] cb_args = new object [] {address, method, userToken};
1235 //                              async_thread.Start (cb_args);
1236 //                      }
1237                 }
1238 //
1239 //              //    UploadDataAsync
1240 //
1241 //              public void UploadDataAsync (Uri address, byte [] data)
1242 //              {
1243 //                      UploadDataAsync (address, null, data);
1244 //              }
1245 //
1246 //              public void UploadDataAsync (Uri address, string method, byte [] data)
1247 //              {
1248 //                      UploadDataAsync (address, method, data, null);
1249 //              }
1250 //
1251 //              public void UploadDataAsync (Uri address, string method, byte [] data, object userToken)
1252 //              {
1253 //                      if (address == null)
1254 //                              throw new ArgumentNullException ("address");
1255 //                      if (data == null)
1256 //                              throw new ArgumentNullException ("data");
1257 //                      
1258 //                      lock (this) {
1259 //                              SetBusy ();
1260 //                              async = true;
1261 //
1262 //                              async_thread = new Thread (delegate (object state) {
1263 //                                      object [] args = (object []) state;
1264 //                                      byte [] data2;
1265 //
1266 //                                      try {
1267 //                                              data2 = UploadDataCore ((Uri) args [0], (string) args [1], (byte []) args [2], args [3]);
1268 //                                      
1269 //                                              OnUploadDataCompleted (
1270 //                                                      new UploadDataCompletedEventArgs (data2, null, false, args [3]));
1271 //                                      } catch (ThreadInterruptedException){
1272 //                                              OnUploadDataCompleted (
1273 //                                                      new UploadDataCompletedEventArgs (null, null, true, args [3]));
1274 //                                      } catch (Exception e){
1275 //                                              OnUploadDataCompleted (
1276 //                                                      new UploadDataCompletedEventArgs (null, e, false, args [3]));
1277 //                                      }});
1278 //                              object [] cb_args = new object [] {address, method, data,  userToken};
1279 //                              async_thread.Start (cb_args);
1280 //                      }
1281 //              }
1282 //
1283 //              //    UploadFileAsync
1284 //
1285 //              public void UploadFileAsync (Uri address, string fileName)
1286 //              {
1287 //                      UploadFileAsync (address, null, fileName);
1288 //              }
1289 //
1290 //              public void UploadFileAsync (Uri address, string method, string fileName)
1291 //              {
1292 //                      UploadFileAsync (address, method, fileName, null);
1293 //              }
1294 //
1295 //              public void UploadFileAsync (Uri address, string method, string fileName, object userToken)
1296 //              {
1297 //                      if (address == null)
1298 //                              throw new ArgumentNullException ("address");
1299 //                      if (fileName == null)
1300 //                              throw new ArgumentNullException ("fileName");
1301 //
1302 //                      lock (this) {
1303 //                              SetBusy ();
1304 //                              async = true;
1305 //
1306 //                              async_thread = new Thread (delegate (object state) {
1307 //                                      object [] args = (object []) state;
1308 //                                      byte [] data;
1309 //
1310 //                                      try {
1311 //                                              data = UploadFileCore ((Uri) args [0], (string) args [1], (string) args [2], args [3]);
1312 //                                              OnUploadFileCompleted (
1313 //                                                      new UploadFileCompletedEventArgs (data, null, false, args [3]));
1314 //                                      } catch (ThreadInterruptedException){
1315 //                                              OnUploadFileCompleted (
1316 //                                                      new UploadFileCompletedEventArgs (null, null, true, args [3]));
1317 //                                      } catch (Exception e){
1318 //                                              OnUploadFileCompleted (
1319 //                                                      new UploadFileCompletedEventArgs (null, e, false, args [3]));
1320 //                                      }});
1321 //                              object [] cb_args = new object [] {address, method, fileName,  userToken};
1322 //                              async_thread.Start (cb_args);
1323 //                      }
1324 //              }
1325 //
1326 //              //    UploadStringAsync
1327 //
1328                 public void UploadStringAsync (Uri address, string data)
1329                 {
1330                         UploadStringAsync (address, null, data);
1331                 }
1332
1333                 public void UploadStringAsync (Uri address, string method, string data)
1334                 {
1335                         UploadStringAsync (address, method, data, null);
1336                 }
1337
1338                 public void UploadStringAsync (Uri address, string method, string data, object userToken)
1339                 {
1340                         throw new NotImplementedException ();
1341 //                      if (address == null)
1342 //                              throw new ArgumentNullException ("address");
1343 //                      if (data == null)
1344 //                              throw new ArgumentNullException ("data");
1345 //                      
1346 //                      lock (this) {
1347 //                              SetBusy ();
1348 //                              async = true;
1349 //                              
1350 //                              async_thread = new Thread (delegate (object state) {
1351 //                                      object [] args = (object []) state;
1352 //
1353 //                                      try {
1354 //                                              string data2 = UploadString ((Uri) args [0], (string) args [1], (string) args [2]);
1355 //                                              OnUploadStringCompleted (
1356 //                                                      new UploadStringCompletedEventArgs (data2, null, false, args [3]));
1357 //                                      } catch (ThreadInterruptedException){
1358 //                                              OnUploadStringCompleted (
1359 //                                                      new UploadStringCompletedEventArgs (null, null, true, args [3]));
1360 //                                      } catch (Exception e){
1361 //                                              OnUploadStringCompleted (
1362 //                                                      new UploadStringCompletedEventArgs (null, e, false, args [3]));
1363 //                                      }});
1364 //                              object [] cb_args = new object [] {address, method, data, userToken};
1365 //                              async_thread.Start (cb_args);
1366 //                      }
1367                 }
1368 //
1369 //              //    UploadValuesAsync
1370 //
1371 //              public void UploadValuesAsync (Uri address, NameValueCollection values)
1372 //              {
1373 //                      UploadValuesAsync (address, null, values);
1374 //              }
1375 //
1376 //              public void UploadValuesAsync (Uri address, string method, NameValueCollection values)
1377 //              {
1378 //                      UploadValuesAsync (address, method, values, null);
1379 //              }
1380 //
1381 //              public void UploadValuesAsync (Uri address, string method, NameValueCollection values, object userToken)
1382 //              {
1383 //                      if (address == null)
1384 //                              throw new ArgumentNullException ("address");
1385 //                      if (values == null)
1386 //                              throw new ArgumentNullException ("values");
1387 //
1388 //                      lock (this) {
1389 //                              CheckBusy ();
1390 //                              async = true;
1391 //
1392 //                              async_thread = new Thread (delegate (object state) {
1393 //                                      object [] args = (object []) state;
1394 //                                      try {
1395 //                                              byte [] data = UploadValuesCore ((Uri) args [0], (string) args [1], (NameValueCollection) args [2], args [3]);
1396 //                                              OnUploadValuesCompleted (
1397 //                                                      new UploadValuesCompletedEventArgs (data, null, false, args [3]));
1398 //                                      } catch (ThreadInterruptedException){
1399 //                                              OnUploadValuesCompleted (
1400 //                                                      new UploadValuesCompletedEventArgs (null, null, true, args [3]));
1401 //                                      } catch (Exception e){
1402 //                                              OnUploadValuesCompleted (
1403 //                                                      new UploadValuesCompletedEventArgs (null, e, false, args [3]));
1404 //                                      }});
1405 //                              object [] cb_args = new object [] {address, method, values,  userToken};
1406 //                              async_thread.Start (cb_args);
1407 //                      }
1408 //              }
1409 //
1410 //              protected virtual void OnDownloadDataCompleted (DownloadDataCompletedEventArgs args)
1411 //              {
1412 //                      CompleteAsync ();
1413 //                      if (DownloadDataCompleted != null)
1414 //                              DownloadDataCompleted (this, args);
1415 //              }
1416 //
1417 //              protected virtual void OnDownloadFileCompleted (AsyncCompletedEventArgs args)
1418 //              {
1419 //                      CompleteAsync ();
1420 //                      if (DownloadFileCompleted != null)
1421 //                              DownloadFileCompleted (this, args);
1422 //              }
1423 //
1424                 protected virtual void OnDownloadProgressChanged (DownloadProgressChangedEventArgs e)
1425                 {
1426                         if (DownloadProgressChanged != null) {
1427                                 DownloadProgressChanged (this, e);
1428                         }
1429                 }
1430                 
1431                 private object callback_args;
1432
1433                 protected virtual void OnOpenReadCompleted (OpenReadCompletedEventArgs args)
1434                 {
1435                         CompleteAsync ();
1436                         if (OpenReadCompleted != null) {
1437                                 ManualResetEvent wait_event = new ManualResetEvent (false);
1438                                 GSourceFunc callback = (GSourceFunc) delegate (IntPtr ctx)
1439                                 {
1440                                         try {
1441                                                 OpenReadCompleted (this, (OpenReadCompletedEventArgs) callback_args);
1442                                         } catch (Exception ex) {
1443                                                 try {
1444                                                         Console.WriteLine ("Unhandled exception: {0}", ex);
1445                                                 } catch {
1446                                                 }
1447                                         }
1448                                         try {
1449                                                 wait_event.Set ();
1450                                         } catch (Exception ex) {
1451                                                 try {
1452                                                         Console.WriteLine ("Unhandled exception: {0}", ex);
1453                                                 } catch {
1454                                                 }
1455                                         }
1456                                         return false;
1457                                 };
1458                                 callback_args = args;
1459
1460                                 g_timeout_add (0, callback, IntPtr.Zero);
1461
1462                                 wait_event.WaitOne ();
1463                                 GC.KeepAlive (callback);
1464                         }
1465                 }
1466
1467                 public delegate bool GSourceFunc (IntPtr data);
1468
1469                 [DllImport ("moon")]
1470                 static extern uint g_timeout_add (uint delay, GSourceFunc callback, IntPtr data);
1471
1472                 protected virtual void OnDownloadStringCompleted (DownloadStringCompletedEventArgs args)
1473                 {
1474                         CompleteAsync ();
1475                         if (DownloadStringCompleted != null) {
1476                                 ManualResetEvent wait_event = new ManualResetEvent (false);
1477                                 GSourceFunc callback = (GSourceFunc) delegate (IntPtr ctx) 
1478                                 {
1479                                         try {
1480                                                 DownloadStringCompleted (this, (DownloadStringCompletedEventArgs) callback_args);
1481                                         } catch (Exception ex) {
1482                                                 try {
1483                                                         Console.WriteLine ("Unhandled exception: {0}", ex);
1484                                                 } catch {
1485                                                 }
1486                                         }
1487                                         try {
1488                                                 wait_event.Set ();
1489                                         } catch (Exception ex) {
1490                                                 try {
1491                                                         Console.WriteLine ("Unhandled exception: {0}", ex);
1492                                                 } catch {
1493                                                 }
1494                                         }
1495                                         return false;
1496                                 };
1497                                 callback_args = args;
1498
1499                                 g_timeout_add (0, callback, IntPtr.Zero);
1500
1501                                 wait_event.WaitOne ();
1502                                 GC.KeepAlive (callback);
1503                         }
1504                 }
1505
1506
1507                 protected virtual void OnOpenWriteCompleted (OpenWriteCompletedEventArgs args)
1508                 {
1509                         CompleteAsync ();
1510                         if (OpenWriteCompleted != null)
1511                                 OpenWriteCompleted (this, args);
1512                 }
1513 //
1514 //              protected virtual void OnUploadDataCompleted (UploadDataCompletedEventArgs args)
1515 //              {
1516 //                      CompleteAsync ();
1517 //                      if (UploadDataCompleted != null)
1518 //                              UploadDataCompleted (this, args);
1519 //              }
1520 //
1521 //              protected virtual void OnUploadFileCompleted (UploadFileCompletedEventArgs args)
1522 //              {
1523 //                      CompleteAsync ();
1524 //                      if (UploadFileCompleted != null)
1525 //                              UploadFileCompleted (this, args);
1526 //              }
1527 //
1528                 protected virtual void OnUploadProgressChanged (UploadProgressChangedEventArgs e)
1529                 {
1530                         if (UploadProgressChanged != null)
1531                                 UploadProgressChanged (this, e);
1532                 }
1533
1534                 protected virtual void OnUploadStringCompleted (UploadStringCompletedEventArgs args)
1535                 {
1536                         CompleteAsync ();
1537                         if (UploadStringCompleted != null)
1538                                 UploadStringCompleted (this, args);
1539                 }
1540 //
1541 //              protected virtual void OnUploadValuesCompleted (UploadValuesCompletedEventArgs args)
1542 //              {
1543 //                      CompleteAsync ();
1544 //                      if (UploadValuesCompleted != null)
1545 //                              UploadValuesCompleted (this, args);
1546 //              }
1547 //
1548                 protected virtual void OnWriteStreamClosed (WriteStreamClosedEventArgs e)
1549                 {
1550                         throw new NotImplementedException ();
1551                 }
1552
1553                 [MonoNotSupported("")]
1554                 protected virtual WebRequest GetWebRequest (Uri address)
1555                 {
1556                         throw new NotImplementedException ();
1557                 }
1558 //
1559 //              protected virtual WebResponse GetWebResponse (WebRequest request)
1560 //              {
1561 //                      return request.GetResponse ();
1562 //              }
1563 //
1564                 protected virtual WebResponse GetWebResponse (WebRequest request, IAsyncResult result)
1565                 {
1566                         return request.EndGetResponse (result);
1567                 }
1568 //#endif
1569 #endif
1570         }
1571 }
1572
1573