// Path: rfc3986-uri/src/main/java/org/dmfs/rfc3986/Authority.java
// public interface Authority
// {
//     /**
//      * Returns the {@link Optional} user info part of the authority in encoded form.
//      *
//      * @return The {@link UriEncoded} user info.
//      */
//     Optional<? extends UriEncoded> userInfo();
// 
//     /**
//      * Returns the host of this authority.
//      *
//      * @return The {@link UriEncoded} host.
//      */
//     UriEncoded host();
// 
//     /**
//      * The {@link Optional} port number.
//      *
//      * @return An {@link Optional} port number (as an {@link Integer}).
//      */
//     Optional<Integer> port();
// }
// 
// Path: rfc3986-uri/src/main/java/org/dmfs/rfc3986/UriEncoded.java
// public interface UriEncoded extends CharSequence
// {
//     /**
//      * Returns a normalized version of this {@link UriEncoded}. In particular that means any percent-encoded unreserved characters are decoded and
//      * percent-encoding sequences are converted to uppercase.
//      *
//      * @return The normalized version of this {@link UriEncoded}.
//      */
//     UriEncoded normalized();
// 
//     /**
//      * Returns the decoded text, using the given charset to decode the non-ASCII characters.
//      *
//      * @param charset
//      *         The name of the charset.
//      *
//      * @return
//      */
//     CharSequence decoded(String charset) throws UnsupportedEncodingException;
// 
//     /**
//      * Returns the decoded text assuming UTF-8 encoding.
//      *
//      * @return
//      */
//     CharSequence decoded();
// 
//     @Override
//     UriEncoded subSequence(int startIndex, int endIndex);
// 
//     @Override
//     String toString();
// }
// 
// Path: rfc3986-uri/src/main/java/org/dmfs/rfc3986/utils/Parsed.java
// public interface Parsed
// {
//     /**
//      * The length of the component in the source.
//      *
//      * @return
//      */
//     int parsedLength();
// }
// 
// Path: rfc3986-uri/src/main/java/org/dmfs/rfc3986/validation/CharSets.java
// public final static CharSet DIGIT = new BitMapCharSet(0, 0x03FF0000, 0, 0);
// 
// Path: rfc3986-uri/src/main/java/org/dmfs/rfc3986/validation/CharSets.java
// public final static CharSet HOST_TERMINATOR_CHARS = new BitMapCharSet(0, 0x84008008, 0x00000000, 0x00000000);
// 
// Path: rfc3986-uri/src/main/java/org/dmfs/rfc3986/validation/CharSets.java
// public final static CharSet REG_NAME_CHAR = new BitMapCharSet(0, 0x2BFF7FF2, 0x87FFFFFE, 0x47FFFFFE);


