From 8f498ad5f6bddfa88d9e9e735935801c7490bded Mon Sep 17 00:00:00 2001
From: "cedric@yterium.com" <>
Date: Wed, 30 Mar 2011 09:54:37 +0000
Subject: [PATCH] =?UTF-8?q?http://core.spip.org/issues/1566=20verifier=20p?=
 =?UTF-8?q?lus=20en=20amont=20que=20le=20type=20de=20fichier=20qu'on=20ess?=
 =?UTF-8?q?ayer=20d'uploader=20est=20autorise=20pour=20eviter=20de=20creer?=
 =?UTF-8?q?=20des=20repertoires=20fantomes=20inutiles.=20Du=20coup=20on=20?=
 =?UTF-8?q?deplace=20la=20verification=20du=20type=20image=20dans=20une=20?=
 =?UTF-8?q?fonction=20verifier=5Fdocument=5Fmode=5Fimage,=20et=20ces=20fon?=
 =?UTF-8?q?ctions=20de=20verifications=20sont=20appelees=20deux=20fois=20:?=
 =?UTF-8?q?=20-=20une=20fois=20avant=20copie=20du=20fichier=20dans=20IMG/?=
 =?UTF-8?q?=20-=20une=20fois=20apres=20analyse=20d=C3=A9taill=C3=A9e=20du?=
 =?UTF-8?q?=20contenu=20du=20fichier=20Les=20fonctions=20ne=20doivent=20pa?=
 =?UTF-8?q?s=20refuser=20a=20tort=20un=20document=20a=20la=20premiere=20pa?=
 =?UTF-8?q?sse=20si=20les=20infos=20ne=20sont=20pas=20completes?=
MIME-Version: 1.0
Content-Type: text/plain; charset=UTF-8
Content-Transfer-Encoding: 8bit

---
 .gitattributes                          |   1 +
 action/ajouter_documents.php            | 127 +++++++++++++-----------
 inc/joindre_document.php                |   4 +-
 inc/verifier_document_mode_image.php    |  26 +++++
 inc/verifier_document_mode_vignette.php |   6 +-
 5 files changed, 104 insertions(+), 60 deletions(-)
 create mode 100644 inc/verifier_document_mode_image.php

diff --git a/.gitattributes b/.gitattributes
index 10063033..08dc238f 100644
--- a/.gitattributes
+++ b/.gitattributes
@@ -30,6 +30,7 @@ inc/getdocument.php -text
 inc/joindre_document.php -text
 inc/marquer_doublons_doc.php -text
 inc/renseigner_document.php -text
+inc/verifier_document_mode_image.php -text
 inc/verifier_document_mode_vignette.php -text
 inc/vignette.php -text
 javascript/jquery.multifile.js -text
diff --git a/action/ajouter_documents.php b/action/ajouter_documents.php
index 2dff3bd8..8cbf139f 100644
--- a/action/ajouter_documents.php
+++ b/action/ajouter_documents.php
@@ -131,8 +131,8 @@ function action_ajouter_un_document_dist($id_document, $file, $objet, $id_objet,
 			$champs['titre'] = preg_replace(',\.([^.]+)$,', '', $titre);
 		}
 
-		if (!$fichier = fixer_fichier_upload($file))
-			return ("Impossible de telecharger le fichier");
+		if (!is_array($fichier = fixer_fichier_upload($file, $mode)))
+			return is_string($fichier)?$fichier:_T("erreur_upload_type_interdit",array('nom'=>$file['name']));
 		
 		$champs['inclus'] = $fichier['inclus'];
 		$champs['extension'] = $fichier['extension'];
