Merge "Updating information for OkHttp suppressions"
diff --git a/benchmarks/src/benchmarks/regression/IcuBenchmark.java b/benchmarks/src/benchmarks/regression/IcuBenchmark.java
index ee8270a..2aed36b 100644
--- a/benchmarks/src/benchmarks/regression/IcuBenchmark.java
+++ b/benchmarks/src/benchmarks/regression/IcuBenchmark.java
@@ -26,7 +26,7 @@
public class IcuBenchmark extends SimpleBenchmark {
public void time_getBestDateTimePattern(int reps) throws Exception {
for (int rep = 0; rep < reps; ++rep) {
- ICU.getBestDateTimePattern("dEEEMMM", "US");
+ ICU.getBestDateTimePattern("dEEEMMM", new Locale("en", "US"));
}
}
}
diff --git a/benchmarks/src/benchmarks/regression/StringCaseMappingBenchmark.java b/benchmarks/src/benchmarks/regression/StringCaseMappingBenchmark.java
index cde257b..ae6b6b6 100644
--- a/benchmarks/src/benchmarks/regression/StringCaseMappingBenchmark.java
+++ b/benchmarks/src/benchmarks/regression/StringCaseMappingBenchmark.java
@@ -106,13 +106,13 @@
public void timeToUpperCase_ICU(int reps) {
for (int i = 0; i < reps; ++i) {
- libcore.icu.ICU.toUpperCase(s.value, Locale.US.toString());
+ libcore.icu.ICU.toUpperCase(s.value, Locale.US);
}
}
public void timeToLowerCase_ICU(int reps) {
for (int i = 0; i < reps; ++i) {
- libcore.icu.ICU.toLowerCase(s.value, Locale.US.toString());
+ libcore.icu.ICU.toLowerCase(s.value, Locale.US);
}
}
diff --git a/harmony-tests/src/test/java/org/apache/harmony/tests/java/net/MulticastSocketTest.java b/harmony-tests/src/test/java/org/apache/harmony/tests/java/net/MulticastSocketTest.java
index 6a75746..e3e1207 100644
--- a/harmony-tests/src/test/java/org/apache/harmony/tests/java/net/MulticastSocketTest.java
+++ b/harmony-tests/src/test/java/org/apache/harmony/tests/java/net/MulticastSocketTest.java
@@ -18,7 +18,6 @@
package org.apache.harmony.tests.java.net;
import java.io.IOException;
-import java.io.InterruptedIOException;
import java.net.BindException;
import java.net.DatagramPacket;
import java.net.Inet4Address;
@@ -29,8 +28,10 @@
import java.net.NetworkInterface;
import java.net.SocketAddress;
import java.net.SocketException;
+import java.net.SocketTimeoutException;
import java.util.ArrayList;
import java.util.Enumeration;
+import java.util.List;
public class MulticastSocketTest extends junit.framework.TestCase {
@@ -52,158 +53,124 @@
private static InetAddress GOOD_IPv6 = lookup("ff05::7:7");
private static InetAddress BAD_IPv6 = lookup("ff05::7:8");
- static class MulticastServer extends Thread {
+ private NetworkInterface loopbackInterface;
+ private NetworkInterface ipv4NetworkInterface;
+ private NetworkInterface ipv6NetworkInterface;
- public final MulticastSocket ms;
- public final byte[] rbuf = new byte[512];
- public final DatagramPacket rdp;
- private final InetAddress groupAddr;
- private final NetworkInterface groupNI;
+ @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());
- private volatile boolean running = true;
+ Enumeration<NetworkInterface> interfaces = NetworkInterface.getNetworkInterfaces();
+ assertNotNull(interfaces);
- public MulticastServer(InetAddress anAddress, int aPort) throws java.io.IOException {
- rbuf[0] = -1;
- rdp = new DatagramPacket(rbuf, rbuf.length);
- ms = new MulticastSocket(aPort);
- ms.setSoTimeout(2000);
-
- groupAddr = anAddress;
- groupNI = null;
-
- ms.joinGroup(groupAddr);
- }
-
- public MulticastServer(InetAddress anAddress, int aPort,
- NetworkInterface netInterface) throws java.io.IOException {
- rbuf[0] = -1;
- rdp = new DatagramPacket(rbuf, rbuf.length);
- ms = new MulticastSocket(aPort);
- ms.setSoTimeout(2000);
-
- groupAddr = anAddress;
- groupNI = netInterface;
-
- ms.joinGroup(new InetSocketAddress(groupAddr, ms.getLocalPort()), groupNI);
- }
-
- public void run() {
- try {
- byte[] tmpbuf = new byte[512];
- DatagramPacket tmpPack = new DatagramPacket(tmpbuf, tmpbuf.length);
-
- while (running) {
- try {
- ms.receive(tmpPack);
- System.arraycopy(tmpPack.getData(), 0, rdp.getData(), rdp.getOffset(),
- tmpPack.getLength());
- rdp.setLength(tmpPack.getLength());
- rdp.setAddress(tmpPack.getAddress());
- rdp.setPort(tmpPack.getPort());
- } catch (InterruptedIOException e) {
+ while (interfaces.hasMoreElements()
+ && (ipv4NetworkInterface == null || ipv6NetworkInterface == null)) {
+ NetworkInterface nextInterface = interfaces.nextElement();
+ if (willWorkForMulticast(nextInterface)) {
+ Enumeration<InetAddress> addresses = nextInterface.getInetAddresses();
+ while (addresses.hasMoreElements()) {
+ final InetAddress nextAddress = addresses.nextElement();
+ if (nextAddress instanceof Inet6Address && ipv6NetworkInterface == null) {
+ ipv6NetworkInterface = nextInterface;
+ } else if (nextAddress instanceof Inet4Address && ipv4NetworkInterface == null) {
+ ipv4NetworkInterface = nextInterface;
}
}
- } catch (java.io.IOException e) {
- fail();
- } finally {
- ms.close();
}
}
-
- public void stopServer() {
- running = false;
- try {
- ms.leaveGroup(groupAddr);
- } catch (IOException e) {
- }
- }
+ assertTrue("Test environment must have at least one interface capable of multicast for IPv4"
+ + " and IPv6",
+ ipv4NetworkInterface != null && ipv6NetworkInterface != null);
}
- private NetworkInterface loopbackInterface;
- private NetworkInterface networkInterface1;
- private NetworkInterface IPV6networkInterface1;
-
public void test_Constructor() throws IOException {
- // regression test for 497
+ // Regression test for 497.
MulticastSocket s = new MulticastSocket();
- // regression test for Harmony-1162
+ // Regression test for Harmony-1162.
assertTrue(s.getReuseAddress());
+
+ s.close();
}
public void test_ConstructorI() throws IOException {
MulticastSocket orig = new MulticastSocket();
int port = orig.getLocalPort();
orig.close();
- MulticastSocket dup = null;
- try {
- dup = new MulticastSocket(port);
- // regression test for Harmony-1162
- assertTrue(dup.getReuseAddress());
- } catch (IOException e) {
- fail("duplicate binding not allowed: " + e);
- }
- if (dup != null) {
- dup.close();
- }
+
+ MulticastSocket dup = new MulticastSocket(port);
+ // Regression test for Harmony-1162.
+ assertTrue(dup.getReuseAddress());
+ dup.close();
}
public void test_getInterface() throws Exception {
- // validate that we get the expected response when one was not set
+ // Validate that we get the expected response when one was not set.
MulticastSocket mss = new MulticastSocket(0);
- // we expect an ANY address in this case
+ // We expect an ANY address in this case.
assertTrue(mss.getInterface().isAnyLocalAddress());
- // validate that we get the expected response when we set via
- // setInterface
- Enumeration addresses = networkInterface1.getInetAddresses();
+ // Validate that we get the expected response when we set via setInterface.
+ Enumeration addresses = ipv4NetworkInterface.getInetAddresses();
if (addresses.hasMoreElements()) {
InetAddress firstAddress = (InetAddress) addresses.nextElement();
mss.setInterface(firstAddress);
- assertEquals("getNetworkInterface did not return interface set by setInterface", firstAddress, mss.getInterface());
+ assertEquals("getNetworkInterface did not return interface set by setInterface",
+ firstAddress, mss.getInterface());
mss.close();
mss = new MulticastSocket(0);
- mss.setNetworkInterface(networkInterface1);
- assertEquals("getInterface did not return interface set by setNetworkInterface", networkInterface1, NetworkInterface.getByInetAddress(mss.getInterface()));
+ mss.setNetworkInterface(ipv4NetworkInterface);
+ assertEquals("getInterface did not return interface set by setNetworkInterface",
+ ipv4NetworkInterface, NetworkInterface.getByInetAddress(mss.getInterface()));
}
mss.close();
}
public void test_getNetworkInterface() throws IOException {
- // validate that we get the expected response when one was not set
+ // Validate that we get the expected response when one was not set.
MulticastSocket mss = new MulticastSocket(0);
NetworkInterface theInterface = mss.getNetworkInterface();
- assertTrue("network interface returned wrong network interface when not set:" + theInterface,
+ assertTrue(
+ "network interface returned wrong network interface when not set:" + theInterface,
theInterface.getInetAddresses().hasMoreElements());
- InetAddress firstAddress = (InetAddress) theInterface.getInetAddresses().nextElement();
- // validate we the first address in the network interface is the ANY address
+ InetAddress firstAddress = theInterface.getInetAddresses().nextElement();
+ // Validate we the first address in the network interface is the ANY address.
assertTrue(firstAddress.isAnyLocalAddress());
- mss.setNetworkInterface(networkInterface1);
+ mss.setNetworkInterface(ipv4NetworkInterface);
assertEquals("getNetworkInterface did not return interface set by setNeworkInterface",
- networkInterface1, mss.getNetworkInterface());
+ ipv4NetworkInterface, mss.getNetworkInterface());
mss.setNetworkInterface(loopbackInterface);
- assertEquals("getNetworkInterface did not return network interface set by second setNetworkInterface call",
+ assertEquals(
+ "getNetworkInterface did not return network interface set by second"
+ + " setNetworkInterface call",
loopbackInterface, mss.getNetworkInterface());
mss.close();
- mss = new MulticastSocket(0);
- if (IPV6networkInterface1 != null) {
- mss.setNetworkInterface(IPV6networkInterface1);
+ if (ipv6NetworkInterface != null) {
+ mss = new MulticastSocket(0);
+ mss.setNetworkInterface(ipv6NetworkInterface);
assertEquals("getNetworkInterface did not return interface set by setNeworkInterface",
- IPV6networkInterface1, mss.getNetworkInterface());
+ ipv6NetworkInterface, mss.getNetworkInterface());
+ mss.close();
}
- // validate that we get the expected response when we set via setInterface
+ // Validate that we get the expected response when we set via setInterface.
mss = new MulticastSocket(0);
- Enumeration addresses = networkInterface1.getInetAddresses();
+ Enumeration addresses = ipv4NetworkInterface.getInetAddresses();
if (addresses.hasMoreElements()) {
firstAddress = (InetAddress) addresses.nextElement();
mss.setInterface(firstAddress);
assertEquals("getNetworkInterface did not return interface set by setInterface",
- networkInterface1, mss.getNetworkInterface());
+ ipv4NetworkInterface, mss.getNetworkInterface());
}
mss.close();
}
@@ -214,12 +181,14 @@
assertEquals("Returned incorrect 1st TTL", 120, mss.getTimeToLive());
mss.setTimeToLive(220);
assertEquals("Returned incorrect 2nd TTL", 220, mss.getTimeToLive());
+ mss.close();
}
public void test_getTTL() throws Exception {
MulticastSocket mss = new MulticastSocket();
mss.setTTL((byte) 120);
assertEquals("Returned incorrect TTL", 120, mss.getTTL());
+ mss.close();
}
public void test_joinGroupLjava_net_InetAddress_IPv4() throws Exception {
@@ -231,19 +200,23 @@
}
private void test_joinGroupLjava_net_InetAddress(InetAddress group) throws Exception {
- MulticastServer server = new MulticastServer(group, 0);
- server.start();
- Thread.sleep(1000);
+ MulticastSocket receivingSocket = createReceivingSocket(0);
+ receivingSocket.joinGroup(group);
+
String msg = "Hello World";
- MulticastSocket mss = new MulticastSocket(server.ms.getLocalPort());
- DatagramPacket sdp = new DatagramPacket(msg.getBytes(), msg.length(), group,
- server.ms.getLocalPort());
- mss.send(sdp, (byte) 10);
- Thread.sleep(1000);
- String receivedMessage = new String(server.rdp.getData(), 0, server.rdp.getLength());
+ MulticastSocket sendingSocket = new MulticastSocket(receivingSocket.getLocalPort());
+ InetSocketAddress groupAddress =
+ new InetSocketAddress(group, receivingSocket.getLocalPort());
+ DatagramPacket sdp = createSendDatagramPacket(groupAddress, msg);
+ sendingSocket.send(sdp, (byte) 10 /* ttl */);
+
+ DatagramPacket rdp = createReceiveDatagramPacket();
+ receivingSocket.receive(rdp);
+ String receivedMessage = extractMessage(rdp);
assertEquals("Group member did not recv data", msg, receivedMessage);
- mss.close();
- server.stopServer();
+
+ sendingSocket.close();
+ receivingSocket.close();
}
public void test_joinGroup_null_null() throws Exception {
@@ -276,52 +249,64 @@
mss.close();
}
- public void test_joinGroupLjava_net_SocketAddressLjava_net_NetworkInterface_IPv4() throws Exception {
- test_joinGroupLjava_net_SocketAddressLjava_net_NetworkInterface(GOOD_IPv4, BAD_IPv4);
+ public void test_joinGroupLjava_net_SocketAddressLjava_net_NetworkInterface_IPv4()
+ throws Exception {
+ test_joinGroupLjava_net_SocketAddressLjava_net_NetworkInterface(
+ ipv4NetworkInterface, GOOD_IPv4, BAD_IPv4);
}
- public void test_joinGroupLjava_net_SocketAddressLjava_net_NetworkInterface_IPv6() throws Exception {
- test_joinGroupLjava_net_SocketAddressLjava_net_NetworkInterface(GOOD_IPv6, BAD_IPv6);
+ public void test_joinGroupLjava_net_SocketAddressLjava_net_NetworkInterface_IPv6()
+ throws Exception {
+ test_joinGroupLjava_net_SocketAddressLjava_net_NetworkInterface(
+ ipv6NetworkInterface, GOOD_IPv6, BAD_IPv6);
}
- private void test_joinGroupLjava_net_SocketAddressLjava_net_NetworkInterface(InetAddress group, InetAddress group2) throws Exception {
+ private void test_joinGroupLjava_net_SocketAddressLjava_net_NetworkInterface(
+ NetworkInterface networkInterface, InetAddress group, InetAddress group2)
+ throws Exception {
// Check that we can join a group using a null network interface.
- MulticastSocket mss = new MulticastSocket(0);
- SocketAddress groupSockAddr = new InetSocketAddress(group, mss.getLocalPort());
+ MulticastSocket sendingSocket = new MulticastSocket(0);
+ SocketAddress groupSockAddr = new InetSocketAddress(group, sendingSocket.getLocalPort());
+ sendingSocket.joinGroup(groupSockAddr, null);
+ sendingSocket.setTimeToLive(2);
- mss.joinGroup(groupSockAddr, null);
- mss.setTimeToLive(2);
- Thread.sleep(1000);
+ MulticastSocket receivingSocket = createReceivingSocket(0);
+ InetSocketAddress groupAddress =
+ new InetSocketAddress(group, receivingSocket.getLocalPort());
+ receivingSocket.joinGroup(groupAddress, networkInterface);
- // set up the server and join the group on networkInterface1
- MulticastServer server = new MulticastServer(group, 0, networkInterface1);
- server.start();
- Thread.sleep(1000);
String msg = "Hello World";
- DatagramPacket sdp = new DatagramPacket(msg.getBytes(), msg.length(), group,
- server.ms.getLocalPort());
- mss.setTimeToLive(2);
- mss.send(sdp);
- Thread.sleep(1000);
- // now validate that we received the data as expected
- assertEquals("Group member did not recv data", msg, new String(server.rdp.getData(), 0, server.rdp.getLength()));
- server.stopServer();
- mss.close();
+ DatagramPacket sdp = createSendDatagramPacket(groupAddress, msg);
+ sendingSocket.send(sdp);
- server = new MulticastServer(group, 0, networkInterface1);
- server.start();
- Thread.sleep(1000);
+ DatagramPacket rdp = createReceiveDatagramPacket();
+ receivingSocket.receive(rdp);
+ // Now validate that we received the data as expected.
+ assertEquals("Group member did not recv data", msg, extractMessage(rdp));
+ receivingSocket.close();
+ sendingSocket.close();
- mss = new MulticastSocket(0);
- mss.setTimeToLive(10);
+ receivingSocket = createReceivingSocket(0);
+ groupAddress = new InetSocketAddress(group, receivingSocket.getLocalPort());
+ receivingSocket.joinGroup(groupAddress, networkInterface);
+
+ sendingSocket = new MulticastSocket(0);
+ sendingSocket.setTimeToLive(10);
msg = "Hello World - Different Group";
- sdp = new DatagramPacket(msg.getBytes(), msg.length(), group2, server.ms.getLocalPort());
- mss.send(sdp);
- Thread.sleep(1000);
- assertFalse("Group member received data when sent on different group: ",
- new String(server.rdp.getData(), 0, server.rdp.getLength()).equals(msg));
- server.stopServer();
- mss.close();
+ InetSocketAddress group2Address =
+ new InetSocketAddress(group2, receivingSocket.getLocalPort());
+ sdp = createSendDatagramPacket(group2Address, msg);
+ sendingSocket.send(sdp);
+
+ rdp = createReceiveDatagramPacket();
+ try {
+ receivingSocket.receive(rdp);
+ fail("Expected timeout");
+ } catch (SocketTimeoutException expected) {
+ }
+
+ receivingSocket.close();
+ sendingSocket.close();
}
public void test_joinGroupLjava_net_SocketAddressLjava_net_NetworkInterface() throws Exception {
@@ -329,27 +314,19 @@
// received on that interface. This test is only really useful on devices with multiple
// non-loopback interfaces.
- ArrayList<NetworkInterface> realInterfaces = new ArrayList<NetworkInterface>();
+ List<NetworkInterface> realInterfaces = new ArrayList<NetworkInterface>();
Enumeration<NetworkInterface> theInterfaces = NetworkInterface.getNetworkInterfaces();
while (theInterfaces.hasMoreElements()) {
NetworkInterface thisInterface = theInterfaces.nextElement();
- if (thisInterface.getInetAddresses().hasMoreElements()) {
+ // 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 (int i = 0; i < realInterfaces.size(); i++) {
- NetworkInterface thisInterface = realInterfaces.get(i);
- if (!thisInterface.supportsMulticast()) {
- // Skip interfaces that do not support multicast - there's no point in proving
- // they cannot send / receive multicast messages.
- continue;
- }
-
- // get the first address on the interface
-
- // start server which is joined to the group and has
- // only asked for packets on this interface
+ for (NetworkInterface thisInterface : realInterfaces) {
+ // Find a suitable group IP and interface to use to sent packets to thisInterface.
Enumeration<InetAddress> addresses = thisInterface.getInetAddresses();
NetworkInterface sendingInterface = null;
@@ -358,57 +335,69 @@
InetAddress firstAddress = addresses.nextElement();
if (firstAddress instanceof Inet4Address) {
group = GOOD_IPv4;
- sendingInterface = networkInterface1;
+ sendingInterface = ipv4NetworkInterface;
} else {
// if this interface only seems to support IPV6 addresses
group = GOOD_IPv6;
- sendingInterface = IPV6networkInterface1;
+ sendingInterface = ipv6NetworkInterface;
}
}
- MulticastServer server = new MulticastServer(group, 0, thisInterface);
- server.start();
- Thread.sleep(1000);
+ // Create a receivingSocket which is joined to the group and has only asked for packets
+ // on thisInterface.
+ MulticastSocket receivingSocket = createReceivingSocket(0);
+ InetSocketAddress groupAddress =
+ new InetSocketAddress(group, receivingSocket.getLocalPort());
+ receivingSocket.joinGroup(groupAddress, thisInterface);
- // Now send out a package on interface networkInterface 1. We should
- // only see the packet if we send it on interface 1
- MulticastSocket mss = new MulticastSocket(0);
- mss.setNetworkInterface(sendingInterface);
- String msg = "Hello World - Again" + thisInterface.getName();
- DatagramPacket sdp = new DatagramPacket(msg.getBytes(), msg.length(), group,
- server.ms.getLocalPort());
- mss.send(sdp);
- Thread.sleep(1000);
- if (thisInterface.equals(sendingInterface)) {
+ // Now send out a packet on sendingInterface. We should only see the packet if we send
+ // it on thisInterface.
+ MulticastSocket sendingSocket = new MulticastSocket(0);
+ sendingSocket.setNetworkInterface(sendingInterface);
+ String msg = "Hello World - Again " + thisInterface.getName();
+ DatagramPacket sdp = createSendDatagramPacket(groupAddress, msg);
+ sendingSocket.send(sdp);
+
+ DatagramPacket rdp = createReceiveDatagramPacket();
+ try {
+ receivingSocket.receive(rdp);
+
+ // If the packet is received....
+ assertEquals(thisInterface, sendingInterface);
assertEquals("Group member did not recv data when bound on specific interface",
- msg, new String(server.rdp.getData(), 0, server.rdp.getLength()));
- } else {
- assertFalse("Group member received data on other interface when only asked for it on one interface: ",
- new String(server.rdp.getData(), 0, server.rdp.getLength()).equals(msg));
+ msg, extractMessage(rdp));
+ } catch (SocketTimeoutException e) {
+ // If the packet was not received...
+ assertTrue(!thisInterface.equals(sendingInterface));
}
- server.stopServer();
- mss.close();
+ receivingSocket.close();
+ sendingSocket.close();
}
}
- public void test_joinGroupLjava_net_SocketAddressLjava_net_NetworkInterface_multiple_joins_IPv4() throws Exception {
- test_joinGroupLjava_net_SocketAddressLjava_net_NetworkInterface_multiple_joins(GOOD_IPv4);
+ public void test_joinGroupLjava_net_SocketAddressLjava_net_NetworkInterface_multiple_joins_IPv4()
+ throws Exception {
+ test_joinGroupLjava_net_SocketAddressLjava_net_NetworkInterface_multiple_joins(
+ ipv4NetworkInterface, GOOD_IPv4);
}
- public void test_joinGroupLjava_net_SocketAddressLjava_net_NetworkInterface_multiple_joins_IPv6() throws Exception {
- test_joinGroupLjava_net_SocketAddressLjava_net_NetworkInterface_multiple_joins(GOOD_IPv6);
+ public void test_joinGroupLjava_net_SocketAddressLjava_net_NetworkInterface_multiple_joins_IPv6()
+ throws Exception {
+ test_joinGroupLjava_net_SocketAddressLjava_net_NetworkInterface_multiple_joins(
+ ipv6NetworkInterface, GOOD_IPv6);
}
- private void test_joinGroupLjava_net_SocketAddressLjava_net_NetworkInterface_multiple_joins(InetAddress group) throws Exception {
- // validate that we can join the same address on two
- // different interfaces but not on the same interface
+ private void test_joinGroupLjava_net_SocketAddressLjava_net_NetworkInterface_multiple_joins(
+ NetworkInterface networkInterface, InetAddress group) throws Exception {
+ // Validate that we can join the same address on two different interfaces but not on the
+ // same interface.
MulticastSocket mss = new MulticastSocket(0);
SocketAddress groupSockAddr = new InetSocketAddress(group, mss.getLocalPort());
- mss.joinGroup(groupSockAddr, networkInterface1);
+ mss.joinGroup(groupSockAddr, networkInterface);
mss.joinGroup(groupSockAddr, loopbackInterface);
try {
- mss.joinGroup(groupSockAddr, networkInterface1);
+ mss.joinGroup(groupSockAddr, networkInterface);
fail("Did not get expected exception when joining for second time on same interface");
} catch (IOException e) {
}
@@ -426,9 +415,9 @@
private void test_leaveGroupLjava_net_InetAddress(InetAddress group) throws Exception {
String msg = "Hello World";
MulticastSocket mss = new MulticastSocket(0);
- DatagramPacket sdp = new DatagramPacket(msg.getBytes(), msg.length(), group,
- mss.getLocalPort());
- mss.send(sdp, (byte) 10);
+ InetSocketAddress groupAddress = new InetSocketAddress(group, mss.getLocalPort());
+ DatagramPacket sdp = createSendDatagramPacket(groupAddress, msg);
+ mss.send(sdp, (byte) 10 /* ttl */);
try {
// Try to leave a group we didn't join.
mss.leaveGroup(group);
@@ -468,15 +457,21 @@
mss.close();
}
- public void test_leaveGroupLjava_net_SocketAddressLjava_net_NetworkInterface_IPv4() throws Exception {
- test_leaveGroupLjava_net_SocketAddressLjava_net_NetworkInterface(GOOD_IPv4, BAD_IPv4);
+ public void test_leaveGroupLjava_net_SocketAddressLjava_net_NetworkInterface_IPv4()
+ throws Exception {
+ test_leaveGroupLjava_net_SocketAddressLjava_net_NetworkInterface(
+ ipv4NetworkInterface, GOOD_IPv4, BAD_IPv4);
}
- public void test_leaveGroupLjava_net_SocketAddressLjava_net_NetworkInterface_IPv6() throws Exception {
- test_leaveGroupLjava_net_SocketAddressLjava_net_NetworkInterface(GOOD_IPv6, BAD_IPv6);
+ public void test_leaveGroupLjava_net_SocketAddressLjava_net_NetworkInterface_IPv6()
+ throws Exception {
+ test_leaveGroupLjava_net_SocketAddressLjava_net_NetworkInterface(
+ ipv6NetworkInterface, GOOD_IPv6, BAD_IPv6);
}
- private void test_leaveGroupLjava_net_SocketAddressLjava_net_NetworkInterface(InetAddress group, InetAddress group2) throws Exception {
+ private void test_leaveGroupLjava_net_SocketAddressLjava_net_NetworkInterface(
+ NetworkInterface networkInterface, InetAddress group, InetAddress group2)
+ throws Exception {
SocketAddress groupSockAddr = null;
SocketAddress groupSockAddr2 = null;
@@ -491,20 +486,20 @@
}
groupSockAddr2 = new InetSocketAddress(group2, mss.getLocalPort());
- mss.joinGroup(groupSockAddr, networkInterface1);
+ mss.joinGroup(groupSockAddr, networkInterface);
try {
- mss.leaveGroup(groupSockAddr2, networkInterface1);
+ mss.leaveGroup(groupSockAddr2, networkInterface);
fail("Did not get exception when trying to leave group that was never joined");
} catch (IOException expected) {
}
- mss.leaveGroup(groupSockAddr, networkInterface1);
+ mss.leaveGroup(groupSockAddr, networkInterface);
- mss.joinGroup(groupSockAddr, networkInterface1);
+ mss.joinGroup(groupSockAddr, networkInterface);
try {
mss.leaveGroup(groupSockAddr, loopbackInterface);
fail("Did not get exception when trying to leave group on wrong interface " +
- "joined on [" + networkInterface1 + "] left on [" + loopbackInterface + "]");
+ "joined on [" + networkInterface + "] left on [" + loopbackInterface + "]");
} catch (IOException expected) {
}
}
@@ -519,31 +514,36 @@
private void test_sendLjava_net_DatagramPacketB(InetAddress group) throws Exception {
String msg = "Hello World";
- MulticastSocket mss = new MulticastSocket(0);
- MulticastServer server = new MulticastServer(group, mss.getLocalPort());
- server.start();
- Thread.sleep(200);
- DatagramPacket sdp = new DatagramPacket(msg.getBytes(), msg.length(), group, mss.getLocalPort());
- mss.send(sdp, (byte) 10);
- Thread.sleep(1000);
- mss.close();
- byte[] data = server.rdp.getData();
- int length = server.rdp.getLength();
- assertEquals("Failed to send data. Received " + length, msg, new String(data, 0, length));
- server.stopServer();
+ MulticastSocket sendingSocket = new MulticastSocket(0);
+ MulticastSocket receivingSocket = createReceivingSocket(sendingSocket.getLocalPort());
+ receivingSocket.joinGroup(group);
+
+ InetSocketAddress groupAddress = new InetSocketAddress(group, sendingSocket.getLocalPort());
+ DatagramPacket sdp = createSendDatagramPacket(groupAddress, msg);
+ sendingSocket.send(sdp, (byte) 10 /* ttl */);
+ sendingSocket.close();
+
+ DatagramPacket rdp = createReceiveDatagramPacket();
+ receivingSocket.receive(rdp);
+ String receivedMessage = extractMessage(rdp);
+ assertEquals("Failed to send data. Received " + rdp.getLength(), msg, receivedMessage);
+ receivingSocket.close();
}
public void test_setInterfaceLjava_net_InetAddress() throws Exception {
MulticastSocket mss = new MulticastSocket();
mss.setInterface(InetAddress.getLocalHost());
InetAddress theInterface = mss.getInterface();
- // under IPV6 we are not guarrenteed to get the same address back as
- // the address, all we should be guaranteed is that we get an
- // address on the same interface
+ // Under IPV6 we are not guaranteed to get the same address back as the address that was
+ // set, all we should be guaranteed is that we get an address on the same interface.
if (theInterface instanceof Inet6Address) {
- assertTrue("Failed to return correct interface IPV6", NetworkInterface.getByInetAddress(mss.getInterface()).equals(NetworkInterface.getByInetAddress(theInterface)));
+ assertEquals("Failed to return correct interface IPV6",
+ NetworkInterface.getByInetAddress(mss.getInterface()),
+ NetworkInterface.getByInetAddress(theInterface));
} else {
- assertTrue("Failed to return correct interface IPV4 got:" + mss.getInterface() + " excpeted: " + InetAddress.getLocalHost(), mss.getInterface().equals(InetAddress.getLocalHost()));
+ assertTrue("Failed to return correct interface IPV4 got:" + mss.getInterface() +
+ " expected: " + InetAddress.getLocalHost(),
+ mss.getInterface().equals(InetAddress.getLocalHost()));
}
mss.close();
}
@@ -556,7 +556,7 @@
test_setInterface_unbound_address(GOOD_IPv6);
}
- // Regression test for Harmony-2410
+ // Regression test for Harmony-2410.
private void test_setInterface_unbound_address(InetAddress address) throws Exception {
MulticastSocket mss = new MulticastSocket();
try {
@@ -568,7 +568,7 @@
}
public void test_setNetworkInterfaceLjava_net_NetworkInterface_null() throws Exception {
- // validate that null interface is handled ok
+ // Validate that null interface is handled ok.
MulticastSocket mss = new MulticastSocket();
try {
mss.setNetworkInterface(null);
@@ -579,10 +579,11 @@
}
public void test_setNetworkInterfaceLjava_net_NetworkInterface_round_trip() throws Exception {
- // validate that we can get and set the interface
+ // Validate that we can get and set the interface.
MulticastSocket mss = new MulticastSocket();
- mss.setNetworkInterface(networkInterface1);
- assertEquals("Interface did not seem to be set by setNeworkInterface", networkInterface1, mss.getNetworkInterface());
+ mss.setNetworkInterface(ipv4NetworkInterface);
+ assertEquals("Interface did not seem to be set by setNeworkInterface",
+ ipv4NetworkInterface, mss.getNetworkInterface());
mss.close();
}
@@ -594,35 +595,35 @@
test_setNetworkInterfaceLjava_net_NetworkInterface(GOOD_IPv6);
}
- private void test_setNetworkInterfaceLjava_net_NetworkInterface(InetAddress group) throws IOException, InterruptedException {
- // set up the server and join the group
+ private void test_setNetworkInterfaceLjava_net_NetworkInterface(InetAddress group)
+ throws IOException, InterruptedException {
+ // Set up the receiving socket and join the group.
Enumeration theInterfaces = NetworkInterface.getNetworkInterfaces();
while (theInterfaces.hasMoreElements()) {
NetworkInterface thisInterface = (NetworkInterface) theInterfaces.nextElement();
if (thisInterface.getInetAddresses().hasMoreElements() && thisInterface.isUp()) {
if ((!(thisInterface.getInetAddresses().nextElement()).isLoopbackAddress())) {
- MulticastServer server = new MulticastServer(group, 0);
- server.start();
- // give the server some time to start up
- Thread.sleep(1000);
+ MulticastSocket receivingSocket = createReceivingSocket(0);
+ InetSocketAddress groupAddress =
+ new InetSocketAddress(group, receivingSocket.getLocalPort());
+ receivingSocket.joinGroup(groupAddress, thisInterface);
- // Send the packets on a particular interface. The
- // source address in the received packet
- // should be one of the addresses for the interface
- // set
- MulticastSocket mss = new MulticastSocket(0);
- mss.setNetworkInterface(thisInterface);
+ // Send the packets on a particular interface. The source address in the
+ // received packet should be one of the addresses for the interface set.
+ MulticastSocket sendingSocket = new MulticastSocket(0);
+ sendingSocket.setNetworkInterface(thisInterface);
String msg = thisInterface.getName();
- byte theBytes[] = msg.getBytes();
- DatagramPacket sdp = new DatagramPacket(theBytes, theBytes.length, group,
- server.ms.getLocalPort());
- mss.send(sdp);
- Thread.sleep(1000);
- String receivedMessage = new String(server.rdp.getData(), 0, server.rdp.getLength());
- assertEquals("Group member did not recv data sent on a specific interface", msg, receivedMessage);
- // stop the server
- server.stopServer();
- mss.close();
+ DatagramPacket sdp = createSendDatagramPacket(groupAddress, msg);
+ sendingSocket.send(sdp);
+
+ DatagramPacket rdp = createReceiveDatagramPacket();
+ receivingSocket.receive(rdp);
+ String receivedMessage = extractMessage(rdp);
+ assertEquals("Group member did not recv data sent on a specific interface",
+ msg, receivedMessage);
+ // Stop the server.
+ receivingSocket.close();
+ sendingSocket.close();
}
}
}
@@ -651,24 +652,28 @@
assertTrue("should be bound", ms.isBound() && !ms.isClosed() && !ms.isConnected());
ms.close();
assertTrue("should be closed", ms.isClosed());
+
ms = new MulticastSocket(0);
assertTrue("should be bound", ms.isBound() && !ms.isClosed() && !ms.isConnected());
ms.close();
assertTrue("should be closed", ms.isClosed());
+
ms = new MulticastSocket(0);
assertTrue("should be bound", ms.isBound() && !ms.isClosed() && !ms.isConnected());
ms.close();
assertTrue("should be closed", ms.isClosed());
+
try {
- ms = new MulticastSocket(new InetSocketAddress("unresolvedname", 31415));
+ new MulticastSocket(new InetSocketAddress("unresolvedname", 31415));
fail();
} catch (IOException expected) {
}
- // regression test for Harmony-1162
+ // Regression test for Harmony-1162.
InetSocketAddress addr = new InetSocketAddress("0.0.0.0", 0);
MulticastSocket s = new MulticastSocket(addr);
assertTrue(s.getReuseAddress());
+ s.close();
}
public void test_getLoopbackMode() throws Exception {
@@ -699,129 +704,69 @@
}
private void test_setLoopbackModeSendReceive(InetAddress group) throws IOException {
+ // Test send receive.
final String message = "Hello, world!";
- // test send receive
MulticastSocket socket = new MulticastSocket(0);
socket.setLoopbackMode(false); // false indicates doing loop back
socket.joinGroup(group);
- // send the datagram
- byte[] sendData = message.getBytes();
- DatagramPacket sendDatagram = new DatagramPacket(sendData, 0, sendData.length,
- new InetSocketAddress(group, socket.getLocalPort()));
+ // Send the datagram.
+ InetSocketAddress groupAddress = new InetSocketAddress(group, socket.getLocalPort());
+ DatagramPacket sendDatagram = createSendDatagramPacket(groupAddress, message);
socket.send(sendDatagram);
- // receive the datagram
- byte[] recvData = new byte[100];
- DatagramPacket recvDatagram = new DatagramPacket(recvData, recvData.length);
- socket.setSoTimeout(5000); // prevent eternal block in
+ // Receive the datagram.
+ DatagramPacket recvDatagram = createReceiveDatagramPacket();
+ socket.setSoTimeout(5000); // Prevent eternal block in.
socket.receive(recvDatagram);
- String recvMessage = new String(recvData, 0, recvDatagram.getLength());
+ String recvMessage = extractMessage(recvDatagram);
assertEquals(message, recvMessage);
socket.close();
}
public void test_setReuseAddressZ() throws Exception {
- // test case were we set it to false
- MulticastSocket theSocket1 = null;
- MulticastSocket theSocket2 = null;
+ // Test case were we to set ReuseAddress to false.
+ MulticastSocket theSocket1 = new MulticastSocket(null);
+ theSocket1.setReuseAddress(false);
+
+ MulticastSocket theSocket2 = new MulticastSocket(null);
+ theSocket2.setReuseAddress(false);
+
+ InetSocketAddress addr = new InetSocketAddress(Inet4Address.getLocalHost(), 0);
+ theSocket1.bind(addr);
+ addr = new InetSocketAddress(Inet4Address.getLocalHost(), theSocket1.getLocalPort());
try {
- theSocket1 = new MulticastSocket(null);
- theSocket2 = new MulticastSocket(null);
- theSocket1.setReuseAddress(false);
- theSocket2.setReuseAddress(false);
- InetSocketAddress addr = new InetSocketAddress(Inet4Address.getLocalHost(), 0);
- theSocket1.bind(addr);
- addr = new InetSocketAddress(Inet4Address.getLocalHost(), theSocket1.getLocalPort());
theSocket2.bind(addr);
- fail("No exception when trying to connect to do duplicate socket bind with re-useaddr set to false");
+ fail("No exception when trying to connect to do duplicate socket bind with re-useaddr"
+ + " set to false");
} catch (BindException expected) {
}
- if (theSocket1 != null) {
- theSocket1.close();
- }
- if (theSocket2 != null) {
- theSocket2.close();
- }
+ theSocket1.close();
+ theSocket2.close();
- // test case were we set it to true
+ // Test case were we set it to true.
theSocket1 = new MulticastSocket(null);
theSocket2 = new MulticastSocket(null);
theSocket1.setReuseAddress(true);
theSocket2.setReuseAddress(true);
- InetSocketAddress addr = new InetSocketAddress(Inet4Address.getLocalHost(), 0);
+ addr = new InetSocketAddress(Inet4Address.getLocalHost(), 0);
theSocket1.bind(addr);
addr = new InetSocketAddress(Inet4Address.getLocalHost(), theSocket1.getLocalPort());
theSocket2.bind(addr);
- if (theSocket1 != null) {
- theSocket1.close();
- }
- if (theSocket2 != null) {
- theSocket2.close();
- }
+ theSocket1.close();
+ theSocket2.close();
- // test the default case which we expect to be
- // the same on all platforms
+ // Test the default case which we expect to be the same on all platforms.
theSocket1 = new MulticastSocket(null);
theSocket2 = new MulticastSocket(null);
addr = new InetSocketAddress(Inet4Address.getLocalHost(), 0);
theSocket1.bind(addr);
addr = new InetSocketAddress(Inet4Address.getLocalHost(), theSocket1.getLocalPort());
theSocket2.bind(addr);
- if (theSocket1 != null) {
- theSocket1.close();
- }
- if (theSocket2 != null) {
- theSocket2.close();
- }
- }
-
- @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();
-
- // only consider interfaces that have addresses associated with them.
- // Otherwise tests don't work so well
- if (interfaces != null) {
- boolean atLeastOneInterface = false;
- while (interfaces.hasMoreElements() && (atLeastOneInterface == false)) {
- networkInterface1 = interfaces.nextElement();
- if (willWorkForMulticast(networkInterface1)) {
- atLeastOneInterface = true;
- }
- }
-
- assertTrue("Test environment must have at least one environment capable of multicast",
- atLeastOneInterface);
-
- // Find the first multicast-compatible interface that supports IPV6 if one exists
- interfaces = NetworkInterface.getNetworkInterfaces();
-
- boolean found = false;
- while (interfaces.hasMoreElements() && !found) {
- NetworkInterface nextInterface = interfaces.nextElement();
- if (willWorkForMulticast(nextInterface)) {
- Enumeration<InetAddress> addresses = nextInterface.getInetAddresses();
- while (addresses.hasMoreElements()) {
- final InetAddress nextAddress = addresses.nextElement();
- if (nextAddress instanceof Inet6Address) {
- IPV6networkInterface1 = nextInterface;
- found = true;
- break;
- }
- }
- }
- }
- }
+ theSocket1.close();
+ theSocket2.close();
}
private static boolean willWorkForMulticast(NetworkInterface iface) throws IOException {
@@ -831,4 +776,26 @@
&& !iface.isLoopback() && iface.supportsMulticast()
&& iface.getInetAddresses().hasMoreElements();
}
+
+ private static MulticastSocket createReceivingSocket(int aPort) throws IOException {
+ MulticastSocket ms = new MulticastSocket(aPort);
+ ms.setSoTimeout(2000);
+ return ms;
+ }
+
+ private static DatagramPacket createReceiveDatagramPacket() {
+ byte[] rbuf = new byte[512];
+ return new DatagramPacket(rbuf, rbuf.length);
+ }
+
+ private static DatagramPacket createSendDatagramPacket(
+ InetSocketAddress groupAndPort, String msg) {
+ return new DatagramPacket(
+ msg.getBytes(), msg.length(), groupAndPort.getAddress(), groupAndPort.getPort());
+ }
+
+ private static String extractMessage(DatagramPacket rdp) {
+ return new String(rdp.getData(), 0, rdp.getLength());
+ }
+
}
diff --git a/include/ScopedIcuLocale.h b/include/ScopedIcuLocale.h
new file mode 100644
index 0000000..2109e03
--- /dev/null
+++ b/include/ScopedIcuLocale.h
@@ -0,0 +1,62 @@
+/*
+ * 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.
+ */
+
+#ifndef SCOPED_ICU_LOCALE_H_included
+#define SCOPED_ICU_LOCALE_H_included
+
+#include "JNIHelp.h"
+#include "ScopedUtfChars.h"
+#include "unicode/locid.h"
+
+class ScopedIcuLocale {
+ public:
+ ScopedIcuLocale(JNIEnv* env, jstring javaLocaleName) : mEnv(env) {
+ mLocale.setToBogus();
+
+ if (javaLocaleName == NULL) {
+ jniThrowNullPointerException(mEnv, "javaLocaleName == null");
+ return;
+ }
+
+ const ScopedUtfChars localeName(env, javaLocaleName);
+ if (localeName.c_str() == NULL) {
+ return;
+ }
+
+ mLocale = Locale::createFromName(localeName.c_str());
+ }
+
+ ~ScopedIcuLocale() {
+ }
+
+ bool valid() const {
+ return !mLocale.isBogus();
+ }
+
+ Locale& locale() {
+ return mLocale;
+ }
+
+ private:
+ JNIEnv* const mEnv;
+ Locale mLocale;
+
+ // Disallow copy and assignment.
+ ScopedIcuLocale(const ScopedIcuLocale&);
+ void operator=(const ScopedIcuLocale&);
+};
+
+#endif // SCOPED_ICU_LOCALE_H_included
diff --git a/luni/src/main/java/java/lang/CaseMapper.java b/luni/src/main/java/java/lang/CaseMapper.java
index 4e411d1..1da621c 100644
--- a/luni/src/main/java/java/lang/CaseMapper.java
+++ b/luni/src/main/java/java/lang/CaseMapper.java
@@ -49,7 +49,7 @@
// Note that Greek isn't a particularly hard case for toLowerCase, only toUpperCase.
String languageCode = locale.getLanguage();
if (languageCode.equals("tr") || languageCode.equals("az") || languageCode.equals("lt")) {
- return ICU.toLowerCase(s, locale.toString());
+ return ICU.toLowerCase(s, locale);
}
char[] newValue = null;
@@ -59,7 +59,7 @@
char newCh;
if (ch == LATIN_CAPITAL_I_WITH_DOT || Character.isHighSurrogate(ch)) {
// Punt these hard cases.
- return ICU.toLowerCase(s, locale.toString());
+ return ICU.toLowerCase(s, locale);
} else if (ch == GREEK_CAPITAL_SIGMA && isFinalSigma(value, offset, count, i)) {
newCh = GREEK_SMALL_FINAL_SIGMA;
} else {
@@ -150,7 +150,7 @@
public static String toUpperCase(Locale locale, String s, char[] value, int offset, int count) {
String languageCode = locale.getLanguage();
if (languageCode.equals("tr") || languageCode.equals("az") || languageCode.equals("lt")) {
- return ICU.toUpperCase(s, locale.toString());
+ return ICU.toUpperCase(s, locale);
}
if (languageCode.equals("el")) {
return EL_UPPER.get().transliterate(s);
@@ -161,7 +161,7 @@
for (int o = offset, end = offset + count; o < end; o++) {
char ch = value[o];
if (Character.isHighSurrogate(ch)) {
- return ICU.toUpperCase(s, locale.toString());
+ return ICU.toUpperCase(s, locale);
}
int index = upperIndex(ch);
if (index == -1) {
diff --git a/luni/src/main/java/java/lang/Character.java b/luni/src/main/java/java/lang/Character.java
index 59931f6..f088c24 100644
--- a/luni/src/main/java/java/lang/Character.java
+++ b/luni/src/main/java/java/lang/Character.java
@@ -1535,6 +1535,7 @@
* don't have a corresponding {@code UnicodeScript} will be in {@code UNKNOWN}.
*
* @since 1.7
+ * @hide 1.7
*/
public static enum UnicodeScript {
/** ISO 15924 English name "Arabic" */
diff --git a/luni/src/main/java/java/net/HttpCookie.java b/luni/src/main/java/java/net/HttpCookie.java
index 1d8a8cc..3748b9f 100644
--- a/luni/src/main/java/java/net/HttpCookie.java
+++ b/luni/src/main/java/java/net/HttpCookie.java
@@ -564,6 +564,7 @@
* to scripts in a browser.
*
* @since 1.7
+ * @hide 1.7
*/
public boolean isHttpOnly() {
return httpOnly;
@@ -574,6 +575,7 @@
* to scripts in a browser.
*
* @since 1.7
+ * @hide 1.7
*/
public void setHttpOnly(boolean httpOnly) {
this.httpOnly = httpOnly;
diff --git a/luni/src/main/java/java/net/SocketOption.java b/luni/src/main/java/java/net/SocketOption.java
index bc3e101..2bd4c6d 100644
--- a/luni/src/main/java/java/net/SocketOption.java
+++ b/luni/src/main/java/java/net/SocketOption.java
@@ -27,6 +27,7 @@
*
* @param <T> the type of the value
* @since 1.7
+ * @hide 1.7
*/
public interface SocketOption<T> {
diff --git a/luni/src/main/java/java/net/StandardSocketOptions.java b/luni/src/main/java/java/net/StandardSocketOptions.java
index a793f66..d61d937 100644
--- a/luni/src/main/java/java/net/StandardSocketOptions.java
+++ b/luni/src/main/java/java/net/StandardSocketOptions.java
@@ -32,6 +32,7 @@
* for each type of socket.
*
* @since 1.7
+ * @hide 1.7
*/
public final class StandardSocketOptions {
diff --git a/luni/src/main/java/java/net/URLConnection.java b/luni/src/main/java/java/net/URLConnection.java
index d24e273..5147b7b 100644
--- a/luni/src/main/java/java/net/URLConnection.java
+++ b/luni/src/main/java/java/net/URLConnection.java
@@ -320,6 +320,7 @@
* {@code content-length} or {@code -1} if this field is not set.
*
* @since 1.7
+ * @hide 1.7
*/
public long getContentLengthLong() {
return getHeaderFieldLong("Content-Length", -1);
@@ -567,6 +568,7 @@
* the default value if no field has been found.
* @return the value of the specified header field as a number.
* @since 1.7
+ * @hide 1.7
*/
public long getHeaderFieldLong(String field, long defaultValue) {
try {
diff --git a/luni/src/main/java/java/nio/channels/AlreadyBoundException.java b/luni/src/main/java/java/nio/channels/AlreadyBoundException.java
index 70c70ac..e76b574 100644
--- a/luni/src/main/java/java/nio/channels/AlreadyBoundException.java
+++ b/luni/src/main/java/java/nio/channels/AlreadyBoundException.java
@@ -19,6 +19,9 @@
/**
* An {@code AlreadyBoundException} is thrown when an attempt is made to bind a NetworkChannel that
* is already bound.
+ *
+ * @since 1.7
+ * @hide 1.7
*/
public class AlreadyBoundException extends IllegalStateException {
diff --git a/luni/src/main/java/java/nio/channels/DatagramChannel.java b/luni/src/main/java/java/nio/channels/DatagramChannel.java
index b0cc2ac..7278655 100644
--- a/luni/src/main/java/java/nio/channels/DatagramChannel.java
+++ b/luni/src/main/java/java/nio/channels/DatagramChannel.java
@@ -92,6 +92,10 @@
*/
public abstract DatagramSocket socket();
+ /**
+ * @since 1.7
+ * @hide 1.7
+ */
@Override
public DatagramChannel bind(SocketAddress local) throws IOException {
// This method was added for interoperability with Java 7, where it is abstract. It is
@@ -99,6 +103,10 @@
throw new UnsupportedOperationException("Subclasses must override this method");
}
+ /**
+ * @since 1.7
+ * @hide 1.7
+ */
@Override
public SocketAddress getLocalAddress() throws IOException {
// This method was added for interoperability with Java 7, where it is abstract. It is
@@ -106,6 +114,10 @@
throw new UnsupportedOperationException("Subclasses must override this method");
}
+ /**
+ * @since 1.7
+ * @hide 1.7
+ */
@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
@@ -113,6 +125,10 @@
throw new UnsupportedOperationException("Subclasses must override this method");
}
+ /**
+ * @since 1.7
+ * @hide 1.7
+ */
@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
@@ -120,6 +136,10 @@
throw new UnsupportedOperationException("Subclasses must override this method");
}
+ /**
+ * @since 1.7
+ * @hide 1.7
+ */
@Override
public Set<SocketOption<?>> supportedOptions() {
// This method was added for interoperability with Java 7, where it is abstract. It is
@@ -127,6 +147,10 @@
throw new UnsupportedOperationException("Subclasses must override this method");
}
+ /**
+ * @since 1.7
+ * @hide 1.7
+ */
@Override
public MembershipKey join(InetAddress groupAddress, NetworkInterface networkInterface)
throws IOException {
@@ -135,6 +159,10 @@
throw new UnsupportedOperationException("Subclasses must override this method");
}
+ /**
+ * @since 1.7
+ * @hide 1.7
+ */
@Override
public MembershipKey join(InetAddress groupAddress, NetworkInterface networkInterface,
InetAddress sourceAddress) throws IOException {
diff --git a/luni/src/main/java/java/nio/channels/FileChannel.java b/luni/src/main/java/java/nio/channels/FileChannel.java
index 3989167..59dc26e 100644
--- a/luni/src/main/java/java/nio/channels/FileChannel.java
+++ b/luni/src/main/java/java/nio/channels/FileChannel.java
@@ -77,7 +77,7 @@
* content, size, etc.
*/
public abstract class FileChannel extends AbstractInterruptibleChannel
- implements GatheringByteChannel, ScatteringByteChannel, SeekableByteChannel {
+ implements ByteChannel, GatheringByteChannel, ScatteringByteChannel, SeekableByteChannel {
/**
* {@code MapMode} defines file mapping mode constants.
diff --git a/luni/src/main/java/java/nio/channels/FileLock.java b/luni/src/main/java/java/nio/channels/FileLock.java
index d1ba872..986527c 100644
--- a/luni/src/main/java/java/nio/channels/FileLock.java
+++ b/luni/src/main/java/java/nio/channels/FileLock.java
@@ -107,7 +107,7 @@
}
/**
- * Returns the lock's {@link FileChannel}. This method has been superseded by {@link #acquiredBy()}.
+ * Returns the lock's {@link FileChannel}.
*/
public final FileChannel channel() {
return channel;
@@ -117,7 +117,9 @@
* Returns the {@link Channel} that holds this lock.
*
* @since 1.7
+ * @hide 1.7
*/
+ // Add "This method has been superseded by {@link #acquiredBy()}." to channel when unhiding.
public Channel acquiredBy() {
return channel;
}
diff --git a/luni/src/main/java/java/nio/channels/MembershipKey.java b/luni/src/main/java/java/nio/channels/MembershipKey.java
index a7eecac..ed8caad 100644
--- a/luni/src/main/java/java/nio/channels/MembershipKey.java
+++ b/luni/src/main/java/java/nio/channels/MembershipKey.java
@@ -36,6 +36,7 @@
* Multicast Source Filters</a> for concepts and terminology associated with multicast membership.
*
* @since 1.7
+ * @hide 1.7
*/
public abstract class MembershipKey {
diff --git a/luni/src/main/java/java/nio/channels/MulticastChannel.java b/luni/src/main/java/java/nio/channels/MulticastChannel.java
index 47433d0..b8e6c8b 100644
--- a/luni/src/main/java/java/nio/channels/MulticastChannel.java
+++ b/luni/src/main/java/java/nio/channels/MulticastChannel.java
@@ -69,6 +69,7 @@
* information.
*
* @since 1.7
+ * @hide 1.7
*/
public interface MulticastChannel extends NetworkChannel {
@@ -110,6 +111,8 @@
* if the channel is closed
* @throws IOException
* if some other I/O error occurs
+ * @since 1.7
+ * @hide 1.7
*/
MembershipKey join(InetAddress groupAddress, NetworkInterface networkInterface)
throws IOException;
@@ -148,6 +151,8 @@
* if the channel is closed
* @throws IOException
* if some other I/O error occurs
+ * @since 1.7
+ * @hide 1.7
*/
MembershipKey join(
InetAddress groupAddress, NetworkInterface networkInterface, InetAddress sourceAddress)
diff --git a/luni/src/main/java/java/nio/channels/NetworkChannel.java b/luni/src/main/java/java/nio/channels/NetworkChannel.java
index 3ae1e6b..31b81d5 100644
--- a/luni/src/main/java/java/nio/channels/NetworkChannel.java
+++ b/luni/src/main/java/java/nio/channels/NetworkChannel.java
@@ -26,6 +26,7 @@
* A common interface for channels that are backed by network sockets.
*
* @since 1.7
+ * @hide 1.7
*/
public interface NetworkChannel extends AutoCloseable, Channel, Closeable {
@@ -45,14 +46,14 @@
* if the channel is already bound.
* @throws IOException
* if another I/O error occurs.
+ * @hide 1.7
*/
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.
+ * with {@code bind} 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}
@@ -62,6 +63,7 @@
* if the channel is closed.
* @throws IOException
* if another I/O error occurs.
+ * @hide 1.7
*/
SocketAddress getLocalAddress() throws IOException;
@@ -75,6 +77,7 @@
* @throws IOException
* if the value cannot be read.
* @see java.net.StandardSocketOptions
+ * @hide 1.7
*/
<T> T getOption(SocketOption<T> option) throws IOException;
@@ -91,11 +94,13 @@
* @throws IOException
* if the value cannot be written.
* @see java.net.StandardSocketOptions
+ * @hide 1.7
*/
<T> NetworkChannel setOption(SocketOption<T> option, T value) throws IOException;
/**
* Returns the set of socket options supported by this channel.
+ * @hide 1.7
*/
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
index da4671d..edd2645 100644
--- a/luni/src/main/java/java/nio/channels/SeekableByteChannel.java
+++ b/luni/src/main/java/java/nio/channels/SeekableByteChannel.java
@@ -34,6 +34,7 @@
* be queried.
*
* @since 1.7
+ * @hide 1.7
*/
public interface SeekableByteChannel extends ByteChannel {
diff --git a/luni/src/main/java/java/nio/channels/ServerSocketChannel.java b/luni/src/main/java/java/nio/channels/ServerSocketChannel.java
index 790344b..01adbc7 100644
--- a/luni/src/main/java/java/nio/channels/ServerSocketChannel.java
+++ b/luni/src/main/java/java/nio/channels/ServerSocketChannel.java
@@ -89,6 +89,8 @@
* {@inheritDoc}
*
* <p>This is equivalent to {@code bind(local, 0)}.
+ * @since 1.7
+ * @hide 1.7
*/
@Override
public final ServerSocketChannel bind(SocketAddress local) throws IOException {
@@ -114,6 +116,7 @@
* @throws IOException
* if another I/O error occurs.
* @since 1.7
+ * @hide 1.7
*/
public ServerSocketChannel bind(SocketAddress localAddr, int backlog) throws IOException {
// This method was added for interoperability with Java 7, where it is abstract. It is
@@ -121,6 +124,10 @@
throw new UnsupportedOperationException("Subclasses must override this method");
}
+ /**
+ * @since 1.7
+ * @hide 1.7
+ */
@Override
public SocketAddress getLocalAddress() throws IOException {
// This method was added for interoperability with Java 7, where it is abstract. It is
@@ -128,6 +135,10 @@
throw new UnsupportedOperationException("Subclasses must override this method");
}
+ /**
+ * @since 1.7
+ * @hide 1.7
+ */
@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
@@ -135,6 +146,10 @@
throw new UnsupportedOperationException("Subclasses must override this method");
}
+ /**
+ * @since 1.7
+ * @hide 1.7
+ */
@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
@@ -142,6 +157,10 @@
throw new UnsupportedOperationException("Subclasses must override this method");
}
+ /**
+ * @since 1.7
+ * @hide 1.7
+ */
@Override
public Set<SocketOption<?>> supportedOptions() {
// This method was added for interoperability with Java 7, where it is abstract. It is
diff --git a/luni/src/main/java/java/nio/channels/SocketChannel.java b/luni/src/main/java/java/nio/channels/SocketChannel.java
index e96c6a1..9788c99 100644
--- a/luni/src/main/java/java/nio/channels/SocketChannel.java
+++ b/luni/src/main/java/java/nio/channels/SocketChannel.java
@@ -142,6 +142,10 @@
*/
public abstract Socket socket();
+ /**
+ * @since 1.7
+ * @hide 1.7
+ */
@Override
public SocketChannel bind(SocketAddress local) throws IOException {
// This method was added for interoperability with Java 7, where it is abstract. It is
@@ -149,6 +153,10 @@
throw new UnsupportedOperationException("Subclasses must override this method");
}
+ /**
+ * @since 1.7
+ * @hide 1.7
+ */
@Override
public SocketAddress getLocalAddress() throws IOException {
// This method was added for interoperability with Java 7, where it is abstract. It is
@@ -156,6 +164,10 @@
throw new UnsupportedOperationException("Subclasses must override this method");
}
+ /**
+ * @since 1.7
+ * @hide 1.7
+ */
@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
@@ -163,6 +175,10 @@
throw new UnsupportedOperationException("Subclasses must override this method");
}
+ /**
+ * @since 1.7
+ * @hide 1.7
+ */
@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
@@ -170,6 +186,10 @@
throw new UnsupportedOperationException("Subclasses must override this method");
}
+ /**
+ * @since 1.7
+ * @hide 1.7
+ */
@Override
public Set<SocketOption<?>> supportedOptions() {
// This method was added for interoperability with Java 7, where it is abstract. It is
diff --git a/luni/src/main/java/java/text/BreakIterator.java b/luni/src/main/java/java/text/BreakIterator.java
index b14647c..81545b2 100644
--- a/luni/src/main/java/java/text/BreakIterator.java
+++ b/luni/src/main/java/java/text/BreakIterator.java
@@ -268,13 +268,9 @@
/**
* Returns a new instance of {@code BreakIterator} to iterate over
* characters using the given locale.
- *
- * @param where
- * the given locale.
- * @return a new instance of {@code BreakIterator} using the given locale.
*/
- public static BreakIterator getCharacterInstance(Locale where) {
- return new RuleBasedBreakIterator(NativeBreakIterator.getCharacterInstance(where));
+ public static BreakIterator getCharacterInstance(Locale locale) {
+ return new RuleBasedBreakIterator(NativeBreakIterator.getCharacterInstance(locale));
}
/**
@@ -290,14 +286,9 @@
/**
* Returns a new instance of {@code BreakIterator} to iterate over
* line breaks using the given locale.
- *
- * @param where
- * the given locale.
- * @return a new instance of {@code BreakIterator} using the given locale.
- * @throws NullPointerException if {@code where} is {@code null}.
*/
- public static BreakIterator getLineInstance(Locale where) {
- return new RuleBasedBreakIterator(NativeBreakIterator.getLineInstance(where));
+ public static BreakIterator getLineInstance(Locale locale) {
+ return new RuleBasedBreakIterator(NativeBreakIterator.getLineInstance(locale));
}
/**
@@ -313,14 +304,9 @@
/**
* Returns a new instance of {@code BreakIterator} to iterate over
* sentence-breaks using the given locale.
- *
- * @param where
- * the given locale.
- * @return a new instance of {@code BreakIterator} using the given locale.
- * @throws NullPointerException if {@code where} is {@code null}.
*/
- public static BreakIterator getSentenceInstance(Locale where) {
- return new RuleBasedBreakIterator(NativeBreakIterator.getSentenceInstance(where));
+ public static BreakIterator getSentenceInstance(Locale locale) {
+ return new RuleBasedBreakIterator(NativeBreakIterator.getSentenceInstance(locale));
}
/**
@@ -336,14 +322,9 @@
/**
* Returns a new instance of {@code BreakIterator} to iterate over
* word-breaks using the given locale.
- *
- * @param where
- * the given locale.
- * @return a new instance of {@code BreakIterator} using the given locale.
- * @throws NullPointerException if {@code where} is {@code null}.
*/
- public static BreakIterator getWordInstance(Locale where) {
- return new RuleBasedBreakIterator(NativeBreakIterator.getWordInstance(where));
+ public static BreakIterator getWordInstance(Locale locale) {
+ return new RuleBasedBreakIterator(NativeBreakIterator.getWordInstance(locale));
}
/**
diff --git a/luni/src/main/java/java/util/Currency.java b/luni/src/main/java/java/util/Currency.java
index 333ebc4..0dea411 100644
--- a/luni/src/main/java/java/util/Currency.java
+++ b/luni/src/main/java/java/util/Currency.java
@@ -35,7 +35,7 @@
private Currency(String currencyCode) {
this.currencyCode = currencyCode;
- String symbol = ICU.getCurrencySymbol(Locale.US.toString(), currencyCode);
+ String symbol = ICU.getCurrencySymbol(Locale.US, currencyCode);
if (symbol == null) {
throw new IllegalArgumentException("Unsupported ISO 4217 currency code: " +
currencyCode);
@@ -123,7 +123,7 @@
* @since 1.7
*/
public String getDisplayName(Locale locale) {
- return ICU.getCurrencyDisplayName(locale.toString(), currencyCode);
+ return ICU.getCurrencyDisplayName(locale, currencyCode);
}
/**
@@ -131,6 +131,7 @@
* zero is returned.
*
* @since 1.7
+ * @hide 1.7
*/
public int getNumericCode() {
return ICU.getCurrencyNumericCode(currencyCode);
@@ -167,7 +168,7 @@
}
// Try ICU, and fall back to the currency code if ICU has nothing.
- String symbol = ICU.getCurrencySymbol(locale.toString(), currencyCode);
+ String symbol = ICU.getCurrencySymbol(locale, currencyCode);
return symbol != null ? symbol : currencyCode;
}
diff --git a/luni/src/main/java/java/util/IllformedLocaleException.java b/luni/src/main/java/java/util/IllformedLocaleException.java
index 3dec1cd..ff844f7 100644
--- a/luni/src/main/java/java/util/IllformedLocaleException.java
+++ b/luni/src/main/java/java/util/IllformedLocaleException.java
@@ -22,6 +22,7 @@
* See {@link Locale} and {@link Locale.Builder}.
*
* @since 1.7
+ * @hide 1.7
*/
public class IllformedLocaleException extends RuntimeException {
diff --git a/luni/src/main/java/java/util/Locale.java b/luni/src/main/java/java/util/Locale.java
index 17eb26c..7c5ce5a 100644
--- a/luni/src/main/java/java/util/Locale.java
+++ b/luni/src/main/java/java/util/Locale.java
@@ -254,6 +254,7 @@
* See {@link #getExtension(char)} and {@link Builder#setExtension(char, String)}.
*
* @since 1.7
+ * @hide 1.7
*/
public static final char PRIVATE_USE_EXTENSION = 'x';
@@ -264,6 +265,7 @@
* See {@link #getExtension(char)} and {@link Builder#setExtension(char, String)}.
*
* @since 1.7
+ * @hide 1.7
*/
public static final char UNICODE_LOCALE_EXTENSION = 'u';
@@ -295,6 +297,7 @@
* the structured state (keywords and attributes) specified therein.
*
* @since 1.7
+ * @hide 1.7
*/
public static final class Builder {
private String language;
@@ -779,11 +782,13 @@
/**
* Returns a locale for a given BCP-47 language tag. This method is more
* lenient than {@link Builder#setLanguageTag}. For a given language tag, parsing
- * will proceed upto the first malformed subtag. All subsequent tags are discarded.
+ * will proceed up to the first malformed subtag. All subsequent tags are discarded.
+ * Note that language tags use {@code -} rather than {@code _}, for example {@code en-US}.
*
* @throws NullPointerException if {@code languageTag} is {@code null}.
*
* @since 1.7
+ * @hide 1.7
*/
public static Locale forLanguageTag(String languageTag) {
if (languageTag == null) {
@@ -887,17 +892,14 @@
if (hasValidatedFields) {
Set<String> attribsCopy = new TreeSet<String>(unicodeAttributes);
- Map<String, String> keywordsCopy = new TreeMap<String, String>(
- unicodeKeywords);
- Map<Character, String> extensionsCopy = new TreeMap<Character, String>(
- extensions);
+ Map<String, String> keywordsCopy = new TreeMap<String, String>(unicodeKeywords);
+ Map<Character, String> extensionsCopy = new TreeMap<Character, String>(extensions);
// We need to transform the list of attributes & keywords set on the
// builder to a unicode locale extension. i.e, if we have any keywords
// or attributes set, Locale#getExtension('u') should return a well
// formed extension.
- addUnicodeExtensionToExtensionsMap(attribsCopy, keywordsCopy,
- extensionsCopy);
+ addUnicodeExtensionToExtensionsMap(attribsCopy, keywordsCopy, extensionsCopy);
this.unicodeAttributes = Collections.unmodifiableSet(attribsCopy);
this.unicodeKeywords = Collections.unmodifiableMap(keywordsCopy);
@@ -1002,10 +1004,16 @@
if (countryCode.isEmpty()) {
return "";
}
- String result = ICU.getDisplayCountryNative(getIcuLocaleId(), locale.getIcuLocaleId());
+
+ try {
+ Builder.normalizeAndValidateRegion(countryCode);
+ } catch (IllformedLocaleException ex) {
+ return countryCode;
+ }
+
+ String result = ICU.getDisplayCountry(this, locale);
if (result == null) { // TODO: do we need to do this, or does ICU do it for us?
- result = ICU.getDisplayCountryNative(getIcuLocaleId(),
- Locale.getDefault().getIcuLocaleId());
+ result = ICU.getDisplayCountry(this, Locale.getDefault());
}
return result;
}
@@ -1026,19 +1034,24 @@
return "";
}
- // http://b/8049507 --- frameworks/base should use fil_PH instead of tl_PH.
- // Until then, we're stuck covering their tracks, making it look like they're
- // using "fil" when they're not.
- String localeString = toString();
- if (languageCode.equals("tl")) {
- localeString = toNewString("fil", countryCode, variantCode, scriptCode,
- extensions);
+ // Hacks for backward compatibility.
+ //
+ // Our language tag will contain "und" if the languageCode is invalid
+ // or missing. ICU will then return "langue indéterminée" or the equivalent
+ // display language for the indeterminate language code.
+ //
+ // Sigh... ugh... and what not.
+ try {
+ Builder.normalizeAndValidateLanguage(languageCode);
+ } catch (IllformedLocaleException ex) {
+ return languageCode;
}
- String result = ICU.getDisplayLanguageNative(localeString, locale.getIcuLocaleId());
+ // TODO: We need a new hack or a complete fix for http://b/8049507 --- We would
+ // cover the frameworks' tracks when they were using "tl" instead of "fil".
+ String result = ICU.getDisplayLanguage(this, locale);
if (result == null) { // TODO: do we need to do this, or does ICU do it for us?
- result = ICU.getDisplayLanguageNative(localeString,
- Locale.getDefault().getIcuLocaleId());
+ result = ICU.getDisplayLanguage(this, Locale.getDefault());
}
return result;
}
@@ -1112,6 +1125,8 @@
* Returns the full variant name in the default {@code Locale} for the variant code of
* this {@code Locale}. If there is no matching variant name, the variant code is
* returned.
+ *
+ * @since 1.7
*/
public final String getDisplayVariant() {
return getDisplayVariant(getDefault());
@@ -1121,15 +1136,31 @@
* Returns the full variant name in the specified {@code Locale} for the variant code
* of this {@code Locale}. If there is no matching variant name, the variant code is
* returned.
+ *
+ * @since 1.7
*/
public String getDisplayVariant(Locale locale) {
- if (variantCode.length() == 0) {
+ if (variantCode.isEmpty()) {
+ return "";
+ }
+
+ try {
+ Builder.normalizeAndValidateVariant(variantCode);
+ } catch (IllformedLocaleException ilfe) {
return variantCode;
}
- String result = ICU.getDisplayVariantNative(getIcuLocaleId(), locale.getIcuLocaleId());
+
+ String result = ICU.getDisplayVariant(this, locale);
if (result == null) { // TODO: do we need to do this, or does ICU do it for us?
- result = ICU.getDisplayVariantNative(getIcuLocaleId(),
- Locale.getDefault().getIcuLocaleId());
+ result = ICU.getDisplayVariant(this, Locale.getDefault());
+ }
+
+ // The "old style" locale constructors allow us to pass in variants that aren't
+ // valid BCP-47 variant subtags. When that happens, toLanguageTag will not emit
+ // them. Note that we know variantCode.length() > 0 due to the isEmpty check at
+ // the beginning of this function.
+ if (result.isEmpty()) {
+ return variantCode;
}
return result;
}
@@ -1140,7 +1171,7 @@
* @throws MissingResourceException if there's no 3-letter country code for this locale.
*/
public String getISO3Country() {
- String code = ICU.getISO3CountryNative(getIcuLocaleId());
+ String code = ICU.getISO3Country(this);
if (!countryCode.isEmpty() && code.isEmpty()) {
throw new MissingResourceException("No 3-letter country code for locale: " + this, "FormatData_" + this, "ShortCountry");
}
@@ -1153,7 +1184,15 @@
* @throws MissingResourceException if there's no 3-letter language code for this locale.
*/
public String getISO3Language() {
- String code = ICU.getISO3LanguageNative(getIcuLocaleId());
+ // For backward compatibility, we must return "" for an empty language
+ // code and not "und" which is the accurate ISO-639-3 code for an
+ // undetermined language.
+ if (languageCode.isEmpty()) {
+ return "";
+ }
+
+ String code = ICU.getISO3Language(this);
+
if (!languageCode.isEmpty() && code.isEmpty()) {
throw new MissingResourceException("No 3-letter language code for locale: " + this, "FormatData_" + this, "ShortLanguage");
}
@@ -1200,6 +1239,7 @@
* specification.
*
* @since 1.7
+ * @hide 1.7
*/
public String getScript() {
return scriptCode;
@@ -1209,6 +1249,7 @@
* Equivalent to {@code getDisplayScript(Locale.getDefault()))}
*
* @since 1.7
+ * @hide 1.7
*/
public String getDisplayScript() {
return getDisplayScript(getDefault());
@@ -1220,16 +1261,16 @@
* {@link #getScript()}.
*
* @since 1.7
+ * @hide 1.7
*/
public String getDisplayScript(Locale locale) {
if (scriptCode.isEmpty()) {
return "";
}
- String result = ICU.getDisplayScriptNative(getIcuLocaleId(), locale.getIcuLocaleId());
+ String result = ICU.getDisplayScript(this, locale);
if (result == null) { // TODO: do we need to do this, or does ICU do it for us?
- result = ICU.getDisplayScriptNative(getIcuLocaleId(),
- Locale.getDefault().getIcuLocaleId());
+ result = ICU.getDisplayScript(this, Locale.getDefault());
}
return result;
@@ -1250,12 +1291,13 @@
* where they will appear after a subtag whose value is {@code "lvariant"}.
*
* It's also important to note that the BCP-47 tag is well formed in the sense
- * that it is unambiguously parsable into its specified components. We do not
+ * that it is unambiguously parseable into its specified components. We do not
* require that any of the components are registered with the applicable registries.
* For example, we do not require scripts to be a registered ISO 15924 scripts or
* languages to appear in the ISO-639-2 code list.
*
* @since 1.7
+ * @hide 1.7
*/
public String toLanguageTag() {
if (cachedLanguageTag == null) {
@@ -1471,6 +1513,7 @@
* the IETF BCP-47 specification</a> (Section 2.2.6) for details.
*
* @since 1.7
+ * @hide 1.7
*/
public Set<Character> getExtensionKeys() {
return extensions.keySet();
@@ -1485,6 +1528,7 @@
* {@link #getUnicodeLocaleKeys()} and {@link #getUnicodeLocaleType}.
*
* @since 1.7
+ * @hide 1.7
*/
public String getExtension(char extensionKey) {
return extensions.get(extensionKey);
@@ -1497,6 +1541,7 @@
* and <a href="http://www.unicode.org/reports/tr35/#BCP47">Unicode Technical Standard #35</a>
*
* @since 1.7
+ * @hide 1.7
*/
public String getUnicodeLocaleType(String keyWord) {
return unicodeKeywords.get(keyWord);
@@ -1509,6 +1554,7 @@
* and <a href="http://www.unicode.org/reports/tr35/#BCP47">Unicode Technical Standard #35</a>
*
* @since 1.7
+ * @hide 1.7
*/
public Set<String> getUnicodeLocaleAttributes() {
return unicodeAttributes;
@@ -1521,6 +1567,7 @@
* and <a href="http://www.unicode.org/reports/tr35/#BCP47">Unicode Technical Standard #35</a>
*
* @since 1.7
+ * @hide 1.7
*/
public Set<String> getUnicodeLocaleKeys() {
return unicodeKeywords.keySet();
@@ -1545,8 +1592,9 @@
if (locale == null) {
throw new NullPointerException("locale == null");
}
+ String languageTag = locale.toLanguageTag();
defaultLocale = locale;
- ICU.setDefaultLocale(ICU.localeIdFromLocale(locale));
+ ICU.setDefaultLocale(languageTag);
}
/**
@@ -1564,20 +1612,12 @@
public final String toString() {
String result = cachedToStringResult;
if (result == null) {
- result = cachedToStringResult = toNewString(languageCode, countryCode,
- variantCode, scriptCode, extensions);
+ result = cachedToStringResult = toNewString(languageCode, countryCode, variantCode,
+ scriptCode, extensions);
}
return result;
}
- private String getIcuLocaleId() {
- if (cachedIcuLocaleId == null) {
- cachedIcuLocaleId = ICU.localeIdFromLocale(this);
- }
-
- return cachedIcuLocaleId;
- }
-
private static String toNewString(String languageCode, String countryCode,
String variantCode, String scriptCode, Map<Character, String> extensions) {
// The string form of a locale that only has a variant is the empty string.
@@ -1592,8 +1632,7 @@
StringBuilder result = new StringBuilder(11);
result.append(languageCode);
- final boolean hasScriptOrExtensions = !scriptCode.isEmpty() ||
- !extensions.isEmpty();
+ final boolean hasScriptOrExtensions = !scriptCode.isEmpty() || !extensions.isEmpty();
if (!countryCode.isEmpty() || !variantCode.isEmpty() || hasScriptOrExtensions) {
result.append('_');
@@ -1799,8 +1838,7 @@
return true;
}
- private static boolean isValidBcp47Alpha(String string,
- int lowerBound, int upperBound) {
+ private static boolean isValidBcp47Alpha(String string, int lowerBound, int upperBound) {
final int length = string.length();
if (length < lowerBound || length > upperBound) {
return false;
diff --git a/luni/src/main/java/java/util/concurrent/ConcurrentLinkedDeque.java b/luni/src/main/java/java/util/concurrent/ConcurrentLinkedDeque.java
index b38d6a5..eae9497 100644
--- a/luni/src/main/java/java/util/concurrent/ConcurrentLinkedDeque.java
+++ b/luni/src/main/java/java/util/concurrent/ConcurrentLinkedDeque.java
@@ -57,6 +57,7 @@
* the {@code ConcurrentLinkedDeque} in another thread.
*
* @since 1.7
+ * @hide 1.7
* @author Doug Lea
* @author Martin Buchholz
* @param <E> the type of elements held in this collection
diff --git a/luni/src/main/java/java/util/concurrent/ForkJoinPool.java b/luni/src/main/java/java/util/concurrent/ForkJoinPool.java
index 9448616..2cbee65 100644
--- a/luni/src/main/java/java/util/concurrent/ForkJoinPool.java
+++ b/luni/src/main/java/java/util/concurrent/ForkJoinPool.java
@@ -127,6 +127,7 @@
* or internal resources have been exhausted.
*
* @since 1.7
+ * @hide 1.7
* @author Doug Lea
*/
public class ForkJoinPool extends AbstractExecutorService {
diff --git a/luni/src/main/java/java/util/concurrent/ForkJoinTask.java b/luni/src/main/java/java/util/concurrent/ForkJoinTask.java
index c6bc6de..2936be8 100644
--- a/luni/src/main/java/java/util/concurrent/ForkJoinTask.java
+++ b/luni/src/main/java/java/util/concurrent/ForkJoinTask.java
@@ -175,6 +175,7 @@
* execution. Serialization is not relied on during execution itself.
*
* @since 1.7
+ * @hide 1.7
* @author Doug Lea
*/
public abstract class ForkJoinTask<V> implements Future<V>, Serializable {
diff --git a/luni/src/main/java/java/util/concurrent/ForkJoinWorkerThread.java b/luni/src/main/java/java/util/concurrent/ForkJoinWorkerThread.java
index ae28700..05c28a0 100644
--- a/luni/src/main/java/java/util/concurrent/ForkJoinWorkerThread.java
+++ b/luni/src/main/java/java/util/concurrent/ForkJoinWorkerThread.java
@@ -18,6 +18,7 @@
* {@linkplain ForkJoinPool#ForkJoinPool use it} in a {@code ForkJoinPool}.
*
* @since 1.7
+ * @hide 1.7
* @author Doug Lea
*/
public class ForkJoinWorkerThread extends Thread {
diff --git a/luni/src/main/java/java/util/concurrent/LinkedTransferQueue.java b/luni/src/main/java/java/util/concurrent/LinkedTransferQueue.java
index a041fb1..43d9fb7 100644
--- a/luni/src/main/java/java/util/concurrent/LinkedTransferQueue.java
+++ b/luni/src/main/java/java/util/concurrent/LinkedTransferQueue.java
@@ -50,6 +50,7 @@
* the {@code LinkedTransferQueue} in another thread.
*
* @since 1.7
+ * @hide 1.7
* @author Doug Lea
* @param <E> the type of elements held in this collection
*/
diff --git a/luni/src/main/java/java/util/concurrent/Phaser.java b/luni/src/main/java/java/util/concurrent/Phaser.java
index a97d187..4f9c76c 100644
--- a/luni/src/main/java/java/util/concurrent/Phaser.java
+++ b/luni/src/main/java/java/util/concurrent/Phaser.java
@@ -227,6 +227,7 @@
* of participants.
*
* @since 1.7
+ * @hide 1.7
* @author Doug Lea
*/
public class Phaser {
diff --git a/luni/src/main/java/java/util/concurrent/RecursiveAction.java b/luni/src/main/java/java/util/concurrent/RecursiveAction.java
index e3a6340..a16388c 100644
--- a/luni/src/main/java/java/util/concurrent/RecursiveAction.java
+++ b/luni/src/main/java/java/util/concurrent/RecursiveAction.java
@@ -131,6 +131,7 @@
* }}</pre>
*
* @since 1.7
+ * @hide 1.7
* @author Doug Lea
*/
public abstract class RecursiveAction extends ForkJoinTask<Void> {
diff --git a/luni/src/main/java/java/util/concurrent/RecursiveTask.java b/luni/src/main/java/java/util/concurrent/RecursiveTask.java
index 80baa52..45adeee 100644
--- a/luni/src/main/java/java/util/concurrent/RecursiveTask.java
+++ b/luni/src/main/java/java/util/concurrent/RecursiveTask.java
@@ -34,6 +34,7 @@
* sequentially solve rather than subdividing.
*
* @since 1.7
+ * @hide 1.7
* @author Doug Lea
*/
public abstract class RecursiveTask<V> extends ForkJoinTask<V> {
diff --git a/luni/src/main/java/java/util/concurrent/ScheduledThreadPoolExecutor.java b/luni/src/main/java/java/util/concurrent/ScheduledThreadPoolExecutor.java
index 483981d..f450a0f 100644
--- a/luni/src/main/java/java/util/concurrent/ScheduledThreadPoolExecutor.java
+++ b/luni/src/main/java/java/util/concurrent/ScheduledThreadPoolExecutor.java
@@ -690,6 +690,7 @@
* @param value if {@code true}, remove on cancellation, else don't
* @see #getRemoveOnCancelPolicy
* @since 1.7
+ * @hide 1.7
*/
public void setRemoveOnCancelPolicy(boolean value) {
removeOnCancel = value;
@@ -704,6 +705,7 @@
* from the queue
* @see #setRemoveOnCancelPolicy
* @since 1.7
+ * @hide 1.7
*/
public boolean getRemoveOnCancelPolicy() {
return removeOnCancel;
diff --git a/luni/src/main/java/java/util/concurrent/ThreadLocalRandom.java b/luni/src/main/java/java/util/concurrent/ThreadLocalRandom.java
index 5baf75f..bd618ca 100644
--- a/luni/src/main/java/java/util/concurrent/ThreadLocalRandom.java
+++ b/luni/src/main/java/java/util/concurrent/ThreadLocalRandom.java
@@ -30,6 +30,7 @@
* generation methods.
*
* @since 1.7
+ * @hide 1.7
* @author Doug Lea
*/
public class ThreadLocalRandom extends Random {
diff --git a/luni/src/main/java/java/util/concurrent/TransferQueue.java b/luni/src/main/java/java/util/concurrent/TransferQueue.java
index 4c2be6f..debcedc 100644
--- a/luni/src/main/java/java/util/concurrent/TransferQueue.java
+++ b/luni/src/main/java/java/util/concurrent/TransferQueue.java
@@ -33,6 +33,7 @@
* and {@code transfer} are effectively synonymous.
*
* @since 1.7
+ * @hide 1.7
* @author Doug Lea
* @param <E> the type of elements held in this collection
*/
diff --git a/luni/src/main/java/java/util/concurrent/locks/AbstractQueuedLongSynchronizer.java b/luni/src/main/java/java/util/concurrent/locks/AbstractQueuedLongSynchronizer.java
index 37aa9d0..f130fb0 100644
--- a/luni/src/main/java/java/util/concurrent/locks/AbstractQueuedLongSynchronizer.java
+++ b/luni/src/main/java/java/util/concurrent/locks/AbstractQueuedLongSynchronizer.java
@@ -1255,6 +1255,7 @@
* current thread, and {@code false} if the current thread
* is at the head of the queue or the queue is empty
* @since 1.7
+ * @hide 1.7
*/
public final boolean hasQueuedPredecessors() {
// The correctness of this depends on head being initialized
diff --git a/luni/src/main/java/java/util/concurrent/locks/AbstractQueuedSynchronizer.java b/luni/src/main/java/java/util/concurrent/locks/AbstractQueuedSynchronizer.java
index e711da5..1c766e7 100644
--- a/luni/src/main/java/java/util/concurrent/locks/AbstractQueuedSynchronizer.java
+++ b/luni/src/main/java/java/util/concurrent/locks/AbstractQueuedSynchronizer.java
@@ -1485,6 +1485,7 @@
* current thread, and {@code false} if the current thread
* is at the head of the queue or the queue is empty
* @since 1.7
+ * @hide 1.7
*/
public final boolean hasQueuedPredecessors() {
// The correctness of this depends on head being initialized
diff --git a/luni/src/main/java/java/util/zip/ZipFile.java b/luni/src/main/java/java/util/zip/ZipFile.java
index 877e9ee..9894152 100644
--- a/luni/src/main/java/java/util/zip/ZipFile.java
+++ b/luni/src/main/java/java/util/zip/ZipFile.java
@@ -132,6 +132,7 @@
* @throws ZipException if a zip error occurs.
* @throws IOException if an {@code IOException} occurs.
* @since 1.7
+ * @hide 1.7
*/
public ZipFile(File file, Charset charset) throws ZipException, IOException {
this(file, OPEN_READ, charset);
@@ -178,6 +179,7 @@
*
* @throws IOException if an {@code IOException} occurs.
* @since 1.7
+ * @hide 1.7
*/
public ZipFile(File file, int mode, Charset charset) throws IOException {
filename = file.getPath();
diff --git a/luni/src/main/java/java/util/zip/ZipInputStream.java b/luni/src/main/java/java/util/zip/ZipInputStream.java
index 402cd33..f1a5208 100644
--- a/luni/src/main/java/java/util/zip/ZipInputStream.java
+++ b/luni/src/main/java/java/util/zip/ZipInputStream.java
@@ -108,6 +108,7 @@
* by the zip file then {@code charset} is used to decode them.
*
* @since 1.7
+ * @hide 1.7
*/
public ZipInputStream(InputStream stream, Charset charset) {
super(new PushbackInputStream(stream, BUF_SIZE), new Inflater(true));
diff --git a/luni/src/main/java/java/util/zip/ZipOutputStream.java b/luni/src/main/java/java/util/zip/ZipOutputStream.java
index 77b00c9..aeb77e9 100644
--- a/luni/src/main/java/java/util/zip/ZipOutputStream.java
+++ b/luni/src/main/java/java/util/zip/ZipOutputStream.java
@@ -114,6 +114,7 @@
* comments.
*
* @since 1.7
+ * @hide 1.7
*/
public ZipOutputStream(OutputStream os, Charset charset) {
super(os, new Deflater(Deflater.DEFAULT_COMPRESSION, true));
diff --git a/luni/src/main/java/javax/net/ssl/SSLEngine.java b/luni/src/main/java/javax/net/ssl/SSLEngine.java
index b55acd4..d938642 100644
--- a/luni/src/main/java/javax/net/ssl/SSLEngine.java
+++ b/luni/src/main/java/javax/net/ssl/SSLEngine.java
@@ -783,6 +783,7 @@
*
* @return the SSL session for this engine instance.
* @since 1.7
+ * @hide 1.7
*/
public SSLSession getHandshakeSession() {
throw new UnsupportedOperationException();
diff --git a/luni/src/main/java/javax/net/ssl/SSLParameters.java b/luni/src/main/java/javax/net/ssl/SSLParameters.java
index 93e766f..d049038 100644
--- a/luni/src/main/java/javax/net/ssl/SSLParameters.java
+++ b/luni/src/main/java/javax/net/ssl/SSLParameters.java
@@ -146,6 +146,7 @@
*
* @see #setEndpointIdentificationAlgorithm(String)
* @since 1.7
+ * @hide 1.7
*/
public String getEndpointIdentificationAlgorithm() {
return endpointIdentificationAlgorithm;
@@ -157,6 +158,7 @@
*
* @see #getEndpointIdentificationAlgorithm()
* @since 1.7
+ * @hide 1.7
*/
public void setEndpointIdentificationAlgorithm(String endpointIdentificationAlgorithm) {
this.endpointIdentificationAlgorithm = endpointIdentificationAlgorithm;
diff --git a/luni/src/main/java/javax/net/ssl/SSLSocket.java b/luni/src/main/java/javax/net/ssl/SSLSocket.java
index 148f3cf..dd89e90 100644
--- a/luni/src/main/java/javax/net/ssl/SSLSocket.java
+++ b/luni/src/main/java/javax/net/ssl/SSLSocket.java
@@ -895,6 +895,7 @@
*
* @return the session object.
* @since 1.7
+ * @hide 1.7
*/
public SSLSession getHandshakeSession() {
throw new UnsupportedOperationException();
diff --git a/luni/src/main/java/javax/net/ssl/X509ExtendedTrustManager.java b/luni/src/main/java/javax/net/ssl/X509ExtendedTrustManager.java
index 2af1c11..61ab169 100644
--- a/luni/src/main/java/javax/net/ssl/X509ExtendedTrustManager.java
+++ b/luni/src/main/java/javax/net/ssl/X509ExtendedTrustManager.java
@@ -27,6 +27,7 @@
*
* @see SSLParameters#setEndpointIdentificationAlgorithm(String)
* @since 1.7
+ * @hide 1.7
*/
public abstract class X509ExtendedTrustManager implements X509TrustManager {
/**
diff --git a/luni/src/main/java/libcore/icu/ICU.java b/luni/src/main/java/libcore/icu/ICU.java
index cf04ff9..407ebfd 100644
--- a/luni/src/main/java/libcore/icu/ICU.java
+++ b/luni/src/main/java/libcore/icu/ICU.java
@@ -239,70 +239,6 @@
true /* has validated fields */);
}
- /**
- * Builds an ICU locale ID from the given locale. The format is very
- * straightforward. It is a series of subtags in BCP 47 order
- * {@code lang[_script][_country][_variant]} followed by the keyword
- * separator {@code @} followed by a list of keywords. Each keyword is
- * a key value pair, and appear in the form {@code k1=v1;k2=v2;...}.
- *
- * In this use case, each key is an extension identifier, and each value
- * is the value of the extension.
- */
- public static String localeIdFromLocale(Locale l) {
- StringBuilder b = new StringBuilder(16);
- b.append(l.getLanguage());
-
- final boolean hasScript = !l.getScript().isEmpty();
- final boolean hasCountry = !l.getCountry().isEmpty();
- final boolean hasVariant = !l.getVariant().isEmpty();
-
- if (hasScript || hasCountry || hasVariant) {
- b.append('_');
- if (hasScript) {
- b.append(l.getScript());
- if (hasCountry || hasVariant) {
- b.append('_');
- }
- }
-
- if (hasCountry) {
- b.append(l.getCountry());
- if (hasVariant) {
- b.append('_');
- }
- }
-
- b.append(l.getVariant());
- }
-
- if (!l.getExtensionKeys().isEmpty()) {
- b.append('@');
- // The private use extension ('x') must show up last in the list
- // so we cache its value here and append it right at the end.
- String privateUseExtensionValue = null;
- for (char c : l.getExtensionKeys()) {
- if (c == Locale.PRIVATE_USE_EXTENSION) {
- privateUseExtensionValue = l.getExtension(Locale.PRIVATE_USE_EXTENSION);
- } else {
- b.append(c);
- b.append('=');
- b.append(l.getExtension(c));
- b.append(';');
- }
- }
-
- if (privateUseExtensionValue != null) {
- b.append(Locale.PRIVATE_USE_EXTENSION);
- b.append('=');
- b.append(privateUseExtensionValue);
- b.append(';');
- }
- }
-
- return b.toString();
- }
-
public static Locale[] localesFromStrings(String[] localeNames) {
// We need to remove duplicates caused by the conversion of "he" to "iw", et cetera.
// Java needs the obsolete code, ICU needs the modern code, but we let ICU know about
@@ -349,19 +285,20 @@
return localesFromStrings(getAvailableNumberFormatLocalesNative());
}
- public static String getBestDateTimePattern(String skeleton, String localeName) {
- String key = skeleton + "\t" + localeName;
+ public static String getBestDateTimePattern(String skeleton, Locale locale) {
+ String languageTag = locale.toLanguageTag();
+ String key = skeleton + "\t" + languageTag;
synchronized (CACHED_PATTERNS) {
String pattern = CACHED_PATTERNS.get(key);
if (pattern == null) {
- pattern = getBestDateTimePatternNative(skeleton, localeName);
+ pattern = getBestDateTimePatternNative(skeleton, languageTag);
CACHED_PATTERNS.put(key, pattern);
}
return pattern;
}
}
- private static native String getBestDateTimePatternNative(String skeleton, String localeName);
+ private static native String getBestDateTimePatternNative(String skeleton, String languageTag);
public static char[] getDateFormatOrder(String pattern) {
char[] result = new char[3];
@@ -421,8 +358,17 @@
// --- Case mapping.
- public static native String toLowerCase(String s, String localeName);
- public static native String toUpperCase(String s, String localeName);
+ public static String toLowerCase(String s, Locale locale) {
+ return toLowerCase(s, locale.toLanguageTag());
+ }
+
+ private static native String toLowerCase(String s, String languageTag);
+
+ public static String toUpperCase(String s, Locale locale) {
+ return toUpperCase(s, locale.toLanguageTag());
+ }
+
+ private static native String toUpperCase(String s, String languageTag);
// --- Errors.
@@ -448,18 +394,57 @@
public static native String[] getAvailableCurrencyCodes();
public static native String getCurrencyCode(String countryCode);
- public static native String getCurrencyDisplayName(String locale, String currencyCode);
+
+ public static String getCurrencyDisplayName(Locale locale, String currencyCode) {
+ return getCurrencyDisplayName(locale.toLanguageTag(), currencyCode);
+ }
+
+ private static native String getCurrencyDisplayName(String languageTag, String currencyCode);
+
public static native int getCurrencyFractionDigits(String currencyCode);
public static native int getCurrencyNumericCode(String currencyCode);
- public static native String getCurrencySymbol(String locale, String currencyCode);
- public static native String getDisplayCountryNative(String countryCode, String locale);
- public static native String getDisplayLanguageNative(String languageCode, String locale);
- public static native String getDisplayVariantNative(String variantCode, String locale);
- public static native String getDisplayScriptNative(String variantCode, String locale);
+ public static String getCurrencySymbol(Locale locale, String currencyCode) {
+ return getCurrencySymbol(locale.toLanguageTag(), currencyCode);
+ }
- public static native String getISO3CountryNative(String locale);
- public static native String getISO3LanguageNative(String locale);
+ private static native String getCurrencySymbol(String languageTag, String currencyCode);
+
+ public static String getDisplayCountry(Locale targetLocale, Locale locale) {
+ return getDisplayCountryNative(targetLocale.toLanguageTag(), locale.toLanguageTag());
+ }
+
+ private static native String getDisplayCountryNative(String targetLanguageTag, String languageTag);
+
+ public static String getDisplayLanguage(Locale targetLocale, Locale locale) {
+ return getDisplayLanguageNative(targetLocale.toLanguageTag(), locale.toLanguageTag());
+ }
+
+ private static native String getDisplayLanguageNative(String targetLanguageTag, String languageTag);
+
+ public static String getDisplayVariant(Locale targetLocale, Locale locale) {
+ return getDisplayVariantNative(targetLocale.toLanguageTag(), locale.toLanguageTag());
+ }
+
+ private static native String getDisplayVariantNative(String targetLanguageTag, String languageTag);
+
+ public static String getDisplayScript(Locale targetLocale, Locale locale) {
+ return getDisplayScriptNative(targetLocale.toLanguageTag(), locale.toLanguageTag());
+ }
+
+ private static native String getDisplayScriptNative(String targetLanguageTag, String languageTag);
+
+ public static String getISO3Country(Locale locale) {
+ return getISO3CountryNative(locale.toLanguageTag());
+ }
+
+ private static native String getISO3CountryNative(String languageTag);
+
+ public static String getISO3Language(Locale locale) {
+ return getISO3LanguageNative(locale.toLanguageTag());
+ }
+
+ private static native String getISO3LanguageNative(String languageTag);
public static native String addLikelySubtags(String locale);
public static native String getScript(String locale);
@@ -471,6 +456,6 @@
static native boolean initLocaleDataNative(String locale, LocaleData result);
- public static native void setDefaultLocale(String locale);
+ public static native void setDefaultLocale(String languageTag);
public static native String getDefaultLocale();
}
diff --git a/luni/src/main/java/libcore/icu/LocaleData.java b/luni/src/main/java/libcore/icu/LocaleData.java
index 49228b3..845ba32 100644
--- a/luni/src/main/java/libcore/icu/LocaleData.java
+++ b/luni/src/main/java/libcore/icu/LocaleData.java
@@ -176,8 +176,8 @@
}
// Get the "h:mm a" and "HH:mm" 12- and 24-hour time format strings.
- localeData.timeFormat12 = ICU.getBestDateTimePattern("hm", locale.toString());
- localeData.timeFormat24 = ICU.getBestDateTimePattern("Hm", locale.toString());
+ localeData.timeFormat12 = ICU.getBestDateTimePattern("hm", locale);
+ localeData.timeFormat24 = ICU.getBestDateTimePattern("Hm", locale);
// Fix up a couple of patterns.
if (localeData.fullTimeFormat != null) {
diff --git a/luni/src/main/java/libcore/icu/NativeBreakIterator.java b/luni/src/main/java/libcore/icu/NativeBreakIterator.java
index 7168d96..992aac2 100644
--- a/luni/src/main/java/libcore/icu/NativeBreakIterator.java
+++ b/luni/src/main/java/libcore/icu/NativeBreakIterator.java
@@ -138,23 +138,23 @@
}
public int preceding(int offset) {
- return precedingImpl(this.address, this.string, offset);
+ return precedingImpl(this.address, this.string, offset);
}
- public static NativeBreakIterator getCharacterInstance(Locale where) {
- return new NativeBreakIterator(getCharacterInstanceImpl(where.toString()), BI_CHAR_INSTANCE);
+ public static NativeBreakIterator getCharacterInstance(Locale locale) {
+ return new NativeBreakIterator(getCharacterInstanceImpl(locale.toLanguageTag()), BI_CHAR_INSTANCE);
}
- public static NativeBreakIterator getLineInstance(Locale where) {
- return new NativeBreakIterator(getLineInstanceImpl(where.toString()), BI_LINE_INSTANCE);
+ public static NativeBreakIterator getLineInstance(Locale locale) {
+ return new NativeBreakIterator(getLineInstanceImpl(locale.toLanguageTag()), BI_LINE_INSTANCE);
}
- public static NativeBreakIterator getSentenceInstance(Locale where) {
- return new NativeBreakIterator(getSentenceInstanceImpl(where.toString()), BI_SENT_INSTANCE);
+ public static NativeBreakIterator getSentenceInstance(Locale locale) {
+ return new NativeBreakIterator(getSentenceInstanceImpl(locale.toLanguageTag()), BI_SENT_INSTANCE);
}
- public static NativeBreakIterator getWordInstance(Locale where) {
- return new NativeBreakIterator(getWordInstanceImpl(where.toString()), BI_WORD_INSTANCE);
+ public static NativeBreakIterator getWordInstance(Locale locale) {
+ return new NativeBreakIterator(getWordInstanceImpl(locale.toLanguageTag()), BI_WORD_INSTANCE);
}
private static native long getCharacterInstanceImpl(String locale);
diff --git a/luni/src/main/java/libcore/icu/NativeCollation.java b/luni/src/main/java/libcore/icu/NativeCollation.java
index 64e0278..b4b4f46 100644
--- a/luni/src/main/java/libcore/icu/NativeCollation.java
+++ b/luni/src/main/java/libcore/icu/NativeCollation.java
@@ -10,6 +10,8 @@
package libcore.icu;
+import java.util.Locale;
+
/**
* Package static class for declaring all native methods for collation use.
* @author syn wee quek
@@ -26,7 +28,10 @@
public static native long getCollationElementIterator(long address, String source);
public static native String getRules(long address);
public static native byte[] getSortKey(long address, String source);
- public static native long openCollator(String locale);
+ public static long openCollator(Locale locale) {
+ return openCollator(locale.toLanguageTag());
+ }
+ private static native long openCollator(String languageTag);
public static native long openCollatorFromRules(String rules, int normalizationMode, int collationStrength);
public static native long safeClone(long address);
public static native void setAttribute(long address, int type, int value);
diff --git a/luni/src/main/java/libcore/icu/RuleBasedCollatorICU.java b/luni/src/main/java/libcore/icu/RuleBasedCollatorICU.java
index 3ea942d..b23013b 100644
--- a/luni/src/main/java/libcore/icu/RuleBasedCollatorICU.java
+++ b/luni/src/main/java/libcore/icu/RuleBasedCollatorICU.java
@@ -52,7 +52,7 @@
}
public RuleBasedCollatorICU(Locale locale) {
- address = NativeCollation.openCollator(locale.toString());
+ address = NativeCollation.openCollator(locale);
}
private RuleBasedCollatorICU(long address) {
diff --git a/luni/src/main/native/IcuUtilities.cpp b/luni/src/main/native/IcuUtilities.cpp
index c6f3950..7ce2168 100644
--- a/luni/src/main/native/IcuUtilities.cpp
+++ b/luni/src/main/native/IcuUtilities.cpp
@@ -28,10 +28,6 @@
#include "unicode/uloc.h"
#include "unicode/ustring.h"
-Locale getLocale(JNIEnv* env, jstring localeName) {
- return Locale::createFromName(ScopedUtfChars(env, localeName).c_str());
-}
-
jobjectArray fromStringEnumeration(JNIEnv* env, UErrorCode& status, const char* provider, StringEnumeration* se) {
if (maybeThrowIcuException(env, provider, status)) {
return NULL;
diff --git a/luni/src/main/native/IcuUtilities.h b/luni/src/main/native/IcuUtilities.h
index ffcfcda..737379e 100644
--- a/luni/src/main/native/IcuUtilities.h
+++ b/luni/src/main/native/IcuUtilities.h
@@ -23,9 +23,7 @@
#include "jni.h"
#include "ustrenum.h" // For UStringEnumeration.
#include "unicode/utypes.h" // For UErrorCode.
-#include "unicode/locid.h" // For Locale.
-extern Locale getLocale(JNIEnv* env, jstring localeName);
extern jobjectArray fromStringEnumeration(JNIEnv* env, UErrorCode& status, const char* provider, StringEnumeration*);
bool maybeThrowIcuException(JNIEnv* env, const char* function, UErrorCode error);
diff --git a/luni/src/main/native/android_system_OsConstants.cpp b/luni/src/main/native/android_system_OsConstants.cpp
index 13a0b1c..87ebc21 100644
--- a/luni/src/main/native/android_system_OsConstants.cpp
+++ b/luni/src/main/native/android_system_OsConstants.cpp
@@ -254,7 +254,7 @@
#if defined(IFA_F_TEMPORARY)
initConstant(env, c, "IFA_F_TEMPORARY", IFA_F_TEMPORARY);
#endif
-#if defined(IDA_F_TENTATIVE)
+#if defined(IFA_F_TENTATIVE)
initConstant(env, c, "IFA_F_TENTATIVE", IFA_F_TENTATIVE);
#endif
initConstant(env, c, "IFF_ALLMULTI", IFF_ALLMULTI);
@@ -390,19 +390,15 @@
initConstant(env, c, "PROT_READ", PROT_READ);
initConstant(env, c, "PROT_WRITE", PROT_WRITE);
initConstant(env, c, "R_OK", R_OK);
-#if defined(RT_SCOPE_HOST)
+// NOTE: The RT_* constants are not preprocessor defines, they're enum
+// members. The best we can do (barring UAPI / kernel version checks) is
+// to hope they exist on all host linuxes we're building on. These
+// constants have been around since 2.6.35 at least, so we should be ok.
+#if !defined(__APPLE__)
initConstant(env, c, "RT_SCOPE_HOST", RT_SCOPE_HOST);
-#endif
-#if defined(RT_SCOPE_LINK)
initConstant(env, c, "RT_SCOPE_LINK", RT_SCOPE_LINK);
-#endif
-#if defined(RT_SCOPE_NOWHERE)
initConstant(env, c, "RT_SCOPE_NOWHERE", RT_SCOPE_NOWHERE);
-#endif
-#if defined(RT_SCOPE_SITE)
initConstant(env, c, "RT_SCOPE_SITE", RT_SCOPE_SITE);
-#endif
-#if defined(RT_SCOPE_UNIVERSE)
initConstant(env, c, "RT_SCOPE_UNIVERSE", RT_SCOPE_UNIVERSE);
#endif
initConstant(env, c, "SEEK_CUR", SEEK_CUR);
diff --git a/luni/src/main/native/libcore_icu_AlphabeticIndex.cpp b/luni/src/main/native/libcore_icu_AlphabeticIndex.cpp
index bb05193..e0638bd 100644
--- a/luni/src/main/native/libcore_icu_AlphabeticIndex.cpp
+++ b/luni/src/main/native/libcore_icu_AlphabeticIndex.cpp
@@ -20,6 +20,7 @@
#include "JNIHelp.h"
#include "JniConstants.h"
#include "JniException.h"
+#include "ScopedIcuLocale.h"
#include "ScopedJavaUnicodeString.h"
#include "unicode/alphaindex.h"
#include "unicode/uniset.h"
@@ -28,9 +29,13 @@
return reinterpret_cast<AlphabeticIndex*>(static_cast<uintptr_t>(peer));
}
-static jlong AlphabeticIndex_create(JNIEnv* env, jclass, jstring javaLocale) {
+static jlong AlphabeticIndex_create(JNIEnv* env, jclass, jstring javaLocaleName) {
UErrorCode status = U_ZERO_ERROR;
- AlphabeticIndex* ai = new AlphabeticIndex(getLocale(env, javaLocale), status);
+ ScopedIcuLocale icuLocale(env, javaLocaleName);
+ if (!icuLocale.valid()) {
+ return 0;
+ }
+ AlphabeticIndex* ai = new AlphabeticIndex(icuLocale.locale(), status);
if (maybeThrowIcuException(env, "AlphabeticIndex", status)) {
return 0;
}
@@ -53,10 +58,14 @@
maybeThrowIcuException(env, "AlphabeticIndex::setMaxLabelCount", status);
}
-static void AlphabeticIndex_addLabels(JNIEnv* env, jclass, jlong peer, jstring javaLocale) {
+static void AlphabeticIndex_addLabels(JNIEnv* env, jclass, jlong peer, jstring javaLocaleName) {
AlphabeticIndex* ai = fromPeer(peer);
+ ScopedIcuLocale icuLocale(env, javaLocaleName);
+ if (!icuLocale.valid()) {
+ return;
+ }
UErrorCode status = U_ZERO_ERROR;
- ai->addLabels(getLocale(env, javaLocale), status);
+ ai->addLabels(icuLocale.locale(), status);
maybeThrowIcuException(env, "AlphabeticIndex::addLabels", status);
}
diff --git a/luni/src/main/native/libcore_icu_DateIntervalFormat.cpp b/luni/src/main/native/libcore_icu_DateIntervalFormat.cpp
index 72bc631..a3258c1 100644
--- a/luni/src/main/native/libcore_icu_DateIntervalFormat.cpp
+++ b/luni/src/main/native/libcore_icu_DateIntervalFormat.cpp
@@ -18,13 +18,17 @@
#include "IcuUtilities.h"
#include "JniConstants.h"
+#include "ScopedIcuLocale.h"
#include "ScopedJavaUnicodeString.h"
#include "UniquePtr.h"
#include "cutils/log.h"
#include "unicode/dtitvfmt.h"
static jlong DateIntervalFormat_createDateIntervalFormat(JNIEnv* env, jclass, jstring javaSkeleton, jstring javaLocaleName, jstring javaTzName) {
- Locale locale = getLocale(env, javaLocaleName);
+ ScopedIcuLocale icuLocale(env, javaLocaleName);
+ if (!icuLocale.valid()) {
+ return 0;
+ }
ScopedJavaUnicodeString skeletonHolder(env, javaSkeleton);
if (!skeletonHolder.valid()) {
@@ -32,7 +36,7 @@
}
UErrorCode status = U_ZERO_ERROR;
- DateIntervalFormat* formatter(DateIntervalFormat::createInstance(skeletonHolder.unicodeString(), locale, status));
+ DateIntervalFormat* formatter(DateIntervalFormat::createInstance(skeletonHolder.unicodeString(), icuLocale.locale(), status));
if (maybeThrowIcuException(env, "DateIntervalFormat::createInstance", status)) {
return 0;
}
diff --git a/luni/src/main/native/libcore_icu_ICU.cpp b/luni/src/main/native/libcore_icu_ICU.cpp
index 7b1aac1..8cf58bc 100644
--- a/luni/src/main/native/libcore_icu_ICU.cpp
+++ b/luni/src/main/native/libcore_icu_ICU.cpp
@@ -21,6 +21,7 @@
#include "JniConstants.h"
#include "JniException.h"
#include "ScopedFd.h"
+#include "ScopedIcuLocale.h"
#include "ScopedJavaUnicodeString.h"
#include "ScopedLocalRef.h"
#include "ScopedUtfChars.h"
@@ -96,30 +97,30 @@
DISALLOW_COPY_AND_ASSIGN(ScopedResourceBundle);
};
-static jstring ICU_addLikelySubtags(JNIEnv* env, jclass, jstring javaLocale) {
+static jstring ICU_addLikelySubtags(JNIEnv* env, jclass, jstring javaLocaleName) {
UErrorCode status = U_ZERO_ERROR;
- ScopedUtfChars localeID(env, javaLocale);
+ ScopedUtfChars localeID(env, javaLocaleName);
char maximizedLocaleID[ULOC_FULLNAME_CAPACITY];
uloc_addLikelySubtags(localeID.c_str(), maximizedLocaleID, sizeof(maximizedLocaleID), &status);
if (U_FAILURE(status)) {
- return javaLocale;
+ return javaLocaleName;
}
return env->NewStringUTF(maximizedLocaleID);
}
-static jstring ICU_getScript(JNIEnv* env, jclass, jstring javaLocale) {
- UErrorCode status = U_ZERO_ERROR;
- ScopedUtfChars localeID(env, javaLocale);
- char script[ULOC_SCRIPT_CAPACITY];
- uloc_getScript(localeID.c_str(), script, sizeof(script), &status);
- if (U_FAILURE(status)) {
- return NULL;
- }
- return env->NewStringUTF(script);
+static jstring ICU_getScript(JNIEnv* env, jclass, jstring javaLocaleName) {
+ ScopedIcuLocale icuLocale(env, javaLocaleName);
+ if (!icuLocale.valid()) {
+ return NULL;
+ }
+ return env->NewStringUTF(icuLocale.locale().getScript());
}
static jstring ICU_localeForLanguageTag(JNIEnv* env, jclass, jstring languageTag, jboolean strict) {
ScopedUtfChars languageTagChars(env, languageTag);
+ if (languageTagChars.c_str() == NULL) {
+ return NULL;
+ }
// Naively assume that in the average case, the size of
// the normalized language tag will be very nearly the same as the
@@ -158,8 +159,7 @@
// NOTE: The cast is safe because parsedLength can never be negative thanks
// to the check above. ICU does not document any negative return values for
// that field, but check for it anyway.
- if ((strict == JNI_TRUE) &&
- (static_cast<uint32_t>(parsedLength) != languageTagChars.size())) {
+ if ((strict == JNI_TRUE) && (static_cast<uint32_t>(parsedLength) != languageTagChars.size())) {
return NULL;
}
@@ -228,9 +228,9 @@
return (charCount == 0) ? env->NewStringUTF("XXX") : env->NewString(chars, charCount);
}
-static jstring getCurrencyName(JNIEnv* env, jstring javaLocaleName, jstring javaCurrencyCode, UCurrNameStyle nameStyle) {
- ScopedUtfChars localeName(env, javaLocaleName);
- if (localeName.c_str() == NULL) {
+static jstring getCurrencyName(JNIEnv* env, jstring javaLanguageTag, jstring javaCurrencyCode, UCurrNameStyle nameStyle) {
+ ScopedUtfChars languageTag(env, javaLanguageTag);
+ if (languageTag.c_str() == NULL) {
return NULL;
}
ScopedJavaUnicodeString currencyCode(env, javaCurrencyCode);
@@ -241,7 +241,7 @@
UErrorCode status = U_ZERO_ERROR;
UBool isChoiceFormat = false;
int32_t charCount;
- const UChar* chars = ucurr_getName(icuCurrencyCode.getTerminatedBuffer(), localeName.c_str(),
+ const UChar* chars = ucurr_getName(icuCurrencyCode.getTerminatedBuffer(), languageTag.c_str(),
nameStyle, &isChoiceFormat, &charCount, &status);
if (status == U_USING_DEFAULT_WARNING) {
if (nameStyle == UCURR_SYMBOL_NAME) {
@@ -260,54 +260,88 @@
return (charCount == 0) ? NULL : env->NewString(chars, charCount);
}
-static jstring ICU_getCurrencyDisplayName(JNIEnv* env, jclass, jstring javaLocaleName, jstring javaCurrencyCode) {
- return getCurrencyName(env, javaLocaleName, javaCurrencyCode, UCURR_LONG_NAME);
+static jstring ICU_getCurrencyDisplayName(JNIEnv* env, jclass, jstring javaLanguageTag, jstring javaCurrencyCode) {
+ return getCurrencyName(env, javaLanguageTag, javaCurrencyCode, UCURR_LONG_NAME);
}
-static jstring ICU_getCurrencySymbol(JNIEnv* env, jclass, jstring javaLocaleName, jstring javaCurrencyCode) {
- return getCurrencyName(env, javaLocaleName, javaCurrencyCode, UCURR_SYMBOL_NAME);
+static jstring ICU_getCurrencySymbol(JNIEnv* env, jclass, jstring javaLanguageTag, jstring javaCurrencyCode) {
+ return getCurrencyName(env, javaLanguageTag, javaCurrencyCode, UCURR_SYMBOL_NAME);
}
-static jstring ICU_getDisplayCountryNative(JNIEnv* env, jclass, jstring targetLocale, jstring locale) {
- Locale loc = getLocale(env, locale);
- Locale targetLoc = getLocale(env, targetLocale);
- UnicodeString str;
- targetLoc.getDisplayCountry(loc, str);
- return env->NewString(str.getBuffer(), str.length());
+static jstring ICU_getDisplayCountryNative(JNIEnv* env, jclass, jstring javaTargetLanguageTag, jstring javaLanguageTag) {
+ ScopedIcuLocale icuLocale(env, javaLanguageTag);
+ if (!icuLocale.valid()) {
+ return NULL;
+ }
+ ScopedIcuLocale icuTargetLocale(env, javaTargetLanguageTag);
+ if (!icuTargetLocale.valid()) {
+ return NULL;
+ }
+
+ UnicodeString str;
+ icuTargetLocale.locale().getDisplayCountry(icuLocale.locale(), str);
+ return env->NewString(str.getBuffer(), str.length());
}
-static jstring ICU_getDisplayLanguageNative(JNIEnv* env, jclass, jstring targetLocale, jstring locale) {
- Locale loc = getLocale(env, locale);
- Locale targetLoc = getLocale(env, targetLocale);
- UnicodeString str;
- targetLoc.getDisplayLanguage(loc, str);
- return env->NewString(str.getBuffer(), str.length());
+static jstring ICU_getDisplayLanguageNative(JNIEnv* env, jclass, jstring javaTargetLanguageTag, jstring javaLanguageTag) {
+ ScopedIcuLocale icuLocale(env, javaLanguageTag);
+ if (!icuLocale.valid()) {
+ return NULL;
+ }
+ ScopedIcuLocale icuTargetLocale(env, javaTargetLanguageTag);
+ if (!icuTargetLocale.valid()) {
+ return NULL;
+ }
+
+ UnicodeString str;
+ icuTargetLocale.locale().getDisplayLanguage(icuLocale.locale(), str);
+ return env->NewString(str.getBuffer(), str.length());
}
-static jstring ICU_getDisplayScriptNative(JNIEnv* env, jclass, jstring targetLocale, jstring locale) {
- Locale loc = getLocale(env, locale);
- Locale targetLoc = getLocale(env, targetLocale);
- UnicodeString str;
- targetLoc.getDisplayScript(loc, str);
- return env->NewString(str.getBuffer(), str.length());
+static jstring ICU_getDisplayScriptNative(JNIEnv* env, jclass, jstring javaTargetLanguageTag, jstring javaLanguageTag) {
+ ScopedIcuLocale icuLocale(env, javaLanguageTag);
+ if (!icuLocale.valid()) {
+ return NULL;
+ }
+ ScopedIcuLocale icuTargetLocale(env, javaTargetLanguageTag);
+ if (!icuTargetLocale.valid()) {
+ return NULL;
+ }
+
+ UnicodeString str;
+ icuTargetLocale.locale().getDisplayScript(icuLocale.locale(), str);
+ return env->NewString(str.getBuffer(), str.length());
}
-static jstring ICU_getDisplayVariantNative(JNIEnv* env, jclass, jstring targetLocale, jstring locale) {
- Locale loc = getLocale(env, locale);
- Locale targetLoc = getLocale(env, targetLocale);
- UnicodeString str;
- targetLoc.getDisplayVariant(loc, str);
- return env->NewString(str.getBuffer(), str.length());
+static jstring ICU_getDisplayVariantNative(JNIEnv* env, jclass, jstring javaTargetLanguageTag, jstring javaLanguageTag) {
+ ScopedIcuLocale icuLocale(env, javaLanguageTag);
+ if (!icuLocale.valid()) {
+ return NULL;
+ }
+ ScopedIcuLocale icuTargetLocale(env, javaTargetLanguageTag);
+ if (!icuTargetLocale.valid()) {
+ return NULL;
+ }
+
+ UnicodeString str;
+ icuTargetLocale.locale().getDisplayVariant(icuLocale.locale(), str);
+ return env->NewString(str.getBuffer(), str.length());
}
-static jstring ICU_getISO3CountryNative(JNIEnv* env, jclass, jstring locale) {
- Locale loc = getLocale(env, locale);
- return env->NewStringUTF(loc.getISO3Country());
+static jstring ICU_getISO3CountryNative(JNIEnv* env, jclass, jstring javaLanguageTag) {
+ ScopedIcuLocale icuLocale(env, javaLanguageTag);
+ if (!icuLocale.valid()) {
+ return NULL;
+ }
+ return env->NewStringUTF(icuLocale.locale().getISO3Country());
}
-static jstring ICU_getISO3LanguageNative(JNIEnv* env, jclass, jstring locale) {
- Locale loc = getLocale(env, locale);
- return env->NewStringUTF(loc.getISO3Language());
+static jstring ICU_getISO3LanguageNative(JNIEnv* env, jclass, jstring javaLanguageTag) {
+ ScopedIcuLocale icuLocale(env, javaLanguageTag);
+ if (!icuLocale.valid()) {
+ return NULL;
+ }
+ return env->NewStringUTF(icuLocale.locale().getISO3Language());
}
static jobjectArray ICU_getISOCountriesNative(JNIEnv* env, jclass) {
@@ -538,7 +572,10 @@
return JNI_FALSE; // ICU has a fixed-length limit.
}
- Locale locale = getLocale(env, javaLocaleName);
+ ScopedIcuLocale icuLocale(env, javaLocaleName);
+ if (!icuLocale.valid()) {
+ return JNI_FALSE;
+ }
// Get the DateTimePatterns.
UErrorCode status = U_ZERO_ERROR;
@@ -557,7 +594,7 @@
// Get the "Yesterday", "Today", and "Tomorrow" strings.
bool foundYesterdayTodayAndTomorrow = false;
for (LocaleNameIterator it(localeName.c_str(), status); it.HasNext(); it.Up()) {
- if (getYesterdayTodayAndTomorrow(env, localeData, locale, it.Get())) {
+ if (getYesterdayTodayAndTomorrow(env, localeData, icuLocale.locale(), it.Get())) {
foundYesterdayTodayAndTomorrow = true;
break;
}
@@ -568,7 +605,7 @@
}
status = U_ZERO_ERROR;
- UniquePtr<Calendar> cal(Calendar::createInstance(locale, status));
+ UniquePtr<Calendar> cal(Calendar::createInstance(icuLocale.locale(), status));
if (U_FAILURE(status)) {
return JNI_FALSE;
}
@@ -578,7 +615,7 @@
// Get DateFormatSymbols.
status = U_ZERO_ERROR;
- DateFormatSymbols dateFormatSym(locale, status);
+ DateFormatSymbols dateFormatSym(icuLocale.locale(), status);
if (U_FAILURE(status)) {
return JNI_FALSE;
}
@@ -631,8 +668,8 @@
status = U_ZERO_ERROR;
// For numberPatterns and symbols.
- setNumberPatterns(env, localeData, locale);
- setDecimalFormatSymbolsData(env, localeData, locale);
+ setNumberPatterns(env, localeData, icuLocale.locale());
+ setDecimalFormatSymbolsData(env, localeData, icuLocale.locale());
jstring countryCode = env->NewStringUTF(Locale::createFromName(localeName.c_str()).getCountry());
jstring internationalCurrencySymbol = ICU_getCurrencyCode(env, NULL, countryCode);
@@ -655,25 +692,33 @@
return JNI_TRUE;
}
-static jstring ICU_toLowerCase(JNIEnv* env, jclass, jstring javaString, jstring localeName) {
+static jstring ICU_toLowerCase(JNIEnv* env, jclass, jstring javaString, jstring javaLanguageTag) {
ScopedJavaUnicodeString scopedString(env, javaString);
if (!scopedString.valid()) {
return NULL;
}
+ ScopedIcuLocale icuLocale(env, javaLanguageTag);
+ if (!icuLocale.valid()) {
+ return NULL;
+ }
UnicodeString& s(scopedString.unicodeString());
UnicodeString original(s);
- s.toLower(getLocale(env, localeName));
+ s.toLower(icuLocale.locale());
return s == original ? javaString : env->NewString(s.getBuffer(), s.length());
}
-static jstring ICU_toUpperCase(JNIEnv* env, jclass, jstring javaString, jstring localeName) {
+static jstring ICU_toUpperCase(JNIEnv* env, jclass, jstring javaString, jstring javaLanguageTag) {
ScopedJavaUnicodeString scopedString(env, javaString);
if (!scopedString.valid()) {
return NULL;
}
+ ScopedIcuLocale icuLocale(env, javaLanguageTag);
+ if (!icuLocale.valid()) {
+ return NULL;
+ }
UnicodeString& s(scopedString.unicodeString());
UnicodeString original(s);
- s.toUpper(getLocale(env, localeName));
+ s.toUpper(icuLocale.locale());
return s == original ? javaString : env->NewString(s.getBuffer(), s.length());
}
@@ -708,10 +753,14 @@
return fromStringEnumeration(env, status, "ucurr_openISOCurrencies", &e);
}
-static jstring ICU_getBestDateTimePatternNative(JNIEnv* env, jclass, jstring javaSkeleton, jstring javaLocaleName) {
- Locale locale = getLocale(env, javaLocaleName);
+static jstring ICU_getBestDateTimePatternNative(JNIEnv* env, jclass, jstring javaSkeleton, jstring javaLanguageTag) {
+ ScopedIcuLocale icuLocale(env, javaLanguageTag);
+ if (!icuLocale.valid()) {
+ return NULL;
+ }
+
UErrorCode status = U_ZERO_ERROR;
- UniquePtr<DateTimePatternGenerator> generator(DateTimePatternGenerator::createInstance(locale, status));
+ UniquePtr<DateTimePatternGenerator> generator(DateTimePatternGenerator::createInstance(icuLocale.locale(), status));
if (maybeThrowIcuException(env, "DateTimePatternGenerator::createInstance", status)) {
return NULL;
}
@@ -728,16 +777,14 @@
return env->NewString(result.getBuffer(), result.length());
}
-static void ICU_setDefaultLocale(JNIEnv* env, jclass, jstring javaLocaleName) {
- Locale locale = getLocale(env, javaLocaleName);
- UErrorCode status = U_ZERO_ERROR;
+static void ICU_setDefaultLocale(JNIEnv* env, jclass, jstring javaLanguageTag) {
+ ScopedIcuLocale icuLocale(env, javaLanguageTag);
+ if (!icuLocale.valid()) {
+ return;
+ }
- // TODO: Should we check whether locale.isBogus() here ? ICU will
- // accept bogus locales as the default without complaint. It
- // shouldn't make a difference in practice, users that set a bogus
- // locale as the default shouldn't have any realistic expectation that
- // things like defaults etc. will work correctly.
- Locale::setDefault(locale, status);
+ UErrorCode status = U_ZERO_ERROR;
+ Locale::setDefault(icuLocale.locale(), status);
maybeThrowIcuException(env, "Locale::setDefault", status);
}
diff --git a/luni/src/main/native/libcore_icu_NativeBreakIterator.cpp b/luni/src/main/native/libcore_icu_NativeBreakIterator.cpp
index 0c8c3c9..ef0c2a9 100644
--- a/luni/src/main/native/libcore_icu_NativeBreakIterator.cpp
+++ b/luni/src/main/native/libcore_icu_NativeBreakIterator.cpp
@@ -20,6 +20,7 @@
#include "JNIHelp.h"
#include "JniConstants.h"
#include "JniException.h"
+#include "ScopedIcuLocale.h"
#include "ScopedUtfChars.h"
#include "unicode/brkiter.h"
#include "unicode/putil.h"
@@ -107,13 +108,12 @@
};
#define MAKE_BREAK_ITERATOR_INSTANCE(F) \
- UErrorCode status = U_ZERO_ERROR; \
- const ScopedUtfChars localeChars(env, javaLocale); \
- if (localeChars.c_str() == NULL) { \
+ ScopedIcuLocale icuLocale(env, javaLocaleName); \
+ if (!icuLocale.valid()) { \
return 0; \
} \
- Locale locale(Locale::createFromName(localeChars.c_str())); \
- BreakIterator* it = F(locale, status); \
+ UErrorCode status = U_ZERO_ERROR; \
+ BreakIterator* it = F(icuLocale.locale(), status); \
if (maybeThrowIcuException(env, "ubrk_open", status)) { \
return 0; \
} \
@@ -143,19 +143,19 @@
return it->following(offset);
}
-static jlong NativeBreakIterator_getCharacterInstanceImpl(JNIEnv* env, jclass, jstring javaLocale) {
+static jlong NativeBreakIterator_getCharacterInstanceImpl(JNIEnv* env, jclass, jstring javaLocaleName) {
MAKE_BREAK_ITERATOR_INSTANCE(BreakIterator::createCharacterInstance);
}
-static jlong NativeBreakIterator_getLineInstanceImpl(JNIEnv* env, jclass, jstring javaLocale) {
+static jlong NativeBreakIterator_getLineInstanceImpl(JNIEnv* env, jclass, jstring javaLocaleName) {
MAKE_BREAK_ITERATOR_INSTANCE(BreakIterator::createLineInstance);
}
-static jlong NativeBreakIterator_getSentenceInstanceImpl(JNIEnv* env, jclass, jstring javaLocale) {
+static jlong NativeBreakIterator_getSentenceInstanceImpl(JNIEnv* env, jclass, jstring javaLocaleName) {
MAKE_BREAK_ITERATOR_INSTANCE(BreakIterator::createSentenceInstance);
}
-static jlong NativeBreakIterator_getWordInstanceImpl(JNIEnv* env, jclass, jstring javaLocale) {
+static jlong NativeBreakIterator_getWordInstanceImpl(JNIEnv* env, jclass, jstring javaLocaleName) {
MAKE_BREAK_ITERATOR_INSTANCE(BreakIterator::createWordInstance);
}
diff --git a/luni/src/main/native/libcore_icu_NativeCollation.cpp b/luni/src/main/native/libcore_icu_NativeCollation.cpp
index 00ec9ae..4ce42ec 100644
--- a/luni/src/main/native/libcore_icu_NativeCollation.cpp
+++ b/luni/src/main/native/libcore_icu_NativeCollation.cpp
@@ -180,11 +180,12 @@
return result;
}
-static jlong NativeCollation_openCollator(JNIEnv* env, jclass, jstring localeName) {
- ScopedUtfChars localeChars(env, localeName);
+static jlong NativeCollation_openCollator(JNIEnv* env, jclass, jstring javaLocaleName) {
+ ScopedUtfChars localeChars(env, javaLocaleName);
if (localeChars.c_str() == NULL) {
return 0;
}
+
UErrorCode status = U_ZERO_ERROR;
UCollator* c = ucol_open(localeChars.c_str(), &status);
maybeThrowIcuException(env, "ucol_open", status);
diff --git a/luni/src/main/native/libcore_icu_TimeZoneNames.cpp b/luni/src/main/native/libcore_icu_TimeZoneNames.cpp
index ef1743e..faf87f1 100644
--- a/luni/src/main/native/libcore_icu_TimeZoneNames.cpp
+++ b/luni/src/main/native/libcore_icu_TimeZoneNames.cpp
@@ -20,6 +20,7 @@
#include "JNIHelp.h"
#include "JniConstants.h"
#include "JniException.h"
+#include "ScopedIcuLocale.h"
#include "ScopedJavaUnicodeString.h"
#include "ScopedLocalRef.h"
#include "ScopedUtfChars.h"
@@ -59,11 +60,14 @@
return true;
}
-static void TimeZoneNames_fillZoneStrings(JNIEnv* env, jclass, jstring localeName, jobjectArray result) {
- Locale locale = getLocale(env, localeName);
+static void TimeZoneNames_fillZoneStrings(JNIEnv* env, jclass, jstring javaLocaleName, jobjectArray result) {
+ ScopedIcuLocale icuLocale(env, javaLocaleName);
+ if (!icuLocale.valid()) {
+ return;
+ }
UErrorCode status = U_ZERO_ERROR;
- UniquePtr<TimeZoneNames> names(TimeZoneNames::createInstance(locale, status));
+ UniquePtr<TimeZoneNames> names(TimeZoneNames::createInstance(icuLocale.locale(), status));
if (maybeThrowIcuException(env, "TimeZoneNames::createInstance", status)) {
return;
}
@@ -118,11 +122,14 @@
}
}
-static jstring TimeZoneNames_getExemplarLocation(JNIEnv* env, jclass, jstring javaLocale, jstring javaTz) {
- Locale locale = getLocale(env, javaLocale);
+static jstring TimeZoneNames_getExemplarLocation(JNIEnv* env, jclass, jstring javaLocaleName, jstring javaTz) {
+ ScopedIcuLocale icuLocale(env, javaLocaleName);
+ if (!icuLocale.valid()) {
+ return NULL;
+ }
UErrorCode status = U_ZERO_ERROR;
- UniquePtr<TimeZoneNames> names(TimeZoneNames::createInstance(locale, status));
+ UniquePtr<TimeZoneNames> names(TimeZoneNames::createInstance(icuLocale.locale(), status));
if (maybeThrowIcuException(env, "TimeZoneNames::createInstance", status)) {
return NULL;
}
diff --git a/luni/src/test/java/libcore/android/system/OsConstantsTest.java b/luni/src/test/java/libcore/android/system/OsConstantsTest.java
new file mode 100644
index 0000000..681d68c
--- /dev/null
+++ b/luni/src/test/java/libcore/android/system/OsConstantsTest.java
@@ -0,0 +1,31 @@
+/*
+ * 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 android.system;
+
+import junit.framework.TestCase;
+
+public class OsConstantsTest extends TestCase {
+
+ // http://b/15602893
+ public void testBug15602893() {
+ assertTrue(OsConstants.RT_SCOPE_HOST > 0);
+ assertTrue(OsConstants.RT_SCOPE_LINK > 0);
+ assertTrue(OsConstants.RT_SCOPE_SITE > 0);
+
+ assertTrue(OsConstants.IFA_F_TENTATIVE > 0);
+ }
+}
diff --git a/luni/src/test/java/libcore/icu/ICUTest.java b/luni/src/test/java/libcore/icu/ICUTest.java
index 60ed0ca..be2da25 100644
--- a/luni/src/test/java/libcore/icu/ICUTest.java
+++ b/luni/src/test/java/libcore/icu/ICUTest.java
@@ -16,6 +16,8 @@
package libcore.icu;
+import java.text.BreakIterator;
+import java.text.Collator;
import java.util.Arrays;
import java.util.Locale;
@@ -42,12 +44,12 @@
}
public void test_getBestDateTimePattern() throws Exception {
- assertEquals("d MMMM", ICU.getBestDateTimePattern("MMMMd", "ca_ES"));
- assertEquals("d 'de' MMMM", ICU.getBestDateTimePattern("MMMMd", "es_ES"));
- assertEquals("d. MMMM", ICU.getBestDateTimePattern("MMMMd", "de_CH"));
- assertEquals("MMMM d", ICU.getBestDateTimePattern("MMMMd", "en_US"));
- assertEquals("d LLLL", ICU.getBestDateTimePattern("MMMMd", "fa_IR"));
- assertEquals("M月d日", ICU.getBestDateTimePattern("MMMMd", "ja_JP"));
+ assertEquals("d MMMM", ICU.getBestDateTimePattern("MMMMd", new Locale("ca", "ES")));
+ assertEquals("d 'de' MMMM", ICU.getBestDateTimePattern("MMMMd", new Locale("es", "ES")));
+ assertEquals("d. MMMM", ICU.getBestDateTimePattern("MMMMd", new Locale("de", "CH")));
+ assertEquals("MMMM d", ICU.getBestDateTimePattern("MMMMd", new Locale("en", "US")));
+ assertEquals("d LLLL", ICU.getBestDateTimePattern("MMMMd", new Locale("fa", "IR")));
+ assertEquals("M月d日", ICU.getBestDateTimePattern("MMMMd", new Locale("ja", "JP")));
}
public void test_localeFromString() throws Exception {
@@ -73,7 +75,7 @@
}
private String best(Locale l, String skeleton) {
- return ICU.getBestDateTimePattern(skeleton, l.toString());
+ return ICU.getBestDateTimePattern(skeleton, l);
}
public void test_getDateFormatOrder() throws Exception {
@@ -123,4 +125,95 @@
} catch (IllegalArgumentException expected) {
}
}
+
+ public void testScriptsPassedToIcu() throws Exception {
+ Locale sr_Cyrl_BA = Locale.forLanguageTag("sr-Cyrl-BA");
+ Locale sr_Cyrl_ME = Locale.forLanguageTag("sr-Cyrl-ME");
+ Locale sr_Latn_BA = Locale.forLanguageTag("sr-Latn-BA");
+ Locale sr_Latn_ME = Locale.forLanguageTag("sr-Latn-ME");
+
+ assertEquals("sr_BA_#Cyrl", sr_Cyrl_BA.toString());
+ assertEquals("Cyrl", sr_Cyrl_BA.getScript());
+
+ assertEquals("sr_ME_#Cyrl", sr_Cyrl_ME.toString());
+ assertEquals("Cyrl", sr_Cyrl_ME.getScript());
+
+ assertEquals("sr_BA_#Latn", sr_Latn_BA.toString());
+ assertEquals("Latn", sr_Latn_BA.getScript());
+
+ assertEquals("sr_ME_#Latn", sr_Latn_ME.toString());
+ assertEquals("Latn", sr_Latn_ME.getScript());
+
+ assertEquals("Српски", sr_Cyrl_BA.getDisplayLanguage(sr_Cyrl_BA));
+ assertEquals("Босна и Херцеговина", sr_Cyrl_BA.getDisplayCountry(sr_Cyrl_BA));
+ assertEquals("Ћирилица", sr_Cyrl_BA.getDisplayScript(sr_Cyrl_BA));
+ assertEquals("", sr_Cyrl_BA.getDisplayVariant(sr_Cyrl_BA));
+
+ assertEquals("Српски", sr_Cyrl_ME.getDisplayLanguage(sr_Cyrl_ME));
+ assertEquals("Црна Гора", sr_Cyrl_ME.getDisplayCountry(sr_Cyrl_ME));
+ assertEquals("Ћирилица", sr_Cyrl_ME.getDisplayScript(sr_Cyrl_ME));
+ assertEquals("", sr_Cyrl_ME.getDisplayVariant(sr_Cyrl_ME));
+
+ assertEquals("Srpski", sr_Latn_BA.getDisplayLanguage(sr_Latn_BA));
+ assertEquals("Bosna i Hercegovina", sr_Latn_BA.getDisplayCountry(sr_Latn_BA));
+ assertEquals("Latinica", sr_Latn_BA.getDisplayScript(sr_Latn_BA));
+ assertEquals("", sr_Latn_BA.getDisplayVariant(sr_Latn_BA));
+
+ assertEquals("Srpski", sr_Latn_ME.getDisplayLanguage(sr_Latn_ME));
+ assertEquals("Crna Gora", sr_Latn_ME.getDisplayCountry(sr_Latn_ME));
+ assertEquals("Latinica", sr_Latn_ME.getDisplayScript(sr_Latn_ME));
+ assertEquals("", sr_Latn_ME.getDisplayVariant(sr_Latn_ME));
+
+ assertEquals("BIH", sr_Cyrl_BA.getISO3Country());
+ assertEquals("srp", sr_Cyrl_BA.getISO3Language());
+ assertEquals("MNE", sr_Cyrl_ME.getISO3Country());
+ assertEquals("srp", sr_Cyrl_ME.getISO3Language());
+ assertEquals("BIH", sr_Latn_BA.getISO3Country());
+ assertEquals("srp", sr_Latn_BA.getISO3Language());
+ assertEquals("MNE", sr_Latn_ME.getISO3Country());
+ assertEquals("srp", sr_Latn_ME.getISO3Language());
+
+ BreakIterator.getCharacterInstance(sr_Cyrl_BA);
+ BreakIterator.getCharacterInstance(sr_Cyrl_ME);
+ BreakIterator.getCharacterInstance(sr_Latn_BA);
+ BreakIterator.getCharacterInstance(sr_Latn_ME);
+
+ BreakIterator.getLineInstance(sr_Cyrl_BA);
+ BreakIterator.getLineInstance(sr_Cyrl_ME);
+ BreakIterator.getLineInstance(sr_Latn_BA);
+ BreakIterator.getLineInstance(sr_Latn_ME);
+
+ BreakIterator.getSentenceInstance(sr_Cyrl_BA);
+ BreakIterator.getSentenceInstance(sr_Cyrl_ME);
+ BreakIterator.getSentenceInstance(sr_Latn_BA);
+ BreakIterator.getSentenceInstance(sr_Latn_ME);
+
+ BreakIterator.getWordInstance(sr_Cyrl_BA);
+ BreakIterator.getWordInstance(sr_Cyrl_ME);
+ BreakIterator.getWordInstance(sr_Latn_BA);
+ BreakIterator.getWordInstance(sr_Latn_ME);
+
+ Collator.getInstance(sr_Cyrl_BA);
+ Collator.getInstance(sr_Cyrl_ME);
+ Collator.getInstance(sr_Latn_BA);
+ Collator.getInstance(sr_Latn_ME);
+
+ // TODO: This needs to be fixed. We shouldn't output attribute key
+ // expansions in the language tag or the toString output. The tests
+ // will fail with something like:
+ //
+ // expected:<de-u-co[-phonebk-kf-upper-kn]> but was:
+ // <de-u-co[lcasefirst-upper-collation-phonebook-colnumeric-yes]>
+ Locale l = Locale.forLanguageTag("de-u-co-phonebk-kf-upper-kn");
+ assertEquals("de__#u-co-phonebk-kf-upper-kn", l.toString());
+ assertEquals("de-u-co-phonebk-kf-upper-kn", l.toLanguageTag());
+
+ Collator c = Collator.getInstance(l);
+ assertTrue(c.compare("2", "11") < 0);
+ assertTrue(c.compare("11", "ae") < 0);
+ assertTrue(c.compare("ae", "Ä") < 0);
+ assertTrue(c.compare("Ä", "ä") < 0);
+ assertTrue(c.compare("ä", "AF") < 0);
+ assertTrue(c.compare("AF", "af") < 0);
+ }
}
diff --git a/luni/src/test/java/libcore/java/util/LocaleTest.java b/luni/src/test/java/libcore/java/util/LocaleTest.java
index b87dc97..0512b13 100644
--- a/luni/src/test/java/libcore/java/util/LocaleTest.java
+++ b/luni/src/test/java/libcore/java/util/LocaleTest.java
@@ -39,9 +39,22 @@
// and variant, but a display name made up of the raw strings.
// Newer releases return slightly different results, but no less unreasonable.
assertEquals("aabbcc", invalid.getDisplayLanguage());
- assertEquals("", invalid.getDisplayCountry());
- assertEquals("DDEEFF_GGHHII", invalid.getDisplayVariant());
- assertEquals("aabbcc (DDEEFF,DDEEFF_GGHHII)", invalid.getDisplayName());
+ assertEquals("DDEEFF", invalid.getDisplayCountry());
+ assertEquals("GGHHII", invalid.getDisplayVariant());
+ assertEquals("aabbcc (DDEEFF,GGHHII)", invalid.getDisplayName());
+ }
+
+ public void test_getDisplayName_emptyCodes() {
+ Locale emptyLanguage = new Locale("", "DdeEFf");
+ assertEquals("", emptyLanguage.getDisplayLanguage());
+
+ Locale emptyCountry = new Locale("AaBbCc", "");
+ assertEquals("", emptyCountry.getDisplayCountry());
+
+ Locale emptyCountryAndLanguage = new Locale("", "", "Farl");
+ assertEquals("", emptyCountryAndLanguage.getDisplayLanguage());
+ assertEquals("", emptyCountryAndLanguage.getDisplayCountry());
+ assertEquals("Farl", emptyCountryAndLanguage.getDisplayVariant());
}
// http://b/2611311; if there's no display language/country/variant, use the raw codes.
@@ -53,8 +66,8 @@
assertEquals("xx", unknown.getDisplayLanguage());
assertEquals("YY", unknown.getDisplayCountry());
- assertEquals("TRADITIONAL", unknown.getDisplayVariant());
- assertEquals("xx (YY,TRADITIONAL)", unknown.getDisplayName());
+ assertEquals("Traditional", unknown.getDisplayVariant());
+ assertEquals("xx (YY,Traditional)", unknown.getDisplayName());
}
public void test_getDisplayName_easy() throws Exception {