3v4l.org

run code in 300+ PHP versions simultaneously
<?php namespace Demo; class OutOfMemory extends \Exception {} class InvalidFree extends \Exception {} // This is the system heap, this system only has 128 bytes of memory available to applications const HEAP_SIZE = 128; $heap = "0123456789ABCDEF0123456789ABCDEF0123456789ABCDEF0123456789ABCDEF0123456789ABCDEF0123456789ABCDEF0123456789ABCDEF0123456789ABCDEF"; // The operating system allocator keeps track of the memory block that have been allocated to each application $blocks = []; function malloc($size) { global $blocks; $newPtr = 0; foreach ($blocks as $ptr => $size) { // If the gap between $newPtr and the start of this block is big enough to fit the request size, // allocate the block in between if ($newPtr + $size <= $ptr) { $blocks[$newPtr] = $size; return $newPtr; } $newPtr = $ptr + $size; } // Check if there's enough space at the end // When allocating at the end, verify that the requested size won't overflow the heap if ($newPtr + $size <= HEAP_SIZE) { $blocks[$newPtr] = $size; return $newPtr; } // There was not a large enough contiguous block on the heap to allocate the requested size throw new OutOfMemory; } function free($ptr) { global $blocks; // Can only free a complete block that has been allocated (can't free a partial one) if (!isset($blocks[$ptr])) { throw new InvalidFree; } unset($blocks[$ptr]); } // strcpy() is an example of a function that works with C strings and relies on the presence of a null terminator function strcpy($dstPtr, $srcPtr) { global $heap; for ($i = 0; $heap[$srcPtr + $i] !== "\0"; $i++) { $heap[$dstPtr + 0] = $heap[$srcPtr + $i]; } } // Output an arbitrary block from the heap // Notice that this requires a length argument so it knows when to stop function output($ptr, $len) { global $heap; for ($i = 0; $ptr + $i < HEAP_SIZE && $i < $len; $i++) { echo $heap[$ptr + $i]; } // This is just here to make the output readable echo "\n\n"; } // Output a string // No length argument here, so it must be a valid string function output_string($ptr) { global $heap; for ($i = 0; $ptr + $i < HEAP_SIZE && $heap[$ptr + $i] !== "\0"; $i++) { echo $heap[$ptr + $i]; } // This is just here to make the output readable echo "\n\n"; } $myString = malloc(14); $heap[$myString + 0] = 'h'; $heap[$myString + 1] = 'e'; $heap[$myString + 2] = 'l'; $heap[$myString + 3] = 'l'; $heap[$myString + 4] = 'o'; $heap[$myString + 5] = ','; $heap[$myString + 6] = ' '; $heap[$myString + 7] = 'w'; $heap[$myString + 8] = 'o'; $heap[$myString + 9] = 'r'; $heap[$myString + 10] = 'l'; $heap[$myString + 11] = 'd'; $heap[$myString + 12] = '!'; $heap[$myString + 13] = "\0"; // fine, this is a valid string, it has a null terminator output_string($myString); $arbitraryBlock = malloc(1); $heap[$arbitraryBlock] = '#'; // fine, we gave it a sensible length output($arbitraryBlock, 1); // but if we do this, we get an overflow and it keeps going until it encounters the next null byte or the end of the heap output_string($arbitraryBlock); // things can get weirder when stuff like this happens free($myString); // release the memory back to the OS $newString = malloc(9); // this will end up reallocating the same block $heap[$newString + 0] = 'H'; $heap[$newString + 1] = 'i'; $heap[$newString + 2] = ' '; $heap[$newString + 3] = 't'; $heap[$newString + 4] = 'h'; $heap[$newString + 5] = 'e'; $heap[$newString + 6] = 'r'; $heap[$newString + 7] = 'e'; // oops! no null terminator output_string($newString);
Finding entry points
Branch analysis from position: 0
1 jumps found. (Code = 62) Position 1 = -2
filename:       /in/871f4
function name:  (null)
number of ops:  100
compiled vars:  !0 = $heap, !1 = $blocks, !2 = $myString, !3 = $arbitraryBlock, !4 = $newString
line      #* E I O op                           fetch          ext  return  operands
-------------------------------------------------------------------------------------
    9     0  E >   DECLARE_CONST                                            'Demo%5CHEAP_SIZE', 128
   10     1        ASSIGN                                                   !0, '0123456789ABCDEF0123456789ABCDEF0123456789ABCDEF0123456789ABCDEF0123456789ABCDEF0123456789ABCDEF0123456789ABCDEF0123456789ABCDEF'
   13     2        ASSIGN                                                   !1, <array>
   93     3        INIT_NS_FCALL_BY_NAME                                    'Demo%5Cmalloc'
          4        SEND_VAL_EX                                              14
          5        DO_FCALL                                      0  $7      
          6        ASSIGN                                                   !2, $7
   94     7        ADD                                              ~9      !2, 0
          8        ASSIGN_DIM                                               !0, ~9
          9        OP_DATA                                                  'h'
   95    10        ADD                                              ~11     !2, 1
         11        ASSIGN_DIM                                               !0, ~11
         12        OP_DATA                                                  'e'
   96    13        ADD                                              ~13     !2, 2
         14        ASSIGN_DIM                                               !0, ~13
         15        OP_DATA                                                  'l'
   97    16        ADD                                              ~15     !2, 3
         17        ASSIGN_DIM                                               !0, ~15
         18        OP_DATA                                                  'l'
   98    19        ADD                                              ~17     !2, 4
         20        ASSIGN_DIM                                               !0, ~17
         21        OP_DATA                                                  'o'
   99    22        ADD                                              ~19     !2, 5
         23        ASSIGN_DIM                                               !0, ~19
         24        OP_DATA                                                  '%2C'
  100    25        ADD                                              ~21     !2, 6
         26        ASSIGN_DIM                                               !0, ~21
         27        OP_DATA                                                  '+'
  101    28        ADD                                              ~23     !2, 7
         29        ASSIGN_DIM                                               !0, ~23
         30        OP_DATA                                                  'w'
  102    31        ADD                                              ~25     !2, 8
         32        ASSIGN_DIM                                               !0, ~25
         33        OP_DATA                                                  'o'
  103    34        ADD                                              ~27     !2, 9
         35        ASSIGN_DIM                                               !0, ~27
         36        OP_DATA                                                  'r'
  104    37        ADD                                              ~29     !2, 10
         38        ASSIGN_DIM                                               !0, ~29
         39        OP_DATA                                                  'l'
  105    40        ADD                                              ~31     !2, 11
         41        ASSIGN_DIM                                               !0, ~31
         42        OP_DATA                                                  'd'
  106    43        ADD                                              ~33     !2, 12
         44        ASSIGN_DIM                                               !0, ~33
         45        OP_DATA                                                  '%21'
  107    46        ADD                                              ~35     !2, 13
         47        ASSIGN_DIM                                               !0, ~35
         48        OP_DATA                                                  '%00'
  110    49        INIT_NS_FCALL_BY_NAME                                    'Demo%5Coutput_string'
         50        SEND_VAR_EX                                              !2
         51        DO_FCALL                                      0          
  112    52        INIT_NS_FCALL_BY_NAME                                    'Demo%5Cmalloc'
         53        SEND_VAL_EX                                              1
         54        DO_FCALL                                      0  $38     
         55        ASSIGN                                                   !3, $38
  113    56        ASSIGN_DIM                                               !0, !3
         57        OP_DATA                                                  '%23'
  116    58        INIT_NS_FCALL_BY_NAME                                    'Demo%5Coutput'
         59        SEND_VAR_EX                                              !3
         60        SEND_VAL_EX                                              1
         61        DO_FCALL                                      0          
  119    62        INIT_NS_FCALL_BY_NAME                                    'Demo%5Coutput_string'
         63        SEND_VAR_EX                                              !3
         64        DO_FCALL                                      0          
  122    65        INIT_NS_FCALL_BY_NAME                                    'Demo%5Cfree'
         66        SEND_VAR_EX                                              !2
         67        DO_FCALL                                      0          
  124    68        INIT_NS_FCALL_BY_NAME                                    'Demo%5Cmalloc'
         69        SEND_VAL_EX                                              9
         70        DO_FCALL                                      0  $44     
         71        ASSIGN                                                   !4, $44
  126    72        ADD                                              ~46     !4, 0
         73        ASSIGN_DIM                                               !0, ~46
         74        OP_DATA                                                  'H'
  127    75        ADD                                              ~48     !4, 1
         76        ASSIGN_DIM                                               !0, ~48
         77        OP_DATA                                                  'i'
  128    78        ADD                                              ~50     !4, 2
         79        ASSIGN_DIM                                               !0, ~50
         80        OP_DATA                                                  '+'
  129    81        ADD                                              ~52     !4, 3
         82        ASSIGN_DIM                                               !0, ~52
         83        OP_DATA                                                  't'
  130    84        ADD                                              ~54     !4, 4
         85        ASSIGN_DIM                                               !0, ~54
         86        OP_DATA                                                  'h'
  131    87        ADD                                              ~56     !4, 5
         88        ASSIGN_DIM                                               !0, ~56
         89        OP_DATA                                                  'e'
  132    90        ADD                                              ~58     !4, 6
         91        ASSIGN_DIM                                               !0, ~58
         92        OP_DATA                                                  'r'
  133    93        ADD                                              ~60     !4, 7
         94        ASSIGN_DIM                                               !0, ~60
         95        OP_DATA                                                  'e'
  136    96        INIT_NS_FCALL_BY_NAME                                    'Demo%5Coutput_string'
         97        SEND_VAR_EX                                              !4
         98        DO_FCALL                                      0          
         99      > RETURN                                                   1

