// Workaround for Samsung CDMA "ring of death" bug:
  //
  // Symptom: As soon as the phone receives notice of an incoming call, an
  // audible "old fashioned ring" is emitted through the earpiece and
  // persists through the duration of the call, or until reboot if the call
  // isn't answered.
  //
  // Background: The CDMA telephony stack implements a number of "signal info
  // tones" that are locally generated by ToneGenerator and mixed into the
  // voice call path in response to radio RIL_UNSOL_CDMA_INFO_REC requests.
  // One of these tones, IS95_CONST_IR_SIG_IS54B_L, is requested by the
  // radio just prior to notice of an incoming call when the voice call
  // path is muted. CallNotifier is responsible for stopping all signal
  // tones (by "playing" the TONE_CDMA_SIGNAL_OFF tone) upon receipt of a
  // "new ringing connection", prior to unmuting the voice call path.
  //
  // Problem: CallNotifier's incoming call path is designed to minimize
  // latency to notify users of incoming calls ASAP. Thus,
  // SignalInfoTonePlayer requests are handled asynchronously by spawning a
  // one-shot thread for each. Unfortunately the ToneGenerator API does
  // not provide a mechanism to specify an ordering on requests, and thus,
  // unexpected thread interleaving may result in ToneGenerator processing
  // them in the opposite order that CallNotifier intended. In this case,
  // playing the "signal off" tone first, followed by playing the "old
  // fashioned ring" indefinitely.
  //
  // Solution: An API change to ToneGenerator is required to enable
  // SignalInfoTonePlayer to impose an ordering on requests (i.e., drop any
  // request that's older than the most recent observed). Such a change,
  // or another appropriate fix should be implemented in AOSP first.
  //
  // Workaround: Intercept RIL_UNSOL_CDMA_INFO_REC requests from the radio,
  // check for a signal info record matching IS95_CONST_IR_SIG_IS54B_L, and
  // drop it so it's never seen by CallNotifier. If other signal tones are
  // observed to cause this problem, they should be dropped here as well.
  @Override
  protected void notifyRegistrantsCdmaInfoRec(CdmaInformationRecords infoRec) {
    final int response = RIL_UNSOL_CDMA_INFO_REC;

    if (infoRec.record instanceof CdmaSignalInfoRec) {
      CdmaSignalInfoRec sir = (CdmaSignalInfoRec) infoRec.record;
      if (sir != null
          && sir.isPresent
          && sir.signalType == SignalToneUtil.IS95_CONST_IR_SIGNAL_IS54B
          && sir.alertPitch == SignalToneUtil.IS95_CONST_IR_ALERT_MED
          && sir.signal == SignalToneUtil.IS95_CONST_IR_SIG_IS54B_L) {

        Rlog.d(
            RILJ_LOG_TAG,
            "Dropping \""
                + responseToString(response)
                + " "
                + retToString(response, sir)
                + "\" to prevent \"ring of death\" bug.");
        return;
      }
    }

    super.notifyRegistrantsCdmaInfoRec(infoRec);
  }