Sat Aug 6 00:39:40 2011

Asterisk developer's documentation


cdr_tds.c File Reference

FreeTDS CDR logger. More...

#include "asterisk.h"
#include <sys/types.h>
#include <stdio.h>
#include <string.h>
#include <stdlib.h>
#include <unistd.h>
#include <time.h>
#include <math.h>
#include <tds.h>
#include <tdsconvert.h>
#include <ctype.h>
#include "asterisk/config.h"
#include "asterisk/options.h"
#include "asterisk/channel.h"
#include "asterisk/cdr.h"
#include "asterisk/module.h"
#include "asterisk/logger.h"

Go to the source code of this file.

Defines

#define DATE_FORMAT   "%Y/%m/%d %T"

Functions

static void __reg_module (void)
static void __unreg_module (void)
static char * anti_injection (const char *, int)
static void get_date (char *, size_t, struct timeval)
static int load_module (void)
static int mssql_connect (void)
static int mssql_disconnect (void)
static int reload (void)
static int tds_load_module (void)
static int tds_log (struct ast_cdr *cdr)
static int tds_unload_module (void)
static int unload_module (void)

Variables

static struct ast_module_info __mod_info = { .name = AST_MODULE, .flags = AST_MODFLAG_DEFAULT | AST_MODFLAG_BUILDSUM, .description = "MSSQL CDR Backend" , .key = "This paragraph is copyright (c) 2006 by Digium, Inc. \In order for your module to load, it must return this \key via a function called \"key\". Any code which \includes this paragraph must be licensed under the GNU \General Public License version 2 or later (at your \option). In addition to Digium's general reservations \of rights, Digium expressly reserves the right to \allow other parties to license this paragraph under \different terms. Any use of Digium, Inc. trademarks or \logos (including \"Asterisk\" or \"Digium\") without \express written permission of Digium, Inc. is prohibited.\n" , .buildopt_sum = "361d7bb937402d51e4658efb5b4d76e4" , .load = load_module, .unload = unload_module, .reload = reload, }
static const struct ast_module_infoast_module_info = &__mod_info
static char * charset = NULL
static char * config = "cdr_tds.conf"
static int connected = 0
static TDSCONTEXT * context
static char * dbname = NULL
static char * dbuser = NULL
static int has_userfield = 0
static char * hostname = NULL
static char * language = NULL
static TDSLOGIN * login
static char * name = "mssql"
static char * password = NULL
static char * table = NULL
static TDSSOCKET * tds
static ast_mutex_t tds_lock = ((ast_mutex_t) PTHREAD_MUTEX_INITIALIZER )


Detailed Description

FreeTDS CDR logger.

See also

Definition in file cdr_tds.c.


Define Documentation

#define DATE_FORMAT   "%Y/%m/%d %T"

 *
 * Table Structure for `cdr`
 *
 * Created on: 05/20/2004 16:16
 * Last changed on: 07/27/2004 20:01

CREATE TABLE [dbo].[cdr] (
	[accountcode] [varchar] (20) NULL ,
	[src] [varchar] (80) NULL ,
	[dst] [varchar] (80) NULL ,
	[dcontext] [varchar] (80) NULL ,
	[clid] [varchar] (80) NULL ,
	[channel] [varchar] (80) NULL ,
	[dstchannel] [varchar] (80) NULL ,
	[lastapp] [varchar] (80) NULL ,
	[lastdata] [varchar] (80) NULL ,
	[start] [datetime] NULL ,
	[answer] [datetime] NULL ,
	[end] [datetime] NULL ,
	[duration] [int] NULL ,
	[billsec] [int] NULL ,
	[disposition] [varchar] (20) NULL ,
	[amaflags] [varchar] (16) NULL ,
	[uniqueid] [varchar] (32) NULL ,
	[userfield] [varchar] (256) NULL
) ON [PRIMARY]

Definition at line 90 of file cdr_tds.c.


