Use -fvisibility and clean up a little.

The visibility change isn't obviously useful, but it's a good excuse to clean
up some of our networking code a little.

Change-Id: I165b32b9c76a3707c512e07de07992f63673ab4f
diff --git a/NativeCode.mk b/NativeCode.mk
index d4960c5..648cd33 100644
--- a/NativeCode.mk
+++ b/NativeCode.mk
@@ -78,6 +78,8 @@
 core_c_includes := $(sort libcore/include $(LOCAL_C_INCLUDES) $(JNI_H_INCLUDE))
 core_shared_libraries := $(sort $(LOCAL_SHARED_LIBRARIES))
 core_static_libraries := $(sort $(LOCAL_STATIC_LIBRARIES))
+core_cflags := -fvisibility=hidden -fvisibility-inlines-hidden
+core_cflags += '-DGCC_HIDDEN=__attribute__((visibility("hidden")))'
 
 
 #
@@ -87,7 +89,7 @@
 include $(CLEAR_VARS)
 
 LOCAL_CFLAGS += -Wall -Wextra -Werror
-
+LOCAL_CFLAGS += $(core_cflags)
 ifeq ($(TARGET_ARCH),arm)
 # Ignore "note: the mangling of 'va_list' has changed in GCC 4.4"
 LOCAL_CFLAGS += -Wno-psabi
@@ -125,6 +127,7 @@
 
     # Define the rules.
     LOCAL_SRC_FILES := $(core_src_files)
+    LOCAL_CFLAGS += $(core_cflags)
     LOCAL_C_INCLUDES := $(core_c_includes)
     LOCAL_SHARED_LIBRARIES := $(core_shared_libraries)
     LOCAL_STATIC_LIBRARIES := $(core_static_libraries)
diff --git a/dalvik/src/main/java/dalvik/system/BlockGuard.java b/dalvik/src/main/java/dalvik/system/BlockGuard.java
index 9b9268d..0f7ff10 100644
--- a/dalvik/src/main/java/dalvik/system/BlockGuard.java
+++ b/dalvik/src/main/java/dalvik/system/BlockGuard.java
@@ -404,10 +404,6 @@
             mNetwork.close(aFD);
         }
 
-        public void setInetAddress(InetAddress sender, byte[] address) {
-            mNetwork.setInetAddress(sender, address);
-        }
-
         private boolean isLingerSocket(FileDescriptor fd) throws SocketException {
             try {
                 Object lingerValue = mNetwork.getSocketOption(fd, SocketOptions.SO_LINGER);
diff --git a/luni/src/main/java/java/net/PlainDatagramSocketImpl.java b/luni/src/main/java/java/net/PlainDatagramSocketImpl.java
index d28ac1f..1109a0e 100644
--- a/luni/src/main/java/java/net/PlainDatagramSocketImpl.java
+++ b/luni/src/main/java/java/net/PlainDatagramSocketImpl.java
@@ -155,7 +155,8 @@
         // We don't actually want the data: we just want the DatagramPacket's filled-in address.
         DatagramPacket packet = new DatagramPacket(EmptyArray.BYTE, 0);
         int result = peekData(packet);
-        Platform.NETWORK.setInetAddress(sender, packet.getAddress().getAddress());
+        // TODO: maybe recv should do this?
+        sender.ipaddress = packet.getAddress().getAddress();
         return result;
     }
 
diff --git a/luni/src/main/java/org/apache/harmony/luni/platform/INetworkSystem.java b/luni/src/main/java/org/apache/harmony/luni/platform/INetworkSystem.java
index c073c41..3cf4549 100644
--- a/luni/src/main/java/org/apache/harmony/luni/platform/INetworkSystem.java
+++ b/luni/src/main/java/org/apache/harmony/luni/platform/INetworkSystem.java
@@ -141,8 +141,4 @@
      * concurrently.
      */
     public void close(FileDescriptor fd) throws IOException;
-
-    // TODO: change the single caller so that recv/recvDirect
-    // can mutate the InetAddress as a side-effect.
-    public void setInetAddress(InetAddress sender, byte[] address);
 }
diff --git a/luni/src/main/java/org/apache/harmony/luni/platform/OSNetworkSystem.java b/luni/src/main/java/org/apache/harmony/luni/platform/OSNetworkSystem.java
index 4be00f2..6ff29c6 100644
--- a/luni/src/main/java/org/apache/harmony/luni/platform/OSNetworkSystem.java
+++ b/luni/src/main/java/org/apache/harmony/luni/platform/OSNetworkSystem.java
@@ -101,8 +101,6 @@
 
     public native void sendUrgentData(FileDescriptor fd, byte value);
 
