Sat Aug 6 00:40:03 2011

Asterisk developer's documentation


res_config_odbc.c File Reference

odbc+odbc plugin for portable configuration engine More...

#include "asterisk.h"
#include <stdio.h>
#include <stdlib.h>
#include <unistd.h>
#include <string.h>
#include "asterisk/file.h"
#include "asterisk/logger.h"
#include "asterisk/channel.h"
#include "asterisk/pbx.h"
#include "asterisk/config.h"
#include "asterisk/module.h"
#include "asterisk/lock.h"
#include "asterisk/options.h"
#include "asterisk/res_odbc.h"
#include "asterisk/utils.h"
#include "asterisk/stringfields.h"

Go to the source code of this file.

Data Structures

struct  config_odbc_obj
struct  custom_prepare_struct

Functions

static void __reg_module (void)
static void __unreg_module (void)
static struct ast_configconfig_odbc (const char *database, const char *table, const char *file, struct ast_config *cfg, int withcomments)
static SQLHSTMT config_odbc_prepare (struct odbc_obj *obj, void *data)
static SQLHSTMT custom_prepare (struct odbc_obj *obj, void *data)
static void decode_chunk (char *chunk)
static int load_module (void)
static struct ast_configrealtime_multi_odbc (const char *database, const char *table, va_list ap)
static struct ast_variablerealtime_odbc (const char *database, const char *table, va_list ap)
static int unload_module (void)
static int update_odbc (const char *database, const char *table, const char *keyfield, const char *lookup, va_list ap)

Variables

static struct ast_module_info __mod_info = { .name = AST_MODULE, .flags = AST_MODFLAG_DEFAULT | AST_MODFLAG_BUILDSUM, .description = "ODBC Configuration" , .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, }
static const struct ast_module_infoast_module_info = &__mod_info
static struct ast_config_engine odbc_engine


Detailed Description

odbc+odbc plugin for portable configuration engine

Author:
Mark Spencer <markster@digium.com>

Anthony Minessale II <anthmct@yahoo.com>

Definition in file res_config_odbc.c.


Function Documentation

static void __reg_module ( void   )  [static]

Definition at line 636 of file res_config_odbc.c.

static void __unreg_module ( void   )  [static]

Definition at line 636 of file res_config_odbc.c.

static struct ast_config* config_odbc ( const char *  database,
const char *  table,
const char *  file,
struct ast_config cfg,
int  withcomments 
) [static]

Definition at line 525 of file res_config_odbc.c.

References ast_build_string(), ast_category_append(), ast_category_new(), ast_config_get_current_category(), ast_config_internal_load(), ast_log(), ast_odbc_prepare_and_execute(), ast_odbc_release_obj(), ast_odbc_request_obj(), ast_variable_append(), ast_variable_new(), config_odbc_prepare(), last, LOG_NOTICE, and LOG_WARNING.

