bool ExecuteRegExpImpl(JSContext *cx, RegExpStatics *res, T *re, JSLinearString *input, const jschar *chars, size_t length, size_t *lastIndex, RegExpExecType type, Value *rval) { LifoAllocScope allocScope(&cx->tempLifoAlloc()); MatchPairs *matchPairs = NULL; RegExpRunStatus status = re->execute(cx, chars, length, lastIndex, allocScope, &matchPairs); switch (status) { case RegExpRunStatus_Error: return false; case RegExpRunStatus_Success_NotFound: *rval = NullValue(); return true; default: JS_ASSERT(status == RegExpRunStatus_Success); JS_ASSERT(matchPairs); } if (res) res->updateFromMatchPairs(cx, input, matchPairs); *lastIndex = matchPairs->pair(0).limit; if (type == RegExpTest) { *rval = BooleanValue(true); return true; } return CreateRegExpMatchResult(cx, input, chars, length, matchPairs, rval); }
RegExpRunStatus RegExpShared::execute(JSContext *cx, const jschar *chars, size_t length, size_t *lastIndex, MatchPairs **output) { const size_t origLength = length; size_t backingPairCount = RegExpCode::getOutputSize(pairCount()); LifoAlloc &alloc = cx->tempLifoAlloc(); MatchPairs *matchPairs = MatchPairs::create(alloc, pairCount(), backingPairCount); if (!matchPairs) return RegExpRunStatus_Error; /* * |displacement| emulates sticky mode by matching from this offset * into the char buffer and subtracting the delta off at the end. */ size_t start = *lastIndex; size_t displacement = 0; if (sticky()) { displacement = *lastIndex; chars += displacement; length -= displacement; start = 0; } RegExpRunStatus status = code.execute(cx, chars, length, start, matchPairs->buffer(), backingPairCount); switch (status) { case RegExpRunStatus_Error: return status; case RegExpRunStatus_Success_NotFound: *output = matchPairs; return status; default: JS_ASSERT(status == RegExpRunStatus_Success); } matchPairs->displace(displacement); matchPairs->checkAgainst(origLength); *lastIndex = matchPairs->pair(0).limit; *output = matchPairs; return RegExpRunStatus_Success; }