Asterisk.org: Developer Documentation (28 Oct 2009)

Wed Oct 28 15:49:13 2009

## Asterisk developer's documentation

# res_adsi.c File Reference

ADSI support. More...

`#include <time.h>`
`#include <string.h>`
`#include <stdio.h>`
`#include <stdlib.h>`
`#include <unistd.h>`
`#include <math.h>`
`#include <errno.h>`
`#include "asterisk.h"`
`#include "asterisk/ulaw.h"`
`#include "asterisk/alaw.h"`
`#include "asterisk/callerid.h"`
`#include "asterisk/logger.h"`
`#include "asterisk/fskmodem.h"`
`#include "asterisk/channel.h"`
`#include "asterisk/adsi.h"`
`#include "asterisk/module.h"`
`#include "asterisk/config.h"`
`#include "asterisk/file.h"`

Include dependency graph for res_adsi.c:

Go to the source code of this file.

## Defines

#define | ADSI_FLAG_DATAMODE (1 << 8)
#define | ADSI_MAX_INTRO 20
#define | ADSI_MAX_SPEED_DIAL 6
#define | ADSI_SPEED_DIAL 10
#define | DEFAULT_ADSI_MAX_RETRIES 3

## Functions

static int | __adsi_transmit_messages (struct ast_channel *chan, unsigned char **msg, int *msglen, int *msgtype)
int | adsi_available (struct ast_channel *chan)
int | adsi_begin_download (struct ast_channel *chan, char *service, unsigned char *fdn, unsigned char *sec, int version)
static int | adsi_careful_send (struct ast_channel *chan, unsigned char *buf, int len, int *remainder)
int | adsi_channel_restore (struct ast_channel *chan)
int | adsi_clear_screen (unsigned char *buf)
int | adsi_clear_soft_keys (unsigned char *buf)
int | adsi_connect_session (unsigned char *buf, unsigned char *fdn, int ver)
int | adsi_data_mode (unsigned char *buf)
int | adsi_disconnect_session (unsigned char *buf)
int | adsi_display (unsigned char *buf, int page, int line, int just, int wrap, char *col1, char *col2)
int | adsi_download_connect (unsigned char *buf, char *service, unsigned char *fdn, unsigned char *sec, int ver)
int | adsi_download_disconnect (unsigned char *buf)
int | adsi_end_download (struct ast_channel *chan)
static int | adsi_generate (unsigned char *buf, int msgtype, unsigned char *msg, int msglen, int msgnum, int last, int codec)
int | adsi_get_cpeid (struct ast_channel *chan, unsigned char *cpeid, int voice)
int | adsi_get_cpeinfo (struct ast_channel *chan, int *width, int *height, int *buttons, int voice)
int | adsi_input_control (unsigned char *buf, int page, int line, int display, int format, int just)
int | adsi_input_format (unsigned char *buf, int num, int dir, int wrap, char *format1, char *format2)
static void | adsi_load (void)
int | adsi_load_session (struct ast_channel *chan, unsigned char *app, int ver, int data)
int | adsi_load_soft_key (unsigned char *buf, int key, char *llabel, char *slabel, char *ret, int data)
int | adsi_print (struct ast_channel *chan, char **lines, int *aligns, int voice)
int | adsi_query_cpeid (unsigned char *buf)
int | adsi_query_cpeinfo (unsigned char *buf)
int | adsi_read_encoded_dtmf (struct ast_channel *chan, unsigned char *buf, int maxlen)
int | adsi_set_keys (unsigned char *buf, unsigned char *keys)
int | adsi_set_line (unsigned char *buf, int page, int line)
int | adsi_transmit_message (struct ast_channel *chan, unsigned char *msg, int msglen, int msgtype)
int | adsi_transmit_message_full (struct ast_channel *chan, unsigned char *msg, int msglen, int msgtype, int dowait)
int | adsi_unload_session (struct ast_channel *chan)
int | adsi_voice_mode (unsigned char *buf, int when)
static int | ccopy (unsigned char *dst, unsigned char *src, int max)
char * | description (void)
| Provides a description of the module.
static void | init_state (void)
char * | key ()
| Returns the ASTERISK_GPL_KEY.
int | load_module (void)
| Initialize the module.
int | reload (void)
| Reload stuff.
static int | str2align (char *s)
int | unload_module (void)
| Cleanup all module structures, sockets, etc.
int | usecount (void)
| Provides a usecount.

## Variables

static int | alignment = 0
static int | aligns [ADSI_MAX_INTRO]
static char | intro [ADSI_MAX_INTRO][20]
static int | maxretries = DEFAULT_ADSI_MAX_RETRIES
static char | speeddial [ADSI_MAX_SPEED_DIAL][3][20]
static int | speeds = 0
static int | total = 0

## Detailed Description

ADSI support.

Definition in file res_adsi.c.

## Define Documentation

#define ADSI_FLAG_DATAMODE (1 << 8)

Definition at line 55 of file res_adsi.c.

Referenced by __adsi_transmit_messages(), and adsi_transmit_message_full().

#define ADSI_MAX_INTRO 20

Definition at line 52 of file res_adsi.c.

Referenced by adsi_load(), and init_state().

#define ADSI_MAX_SPEED_DIAL 6

Definition at line 53 of file res_adsi.c.

Referenced by adsi_load().

#define ADSI_SPEED_DIAL 10

Definition at line 60 of file res_adsi.c.

Referenced by adsi_channel_restore().

#define DEFAULT_ADSI_MAX_RETRIES 3

Definition at line 50 of file res_adsi.c.

## Function Documentation

static int __adsi_transmit_messages | ( | struct ast_channel * | chan,
|  | unsigned char ** | msg,
|  | int * | msglen,
|  | int * | msgtype |
| ) |  |  | `[static]`

Definition at line 190 of file res_adsi.c.

References adsi_careful_send(), ADSI_FLAG_DATAMODE, adsi_generate(), ast_channel::adsicpe, AST_ADSI_AVAILABLE, AST_ADSI_UNAVAILABLE, ast_channel_defer_dtmf(), ast_channel_undefer_dtmf(), AST_FORMAT_ULAW, AST_FRAME_DTMF, ast_frfree(), ast_gen_cas(), ast_log(), ast_read(), ast_readstring(), ast_waitfor(), ast_frame::frametype, LOG_DEBUG, LOG_WARNING, ast_channel::name, and ast_frame::subclass.