Function Documentation

static void __reg_module ( void   )  [static]

Definition at line 630 of file cdr_tds.c.

static void __unreg_module ( void   )  [static]

Definition at line 630 of file cdr_tds.c.

static char * anti_injection ( const char *  ,
int   
) [static]

Definition at line 318 of file cdr_tds.c.

References ast_log(), LOG_ERROR, and malloc.

Referenced by tds_log().

00319 {
00320    /* Reference to http://www.nextgenss.com/papers/advanced_sql_injection.pdf */
00321 
00322    char *buf;
00323    char *buf_ptr, *srh_ptr;
00324    char *known_bad[] = {"select", "insert", "update", "delete", "drop", ";", "--", "\0"};
00325    int idx;
00326 
00327    if ((buf = malloc(len + 1)) == NULL)
00328    {
00329       ast_log(LOG_ERROR, "cdr_tds:  Out of memory error\n");
00330       return NULL;
00331    }
00332    memset(buf, 0, len);
00333 
00334    buf_ptr = buf;
00335 
00336    /* Escape single quotes */
00337    for (; *str && strlen(buf) < len; str++)
00338    {
00339       if (*str == '\'')
00340          *buf_ptr++ = '\'';
00341       *buf_ptr++ = *str;
00342    }
00343    *buf_ptr = '\0';
00344 
00345    /* Erase known bad input */
00346    for (idx=0; *known_bad[idx]; idx++)
00347    {
00348       while((srh_ptr = strcasestr(buf, known_bad[idx])))
00349       {
00350          memmove(srh_ptr, srh_ptr+strlen(known_bad[idx]), strlen(srh_ptr+strlen(known_bad[idx]))+1);
00351       }
00352    }
00353 
00354    return buf;
00355 }

static void get_date ( char *  ,
size_t  ,
struct  timeval 
) [static]

Definition at line 357 of file cdr_tds.c.

References ast_copy_string(), ast_localtime(), ast_tvzero(), DATE_FORMAT, and t.

00358 {
00359    struct tm tm;
00360    time_t t;
00361    char buf[80];
00362 
00363    /* To make sure we have date variable if not insert null to SQL */
00364    if (!ast_tvzero(tv))
00365    {
00366       t = tv.tv_sec;
00367       ast_localtime(&t, &tm, NULL);
00368       strftime(buf, sizeof(buf), DATE_FORMAT, &tm);
00369       snprintf(dateField, length, "'%s'", buf);
00370    }
00371    else
00372    {
00373       ast_copy_string(dateField, "null", length);
00374    }
00375 }

static int load_module ( void   )  [static]

Definition at line 613 of file cdr_tds.c.

References AST_MODULE_LOAD_DECLINE, AST_MODULE_LOAD_SUCCESS, and tds_load_module().

00614 {
00615    if(!tds_load_module())
00616       return AST_MODULE_LOAD_DECLINE;
00617    else 
00618       return AST_MODULE_LOAD_SUCCESS;
00619 }

static int mssql_connect ( void   )  [static]

Definition at line 399 of file cdr_tds.c.

References ast_log(), LOG_ERROR, LOG_NOTICE, and mssql_disconnect().

Referenced by tds_load_module(), and tds_log().

