1/* 2 * Copyright (C) 2009 Apple Inc. All rights reserved. 3 * 4 * Redistribution and use in source and binary forms, with or without 5 * modification, are permitted provided that the following conditions 6 * are met: 7 * 1. Redistributions of source code must retain the above copyright 8 * notice, this list of conditions and the following disclaimer. 9 * 2. Redistributions in binary form must reproduce the above copyright 10 * notice, this list of conditions and the following disclaimer in the 11 * documentation and/or other materials provided with the distribution. 12 * 13 * THIS SOFTWARE IS PROVIDED BY APPLE INC. ``AS IS'' AND ANY 14 * EXPRESS OR IMPLIED WARRANTIES, INCLUDING, BUT NOT LIMITED TO, THE 15 * IMPLIED WARRANTIES OF MERCHANTABILITY AND FITNESS FOR A PARTICULAR 16 * PURPOSE ARE DISCLAIMED. IN NO EVENT SHALL APPLE INC. OR 17 * CONTRIBUTORS BE LIABLE FOR ANY DIRECT, INDIRECT, INCIDENTAL, SPECIAL, 18 * EXEMPLARY, OR CONSEQUENTIAL DAMAGES (INCLUDING, BUT NOT LIMITED TO, 19 * PROCUREMENT OF SUBSTITUTE GOODS OR SERVICES; LOSS OF USE, DATA, OR 20 * PROFITS; OR BUSINESS INTERRUPTION) HOWEVER CAUSED AND ON ANY THEORY 21 * OF LIABILITY, WHETHER IN CONTRACT, STRICT LIABILITY, OR TORT 22 * (INCLUDING NEGLIGENCE OR OTHERWISE) ARISING IN ANY WAY OUT OF THE USE 23 * OF THIS SOFTWARE, EVEN IF ADVISED OF THE POSSIBILITY OF SUCH DAMAGE. 24 */ 25 26#ifndef YarrJIT_h 27#define YarrJIT_h 28 29#if ENABLE(YARR_JIT) 30 31#include "VM.h" 32#include "MacroAssemblerCodeRef.h" 33#include "MatchResult.h" 34#include "Yarr.h" 35#include "YarrPattern.h" 36 37#if CPU(X86) && !COMPILER(MSVC) 38#define YARR_CALL __attribute__ ((regparm (3))) 39#else 40#define YARR_CALL 41#endif 42 43namespace JSC { 44 45class VM; 46class ExecutablePool; 47 48namespace Yarr { 49 50class YarrCodeBlock { 51#if CPU(X86_64) || CPU(ARM64) 52 typedef MatchResult (*YarrJITCode8)(const LChar* input, unsigned start, unsigned length, int* output) YARR_CALL; 53 typedef MatchResult (*YarrJITCode16)(const UChar* input, unsigned start, unsigned length, int* output) YARR_CALL; 54 typedef MatchResult (*YarrJITCodeMatchOnly8)(const LChar* input, unsigned start, unsigned length) YARR_CALL; 55 typedef MatchResult (*YarrJITCodeMatchOnly16)(const UChar* input, unsigned start, unsigned length) YARR_CALL; 56#else 57 typedef EncodedMatchResult (*YarrJITCode8)(const LChar* input, unsigned start, unsigned length, int* output) YARR_CALL; 58 typedef EncodedMatchResult (*YarrJITCode16)(const UChar* input, unsigned start, unsigned length, int* output) YARR_CALL; 59 typedef EncodedMatchResult (*YarrJITCodeMatchOnly8)(const LChar* input, unsigned start, unsigned length) YARR_CALL; 60 typedef EncodedMatchResult (*YarrJITCodeMatchOnly16)(const UChar* input, unsigned start, unsigned length) YARR_CALL; 61#endif 62 63public: 64 YarrCodeBlock() 65 : m_needFallBack(false) 66 { 67 } 68 69 ~YarrCodeBlock() 70 { 71 } 72 73 void setFallBack(bool fallback) { m_needFallBack = fallback; } 74 bool isFallBack() { return m_needFallBack; } 75 76 bool has8BitCode() { return m_ref8.size(); } 77 bool has16BitCode() { return m_ref16.size(); } 78 void set8BitCode(MacroAssemblerCodeRef ref) { m_ref8 = ref; } 79 void set16BitCode(MacroAssemblerCodeRef ref) { m_ref16 = ref; } 80 81 bool has8BitCodeMatchOnly() { return m_matchOnly8.size(); } 82 bool has16BitCodeMatchOnly() { return m_matchOnly16.size(); } 83 void set8BitCodeMatchOnly(MacroAssemblerCodeRef matchOnly) { m_matchOnly8 = matchOnly; } 84 void set16BitCodeMatchOnly(MacroAssemblerCodeRef matchOnly) { m_matchOnly16 = matchOnly; } 85 86 MatchResult execute(const LChar* input, unsigned start, unsigned length, int* output) 87 { 88 ASSERT(has8BitCode()); 89 return MatchResult(reinterpret_cast<YarrJITCode8>(m_ref8.code().executableAddress())(input, start, length, output)); 90 } 91 92 MatchResult execute(const UChar* input, unsigned start, unsigned length, int* output) 93 { 94 ASSERT(has16BitCode()); 95 return MatchResult(reinterpret_cast<YarrJITCode16>(m_ref16.code().executableAddress())(input, start, length, output)); 96 } 97 98 MatchResult execute(const LChar* input, unsigned start, unsigned length) 99 { 100 ASSERT(has8BitCodeMatchOnly()); 101 return MatchResult(reinterpret_cast<YarrJITCodeMatchOnly8>(m_matchOnly8.code().executableAddress())(input, start, length)); 102 } 103 104 MatchResult execute(const UChar* input, unsigned start, unsigned length) 105 { 106 ASSERT(has16BitCodeMatchOnly()); 107 return MatchResult(reinterpret_cast<YarrJITCodeMatchOnly16>(m_matchOnly16.code().executableAddress())(input, start, length)); 108 } 109 110#if ENABLE(REGEXP_TRACING) 111 void *get8BitMatchOnlyAddr() 112 { 113 if (!has8BitCodeMatchOnly()) 114 return 0; 115 116 return m_matchOnly8.code().executableAddress(); 117 } 118 119 void *get16BitMatchOnlyAddr() 120 { 121 if (!has16BitCodeMatchOnly()) 122 return 0; 123 124 return m_matchOnly16.code().executableAddress(); 125 } 126 127 void *get8BitMatchAddr() 128 { 129 if (!has8BitCode()) 130 return 0; 131 132 return m_ref8.code().executableAddress(); 133 } 134 135 void *get16BitMatchAddr() 136 { 137 if (!has16BitCode()) 138 return 0; 139 140 return m_ref16.code().executableAddress(); 141 } 142#endif 143 144 void clear() 145 { 146 m_ref8 = MacroAssemblerCodeRef(); 147 m_ref16 = MacroAssemblerCodeRef(); 148 m_matchOnly8 = MacroAssemblerCodeRef(); 149 m_matchOnly16 = MacroAssemblerCodeRef(); 150 m_needFallBack = false; 151 } 152 153private: 154 MacroAssemblerCodeRef m_ref8; 155 MacroAssemblerCodeRef m_ref16; 156 MacroAssemblerCodeRef m_matchOnly8; 157 MacroAssemblerCodeRef m_matchOnly16; 158 bool m_needFallBack; 159}; 160 161enum YarrJITCompileMode { 162 MatchOnly, 163 IncludeSubpatterns 164}; 165void jitCompile(YarrPattern&, YarrCharSize, VM*, YarrCodeBlock& jitObject, YarrJITCompileMode = IncludeSubpatterns); 166 167} } // namespace JSC::Yarr 168 169#endif 170 171#endif // YarrJIT_h 172