Referenced by adsi_transmit_message_full().

    00191 {
    00192    /* msglen must be no more than 256 bits, each */
    00193    unsigned char buf[24000 * 5];
    00194    int pos = 0, res;
    00195    int x;
    00196    int start=0;
    00197    int retries = 0;
    00198
    00199    char ack[3];
    00200
    00201    /* Wait up to 500 ms for initial ACK */
    00202    int waittime;
    00203    struct ast_frame *f;
    00204    int rem = 0;
    00205    int def;
    00206
    00207    if (chan->adsicpe == AST_ADSI_UNAVAILABLE) {
    00208       /* Don't bother if we know they don't support ADSI */
    00209       errno = ENOSYS;
    00210       return -1;
    00211    }
    00212
    00213    while(retries < maxretries) {
    00214       if (!(chan->adsicpe & ADSI_FLAG_DATAMODE)) {
    00215          /* Generate CAS (no SAS) */
    00216          ast_gen_cas(buf, 0, 680, AST_FORMAT_ULAW);
    00217
    00218          /* Send CAS */
    00219          if (adsi_careful_send(chan, buf, 680, NULL)) {
    00220             ast_log(LOG_WARNING, "Unable to send CAS\n");
    00221          }
    00222          /* Wait For DTMF result */
    00223          waittime = 500;
    00224          for(;;) {
    00225             if (((res = ast_waitfor(chan, waittime)) < 1)) {
    00226                /* Didn't get back DTMF A in time */
    00227                ast_log(LOG_DEBUG, "No ADSI CPE detected (%d)\n", res);
    00228                if (!chan->adsicpe)
    00229                   chan->adsicpe = AST_ADSI_UNAVAILABLE;
    00230                errno = ENOSYS;
    00231                return -1;
    00232             }
    00233             waittime = res;
    00234             f = ast_read(chan);
    00235             if (!f) {
    00236                ast_log(LOG_DEBUG, "Hangup in ADSI\n");
    00237                return -1;
    00238             }
    00239             if (f->frametype == AST_FRAME_DTMF) {
    00240                if (f->subclass == 'A') {
    00241                   /* Okay, this is an ADSI CPE.  Note this for future reference, too */
    00242                   if (!chan->adsicpe)
    00243                      chan->adsicpe = AST_ADSI_AVAILABLE;
    00244                   break;
    00245                } else {
    00246                   if (f->subclass == 'D')  {
    00247                      ast_log(LOG_DEBUG, "Off-hook capable CPE only, not ADSI\n");
    00248                   } else
    00249                      ast_log(LOG_WARNING, "Unknown ADSI response '%c'\n", f->subclass);
    00250                   if (!chan->adsicpe)
    00251                      chan->adsicpe = AST_ADSI_UNAVAILABLE;
    00252                   errno =  ENOSYS;
    00253                   return -1;
    00254                }
    00255             }
    00256             ast_frfree(f);
    00257          }
    00258
    00259          ast_log(LOG_DEBUG, "ADSI Compatible CPE Detected\n");
    00260       } else
    00261          ast_log(LOG_DEBUG, "Already in data mode\n");
    00262
    00263       x = 0;
    00264       pos = 0;
    00265 #if 1
    00266       def= ast_channel_defer_dtmf(chan);
    00267 #endif
    00268       while((x < 6) && msg[x]) {
    00269          res = adsi_generate(buf + pos, msgtype[x], msg[x], msglen[x], x+1 - start, (x == 5) || !msg[x+1], AST_FORMAT_ULAW);
    00270          if (res < 0) {
    00271             ast_log(LOG_WARNING, "Failed to generate ADSI message %d on channel %s\n", x + 1, chan->name);
    00272             return -1;
    00273          }
    00274          ast_log(LOG_DEBUG, "Message %d, of %d input bytes, %d output bytes\n",
    00275                x + 1, msglen[x], res);
    00276          pos += res;
    00277          x++;
    00278       }
    00279
    00280
    00281       rem = 0;
    00282       res = adsi_careful_send(chan, buf, pos, &rem);
    00283       if (!def)
    00284          ast_channel_undefer_dtmf(chan);
    00285       if (res)
    00286          return -1;
    00287
    00288       ast_log(LOG_DEBUG, "Sent total spill of %d bytes\n", pos);
    00289
    00290       memset(ack, 0, sizeof(ack));
    00291       /* Get real result */
    00292       res = ast_readstring(chan, ack, 2, 1000, 1000, "");
    00293       /* Check for hangup */
    00294       if (res < 0)
    00295          return -1;
    00296       if (ack[0] == 'D') {
    00297          ast_log(LOG_DEBUG, "Acked up to message %d\n", atoi(ack + 1));
    00298          start += atoi(ack + 1);
    00299          if (start >= x)
    00300             break;
    00301          else {
    00302             retries++;
    00303             ast_log(LOG_DEBUG, "Retransmitting (%d), from %d\n", retries, start + 1);
    00304          }
    00305       } else {
    00306          retries++;
    00307          ast_log(LOG_WARNING, "Unexpected response to ack: %s (retry %d)\n", ack, retries);
    00308       }
    00309    }
    00310    if (retries >= maxretries) {
    00311       ast_log(LOG_WARNING, "Maximum ADSI Retries (%d) exceeded\n", maxretries);
    00312       errno = ETIMEDOUT;
    00313       return -1;
    00314    }
    00315    return 0;
    00316
    00317 }

int adsi_available | ( | struct ast_channel * | chan | ) |

Returns non-zero if Channel does or might support ADSI

Parameters:

  | chan | Channel to check

Definition at line 762 of file res_adsi.c.

References ast_channel::adsicpe, AST_ADSI_AVAILABLE, and AST_ADSI_UNKNOWN.

Referenced by adsi_begin(), adsi_delete(), adsi_exec(), adsi_folders(), adsi_goodbye(), adsi_login(), adsi_message(), adsi_password(), adsi_status(), adsi_status2(), ast_park_call(), vm_newuser(), vm_options(), and vm_tempgreeting().

    00763 {
    00764    int cpe = chan->adsicpe & 0xff;
    00765    if ((cpe == AST_ADSI_AVAILABLE) ||
    00766        (cpe == AST_ADSI_UNKNOWN))
    00767       return 1;
    00768    return 0;
    00769 }

int adsi_begin_download | ( | struct ast_channel * | chan,
|  | char * | service,
|  | unsigned char * | fdn,
|  | unsigned char * | sec,
|  | int | version |
| ) |  |  |

Definition at line 319 of file res_adsi.c.

References adsi_download_connect(), ADSI_MSG_DOWNLOAD, adsi_transmit_message_full(), ast_log(), ast_readstring(), and LOG_DEBUG.

Referenced by adsi_load_vmail(), and adsi_prog().

    00320 {
    00321    int bytes;
    00322    unsigned char buf[256];
    00323    char ack[2];
    00324    bytes = 0;
    00325    /* Setup the resident soft key stuff, a piece at a time */
    00326    /* Upload what scripts we can for voicemail ahead of time */
    00327    bytes += adsi_download_connect(buf + bytes, service, fdn, sec, version);
    00328    if (adsi_transmit_message_full(chan, buf, bytes, ADSI_MSG_DOWNLOAD, 0))
    00329       return -1;
    00330    if (ast_readstring(chan, ack, 1, 10000, 10000, ""))
    00331       return -1;
    00332    if (ack[0] == 'B')
    00333       return 0;
    00334    ast_log(LOG_DEBUG, "Download was denied by CPE\n");
    00335    return -1;
    00336 }

static int adsi_careful_send | ( | struct ast_channel * | chan,
|  | unsigned char * | buf,
|  | int | len,
|  | int * | remainder |
| ) |  |  | `[static]`

Definition at line 119 of file res_adsi.c.

References AST_FORMAT_ULAW, AST_FRAME_VOICE, ast_frfree(), ast_log(), ast_read(), ast_waitfor(), ast_write(), ast_frame::data, ast_frame::datalen, ast_frame::frametype, LOG_WARNING, ast_frame::samples, and ast_frame::subclass.

Referenced by __adsi_transmit_messages().

    00120 {
    00121    /* Sends carefully on a full duplex channel by using reading for
    00122       timing */
    00123    struct ast_frame *inf, outf;
    00124    int amt;
    00125
    00126    /* Zero out our outgoing frame */
    00127    memset(&outf, 0, sizeof(outf));
    00128
    00129    if (remainder && *remainder) {
    00130       amt = len;
    00131
    00132       /* Send remainder if provided */
    00133       if (amt > *remainder)
    00134          amt = *remainder;
    00135       else
    00136          *remainder = *remainder - amt;
    00137       outf.frametype = AST_FRAME_VOICE;
    00138       outf.subclass = AST_FORMAT_ULAW;
    00139       outf.data = buf;
    00140       outf.datalen = amt;
    00141       outf.samples = amt;
    00142       if (ast_write(chan, &outf)) {
    00143          ast_log(LOG_WARNING, "Failed to carefully write frame\n");
    00144          return -1;
    00145       }
    00146       /* Update pointers and lengths */
    00147       buf += amt;
    00148       len -= amt;
    00149    }
    00150
    00151    while(len) {
    00152       amt = len;
    00153       /* If we don't get anything at all back in a second, forget
    00154          about it */
    00155       if (ast_waitfor(chan, 1000) < 1)
    00156          return -1;
    00157       inf = ast_read(chan);
    00158       /* Detect hangup */
    00159       if (!inf)
    00160          return -1;
    00161       if (inf->frametype == AST_FRAME_VOICE) {
    00162          /* Read a voice frame */
    00163          if (inf->subclass != AST_FORMAT_ULAW) {
    00164             ast_log(LOG_WARNING, "Channel not in ulaw?\n");
    00165             return -1;
    00166          }
    00167          /* Send no more than they sent us */
    00168          if (amt > inf->datalen)
    00169             amt = inf->datalen;
    00170          else if (remainder)
    00171             *remainder = inf->datalen - amt;
    00172          outf.frametype = AST_FRAME_VOICE;
    00173          outf.subclass = AST_FORMAT_ULAW;
    00174          outf.data = buf;
    00175          outf.datalen = amt;
    00176          outf.samples = amt;
    00177          if (ast_write(chan, &outf)) {
    00178             ast_log(LOG_WARNING, "Failed to carefully write frame\n");
    00179             return -1;
    00180          }
    00181          /* Update pointers and lengths */
    00182          buf += amt;
    00183          len -= amt;
    00184       }
    00185       ast_frfree(inf);
    00186    }
    00187    return 0;
    00188 }