00400 {
00401 #if (defined(FREETDS_0_63) || defined(FREETDS_0_64))
00402    TDSCONNECTION *connection = NULL;
00403 #else
00404    TDSCONNECTINFO *connection = NULL;
00405 #endif
00406    char query[512];
00407 
00408    /* Connect to M$SQL Server */
00409    if (!(login = tds_alloc_login()))
00410    {
00411       ast_log(LOG_ERROR, "tds_alloc_login() failed.\n");
00412       return -1;
00413    }
00414    
00415    tds_set_server(login, hostname);
00416    tds_set_user(login, dbuser);
00417    tds_set_passwd(login, password);
00418    tds_set_app(login, "TSQL");
00419    tds_set_library(login, "TDS-Library");
00420 #ifndef FREETDS_PRE_0_62
00421    tds_set_client_charset(login, charset);
00422 #endif
00423    tds_set_language(login, language);
00424    tds_set_packet(login, 512);
00425    tds_set_version(login, 7, 0);
00426 
00427 #ifdef FREETDS_0_64
00428    if (!(context = tds_alloc_context(NULL)))
00429 #else
00430    if (!(context = tds_alloc_context()))
00431 #endif
00432    {
00433       ast_log(LOG_ERROR, "tds_alloc_context() failed.\n");
00434       goto connect_fail;
00435    }
00436 
00437    if (!(tds = tds_alloc_socket(context, 512))) {
00438       ast_log(LOG_ERROR, "tds_alloc_socket() failed.\n");
00439       goto connect_fail;
00440    }
00441 
00442    tds_set_parent(tds, NULL);
00443    connection = tds_read_config_info(tds, login, context->locale);
00444    if (!connection)
00445    {
00446       ast_log(LOG_ERROR, "tds_read_config() failed.\n");
00447       goto connect_fail;
00448    }
00449 
00450    if (tds_connect(tds, connection) == TDS_FAIL)
00451    {
00452       ast_log(LOG_ERROR, "Failed to connect to MSSQL server.\n");
00453       tds = NULL; /* freed by tds_connect() on error */
00454 #if (defined(FREETDS_0_63) || defined(FREETDS_0_64))
00455       tds_free_connection(connection);
00456 #else
00457       tds_free_connect(connection);
00458 #endif
00459       connection = NULL;
00460       goto connect_fail;
00461    }
00462 #if (defined(FREETDS_0_63) || defined(FREETDS_0_64))
00463    tds_free_connection(connection);
00464 #else
00465    tds_free_connect(connection);
00466 #endif
00467    connection = NULL;
00468 
00469    snprintf(query, sizeof(query), "USE %s", dbname);
00470 #ifdef FREETDS_PRE_0_62
00471    if ((tds_submit_query(tds, query) != TDS_SUCCEED) || (tds_process_simple_query(tds, &result_type) != TDS_SUCCEED || result_type != TDS_CMD_SUCCEED))
00472 #else
00473    if ((tds_submit_query(tds, query) != TDS_SUCCEED) || (tds_process_simple_query(tds) != TDS_SUCCEED))
00474 #endif
00475    {
00476       ast_log(LOG_ERROR, "Could not change database (%s)\n", dbname);
00477       goto connect_fail;
00478    }
00479 
00480    snprintf(query, sizeof(query), "SELECT 1 FROM %s WHERE 1 = 0", table);
00481 #ifdef FREETDS_PRE_0_62
00482    if ((tds_submit_query(tds, query) != TDS_SUCCEED) || (tds_process_simple_query(tds, &result_type) != TDS_SUCCEED || result_type != TDS_CMD_SUCCEED))
00483 #else
00484    if ((tds_submit_query(tds, query) != TDS_SUCCEED) || (tds_process_simple_query(tds) != TDS_SUCCEED))
00485 #endif
00486    {
00487       ast_log(LOG_ERROR, "Could not find table '%s' in database '%s'\n", table, dbname);
00488       goto connect_fail;
00489    }
00490 
00491    has_userfield = 1;
00492    snprintf(query, sizeof(query), "SELECT userfield FROM %s WHERE 1 = 0", table);
00493 #ifdef FREETDS_PRE_0_62
00494    if ((tds_submit_query(tds, query) != TDS_SUCCEED) || (tds_process_simple_query(tds, &result_type) != TDS_SUCCEED || result_type != TDS_CMD_SUCCEED))
00495 #else
00496    if ((tds_submit_query(tds, query) != TDS_SUCCEED) || (tds_process_simple_query(tds) != TDS_SUCCEED))
00497 #endif
00498    {
00499       ast_log(LOG_NOTICE, "Unable to find 'userfield' column in table '%s'\n", table);
00500       has_userfield = 0;
00501    }
00502 
00503    connected = 1;
00504    return 0;
00505 
00506 connect_fail:
00507    mssql_disconnect();
00508    return -1;
00509 }

