remotestoragefw/webdavaccessplugin/src/rsfwdavsession.cpp
changeset 0 3ad9d5175a89
--- /dev/null	Thu Jan 01 00:00:00 1970 +0000
+++ b/remotestoragefw/webdavaccessplugin/src/rsfwdavsession.cpp	Thu Dec 17 09:07:59 2009 +0200
@@ -0,0 +1,1322 @@
+/*
+* Copyright (c) 2002-2004 Nokia Corporation and/or its subsidiary(-ies).
+* All rights reserved.
+* This component and the accompanying materials are made available
+* under the terms of "Eclipse Public License v1.0"
+* which accompanies this distribution, and is available
+* at the URL "http://www.eclipse.org/legal/epl-v10.html".
+*
+* Initial Contributors:
+* Nokia Corporation - initial contribution.
+*
+* Contributors:
+*
+* Description:  API for WebDAV operations
+ *
+*/
+
+
+// INCLUDE FILES
+#include <httpstringconstants.h>
+#include <http/rhttpheaders.h>
+#include <escapeutils.h>
+#include <xml/matchdata.h>
+
+#include "rsfwdavsession.h"
+#include "rsfwdavtransaction.h"
+#include "rsfwconnectionmanager.h"
+#include "rsfwpropfindparser.h"
+#include "rsfwlockqueryparser.h"
+#include "mdebug.h"
+
+// CONSTANTS
+// characters that will be encoded in the url
+_LIT8(KSpecials8, " \"<>#%{}|\\^~[]`");
+
+// ============================ MEMBER FUNCTIONS ==============================
+CRsfwDavSession* CRsfwDavSession::NewL(
+    MRsfwDavResponseObserver* aWebDavResponseObserver,
+    MRsfwConnectionObserver* aRsfwConnectionObserver)
+    {
+    CRsfwDavSession* self = new (ELeave) CRsfwDavSession;
+    CleanupStack::PushL(self);
+    self->ConstructL(aWebDavResponseObserver, aRsfwConnectionObserver);
+    CleanupStack::Pop(self);
+    return self;
+    }
+
+void CRsfwDavSession::ConstructL(
+    MRsfwDavResponseObserver* aWebDavResponseObserver,
+    MRsfwConnectionObserver* aRsfwConnectionObserver)
+    {
+    DEBUGSTRING(("DavSess: ConstructL: enter"));
+    User::LeaveIfError(iFs.Connect());
+    iWebDavResponseObserver = aWebDavResponseObserver;
+    iRsfwConnectionObserver = aRsfwConnectionObserver;
+
+    // Create classes needed for parsing PropFind and Lock request replies
+    // Creating these later seems to cause emulator hang-ups.
+    // If the problem does not exist in the real device we may want to
+    // delay especially Lock parser creation as locking may not be used at all.
+    Xml::CMatchData* matchData = Xml::CMatchData::NewLC();
+	matchData->SetMimeTypeL(KTextXml);
+	// Select libxml2 parsesr
+	matchData->SetVariantL(_L8("libxml2"));
+	// Select Symbian XML Parser (=Expat)
+//	matchData->SetVariantL(_L8("Symbian"));
+    iPropFindParserImpl = CRsfwPropFindParser::NewL();
+    iPropFindParser = Xml::CParser::NewL(*matchData, *iPropFindParserImpl);
+    iLockQueryParserImpl = CRsfwLockQueryParser::NewL();
+    iLockQueryParser = Xml::CParser::NewL(*matchData, *iLockQueryParserImpl);
+    CleanupStack::PopAndDestroy(matchData);
+
+    // Open the RHTTPSession
+    iHttpSession.OpenL();
+    iHttpSession.FilterCollection().RemoveFilter( 
+            iHttpSession.StringPool().StringF( HTTP::EAuthentication, RHTTPSession::GetTable() ));
+    // Install this class as the callback for authentication requests:
+    // it will take care of basic/digest auth, SSL
+    InstallAuthenticationL(iHttpSession);
+    DEBUGSTRING(("auth filter installed"));
+    }
+
+CRsfwDavSession::~CRsfwDavSession()
+    {
+    DEBUGSTRING(("CRsfwDavSession::~CRsfwDavSession"));
+    delete iPropFindParser;
+    delete iPropFindParserImpl;
+    delete iLockQueryParser;
+    delete iLockQueryParserImpl;
+    delete iEncodedHost;
+    if (iUserName) 
+    {
+    	delete iUserName;	
+    }
+    if (iPassword) 
+    {
+    	delete iPassword;
+    }
+  	iHttpSession.Close();
+  	delete iRsfwConnectionManager;
+    iFs.Close();
+    }
+
+// ----------------------------------------------------------------------------
+// CRsfwDavSession::SetConnected
+// ----------------------------------------------------------------------------
+//
+void CRsfwDavSession::SetConnected(TBool aConnected)
+    {
+    iConnected = aConnected;
+    }
+
+// ----------------------------------------------------------------------------
+// CRsfwDavSession::SetWebDavSupportClass
+// ----------------------------------------------------------------------------
+//
+void CRsfwDavSession::SetWebDavSupportClass(TInt aWebDavSupportClass)
+    {
+    iWebDavSupportClass = aWebDavSupportClass;
+    }
+    
+// ----------------------------------------------------------------------------
+// CRsfwDavSession::WebDavSupportClass
+// ----------------------------------------------------------------------------
+//
+TInt CRsfwDavSession::WebDavSupportClass()
+    {
+    return iWebDavSupportClass;
+    }
+
+
+// ----------------------------------------------------------------------------
+// CRsfwDavSession::OpenL
+// After calling this function, use options query
+// to trigger TCP level connection.
+// ----------------------------------------------------------------------------
+//
+void CRsfwDavSession::OpenL(const TDesC& aUri,
+                           TInt aPort,
+                           const TDesC& aUserName,
+                           const TDesC& aPassword,
+                           const TDesC& aAuxData)
+    {
+    // Store connection parameters
+    iHost.Zero();
+    iDavRoot.Zero();
+
+    // Here we add the port using a simple approach:
+    // it needs to go after http://name/
+    TInt slashCnt = 0;
+    TInt cnt = 0;
+    while (cnt < aUri.Length())
+        {
+        TChar ch = aUri[cnt++];
+        if (ch == '/')
+            {
+            slashCnt++;
+            if (slashCnt == 3)
+                {
+                iHost.Append(':');
+                iHost.AppendNum(aPort);
+                // At this point we know that
+                // the remainder of the uri is the root directory
+                }  
+            }
+
+        if (slashCnt > 2)
+            {
+            iDavRoot.Append(ch);
+            }
+        else
+            {
+            iHost.Append(ch);
+            }
+        }
+    // We elso need an encoded form of the host part
+    iEncodedHost = EncodeL(iHost.Right(iHost.Length() - KProtocolPrefix));
+
+    // iDavRoot must be a directory, and thus should end with a slash
+    Slashify(iDavRoot);
+
+    // Make the pair
+    iHostRoot.Copy(iHost);
+    iHostRoot.Append(iDavRoot);
+
+    // Assume that the parameters are constant and stable across the session
+    iUserName = EncodeL(aUserName);
+    iPassword = EncodeL(aPassword);
+    iAuxData.Copy(aAuxData);
+
+    DEBUGSTRING16(("connecting to host='%S', port=%d, root='%S', data=%S",
+                   &iHost,
+                   aPort,
+                   &iDavRoot,
+                   &iAuxData));
+
+   if (iAuxData.Length() == 0) 
+   {
+   		// in case of empty access point info, set it to '?' (ask user)
+   		_LIT(KAskUser, "?");
+   		iAuxData.Copy(KAskUser);
+   }
+   
+   if (!iRsfwConnectionManager)
+   		{
+        iRsfwConnectionManager =
+             CRsfwConnectionManager::NewL(iRsfwConnectionObserver);
+        iRsfwConnectionManager->UseIapL(aAuxData);
+        }
+        
+    }
+
+// ----------------------------------------------------------------------------
+// CRsfwDavSession::OptionsL
+// ----------------------------------------------------------------------------
+//
+CRsfwDavTransaction* CRsfwDavSession::OptionsL()
+    {
+    TPtrC null;
+    TUriParser8 uriParser;
+    HBufC8* uri = BuildUriLC(null, EFalse, &uriParser);
+
+    DEBUGSTRING8(("OPTIONS '%S'", &uriParser.UriDes()));
+
+    // Establish a link-layer connection
+    if (iRsfwConnectionManager)
+        {
+        SetupConnectionL();
+        }
+
+    RStringPool stringPool = StringPool();
+
+    // Introducing the webdav headers for the propfind
+    RStringF mOptions = stringPool.OpenFStringL(KWebDavOptions);
+    CleanupClosePushL(mOptions);
+    CRsfwDavTransaction* webDavTransaction =
+        CRsfwDavTransaction::NewL(this,
+                                 EWebDavOpOptions,
+                                 uriParser,
+                                 mOptions,
+                                 NextWebDavTransactionId());
+    CleanupStack::PopAndDestroy(); // mOptions
+    CleanupStack::PushL(webDavTransaction);
+
+    RHTTPHeaders hdr = webDavTransaction->
+        HttpTransaction().Request().GetHeaderCollection(); 
+ 
+ 	SetBasicHeadersL(hdr, uriParser, ETrue);
+ 	
+    CleanupStack::Pop(2); //webDavTransaction, uri
+    delete uri;
+    return webDavTransaction;
+    }
+
+// ----------------------------------------------------------------------------
+// CRsfwDavSession::PropFindL
+// Implements WebDAV PROPFIND method.
+// Parameters: Name of the directory or file
+//             CRsfwDirEnt pointer array to be filled with directory metadata
+//             PROPFIND depth
+//             aIsDir, is this directory or file,
+//                     some extra checks are made based on this...
+// ----------------------------------------------------------------------------
+//
+CRsfwDavTransaction* CRsfwDavSession::PropFindL(const TDesC &aPath,
+                                              TInt aDepth,
+                                              TBool aIsDir,
+                                              RPointerArray<CRsfwDirEnt>& aDirEnts)
+    {
+    if (!IsConnected())
+        {
+        User::Leave(KErrNotReady);
+        }
+
+    TUriParser8 uriParser;
+    HBufC8* uri = BuildUriLC(aPath, aIsDir, &uriParser);
+
+    DEBUGSTRING8(("PROPFIND '%S'", &uriParser.UriDes()));
+ 
+    // This function is used from several places
+    TWebDavOp op;
+    if (aDepth == 1)
+        {
+        op = EWebDavOpPropFindMulti;
+        }
+    else // (aDepth == 0)
+        {
+        op = EWebDavOpPropFindSingle;  
+        }
+
+    RStringPool stringPool = StringPool();
+    RStringF mPropFind = stringPool.OpenFStringL(KWebDavPropFind);
+    CleanupClosePushL(mPropFind);
+    CRsfwDavTransaction* webDavTransaction =
+        CRsfwDavTransaction::NewL(this,
+                                 op,
+                                 uriParser,
+                                 mPropFind,
+                                 NextWebDavTransactionId());
+    CleanupStack::PopAndDestroy(); // mPropFind
+    CleanupStack::PushL(webDavTransaction);
+
+    RHTTPHeaders hdr = webDavTransaction->
+        HttpTransaction().Request().GetHeaderCollection();
+
+    // Add headers appropriate to all methods
+    SetBasicHeadersL(hdr, uriParser, ETrue);
+
+    SetHeaderL(hdr, HTTP::EContentType, KTextXml);
+
+    // Assumes that the target uri has been cached in an earlier connect
+    SetDepthHeaderL(hdr, aDepth);
+
+    // XML body
+    HBufC8* requestBodyBuffer = HBufC8::NewL(KDefaultSubmitSize);
+    TPtr8 requestBodyBufferPtr = requestBodyBuffer->Des();
+
+    // To make things at least little bit faster,
+    // let's try to get "minimal" set
+    // Maybe useful one day:
+    // - <D:getcontentlanguage/>
+    // - <D:creationdate/>
+    // Apache mod_dav 1.0.3 doesn't support:
+    //  - <D:displayname/>
+    _LIT8(KPropFindRequestBody, "\
+<?xml version=\"1.0\"?>\
+<propfind xmlns=\"DAV:\">\
+<prop>\
+<getcontenttype/>\
+<getlastmodified/>\
+<getcontentlength/>\
+<resourcetype/>\
+<getetag/>\
+</prop>\
+</propfind>\
+");
+    requestBodyBufferPtr.Append(KPropFindRequestBody);
+    webDavTransaction->SetBodyData(requestBodyBuffer);
+
+    webDavTransaction->SetPropFindDirEntryArray(aDirEnts);
+    // We must remember the work directory,
+    // as we don't want to list that when building directory listing.
+    HBufC* propFindPath = HBufC::NewL(iHostRoot.Length() +
+                                       KMaxPath +
+                                       1);
+    TPtr propFindPathPtr = propFindPath->Des();
+    propFindPathPtr.Copy(iDavRoot);
+    propFindPathPtr.Append(aPath);
+    // The whole path must end with a slash
+    Slashify(propFindPathPtr);
+    // Before comparing the path from the server is decoded,
+    // so we can compare against the original 16-bit string.
+    webDavTransaction->SetPropFindPath(propFindPath);
+    CleanupStack::Pop(2); // webdavtransaction, uri
+    delete uri;
+    return webDavTransaction;
+    }
+
+// ----------------------------------------------------------------------------
+// CRsfwDavSession::GetL
+// ----------------------------------------------------------------------------
+//
+CRsfwDavTransaction* CRsfwDavSession::GetL(const TDesC& aSrcPath,
+                                         const TDesC& aDstPath,
+                                         TInt aOffset,
+                                         TInt* aLength,
+                                         TUint aFlags)
+    {
+    // Basically just a HTTP get with some local processing
+    if (!IsConnected())
+        {
+        User::Leave(KErrNotReady);
+        }
+
+    TUriParser8 uriParser;
+    HBufC8* uri = BuildUriLC(aSrcPath, EFalse, &uriParser);
+
+#ifdef _DEBUG
+    {
+    TInt length;
+    if (aLength)
+        {
+        length = *aLength;
+        }
+    else
+        {
+        length = 0;
+        }
+    DEBUGSTRING8(("GET '%S' (off=%d, len=%d)",
+                  &uriParser.UriDes(),
+                  aOffset,
+                  length));
+    }
+#endif // DEBUG
+
+    // Introducing the webdav headers for GET
+    RStringPool stringPool = StringPool();
+    RStringF mGet = stringPool.StringF(HTTP::EGET,
+                                       RHTTPSession::GetTable());  
+    CRsfwDavTransaction* webDavTransaction =
+        CRsfwDavTransaction::NewL(this,
+                                 EWebDavOpGet,
+                                 uriParser,
+                                 mGet,
+                                 NextWebDavTransactionId());
+    CleanupStack::PushL(webDavTransaction);
+
+    // Not sure if this is needed: we are setting conditions
+    // which mod_dav never gets, cos this is a GET..
+    RHTTPHeaders hdr =
+        webDavTransaction->HttpTransaction().Request().GetHeaderCollection();
+
+    // Add headers appropriate to all methods
+    SetBasicHeadersL(hdr, uriParser, ETrue);
+
+    if (aLength && (*aLength > 0)) // partial get
+        {
+        TBuf8<KMaxFieldValueLength> rangeHeader;
+        _LIT8(KBytesEquals, "bytes=");
+        rangeHeader.Append(KBytesEquals);
+        rangeHeader.AppendNum(aOffset);
+        rangeHeader.Append('-');
+        rangeHeader.AppendNum(aOffset + *aLength - 1);
+        SetHeaderL(hdr, HTTP::ERange, rangeHeader);
+        }
+
+    webDavTransaction->SetBodyFileL(aDstPath, aOffset, aLength, aFlags);
+    CleanupStack::Pop(webDavTransaction);
+    CleanupStack::PopAndDestroy(uri);
+    return webDavTransaction;
+    }
+
+// ----------------------------------------------------------------------------
+// CRsfwDavSession::PutL
+// This amounts to a PUT sending the src data to the destination.
+// Expects that the aSrcPath param is relative to iDavRoot.
+// If aSrcPath is empty, an empty file will be created.
+// ----------------------------------------------------------------------------
+//
+CRsfwDavTransaction* CRsfwDavSession::PutL(const TDesC& aSrcPath,
+                                         const TDesC& aDstPath,
+                                         const TDesC8& aMimeType,
+                                         TInt aOffset,
+                                         TInt aLength,
+                                         TInt aTotalLength,
+                                         TBool aUseContentRange,
+                                         const TDesC8* aLockToken)
+    {  
+    if (!IsConnected())
+        {
+        User::Leave(KErrNotReady);
+        }
+
+    TUriParser8 uriParser;
+    HBufC8* uri = BuildUriLC(aDstPath, EFalse, &uriParser);
+
+    DEBUGSTRING8(("PUT '%S'", &uriParser.UriDes()));
+
+    RStringPool stringPool = StringPool();
+    RStringF mPut = stringPool.OpenFStringL(KWebDavPut);
+    CleanupClosePushL(mPut);
+    CRsfwDavTransaction* webDavTransaction =
+        CRsfwDavTransaction::NewL(this,
+                                 EWebDavOpPut,
+                                 uriParser,
+                                 mPut,
+                                 NextWebDavTransactionId());
+    CleanupStack::PopAndDestroy(); // mPut
+    CleanupStack::PushL(webDavTransaction);
+
+    RHTTPHeaders hdr =
+        webDavTransaction->HttpTransaction().Request().GetHeaderCollection(); 
+
+    // Add headers appropriate to all methods
+    SetBasicHeadersL(hdr, uriParser, ETrue);  
+    SetHeaderL(hdr, HTTP::EContentType, aMimeType);
+
+    if (aLength > 0) // partial put
+        {
+        if (aUseContentRange)
+            {
+            TBuf8<KMaxFieldValueLength> rangeHeader;
+            _LIT8(KBytes, "bytes ");
+            rangeHeader.Append(KBytes);
+            rangeHeader.AppendNum(aOffset);
+            rangeHeader.Append('-');
+            rangeHeader.AppendNum(aOffset + aLength - 1);
+            rangeHeader.Append('/');
+            if (aTotalLength == 0) 
+                {
+                // The asterisk "*" character means that 
+                // the instance-length is unknown at the time when 
+                // the message was generated. 
+                rangeHeader.Append('*');
+                }
+            else
+                {
+                rangeHeader.AppendNum(aTotalLength);
+                }
+            SetHeaderL(hdr, HTTP::EContentRange, rangeHeader);
+            }
+        else
+            {
+            // server doesn't support Content-Range
+            // Leave with KrrNotSupported
+            // *aLength = aTotalLength;
+            }  
+        }
+
+    if (aLockToken)
+        {  
+        SetLockTokenHeaderL(hdr, uri, aLockToken, ETrue);
+        }
+
+    webDavTransaction->SetBodyFileL(aSrcPath, aOffset, &aLength, 0);
+    CleanupStack::Pop(webDavTransaction);
+    CleanupStack::PopAndDestroy(uri);
+    return webDavTransaction;
+    }
+
+// ----------------------------------------------------------------------------
+// CRsfwDavSession::DeleteL
+// ----------------------------------------------------------------------------
+//
+CRsfwDavTransaction* CRsfwDavSession::DeleteL(const TDesC& aPath,
+                                            TBool aIsDir,
+                                            const TDesC8* aLockToken)
+    {
+    // Needs to take locking into account
+    if (!IsConnected())
+        {
+        User::Leave(KErrNotReady);
+        }
+
+    TUriParser8 uriParser;
+    HBufC8* uri = BuildUriLC(aPath, aIsDir, &uriParser);
+
+    DEBUGSTRING8(("DELETE '%S'", &uriParser.UriDes()));
+
+    RStringPool stringPool = StringPool();
+    RStringF mDelete = stringPool.OpenFStringL(KWebDavDelete);
+    CleanupClosePushL(mDelete);
+    CRsfwDavTransaction* webDavTransaction =
+        CRsfwDavTransaction::NewL(this,
+                                 EWebDavOpDelete,
+                                 uriParser,
+                                 mDelete,
+                                 NextWebDavTransactionId());
+    CleanupStack::PopAndDestroy(); // mDelete
+    CleanupStack::PushL(webDavTransaction);
+
+    // need to add a special dir on the i
+    RHTTPHeaders hdr =
+        webDavTransaction->HttpTransaction().Request().GetHeaderCollection(); 
+    // Add headers appropriate to all methods
+    SetBasicHeadersL(hdr, uriParser, ETrue);
+
+    if (aLockToken)
+        {
+        SetLockTokenHeaderL(hdr, uri, aLockToken, ETrue); 
+        }
+
+    CleanupStack::Pop(webDavTransaction);
+    CleanupStack::PopAndDestroy(uri);
+    return webDavTransaction;
+    }
+
+// ----------------------------------------------------------------------------
+// CRsfwDavSession::MkDirL
+// ----------------------------------------------------------------------------
+//
+CRsfwDavTransaction* CRsfwDavSession::MkDirL(const TDesC& aPath)
+    {
+    // Executes a MKCOL with the specified name
+    if (!IsConnected())
+        {
+        User::Leave(KErrNotReady);
+        }
+
+    TUriParser8 uriParser;
+    HBufC8* uri = BuildUriLC(aPath, ETrue, &uriParser);
+
+    DEBUGSTRING8(("MKCOL '%S'", &uriParser.UriDes()));
+
+    RStringPool stringPool = StringPool();
+    RStringF mMkCol = stringPool.OpenFStringL(KWebDavMkCol);
+    CleanupClosePushL(mMkCol);
+    CRsfwDavTransaction* webDavTransaction =
+        CRsfwDavTransaction::NewL(this,
+                                 EWebDavOpMkCol,
+                                 uriParser,
+                                 mMkCol,
+                                 NextWebDavTransactionId());
+    CleanupStack::PopAndDestroy(1); // mMkCol
+    CleanupStack::PushL(webDavTransaction);
+
+    // Neeed to add a special dir on the i
+    RHTTPHeaders hdr =
+        webDavTransaction->HttpTransaction().Request().GetHeaderCollection(); 
+
+    // Add headers appropriate to all methods
+    SetBasicHeadersL(hdr, uriParser, ETrue);
+
+    CleanupStack::Pop(2); // webDavTransaction, uri
+    delete uri;
+    return webDavTransaction;
+    }
+
+// ----------------------------------------------------------------------------
+// CRsfwDavSession::MoveL
+// ----------------------------------------------------------------------------
+//
+CRsfwDavTransaction* CRsfwDavSession::MoveL(const TDesC& aOldPath,
+                                          const TDesC& aNewPath,
+                                          TBool aOverwrite,
+                                          const TDesC8* aSrcLockToken,
+                                          const TDesC8* aDstLockToken)
+    {
+    if (!IsConnected())
+        {
+        User::Leave(KErrNotReady);
+        }
+
+    TUriParser8 uriParserNew;
+    HBufC8* uriNew = BuildUriLC(aNewPath, EFalse, &uriParserNew);
+    TUriParser8 uriParserOld;
+    HBufC8* uriOld = BuildUriLC(aOldPath, EFalse, &uriParserOld);
+
+    DEBUGSTRING8(("MOVE '%S' to '%S'",
+                  &uriParserOld.UriDes(),
+                  &uriParserNew.UriDes()));
+
+    RStringPool stringPool = StringPool();
+    RStringF mMove = stringPool.OpenFStringL(KWebDavMove);
+    CleanupClosePushL(mMove);
+    CRsfwDavTransaction* webDavTransaction =
+        CRsfwDavTransaction::NewL(this,
+                                 EWebDavOpMove,
+                                 uriParserOld,
+                                 mMove,
+                                 NextWebDavTransactionId());
+    CleanupStack::PopAndDestroy(); // mMove
+    CleanupStack::PushL(webDavTransaction);
+
+    RHTTPHeaders hdr =
+        webDavTransaction->HttpTransaction().Request().GetHeaderCollection();
+
+    // Add headers appropriate to all methods
+    SetBasicHeadersL(hdr, uriParserOld, ETrue);
+    
+    if (aSrcLockToken)
+        {
+        SetLockTokenHeaderL(hdr, uriOld, aSrcLockToken, ETrue);
+        }
+    
+    
+     if (aDstLockToken)
+        {
+        SetLockTokenHeaderL(hdr, uriNew, aDstLockToken, ETrue);
+        }      
+        
+    SetHeaderL(hdr, KWebDavDest, *uriNew);
+    if (aOverwrite)
+        {
+        SetHeaderL(hdr, KWebDavOverwrite, KWebDavOverwriteY);
+        }
+    else
+        {
+        SetHeaderL(hdr, KWebDavOverwrite, KWebDavOverwriteN);
+        }
+
+    CleanupStack::Pop(webDavTransaction);
+    CleanupStack::PopAndDestroy(2, uriNew);   // uriOld, uriNew
+    return webDavTransaction;
+    }
+
+// ----------------------------------------------------------------------------
+// CRsfwDavSession::LockL
+// ----------------------------------------------------------------------------
+//
+CRsfwDavTransaction* CRsfwDavSession::LockL(const TDesC& aPath,
+                                          TUint aFlags,
+                                          TUint aTimeout,
+                                          CRsfwDavFileInfo** aDavFileInfo)
+    {
+    // Opens LOCK transaction
+    if (!IsConnected())
+        {
+        User::Leave(KErrNotReady);
+        }
+
+    TUriParser8 uriParser;
+    HBufC8* uri = BuildUriLC(aPath, EFalse, &uriParser);
+
+    DEBUGSTRING8(("LOCK '%S' (%d seconds)", &uriParser.UriDes(), aTimeout));
+
+    RStringPool stringPool = StringPool();
+    RStringF mLock = stringPool.OpenFStringL(KWebDavLock);
+    CleanupClosePushL(mLock);
+    CRsfwDavTransaction* webDavTransaction =
+        CRsfwDavTransaction::NewL(this,
+                                 EWebDavOpLock,
+                                 uriParser,
+                                 mLock,
+                                 NextWebDavTransactionId());
+    CleanupStack::PopAndDestroy(&mLock);
+    CleanupStack::PushL(webDavTransaction);
+
+    // headers
+    RHTTPHeaders hdr =
+        webDavTransaction->HttpTransaction().Request().GetHeaderCollection(); 
+
+    // Add headers appropriate to all methods
+    SetBasicHeadersL(hdr, uriParser, ETrue);
+
+    SetHeaderL(hdr, HTTP::EContentType, KTextXml);
+
+    HBufC8* timeoutBuffer = HBufC8::NewLC(KMaxFieldValueLength);
+    TPtr8 timeoutBufferPtr = timeoutBuffer->Des();
+    timeoutBufferPtr.Append(KSecondDash);
+    if (aTimeout != 0)
+        {
+        timeoutBufferPtr.AppendNum(aTimeout);
+        }
+    SetHeaderL(hdr, KWebDavTimeout, timeoutBufferPtr);
+    CleanupStack::PopAndDestroy(timeoutBuffer);
+
+    // XML body
+    HBufC8* requestBodyBuffer = HBufC8::NewL(KDefaultSubmitSize);
+    TPtr8 requestBodyBufferPtr = requestBodyBuffer->Des();
+
+    // Note: locktype "write" is currently the only legal value
+    _LIT8(KLockHeaderFormat, "\
+<?xml version=\"1.0\" encoding=\"utf-8\" ?>\
+<D:lockinfo xmlns:D=\"DAV:\">\
+<D:lockscope><D:%S/></D:lockscope>\
+<D:locktype><D:write/></D:locktype>\
+<D:owner xmlns:x=\"http://www.webdav.org/\">\
+<x:lock-user>%S</x:lock-user>\
+<x:created-by>%S</x:created-by>\
+</D:owner>\
+</D:lockinfo>");
+
+    _LIT8(KLockScopeShared, "shared");
+    _LIT8(KLockScopeExclusive, "exclusive");
+    TPtrC8 lockScope;
+    if (aFlags & EFileShareAny)
+        {
+        lockScope.Set(KLockScopeShared);
+        }
+    else
+        {
+        lockScope.Set(KLockScopeExclusive);
+        }
+     
+    requestBodyBufferPtr.Format(KLockHeaderFormat, &lockScope, iUserName, iUserName);
+    webDavTransaction->SetBodyData(requestBodyBuffer);
+
+    HBufC* fileInfoPath = BuildFullPathLC(aPath, EFalse);
+    webDavTransaction->SetDavFileInfoL(aDavFileInfo, *fileInfoPath);
+    CleanupStack::PopAndDestroy(fileInfoPath);
+    CleanupStack::Pop(webDavTransaction);
+    CleanupStack::PopAndDestroy(uri);
+    return webDavTransaction;
+    }
+
+// ----------------------------------------------------------------------------
+// CRsfwDavSession::UnlockL
+// ----------------------------------------------------------------------------
+//
+CRsfwDavTransaction* CRsfwDavSession::UnlockL(const TDesC& aPath,
+                                            const TDesC8* aLockToken)
+    {
+    // Opens LOCK transaction
+    if (!IsConnected())
+        {
+        User::Leave(KErrNotReady);
+        }
+
+    if (iWebDavSupportClass < KDavVersionTwo)
+        {
+        User::Leave(KErrNotSupported);
+        }
+
+    TUriParser8 uriParser;
+    HBufC8* uri = BuildUriLC(aPath, EFalse, &uriParser);
+
+    DEBUGSTRING8(("UNLOCK '%S'", &uriParser.UriDes()));
+
+    RStringPool stringPool = StringPool();
+    RStringF mUnlock = stringPool.OpenFStringL(KWebDavUnlock);
+    CleanupClosePushL(mUnlock);
+    CRsfwDavTransaction* webDavTransaction =
+        CRsfwDavTransaction::NewL(this,
+                                 EWebDavOpUnlock,
+                                 uriParser,
+                                 mUnlock,
+                                 NextWebDavTransactionId());
+    CleanupStack::PopAndDestroy(); // mUnlock
+    CleanupStack::PushL(webDavTransaction);
+
+    RHTTPHeaders hdr =
+        webDavTransaction->HttpTransaction().Request().GetHeaderCollection(); 
+
+    // Add headers appropriate to all methods
+    SetBasicHeadersL(hdr, uriParser, ETrue);
+
+    HBufC8* lockToken = HBufC8::NewLC(aLockToken->Length() +
+                                      KLockTokenOverhead);
+    TPtr8 lockTokenPtr = lockToken->Des();
+    lockTokenPtr.Append('<');
+    lockTokenPtr.Append(*aLockToken);
+    lockTokenPtr.Append('>');
+    SetHeaderL(hdr, KWedDavLockToken, lockTokenPtr);
+    CleanupStack::PopAndDestroy(lockToken);
+
+    CleanupStack::Pop(2); // webdavtransaction , uri
+    delete uri;
+    return webDavTransaction;
+    }
+
+// ----------------------------------------------------------------------------
+// CRsfwDavSession::RefreshLockL
+// ----------------------------------------------------------------------------
+//
+CRsfwDavTransaction* CRsfwDavSession::RefreshLockL(const TDesC& aPath,
+                                                 TUint aTimeout,
+                                                 const TDesC8* aLockToken,
+                                                 CRsfwDavFileInfo** aDavFileInfo)
+    {
+    // Opens LOCK transaction
+    if (!IsConnected())
+        {
+        User::Leave(KErrNotReady);
+        }
+
+    if (iWebDavSupportClass < KDavVersionTwo)
+        {
+        User::Leave(KErrNotSupported);
+        }
+
+    TUriParser8 uriParser;
+    HBufC8* uri = BuildUriLC(aPath, EFalse, &uriParser);
+
+    DEBUGSTRING8(("LOCK (refresh) '%S' (%d seconds)",
+                  &uriParser.UriDes(),
+                  aTimeout));
+
+    RStringPool stringPool = StringPool();
+    RStringF mLock = stringPool.OpenFStringL(KWebDavLock);
+    CleanupClosePushL(mLock);
+    CRsfwDavTransaction* webDavTransaction =
+        CRsfwDavTransaction::NewL(this,
+                                 EWebDavOpRefreshLock,
+                                 uriParser,
+                                 mLock,
+                                 NextWebDavTransactionId());
+    CleanupStack::PopAndDestroy(&mLock);
+    CleanupStack::PushL(webDavTransaction);
+
+    RHTTPHeaders hdr =
+        webDavTransaction->HttpTransaction().Request().GetHeaderCollection(); 
+
+    // Add headers appropriate to all methods
+    SetBasicHeadersL(hdr, uriParser, ETrue);
+
+    // do not use tagged lock token, as refresh 'If' header 
+    // should always contain only a single lock token 
+    // (only one lock may be refreshed at a time).
+    SetLockTokenHeaderL(hdr, uri, aLockToken, EFalse);
+
+    HBufC8* timeoutBuffer = HBufC8::NewLC(KMaxFieldValueLength);
+    TPtr8 timeoutBufferPtr = timeoutBuffer->Des();
+    timeoutBufferPtr.Append(KSecondDash);
+    if (aTimeout != 0)
+        {
+        timeoutBufferPtr.AppendNum(aTimeout);
+        }
+    SetHeaderL(hdr, KWebDavTimeout, timeoutBufferPtr);
+    CleanupStack::PopAndDestroy(timeoutBuffer);
+
+    HBufC* fileInfoPath = BuildFullPathLC(aPath, EFalse);
+    webDavTransaction->SetDavFileInfoL(aDavFileInfo, *fileInfoPath);
+    CleanupStack::PopAndDestroy(fileInfoPath);
+    CleanupStack::Pop(webDavTransaction);
+    CleanupStack::PopAndDestroy(uri);
+    return webDavTransaction;
+    }
+
+// ----------------------------------------------------------------------------
+// CRsfwDavSession::GetCredentialsL
+// From MHTTPAuthenticationCallback
+// ----------------------------------------------------------------------------
+//
+TBool CRsfwDavSession::GetCredentialsL(const TUriC8& /* aURI */,
+                                      RString aRealm,
+                                      RStringF /*aAuthenticationType*/,
+                                      RString& aUserName,
+                                      RString& aPassword)
+    {
+    // if we have not tried to send the current credentials once,
+    // and we have at least username proceed, othwise return KErrAccessDenied
+    if (iCredentialRequestCount || (!iUserName))
+        {
+        iCredentialRequestCount = 0;
+        User::Leave(KErrAccessDenied);
+        }
+    iCredentialRequestCount++;
+
+    TRAPD(err, aUserName = aRealm.Pool().OpenStringL(*iUserName));
+    if (!err)
+        {
+        TRAP(err, aPassword = aRealm.Pool().OpenStringL(*iPassword));
+        if (!err)
+            {
+            return ETrue;
+            }
+        }  
+    return EFalse;
+    }
+
+// ----------------------------------------------------------------------------
+// CRsfwDavSession::SetHeaderL
+// Convenience method for setting up the header.
+// ----------------------------------------------------------------------------
+//
+void CRsfwDavSession::SetHeaderL(RHTTPHeaders aHeaders,
+                                TInt aHdrField,
+                                const TDesC8& aHdrValue)
+    {
+    RStringF valStr = StringPool().OpenFStringL(aHdrValue);
+    CleanupClosePushL(valStr);
+    THTTPHdrVal val(valStr);
+    aHeaders.SetFieldL(
+        StringPool().StringF(aHdrField, RHTTPSession::GetTable()), val);
+    CleanupStack::PopAndDestroy(&valStr);
+    }
+
+// ----------------------------------------------------------------------------
+// CRsfwDavSession::SetHeaderL
+// Convenience method for setting up the header.
+// ----------------------------------------------------------------------------
+//
+void CRsfwDavSession::SetHeaderL(RHTTPHeaders aHeaders,
+                                const TDesC8& aHdrName,
+                                const TDesC8& aHdrValue)
+    {
+    RStringF nameStr = StringPool().OpenFStringL(aHdrName);
+    CleanupClosePushL(nameStr);
+    RStringF valueStr = StringPool().OpenFStringL(aHdrValue);
+    CleanupClosePushL(valueStr);
+    THTTPHdrVal value(valueStr);
+    aHeaders.SetFieldL(nameStr, value);
+    CleanupStack::PopAndDestroy(2); // valueStr, nameStr
+    }
+
+// ----------------------------------------------------------------------------
+// CRsfwDavSession::SetBasicHeadersL
+// Convenience method for setting up the header.
+// ----------------------------------------------------------------------------
+//
+void CRsfwDavSession::SetBasicHeadersL(RHTTPHeaders aHeaders, 
+                                       const TUriC8& aUri,
+                                       TBool aNoProxy)
+    {
+    // Add headers appropriate to all methods
+    SetHeaderL(aHeaders, HTTP::EUserAgent, KUserAgent);
+    SetHeaderL(aHeaders, HTTP::EAccept, KAccept);
+    // do not send host header if using SSL (not supported currently)
+    TPtrC8 scheme;
+    if (aUri.IsPresent(EUriScheme))
+        {
+        scheme.Set(aUri.Extract(EUriScheme));
+        }
+    if (scheme.CompareF(KHttpsScheme8) != 0) 
+    	{
+    	SetHeaderL(aHeaders, HTTP::EHost, *iEncodedHost);
+    	}
+    SetHeaderL(aHeaders, HTTP::EConnection, KKeepAlive);
+    if (aNoProxy) 
+        {
+        // see RFC 2518 10.4.5 If Header and Non-DAV Aware Proxies
+        // "As in general clients may not be able to reliably detect 
+        // non-DAV aware intermediates, they are advised to always 
+        // prevent caching using the request directives mentioned above."
+        SetHeaderL(aHeaders, HTTP::EPragma, KWebDavNoProxy);
+        SetHeaderL(aHeaders, HTTP::ECacheControl, KWebDavNoProxy);
+        }
+    }
+
+// ----------------------------------------------------------------------------
+// CRsfwDavSession::SetDepthHeaderL
+// Some DAV requests require this for specifying depth of copies etc.
+// ----------------------------------------------------------------------------
+//
+void CRsfwDavSession::SetDepthHeaderL(RHTTPHeaders aHeaders, TInt aDepth)
+    {
+    RStringF depthStr = StringPool().OpenFStringL(KWebDavDepth);
+    CleanupClosePushL(depthStr);
+    THTTPHdrVal depth(aDepth);
+    aHeaders.SetFieldL(depthStr, depth);
+    CleanupStack::PopAndDestroy(&depthStr);
+    }
+
+// ----------------------------------------------------------------------------
+// CRsfwDavSession::SetLockTokenHeaderL
+// The lock token header can be tagged with the resource (file) URI
+// This is especially important for DELETE and MOVE of a file,
+// as they will also affect the container (directory), which is not locked
+// (in which case supplying a lock token is an error).
+// ----------------------------------------------------------------------------
+//
+void CRsfwDavSession::SetLockTokenHeaderL(RHTTPHeaders aHeaders,
+                                         const TDesC8* aUri,
+                                         const TDesC8* aLockToken,
+                                         TBool aUseTaggedLockToken)
+    {
+    DEBUGSTRING(("using a tagged lock token"));
+    // KLockTokenOverhead for 'tagged' lock token is 2 chars around the uri,
+    // one space, and 4 chars around the locktoken
+    // i.e. <target-url> (<target-token>)
+    TInt tagoverhead;
+    if (aUseTaggedLockToken) 
+        {
+        tagoverhead = KTaggedLockTokenOverhead;
+        }
+    else 
+        {
+        tagoverhead = KLockTokenOverhead;
+        }
+    HBufC8* lockToken = HBufC8::NewLC(aUri->Length()+ aLockToken->Length() +
+                                      tagoverhead);
+    TPtr8 lockTokenPtr = lockToken->Des();
+    if (aUseTaggedLockToken) 
+        {
+        lockTokenPtr.Format(KTaggedParenthAngleFormat, aUri, aLockToken);
+        }
+    else 
+        {
+        lockTokenPtr.Format(KParenthAngleFormat, aLockToken);
+        }
+
+    DEBUGSTRING8(("lt='%S'", &lockTokenPtr));
+    SetHeaderL(aHeaders, KWebDavIf, lockTokenPtr);
+    CleanupStack::PopAndDestroy(lockToken);
+    }
+
+// ----------------------------------------------------------------------------
+// CRsfwDavSession::WebDavTransactionCompleteL
+// ----------------------------------------------------------------------------
+//
+void CRsfwDavSession::WebDavTransactionCompleteL(
+    CRsfwDavTransaction* aWebDavTransaction)
+    {
+    TUint webDavTransactionId = aWebDavTransaction->Id();
+    delete aWebDavTransaction;
+    iWebDavResponseObserver->RequestCompleteL(webDavTransactionId);
+    }
+
+// ----------------------------------------------------------------------------
+// CRsfwDavSession::WebDavTransactionError
+// ----------------------------------------------------------------------------
+//
+void CRsfwDavSession::WebDavTransactionError(
+    CRsfwDavTransaction* aWebDavTransaction)
+    {
+    TUint webDavTransactionId = aWebDavTransaction->Id();
+    TInt status = aWebDavTransaction->Status();
+    delete aWebDavTransaction;
+    iWebDavResponseObserver->RequestError(webDavTransactionId, status);
+    }
+
+// ----------------------------------------------------------------------------
+// CRsfwDavSession::SetPropFindParameters
+// ----------------------------------------------------------------------------
+//
+void CRsfwDavSession::SetPropFindParametersL(
+    RPointerArray<CRsfwDirEnt>* aDirEntArray,
+    const TDesC& aPropFindPath,
+    TInt aDepth)
+    {
+    iPropFindParserImpl->SetDirEntArray(aDirEntArray);
+    iPropFindParserImpl->SetTargetDirectory(aPropFindPath, aDepth);
+    iPropFindParser->ParseBeginL();
+    }
+
+// ----------------------------------------------------------------------------
+// CRsfwDavSession::SetLockQueryParameters
+// ----------------------------------------------------------------------------
+//
+void CRsfwDavSession::SetLockQueryParameters(CRsfwDavFileInfo* aDavFileInfo)
+    {
+    iLockQueryParserImpl->SetDavFileInfo(aDavFileInfo);
+    }
+
+// ----------------------------------------------------------------------------
+// CRsfwDavSession::ParsePropFindResponseL
+// ----------------------------------------------------------------------------
+//
+void CRsfwDavSession::ParsePropFindResponseL(const TDesC8& aResponse)
+    {
+    // only first call to this function really initiates data structures in the XML parser
+    iPropfindParsingActive = ETrue;
+    iPropFindParser->ParseL(aResponse);
+    }
+
+// ----------------------------------------------------------------------------
+// CRsfwDavSession::ParseLockResponseL
+// ----------------------------------------------------------------------------
+//
+void CRsfwDavSession::ParseLockResponseL(const TDesC8& aResponse)
+    {
+    iLockQueryParser->ParseL(aResponse);
+    }
+
+// ----------------------------------------------------------------------------
+// CRsfwDavSession::PropFindResponseEndL
+// ----------------------------------------------------------------------------
+//
+void CRsfwDavSession::PropFindResponseEndL()
+    {
+    iPropFindParser->ParseEndL();
+    iPropfindParsingActive = EFalse;
+    TInt err = iPropFindParserImpl->GetLastError();
+    if (err) 
+   	 	{
+    	User::Leave(err);
+    	}
+    }
+
+// ----------------------------------------------------------------------------
+// CRsfwDavSession::LockResponseEndL
+// ----------------------------------------------------------------------------
+//
+void CRsfwDavSession::LockResponseEndL()
+    {
+    iLockQueryParser->ParseEndL();
+    TInt err = iPropFindParserImpl->GetLastError();
+    if (err) 
+   	 	{
+    	User::Leave(err);
+    	}
+    }
+
+// ----------------------------------------------------------------------------
+// CRsfwDavSession::CancelParsing
+// ----------------------------------------------------------------------------
+//
+void CRsfwDavSession::CancelParsing(TWebDavOp aOp)
+    {
+    // Only will do something if this operation is PROPFIND,
+    // and we have started to parse the response.
+    // UI does not allow to cancel LOCK requests.
+    // If this would be possible this mechanism should be expanded
+    // to also cover LOCK parsing.
+    if ((aOp == EWebDavOpPropFindSingle) || 
+    (aOp == EWebDavOpPropFindMulti)) 
+        {
+        if (iPropfindParsingActive)   
+            {
+            // When XML parsing is cancelled when the request is cancelled, 
+            // there is some XML error (invalid token etc.), ignore the error
+            TRAP_IGNORE(iPropFindParser->ParseEndL());
+            iPropfindParsingActive = EFalse;
+            }
+        }
+    }
+    
+
+// ----------------------------------------------------------------------------
+// CRsfwDavSession::HttpSession
+// ----------------------------------------------------------------------------
+//
+RHTTPSession& CRsfwDavSession::HttpSession()
+    {
+    return iHttpSession;
+    }
+
+// ----------------------------------------------------------------------------
+// CRsfwDavSession::StringPool
+// ----------------------------------------------------------------------------
+//
+RStringPool CRsfwDavSession::StringPool()
+    {
+    return iHttpSession.StringPool();
+    }
+
+// ----------------------------------------------------------------------------
+// CRsfwDavSession::Slashify
+// ----------------------------------------------------------------------------
+//
+void CRsfwDavSession::Slashify(TDes& aStr)
+    {
+    if (aStr.Length() &&
+        (aStr[aStr.Length() - 1] != '/') &&
+        aStr.Length() < aStr.MaxLength())
+        {
+        aStr.Append('/');
+        }
+    }
+
+// ----------------------------------------------------------------------------
+// CRsfwDavSession::BuildPathLC
+// This function constructs a file path from davroot + path
+// ----------------------------------------------------------------------------
+//
+HBufC* CRsfwDavSession::BuildPathLC(const TDesC& aRoot,
+                                   const TDesC& aPath,
+                                   TBool aEndSlash)
+    {
+    // 1 is for a possible slash added to the end of the uri...
+    HBufC* path = HBufC::NewLC(aRoot.Length() +
+                               aPath.Length() +
+                               1);
+    TPtr pathPtr = path->Des();
+    pathPtr.Append(aRoot);
+    pathPtr.Append(aPath);
+    if (aEndSlash)
+        {
+        Slashify(pathPtr);
+        }
+    return path;
+    }
+
+// ----------------------------------------------------------------------------
+// CRsfwDavSession::BuildFullPathLC
+// This function constructs a file path from davroot + path
+// ----------------------------------------------------------------------------
+//
+HBufC* CRsfwDavSession::BuildFullPathLC(const TDesC& aPath,
+                                       TBool aEndSlash)
+    {
+    return BuildPathLC(iDavRoot, aPath, aEndSlash);
+    }
+
+// ----------------------------------------------------------------------------
+// CRsfwDavSession::BuildUriLC
+// This function constructs an URI from hostname + davroot + path
+// The URI is first escape encoded and then UTF-8 encoded.
+// Note that in addition to returning the uri string, this function
+// will also "populate" aUriParser with the full URI
+// ----------------------------------------------------------------------------
+//
+HBufC8* CRsfwDavSession::BuildUriLC(const TDesC& aPath,
+                                   TBool aEndSlash,
+                                   TUriParser8* aUriParser)
+    {
+    // 1 is for a possible slash added to the end of the uri...
+    HBufC* uri = BuildPathLC(iHostRoot, aPath, aEndSlash);
+    HBufC8* utf8Path = EncodeL(*uri);
+    CleanupStack::PopAndDestroy(uri);
+    CleanupStack::PushL(utf8Path);
+    TPtr8 utf8PathPtr = utf8Path->Des();
+    if (aUriParser)
+        {
+        if (aUriParser->Parse(utf8PathPtr) != KErrNone)
+            {
+            User::Leave(KErrBadName);
+            }
+        }
+    return utf8Path;
+    }
+
+// ----------------------------------------------------------------------------
+// CRsfwDavSession::EncodeL
+// First escape encode and then UTF-8 encode data.
+// ----------------------------------------------------------------------------
+//
+HBufC8* CRsfwDavSession::EncodeL(const TDesC& aData)
+    {
+    HBufC8* utf8Data = EscapeUtils::ConvertFromUnicodeToUtf8L(aData);
+    CleanupStack::PushL(utf8Data);
+    HBufC8* escapedData = EscapeUtils::EscapeEncodeL(*utf8Data, KSpecials8);
+    CleanupStack::PopAndDestroy(utf8Data);
+    return escapedData;
+    }
+
+// ----------------------------------------------------------------------------
+// CRsfwDavSession::IsConnected
+// ----------------------------------------------------------------------------
+//
+TBool CRsfwDavSession::IsConnected()
+    {
+    return iConnected;
+    }
+
+// ----------------------------------------------------------------------------
+// CRsfwDavSession::NextWebDavTransactionId
+// ----------------------------------------------------------------------------
+//
+TUint CRsfwDavSession::NextWebDavTransactionId()
+    {
+    return ++iCurrentWebDavTransactionId;
+    }
+
+// ----------------------------------------------------------------------------
+// CRsfwDavSession::SetupConnectionL
+// ----------------------------------------------------------------------------
+//
+void CRsfwDavSession::SetupConnectionL()
+    {
+    RSocketServ* socketServ;
+    RConnection* connection;
+
+    DEBUGSTRING(("SetupConnection - start"));
+    User::LeaveIfError(iRsfwConnectionManager->GetConnection(socketServ, 
+                                                             connection));
+    DEBUGSTRING(("iRsfwConnectionManager->GetConnection called"));                                                        
+    // Now bind the HTTP session with the socket server connection
+    RStringPool stringPool = iHttpSession.StringPool();
+    RHTTPConnectionInfo connInfo = iHttpSession.ConnectionInfo();
+    connInfo.SetPropertyL(
+        stringPool.StringF(HTTP::EHttpSocketServ, RHTTPSession::GetTable()),
+        THTTPHdrVal(socketServ->Handle()));
+    connInfo.SetPropertyL(
+        stringPool.StringF(HTTP::EHttpSocketConnection,
+                           RHTTPSession::GetTable()), 
+        THTTPHdrVal(reinterpret_cast<TInt>(connection)));
+    DEBUGSTRING(("SetupConnection - done"));
+    }
+    
+//  End of File