diff --git a/files/webdav.php b/files/webdav.php
index a59dee70c2ed65f7cdcbb503ba71e6bc3992777f..b1d242b2cc9017f5309cef378e7e4b1e0d2d8d78 100644
--- a/files/webdav.php
+++ b/files/webdav.php
@@ -27,26 +27,21 @@
 $RUNTIME_NOSETUPFS = true;
 
 require_once('../lib/base.php');
-require_once('Sabre/autoload.php');
+
+// Backends
+$authBackend = new OC_Connector_Sabre_Auth();
+$lockBackend = new OC_Connector_Sabre_Locks();
 
 // Create ownCloud Dir
 $publicDir = new OC_Connector_Sabre_Directory('');
-$server = new Sabre_DAV_Server($publicDir);
 
-// Path to our script
+// Fire up server
+$server = new Sabre_DAV_Server($publicDir);
 $server->setBaseUri($WEBROOT.'/files/webdav.php');
 
-// Auth backend
-$authBackend = new OC_Connector_Sabre_Auth();
-$authPlugin = new Sabre_DAV_Auth_Plugin($authBackend,'ownCloud');
-$server->addPlugin($authPlugin);
-
-// Also make sure there is a 'data' directory, writable by the server. This directory is used to store information about locks
-$lockBackend = new OC_Connector_Sabre_Locks();
-$lockPlugin = new Sabre_DAV_Locks_Plugin($lockBackend);
-$server->addPlugin($lockPlugin);
+// Load plugins
+$server->addPlugin(new Sabre_DAV_Auth_Plugin($authBackend,'ownCloud'));
+$server->addPlugin(new Sabre_DAV_Locks_Plugin($lockBackend));
 
 // And off we go!
 $server->exec();
-
-?>
diff --git a/lib/base.php b/lib/base.php
index b2c5bd323146ffcc194cba4c1a0c856d065691c0..e9451c45b6162cc22f714b350e4dc2f891485137 100644
--- a/lib/base.php
+++ b/lib/base.php
@@ -22,6 +22,8 @@
 
 /**
  * Class that is a namespace for all global OC variables
+ * No, we can not put this class in its own file because it is used by
+ * OC_autoload!
  */
 class OC{
 	/**
@@ -52,19 +54,22 @@ class OC{
 	 * TODO: What's this for?
 	 */
 	public static $CONFIG_DATADIRECTORY_ROOT = '';
-}
 
