diff -r f5050f1da672 -r 04becd199f91 javacommons/comms/ipclib/clientserver/src.s60/ipcclient.cpp --- /dev/null Thu Jan 01 00:00:00 1970 +0000 +++ b/javacommons/comms/ipclib/clientserver/src.s60/ipcclient.cpp Tue Apr 27 16:30:29 2010 +0300 @@ -0,0 +1,198 @@ +/* +* Copyright (c) 2008 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: IpcClient is the client side implementation +* +*/ +#include +#include +#include + +#include "logger.h" +#include "javasymbianoslayer.h" + +#include "ipcclient.h" +#include "rcomms.h" +#include "creceiver.h" +#include "common.h" + +namespace java +{ +namespace comms +{ +using java::util::ScopedLock; + +IpcClient::IpcClient(IpcListener* aListener) : CActive(EPriorityStandard), + mAddress(0), mRunning(false), mReceiver(0), mListener(aListener) +{ +} + +IpcClient::~IpcClient() +{ +} + +int IpcClient::connect(int aAddr) +{ + ScopedLock lock(mMutex); + + if (mRunning) return 0; + + mAddress = aAddr; + // create unique thread name + std::stringstream name; + name << "JavaCommsClient-" << mAddress << "-" << this << "-" << rand(); + std::auto_ptr threadName(stringToDes(name.str().c_str())); + + TInt rc = mThread.Create( + threadName->Des(), + reinterpret_cast(messageLoop), + KCommsStackSize, + NULL, + this); + + if (rc == KErrNone) + { + // make sure that thread has been started ok before we continue. + TRequestStatus rendezvousStatus; + mThread.Rendezvous(rendezvousStatus); + mThread.Resume(); + User::WaitForRequest(rendezvousStatus); + rc = rendezvousStatus.Int(); + if (rc == KErrNone) + { + mRunning = true; + } + } + + if (rc != KErrNone) + { + mThread.Close(); + ELOG3(EJavaComms, "%s failed to java-comms-%d, err = %d", __PRETTY_FUNCTION__, aAddr, rc); + } + + return rc; +} + +void IpcClient::disconnect() +{ + ScopedLock lock(mMutex); + + if (!mRunning) return; + + TRequestStatus status; + mThread.Logon(status); + + TRequestStatus* istatus = &iStatus; + mThread.RequestComplete(istatus, KErrNone); + + User::WaitForRequest(status); + mThread.Close(); + LOG1(EJavaComms, EInfo, "IpcClient disconnected from java-comms-%d", mAddress); +} + +void IpcClient::error(TInt aError) +{ + ELOG2(EJavaComms, "%s, err = %d", __PRETTY_FUNCTION__, aError); + TRequestStatus* status = &iStatus; + User::RequestComplete(status, aError); +} + + +int IpcClient::send(ipcMessage_t* aMsg) +{ +// ScopedLock lock(mMutex); + + int rc = KErrNotReady; + if (mRunning) + { + std::auto_ptr msg(messageToDes(*aMsg)); + rc = mComms.Send(msg->Des()); + } + + if (rc) + { + ELOG2(EJavaComms, "%s failed, err = %d", __PRETTY_FUNCTION__, rc); + } + return rc; +} + +void IpcClient::RunL() +{ +// JELOG2(EJavaComms); + mRunning = false; // don't allow sends while exiting + + mReceiver->Cancel(); + mComms.Disconnect(); + CActiveScheduler::Stop(); +} + +void IpcClient::DoCancel() +{ + ELOG1(EJavaComms, "%s", __PRETTY_FUNCTION__); +} + +TInt IpcClient::RunError(TInt aError) +{ + ELOG2(EJavaComms, "%s, err = %d", __PRETTY_FUNCTION__, aError); + return KErrNone; +} + +void IpcClient::messageLoop(TAny* aArgs) +{ + std::auto_ptr cleanup(CTrapCleanup::New()); + TInt r = KErrNoMemory; + if (cleanup.get()) + { + IpcClient* me = reinterpret_cast(aArgs); + TRAP(r,me->doMainL()); + me->mListener->onExit(); + me->mRunning = false; + } + // disconnect blocks until this notification + RThread::Rendezvous(r); +} + +void IpcClient::doMainL() +{ + CActiveScheduler* s = new(ELeave) CActiveScheduler; + CleanupStack::PushL(s); + CActiveScheduler::Install(s); + + std::stringstream address; + address << "java-comms-" << mAddress; + + std::auto_ptr serverName(stringToDes(address.str().c_str())); + + User::LeaveIfError(mComms.Connect(serverName->Des())); + LOG1(EJavaComms, EInfo, "IpcClient connected to %s", address.str().c_str()); + + mReceiver = new(ELeave) CReceiver(*this, *mListener, mComms); + CleanupStack::PushL(mReceiver); + mReceiver->Receive(); + + CActiveScheduler::Add(this); + iStatus = KRequestPending; + SetActive(); + + // connect blocks until this notification + RThread::Rendezvous(KErrNone); + mListener->onStart(); + + CActiveScheduler::Start(); + + CleanupStack::PopAndDestroy(mReceiver); + CleanupStack::PopAndDestroy(s); +} + +} // namespace comms +} // namespace java