diff options
author | Elliott Hughes <enh@google.com> | 2014-06-16 19:55:23 -0700 |
---|---|---|
committer | Elliott Hughes <enh@google.com> | 2014-07-07 16:29:09 -0700 |
commit | 0aff1dd0b4be1b8d8cb45b59079ca883a1b3205a (patch) | |
tree | a94a4f9762003225f6220049aff1896622ef6965 /luni | |
parent | 7299cf9fcacfe96eacd15584efb065c32be4ffee (diff) | |
download | libcore-0aff1dd0b4be1b8d8cb45b59079ca883a1b3205a.zip libcore-0aff1dd0b4be1b8d8cb45b59079ca883a1b3205a.tar.gz libcore-0aff1dd0b4be1b8d8cb45b59079ca883a1b3205a.tar.bz2 |
Remove.
(cherry-pick of 63744c884dd4b4f4307f2b021fb894af164972af.)
Change-Id: Ibf79a402e1bad98a262e380fcee3d35c127ae6d5
Diffstat (limited to 'luni')
34 files changed, 149 insertions, 4938 deletions
diff --git a/luni/src/main/java/java/lang/Character.java b/luni/src/main/java/java/lang/Character.java index 2bf3a89..8efd6cd 100644 --- a/luni/src/main/java/java/lang/Character.java +++ b/luni/src/main/java/java/lang/Character.java @@ -1526,426 +1526,6 @@ public final class Character implements Serializable, Comparable<Character> { private static native int unicodeBlockForCodePoint(int codePoint); - /** - * Represents a <a href="http://www.unicode.org/reports/tr24/">Unicode script</a>. - * Every Unicode code point is contained by a single {@code UnicodeScript}. Code points - * shared between scripts will be in {@code COMMON}. Code points for combining - * characters that can be applied to multiple scripts will be in {@code INHERITED} - * because they inherit the script of their base character. Code points whose scripts - * don't have a corresponding {@code UnicodeScript} will be in {@code UNKNOWN}. - * - * @since 1.7 - * @hide - */ - public static enum UnicodeScript { - /** ISO 15924 English name "Arabic" */ - ARABIC, - /** ISO 15924 English name "Armenian" */ - ARMENIAN, - /** ISO 15924 English name "Avestan" */ - AVESTAN, - /** ISO 15924 English name "Balinese" */ - BALINESE, - /** ISO 15924 English name "Bamum" */ - BAMUM, - /** ISO 15924 English name "Batak" */ - BATAK, - /** ISO 15924 English name "Bengali" */ - BENGALI, - /** ISO 15924 English name "Bopomofo" */ - BOPOMOFO, - /** ISO 15924 English name "Brahmi" */ - BRAHMI, - /** ISO 15924 English name "Braille" */ - BRAILLE, - /** ISO 15924 English name "Buginese" */ - BUGINESE, - /** ISO 15924 English name "Buhid" */ - BUHID, - /** ISO 15924 English name "Unified Canadian Aboriginal Syllabics" */ - CANADIAN_ABORIGINAL, - /** ISO 15924 English name "Carian" */ - CARIAN, - /** ISO 15924 English name "Cham" */ - CHAM, - /** ISO 15924 English name "Cherokee" */ - CHEROKEE, - /** ISO 15924 English name "Common" */ - COMMON, - /** ISO 15924 English name "Coptic" */ - COPTIC, - /** ISO 15924 English name "Cuneiform" */ - CUNEIFORM, - /** ISO 15924 English name "Cypriot" */ - CYPRIOT, - /** ISO 15924 English name "Cyrillic" */ - CYRILLIC, - /** ISO 15924 English name "Deseret" */ - DESERET, - /** ISO 15924 English name "Devanagari" */ - DEVANAGARI, - /** ISO 15924 English name "Egyptian hieroglyphs" */ - EGYPTIAN_HIEROGLYPHS, - /** ISO 15924 English name "Ethiopic" */ - ETHIOPIC, - /** ISO 15924 English name "Georgian" */ - GEORGIAN, - /** ISO 15924 English name "Glagolitic" */ - GLAGOLITIC, - /** ISO 15924 English name "Gothic" */ - GOTHIC, - /** ISO 15924 English name "Greek" */ - GREEK, - /** ISO 15924 English name "Gujarati" */ - GUJARATI, - /** ISO 15924 English name "Gurmukhi" */ - GURMUKHI, - /** ISO 15924 English name "Han" */ - HAN, - /** ISO 15924 English name "Hangul" */ - HANGUL, - /** ISO 15924 English name "Hanunoo" */ - HANUNOO, - /** ISO 15924 English name "Hebrew" */ - HEBREW, - /** ISO 15924 English name "Hiragana" */ - HIRAGANA, - /** ISO 15924 English name "Imperial aramaic" */ - IMPERIAL_ARAMAIC, - /** ISO 15924 English name "Inherited" */ - INHERITED, - /** ISO 15924 English name "Inscriptional pahlavi" */ - INSCRIPTIONAL_PAHLAVI, - /** ISO 15924 English name "Inscriptional parthian" */ - INSCRIPTIONAL_PARTHIAN, - /** ISO 15924 English name "Javanese" */ - JAVANESE, - /** ISO 15924 English name "Kaithi" */ - KAITHI, - /** ISO 15924 English name "Kannada" */ - KANNADA, - /** ISO 15924 English name "Katakana" */ - KATAKANA, - /** ISO 15924 English name "Kayah li" */ - KAYAH_LI, - /** ISO 15924 English name "Kharoshthi" */ - KHAROSHTHI, - /** ISO 15924 English name "Khmer" */ - KHMER, - /** ISO 15924 English name "Lao" */ - LAO, - /** ISO 15924 English name "Latin" */ - LATIN, - /** ISO 15924 English name "Lepcha" */ - LEPCHA, - /** ISO 15924 English name "Limbu" */ - LIMBU, - /** ISO 15924 English name "Linear B" */ - LINEAR_B, - /** ISO 15924 English name "Lisu" */ - LISU, - /** ISO 15924 English name "Lycian" */ - LYCIAN, - /** ISO 15924 English name "Lydian" */ - LYDIAN, - /** ISO 15924 English name "Malayalam" */ - MALAYALAM, - /** ISO 15924 English name "Mandaic" */ - MANDAIC, - /** ISO 15924 English name "Meetei Mayek (Meithei, Meetei)" */ - MEETEI_MAYEK, - /** ISO 15924 English name "Mongolian" */ - MONGOLIAN, - /** ISO 15924 English name "Myanmar" */ - MYANMAR, - /** ISO 15924 English name "New Tai Lue" */ - NEW_TAI_LUE, - /** ISO 15924 English name "Nko" */ - NKO, - /** ISO 15924 English name "Ogham" */ - OGHAM, - /** ISO 15924 English name "Ol Chiki" */ - OL_CHIKI, - /** ISO 15924 English name "Old Italic" */ - OLD_ITALIC, - /** ISO 15924 English name "Old Persian" */ - OLD_PERSIAN, - /** ISO 15924 English name "Old South Arabian" */ - OLD_SOUTH_ARABIAN, - /** ISO 15924 English name "Old Turkic, Orkhon Runic" */ - OLD_TURKIC, - /** ISO 15924 English name "Oriya" */ - ORIYA, - /** ISO 15924 English name "Osmanya" */ - OSMANYA, - /** ISO 15924 English name "Phags-pa" */ - PHAGS_PA, - /** ISO 15924 English name "Phoenician" */ - PHOENICIAN, - /** ISO 15924 English name "Rejang" */ - REJANG, - /** ISO 15924 English name "Runic" */ - RUNIC, - /** ISO 15924 English name "Samaritan" */ - SAMARITAN, - /** ISO 15924 English name "Saurashtra" */ - SAURASHTRA, - /** ISO 15924 English name "Shavian" */ - SHAVIAN, - /** ISO 15924 English name "Sinhala" */ - SINHALA, - /** ISO 15924 English name "Sundanese" */ - SUNDANESE, - /** ISO 15924 English name "Syloti Nagri" */ - SYLOTI_NAGRI, - /** ISO 15924 English name "Syriac" */ - SYRIAC, - /** ISO 15924 English name "Tagalog" */ - TAGALOG, - /** ISO 15924 English name "Tagbanwa" */ - TAGBANWA, - /** ISO 15924 English name "Tai Le" */ - TAI_LE, - /** ISO 15924 English name "Tai Tham (Lanna)" */ - TAI_THAM, - /** ISO 15924 English name "Tai Viet" */ - TAI_VIET, - /** ISO 15924 English name "Tamil" */ - TAMIL, - /** ISO 15924 English name "Telugu" */ - TELUGU, - /** ISO 15924 English name "Thaana" */ - THAANA, - /** ISO 15924 English name "Thai" */ - THAI, - /** ISO 15924 English name "Tibetan" */ - TIBETAN, - /** ISO 15924 English name "Tifinagh" */ - TIFINAGH, - /** ISO 15924 English name "Ugaritic" */ - UGARITIC, - /** ISO 15924 English name "Unknown" */ - UNKNOWN, - /** ISO 15924 English name "Vai" */ - VAI, - /** ISO 15924 English name "Yi" */ - YI; - - private static final UnicodeScript[] SCRIPTS = { - COMMON, - INHERITED, - ARABIC, - ARMENIAN, - BENGALI, - BOPOMOFO, - CHEROKEE, - COPTIC, - CYRILLIC, - DESERET, - DEVANAGARI, - ETHIOPIC, - GEORGIAN, - GOTHIC, - GREEK, - GUJARATI, - GURMUKHI, - HAN, - HANGUL, - HEBREW, - HIRAGANA, - KANNADA, - KATAKANA, - KHMER, - LAO, - LATIN, - MALAYALAM, - MONGOLIAN, - MYANMAR, - OGHAM, - OLD_ITALIC, - ORIYA, - RUNIC, - SINHALA, - SYRIAC, - TAMIL, - TELUGU, - THAANA, - THAI, - TIBETAN, - CANADIAN_ABORIGINAL, - YI, - TAGALOG, - HANUNOO, - BUHID, - TAGBANWA, - BRAILLE, - CYPRIOT, - LIMBU, - LINEAR_B, - OSMANYA, - SHAVIAN, - TAI_LE, - UGARITIC, - null, // USCRIPT_KATAKANA_OR_HIRAGANA - BUGINESE, - GLAGOLITIC, - KHAROSHTHI, - SYLOTI_NAGRI, - NEW_TAI_LUE, - TIFINAGH, - OLD_PERSIAN, - BALINESE, - BATAK, - null, // USCRIPT_BLISSYMBOLS, - BRAHMI, - CHAM, - null, // USCRIPT_CIRTH, - null, // USCRIPT_OLD_CHURCH_SLAVONIC_CYRILLIC, - null, // USCRIPT_DEMOTIC_EGYPTIAN, - null, // USCRIPT_HIERATIC_EGYPTIAN, - EGYPTIAN_HIEROGLYPHS, - null, // USCRIPT_USCRIPT_KHUTSURI, - null, // USCRIPT_SIMPLIFIED_HAN, - null, // USCRIPT_TRADITIONAL_HAN, - null, // USCRIPT_PAHAWH_HMONG, - null, // USCRIPT_OLD_HUNGARIAN, - null, // USCRIPT_HARAPPAN_INDUS, - JAVANESE, - KAYAH_LI, - null, // USCRIPT_LATIN_FRAKTUR, - null, // USCRIPT_LATIN_GAELIC, - LEPCHA, - null, // USCRIPT_LINEAR_A, - MANDAIC, // == MANDAEAN - null, // USCRIPT_MAYAN_HIEROGLYPHS, - null, // USCRIPT_MEROITIC_HIEROGLYPHS == USCRIPT_MEROITIC - null, // USCRIPT_NKO, - OLD_TURKIC, // USCRIPT_ORKHON == OLD_TURKIC, - null, // USCRIPT_OLD_PERMIC, - PHAGS_PA, - PHOENICIAN, - null, // USCRIPT_PHONETIC_POLLARD === MIAO, - null, // USCRIPT_RONGORONGO, - null, // USCRIPT_SARATI, - null, // USCRIPT_ESTRANGELO_SYRIAC, - null, // USCRIPT_WESTERN_SYRIAC, - null, // USCRIPT_EASTERN_SYRIAC, - null, // USCRIPT_TENGWAR, - VAI, - null, // USCRIPT_VISIBLE_SPEECH, - CUNEIFORM, - null, // USCRIPT_UNWRITTEN_LANGUAGES, - UNKNOWN, - CARIAN, - null, // USCRIPT_JAPANESE, - TAI_THAM, // USCRIPT_LANNA (aka TAI_THAM), - LYCIAN, - LYDIAN, - OL_CHIKI, - REJANG, - SAURASHTRA, - null, // USCRIPT_SIGN_WRITING, - SUNDANESE, - null, // USCRIPT_MOON, - MEETEI_MAYEK, // USCRIPT_MEITEI_MAYEK (aka MEETEI, MEITHEI), - IMPERIAL_ARAMAIC, - AVESTAN, - null, // USCRIPT_CHAKMA, - null, // USCRIPT_KOREAN, - KAITHI, - null, // USCRIPT_MANICHAEAN, - INSCRIPTIONAL_PAHLAVI, - null, // USCRIPT_PSALTER_PAHLAVI, - null, // USCRIPT_BOOK_PAHLAVI, - INSCRIPTIONAL_PARTHIAN, - SAMARITAN, - TAI_VIET, - null, // USCRIPT_MATHEMATICAL_NOTATION, - null, // USCRIPT_SYMBOLS, - BAMUM, - LISU, - null, // USCRIPT_NAKHI_GEBA, - OLD_SOUTH_ARABIAN, - null, // USCRIPT_BASSA_VAH, - null, // USCRIPT_DUPLOYAN_SHORTAND, - null, // USCRIPT_ELBASAN, - null, // USCRIPT_GRANTHA, - null, // USCRIPT_KPELLE, - null, // USCRIPT_LOMA, - null, // USCRIPT_MENDE, - null, // USCRIPT_MEROITIC_CURSIVE, - null, // USCRIPT_OLD_NORTH_ARABIAN, - null, // USCRIPT_NABATAEAN, - null, // USCRIPT_PALMYRENE, - null, // USCRIPT_SINDHI, - null, // USCRIPT_WARANG_CITI, - null, // USCRIPT_AFAKA, - null, // USCRIPT_JURCHEN, - null, // USCRIPT_MRO, - null, // USCRIPT_NUSHU, - null, // USCRIPT_SHARADA, - null, // USCRIPT_SORA_SOMPENG, - null, // USCRIPT_TAKRI, - null, // USCRIPT_TANGUT, - null, // USCRIPT_WOLEAI, - null, // USCRIPT_ANATOLIAN_HIEROGLYPHS, - null, // USCRIPT_KHOJKI, - null, // USCRIPT_TIRHUTA, - }; - - /** - * Returns the {@link UnicodeScript} value identified by {@code scriptName}. - * {@code scriptName} can be a ISO-15924 English script name - * or an alias (ISO-15924 script code) for that name. - * {@see http://www.unicode.org/iso15924/iso15924-codes.html} - * Lookups are case insensitive. - * - * @throws NullPointerException if {@code scriptName} is null. - * @throws IllegalAccessException if {@code scriptName} in invalid. - * - * @since 1.7 - */ - public static UnicodeScript forName(String scriptName) { - if (scriptName == null) { - throw new NullPointerException("scriptName == null"); - } - - final int script = unicodeScriptForName(scriptName); - if (script == -1 || script >= SCRIPTS.length || - SCRIPTS[script] == null) { - throw new IllegalArgumentException("Unknown script: " + scriptName); - } - - return SCRIPTS[script]; - } - - /** - * Returns the {@link UnicodeScript} value that the given Unicode code - * point is assigned to. - * - * @throws IllegalArgumentException if {@code Point} is not a valid Unicode code point. - * - * @since 1.7 - */ - public static UnicodeScript of(int codePoint) { - checkValidCodePoint(codePoint); - int script = unicodeScriptForCodePoint(codePoint); - if (script == -1 || script >= SCRIPTS.length) { - // This signifies an ICU error. Complain loudly instead of swallowing - // the error up. - throw new IllegalArgumentException("Invalid codePoint: " + codePoint); - } - - // This happens when ICU maps the code point to a script known to ICU but - // not the Java API. - if (SCRIPTS[script] == null) { - return UNKNOWN; - } - - return SCRIPTS[script]; - } - } - private static native int unicodeScriptForName(String blockName); private static native int unicodeScriptForCodePoint(int codePoint); diff --git a/luni/src/main/java/java/net/HttpCookie.java b/luni/src/main/java/java/net/HttpCookie.java index 04121f7..dd81fd6 100644 --- a/luni/src/main/java/java/net/HttpCookie.java +++ b/luni/src/main/java/java/net/HttpCookie.java @@ -560,28 +560,6 @@ public final class HttpCookie implements Cloneable { } /** - * Returns the {@code HttpOnly} attribute. If {@code true} the cookie should not be accessible - * to scripts in a browser. - * - * @since 1.7 - * @hide Until ready for an API update - */ - public boolean isHttpOnly() { - return httpOnly; - } - - /** - * Returns the {@code HttpOnly} attribute. If {@code true} the cookie should not be accessible - * to scripts in a browser. - * - * @since 1.7 - * @hide Until ready for an API update - */ - public void setHttpOnly(boolean httpOnly) { - this.httpOnly = httpOnly; - } - - /** * Returns the value of this cookie. */ public String getValue() { diff --git a/luni/src/main/java/java/net/SocketOption.java b/luni/src/main/java/java/net/SocketOption.java deleted file mode 100644 index 3f65494..0000000 --- a/luni/src/main/java/java/net/SocketOption.java +++ /dev/null @@ -1,43 +0,0 @@ -/* - * Copyright (C) 2014 The Android Open Source Project - * - * Licensed under the Apache License, Version 2.0 (the "License"); - * you may not use this file except in compliance with the License. - * You may obtain a copy of the License at - * - * http://www.apache.org/licenses/LICENSE-2.0 - * - * Unless required by applicable law or agreed to in writing, software - * distributed under the License is distributed on an "AS IS" BASIS, - * WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied. - * See the License for the specific language governing permissions and - * limitations under the License. - */ - -package java.net; - -/** - * An option associated with a socket. - * - * <p>See {@link java.nio.channels.NetworkChannel#setOption}, - * {@link java.nio.channels.NetworkChannel#getOption} and - * {@link java.nio.channels.NetworkChannel#supportedOptions} for methods that use SocketOption. - * - * <p>See {@link StandardSocketOptions} for valid SocketOptions. - * - * @param <T> the type of the value - * @since 1.7 - * @hide Until ready for a public API change - */ -public interface SocketOption<T> { - - /** - * Returns the name of the option. - */ - String name(); - - /** - * Returns the type of the value of the option. - */ - Class<T> type(); -} diff --git a/luni/src/main/java/java/net/StandardSocketOptions.java b/luni/src/main/java/java/net/StandardSocketOptions.java deleted file mode 100644 index 3d10caf..0000000 --- a/luni/src/main/java/java/net/StandardSocketOptions.java +++ /dev/null @@ -1,407 +0,0 @@ -/* - * Copyright (C) 2014 The Android Open Source Project - * - * Licensed under the Apache License, Version 2.0 (the "License"); - * you may not use this file except in compliance with the License. - * You may obtain a copy of the License at - * - * http://www.apache.org/licenses/LICENSE-2.0 - * - * Unless required by applicable law or agreed to in writing, software - * distributed under the License is distributed on an "AS IS" BASIS, - * WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied. - * See the License for the specific language governing permissions and - * limitations under the License. - */ - -package java.net; - -import java.io.FileDescriptor; -import java.io.IOException; -import java.util.Collections; -import java.util.HashSet; -import java.util.Set; - -import libcore.io.IoBridge; - -/** - * Defines the set standard of socket options that can be supported by network channels. - * - * <p>See {@link java.nio.channels.NetworkChannel} for more information, particularly - * {@link java.nio.channels.NetworkChannel#supportedOptions()} for the options that are supported - * for each type of socket. - * - * @since 1.7 - * @hide Until ready for a public API change - */ -public final class StandardSocketOptions { - - /** - * The outgoing interface for multicast packets. - * - * <p>See {@link SocketOptions#IP_MULTICAST_IF2} for further documentation. - */ - public static final SocketOption<NetworkInterface> IP_MULTICAST_IF = - new NetworkInterfaceSocketOption("IP_MULTICAST_IF", SocketOptions.IP_MULTICAST_IF2); - - /** - * Whether the local loopback of multicast packets is enabled (true) or disabled (false). This - * option is enabled by default. - * - * <p>See {@link SocketOptions#IP_MULTICAST_LOOP} for further documentation. - */ - public static final SocketOption<Boolean> IP_MULTICAST_LOOP = - new BooleanSocketOption("IP_MULTICAST_LOOP", SocketOptions.IP_MULTICAST_LOOP); - - /** - * The time-to-live (TTL) for multicast packets. The value must be between 0 and 255 inclusive. - * A 0 value restricts the packet to the originating host. See also {@link #IP_MULTICAST_LOOP}. - * The default value is 1. - * - * <p>See <a href="http://tools.ietf.org/rfc/rfc1112.txt">RFC 1112: Host Extensions for IP - * Multicasting</a> for more information about IP multicast. - */ - public static final SocketOption<Integer> IP_MULTICAST_TTL = - new ByteRangeSocketOption("IP_MULTICAST_TTL", IoBridge.JAVA_IP_MULTICAST_TTL); - - /** - * The value for the type-of-service field of the IPv4 header, or the traffic class field of the - * IPv6 header. These correspond to the IP_TOS and IPV6_TCLASS socket options. These may be - * ignored by the underlying OS. Values must be between 0 and 255 inclusive. - * - * <p>See {@link SocketOptions#IP_TOS} for further documentation. - */ - public static final SocketOption<Integer> IP_TOS = - new ByteRangeSocketOption("IP_TOS", SocketOptions.IP_TOS); - - /** - * Whether broadcasting on datagram sockets is enabled or disabled. This option must be enabled to - * send broadcast messages. The default value is false. - * - * <p>See {@link SocketOptions#SO_BROADCAST} for further documentation. - */ - public static final SocketOption<Boolean> SO_BROADCAST = - new BooleanSocketOption("SO_BROADCAST", SocketOptions.SO_BROADCAST); - - /** - * Whether the kernel sends keepalive messages on connection-oriented sockets. - * - * <p>See {@link SocketOptions#SO_KEEPALIVE} for further documentation. - */ - public static final SocketOption<Boolean> SO_KEEPALIVE = - new BooleanSocketOption("SO_KEEPALIVE", SocketOptions.SO_KEEPALIVE); - - /** - * Number of seconds to wait when closing a socket if there is still some buffered data to be - * sent. - * - * <p>If this option is negative this option is disabled. This is the default value. If the value - * is 0 or positive it is enabled. - * - * <p>See {@link SocketOptions#SO_LINGER} for further documentation. - * - */ - public static final SocketOption<Integer> SO_LINGER = - new SocketOptionImpl<Integer>("SO_LINGER", Integer.class, SocketOptions.SO_LINGER) { - @Override - protected Object validateAndConvertValueBeforeSet( - FileDescriptor fd, Integer value) { - Object objectValue = super.validateAndConvertValueBeforeSet(fd, value); - if (value != null && value < 0) { - // IoBridge requires a "false" object to disable linger. - objectValue = Boolean.FALSE; - } - return objectValue; - } - - @Override - protected Integer validateAndConvertValueAfterGet(FileDescriptor fd, Object value) { - // IoBridge returns a "false" object to indicate that linger is disabled. - if (value != null && value instanceof Boolean) { - value = -1; - } - return super.validateAndConvertValueAfterGet(fd, value); - } - }; - - /** - * The size in bytes of a socket's receive buffer. This must be an integer greater than 0. - * This is a hint to the kernel; the kernel may use a larger buffer. - * - * <p>See {@link SocketOptions#SO_RCVBUF} for further documentation. - */ - public static final SocketOption<Integer> SO_RCVBUF = - new PositiveIntegerSocketOption("SO_RCVBUF", SocketOptions.SO_RCVBUF); - - /** - * Whether a reuse of a local address is allowed when another socket has not yet been removed by - * the operating system. - * - * <p>See {@link SocketOptions#SO_REUSEADDR} for further documentation. - */ - public static final SocketOption<Boolean> SO_REUSEADDR = - new BooleanSocketOption("SO_REUSEADDR", SocketOptions.SO_REUSEADDR); - - /** - * The size in bytes of a socket's send buffer. This must be an integer greater than 0. - * This is a hint to the kernel; the kernel may use a larger buffer. - * - * <p>See {@link SocketOptions#SO_SNDBUF} for further documentation. - */ - public static final SocketOption<Integer> SO_SNDBUF = - new PositiveIntegerSocketOption("SO_SNDBUF", SocketOptions.SO_SNDBUF); - - /** - * Specifies whether data is sent immediately on this socket or buffered. - * - * <p>See {@link SocketOptions#TCP_NODELAY} for further documentation. - */ - public static final SocketOption<Boolean> TCP_NODELAY = - new BooleanSocketOption("TCP_NODELAY", SocketOptions.TCP_NODELAY); - - /** - * The set of supported options for UDP sockets. - * - * @hide internal use only - */ - public static final Set<SocketOption<?>> DATAGRAM_SOCKET_OPTIONS; - - static { - HashSet<SocketOption<?>> mutableSet = new HashSet<SocketOption<?>>(8); - mutableSet.add(IP_MULTICAST_IF); - mutableSet.add(IP_MULTICAST_LOOP); - mutableSet.add(IP_MULTICAST_TTL); - mutableSet.add(IP_TOS); - mutableSet.add(SO_BROADCAST); - mutableSet.add(SO_REUSEADDR); - mutableSet.add(SO_RCVBUF); - mutableSet.add(SO_SNDBUF); - DATAGRAM_SOCKET_OPTIONS = Collections.unmodifiableSet(mutableSet); - } - - /** - * The set of supported options for TCP sockets. - * - * @hide internal use only - */ - public static final Set<SocketOption<?>> SOCKET_OPTIONS; - - static { - HashSet<SocketOption<?>> mutableSet = new HashSet<SocketOption<?>>(7); - mutableSet.add(IP_TOS); - mutableSet.add(SO_KEEPALIVE); - mutableSet.add(SO_LINGER); - mutableSet.add(TCP_NODELAY); - mutableSet.add(SO_RCVBUF); - mutableSet.add(SO_REUSEADDR); - mutableSet.add(SO_SNDBUF); - SOCKET_OPTIONS = Collections.unmodifiableSet(mutableSet); - } - - /** - * The set of supported options for TCP server sockets. - * - * @hide internal use only - */ - public static final Set<SocketOption<?>> SERVER_SOCKET_OPTIONS; - - static { - HashSet<SocketOption<?>> mutableSet = new HashSet<SocketOption<?>>(2); - mutableSet.add(SO_RCVBUF); - mutableSet.add(SO_REUSEADDR); - SERVER_SOCKET_OPTIONS = Collections.unmodifiableSet(mutableSet); - } - - /** - * A base class for SocketOption objects that passes the values to/from {@link IoBridge} as they - * are. For use with simple types like Integer and Boolean, and can be extended for more - * validation / type conversion. - * - * @hide internal use only - */ - public static class SocketOptionImpl<T> implements SocketOption<T> { - - protected final String name; - - private final Class<T> type; - - protected final int socketOption; - - public SocketOptionImpl(String name, Class<T> type, int socketOption) { - this.name = name; - this.type = type; - this.socketOption = socketOption; - } - - @Override - public String name() { - return name; - } - - @Override - public Class<T> type() { - return type; - } - - /** - * Sets the socket option of the file descriptor to value using IoBridge. - * - * @hide internal method - */ - public final void setValue(FileDescriptor fd, T value) throws IOException { - // Sanity check required because of type erasure. - if (value != null && !type.isAssignableFrom(value.getClass())) { - throw new AssertionError("Invalid type " + value + " of value for " + name); - } - Object objectValue = validateAndConvertValueBeforeSet(fd, value); - IoBridge.setSocketOption(fd, socketOption, objectValue); - } - - /** - * Throws IllegalArgumentException if the value is outside of the acceptable range. - * Subclasses can override to apply option-specific validate, and may also convert the value - * to a different type or value. The default implementation prevents null values and returns - * the value unchanged. - */ - protected Object validateAndConvertValueBeforeSet(FileDescriptor fd, T value) { - if (value == null) { - throw new IllegalArgumentException("value for " + name + " must not be null"); - } - return value; - } - - /** - * Gets the value of the socket option. - * - * @hide internal method - */ - public final T getValue(FileDescriptor fd) throws IOException { - Object value = IoBridge.getSocketOption(fd, socketOption); - T typedValue = validateAndConvertValueAfterGet(fd, value); - if (typedValue != null && !type.isAssignableFrom(typedValue.getClass())) { - // Sanity check required because of type erasure. - throw new AssertionError("Unexpected type of value returned for " + name); - } - return typedValue; - } - - /** - * Throws AssertionError if the value is outside of the acceptable range. - * Implementations may also convert the value to a different type or - * value. The default implementation does nothing. - */ - @SuppressWarnings("unchecked") - protected T validateAndConvertValueAfterGet(FileDescriptor fd, Object value) { - return (T) value; - } - } - - /** - * A SocketOption capable of setting / getting an boolean value. - */ - private static class BooleanSocketOption extends SocketOptionImpl<Boolean> { - - public BooleanSocketOption(String name, int socketOption) { - super(name, Boolean.class, socketOption); - } - } - - /** - * A SocketOption capable of setting / getting an network interface value. - */ - private static class NetworkInterfaceSocketOption extends SocketOptionImpl<NetworkInterface> { - - public NetworkInterfaceSocketOption(String name, int socketOption) { - super(name, NetworkInterface.class, socketOption); - } - - @Override - public Integer validateAndConvertValueBeforeSet(FileDescriptor fd, NetworkInterface value) { - if (value == null) { - throw new IllegalArgumentException("value for " + name + " must not be null"); - } - int nicIndex = value.getIndex(); - if (nicIndex == -1) { - throw new IllegalArgumentException("The NetworkInterface must have a valid index"); - } - return nicIndex; - } - - @Override - public NetworkInterface validateAndConvertValueAfterGet(FileDescriptor fd, Object value) { - if (value == null) { - return null; - } else if (!(value instanceof Integer)) { - throw new AssertionError("Unexpected type of value returned for " + name); - } - - int nicIndex = (Integer) value; - try { - return NetworkInterface.getByIndex(nicIndex); - } catch (SocketException e) { - throw new IllegalArgumentException( - "Unable to resolve NetworkInterface index: " + nicIndex, e); - } - } - } - - /** - * A SocketOption capable of setting / getting an integer in the range 0-255. - */ - private static class ByteRangeSocketOption extends SocketOptionImpl<Integer> { - - public ByteRangeSocketOption(String name, int socketOption) { - super(name, Integer.class, socketOption); - } - - @Override - protected Object validateAndConvertValueBeforeSet(FileDescriptor fd, Integer value) { - if (value == null || value < 0 || value > 255) { - throw new IllegalArgumentException(name + " must be >= 0 and <= 255, is " + value); - } - return value; - } - - @Override - protected Integer validateAndConvertValueAfterGet(FileDescriptor fd, Object value) { - if (!(value instanceof Integer)) { - throw new AssertionError("Unexpected value for option " + name + ": " + value); - } - int intValue = (Integer) value; - if (intValue < 0 || intValue > 255) { - throw new AssertionError("Unexpected value for option " + name + ": " + value); - } - return intValue; - } - } - - /** - * A SocketOption capable of setting / getting an integer in the range 1.. - */ - private static class PositiveIntegerSocketOption extends SocketOptionImpl<Integer> { - - public PositiveIntegerSocketOption(String name, int socketOption) { - super(name, Integer.class, socketOption); - } - - @Override - protected Integer validateAndConvertValueBeforeSet(FileDescriptor fd, Integer value) { - if (value < 1) { - throw new IllegalArgumentException(name + " value must be > 0"); - } - return value; - } - - @Override - protected Integer validateAndConvertValueAfterGet(FileDescriptor fd, Object value) { - if (!(value instanceof Integer)) { - throw new AssertionError("Unexpected value for option " + name + ": " + value); - } - int intValue = (Integer) value; - if (intValue < 1) { - throw new AssertionError("Unexpected value for option " + name + ": " + value); - } - return intValue; - } - } -} diff --git a/luni/src/main/java/java/nio/DatagramChannelImpl.java b/luni/src/main/java/java/nio/DatagramChannelImpl.java index 8a5dbb6..e736c40 100644 --- a/luni/src/main/java/java/nio/DatagramChannelImpl.java +++ b/luni/src/main/java/java/nio/DatagramChannelImpl.java @@ -32,14 +32,10 @@ import java.net.NetworkInterface; import java.net.PlainDatagramSocketImpl; import java.net.SocketAddress; import java.net.SocketException; -import java.net.SocketOption; -import java.net.StandardSocketOptions; -import java.nio.channels.AlreadyBoundException; import java.nio.channels.AlreadyConnectedException; import java.nio.channels.ClosedChannelException; import java.nio.channels.DatagramChannel; import java.nio.channels.IllegalBlockingModeException; -import java.nio.channels.MembershipKey; import java.nio.channels.NotYetConnectedException; import java.nio.channels.spi.SelectorProvider; import java.nio.channels.UnresolvedAddressException; @@ -79,9 +75,6 @@ class DatagramChannelImpl extends DatagramChannel implements FileDescriptorChann private final Object readLock = new Object(); private final Object writeLock = new Object(); - // A helper to manage multicast group membership. Created as required. - private MulticastMembershipHandler multicastMembershipHandler; - /* * Constructor */ @@ -112,29 +105,6 @@ class DatagramChannelImpl extends DatagramChannel implements FileDescriptorChann return socket; } - /** @hide Until ready for a public API change */ - @Override - synchronized public DatagramChannel bind(SocketAddress local) throws IOException { - checkOpen(); - if (isBound) { - throw new AlreadyBoundException(); - } - - if (local == null) { - local = new InetSocketAddress(Inet4Address.ANY, 0); - } else if (!(local instanceof InetSocketAddress)) { - throw new UnsupportedAddressTypeException(); - } - - InetSocketAddress localAddress = (InetSocketAddress) local; - if (localAddress.isUnresolved()) { - throw new UnresolvedAddressException(); - } - IoBridge.bind(fd, localAddress.getAddress(), localAddress.getPort()); - onBind(true /* updateSocketState */); - return this; - } - /** * Initialise the isBound, localAddress and localPort state from the file descriptor. Used when * some or all of the bound state has been left to the OS to decide, or when the Socket handled @@ -162,34 +132,6 @@ class DatagramChannelImpl extends DatagramChannel implements FileDescriptorChann /** @hide Until ready for a public API change */ @Override - synchronized public SocketAddress getLocalAddress() throws IOException { - checkOpen(); - return isBound ? new InetSocketAddress(localAddress, localPort) : null; - } - - /** @hide Until ready for a public API change */ - @Override - public <T> T getOption(SocketOption<T> option) throws IOException { - return NioUtils.getSocketOption( - this, StandardSocketOptions.DATAGRAM_SOCKET_OPTIONS, option); - } - - /** @hide Until ready for a public API change */ - @Override - public <T> DatagramChannel setOption(SocketOption<T> option, T value) throws IOException { - checkOpen(); - NioUtils.setSocketOption( - this, StandardSocketOptions.DATAGRAM_SOCKET_OPTIONS, option, value); - return this; - } - - /** @hide Until ready for a public API change */ - @Override - public Set<SocketOption<?>> supportedOptions() { - return StandardSocketOptions.DATAGRAM_SOCKET_OPTIONS; - } - - @Override synchronized public boolean isConnected() { return connected; } @@ -524,7 +466,6 @@ class DatagramChannelImpl extends DatagramChannel implements FileDescriptorChann // A closed channel is not connected. onDisconnect(true /* updateSocketState */); IoBridge.closeAndSignalBlockedThreads(fd); - multicastMembershipHandler = null; if (socket != null && !socket.isClosed()) { socket.onClose(); @@ -570,52 +511,6 @@ class DatagramChannelImpl extends DatagramChannel implements FileDescriptorChann return fd; } - @Override - synchronized public MembershipKey join(InetAddress groupAddress, - NetworkInterface networkInterface) throws IOException { - - checkOpen(); - ensureMembershipHandlerExists(); - return multicastMembershipHandler.addAnySourceMembership(networkInterface, groupAddress); - } - - @Override - synchronized public MembershipKey join( - InetAddress groupAddress, NetworkInterface networkInterface, InetAddress sourceAddress) - throws IOException { - checkOpen(); - ensureMembershipHandlerExists(); - return multicastMembershipHandler.addSourceSpecificMembership( - networkInterface, groupAddress, sourceAddress); - } - - synchronized void multicastDrop(MembershipKeyImpl membershipKey) { - ensureMembershipHandlerExists(); - multicastMembershipHandler.dropMembership(membershipKey); - } - - synchronized void multicastBlock(MembershipKeyImpl membershipKey, InetAddress sourceAddress) - throws SocketException { - - ensureMembershipHandlerExists(); - multicastMembershipHandler.block(membershipKey, sourceAddress); - } - - synchronized void multicastUnblock(MembershipKeyImpl membershipKey, InetAddress sourceAddress) { - ensureMembershipHandlerExists(); - multicastMembershipHandler.unblock(membershipKey, sourceAddress); - } - - /** - * Creates the {@code multicastMembershipHandler} if one doesn't already exist. Callers must - * handle synchronization. - */ - private void ensureMembershipHandlerExists() { - if (multicastMembershipHandler == null) { - multicastMembershipHandler = new MulticastMembershipHandler(this); - } - } - /* * The adapter class of DatagramSocket */ diff --git a/luni/src/main/java/java/nio/MembershipKeyImpl.java b/luni/src/main/java/java/nio/MembershipKeyImpl.java deleted file mode 100644 index 3d7e957..0000000 --- a/luni/src/main/java/java/nio/MembershipKeyImpl.java +++ /dev/null @@ -1,106 +0,0 @@ -/* - * Copyright (C) 2014 The Android Open Source Project - * - * Licensed under the Apache License, Version 2.0 (the "License"); - * you may not use this file except in compliance with the License. - * You may obtain a copy of the License at - * - * http://www.apache.org/licenses/LICENSE-2.0 - * - * Unless required by applicable law or agreed to in writing, software - * distributed under the License is distributed on an "AS IS" BASIS, - * WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied. - * See the License for the specific language governing permissions and - * limitations under the License. - */ - -package java.nio; - -import java.io.IOException; -import java.net.InetAddress; -import java.net.NetworkInterface; -import java.nio.channels.MembershipKey; -import java.nio.channels.MulticastChannel; - -/** - * An implementation of {@link MembershipKey}. - * - * To keep this class simple and keep all mutation operations in one place and easily synchronized, - * most socket logic is held in {@link java.nio.DatagramChannelImpl}. - */ -final class MembershipKeyImpl extends MembershipKey { - - private final DatagramChannelImpl channel; - private final InetAddress groupAddress; - private final NetworkInterface networkInterface; - private final InetAddress sourceAddress; - private volatile boolean isValid; - - public MembershipKeyImpl(DatagramChannelImpl channel, NetworkInterface networkInterface, - InetAddress groupAddress, InetAddress sourceAddress) { - - this.channel = channel; - this.networkInterface = networkInterface; - this.groupAddress = groupAddress; - this.sourceAddress = sourceAddress; - this.isValid = true; - } - - @Override - public boolean isValid() { - // invalidate() is called if the key is dropped, but for simplicity it is not - // invalidated when the channel is closed. Therefore, the channel must also be checked to see - // if it is still open. - return isValid && channel.isOpen(); - } - - void invalidate() { - this.isValid = false; - } - - @Override - public void drop() { - channel.multicastDrop(this); - } - - @Override - public MembershipKey block(InetAddress source) throws IOException { - channel.multicastBlock(this, source); - return this; - } - - @Override - synchronized public MembershipKey unblock(InetAddress source) { - channel.multicastUnblock(this, source); - return this; - } - - @Override - public MulticastChannel channel() { - return channel; - } - - @Override - public InetAddress group() { - return groupAddress; - } - - @Override - public NetworkInterface networkInterface() { - return networkInterface; - } - - @Override - public InetAddress sourceAddress() { - return sourceAddress; - } - - @Override - public String toString() { - return "MembershipKeyImpl{" + - "groupAddress=" + groupAddress + - ", networkInterface=" + networkInterface + - ", sourceAddress=" + sourceAddress + - '}'; - } -} diff --git a/luni/src/main/java/java/nio/MulticastMembershipHandler.java b/luni/src/main/java/java/nio/MulticastMembershipHandler.java deleted file mode 100644 index 2fe8130..0000000 --- a/luni/src/main/java/java/nio/MulticastMembershipHandler.java +++ /dev/null @@ -1,495 +0,0 @@ -package java.nio; - -import android.system.StructGroupReq; -import android.system.StructGroupSourceReq; -import java.net.InetAddress; -import java.net.NetworkInterface; -import java.net.SocketException; -import java.nio.channels.MembershipKey; -import java.util.HashMap; -import java.util.HashSet; -import java.util.Map; -import java.util.Set; -import libcore.io.IoBridge; - -/** - * A helper class for {@link DatagramChannelImpl} that keeps track of multicast group - * memberships. This class is not threadsafe, and relies on the DatagramChannelImpl to synchronize. - * - * <p>See <a href="http://tools.ietf.org/html/rfc3678">RFC 3678</a> for context and terminology. - */ -final class MulticastMembershipHandler { - - private final DatagramChannelImpl channel; - private final Map<Id, Membership> memberships = new HashMap<Id, Membership>(); - - MulticastMembershipHandler(DatagramChannelImpl channel) { - this.channel = channel; - } - - /** - * The implementation for - * {@link java.nio.channels.MulticastChannel#join(InetAddress, NetworkInterface)}. - */ - public MembershipKeyImpl addAnySourceMembership( - NetworkInterface networkInterface, InetAddress groupAddress) throws SocketException { - - validateMulticastGroupArgs(groupAddress, networkInterface); - assertChannelOpen(); - - Id id = new Id(networkInterface, groupAddress); - Membership membership = memberships.get(id); - if (membership != null) { - return membership.getAnySourceMembershipKey(); - } - - // No existing membership found. Attempt to join. - StructGroupReq groupReq = makeGroupReq(groupAddress, networkInterface); - IoBridge.setSocketOption(channel.getFD(), IoBridge.JAVA_MCAST_JOIN_GROUP, groupReq); - - // Record the membership and return the key. - membership = Membership.createAnySource(channel, networkInterface, groupAddress); - memberships.put(id, membership); - return membership.getAnySourceMembershipKey(); - } - - /** - * The implementation for - * {@link java.nio.channels.MulticastChannel#join(InetAddress, NetworkInterface, InetAddress)}. - */ - public MembershipKeyImpl addSourceSpecificMembership( - NetworkInterface networkInterface, InetAddress groupAddress, InetAddress sourceAddress) - throws SocketException { - - validateMulticastGroupArgs(groupAddress, networkInterface); - validateSourceAddress(sourceAddress); - validateAddressProtocolTheSame(groupAddress, sourceAddress); - assertChannelOpen(); - - Id id = new Id(networkInterface, groupAddress); - Membership membership = memberships.get(id); - if (membership != null) { - MembershipKeyImpl existingMembershipKey = - membership.getSourceSpecificMembershipKey(sourceAddress); - if (existingMembershipKey != null) { - return existingMembershipKey; - } - } - - // No existing membership found. Attempt to join. - IoBridge.setSocketOption(channel.getFD(), IoBridge.JAVA_MCAST_JOIN_SOURCE_GROUP, - makeGroupSourceReq(groupAddress, networkInterface, sourceAddress)); - - if (membership == null) { - // Record the membership and return the key. - membership = Membership.createSourceSpecific( - channel, networkInterface, groupAddress, sourceAddress); - memberships.put(id, membership); - return membership.getSourceSpecificMembershipKey(sourceAddress); - } else { - // Add a new source to the existing membership. - return membership.addSource(sourceAddress); - } - } - - /** - * The implementation for {@link MembershipKey#drop()}. - */ - public void dropMembership(MembershipKeyImpl membershipKey) { - // For compatibility with the RI, this is one case where the membershipKey can no longer be - // valid. - if (!membershipKey.isValid()) { - return; - } - if (membershipKey.channel() != this.channel) { - throw new AssertionError("Bad membership key"); - } - assertChannelOpen(); - - Id id = createId(membershipKey); - Membership membership = memberships.get(id); - if (membership == null) { - throw new AssertionError("Bad membership key" + membershipKey); - } - - if (!membership.isSourceSpecific()) { - try { - StructGroupReq groupReq = - makeGroupReq(membershipKey.group(), membershipKey.networkInterface()); - IoBridge.setSocketOption(channel.getFD(), IoBridge.JAVA_MCAST_LEAVE_GROUP, groupReq); - } catch (SocketException e) { - // TODO: Obtain opinion on how to report this, throw this or if it is safe to ignore. - throw new IllegalStateException(e); - } - memberships.remove(id); - } else { - StructGroupSourceReq groupSourceReq = makeGroupSourceReq(membershipKey.group(), - membershipKey.networkInterface(), membershipKey.sourceAddress()); - - try { - IoBridge.setSocketOption( - channel.getFD(), IoBridge.JAVA_MCAST_LEAVE_SOURCE_GROUP, - groupSourceReq); - } catch (SocketException e) { - // TODO: Obtain opinion on how to report this, throw this or if it is safe to ignore. - throw new IllegalStateException(e); - } - - boolean isLast = membership.removeSource(membershipKey.sourceAddress()); - if (isLast) { - memberships.remove(id); - } - } - membershipKey.invalidate(); - } - - /** - * The implementation for {@link MembershipKey#block(java.net.InetAddress)}. - */ - public void block(MembershipKeyImpl membershipKey, InetAddress sourceAddress) - throws SocketException { - validateMembershipKey(membershipKey); - validateSourceAddress(sourceAddress); - validateAddressProtocolTheSame(membershipKey.group(), sourceAddress); - assertChannelOpen(); - - Membership membership = getMembershipForKey(membershipKey); - if (membership == null) { - throw new AssertionError("Bad membership key" + membershipKey); - } - - if (membership.isBlocked(sourceAddress)) { - return; - } - - IoBridge.setSocketOption(channel.getFD(), IoBridge.JAVA_MCAST_BLOCK_SOURCE, - makeGroupSourceReq( - membershipKey.group(), membershipKey.networkInterface(), sourceAddress)); - - membership.block(sourceAddress); - } - - /** - * The implementation for {@link MembershipKey#unblock(java.net.InetAddress)}. - */ - public void unblock(MembershipKeyImpl membershipKey, InetAddress sourceAddress) { - validateMembershipKey(membershipKey); - validateSourceAddress(sourceAddress); - validateAddressProtocolTheSame(membershipKey.group(), sourceAddress); - assertChannelOpen(); - - Membership membership = getMembershipForKey(membershipKey); - if (membership == null) { - throw new AssertionError("Bad membership key" + membershipKey); - } - - if (!membership.isBlocked(sourceAddress)) { - throw new IllegalStateException( - "sourceAddress " + sourceAddress + " is not blocked for " + membership.debugId()); - } - - try { - IoBridge.setSocketOption(channel.getFD(), IoBridge.JAVA_MCAST_UNBLOCK_SOURCE, - makeGroupSourceReq(membershipKey.group(), membershipKey.networkInterface(), - sourceAddress)); - } catch (SocketException e) { - throw new IllegalStateException(e); - } - - membership.unblock(sourceAddress); - } - - private Membership getMembershipForKey(MembershipKey membershipKey) { - Id id = createId(membershipKey); - Membership membership = memberships.get(id); - if (membership == null) { - throw new AssertionError("No membership found for id " + id); - } - return membership; - } - - private void assertChannelOpen() { - if (!channel.isOpen()) { - throw new AssertionError("Channel is closed"); - } - } - - private void validateMembershipKey(MembershipKeyImpl membershipKey) { - if (membershipKey.channel() != this.channel) { - throw new AssertionError("Invalid or bad membership key"); - } - if (!membershipKey.isValid()) { - throw new IllegalStateException("Membership key is no longer valid: " + membershipKey); - } - } - - private static Id createId(MembershipKey membershipKey) { - return new Id(membershipKey.networkInterface(), membershipKey.group()); - } - - private static void validateSourceAddress(InetAddress sourceAddress) { - if (sourceAddress.isAnyLocalAddress()) { - throw new IllegalArgumentException( - "sourceAddress must not be a wildcard address, is " + sourceAddress); - } - if (sourceAddress.isMulticastAddress()) { - throw new IllegalArgumentException( - "sourceAddress must be a unicast address, is " + sourceAddress); - } - } - - private static void validateMulticastGroupArgs( - InetAddress groupAddress, NetworkInterface networkInterface) throws SocketException { - - if (groupAddress == null) { - // RI throws NullPointerException. - throw new NullPointerException("groupAddress == null"); - } - if (networkInterface == null) { - // RI throws NullPointerException. - throw new NullPointerException("networkInterface == null"); - } - if (!networkInterface.isLoopback() && !networkInterface.supportsMulticast()) { - throw new IllegalArgumentException( - "networkInterface " + networkInterface + " does not support multicast"); - } - if (!groupAddress.isMulticastAddress()) { - throw new IllegalArgumentException("Not a multicast group: " + groupAddress); - } - } - - private static void validateAddressProtocolTheSame( - InetAddress groupAddress, InetAddress sourceAddress) { - - if (groupAddress.getClass() != sourceAddress.getClass()) { - throw new IllegalArgumentException("Mixed address types not permitted: groupAddress: " + - groupAddress + ", sourceAddress: " + sourceAddress); - } - } - - private static StructGroupSourceReq makeGroupSourceReq( - InetAddress gsr_group, NetworkInterface networkInterface, InetAddress gsr_source) { - int gsr_interface = (networkInterface != null) ? networkInterface.getIndex() : 0; - return new StructGroupSourceReq(gsr_interface, gsr_group, gsr_source); - } - - private static StructGroupReq makeGroupReq(InetAddress gr_group, - NetworkInterface networkInterface) { - int gr_interface = (networkInterface != null) ? networkInterface.getIndex() : 0; - return new StructGroupReq(gr_interface, gr_group); - } - - /** - * Membership information associated with an {@link Id}. A membership can be one of two types: - * "source-specific" and "any-source". The two types a mutually exclusive for a given Id. - */ - static final class Membership { - - private final DatagramChannelImpl channel; - private final InetAddress groupAddress; - private final NetworkInterface networkInterface; - - // Any-source membership key. Mutually exclusive with sourceSpecificMembershipKeys. - private final MembershipKeyImpl anySourceMembershipKey; - // Blocked source addresses for any-source memberships. Assigned when required. - private Set<InetAddress> blockedSourceAddresses; - - // Source-specific membership keys. Mutually exclusive with anySourceMembershipKey. - private final Map<InetAddress, MembershipKeyImpl> sourceSpecificMembershipKeys; - - /** Use {@link #createSourceSpecific} or {@link #createAnySource} to construct. */ - private Membership( - DatagramChannelImpl channel, - InetAddress groupAddress, - NetworkInterface networkInterface, - MembershipKeyImpl anySourceMembershipKey, - Map<InetAddress, MembershipKeyImpl> sourceSpecificMembershipKeys) { - - this.channel = channel; - this.groupAddress = groupAddress; - this.networkInterface = networkInterface; - this.anySourceMembershipKey = anySourceMembershipKey; - this.sourceSpecificMembershipKeys = sourceSpecificMembershipKeys; - } - - /** Creates an any-source membership. */ - public static Membership createAnySource(DatagramChannelImpl channel, - NetworkInterface networkInterface, InetAddress groupAddress) { - - MembershipKeyImpl withoutSourceAddressKey = - new MembershipKeyImpl(channel, networkInterface, groupAddress, null /* sourceAddress */); - return new Membership( - channel, groupAddress, networkInterface, withoutSourceAddressKey, - null /* sourceSpecificMembershipKeys */); - } - - /** - * Creates a source-specific membership. See {@link #addSource} to add additional source - * addresses. - */ - public static Membership createSourceSpecific(DatagramChannelImpl channel, - NetworkInterface networkInterface, InetAddress groupAddress, InetAddress sourceAddress) { - - Map<InetAddress, MembershipKeyImpl> withSourceKeys = - new HashMap<InetAddress, MembershipKeyImpl>(); - Membership membership = new Membership( - channel, groupAddress, networkInterface, null /* anySourceMembershipKey */, - withSourceKeys); - membership.addSource(sourceAddress); - return membership; - } - - /** - * Adds a new source address filter to an existing membership, returning the associated - * {@link MembershipKeyImpl}. Throws an {@code IllegalStateException} if this is an - * any-source membership. - */ - public MembershipKeyImpl addSource(InetAddress sourceAddress) { - if (sourceSpecificMembershipKeys == null) { - throw new IllegalStateException( - "Can only add sources to source-specific memberships: " + debugId()); - } - - MembershipKeyImpl membershipKey = - new MembershipKeyImpl(channel, networkInterface, groupAddress, sourceAddress); - sourceSpecificMembershipKeys.put(sourceAddress, membershipKey); - return membershipKey; - } - - /** - * Removes the specified {@code sourceAddress} from the set of filters. Returns {@code true} if - * the set of filters is now empty. Throws an {@code IllegalStateException} if this is an - * any-source membership. - */ - public boolean removeSource(InetAddress sourceAddress) { - if (sourceSpecificMembershipKeys == null) { - throw new IllegalStateException( - "Can only remove sources from source-specific memberships: " + debugId()); - } - sourceSpecificMembershipKeys.remove(sourceAddress); - return sourceSpecificMembershipKeys.isEmpty(); - } - - /** - * Returns {@code true} if the membership source-specific, false if it is any-source. - */ - public boolean isSourceSpecific() { - return sourceSpecificMembershipKeys != null; - } - - /** - * Returns the {@link MembershipKeyImpl} for this membership. Throws an - * {@code IllegalStateException} if this is not an any-source membership. - */ - public MembershipKeyImpl getAnySourceMembershipKey() { - if (sourceSpecificMembershipKeys != null) { - throw new IllegalStateException( - "There an existing source-specific membership for " + debugId()); - } - return anySourceMembershipKey; - } - - /** - * Returns the {@link MembershipKeyImpl} for the specified {@code sourceAddress}. Throws an - * {@code IllegalStateException} if this is not a source-specific membership. - */ - public MembershipKeyImpl getSourceSpecificMembershipKey(InetAddress sourceAddress) { - if (anySourceMembershipKey != null) { - throw new IllegalStateException("There an existing any-source membership for " + debugId()); - } - return sourceSpecificMembershipKeys.get(sourceAddress); - } - - /** - * Returns {@code true} if there is an existing block for the specified address. Throws an - * {@code IllegalStateException} if this is not an any-source membership. - */ - public boolean isBlocked(InetAddress sourceAddress) { - if (anySourceMembershipKey == null) { - throw new IllegalStateException( - "block()/unblock() are only applicable for any-source memberships: " + debugId()); - } - return blockedSourceAddresses != null && blockedSourceAddresses.contains(sourceAddress); - } - - /** - * Adds a blocked address to this membership. Throws an {@code IllegalStateException} if - * the address is already blocked. Throws an {@code IllegalStateException} if this is not an - * any-source membership. - */ - public void block(InetAddress sourceAddress) { - if (anySourceMembershipKey == null) { - throw new IllegalStateException( - "block() is not supported for source-specific group memberships: " + debugId()); - } - if (blockedSourceAddresses == null) { - blockedSourceAddresses = new HashSet<InetAddress>(); - } - if (!blockedSourceAddresses.add(sourceAddress)) { - throw new IllegalStateException( - "Could not block " + sourceAddress + ": it was already blocked for " + debugId()); - } - } - - /** - * Removes a blocked address from this membership. Throws an {@code IllegalStateException} if - * the address is not blocked. Throws an {@code IllegalStateException} if this is not an - * any-source membership. - */ - public void unblock(InetAddress sourceAddress) { - if (anySourceMembershipKey == null) { - throw new IllegalStateException( - "unblock() is not supported for source-specific group memberships: " + debugId()); - } - if (blockedSourceAddresses == null || !blockedSourceAddresses.remove(sourceAddress)) { - throw new IllegalStateException( - "Could not unblock " + sourceAddress + ": it was not blocked for " + debugId()); - } - } - - public String debugId() { - return "<" + networkInterface + ":" + groupAddress + ">"; - } - - } - - /** An identifier for a multicast group membership, independent of membership type. */ - private static final class Id { - - private final InetAddress groupAddress; - private final NetworkInterface networkInterface; - - public Id(NetworkInterface networkInterface, InetAddress groupAddress) { - this.groupAddress = groupAddress; - this.networkInterface = networkInterface; - } - - @Override - public boolean equals(Object o) { - if (this == o) { - return true; - } - if (!(o instanceof Id)) { - return false; - } - - Id id = (Id) o; - - if (!groupAddress.equals(id.groupAddress)) { - return false; - } - if (!networkInterface.equals(id.networkInterface)) { - return false; - } - - return true; - } - - @Override - public int hashCode() { - int result = groupAddress.hashCode(); - result = 31 * result + networkInterface.hashCode(); - return result; - } - } -} diff --git a/luni/src/main/java/java/nio/NioUtils.java b/luni/src/main/java/java/nio/NioUtils.java index 51adddb..f2a0b10 100644 --- a/luni/src/main/java/java/nio/NioUtils.java +++ b/luni/src/main/java/java/nio/NioUtils.java @@ -19,8 +19,6 @@ package java.nio; import java.io.Closeable; import java.io.FileDescriptor; import java.io.IOException; -import java.net.SocketOption; -import java.net.StandardSocketOptions; import java.nio.channels.ClosedChannelException; import java.nio.channels.FileChannel; import java.util.Set; @@ -68,66 +66,4 @@ public final class NioUtils { public static int unsafeArrayOffset(ByteBuffer b) { return ((ByteArrayBuffer) b).arrayOffset; } - - /** - * Sets the supplied option on the channel to have the value if option is a member of - * allowedOptions. - * - * @throws IOException - * if the value could not be set due to IO errors. - * @throws IllegalArgumentException - * if the socket option or the value is invalid. - * @throws UnsupportedOperationException - * if the option is not a member of allowedOptions. - * @throws ClosedChannelException - * if the channel is closed - */ - public static <T> void setSocketOption( - FileDescriptorChannel channel, Set<SocketOption<?>> allowedOptions, - SocketOption<T> option, T value) - throws IOException { - - if (!(option instanceof StandardSocketOptions.SocketOptionImpl)) { - throw new IllegalArgumentException("SocketOption must come from StandardSocketOptions"); - } - if (!allowedOptions.contains(option)) { - throw new UnsupportedOperationException( - option + " is not supported for this type of socket"); - } - if (!channel.getFD().valid()) { - throw new ClosedChannelException(); - } - ((StandardSocketOptions.SocketOptionImpl<T>) option).setValue(channel.getFD(), value); - } - - /** - * Gets the supplied option from the channel if option is a member of allowedOptions. - * - * @throws IOException - * if the value could not be read due to IO errors. - * @throws IllegalArgumentException - * if the socket option is invalid. - * @throws UnsupportedOperationException - * if the option is not a member of allowedOptions. - * @throws ClosedChannelException - * if the channel is closed - */ - public static <T> T getSocketOption( - FileDescriptorChannel channel, Set<SocketOption<?>> allowedOptions, - SocketOption<T> option) - throws IOException { - - if (!(option instanceof StandardSocketOptions.SocketOptionImpl)) { - throw new IllegalArgumentException("SocketOption must come from StandardSocketOptions"); - } - if (!allowedOptions.contains(option)) { - throw new UnsupportedOperationException( - option + " is not supported for this type of socket"); - } - if (!channel.getFD().valid()) { - throw new ClosedChannelException(); - } - return ((StandardSocketOptions.SocketOptionImpl<T>) option).getValue(channel.getFD()); - } - } diff --git a/luni/src/main/java/java/nio/ServerSocketChannelImpl.java b/luni/src/main/java/java/nio/ServerSocketChannelImpl.java index d2cbf36..7185c32 100644 --- a/luni/src/main/java/java/nio/ServerSocketChannelImpl.java +++ b/luni/src/main/java/java/nio/ServerSocketChannelImpl.java @@ -24,10 +24,7 @@ import java.net.InetSocketAddress; import java.net.ServerSocket; import java.net.Socket; import java.net.SocketAddress; -import java.net.SocketOption; import java.net.SocketTimeoutException; -import java.net.StandardSocketOptions; -import java.nio.channels.AlreadyBoundException; import java.nio.channels.ClosedChannelException; import java.nio.channels.IllegalBlockingModeException; import java.nio.channels.NotYetBoundException; @@ -60,56 +57,6 @@ final class ServerSocketChannelImpl extends ServerSocketChannel implements FileD /** @hide Until ready for a public API change */ @Override - public final ServerSocketChannel bind(SocketAddress localAddr, int backlog) throws IOException { - if (!isOpen()) { - throw new ClosedChannelException(); - } - if (socket.isBound()) { - throw new AlreadyBoundException(); - } - if (localAddr != null) { - if (!(localAddr instanceof InetSocketAddress)) { - throw new UnsupportedAddressTypeException(); - } - InetSocketAddress localInetAddress = (InetSocketAddress) localAddr; - if (localInetAddress.isUnresolved()) { - throw new UnresolvedAddressException(); - } - } - - socket.bind(localAddr, backlog); - return this; - } - - /** @hide Until ready for a public API change */ - @Override - public SocketAddress getLocalAddress() throws IOException { - if (!isOpen()) { - throw new ClosedChannelException(); - } - return socket.getLocalSocketAddress(); - } - - /** @hide Until ready for a public API change */ - @Override - public <T> T getOption(SocketOption<T> option) throws IOException { - return NioUtils.getSocketOption(this, StandardSocketOptions.SERVER_SOCKET_OPTIONS, option); - } - - /** @hide Until ready for a public API change */ - @Override - public <T> ServerSocketChannel setOption(SocketOption<T> option, T value) throws IOException { - NioUtils.setSocketOption(this, StandardSocketOptions.SERVER_SOCKET_OPTIONS, option, value); - return this; - } - - /** @hide Until ready for a public API change */ - @Override - public Set<SocketOption<?>> supportedOptions() { - return StandardSocketOptions.SERVER_SOCKET_OPTIONS; - } - - @Override public SocketChannel accept() throws IOException { if (!isOpen()) { throw new ClosedChannelException(); diff --git a/luni/src/main/java/java/nio/SocketChannelImpl.java b/luni/src/main/java/java/nio/SocketChannelImpl.java index 7c3cd78..d5cb716 100644 --- a/luni/src/main/java/java/nio/SocketChannelImpl.java +++ b/luni/src/main/java/java/nio/SocketChannelImpl.java @@ -32,10 +32,7 @@ import java.net.PlainSocketImpl; import java.net.Socket; import java.net.SocketAddress; import java.net.SocketException; -import java.net.SocketOption; import java.net.SocketUtils; -import java.net.StandardSocketOptions; -import java.nio.channels.AlreadyBoundException; import java.nio.channels.AlreadyConnectedException; import java.nio.channels.ClosedChannelException; import java.nio.channels.ConnectionPendingException; @@ -139,31 +136,6 @@ class SocketChannelImpl extends SocketChannel implements FileDescriptorChannel { return socket; } - /** @hide Until ready for a public API change */ - @Override - synchronized public final SocketChannel bind(SocketAddress local) throws IOException { - if (!isOpen()) { - throw new ClosedChannelException(); - } - if (isBound) { - throw new AlreadyBoundException(); - } - - if (local == null) { - local = new InetSocketAddress(Inet4Address.ANY, 0); - } else if (!(local instanceof InetSocketAddress)) { - throw new UnsupportedAddressTypeException(); - } - - InetSocketAddress localAddress = (InetSocketAddress) local; - if (localAddress.isUnresolved()) { - throw new UnresolvedAddressException(); - } - IoBridge.bind(fd, localAddress.getAddress(), localAddress.getPort()); - onBind(true /* updateSocketState */); - return this; - } - /** * Initialise the isBound, localAddress and localPort state from the file descriptor. Used when * some or all of the bound state has been left to the OS to decide, or when the Socket handled @@ -189,34 +161,6 @@ class SocketChannelImpl extends SocketChannel implements FileDescriptorChannel { } } - /** @hide Until ready for a public API change */ - @Override - synchronized public SocketAddress getLocalAddress() throws IOException { - if (!isOpen()) { - throw new ClosedChannelException(); - } - return isBound ? new InetSocketAddress(localAddress, localPort) : null; - } - - /** @hide Until ready for a public API change */ - @Override - public <T> T getOption(SocketOption<T> option) throws IOException { - return NioUtils.getSocketOption(this, StandardSocketOptions.SOCKET_OPTIONS, option); - } - - /** @hide Until ready for a public API change */ - @Override - public <T> SocketChannel setOption(SocketOption<T> option, T value) throws IOException { - NioUtils.setSocketOption(this, StandardSocketOptions.SOCKET_OPTIONS, option, value); - return this; - } - - /** @hide Until ready for a public API change */ - @Override - public Set<SocketOption<?>> supportedOptions() { - return StandardSocketOptions.SOCKET_OPTIONS; - } - @Override synchronized public boolean isConnected() { return status == SOCKET_STATUS_CONNECTED; diff --git a/luni/src/main/java/java/nio/channels/AlreadyBoundException.java b/luni/src/main/java/java/nio/channels/AlreadyBoundException.java deleted file mode 100644 index 0a35fc3..0000000 --- a/luni/src/main/java/java/nio/channels/AlreadyBoundException.java +++ /dev/null @@ -1,31 +0,0 @@ -/* - * Copyright (C) 2014 The Android Open Source Project - * - * Licensed under the Apache License, Version 2.0 (the "License"); - * you may not use this file except in compliance with the License. - * You may obtain a copy of the License at - * - * http://www.apache.org/licenses/LICENSE-2.0 - * - * Unless required by applicable law or agreed to in writing, software - * distributed under the License is distributed on an "AS IS" BASIS, - * WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied. - * See the License for the specific language governing permissions and - * limitations under the License. - */ - -package java.nio.channels; - -/** - * An {@code AlreadyBoundException} is thrown when an attempt is made to bind a NetworkChannel that - * is already bound. - * - * @hide Until ready for a public API change - */ -public class AlreadyBoundException extends IllegalStateException { - - private static final long serialVersionUID = 6796072983322737592L; - - public AlreadyBoundException() { - } -} diff --git a/luni/src/main/java/java/nio/channels/DatagramChannel.java b/luni/src/main/java/java/nio/channels/DatagramChannel.java index 3a5d1cc..2cff7f0 100644 --- a/luni/src/main/java/java/nio/channels/DatagramChannel.java +++ b/luni/src/main/java/java/nio/channels/DatagramChannel.java @@ -22,7 +22,6 @@ import java.net.DatagramSocket; import java.net.InetAddress; import java.net.NetworkInterface; import java.net.SocketAddress; -import java.net.SocketOption; import java.nio.ByteBuffer; import java.nio.channels.spi.AbstractSelectableChannel; import java.nio.channels.spi.SelectorProvider; @@ -44,7 +43,7 @@ import java.util.Set; * same time. */ public abstract class DatagramChannel extends AbstractSelectableChannel - implements ByteChannel, ScatteringByteChannel, GatheringByteChannel, MulticastChannel { + implements ByteChannel, ScatteringByteChannel, GatheringByteChannel { /** * Constructs a new {@code DatagramChannel}. @@ -92,64 +91,6 @@ public abstract class DatagramChannel extends AbstractSelectableChannel */ public abstract DatagramSocket socket(); - /** @hide Until ready for a public API change */ - @Override - public DatagramChannel bind(SocketAddress local) throws IOException { - // This method was added for interoperability with Java 7, where it is abstract. It is - // concrete here to avoid breaking existing Android applications that extend this class. - throw new UnsupportedOperationException("Subclasses must override this method"); - } - - /** @hide Until ready for a public API change */ - @Override - public SocketAddress getLocalAddress() throws IOException { - // This method was added for interoperability with Java 7, where it is abstract. It is - // concrete here to avoid breaking existing Android applications that extend this class. - throw new UnsupportedOperationException("Subclasses must override this method"); - } - - /** @hide Until ready for a public API change */ - @Override - public <T> T getOption(SocketOption<T> option) throws IOException { - // This method was added for interoperability with Java 7, where it is abstract. It is - // concrete here to avoid breaking existing Android applications that extend this class. - throw new UnsupportedOperationException("Subclasses must override this method"); - } - - /** @hide Until ready for a public API change */ - @Override - public <T> DatagramChannel setOption(SocketOption<T> option, T value) throws IOException { - // This method was added for interoperability with Java 7, where it is abstract. It is - // concrete here to avoid breaking existing Android applications that extend this class. - throw new UnsupportedOperationException("Subclasses must override this method"); - } - - /** @hide Until ready for a public API change */ - @Override - public Set<SocketOption<?>> supportedOptions() { - // This method was added for interoperability with Java 7, where it is abstract. It is - // concrete here to avoid breaking existing Android applications that extend this class. - throw new UnsupportedOperationException("Subclasses must override this method"); - } - - /** @hide Until ready for a public API change */ - @Override - public MembershipKey join(InetAddress groupAddress, NetworkInterface networkInterface) - throws IOException { - // This method was added for interoperability with Java 7, where it is abstract. It is - // concrete here to avoid breaking existing Android applications that extend this class. - throw new UnsupportedOperationException("Subclasses must override this method"); - } - - /** @hide Until ready for a public API change */ - @Override - public MembershipKey join(InetAddress groupAddress, NetworkInterface networkInterface, - InetAddress sourceAddress) throws IOException { - // This method was added for interoperability with Java 7, where it is abstract. It is - // concrete here to avoid breaking existing Android applications that extend this class. - throw new UnsupportedOperationException("Subclasses must override this method"); - } - /** * Returns whether this channel's socket is connected or not. * diff --git a/luni/src/main/java/java/nio/channels/FileChannel.java b/luni/src/main/java/java/nio/channels/FileChannel.java index e5f2862..d6c140b 100644 --- a/luni/src/main/java/java/nio/channels/FileChannel.java +++ b/luni/src/main/java/java/nio/channels/FileChannel.java @@ -76,9 +76,8 @@ import java.nio.channels.spi.AbstractInterruptibleChannel; * stream and vice versa; this includes modifications to the file position, * content, size, etc. */ -// TODO: Remove ByteChannel when SeekableByteChannel is unhidden. public abstract class FileChannel extends AbstractInterruptibleChannel - implements GatheringByteChannel, ScatteringByteChannel, ByteChannel, SeekableByteChannel { + implements ByteChannel, GatheringByteChannel, ScatteringByteChannel { /** * {@code MapMode} defines file mapping mode constants. @@ -282,21 +281,65 @@ public abstract class FileChannel extends AbstractInterruptibleChannel long position, long size) throws IOException; /** - * {@inheritDoc} + * Returns the current position as a positive integer number of bytes from + * the start of the file. + * + * @throws ClosedChannelException + * if this channel is closed. + * @throws IOException + * if another I/O error occurs. */ - @Override public abstract long position() throws IOException; /** - * {@inheritDoc} + * Sets the file position pointer to a new value. + * <p> + * The argument is the number of bytes counted from the start of the file. + * The position cannot be set to a value that is negative. The new position + * can be set beyond the current file size. If set beyond the current file + * size, attempts to read will return end of file. Write operations will + * succeed but they will fill the bytes between the current end of file and + * the new position with the required number of (unspecified) byte values. + * + * @return this. + * @throws IllegalArgumentException + * if the new position is negative. + * @throws ClosedChannelException + * if this channel is closed. + * @throws IOException + * if another I/O error occurs. */ - @Override public abstract FileChannel position(long newPosition) throws IOException; /** - * {@inheritDoc} + * Reads bytes from this file channel into the given buffer. + * <p> + * The maximum number of bytes that will be read is the remaining number of + * bytes in the buffer when the method is invoked. The bytes will be copied + * into the buffer starting at the buffer's current position. + * <p> + * The call may block if other threads are also attempting to read from this + * channel. + * <p> + * Upon completion, the buffer's position is set to the end of the bytes + * that have been read. The buffer's limit is not changed. + * + * @param buffer + * the byte buffer to receive the bytes. + * @return the number of bytes actually read. + * @throws AsynchronousCloseException + * if another thread closes the channel during the read. + * @throws ClosedByInterruptException + * if another thread interrupts the calling thread during the + * read. + * @throws ClosedChannelException + * if this channel is closed. + * @throws IOException + * if another I/O error occurs, details are in the message. + * @throws NonReadableChannelException + * if the channel has not been opened in a mode that permits + * reading. */ - @Override public abstract int read(ByteBuffer buffer) throws IOException; /** @@ -411,9 +454,13 @@ public abstract class FileChannel extends AbstractInterruptibleChannel throws IOException; /** - * {@inheritDoc} + * Returns the size of the file underlying this channel in bytes. + * + * @throws ClosedChannelException + * if this channel is closed. + * @throws IOException + * if an I/O error occurs while getting the size of the file. */ - @Override public abstract long size() throws IOException; /** @@ -491,9 +538,25 @@ public abstract class FileChannel extends AbstractInterruptibleChannel WritableByteChannel target) throws IOException; /** - * {@inheritDoc} + * Truncates the file underlying this channel to a given size. Any bytes + * beyond the given size are removed from the file. If there are no bytes + * beyond the given size then the file contents are unmodified. + * <p> + * If the file position is currently greater than the given size, then it is + * set to the new size. + * + * @param size + * the maximum size of the underlying file. + * @throws IllegalArgumentException + * if the requested size is negative. + * @throws ClosedChannelException + * if this channel is closed. + * @throws NonWritableChannelException + * if the channel cannot be written to. + * @throws IOException + * if another I/O error occurs. + * @return this channel. */ - @Override public abstract FileChannel truncate(long size) throws IOException; /** @@ -554,9 +617,30 @@ public abstract class FileChannel extends AbstractInterruptibleChannel throws IOException; /** - * {@inheritDoc} + * Writes bytes from the given byte buffer to this file channel. + * <p> + * The bytes are written starting at the current file position, and after + * some number of bytes are written (up to the remaining number of bytes in + * the buffer) the file position is increased by the number of bytes + * actually written. + * + * @param src + * the byte buffer containing the bytes to be written. + * @return the number of bytes actually written. + * @throws NonWritableChannelException + * if the channel was not opened for writing. + * @throws ClosedChannelException + * if the channel was already closed. + * @throws AsynchronousCloseException + * if another thread closes the channel during the write. + * @throws ClosedByInterruptException + * if another thread interrupts the calling thread while this + * operation is in progress. The interrupt state of the calling + * thread is set and the channel is closed. + * @throws IOException + * if another I/O error occurs, details are in the message. + * @see java.nio.channels.WritableByteChannel#write(java.nio.ByteBuffer) */ - @Override public abstract int write(ByteBuffer src) throws IOException; /** diff --git a/luni/src/main/java/java/nio/channels/FileLock.java b/luni/src/main/java/java/nio/channels/FileLock.java index 037537c..5b26475 100644 --- a/luni/src/main/java/java/nio/channels/FileLock.java +++ b/luni/src/main/java/java/nio/channels/FileLock.java @@ -114,17 +114,6 @@ public abstract class FileLock implements AutoCloseable { } /** - * Returns the {@link Channel} that holds this lock. - * - * @since 1.7 - * @hide Until ready for an API update - */ - // TODO: unhiding, add to channel(): This method has been superseded by {@link #acquiredBy()}. - public Channel acquiredBy() { - return channel; - } - - /** * Returns the lock's starting position in the file. * * @return the lock position. diff --git a/luni/src/main/java/java/nio/channels/MembershipKey.java b/luni/src/main/java/java/nio/channels/MembershipKey.java deleted file mode 100644 index 18ff92d..0000000 --- a/luni/src/main/java/java/nio/channels/MembershipKey.java +++ /dev/null @@ -1,121 +0,0 @@ -/* - * Copyright (C) 2014 The Android Open Source Project - * - * Licensed under the Apache License, Version 2.0 (the "License"); - * you may not use this file except in compliance with the License. - * You may obtain a copy of the License at - * - * http://www.apache.org/licenses/LICENSE-2.0 - * - * Unless required by applicable law or agreed to in writing, software - * distributed under the License is distributed on an "AS IS" BASIS, - * WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied. - * See the License for the specific language governing permissions and - * limitations under the License. - */ - -package java.nio.channels; - -import java.io.IOException; -import java.net.InetAddress; -import java.net.NetworkInterface; - -/** - * A token produced as the result of joining a multicast group with - * {@link DatagramChannel#join(java.net.InetAddress, java.net.NetworkInterface)} or - * {@link DatagramChannel#join(java.net.InetAddress, java.net.NetworkInterface, - * java.net.InetAddress)}. - * - * <p>A multicast group membership can be source-specific or any-source. Source-specific memberships - * only allow datagrams from a single source address to be received. Any-source memberships - * initially allow datagrams from any source address to be received, but may have individual unicast - * IP addresses blocked via {@link #block(java.net.InetAddress)}. Any-source membership keys return - * {@code null} from {@link #sourceAddress()}. - * - * <p>See <a href="http://tools.ietf.org/html/rfc3678">RFC 3678: Socket Interface Extensions for - * Multicast Source Filters</a> for concepts and terminology associated with multicast membership. - * - * @since 1.7 - * @hide Until ready for a public API change - */ -public abstract class MembershipKey { - - protected MembershipKey() {} - - /** - * Returns {@code true} until the membership is dropped with {@link #drop()} or the associated - * channel is closed. - */ - public abstract boolean isValid(); - - /** - * Drops this membership from the multicast group, invalidating this key. - */ - public abstract void drop(); - - /** - * Blocks datagrams from the specified source address; after this call any datagrams received from - * the address will be discarded. Blocking an already-blocked source address has no effect. A - * blocked address can be unblocked by calling {@link #unblock(java.net.InetAddress)}. - * - * <p>The block may not take effect instantaneously: datagrams that are already buffered by the - * underlying OS may still be delivered. - * - * <p>There is an OS-level limit on the number of source addresses that can be block for a given - * {@code groupAddress}, {@code networkInterface} pair. This is typically 10. Attempts to add - * more than this result in a {@code SocketException}. - * - * <p>If this membership key is source-specific an {@link IllegalStateException} is thrown. - * - * @throws IllegalStateException - * if this membership key is no longer valid or is of the wrong type - * @throws IllegalArgumentException - * if the source address is not unicast address of the same type as the multicast group - * address supplied when the group was joined - * @throws IOException - * if an I/O error occurs. - */ - public abstract MembershipKey block(InetAddress source) throws IOException; - - /** - * Unblocks datagrams from the specified source address that were previously blocked with a call - * to {@link #block(java.net.InetAddress)}; after this call any datagrams received from the - * address will be received. Unblocking an address that is not currently blocked throws an - * {@code IllegalStateException}. - * - * <p>If this membership key is source-specific an {@link IllegalStateException} is thrown. - * - * @throws IllegalStateException - * if this membership key is no longer valid or is of the wrong type, or the address is - * not currently blocked - * @throws IllegalArgumentException - * if the source address is not unicast address of the same type as the multicast group - * address supplied when the group was joined - */ - public abstract MembershipKey unblock(InetAddress source); - - /** - * Returns the {@code MulticastChannel} associated with this key. Continues returning the value - * even when the key has been invalidated. - */ - public abstract MulticastChannel channel(); - - /** - * Returns the multicast group address associated with this key. Continues returning the value - * even when the key has been invalidated. - */ - public abstract InetAddress group(); - - /** - * Returns the network interface associated with this key. Continues returning the value - * even when the key has been invalidated. - */ - public abstract NetworkInterface networkInterface(); - - /** - * Returns the source address associated with this key if the membership is source-specific. - * Returns {@code null} if the membership is any-source. Continues returning the value - * even when the key has been invalidated. - */ - public abstract InetAddress sourceAddress(); -} diff --git a/luni/src/main/java/java/nio/channels/MulticastChannel.java b/luni/src/main/java/java/nio/channels/MulticastChannel.java deleted file mode 100644 index 41ef501..0000000 --- a/luni/src/main/java/java/nio/channels/MulticastChannel.java +++ /dev/null @@ -1,160 +0,0 @@ -/* - * Copyright (C) 2014 The Android Open Source Project - * - * Licensed under the Apache License, Version 2.0 (the "License"); - * you may not use this file except in compliance with the License. - * You may obtain a copy of the License at - * - * http://www.apache.org/licenses/LICENSE-2.0 - * - * Unless required by applicable law or agreed to in writing, software - * distributed under the License is distributed on an "AS IS" BASIS, - * WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied. - * See the License for the specific language governing permissions and - * limitations under the License. - */ - -package java.nio.channels; - -import java.io.IOException; -import java.net.InetAddress; -import java.net.NetworkInterface; - -/** - * A type of {@link NetworkChannel} that supports IP multicasting. IP multicasting allows for - * efficient routing of an IP datagram to multiple hosts. Hosts wishing to receive multicast - * datagrams join a multicast group identified by a multicast IP address. - * - * <p>Any datagram socket can be used to <em>send</em> to a multicast group: senders <em>do not</em> - * have to be a member of the group. - * - * <p>See <a href="http://www.ietf.org/rfc/rfc2236.txt">RFC 2236: Internet Group Management - * Protocol, Version 2</a> and <a href="http://www.ietf.org/rfc/rfc3376.txt">RFC 3376: Internet - * Group Management Protocol, Version 3</a> for network-level information regarding IPv4 group - * membership. See <a href="http://www.ietf.org/rfc/rfc2710.txt">RFC 2710: Multicast Listener - * Discovery (MLD) for IPv6</a> and <a href="http://www.ietf.org/rfc/rfc3810.txt">RFC 3810: - * Multicast Listener Discovery Version 2 (MLDv2) for IPv6</a> for equivalent IPv6 information. - * - * <p>See <a href="http://tools.ietf.org/html/rfc3678">RFC 3678: Socket Interface Extensions for - * Multicast Source Filters</a> for concepts and terminology associated with multicast membership. - * - * <p>IP multicast requires support from network infrastructure; networks may not support - * all features of IP multicast. - * - * <p>A channel can be restricted to send multicast datagrams through a specific - * {@link NetworkInterface} by using {@link #setOption(java.net.SocketOption, Object)} with - * {@link java.net.StandardSocketOptions#IP_MULTICAST_IF}. - * - * <p>A channel may or may not receive multicast datagrams sent from this host, determined by the - * {@link java.net.StandardSocketOptions#IP_MULTICAST_LOOP} option. - * - * <p>The time-to-live for multicast datagrams can be set using the - * {@link java.net.StandardSocketOptions#IP_MULTICAST_TTL} option. - * - * <p>Usually multicast channels should have {@link java.net.StandardSocketOptions#SO_REUSEADDR} - * set to {@code true} before binding to enable multiple sockets on this host to be members of - * the same multicast group. - * - * <p>Typically multicast channels are {@link NetworkChannel#bind bound} to a wildcard address - * such as "0.0.0.0" (IPv4) or "::" (IPv6). They may also be bound to a multicast group address. - * Binding to a multicast group address restricts datagrams received to only those sent to the - * multicast group. When the wildcard address is used the socket may join multiple groups and also - * receive non-multicast datagrams sent directly to the host. The port the channel is bound to is - * important: only datagrams sent to the group on that port will be received. - * - * <p>Having bound a channel, the group can be joined. Memberships are either "any-source" or - * "source-specific". The type of membership is determined by the variant of {@code join} that is - * used. See {@link #join(java.net.InetAddress, java.net.NetworkInterface)} and - * {@link #join(java.net.InetAddress, java.net.NetworkInterface, java.net.InetAddress)} for more - * information. - * - * @since 1.7 - * @hide Until ready for a public API change - */ -public interface MulticastChannel extends NetworkChannel { - - // @hide Until ready for a public API change - // /** - // * {@inheritDoc} - // * - // * If the channel is currently part of one or more multicast groups then the memberships are - // * dropped and any associated {@code MembershipKey} objects are invalidated. - // */ - void close() throws IOException; - - /** - * Creates an any-source membership to the {@code groupAddress} on the specified - * {@code networkInterface}. Returns a {@code MembershipKey} that can be used to modify or - * {@link MembershipKey#drop()} the membership. See {@link MembershipKey#block(InetAddress)} and - * {@link MembershipKey#unblock(InetAddress)} for methods to modify source-address - * filtering. - * - * <p>A channel may join several groups. Each membership is network interface-specific: an - * application must join the group for each applicable network interface to receive datagrams. - * - * <p>Any-source and source-specific memberships cannot be mixed for a group address on a given - * network interface. An {@code IllegalStateException} will be thrown if joins of different types - * are attempted for a given {@code groupAddress}, {@code networkInterface} pair. Joining a - * multicast group with the same arguments as an existing, valid membership returns the same - * {@code MembershipKey}. - * - * <p>There is an OS-level limit on the number of multicast groups a process can join. - * This is typically 20. Attempts to join more than this result in a {@code SocketException}. - * - * @param groupAddress the multicast group address to join - * @param networkInterface the network address to join with - * @throws IllegalArgumentException - * if the group address is not a multicast address or the network interface does not - * support multicast - * @throws IllegalStateException - * if the channel already has a source-specific membership for the group/network interface - * @throws ClosedChannelException - * if the channel is closed - * @throws IOException - * if some other I/O error occurs - * @hide Until ready for a public API change - */ - MembershipKey join(InetAddress groupAddress, NetworkInterface networkInterface) - throws IOException; - - /** - * Creates a source-specific membership to the {@code groupAddress} on the specified - * {@code networkInterface} filtered by the {@code sourceAddress}. Returns a - * {@code MembershipKey} that can be used to {@link MembershipKey#drop()} the membership. - * - * <p>A channel may join several groups. Each membership is network interface-specific: an - * application must join the group for each applicable network interface to receive datagrams. - * - * <p>Any-source and source-specific memberships cannot be mixed for a group address on a given - * network interface. An {@code IllegalStateException} will be thrown if joins of different types - * are attempted for a given {@code groupAddress}, {@code networkInterface} pair. Joining a - * multicast group with the same arguments as an existing, valid membership returns the same - * {@code MembershipKey}. - * - * <p>There is an OS-level limit on the number of multicast groups a process can join. - * This is typically 20. Attempts to join more than this result in a {@code SocketException}. - * - * <p>There is an OS-level limit on the number of source addresses that can be joined for a given - * {@code groupAddress}, {@code networkInterface} pair. This is typically 10. Attempts to add - * more than this result in a {@code SocketException}. - * - * @param groupAddress the multicast group address to join - * @param networkInterface the network address to join with - * @param sourceAddress the source address to restrict datagrams to - * @throws IllegalArgumentException - * if the group address is not a multicast address, the network interface does not - * support multicast, or the {@code groupAddress} and {@code sourceAddress} are not of - * compatible types - * @throws IllegalStateException - * if the channel already has a source-specific membership for the group/network interface - * @throws ClosedChannelException - * if the channel is closed - * @throws IOException - * if some other I/O error occurs - * @hide Until ready for a public API change - */ - MembershipKey join( - InetAddress groupAddress, NetworkInterface networkInterface, InetAddress sourceAddress) - throws IOException; - -} diff --git a/luni/src/main/java/java/nio/channels/NetworkChannel.java b/luni/src/main/java/java/nio/channels/NetworkChannel.java deleted file mode 100644 index 9b46e30..0000000 --- a/luni/src/main/java/java/nio/channels/NetworkChannel.java +++ /dev/null @@ -1,108 +0,0 @@ -/* - * Copyright (C) 2014 The Android Open Source Project - * - * Licensed under the Apache License, Version 2.0 (the "License"); - * you may not use this file except in compliance with the License. - * You may obtain a copy of the License at - * - * http://www.apache.org/licenses/LICENSE-2.0 - * - * Unless required by applicable law or agreed to in writing, software - * distributed under the License is distributed on an "AS IS" BASIS, - * WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied. - * See the License for the specific language governing permissions and - * limitations under the License. - */ - -package java.nio.channels; - -import java.io.Closeable; -import java.io.IOException; -import java.net.SocketAddress; -import java.net.SocketOption; -import java.util.Set; - -/** - * A common interface for channels that are backed by network sockets. - * - * @since 1.7 - * @hide Until ready for a public API change - */ -public interface NetworkChannel extends AutoCloseable, Channel, Closeable { - - /** - * Binds this channel to the given local socket address. If the {@code localAddr} is set - * to {@code null} the socket will be bound to an available local address on any free port of - * the system. - * - * @param local - * the local machine address and port to bind on. - * @return this channel. - * @throws UnsupportedAddressTypeException - * if the {@code SocketAddress} is not supported. - * @throws ClosedChannelException - * if the channel is closed. - * @throws AlreadyBoundException - * if the channel is already bound. - * @throws IOException - * if another I/O error occurs. - * @hide Until ready for a public API change - */ - NetworkChannel bind(SocketAddress local) throws IOException; - - /** - * Returns the local socket address the channel is bound to. The socket may be bound explicitly - * via {@link #bind(java.net.SocketAddress)} or similar methods, or as a side-effect when other - * methods are called, depending on the implementation. If the channel is not bound {@code null} - * is returned. - * - * <p>If IP is being used, the returned object will be a subclass of - * {@link java.net.InetSocketAddress} - * - * @return the local socket address, or {@code null} if the socket is not bound - * @throws ClosedChannelException - * if the channel is closed. - * @throws IOException - * if another I/O error occurs. - * @hide Until ready for a public API change - */ - SocketAddress getLocalAddress() throws IOException; - - /** - * Returns the value for the socket option. - * - * @throws UnsupportedOperationException - * if the option is not supported by the socket. - * @throws java.nio.channels.ClosedChannelException - * if the socket is closed - * @throws IOException - * if the value cannot be read. - * @hide Until ready for a public API change - * @see java.net.StandardSocketOptions - */ - <T> T getOption(SocketOption<T> option) throws IOException; - - /** - * Sets the value for the socket option. - * - * @return this NetworkChannel - * @throws UnsupportedOperationException - * if the option is not supported by the socket. - * @throws IllegalArgumentException - * if the value is not valid for the option. - * @throws java.nio.channels.ClosedChannelException - * if the socket is closed - * @throws IOException - * if the value cannot be written. - * @hide Until ready for a public API change - * @see java.net.StandardSocketOptions - */ - <T> NetworkChannel setOption(SocketOption<T> option, T value) throws IOException; - - /** - * Returns the set of socket options supported by this channel. - * - * @hide Until ready for a public API change - */ - Set<SocketOption<?>> supportedOptions(); -} diff --git a/luni/src/main/java/java/nio/channels/SeekableByteChannel.java b/luni/src/main/java/java/nio/channels/SeekableByteChannel.java deleted file mode 100644 index f4d6beb..0000000 --- a/luni/src/main/java/java/nio/channels/SeekableByteChannel.java +++ /dev/null @@ -1,163 +0,0 @@ -/* - * Copyright (C) 2014 The Android Open Source Project - * - * Licensed under the Apache License, Version 2.0 (the "License"); - * you may not use this file except in compliance with the License. - * You may obtain a copy of the License at - * - * http://www.apache.org/licenses/LICENSE-2.0 - * - * Unless required by applicable law or agreed to in writing, software - * distributed under the License is distributed on an "AS IS" BASIS, - * WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied. - * See the License for the specific language governing permissions and - * limitations under the License. - */ - -package java.nio.channels; - -import java.io.IOException; -import java.nio.ByteBuffer; - -/** - * An interface for channels that keep a pointer to a current position within an underlying - * byte-based data source such as a file. - * - * <p>SeekableByteChannels have a pointer into the underlying data source which is referred to as a - * <em>position</em>. The position can be manipulated by moving it within the data source, and the - * current position can be queried. - * - * <p>SeekableByteChannels also have an associated <em>size</em>. The size of the channel is the - * number of bytes that the data source currently contains. The size of the data source can be - * manipulated by adding more bytes to the end or by removing bytes from the end. See - * {@link #truncate}, {@link #position} and {@link #write} for details. The current size can also - * be queried. - * - * @hide Until ready for a public API change - * @since 1.7 - */ -public interface SeekableByteChannel extends ByteChannel { - - /** - * Returns the current position as a positive number of bytes from the start of the underlying - * data source. - * - * @throws ClosedChannelException - * if this channel is closed. - * @throws IOException - * if another I/O error occurs. - */ - long position() throws IOException; - - /** - * Sets the channel's position to {@code newPosition}. - * - * <p>The argument is the number of bytes counted from the start of the data source. The position - * cannot be set to a value that is negative. The new position can be set beyond the current - * size. If set beyond the current size, attempts to read will return end-of-file. Write - * operations will succeed but they will fill the bytes between the current end of the data - * source - * and the new position with the required number of (unspecified) byte values. - * - * @return the channel. - * @throws IllegalArgumentException - * if the new position is negative. - * @throws ClosedChannelException - * if this channel is closed. - * @throws IOException - * if another I/O error occurs. - */ - SeekableByteChannel position(long newPosition) throws IOException; - - /** - * Returns the size of the data source underlying this channel in bytes. - * - * @throws ClosedChannelException - * if this channel is closed. - * @throws IOException - * if an I/O error occurs. - */ - long size() throws IOException; - - /** - * Truncates the data source underlying this channel to a given size. Any bytes beyond the given - * size are removed. If there are no bytes beyond the given size then the contents are - * unmodified. - * - * <p>If the position is currently greater than the given size, then it is set to the new size. - * - * @return this channel. - * @throws IllegalArgumentException - * if the requested size is negative. - * @throws ClosedChannelException - * if this channel is closed. - * @throws NonWritableChannelException - * if the channel cannot be written to. - * @throws IOException - * if another I/O error occurs. - */ - SeekableByteChannel truncate(long size) throws IOException; - - /** - * Writes bytes from the given byte buffer to this channel. - * - * <p>The bytes are written starting at the channel's current position, and after some number of - * bytes are written (up to the {@link java.nio.Buffer#remaining() remaining} number of bytes in - * the buffer) the channel's position is increased by the number of bytes actually written. - * - * <p>If the channel's position is beyond the current end of the underlying data source, then the - * data source is first extended up to the given position by the required number of unspecified - * byte values. - * - * @param buffer - * the byte buffer containing the bytes to be written. - * @return the number of bytes actually written. - * @throws NonWritableChannelException - * if the channel was not opened for writing. - * @throws ClosedChannelException - * if the channel was already closed. - * @throws AsynchronousCloseException - * if another thread closes the channel during the write. - * @throws ClosedByInterruptException - * if another thread interrupts the calling thread while this operation is in progress. The - * interrupt state of the calling thread is set and the channel is closed. - * @throws IOException - * if another I/O error occurs, details are in the message. - */ - @Override - int write(ByteBuffer buffer) throws IOException; - - /** - * Reads bytes from this channel into the given buffer. - * - * <p>If the channels position is beyond the current end of the underlying data source then - * end-of-file (-1) is returned. - * - * <p>The bytes are read starting at the channel's current position, and after some number of - * bytes are read (up to the {@link java.nio.Buffer#remaining() remaining} number of bytes in the - * buffer) the channel's position is increased by the number of bytes actually read. The bytes - * will be read into the buffer starting at the buffer's current - * {@link java.nio.Buffer#position() position}. The buffer's {@link java.nio.Buffer#limit() - * limit} is not changed. - * - * <p>The call may block if other threads are also attempting to read from the same channel. - * - * @param buffer - * the byte buffer to receive the bytes. - * @return the number of bytes actually read, or -1 if the end of the data has been reached - * @throws AsynchronousCloseException - * if another thread closes the channel during the read. - * @throws ClosedByInterruptException - * if another thread interrupts the calling thread while the operation is in progress. The - * interrupt state of the calling thread is set and the channel is closed. - * @throws ClosedChannelException - * if the channel is closed. - * @throws IOException - * another I/O error occurs, details are in the message. - * @throws NonReadableChannelException - * if the channel was not opened for reading. - */ - @Override - int read(ByteBuffer buffer) throws IOException; - -} diff --git a/luni/src/main/java/java/nio/channels/ServerSocketChannel.java b/luni/src/main/java/java/nio/channels/ServerSocketChannel.java index c720451..ef50155 100644 --- a/luni/src/main/java/java/nio/channels/ServerSocketChannel.java +++ b/luni/src/main/java/java/nio/channels/ServerSocketChannel.java @@ -20,7 +20,6 @@ package java.nio.channels; import java.io.IOException; import java.net.ServerSocket; import java.net.SocketAddress; -import java.net.SocketOption; import java.nio.channels.spi.AbstractSelectableChannel; import java.nio.channels.spi.SelectorProvider; import java.util.Set; @@ -37,9 +36,7 @@ import java.util.Set; * {@link NotYetBoundException}. It can be bound by calling the bind method of a * related {@code ServerSocket} instance. */ -public abstract class ServerSocketChannel extends AbstractSelectableChannel - implements NetworkChannel { - +public abstract class ServerSocketChannel extends AbstractSelectableChannel { /** * Constructs a new {@link ServerSocketChannel}. * @@ -86,76 +83,6 @@ public abstract class ServerSocketChannel extends AbstractSelectableChannel public abstract ServerSocket socket(); /** - * {@inheritDoc} - * - * <p>This is equivalent to {@code bind(local, 0)}. - * @hide Until ready for a public API change - */ - @Override - public final ServerSocketChannel bind(SocketAddress local) throws IOException { - return bind(local, 0); - } - - /** - * Binds this server channel to the given local socket address. If the {@code localAddr} is set - * to {@code null} the socket will be bound to an available local address on any free port of - * the system. - * - * @param localAddr - * the local machine address and port to bind on. - * @param backlog the maximum number of unaccepted connections. Passing 0 or - * a negative value yields the default backlog of 50. - * @return this {@code ServerSocketChannel}. - * @throws UnsupportedAddressTypeException - * if the {@code SocketAddress} is not supported. - * @throws ClosedChannelException - * if the channel is closed. - * @throws AlreadyBoundException - * if the channel is already bound. - * @throws IOException - * if another I/O error occurs. - * @since 1.7 - * @hide Until ready for a public API change - */ - public ServerSocketChannel bind(SocketAddress localAddr, int backlog) throws IOException { - // This method was added for interoperability with Java 7, where it is abstract. It is - // concrete here to avoid breaking existing Android applications that extend this class. - throw new UnsupportedOperationException("Subclasses must override this method"); - } - - /** @hide Until ready for a public API change */ - @Override - public SocketAddress getLocalAddress() throws IOException { - // This method was added for interoperability with Java 7, where it is abstract. It is - // concrete here to avoid breaking existing Android applications that extend this class. - throw new UnsupportedOperationException("Subclasses must override this method"); - } - - /** @hide Until ready for a public API change */ - @Override - public <T> T getOption(SocketOption<T> option) throws IOException { - // This method was added for interoperability with Java 7, where it is abstract. It is - // concrete here to avoid breaking existing Android applications that extend this class. - throw new UnsupportedOperationException("Subclasses must override this method"); - } - - /** @hide Until ready for a public API change */ - @Override - public <T> ServerSocketChannel setOption(SocketOption<T> option, T value) throws IOException { - // This method was added for interoperability with Java 7, where it is abstract. It is - // concrete here to avoid breaking existing Android applications that extend this class. - throw new UnsupportedOperationException("Subclasses must override this method"); - } - - /** @hide Until ready for a public API change */ - @Override - public Set<SocketOption<?>> supportedOptions() { - // This method was added for interoperability with Java 7, where it is abstract. It is - // concrete here to avoid breaking existing Android applications that extend this class. - throw new UnsupportedOperationException("Subclasses must override this method"); - } - - /** * Accepts a connection to this server-socket channel. * <p> * This method returns {@code null} when this channel is non-blocking and no diff --git a/luni/src/main/java/java/nio/channels/SocketChannel.java b/luni/src/main/java/java/nio/channels/SocketChannel.java index a6d1551..a91fccd 100644 --- a/luni/src/main/java/java/nio/channels/SocketChannel.java +++ b/luni/src/main/java/java/nio/channels/SocketChannel.java @@ -20,7 +20,6 @@ package java.nio.channels; import java.io.IOException; import java.net.Socket; import java.net.SocketAddress; -import java.net.SocketOption; import java.nio.ByteBuffer; import java.nio.channels.spi.AbstractSelectableChannel; import java.nio.channels.spi.SelectorProvider; @@ -64,7 +63,7 @@ import java.util.Set; * processing, calls to {@link #read} and {@link #write} will block. */ public abstract class SocketChannel extends AbstractSelectableChannel implements - ByteChannel, ScatteringByteChannel, GatheringByteChannel, NetworkChannel { + ByteChannel, ScatteringByteChannel, GatheringByteChannel { /** * Constructs a new {@code SocketChannel}. @@ -142,46 +141,6 @@ public abstract class SocketChannel extends AbstractSelectableChannel implements */ public abstract Socket socket(); - /** @hide Until ready for a public API change */ - @Override - public SocketChannel bind(SocketAddress local) throws IOException { - // This method was added for interoperability with Java 7, where it is abstract. It is - // concrete here to avoid breaking existing Android applications that extend this class. - throw new UnsupportedOperationException("Subclasses must override this method"); - } - - /** @hide Until ready for a public API change */ - @Override - public SocketAddress getLocalAddress() throws IOException { - // This method was added for interoperability with Java 7, where it is abstract. It is - // concrete here to avoid breaking existing Android applications that extend this class. - throw new UnsupportedOperationException("Subclasses must override this method"); - } - - /** @hide Until ready for a public API change */ - @Override - public <T> T getOption(SocketOption<T> option) throws IOException { - // This method was added for interoperability with Java 7, where it is abstract. It is - // concrete here to avoid breaking existing Android applications that extend this class. - throw new UnsupportedOperationException("Subclasses must override this method"); - } - - /** @hide Until ready for a public API change */ - @Override - public <T> SocketChannel setOption(SocketOption<T> option, T value) throws IOException { - // This method was added for interoperability with Java 7, where it is abstract. It is - // concrete here to avoid breaking existing Android applications that extend this class. - throw new UnsupportedOperationException("Subclasses must override this method"); - } - - /** @hide Until ready for a public API change */ - @Override - public Set<SocketOption<?>> supportedOptions() { - // This method was added for interoperability with Java 7, where it is abstract. It is - // concrete here to avoid breaking existing Android applications that extend this class. - throw new UnsupportedOperationException("Subclasses must override this method"); - } - /** * Indicates whether this channel's socket is connected. * diff --git a/luni/src/main/java/java/util/Currency.java b/luni/src/main/java/java/util/Currency.java index 11b5af1..8cfb68f 100644 --- a/luni/src/main/java/java/util/Currency.java +++ b/luni/src/main/java/java/util/Currency.java @@ -127,17 +127,6 @@ public final class Currency implements Serializable { } /** - * Returns the ISO 4217 numeric code for this currency. If there is no standard numeric code a - * zero is returned. - * - * @since 1.7 - * @hide Until ready for an API update - */ - public int getNumericCode() { - return ICU.getCurrencyNumericCode(currencyCode); - } - - /** * Equivalent to {@code getSymbol(Locale.getDefault())}. * See "<a href="../util/Locale.html#default_locale">Be wary of the default locale</a>". */ diff --git a/luni/src/main/java/java/util/zip/ZipFile.java b/luni/src/main/java/java/util/zip/ZipFile.java index 43e8567..b44156e 100644 --- a/luni/src/main/java/java/util/zip/ZipFile.java +++ b/luni/src/main/java/java/util/zip/ZipFile.java @@ -26,7 +26,6 @@ import java.io.IOException; import java.io.InputStream; import java.io.RandomAccessFile; import java.nio.ByteOrder; -import java.nio.charset.Charset; import java.nio.charset.StandardCharsets; import java.util.Enumeration; import java.util.Iterator; @@ -98,8 +97,6 @@ public class ZipFile implements Closeable, ZipConstants { private final String filename; - private final Charset charset; - private File fileToDeleteOnClose; private RandomAccessFile raf; @@ -119,23 +116,7 @@ public class ZipFile implements Closeable, ZipConstants { * @throws IOException if an {@code IOException} occurs. */ public ZipFile(File file) throws ZipException, IOException { - this(file, OPEN_READ, StandardCharsets.UTF_8); - } - - /** - * Constructs a new {@code ZipFile} allowing read access to the contents of the given file. - * - * <p>The {@code charset} is used to decode the file comment if one exists. If the character - * encoding for entry names and comments is not explicitly marked as UTF-8 by the zip file - * then {@code charset} is used to decode them. - * - * @throws ZipException if a zip error occurs. - * @throws IOException if an {@code IOException} occurs. - * @since 1.7 - * @hide Until ready for an API update - */ - public ZipFile(File file, Charset charset) throws ZipException, IOException { - this(file, OPEN_READ, charset); + this(file, OPEN_READ); } /** @@ -146,7 +127,7 @@ public class ZipFile implements Closeable, ZipConstants { * @throws IOException if an IOException occurs. */ public ZipFile(String name) throws IOException { - this(new File(name), OPEN_READ, StandardCharsets.UTF_8); + this(new File(name), OPEN_READ); } /** @@ -162,31 +143,7 @@ public class ZipFile implements Closeable, ZipConstants { * @throws IOException if an {@code IOException} occurs. */ public ZipFile(File file, int mode) throws IOException { - this(file, mode, StandardCharsets.UTF_8); - } - - /** - * Constructs a new {@code ZipFile} allowing access to the given file. - * - * <p>The {@code mode} must be either {@code OPEN_READ} or {@code OPEN_READ|OPEN_DELETE}. - * If the {@code OPEN_DELETE} flag is supplied, the file will be deleted at or before the - * time that the {@code ZipFile} is closed (the contents will remain accessible until - * this {@code ZipFile} is closed); it also calls {@code File.deleteOnExit}. - * - * <p>The {@code charset} is used to decode the file comment if one exists. If the character - * encoding for entry names and comments is not explicitly marked as UTF-8 by the zip file - * then {@code charset} is used to decode them. - * - * @throws IOException if an {@code IOException} occurs. - * @since 1.7 - * @hide Until ready for an API update - */ - public ZipFile(File file, int mode, Charset charset) throws IOException { filename = file.getPath(); - if (charset == null) { - throw new NullPointerException("charset == null"); - } - this.charset = charset; if (mode != OPEN_READ && mode != (OPEN_READ | OPEN_DELETE)) { throw new IllegalArgumentException("Bad mode: " + mode); } @@ -467,7 +424,7 @@ public class ZipFile implements Closeable, ZipConstants { if (commentLength > 0) { byte[] commentBytes = new byte[commentLength]; raf.readFully(commentBytes); - comment = new String(commentBytes, 0, commentBytes.length, charset); + comment = new String(commentBytes, 0, commentBytes.length, StandardCharsets.UTF_8); } // Seek to the first CDE and read all entries. @@ -478,7 +435,7 @@ public class ZipFile implements Closeable, ZipConstants { BufferedInputStream bufferedStream = new BufferedInputStream(rafStream, 4096); byte[] hdrBuf = new byte[CENHDR]; // Reuse the same buffer for each entry. for (int i = 0; i < numEntries; ++i) { - ZipEntry newEntry = new ZipEntry(hdrBuf, bufferedStream, charset); + ZipEntry newEntry = new ZipEntry(hdrBuf, bufferedStream, StandardCharsets.UTF_8); if (newEntry.localHeaderRelOffset >= centralDirOffset) { throw new ZipException("Local file header offset is after central directory"); } diff --git a/luni/src/main/java/java/util/zip/ZipInputStream.java b/luni/src/main/java/java/util/zip/ZipInputStream.java index 5a73619..4c0034e 100644 --- a/luni/src/main/java/java/util/zip/ZipInputStream.java +++ b/luni/src/main/java/java/util/zip/ZipInputStream.java @@ -21,7 +21,6 @@ import java.io.IOException; import java.io.InputStream; import java.io.PushbackInputStream; import java.nio.ByteOrder; -import java.nio.charset.Charset; import java.nio.charset.ModifiedUtf8; import java.nio.charset.StandardCharsets; import java.util.Arrays; @@ -90,35 +89,16 @@ public class ZipInputStream extends InflaterInputStream implements ZipConstants private char[] stringCharBuf = new char[256]; - private final Charset charset; - /** * Constructs a new {@code ZipInputStream} to read zip entries from the given input stream. * * <p>UTF-8 is used to decode all strings in the file. */ public ZipInputStream(InputStream stream) { - this(stream, StandardCharsets.UTF_8); - } - - /** - * Constructs a new {@code ZipInputStream} to read zip entries from the given input stream. - * - * <p>If the character encoding for entry names and comments is not explicitly marked as UTF-8 - * by the zip file then {@code charset} is used to decode them. - * - * @since 1.7 - * @hide Until ready for an API update - */ - public ZipInputStream(InputStream stream, Charset charset) { super(new PushbackInputStream(stream, BUF_SIZE), new Inflater(true)); if (stream == null) { throw new NullPointerException("stream == null"); } - if (charset == null) { - throw new NullPointerException("charset == null"); - } - this.charset = charset; } /** @@ -272,12 +252,7 @@ public class ZipInputStream extends InflaterInputStream implements ZipConstants } int extraLength = peekShort(LOCEXT - LOCVER); - // Determine the character set to use to decode strings. - Charset charset = this.charset; - if ((flags & ZipFile.GPBF_UTF8_FLAG) != 0) { - charset = StandardCharsets.UTF_8; - } - String name = readString(nameLength, charset); + String name = readString(nameLength); currentEntry = createZipEntry(name); currentEntry.time = ceLastModifiedTime; currentEntry.modDate = ceLastModifiedDate; @@ -298,21 +273,17 @@ public class ZipInputStream extends InflaterInputStream implements ZipConstants /** * Reads bytes from the current stream position returning the string representation. */ - private String readString(int byteLength, Charset charset) throws IOException { + private String readString(int byteLength) throws IOException { if (byteLength > stringBytesBuf.length) { stringBytesBuf = new byte[byteLength]; } Streams.readFully(in, stringBytesBuf, 0, byteLength); - if (charset == StandardCharsets.UTF_8) { - // The number of chars will always be less than or equal to the number of bytes. It's - // fine if this buffer is too long. - if (byteLength > stringCharBuf.length) { - stringCharBuf = new char[byteLength]; - } - return ModifiedUtf8.decode(stringBytesBuf, stringCharBuf, 0, byteLength); - } else { - return new String(stringBytesBuf, 0, byteLength, charset); + // The number of chars will always be less than or equal to the number of bytes. It's + // fine if this buffer is too long. + if (byteLength > stringCharBuf.length) { + stringCharBuf = new char[byteLength]; } + return ModifiedUtf8.decode(stringBytesBuf, stringCharBuf, 0, byteLength); } private int peekShort(int offset) { diff --git a/luni/src/main/java/java/util/zip/ZipOutputStream.java b/luni/src/main/java/java/util/zip/ZipOutputStream.java index ac6bdf2..8278355 100644 --- a/luni/src/main/java/java/util/zip/ZipOutputStream.java +++ b/luni/src/main/java/java/util/zip/ZipOutputStream.java @@ -20,7 +20,6 @@ package java.util.zip; import java.io.ByteArrayOutputStream; import java.io.IOException; import java.io.OutputStream; -import java.nio.charset.Charset; import java.nio.charset.StandardCharsets; import java.util.Arrays; import java.util.HashSet; @@ -76,8 +75,6 @@ public class ZipOutputStream extends DeflaterOutputStream implements ZipConstant private final HashSet<String> entries = new HashSet<String>(); - private final Charset charset; - private int defaultCompressionMethod = DEFLATED; private int compressionLevel = Deflater.DEFAULT_COMPRESSION; @@ -103,25 +100,7 @@ public class ZipOutputStream extends DeflaterOutputStream implements ZipConstant * <p>UTF-8 will be used to encode the file comment, entry names and comments. */ public ZipOutputStream(OutputStream os) { - this(os, StandardCharsets.UTF_8); - } - - /** - * Constructs a new {@code ZipOutputStream} that writes a zip file to the given - * {@code OutputStream}. - * - * <p>The specified character set will be used to encode the file comment, entry names and - * comments. - * - * @since 1.7 - * @hide Until ready for an API update - */ - public ZipOutputStream(OutputStream os, Charset charset) { super(os, new Deflater(Deflater.DEFAULT_COMPRESSION, true)); - if (charset == null) { - throw new NullPointerException("charset == null"); - } - this.charset = charset; } /** @@ -183,9 +162,7 @@ public class ZipOutputStream extends DeflaterOutputStream implements ZipConstant // Since gingerbread, we always set the UTF-8 flag on individual files if appropriate. // Some tools insist that the central directory have the UTF-8 flag. // http://code.google.com/p/android/issues/detail?id=20214 - if (charset == StandardCharsets.UTF_8) { - flags |= ZipFile.GPBF_UTF8_FLAG; - } + flags |= ZipFile.GPBF_UTF8_FLAG; writeLong(cDir, CENSIG); writeShort(cDir, ZIP_VERSION_2_0); // Version this file was made by. writeShort(cDir, ZIP_VERSION_2_0); // Minimum version needed to extract. @@ -319,11 +296,11 @@ public class ZipOutputStream extends DeflaterOutputStream implements ZipConstant // TODO: support Zip64. throw new ZipException("Too many entries for the zip file format's 16-bit entry count"); } - nameBytes = ze.name.getBytes(charset); + nameBytes = ze.name.getBytes(StandardCharsets.UTF_8); checkSizeIsWithinShort("Name", nameBytes); entryCommentBytes = EmptyArray.BYTE; if (ze.comment != null) { - entryCommentBytes = ze.comment.getBytes(charset); + entryCommentBytes = ze.comment.getBytes(StandardCharsets.UTF_8); // The comment is not written out until the entry is finished, but it is validated here // to fail-fast. checkSizeIsWithinShort("Comment", entryCommentBytes); @@ -340,9 +317,7 @@ public class ZipOutputStream extends DeflaterOutputStream implements ZipConstant int flags = (method == STORED) ? 0 : ZipFile.GPBF_DATA_DESCRIPTOR_FLAG; // Java always outputs UTF-8 filenames. (Before Java 7, the RI didn't set this flag and used // modified UTF-8. From Java 7, when using UTF_8 it sets this flag and uses normal UTF-8.) - if (charset == StandardCharsets.UTF_8) { - flags |= ZipFile.GPBF_UTF8_FLAG; - } + flags |= ZipFile.GPBF_UTF8_FLAG; writeLong(out, LOCSIG); // Entry header writeShort(out, ZIP_VERSION_2_0); // Minimum version needed to extract. writeShort(out, flags); @@ -384,7 +359,7 @@ public class ZipOutputStream extends DeflaterOutputStream implements ZipConstant return; } - byte[] newCommentBytes = comment.getBytes(charset); + byte[] newCommentBytes = comment.getBytes(StandardCharsets.UTF_8); checkSizeIsWithinShort("Comment", newCommentBytes); this.commentBytes = newCommentBytes; } @@ -455,8 +430,8 @@ public class ZipOutputStream extends DeflaterOutputStream implements ZipConstant private void checkSizeIsWithinShort(String property, byte[] bytes) { if (bytes.length > 0xffff) { - throw new IllegalArgumentException( - property + " too long in " + charset + ":" + bytes.length + " bytes"); + throw new IllegalArgumentException(property + " too long in UTF-8:" + bytes.length + + " bytes"); } } } diff --git a/luni/src/test/java/libcore/java/lang/CharacterTest.java b/luni/src/test/java/libcore/java/lang/CharacterTest.java index 0028521..94e3b96 100644 --- a/luni/src/test/java/libcore/java/lang/CharacterTest.java +++ b/luni/src/test/java/libcore/java/lang/CharacterTest.java @@ -277,66 +277,4 @@ public class CharacterTest extends junit.framework.TestCase { } } } - - public void test_UnicodeScript_forName() throws Exception { - try { - Character.UnicodeScript.forName(null); - fail(); - } catch (NullPointerException expected) { - } - - try { - Character.UnicodeScript.forName("existential_dilemmas"); - fail(); - } catch (IllegalArgumentException expected) { - } - - // Note that ICU is pretty lenient about block names and their abbreviations. - assertSame(Character.UnicodeScript.MALAYALAM, Character.UnicodeScript.forName("Malayalam")); - assertSame(Character.UnicodeScript.MALAYALAM, Character.UnicodeScript.forName("MalayaLAM")); - assertSame(Character.UnicodeScript.MALAYALAM, Character.UnicodeScript.forName("Mlym")); - assertSame(Character.UnicodeScript.MALAYALAM, Character.UnicodeScript.forName("MlYM")); - - assertSame(Character.UnicodeScript.OLD_SOUTH_ARABIAN, Character.UnicodeScript.forName("Old_south_arabian")); - - // NOTE: This test fails on the RI because they're much stricter in - // their matching. Strict enough that they fail on "Old south arabian", despite - // it being the official name AND the alias for this script. - assertSame(Character.UnicodeScript.OLD_SOUTH_ARABIAN, Character.UnicodeScript.forName("Old south arabian")); - assertSame(Character.UnicodeScript.OLD_SOUTH_ARABIAN, Character.UnicodeScript.forName("SARB")); - - // A script that's recognized by ICU but not a part of the standard - // java script values. - try { - Character.UnicodeScript.forName("Old north arabian"); - fail(); - } catch (IllegalArgumentException expected) { - } - } - - public void test_UnicodeScript_of() throws Exception { - try { - Character.UnicodeScript.of(-1); - fail(); - } catch (IllegalArgumentException expected) { - } - - try { - Character.UnicodeScript.of(0xffffff); - fail(); - } catch (IllegalArgumentException expected) { - } - - // The example from the ICU4C unit tests. - assertSame(Character.UnicodeScript.MALAYALAM, Character.UnicodeScript.of(0x0D02)); - - // Special cases: - // - // 0640 is the ARABIC_TATWEEL, used by both Mandiac & Syriac - assertSame(Character.UnicodeScript.COMMON, Character.UnicodeScript.of(0x0640)); - // 0300 is the COMBINING GRAVE ACCENT, which should be INHERITED because it's - // a nonspacing mark. - assertSame(Character.UnicodeScript.INHERITED, Character.UnicodeScript.of(0x0300)); - assertSame(Character.UnicodeScript.COMMON, Character.UnicodeScript.of(0x0640)); - } } diff --git a/luni/src/test/java/libcore/java/net/SocketTest.java b/luni/src/test/java/libcore/java/net/SocketTest.java index b9ed99c..fb09be0 100644 --- a/luni/src/test/java/libcore/java/net/SocketTest.java +++ b/luni/src/test/java/libcore/java/net/SocketTest.java @@ -90,7 +90,7 @@ public class SocketTest extends junit.framework.TestCase { // Open a local server port. ServerSocketChannel ssc = ServerSocketChannel.open(); InetSocketAddress listenAddr = new InetSocketAddress(host, 0); - ssc.bind(listenAddr, 0); + ssc.socket().bind(listenAddr, 0); ServerSocket ss = ssc.socket(); // Open a socket to the local port. @@ -110,7 +110,7 @@ public class SocketTest extends junit.framework.TestCase { in.socket().setTcpNoDelay(false); } - InetSocketAddress listenAddress = (InetSocketAddress) in.getLocalAddress(); + InetSocketAddress listenAddress = (InetSocketAddress) in.socket().getLocalSocketAddress(); InetSocketAddress outRemoteAddress = (InetSocketAddress) out.socket().getRemoteSocketAddress(); InetSocketAddress outLocalAddress = (InetSocketAddress) out.socket().getLocalSocketAddress(); InetSocketAddress inLocalAddress = (InetSocketAddress) in.socket().getLocalSocketAddress(); diff --git a/luni/src/test/java/libcore/java/nio/channels/DatagramChannelMulticastTest.java b/luni/src/test/java/libcore/java/nio/channels/DatagramChannelMulticastTest.java deleted file mode 100644 index f0db3ba..0000000 --- a/luni/src/test/java/libcore/java/nio/channels/DatagramChannelMulticastTest.java +++ /dev/null @@ -1,1120 +0,0 @@ -package libcore.java.nio.channels; - -import junit.framework.AssertionFailedError; -import junit.framework.TestCase; - -import java.io.IOException; -import java.net.Inet4Address; -import java.net.Inet6Address; -import java.net.InetAddress; -import java.net.InetSocketAddress; -import java.net.InterfaceAddress; -import java.net.NetworkInterface; -import java.net.SocketAddress; -import java.net.SocketException; -import java.net.StandardSocketOptions; -import java.nio.ByteBuffer; -import java.nio.channels.ClosedChannelException; -import java.nio.channels.DatagramChannel; -import java.nio.channels.MembershipKey; -import java.util.ArrayList; -import java.util.Enumeration; -import java.util.List; - -/** - * Tests associated with multicast behavior of DatagramChannel. - */ -public class DatagramChannelMulticastTest extends TestCase { - - private static InetAddress lookup(String s) { - try { - return InetAddress.getByName(s); - } catch (IOException ex) { - throw new RuntimeException(ex); - } - } - - // These IP addresses aren't inherently "good" or "bad"; they're just used like that. - // We use the "good" addresses for our actual group, and the "bad" addresses are for a group that - // we won't actually set up. - private static final InetAddress GOOD_MULTICAST_IPv4 = lookup("239.255.0.1"); - private static final InetAddress BAD_MULTICAST_IPv4 = lookup("239.255.0.2"); - private static final InetAddress GOOD_MULTICAST_IPv6 = lookup("ff05::7:7"); - private static final InetAddress BAD_MULTICAST_IPv6 = lookup("ff05::7:8"); - - // Special addresses. - private static final InetAddress WILDCARD_IPv4 = lookup("0.0.0.0"); - private static final InetAddress WILDCARD_IPv6 = lookup("::"); - - // Arbitrary unicast addresses. Used when the value doesn't actually matter. e.g. for source - // filters. - private static final InetAddress UNICAST_IPv4_1 = lookup("192.168.1.1"); - private static final InetAddress UNICAST_IPv4_2 = lookup("192.168.1.2"); - private static final InetAddress UNICAST_IPv6_1 = lookup("2001:db8::1"); - private static final InetAddress UNICAST_IPv6_2 = lookup("2001:db8::2"); - - private List<NetworkInterface> ipv4networkInterfaces = new ArrayList<NetworkInterface>(); - private List<NetworkInterface> ipv6networkInterfaces = new ArrayList<NetworkInterface>(); - private NetworkInterface ipv4networkInterface; - private NetworkInterface ipv6networkInterface; - private NetworkInterface loopbackInterface; - - @Override - protected void setUp() throws Exception { - // The loopback interface isn't actually useful for sending/receiving multicast messages but it - // can be used as a dummy for tests where that does not matter. - loopbackInterface = NetworkInterface.getByInetAddress(InetAddress.getLoopbackAddress()); - assertNotNull(loopbackInterface); - assertTrue(loopbackInterface.isLoopback()); - assertFalse(loopbackInterface.supportsMulticast()); - - Enumeration<NetworkInterface> interfaces = NetworkInterface.getNetworkInterfaces(); - assertNotNull(interfaces); - // Only consider interfaces that have addresses associated with them. Otherwise tests don't work - // so well. - while (interfaces.hasMoreElements()) { - NetworkInterface networkInterface = interfaces.nextElement(); - if (willWorkForMulticast(networkInterface)) { - Enumeration<InetAddress> addresses = networkInterface.getInetAddresses(); - while (addresses.hasMoreElements()) { - final InetAddress nextAddress = addresses.nextElement(); - if (nextAddress instanceof Inet4Address) { - ipv4networkInterfaces.add(networkInterface); - } else if (nextAddress instanceof Inet6Address) { - ipv6networkInterfaces.add(networkInterface); - } - } - } - } - assertTrue( - "Test environment must have network interfaces capable of both IPv4 and IPv6 multicast", - ipv4networkInterfaces.size() > 0 && ipv6networkInterfaces.size() > 0); - ipv4networkInterface = ipv4networkInterfaces.get(0); - ipv6networkInterface = ipv6networkInterfaces.get(0); - } - - public void test_open() throws IOException { - DatagramChannel dc = DatagramChannel.open(); - - // Unlike MulticastSocket, DatagramChannel has SO_REUSEADDR set to false by default. - assertFalse(dc.getOption(StandardSocketOptions.SO_REUSEADDR)); - - // Confirm multicast loop is on by default as specified in the docs. Many tests in this class - // depend on this being true. - assertTrue(dc.getOption(StandardSocketOptions.IP_MULTICAST_LOOP)); - - assertNull(dc.getLocalAddress()); - assertTrue(dc.isOpen()); - assertFalse(dc.isConnected()); - - dc.close(); - } - - public void test_bind_null() throws Exception { - DatagramChannel dc = createReceiverChannel(); - assertNotNull(dc.getLocalAddress()); - assertTrue(dc.isOpen()); - assertFalse(dc.isConnected()); - - dc.close(); - try { - dc.getLocalAddress(); - fail(); - } catch (ClosedChannelException expected) { - } - assertFalse(dc.isOpen()); - assertFalse(dc.isConnected()); - } - - public void test_joinAnySource_afterClose() throws Exception { - DatagramChannel dc = createReceiverChannel(); - dc.close(); - try { - dc.join(GOOD_MULTICAST_IPv4, ipv4networkInterface); - fail(); - } catch (ClosedChannelException expected) { - } - } - - public void test_joinAnySource_nullGroupAddress() throws Exception { - DatagramChannel dc = createReceiverChannel(); - try { - dc.join(null, ipv4networkInterface); - fail(); - } catch (NullPointerException expected) { - } - dc.close(); - } - - public void test_joinAnySource_nullNetworkInterface() throws Exception { - DatagramChannel dc = createReceiverChannel(); - try { - dc.join(GOOD_MULTICAST_IPv4, null); - fail(); - } catch (NullPointerException expected) { - } - dc.close(); - } - - public void test_joinAnySource_nonMulticastGroupAddress_IPv4() throws Exception { - for (NetworkInterface networkInterface : ipv4networkInterfaces) { - test_joinAnySource_illegalArgumentExpected(networkInterface, UNICAST_IPv4_1); - } - } - - public void test_joinAnySource_nonMulticastGroupAddress_IPv6() throws Exception { - for (NetworkInterface networkInterface : ipv6networkInterfaces) { - test_joinAnySource_illegalArgumentExpected(networkInterface, UNICAST_IPv6_1); - } - } - - private void test_joinAnySource_illegalArgumentExpected(NetworkInterface networkInterface, - InetAddress group) throws Exception { - DatagramChannel dc = createReceiverChannel(); - try { - dc.join(group, networkInterface); - fail(); - } catch (IllegalArgumentException expected) { - } - dc.close(); - } - - public void test_joinAnySource_IPv4() throws Exception { - test_joinAnySource(ipv4networkInterfaces, GOOD_MULTICAST_IPv4, BAD_MULTICAST_IPv4); - } - - public void test_joinAnySource_IPv6() throws Exception { - test_joinAnySource(ipv6networkInterfaces, GOOD_MULTICAST_IPv6, BAD_MULTICAST_IPv6); - } - - private void test_joinAnySource( - Iterable<NetworkInterface> networkInterfaces, InetAddress group, InetAddress group2) - throws Exception { - for (NetworkInterface networkInterface : networkInterfaces) { - // Set up a receiver join the group on networkInterface. - DatagramChannel receiverChannel = createReceiverChannel(); - InetSocketAddress localAddress = (InetSocketAddress) receiverChannel.getLocalAddress(); - receiverChannel.join(group, networkInterface); - - // Send a message to the group we joined. - String msg = "Hello World"; - sendMessage(group, localAddress.getPort(), msg, networkInterface); - - // Now verify that we received the data as expected. - ByteBuffer recvBuffer = ByteBuffer.allocate(100); - SocketAddress sourceAddress = receiverChannel.receive(recvBuffer); - assertNotNull(sourceAddress); - assertEquals(msg, new String(recvBuffer.array(), 0, recvBuffer.position())); - - // Send a message to the group we did not join. - String msg2 = "Hello World - Different Group"; - sendMessage(group2, localAddress.getPort(), msg2, networkInterface); - recvBuffer.position(0); - // Now verify that we didn't receive the second message. - SocketAddress sourceAddress2 = receiverChannel.receive(recvBuffer); - assertNull(sourceAddress2); - - receiverChannel.close(); - } - } - - public void test_joinAnySource_processLimit() throws Exception { - DatagramChannel dc = createReceiverChannel(); - for (byte i = 1; i <= 25; i++) { - InetAddress groupAddress = Inet4Address.getByName("239.255.0." + i); - try { - dc.join(groupAddress, ipv4networkInterface); - } catch (SocketException e) { - // There is a limit, that's ok according to the RI docs. For this test a lower bound of 20 - // is used, which appears to be the default linux limit. - // See /proc/sys/net/ipv4/igmp_max_memberships. - assertTrue(i > 20); - break; - } - } - - dc.close(); - } - - public void test_joinAnySource_blockLimit() throws Exception { - DatagramChannel dc = createReceiverChannel(); - MembershipKey key = dc.join(GOOD_MULTICAST_IPv4, ipv4networkInterface); - for (byte i = 1; i <= 15; i++) { - InetAddress sourceAddress = Inet4Address.getByName("10.0.0." + i); - try { - key.block(sourceAddress); - } catch (SocketException e) { - // There is a limit, that's ok according to the RI docs. For this test a lower bound of 10 - // is used, which appears to be the default linux limit. - // See /proc/sys/net/ipv4/igmp_max_msf. - assertTrue(i > 10); - break; - } - } - - dc.close(); - } - - /** Confirms that calling join() does not cause an implicit bind() to take place. */ - public void test_joinAnySource_doesNotCauseBind_IPv4() throws Exception { - test_joinAnySource_doesNotCauseBind(ipv4networkInterfaces, GOOD_MULTICAST_IPv4); - } - - public void test_joinAnySource_doesNotCauseBind_IPv6() throws Exception { - test_joinAnySource_doesNotCauseBind(ipv6networkInterfaces, GOOD_MULTICAST_IPv6); - } - - private void test_joinAnySource_doesNotCauseBind( - Iterable<NetworkInterface> networkInterfaces, InetAddress group) throws IOException { - for (NetworkInterface networkInterface : networkInterfaces) { - DatagramChannel dc = DatagramChannel.open(); - dc.join(group, networkInterface); - assertNull(dc.getLocalAddress()); - dc.close(); - } - } - - public void test_joinAnySource_networkInterfaces() throws Exception { - // Check that we can join on specific interfaces and that we only receive if data is - // received on that interface. This test is only really useful on devices with multiple - // non-loopback interfaces. - - ArrayList<NetworkInterface> realInterfaces = new ArrayList<NetworkInterface>(); - Enumeration<NetworkInterface> theInterfaces = NetworkInterface.getNetworkInterfaces(); - while (theInterfaces.hasMoreElements()) { - NetworkInterface thisInterface = theInterfaces.nextElement(); - // Skip interfaces that do not support multicast - there's no point in proving they cannot - // send / receive multicast messages. - if (willWorkForMulticast(thisInterface)) { - realInterfaces.add(thisInterface); - } - } - - for (NetworkInterface thisInterface : realInterfaces) { - // Get the first address on the interface. - Enumeration<InetAddress> addresses = thisInterface.getInetAddresses(); - - while (addresses.hasMoreElements()) { - InetAddress listenAddress = addresses.nextElement(); - - // Start a server which is joined to the group and has only asked for packets on this - // interface. - NetworkInterface sendingInterface; - InetAddress group; - if (listenAddress instanceof Inet4Address) { - group = GOOD_MULTICAST_IPv4; - sendingInterface = ipv4networkInterface; - } else { - group = GOOD_MULTICAST_IPv6; - sendingInterface = ipv6networkInterface; - } - DatagramChannel dc = createReceiverChannel(); - InetSocketAddress localAddress = (InetSocketAddress) dc.getLocalAddress(); - dc.join(group, thisInterface); - - // Now send out a packet on sendingInterface. We should only see the packet if we send - // it on the same interface we are listening on (thisInterface). - String msg = "Hello World - Again " + thisInterface.getName(); - sendMessage(group, localAddress.getPort(), msg, sendingInterface); - - ByteBuffer recvBuffer = ByteBuffer.allocate(100); - SocketAddress sourceAddress = dc.receive(recvBuffer); - if (thisInterface.equals(sendingInterface)) { - assertEquals(msg, new String(recvBuffer.array(), 0, recvBuffer.position())); - } else { - assertNull(sourceAddress); - } - - dc.close(); - } - } - } - - /** Confirms that the scope of each membership is network interface-level. */ - public void test_join_canMixJoinTypesOnDifferentInterfaces() throws Exception { - DatagramChannel dc = DatagramChannel.open(); - MembershipKey membershipKey1 = dc.join(GOOD_MULTICAST_IPv4, ipv4networkInterface); - MembershipKey membershipKey2 = dc.join(GOOD_MULTICAST_IPv4, loopbackInterface, UNICAST_IPv4_1); - assertNotSame(membershipKey1, membershipKey2); - - dc.close(); - } - - public void test_joinAnySource_multiple_joins_IPv4() - throws Exception { - test_joinAnySource_multiple_joins(ipv4networkInterfaces, GOOD_MULTICAST_IPv4); - } - - public void test_joinAnySource_multiple_joins_IPv6() - throws Exception { - test_joinAnySource_multiple_joins(ipv6networkInterfaces, GOOD_MULTICAST_IPv6); - } - - private void test_joinAnySource_multiple_joins( - Iterable<NetworkInterface> networkInterfaces, InetAddress group) throws Exception { - for (NetworkInterface networkInterface : networkInterfaces) { - DatagramChannel dc = createReceiverChannel(); - - MembershipKey membershipKey1 = dc.join(group, networkInterface); - - MembershipKey membershipKey2 = dc.join(group, loopbackInterface); - assertFalse(membershipKey1.equals(membershipKey2)); - - MembershipKey membershipKey1_2 = dc.join(group, networkInterface); - assertEquals(membershipKey1, membershipKey1_2); - - dc.close(); - } - } - - public void test_joinAnySource_multicastLoopOption_IPv4() throws Exception { - test_joinAnySource_multicastLoopOption(ipv4networkInterfaces, GOOD_MULTICAST_IPv4); - } - - public void test_joinAnySource_multicastLoopOption_IPv6() throws Exception { - test_joinAnySource_multicastLoopOption(ipv6networkInterfaces, GOOD_MULTICAST_IPv6); - } - - private void test_joinAnySource_multicastLoopOption( - Iterable<NetworkInterface> networkInterfaces, InetAddress group) throws Exception { - final String message = "Hello, world!"; - - for (NetworkInterface networkInterface : networkInterfaces) { - DatagramChannel dc = DatagramChannel.open(); - configureChannelForReceiving(dc); - dc.bind(null /* leave the OS to determine the port, and use the wildcard address */); - - // Make sure that the sent packets will be sent via the interface we will be joining with. - dc.setOption(StandardSocketOptions.IP_MULTICAST_IF, networkInterface); - dc.join(group, networkInterface); - - // Test with loop on. - dc.setOption(StandardSocketOptions.IP_MULTICAST_LOOP, true /* enable loop */); - - InetSocketAddress localAddress = (InetSocketAddress) dc.getLocalAddress(); - - // Send the datagram. - sendMessage(dc, message, new InetSocketAddress(group, localAddress.getPort())); - - // Receive the datagram. - ByteBuffer recvBuffer = ByteBuffer.allocate(100); - SocketAddress sourceAddress = dc.receive(recvBuffer); - assertNotNull(sourceAddress); - - String recvMessage = new String(recvBuffer.array(), 0, recvBuffer.position()); - assertEquals(message, recvMessage); - - // Turn off loop. - dc.setOption(StandardSocketOptions.IP_MULTICAST_LOOP, false /* enable loopback */); - - // Send another datagram. - recvBuffer.position(0); - sendMessage(dc, message, new InetSocketAddress(group, localAddress.getPort())); - - SocketAddress sourceAddress2 = dc.receive(recvBuffer); - assertNull(sourceAddress2); - - dc.close(); - } - } - - public void testMembershipKeyAccessors_IPv4() throws Exception { - testMembershipKeyAccessors(ipv4networkInterfaces, GOOD_MULTICAST_IPv4); - } - - public void testMembershipKeyAccessors_IPv6() throws Exception { - testMembershipKeyAccessors(ipv6networkInterfaces, GOOD_MULTICAST_IPv6); - } - - private void testMembershipKeyAccessors( - Iterable<NetworkInterface> networkInterfaces, InetAddress group) throws Exception { - for (NetworkInterface networkInterface : networkInterfaces) { - DatagramChannel dc = createReceiverChannel(); - - MembershipKey key = dc.join(group, networkInterface); - assertSame(dc, key.channel()); - assertSame(group, key.group()); - assertTrue(key.isValid()); - assertSame(networkInterface, key.networkInterface()); - assertNull(key.sourceAddress()); - } - } - - public void test_dropAnySource_twice_IPv4() throws Exception { - test_dropAnySource_twice(ipv4networkInterfaces, GOOD_MULTICAST_IPv4); - } - - public void test_dropAnySource_twice_IPv6() throws Exception { - test_dropAnySource_twice(ipv6networkInterfaces, GOOD_MULTICAST_IPv6); - } - - private void test_dropAnySource_twice( - Iterable<NetworkInterface> networkInterfaces, InetAddress group) - throws Exception { - for (NetworkInterface networkInterface : networkInterfaces) { - DatagramChannel dc = createReceiverChannel(); - MembershipKey membershipKey = dc.join(group, networkInterface); - - assertTrue(membershipKey.isValid()); - membershipKey.drop(); - assertFalse(membershipKey.isValid()); - - // Try to leave a group we are no longer a member of. It should do nothing. - membershipKey.drop(); - - dc.close(); - } - } - - public void test_close_invalidatesMembershipKey() throws Exception { - DatagramChannel dc = createReceiverChannel(); - MembershipKey membershipKey = dc.join(GOOD_MULTICAST_IPv4, ipv4networkInterface); - - assertTrue(membershipKey.isValid()); - - dc.close(); - - assertFalse(membershipKey.isValid()); - } - - public void test_block_null() throws Exception { - DatagramChannel dc = createReceiverChannel(); - MembershipKey membershipKey = dc.join(GOOD_MULTICAST_IPv4, ipv4networkInterface); - try { - membershipKey.block(null); - fail(); - } catch (NullPointerException expected) { - } - - dc.close(); - } - - public void test_block_mixedAddressTypes_IPv4() throws Exception { - test_block_illegalArgument(ipv4networkInterfaces, GOOD_MULTICAST_IPv4, UNICAST_IPv6_1); - } - - public void test_block_mixedAddressTypes_IPv6() throws Exception { - test_block_illegalArgument(ipv6networkInterfaces, GOOD_MULTICAST_IPv6, UNICAST_IPv4_1); - } - - private void test_block_illegalArgument( - Iterable<NetworkInterface> networkInterfaces, InetAddress groupAddress, - InetAddress badBlockAddress) throws Exception { - - for (NetworkInterface networkInterface : networkInterfaces) { - DatagramChannel dc = createReceiverChannel(); - MembershipKey membershipKey = dc.join(groupAddress, networkInterface); - try { - membershipKey.block(badBlockAddress); - fail(); - } catch (IllegalArgumentException expected) { - } - - dc.close(); - } - } - - public void test_block_cannotBlockWithSourceSpecificMembership() throws Exception { - DatagramChannel dc = createReceiverChannel(); - MembershipKey membershipKey = - dc.join(GOOD_MULTICAST_IPv4, ipv4networkInterface, UNICAST_IPv4_1); - try { - membershipKey.block(UNICAST_IPv4_2); - fail(); - } catch (IllegalStateException expected) { - } - - dc.close(); - } - - public void test_block_multipleBlocksIgnored() throws Exception { - DatagramChannel dc = createReceiverChannel(); - MembershipKey membershipKey = dc.join(GOOD_MULTICAST_IPv4, ipv4networkInterface); - membershipKey.block(UNICAST_IPv4_1); - - MembershipKey membershipKey2 = membershipKey.block(UNICAST_IPv4_1); - assertSame(membershipKey2, membershipKey); - - dc.close(); - } - - public void test_block_wildcardAddress() throws Exception { - DatagramChannel dc = createReceiverChannel(); - MembershipKey membershipKey = dc.join(GOOD_MULTICAST_IPv4, ipv4networkInterface); - try { - membershipKey.block(WILDCARD_IPv4); - fail(); - } catch (IllegalArgumentException expected) { - } - - dc.close(); - } - - public void test_unblock_multipleUnblocksFail() throws Exception { - DatagramChannel dc = createReceiverChannel(); - MembershipKey membershipKey = dc.join(GOOD_MULTICAST_IPv4, ipv4networkInterface); - - try { - membershipKey.unblock(UNICAST_IPv4_1); - fail(); - } catch (IllegalStateException expected) { - } - - assertTrue(membershipKey.isValid()); - - membershipKey.block(UNICAST_IPv4_1); - membershipKey.unblock(UNICAST_IPv4_1); - - try { - membershipKey.unblock(UNICAST_IPv4_1); - fail(); - } catch (IllegalStateException expected) { - } - - dc.close(); - } - - public void test_unblock_null() throws Exception { - DatagramChannel dc = createReceiverChannel(); - MembershipKey membershipKey = dc.join(GOOD_MULTICAST_IPv4, ipv4networkInterface); - membershipKey.block(UNICAST_IPv4_1); - - try { - membershipKey.unblock(null); - fail(); - } catch (IllegalStateException expected) { - // Either of these exceptions are fine. - } catch (NullPointerException expected) { - // Either of these exception are fine. - } - - dc.close(); - } - - public void test_unblock_mixedAddressTypes_IPv4() throws Exception { - DatagramChannel dc = createReceiverChannel(); - MembershipKey membershipKey = dc.join(GOOD_MULTICAST_IPv4, ipv4networkInterface); - try { - membershipKey.unblock(UNICAST_IPv6_1); - fail(); - } catch (IllegalStateException expected) { - // Either of these exceptions are fine. - } catch (IllegalArgumentException expected) { - // Either of these exceptions are fine. - } - - dc.close(); - } - - public void test_unblock_mixedAddressTypes_IPv6() throws Exception { - DatagramChannel dc = createReceiverChannel(); - MembershipKey membershipKey = dc.join(GOOD_MULTICAST_IPv6, ipv6networkInterface); - try { - membershipKey.unblock(UNICAST_IPv4_1); - fail(); - } catch (IllegalStateException expected) { - // Either of these exceptions are fine. - } catch (IllegalArgumentException expected) { - // Either of these exceptions are fine. - } - - dc.close(); - } - - /** Checks that block() works when the receiver is bound to the multicast group address */ - public void test_block_filtersAsExpected_groupBind_IPv4() throws Exception { - for (NetworkInterface networkInterface : ipv4networkInterfaces) { - InetAddress ipv4LocalAddress = getLocalIpv4Address(networkInterface); - test_block_filtersAsExpected( - networkInterface, - ipv4LocalAddress /* senderBindAddress */, - GOOD_MULTICAST_IPv4 /* receiverBindAddress */, - GOOD_MULTICAST_IPv4 /* groupAddress */); - } - } - - /** Checks that block() works when the receiver is bound to the multicast group address */ - public void test_block_filtersAsExpected_groupBind_IPv6() throws Exception { - for (NetworkInterface networkInterface : ipv6networkInterfaces) { - InetAddress ipv6LocalAddress = getLocalIpv6Address(networkInterface); - test_block_filtersAsExpected( - networkInterface, - ipv6LocalAddress /* senderBindAddress */, - GOOD_MULTICAST_IPv6 /* receiverBindAddress */, - GOOD_MULTICAST_IPv6 /* groupAddress */); - } - } - - /** Checks that block() works when the receiver is bound to the "any" address */ - public void test_block_filtersAsExpected_anyBind_IPv4() throws Exception { - for (NetworkInterface networkInterface : ipv4networkInterfaces) { - InetAddress ipv4LocalAddress = getLocalIpv4Address(networkInterface); - test_block_filtersAsExpected( - networkInterface, - ipv4LocalAddress /* senderBindAddress */, - WILDCARD_IPv4 /* receiverBindAddress */, - GOOD_MULTICAST_IPv4 /* groupAddress */); - } - } - - /** Checks that block() works when the receiver is bound to the "any" address */ - public void test_block_filtersAsExpected_anyBind_IPv6() throws Exception { - for (NetworkInterface networkInterface : ipv6networkInterfaces) { - InetAddress ipv6LocalAddress = getLocalIpv6Address(networkInterface); - test_block_filtersAsExpected( - networkInterface, - ipv6LocalAddress /* senderBindAddress */, - WILDCARD_IPv6 /* receiverBindAddress */, - GOOD_MULTICAST_IPv6 /* groupAddress */); - } - } - - private void test_block_filtersAsExpected( - NetworkInterface networkInterface, InetAddress senderBindAddress, - InetAddress receiverBindAddress, InetAddress groupAddress) throws Exception { - - DatagramChannel sendingChannel = DatagramChannel.open(); - // In order to block a sender the sender's address must be known. The sendingChannel is - // explicitly bound to a known, non-loopback address. - sendingChannel.bind(new InetSocketAddress(senderBindAddress, 0)); - InetSocketAddress sendingAddress = (InetSocketAddress) sendingChannel.getLocalAddress(); - - DatagramChannel receivingChannel = DatagramChannel.open(); - configureChannelForReceiving(receivingChannel); - receivingChannel.bind( - new InetSocketAddress(receiverBindAddress, 0) /* local port left to the OS to determine */); - InetSocketAddress localReceivingAddress = - (InetSocketAddress) receivingChannel.getLocalAddress(); - InetSocketAddress groupSocketAddress = - new InetSocketAddress(groupAddress, localReceivingAddress.getPort()); - MembershipKey membershipKey = - receivingChannel.join(groupSocketAddress.getAddress(), networkInterface); - - ByteBuffer receiveBuffer = ByteBuffer.allocate(10); - - // Send a message. It should be received. - String msg1 = "Hello1"; - sendMessage(sendingChannel, msg1, groupSocketAddress); - InetSocketAddress sourceAddress1 = (InetSocketAddress) receivingChannel.receive(receiveBuffer); - assertEquals(sendingAddress, sourceAddress1); - assertEquals(msg1, new String(receiveBuffer.array(), 0, receiveBuffer.position())); - - // Now block the sender. - membershipKey.block(sendingAddress.getAddress()); - - // Send a message. It should be filtered. - String msg2 = "Hello2"; - sendMessage(sendingChannel, msg2, groupSocketAddress); - receiveBuffer.position(0); - InetSocketAddress sourceAddress2 = (InetSocketAddress) receivingChannel.receive(receiveBuffer); - assertNull(sourceAddress2); - - // Now unblock the sender. - membershipKey.unblock(sendingAddress.getAddress()); - - // Send a message. It should be received. - String msg3 = "Hello3"; - sendMessage(sendingChannel, msg3, groupSocketAddress); - receiveBuffer.position(0); - InetSocketAddress sourceAddress3 = (InetSocketAddress) receivingChannel.receive(receiveBuffer); - assertEquals(sourceAddress3, sendingAddress); - assertEquals(msg3, new String(receiveBuffer.array(), 0, receiveBuffer.position())); - - sendingChannel.close(); - receivingChannel.close(); - } - - public void test_joinSourceSpecific_nullGroupAddress() throws Exception { - DatagramChannel dc = createReceiverChannel(); - try { - dc.join(null, ipv4networkInterface, UNICAST_IPv4_1); - fail(); - } catch (NullPointerException expected) { - } - dc.close(); - } - - public void test_joinSourceSpecific_afterClose() throws Exception { - DatagramChannel dc = createReceiverChannel(); - dc.close(); - try { - dc.join(GOOD_MULTICAST_IPv4, ipv4networkInterface, UNICAST_IPv4_1); - fail(); - } catch (ClosedChannelException expected) { - } - } - - public void test_joinSourceSpecific_nullNetworkInterface() throws Exception { - DatagramChannel dc = createReceiverChannel(); - try { - dc.join(GOOD_MULTICAST_IPv4, null, UNICAST_IPv4_1); - fail(); - } catch (NullPointerException expected) { - } - dc.close(); - } - - public void test_joinSourceSpecific_nonMulticastGroupAddress_IPv4() throws Exception { - DatagramChannel dc = createReceiverChannel(); - try { - dc.join(UNICAST_IPv4_1, ipv4networkInterface, UNICAST_IPv4_1); - fail(); - } catch (IllegalArgumentException expected) { - } - dc.close(); - } - - public void test_joinSourceSpecific_nonMulticastGroupAddress_IPv6() throws Exception { - DatagramChannel dc = createReceiverChannel(); - try { - dc.join(UNICAST_IPv6_1, ipv6networkInterface, UNICAST_IPv6_1); - fail(); - } catch (IllegalArgumentException expected) { - } - dc.close(); - } - - public void test_joinSourceSpecific_nullSourceAddress_IPv4() throws Exception { - DatagramChannel dc = createReceiverChannel(); - try { - dc.join(GOOD_MULTICAST_IPv4, ipv4networkInterface, null); - fail(); - } catch (NullPointerException expected) { - } - dc.close(); - } - - public void test_joinSourceSpecific_nullSourceAddress_IPv6() throws Exception { - DatagramChannel dc = createReceiverChannel(); - try { - dc.join(GOOD_MULTICAST_IPv6, ipv6networkInterface, null); - fail(); - } catch (NullPointerException expected) { - } - dc.close(); - } - - public void test_joinSourceSpecific_mixedAddressTypes() throws Exception { - DatagramChannel dc = createReceiverChannel(); - try { - dc.join(GOOD_MULTICAST_IPv4, ipv4networkInterface, UNICAST_IPv6_1); - fail(); - } catch (IllegalArgumentException expected) { - } - try { - dc.join(GOOD_MULTICAST_IPv6, ipv6networkInterface, UNICAST_IPv4_1); - fail(); - } catch (IllegalArgumentException expected) { - } - dc.close(); - } - - public void test_joinSourceSpecific_nonUnicastSourceAddress_IPv4() throws Exception { - DatagramChannel dc = createReceiverChannel(); - try { - dc.join(GOOD_MULTICAST_IPv4, ipv4networkInterface, BAD_MULTICAST_IPv4); - fail(); - } catch (IllegalArgumentException expected) { - } - dc.close(); - } - - public void test_joinSourceSpecific_nonUnicastSourceAddress_IPv6() throws Exception { - DatagramChannel dc = createReceiverChannel(); - try { - dc.join(GOOD_MULTICAST_IPv6, ipv6networkInterface, BAD_MULTICAST_IPv6); - fail(); - } catch (IllegalArgumentException expected) { - } - dc.close(); - } - - public void test_joinSourceSpecific_multipleSourceAddressLimit() throws Exception { - DatagramChannel dc = createReceiverChannel(); - for (byte i = 1; i <= 20; i++) { - InetAddress sourceAddress = Inet4Address.getByAddress(new byte[] { 10, 0, 0, i}); - try { - dc.join(GOOD_MULTICAST_IPv4, ipv4networkInterface, sourceAddress); - } catch (SocketException e) { - // There is a limit, that's ok according to the RI docs. For this test a lower bound of 10 - // is used, which appears to be the default linux limit. See /proc/sys/net/ipv4/igmp_max_msf - assertTrue(i > 10); - break; - } - } - - dc.close(); - } - - /** - * Checks that a source-specific join() works when the receiver is bound to the multicast group - * address - */ - public void test_joinSourceSpecific_groupBind_IPv4() throws Exception { - for (NetworkInterface networkInterface : ipv4networkInterfaces) { - InetAddress ipv4LocalAddress = getLocalIpv4Address(networkInterface); - test_joinSourceSpecific( - networkInterface, - ipv4LocalAddress /* senderBindAddress */, - GOOD_MULTICAST_IPv4 /* receiverBindAddress */, - GOOD_MULTICAST_IPv4 /* groupAddress */, - UNICAST_IPv4_1 /* badSenderAddress */); - } - } - - /** - * Checks that a source-specific join() works when the receiver is bound to the multicast group - * address - */ - public void test_joinSourceSpecific_groupBind_IPv6() throws Exception { - for (NetworkInterface networkInterface : ipv6networkInterfaces) { - InetAddress ipv6LocalAddress = getLocalIpv6Address(networkInterface); - test_joinSourceSpecific( - networkInterface, - ipv6LocalAddress /* senderBindAddress */, - GOOD_MULTICAST_IPv6 /* receiverBindAddress */, - GOOD_MULTICAST_IPv6 /* groupAddress */, - UNICAST_IPv6_1 /* badSenderAddress */); - } - } - - /** Checks that a source-specific join() works when the receiver is bound to the "any" address */ - public void test_joinSourceSpecific_anyBind_IPv4() throws Exception { - for (NetworkInterface networkInterface : ipv4networkInterfaces) { - InetAddress ipv4LocalAddress = getLocalIpv4Address(networkInterface); - test_joinSourceSpecific( - networkInterface, - ipv4LocalAddress /* senderBindAddress */, - WILDCARD_IPv4 /* receiverBindAddress */, - GOOD_MULTICAST_IPv4 /* groupAddress */, - UNICAST_IPv4_1 /* badSenderAddress */); - } - } - - /** Checks that a source-specific join() works when the receiver is bound to the "any" address */ - public void test_joinSourceSpecific_anyBind_IPv6() throws Exception { - for (NetworkInterface networkInterface : ipv6networkInterfaces) { - InetAddress ipv6LocalAddress = getLocalIpv6Address(networkInterface); - test_joinSourceSpecific( - networkInterface, - ipv6LocalAddress /* senderBindAddress */, - WILDCARD_IPv6 /* receiverBindAddress */, - GOOD_MULTICAST_IPv6 /* groupAddress */, - UNICAST_IPv6_1 /* badSenderAddress */); - } - } - - /** - * Checks that the source-specific membership is correctly source-filtered. - * - * @param networkInterface the network interface to use when joining - * @param senderBindAddress the address to bind the sender socket to - * @param receiverBindAddress the address to bind the receiver socket to - * @param groupAddress the group address to join - * @param badSenderAddress a unicast address to join to perform a negative test - */ - private void test_joinSourceSpecific( - NetworkInterface networkInterface, InetAddress senderBindAddress, - InetAddress receiverBindAddress, InetAddress groupAddress, InetAddress badSenderAddress) - throws Exception { - DatagramChannel sendingChannel = DatagramChannel.open(); - // In order to be source-specific the sender's address must be known. The sendingChannel is - // explicitly bound to a known, non-loopback address. - sendingChannel.bind(new InetSocketAddress(senderBindAddress, 0)); - InetSocketAddress sendingAddress = (InetSocketAddress) sendingChannel.getLocalAddress(); - - DatagramChannel receivingChannel = DatagramChannel.open(); - configureChannelForReceiving(receivingChannel); - receivingChannel.bind( - new InetSocketAddress(receiverBindAddress, 0) /* local port left to the OS to determine */); - - InetSocketAddress localReceivingAddress = - (InetSocketAddress) receivingChannel.getLocalAddress(); - InetSocketAddress groupSocketAddress = - new InetSocketAddress(groupAddress, localReceivingAddress.getPort()); - MembershipKey membershipKey1 = receivingChannel - .join(groupSocketAddress.getAddress(), networkInterface, senderBindAddress); - - ByteBuffer receiveBuffer = ByteBuffer.allocate(10); - - // Send a message. It should be received. - String msg1 = "Hello1"; - sendMessage(sendingChannel, msg1, groupSocketAddress); - InetSocketAddress sourceAddress1 = (InetSocketAddress) receivingChannel.receive(receiveBuffer); - assertEquals(sourceAddress1, sendingAddress); - assertEquals(msg1, new String(receiveBuffer.array(), 0, receiveBuffer.position())); - - membershipKey1.drop(); - - receivingChannel.join(groupSocketAddress.getAddress(), networkInterface, badSenderAddress); - - // Send a message. It should not be received. - String msg2 = "Hello2"; - sendMessage(sendingChannel, msg2, groupSocketAddress); - InetSocketAddress sourceAddress2 = (InetSocketAddress) receivingChannel.receive(receiveBuffer); - assertNull(sourceAddress2); - - receivingChannel.close(); - sendingChannel.close(); - } - - public void test_dropSourceSpecific_twice_IPv4() throws Exception { - for (NetworkInterface networkInterface : ipv4networkInterfaces) { - test_dropSourceSpecific_twice( - networkInterface, - GOOD_MULTICAST_IPv4 /* groupAddress */, - UNICAST_IPv4_1 /* sourceAddress */); - } - } - - public void test_dropSourceSpecific_twice_IPv6() throws Exception { - for (NetworkInterface networkInterface : ipv6networkInterfaces) { - test_dropSourceSpecific_twice( - networkInterface, - GOOD_MULTICAST_IPv6 /* groupAddress */, - UNICAST_IPv6_1 /* sourceAddress */); - } - } - - private void test_dropSourceSpecific_twice( - NetworkInterface networkInterface, InetAddress groupAddress, InetAddress sourceAddress) - throws Exception { - DatagramChannel dc = createReceiverChannel(); - MembershipKey membershipKey = dc.join(groupAddress, networkInterface, sourceAddress); - - assertTrue(membershipKey.isValid()); - membershipKey.drop(); - assertFalse(membershipKey.isValid()); - - // Try to leave a group we are no longer a member of. It should do nothing. - membershipKey.drop(); - - dc.close(); - } - - public void test_dropSourceSpecific_sourceKeysAreIndependent_IPv4() throws Exception { - for (NetworkInterface networkInterface : ipv4networkInterfaces) { - test_dropSourceSpecific_sourceKeysAreIndependent( - networkInterface, - GOOD_MULTICAST_IPv4 /* groupAddress */, - UNICAST_IPv4_1 /* sourceAddress1 */, - UNICAST_IPv4_2 /* sourceAddress2 */); - } - } - - public void test_dropSourceSpecific_sourceKeysAreIndependent_IPv6() throws Exception { - for (NetworkInterface networkInterface : ipv6networkInterfaces) { - test_dropSourceSpecific_sourceKeysAreIndependent( - networkInterface, - GOOD_MULTICAST_IPv6 /* groupAddress */, - UNICAST_IPv6_1 /* sourceAddress1 */, - UNICAST_IPv6_2 /* sourceAddress2 */); - } - } - - private void test_dropSourceSpecific_sourceKeysAreIndependent( - NetworkInterface networkInterface, InetAddress groupAddress, InetAddress sourceAddress1, - InetAddress sourceAddress2) - throws Exception { - DatagramChannel dc = createReceiverChannel(); - MembershipKey membershipKey1 = dc.join(groupAddress, networkInterface, sourceAddress1); - MembershipKey membershipKey2 = dc.join(groupAddress, networkInterface, sourceAddress2); - assertFalse(membershipKey1.equals(membershipKey2)); - assertTrue(membershipKey1.isValid()); - assertTrue(membershipKey2.isValid()); - - membershipKey1.drop(); - - assertFalse(membershipKey1.isValid()); - assertTrue(membershipKey2.isValid()); - - dc.close(); - } - - public void test_drop_keyBehaviorAfterDrop() throws Exception { - DatagramChannel dc = createReceiverChannel(); - MembershipKey membershipKey = - dc.join(GOOD_MULTICAST_IPv4, ipv4networkInterface, UNICAST_IPv4_1); - membershipKey.drop(); - assertFalse(membershipKey.isValid()); - - try { - membershipKey.block(UNICAST_IPv4_1); - } catch (IllegalStateException expected) { - } - - try { - membershipKey.unblock(UNICAST_IPv4_1); - } catch (IllegalStateException expected) { - } - - assertSame(dc, membershipKey.channel()); - assertSame(GOOD_MULTICAST_IPv4, membershipKey.group()); - assertSame(UNICAST_IPv4_1, membershipKey.sourceAddress()); - assertSame(ipv4networkInterface, membershipKey.networkInterface()); - } - - private static DatagramChannel createReceiverChannel() throws Exception { - DatagramChannel dc = DatagramChannel.open(); - configureChannelForReceiving(dc); - dc.bind(null /* leave the OS to determine the port, and use the wildcard address */); - return dc; - } - - private static void configureChannelForReceiving(DatagramChannel receivingChannel) - throws Exception { - - // NOTE: At the time of writing setSoTimeout() has no effect in the RI, making these tests hang - // if the channel is in blocking mode. - receivingChannel.socket().setSoTimeout(200); - receivingChannel.configureBlocking(true); - // configureBlocking(false) can be used instead in the RI and we rely on the network to the - // local host being instantaneous. - // receivingChannel.configureBlocking(false); - } - - private static boolean willWorkForMulticast(NetworkInterface iface) throws IOException { - return iface.isUp() - // Typically loopback interfaces do not support multicast, but they are ruled out - // explicitly here anyway. - && !iface.isLoopback() && iface.supportsMulticast() - && iface.getInetAddresses().hasMoreElements(); - } - - private static void sendMessage( - InetAddress targetGroup, int targetPort, String msg, NetworkInterface sendingInterface) - throws IOException { - // Any datagram socket can send to a group. It does not need to have joined the group. - DatagramChannel dc = DatagramChannel.open(); - dc.setOption(StandardSocketOptions.IP_MULTICAST_IF, sendingInterface); - sendMessage(dc, msg, new InetSocketAddress(targetGroup, targetPort)); - dc.close(); - } - - private static void sendMessage( - DatagramChannel sendingChannel, String msg, InetSocketAddress targetAddress) - throws IOException { - - ByteBuffer sendBuffer = ByteBuffer.wrap(msg.getBytes()); - sendingChannel.send(sendBuffer, targetAddress); - } - - private static InetAddress getLocalIpv4Address(NetworkInterface networkInterface) { - for (InterfaceAddress interfaceAddress : networkInterface.getInterfaceAddresses()) { - if (interfaceAddress.getAddress() instanceof Inet4Address) { - return interfaceAddress.getAddress(); - } - } - throw new AssertionFailedError("Unable to find local IPv4 address for " + networkInterface); - } - - private static InetAddress getLocalIpv6Address(NetworkInterface networkInterface) { - for (InterfaceAddress interfaceAddress : networkInterface.getInterfaceAddresses()) { - if (interfaceAddress.getAddress() instanceof Inet6Address) { - return interfaceAddress.getAddress(); - } - } - throw new AssertionFailedError("Unable to find local IPv6 address for " + networkInterface); - } - -} diff --git a/luni/src/test/java/libcore/java/nio/channels/DatagramChannelTest.java b/luni/src/test/java/libcore/java/nio/channels/DatagramChannelTest.java index cd4bb22..efcfece 100644 --- a/luni/src/test/java/libcore/java/nio/channels/DatagramChannelTest.java +++ b/luni/src/test/java/libcore/java/nio/channels/DatagramChannelTest.java @@ -23,9 +23,6 @@ import java.net.Inet6Address; import java.net.InetAddress; import java.net.InetSocketAddress; import java.net.NetworkInterface; -import java.net.SocketException; -import java.net.SocketOption; -import java.net.StandardSocketOptions; import java.nio.ByteBuffer; import java.nio.channels.ClosedChannelException; import java.nio.channels.DatagramChannel; @@ -61,7 +58,7 @@ public class DatagramChannelTest extends junit.framework.TestCase { DatagramChannel dc = DatagramChannel.open(); try { dc.configureBlocking(false); - dc.bind(null); + dc.socket().bind(null); // Should return immediately, since we're non-blocking. assertNull(dc.receive(ByteBuffer.allocate(2048))); } finally { @@ -72,8 +69,6 @@ public class DatagramChannelTest extends junit.framework.TestCase { public void testInitialState() throws Exception { DatagramChannel dc = DatagramChannel.open(); try { - assertNull(dc.getLocalAddress()); - DatagramSocket socket = dc.socket(); assertFalse(socket.isBound()); assertFalse(socket.getBroadcast()); @@ -93,408 +88,20 @@ public class DatagramChannelTest extends junit.framework.TestCase { } } - public void test_supportedOptions() throws Exception { - DatagramChannel dc = DatagramChannel.open(); - Set<SocketOption<?>> options = dc.supportedOptions(); - - // Probe some values. This is not intended to be complete. - assertTrue(options.contains(StandardSocketOptions.SO_REUSEADDR)); - assertFalse(options.contains(StandardSocketOptions.TCP_NODELAY)); - } - - public void test_getOption_unsupportedOption() throws Exception { - DatagramChannel dc = DatagramChannel.open(); - try { - dc.getOption(StandardSocketOptions.TCP_NODELAY); - fail(); - } catch (UnsupportedOperationException expected) {} - - dc.close(); - } - - public void test_getOption_afterClose() throws Exception { - DatagramChannel dc = DatagramChannel.open(); - dc.close(); - - try { - dc.getOption(StandardSocketOptions.SO_RCVBUF); - fail(); - } catch (ClosedChannelException expected) {} - } - - public void test_setOption_afterClose() throws Exception { - DatagramChannel dc = DatagramChannel.open(); - dc.close(); - - try { - dc.setOption(StandardSocketOptions.SO_RCVBUF, 1234); - fail(); - } catch (ClosedChannelException expected) {} - } - - public void test_getOption_SO_RCVBUF_defaults() throws Exception { - DatagramChannel dc = DatagramChannel.open(); - - int value = dc.getOption(StandardSocketOptions.SO_RCVBUF); - assertTrue(value > 0); - assertEquals(value, dc.socket().getReceiveBufferSize()); - - dc.close(); - } - - public void test_setOption_SO_RCVBUF_afterOpen() throws Exception { - DatagramChannel dc = DatagramChannel.open(); - - trySetReceiveBufferSizeOption(dc); - - dc.close(); - } - - private static void trySetReceiveBufferSizeOption(DatagramChannel dc) throws IOException { - int initialValue = dc.getOption(StandardSocketOptions.SO_RCVBUF); - try { - dc.setOption(StandardSocketOptions.SO_RCVBUF, -1); - fail(); - } catch (IllegalArgumentException expected) {} - int actualValue = dc.getOption(StandardSocketOptions.SO_RCVBUF); - assertEquals(initialValue, actualValue); - assertEquals(initialValue, dc.socket().getReceiveBufferSize()); - - int newBufferSize = initialValue - 1; - dc.setOption(StandardSocketOptions.SO_RCVBUF, newBufferSize); - actualValue = dc.getOption(StandardSocketOptions.SO_RCVBUF); - // The Linux Kernel actually doubles the value it is given and may choose to ignore it. - // This assertion may be brittle. - assertTrue(actualValue != initialValue); - assertEquals(actualValue, dc.socket().getReceiveBufferSize()); - } - - public void test_getOption_SO_SNDBUF_defaults() throws Exception { - DatagramChannel dc = DatagramChannel.open(); - - int value = dc.getOption(StandardSocketOptions.SO_SNDBUF); - assertTrue(value > 0); - assertEquals(value, dc.socket().getSendBufferSize()); - - dc.close(); - } - - public void test_setOption_SO_SNDBUF_afterOpen() throws Exception { - DatagramChannel dc = DatagramChannel.open(); - - trySetSendBufferSizeOption(dc); - - dc.close(); - } - - private static void trySetSendBufferSizeOption(DatagramChannel dc) throws IOException { - int initialValue = dc.getOption(StandardSocketOptions.SO_SNDBUF); - try { - dc.setOption(StandardSocketOptions.SO_SNDBUF, -1); - fail(); - } catch (IllegalArgumentException expected) {} - int actualValue = dc.getOption(StandardSocketOptions.SO_SNDBUF); - assertEquals(initialValue, actualValue); - assertEquals(initialValue, dc.socket().getSendBufferSize()); - - int newBufferSize = initialValue - 1; - dc.setOption(StandardSocketOptions.SO_SNDBUF, newBufferSize); - actualValue = dc.getOption(StandardSocketOptions.SO_SNDBUF); - // The Linux Kernel actually doubles the value it is given and may choose to ignore it. - // This assertion may be brittle. - assertTrue(actualValue != initialValue); - assertEquals(actualValue, dc.socket().getSendBufferSize()); - } - - public void test_getOption_IP_MULTICAST_IF_defaults() throws Exception { - DatagramChannel dc = DatagramChannel.open(); - - NetworkInterface networkInterface = dc.getOption(StandardSocketOptions.IP_MULTICAST_IF); - assertNull(networkInterface); - - dc.close(); - } - - public void test_getOption_IP_MULTICAST_IF_nullCheck() throws Exception { - DatagramChannel dc = DatagramChannel.open(); - try { - dc.setOption(StandardSocketOptions.IP_MULTICAST_IF, null); - fail(); - } catch (IllegalArgumentException expected) {} - - dc.close(); - } - - public void test_setOption_IP_MULTICAST_IF_afterOpen() throws Exception { - DatagramChannel dc = DatagramChannel.open(); - - Enumeration<NetworkInterface> networkInterfaces = NetworkInterface.getNetworkInterfaces(); - assertTrue(networkInterfaces.hasMoreElements()); - while (networkInterfaces.hasMoreElements()) { - trySetNetworkInterfaceOption(dc, networkInterfaces.nextElement()); - } - - dc.close(); - } - - public void test_setOption_IP_MULTICAST_IF_afterBind() throws Exception { - DatagramChannel dc = DatagramChannel.open(); - dc.bind(new InetSocketAddress(Inet4Address.getLoopbackAddress(), 0)); - - Enumeration<NetworkInterface> networkInterfaces = NetworkInterface.getNetworkInterfaces(); - assertTrue(networkInterfaces.hasMoreElements()); - while (networkInterfaces.hasMoreElements()) { - trySetNetworkInterfaceOption(dc, networkInterfaces.nextElement()); - } - - dc.close(); - } - - private static void trySetNetworkInterfaceOption( - DatagramChannel dc, NetworkInterface networkInterface) throws IOException { - - NetworkInterface initialValue = dc.getOption(StandardSocketOptions.IP_MULTICAST_IF); - try { - dc.setOption(StandardSocketOptions.IP_MULTICAST_IF, null); - fail(); - } catch (IllegalArgumentException expected) {} - assertEquals(initialValue, dc.getOption(StandardSocketOptions.IP_MULTICAST_IF)); - - dc.setOption(StandardSocketOptions.IP_MULTICAST_IF, networkInterface); - NetworkInterface actualValue = - dc.getOption(StandardSocketOptions.IP_MULTICAST_IF); - assertEquals(networkInterface, actualValue); - } - - public void test_getOption_IP_MULTICAST_LOOP_defaults() throws Exception { - DatagramChannel dc = DatagramChannel.open(); - - assertTrue(dc.getOption(StandardSocketOptions.IP_MULTICAST_LOOP)); - - dc.close(); - } - - public void test_getOption_IP_MULTICAST_LOOP_nullCheck() throws Exception { - DatagramChannel dc = DatagramChannel.open(); - try { - dc.setOption(StandardSocketOptions.IP_MULTICAST_LOOP, null); - fail(); - } catch (IllegalArgumentException expected) {} - - dc.close(); - } - - public void test_setOption_IP_MULTICAST_LOOP_afterOpen() throws Exception { - DatagramChannel dc = DatagramChannel.open(); - assertTrue(dc.getOption(StandardSocketOptions.IP_MULTICAST_LOOP)); - - dc.setOption(StandardSocketOptions.IP_MULTICAST_LOOP, false); - assertFalse(dc.getOption(StandardSocketOptions.IP_MULTICAST_LOOP)); - - dc.close(); - } - - public void test_setOption_IP_MULTICAST_LOOP_afterBind() throws Exception { - DatagramChannel dc = DatagramChannel.open(); - dc.bind(new InetSocketAddress(Inet4Address.getLoopbackAddress(), 0)); - - assertTrue(dc.getOption(StandardSocketOptions.IP_MULTICAST_LOOP)); - - dc.setOption(StandardSocketOptions.IP_MULTICAST_LOOP, false); - assertFalse(dc.getOption(StandardSocketOptions.IP_MULTICAST_LOOP)); - - dc.close(); - } - - public void test_getOption_IP_MULTICAST_TTL_defaults() throws Exception { - DatagramChannel dc = DatagramChannel.open(); - - int value = dc.getOption(StandardSocketOptions.IP_MULTICAST_TTL); - assertEquals(1, value); - - dc.close(); - } - - public void test_setOption_IP_MULTICAST_TTL_afterOpen() throws Exception { - DatagramChannel dc = DatagramChannel.open(); - - trySetMulticastTtlOption(dc); - - dc.close(); - } - - private static void trySetMulticastTtlOption(DatagramChannel dc) throws IOException { - int initialValue = dc.getOption(StandardSocketOptions.IP_MULTICAST_TTL); - try { - dc.setOption(StandardSocketOptions.IP_MULTICAST_TTL, -1); - fail(); - } catch (IllegalArgumentException expected) {} - int actualValue = dc.getOption(StandardSocketOptions.IP_MULTICAST_TTL); - assertEquals(initialValue, actualValue); - - int newTtl = initialValue + 1; - dc.setOption(StandardSocketOptions.IP_MULTICAST_TTL, newTtl); - actualValue = dc.getOption(StandardSocketOptions.IP_MULTICAST_TTL); - assertEquals(newTtl, actualValue); - } - - public void test_setOption_IP_MULTICAST_TTL_afterBind() throws Exception { - DatagramChannel dc = DatagramChannel.open(); - dc.bind(null); - - trySetMulticastTtlOption(dc); - - dc.close(); - } - - public void test_getOption_SO_BROADCAST_defaults() throws Exception { - DatagramChannel dc = DatagramChannel.open(); - - assertFalse(dc.getOption(StandardSocketOptions.SO_BROADCAST)); - - dc.close(); - } - - public void test_setOption_SO_BROADCAST_afterOpen() throws Exception { - DatagramChannel dc = DatagramChannel.open(); - - trySetSoBroadcastOption(dc); - - dc.close(); - } - - private static void trySetSoBroadcastOption(DatagramChannel dc) throws IOException { - boolean initialValue = dc.getOption(StandardSocketOptions.SO_BROADCAST); - - dc.setOption(StandardSocketOptions.SO_BROADCAST, !initialValue); - boolean actualValue = dc.getOption(StandardSocketOptions.SO_BROADCAST); - assertEquals(!initialValue, actualValue); - } - - public void test_setOption_SO_BROADCAST_afterBind() throws Exception { - DatagramChannel dc = DatagramChannel.open(); - dc.bind(null); - - trySetSoBroadcastOption(dc); - - dc.close(); - } - - public void test_getOption_IP_TOS_defaults() throws Exception { - DatagramChannel dc = DatagramChannel.open(); - - int value = dc.getOption(StandardSocketOptions.IP_TOS); - assertEquals(0, value); - assertEquals(value, dc.socket().getTrafficClass()); - - dc.close(); - } - - public void test_setOption_IP_TOS_afterOpen() throws Exception { - DatagramChannel dc = DatagramChannel.open(); - - trySetTosOption(dc); - - dc.close(); - } - - private static void trySetTosOption(DatagramChannel dc) throws IOException { - int initialValue = dc.getOption(StandardSocketOptions.IP_TOS); - try { - dc.setOption(StandardSocketOptions.IP_TOS, -1); - fail(); - } catch (IllegalArgumentException expected) {} - assertEquals(initialValue, (int) dc.getOption(StandardSocketOptions.IP_TOS)); - assertEquals(initialValue, dc.socket().getTrafficClass()); - - try { - dc.setOption(StandardSocketOptions.IP_TOS, 256); - fail(); - } catch (IllegalArgumentException expected) {} - assertEquals(initialValue, (int) dc.getOption(StandardSocketOptions.IP_TOS)); - assertEquals(initialValue, dc.socket().getTrafficClass()); - - int newValue = (initialValue + 1) % 255; - dc.setOption(StandardSocketOptions.IP_TOS, newValue); - assertEquals(newValue, (int) dc.getOption(StandardSocketOptions.IP_TOS)); - assertEquals(newValue, dc.socket().getTrafficClass()); - } - - public void test_setOption_IP_TOS_afterBind() throws Exception { - DatagramChannel dc = DatagramChannel.open(); - dc.bind(null); - - trySetTosOption(dc); - - dc.close(); - } - - public void test_getOption_SO_REUSEADDR_defaults() throws Exception { - DatagramChannel dc = DatagramChannel.open(); - - boolean value = dc.getOption(StandardSocketOptions.SO_REUSEADDR); - assertFalse(value); - assertFalse(dc.socket().getReuseAddress()); - - dc.close(); - } - - public void test_setOption_SO_REUSEADDR_afterOpen() throws Exception { - DatagramChannel dc = DatagramChannel.open(); - - boolean initialValue = dc.getOption(StandardSocketOptions.SO_REUSEADDR); - dc.setOption(StandardSocketOptions.SO_REUSEADDR, !initialValue); - assertEquals(!initialValue, (boolean) dc.getOption(StandardSocketOptions.SO_REUSEADDR)); - assertEquals(!initialValue, dc.socket().getReuseAddress()); - - dc.close(); - } - public void test_bind_unresolvedAddress() throws IOException { DatagramChannel dc = DatagramChannel.open(); try { - dc.bind(new InetSocketAddress("unresolvedname", 31415)); + dc.socket().bind(new InetSocketAddress("unresolvedname", 31415)); fail(); - } catch (UnresolvedAddressException expected) { + } catch (IOException expected) { } - assertNull(dc.getLocalAddress()); assertTrue(dc.isOpen()); assertFalse(dc.isConnected()); dc.close(); } - public void test_bind_noReuseAddress() throws Exception { - DatagramChannel dc1 = DatagramChannel.open(); - dc1.setOption(StandardSocketOptions.SO_REUSEADDR, false); - DatagramChannel dc2 = DatagramChannel.open(); - dc1.setOption(StandardSocketOptions.SO_REUSEADDR, false); - - dc1.bind(null); - - try { - dc2.bind(dc1.getLocalAddress()); - fail(); - } catch (IOException expected) {} - - dc1.close(); - dc2.close(); - } - - public void test_bind_withReuseAddress() throws Exception { - DatagramChannel dc1 = DatagramChannel.open(); - dc1.setOption(StandardSocketOptions.SO_REUSEADDR, true); - DatagramChannel dc2 = DatagramChannel.open(); - dc2.setOption(StandardSocketOptions.SO_REUSEADDR, true); - - dc1.bind(null); - dc2.bind(dc1.getLocalAddress()); - - dc1.close(); - dc2.close(); - } - public void test_bind_any_IPv4() throws Exception { test_bind_any(InetAddress.getByName("0.0.0.0")); } @@ -505,12 +112,12 @@ public class DatagramChannelTest extends junit.framework.TestCase { private void test_bind_any(InetAddress bindAddress) throws Exception { DatagramChannel dc = DatagramChannel.open(); - dc.bind(new InetSocketAddress(bindAddress, 0)); + dc.socket().bind(new InetSocketAddress(bindAddress, 0)); assertTrue(dc.isOpen()); assertFalse(dc.isConnected()); - InetSocketAddress actualAddress = (InetSocketAddress) dc.getLocalAddress(); + InetSocketAddress actualAddress = (InetSocketAddress) dc.socket().getLocalSocketAddress(); assertTrue(actualAddress.getAddress().isAnyLocalAddress()); assertTrue(actualAddress.getPort() > 0); @@ -537,18 +144,16 @@ public class DatagramChannelTest extends junit.framework.TestCase { private void test_bind(InetAddress bindAddress) throws IOException { DatagramChannel dc = DatagramChannel.open(); - dc.bind(new InetSocketAddress(bindAddress, 0)); + dc.socket().bind(new InetSocketAddress(bindAddress, 0)); - InetSocketAddress actualAddress = (InetSocketAddress) dc.getLocalAddress(); + InetSocketAddress actualAddress = (InetSocketAddress) dc.socket().getLocalSocketAddress(); assertEquals(bindAddress, actualAddress.getAddress()); assertTrue(actualAddress.getPort() > 0); dc.close(); } - private static InetAddress getNonLoopbackNetworkInterfaceAddress(boolean ipv4) - throws SocketException { - + private static InetAddress getNonLoopbackNetworkInterfaceAddress(boolean ipv4) throws IOException { Enumeration<NetworkInterface> networkInterfaces = NetworkInterface.getNetworkInterfaces(); while (networkInterfaces.hasMoreElements()) { NetworkInterface networkInterface = networkInterfaces.nextElement(); diff --git a/luni/src/test/java/libcore/java/nio/channels/ServerSocketChannelTest.java b/luni/src/test/java/libcore/java/nio/channels/ServerSocketChannelTest.java index e819d82..1178b70 100644 --- a/luni/src/test/java/libcore/java/nio/channels/ServerSocketChannelTest.java +++ b/luni/src/test/java/libcore/java/nio/channels/ServerSocketChannelTest.java @@ -21,8 +21,7 @@ import java.net.InetAddress; import java.net.InetSocketAddress; import java.net.NetworkInterface; import java.net.ServerSocket; -import java.net.SocketOption; -import java.net.StandardSocketOptions; +import java.net.SocketException; import java.nio.channels.ClosedChannelException; import java.nio.channels.ServerSocketChannel; import java.nio.channels.SocketChannel; @@ -36,7 +35,7 @@ public class ServerSocketChannelTest extends junit.framework.TestCase { ServerSocketChannel ssc = ServerSocketChannel.open(); try { ssc.configureBlocking(false); - ssc.bind(null); + ssc.socket().bind(null); // Should return immediately, since we're non-blocking. assertNull(ssc.accept()); } finally { @@ -48,7 +47,7 @@ public class ServerSocketChannelTest extends junit.framework.TestCase { public void test_open_initialState() throws Exception { ServerSocketChannel ssc = ServerSocketChannel.open(); try { - assertNull(ssc.getLocalAddress()); + assertNull(ssc.socket().getLocalSocketAddress()); ServerSocket socket = ssc.socket(); assertFalse(socket.isBound()); @@ -67,12 +66,12 @@ public class ServerSocketChannelTest extends junit.framework.TestCase { public void test_bind_unresolvedAddress() throws IOException { ServerSocketChannel ssc = ServerSocketChannel.open(); try { - ssc.bind(new InetSocketAddress("unresolvedname", 31415)); + ssc.socket().bind(new InetSocketAddress("unresolvedname", 31415)); fail(); - } catch (UnresolvedAddressException expected) { + } catch (SocketException expected) { } - assertNull(ssc.getLocalAddress()); + assertNull(ssc.socket().getLocalSocketAddress()); assertTrue(ssc.isOpen()); ssc.close(); @@ -80,8 +79,8 @@ public class ServerSocketChannelTest extends junit.framework.TestCase { public void test_bind_nullBindsToAll() throws Exception { ServerSocketChannel ssc = ServerSocketChannel.open(); - ssc.bind(null); - InetSocketAddress boundAddress = (InetSocketAddress) ssc.getLocalAddress(); + ssc.socket().bind(null); + InetSocketAddress boundAddress = (InetSocketAddress) ssc.socket().getLocalSocketAddress(); assertTrue(boundAddress.getAddress().isAnyLocalAddress()); assertFalse(boundAddress.getAddress().isLinkLocalAddress()); assertFalse(boundAddress.getAddress().isLoopbackAddress()); @@ -106,8 +105,8 @@ public class ServerSocketChannelTest extends junit.framework.TestCase { public void test_bind_loopback() throws Exception { ServerSocketChannel ssc = ServerSocketChannel.open(); - ssc.bind(new InetSocketAddress(InetAddress.getLoopbackAddress(), 0)); - InetSocketAddress boundAddress = (InetSocketAddress) ssc.getLocalAddress(); + ssc.socket().bind(new InetSocketAddress(InetAddress.getLoopbackAddress(), 0)); + InetSocketAddress boundAddress = (InetSocketAddress) ssc.socket().getLocalSocketAddress(); assertFalse(boundAddress.getAddress().isAnyLocalAddress()); assertFalse(boundAddress.getAddress().isLinkLocalAddress()); assertTrue(boundAddress.getAddress().isLoopbackAddress()); @@ -146,102 +145,4 @@ public class ServerSocketChannelTest extends junit.framework.TestCase { return false; } } - - public void test_supportedOptions() throws Exception { - ServerSocketChannel ssc = ServerSocketChannel.open(); - Set<SocketOption<?>> options = ssc.supportedOptions(); - - // Probe some values. This is not intended to be complete. - assertTrue(options.contains(StandardSocketOptions.SO_REUSEADDR)); - assertFalse(options.contains(StandardSocketOptions.IP_MULTICAST_TTL)); - } - - public void test_getOption_unsupportedOption() throws Exception { - ServerSocketChannel ssc = ServerSocketChannel.open(); - try { - ssc.getOption(StandardSocketOptions.IP_MULTICAST_TTL); - fail(); - } catch (UnsupportedOperationException expected) {} - - ssc.close(); - } - - public void test_getOption_afterClose() throws Exception { - ServerSocketChannel ssc = ServerSocketChannel.open(); - ssc.close(); - - try { - ssc.getOption(StandardSocketOptions.SO_RCVBUF); - fail(); - } catch (ClosedChannelException expected) {} - } - - public void test_setOption_afterClose() throws Exception { - ServerSocketChannel ssc = ServerSocketChannel.open(); - ssc.close(); - - try { - ssc.setOption(StandardSocketOptions.SO_RCVBUF, 1234); - fail(); - } catch (ClosedChannelException expected) {} - } - - public void test_getOption_SO_RCVBUF_defaults() throws Exception { - ServerSocketChannel ssc = ServerSocketChannel.open(); - - int value = ssc.getOption(StandardSocketOptions.SO_RCVBUF); - assertTrue(value > 0); - assertEquals(value, ssc.socket().getReceiveBufferSize()); - - ssc.close(); - } - - public void test_setOption_SO_RCVBUF_afterOpen() throws Exception { - ServerSocketChannel ssc = ServerSocketChannel.open(); - - trySetReceiveBufferSizeOption(ssc); - - ssc.close(); - } - - private static void trySetReceiveBufferSizeOption(ServerSocketChannel ssc) throws IOException { - int initialValue = ssc.getOption(StandardSocketOptions.SO_RCVBUF); - try { - ssc.setOption(StandardSocketOptions.SO_RCVBUF, -1); - fail(); - } catch (IllegalArgumentException expected) {} - int actualValue = ssc.getOption(StandardSocketOptions.SO_RCVBUF); - assertEquals(initialValue, actualValue); - assertEquals(initialValue, ssc.socket().getReceiveBufferSize()); - - int newBufferSize = initialValue - 1; - ssc.setOption(StandardSocketOptions.SO_RCVBUF, newBufferSize); - actualValue = ssc.getOption(StandardSocketOptions.SO_RCVBUF); - // The Linux Kernel actually doubles the value it is given and may choose to ignore it. - // This assertion may be brittle. - assertTrue(actualValue != initialValue); - assertEquals(actualValue, ssc.socket().getReceiveBufferSize()); - } - - public void test_getOption_SO_REUSEADDR_defaults() throws Exception { - ServerSocketChannel ssc = ServerSocketChannel.open(); - - boolean value = ssc.getOption(StandardSocketOptions.SO_REUSEADDR); - assertTrue(value); - assertTrue(ssc.socket().getReuseAddress()); - - ssc.close(); - } - - public void test_setOption_SO_REUSEADDR_afterOpen() throws Exception { - ServerSocketChannel ssc = ServerSocketChannel.open(); - - boolean initialValue = ssc.getOption(StandardSocketOptions.SO_REUSEADDR); - ssc.setOption(StandardSocketOptions.SO_REUSEADDR, !initialValue); - assertEquals(!initialValue, (boolean) ssc.getOption(StandardSocketOptions.SO_REUSEADDR)); - assertEquals(!initialValue, ssc.socket().getReuseAddress()); - - ssc.close(); - } - } diff --git a/luni/src/test/java/libcore/java/nio/channels/SocketChannelTest.java b/luni/src/test/java/libcore/java/nio/channels/SocketChannelTest.java index 6bba862..a54b30a 100644 --- a/luni/src/test/java/libcore/java/nio/channels/SocketChannelTest.java +++ b/luni/src/test/java/libcore/java/nio/channels/SocketChannelTest.java @@ -24,8 +24,6 @@ import java.net.Socket; import java.net.InetAddress; import java.net.InetSocketAddress; import java.net.ServerSocket; -import java.net.SocketOption; -import java.net.StandardSocketOptions; import java.nio.ByteBuffer; import java.nio.channels.ClosedChannelException; import java.nio.channels.SocketChannel; @@ -143,7 +141,7 @@ public class SocketChannelTest extends junit.framework.TestCase { public void test_open_initialState() throws Exception { SocketChannel sc = SocketChannel.open(); try { - assertNull(sc.getLocalAddress()); + assertNull(sc.socket().getLocalSocketAddress()); Socket socket = sc.socket(); assertFalse(socket.isBound()); @@ -166,12 +164,12 @@ public class SocketChannelTest extends junit.framework.TestCase { public void test_bind_unresolvedAddress() throws IOException { SocketChannel sc = SocketChannel.open(); try { - sc.bind(new InetSocketAddress("unresolvedname", 31415)); + sc.socket().bind(new InetSocketAddress("unresolvedname", 31415)); fail(); - } catch (UnresolvedAddressException expected) { + } catch (IOException expected) { } - assertNull(sc.getLocalAddress()); + assertNull(sc.socket().getLocalSocketAddress()); assertTrue(sc.isOpen()); assertFalse(sc.isConnected()); @@ -181,16 +179,16 @@ public class SocketChannelTest extends junit.framework.TestCase { /** Checks that the SocketChannel and associated Socket agree on the socket state. */ public void test_bind_socketStateSync() throws IOException { SocketChannel sc = SocketChannel.open(); - assertNull(sc.getLocalAddress()); + assertNull(sc.socket().getLocalSocketAddress()); Socket socket = sc.socket(); assertNull(socket.getLocalSocketAddress()); assertFalse(socket.isBound()); InetSocketAddress bindAddr = new InetSocketAddress("localhost", 0); - sc.bind(bindAddr); + sc.socket().bind(bindAddr); - InetSocketAddress actualAddr = (InetSocketAddress) sc.getLocalAddress(); + InetSocketAddress actualAddr = (InetSocketAddress) sc.socket().getLocalSocketAddress(); assertEquals(actualAddr, socket.getLocalSocketAddress()); assertEquals(bindAddr.getHostName(), actualAddr.getHostName()); assertTrue(socket.isBound()); @@ -209,14 +207,14 @@ public class SocketChannelTest extends junit.framework.TestCase { */ public void test_bind_socketObjectCreationAfterBind() throws IOException { SocketChannel sc = SocketChannel.open(); - assertNull(sc.getLocalAddress()); + assertNull(sc.socket().getLocalSocketAddress()); InetSocketAddress bindAddr = new InetSocketAddress("localhost", 0); - sc.bind(bindAddr); + sc.socket().bind(bindAddr); // Socket object creation after bind(). Socket socket = sc.socket(); - InetSocketAddress actualAddr = (InetSocketAddress) sc.getLocalAddress(); + InetSocketAddress actualAddr = (InetSocketAddress) sc.socket().getLocalSocketAddress(); assertEquals(actualAddr, socket.getLocalSocketAddress()); assertEquals(bindAddr.getHostName(), actualAddr.getHostName()); assertTrue(socket.isBound()); @@ -276,307 +274,4 @@ public class SocketChannelTest extends junit.framework.TestCase { ss.close(); sc.close(); } - - public void test_supportedOptions() throws Exception { - SocketChannel sc = SocketChannel.open(); - Set<SocketOption<?>> options = sc.supportedOptions(); - - // Probe some values. This is not intended to be complete. - assertTrue(options.contains(StandardSocketOptions.SO_REUSEADDR)); - assertFalse(options.contains(StandardSocketOptions.IP_MULTICAST_TTL)); - } - - public void test_getOption_unsupportedOption() throws Exception { - SocketChannel sc = SocketChannel.open(); - try { - sc.getOption(StandardSocketOptions.IP_MULTICAST_TTL); - fail(); - } catch (UnsupportedOperationException expected) { - } - - sc.close(); - } - - public void test_getOption_afterClose() throws Exception { - SocketChannel sc = SocketChannel.open(); - sc.close(); - - try { - sc.getOption(StandardSocketOptions.SO_RCVBUF); - fail(); - } catch (ClosedChannelException expected) { - } - } - - public void test_setOption_afterClose() throws Exception { - SocketChannel sc = SocketChannel.open(); - sc.close(); - - try { - sc.setOption(StandardSocketOptions.SO_RCVBUF, 1234); - fail(); - } catch (ClosedChannelException expected) { - } - } - - public void test_getOption_SO_RCVBUF_defaults() throws Exception { - SocketChannel sc = SocketChannel.open(); - - int value = sc.getOption(StandardSocketOptions.SO_RCVBUF); - assertTrue(value > 0); - assertEquals(value, sc.socket().getReceiveBufferSize()); - - sc.close(); - } - - public void test_setOption_SO_RCVBUF_afterOpen() throws Exception { - SocketChannel sc = SocketChannel.open(); - - trySetReceiveBufferSizeOption(sc); - - sc.close(); - } - - private static void trySetReceiveBufferSizeOption(SocketChannel sc) throws IOException { - int initialValue = sc.getOption(StandardSocketOptions.SO_RCVBUF); - try { - sc.setOption(StandardSocketOptions.SO_RCVBUF, -1); - fail(); - } catch (IllegalArgumentException expected) { - } - int actualValue = sc.getOption(StandardSocketOptions.SO_RCVBUF); - assertEquals(initialValue, actualValue); - assertEquals(initialValue, sc.socket().getReceiveBufferSize()); - - int newBufferSize = initialValue - 1; - sc.setOption(StandardSocketOptions.SO_RCVBUF, newBufferSize); - actualValue = sc.getOption(StandardSocketOptions.SO_RCVBUF); - // The Linux Kernel actually doubles the value it is given and may choose to ignore it. - // This assertion may be brittle. - assertTrue(actualValue != initialValue); - assertEquals(actualValue, sc.socket().getReceiveBufferSize()); - } - - public void test_getOption_SO_SNDBUF_defaults() throws Exception { - SocketChannel sc = SocketChannel.open(); - - int bufferSize = sc.getOption(StandardSocketOptions.SO_SNDBUF); - assertTrue(bufferSize > 0); - assertEquals(bufferSize, sc.socket().getSendBufferSize()); - - sc.close(); - } - - public void test_setOption_SO_SNDBUF_afterOpen() throws Exception { - SocketChannel sc = SocketChannel.open(); - - trySetSendBufferSizeOption(sc); - - sc.close(); - } - - private static void trySetSendBufferSizeOption(SocketChannel sc) throws IOException { - int initialValue = sc.getOption(StandardSocketOptions.SO_SNDBUF); - try { - sc.setOption(StandardSocketOptions.SO_SNDBUF, -1); - fail(); - } catch (IllegalArgumentException expected) { - } - int actualValue = sc.getOption(StandardSocketOptions.SO_SNDBUF); - assertEquals(initialValue, actualValue); - assertEquals(initialValue, sc.socket().getSendBufferSize()); - - int newValue = initialValue - 1; - sc.setOption(StandardSocketOptions.SO_SNDBUF, newValue); - actualValue = sc.getOption(StandardSocketOptions.SO_SNDBUF); - // The Linux Kernel actually doubles the value it is given and may choose to ignore it. - // This assertion may be brittle. - assertTrue(actualValue != initialValue); - assertEquals(actualValue, sc.socket().getSendBufferSize()); - } - - public void test_getOption_SO_KEEPALIVE_defaults() throws Exception { - SocketChannel sc = SocketChannel.open(); - - assertFalse(sc.getOption(StandardSocketOptions.SO_KEEPALIVE)); - - sc.close(); - } - - public void test_setOption_SO_KEEPALIVE_afterOpen() throws Exception { - SocketChannel sc = SocketChannel.open(); - - trySetSoKeepaliveOption(sc); - - sc.close(); - } - - private static void trySetSoKeepaliveOption(SocketChannel sc) throws IOException { - boolean initialValue = sc.getOption(StandardSocketOptions.SO_KEEPALIVE); - - sc.setOption(StandardSocketOptions.SO_KEEPALIVE, !initialValue); - boolean actualValue = sc.getOption(StandardSocketOptions.SO_KEEPALIVE); - assertEquals(!initialValue, actualValue); - } - - public void test_setOption_SO_KEEPALIVE_afterBind() throws Exception { - SocketChannel sc = SocketChannel.open(); - sc.bind(null); - - trySetSoKeepaliveOption(sc); - - sc.close(); - } - - public void test_getOption_IP_TOS_defaults() throws Exception { - SocketChannel sc = SocketChannel.open(); - - int value = sc.getOption(StandardSocketOptions.IP_TOS); - assertEquals(0, value); - assertEquals(value, sc.socket().getTrafficClass()); - - sc.close(); - } - - public void test_setOption_IP_TOS_afterOpen() throws Exception { - SocketChannel sc = SocketChannel.open(); - - trySetTosOption(sc); - - sc.close(); - } - - private static void trySetTosOption(SocketChannel sc) throws IOException { - int initialValue = sc.getOption(StandardSocketOptions.IP_TOS); - try { - sc.setOption(StandardSocketOptions.IP_TOS, -1); - fail(); - } catch (IllegalArgumentException expected) { - } - assertEquals(initialValue, (int) sc.getOption(StandardSocketOptions.IP_TOS)); - assertEquals(initialValue, sc.socket().getTrafficClass()); - - try { - sc.setOption(StandardSocketOptions.IP_TOS, 256); - fail(); - } catch (IllegalArgumentException expected) { - } - assertEquals(initialValue, (int) sc.getOption(StandardSocketOptions.IP_TOS)); - assertEquals(initialValue, sc.socket().getTrafficClass()); - - int newValue = (initialValue + 1) % 255; - sc.setOption(StandardSocketOptions.IP_TOS, newValue); - assertEquals(newValue, (int) sc.getOption(StandardSocketOptions.IP_TOS)); - assertEquals(newValue, sc.socket().getTrafficClass()); - } - - public void test_setOption_IP_TOS_afterBind() throws Exception { - SocketChannel sc = SocketChannel.open(); - sc.bind(null); - - trySetTosOption(sc); - - sc.close(); - } - - public void test_getOption_SO_LINGER_defaults() throws Exception { - SocketChannel sc = SocketChannel.open(); - - int value = sc.getOption(StandardSocketOptions.SO_LINGER); - assertTrue(value < 0); - assertEquals(value, sc.socket().getSoLinger()); - - sc.close(); - } - - public void test_setOption_SO_LINGER_afterOpen() throws Exception { - SocketChannel sc = SocketChannel.open(); - - trySetLingerOption(sc); - - sc.close(); - } - - private static void trySetLingerOption(SocketChannel sc) throws IOException { - int initialValue = sc.getOption(StandardSocketOptions.SO_LINGER); - // Any negative value disables the setting, -1 is used to report SO_LINGER being disabled. - sc.setOption(StandardSocketOptions.SO_LINGER, -2); - int soLingerDisabled = -1; - assertEquals(soLingerDisabled, (int) sc.getOption(StandardSocketOptions.SO_LINGER)); - assertEquals(soLingerDisabled, sc.socket().getSoLinger()); - - sc.setOption(StandardSocketOptions.SO_LINGER, 65536); - assertEquals(65535, (int) sc.getOption(StandardSocketOptions.SO_LINGER)); - assertEquals(65535, sc.socket().getSoLinger()); - - int newValue = (initialValue + 1) % 65535; - sc.setOption(StandardSocketOptions.SO_LINGER, newValue); - assertEquals(newValue, (int) sc.getOption(StandardSocketOptions.SO_LINGER)); - assertEquals(newValue, sc.socket().getSoLinger()); - } - - public void test_setOption_SO_LINGER_afterBind() throws Exception { - SocketChannel sc = SocketChannel.open(); - sc.bind(null); - - trySetLingerOption(sc); - - sc.close(); - } - - public void test_getOption_SO_REUSEADDR_defaults() throws Exception { - SocketChannel sc = SocketChannel.open(); - - boolean value = sc.getOption(StandardSocketOptions.SO_REUSEADDR); - assertFalse(value); - assertFalse(sc.socket().getReuseAddress()); - - sc.close(); - } - - public void test_setOption_SO_REUSEADDR_afterOpen() throws Exception { - SocketChannel sc = SocketChannel.open(); - - boolean initialValue = sc.getOption(StandardSocketOptions.SO_REUSEADDR); - sc.setOption(StandardSocketOptions.SO_REUSEADDR, !initialValue); - assertEquals(!initialValue, (boolean) sc.getOption(StandardSocketOptions.SO_REUSEADDR)); - assertEquals(!initialValue, sc.socket().getReuseAddress()); - - sc.close(); - } - - public void test_getOption_TCP_NODELAY_defaults() throws Exception { - SocketChannel sc = SocketChannel.open(); - - boolean value = sc.getOption(StandardSocketOptions.TCP_NODELAY); - assertFalse(value); - assertFalse(sc.socket().getTcpNoDelay()); - - sc.close(); - } - - public void test_setOption_TCP_NODELAY_afterOpen() throws Exception { - SocketChannel sc = SocketChannel.open(); - - trySetNoDelay(sc); - - sc.close(); - } - - private static void trySetNoDelay(SocketChannel sc) throws IOException { - boolean initialValue = sc.getOption(StandardSocketOptions.TCP_NODELAY); - sc.setOption(StandardSocketOptions.TCP_NODELAY, !initialValue); - assertEquals(!initialValue, (boolean) sc.getOption(StandardSocketOptions.TCP_NODELAY)); - assertEquals(!initialValue, sc.socket().getTcpNoDelay()); - } - - public void test_setOption_TCP_NODELAY_afterBind() throws Exception { - SocketChannel sc = SocketChannel.open(); - sc.bind(null); - - trySetNoDelay(sc); - - sc.close(); - } - } diff --git a/luni/src/test/java/libcore/java/util/CurrencyTest.java b/luni/src/test/java/libcore/java/util/CurrencyTest.java index fb7fbf6..61a22fd 100644 --- a/luni/src/test/java/libcore/java/util/CurrencyTest.java +++ b/luni/src/test/java/libcore/java/util/CurrencyTest.java @@ -67,13 +67,6 @@ public class CurrencyTest extends junit.framework.TestCase { assertEquals(-1, Currency.getInstance("XXX").getDefaultFractionDigits()); } - public void test_getNumericCode() throws Exception { - assertEquals(840, Currency.getInstance("USD").getNumericCode()); - assertEquals(826, Currency.getInstance("GBP").getNumericCode()); - assertEquals(999, Currency.getInstance("XXX").getNumericCode()); - assertEquals(0, Currency.getInstance("XFU").getNumericCode()); - } - // http://code.google.com/p/android/issues/detail?id=38622 public void test_getSymbol_38622() throws Exception { // The CLDR data had the Portuguese symbol for "EUR" in pt, not in pt_PT. diff --git a/luni/src/test/java/libcore/java/util/zip/ZipFileTest.java b/luni/src/test/java/libcore/java/util/zip/ZipFileTest.java index 81ff673..a9ff56f 100644 --- a/luni/src/test/java/libcore/java/util/zip/ZipFileTest.java +++ b/luni/src/test/java/libcore/java/util/zip/ZipFileTest.java @@ -217,96 +217,6 @@ public final class ZipFileTest extends TestCase { } } - public void testNullCharset() throws IOException { - try { - new ZipFile(createTemporaryZipFile(), null); - fail(); - } catch (NullPointerException expected) { - } - } - - // Tests that non-UTF8 encoded zip files can be interpreted. Relies on ZipOutputStream. - public void testNonUtf8Encoding() throws IOException { - Charset charset = Charset.forName("Cp437"); - String encodingDependentString = "\u00FB"; - assertEncodingDiffers(encodingDependentString, charset, StandardCharsets.US_ASCII, - StandardCharsets.UTF_8); - String name = "name" + encodingDependentString; - String comment = "comment" + encodingDependentString; - - File result = createTemporaryZipFile(); - OutputStream os = new BufferedOutputStream(new FileOutputStream(result)); - ZipOutputStream out = new ZipOutputStream(os, charset); - out.setComment(comment); - ZipEntry writeEntry = new ZipEntry(name); - writeEntry.setComment(comment); - out.putNextEntry(writeEntry); - out.write("FileContentsIrrelevant".getBytes()); - out.closeEntry(); - out.close(); - - ZipFile zipFile = new ZipFile(result, StandardCharsets.US_ASCII); - assertNull(zipFile.getEntry(name)); - assertFalse(zipFile.getComment().equals(comment)); - zipFile.close(); - - zipFile = new ZipFile(result, charset); - ZipEntry readEntry = zipFile.getEntry(name); - assertNotNull(readEntry); - assertEquals(name, readEntry.getName()); - assertEquals(comment, readEntry.getComment()); - assertEquals(comment, zipFile.getComment()); - zipFile.close(); - } - - // Tests that UTF8 encoded zip files can be interpreted when the constructor is provided with a - // non-UTF-8 encoding. Relies on ZipOutputStream. - public void testUtf8EncodingOverridesConstructor() throws IOException { - Charset charset = Charset.forName("Cp437"); - String encodingDependentString = "\u00FB"; - assertEncodingDiffers(encodingDependentString, charset, StandardCharsets.UTF_8); - String name = "name" + encodingDependentString; - String comment = "comment" + encodingDependentString; - - File result = createTemporaryZipFile(); - OutputStream os = new BufferedOutputStream(new FileOutputStream(result)); - ZipOutputStream out = new ZipOutputStream(os, StandardCharsets.UTF_8); - // The file comment does not get meta-data about the character encoding. - out.setComment(comment); - // The entry will be tagged as being UTF-8 encoded. - ZipEntry writeEntry = new ZipEntry(name); - writeEntry.setComment(comment); - out.putNextEntry(writeEntry); - out.write("FileContentsIrrelevant".getBytes()); - out.closeEntry(); - out.close(); - - ZipFile zipFile = new ZipFile(result, charset); - // The entry should be found, because it should be tagged as being UTF-8 encoded. - ZipEntry readEntry = zipFile.getEntry(name); - assertNotNull(readEntry); - assertEquals(name, readEntry.getName()); - assertEquals(comment, readEntry.getComment()); - // We expect the comment to be mangled because it is not tagged. - assertFalse(zipFile.getComment().equals(comment)); - zipFile.close(); - } - - /** - * Asserts the byte encoding for the string is different for all the supplied character - * sets. - */ - private void assertEncodingDiffers(String string, Charset... charsets) { - Set<List<Byte>> encodings = new HashSet<List<Byte>>(); - for (int i = 0; i < charsets.length; i++) { - List<Byte> byteList = new ArrayList<Byte>(); - for (byte b : string.getBytes(charsets[i])) { - byteList.add(b); - } - assertTrue("Encoding has been seen before", encodings.add(byteList)); - } - } - /** * Compresses the given number of files, each of the given size, into a .zip archive. */ diff --git a/luni/src/test/java/libcore/java/util/zip/ZipInputStreamTest.java b/luni/src/test/java/libcore/java/util/zip/ZipInputStreamTest.java index 2daa127..49990a3 100644 --- a/luni/src/test/java/libcore/java/util/zip/ZipInputStreamTest.java +++ b/luni/src/test/java/libcore/java/util/zip/ZipInputStreamTest.java @@ -50,97 +50,6 @@ public final class ZipInputStreamTest extends TestCase { assertTrue(Arrays.equals(data, unzip("r", ZipOutputStreamTest.zip("r", data)))); } - public void testNullCharset() throws IOException { - try { - new ZipInputStream(new ByteArrayInputStream(new byte[1]), null); - fail(); - } catch (NullPointerException expected) { - } - } - - // Tests that non-UTF8 encoded zip file entries can be interpreted. Relies on ZipOutputStream. - public void testNonUtf8Encoding() throws IOException { - Charset charset = Charset.forName("Cp437"); - String encodingDependentString = "\u00FB"; - assertEncodingDiffers(encodingDependentString, charset, StandardCharsets.US_ASCII, - StandardCharsets.UTF_8); - String name = "name" + encodingDependentString; - String comment = "comment" + encodingDependentString; - - ByteArrayOutputStream bytesOutputStream = new ByteArrayOutputStream(); - ZipOutputStream out = new ZipOutputStream(bytesOutputStream, charset); - ZipEntry writeEntry = new ZipEntry(name); - writeEntry.setComment(comment); - out.putNextEntry(writeEntry); - out.write("FileContentsIrrelevant".getBytes()); - out.closeEntry(); - out.close(); - - ByteArrayInputStream bytesInputStream = - new ByteArrayInputStream(bytesOutputStream.toByteArray()); - ZipInputStream in = new ZipInputStream(bytesInputStream, StandardCharsets.US_ASCII); - ZipEntry readEntry = in.getNextEntry(); - // Due to the way ZipInputStream works it never returns entry comments. - assertNull("ZipInputStream must not retrieve comments", readEntry.getComment()); - assertFalse(readEntry.getName().equals(name)); - in.close(); - - bytesInputStream = new ByteArrayInputStream(bytesOutputStream.toByteArray()); - in = new ZipInputStream(bytesInputStream, charset); - readEntry = in.getNextEntry(); - // Because ZipInputStream never reads the central directory it never returns entry - // comments or the file comment. - assertNull("ZipInputStream must not retrieve comments", readEntry.getComment()); - assertEquals(name, readEntry.getName()); - in.close(); - } - - // Tests that UTF8 encoded zip file entries can be interpreted when the constructor is provided - // with a non-UTF-8 encoding. Relies on ZipOutputStream. - public void testUtf8EncodingOverridesConstructor() throws IOException { - Charset charset = Charset.forName("Cp437"); - String encodingDependentString = "\u00FB"; - assertEncodingDiffers(encodingDependentString, charset, StandardCharsets.UTF_8); - String name = "name" + encodingDependentString; - String comment = "comment" + encodingDependentString; - - ByteArrayOutputStream bytesOutputStream = new ByteArrayOutputStream(); - ZipOutputStream out = new ZipOutputStream(bytesOutputStream, StandardCharsets.UTF_8); - // The entry will be tagged as being UTF-8 encoded. - ZipEntry writeEntry = new ZipEntry(name); - writeEntry.setComment(comment); - out.putNextEntry(writeEntry); - out.write("FileContentsIrrelevant".getBytes()); - out.closeEntry(); - out.close(); - - ByteArrayInputStream bytesInputStream = - new ByteArrayInputStream(bytesOutputStream.toByteArray()); - ZipInputStream in = new ZipInputStream(bytesInputStream, charset); - ZipEntry readEntry = in.getNextEntry(); - // Because ZipInputStream never reads the central directory it never returns entry - // comments or the file comment. - assertNull("ZipInputStream must not retrieve comments", readEntry.getComment()); - assertNotNull(readEntry); - assertEquals(name, readEntry.getName()); - in.close(); - } - - /** - * Asserts the byte encoding for the string is different for all the supplied character - * sets. - */ - private void assertEncodingDiffers(String string, Charset... charsets) { - Set<List<Byte>> encodings = new HashSet<List<Byte>>(); - for (int i = 0; i < charsets.length; i++) { - List<Byte> byteList = new ArrayList<Byte>(); - for (byte b : string.getBytes(charsets[i])) { - byteList.add(b); - } - assertTrue("Encoding has been seen before", encodings.add(byteList)); - } - } - public static byte[] unzip(String name, byte[] bytes) throws IOException { ZipInputStream in = new ZipInputStream(new ByteArrayInputStream(bytes)); ByteArrayOutputStream out = new ByteArrayOutputStream(); diff --git a/luni/src/test/java/libcore/java/util/zip/ZipOutputStreamTest.java b/luni/src/test/java/libcore/java/util/zip/ZipOutputStreamTest.java index 92afffa..e69f010 100644 --- a/luni/src/test/java/libcore/java/util/zip/ZipOutputStreamTest.java +++ b/luni/src/test/java/libcore/java/util/zip/ZipOutputStreamTest.java @@ -78,14 +78,6 @@ public final class ZipOutputStreamTest extends TestCase { } } - public void testNullCharset() throws IOException { - try { - new ZipOutputStream(new ByteArrayOutputStream(), null); - fail(); - } catch (NullPointerException expected) { - } - } - /** Regression test for null comment causing a NullPointerException during write. */ public void testNullComment() throws IOException { ZipOutputStream out = new ZipOutputStream(new ByteArrayOutputStream()); @@ -95,54 +87,4 @@ public final class ZipOutputStreamTest extends TestCase { out.closeEntry(); out.finish(); } - - /** Contrived test to force a longer name than can be stored. */ - public void testLongName() throws IOException { - int maxNameBytes = 0xffff; // 2 bytes - String longName = createString(maxNameBytes); - - ZipEntry entry = new ZipEntry(longName); - - // Using UTF-16 will result in name bytes twice as large as is supported by Zip. - // UTF-16 is an unlikely character set to actually want to use with Zip but enables - // the edge-case behavior required without using direct field access. - ZipOutputStream out = new ZipOutputStream( - new ByteArrayOutputStream(), StandardCharsets.UTF_16); - try { - out.putNextEntry(entry); - fail(); - } catch (IllegalArgumentException expected) { - } - } - - /** Contrived test to force a longer comment than can be stored. */ - public void testLongComment() throws IOException { - int maxCommentBytes = 0xffff; // 2 bytes - String longComment = createString(maxCommentBytes); - - ZipEntry entry = new ZipEntry("name"); - // setComment() should pass, because it is at the limit of what ZipEntry will detect as - // valid (since it uses UTF-8 as a worst-case guess). - entry.setComment(longComment); - - // Using UTF-16 will result in comment bytes twice as large as is supported by Zip. - // UTF-16 is an unlikely character set to actually want to use with Zip but enables - // the edge-case behavior required without using direct field access. - ZipOutputStream out = new ZipOutputStream( - new ByteArrayOutputStream(), StandardCharsets.UTF_16); - try { - out.putNextEntry(entry); - fail(); - } catch (IllegalArgumentException expected) { - } - } - - private static String createString(int numChars) { - char c = 'a'; - StringBuilder sb = new StringBuilder(numChars); - for (int i = 0; i < numChars; i++) { - sb.append(c); - } - return sb.toString(); - } } |