/*
 *******************************************************************************
 * Copyright (C) 2007-2014, International Business Machines Corporation and    *
 * others. All Rights Reserved.                                                *
 *******************************************************************************
 */
package com.ibm.icu.util;

import java.io.BufferedWriter;
import java.io.IOException;
import java.io.Reader;
import java.io.Writer;
import java.util.ArrayList;
import java.util.Date;
import java.util.LinkedList;
import java.util.List;
import java.util.MissingResourceException;
import java.util.StringTokenizer;

import com.ibm.icu.impl.Grego;

/**
 * <code>VTimeZone</code> is a class implementing RFC2445 VTIMEZONE.  You can create a
 * <code>VTimeZone</code> instance from a time zone ID supported by <code>TimeZone</code>.
 * With the <code>VTimeZone</code> instance created from the ID, you can write out the rule
 * in RFC2445 VTIMEZONE format.  Also, you can create a <code>VTimeZone</code> instance
 * from RFC2445 VTIMEZONE data stream, which allows you to calculate time
 * zone offset by the rules defined by the data.<br><br>
 * 
 * Note: The consumer of this class reading or writing VTIMEZONE data is responsible to
 * decode or encode Non-ASCII text.  Methods reading/writing VTIMEZONE data in this class
 * do nothing with MIME encoding.
 * 
 * @stable ICU 3.8
 */
public class VTimeZone extends BasicTimeZone {

    private static final long serialVersionUID = -6851467294127795902L;

    /**
     * Create a <code>VTimeZone</code> instance by the time zone ID.
     * 
     * @param tzid The time zone ID, such as America/New_York
     * @return A <code>VTimeZone</code> initialized by the time zone ID, or null
     * when the ID is unknown.
     * 
     * @stable ICU 3.8
     */
    public static VTimeZone create(String tzid) {
        VTimeZone vtz = new VTimeZone(tzid);
        vtz.tz = (BasicTimeZone)TimeZone.getTimeZone(tzid, TimeZone.TIMEZONE_ICU);
        vtz.olsonzid = vtz.tz.getID();

        return vtz;
    }
    
    /**
     * Create a <code>VTimeZone</code> instance by RFC2445 VTIMEZONE data.
     * 
     * @param reader The Reader for VTIMEZONE data input stream
     * @return A <code>VTimeZone</code> initialized by the VTIMEZONE data or
     * null if failed to load the rule from the VTIMEZONE data.
     * 
     * @stable ICU 3.8
     */
    public static VTimeZone create(Reader reader) {
        VTimeZone vtz = new VTimeZone();
        if (vtz.load(reader)) {
            return vtz;
        }
        return null;
    }

    /**
     * {@inheritDoc}
     * @stable ICU 3.8
     */
    @Override
    public int getOffset(int era, int year, int month, int day, int dayOfWeek,
            int milliseconds) {
        return tz.getOffset(era, year, month, day, dayOfWeek, milliseconds);
    }

    /**
     * {@inheritDoc}
     * @stable ICU 3.8
     */
    @Override
    public void getOffset(long date, boolean local, int[] offsets) {
        tz.getOffset(date, local, offsets);
    }

    /**
     * {@inheritDoc}
     * @internal
     * @deprecated This API is ICU internal only.
     */
    @Deprecated
    @Override
    public void getOffsetFromLocal(long date,
            int nonExistingTimeOpt, int duplicatedTimeOpt, int[] offsets) {
        tz.getOffsetFromLocal(date, nonExistingTimeOpt, duplicatedTimeOpt, offsets);
    }

    /**
     * {@inheritDoc}
     * @stable ICU 3.8
     */
    @Override
    public int getRawOffset() {
        return tz.getRawOffset();
    }

    /**
     * {@inheritDoc}
     * @stable ICU 3.8
     */
    @Override
    public boolean inDaylightTime(Date date) {
        return tz.inDaylightTime(date);
    }

    /**
     * {@inheritDoc}
     * @stable ICU 3.8
     */
    @Override
    public void setRawOffset(int offsetMillis) {
        if (isFrozen()) {
            throw new UnsupportedOperationException("Attempt to modify a frozen VTimeZone instance.");
        }
        tz.setRawOffset(offsetMillis);
    }

    /**
     * {@inheritDoc}
     * @stable ICU 3.8
     */
    @Override
    public boolean useDaylightTime() {
        return tz.useDaylightTime();
    }

    /**
     * {@inheritDoc}
     * @stable ICU 49
     */
    @Override
    public boolean observesDaylightTime() {
        return tz.observesDaylightTime();
    }

    /**
     * {@inheritDoc}
     * @stable ICU 3.8
     */
    @Override
    public boolean hasSameRules(TimeZone other) {
        if (this == other) {
            return true;
        }
        if (other instanceof VTimeZone) {
            return tz.hasSameRules(((VTimeZone)other).tz);
        }
        return tz.hasSameRules(other);
    }

    /**
     * Gets the RFC2445 TZURL property value.  When a <code>VTimeZone</code> instance was created from
     * VTIMEZONE data, the value is set by the TZURL property value in the data.  Otherwise,
     * the initial value is null.
     * 
     * @return The RFC2445 TZURL property value
     * 
     * @stable ICU 3.8
     */
    public String getTZURL() {
        return tzurl;
    }

    /**
     * Sets the RFC2445 TZURL property value.
     * 
     * @param url The TZURL property value.
     * 
     * @stable ICU 3.8
     */
    public void setTZURL(String url) {
        if (isFrozen()) {
            throw new UnsupportedOperationException("Attempt to modify a frozen VTimeZone instance.");
        }
        tzurl = url;
    }

    /**
     * Gets the RFC2445 LAST-MODIFIED property value.  When a <code>VTimeZone</code> instance was created
     * from VTIMEZONE data, the value is set by the LAST-MODIFIED property value in the data.
     * Otherwise, the initial value is null.
     * 
     * @return The Date represents the RFC2445 LAST-MODIFIED date.
     * 
     * @stable ICU 3.8
     */
    public Date getLastModified() {
        return lastmod;
    }

    /**
     * Sets the date used for RFC2445 LAST-MODIFIED property value.
     * 
     * @param date The <code>Date</code> object represents the date for RFC2445 LAST-MODIFIED property value.
     * 
     * @stable ICU 3.8
     */
    public void setLastModified(Date date) {
        if (isFrozen()) {
            throw new UnsupportedOperationException("Attempt to modify a frozen VTimeZone instance.");
        }
        lastmod = date;
    }

    /**
     * Writes RFC2445 VTIMEZONE data for this time zone
     * 
     * @param writer A <code>Writer</code> used for the output
     * @throws IOException If there were problems creating a buffered writer or writing to it.
     * 
     * @stable ICU 3.8
     */
    public void write(Writer writer) throws IOException {
        BufferedWriter bw = new BufferedWriter(writer);
        if (vtzlines != null) {
            for (String line : vtzlines) {
                if (line.startsWith(ICAL_TZURL + COLON)) {
                    if (tzurl != null) {
                        bw.write(ICAL_TZURL);
                        bw.write(COLON);
                        bw.write(tzurl);
                        bw.write(NEWLINE);
                    }
                } else if (line.startsWith(ICAL_LASTMOD + COLON)) {
                    if (lastmod != null) {
                        bw.write(ICAL_LASTMOD);
                        bw.write(COLON);
                        bw.write(getUTCDateTimeString(lastmod.getTime()));
                        bw.write(NEWLINE);
                    }
                } else {
                    bw.write(line);
                    bw.write(NEWLINE);
                }
            }
            bw.flush();
        } else {
            String[] customProperties = null;
            if (olsonzid != null && ICU_TZVERSION != null) {
                customProperties = new String[1];
                customProperties[0] = ICU_TZINFO_PROP + COLON + olsonzid + "[" + ICU_TZVERSION + "]";
            }
            writeZone(writer, tz, customProperties);
        }
    }

    /**
     * Writes RFC2445 VTIMEZONE data applicable for dates after
     * the specified start time.
     * 
     * @param writer    The <code>Writer</code> used for the output
     * @param start     The start time
     * 
     * @throws IOException If there were problems reading and writing to the writer.
     * 
     * @stable ICU 3.8
     */
    public void write(Writer writer, long start) throws IOException {
        // Extract rules applicable to dates after the start time
        TimeZoneRule[] rules = tz.getTimeZoneRules(start);

        // Create a RuleBasedTimeZone with the subset rule
        RuleBasedTimeZone rbtz = new RuleBasedTimeZone(tz.getID(), (InitialTimeZoneRule)rules[0]);
        for (int i = 1; i < rules.length; i++) {
            rbtz.addTransitionRule(rules[i]);
        }
        String[] customProperties = null;
        if (olsonzid != null && ICU_TZVERSION != null) {
            customProperties = new String[1];
            customProperties[0] = ICU_TZINFO_PROP + COLON + olsonzid + "[" + ICU_TZVERSION + 
                "/Partial@" + start + "]";
        }
        writeZone(writer, rbtz, customProperties);
    }