@@ -241,24 +241,40 @@ function corriger_extension($ext) {
 /**
  * Verifie la possibilite d'uploader une extension
  * renvoie un tableau descriptif si l'extension est acceptee
- * une chaine 'zip' si il faut zipper
- * false si l'extension est refusee
+ * avec un index 'autozip' si il faut zipper
+ * false ou message d'erreur si l'extension est refusee
+ * Verifie aussi si l'extension est autorisee pour le mode demande
+ * si on connait le mode a ce moment la
  * 
  */
-function verifier_upload_autorise($source){
+function verifier_upload_autorise($source, $mode=''){
+	$infos = array('fichier'=>$source);
+	$res = false;
 	if (preg_match(",\.([^.]+)$,", $source, $match)
 	  AND $ext = $match[1]){
 		
 	  $ext = corriger_extension(strtolower($ext));
-		if ($row = sql_fetsel("extension,inclus", "spip_types_documents", "extension=" . sql_quote($ext) . " AND upload='oui'"))
-			return $row;
+		if ($res = sql_fetsel("extension,inclus,media", "spip_types_documents", "extension=" . sql_quote($ext) . " AND upload='oui'"))
+			$infos = array_merge($infos,$res);
+	}
+	if (!$res){
+		if ($res = sql_fetsel("extension,inclus,media", "spip_types_documents", "extension='zip' AND upload='oui'")){
+			$infos = array_merge($infos,$res);
+			$res['autozip'] = true;
+		}
+	}
+	if ($mode AND $res){
+		// verifier en fonction du mode si une fonction est proposee
+		if ($verifier_document_mode = charger_fonction("verifier_document_mode_".$mode,"inc",true)){
+			$check = $verifier_document_mode($infos); // true ou message d'erreur sous forme de chaine
+			if ($check!==true)
+				$res = $check;
+		}
 	}
-		
-	if (sql_countsel("spip_types_documents", "extension='zip' AND upload='oui'"))
-		return 'zip';
 
-	spip_log("Extension $ext interdite a l'upload");
-	return false;
+	if (!$res OR is_string($res));
+		spip_log("Upload $source interdit ($res)",_LOG_INFO_IMPORTANTE);
+	return $res;
 }
 
 
@@ -273,53 +289,55 @@ function verifier_upload_autorise($source){
  * @param array $file //format $_FILES
  * @return array
  */
-function fixer_fichier_upload($file){
+function fixer_fichier_upload($file, $mode=''){
 
-	if (is_array($row=verifier_upload_autorise($file['name']))) {
-		$row['fichier'] = copier_document($row['extension'], $file['name'], $file['tmp_name']);
-		return $row;
-	}
-	// creer un zip comme demande
-	// pour encapsuler un fichier dont l'extension n'est pas supportee
-	elseif($row==='zip'){
+	if (is_array($row=verifier_upload_autorise($file['name'], $mode))) {
+		if (!isset($row['autozip'])){
+			$row['fichier'] = copier_document($row['extension'], $file['name'], $file['tmp_name']);
+			return $row;
+		}
+		// creer un zip comme demande
+		// pour encapsuler un fichier dont l'extension n'est pas supportee
+		else{
 		
-		$row = array('extension'=>'zip','inclus'=>false);
+			unset($row['autozip']);
 
-		$ext = 'zip';
-		if (!$tmp_dir = tempnam(_DIR_TMP, 'tmp_upload'))
-			return false;
-	
-		spip_unlink($tmp_dir);
-		@mkdir($tmp_dir);
-		
-		include_spip('inc/charset');
-		$tmp = $tmp_dir.'/'.translitteration($file['name']);
-		
-		$file['name'] .= '.zip'; # conserver l'extension dans le nom de fichier, par exemple toto.js => toto.js.zip
+			$ext = 'zip';
+			if (!$tmp_dir = tempnam(_DIR_TMP, 'tmp_upload'))
+				return false;
 
-		// deplacer le fichier tmp_name dans le dossier tmp
-		deplacer_fichier_upload($file['tmp_name'], $tmp, true);
-		
-		include_spip('inc/pclzip');
-		$source = _DIR_TMP . basename($tmp_dir) . '.zip';
-		$archive = new PclZip($source);
-		
-		$v_list = $archive->create($tmp,
-				PCLZIP_OPT_REMOVE_PATH, $tmp_dir,
-				PCLZIP_OPT_ADD_PATH, '');
-		
-		effacer_repertoire_temporaire($tmp_dir);
-		if (!$v_list) {
-			spip_log("Echec creation du zip ");
-			return false;
+			spip_unlink($tmp_dir);
+			@mkdir($tmp_dir);
+
+			include_spip('inc/charset');
+			$tmp = $tmp_dir.'/'.translitteration($file['name']);
+
+			$file['name'] .= '.'.$ext; # conserver l'extension dans le nom de fichier, par exemple toto.js => toto.js.zip
+
+			// deplacer le fichier tmp_name dans le dossier tmp
+			deplacer_fichier_upload($file['tmp_name'], $tmp, true);
+
+			include_spip('inc/pclzip');
+			$source = _DIR_TMP . basename($tmp_dir) . '.'.$ext;
+			$archive = new PclZip($source);
+
+			$v_list = $archive->create($tmp,
+					PCLZIP_OPT_REMOVE_PATH, $tmp_dir,
+					PCLZIP_OPT_ADD_PATH, '');
+
+			effacer_repertoire_temporaire($tmp_dir);
+			if (!$v_list) {
+				spip_log("Echec creation du zip ");
+				return false;
+			}
+
+			$row['fichier']  = copier_document($row['extension'], $file['name'], $source);
+			spip_unlink($source);
+			return $row;
 		}
-		
-		$row['fichier']  = copier_document($row['extension'], $file['name'], $source);
-		spip_unlink($source);
-		return $row;
 	}
-	
-	return false;
+	else
+		return $row; // retourner le message d'erreur
 }
 
 /**
@@ -335,9 +353,6 @@ function verifier_taille_document_acceptable($infos){
 		if (_DOC_MAX_SIZE > 0
 		 AND $infos['taille'] > _DOC_MAX_SIZE*1024)
 			return _T('medias:info_doc_max_poids', array('maxi' => taille_en_octets(_DOC_MAX_SIZE*1024), 'actuel' => taille_en_octets($infos['taille'])));
-
-		if ($infos['mode'] == 'image')
-			return _T('medias:erreur_format_fichier_image',array('nom'=> $infos['fichier']));
 	}
 	
 	// si c'est une image
diff --git a/inc/joindre_document.php b/inc/joindre_document.php
index e5a57a11..68d26d0a 100644
--- a/inc/joindre_document.php
+++ b/inc/joindre_document.php
@@ -47,7 +47,7 @@ function joindre_trouver_fichier_envoye(){
 						if (!($test['error'] == 4)){
 							if (is_string($err = joindre_upload_error($test['error'])))
 								return $err; // un erreur upload
-							if (!verifier_upload_autorise($test['name']))
+							if (!is_array(verifier_upload_autorise($test['name'])))
 								return _T('medias:erreur_upload_type_interdit',array('nom'=>$test['name']));
 							$files[]=$test;
 						}
@@ -58,7 +58,7 @@ function joindre_trouver_fichier_envoye(){
 					if (!($file['error'] == 4)){
 						if (is_string($err = joindre_upload_error($file['error'])))
 							return $err; // un erreur upload
-						if (!verifier_upload_autorise($file['name']))
+						if (!is_array(verifier_upload_autorise($file['name'])))
 							return _T('medias:erreur_upload_type_interdit',array('nom'=>$file['name']));
 						$files[]=$file;
 					}
diff --git a/inc/verifier_document_mode_image.php b/inc/verifier_document_mode_image.php
new file mode 100644
index 00000000..1b2afbe5
--- /dev/null
+++ b/inc/verifier_document_mode_image.php
@@ -0,0 +1,26 @@
+<?php
+/***************************************************************************\
+ *  SPIP, Systeme de publication pour l'internet                           *
+ *                                                                         *
+ *  Copyright (c) 2001-2010                                                *
+ *  Arnaud Martin, Antoine Pitrou, Philippe Riviere, Emmanuel Saint-James  *
+ *                                                                         *
+ *  Ce programme est un logiciel libre distribue sous licence GNU/GPL.     *
+ *  Pour plus de details voir le fichier COPYING.txt ou l'aide en ligne.   *
+\***************************************************************************/
+
+if (!defined("_ECRIRE_INC_VERSION")) return;
+
+function inc_verifier_document_mode_image_dist($infos){
+
+	// Si on veut uploader une image, il faut qu'elle ait ete bien lue
+	if ($infos['inclus'] != 'image')
+		return _T('medias:erreur_format_fichier_image',array('nom'=> $infos['fichier'])); #SVG
+
+	if (isset($infos['largeur']) AND isset($infos['hauteur'])){
+		if (!($infos['largeur'] OR $infos['hauteur']))
+			return _T('medias:erreur_upload_vignette',array('nom'=>$infos['fichier']));
+	}
+
+	return true;
+}
\ No newline at end of file
diff --git a/inc/verifier_document_mode_vignette.php b/inc/verifier_document_mode_vignette.php
index 83176528..9b829117 100644
--- a/inc/verifier_document_mode_vignette.php
+++ b/inc/verifier_document_mode_vignette.php
@@ -17,8 +17,10 @@ function inc_verifier_document_mode_vignette_dist($infos){
 	if ($infos['inclus'] != 'image')
 		return _T('medias:erreur_format_fichier_image',array('nom'=> $infos['fichier'])); #SVG
 
-	if (!($infos['largeur'] OR $infos['hauteur']))
-		return _T('medias:erreur_upload_vignette',array('nom'=>$infos['fichier']));
+	if (isset($infos['largeur']) AND isset($infos['hauteur'])){
+		if (!($infos['largeur'] OR $infos['hauteur']))
+			return _T('medias:erreur_upload_vignette',array('nom'=>$infos['fichier']));
+	}
 
 	return true;
 }
\ No newline at end of file
-- 
GitLab