static int mssql_disconnect ( void   )  [static]

Definition at line 377 of file cdr_tds.c.

Referenced by mssql_connect(), tds_log(), and tds_unload_module().

00378 {
00379    if (tds) {
00380       tds_free_socket(tds);
00381       tds = NULL;
00382    }
00383 
00384    if (context) {
00385       tds_free_context(context);
00386       context = NULL;
00387    }
00388 
00389    if (login) {
00390       tds_free_login(login);
00391       login = NULL;
00392    }
00393 
00394    connected = 0;
00395 
00396    return 0;
00397 }

static int reload ( void   )  [static]

Definition at line 607 of file cdr_tds.c.

References tds_load_module(), and tds_unload_module().

00608 {
00609    tds_unload_module();
00610    return tds_load_module();
00611 }

static int tds_load_module ( void   )  [static]

Definition at line 528 of file cdr_tds.c.

References ast_cdr_register(), ast_config_destroy(), ast_config_load(), ast_log(), ast_variable_browse(), ast_variable_retrieve(), LOG_DEBUG, LOG_ERROR, LOG_NOTICE, mssql_connect(), strdup, tds_log(), and var.

Referenced by load_module(), and reload().

00529 {
00530    int res = 0;
00531    struct ast_config *cfg;
00532    struct ast_variable *var;
00533    const char *ptr = NULL;
00534 #ifdef FREETDS_PRE_0_62
00535    TDS_INT result_type;
00536 #endif
00537 
00538    cfg = ast_config_load(config);
00539    if (!cfg) {
00540       ast_log(LOG_NOTICE, "Unable to load config for MSSQL CDR's: %s\n", config);
00541       return 0;
00542    }
00543 
00544    var = ast_variable_browse(cfg, "global");
00545    if (!var) /* nothing configured */ {
00546       ast_config_destroy(cfg);
00547       return 0;
00548    }
00549    
00550    ptr = ast_variable_retrieve(cfg, "global", "hostname");
00551    if (ptr)
00552       hostname = strdup(ptr);
00553    else
00554       ast_log(LOG_ERROR,"Database server hostname not specified.\n");
00555 
00556    ptr = ast_variable_retrieve(cfg, "global", "dbname");
00557    if (ptr)
00558       dbname = strdup(ptr);
00559    else
00560       ast_log(LOG_ERROR,"Database dbname not specified.\n");
00561 
00562    ptr = ast_variable_retrieve(cfg, "global", "user");
00563    if (ptr)
00564       dbuser = strdup(ptr);
00565    else
00566       ast_log(LOG_ERROR,"Database dbuser not specified.\n");
00567 
00568    ptr = ast_variable_retrieve(cfg, "global", "password");
00569    if (ptr)
00570       password = strdup(ptr);
00571    else
00572       ast_log(LOG_ERROR,"Database password not specified.\n");
00573 
00574    ptr = ast_variable_retrieve(cfg, "global", "charset");
00575    if (ptr)
00576       charset = strdup(ptr);
00577    else
00578       charset = strdup("iso_1");
00579 
00580    ptr = ast_variable_retrieve(cfg, "global", "language");
00581    if (ptr)
00582       language = strdup(ptr);
00583    else
00584       language = strdup("us_english");
00585 
00586    ptr = ast_variable_retrieve(cfg,"global","table");
00587    if (ptr == NULL) {
00588       ast_log(LOG_DEBUG,"cdr_tds: table not specified.  Assuming cdr\n");
00589       ptr = "cdr";
00590    }
00591    table = strdup(ptr);
00592 
00593    ast_config_destroy(cfg);
00594 
00595    mssql_connect();
00596 
00597    /* Register MSSQL CDR handler */
00598    res = ast_cdr_register(name, ast_module_info->description, tds_log);
00599    if (res)
00600    {
00601       ast_log(LOG_ERROR, "Unable to register MSSQL CDR handling\n");
00602    }
00603 
00604    return res;
00605 }