Function demo%5Cmalloc:
Finding entry points
Branch analysis from position: 0
2 jumps found. (Code = 77) Position 1 = 4, Position 2 = 16
Branch analysis from position: 4
2 jumps found. (Code = 78) Position 1 = 5, Position 2 = 16
Branch analysis from position: 5
2 jumps found. (Code = 43) Position 1 = 9, Position 2 = 13
Branch analysis from position: 9
1 jumps found. (Code = 62) Position 1 = -2
Branch analysis from position: 13
1 jumps found. (Code = 42) Position 1 = 4
Branch analysis from position: 4
Branch analysis from position: 16
2 jumps found. (Code = 43) Position 1 = 21, Position 2 = 24
Branch analysis from position: 21
1 jumps found. (Code = 62) Position 1 = -2
Branch analysis from position: 24
1 jumps found. (Code = 108) Position 1 = -2
Branch analysis from position: 16
filename:       /in/871f4
function name:  Demo\malloc
number of ops:  28
compiled vars:  !0 = $size, !1 = $blocks, !2 = $newPtr, !3 = $ptr
line      #* E I O op                           fetch          ext  return  operands
-------------------------------------------------------------------------------------
   15     0  E >   RECV                                             !0      
   17     1        BIND_GLOBAL                                              !1, 'blocks'
   19     2        ASSIGN                                                   !2, 0
   21     3      > FE_RESET_R                                       $5      !1, ->16
          4    > > FE_FETCH_R                                       ~6      $5, !0, ->16
          5    >   ASSIGN                                                   !3, ~6
   24     6        ADD                                              ~8      !2, !0
          7        IS_SMALLER_OR_EQUAL                                      ~8, !3
          8      > JMPZ                                                     ~9, ->13
   25     9    >   ASSIGN_DIM                                               !1, !2
         10        OP_DATA                                                  !0
   26    11        FE_FREE                                                  $5
         12      > RETURN                                                   !2
   29    13    >   ADD                                              ~11     !3, !0
         14        ASSIGN                                                   !2, ~11
   21    15      > JMP                                                      ->4
         16    >   FE_FREE                                                  $5
   34    17        ADD                                              ~13     !2, !0
         18        FETCH_CONSTANT                                   ~14     'Demo%5CHEAP_SIZE'
         19        IS_SMALLER_OR_EQUAL                                      ~13, ~14
         20      > JMPZ                                                     ~15, ->24
   35    21    >   ASSIGN_DIM                                               !1, !2
         22        OP_DATA                                                  !0
   36    23      > RETURN                                                   !2
   40    24    >   NEW                                              $17     'Demo%5COutOfMemory'
         25        DO_FCALL                                      0          
         26      > THROW                                         0          $17
   41    27*     > RETURN                                                   null