-    public native void setInetAddress(InetAddress sender, byte[] address);
-
     public native void setSocketOption(FileDescriptor fd, int opt, Object optVal)
             throws SocketException;
 
diff --git a/luni/src/main/native/libcore_net_RawSocket.cpp b/luni/src/main/native/libcore_net_RawSocket.cpp
index 7878986..b23208d 100644
--- a/luni/src/main/native/libcore_net_RawSocket.cpp
+++ b/luni/src/main/native/libcore_net_RawSocket.cpp
@@ -39,6 +39,11 @@
 #include <netinet/ip.h>
 #include <linux/udp.h>
 
+union GCC_HIDDEN sockunion {
+    sockaddr sa;
+    sockaddr_ll sll;
+} su;
+
 /*
  * Creates a socket suitable for raw socket operations.  The socket is
  * bound to the interface specified by the supplied name.  The socket
@@ -51,24 +56,19 @@
 static void RawSocket_create(JNIEnv* env, jclass, jobject fileDescriptor,
     jstring interfaceName) {
 
-  union sockunion {
-    struct sockaddr sa;
-    struct sockaddr_ll sll;
-  } su;
-
-  short protocol = ETH_P_IP;
   ScopedUtfChars ifname(env, interfaceName);
-
   if (ifname.c_str() == NULL) {
     return;
   }
 
+  short protocol = ETH_P_IP;
+  sockunion su;
   memset(&su, 0, sizeof(su));
   su.sll.sll_family = PF_PACKET;
   su.sll.sll_protocol = htons(protocol);
   su.sll.sll_ifindex = if_nametoindex(ifname.c_str());
-  int sock = socket(PF_PACKET, SOCK_DGRAM, htons(protocol));
 
+  int sock = socket(PF_PACKET, SOCK_DGRAM, htons(protocol));
   if (sock == -1) {
     LOGE("Can't create socket %s", strerror(errno));
     jniThrowSocketException(env, errno);
@@ -76,7 +76,6 @@
   }
 
   jniSetFileDescriptorOfFD(env, fileDescriptor, sock);
-
   if (!setBlocking(sock, false)) {
     LOGE("Can't set non-blocking mode on socket %s", strerror(errno));
     jniThrowSocketException(env, errno);
@@ -84,7 +83,6 @@
   }
 
   int err = bind(sock, &su.sa, sizeof(su));
-
   if (err != 0) {
     LOGE("Socket bind error %s", strerror(errno));
     jniThrowSocketException(env, errno);
@@ -108,29 +106,23 @@
     return 0;
   }
 
-  union sockunion {
-    struct sockaddr sa;
-    struct sockaddr_ll sll;
-  } su;
-  short protocol = ETH_P_IP;
   ScopedUtfChars ifname(env, interfaceName);
-
   if (ifname.c_str() == NULL) {
     return 0;
   }
 
   ScopedByteArrayRO byteArray(env, packet);
-
   if (byteArray.get() == NULL) {
     return 0;
   }
 
   ScopedByteArrayRO mac(env, destMac);
-
   if (mac.get() == NULL) {
     return 0;
   }
 
+  short protocol = ETH_P_IP;
+  sockunion su;
   memset(&su, 0, sizeof(su));
   su.sll.sll_hatype = htons(1); // ARPHRD_ETHER
   su.sll.sll_halen = mac.size();
@@ -140,7 +132,6 @@
   su.sll.sll_ifindex = if_nametoindex(ifname.c_str());
 
   int err;
-
   {
     int intFd = fd.get();
     AsynchronousSocketCloseMonitor monitor(intFd);
@@ -163,33 +154,29 @@
     jint timeout_millis)
 {
   NetFd fd(env, fileDescriptor);
-
   if (fd.isClosed()) {
     return 0;
   }
 
   ScopedByteArrayRW body(env, packet);
   jbyte* packetData = body.get();
-
   if (packetData == NULL) {
     return 0;
   }
 
   packetData += offset;
 
-  int packetSize = byteCount;
-  unsigned int size = 0;
-  struct pollfd fds[1];
-
+  pollfd fds[1];
   fds[0].fd = fd.get();
   fds[0].events = POLLIN;
   int retval = poll(fds, 1, timeout_millis);
-
   if (retval <= 0) {
     return 0;
   }
 
+  unsigned int size = 0;
   {
+    int packetSize = byteCount;
     int intFd = fd.get();
     AsynchronousSocketCloseMonitor monitor(intFd);
     size = NET_FAILURE_RETRY(fd, read(intFd, packetData, packetSize));
@@ -201,20 +188,16 @@
 
   // quick check for UDP type & UDP port
   // the packet is an IP header, UDP header, and UDP payload
-  if ((size < (sizeof(struct iphdr) + sizeof(struct udphdr)))) {
+  if ((size < (sizeof(iphdr) + sizeof(udphdr)))) {
     return 0;  // runt packet
   }
 
-  u_int8_t ip_proto = ((struct iphdr *) packetData)->protocol;
-
+  u_int8_t ip_proto = ((iphdr *) packetData)->protocol;
   if (ip_proto != IPPROTO_UDP) {
     return 0;  // something other than UDP
   }
 
-  __be16 destPort =
-      htons((reinterpret_cast<struct udphdr*>
-             (packetData + sizeof(struct iphdr)))->dest);
-
+  __be16 destPort = htons((reinterpret_cast<udphdr*>(packetData + sizeof(iphdr)))->dest);
   if (destPort != port) {
     return 0; // something other than requested port
   }
@@ -222,19 +205,12 @@
   return size;
 }
 
-/*
- * JNI registration
- */
 static JNINativeMethod gRawMethods[] = {
-  NATIVE_METHOD(RawSocket, create,
-                "(Ljava/io/FileDescriptor;Ljava/lang/String;)V"),
-  NATIVE_METHOD(RawSocket, sendPacket,
-                "(Ljava/io/FileDescriptor;Ljava/lang/String;[B[BII)I"),
-  NATIVE_METHOD(RawSocket, recvPacket,
-                "(Ljava/io/FileDescriptor;[BIIII)I"),
+  NATIVE_METHOD(RawSocket, create, "(Ljava/io/FileDescriptor;Ljava/lang/String;)V"),
+  NATIVE_METHOD(RawSocket, sendPacket, "(Ljava/io/FileDescriptor;Ljava/lang/String;[B[BII)I"),
+  NATIVE_METHOD(RawSocket, recvPacket, "(Ljava/io/FileDescriptor;[BIIII)I"),
 };
 
 int register_libcore_net_RawSocket(JNIEnv* env) {
-  return jniRegisterNativeMethods(env,
-         "libcore/net/RawSocket", gRawMethods, NELEM(gRawMethods));
+  return jniRegisterNativeMethods(env, "libcore/net/RawSocket", gRawMethods, NELEM(gRawMethods));
 }