static int tds_log ( struct ast_cdr cdr  )  [static]

Definition at line 113 of file cdr_tds.c.

References ast_cdr::accountcode, accountcode, ast_cdr::amaflags, ast_cdr::answer, answer, anti_injection(), ast_cdr_disp2str(), ast_cdr_flags2str(), ast_log(), AST_MAX_USER_FIELD, ast_mutex_lock(), ast_mutex_unlock(), ast_cdr::billsec, ast_cdr::channel, ast_cdr::clid, ast_cdr::dcontext, ast_cdr::disposition, ast_cdr::dst, ast_cdr::dstchannel, ast_cdr::duration, ast_cdr::end, free, get_date(), ast_cdr::lastapp, ast_cdr::lastdata, LOG_ERROR, LOG_WARNING, mssql_connect(), mssql_disconnect(), ast_cdr::src, ast_cdr::start, tds_lock, ast_cdr::uniqueid, and ast_cdr::userfield.

Referenced by tds_load_module().

00114 {
00115    char sqlcmd[2048], start[80], answer[80], end[80];
00116    char *accountcode, *src, *dst, *dcontext, *clid, *channel, *dstchannel, *lastapp, *lastdata, *uniqueid, *userfield = NULL;
00117    int res = 0;
00118    int retried = 0;
00119 #ifdef FREETDS_PRE_0_62
00120    TDS_INT result_type;
00121 #endif
00122 
00123    ast_mutex_lock(&tds_lock);
00124 
00125    memset(sqlcmd, 0, 2048);
00126 
00127    accountcode = anti_injection(cdr->accountcode, 20);
00128    src = anti_injection(cdr->src, 80);
00129    dst = anti_injection(cdr->dst, 80);
00130    dcontext = anti_injection(cdr->dcontext, 80);
00131    clid = anti_injection(cdr->clid, 80);
00132    channel = anti_injection(cdr->channel, 80);
00133    dstchannel = anti_injection(cdr->dstchannel, 80);
00134    lastapp = anti_injection(cdr->lastapp, 80);
00135    lastdata = anti_injection(cdr->lastdata, 80);
00136    uniqueid = anti_injection(cdr->uniqueid, 32);
00137 
00138    if (has_userfield) {
00139       userfield = anti_injection(cdr->userfield, AST_MAX_USER_FIELD);
00140    }
00141 
00142    get_date(start, sizeof(start), cdr->start);
00143    get_date(answer, sizeof(answer), cdr->answer);
00144    get_date(end, sizeof(end), cdr->end);
00145 
00146    if (has_userfield) {
00147       snprintf(
00148          sqlcmd,
00149          sizeof(sqlcmd),
00150          "INSERT INTO %s "
00151          "("
00152             "accountcode, "
00153             "src, "
00154             "dst, "
00155             "dcontext, "
00156             "clid, "
00157             "channel, "
00158             "dstchannel, "
00159             "lastapp, "
00160             "lastdata, "
00161             "start, "
00162             "answer, "
00163             "[end], "
00164             "duration, "
00165             "billsec, "
00166             "disposition, "
00167             "amaflags, "
00168             "uniqueid, "
00169             "userfield"
00170          ") "
00171          "VALUES "
00172          "("
00173             "'%s', " /* accountcode */
00174             "'%s', " /* src */
00175             "'%s', " /* dst */
00176             "'%s', " /* dcontext */
00177             "'%s', " /* clid */
00178             "'%s', " /* channel */
00179             "'%s', " /* dstchannel */
00180             "'%s', " /* lastapp */
00181             "'%s', " /* lastdata */
00182             "%s, "      /* start */
00183             "%s, "      /* answer */
00184             "%s, "      /* end */
00185             "%ld, "     /* duration */
00186             "%ld, "     /* billsec */
00187             "'%s', " /* disposition */
00188             "'%s', " /* amaflags */
00189             "'%s', " /* uniqueid */
00190             "'%s'"      /* userfield */
00191          ")",
00192          table,
00193          accountcode,
00194          src,
00195          dst,
00196          dcontext,
00197          clid,
00198          channel,
00199          dstchannel,
00200          lastapp,
00201          lastdata,
00202          start,
00203          answer,
00204          end,
00205          cdr->duration,
00206          cdr->billsec,
00207          ast_cdr_disp2str(cdr->disposition),
00208          ast_cdr_flags2str(cdr->amaflags),
00209          uniqueid,
00210          userfield
00211          );
00212    } else {
00213       snprintf(
00214          sqlcmd,
00215          sizeof(sqlcmd),
00216          "INSERT INTO %s "
00217          "("
00218             "accountcode, "
00219             "src, "
00220             "dst, "
00221             "dcontext, "
00222             "clid, "
00223             "channel, "
00224             "dstchannel, "
00225             "lastapp, "
00226             "lastdata, "
00227             "start, "
00228             "answer, "
00229             "[end], "
00230             "duration, "
00231             "billsec, "
00232             "disposition, "
00233             "amaflags, "
00234             "uniqueid"
00235          ") "
00236          "VALUES "
00237          "("
00238             "'%s', " /* accountcode */
00239             "'%s', " /* src */
00240             "'%s', " /* dst */
00241             "'%s', " /* dcontext */
00242             "'%s', " /* clid */
00243             "'%s', " /* channel */
00244             "'%s', " /* dstchannel */
00245             "'%s', " /* lastapp */
00246             "'%s', " /* lastdata */
00247             "%s, "      /* start */
00248             "%s, "      /* answer */
00249             "%s, "      /* end */
00250             "%ld, "     /* duration */
00251             "%ld, "     /* billsec */
00252             "'%s', " /* disposition */
00253             "'%s', " /* amaflags */
00254             "'%s'"      /* uniqueid */
00255          ")",
00256          table,
00257          accountcode,
00258          src,
00259          dst,
00260          dcontext,
00261          clid,
00262          channel,
00263          dstchannel,
00264          lastapp,
00265          lastdata,
00266          start,
00267          answer,
00268          end,
00269          cdr->duration,
00270          cdr->billsec,
00271          ast_cdr_disp2str(cdr->disposition),
00272          ast_cdr_flags2str(cdr->amaflags),
00273          uniqueid
00274          );
00275    }
00276 
00277    do {
00278       if (!connected) {
00279          if (mssql_connect())
00280             ast_log(LOG_ERROR, "Failed to reconnect to SQL database.\n");
00281          else
00282             ast_log(LOG_WARNING, "Reconnected to SQL database.\n");
00283 
00284          retried = 1;   /* note that we have now tried */
00285       }
00286 
00287 #ifdef FREETDS_PRE_0_62
00288       if (!connected || (tds_submit_query(tds, sqlcmd) != TDS_SUCCEED) || (tds_process_simple_query(tds, &result_type) != TDS_SUCCEED || result_type != TDS_CMD_SUCCEED))
00289 #else
00290       if (!connected || (tds_submit_query(tds, sqlcmd) != TDS_SUCCEED) || (tds_process_simple_query(tds) != TDS_SUCCEED))
00291 #endif
00292       {
00293          ast_log(LOG_ERROR, "Failed to insert Call Data Record into SQL database.\n");
00294 
00295          mssql_disconnect();  /* this is ok even if we are already disconnected */
00296       }
00297    } while (!connected && !retried);
00298 
00299    free(accountcode);
00300    free(src);
00301    free(dst);
00302    free(dcontext);
00303    free(clid);
00304    free(channel);
00305    free(dstchannel);
00306    free(lastapp);
00307    free(lastdata);
00308    free(uniqueid);
00309    if (userfield) {
00310       free(userfield);
00311    }
00312 
00313    ast_mutex_unlock(&tds_lock);
00314 
00315    return res;
00316 }