import org.dmfs.optional.Optional;
import org.dmfs.optional.Present;
import org.dmfs.rfc3986.Authority;
import org.dmfs.rfc3986.UriEncoded;
import org.dmfs.rfc3986.utils.Parsed;
import static org.dmfs.optional.Absent.absent;
import static org.dmfs.rfc3986.validation.CharSets.DIGIT;
import static org.dmfs.rfc3986.validation.CharSets.HOST_TERMINATOR_CHARS;
import static org.dmfs.rfc3986.validation.CharSets.REG_NAME_CHAR;
    }


    @Override
    public Optional<Integer> port()
    {
        if (mPort == null)
        {
            mPort = parsedPort();
        }
        return mPort;
    }


    private Optional<Integer> parsedPort()
    {
        final UriEncoded authority = mAuthority;
        final int count = authority.length();
        final int portPos = host().length() + userInfo().parsedLength();
        if (portPos + 1 >= count || authority.charAt(portPos) != ':')
        {
            mEnd = portPos;
            // no port
            return absent();
        }
        int port = 0;
        int i = portPos + 1;
        while (i < count && DIGIT.contains(authority.charAt(i)))
        {
            port = port * 10 + authority.charAt(i) - '0';
// Path: rfc3986-uri/src/main/java/org/dmfs/rfc3986/Authority.java
// public interface Authority
// {
//     /**
//      * Returns the {@link Optional} user info part of the authority in encoded form.
//      *
//      * @return The {@link UriEncoded} user info.
//      */
//     Optional<? extends UriEncoded> userInfo();
// 
//     /**
//      * Returns the host of this authority.
//      *
//      * @return The {@link UriEncoded} host.
//      */
//     UriEncoded host();
// 
//     /**
//      * The {@link Optional} port number.
//      *
//      * @return An {@link Optional} port number (as an {@link Integer}).
//      */
//     Optional<Integer> port();
// }
// 
// Path: rfc3986-uri/src/main/java/org/dmfs/rfc3986/UriEncoded.java
// public interface UriEncoded extends CharSequence
// {
//     /**
//      * Returns a normalized version of this {@link UriEncoded}. In particular that means any percent-encoded unreserved characters are decoded and
//      * percent-encoding sequences are converted to uppercase.
//      *
//      * @return The normalized version of this {@link UriEncoded}.
//      */
//     UriEncoded normalized();
// 
//     /**
//      * Returns the decoded text, using the given charset to decode the non-ASCII characters.
//      *
//      * @param charset
//      *         The name of the charset.
//      *
//      * @return
//      */
//     CharSequence decoded(String charset) throws UnsupportedEncodingException;
// 
//     /**
//      * Returns the decoded text assuming UTF-8 encoding.
//      *
//      * @return
//      */
//     CharSequence decoded();
// 
//     @Override
//     UriEncoded subSequence(int startIndex, int endIndex);
// 
//     @Override
//     String toString();
// }
// 
// Path: rfc3986-uri/src/main/java/org/dmfs/rfc3986/utils/Parsed.java
// public interface Parsed
// {
//     /**
//      * The length of the component in the source.
//      *
//      * @return
//      */
//     int parsedLength();
// }
// 
// Path: rfc3986-uri/src/main/java/org/dmfs/rfc3986/validation/CharSets.java
// public final static CharSet DIGIT = new BitMapCharSet(0, 0x03FF0000, 0, 0);
// 
// Path: rfc3986-uri/src/main/java/org/dmfs/rfc3986/validation/CharSets.java
// public final static CharSet HOST_TERMINATOR_CHARS = new BitMapCharSet(0, 0x84008008, 0x00000000, 0x00000000);
// 
// Path: rfc3986-uri/src/main/java/org/dmfs/rfc3986/validation/CharSets.java
// public final static CharSet REG_NAME_CHAR = new BitMapCharSet(0, 0x2BFF7FF2, 0x87FFFFFE, 0x47FFFFFE);


// Path: rfc3986-uri/src/main/java/org/dmfs/rfc3986/authorities/EncodedAuthority.java
import org.dmfs.optional.Optional;
import org.dmfs.optional.Present;
import org.dmfs.rfc3986.Authority;
import org.dmfs.rfc3986.UriEncoded;
import org.dmfs.rfc3986.utils.Parsed;
import static org.dmfs.optional.Absent.absent;
import static org.dmfs.rfc3986.validation.CharSets.DIGIT;
import static org.dmfs.rfc3986.validation.CharSets.HOST_TERMINATOR_CHARS;
import static org.dmfs.rfc3986.validation.CharSets.REG_NAME_CHAR;

    }


    @Override
    public Optional<Integer> port()
    {
        if (mPort == null)
        {
            mPort = parsedPort();
        }
        return mPort;
    }


    private Optional<Integer> parsedPort()
    {
        final UriEncoded authority = mAuthority;
        final int count = authority.length();
        final int portPos = host().length() + userInfo().parsedLength();
        if (portPos + 1 >= count || authority.charAt(portPos) != ':')
        {
            mEnd = portPos;
            // no port
            return absent();
        }
        int port = 0;
        int i = portPos + 1;
        while (i < count && DIGIT.contains(authority.charAt(i)))
        {
            port = port * 10 + authority.charAt(i) - '0';
            ++i;