    /**
     * Writes RFC2445 VTIMEZONE data applicable near the specified date.
     * Some common iCalendar implementations can only handle a single time
     * zone property or a pair of standard and daylight time properties using
     * BYDAY rule with day of week (such as BYDAY=1SUN).  This method produce
     * the VTIMEZONE data which can be handled these implementations.  The rules
     * produced by this method can be used only for calculating time zone offset
     * around the specified date.
     * 
     * @param writer    The <code>Writer</code> used for the output
     * @param time      The date
     * 
     * @throws IOException If there were problems reading or writing to the writer.
     * 
     * @stable ICU 3.8
     */
    public void writeSimple(Writer writer, long time) throws IOException {
        // Extract simple rules
        TimeZoneRule[] rules = tz.getSimpleTimeZoneRulesNear(time);

        // Create a RuleBasedTimeZone with the subset rule
        RuleBasedTimeZone rbtz = new RuleBasedTimeZone(tz.getID(), (InitialTimeZoneRule)rules[0]);
        for (int i = 1; i < rules.length; i++) {
            rbtz.addTransitionRule(rules[i]);
        }
        String[] customProperties = null;
        if (olsonzid != null && ICU_TZVERSION != null) {
            customProperties = new String[1];
            customProperties[0] = ICU_TZINFO_PROP + COLON + olsonzid + "[" + ICU_TZVERSION + 
                "/Simple@" + time + "]";
        }
        writeZone(writer, rbtz, customProperties);
    }

    // BasicTimeZone methods

    /**
     * {@inheritDoc}
     * @stable ICU 3.8
     */
    @Override
    public TimeZoneTransition getNextTransition(long base, boolean inclusive) {
        return tz.getNextTransition(base, inclusive);
    }

    /**
     * {@inheritDoc}
     * @stable ICU 3.8
     */
    @Override
    public TimeZoneTransition getPreviousTransition(long base, boolean inclusive) {
        return tz.getPreviousTransition(base, inclusive);
    }

    /**
     * {@inheritDoc}
     * @stable ICU 3.8
     */
    @Override
    public boolean hasEquivalentTransitions(TimeZone other, long start, long end) {
        if (this == other) {
            return true;
        }
        return tz.hasEquivalentTransitions(other, start, end);
    }

    /**
     * {@inheritDoc}
     * @stable ICU 3.8
     */
    @Override
    public TimeZoneRule[] getTimeZoneRules() {
        return tz.getTimeZoneRules();
    }

    /**
     * {@inheritDoc}
     * @stable ICU 3.8
     */
    @Override
    public TimeZoneRule[] getTimeZoneRules(long start) {
        return tz.getTimeZoneRules(start);
    }

    /**
     * {@inheritDoc}
     * @stable ICU 3.8
     */
    @Override
    public Object clone() {
        if (isFrozen()) {
            return this;
        }
        return cloneAsThawed();
    }

    // private stuff ------------------------------------------------------

    private BasicTimeZone tz;
    private List<String> vtzlines;
    private String olsonzid = null;
    private String tzurl = null;
    private Date lastmod = null;

    private static String ICU_TZVERSION;
    private static final String ICU_TZINFO_PROP = "X-TZINFO";

    // Default DST savings
    private static final int DEF_DSTSAVINGS = 60*60*1000; // 1 hour
    
    // Default time start
    private static final long DEF_TZSTARTTIME = 0;

    // minimum/max
    private static final long MIN_TIME = Long.MIN_VALUE;
    private static final long MAX_TIME = Long.MAX_VALUE;

    // Symbol characters used by RFC2445 VTIMEZONE
    private static final String COLON = ":";
    private static final String SEMICOLON = ";";
    private static final String EQUALS_SIGN = "=";
    private static final String COMMA = ",";
    private static final String NEWLINE = "\r\n";   // CRLF

    // RFC2445 VTIMEZONE tokens
    private static final String ICAL_BEGIN_VTIMEZONE = "BEGIN:VTIMEZONE";
    private static final String ICAL_END_VTIMEZONE = "END:VTIMEZONE";
    private static final String ICAL_BEGIN = "BEGIN";
    private static final String ICAL_END = "END";
    private static final String ICAL_VTIMEZONE = "VTIMEZONE";
    private static final String ICAL_TZID = "TZID";
    private static final String ICAL_STANDARD = "STANDARD";
    private static final String ICAL_DAYLIGHT = "DAYLIGHT";
    private static final String ICAL_DTSTART = "DTSTART";
    private static final String ICAL_TZOFFSETFROM = "TZOFFSETFROM";
    private static final String ICAL_TZOFFSETTO = "TZOFFSETTO";
    private static final String ICAL_RDATE = "RDATE";
    private static final String ICAL_RRULE = "RRULE";
    private static final String ICAL_TZNAME = "TZNAME";
    private static final String ICAL_TZURL = "TZURL";
    private static final String ICAL_LASTMOD = "LAST-MODIFIED";

    private static final String ICAL_FREQ = "FREQ";
    private static final String ICAL_UNTIL = "UNTIL";
    private static final String ICAL_YEARLY = "YEARLY";
    private static final String ICAL_BYMONTH = "BYMONTH";
    private static final String ICAL_BYDAY = "BYDAY";
    private static final String ICAL_BYMONTHDAY = "BYMONTHDAY";

    private static final String[] ICAL_DOW_NAMES = 
    {"SU", "MO", "TU", "WE", "TH", "FR", "SA"};

    // Month length in regular year
    private static final int[] MONTHLENGTH = {31, 28, 31, 30, 31, 30, 31, 31, 30, 31, 30, 31};

    static {
        // Initialize ICU_TZVERSION
        try {
            ICU_TZVERSION = TimeZone.getTZDataVersion();
        } catch (MissingResourceException e) {
            ///CLOVER:OFF
            ICU_TZVERSION = null;
            ///CLOVER:ON
        }
    }
    
    /* Hide the constructor */
    private VTimeZone() {
    }

    private VTimeZone(String tzid) {
        super(tzid);
    }

    /*
     * Read the input stream to locate the VTIMEZONE block and
     * parse the contents to initialize this VTimeZone object.
     * The reader skips other RFC2445 message headers.  After
     * the parse is completed, the reader points at the beginning
     * of the header field just after the end of VTIMEZONE block.
     * When VTIMEZONE block is found and this object is successfully
     * initialized by the rules described in the data, this method
     * returns true.  Otherwise, returns false.
     */
    private boolean load(Reader reader) {
        // Read VTIMEZONE block into string array
        try {
            vtzlines = new LinkedList<String>();
            boolean eol = false;
            boolean start = false;
            boolean success = false;
            StringBuilder line = new StringBuilder();
            while (true) {
                int ch = reader.read();
                if (ch == -1) {
                    // end of file
                    if (start && line.toString().startsWith(ICAL_END_VTIMEZONE)) {
                        vtzlines.add(line.toString());
                        success = true;
                    }
                    break;
                }
                if (ch == 0x0D) {
                    // CR, must be followed by LF by the definition in RFC2445
                    continue;
                }

                if (eol) {
                    if (ch != 0x09 && ch != 0x20) {
                        // NOT followed by TAB/SP -> new line
                        if (start) {
                            if (line.length() > 0) {
                                vtzlines.add(line.toString());
                            }
                        }
                        line.setLength(0);
                        if (ch != 0x0A) {
                            line.append((char)ch);
                        }
                    }
                    eol = false;
                } else {
                    if (ch == 0x0A) {
                        // LF
                        eol = true;
                        if (start) {
                            if (line.toString().startsWith(ICAL_END_VTIMEZONE)) {
                                vtzlines.add(line.toString());
                                success = true;
                                break;
                            }
                        } else {
                            if (line.toString().startsWith(ICAL_BEGIN_VTIMEZONE)) {
                                vtzlines.add(line.toString());
                                line.setLength(0);
                                start = true;
                                eol = false;
                            }
                        }
                    } else {
                        line.append((char)ch);
                    }
                }
            }
            if (!success) {
                return false;
            }
        } catch (IOException ioe) {
            ///CLOVER:OFF
            return false;
            ///CLOVER:ON
        }
        return parse();
    }

    // parser state
    private static final int INI = 0;   // Initial state
    private static final int VTZ = 1;   // In VTIMEZONE
    private static final int TZI = 2;   // In STANDARD or DAYLIGHT
    private static final int ERR = 3;   // Error state