static int tds_unload_module ( void   )  [static]

Definition at line 511 of file cdr_tds.c.

References ast_cdr_unregister(), free, and mssql_disconnect().

Referenced by reload(), and unload_module().

00512 {
00513    mssql_disconnect();
00514 
00515    ast_cdr_unregister(name);
00516 
00517    if (hostname) free(hostname);
00518    if (dbname) free(dbname);
00519    if (dbuser) free(dbuser);
00520    if (password) free(password);
00521    if (charset) free(charset);
00522    if (language) free(language);
00523    if (table) free(table);
00524 
00525    return 0;
00526 }

static int unload_module ( void   )  [static]

Definition at line 621 of file cdr_tds.c.

References tds_unload_module().

00622 {
00623    return tds_unload_module();
00624 }


Variable Documentation

struct ast_module_info __mod_info = { .name = AST_MODULE, .flags = AST_MODFLAG_DEFAULT | AST_MODFLAG_BUILDSUM, .description = "MSSQL CDR Backend" , .key = "This paragraph is copyright (c) 2006 by Digium, Inc. \In order for your module to load, it must return this \key via a function called \"key\". Any code which \includes this paragraph must be licensed under the GNU \General Public License version 2 or later (at your \option). In addition to Digium's general reservations \of rights, Digium expressly reserves the right to \allow other parties to license this paragraph under \different terms. Any use of Digium, Inc. trademarks or \logos (including \"Asterisk\" or \"Digium\") without \express written permission of Digium, Inc. is prohibited.\n" , .buildopt_sum = "361d7bb937402d51e4658efb5b4d76e4" , .load = load_module, .unload = unload_module, .reload = reload, } [static]

