tsrc/testtools/usbman_stub/usbman/client/src/RUsb.cpp
branchRCL_3
changeset 92 dde4619868dc
parent 86 703a2b94c06c
child 95 55a3258355ea
equal deleted inserted replaced
86:703a2b94c06c 92:dde4619868dc
     1 /*
       
     2 * Copyright (c) 2010 Nokia Corporation and/or its subsidiary(-ies).
       
     3 * All rights reserved.
       
     4 * This component and the accompanying materials are made available
       
     5 * under the terms of "Eclipse Public License v1.0"
       
     6 * which accompanies this distribution, and is available
       
     7 * at the URL "http://www.eclipse.org/legal/epl-v10.html".
       
     8 *
       
     9 * Initial Contributors:
       
    10 * Nokia Corporation - initial contribution.
       
    11 *
       
    12 * Contributors:
       
    13 *
       
    14 * Description:
       
    15 *
       
    16 */
       
    17 
       
    18 #include <e32uid.h>
       
    19 #include <f32file.h>
       
    20 #include <usbman.h>
       
    21 #include <usb.h>
       
    22 #include <e32base.h>
       
    23 #include "rusb.h"
       
    24 #include <usb/usblogger.h>
       
    25 #include <stubber.h>
       
    26 #include "usbmandll_stub.h"
       
    27 #include <usbpersonalityids.h>
       
    28 
       
    29 #ifdef __FLOG_ACTIVE
       
    30 _LIT8(KLogComponent, "USBMAN");
       
    31 #endif
       
    32 
       
    33 #ifdef __USBMAN_NO_PROCESSES__
       
    34 #include <e32math.h>
       
    35 #endif
       
    36 
       
    37 // CONSTANTS
       
    38 //const TUint KUsbAllStates = 0xFFFFFFFF;
       
    39 
       
    40 _LIT8(KLogStub, "[USBMAN] [Stub]");
       
    41 
       
    42 static TInt StartServer()
       
    43 //
       
    44 // Start the server process or thread
       
    45 //
       
    46 	{
       
    47 	const TUidType serverUid(KNullUid, KNullUid, KUsbmanSvrUid);
       
    48 
       
    49 #ifdef __USBMAN_NO_PROCESSES__
       
    50 	//
       
    51 	// In EKA1 WINS the server is a DLL, the exported entrypoint returns a TInt
       
    52 	// which represents the real entry-point for the server thread
       
    53 	//
       
    54 	RLibrary lib;
       
    55 	TInt err = lib.Load(KUsbmanImg, serverUid);
       
    56 	
       
    57 	if (err != KErrNone)
       
    58 		{
       
    59 		return err;
       
    60 		}
       
    61 
       
    62 	TLibraryFunction ordinal1 = lib.Lookup(1);
       
    63 	TThreadFunction serverFunc = reinterpret_cast<TThreadFunction>(ordinal1());
       
    64 
       
    65 	//
       
    66 	// To deal with the unique thread (+semaphore!) naming in EPOC, and that we may
       
    67 	// be trying to restart a server that has just exited we attempt to create a
       
    68 	// unique thread name for the server.
       
    69 	// This uses Math::Random() to generate a 32-bit random number for the name
       
    70 	//
       
    71 	TName name(KUsbServerName);
       
    72 	name.AppendNum(Math::Random(),EHex);
       
    73 	
       
    74 	RThread server;
       
    75 	err = server.Create (
       
    76 		name,
       
    77 		serverFunc,
       
    78 		KUsbmanStackSize,
       
    79 		NULL,
       
    80 		&lib,
       
    81 		NULL,
       
    82 		KUsbmanMinHeapSize,
       
    83 		KUsbmanMaxHeapSize,
       
    84 		EOwnerProcess
       
    85 	);
       
    86 
       
    87 	lib.Close();	// if successful, server thread has handle to library now
       
    88 #else
       
    89 	//
       
    90 	// EPOC and EKA2 is easy, we just create a new server process. Simultaneous
       
    91 	// launching of two such processes should be detected when the second one
       
    92 	// attempts to create the server object, failing with KErrAlreadyExists.
       
    93 	//
       
    94 	RProcess server;
       
    95 	TInt err = server.Create(KUsbmanImg, KNullDesC, serverUid);
       
    96 #endif //__USBMAN_NO_PROCESSES__
       
    97 	
       
    98 	if (err != KErrNone)
       
    99 		{
       
   100 		return err;
       
   101 		}
       
   102 
       
   103 	TRequestStatus stat;
       
   104 	server.Rendezvous(stat);
       
   105 	
       
   106 	if (stat!=KRequestPending)
       
   107 		server.Kill(0);		// abort startup
       
   108 	else
       
   109 		server.Resume();	// logon OK - start the server
       
   110 
       
   111 	User::WaitForRequest(stat);		// wait for start or death
       
   112 
       
   113 	// we can't use the 'exit reason' if the server panicked as this
       
   114 	// is the panic 'reason' and may be '0' which cannot be distinguished
       
   115 	// from KErrNone
       
   116 	err = (server.ExitType() == EExitPanic) ? KErrServerTerminated : stat.Int();
       
   117 
       
   118 	server.Close();
       
   119 	
       
   120 	LOGTEXT2(_L8("USB server started successfully: err = %d\n"),err);
       
   121 
       
   122 	return err;
       
   123 	}
       
   124 
       
   125 
       
   126 
       
   127 
       
   128 EXPORT_C RUsb::RUsb() 
       
   129 	: iDeviceStatePkg(0), iServiceStatePkg(0), iMessagePkg(0), 
       
   130 	  iHostPkg(TDeviceEventInformation())
       
   131 	{
       
   132 	LOG_LINE
       
   133 	LOG_FUNC
       
   134 	}
       
   135 
       
   136 EXPORT_C RUsb::~RUsb()
       
   137 	{
       
   138 	LOG_LINE
       
   139 	LOG_FUNC
       
   140 	}
       
   141 
       
   142 EXPORT_C TVersion RUsb::Version() const
       
   143 	{
       
   144 	return(TVersion(KUsbSrvMajorVersionNumber,KUsbSrvMinorVersionNumber,KUsbSrvBuildVersionNumber));
       
   145 	}
       
   146 
       
   147 EXPORT_C TInt RUsb::Connect()
       
   148 	{
       
   149 	LOG_LINE
       
   150 	LOG_FUNC
       
   151 
       
   152 	TInt retry = 2;
       
   153 	
       
   154 	FOREVER
       
   155 		{
       
   156 		// Create the session to UsbSrv with 10 asynchronous message slots
       
   157 		TInt err = CreateSession(KUsbServerName, Version(), 10);
       
   158 
       
   159 		if ((err != KErrNotFound) && (err != KErrServerTerminated))
       
   160 			{
       
   161 			return err;
       
   162 			}
       
   163 
       
   164 		if (--retry == 0)
       
   165 			{
       
   166 			return err;
       
   167 			}
       
   168 
       
   169 		err = StartServer();		
       
   170 		
       
   171 		if ((err != KErrNone) && (err != KErrAlreadyExists))
       
   172 			{
       
   173 			return err;
       
   174 			}
       
   175 		}
       
   176 	}
       
   177 
       
   178 EXPORT_C void RUsb::Start(TRequestStatus& aStatus)
       
   179 	{
       
   180 	LOG_LINE
       
   181 	LOG_FUNC
       
   182 
       
   183 	SendReceive(EUsbStart, aStatus);
       
   184 	}
       
   185 
       
   186 EXPORT_C void RUsb::StartCancel()
       
   187 	{
       
   188 	LOG_LINE
       
   189 	LOG_FUNC
       
   190 
       
   191 	SendReceive(EUsbStartCancel);
       
   192 	}
       
   193 
       
   194 EXPORT_C void RUsb::Stop()
       
   195 	{
       
   196 	LOG_LINE
       
   197 	LOG_FUNC
       
   198 
       
   199 	SendReceive(EUsbStop);
       
   200 	}
       
   201 
       
   202 EXPORT_C void RUsb::Stop(TRequestStatus& aStatus)
       
   203 	{
       
   204 	LOG_LINE
       
   205 	LOG_FUNC
       
   206 
       
   207 	SendReceive(EUsbStop, aStatus);
       
   208 	}
       
   209 
       
   210 EXPORT_C void RUsb::StopCancel()
       
   211 	{
       
   212 	LOG_LINE
       
   213 	LOG_FUNC
       
   214 
       
   215 	SendReceive(EUsbStopCancel);
       
   216 	}
       
   217 
       
   218 EXPORT_C TInt RUsb::GetServiceState(TUsbServiceState& aState)
       
   219 	{
       
   220 	LOG_LINE
       
   221 	LOG_FUNC
       
   222 
       
   223 	CStubber* stubber = CStubber::NewL();
       
   224 	TApiBehavior beh( KUsbManStubAgentDll, EServiceState, 0, 0, KNullDesC8 );
       
   225 	stubber -> InvokeApi( beh );
       
   226 
       
   227 	delete stubber;
       
   228 	stubber = NULL;
       
   229 
       
   230 	if ( beh.iOutput != KNullDesC8 )
       
   231 	    {           
       
   232 	    if ( !beh.iOutput.Compare( _L8( "EUsbServiceIdle" ) ) )
       
   233 	        aState = EUsbServiceIdle;
       
   234 	    else if ( !beh.iOutput.Compare( _L8( "EUsbServiceStarting" ) ) )
       
   235             aState = EUsbServiceStarting;
       
   236 	    else if ( !beh.iOutput.Compare( _L8( "EUsbServiceStarted" ) ) )
       
   237             aState = EUsbServiceStarted;
       
   238 	    else if ( !beh.iOutput.Compare( _L8( "EUsbServiceStopping" ) ) )
       
   239             aState = EUsbServiceStopping;
       
   240 	    else if ( !beh.iOutput.Compare( _L8( "EUsbServiceFatalError" ) ) )
       
   241             aState = EUsbServiceFatalError;
       
   242 	    else
       
   243 	    	{}
       
   244 	    }
       
   245     else
       
   246         {
       
   247 		TPckg<TUint32> pkg(aState);
       
   248 		TInt ret=SendReceive(EUsbGetCurrentState, TIpcArgs(&pkg));
       
   249 		aState=(TUsbServiceState)pkg();
       
   250 		return ret;
       
   251         }
       
   252 	return beh.iCompleteCode;
       
   253 	}
       
   254 
       
   255 EXPORT_C TInt RUsb::GetCurrentState(TUsbServiceState& aState)
       
   256 	{
       
   257 	LOG_LINE
       
   258 	LOG_FUNC
       
   259 
       
   260 	return GetServiceState(aState);
       
   261 	}
       
   262 
       
   263 EXPORT_C void RUsb::ServiceStateNotification(TUsbServiceState& aState,
       
   264 	TRequestStatus& aStatus)
       
   265 	{
       
   266 	LOG_LINE
       
   267 	LOG_FUNC
       
   268 
       
   269 	iServiceStatePkg.Set((TUint8*)&aState, sizeof(TUint32), sizeof(TUint32));
       
   270 
       
   271 	SendReceive(EUsbRegisterServiceObserver, TIpcArgs(&iServiceStatePkg), aStatus);
       
   272 	}
       
   273 
       
   274 EXPORT_C void RUsb::ServiceStateNotificationCancel()
       
   275 	{
       
   276 	LOG_LINE
       
   277 	LOG_FUNC
       
   278 
       
   279 	SendReceive(EUsbCancelServiceObserver);
       
   280 	}
       
   281 
       
   282 EXPORT_C TInt RUsb::GetDeviceState(TUsbDeviceState& aState)
       
   283 	{
       
   284 	LOG_LINE
       
   285 	LOG_FUNC
       
   286 
       
   287 	_LIT8( KLogStubConfigured, "[USBMAN] [StubConfigured]");
       
   288 	CUsbLog::Write(KLogStub, KNullDesC8());
       
   289 	
       
   290 	CStubber* stubber = CStubber::NewL();
       
   291 	TApiBehavior beh( KUsbManStubAgentDll, EGetDeviceState, 0, 0, KNullDesC8 );
       
   292 	stubber -> InvokeApi( beh );
       
   293 
       
   294 	delete stubber;
       
   295 	stubber = NULL;
       
   296 
       
   297 	if ( beh.iOutput != KNullDesC8 )
       
   298 	    {           
       
   299 	    CUsbLog::Write(KLogStub, KNullDesC8());
       
   300 	    if ( !beh.iOutput.Compare( _L8( "EUsbDeviceStateUndefined" ) ) )
       
   301 	        aState = EUsbDeviceStateUndefined;
       
   302 	    else if ( !beh.iOutput.Compare( _L8( "EUsbDeviceStateDefault" ) ) )
       
   303             aState = EUsbDeviceStateDefault;
       
   304 	    else if ( !beh.iOutput.Compare( _L8( "EUsbDeviceStateAttached" ) ) )
       
   305             aState = EUsbDeviceStateAttached;
       
   306 	    else if ( !beh.iOutput.Compare( _L8( "EUsbDeviceStatePowered" ) ) )
       
   307             aState = EUsbDeviceStatePowered;
       
   308 	    else if ( !beh.iOutput.Compare( _L8( "EUsbDeviceStateConfigured" ) ) )
       
   309 	    	{
       
   310             aState = EUsbDeviceStateConfigured;
       
   311     	    CUsbLog::Write(KLogStubConfigured, KNullDesC8());
       
   312 	    	}
       
   313 	    else if ( !beh.iOutput.Compare( _L8( "EUsbDeviceStateAddress" ) ) )
       
   314             aState = EUsbDeviceStateAddress;
       
   315 	    else if ( !beh.iOutput.Compare( _L8( "EUsbDeviceStateSuspended" ) ) )
       
   316             aState = EUsbDeviceStateSuspended;
       
   317 	    else
       
   318 	    	{}
       
   319 	    }
       
   320     else
       
   321         {
       
   322         _LIT8(KLogNoStub, "[USBMAN] [NoStub]");
       
   323         CUsbLog::Write(KLogNoStub, KNullDesC8());
       
   324 		TPckg<TUint32> pkg(aState);
       
   325 		TInt ret=SendReceive(EUsbGetCurrentDeviceState, TIpcArgs(&pkg));
       
   326 		aState=(TUsbDeviceState)pkg();
       
   327 		return ret;
       
   328         }
       
   329 		
       
   330 	return beh.iCompleteCode;
       
   331 	}
       
   332 
       
   333 EXPORT_C void RUsb::DeviceStateNotification(TUint aEventMask, TUsbDeviceState& aState,
       
   334 											TRequestStatus& aStatus)
       
   335 	{
       
   336 	LOG_LINE
       
   337 	LOG_FUNC
       
   338 
       
   339     CUsbLog::Write(KLogStub, KNullDesC8());
       
   340     CStubber* stubber = CStubber::NewL();
       
   341     TApiBehavior beh( KUsbManStubAgentDll, EDeviceStateNotification, 0, 0, KNullDesC8 );
       
   342     stubber -> InvokeApi( beh );
       
   343 
       
   344     delete stubber;
       
   345     stubber = NULL;
       
   346     
       
   347     TRequestStatus* stat = &aStatus;
       
   348     
       
   349     if ( beh.iOutput != KNullDesC8 )
       
   350         {                        
       
   351         if ( !beh.iOutput.Compare( _L8( "EUsbDeviceStateUndefined" ) ) )
       
   352             aState = EUsbDeviceStateUndefined;
       
   353         else if ( !beh.iOutput.Compare( _L8( "EUsbDeviceStateDefault" ) ) )
       
   354             aState = EUsbDeviceStateDefault;
       
   355         else if ( !beh.iOutput.Compare( _L8( "EUsbDeviceStateAttached" ) ) )
       
   356             aState = EUsbDeviceStateAttached;
       
   357         else if ( !beh.iOutput.Compare( _L8( "EUsbDeviceStatePowered" ) ) )
       
   358             aState = EUsbDeviceStatePowered;
       
   359         else if ( !beh.iOutput.Compare( _L8( "EUsbDeviceStateConfigured" ) ) )
       
   360             aState = EUsbDeviceStateConfigured;
       
   361         else if ( !beh.iOutput.Compare( _L8( "EUsbDeviceStateAddress" ) ) )
       
   362             aState = EUsbDeviceStateAddress;
       
   363         else if ( !beh.iOutput.Compare( _L8( "EUsbDeviceStateSuspended" ) ) )
       
   364             aState = EUsbDeviceStateSuspended;
       
   365         else
       
   366             {}
       
   367         User::RequestComplete( stat, beh.iAsyncCompleteCode );
       
   368         }
       
   369     else
       
   370         {
       
   371         iDeviceStatePkg.Set((TUint8*)&aState, sizeof(TUint32), sizeof(TUint32));
       
   372         SendReceive(EUsbRegisterObserver, TIpcArgs(aEventMask, &iDeviceStatePkg), aStatus);
       
   373         }
       
   374 
       
   375 	}
       
   376 
       
   377 EXPORT_C void RUsb::DeviceStateNotificationCancel()
       
   378 	{
       
   379 	LOG_LINE
       
   380 	LOG_FUNC
       
   381 
       
   382     CStubber* stubber = CStubber::NewL();
       
   383     TApiBehavior beh( KUsbManStubAgentDll, EDeviceStateNotificationCancel, 0, 0, KNullDesC8 );
       
   384     stubber -> InvokeApi( beh );
       
   385 
       
   386     delete stubber;
       
   387     stubber = NULL;
       
   388     
       
   389     if ( beh.iOutput != KNullDesC8 )
       
   390         {        
       
   391         
       
   392         }
       
   393     else 
       
   394     	{
       
   395     	SendReceive(EUsbCancelObserver);
       
   396     	}
       
   397 	}
       
   398 
       
   399 EXPORT_C void RUsb::StateNotification(TUint aEventMask, TUsbDeviceState& aState, TRequestStatus& aStatus)
       
   400 	{
       
   401 	LOG_LINE
       
   402 	LOG_FUNC
       
   403 
       
   404 	DeviceStateNotification(aEventMask, aState, aStatus);
       
   405 	}
       
   406 
       
   407 EXPORT_C void RUsb::StateNotificationCancel()
       
   408 	{
       
   409 	LOG_LINE
       
   410 	LOG_FUNC
       
   411 
       
   412 	DeviceStateNotificationCancel();
       
   413 	}
       
   414 	
       
   415 EXPORT_C void RUsb::TryStart(TInt aPersonalityId, TRequestStatus& aStatus)
       
   416 	{
       
   417 	LOG_LINE
       
   418 	LOG_FUNC
       
   419 
       
   420     CStubber* stubber = CStubber::NewL();
       
   421     TApiBehavior beh( KUsbManStubAgentDll, ETryStartAsync, 0, 0, KNullDesC8 );
       
   422     stubber -> InvokeApi( beh );
       
   423     
       
   424     delete stubber;
       
   425     stubber = NULL;
       
   426     
       
   427     if ( beh.iOutput != KNullDesC8 )
       
   428         {
       
   429         TRequestStatus* stat = &aStatus;
       
   430         User::RequestComplete( stat, beh.iAsyncCompleteCode );
       
   431         }
       
   432     else
       
   433         {    
       
   434 		TIpcArgs ipcArgs(aPersonalityId);
       
   435 		SendReceive(EUsbTryStart, ipcArgs, aStatus);
       
   436         }
       
   437 	}
       
   438 
       
   439 EXPORT_C void RUsb::TryStop(TRequestStatus& aStatus)
       
   440 	{
       
   441 	LOG_LINE
       
   442 	LOG_FUNC
       
   443 
       
   444     CStubber* stubber = CStubber::NewL();
       
   445     TApiBehavior beh( KUsbManStubAgentDll, ETryStopAsync, 0, 0, KNullDesC8 );
       
   446     stubber -> InvokeApi( beh );
       
   447     
       
   448     delete stubber;
       
   449     stubber = NULL;
       
   450     
       
   451     if ( beh.iOutput != KNullDesC8 )
       
   452         {
       
   453         TRequestStatus* stat = &aStatus;
       
   454         User::RequestComplete( stat, beh.iAsyncCompleteCode );
       
   455         }
       
   456     else
       
   457     	SendReceive(EUsbTryStop, aStatus);
       
   458 	}
       
   459 	
       
   460 EXPORT_C TInt RUsb::CancelInterest(TUsbReqType aMessageId)
       
   461 	{
       
   462 	LOG_LINE
       
   463 	LOG_FUNC
       
   464 
       
   465     CStubber* stubber = CStubber::NewL();
       
   466     TApiBehavior beh( KUsbManStubAgentDll, ECancelInterest, 0, 0, KNullDesC8 );
       
   467     stubber -> InvokeApi( beh );
       
   468     
       
   469     delete stubber;
       
   470     stubber = NULL;
       
   471 	
       
   472     if ( beh.iOutput != KNullDesC8 )
       
   473         {
       
   474         
       
   475         }
       
   476     else
       
   477         {
       
   478 		TInt messageId;
       
   479 		switch (aMessageId)
       
   480 			{
       
   481 		case EStart:
       
   482 			messageId = EUsbStart;
       
   483 			break;
       
   484 		case EStop:
       
   485 			messageId = EUsbStop;
       
   486 			break;
       
   487 		case ETryStart:
       
   488 			messageId = EUsbTryStart;
       
   489 			break;
       
   490 		case ETryStop:
       
   491 			messageId = EUsbTryStop;
       
   492 			break;
       
   493 		default:
       
   494 			return KErrNotSupported;
       
   495 			}
       
   496 			
       
   497 		TIpcArgs ipcArgs(messageId);
       
   498 		return SendReceive(EUsbCancelInterest, ipcArgs);
       
   499         }
       
   500 
       
   501     return beh.iCompleteCode;
       
   502 	}
       
   503 
       
   504 EXPORT_C TInt RUsb::GetDescription(TInt aPersonalityId, HBufC*& aLocalizedPersonalityDescriptor)
       
   505 	{
       
   506 	LOG_LINE
       
   507 	LOG_FUNC
       
   508 
       
   509 	TInt ret = KErrNone;
       
   510 	// caller is responsible for freeing up memory allocatd for aLocalizedPersonalityDescriptor
       
   511 	TRAP(ret, aLocalizedPersonalityDescriptor = HBufC::NewL(KUsbStringDescStringMaxSize));
       
   512 	if (ret == KErrNone)
       
   513 		{
       
   514 		TPtr ptr = aLocalizedPersonalityDescriptor->Des();
       
   515 		TIpcArgs ipcArgs(0, &ptr);
       
   516 		ipcArgs.Set(0, aPersonalityId);
       
   517 		ret = SendReceive(EUsbGetDescription, ipcArgs);
       
   518 		}
       
   519 	else
       
   520 		{
       
   521 		// just in case caller tries to free the memory before checking the return code
       
   522 		aLocalizedPersonalityDescriptor = NULL;
       
   523 		}
       
   524 
       
   525 	return ret;	
       
   526 	}
       
   527 	
       
   528 EXPORT_C TInt RUsb::GetCurrentPersonalityId(TInt& aPersonalityId)
       
   529 	{
       
   530 	LOG_LINE
       
   531 	LOG_FUNC
       
   532 
       
   533     CUsbLog::Write(KLogStub, KNullDesC8());
       
   534     CStubber* stubber = CStubber::NewL();
       
   535     TApiBehavior beh( KUsbManStubAgentDll, EGetCurrentPersonalityId, 0, 0, KNullDesC8 );
       
   536     stubber -> InvokeApi( beh );
       
   537     
       
   538     delete stubber;
       
   539     stubber = NULL;    
       
   540     
       
   541     if ( beh.iOutput != KNullDesC8 )
       
   542         {
       
   543         if ( !beh.iOutput.Compare( _L8( "KUsbPersonalityIdPCSuite" ) ) )
       
   544             aPersonalityId = KUsbPersonalityIdPCSuite;
       
   545         else if ( !beh.iOutput.Compare( _L8( "KUsbPersonalityIdMS" ) ) )
       
   546             aPersonalityId = KUsbPersonalityIdMS;
       
   547         else if ( !beh.iOutput.Compare( _L8( "KUsbPersonalityIdPTP" ) ) )
       
   548             aPersonalityId = KUsbPersonalityIdPTP;
       
   549         else if ( !beh.iOutput.Compare( _L8( "KUsbPersonalityIdMTP" ) ) )
       
   550             aPersonalityId = KUsbPersonalityIdMTP;
       
   551         else if ( !beh.iOutput.Compare( _L8( "KUsbPersonalityIdPCSuite" ) ) )
       
   552             aPersonalityId = KUsbPersonalityIdPCSuite;
       
   553         else
       
   554         	{}
       
   555         }
       
   556     else
       
   557         {
       
   558 		TPckg<TInt> pkg0(aPersonalityId);
       
   559 		TInt ret = SendReceive(EUsbGetCurrentPersonalityId, TIpcArgs(&pkg0));
       
   560 		aPersonalityId = static_cast<TInt>(pkg0());
       
   561 		return ret;	
       
   562         }
       
   563 
       
   564     return beh.iCompleteCode;
       
   565 	}
       
   566 
       
   567 EXPORT_C TInt RUsb::GetSupportedClasses(TInt aPersonalityId, RArray<TUid>& aClassUids)
       
   568 	{
       
   569 	LOG_LINE
       
   570 	LOG_FUNC
       
   571 
       
   572 	TInt ret = KErrNone;
       
   573 	HBufC8* buf = NULL;
       
   574 	// +1 for the actual count of personality ids
       
   575 	TRAP(ret, buf = HBufC8::NewL((KUsbMaxSupportedClasses + 1)*sizeof (TInt32)));
       
   576 	if (ret != KErrNone)
       
   577 		{
       
   578 		return ret;
       
   579 		}
       
   580 
       
   581 	TPtr8 ptr8 = buf->Des();
       
   582 	ret = SendReceive(EUsbGetSupportedClasses, TIpcArgs(aPersonalityId, &ptr8));
       
   583 		
       
   584 	if (ret == KErrNone)
       
   585 		{
       
   586 		const TInt32* recvedIds = reinterpret_cast<const TInt32*>(buf->Ptr());
       
   587 		if (!recvedIds)
       
   588 			{
       
   589 			delete buf;
       
   590 			return KErrCorrupt;
       
   591 			}
       
   592 			
       
   593 		TInt arraySize = *recvedIds++;
       
   594 		// Copy received supported class ids to aClassUids
       
   595 		for (TInt i = 0; i < arraySize; i++)
       
   596 			{
       
   597 			if (recvedIds)
       
   598 				{
       
   599 				ret = aClassUids.Append(TUid::Uid(*recvedIds++));
       
   600 				if(ret!=KErrNone)
       
   601 					{
       
   602 					//Remove all the ids appended so far (assume the last append failed, because
       
   603 					//the only reason to fail is if the array couldn't grow to accommodate another
       
   604 					//element).
       
   605 					//It would be easier to just reset the array, but we never specified that
       
   606 					//aClassUids should be an empty array, nor did we specify that this method
       
   607 					//might empty the array. To maintain exisiting behaviour we should return
       
   608 					//aClassUids to the state it was in when this method was called.
       
   609 					TInt last = aClassUids.Count() - 1;
       
   610 					while(i>0)
       
   611 						{
       
   612 						aClassUids.Remove(last);
       
   613 						i--;
       
   614 						last--;
       
   615 						}	
       
   616 					break;
       
   617 					}
       
   618 				}
       
   619 			else
       
   620 				{
       
   621 				ret = KErrCorrupt;
       
   622 				break;
       
   623 				}
       
   624 			}
       
   625 		}
       
   626 		
       
   627 	delete buf;
       
   628 	return ret;
       
   629 	}
       
   630 	
       
   631 EXPORT_C TInt RUsb::ClassSupported(TInt aPersonalityId, TUid aClassUid, TBool& aSupported)
       
   632 	{
       
   633 	LOG_LINE
       
   634 	LOG_FUNC
       
   635 
       
   636 	TPckg<TInt32>  	pkg2(aSupported);
       
   637 	TIpcArgs ipcArgs(aPersonalityId, aClassUid.iUid, &pkg2);
       
   638 	
       
   639 	TInt ret = SendReceive(EUsbClassSupported, ipcArgs);
       
   640 	
       
   641 	if (ret == KErrNone)
       
   642 		{
       
   643 		aSupported = static_cast<TBool>(pkg2());		
       
   644 		}
       
   645 		
       
   646 	return ret;
       
   647 	}
       
   648 	
       
   649 EXPORT_C TInt RUsb::GetPersonalityIds(RArray<TInt>& aPersonalityIds)
       
   650 	{
       
   651 	LOG_LINE
       
   652 	LOG_FUNC
       
   653 
       
   654 	TInt ret = KErrNone;
       
   655 	HBufC8* buf = NULL;
       
   656 	// +1 for the actual count of personality ids
       
   657 	TRAP(ret, buf = HBufC8::NewL((KUsbMaxSupportedPersonalities + 1)*sizeof (TInt)));
       
   658 	if (ret != KErrNone)
       
   659 		{
       
   660 		return ret;
       
   661 		}
       
   662 
       
   663 	TPtr8 ptr8 = buf->Des();
       
   664 	ret = SendReceive(EUsbGetPersonalityIds, TIpcArgs(&ptr8));
       
   665 		
       
   666 	if (ret == KErrNone)
       
   667 		{
       
   668 		const TInt* recvedIds = reinterpret_cast<const TInt*>(buf->Ptr());
       
   669 		if (!recvedIds)
       
   670 			{
       
   671 			delete buf;
       
   672 			return KErrCorrupt;
       
   673 			}
       
   674 			
       
   675 		TInt arraySize = *recvedIds++;
       
   676 		// Copy received personality ids to aPersonalityIds
       
   677 		for (TInt i = 0; i < arraySize; i++)
       
   678 			{
       
   679 			if (recvedIds)
       
   680 				{		
       
   681 				ret = aPersonalityIds.Append(*recvedIds++);
       
   682 				
       
   683 				if(ret!=KErrNone)
       
   684 					{
       
   685 					//Remove all the ids appended so far (assume the last append failed, because
       
   686 					//the only reason to fail is if the array couldn't grow to accommodate another
       
   687 					//element).
       
   688 					//It would be easier to just reset the array, but we never specified that
       
   689 					//aPersonalityIds should be an empty array, nor did we specify that this method
       
   690 					//might empty the array. To maintain exisiting behaviour we should return
       
   691 					//aPersonalityIds to the state it was in when this method was called.
       
   692 					TInt last = aPersonalityIds.Count() - 1;
       
   693 					while(i>0)
       
   694 						{
       
   695 						aPersonalityIds.Remove(last);
       
   696 						i--;
       
   697 						last--;
       
   698 						}	
       
   699 					break;
       
   700 					}
       
   701 				}
       
   702 			else
       
   703 				{
       
   704 				ret = KErrCorrupt;
       
   705 				break;
       
   706 				}
       
   707 			}
       
   708 		}
       
   709 		
       
   710 	delete buf;
       
   711 	return ret;
       
   712 	}
       
   713 	
       
   714 EXPORT_C TInt RUsb::__DbgMarkHeap()
       
   715 	{
       
   716 #ifdef _DEBUG
       
   717     return SendReceive(EUsbDbgMarkHeap);
       
   718 #else
       
   719     return KErrNone;
       
   720 #endif
       
   721 	}
       
   722 
       
   723 EXPORT_C TInt RUsb::__DbgCheckHeap(TInt aCount)
       
   724 	{
       
   725 #ifdef _DEBUG
       
   726     return SendReceive(EUsbDbgCheckHeap, TIpcArgs(aCount));
       
   727 #else
       
   728 	(void)aCount; // not used for Release builds
       
   729     return KErrNone;
       
   730 #endif
       
   731 	}
       
   732 
       
   733 EXPORT_C TInt RUsb::__DbgMarkEnd(TInt aCount)
       
   734 	{
       
   735 #ifdef _DEBUG
       
   736     return SendReceive(EUsbDbgMarkEnd, TIpcArgs(aCount));
       
   737 #else
       
   738 	(void)aCount; // not used for Release builds
       
   739     return KErrNone;
       
   740 #endif
       
   741 	}
       
   742 
       
   743 EXPORT_C TInt RUsb::__DbgFailNext(TInt aCount)
       
   744 	{
       
   745 #ifdef _DEBUG
       
   746     return SendReceive(EUsbDbgFailNext, TIpcArgs(aCount));
       
   747 #else
       
   748 	(void)aCount; // not used for Release builds
       
   749     return KErrNone;
       
   750 #endif
       
   751 	}
       
   752 
       
   753 EXPORT_C TInt RUsb::__DbgAlloc()
       
   754 	{
       
   755 #ifdef _DEBUG
       
   756     return SendReceive(EUsbDbgAlloc);
       
   757 #else
       
   758     return KErrNone;
       
   759 #endif
       
   760 	}
       
   761 
       
   762 EXPORT_C void panic()
       
   763 	{
       
   764 	_USB_PANIC(KUsbCliPncCat, EUsbPanicRemovedExport);
       
   765 	}
       
   766 
       
   767 EXPORT_C TInt RUsb::SetCtlSessionMode(TBool aValue)
       
   768 	{
       
   769 	LOG_LINE
       
   770 	LOG_FUNC
       
   771 
       
   772 //    CUsbLog::Write(KLogStub, KNullDesC8());
       
   773 //    CStubber* stubber = CStubber::NewL();
       
   774 //    TApiBehavior beh( KUsbManStubAgentDll, ESetCtlSessionMode, 0, 0, KNullDesC8 );
       
   775 //    stubber -> InvokeApi( beh );
       
   776 //    
       
   777 //    delete stubber;
       
   778 //    stubber = NULL;    
       
   779 //    
       
   780 //    if ( beh.iOutput != KNullDesC8 )
       
   781 //        {
       
   782 //        return KErrNone;
       
   783 //        }
       
   784 //    else
       
   785 //        {
       
   786         TPckg<TBool> pkg(aValue);
       
   787         return SendReceive(EUsbSetCtlSessionMode, TIpcArgs(&pkg)); 
       
   788 //        }
       
   789     
       
   790 	}
       
   791 
       
   792 EXPORT_C TInt RUsb::BusRequest()
       
   793 	{
       
   794 	LOG_LINE
       
   795 	LOG_FUNC
       
   796 
       
   797 	return SendReceive(EUsbBusRequest);
       
   798 	}
       
   799 
       
   800 EXPORT_C TInt RUsb::BusRespondSrp()
       
   801 	{
       
   802 	LOG_LINE
       
   803 	LOG_FUNC
       
   804 
       
   805 	return SendReceive(EUsbBusRespondSrp);
       
   806 	}
       
   807 
       
   808 EXPORT_C TInt RUsb::BusClearError()
       
   809 	{
       
   810 	LOG_LINE
       
   811 	LOG_FUNC
       
   812 
       
   813 	return SendReceive(EUsbBusClearError);
       
   814 	}
       
   815 
       
   816 
       
   817 EXPORT_C TInt RUsb::BusDrop()
       
   818 	{
       
   819 	LOG_LINE
       
   820 	LOG_FUNC
       
   821 
       
   822 	return SendReceive(EUsbBusDrop);
       
   823 	}
       
   824 
       
   825 EXPORT_C void RUsb::MessageNotification(TRequestStatus& aStatus, TInt& aMessage)
       
   826 	{
       
   827 	LOG_LINE
       
   828 	LOG_FUNC
       
   829 
       
   830 	iMessagePkg.Set((TUint8*)&aMessage, sizeof(TInt), sizeof(TInt));
       
   831 
       
   832 	SendReceive(EUsbRegisterMessageObserver, TIpcArgs(&iMessagePkg), aStatus);
       
   833 	}
       
   834 
       
   835 EXPORT_C void RUsb::MessageNotificationCancel()
       
   836 	{
       
   837 	LOG_LINE
       
   838 	LOG_FUNC
       
   839 
       
   840 	SendReceive(EUsbCancelMessageObserver);
       
   841 	}
       
   842 
       
   843 EXPORT_C void RUsb::HostEventNotification(TRequestStatus& aStatus,
       
   844 										  TDeviceEventInformation& aDeviceInformation)
       
   845 	{
       
   846 	LOG_LINE
       
   847 	LOG_FUNC
       
   848 
       
   849 	iHostPkg.Set((TUint8*)&aDeviceInformation, sizeof(TDeviceEventInformation), sizeof(TDeviceEventInformation));
       
   850 
       
   851 	SendReceive(EUsbRegisterHostObserver, TIpcArgs(&iHostPkg), aStatus);
       
   852 	}
       
   853 	
       
   854 EXPORT_C void RUsb::HostEventNotificationCancel()
       
   855 	{
       
   856 	LOG_LINE
       
   857 	LOG_FUNC
       
   858 
       
   859 	SendReceive(EUsbCancelHostObserver);
       
   860 	}
       
   861 
       
   862 EXPORT_C TInt RUsb::EnableFunctionDriverLoading()
       
   863 	{
       
   864 	LOG_LINE
       
   865 	LOG_FUNC
       
   866 
       
   867 	return SendReceive(EUsbEnableFunctionDriverLoading);
       
   868 	}
       
   869 
       
   870 EXPORT_C void RUsb::DisableFunctionDriverLoading()
       
   871 	{
       
   872 	LOG_LINE
       
   873 	LOG_FUNC
       
   874 
       
   875 	SendReceive(EUsbDisableFunctionDriverLoading);
       
   876 	}
       
   877 
       
   878 EXPORT_C TInt RUsb::GetSupportedLanguages(TUint aDeviceId, RArray<TUint>& aLangIds)
       
   879 	{
       
   880 	LOG_LINE
       
   881 	LOG_FUNC
       
   882 
       
   883 	aLangIds.Reset();
       
   884 
       
   885 	TInt ret = KErrNone;
       
   886 	HBufC8* buf = NULL;
       
   887 	// +1 for the actual count of language ids
       
   888 	TRAP(ret, buf = HBufC8::NewL((KUsbMaxSupportedLanguageIds + 1)*sizeof (TUint)));
       
   889 	if (ret != KErrNone)
       
   890 		{
       
   891 		return ret;
       
   892 		}
       
   893 
       
   894 	TPtr8 ptr8 = buf->Des();
       
   895 	ret = SendReceive(EUsbGetSupportedLanguages, TIpcArgs(aDeviceId, &ptr8));
       
   896 		
       
   897 	if (ret == KErrNone)
       
   898 		{
       
   899 		const TUint* recvedIds = reinterpret_cast<const TUint*>(buf->Ptr());
       
   900 		if (!recvedIds)
       
   901 			{
       
   902 			delete buf;
       
   903 			return KErrCorrupt;
       
   904 			}
       
   905 			
       
   906 		TInt arraySize = *recvedIds++;
       
   907 		// Copy received language ids to aLangIds
       
   908 		for (TInt i = 0; i < arraySize; i++)
       
   909 			{
       
   910 			ret = aLangIds.Append(*recvedIds++); // increments by sizeof(TUint)
       
   911 			if ( ret )
       
   912 				{
       
   913 				aLangIds.Reset();
       
   914 				break;
       
   915 				}
       
   916 			}
       
   917 		}
       
   918 		
       
   919 	delete buf;	
       
   920 	return ret;
       
   921 	}
       
   922 	
       
   923 EXPORT_C TInt RUsb::GetManufacturerStringDescriptor(TUint aDeviceId, TUint aLangId, TName& aString)
       
   924 	{
       
   925 	LOG_LINE
       
   926 	LOG_FUNC
       
   927 
       
   928 	return SendReceive(EUsbGetManufacturerStringDescriptor, TIpcArgs(aDeviceId, aLangId, &aString));
       
   929 	}
       
   930 
       
   931 EXPORT_C TInt RUsb::GetProductStringDescriptor(TUint aDeviceId, TUint aLangId, TName& aString)
       
   932 	{
       
   933 	LOG_LINE
       
   934 	LOG_FUNC
       
   935 
       
   936 	return SendReceive(EUsbGetProductStringDescriptor, TIpcArgs(aDeviceId, aLangId, &aString));
       
   937 	}
       
   938 
       
   939 EXPORT_C TInt RUsb::GetOtgDescriptor(TUint aDeviceId, TOtgDescriptor& aDescriptor)
       
   940 	{
       
   941 	LOG_LINE
       
   942 	LOG_FUNC
       
   943 		
       
   944 	TPckg<TOtgDescriptor> otgDescPkg(aDescriptor);
       
   945 	
       
   946 	TIpcArgs args;
       
   947 	args.Set(0, aDeviceId);
       
   948 	args.Set(1, &otgDescPkg);
       
   949 
       
   950 	return SendReceive(EUsbGetOtgDescriptor, args);
       
   951 	}
       
   952 
       
   953 
       
   954 EXPORT_C TInt RUsb::RequestSession()
       
   955 	{
       
   956 	LOG_LINE
       
   957 	LOG_FUNC
       
   958 
       
   959 	return SendReceive(EUsbRequestSession);
       
   960 	}
       
   961 
       
   962 EXPORT_C TInt RUsb::GetDetailedDescription(TInt aPersonalityId, HBufC*& aLocalizedPersonalityDescriptor)
       
   963 	{
       
   964 	LOG_LINE
       
   965 	LOG_FUNC
       
   966 
       
   967  	TInt ret = KErrNone;
       
   968 	// caller is responsible for freeing up memory allocated for aLocalizedPersonalityDescriptor
       
   969 	TRAP(ret, aLocalizedPersonalityDescriptor = HBufC::NewL(KUsbStringDescStringMaxSize));
       
   970 	if (ret == KErrNone)
       
   971 		{
       
   972 		TPtr ptr = aLocalizedPersonalityDescriptor->Des();
       
   973 		TIpcArgs ipcArgs(0, &ptr);
       
   974 		ipcArgs.Set(0, aPersonalityId);
       
   975 		ret = SendReceive(EUsbGetDetailedDescription, ipcArgs);
       
   976 		}
       
   977 	else
       
   978 		{
       
   979 		// just in case caller tries to free the memory before checking the return code
       
   980 		aLocalizedPersonalityDescriptor = NULL;
       
   981 		}
       
   982 
       
   983 	return ret; 
       
   984 	}
       
   985 
       
   986 EXPORT_C TInt RUsb::GetPersonalityProperty(TInt aPersonalityId, TUint32& aProperty)
       
   987 	{
       
   988 	LOG_LINE
       
   989 	LOG_FUNC
       
   990 
       
   991     CUsbLog::Write(KLogStub, KNullDesC8());
       
   992 	TPckg<TUint32> pkg(aProperty);
       
   993 	TInt ret = SendReceive(EUsbGetPersonalityProperty, TIpcArgs(aPersonalityId, &pkg));
       
   994 	if (ret == KErrNone)
       
   995 		{
       
   996 		aProperty = static_cast<TUint32>(pkg());
       
   997 		}
       
   998 
       
   999 //    CUsbLog::Write(KLogStub, KNullDesC8());
       
  1000 //    CStubber* stubber = CStubber::NewL();
       
  1001 //    TApiBehavior beh( KUsbManStubAgentDll, EGetPersonalityProperty, 0, 0, KNullDesC8 );
       
  1002 //    stubber -> InvokeApi( beh );
       
  1003 //    
       
  1004 //    delete stubber;
       
  1005 //    stubber = NULL;
       
  1006 //
       
  1007 //    if ( beh.iOutput != KNullDesC8 )
       
  1008 //        {
       
  1009 //        if ( !beh.iOutput.Compare( _L8( "stub" ) ) )
       
  1010 //            {
       
  1011 //            CUsbLog::Write(KLogStub, KNullDesC8());
       
  1012 //            TRequestStatus stat;
       
  1013 //            TInt message;
       
  1014 //            MessageNotification(stat,message);
       
  1015 //            DeviceStateNotificationCancel();
       
  1016 //            TUsbDeviceState aState;
       
  1017 //            GetDeviceState(aState);
       
  1018 //            DeviceStateNotification( KUsbAllStates, aState, stat );
       
  1019 //            TryStop(stat);
       
  1020 //            User::WaitForRequest(stat);
       
  1021 //            TInt personalityId;
       
  1022 //            GetCurrentPersonalityId(personalityId);
       
  1023 //            TryStart(personalityId,stat);
       
  1024 //            User::WaitForRequest(stat);
       
  1025 //            }
       
  1026 //        else
       
  1027 //            {}
       
  1028 //        }
       
  1029     
       
  1030 	return ret;	
       
  1031 	}