Donate to e Foundation | Murena handsets with /e/OS | Own a part of Murena! Learn more

Commit fb8021c8 authored by Etan Cohen's avatar Etan Cohen
Browse files

[NAN] Add support for NAN RTT.

Provide API for NAN RTT through WifiNanManager. While NAN RTT could be executed
directly through RttManager the peer information is hidden by WifiNanManager (no
MAC address is exposed). Using WifiNanManager keeps the information hidden.

Bug: 26564277
Change-Id: I8deeb3f9e360dc05f2ea175d115f287590d50322
parent cbf37593
Loading
Loading
Loading
Loading
+4 −1
Original line number Diff line number Diff line
@@ -15,4 +15,7 @@
 */

package android.net.wifi;

parcelable RttManager.RttCapabilities;
parcelable RttManager.ParcelableRttResults;
parcelable RttManager.ParcelableRttParams;
+77 −1
Original line number Diff line number Diff line
@@ -459,6 +459,34 @@ public class RttManager {
            preamble = PREAMBLE_HT;
            bandwidth = RTT_BW_20_SUPPORT;
        }

        /**
         * {@hide}
         */
        public String toString() {
            StringBuilder sb = new StringBuilder();
            sb.append("deviceType=" + deviceType);
            sb.append(", requestType=" + requestType);
            sb.append(", secure=" + secure);
            sb.append(", bssid=" + bssid);
            sb.append(", frequency=" + frequency);
            sb.append(", channelWidth=" + channelWidth);
            sb.append(", centerFreq0=" + centerFreq0);
            sb.append(", centerFreq1=" + centerFreq1);
            sb.append(", num_samples=" + num_samples);
            sb.append(", num_retries=" + num_retries);
            sb.append(", numberBurst=" + numberBurst);
            sb.append(", interval=" + interval);
            sb.append(", numSamplesPerBurst=" + numSamplesPerBurst);
            sb.append(", numRetriesPerMeasurementFrame=" + numRetriesPerMeasurementFrame);
            sb.append(", numRetriesPerFTMR=" + numRetriesPerFTMR);
            sb.append(", LCIRequest=" + LCIRequest);
            sb.append(", LCRRequest=" + LCRRequest);
            sb.append(", burstTimeout=" + burstTimeout);
            sb.append(", preamble=" + preamble);
            sb.append(", bandwidth=" + bandwidth);
            return sb.toString();
        }
    }

    /** pseudo-private class used to parcel arguments */
