Merge changes from topic "cherry-pick-cell-keepalive"
* changes: Rework KeepalivePacketData for Compatibility with Cell Add Constants for NATT Keepalive to RILConstants Relocate KeepalivePacketData to frameworks/base
This commit is contained in:
@@ -14,15 +14,15 @@
|
|||||||
* limitations under the License.
|
* limitations under the License.
|
||||||
*/
|
*/
|
||||||
|
|
||||||
package com.android.server.connectivity;
|
package android.net;
|
||||||
|
|
||||||
import static android.net.util.NetworkConstants.IPV4_HEADER_MIN_LEN;
|
|
||||||
import static android.net.util.NetworkConstants.UDP_HEADER_LEN;
|
|
||||||
|
|
||||||
import android.system.OsConstants;
|
import android.system.OsConstants;
|
||||||
import android.net.ConnectivityManager;
|
import android.net.ConnectivityManager;
|
||||||
import android.net.NetworkUtils;
|
|
||||||
import android.net.util.IpUtils;
|
import android.net.util.IpUtils;
|
||||||
|
import android.os.Parcel;
|
||||||
|
import android.os.Parcelable;
|
||||||
|
import android.system.OsConstants;
|
||||||
|
import android.util.Log;
|
||||||
|
|
||||||
import java.net.Inet4Address;
|
import java.net.Inet4Address;
|
||||||
import java.net.Inet6Address;
|
import java.net.Inet6Address;
|
||||||
@@ -38,9 +38,8 @@ import static android.net.ConnectivityManager.PacketKeepalive.*;
|
|||||||
*
|
*
|
||||||
* @hide
|
* @hide
|
||||||
*/
|
*/
|
||||||
public class KeepalivePacketData {
|
public class KeepalivePacketData implements Parcelable {
|
||||||
/** Protocol of the packet to send; one of the OsConstants.ETH_P_* values. */
|
private static final String TAG = "KeepalivePacketData";
|
||||||
public final int protocol;
|
|
||||||
|
|
||||||
/** Source IP address */
|
/** Source IP address */
|
||||||
public final InetAddress srcAddress;
|
public final InetAddress srcAddress;
|
||||||
@@ -54,54 +53,57 @@ public class KeepalivePacketData {
|
|||||||
/** Destination port */
|
/** Destination port */
|
||||||
public final int dstPort;
|
public final int dstPort;
|
||||||
|
|
||||||
/** Destination MAC address. Can change if routing changes. */
|
|
||||||
public byte[] dstMac;
|
|
||||||
|
|
||||||
/** Packet data. A raw byte string of packet data, not including the link-layer header. */
|
/** Packet data. A raw byte string of packet data, not including the link-layer header. */
|
||||||
public final byte[] data;
|
private final byte[] mPacket;
|
||||||
|
|
||||||
|
private static final int IPV4_HEADER_LENGTH = 20;
|
||||||
|
private static final int UDP_HEADER_LENGTH = 8;
|
||||||
|
|
||||||
|
// This should only be constructed via static factory methods, such as
|
||||||
|
// nattKeepalivePacket
|
||||||
protected KeepalivePacketData(InetAddress srcAddress, int srcPort,
|
protected KeepalivePacketData(InetAddress srcAddress, int srcPort,
|
||||||
InetAddress dstAddress, int dstPort, byte[] data) throws InvalidPacketException {
|
InetAddress dstAddress, int dstPort, byte[] data) throws InvalidPacketException {
|
||||||
this.srcAddress = srcAddress;
|
this.srcAddress = srcAddress;
|
||||||
this.dstAddress = dstAddress;
|
this.dstAddress = dstAddress;
|
||||||
this.srcPort = srcPort;
|
this.srcPort = srcPort;
|
||||||
this.dstPort = dstPort;
|
this.dstPort = dstPort;
|
||||||
this.data = data;
|
this.mPacket = data;
|
||||||
|
|
||||||
// Check we have two IP addresses of the same family.
|
// Check we have two IP addresses of the same family.
|
||||||
if (srcAddress == null || dstAddress == null ||
|
if (srcAddress == null || dstAddress == null || !srcAddress.getClass().getName()
|
||||||
!srcAddress.getClass().getName().equals(dstAddress.getClass().getName())) {
|
.equals(dstAddress.getClass().getName())) {
|
||||||
throw new InvalidPacketException(ERROR_INVALID_IP_ADDRESS);
|
Log.e(TAG, "Invalid or mismatched InetAddresses in KeepalivePacketData");
|
||||||
}
|
|
||||||
|
|
||||||
// Set the protocol.
|
|
||||||
if (this.dstAddress instanceof Inet4Address) {
|
|
||||||
this.protocol = OsConstants.ETH_P_IP;
|
|
||||||
} else if (this.dstAddress instanceof Inet6Address) {
|
|
||||||
this.protocol = OsConstants.ETH_P_IPV6;
|
|
||||||
} else {
|
|
||||||
throw new InvalidPacketException(ERROR_INVALID_IP_ADDRESS);
|
throw new InvalidPacketException(ERROR_INVALID_IP_ADDRESS);
|
||||||
}
|
}
|
||||||
|
|
||||||
// Check the ports.
|
// Check the ports.
|
||||||
if (!IpUtils.isValidUdpOrTcpPort(srcPort) || !IpUtils.isValidUdpOrTcpPort(dstPort)) {
|
if (!IpUtils.isValidUdpOrTcpPort(srcPort) || !IpUtils.isValidUdpOrTcpPort(dstPort)) {
|
||||||
|
Log.e(TAG, "Invalid ports in KeepalivePacketData");
|
||||||
throw new InvalidPacketException(ERROR_INVALID_PORT);
|
throw new InvalidPacketException(ERROR_INVALID_PORT);
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
|
|
||||||
public static class InvalidPacketException extends Exception {
|
public static class InvalidPacketException extends Exception {
|
||||||
final public int error;
|
public final int error;
|
||||||
public InvalidPacketException(int error) {
|
public InvalidPacketException(int error) {
|
||||||
this.error = error;
|
this.error = error;
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
|
|
||||||
/**
|
public byte[] getPacket() {
|
||||||
* Creates an IPsec NAT-T keepalive packet with the specified parameters.
|
return mPacket.clone();
|
||||||
*/
|
}
|
||||||
|
|
||||||
public static KeepalivePacketData nattKeepalivePacket(
|
public static KeepalivePacketData nattKeepalivePacket(
|
||||||
InetAddress srcAddress, int srcPort,
|
InetAddress srcAddress, int srcPort, InetAddress dstAddress, int dstPort)
|
||||||
InetAddress dstAddress, int dstPort) throws InvalidPacketException {
|
throws InvalidPacketException {
|
||||||
|
|
||||||
|
// FIXME: remove this and actually support IPv6 keepalives
|
||||||
|
if (srcAddress instanceof Inet6Address && dstAddress instanceof Inet6Address) {
|
||||||
|
// Optimistically returning an IPv6 Keepalive Packet with no data,
|
||||||
|
// which currently only works on cellular
|
||||||
|
return new KeepalivePacketData(srcAddress, srcPort, dstAddress, dstPort, new byte[0]);
|
||||||
|
}
|
||||||
|
|
||||||
if (!(srcAddress instanceof Inet4Address) || !(dstAddress instanceof Inet4Address)) {
|
if (!(srcAddress instanceof Inet4Address) || !(dstAddress instanceof Inet4Address)) {
|
||||||
throw new InvalidPacketException(ERROR_INVALID_IP_ADDRESS);
|
throw new InvalidPacketException(ERROR_INVALID_IP_ADDRESS);
|
||||||
@@ -111,7 +113,7 @@ public class KeepalivePacketData {
|
|||||||
throw new InvalidPacketException(ERROR_INVALID_PORT);
|
throw new InvalidPacketException(ERROR_INVALID_PORT);
|
||||||
}
|
}
|
||||||
|
|
||||||
int length = IPV4_HEADER_MIN_LEN + UDP_HEADER_LEN + 1;
|
int length = IPV4_HEADER_LENGTH + UDP_HEADER_LENGTH + 1;
|
||||||
ByteBuffer buf = ByteBuffer.allocate(length);
|
ByteBuffer buf = ByteBuffer.allocate(length);
|
||||||
buf.order(ByteOrder.BIG_ENDIAN);
|
buf.order(ByteOrder.BIG_ENDIAN);
|
||||||
buf.putShort((short) 0x4500); // IP version and TOS
|
buf.putShort((short) 0x4500); // IP version and TOS
|
||||||
@@ -130,8 +132,43 @@ public class KeepalivePacketData {
|
|||||||
buf.putShort((short) 0); // UDP checksum
|
buf.putShort((short) 0); // UDP checksum
|
||||||
buf.put((byte) 0xff); // NAT-T keepalive
|
buf.put((byte) 0xff); // NAT-T keepalive
|
||||||
buf.putShort(ipChecksumOffset, IpUtils.ipChecksum(buf, 0));
|
buf.putShort(ipChecksumOffset, IpUtils.ipChecksum(buf, 0));
|
||||||
buf.putShort(udpChecksumOffset, IpUtils.udpChecksum(buf, 0, IPV4_HEADER_MIN_LEN));
|
buf.putShort(udpChecksumOffset, IpUtils.udpChecksum(buf, 0, IPV4_HEADER_LENGTH));
|
||||||
|
|
||||||
return new KeepalivePacketData(srcAddress, srcPort, dstAddress, dstPort, buf.array());
|
return new KeepalivePacketData(srcAddress, srcPort, dstAddress, dstPort, buf.array());
|
||||||
}
|
}
|
||||||
|
|
||||||
|
/* Parcelable Implementation */
|
||||||
|
public int describeContents() {
|
||||||
|
return 0;
|
||||||
|
}
|
||||||
|
|
||||||
|
/** Write to parcel */
|
||||||
|
public void writeToParcel(Parcel out, int flags) {
|
||||||
|
out.writeString(srcAddress.getHostAddress());
|
||||||
|
out.writeString(dstAddress.getHostAddress());
|
||||||
|
out.writeInt(srcPort);
|
||||||
|
out.writeInt(dstPort);
|
||||||
|
out.writeByteArray(mPacket);
|
||||||
|
}
|
||||||
|
|
||||||
|
private KeepalivePacketData(Parcel in) {
|
||||||
|
srcAddress = NetworkUtils.numericToInetAddress(in.readString());
|
||||||
|
dstAddress = NetworkUtils.numericToInetAddress(in.readString());
|
||||||
|
srcPort = in.readInt();
|
||||||
|
dstPort = in.readInt();
|
||||||
|
mPacket = in.createByteArray();
|
||||||
|
}
|
||||||
|
|
||||||
|
/** Parcelable Creator */
|
||||||
|
public static final Parcelable.Creator<KeepalivePacketData> CREATOR =
|
||||||
|
new Parcelable.Creator<KeepalivePacketData>() {
|
||||||
|
public KeepalivePacketData createFromParcel(Parcel in) {
|
||||||
|
return new KeepalivePacketData(in);
|
||||||
|
}
|
||||||
|
|
||||||
|
public KeepalivePacketData[] newArray(int size) {
|
||||||
|
return new KeepalivePacketData[size];
|
||||||
|
}
|
||||||
|
};
|
||||||
|
|
||||||
}
|
}
|
||||||
@@ -18,10 +18,10 @@ package com.android.server.connectivity;
|
|||||||
|
|
||||||
import com.android.internal.util.HexDump;
|
import com.android.internal.util.HexDump;
|
||||||
import com.android.internal.util.IndentingPrintWriter;
|
import com.android.internal.util.IndentingPrintWriter;
|
||||||
import com.android.server.connectivity.KeepalivePacketData;
|
|
||||||
import com.android.server.connectivity.NetworkAgentInfo;
|
import com.android.server.connectivity.NetworkAgentInfo;
|
||||||
import android.net.ConnectivityManager;
|
import android.net.ConnectivityManager;
|
||||||
import android.net.ConnectivityManager.PacketKeepalive;
|
import android.net.ConnectivityManager.PacketKeepalive;
|
||||||
|
import android.net.KeepalivePacketData;
|
||||||
import android.net.LinkAddress;
|
import android.net.LinkAddress;
|
||||||
import android.net.NetworkAgent;
|
import android.net.NetworkAgent;
|
||||||
import android.net.NetworkUtils;
|
import android.net.NetworkUtils;
|
||||||
@@ -129,7 +129,7 @@ public class KeepaliveTracker {
|
|||||||
.append("->")
|
.append("->")
|
||||||
.append(IpUtils.addressAndPortToString(mPacket.dstAddress, mPacket.dstPort))
|
.append(IpUtils.addressAndPortToString(mPacket.dstAddress, mPacket.dstPort))
|
||||||
.append(" interval=" + mInterval)
|
.append(" interval=" + mInterval)
|
||||||
.append(" data=" + HexDump.toHexString(mPacket.data))
|
.append(" packetData=" + HexDump.toHexString(mPacket.getPacket()))
|
||||||
.append(" uid=").append(mUid).append(" pid=").append(mPid)
|
.append(" uid=").append(mUid).append(" pid=").append(mPid)
|
||||||
.append(" ]")
|
.append(" ]")
|
||||||
.toString();
|
.toString();
|
||||||
@@ -172,7 +172,7 @@ public class KeepaliveTracker {
|
|||||||
}
|
}
|
||||||
|
|
||||||
private int checkInterval() {
|
private int checkInterval() {
|
||||||
return mInterval >= 20 ? SUCCESS : ERROR_INVALID_INTERVAL;
|
return mInterval >= 10 ? SUCCESS : ERROR_INVALID_INTERVAL;
|
||||||
}
|
}
|
||||||
|
|
||||||
private int isValid() {
|
private int isValid() {
|
||||||
|
|||||||
Reference in New Issue
Block a user