    /*
     * Parse VTIMEZONE data and create a RuleBasedTimeZone
     */
    private boolean parse() {
        ///CLOVER:OFF
        if (vtzlines == null || vtzlines.size() == 0) {
            return false;
        }
        ///CLOVER:ON

        // timezone ID
        String tzid = null;

        int state = INI;
        boolean dst = false;    // current zone type
        String from = null;     // current zone from offset
        String to = null;       // current zone offset
        String tzname = null;   // current zone name
        String dtstart = null;  // current zone starts
        boolean isRRULE = false;    // true if the rule is described by RRULE
        List<String> dates = null;  // list of RDATE or RRULE strings
        List<TimeZoneRule> rules = new ArrayList<TimeZoneRule>();   // rule list
        int initialRawOffset = 0;  // initial offset
        int initialDSTSavings = 0;  // initial offset
        long firstStart = MAX_TIME; // the earliest rule start time

        for (String line : vtzlines) {
            int valueSep = line.indexOf(COLON);
            if (valueSep < 0) {
                continue;
            }
            String name = line.substring(0, valueSep);
            String value = line.substring(valueSep + 1);

            switch (state) {
            case INI:
                if (name.equals(ICAL_BEGIN) && value.equals(ICAL_VTIMEZONE)) {
                    state = VTZ;
                }
                break;
            case VTZ:
                if (name.equals(ICAL_TZID)) {
                    tzid = value;
                } else if (name.equals(ICAL_TZURL)) {
                    tzurl = value;
                } else if (name.equals(ICAL_LASTMOD)) {
                    // Always in 'Z' format, so the offset argument for the parse method
                    // can be any value.
                    lastmod = new Date(parseDateTimeString(value, 0));
                } else if (name.equals(ICAL_BEGIN)) {
                    boolean isDST = value.equals(ICAL_DAYLIGHT);
                    if (value.equals(ICAL_STANDARD) || isDST) {
                        // tzid must be ready at this point
                        if (tzid == null) {
                            state = ERR;
                            break;
                        }
                        // initialize current zone properties
                        dates = null;
                        isRRULE = false;
                        from = null;
                        to = null;
                        tzname = null;
                        dst = isDST;
                        state = TZI;
                    } else {
                        // BEGIN property other than STANDARD/DAYLIGHT
                        // must not be there.
                        state = ERR;
                        break;
                    }
                } else if (name.equals(ICAL_END) /* && value.equals(ICAL_VTIMEZONE) */) {
                    break;
                }
                break;

            case TZI:
                if (name.equals(ICAL_DTSTART)) {
                    dtstart = value;
                } else if (name.equals(ICAL_TZNAME)) {
                    tzname = value;
                } else if (name.equals(ICAL_TZOFFSETFROM)) {
                    from = value;
                } else if (name.equals(ICAL_TZOFFSETTO)) {
                    to = value;
                } else if (name.equals(ICAL_RDATE)) {
                    // RDATE mixed with RRULE is not supported
                    if (isRRULE) {
                        state = ERR;
                        break;
                    }
                    if (dates == null) {
                        dates = new LinkedList<String>();
                    }
                    // RDATE value may contain multiple date delimited
                    // by comma
                    StringTokenizer st = new StringTokenizer(value, COMMA);
                    while (st.hasMoreTokens()) {
                        String date = st.nextToken();
                        dates.add(date);
                    }
                } else if (name.equals(ICAL_RRULE)) {
                    // RRULE mixed with RDATE is not supported
                    if (!isRRULE && dates != null) {
                        state = ERR;
                        break;
                    } else if (dates == null) {
                        dates = new LinkedList<String>();
                    }
                    isRRULE = true;
                    dates.add(value);
                } else if (name.equals(ICAL_END)) {
                    // Mandatory properties
                    if (dtstart == null || from == null || to == null) {
                        state = ERR;
                        break;
                    }
                    // if tzname is not available, create one from tzid
                    if (tzname == null) {
                        tzname = getDefaultTZName(tzid, dst);
                    }

                    // create a time zone rule
                    TimeZoneRule rule = null;
                    int fromOffset = 0;
                    int toOffset = 0;
                    int rawOffset = 0;
                    int dstSavings = 0;
                    long start = 0;
                    try {
                        // Parse TZOFFSETFROM/TZOFFSETTO
                        fromOffset = offsetStrToMillis(from);
                        toOffset = offsetStrToMillis(to);

                        if (dst) {
                            // If daylight, use the previous offset as rawoffset if positive
                            if (toOffset - fromOffset > 0) {
                                rawOffset = fromOffset;
                                dstSavings = toOffset - fromOffset;
                            } else {
                                // This is rare case..  just use 1 hour DST savings
                                rawOffset = toOffset - DEF_DSTSAVINGS;
                                dstSavings = DEF_DSTSAVINGS;                                
                            }
                        } else {
                            rawOffset = toOffset;
                            dstSavings = 0;
                        }

                        // start time
                        start = parseDateTimeString(dtstart, fromOffset);

                        // Create the rule
                        Date actualStart = null;
                        if (isRRULE) {
                            rule = createRuleByRRULE(tzname, rawOffset, dstSavings, start, dates, fromOffset);
                        } else {
                            rule = createRuleByRDATE(tzname, rawOffset, dstSavings, start, dates, fromOffset);
                        }
                        if (rule != null) {
                            actualStart = rule.getFirstStart(fromOffset, 0);
                            if (actualStart.getTime() < firstStart) {
                                // save from offset information for the earliest rule
                                firstStart = actualStart.getTime();
                                // If this is STD, assume the time before this transtion
                                // is DST when the difference is 1 hour.  This might not be
                                // accurate, but VTIMEZONE data does not have such info.
                                if (dstSavings > 0) {
                                    initialRawOffset = fromOffset;
                                    initialDSTSavings = 0;
                                } else {
                                    if (fromOffset - toOffset == DEF_DSTSAVINGS) {
                                        initialRawOffset = fromOffset - DEF_DSTSAVINGS;
                                        initialDSTSavings = DEF_DSTSAVINGS;
                                    } else {
                                        initialRawOffset = fromOffset;
                                        initialDSTSavings = 0;
                                    }
                                }
                            }
                        }
                    } catch (IllegalArgumentException iae) {
                        // bad format - rule == null..
                    }

                    if (rule == null) {
                        state = ERR;
                        break;
                    }
                    rules.add(rule);
                    state = VTZ;
                }
                break;
            }

            if (state == ERR) {
                vtzlines = null;
                return false;
            }
        }

        // Must have at least one rule
        if (rules.size() == 0) {
            return false;
        }

        // Create a initial rule
        InitialTimeZoneRule initialRule = new InitialTimeZoneRule(getDefaultTZName(tzid, false),
                initialRawOffset, initialDSTSavings);

        // Finally, create the RuleBasedTimeZone
        RuleBasedTimeZone rbtz = new RuleBasedTimeZone(tzid, initialRule);

        int finalRuleIdx = -1;
        int finalRuleCount = 0;
        for (int i = 0; i < rules.size(); i++) {
            TimeZoneRule r = rules.get(i);
            if (r instanceof AnnualTimeZoneRule) {
                if (((AnnualTimeZoneRule)r).getEndYear() == AnnualTimeZoneRule.MAX_YEAR) {
                    finalRuleCount++;
                    finalRuleIdx = i;
                }
            }
        }
        if (finalRuleCount > 2) {
            // Too many final rules
            return false;
        }

        if (finalRuleCount == 1) {
            if (rules.size() == 1) {
                // Only one final rule, only governs the initial rule,
                // which is already initialized, thus, we do not need to
                // add this transition rule
                rules.clear();
            } else {
                // Normalize the final rule
                AnnualTimeZoneRule finalRule = (AnnualTimeZoneRule)rules.get(finalRuleIdx);
                int tmpRaw = finalRule.getRawOffset();
                int tmpDST = finalRule.getDSTSavings();
    
                // Find the last non-final rule
                Date finalStart = finalRule.getFirstStart(initialRawOffset, initialDSTSavings);
                Date start = finalStart;
                for (int i = 0; i < rules.size(); i++) {
                    if (finalRuleIdx == i) {
                        continue;
                    }
                    TimeZoneRule r = rules.get(i);
                    Date lastStart = r.getFinalStart(tmpRaw, tmpDST);
                    if (lastStart.after(start)) {
                        start = finalRule.getNextStart(lastStart.getTime(),
                                r.getRawOffset(),
                                r.getDSTSavings(),
                                false);
                    }
                }
                TimeZoneRule newRule;
                if (start == finalStart) {
                    // Transform this into a single transition
                    newRule = new TimeArrayTimeZoneRule(
                            finalRule.getName(),
                            finalRule.getRawOffset(),
                            finalRule.getDSTSavings(),
                            new long[] {finalStart.getTime()},
                            DateTimeRule.UTC_TIME);
                } else {
                    // Update the end year
                    int fields[] = Grego.timeToFields(start.getTime(), null);
                    newRule = new AnnualTimeZoneRule(
                            finalRule.getName(),
                            finalRule.getRawOffset(),
                            finalRule.getDSTSavings(),
                            finalRule.getRule(),
                            finalRule.getStartYear(),
                            fields[0]);
                }
                rules.set(finalRuleIdx, newRule);
            }
        }

        for (TimeZoneRule r : rules) {
            rbtz.addTransitionRule(r);
        }

        tz = rbtz;
        setID(tzid);
        return true;
    }

    /*
     * Create a default TZNAME from TZID
     */
    private static String getDefaultTZName(String tzid, boolean isDST) {
        if (isDST) {
            return tzid + "(DST)";
        }
        return tzid + "(STD)";
    }

