⭐ 欢迎来到虫虫下载站! | 📦 资源下载 📁 资源专辑 ℹ️ 关于我们
⭐ 虫虫下载站

📄 securesockets.cpp

📁 《UIQ 3 The Complete Guide》书的源代码
💻 CPP
📖 第 1 页 / 共 2 页
字号:
//
// SecureSockets.cpp - SecureSockets example
//
// Copyright (C) UIQ Technology AB, 2007
//
// This material is provided "as is" without any warranty to its performance or functionality. 
// In no event shall UIQ Technology be liable for any damages whatsoever arising out of the
// use or inabilty to use this material. 
//

#include "SecureSockets.h"
#include "SecureSockets.hrh"
#include <SecureSockets.rsg>

#include <QikViewBase.h>
#include <QikCommand.h>
#include <QikListBoxModel.h>
#include <QikListBox.h>
#include <MQikListBoxData.h>
#include <QikListBoxData.h>
#include <eikstart.h>

#include <es_sock.h>
#include <in_sock.h>
#include <securesocket.h>
#include <x509cert.h>

//////////////////////////////////////////////////////////////////////////////
// The application Uid here MUST match UID3 defined in the MMP file 
// This is a development UID and must NOT be used in production type software
const TUid KAppSpecificUid={0xEDEAD013};

// internal secondary view id, must be unique amongst this applications views
const TUid KUidListView={0x00000001};

// views within applications are fully identified by the app Uid and secondary view id
#define KViewIdListView TVwsViewId(KAppSpecificUid,KUidListView)

//////////////////////////////////////////////////////////////////////////////////
class CLogText : public CBase
    {
public:
	// new methods
	~CLogText();
	void ConstructL();
	TInt Count();
	const TDesC& At(const TInt aIndex);
	void LogText(const TDesC& aBuf);
	void ResetText();

protected:
	CArrayFixFlat<HBufC*>* iText;
	};

CLogText::~CLogText()
	{
	ResetText();
	delete(iText);
	}

void CLogText::ConstructL()
	{
	iText=new(ELeave)CArrayFixFlat<HBufC*>(32);
	}
	
TInt CLogText::Count()
// Report number of logged messages
	{
	return(iText->Count());
	}

const TDesC& CLogText::At(const TInt aIndex)
// report 'n'th text message
	{
	return(*iText->At(aIndex));
	}

void CLogText::ResetText()
	{
	TInt count=Count();
	for (TInt i=0;i<count;i++)
		delete(iText->At(i));
	iText->Reset();
	}

void CLogText::LogText(const TDesC& aBuf)
	{ // add new text item to front of the list
	TRAPD(err,
		TBuf<128>bb;
		if (aBuf.Length()>120)
			bb=aBuf.Left(120);
		else
			bb=aBuf;
		HBufC* q=bb.AllocLC();
		iText->InsertL(0,q);	// at front of list
		CleanupStack::Pop(q);
		if (iText->Count()>100)
			{ // restrict to last 100 log msgs
			delete(iText->At(100));
			iText->Delete(100);
			}
		);
	}

//////////////////////////////////////////////////////////////////////////////////
class MSocketEngineObserver
	{
public:
	virtual void LogInfo(const TDesC& aBuf,const TDesC& aBuf2)=0;
	virtual void DataReceived(const TDesC8& aData)=0;
	virtual void DataSent(const TInt aError)=0;
	};

//////////////////////////////////////////////////////////////////////////////////
// we read/write upto 2k at a time from the secure socket
const TInt KMaxSocketBuffer=2048;

class CSecureSocketWriter : public CActive
	{
protected:
	// from CActive
	void DoCancel();
	void RunL();

public:
	// ew methods
	~CSecureSocketWriter();
	CSecureSocketWriter(MSocketEngineObserver* aObserver);
	TBool SendData(CSecureSocket* aSocket,const TDesC8& aData);

protected:
	MSocketEngineObserver* iObserver;

	CSecureSocket* iSecureSocket;
	TBuf8<KMaxSocketBuffer> iData;
	};

