1 /* 2 * Copyright (C) 2014 The Android Open Source Project 3 * 4 * Licensed under the Apache License, Version 2.0 (the "License"); 5 * you may not use this file except in compliance with the License. 6 * You may obtain a copy of the License at 7 * 8 * http://www.apache.org/licenses/LICENSE-2.0 9 * 10 * Unless required by applicable law or agreed to in writing, software 11 * distributed under the License is distributed on an "AS IS" BASIS, 12 * WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied. 13 * See the License for the specific language governing permissions and 14 * limitations under the License. 15 */ 16 17 package android.telephony; 18 19 import android.annotation.NonNull; 20 import android.annotation.Nullable; 21 import android.annotation.SystemApi; 22 import android.compat.annotation.UnsupportedAppUsage; 23 import android.os.Parcel; 24 import android.os.Parcelable; 25 import android.telephony.Annotation.DisconnectCauses; 26 import android.telephony.Annotation.PreciseCallStates; 27 import android.telephony.Annotation.PreciseDisconnectCauses; 28 29 import java.util.Objects; 30 31 /** 32 * Contains precise call states. 33 * 34 * The following call information is included in returned PreciseCallState: 35 * 36 * <ul> 37 * <li>Precise ringing call state. 38 * <li>Precise foreground call state. 39 * <li>Precise background call state. 40 * </ul> 41 * 42 * @see android.telephony.Annotation.CallState which contains generic call states. 43 * 44 * @hide 45 */ 46 @SystemApi 47 public final class PreciseCallState implements Parcelable { 48 49 /** Call state is not valid (Not received a call state). */ 50 public static final int PRECISE_CALL_STATE_NOT_VALID = -1; 51 /** Call state: No activity. */ 52 public static final int PRECISE_CALL_STATE_IDLE = 0; 53 /** Call state: Active. */ 54 public static final int PRECISE_CALL_STATE_ACTIVE = 1; 55 /** Call state: On hold. */ 56 public static final int PRECISE_CALL_STATE_HOLDING = 2; 57 /** Call state: Dialing. */ 58 public static final int PRECISE_CALL_STATE_DIALING = 3; 59 /** Call state: Alerting. */ 60 public static final int PRECISE_CALL_STATE_ALERTING = 4; 61 /** Call state: Incoming. */ 62 public static final int PRECISE_CALL_STATE_INCOMING = 5; 63 /** Call state: Waiting. */ 64 public static final int PRECISE_CALL_STATE_WAITING = 6; 65 /** Call state: Disconnected. */ 66 public static final int PRECISE_CALL_STATE_DISCONNECTED = 7; 67 /** Call state: Disconnecting. */ 68 public static final int PRECISE_CALL_STATE_DISCONNECTING = 8; 69 /** 70 * Call state: Incoming in pre-alerting state i.e. prior to entering 71 * {@link #PRECISE_CALL_STATE_INCOMING}. 72 */ 73 public static final int PRECISE_CALL_STATE_INCOMING_SETUP = 9; 74 75 private @PreciseCallStates int mRingingCallState = PRECISE_CALL_STATE_NOT_VALID; 76 private @PreciseCallStates int mForegroundCallState = PRECISE_CALL_STATE_NOT_VALID; 77 private @PreciseCallStates int mBackgroundCallState = PRECISE_CALL_STATE_NOT_VALID; 78 private @DisconnectCauses int mDisconnectCause = DisconnectCause.NOT_VALID; 79 private @PreciseDisconnectCauses int mPreciseDisconnectCause = PreciseDisconnectCause.NOT_VALID; 80 81 /** 82 * Construct PreciseCallState with parameters 83 * 84 * @param ringingCall ring call state 85 * @param foregroundCall foreground call state 86 * @param backgroundCall background call state 87 * @param disconnectCause disconnect cause 88 * @param preciseDisconnectCause precise disconnect cause 89 * 90 * @hide 91 */ 92 @SystemApi PreciseCallState(@reciseCallStates int ringingCall, @PreciseCallStates int foregroundCall, @PreciseCallStates int backgroundCall, @DisconnectCauses int disconnectCause, @PreciseDisconnectCauses int preciseDisconnectCause)93 public PreciseCallState(@PreciseCallStates int ringingCall, 94 @PreciseCallStates int foregroundCall, 95 @PreciseCallStates int backgroundCall, 96 @DisconnectCauses int disconnectCause, 97 @PreciseDisconnectCauses int preciseDisconnectCause) { 98 mRingingCallState = ringingCall; 99 mForegroundCallState = foregroundCall; 100 mBackgroundCallState = backgroundCall; 101 mDisconnectCause = disconnectCause; 102 mPreciseDisconnectCause = preciseDisconnectCause; 103 } 104 105 /** 106 * Empty Constructor 107 * 108 * @hide 109 */ PreciseCallState()110 public PreciseCallState() { 111 } 112 113 /** 114 * Construct a PreciseCallState object from the given parcel. 115 * 116 * @hide 117 */ PreciseCallState(Parcel in)118 private PreciseCallState(Parcel in) { 119 mRingingCallState = in.readInt(); 120 mForegroundCallState = in.readInt(); 121 mBackgroundCallState = in.readInt(); 122 mDisconnectCause = in.readInt(); 123 mPreciseDisconnectCause = in.readInt(); 124 } 125 126 /** 127 * Returns the precise ringing call state. 128 */ getRingingCallState()129 public @PreciseCallStates int getRingingCallState() { 130 return mRingingCallState; 131 } 132 133 /** 134 * Returns the precise foreground call state. 135 */ getForegroundCallState()136 public @PreciseCallStates int getForegroundCallState() { 137 return mForegroundCallState; 138 } 139 140 /** 141 * Returns the precise background call state. 142 */ getBackgroundCallState()143 public @PreciseCallStates int getBackgroundCallState() { 144 return mBackgroundCallState; 145 } 146 147 /** 148 * Get disconnect cause generated by the framework 149 * 150 * @see DisconnectCause#NOT_VALID 151 * @see DisconnectCause#NOT_DISCONNECTED 152 * @see DisconnectCause#INCOMING_MISSED 153 * @see DisconnectCause#NORMAL 154 * @see DisconnectCause#LOCAL 155 * @see DisconnectCause#BUSY 156 * @see DisconnectCause#CONGESTION 157 * @see DisconnectCause#MMI 158 * @see DisconnectCause#INVALID_NUMBER 159 * @see DisconnectCause#NUMBER_UNREACHABLE 160 * @see DisconnectCause#SERVER_UNREACHABLE 161 * @see DisconnectCause#INVALID_CREDENTIALS 162 * @see DisconnectCause#OUT_OF_NETWORK 163 * @see DisconnectCause#SERVER_ERROR 164 * @see DisconnectCause#TIMED_OUT 165 * @see DisconnectCause#LOST_SIGNAL 166 * @see DisconnectCause#LIMIT_EXCEEDED 167 * @see DisconnectCause#INCOMING_REJECTED 168 * @see DisconnectCause#POWER_OFF 169 * @see DisconnectCause#OUT_OF_SERVICE 170 * @see DisconnectCause#ICC_ERROR 171 * @see DisconnectCause#CALL_BARRED 172 * @see DisconnectCause#FDN_BLOCKED 173 * @see DisconnectCause#CS_RESTRICTED 174 * @see DisconnectCause#CS_RESTRICTED_NORMAL 175 * @see DisconnectCause#CS_RESTRICTED_EMERGENCY 176 * @see DisconnectCause#UNOBTAINABLE_NUMBER 177 * @see DisconnectCause#CDMA_LOCKED_UNTIL_POWER_CYCLE 178 * @see DisconnectCause#CDMA_DROP 179 * @see DisconnectCause#CDMA_INTERCEPT 180 * @see DisconnectCause#CDMA_REORDER 181 * @see DisconnectCause#CDMA_SO_REJECT 182 * @see DisconnectCause#CDMA_RETRY_ORDER 183 * @see DisconnectCause#CDMA_ACCESS_FAILURE 184 * @see DisconnectCause#CDMA_PREEMPTED 185 * @see DisconnectCause#CDMA_NOT_EMERGENCY 186 * @see DisconnectCause#CDMA_ACCESS_BLOCKED 187 * @see DisconnectCause#ERROR_UNSPECIFIED 188 * 189 * TODO: remove disconnect cause from preciseCallState as there is no link between random 190 * connection disconnect cause with foreground, background or ringing call. 191 * 192 * @hide 193 */ 194 @UnsupportedAppUsage getDisconnectCause()195 public int getDisconnectCause() { 196 return mDisconnectCause; 197 } 198 199 /** 200 * Get disconnect cause generated by the RIL 201 * 202 * @see PreciseDisconnectCause#NOT_VALID 203 * @see PreciseDisconnectCause#NO_DISCONNECT_CAUSE_AVAILABLE 204 * @see PreciseDisconnectCause#UNOBTAINABLE_NUMBER 205 * @see PreciseDisconnectCause#NORMAL 206 * @see PreciseDisconnectCause#BUSY 207 * @see PreciseDisconnectCause#NUMBER_CHANGED 208 * @see PreciseDisconnectCause#STATUS_ENQUIRY 209 * @see PreciseDisconnectCause#NORMAL_UNSPECIFIED 210 * @see PreciseDisconnectCause#NO_CIRCUIT_AVAIL 211 * @see PreciseDisconnectCause#TEMPORARY_FAILURE 212 * @see PreciseDisconnectCause#SWITCHING_CONGESTION 213 * @see PreciseDisconnectCause#CHANNEL_NOT_AVAIL 214 * @see PreciseDisconnectCause#QOS_NOT_AVAIL 215 * @see PreciseDisconnectCause#BEARER_NOT_AVAIL 216 * @see PreciseDisconnectCause#ACM_LIMIT_EXCEEDED 217 * @see PreciseDisconnectCause#CALL_BARRED 218 * @see PreciseDisconnectCause#FDN_BLOCKED 219 * @see PreciseDisconnectCause#IMSI_UNKNOWN_IN_VLR 220 * @see PreciseDisconnectCause#IMEI_NOT_ACCEPTED 221 * @see PreciseDisconnectCause#CDMA_LOCKED_UNTIL_POWER_CYCLE 222 * @see PreciseDisconnectCause#CDMA_DROP 223 * @see PreciseDisconnectCause#CDMA_INTERCEPT 224 * @see PreciseDisconnectCause#CDMA_REORDER 225 * @see PreciseDisconnectCause#CDMA_SO_REJECT 226 * @see PreciseDisconnectCause#CDMA_RETRY_ORDER 227 * @see PreciseDisconnectCause#CDMA_ACCESS_FAILURE 228 * @see PreciseDisconnectCause#CDMA_PREEMPTED 229 * @see PreciseDisconnectCause#CDMA_NOT_EMERGENCY 230 * @see PreciseDisconnectCause#CDMA_ACCESS_BLOCKED 231 * @see PreciseDisconnectCause#ERROR_UNSPECIFIED 232 * 233 * TODO: remove precise disconnect cause from preciseCallState as there is no link between 234 * random connection disconnect cause with foreground, background or ringing call. 235 * 236 * @hide 237 */ 238 @UnsupportedAppUsage getPreciseDisconnectCause()239 public int getPreciseDisconnectCause() { 240 return mPreciseDisconnectCause; 241 } 242 243 @Override describeContents()244 public int describeContents() { 245 return 0; 246 } 247 248 @Override writeToParcel(Parcel out, int flags)249 public void writeToParcel(Parcel out, int flags) { 250 out.writeInt(mRingingCallState); 251 out.writeInt(mForegroundCallState); 252 out.writeInt(mBackgroundCallState); 253 out.writeInt(mDisconnectCause); 254 out.writeInt(mPreciseDisconnectCause); 255 } 256 257 public static final @android.annotation.NonNull Parcelable.Creator<PreciseCallState> CREATOR 258 = new Parcelable.Creator<PreciseCallState>() { 259 260 public PreciseCallState createFromParcel(Parcel in) { 261 return new PreciseCallState(in); 262 } 263 264 public PreciseCallState[] newArray(int size) { 265 return new PreciseCallState[size]; 266 } 267 }; 268 269 @Override hashCode()270 public int hashCode() { 271 return Objects.hash(mRingingCallState, mForegroundCallState, mForegroundCallState, 272 mDisconnectCause, mPreciseDisconnectCause); 273 } 274 275 @Override equals(@ullable Object obj)276 public boolean equals(@Nullable Object obj) { 277 if (this == obj) { 278 return true; 279 } 280 if (obj == null) { 281 return false; 282 } 283 if (getClass() != obj.getClass()) { 284 return false; 285 } 286 PreciseCallState other = (PreciseCallState) obj; 287 return (mRingingCallState == other.mRingingCallState 288 && mForegroundCallState == other.mForegroundCallState 289 && mBackgroundCallState == other.mBackgroundCallState 290 && mDisconnectCause == other.mDisconnectCause 291 && mPreciseDisconnectCause == other.mPreciseDisconnectCause); 292 } 293 294 @NonNull 295 @Override toString()296 public String toString() { 297 StringBuffer sb = new StringBuffer(); 298 299 sb.append("Ringing call state: " + mRingingCallState); 300 sb.append(", Foreground call state: " + mForegroundCallState); 301 sb.append(", Background call state: " + mBackgroundCallState); 302 sb.append(", Disconnect cause: " + mDisconnectCause); 303 sb.append(", Precise disconnect cause: " + mPreciseDisconnectCause); 304 305 return sb.toString(); 306 } 307 } 308