    /*
     * Create a TimeZoneRule by the RRULE definition
     */
    private static TimeZoneRule createRuleByRRULE(String tzname,
            int rawOffset, int dstSavings, long start, List<String> dates, int fromOffset) {
        if (dates == null || dates.size() == 0) {
            return null;
        }
        // Parse the first rule
        String rrule = dates.get(0);

        long until[] = new long[1];
        int[] ruleFields = parseRRULE(rrule, until);
        if (ruleFields == null) {
            // Invalid RRULE
            return null;
        }

        int month = ruleFields[0];
        int dayOfWeek = ruleFields[1];
        int nthDayOfWeek = ruleFields[2];
        int dayOfMonth = ruleFields[3];

        if (dates.size() == 1) {
            // No more rules
            if (ruleFields.length > 4) {
                // Multiple BYMONTHDAY values

                if (ruleFields.length != 10 || month == -1 || dayOfWeek == 0) {
                    // Only support the rule using 7 continuous days
                    // BYMONTH and BYDAY must be set at the same time
                    return null;
                }
                int firstDay = 31; // max possible number of dates in a month
                int days[] = new int[7];
                for (int i = 0; i < 7; i++) {
                    days[i] = ruleFields[3 + i];
                    // Resolve negative day numbers.  A negative day number should
                    // not be used in February, but if we see such case, we use 28
                    // as the base.
                    days[i] = days[i] > 0 ? days[i] : MONTHLENGTH[month] + days[i] + 1;
                    firstDay = days[i] < firstDay ? days[i] : firstDay;
                }
                // Make sure days are continuous
                for (int i = 1; i < 7; i++) {
                    boolean found = false;
                    for (int j = 0; j < 7; j++) {
                        if (days[j] == firstDay + i) {
                            found = true;
                            break;
                        }
                    }
                    if (!found) {
                        // days are not continuous
                        return null;
                    }
                }
                // Use DOW_GEQ_DOM rule with firstDay as the start date
                dayOfMonth = firstDay;
            }
        } else {
            // Check if BYMONTH + BYMONTHDAY + BYDAY rule with multiple RRULE lines.
            // Otherwise, not supported.
            if (month == -1 || dayOfWeek == 0 || dayOfMonth == 0) {
                // This is not the case
                return null;
            }
            // Parse the rest of rules if number of rules is not exceeding 7.
            // We can only support 7 continuous days starting from a day of month.
            if (dates.size() > 7) {
                return null;
            }

            // Note: To check valid date range across multiple rule is a little
            // bit complicated.  For now, this code is not doing strict range
            // checking across month boundary

            int earliestMonth = month;
            int daysCount = ruleFields.length - 3;
            int earliestDay = 31;
            for (int i = 0; i < daysCount; i++) {
                int dom = ruleFields[3 + i];
                dom = dom > 0 ? dom : MONTHLENGTH[month] + dom + 1;
                earliestDay = dom < earliestDay ? dom : earliestDay;
            }

            int anotherMonth = -1;
            for (int i = 1; i < dates.size(); i++) {
                rrule = dates.get(i);
                long[] unt = new long[1];
                int[] fields = parseRRULE(rrule, unt);

                // If UNTIL is newer than previous one, use the one
                if (unt[0] > until[0]) {
                    until = unt;
                }
                
                // Check if BYMONTH + BYMONTHDAY + BYDAY rule
                if (fields[0] == -1 || fields[1] == 0 || fields[3] == 0) {
                    return null;
                }
                // Count number of BYMONTHDAY
                int count = fields.length - 3;
                if (daysCount + count > 7) {
                    // We cannot support BYMONTHDAY more than 7
                    return null;
                }
                // Check if the same BYDAY is used.  Otherwise, we cannot
                // support the rule
                if (fields[1] != dayOfWeek) {
                    return null;
                }
                // Check if the month is same or right next to the primary month
                if (fields[0] != month) {
                    if (anotherMonth == -1) {
                        int diff = fields[0] - month;
                        if (diff == -11 || diff == -1) {
                            // Previous month
                            anotherMonth = fields[0];
                            earliestMonth = anotherMonth;
                            // Reset earliest day
                            earliestDay = 31;
                        } else if (diff == 11 || diff == 1) {
                            // Next month
                            anotherMonth = fields[0];
                        } else {
                            // The day range cannot exceed more than 2 months
                            return null;
                        }
                    } else if (fields[0] != month && fields[0] != anotherMonth) {
                        // The day range cannot exceed more than 2 months
                        return null;
                    }
                }
                // If ealier month, go through days to find the earliest day
                if (fields[0] == earliestMonth) {
                    for (int j = 0; j < count; j++) {
                        int dom = fields[3 + j];
                        dom = dom > 0 ? dom : MONTHLENGTH[fields[0]] + dom + 1;
                        earliestDay = dom < earliestDay ? dom : earliestDay;
                    }
                }
                daysCount += count;
            }
            if (daysCount != 7) {
                // Number of BYMONTHDAY entries must be 7
                return null;
            }
            month = earliestMonth;
            dayOfMonth = earliestDay;
        }

        // Calculate start/end year and missing fields
        int[] dfields = Grego.timeToFields(start + fromOffset, null);
        int startYear = dfields[0];
        if (month == -1) {
            // If MYMONTH is not set, use the month of DTSTART
            month = dfields[1];
        }
        if (dayOfWeek == 0 && nthDayOfWeek == 0 && dayOfMonth == 0) {
            // If only YEARLY is set, use the day of DTSTART as BYMONTHDAY
            dayOfMonth = dfields[2];
        }
        int timeInDay = dfields[5];

        int endYear = AnnualTimeZoneRule.MAX_YEAR;
        if (until[0] != MIN_TIME) {
            Grego.timeToFields(until[0], dfields);
            endYear = dfields[0];
        }

        // Create the AnnualDateTimeRule
        DateTimeRule adtr = null;
        if (dayOfWeek == 0 && nthDayOfWeek == 0 && dayOfMonth != 0) {
            // Day in month rule, for example, 15th day in the month
            adtr = new DateTimeRule(month, dayOfMonth, timeInDay, DateTimeRule.WALL_TIME);
        } else if (dayOfWeek != 0 && nthDayOfWeek != 0 && dayOfMonth == 0) {
            // Nth day of week rule, for example, last Sunday
            adtr = new DateTimeRule(month, nthDayOfWeek, dayOfWeek, timeInDay, DateTimeRule.WALL_TIME);
        } else if (dayOfWeek != 0 && nthDayOfWeek == 0 && dayOfMonth != 0) {
            // First day of week after day of month rule, for example,
            // first Sunday after 15th day in the month
            adtr = new DateTimeRule(month, dayOfMonth, dayOfWeek, true, timeInDay, DateTimeRule.WALL_TIME);
        } else {
            // RRULE attributes are insufficient
            return null;
        }

        return new AnnualTimeZoneRule(tzname, rawOffset, dstSavings, adtr, startYear, endYear);
    }

    /*
     * Parse individual RRULE
     * 
     * On return -
     * 
     * int[0] month calculated by BYMONTH - 1, or -1 when not found
     * int[1] day of week in BYDAY, or 0 when not found
     * int[2] day of week ordinal number in BYDAY, or 0 when not found
     * int[i >= 3] day of month, which could be multiple values, or 0 when not found
     * 
     *  or
     * 
     * null on any error cases, for exmaple, FREQ=YEARLY is not available
     * 
     * When UNTIL attribute is available, the time will be set to until[0],
     * otherwise, MIN_TIME
     */
    private static int[] parseRRULE(String rrule, long[] until) {
        int month = -1;
        int dayOfWeek = 0;
        int nthDayOfWeek = 0;
        int[] dayOfMonth = null;

        long untilTime = MIN_TIME;
        boolean yearly = false;
        boolean parseError = false;
        StringTokenizer st= new StringTokenizer(rrule, SEMICOLON);

        while (st.hasMoreTokens()) {
            String attr, value;
            String prop = st.nextToken();
            int sep = prop.indexOf(EQUALS_SIGN);
            if (sep != -1) {
                attr = prop.substring(0, sep);
                value = prop.substring(sep + 1);
            } else {
                parseError = true;
                break;
            }

            if (attr.equals(ICAL_FREQ)) {
                // only support YEARLY frequency type
                if (value.equals(ICAL_YEARLY)) {
                    yearly = true;
                } else {
                    parseError = true;
                    break;                        
                }
            } else if (attr.equals(ICAL_UNTIL)) {
                // ISO8601 UTC format, for example, "20060315T020000Z"
                try {
                    untilTime = parseDateTimeString(value, 0);
                } catch (IllegalArgumentException iae) {
                    parseError = true;
                    break;
                }
            } else if (attr.equals(ICAL_BYMONTH)) {
                // Note: BYMONTH may contain multiple months, but only single month make sense for
                // VTIMEZONE property.
                if (value.length() > 2) {
                    parseError = true;
                    break;
                }
                try {
                    month = Integer.parseInt(value) - 1;
                    if (month < 0 || month >= 12) {
                        parseError = true;
                        break;
                    }
                } catch (NumberFormatException nfe) {
                    parseError = true;
                    break;
                }
            } else if (attr.equals(ICAL_BYDAY)) {
                // Note: BYDAY may contain multiple day of week separated by comma.  It is unlikely used for
                // VTIMEZONE property.  We do not support the case.

                // 2-letter format is used just for representing a day of week, for example, "SU" for Sunday
                // 3 or 4-letter format is used for represeinging Nth day of week, for example, "-1SA" for last Saturday
                int length = value.length();
                if (length < 2 || length > 4) {
                    parseError = true;
                    break;
                }
                if (length > 2) {
                    // Nth day of week
                    int sign = 1;
                    if (value.charAt(0) == '+') {
                        sign = 1;
                    } else if (value.charAt(0) == '-') {
                        sign = -1;
                    } else if (length == 4) {
                        parseError = true;
                        break;
                    }
                    try {
                        int n = Integer.parseInt(value.substring(length - 3, length - 2));
                        if (n == 0 || n > 4) {
                            parseError = true;
                            break;
                        }
                        nthDayOfWeek = n * sign;
                    } catch(NumberFormatException nfe) {
                        parseError = true;
                        break;
                    }
                    value = value.substring(length - 2);
                }
                int wday;
                for (wday = 0; wday < ICAL_DOW_NAMES.length; wday++) {
                    if (value.equals(ICAL_DOW_NAMES[wday])) {
                        break;
                    }
                }
                if (wday < ICAL_DOW_NAMES.length) {
                    // Sunday(1) - Saturday(7)
                    dayOfWeek = wday + 1;
                } else {
                    parseError = true;
                    break;
                }
            } else if (attr.equals(ICAL_BYMONTHDAY)) {
                // Note: BYMONTHDAY may contain multiple days delimited by comma
                //
                // A value of BYMONTHDAY could be negative, for example, -1 means
                // the last day in a month
                StringTokenizer days = new StringTokenizer(value, COMMA);
                int count = days.countTokens();
                dayOfMonth = new int[count];
                int index = 0;
                while(days.hasMoreTokens()) {
                    try {
                        dayOfMonth[index++] = Integer.parseInt(days.nextToken());
                    } catch (NumberFormatException nfe) {
                        parseError = true;
                        break;
                    }
                }
            }
        }

        if (parseError) {
            return null;
        }
        if (!yearly) {
            // FREQ=YEARLY must be set
            return null;
        }

        until[0] = untilTime;

        int[] results;
        if (dayOfMonth == null) {
            results = new int[4];
            results[3] = 0;
        } else {
            results = new int[3 + dayOfMonth.length];
            for (int i = 0; i < dayOfMonth.length; i++) {
                results[3 + i] = dayOfMonth[i];
            }
        }
        results[0] = month;
        results[1] = dayOfWeek;
        results[2] = nthDayOfWeek;
        return results;
    }
    
