OpenCores
URL https://opencores.org/ocsvn/scarts/scarts/trunk

Subversion Repositories scarts

[/] [scarts/] [trunk/] [toolchain/] [scarts-gcc/] [gcc-4.1.1/] [libjava/] [classpath/] [java/] [net/] [URLStreamHandler.java] - Blame information for rev 14

Details | Compare with Previous | View Log

Line No. Rev Author Line
1 14 jlechner
/* URLStreamHandler.java -- Abstract superclass for all protocol handlers
2
   Copyright (C) 1998, 1999, 2002, 2003, 2004 Free Software Foundation, Inc.
3
 
4
This file is part of GNU Classpath.
5
 
6
GNU Classpath is free software; you can redistribute it and/or modify
7
it under the terms of the GNU General Public License as published by
8
the Free Software Foundation; either version 2, or (at your option)
9
any later version.
10
 
11
GNU Classpath is distributed in the hope that it will be useful, but
12
WITHOUT ANY WARRANTY; without even the implied warranty of
13
MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE.  See the GNU
14
General Public License for more details.
15
 
16
You should have received a copy of the GNU General Public License
17
along with GNU Classpath; see the file COPYING.  If not, write to the
18
Free Software Foundation, Inc., 51 Franklin Street, Fifth Floor, Boston, MA
19
02110-1301 USA.
20
 
21
Linking this library statically or dynamically with other modules is
22
making a combined work based on this library.  Thus, the terms and
23
conditions of the GNU General Public License cover the whole
24
combination.
25
 
26
As a special exception, the copyright holders of this library give you
27
permission to link this library with independent modules to produce an
28
executable, regardless of the license terms of these independent
29
modules, and to copy and distribute the resulting executable under
30
terms of your choice, provided that you also meet, for each linked
31
independent module, the terms and conditions of the license of that
32
module.  An independent module is a module which is not derived from
33
or based on this library.  If you modify this library, you may extend
34
this exception to your version of the library, but you are not
35
obligated to do so.  If you do not wish to do so, delete this
36
exception statement from your version. */
37
 
38
package java.net;
39
 
40
import java.io.File;
41
import java.io.IOException;
42
 
43
 
44
/*
45
 * Written using on-line Java Platform 1.2 API Specification, as well
46
 * as "The Java Class Libraries", 2nd edition (Addison-Wesley, 1998).
47
 * Status:  Believed complete and correct.
48
 */
49
 
50
/**
51
 * This class is the superclass of all URL protocol handlers.  The URL
52
 * class loads the appropriate protocol handler to establish a connection
53
 * to a (possibly) remote service (eg, "http", "ftp") and to do protocol
54
 * specific parsing of URL's.  Refer to the URL class documentation for
55
 * details on how that class locates and loads protocol handlers.
56
 * <p>
57
 * A protocol handler implementation should override the openConnection()
58
 * method, and optionally override the parseURL() and toExternalForm()
59
 * methods if necessary. (The default implementations will parse/write all
60
 * URL's in the same form as http URL's).  A protocol  specific subclass
61
 * of URLConnection will most likely need to be created as well.
62
 * <p>
63
 * Note that the instance methods in this class are called as if they
64
 * were static methods.  That is, a URL object to act on is passed with
65
 * every call rather than the caller assuming the URL is stored in an
66
 * instance variable of the "this" object.
67
 * <p>
68
 * The methods in this class are protected and accessible only to subclasses.
69
 * URLStreamConnection objects are intended for use by the URL class only,
70
 * not by other classes (unless those classes are implementing protocols).
71
 *
72
 * @author Aaron M. Renn (arenn@urbanophile.com)
73
 * @author Warren Levy (warrenl@cygnus.com)
74
 *
75
 * @see URL
76
 */
