diff options
author | matteo <matteo@5390a7c7-147a-4af0-8ec9-7488f05a26cb> | 2003-03-17 18:11:45 +0000 |
---|---|---|
committer | matteo <matteo@5390a7c7-147a-4af0-8ec9-7488f05a26cb> | 2003-03-17 18:11:45 +0000 |
commit | f04ea3143569dbadcdd5ed96e8feed0601464156 (patch) | |
tree | ba9a6a7e6bfd24d828419d8707209c8cc9f6798e /ztcfg.c | |
parent | ef7de3f35f2ef572c106a972b7b16b0e947e620b (diff) |
lun mar 17 19:11:15 CET 2003
git-svn-id: http://svn.digium.com/svn/zaptel/trunk@155 5390a7c7-147a-4af0-8ec9-7488f05a26cb
Diffstat (limited to 'ztcfg.c')
-rwxr-xr-x | ztcfg.c | 101 |
1 files changed, 97 insertions, 4 deletions
@@ -37,6 +37,7 @@ #include <sys/ioctl.h> #include <fcntl.h> #include <errno.h> +#include <math.h> #include "ztcfg.h" #include "tonezone.h" #include "zaptel.h" @@ -65,6 +66,8 @@ static struct zt_lineconfig lc[ZT_MAX_SPANS]; static struct zt_chanconfig cc[ZT_MAX_CHANNELS]; +static struct zt_sfconfig sf[ZT_MAX_CHANNELS]; + static struct zt_dynamic_span zds[NUM_DYNAMIC]; static char *sig[ZT_MAX_CHANNELS]; /* Signalling */ @@ -355,6 +358,76 @@ int parse_idle(int *i, char *s) return -1; } +void mknotch(float freq, float bw, long *p1, long *p2, long *p3); + +static void mktxtone(float freq, float l, int *fac, int *init_v2, int *init_v3) +{ +float gain; + + /* Bring it down -8 dbm */ + gain = pow(10.0, (l - 3.14) / 20.0) * 65536.0 / 2.0; + + *fac = 2.0 * cos(2.0 * M_PI * (freq / 8000.0)) * 32768.0; + *init_v2 = sin(-4.0 * M_PI * (freq / 8000.0)) * gain; + *init_v3 = sin(-2.0 * M_PI * (freq / 8000.0)) * gain; +} + +static int parse_sf(struct zt_sfconfig *sf, char *str) +{ +char *realargs[10],*args; +int res; +float rxfreq,rxbw,txfreq,txlevel; +int flags = 0; + + args = strdup(str); + res = parseargs(args, realargs, 6, ','); + if (res != 6) + { + error("Incorrect number of arguments to 'sf' (should be :<rx freq (hz)>,<bandwidth (hz)>,<normal/reverse (rx)>,<tx freq (hz)>,<tx level (dbm)>,<normal/reverse (tx)>)\n"); + free(args); + return -1; + } + res = sscanf(realargs[0],"%f",&rxfreq); + if ((res < 1) || (rxfreq && ((rxfreq < 100.0) || (rxfreq >= 4000.0)))) + { + error("Invalid rx freq. specification (should be between 100.0 and 4000.0 hertz\n"); + free(args); + return -1; + } + res = sscanf(realargs[1],"%f",&rxbw); + if ((res < 1) || (rxfreq && ((rxbw < 5.0) || (rxbw >= 1000.0)))) + { + error("Invalid rx bandwidth specification (should be between 5.0 and 1000.0 hertz\n"); + free(args); + return -1; + } + res = sscanf(realargs[3],"%f",&txfreq); + if ((res < 1) || (txfreq && ((txfreq < 100.0) || (txfreq >= 4000.0)))) + { + error("Invalid tx freq. specification (should be between 100.0 and 4000.0 hertz\n"); + free(args); + return -1; + } + res = sscanf(realargs[4],"%f",&txlevel); + if ((res < 1) || (txfreq && ((txlevel < -50.0) || (txlevel > 3.0)))) + { + error("Invalid tx level specification (should be between -50.0 and 3.0 dbm\n"); + free(args); + return -1; + } + if ((*realargs[2] == 'i') || (*realargs[2] == 'I') || + (*realargs[2] == 'r') || (*realargs[2] == 'R')) + flags |= ZT_REVERSE_RXTONE; + if ((*realargs[5] == 'i') || (*realargs[5] == 'I') || + (*realargs[5] == 'r') || (*realargs[5] == 'R')) + flags |= ZT_REVERSE_TXTONE; + if (rxfreq) mknotch(rxfreq,rxbw,&sf->rxp1,&sf->rxp2,&sf->rxp3); + if (txfreq) mktxtone(txfreq,txlevel,&sf->txtone,&sf->tx_v2,&sf->tx_v3); + sf->toneflag = flags; + free(args); + return 0; +} + static int chanconfig(char *keyword, char *args) { int chans[ZT_MAX_CHANNELS]; @@ -375,11 +448,18 @@ static int chanconfig(char *keyword, char *args) continue; } cc[x].chan = x; + memset(&sf[x],0,sizeof(struct zt_sfconfig)); + sf[x].chan = x; cc[x].master = x; slineno[x] = lineno; if (!strcasecmp(keyword, "e&m")) { sig[x] = "E & M"; cc[x].sigtype = ZT_SIG_EM; + } else if (!strcasecmp(keyword, "sf")) { + if (idle && parse_sf(&sf[x], idle)) + return -1; + sig[x] = "Single Freq. Tone Only (No Signalling)"; + cc[x].sigtype = ZT_SIG_SF; } else if (!strcasecmp(keyword, "fxsls")) { sig[x] = "FXS Loopstart"; cc[x].sigtype = ZT_SIG_FXSLS; @@ -556,6 +636,7 @@ static struct handler { { "loadzone", registerzone }, { "defaultzone", defaultzone }, { "e&m", chanconfig }, + { "sf", chanconfig }, { "fxsls", chanconfig }, { "fxsgs", chanconfig }, { "fxsks", chanconfig }, @@ -725,10 +806,12 @@ int main(int argc, char *argv[]) printf("Configuring device %d\n", x); fflush(stdout); } - if (cc[x].sigtype && ioctl(fd, ZT_CHANCONFIG, &cc[x])) { - fprintf(stderr, "ZT_CHANCONFIG failed on channel %d: %s (%d)\n", x, strerror(errno), errno); - close(fd); - exit(1); + if (cc[x].sigtype) { + if (ioctl(fd, ZT_CHANCONFIG, &cc[x]) == -1) { + fprintf(stderr, "ZT_CHANCONFIG failed on channel %d: %s (%d)\n", x, strerror(errno), errno); + close(fd); + exit(1); + } } } for (x=0;x<numzones;x++) { @@ -757,6 +840,16 @@ int main(int argc, char *argv[]) exit(1); } } + for (x=1;x<ZT_MAX_CHANNELS;x++) { + if ((sf[x].rxp1 || sf[x].txtone)) + { + if (ioctl(fd, ZT_SFCONFIG, &sf[x]) == -1) { + fprintf(stderr, "ZT_SFCONFIG failed on channel %d: %s (%d)\n", x, strerror(errno), errno); + close(fd); + exit(1); + } + } + } } close(fd); } |