Definition at line 630 of file cdr_tds.c.

const struct ast_module_info* ast_module_info = &__mod_info [static]

Definition at line 630 of file cdr_tds.c.

char * charset = NULL [static]

Definition at line 95 of file cdr_tds.c.

char* config = "cdr_tds.conf" [static]

Definition at line 93 of file cdr_tds.c.

int connected = 0 [static]

Definition at line 98 of file cdr_tds.c.

TDSCONTEXT* context [static]

Definition at line 105 of file cdr_tds.c.

char * dbname = NULL [static]

Definition at line 95 of file cdr_tds.c.

Referenced by lookupcidname_exec(), parse_config(), pgsql_reconnect(), and realtime_pgsql_status().

char * dbuser = NULL [static]

Definition at line 95 of file cdr_tds.c.

Referenced by parse_config(), pgsql_reconnect(), and realtime_pgsql_status().

int has_userfield = 0 [static]

Definition at line 99 of file cdr_tds.c.

char* hostname = NULL [static]

Definition at line 95 of file cdr_tds.c.

char * language = NULL [static]

Definition at line 95 of file cdr_tds.c.

TDSLOGIN* login [static]

Definition at line 104 of file cdr_tds.c.

char* name = "mssql" [static]

Definition at line 92 of file cdr_tds.c.

char * password = NULL [static]

Definition at line 95 of file cdr_tds.c.

char* table = NULL [static]

Definition at line 96 of file cdr_tds.c.

TDSSOCKET* tds [static]

Definition at line 103 of file cdr_tds.c.

ast_mutex_t tds_lock = ((ast_mutex_t) PTHREAD_MUTEX_INITIALIZER ) [static]

Definition at line 101 of file cdr_tds.c.

Referenced by tds_log().


Generated on Sat Aug 6 00:39:40 2011 for Asterisk - the Open Source PBX by  doxygen 1.4.7