summaryrefslogtreecommitdiff
path: root/zaptel.c
diff options
context:
space:
mode:
authorfile <file@5390a7c7-147a-4af0-8ec9-7488f05a26cb>2006-08-31 01:41:30 +0000
committerfile <file@5390a7c7-147a-4af0-8ec9-7488f05a26cb>2006-08-31 01:41:30 +0000
commit48a7bd8b9a59a6b8698deed84ce6575c3bedd417 (patch)
treea9803770fe49d39b2b61d31b47457858db5f688a /zaptel.c
parentba78520cd38addc74ea5b10ebf8f8ef5197a5b84 (diff)
Merge in Zaptel VLDTMF support. This does currently have the bug where dialtone briefly returns after a digit is being played, but that will be fixed shortly.
git-svn-id: http://svn.digium.com/svn/zaptel/trunk@1374 5390a7c7-147a-4af0-8ec9-7488f05a26cb
Diffstat (limited to 'zaptel.c')
-rw-r--r--zaptel.c84
1 files changed, 68 insertions, 16 deletions
diff --git a/zaptel.c b/zaptel.c
index 77a2cca..bf561ff 100644
--- a/zaptel.c
+++ b/zaptel.c
@@ -338,6 +338,9 @@ of the next sample chunk's data (next time around the world).
#include "digits.h"
+static struct zt_tone *dtmf_tones_continuous = NULL;
+static struct zt_tone *mfv1_tones_continuous = NULL;
+
static int zt_chan_ioctl(struct inode *inode, struct file *file, unsigned int cmd, unsigned long data, int unit);
#if defined(CONFIG_ZAPTEL_MMX) || defined(ECHO_CAN_FP)
@@ -1104,28 +1107,44 @@ static int zt_register_tone_zone(int num, struct zt_zone *zone)
static int start_tone(struct zt_chan *chan, int tone)
{
int res = -EINVAL;
+
/* Stop the current tone, no matter what */
chan->tonep = 0;
chan->curtone = NULL;
chan->pdialcount = 0;
chan->txdialbuf[0] = '\0';
- chan->dialing = 0;
- if ((tone >= ZT_TONE_MAX) || (tone < -1))
- return -EINVAL;
- /* Just wanted to stop the tone anyway */
- if (tone < 0)
- return 0;
- if (chan->curzone) {
- /* Have a tone zone */
- if (chan->curzone->tones[tone]) {
- chan->curtone = chan->curzone->tones[tone];
- res = 0;
- } else /* Indicate that zone is loaded but no such tone exists */
- res = -ENOSYS;
- } else /* Note that no tone zone exists at the moment */
- res = -ENODATA;
+ chan->dialing = 0;
+
+ if (tone == -1) {
+ /* Just stop the current tone */
+ res = 0;
+ } else if ((tone >= 0 && tone <= ZT_TONE_MAX)) {
+ if (chan->curzone) {
+ /* Have a tone zone */
+ if (chan->curzone->tones[tone]) {
+ chan->curtone = chan->curzone->tones[tone];
+ res = 0;
+ } else /* Indicate that zone is loaded but no such tone exists */
+ res = -ENOSYS;
+ } else /* Note that no tone zone exists at the moment */
+ res = -ENODATA;
+ } else if (tone >= ZT_TONE_DTMF_BASE && tone <= ZT_TONE_DTMF_MAX) {
+ /* ZT_SENDTONE should never be used on a channel configured for pulse dialing */
+ chan->dialing = 1;
+ res = 0;
+ if (chan->digitmode == DIGIT_MODE_DTMF)
+ chan->curtone = dtmf_tones_continuous + (tone - ZT_TONE_DTMF_BASE);
+ else if (chan->digitmode == DIGIT_MODE_MFV1 && tone != ZT_TONE_DTMF_MAX) /* No 'D' */
+ chan->curtone = mfv1_tones_continuous + (tone - ZT_TONE_DTMF_BASE);
+ else {
+ chan->dialing = 0;
+ res = -EINVAL;
+ }
+ }
+
if (chan->curtone)
zt_init_tone_state(&chan->ts, chan->curtone);
+
return res;
}
@@ -6894,6 +6913,7 @@ static void __exit watchdog_cleanup(void)
static int __init zt_init(void) {
int res = 0;
+ int i = 0;
#ifdef CONFIG_PROC_FS
proc_entries[0] = proc_mkdir("zaptel", NULL);
@@ -6927,6 +6947,26 @@ static int __init zt_init(void) {
}
#endif /* CONFIG_DEVFS_FS */
+ if (!(dtmf_tones_continuous = kmalloc(sizeof(dtmf_tones), GFP_KERNEL))) {
+ printk(KERN_ERR "Zaptel: THERE IS A CRISIS IN THE BATCAVE!"
+ " Unable to allocate memory for continuous DTMF tones list!\n");
+ return -ENOMEM;
+ }
+
+ if (!(mfv1_tones_continuous = kmalloc(sizeof(mfv1_tones), GFP_KERNEL))) {
+ printk(KERN_ERR "Zaptel: THERE IS A CRISIS IN THE BATCAVE!"
+ " Unable to allocate memory for continuous MFV1 tones list!\n");
+ return -ENOMEM;
+ }
+
+ memcpy(dtmf_tones_continuous, dtmf_tones, sizeof(dtmf_tones));
+ for (i = 0; i < (sizeof(dtmf_tones) / sizeof(dtmf_tones[0])); i++)
+ dtmf_tones_continuous[i].next = dtmf_tones_continuous + i;
+
+ memcpy(mfv1_tones_continuous, mfv1_tones, sizeof(mfv1_tones));
+ for (i = 0; i < (sizeof(mfv1_tones) / sizeof(mfv1_tones[0])); i++)
+ mfv1_tones_continuous[i].next = mfv1_tones_continuous + i;
+
printk(KERN_INFO "Zapata Telephony Interface Registered on major %d\n", ZT_MAJOR);
printk(KERN_INFO "Zaptel Version: %s Echo Canceller: %s\n", ZAPTEL_VERSION,
ZAPTEL_ECHO_CANCELLER ZAPTEL_ECHO_AGGRESSIVE);
@@ -6949,9 +6989,21 @@ static void __exit zt_cleanup(void) {
#endif
printk(KERN_INFO "Zapata Telephony Interface Unloaded\n");
- for (x=0;x<ZT_TONE_ZONE_MAX;x++)
+ for (x = 0; x < ZT_TONE_ZONE_MAX; x++) {
if (tone_zones[x])
kfree(tone_zones[x]);
+ }
+
+ if (dtmf_tones_continuous) {
+ kfree(dtmf_tones_continuous);
+ dtmf_tones_continuous = NULL;
+ }
+
+ if (mfv1_tones_continuous) {
+ kfree(mfv1_tones_continuous);
+ mfv1_tones_continuous = NULL;
+ }
+
#ifdef CONFIG_DEVFS_FS
devfs_unregister(timer);
devfs_unregister(transcode);