00526 {
00527    struct ast_variable *new_v;
00528    struct ast_category *cur_cat;
00529    int res = 0;
00530    struct odbc_obj *obj;
00531    char sqlbuf[1024] = "";
00532    char *sql = sqlbuf;
00533    size_t sqlleft = sizeof(sqlbuf);
00534    unsigned int last_cat_metric = 0;
00535    SQLSMALLINT rowcount = 0;
00536    SQLHSTMT stmt;
00537    char last[128] = "";
00538    struct config_odbc_obj q;
00539 
00540    memset(&q, 0, sizeof(q));
00541 
00542    if (!file || !strcmp (file, "res_config_odbc.conf"))
00543       return NULL;      /* cant configure myself with myself ! */
00544 
00545    obj = ast_odbc_request_obj(database, 0);
00546    if (!obj)
00547       return NULL;
00548 
00549    ast_build_string(&sql, &sqlleft, "SELECT cat_metric, category, var_name, var_val FROM %s ", table);
00550    ast_build_string(&sql, &sqlleft, "WHERE filename='%s' AND commented=0 ", file);
00551    ast_build_string(&sql, &sqlleft, "ORDER BY cat_metric DESC, var_metric ASC, category, var_name ");
00552    q.sql = sqlbuf;
00553 
00554    stmt = ast_odbc_prepare_and_execute(obj, config_odbc_prepare, &q);
00555 
00556    if (!stmt) {
00557       ast_log(LOG_WARNING, "SQL select error!\n[%s]\n\n", sql);
00558       ast_odbc_release_obj(obj);
00559       return NULL;
00560    }
00561 
00562    res = SQLNumResultCols(stmt, &rowcount);
00563 
00564    if ((res != SQL_SUCCESS) && (res != SQL_SUCCESS_WITH_INFO)) {
00565       ast_log(LOG_WARNING, "SQL NumResultCols error!\n[%s]\n\n", sql);
00566       SQLFreeHandle(SQL_HANDLE_STMT, stmt);
00567       ast_odbc_release_obj(obj);
00568       return NULL;
00569    }
00570 
00571    if (!rowcount) {
00572       ast_log(LOG_NOTICE, "found nothing\n");
00573       ast_odbc_release_obj(obj);
00574       return cfg;
00575    }
00576 
00577    cur_cat = ast_config_get_current_category(cfg);
00578 
00579    while ((res = SQLFetch(stmt)) != SQL_NO_DATA) {
00580       if (!strcmp (q.var_name, "#include")) {
00581          if (!ast_config_internal_load(q.var_val, cfg, 0)) {
00582             SQLFreeHandle(SQL_HANDLE_STMT, stmt);
00583             ast_odbc_release_obj(obj);
00584             return NULL;
00585          }
00586          continue;
00587       } 
00588       if (strcmp(last, q.category) || last_cat_metric != q.cat_metric) {
00589          cur_cat = ast_category_new(q.category);
00590          if (!cur_cat) {
00591             ast_log(LOG_WARNING, "Out of memory!\n");
00592             break;
00593          }
00594          strcpy(last, q.category);
00595          last_cat_metric   = q.cat_metric;
00596          ast_category_append(cfg, cur_cat);
00597       }
00598 
00599       new_v = ast_variable_new(q.var_name, q.var_val);
00600       ast_variable_append(cur_cat, new_v);
00601    }
00602 
00603    SQLFreeHandle(SQL_HANDLE_STMT, stmt);
00604    ast_odbc_release_obj(obj);
00605    return cfg;
00606 }

static SQLHSTMT config_odbc_prepare ( struct odbc_obj obj,
void *  data 
) [static]

Definition at line 496 of file res_config_odbc.c.

References ast_verbose(), config_odbc_obj::cat_metric, config_odbc_obj::category, odbc_obj::con, config_odbc_obj::err, option_verbose, config_odbc_obj::sql, config_odbc_obj::var_name, config_odbc_obj::var_val, and VERBOSE_PREFIX_4.

Referenced by config_odbc().

00497 {
00498    struct config_odbc_obj *q = data;
00499    SQLHSTMT sth;
00500    int res;
00501 
00502    res = SQLAllocHandle(SQL_HANDLE_STMT, obj->con, &sth);
00503    if ((res != SQL_SUCCESS) && (res != SQL_SUCCESS_WITH_INFO)) {
00504       if (option_verbose > 3)
00505          ast_verbose( VERBOSE_PREFIX_4 "Failure in AllocStatement %d\n", res);
00506       return NULL;
00507    }
00508 
00509    res = SQLPrepare(sth, (unsigned char *)q->sql, SQL_NTS);
00510    if ((res != SQL_SUCCESS) && (res != SQL_SUCCESS_WITH_INFO)) {
00511       if (option_verbose > 3)
00512          ast_verbose( VERBOSE_PREFIX_4 "Error in PREPARE %d\n", res);
00513       SQLFreeHandle(SQL_HANDLE_STMT, sth);
00514       return NULL;
00515    }
00516 
00517    SQLBindCol(sth, 1, SQL_C_ULONG, &q->cat_metric, sizeof(q->cat_metric), &q->err);
00518    SQLBindCol(sth, 2, SQL_C_CHAR, q->category, sizeof(q->category), &q->err);
00519    SQLBindCol(sth, 3, SQL_C_CHAR, q->var_name, sizeof(q->var_name), &q->err);
00520    SQLBindCol(sth, 4, SQL_C_CHAR, q->var_val, sizeof(q->var_val), &q->err);
00521 
00522    return sth;
00523 }

static SQLHSTMT custom_prepare ( struct odbc_obj obj,
void *  data 
) [static]

Definition at line 77 of file res_config_odbc.c.

References custom_prepare_struct::ap, ast_log(), ast_string_field_set, ast_strlen_zero(), odbc_obj::con, custom_prepare_struct::encoding, encoding, custom_prepare_struct::extra, LOG_WARNING, and custom_prepare_struct::sql.

