home *** CD-ROM | disk | FTP | other *** search
/ Cricao de Sites - 650 Layouts Prontos / WebMasters.iso / Servidores / xampp-win32-1.6.7-installer.exe / php / tmp / PEAR-1.7.1 / PEAR / Dependency2.php < prev    next >
Encoding:
PHP Script  |  2008-02-15  |  52.2 KB  |  1,299 lines

  1. <?php
  2. /**
  3.  * PEAR_Dependency2, advanced dependency validation
  4.  *
  5.  * PHP versions 4 and 5
  6.  *
  7.  * LICENSE: This source file is subject to version 3.0 of the PHP license
  8.  * that is available through the world-wide-web at the following URI:
  9.  * http://www.php.net/license/3_0.txt.  If you did not receive a copy of
  10.  * the PHP License and are unable to obtain it through the web, please
  11.  * send a note to license@php.net so we can mail you a copy immediately.
  12.  *
  13.  * @category   pear
  14.  * @package    PEAR
  15.  * @author     Greg Beaver <cellog@php.net>
  16.  * @copyright  1997-2008 The PHP Group
  17.  * @license    http://www.php.net/license/3_0.txt  PHP License 3.0
  18.  * @version    CVS: $Id: Dependency2.php,v 1.56 2008/01/03 20:26:35 cellog Exp $
  19.  * @link       http://pear.php.net/package/PEAR
  20.  * @since      File available since Release 1.4.0a1
  21.  */
  22.  
  23. /**
  24.  * Required for the PEAR_VALIDATE_* constants
  25.  */
  26. require_once 'PEAR/Validate.php';
  27.  
  28. /**
  29.  * Dependency check for PEAR packages
  30.  *
  31.  * This class handles both version 1.0 and 2.0 dependencies
  32.  * WARNING: *any* changes to this class must be duplicated in the
  33.  * test_PEAR_Dependency2 class found in tests/PEAR_Dependency2/setup.php.inc,
  34.  * or unit tests will not actually validate the changes
  35.  * @category   pear
  36.  * @package    PEAR
  37.  * @author     Greg Beaver <cellog@php.net>
  38.  * @copyright  1997-2008 The PHP Group
  39.  * @license    http://www.php.net/license/3_0.txt  PHP License 3.0
  40.  * @version    Release: 1.7.1
  41.  * @link       http://pear.php.net/package/PEAR
  42.  * @since      Class available since Release 1.4.0a1
  43.  */
  44. class PEAR_Dependency2
  45. {
  46.     /**
  47.      * One of the PEAR_VALIDATE_* states
  48.      * @see PEAR_VALIDATE_NORMAL
  49.      * @var integer
  50.      */
  51.     var $_state;
  52.     /**
  53.      * Command-line options to install/upgrade/uninstall commands
  54.      * @param array
  55.      */
  56.     var $_options;
  57.     /**
  58.      * @var OS_Guess
  59.      */
  60.     var $_os;
  61.     /**
  62.      * @var PEAR_Registry
  63.      */
  64.     var $_registry;
  65.     /**
  66.      * @var PEAR_Config
  67.      */
  68.     var $_config;
  69.     /**
  70.      * @var PEAR_DependencyDB
  71.      */
  72.     var $_dependencydb;
  73.     /**
  74.      * Output of PEAR_Registry::parsedPackageName()
  75.      * @var array
  76.      */
  77.     var $_currentPackage;
  78.     /**
  79.      * @param PEAR_Config
  80.      * @param array installation options
  81.      * @param array format of PEAR_Registry::parsedPackageName()
  82.      * @param int installation state (one of PEAR_VALIDATE_*)
  83.      */
  84.     function PEAR_Dependency2(&$config, $installoptions, $package,
  85.                               $state = PEAR_VALIDATE_INSTALLING)
  86.     {
  87.         $this->_config = &$config;
  88.         if (!class_exists('PEAR_DependencyDB')) {
  89.             require_once 'PEAR/DependencyDB.php';
  90.         }
  91.         if (isset($installoptions['packagingroot'])) {
  92.             // make sure depdb is in the right location
  93.             $config->setInstallRoot($installoptions['packagingroot']);
  94.         }
  95.         $this->_registry = &$config->getRegistry();
  96.         $this->_dependencydb = &PEAR_DependencyDB::singleton($config);
  97.         if (isset($installoptions['packagingroot'])) {
  98.             $config->setInstallRoot(false);
  99.         }
  100.         $this->_options = $installoptions;
  101.         $this->_state = $state;
  102.         if (!class_exists('OS_Guess')) {
  103.             require_once 'OS/Guess.php';
  104.         }
  105.         $this->_os = new OS_Guess;
  106.         $this->_currentPackage = $package;
  107.     }
  108.  
  109.     function _getExtraString($dep)
  110.     {
  111.         $extra = ' (';
  112.         if (isset($dep['uri'])) {
  113.             return '';
  114.         }
  115.         if (isset($dep['recommended'])) {
  116.             $extra .= 'recommended version ' . $dep['recommended'];
  117.         } else {
  118.             if (isset($dep['min'])) {
  119.                 $extra .= 'version >= ' . $dep['min'];
  120.             }
  121.             if (isset($dep['max'])) {
  122.                 if ($extra != ' (') {
  123.                     $extra .= ', ';
  124.                 }
  125.                 $extra .= 'version <= ' . $dep['max'];
  126.             }
  127.             if (isset($dep['exclude'])) {
  128.                 if (!is_array($dep['exclude'])) {
  129.                     $dep['exclude'] = array($dep['exclude']);
  130.                 }
  131.                 if ($extra != ' (') {
  132.                     $extra .= ', ';
  133.                 }
  134.                 $extra .= 'excluded versions: ';
  135.                 foreach ($dep['exclude'] as $i => $exclude) {
  136.                     if ($i) {
  137.                         $extra .= ', ';
  138.                     }
  139.                     $extra .= $exclude;
  140.                 }
  141.             }
  142.         }
  143.         $extra .= ')';
  144.         if ($extra == ' ()') {
  145.             $extra = '';
  146.         }
  147.         return $extra;
  148.     }
  149.  
  150.     /**
  151.      * This makes unit-testing a heck of a lot easier
  152.      */
  153.     function getPHP_OS()
  154.     {
  155.         return PHP_OS;
  156.     }
  157.  
  158.     /**
  159.      * This makes unit-testing a heck of a lot easier
  160.      */
  161.     function getsysname()
  162.     {
  163.         return $this->_os->getSysname();
  164.     }
  165.  
  166.     /**
  167.      * Specify a dependency on an OS.  Use arch for detailed os/processor information
  168.      *
  169.      * There are two generic OS dependencies that will be the most common, unix and windows.
  170.      * Other options are linux, freebsd, darwin (OS X), sunos, irix, hpux, aix
  171.      */
  172.     function validateOsDependency($dep)
  173.     {
  174.         if ($this->_state != PEAR_VALIDATE_INSTALLING &&
  175.               $this->_state != PEAR_VALIDATE_DOWNLOADING) {
  176.             return true;
  177.         }
  178.         if (isset($dep['conflicts'])) {
  179.             $not = true;
  180.         } else {
  181.             $not = false;
  182.         }
  183.         if ($dep['name'] == '*') {
  184.             return true;
  185.         }
  186.         switch (strtolower($dep['name'])) {
  187.             case 'windows' :
  188.                 if ($not) {
  189.                     if (strtolower(substr($this->getPHP_OS(), 0, 3)) == 'win') {
  190.                         if (!isset($this->_options['nodeps']) &&
  191.                               !isset($this->_options['force'])) {
  192.                             return $this->raiseError("Cannot install %s on Windows");
  193.                         } else {
  194.                             return $this->warning("warning: Cannot install %s on Windows");
  195.                         }
  196.                     }
  197.                 } else {
  198.                     if (strtolower(substr($this->getPHP_OS(), 0, 3)) != 'win') {
  199.                         if (!isset($this->_options['nodeps']) &&
  200.                               !isset($this->_options['force'])) {
  201.                             return $this->raiseError("Can only install %s on Windows");
  202.                         } else {
  203.                             return $this->warning("warning: Can only install %s on Windows");
  204.                         }
  205.                     }
  206.                 }
  207.             break;
  208.             case 'unix' :
  209.                 $unices = array('linux', 'freebsd', 'darwin', 'sunos', 'irix', 'hpux', 'aix');
  210.                 if ($not) {
  211.                     if (in_array($this->getSysname(), $unices)) {
  212.                         if (!isset($this->_options['nodeps']) &&
  213.                               !isset($this->_options['force'])) {
  214.                             return $this->raiseError("Cannot install %s on any Unix system");
  215.                         } else {
  216.                             return $this->warning(
  217.                                 "warning: Cannot install %s on any Unix system");
  218.                         }
  219.                     }
  220.                 } else {
  221.                     if (!in_array($this->getSysname(), $unices)) {
  222.                         if (!isset($this->_options['nodeps']) &&
  223.                               !isset($this->_options['force'])) {
  224.                             return $this->raiseError("Can only install %s on a Unix system");
  225.                         } else {
  226.                             return $this->warning(
  227.                                 "warning: Can only install %s on a Unix system");
  228.                         }
  229.                     }
  230.                 }
  231.             break;
  232.             default :
  233.                 if ($not) {
  234.                     if (strtolower($dep['name']) == strtolower($this->getSysname())) {
  235.                         if (!isset($this->_options['nodeps']) &&
  236.                               !isset($this->_options['force'])) {
  237.                             return $this->raiseError('Cannot install %s on ' . $dep['name'] .
  238.                                 ' operating system');
  239.                         } else {
  240.                             return $this->warning('warning: Cannot install %s on ' .
  241.                                 $dep['name'] . ' operating system');
  242.                         }
  243.                     }
  244.                 } else {
  245.                     if (strtolower($dep['name']) != strtolower($this->getSysname())) {
  246.                         if (!isset($this->_options['nodeps']) &&
  247.                               !isset($this->_options['force'])) {
  248.                             return $this->raiseError('Cannot install %s on ' .
  249.                                 $this->getSysname() .
  250.                                 ' operating system, can only install on ' . $dep['name']);
  251.                         } else {
  252.                             return $this->warning('warning: Cannot install %s on ' .
  253.                                 $this->getSysname() .
  254.                                 ' operating system, can only install on ' . $dep['name']);
  255.                         }
  256.                     }
  257.                 }
  258.         }
  259.         return true;
  260.     }
  261.  
  262.     /**
  263.      * This makes unit-testing a heck of a lot easier
  264.      */
  265.     function matchSignature($pattern)
  266.     {
  267.         return $this->_os->matchSignature($pattern);
  268.     }
  269.  
  270.     /**
  271.      * Specify a complex dependency on an OS/processor/kernel version,
  272.      * Use OS for simple operating system dependency.
  273.      *
  274.      * This is the only dependency that accepts an eregable pattern.  The pattern
  275.      * will be matched against the php_uname() output parsed by OS_Guess
  276.      */
  277.     function validateArchDependency($dep)
  278.     {
  279.         if ($this->_state != PEAR_VALIDATE_INSTALLING) {
  280.             return true;
  281.         }
  282.         if (isset($dep['conflicts'])) {
  283.             $not = true;
  284.         } else {
  285.             $not = false;
  286.         }
  287.         if (!$this->matchSignature($dep['pattern'])) {
  288.             if (!$not) {
  289.                 if (!isset($this->_options['nodeps']) && !isset($this->_options['force'])) {
  290.                     return $this->raiseError('%s Architecture dependency failed, does not ' .
  291.                         'match "' . $dep['pattern'] . '"');
  292.                 } else {
  293.                     return $this->warning('warning: %s Architecture dependency failed, does ' .
  294.                         'not match "' . $dep['pattern'] . '"');
  295.                 }
  296.             }
  297.             return true;
  298.         } else {
  299.             if ($not) {
  300.                 if (!isset($this->_options['nodeps']) && !isset($this->_options['force'])) {
  301.                     return $this->raiseError('%s Architecture dependency failed, required "' .
  302.                         $dep['pattern'] . '"');
  303.                 } else {
  304.                     return $this->warning('warning: %s Architecture dependency failed, ' .
  305.                         'required "' . $dep['pattern'] . '"');
  306.                 }
  307.             }
  308.             return true;
  309.         }
  310.     }
  311.  
  312.     /**
  313.      * This makes unit-testing a heck of a lot easier
  314.      */
  315.     function extension_loaded($name)
  316.     {
  317.         return extension_loaded($name);
  318.     }
  319.  
  320.     /**
  321.      * This makes unit-testing a heck of a lot easier
  322.      */
  323.     function phpversion($name = null)
  324.     {
  325.         if ($name !== null) {
  326.             return phpversion($name);
  327.         } else {
  328.             return phpversion();
  329.         }
  330.     }
  331.  
  332.     function validateExtensionDependency($dep, $required = true)
  333.     {
  334.         if ($this->_state != PEAR_VALIDATE_INSTALLING &&
  335.               $this->_state != PEAR_VALIDATE_DOWNLOADING) {
  336.             return true;
  337.         }
  338.         $loaded = $this->extension_loaded($dep['name']);
  339.         $extra = $this->_getExtraString($dep);
  340.         if (isset($dep['exclude'])) {
  341.             if (!is_array($dep['exclude'])) {
  342.                 $dep['exclude'] = array($dep['exclude']);
  343.             }
  344.         }
  345.         if (!isset($dep['min']) && !isset($dep['max']) &&
  346.               !isset($dep['recommended']) && !isset($dep['exclude'])) {
  347.             if ($loaded) {
  348.                 if (isset($dep['conflicts'])) {
  349.                     if (!isset($this->_options['nodeps']) && !isset($this->_options['force'])) {
  350.                         return $this->raiseError('%s conflicts with PHP extension "' .
  351.                             $dep['name'] . '"' . $extra);
  352.                     } else {
  353.                         return $this->warning('warning: %s conflicts with PHP extension "' .
  354.                             $dep['name'] . '"' . $extra);
  355.                     }
  356.                 }
  357.                 return true;
  358.             } else {
  359.                 if (isset($dep['conflicts'])) {
  360.                     return true;
  361.                 }
  362.                 if ($required) {
  363.                     if (!isset($this->_options['nodeps']) && !isset($this->_options['force'])) {
  364.                         return $this->raiseError('%s requires PHP extension "' .
  365.                             $dep['name'] . '"' . $extra);
  366.                     } else {
  367.                         return $this->warning('warning: %s requires PHP extension "' .
  368.                             $dep['name'] . '"' . $extra);
  369.                     }
  370.                 } else {
  371.                     return $this->warning('%s can optionally use PHP extension "' .
  372.                         $dep['name'] . '"' . $extra);
  373.                 }
  374.             }
  375.         }
  376.         if (!$loaded) {
  377.             if (isset($dep['conflicts'])) {
  378.                 return true;
  379.             }
  380.             if (!$required) {
  381.                 return $this->warning('%s can optionally use PHP extension "' .
  382.                     $dep['name'] . '"' . $extra);
  383.             } else {
  384.                 if (!isset($this->_options['nodeps']) && !isset($this->_options['force'])) {
  385.                     return $this->raiseError('%s requires PHP extension "' . $dep['name'] .
  386.                         '"' . $extra);
  387.                 }
  388.                     return $this->warning('warning: %s requires PHP extension "' . $dep['name'] .
  389.                         '"' . $extra);
  390.             }
  391.         }
  392.         $version = (string) $this->phpversion($dep['name']);
  393.         if (empty($version)) {
  394.             $version = '0';
  395.         }
  396.         $fail = false;
  397.         if (isset($dep['min'])) {
  398.             if (!version_compare($version, $dep['min'], '>=')) {
  399.                 $fail = true;
  400.             }
  401.         }
  402.         if (isset($dep['max'])) {
  403.             if (!version_compare($version, $dep['max'], '<=')) {
  404.                 $fail = true;
  405.             }
  406.         }
  407.         if ($fail && !isset($dep['conflicts'])) {
  408.             if (!isset($this->_options['nodeps']) && !isset($this->_options['force'])) {
  409.                 return $this->raiseError('%s requires PHP extension "' . $dep['name'] .
  410.                     '"' . $extra . ', installed version is ' . $version);
  411.             } else {
  412.                 return $this->warning('warning: %s requires PHP extension "' . $dep['name'] .
  413.                     '"' . $extra . ', installed version is ' . $version);
  414.             }
  415.         } elseif ((isset($dep['min']) || isset($dep['max'])) && !$fail && isset($dep['conflicts'])) {
  416.             if (!isset($this->_options['nodeps']) && !isset($this->_options['force'])) {
  417.                 return $this->raiseError('%s conflicts with PHP extension "' .
  418.                     $dep['name'] . '"' . $extra . ', installed version is ' . $version);
  419.             } else {
  420.                 return $this->warning('warning: %s conflicts with PHP extension "' .
  421.                     $dep['name'] . '"' . $extra . ', installed version is ' . $version);
  422.             }
  423.         }
  424.         if (isset($dep['exclude'])) {
  425.             foreach ($dep['exclude'] as $exclude) {
  426.                 if (version_compare($version, $exclude, '==')) {
  427.                     if (isset($dep['conflicts'])) {
  428.                         continue;
  429.                     }
  430.                     if (!isset($this->_options['nodeps']) &&
  431.                           !isset($this->_options['force'])) {
  432.                         return $this->raiseError('%s is not compatible with PHP extension "' .
  433.                             $dep['name'] . '" version ' .
  434.                             $exclude);
  435.                     } else {
  436.                         return $this->warning('warning: %s is not compatible with PHP extension "' .
  437.                             $dep['name'] . '" version ' .
  438.                             $exclude);
  439.                     }
  440.                 } elseif (version_compare($version, $exclude, '!=') && isset($dep['conflicts'])) {
  441.                     if (!isset($this->_options['nodeps']) && !isset($this->_options['force'])) {
  442.                         return $this->raiseError('%s conflicts with PHP extension "' .
  443.                             $dep['name'] . '"' . $extra . ', installed version is ' . $version);
  444.                     } else {
  445.                         return $this->warning('warning: %s conflicts with PHP extension "' .
  446.                             $dep['name'] . '"' . $extra . ', installed version is ' . $version);
  447.                     }
  448.                 }
  449.             }
  450.         }
  451.         if (isset($dep['recommended'])) {
  452.             if (version_compare($version, $dep['recommended'], '==')) {
  453.                 return true;
  454.             } else {
  455.                 if (!isset($this->_options['nodeps']) && !isset($this->_options['force'])) {
  456.                     return $this->raiseError('%s dependency: PHP extension ' . $dep['name'] .
  457.                         ' version "' . $version . '"' .
  458.                         ' is not the recommended version "' . $dep['recommended'] .
  459.                         '", but may be compatible, use --force to install');
  460.                 } else {
  461.                     return $this->warning('warning: %s dependency: PHP extension ' .
  462.                         $dep['name'] . ' version "' . $version . '"' .
  463.                         ' is not the recommended version "' . $dep['recommended'].'"');
  464.                 }
  465.             }
  466.         }
  467.         return true;
  468.     }
  469.  
  470.     function validatePhpDependency($dep)
  471.     {
  472.         if ($this->_state != PEAR_VALIDATE_INSTALLING &&
  473.               $this->_state != PEAR_VALIDATE_DOWNLOADING) {
  474.             return true;
  475.         }
  476.         $version = $this->phpversion();
  477.         $extra = $this->_getExtraString($dep);
  478.         if (isset($dep['exclude'])) {
  479.             if (!is_array($dep['exclude'])) {
  480.                 $dep['exclude'] = array($dep['exclude']);
  481.             }
  482.         }
  483.         if (isset($dep['min'])) {
  484.             if (!version_compare($version, $dep['min'], '>=')) {
  485.                 if (!isset($this->_options['nodeps']) && !isset($this->_options['force'])) {
  486.                     return $this->raiseError('%s requires PHP' .
  487.                         $extra . ', installed version is ' . $version);
  488.                 } else {
  489.                     return $this->warning('warning: %s requires PHP' .
  490.                         $extra . ', installed version is ' . $version);
  491.                 }
  492.             }
  493.         }
  494.         if (isset($dep['max'])) {
  495.             if (!version_compare($version, $dep['max'], '<=')) {
  496.                 if (!isset($this->_options['nodeps']) && !isset($this->_options['force'])) {
  497.                     return $this->raiseError('%s requires PHP' .
  498.                         $extra . ', installed version is ' . $version);
  499.                 } else {
  500.                     return $this->warning('warning: %s requires PHP' .
  501.                         $extra . ', installed version is ' . $version);
  502.                 }
  503.             }
  504.         }
  505.         if (isset($dep['exclude'])) {
  506.             foreach ($dep['exclude'] as $exclude) {
  507.                 if (version_compare($version, $exclude, '==')) {
  508.                     if (!isset($this->_options['nodeps']) &&
  509.                           !isset($this->_options['force'])) {
  510.                         return $this->raiseError('%s is not compatible with PHP version ' .
  511.                             $exclude);
  512.                     } else {
  513.                         return $this->warning(
  514.                             'warning: %s is not compatible with PHP version ' .
  515.                             $exclude);
  516.                     }
  517.                 }
  518.             }
  519.         }
  520.         return true;
  521.     }
  522.  
  523.     /**
  524.      * This makes unit-testing a heck of a lot easier
  525.      */
  526.     function getPEARVersion()
  527.     {
  528.         return '1.7.1';
  529.     }
  530.  
  531.     function validatePearinstallerDependency($dep)
  532.     {
  533.         $pearversion = $this->getPEARVersion();
  534.         $extra = $this->_getExtraString($dep);
  535.         if (isset($dep['exclude'])) {
  536.             if (!is_array($dep['exclude'])) {
  537.                 $dep['exclude'] = array($dep['exclude']);
  538.             }
  539.         }
  540.         if (version_compare($pearversion, $dep['min'], '<')) {
  541.             if (!isset($this->_options['nodeps']) && !isset($this->_options['force'])) {
  542.                 return $this->raiseError('%s requires PEAR Installer' . $extra .
  543.                     ', installed version is ' . $pearversion);
  544.             } else {
  545.                 return $this->warning('warning: %s requires PEAR Installer' . $extra .
  546.                     ', installed version is ' . $pearversion);
  547.             }
  548.         }
  549.         if (isset($dep['max'])) {
  550.             if (version_compare($pearversion, $dep['max'], '>')) {
  551.                 if (!isset($this->_options['nodeps']) && !isset($this->_options['force'])) {
  552.                     return $this->raiseError('%s requires PEAR Installer' . $extra .
  553.                         ', installed version is ' . $pearversion);
  554.                 } else {
  555.                     return $this->warning('warning: %s requires PEAR Installer' . $extra .
  556.                         ', installed version is ' . $pearversion);
  557.                 }
  558.             }
  559.         }
  560.         if (isset($dep['exclude'])) {
  561.             if (!isset($dep['exclude'][0])) {
  562.                 $dep['exclude'] = array($dep['exclude']);
  563.             }
  564.             foreach ($dep['exclude'] as $exclude) {
  565.                 if (version_compare($exclude, $pearversion, '==')) {
  566.                     if (!isset($this->_options['nodeps']) && !isset($this->_options['force'])) {
  567.                         return $this->raiseError('%s is not compatible with PEAR Installer ' .
  568.                             'version ' . $exclude);
  569.                     } else {
  570.                         return $this->warning('warning: %s is not compatible with PEAR ' .
  571.                             'Installer version ' . $exclude);
  572.                     }
  573.                 }
  574.             }
  575.         }
  576.         return true;
  577.     }
  578.  
  579.     function validateSubpackageDependency($dep, $required, $params)
  580.     {
  581.         return $this->validatePackageDependency($dep, $required, $params);
  582.     }
  583.  
  584.     /**
  585.      * @param array dependency information (2.0 format)
  586.      * @param boolean whether this is a required dependency
  587.      * @param array a list of downloaded packages to be installed, if any
  588.      * @param boolean if true, then deps on pear.php.net that fail will also check
  589.      *                against pecl.php.net packages to accomodate extensions that have
  590.      *                moved to pecl.php.net from pear.php.net
  591.      */
  592.     function validatePackageDependency($dep, $required, $params, $depv1 = false)
  593.     {
  594.         if ($this->_state != PEAR_VALIDATE_INSTALLING &&
  595.               $this->_state != PEAR_VALIDATE_DOWNLOADING) {
  596.             return true;
  597.         }
  598.         if (isset($dep['providesextension'])) {
  599.             if ($this->extension_loaded($dep['providesextension'])) {
  600.                 $save = $dep;
  601.                 $subdep = $dep;
  602.                 $subdep['name'] = $subdep['providesextension'];
  603.                 PEAR::pushErrorHandling(PEAR_ERROR_RETURN);
  604.                 $ret = $this->validateExtensionDependency($subdep, $required);
  605.                 PEAR::popErrorHandling();
  606.                 if (!PEAR::isError($ret)) {
  607.                     return true;
  608.                 }
  609.             }
  610.         }
  611.         if ($this->_state == PEAR_VALIDATE_INSTALLING) {
  612.             return $this->_validatePackageInstall($dep, $required, $depv1);
  613.         }
  614.         if ($this->_state == PEAR_VALIDATE_DOWNLOADING) {
  615.             return $this->_validatePackageDownload($dep, $required, $params, $depv1);
  616.         }
  617.     }
  618.  
  619.     function _validatePackageDownload($dep, $required, $params, $depv1 = false)
  620.     {
  621.         $dep['package'] = $dep['name'];
  622.         if (isset($dep['uri'])) {
  623.             $dep['channel'] = '__uri';
  624.         }
  625.         $depname = $this->_registry->parsedPackageNameToString($dep, true);
  626.         $found = false;
  627.         foreach ($params as $param) {
  628.             if ($param->isEqual(
  629.                   array('package' => $dep['name'],
  630.                         'channel' => $dep['channel']))) {
  631.                 $found = true;
  632.                 break;
  633.             }
  634.             if ($depv1 && $dep['channel'] == 'pear.php.net') {
  635.                 if ($param->isEqual(
  636.                   array('package' => $dep['name'],
  637.                         'channel' => 'pecl.php.net'))) {
  638.                     $found = true;
  639.                     break;
  640.                 }
  641.             }
  642.         }
  643.         if (!$found && isset($dep['providesextension'])) {
  644.             foreach ($params as $param) {
  645.                 if ($param->isExtension($dep['providesextension'])) {
  646.                     $found = true;
  647.                     break;
  648.                 }
  649.             }
  650.         }
  651.         if ($found) {
  652.             $version = $param->getVersion();
  653.             $installed = false;
  654.             $downloaded = true;
  655.         } else {
  656.             if ($this->_registry->packageExists($dep['name'], $dep['channel'])) {
  657.                 $installed = true;
  658.                 $downloaded = false;
  659.                 $version = $this->_registry->packageinfo($dep['name'], 'version',
  660.                     $dep['channel']);
  661.             } else {
  662.                 if ($dep['channel'] == 'pecl.php.net' && $this->_registry->packageExists($dep['name'],
  663.                       'pear.php.net')) {
  664.                     $installed = true;
  665.                     $downloaded = false;
  666.                     $version = $this->_registry->packageinfo($dep['name'], 'version',
  667.                         'pear.php.net');
  668.                 } else {
  669.                     $version = 'not installed or downloaded';
  670.                     $installed = false;
  671.                     $downloaded = false;
  672.                 }
  673.             }
  674.         }
  675.         $extra = $this->_getExtraString($dep);
  676.         if (isset($dep['exclude'])) {
  677.             if (!is_array($dep['exclude'])) {
  678.                 $dep['exclude'] = array($dep['exclude']);
  679.             }
  680.         }
  681.         if (!isset($dep['min']) && !isset($dep['max']) &&
  682.               !isset($dep['recommended']) && !isset($dep['exclude'])) {
  683.             if ($installed || $downloaded) {
  684.                 $installed = $installed ? 'installed' : 'downloaded';
  685.                 if (isset($dep['conflicts'])) {
  686.                     if ($version) {
  687.                         $rest = ", $installed version is " . $version;
  688.                     } else {
  689.                         $rest = '';
  690.                     }
  691.                     if (!isset($this->_options['nodeps']) && !isset($this->_options['force'])) {
  692.                         return $this->raiseError('%s conflicts with package "' . $depname . '"' .
  693.                             $extra . $rest);
  694.                     } else {
  695.                         return $this->warning('warning: %s conflicts with package "' . $depname . '"' .
  696.                             $extra . $rest);
  697.                     }
  698.                 }
  699.                 return true;
  700.             } else {
  701.                 if (isset($dep['conflicts'])) {
  702.                     return true;
  703.                 }
  704.                 if ($required) {
  705.                     if (!isset($this->_options['nodeps']) && !isset($this->_options['force'])) {
  706.                         return $this->raiseError('%s requires package "' . $depname . '"' .
  707.                             $extra);
  708.                     } else {
  709.                         return $this->warning('warning: %s requires package "' . $depname . '"' .
  710.                             $extra);
  711.                     }
  712.                 } else {
  713.                     return $this->warning('%s can optionally use package "' . $depname . '"' .
  714.                         $extra);
  715.                 }
  716.             }
  717.         }
  718.         if (!$installed && !$downloaded) {
  719.             if (isset($dep['conflicts'])) {
  720.                 return true;
  721.             }
  722.             if ($required) {
  723.                 if (!isset($this->_options['nodeps']) && !isset($this->_options['force'])) {
  724.                     return $this->raiseError('%s requires package "' . $depname . '"' .
  725.                         $extra);
  726.                 } else {
  727.                     return $this->warning('warning: %s requires package "' . $depname . '"' .
  728.                         $extra);
  729.                 }
  730.             } else {
  731.                 return $this->warning('%s can optionally use package "' . $depname . '"' .
  732.                     $extra);
  733.             }
  734.         }
  735.         $fail = false;
  736.         if (isset($dep['min'])) {
  737.             if (version_compare($version, $dep['min'], '<')) {
  738.                 $fail = true;
  739.             }
  740.         }
  741.         if (isset($dep['max'])) {
  742.             if (version_compare($version, $dep['max'], '>')) {
  743.                 $fail = true;
  744.             }
  745.         }
  746.         if ($fail && !isset($dep['conflicts'])) {
  747.             $installed = $installed ? 'installed' : 'downloaded';
  748.             $dep['package'] = $dep['name'];
  749.             $dep = $this->_registry->parsedPackageNameToString($dep, true);
  750.             if (!isset($this->_options['nodeps']) && !isset($this->_options['force'])) {
  751.                 return $this->raiseError('%s requires package "' . $depname . '"' .
  752.                     $extra . ", $installed version is " . $version);
  753.             } else {
  754.                 return $this->warning('warning: %s requires package "' . $depname . '"' .
  755.                     $extra . ", $installed version is " . $version);
  756.             }
  757.         } elseif ((isset($dep['min']) || isset($dep['max'])) && !$fail &&
  758.               isset($dep['conflicts']) && !isset($dep['exclude'])) {
  759.             $installed = $installed ? 'installed' : 'downloaded';
  760.             if (!isset($this->_options['nodeps']) && !isset($this->_options['force'])) {
  761.                 return $this->raiseError('%s conflicts with package "' . $depname . '"' . $extra .
  762.                     ", $installed version is " . $version);
  763.             } else {
  764.                 return $this->warning('warning: %s conflicts with package "' . $depname . '"' .
  765.                     $extra . ", $installed version is " . $version);
  766.             }
  767.         }
  768.         if (isset($dep['exclude'])) {
  769.             $installed = $installed ? 'installed' : 'downloaded';
  770.             foreach ($dep['exclude'] as $exclude) {
  771.                 if (version_compare($version, $exclude, '==') && !isset($dep['conflicts'])) {
  772.                     if (!isset($this->_options['nodeps']) &&
  773.                           !isset($this->_options['force'])) {
  774.                         return $this->raiseError('%s is not compatible with ' .
  775.                             $installed . ' package "' .
  776.                             $depname . '" version ' .
  777.                             $exclude);
  778.                     } else {
  779.                         return $this->warning('warning: %s is not compatible with ' .
  780.                             $installed . ' package "' .
  781.                             $depname . '" version ' .
  782.                             $exclude);
  783.                     }
  784.                 } elseif (version_compare($version, $exclude, '!=') && isset($dep['conflicts'])) {
  785.                     $installed = $installed ? 'installed' : 'downloaded';
  786.                     if (!isset($this->_options['nodeps']) && !isset($this->_options['force'])) {
  787.                         return $this->raiseError('%s conflicts with package "' . $depname . '"' .
  788.                             $extra . ", $installed version is " . $version);
  789.                     } else {
  790.                         return $this->warning('warning: %s conflicts with package "' . $depname . '"' .
  791.                             $extra . ", $installed version is " . $version);
  792.                     }
  793.                 }
  794.             }
  795.         }
  796.         if (isset($dep['recommended'])) {
  797.             $installed = $installed ? 'installed' : 'downloaded';
  798.             if (version_compare($version, $dep['recommended'], '==')) {
  799.                 return true;
  800.             } else {
  801.                 if (!$found && $installed) {
  802.                     $param = $this->_registry->getPackage($dep['name'], $dep['channel']);
  803.                 }
  804.                 if ($param) {
  805.                     $found = false;
  806.                     foreach ($params as $parent) {
  807.                         if ($parent->isEqual($this->_currentPackage)) {
  808.                             $found = true;
  809.                             break;
  810.                         }
  811.                     }
  812.                     if ($found) {
  813.                         if ($param->isCompatible($parent)) {
  814.                             return true;
  815.                         }
  816.                     } else { // this is for validPackage() calls
  817.                         $parent = $this->_registry->getPackage($this->_currentPackage['package'],
  818.                             $this->_currentPackage['channel']);
  819.                         if ($parent !== null) {
  820.                             if ($param->isCompatible($parent)) {
  821.                                 return true;
  822.                             }
  823.                         }
  824.                     }
  825.                 }
  826.                 if (!isset($this->_options['nodeps']) && !isset($this->_options['force']) &&
  827.                       !isset($this->_options['loose'])) {
  828.                     return $this->raiseError('%s dependency package "' . $depname .
  829.                         '" ' . $installed . ' version ' . $version . 
  830.                         ' is not the recommended version ' . $dep['recommended'] .
  831.                         ', but may be compatible, use --force to install');
  832.                 } else {
  833.                     return $this->warning('warning: %s dependency package "' . $depname .
  834.                         '" ' . $installed . ' version ' . $version .
  835.                         ' is not the recommended version ' . $dep['recommended']);
  836.                 }
  837.             }
  838.         }
  839.         return true;
  840.     }
  841.  
  842.     function _validatePackageInstall($dep, $required, $depv1 = false)
  843.     {
  844.         return $this->_validatePackageDownload($dep, $required, array(), $depv1);
  845.     }
  846.  
  847.     /**
  848.      * Verify that uninstalling packages passed in to command line is OK.
  849.      *
  850.      * @param PEAR_Installer $dl
  851.      * @return PEAR_Error|true
  852.      */
  853.     function validatePackageUninstall(&$dl)
  854.     {
  855.         if (PEAR::isError($this->_dependencydb)) {
  856.             return $this->_dependencydb;
  857.         }
  858.         $params = array();
  859.         // construct an array of "downloaded" packages to fool the package dependency checker
  860.         // into using these to validate uninstalls of circular dependencies
  861.         $downloaded = &$dl->getUninstallPackages();
  862.         foreach ($downloaded as $i => $pf) {
  863.             if (!class_exists('PEAR_Downloader_Package')) {
  864.                 require_once 'PEAR/Downloader/Package.php';
  865.             }
  866.             $dp = &new PEAR_Downloader_Package($dl);
  867.             $dp->setPackageFile($downloaded[$i]);
  868.             $params[$i] = &$dp;
  869.         }
  870.         // check cache
  871.         $memyselfandI = strtolower($this->_currentPackage['channel']) . '/' .
  872.             strtolower($this->_currentPackage['package']);
  873.         if (isset($dl->___uninstall_package_cache)) {
  874.             $badpackages = $dl->___uninstall_package_cache;
  875.             if (isset($badpackages[$memyselfandI]['warnings'])) {
  876.                 foreach ($badpackages[$memyselfandI]['warnings'] as $warning) {
  877.                     $dl->log(0, $warning[0]);
  878.                 }
  879.             }
  880.             if (isset($badpackages[$memyselfandI]['errors'])) {
  881.                 foreach ($badpackages[$memyselfandI]['errors'] as $error) {
  882.                     if (is_array($error)) {
  883.                         $dl->log(0, $error[0]);
  884.                     } else {
  885.                         $dl->log(0, $error->getMessage());
  886.                     }
  887.                 }
  888.                 if (isset($this->_options['nodeps']) || isset($this->_options['force'])) {
  889.                     return $this->warning(
  890.                         'warning: %s should not be uninstalled, other installed packages depend ' .
  891.                         'on this package');
  892.                 } else {
  893.                     return $this->raiseError(
  894.                         '%s cannot be uninstalled, other installed packages depend on this package');
  895.                 }
  896.             }
  897.             return true;
  898.         }
  899.         // first, list the immediate parents of each package to be uninstalled
  900.         $perpackagelist = array();
  901.         $allparents = array();
  902.         foreach ($params as $i => $param) {
  903.             $a = array('channel' => strtolower($param->getChannel()),
  904.                       'package' => strtolower($param->getPackage()));
  905.             $deps = $this->_dependencydb->getDependentPackages($a);
  906.             if ($deps) {
  907.                 foreach ($deps as $d) {
  908.                     $pardeps = $this->_dependencydb->getDependencies($d);
  909.                     foreach ($pardeps as $dep) {
  910.                         if (strtolower($dep['dep']['channel']) == $a['channel'] &&
  911.                               strtolower($dep['dep']['name']) == $a['package']) {
  912.                             if (!isset($perpackagelist[$a['channel'] . '/' . $a['package']])) {
  913.                                 $perpackagelist[$a['channel'] . '/' . $a['package']] = array();
  914.                             }
  915.                             $perpackagelist[$a['channel'] . '/' . $a['package']][]
  916.                                 = array($d['channel'] . '/' . $d['package'], $dep);
  917.                             if (!isset($allparents[$d['channel'] . '/' . $d['package']])) {
  918.                                 $allparents[$d['channel'] . '/' . $d['package']] = array();
  919.                             }
  920.                             if (!isset($allparents[$d['channel'] . '/' . $d['package']][$a['channel'] . '/' . $a['package']])) {
  921.                                 $allparents[$d['channel'] . '/' . $d['package']][$a['channel'] . '/' . $a['package']] = array();
  922.                             }
  923.                             $allparents[$d['channel'] . '/' . $d['package']]
  924.                                        [$a['channel'] . '/' . $a['package']][]
  925.                                 = array($d, $dep);
  926.                         }
  927.                     }
  928.                 }
  929.             }
  930.         }
  931.         // next, remove any packages from the parents list that are not installed
  932.         $remove = array();
  933.         foreach ($allparents as $parent => $d1) {
  934.             foreach ($d1 as $d) {
  935.                 if ($this->_registry->packageExists($d[0][0]['package'], $d[0][0]['channel'])) {
  936.                     continue;
  937.                 }
  938.                 $remove[$parent] = true;
  939.             }
  940.         }
  941.         // next remove any packages from the parents list that are not passed in for
  942.         // uninstallation
  943.         foreach ($allparents as $parent => $d1) {
  944.             foreach ($d1 as $d) {
  945.                 foreach ($params as $param) {
  946.                     if (strtolower($param->getChannel()) == $d[0][0]['channel'] &&
  947.                           strtolower($param->getPackage()) == $d[0][0]['package']) {
  948.                         // found it
  949.                         continue 3;
  950.                     }
  951.                 }
  952.                 $remove[$parent] = true;
  953.             }
  954.         }
  955.         // remove all packages whose dependencies fail
  956.         // save which ones failed for error reporting
  957.         $badchildren = array();
  958.         do {
  959.             $fail = false;
  960.             foreach ($remove as $package => $unused) {
  961.                 if (!isset($allparents[$package])) {
  962.                     continue;
  963.                 }
  964.                 foreach ($allparents[$package] as $kid => $d1) {
  965.                     foreach ($d1 as $depinfo) {
  966.                         if ($depinfo[1]['type'] != 'optional') {
  967.                             if (isset($badchildren[$kid])) {
  968.                                 continue;
  969.                             }
  970.                             $badchildren[$kid] = true;
  971.                             $remove[$kid] = true;
  972.                             $fail = true;
  973.                             continue 2;
  974.                         }
  975.                     }
  976.                 }
  977.                 if ($fail) {
  978.                     // start over, we removed some children
  979.                     continue 2;
  980.                 }
  981.             }
  982.         } while ($fail);
  983.         // next, construct the list of packages that can't be uninstalled
  984.         $badpackages = array();
  985.         $save = $this->_currentPackage;
  986.         foreach ($perpackagelist as $package => $packagedeps) {
  987.             foreach ($packagedeps as $parent) {
  988.                 if (!isset($remove[$parent[0]])) {
  989.                     continue;
  990.                 }
  991.                 $packagename = $this->_registry->parsePackageName($parent[0]);
  992.                 $packagename['channel'] = $this->_registry->channelAlias($packagename['channel']);
  993.                 $pa = $this->_registry->getPackage($packagename['package'], $packagename['channel']);
  994.                 $packagename['package'] = $pa->getPackage();
  995.                 $this->_currentPackage = $packagename;
  996.                 // parent is not present in uninstall list, make sure we can actually
  997.                 // uninstall it (parent dep is optional)
  998.                 $parentname['channel'] = $this->_registry->channelAlias($parent[1]['dep']['channel']);
  999.                 $pa = $this->_registry->getPackage($parent[1]['dep']['name'], $parent[1]['dep']['channel']);
  1000.                 $parentname['package'] = $pa->getPackage();
  1001.                 $parent[1]['dep']['package'] = $parentname['package'];
  1002.                 $parent[1]['dep']['channel'] = $parentname['channel'];
  1003.                 if ($parent[1]['type'] == 'optional') {
  1004.                     $test = $this->_validatePackageUninstall($parent[1]['dep'], false, $dl);
  1005.                     if ($test !== true) {
  1006.                         $badpackages[$package]['warnings'][] = $test;
  1007.                     }
  1008.                 } else {
  1009.                     $test = $this->_validatePackageUninstall($parent[1]['dep'], true, $dl);
  1010.                     if ($test !== true) {
  1011.                         $badpackages[$package]['errors'][] = $test;
  1012.                     }
  1013.                 }
  1014.             }
  1015.         }
  1016.         $this->_currentPackage = $save;
  1017.         $dl->___uninstall_package_cache = $badpackages;
  1018.         if (isset($badpackages[$memyselfandI])) {
  1019.             if (isset($badpackages[$memyselfandI]['warnings'])) {
  1020.                 foreach ($badpackages[$memyselfandI]['warnings'] as $warning) {
  1021.                     $dl->log(0, $warning[0]);
  1022.                 }
  1023.             }
  1024.             if (isset($badpackages[$memyselfandI]['errors'])) {
  1025.                 foreach ($badpackages[$memyselfandI]['errors'] as $error) {
  1026.                     if (is_array($error)) {
  1027.                         $dl->log(0, $error[0]);
  1028.                     } else {
  1029.                         $dl->log(0, $error->getMessage());
  1030.                     }
  1031.                 }
  1032.                 if (isset($this->_options['nodeps']) || isset($this->_options['force'])) {
  1033.                     return $this->warning(
  1034.                         'warning: %s should not be uninstalled, other installed packages depend ' .
  1035.                         'on this package');
  1036.                 } else {
  1037.                     return $this->raiseError(
  1038.                         '%s cannot be uninstalled, other installed packages depend on this package');
  1039.                 }
  1040.             }
  1041.         }
  1042.         return true;
  1043.     }
  1044.  
  1045.     function _validatePackageUninstall($dep, $required, $dl)
  1046.     {
  1047.         $depname = $this->_registry->parsedPackageNameToString($dep, true);
  1048.         $version = $this->_registry->packageinfo($dep['package'], 'version',
  1049.             $dep['channel']);
  1050.         if (!$version) {
  1051.             return true;
  1052.         }
  1053.         $extra = $this->_getExtraString($dep);
  1054.         if (isset($dep['exclude'])) {
  1055.             if (!is_array($dep['exclude'])) {
  1056.                 $dep['exclude'] = array($dep['exclude']);
  1057.             }
  1058.         }
  1059.         if (isset($dep['conflicts'])) {
  1060.             return true; // uninstall OK - these packages conflict (probably installed with --force)
  1061.         }
  1062.         if (!isset($dep['min']) && !isset($dep['max'])) {
  1063.             if ($required) {
  1064.                 if (!isset($this->_options['nodeps']) && !isset($this->_options['force'])) {
  1065.                     return $this->raiseError('"' . $depname . '" is required by ' .
  1066.                         'installed package %s' . $extra);
  1067.                 } else {
  1068.                     return $this->warning('warning: "' . $depname . '" is required by ' .
  1069.                         'installed package %s' . $extra);
  1070.                 }
  1071.             } else {
  1072.                 return $this->warning('"' . $depname . '" can be optionally used by ' .
  1073.                         'installed package %s' . $extra);
  1074.             }
  1075.         }
  1076.         $fail = false;
  1077.         if (isset($dep['min'])) {
  1078.             if (version_compare($version, $dep['min'], '>=')) {
  1079.                 $fail = true;
  1080.             }
  1081.         }
  1082.         if (isset($dep['max'])) {
  1083.             if (version_compare($version, $dep['max'], '<=')) {
  1084.                 $fail = true;
  1085.             }
  1086.         }
  1087.         // we re-use this variable, preserve the original value
  1088.         $saverequired = $required;
  1089.         if ($required) {
  1090.             if (!isset($this->_options['nodeps']) && !isset($this->_options['force'])) {
  1091.                 return $this->raiseError($depname . $extra . ' is required by installed package' .
  1092.                     ' "%s"');
  1093.             } else {
  1094.                 return $this->raiseError('warning: ' . $depname . $extra .
  1095.                     ' is required by installed package "%s"');
  1096.             }
  1097.         } else {
  1098.             return $this->warning($depname . $extra . ' can be optionally used by installed package' .
  1099.                     ' "%s"');
  1100.         }
  1101.         return true;
  1102.     }
  1103.  
  1104.     /**
  1105.      * validate a downloaded package against installed packages
  1106.      * 
  1107.      * As of PEAR 1.4.3, this will only validate
  1108.      *
  1109.      * @param array|PEAR_Downloader_Package|PEAR_PackageFile_v1|PEAR_PackageFile_v2
  1110.      *              $pkg package identifier (either
  1111.      *                   array('package' => blah, 'channel' => blah) or an array with
  1112.      *                   index 'info' referencing an object)
  1113.      * @param PEAR_Downloader $dl
  1114.      * @param array $params full list of packages to install
  1115.      * @return true|PEAR_Error
  1116.      */
  1117.     function validatePackage($pkg, &$dl, $params = array())
  1118.     {
  1119.         if (is_array($pkg) && isset($pkg['info'])) {
  1120.             $deps = $this->_dependencydb->getDependentPackageDependencies($pkg['info']);
  1121.         } else {
  1122.             $deps = $this->_dependencydb->getDependentPackageDependencies($pkg);
  1123.         }
  1124.         $fail = false;
  1125.         if ($deps) {
  1126.             if (!class_exists('PEAR_Downloader_Package')) {
  1127.                 require_once 'PEAR/Downloader/Package.php';
  1128.             }
  1129.             $dp = &new PEAR_Downloader_Package($dl);
  1130.             if (is_object($pkg)) {
  1131.                 $dp->setPackageFile($pkg);
  1132.             } else {
  1133.                 $dp->setDownloadURL($pkg);
  1134.             }
  1135.             PEAR::pushErrorHandling(PEAR_ERROR_RETURN);
  1136.             foreach ($deps as $channel => $info) {
  1137.                 foreach ($info as $package => $ds) {
  1138.                     foreach ($params as $packd) {
  1139.                         if (strtolower($packd->getPackage()) == strtolower($package) &&
  1140.                               $packd->getChannel() == $channel) {
  1141.                             $dl->log(3, 'skipping installed package check of "' .
  1142.                                         $this->_registry->parsedPackageNameToString(
  1143.                                             array('channel' => $channel, 'package' => $package),
  1144.                                             true) .
  1145.                                         '", version "' . $packd->getVersion() . '" will be ' .
  1146.                                         'downloaded and installed');
  1147.                             continue 2; // jump to next package
  1148.                         }
  1149.                     }
  1150.                     foreach ($ds as $d) {
  1151.                         $checker = &new PEAR_Dependency2($this->_config, $this->_options,
  1152.                             array('channel' => $channel, 'package' => $package), $this->_state);
  1153.                         $dep = $d['dep'];
  1154.                         $required = $d['type'] == 'required';
  1155.                         $ret = $checker->_validatePackageDownload($dep, $required, array(&$dp));
  1156.                         if (is_array($ret)) {
  1157.                             $dl->log(0, $ret[0]);
  1158.                         } elseif (PEAR::isError($ret)) {
  1159.                             $dl->log(0, $ret->getMessage());
  1160.                             $fail = true;
  1161.                         }
  1162.                     }
  1163.                 }
  1164.             }
  1165.             PEAR::popErrorHandling();
  1166.         }
  1167.         if ($fail) {
  1168.             return $this->raiseError(
  1169.                 '%s cannot be installed, conflicts with installed packages');
  1170.         }
  1171.         return true;
  1172.     }
  1173.  
  1174.     /**
  1175.      * validate a package.xml 1.0 dependency
  1176.      */
  1177.     function validateDependency1($dep, $params = array())
  1178.     {
  1179.         if (!isset($dep['optional'])) {
  1180.             $dep['optional'] = 'no';
  1181.         }
  1182.         list($newdep, $type) = $this->normalizeDep($dep);
  1183.         if (!$newdep) {
  1184.             return $this->raiseError("Invalid Dependency");
  1185.         }
  1186.         if (method_exists($this, "validate{$type}Dependency")) {
  1187.             return $this->{"validate{$type}Dependency"}($newdep, $dep['optional'] == 'no',
  1188.                 $params, true);
  1189.         }
  1190.     }
  1191.  
  1192.     /**
  1193.      * Convert a 1.0 dep into a 2.0 dep
  1194.      */
  1195.     function normalizeDep($dep)
  1196.     {
  1197.         $types = array(
  1198.             'pkg' => 'Package',
  1199.             'ext' => 'Extension',
  1200.             'os' => 'Os',
  1201.             'php' => 'Php'
  1202.         );
  1203.         if (isset($types[$dep['type']])) {
  1204.             $type = $types[$dep['type']];
  1205.         } else {
  1206.             return array(false, false);
  1207.         }
  1208.         $newdep = array();
  1209.         switch ($type) {
  1210.             case 'Package' :
  1211.                 $newdep['channel'] = 'pear.php.net';
  1212.             case 'Extension' :
  1213.             case 'Os' :
  1214.                 $newdep['name'] = $dep['name'];
  1215.             break;
  1216.         }
  1217.         $dep['rel'] = PEAR_Dependency2::signOperator($dep['rel']);
  1218.         switch ($dep['rel']) {
  1219.             case 'has' :
  1220.                 return array($newdep, $type);
  1221.             break;
  1222.             case 'not' :
  1223.                 $newdep['conflicts'] = true;
  1224.             break;
  1225.             case '>=' :
  1226.             case '>' :
  1227.                 $newdep['min'] = $dep['version'];
  1228.                 if ($dep['rel'] == '>') {
  1229.                     $newdep['exclude'] = $dep['version'];
  1230.                 }
  1231.             break;
  1232.             case '<=' :
  1233.             case '<' :
  1234.                 $newdep['max'] = $dep['version'];
  1235.                 if ($dep['rel'] == '<') {
  1236.                     $newdep['exclude'] = $dep['version'];
  1237.                 }
  1238.             break;
  1239.             case 'ne' :
  1240.             case '!=' :
  1241.                 $newdep['min'] = '0';
  1242.                 $newdep['max'] = '100000';
  1243.                 $newdep['exclude'] = $dep['version'];
  1244.             break;
  1245.             case '==' :
  1246.                 $newdep['min'] = $dep['version'];
  1247.                 $newdep['max'] = $dep['version'];
  1248.             break;
  1249.         }
  1250.         if ($type == 'Php') {
  1251.             if (!isset($newdep['min'])) {
  1252.                 $newdep['min'] = '4.2.0';
  1253.             }
  1254.             if (!isset($newdep['max'])) {
  1255.                 $newdep['max'] = '6.0.0';
  1256.             }
  1257.         }
  1258.         return array($newdep, $type);
  1259.     }
  1260.  
  1261.     /**
  1262.      * Converts text comparing operators to them sign equivalents
  1263.      *
  1264.      * Example: 'ge' to '>='
  1265.      *
  1266.      * @access public
  1267.      * @param  string Operator
  1268.      * @return string Sign equivalent
  1269.      */
  1270.     function signOperator($operator)
  1271.     {
  1272.         switch($operator) {
  1273.             case 'lt': return '<';
  1274.             case 'le': return '<=';
  1275.             case 'gt': return '>';
  1276.             case 'ge': return '>=';
  1277.             case 'eq': return '==';
  1278.             case 'ne': return '!=';
  1279.             default:
  1280.                 return $operator;
  1281.         }
  1282.     }
  1283.  
  1284.     function raiseError($msg)
  1285.     {
  1286.         if (isset($this->_options['ignore-errors'])) {
  1287.             return $this->warning($msg);
  1288.         }
  1289.         return PEAR::raiseError(sprintf($msg, $this->_registry->parsedPackageNameToString(
  1290.             $this->_currentPackage, true)));
  1291.     }
  1292.  
  1293.     function warning($msg)
  1294.     {
  1295.         return array(sprintf($msg, $this->_registry->parsedPackageNameToString(
  1296.             $this->_currentPackage, true)));
  1297.     }
  1298. }
  1299. ?>