⭐ 欢迎来到虫虫下载站! | 📦 资源下载 📁 资源专辑 ℹ️ 关于我们
⭐ 虫虫下载站

📄 jsregexp.c

📁 java script test programing source code
💻 C
📖 第 1 页 / 共 5 页
字号:
                --operatorSP;                switch (operatorStack[operatorSP].op) {                case REOP_ASSERT:                case REOP_ASSERT_NOT:                case REOP_LPAREN:                    operand = NewRENode(state, operatorStack[operatorSP].op);                    if (!operand)                        goto out;                    operand->u.parenIndex =                        operatorStack[operatorSP].parenIndex;                    JS_ASSERT(operandSP);                    operand->kid = operandStack[operandSP - 1];                    operandStack[operandSP - 1] = operand;                    if (state->treeDepth == TREE_DEPTH_MAX) {                        js_ReportCompileErrorNumber(state->context,                                                    state->tokenStream,                                                    JSREPORT_TS |                                                    JSREPORT_ERROR,                                                    JSMSG_REGEXP_TOO_COMPLEX);                        goto out;                    }                    ++state->treeDepth;                    /* FALL THROUGH */                case REOP_LPARENNON:                    state->result = operandStack[operandSP - 1];                    if (!ParseQuantifier(state))                        goto out;                    operandStack[operandSP - 1] = state->result;                    goto restartOperator;                default:                    if (!ProcessOp(state, &operatorStack[operatorSP],                                   operandStack, operandSP))                        goto out;                    --operandSP;                    break;                }            }            break;        case '{':        {            const jschar *errp = state->cp;            if (ParseMinMaxQuantifier(state, JS_TRUE) < 0) {                /*                 * This didn't even scan correctly as a quantifier, so we should                 * treat it as flat.                 */                op = REOP_CONCAT;                goto pushOperator;            }            state->cp = errp;            /* FALL THROUGH */        }        case '+':        case '*':        case '?':            js_ReportCompileErrorNumberUC(state->context, state->tokenStream,                                          JSREPORT_TS | JSREPORT_ERROR,                                          JSMSG_BAD_QUANTIFIER, state->cp);            result = JS_FALSE;            goto out;        default:            /* Anything else is the start of the next term. */            op = REOP_CONCAT;pushOperator:            if (operatorSP == operatorStackSize) {                operatorStackSize += operatorStackSize;                operatorStack = (REOpData *)                    JS_realloc(state->context, operatorStack,                               sizeof(REOpData) * operatorStackSize);                if (!operatorStack)                    goto out;            }            operatorStack[operatorSP].op = op;            operatorStack[operatorSP].errPos = state->cp;            operatorStack[operatorSP++].parenIndex = parenIndex;            break;        }    }out:    if (operatorStack)        JS_free(state->context, operatorStack);    if (operandStack)        JS_free(state->context, operandStack);    return result;}/* * Hack two bits in CompilerState.flags, for use within FindParenCount to flag * its being on the stack, and to propagate errors to its callers. */#define JSREG_FIND_PAREN_COUNT  0x8000#define JSREG_FIND_PAREN_ERROR  0x4000/* * Magic return value from FindParenCount and GetDecimalValue, to indicate * overflow beyond GetDecimalValue's max parameter, or a computed maximum if * its findMax parameter is non-null. */#define OVERFLOW_VALUE          ((uintN)-1)static uintNFindParenCount(CompilerState *state){    CompilerState temp;    int i;    if (state->flags & JSREG_FIND_PAREN_COUNT)        return OVERFLOW_VALUE;    /*     * Copy state into temp, flag it so we never report an invalid backref,     * and reset its members to parse the entire regexp.  This is obviously     * suboptimal, but GetDecimalValue calls us only if a backref appears to     * refer to a forward parenthetical, which is rare.     */    temp = *state;    temp.flags |= JSREG_FIND_PAREN_COUNT;    temp.cp = temp.cpbegin;    temp.parenCount = 0;    temp.classCount = 0;    temp.progLength = 0;    temp.treeDepth = 0;    temp.classBitmapsMem = 0;    for (i = 0; i < CLASS_CACHE_SIZE; i++)        temp.classCache[i].start = NULL;    if (!ParseRegExp(&temp)) {        state->flags |= JSREG_FIND_PAREN_ERROR;        return OVERFLOW_VALUE;    }    return temp.parenCount;}/* * Extract and return a decimal value at state->cp.  The initial character c * has already been read.  Return OVERFLOW_VALUE if the result exceeds max. * Callers who pass a non-null findMax should test JSREG_FIND_PAREN_ERROR in * state->flags to discover whether an error occurred under findMax. */static uintNGetDecimalValue(jschar c, uintN max, uintN (*findMax)(CompilerState *state),                CompilerState *state){    uintN value = JS7_UNDEC(c);    JSBool overflow = (value > max && (!findMax || value > findMax(state)));    /* The following restriction allows simpler overflow checks. */    JS_ASSERT(max <= ((uintN)-1 - 9) / 10);    while (state->cp < state->cpend) {        c = *state->cp;        if (!JS7_ISDEC(c))            break;        value = 10 * value + JS7_UNDEC(c);        if (!overflow && value > max && (!findMax || value > findMax(state)))            overflow = JS_TRUE;        ++state->cp;    }    return overflow ? OVERFLOW_VALUE : value;}/* * Calculate the total size of the bitmap required for a class expression. */static JSBoolCalculateBitmapSize(CompilerState *state, RENode *target, const jschar *src,                    const jschar *end){    uintN max = 0;    JSBool inRange = JS_FALSE;    jschar c, rangeStart = 0;    uintN n, digit, nDigits, i;    target->u.ucclass.bmsize = 0;    target->u.ucclass.sense = JS_TRUE;    if (src == end)        return JS_TRUE;    if (*src == '^') {        ++src;        target->u.ucclass.sense = JS_FALSE;    }    while (src != end) {        uintN localMax = 0;        switch (*src) {        case '\\':            ++src;            c = *src++;            switch (c) {            case 'b':                localMax = 0x8;                break;            case 'f':                localMax = 0xC;                break;            case 'n':                localMax = 0xA;                break;            case 'r':                localMax = 0xD;                break;            case 't':                localMax = 0x9;                break;            case 'v':                localMax = 0xB;                break;            case 'c':                if (src < end && RE_IS_LETTER(*src)) {                    localMax = (jschar) (*src++ & 0x1F);                } else {                    --src;                    localMax = '\\';                }                break;            case 'x':                nDigits = 2;                goto lexHex;            case 'u':                nDigits = 4;lexHex:                n = 0;                for (i = 0; (i < nDigits) && (src < end); i++) {                    c = *src++;                    if (!isASCIIHexDigit(c, &digit)) {                        /*                         * Back off to accepting the original                         *'\' as a literal.                         */                        src -= i + 1;                        n = '\\';                        break;                    }                    n = (n << 4) | digit;                }                localMax = n;                break;            case 'd':                if (inRange) {                    JS_ReportErrorNumber(state->context,                                         js_GetErrorMessage, NULL,                                         JSMSG_BAD_CLASS_RANGE);                    return JS_FALSE;                }                localMax = '9';                break;            case 'D':            case 's':            case 'S':            case 'w':            case 'W':                if (inRange) {                    JS_ReportErrorNumber(state->context,                                         js_GetErrorMessage, NULL,                                         JSMSG_BAD_CLASS_RANGE);                    return JS_FALSE;                }                target->u.ucclass.bmsize = 65535;                return JS_TRUE;            case '0':            case '1':            case '2':            case '3':            case '4':            case '5':            case '6':            case '7':                /*                 *  This is a non-ECMA extension - decimal escapes (in this                 *  case, octal!) are supposed to be an error inside class                 *  ranges, but supported here for backwards compatibility.                 *                 */                n = JS7_UNDEC(c);                c = *src;                if ('0' <= c && c <= '7') {                    src++;                    n = 8 * n + JS7_UNDEC(c);                    c = *src;                    if ('0' <= c && c <= '7') {                        src++;                        i = 8 * n + JS7_UNDEC(c);                        if (i <= 0377)                            n = i;                        else                            src--;                    }                }                localMax = n;                break;            default:                localMax = c;                break;            }            break;        default:            localMax = *src++;            break;        }        if (state->flags & JSREG_FOLD) {            c = JS_MAX(upcase((jschar) localMax), downcase((jschar) localMax));            if (c > localMax)                localMax = c;        }        if (inRange) {            if (rangeStart > localMax) {                JS_ReportErrorNumber(state->context,                                     js_GetErrorMessage, NULL,                                     JSMSG_BAD_CLASS_RANGE);                return JS_FALSE;            }            inRange = JS_FALSE;        } else {            if (src < end - 1) {                if (*src == '-') {                    ++src;                    inRange = JS_TRUE;                    rangeStart = (jschar)localMax;                    continue;                }            }        }        if (localMax > max)            max = localMax;    }    target->u.ucclass.bmsize = max;    return JS_TRUE;}/* *  item:       assertion               An item is either an assertion or *              quantatom               a quantified atom. * *  assertion:  '^'                     Assertions match beginning of string *                                      (or line if the class static property *                                      RegExp.multiline is true). *              '$'                     End of string (or line if the class *                                      static property RegExp.multiline is *                                      true). *              '\b'                    Word boundary (between \w and \W). *              '\B'                    Word non-boundary. * *  quantatom:  atom                    An unquantified atom. *              quantatom '{' n ',' m '}' *                                      Atom must occur between n and m times. *              quantatom '{' n ',' '}' Atom must occur at least n times. *              quantatom '{' n '}'     Atom must occur exactly n times. *              quantatom '*'           Zero or more times (same as {0,}). *              quantatom '+'           One or more times (same as {1,}). *              quantatom '?'           Zero or one time (same as {0,1}). *

⌨️ 快捷键说明

复制代码 Ctrl + C
搜索代码 Ctrl + F
全屏模式 F11
切换主题 Ctrl + Shift + D
显示快捷键 ?
增大字号 Ctrl + =
减小字号 Ctrl + -