    /*
     * Create a TimeZoneRule by the RDATE definition
     */
    private static TimeZoneRule createRuleByRDATE(String tzname,
            int rawOffset, int dstSavings, long start, List<String> dates, int fromOffset) {
        // Create an array of transition times
        long[] times;
        if (dates == null || dates.size() == 0) {
            // When no RDATE line is provided, use start (DTSTART)
            // as the transition time
            times = new long[1];
            times[0] = start;
        } else {
            times = new long[dates.size()];
            int idx = 0;
            try {
                for (String date : dates) {
                    times[idx++] = parseDateTimeString(date, fromOffset);
                }
            } catch (IllegalArgumentException iae) {
                return null;
            }
        }
        return new TimeArrayTimeZoneRule(tzname, rawOffset, dstSavings, times, DateTimeRule.UTC_TIME);
    }

    /*
     * Write the time zone rules in RFC2445 VTIMEZONE format
     */
    private void writeZone(Writer w, BasicTimeZone basictz, String[] customProperties) throws IOException {
        // Write the header
        writeHeader(w);

        if (customProperties != null && customProperties.length > 0) {
            for (int i = 0; i < customProperties.length; i++) {
                if (customProperties[i] != null) {
                    w.write(customProperties[i]);
                    w.write(NEWLINE);
                }
            }
        }

        long t = MIN_TIME;
        String dstName = null;
        int dstFromOffset = 0;
        int dstFromDSTSavings = 0;
        int dstToOffset = 0;
        int dstStartYear = 0;
        int dstMonth = 0;
        int dstDayOfWeek = 0;
        int dstWeekInMonth = 0;
        int dstMillisInDay = 0;
        long dstStartTime = 0;
        long dstUntilTime = 0;
        int dstCount = 0;
        AnnualTimeZoneRule finalDstRule = null;

        String stdName = null;
        int stdFromOffset = 0;
        int stdFromDSTSavings = 0;
        int stdToOffset = 0;
        int stdStartYear = 0;
        int stdMonth = 0;
        int stdDayOfWeek = 0;
        int stdWeekInMonth = 0;
        int stdMillisInDay = 0;
        long stdStartTime = 0;
        long stdUntilTime = 0;
        int stdCount = 0;
        AnnualTimeZoneRule finalStdRule = null;

        int[] dtfields = new int[6];
        boolean hasTransitions = false;

        // Going through all transitions
        while(true) {
            TimeZoneTransition tzt = basictz.getNextTransition(t, false);
            if (tzt == null) {
                break;
            }
            hasTransitions = true;
            t = tzt.getTime();
            String name = tzt.getTo().getName();
            boolean isDst = (tzt.getTo().getDSTSavings() != 0);
            int fromOffset = tzt.getFrom().getRawOffset() + tzt.getFrom().getDSTSavings();
            int fromDSTSavings = tzt.getFrom().getDSTSavings();
            int toOffset = tzt.getTo().getRawOffset() + tzt.getTo().getDSTSavings();
            Grego.timeToFields(tzt.getTime() + fromOffset, dtfields);
            int weekInMonth = Grego.getDayOfWeekInMonth(dtfields[0], dtfields[1], dtfields[2]);
            int year = dtfields[0];
            boolean sameRule = false;
            if (isDst) {
                if (finalDstRule == null && tzt.getTo() instanceof AnnualTimeZoneRule) {
                    if (((AnnualTimeZoneRule)tzt.getTo()).getEndYear() == AnnualTimeZoneRule.MAX_YEAR) {
                        finalDstRule = (AnnualTimeZoneRule)tzt.getTo();
                    }
                }
                if (dstCount > 0) {
                    if (year == dstStartYear + dstCount
                            && name.equals(dstName)
                            && dstFromOffset == fromOffset
                            && dstToOffset == toOffset
                            && dstMonth == dtfields[1]
                            && dstDayOfWeek == dtfields[3]
                            && dstWeekInMonth == weekInMonth
                            && dstMillisInDay == dtfields[5]) {
                        // Update until time
                        dstUntilTime = t;
                        dstCount++;
                        sameRule = true;
                    }
                    if (!sameRule) {
                        if (dstCount == 1) {
                            writeZonePropsByTime(w, true, dstName, dstFromOffset, dstToOffset,
                                    dstStartTime, true);
                        } else {
                            writeZonePropsByDOW(w, true, dstName, dstFromOffset, dstToOffset,
                                    dstMonth, dstWeekInMonth, dstDayOfWeek, dstStartTime, dstUntilTime);
                        }
                    }
                } 
                if (!sameRule) {
                    // Reset this DST information
                    dstName = name;
                    dstFromOffset = fromOffset;
                    dstFromDSTSavings = fromDSTSavings;
                    dstToOffset = toOffset;
                    dstStartYear = year;
                    dstMonth = dtfields[1];
                    dstDayOfWeek = dtfields[3];
                    dstWeekInMonth = weekInMonth;
                    dstMillisInDay = dtfields[5];
                    dstStartTime = dstUntilTime = t;
                    dstCount = 1;
                }
                if (finalStdRule != null && finalDstRule != null) {
                    break;
                }
            } else {
                if (finalStdRule == null && tzt.getTo() instanceof AnnualTimeZoneRule) {
                    if (((AnnualTimeZoneRule)tzt.getTo()).getEndYear() == AnnualTimeZoneRule.MAX_YEAR) {
                        finalStdRule = (AnnualTimeZoneRule)tzt.getTo();
                    }
                }
                if (stdCount > 0) {
                    if (year == stdStartYear + stdCount
                            && name.equals(stdName)
                            && stdFromOffset == fromOffset
                            && stdToOffset == toOffset
                            && stdMonth == dtfields[1]
                            && stdDayOfWeek == dtfields[3]
                            && stdWeekInMonth == weekInMonth
                            && stdMillisInDay == dtfields[5]) {
                        // Update until time
                        stdUntilTime = t;
                        stdCount++;
                        sameRule = true;
                    }
                    if (!sameRule) {
                        if (stdCount == 1) {
                            writeZonePropsByTime(w, false, stdName, stdFromOffset, stdToOffset,
                                    stdStartTime, true);
                        } else {
                            writeZonePropsByDOW(w, false, stdName, stdFromOffset, stdToOffset,
                                    stdMonth, stdWeekInMonth, stdDayOfWeek, stdStartTime, stdUntilTime);
                        }
                    }
                }
                if (!sameRule) {
                    // Reset this STD information
                    stdName = name;
                    stdFromOffset = fromOffset;
                    stdFromDSTSavings = fromDSTSavings;
                    stdToOffset = toOffset;
                    stdStartYear = year;
                    stdMonth = dtfields[1];
                    stdDayOfWeek = dtfields[3];
                    stdWeekInMonth = weekInMonth;
                    stdMillisInDay = dtfields[5];
                    stdStartTime = stdUntilTime = t;
                    stdCount = 1;
                }
                if (finalStdRule != null && finalDstRule != null) {
                    break;
                }
            }
        }
        if (!hasTransitions) {
            // No transition - put a single non transition RDATE
            int offset = basictz.getOffset(0 /* any time */);
            boolean isDst = (offset != basictz.getRawOffset());
            writeZonePropsByTime(w, isDst, getDefaultTZName(basictz.getID(), isDst),
                    offset, offset, DEF_TZSTARTTIME - offset, false);                
        } else {
            if (dstCount > 0) {
                if (finalDstRule == null) {
                    if (dstCount == 1) {
                        writeZonePropsByTime(w, true, dstName, dstFromOffset, dstToOffset,
                                dstStartTime, true);
                    } else {
                        writeZonePropsByDOW(w, true, dstName, dstFromOffset, dstToOffset,
                                dstMonth, dstWeekInMonth, dstDayOfWeek, dstStartTime, dstUntilTime);
                    }
                } else {
                    if (dstCount == 1) {
                        writeFinalRule(w, true, finalDstRule,
                                dstFromOffset - dstFromDSTSavings, dstFromDSTSavings, dstStartTime);
                    } else {
                        // Use a single rule if possible
                        if (isEquivalentDateRule(dstMonth, dstWeekInMonth, dstDayOfWeek, finalDstRule.getRule())) {
                            writeZonePropsByDOW(w, true, dstName, dstFromOffset, dstToOffset,
                                    dstMonth, dstWeekInMonth, dstDayOfWeek, dstStartTime, MAX_TIME);
                        } else {
                            // Not equivalent rule - write out two different rules
                            writeZonePropsByDOW(w, true, dstName, dstFromOffset, dstToOffset,
                                    dstMonth, dstWeekInMonth, dstDayOfWeek, dstStartTime, dstUntilTime);

                            Date nextStart = finalDstRule.getNextStart(dstUntilTime,
                                    dstFromOffset - dstFromDSTSavings, dstFromDSTSavings, false);

                            assert nextStart != null;
                            if (nextStart != null) {
                                writeFinalRule(w, true, finalDstRule,
                                        dstFromOffset - dstFromDSTSavings, dstFromDSTSavings, nextStart.getTime());
                            }
                        }
                    }
                }
            }
            if (stdCount > 0) {
                if (finalStdRule == null) {
                    if (stdCount == 1) {
                        writeZonePropsByTime(w, false, stdName, stdFromOffset, stdToOffset,
                                stdStartTime, true);
                    } else {
                        writeZonePropsByDOW(w, false, stdName, stdFromOffset, stdToOffset,
                                stdMonth, stdWeekInMonth, stdDayOfWeek, stdStartTime, stdUntilTime);
                    }
                } else {
                    if (stdCount == 1) {
                        writeFinalRule(w, false, finalStdRule,
                                stdFromOffset - stdFromDSTSavings, stdFromDSTSavings, stdStartTime);
                    } else {
                        // Use a single rule if possible
                        if (isEquivalentDateRule(stdMonth, stdWeekInMonth, stdDayOfWeek, finalStdRule.getRule())) {
                            writeZonePropsByDOW(w, false, stdName, stdFromOffset, stdToOffset,
                                    stdMonth, stdWeekInMonth, stdDayOfWeek, stdStartTime, MAX_TIME);
                        } else {
                            // Not equivalent rule - write out two different rules
                            writeZonePropsByDOW(w, false, stdName, stdFromOffset, stdToOffset,
                                    stdMonth, stdWeekInMonth, stdDayOfWeek, stdStartTime, stdUntilTime);

                            Date nextStart = finalStdRule.getNextStart(stdUntilTime,
                                    stdFromOffset - stdFromDSTSavings, stdFromDSTSavings, false);

                            assert nextStart != null;
                            if (nextStart != null) {
                                writeFinalRule(w, false, finalStdRule,
                                        stdFromOffset - stdFromDSTSavings, stdFromDSTSavings, nextStart.getTime());
                                
                            }
                        }
                    }
                }
            }            
        }
        writeFooter(w);
    }