End of function demo%5Cmalloc

Function demo%5Cfree:
Finding entry points
Branch analysis from position: 0
2 jumps found. (Code = 43) Position 1 = 5, Position 2 = 8
Branch analysis from position: 5
1 jumps found. (Code = 108) Position 1 = -2
Branch analysis from position: 8
1 jumps found. (Code = 62) Position 1 = -2
filename:       /in/871f4
function name:  Demo\free
number of ops:  10
compiled vars:  !0 = $ptr, !1 = $blocks
line      #* E I O op                           fetch          ext  return  operands
-------------------------------------------------------------------------------------
   43     0  E >   RECV                                             !0      
   45     1        BIND_GLOBAL                                              !1, 'blocks'
   48     2        ISSET_ISEMPTY_DIM_OBJ                         0  ~2      !1, !0
          3        BOOL_NOT                                         ~3      ~2
          4      > JMPZ                                                     ~3, ->8
   49     5    >   NEW                                              $4      'Demo%5CInvalidFree'
          6        DO_FCALL                                      0          
          7      > THROW                                         0          $4
   52     8    >   UNSET_DIM                                                !1, !0
   53     9      > RETURN                                                   null

End of function demo%5Cfree

Function demo%5Cstrcpy:
Finding entry points
Branch analysis from position: 0
1 jumps found. (Code = 42) Position 1 = 11
Branch analysis from position: 11
2 jumps found. (Code = 44) Position 1 = 15, Position 2 = 5
Branch analysis from position: 15
1 jumps found. (Code = 62) Position 1 = -2
Branch analysis from position: 5
2 jumps found. (Code = 44) Position 1 = 15, Position 2 = 5
Branch analysis from position: 15
Branch analysis from position: 5
filename:       /in/871f4
function name:  Demo\strcpy
number of ops:  16
compiled vars:  !0 = $dstPtr, !1 = $srcPtr, !2 = $heap, !3 = $i
line      #* E I O op                           fetch          ext  return  operands
-------------------------------------------------------------------------------------
   56     0  E >   RECV                                             !0      
          1        RECV                                             !1      
   58     2        BIND_GLOBAL                                              !2, 'heap'
   60     3        ASSIGN                                                   !3, 0
          4      > JMP                                                      ->11
   61     5    >   ADD                                              ~5      !0, 0
          6        ADD                                              ~7      !1, !3
          7        FETCH_DIM_R                                      ~8      !2, ~7
          8        ASSIGN_DIM                                               !2, ~5
          9        OP_DATA                                                  ~8
   60    10        PRE_INC                                                  !3
         11    >   ADD                                              ~10     !1, !3
         12        FETCH_DIM_R                                      ~11     !2, ~10
         13        IS_NOT_IDENTICAL                                         ~11, '%00'
         14      > JMPNZ                                                    ~12, ->5
   63    15    > > RETURN                                                   null

