diff --git a/htdocs/admin/tools/update.php b/htdocs/admin/tools/update.php
index 1b59612c369c11d0dcc88aa497478bc2eb8bb31f..32e2b7bba7f7251a50bbbfd4384fbb73a2e39a1f 100644
--- a/htdocs/admin/tools/update.php
+++ b/htdocs/admin/tools/update.php
@@ -78,7 +78,7 @@ if (GETPOST('action','alpha')=='install')
 		if ($result > 0)
 		{
 			$documentrootalt=DOL_DOCUMENT_ROOT_ALT;
-			$result=dol_uncompress($newfile,$_FILES['fileinstall']['type'],$documentrootalt);
+			$result=dol_uncompress($newfile,$documentrootalt);
 			if (! empty($result['error']))
 			{
 				if ($result['error'] == -1)
@@ -175,13 +175,13 @@ if (! empty($conf->global->MAIN_ONLINE_INSTALL_MODULE))
 		$message=info_admin($langs->transnoentities("ErrorOSSystem"));
 		print $message;
 	}
-	else 
+	else
 	{
 		$message=info_admin($langs->trans("NotExistsDirect").$langs->trans("InfDirAlt").$langs->trans("InfDirExample"));
 		print $message;
-	}	
+	}
 }
-else 
+else
 {
 	print '<b>'.$langs->trans("StepNb",4).'</b>: ';
 	print $langs->trans("SetupIsReadyForUse").'<br>';
@@ -191,7 +191,7 @@ print '</form>';
 if (! empty($result['return']))
 {
 	print '<br>';
-	
+
 	foreach($result['return'] as $value)
 	{
 		echo $value.'<br>';
diff --git a/htdocs/core/lib/files.lib.php b/htdocs/core/lib/files.lib.php
index 85cd1c1eb7e7f1b4918a597e21b5d49e7c3027e4..42b54a24f4e852c9bb9b306b04d8d5c9782029c1 100644
--- a/htdocs/core/lib/files.lib.php
+++ b/htdocs/core/lib/files.lib.php
@@ -618,65 +618,6 @@ function dol_move_uploaded_file($src_file, $dest_file, $allowoverwrite, $disable
 	}
 }
 
-/**
- * Uncompress a file
- * 
- * @param 	string 	$newfile	file to uncompress
- * @param 	stirng	$typefile	type of file
- * @param 	string	$dstdir		destination dir
- * @return 	int					0 if ok, >0 if ko
- */
-function dol_uncompress($newfile,$typefile,$dstdir)
-{
-	global $conf;
-	
-	$error=0;
-	$output=array();
-	$system=PHP_OS;
-	
-	//TODO: See best method for this
-	
-	if ($system=="Linux" || $system=="Darwin")
-	{
-		if ($typefile == 'application/x-gzip' || $typefile == 'application/x-gtar')
-		{
-			$prog= "tar -xzvf ";
-		}
-		elseif ($typefile == 'application/zip')
-		{
-			$prog= "unzip ";
-		}
-		else 
-		{
-			$output['error'] = -1;
-			$error++;
-		}
-	}
-	else 
-	{
-		$output['error'] = -2;
-		$error++;
-	}
-	
-	if (! $error)
-	{
-		$original_file=basename($_FILES["fileinstall"]["name"]);
-		$dir=$conf->admin->dir_temp.'/'.$original_file;
-		$file=$dir.'/'.$original_file;
-		$command= $prog.$file.' 2>&1';
-		
-		chdir($dstdir);
-		
-		exec($command, $out, $return_var);
-		if ($return_var == 1) $output['error'] = -3;		// OK with Warning
-		elseif ($return_var == 127) $output['error'] = -4;	// KO
-		
-		$output['return'] = $out;
-	}
-	
-	return $output;
-}
-
 /**
  *  Remove a file or several files with a mask
  *
@@ -802,7 +743,7 @@ function dol_delete_preview($object)
 {
 	global $langs,$conf;
     require_once(DOL_DOCUMENT_ROOT."/core/lib/files.lib.php");
-    
+
     $element = $object->element;
     $dir = $conf->$element->dir_output;
 
@@ -1081,20 +1022,44 @@ function dol_convert_file($file,$ext='png')
  *
  * @param 	string	$inputfile		Source file name
  * @param 	string	$outputfile		Target file name
- * @param 	string	$mode			'gz' or 'bz'
+ * @param 	string	$mode			'gz' or 'bz' or 'zip'
  * @return	int						<0 if KO, >0 if OK
  */
 function dol_compress_file($inputfile, $outputfile, $mode="gz")
 {
+    $foundhandler=0;
+
     try
     {
-        $data = implode("", file($inputfile));
-        if ($mode == 'gz') $compressdata = gzencode($data, 9);
-        elseif ($mode == 'bz') $compressdata = bzcompress($data, 9);
+        $data = implode("", file(dol_osencode($inputfile)));
+        if ($mode == 'gz')     { $foundhandler=1; $compressdata = gzencode($data, 9); }
+        elseif ($mode == 'bz') { $foundhandler=1; $compressdata = bzcompress($data, 9); }
+        elseif ($mode == 'zip')
+        {
+            if (defined('ODTPHP_PATHTOPCLZIP'))
+            {
+                $foundhandler=1;
 
-        $fp = fopen($outputfile, "w");
-        fwrite($fp, $compressdata);
-        fclose($fp);
+                include_once(ODTPHP_PATHTOPCLZIP.'/pclzip.lib.php');
+                $archive = new PclZip($outputfile);
+                $archive->add($inputfile, PCLZIP_OPT_REMOVE_PATH, dirname($inputfile));
+                //$archive->add($inputfile);
+                return 1;
+            }
+        }
+
+        if ($foundhandler)
+        {
+            $fp = fopen($outputfile, "w");
+            fwrite($fp, $compressdata);
+            fclose($fp);
+            return 1;
+        }
+        else
+        {
+            dol_syslog("Try to zip with format ".$mode." with no handler for this format",LOG_ERR);
+            return -2;
+        }
     }
     catch (Exception $e)
     {
@@ -1106,6 +1071,44 @@ function dol_compress_file($inputfile, $outputfile, $mode="gz")
     }
 }
 
+/**
+ * Uncompress a file
+ *
+ * @param 	string 	$inputfile		File to uncompress
+ * @param 	string	$outputdir		Target dir name
+ * @return 	array					array('error'=>'Error code') or array() if no error
+ */
+function dol_uncompress($inputfile,$outputdir)
+{
+    global $conf;
+
+    if (defined('ODTPHP_PATHTOPCLZIP'))
+    {
+        include_once(ODTPHP_PATHTOPCLZIP.'/pclzip.lib.php');
+        $archive = new PclZip($inputfile);
+        if ($archive->extract(PCLZIP_OPT_PATH, $outputdir) == 0) return array('error'=>$archive->errorInfo(true));
+        else return array();
+    }
+
+    if (class_exists('ZipArchive'))
+    {
+        $zip = new ZipArchive;
+        $res = $zip->open($inputfile);
+        if ($res === TRUE)
+        {
+            $zip->extractTo($outputdir.'/');
+            $zip->close();
+            return array();
+        }
+        else
+        {
+            return array('error'=>'Failed to unzip with ZipArchive');
+        }
+    }
+
+    return array('error'=>'No engine to unzip files int this PHP');
+}
+
 
 /**
  * Return most recent file
diff --git a/test/phpunit/FilesLibTest.php b/test/phpunit/FilesLibTest.php
index dc856064a2082664bed41e1afee91c3abcf6c222..fb919ab56b952092a3e8a2f364cca3367b1a8c9e 100644
--- a/test/phpunit/FilesLibTest.php
+++ b/test/phpunit/FilesLibTest.php
@@ -239,7 +239,7 @@ class FilesLibTest extends PHPUnit_Framework_TestCase
         print __METHOD__." result=".$result."\n";
         $this->assertTrue($result);
     }
-    
+
     /**
      * testDolMimeType
      *
@@ -279,10 +279,41 @@ class FilesLibTest extends PHPUnit_Framework_TestCase
 		$result=dol_mimetype('file.php','',2);
 		$this->assertEquals('php.png',$result);
 		$result=dol_mimetype('file.php','',3);
-        $this->assertEquals('php',$result);        
+        $this->assertEquals('php',$result);
 		// file.php.noexe
 		$result=dol_mimetype('file.php.noexe','',0);
         $this->assertEquals('text/plain',$result);
-    }		
+    }
+
+    /**
+     * testDolCompressUnCompress
+     *
+     * @return	string
+     */
+    public function testDolCompressUnCompress()
+    {
+        global $conf,$user,$langs,$db;
+        $conf=$this->savconf;
+        $user=$this->savuser;
+        $langs=$this->savlangs;
+        $db=$this->savdb;
+
+        $format='zip';
+        $filein=dirname(__FILE__).'/Example_import_company_1.csv';
+        $fileout=$conf->admin->dir_temp.'/test.'.$format;
+        $dirout=$conf->admin->dir_temp.'/test';
+
+        dol_delete_file($fileout);
+        $count=0;
+        dol_delete_dir_recursive($dirout,$count,1);
+
+        $result=dol_compress_file($filein, $fileout, $format);
+        print __METHOD__." result=".$result."\n";
+        $this->assertGreaterThanOrEqual(1,$result);
+
+        $result=dol_uncompress($fileout, $dirout);
+        print __METHOD__." result=".join(',',$result)."\n";
+        $this->assertEquals(0,count($result));
+    }
 }
 ?>
\ No newline at end of file