77
public abstract class URLStreamHandler
78
{
79
  /**
80
   * Creates a URLStreamHander
81
   */
82
  public URLStreamHandler()
83
  {
84
  }
85
 
86
  /**
87
   * Returns a URLConnection for the passed in URL.  Note that this should
88
   * not actually create the connection to the (possibly) remote host, but
89
   * rather simply return a URLConnection object.  The connect() method of
90
   * URL connection is used to establish the actual connection, possibly
91
   * after the caller sets up various connection options.
92
   *
93
   * @param url The URL to get a connection object for
94
   *
95
   * @return A URLConnection object for the given URL
96
   *
97
   * @exception IOException If an error occurs
98
   */
99
  protected abstract URLConnection openConnection(URL url)
100
    throws IOException;
101
 
102
  /**
103
   * This method parses the string passed in as a URL and set's the
104
   * instance data fields in the URL object passed in to the various values
105
   * parsed out of the string.  The start parameter is the position to start
106
   * scanning the string.  This is usually the position after the ":" which
107
   * terminates the protocol name.  The end parameter is the position to
108
   * stop scanning.  This will be either the end of the String, or the
109
   * position of the "#" character, which separates the "file" portion of
110
   * the URL from the "anchor" portion.
111
   * <p>
112
   * This method assumes URL's are formatted like http protocol URL's, so
113
   * subclasses that implement protocols with URL's the follow a different
114
   * syntax should override this method.  The lone exception is that if
115
   * the protocol name set in the URL is "file", this method will accept
116
   * an empty hostname (i.e., "file:///"), which is legal for that protocol
117
   *
118
   * @param url The URL object in which to store the results
119
   * @param spec The String-ized URL to parse
120
   * @param start The position in the string to start scanning from
121
   * @param end The position in the string to stop scanning
122
   */
123
  protected void parseURL(URL url, String spec, int start, int end)
124
  {
125
    String host = url.getHost();
126
    int port = url.getPort();
127
    String file = url.getFile();
128
    String ref = url.getRef();
129
    String userInfo = url.getUserInfo();
130
    String authority = url.getAuthority();
131
    String query = null;
132
 
133
    // On Windows we need to change \ to / for file URLs
134
    char separator = File.separatorChar;
135
    if (url.getProtocol().equals("file") && separator != '/')
136
      {
137
        file = file.replace(separator, '/');
138
        spec = spec.replace(separator, '/');
139
      }
140
 
141
    if (spec.regionMatches(start, "//", 0, 2))
142
      {
143
        String genuineHost;
144
        int hostEnd;
145
        int colon;
146
        int at_host;
147
 
148
        start += 2;
149
        int slash = spec.indexOf('/', start);
150
        if (slash >= 0)
151
          hostEnd = slash;
152
        else
153
          hostEnd = end;
154
 
155
        authority = host = spec.substring(start, hostEnd);
156
 
157
        // We first need a genuine host name (with userinfo).
158
        // So we check for '@': if it's present check the port in the
159
        // section after '@' in the other case check it in the full string.
160
        // P.S.: We don't care having '@' at the beginning of the string.
161
        if ((at_host = host.indexOf('@')) >= 0)
162
          {
163
            genuineHost = host.substring(at_host);
164
            userInfo = host.substring(0, at_host);
165
          }
166
        else
167
          genuineHost = host;
168
 
169
        // Look for optional port number.  It is valid for the non-port
170
        // part of the host name to be null (e.g. a URL "http://:80").
171
        // TBD: JDK 1.2 in this case sets host to null rather than "";
172
        // this is undocumented and likely an unintended side effect in 1.2
173
        // so we'll be simple here and stick with "". Note that
174
        // "http://" or "http:///" produce a "" host in JDK 1.2.
175
        if ((colon = genuineHost.indexOf(':')) >= 0)
176
          {
177
            try
178
              {
179
                port = Integer.parseInt(genuineHost.substring(colon + 1));
180
              }
181
            catch (NumberFormatException e)
182
              {
183
                // Ignore invalid port values; port is already set to u's
184
                // port.
185
              }
186
 
187
            // Now we must cut the port number in the original string.
188
            if (at_host >= 0)
189
              host = host.substring(0, at_host + colon);
190
            else
191
              host = host.substring(0, colon);
192
          }
193
        file = null;
194
        start = hostEnd;
195
      }
196
    else if (host == null)
197
      host = "";
198
 
199
    if (file == null || file.length() == 0
200
        || (start < end && spec.charAt(start) == '/'))
201
      {
202
        // No file context available; just spec for file.
203
        // Or this is an absolute path name; ignore any file context.
204
        file = spec.substring(start, end);
205
        ref = null;
206
      }
207
    else if (start < end)
208
      {
209
        // Context is available, but only override it if there is a new file.
210
        int lastSlash = file.lastIndexOf('/');
211
        if (lastSlash < 0)
212
          file = spec.substring(start, end);
213
        else
214
          file = (file.substring(0, lastSlash)
215
                  + '/' + spec.substring(start, end));
216
 
217
        // For URLs constructed relative to a context, we
218
        // need to canonicalise the file path.
219
        file = canonicalizeFilename(file);
220
 
221
        ref = null;
222
      }
223
 
224
    if (ref == null)
225
      {
226
        // Normally there should be no '#' in the file part,
227
        // but we are nice.
228
        int hash = file.indexOf('#');
229
        if (hash != -1)
230
          {
231
            ref = file.substring(hash + 1, file.length());
232
            file = file.substring(0, hash);
233
          }
234
      }
235
 
236
    // We care about the query tag only if there is no reference at all.
237
    if (ref == null)
238
      {
239
          int queryTag = file.indexOf('?');
240
          if (queryTag != -1)
241
            {
242
              query = file.substring(queryTag + 1);
243
              file = file.substring(0, queryTag);
244
            }
245
      }
246
 
247
    // XXX - Classpath used to call PlatformHelper.toCanonicalForm() on
248
    // the file part. It seems like overhead, but supposedly there is some
249
    // benefit in windows based systems (it also lowercased the string).
250
    setURL(url, url.getProtocol(), host, port, authority, userInfo, file, query, ref);
251
  }
252
 
253
  /*
254
   * Canonicalize a filename.
255
   */
256
  private static String canonicalizeFilename(String file)
257
  {
258
    // XXX - GNU Classpath has an implementation that might be more appropriate
259
    // for Windows based systems (gnu.java.io.PlatformHelper.toCanonicalForm)
260
    int index;
261
 
262
    // Replace "/./" with "/".  This probably isn't very efficient in
263
    // the general case, but it's probably not bad most of the time.
264
    while ((index = file.indexOf("/./")) >= 0)
265
      file = file.substring(0, index) + file.substring(index + 2);
266
 
267
    // Process "/../" correctly.  This probably isn't very efficient in
268
    // the general case, but it's probably not bad most of the time.
269
    while ((index = file.indexOf("/../")) >= 0)
270
      {
271
        // Strip of the previous directory - if it exists.
272
        int previous = file.lastIndexOf('/', index - 1);
273
        if (previous >= 0)
274
          file = file.substring(0, previous) + file.substring(index + 3);
275
        else
276
          break;
277
      }
278
    return file;
279
  }
280
 
281
  /**
282
   * Compares two URLs, excluding the fragment component
283
   *
284
   * @param url1 The first url
285
   * @param url2 The second url to compare with the first
286
   *
287
   * @return True if both URLs point to the same file, false otherwise.
288
   *
289
   * @specnote Now protected
290
   */
291
  protected boolean sameFile(URL url1, URL url2)
292
  {
293
    if (url1 == url2)
294
      return true;
295
 
296
    // This comparison is very conservative.  It assumes that any
297
    // field can be null.
298
    if (url1 == null || url2 == null)
299
      return false;
300
    int p1 = url1.getPort();
301
    if (p1 == -1)
302
      p1 = url1.ph.getDefaultPort();
303
    int p2 = url2.getPort();
304
    if (p2 == -1)
305
      p2 = url2.ph.getDefaultPort();
306
    if (p1 != p2)
307
      return false;
308
    String s1;
309
    String s2;
310
    s1 = url1.getProtocol();
311
    s2 = url2.getProtocol();
312
    if (s1 != s2 && (s1 == null || ! s1.equals(s2)))
313
      return false;
314
    s1 = url1.getHost();
315
    s2 = url2.getHost();
316
    if (s1 != s2 && (s1 == null || ! s1.equals(s2)))
317
      return false;
318
    s1 = canonicalizeFilename(url1.getFile());
319
    s2 = canonicalizeFilename(url2.getFile());
320
    if (s1 != s2 && (s1 == null || ! s1.equals(s2)))
321
      return false;
322
    return true;
323
  }
324
 
325
  /**
326
   * This methods sets the instance variables representing the various fields
327
   * of the URL to the values passed in.
328
   *
329
   * @param u The URL to modify
330
   * @param protocol The protocol to set
331
   * @param host The host name to et
332
   * @param port The port number to set
333
   * @param file The filename to set
334
   * @param ref The reference
335
   *
336
   * @exception SecurityException If the protocol handler of the URL is
337
   * different from this one
338
   *
339
   * @deprecated 1.2 Please use
340
   * #setURL(URL,String,String,int,String,String,String,String);
341
   */
342
  protected void setURL(URL u, String protocol, String host, int port,
343
                        String file, String ref)
344
  {
345
    u.set(protocol, host, port, file, ref);
346
  }
347
 
348
  /**
349
   * Sets the fields of the URL argument to the indicated values
350
   *
351
   * @param u The URL to modify
352
   * @param protocol The protocol to set
353
   * @param host The host name to set
354
   * @param port The port number to set
355
   * @param authority The authority to set
356
   * @param userInfo The user information to set
357
   * @param path The path/filename to set
358
   * @param query The query part to set
359
   * @param ref The reference
360
   *
361
   * @exception SecurityException If the protocol handler of the URL is
362
   * different from this one
363
   */
364
  protected void setURL(URL u, String protocol, String host, int port,
365
                        String authority, String userInfo, String path,
366
                        String query, String ref)
367
  {
368
    u.set(protocol, host, port, authority, userInfo, path, query, ref);
369
  }
370
 
371
  /**
372
   * Provides the default equals calculation. May be overidden by handlers for
373
   * other protocols that have different requirements for equals(). This method
374
   * requires that none of its arguments is null. This is guaranteed by the
375
   * fact that it is only called by java.net.URL class.
376
   *
377
   * @param url1 An URL object
378
   * @param url2 An URL object
379
   *
380
   * @return True if both given URLs are equal, false otherwise.
381
   */
382
  protected boolean equals(URL url1, URL url2)
383
  {
384
    // This comparison is very conservative.  It assumes that any
385
    // field can be null.
386
    return (url1.getPort() == url2.getPort()
387
           && ((url1.getProtocol() == null && url2.getProtocol() == null)
388
           || (url1.getProtocol() != null
389
           && url1.getProtocol().equals(url2.getProtocol())))
390
           && ((url1.getUserInfo() == null && url2.getUserInfo() == null)
391
           || (url1.getUserInfo() != null
392
           && url1.getUserInfo().equals(url2.getUserInfo())))
393
           && ((url1.getAuthority() == null && url2.getAuthority() == null)
394
           || (url1.getAuthority() != null
395
           && url1.getAuthority().equals(url2.getAuthority())))
396
           && ((url1.getHost() == null && url2.getHost() == null)
397
           || (url1.getHost() != null && url1.getHost().equals(url2.getHost())))
398
           && ((url1.getPath() == null && url2.getPath() == null)
399
           || (url1.getPath() != null && url1.getPath().equals(url2.getPath())))
400
           && ((url1.getQuery() == null && url2.getQuery() == null)
401
           || (url1.getQuery() != null
402
           && url1.getQuery().equals(url2.getQuery())))
403
           && ((url1.getRef() == null && url2.getRef() == null)
404
           || (url1.getRef() != null && url1.getRef().equals(url2.getRef()))));
405
  }
406
 
407
  /**
408
   * Compares the host components of two URLs.
409
   *
410
   * @param url1 The first URL.
411
   * @param url2 The second URL.
412
   *
413
   * @return True if both URLs contain the same host.
414
   */
415
  protected boolean hostsEqual(URL url1, URL url2)
416
  {
417
    InetAddress addr1 = getHostAddress(url1);
418
    InetAddress addr2 = getHostAddress(url2);
419
 
420
    if (addr1 != null && addr2 != null)
421
      return addr1.equals(addr2);
422
 
423
    String host1 = url1.getHost();
424
    String host2 = url2.getHost();
425
 
426
    if (host1 != null && host2 != null)
427
      return host1.equalsIgnoreCase(host2);
428
 
429
    return host1 == null && host2 == null;
430
  }
431
 
432
  /**
433
   * Get the IP address of our host. An empty host field or a DNS failure will
434
   * result in a null return.
435
   *
436
   * @param url The URL to return the host address for.
437
   *
438
   * @return The address of the hostname in url.
439
   */
440
  protected InetAddress getHostAddress(URL url)
441
  {
442
    String hostname = url.getHost();
443
 
444
    if (hostname.equals(""))
445
      return null;
446
 
447
    try
448
      {
449
        return InetAddress.getByName(hostname);
450
      }
451
    catch (UnknownHostException e)
452
      {
453
        return null;
454
      }
455
  }
456
 
457
  /**
458
   * Returns the default port for a URL parsed by this handler. This method is
459
   * meant to be overidden by handlers with default port numbers.
460
   *
461
   * @return The default port number.
462
   */
463
  protected int getDefaultPort()
464
  {
465
    return -1;
466
  }
467
 
468
  /**
469
   * Provides the default hash calculation. May be overidden by handlers for
470
   * other protocols that have different requirements for hashCode calculation.
471
   *
472
   * @param url The URL to calc the hashcode for.
473
   *
474
   * @return The hashcode for the given URL.
475
   */
476
  protected int hashCode(URL url)
477
  {
478
    return url.getProtocol().hashCode()
479
           + ((url.getHost() == null) ? 0 : url.getHost().hashCode())
480
           + url.getFile().hashCode() + url.getPort();
481
  }
482
 
483
  /**
484
   * This method converts a URL object into a String.  This method creates
485
   * Strings in the mold of http URL's, so protocol handlers which use URL's
486
   * that have a different syntax should override this method
487
   *
488
   * @param url The URL object to convert
489
   *
490
   * @return A string representation of the url
491
   */
492
  protected String toExternalForm(URL url)
493
  {
494
    String protocol;
495
    String file;
496
    String ref;
497
    String authority;
498
 
499
    protocol = url.getProtocol();
500
    authority = url.getAuthority();
501
    if (authority == null)
502
      authority = "";
503
 
504
    file = url.getFile();
505
    ref = url.getRef();
506
 
507
    // Guess a reasonable size for the string buffer so we have to resize
508
    // at most once.
509
    int size = protocol.length() + authority.length() + file.length() + 24;
510
    StringBuffer sb = new StringBuffer(size);
511
 
512
    if (protocol.length() > 0)
513
      {
514
        sb.append(protocol);
515
        sb.append(":");
516
      }
517
 
518
    // If we have superfluous leading slashes (that means, at least 2)
519
    // we always add the authority component ("//" + host) to
520
    // avoid ambiguity. Otherwise we would generate an URL like
521
    // proto://home/foo
522
    // where we meant: 
523
    // host: <empty> - file: //home/foo
524
    // but URL spec says it is:
525
    // host: home - file: /foo
526
    if (authority.length() != 0 || file.startsWith("//") )
527
      sb.append("//").append(authority).append(file);
528
    else
529
      sb.append(file);
530
 
531
    if (ref != null)
532
      sb.append('#').append(ref);
533
 
534
    return sb.toString();
535
  }
536
}

powered by: WebSVN 2.1.0

© copyright 1999-2024 OpenCores.org, equivalent to Oliscience, all rights reserved. OpenCores®, registered trademark.