如何通过AT命令检测远程端拒绝语音呼叫

时间:2014-04-09 11:52:41

标签: gsm 3g at-command modem

情况:

在基于GSM的调制解调器上,您使用ATDxxxxxxxxx开始语音呼叫;

当远程端应答时,某些调制解调器发出“CONNECT”,或者其他调制解调器在诊断端口上返回“^ CONN:1,0”。

但是,如果远程端拒绝呼叫,则仍会发送此连接反馈。

AT + CPAS返回4(正在进行通话)。

AT + CIND(支持时)返回正在运行的呼叫,并且呼叫没有响铃。

某些调制解调器没有在数据端口上发送数据,但其他调制解调器没有(通常发送静音或音调)。

时间之后,网络断开呼叫,然后调制解调器最终在诊断端口上发出“^ CEND”,或在应用程序端口上发出“HANGUP:1”。

我想检测远程端何时尽快拒绝呼叫,而不是在网络超时之后。我该怎么做?

编辑:顺便说一下,我不是在谈论“自动”应答机,而是明确拒绝接听电话(因此它不会被重定向到应答机)。

此外,我想避免“检测数据端口上的铃声”,就像解决方案一样,这些解决方案会变得非常棘手并且CPU密集。“

1 个答案:

答案 0 :(得分:1)

我回答了我自己的问题,所以它在同一个案例中为其他人服务。

检测取决于网络。通常,在法语的运营商Free中,网络不会在呼叫拒绝时断开您的连接(但是让您听到铃声)。在德国,确实如此。所以我认为法国网络的行为是错误的,或者至少没有帮助。

GSM / 3GPP标准中没有特定的用于检测铃声的信息,因此进入这种网络的唯一方法是以编程方式执行检测。 它可以通过检查类似“声音”值之间的时间距离“简单地”完成。 算法是这样的:

int range = 5, value = 350, periodFound = 0; // Arbitrary
int period[16] = {};
void onDataReceived(int sampleRate, short * data, int len)
{
     for (int i = 0; i < len; i++)
     {
         if (data[i] >= value - range && data[i] <= value + range)
         {
             period[periodFound++] = i;
         }
         if (periodFound == 16) break;
     }
     // Compute distance between periods (if it's the same, it's a ring tone)
     float avg = 0, dev = 0;
     int prev = period[0];
     for (int i = 1; i < periodFound; i++)
     {
         avg += (period[i] - prev);
         prev = period[i];
     }
     avg /= periodFound-1;
     prev = period[0];
     for (int i = 1; i < periodFound; i++)
     {
         dev += (period[i] - prev - avg) * (period[i] - prev - avg);
         prev = period[i]
     }

     // Last test
     if (fabs(avg - expectedPeriod) < range && dev < errorAllowed)
         printf("Ring tone!");
}