Java Code Examples for android.system.Os#bind()

The following examples show how to use android.system.Os#bind() . You can vote up the ones you like or vote down the ones you don't like, and go to the original project or source file by following the links above each example. You may check out the related API usage on the sidebar.
Example 1
Source File: NetworkDiagnostics.java    From android_9.0.0_r45 with Apache License 2.0 6 votes vote down vote up
protected void setupSocket(
        int sockType, int protocol, long writeTimeout, long readTimeout, int dstPort)
        throws ErrnoException, IOException {
    final int oldTag = TrafficStats.getAndSetThreadStatsTag(TrafficStats.TAG_SYSTEM_PROBE);
    try {
        mFileDescriptor = Os.socket(mAddressFamily, sockType, protocol);
    } finally {
        TrafficStats.setThreadStatsTag(oldTag);
    }
    // Setting SNDTIMEO is purely for defensive purposes.
    Os.setsockoptTimeval(mFileDescriptor,
            SOL_SOCKET, SO_SNDTIMEO, StructTimeval.fromMillis(writeTimeout));
    Os.setsockoptTimeval(mFileDescriptor,
            SOL_SOCKET, SO_RCVTIMEO, StructTimeval.fromMillis(readTimeout));
    // TODO: Use IP_RECVERR/IPV6_RECVERR, pending OsContants availability.
    mNetwork.bindSocket(mFileDescriptor);
    if (mSource != null) {
        Os.bind(mFileDescriptor, mSource, 0);
    }
    Os.connect(mFileDescriptor, mTarget, dstPort);
    mSocketAddress = Os.getsockname(mFileDescriptor);
}
 
Example 2
Source File: IpSecService.java    From android_9.0.0_r45 with Apache License 2.0 6 votes vote down vote up
/**
 * This function finds and forcibly binds to a random system port, ensuring that the port cannot
 * be unbound.
 *
 * <p>A socket cannot be un-bound from a port if it was bound to that port by number. To select
 * a random open port and then bind by number, this function creates a temp socket, binds to a
 * random port (specifying 0), gets that port number, and then uses is to bind the user's UDP
 * Encapsulation Socket forcibly, so that it cannot be un-bound by the user with the returned
 * FileHandle.
 *
 * <p>The loop in this function handles the inherent race window between un-binding to a port
 * and re-binding, during which the system could *technically* hand that port out to someone
 * else.
 */
private int bindToRandomPort(FileDescriptor sockFd) throws IOException {
    for (int i = MAX_PORT_BIND_ATTEMPTS; i > 0; i--) {
        try {
            FileDescriptor probeSocket = Os.socket(AF_INET, SOCK_DGRAM, IPPROTO_UDP);
            Os.bind(probeSocket, INADDR_ANY, 0);
            int port = ((InetSocketAddress) Os.getsockname(probeSocket)).getPort();
            Os.close(probeSocket);
            Log.v(TAG, "Binding to port " + port);
            Os.bind(sockFd, INADDR_ANY, port);
            return port;
        } catch (ErrnoException e) {
            // Someone miraculously claimed the port just after we closed probeSocket.
            if (e.errno == OsConstants.EADDRINUSE) {
                continue;
            }
            throw e.rethrowAsIOException();
        }
    }
    throw new IOException("Failed " + MAX_PORT_BIND_ATTEMPTS + " attempts to bind to a port");
}
 
Example 3
Source File: IpSecService.java    From android_9.0.0_r45 with Apache License 2.0 4 votes vote down vote up
/**
 * Open a socket via the system server and bind it to the specified port (random if port=0).
 * This will return a PFD to the user that represent a bound UDP socket. The system server will
 * cache the socket and a record of its owner so that it can and must be freed when no longer
 * needed.
 */
@Override
public synchronized IpSecUdpEncapResponse openUdpEncapsulationSocket(int port, IBinder binder)
        throws RemoteException {
    if (port != 0 && (port < FREE_PORT_MIN || port > PORT_MAX)) {
        throw new IllegalArgumentException(
                "Specified port number must be a valid non-reserved UDP port");
    }
    checkNotNull(binder, "Null Binder passed to openUdpEncapsulationSocket");

    int callingUid = Binder.getCallingUid();
    UserRecord userRecord = mUserResourceTracker.getUserRecord(callingUid);
    final int resourceId = mNextResourceId++;
    FileDescriptor sockFd = null;
    try {
        if (!userRecord.mSocketQuotaTracker.isAvailable()) {
            return new IpSecUdpEncapResponse(IpSecManager.Status.RESOURCE_UNAVAILABLE);
        }

        sockFd = Os.socket(AF_INET, SOCK_DGRAM, IPPROTO_UDP);
        mUidFdTagger.tag(sockFd, callingUid);

        // This code is common to both the unspecified and specified port cases
        Os.setsockoptInt(
                sockFd,
                OsConstants.IPPROTO_UDP,
                OsConstants.UDP_ENCAP,
                OsConstants.UDP_ENCAP_ESPINUDP);

        mSrvConfig.getNetdInstance().ipSecSetEncapSocketOwner(sockFd, callingUid);
        if (port != 0) {
            Log.v(TAG, "Binding to port " + port);
            Os.bind(sockFd, INADDR_ANY, port);
        } else {
            port = bindToRandomPort(sockFd);
        }

        userRecord.mEncapSocketRecords.put(
                resourceId,
                new RefcountedResource<EncapSocketRecord>(
                        new EncapSocketRecord(resourceId, sockFd, port), binder));
        return new IpSecUdpEncapResponse(IpSecManager.Status.OK, resourceId, port, sockFd);
    } catch (IOException | ErrnoException e) {
        IoUtils.closeQuietly(sockFd);
    }
    // If we make it to here, then something has gone wrong and we couldn't open a socket.
    // The only reasonable condition that would cause that is resource unavailable.
    return new IpSecUdpEncapResponse(IpSecManager.Status.RESOURCE_UNAVAILABLE);
}