2 **********************************
3 * HipHop Bytecode v1 revision 17 *
4 **********************************
10 HipHop bytecode (HHBC) v1 is intended to serve as the conceptual basis for
11 encoding the semantic meaning of HipHop source code into a format that is
12 appropriate for consumption by interpreters and just-in-time compilers. By
13 using simpler constructs to encode more complex expressesion and statements,
14 HHBC makes it straightforward for an interpreter or a compiler to determine
15 the order of execution for a program.
17 HHBC was designed with several competing goals in mind:
19 1) Run-time efficiency. The design of HHBC should be congruous to implementing
20 an efficient execution engine, whether it be an interpreter or a just-in-time
23 2) PHP 5.4 compatibility. It should be possible to compile valid PHP 5.4 source
24 code into HipHop bytecode in a way that preserves the semantic meaning of the
27 3) Simplicity. The design of HHBC should avoid features that could be removed
28 or simplified without comprimising PHP 5.4 compatibility, run-time efficiency,
29 or design cleanliness.
35 Each HipHop source file is compiled into a separate "compilation unit", or
36 "unit" for short. Units are composed of bytecode and metadata.
38 A unit's bytecode is an array of bytes encoding a sequence of HHBC
39 instructions, where each instruction is encoded using one or more bytes. This
40 specification defines an instruction set and defines the behavior of each HHBC
41 instruction, but the exact byte values used to encode HHBC instructions is
42 currently unspecified.
44 A unit's metadata is a set of structures that provide essential information
45 that is needed at run time by the execution engine. This specification will
46 describe a unit's metadata as a set of named tables with ordered rows, but the
47 exact format of the metadata is currently unspecified.
49 Each instruction in a unit's bytecode can be referred to using a "bytecode
50 offset", which is the distance in bytes from the first byte of a unit's
51 bytecode to the first byte of the instruction.
53 A unit's bytecode is partitioned into sections called "functions". The unit's
54 metadata uses bytecode offsets to specify which instructions belong to which
57 When a unit is loaded at run time, the execution engine assigns the unit's
58 bytecode a logical range of addresses called "bytecode addresses". An
59 instruction is referred to at run time using its bytecode address.
65 HipHop bytecode models the flow of execution using a stack of frames referred
66 to as the "call stack". A "frame" is a structure that logically consists of a
67 header, a program counter (PC), a local variable store, an iterator variable
68 store, an evaluation stack, and a function parameter info (FPI) stack.
70 The frame at the top of the call stack is referred to as the "current frame".
71 The current frame represents the function that is currently executing. The
72 program counter (PC) of the current frame is referred to as the "current PC".
73 At any given time, the current PC holds the bytecode address of the current
74 instruction to execute. When the execution engine executes an instruction, the
75 current PC is updated to point to the next instruction. By default, the current
76 PC is updated to point to the byte that sequentially follows the last byte of
77 the current instruction in the bytecode. Some instructions override the default
78 behavior and explicitly update the current PC in a specific way.
80 HHBC provides special instructions to allow for calling a function and
81 returning from a function. When a function is called, a new frame is pushed
82 onto the call stack, and the PC of the new frame is initialized to the
83 appropriate entry point (typically the instruction of the function that is
84 sequentially first in the bytecode). The new frame becomes the current frame,
85 and the PC of the new frame becomes the current PC. When a function returns,
86 the current frame is popped off the call stack. The previous frame becomes the
87 current frame, and its PC becomes the current PC. The facility provided by the
88 execution engine that is responsible for handling function calls and returns is
89 called the "dispatcher".
91 Typically, a frame is removed from the call stack when its corresponding
92 function returns. However, a frame may be removed from the call stack before
93 its corresponding function returns in the course of processing an exception.
94 The facility provided by the execution engine that is responsible for
95 processing exceptions is called the "unwinder".
101 HHBC instructions may push and pop values on the current frame's evaluation
102 stack and they may read and write values to the current frame's local
103 variables. Values come in three flavors: cells, refs, and classrefs.
105 A "cell" is a structure that contains a type identifier and either data (for
106 non-refcounted types) or a pointer to data (for refcounted types). When a
107 cell containing a pointer is duplicated, the new cell will point to the same
108 data as the original cell. When a cell containing a pointer is duplicated or
109 discarded, the execution engine is responsible for honoring the data's refcount
112 A "ref" is a structure that contains a pointer to a cell container. When a
113 ref is duplicated, the new ref will point to the same container as the
114 original ref. When a ref is duplicated or destroyed, the execution engine is
115 responsible for honoring the containers's refcount logic. When the container
116 is destroyed, the cell it contains is also destroyed.
118 A "classref" is a structure that contains a reference to a class. When a
119 classref is pushed onto the stack or popped of the stack, no refcounting is
122 Values on the evaluation stack may be any of the three flavors listed above.
123 Values stored in local variables may only be cells or refs.
129 A unit's bytecode is organized into functions. Each function has its own
130 metadata that provdes essential information about the function, such as the
131 name of the function, how many local variables it has, how many iterator
132 variables it has, how many formal parameters it has, the names of the local
133 variables, the names of the formal parameters, how each parameter should be
134 passed (pass by value vs. pass by reference), whether each parameter has a
135 default value, and an upper bound for the maximum depth the evaluation stack
136 can reach at run time.
138 Each local variable and iterator variable has an id, and HHBC instructions can
139 reference these variables using these ids. The id space for local variables is
140 distinct from the id space for iterator variables. Thus local id 1 refers to a
141 different variable than iterator id 1. Local variable ids and iterator ids are
142 signed 32-bit integer values. No function may have more than 2^31 - 1 local
143 variables, and no function may have more than 2^31 - 1 iterator variables.
145 Some local variables have names associated with them (called "named local
146 variables"), while other local variables do not have names associated with them
147 (called "unnamed local variables"). All local variables that reference formally
148 declared parameters have names associated with them. Iterator variables do not
149 have names associated with them. Variables that have a name associated with
150 them will appear in the current variable environment (if they are defined),
151 while variables that do not have a name associated with them will never appear
152 in the current variable environment.
154 Formally declared parameters are considered to be local variables. Given a
155 function with n formally declared parameters, local ids 0 through n-1 will be
156 used to reference the formally declared parameters. Formal parameters without
157 default values are called "required parameters", while formal parmeters with
158 default values are called "optional parameters".
160 The bytecode for each function consists of the instructions of the primary
161 function body, optionally followed by the instructions for one or more fault
162 funclets. The metadata for each function specifies one or more entry points for
163 the primary function body, along with information about each fault funclet.
164 Entry points and fault funclets are discussed in more detail in the next
165 section. The total size of the bytecode for the primary function body and all
166 the fault funclets must not exceed 2^31 - 1 bytes. The primary function body
167 and each fault funclet must be a continguous range of bytecode.
169 Each function's metadata provides a "line number table" to allow mapping
170 bytecode offsets back to source line numbers. Each row in the line number table
171 consists of a source line number and a range of bytecode. The table is sorted
172 by starting bytecode offset, lowest offset first. The bytecode offset of the
173 beginning of each instruction in the function must belong to exactly one of the
174 ranges of bytecode in the line number table.
177 Entry points and fault funclets
178 -------------------------------
180 Entry points come in three varieties: the main entry point, DV entry points,
181 and catch entry points.
183 Every function has exactly one main entry point. When a function is called, the
184 dispatcher will set the PC of the new frame to point to the main entry point if
185 either (1) the function does not have any optional parameters or (2) the caller
186 provides values for all of the optional parameters.
188 DV entry points are used to handle initializing optional parameters that the
189 caller did not provide. Each DV entry point enters into a corresponding basic
190 block of instructions that operates directly on the appropriate local variable
191 to set it to its default value. These basic blocks fall through directly into
192 one another and the last basic block ends with a jump to the main entry point.
193 The dispatcher selects the appropriate DV entry point based on the number of
194 arguments passed into the function.
196 The main entry point and DV entry points are used by the dispatcher when
197 handling a function call. Each function's metadata provides an "entry point
198 table". Each row in the entry point table consists of a number of arguments and
199 the bytecode offset of the entry point that should be used by the dispatcher
200 (either the main entry point or a DV entry point).
202 Catch entry points are used to implement "catch" blocks in source code. When an
203 exception is thrown and the unwinder identifies a matching catch, after it
204 unwinds the stack it will transfer control to the catch entry point that
205 corresponds to the matching catch. The caught exception object can be retrieved
206 by the bytecode using the Catch instruction.
208 Fault funclets are used to perform necessary cleanup when a region of code
209 exits abnormally through an exception. When an exception is thrown that exits a
210 region protected by a fault funclet, the unwinder will transfer control to the
211 fault funclet. When a fault funclet executes the Unwind instruction, it
212 transfers control back to the unwinder. Fault funclets are referred to by the
213 bytecode offset of their first instruction.
215 Catch entry points and fault funclets are used by the unwinder when processing
216 an exception. The exact details about how the unwinder uses catch entry points
217 and fault funclets is covered in the next section.
223 The metadata for each function provides an "exception handler (EH) table".
224 Each row in the EH table consists of a kind ("fault" or "catch"), a range
225 of bytecode that constitues the protected region, and an offset of a fault
226 funclet or list of (classname, offset) pairs describing catch entry points.
228 Each range of bytecode is given by a starting offset and an ending
229 offset, where the starting offset is the bytecode offset at the beginning of
230 the first instruction in the range and the ending offset is the bytecode offset
231 after the last instruction in the range. For any pair of protected regions,
232 one of the following must hold: (1) the regions are disjoint and do not
233 overlap, or (2) one of the regions must be nested inside the other region.
235 The offset for each catch target in a "catch" EH row must be within the
236 primary function body. The handler offsets listed in either type of EH
237 row do not need to be unique; i.e. they may appear as a target in multiple
240 When an exception is thrown, control is transferred to the unwinder. The
241 unwinder starts with the current frame and consults the EH table of the
242 corresponding function. The unwinder visits each row in the EH table whose
243 protected region protects the instruction pointed to by the current PC,
244 starting with the row of the innermost protected region, then the row of the
245 next innermost protected region, and so forth. If two rows have identical
246 protected regions, the row occurring first in the EH table will be visited
249 When the unwinder visits a "fault" kind protected region, it transfers control
250 to the corresponding fault funclet. When the fault funclet ends, it transfers
251 control back to the unwinder with the Unwind instruction.
253 When the unwinder visits a "catch" kind protected region, it considers each
254 catch target in the order they appear in the list. If the exception's type is
255 compatible with type of exception handled by the catch block, the unwinder
256 transfers control to the corresponding catch entry point, and normal execution
257 resumes. Otherwise, the unwinder continues visiting protected regions
258 searching for a matching catch.
260 If the unwinder visits all of the relevant protected regions in the current
261 frame's EH table and is unable to find a matching catch, the unwinder pops the
262 current frame off of the call stack, and repeats the process with the previous
263 frame on the call stack. If the unwinder is unable to find a matching catch and
264 pops every frame off the call stack, it transfers control to the unhandled
271 Every compilation unit has a litstr table, a scalar array table, a function
272 table, and a class table.
274 The litstr table maps litstr ids to literal strings. Litstr ids are signed
275 32-bit integer values. Each litstr id must be between 0 and 2^31 - 2 inclusive.
277 The scalar array table maps scalar array ids to a description of the contents
278 of a scalar array. An array is a scalar array if and only if each element of
279 the array is a null, boolean, integer, double, string, or a scalar array.
280 Furthermore, each element of a scalar array must be a cell. Finally, scalar
281 arrays may not recurse infinitely. Each scalar array id must be between 0 and
284 Each row in the function table contains a unique function id, a function name
285 specified by a litstr id, the bytecode offset for the corresponding function,
286 a flag that indicates if the function is unconditionally declared in the
287 outermost scope, and the function metadata. Note that there may be multiple
288 rows in the function table with same function name. However, there may not be
289 multiple rows that are marked as being unconditionally declared in the
290 outermost scope with the same function name. Each function id must be between 0
291 and 2^31 - 2 inclusive.
293 Each row in the class table contains a unique class id, a class name specified
294 by a litstr id, a flag that indicates if the class declaration is hoisted to
295 the prelude of pseudo-main, and the class metadata. Note that there may be
296 multiple rows in the class table with same class name. However, there may not
297 be multiple rows that are marked as being hoisted with the same class name.
298 Each class id must be between 0 and 2^31 - 2 inclusive.
301 Function parameter info (FPI) structures and the FPI stack
302 ----------------------------------------------------------
304 Every function has a function parameter info (FPI) structure associated with it
305 that can be retrieved at run time. The FPI structure contains the bytecode
306 address of the function, the number of parameters the function has, and a
307 parameter table that indicates whether each parameter is pass by value or pass
310 In addition to the evaluation stack, each frame also contains another stack
311 called the FPI stack. Each entry on the FPI stack consists of a reference to an
312 FPI structure and a bytecode address of a function. The entry on the top of the
313 FPI stack is called the "current FPI".
315 The FPush* instructions push a new entry onto the FPI stack, initializing the
316 entry with a reference to the FPI structure for a given function and the
317 bytecode address of the appropriate entry point. The FPass* instructions
318 prepare the parameters that will be passed into the callee. The FCall*
319 instructions look at the current FPI to get the bytecode address of the
320 function (the callee), transfers the parameters from the evaluation stack to
321 the callee, pops the current FPI off of the FPI stack, and then invokes the
322 dispatcher to call the function.
324 Calls to builtin functions may be optimized to avoid pusing an entry on the FPI
325 stack if it is known that the builtin function does not need access to the call
326 stack. In this case, the arguments to the builtin are pushed on stack as Cells
327 and Vars, and the builtin can be invoked with the FCallBuiltin instruction.
328 Unless otherwise noted, subsequent references to FCall* instructions should be
329 meant to refer to non-optimized FCall instructions, i.e. all FCall instructions
330 other than FCallBuiltin.
336 The caller may pass any number of parameters to the callee by executing FPass*
337 instructions zero or more times prior to executing an FCall* instruction. The
338 caller must pass the parameters in forward order, i.e. the first use of FPass*
339 passes the first parameter, the second use of FPass* passes the second
340 parameter, and so forth.
342 The FPush*/FPass*/FCall* instructions can be used to call a global function, a
343 method on an object, or a method from a class. The caller is responsible for
344 evaluating all of the parameters in forward order. When the caller executes an
345 FCall* instruction, the dispatcher creates a new frame and moves the parameters
346 prepared by the caller into the callee's variable environment. The dispatcher
347 then transfers control to the appropriate entry point of the callee (either the
348 main entry point or a DV entry point) based on the number of parameters passed.
350 When the callee executes the Ret* instruction, the dispatcher pushes the return
351 value onto the caller's evaluation stack. Then the dispatcher destroys the
352 callee's frame and transfers control back to the caller.
358 As object properties are accessed during execution, the execution engine is
359 responsible for following certain rules to honor each property's accessibility
362 The accessibility and visibility of a property in a given class is determined
363 by that class's definition and the definitons of all of that class's ancestors.
364 When a property is declared in a class definition (a "declared property") it
365 may be specified as being "public", "protected", or "private". Accessibility
366 and visibility are two related but distinct concepts. Depending on the current
367 context, a property may be visible and accessible, visible but inaccessible, or
368 invisible and inaccessible.
370 If a property P is declared with the "public" qualifier in the definition of
371 class C, for instances of class C and descendent classes the property P will be
372 visible and accessible in all contexts. If C has an ancestor that declares a
373 public property with the same name as P, C is said to "redeclare" property P,
374 and the declaration of P in class C is considered to refer to the same property
375 as the declaration in the ancestor class.
377 If a property P is declared as "protected" in the definition of class C, for
378 instances of class C the property P will be visible in all contexts, but only
379 accessible in the context of class C, an ancestor class, or descendent class.
380 When class C is loaded at run time, a semantic check must be performed to
381 ensure that all ancestor classes of C do not declare a property as "public"
382 with the same name as P. If C has an ancestor that declares a public property
383 with the same name as P, the execution engine must throw a fatal error when
384 class C is loaded. If C has an ancestor that declares a protected property with
385 the same name as P, C is said to "redeclare" property P, and the declaration of
386 P in class C is considered to refer to the same property as the declaration in
387 the ancestor class. Note that there may exist a class D that is a descendent of
388 C and declares a property as "public" with the same name as P. In such cases
389 the new "public" declaration in D is considered to refer to the same property
390 as the original "protected" declaration in C, and the "protected" qualifier
391 from the original declaration is effectively overriden by the "public"
392 qualifier from the new declaration. Class D is said to "redeclare" property P
393 with the "public" qualifier. Thus, for instances of class D and descendent
394 classes of D, property P will be visible and accessible in all contexts.
395 Finally, if a class E that is descendent of C does not redeclare P as public
396 and does not have an ancestor class that redeclares P as public, for instances
397 of class E the property P will be visibile in all contexts, but only accessible
398 in the context of class E, an ancestor class of E, or a descendent class of E.
400 If a property P is declared with the "private" qualifier in the definition of
401 class C, for instances of class C the property P will be visible in all
402 contexts, but only accessible in the context of class C. For instances of
403 descendent classes of C, the property P will be visible and accessible in the
404 context of the class C, and in all other contexts property P will be invisible
405 and inaccessible. When class C is loaded at run time, a semantic check must be
406 performed to ensure that all ancestor classes of C do not declare a property as
407 "public" or "protected" with the same as P. If C has an ancestor that declares
408 a public or protected property with the same name as P, the execution engine
409 must throw a fatal error when class C is loaded. Note that descendent classes
410 of C may declare another property with the same name as P. The declaration of
411 property P as "private" in class C is considered to define a separate property
412 that is distinct from all other properties of the same name declared in
413 ancestor classes and descendent classes of C.
415 An instruction that accesses a property specifies the property by a name N via
416 a litstr id, a local variable id, or a cell consumed from the evaluation stack.
417 As noted above, it is possible for a class to have multiple distinct properties
418 named N. In cases where there are multiple distinct properties named N, the
419 visibility rules are used to determine which property is retrieved. If there is
420 a visible private property P named N, then property P is retrieved. Otherwise,
421 if there is a visible non-private property Q named N, then property Q is
422 retrieved. If there is no visible property named N, the behavior is determined
423 by the specific instruction. The semantic checks and the visibility rules
424 ensure that for any context there cannot be more than one visible private
425 property, and there cannot be more than one visible non-private property.
427 Some instructions can create a new property at run time with a name that is
428 different than the names of all declared properties that are visible in the
429 current context. Such properties are called "non-declared properties" or
430 "dynamic properties". Dynamic properties are considered to be visible and
431 accessible in all contexts.
433 If a declared property is unset, and then re-accessed/re-created, then it is
434 treated the same way as an invisible property with the same attributes as the
435 original declared property. Specifically, if the property gets created again,
436 it must have the same access attributes as the original declared property.
439 Magic property access methods
440 -----------------------------
442 Instructions that access properties may in some cases invoke a magic property
443 access method (__get, __set, __isset, or __unset) if an object implements the
444 method and the method is considered eligible for invocation. A magic property
445 access method is considered "eligible" for a given object if there is not a
446 frame on the call stack that corresponds to an invocation of the same method on
450 Static property access
451 ----------------------
453 As a class's static properties are accessed during execution, the execution
454 engine is responsible for following certain rules to honor each static
455 property's accessibility and visibility.
457 The accessibility and visibility of a static property in a given class is
458 determined by that class's definition and the definitons of all of that class's
459 ancestors. When a static property is declared in a class definition it may be
460 specified as being "public", "protected", or "private". Depending on the
461 current context, a static property may be visible and accessible, visible but
462 inaccessible, or invisible and inaccessible.
464 Conceptually, each class has a "static store" associated with it at run time
465 that provides storage for the static properties declared in the class's
466 definition. Static properties are accessed at run time by name through the
467 scope of a class. When an instruction accesses a static property through the
468 scope of class C, it will search the static store of C and then the static
469 stores of C's ancestors (starting with C's base class and moving up the
470 inheritance chain) for the first static property with the given name that is
471 visible in the current context.
473 If a static property S is declared with the "public" qualifier in the
474 definition of class C, the static property S when accessed through the scope of
475 class C or a descendent of C will be visible and accessible in all contexts.
476 Note that descendent classes of C may declare another static property with the
477 same name as S. The declaration in class C is considered to define a separate
478 static property that is distinct from all other static properties declared in
479 descendent classes of C.
481 If a static property S is declared with the "protected" qualifier in the
482 definition of class C, the static property S when accessed through the scope of
483 class C or a descendent of C will be visible in all contexts, but only
484 accessible in the context of class C, an ancestor class of C, or descendent
485 class of C. When class C is loaded at run time, a semantic check must be
486 performed to ensure that all ancestor classes of C do not declare a static
487 property as "public" with the same name as S. If C has an ancestor that
488 declares a public static property with the same name as S, the execution engine
489 must throw a fatal error when class C is loaded. Note that descendent classes
490 of C may declare another static property with the same name as S. The
491 declaration in class C is considered to define a separate static property that
492 is distinct from all other static properties declared in descendent classes of
495 If a static property S is declared with the "private" qualifier in the
496 definition of class C, the static property S when accessed through the scope of
497 class C will be visible in all contexts, but only accessible in the context of
498 class C. The static property S when accessed through the scope of a descendent
499 of C will only be visible and accessible in the context of class C. When class
500 C is loaded at run time, a semantic check must be performed to ensure that all
501 ancestor classes of C do not declare a static property as "public" or
502 "protected" with the same name as S. If C has an ancestor that declares a
503 public or protected static property with the same name as S, the execution
504 engine must throw a fatal error when class C is loaded. Note that descendent
505 classes of C may declare another static property with the same name as S. The
506 declaration in class C is considered to define a separate static property that
507 is distinct from all other static properties declared in descendent classes of
510 Note that instructions cannot create new static properties in a class that were
511 not declared in the class definition.
517 An FPI region is a continguous range of bytecode that constitutes a call site.
518 Each FPI region begins immediately after an FPush* instruction that pushes an
519 FPI structure onto the FPI stack and must end with the corresponding FCall*
520 instruction that pops that FPI structure off of the FPI stack. If two FPI
521 regions overlap, one of the FPI regions must be completely enclosed by the other
522 FPI region. An FPI region may not contain backward jumps, nor may it contain
523 forward jumps that jump past the end of the FPI region.
525 Each function has an "FPI region table". Each row in the FPI region table
526 consists of the starting offset of the FPI region (the bytecode offset
527 immediately following the FPush* instruction), the ending offset of the FPI
528 region (the bytecode offset of the FCall* instruction), and the number of
529 parameters being passed.
535 Any given value on the stack must either be a cell, ref, or classref at run
536 time. However, at bytecode generation time the specific flavor of a value on
537 the stack is not always known. HipHop bytecode uses symbols called "flavor
538 descriptors" to precisely describe what is known at bytecode generation about
539 the state of the evaluation stack at each instruction boundary.
541 Each instruction description specifies the flavor descriptor produced for each
542 of its outputs. Each description also specifies the flavor descriptor consumed
543 for each of the instruction's inputs.
545 Here is a description of each flavor descriptor:
547 C - cell; specifies that the value must be a cell at run time
548 V - ref; specifies that the value must be a ref at run time
549 A - classref; specifies that the value must be a classref at run time
550 R - return value; specifies that the value may be a cell or a ref at run
551 time; this flavor descriptor is used for return values from function
553 F - function argument; specifies that the value may be a cell or a ref at run
554 time; this flavor descriptor is used for parameter values that are
555 about to be passed into a function
561 Because instructions specify constraints on the flavor descriptor of each
562 input, it is important to be able to determine if a given HHBC program
563 satisfies these constraints. A program that satisfies the constraints on the
564 inputs to each instruction is said to be "flavor-safe".
566 HHBC provides a set of verification rules that can be mechanically applied to
567 verify that an HHBC program is flavor-safe. All valid HHBC programs must be
568 verifiably flavor-safe, and the execution execution may refuse to execute HHBC
569 programs that cannot be verified.
571 At bytecode generation time, what is known about the state of the evaluation
572 stack at a given instruction boundary can be precisely described using flavor
575 In addition to being flavor-safe, there are other invariants that valid
576 HHBC programs must uphold with respect to metadata and how certain instructions
579 Below is the complete list of verifiability rules. If the bytecode to be
580 executed does not come from a trusted source, it is the responsibility of the
581 bytecode execution engine to verify that these invariants hold.
583 1) The depth of the evaluation stack at any given point in the bytecode must
584 the same for all possible control flow paths. The flavor descriptor of any
585 given slot on the evaluation stack at any given point in the bytecode must the
586 same for all possible control flow paths.
588 2) No instruction may consume more values from the evaluation stack than are
589 available at that given point in the bytecode. Likewise, the flavor descriptor
590 of each slot on the evaluation stack must be compatible with the instruction's
591 inputs' flavor descriptors.
593 3) The evaluation stack must be empty at the beginning and end of each
594 try region. The evaluation stack must also be empty at any offset
595 listed as a catch entry point.
597 4) If a given instruction is not the target of a forward branch and it follows
598 a Jmp, Switch, SSwitch, RetC, RetV, Unwind, Fatal, Throw, NativeImpl, or
599 ContHandle instruction, the evaluation stack before executing the given
600 instruction must be empty.
602 5) Before executing the RetC instruction, the evaluation stack must contain
603 exactly one value and the flavor descriptor of the value must be cell.
604 Likewise, before executing the RetV instruction, the evaluation stack must
605 contain exactly one value and the flavor descriptor of the value must be the
606 ref. Finally, before executing the Unwind instruction, the evaluation stack
609 6) The code for the primary function body and fault funclets must be laid out
610 in order in one contiguous block, starting with the primary function body and
611 optionally followed by one or more fault funclets. The code for primary
612 function body may not jump into the code for the funclets. Similarly, the code
613 for a funclet may not jump into the code for the primary function body or
616 7) The primary function body and each fault funclet must end with one of the
617 following instructions: Jmp, Switch, SSwitch, RetC, RetV, Unwind, Fatal, Throw,
618 NativeImpl, or ContHandle. The primary function body may not contain the Unwind
619 instruction. Also, fault funclets may not contain the Ret* instructions.
621 8) Each FPI region enumerated in the FPI region table must start with an FPush*
622 instruction and it must end with an FCall* instruction. Each use of the FPush*
623 instruction must be the first instruction in exactly one FPI region. Likewise,
624 each use of the FCall* instruction must be the last instruction in exactly one
625 FPI region. Finally, the FPass* instructions may not be used outside an FPI
628 9) Each FPI region may not contain backward jumps, nor may it contain forward
629 jumps that jump outside the end of the FPI region. Also, there may not be jumps
630 anywhere in the function that transfer control from the outside of a given FPI
631 region to the inside of that region. Finally, an FPI region may not contain the
632 Ret*, Unwind, Throw, or Fatal instructions.
634 10) The depth of the FPI stack at any given point in the bytecode must be the
635 same for all possible control flow paths. Also, for any given FPI region that
636 passes n parameters, all possible control flow paths from the beginning of the
637 region to the end must pass through exactly n FPass* instructions associated
638 with the region which pass the parameters in forward order.
640 11) Given an evaluation stack of depth n after an FPush* instruction, the
641 evaluation stack before the corresponding FCall* instruction must also have a
642 depth of n. Likewise, the evaluation stack after corresponding FPass*
643 instructions must have a depth of n as well. Finally, no instruction between an
644 FPush* and its corresponding FCall* may consume any of the values from the
645 evaluation stack that were pushed onto the stack before the FPush* instruction.
647 12) The initialization 'state' of each iterator variable must be known at every
648 point in the code and must be the same for all control paths. There are three
649 possible states: (1) uninitialized, (2) "iter-initialized" (initialized via
650 IterInit*), and (3) "miter-initialized" (initialized via MIterInit*). Every
651 range of bytecode for which an iterator variable i is initialized must be
652 protected by a fault funclet that unsets i by calling IterFree or MIterFree so
653 that when the unwinder or dispatcher pops the current frame, each iterator
654 variable is uninitialized.
656 13) The iterator variable referenced by IterInit* or MIterInit* or
657 DecodeCufIter must be in the uninitialized state when the instruction
658 executes. An iterator variable referenced by IterNext* and IterFree must be
659 in the "iter-initialized" state, an iterator variable referenced by MIterNext*
660 or MIterFree must be in the "miter-initialized" state, and an iterator variable
661 referenced by FPushCufIter or CIterFree must be in the citer-initialized state.
662 Note that IterInit* and MIterInit* conditionally initialize the iterator variable,
663 and IterNext* and MIterNext* conditionally free the iterator variable.
669 Each instruction description below consists of a mnemonic, followed by 0 or
670 more immediate operands, followed by a stack transition description of the form
671 "[xn,...,x2,x1] -> [ym,...,y2,y1]", where "[xn,...,x2,x1]" is a list of flavor
672 descriptors describing what the instruction consumes from the evaluation stack
673 and "[ym,...,y2,y1]" is the list of flavor descriptors describing what the
674 instruction pushes onto the stack. x1 and y1 represent the topmost stack
675 elements before and after execution, respectively.
677 Each element of a stack transition may also contain an optional type
678 annotation. Here is the list of the type annotations used in instruction
681 Null - denotes the null type
682 Bool - denotes the boolean type
683 Int - denotes the integer type
684 Dbl - denotes the double-precision floating-point type
685 Str - denotes the string type
686 Arr - denotes the array type
687 Obj - denotes the object type
689 Multiple type annotations may be combined together using the "|" symbol. For
690 example, the type annotation "Int|Dbl" means that a value is either integer or
693 Some instructions may contain multiple stack transition descriptions to express
694 the relationship between the types of the values consumed from the stack and
695 types of the values pushed onto the stack. Also, in some stack transition
696 descriptions, "<T>" is used as shorthand to represent any one specific type.
697 For example, a transition such as "[C:<T>] -> [C:<T>]" indicates that the type
698 of value that the instruction pushes onto the stack will match the type of
699 value that it consumed from the stack. Likewise, "<F>" is used as shorthand to
700 represent any one specific flavor descriptor.
702 $1 is used to refer to the value at the top of the evaluation stack, $2 is used
703 to refer to the value directly below $1 on the evaluation stack, $3 is used to
704 refer to the value directly below $2, and so forth. Also, %1 is used to refer
705 to the first immediate argument, and %2 is used to refer to the second
708 Note that the relative offset immediate used by a Jmp*, Iter*, MIter*, Switch,
709 or SSwitch instruction is relative the beginning of the instruction.
711 There are numerous instructions that operate on different kinds of locations.
712 Locations are specified using "location descriptors". The complete list of
713 location descriptors is given below:
715 L - local id; location is the local variable whose id is given by an
717 N - local name; location is the local variable whose name is given by the
719 G - global name; location is the global variable whose name is given by the
721 S - static property; location is the static property whose class is given by
722 a classref and whose name is given by value of a cell.
723 C - cell; location is a temporary value given by a cell.
724 R - return value; location is a temporary value given by a cell or a ref
725 H - $this; location is the $this pointer in the current frame. Must
726 only be used in a frame that is known to have a non-null $this
727 pointer; CheckThis is most commonly used to ensure this.
729 There are several groups of similarly named instructions where the name of each
730 instruction ends with a different location descriptor (for example, Set*). Each
731 instruction in the group perform similar actions but take different kinds of
732 inputs to specify the location to access.
734 The Member instructions provide functionality to operate on elements and
735 properties. These instructions incorporate an immediate argument vector which
736 specifies a location descriptor (defined above) followed by one or more member
739 EC - consume a cell from the evaluation stack as an element
740 EL:<id> - consume a local given by an immediate id as an element
741 ET:<id> - consume a litstr given by an immediate id as an element
742 EI:<int>- consume a immediate integer as an element
743 PC - consume a cell from the evaluation stack as a property
744 PL:<id> - consume a local given by an immediate id as a property
745 PT:<id> - consume a litstr given by an immediate id as a property
746 W - synthesize a new element (no corresponding local variable or
747 evaluation stack slot)
749 For example, the following correspondence exists (ignoring setup bytecode):
751 Source code: $a[3][$b][]['hi'] = 42;
752 Bytecode: SetM <L:0 EI:3 EL:1 W ET:hi>
755 Instructions that have an immediate argument vector have different stack
756 transition descriptions depending on the kind of location descriptor and member
757 descriptors contained in the immediate argument vector. Member instructions
758 denote the immediate argument vector using the notation "<loc-desc/M-vector>"
759 and "C..C" is used to indicate that the member instructions consume a variable
760 number of cells from the stack. In most cases the immediate vector arguments
761 are ordered such that the loc-desc comes first (deepest in the stack), with the
762 last M-vector element last (shallowest in the stack). However, classrefs that
763 are part of the BaseSC and BaseSL loc-desc inputs always come last (the cell
764 input to BaseSC comes first though). Instuctions accepting an immediate vector
765 containing a list of iterators and iterator types use the notation "<iter-vec>".
767 In addition to describing each instruction, this instruction set documentation
768 also describes several operations that encapsulate fundamental, but non-trivial
769 processes that are shared by the Member instructions.
771 The instruction set is organized into the following sections:
772 1. Basic instructions
773 2. Literal and constant instructions
774 3. Operator instructions
775 4. Control flow instructions
777 6. Isset, Empty and type querying instructions
778 7. Mutator instructions
781 10. Member instructions
782 11. Iterator instructions
783 12. Include, eval, and define instructions
784 13. Miscellaneous instructions
785 14. Continuation creation and execution
788 1. Basic instructions
789 ---------------------
793 No operation. This instruction does nothing.
799 Pop. Discards the value on the top of the stack.
801 Dup [C:<T>] -> [C:<T> C:<T>]
803 Duplicate. Duplicates the cell $1 and pushes it onto the stack.
805 Box [C:<T>] -> [V:<T>]
807 Box. Creates a new ref, sets the new ref to point at a copy of cell $1, and
808 pushes the ref onto the stack.
810 Unbox [V:<T>] -> [C:<T>]
812 Unbox. Creates a copy of the cell that ref $1 points to, and pushes the cell
815 BoxR [R:<T>] -> [V:<T>]
817 Box. If $1 is a ref at run time, this instruction does nothing.
819 If $1 is a cell at run time, this instruction creates a new ref, sets the new
820 ref to point at a copy of cell $1, and pushes the ref onto the stack.
822 UnboxR [R:<T>] -> [C:<T>]
824 Unbox. If $1 is a cell at run time, this instruction does nothing.
826 If $1 is a ref at run time, this instruction creates a copy of the cell that
827 ref $1 points to, and pushes the cell onto the stack.
830 2. Literal and constant instructions
831 ------------------------------------
837 Push constant. Null pushes null onto the stack, True pushes true onto
838 the stack, and False pushes false onto the stack.
840 NullUninit [] -> [C:Uninit]
842 Push Uninit Null Cell onto stack.
844 Int <signed 64-bit integer value> [] -> [C:Int]
845 Double <double value> [] -> [C:Dbl]
846 String <litstr id> [] -> [C:Str]
847 Array <scalar array id> [] -> [C:Arr]
849 Push immediate. Pushes %1 onto the stack.
851 NewArray [] -> [C:Arr]
853 New array. Creates a new empty array and pushes it onto the stack.
855 NewPackedArray <num elems> [C..C] -> [C]
857 New array. Creates a new array from the top %1 cells on the stack,
858 pops those cells, then pushes the new array onto the stack. Elements
859 are implicitly numbered from 0 to num elems - 1; $1 is at index 0,
860 $2 is at 1, and so on. %1 must be greater than zero.
862 AddElemC [C C C] -> [C:Arr]
864 Add element. If $3 is an array, this instruction executes $3[$2] = $1 and
865 then pushes $3 onto the stack.
867 If $3 is not an array, this instruction throws a fatal error.
869 AddElemV [C C V] -> [C:Arr]
871 Add element. If $3 is an array, this instruction executes $3[$2] = &$1 and
872 then pushes $3 onto the stack.
874 If $3 is not an array, this instruction throws a fatal error.
876 AddNewElemC [C C] -> [C:Arr]
878 Add new element. If $2 is an array, this instruction executes $2[] = $1 and
879 then pushes $2 onto the stack.
881 If $2 is not an array, this instruction throws a fatal error.
883 AddNewElemV [C V] -> [C:Arr]
885 Add new element. If $2 is an array, this instruction executes $2[] = &$1 and
886 then pushes $2 onto the stack.
888 If $2 is not an array, this instruction throws a fatal error.
890 NewCol <coll type> <num elems> [] -> [C:Obj]
892 New collection. Creates a new collection of type %1 with an initial capacity
893 sufficient to hold the number of elements specified by %2, and pushes the
894 collection onto the stack.
896 ColAddElemC [C C C] -> [C:Obj]
898 Collection add key/value pair. If $3 is a collection object, this instruction
899 executes $3[$2] = $1 and then pushes $3 onto the stack.
901 If $3 is not a collection object, this instruction throws a fatal error.
903 ColAddNewElemC [C C] -> [C:Obj]
905 Collection add value. If $2 is a collection object, this instruction executes
906 $2[] = $1 and then pushes $2 onto the stack.
908 If $2 is not a collection object, this instruction throws a fatal error.
910 Cns <litstr id> [] -> [C:Null|Bool|Int|Dbl|Str]
912 Get constant. Pushes the value of the global constant named %1 onto the stack
913 as a cell. If there is no constant named %1, this instruction raises a notice
914 and pushes the string %1 onto the stack as a cell.
916 CnsE <litstr id> [] -> [C:Null|Bool|Int|Dbl|Str]
918 Get constant. Pushes the value of the global constant named %1 onto the stack
919 as a cell. If there is no constant named %1, throws a fatal error.
921 CnsU <litstr id> <litstr fallback> [] -> [C:Null|Bool|Int|Dbl|Str]
923 Get constant. Identical to Cns except returns constant named %2 if the
924 constant named %1 is undefined.
926 ClsCns <litstr id> [A] -> [C:Null|Bool|Int|Dbl|Static Str]
928 Get class constant. This instruction pushes the value of the class constant
929 named %1 from class $1 onto the stack. If there is no class constant named %1
930 in class $1, this instruction throws a fatal error.
932 ClsCnsD <litstr id> <litstr id> [] -> [C:Null|Bool|Int|Dbl|Static Str]
934 Get class constant (direct). This instruction first checks if %2 matches the
935 name of a defined class. If %2 does not match the name of a defined class,
936 this instruction will invoke the autoload facility passing in the class name
937 %2, and then it will again check if %2 matches the name of a defined class.
938 If %2 still does not match the name of a defined class this instruction
939 throws a fatal error.
941 Next, this instruction pushes the value of the class constant named %1 from
942 class %2 onto the stack. If there is no class constant named %1 in class %2,
943 this instruction throws a fatal error.
948 Push string. File pushes __FILE__ onto the stack, and Dir pushes __DIR__ onto
952 3. Operator instructions
953 ------------------------
955 Concat [C C] -> [C:Str]
957 Concatenation (.). Pushes ((string)$2 . (string)$1) on the stack.
961 Absolute value. Computes the absolute value of $1 and pushes the result onto
964 Add [C:Arr C:Arr] -> [C:Arr]
965 [C:<T2> C:<T1>] -> [C:Dbl] (where T1 == Dbl || T2 == Dbl)
966 [C:<T2> C:<T1>] -> [C:Int] (where T1 != Dbl && T2 != Dbl &&
967 (T1 != Arr || T2 != Arr))
969 Addition (+). Performs addition (or plus-merge if $1 and $2 are both arrays).
970 Pushes ($2 + $1) onto the stack. This instruction throws a fatal error if
971 is_array($1) xor is_array($2) is true.
973 Sub [C:<T2> C:<T1>] -> [C:Dbl] (where T1 == Dbl || T2 == Dbl)
974 [C:<T2> C:<T1>] -> [C:Int] (where T1 != Dbl && T2 != Dbl)
976 Subtraction (-). Pushes ($2 - $1) onto the stack. This instruction throws a
977 fatal error if is_array($1) || is_array($2) is true.
979 Mul [C:<T2> C:<T1>] -> [C:Dbl] (where T1 == Dbl || T2 == Dbl)
980 [C:<T2> C:<T1>] -> [C:Int] (where T1 != Dbl && T2 != Dbl)
982 Multiplication (*). Pushes ($2 * $1) onto the stack. This instruction throws
983 a fatal error if is_array($1) || is_array($2) is true.
985 Div [C C] -> [C:Bool|Int|Dbl]
986 [C:Dbl C:Int] -> [C:Bool|Dbl]
987 [C:Int C:Dbl] -> [C:Bool|Dbl]
988 [C:Dbl C:Dbl] -> [C:Bool|Dbl]
990 Division (/). Pushes ($2 / $1) onto the stack. This instruction throws a
991 fatal error if is_array($1) || is_array($2) is true.
993 Mod [C C] -> [C:Bool|Int]
995 Modulus (%). Pushes ((int)$2 % (int)$1) onto the stack. This instruction
996 never throws a fatal error.
998 Sqrt [C] -> [C:Null|Dbl]
1000 Square root. Computes the square root of $1 and pushes the result onto
1001 the stack. If $1 is not null, a bool, an int, a double, or a numeric
1002 string, it raises a warning and pushes null onto the stack.
1004 If $1 is a negative number, this instruction pushes a floating-point
1005 value representing NAN onto the stack.
1007 Xor [C C] -> [C:Bool]
1009 Logical xor (xor). Pushes ((bool)$2 xor (bool)$1) onto the stack.
1013 Logical not (!). Pushes (!(bool)$1) onto the stack.
1015 Same [C C] -> [C:Bool]
1017 Same (===). Pushes ($2 === $1) onto the stack.
1019 NSame [C C] -> [C:Bool]
1021 Not same (!==). Pushes ($2 !== $1) onto the stack.
1023 Eq [C C] -> [C:Bool]
1025 Equals (==). Pushes ($2 == $1) onto the stack.
1027 Neq [C C] -> [C:Bool]
1029 Not equal (!=). Pushes ($2 != $1) onto the stack.
1031 Lt [C C] -> [C:Bool]
1033 Less than (<). Pushes ($2 < $1) onto the stack.
1035 Lte [C C] -> [C:Bool]
1037 Less than or equal to (<=). Pushes ($2 <= $1) onto the stack.
1039 Gt [C C] -> [C:Bool]
1041 Greater than (>). Pushes ($2 > $1) onto the stack.
1043 Gte [C C] -> [C:Bool]
1045 Greater than or equal to (>=). Pushes ($2 >= $1) onto the stack.
1047 BitAnd [C:<T2> C:<T1>] -> [C:Int] (where T1 != Str || T2 != Str)
1048 [C:Str C:Str] -> [C:Str]
1050 Bitwise and (&). Pushes ($2 & $1) onto the stack. If either $1 or $2 is an
1051 object, this instruction throws a fatal error.
1053 BitOr [C:<T2> C:<T1>] -> [C:Int] (where T1 != Str || T2 != Str)
1054 [C:Str C:Str] -> [C:Str]
1056 Bitwise or (|). Pushes ($2 | $1) onto the stack. If either $1 or $2 is an
1057 object, this instruction throws a fatal error.
1059 BitXor [C:<T2> C:<T1>] -> [C:Int] (where T1 != Str || T2 != Str)
1060 [C:Str C:Str] -> [C:Str]
1062 Bitwise xor (^). Pushes ($2 ^ $1) onto the stack. If either $1 or $2 is an
1063 object, this instruction throws a fatal error.
1065 BitNot [C:<T>] -> [C:Int] (where T != Str)
1068 Bitwise not (~). Pushes (~$1) onto the stack. If $1 is null, a boolean, an
1069 array, or an object, this instruction throws a fatal error.
1071 Shl [C C] -> [C:Int]
1073 Shift left (<<). Pushes ((int)$2 << (int)$1) onto the stack. This instruction
1074 never throws a fatal error.
1076 Shr [C C] -> [C:Int]
1078 Shift right (>>). Pushes ((int)$2 >> (int)$1) onto the stack. This
1079 instruction never throws a fatal error.
1081 Floor [C] -> [C:Dbl]
1083 Round $1 to nearest integer value not greater than $1. Converts $1 to
1084 numeric as appropriate and then takes floor of resulting numeric value.
1088 Round $1 to nearest integer value not less than $1. Converts $1 to numeric
1089 as appropriate and then takes ceil of resulting numeric value.
1091 CastBool [C] -> [C:Bool]
1093 Cast to boolean ((bool),(boolean)). Pushes (bool)$1 onto the stack.
1095 CastInt [C] -> [C:Int]
1097 Cast to integer ((int),(integer)). Pushes (int)$1 onto the stack.
1099 CastDouble [C] -> [C:Dbl]
1101 Cast to double ((float),(double),(real)). Pushes (double)$1 onto the stack.
1103 CastString [C] -> [C:Str]
1105 Cast to string ((string),(binary)). Pushes (string)$1 onto the stack. If $1
1106 is an object that implements the __toString method, the string cast returns
1107 $1->__toString(). If $1 is an object that does not implement __toString
1108 method, the string cast throws a fatal error.
1110 CastArray [C] -> [C:Arr]
1112 Cast to array ((array)). Pushes (array)$1 onto the stack.
1114 CastObject [C] -> [C:Obj]
1116 Cast to object ((object)). Pushes (object)$1 onto the stack.
1118 InstanceOf [C C] -> [C:Bool]
1120 Instance of (instanceof). If $1 is a string and it matches the name of a
1121 defined class and $2 is an object that is an instance of $1, this instruction
1122 pushes true onto the stack. If $1 is an object and get_class($1) matches the
1123 name of a defined class and $2 is an object that is an instance of
1124 get_class($1), this instruction pushes true onto the stack. If $1 is not a
1125 string or an object, this instruction throws a fatal error.
1127 InstanceOfD <litstr id> [C] -> [C:Bool]
1129 Instance of direct (instanceof). If %1 matches the name of a defined class
1130 and $1 is an instance of the %1, this instruction pushes true onto the stack,
1131 otherwise it pushes false onto the stack.
1133 Print [C] -> [C:Int]
1135 Print (print). Outputs (string)$1 to STDOUT and pushes the integer value 1
1138 Clone [C] -> [C:Obj]
1140 Clone (clone). Clones $1 and pushes it onto the stack. If $1 is not an
1141 object, this instruction throws a fatal error.
1143 Exit [C] -> [C:Null]
1145 Exit (exit). Terminates execution of the program.
1147 If $1 is an integer, this instruction will set the exit status to $1, push
1148 null onto the stack, and then it will terminate execution.
1150 If $1 is not an integer, this instruction will output (string)$1 to STDOUT,
1151 set the exit status to 0, push null onto the stack, and then it will
1152 terminate execution.
1154 Fatal <skip frame> [C] -> []
1156 Fatal. This instruction throws a fatal error using $1 as the error message.
1157 If $1 is not a string, this instruction throws a fatal error with an error
1158 message that indicates that the error message was not a string.
1159 Setting %1 to 0 will include the full backtrace.
1160 Setting %1 to 1 will make the backtrace not include the topmost frame. This
1161 is useful when fatalling from functions that shouldn't be seen from userland.
1164 4. Control flow instructions
1165 ----------------------------
1167 Jmp <rel offset> [] -> []
1169 Jump. Transfers control to the location specified by %1.
1171 JmpZ <rel offset> [C] -> []
1173 Jump if zero. Conditionally transfers control to the location specified by %1
1174 if (bool)$1 == (bool)0.
1176 JmpNZ <rel offset> [C] -> []
1178 Jump if not zero. Conditionally transfers control to the location specified
1179 by %1 if (bool)$1 != (bool)0.
1181 Switch <offset vector> <base> <bounded> [C] -> []
1183 Switch over integer case values. If bounded == 0, the implementation will
1184 assume that $1 is an integer in the range [0, length(vector)) and
1185 unconditionally transfer control to the location specified by
1186 vector[$1]. Undefined behavior will result if $1 is not an integer inside
1187 this range. If bounded != 0, the following rules take over:
1189 For a bounded Switch, the last two elements of the offset vector are special:
1190 they represent the first non-zero case and the default case,
1191 respectively. base + length(vector) - 2 must not be greater than 2^63-1. If
1192 $1 === true, control will be transferred to the location specified by
1193 vector[length(vector) - 2]. If $1 is equal (as defined by Eq) to any integer
1194 $n in the range [base, base + length(vector) - 2), control will be
1195 transferred to the location specified by vector[$n - base]. Otherwise,
1196 control will be transferred to the location specified by
1197 vector[length(vector) - 1].
1199 SSwitch <litstr id/offset vector> [C] -> []
1201 Switch over string case values. This instruction will search the
1202 string/offset vector from the beginning until it finds a string that is equal
1203 to $1. If one is found, control will be transferred to the location specified
1204 by the offset corresponding to that string. If a matching string is not
1205 found, control is transferred to the location specified by the final element
1211 Return. Returns $1 to the caller. This instruction may not be used inside
1212 default value funclets or fault funclets.
1216 Unwind. Transfers control back to the unwinder. This instruction may only be
1217 used inside a fault funclet.
1221 Throw. Throws the object $1. If $1 is not an object that extends the
1222 Exception class, this instruction throws a fatal error.
1228 CGetL <local variable id> [] -> [C]
1230 Get local as cell. If the local variable given by %1 is defined, this
1231 instruction gets the value of the local variable and pushes it onto the stack
1232 as a cell. If the local variable is not defined, this instruction raises a
1233 warning and pushes null onto the stack.
1235 CGetL2 <local variable id> [<F>:<T>] -> [C <F>:<T>]
1237 Get local as cell. If the local variable given by %1 is defined, this
1238 instruction gets the value of the local variable, pushes it onto the stack
1239 as a cell, and then pushes $1 onto the stack.
1241 If the local variable is not defined, this instruction raises a warning,
1242 pushes null onto the stack, and then pushes $1 onto the stack.
1244 CGetL3 <local variable id> [<F2>:<T2> <F1>:<T1>] -> [C <F2>:<T1> <F1>:<T1>]
1246 Get local as cell. If the local variable given by %1 is defined, this
1247 instruction gets the value of the local variable, pushes it onto the stack
1248 as a cell, then pushes $2 onto the stack, and then pushes $1 onto the stack.
1250 If the local variable given by %1 is not defined, this instruction raises a
1251 warning, pushes null onto the stack, then pushes $2 onto the stack, and then
1252 pushes $1 onto the stack.
1256 Get local as cell. This instruction first computes x = (string)$1. Next, this
1257 instruction reads the local variable named x pushes its value onto the stack
1260 If there is no local variable defined named x, this instruction pushes null
1261 onto the stack and raises a warning.
1265 Get global as cell. This instruction first computes x = (string)$1. Next,
1266 this instruction reads the global variable named x pushes its value onto the
1269 If there is not a global variable defined named x, this instruction pushes
1270 null onto the stack and raises a warning.
1274 Get static property as cell. This instruction first checks if class $1 has a
1275 visible and accessible static property named (string)$2. If it doesn't, this
1276 instruction throws a fatal error. Otherwise, this instruction pushes the
1277 static property onto the stack as a cell.
1279 VGetL <local variable id> [] -> [V]
1281 Get local as ref. This instruction boxes the local variable given by %1 if
1282 necessary and pushes it onto the stack as a ref. If the given local variable
1283 is not defined, this instruction defines it, sets it to null, boxes it, and
1284 pushes a the value of the local variable onto the stack as a ref.
1288 Get local as ref. This instruction first computes x = (string)$1. Next, this
1289 instruction boxes the local variable named x (if the local is a cell) and
1290 pushes its value onto the stack as a ref. If there is no local variable
1291 defined named x, this instruction defines a local variable named x, sets it
1292 to null, boxes it, and pushes the value of the local variable onto the stack
1297 Get global as ref. This instruction first computes x = (string)$1. Next, this
1298 instruction boxes the global variable named x (if the local is a cell) and
1299 pushes its value onto the stack as a ref. If there is no global variable
1300 defined named x, this instruction defines a global variable named x, sets it
1301 to null, boxes it, and pushes the value of the global variable onto the stack
1306 Get static property as ref. This instruction first checks if class $1 has a
1307 visible and accessible static property named (string)$2. If it doesn't, this
1308 instruction throws a fatal error. Otherwise, this instruction boxes the
1309 static property and pushes it onto the stack as a ref.
1312 AGetL <local variable id> [] -> [A]
1314 Fetch class. This instruction first loads a value into x as shown by the
1322 Next this instruction checks if x is a string or an object. If x is not a
1323 string or object, this instruction throws a fatal error. Otherwise, this
1324 instruction executes y = (is_object(x) ? get_class(x) : (string)x) and checks
1325 if y matches the name of a defined class. If y does not match the name of a
1326 defined class, this instruction will invoke the autoload facility passing in
1327 the class name y, and then it will again check if y matches the name of a
1328 defined class. If y still does not match the name of a defined class this
1329 instruction throws a fatal error.
1331 Next, this instruction pushs a classref that refers to the class named y.
1334 6. Isset, Empty, and type querying instructions
1335 -----------------------------------------------
1337 IssetC [C] -> [C:Bool]
1339 Isset. If $1 is null this instruction pushes false onto the stack, otherwise
1342 IssetL <local variable id> [] -> [C:Bool]
1344 Isset local. This instruction reads the local variable given by %1. If the
1345 local variable is undefined or null, this instruction pushes false onto the
1346 stack, otherwise it pushes true.
1348 IssetN [C] -> [C:Bool]
1350 Isset local. This instruction reads the local variable named (string)$1. If
1351 the local variable is undefined or null, this instruction pushes false onto
1352 the stack, otherwise it pushes true.
1354 IssetG [C] -> [C:Bool]
1356 Isset global. This instruction reads the global variable named (string)$1. If
1357 the global variable is undefined or null, this instruction pushes false onto
1358 the stack, otherwise it pushes true.
1360 IssetS [C A] -> [C:Bool]
1362 Isset static property. This instruction first computes x = (string)$2. Next
1363 it checks if class $1 has an accessible static property named x. If it
1364 doesn't, this instruction pushes false.
1366 If class $1 does have an accessible property named x, this instruction reads
1367 the static property named x. If the static property is null, this instruction
1368 pushes false onto the stack, otherwise it pushes true.
1370 EmptyL <local variable id> [] -> [C:Bool]
1372 Empty local. This instruction reads the local variable named %1 into x. If
1373 the local variable is defined this instruction pushes !(x) onto the stack,
1374 otherwise it pushes true.
1376 EmptyN [C] -> [C:Bool]
1378 Empty local. This instruction reads the local variable named (string)$1 into
1379 x. If the local variable is defined this instruction pushes !(x) onto the
1380 stack, otherwise it pushes true.
1382 EmptyG [C] -> [C:Bool]
1384 Empty global. This instruction reads the global variable named (string)$1
1385 into x. If the global variable is defined this instruction pushes !(x) onto
1386 the stack, otherwise it pushes true.
1388 EmptyS [C A] -> [C:Bool]
1390 Empty static property. This instruction first checks if class $1 has an
1391 accessible static property named (string)$2. If it doesn't, this instruction
1392 pushes true, otherwise this instruction reads the static property into x and
1393 pushes !(x) onto the stack.
1395 IsNullC [C] -> [C:Bool]
1396 IsBoolC [C] -> [C:Bool]
1397 IsIntC [C] -> [C:Bool]
1398 IsDoubleC [C] -> [C:Bool]
1399 IsStringC [C] -> [C:Bool]
1400 IsArrayC [C] -> [C:Bool]
1401 IsObjectC [C] -> [C:Bool]
1403 Is type. This instruction first loads a type into t as given by the following
1407 -------------+------
1416 If $1 is of type t, this instruction pushes true onto the stack, otherwise it
1419 IsNullL <local variable id> [] -> [C:Bool]
1420 IsBoolL <local variable id> [] -> [C:Bool]
1421 IsIntL <local variable id> [] -> [C:Bool]
1422 IsDoubleL <local variable id> [] -> [C:Bool]
1423 IsStringL <local variable id> [] -> [C:Bool]
1424 IsArrayL <local variable id> [] -> [C:Bool]
1425 IsObjectL <local variable id> [] -> [C:Bool]
1427 Is type. This instruction first loads a type into t and a value into x as
1428 given by the following table:
1431 -------------+------+-------
1432 IsNullL | Null | true
1433 IsBoolL | Bool | false
1434 IsIntL | Int | false
1435 IsDoubleL | Dbl | false
1436 IsStringL | Str | false
1437 IsArrayL | Arr | false
1438 IsObjectL | Obj | false
1440 If the local variable given by %1 is defined, this pushes true onto the stack
1441 if the local variable is of type t, otherwise it pushes false.
1443 If the local variable given by %1 is not defined, this instruction raises a
1444 warning and pushes x onto the stack.
1447 7. Mutator instructions
1448 -----------------------
1450 SetL <local variable id> [C] -> [C]
1452 Set local. This instruction marks the local variable given by %1 as defined,
1453 stores the value $1 into the local variable, and then pushes $1 onto the
1458 Set local. This instruction marks the local variable named (string)$2 as
1459 defined, assigns the value $1 to the local variable, and then pushes $1 onto
1464 Set global. This instruction marks the global variable named (string)$2 as
1465 defined, assigns the value $1 to the global variable, and then pushes $1 onto
1470 Set static property. First this instruction checks if class $2 has an
1471 accessible static property named (string)$3. If it doesn't, this instruction
1472 throws a fatal error. Otherwise, this instruction assigns the value $1 to the
1473 static property, and then it pushes $1 onto the stack.
1475 SetOpL <local variable id> <op> [C] -> [C]
1477 Set op local. If the local variable given %1 is not defined, this instruction
1478 marks it as defined, sets it to null, and raises a warning.
1480 Next, this instruction reads the local variable into x, then executes y = x
1481 <op> $1, assigns y into local variable %1, and then pushes y onto the stack.
1482 The immediate value must be one of the following opcodes:
1483 Add, Sub, Mul, Div, Mod, Shl, Shr, Concat, BitAnd, BitOr, BitXor.
1485 SetOpN <op> [C C] -> [C]
1487 Set op local. This instruction first computes x = (string)$2. If the local
1488 variable named n is not defined, this instruction marks it as defined, sets
1489 it to null, and raises a warning.
1491 Next, this instruction reads the local variable named x into y, executes
1492 z = y <op> $1, assigns z into the local variable named x, and then pushes z
1493 onto the stack as a cell. The immediate value must be one of the following
1495 Add, Sub, Mul, Div, Mod, Shl, Shr, Concat, BitAnd, BitOr, BitXor.
1497 SetOpG <op> [C C] -> [C]
1499 Set op global. This instruction first computes x = (string)$2. If the global
1500 variable named n is not defined, this instruction marks it as defined, sets
1501 it to null, and raises a warning.
1503 Next, this instruction reads the global variable named x into y, executes
1504 z = y <op> $1, assigns z into the global variable named x, and then pushes z
1505 onto the stack as a cell. The immediate value must be one of the following
1507 Add, Sub, Mul, Div, Mod, Shl, Shr, Concat, BitAnd, BitOr, BitXor.
1509 SetOpS <op> [C A C] -> [C]
1511 Set op static property. This instruction first computes x = (string)$3. Next
1512 it checks if class $2 has an accessible static property named x. If it
1513 doesn't, this instruction throws a fatal error. Otherwise, this instruction
1514 reads the static property named x into y, executes z = y <op> $1, assigns z
1515 into the static property, and then pushes z onto the stack. The immediate
1516 value must be one of the following opcodes:
1517 Add, Sub, Mul, Div, Mod, Shl, Shr, Concat, BitAnd, BitOr, BitXor.
1519 IncDecL <local variable id> <op> [] -> [C]
1521 Increment/decrement local. If the local variable given by %1 is not defined,
1522 this instruction marks it as defined, sets it to null, and raises a warning.
1524 Where x is the local given by %1, this instruction then does the following:
1526 If op is PreInc, this instruction executes ++x and then pushes x onto the
1529 If op is PostInc, this instruction pushes x onto the stack and then it
1532 If op is PreDec, this instruction executes --x and then pushes x onto the
1535 If op is PostDec, this instruction pushes x onto the stack and then it
1538 IncDecN <op> [C] -> [C]
1539 IncDecG <op> [C] -> [C]
1541 Increment/decrement. This instruction first computes x = (string)$1. Next, if
1542 the local variable (IncDecN) or global variable (IncDecG) named x is not
1543 defined, this instruction first defines it, sets it to null, and raises a
1546 Where v is the local variable or global variable named x, this instruction
1547 performs the following:
1549 If op is PreInc, this instruction executes ++v and then pushes v onto the
1552 If op is PostInc, this instruction pushes v onto the stack and then it
1555 If op is PreDec, this instruction executes --v and then pushes v onto the
1558 If op is PostDec, this instruction pushes v onto the stack and then it
1561 IncDecS <op> [C A] -> [C]
1563 Increment/decrement static property. This instruction first computes
1564 x = (string)$2. Next it checks if class $1 has an accessible static property
1565 named x. If it doesn't, this instruction throws a fatal error.
1567 Where s is the static property named x, this instruction performs the
1570 If op is PreInc, this instruction increments the ++s and then pushes s onto
1573 If op is PostInc, this instruction pushes s onto the stack and then it
1576 If op is PreDec, this instruction executes --s and then pushes s onto the
1579 If op is PostDec, this instruction pushes s onto the stack and then it
1582 BindL <local variable id> [V] -> [V]
1584 Bind local. This instruction marks the local variable given by %1 as defined,
1585 binds the local variable to $1, and pushes $1 onto the stack.
1589 Bind local. This instruction marks the local variable named (string)$2 as
1590 defined, binds the local variable to $1, and pushes $1 onto the stack.
1594 Bind global. This instruction marks the global variable named (string)$2 as
1595 defined, binds the global variable to $1, and pushes $1 onto the stack.
1597 BindS [C A V] -> [V]
1599 Bind static property. This instruction first checks if class $2 has an
1600 accessible static property named (string)$3. If it doesn't, this instruction
1601 throws a fatal error. Otherwise, this instrution binds the static property
1602 to $1, and pushes $1 onto the stack.
1604 UnsetL <local variable id> [] -> []
1606 Unset local. Breaks any bindings the local variable given by %1 may have and
1607 marks the local variable as undefined.
1611 Unset local. This instruction breaks any bindings the local variable named
1612 (string)$1 may have and marks the local variable as undefined.
1616 Unset global. This instruction breaks any bindings the global variable named
1617 (string)$1 may have and marks the global variable as undefined.
1620 8. Call instructions
1621 --------------------
1623 FPushFunc <num params> [C] -> []
1624 FPushFuncD <num params> <litstr id> [] -> []
1626 FPI push function. First, these instructions load a value into x as given by
1627 the following table:
1634 If x is a string, this instruction attempts to lookup a function named x. If
1635 no function named x is defined, this instruction throws a fatal error.
1636 Otherwise this instruction pushes a new entry on the FPI stack, initializing
1637 it with the number of parameters being passed (given by %1) and a reference
1638 to the FPI structure for the function named x.
1640 If x is an object, this instruction checks if the object has an __invoke
1641 method. If the object does not have an __invoke method, this instruction
1642 throws a fatal error. Otherwise this instruction pushes a new entry on the
1643 FPI stack, intializing it with the number of parameters being passed (given
1644 by %1) and a reference to the FPI structure for the __invoke method from
1647 If x is not a string or object, this instruction throws a fatal error.
1649 FPushFuncU <num params> <litstr id> <litstr fallback> [] -> []
1651 FPI push function unqualified. Identical to FPushFuncD except first trys to
1652 lookup the function named %2 and if it isn't defined calls the function named
1655 FPushObjMethod <num params> [C C] -> []
1656 FPushObjMethodD <num params> <litstr id> [C] -> []
1658 FPI push object-based method. First, these instructions load values into x
1659 and y as given by the following table:
1662 -------------------+----+-----
1663 FPushObjMethod | $2 | $1
1664 FPushObjMethodD | $1 | %2
1666 If x is not an object or if y is not a string, this instruction throws a
1667 fatal error. Next, this instruction checks if object x has an accessible
1668 method named y. If it does, this instruction pushes a new entry on the FPI
1669 stack, initializing it with the number of parameters being passed (given by
1670 %1) and a reference to the FPI structure for the method named y from object x.
1672 If object x does not have an accessible method named y, this instruction
1673 checks if object x has a __call method. If a __call method is found, this
1674 instruction pushes a new entry on the FPI stack, initializing it with the
1675 number of parameters being passed (given by %1) and a reference to the FPI
1676 structure for the __call from object x, and stores the original name y in the
1679 If object x does not have an accessible method named y and it does not have a
1680 __call method, this instruction throws a fatal error.
1682 FPushClsMethod <num params> [C A] -> []
1683 FPushClsMethodF <num params> [C A] -> []
1684 FPushClsMethodD <num params> <litstr id> <litstr id> [] -> []
1686 FPI push class-based method. First, these instructions load values into x and
1687 y as given by the following table:
1690 -------------------+----+-----
1691 FPushClsMethod | $1 | $2
1692 FPushClsMethodF | $1 | $2
1693 FPushClsMethodD | %3 | %2
1695 When loading %3 into x, FPushClsMethodD will perform the work performed by
1696 the AGetC instruction to convert the name given by %3 into a classref.
1698 If y is not a string, this instruction throws a fatal error. Next, this
1699 instruction checks if class x has an accessible method named y. If class x
1700 has a method named y. If it does, this instruction pushes a new entry on the
1701 FPI stack, initializing it with the number of parameters being passed (given
1702 by %1) and a reference to the FPI structure for the method named y from class
1705 If class x does not have an accessible method named y, this instruction
1706 checks if the current function's $this is non-null, if the class of $this
1707 is the same or derived from class x, and if $this has a __call method. If no
1708 suitable __call method is found, this instruction will check if class x has a
1709 __callStatic method. If a suitable __call method or a __callStatic method is
1710 found, this instruction pushes a new entry on the FPI stack, initializing it
1711 with the number of parameters being passed (given by %1) and a reference to
1712 the FPI structure for the __call or __callStatic method that was found,
1713 and stores the original name y in the FPI stack entry.
1715 If class x does not have an accessible method named y, and if a suitable
1716 __call method or a __callStatic method could not be found, this instruction
1717 throws a fatal error.
1719 FPushCtor <num params> [A] -> [C]
1720 FPushCtorD <num params> <litstr id> [] -> [C]
1722 FPI push constructor. First, these instructions load a value into x as given
1723 by the following table:
1730 When loading %2 into x, FPushCtorD will perform the work performed by the
1731 AGetC instruction to convert the name given by %2 into a classref.
1733 This instruction pushes an uninitialized object onto the stack (to be
1734 initialized during FCall*) prior to entering the FPI region, then pushes a new
1735 entry on the FPI stack, initializing it with the number of parameters being
1736 passed (given by %1) and a reference to the FPI structure for the constructor
1739 DecodeCufIter <iterator id> [C] -> [C]
1740 This instruction looks up $1 as a callable, and writes enough information
1741 to iterator %1 for FPushDecoded to be able to push an actrec, as if it had
1742 been given the callable.
1743 If the function is successfully decoded, pushes true, otherwise, pushes
1744 false, and sets up iter to call a function that does nothing, and returns
1745 Null. No warning is raised.
1747 FPushCufIter <num params> <iterator id> [] -> []
1748 FPI push the result of a previous DecodeCufIter. No warning is raised.
1750 FPushCuf <num params> [C] -> []
1751 FPushCufF <num params> [C] -> []
1753 FPI push call user function. These instructions lookup $1 as a callable, and
1754 push a new entry onto the FPI stack. If $1 is not callable, they issue a
1755 warning, and push an entry representing a function which does nothing, takes
1756 no argument, and returns null.
1758 FPushCufSafe <num params> [C C] -> [C C]
1760 FPI push call user function. This instruction pops $1 and $2, then pushes
1761 $1 back onto the stack. It then looks up $2 as a callable, and pushes a
1762 new entry onto the FPI stack. If $2 is not callable, it pushes an entry
1763 representing a function which does nothing, takes no argument, and returns
1764 null, and in addition pushes boolean false onto the evaluation stack;
1765 otherwise it pushes true onto the evaluation stack.
1767 CufSafeArray [C C R] -> [C]
1769 Pops 3 elements from the stack, and pushes array($2, $1), preserving
1772 CufSafeReturn [C C R] -> [R]
1774 Pops 3 elements from the stack, and pushes $2 ? $1 : $3, preserving
1777 FPassC <param id> [C] -> [F]
1778 FPassCW <param id> [C] -> [F]
1779 FPassCE <param id> [C] -> [F]
1781 FPI pass parameter. This instruction pushes $1 onto the stack as a cell
1782 regardless of whether parameter %1 is pass by value or pass by reference.
1784 If parameter %1 is pass by reference, FPassCW and FPassCE check if the
1785 function associated with the current FPI (the callee) is an extension
1786 function that can accept a cell for parameter %1. If this condition is not
1787 met, FPassCW will raise a warning while FPassCE will throw a fatal error.
1789 FPassV <param id> [V] -> [F]
1791 FPI pass parameter. If parameter %1 is pass by value, this instruction will
1792 unbox $1 and push it onto the stack as a cell. If parameter %1 is pass by
1793 reference, this instruction will push $1 onto the stack as a ref.
1795 FPassR <param id> [R] -> [F]
1797 FPI pass parameter. If $1 is a cell at run time, this instruction will behave
1798 like FPassC. Otherwise, this instruction will behave like FPassV.
1800 FPassL <param id> <local variable id> [] -> [F]
1802 FPI pass local as parameter. This instruction behaves as CGetL if parameter
1803 %1 is pass by value, or it behaves like VGetL if parameter %1 is pass by
1806 FPassN <param id> [C] -> [F]
1808 FPI pass local as parameter. This instruction behaves as CGetN if parameter
1809 %1 is pass by value, or it behaves like VGetN if parameter %1 is pass by
1812 FPassG <param id> [C] -> [F]
1814 FPI pass global as parameter. This instruction behaves as CGetG if parameter
1815 %1 is pass by value, or it behaves like VGetG if parameter %1 is pass by
1818 FPassS <param id> [C A] -> [F]
1820 FPI pass parameter. This instruction behaves as CGetS if parameter %1 is pass
1821 by value, or it behaves like VGetS if parameter %1 is pass by reference.
1823 FCall <num params> [F..F] -> [R]
1825 FPI call. This instruction gets the bytecode address of the function
1826 associated with the current FPI (the callee), transfers the top %1 values
1827 from the stack to the callee as parameters, pops the current FPI off of the
1828 FPI stack, and then invokes the dispatcher to call the callee. When the
1829 callee returns, it will transfer the return value onto the caller's
1830 evaluation stack using the R flavor.
1832 FCallArray [F] -> [R]
1834 FPI call with array. This instruction gets the bytecode address of the
1835 function associated with the current FPI (the callee), transfers the
1836 elements of $1 (which must be an array) to the callee as parameters, pops
1837 the current FPI off of the FPI stack, and then invokes the dispatcher to
1838 call the callee. When the callee returns, it will transfer the return value
1839 onto the caller's evaluation stack using the R flavor.
1841 FCallBuiltin <total params> <passed params> <litstr id> [C|V..C|V] -> [R]
1843 Optimized builtin call without an ActRec. This instruction attempts to
1844 lookup a builtin function named %3. If no function named %3 is defined,
1845 this instruction throws a fatal error. Otherwise, this function gets
1846 address of the builtin function named %3, transfers the top %1 values
1847 from the stack to the callee as parameters, and then invokes the dispatcher
1848 to call the callee. %2 denotes the number of non-default parameters pushed
1849 onto stack by user level code. When the callee returns, it will transfer
1850 the return value onto the caller's evaluation stack using the R flavor.
1853 9. Member operations
1854 --------------------
1856 The following operations describe processes that are shared across the Member
1857 instructions. Operations are not considered instructions; they do not have
1858 opcodes associated with them.
1860 Operations can produce and consume intermediate values called "bases". A "base"
1861 is a structure that contains either a cell or a ref or a reference to a memory
1862 location that is occupied by a cell or a ref. Bases are never pushed onto the
1865 For operations that create a base, the operation descriptions specify whether
1866 the base created "contains" a value or "references" a location. In the former
1867 case, the base created contains a cell or a ref. In the latter case, the base
1868 created contains a reference to a memory location occupied by a cell or a ref.
1870 When a base that contains a cell is destroyed, if the cell points to data then
1871 the execution engine is responsible for honoring the data's refcount logic.
1872 Likewise when a base that contains a ref is destroyed, the execution engine is
1873 responsible for honoring the refcount logic of the cell container pointed to by
1874 the ref. When a base that contains a reference to a memory location occupied
1875 by a cell or a ref is destroyed, no refcounting is required.
1877 Some operations that take a base as input can modify that base as part of the
1878 work performed by the operation. Such operations are said to "set" the base to
1879 a new value. When a base that contains a cell or a reference to a memory
1880 location occupied by a cell is set to a new value, the new value overwrites the
1881 previous value contained in the cell (honoring the data refcount logic if the
1882 previous value was a refcounted type). When a base that contains a ref or a
1883 reference to a memory location occupied by a ref is set to the new value, the
1884 new value is written into the cell container referenced by the ref, overwriting
1885 the previous cell in that container (honoring the data refcount logic if the
1886 previous cell was a refcounted type). Note that for bases that contain a
1887 reference to a memory location, "setting" the base does not change which memory
1888 location the base references.
1890 Operations are specified as if they directly operate on the top of the
1891 evaluation stack in the name of consistency and clarity, but in fact their
1892 inputs and outputs may reside elsewhere. The symbol 'B' is used in the input
1893 descriptions and output descriptions of operations to indicate that a given
1894 operation consumes a base as input or produces a base as output.
1898 Get base from value. This operation outputs a base that contains the value
1903 Get base from return value. This operation outputs a base that contains the
1904 return value given by $1.
1906 BaseL <local variable id> [] -> [B]
1908 Get base from local. This operation outputs a base that references the local
1909 given by %1. If the local is not defined, this operation outputs a base that
1912 BaseLW <local variable id> [] -> [B]
1914 Get base from local. This operation outputs a base that references the local
1915 given by %1. If the local is not defined, this operation raises a warning and
1916 outputs a base that contains null.
1918 BaseLD <local variable id> [] -> [B]
1920 Get base from local. This operation outputs a base that references the local
1921 given by %1. If the local is not defined, this operation defines it and
1922 returns a base that references the local.
1924 BaseLWD <local variable id> [] -> [B]
1926 Get base from local. This operation outputs a base that references the local
1927 variable given by %1. If the local is not defined, this operation defines it,
1928 raises a warning, and returns a base that references the local.
1931 BaseNL <local variable id> [] -> [B]
1933 Get base from name. This operation outputs a base that references the local
1934 variable whose name is given by (string)%1 or (string)$1. If the local is not
1935 defined, this operation outputs a base that contains null.
1938 BaseNLW <local variable id> [] -> [B]
1940 Get base from name. This operation outputs a base that references the local
1941 variable whose name is given by (string)%1 or (string)$1. If the local is not
1942 defined, this operation raises a warning and outputs a base that contains
1946 BaseNLD <local variable id> [] -> [B]
1948 Get base from name. This operation outputs a base that references the local
1949 variable whose name is given by (string)%1 or (string)$1. If the local is not
1950 defined, this operation defines it and returns a base that references the
1954 BaseNLWD <local variable id> [] -> [B]
1956 Get base from name. This operation outputs a base that references the local
1957 variable whose name is given by (string)%1 or (string)$1. If the local is not
1958 defined, this operation defines it, raises a warning, and returns a base that
1959 references the local.
1962 BaseGL <local variable id> [] -> [B]
1964 Get base from global name. This operation outputs a base that references the
1965 global variable whose name is given by (string)%1 or (string)$1. If the
1966 global is not defined, this operation produces a base that contains null.
1969 BaseGLW <local variable id> [] -> [B]
1971 Get base from global name. This operation outputs a base that references the
1972 global variable whose name is given by (string)%1 or (string)$1. If the
1973 global is not defined, this operation raises a warning and outputs a base
1977 BaseGLD <local variable id> [] -> [B]
1979 Get base from global name. This operation outputs a base that references the
1980 global variable whose name is given by (string)%1 or (string)$1. If the
1981 global is not defined, this operation defines it and returns a base that
1982 references the global.
1985 BaseGLWD <local variable id> [] -> [B]
1987 Get base from global name. This operation outputs a base that references the
1988 global variable whose name is given by (string)%1 or (string)$1. If the
1989 global is not defined, this operation defines it, raises a warning, and
1990 returns a base that references the global.
1993 BaseSL <local variable id> [A] -> [B]
1995 Get base from static property. First, this operation loads a value into x as
1996 given by the following table:
2003 Next this operation computes y = (string)x. Then this instruction checks if
2004 class $1 has an accessible property named y. If it does, this operation
2005 outputs a base that references the static property. Otherwise, this operation
2006 throws a fatal error.
2010 Get base from $this. This operation assumes that the current frame contains a
2011 valid $this pointer and outputs a base containing the object in $this.
2014 ElemL <local variable id> [B] -> [B]
2016 Fetch element if it exists. First, these operations load a value into x and a
2017 base into y, as given by the following table:
2020 ----------+----+-----
2024 Then, if y is an array, this operation outputs a base that
2025 references the element at index x from array y. If there is no
2026 element at index x, this operation outputs a base that contains
2029 If y is an object that implements the ArrayAccess interface, this operation
2030 outputs a base that contains the result of y->offsetGet(x).
2032 If y is an object that does not implement the ArrayAccess interface,
2033 this operation throws a fatal error.
2035 If y is a string, this operation computes z = (int)x. If z >= 0 and
2036 z < strlen(z), this operation builds a new string consisting of the
2037 character at offset z from y and outputs a base that contains the new
2038 string. Otherwise, this operation outputs a base that contains the
2041 If y is not a string, array, or object, this operation will output a
2045 ElemLW <local variable id> [B] -> [B]
2047 Fetch element; warn if it doesn't exist.
2049 First, these operations load a value into x and a base into y, as
2050 given by the following table:
2053 ----------+----+-----
2057 If y is an array, this operation outputs a base that references the
2058 element at index x from array y. If there is no element at index x,
2059 this operation outputs a base that contains null and raises a
2062 If y is an object that implements the ArrayAccess interface, this
2063 operation outputs a base that contains the result of
2066 If y is an object that does not implement the ArrayAccess interface,
2067 this operation throws a fatal error.
2069 If y is a string, this operation continues to compute z = (int)x.
2070 If z >= 0 and z < strlen(z), this operation builds a new
2071 string consisting of the character at offset z from y and outputs a
2072 base that contains the new string. Otherwise, this operation raises
2073 a warning and outputs a base that contains the empty string.
2075 If y is not a string, array, or object, this operation will output
2079 ElemLD <local variable id> [B] -> [B]
2081 Fetch element; define it if it doesn't exist.
2083 First, these operations load a value into x and a base into y, as
2084 given by the following table:
2087 ----------+----+-----
2091 If y is an array, this operation outputs a base that references the element
2092 at index x. If there is no element at index x, this operation creates an
2093 element at index x, and outputs a base that references the element.
2095 If y is an object that implements the ArrayAccess interface, this operation
2096 outputs a base that contains the result of y->offsetGet(x).
2098 If y is non-empty string or an object that does not implement the
2099 ArrayAccess interface, this operation throws a fatal error.
2101 If y is null, the empty string, or false, this operation will set y to a
2102 new empty array, create an element at index x, and output a base that
2103 references the element.
2105 If y is true, integer, double, this operation raises a warning and outputs a
2106 base that contains null.
2108 ElemCWD [C B] -> [B]
2109 ElemLWD <local variable id> [B] -> [B]
2111 Fetch element; warn and define it if it doesn't exist.
2113 First, these operations load a value into x and a base into y, as
2114 given by the following table:
2117 ----------+----+-----
2121 If y is an array, this operation outputs a base that references the
2122 element at index x. If there is no element at index x, this
2123 operation creates an element at index x, raises a warning, and
2124 outputs a base that references the element.
2126 If y is an object that implements the ArrayAccess interface, this
2127 operation outputs a base that contains the result of
2130 If y is non-empty string or an object that does not implement the
2131 ArrayAccess interface, this operation throws a fatal error.
2133 If y is null, the empty string, or false, this operation will set y
2134 to a new empty array, create an element at index x, and output a
2135 base that references the element.
2137 If y is true, integer, or double, this operation raises a warning
2138 and outputs a base that contains null.
2141 ElemLU <local variable id> [B] -> [B]
2143 Fetch element for unset.
2145 First, these operations load a value into x and a base into y, as
2146 given by the following table:
2149 ----------+----+-----
2153 If y is an array, this operation outputs a base that references the element
2154 at index x from array y. If there is no element at index x, this operation
2155 outputs a base that contains null.
2157 If y is an object that implements the ArrayAccess interface, this operation
2158 outputs a base that contains the result of y->offsetGet(x).
2160 If y is an object that does not implement the ArrayAccess interface, this
2161 operation throws a fatal error.
2163 If y is a string, this operation throws a fatal error.
2165 If y is not a string, array, or object, this operation will output a
2170 Fetch new element. If $1 is an array, this operation creates a new element
2171 with the next available numeric key in array $1 and outputs a base that
2172 references the new element.
2174 If $1 is an object that implements the ArrayAccess interface, this operation
2175 outputs a base that contains the result of $1->offsetGet(null).
2177 If $1 is a non-empty string or an object that does not implement the
2178 ArrayAccess interface, this operation throws a fatal error.
2180 If $1 is null, false, or the empty string, this operation sets $1 to a new
2181 empty array, creates a new element with the next available numeric key in
2182 array $1, and then outputs a base that references the new element.
2184 If $1 is true, integer, or double, this operation raises a warning and
2185 outputs a base that contains null.
2188 PropL <local variable id> [B] -> [B]
2190 Fetch property if it exists.
2192 First, these operations load a value into x and a base into y, as
2193 given by the following table:
2196 ----------+----+-----
2200 Next, performs one of the following actions:
2205 y has eligible __get method
2206 y->x has been unset previously
2207 ------+---------------------------------------------------------------------
2210 10X1X | push ref(y->__get(x))
2211 1100X | throw fatal error
2212 1101X | push ref(y->__get(x))
2213 111X0 | push ref(y->x)
2215 11111 | push ref(y->__get(x))
2218 PropLW <local variable id> [B] -> [B]
2220 Fetch property; warn if it doesn't exist.
2222 First, these operations load a value into x and a base into y, as
2223 given by the following table:
2226 ----------+----+-----
2230 Next, performs one of the following actions:
2235 y has eligible __get method
2236 y->x has been unset previously
2237 -----+----------------------------------------------------------------------
2238 0XXXX | raise warning; push null
2239 10X0X | raise warning; push null
2240 10X1X | push ref(y->__get(x))
2241 1100X | throw fatal error
2242 1101X | push ref(y->__get(x))
2243 111X0 | push ref(y->x)
2244 11101 | raise warning; push null
2245 11111 | push ref(y->__get(x))
2248 PropLD <local variable id> [B] -> [B]
2250 Fetch property; define it if it doesn't exist.
2252 First, these operations load a value into x and a base into y, as
2253 given by the following table:
2256 ----------+----+-----
2260 Next, performs one of the following actions:
2266 y has eligible __get method
2267 y->x has been unset previously
2268 ------+---------------------------------------------------------------------
2270 01XXXX | y = new stdclass; create property y->x; push ref(y->x)
2271 1X0X0X | create property y->x; push ref(y->x)
2272 1X0X1X | push ref(y->__get(x))
2273 1X100X | throw fatal error
2274 1X101X | push ref(y->__get(x))
2275 1X11X0 | push ref(y->x)
2276 1X1101 | re-create property y->x, push ref(y->x)
2277 1X1111 | push ref(y->__get(x))
2279 PropCWD [C B] -> [B]
2280 PropLWD <local variable id> [B] -> [B]
2282 Fetch property; warn and define it if it doesn't exist.
2284 First, these operations load a value into x and a base into y, as
2285 given by the following table:
2288 ----------+----+-----
2292 Next, performs one of the following actions:
2298 y has eligible __get method
2299 y->x has been unset previously
2300 ------+---------------------------------------------------------------------
2301 00XXXX | raise warning; push null
2302 01XXXX | raise warning; y = new stdclass; create property y->x;
2304 1X0X0X | raise warning; create property y->x; push ref(y->x)
2305 1X0X1X | push ref(y->__get(x))
2306 1X100X | throw fatal error
2307 1X101X | push ref(y->__get(x))
2308 1X11X0 | push ref(y->x)
2309 1X1101 | re-create property y->x, push ref(y->x)
2310 1X1111 | push ref(y->__get(x))
2313 PropLU <local variabld id> [B] -> [B]
2315 Fetch property for unset.
2317 First, these operations load a value into x and a base into y, as
2318 given by the following table:
2321 ----------+----+-----
2325 Next, performs one of the following actions:
2330 y has eligible __get method
2331 y->x has been unset previously
2332 -----+----------------------------------------------------------------------
2334 10XXX | create property y->x; push ref(y->x)
2335 110XX | throw fatal error
2336 111X0 | push ref(y->x)
2337 111X1 | re-create property y->x, push ref(y->x)
2339 CGetElemC [C B] -> [C]
2340 CGetElemL <local variable id> [B] -> [C]
2342 Get element as cell.
2344 These instructions first load a value into x and a base into y, as
2345 given by the following table:
2348 ------------+----+-----
2352 If y is an array, this operation retrieves the element at index x from
2353 array y and pushes it onto the stack as a cell. If there is no element at
2354 index x, this operation raises a warning and pushes null onto the stack.
2356 If y is an object that implements the ArrayAccess interface, this operation
2357 pushes x->offsetGet($2) onto the stack.
2359 If y is an object that does not implement the ArrayAccess interface, this
2360 operation throws a fatal error.
2362 If y is a string, this operation continues to compute z = (int)x. If z >= 0
2363 and z < strlen(z), this operation builds a new string consisting of the character
2364 at offset z from y and pushes it onto the stack. Otherwise, this operation
2365 raises a warning and pushes the empty string onto the stack.
2367 If y is not a string, array, or object, this operation will push null onto
2370 VGetElemC [C B] -> [V]
2371 VGetElemL <local variable id> [B] -> [V]
2375 These instructions first load a value into x and a base into y, as
2376 given by the following table:
2379 ------------+----+-----
2383 If y is an array, this operation retrieves the element at index x from
2384 array y and pushes it onto the stack as a ref. If there is no element at
2385 index x, this operation creates a new element at index x, and pushes it
2386 onto the stack as a ref.
2388 If y is an object that implements the ArrayAccess interface, this operation
2389 pushes y->offsetGet(x) onto the stack as a ref.
2391 If y is a non-empty string or an object that does not implement the
2392 ArrayAccess interface, this operation throws a fatal error.
2394 If y is null, false, or the empty string, this operation sets y to a new
2395 empty array. Then this operation retrieves the element at index x from array
2396 y and pushes it onto the stack as a ref. If there is no element at index x,
2397 this operation creates a new element at index x, and pushes it onto the
2400 If y is true, integer, or double, this operation raises a warning and
2401 pushes null onto the stack.
2403 IssetElemC [C B] -> [C:Bool]
2404 IssetElemL <local variable id> [B] -> [C:Bool]
2408 These instructions first load a value into x and a base into y, as
2409 given by the following table:
2412 ------------+----+-----
2413 IssetElemC | $2 | $1
2414 IssetElemL | %1 | $1
2416 If y is an array, this operation pushes !is_null(y[x]) onto the stack.
2418 If y is an object that implements the ArrayAccess interface, this operation
2419 pushes y->offsetExists(x) onto the stack.
2421 If y is an object that does not implement the ArrayAccess interface, this
2422 operation throws a fatal error.
2424 If y is a string, this operation computes x = (int)x and then it pushes
2425 (x >= 0 && x < strlen(y)) onto the stack.
2427 If y is a not a string, array, or object, this operation pushes false onto
2430 EmptyElemC [C B] -> [C]
2431 EmptyElemL <local variable id> [B] -> [C]
2435 These instructions first load a value into x and a base into y, as
2436 given by the following table:
2439 ------------+----+-----
2440 EmptyElemC | $2 | $1
2441 EmptyElemL | %1 | $1
2443 If y is an array, this operation pushes !(y[x]) onto the stack.
2445 If y is an object that implements the ArrayAccess interface, this operation
2446 first calls y->offsetExists(x); if that returns false this operation pushes
2447 true onto the stack, otherwise it pushes !(y->offsetGet(x)) onto the stack.
2449 If y is an object that does not implement the ArrayAccess interface, this
2450 operation throws a fatal error.
2452 If y is a string, this operation computes z = (int)x, then pushes true if
2453 (z < 0 || z >= strlen(y)), !(y[z]) otherwise.
2455 If y is, not an array, object, or string, this operation pushes true onto
2458 SetElemC [C C B] -> [C]
2460 Set element. If $1 is an array, this operation executes $1[$3] = $2 and then
2461 pushes $2 onto the stack.
2463 If $1 is an object that implements the ArrayAccess interface, this operation
2464 executes $1->offsetSet($3, $2) and then pushes $2 onto the stack.
2466 If $1 is an object that does not implement the ArrayAccess interface, this
2467 operation throws a fatal error.
2469 If $1 is null, the empty string, or false, this operation sets $1 to a new
2470 empty array, executes $1[$3] = $2, and then pushes $2 onto the stack.
2472 If $1 is a non-empty string, this operation first computes x = (int)$3. If x
2473 is negative, this operation raises a warning and does nothing else. If x is
2474 nonnegative, this operation appends spaces to the end of $1 as needed to
2475 ensure that x is in bounds, then it computes y = substr((string)$2,0,1), and
2476 then it sets the character at index x in $1 equal to y (if y is not empty) or
2477 it sets the character at index x in $1 to "\0" (if y is empty). Then this
2478 operation pushes y on to the stack.
2480 If $1 is true, integer, or double, this operation raises a warning and pushes
2481 null onto the stack as a cell.
2483 SetElemL <local variable id> [C B] -> [C]
2485 Set element. If $1 is an array, this operation executes $1[%1] = $2 and then
2486 pushes $2 onto the stack.
2488 If $1 is an object that implements the ArrayAccess interface, this operation
2489 executes $1->offsetSet(%1, $2) and then pushes $2 onto the stack.
2491 If $1 is an object that does not implement the ArrayAccess interface, this
2492 operation throws a fatal error.
2494 If $1 is null, the empty string, or false, this operation sets $1 to a new
2495 empty array, executes $1[%1] = $2, and then pushes $2 onto the stack.
2497 If $1 is a non-empty string, this operation first computes x = (int)%1. If x
2498 is negative, this operation raises a warning and does nothing else. If x is
2499 nonnegative, this operation appends spaces to the end of $1 as needed to
2500 ensure that x is in bounds, then it computes y = substr((string)$2,0,1), and
2501 then it sets the character at index x in $1 equal to y (if y is not empty) or
2502 it sets the character at index x in $1 to "\0" (if y is empty). Then this
2503 operation pushes y on to the stack.
2505 If $1 is true, integer, or double, this operation raises a warning and pushes
2506 null onto the stack as a cell.
2508 SetOpElemC <op> [C C B] -> [C]
2510 Set element op. If $1 is an array, this operation first checks $1 contains
2511 an element at offset $2. If it does not, this operation creates an element
2512 at offset $2, sets it to null, and raises a warning. Next, this operation
2513 executes x = $1[$3], y = x <op> $2, and $1[$3] = y, and then it pushes y onto
2514 the stack as a cell.
2516 If $1 is null, false, or the empty string, this operation first sets $1 to
2517 a new empty array. Then it follows the rules described in the case above.
2519 If $1 is an object that implements the ArrayAccess interface, this
2520 operation executes x = $1->offsetGet($3), y = x <op> $2, and
2521 $1->offsetSet($3, y), and then it pushes y onto the stack as a cell.
2523 If $1 is a non-empty string or an object that does not implement the
2524 ArrayAccess interface, this operation throws a fatal error.
2526 If $1 is true, integer, or double, this operation raises a warning and
2527 pushes null onto the stack.
2529 SetOpElemL <op> <local variable id> [C B] -> [C]
2531 Set element op. If $1 is an array, this operation first checks $1 contains
2532 an element at offset $2. If it does not, this operation creates an element
2533 at offset $2, sets it to null, and raises a warning. Next, this operation
2534 executes x = $1[%1], y = x <op> $2, and $1[%1] = y, and then it pushes y onto
2535 the stack as a cell.
2537 If $1 is null, false, or the empty string, this operation first sets $1 to
2538 a new empty array. Then it follows the rules described in the case above.
2540 If $1 is an object that implements the ArrayAccess interface, this
2541 operation executes x = $1->offsetGet(%1), y = x <op> $2, and
2542 $1->offsetSet(%1, y), and then it pushes y onto the stack as a cell.
2544 If $1 is a non-empty string or an object that does not implement the
2545 ArrayAccess interface, this operation throws a fatal error.
2547 If $1 is true, integer, or double, this operation raises a warning and
2548 pushes null onto the stack.
2550 IncDecElemC <op> [C B] -> [C]
2552 Increment/decrement element. If $1 is an array, this operation checks if $1
2553 contains an element at offset $2. If it does not, this operation creates an
2554 element at offset $2, sets it to null, and raises a warning. Next, this
2555 operation executes x = $1[$2], y = x, and either ++y (if op is PreInc or
2556 PostInc) or --y (if op is PreDec or PostDec). Then it assigns y to $1[$2]
2557 and pushes either y (if op is PreInc or PreDec) or x (if op is PostInc or
2558 PostDec) onto the stack.
2560 If $1 is null, false, or the empty string, this operation first sets $1 to
2561 an empty array. Then it follows the rules described in the case above.
2563 If $1 is a non-empty string or an object that does not implement the
2564 ArrayAccess interface, this operation throws a fatal error.
2566 If $1 is an object that implements ArrayAccess, this operation executes
2567 x = $1->offsetGet($2), y = x, and either ++y (if op is PreInc or PostInc) or
2568 --y (if op is PreDec or PostDec). Then it pushes either y (if op is PreInc or
2569 PreDec) or x (if op is PostInc or PostDec) onto the stack.
2571 If $1 is true, integer, or double, this operation raises a warning and
2572 pushes null onto the stack.
2574 IncDecElemL <op> <local variable id> [B] -> [C]
2576 Increment/decrement element. If $1 is an array, this operation checks if $1
2577 contains an element at offset %1. If it does not, this operation creates an
2578 element at offset %1, sets it to null, and raises a warning. Next, this
2579 operation executes x = $1[%1], y = x, and either ++y (if op is PreInc or
2580 PostInc) or --y (if op is PreDec or PostDec). Then it assigns y to $1[%1]
2581 and pushes either y (if op is PreInc or PreDec) or x (if op is PostInc or
2582 PostDec) onto the stack.
2584 If $1 is null, false, or the empty string, this operation first sets $1 to
2585 an empty array. Then it follows the rules described in the case above.
2587 If $1 is a non-empty string or an object that does not implement the
2588 ArrayAccess interface, this operation throws a fatal error.
2590 If $1 is an object that implements ArrayAccess, this operation executes
2591 x = $1->offsetGet(%1), y = x, and either ++y (if op is PreInc or PostInc) or
2592 --y (if op is PreDec or PostDec). Then it pushes either y (if op is PreInc or
2593 PreDec) or x (if op is PostInc or PostDec) onto the stack.
2595 If $1 is true, integer, or double, this operation raises a warning and
2596 pushes null onto the stack.
2598 BindElemC [C V B] -> [V]
2599 BindElemL <local variable id> [V B] -> [V]
2603 This instruction first loads a value into x, from $3 or the local
2606 If $1 is an array, this operation executes $1[x] =& $2 and pushes $2
2607 onto the stack as a ref.
2609 If $1 is an object, this operation throws a fatal error.
2611 If $1 is null, false, or the empty string, this operation sets $1 to a new
2612 empty array, executes $1[x] =& $2, and pushes $2 onto the stack as a ref.
2614 If $1 is a non-empty string, this operation throws a fatal error.
2616 If $1 is true, integer, or double, this operation raises a warning.
2618 UnsetElemC [C B] -> []
2619 UnsetElemL <local variable id> [B] -> []
2623 These instructions first load a value into x and a base into y, as
2624 given by the following table:
2627 ------------+----+-----
2628 UnsetElemL | %1 | $1
2629 UnsetElemC | $2 | $1
2631 If y is an array, this operation removes the element at index x
2634 If y is an object that implements ArrayAccess interface, this operation
2635 executes y->offsetUnset(x).
2637 If y is an object that does not implement the ArrayAccess interface, this
2638 operation throws a fatal error.
2640 If y is a string, this operation throws a fatal error.
2642 If y is not a string, array, or object, this operation does nothing.
2644 VGetNewElem [B] -> [V]
2646 Get new element as ref.
2648 If $1 is an array, this operation creates a new element with the next
2649 available numeric key in array $1 and pushes it onto the stack as a ref.
2651 If $1 is an object that implements the ArrayAccess interface, this operation
2652 pushes $1->offsetGet($2) onto the stack as a ref.
2654 If $1 is a non-empty string or an object that does not implement the
2655 ArrayAccess interface, this operation throws a fatal error.
2657 If $1 is null, false, or the empty string, this operation first sets $1 to a
2658 new empty array. Then it creates a new element with the next available
2659 numeric key in array $1 and pushes it onto the stack as a ref.
2661 If $1 is true, integer, or double, this operation raises a warning and
2662 pushes null onto the stack.
2664 SetNewElem [C B] -> [C]
2666 Set new element. If $1 is an array, this operation executes $1[] = $2 and
2667 then pushes $2 onto the stack.
2669 If $1 is null, false, or the empty string, this operation sets $1 to a new
2670 empty array, and then it executes $1[] = $2 and pushes $2 onto the stack.
2672 If $1 is a non-empty string or an object that does not implement the
2673 ArrayAccess interface, this operation throws a fatal error.
2675 If $1 is an object that implements the ArrayAccess interface, this operation
2676 executes $1->offsetSet(null, $2) and then pushes $2 onto the stack.
2678 If $1 is true, integer, or double, this operation raises a warning and
2679 pushes null onto the stack.
2681 SetOpNewElem <op> [C B] -> [C]
2683 Set op new element. If $1 is an array, this operation first determines the
2684 next available integer offset k in array $1. Next, this operation executes
2685 $1[k] = null, x = $1[k], and y = x <op> $2. Then it assigns y to $1[k] and
2686 pushes y onto the stack.
2688 If $1 is null, false, or the empty string, this operation first sets $1 to
2689 an empty array. Then it follows the rules described in the case above.
2691 If $1 is a non-empty string or an object that does not implement the
2692 ArrayAccess interface, this operation throws a fatal error.
2694 If $1 is an object that implements ArrayAccess, this operation executes
2695 x = $1->offsetGet(null), y = x <op> $2, and $1->offsetSet(null, y). Then it
2696 pushes y onto the stack.
2698 If $1 is true, integer, or double, this operation raises a warning and
2699 pushes null onto the stack.
2701 IncDecNewElem <op> [B] -> [C]
2703 Increment/decrement new element. If $1 is an array, this operation first
2704 determines the next available integer offset k in array $1. Next, this
2705 operation executes $1[k] = null, x = $1[k], y = x, and either ++y (if op is
2706 PreInc or PostInc) or --y (if op is PreDec or PostDec). Then it assigns y to
2707 $1[k] and pushes either y (if op is PreInc or PreDec) or x (if op is PostInc
2708 or PostDec) onto the stack.
2710 If $1 is null, false, or the empty string, this operation first sets $1 to
2711 an empty array. Then it follows the rules described in the case above.
2713 If $1 is a non-empty string or an object that does not implement the
2714 ArrayAccess interface, this operation throws a fatal error.
2716 If $1 is an object that implements ArrayAccess, this operation executes x =
2717 $1->offsetGet(null), y = x, and either ++y (if op is PreInc or PostInc) or
2718 --y (if op is PreDec or PostDec). Then it pushes either y (if op is PreInc or
2719 PreDec) or x (if op is PostInc or PostDec) onto the stack.
2721 If $1 is true, integer, or double, this operation raises a warning and
2722 pushes null onto the stack.
2724 BindNewElem [V B] -> [V]
2726 Bind new element. If $1 is an array, this operation executes $1[] =& $2 and
2727 then it pushes $2 onto the stack.
2729 If $1 is null, false, or empty string, this operation sets $1 to a new empty
2730 array, executes $1[] =& $2, and pushes $2 onto the stack.
2732 If $1 is a non-empty string or an object, this operation throws a fatal
2735 If $1 is true, integer, or double, this operation raises a warning and
2736 pushes null onto the stack.
2738 CGetPropC [C B] -> [C]
2739 CGetPropL <local variable id> [B] -> [C]
2741 Get property as cell.
2743 These instructions first load a value into x and a base into y, as
2744 given by the following table:
2747 ------------+----+-----
2751 If y is an object that does not have an eligible __get method, this
2752 operation first checks if y has a visible property named x. If it
2753 does not, this operation raises a warning and pushes
2754 null. Otherwise, this operation continues to check if the property
2755 named x is accessible. If the property named x is accessible this
2756 operation pushes it onto the stack as a cell, otherwise this
2757 operation throws a fatal error.
2759 If y is an object that has an eligible __get method, this operation
2760 checks if y has a visible and accessible property named x. If it
2761 does, this operation pushes the property onto the stack. Otherwise,
2762 this operation pushes y->__get(x) onto the stack.
2764 If y is not an object, this operation will raise a warning and push
2765 null onto the stack.
2767 VGetPropC [C B] -> [V]
2768 VGetPropL <local variable id> [B] -> [V]
2770 Get property as ref.
2772 These instructions first load a value into x and a base into y, as
2773 given by the following table:
2776 ------------+----+-----
2780 If y is an object that does not have an eligible __get method, this
2781 operation first checks if y has a visible property named x. If it
2782 does not, this operation will create a new property named x and push
2783 it onto the stack as a ref. Otherwise this operation continues to
2784 check if the property named x is accessible. If it the property
2785 named x is accessible this operation pushes it onto the stack as a
2786 ref, otherwise this operation throws a fatal error.
2788 If y is an object has an eligible __get method, this operation
2789 checks if y has a visible and accessible property named x. If it
2790 does, this operation pushes the property onto the stack. Otherwise,
2791 this operation pushes y->__get(x) onto the stack.
2793 If y is null, false, or the empty string, this operation will set y
2794 to a new object of type stdclass, create a new property named x, and
2795 pushes it onto the stack.
2797 If y is true, integer, double, a non-empty string, or an array, this
2798 operation raises a warning and pushes null.
2800 IssetPropC [C B] -> [C:Bool]
2801 IssetPropL <local variable id> [B] -> [C:Bool]
2805 These instructions first load a value into x and a base into y, as
2806 given by the following table:
2809 -------------+----+-----
2810 IssetPropC | $2 | $1
2811 IssetPropL | %1 | $1
2813 If y is an object that does not have an eligible __isset method,
2814 this operation checks if y has a visible accessible property named
2815 x. If it does, this operation pushes !is_null(y->x) onto the
2816 stack. Otherwise this operation pushes false onto the stack.
2818 If y is an object that has an eligible __isset method, this operation checks
2819 if y has a visible and accessible property named x. If it does, this
2820 operation pushes !is_null(y->x) onto the stack. Otherwise this operation
2821 pushes y->__isset(x) onto the stack.
2823 If y is an array, this operation pushes !is_null(y[x]) onto the stack.
2825 If y is not an object or array, this operation pushes false.
2827 EmptyPropC [C B] -> [C:Bool]
2828 EmptyPropL <local variable id> [B] -> [C:Bool]
2832 These instructions first load a value into x and a base into y, as
2833 given by the following table:
2836 -------------+----+-----
2837 EmptyPropC | $2 | $1
2838 EmptyPropL | %1 | $1
2840 If y is an object that does not have an eligible __isset method, this
2841 operation first checks if y has a visible and accessible property named x.
2842 If it does, this operation pushes !(y->x) onto the stack. Otherwise this
2843 operation pushes true onto the stack.
2845 If y is an object that has an eligible __isset method but it does not have
2846 an eligible __get method, this operation checks if y has a visible and
2847 accessible property named x. If it does, this operation pushes !(y->x) onto
2848 the stack. Otherwise this operation pushes !(y->__isset(x)) onto the stack.
2850 If y is an object that has an eligible __isset method and an eligible __get
2851 method, this operation checks if y has a visible and accessible property
2852 named x. If it does, this operation pushes !(y->x) onto the stack. Otherwise
2853 this operation continues to execute x = y->__isset(x). If x is false this
2854 operation pushes true onto the stack, otherwise this operation pushes
2855 !(y->__get(x)) onto the stack.
2857 If y is an array, this operation pushes !(y[x]) onto the stack.
2859 If y is not an object or array, this operation pushes true.
2861 SetPropC [C C B] -> [C]
2862 SetPropL <local variable id> [C B] -> [C]
2864 Set property. Perform one of the following actions:
2866 First, these operations load values into k and x, and a base into y,
2867 as given by the following table:
2870 ----------+----+----+----
2871 SetPropC | $3 | $2 | $1
2872 SetPropL | %1 | $2 | $1
2874 Next, performs one of the following actions:
2880 y has eligible __set method
2881 y->k has been unset previously
2882 ------+---------------------------------------------------------------------
2883 00XXXX | raise warning; push null
2884 01XXXX | y = new stdclass; y->k = x; push x
2885 1X0X0X | create property y->k; y->k = x; push x
2886 1X0X1X | y->__set(k, x); push x
2887 1X100X | throw fatal error
2888 1X101X | y->__set(k, x); push x
2889 1X11X0 | y->k = x; push x
2890 1X1101 | re-create property y->k; y->k = x; push x
2891 1X1111 | y->__set(k, x); push x
2893 SetOpPropC <op> [C C B] -> [C]
2895 Set op property. Perform one of the following actions:
2900 $1->$3 is accessible
2901 $1 has eligible __get method
2902 $1 has eligible __set method
2903 $1->$3 has been unset previously
2904 -------+--------------------------------------------------------------------
2905 00XXXXX | raise warning; push null
2906 01XXXXX | $1 = new stdclass; y = null <op> $2; $1->$3 = y; push y
2907 100X0XX | y = null <op> $2; $1->$3 = y; push y
2908 100X10X | x = $1->__get($3); y = x <op> $2; $1->$3 = y; push y
2909 100X11X | x = $1->__get($3); y = x <op> $2; $1->__set($3, y), push y
2910 10100XX | throw fatal error
2911 101010X | throw fatal error
2912 101011X | x = $1->__get($3); y = x <op> $2; $1->__set($3, y), push y
2913 1011XX0 | x = $1->$3; y = x <op> $2; $1->$3 = y; push y
2914 10110X1 | y = null <op> $2; re-create $1->$3; $1->$3 = y; push y
2915 1011101 | x = $1->__get($3); y = x <op> $2; re-create $1->$3; $1->$3 = y;
2917 1011111 | x = $1->__get($3); y = x <op> $2; $1->__set($3, y); push y
2919 SetOpPropL <op> <local variable id> [C B] -> [C]
2921 Set op property. Perform one of the following actions, where k is
2922 the value of the local given by %2.
2928 $1 has eligible __get method
2929 $1 has eligible __set method
2930 $1->k has been unset previously
2931 -------+--------------------------------------------------------------------
2932 00XXXXX | raise warning; push null
2933 01XXXXX | $1 = new stdclass; y = null <op> $2; $1->k = y; push y
2934 100X0XX | y = null <op> $2; $1->k = y; push y
2935 100X10X | x = $1->__get(k); y = x <op> $2; $1->k = y; push y
2936 100X11X | x = $1->__get(k); y = x <op> $2; $1->__set(k, y), push y
2937 10100XX | throw fatal error
2938 101010X | throw fatal error
2939 101011X | x = $1->__get(k); y = x <op> $2; $1->__set(k, y), push y
2940 1011XX0 | x = $1->k; y = x <op> $2; $1->k = y; push y
2941 10110X1 | y = null <op> $2; re-create $1->k; $1->k = y; push y
2942 1011101 | x = $1->__get(k); y = x <op> $2; re-create $1->k; $1->k = y;
2944 1011111 | x = $1->__get(k); y = x <op> $2; $1->__set(k, y); push y
2946 IncDecPropC <op> [C B] -> [C]
2948 Increment/decrement property. Perform one of the following actions:
2953 $1->$2 is accessible
2954 $1 has eligible __get method
2955 $1 has eligible __set method
2956 $1->$2 has been unset previously
2957 -------+--------------------------------------------------------------------
2958 00XXXXX | raise warning; push null
2959 01XXXXX | $1 = new stdclass; x = null; y = x; <op>y; $1->$2 = y;
2960 | push y (Pre*) or x (Post*)
2961 100X0XX | x = null; y = x; <op>y; $1->$2 = y; push y (Pre*) or x (Post*)
2962 100X10X | x = $1->__get($2); y = x; <op>y; $1->$2 = y;
2963 | push y (Pre*) or x (Post*)
2964 100X11X | x = $1->__get($2); y = x, <op>y; $1->__set($2, y);
2965 | push y (Pre*) or x (Post*)
2966 10100XX | throw fatal error
2967 101010X | throw fatal error
2968 101011X | x = $1->__get($2); y = x, <op>y; $1->__set($2, y);
2969 | push y (Pre*) or x (Post*)
2970 1011XX0 | x = $1->$2; y = x; <op>y; $1->$2 = y; push y (Pre*) or x (Post*)
2971 10110X1 | x = null; y = x; <op>y; re-create $1->$2; $1->$2 = y;
2972 | push y (Pre*) or x (Post*)
2973 1011101 | x = $1->__get($2); y = x; <op>y; re-create $1->$2; $1->$2 = y;
2974 | push y (Pre*) or x (Post*)
2975 1011111 | x = $1->__get($2); y = x; <op>y; $1->__set($2, y);
2976 | push y (Pre*) or x (Post*)
2978 IncDecPropL <op> <local variable id> [B] -> [C]
2980 Increment/decrement property. Perform one of the following actions,
2981 where k is the value of the local variable given by %2.
2987 $1 has eligible __get method
2988 $1 has eligible __set method
2989 $1->k has been unset previously
2990 -------+--------------------------------------------------------------------
2991 00XXXXX | raise warning; push null
2992 01XXXXX | $1 = new stdclass; x = null; y = x; <op>y; $1->k = y;
2993 | push y (Pre*) or x (Post*)
2994 100X0XX | x = null; y = x; <op>y; $1->k = y; push y (Pre*) or x (Post*)
2995 100X10X | x = $1->__get(k); y = x; <op>y; $1->k = y;
2996 | push y (Pre*) or x (Post*)
2997 100X11X | x = $1->__get(k); y = x, <op>y; $1->__set(k, y);
2998 | push y (Pre*) or x (Post*)
2999 10100XX | throw fatal error
3000 101010X | throw fatal error
3001 101011X | x = $1->__get(k); y = x, <op>y; $1->__set(k, y);
3002 | push y (Pre*) or x (Post*)
3003 1011XX0 | x = $1->k; y = x; <op>y; $1->k = y; push y (Pre*) or x (Post*)
3004 10110X1 | x = null; y = x; <op>y; re-create $1->k; $1->k = y;
3005 | push y (Pre*) or x (Post*)
3006 1011101 | x = $1->__get(k); y = x; <op>y; re-create $1->k; $1->k = y;
3007 | push y (Pre*) or x (Post*)
3008 1011111 | x = $1->__get(k); y = x; <op>y; $1->__set(k, y);
3009 | push y (Pre*) or x (Post*)
3011 BindPropC [C V B] -> [V]
3013 Bind property. If $1 is an object that does not have an eligible __set method,
3014 this operation first checks if $1 has a visible property named $3. If it does
3015 not, this operation creates a new property named $3, executes $1->$3 =& $2,
3016 and pushes $2 onto the stack. Otherwise, this operation continues to check if
3017 the property named $3 is accessible. If the property named $3 is not
3018 accessible, this operation throws a fatal error. Otherwise, this operation
3019 executes $1->$3 =& $2 and pushes $2 onto the stack.
3021 If $1 is an object that has an eligible __set method, this operation checks
3022 if $1 has a visible and accessible property named $3. If it does, this
3023 operation follows the rules described in the first case given above.
3024 Otherwise this operation throws a fatal error.
3026 If $1 is null, false, or empty string, this operation sets $1 to a new object
3027 of type stdclass, executes $1->$3 =& $2, and pushes $2 onto the stack.
3029 If $1 is true, integer, double, a non-empty string, or an array, this
3030 operation raises a warning and pushes null onto the stack.
3032 BindPropL <local variable id> [V B] -> [V]
3034 Bind property. Where k is the value of the local variable given by %1:
3036 If $1 is an object that does not have an eligible __set method,
3037 this operation first checks if $1 has a visible property named k. If it does
3038 not, this operation creates a new property named k, executes $1->k =& $2,
3039 and pushes $2 onto the stack. Otherwise, this operation continues to check if
3040 the property named k is accessible. If the property named k is not
3041 accessible, this operation throws a fatal error. Otherwise, this operation
3042 executes $1->k =& $2 and pushes $2 onto the stack.
3044 If $1 is an object that has an eligible __set method, this operation checks
3045 if $1 has a visible and accessible property named k. If it does, this
3046 operation follows the rules described in the first case given above.
3047 Otherwise this operation throws a fatal error.
3049 If $1 is null, false, or empty string, this operation sets $1 to a new object
3050 of type stdclass, executes $1->k =& $2, and pushes $2 onto the stack.
3052 If $1 is true, integer, double, a non-empty string, or an array, this
3053 operation raises a warning and pushes null onto the stack.
3055 UnsetPropC [C B] -> []
3056 UnsetPropL <local variable id> [B] -> []
3060 These instructions first load a value into x and a base into y, as
3061 given by the following table:
3064 -------------+----+-----
3065 UnsetPropC | $2 | $1
3066 UnsetPropL | %1 | $1
3068 Next, performs one of the following actions:
3073 y has eligible __unset method
3074 -----+----------------------------------------------------------------------
3077 10X1 | y->__unset(x)
3078 1100 | throw fatal error
3079 1101 | y->__unset(x)
3083 10. Member instructions
3084 -----------------------
3086 Member instructions perform series of operations that are structurally
3087 identical, but each instruction utilizes a distinct set of operations. For each
3088 member instruction, first use a Base* operation depending on the kind of
3089 location code. Next perform a series of intermediate operations depending on
3090 member code to process all but the last member. Finally, perform a final
3091 operation depending on member code to process the last member. See the
3092 instruction-specific tables for details.
3094 The member codes that represent immediate literal data (ET, EI, PT) are
3095 implemented using the corresponding EC or PC intermediate operation: they
3096 behave exactly as though that literal data had been pushed on the stack as a
3097 cell, then consumed by an ElemC* or PropC* operation.
3099 CGetM <loc-desc/M-vector> [C..C] -> [C]
3103 location Base* member intermediate final
3104 descriptor operation code operation operation
3105 -----------+---------- -------+--------------+----------
3106 C | BaseC EC | ElemCW | CGetElemC
3107 R | BaseR PC | PropCW | CGetPropC
3108 L | BaseLW EL | ElemLW | CGetElemL
3109 NC | BaseNCW PL | PropLW | CGetPropL
3110 NL | BaseNLW W | N/A | N/A
3117 VGetM <loc-desc/M-vector> [C..C] -> [V]
3121 location Base* member intermediate final
3122 descriptor operation code operation operation
3123 -----------+---------- -------+--------------+------------
3124 C | BaseC EC | ElemCD | VGetElemC
3125 R | BaseR PC | PropCD | VGetPropC
3126 L | BaseLD EL | ElemLD | VGetElemL
3127 NC | BaseNCD PL | PropLD | VGetPropL
3128 NL | BaseNLD W | NewElem | VGetNewElem
3135 FPassM <param id> <loc-desc/M-vector> [C..C] -> [F]
3137 FPI pass parameter. This instruction behaves as CGetM if parameter
3138 %1 is pass by value, or it behaves like VGetM if parameter %1 is
3139 pass by reference. Then it passes the value produced to the callee.
3141 IssetM <loc-desc/M-vector> [C..C] -> [C:Bool]
3145 location Base* member intermediate final
3146 descriptor operation code operation operation
3147 -----------+---------- -------+--------------+-----------
3148 C | BaseC EC | ElemC | IssetElemC
3149 R | BaseR PC | PropC | IssetPropC
3150 L | BaseL EL | ElemL | IssetElemL
3151 NC | BaseNC PL | PropL | IssetPropL
3152 NL | BaseNL W | N/A | N/A
3159 EmptyM <loc-desc/M-vector> [C..C] -> [C:Bool]
3163 location Base* member intermediate final
3164 descriptor operation code operation operation
3165 -----------+---------- -------+--------------+-----------
3166 C | BaseC EC | ElemC | EmptyElemC
3167 R | BaseR PC | PropC | EmptyPropC
3168 L | BaseL EL | ElemL | EmptyElemL
3169 NC | BaseNC PL | PropL | EmptyPropL
3170 NL | BaseNL W | N/A | N/A
3177 SetM <loc-desc/M-vector> [C..C C] -> [C]
3181 location Base* member intermediate final
3182 descriptor operation code operation operation
3183 -----------+---------- -------+--------------+-----------
3184 C | BaseC EC | ElemCD | SetElemC
3185 R | BaseR PC | PropCD | SetPropC
3186 L | BaseLD EL | ElemLD | SetElemL
3187 NC | BaseNCD PL | PropLD | SetPropL
3188 NL | BaseNLD W | NewElem | SetNewElem
3195 SetWithRefLM <loc-desc/M-vector> <local variable id> [C..C] -> []
3197 Set member preserving the reffiness of the local.
3199 location Base* member intermediate final
3200 descriptor operation code operation operation
3201 -----------+---------- -------+--------------+-----------
3202 C | BaseC EC | ElemCD | SetWithRefElemC
3203 R | BaseR PC | PropCD | SetPropC
3204 L | BaseLD EL | ElemLD | SetWithRefElemL
3205 NC | BaseNCD PL | PropLD | SetPropL
3206 NL | BaseNLD W | NewElem | SetWithRefNewElem
3213 SetWithRefRM <loc-desc/M-vector> [C..C R] -> []
3215 Set member preserving the reffiness of the stack element.
3217 location Base* member intermediate final
3218 descriptor operation code operation operation
3219 -----------+---------- -------+--------------+-----------
3220 C | BaseC EC | ElemCD | SetWithRefElemC
3221 R | BaseR PC | PropCD | SetPropC
3222 L | BaseLD EL | ElemLD | SetWithRefElemL
3223 NC | BaseNCD PL | PropLD | SetPropL
3224 NL | BaseNLD W | NewElem | SetWithRefNewElem
3231 SetOpM <op> <loc-desc/M-vector> [C..C C] -> [C]
3235 location Base* member intermediate final
3236 descriptor operation code operation operation
3237 -----------+---------- -------+--------------+-------------
3238 C | BaseC EC | ElemCWD | SetOpElemC
3239 R | BaseR PC | PropCWD | SetOpPropC
3240 L | BaseLWD EL | ElemLWD | SetOpElemL
3241 NC | BaseNCWD PL | PropLWD | SetOpPropL
3242 NL | BaseNLWD W | NewElem | SetOpNewElem
3249 IncDecM <op> <loc-desc/M-vector> [C..C] -> [C]
3251 Increment/decrement member.
3253 location Base* member intermediate final
3254 descriptor operation code operation operation
3255 -----------+---------- -------+--------------+--------------
3256 C | BaseC EC | ElemCWD | IncDecElemC
3257 R | BaseR PC | PropCWD | IncDecPropC
3258 L | BaseLWD EL | ElemLWD | IncDecElemL
3259 NC | BaseNCWD PL | PropLWD | IncDecPropL
3260 NL | BaseNLWD W | NewElem | IncDecNewElem
3267 BindM <loc-desc/M-vector> [C..C V] -> [V]
3271 location Base* member intermediate final
3272 descriptor operation code operation operation
3273 -----------+---------- -------+--------------+------------
3274 C | BaseC EC | ElemCD | BindElemC
3275 R | BaseR PC | PropCD | BindPropC
3276 L | BaseLD EL | ElemLD | BindElemL
3277 NC | BaseNCD PL | PropLD | BindPropL
3278 NL | BaseNLD W | NewElem | BindNewElem
3285 UnsetM <loc-desc/M-vector> [C..C] -> []
3289 location Base* member intermediate final
3290 descriptor operation code operation operation
3291 -----------+---------- -------+--------------+-----------
3292 C | BaseC EC | ElemCU | UnsetElemC
3293 R | BaseR PC | PropCU | UnsetPropC
3294 L | BaseL EL | ElemLU | UnsetElemL
3295 NC | BaseNC PL | PropLU | UnsetPropL
3296 NL | BaseNL W | N/A | N/A
3304 11. Iterator instructions
3305 -------------------------
3307 IterInit <iterator id> <rel offset> <local id> [C] -> []
3308 IterInitK <iterator id> <rel offset> <local id> <local id> [C] -> []
3309 WIterInit <iterator id> <rel offset> <local id> [C] -> []
3310 WIterInitK <iterator id> <rel offset> <local id> <local id> [C] -> []
3312 Initialize iterator. If $1 is an array, these instructions create an array
3313 iterator, rewind the array iterator to point to the beginning of the array,
3314 and store the array iterator in the iterator variable %1. Then these
3315 instructions check if the iterator is at the end, and if it is, these
3316 instructions free the iterator and transfer control to the location specified
3319 If $1 is an object that is an instance of an extension class that implements
3320 the Traversable interface, these instructions create an extension class
3321 iterator and store it in the iterator variable %1. Then these instructions
3322 check if the iterator is at the end, and if it is these instructions free the
3323 iterator and transfer control the location specified by %2.
3325 If $1 is an object that implements the Iterator interface, these instructions
3326 create an user class iterator, call $1->rewind(), and store the user class
3327 iterator in the iterator variable %1. Then these instructions check if
3328 $1->valid() returns false, and if it does these instructions free the iterator
3329 and transfer control to the location specified by %2.
3331 If $1 is an object that implements the IteratorAggregate interface, these
3332 instructions call $1->getIterator() and inspect the object x that is
3333 returned. If x is an instance of IteratorAggregate, these instructions will
3334 repeatedly execute "x = x->getIterator()" until x is not an object that is an
3335 instance of IteratorAggregate. If x is an object that implements the
3336 Traversable interface, then this instruction will behave according to the
3337 appropriate case described above. Otherwise, these instructions will throw an
3338 exception of type Exception.
3340 If $1 is an object that does not match any of the three cases above, these
3341 instructions create a default class iterator, rewind the default class
3342 iterator to point to the first accessible property, and store the default
3343 class iterator in the iterator variable %1. Then these instructions check if
3344 the iterator is at the end, and if it is these instructions free the iterator
3345 and transfer control the location specified by %2.
3347 If $1 is not an array or an object, these instructions raise a warning and
3348 transfer control to the location specified by %2.
3350 If the iterator specified by %1 is a non-mutable array iterator or an
3351 extension class iterator, IterInit and IterInitK store a copy of the current
3352 value in %3 as a cell; WIterInit and WIterInitK will store a reference
3353 if the current element is a reference, or a value otherwise in %3
3355 If the iterator specified by %1 is a user class iterator for object $x, these
3356 instructions store the return value of $x->current() in %3 as a cell.
3358 If the iterator specified by %1 is a non-mutable default class iterator, these
3359 instructions store a copy of the current property in %3 as a cell.
3361 For the IterInitK version, the following also happens:
3363 If the iterator specified by %1 is an array iterator or an extension class
3364 iterator, this instruction stores a copy of the current key in %4 as a cell.
3366 If the iterator specified by %1 is a user class iterator for object $x, this
3367 instruction stores the return value of $x->key() in %4 as a cell.
3369 If the iterator specified by %1 is a non-mutable default class iterator,
3370 this instruction stores a copy of the name of the current property in %4 as a
3373 MIterInit <iterator id> <rel offset> <local id> [V] -> []
3374 MIterInitK <iterator id> <rel offset> <local id> <local id> [V] -> []
3376 Initialize mutable iterator. If $1 is an array, these instructions create a
3377 mutable array iterator, rewind the mutable array iterator to point to the
3378 beginning of the array, and store the mutable array iterator in the iterator
3379 variable %1. Then these instructions check if the iterator is at the end, and
3380 if it is these instructions free the iterator and transfers control the
3381 location specified by %2.
3383 If $1 is an object that is an instance of an extension class that implements
3384 the Traversable interface, these instructions raise a fatal error.
3386 If $1 is an object that implements the Iterator interface, these instructions
3387 throw a fatal error.
3389 If $1 is an object that implements the IteratorAggregate interface, these
3390 instructions throw a fatal error.
3392 If $1 is an object that does not match any of the three cases above, these
3393 instructions create a mutable default class iterator, rewind it to point to
3394 the first accessible property, and store the it in the iterator variable %1.
3395 Then these instructions check if the iterator is at the end, and if it is
3396 these instructions free the iterator and transfer control to the location
3399 If $1 is not an array or an object, these instructions raise a warning and
3400 transfer control to the location specified by %2.
3402 If the iterator specified by %1 is a mutable array iterator, these
3403 instructions store the current value in %3 as a ref.
3405 If the iterator specified by %1 is a mutable default class iterator, these
3406 instructions store the current property in %3 as a ref.
3408 For the MIterInitK version, the following also happens:
3410 If the iterator specified by %1 is an array iterator, this instruction
3411 stores a copy of the current key in %4 as a cell.
3413 If the iterator specified by %1 is a mutable default class iterator,
3414 this instruction stores a copy of the name of the current property in %4 as a
3417 IterNext <iterator id> <rel offset> <local id> [] -> []
3418 IterNextK <iterator id> <rel offset> <local id> <local id> [] -> []
3419 WIterNext <iterator id> <rel offset> <local id> [] -> []
3420 WIterNextK <iterator id> <rel offset> <local id> <local id> [] -> []
3422 Iterator next. If the specified iterator is a non-mutable array iterator
3423 or an extension class iterator, advance the iterator to point to the next
3424 element. If the iterator is not at the end, these instructions transfer
3425 control to the location specified by %2.
3427 If the specified iterator is a user class iterator for object $x, this
3428 instruction executes $x->next(). Then these instructions check if $x->valid()
3429 returns true, and if it does these instructions transfer control to the
3430 location specified by %2.
3432 If the specified iterator is a non-mutable default class iterator, advance
3433 the iterator to point to the next accessible property in the object.
3434 If the iterator is not at the end, these instructions transfer control
3435 to the location specified by %2.
3437 If the specified iterator is at the end, free the iterator variable with
3438 an implicit IterFree, then fall through to the next instruction.
3440 If the specified iterator is not at the end, retrieve the key and value:
3442 If the iterator specified by %1 is a non-mutable array iterator or an
3443 extension class iterator, IterNext and IterNextK store a copy of the new current
3444 value in %3 as a cell; WIterNext and WIterNextK store a reference to the
3445 new current value in %3 if the current value is a reference, otherwise
3446 they store the new current value in %3 as a cell.
3448 If the iterator specified by %1 is a user class iterator for object $x, these
3449 instructions store the return value of $x->current() in %3 as a cell.
3451 If the iterator specified by %1 is a non-mutable default class iterator, these
3452 instructions store a copy of the new current property in %3 as a cell.
3454 For the IterNextK version, the following also happens:
3456 If the iterator specified by %1 is an array iterator or an extension class
3457 iterator, this instruction stores a copy of the new current key in %4 as a
3460 If the iterator specified by %1 is a user class iterator for object $x, this
3461 instruction stores the return value of $x->key() in %4 as a cell.
3463 If the iterator specified by %1 is a non-mutable default class iterator,
3464 this instruction stores a copy of the name of the new current property in %4
3467 MIterNext <iterator id> <rel offset> <local id> [] -> []
3468 MIterNextK <iterator id> <rel offset> <local id> <local id> [] -> []
3470 Iterator next. If the specified iterator is a mutable array iterator,
3471 advance the iterator to point to the next element. If the iterator
3472 is not at the end, these instructions transfer control to the
3473 location specified by %2.
3475 If the specified iterator is a mutable default class iterator, advance
3476 the iterator to point to the next accessible property in the object.
3477 If the iterator is not at the end, these instructions transfer control
3478 to the location specified by %2.
3480 If the specified iterator is at the end, free the iterator variable with
3481 an implicit MIterFree, then fall through to the next instruction.
3483 If the specified iterator is not at the end, retrieve the key and value:
3485 If the iterator specified by %1 is a mutable array iterator, these
3486 instructions store the new current value in %3 as a ref.
3488 If the iterator specified by %1 is a mutable default class iterator, these
3489 instructions store the new current property in %3 as a ref.
3491 For the MIterNextK version, the following also happens:
3493 If the iterator specified by %1 is an array iterator, this instruction
3494 stores a copy of the new current key in %4 as a cell.
3496 If the iterator specified by %1 is a mutable default class iterator,
3497 this instruction stores a copy of the name of the new current property in %4
3500 IterFree <iterator id> [] -> []
3502 Iterator free. This instruction frees the specified iterator variable.
3503 Typically an iterator gets freed by IterNext, so IterFree is only needed
3504 for guarding against exceptions and implementing break and return control
3505 flow statements inside iterator loops.
3507 MIterFree <iterator id> [] -> []
3509 Mutable iterator free. This instruction frees the specified iterator
3510 variable. Typically an iterator gets freed by MIterNext*, so MIterFree is
3511 only needed for guarding against exceptions and implementing break and
3512 return control flow statements inside iterator loops.
3514 CIterFree <iterator id> [] -> []
3516 Cuf iterator free. This instruction frees the specified iterator
3519 IterBreak <iter-vec> <rel offset> [] -> []
3521 Iterator break. Frees vectors in %1 in left to right order then transfers
3522 control to the locaton specified by %2. Surprise checks are performed
3523 before iterators are freed so that in the event of an exception iterators
3524 are not double freed. Note that as with normal jumps surprise checks will
3525 only be performed if %2 is negative.
3528 12. Include, eval, and define instructions
3529 ------------------------------------------
3533 Include. Includes the compilation unit containing the file (string)$1. The
3534 instruction eagerly marks all functions and classes that are unconditionally
3535 declared in the outermost scope as defined. Next this instruction calls the
3536 pseudo-main function from the file (string)$1. The pseudo-main function
3537 inherits the caller's variable environment. If the execution engine cannot
3538 find a compilation unit containing the file (string)$1, this instruction
3543 Include once. Include the compilation unit containing the file (string)$1 if
3544 it hasn't been included already. This instruction eagerly marks all functions
3545 and classes that are unconditionally declared in the outermost scope as
3546 defined, and then calls the pseudo-main function from (string)$1 if it hasn't
3547 run already. The pseudo-main function inherits the caller's variable
3548 environment. If the execution engine cannot find a compilation unit
3549 containing the file (string)$1, this instruction raises a warning.
3553 Require. Includes the compilation unit containing the file (string)$1. The
3554 instruction eagerly marks all functions and classes that are unconditionally
3555 declared in the outermost scope as defined. Next this instruction calls the
3556 pseudo-main function from the file (string)$1. The pseudo-main function
3557 inherits the caller's variable environment. If the execution engine cannot
3558 find a compilation unit containing the file (string)$1, this instruction
3559 throws a fatal error.
3563 Require once. Include the compilation unit containing the file (string)$1 if
3564 it hasn't been included already. This instruction eagerly marks all functions
3565 and classes that are unconditionally declared in the outermost scope as
3566 defined, and then calls the pseudo-main function from (string)$1 if it hasn't
3567 run already. The pseudo-main function inherits the caller's variable
3568 environment. If the execution engine cannot find a compilation unit
3569 containing the file (string)$1, this instruction throws a fatal error.
3573 As ReqOnce except the string is always taken to be relative to the document
3574 root (ie SourceRoot).
3578 Eval. Executes the source code in (string)$1. This instruction eagerly marks
3579 all functions and classes that are unconditionally declared in the outermost
3580 scope as defined, and then calls the pseudo-main function from (string)$1.
3581 The pseudo-main function from (string)$1 inherits the caller's variable
3584 DefFunc <function id> [] -> []
3586 Define function. Bind the function specified by %1. If the function specified
3587 by %1 is already bound, this instruction does nothing. If another function is
3588 already bound to the name associated with %1, this instruction throws a fatal
3591 DefCls <class id> [] -> []
3593 Define class. Bind the class specified by %1. If the class specified by %1 is
3594 already bound, this instruction does nothing. If another class is already
3595 bound to the associated name, this instruction throws a fatal error.
3597 DefCns <litstr id> [C] -> [C]
3599 Define constant. If there is already a global constant named %1, raises a
3600 notice and pushes false. If $1 is an array or an object, raises a notice, and
3601 pushes false. Otherwise defines the constant named %1 to have the value $1,
3604 DefTypedef <litstr id> [] -> []
3606 Define typedef. Typedefs are a hhvm extension to php that allow
3607 declaring new names for existing types. The unit contains a table
3608 of the typedefs it was compiled with. This instruction looks up the
3609 typedef given by %1 in the table. If there is an existing class or
3610 typedef defined with the same name as %1, this function checks
3611 whether it is compatible with the typedef given by %1, and if it
3612 isn't it raises a fatal error.
3615 13. Miscellaneous instructions
3616 ------------------------------
3620 This. This instruction checks the current instance, and if it is null, this
3621 instruction throws a fatal error. Next, this instruction pushes the current
3622 instance onto the stack.
3624 BareThis <notice> [] -> [C:Obj]
3626 This. This instruction pushes the current instance onto the stack. If %1 is
3627 not zero, and the current instance is null, emits a notice.
3631 Check existence of this. This instruction checks the current instance, and if
3632 it is null, throws a fatal error.
3634 InitThisLoc <local variable id> [] -> []
3636 Initialize this local variable. This instruction checks the current instance,
3637 and if it is not null this instruction stores it to the specified local
3638 variable. If the current instance is null, or if this bytecode appears in
3639 a function body that is not a class method, this instruction does nothing.
3641 StaticLoc <local variable id> <litstr id> [] -> [C:Bool]
3643 Static variable. This instruction first checks if the static variable named
3644 %2 has been marked as initialized. If the static variable has been marked as
3645 initialized, this instruction binds the static variable to the local variable
3646 %1 and pushes true. Otherwise, this instruction binds the static variable to
3647 the local variable %1, marks the static variable as initialized, and pushes
3650 StaticLocInit <local variable id> <litstr id> [C] -> []
3652 Static variable with initializer. This instruction first checks if the static
3653 variable named %2 has been marked as initialized. If the static variable has
3654 been marked as initialized, this instruction binds the static variable to the
3655 local variable %1. Otherwise, this instruction binds the static variable to
3656 the local variable, assigns $1 to the local variable, and marks the static
3657 variable as initialized.
3659 The cell in $1 must not be a reference counted type.
3663 Catch. Retrieves the current exception object and pushes it onto the stack.
3664 This instruction may only be used at the beginning of a catch entry point.
3666 ClassExists [C C] -> [C:Bool]
3667 InterfaceExists [C C] -> [C:Bool]
3668 TraitExists [C C] -> [C:Bool]
3670 Check for class/interface/trait existence. If $1 cannot be cast to a
3671 bool or $2 cannot be cast to a string, this instruction will throw a
3672 fatal error. Otherwise, it will check for existence of the entity
3673 named by $2, invoking the autoloader if needed and if $1 is
3674 true. The result of the existence check will be pushed on the stack.
3676 VerifyParamType <parameter id> [] -> []
3678 Verify parameter type. Functions and methods can optionally specify the
3679 types of arguments they will accept. These type constraints are memoized
3680 into each function's FPI structure.
3682 VerifyParamTypes checks the specified parameter against the enclosing
3683 function's corresponding parameter constraints. In case of a mismatch, a
3684 recoverable error is raised.
3688 Creates a classref that refers to the class in which the current
3689 function is defined. This instruction throws a fatal error if the
3690 current method is defined outside of a class, otherwise it pushes a
3691 classref on the stack.
3695 Creates a classref that refers to the parent of the class in which
3696 the current method is defined. This instruction throws a fatal
3697 error if the current method is defined outside of a class or if the
3698 class in which the current method is defined has no parent,
3699 otherwise it pushes a classref on the stack.
3701 LateBoundCls [] -> [A]
3703 Late-bound class. Creates a classref that refers to the current late-bound
3704 class and pushes it onto the stack.
3708 Native implementation. This instruction invokes the native implementation
3709 associated with current function and returns the return value to the caller
3710 of the current function.
3712 IncStat <counter id> <value> [] -> []
3714 Increment stat counter. If stats are enabled, this instruction adds
3715 <value> to the counter specified by <counter id>. The meaning of the
3716 <counter id> immediate is implementation defined
3718 AKExists [C C] -> [C:Bool]
3720 Checks if array (object) in $1 contains key (property) in $2 and
3721 pushes the resulting boolean onto the stack. If $2 is null, uses
3722 the empty string as key. Throws a fatal error if $1 is not an array
3723 or object, and raises a warning if $2 is not a string, integer, or
3726 CreateCl <num args> <class name> [C|V..C|V] -> [C]
3728 Creates an instance of <class name> and pushes it on the stack. The
3729 class named by %2 must be a subclass of "Closure", and must be
3730 defined at the point of the CreateCl opcode, or the behavior is
3733 ArrayIdx [C C C] -> [C]
3735 Checks if array in $3 contains key in $2 and pushes the result onto the stack
3736 if found. Otherwise, $1 is pushed onto the stack. A fatal error will be
3737 thrown if $3 is not an array.
3739 14. Continuation creation and execution
3740 ---------------------------------------
3742 CreateCont <function name> [] -> [C]
3744 Creates a Continuation object and pushes it on the stack. The Continuation
3745 will capture all defined local variables in the current function. The
3746 Continuation will store a reference to the function named by the string
3747 immediate to be used as its body.
3749 CreateAsync <function name> <label id> <number of iterators> [C] -> [C]
3751 Analogy of CreateCont for async functions. Creates a Continuation object,
3752 updates its label with <label id> immediate and stores a value from the stack
3753 to its m_value field. Unlike CreateCont, it also copies the first
3754 <number of iterators> iterators into the continuation frame.
3758 This instruction may only appear in non-static methods of the Continuation
3759 class. It transfers control flow to the beginning of the continuation body
3760 associated with the $this object of the Continuation object. The value on the
3761 stack is sent to the Continuation to be retrieved by UnpackCont.
3763 ContSuspend <label id> [C] -> []
3765 Suspend continuation. This instruction may only appear in continuation bodies.
3766 Packs all defined local variables into the Continuation object in local 0.
3767 Store $1 in the continuation as the result of the current iteration and
3768 set the continuation's label to <label id>. Transfer control flow to the
3769 caller of the continuation body, which must be a non-static method of the
3772 ContSuspendK <label id> [C C] -> []
3774 Suspend continuation. This instruction may only appear in continuation bodies.
3775 Packs all defined local variables into the Continuation object in local 0.
3776 Store $1 in the continuation as the result of the current iteration,
3777 store $2 as the key of the current iteration, and set the continuation's label
3778 to <label id>. Transfer control flow to the caller of the continuation body,
3779 which must be a non-static method of the Continuation class.
3781 UnpackCont [] -> [C:Int C]
3783 Unpack continuation. Unpacks variables from the Continuation object in local
3784 0 into the containing environment. The stack will contain the current label of
3785 the continuation in $1 and the value sent to the continuation in $2. The value
3786 will be no longer referenced by the Continuation object.
3790 Return from continuation. Marks the continuation in local 0 as finished, sets
3791 the result and transfers control flow to the caller of the continuation body,
3792 which must be a non-static method of the Continuation class. Further attempts
3793 to iterate it will fail.
3795 ContCheck <check started> [] -> []
3797 Check whether continuation can be iterated. $this must be a Continuation
3798 object. If the continuation is finished, already running, or not yet started
3799 and <check started> is enabled, an exception will be thrown.
3803 Prepare continuation to receive a thrown exception. $this must be a
3804 Continuation object that passed ContCheck<true> check.
3806 ContValid [] -> [C:Bool]
3808 Check continuation validity. $this must be a Continuation object. Pushes true
3809 onto the stack if the continuation can be iterated further, false otherwise.
3813 Get continuation key. $this must be a Continuation object. Pushes the most
3814 recently yielded key from the continuation onto the stack.
3816 ContCurrent [] -> [C]
3818 Get continuation value. $this must be a Continuation object. Pushes the most
3819 recently yielded value from the continuation onto the stack.
3821 ContStopped [] -> []
3823 Mark continuation as stopped. $this must be a Continuation object.
3825 ContHandle [C] -> []
3827 Handle exception from continuation body. $this must be a Continuation
3828 object. Marks the continuation as no longer running and finished and rethrows
3829 the exception on the top of the stack.
3831 Basic statement transformations
3832 -------------------------------
3834 To achieve HHBC's goal of making it straightforward for an interpreter or a
3835 compiler to determine order of execution, control flow statements are
3836 transformed to use the simpler constructs. Most control flow statements such as
3837 "if", "while", and "for" are implemented in a straightforward manner using the
3840 HHBC provides the Switch instruction for implementing very simple switch
3841 statements; most real switch statements are implemented naively using the Eq
3842 and JmpNZ instructions. Also, the functionality of both the echo statement and
3843 the print statement is implemented with the Print instruction.
3845 Foreach statements are implemented using iterator variables and the Iter* and
3846 MIter* instructions. Each foreach loop must be protected by a fault funclet to
3847 ensure that the iterator variable is freed when a foreach loop exits abnormally
3848 through an exception.
3850 Simple break statements and continue statements are implemented using the Jmp*,
3851 IterFree, MIterFree and CIterFree instructions. Dynamic break is implemented using
3852 an unnamed local (to store the 'break count') and a chain of basic blocks, where
3853 each block decrements the unnamed local variable and compares it with 0, and
3854 then decides where to jump next.
3857 Basic expression transformations
3858 --------------------------------
3860 To reduce the size of the instruction set, certain types of expressions are
3863 1) Unary plus and negation
3864 Unary plus and negation "+(<expression>)" gets converted to
3865 "(0 + (<expression>))", and "-(<expression>)" gets converted to
3866 "(0 - (<expression>))".
3868 2) Assignment-by operators (+=, -=, etc)
3869 Assignment-by operators are converted to use the SetOp* instructions.
3871 3) List assignment (list)
3872 List assignments are converted to use an unnamed local variable and the SetM
3873 and VGet* instructions. If the function contains any catch funclets, then
3874 list assignment requires a fault funclet as well.
3876 4) Logical and and logical or operators (and/&&, or/||)
3877 If any of the operands side-effect, these operators are implemented using Jmp*
3878 instructions instead of using the "and" and "or" instructions to implement
3879 short-circuit semantics correctly. All Jmp* instructions used to implement
3880 "and" and "or" operators will be forward jumps.
3882 5) The new expression
3883 The new expression is implemented by using the FPushCtor*, FPass*, and FCall
3886 6) The ternary operator (?:)
3887 The functionality of the ternary operator is implemented using Jmp*
3888 instructions. All Jmp* instructions used to implement the ternary operator will
3891 7) Silence operator (@)
3892 The silence operator is implemented by using various instructions (including
3893 the Jmp* instructions), unnamed local variables, and a fault funclet. All Jmp*
3894 instructions used to implement the silence operator will be forward jumps.
3896 8) The $this expression
3897 The $this expression has different effects depending on whether or not $this is
3898 the direct base of a property expression (such as "$this->x") or a method call
3899 expression (such as "$this->foo()"). When the $this expression is the direct
3900 base of a property expression or a method call expression, the This instruction
3903 A bare $this expression within an instance method is handled one of two ways:
3904 general or BareThis-optimized (optional). The general solution accesses a
3905 local variable named "this", which is initialized at the beginning of the
3906 method using the InitThisLoc instruction. The BareThis optimization applies to
3907 bare $this access as long as $this is not passed by reference and there are no
3908 dynamic method variables. In such cases, the BareThis instruction can be used
3909 to directly access $this, and the InitThisLoc instruction is not needed.
3912 Warning and errors at parse time
3913 --------------------------------
3915 Certain syntactically correct source code may cause warnings or errors to be
3916 raised when the source file is parsed. Examples of this include using "$this"
3917 on the left hand side of the assignment, using "$this" with binding assignment,
3918 using "$a[]" in an r-value context, and doing "unset($a[])". HHBC handles these
3919 cases by generating Raise or Fatal instructions at the beginning of the body
3920 for the pseudo-main function.
3926 HipHop bytecode v1 revision 16 does not implement the following:
3927 1) Description of traits
3928 2) Description of metadata for class statements, trait statements, and method
3930 3) Description and examples for the yield generator feature
3931 4) Description of the late static binding feature
3932 5) Description of the resource type
3933 6) Definitions of operators (ex. +, -, !) and other helper functions (ex.
3934 is_null, get_class, strlen)
3935 7) Support for the PHP 5.3 namespace feature
3938 Source code to HHBC examples
3939 ----------------------------
3941 function f() { return $a = $b; }
3947 function f() { g($a, $b); }
3957 function f() { return $a + $b; }
3964 function f() { echo "Hello world\n"; }
3966 String "Hello world\n"
3972 function f($a) { return $a[0]++; }
3975 IncDecM PostInc <L:0 EC>
3978 function f($a, $b) { $a[4] = $b; }
3987 function f($a, $b, $i) { $a[$i] = $b; }
3995 function f($a, $b) { return $a[4] = $b; }
4002 function f($a, $b) { return $a[4][5] = $b[6]; }
4011 function f($a, $b, $i) { return $a[$i][5] = $b[6]; }
4019 function f($a, $b) { $a->prop = $b; }
4028 function f() { return FOO; }
4033 function f() { return c::FOO; }
4038 function f($cls) { return $cls::FOO; }
4044 class c { public function f($a) { $this->prop = $a; return $this; } }
4046 // The emitter emits the InitThisLoc instruction at the top of an instance
4047 // method if and only if the function contains a use of "$this" that is not
4048 // part of a property expression or a method call expression. The emitter never
4049 // emits the InitThisLoc instruction for static methods.
4051 // Evaluate "$this->prop = $a". The This instruction will throw a fatal error
4052 // if the current instance is null.
4058 // Return the local variable named "this"
4062 class c { static public function f($a) { $this->prop = $a; return $this; } }
4064 // Evaluate "$this->prop = $a". The This instruction will throw a fatal error
4065 // because this is a static method.
4071 // Return the local variable named "this"
4075 function f($a, $b, $c, $d) {
4076 static $foo = array(array());
4077 return $foo[0][$c + $d] += $a + $b;
4080 // Bind static variable named "foo" to local variable named "foo"
4081 Array array(0=>array())
4082 StaticLocInit 4 "foo"
4083 // Evaluate $foo[0][$c + $d]
4088 // Evaluate ($a + $b)
4092 // Execute $foo[0][$c + $d] += $a + $b
4093 SetOpM OpAdd <L:4 EC EC>
4096 function f($a) { list($x, $y, $z) = $a[7]; return $x + $y + $z; }
4098 // Evaluate $a[7] and store it in an unnamed local
4102 // Read the unnamed local, get the value at index 2, and store it in $z
4106 // Read the unnamed local, get the value at index 1, and store it in $y
4110 // Read the unnamed local, get the value at index 0, and store it in $x
4114 // Unset the unnamed local
4116 // Evaluate $x + $y + $z and return the result
4124 function f(&$a, $b) {
4126 $r[v()] = (list(list($a[w()], $a[x()]), list($a[y()], $a[z()])) = $b[100]);
4130 // Evaluate $r = array()
4134 // Do the first pass of evaluation for $r[v()]
4138 // Do the first pass of evaluation for $a[w()]
4142 // Do the first pass of evaluation for $a[x()]
4146 // Do the first pass of evaluation for $a[y()]
4150 // Do the first pass of evaluation for $a[z()]
4154 // Evaluate $b[100] and store it in an unnamed local t
4158 // Read t[1][1] and store it in $a[z()]
4159 CGetM <L:3 EI:1 EI:1>
4162 // Read t[1][0] and store it in $a[y()]
4163 CGetM <L:3 EI:1 EI:0>
4166 // Read t[0][1] and store it in $a[x()]
4167 CGetM <L:3 EI:0 EI:1>
4170 // Read t[0][0] and store it in $a[w()]
4171 CGetM <L:3 EI:0 EI:0>
4174 // Read t and leave the value on the stack
4176 // Unset the unnamed local t
4178 // Assign the output of the outer list assignment expression into $r[v()]
4186 $arr1 = array(0 => 1, 2 => 5, 7 => 'foo', 'bar' => 888);
4187 $arr2 = array(0 => 6, 2 => 8, 5 => 'yar', 'baz' => 333);
4188 $arr3 = array_merge((list($a, , $b) = $arr1), (list($c, , $d) = $arr2));
4189 var_dump($a, $b, $c, $d, $arr3);
4192 // Evaluate $arr1 = array(0 => 1, 2 => 5, 7 => 'foo', 'bar' => 888)
4193 Array array(0=>1,2=>5,7=>"foo","bar"=>888)
4196 // Evaluate $arr2 = array(0 => 6, 2 => 8, 5 => 'yar', 'baz' => 333)
4197 Array array(0=>6,2=>8,5=>"yar","baz"=>333)
4200 // Prepare to call array_merge
4201 FPushFuncD 2 "array_merge"
4202 // Evaluate (list($a, , $b) = $arr1)
4209 // Pass the result as the first parameter
4211 // Evaluate (list($c, , $d) = $arr2)
4218 // Pass the result as the second parameter
4222 // Store the result in $arr3
4226 // Evaluate var_dump($a, $b, $c, $d, $arr3)
4227 FPushFuncD 5 "var_dump"
4239 function f() { global $foo; return ++$foo; }
4241 // Bind global variable named "foo" to local variable named "foo"
4246 // Evaluate "++$foo" and return the result
4250 function f($name) { global $$name; return $$name++; }
4252 // Bind global variable named $name to a local variable named $name
4258 // Evaluate "$$name++" and return the result
4263 function f() { $GLOBALS['blah'] = array(2, "foo" => "bar"); }
4265 // If a global variable is superglobal, don't bind it to a local; instead we
4266 // access it directly
4268 Array array(0=>2,"foo"=>"bar")
4274 function &f(&$x) { return $x; }
4279 function f($x) { return $x[0]->h()->prop[1]; }
4283 FPushObjMethodD 0 "h"
4290 function f($x, $y) { return $y($x[0]->h()->prop[1]); }
4296 FPushObjMethodD 0 "h"
4305 function f() { return new c; }
4312 function f() { return c::$d; }
4320 function f() { return c::$d[0]; }
4329 function f($cls, $name) { $cls::$$name = g(); }
4341 function f($cls, $name, $index) { $cls::${$name}[$index] = g(); }
4352 function f($cls, $name, $index) { $cls::$$name[$index] = g(); }
4365 if (empty(c::$foo)) {
4367 c::$foo[0]->prop = 3;
4369 h(c::$foo[0]->prop);
4403 function f($cls, $spropName) {
4404 if (!isset($cls::$$spropName)){
4405 $cls::$$spropName = g();
4407 h($cls::$$spropName);
4430 class c { public static function f() { return c::g(); } }
4432 FPushClsMethodD 0 "g" "c"
4437 class c { public static function f() { return static::g(); } }
4446 function f() { self::x(); }
4456 class c { public static function f() { return self::$x; } }
4463 function f() { return new parent(); }
4471 class B extends A { public static function f() { return parent::x; } }
4476 foreach ($arr1 as $v1) {
4477 foreach($arr2 as $v2) {
4485 IterInit 0 endFor1 $v1
4489 IterInit 1 endFor2 $v2
4497 IterBreak <(Iter) 1, (Iter) 2> endFor1
4500 IterNext 1 startFor2 $v2
4503 IterNext 1 startFor1 $v1