Annotation of embedaddon/php/ext/sqlite/pdo_sqlite2.c, revision 1.1.1.1

1.1       misho       1: /*
                      2:   +----------------------------------------------------------------------+
                      3:   | PHP Version 5                                                        |
                      4:   +----------------------------------------------------------------------+
                      5:   | Copyright (c) 1997-2012 The PHP Group                                |
                      6:   +----------------------------------------------------------------------+
                      7:   | This source file is subject to version 3.01 of the PHP license,      |
                      8:   | that is bundled with this package in the file LICENSE, and is        |
                      9:   | available through the world-wide-web at the following url:           |
                     10:   | http://www.php.net/license/3_01.txt                                  |
                     11:   | If you did not receive a copy of the PHP license and are unable to   |
                     12:   | obtain it through the world-wide-web, please send a note to          |
                     13:   | license@php.net so we can mail you a copy immediately.               |
                     14:   +----------------------------------------------------------------------+
                     15:   | Author: Wez Furlong <wez@php.net>                                    |
                     16:   +----------------------------------------------------------------------+
                     17: */
                     18: 
                     19: /* $Id: pdo_sqlite2.c 321634 2012-01-01 13:15:04Z felipe $ */
                     20: #ifdef HAVE_CONFIG_H
                     21: #include "config.h"
                     22: #endif
                     23: #include "php.h"
                     24: 
                     25: #ifdef PHP_SQLITE2_HAVE_PDO
                     26: #include "sqlite.h"
                     27: #include "pdo/php_pdo.h"
                     28: #include "pdo/php_pdo_driver.h"
                     29: #include "zend_exceptions.h"
                     30: 
                     31: #define php_sqlite_encode_binary(in, n, out) sqlite_encode_binary((const unsigned char *)in, n, (unsigned char *)out)
                     32: #define php_sqlite_decode_binary(in, out)    sqlite_decode_binary((const unsigned char *)in, (unsigned char *)out)
                     33: 
                     34: 
                     35: typedef struct {
                     36:        const char *file;
                     37:        int line;
                     38:        unsigned int errcode;
                     39:        char *errmsg;
                     40: } pdo_sqlite2_error_info;
                     41: 
                     42: typedef struct {
                     43:        sqlite *db;
                     44:        pdo_sqlite2_error_info einfo;
                     45: } pdo_sqlite2_db_handle;
                     46: 
                     47: typedef struct {
                     48:        pdo_sqlite2_db_handle   *H;
                     49:        sqlite_vm *vm;
                     50:        const char **rowdata, **colnames;
                     51:        int ncols;
                     52:        unsigned pre_fetched:1;
                     53:        unsigned done:1;
                     54:        pdo_sqlite2_error_info einfo;
                     55: } pdo_sqlite2_stmt;
                     56: 
                     57: extern int _pdo_sqlite2_error(pdo_dbh_t *dbh, pdo_stmt_t *stmt, char *errmsg, const char *file, int line TSRMLS_DC);
                     58: #define pdo_sqlite2_error(msg, s) _pdo_sqlite2_error(s, NULL, msg, __FILE__, __LINE__ TSRMLS_CC)
                     59: #define pdo_sqlite2_error_stmt(msg, s) _pdo_sqlite2_error(stmt->dbh, stmt, msg, __FILE__, __LINE__ TSRMLS_CC)
                     60: 
                     61: extern struct pdo_stmt_methods sqlite2_stmt_methods;
                     62: 
                     63: static int pdo_sqlite2_stmt_dtor(pdo_stmt_t *stmt TSRMLS_DC)
                     64: {
                     65:        pdo_sqlite2_stmt *S = (pdo_sqlite2_stmt*)stmt->driver_data;
                     66: 
                     67:        if (S->vm) {
                     68:                char *errmsg = NULL;
                     69:                sqlite_finalize(S->vm, &errmsg);
                     70:                if (errmsg) {
                     71:                        sqlite_freemem(errmsg);
                     72:                }
                     73:                S->vm = NULL;
                     74:        }
                     75:        if (S->einfo.errmsg) {
                     76:                pefree(S->einfo.errmsg, stmt->dbh->is_persistent);
                     77:        }
                     78:        efree(S);
                     79:        return 1;
                     80: }
                     81: 
                     82: static int pdo_sqlite2_stmt_execute(pdo_stmt_t *stmt TSRMLS_DC)
                     83: {
                     84:        pdo_sqlite2_stmt *S = (pdo_sqlite2_stmt*)stmt->driver_data;
                     85:        char *errmsg = NULL;
                     86:        const char *tail;
                     87: 
                     88:        if (stmt->executed && !S->done) {
                     89:                sqlite_finalize(S->vm, &errmsg);
                     90:                pdo_sqlite2_error_stmt(errmsg, stmt);
                     91:                errmsg = NULL;
                     92:                S->vm = NULL;
                     93:        }
                     94: 
                     95:        S->einfo.errcode = sqlite_compile(S->H->db, stmt->active_query_string, &tail, &S->vm, &errmsg);
                     96:        if (S->einfo.errcode != SQLITE_OK) {
                     97:                pdo_sqlite2_error_stmt(errmsg, stmt);
                     98:                return 0;
                     99:        }
                    100: 
                    101:        S->done = 0;
                    102:        S->einfo.errcode = sqlite_step(S->vm, &S->ncols, &S->rowdata, &S->colnames);
                    103:        switch (S->einfo.errcode) {
                    104:                case SQLITE_ROW:
                    105:                        S->pre_fetched = 1;
                    106:                        stmt->column_count = S->ncols;
                    107:                        return 1;
                    108: 
                    109:                case SQLITE_DONE:
                    110:                        stmt->column_count = S->ncols;
                    111:                        stmt->row_count = sqlite_changes(S->H->db);
                    112:                        S->einfo.errcode = sqlite_reset(S->vm, &errmsg);
                    113:                        if (S->einfo.errcode != SQLITE_OK) {
                    114:                                pdo_sqlite2_error_stmt(errmsg, stmt);
                    115:                        }
                    116:                        S->done = 1;
                    117:                        return 1;
                    118: 
                    119:                case SQLITE_ERROR:
                    120:                case SQLITE_MISUSE:
                    121:                case SQLITE_BUSY:
                    122:                default:
                    123:                        pdo_sqlite2_error_stmt(errmsg, stmt);
                    124:                        return 0;
                    125:        }
                    126: }
                    127: 
                    128: static int pdo_sqlite2_stmt_param_hook(pdo_stmt_t *stmt, struct pdo_bound_param_data *param,
                    129:                enum pdo_param_event event_type TSRMLS_DC)
                    130: {
                    131:        return 1;
                    132: }
                    133: 
                    134: static int pdo_sqlite2_stmt_fetch(pdo_stmt_t *stmt,
                    135:        enum pdo_fetch_orientation ori, long offset TSRMLS_DC)
                    136: {
                    137:        pdo_sqlite2_stmt *S = (pdo_sqlite2_stmt*)stmt->driver_data;
                    138:        char *errmsg = NULL;
                    139: 
                    140:        if (!S->vm) {
                    141:                return 0;       
                    142:        }
                    143:        if (S->pre_fetched) {
                    144:                S->pre_fetched = 0;
                    145:                return 1;
                    146:        }
                    147:        if (S->done) {
                    148:                return 0;
                    149:        }
                    150: 
                    151:        S->einfo.errcode = sqlite_step(S->vm, &S->ncols, &S->rowdata, &S->colnames);
                    152:        switch (S->einfo.errcode) {
                    153:                case SQLITE_ROW:
                    154:                        return 1;
                    155: 
                    156:                case SQLITE_DONE:
                    157:                        S->done = 1;
                    158:                        S->einfo.errcode = sqlite_reset(S->vm, &errmsg);
                    159:                        if (S->einfo.errcode != SQLITE_OK) {
                    160:                                pdo_sqlite2_error_stmt(errmsg, stmt);
                    161:                                errmsg = NULL;
                    162:                        }
                    163:                        return 0;
                    164: 
                    165:                default:
                    166:                        pdo_sqlite2_error_stmt(errmsg, stmt);
                    167:                        return 0;
                    168:        }
                    169: }
                    170: 
                    171: static int pdo_sqlite2_stmt_describe(pdo_stmt_t *stmt, int colno TSRMLS_DC)
                    172: {
                    173:        pdo_sqlite2_stmt *S = (pdo_sqlite2_stmt*)stmt->driver_data;
                    174: 
                    175:        if(colno >= S->ncols) {
                    176:                /* error invalid column */
                    177:                pdo_sqlite2_error_stmt(NULL, stmt);
                    178:                return 0;
                    179:        }
                    180: 
                    181:        stmt->columns[colno].name = estrdup(S->colnames[colno]);
                    182:        stmt->columns[colno].namelen = strlen(stmt->columns[colno].name);
                    183:        stmt->columns[colno].maxlen = 0xffffffff;
                    184:        stmt->columns[colno].precision = 0;
                    185:        stmt->columns[colno].param_type = PDO_PARAM_STR;
                    186: 
                    187:        return 1;
                    188: }
                    189: 
                    190: static int pdo_sqlite2_stmt_get_col(pdo_stmt_t *stmt, int colno, char **ptr, unsigned long *len, int *caller_frees TSRMLS_DC)
                    191: {
                    192:        pdo_sqlite2_stmt *S = (pdo_sqlite2_stmt*)stmt->driver_data;
                    193:        if (!S->vm) {
                    194:                return 0;
                    195:        }
                    196:        if(colno >= S->ncols) {
                    197:                /* error invalid column */
                    198:                pdo_sqlite2_error_stmt(NULL, stmt);
                    199:                return 0;
                    200:        }
                    201:        if (S->rowdata[colno]) {
                    202:                if (S->rowdata[colno][0] == '\x01') {
                    203:                        /* encoded */
                    204:                        *caller_frees = 1;
                    205:                        *ptr = emalloc(strlen(S->rowdata[colno]));
                    206:                        *len = php_sqlite_decode_binary(S->rowdata[colno]+1, *ptr);
                    207:                        (*(char**)ptr)[*len] = '\0';
                    208:                } else {
                    209:                        *ptr = (char*)S->rowdata[colno];
                    210:                        *len = strlen(*ptr);
                    211:                }
                    212:        } else {
                    213:                *ptr = NULL;
                    214:                *len = 0;
                    215:        }
                    216:        return 1;
                    217: }
                    218: 
                    219: struct pdo_stmt_methods sqlite2_stmt_methods = {
                    220:        pdo_sqlite2_stmt_dtor,
                    221:        pdo_sqlite2_stmt_execute,
                    222:        pdo_sqlite2_stmt_fetch,
                    223:        pdo_sqlite2_stmt_describe,
                    224:        pdo_sqlite2_stmt_get_col,
                    225:        pdo_sqlite2_stmt_param_hook,
                    226:        NULL, /* set_attr */
                    227:        NULL, /* get_attr */
                    228:        NULL
                    229: };
                    230: 
                    231: 
                    232: int _pdo_sqlite2_error(pdo_dbh_t *dbh, pdo_stmt_t *stmt, char *errmsg, const char *file, int line TSRMLS_DC) /* {{{ */
                    233: {
                    234:        pdo_sqlite2_db_handle *H = (pdo_sqlite2_db_handle *)dbh->driver_data;
                    235:        pdo_error_type *pdo_err = stmt ? &stmt->error_code : &dbh->error_code;
                    236:        pdo_sqlite2_error_info *einfo = &H->einfo;
                    237:        pdo_sqlite2_stmt *S;
                    238: 
                    239:        if (stmt) {
                    240:                S = stmt->driver_data;
                    241:                einfo = &S->einfo;
                    242:        }
                    243: 
                    244:        einfo->file = file;
                    245:        einfo->line = line;
                    246: 
                    247:        if (einfo->errmsg) {
                    248:                pefree(einfo->errmsg, dbh->is_persistent);
                    249:                einfo->errmsg = NULL;
                    250:        }
                    251: 
                    252:        if (einfo->errcode != SQLITE_OK) {
                    253:                if (errmsg) {
                    254:                        einfo->errmsg = pestrdup(errmsg, dbh->is_persistent);
                    255:                        sqlite_freemem(errmsg);
                    256:                } else {
                    257:                        einfo->errmsg = pestrdup(sqlite_error_string(einfo->errcode), dbh->is_persistent);
                    258:                }
                    259:        } else { /* no error */
                    260:                strcpy(*pdo_err, PDO_ERR_NONE);
                    261:                return 0;
                    262:        }
                    263:        switch (einfo->errcode) {
                    264:                case SQLITE_NOTFOUND:
                    265:                        strcpy(*pdo_err, "42S02");
                    266:                        break;  
                    267: 
                    268:                case SQLITE_INTERRUPT:
                    269:                        strcpy(*pdo_err, "01002");
                    270:                        break;
                    271: 
                    272:                case SQLITE_NOLFS:
                    273:                        strcpy(*pdo_err, "HYC00");
                    274:                        break;
                    275: 
                    276:                case SQLITE_TOOBIG:
                    277:                        strcpy(*pdo_err, "22001");
                    278:                        break;
                    279: 
                    280:                case SQLITE_CONSTRAINT:
                    281:                        strcpy(*pdo_err, "23000");
                    282:                        break;
                    283: 
                    284:                case SQLITE_ERROR:
                    285:                default:
                    286:                        strcpy(*pdo_err, "HY000");
                    287:                        break;
                    288:        }
                    289: 
                    290:        if (!dbh->methods) {
                    291:                zend_throw_exception_ex(php_pdo_get_exception(), 0 TSRMLS_CC, "SQLSTATE[%s] [%d] %s",
                    292:                                *pdo_err, einfo->errcode, einfo->errmsg);
                    293:        }
                    294: 
                    295:        return einfo->errcode;
                    296: }
                    297: /* }}} */
                    298: 
                    299: static int pdo_sqlite2_fetch_error_func(pdo_dbh_t *dbh, pdo_stmt_t *stmt, zval *info TSRMLS_DC)
                    300: {
                    301:        pdo_sqlite2_db_handle *H = (pdo_sqlite2_db_handle *)dbh->driver_data;
                    302:        pdo_sqlite2_error_info *einfo = &H->einfo;
                    303:        pdo_sqlite2_stmt *S;
                    304: 
                    305:        if (stmt) {
                    306:                S = stmt->driver_data;
                    307:                einfo = &S->einfo;
                    308:        }
                    309: 
                    310:        if (einfo->errcode) {
                    311:                add_next_index_long(info, einfo->errcode);
                    312:                if (einfo->errmsg) {
                    313:                        add_next_index_string(info, einfo->errmsg, 1);
                    314:                }
                    315:        }
                    316: 
                    317:        return 1;
                    318: }
                    319: 
                    320: static int sqlite2_handle_closer(pdo_dbh_t *dbh TSRMLS_DC) /* {{{ */
                    321: {
                    322:        pdo_sqlite2_db_handle *H = (pdo_sqlite2_db_handle *)dbh->driver_data;
                    323:        
                    324:        if (H) {
                    325:                if (H->db) {
                    326:                        sqlite_close(H->db);
                    327:                        H->db = NULL;
                    328:                }
                    329:                if (H->einfo.errmsg) {
                    330:                        pefree(H->einfo.errmsg, dbh->is_persistent);
                    331:                        H->einfo.errmsg = NULL;
                    332:                }
                    333:                pefree(H, dbh->is_persistent);
                    334:                dbh->driver_data = NULL;
                    335:        }
                    336:        return 0;
                    337: }
                    338: /* }}} */
                    339: 
                    340: static int sqlite2_handle_preparer(pdo_dbh_t *dbh, const char *sql, long sql_len, pdo_stmt_t *stmt, zval *driver_options TSRMLS_DC)
                    341: {
                    342:        pdo_sqlite2_db_handle *H = (pdo_sqlite2_db_handle *)dbh->driver_data;
                    343:        pdo_sqlite2_stmt *S = ecalloc(1, sizeof(pdo_sqlite2_stmt));
                    344: 
                    345:        S->H = H;
                    346:        stmt->driver_data = S;
                    347:        stmt->methods = &sqlite2_stmt_methods;
                    348:        stmt->supports_placeholders = PDO_PLACEHOLDER_NONE;
                    349: 
                    350:        if (PDO_CURSOR_FWDONLY != pdo_attr_lval(driver_options, PDO_ATTR_CURSOR, PDO_CURSOR_FWDONLY TSRMLS_CC)) {
                    351:                H->einfo.errcode = SQLITE_ERROR;
                    352:                pdo_sqlite2_error(NULL, dbh);
                    353:                return 0;
                    354:        }
                    355: 
                    356:        return 1;
                    357: }
                    358: 
                    359: static long sqlite2_handle_doer(pdo_dbh_t *dbh, const char *sql, long sql_len TSRMLS_DC)
                    360: {
                    361:        pdo_sqlite2_db_handle *H = (pdo_sqlite2_db_handle *)dbh->driver_data;
                    362:        char *errmsg = NULL;
                    363: 
                    364:        if ((H->einfo.errcode = sqlite_exec(H->db, sql, NULL, NULL, &errmsg)) != SQLITE_OK) {
                    365:                pdo_sqlite2_error(errmsg, dbh);
                    366:                return -1;
                    367:        } else {
                    368:                return sqlite_changes(H->db);
                    369:        }
                    370: }
                    371: 
                    372: static char *pdo_sqlite2_last_insert_id(pdo_dbh_t *dbh, const char *name, unsigned int *len TSRMLS_DC)
                    373: {
                    374:        pdo_sqlite2_db_handle *H = (pdo_sqlite2_db_handle *)dbh->driver_data;
                    375:        char *id;
                    376:        
                    377:        id = php_pdo_int64_to_str(sqlite_last_insert_rowid(H->db) TSRMLS_CC);
                    378:        *len = strlen(id);
                    379:        return id;
                    380: }
                    381: 
                    382: static int sqlite2_handle_quoter(pdo_dbh_t *dbh, const char *unquoted, int unquotedlen, char **quoted, int *quotedlen, enum pdo_param_type paramtype  TSRMLS_DC)
                    383: {
                    384:        char *ret;
                    385: 
                    386:        if (unquotedlen && (unquoted[0] == '\x01' || memchr(unquoted, '\0', unquotedlen) != NULL)) {
                    387:                /* binary string */
                    388:                int len;
                    389:                ret = safe_emalloc(1 + unquotedlen / 254, 257, 5);
                    390:                ret[0] = '\'';
                    391:                ret[1] = '\x01';
                    392:                len = php_sqlite_encode_binary(unquoted, unquotedlen, ret+2);
                    393:                ret[len + 2] = '\'';
                    394:                ret[len + 3] = '\0';
                    395:                *quoted = ret;
                    396:                *quotedlen = len + 3;
                    397:                /* fprintf(stderr, "Quoting:%d:%.*s:\n", *quotedlen, *quotedlen, *quoted); */
                    398:                return 1;
                    399:        } else if (unquotedlen) {
                    400:                ret = sqlite_mprintf("'%q'", unquoted);
                    401:                if (ret) {
                    402:                        *quoted = estrdup(ret);
                    403:                        *quotedlen = strlen(ret);
                    404:                        sqlite_freemem(ret);
                    405:                        return 1;
                    406:                }
                    407:                return 0;
                    408:        } else {
                    409:                *quoted = estrdup("''");
                    410:                *quotedlen = 2;
                    411:                return 1;
                    412:        }
                    413: }
                    414: 
                    415: static int sqlite2_handle_begin(pdo_dbh_t *dbh TSRMLS_DC)
                    416: {
                    417:        pdo_sqlite2_db_handle *H = (pdo_sqlite2_db_handle *)dbh->driver_data;
                    418:        char *errmsg = NULL;
                    419: 
                    420:        if (sqlite_exec(H->db, "BEGIN", NULL, NULL, &errmsg) != SQLITE_OK) {
                    421:                pdo_sqlite2_error(errmsg, dbh);
                    422:                return 0;
                    423:        }
                    424:        return 1;
                    425: }
                    426: 
                    427: static int sqlite2_handle_commit(pdo_dbh_t *dbh TSRMLS_DC)
                    428: {
                    429:        pdo_sqlite2_db_handle *H = (pdo_sqlite2_db_handle *)dbh->driver_data;
                    430:        char *errmsg = NULL;
                    431: 
                    432:        if (sqlite_exec(H->db, "COMMIT", NULL, NULL, &errmsg) != SQLITE_OK) {
                    433:                pdo_sqlite2_error(errmsg, dbh);
                    434:                return 0;
                    435:        }
                    436:        return 1;
                    437: }
                    438: 
                    439: static int sqlite2_handle_rollback(pdo_dbh_t *dbh TSRMLS_DC)
                    440: {
                    441:        pdo_sqlite2_db_handle *H = (pdo_sqlite2_db_handle *)dbh->driver_data;
                    442:        char *errmsg = NULL;
                    443: 
                    444:        if (sqlite_exec(H->db, "ROLLBACK", NULL, NULL, &errmsg) != SQLITE_OK) {
                    445:                pdo_sqlite2_error(errmsg, dbh);
                    446:                return 0;
                    447:        }
                    448:        return 1;
                    449: }
                    450: 
                    451: static int pdo_sqlite2_get_attribute(pdo_dbh_t *dbh, long attr, zval *return_value TSRMLS_DC)
                    452: {
                    453:        switch (attr) {
                    454:                case PDO_ATTR_CLIENT_VERSION:
                    455:                case PDO_ATTR_SERVER_VERSION:
                    456:                        ZVAL_STRING(return_value, (char *)sqlite_libversion(), 1);
                    457:                        break;
                    458:                
                    459:                default:
                    460:                        return 0;       
                    461:        }
                    462: 
                    463:        return 1;
                    464: }
                    465: 
                    466: static int pdo_sqlite2_set_attr(pdo_dbh_t *dbh, long attr, zval *val TSRMLS_DC)
                    467: {
                    468:        pdo_sqlite2_db_handle *H = (pdo_sqlite2_db_handle *)dbh->driver_data;
                    469: 
                    470:        switch (attr) {
                    471:                case PDO_ATTR_TIMEOUT:
                    472:                        convert_to_long(val);
                    473:                        sqlite_busy_timeout(H->db, Z_LVAL_P(val) * 1000);
                    474:                        return 1;
                    475:        }
                    476:        return 0;
                    477: }
                    478: 
                    479: static PHP_FUNCTION(sqlite2_create_function)
                    480: {
                    481:        /* TODO: implement this stuff */
                    482: }
                    483: 
                    484: static const zend_function_entry dbh_methods[] = {
                    485:        PHP_FE(sqlite2_create_function, NULL)
                    486:        {NULL, NULL, NULL}
                    487: };
                    488: 
                    489: static const zend_function_entry *get_driver_methods(pdo_dbh_t *dbh, int kind TSRMLS_DC)
                    490: {
                    491:        switch (kind) {
                    492:                case PDO_DBH_DRIVER_METHOD_KIND_DBH:
                    493:                        return dbh_methods;
                    494: 
                    495:                default:
                    496:                        return NULL;
                    497:        }
                    498: }
                    499: 
                    500: static struct pdo_dbh_methods sqlite2_methods = {
                    501:        sqlite2_handle_closer,
                    502:        sqlite2_handle_preparer,
                    503:        sqlite2_handle_doer,
                    504:        sqlite2_handle_quoter,
                    505:        sqlite2_handle_begin,
                    506:        sqlite2_handle_commit,
                    507:        sqlite2_handle_rollback,
                    508:        pdo_sqlite2_set_attr,
                    509:        pdo_sqlite2_last_insert_id,
                    510:        pdo_sqlite2_fetch_error_func,
                    511:        pdo_sqlite2_get_attribute,
                    512:        NULL,   /* check_liveness: not needed */
                    513:        get_driver_methods
                    514: };
                    515: 
                    516: static char *make_filename_safe(const char *filename TSRMLS_DC)
                    517: {
                    518:        if (*filename && strncmp(filename, ":memory:", sizeof(":memory:")-1)) {
                    519:                char *fullpath = expand_filepath(filename, NULL TSRMLS_CC);
                    520: 
                    521:                if (!fullpath) {
                    522:                        return NULL;
                    523:                }
                    524: 
                    525:                if (PG(safe_mode) && (!php_checkuid(fullpath, NULL, CHECKUID_CHECK_FILE_AND_DIR))) {
                    526:                        efree(fullpath);
                    527:                        return NULL;
                    528:                }
                    529: 
                    530:                if (php_check_open_basedir(fullpath TSRMLS_CC)) {
                    531:                        efree(fullpath);
                    532:                        return NULL;
                    533:                }
                    534:                return fullpath;
                    535:        }
                    536:        return estrdup(filename);
                    537: }
                    538: 
                    539: static int authorizer(void *autharg, int access_type, const char *arg3, const char *arg4,
                    540:                const char *arg5, const char *arg6)
                    541: {
                    542:        char *filename;
                    543:        switch (access_type) {
                    544:                case SQLITE_COPY: {
                    545:                        TSRMLS_FETCH();
                    546:                        filename = make_filename_safe(arg4 TSRMLS_CC);
                    547:                        if (!filename) {
                    548:                                return SQLITE_DENY;
                    549:                        }
                    550:                        efree(filename);
                    551:                        return SQLITE_OK;
                    552:                }
                    553: 
                    554:                case SQLITE_ATTACH: {
                    555:                        TSRMLS_FETCH();
                    556:                        filename = make_filename_safe(arg3 TSRMLS_CC);
                    557:                        if (!filename) {
                    558:                                return SQLITE_DENY;
                    559:                        }
                    560:                        efree(filename);
                    561:                        return SQLITE_OK;
                    562:                }
                    563: 
                    564:                default:
                    565:                        /* access allowed */
                    566:                        return SQLITE_OK;
                    567:        }
                    568: }
                    569: 
                    570: static int pdo_sqlite2_handle_factory(pdo_dbh_t *dbh, zval *driver_options TSRMLS_DC) /* {{{ */
                    571: {
                    572:        pdo_sqlite2_db_handle *H;
                    573:        int ret = 0;
                    574:        long timeout = 60;
                    575:        char *filename;
                    576:        char *errmsg = NULL;
                    577: 
                    578:        H = pecalloc(1, sizeof(pdo_sqlite2_db_handle), dbh->is_persistent);
                    579: 
                    580:        H->einfo.errcode = 0;
                    581:        H->einfo.errmsg = NULL;
                    582:        dbh->driver_data = H;
                    583: 
                    584:        filename = make_filename_safe(dbh->data_source TSRMLS_CC);
                    585: 
                    586:        if (!filename) {
                    587:                zend_throw_exception_ex(php_pdo_get_exception(), 0 TSRMLS_CC,
                    588:                                "safe_mode/open_basedir prohibits opening %s",
                    589:                                dbh->data_source);
                    590:                goto cleanup;
                    591:        }
                    592: 
                    593:        H->db = sqlite_open(filename, 0666, &errmsg);
                    594:        efree(filename);
                    595: 
                    596:        if (!H->db) {
                    597:                H->einfo.errcode = SQLITE_ERROR;
                    598:                pdo_sqlite2_error(errmsg, dbh);
                    599:                goto cleanup;
                    600:        }
                    601: 
                    602:        sqlite_set_authorizer(H->db, authorizer, NULL);
                    603: 
                    604:        if (driver_options) {
                    605:                timeout = pdo_attr_lval(driver_options, PDO_ATTR_TIMEOUT, timeout TSRMLS_CC);
                    606:        }
                    607:        sqlite_busy_timeout(H->db, timeout * 1000);
                    608: 
                    609:        dbh->alloc_own_columns = 1;
                    610:        dbh->max_escaped_char_length = 2;
                    611: 
                    612:        ret = 1;
                    613: 
                    614: cleanup:
                    615:        dbh->methods = &sqlite2_methods;
                    616: 
                    617:        return ret;
                    618: }
                    619: /* }}} */
                    620: 
                    621: pdo_driver_t pdo_sqlite2_driver = {
                    622:        PDO_DRIVER_HEADER(sqlite2),
                    623:        pdo_sqlite2_handle_factory
                    624: };
                    625: 
                    626: 
                    627: 
                    628: #endif
                    629: 
                    630: 
                    631: /*
                    632:  * Local variables:
                    633:  * tab-width: 4
                    634:  * c-basic-offset: 4
                    635:  * End:
                    636:  * vim600: noet sw=4 ts=4 fdm=marker
                    637:  * vim<600: noet sw=4 ts=4
                    638:  */

FreeBSD-CVSweb <freebsd-cvsweb@FreeBSD.org>