    /*
     * Check if the DOW rule specified by month, weekInMonth and dayOfWeek is equivalent
     * to the DateTimerule.
     */
    private static boolean isEquivalentDateRule(int month, int weekInMonth, int dayOfWeek, DateTimeRule dtrule) {
        if (month != dtrule.getRuleMonth() || dayOfWeek != dtrule.getRuleDayOfWeek()) {
            return false;
        }
        if (dtrule.getTimeRuleType() != DateTimeRule.WALL_TIME) {
            // Do not try to do more intelligent comparison for now.
            return false;
        }
        if (dtrule.getDateRuleType() == DateTimeRule.DOW
                && dtrule.getRuleWeekInMonth() == weekInMonth) {
            return true;
        }
        int ruleDOM = dtrule.getRuleDayOfMonth();
        if (dtrule.getDateRuleType() == DateTimeRule.DOW_GEQ_DOM) {
            if (ruleDOM%7 == 1 && (ruleDOM + 6)/7 == weekInMonth) {
                return true;
            }
            if (month != Calendar.FEBRUARY && (MONTHLENGTH[month] - ruleDOM)%7 == 6
                    && weekInMonth == -1*((MONTHLENGTH[month]-ruleDOM+1)/7)) {
                return true;
            }
        }
        if (dtrule.getDateRuleType() == DateTimeRule.DOW_LEQ_DOM) {
            if (ruleDOM%7 == 0 && ruleDOM/7 == weekInMonth) {
                return true;
            }
            if (month != Calendar.FEBRUARY && (MONTHLENGTH[month] - ruleDOM)%7 == 0
                    && weekInMonth == -1*((MONTHLENGTH[month] - ruleDOM)/7 + 1)) {
                return true;
            }
        }
        return false;
    }

    /*
     * Write a single start time
     */
    private static void writeZonePropsByTime(Writer writer, boolean isDst, String tzname,
            int fromOffset, int toOffset, long time, boolean withRDATE) throws IOException {
        beginZoneProps(writer, isDst, tzname, fromOffset, toOffset, time);
        if (withRDATE) {
            writer.write(ICAL_RDATE);
            writer.write(COLON);
            writer.write(getDateTimeString(time + fromOffset));
            writer.write(NEWLINE);
        }
        endZoneProps(writer, isDst);
    }

    /*
     * Write start times defined by a DOM rule using VTIMEZONE RRULE
     */
    private static void writeZonePropsByDOM(Writer writer, boolean isDst, String tzname, int fromOffset, int toOffset,
            int month, int dayOfMonth, long startTime, long untilTime) throws IOException {
        beginZoneProps(writer, isDst, tzname, fromOffset, toOffset, startTime);

        beginRRULE(writer, month);
        writer.write(ICAL_BYMONTHDAY);
        writer.write(EQUALS_SIGN);
        writer.write(Integer.toString(dayOfMonth));

        if (untilTime != MAX_TIME) {
            appendUNTIL(writer, getDateTimeString(untilTime + fromOffset));
        }
        writer.write(NEWLINE);

        endZoneProps(writer, isDst);
    }

    /*
     * Write start times defined by a DOW rule using VTIMEZONE RRULE
     */
    private static void writeZonePropsByDOW(Writer writer, boolean isDst, String tzname, int fromOffset, int toOffset,
            int month, int weekInMonth, int dayOfWeek, long startTime, long untilTime) throws IOException {
        beginZoneProps(writer, isDst, tzname, fromOffset, toOffset, startTime);

        beginRRULE(writer, month);
        writer.write(ICAL_BYDAY);
        writer.write(EQUALS_SIGN);
        writer.write(Integer.toString(weekInMonth));    // -4, -3, -2, -1, 1, 2, 3, 4
        writer.write(ICAL_DOW_NAMES[dayOfWeek - 1]);    // SU, MO, TU...

        if (untilTime != MAX_TIME) {
            appendUNTIL(writer, getDateTimeString(untilTime + fromOffset));
        }
        writer.write(NEWLINE);

        endZoneProps(writer, isDst);
    }

    /*
     * Write start times defined by a DOW_GEQ_DOM rule using VTIMEZONE RRULE
     */
    private static void writeZonePropsByDOW_GEQ_DOM(Writer writer, boolean isDst, String tzname, int fromOffset, int toOffset,
            int month, int dayOfMonth, int dayOfWeek, long startTime, long untilTime) throws IOException {
        // Check if this rule can be converted to DOW rule
        if (dayOfMonth%7 == 1) {
            // Can be represented by DOW rule
            writeZonePropsByDOW(writer, isDst, tzname, fromOffset, toOffset,
                    month, (dayOfMonth + 6)/7, dayOfWeek, startTime, untilTime);
        } else if (month != Calendar.FEBRUARY && (MONTHLENGTH[month] - dayOfMonth)%7 == 6) {
            // Can be represented by DOW rule with negative week number
            writeZonePropsByDOW(writer, isDst, tzname, fromOffset, toOffset,
                    month, -1*((MONTHLENGTH[month] - dayOfMonth + 1)/7), dayOfWeek, startTime, untilTime);
        } else {
            // Otherwise, use BYMONTHDAY to include all possible dates
            beginZoneProps(writer, isDst, tzname, fromOffset, toOffset, startTime);

            // Check if all days are in the same month
            int startDay = dayOfMonth;
            int currentMonthDays = 7;
        
            if (dayOfMonth <= 0) {
                // The start day is in previous month
                int prevMonthDays = 1 - dayOfMonth;
                currentMonthDays -= prevMonthDays;

                int prevMonth = (month - 1) < 0 ? 11 : month - 1;

                // Note: When a rule is separated into two, UNTIL attribute needs to be
                // calculated for each of them.  For now, we skip this, because we basically use this method
                // only for final rules, which does not have the UNTIL attribute
                writeZonePropsByDOW_GEQ_DOM_sub(writer, prevMonth, -prevMonthDays, dayOfWeek, prevMonthDays, MAX_TIME /* Do not use UNTIL */, fromOffset);

                // Start from 1 for the rest
                startDay = 1;
            } else if (dayOfMonth + 6 > MONTHLENGTH[month]) {
                // Note: This code does not actually work well in February.  For now, days in month in
                // non-leap year.
                int nextMonthDays = dayOfMonth + 6 - MONTHLENGTH[month];
                currentMonthDays -= nextMonthDays;

                int nextMonth = (month + 1) > 11 ? 0 : month + 1;
                
                writeZonePropsByDOW_GEQ_DOM_sub(writer, nextMonth, 1, dayOfWeek, nextMonthDays, MAX_TIME /* Do not use UNTIL */, fromOffset);
            }
            writeZonePropsByDOW_GEQ_DOM_sub(writer, month, startDay, dayOfWeek, currentMonthDays, untilTime, fromOffset);
            endZoneProps(writer, isDst);
        }
    }
 
