Annotation of embedaddon/php/Zend/zend_constants.c, revision 1.1

1.1     ! misho       1: /*
        !             2:    +----------------------------------------------------------------------+
        !             3:    | Zend Engine                                                          |
        !             4:    +----------------------------------------------------------------------+
        !             5:    | Copyright (c) 1998-2012 Zend Technologies Ltd. (http://www.zend.com) |
        !             6:    +----------------------------------------------------------------------+
        !             7:    | This source file is subject to version 2.00 of the Zend 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.zend.com/license/2_00.txt.                                |
        !            11:    | If you did not receive a copy of the Zend license and are unable to  |
        !            12:    | obtain it through the world-wide-web, please send a note to          |
        !            13:    | license@zend.com so we can mail you a copy immediately.              |
        !            14:    +----------------------------------------------------------------------+
        !            15:    | Authors: Andi Gutmans <andi@zend.com>                                |
        !            16:    |          Zeev Suraski <zeev@zend.com>                                |
        !            17:    +----------------------------------------------------------------------+
        !            18: */
        !            19: 
        !            20: /* $Id: zend_constants.c 321634 2012-01-01 13:15:04Z felipe $ */
        !            21: 
        !            22: #include "zend.h"
        !            23: #include "zend_constants.h"
        !            24: #include "zend_execute.h"
        !            25: #include "zend_variables.h"
        !            26: #include "zend_operators.h"
        !            27: #include "zend_globals.h"
        !            28: 
        !            29: 
        !            30: void free_zend_constant(zend_constant *c)
        !            31: {
        !            32:        if (!(c->flags & CONST_PERSISTENT)) {
        !            33:                zval_dtor(&c->value);
        !            34:        }
        !            35:        free(c->name);
        !            36: }
        !            37: 
        !            38: 
        !            39: void copy_zend_constant(zend_constant *c)
        !            40: {
        !            41:        c->name = zend_strndup(c->name, c->name_len - 1);
        !            42:        if (!(c->flags & CONST_PERSISTENT)) {
        !            43:                zval_copy_ctor(&c->value);
        !            44:        }
        !            45: }
        !            46: 
        !            47: 
        !            48: void zend_copy_constants(HashTable *target, HashTable *source)
        !            49: {
        !            50:        zend_constant tmp_constant;
        !            51: 
        !            52:        zend_hash_copy(target, source, (copy_ctor_func_t) copy_zend_constant, &tmp_constant, sizeof(zend_constant));
        !            53: }
        !            54: 
        !            55: 
        !            56: static int clean_non_persistent_constant(const zend_constant *c TSRMLS_DC)
        !            57: {
        !            58:        return (c->flags & CONST_PERSISTENT) ? ZEND_HASH_APPLY_STOP : ZEND_HASH_APPLY_REMOVE;
        !            59: }
        !            60: 
        !            61: 
        !            62: static int clean_non_persistent_constant_full(const zend_constant *c TSRMLS_DC)
        !            63: {
        !            64:        return (c->flags & CONST_PERSISTENT) ? 0 : 1;
        !            65: }
        !            66: 
        !            67: 
        !            68: static int clean_module_constant(const zend_constant *c, int *module_number TSRMLS_DC)
        !            69: {
        !            70:        if (c->module_number == *module_number) {
        !            71:                return 1;
        !            72:        } else {
        !            73:                return 0;
        !            74:        }
        !            75: }
        !            76: 
        !            77: 
        !            78: void clean_module_constants(int module_number TSRMLS_DC)
        !            79: {
        !            80:        zend_hash_apply_with_argument(EG(zend_constants), (apply_func_arg_t) clean_module_constant, (void *) &module_number TSRMLS_CC);
        !            81: }
        !            82: 
        !            83: 
        !            84: int zend_startup_constants(TSRMLS_D)
        !            85: {
        !            86:        EG(zend_constants) = (HashTable *) malloc(sizeof(HashTable));
        !            87: 
        !            88:        if (zend_hash_init(EG(zend_constants), 20, NULL, ZEND_CONSTANT_DTOR, 1)==FAILURE) {
        !            89:                return FAILURE;
        !            90:        }
        !            91:        return SUCCESS;
        !            92: }
        !            93: 
        !            94: 
        !            95: 
        !            96: void zend_register_standard_constants(TSRMLS_D)
        !            97: {
        !            98:        REGISTER_MAIN_LONG_CONSTANT("E_ERROR", E_ERROR, CONST_PERSISTENT | CONST_CS);
        !            99:        REGISTER_MAIN_LONG_CONSTANT("E_RECOVERABLE_ERROR", E_RECOVERABLE_ERROR, CONST_PERSISTENT | CONST_CS);
        !           100:        REGISTER_MAIN_LONG_CONSTANT("E_WARNING", E_WARNING, CONST_PERSISTENT | CONST_CS);
        !           101:        REGISTER_MAIN_LONG_CONSTANT("E_PARSE", E_PARSE, CONST_PERSISTENT | CONST_CS);
        !           102:        REGISTER_MAIN_LONG_CONSTANT("E_NOTICE", E_NOTICE, CONST_PERSISTENT | CONST_CS);
        !           103:        REGISTER_MAIN_LONG_CONSTANT("E_STRICT", E_STRICT, CONST_PERSISTENT | CONST_CS);
        !           104:        REGISTER_MAIN_LONG_CONSTANT("E_DEPRECATED", E_DEPRECATED, CONST_PERSISTENT | CONST_CS);
        !           105:        REGISTER_MAIN_LONG_CONSTANT("E_CORE_ERROR", E_CORE_ERROR, CONST_PERSISTENT | CONST_CS);
        !           106:        REGISTER_MAIN_LONG_CONSTANT("E_CORE_WARNING", E_CORE_WARNING, CONST_PERSISTENT | CONST_CS);
        !           107:        REGISTER_MAIN_LONG_CONSTANT("E_COMPILE_ERROR", E_COMPILE_ERROR, CONST_PERSISTENT | CONST_CS);
        !           108:        REGISTER_MAIN_LONG_CONSTANT("E_COMPILE_WARNING", E_COMPILE_WARNING, CONST_PERSISTENT | CONST_CS);
        !           109:        REGISTER_MAIN_LONG_CONSTANT("E_USER_ERROR", E_USER_ERROR, CONST_PERSISTENT | CONST_CS);
        !           110:        REGISTER_MAIN_LONG_CONSTANT("E_USER_WARNING", E_USER_WARNING, CONST_PERSISTENT | CONST_CS);
        !           111:        REGISTER_MAIN_LONG_CONSTANT("E_USER_NOTICE", E_USER_NOTICE, CONST_PERSISTENT | CONST_CS);
        !           112:        REGISTER_MAIN_LONG_CONSTANT("E_USER_DEPRECATED", E_USER_DEPRECATED, CONST_PERSISTENT | CONST_CS);
        !           113: 
        !           114:        REGISTER_MAIN_LONG_CONSTANT("E_ALL", E_ALL, CONST_PERSISTENT | CONST_CS);
        !           115: 
        !           116: #if SUHOSIN_PATCH
        !           117:        REGISTER_MAIN_LONG_CONSTANT("S_MEMORY", S_MEMORY, CONST_PERSISTENT | CONST_CS);
        !           118:        REGISTER_MAIN_LONG_CONSTANT("S_VARS", S_VARS, CONST_PERSISTENT | CONST_CS);
        !           119:        REGISTER_MAIN_LONG_CONSTANT("S_FILES", S_FILES, CONST_PERSISTENT | CONST_CS);
        !           120:        REGISTER_MAIN_LONG_CONSTANT("S_INCLUDE", S_INCLUDE, CONST_PERSISTENT | CONST_CS);
        !           121:        REGISTER_MAIN_LONG_CONSTANT("S_SQL", S_SQL, CONST_PERSISTENT | CONST_CS);
        !           122:        REGISTER_MAIN_LONG_CONSTANT("S_EXECUTOR", S_EXECUTOR, CONST_PERSISTENT | CONST_CS);
        !           123:        REGISTER_MAIN_LONG_CONSTANT("S_MAIL", S_MAIL, CONST_PERSISTENT | CONST_CS);
        !           124:        REGISTER_MAIN_LONG_CONSTANT("S_SESSION", S_SESSION, CONST_PERSISTENT | CONST_CS);
        !           125:        REGISTER_MAIN_LONG_CONSTANT("S_MISC", S_MISC, CONST_PERSISTENT | CONST_CS);
        !           126:        REGISTER_MAIN_LONG_CONSTANT("S_INTERNAL", S_INTERNAL, CONST_PERSISTENT | CONST_CS);
        !           127:        REGISTER_MAIN_LONG_CONSTANT("S_ALL", S_ALL, CONST_PERSISTENT | CONST_CS);
        !           128: 
        !           129:        /* error levels */
        !           130:        REGISTER_MAIN_LONG_CONSTANT("LOG_EMERG", LOG_EMERG, CONST_CS | CONST_PERSISTENT); /* system unusable */
        !           131:        REGISTER_MAIN_LONG_CONSTANT("LOG_ALERT", LOG_ALERT, CONST_CS | CONST_PERSISTENT); /* immediate action required */
        !           132:        REGISTER_MAIN_LONG_CONSTANT("LOG_CRIT", LOG_CRIT, CONST_CS | CONST_PERSISTENT); /* critical conditions */
        !           133:        REGISTER_MAIN_LONG_CONSTANT("LOG_ERR", LOG_ERR, CONST_CS | CONST_PERSISTENT); 
        !           134:        REGISTER_MAIN_LONG_CONSTANT("LOG_WARNING", LOG_WARNING, CONST_CS | CONST_PERSISTENT);
        !           135:        REGISTER_MAIN_LONG_CONSTANT("LOG_NOTICE", LOG_NOTICE, CONST_CS | CONST_PERSISTENT);
        !           136:        REGISTER_MAIN_LONG_CONSTANT("LOG_INFO", LOG_INFO, CONST_CS | CONST_PERSISTENT);
        !           137:        REGISTER_MAIN_LONG_CONSTANT("LOG_DEBUG", LOG_DEBUG, CONST_CS | CONST_PERSISTENT);
        !           138:        /* facility: type of program logging the message */
        !           139:        REGISTER_MAIN_LONG_CONSTANT("LOG_KERN", LOG_KERN, CONST_CS | CONST_PERSISTENT);
        !           140:        REGISTER_MAIN_LONG_CONSTANT("LOG_USER", LOG_USER, CONST_CS | CONST_PERSISTENT); /* generic user level */
        !           141:        REGISTER_MAIN_LONG_CONSTANT("LOG_MAIL", LOG_MAIL, CONST_CS | CONST_PERSISTENT); /* log to email */
        !           142:        REGISTER_MAIN_LONG_CONSTANT("LOG_DAEMON", LOG_DAEMON, CONST_CS | CONST_PERSISTENT); /* other system daemons */
        !           143:        REGISTER_MAIN_LONG_CONSTANT("LOG_AUTH", LOG_AUTH, CONST_CS | CONST_PERSISTENT);
        !           144:        REGISTER_MAIN_LONG_CONSTANT("LOG_SYSLOG", LOG_SYSLOG, CONST_CS | CONST_PERSISTENT);
        !           145:        REGISTER_MAIN_LONG_CONSTANT("LOG_LPR", LOG_LPR, CONST_CS | CONST_PERSISTENT);
        !           146: #ifdef LOG_NEWS
        !           147:        /* No LOG_NEWS on HP-UX */
        !           148:        REGISTER_MAIN_LONG_CONSTANT("LOG_NEWS", LOG_NEWS, CONST_CS | CONST_PERSISTENT); /* usenet new */
        !           149: #endif
        !           150: #ifdef LOG_UUCP
        !           151:        /* No LOG_UUCP on HP-UX */
        !           152:        REGISTER_MAIN_LONG_CONSTANT("LOG_UUCP", LOG_UUCP, CONST_CS | CONST_PERSISTENT);
        !           153: #endif
        !           154: #ifdef LOG_CRON
        !           155:        /* apparently some systems don't have this one */
        !           156:        REGISTER_MAIN_LONG_CONSTANT("LOG_CRON", LOG_CRON, CONST_CS | CONST_PERSISTENT);
        !           157: #endif
        !           158: #ifdef LOG_AUTHPRIV
        !           159:        /* AIX doesn't have LOG_AUTHPRIV */
        !           160:        REGISTER_MAIN_LONG_CONSTANT("LOG_AUTHPRIV", LOG_AUTHPRIV, CONST_CS | CONST_PERSISTENT);
        !           161: #endif
        !           162: #ifndef PHP_WIN32
        !           163:        REGISTER_MAIN_LONG_CONSTANT("LOG_LOCAL0", LOG_LOCAL0, CONST_CS | CONST_PERSISTENT);
        !           164:        REGISTER_MAIN_LONG_CONSTANT("LOG_LOCAL1", LOG_LOCAL1, CONST_CS | CONST_PERSISTENT);
        !           165:        REGISTER_MAIN_LONG_CONSTANT("LOG_LOCAL2", LOG_LOCAL2, CONST_CS | CONST_PERSISTENT);
        !           166:        REGISTER_MAIN_LONG_CONSTANT("LOG_LOCAL3", LOG_LOCAL3, CONST_CS | CONST_PERSISTENT);
        !           167:        REGISTER_MAIN_LONG_CONSTANT("LOG_LOCAL4", LOG_LOCAL4, CONST_CS | CONST_PERSISTENT);
        !           168:        REGISTER_MAIN_LONG_CONSTANT("LOG_LOCAL5", LOG_LOCAL5, CONST_CS | CONST_PERSISTENT);
        !           169:        REGISTER_MAIN_LONG_CONSTANT("LOG_LOCAL6", LOG_LOCAL6, CONST_CS | CONST_PERSISTENT);
        !           170:        REGISTER_MAIN_LONG_CONSTANT("LOG_LOCAL7", LOG_LOCAL7, CONST_CS | CONST_PERSISTENT);
        !           171: #endif
        !           172:        /* options */
        !           173:        REGISTER_MAIN_LONG_CONSTANT("LOG_PID", LOG_PID, CONST_CS | CONST_PERSISTENT);
        !           174:        REGISTER_MAIN_LONG_CONSTANT("LOG_CONS", LOG_CONS, CONST_CS | CONST_PERSISTENT);
        !           175:        REGISTER_MAIN_LONG_CONSTANT("LOG_ODELAY", LOG_ODELAY, CONST_CS | CONST_PERSISTENT);
        !           176:        REGISTER_MAIN_LONG_CONSTANT("LOG_NDELAY", LOG_NDELAY, CONST_CS | CONST_PERSISTENT);
        !           177: #ifdef LOG_NOWAIT
        !           178:        REGISTER_MAIN_LONG_CONSTANT("LOG_NOWAIT", LOG_NOWAIT, CONST_CS | CONST_PERSISTENT);
        !           179: #endif
        !           180: #ifdef LOG_PERROR
        !           181:        /* AIX doesn't have LOG_PERROR */
        !           182:        REGISTER_MAIN_LONG_CONSTANT("LOG_PERROR", LOG_PERROR, CONST_CS | CONST_PERSISTENT); /*log to stderr*/
        !           183: #endif
        !           184: #endif
        !           185: 
        !           186:        REGISTER_MAIN_LONG_CONSTANT("DEBUG_BACKTRACE_PROVIDE_OBJECT", DEBUG_BACKTRACE_PROVIDE_OBJECT, CONST_PERSISTENT | CONST_CS);
        !           187:        REGISTER_MAIN_LONG_CONSTANT("DEBUG_BACKTRACE_IGNORE_ARGS", DEBUG_BACKTRACE_IGNORE_ARGS, CONST_PERSISTENT | CONST_CS);
        !           188:        /* true/false constants */
        !           189:        {
        !           190:                zend_constant c;
        !           191:        
        !           192:                c.flags = CONST_PERSISTENT | CONST_CT_SUBST;
        !           193:                c.module_number = 0;
        !           194: 
        !           195:                c.name = zend_strndup(ZEND_STRL("TRUE"));
        !           196:                c.name_len = sizeof("TRUE");
        !           197:                c.value.value.lval = 1;
        !           198:                c.value.type = IS_BOOL;
        !           199:                zend_register_constant(&c TSRMLS_CC);
        !           200:                
        !           201:                c.name = zend_strndup(ZEND_STRL("FALSE"));
        !           202:                c.name_len = sizeof("FALSE");
        !           203:                c.value.value.lval = 0;
        !           204:                c.value.type = IS_BOOL;
        !           205:                zend_register_constant(&c TSRMLS_CC);
        !           206: 
        !           207:                c.name = zend_strndup(ZEND_STRL("NULL"));
        !           208:                c.name_len = sizeof("NULL");
        !           209:                c.value.type = IS_NULL;
        !           210:                zend_register_constant(&c TSRMLS_CC);
        !           211: 
        !           212:                c.flags = CONST_PERSISTENT;
        !           213: 
        !           214:                c.name = zend_strndup(ZEND_STRL("ZEND_THREAD_SAFE"));
        !           215:                c.name_len = sizeof("ZEND_THREAD_SAFE");
        !           216:                c.value.value.lval = ZTS_V;
        !           217:                c.value.type = IS_BOOL;
        !           218:                zend_register_constant(&c TSRMLS_CC);
        !           219: 
        !           220:                c.name = zend_strndup(ZEND_STRL("ZEND_DEBUG_BUILD"));
        !           221:                c.name_len = sizeof("ZEND_DEBUG_BUILD");
        !           222:                c.value.value.lval = ZEND_DEBUG;
        !           223:                c.value.type = IS_BOOL;
        !           224:                zend_register_constant(&c TSRMLS_CC);
        !           225:        }
        !           226: }
        !           227: 
        !           228: 
        !           229: int zend_shutdown_constants(TSRMLS_D)
        !           230: {
        !           231:        zend_hash_destroy(EG(zend_constants));
        !           232:        free(EG(zend_constants));
        !           233:        return SUCCESS;
        !           234: }
        !           235: 
        !           236: 
        !           237: void clean_non_persistent_constants(TSRMLS_D)
        !           238: {
        !           239:        if (EG(full_tables_cleanup)) {
        !           240:                zend_hash_apply(EG(zend_constants), (apply_func_t) clean_non_persistent_constant_full TSRMLS_CC);
        !           241:        } else {
        !           242:                zend_hash_reverse_apply(EG(zend_constants), (apply_func_t) clean_non_persistent_constant TSRMLS_CC);
        !           243:        }
        !           244: }
        !           245: 
        !           246: 
        !           247: ZEND_API void zend_register_long_constant(const char *name, uint name_len, long lval, int flags, int module_number TSRMLS_DC)
        !           248: {
        !           249:        zend_constant c;
        !           250:        
        !           251:        c.value.type = IS_LONG;
        !           252:        c.value.value.lval = lval;
        !           253:        c.flags = flags;
        !           254:        c.name = zend_strndup(name, name_len-1);
        !           255:        c.name_len = name_len;
        !           256:        c.module_number = module_number;
        !           257:        zend_register_constant(&c TSRMLS_CC);
        !           258: }
        !           259: 
        !           260: 
        !           261: ZEND_API void zend_register_double_constant(const char *name, uint name_len, double dval, int flags, int module_number TSRMLS_DC)
        !           262: {
        !           263:        zend_constant c;
        !           264:        
        !           265:        c.value.type = IS_DOUBLE;
        !           266:        c.value.value.dval = dval;
        !           267:        c.flags = flags;
        !           268:        c.name = zend_strndup(name, name_len-1);
        !           269:        c.name_len = name_len;
        !           270:        c.module_number = module_number;
        !           271:        zend_register_constant(&c TSRMLS_CC);
        !           272: }
        !           273: 
        !           274: 
        !           275: ZEND_API void zend_register_stringl_constant(const char *name, uint name_len, char *strval, uint strlen, int flags, int module_number TSRMLS_DC)
        !           276: {
        !           277:        zend_constant c;
        !           278:        
        !           279:        c.value.type = IS_STRING;
        !           280:        c.value.value.str.val = strval;
        !           281:        c.value.value.str.len = strlen;
        !           282:        c.flags = flags;
        !           283:        c.name = zend_strndup(name, name_len-1);
        !           284:        c.name_len = name_len;
        !           285:        c.module_number = module_number;
        !           286:        zend_register_constant(&c TSRMLS_CC);
        !           287: }
        !           288: 
        !           289: 
        !           290: ZEND_API void zend_register_string_constant(const char *name, uint name_len, char *strval, int flags, int module_number TSRMLS_DC)
        !           291: {
        !           292:        zend_register_stringl_constant(name, name_len, strval, strlen(strval), flags, module_number TSRMLS_CC);
        !           293: }
        !           294: 
        !           295: 
        !           296: ZEND_API int zend_get_constant(const char *name, uint name_len, zval *result TSRMLS_DC)
        !           297: {
        !           298:        zend_constant *c;
        !           299:        int retval = 1;
        !           300:        char *lookup_name;
        !           301: 
        !           302:        if (zend_hash_find(EG(zend_constants), name, name_len+1, (void **) &c) == FAILURE) {
        !           303:                lookup_name = zend_str_tolower_dup(name, name_len);
        !           304: 
        !           305:                if (zend_hash_find(EG(zend_constants), lookup_name, name_len+1, (void **) &c)==SUCCESS) {
        !           306:                        if (c->flags & CONST_CS) {
        !           307:                                retval=0;
        !           308:                        }
        !           309:                } else {
        !           310:                        static char haltoff[] = "__COMPILER_HALT_OFFSET__";
        !           311: 
        !           312:                        if (!EG(in_execution)) {
        !           313:                                retval = 0;
        !           314:                        } else if (name_len == sizeof("__COMPILER_HALT_OFFSET__")-1 &&
        !           315:                                  !memcmp(name, "__COMPILER_HALT_OFFSET__", sizeof("__COMPILER_HALT_OFFSET__")-1)) {
        !           316:                                char *cfilename, *haltname;
        !           317:                                int len, clen;
        !           318: 
        !           319:                                cfilename = zend_get_executed_filename(TSRMLS_C);
        !           320:                                clen = strlen(cfilename);
        !           321:                                /* check for __COMPILER_HALT_OFFSET__ */
        !           322:                                zend_mangle_property_name(&haltname, &len, haltoff,
        !           323:                                        sizeof("__COMPILER_HALT_OFFSET__") - 1, cfilename, clen, 0);
        !           324:                                if (zend_hash_find(EG(zend_constants), haltname, len+1, (void **) &c) == SUCCESS) {
        !           325:                                        retval = 1;
        !           326:                                } else {
        !           327:                                        retval=0;
        !           328:                                }
        !           329:                                pefree(haltname, 0);
        !           330:                        } else {
        !           331:                                retval=0;
        !           332:                        }
        !           333:                }
        !           334:                efree(lookup_name);
        !           335:        }
        !           336: 
        !           337:        if (retval) {
        !           338:                *result = c->value;
        !           339:                zval_copy_ctor(result);
        !           340:                Z_SET_REFCOUNT_P(result, 1);
        !           341:                Z_UNSET_ISREF_P(result);
        !           342:        }
        !           343: 
        !           344:        return retval;
        !           345: }
        !           346: 
        !           347: ZEND_API int zend_get_constant_ex(const char *name, uint name_len, zval *result, zend_class_entry *scope, ulong flags TSRMLS_DC)
        !           348: {
        !           349:        zend_constant *c;
        !           350:        int retval = 1;
        !           351:        char *colon;
        !           352:        zend_class_entry *ce = NULL;
        !           353:        char *class_name;
        !           354:        zval **ret_constant;
        !           355: 
        !           356:        /* Skip leading \\ */
        !           357:        if (name[0] == '\\') {
        !           358:                name += 1;
        !           359:                name_len -= 1;
        !           360:        }
        !           361: 
        !           362: 
        !           363:        if ((colon = zend_memrchr(name, ':', name_len)) &&
        !           364:            colon > name && (*(colon - 1) == ':')) {
        !           365:                int class_name_len = colon - name - 1;
        !           366:                int const_name_len = name_len - class_name_len - 2;
        !           367:                char *constant_name = colon + 1;
        !           368:                char *lcname;
        !           369: 
        !           370:                class_name = estrndup(name, class_name_len);
        !           371:                lcname = zend_str_tolower_dup(class_name, class_name_len);
        !           372:                if (!scope) {
        !           373:                        if (EG(in_execution)) {
        !           374:                                scope = EG(scope);
        !           375:                        } else {
        !           376:                                scope = CG(active_class_entry);
        !           377:                        }
        !           378:                }
        !           379: 
        !           380:                if (class_name_len == sizeof("self")-1 &&
        !           381:                    !memcmp(lcname, "self", sizeof("self")-1)) {
        !           382:                        if (scope) {
        !           383:                                ce = scope;
        !           384:                        } else {
        !           385:                                zend_error(E_ERROR, "Cannot access self:: when no class scope is active");
        !           386:                                retval = 0;
        !           387:                        }
        !           388:                        efree(lcname);
        !           389:                } else if (class_name_len == sizeof("parent")-1 &&
        !           390:                           !memcmp(lcname, "parent", sizeof("parent")-1)) {
        !           391:                        if (!scope) {
        !           392:                                zend_error(E_ERROR, "Cannot access parent:: when no class scope is active");
        !           393:                        } else if (!scope->parent) {
        !           394:                                zend_error(E_ERROR, "Cannot access parent:: when current class scope has no parent");
        !           395:                        } else {
        !           396:                                ce = scope->parent;
        !           397:                        }
        !           398:                        efree(lcname);
        !           399:                } else if (class_name_len == sizeof("static")-1 &&
        !           400:                           !memcmp(lcname, "static", sizeof("static")-1)) {
        !           401:                        if (EG(called_scope)) {
        !           402:                                ce = EG(called_scope);
        !           403:                        } else {
        !           404:                                zend_error(E_ERROR, "Cannot access static:: when no class scope is active");
        !           405:                        }
        !           406:                        efree(lcname);
        !           407:                } else {
        !           408:                        efree(lcname);
        !           409:                        ce = zend_fetch_class(class_name, class_name_len, flags TSRMLS_CC);
        !           410:                }
        !           411:                if (retval && ce) {
        !           412:                        if (zend_hash_find(&ce->constants_table, constant_name, const_name_len+1, (void **) &ret_constant) != SUCCESS) {
        !           413:                                retval = 0;
        !           414:                                if ((flags & ZEND_FETCH_CLASS_SILENT) == 0) {
        !           415:                                        zend_error(E_ERROR, "Undefined class constant '%s::%s'", class_name, constant_name);
        !           416:                                }
        !           417:                        }
        !           418:                } else if (!ce) {
        !           419:                        retval = 0;
        !           420:                }
        !           421:                efree(class_name);
        !           422:                goto finish;
        !           423:        }
        !           424: 
        !           425:        /* non-class constant */
        !           426:        if ((colon = zend_memrchr(name, '\\', name_len)) != NULL) {
        !           427:                /* compound constant name */
        !           428:                int prefix_len = colon - name;
        !           429:                int const_name_len = name_len - prefix_len - 1;
        !           430:                char *constant_name = colon + 1;
        !           431:                char *lcname;
        !           432:                int found_const = 0;
        !           433: 
        !           434:                lcname = zend_str_tolower_dup(name, prefix_len);
        !           435:                /* Check for namespace constant */
        !           436: 
        !           437:                /* Concatenate lowercase namespace name and constant name */
        !           438:                lcname = erealloc(lcname, prefix_len + 1 + const_name_len + 1);
        !           439:                lcname[prefix_len] = '\\';
        !           440:                memcpy(lcname + prefix_len + 1, constant_name, const_name_len + 1);
        !           441: 
        !           442:                if (zend_hash_find(EG(zend_constants), lcname, prefix_len + 1 + const_name_len + 1, (void **) &c) == SUCCESS) {
        !           443:                        found_const = 1;
        !           444:                } else {
        !           445:                        /* try lowercase */
        !           446:                        zend_str_tolower(lcname + prefix_len + 1, const_name_len);
        !           447:                        if (zend_hash_find(EG(zend_constants), lcname, prefix_len + 1 + const_name_len + 1, (void **) &c) == SUCCESS) {
        !           448:                                if ((c->flags & CONST_CS) == 0) {
        !           449:                                        found_const = 1;
        !           450:                                }
        !           451:                        }
        !           452:                }
        !           453:                efree(lcname);
        !           454:                if(found_const) {
        !           455:                        *result = c->value;
        !           456:                        zval_update_constant_ex(&result, (void*)1, NULL TSRMLS_CC);
        !           457:                        zval_copy_ctor(result);
        !           458:                        Z_SET_REFCOUNT_P(result, 1);
        !           459:                        Z_UNSET_ISREF_P(result);
        !           460:                        return 1;
        !           461:                }
        !           462:                /* name requires runtime resolution, need to check non-namespaced name */
        !           463:                if ((flags & IS_CONSTANT_UNQUALIFIED) != 0) {
        !           464:                        name = constant_name;
        !           465:                        name_len = const_name_len;
        !           466:                        return zend_get_constant(name, name_len, result TSRMLS_CC);
        !           467:                }
        !           468:                retval = 0;
        !           469: finish:
        !           470:                if (retval) {
        !           471:                        zval_update_constant_ex(ret_constant, (void*)1, ce TSRMLS_CC);
        !           472:                        *result = **ret_constant;
        !           473:                        zval_copy_ctor(result);
        !           474:                        INIT_PZVAL(result);
        !           475:                }
        !           476: 
        !           477:                return retval;
        !           478:        }
        !           479: 
        !           480:        return zend_get_constant(name, name_len, result TSRMLS_CC);
        !           481: }
        !           482: 
        !           483: ZEND_API int zend_register_constant(zend_constant *c TSRMLS_DC)
        !           484: {
        !           485:        char *lowercase_name = NULL;
        !           486:        char *name;
        !           487:        int ret = SUCCESS;
        !           488: 
        !           489: #if 0
        !           490:        printf("Registering constant for module %d\n", c->module_number);
        !           491: #endif
        !           492: 
        !           493:        if (!(c->flags & CONST_CS)) {
        !           494:                /* keep in mind that c->name_len already contains the '\0' */
        !           495:                lowercase_name = estrndup(c->name, c->name_len-1);
        !           496:                zend_str_tolower(lowercase_name, c->name_len-1);
        !           497:                name = lowercase_name;
        !           498:        } else {
        !           499:                char *slash = strrchr(c->name, '\\');
        !           500:                if(slash) {
        !           501:                        lowercase_name = estrndup(c->name, c->name_len-1);
        !           502:                        zend_str_tolower(lowercase_name, slash-c->name);
        !           503:                        name = lowercase_name;
        !           504:                } else {
        !           505:                        name = c->name;
        !           506:                }
        !           507:        }
        !           508: 
        !           509:        /* Check if the user is trying to define the internal pseudo constant name __COMPILER_HALT_OFFSET__ */
        !           510:        if ((c->name_len == sizeof("__COMPILER_HALT_OFFSET__")
        !           511:                && !memcmp(name, "__COMPILER_HALT_OFFSET__", sizeof("__COMPILER_HALT_OFFSET__")-1))
        !           512:                || zend_hash_add(EG(zend_constants), name, c->name_len, (void *) c, sizeof(zend_constant), NULL)==FAILURE) {
        !           513:                
        !           514:                /* The internal __COMPILER_HALT_OFFSET__ is prefixed by NULL byte */
        !           515:                if (c->name[0] == '\0' && c->name_len > sizeof("\0__COMPILER_HALT_OFFSET__")
        !           516:                        && memcmp(name, "\0__COMPILER_HALT_OFFSET__", sizeof("\0__COMPILER_HALT_OFFSET__")) == 0) {
        !           517:                        name++;
        !           518:                }
        !           519:                zend_error(E_NOTICE,"Constant %s already defined", name);
        !           520:                free(c->name);
        !           521:                if (!(c->flags & CONST_PERSISTENT)) {
        !           522:                        zval_dtor(&c->value);
        !           523:                }
        !           524:                ret = FAILURE;
        !           525:        }
        !           526:        if (lowercase_name) {
        !           527:                efree(lowercase_name);
        !           528:        }
        !           529:        return ret;
        !           530: }
        !           531: 
        !           532: 
        !           533: /*
        !           534:  * Local variables:
        !           535:  * tab-width: 4
        !           536:  * c-basic-offset: 4
        !           537:  * indent-tabs-mode: t
        !           538:  * End:
        !           539:  */

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