Referenced by realtime_multi_odbc(), realtime_odbc(), and update_odbc().

00078 {
00079    int res, x = 1;
00080    struct custom_prepare_struct *cps = data;
00081    const char *newparam, *newval;
00082    char encodebuf[1024];
00083    SQLHSTMT stmt;
00084    va_list ap;
00085 
00086    va_copy(ap, cps->ap);
00087 
00088    res = SQLAllocHandle(SQL_HANDLE_STMT, obj->con, &stmt);
00089    if ((res != SQL_SUCCESS) && (res != SQL_SUCCESS_WITH_INFO)) {
00090       ast_log(LOG_WARNING, "SQL Alloc Handle failed!\n");
00091       return NULL;
00092    }
00093 
00094    res = SQLPrepare(stmt, (unsigned char *)cps->sql, SQL_NTS);
00095    if ((res != SQL_SUCCESS) && (res != SQL_SUCCESS_WITH_INFO)) {
00096       ast_log(LOG_WARNING, "SQL Prepare failed![%s]\n", cps->sql);
00097       SQLFreeHandle (SQL_HANDLE_STMT, stmt);
00098       return NULL;
00099    }
00100 
00101    while ((newparam = va_arg(ap, const char *))) {
00102       newval = va_arg(ap, const char *);
00103       if (strchr(newval, ';') || strchr(newval, '^')) {
00104          char *eptr = encodebuf;
00105          const char *vptr = newval;
00106          for (; *vptr && eptr < encodebuf + sizeof(encodebuf); vptr++) {
00107             if (strchr("^;", *vptr)) {
00108                /* We use ^XX, instead of %XX because '%' is a special character in SQL */
00109                snprintf(eptr, encodebuf + sizeof(encodebuf) - eptr, "^%02hhX", *vptr);
00110                eptr += 3;
00111             } else {
00112                *eptr++ = *vptr;
00113             }
00114          }
00115          if (eptr < encodebuf + sizeof(encodebuf)) {
00116             *eptr = '\0';
00117          } else {
00118             encodebuf[sizeof(encodebuf) - 1] = '\0';
00119          }
00120          ast_string_field_set(cps, encoding[x], encodebuf);
00121          newval = cps->encoding[x];
00122       }
00123       SQLBindParameter(stmt, x++, SQL_PARAM_INPUT, SQL_C_CHAR, SQL_CHAR, strlen(newval), 0, (void *)newval, 0, NULL);
00124    }
00125    va_end(ap);
00126 
00127    if (!ast_strlen_zero(cps->extra))
00128       SQLBindParameter(stmt, x++, SQL_PARAM_INPUT, SQL_C_CHAR, SQL_CHAR, strlen(cps->extra), 0, (void *)cps->extra, 0, NULL);
00129    return stmt;
00130 }

static void decode_chunk ( char *  chunk  )  [static]

Definition at line 67 of file res_config_odbc.c.

Referenced by realtime_multi_odbc(), realtime_multi_pgsql(), realtime_odbc(), and realtime_pgsql().

00068 {
00069    for (; *chunk; chunk++) {
00070       if (*chunk == '^' && strchr("0123456789ABCDEF", chunk[1]) && strchr("0123456789ABCDEF", chunk[2])) {
00071          sscanf(chunk + 1, "%02hhX", chunk);
00072          memmove(chunk + 1, chunk + 3, strlen(chunk + 3) + 1);
00073       }
00074    }
00075 }

static int load_module ( void   )  [static]

Definition at line 625 of file res_config_odbc.c.

References ast_config_engine_register(), ast_verbose(), odbc_engine, and option_verbose.

00626 {
00627    ast_config_engine_register(&odbc_engine);
00628    if (option_verbose)
00629       ast_verbose("res_config_odbc loaded.\n");
00630    return 0;
00631 }

static struct ast_config* realtime_multi_odbc ( const char *  database,
const char *  table,
va_list  ap 
) [static]

Definition at line 277 of file res_config_odbc.c.

References custom_prepare_struct::ap, ast_category_append(), ast_category_destroy(), ast_category_new(), ast_category_rename(), ast_config_new(), ast_log(), ast_odbc_backslash_is_escape(), ast_odbc_prepare_and_execute(), ast_odbc_release_obj(), ast_odbc_request_obj(), ast_strdupa, ast_string_field_free_memory, ast_string_field_init, ast_strip(), ast_strlen_zero(), ast_variable_append(), ast_variable_new(), custom_prepare(), decode_chunk(), LOG_WARNING, custom_prepare_struct::sql, and var.

