Loading voip/java/com/android/server/sip/SipService.java +53 −12 Original line number Original line Diff line number Diff line Loading @@ -462,17 +462,30 @@ public final class SipService extends ISipService.Stub { private void startPortMappingLifetimeMeasurement( private void startPortMappingLifetimeMeasurement( SipProfile localProfile) { SipProfile localProfile) { startPortMappingLifetimeMeasurement(localProfile, -1); } private void startPortMappingLifetimeMeasurement( SipProfile localProfile, int maxInterval) { if ((mIntervalMeasurementProcess == null) if ((mIntervalMeasurementProcess == null) && (mKeepAliveInterval == -1) && (mKeepAliveInterval == -1) && isBehindNAT(mLocalIp)) { && isBehindNAT(mLocalIp)) { Log.d(TAG, "start NAT port mapping timeout measurement on " Log.d(TAG, "start NAT port mapping timeout measurement on " + localProfile.getUriString()); + localProfile.getUriString()); mIntervalMeasurementProcess = new IntervalMeasurementProcess(localProfile); mIntervalMeasurementProcess = new IntervalMeasurementProcess(localProfile, maxInterval); mIntervalMeasurementProcess.start(); mIntervalMeasurementProcess.start(); } } } } private void restartPortMappingLifetimeMeasurement( SipProfile localProfile, int maxInterval) { stopPortMappingMeasurement(); mKeepAliveInterval = -1; startPortMappingLifetimeMeasurement(localProfile, maxInterval); } private synchronized void addPendingSession(ISipSession session) { private synchronized void addPendingSession(ISipSession session) { try { try { cleanUpPendingSessions(); cleanUpPendingSessions(); Loading Loading @@ -746,18 +759,30 @@ public final class SipService extends ISipService.Stub { private class IntervalMeasurementProcess implements private class IntervalMeasurementProcess implements SipSessionGroup.KeepAliveProcessCallback { SipSessionGroup.KeepAliveProcessCallback { private static final String TAG = "SipKeepAliveInterval"; private static final String TAG = "SipKeepAliveInterval"; private static final int MAX_INTERVAL = 120; // seconds private static final int MAX_INTERVAL = 120; // in seconds private static final int MIN_INTERVAL = SHORT_EXPIRY_TIME; private static final int MIN_INTERVAL = 10; // in seconds private static final int PASS_THRESHOLD = 10; private static final int PASS_THRESHOLD = 10; private static final int MAX_RETRY_COUNT = 5; private SipSessionGroupExt mGroup; private SipSessionGroupExt mGroup; private SipSessionGroup.SipSessionImpl mSession; private SipSessionGroup.SipSessionImpl mSession; private boolean mRunning; private boolean mRunning; private int mMinInterval = 10; // in seconds private int mMinInterval = 10; // in seconds private int mMaxInterval = MAX_INTERVAL; private int mMaxInterval; private int mInterval = MAX_INTERVAL / 2; private int mInterval; private int mPassCounter = 0; private int mPassCount = 0; private int mErrorCount = 0; public IntervalMeasurementProcess(SipProfile localProfile, int maxInterval) { mMaxInterval = (maxInterval < 0) ? MAX_INTERVAL : maxInterval; mInterval = (mMaxInterval + mMinInterval) / 2; // Don't start measurement if the interval is too small if (mInterval < MIN_INTERVAL) { Log.w(TAG, "interval is too small; measurement aborted; " + "maxInterval=" + mMaxInterval); return; } public IntervalMeasurementProcess(SipProfile localProfile) { try { try { mGroup = new SipSessionGroupExt(localProfile, null, null); mGroup = new SipSessionGroupExt(localProfile, null, null); // TODO: remove this line once SipWakeupTimer can better handle // TODO: remove this line once SipWakeupTimer can better handle Loading Loading @@ -801,8 +826,10 @@ public final class SipService extends ISipService.Stub { @Override @Override public void onResponse(boolean portChanged) { public void onResponse(boolean portChanged) { synchronized (SipService.this) { synchronized (SipService.this) { mErrorCount = 0; if (!portChanged) { if (!portChanged) { if (++mPassCounter != PASS_THRESHOLD) return; if (++mPassCount != PASS_THRESHOLD) return; // update the interval, since the current interval is good to // update the interval, since the current interval is good to // keep the port mapping. // keep the port mapping. mKeepAliveInterval = mMinInterval = mInterval; mKeepAliveInterval = mMinInterval = mInterval; Loading @@ -826,7 +853,7 @@ public final class SipService extends ISipService.Stub { } else { } else { // calculate the new interval and continue. // calculate the new interval and continue. mInterval = (mMaxInterval + mMinInterval) / 2; mInterval = (mMaxInterval + mMinInterval) / 2; mPassCounter = 0; mPassCount = 0; if (DEBUG) { if (DEBUG) { Log.d(TAG, "current interval: " + mKeepAliveInterval Log.d(TAG, "current interval: " + mKeepAliveInterval + ", test new interval: " + mInterval); + ", test new interval: " + mInterval); Loading @@ -841,6 +868,13 @@ public final class SipService extends ISipService.Stub { public void onError(int errorCode, String description) { public void onError(int errorCode, String description) { synchronized (SipService.this) { synchronized (SipService.this) { Log.w(TAG, "interval measurement error: " + description); Log.w(TAG, "interval measurement error: " + description); if (++mErrorCount < MAX_RETRY_COUNT) { Log.w(TAG, " retry count = " + mErrorCount); mPassCount = 0; restart(); } else { Log.w(TAG, " max retry count reached; measurement aborted"); } } } } } } } Loading Loading @@ -885,9 +919,15 @@ public final class SipService extends ISipService.Stub { @Override @Override public void onResponse(boolean portChanged) { public void onResponse(boolean portChanged) { synchronized (SipService.this) { synchronized (SipService.this) { // Start keep-alive interval measurement on the first successfully if (portChanged) { // kept-alive SipSessionGroup restartPortMappingLifetimeMeasurement( startPortMappingLifetimeMeasurement(mSession.getLocalProfile()); mSession.getLocalProfile(), getKeepAliveInterval()); } else { // Start keep-alive interval measurement on the first // successfully kept-alive SipSessionGroup startPortMappingLifetimeMeasurement( mSession.getLocalProfile()); } if (!mRunning || !portChanged) return; if (!mRunning || !portChanged) return; Loading @@ -907,6 +947,7 @@ public final class SipService extends ISipService.Stub { @Override @Override public void onError(int errorCode, String description) { public void onError(int errorCode, String description) { Log.e(TAG, "keepalive error: " + description); Log.e(TAG, "keepalive error: " + description); onResponse(true); // re-register immediately } } public void stop() { public void stop() { Loading voip/java/com/android/server/sip/SipSessionGroup.java +3 −1 Original line number Original line Diff line number Diff line Loading @@ -1259,11 +1259,13 @@ class SipSessionGroup implements SipListener { private boolean mPortChanged = false; private boolean mPortChanged = false; private int mRPort = 0; private int mRPort = 0; private int mInterval; // just for debugging // @param interval in seconds // @param interval in seconds void start(int interval, KeepAliveProcessCallback callback) { void start(int interval, KeepAliveProcessCallback callback) { if (mRunning) return; if (mRunning) return; mRunning = true; mRunning = true; mInterval = interval; mCallback = new KeepAliveProcessCallbackProxy(callback); mCallback = new KeepAliveProcessCallbackProxy(callback); mWakeupTimer.set(interval * 1000, this); mWakeupTimer.set(interval * 1000, this); if (DEBUG) { if (DEBUG) { Loading Loading @@ -1311,7 +1313,7 @@ class SipSessionGroup implements SipListener { if (DEBUG_PING) { if (DEBUG_PING) { Log.d(TAG, "keepalive: " + mLocalProfile.getUriString() Log.d(TAG, "keepalive: " + mLocalProfile.getUriString() + " --> " + mPeerProfile); + " --> " + mPeerProfile + ", interval=" + mInterval); } } try { try { sendKeepAlive(); sendKeepAlive(); Loading Loading
voip/java/com/android/server/sip/SipService.java +53 −12 Original line number Original line Diff line number Diff line Loading @@ -462,17 +462,30 @@ public final class SipService extends ISipService.Stub { private void startPortMappingLifetimeMeasurement( private void startPortMappingLifetimeMeasurement( SipProfile localProfile) { SipProfile localProfile) { startPortMappingLifetimeMeasurement(localProfile, -1); } private void startPortMappingLifetimeMeasurement( SipProfile localProfile, int maxInterval) { if ((mIntervalMeasurementProcess == null) if ((mIntervalMeasurementProcess == null) && (mKeepAliveInterval == -1) && (mKeepAliveInterval == -1) && isBehindNAT(mLocalIp)) { && isBehindNAT(mLocalIp)) { Log.d(TAG, "start NAT port mapping timeout measurement on " Log.d(TAG, "start NAT port mapping timeout measurement on " + localProfile.getUriString()); + localProfile.getUriString()); mIntervalMeasurementProcess = new IntervalMeasurementProcess(localProfile); mIntervalMeasurementProcess = new IntervalMeasurementProcess(localProfile, maxInterval); mIntervalMeasurementProcess.start(); mIntervalMeasurementProcess.start(); } } } } private void restartPortMappingLifetimeMeasurement( SipProfile localProfile, int maxInterval) { stopPortMappingMeasurement(); mKeepAliveInterval = -1; startPortMappingLifetimeMeasurement(localProfile, maxInterval); } private synchronized void addPendingSession(ISipSession session) { private synchronized void addPendingSession(ISipSession session) { try { try { cleanUpPendingSessions(); cleanUpPendingSessions(); Loading Loading @@ -746,18 +759,30 @@ public final class SipService extends ISipService.Stub { private class IntervalMeasurementProcess implements private class IntervalMeasurementProcess implements SipSessionGroup.KeepAliveProcessCallback { SipSessionGroup.KeepAliveProcessCallback { private static final String TAG = "SipKeepAliveInterval"; private static final String TAG = "SipKeepAliveInterval"; private static final int MAX_INTERVAL = 120; // seconds private static final int MAX_INTERVAL = 120; // in seconds private static final int MIN_INTERVAL = SHORT_EXPIRY_TIME; private static final int MIN_INTERVAL = 10; // in seconds private static final int PASS_THRESHOLD = 10; private static final int PASS_THRESHOLD = 10; private static final int MAX_RETRY_COUNT = 5; private SipSessionGroupExt mGroup; private SipSessionGroupExt mGroup; private SipSessionGroup.SipSessionImpl mSession; private SipSessionGroup.SipSessionImpl mSession; private boolean mRunning; private boolean mRunning; private int mMinInterval = 10; // in seconds private int mMinInterval = 10; // in seconds private int mMaxInterval = MAX_INTERVAL; private int mMaxInterval; private int mInterval = MAX_INTERVAL / 2; private int mInterval; private int mPassCounter = 0; private int mPassCount = 0; private int mErrorCount = 0; public IntervalMeasurementProcess(SipProfile localProfile, int maxInterval) { mMaxInterval = (maxInterval < 0) ? MAX_INTERVAL : maxInterval; mInterval = (mMaxInterval + mMinInterval) / 2; // Don't start measurement if the interval is too small if (mInterval < MIN_INTERVAL) { Log.w(TAG, "interval is too small; measurement aborted; " + "maxInterval=" + mMaxInterval); return; } public IntervalMeasurementProcess(SipProfile localProfile) { try { try { mGroup = new SipSessionGroupExt(localProfile, null, null); mGroup = new SipSessionGroupExt(localProfile, null, null); // TODO: remove this line once SipWakeupTimer can better handle // TODO: remove this line once SipWakeupTimer can better handle Loading Loading @@ -801,8 +826,10 @@ public final class SipService extends ISipService.Stub { @Override @Override public void onResponse(boolean portChanged) { public void onResponse(boolean portChanged) { synchronized (SipService.this) { synchronized (SipService.this) { mErrorCount = 0; if (!portChanged) { if (!portChanged) { if (++mPassCounter != PASS_THRESHOLD) return; if (++mPassCount != PASS_THRESHOLD) return; // update the interval, since the current interval is good to // update the interval, since the current interval is good to // keep the port mapping. // keep the port mapping. mKeepAliveInterval = mMinInterval = mInterval; mKeepAliveInterval = mMinInterval = mInterval; Loading @@ -826,7 +853,7 @@ public final class SipService extends ISipService.Stub { } else { } else { // calculate the new interval and continue. // calculate the new interval and continue. mInterval = (mMaxInterval + mMinInterval) / 2; mInterval = (mMaxInterval + mMinInterval) / 2; mPassCounter = 0; mPassCount = 0; if (DEBUG) { if (DEBUG) { Log.d(TAG, "current interval: " + mKeepAliveInterval Log.d(TAG, "current interval: " + mKeepAliveInterval + ", test new interval: " + mInterval); + ", test new interval: " + mInterval); Loading @@ -841,6 +868,13 @@ public final class SipService extends ISipService.Stub { public void onError(int errorCode, String description) { public void onError(int errorCode, String description) { synchronized (SipService.this) { synchronized (SipService.this) { Log.w(TAG, "interval measurement error: " + description); Log.w(TAG, "interval measurement error: " + description); if (++mErrorCount < MAX_RETRY_COUNT) { Log.w(TAG, " retry count = " + mErrorCount); mPassCount = 0; restart(); } else { Log.w(TAG, " max retry count reached; measurement aborted"); } } } } } } } Loading Loading @@ -885,9 +919,15 @@ public final class SipService extends ISipService.Stub { @Override @Override public void onResponse(boolean portChanged) { public void onResponse(boolean portChanged) { synchronized (SipService.this) { synchronized (SipService.this) { // Start keep-alive interval measurement on the first successfully if (portChanged) { // kept-alive SipSessionGroup restartPortMappingLifetimeMeasurement( startPortMappingLifetimeMeasurement(mSession.getLocalProfile()); mSession.getLocalProfile(), getKeepAliveInterval()); } else { // Start keep-alive interval measurement on the first // successfully kept-alive SipSessionGroup startPortMappingLifetimeMeasurement( mSession.getLocalProfile()); } if (!mRunning || !portChanged) return; if (!mRunning || !portChanged) return; Loading @@ -907,6 +947,7 @@ public final class SipService extends ISipService.Stub { @Override @Override public void onError(int errorCode, String description) { public void onError(int errorCode, String description) { Log.e(TAG, "keepalive error: " + description); Log.e(TAG, "keepalive error: " + description); onResponse(true); // re-register immediately } } public void stop() { public void stop() { Loading
voip/java/com/android/server/sip/SipSessionGroup.java +3 −1 Original line number Original line Diff line number Diff line Loading @@ -1259,11 +1259,13 @@ class SipSessionGroup implements SipListener { private boolean mPortChanged = false; private boolean mPortChanged = false; private int mRPort = 0; private int mRPort = 0; private int mInterval; // just for debugging // @param interval in seconds // @param interval in seconds void start(int interval, KeepAliveProcessCallback callback) { void start(int interval, KeepAliveProcessCallback callback) { if (mRunning) return; if (mRunning) return; mRunning = true; mRunning = true; mInterval = interval; mCallback = new KeepAliveProcessCallbackProxy(callback); mCallback = new KeepAliveProcessCallbackProxy(callback); mWakeupTimer.set(interval * 1000, this); mWakeupTimer.set(interval * 1000, this); if (DEBUG) { if (DEBUG) { Loading Loading @@ -1311,7 +1313,7 @@ class SipSessionGroup implements SipListener { if (DEBUG_PING) { if (DEBUG_PING) { Log.d(TAG, "keepalive: " + mLocalProfile.getUriString() Log.d(TAG, "keepalive: " + mLocalProfile.getUriString() + " --> " + mPeerProfile); + " --> " + mPeerProfile + ", interval=" + mInterval); } } try { try { sendKeepAlive(); sendKeepAlive(); Loading