/[classpath]/classpath/java/util/TimeZone.java
ViewVC logotype

Diff of /classpath/java/util/TimeZone.java

Parent Directory Parent Directory | Revision Log Revision Log | View Patch Patch

revision 1.24 by mark, Sat Aug 28 19:39:30 2004 UTC revision 1.25 by mark, Tue Aug 31 21:06:48 2004 UTC
# Line 38  exception statement from your version. * Line 38  exception statement from your version. *
38    
39    
40  package java.util;  package java.util;
 import gnu.classpath.Configuration;  
41    
 import java.io.*;  
42  import java.security.AccessController;  import java.security.AccessController;
43  import java.security.PrivilegedAction;  import java.security.PrivilegedAction;
44  import java.text.DateFormatSymbols;  import java.text.DateFormatSymbols;
# Line 90  public abstract class TimeZone implement Line 88  public abstract class TimeZone implement
88    /**    /**
89     * Tries to get the default TimeZone for this system if not already     * Tries to get the default TimeZone for this system if not already
90     * set.  It will call <code>getDefaultTimeZone(String)</code> with     * set.  It will call <code>getDefaultTimeZone(String)</code> with
91     * the result of     * the result of <code>System.getProperty("user.timezone")</code>.
92     * <code>System.getProperty("user.timezone")</code>,     * If that fails it calls <code>VMTimeZone.getDefaultTimeZoneId()</code>.
93     * <code>System.getenv("TZ")</code>,     * If that also fails GMT is returned.
    * <code>readTimeZoneFile("/etc/timezone")</code>,  
    * <code>readtzFile("/etc/localtime")</code> and  
    * <code>getDefaultTimeZoneId()</code>  
    * till a supported TimeZone is found.  
    * If every method fails GMT is returned.  
94     */     */
95    private static synchronized TimeZone defaultZone()    private static synchronized TimeZone defaultZone()
96    {    {
# Line 109  public abstract class TimeZone implement Line 102  public abstract class TimeZone implement
102              {              {
103                public Object run()                public Object run()
104                {                {
                 if (Configuration.INIT_LOAD_LIBRARY)  
                   {  
                     System.loadLibrary("javautil");  
                   }  
                   
105                  TimeZone zone = null;                  TimeZone zone = null;
106                                    
107                  // Prefer System property user.timezone.                  // Prefer System property user.timezone.
# Line 121  public abstract class TimeZone implement Line 109  public abstract class TimeZone implement
109                  if (tzid != null && !tzid.equals(""))                  if (tzid != null && !tzid.equals(""))
110                    zone = getDefaultTimeZone(tzid);                    zone = getDefaultTimeZone(tzid);
111                                    
112                  // See if TZ environment variable is set and accessible.                  // Try platfom specific way.
                 if (zone == null)  
                   {  
                     tzid = System.getenv("TZ");  
                     if (tzid != null && !tzid.equals(""))  
                       zone = getDefaultTimeZone(tzid);  
                   }  
                   
                 // Try to parse /etc/timezone.  
                 if (zone == null)  
                   {  
                     tzid = readTimeZoneFile("/etc/timezone");  
                     if (tzid != null && !tzid.equals(""))  
                       zone = getDefaultTimeZone(tzid);  
                   }  
                   
                 // Try to parse /etc/localtime  
                 if (zone == null)  
                   {  
                     tzid = readtzFile("/etc/localtime");  
                     if (tzid != null && !tzid.equals(""))  
                       zone = getDefaultTimeZone(tzid);  
                   }  
                   
                 // Try some system specific way  
113                  if (zone == null)                  if (zone == null)
114                    {                    zone = VMTimeZone.getDefaultTimeZoneId();
                     tzid = getDefaultTimeZoneId();  
                     if (tzid != null && !tzid.equals(""))  
                       zone = getDefaultTimeZone(tzid);  
                   }  
115                                    
116                  // Fall back on GMT.                  // Fall back on GMT.
117                  if (zone == null)                  if (zone == null)
# Line 843  public abstract class TimeZone implement Line 803  public abstract class TimeZone implement
803    }    }
804    
805    /**    /**
    * This method returns a time zone id string which is in the form  
    * (standard zone name) or (standard zone name)(GMT offset) or  
    * (standard zone name)(GMT offset)(daylight time zone name).  The  
    * GMT offset can be in seconds, or where it is evenly divisible by  
    * 3600, then it can be in hours.  The offset must be the time to  
    * add to the local time to get GMT.  If a offset is given and the  
    * time zone observes daylight saving then the (daylight time zone  
    * name) must also be given (otherwise it is assumed the time zone  
    * does not observe any daylight savings).  
    * <p>  
    * The result of this method is given to getDefaultTimeZone(String)  
    * which tries to map the time zone id to a known TimeZone.  See  
    * that method on how the returned String is mapped to a real  
    * TimeZone object.  
    */  
   private static native String getDefaultTimeZoneId();  
   
   /**  
    * Tries to read the time zone name from a file. Only the first  
    * consecutive letters, digits, slashes, dashes and underscores are  
    * read from the file. If the file cannot be read or an IOException  
    * occurs null is returned.  
    * <p>  
    * The /etc/timezone file is not standard, but a lot of systems have  
    * it. If it exist the first line always contains a string  
    * describing the timezone of the host of domain. Some systems  
    * contain a /etc/TIMEZONE file which is used to set the TZ  
    * environment variable (which is checked before /etc/timezone is  
    * read).  
    */  
   private static String readTimeZoneFile(String file)  
   {  
     File f = new File(file);  
     if (!f.exists())  
       return null;  
   
     InputStreamReader isr = null;  
     try  
       {  
         FileInputStream fis = new FileInputStream(f);  
         BufferedInputStream bis = new BufferedInputStream(fis);  
         isr = new InputStreamReader(bis);  
           
         StringBuffer sb = new StringBuffer();  
         int i = isr.read();  
         while (i != -1)  
           {  
             char c = (char) i;  
             if (Character.isLetter(c) || Character.isDigit(c)  
                 || c == '/' || c == '-' || c == '_')  
               {  
                 sb.append(c);  
                 i = isr.read();  
               }  
             else  
               break;  
           }  
         return sb.toString();  
       }  
     catch (IOException ioe)  
       {  
         // Parse error, not a proper tzfile.  
         return null;  
       }  
     finally  
       {  
         try  
           {  
             if (isr != null)  
               isr.close();  
           }  
         catch (IOException ioe)  
           {  
             // Error while close, nothing we can do.  
           }  
       }  
   }  
   
   /**  
    * Tries to read a file as a "standard" tzfile and return a time  
    * zone id string as expected by <code>getDefaultTimeZone(String)</code>.  
    * If the file doesn't exist, an IOException occurs or it isn't a tzfile  
    * that can be parsed null is returned.  
    * <p>  
    * The tzfile structure (as also used by glibc) is described in the Olson  
    * tz database archive as can be found at  
    * <code>ftp://elsie.nci.nih.gov/pub/</code>.  
    * <p>  
    * At least the following platforms support the tzdata file format  
    * and /etc/localtime (GNU/Linux, Darwin, Solaris and FreeBSD at  
    * least). Some systems (like Darwin) don't start the file with the  
    * required magic bytes 'TZif', this implementation can handle  
    * that).  
    */  
   private static String readtzFile(String file)  
   {  
     File f = new File(file);  
     if (!f.exists())  
       return null;  
       
     DataInputStream dis = null;  
     try  
       {  
         FileInputStream fis = new FileInputStream(f);  
         BufferedInputStream bis = new BufferedInputStream(fis);  
         dis = new DataInputStream(bis);  
           
         // Make sure we are reading a tzfile.  
         byte[] tzif = new byte[4];  
         dis.readFully(tzif);  
         if (tzif[0] == 'T' && tzif[1] == 'Z'  
             && tzif[2] == 'i' && tzif[3] == 'f')  
           // Reserved bytes, ttisgmtcnt, ttisstdcnt and leapcnt  
           skipFully(dis, 16 + 3 * 4);  
         else  
           // Darwin has tzdata files that don't start with the TZif marker  
           skipFully(dis, 16 + 3 * 4 - 4);  
           
         int timecnt = dis.readInt();  
         int typecnt = dis.readInt();  
         if (typecnt > 0)  
           {  
             int charcnt = dis.readInt();  
             // Transition times plus indexed transition times.  
             skipFully(dis, timecnt * (4 + 1));  
               
             // Get last gmt_offset and dst/non-dst time zone names.  
             int abbrind = -1;  
             int dst_abbrind = -1;  
             int gmt_offset = 0;  
             while (typecnt-- > 0)  
               {  
                 // gmtoff  
                 int offset = dis.readInt();  
                 int dst = dis.readByte();  
                 if (dst == 0)  
                   {  
                     abbrind = dis.readByte();  
                     gmt_offset = offset;  
                   }  
                 else  
                   dst_abbrind = dis.readByte();  
               }  
               
             // gmt_offset is the offset you must add to UTC/GMT to  
             // get the local time, we need the offset to add to  
             // the local time to get UTC/GMT.  
             gmt_offset *= -1;  
               
             // Turn into hours if possible.  
             if (gmt_offset % 3600 == 0)  
               gmt_offset /= 3600;  
               
             if (abbrind >= 0)  
               {  
                 byte[] names = new byte[charcnt];  
                 dis.readFully(names);  
                 int j = abbrind;  
                 while (j < charcnt && names[j] != 0)  
                   j++;  
                   
                 String zonename = new String(names, abbrind, j - abbrind,  
                                              "ASCII");  
                   
                 String dst_zonename;  
                 if (dst_abbrind >= 0)  
                   {  
                     j = dst_abbrind;  
                     while (j < charcnt && names[j] != 0)  
                       j++;  
                     dst_zonename = new String(names, dst_abbrind,  
                                               j - dst_abbrind, "ASCII");  
                   }  
                 else  
                   dst_zonename = "";  
                   
                 // Only use gmt offset when necessary.  
                 // Also special case GMT+/- timezones.  
                 String offset_string;  
                 if ("".equals(dst_zonename)  
                     && (gmt_offset == 0  
                         || zonename.startsWith("GMT+")  
                         || zonename.startsWith("GMT-")))  
                   offset_string = "";  
                 else  
                   offset_string = Integer.toString(gmt_offset);  
                   
                 String id = zonename + offset_string + dst_zonename;  
                   
                 return id;  
               }  
           }  
           
         // Something didn't match while reading the file.  
         return null;  
       }  
     catch (IOException ioe)  
       {  
         // Parse error, not a proper tzfile.  
         return null;  
       }  
     finally  
       {  
         try  
           {  
             if (dis != null)  
               dis.close();  
           }  
         catch(IOException ioe)  
           {  
             // Error while close, nothing we can do.  
           }  
       }  
   }  
     
   /**  
    * Skips the requested number of bytes in the given InputStream.  
    * Throws EOFException if not enough bytes could be skipped.  
    * Negative numbers of bytes to skip are ignored.  
    */  
   private static void skipFully(InputStream is, long l) throws IOException  
   {  
     while (l > 0)  
       {  
         long k = is.skip(l);  
         if (k <= 0)  
           throw new EOFException();  
         l -= k;  
       }  
   }  
     
   /**  
806     * Maps a time zone name (with optional GMT offset and daylight time     * Maps a time zone name (with optional GMT offset and daylight time
807     * zone name) to one of the known time zones.  This method called     * zone name) to one of the known time zones.  This method called
808     * with the result of <code>System.getProperty("user.timezone")</code>     * with the result of <code>System.getProperty("user.timezone")</code>
# Line 1111  public abstract class TimeZone implement Line 839  public abstract class TimeZone implement
839     * The standard time zone name for The Netherlands is "Europe/Amsterdam",     * The standard time zone name for The Netherlands is "Europe/Amsterdam",
840     * but can also be given as "CET-1CEST".     * but can also be given as "CET-1CEST".
841     */     */
842    private static TimeZone getDefaultTimeZone(String sysTimeZoneId)    static TimeZone getDefaultTimeZone(String sysTimeZoneId)
843    {    {
844      // First find start of GMT offset info and any Daylight zone name.      // First find start of GMT offset info and any Daylight zone name.
845      int startGMToffset = 0;      int startGMToffset = 0;
# Line 1119  public abstract class TimeZone implement Line 847  public abstract class TimeZone implement
847      for (int i = 0; i < sysTimeZoneIdLength && startGMToffset == 0; i++)      for (int i = 0; i < sysTimeZoneIdLength && startGMToffset == 0; i++)
848        {        {
849          char c = sysTimeZoneId.charAt(i);          char c = sysTimeZoneId.charAt(i);
850          if (c == '+' || c == '-' || Character.isDigit(c))          if (Character.isDigit(c))
851              startGMToffset = i;
852            else if ((c == '+' || c == '-')
853                     && i + 1 < sysTimeZoneIdLength
854                     && Character.isDigit(sysTimeZoneId.charAt(i + 1)))
855            startGMToffset = i;            startGMToffset = i;
856        }        }
857            

Legend:
Removed from v.1.24  
changed lines
  Added in v.1.25

savannah-hackers-public@gnu.org
ViewVC Help
Powered by ViewVC 1.1.26