00278 {
00279    struct odbc_obj *obj;
00280    SQLHSTMT stmt;
00281    char sql[1024];
00282    char coltitle[256];
00283    char rowdata[2048];
00284    const char *initfield=NULL;
00285    char *op;
00286    const char *newparam, *newval;
00287    char *stringp;
00288    char *chunk;
00289    SQLSMALLINT collen;
00290    int res;
00291    int x;
00292    struct ast_variable *var=NULL;
00293    struct ast_config *cfg=NULL;
00294    struct ast_category *cat=NULL;
00295    struct ast_realloca ra;
00296    SQLULEN colsize;
00297    SQLSMALLINT colcount=0;
00298    SQLSMALLINT datatype;
00299    SQLSMALLINT decimaldigits;
00300    SQLSMALLINT nullable;
00301    SQLLEN indicator;
00302    struct custom_prepare_struct cps = { .sql = sql };
00303    va_list aq;
00304 
00305    if (!table || ast_string_field_init(&cps, 256)) {
00306       return NULL;
00307    }
00308    va_copy(cps.ap, ap);
00309    va_copy(aq, ap);
00310 
00311    memset(&ra, 0, sizeof(ra));
00312 
00313    obj = ast_odbc_request_obj(database, 0);
00314    if (!obj) {
00315       ast_string_field_free_memory(&cps);
00316       return NULL;
00317    }
00318 
00319    newparam = va_arg(aq, const char *);
00320    if (!newparam)  {
00321       ast_odbc_release_obj(obj);
00322       ast_string_field_free_memory(&cps);
00323       return NULL;
00324    }
00325    initfield = ast_strdupa(newparam);
00326    if ((op = strchr(initfield, ' '))) 
00327       *op = '\0';
00328    newval = va_arg(aq, const char *);
00329    op = !strchr(newparam, ' ') ? " =" : "";
00330    snprintf(sql, sizeof(sql), "SELECT * FROM %s WHERE %s%s ?%s", table, newparam, op,
00331       strcasestr(newparam, "LIKE") && !ast_odbc_backslash_is_escape(obj) ? " ESCAPE '\\'" : "");
00332    while((newparam = va_arg(aq, const char *))) {
00333       op = !strchr(newparam, ' ') ? " =" : "";
00334       snprintf(sql + strlen(sql), sizeof(sql) - strlen(sql), " AND %s%s ?%s", newparam, op,
00335          strcasestr(newparam, "LIKE") && !ast_odbc_backslash_is_escape(obj) ? " ESCAPE '\\'" : "");
00336       newval = va_arg(aq, const char *);
00337    }
00338    if (initfield)
00339       snprintf(sql + strlen(sql), sizeof(sql) - strlen(sql), " ORDER BY %s", initfield);
00340    va_end(aq);
00341 
00342    stmt = ast_odbc_prepare_and_execute(obj, custom_prepare, &cps);
00343 
00344    if (!stmt) {
00345       ast_odbc_release_obj(obj);
00346       ast_string_field_free_memory(&cps);
00347       return NULL;
00348    }
00349 
00350    res = SQLNumResultCols(stmt, &colcount);
00351    if ((res != SQL_SUCCESS) && (res != SQL_SUCCESS_WITH_INFO)) {
00352       ast_log(LOG_WARNING, "SQL Column Count error!\n[%s]\n\n", sql);
00353       SQLFreeHandle(SQL_HANDLE_STMT, stmt);
00354       ast_odbc_release_obj(obj);
00355       ast_string_field_free_memory(&cps);
00356       return NULL;
00357    }
00358 
00359    cfg = ast_config_new();
00360    if (!cfg) {
00361       ast_log(LOG_WARNING, "Out of memory!\n");
00362       SQLFreeHandle(SQL_HANDLE_STMT, stmt);
00363       ast_odbc_release_obj(obj);
00364       ast_string_field_free_memory(&cps);
00365       return NULL;
00366    }
00367 
00368    while ((res=SQLFetch(stmt)) != SQL_NO_DATA) {
00369       var = NULL;
00370       if ((res != SQL_SUCCESS) && (res != SQL_SUCCESS_WITH_INFO)) {
00371          ast_log(LOG_WARNING, "SQL Fetch error!\n[%s]\n\n", sql);
00372          continue;
00373       }
00374       cat = ast_category_new("");
00375       if (!cat) {
00376          ast_log(LOG_WARNING, "Out of memory!\n");
00377          continue;
00378       }
00379       for (x=0;x<colcount;x++) {
00380          rowdata[0] = '\0';
00381          colsize = 0;
00382          collen = sizeof(coltitle);
00383          res = SQLDescribeCol(stmt, x + 1, (unsigned char *)coltitle, sizeof(coltitle), &collen, 
00384                   &datatype, &colsize, &decimaldigits, &nullable);
00385          if ((res != SQL_SUCCESS) && (res != SQL_SUCCESS_WITH_INFO)) {
00386             ast_log(LOG_WARNING, "SQL Describe Column error!\n[%s]\n\n", sql);
00387             ast_category_destroy(cat);
00388             continue;
00389          }
00390 
00391          indicator = 0;
00392          res = SQLGetData(stmt, x + 1, SQL_CHAR, rowdata, sizeof(rowdata), &indicator);
00393          if (indicator == SQL_NULL_DATA)
00394             continue;
00395 
00396          if ((res != SQL_SUCCESS) && (res != SQL_SUCCESS_WITH_INFO)) {
00397             ast_log(LOG_WARNING, "SQL Get Data error!\n[%s]\n\n", sql);
00398             ast_category_destroy(cat);
00399             continue;
00400          }
00401          stringp = rowdata;
00402          while (stringp) {
00403             chunk = strsep(&stringp, ";");
00404             if (!ast_strlen_zero(ast_strip(chunk))) {
00405                if (strchr(chunk, '^')) {
00406                   decode_chunk(chunk);
00407                }
00408                if (initfield && !strcmp(initfield, coltitle)) {
00409                   ast_category_rename(cat, chunk);
00410                }
00411                var = ast_variable_new(coltitle, chunk);
00412                ast_variable_append(cat, var);
00413             }
00414          }
00415       }
00416       ast_category_append(cfg, cat);
00417    }
00418 
00419    SQLFreeHandle(SQL_HANDLE_STMT, stmt);
00420    ast_odbc_release_obj(obj);
00421    ast_string_field_free_memory(&cps);
00422    return cfg;
00423 }

