gan_parser_html.php
protected function parse_hierarchy($self_close = null) {
		if ($self_close === null) {
			$this->status['self_close'] = ($self_close = isset($this->tags_selfclose[strtolower($this->status['tag_name'])]));
		}

		if ($self_close) {
			if ($this->status['closing_tag']) {

				//$c = end($this->hierarchy)->children
				$c = $this->hierarchy[count($this->hierarchy) - 1]->children;
				$found = false;
				for ($count = count($c), $i = $count - 1; $i >= 0; $i--) {
					if (strcasecmp($c[$i]->tag, $this->status['tag_name']) === 0) {
						for($ii = $i + 1; $ii < $count; $ii++) {
							$index = null; //Needs to be passed by ref
							$c[$i + 1]->changeParent($c[$i], $index);
						}
						$c[$i]->self_close = false;

						$found = true;
						break;
					}
				}

				if (!$found) {
					$this->addError('Closing tag "'.$this->status['tag_name'].'" which is not open');
				}

			} elseif ($this->status['tag_name'][0] === '?') {
				//end($this->hierarchy)->addXML($this->status['tag_name'], '', $this->status['attributes']);
				$index = null; //Needs to be passed by ref
				$this->hierarchy[count($this->hierarchy) - 1]->addXML($this->status['tag_name'], '', $this->status['attributes'], $index);
			} elseif ($this->status['tag_name'][0] === '%') {
				//end($this->hierarchy)->addASP($this->status['tag_name'], '', $this->status['attributes']);
				$index = null; //Needs to be passed by ref
				$this->hierarchy[count($this->hierarchy) - 1]->addASP($this->status['tag_name'], '', $this->status['attributes'], $index);
			} else {
				//end($this->hierarchy)->addChild($this->status);
				$index = null; //Needs to be passed by ref
				$this->hierarchy[count($this->hierarchy) - 1]->addChild($this->status, $index);
			}
		} elseif ($this->status['closing_tag']) {
			$found = false;
			for ($count = count($this->hierarchy), $i = $count - 1; $i >= 0; $i--) {
				if (strcasecmp($this->hierarchy[$i]->tag, $this->status['tag_name']) === 0) {

					for($ii = ($count - $i - 1); $ii >= 0; $ii--) {
						$e = array_pop($this->hierarchy);
						if ($ii > 0) {
							$this->addError('Closing tag "'.$this->status['tag_name'].'" while "'.$e->tag.'" is not closed yet');
						}
					}

					$found = true;
					break;
				}
			}

			if (!$found) {
				$this->addError('Closing tag "'.$this->status['tag_name'].'" which is not open');
			}

		} else {
			//$this->hierarchy[] = end($this->hierarchy)->addChild($this->status);
			$index = null; //Needs to be passed by ref
			$this->hierarchy[] = $this->hierarchy[count($this->hierarchy) - 1]->addChild($this->status, $index);
		}
	}
protected function parse_hierarchy($self_close = null) {
		if ($self_close === null) {
			$this->status['self_close'] = ($self_close = isset($this->tags_selfclose[strtolower($this->status['tag_name'])]));
		}

		if ($self_close) {
			if ($this->status['closing_tag']) {

				//$c = end($this->hierarchy)->children
				$c = $this->hierarchy[count($this->hierarchy) - 1]->children;
				$found = false;
				for ($count = count($c), $i = $count - 1; $i >= 0; $i--) {
					if (strcasecmp($c[$i]->tag, $this->status['tag_name']) === 0) {
						for($ii = $i + 1; $ii < $count; $ii++) {
							$index = null; //Needs to be passed by ref
							$c[$i + 1]->changeParent($c[$i], $index);
						}
						$c[$i]->self_close = false;

						$found = true;
						break;
					}
				}

				if (!$found) {
					$this->addError('Closing tag "'.$this->status['tag_name'].'" which is not open');
				}

			} elseif ($this->status['tag_name'][0] === '?') {
				//end($this->hierarchy)->addXML($this->status['tag_name'], '', $this->status['attributes']);
				$index = null; //Needs to be passed by ref
				$this->hierarchy[count($this->hierarchy) - 1]->addXML($this->status['tag_name'], '', $this->status['attributes'], $index);
			} elseif ($this->status['tag_name'][0] === '%') {
				//end($this->hierarchy)->addASP($this->status['tag_name'], '', $this->status['attributes']);
				$index = null; //Needs to be passed by ref
				$this->hierarchy[count($this->hierarchy) - 1]->addASP($this->status['tag_name'], '', $this->status['attributes'], $index);
			} else {
				//end($this->hierarchy)->addChild($this->status);
				$index = null; //Needs to be passed by ref
				$this->hierarchy[count($this->hierarchy) - 1]->addChild($this->status, $index);
			}
		} elseif ($this->status['closing_tag']) {
			$found = false;
			for ($count = count($this->hierarchy), $i = $count - 1; $i >= 0; $i--) {
				if (strcasecmp($this->hierarchy[$i]->tag, $this->status['tag_name']) === 0) {

					for($ii = ($count - $i - 1); $ii >= 0; $ii--) {
						$e = array_pop($this->hierarchy);
						if ($ii > 0) {
							$this->addError('Closing tag "'.$this->status['tag_name'].'" while "'.$e->tag.'" is not closed yet');
						}
					}

					$found = true;
					break;
				}
			}

			if (!$found) {
				$this->addError('Closing tag "'.$this->status['tag_name'].'" which is not open');
			}

		} else {
			//$this->hierarchy[] = end($this->hierarchy)->addChild($this->status);
			$index = null; //Needs to be passed by ref
			$this->hierarchy[] = $this->hierarchy[count($this->hierarchy) - 1]->addChild($this->status, $index);
		}
	}
Updates the current hierarchy status and checks for
correct opening/closing of tags
@param bool $self_close Is current tag self closing? Null to use {@link tags_selfclose}
@internal This is were most of the nodes get added
@access private