CSecureSocketWriter::CSecureSocketWriter(MSocketEngineObserver* aObserver) :
	CActive(CActive::EPriorityLow),iObserver(aObserver)
	{
	CActiveScheduler::Add(this);
	}

CSecureSocketWriter::~CSecureSocketWriter()
	{
	Cancel(); // calls DoCancel() iff we are currently active.
	}

TBool CSecureSocketWriter::SendData(CSecureSocket* aSocket,const TDesC8& aData)
// Were requested to send this data. If were currently active report that we cannot send the
// data at this time, dont take ownership of the data. Otherwise take copy of the data and 
// start sending it. 
	{
	// the last SendData() request has not yet finished. 
	if (IsActive())
		return(EFalse);

	// take local copy so caller can re-use their buffer
	iData=aData;

	// take a temporary copy of the secure socket handle so we can cancel any writes if required
	iSecureSocket=aSocket;

	// start transmission of data. It will have finished when our RunL() gets called
	iSecureSocket->Send(iData,iStatus);

	// dont forget to mark the AO as representing an outstanding event
	SetActive();

	// tell caller we started data transmission.
	return(ETrue);
	}

void CSecureSocketWriter::RunL()
// Weve finished writing, sucessfully or otherwise. 
	{
	iObserver->DataSent(iStatus.Int());

	iSecureSocket=NULL; // simply tidying up - we dont own this
	}

void CSecureSocketWriter::DoCancel()
// Cancel any outstanding activity, maybe called from destructor
// To get here we must have an outstanding Send() request.
	{
	iSecureSocket->CancelSend();

	iSecureSocket=NULL; // simply tidying up - we dont own this
	}


//////////////////////////////////////////////////////////////////////////////////
const TInt KMaxServerNameLen=256;

enum TSocketEngineStatus
	{
	ESeNotConnected=0,	// must be 0
	ESeConnecting,		// were attempting to connect to a server
	ESeLookingUp,		// translating name to IP
	ESeClientHandshake,	// establishing the secure connection
	ESeReading,			// we have a read request outstanding
	};

class CSecureSocketEngine : public CActive
	{
protected:
	// from CActive
	void DoCancel();
	void RunL();

	// new methods
	void Connect(const TUint32 aAddr);
public:
	~CSecureSocketEngine();
	CSecureSocketEngine(RSocketServ& aServer,MSocketEngineObserver* aObserver);
	void ConstructL();
	void SetServerName(const TDesC& aName);
	const TDesC& GetServerName() const;
	void SetPort(const TInt aPort);
	TInt GetPort() const;
	void Connect();

protected:
	RSocketServ& iSocketServer;				// connection to the Symbian OS socket server process
	MSocketEngineObserver* iObserver;

	RHostResolver iHostResolver;			// host name resolver
	TSocketEngineStatus iState;				// our state machine status
	TInetAddr iAddress;						// address were attempting to connect to
	TInt iPort;								// which port to connect to
    TBuf<KMaxServerNameLen> iServerName;	// which server we are to talk to
	TNameEntry iNameEntry;					// resolved name
	RSocket iSocket;						// socket though which were communicating

	CSecureSocket* iSecureSocket;			// the secure socket
	CSecureSocketWriter* iWriter;			// our AO to handle async writing of content

	TSockXfrLength iXfrLen;
	TBuf8<KMaxSocketBuffer> iRecvBuffer;	// where we read data
	};

CSecureSocketEngine::CSecureSocketEngine(RSocketServ& aServer,MSocketEngineObserver* aObserver) :
	CActive(CActive::EPriorityStandard),iSocketServer(aServer),iObserver(aObserver)
    {
	CActiveScheduler::Add(this); 
	}

CSecureSocketEngine::~CSecureSocketEngine()
    {
	// any outstanding connect/read requests
    Cancel();

	// cancel any secure socket writes before we shutdown secure socket
	delete(iWriter);

	// now all possible outstanding events cancelled we can shut down the sockets
	if (iSecureSocket)
		{
		iSecureSocket->Close();
		delete(iSecureSocket);
		iSecureSocket=NULL;
		}

	// after secure socket as it references it internally 
    iSocket.Close();
    }