int adsi_channel_restore | ( | struct ast_channel * | chan | ) |

Restore ADSI initialization (for applications that play with ADSI

Parameters:

  | chan | Channel to restore

Returns 0 on success (or adsi unavailable) and -1 on hangup

Definition at line 920 of file res_adsi.c.

References ADSI_INFO_PAGE, ADSI_MSG_DISPLAY, adsi_set_keys(), adsi_set_line(), ADSI_SPEED_DIAL, adsi_transmit_message_full(), and dsp.

    00921 {
    00922    unsigned char dsp[256];
    00923    int bytes;
    00924    int x;
    00925    unsigned char keyd[6];
    00926
    00927    memset(dsp, 0, sizeof(dsp));
    00928
    00929    /* Start with initial display setup */
    00930    bytes = 0;
    00931    bytes += adsi_set_line(dsp + bytes, ADSI_INFO_PAGE, 1);
    00932
    00933    /* Prepare key setup messages */
    00934
    00935    if (speeds) {
    00936       memset(keyd, 0, sizeof(keyd));
    00937       for (x=0;x<speeds;x++) {
    00938          keyd[x] = ADSI_SPEED_DIAL + x;
    00939       }
    00940       bytes += adsi_set_keys(dsp + bytes, keyd);
    00941    }
    00942    adsi_transmit_message_full(chan, dsp, bytes, ADSI_MSG_DISPLAY, 0);
    00943    return 0;
    00944
    00945 }

int adsi_clear_screen | ( | unsigned char * | buf | ) |

Definition at line 730 of file res_adsi.c.

References ADSI_CLEAR_SCREEN.

    00731 {
    00732    int bytes=0;
    00733
    00734    /* Message type */
    00735    buf[bytes++] = ADSI_CLEAR_SCREEN;
    00736
    00737    /* Reserve space for length */
    00738    bytes++;
    00739
    00740    buf[1] = bytes - 2;
    00741    return bytes;
    00742
    00743 }

int adsi_clear_soft_keys | ( | unsigned char * | buf | ) |

Definition at line 715 of file res_adsi.c.

References ADSI_CLEAR_SOFTKEY.

    00716 {
    00717    int bytes=0;
    00718
    00719    /* Message type */
    00720    buf[bytes++] = ADSI_CLEAR_SOFTKEY;
    00721
    00722    /* Reserve space for length */
    00723    bytes++;
    00724
    00725    buf[1] = bytes - 2;
    00726    return bytes;
    00727
    00728 }

int adsi_connect_session | ( | unsigned char * | buf,
|  | unsigned char * | fdn,
|  | int | ver |
| ) |  |  |

Connects an ADSI Display Session

Parameters:

  | buf | Character buffer to create parameter in (must have at least 256 free)
  | fdn | Optional 4 byte Feature Download Number (for loading soft keys)
  | ver | Optional version number (0-255, or -1 to omit)

Returns number of bytes added to buffer or -1 on error.

Definition at line 480 of file res_adsi.c.

References ADSI_CONNECT_SESSION.

Referenced by adsi_load_session().

    00481 {
    00482    int bytes=0;
    00483    int x;
    00484
    00485    /* Message type */
    00486    buf[bytes++] = ADSI_CONNECT_SESSION;
    00487
    00488    /* Reserve space for length */
    00489    bytes++;
    00490
    00491    if (fdn) {
    00492       for (x=0;x<4;x++)
    00493          buf[bytes++] = fdn[x];
    00494       if (ver > -1)
    00495          buf[bytes++] = ver & 0xff;
    00496    }
    00497
    00498    buf[1] = bytes - 2;
    00499    return bytes;
    00500
    00501 }

int adsi_data_mode | ( | unsigned char * | buf | ) |

Puts CPE in data mode...

Parameters:

  | buf | Character buffer to create parameter in (must have at least 256 free)

Returns number of bytes added to buffer or -1 on error.

Definition at line 700 of file res_adsi.c.

References ADSI_SWITCH_TO_DATA.

Referenced by adsi_get_cpeid(), adsi_get_cpeinfo(), adsi_load_session(), and adsi_load_vmail().

    00701 {
    00702    int bytes=0;
    00703
    00704    /* Message type */
    00705    buf[bytes++] = ADSI_SWITCH_TO_DATA;
    00706
    00707    /* Reserve space for length */
    00708    bytes++;
    00709
    00710    buf[1] = bytes - 2;
    00711    return bytes;
    00712
    00713 }

int adsi_disconnect_session | ( | unsigned char * | buf | ) |

Disconnects a running session

Parameters:

  | buf | Character buffer to create parameter in (must have at least 256 free)

Returns number of bytes added to buffer or -1 on error.

Definition at line 533 of file res_adsi.c.

References ADSI_DISC_SESSION.

Referenced by adsi_unload_session().

    00534 {
    00535    int bytes=0;
    00536
    00537    /* Message type */
    00538    buf[bytes++] = ADSI_DISC_SESSION;
    00539
    00540    /* Reserve space for length */
    00541    bytes++;
    00542
    00543    buf[1] = bytes - 2;
    00544    return bytes;
    00545
    00546 }

int adsi_display | ( | unsigned char * | buf,
|  | int | page,
|  | int | line,
|  | int | just,
|  | int | wrap,
|  | char * | col1,
|  | char * | col2 |
| ) |  |  |

Loads a line of info into the display

Parameters:

  | buf | Character buffer to create parameter in (must have at least 256 free)
  | page | Page to load (ADSI_COMM_PAGE or ADSI_INFO_PAGE)
  | line | Line number to load (1-4 for Comm page, 1-33 for info page)
  | just | Line justification (ADSI_JUST_LEFT, ADSI_JUST_RIGHT, ADSI_JUST_CENT, ADSI_JUST_IND)
  | wrap | Wrap (1 = yes, 0 = no)
  | col1 | Text to place in first column
  | col2 | Text to place in second column

Returns number of bytes added to buffer or -1 on error.

Definition at line 786 of file res_adsi.c.

References ADSI_LOAD_VIRTUAL_DISP, and ccopy().

Referenced by adsi_folders(), adsi_goodbye(), adsi_load_vmail(), adsi_login(), adsi_logo(), adsi_message(), adsi_print(), adsi_prog(), adsi_status(), adsi_status2(), vm_newuser(), vm_options(), and vm_tempgreeting().

    00788 {
    00789    int bytes=0;
    00790
    00791    /* Sanity check line number */
    00792
    00793    if (page) {
    00794       if (line > 4) return -1;
    00795    } else {
    00796       if (line > 33) return -1;
    00797    }
    00798
    00799    if (line < 1)
    00800       return -1;
    00801    /* Parameter type */
    00802    buf[bytes++] = ADSI_LOAD_VIRTUAL_DISP;
    00803
    00804    /* Reserve space for size */
    00805    bytes++;
    00806
    00807    /* Page and wrap indicator */
    00808    buf[bytes++] = ((page & 0x1) << 7) | ((wrap & 0x1) << 6) | (line & 0x3f);
    00809
    00810    /* Justification */
    00811    buf[bytes++] = (just & 0x3) << 5;
    00812
    00813    /* Omit highlight mode definition */
    00814    buf[bytes++] = 0xff;
    00815
    00816    /* Primary column */
    00817    bytes+= ccopy(buf + bytes, (unsigned char *)col1, 20);
    00818
    00819    /* Delimiter */
    00820    buf[bytes++] = 0xff;
    00821
    00822    /* Secondary column */
    00823    bytes += ccopy(buf + bytes, (unsigned char *)col2, 20);
    00824
    00825    /* Update length */
    00826    buf[1] = bytes - 2;
    00827
    00828    return bytes;
    00829
    00830 }

int adsi_download_connect | ( | unsigned char * | buf,
|  | char * | service,
|  | unsigned char * | fdn,
|  | unsigned char * | sec,
|  | int | ver |
| ) |  |  |

Begin an ADSI script download

Parameters:

  | buf | Character buffer to create parameter in (must have at least 256 free)
  | service | a 1-18 byte name of the feature
  | fdn | 4 byte Feature Download Number (for loading soft keys)
  | sec | 4 byte vendor security code
  | ver | version number (0-255, or -1 to omit)

Returns number of bytes added to buffer or -1 on error.

Definition at line 503 of file res_adsi.c.

References ADSI_DOWNLOAD_CONNECT, and ccopy().

Referenced by adsi_begin_download().

    00504 {
    00505    int bytes=0;
    00506    int x;
    00507
    00508    /* Message type */
    00509    buf[bytes++] = ADSI_DOWNLOAD_CONNECT;
    00510
    00511    /* Reserve space for length */
    00512    bytes++;
    00513
    00514    /* Primary column */
    00515    bytes+= ccopy(buf + bytes, (unsigned char *)service, 18);
    00516
    00517    /* Delimiter */
    00518    buf[bytes++] = 0xff;
    00519
    00520    for (x=0;x<4;x++) {
    00521       buf[bytes++] = fdn[x];
    00522    }
    00523    for (x=0;x<4;x++)
    00524       buf[bytes++] = sec[x];
    00525    buf[bytes++] = ver & 0xff;
    00526
    00527    buf[1] = bytes - 2;
    00528
    00529    return bytes;
    00530
    00531 }

int adsi_download_disconnect | ( | unsigned char * | buf | ) |

Disconnects (and hopefully saves) a downloaded script

Parameters:

  | buf | Character buffer to create parameter in (must have at least 256 free)

Returns number of bytes added to buffer or -1 on error.

Definition at line 771 of file res_adsi.c.

References ADSI_DOWNLOAD_DISC.

Referenced by adsi_end_download(), and adsi_load_vmail().

    00772 {
    00773    int bytes=0;
    00774
    00775    /* Message type */
    00776    buf[bytes++] = ADSI_DOWNLOAD_DISC;
    00777
    00778    /* Reserve space for length */
    00779    bytes++;
    00780
    00781    buf[1] = bytes - 2;
    00782    return bytes;
    00783
    00784 }

int adsi_end_download | ( | struct ast_channel * | chan | ) |

Definition at line 338 of file res_adsi.c.

References adsi_download_disconnect(), ADSI_MSG_DOWNLOAD, and adsi_transmit_message_full().

Referenced by adsi_load_vmail(), and adsi_prog().

    00339 {
    00340    int bytes;
    00341    unsigned char buf[256];
    00342         bytes = 0;
    00343         /* Setup the resident soft key stuff, a piece at a time */
    00344         /* Upload what scripts we can for voicemail ahead of time */
    00345         bytes += adsi_download_disconnect(buf + bytes);
    00346    if (adsi_transmit_message_full(chan, buf, bytes, ADSI_MSG_DOWNLOAD, 0))
    00347       return -1;
    00348    return 0;
    00349 }

static int adsi_generate | ( | unsigned char * | buf,
|  | int | msgtype,
|  | unsigned char * | msg,
|  | int | msglen,
|  | int | msgnum,
|  | int | last,
|  | int | codec |
| ) |  |  | `[static]`

Definition at line 69 of file res_adsi.c.

References PUT_CLID, and PUT_CLID_MARKMS.

Referenced by __adsi_transmit_messages().

    00070 {
    00071    int sum;
    00072    int x;
    00073    int bytes=0;
    00074    /* Initial carrier (imaginary) */
    00075    float cr = 1.0;
    00076    float ci = 0.0;
    00077    float scont = 0.0;
    00078
    00079    if (msglen > 255)
    00080       msglen = 255;
    00081
    00082    /* If first message, Send 150ms of MARK's */
    00083    if (msgnum == 1) {
    00084       for (x=0;x<150;x++)  /* was 150 */
    00085          PUT_CLID_MARKMS;
    00086    }
    00087    /* Put message type */
    00088    PUT_CLID(msgtype);
    00089    sum = msgtype;
    00090
    00091    /* Put message length (plus one  for the message number) */
    00092    PUT_CLID(msglen + 1);
    00093    sum += msglen + 1;
    00094
    00095    /* Put message number */
    00096    PUT_CLID(msgnum);
    00097    sum += msgnum;
    00098
    00099    /* Put actual message */
    00100    for (x=0;x<msglen;x++) {
    00101       PUT_CLID(msg[x]);
    00102       sum += msg[x];
    00103    }
    00104
    00105    /* Put 2's compliment of sum */
    00106    PUT_CLID(256-(sum & 0xff));
    00107
    00108 #if 0
    00109    if (last) {
    00110       /* Put trailing marks */
    00111       for (x=0;x<50;x++)
    00112          PUT_CLID_MARKMS;
    00113    }
    00114 #endif
    00115    return bytes;
    00116
    00117 }

int adsi_get_cpeid | ( | struct ast_channel * | chan,
|  | unsigned char * | cpeid,
|  | int | voice |
| ) |  |  |

Get CPE ID from an attached ADSI compatible CPE.

Returns 1 on success, storing 4 bytes of CPE ID at buf or -1 on hangup, or 0 if there was no hangup but it failed to find the device ID. Returns to voice mode if "voice" is non-zero.

Definition at line 603 of file res_adsi.c.

References adsi_data_mode(), ADSI_MSG_DISPLAY, adsi_query_cpeid(), adsi_read_encoded_dtmf(), adsi_transmit_message_full(), adsi_voice_mode(), ast_log(), ast_waitfordigit(), and LOG_WARNING.

Referenced by cpeid_exec().

    00604 {
    00605    unsigned char buf[256];
    00606    int bytes = 0;
    00607    int res;
    00608    bytes += adsi_data_mode(buf);
    00609    adsi_transmit_message_full(chan, buf, bytes, ADSI_MSG_DISPLAY, 0);
    00610
    00611    bytes = 0;
    00612    bytes += adsi_query_cpeid(buf);
    00613    adsi_transmit_message_full(chan, buf, bytes, ADSI_MSG_DISPLAY, 0);
    00614
    00615    /* Get response */
    00616    memset(buf, 0, sizeof(buf));
    00617    res = adsi_read_encoded_dtmf(chan, cpeid, 4);
    00618    if (res != 4) {
    00619       ast_log(LOG_WARNING, "Got %d bytes back of encoded DTMF, expecting 4\n", res);
    00620       res = 0;
    00621    } else {
    00622       res = 1;
    00623    }
    00624
    00625    if (voice) {
    00626       bytes = 0;
    00627       bytes += adsi_voice_mode(buf, 0);
    00628       adsi_transmit_message_full(chan, buf, bytes, ADSI_MSG_DISPLAY, 0);
    00629       /* Ignore the resulting DTMF B announcing it's in voice mode */
    00630       ast_waitfordigit(chan, 1000);
    00631    }
    00632    return res;
    00633 }

int adsi_get_cpeinfo | ( | struct ast_channel * | chan,
|  | int * | width,
|  | int * | height,
|  | int * | buttons,
|  | int | voice |
| ) |  |  |

Definition at line 635 of file res_adsi.c.

References adsi_data_mode(), ADSI_MSG_DISPLAY, adsi_query_cpeinfo(), adsi_transmit_message_full(), adsi_voice_mode(), ast_log(), ast_readstring(), ast_waitfordigit(), and LOG_WARNING.

Referenced by cpeid_exec().

    00636 {
    00637    unsigned char buf[256];
    00638    int bytes = 0;
    00639    int res;
    00640    bytes += adsi_data_mode(buf);
    00641    adsi_transmit_message_full(chan, buf, bytes, ADSI_MSG_DISPLAY, 0);
    00642
    00643    bytes = 0;
    00644    bytes += adsi_query_cpeinfo(buf);
    00645    adsi_transmit_message_full(chan, buf, bytes, ADSI_MSG_DISPLAY, 0);
    00646
    00647    /* Get width */
    00648    memset(buf, 0, sizeof(buf));
    00649    res = ast_readstring(chan, (char *)buf, 2, 1000, 500, "");
    00650    if (res < 0)
    00651       return res;
    00652    if (strlen((char *)buf) != 2) {
    00653       ast_log(LOG_WARNING, "Got %d bytes of width, expecting 2\n", res);
    00654       res = 0;
    00655    } else {
    00656       res = 1;
    00657    }
    00658    if (width)
    00659       *width = atoi((char *)buf);
    00660    /* Get height */
    00661    memset(buf, 0, sizeof(buf));
    00662    if (res) {
    00663       res = ast_readstring(chan, (char *)buf, 2, 1000, 500, "");
    00664       if (res < 0)
    00665          return res;
    00666       if (strlen((char *)buf) != 2) {
    00667          ast_log(LOG_WARNING, "Got %d bytes of height, expecting 2\n", res);
    00668          res = 0;
    00669       } else {
    00670          res = 1;
    00671       }
    00672       if (height)
    00673          *height= atoi((char *)buf);
    00674    }
    00675    /* Get buttons */
    00676    memset(buf, 0, sizeof(buf));
    00677    if (res) {
    00678       res = ast_readstring(chan, (char *)buf, 1, 1000, 500, "");
    00679       if (res < 0)
    00680          return res;
    00681       if (strlen((char *)buf) != 1) {
    00682          ast_log(LOG_WARNING, "Got %d bytes of buttons, expecting 1\n", res);
    00683          res = 0;
    00684       } else {
    00685          res = 1;
    00686       }
    00687       if (buttons)
    00688          *buttons = atoi((char *)buf);
    00689    }
    00690    if (voice) {
    00691       bytes = 0;
    00692       bytes += adsi_voice_mode(buf, 0);
    00693       adsi_transmit_message_full(chan, buf, bytes, ADSI_MSG_DISPLAY, 0);
    00694       /* Ignore the resulting DTMF B announcing it's in voice mode */
    00695       ast_waitfordigit(chan, 1000);
    00696    }
    00697    return res;
    00698 }

int adsi_input_control | ( | unsigned char * | buf,
|  | int | page,
|  | int | line,
|  | int | display,
|  | int | format,
|  | int | just |
| ) |  |  |

Set input information

Parameters:

  | buf | Character buffer to create parameter in (must have at least 256 free)
  | page | Which page to input on (ADSI_COMM_PAGE or ADSI_INFO_PAGE)
  | line | Line number to input on
  | display | Set to zero to obscure input, or 1 to leave visible
  | format | Format number to use (0-7)
  | just | Justification (left, right center, indent)

Returns number of bytes added to buffer or -1 on error.

Definition at line 832 of file res_adsi.c.

References ADSI_INPUT_CONTROL.

Referenced by adsi_login(), and adsi_password().

    00833 {
    00834    int bytes=0;
    00835
    00836    if (page) {
    00837       if (line > 4) return -1;
    00838    } else {
    00839       if (line > 33) return -1;
    00840    }
    00841
    00842    if (line < 1)
    00843       return -1;
    00844
    00845    buf[bytes++] = ADSI_INPUT_CONTROL;
    00846    bytes++;
    00847    buf[bytes++] = ((page & 1) << 7) | (line & 0x3f);
    00848    buf[bytes++] = ((display & 1) << 7) | ((just & 0x3) << 4) | (format & 0x7);
    00849
    00850    buf[1] = bytes - 2;
    00851    return bytes;
    00852
    00853 }

int adsi_input_format | ( | unsigned char * | buf,
|  | int | num,
|  | int | dir,
|  | int | wrap,
|  | char * | format1,
|  | char * | format2 |
| ) |  |  |

Set input format

Parameters:

  | buf | Character buffer to create parameter in (must have at least 256 free)
  | num | Which format we are setting
  | dir | Which direction (ADSI_DIR_FROM_LEFT or ADSI_DIR_FROM_RIGHT)
  | wrap | Set to 1 to permit line wrap, or 0 if not
  | format1 | Format for column 1
  | format2 | Format for column 2

Returns number of bytes added to buffer or -1 on error.

Definition at line 855 of file res_adsi.c.

References ADSI_INPUT_FORMAT, and ccopy().

Referenced by adsi_login(), and adsi_password().

    00856 {
    00857    int bytes = 0;
    00858
    00859    if (!strlen((char *)format1))
    00860       return -1;
    00861
    00862    buf[bytes++] = ADSI_INPUT_FORMAT;
    00863    bytes++;
    00864    buf[bytes++] = ((dir & 1) << 7) | ((wrap & 1) << 6) | (num & 0x7);
    00865    bytes += ccopy(buf + bytes, (unsigned char *)format1, 20);
    00866    buf[bytes++] = 0xff;
    00867    if (format2 && strlen((char *)format2)) {
    00868       bytes += ccopy(buf + bytes, (unsigned char *)format2, 20);
    00869    }
    00870    buf[1] = bytes - 2;
    00871    return bytes;
    00872 }

static void adsi_load | ( | void |  | ) | `[static]`

Definition at line 1055 of file res_adsi.c.

References ADSI_MAX_INTRO, ADSI_MAX_SPEED_DIAL, ast_config_destroy(), ast_config_load(), ast_variable_browse(), init_state(), ast_variable::name, name, ast_variable::next, str2align(), strsep(), and ast_variable::value.

Referenced by load_module(), and reload().

    01056 {
    01057    int x;
    01058    struct ast_config *conf;
    01059    struct ast_variable *v;
    01060    char *name, *sname;
    01061    init_state();
    01062    conf = ast_config_load("adsi.conf");
    01063    if (conf) {
    01064       x=0;
    01065       v = ast_variable_browse(conf, "intro");
    01066       while(v) {
    01067          if (!strcasecmp(v->name, "alignment"))
    01068             alignment = str2align(v->value);
    01069          else if (!strcasecmp(v->name, "greeting")) {
    01070             if (x < ADSI_MAX_INTRO) {
    01071                aligns[x] = alignment;
    01072                strncpy(intro[x], v->value, sizeof(intro[x]) - 1);
    01073                intro[x][sizeof(intro[x]) - 1] = '\0';
    01074                x++;
    01075             }
    01076          } else if (!strcasecmp(v->name, "maxretries")) {
    01077             if (atoi(v->value) > 0)
    01078                maxretries = atoi(v->value);
    01079          }
    01080          v = v->next;
    01081       }
    01082       v = ast_variable_browse(conf, "speeddial");
    01083       if (x)
    01084          total = x;
    01085       x = 0;
    01086       while(v) {
    01087          char *stringp=NULL;
    01088          stringp=v->value;
    01089          name = strsep(&stringp, ",");
    01090          sname = strsep(&stringp, ",");
    01091          if (!sname)
    01092             sname = name;
    01093          if (x < ADSI_MAX_SPEED_DIAL) {
    01094             /* Up to 20 digits */
    01095             strncpy(speeddial[x][0], v->name, sizeof(speeddial[x][0]) - 1);
    01096             strncpy(speeddial[x][1], name, 18);
    01097             strncpy(speeddial[x][2], sname, 7);
    01098             x++;
    01099          }
    01100          v = v->next;
    01101
    01102       }
    01103       if (x)
    01104          speeds = x;
    01105       ast_config_destroy(conf);
    01106    }
    01107 }

int adsi_load_session | ( | struct ast_channel * | chan,
|  | unsigned char * | app,
|  | int | ver,
|  | int | data |
| ) |  |  |

Check if scripts for a given app are already loaded. Version may be -1

Parameters:

  | chan | Channel to test for loaded app
  | app | Four character app name (must be unique to your application)
  | ver | optional version number
  | data | Non-zero if you want to be put in data mode

Returns 0 if scripts is not loaded or not an ADSI CPE. Returns -1 on hangup. Returns 1 if script already loaded.

Definition at line 967 of file res_adsi.c.

References adsi_connect_session(), adsi_data_mode(), ADSI_MSG_DISPLAY, adsi_transmit_message_full(), ast_log(), ast_readstring(), dsp, LOG_DEBUG, and LOG_WARNING.

Referenced by adsi_announce_park(), adsi_begin(), adsi_load_vmail(), adsi_prog(), and cpeid_exec().

    00968 {
    00969    unsigned char dsp[256];
    00970    int bytes;
    00971    int res;
    00972    char resp[2];
    00973
    00974    memset(dsp, 0, sizeof(dsp));
    00975
    00976    /* Connect to session */
    00977    bytes = 0;
    00978    bytes += adsi_connect_session(dsp + bytes, app, ver);
    00979
    00980    if (data)
    00981       bytes += adsi_data_mode(dsp + bytes);
    00982
    00983    /* Prepare key setup messages */
    00984    if (adsi_transmit_message_full(chan, dsp, bytes, ADSI_MSG_DISPLAY, 0))
    00985       return -1;
    00986    if (app) {
    00987       res = ast_readstring(chan, resp, 1, 1200, 1200, "");
    00988       if (res < 0)
    00989          return -1;
    00990       if (res) {
    00991          ast_log(LOG_DEBUG, "No response from CPE about version.  Assuming not there.\n");
    00992          return 0;
    00993       }
    00994       if (!strcmp(resp, "B")) {
    00995          ast_log(LOG_DEBUG, "CPE has script '%s' version %d already loaded\n", app, ver);
    00996          return 1;
    00997       } else if (!strcmp(resp, "A")) {
    00998          ast_log(LOG_DEBUG, "CPE hasn't script '%s' version %d already loaded\n", app, ver);
    00999       } else {
    01000          ast_log(LOG_WARNING, "Unexpected CPE response to script query: %s\n", resp);
    01001       }
    01002    } else
    01003       return 1;
    01004    return 0;
    01005
    01006 }

int adsi_load_soft_key | ( | unsigned char * | buf,
|  | int | key,
|  | char * | llabel,
|  | char * | slabel,
|  | char * | ret,
|  | int | data |
| ) |  |  |

Creates "load soft key" parameters

Parameters:

  | buf | Character buffer to create parameter in (must have at least 256 free)
  | key | Key code from 2 to 33, for which key we are loading
  | llabel | Long label for key (1-18 bytes)
  | slabel | Short label for key (1-7 bytes)
  | ret | Optional return sequence (NULL for none)
  | data | whether to put CPE in data mode before sending digits

Returns number of bytes added to buffer or -1 on error.

Definition at line 441 of file res_adsi.c.

References ADSI_LOAD_SOFTKEY, ADSI_SWITCH_TO_DATA2, and ccopy().

Referenced by adsi_load_vmail(), and adsi_login().

    00442 {
    00443    int bytes=0;
    00444
    00445    /* Abort if invalid key specified */
    00446    if ((key < 2) || (key > 33))
    00447       return -1;
    00448    buf[bytes++] = ADSI_LOAD_SOFTKEY;
    00449    /* Reserve for length */
    00450    bytes++;
    00451    /* Which key */
    00452    buf[bytes++] = key;
    00453
    00454    /* Carefully copy long label */
    00455    bytes += ccopy(buf + bytes, (unsigned char *)llabel, 18);
    00456
    00457    /* Place delimiter */
    00458    buf[bytes++] = 0xff;
    00459
    00460    /* Short label */
    00461    bytes += ccopy(buf + bytes, (unsigned char *)slabel, 7);
    00462
    00463
    00464    /* If specified, copy return string */
    00465    if (ret) {
    00466       /* Place delimiter */
    00467       buf[bytes++] = 0xff;
    00468       if (data)
    00469          buf[bytes++] = ADSI_SWITCH_TO_DATA2;
    00470       /* Carefully copy return string */
    00471       bytes += ccopy(buf + bytes, (unsigned char *)ret, 20);
    00472
    00473    }
    00474    /* Replace parameter length */
    00475    buf[1] = bytes - 2;
    00476    return bytes;
    00477
    00478 }

int adsi_print | ( | struct ast_channel * | chan,
|  | char ** | lines,
|  | int * | align,
|  | int | voice |
| ) |  |  |

Display some stuff on the screen

Parameters:

  | chan | Channel to display on
  | lines | NULL-terminated list of things to print (no more than 4 recommended)
  | align | list of alignments to use (ADSI_JUST_LEFT, ADSI_JUST_RIGHT, ADSI_JUST_CEN, etc..)
  | voice | whether to jump into voice mode when finished

Return 0 on success (or adsi unavailable) and -1 on hangup

Definition at line 947 of file res_adsi.c.

References adsi_display(), ADSI_INFO_PAGE, ADSI_MSG_DISPLAY, adsi_set_line(), adsi_transmit_message_full(), adsi_voice_mode(), and ast_waitfordigit().

Referenced by adsi_announce_park(), and cpeid_setstatus().

    00948 {
    00949    unsigned char buf[4096];
    00950    int bytes=0;
    00951    int res;
    00952    int x;
    00953    for(x=0;lines[x];x++)
    00954       bytes += adsi_display(buf + bytes, ADSI_INFO_PAGE, x+1, aligns[x], 0, lines[x], "");
    00955    bytes += adsi_set_line(buf + bytes, ADSI_INFO_PAGE, 1);
    00956    if (voice) {
    00957       bytes += adsi_voice_mode(buf + bytes, 0);
    00958    }
    00959    res = adsi_transmit_message_full(chan, buf, bytes, ADSI_MSG_DISPLAY, 0);
    00960    if (voice) {
    00961       /* Ignore the resulting DTMF B announcing it's in voice mode */
    00962       ast_waitfordigit(chan, 1000);
    00963    }
    00964    return res;
    00965 }

int adsi_query_cpeid | ( | unsigned char * | buf | ) |

Build Query CPE ID of equipment

Returns number of bytes added to message

Definition at line 548 of file res_adsi.c.

References ADSI_QUERY_CPEID.

Referenced by adsi_get_cpeid().

    00549 {
    00550    int bytes = 0;
    00551    buf[bytes++] = ADSI_QUERY_CPEID;
    00552    /* Reserve space for length */
    00553    bytes++;
    00554    buf[1] = bytes - 2;
    00555    return bytes;
    00556 }

int adsi_query_cpeinfo | ( | unsigned char * | buf | ) |

Definition at line 558 of file res_adsi.c.

References ADSI_QUERY_CONFIG.

Referenced by adsi_get_cpeinfo().

    00559 {
    00560    int bytes = 0;
    00561    buf[bytes++] = ADSI_QUERY_CONFIG;
    00562    /* Reserve space for length */
    00563    bytes++;
    00564    buf[1] = bytes - 2;
    00565    return bytes;
    00566 }

int adsi_read_encoded_dtmf | ( | struct ast_channel * | chan,
|  | unsigned char * | buf,
|  | int | maxlen |
| ) |  |  |

Read some encoded DTMF data.

Returns number of bytes received

Definition at line 568 of file res_adsi.c.

References ast_waitfordigit().

Referenced by adsi_get_cpeid().

    00569 {
    00570    int bytes = 0;
    00571    int res;
    00572    unsigned char current = 0;
    00573    int gotstar = 0;
    00574    int pos = 0;
    00575    memset(buf, 0, sizeof(buf));
    00576    while(bytes <= maxlen) {
    00577       /* Wait up to a second for a digit */
    00578       res = ast_waitfordigit(chan, 1000);
    00579       if (!res)
    00580          break;
    00581       if (res == '*') {
    00582          gotstar = 1;
    00583          continue;
    00584       }
    00585       /* Ignore anything other than a digit */
    00586       if ((res < '0') || (res > '9'))
    00587          continue;
    00588       res -= '0';
    00589       if (gotstar)
    00590          res += 9;
    00591       if (pos)  {
    00592          pos = 0;
    00593          buf[bytes++] = (res << 4) | current;
    00594       } else {
    00595          pos = 1;
    00596          current = res;
    00597       }
    00598       gotstar = 0;
    00599    }
    00600    return bytes;
    00601 }

int adsi_set_keys | ( | unsigned char * | buf,
|  | unsigned char * | keys |
| ) |  |  |

Set which soft keys should be displayed

Parameters:

  | buf | Character buffer to create parameter in (must have at least 256 free)
  | keys | Array of 8 unsigned chars with the key numbers, may be OR'd with ADSI_KEY_HILITE But remember, the last two keys aren't real keys, they're for scrolling

Returns number of bytes added to buffer or -1 on error.

Definition at line 874 of file res_adsi.c.

References ADSI_INIT_SOFTKEY_LINE.

Referenced by adsi_channel_restore(), adsi_delete(), adsi_folders(), adsi_login(), adsi_message(), adsi_password(), adsi_status(), and adsi_status2().

    00875 {
    00876    int bytes=0;
    00877    int x;
    00878    /* Message type */
    00879    buf[bytes++] = ADSI_INIT_SOFTKEY_LINE;
    00880    /* Space for size */
    00881    bytes++;
    00882    /* Key definitions */
    00883    for (x=0;x<6;x++)
    00884       buf[bytes++] = (keys[x] & 0x3f) ? keys[x] : (keys[x] | 0x1);
    00885    buf[1] = bytes - 2;
    00886    return bytes;
    00887 }

int adsi_set_line | ( | unsigned char * | buf,
|  | int | page,
|  | int | line |
| ) |  |  |

Sets the current line and page

Parameters:

  | buf | Character buffer to create parameter in (must have at least 256 free)
  | page | Which page (ADSI_COMM_PAGE or ADSI_INFO_PAGE)
  | line | Line number (1-33 for info page, 1-4 for comm page)

Returns number of bytes added to buffer or -1 on error.

Definition at line 889 of file res_adsi.c.

References ADSI_LINE_CONTROL.

Referenced by adsi_channel_restore(), adsi_folders(), adsi_goodbye(), adsi_load_vmail(), adsi_login(), adsi_message(), adsi_password(), adsi_print(), adsi_prog(), adsi_status(), adsi_status2(), vm_newuser(), vm_options(), and vm_tempgreeting().

    00890 {
    00891    int bytes=0;
    00892
    00893    /* Sanity check line number */
    00894
    00895    if (page) {
    00896       if (line > 4) return -1;
    00897    } else {
    00898       if (line > 33) return -1;
    00899    }
    00900
    00901    if (line < 1)
    00902       return -1;
    00903    /* Parameter type */
    00904    buf[bytes++] = ADSI_LINE_CONTROL;
    00905
    00906    /* Reserve space for size */
    00907    bytes++;
    00908
    00909    /* Page and line */
    00910    buf[bytes++] = ((page & 0x1) << 7) | (line & 0x3f);
    00911
    00912    buf[1] = bytes - 2;
    00913    return bytes;
    00914
    00915 };

int adsi_transmit_message | ( | struct ast_channel * | chan,
|  | unsigned char * | msg,
|  | int | msglen,
|  | int | msgtype |
| ) |  |  |

Definition at line 425 of file res_adsi.c.

References adsi_transmit_message_full().

Referenced by adsi_delete(), adsi_folders(), adsi_goodbye(), adsi_load_vmail(), adsi_login(), adsi_message(), adsi_password(), adsi_prog(), adsi_status(), adsi_status2(), vm_newuser(), vm_options(), and vm_tempgreeting().

    00426 {
    00427    return adsi_transmit_message_full(chan, msg, msglen, msgtype, 1);
    00428 }

int adsi_transmit_message_full | ( | struct ast_channel * | chan,
|  | unsigned char * | msg,
|  | int | msglen,
|  | int | msgtype,
|  | int | dowait |
| ) |  |  |

Definition at line 351 of file res_adsi.c.

References __adsi_transmit_messages(), ADSI_FLAG_DATAMODE, ADSI_SWITCH_TO_DATA, ADSI_SWITCH_TO_VOICE, ast_channel::adsicpe, AST_FORMAT_ULAW, ast_log(), ast_safe_sleep(), ast_set_read_format(), ast_set_write_format(), ast_stopstream(), ast_waitfordigit(), LOG_DEBUG, LOG_WARNING, ast_channel::readformat, and ast_channel::writeformat.

Referenced by adsi_begin_download(), adsi_channel_restore(), adsi_end_download(), adsi_get_cpeid(), adsi_get_cpeinfo(), adsi_load_session(), adsi_print(), adsi_transmit_message(), and adsi_unload_session().

    00352 {
    00353    unsigned char *msgs[5] = { NULL, NULL, NULL, NULL, NULL };
    00354    int msglens[5];
    00355    int msgtypes[5];
    00356    int newdatamode;
    00357    int res;
    00358    int x;
    00359    int writeformat, readformat;
    00360    int waitforswitch = 0;
    00361
    00362    writeformat = chan->writeformat;
    00363    readformat = chan->readformat;
    00364
    00365    newdatamode = chan->adsicpe & ADSI_FLAG_DATAMODE;
    00366
    00367    for (x=0;x<msglen;x+=(msg[x+1]+2)) {
    00368       if (msg[x] == ADSI_SWITCH_TO_DATA) {
    00369          ast_log(LOG_DEBUG, "Switch to data is sent!\n");
    00370          waitforswitch++;
    00371          newdatamode = ADSI_FLAG_DATAMODE;
    00372       }
    00373
    00374       if (msg[x] == ADSI_SWITCH_TO_VOICE) {
    00375          ast_log(LOG_DEBUG, "Switch to voice is sent!\n");
    00376          waitforswitch++;
    00377          newdatamode = 0;
    00378       }
    00379    }
    00380    msgs[0] = msg;
    00381
    00382    msglens[0] = msglen;
    00383    msgtypes[0] = msgtype;
    00384
    00385    if (msglen > 253) {
    00386       ast_log(LOG_WARNING, "Can't send ADSI message of %d bytes, too large\n", msglen);
    00387       return -1;
    00388    }
    00389
    00390    ast_stopstream(chan);
    00391
    00392    if (ast_set_write_format(chan, AST_FORMAT_ULAW)) {
    00393       ast_log(LOG_WARNING, "Unable to set write format to ULAW\n");
    00394       return -1;
    00395    }
    00396
    00397    if (ast_set_read_format(chan, AST_FORMAT_ULAW)) {
    00398       ast_log(LOG_WARNING, "Unable to set read format to ULAW\n");
    00399       if (writeformat) {
    00400          if (ast_set_write_format(chan, writeformat))
    00401             ast_log(LOG_WARNING, "Unable to restore write format to %d\n", writeformat);
    00402       }
    00403       return -1;
    00404    }
    00405    res = __adsi_transmit_messages(chan, msgs, msglens, msgtypes);
    00406
    00407    if (dowait) {
    00408       ast_log(LOG_DEBUG, "Wait for switch is '%d'\n", waitforswitch);
    00409       while(waitforswitch-- && ((res = ast_waitfordigit(chan, 1000)) > 0)) { res = 0; ast_log(LOG_DEBUG, "Waiting for 'B'...\n"); }
    00410    }
    00411
    00412    if (!res)
    00413       chan->adsicpe = (chan->adsicpe & ~ADSI_FLAG_DATAMODE) | newdatamode;
    00414
    00415    if (writeformat)
    00416       ast_set_write_format(chan, writeformat);
    00417    if (readformat)
    00418       ast_set_read_format(chan, readformat);
    00419
    00420    if (!res)
    00421       res = ast_safe_sleep(chan, 100 );
    00422    return res;
    00423 }

int adsi_unload_session | ( | struct ast_channel * | chan | ) |

Definition at line 1008 of file res_adsi.c.

References adsi_disconnect_session(), ADSI_MSG_DISPLAY, adsi_transmit_message_full(), adsi_voice_mode(), and dsp.

Referenced by adsi_prog(), ast_park_call(), cpeid_exec(), and vm_execmain().

    01009 {
    01010    unsigned char dsp[256];
    01011    int bytes;
    01012
    01013    memset(dsp, 0, sizeof(dsp));
    01014
    01015    /* Connect to session */
    01016    bytes = 0;
    01017    bytes += adsi_disconnect_session(dsp + bytes);
    01018    bytes += adsi_voice_mode(dsp + bytes, 0);
    01019
    01020    /* Prepare key setup messages */
    01021    if (adsi_transmit_message_full(chan, dsp, bytes, ADSI_MSG_DISPLAY, 0))
    01022       return -1;
    01023    return 0;
    01024 }

int adsi_voice_mode | ( | unsigned char * | buf,
|  | int | when |
| ) |  |  |

Puts CPE in voice mode...

Parameters:

  | buf | Character buffer to create parameter in (must have at least 256 free)
  | when | (a time in seconds) to make the switch

Returns number of bytes added to buffer or -1 on error.

Definition at line 745 of file res_adsi.c.

References ADSI_SWITCH_TO_VOICE.

Referenced by adsi_delete(), adsi_folders(), adsi_get_cpeid(), adsi_get_cpeinfo(), adsi_goodbye(), adsi_load_vmail(), adsi_login(), adsi_message(), adsi_password(), adsi_print(), adsi_status(), adsi_status2(), adsi_unload_session(), vm_newuser(), vm_options(), and vm_tempgreeting().

    00746 {
    00747    int bytes=0;
    00748
    00749    /* Message type */
    00750    buf[bytes++] = ADSI_SWITCH_TO_VOICE;
    00751
    00752    /* Reserve space for length */
    00753    bytes++;
    00754
    00755    buf[bytes++] = when & 0x7f;
    00756
    00757    buf[1] = bytes - 2;
    00758    return bytes;
    00759
    00760 }

static int ccopy | ( | unsigned char * | dst,
|  | unsigned char * | src,
|  | int | max |
| ) |  |  | `[inline, static]`

Definition at line 430 of file res_adsi.c.

Referenced by adsi_display(), adsi_download_connect(), adsi_input_format(), and adsi_load_soft_key().

    00431 {
    00432    int x=0;
    00433    /* Carefully copy the requested data */
    00434    while ((x < max) && src[x] && (src[x] != 0xff)) {
    00435       dst[x] = src[x];
    00436       x++;
    00437    }
    00438    return x;
    00439 }

char* description | ( | void |  | ) |

Provides a description of the module.

Returns:
  a short description of your module

Definition at line 1127 of file res_adsi.c.

    01128 {
    01129    return "ADSI Resource";
    01130 }

static void init_state | ( | void |  | ) | `[static]`

Definition at line 1038 of file res_adsi.c.

References ADSI_JUST_CENT, and ADSI_MAX_INTRO.

Referenced by adsi_load().

    01039 {
    01040    int x;
    01041
    01042    for (x=0;x<ADSI_MAX_INTRO;x++)
    01043       aligns[x] = ADSI_JUST_CENT;
    01044    strncpy(intro[0], "Welcome to the", sizeof(intro[0]) - 1);
    01045    strncpy(intro[1], "Asterisk", sizeof(intro[1]) - 1);
    01046    strncpy(intro[2], "Open Source PBX", sizeof(intro[2]) - 1);
    01047    total = 3;
    01048    speeds = 0;
    01049    for (x=3;x<ADSI_MAX_INTRO;x++)
    01050       intro[x][0] = '\0';
    01051    memset(speeddial, 0, sizeof(speeddial));
    01052    alignment = ADSI_JUST_CENT;
    01053 }

char* key | ( | void |  | ) |

Returns the ASTERISK_GPL_KEY.

This returns the ASTERISK_GPL_KEY, signifiying that you agree to the terms of the GPL stated in the ASTERISK_GPL_KEY. Your module will not load if it does not return the EXACT message:

     char *key(void) {
             return ASTERISK_GPL_KEY;
     }

Returns:
  ASTERISK_GPL_KEY

Definition at line 1138 of file res_adsi.c.

References ASTERISK_GPL_KEY.

    01139 {
    01140    return ASTERISK_GPL_KEY;
    01141 }

int load_module | ( | void |  | ) |

Initialize the module.

This function is called at module load time. Put all code in here that needs to set up your module's hardware, software, registrations, etc.

Returns:
  This function should return 0 on success and non-zero on failure. If the module is not loaded successfully, Asterisk will call its unload_module() function.

Initialize the Agents module. This function is being called by Asterisk when loading the module. Among other thing it registers applications, cli commands and reads the cofiguration file.

Returns:
  int Always 0.

TE STUFF END

Definition at line 1115 of file res_adsi.c.

References adsi_load().

    01116 {
    01117    adsi_load();
    01118    return 0;
    01119 }

int reload | ( | void |  | ) |

Reload stuff.

This function is where any reload routines take place. Re-read config files, change signalling, whatever is appropriate on a reload.

Returns:
  The return value is not used.

Definition at line 1109 of file res_adsi.c.

References adsi_load().

    01110 {
    01111    adsi_load();
    01112    return 0;
    01113 }

static int str2align | ( | char * | s | ) | `[static]`

Definition at line 1026 of file res_adsi.c.

References ADSI_JUST_CENT, ADSI_JUST_IND, ADSI_JUST_LEFT, and ADSI_JUST_RIGHT.

Referenced by adsi_load().

    01027 {
    01028    if (!strncasecmp(s, "l", 1))
    01029       return ADSI_JUST_LEFT;
    01030    else if (!strncasecmp(s, "r", 1))
    01031       return ADSI_JUST_RIGHT;
    01032    else if (!strncasecmp(s, "i", 1))
    01033       return ADSI_JUST_IND;
    01034    else
    01035       return ADSI_JUST_CENT;
    01036 }

int unload_module | ( | void |  | ) |

Cleanup all module structures, sockets, etc.

This is called at exit. Any registrations and memory allocations need to be unregistered and free'd here. Nothing else will do these for you (until exit).

Returns:
  Zero on success, or non-zero on error.

Standard module functions ...

Definition at line 1121 of file res_adsi.c.

    01122 {
    01123    /* Can't unload this once we're loaded */
    01124    return -1;
    01125 }

int usecount | ( | void |  | ) |

Provides a usecount.

This function will be called by various parts of asterisk. Basically, all it has to do is to return a usecount when called. You will need to maintain your usecount within the module somewhere. The usecount should be how many channels provided by this module are in use.

Returns:
  The module's usecount.

Definition at line 1132 of file res_adsi.c.

    01133 {
    01134    /* We should never be unloaded */
    01135    return 1;
    01136 }

## Variable Documentation

int alignment = 0`[static]`

Definition at line 67 of file res_adsi.c.

int aligns[ADSI_MAX_INTRO]`[static]`

Definition at line 63 of file res_adsi.c.

char intro[ADSI_MAX_INTRO][20]`[static]`

Definition at line 62 of file res_adsi.c.

int maxretries = DEFAULT_ADSI_MAX_RETRIES`[static]`

Definition at line 57 of file res_adsi.c.

Referenced by ast_ivr_menu_run_internal(), and privacy_exec().

char speeddial[ADSI_MAX_SPEED_DIAL][3][20]`[static]`

Definition at line 65 of file res_adsi.c.

int speeds = 0`[static]`

Definition at line 918 of file res_adsi.c.

int total = 0`[static]`

Definition at line 917 of file res_adsi.c.

Referenced by ast_app_getvoice(), ast_cdr_serialize_variables(), conf_cmd(), manager_sip_show_peers(), pbx_builtin_serialize_variables(), and send_sound().