Return not supported if no necessary socket option

In order to support tcp keepalive offload, some socket
options are necessary. If one of them isn't supported in
kernel, just return ERROR_HARDWARE_UNSUPPORTED to the
caller.
e.g.
TCP_REPAIR starts from kernel 3.5
TCP_REPAIR_QUEUE starts from kernel 3.5
TCP_QUEUE_SEQ starts from kernel 3.5
TCP_REPAIR_WINDOW starts from kernel version 4.8

Bug: 124453402
Test: -boot, flash, atest FrameworksNetTests
      -start tcp keepalive offload in kernel 4.4 and 4.9 device.

Change-Id: I6f87e5be2f2ca7aae1293820c164d0bc7b664eb6
diff --git a/services/core/java/com/android/server/connectivity/TcpKeepaliveController.java b/services/core/java/com/android/server/connectivity/TcpKeepaliveController.java
index 8a9ac23..65de83b 100644
--- a/services/core/java/com/android/server/connectivity/TcpKeepaliveController.java
+++ b/services/core/java/com/android/server/connectivity/TcpKeepaliveController.java
@@ -16,10 +16,12 @@
 package com.android.server.connectivity;
 
 import static android.net.SocketKeepalive.DATA_RECEIVED;
+import static android.net.SocketKeepalive.ERROR_HARDWARE_UNSUPPORTED;
 import static android.net.SocketKeepalive.ERROR_INVALID_SOCKET;
 import static android.net.SocketKeepalive.ERROR_SOCKET_NOT_IDLE;
 import static android.os.MessageQueue.OnFileDescriptorEventListener.EVENT_ERROR;
 import static android.os.MessageQueue.OnFileDescriptorEventListener.EVENT_INPUT;
+import static android.system.OsConstants.ENOPROTOOPT;
 import static android.system.OsConstants.FIONREAD;
 import static android.system.OsConstants.IPPROTO_TCP;
 import static android.system.OsConstants.TIOCOUTQ;
@@ -179,12 +181,13 @@
             trw = NetworkUtils.getTcpRepairWindow(fd);
         } catch (ErrnoException e) {
             Log.e(TAG, "Exception reading TCP state from socket", e);
-            try {
-                Os.setsockoptInt(fd, IPPROTO_TCP, TCP_REPAIR, TCP_REPAIR_OFF);
-            } catch (ErrnoException ex) {
-                Log.e(TAG, "Exception while turning off repair mode due to exception", ex);
+            if (e.errno == ENOPROTOOPT) {
+                // ENOPROTOOPT may happen in kernel version lower than 4.8.
+                // Treat it as ERROR_HARDWARE_UNSUPPORTED.
+                throw new InvalidSocketException(ERROR_HARDWARE_UNSUPPORTED, e);
+            } else {
+                throw new InvalidSocketException(ERROR_INVALID_SOCKET, e);
             }
-            throw new InvalidSocketException(ERROR_INVALID_SOCKET, e);
         } finally {
             dropAllIncomingPackets(fd, false);
         }