Index: contrib/z-push/include/authldap.php
===================================================================
--- contrib/z-push/include/authldap.php	(revision 4000)
+++ contrib/z-push/include/authldap.php	(revision 4000)
@@ -0,0 +1,116 @@
+<?php
+/***********************************************
+ * File      :   authLDAP.php
+ * Project   :   Z-Push
+ * Descr     :   Authenticate user in an Ldap Server
+ *               and get required information.
+ *               Parameters must be configured in config.php
+ *               This program is based on SearchLdap.php from Z-Push project.
+ *
+ * Created   :   emerson-faria.nobre@serpro.gov.br - 21/feb/2011
+ *
+ *
+ * This program is free software: you can redistribute it and/or modify
+ * it under the terms of the GNU Affero General Public License, version 3,
+ * as published by the Free Software Foundation with the following additional
+ * term according to sec. 7:
+ *
+ * According to sec. 7 of the GNU Affero General Public License, version 3,
+ * the terms of the AGPL are supplemented with the following terms:
+ *
+ * This program is distributed in the hope that it will be useful,
+ * but WITHOUT ANY WARRANTY; without even the implied warranty of
+ * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the
+ * GNU Affero General Public License for more details.
+ *
+ * You should have received a copy of the GNU Affero General Public License
+ * along with this program.  If not, see <http://www.gnu.org/licenses/>.
+ *
+ * Consult LICENSE file for details
+ ************************************************/
+
+require_once("config.php");
+
+class AuthLDAP {
+	var $_connection;
+
+	// connect and bind with LDAP server and return UIDNUMBER
+	function bind($user,$pwd) {
+		if (!function_exists("ldap_connect")) {
+			debugLog("AuthLDAP: php-ldap is not installed. Search aborted.");
+			return false;
+		}
+
+		// connect to LDAP
+		$this->_connection = @ldap_connect(LDAP_HOST, LDAP_PORT);
+		@ldap_set_option($this->_connection, LDAP_OPT_PROTOCOL_VERSION, 3);
+
+		// Authenticate
+		if (constant('ANONYMOUS_BIND') === true) {
+			if(! @ldap_bind($this->_connection)) {
+				debugLog("AuthLDAP: Could not bind anonymously to server! Search aborted.");
+				$this->_connection = false;
+				return false;
+			}
+		}
+		else if(! @ldap_bind($this->_connection, LDAP_BIND_USER, LDAP_BIND_PASSWORD)) {
+			debugLog("AuthLDAP: Could not bind to server with ADMIN user '".LDAP_BIND_USER."' and given password! Authentication aborted.");
+			$this->_connection = false;
+			return false;
+		}
+		$user_attributes = $this->getSearchResults($user);
+		if (! $user_attributes or $user_attributes["searchtotal"] !== 1) {
+			debugLog("AuthLDAP: Could not retrieve user $user information. Authentication aborted.");
+			$this->_connection = false;
+			return false;
+		}
+		if(! @ldap_bind($this->_connection, $user_attributes[0]["DN"], $pwd)) {
+			debugLog("AuthLDAP: Could not bind to server with LOGON user '".$user."' and given password! Authentication aborted.");
+			$this->_connection = false;
+			return false;
+		} else return $user_attributes[0]["UIDNUMBER"];
+	}
+
+	// perfom the search on the LDAP server
+	function getSearchResults($searchquery) {
+		global $ldap_field_map;
+		if (isset($this->_connection) && $this->_connection !== false) {
+			$searchfilter = str_replace("SEARCHVALUE", ",", $searchquery);
+		}
+
+		if (isset($this->_connection) && $this->_connection !== false) {
+			$searchfilter = str_replace("SEARCHVALUE", $searchquery, LDAP_SEARCH_FILTER);
+			$result = @ldap_search($this->_connection, LDAP_SEARCH_BASE, $searchfilter);
+			if (!$result) {
+				debugLog("AuthLDAP: Error in search query. Search aborted");
+				return false;
+			}
+
+			// get entry data as array
+			$searchresult = ldap_get_entries($this->_connection, $result);
+
+			$items = array();
+			$querycnt = $searchresult['count'];
+			$items['searchtotal'] = $querycnt;
+
+			foreach ($ldap_field_map as $key=>$value ) {
+				if (isset($searchresult[0][$value])) {
+					if (is_array($searchresult[0][$value]))
+					$items[0][$key] = $searchresult[0][$value][0];
+					else
+					$items[0][$key] = $searchresult[0][$value];
+				}
+			}
+			return $items;
+		}
+		else return false;
+	}
+
+	function disconnect() {
+		if ($this->_connection)
+		@ldap_close($this->_connection);
+
+		return true;
+	}
+}
+?>
Index: contrib/z-push/backend/BackendProxy.php
===================================================================
--- contrib/z-push/backend/BackendProxy.php	(revision 3754)
+++ contrib/z-push/backend/BackendProxy.php	(revision 4000)
@@ -11,5 +11,5 @@
  * Consult LICENSE file for details
  ************************************************/
