Loading core/java/android/provider/CallLog.java +51 −44 Original line number Diff line number Diff line Loading @@ -772,19 +772,6 @@ public class CallLog { * @param callBlockReason The reason why the call is blocked. * @param callScreeningAppName The call screening application name which block the call. * @param callScreeningComponentName The call screening component name which block the call. * @param callIdPackageName The package name of the * {@link android.telecom.CallScreeningService} which provided * {@link CallIdentification}. * @param callIdAppName The app name of the {@link android.telecom.CallScreeningService} * which provided {@link CallIdentification}. * @param callIdName The caller name provided by the * {@link android.telecom.CallScreeningService}. * @param callIdDescription The caller description provided by the * {@link android.telecom.CallScreeningService}. * @param callIdDetails The caller details provided by the * {@link android.telecom.CallScreeningService}. * @param callIdCallType The caller type provided by the * {@link android.telecom.CallScreeningService}. * * @result The URI of the call log entry belonging to the user that made or received this * call. This could be of the shadow provider. Do not return it to non-system apps, Loading @@ -803,37 +790,10 @@ public class CallLog { number, userToBeInsertedTo, addForAllUsers)); } final ContentResolver resolver = context.getContentResolver(); int numberPresentation = PRESENTATION_ALLOWED; TelecomManager tm = null; try { tm = TelecomManager.from(context); } catch (UnsupportedOperationException e) {} String accountAddress = null; if (tm != null && accountHandle != null) { PhoneAccount account = tm.getPhoneAccount(accountHandle); if (account != null) { Uri address = account.getSubscriptionAddress(); if (address != null) { accountAddress = address.getSchemeSpecificPart(); } } } String accountAddress = getLogAccountAddress(context, accountHandle); // Remap network specified number presentation types // PhoneConstants.PRESENTATION_xxx to calllog number presentation types // Calls.PRESENTATION_xxx, in order to insulate the persistent calllog // from any future radio changes. // If the number field is empty set the presentation type to Unknown. if (presentation == PhoneConstants.PRESENTATION_RESTRICTED) { numberPresentation = PRESENTATION_RESTRICTED; } else if (presentation == PhoneConstants.PRESENTATION_PAYPHONE) { numberPresentation = PRESENTATION_PAYPHONE; } else if (TextUtils.isEmpty(number) || presentation == PhoneConstants.PRESENTATION_UNKNOWN) { numberPresentation = PRESENTATION_UNKNOWN; } int numberPresentation = getLogNumberPresentation(number, presentation); if (numberPresentation != PRESENTATION_ALLOWED) { number = ""; if (ci != null) { Loading Loading @@ -1138,8 +1098,7 @@ public class CallLog { if (TextUtils.isEmpty(countryIso)) { return; } final String normalizedNumber = PhoneNumberUtils.formatNumberToE164(number, getCurrentCountryIso(context)); final String normalizedNumber = PhoneNumberUtils.formatNumberToE164(number, countryIso); if (TextUtils.isEmpty(normalizedNumber)) { return; } Loading @@ -1148,6 +1107,54 @@ public class CallLog { resolver.update(Data.CONTENT_URI, values, Data._ID + "=?", new String[] {dataId}); } /** * Remap network specified number presentation types * PhoneConstants.PRESENTATION_xxx to calllog number presentation types * Calls.PRESENTATION_xxx, in order to insulate the persistent calllog * from any future radio changes. * If the number field is empty set the presentation type to Unknown. */ private static int getLogNumberPresentation(String number, int presentation) { if (presentation == PhoneConstants.PRESENTATION_RESTRICTED) { return presentation; } if (presentation == PhoneConstants.PRESENTATION_PAYPHONE) { return presentation; } if (TextUtils.isEmpty(number) || presentation == PhoneConstants.PRESENTATION_UNKNOWN) { return PRESENTATION_UNKNOWN; } return PRESENTATION_ALLOWED; } private static String getLogAccountAddress(Context context, PhoneAccountHandle accountHandle) { TelecomManager tm = null; try { tm = TelecomManager.from(context); } catch (UnsupportedOperationException e) { if (VERBOSE_LOG) { Log.v(LOG_TAG, "No TelecomManager found to get account address."); } } String accountAddress = null; if (tm != null && accountHandle != null) { PhoneAccount account = tm.getPhoneAccount(accountHandle); if (account != null) { Uri address = account.getSubscriptionAddress(); if (address != null) { accountAddress = address.getSchemeSpecificPart(); } } } return accountAddress; } private static String getCurrentCountryIso(Context context) { String countryIso = null; final CountryDetector detector = (CountryDetector) context.getSystemService( Loading telecomm/java/android/telecom/ConferenceParticipant.java +93 −0 Original line number Diff line number Diff line Loading @@ -19,6 +19,10 @@ package android.telecom; import android.net.Uri; import android.os.Parcel; import android.os.Parcelable; import android.text.TextUtils; import com.android.internal.annotations.VisibleForTesting; import com.android.internal.telephony.PhoneConstants; /** * Parcelable representation of a participant's state in a conference call. Loading @@ -26,6 +30,11 @@ import android.os.Parcelable; */ public class ConferenceParticipant implements Parcelable { /** * RFC5767 states that a SIP URI with an unknown number should use an address of * {@code anonymous@anonymous.invalid}. E.g. the host name is anonymous.invalid. */ private static final String ANONYMOUS_INVALID_HOST = "anonymous.invalid"; /** * The conference participant's handle (e.g., phone number). */ Loading @@ -49,6 +58,16 @@ public class ConferenceParticipant implements Parcelable { */ private final int mState; /** * The connect time of the participant. */ private long mConnectTime; /** * The connect elapsed time of the participant. */ private long mConnectElapsedTime; /** * Creates an instance of {@code ConferenceParticipant}. * Loading Loading @@ -91,6 +110,54 @@ public class ConferenceParticipant implements Parcelable { return 0; } /** * Determines the number presentation for a conference participant. Per RFC5767, if the host * name contains {@code anonymous.invalid} we can assume that there is no valid caller ID * information for the caller, otherwise we'll assume that the URI can be shown. * * @return The number presentation. */ @VisibleForTesting public int getParticipantPresentation() { Uri address = getHandle(); if (address == null) { return PhoneConstants.PRESENTATION_RESTRICTED; } String number = address.getSchemeSpecificPart(); // If no number, bail early and set restricted presentation. if (TextUtils.isEmpty(number)) { return PhoneConstants.PRESENTATION_RESTRICTED; } // Per RFC3261, the host name portion can also potentially include extra information: // E.g. sip:anonymous1@anonymous.invalid;legid=1 // In this case, hostName will be anonymous.invalid and there is an extra parameter for // legid=1. // Parameters are optional, and the address (e.g. test@test.com) will always be the first // part, with any parameters coming afterwards. String [] hostParts = number.split("[;]"); String addressPart = hostParts[0]; // Get the number portion from the address part. // This will typically be formatted similar to: 6505551212@test.com String [] numberParts = addressPart.split("[@]"); // If we can't parse the host name out of the URI, then there is probably other data // present, and is likely a valid SIP URI. if (numberParts.length != 2) { return PhoneConstants.PRESENTATION_ALLOWED; } String hostName = numberParts[1]; // If the hostname portion of the SIP URI is the invalid host string, presentation is // restricted. if (hostName.equals(ANONYMOUS_INVALID_HOST)) { return PhoneConstants.PRESENTATION_RESTRICTED; } return PhoneConstants.PRESENTATION_ALLOWED; } /** * Writes the {@code ConferenceParticipant} to a parcel. * Loading Loading @@ -121,6 +188,10 @@ public class ConferenceParticipant implements Parcelable { sb.append(Log.pii(mEndpoint)); sb.append(" State: "); sb.append(Connection.stateToString(mState)); sb.append(" ConnectTime: "); sb.append(getConnectTime()); sb.append(" ConnectElapsedTime: "); sb.append(getConnectElapsedTime()); sb.append("]"); return sb.toString(); } Loading Loading @@ -155,4 +226,26 @@ public class ConferenceParticipant implements Parcelable { public int getState() { return mState; } /** * The connect time of the participant to the conference. */ public long getConnectTime() { return mConnectTime; } public void setConnectTime(long connectTime) { this.mConnectTime = connectTime; } /** * The connect elpased time of the participant to the conference. */ public long getConnectElapsedTime() { return mConnectElapsedTime; } public void setConnectElapsedTime(long connectElapsedTime) { mConnectElapsedTime = connectElapsedTime; } } telecomm/java/android/telecom/Connection.java +4 −4 Original line number Diff line number Diff line Loading @@ -16,10 +16,6 @@ package android.telecom; import com.android.internal.os.SomeArgs; import com.android.internal.telecom.IVideoCallback; import com.android.internal.telecom.IVideoProvider; import android.annotation.NonNull; import android.annotation.Nullable; import android.annotation.SystemApi; Loading @@ -43,6 +39,10 @@ import android.telephony.TelephonyManager; import android.util.ArraySet; import android.view.Surface; import com.android.internal.os.SomeArgs; import com.android.internal.telecom.IVideoCallback; import com.android.internal.telecom.IVideoProvider; import java.io.FileInputStream; import java.io.FileOutputStream; import java.io.IOException; Loading telecomm/java/android/telecom/DisconnectCause.java +7 −1 Original line number Diff line number Diff line Loading @@ -16,9 +16,9 @@ package android.telecom; import android.media.ToneGenerator; import android.os.Parcel; import android.os.Parcelable; import android.media.ToneGenerator; import android.text.TextUtils; import java.util.Objects; Loading Loading @@ -91,6 +91,12 @@ public final class DisconnectCause implements Parcelable { */ public static final String REASON_IMS_ACCESS_BLOCKED = "REASON_IMS_ACCESS_BLOCKED"; /** * Reason code, which indicates that the conference call is simulating single party conference. * @hide */ public static final String REASON_EMULATING_SINGLE_CALL = "EMULATING_SINGLE_CALL"; private int mDisconnectCode; private CharSequence mDisconnectLabel; private CharSequence mDisconnectDescription; Loading Loading
core/java/android/provider/CallLog.java +51 −44 Original line number Diff line number Diff line Loading @@ -772,19 +772,6 @@ public class CallLog { * @param callBlockReason The reason why the call is blocked. * @param callScreeningAppName The call screening application name which block the call. * @param callScreeningComponentName The call screening component name which block the call. * @param callIdPackageName The package name of the * {@link android.telecom.CallScreeningService} which provided * {@link CallIdentification}. * @param callIdAppName The app name of the {@link android.telecom.CallScreeningService} * which provided {@link CallIdentification}. * @param callIdName The caller name provided by the * {@link android.telecom.CallScreeningService}. * @param callIdDescription The caller description provided by the * {@link android.telecom.CallScreeningService}. * @param callIdDetails The caller details provided by the * {@link android.telecom.CallScreeningService}. * @param callIdCallType The caller type provided by the * {@link android.telecom.CallScreeningService}. * * @result The URI of the call log entry belonging to the user that made or received this * call. This could be of the shadow provider. Do not return it to non-system apps, Loading @@ -803,37 +790,10 @@ public class CallLog { number, userToBeInsertedTo, addForAllUsers)); } final ContentResolver resolver = context.getContentResolver(); int numberPresentation = PRESENTATION_ALLOWED; TelecomManager tm = null; try { tm = TelecomManager.from(context); } catch (UnsupportedOperationException e) {} String accountAddress = null; if (tm != null && accountHandle != null) { PhoneAccount account = tm.getPhoneAccount(accountHandle); if (account != null) { Uri address = account.getSubscriptionAddress(); if (address != null) { accountAddress = address.getSchemeSpecificPart(); } } } String accountAddress = getLogAccountAddress(context, accountHandle); // Remap network specified number presentation types // PhoneConstants.PRESENTATION_xxx to calllog number presentation types // Calls.PRESENTATION_xxx, in order to insulate the persistent calllog // from any future radio changes. // If the number field is empty set the presentation type to Unknown. if (presentation == PhoneConstants.PRESENTATION_RESTRICTED) { numberPresentation = PRESENTATION_RESTRICTED; } else if (presentation == PhoneConstants.PRESENTATION_PAYPHONE) { numberPresentation = PRESENTATION_PAYPHONE; } else if (TextUtils.isEmpty(number) || presentation == PhoneConstants.PRESENTATION_UNKNOWN) { numberPresentation = PRESENTATION_UNKNOWN; } int numberPresentation = getLogNumberPresentation(number, presentation); if (numberPresentation != PRESENTATION_ALLOWED) { number = ""; if (ci != null) { Loading Loading @@ -1138,8 +1098,7 @@ public class CallLog { if (TextUtils.isEmpty(countryIso)) { return; } final String normalizedNumber = PhoneNumberUtils.formatNumberToE164(number, getCurrentCountryIso(context)); final String normalizedNumber = PhoneNumberUtils.formatNumberToE164(number, countryIso); if (TextUtils.isEmpty(normalizedNumber)) { return; } Loading @@ -1148,6 +1107,54 @@ public class CallLog { resolver.update(Data.CONTENT_URI, values, Data._ID + "=?", new String[] {dataId}); } /** * Remap network specified number presentation types * PhoneConstants.PRESENTATION_xxx to calllog number presentation types * Calls.PRESENTATION_xxx, in order to insulate the persistent calllog * from any future radio changes. * If the number field is empty set the presentation type to Unknown. */ private static int getLogNumberPresentation(String number, int presentation) { if (presentation == PhoneConstants.PRESENTATION_RESTRICTED) { return presentation; } if (presentation == PhoneConstants.PRESENTATION_PAYPHONE) { return presentation; } if (TextUtils.isEmpty(number) || presentation == PhoneConstants.PRESENTATION_UNKNOWN) { return PRESENTATION_UNKNOWN; } return PRESENTATION_ALLOWED; } private static String getLogAccountAddress(Context context, PhoneAccountHandle accountHandle) { TelecomManager tm = null; try { tm = TelecomManager.from(context); } catch (UnsupportedOperationException e) { if (VERBOSE_LOG) { Log.v(LOG_TAG, "No TelecomManager found to get account address."); } } String accountAddress = null; if (tm != null && accountHandle != null) { PhoneAccount account = tm.getPhoneAccount(accountHandle); if (account != null) { Uri address = account.getSubscriptionAddress(); if (address != null) { accountAddress = address.getSchemeSpecificPart(); } } } return accountAddress; } private static String getCurrentCountryIso(Context context) { String countryIso = null; final CountryDetector detector = (CountryDetector) context.getSystemService( Loading
telecomm/java/android/telecom/ConferenceParticipant.java +93 −0 Original line number Diff line number Diff line Loading @@ -19,6 +19,10 @@ package android.telecom; import android.net.Uri; import android.os.Parcel; import android.os.Parcelable; import android.text.TextUtils; import com.android.internal.annotations.VisibleForTesting; import com.android.internal.telephony.PhoneConstants; /** * Parcelable representation of a participant's state in a conference call. Loading @@ -26,6 +30,11 @@ import android.os.Parcelable; */ public class ConferenceParticipant implements Parcelable { /** * RFC5767 states that a SIP URI with an unknown number should use an address of * {@code anonymous@anonymous.invalid}. E.g. the host name is anonymous.invalid. */ private static final String ANONYMOUS_INVALID_HOST = "anonymous.invalid"; /** * The conference participant's handle (e.g., phone number). */ Loading @@ -49,6 +58,16 @@ public class ConferenceParticipant implements Parcelable { */ private final int mState; /** * The connect time of the participant. */ private long mConnectTime; /** * The connect elapsed time of the participant. */ private long mConnectElapsedTime; /** * Creates an instance of {@code ConferenceParticipant}. * Loading Loading @@ -91,6 +110,54 @@ public class ConferenceParticipant implements Parcelable { return 0; } /** * Determines the number presentation for a conference participant. Per RFC5767, if the host * name contains {@code anonymous.invalid} we can assume that there is no valid caller ID * information for the caller, otherwise we'll assume that the URI can be shown. * * @return The number presentation. */ @VisibleForTesting public int getParticipantPresentation() { Uri address = getHandle(); if (address == null) { return PhoneConstants.PRESENTATION_RESTRICTED; } String number = address.getSchemeSpecificPart(); // If no number, bail early and set restricted presentation. if (TextUtils.isEmpty(number)) { return PhoneConstants.PRESENTATION_RESTRICTED; } // Per RFC3261, the host name portion can also potentially include extra information: // E.g. sip:anonymous1@anonymous.invalid;legid=1 // In this case, hostName will be anonymous.invalid and there is an extra parameter for // legid=1. // Parameters are optional, and the address (e.g. test@test.com) will always be the first // part, with any parameters coming afterwards. String [] hostParts = number.split("[;]"); String addressPart = hostParts[0]; // Get the number portion from the address part. // This will typically be formatted similar to: 6505551212@test.com String [] numberParts = addressPart.split("[@]"); // If we can't parse the host name out of the URI, then there is probably other data // present, and is likely a valid SIP URI. if (numberParts.length != 2) { return PhoneConstants.PRESENTATION_ALLOWED; } String hostName = numberParts[1]; // If the hostname portion of the SIP URI is the invalid host string, presentation is // restricted. if (hostName.equals(ANONYMOUS_INVALID_HOST)) { return PhoneConstants.PRESENTATION_RESTRICTED; } return PhoneConstants.PRESENTATION_ALLOWED; } /** * Writes the {@code ConferenceParticipant} to a parcel. * Loading Loading @@ -121,6 +188,10 @@ public class ConferenceParticipant implements Parcelable { sb.append(Log.pii(mEndpoint)); sb.append(" State: "); sb.append(Connection.stateToString(mState)); sb.append(" ConnectTime: "); sb.append(getConnectTime()); sb.append(" ConnectElapsedTime: "); sb.append(getConnectElapsedTime()); sb.append("]"); return sb.toString(); } Loading Loading @@ -155,4 +226,26 @@ public class ConferenceParticipant implements Parcelable { public int getState() { return mState; } /** * The connect time of the participant to the conference. */ public long getConnectTime() { return mConnectTime; } public void setConnectTime(long connectTime) { this.mConnectTime = connectTime; } /** * The connect elpased time of the participant to the conference. */ public long getConnectElapsedTime() { return mConnectElapsedTime; } public void setConnectElapsedTime(long connectElapsedTime) { mConnectElapsedTime = connectElapsedTime; } }
telecomm/java/android/telecom/Connection.java +4 −4 Original line number Diff line number Diff line Loading @@ -16,10 +16,6 @@ package android.telecom; import com.android.internal.os.SomeArgs; import com.android.internal.telecom.IVideoCallback; import com.android.internal.telecom.IVideoProvider; import android.annotation.NonNull; import android.annotation.Nullable; import android.annotation.SystemApi; Loading @@ -43,6 +39,10 @@ import android.telephony.TelephonyManager; import android.util.ArraySet; import android.view.Surface; import com.android.internal.os.SomeArgs; import com.android.internal.telecom.IVideoCallback; import com.android.internal.telecom.IVideoProvider; import java.io.FileInputStream; import java.io.FileOutputStream; import java.io.IOException; Loading
telecomm/java/android/telecom/DisconnectCause.java +7 −1 Original line number Diff line number Diff line Loading @@ -16,9 +16,9 @@ package android.telecom; import android.media.ToneGenerator; import android.os.Parcel; import android.os.Parcelable; import android.media.ToneGenerator; import android.text.TextUtils; import java.util.Objects; Loading Loading @@ -91,6 +91,12 @@ public final class DisconnectCause implements Parcelable { */ public static final String REASON_IMS_ACCESS_BLOCKED = "REASON_IMS_ACCESS_BLOCKED"; /** * Reason code, which indicates that the conference call is simulating single party conference. * @hide */ public static final String REASON_EMULATING_SINGLE_CALL = "EMULATING_SINGLE_CALL"; private int mDisconnectCode; private CharSequence mDisconnectLabel; private CharSequence mDisconnectDescription; Loading