End of function demo%5Cstrcpy

Function demo%5Coutput:
Finding entry points
Branch analysis from position: 0
1 jumps found. (Code = 42) Position 1 = 9
Branch analysis from position: 9
2 jumps found. (Code = 46) Position 1 = 13, Position 2 = 15
Branch analysis from position: 13
2 jumps found. (Code = 44) Position 1 = 16, Position 2 = 5
Branch analysis from position: 16
1 jumps found. (Code = 62) Position 1 = -2
Branch analysis from position: 5
2 jumps found. (Code = 46) Position 1 = 13, Position 2 = 15
Branch analysis from position: 13
Branch analysis from position: 15
Branch analysis from position: 15
filename:       /in/871f4
function name:  Demo\output
number of ops:  18
compiled vars:  !0 = $ptr, !1 = $len, !2 = $heap, !3 = $i
line      #* E I O op                           fetch          ext  return  operands
-------------------------------------------------------------------------------------
   67     0  E >   RECV                                             !0      
          1        RECV                                             !1      
   69     2        BIND_GLOBAL                                              !2, 'heap'
   71     3        ASSIGN                                                   !3, 0
          4      > JMP                                                      ->9
   72     5    >   ADD                                              ~5      !0, !3
          6        FETCH_DIM_R                                      ~6      !2, ~5
          7        ECHO                                                     ~6
   71     8        PRE_INC                                                  !3
          9    >   ADD                                              ~8      !0, !3
         10        FETCH_CONSTANT                                   ~9      'Demo%5CHEAP_SIZE'
         11        IS_SMALLER                                       ~10     ~8, ~9
         12      > JMPZ_EX                                          ~10     ~10, ->15
         13    >   IS_SMALLER                                       ~11     !3, !1
         14        BOOL                                             ~10     ~11
         15    > > JMPNZ                                                    ~10, ->5
   76    16    >   ECHO                                                     '%0A%0A'
   77    17      > RETURN                                                   null

