|
|
1.1 ! root 1: /* -*- Mode: C; tab-width: 8; indent-tabs-mode: nil; c-basic-offset: 4 -*- ! 2: * ! 3: * ***** BEGIN LICENSE BLOCK ***** ! 4: * Version: MPL 1.1/GPL 2.0/LGPL 2.1 ! 5: * ! 6: * The contents of this file are subject to the Mozilla Public License Version ! 7: * 1.1 (the "License"); you may not use this file except in compliance with ! 8: * the License. You may obtain a copy of the License at ! 9: * http://www.mozilla.org/MPL/ ! 10: * ! 11: * Software distributed under the License is distributed on an "AS IS" basis, ! 12: * WITHOUT WARRANTY OF ANY KIND, either express or implied. See the License ! 13: * for the specific language governing rights and limitations under the ! 14: * License. ! 15: * ! 16: * The Original Code is Mozilla Communicator client code, released ! 17: * March 31, 1998. ! 18: * ! 19: * The Initial Developer of the Original Code is ! 20: * Netscape Communications Corporation. ! 21: * Portions created by the Initial Developer are Copyright (C) 1998 ! 22: * the Initial Developer. All Rights Reserved. ! 23: * ! 24: * Contributor(s): ! 25: * ! 26: * Alternatively, the contents of this file may be used under the terms of ! 27: * either of the GNU General Public License Version 2 or later (the "GPL"), ! 28: * or the GNU Lesser General Public License Version 2.1 or later (the "LGPL"), ! 29: * in which case the provisions of the GPL or the LGPL are applicable instead ! 30: * of those above. If you wish to allow use of your version of this file only ! 31: * under the terms of either the GPL or the LGPL, and not to allow others to ! 32: * use your version of this file under the terms of the MPL, indicate your ! 33: * decision by deleting the provisions above and replace them with the notice ! 34: * and other provisions required by the GPL or the LGPL. If you do not delete ! 35: * the provisions above, a recipient may use your version of this file under ! 36: * the terms of any one of the MPL, the GPL or the LGPL. ! 37: * ! 38: * ***** END LICENSE BLOCK ***** */ ! 39: ! 40: #ifndef jsopcode_h___ ! 41: #define jsopcode_h___ ! 42: /* ! 43: * JS bytecode definitions. ! 44: */ ! 45: #include <stddef.h> ! 46: #include "jsprvtd.h" ! 47: #include "jspubtd.h" ! 48: ! 49: JS_BEGIN_EXTERN_C ! 50: ! 51: /* ! 52: * JS operation bytecodes. ! 53: */ ! 54: typedef enum JSOp { ! 55: #define OPDEF(op,val,name,token,length,nuses,ndefs,prec,format) \ ! 56: op = val, ! 57: #include "jsopcode.tbl" ! 58: #undef OPDEF ! 59: JSOP_LIMIT ! 60: } JSOp; ! 61: ! 62: /* ! 63: * JS bytecode formats. ! 64: */ ! 65: #define JOF_BYTE 0 /* single bytecode, no immediates */ ! 66: #define JOF_JUMP 1 /* signed 16-bit jump offset immediate */ ! 67: #define JOF_CONST 2 /* unsigned 16-bit constant pool index */ ! 68: #define JOF_UINT16 3 /* unsigned 16-bit immediate operand */ ! 69: #define JOF_TABLESWITCH 4 /* table switch */ ! 70: #define JOF_LOOKUPSWITCH 5 /* lookup switch */ ! 71: #define JOF_QARG 6 /* quickened get/set function argument ops */ ! 72: #define JOF_QVAR 7 /* quickened get/set local variable ops */ ! 73: #define JOF_DEFLOCALVAR 8 /* define local var with initial value */ ! 74: #define JOF_JUMPX 9 /* signed 32-bit jump offset immediate */ ! 75: #define JOF_TABLESWITCHX 10 /* extended (32-bit offset) table switch */ ! 76: #define JOF_LOOKUPSWITCHX 11 /* extended (32-bit offset) lookup switch */ ! 77: #define JOF_TYPEMASK 0x000f /* mask for above immediate types */ ! 78: #define JOF_NAME 0x0010 /* name operation */ ! 79: #define JOF_PROP 0x0020 /* obj.prop operation */ ! 80: #define JOF_ELEM 0x0030 /* obj[index] operation */ ! 81: #define JOF_MODEMASK 0x0030 /* mask for above addressing modes */ ! 82: #define JOF_SET 0x0040 /* set (i.e., assignment) operation */ ! 83: #define JOF_DEL 0x0080 /* delete operation */ ! 84: #define JOF_DEC 0x0100 /* decrement (--, not ++) opcode */ ! 85: #define JOF_INC 0x0200 /* increment (++, not --) opcode */ ! 86: #define JOF_INCDEC 0x0300 /* increment or decrement opcode */ ! 87: #define JOF_POST 0x0400 /* postorder increment or decrement */ ! 88: #define JOF_IMPORT 0x0800 /* import property op */ ! 89: #define JOF_FOR 0x1000 /* for-in property op */ ! 90: #define JOF_ASSIGNING JOF_SET /* hint for JSClass.resolve, used for ops ! 91: that do simplex assignment */ ! 92: #define JOF_DETECTING 0x2000 /* object detection flag for JSNewResolveOp */ ! 93: #define JOF_BACKPATCH 0x4000 /* backpatch placeholder during codegen */ ! 94: #define JOF_LEFTASSOC 0x8000 /* left-associative operator */ ! 95: #define JOF_DECLARING 0x10000 /* var, const, or function declaration op */ ! 96: ! 97: #define JOF_TYPE_IS_EXTENDED_JUMP(t) \ ! 98: ((unsigned)((t) - JOF_JUMPX) <= (unsigned)(JOF_LOOKUPSWITCHX - JOF_JUMPX)) ! 99: ! 100: /* ! 101: * Immediate operand getters, setters, and bounds. ! 102: */ ! 103: ! 104: /* Short (2-byte signed offset) relative jump macros. */ ! 105: #define JUMP_OFFSET_LEN 2 ! 106: #define JUMP_OFFSET_HI(off) ((jsbytecode)((off) >> 8)) ! 107: #define JUMP_OFFSET_LO(off) ((jsbytecode)(off)) ! 108: #define GET_JUMP_OFFSET(pc) ((int16)(((pc)[1] << 8) | (pc)[2])) ! 109: #define SET_JUMP_OFFSET(pc,off) ((pc)[1] = JUMP_OFFSET_HI(off), \ ! 110: (pc)[2] = JUMP_OFFSET_LO(off)) ! 111: #define JUMP_OFFSET_MIN ((int16)0x8000) ! 112: #define JUMP_OFFSET_MAX ((int16)0x7fff) ! 113: ! 114: /* ! 115: * When a short jump won't hold a relative offset, its 2-byte immediate offset ! 116: * operand is an unsigned index of a span-dependency record, maintained until ! 117: * code generation finishes -- after which some (but we hope not nearly all) ! 118: * span-dependent jumps must be extended (see OptimizeSpanDeps in jsemit.c). ! 119: * ! 120: * If the span-dependency record index overflows SPANDEP_INDEX_MAX, the jump ! 121: * offset will contain SPANDEP_INDEX_HUGE, indicating that the record must be ! 122: * found (via binary search) by its "before span-dependency optimization" pc ! 123: * offset (from script main entry point). ! 124: */ ! 125: #define GET_SPANDEP_INDEX(pc) ((uint16)(((pc)[1] << 8) | (pc)[2])) ! 126: #define SET_SPANDEP_INDEX(pc,i) ((pc)[1] = JUMP_OFFSET_HI(i), \ ! 127: (pc)[2] = JUMP_OFFSET_LO(i)) ! 128: #define SPANDEP_INDEX_MAX ((uint16)0xfffe) ! 129: #define SPANDEP_INDEX_HUGE ((uint16)0xffff) ! 130: ! 131: /* Ultimately, if short jumps won't do, emit long (4-byte signed) offsets. */ ! 132: #define JUMPX_OFFSET_LEN 4 ! 133: #define JUMPX_OFFSET_B3(off) ((jsbytecode)((off) >> 24)) ! 134: #define JUMPX_OFFSET_B2(off) ((jsbytecode)((off) >> 16)) ! 135: #define JUMPX_OFFSET_B1(off) ((jsbytecode)((off) >> 8)) ! 136: #define JUMPX_OFFSET_B0(off) ((jsbytecode)(off)) ! 137: #define GET_JUMPX_OFFSET(pc) ((int32)(((pc)[1] << 24) | ((pc)[2] << 16) \ ! 138: | ((pc)[3] << 8) | (pc)[4])) ! 139: #define SET_JUMPX_OFFSET(pc,off)((pc)[1] = JUMPX_OFFSET_B3(off), \ ! 140: (pc)[2] = JUMPX_OFFSET_B2(off), \ ! 141: (pc)[3] = JUMPX_OFFSET_B1(off), \ ! 142: (pc)[4] = JUMPX_OFFSET_B0(off)) ! 143: #define JUMPX_OFFSET_MIN ((int32)0x80000000) ! 144: #define JUMPX_OFFSET_MAX ((int32)0x7fffffff) ! 145: ! 146: /* A literal is indexed by a per-script atom map. */ ! 147: #define ATOM_INDEX_LEN 2 ! 148: #define ATOM_INDEX_HI(index) ((jsbytecode)((index) >> 8)) ! 149: #define ATOM_INDEX_LO(index) ((jsbytecode)(index)) ! 150: #define GET_ATOM_INDEX(pc) ((jsatomid)(((pc)[1] << 8) | (pc)[2])) ! 151: #define SET_ATOM_INDEX(pc,index)((pc)[1] = ATOM_INDEX_HI(index), \ ! 152: (pc)[2] = ATOM_INDEX_LO(index)) ! 153: #define GET_ATOM(cx,script,pc) js_GetAtom((cx), &(script)->atomMap, \ ! 154: GET_ATOM_INDEX(pc)) ! 155: #define ATOM_INDEX_LIMIT_LOG2 16 ! 156: #define ATOM_INDEX_LIMIT ((uint32)1 << ATOM_INDEX_LIMIT_LOG2) ! 157: ! 158: /* Actual argument count operand format helpers. */ ! 159: #define ARGC_HI(argc) ((jsbytecode)((argc) >> 8)) ! 160: #define ARGC_LO(argc) ((jsbytecode)(argc)) ! 161: #define GET_ARGC(pc) ((uintN)(((pc)[1] << 8) | (pc)[2])) ! 162: #define ARGC_LIMIT ((uint32)1 << 16) ! 163: ! 164: /* Synonyms for quick JOF_QARG and JOF_QVAR bytecodes. */ ! 165: #define GET_ARGNO(pc) GET_ARGC(pc) ! 166: #define SET_ARGNO(pc,argno) SET_JUMP_OFFSET(pc,argno) ! 167: #define ARGNO_LEN JUMP_OFFSET_LEN ! 168: #define GET_VARNO(pc) GET_ARGC(pc) ! 169: #define SET_VARNO(pc,varno) SET_JUMP_OFFSET(pc,varno) ! 170: #define VARNO_LEN JUMP_OFFSET_LEN ! 171: ! 172: struct JSCodeSpec { ! 173: const char *name; /* JS bytecode name */ ! 174: const char *token; /* JS source literal or null */ ! 175: int8 length; /* length including opcode byte */ ! 176: int8 nuses; /* arity, -1 if variadic */ ! 177: int8 ndefs; /* number of stack results */ ! 178: uint8 prec; /* operator precedence */ ! 179: uint32 format; /* immediate operand format */ ! 180: }; ! 181: ! 182: extern const char js_const_str[]; ! 183: extern const char js_var_str[]; ! 184: extern const char js_function_str[]; ! 185: extern const char js_in_str[]; ! 186: extern const char js_instanceof_str[]; ! 187: extern const char js_new_str[]; ! 188: extern const char js_delete_str[]; ! 189: extern const char js_typeof_str[]; ! 190: extern const char js_void_str[]; ! 191: extern const char js_null_str[]; ! 192: extern const char js_this_str[]; ! 193: extern const char js_false_str[]; ! 194: extern const char js_true_str[]; ! 195: extern const JSCodeSpec js_CodeSpec[]; ! 196: extern uintN js_NumCodeSpecs; ! 197: extern const jschar js_EscapeMap[]; ! 198: ! 199: /* ! 200: * Return a GC'ed string containing the chars in str, with any non-printing ! 201: * chars or quotes (' or " as specified by the quote argument) escaped, and ! 202: * with the quote character at the beginning and end of the result string. ! 203: */ ! 204: extern JSString * ! 205: js_QuoteString(JSContext *cx, JSString *str, jschar quote); ! 206: ! 207: /* ! 208: * JSPrinter operations, for printf style message formatting. The return ! 209: * value from js_GetPrinterOutput() is the printer's cumulative output, in ! 210: * a GC'ed string. ! 211: */ ! 212: extern JSPrinter * ! 213: js_NewPrinter(JSContext *cx, const char *name, uintN indent, JSBool pretty); ! 214: ! 215: extern void ! 216: js_DestroyPrinter(JSPrinter *jp); ! 217: ! 218: extern JSString * ! 219: js_GetPrinterOutput(JSPrinter *jp); ! 220: ! 221: extern int ! 222: js_printf(JSPrinter *jp, const char *format, ...); ! 223: ! 224: extern JSBool ! 225: js_puts(JSPrinter *jp, const char *s); ! 226: ! 227: #ifdef DEBUG ! 228: /* ! 229: * Disassemblers, for debugging only. ! 230: */ ! 231: #include <stdio.h> ! 232: ! 233: extern JS_FRIEND_API(void) ! 234: js_Disassemble(JSContext *cx, JSScript *script, JSBool lines, FILE *fp); ! 235: ! 236: extern JS_FRIEND_API(uintN) ! 237: js_Disassemble1(JSContext *cx, JSScript *script, jsbytecode *pc, uintN loc, ! 238: JSBool lines, FILE *fp); ! 239: #endif /* DEBUG */ ! 240: ! 241: /* ! 242: * Decompilers, for script, function, and expression pretty-printing. ! 243: */ ! 244: extern JSBool ! 245: js_DecompileCode(JSPrinter *jp, JSScript *script, jsbytecode *pc, uintN len); ! 246: ! 247: extern JSBool ! 248: js_DecompileScript(JSPrinter *jp, JSScript *script); ! 249: ! 250: extern JSBool ! 251: js_DecompileFunctionBody(JSPrinter *jp, JSFunction *fun); ! 252: ! 253: extern JSBool ! 254: js_DecompileFunction(JSPrinter *jp, JSFunction *fun); ! 255: ! 256: /* ! 257: * Find the source expression that resulted in v, and return a new string ! 258: * containing it. Fall back on v's string conversion (fallback) if we can't ! 259: * find the bytecode that generated and pushed v on the operand stack. ! 260: * ! 261: * Search the current stack frame if spindex is JSDVG_SEARCH_STACK. Don't ! 262: * look for v on the stack if spindex is JSDVG_IGNORE_STACK. Otherwise, ! 263: * spindex is the negative index of v, measured from cx->fp->sp, or from a ! 264: * lower frame's sp if cx->fp is native. ! 265: */ ! 266: extern JSString * ! 267: js_DecompileValueGenerator(JSContext *cx, intN spindex, jsval v, ! 268: JSString *fallback); ! 269: ! 270: #define JSDVG_IGNORE_STACK 0 ! 271: #define JSDVG_SEARCH_STACK 1 ! 272: ! 273: JS_END_EXTERN_C ! 274: ! 275: #endif /* jsopcode_h___ */
This archive runs on limited infrastructure. Preserving old code on modern bandwidth. Automated agents are requested to crawl responsibly.