os/kernelhwsrv/kerneltest/e32test/rm_debug/d_rmdebugserver.cpp
author sl
Tue, 10 Jun 2014 14:32:02 +0200
changeset 1 260cb5ec6c19
permissions -rw-r--r--
Update contrib.
     1 // Copyright (c) 2006-2009 Nokia Corporation and/or its subsidiary(-ies).
     2 // All rights reserved.
     3 // This component and the accompanying materials are made available
     4 // under the terms of the License "Eclipse Public License v1.0"
     5 // which accompanies this distribution, and is available
     6 // at the URL "http://www.eclipse.org/legal/epl-v10.html".
     7 //
     8 // Initial Contributors:
     9 // Nokia Corporation - initial contribution.
    10 //
    11 // Contributors:
    12 //
    13 // Description:
    14 // Provides the debug agent server implementation.
    15 // 
    16 //
    17 
    18 #include <e32base.h>
    19 #include <e32base_private.h>
    20 #include <e32cons.h>
    21 #include <trkkerneldriver.h>
    22 #include "d_rmdebugserver.h"
    23 #include "d_rmdebugclient.h"
    24 #include "t_rmdebug.h"
    25 
    26 
    27 CDebugServServer::CDebugServServer(CActive::TPriority aActiveObjectPriority)
    28    : CServer2(aActiveObjectPriority)
    29 //
    30 // Server constructor
    31 //
    32 	{
    33 	}
    34 
    35 CSession2* CDebugServServer::NewSessionL(const TVersion& /*aVersion*/, const RMessage2& /*aMessage*/) const
    36 //
    37 // Session constructor
    38 //
    39 	{
    40 	// make sure the kernel side device driver is not already loaded
    41    TInt err;
    42 	err = User::LoadLogicalDevice(KDebugDriverFileName);
    43 	if ((KErrNone == err) || (KErrAlreadyExists == err))
    44        {
    45        return new(ELeave) CDebugServSession();
    46        }
    47    else
    48        {
    49        return (NULL);
    50        }
    51 	}   
    52 
    53 CDebugServSession::CDebugServSession()
    54 // Session implementation
    55 	{
    56    TInt err;
    57 	TMetroTrkDriverInfo info;
    58    info.iUserLibraryEnd = 0;
    59    err = iKernelDriver.Open(info);
    60    if (KErrNone != err)
    61 		{
    62  		User::Leave(err);
    63 		}          
    64 	}
    65 
    66 CDebugServSession::~CDebugServSession()
    67 //
    68 // Session destructor
    69 //
    70 	{
    71 	// stop the kernel side driver
    72 	iKernelDriver.Close();
    73 
    74 	User::FreeLogicalDevice(KDebugDriverName);
    75 	}
    76 
    77 
    78 void CDebugServSession::ServiceL(const RMessage2& aMessage)
    79 //
    80 // Session service handler
    81 //
    82 	{
    83 	TInt res = KErrNone;
    84 
    85 	switch(aMessage.Function())
    86 		{
    87 		case EDebugServResumeThread:
    88 			res = ResumeThread(aMessage);
    89 			break;
    90 
    91 		case EDebugServSuspendThread:
    92 			res = SuspendThread(aMessage);
    93 			break;          
    94 
    95 //		case EDebugServReadProcessInfo:
    96 //			res = ReadProcessInfo(aMessage);
    97 //			break;        
    98 //
    99 //		case EDebugServReadThreadInfo:
   100 //			res = ReadThreadInfo(aMessage);
   101 //			break;
   102 
   103 		case EDebugServReadMemory:
   104 			res = ReadMemory(aMessage);
   105 			break;        
   106 
   107 		case EDebugServWriteMemory:
   108 			res = WriteMemory(aMessage);
   109 			break;        
   110 
   111 		default:
   112 			User::Leave(KErrNotSupported);
   113 			break;
   114 		}
   115 
   116 	aMessage.Complete(res);
   117 	}
   118 
   119 
   120 
   121 TInt CDebugServSession::SuspendThread(const RMessage2& aMessage)
   122 //
   123 // Session suspend thread
   124 //
   125 	{
   126 	TInt err;
   127 
   128 	err = iKernelDriver.SuspendThread(aMessage.Int0());
   129 
   130 	return err;
   131 	}
   132 
   133 TInt CDebugServSession::ResumeThread(const RMessage2& aMessage)
   134 //
   135 // Server resume thread
   136 //
   137 	{
   138 	TInt err;
   139 
   140 	err = iKernelDriver.ResumeThread(aMessage.Int0());
   141 
   142 	return err;
   143 	}
   144 
   145 //TInt CDebugServSession::ReadProcessInfo(const RMessage2& aMessage)
   146 ////
   147 //// Server read process information
   148 ////
   149 //	{
   150 //	TInt err;
   151 //	TProcessInfo procinfo;
   152 //	TMetroTrkTaskInfo processInfo(0);
   153 //
   154 //	err = iKernelDriver.GetProcessInfo(aMessage.Int0(), processInfo);
   155 //
   156 //	if (KErrNone == err)
   157 //		{
   158 //		procinfo.iProcessID = processInfo.iId;
   159 //		procinfo.iPriority = processInfo.iPriority;
   160 //		procinfo.iName.Copy(processInfo.iName);
   161 //
   162 //		TPckgBuf<TProcessInfo> p(procinfo);
   163 //		aMessage.WriteL(1,p);        
   164 //		}
   165 //
   166 //	return err;
   167 //	}
   168 //
   169 //TInt CDebugServSession::ReadThreadInfo(const RMessage2& aMessage)
   170 ////
   171 //// Server read thread information
   172 ////
   173 //	{
   174 //	TInt err;
   175 //	TThreadInfo thrdinfo;
   176 //	TMetroTrkTaskInfo threadInfo(aMessage.Int1()); // Sets OtherID to the second input parameter in aMessage
   177 //
   178 //	// aMessage.Int0 is the index into the thread list for the process
   179 //	err = iKernelDriver.GetThreadInfo(aMessage.Int0(), threadInfo);	   
   180 //
   181 //	if (KErrNone == err)
   182 //		{
   183 //		thrdinfo.iThreadID = threadInfo.iId;
   184 //		thrdinfo.iPriority = threadInfo.iPriority;
   185 //		thrdinfo.iName.Copy(threadInfo.iName);
   186 //		thrdinfo.iOwningProcessID = threadInfo.iOtherId;
   187 //
   188 //		TPckgBuf<TThreadInfo> p(thrdinfo);
   189 //
   190 //		// Write out the results to the third argument passed in (pointer to the threadinfo structure)
   191 //		aMessage.WriteL(2,p);           
   192 //		}
   193 //
   194 //	return err;
   195 //	}
   196 
   197 TInt CDebugServSession::ReadMemory(const RMessage2& aMessage)
   198 //
   199 // Server read process memory
   200 //
   201 	{   
   202 	TInt err;
   203 	TUint32 threadId = aMessage.Int0();
   204 	TPckgBuf<TMemoryInfo> pckg = *(TPckgBuf<TMemoryInfo> *)(aMessage.Ptr1());
   205 	TMemoryInfo* InputMemoryInfo = &pckg();
   206 
   207 	TPtr8 *ptrtst = InputMemoryInfo->iDataPtr;
   208 
   209 	err = iKernelDriver.ReadMemory(threadId, InputMemoryInfo->iAddress, InputMemoryInfo->iSize, *ptrtst);
   210 
   211 	return err;
   212 	}
   213 
   214 TInt CDebugServSession::WriteMemory(const RMessage2& aMessage)
   215 //
   216 // Server write process memory
   217 //
   218 	{
   219 	TInt err;
   220 	TUint32 threadId = aMessage.Int0();
   221 	TPckgBuf<TMemoryInfo> pckg = *(TPckgBuf<TMemoryInfo> *)(aMessage.Ptr1());
   222 	TMemoryInfo* InputMemoryInfo = &pckg();
   223 
   224 	TPtr8 *ptrtst = InputMemoryInfo->iDataPtr;
   225 
   226 	err = iKernelDriver.WriteMemory(threadId, InputMemoryInfo->iAddress, InputMemoryInfo->iSize, *ptrtst);
   227 
   228 	return err;
   229 	}
   230 
   231 
   232 GLDEF_C TInt CDebugServServer::ThreadFunction(TAny*)
   233 //
   234 // Server thread function, continues until active scheduler stops
   235 //
   236 	{
   237 	CTrapCleanup* cleanup=CTrapCleanup::New();
   238 	if (cleanup == NULL)
   239 		{
   240 		User::Leave(KErrNoMemory);
   241 		}
   242 
   243 	CActiveScheduler *pA=new CActiveScheduler;
   244 	CDebugServServer *pS=new CDebugServServer(EPriorityStandard);
   245 
   246 	CActiveScheduler::Install(pA);
   247 
   248 	TInt err = pS->Start(KDebugServerName);
   249 	if (err != KErrNone)
   250 		{
   251 		User::Leave(KErrNone);
   252 		}
   253 
   254 	RThread::Rendezvous(KErrNone);
   255 
   256 	CActiveScheduler::Start();
   257 
   258 	delete pS;
   259 	delete pA;
   260 	delete cleanup;
   261 
   262 	return (KErrNone);
   263 	}
   264 
   265 
   266 
   267 EXPORT_C TInt StartThread(RThread& aServerThread)
   268 //
   269 // Start the server thread
   270 //
   271 	{
   272 	TInt res=KErrNone;
   273 
   274 	TFindServer finddebugserver(KDebugServerName);
   275 	TFullName name;
   276 
   277 	if (finddebugserver.Next(name) != KErrNone)
   278 		{
   279 		res = aServerThread.Create( KDebugServerName,
   280 									CDebugServServer::ThreadFunction,
   281 									KDefaultStackSize,
   282 									KDefaultHeapSize,
   283 									KDefaultHeapSize,
   284 									NULL
   285 									);
   286 
   287 		if (res == KErrNone)
   288 			{
   289 			TRequestStatus rendezvousStatus;
   290 
   291 			aServerThread.SetPriority(EPriorityNormal);
   292 			aServerThread.Rendezvous(rendezvousStatus);
   293 			aServerThread.Resume();
   294 			User::WaitForRequest(rendezvousStatus);
   295 			}                                 
   296 		else
   297 			{
   298 			aServerThread.Close();
   299 			}
   300 		}
   301 
   302 	return res;
   303 	}
   304 
   305 
   306 
   307 RDebugServSession::RDebugServSession()
   308 //
   309 // Server session constructor
   310 //
   311 	{
   312 	}
   313 
   314 TInt RDebugServSession::Open()
   315 //
   316 // Session open
   317 //
   318 	{
   319 	TInt r = StartThread(iServerThread);
   320 	if (r == KErrNone)
   321 		{
   322 		r=CreateSession(KDebugServerName, Version(), KDefaultMessageSlots);
   323 		}
   324 
   325 	return r;
   326 	}
   327 
   328 
   329 TVersion RDebugServSession::Version(void) const
   330 //
   331 // Session version
   332 //
   333 	{
   334 	return (TVersion(KDebugServMajorVersionNumber, KDebugServMinorVersionNumber, KDebugServBuildVersionNumber));
   335 	}
   336 
   337 TInt RDebugServSession::SuspendThread(const TInt aThreadID)
   338 //
   339 // Session suspend thread request
   340 //
   341 	{
   342 	TIpcArgs args(aThreadID);
   343 	TInt res;
   344 	res = SendReceive(EDebugServSuspendThread, args);
   345 
   346 	return res;
   347 	}
   348 
   349 TInt RDebugServSession::ResumeThread(const TInt aThreadID)
   350 //
   351 // Session resume thread request
   352 //
   353 	{
   354 	TIpcArgs args(aThreadID);
   355 	TInt res;
   356 	res = SendReceive(EDebugServResumeThread, args);
   357 
   358 	return res;
   359 	}
   360 
   361 
   362 //TInt RDebugServSession::ReadProcessInfo(const TInt aIndex, TProcessInfo* aInfo)
   363 ////
   364 //// Session read process information request
   365 ////
   366 //	{
   367 //	TPckgBuf<TProcessInfo> pckg;
   368 //	pckg = *aInfo;
   369 //
   370 //	TIpcArgs args(aIndex, &pckg);
   371 //
   372 //	TInt res;
   373 //
   374 //	res = SendReceive(EDebugServReadProcessInfo, args);
   375 //
   376 //	*aInfo = pckg();
   377 //
   378 //	return res;
   379 //
   380 //	}
   381 //
   382 //TInt RDebugServSession::ReadThreadInfo(const TInt aIndex, const TInt aProc, TThreadInfo* aInfo)
   383 ////
   384 //// Session read thread information request
   385 ////
   386 //	{
   387 //	TPckgBuf<TThreadInfo> pckg;
   388 //	pckg = *aInfo;
   389 //
   390 //	TIpcArgs args(aIndex, aProc, &pckg);
   391 //
   392 //	TInt res;
   393 //
   394 //	res = SendReceive(EDebugServReadThreadInfo, args);
   395 //
   396 //	*aInfo = pckg();
   397 //
   398 //	return res;
   399 //
   400 //	}
   401 
   402 
   403 TInt RDebugServSession::ReadMemory(const TUint32 aThreadID, TMemoryInfo* aInfo)
   404 //
   405 // Session read thread memory request
   406 //
   407 	{
   408 	TPckgBuf<TMemoryInfo> pckg;
   409 	pckg = *aInfo;
   410 
   411 	TIpcArgs args(aThreadID, &pckg);
   412 
   413 	TInt res;
   414 
   415 	res = SendReceive(EDebugServReadMemory, args);
   416 
   417 	*aInfo = pckg();
   418 
   419 	return res;
   420 
   421 	}
   422 
   423 
   424 TInt RDebugServSession::WriteMemory(const TUint32 aThreadID, TMemoryInfo* aInfo)
   425 //
   426 // Session write thread memory request
   427 //
   428 	{
   429 	TPckgBuf<TMemoryInfo> pckg;
   430 	pckg = *aInfo;
   431 
   432 	TIpcArgs args(aThreadID, &pckg);
   433 
   434 	TInt res;
   435 
   436 	res = SendReceive(EDebugServWriteMemory, args);
   437 
   438 	return res;
   439 	}
   440 
   441 
   442 
   443 TInt RDebugServSession::Close()
   444 //
   445 // Session close the session and thread
   446 //
   447 	{
   448 	RSessionBase::Close();
   449 	iServerThread.Close();
   450 
   451 	return KErrNone;
   452 	}
   453