-include_once('diffbackend.php');
+require_once("diffbackend.php");
 
 class BackendProxy extends BackendDiff {
@@ -28,7 +28,9 @@
 
 	function Logon($username, $domain, $password) {
-		global $BACKEND_EMAIL;
-		if (isset($BACKEND_EMAIL)) return $this->BackendEmail->Logon($username, $domain, $password);
-		else return true;
+		global $BACKEND_EMAIL, $BACKEND_CONTACTS, $BACKEND_CALENDAR;
+		if (isset($BACKEND_EMAIL) and (! $this->BackendEmail->Logon($username, $domain, $password))) return false;
+		if (isset($BACKEND_CONTACTS) and (! $this->BackendContacts->Logon($username, $domain, $password))) return false;
+		if (isset($BACKEND_CALENDAR) and (! $this->BackendCalendar->Logon($username, $domain, $password))) return false;
+		return true;
 	}
 
@@ -42,7 +44,4 @@
 		debugLog('BackendProxy::Setup('.$user.','.$devid.','.$protocolversion.')');
 		global $BACKEND_EMAIL, $BACKEND_CONTACTS, $BACKEND_CALENDAR;
-		$this->_user = $user;
-		$this->_devid = $devid;
-		$this->_protocolversion = $protocolversion;
 		if (isset($BACKEND_EMAIL)) $this->BackendEmail->Setup($user, $devid, $protocolversion);
 		if (isset($BACKEND_CONTACTS)) $this->BackendContacts->Setup($user, $devid, $protocolversion);
Index: contrib/z-push/backend/BackendCalendarExpresso.php
===================================================================
--- contrib/z-push/backend/BackendCalendarExpresso.php	(revision 3637)
+++ contrib/z-push/backend/BackendCalendarExpresso.php	(revision 4000)
@@ -11,13 +11,12 @@
  * Consult LICENSE file for details
  ************************************************/
-include_once('diffbackend.php');
-include_once('include/z_RTF.php');
-include_once "include/dbconnect.php";
+require_once("diffbackend.php");
+require_once("include/z_RTF.php");
+require_once("include/dbconnect.php");
+require_once("include/authldap.php");
 
 class BackendCalendarExpresso extends BackendDiff {
-	var $_user;
-	var $_devid;
-	var $_protocolversion;
 	var $db;
+	var $_uidnumber;
 
 	function __construct()
@@ -26,7 +25,13 @@
 
 		if (!$this->db) {
-			echo "A DB connect error occured.\n";
+			echo "Erro de conexao com o banco.\n";
 			exit;
 		}
+	}
+
+	function Logon($username, $domain, $password) {
+		$this->_uidnumber = $this->authUser($this->parseUser($username), $password);
+		if(! $this->_uidnumber) return false;
+		else return true;
 	}
 
@@ -35,6 +40,4 @@
 		$this->_devid = $devid;
 		$this->_protocolversion = $protocolversion;
-		//TODO: Autenticar Usuario no LDAP
-
 		return true;
 	}