diff --git a/luni/src/main/native/org_apache_harmony_luni_platform_OSNetworkSystem.cpp b/luni/src/main/native/org_apache_harmony_luni_platform_OSNetworkSystem.cpp
index 03d1e69..9e5e69f 100644
--- a/luni/src/main/native/org_apache_harmony_luni_platform_OSNetworkSystem.cpp
+++ b/luni/src/main/native/org_apache_harmony_luni_platform_OSNetworkSystem.cpp
@@ -81,18 +81,6 @@
 #define SOCKET_OP_READ 1
 #define SOCKET_OP_WRITE 2
 
-static struct CachedFields {
-    jfieldID iaddr_ipaddress;
-    jfieldID integer_class_value;
-    jfieldID boolean_class_value;
-    jfieldID socketimpl_address;
-    jfieldID socketimpl_port;
-    jfieldID socketimpl_localport;
-    jfieldID dpack_address;
-    jfieldID dpack_port;
-    jfieldID dpack_length;
-} gCachedFields;
-
 /**
  * Returns the port number in a sockaddr_storage structure.
  *
@@ -203,10 +191,8 @@
         jniThrowNullPointerException(env, NULL);
         return false;
     }
-    jbyteArray addressBytes =
-        reinterpret_cast<jbyteArray>(env->GetObjectField(inetAddress,
-            gCachedFields.iaddr_ipaddress));
-
+    static jfieldID fid = env->GetFieldID(JniConstants::inetAddressClass, "ipaddress", "[B");
+    jbyteArray addressBytes = reinterpret_cast<jbyteArray>(env->GetObjectField(inetAddress, fid));
     return byteArrayToSocketAddress(env, NULL, addressBytes, port, ss);
 }
 
@@ -379,7 +365,7 @@
     if (rc == -1 && errno == EINVAL) {
         // Maybe we're a 32-bit binary talking to a 64-bit kernel?
         // glibc doesn't automatically handle this.
-        struct group_req64 {
+        struct GCC_HIDDEN group_req64 {
             uint32_t gr_interface;
             uint32_t my_padding;
             sockaddr_storage gr_group;
@@ -396,34 +382,6 @@
 }
 #endif // def ENABLE_MULTICAST
 
-static bool initCachedFields(JNIEnv* env) {
-    memset(&gCachedFields, 0, sizeof(gCachedFields));
-    struct CachedFields* c = &gCachedFields;
-
-    struct fieldInfo {
-        jfieldID* field;
-        jclass clazz;
-        const char* name;
-        const char* type;
-    } fields[] = {
-        {&c->iaddr_ipaddress, JniConstants::inetAddressClass, "ipaddress", "[B"},
-        {&c->integer_class_value, JniConstants::integerClass, "value", "I"},
-        {&c->boolean_class_value, JniConstants::booleanClass, "value", "Z"},
-        {&c->socketimpl_port, JniConstants::socketImplClass, "port", "I"},
-        {&c->socketimpl_localport, JniConstants::socketImplClass, "localport", "I"},
-        {&c->socketimpl_address, JniConstants::socketImplClass, "address", "Ljava/net/InetAddress;"},
-        {&c->dpack_address, JniConstants::datagramPacketClass, "address", "Ljava/net/InetAddress;"},
-        {&c->dpack_port, JniConstants::datagramPacketClass, "port", "I"},
-        {&c->dpack_length, JniConstants::datagramPacketClass, "length", "I"}
-    };
-    for (unsigned i = 0; i < sizeof(fields) / sizeof(fields[0]); i++) {
-        fieldInfo f = fields[i];
-        *f.field = env->GetFieldID(f.clazz, f.name, f.type);
-        if (*f.field == NULL) return false;
-    }
-    return true;
-}
-
 static void OSNetworkSystem_socket(JNIEnv* env, jobject, jobject fileDescriptor, jboolean stream) {
     if (fileDescriptor == NULL) {
         jniThrowNullPointerException(env, NULL);
@@ -670,8 +628,6 @@
             return;
         }
         int remotePort = getSocketAddressPort(&ss);
-        env->SetObjectField(newSocket, gCachedFields.socketimpl_address, remoteAddress);
-        env->SetIntField(newSocket, gCachedFields.socketimpl_port, remotePort);
 
         // Local port.
         memset(&ss, 0, addrLen);
@@ -682,7 +638,13 @@
             return;
         }
         int localPort = getSocketAddressPort(&ss);
-        env->SetIntField(newSocket, gCachedFields.socketimpl_localport, localPort);
+
+        static jfieldID addressFid = env->GetFieldID(JniConstants::socketImplClass, "address", "Ljava/net/InetAddress;");
+        static jfieldID localPortFid = env->GetFieldID(JniConstants::socketImplClass, "localport", "I");
+        static jfieldID portFid = env->GetFieldID(JniConstants::socketImplClass, "port", "I");
+        env->SetObjectField(newSocket, addressFid, remoteAddress);
+        env->SetIntField(newSocket, portFid, remotePort);
+        env->SetIntField(newSocket, localPortFid, localPort);
     }
 
     jniSetFileDescriptorOfFD(env, clientFileDescriptor, clientFd);
@@ -719,11 +681,6 @@
     }
 }
 
-static void OSNetworkSystem_setInetAddress(JNIEnv* env, jobject,
-        jobject sender, jbyteArray address) {
-    env->SetObjectField(sender, gCachedFields.iaddr_ipaddress, address);
-}
-
 // TODO: can we merge this with recvDirect?
 static jint OSNetworkSystem_readDirect(JNIEnv* env, jobject, jobject fileDescriptor,
         jint address, jint count) {
@@ -804,8 +761,11 @@
         return 0;
     }
 
+    static jfieldID addressFid = env->GetFieldID(JniConstants::datagramPacketClass, "address", "Ljava/net/InetAddress;");
+    static jfieldID lengthFid = env->GetFieldID(JniConstants::datagramPacketClass, "length", "I");
+    static jfieldID portFid = env->GetFieldID(JniConstants::datagramPacketClass, "port", "I");
     if (packet != NULL) {
-        env->SetIntField(packet, gCachedFields.dpack_length, bytesReceived);
+        env->SetIntField(packet, lengthFid, bytesReceived);
         if (!connected) {
             jbyteArray addr = socketAddressToByteArray(env, &ss);
             if (addr == NULL) {
@@ -816,8 +776,8 @@
             if (sender == NULL) {
                 return 0;
             }
-            env->SetObjectField(packet, gCachedFields.dpack_address, sender);
-            env->SetIntField(packet, gCachedFields.dpack_port, port);
+            env->SetObjectField(packet, addressFid, sender);
+            env->SetIntField(packet, portFid, port);
         }
     }
     return bytesReceived;
@@ -1182,9 +1142,9 @@
     int intVal;
     bool wasBoolean = false;
     if (env->IsInstanceOf(optVal, JniConstants::integerClass)) {
-        intVal = (int) env->GetIntField(optVal, gCachedFields.integer_class_value);
+        intVal = intValue(env, optVal);
     } else if (env->IsInstanceOf(optVal, JniConstants::booleanClass)) {
-        intVal = (int) env->GetBooleanField(optVal, gCachedFields.boolean_class_value);
+        intVal = (int) booleanValue(env, optVal);
         wasBoolean = true;
     } else if (env->IsInstanceOf(optVal, JniConstants::inetAddressClass)) {
         // We use optVal directly as an InetAddress for IP_MULTICAST_IF.
@@ -1391,7 +1351,6 @@
     NATIVE_METHOD(OSNetworkSystem, send, "(Ljava/io/FileDescriptor;[BIIILjava/net/InetAddress;)I"),
     NATIVE_METHOD(OSNetworkSystem, sendDirect, "(Ljava/io/FileDescriptor;IIIILjava/net/InetAddress;)I"),
     NATIVE_METHOD(OSNetworkSystem, sendUrgentData, "(Ljava/io/FileDescriptor;B)V"),
-    NATIVE_METHOD(OSNetworkSystem, setInetAddress, "(Ljava/net/InetAddress;[B)V"),
     NATIVE_METHOD(OSNetworkSystem, setSocketOption, "(Ljava/io/FileDescriptor;ILjava/lang/Object;)V"),
     NATIVE_METHOD(OSNetworkSystem, shutdownInput, "(Ljava/io/FileDescriptor;)V"),
     NATIVE_METHOD(OSNetworkSystem, shutdownOutput, "(Ljava/io/FileDescriptor;)V"),
@@ -1402,6 +1361,5 @@
 
 int register_org_apache_harmony_luni_platform_OSNetworkSystem(JNIEnv* env) {
     AsynchronousSocketCloseMonitor::init();
-    return initCachedFields(env) && jniRegisterNativeMethods(env,
-            "org/apache/harmony/luni/platform/OSNetworkSystem", gMethods, NELEM(gMethods));
+    return jniRegisterNativeMethods(env, "org/apache/harmony/luni/platform/OSNetworkSystem", gMethods, NELEM(gMethods));
 }
diff --git a/luni/src/main/native/valueOf.cpp b/luni/src/main/native/valueOf.cpp
index a3475e3..310d48c 100644
--- a/luni/src/main/native/valueOf.cpp
+++ b/luni/src/main/native/valueOf.cpp
@@ -41,3 +41,13 @@
 jobject longValueOf(JNIEnv* env, jlong value) {
     return valueOf(env, JniConstants::longClass, "(J)Ljava/lang/Long;", value);
 }
+
+jboolean booleanValue(JNIEnv* env, jobject javaLangBoolean) {
+    static jfieldID fid = env->GetFieldID(JniConstants::booleanClass, "value", "Z");
+    return env->GetBooleanField(javaLangBoolean, fid);
+}
+
+jint intValue(JNIEnv* env, jobject javaLangInteger) {
+    static jfieldID fid = env->GetFieldID(JniConstants::integerClass, "value", "I");
+    return env->GetIntField(javaLangInteger, fid);
+}
diff --git a/luni/src/main/native/valueOf.h b/luni/src/main/native/valueOf.h
index 5c8588f..592977d 100644
--- a/luni/src/main/native/valueOf.h
+++ b/luni/src/main/native/valueOf.h
@@ -24,4 +24,9 @@
 jobject integerValueOf(JNIEnv* env, jint i);
 jobject longValueOf(JNIEnv* env, jlong l);
 
+// Note that these aren't equivalent to the Number methods: the jobject MUST be of the exact
+// type specified. This is less general but faster (and currently sufficient).
+jboolean booleanValue(JNIEnv* env, jobject javaLangBoolean);
+jint intValue(JNIEnv* env, jobject javaLangInteger);
+
 #endif  // VALUE_OF_H_included