I created a small test program to demonstrate the problem. You can download a zip file containing the sources, a package file and an installation file for the Nokia 9500 at:
http://www.powerjuice.nl/NokiaTest.zip
The core is the CNokiaTest class.
Header:
Code:
// CNokiaTest.h
// Test class for Nokia 9500 HTTP connection.
#ifndef __CNOKIATEST_H
#define __CNOKIATEST_H
class CIdle;
#include <http/rhttpsession.h>
#include <http/mhttptransactioncallback.h>
#include <http/mhttpdatasupplier.h>
class CNokiaTest :
public CBase,
public MHTTPTransactionCallback,
public MHTTPDataSupplier
{
public:
static CNokiaTest* NewL();
~CNokiaTest();
void StartL();
static TInt IdleCallback(TAny *aPtr);
// Implementation of MHTTPTransactionCallBack interface
void MHFRunL(RHTTPTransaction aTransaction, const THTTPEvent& aEvent);
TInt MHFRunError(TInt aError, RHTTPTransaction aTransaction, const THTTPEvent& aEvent);
// Implementation of MHTTPDataSupplier interface
TBool GetNextDataPart(TPtrC8& aDataPart) { aDataPart.Set(KNullDesC8); return(ETrue); }
void ReleaseData() {}
TInt OverallDataSize() { return 0; }
TInt Reset() { return KErrNone; }
private:
CNokiaTest();
void ConstructL();
void StartHttpConnectionL();
TInt CheckConnection();
CIdle* iIdle;
RHTTPSession iSession;
RHTTPTransaction iTransaction;
TBool iConnClosed;
TPtrC iMsgPtr;
};
#endif // #ifndef __CNOKIATEST_H
And cpp file:
Code:
// CNokiaTest.cpp
#include <e32base.h>
#include <eikenv.h>
#include <http/rhttpsession.h>
#include <HttpStringConstants.h>
#include <http/rhttpheaders.h>
#include "CNokiaTest.h"
_LIT(KConnIdle, "Idle");
_LIT(KConnInit, "Initializing");
_LIT(KConnConnecting, "Connecting");
_LIT(KConnResponse, "Got response");
_LIT(KConnResponseComplete, "Response complete");
_LIT(KConnClosed, "Connection closed");
_LIT(KConnFailed, "Connection failed");
_LIT(KConnError, "Connection error");
_LIT(KConnUnhandled, "Unhandled event");
CNokiaTest::CNokiaTest() :
iIdle(NULL),
iConnClosed(EFalse),
iMsgPtr(KConnIdle)
{
}
CNokiaTest::~CNokiaTest()
{
delete iIdle;
iSession.Close();
}
CNokiaTest* CNokiaTest::NewL()
{
CNokiaTest* result = new(ELeave) CNokiaTest();
CleanupStack::PushL(result);
result->ConstructL();
CleanupStack::Pop(result);
return result;
}
void CNokiaTest::ConstructL()
{
iIdle = CIdle::NewL(CActive::EPriorityIdle);
iSession.OpenL();
}
void CNokiaTest::StartL()
{
// Start the HTTP connection; then start the idle AO.
StartHttpConnectionL();
iIdle->Start(TCallBack(IdleCallback, this));
}
void CNokiaTest::StartHttpConnectionL()
{
_LIT8(KUrl, "http://www.powerjuice.nl");
_LIT8(KContentType, "text/html");
iConnClosed = EFalse;
iMsgPtr.Set(KConnInit);
RStringPool string_pool = iSession.StringPool();
RStringF method = string_pool.StringF(HTTP::EPOST, RHTTPSession::GetTable());
TUriParser8 uri;
uri.Parse(KUrl);
iTransaction = iSession.OpenTransactionL(uri, *this, method);
RHTTPHeaders hdr = iTransaction.Request().GetHeaderCollection();
RStringF cont_type_str = string_pool.OpenFStringL(KContentType);
THTTPHdrVal cont_type(cont_type_str);
hdr.SetFieldL(string_pool.StringF(HTTP::EContentType,RHTTPSession::GetTable()), cont_type);
cont_type_str.Close();
iTransaction.Request().SetBody(*this);
iTransaction.SubmitL();
iMsgPtr.Set(KConnConnecting);
}
TInt CNokiaTest::IdleCallback(TAny *aPtr)
{
CNokiaTest* test_obj = static_cast<CNokiaTest*>(aPtr);
return test_obj->CheckConnection();
}
TInt CNokiaTest::CheckConnection()
{
TRAPD(err, CEikonEnv::Static()->BusyMsgL(iMsgPtr));
return (!iConnClosed);
}
void CNokiaTest::MHFRunL(RHTTPTransaction /* aTransaction */, const THTTPEvent& aEvent)
{
switch (aEvent.iStatus)
{
case THTTPEvent::EGotResponseHeaders:
case THTTPEvent::EGotResponseBodyData:
iMsgPtr.Set(KConnResponse);
break;
case THTTPEvent::EResponseComplete:
iMsgPtr.Set(KConnResponseComplete);
break;
case THTTPEvent::ESucceeded:
iMsgPtr.Set(KConnClosed);
iTransaction.Close();
iConnClosed = ETrue;
break;
case THTTPEvent::EFailed:
iMsgPtr.Set(KConnFailed);
iTransaction.Close();
iConnClosed = ETrue;
break;
default:
{
iMsgPtr.Set(KConnUnhandled);
// Stop the transaction handling in case of error
if (aEvent.iStatus < 0)
{
iTransaction.Close();
iConnClosed = ETrue;
}
}
break;
}
}
TInt CNokiaTest::MHFRunError(TInt /*aError*/, RHTTPTransaction /*aTransaction*/, const THTTPEvent& /*aEvent*/)
{
iMsgPtr.Set(KConnError);
return KErrNone;
}
After making a connection, the display freezes for more than 20 seconds, which is enough for the View Server to panic.
It should not freeze. This looks to be a bug in the HTTP server implementation on the Nokia 9500..