End of function demo%5Coutput

Function demo%5Coutput_string:
Finding entry points
Branch analysis from position: 0
1 jumps found. (Code = 42) Position 1 = 8
Branch analysis from position: 8
2 jumps found. (Code = 46) Position 1 = 12, Position 2 = 16
Branch analysis from position: 12
2 jumps found. (Code = 44) Position 1 = 17, Position 2 = 4
Branch analysis from position: 17
1 jumps found. (Code = 62) Position 1 = -2
Branch analysis from position: 4
2 jumps found. (Code = 46) Position 1 = 12, Position 2 = 16
Branch analysis from position: 12
Branch analysis from position: 16
Branch analysis from position: 16
filename:       /in/871f4
function name:  Demo\output_string
number of ops:  19
compiled vars:  !0 = $ptr, !1 = $heap, !2 = $i
line      #* E I O op                           fetch          ext  return  operands
-------------------------------------------------------------------------------------
   81     0  E >   RECV                                             !0      
   83     1        BIND_GLOBAL                                              !1, 'heap'
   85     2        ASSIGN                                                   !2, 0
          3      > JMP                                                      ->8
   86     4    >   ADD                                              ~4      !0, !2
          5        FETCH_DIM_R                                      ~5      !1, ~4
          6        ECHO                                                     ~5
   85     7        PRE_INC                                                  !2
          8    >   ADD                                              ~7      !0, !2
          9        FETCH_CONSTANT                                   ~8      'Demo%5CHEAP_SIZE'
         10        IS_SMALLER                                       ~9      ~7, ~8
         11      > JMPZ_EX                                          ~9      ~9, ->16
         12    >   ADD                                              ~10     !0, !2
         13        FETCH_DIM_R                                      ~11     !1, ~10
         14        IS_NOT_IDENTICAL                                 ~12     ~11, '%00'
         15        BOOL                                             ~9      ~12
         16    > > JMPNZ                                                    ~9, ->4
   90    17    >   ECHO                                                     '%0A%0A'
   91    18      > RETURN                                                   null

End of function demo%5Coutput_string

Class Demo\OutOfMemory: [no user functions]
Class Demo\InvalidFree: [no user functions]

Generated using Vulcan Logic Dumper, using php 8.0.0


preferences:
142.07 ms | 1019 KiB | 21 Q