@@ -466,7 +494,10 @@ public class RttManager {

        public RttParams mParams[];

        ParcelableRttParams(RttParams[] params) {
        /**
         * {@hide}
         */
        public ParcelableRttParams(RttParams[] params) {
            mParams = params;
        }

@@ -714,6 +745,51 @@ public class RttManager {
            mResults = results;
        }

        /**
         * {@hide}
         */
        public String toString() {
            StringBuilder sb = new StringBuilder();
            for (int i = 0; i < mResults.length; ++i) {
                sb.append("[" + i + "]: ");
                sb.append("bssid=" + mResults[i].bssid);
                sb.append(", burstNumber=" + mResults[i].burstNumber);
                sb.append(", measurementFrameNumber=" + mResults[i].measurementFrameNumber);
                sb.append(", successMeasurementFrameNumber="
                        + mResults[i].successMeasurementFrameNumber);
                sb.append(", frameNumberPerBurstPeer=" + mResults[i].frameNumberPerBurstPeer);
                sb.append(", status=" + mResults[i].status);
                sb.append(", requestType=" + mResults[i].requestType);
                sb.append(", measurementType=" + mResults[i].measurementType);
                sb.append(", retryAfterDuration=" + mResults[i].retryAfterDuration);
                sb.append(", ts=" + mResults[i].ts);
                sb.append(", rssi=" + mResults[i].rssi);
                sb.append(", rssi_spread=" + mResults[i].rssi_spread);
                sb.append(", rssiSpread=" + mResults[i].rssiSpread);
                sb.append(", tx_rate=" + mResults[i].tx_rate);
                sb.append(", txRate=" + mResults[i].txRate);
                sb.append(", rxRate=" + mResults[i].rxRate);
                sb.append(", rtt_ns=" + mResults[i].rtt_ns);
                sb.append(", rtt=" + mResults[i].rtt);
                sb.append(", rtt_sd_ns=" + mResults[i].rtt_sd_ns);
                sb.append(", rttStandardDeviation=" + mResults[i].rttStandardDeviation);
                sb.append(", rtt_spread_ns=" + mResults[i].rtt_spread_ns);
                sb.append(", rttSpread=" + mResults[i].rttSpread);
                sb.append(", distance_cm=" + mResults[i].distance_cm);
                sb.append(", distance=" + mResults[i].distance);
                sb.append(", distance_sd_cm=" + mResults[i].distance_sd_cm);
                sb.append(", distanceStandardDeviation=" + mResults[i].distanceStandardDeviation);
                sb.append(", distance_spread_cm=" + mResults[i].distance_spread_cm);
                sb.append(", distanceSpread=" + mResults[i].distanceSpread);
                sb.append(", burstDuration=" + mResults[i].burstDuration);
                sb.append(", negotiatedBurstNum=" + mResults[i].negotiatedBurstNum);
                sb.append(", LCI=" + mResults[i].LCI);
                sb.append(", LCR=" + mResults[i].LCR);
                sb.append(", secure=" + mResults[i].secure);
            }
            return sb.toString();
        }

        /** Implement the Parcelable interface {@hide} */
        public int describeContents() {
            return 0;
+5 −0
Original line number Diff line number Diff line
@@ -17,6 +17,7 @@
package android.net.wifi.nan;

import android.net.wifi.nan.ConfigRequest;
import android.net.wifi.RttManager;

/**
 * Callback interface that WifiNanManager implements
@@ -28,4 +29,8 @@ oneway interface IWifiNanEventCallback
    void onConnectSuccess();
    void onConnectFail(int reason);
    void onIdentityChanged();

    void onRangingSuccess(int rangingId, in RttManager.ParcelableRttResults results);
    void onRangingFailure(int rangingId, int reason, in String description);
    void onRangingAborted(int rangingId);
}
+2 −0
Original line number Diff line number Diff line
@@ -23,6 +23,7 @@ import android.net.wifi.nan.IWifiNanEventCallback;
import android.net.wifi.nan.IWifiNanSessionCallback;
import android.net.wifi.nan.PublishConfig;
import android.net.wifi.nan.SubscribeConfig;
import android.net.wifi.RttManager;

/**
 * Interface that WifiNanService implements
@@ -51,4 +52,5 @@ interface IWifiNanManager
    void sendMessage(int clientId, int sessionId, int peerId, in byte[] message, int messageLength,
            int messageId);
    void terminateSession(int clientId, int sessionId);
    int startRanging(int clientId, int sessionId, in RttManager.ParcelableRttParams parms);
}
+130 −4
Original line number Diff line number Diff line
@@ -20,6 +20,7 @@ import android.annotation.NonNull;
import android.annotation.Nullable;
import android.annotation.SdkConstant;
import android.annotation.SdkConstant.SdkConstantType;
import android.net.wifi.RttManager;
import android.os.Binder;
import android.os.Bundle;
import android.os.Handler;
@@ -28,10 +29,12 @@ import android.os.Looper;
import android.os.Message;
import android.os.RemoteException;
import android.util.Log;
import android.util.SparseArray;

import com.android.internal.annotations.GuardedBy;

import java.lang.ref.WeakReference;
import java.util.Arrays;

/**
 * This class provides the primary API for managing Wi-Fi NAN operation:
@@ -91,7 +94,7 @@ public class WifiNanManager {

    private final IWifiNanManager mService;

    private Object mLock = new Object(); // lock access to the following vars
    private final Object mLock = new Object(); // lock access to the following vars

    @GuardedBy("mLock")
    private final IBinder mBinder = new Binder();
@@ -102,6 +105,9 @@ public class WifiNanManager {
    @GuardedBy("mLock")
    private Looper mLooper;

    @GuardedBy("mLock")
    private SparseArray<RttManager.RttListener> mRangingListeners = new SparseArray<>();

    /**
     * {@hide}
     */
@@ -237,6 +243,7 @@ public class WifiNanManager {
    @Override
    protected void finalize() throws Throwable {
        disconnect();
        super.finalize();
    }

    /**
@@ -415,12 +422,63 @@ public class WifiNanManager {
        }
    }

    /**
     * {@hide}
     */
    public void startRanging(int sessionId, RttManager.RttParams[] params,
                             RttManager.RttListener listener) {
        if (VDBG) {
            Log.v(TAG, "startRanging: sessionId=" + sessionId + ", " + "params="
                    + Arrays.toString(params) + ", listener=" + listener);
        }

        int clientId;
        synchronized (mLock) {
            if (mClientId == INVALID_CLIENT_ID) {
                Log.e(TAG, "startRanging(): called with invalid client ID - not connected first?");
                return;
            }

            clientId = mClientId;
        }

        int rangingKey = 0;
        try {
            rangingKey = mService.startRanging(clientId, sessionId,
                    new RttManager.ParcelableRttParams(params));
        } catch (RemoteException e) {
            e.rethrowAsRuntimeException();
        }

        synchronized (mLock) {
            mRangingListeners.put(rangingKey, listener);
        }
    }

    private static class WifiNanEventCallbackProxy extends IWifiNanEventCallback.Stub {
        private static final int CALLBACK_CONNECT_SUCCESS = 0;
        private static final int CALLBACK_CONNECT_FAIL = 1;
        private static final int CALLBACK_IDENTITY_CHANGED = 2;
        private static final int CALLBACK_RANGING_SUCCESS = 3;
        private static final int CALLBACK_RANGING_FAILURE = 4;
        private static final int CALLBACK_RANGING_ABORTED = 5;

        private final Handler mHandler;
        private final WeakReference<WifiNanManager> mNanManager;

        RttManager.RttListener getAndRemoveRangingListener(int rangingId) {
            WifiNanManager mgr = mNanManager.get();
            if (mgr == null) {
                Log.w(TAG, "getAndRemoveRangingListener: called post GC");
                return null;
            }

            synchronized (mgr.mLock) {
                RttManager.RttListener listener = mgr.mRangingListeners.get(rangingId);
                mgr.mRangingListeners.delete(rangingId);
                return listener;
            }
        }

        /**
         * Constructs a {@link WifiNanEventCallback} using the specified looper.
@@ -430,7 +488,7 @@ public class WifiNanManager {
         */
        WifiNanEventCallbackProxy(WifiNanManager mgr, Looper looper,
                final WifiNanEventCallback originalCallback) {
            final WeakReference<WifiNanManager> nanManager = new WeakReference<WifiNanManager>(mgr);
            mNanManager = new WeakReference<>(mgr);

            if (VDBG) Log.v(TAG, "WifiNanEventCallbackProxy ctor: looper=" + looper);
            mHandler = new Handler(looper) {
@@ -440,7 +498,7 @@ public class WifiNanManager {
                        Log.d(TAG, "WifiNanEventCallbackProxy: What=" + msg.what + ", msg=" + msg);
                    }

                    WifiNanManager mgr = nanManager.get();
                    WifiNanManager mgr = mNanManager.get();
                    if (mgr == null) {
                        Log.w(TAG, "WifiNanEventCallbackProxy: handleMessage post GC");
                        return;
@@ -455,12 +513,43 @@ public class WifiNanManager {
                                mgr.mLooper = null;
                                mgr.mClientId = INVALID_CLIENT_ID;
                            }
                            nanManager.clear();
                            mNanManager.clear();
                            originalCallback.onConnectFail(msg.arg1);
                            break;
                        case CALLBACK_IDENTITY_CHANGED:
                            originalCallback.onIdentityChanged();
                            break;
                        case CALLBACK_RANGING_SUCCESS: {
                            RttManager.RttListener listener = getAndRemoveRangingListener(msg.arg1);
                            if (listener == null) {
                                Log.e(TAG, "CALLBACK_RANGING_SUCCESS rangingId=" + msg.arg1
                                        + ": no listener registered (anymore)");
                            } else {
                                listener.onSuccess(
                                        ((RttManager.ParcelableRttResults) msg.obj).mResults);
                            }
                            break;
                        }
                        case CALLBACK_RANGING_FAILURE: {
                            RttManager.RttListener listener = getAndRemoveRangingListener(msg.arg1);
                            if (listener == null) {
                                Log.e(TAG, "CALLBACK_RANGING_SUCCESS rangingId=" + msg.arg1
                                        + ": no listener registered (anymore)");
                            } else {
                                listener.onFailure(msg.arg2, (String) msg.obj);
                            }
                            break;
                        }
                        case CALLBACK_RANGING_ABORTED: {
                            RttManager.RttListener listener = getAndRemoveRangingListener(msg.arg1);
                            if (listener == null) {
                                Log.e(TAG, "CALLBACK_RANGING_SUCCESS rangingId=" + msg.arg1
                                        + ": no listener registered (anymore)");
                            } else {
                                listener.onAborted();
                            }
                            break;
                        }
                    }
                }
            };
@@ -490,6 +579,43 @@ public class WifiNanManager {
            Message msg = mHandler.obtainMessage(CALLBACK_IDENTITY_CHANGED);
            mHandler.sendMessage(msg);
        }

        @Override
        public void onRangingSuccess(int rangingId, RttManager.ParcelableRttResults results) {
            if (VDBG) {
                Log.v(TAG, "onRangingSuccess: rangingId=" + rangingId + ", results=" + results);
            }

            Message msg = mHandler.obtainMessage(CALLBACK_RANGING_SUCCESS);
            msg.arg1 = rangingId;
            msg.obj = results;
            mHandler.sendMessage(msg);
        }

        @Override
        public void onRangingFailure(int rangingId, int reason, String description) {
            if (VDBG) {
                Log.v(TAG, "onRangingSuccess: rangingId=" + rangingId + ", reason=" + reason
                        + ", description=" + description);
            }

            Message msg = mHandler.obtainMessage(CALLBACK_RANGING_FAILURE);
            msg.arg1 = rangingId;
            msg.arg2 = reason;
            msg.obj = description;
            mHandler.sendMessage(msg);

        }

        @Override
        public void onRangingAborted(int rangingId) {
            if (VDBG) Log.v(TAG, "onRangingAborted: rangingId=" + rangingId);

            Message msg = mHandler.obtainMessage(CALLBACK_RANGING_ABORTED);
            msg.arg1 = rangingId;
            mHandler.sendMessage(msg);

        }
    }

    private static class WifiNanSessionCallbackProxy extends IWifiNanSessionCallback.Stub {
Loading