static struct ast_variable* realtime_odbc ( const char *  database,
const char *  table,
va_list  ap 
) [static]

Definition at line 132 of file res_config_odbc.c.

References custom_prepare_struct::ap, ast_log(), ast_odbc_backslash_is_escape(), ast_odbc_prepare_and_execute(), ast_odbc_release_obj(), ast_odbc_request_obj(), ast_string_field_free_memory, ast_string_field_init, ast_strip(), ast_strlen_zero(), ast_variable_new(), ast_variables_destroy(), custom_prepare(), decode_chunk(), LOG_ERROR, LOG_WARNING, custom_prepare_struct::sql, and var.

00133 {
00134    struct odbc_obj *obj;
00135    SQLHSTMT stmt;
00136    char sql[1024];
00137    char coltitle[256];
00138    char rowdata[2048];
00139    char *op;
00140    const char *newparam, *newval;
00141    char *stringp;
00142    char *chunk;
00143    SQLSMALLINT collen;
00144    int res;
00145    int x;
00146    struct ast_variable *var=NULL, *prev=NULL;
00147    SQLULEN colsize;
00148    SQLSMALLINT colcount=0;
00149    SQLSMALLINT datatype;
00150    SQLSMALLINT decimaldigits;
00151    SQLSMALLINT nullable;
00152    SQLLEN indicator;
00153    va_list aq;
00154    struct custom_prepare_struct cps = { .sql = sql };
00155 
00156    if (ast_string_field_init(&cps, 256)) {
00157       return NULL;
00158    }
00159    va_copy(cps.ap, ap);
00160    va_copy(aq, ap);
00161 
00162    if (!table) {
00163       ast_string_field_free_memory(&cps);
00164       return NULL;
00165    }
00166 
00167    obj = ast_odbc_request_obj(database, 0);
00168 
00169    if (!obj) {
00170       ast_log(LOG_ERROR, "No database handle available with the name of '%s' (check res_odbc.conf)\n", database);
00171       ast_string_field_free_memory(&cps);
00172       return NULL;
00173    }
00174 
00175    newparam = va_arg(aq, const char *);
00176    if (!newparam) {
00177       ast_odbc_release_obj(obj);
00178       ast_string_field_free_memory(&cps);
00179       return NULL;
00180    }
00181    newval = va_arg(aq, const char *);
00182    op = !strchr(newparam, ' ') ? " =" : "";
00183    snprintf(sql, sizeof(sql), "SELECT * FROM %s WHERE %s%s ?%s", table, newparam, op,
00184       strcasestr(newparam, "LIKE") && !ast_odbc_backslash_is_escape(obj) ? " ESCAPE '\\'" : "");
00185    while((newparam = va_arg(aq, const char *))) {
00186       op = !strchr(newparam, ' ') ? " =" : "";
00187       snprintf(sql + strlen(sql), sizeof(sql) - strlen(sql), " AND %s%s ?%s", newparam, op,
00188          strcasestr(newparam, "LIKE") && !ast_odbc_backslash_is_escape(obj) ? " ESCAPE '\\'" : "");
00189       newval = va_arg(aq, const char *);
00190    }
00191    va_end(aq);
00192 
00193    stmt = ast_odbc_prepare_and_execute(obj, custom_prepare, &cps);
00194 
00195    if (!stmt) {
00196       ast_odbc_release_obj(obj);
00197       ast_string_field_free_memory(&cps);
00198       return NULL;
00199    }
00200 
00201    res = SQLNumResultCols(stmt, &colcount);
00202    if ((res != SQL_SUCCESS) && (res != SQL_SUCCESS_WITH_INFO)) {
00203       ast_log(LOG_WARNING, "SQL Column Count error!\n[%s]\n\n", sql);
00204       SQLFreeHandle (SQL_HANDLE_STMT, stmt);
00205       ast_odbc_release_obj(obj);
00206       ast_string_field_free_memory(&cps);
00207       return NULL;
00208    }
00209 
00210    res = SQLFetch(stmt);
00211    if (res == SQL_NO_DATA) {
00212       SQLFreeHandle (SQL_HANDLE_STMT, stmt);
00213       ast_odbc_release_obj(obj);
00214       ast_string_field_free_memory(&cps);
00215       return NULL;
00216    }
00217    if ((res != SQL_SUCCESS) && (res != SQL_SUCCESS_WITH_INFO)) {
00218       ast_log(LOG_WARNING, "SQL Fetch error!\n[%s]\n\n", sql);
00219       SQLFreeHandle (SQL_HANDLE_STMT, stmt);
00220       ast_odbc_release_obj(obj);
00221       ast_string_field_free_memory(&cps);
00222       return NULL;
00223    }
00224    for (x = 0; x < colcount; x++) {
00225       rowdata[0] = '\0';
00226       colsize = 0;
00227       collen = sizeof(coltitle);
00228       res = SQLDescribeCol(stmt, x + 1, (unsigned char *)coltitle, sizeof(coltitle), &collen, 
00229                &datatype, &colsize, &decimaldigits, &nullable);
00230       if ((res != SQL_SUCCESS) && (res != SQL_SUCCESS_WITH_INFO)) {
00231          ast_log(LOG_WARNING, "SQL Describe Column error!\n[%s]\n\n", sql);
00232          if (var)
00233             ast_variables_destroy(var);
00234          ast_odbc_release_obj(obj);
00235          ast_string_field_free_memory(&cps);
00236          return NULL;
00237       }
00238 
00239       indicator = 0;
00240       res = SQLGetData(stmt, x + 1, SQL_CHAR, rowdata, sizeof(rowdata), &indicator);
00241       if (indicator == SQL_NULL_DATA)
00242          continue;
00243 
00244       if ((res != SQL_SUCCESS) && (res != SQL_SUCCESS_WITH_INFO)) {
00245          ast_log(LOG_WARNING, "SQL Get Data error!\n[%s]\n\n", sql);
00246          if (var)
00247             ast_variables_destroy(var);
00248          ast_odbc_release_obj(obj);
00249          return NULL;
00250       }
00251       stringp = rowdata;
00252       while (stringp) {
00253          chunk = strsep(&stringp, ";");
00254          if (!ast_strlen_zero(ast_strip(chunk))) {
00255             if (strchr(chunk, '^')) {
00256                decode_chunk(chunk);
00257             }
00258             if (prev) {
00259                prev->next = ast_variable_new(coltitle, chunk);
00260                if (prev->next) {
00261                   prev = prev->next;
00262                }
00263             } else {
00264                prev = var = ast_variable_new(coltitle, chunk);
00265             }
00266          }
00267       }
00268    }
00269 
00270 
00271    SQLFreeHandle(SQL_HANDLE_STMT, stmt);
00272    ast_odbc_release_obj(obj);
00273    ast_string_field_free_memory(&cps);
00274    return var;
00275 }