    /*
     * Called from writeZonePropsByDOW_GEQ_DOM
     */
    private static void writeZonePropsByDOW_GEQ_DOM_sub(Writer writer, int month,
            int dayOfMonth, int dayOfWeek, int numDays, long untilTime, int fromOffset) throws IOException {

        int startDayNum = dayOfMonth;
        boolean isFeb = (month == Calendar.FEBRUARY);
        if (dayOfMonth < 0 && !isFeb) {
            // Use positive number if possible
            startDayNum = MONTHLENGTH[month] + dayOfMonth + 1;
        }
        beginRRULE(writer, month);
        writer.write(ICAL_BYDAY);
        writer.write(EQUALS_SIGN);
        writer.write(ICAL_DOW_NAMES[dayOfWeek - 1]);    // SU, MO, TU...
        writer.write(SEMICOLON);
        writer.write(ICAL_BYMONTHDAY);
        writer.write(EQUALS_SIGN);

        writer.write(Integer.toString(startDayNum));
        for (int i = 1; i < numDays; i++) {
            writer.write(COMMA);
            writer.write(Integer.toString(startDayNum + i));
        }

        if (untilTime != MAX_TIME) {
            appendUNTIL(writer, getDateTimeString(untilTime + fromOffset));
        }
        writer.write(NEWLINE);
    }

    /*
     * Write start times defined by a DOW_LEQ_DOM rule using VTIMEZONE RRULE
     */
    private static void writeZonePropsByDOW_LEQ_DOM(Writer writer, boolean isDst, String tzname, int fromOffset, int toOffset,
            int month, int dayOfMonth, int dayOfWeek, long startTime, long untilTime) throws IOException {
        // Check if this rule can be converted to DOW rule
        if (dayOfMonth%7 == 0) {
            // Can be represented by DOW rule
            writeZonePropsByDOW(writer, isDst, tzname, fromOffset, toOffset,
                    month, dayOfMonth/7, dayOfWeek, startTime, untilTime);
        } else if (month != Calendar.FEBRUARY && (MONTHLENGTH[month] - dayOfMonth)%7 == 0){
            // Can be represented by DOW rule with negative week number
            writeZonePropsByDOW(writer, isDst, tzname, fromOffset, toOffset,
                    month, -1*((MONTHLENGTH[month] - dayOfMonth)/7 + 1), dayOfWeek, startTime, untilTime);
        } else if (month == Calendar.FEBRUARY && dayOfMonth == 29) {
            // Specical case for February
            writeZonePropsByDOW(writer, isDst, tzname, fromOffset, toOffset,
                    Calendar.FEBRUARY, -1, dayOfWeek, startTime, untilTime);
        } else {
            // Otherwise, convert this to DOW_GEQ_DOM rule
            writeZonePropsByDOW_GEQ_DOM(writer, isDst, tzname, fromOffset, toOffset,
                    month, dayOfMonth - 6, dayOfWeek, startTime, untilTime);
        }
    }

    /*
     * Write the final time zone rule using RRULE, with no UNTIL attribute
     */
    private static void writeFinalRule(Writer writer, boolean isDst, AnnualTimeZoneRule rule,
            int fromRawOffset, int fromDSTSavings, long startTime) throws IOException{
        DateTimeRule dtrule = toWallTimeRule(rule.getRule(), fromRawOffset, fromDSTSavings);

        // If the rule's mills in a day is out of range, adjust start time.
        // Olson tzdata supports 24:00 of a day, but VTIMEZONE does not.
        // See ticket#7008/#7518

        int timeInDay = dtrule.getRuleMillisInDay();
        if (timeInDay < 0) {
            startTime = startTime + (0 - timeInDay);
        } else if (timeInDay >= Grego.MILLIS_PER_DAY) {
            startTime = startTime - (timeInDay - (Grego.MILLIS_PER_DAY - 1));
        }

        int toOffset = rule.getRawOffset() + rule.getDSTSavings();
        switch (dtrule.getDateRuleType()) {
        case DateTimeRule.DOM:
            writeZonePropsByDOM(writer, isDst, rule.getName(), fromRawOffset + fromDSTSavings, toOffset,
                    dtrule.getRuleMonth(), dtrule.getRuleDayOfMonth(), startTime, MAX_TIME);
            break;
        case DateTimeRule.DOW:
            writeZonePropsByDOW(writer, isDst, rule.getName(), fromRawOffset + fromDSTSavings, toOffset,
                    dtrule.getRuleMonth(), dtrule.getRuleWeekInMonth(), dtrule.getRuleDayOfWeek(), startTime, MAX_TIME);
            break;
        case DateTimeRule.DOW_GEQ_DOM:
            writeZonePropsByDOW_GEQ_DOM(writer, isDst, rule.getName(), fromRawOffset + fromDSTSavings, toOffset,
                    dtrule.getRuleMonth(), dtrule.getRuleDayOfMonth(), dtrule.getRuleDayOfWeek(), startTime, MAX_TIME);
            break;
        case DateTimeRule.DOW_LEQ_DOM:
            writeZonePropsByDOW_LEQ_DOM(writer, isDst, rule.getName(), fromRawOffset + fromDSTSavings, toOffset,
                    dtrule.getRuleMonth(), dtrule.getRuleDayOfMonth(), dtrule.getRuleDayOfWeek(), startTime, MAX_TIME);
            break;
        }
    }

    /*
     * Convert the rule to its equivalent rule using WALL_TIME mode
     */
    private static DateTimeRule toWallTimeRule(DateTimeRule rule, int rawOffset, int dstSavings) {
        if (rule.getTimeRuleType() == DateTimeRule.WALL_TIME) {
            return rule;
        }
        int wallt = rule.getRuleMillisInDay();
        if (rule.getTimeRuleType() == DateTimeRule.UTC_TIME) {
            wallt += (rawOffset + dstSavings);
        } else if (rule.getTimeRuleType() == DateTimeRule.STANDARD_TIME) {
            wallt += dstSavings;
        }

        int month = -1, dom = 0, dow = 0, dtype = -1;
        int dshift = 0;
        if (wallt < 0) {
            dshift = -1;
            wallt += Grego.MILLIS_PER_DAY;
        } else if (wallt >= Grego.MILLIS_PER_DAY) {
            dshift = 1;
            wallt -= Grego.MILLIS_PER_DAY;
        }

        month = rule.getRuleMonth();
        dom = rule.getRuleDayOfMonth();
        dow = rule.getRuleDayOfWeek();
        dtype = rule.getDateRuleType();

        if (dshift != 0) {
            if (dtype == DateTimeRule.DOW) {
                // Convert to DOW_GEW_DOM or DOW_LEQ_DOM rule first
                int wim = rule.getRuleWeekInMonth();
                if (wim > 0) {
                    dtype = DateTimeRule.DOW_GEQ_DOM;
                    dom = 7 * (wim - 1) + 1;
                } else {
                    dtype = DateTimeRule.DOW_LEQ_DOM;
                    dom = MONTHLENGTH[month] + 7 * (wim + 1);
                }

            }
            // Shift one day before or after
            dom += dshift;
            if (dom == 0) {
                month--;
                month = month < Calendar.JANUARY ? Calendar.DECEMBER : month;
                dom = MONTHLENGTH[month];
            } else if (dom > MONTHLENGTH[month]) {
                month++;
                month = month > Calendar.DECEMBER ? Calendar.JANUARY : month;
                dom = 1;
            }
            if (dtype != DateTimeRule.DOM) {
                // Adjust day of week
                dow += dshift;
                if (dow < Calendar.SUNDAY) {
                    dow = Calendar.SATURDAY;
                } else if (dow > Calendar.SATURDAY) {
                    dow = Calendar.SUNDAY;
                }
            }
        }
        // Create a new rule
        DateTimeRule modifiedRule;
        if (dtype == DateTimeRule.DOM) {
            modifiedRule = new DateTimeRule(month, dom, wallt, DateTimeRule.WALL_TIME);
        } else {
            modifiedRule = new DateTimeRule(month, dom, dow,
                    (dtype == DateTimeRule.DOW_GEQ_DOM), wallt, DateTimeRule.WALL_TIME);
        }
        return modifiedRule;
    }