void CSecureSocketEngine::ConstructL()
    {
	// this app has an AO to represent outstanding write requests
	iWriter=new(ELeave)CSecureSocketWriter(iObserver);
    }

void CSecureSocketEngine::DoCancel()
//
// Cancel whatever is currently running
//
    {
    // Cancel appropriate request to socket
    switch (iState)
        {
    case ESeConnecting:	// cancel the tcp connect request
        iSocket.CancelConnect();
        break;

	case ESeClientHandshake:
		iSecureSocket->CancelHandshake();	
		break;

	case ESeReading:
		iSecureSocket->CancelRecv();	
		break;

    case ESeLookingUp: // cancel the name look up 
        iHostResolver.Cancel();
        iHostResolver.Close();
	default:
        break;
	    }
    iState=ESeNotConnected;
    }

_LIT(KEngRunL,"Eng::RunL");
_LIT(KSecureSocket,"SecureSocket");
_LIT(KSecureSocketFailed,"SecureSocketFailed");
_LIT(KConnectFailed,"ConnectFailed");
_LIT(KConnectedOK,"Connected OK");
_LIT(KSecConnFailed,"SecConnFailed %d");
_LIT(KReadFailed,"ReadFailed");
_LIT(KResolverErr,"ResolverErr:%d");

void CSecureSocketEngine::RunL()
//
// One of our requests has completed
//
    {
    switch (iState)
        {
    case ESeConnecting:	// IP connect request has completed
		if (iStatus==KErrNone)
			{ // sucessfully established a socket level connec
			iObserver->LogInfo(KEngRunL,KSecureSocket);

			TRAPD(err,
				_LIT(KTLS1,"TLS1.0");
//				_LIT(KTLS1,"SSL3.0");
				iSecureSocket=CSecureSocket::NewL(iSocket,KTLS1);
				);

			if (err!=KErrNone)
				{
		        iSocket.Close();
			    iState=ESeNotConnected;
				iObserver->LogInfo(KEngRunL,KSecureSocketFailed);
				}
			else
				{ // perform a client handshake with the server = establish security 


				// attempt to establish a secure connection
				iSecureSocket->StartClientHandshake(iStatus);
				iState=ESeClientHandshake;
				SetActive();
				}
			}
		else
			{ // connect attempt failed, allow retry or different addr
	        iSocket.Close();
		    iState=ESeNotConnected;
			iObserver->LogInfo(KEngRunL,KConnectFailed);
			}
        break;

	case ESeClientHandshake: // establishing secure connection
		if (iStatus==KErrNone)
			{ // established a connection, queue a read for any content we get sent..
			iObserver->LogInfo(KEngRunL,KConnectedOK);

			iSecureSocket->RecvOneOrMore(iRecvBuffer,iStatus,iXfrLen);
		    iState=ESeReading;
			SetActive();
			}
		else
			{ // failed to get secure connection
			iSecureSocket->Close();
			delete(iSecureSocket);
			iSecureSocket=NULL;
	        iSocket.Close();
		    iState=ESeNotConnected;

			TBuf<64> bb;
			bb.Format(KSecConnFailed,iStatus.Int());
			iObserver->LogInfo(KEngRunL,bb);
			}
		break;

	case ESeReading:
		if (iStatus==KErrNone)	
			{ // some data has arrived for us to process

			// do something with the data received, before we reuse the buffer
			iObserver->DataReceived(iRecvBuffer);

			// read more data
			iSecureSocket->RecvOneOrMore(iRecvBuffer,iStatus,iXfrLen);
		    iState=ESeReading;
			SetActive();

⌨️ 快捷键说明

复制代码 Ctrl + C
搜索代码 Ctrl + F
全屏模式 F11
切换主题 Ctrl + Shift + D
显示快捷键 ?
增大字号 Ctrl + =
减小字号 Ctrl + -