-// Get rid of this stupid require_once OC_...
-function OC_autoload($className){
-	if(array_key_exists($className,OC::$CLASSPATH)){
-		require_once OC::$CLASSPATH[$className];
-	}
-	elseif(strpos($className,'OC_')===0){
-		require_once strtolower(str_replace('_','/',substr($className,3)) . '.php');
+	/**
+	 * SPL autoload
+	 */
+	public static function autoload($className){
+		if(array_key_exists($className,OC::$CLASSPATH)){
+			require_once OC::$CLASSPATH[$className];
+		}
+		elseif(strpos($className,'OC_')===0){
+			require_once strtolower(str_replace('_','/',substr($className,3)) . '.php');
+		}
 	}
 }
 
-spl_autoload_register('OC_autoload');
+// this requires all our OC_* classes
+spl_autoload_register(array('OC','autoload'));
 
 // set some stuff
 //ob_start();
@@ -94,6 +99,9 @@ if($WEBROOT!='' and $WEBROOT[0]!=='/'){
 // set the right include path
 set_include_path($SERVERROOT.'/lib'.PATH_SEPARATOR.$SERVERROOT.'/config'.PATH_SEPARATOR.$SERVERROOT.'/3dparty'.PATH_SEPARATOR.get_include_path().PATH_SEPARATOR.$SERVERROOT);
 
+//Some libs we really depend on
+require_once('Sabre/autoload.php');
+
 // define runtime variables - unless this already has been done
 if( !isset( $RUNTIME_NOSETUPFS )){
 	$RUNTIME_NOSETUPFS = false;
@@ -150,6 +158,10 @@ if(!$error and !$RUNTIME_NOSETUPFS ){
 	OC_Util::setupFS();
 }
 
+// Last part: connect some hooks
+OC_HOOK::connect('OC_User', 'post_createUser', 'OC_Connector_Sabre_Principal', 'addPrincipal');
+OC_HOOK::connect('OC_User', 'post_deleteUser', 'OC_Connector_Sabre_Principal', 'deletePrincipal');
+
 
 // FROM Connect.php
 function OC_CONNECT_TEST($path,$user,$password){
diff --git a/lib/connector/sabre/principal.php b/lib/connector/sabre/principal.php
new file mode 100644
index 0000000000000000000000000000000000000000..b3070087fd7f89d41633b218e5602c9317634120
--- /dev/null
+++ b/lib/connector/sabre/principal.php
@@ -0,0 +1,181 @@
+<?php
+
+class OC_Connector_Sabre_Principal implements Sabre_DAVACL_IPrincipalBackend {
+	/**
+	 * TODO: write doc
+	 */
+	public static function addPrincipal($params){
+		// Add the user
+		$uri = 'principals/'.$params['uid'];
+		$displayname = $params['uid'];
+		$query = OC_DB::prepare('INSERT INTO *PREFIX*principals (uri,displayname) VALUES(?,?)');
+		$query->execute(array($uri,$displayname));
+		
+		// Add calendar and addressbook read and write support (sharing calendars)
+		$uri = 'principals/'.$params['uid'].'/calendar-proxy-read';
+		$displayname = null;
+		$query->execute(array($uri,$displayname));
+		$uri = 'principals/'.$params['uid'].'/calendar-proxy-write';
+		$query->execute(array($uri,$displayname));
+		$uri = 'principals/'.$params['uid'].'/addressbook-proxy-read';
+		$query->execute(array($uri,$displayname));
+		$uri = 'principals/'.$params['uid'].'/addressbook-proxy-write';
+		$query->execute(array($uri,$displayname));
+
+		return true;
+	}
+	
+	/**
+	 * TODO: write doc
+	 */
+	public static function deletePrincipal($params){
+		$query = OC_DB::prepare('SELECT * FROM *PREFIX*principals');
+		$result = $query->execute();
+
+		$deleteprincipal = OC_DB::prepare('DELETE FROM *PREFIX*principals WHERE id = ?');
+		$deletegroup = OC_DB::prepare('DELETE FROM *PREFIX*principalgroups WHERE principal_id = ? OR member_id = ?');
+		// We have to delete the principals and relations! Principals include 
+		while($row = $result->fetchRow()){
+			// Checking if the principal is in the prefix
+			list($rowPrefix,$rowUser) = Sabre_DAV_URLUtil::splitPath($row['uri']);
+			if ($rowUser !== $params['uid']) continue;
+			$deleteprincipal->execute(array($row['id']));
+			$deletegroup->execute(array($row['id'],$row['id']));
+		}
+		return true;
+	}
+	/**
+	 * Returns a list of principals based on a prefix.
+	 *
+	 * This prefix will often contain something like 'principals'. You are only
+	 * expected to return principals that are in this base path.
+	 *
+	 * You are expected to return at least a 'uri' for every user, you can
+	 * return any additional properties if you wish so. Common properties are:
+	 *   {DAV:}displayname
+	 *
+	 * @param string $prefixPath
+	 * @return array
+	 */
+	public function getPrincipalsByPrefix( $prefixPath ){
+		$query = OC_DB::prepare('SELECT * FROM *PREFIX*principals');
+		$result = $query->execute();
+
+		$principals = array();
+
+		while($row = $result->fetchRow()){
+			// Checking if the principal is in the prefix
+			list($rowPrefix) = Sabre_DAV_URLUtil::splitPath($row['uri']);
+			if ($rowPrefix !== $prefixPath) continue;
+
+			$principals[] = array(
+				'uri' => $row['uri'],
+				'{DAV:}displayname' => $row['displayname']?$row['displayname']:basename($row['uri'])
+			);
+
+		}
+
+		return $principals;
+	}
+
+	/**
+	 * Returns a specific principal, specified by it's path.
+	 * The returned structure should be the exact same as from
+	 * getPrincipalsByPrefix.
+	 *
+	 * @param string $path
+	 * @return array
+	 */
+	public function getPrincipalByPath($path) {
+		$query = OC_DB::prepare('SELECT * FROM *PREFIX*principals WHERE uri=?');
+		$result = $query->execute(array($path));
+
+		$users = array();
+
+		$row = $result->fetchRow();
+		if (!$row) return;
+
+		return array(
+			'id'  => $row['id'],
+			'uri' => $row['uri'],
+			'{DAV:}displayname' => $row['displayname']?$row['displayname']:basename($row['uri'])
+		);
+
+	}
+
+	/**
+	 * Returns the list of members for a group-principal
+	 *
+	 * @param string $principal
+	 * @return array
+	 */
+	public function getGroupMemberSet($principal) {
+		$principal = $this->getPrincipalByPath($principal);
+		if (!$principal) throw new Sabre_DAV_Exception('Principal not found');
+
+		$query = OC_DB::prepare('SELECT principals.uri as uri FROM *PREFIX*principalgroups AS groupmembers LEFT JOIN *PREFIX*principals AS principals ON groupmembers.member_id = principals.id WHERE groupmembers.principal_id = ?');
+		$result = $query->execute(array($principal['id']));
+	
+		$return = array();
+		while ($row = $result->fetchRow()){
+			$return[] = $row['uri'];
+		}
+		return $return;
+	}
+
+	/**
+	 * Returns the list of groups a principal is a member of
+	 *
+	 * @param string $principal
+	 * @return array
+	 */
+	public function getGroupMembership($principal) {
+		$principal = $this->getPrincipalByPath($principal);
+		if (!$principal) throw new Sabre_DAV_Exception('Principal not found');
+
+		$query = OC_DB::prepare('SELECT principals.uri as uri FROM *PREFIX*principalgroups AS groupmembers LEFT JOIN *PREFIX*principals AS principals ON groupmembers.member_id = principals.id WHERE groupmembers.member_id = ?');
+		$result = $query->execute(array($principal['id']));
+
+		$return = array();
+		while ($row = $result->fetchRow()){
+			$return[] = $row['uri'];
+		}
+		return $return;
+	}
+
+	/**
+	 * Updates the list of group members for a group principal.
+	 *
+	 * The principals should be passed as a list of uri's.
+	 *
+	 * @param string $principal
+	 * @param array $members
+	 * @return void
+	 */
+	public function setGroupMemberSet($principal, array $members) {
+		$query = OC_DB::prepare('SELECT id, uri FROM *PREFIX*principals WHERE uri IN (? '.str_repeat(', ?', count($members)).')');
+		$result = $query->execute(array_merge(array($principal), $members));
+
+		$memberIds = array();
+		$principalId = null;
+
+		while($row = $$result->fetchRow()) {
+			if ($row['uri'] == $principal) {
+				$principalId = $row['id'];
+			}
+			else{
+				$memberIds[] = $row['id'];
+			}
+		}
+		if (!$principalId) throw new Sabre_DAV_Exception('Principal not found');
+
+		// Wiping out old members
+		$query = OC_DB::prepare('DELETE FROM *PREFIX*principalgroups WHERE principal_id = ?');
+		$query->execute(array($principalID));
+
+		$query = OC_DB::prepare('INSERT INTO *PREFIX*principalgroups (principal_id, member_id) VALUES (?, ?);');
+		foreach($memberIds as $memberId) {
+			$query->execute(array($principalId, $memberId));
+		}
+	}
+}
diff --git a/lib/template.php b/lib/template.php
index fe173f609b21b63f8cb915cd359ac3b2e4fff997..045ecdaf13086828304cfc533fda07577ad220cd 100644
--- a/lib/template.php
+++ b/lib/template.php
@@ -320,6 +320,28 @@ class OC_Template{
 		return $data;
 	}
 
+	/**
+	 * @brief Include template
+	 * @returns returns content of included template
+	 *
+	 * Includes another template. use <?php echo $this->inc('template'); ?> to
+	 * do this.
+	 */
+	public function inc( $file )
+	{
+		// $_ erstellen
+		$_ = $this->vars;
+
+		// Einbinden
+		ob_start();
+		include( $this->path.'/'.$file.'.php' );
+		$data = ob_get_contents();
+		ob_end_clean();
+
+		// Daten zurückgeben
+		return $data;
+	}
+
 	/**
 	 * @brief Shortcut to print a simple page for users
 	 * @param $application The application we render the template for