Skip to main content
Drupal API
User account menu
  • Log in

Breadcrumb

  1. Drupal Core 11.1.x
  2. Tokenizer.php

function Tokenizer::createLevelMap

Constructs the level map.

The level map adds a 'level' index to each token which indicates the depth that a token within a set of scope blocks. It also adds a 'conditions' index which is an array of the scope conditions that opened each of the scopes - position 0 being the first scope opener.

Return value

void

1 call to Tokenizer::createLevelMap()
Tokenizer::__construct in vendor/squizlabs/php_codesniffer/src/Tokenizers/Tokenizer.php
Initialise and run the tokenizer.

File

vendor/squizlabs/php_codesniffer/src/Tokenizers/Tokenizer.php, line 1504

Class

Tokenizer

Namespace

PHP_CodeSniffer\Tokenizers

Code

private function createLevelMap() {
    if (PHP_CODESNIFFER_VERBOSITY > 1) {
        echo "\t*** START LEVEL MAP ***" . PHP_EOL;
    }
    $this->numTokens = count($this->tokens);
    $level = 0;
    $conditions = [];
    $lastOpener = null;
    $openers = [];
    for ($i = 0; $i < $this->numTokens; $i++) {
        if (PHP_CODESNIFFER_VERBOSITY > 1) {
            $type = $this->tokens[$i]['type'];
            $line = $this->tokens[$i]['line'];
            $len = $this->tokens[$i]['length'];
            $col = $this->tokens[$i]['column'];
            $content = Common::prepareForOutput($this->tokens[$i]['content']);
            echo str_repeat("\t", $level + 1);
            echo "Process token {$i} on line {$line} [col:{$col};len:{$len};lvl:{$level};";
            if (empty($conditions) !== true) {
                $conditionString = 'conds;';
                foreach ($conditions as $condition) {
                    $conditionString .= Tokens::tokenName($condition) . ',';
                }
                echo rtrim($conditionString, ',') . ';';
            }
            echo "]: {$type} => {$content}" . PHP_EOL;
        }
        
        //end if
        $this->tokens[$i]['level'] = $level;
        $this->tokens[$i]['conditions'] = $conditions;
        if (isset($this->tokens[$i]['scope_condition']) === true) {
            // Check to see if this token opened the scope.
            if ($this->tokens[$i]['scope_opener'] === $i) {
                $stackPtr = $this->tokens[$i]['scope_condition'];
                if (PHP_CODESNIFFER_VERBOSITY > 1) {
                    $type = $this->tokens[$stackPtr]['type'];
                    echo str_repeat("\t", $level + 1);
                    echo "=> Found scope opener for {$stackPtr}:{$type}" . PHP_EOL;
                }
                $stackPtr = $this->tokens[$i]['scope_condition'];
                // If we find a scope opener that has a shared closer,
                // then we need to go back over the condition map that we
                // just created and fix ourselves as we just added some
                // conditions where there was none. This happens for T_CASE
                // statements that are using the same break statement.
                if ($lastOpener !== null && $this->tokens[$lastOpener]['scope_closer'] === $this->tokens[$i]['scope_closer']) {
                    // This opener shares its closer with the previous opener,
                    // but we still need to check if the two openers share their
                    // closer with each other directly (like CASE and DEFAULT)
                    // or if they are just sharing because one doesn't have a
                    // closer (like CASE with no BREAK using a SWITCHes closer).
                    $thisType = $this->tokens[$this->tokens[$i]['scope_condition']]['code'];
                    $opener = $this->tokens[$lastOpener]['scope_condition'];
                    $isShared = isset($this->scopeOpeners[$thisType]['with'][$this->tokens[$opener]['code']]);
                    reset($this->scopeOpeners[$thisType]['end']);
                    reset($this->scopeOpeners[$this->tokens[$opener]['code']]['end']);
                    $sameEnd = current($this->scopeOpeners[$thisType]['end']) === current($this->scopeOpeners[$this->tokens[$opener]['code']]['end']);
                    if ($isShared === true && $sameEnd === true) {
                        $badToken = $opener;
                        if (PHP_CODESNIFFER_VERBOSITY > 1) {
                            $type = $this->tokens[$badToken]['type'];
                            echo str_repeat("\t", $level + 1);
                            echo "* shared closer, cleaning up {$badToken}:{$type} *" . PHP_EOL;
                        }
                        for ($x = $this->tokens[$i]['scope_condition']; $x <= $i; $x++) {
                            $oldConditions = $this->tokens[$x]['conditions'];
                            $oldLevel = $this->tokens[$x]['level'];
                            $this->tokens[$x]['level']--;
                            unset($this->tokens[$x]['conditions'][$badToken]);
                            if (PHP_CODESNIFFER_VERBOSITY > 1) {
                                $type = $this->tokens[$x]['type'];
                                $oldConds = '';
                                foreach ($oldConditions as $condition) {
                                    $oldConds .= Tokens::tokenName($condition) . ',';
                                }
                                $oldConds = rtrim($oldConds, ',');
                                $newConds = '';
                                foreach ($this->tokens[$x]['conditions'] as $condition) {
                                    $newConds .= Tokens::tokenName($condition) . ',';
                                }
                                $newConds = rtrim($newConds, ',');
                                $newLevel = $this->tokens[$x]['level'];
                                echo str_repeat("\t", $level + 1);
                                echo "* cleaned {$x}:{$type} *" . PHP_EOL;
                                echo str_repeat("\t", $level + 2);
                                echo "=> level changed from {$oldLevel} to {$newLevel}" . PHP_EOL;
                                echo str_repeat("\t", $level + 2);
                                echo "=> conditions changed from {$oldConds} to {$newConds}" . PHP_EOL;
                            }
                            
                            //end if
                        }
                        
                        //end for
                        unset($conditions[$badToken]);
                        if (PHP_CODESNIFFER_VERBOSITY > 1) {
                            $type = $this->tokens[$badToken]['type'];
                            echo str_repeat("\t", $level + 1);
                            echo "* token {$badToken}:{$type} removed from conditions array *" . PHP_EOL;
                        }
                        unset($openers[$lastOpener]);
                        $level--;
                        if (PHP_CODESNIFFER_VERBOSITY > 1) {
                            echo str_repeat("\t", $level + 2);
                            echo '* level decreased *' . PHP_EOL;
                        }
                    }
                    
                    //end if
                }
                
                //end if
                $level++;
                if (PHP_CODESNIFFER_VERBOSITY > 1) {
                    echo str_repeat("\t", $level + 1);
                    echo '* level increased *' . PHP_EOL;
                }
                $conditions[$stackPtr] = $this->tokens[$stackPtr]['code'];
                if (PHP_CODESNIFFER_VERBOSITY > 1) {
                    $type = $this->tokens[$stackPtr]['type'];
                    echo str_repeat("\t", $level + 1);
                    echo "* token {$stackPtr}:{$type} added to conditions array *" . PHP_EOL;
                }
                $lastOpener = $this->tokens[$i]['scope_opener'];
                if ($lastOpener !== null) {
                    $openers[$lastOpener] = $lastOpener;
                }
            }
            else {
                if ($lastOpener !== null && $this->tokens[$lastOpener]['scope_closer'] === $i) {
                    foreach (array_reverse($openers) as $opener) {
                        if ($this->tokens[$opener]['scope_closer'] === $i) {
                            $oldOpener = array_pop($openers);
                            if (empty($openers) === false) {
                                $lastOpener = array_pop($openers);
                                $openers[$lastOpener] = $lastOpener;
                            }
                            else {
                                $lastOpener = null;
                            }
                            if (PHP_CODESNIFFER_VERBOSITY > 1) {
                                $type = $this->tokens[$oldOpener]['type'];
                                echo str_repeat("\t", $level + 1);
                                echo "=> Found scope closer for {$oldOpener}:{$type}" . PHP_EOL;
                            }
                            $oldCondition = array_pop($conditions);
                            if (PHP_CODESNIFFER_VERBOSITY > 1) {
                                echo str_repeat("\t", $level + 1);
                                echo '* token ' . Tokens::tokenName($oldCondition) . ' removed from conditions array *' . PHP_EOL;
                            }
                            // Make sure this closer actually belongs to us.
                            // Either the condition also has to think this is the
                            // closer, or it has to allow sharing with us.
                            $condition = $this->tokens[$this->tokens[$i]['scope_condition']]['code'];
                            if ($condition !== $oldCondition) {
                                if (isset($this->scopeOpeners[$oldCondition]['with'][$condition]) === false) {
                                    $badToken = $this->tokens[$oldOpener]['scope_condition'];
                                    if (PHP_CODESNIFFER_VERBOSITY > 1) {
                                        $type = Tokens::tokenName($oldCondition);
                                        echo str_repeat("\t", $level + 1);
                                        echo "* scope closer was bad, cleaning up {$badToken}:{$type} *" . PHP_EOL;
                                    }
                                    for ($x = $oldOpener + 1; $x <= $i; $x++) {
                                        $oldConditions = $this->tokens[$x]['conditions'];
                                        $oldLevel = $this->tokens[$x]['level'];
                                        $this->tokens[$x]['level']--;
                                        unset($this->tokens[$x]['conditions'][$badToken]);
                                        if (PHP_CODESNIFFER_VERBOSITY > 1) {
                                            $type = $this->tokens[$x]['type'];
                                            $oldConds = '';
                                            foreach ($oldConditions as $condition) {
                                                $oldConds .= Tokens::tokenName($condition) . ',';
                                            }
                                            $oldConds = rtrim($oldConds, ',');
                                            $newConds = '';
                                            foreach ($this->tokens[$x]['conditions'] as $condition) {
                                                $newConds .= Tokens::tokenName($condition) . ',';
                                            }
                                            $newConds = rtrim($newConds, ',');
                                            $newLevel = $this->tokens[$x]['level'];
                                            echo str_repeat("\t", $level + 1);
                                            echo "* cleaned {$x}:{$type} *" . PHP_EOL;
                                            echo str_repeat("\t", $level + 2);
                                            echo "=> level changed from {$oldLevel} to {$newLevel}" . PHP_EOL;
                                            echo str_repeat("\t", $level + 2);
                                            echo "=> conditions changed from {$oldConds} to {$newConds}" . PHP_EOL;
                                        }
                                        
                                        //end if
                                    }
                                    
                                    //end for
                                }
                                
                                //end if
                            }
                            
                            //end if
                            $level--;
                            if (PHP_CODESNIFFER_VERBOSITY > 1) {
                                echo str_repeat("\t", $level + 2);
                                echo '* level decreased *' . PHP_EOL;
                            }
                            $this->tokens[$i]['level'] = $level;
                            $this->tokens[$i]['conditions'] = $conditions;
                        }
                        
                        //end if
                    }
                    
                    //end foreach
                }
            }
            
            //end if
        }
        
        //end if
    }
    
    //end for
    if (PHP_CODESNIFFER_VERBOSITY > 1) {
        echo "\t*** END LEVEL MAP ***" . PHP_EOL;
    }
}
RSS feed
Powered by Drupal