    /*
     * Write the opening section of zone properties
     */
    private static void beginZoneProps(Writer writer, boolean isDst, String tzname, int fromOffset, int toOffset, long startTime) throws IOException {
        writer.write(ICAL_BEGIN);
        writer.write(COLON);
        if (isDst) {
            writer.write(ICAL_DAYLIGHT);
        } else {
            writer.write(ICAL_STANDARD);
        }
        writer.write(NEWLINE);

        // TZOFFSETTO
        writer.write(ICAL_TZOFFSETTO);
        writer.write(COLON);
        writer.write(millisToOffset(toOffset));
        writer.write(NEWLINE);

        // TZOFFSETFROM
        writer.write(ICAL_TZOFFSETFROM);
        writer.write(COLON);
        writer.write(millisToOffset(fromOffset));
        writer.write(NEWLINE);

        // TZNAME
        writer.write(ICAL_TZNAME);
        writer.write(COLON);
        writer.write(tzname);
        writer.write(NEWLINE);
        
        // DTSTART
        writer.write(ICAL_DTSTART);
        writer.write(COLON);
        writer.write(getDateTimeString(startTime + fromOffset));
        writer.write(NEWLINE);        
    }

    /*
     * Writes the closing section of zone properties
     */
    private static void endZoneProps(Writer writer, boolean isDst) throws IOException{
        // END:STANDARD or END:DAYLIGHT
        writer.write(ICAL_END);
        writer.write(COLON);
        if (isDst) {
            writer.write(ICAL_DAYLIGHT);
        } else {
            writer.write(ICAL_STANDARD);
        }
        writer.write(NEWLINE);
    }

    /*
     * Write the beginning part of RRULE line
     */
    private static void beginRRULE(Writer writer, int month) throws IOException {
        writer.write(ICAL_RRULE);
        writer.write(COLON);
        writer.write(ICAL_FREQ);
        writer.write(EQUALS_SIGN);
        writer.write(ICAL_YEARLY);
        writer.write(SEMICOLON);
        writer.write(ICAL_BYMONTH);
        writer.write(EQUALS_SIGN);
        writer.write(Integer.toString(month + 1));
        writer.write(SEMICOLON);
    }

    /*
     * Append the UNTIL attribute after RRULE line
     */
    private static void appendUNTIL(Writer writer, String until) throws IOException {
        if (until != null) {
            writer.write(SEMICOLON);
            writer.write(ICAL_UNTIL);
            writer.write(EQUALS_SIGN);
            writer.write(until);
        }
    }

    /*
     * Write the opening section of the VTIMEZONE block
     */
    private void writeHeader(Writer writer)throws IOException {
        writer.write(ICAL_BEGIN);
        writer.write(COLON);
        writer.write(ICAL_VTIMEZONE);
        writer.write(NEWLINE);
        writer.write(ICAL_TZID);
        writer.write(COLON);
        writer.write(tz.getID());
        writer.write(NEWLINE);
        if (tzurl != null) {
            writer.write(ICAL_TZURL);
            writer.write(COLON);
            writer.write(tzurl);
            writer.write(NEWLINE);
        }
        if (lastmod != null) {
            writer.write(ICAL_LASTMOD);
            writer.write(COLON);
            writer.write(getUTCDateTimeString(lastmod.getTime()));
            writer.write(NEWLINE);
        }
    }

    /*
     * Write the closing section of the VTIMEZONE definition block
     */
    private static void writeFooter(Writer writer) throws IOException {
        writer.write(ICAL_END);
        writer.write(COLON);
        writer.write(ICAL_VTIMEZONE);
        writer.write(NEWLINE);
    }

    /*
     * Convert date/time to RFC2445 Date-Time form #1 DATE WITH LOCAL TIME
     */
    private static String getDateTimeString(long time) {
        int[] fields = Grego.timeToFields(time, null);
        StringBuilder sb = new StringBuilder(15);
        sb.append(numToString(fields[0], 4));
        sb.append(numToString(fields[1] + 1, 2));
        sb.append(numToString(fields[2], 2));
        sb.append('T');

        int t = fields[5];
        int hour = t / Grego.MILLIS_PER_HOUR;
        t %= Grego.MILLIS_PER_HOUR;
        int min = t / Grego.MILLIS_PER_MINUTE;
        t %= Grego.MILLIS_PER_MINUTE;
        int sec = t / Grego.MILLIS_PER_SECOND;
        
        sb.append(numToString(hour, 2));
        sb.append(numToString(min, 2));
        sb.append(numToString(sec, 2));
        return sb.toString();
    }

    /*
     * Convert date/time to RFC2445 Date-Time form #2 DATE WITH UTC TIME
     */
    private static String getUTCDateTimeString(long time) {
        return getDateTimeString(time) + "Z";
    }

    /*
     * Parse RFC2445 Date-Time form #1 DATE WITH LOCAL TIME and
     * #2 DATE WITH UTC TIME
     */
    private static long parseDateTimeString(String str, int offset) {
        int year = 0, month = 0, day = 0, hour = 0, min = 0, sec = 0;
        boolean isUTC = false;
        boolean isValid = false;
        do {
            if (str == null) {
                break;
            }

            int length = str.length();
            if (length != 15 && length != 16) {
                // FORM#1 15 characters, such as "20060317T142115"
                // FORM#2 16 characters, such as "20060317T142115Z"
                break;
            }
            if (str.charAt(8) != 'T') {
                // charcter "T" must be used for separating date and time
                break;
            }
            if (length == 16) {
                if (str.charAt(15) != 'Z') {
                    // invalid format
                    break;
                }
                isUTC = true;
            }

            try {
                year = Integer.parseInt(str.substring(0, 4));
                month = Integer.parseInt(str.substring(4, 6)) - 1;  // 0-based
                day = Integer.parseInt(str.substring(6, 8));
                hour = Integer.parseInt(str.substring(9, 11));
                min = Integer.parseInt(str.substring(11, 13));
                sec = Integer.parseInt(str.substring(13, 15));
            } catch (NumberFormatException nfe) {
                break;
            }

            // check valid range
            int maxDayOfMonth = Grego.monthLength(year, month);
            if (year < 0 || month < 0 || month > 11 || day < 1 || day > maxDayOfMonth ||
                    hour < 0 || hour >= 24 || min < 0 || min >= 60 || sec < 0 || sec >= 60) {
                break;
            }

            isValid = true;
        } while(false);

        if (!isValid) {
            throw new IllegalArgumentException("Invalid date time string format");
        }
        // Calculate the time
        long time = Grego.fieldsToDay(year, month, day) * Grego.MILLIS_PER_DAY;
        time += (hour*Grego.MILLIS_PER_HOUR + min*Grego.MILLIS_PER_MINUTE + sec*Grego.MILLIS_PER_SECOND);
        if (!isUTC) {
            time -= offset;
        }
        return time;
    }

    /*
     * Convert RFC2445 utc-offset string to milliseconds
     */
    private static int offsetStrToMillis(String str) {
        boolean isValid = false;
        int sign = 0, hour = 0, min = 0, sec = 0;

        do {
            if (str == null) {
                break;
            }
            int length = str.length();
            if (length != 5 && length != 7) {
                // utf-offset must be 5 or 7 characters
                break;
            }
            // sign
            char s = str.charAt(0);
            if (s == '+') {
                sign = 1;
            } else if (s == '-') {
                sign = -1;
            } else {
                // utf-offset must start with "+" or "-"
                break;
            }

            try {
                hour = Integer.parseInt(str.substring(1, 3));
                min = Integer.parseInt(str.substring(3, 5));
                if (length == 7) {
                    sec = Integer.parseInt(str.substring(5, 7));
                }
            } catch (NumberFormatException nfe) {
                break;
            }
            isValid = true;
        } while(false);

        if (!isValid) {
            throw new IllegalArgumentException("Bad offset string");
        }
        int millis = sign * ((hour * 60 + min) * 60 + sec) * 1000;
        return millis;
    }

    /*
     * Convert milliseconds to RFC2445 utc-offset string
     */
    private static String millisToOffset(int millis) {
        StringBuilder sb = new StringBuilder(7);
        if (millis >= 0) {
            sb.append('+');
        } else {
            sb.append('-');
            millis = -millis;
        }
        int hour, min, sec;
        int t = millis / 1000;

        sec = t % 60;
        t = (t - sec) / 60;
        min = t % 60;
        hour = t / 60;

        sb.append(numToString(hour, 2));
        sb.append(numToString(min, 2));
        sb.append(numToString(sec, 2));

        return sb.toString();
    }

    /*
     * Format integer number
     */
    private static String numToString(int num, int width) {
        String str = Integer.toString(num);
        int len = str.length();
        if (len >= width) {
            return str.substring(len - width, len);
        }
        StringBuilder sb = new StringBuilder(width);
        for (int i = len; i < width; i++) {
            sb.append('0');
        }
        sb.append(str);
        return sb.toString();
    }

    // Freezable stuffs
    private volatile transient boolean isFrozen = false;

    /**
     * {@inheritDoc}
     * @stable ICU 49
     */
    public boolean isFrozen() {
        return isFrozen;
    }

    /**
     * {@inheritDoc}
     * @stable ICU 49
     */
    public TimeZone freeze() {
        isFrozen = true;
        return this;
    }

    /**
     * {@inheritDoc}
     * @stable ICU 49
     */
    public TimeZone cloneAsThawed() {
        VTimeZone vtz = (VTimeZone)super.cloneAsThawed();
        vtz.tz = (BasicTimeZone)tz.cloneAsThawed();
        vtz.isFrozen = false;
        return vtz;
    }
}