@@ -49,8 +52,5 @@
 
 	function GetMessageList($folderid, $cutoffdate) {
-		$id_owner = $this->parseOwner($this->_user);
-		if ($id_owner == false) return false;
-
-		debugLog('CalendarExpresso::GetMessageList('.$id_owner.')');
+		debugLog('CalendarExpresso::GetMessageList('.$this->_uidnumber.')');
 		if ($folderid != "calendar") return false;
 
@@ -59,6 +59,6 @@
 			$result = pg_query($this->db,"BEGIN;");
 			if ($result == FALSE) throw new Exception(pg_last_error($this->db));
-			if ($cutoffdate == 0) $result = pg_query($this->db, "select c.cal_id, c.last_update, c.datetime, c.cal_type from phpgw_cal c join phpgw_cal_user u on (c.cal_id = u.cal_id) where u.cal_login ='" . $id_owner . "'and c.reference = 0;");
-			else $result = pg_query($this->db, "select c.cal_id, c.last_update, c.datetime, c.cal_type from phpgw_cal c join phpgw_cal_user u on (c.cal_id = u.cal_id) where u.cal_login ='" . $id_owner . "'and c.reference = 0 and c.edatetime > " . $cutoffdate . ";");
+			if ($cutoffdate == 0) $result = pg_query($this->db, "select c.cal_id, c.last_update, c.datetime, c.cal_type from phpgw_cal c join phpgw_cal_user u on (c.cal_id = u.cal_id) where u.cal_login ='" . $this->_uidnumber . "'and c.reference = 0;");
+			else $result = pg_query($this->db, "select c.cal_id, c.last_update, c.datetime, c.cal_type from phpgw_cal c join phpgw_cal_user u on (c.cal_id = u.cal_id) where u.cal_login ='" . $this->_uidnumber . "'and c.reference = 0 and c.edatetime > " . $cutoffdate . ";");
 			if ($result == FALSE) throw new Exception(pg_last_error($this->db));
 			while ($row = pg_fetch_row($result)) {
@@ -88,8 +88,5 @@
 	function GetFolderList() {
 		debugLog('CalendarExpresso::GetFolderList()');
-		$calendars = array();
 		$folder = $this->StatFolder("calendar");
-		$calendars[] = $folder;
-		//return $calendars;
 		return $folder;
 	}
@@ -327,23 +324,4 @@
 		$message = $this->GetMessageDAO($id);
 		return $message;
-
-		//$message->?????  //phpgw_cal.priority (1 - baixa, 2 - normal, 3 - alta) //Quando for criar um registro o valor será 2.
-		//$message->?????  //phpgw_cal.groups (Não vou atribuir nenhum valor)
-		//$message->?????  //phpgw_cal.cal_type (quando for criar um novo registro vou inserir R para Recursivo e E para não recursivo). Quando Alterar um registro entre de Recursivo para não Recursivo e vice-versa vou fazer o mesmo da inclusão. Quando alterar entre dois tipos não recursivos, não faço nada.
-		//$message->?????  //phpgw_cal.ex_participants
-		//$message->?????  //phpgw_cal_user.cal_status
-		//$message->?????  //phpgw_cal_user.cal_type
-		//$message->?????  //phpgw_cal_repeats.recur_interval
-		//$message->?????  //phpgw_cal_repeats.recur_data
-		//$message->?????  //phpgw_cal_repeats.recur_exception
-
-		//$message->timezone  //phpgw?????
-		//$message->organizername //phpgw?????
-		//$message->organizeremail //phpgw????
-		//$message->attendees // phpgw????  (SyncAttendee array)
-
-		//$syncAttendee = new SyncAttendee();
-		//$syncAttendee->email  //phpgw????
-		//$syncAttendee->name   //phpgw????
 	}
 
@@ -351,9 +329,7 @@
 		debugLog('CalendarExpresso::DeleteMessage('.$folderid.', '.$id.', ..)');
 		if (!isset($id)) return false;
-		$id_owner = $this->parseOwner($this->_user);
-		if ($id_owner == false) return false;
 		$result = pg_query($this->db, "select owner from phpgw_cal where cal_id = " . $id . ";");
 		if ($result == FALSE) throw new Exception(pg_last_error($this->db));
-		if ($id_owner != pg_fetch_result($result, 0, 0)) return false;
+		if ($this->_uidnumber != pg_fetch_result($result, 0, 0)) return false;
 		try {
 			$result = pg_query($this->db,"BEGIN;");
@@ -387,6 +363,4 @@
 	function ChangeMessageDAO($id, $message) {
 		debugLog('CalendarExpresso::ChangeMessageDAO('.$id.', ..)');
-		$id_owner = $this->parseOwner($this->_user);
-		if ($id_owner == false) return false;
 		try {
 			$result = pg_query($this->db,"BEGIN;");
@@ -396,17 +370,18 @@
 			$found_cal_repeats = false;
 			if ($id != false) {
-				$result = pg_query($this->db, "select cal_id, cal_type, owner from phpgw_cal where cal_id = " . $id . ";");
+				$result = pg_query($this->db, "select cal_id, cal_type, owner, description from phpgw_cal where cal_id = " . $id . ";");
 				if ($result == FALSE) throw new Exception(pg_last_error($this->db));
 				// tenta localizar cal_id para fazer Update
 				while ($row = pg_fetch_row($result)) {
 					if(isset($row[0])) {
-						if ($id_owner != $row[2]) return false; // Nao atualiza evento de outro proprietario
+						if ($this->_uidnumber != $row[2]) return false; // Nao atualiza evento de outro proprietario
 						$cal_id = $row[0];
 						$cal_type_from_DB = $row[1];
+						$description_from_DB = $row[3];
 						$found_cal_id = true;
 					}
 				}
 				// Verifica se ja existe o registro do evento na tabela phpgw_cal_user
-				$result = pg_query($this->db, "select cal_id, cal_login from phpgw_cal_user where cal_id = " . $cal_id . " and cal_login = '" . $id_owner . "';");
+				$result = pg_query($this->db, "select cal_id, cal_login from phpgw_cal_user where cal_id = " . $cal_id . " and cal_login = '" . $this->_uidnumber . "';");
 				if ($result == FALSE) throw new Exception(pg_last_error($this->db));
 				if ($row = pg_fetch_row($result)) {
@@ -430,5 +405,5 @@
 			}
 			if(isset($message->subject)) {
-				$arrayCal["title"] = $this->truncateString(utf8_decode($message->subject),80);
+				$arrayCal["title"] = $this->truncateString(utf8_decode($message->subject),299);
 			}
 			if(isset($message->location)) {
@@ -454,6 +429,6 @@
 				if ($result_loadrtf == true) $rtf_to_ascii->parse();
 				$arrayCal["description"] = $rtf_to_ascii->out;
-//			} else {
-//				$arrayCal["description"] = '';
+				//			} else {
+				//				$arrayCal["description"] = '';
 			}
 			$arrayCal["category"] = '';
@@ -482,5 +457,5 @@
 				$cal_id = pg_fetch_result($result, 0, 0);
 				$arrayCal["cal_id"] = $cal_id;
-				$arrayCal["owner"] = $id_owner;
+				$arrayCal["owner"] = $this->_uidnumber;
 				if (isset($message->recurrence)) $arrayCal["cal_type"] = 'M';
 				else $arrayCal["cal_type"] = 'E';
@@ -500,5 +475,5 @@
 			if (!$found_cal_user){
 				$arrayCalUser["cal_id"] = $cal_id;
-				$arrayCalUser["cal_login"] = $id_owner;
+				$arrayCalUser["cal_login"] = $this->_uidnumber;
 				//TODO: Tratar os outros valores de cal_status
 				$arrayCalUser["cal_status"] = 'A';
@@ -506,5 +481,5 @@
 				if ($result == FALSE) throw new Exception(pg_last_error($this->db));
 			} else {
-				$result = pg_update($this->db, 'phpgw_cal_user', $arrayCalUser, array('cal_id' => $cal_id, 'cal_login' => $id_owner));
+				$result = pg_update($this->db, 'phpgw_cal_user', $arrayCalUser, array('cal_id' => $cal_id, 'cal_login' => $this->_uidnumber));
 				if ($result == FALSE) throw new Exception(pg_last_error($this->db));
 			}
@@ -574,5 +549,5 @@
 					else $arrayRecur["recur_enddate"] = $message->recurrence->until;
 					date_default_timezone_set($tz);
-					/*					//$arrayRecur["recur_enddate"] = $message->recurrence->until - $offsetTZ;
+					/*$arrayRecur["recur_enddate"] = $message->recurrence->until - $offsetTZ;
 					 $hour = date("G", $message->starttime - (($tz["bias"] - $tz["dstbias"]) * 60));
 					 $min = date("i", $message->starttime - (($tz["bias"] - $tz["dstbias"]) * 60));
@@ -586,8 +561,6 @@
 				// Trata excecoes da recorrencia
 				if (isset($message->exceptions)){
-					//if ($recur_exception_changed_starttimes != "") {
-					//Tem Excecoes de recorrencia do tipo Edicao
+					// Tem Excecoes de recorrencia do tipo Edicao
 					// Verifica se ja existe o registro do evento de excecao de recorrencia na tabela phpgw_cal
-					//foreach ($array_recur_exception_changed_starttime as $except_starttime) {
 					$recur_exception_changed_ids = "";
 					$recur_exception_deleted_starttimes = "";
@@ -599,7 +572,8 @@
 							if (isset($except_cal_id)) unset($except_cal_id);
 							if (isset($except_cal_type_from_DB)) unset($except_cal_type_from_DB);
+							if (isset($except_description_from_DB)) unset($except_description_from_DB);
 							$found_except_cal_id = false;
 							$found_except_cal_user = false;
-							$result = pg_query($this->db, "select cal_id, cal_type from phpgw_cal where reference = " . $id . " and datetime = " . $recur_exception->exceptionstarttime . ";");
+							$result = pg_query($this->db, "select cal_id, cal_type, description from phpgw_cal where reference = " . $id . " and datetime = " . $recur_exception->exceptionstarttime . ";");
 							if ($result == FALSE) throw new Exception(pg_last_error($this->db));
 							// tenta localizar cal_id para fazer Update
@@ -608,4 +582,5 @@
 									$except_cal_id = $row[0];
 									$except_cal_type_from_DB = $row[1];
+									$except_description_from_DB = $row[2];
 									$found_except_cal_id = true;
 								}
@@ -613,5 +588,5 @@
 							// Verifica se ja existe o registro do evento de excecao de recorrencia na tabela phpgw_cal_user
 							if (isset($except_cal_id)) {
-								$result = pg_query($this->db, "select cal_id, cal_login from phpgw_cal_user where cal_id = " . $except_cal_id . " and cal_login = '" . $id_owner . "';");
+								$result = pg_query($this->db, "select cal_id, cal_login from phpgw_cal_user where cal_id = " . $except_cal_id . " and cal_login = '" . $this->_uidnumber . "';");
 								if ($result == FALSE) throw new Exception(pg_last_error($this->db));
 								if ($row = pg_fetch_row($result)) {
@@ -627,7 +602,7 @@
 							}
 							if(isset($recur_exception->subject)) {
-								$arrayExceptCal["title"] = $this->truncateString(utf8_decode($recur_exception->subject),80);
+								$arrayExceptCal["title"] = $this->truncateString(utf8_decode($recur_exception->subject),299);
 							} elseif(isset($message->subject)) {
-								$arrayExceptCal["title"] = $this->truncateString(utf8_decode($message->subject),80);
+								$arrayExceptCal["title"] = $this->truncateString(utf8_decode($message->subject),299);
 							}
 							if(isset($recur_exception->location)) {
@@ -658,13 +633,16 @@
 								$arrayExceptCal["is_public"] = 1; // 1 - Normal
 							}else $arrayExceptCal["is_public"] = 0; // 0 - Privado
-							if(isset($recur_exception->rtf) or isset($message->rtf)) {
-								$rtf_to_ascii = new rtf();
-								$rtf_to_ascii->output("ascii");
-								if(isset($recur_exception->rtf)) $result_loadrtf = $rtf_to_ascii->loadrtf(base64_decode($recur_exception->rtf));
-								elseif(isset($message->rtf)) $result_loadrtf = $rtf_to_ascii->loadrtf(base64_decode($message->rtf));
-								if ($result_loadrtf == true) $rtf_to_ascii->parse();
-								$arrayExceptCal["description"] = $rtf_to_ascii->out;
-				//			} else {
-				//				$arrayExceptCal["description"] = '';
+							if (isset($recur_exception->body)) {
+								$arrayExceptCal["description"] = utf8_decode($recur_exception->body);
+							} elseif (!isset($except_description_from_DB)) {
+								if (isset($message->rtf)) {
+									$rtf_to_ascii = new rtf();
+									$rtf_to_ascii->output("ascii");
+									$result_loadrtf = $rtf_to_ascii->loadrtf(base64_decode($message->rtf));
+									if ($result_loadrtf == true) $rtf_to_ascii->parse();
+									$arrayExceptCal["description"] = $rtf_to_ascii->out;
+								} elseif (isset($description_from_DB)) {
+									$arrayExceptCal["description"] = utf8_decode($description_from_DB);
+								}
 							}
 							$arrayExceptCal["category"] = '';
@@ -701,5 +679,5 @@
 								$except_cal_id = pg_fetch_result($result, 0, 0);
 								$arrayExceptCal["cal_id"] = $except_cal_id;
-								$arrayExceptCal["owner"] = $id_owner;
+								$arrayExceptCal["owner"] = $this->_uidnumber;
 								$arrayExceptCal["cal_type"] = 'E';
 								$result = pg_insert($this->db, 'phpgw_cal', $arrayExceptCal);
@@ -714,5 +692,5 @@
 							if (!$found_except_cal_user){
 								$arrayExceptCalUser["cal_id"] = $except_cal_id;
-								$arrayExceptCalUser["cal_login"] = $id_owner;
+								$arrayExceptCalUser["cal_login"] = $this->_uidnumber;
 								//TODO: Tratar os outros valores de cal_status
 								$arrayExceptCalUser["cal_status"] = 'A';
@@ -720,5 +698,5 @@
 								if ($result == FALSE) throw new Exception(pg_last_error($this->db));
 							} else {
-								$result = pg_update($this->db, 'phpgw_cal_user', $arrayExceptCalUser, array('cal_id' => $except_cal_id, 'cal_login' => $id_owner));
+								$result = pg_update($this->db, 'phpgw_cal_user', $arrayExceptCalUser, array('cal_id' => $except_cal_id, 'cal_login' => $this->_uidnumber));
 								if ($result == FALSE) throw new Exception(pg_last_error($this->db));
 							}
@@ -805,6 +783,4 @@
 	function addCategory($category) {
 		$cat_id = false;
-		$id_owner = $this->parseOwner($this->_user);
-		if ($id_owner == false) return false;
 		try {
 			$result = pg_query($this->db,"BEGIN;");
@@ -813,5 +789,5 @@
 			if ($result == FALSE) throw new Exception(pg_last_error($this->db));
 			if (!($cat_id = pg_fetch_result($result, 0, 0))){
-				$result = pg_query("SELECT cat_id from phpgw_categories WHERE cat_owner = " . $id_owner . " AND cat_appname = 'calendar' AND LOWER(to_ASCII(cat_name)) = '" . trim(strtolower($this->removeAccents(utf8_decode($category)))) . "';");
+				$result = pg_query("SELECT cat_id from phpgw_categories WHERE cat_owner = " . $this->_uidnumber . " AND cat_appname = 'calendar' AND LOWER(to_ASCII(cat_name)) = '" . trim(strtolower($this->removeAccents(utf8_decode($category)))) . "';");
 				if ($result == FALSE) throw new Exception(pg_last_error($this->db));
 				if (!($cat_id = pg_fetch_result($result, 0, 0))){
@@ -820,5 +796,5 @@
 					$cat_id = pg_fetch_result($result, 0, 0);
 					$arrayCat["cat_id"] = $cat_id;
-					$arrayCat["cat_owner"] = $id_owner;
+					$arrayCat["cat_owner"] = $this->_uidnumber;
 					$arrayCat["cat_access"] = 'public';
 					$arrayCat["cat_appname"] = 'calendar';
@@ -851,5 +827,4 @@
 		$data = str_replace("\r", "\n", $data);
 		$data = str_replace(array('\\', ';', ',', "\n"), array('\\\\', '\\;', '\\,', '\\n'), $data);
-		//return u2wi($data);
 		return $data;
 	}
@@ -871,15 +846,15 @@
 	}
 
-	function parseOwner($id_owner)
+	function parseUser($id_user)
 	{
-		$pos = strripos($id_owner, '\\');
+		$pos = strripos($id_user, '\\');
 		if ($pos === false) {
-			if (strlen($id_owner) <= 2) return false;
-			else return substr($id_owner, 0, strlen($id_owner)-2);
+			if (strlen($id_user) < 1) return false;
+			else return $id_user;
 		} else {
-			if (strlen($id_owner) <= $pos + 3) {
+			if (strlen($id_user) <= $pos + 1) {
 				return false;
 			} else {
-				return substr(substr($id_owner, $pos + 1), 0, strlen(substr($id_owner, $pos + 1))-2);
+				return substr(substr($id_user, $pos + 1), 0, strlen(substr($id_user, $pos + 1)));
 			}
 		}
@@ -916,4 +891,14 @@
 		return $packed;
 	}
+
+	// Authenticate user and return UIDNumber attribute on success
+	function authUser($user, $pwd) {
+		$ldap = new AuthLDAP();
+		$uid_number = ($ldap->bind($user,$pwd));
+		$ldap->disconnect();
+		unset($ldap);
+		if (! $uid_number) return false;
+		return $uid_number;
+	}
 };
 ?>
Index: contrib/z-push/backend/BackendContactsExpresso.php
===================================================================
--- contrib/z-push/backend/BackendContactsExpresso.php	(revision 3637)
+++ contrib/z-push/backend/BackendContactsExpresso.php	(revision 4000)
@@ -11,13 +11,12 @@
  * Consult LICENSE file for details
  ************************************************/
-include_once('diffbackend.php');
-include_once('include/z_RTF.php');
-include_once "include/dbconnect.php";
+require_once("diffbackend.php");
+require_once("include/z_RTF.php");
+require_once("include/dbconnect.php");
+require_once("include/authldap.php");
 
 class BackendContactsExpresso extends BackendDiff {
-	var $_user;
-	var $_devid;
-	var $_protocolversion;
 	var $db;
+	var $_uidnumber;
 
 	function __construct()
@@ -26,7 +25,13 @@
 
 		if (!$this->db) {
-			echo "A DB connect error occured.\n";
+			echo "Erro de conexao com o Banco.\n";
 			exit;
 		}
+	}
+
+	function Logon($username, $domain, $password) {
+		$this->_uidnumber = $this->authUser($this->parseUser($username), $password);
+		if(! $this->_uidnumber) return false;
+		else return true;
 	}
 
@@ -35,5 +40,4 @@
 		$this->_devid = $devid;
 		$this->_protocolversion = $protocolversion;
-		//TODO: Autenticar Usuario no LDAP
 
 		return true;
@@ -49,8 +53,5 @@
 
 	function GetMessageList($folderid, $cutoffdate) {
-		$id_owner = $this->parseOwner($this->_user);
-		if ($id_owner == false) return false;
-
-		debugLog('ContactsExpresso::GetMessageList('.$id_owner.')');
+		debugLog('ContactsExpresso::GetMessageList('.$this->_uidnumber.')');
 		$messages = array();
 		$ids = array();
@@ -58,5 +59,5 @@
 			$result = pg_query($this->db,"BEGIN;");
 			if ($result == FALSE) throw new Exception(pg_last_error($this->db));
-			$result = pg_query($this->db, "select given_names, family_names, last_update, id_contact from phpgw_cc_contact where id_owner = " . $id_owner . ";");
+			$result = pg_query($this->db, "select given_names, family_names, last_update, id_contact from phpgw_cc_contact where id_owner = " . $this->_uidnumber . ";");
 			if ($result == FALSE) throw new Exception(pg_last_error($this->db));
 			while ($row = pg_fetch_row($result)) {
@@ -78,9 +79,6 @@
 	function GetFolderList() {
 		debugLog('ContactsExpresso::GetFolderList()');
-		$contacts = array();
 		$folder = $this->StatFolder("root");
-		$contacts[] = $folder;
 		return $folder;
-		//return $contacts;
 	}
 
@@ -117,7 +115,4 @@
 		debugLog('ContactsExpresso::StatMessage('.$folderid.', '.$id.')');
 		if($folderid != "root") return false;
-
-		$id_owner = $this->parseOwner($this->_user);
-		if ($id_owner == false) return false;
 
 		try {
@@ -149,7 +144,4 @@
 
 		// Parse the database into object
-		$id_owner = $this->parseOwner($this->_user);
-		if ($id_owner == false) return;
-
 		$message = new SyncContact();
 		try {
@@ -354,7 +346,4 @@
 		debugLog('ContactsExpresso::DeleteMessage('.$folderid.', '.$id.', ..)');
 
-		$id_owner = $this->parseOwner($this->_user);
-		if ($id_owner == false) return false;
-
 		$result = pg_query($this->db,"BEGIN;");
 		try {
@@ -416,6 +405,4 @@
 		debugLog('ContactsExpresso::ChangeMessage('.$folderid.', '.$id.', ..)');
 
-		$id_owner = $this->parseOwner($this->_user);
-		if ($id_owner == false) return false;
 		try {
 			$result = pg_query($this->db,"BEGIN;");
@@ -666,5 +653,5 @@
 			if (!$found_id_contact){
 				$arrayContact["id_contact"] = $id_contact;
-				$arrayContact["id_owner"] = $id_owner;
+				$arrayContact["id_owner"] = $this->_uidnumber;
 				$result = pg_insert($this->db, 'phpgw_cc_contact', $arrayContact);
 				if ($result == FALSE) throw new Exception(pg_last_error($this->db));
@@ -1032,5 +1019,5 @@
 				if ($result == FALSE) throw new Exception(pg_last_error($this->db));
 			}
-			
+
 			//TODO : Permitir mais de um número de telefone para Trabalho, Celular e Casa. O Expresso ainda não suporta isso :(
 
@@ -1068,5 +1055,4 @@
 		$data = str_replace("\r", "\n", $data);
 		$data = str_replace(array('\\', ';', ',', "\n"), array('\\\\', '\\;', '\\,', '\\n'), $data);
-		//return u2wi($data);
 		return $data;
 	}
@@ -1088,17 +1074,27 @@
 	}
 
-	function parseOwner($id_owner)
+	function parseUser($id_user)
 	{
-		$pos = strripos($id_owner, '\\');
+		$pos = strripos($id_user, '\\');
 		if ($pos === false) {
-			if (strlen($id_owner) <= 2) return false;
-			else return substr($id_owner, 0, strlen($id_owner)-2);
+			if (strlen($id_user) < 1) return false;
+			else return $id_user;
 		} else {
-			if (strlen($id_owner) <= $pos + 3) {
+			if (strlen($id_user) <= $pos + 1) {
 				return false;
 			} else {
-				return substr(substr($id_owner, $pos + 1), 0, strlen(substr($id_owner, $pos + 1))-2);
+				return substr(substr($id_user, $pos + 1), 0, strlen(substr($id_user, $pos + 1)));
 			}
 		}
+	}
+
+	// Authenticate user and return UIDNumber attribute on success
+	function authUser($user, $pwd) {
+		$ldap = new AuthLDAP();
+		$uid_number = ($ldap->bind($user,$pwd));
+		$ldap->disconnect();
+		unset($ldap);
+		if (! $uid_number) return false;
+		return $uid_number;
 	}
 };
Index: contrib/z-push/config.php
===================================================================
--- contrib/z-push/config.php	(revision 3637)
+++ contrib/z-push/config.php	(revision 4000)
@@ -79,5 +79,5 @@
     //        'domain'    - the value of the "domain" field is used
     //        '@mydomain.com' - the username is used and the given string will be appended
-    define('IMAP_DEFAULTFROM', '');
+    define('IMAP_DEFAULTFROM', 'domain');
     // copy outgoing mail to this folder. If not set z-push will try the default folders
     define('IMAP_SENTFOLDER', 'INBOX/Sent');
@@ -95,3 +95,26 @@
     define('VCARDDIR_DIR', '/var/www/vcf');
 
+    // ****************************************************
+    //	LDAP Authentication settings
+    // ****************************************************    
+    // Set USER and PASSWORD if you are not using anonymous bind
+    // Must have read access to DN, UID and UIDNUMBER of all users
+	define("ANONYMOUS_BIND", false);
+	define("LDAP_BIND_USER", "cn=admin,ou=expressolivre,ou=corp,dc=empresa,dc=gov,dc=br");
+	define("LDAP_BIND_PASSWORD", "senha_do_admin");
+    
+	define("LDAP_HOST", "ldap://10.200.112.132/"); // Address of your LDAP server
+	define("LDAP_PORT", "389"); // Port of your LDAP server
+
+	// Search base & filter
+	define("LDAP_SEARCH_BASE", "dc=empresa,dc=gov,dc=br"); // Base path to search the filter. Example: dc=company,dc=com
+	define("LDAP_SEARCH_FILTER", "uid=SEARCHVALUE"); // The filter is the user login attribute. You can change only the "uid" by other attribute. The SEARCHVALUE string is replaced by the user login inside the backends.
+
+	// LDAP field mapping.
+	global $ldap_field_map;
+	$ldap_field_map = array(
+						DN						=> 'dn', // Change 'dn' only if you use other attribute name in your LDAP.
+        	            UID						=> 'uid', // Change 'uid' only if you use other attribute name in your LDAP.
+    	                UIDNUMBER				=> 'uidnumber', // Change 'uidnumber' only if you use other attribute name in your LDAP.
+   	             );
 ?>