static int unload_module ( void   )  [static]

Definition at line 616 of file res_config_odbc.c.

References ast_config_engine_deregister(), ast_module_user_hangup_all, ast_verbose(), odbc_engine, and option_verbose.

00617 {
00618    ast_module_user_hangup_all();
00619    ast_config_engine_deregister(&odbc_engine);
00620    if (option_verbose)
00621       ast_verbose("res_config_odbc unloaded.\n");
00622    return 0;
00623 }

static int update_odbc ( const char *  database,
const char *  table,
const char *  keyfield,
const char *  lookup,
va_list  ap 
) [static]

Definition at line 425 of file res_config_odbc.c.

References custom_prepare_struct::ap, ast_log(), ast_odbc_prepare_and_execute(), ast_odbc_release_obj(), ast_odbc_request_obj(), ast_string_field_free_memory, ast_string_field_init, custom_prepare(), LOG_WARNING, and custom_prepare_struct::sql.

00426 {
00427    struct odbc_obj *obj;
00428    SQLHSTMT stmt;
00429    char sql[256];
00430    SQLLEN rowcount=0;
00431    const char *newparam, *newval;
00432    int res;
00433    va_list aq;
00434    struct custom_prepare_struct cps = { .sql = sql, .extra = lookup };
00435 
00436    if (!table || ast_string_field_init(&cps, 256)) {
00437       return -1;
00438    }
00439    va_copy(cps.ap, ap);
00440    va_copy(aq, ap);
00441 
00442    if (!(obj = ast_odbc_request_obj(database, 0))) {
00443       ast_string_field_free_memory(&cps);
00444       return -1;
00445    }
00446 
00447    newparam = va_arg(aq, const char *);
00448    if (!newparam)  {
00449       ast_odbc_release_obj(obj);
00450       ast_string_field_free_memory(&cps);
00451       return -1;
00452    }
00453    newval = va_arg(aq, const char *);
00454    snprintf(sql, sizeof(sql), "UPDATE %s SET %s=?", table, newparam);
00455    while((newparam = va_arg(aq, const char *))) {
00456       snprintf(sql + strlen(sql), sizeof(sql) - strlen(sql), ", %s=?", newparam);
00457       newval = va_arg(aq, const char *);
00458    }
00459    va_end(aq);
00460    snprintf(sql + strlen(sql), sizeof(sql) - strlen(sql), " WHERE %s=?", keyfield);
00461 
00462    stmt = ast_odbc_prepare_and_execute(obj, custom_prepare, &cps);
00463 
00464    if (!stmt) {
00465       ast_odbc_release_obj(obj);
00466       ast_string_field_free_memory(&cps);
00467       return -1;
00468    }
00469 
00470    res = SQLRowCount(stmt, &rowcount);
00471    SQLFreeHandle (SQL_HANDLE_STMT, stmt);
00472    ast_odbc_release_obj(obj);
00473    ast_string_field_free_memory(&cps);
00474 
00475    if ((res != SQL_SUCCESS) && (res != SQL_SUCCESS_WITH_INFO)) {
00476       ast_log(LOG_WARNING, "SQL Row Count error!\n[%s]\n\n", sql);
00477       return -1;
00478    }
00479 
00480    if (rowcount >= 0) {
00481       return (int) rowcount;
00482    }
00483 
00484    return -1;
00485 }


Variable Documentation

struct ast_module_info __mod_info = { .name = AST_MODULE, .flags = AST_MODFLAG_DEFAULT | AST_MODFLAG_BUILDSUM, .description = "ODBC Configuration" , .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, } [static]

Definition at line 636 of file res_config_odbc.c.

const struct ast_module_info* ast_module_info = &__mod_info [static]

Definition at line 636 of file res_config_odbc.c.

struct ast_config_engine odbc_engine [static]

Definition at line 608 of file res_config_odbc.c.

Referenced by load_module(), and unload_module().


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